]> git.ipfire.org Git - thirdparty/dovecot/core.git/commitdiff
lib: Add lib_signals_syscall_error()
authorTimo Sirainen <timo.sirainen@dovecot.fi>
Tue, 2 May 2017 12:41:04 +0000 (15:41 +0300)
committerVille Savolainen <ville.savolainen@dovecot.fi>
Thu, 11 May 2017 13:12:42 +0000 (16:12 +0300)
src/lib/lib-signals.c
src/lib/lib-signals.h

index 49037526620baa28a67d16fc4e09ad963803195a..7796a4f1a5a8eae497f4c4273c233f1b6784c8e8 100644 (file)
@@ -4,8 +4,10 @@
 #include "ioloop.h"
 #include "fd-close-on-exec.h"
 #include "fd-set-nonblock.h"
+#include "write-full.h"
 #include "lib-signals.h"
 
+#include <stdio.h>
 #include <signal.h>
 #include <unistd.h>
 
@@ -312,6 +314,26 @@ void lib_signals_reset_ioloop(void)
        }
 }
 
+void lib_signals_syscall_error(const char *prefix)
+{
+       /* @UNSAFE: We're in a signal handler. It's very limited what is
+          allowed in here. Especially strerror() isn't at least officially
+          allowed. */
+       char errno_buf[MAX_INT_STRLEN], *errno_str;
+       errno_str = dec2str_buf(errno_buf, errno);
+
+       size_t prefix_len = strlen(prefix);
+       size_t errno_str_len = strlen(errno_str);
+       char buf[prefix_len + errno_str_len + 1];
+
+       memcpy(buf, prefix, prefix_len);
+       memcpy(buf + prefix_len, errno_str, errno_str_len);
+       buf[prefix_len + errno_str_len] = '\n';
+       if (write_full(STDERR_FILENO, buf, prefix_len + errno_str_len + 1) < 0) {
+               /* can't really do anything */
+       }
+}
+
 void lib_signals_init(void)
 {
        int i;
index e1eb18ef55758b7e31a06fd09b6ed89d24b91525..85b240fdfc35225097decb8d2fa2d70e4454113a 100644 (file)
@@ -42,6 +42,10 @@ void lib_signals_unset_handler(int signo,
    the delayed signals to work when using multiple I/O loops. */
 void lib_signals_reset_ioloop(void);
 
+/* Log a syscall error inside a (non-delayed) signal handler where i_error() is
+   unsafe. errno number will be appended to the prefix. */
+void lib_signals_syscall_error(const char *prefix);
+
 void lib_signals_init(void);
 void lib_signals_deinit(void);