chiark / gitweb /
journal: don't allow adding invalid matches to the context
[elogind.git] / src / journal / journald.c
index 9d45762e2521b5c27437593e55df4691a2ca1cbb..8ce9ce858bc88e44a9b284675089961dce2310d6 100644 (file)
 #include <sys/statvfs.h>
 
 #include <systemd/sd-journal.h>
-#include <systemd/sd-login.h>
 #include <systemd/sd-messages.h>
 #include <systemd/sd-daemon.h>
 
+#ifdef HAVE_LOGIND
+#include <systemd/sd-login.h>
+#endif
+
 #include "mkdir.h"
 #include "hashmap.h"
 #include "journal-file.h"
@@ -330,7 +333,10 @@ static void server_rotate(Server *s) {
         if (s->runtime_journal) {
                 r = journal_file_rotate(&s->runtime_journal);
                 if (r < 0)
-                        log_error("Failed to rotate %s: %s", s->runtime_journal->path, strerror(-r));
+                        if (s->runtime_journal)
+                                log_error("Failed to rotate %s: %s", s->runtime_journal->path, strerror(-r));
+                        else
+                                log_error("Failed to create new runtime journal: %s", strerror(-r));
                 else
                         server_fix_perms(s, s->runtime_journal, 0);
         }
@@ -338,7 +344,11 @@ static void server_rotate(Server *s) {
         if (s->system_journal) {
                 r = journal_file_rotate(&s->system_journal);
                 if (r < 0)
-                        log_error("Failed to rotate %s: %s", s->system_journal->path, strerror(-r));
+                        if (s->system_journal)
+                                log_error("Failed to rotate %s: %s", s->system_journal->path, strerror(-r));
+                        else
+                                log_error("Failed to create new system journal: %s", strerror(-r));
+
                 else
                         server_fix_perms(s, s->system_journal, 0);
         }
@@ -346,7 +356,10 @@ static void server_rotate(Server *s) {
         HASHMAP_FOREACH_KEY(f, k, s->user_journals, i) {
                 r = journal_file_rotate(&f);
                 if (r < 0)
-                        log_error("Failed to rotate %s: %s", f->path, strerror(-r));
+                        if (f->path)
+                                log_error("Failed to rotate %s: %s", f->path, strerror(-r));
+                        else
+                                log_error("Failed to create user journal: %s", strerror(-r));
                 else {
                         hashmap_replace(s->user_journals, k, f);
                         server_fix_perms(s, s->system_journal, PTR_TO_UINT32(k));
@@ -469,7 +482,9 @@ static void dispatch_message_real(
 
         if (ucred) {
                 uint32_t audit;
+#ifdef HAVE_LOGIND
                 uid_t owner;
+#endif
 
                 realuid = ucred->uid;
 
@@ -528,6 +543,7 @@ static void dispatch_message_real(
                                 IOVEC_SET_STRING(iovec[n++], cgroup);
                 }
 
+#ifdef HAVE_LOGIND
                 if (sd_pid_get_session(ucred->pid, &t) >= 0) {
                         session = strappend("_SYSTEMD_SESSION=", t);
                         free(t);
@@ -536,7 +552,12 @@ static void dispatch_message_real(
                                 IOVEC_SET_STRING(iovec[n++], session);
                 }
 
-                if (sd_pid_get_unit(ucred->pid, &t) >= 0) {
+                if (sd_pid_get_owner_uid(ucred->uid, &owner) >= 0)
+                        if (asprintf(&owner_uid, "_SYSTEMD_OWNER_UID=%lu", (unsigned long) owner) >= 0)
+                                IOVEC_SET_STRING(iovec[n++], owner_uid);
+#endif
+
+                if (cg_pid_get_unit(ucred->pid, &t) >= 0) {
                         unit = strappend("_SYSTEMD_UNIT=", t);
                         free(t);
 
@@ -544,10 +565,6 @@ static void dispatch_message_real(
                                 IOVEC_SET_STRING(iovec[n++], unit);
                 }
 
-                if (sd_pid_get_owner_uid(ucred->uid, &owner) >= 0)
-                        if (asprintf(&owner_uid, "_SYSTEMD_OWNER_UID=%lu", (unsigned long) owner) >= 0)
-                                IOVEC_SET_STRING(iovec[n++], owner_uid);
-
 #ifdef HAVE_SELINUX
                 if (label) {
                         selinux_context = malloc(sizeof("_SELINUX_CONTEXT=") + label_len);
@@ -1682,8 +1699,8 @@ static int stdout_stream_new(Server *s) {
         }
 
 #ifdef HAVE_SELINUX
-        if (getpeercon(fd, &stream->security_context) < 0)
-                log_error("Failed to determine peer security context.");
+        if (getpeercon(fd, &stream->security_context) < 0 && errno != ENOPROTOOPT)
+                log_error("Failed to determine peer security context: %m");
 #endif
 
         if (shutdown(fd, SHUT_WR) < 0) {
@@ -1758,6 +1775,17 @@ static int parse_kernel_timestamp(char **_p, usec_t *t) {
         return 1;
 }
 
+static bool is_us(const char *pid) {
+        pid_t t;
+
+        assert(pid);
+
+        if (parse_pid(pid, &t) < 0)
+                return false;
+
+        return t == getpid();
+}
+
 static void proc_kmsg_line(Server *s, const char *p) {
         struct iovec iovec[N_IOVEC_META_FIELDS + 7];
         char *message = NULL, *syslog_priority = NULL, *syslog_pid = NULL, *syslog_facility = NULL, *syslog_identifier = NULL, *source_time = NULL;
@@ -1797,6 +1825,11 @@ static void proc_kmsg_line(Server *s, const char *p) {
         } else {
                 read_identifier(&p, &identifier, &pid);
 
+                /* Avoid any messages we generated ourselves via
+                 * log_info() and friends. */
+                if (is_us(pid))
+                        goto finish;
+
                 if (s->forward_to_syslog)
                         forward_syslog(s, priority, identifier, p, NULL, NULL);
 
@@ -1822,6 +1855,7 @@ static void proc_kmsg_line(Server *s, const char *p) {
 
         dispatch_message(s, iovec, n, ELEMENTSOF(iovec), NULL, NULL, NULL, 0, priority);
 
+finish:
         free(message);
         free(syslog_priority);
         free(syslog_identifier);
@@ -2764,7 +2798,7 @@ int main(int argc, char *argv[]) {
                 return EXIT_FAILURE;
         }
 
-        log_set_target(LOG_TARGET_CONSOLE);
+        log_set_target(LOG_TARGET_SAFE);
         log_set_facility(LOG_SYSLOG);
         log_parse_environment();
         log_open();