When mounting a path being masked, the /dev/null might disappear from
under us, and mount (even on an opened /dev/null file descriptor) will
return ENOENT, which we deliberately ignore, as there's no need to mask
non-existent paths.
Let's open the destination path and ignore ENOENT during open, then
mount via the destination file descriptor, not ignoring ENOENT.
Reported-by: lifubang <lifubang@acmcoder.com>
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
The /dev/null in a container should not be trusted, because when /dev
is a bind mount, /dev/null is not created by runc itself.
1. Add isDevNull which checks the fd minor/major and device type,
and verifyDevNull which does the stat and the check.
2. Rewrite maskPath to open and check /dev/null, and use its fd to
perform mounts. Move the loop over the MaskPaths into the function,
and rename it to maskPaths.
3. reOpenDevNull: use verifyDevNull and isDevNull.
4. fixStdioPermissions: use isDevNull instead of stat.
Fixes: GHSA-9493-h29p-rfm2 CVE-2025-31133
Co-authored-by: Rodrigo Campos <rodrigoca@microsoft.com>
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
Signed-off-by: Aleksa Sarai <cyphar@cyphar.com>
filepath-securejoin v0.3 gave us a much safer re-open primitive, we
should use it to avoid any theoretical attacks. Rather than using it
direcly, add a small pathrs wrapper to make libpathrs migrations in the
future easier...
Signed-off-by: Aleksa Sarai <cyphar@cyphar.com>
We will have more wrappers around filepath-securejoin, and so move them
to their own specific package so that we can eventually use libpathrs
fairly cleanly (by swapping out the implementation).
Signed-off-by: Aleksa Sarai <cyphar@cyphar.com>
The linux.intelRdt.enableMonitoring field enables the creation of
a per-container monitoring group. The monitoring group is removed when
the container is destroyed.
Signed-off-by: Markus Lehtonen <markus.lehtonen@intel.com>
(cherry picked from commit 7aa4e1a63d)
The main benefit here is when we are using a systemd cgroup driver,
we actually ask systemd to add a PID, rather than doing it ourselves.
This way, we can add rootless exec PID to a cgroup.
This requires newer opencontainers/cgroups and coreos/go-systemd.
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
(cherry picked from commit 37b5acc2d7)
Signed-off-by: Aleksa Sarai <cyphar@cyphar.com>
Remove cgroupPaths field from struct setnsProcess, because:
- we can get base cgroup paths from p.manager.GetPaths();
- we can get sub-cgroup paths from p.process.SubCgroupPaths.
But mostly because we are going to need separate cgroup paths when
adopting cgroups.AddPid.
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
(cherry picked from commit 5730a141f1)
Signed-off-by: Aleksa Sarai <cyphar@cyphar.com>
The main idea is to maintain the code separately (and eventually kill V1
implementation).
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
(cherry picked from commit 5560020cbb)
Signed-off-by: Aleksa Sarai <cyphar@cyphar.com>
Implement support for the linux.intelRdt.schemata field of the spec.
This allows management of the "schemata" file in the resctrl group in a
generic way.
Signed-off-by: Markus Lehtonen <markus.lehtonen@intel.com>
(cherry picked from commit 41553216ee)
Signed-off-by: Aleksa Sarai <cyphar@cyphar.com>
This package was marked deprecated in commit 9b60a93cf3
("libcontainer/userns: migrate to github.com/moby/sys/userns"), which
was included in runc 1.2. Users have thus had a year to migrate to
github.com/moby/sys/userns and it's okay for us to remove this wrapper
package.
(Cherry-pick of commit e4f99b5c95b8f49434452edff82e73547c7a8252.)
Signed-off-by: Aleksa Sarai <cyphar@cyphar.com>
Set the process personality early to ensure it takes effect before
seccomp is initialized. If seccomp filters are applied first and they
block personality-related system calls (e.g., `personality(2)`),
subsequent attempts to set the personality will fail.
Signed-off-by: lifubang <lifubang@acmcoder.com>
(cherry picked from commit f7dda6e6dc)
Signed-off-by: lifubang <lifubang@acmcoder.com>
These sysctls are all per-userns (termed `ucounts` in the kernel code) are
settable with CAP_SYS_RESOURCE in the user namespace.
Signed-off-by: Tycho Andersen <tycho@tycho.pizza>
(cherry picked from commit 70d88bc449)
libcontainer/user was marked as deprecated in d9ea71bf96 ("deprecate
libcontainer/user") and users have had plenty of time to migrate to
github.com/moby/sys/user.
Signed-off-by: Aleksa Sarai <cyphar@cyphar.com>
In certain deployments, it's possible for runc to be spawned by a
process with a restrictive cpumask (such as from a systemd unit with
CPUAffinity=... configured) which will be inherited by runc and thus the
container process by default.
The cpuset cgroup used to reconfigure the cpumask automatically for
joining processes, but kcommit da019032819a ("sched: Enforce user
requested affinity") changed this behaviour in Linux 6.2.
The solution is to try to emulate the expected behaviour by resetting
our cpumask to correspond with the configured cpuset (in the case of
"runc exec", if the user did not configure an alternative one). Normally
we would have to parse /proc/stat and /sys/fs/cgroup, but luckily
sched_setaffinity(2) will transparently convert an all-set cpumask (even
if it has more entries than the number of CPUs on the system) to the
correct value for our usecase.
For some reason, in our CI it seems that rootless --systemd-cgroup
results in the cpuset (presumably temporarily?) being configured such
that sched_setaffinity(2) will allow the full set of CPUs. For this
particular case, all we care about is that it is different to the
original set, so include some special-casing (but we should probably
investigate this further...).
Reported-by: ningmingxiao <ning.mingxiao@zte.com.cn>
Reported-by: Martin Sivak <msivak@redhat.com>
Reported-by: Peter Hunt <pehunt@redhat.com>
Signed-off-by: Aleksa Sarai <cyphar@cyphar.com>
Also, use GetPath() in Apply to get the resctrl group path, similar to
other methods of intelRdtManager.
Signed-off-by: Markus Lehtonen <markus.lehtonen@intel.com>
If intelRdt is specified in the spec, check that the resctrl fs is
actually mounted. Fixes e.g. the case where "intelRdt.closID" is
specified but runc silently ignores this if resctrl is not mounted.
Signed-off-by: Markus Lehtonen <markus.lehtonen@intel.com>
This was added in 2ee9cbbd12 ("It's /proc/stat, not /proc/stats") with
no actual justification, and doesn't really make much sense on further
inspection:
* /proc/net is a symlink to "self/net", which means that /proc/net/dev
is a per-process file, and so overmounting it would only affect pid1.
Any other program that cares about /proc/net/dev would see their own
process's configuration, and unprivileged processes wouldn't be able
to see /proc/1/... data anyway.
In addition, the fact that this is a symlink means that runc will
deny the overmount because /proc/1/net/dev is not in the proc
overmount allowlist. This means that this has not worked for many
years, and probably never worked in the first place.
* /proc/self/net is already namespaced with network namespaces, so the
primary argument for allowing /proc overmounts (lxcfs-like masking of
procfs files to emulate namespacing for files that are not properly
namespaced for containers -- such as /proc/cpuinfo) is moot.
It goes without saying that lxcfs has never overmounted
/proc/self/net/... files, so the general "because lxcfs"
justification doesn't hold water either.
* The kernel has slowly been moving towards blocking overmounts in
/proc/self/. Linux 6.12 blocked overmounts for fd, fdinfo, and
map_files; future Linux versions will probably end up blocking
everything under /proc/self/.
Fixes: 2ee9cbbd12 ("It's /proc/stat, not /proc/stats")
Signed-off-by: Aleksa Sarai <cyphar@cyphar.com>
Since opencontainers/cgroups v0.0.2 (commit b206a015), all stuct
Resources fields are annotated with "omitempty" attribute.
As a result, the loaded configuration may have Resources == nil.
It is totally OK (rootless containers may have no resources configured)
except since commit 6c5441e5, cgroup v1 fs manager requires Resources to
be set in the call to NewManager (this is a cgroup v1 deficiency,
or maybe our implementation deficiency, or both).
To work around this, let's add code to ensure Resources is never nil
after loading from state.json.
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
The per-file deprecation in cgroup_deprecated.go is not working,
let's replace it.
Link to Hooks.Run in Hook.Run deprecation notice.
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
Implement support for passing Linux Network Devices to the container
network namespace.
The network device is passed during the creation of the container,
before the process is started.
It implements the logic defined in the OCI runtime specification.
Signed-off-by: Antonio Ojea <aojea@google.com>
Instead of generating a list of tmpfs mount and have a special function
to check whether the path is in the list, let's go over the list of
mounts directly. This simplifies the code and improves readability.
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
Since its code is now trivial, and it is only called from a single
place, it does not make sense to have it as a separate function.
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
It makes sense to ignore cgroup mounts much early in the code,
saving some time on unnecessary operations.
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>