summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRussell Bryant <russell@russellbryant.com>2007-02-23 23:25:22 +0000
committerRussell Bryant <russell@russellbryant.com>2007-02-23 23:25:22 +0000
commitdbd7334dccf82e5516f81ec03d73e2c00fe9b2e2 (patch)
tree764597501b5bb973496ac35b0f06b10f2897689b
parentb85a5ffbe3f687c1ad5a5f6ea0831c805b10fdf6 (diff)
Merged revisions 56505 via svnmerge from
https://origsvn.digium.com/svn/asterisk/branches/1.4 ................ r56505 | russell | 2007-02-23 17:24:18 -0600 (Fri, 23 Feb 2007) | 16 lines Merged revisions 56504 via svnmerge from https://origsvn.digium.com/svn/asterisk/branches/1.2 ........ r56504 | russell | 2007-02-23 17:20:55 -0600 (Fri, 23 Feb 2007) | 8 lines Fix up a couple more signal handlers to not do bad things that could cause various undesirable results. The other day, I made Asterisk deadlock by hitting Control-C because of a bad signal handler. Now, signal handlers just set a flag and write to an alert pipe for the flag to be handled. Then, there is another thread that is monitoring for these flags. If being run in console mode, it is just the main thread. If Asterisk is in the background, a thread is created to do it. ........ ................ git-svn-id: https://origsvn.digium.com/svn/asterisk/trunk@56506 65c4cc65-6c06-0410-ace0-fbb531ad65f3
-rw-r--r--main/asterisk.c70
1 files changed, 48 insertions, 22 deletions
diff --git a/main/asterisk.c b/main/asterisk.c
index ee91b73d5..04809b98d 100644
--- a/main/asterisk.c
+++ b/main/asterisk.c
@@ -235,7 +235,11 @@ static pthread_t consolethread = AST_PTHREADT_NULL;
static char randompool[256];
-static unsigned int need_reload;
+static int sig_alert_pipe[2] = { -1, -1 };
+static struct {
+ unsigned int need_reload:1;
+ unsigned int need_quit:1;
+} sig_flags;
#if !defined(LOW_MEMORY)
struct file_version {
@@ -1052,11 +1056,14 @@ static void urg_handler(int num)
static void hup_handler(int num)
{
+ int a = 0;
if (option_verbose > 1)
printf("Received HUP signal -- Reloading configs\n");
if (restartnow)
execvp(_argv[0], _argv);
- need_reload = 1;
+ sig_flags.need_reload = 1;
+ if (sig_alert_pipe[1] != -1)
+ write(sig_alert_pipe[1], &a, sizeof(a));
signal(num, hup_handler);
}
@@ -1271,7 +1278,12 @@ static void quit_handler(int num, int nice, int safeshutdown, int restart)
static void __quit_handler(int num)
{
- quit_handler(num, 0, 1, 0);
+ int a = 0;
+ sig_flags.need_quit = 1;
+ if (sig_alert_pipe[1] != -1)
+ write(sig_alert_pipe[1], &a, sizeof(a));
+ /* There is no need to restore the signal handler here, since the app
+ * is going to exit */
}
static const char *fix_header(char *outbuf, int maxout, const char *s, char *cmp)
@@ -2192,11 +2204,6 @@ static void ast_remotecontrol(char * data)
}
}
}
-
- if (need_reload) {
- need_reload = 0;
- ast_module_reload(NULL);
- }
}
printf("\nDisconnected from Asterisk server\n");
}
@@ -2402,6 +2409,26 @@ static void ast_readconfig(void)
ast_config_destroy(cfg);
}
+static void *monitor_sig_flags(void *unused)
+{
+ for (;;) {
+ struct pollfd p = { sig_alert_pipe[0], POLLIN, 0 };
+ int a;
+ poll(&p, 1, -1);
+ if (sig_flags.need_reload) {
+ sig_flags.need_reload = 0;
+ ast_module_reload(NULL);
+ }
+ if (sig_flags.need_quit) {
+ sig_flags.need_quit = 0;
+ quit_handler(0, 0, 1, 0);
+ }
+ read(sig_alert_pipe[0], &a, sizeof(a));
+ }
+
+ return NULL;
+}
+
int main(int argc, char *argv[])
{
int c;
@@ -2836,6 +2863,9 @@ int main(int argc, char *argv[])
if (ast_opt_no_fork)
consolethread = pthread_self();
+ if (pipe(sig_alert_pipe))
+ sig_alert_pipe[0] = sig_alert_pipe[1] = -1;
+
ast_set_flag(&ast_options, AST_OPT_FLAG_FULLY_BOOTED);
pthread_sigmask(SIG_UNBLOCK, &sigs, NULL);
@@ -2850,6 +2880,14 @@ int main(int argc, char *argv[])
/* Console stuff now... */
/* Register our quit function */
char title[256];
+ pthread_attr_t attr;
+ pthread_t dont_care;
+
+ pthread_attr_init(&attr);
+ pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);
+ ast_pthread_create(&dont_care, &attr, monitor_sig_flags, NULL);
+ pthread_attr_destroy(&attr);
+
set_icon("Asterisk");
snprintf(title, sizeof(title), "Asterisk Console on '%s' (pid %ld)", hostname, (long)ast_mainpid);
set_title(title);
@@ -2873,22 +2911,10 @@ int main(int argc, char *argv[])
ast_log(LOG_WARNING, "Failed to open /dev/null to recover from dead console. Bad things will happen!\n");
break;
}
- if (need_reload) {
- need_reload = 0;
- ast_module_reload(NULL);
- }
}
}
- /* Do nothing */
- for (;;) { /* apparently needed for Mac OS X */
- struct pollfd p = { -1 /* no descriptor */, 0, 0 };
- poll(&p, 0, -1);
- /* SIGHUP will cause this to break out of poll() */
- if (need_reload) {
- need_reload = 0;
- ast_module_reload(NULL);
- }
- }
+
+ monitor_sig_flags(NULL);
return 0;
}