[systemd-devel] [PATCH] journal, coredump: allow relative values in some configuration options
From: Jan Synacek Journald options SystemMaxUse=, SystemKeepFree=, SystemMaxFileSize=, RuntimeMaxUse=, RuntimeKeepFree= and RuntimeMaxFileSize= can now be specified as a percentage of the available space. Ditto for coredump options MaxUse=, KeepFree=, ExternalSizeMax=, JournalSizeMax= and ProcessSizeMax=. --- man/journald.conf.xml | 4 +- src/journal/coredump.c| 39 src/journal/journal-file.c| 140 +- src/journal/journal-file.h| 17 +++-- src/journal/journald-server.c | 23 --- src/shared/conf-parser.c | 35 +-- 6 files changed, 172 insertions(+), 86 deletions(-) diff --git a/man/journald.conf.xml b/man/journald.conf.xml index 2cbe58b..ec871a8 100644 --- a/man/journald.conf.xml +++ b/man/journald.conf.xml @@ -230,7 +230,9 @@ RuntimeMaxUse=, so that usually seven rotated journal files are kept as history. Specify values in bytes or use K, M, G, T, P, E as units for the specified sizes -(equal to 1024, 1024??,... bytes). Note that size limits are +(equal to 1024, 1024??,... bytes). Alternatively, values can +be specified as a percentage (e.g. 33%) of the available +space of the respective file system. Note that size limits are enforced synchronously when journal files are extended, and no explicit rotation step triggered by time is needed. diff --git a/src/journal/coredump.c b/src/journal/coredump.c index 1c747aa..938ea6a 100644 --- a/src/journal/coredump.c +++ b/src/journal/coredump.c @@ -23,6 +23,7 @@ #include #include #include +#include #include #ifdef HAVE_ELFUTILS @@ -47,6 +48,7 @@ #include "acl-util.h" #include "capability.h" #include "journald-native.h" +#include "journal-file.h" #include "coredump-vacuum.h" #include "process-util.h" @@ -97,11 +99,11 @@ static DEFINE_CONFIG_PARSE_ENUM(config_parse_coredump_storage, coredump_storage, static CoredumpStorage arg_storage = COREDUMP_STORAGE_EXTERNAL; static bool arg_compress = true; -static off_t arg_process_size_max = PROCESS_SIZE_MAX; -static off_t arg_external_size_max = EXTERNAL_SIZE_MAX; -static size_t arg_journal_size_max = JOURNAL_SIZE_MAX; -static off_t arg_keep_free = (off_t) -1; -static off_t arg_max_use = (off_t) -1; +static SizeParameter arg_process_size_max = {PROCESS_SIZE_MAX, false}; +static SizeParameter arg_external_size_max = {EXTERNAL_SIZE_MAX, false}; +static SizeParameter arg_journal_size_max = {JOURNAL_SIZE_MAX, false}; +static SizeParameter arg_keep_free = {(uint64_t) -1, false}; +static SizeParameter arg_max_use = {(uint64_t) -1, false}; static int parse_config(void) { static const ConfigTableItem items[] = { @@ -109,7 +111,7 @@ static int parse_config(void) { { "Coredump", "Compress", config_parse_bool, 0, &arg_compress }, { "Coredump", "ProcessSizeMax", config_parse_iec_off, 0, &arg_process_size_max }, { "Coredump", "ExternalSizeMax", config_parse_iec_off, 0, &arg_external_size_max }, -{ "Coredump", "JournalSizeMax", config_parse_iec_size, 0, &arg_journal_size_max }, +{ "Coredump", "JournalSizeMax", config_parse_iec_off, 0, &arg_journal_size_max }, { "Coredump", "KeepFree", config_parse_iec_off, 0, &arg_keep_free }, { "Coredump", "MaxUse", config_parse_iec_off, 0, &arg_max_use }, {} @@ -122,6 +124,15 @@ static int parse_config(void) { false, NULL); } +static uint64_t get_available(void) { +struct statvfs ss; + +if (statvfs("/var/lib/systemd/coredump", &ss) >= 0) +return ss.f_bsize * ss.f_bavail; + +return 0; +} + static int fix_acl(int fd, uid_t uid) { #ifdef HAVE_ACL @@ -229,7 +240,7 @@ static int maybe_remove_external_coredump(const char *filename, off_t size) { /* Returns 1 if might remove, 0 if will not remove, < 0 on error. */ if (IN_SET(arg_storage, COREDUMP_STORAGE_EXTERNAL, COREDUMP_STORAGE_BOTH) && -size <= arg_external_size_max) +size <= (off_t) size_parameter_evaluate(&arg_external_size_max, get_available())) return 0; if (!filename) @@ -311,7 +322,7 @@ static int save_external_coredump( if (fd < 0) return log_error_errno(errno, "Failed to create coredump file %s: %m", tmp); -r = copy_bytes(STDIN_FILENO, fd, arg_process_size_max, false); +r = copy_bytes(STDIN_FILENO, fd, size_parameter_evaluate(&arg_process_size_max, get_available()), false); if (r == -EFBIG) { log_error("Coredump of %s (%s) is larger than configured processing limit, refusing.", info[INFO_PID], info[INFO_COMM]); goto
[systemd-devel] [PATCH] WIP: conf-parser: allow config_parse_iec_off to parse percentages
From: Jan Synacek --- src/shared/conf-parser.c | 42 ++ 1 file changed, 38 insertions(+), 4 deletions(-) diff --git a/src/shared/conf-parser.c b/src/shared/conf-parser.c index 2c85515..d7d9aa4 100644 --- a/src/shared/conf-parser.c +++ b/src/shared/conf-parser.c @@ -23,6 +23,7 @@ #include #include #include +#include #include "conf-parser.h" #include "conf-files.h" @@ -517,6 +518,37 @@ int config_parse_si_size(const char* unit, return 0; } +static int parse_percent(const char *lvalue, const char *rvalue, off_t *bytes) { +char *p, *e; +off_t percent; +struct statvfs ss; + +p = endswith(rvalue, "%"); +if (!p) +return -ERANGE; + +percent = strtoll(rvalue, &e, 10); +if (*e != '%' || e != p) +return -ERANGE; + +if (percent > 100) +return -ERANGE; + +if (!startswith(lvalue, "System") && !startswith(lvalue, "Runtime")) { +if (statvfs("/var/lib/systemd/coredump", &ss) < 0) +return -errno; +} else if (startswith(lvalue, "System")) { +if (statvfs("/var/log/journal", &ss) < 0) +return -errno; +} else +if (statvfs("/run/log", &ss) < 0) +return -errno; + +*bytes = percent * 0.01 * ss.f_bsize * ss.f_bavail; + +return 0; +} + int config_parse_iec_off(const char* unit, const char *filename, unsigned line, @@ -538,10 +570,12 @@ int config_parse_iec_off(const char* unit, assert_cc(sizeof(off_t) == sizeof(uint64_t)); -r = parse_size(rvalue, 1024, bytes); -if (r < 0) -log_syntax(unit, LOG_ERR, filename, line, -r, "Failed to parse size value, ignoring: %s", rvalue); - +r = parse_percent(lvalue, rvalue, bytes); +if (r < 0) { +r = parse_size(rvalue, 1024, bytes); +if (r < 0) +log_syntax(unit, LOG_ERR, filename, line, -r, "Failed to parse size value, ignoring: %s", rvalue); +} return 0; } -- 2.1.0 ___ systemd-devel mailing list systemd-devel@lists.freedesktop.org http://lists.freedesktop.org/mailman/listinfo/systemd-devel
[systemd-devel] [PATCH] WIP: conf-parser: allow config_parse_iec_off to parse percentages
From: Jan Synacek Allow certain configuration options to be specified as percentages. For example, in journald.conf, SystemMaxUse= can now also be specified as 33%. There is a slight "problem" with the patch. It parses option names to determine what filesystem it should use to get the available space from. This approach is probably not the rigth thing to do, but I couldn't think of a better one. Another approach that came to my mind was to use the highest bit of the off_t value returned by the parser to indicate if the value was a percentage, or a normal value. This would require to rewrite a significant amount of code which now counts on the values being definite (not percentages), and would, IMHO, be hardly any improvement at all. What do you think? Is there a better way to implement this functionality? Is it a real problem to parse the option lvalues like that? Jan Synacek (1): WIP: conf-parser: allow config_parse_iec_off to parse percentages src/shared/conf-parser.c | 42 ++ 1 file changed, 38 insertions(+), 4 deletions(-) -- 2.1.0 ___ systemd-devel mailing list systemd-devel@lists.freedesktop.org http://lists.freedesktop.org/mailman/listinfo/systemd-devel
[systemd-devel] [PATCH] util: fix typo
From: Jan Synacek --- src/shared/util.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/shared/util.c b/src/shared/util.c index da6343f..fd837d9 100644 --- a/src/shared/util.c +++ b/src/shared/util.c @@ -1697,7 +1697,7 @@ int loop_write(int fd, const void *buf, size_t nbytes, bool do_poll) { int parse_size(const char *t, off_t base, off_t *size) { -/* Soo, sometimes we want to parse IEC binary suffxies, and +/* Soo, sometimes we want to parse IEC binary suffixes, and * sometimes SI decimal suffixes. This function can parse * both. Which one is the right way depends on the * context. Wikipedia suggests that SI is customary for -- 2.1.0 ___ systemd-devel mailing list systemd-devel@lists.freedesktop.org http://lists.freedesktop.org/mailman/listinfo/systemd-devel
[systemd-devel] [PATCH v2] systemctl: introduce --now for enable, disable and mask
From: Jan Synacek --- changes in v2: * simplified creation of new arguments (replaced unnecessary dynamic allocation with a VLA) * renamed add_file_change to unit_file_add_changes * addressed wording issues in documentation --- Makefile.am | 1 + man/systemctl.xml| 33 src/libsystemd/sd-bus/bus-util.c | 6 ++- src/libsystemd/sd-bus/bus-util.h | 3 +- src/machine/machinectl.c | 2 +- src/shared/install.c | 112 +++ src/shared/install.h | 1 + src/systemctl/systemctl.c| 28 -- 8 files changed, 114 insertions(+), 72 deletions(-) diff --git a/Makefile.am b/Makefile.am index e8a329f..861f3b2 100644 --- a/Makefile.am +++ b/Makefile.am @@ -5351,6 +5351,7 @@ machinectl_LDADD = \ libsystemd-internal.la \ libsystemd-logs.la \ libsystemd-journal-internal.la \ + libsystemd-units.la \ libsystemd-shared.la rootbin_PROGRAMS += \ diff --git a/man/systemctl.xml b/man/systemctl.xml index 4dbdfe1..dd9e5c5 100644 --- a/man/systemctl.xml +++ b/man/systemctl.xml @@ -456,6 +456,18 @@ +--now + + + When used with enable, the units + will also be started. When used with disable or + mask, the units will also be stopped. The start + or stop operation is only carried out when the respective enable or + disable operation has been successful. + + + + --root= @@ -921,11 +933,12 @@ kobject-uevent 1 systemd-udevd-kernel.socket systemd-udevd.service the changes are taken into account immediately. Note that this does not have the effect of also starting any of the units being enabled. If this -is desired, a separate start command must -be invoked for the unit. Also note that in case of instance -enablement, symlinks named the same as instances are created in -the install location, however they all point to the same -template unit file. +is desired, either --now should be used +together with this command, or an additional start +command must be invoked for the unit. Also note that in case of +instance enablement, symlinks named the same as instances +are created in the install location, however they all point to the +same template unit file. This command will print the actions executed. This output may be suppressed by passing --quiet. @@ -980,9 +993,10 @@ kobject-uevent 1 systemd-udevd-kernel.socket systemd-udevd.service enable. This call implicitly reloads the systemd daemon configuration after completing the disabling of the units. Note that this command does not implicitly -stop the units that are being disabled. If this is desired, -an additional stop command should be -executed afterwards. +stop the units that are being disabled. If this is desired, either +--now should be used together with this command, or +an additional stop command should be executed +afterwards. This command will print the actions executed. This output may be suppressed by passing --quiet. @@ -1128,7 +1142,8 @@ kobject-uevent 1 systemd-udevd-kernel.socket systemd-udevd.service activation of the unit, including enablement and manual activation. Use this option with care. This honors the --runtime option to only mask temporarily -until the next reboot of the system. +until the next reboot of the system. The --now +option can be used to ensure that the units are also stopped. diff --git a/src/libsystemd/sd-bus/bus-util.c b/src/libsystemd/sd-bus/bus-util.c index 7536a96..5e375af 100644 --- a/src/libsystemd/sd-bus/bus-util.c +++ b/src/libsystemd/sd-bus/bus-util.c @@ -1899,7 +1899,7 @@ int bus_wait_for_jobs_one(BusWaitForJobs *d, const char *path, bool quiet) { return bus_wait_for_jobs(d, quiet); } -int bus_deserialize_and_dump_unit_file_changes(sd_bus_message *m, bool quiet) { +int bus_deserialize_and_dump_unit_file_changes(sd_bus_message *m, bool quiet, UnitFileChange **changes, unsigned *n_changes) { const char *type, *path, *source; int r; @@ -1914,6 +1914,10 @@ int bus_deserialize_and_dump_unit_file_changes(sd_bus_message *m, bool quiet) { else log_info("Removed symlink %s.", path); } + +r = unit_file_changes_add(changes, n_changes, streq(type, "symlink") ? UNIT_FILE_SYMLINK : UNIT_FILE_UNLINK, path, source); +if (r < 0) +return r; }
[systemd-devel] [PATCH] systemctl: introduce --now for enable, disable and mask
From: Jan Synacek --- Makefile.am | 1 + man/systemctl.xml| 33 - src/libsystemd/sd-bus/bus-util.c | 6 +- src/libsystemd/sd-bus/bus-util.h | 3 ++- src/machine/machinectl.c | 2 +- src/shared/install.c | 2 +- src/shared/install.h | 3 +++ src/systemctl/systemctl.c| 33 + 8 files changed, 66 insertions(+), 17 deletions(-) diff --git a/Makefile.am b/Makefile.am index e8a329f..861f3b2 100644 --- a/Makefile.am +++ b/Makefile.am @@ -5351,6 +5351,7 @@ machinectl_LDADD = \ libsystemd-internal.la \ libsystemd-logs.la \ libsystemd-journal-internal.la \ + libsystemd-units.la \ libsystemd-shared.la rootbin_PROGRAMS += \ diff --git a/man/systemctl.xml b/man/systemctl.xml index 4dbdfe1..951ce4d 100644 --- a/man/systemctl.xml +++ b/man/systemctl.xml @@ -456,6 +456,17 @@ +--now + + + When used with enable, the units + will also be started. When used with disable + or mask, the units will additionally be + stopped. + + + + --root= @@ -921,11 +932,12 @@ kobject-uevent 1 systemd-udevd-kernel.socket systemd-udevd.service the changes are taken into account immediately. Note that this does not have the effect of also starting any of the units being enabled. If this -is desired, a separate start command must -be invoked for the unit. Also note that in case of instance -enablement, symlinks named the same as instances are created in -the install location, however they all point to the same -template unit file. +is desired, either --now should be used +together with this command, or a separate start +command must be invoked for the unit. Also note that in case of +instance enablement, symlinks named the same as instances +are created in the install location, however they all point to the +same template unit file. This command will print the actions executed. This output may be suppressed by passing --quiet. @@ -980,9 +992,10 @@ kobject-uevent 1 systemd-udevd-kernel.socket systemd-udevd.service enable. This call implicitly reloads the systemd daemon configuration after completing the disabling of the units. Note that this command does not implicitly -stop the units that are being disabled. If this is desired, -an additional stop command should be -executed afterwards. +stop the units that are being disabled. If this is desired, either +--now should be used together with this command, or +an additional stop command should be executed +afterwards. This command will print the actions executed. This output may be suppressed by passing --quiet. @@ -1128,7 +1141,9 @@ kobject-uevent 1 systemd-udevd-kernel.socket systemd-udevd.service activation of the unit, including enablement and manual activation. Use this option with care. This honors the --runtime option to only mask temporarily -until the next reboot of the system. +until the next reboot of the system. The --now +can be additionally used to ensure that the units are also +stopped. diff --git a/src/libsystemd/sd-bus/bus-util.c b/src/libsystemd/sd-bus/bus-util.c index 7536a96..fe7eb43 100644 --- a/src/libsystemd/sd-bus/bus-util.c +++ b/src/libsystemd/sd-bus/bus-util.c @@ -1899,7 +1899,7 @@ int bus_wait_for_jobs_one(BusWaitForJobs *d, const char *path, bool quiet) { return bus_wait_for_jobs(d, quiet); } -int bus_deserialize_and_dump_unit_file_changes(sd_bus_message *m, bool quiet) { +int bus_deserialize_and_dump_unit_file_changes(sd_bus_message *m, bool quiet, UnitFileChange **changes, unsigned *n_changes) { const char *type, *path, *source; int r; @@ -1914,6 +1914,10 @@ int bus_deserialize_and_dump_unit_file_changes(sd_bus_message *m, bool quiet) { else log_info("Removed symlink %s.", path); } + +r = add_file_change(changes, n_changes, streq(type, "symlink") ? UNIT_FILE_SYMLINK : UNIT_FILE_UNLINK, path, source); +if (r < 0) +return r; } if (r < 0) return bus_log_parse_error(r); diff --git a/src/libsystemd/sd-bus/bus-util.h b/src/libsystemd/sd-bus/bus-util.h index 093b48b..999a372 100644 --- a/src/libsystemd/sd-bus/bus-util.h +++ b/src/libsystemd/sd-bus/bus-util.h @@ -24,6 +24,7 @@ #include "sd-event.h" #include "sd-bus.h" #
[systemd-devel] [PATCH] systemctl: introduce -e and -d for start and stop
From: Jan Synacek --- man/systemctl.xml | 26 ++ src/systemctl/systemctl.c | 40 ++-- 2 files changed, 60 insertions(+), 6 deletions(-) diff --git a/man/systemctl.xml b/man/systemctl.xml index 4dbdfe1..51c19e1 100644 --- a/man/systemctl.xml +++ b/man/systemctl.xml @@ -432,6 +432,26 @@ +-e +--enable + + + When used with start, additionally + enable unit after it has been successfully started. + + + + +-d +--disable + + + When used with stop, additionally + disable unit after it has been successfully stopped. + + + + -f --force @@ -633,6 +653,9 @@ kobject-uevent 1 systemd-udevd-kernel.socket systemd-udevd.service instance name until the instance has been started. Therefore, using glob patterns with start has limited usefulness. + +When used with -e, additional enable +operation is performed. @@ -641,6 +664,9 @@ kobject-uevent 1 systemd-udevd-kernel.socket systemd-udevd.service Stop (deactivate) one or more units specified on the command line. + +When used with -d, additional disable +operation is performed. diff --git a/src/systemctl/systemctl.c b/src/systemctl/systemctl.c index 1f18f9c..5655c57 100644 --- a/src/systemctl/systemctl.c +++ b/src/systemctl/systemctl.c @@ -136,12 +136,15 @@ static unsigned arg_lines = 10; static OutputMode arg_output = OUTPUT_SHORT; static bool arg_plain = false; static bool arg_firmware_setup = false; +static bool arg_startenable = false; +static bool arg_stopdisable = false; static bool original_stdout_is_tty; static int daemon_reload(sd_bus *bus, char **args); static int halt_now(enum action a); static int check_one_unit(sd_bus *bus, const char *name, const char *good_states, bool quiet); +static int enable_unit(sd_bus *bus, char **args); static char** strv_skip_first(char **strv) { if (strv_length(strv) > 0) @@ -2677,7 +2680,7 @@ static int start_unit(sd_bus *bus, char **args) { const char *method, *mode, *one_name, *suffix = NULL; _cleanup_strv_free_ char **names = NULL; char **name; -int r = 0; +int r = 0, start_rc = 0; assert(bus); @@ -2722,11 +2725,26 @@ static int start_unit(sd_bus *bus, char **args) { STRV_FOREACH(name, names) { _cleanup_bus_error_free_ sd_bus_error error = SD_BUS_ERROR_NULL; -int q; -q = start_unit_one(bus, method, *name, mode, &error, w); -if (r >= 0 && q < 0) -r = translate_bus_error_to_exit_status(q, &error); +start_rc = start_unit_one(bus, method, *name, mode, &error, w); +if (r >= 0 && start_rc < 0) +r = translate_bus_error_to_exit_status(start_rc, &error); +} + +if (((streq(args[0], "start") && arg_startenable) + || (streq(args[0], "stop") && arg_stopdisable)) +&& start_rc >= 0) { +_cleanup_strv_free_ char **newargs; + +newargs = strv_copy(args); +if (!newargs) +return -ENOMEM; +free(newargs[0]); +newargs[0] = streq(args[0], "start") ? strdup("enable") : strdup("disable"); +if (!newargs[0]) +return -ENOMEM; + +r = enable_unit(bus, newargs); } if (!arg_no_block) { @@ -6257,6 +6275,8 @@ static int systemctl_parse_argv(int argc, char *argv[]) { { "recursive", no_argument, NULL, 'r' }, { "preset-mode", required_argument, NULL, ARG_PRESET_MODE }, { "firmware-setup", no_argument, NULL, ARG_FIRMWARE_SETUP }, +{ "enable", no_argument, NULL, 'e' }, +{ "disable", no_argument, NULL, 'd' }, {} }; @@ -6265,7 +6285,7 @@ static int systemctl_parse_argv(int argc, char *argv[]) { assert(argc >= 0); assert(argv); -while ((c = getopt_long(argc, argv, "ht:p:alqfs:H:M:n:o:ir", options, NULL)) >= 0) +while ((c = getopt_long(argc, argv, "ht:p:alqfs:H:M:n:o:ired", options, NULL)) >= 0) switch (c) { @@ -6537,6 +6557,14 @@ static int systemctl_parse_argv(int argc, char *argv[]) { break; +case 'e': +arg_startenable = true; +break; + +case 'd': +arg_stopdisa