Let's downgrade the log message about our attempts to deal with an
ordering cycle to warning, because this is a "positive" thing, we try to
improve an earlier error.
OTOH increase the log level when we first log about the cycle to error,
since that highlights the actual problem.
Currently, callers of safe_glob() set an empty glob_t or glob_t with
opendir func, and all other components are always zero.
So, let's introduce safe_glob_full() which optionally takes opendir
function, rather than glob_t, and returns result strv, rather than
storing results in glob_t.
Also, introduce safe_glob() which is a trivial wrapper of
safe_glob_full() without opendir func.
No functional change, just refactoring.
Some configuration files that need updates are directly under in /etc. To
update them atomically, we need write access to /etc. For Ubuntu Core this is
an issue as /etc is not writable. Only a selection of subdirectories can be
writable. The general solution is symlinks or bind mounts to writable places.
But for atomic writes in /etc, that does not work. So Ubuntu has had a patch
for that that did not age well.
Instead we would like to introduce some environment variables for alternate
paths.
* SYSTEMD_ETC_HOSTNAME: /etc/hostname
* SYSTEMD_ETC_MACHINE_INFO: /etc/machine-info
* SYSTEMD_ETC_LOCALTIME: /etc/localtime
* SYSTEMD_ETC_LOCALE_CONF: /etc/locale.conf
* SYSTEMD_ETC_VCONSOLE_CONF: /etc/vconsole.conf
* SYSTEMD_ETC_ADJTIME: /etc/adjtime
While it is for now expected that there is a symlink from the standard, we
still try to read them from that alternate path. This is important for
`/etc/localtime`, which is a symlink, so we cannot have an indirect symlink or
bind mount for it.
Since machine-id is typically written only once and not updated. This commit
does not cover it. An initrd can properly create it and bind mount it.
More porting work to label_ops_pre()/label_ops_post()
This also enables labelling of the /etc/localtime symlink in
systemd-firstboot, which should address one small facet of #37857
This controls the new SO_PASSRIGHTS socket option in kernel v6.16.
Note that I intentionally choose a different naming scheme than
Pass*=, since all other Pass*= options controls whether some extra
bits are attached to the message, while this one's about denying
file descriptor transfer and it feels more explicit this way.
And diverging from underlying socket option name is precedented
by Timestamping=. But happy to change it to just say PassRights=
if people disagree.
Currently, if we use a cgroup namespace together with DelegateSubgroup=,
the subgroup becomes the root of the cgroup namespace because we move the
service process to the subgroup before we unshare the cgroup namespace, and
the current cgroup becomes the root of the cgroup namespace when we unshare
the cgroup namespace.
Let's fix the problem by not moving the service process to the subgroup until
we've unshared the cgroup namespace. Note that this doesn't break the primary use
case of CLONE_INTO_CGROUP since we still use it to immediately clone into the service
main cgroup, just not anymore into the subgroup, but this shouldn't matter in practice.
Additionally, we need special handling for control processes, as those *do*
need to get spawned into the subcgroup immediately if delegation is configured to
avoid violating the cgroupsv2 "no inner processes" rule.
Effectively, this leaves us with the following logic:
- In exec_spawn(), spawn into subgroup if we're spawning a control process
that needs to be spawned into a subgroup immediately. Otherwise, spawn into
main service cgroup.
- In exec_invoke(), move into subgroup early if we don't need a cgroup namespace.
Otherwise, move into subgroup after we've unshared the cgroup namespace.
Prompted by https://github.com/systemd/systemd/pull/37646#discussion_r2126882561
Follow-up for 879952a853
Currently, almost all cgroup attr getters check cgroup_path for whether
cgroup is around. This is actually great, because we never want to expose
a non-existent cgroup path via IPC and such. However, it is spuriously
initialized at places where it shouldn't be, e.g. in unit_warn_leftover_processes().
This matters especially to units that *may* carry processes to run, but
not *always*, notably socket units. unit_warn_leftover_processes() is supposed
to be informative only and not try to set cgroup tracking to realized in
a half-assed way.
Hence, let's kill cgroup_realized field, and make sure cgroup_path is set
only if cgroup has been created. Be extra careful with deserialization
though, since the previous versions don't follow this rule and we need
to patch cgroup_path manually based on cgroup_realized we got from deserialization.
Calls to unit_watch_cgroup*() are dropped in cgroup_runtime_deserialize_one(),
because unit_deserialize_state() will invalidate cgroup realized state and
reapply later.
This was from v228, i.e. before cgroup v2 got introduced.
Nowadays cgroup v1 is outright rejected during initialization,
i.e. upgrading isn't possible whatsoever. Remove the compat glue there.
I wanted to see if moving moving out constant string arguments our of
error messages results in smaller binary sizes. Turns out it does, but
the savings are not consistent. Sometimes we get a few kB in a single
binary, sometimes there is no size change.
In multi-seat scenarios, a display manager might need to start multiple
greeter sessions. But systemd allows at most one graphical session per
user. So, display managers now have a range of UIDs to dynamically
allocate users for their greeter sessions.
git grep -l 'Failed to open /'|xargs sed -r -i 's|"Failed to open (/[^ ]+): %m"|"Failed to open %s: %m", "\1"|g'
git grep -l $'Failed to open \'/'|xargs sed -r -i $'s|"Failed to open \'(/[^ ]+)\': %m"|"Failed to open %s: %m", "\\1"|g'
git grep -l "Failed to open /"|xargs sed -r -i $'s|"Failed to open (/[^ ]+), ignoring: %m"|"Failed to open %s, ignoring: %m", "\\1"|g'
+ some manual fixups.
We'd print the filename, but not the full path. Error messages without
the full path are annoying to users since they might not know where the file
is located, esp. if the name is fairly generic, and it is harder to search
for the error message too.
Use a trailing slash to indicate when we're trying to open a directory.
Drop quotes from around paths which are static and known to contain no
whitespace.
This allows some strings constants to be deduplicated.
libsystemd-core.so + systemd are about 2k smaller.
Also tweak some messages for consistency. We used 'exec' in one place and
'execute' in all other messages.