diff options
-rw-r--r-- | debug.c | 30 | ||||
-rw-r--r-- | debug.h | 1 | ||||
-rw-r--r-- | radsecproxy.c | 34 |
3 files changed, 55 insertions, 10 deletions
@@ -19,9 +19,11 @@ #include <syslog.h> #include <errno.h> #include "debug.h" +#include "util.h" static char *debug_ident = NULL; static uint8_t debug_level = DBG_INFO; +static char *debug_filepath = NULL; static FILE *debug_file = NULL; static int debug_syslogfacility = 0; static uint8_t debug_timestamp = 0; @@ -68,11 +70,12 @@ int debug_set_destination(char *dest) { int i; if (!strncasecmp(dest, "file:///", 8)) { - debug_file = fopen(dest + 7, "a"); + debug_filepath = stringcopy(dest + 7, 0); + debug_file = fopen(debug_filepath, "a"); if (!debug_file) { debug_file = stderr; debugx(1, DBG_ERR, "Failed to open logfile %s\n%s", - dest + 7, strerror(errno)); + debug_filepath, strerror(errno)); } setvbuf(debug_file, NULL, _IONBF, 0); return 1; @@ -97,6 +100,29 @@ int debug_set_destination(char *dest) { exit(1); } +void debug_reopen_log() { + extern int errno; + + /* not a file, noop, return success */ + if (!debug_filepath) { + debug(DBG_ERR, "skipping reopen"); + return; + } + + if (debug_file != stderr) + fclose(debug_file); + + debug_file = fopen(debug_filepath, "a"); + if (debug_file) + debug(DBG_ERR, "Reopened logfile %s", debug_filepath); + else { + debug_file = stderr; + debug(DBG_ERR, "Failed to open logfile %s, using stderr\n%s", + debug_filepath, strerror(errno)); + } + setvbuf(debug_file, NULL, _IONBF, 0); +} + void debug_logit(uint8_t level, const char *format, va_list ap) { struct timeval now; char *timebuf; @@ -22,3 +22,4 @@ uint8_t debug_get_level(); void debug(uint8_t level, char *format, ...); void debugx(int status, uint8_t level, char *format, ...); int debug_set_destination(char *dest); +void debug_reopen_log(); diff --git a/radsecproxy.c b/radsecproxy.c index 794af5b..97bd560 100644 --- a/radsecproxy.c +++ b/radsecproxy.c @@ -3012,10 +3012,10 @@ void getmainconfig(const char *configfile) { setprotoopts(i, listenargs[i], sourcearg[i]); } -void getargs(int argc, char **argv, uint8_t *foreground, uint8_t *pretend, uint8_t *loglevel, char **configfile) { +void getargs(int argc, char **argv, uint8_t *foreground, uint8_t *pretend, uint8_t *loglevel, char **configfile, char **pidfile) { int c; - while ((c = getopt(argc, argv, "c:d:fpv")) != -1) { + while ((c = getopt(argc, argv, "c:d:i:fpv")) != -1) { switch (c) { case 'c': *configfile = optarg; @@ -3028,6 +3028,9 @@ void getargs(int argc, char **argv, uint8_t *foreground, uint8_t *pretend, uint8 case 'f': *foreground = 1; break; + case 'i': + *pidfile = optarg; + break; case 'p': *pretend = 1; break; @@ -3055,7 +3058,7 @@ void getargs(int argc, char **argv, uint8_t *foreground, uint8_t *pretend, uint8 return; usage: - debugx(1, DBG_ERR, "Usage:\n%s [ -c configfile ] [ -d debuglevel ] [ -f ] [ -p ] [ -v ]", argv[0]); + debugx(1, DBG_ERR, "Usage:\n%s [ -c configfile ] [ -d debuglevel ] [ -f ] [ -i pidfile ] [ -p ] [ -v ]", argv[0]); } #ifdef SYS_SOLARIS9 @@ -3081,13 +3084,17 @@ void *sighandler(void *arg) { for(;;) { sigemptyset(&sigset); + sigaddset(&sigset, SIGHUP); sigaddset(&sigset, SIGPIPE); sigwait(&sigset, &sig); - /* only get SIGPIPE right now, so could simplify below code */ switch (sig) { case 0: /* completely ignoring this */ break; + case SIGHUP: + debug(DBG_INFO, "sighandler: got SIGHUP"); + debug_reopen_log(); + break; case SIGPIPE: debug(DBG_WARN, "sighandler: got SIGPIPE, TLS write error?"); break; @@ -3097,12 +3104,20 @@ void *sighandler(void *arg) { } } +int createpidfile(const char *pidfile) { + int r; + FILE *f = fopen(pidfile, "w"); + if (f) + r = fprintf(f, "%d\n", getpid()); + return f && !fclose(f) && r >= 0; +} + int main(int argc, char **argv) { pthread_t sigth; sigset_t sigset; struct list_node *entry; uint8_t foreground = 0, pretend = 0, loglevel = 0; - char *configfile = NULL; + char *configfile = NULL, *pidfile = NULL; struct clsrvconf *srvconf; int i; @@ -3115,7 +3130,7 @@ int main(int argc, char **argv) { /* needed even if no TLS/DTLS transport */ sslinit(); - getargs(argc, argv, &foreground, &pretend, &loglevel, &configfile); + getargs(argc, argv, &foreground, &pretend, &loglevel, &configfile, &pidfile); if (loglevel) debug_set_level(loglevel); getmainconfig(configfile ? configfile : CONFIG_MAIN); @@ -3140,9 +3155,12 @@ int main(int argc, char **argv) { debug_timestamp_on(); debug(DBG_INFO, "radsecproxy revision $Rev$ starting"); - + if (pidfile && !createpidfile(pidfile)) + debugx(1, DBG_ERR, "failed to create pidfile %s: %s", pidfile, strerror(errno)); + sigemptyset(&sigset); - /* exit on all but SIGPIPE, ignore more? */ + /* exit on all but SIGHUP|SIGPIPE, ignore more? */ + sigaddset(&sigset, SIGHUP); sigaddset(&sigset, SIGPIPE); pthread_sigmask(SIG_BLOCK, &sigset, NULL); pthread_create(&sigth, NULL, sighandler, NULL); |