[PATCH 2/2] os: Add option to log to the systemd journal

William Douglas william.douglas at intel.com
Mon Sep 9 12:47:29 PDT 2013


Instead of just being able to log to a file on disk, allow option to
log to systemd's journal.

This can work with or without logging to a file enabled.

Signed-off-by: William Douglas <william.douglas at intel.com>
---
 configure.ac             | 14 ++++++++++++++
 include/xorg-config.h.in |  3 +++
 os/Makefile.am           |  2 +-
 os/log.c                 | 43 +++++++++++++++++++++++++++++++++++++++++++
 4 files changed, 61 insertions(+), 1 deletion(-)

diff --git a/configure.ac b/configure.ac
index 68b8762..9b61d7b 100644
--- a/configure.ac
+++ b/configure.ac
@@ -476,6 +476,10 @@ AC_ARG_WITH(module-dir,      AS_HELP_STRING([--with-module-dir=DIR],
 				  [Directory where modules are installed (default: $libdir/xorg/modules)]),
 				[ moduledir="$withval" ],
 				[ moduledir="${libdir}/xorg/modules" ])
+AC_ARG_ENABLE(systemd-logging, AS_HELP_STRING([--enable-systemd-logging],
+				  [Enable logging with systemd (default: disabled)]),
+				[ SYSTEMD_LOGGING=$enableval ],
+				[ SYSTEMD_LOGGING=no ])
 AC_ARG_ENABLE(filesystem-logging, AS_HELP_STRING([--disable-filesystem-logging],
 				  [Write log messages to the filesystem (default: enabled)]),
 				[ FILESYSTEM_LOGGING=$enableval ],
@@ -1487,6 +1491,16 @@ AC_MSG_RESULT([$with_sha1])
 AC_SUBST(SHA1_LIBS)
 AC_SUBST(SHA1_CFLAGS)
 
+AM_CONDITIONAL(SYSTEMD_LOGGING, [test "x$SYSTEMD_LOGGING" = xyes])
+if test "x$SYSTEMD_LOGGING" = xyes; then
+	AC_CHECK_HEADERS([systemd/sd-journal.h], [], AC_MSG_ERROR([systemd logging requires libsystemd journal header]))
+	AC_CHECK_HEADERS([syslog.h], [], AC_MSG_ERROR([systemd logging requires syslog header]))
+	AC_CHECK_LIB(systemd-journal, sd_journal_send, [], AC_MSG_ERROR([systemd logging requires libsystemd journal library]))
+	AC_DEFINE(SYSTEMD_LOGGING, 1, [Use systemd logging])
+	SYSTEMD_LIBS=-lsystemd-journal
+	AC_SUBST(SYSTEMD_LIBS)
+fi
+
 AM_CONDITIONAL(FILESYSTEM_LOGGING, [test "x$FILESYSTEM_LOGGING" = xyes])
 if test "x$FILESYSTEM_LOGGING" = xyes; then
 	AC_DEFINE(FILESYSTEM_LOGGING, 1, [Write log messages to the filesystem])
diff --git a/include/xorg-config.h.in b/include/xorg-config.h.in
index 93027c5..26a4054 100644
--- a/include/xorg-config.h.in
+++ b/include/xorg-config.h.in
@@ -142,6 +142,9 @@
 /* Define to 1 if you have the `seteuid' function. */
 #undef HAVE_SETEUID
 
+/* Use systemd logging */
+#undef SYSTEMD_LOGGING
+
 /* Use filesystem logging */
 #undef FILESYSTEM_LOGGING
 
diff --git a/os/Makefile.am b/os/Makefile.am
index 364b6da..6a210a3 100644
--- a/os/Makefile.am
+++ b/os/Makefile.am
@@ -24,7 +24,7 @@ libos_la_SOURCES = 	\
 	xstrans.c	\
 	xprintf.c	\
 	$(XORG_SRCS)
-libos_la_LIBADD = @SHA1_LIBS@ $(DLOPEN_LIBS) $(LTLIBOBJS)
+libos_la_LIBADD = @SHA1_LIBS@ $(DLOPEN_LIBS) $(LTLIBOBJS) $(SYSTEMD_LIBS)
 
 if SECURE_RPC
 libos_la_SOURCES += $(SECURERPC_SRCS)
diff --git a/os/log.c b/os/log.c
index 856fa0f..c728c1c 100644
--- a/os/log.c
+++ b/os/log.c
@@ -90,6 +90,13 @@ OR PERFORMANCE OF THIS SOFTWARE.
 #include "site.h"
 #include "opaque.h"
 
+#include <xorg-config.h>
+
+#ifdef SYSTEMD_LOGGING
+#include <syslog.h>
+#include <systemd/sd-journal.h>
+#endif
+
 #ifdef WIN32
 #include <process.h>
 #define getpid(x) _getpid(x)
@@ -108,7 +115,9 @@ void (*OsVendorVErrorFProc) (const char *, va_list args) = NULL;
 #endif
 
 static FILE *logFile = NULL;
+static FILE *systemdLogFile = NULL;
 static int logFileFd = -1;
+static int systemdLogFileFd = -1;
 static Bool logFlush = FALSE;
 static Bool logSync = FALSE;
 static int logVerbosity = DEFAULT_LOG_VERBOSITY;
@@ -236,7 +245,24 @@ LogInit(const char *fname, const char *backup)
         }
     }
 #endif
+#ifdef SYSTEMD_LOGGING
+    systemdLogFileFd = sd_journal_stream_fd("X", LOG_INFO, 1);
+    if (systemdLogFileFd < 0)
+        FatalError("Cannot open systemd log file\n");
+    systemdLogFile = fdopen(systemdLogFileFd, "w");
+    if (!systemdLogFile) {
+        close(systemdLogFileFd);
+        FatalError("Cannot open systemd log file object\n");
+    }
 
+    setvbuf(systemdLogFile, NULL, _IONBF, 0);
+
+    /* Flush saved log information. */
+    if (saveBuffer && bufferSize > 0) {
+        fwrite(saveBuffer, bufferPos, 1, systemdLogFile);
+        fflush(systemdLogFile);
+    }
+#endif
     /*
      * Unconditionally free the buffer, and flag that the buffer is no longer
      * needed.
@@ -267,6 +293,15 @@ LogClose(enum ExitCode error)
         logFileFd = -1;
     }
 #endif
+#ifdef SYSTEMD_LOGGING
+    if (systemdLogFile) {
+        ErrorFSigSafe("Server terminated %s (%d). Closing systemd log connection.\n",
+               (error == EXIT_NO_ERROR) ? "successfully" : "with error", error);
+        fclose(systemdLogFile);
+        systemdLogFile = NULL;
+        systemdLogFileFd = -1;
+    }
+#endif
 }
 
 Bool
@@ -530,6 +565,14 @@ LogSWrite(int verb, const char *buf, size_t len, Bool end_line)
             memcpy(saveBuffer + bufferPos, buf, len);
             bufferPos += len;
         }
+        if (inSignalContext && systemdLogFileFd >= 0) {
+            write(systemdLogFileFd, buf, len);
+        }
+        else if (!inSignalContext && systemdLogFile) {
+            fwrite(buf, len, 1, systemdLogFile);
+            if (logFlush)
+                fflush(systemdLogFile);
+        }
     }
 }
 
-- 
1.8.3.4



More information about the xorg-devel mailing list