diff --git a/NEWS b/NEWS index 81b6380cedf..915d61abe30 100644 --- a/NEWS +++ b/NEWS @@ -2,6 +2,15 @@ systemd System and Service Manager CHANGES WITH 257 in spe: + Incompatible changes: + + * The --purge switch of systemd-tmpfiles (which was added in v256) has + been reworked: it will now only apply to tmpfiles.d/ lines marked + with the new "$" flag. This is an incompatible change, and means any + tmpfiles.d/ files which shall be used together with --purge need to + be updated accordingly. This change has been made to make it harder + to accidentally delete too many files when using --purge incorrectly. + Announcements of Future Feature Removals and Incompatible Changes: * Support for automatic flushing of the nscd user/group database caches diff --git a/man/systemd-tmpfiles.xml b/man/systemd-tmpfiles.xml index f3108b53d9c..b7b4d0dca68 100644 --- a/man/systemd-tmpfiles.xml +++ b/man/systemd-tmpfiles.xml @@ -152,10 +152,11 @@ - If this option is passed, all files and directories marked for - creation by the tmpfiles.d/ files specified on the command - line will be deleted. Specifically, this acts on all files and directories - marked with f, F, d, D, + If this option is passed, all files and directories declared for + creation and marked with the $ character by the + tmpfiles.d/ files specified on the command line will be + deleted. Specifically, this acts on all files and directories marked with + f, F, d, D, v, q, Q, p, L, c, b, C, w, e. If this switch is used at least one diff --git a/man/tmpfiles.d.xml b/man/tmpfiles.d.xml index 15027def605..a721c1e66d4 100644 --- a/man/tmpfiles.d.xml +++ b/man/tmpfiles.d.xml @@ -539,6 +539,10 @@ w- /proc/sys/vm/swappiness - - - - 10 service, the line is silently skipped. If ^ and ~ are combined Base64 decoding is applied to the credential contents. + If the dollar sign ($) is used, the file becomes subject to removal when + systemd-tmpfiles is invoked with the switch. Lines without + this character are unaffected by that switch. + Note that for all line types that result in creation of any kind of file node (i.e. f, d/D/v/q/Q, diff --git a/src/tmpfiles/tmpfiles.c b/src/tmpfiles/tmpfiles.c index 59b48492ab7..16f831bc262 100644 --- a/src/tmpfiles/tmpfiles.c +++ b/src/tmpfiles/tmpfiles.c @@ -170,6 +170,8 @@ typedef struct Item { bool try_replace:1; + bool purge:1; + OperationMask done; } Item; @@ -3046,6 +3048,9 @@ static int purge_item(Context *c, Item *i) { if (!needs_purge(i->type)) return 0; + if (!i->purge) + return 0; + log_debug("Running purge action for entry %c %s", (char) i->type, i->path); if (needs_glob(i->type)) @@ -3602,7 +3607,7 @@ static int parse_line( ItemArray *existing; OrderedHashmap *h; bool append_or_force = false, boot = false, allow_failure = false, try_replace = false, - unbase64 = false, from_cred = false, missing_user_or_group = false; + unbase64 = false, from_cred = false, missing_user_or_group = false, purge = false; int r; assert(fname); @@ -3668,6 +3673,8 @@ static int parse_line( unbase64 = true; else if (action[pos] == '^' && !from_cred) from_cred = true; + else if (action[pos] == '$' && !purge) + purge = true; else { *invalid_config = true; return log_syntax(NULL, LOG_ERR, fname, line, SYNTHETIC_ERRNO(EBADMSG), @@ -3684,6 +3691,7 @@ static int parse_line( i.append_or_force = append_or_force; i.allow_failure = allow_failure; i.try_replace = try_replace; + i.purge = purge; r = specifier_printf(path, PATH_MAX-1, specifier_table, arg_root, NULL, &i.path); if (ERRNO_IS_NOINFO(r)) @@ -3838,6 +3846,12 @@ static int parse_line( "Unknown command type '%c'.", (char) i.type); } + if (i.purge && !needs_purge(i.type)) { + *invalid_config = true; + return log_syntax(NULL, LOG_ERR, fname, line, SYNTHETIC_ERRNO(EBADMSG), + "Purge flag '$' combined with line type '%c' which does not support purging.", (char) i.type); + } + if (!should_include_path(i.path)) return 0; diff --git a/test/units/TEST-22-TMPFILES.18.sh b/test/units/TEST-22-TMPFILES.18.sh index 5d24197c813..c81f6bd0ef5 100755 --- a/test/units/TEST-22-TMPFILES.18.sh +++ b/test/units/TEST-22-TMPFILES.18.sh @@ -9,26 +9,39 @@ set -o pipefail export SYSTEMD_LOG_LEVEL=debug c=' -d /tmp/somedir -f /tmp/somedir/somefile - - - - baz +d$ /tmp/somedir +f$ /tmp/somedir/somefile - - - - baz +f /tmp/someotherfile - - - - qux ' systemd-tmpfiles --create - <<<"$c" test -f /tmp/somedir/somefile grep -q baz /tmp/somedir/somefile +grep -q qux /tmp/someotherfile systemd-tmpfiles --purge --dry-run - <<<"$c" test -f /tmp/somedir/somefile grep -q baz /tmp/somedir/somefile +grep -q qux /tmp/someotherfile systemd-tmpfiles --purge - <<<"$c" test ! -f /tmp/somedir/somefile test ! -d /tmp/somedir/ +grep -q qux /tmp/someotherfile systemd-tmpfiles --create --purge --dry-run - <<<"$c" test ! -f /tmp/somedir/somefile test ! -d /tmp/somedir/ +grep -q qux /tmp/someotherfile systemd-tmpfiles --create --purge - <<<"$c" test -f /tmp/somedir/somefile grep -q baz /tmp/somedir/somefile +grep -q qux /tmp/someotherfile + +systemd-tmpfiles --purge - <<<"$c" +test ! -f /tmp/somedir/somefile +test ! -d /tmp/somedir/ +grep -q qux /tmp/someotherfile + +rm /tmp/someotherfile diff --git a/tmpfiles.d/20-systemd-shell-extra.conf.in b/tmpfiles.d/20-systemd-shell-extra.conf.in index 8ebe83dd697..02f1ef58023 100644 --- a/tmpfiles.d/20-systemd-shell-extra.conf.in +++ b/tmpfiles.d/20-systemd-shell-extra.conf.in @@ -8,5 +8,5 @@ # See tmpfiles.d(5) for details {% if LINK_SHELL_EXTRA_DROPIN %} -L {{SHELLPROFILEDIR}}/70-systemd-shell-extra.sh - - - - {{LIBEXECDIR}}/profile.d/70-systemd-shell-extra.sh +L$ {{SHELLPROFILEDIR}}/70-systemd-shell-extra.sh - - - - {{LIBEXECDIR}}/profile.d/70-systemd-shell-extra.sh {% endif %} diff --git a/tmpfiles.d/20-systemd-ssh-generator.conf.in b/tmpfiles.d/20-systemd-ssh-generator.conf.in index dbe354a2d2d..8c9d3af1c35 100644 --- a/tmpfiles.d/20-systemd-ssh-generator.conf.in +++ b/tmpfiles.d/20-systemd-ssh-generator.conf.in @@ -8,7 +8,7 @@ # See tmpfiles.d(5) for details {% if LINK_SSH_PROXY_DROPIN %} -L {{SSHCONFDIR}}/20-systemd-ssh-proxy.conf - - - - {{LIBEXECDIR}}/ssh_config.d/20-systemd-ssh-proxy.conf +L$ {{SSHCONFDIR}}/20-systemd-ssh-proxy.conf - - - - {{LIBEXECDIR}}/ssh_config.d/20-systemd-ssh-proxy.conf {% endif %} {% if CREATE_SSHDPRIVSEPDIR %} d {{SSHDPRIVSEPDIR}} 0755 diff --git a/tmpfiles.d/legacy.conf.in b/tmpfiles.d/legacy.conf.in index 4f2c0d7c431..ec2f7aea72c 100644 --- a/tmpfiles.d/legacy.conf.in +++ b/tmpfiles.d/legacy.conf.in @@ -13,7 +13,7 @@ d /run/lock 0755 root root - L /var/lock - - - - ../run/lock {% if CREATE_LOG_DIRS %} -L /var/log/README - - - - ../..{{DOC_DIR}}/README.logs +L$ /var/log/README - - - - ../..{{DOC_DIR}}/README.logs {% endif %} # /run/lock/subsys is used for serializing SysV service execution, and diff --git a/tmpfiles.d/systemd-network.conf b/tmpfiles.d/systemd-network.conf index 323beca59c5..5898e88de56 100644 --- a/tmpfiles.d/systemd-network.conf +++ b/tmpfiles.d/systemd-network.conf @@ -7,7 +7,7 @@ # See tmpfiles.d(5) for details -d /run/systemd/netif 0755 systemd-network systemd-network - -d /run/systemd/netif/links 0755 systemd-network systemd-network - -d /run/systemd/netif/leases 0755 systemd-network systemd-network - -d /var/lib/systemd/network 0755 systemd-network systemd-network - +d$ /run/systemd/netif 0755 systemd-network systemd-network - +d$ /run/systemd/netif/links 0755 systemd-network systemd-network - +d$ /run/systemd/netif/leases 0755 systemd-network systemd-network - +d$ /var/lib/systemd/network 0755 systemd-network systemd-network - diff --git a/tmpfiles.d/systemd-nspawn.conf b/tmpfiles.d/systemd-nspawn.conf index 78bd1c670e0..6549ea41018 100644 --- a/tmpfiles.d/systemd-nspawn.conf +++ b/tmpfiles.d/systemd-nspawn.conf @@ -19,5 +19,5 @@ Q /var/lib/machines 0700 - - - # systemd-nspawn --ephemeral places snapshots) we are more strict, to # avoid removing unrelated temporary files. -R! /var/lib/machines/.#* -R! /.#machine.* +R!$ /var/lib/machines/.#* +R!$ /.#machine.* diff --git a/tmpfiles.d/systemd-tmp.conf b/tmpfiles.d/systemd-tmp.conf index d47d468fba8..093830586c1 100644 --- a/tmpfiles.d/systemd-tmp.conf +++ b/tmpfiles.d/systemd-tmp.conf @@ -14,10 +14,10 @@ x /var/tmp/systemd-private-%b-* X /var/tmp/systemd-private-%b-*/tmp # Remove top-level private temporary directories on each boot -R! /tmp/systemd-private-* -R! /var/tmp/systemd-private-* +R!$ /tmp/systemd-private-* +R!$ /var/tmp/systemd-private-* # Handle lost systemd-coredump temp files. They could be lost on old filesystems, # for example, after hard reboot. x /var/lib/systemd/coredump/.#core*.%b* -r! /var/lib/systemd/coredump/.#* +r!$ /var/lib/systemd/coredump/.#* diff --git a/tmpfiles.d/systemd.conf.in b/tmpfiles.d/systemd.conf.in index 815fb2dd408..dac2e5bbc40 100644 --- a/tmpfiles.d/systemd.conf.in +++ b/tmpfiles.d/systemd.conf.in @@ -13,11 +13,11 @@ f+! /run/utmp 0664 root utmp - {% endif %} d /run/systemd/ask-password 0755 root root - -d /run/systemd/seats 0755 root root - -d /run/systemd/sessions 0755 root root - -d /run/systemd/users 0755 root root - +d$ /run/systemd/seats 0755 root root - +d$ /run/systemd/sessions 0755 root root - +d$ /run/systemd/users 0755 root root - d /run/systemd/machines 0755 root root - -d /run/systemd/shutdown 0755 root root - +d$ /run/systemd/shutdown 0755 root root - d /run/log 0755 root root -