chiark / gitweb /
dbus: consolidate service SysV conditionals
[elogind.git] / src / main.c
index 54ebb0b08cb8f67b6996a5f52eaab9c8c276e73d..7edd6b5811b145d312ac0f0ced09945e6b72d7cb 100644 (file)
@@ -51,6 +51,7 @@
 #include "label.h"
 #include "build.h"
 #include "strv.h"
+#include "def.h"
 
 static enum {
         ACTION_RUN,
@@ -227,7 +228,6 @@ static int parse_proc_cmdline_word(const char *word) {
         static const char * const rlmap[] = {
                 "emergency", SPECIAL_EMERGENCY_TARGET,
                 "-b",        SPECIAL_EMERGENCY_TARGET,
-                "b",         SPECIAL_EMERGENCY_TARGET,
                 "single",    SPECIAL_RESCUE_TARGET,
                 "-s",        SPECIAL_RESCUE_TARGET,
                 "s",         SPECIAL_RESCUE_TARGET,
@@ -546,6 +546,11 @@ static int parse_proc_cmdline(void) {
         int r;
         size_t l;
 
+        /* Don't read /proc/cmdline if we are in a container, since
+         * that is only relevant for the host system */
+        if (detect_container(NULL) > 0)
+                return 0;
+
         if ((r = read_one_line_file("/proc/cmdline", &line)) < 0) {
                 log_warning("Failed to read /proc/cmdline, ignoring: %s", strerror(-r));
                 return 0;
@@ -626,6 +631,9 @@ static int parse_argv(int argc, char *argv[]) {
         assert(argc >= 1);
         assert(argv);
 
+        if (getpid() == 1)
+                opterr = 0;
+
         while ((c = getopt_long(argc, argv, "hDbsz:", options, NULL)) >= 0)
 
                 switch (c) {
@@ -820,15 +828,30 @@ static int parse_argv(int argc, char *argv[]) {
                         break;
                 }
 
-        /* PID 1 will get the kernel arguments as parameters, which we
-         * ignore and unconditionally read from
-         * /proc/cmdline. However, we need to ignore those arguments
-         * here. */
-        if (getpid() != 1 && optind < argc) {
+        if (optind < argc && getpid() != 1) {
+                /* Hmm, when we aren't run as init system
+                 * let's complain about excess arguments */
+
                 log_error("Excess arguments.");
                 return -EINVAL;
         }
 
+        if (detect_container(NULL) > 0) {
+                char **a;
+
+                /* All /proc/cmdline arguments the kernel didn't
+                 * understand it passed to us. We're not really
+                 * interested in that usually since /proc/cmdline is
+                 * more interesting and complete. With one exception:
+                 * if we are run in a container /proc/cmdline is not
+                 * relevant for the container, hence we rely on argv[]
+                 * instead. */
+
+                for (a = argv; a < argv + argc; a++)
+                        if ((r = parse_proc_cmdline_word(*a)) < 0)
+                                return r;
+        }
+
         return 0;
 }
 
@@ -996,7 +1019,7 @@ int main(int argc, char *argv[]) {
 
         if (getpid() == 1) {
                 arg_running_as = MANAGER_SYSTEM;
-                log_set_target(LOG_TARGET_SYSLOG_OR_KMSG);
+                log_set_target(detect_container(NULL) > 0 ? LOG_TARGET_CONSOLE : LOG_TARGET_SYSLOG_OR_KMSG);
 
                 /* This might actually not return, but cause a
                  * reexecution */
@@ -1093,6 +1116,9 @@ int main(int argc, char *argv[]) {
                  * kernel that don't really make sense for us. */
                 unsetenv("HOME");
                 unsetenv("TERM");
+
+                /* All other variables are left as is, so that clients
+                 * can still read them via /proc/1/environ */
         }
 
         /* Move out of the way, so that we won't block unmounts */