00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012 #include <signal.h>
00013
00014 #include "assa/Assure.h"
00015 #include "assa/SigHandler.h"
00016
00017 using namespace ASSA;
00018
00019 #if !defined(WIN32)
00020
00021
00022
00023 EventHandler* SigHandler::m_signal_handlers [NSIG];
00024
00025 int
00026 SigHandler::
00027 in_range (int signum_)
00028 {
00029 trace_with_mask("SigHandler::in_range", SIGHAND);
00030
00031 if ( signum_ >= 1 && signum_ < NSIG) {
00032 return 0;
00033 }
00034 else {
00035 DL((SIGHAND,"signum_ %d is out of range [1;%d]\n", NSIG));
00036 return -1;
00037 }
00038 }
00039
00040 EventHandler *
00041 SigHandler::
00042 handler (int signum_, EventHandler* newh_)
00043 {
00044 trace_with_mask("SigHandler::handler(int, EH*)", SIGHAND);
00045
00046
00047 if (in_range(signum_) == -1)
00048 return 0;
00049
00050 EventHandler* oh = m_signal_handlers[signum_];
00051 m_signal_handlers[signum_] = newh_;
00052
00053 return oh;
00054 }
00055
00056 EventHandler *
00057 SigHandler::
00058 handler (int signum_)
00059 {
00060 trace_with_mask("SigHandler::handler", SIGHAND);
00061
00062 if ( in_range (signum_) == -1 )
00063 return 0;
00064
00065 return m_signal_handlers[signum_];
00066 }
00067
00068 int
00069 SigHandler::
00070 install (int signum_, EventHandler *new_hand_, SigAction *new_disp_,
00071 EventHandler **old_hand_, SigAction *old_disp_)
00072 {
00073 trace_with_mask("SigHandler::install", SIGHAND);
00074
00075 if (in_range (signum_) == -1)
00076 return -1;
00077
00078
00079
00080
00081 EventHandler* eh = handler(signum_, new_hand_);
00082
00083
00084 if (old_hand_ != 0)
00085 *old_hand_ = eh;
00086
00087
00088 if (old_disp_ != 0) {
00089 old_disp_->retrieve_action (signum_);
00090 old_disp_->handler ((C_SIG_HANDLER) SIG_DFL);
00091 }
00092
00093
00094 SigAction null_sa;
00095
00096 if (new_disp_ == 0)
00097 new_disp_ = &null_sa;
00098
00099
00100 new_disp_->handler((C_SIG_HANDLER) SigHandler::dispatch);
00101
00102 return new_disp_->register_action(signum_, old_disp_);
00103 }
00104
00105 int
00106 SigHandler::
00107 remove (int signum_, EventHandler* ,
00108 SigAction *new_disp_, SigAction *old_disp_)
00109 {
00110 trace_with_mask("SigHandler::remove", SIGHAND);
00111
00112 if (in_range(signum_) == -1)
00113 return -1;
00114
00115
00116
00117 SigAction sa ((C_SIG_HANDLER) SIG_DFL);
00118
00119 if (new_disp_ == 0) {
00120 new_disp_ = &sa;
00121 }
00122
00123 m_signal_handlers[signum_] = 0;
00124
00125 return new_disp_->register_action (signum_, old_disp_);
00126 }
00127
00128 void
00129 SigHandler::
00130 dispatch (int signum_)
00131 {
00132 trace_with_mask("SigHandler::dispatch", SIGHAND);
00133
00134
00135 int my_errno = errno;
00136
00137 EventHandler *eh = m_signal_handlers[signum_];
00138
00139 if (eh != 0 && eh->handle_signal(signum_) == -1) {
00140
00141
00142
00143 SigAction defact((C_SIG_HANDLER) SIG_DFL);
00144 m_signal_handlers[signum_] = 0;
00145 defact.register_action(signum_);
00146 }
00147
00148 errno = my_errno;
00149 }
00150
00151 #endif // !defined(WIN32)
00152