Let's make sure to use strna() on the strings returned by fd_get_path()
where we knowingly ignore any failures. We got this right in most cases,
but two were missing.
We use it pretty much everywhere else, hence use it here too.
This also changes the error generated from EOPNOTSUPP to ENOSYS, to
match the other cases where we do such a check. One user checked for
EOPNOTSUPP which is updated to check for ENOSYS instead.
When 4dfaa528d4 was first commited its callers relied on `errno` instead of the
return value for error reporting. Which worked fine, since internally
under all conditions base were set — even if ugly and not inline with
our coding style. Things then got broken in
f8606626ed where suddenly additional
syscalls might end up being done in the function, thus corrupting `errno`.
Similarly to "setup" vs. "set up", "fallback" is a noun, and "fall back"
is the verb. (This is pretty clear when we construct a sentence in the
present continous: "we are falling back" not "we are fallbacking").
https://tools.ietf.org/html/draft-knodel-terminology-02https://lwn.net/Articles/823224/
This gets rid of most but not occasions of these loaded terms:
1. scsi_id and friends are something that is supposed to be removed from
our tree (see #7594)
2. The test suite defines an API used by the ubuntu CI. We can remove
this too later, but this needs to be done in sync with the ubuntu CI.
3. In some cases the terms are part of APIs we call or where we expose
concepts the kernel names the way it names them. (In particular all
remaining uses of the word "slave" in our codebase are like this,
it's used by the POSIX PTY layer, by the network subsystem, the mount
API and the block device subsystem). Getting rid of the term in these
contexts would mean doing some major fixes of the kernel ABI first.
Regarding the replacements: when whitelist/blacklist is used as noun we
replace with with allow list/deny list, and when used as verb with
allow-list/deny-list.
let's return ENOSYS in that case, to make things a bit less confusng.
Previously we'd just propagate ENOENT, which people might mistake as
applying to the object being modified rather than /proc/ just not being
there.
Let's return ENOSYS instead, i.e. an error clearly indicating that some
kernel API is not available. This hopefully should put people on a
better track.
Note that we only do the procfs check in the error path, which hopefully
means it's the less likely path.
We probably can add similar bits to more suitable codepaths dealing with
/proc/self/fd, but for now, let's pick to the ones noticed in #14745.
Fixes: #14745
Previously there was a weird asymmetry: initially we'd resolve the
specified prefix path when chasing symlinks together with the actual
path we were supposed to cover, except when we hit an absolute symlink
where we'd use the root as it was. Let's unify handling here: the prefix
path is never resolved, and always left as it is.
This in particular fixes issues with symlinks in the prefix path, as
that confused the check that made sure we never left the root directory.
Fixes: #14634
Replaces: #14635
f5947a5e92 dropped missing.h and
replaced with the more specific headers but did not add
missing_fcntl.h in places that use O_TMPFILE. This is needed for
some older versions of glibc.
strerror() is not thread safe. Let's avoid it where it is easy hence.
(Ideally we'd not use it at all anymore, but that's sometimes a bit
nasty, not in this case though, where it is very easy to avoid)
Follow-up for: 27c3112dcb
chase_symlinks() would return negative on error, and either a non-negative status
or a non-negative fd when CHASE_OPEN was given. This made the interface quite
complicated, because dependning on the flags used, we would get two different
"types" of return object. Coverity was always confused by this, and flagged
every use of chase_symlinks() without CHASE_OPEN as a resource leak (because it
would this that an fd is returned). This patch uses a saparate output parameter,
so there is no confusion.
(I think it is OK to have functions which return either an error or an fd. It's
only returning *either* an fd or a non-fd that is confusing.)
The default message for ENOSPC is very misleading: it says that the disk is
filled, but in fact the inotify watch limit is the problem.
So let's introduce and use a wrapper that simply calls inotify_add_watch(2) and
which fixes the error message up in case ENOSPC is returned.
fstat(2) is fine with O_PATH fds.
For changing owership of a file opened with O_PATH, there's fchownat(2).
Only changing permissions is problematic but we introduced fchmod_opath() for
that purpose.
Inspired by #12431 let's also rework chmod_and_chown() and make sure we
never add more rights to a file not owned by the right user.
Also, let's make chmod_and_chown() just a wrapper arond
fchmod_and_chown().
let's also change strategy: instead of chown()ing first and stating
after on failure and supressing errors, let's avoid the chown in the
firts place, in the interest on keeping things minimal.
Let's reduce the chance of failure: if we can't apply the chmod/chown
requested, check if it's applied anyway, and if so, supress the error.
This is even race-free since we operate on an O_PATH fd anyway.
When chase_symlinks is given a root path, it is assumed that all
processed symlinks are restricted under that path. It should not
be necessary to verify components of that prefix path since they
are not relevant to the symlinks.
This change skips unsafe UID transitions in this root prefix, i.e.
it now ignores when an unprivileged user's directory contains a
root-owned directory above the symlink root.
This has been irritating me for quite a while: let's prefix these enum
values with a common prefix, like we do for almost all other enums.
No change in behaviour, just some renaming.
This has the side effect to upgrade the log level at which the log is emitted
from debug to warning.
This might be better since after all we didn't apply a tmpfiles.d/ rule and
that actually might end up being problematic eventually.
We're always interested into finding unsafe transitions so let's make the
helper return true when it finds such transitions so we don't need to negate
its results.
No functional changes.
We previously returned -EPERM but it can be returned for various other reasons
too.
Let's use -ENOLINK instead as this value shouldn't be used currently. This
allows users of CHASE_SAFE to detect without any ambiguities when unsafe
transitions are encountered by chase_symlinks().
All current users of CHASE_SAFE that explicitly reacted on -EPERM have been
converted to react on -ENOLINK.
This splits out a bunch of functions from fileio.c that have to do with
temporary files. Simply to make the header files a bit shorter, and to
group things more nicely.
No code changes, just some rearranging of source files.
This flag can be used to make chase_symlinks() emit a warning when it
encounters an error.
Such flag can be useful for generating a comprehensive and detailed warning
since chase_symlinks() can generate a warning with a full context.
For now only warnings for unsafe transitions are produced.