From 3e7f93e18034ba2e5216fea264e9123f7c34902e Mon Sep 17 00:00:00 2001 From: Kevin Dalley Date: Wed, 17 Mar 2004 04:56:46 +0000 Subject: [PATCH] * client/main.C, api/boinc_diagnostics.C, api/boinc_api.C: use boinc_set_signal rather than signal, so that signals are handled only when not already ignored. svn path=/trunk/boinc/; revision=3086 --- api/boinc_api.C | 33 +++++++++++++--------------- api/boinc_api.h | 7 ++++++ api/boinc_diagnostics.C | 48 ++++++++++++++++++++++++++++++----------- client/main.C | 15 +++++++------ 4 files changed, 67 insertions(+), 36 deletions(-) diff --git a/api/boinc_api.C b/api/boinc_api.C index 30955e98c8..f6195ab6fd 100644 --- a/api/boinc_api.C +++ b/api/boinc_api.C @@ -40,7 +40,9 @@ #include #include #include +#ifdef HAVE_SIGNAL_H #include +#endif #include #include #include @@ -55,6 +57,7 @@ using namespace std; #include "error_numbers.h" #include "app_ipc.h" #include "boinc_api.h" +#include "sighandle.h" // @@ -105,12 +108,6 @@ static int set_timer(double period); // Forward declare implementation functions - Windows Platform Only. LONG CALLBACK boinc_catch_signal(EXCEPTION_POINTERS *ExceptionInfo); -#else - -// Forward declare implementation functions - POSIX Platform Only. -extern void boinc_catch_signal(int signal); -extern void boinc_quit(int sig); - #endif @@ -409,19 +406,19 @@ void boinc_error_release(int iExitCode, const char *pszFormat, ...) #ifdef HAVE_SIGNAL_H int boinc_install_signal_handlers() { - signal(SIGHUP, boinc_catch_signal); // terminal line hangup - signal(SIGINT, boinc_catch_signal); // interrupt program - signal(SIGQUIT, boinc_quit); // quit program - signal(SIGILL, boinc_catch_signal); // illegal instruction - signal(SIGABRT, boinc_catch_signal); // abort(2) call - signal(SIGBUS, boinc_catch_signal); // bus error - signal(SIGSEGV, boinc_catch_signal); // segmentation violation - signal(SIGSYS, boinc_catch_signal); // system call given invalid argument - signal(SIGPIPE, boinc_catch_signal); // write on a pipe with no reader + boinc_set_signal_handler(SIGHUP, boinc_catch_signal); + boinc_set_signal_handler(SIGINT, boinc_catch_signal); + boinc_set_signal_handler(SIGQUIT, boinc_catch_signal); + boinc_set_signal_handler(SIGILL, boinc_catch_signal); + boinc_set_signal_handler(SIGABRT, boinc_catch_signal); + boinc_set_signal_handler(SIGBUS, boinc_catch_signal); + boinc_set_signal_handler(SIGSEGV, boinc_catch_signal); + boinc_set_signal_handler(SIGSYS, boinc_catch_signal); + boinc_set_signal_handler(SIGPIPE, boinc_catch_signal); return 0; } -void boinc_catch_signal(int signal) { +RETSIGTYPE boinc_catch_signal(int signal) { switch(signal) { case SIGHUP: fprintf(stderr, "SIGHUP: terminal line hangup"); break; case SIGINT: fprintf(stderr, "SIGINT: interrupt program"); break; @@ -442,7 +439,7 @@ void boinc_quit(int sig) { time_to_quit = true; } -#endif +#endif /* HAVE_SIGNAL_H */ // **************************************************************************** @@ -681,7 +678,7 @@ int boinc_thread_cpu_time(double& cpu, double& ws) { #ifdef _WIN32 static void CALLBACK on_timer(UINT uTimerID, UINT uMsg, DWORD dwUser, DWORD dw1, DWORD dw2) { #else -static void on_timer(int a) { +static RETSIGTYPE on_timer(int a) { #endif if (!ready_to_checkpoint) { diff --git a/api/boinc_api.h b/api/boinc_api.h index 0b9848cb2f..d5ace888dd 100755 --- a/api/boinc_api.h +++ b/api/boinc_api.h @@ -148,4 +148,11 @@ extern APP_CLIENT_SHM *app_client_shm; /////////// IMPLEMENTATION STUFF ENDS HERE +// Forward declare implementation functions - POSIX Platform Only. +#ifdef HAVE_SIGNAL_H +extern RETSIGTYPE boinc_catch_signal(int signal); +extern void boinc_quit(int sig); +#endif + + #endif diff --git a/api/boinc_diagnostics.C b/api/boinc_diagnostics.C index 6cb73814ee..a10edd8c8c 100644 --- a/api/boinc_diagnostics.C +++ b/api/boinc_diagnostics.C @@ -20,12 +20,16 @@ #ifdef _WIN32 #include #include "win/Stackwalker.h" +#else +#include "config.h" #endif #include #include #include +#ifdef HAVE_SIGNAL_H #include +#endif #include "boinc_diagnostics.h" #include "app_ipc.h" @@ -381,20 +385,40 @@ void boinc_info_release(const char *pszFormat, ...) #ifdef HAVE_SIGNAL_H -// Forward declare implementation specific functions - POSIX Platform Only. -void boinc_catch_signal(int signal); -void boinc_quit(int sig); +// Forward declare implementation functions - POSIX Platform Only. +extern void boinc_catch_signal(int signal); +extern void boinc_quit(int sig); + +// Set a signal handler but only if it is not currently ignored +void boinc_set_signal_handler(int sig) +{ +#ifdef HAVE_SIGACTION + struct sigaction temp; + sigaction(sig, NULL, &temp); + if (temp.sa_handler != SIG_IGN) { + temp.sa_handler = boinc_catch_signal; + sigemptyset(&temp.sa_mask); + sigaction(sig, &temp, NULL); + } +#else + void (*temp)(int); + temp = signal(sig, boinc_catch_signal); + if (temp == SIG_IGN) { + signal(sig, SIG_IGN); + } +#endif +} int boinc_install_signal_handlers() { - signal(SIGHUP, boinc_catch_signal); // terminal line hangup - signal(SIGINT, boinc_catch_signal); // interrupt program - signal(SIGQUIT, boinc_quit); // quit program - signal(SIGILL, boinc_catch_signal); // illegal instruction - signal(SIGABRT, boinc_catch_signal); // abort(2) call - signal(SIGBUS, boinc_catch_signal); // bus error - signal(SIGSEGV, boinc_catch_signal); // segmentation violation - signal(SIGSYS, boinc_catch_signal); // system call given invalid argument - signal(SIGPIPE, boinc_catch_signal); // write on a pipe with no reader + boinc_set_signal_handler(SIGHUP); + boinc_set_signal_handler(SIGINT); + boinc_set_signal_handler(SIGQUIT); + boinc_set_signal_handler(SIGILL); + boinc_set_signal_handler(SIGABRT); + boinc_set_signal_handler(SIGBUS); + boinc_set_signal_handler(SIGSEGV); + boinc_set_signal_handler(SIGSYS); + boinc_set_signal_handler(SIGPIPE); return 0; } diff --git a/client/main.C b/client/main.C index 19346ccada..39c725147b 100644 --- a/client/main.C +++ b/client/main.C @@ -28,10 +28,12 @@ #endif #ifndef _WIN32 +#include "config.h" #ifdef HAVE_UNISTD_H #include #endif #ifdef HAVE_SIGNAL_H +#include "sighandle.h" #include #endif #endif @@ -228,14 +230,15 @@ int boinc_execution_engine(int argc, char** argv) { // Unix/Linux console controls #ifndef WIN32 // Handle quit signals gracefully - signal(SIGHUP, quit_client); - signal(SIGINT, quit_client); - signal(SIGQUIT, quit_client); + boinc_set_signal_handler(SIGHUP, quit_client); + boinc_set_signal_handler(SIGINT, quit_client); + boinc_set_signal_handler(SIGQUIT, quit_client); + boinc_set_signal_handler(SIGTERM, quit_client); #ifdef SIGPWR - signal(SIGPWR, quit_client); + boinc_set_signal_handler(SIGPWR, quit_client); #endif - signal(SIGTSTP, susp_client); - signal(SIGCONT, resume_client); + boinc_set_signal_handler_force(SIGTSTP, susp_client); + boinc_set_signal_handler_force(SIGCONT, resume_client); #endif // Windows console controls