]> git.ipfire.org Git - thirdparty/systemd.git/blobdiff - src/coredump/coredump.c
build-sys: use #if Y instead of #ifdef Y everywhere
[thirdparty/systemd.git] / src / coredump / coredump.c
index 270af630cf9053f488364df54cc9e36dbdc467f5..300d6479039d77197a13269eed8bea215b35f581 100644 (file)
@@ -23,7 +23,7 @@
 #include <sys/xattr.h>
 #include <unistd.h>
 
-#ifdef HAVE_ELFUTILS
+#if HAVE_ELFUTILS
 #include <dwarf.h>
 #include <elfutils/libdwfl.h>
 #endif
@@ -144,10 +144,10 @@ static int parse_config(void) {
         };
 
         return config_parse_many_nulstr(PKGSYSCONFDIR "/coredump.conf",
-                                 CONF_PATHS_NULSTR("systemd/coredump.conf.d"),
-                                 "Coredump\0",
-                                 config_item_table_lookup, items,
-                                 false, NULL);
+                                        CONF_PATHS_NULSTR("systemd/coredump.conf.d"),
+                                        "Coredump\0",
+                                        config_item_table_lookup, items,
+                                        false, NULL);
 }
 
 static inline uint64_t storage_size_max(void) {
@@ -156,7 +156,7 @@ static inline uint64_t storage_size_max(void) {
 
 static int fix_acl(int fd, uid_t uid) {
 
-#ifdef HAVE_ACL
+#if HAVE_ACL
         _cleanup_(acl_freep) acl_t acl = NULL;
         acl_entry_t entry;
         acl_permset_t permset;
@@ -393,7 +393,7 @@ static int save_external_coredump(
                 goto fail;
         }
 
-#if defined(HAVE_XZ) || defined(HAVE_LZ4)
+#if HAVE_XZ || HAVE_LZ4
         /* If we will remove the coredump anyway, do not compress. */
         if (arg_compress && !maybe_remove_external_coredump(NULL, st.st_size)) {
 
@@ -564,7 +564,7 @@ static int compose_open_fds(pid_t pid, char **open_fds) {
                 }
 
                 FOREACH_LINE(line, fdinfo, break) {
-                        fputs(line, stream);
+                        fputs_unlocked(line, stream);
                         if (!endswith(line, "\n"))
                                 fputc('\n', stream);
                 }
@@ -695,6 +695,19 @@ static int change_uid_gid(const char *context[]) {
         return drop_privileges(uid, gid, 0);
 }
 
+static bool is_journald_crash(const char *context[_CONTEXT_MAX]) {
+        assert(context);
+
+        return streq_ptr(context[CONTEXT_UNIT], SPECIAL_JOURNALD_SERVICE);
+}
+
+static bool is_pid1_crash(const char *context[_CONTEXT_MAX]) {
+        assert(context);
+
+        return streq_ptr(context[CONTEXT_UNIT], SPECIAL_INIT_SCOPE) ||
+                streq_ptr(context[CONTEXT_PID], "1");
+}
+
 #define SUBMIT_COREDUMP_FIELDS 4
 
 static int submit_coredump(
@@ -715,7 +728,7 @@ static int submit_coredump(
         assert(n_iovec_allocated >= n_iovec + SUBMIT_COREDUMP_FIELDS);
         assert(input_fd >= 0);
 
-        journald_crash = streq_ptr(context[CONTEXT_UNIT], SPECIAL_JOURNALD_SERVICE);
+        journald_crash = is_journald_crash(context);
 
         /* Vacuum before we write anything again */
         (void) coredump_vacuum(-1, arg_keep_free, arg_max_use);
@@ -736,7 +749,7 @@ static int submit_coredump(
                 const char *coredump_filename;
 
                 coredump_filename = strjoina("COREDUMP_FILENAME=", filename);
-                IOVEC_SET_STRING(iovec[n_iovec++], coredump_filename);
+                iovec[n_iovec++] = IOVEC_MAKE_STRING(coredump_filename);
         } else if (arg_storage == COREDUMP_STORAGE_EXTERNAL)
                 log_info("The core will not be stored: size %"PRIu64" is greater than %"PRIu64" (the configured maximum)",
                          coredump_size, arg_external_size_max);
@@ -752,7 +765,7 @@ static int submit_coredump(
         if (r < 0)
                 return log_error_errno(r, "Failed to drop privileges: %m");
 
-#ifdef HAVE_ELFUTILS
+#if HAVE_ELFUTILS
         /* Try to get a strack trace if we can */
         if (coredump_size <= arg_process_size_max) {
                 _cleanup_free_ char *stacktrace = NULL;
@@ -787,15 +800,14 @@ log:
         if (journald_crash) {
                 /* We cannot log to the journal, so just print the MESSAGE.
                  * The target was set previously to something safe. */
-                log_struct(LOG_ERR, core_message, NULL);
+                log_dispatch(LOG_ERR, 0, core_message);
                 return 0;
         }
 
-        if (core_message)
-                IOVEC_SET_STRING(iovec[n_iovec++], core_message);
+        iovec[n_iovec++] = IOVEC_MAKE_STRING(core_message);
 
         if (truncated)
-                IOVEC_SET_STRING(iovec[n_iovec++], "COREDUMP_TRUNCATED=yes");
+                iovec[n_iovec++] = IOVEC_MAKE_STRING("COREDUMP_TRUNCATED=1");
 
         /* Optionally store the entire coredump in the journal */
         if (arg_storage == COREDUMP_STORAGE_JOURNAL) {
@@ -805,11 +817,9 @@ log:
                         /* Store the coredump itself in the journal */
 
                         r = allocate_journal_field(coredump_fd, (size_t) coredump_size, &coredump_data, &sz);
-                        if (r >= 0) {
-                                iovec[n_iovec].iov_base = coredump_data;
-                                iovec[n_iovec].iov_len = sz;
-                                n_iovec++;
-                        } else
+                        if (r >= 0)
+                                iovec[n_iovec++] = IOVEC_MAKE(coredump_data, sz);
+                        else
                                 log_warning_errno(r, "Failed to attach the core to the journal entry: %m");
                 } else
                         log_info("The core will not be stored: size %"PRIu64" is greater than %"PRIu64" (the configured maximum)",
@@ -1058,7 +1068,7 @@ static char* set_iovec_field(struct iovec iovec[27], size_t *n_iovec, const char
 
         x = strappend(field, value);
         if (x)
-                IOVEC_SET_STRING(iovec[(*n_iovec)++], x);
+                iovec[(*n_iovec)++] = IOVEC_MAKE_STRING(x);
         return x;
 }
 
@@ -1103,14 +1113,14 @@ static int gather_pid_metadata(
                 log_warning_errno(r, "Failed to get EXE, ignoring: %m");
 
         if (cg_pid_get_unit(pid, &context[CONTEXT_UNIT]) >= 0) {
-                if (!streq(context[CONTEXT_UNIT], SPECIAL_JOURNALD_SERVICE)) {
+                if (!is_journald_crash((const char**) context)) {
                         /* OK, now we know it's not the journal, hence we can make use of it now. */
                         log_set_target(LOG_TARGET_JOURNAL_OR_KMSG);
                         log_open();
                 }
 
                 /* If this is PID 1 disable coredump collection, we'll unlikely be able to process it later on. */
-                if (streq(context[CONTEXT_UNIT], SPECIAL_INIT_SCOPE)) {
+                if (is_pid1_crash((const char**) context)) {
                         log_notice("Due to PID 1 having crashed coredump collection will now be turned off.");
                         (void) write_string_file("/proc/sys/kernel/core_pattern", "|/bin/false", 0);
                 }
@@ -1150,7 +1160,7 @@ static int gather_pid_metadata(
         if (sd_pid_get_owner_uid(pid, &owner_uid) >= 0) {
                 r = asprintf(&t, "COREDUMP_OWNER_UID=" UID_FMT, owner_uid);
                 if (r > 0)
-                        IOVEC_SET_STRING(iovec[(*n_iovec)++], t);
+                        iovec[(*n_iovec)++] = IOVEC_MAKE_STRING(t);
         }
 
         if (sd_pid_get_slice(pid, &t) >= 0)
@@ -1206,7 +1216,7 @@ static int gather_pid_metadata(
 
         t = strjoin("COREDUMP_TIMESTAMP=", context[CONTEXT_TIMESTAMP], "000000", NULL);
         if (t)
-                IOVEC_SET_STRING(iovec[(*n_iovec)++], t);
+                iovec[(*n_iovec)++] = IOVEC_MAKE_STRING(t);
 
         if (safe_atoi(context[CONTEXT_SIGNAL], &signo) >= 0 && SIGNAL_VALID(signo))
                 set_iovec_field(iovec, n_iovec, "COREDUMP_SIGNAL_NAME=SIG", signal_to_string(signo));
@@ -1241,16 +1251,14 @@ static int process_kernel(int argc, char* argv[]) {
 
         n_iovec = n_to_free;
 
-        IOVEC_SET_STRING(iovec[n_iovec++], "MESSAGE_ID=" SD_MESSAGE_COREDUMP_STR);
+        iovec[n_iovec++] = IOVEC_MAKE_STRING("MESSAGE_ID=" SD_MESSAGE_COREDUMP_STR);
 
         assert_cc(2 == LOG_CRIT);
-        IOVEC_SET_STRING(iovec[n_iovec++], "PRIORITY=2");
+        iovec[n_iovec++] = IOVEC_MAKE_STRING("PRIORITY=2");
 
         assert(n_iovec <= ELEMENTSOF(iovec));
 
-        if (STRPTR_IN_SET(context[CONTEXT_UNIT],
-                          SPECIAL_JOURNALD_SERVICE,
-                          SPECIAL_INIT_SCOPE))
+        if (is_journald_crash((const char**) context) || is_pid1_crash((const char**) context))
                 r = submit_coredump((const char**) context,
                                     iovec, ELEMENTSOF(iovec), n_iovec,
                                     STDIN_FILENO);
@@ -1315,7 +1323,8 @@ static int process_backtrace(int argc, char *argv[]) {
                         log_error_errno(r, "Failed to parse journal entry on stdin: %m");
                         goto finish;
                 }
-                if (r == 1)
+                if (r == 1 ||                        /* complete entry */
+                    journal_importer_eof(&importer)) /* end of data */
                         break;
         }
 
@@ -1333,15 +1342,15 @@ static int process_backtrace(int argc, char *argv[]) {
                         r = log_oom();
                         goto finish;
                 }
-                IOVEC_SET_STRING(iovec[n_iovec++], message);
+                iovec[n_iovec++] = IOVEC_MAKE_STRING(message);
         } else {
                 for (i = 0; i < importer.iovw.count; i++)
                         iovec[n_iovec++] = importer.iovw.iovec[i];
         }
 
-        IOVEC_SET_STRING(iovec[n_iovec++], "MESSAGE_ID=" SD_MESSAGE_BACKTRACE_STR);
+        iovec[n_iovec++] = IOVEC_MAKE_STRING("MESSAGE_ID=" SD_MESSAGE_BACKTRACE_STR);
         assert_cc(2 == LOG_CRIT);
-        IOVEC_SET_STRING(iovec[n_iovec++], "PRIORITY=2");
+        iovec[n_iovec++] = IOVEC_MAKE_STRING("PRIORITY=2");
 
         assert(n_iovec <= n_allocated);