>From 62ce729510d87909775f2d2720735d2d4c12da1a Mon Sep 17 00:00:00 2001 From: Daniel Santos Date: Sun, 22 Jan 2012 04:50:38 -0600 Subject: Proper termination of wineserver and all processes when primary program terminates MIME-Version: 1.0 Content-Type: multipart/mixed; boundary="------------1.7.3.4" This is a multi-part message in MIME format. --------------1.7.3.4 Content-Type: text/plain; charset=UTF-8; format=fixed Content-Transfer-Encoding: 8bit --- dlls/ntdll/server.c | 3 --- server/fd.c | 13 ------------- server/main.c | 13 +++++++++++++ server/object.h | 13 +++++++++++++ server/process.c | 3 ++- 5 files changed, 28 insertions(+), 17 deletions(-) --------------1.7.3.4 Content-Type: text/x-patch; name="0002-Proper-termination-of-wineserver-and-all-processes-whe.txt" Content-Transfer-Encoding: 8bit Content-Disposition: attachment; filename="0002-Proper-termination-of-wineserver-and-all-processes-whe.txt" diff --git a/dlls/ntdll/server.c b/dlls/ntdll/server.c index 3f7a957..d0ad25b 100644 --- a/dlls/ntdll/server.c +++ b/dlls/ntdll/server.c @@ -82,9 +82,6 @@ WINE_DEFAULT_DEBUG_CHANNEL(server); * make targets (currently in server/Makefile.in) should probably be moved to * libs/libwineserver/Makefile.in or other autotools code modofied so it's built independent of * the wineserver. - * - Properly terminate wineserver when primary program exits. (Currently, auxiliary processes - * stick around and have to be manually killed after the main process/wineserver terminates. Also - * lock and socket files have to be manually cleaned up. * - Use more portable synchronization mechanism in new server code (currently, we're just directly * including pthread.h and using a pthread mutex). * - Discover any other server calls (aside from init_thread and select) that should only be called diff --git a/server/fd.c b/server/fd.c index 513197e..f0aa4b7 100644 --- a/server/fd.c +++ b/server/fd.c @@ -502,19 +502,6 @@ static inline void remove_epoll_user( struct fd *fd, int user ) } } -/* Obtain lock on wineserver_mutex, but only if we're running in-process */ -static void inline wineserver_lock() -{ - if(wineserver_is_inproc && pthread_mutex_lock(&wineserver_mutex)) - perror("wineserver: pthread_mutex_lock"); -} - -static void inline wineserver_unlock() -{ - if(wineserver_is_inproc && pthread_mutex_unlock(&wineserver_mutex)) - perror("wineserver: pthread_mutex_unlock"); -} - static inline void main_loop_epoll(void) { int i, ret, timeout; diff --git a/server/main.c b/server/main.c index 72d92e0..d9ce608 100644 --- a/server/main.c +++ b/server/main.c @@ -155,11 +155,24 @@ int main( int argc, char *argv[] ) return wineserver_start(argc, argv); } +void *ws_shutdown(void *smartie) { + shutdown_master_socket(); + return NULL; +} + +void wineserver_atexit (void) +{ + wineserver_lock(); + shutdown_master_socket(); + wineserver_unlock(); +} + void *wineserver_start_inproc(char *argv[]) { int argc = 0; while (argv[argc]) ++argc; wineserver_is_inproc = 1; + if(atexit(wineserver_atexit)) fatal_perror("failed to set atexit func"); wineserver_start(argc, argv); return 0; } diff --git a/server/object.h b/server/object.h index 51de21a..a6cb0a3 100644 --- a/server/object.h +++ b/server/object.h @@ -40,6 +40,19 @@ extern pthread_mutex_t wineserver_mutex; /* Synchronize access to wineserver data between threads */ extern int wineserver_is_inproc; +/* Obtain lock on wineserver_mutex, but only if we're running in-process */ +static void inline wineserver_lock() +{ + if(wineserver_is_inproc && pthread_mutex_lock(&wineserver_mutex)) + perror("wineserver: pthread_mutex_lock"); +} + +static void inline wineserver_unlock() +{ + if(wineserver_is_inproc && pthread_mutex_unlock(&wineserver_mutex)) + perror("wineserver: pthread_mutex_unlock"); +} + #define DEBUG_OBJECTS /* kernel objects */ diff --git a/server/process.c b/server/process.c index de3b594..3ef03d0 100644 --- a/server/process.c +++ b/server/process.c @@ -588,7 +588,8 @@ static void kill_all_processes(void) LIST_FOR_EACH_ENTRY( process, &process_list, struct process, entry ) { - if (process->running_threads) break; + /* when in-process, don't try to kill self */ + if (process->running_threads && process->unix_pid != getpid()) break; } if (&process->entry == &process_list) break; /* no process found */ terminate_process( process, NULL, 1 ); --------------1.7.3.4--