This repository has been archived by the owner. It is now read-only.
Permalink
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Browse files
Added patch to delay signaling threads until they are really gone (fi…
…xes Wine Staging Bug #473).
- Loading branch information
Showing
with
134 additions
and 22 deletions.
- +2 −1 README.md
- +2 −0 debian/changelog
- +21 −1 patches/patchinstall.sh
- +20 −20 patches/server-Shared_Memory/0002-server-Implement-support-for-global-and-local-shared.patch
- +1 −0 patches/server-Shared_Memory/definition
- +87 −0 patches/server-Signal_Thread/0001-server-Do-not-signal-thread-until-it-is-really-gone.patch
- +1 −0 patches/server-Signal_Thread/definition
| @@ -0,0 +1,87 @@ | ||
| From 67856c891a6d40c6e484f5f29db30a8899a39e04 Mon Sep 17 00:00:00 2001 | ||
| From: Sebastian Lackner <sebastian@fds-team.de> | ||
| Date: Mon, 19 Oct 2015 00:34:01 +0200 | ||
| Subject: server: Do not signal thread until it is really gone. | ||
|
|
||
| --- | ||
| server/thread.c | 22 ++++++++++++++++++++-- | ||
| server/thread.h | 1 + | ||
| 2 files changed, 21 insertions(+), 2 deletions(-) | ||
|
|
||
| diff --git a/server/thread.c b/server/thread.c | ||
| index 6383000..ba84bee 100644 | ||
| --- a/server/thread.c | ||
| +++ b/server/thread.c | ||
| @@ -195,6 +195,7 @@ static inline void init_thread_structure( struct thread *thread ) | ||
| thread->suspend = 0; | ||
| thread->desktop_users = 0; | ||
| thread->token = NULL; | ||
| + thread->exit_poll = NULL; | ||
|
|
||
| thread->creation_time = current_time; | ||
| thread->exit_time = 0; | ||
| @@ -316,6 +317,7 @@ static void destroy_thread( struct object *obj ) | ||
| list_remove( &thread->entry ); | ||
| cleanup_thread( thread ); | ||
| release_object( thread->process ); | ||
| + if (thread->exit_poll) remove_timeout_user( thread->exit_poll ); | ||
| if (thread->id) free_ptid( thread->id ); | ||
| if (thread->token) release_object( thread->token ); | ||
| } | ||
| @@ -333,7 +335,7 @@ static void dump_thread( struct object *obj, int verbose ) | ||
| static int thread_signaled( struct object *obj, struct wait_queue_entry *entry ) | ||
| { | ||
| struct thread *mythread = (struct thread *)obj; | ||
| - return (mythread->state == TERMINATED); | ||
| + return (mythread->state == TERMINATED && !mythread->exit_poll); | ||
| } | ||
|
|
||
| static unsigned int thread_map_access( struct object *obj, unsigned int access ) | ||
| @@ -1091,6 +1093,22 @@ int thread_get_inflight_fd( struct thread *thread, int client ) | ||
| return -1; | ||
| } | ||
|
|
||
| +static void check_terminated( void *arg ) | ||
| +{ | ||
| + struct thread *thread = arg; | ||
| + assert( thread->obj.ops == &thread_ops ); | ||
| + assert( thread->state == TERMINATED ); | ||
| + | ||
| + if (thread->unix_tid != -1 && !kill( thread->unix_tid, 0 )) | ||
| + { | ||
| + thread->exit_poll = add_timeout_user( -TICKS_PER_SEC / 100, check_terminated, thread ); | ||
| + return; | ||
| + } | ||
| + | ||
| + thread->exit_poll = NULL; | ||
| + wake_up( &thread->obj, 0 ); | ||
| +} | ||
| + | ||
| /* kill a thread on the spot */ | ||
| void kill_thread( struct thread *thread, int violent_death ) | ||
| { | ||
| @@ -1111,8 +1129,8 @@ void kill_thread( struct thread *thread, int violent_death ) | ||
| kill_console_processes( thread, 0 ); | ||
| debug_exit_thread( thread ); | ||
| abandon_mutexes( thread ); | ||
| - wake_up( &thread->obj, 0 ); | ||
| if (violent_death) send_thread_signal( thread, SIGQUIT ); | ||
| + check_terminated( thread ); | ||
| cleanup_thread( thread ); | ||
| remove_process_thread( thread->process, thread ); | ||
| release_object( thread ); | ||
| diff --git a/server/thread.h b/server/thread.h | ||
| index 2821991..ac9af24 100644 | ||
| --- a/server/thread.h | ||
| +++ b/server/thread.h | ||
| @@ -88,6 +88,7 @@ struct thread | ||
| timeout_t creation_time; /* Thread creation time */ | ||
| timeout_t exit_time; /* Thread exit time */ | ||
| struct token *token; /* security token associated with this thread */ | ||
| + struct timeout_user *exit_poll; /* poll if the thread/process has exited already */ | ||
| }; | ||
|
|
||
| struct thread_snapshot | ||
| -- | ||
| 2.6.1 | ||
|
|
| @@ -0,0 +1 @@ | ||
| Fixes: Do not signal threads until they are really gone |