#include <mLib/daemonize.h>
#include <mLib/darray.h>
#include <mLib/dstr.h>
+#include <mLib/macros.h>
+#include <mLib/mdup.h>
#include <mLib/mdwopt.h>
#include <mLib/quis.h>
#include <mLib/report.h>
#define f_noinput 64u
#define f_warn 128u
#define f_uclose 256u
+#define f_losing 512u
/*----- Main code ---------------------------------------------------------*/
die(EXIT_FAILURE, "unexpected background tag `%s'", q);
}
-static void dolog(int prio, const char *msg, ...)
+static void PRINTF_LIKE(2, 3) dolog(int prio, const char *msg, ...)
{
va_list ap;
dstr d = DSTR_INIT;
if (!p) {
if (f & f_command)
die(EXIT_FAILURE, "server dropped the connection");
+ f &= ~f_losing;
exit(0);
}
q = str_getword(&p);
if (!q)
return;
if (strcmp(q, "WARN") == 0)
- dolog(LOG_WARNING, p);
+ dolog(LOG_WARNING, "%s", p);
else if (strcmp(q, "TRACE") == 0)
- dolog(LOG_DEBUG, p);
+ dolog(LOG_DEBUG, "%s", p);
else if (!(f & f_command))
dolog(LOG_ERR, "unexpected output `%s %s'", q, p);
else if (strcmp(q, "FAIL") == 0) {
if (logfp)
writelog("error", d.buf);
else if (logname)
- die(EXIT_FAILURE, d.buf);
+ die(EXIT_FAILURE, "%s", d.buf);
if (f & f_syslog)
- syslog(LOG_ERR, d.buf);
+ syslog(LOG_ERR, "%s", d.buf);
dstr_destroy(&d);
}
}
static void sigdie(int sig)
{ cleanup(); signal(sig, SIG_DFL); raise(sig); }
-static void putarg(string_v *av, const char *fmt, ...)
+static void PRINTF_LIKE(2, 3) putarg(string_v *av, const char *fmt, ...)
{
va_list ap;
dstr d = DSTR_INIT;
uid_t u = -1;
gid_t g = -1;
int pfd[2], efd[2];
+ mdup_fd md[3];
pid_t kid;
struct sigaction sa;
sigset_t newmask, oldmask;
die(EXIT_FAILURE, "couldn't set `%s' as current directory: %s",
dir, strerror(errno));
}
- if (logname)
- logfile(logname);
if (!pidfile && (f & f_daemon) && ((f & f_syslog) || logname))
pidfile = "tripectl.pid";
if (pidfile && (pidfp = fopen(pidfile, "w")) == 0) {
if ((kid = fork()) < 0)
die(EXIT_FAILURE, "fork failed: %s", strerror(errno));
if (!kid) {
- dup2(pfd[1], STDIN_FILENO);
- dup2(pfd[1], STDOUT_FILENO);
- dup2(efd[1], STDERR_FILENO);
- close(pfd[0]); close(pfd[1]);
- close(efd[0]); close(efd[1]);
- if (logfp) fclose(logfp);
+ close(pfd[0]); close(efd[0]);
+ sigprocmask(SIG_SETMASK, &oldmask, 0);
+ md[0].cur = pfd[1]; md[0].want = STDIN_FILENO;
+ md[1].cur = pfd[1]; md[1].want = STDOUT_FILENO;
+ md[2].cur = efd[1]; md[2].want = STDERR_FILENO;
+ mdup(md, 3);
if (pidfp) fclose(pidfp);
closelog();
if (f & f_daemon) detachtty();
}
}
+ f |= f_losing; /* pessimism */
u_setugid(u, g);
+ if (logname)
+ logfile(logname);
if (f & f_daemon) {
if (daemonize())
die(EXIT_FAILURE, "error becoming daemon: %s", strerror(errno));