main.c revision ddfa5101a2e0d94571c10e2bbc7c38b60dc6cba1
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering/*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering This file is part of systemd.
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering Copyright 2010 Lennart Poettering
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering systemd is free software; you can redistribute it and/or modify it
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering under the terms of the GNU Lesser General Public License as published by
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering the Free Software Foundation; either version 2.1 of the License, or
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering (at your option) any later version.
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering systemd is distributed in the hope that it will be useful, but
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering WITHOUT ANY WARRANTY; without even the implied warranty of
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering Lesser General Public License for more details.
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering You should have received a copy of the GNU Lesser General Public License
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering along with systemd; If not, see <http://www.gnu.org/licenses/>.
58db254ade4fb2ef77de68f28c4f13814819f6a1Lennart Poetteringstatic ManagerRunningAs arg_running_as = _MANAGER_RUNNING_AS_INVALID;
58db254ade4fb2ef77de68f28c4f13814819f6a1Lennart Poetteringstatic bool arg_dump_core = true;
58db254ade4fb2ef77de68f28c4f13814819f6a1Lennart Poetteringstatic bool arg_crash_shell = false;
58db254ade4fb2ef77de68f28c4f13814819f6a1Lennart Poetteringstatic bool arg_confirm_spawn = false;
36d9205d669bcdcb04fa730d1f3549a9fc9a9001Tom Gundersenstatic bool arg_show_status = true;
36d9205d669bcdcb04fa730d1f3549a9fc9a9001Tom Gundersenstatic bool arg_switched_root = false;
801ad6a6a9cd8fbd58b9f9c27f20dbb3c87d47ddLennart Poetteringstatic char **arg_default_controllers = NULL;
801ad6a6a9cd8fbd58b9f9c27f20dbb3c87d47ddLennart Poetteringstatic char ***arg_join_controllers = NULL;
801ad6a6a9cd8fbd58b9f9c27f20dbb3c87d47ddLennart Poetteringstatic ExecOutput arg_default_std_output = EXEC_OUTPUT_JOURNAL;
801ad6a6a9cd8fbd58b9f9c27f20dbb3c87d47ddLennart Poetteringstatic ExecOutput arg_default_std_error = EXEC_OUTPUT_INHERIT;
801ad6a6a9cd8fbd58b9f9c27f20dbb3c87d47ddLennart Poetteringstatic usec_t arg_shutdown_watchdog = 10 * USEC_PER_MINUTE;
801ad6a6a9cd8fbd58b9f9c27f20dbb3c87d47ddLennart Poetteringstatic struct rlimit *arg_default_rlimit[RLIMIT_NLIMITS] = {};
801ad6a6a9cd8fbd58b9f9c27f20dbb3c87d47ddLennart Poetteringstatic uint64_t arg_capability_bounding_set_drop = 0;
801ad6a6a9cd8fbd58b9f9c27f20dbb3c87d47ddLennart Poetteringstatic nsec_t arg_timer_slack_nsec = (nsec_t) -1;
801ad6a6a9cd8fbd58b9f9c27f20dbb3c87d47ddLennart Poettering log_error("Caught <%s>, not dumping core.", signal_to_string(sig));
801ad6a6a9cd8fbd58b9f9c27f20dbb3c87d47ddLennart Poettering /* We want to wait for the core process, hence let's enable SIGCHLD */
801ad6a6a9cd8fbd58b9f9c27f20dbb3c87d47ddLennart Poettering assert_se(sigaction(SIGCHLD, &sa, NULL) == 0);
faa133f3aa7a18f26563dc5d6b95898cb315c37aLennart Poettering log_error("Caught <%s>, cannot fork for core dump: %s", signal_to_string(sig), strerror(errno));
faa133f3aa7a18f26563dc5d6b95898cb315c37aLennart Poettering else if (pid == 0) {
faa133f3aa7a18f26563dc5d6b95898cb315c37aLennart Poettering /* Enable default signal handler for core dump */
faa133f3aa7a18f26563dc5d6b95898cb315c37aLennart Poettering assert_se(sigaction(sig, &sa, NULL) == 0);
faa133f3aa7a18f26563dc5d6b95898cb315c37aLennart Poettering /* Don't limit the core dump size */
faa133f3aa7a18f26563dc5d6b95898cb315c37aLennart Poettering /* Just to be sure... */
faa133f3aa7a18f26563dc5d6b95898cb315c37aLennart Poettering /* Raise the signal again */
1b4f6e79ec51a57003896a0b605fba427b4a98d2Lennart Poettering assert_not_reached("We shouldn't be here...");
faa133f3aa7a18f26563dc5d6b95898cb315c37aLennart Poettering /* Order things nicely. */
faa133f3aa7a18f26563dc5d6b95898cb315c37aLennart Poettering if ((r = wait_for_terminate(pid, &status)) < 0)
faa133f3aa7a18f26563dc5d6b95898cb315c37aLennart Poettering log_error("Caught <%s>, waitpid() failed: %s", signal_to_string(sig), strerror(-r));
faa133f3aa7a18f26563dc5d6b95898cb315c37aLennart Poettering log_error("Caught <%s>, core dump failed.", signal_to_string(sig));
faa133f3aa7a18f26563dc5d6b95898cb315c37aLennart Poettering log_error("Caught <%s>, dumped core as pid %lu.", signal_to_string(sig), (unsigned long) pid);
28b9b7640603f88cb49f95609331fa5072715f15Lennart Poettering log_info("Executing crash shell in 10s...");
28b9b7640603f88cb49f95609331fa5072715f15Lennart Poettering /* Let the kernel reap children for us */
28b9b7640603f88cb49f95609331fa5072715f15Lennart Poettering sa.sa_flags = SA_NOCLDSTOP|SA_NOCLDWAIT|SA_RESTART;
28b9b7640603f88cb49f95609331fa5072715f15Lennart Poettering assert_se(sigaction(SIGCHLD, &sa, NULL) == 0);
4d247a6cd3f69acbc5a09e8ac7e4fbb50eaa3228Lennart Poettering log_error("Failed to fork off crash shell: %m");
4d247a6cd3f69acbc5a09e8ac7e4fbb50eaa3228Lennart Poettering else if (pid == 0) {
faa133f3aa7a18f26563dc5d6b95898cb315c37aLennart Poettering log_info("Successfully spawned crash shell as pid %lu.", (unsigned long) pid);
105e151299dc1208855380be2b22d0db2d66ebc6Lennart Poetteringstatic void install_crash_handler(void) {
4d247a6cd3f69acbc5a09e8ac7e4fbb50eaa3228Lennart Poettering sigaction_many(&sa, SIGNALS_CRASH_HANDLER, -1);
faa133f3aa7a18f26563dc5d6b95898cb315c37aLennart Poettering /* If we are init, we connect stdin/stdout/stderr to /dev/null
faa133f3aa7a18f26563dc5d6b95898cb315c37aLennart Poettering * and make sure we don't have a controlling tty. */
801ad6a6a9cd8fbd58b9f9c27f20dbb3c87d47ddLennart Poettering tty_fd = open_terminal("/dev/console", O_WRONLY|O_NOCTTY|O_CLOEXEC);
801ad6a6a9cd8fbd58b9f9c27f20dbb3c87d47ddLennart Poettering log_error("Failed to open /dev/console: %s", strerror(-tty_fd));
801ad6a6a9cd8fbd58b9f9c27f20dbb3c87d47ddLennart Poettering /* We don't want to force text mode.
801ad6a6a9cd8fbd58b9f9c27f20dbb3c87d47ddLennart Poettering * plymouth may be showing pictures already from initrd. */
801ad6a6a9cd8fbd58b9f9c27f20dbb3c87d47ddLennart Poettering log_error("Failed to reset /dev/console: %s", strerror(-r));
801ad6a6a9cd8fbd58b9f9c27f20dbb3c87d47ddLennart Poetteringstatic int set_default_unit(const char *u) {
801ad6a6a9cd8fbd58b9f9c27f20dbb3c87d47ddLennart Poetteringstatic int parse_proc_cmdline_word(const char *word) {
801ad6a6a9cd8fbd58b9f9c27f20dbb3c87d47ddLennart Poettering static const char * const rlmap[] = {
547973dea7abd6c124ff6c79fe2bbe322a7314aeLennart Poettering } else if (startswith(word, "rd.systemd.unit=")) {
547973dea7abd6c124ff6c79fe2bbe322a7314aeLennart Poettering } else if (startswith(word, "systemd.log_target=")) {
0936416a1cba187dc76903dae73246f4cbddf312Lennart Poettering if (log_set_target_from_string(word + 19) < 0)
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering log_warning("Failed to parse log target %s. Ignoring.", word + 19);
b826ab586c9e0a9c0d438a75c28cf3a8ab485929Tom Gundersen } else if (startswith(word, "systemd.log_level=")) {
322345fdb9865ef2477fba8e4bdde0e1183ef505Lennart Poettering if (log_set_max_level_from_string(word + 18) < 0)
b826ab586c9e0a9c0d438a75c28cf3a8ab485929Tom Gundersen log_warning("Failed to parse log level %s. Ignoring.", word + 18);
b826ab586c9e0a9c0d438a75c28cf3a8ab485929Tom Gundersen } else if (startswith(word, "systemd.log_color=")) {
b826ab586c9e0a9c0d438a75c28cf3a8ab485929Tom Gundersen if (log_show_color_from_string(word + 18) < 0)
322345fdb9865ef2477fba8e4bdde0e1183ef505Lennart Poettering log_warning("Failed to parse log color setting %s. Ignoring.", word + 18);
d5099efc47d4e6ac60816b5381a5f607ab03f06eMichal Schmidt } else if (startswith(word, "systemd.log_location=")) {
322345fdb9865ef2477fba8e4bdde0e1183ef505Lennart Poettering if (log_show_location_from_string(word + 21) < 0)
322345fdb9865ef2477fba8e4bdde0e1183ef505Lennart Poettering log_warning("Failed to parse log location setting %s. Ignoring.", word + 21);
322345fdb9865ef2477fba8e4bdde0e1183ef505Lennart Poettering } else if (startswith(word, "systemd.dump_core=")) {
322345fdb9865ef2477fba8e4bdde0e1183ef505Lennart Poettering log_warning("Failed to parse dump core switch %s. Ignoring.", word + 18);
322345fdb9865ef2477fba8e4bdde0e1183ef505Lennart Poettering } else if (startswith(word, "systemd.crash_shell=")) {
322345fdb9865ef2477fba8e4bdde0e1183ef505Lennart Poettering log_warning("Failed to parse crash shell switch %s. Ignoring.", word + 20);
d5099efc47d4e6ac60816b5381a5f607ab03f06eMichal Schmidt } else if (startswith(word, "systemd.confirm_spawn=")) {
d5099efc47d4e6ac60816b5381a5f607ab03f06eMichal Schmidt log_warning("Failed to parse confirm spawn switch %s. Ignoring.", word + 22);
2d4c5cbc0ed3ccb09dc086a040088b454c22c644Lennart Poettering } else if (startswith(word, "systemd.crash_chvt=")) {
d23a27a964748967e1ad20e86de869a753af555bTom Gundersen log_warning("Failed to parse crash chvt switch %s. Ignoring.", word + 19);
2d4c5cbc0ed3ccb09dc086a040088b454c22c644Lennart Poettering } else if (startswith(word, "systemd.show_status=")) {
2d4c5cbc0ed3ccb09dc086a040088b454c22c644Lennart Poettering log_warning("Failed to parse show status switch %s. Ignoring.", word + 20);
2d4c5cbc0ed3ccb09dc086a040088b454c22c644Lennart Poettering } else if (startswith(word, "systemd.default_standard_output=")) {
2d4c5cbc0ed3ccb09dc086a040088b454c22c644Lennart Poettering if ((r = exec_output_from_string(word + 32)) < 0)
2d4c5cbc0ed3ccb09dc086a040088b454c22c644Lennart Poettering log_warning("Failed to parse default standard output switch %s. Ignoring.", word + 32);
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering } else if (startswith(word, "systemd.default_standard_error=")) {
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering if ((r = exec_output_from_string(word + 31)) < 0)
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering log_warning("Failed to parse default standard error switch %s. Ignoring.", word + 31);
faa133f3aa7a18f26563dc5d6b95898cb315c37aLennart Poettering } else if (startswith(word, "systemd.setenv=")) {
8bf52d3d17d364438191077d0750b8b80b5dc53aLennart Poettering log_warning("unsetenv failed %m. Ignoring.");
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering log_warning("setenv failed %m. Ignoring.");
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering } else if (startswith(word, "systemd.") ||
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering (in_initrd() && startswith(word, "rd.systemd."))) {
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering log_warning("Unknown kernel switch %s. Ignoring.", word);
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering "systemd.unit=UNIT Default unit to start\n"
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering "rd.systemd.unit=UNIT Default unit to start when run in initrd\n"
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering "systemd.dump_core=0|1 Dump core on crash\n"
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering "systemd.crash_shell=0|1 Run shell on crash\n"
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering "systemd.crash_chvt=N Change to VT #N on crash\n"
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering "systemd.confirm_spawn=0|1 Confirm every process spawn\n"
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering "systemd.show_status=0|1 Show status updates on the console during bootup\n"
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering "systemd.log_target=console|kmsg|journal|journal-or-kmsg|syslog|syslog-or-kmsg|null\n"
74b2466e14a1961bf3ac0e8a60cfaceec705bd59Lennart Poettering " Log target\n"
faa133f3aa7a18f26563dc5d6b95898cb315c37aLennart Poettering "systemd.log_level=LEVEL Log level\n"
9de3e3294065e8697ff10130b53f274319cdcf6fZbigniew Jędrzejewski-Szmek "systemd.log_color=0|1 Highlight important log messages\n"
9c92ce6d67f88beb31dd6555d12ae3f632218a39Lennart Poettering "systemd.log_location=0|1 Include code location in log messages\n"
9c92ce6d67f88beb31dd6555d12ae3f632218a39Lennart Poettering "systemd.default_standard_output=null|tty|syslog|syslog+console|kmsg|kmsg+console|journal|journal+console\n"
9c92ce6d67f88beb31dd6555d12ae3f632218a39Lennart Poettering " Set default log output for services\n"
9c92ce6d67f88beb31dd6555d12ae3f632218a39Lennart Poettering "systemd.default_standard_error=null|tty|syslog|syslog+console|kmsg|kmsg+console|journal|journal+console\n"
9c92ce6d67f88beb31dd6555d12ae3f632218a39Lennart Poettering " Set default log error output for services\n"
9de3e3294065e8697ff10130b53f274319cdcf6fZbigniew Jędrzejewski-Szmek "systemd.setenv=ASSIGNMENT Set an environment variable for all spawned processes\n");
9de3e3294065e8697ff10130b53f274319cdcf6fZbigniew Jędrzejewski-Szmek } else if (streq(word, "quiet"))
9de3e3294065e8697ff10130b53f274319cdcf6fZbigniew Jędrzejewski-Szmek /* SysV compatibility */
faa133f3aa7a18f26563dc5d6b95898cb315c37aLennart Poettering for (i = 0; i < ELEMENTSOF(rlmap); i += 2)
9de3e3294065e8697ff10130b53f274319cdcf6fZbigniew Jędrzejewski-Szmek return set_default_unit(rlmap[i+1]);
78c6a153c47f8d597c827bdcaf8c4e42ac87f738Lennart Poettering FOREACH_WORD_QUOTED(w, l, rvalue, state) {
78c6a153c47f8d597c827bdcaf8c4e42ac87f738Lennart Poettering if (!(t = strndup(w, l)))
78c6a153c47f8d597c827bdcaf8c4e42ac87f738Lennart Poettering log_error("[%s:%u] Failed to parse CPU affinity: %s", filename, line, rvalue);
78c6a153c47f8d597c827bdcaf8c4e42ac87f738Lennart Poettering CPU_SET_S(cpu, CPU_ALLOC_SIZE(ncpus), c);
78c6a153c47f8d597c827bdcaf8c4e42ac87f738Lennart Poettering if (sched_setaffinity(0, CPU_ALLOC_SIZE(ncpus), c) < 0)
78c6a153c47f8d597c827bdcaf8c4e42ac87f738Lennart Poettering log_warning("Failed to set CPU affinity: %m");
322345fdb9865ef2477fba8e4bdde0e1183ef505Lennart Poetteringstatic void strv_free_free(char ***l) {
322345fdb9865ef2477fba8e4bdde0e1183ef505Lennart Poettering for (i = l; *i; i++)
2d4c5cbc0ed3ccb09dc086a040088b454c22c644Lennart Poetteringstatic void free_join_controllers(void) {
2d4c5cbc0ed3ccb09dc086a040088b454c22c644Lennart Poettering unsigned n = 0;
322345fdb9865ef2477fba8e4bdde0e1183ef505Lennart Poettering FOREACH_WORD_QUOTED(w, length, rvalue, state) {
946c70944ebdf428ffeb9991a7449edbd4011461Zbigniew Jędrzejewski-Szmek arg_join_controllers = new(char**, 2);
42cc2eebb01056beb7acd3ecfe8e533558237f84Lennart Poettering for (a = arg_join_controllers; *a; a++) {
5d45a8808431987c370706d365fb0cc95cf03d52Tom Gundersenstatic int parse_config_file(void) {
322345fdb9865ef2477fba8e4bdde0e1183ef505Lennart Poettering { "Manager", "LogLevel", config_parse_level2, 0, NULL },
322345fdb9865ef2477fba8e4bdde0e1183ef505Lennart Poettering { "Manager", "LogTarget", config_parse_target, 0, NULL },
2d4c5cbc0ed3ccb09dc086a040088b454c22c644Lennart Poettering { "Manager", "LogColor", config_parse_color, 0, NULL },
322345fdb9865ef2477fba8e4bdde0e1183ef505Lennart Poettering { "Manager", "LogLocation", config_parse_location, 0, NULL },
322345fdb9865ef2477fba8e4bdde0e1183ef505Lennart Poettering { "Manager", "DumpCore", config_parse_bool, 0, &arg_dump_core },
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "CrashShell", config_parse_bool, 0, &arg_crash_shell },
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "ShowStatus", config_parse_bool, 0, &arg_show_status },
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "CrashChVT", config_parse_int, 0, &arg_crash_chvt },
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "CPUAffinity", config_parse_cpu_affinity2, 0, NULL },
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "DefaultControllers", config_parse_strv, 0, &arg_default_controllers },
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "DefaultStandardOutput", config_parse_output, 0, &arg_default_std_output },
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "DefaultStandardError", config_parse_output, 0, &arg_default_std_error },
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "JoinControllers", config_parse_join_controllers, 0, &arg_join_controllers },
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "RuntimeWatchdogSec", config_parse_usec, 0, &arg_runtime_watchdog },
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "ShutdownWatchdogSec", config_parse_usec, 0, &arg_shutdown_watchdog },
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "CapabilityBoundingSet", config_parse_bounding_set, 0, &arg_capability_bounding_set_drop },
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "TimerSlackNSec", config_parse_nsec, 0, &arg_timer_slack_nsec },
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "DefaultLimitCPU", config_parse_limit, 0, &arg_default_rlimit[RLIMIT_CPU]},
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "DefaultLimitFSIZE", config_parse_limit, 0, &arg_default_rlimit[RLIMIT_FSIZE]},
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "DefaultLimitDATA", config_parse_limit, 0, &arg_default_rlimit[RLIMIT_DATA]},
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "DefaultLimitSTACK", config_parse_limit, 0, &arg_default_rlimit[RLIMIT_STACK]},
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "DefaultLimitCORE", config_parse_limit, 0, &arg_default_rlimit[RLIMIT_CORE]},
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "DefaultLimitRSS", config_parse_limit, 0, &arg_default_rlimit[RLIMIT_RSS]},
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "DefaultLimitNOFILE", config_parse_limit, 0, &arg_default_rlimit[RLIMIT_NOFILE]},
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "DefaultLimitAS", config_parse_limit, 0, &arg_default_rlimit[RLIMIT_AS]},
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "DefaultLimitNPROC", config_parse_limit, 0, &arg_default_rlimit[RLIMIT_NPROC]},
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "DefaultLimitMEMLOCK", config_parse_limit, 0, &arg_default_rlimit[RLIMIT_MEMLOCK]},
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "DefaultLimitLOCKS", config_parse_limit, 0, &arg_default_rlimit[RLIMIT_LOCKS]},
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "DefaultLimitSIGPENDING",config_parse_limit, 0, &arg_default_rlimit[RLIMIT_SIGPENDING]},
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "DefaultLimitMSGQUEUE", config_parse_limit, 0, &arg_default_rlimit[RLIMIT_MSGQUEUE]},
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "DefaultLimitNICE", config_parse_limit, 0, &arg_default_rlimit[RLIMIT_NICE]},
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "DefaultLimitRTPRIO", config_parse_limit, 0, &arg_default_rlimit[RLIMIT_RTPRIO]},
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "Manager", "DefaultLimitRTTIME", config_parse_limit, 0, &arg_default_rlimit[RLIMIT_RTTIME]},
7c6423e19136a7b7b6ef3fe06b94822e582dda27Tom Gundersen const char *fn;
7c6423e19136a7b7b6ef3fe06b94822e582dda27Tom Gundersen fn = arg_running_as == MANAGER_SYSTEM ? SYSTEM_CONFIG_FILE : USER_CONFIG_FILE;
7c6423e19136a7b7b6ef3fe06b94822e582dda27Tom Gundersen log_warning("Failed to open configuration file '%s': %m", fn);
7c6423e19136a7b7b6ef3fe06b94822e582dda27Tom Gundersen r = config_parse(fn, f, "Manager\0", config_item_table_lookup, (void*) items, false, NULL);
50f1e641a93cacfc693b0c3d300bee5df0c8c460Tom Gundersen log_warning("Failed to parse configuration file: %s", strerror(-r));
50f1e641a93cacfc693b0c3d300bee5df0c8c460Tom Gundersenstatic int parse_proc_cmdline(void) {
50f1e641a93cacfc693b0c3d300bee5df0c8c460Tom Gundersen /* Don't read /proc/cmdline if we are in a container, since
50f1e641a93cacfc693b0c3d300bee5df0c8c460Tom Gundersen * that is only relevant for the host system */
50f1e641a93cacfc693b0c3d300bee5df0c8c460Tom Gundersen if ((r = read_one_line_file("/proc/cmdline", &line)) < 0) {
2c1fb4f71206bf970d493294208c5d7597194856Lennart Poettering log_warning("Failed to read /proc/cmdline, ignoring: %s", strerror(-r));
2001c80560e3dae69e14fd994d3978c187af48b8Lennart Poettering log_error("Failed on cmdline argument %s: %s", word, strerror(-r));
2001c80560e3dae69e14fd994d3978c187af48b8Lennart Poetteringstatic int parse_argv(int argc, char *argv[]) {
2d4c5cbc0ed3ccb09dc086a040088b454c22c644Lennart Poettering { "log-level", required_argument, NULL, ARG_LOG_LEVEL },
322345fdb9865ef2477fba8e4bdde0e1183ef505Lennart Poettering { "log-target", required_argument, NULL, ARG_LOG_TARGET },
2d4c5cbc0ed3ccb09dc086a040088b454c22c644Lennart Poettering { "log-color", optional_argument, NULL, ARG_LOG_COLOR },
322345fdb9865ef2477fba8e4bdde0e1183ef505Lennart Poettering { "log-location", optional_argument, NULL, ARG_LOG_LOCATION },
7b50eb2efa122200e39646c19a29abab302f7d24Lennart Poettering { "unit", required_argument, NULL, ARG_UNIT },
7b50eb2efa122200e39646c19a29abab302f7d24Lennart Poettering { "system", no_argument, NULL, ARG_SYSTEM },
7b50eb2efa122200e39646c19a29abab302f7d24Lennart Poettering { "version", no_argument, NULL, ARG_VERSION },
322345fdb9865ef2477fba8e4bdde0e1183ef505Lennart Poettering { "dump-configuration-items", no_argument, NULL, ARG_DUMP_CONFIGURATION_ITEMS },
0dae31d468b1a0e22d98921f7b0dbd92fd217167Zbigniew Jędrzejewski-Szmek { "dump-core", optional_argument, NULL, ARG_DUMP_CORE },
322345fdb9865ef2477fba8e4bdde0e1183ef505Lennart Poettering { "crash-shell", optional_argument, NULL, ARG_CRASH_SHELL },
9c92ce6d67f88beb31dd6555d12ae3f632218a39Lennart Poettering { "confirm-spawn", optional_argument, NULL, ARG_CONFIRM_SPAWN },
9c92ce6d67f88beb31dd6555d12ae3f632218a39Lennart Poettering { "show-status", optional_argument, NULL, ARG_SHOW_STATUS },
9c92ce6d67f88beb31dd6555d12ae3f632218a39Lennart Poettering { "deserialize", required_argument, NULL, ARG_DESERIALIZE },
9c92ce6d67f88beb31dd6555d12ae3f632218a39Lennart Poettering { "switched-root", no_argument, NULL, ARG_SWITCHED_ROOT },
9c92ce6d67f88beb31dd6555d12ae3f632218a39Lennart Poettering { "introspect", optional_argument, NULL, ARG_INTROSPECT },
9c92ce6d67f88beb31dd6555d12ae3f632218a39Lennart Poettering { "default-standard-output", required_argument, NULL, ARG_DEFAULT_STD_OUTPUT, },
9c92ce6d67f88beb31dd6555d12ae3f632218a39Lennart Poettering { "default-standard-error", required_argument, NULL, ARG_DEFAULT_STD_ERROR, },
322345fdb9865ef2477fba8e4bdde0e1183ef505Lennart Poettering while ((c = getopt_long(argc, argv, "hDbsz:", options, NULL)) >= 0)
2d4c5cbc0ed3ccb09dc086a040088b454c22c644Lennart Poettering if ((r = log_set_max_level_from_string(optarg)) < 0) {
7b50eb2efa122200e39646c19a29abab302f7d24Lennart Poettering log_error("Failed to parse log level %s.", optarg);
2e276efc7b0398a3086629a52970bdd4ab7252f9Zbigniew Jędrzejewski-Szmek if ((r = log_set_target_from_string(optarg)) < 0) {
2e276efc7b0398a3086629a52970bdd4ab7252f9Zbigniew Jędrzejewski-Szmek log_error("Failed to parse log target %s.", optarg);
2d4c5cbc0ed3ccb09dc086a040088b454c22c644Lennart Poettering if ((r = log_show_color_from_string(optarg)) < 0) {
7b50eb2efa122200e39646c19a29abab302f7d24Lennart Poettering log_error("Failed to parse log color setting %s.", optarg);
7b50eb2efa122200e39646c19a29abab302f7d24Lennart Poettering if ((r = log_show_location_from_string(optarg)) < 0) {
322345fdb9865ef2477fba8e4bdde0e1183ef505Lennart Poettering log_error("Failed to parse log location setting %s.", optarg);
2d4c5cbc0ed3ccb09dc086a040088b454c22c644Lennart Poettering if ((r = exec_output_from_string(optarg)) < 0) {
2d4c5cbc0ed3ccb09dc086a040088b454c22c644Lennart Poettering log_error("Failed to parse default standard output setting %s.", optarg);
2d4c5cbc0ed3ccb09dc086a040088b454c22c644Lennart Poettering if ((r = exec_output_from_string(optarg)) < 0) {
946c70944ebdf428ffeb9991a7449edbd4011461Zbigniew Jędrzejewski-Szmek log_error("Failed to parse default standard error output setting %s.", optarg);
946c70944ebdf428ffeb9991a7449edbd4011461Zbigniew Jędrzejewski-Szmek if ((r = set_default_unit(optarg)) < 0) {
8db0d2f5c37e7e8f5bfce016cfdad7947a3ea939Zbigniew Jędrzejewski-Szmek log_error("Failed to set default unit %s: %s", optarg, strerror(-r));
8db0d2f5c37e7e8f5bfce016cfdad7947a3ea939Zbigniew Jędrzejewski-Szmek arg_running_as = MANAGER_SYSTEM;
7b50eb2efa122200e39646c19a29abab302f7d24Lennart Poettering log_error("Failed to parse dump core boolean %s.", optarg);
42cc2eebb01056beb7acd3ecfe8e533558237f84Lennart Poettering log_error("Failed to parse crash shell boolean %s.", optarg);
ff3d6560bead6879a2fed1bf99bfe8273b3723f1Zbigniew Jędrzejewski-Szmek log_error("Failed to parse confirm spawn boolean %s.", optarg);
8db0d2f5c37e7e8f5bfce016cfdad7947a3ea939Zbigniew Jędrzejewski-Szmek log_error("Failed to parse show status boolean %s.", optarg);
2d4c5cbc0ed3ccb09dc086a040088b454c22c644Lennart Poettering if ((r = safe_atoi(optarg, &fd)) < 0 || fd < 0) {
151226ab4bf276d60d51864330a99f886b923697Zbigniew Jędrzejewski-Szmek log_error("Failed to parse deserialize option %s.", optarg);
151226ab4bf276d60d51864330a99f886b923697Zbigniew Jędrzejewski-Szmek log_error("Failed to open serialization fd: %m");
7c6423e19136a7b7b6ef3fe06b94822e582dda27Tom Gundersen const char * const * i = NULL;
151226ab4bf276d60d51864330a99f886b923697Zbigniew Jędrzejewski-Szmek for (i = bus_interface_table; *i; i += 2)
151226ab4bf276d60d51864330a99f886b923697Zbigniew Jędrzejewski-Szmek if (!optarg || streq(i[0], optarg)) {
151226ab4bf276d60d51864330a99f886b923697Zbigniew Jędrzejewski-Szmek fputs(DBUS_INTROSPECT_1_0_XML_DOCTYPE_DECL_NODE
7b50eb2efa122200e39646c19a29abab302f7d24Lennart Poettering log_error("Unknown interface %s.", optarg);
5d45a8808431987c370706d365fb0cc95cf03d52Tom Gundersen /* Just to eat away the sysvinit kernel
5d45a8808431987c370706d365fb0cc95cf03d52Tom Gundersen * cmdline args without getopt() error
5d45a8808431987c370706d365fb0cc95cf03d52Tom Gundersen * messages that we'll parse in
f5430a3ef308f3a102899fcaf7fbece757082f2aLennart Poettering * parse_proc_cmdline_word() or ignore. */
5d45a8808431987c370706d365fb0cc95cf03d52Tom Gundersen /* Hmm, when we aren't run as init system
5d45a8808431987c370706d365fb0cc95cf03d52Tom Gundersen * let's complain about excess arguments */
7b50eb2efa122200e39646c19a29abab302f7d24Lennart Poettering /* All /proc/cmdline arguments the kernel didn't
5d45a8808431987c370706d365fb0cc95cf03d52Tom Gundersen * understand it passed to us. We're not really
5d45a8808431987c370706d365fb0cc95cf03d52Tom Gundersen * interested in that usually since /proc/cmdline is
5d45a8808431987c370706d365fb0cc95cf03d52Tom Gundersen * more interesting and complete. With one exception:
5d45a8808431987c370706d365fb0cc95cf03d52Tom Gundersen * if we are run in a container /proc/cmdline is not
8db0d2f5c37e7e8f5bfce016cfdad7947a3ea939Zbigniew Jędrzejewski-Szmek * relevant for the container, hence we rely on argv[]
8db0d2f5c37e7e8f5bfce016cfdad7947a3ea939Zbigniew Jędrzejewski-Szmek if ((r = parse_proc_cmdline_word(*a)) < 0) {
f5430a3ef308f3a102899fcaf7fbece757082f2aLennart Poettering log_error("Failed on cmdline argument %s: %s", *a, strerror(-r));
2d4c5cbc0ed3ccb09dc086a040088b454c22c644Lennart Poetteringstatic int help(void) {
a8812dd7f161a3e459c1730ac92ff2bbc9986ff1Lennart Poettering "Starts up and maintains the system or user services.\n\n"
a8812dd7f161a3e459c1730ac92ff2bbc9986ff1Lennart Poettering " -h --help Show this help\n"
a8812dd7f161a3e459c1730ac92ff2bbc9986ff1Lennart Poettering " --test Determine startup sequence, dump it and exit\n"
a8812dd7f161a3e459c1730ac92ff2bbc9986ff1Lennart Poettering " --dump-configuration-items Dump understood unit configuration items\n"
a8812dd7f161a3e459c1730ac92ff2bbc9986ff1Lennart Poettering " --introspect[=INTERFACE] Extract D-Bus interface data\n"
a8812dd7f161a3e459c1730ac92ff2bbc9986ff1Lennart Poettering " --unit=UNIT Set default unit\n"
a8812dd7f161a3e459c1730ac92ff2bbc9986ff1Lennart Poettering " --system Run a system instance, even if PID != 1\n"
a8812dd7f161a3e459c1730ac92ff2bbc9986ff1Lennart Poettering " --user Run a user instance\n"
a8812dd7f161a3e459c1730ac92ff2bbc9986ff1Lennart Poettering " --dump-core[=0|1] Dump core on crash\n"
a8812dd7f161a3e459c1730ac92ff2bbc9986ff1Lennart Poettering " --crash-shell[=0|1] Run shell on crash\n"
a8812dd7f161a3e459c1730ac92ff2bbc9986ff1Lennart Poettering " --confirm-spawn[=0|1] Ask for confirmation when spawning processes\n"
a8812dd7f161a3e459c1730ac92ff2bbc9986ff1Lennart Poettering " --show-status[=0|1] Show status updates on the console during bootup\n"
a8812dd7f161a3e459c1730ac92ff2bbc9986ff1Lennart Poettering " --log-target=TARGET Set log target (console, journal, syslog, kmsg, journal-or-kmsg, syslog-or-kmsg, null)\n"
a8812dd7f161a3e459c1730ac92ff2bbc9986ff1Lennart Poettering " --log-level=LEVEL Set log level (debug, info, notice, warning, err, crit, alert, emerg)\n"
a8812dd7f161a3e459c1730ac92ff2bbc9986ff1Lennart Poettering " --log-color[=0|1] Highlight important log messages\n"
a8812dd7f161a3e459c1730ac92ff2bbc9986ff1Lennart Poettering " --log-location[=0|1] Include code location in log messages\n"
a8812dd7f161a3e459c1730ac92ff2bbc9986ff1Lennart Poettering " --default-standard-output= Set default standard output for services\n"
a8812dd7f161a3e459c1730ac92ff2bbc9986ff1Lennart Poettering " --default-standard-error= Set default standard error output for services\n",
a8812dd7f161a3e459c1730ac92ff2bbc9986ff1Lennart Poetteringstatic int version(void) {
a8812dd7f161a3e459c1730ac92ff2bbc9986ff1Lennart Poetteringstatic int prepare_reexecute(Manager *m, FILE **_f, FDSet **_fds, bool serialize_jobs) {
a8812dd7f161a3e459c1730ac92ff2bbc9986ff1Lennart Poettering /* Make sure nothing is really destructed when we shut down */
2001c80560e3dae69e14fd994d3978c187af48b8Lennart Poettering log_error("Failed to create serialization file: %s", strerror(-r));
2001c80560e3dae69e14fd994d3978c187af48b8Lennart Poettering log_error("Failed to allocate fd set: %s", strerror(-r));
2001c80560e3dae69e14fd994d3978c187af48b8Lennart Poettering r = manager_serialize(m, f, fds, serialize_jobs);
4d247a6cd3f69acbc5a09e8ac7e4fbb50eaa3228Lennart Poettering log_error("Failed to serialize state: %s", strerror(-r));
2001c80560e3dae69e14fd994d3978c187af48b8Lennart Poettering log_error("Failed to rewind serialization fd: %m");
2001c80560e3dae69e14fd994d3978c187af48b8Lennart Poettering log_error("Failed to disable O_CLOEXEC for serialization: %s", strerror(-r));
8730bccfc59fe507bd3e0a3abcf411b497ac4f0eLennart Poettering log_error("Failed to disable O_CLOEXEC for serialization fds: %s", strerror(-r));
8730bccfc59fe507bd3e0a3abcf411b497ac4f0eLennart Poetteringstatic struct dual_timestamp* parse_initrd_timestamp(struct dual_timestamp *t) {
8730bccfc59fe507bd3e0a3abcf411b497ac4f0eLennart Poettering const char *e;
8730bccfc59fe507bd3e0a3abcf411b497ac4f0eLennart Poettering unsigned long long a, b;
assert(t);
return NULL;
return NULL;
static void test_mtab(void) {
free(p);
"Please make sure to replace this file by a symlink to avoid incorrect or misleading mount(8) output.");
static void test_usr(void) {
log_warning("/usr appears to be on its own filesytem and is not already mounted. This is not a supported setup. "
"Consult http://freedesktop.org/wiki/Software/systemd/separate-usr-is-broken for more information.");
static void test_cgroups(void) {
"Consult http://0pointer.de/blog/projects/cgroups-vs-cgroups.html for more information.");
bool reexecute = false;
bool skip_setup = false;
bool loaded_policy = false;
bool arm_reboot_watchdog = false;
bool queue_default_job = false;
#ifdef HAVE_SYSV_COMPAT
skip_setup = true;
skip_setup = false;
log_show_location(false);
if (in_initrd()) {
if (rd_timestamp) {
if (!skip_setup) {
goto finish;
if (ima_setup() < 0)
goto finish;
log_open();
goto finish;
if (!skip_setup)
if (hwclock_is_localtime() > 0) {
int min;
log_open();
goto finish;
if (!arg_join_controllers)
goto finish;
if (!arg_join_controllers[0])
goto finish;
goto finish;
if (parse_config_file() < 0)
goto finish;
if (parse_proc_cmdline() < 0)
goto finish;
goto finish;
goto finish;
running_in_chroot() > 0) {
goto finish;
goto finish;
goto finish;
goto finish;
goto finish;
log_close();
if (serialization) {
goto finish;
#ifdef HAVE_SPLIT_USR
if (!in_initrd())
setsid();
umask(0);
log_open();
goto finish;
if (virtualization)
if (in_initrd())
locale_setup();
kmod_setup();
test_mtab();
test_usr();
test_cgroups();
goto finish;
goto finish;
goto finish;
if (fds) {
if (serialization) {
if (queue_default_job) {
goto finish;
goto finish;
goto finish;
goto finish;
goto finish;
r = manager_loop(m);
goto finish;
switch (m->exit_code) {
case MANAGER_EXIT:
goto finish;
case MANAGER_RELOAD:
r = manager_reload(m);
case MANAGER_REEXECUTE:
goto finish;
reexecute = true;
goto finish;
case MANAGER_SWITCH_ROOT:
if (!switch_root_init)
goto finish;
reexecute = true;
goto finish;
case MANAGER_REBOOT:
case MANAGER_POWEROFF:
case MANAGER_HALT:
case MANAGER_KEXEC: {
goto finish;
manager_free(m);
for (j = 0; j < RLIMIT_NLIMITS; j++)
label_finish();
if (reexecute) {
const char **args;
unsigned i, args_size;
watchdog_close(true);
if (switch_root_dir) {
if (!switch_root_init) {
if (switch_root_dir)
if (serialization) {
if (fds) {
if (switch_root_init) {
if (serialization)
if (fds)
if (shutdown_verb) {
const char * command_line[] = {
char **env_block;
watchdog_close(false);
char_array_0(e);
watchdog_close(true);
freeze();
return retval;