If an error occurs during a test which sets up loopback devices, the
loopback device is not freed. Since most systems have very conservative
limits on the number of loopback devices, re-running a failing test
locally to debug it often ends up erroring out due to loopback device
exhaustion.
So let's just move the "losetup -d" to teardown, where it belongs.
Signed-off-by: Aleksa Sarai <cyphar@cyphar.com>
Apparently, having a minor of 0 does not always mean it's the
whole device (not a partition):
=== /proc/partitions (using major: 259) ===
major minor #blocks name
8 16 78643200 sdb
8 17 77593583 sdb1
8 30 4096 sdb14
8 31 108544 sdb15
259 0 934912 sdb16
8 0 78643200 sda
8 1 78641152 sda1
Rewrite the test to not assume minor is 0, and use
lsblk -d to find out whole devices.
This fixes a test case which was added in commit 7696402da.
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
The dmem controller is added into kernel v6.13 and is now enabled in
Fedora 42 kernels. Yet, systemd is not aware of dmem.
This fixes the test case failure on Fedora.
For the initial test case, see commit 27515719.
For earlier commits similar to this one, see
commits 601cf582, 05272718, e83ca519.
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>
In case there's a duplicate in the device list, the latter entry
overrides the former one.
So, we need to modify the last entry, not the first one. To do that,
use slices.Backward.
Amend the test case to test the fix.
Reported-by: lifubang <lifubang@acmcoder.com>
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
This support was missing from runc, and thus the example from the
podman-update wasn't working.
To fix, introduce a function to either update or insert new weights and iops.
Add integration tests.
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
Instead of providing systemd CPU quota value (CPUQuotaPerSec),
calculate it based on how opencontainers/cgroups/systemd handles
it (see addCPUQuota).
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
This tests the functionality added by commit cd96170c1
("Need to setup labeling of kernel keyrings."), for both
runc run and runc exec, with and without user namespace.
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
Since v3.14, CRIU always restores processes into a time namespace to
prevent backward jumps of monotonic and boottime clocks. This change
updates the container configuration to ensure that `runc exec` launches
new processes within the container's time namespace.
Fixes#2610
Signed-off-by: Andrei Vagin <avagin@gmail.com>
Those are no longer needed with shellcheck v0.10.0 (possibly with an
earlier version, too, but I am too lazy to check that).
While at it, fix a typo in the comment.
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
It was a mistake to say that SELinux need to be in the enforcing mode
for these tests to run. It only needs to be enabled.
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
As per
- https://github.com/opencontainers/runtime-spec/pull/1253
- https://github.com/opencontainers/runtime-spec/pull/1261
CPU affinity can be set in two ways:
1. When creating/starting a container, in config.json's
Process.ExecCPUAffinity, which is when applied to all execs.
2. When running an exec, in process.json's CPUAffinity, which
applied to a given exec and overrides the value from (1).
Add some basic tests.
Note that older kernels (RHEL8, Ubuntu 20.04) change CPU affinity of a
process to that of a container's cgroup, as soon as it is moved to that
cgroup, while newer kernels (Ubuntu 24.04, Fedora 41) don't do that.
Because of the above,
- it's impossible to really test initial CPU affinity without adding
debug logging to libcontainer/nsenter;
- for older kernels, there can be a brief moment when exec's affinity
is different than either initial or final affinity being set;
- exec's final CPU affinity, if not specified, can be different
depending on the kernel, therefore we don't test it.
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
This removes libcontainer/cgroups packages and starts
using those from github.com/opencontainers/cgroups repo.
Mostly generated by:
git rm -f libcontainer/cgroups
find . -type f -name "*.go" -exec sed -i \
's|github.com/opencontainers/runc/libcontainer/cgroups|github.com/opencontainers/cgroups|g' \
{} +
go get github.com/opencontainers/cgroups@v0.0.1
make vendor
gofumpt -w .
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
The "dmz" name was originally used because the libcontainer/dmz package
housed the runc-dmz binary, but since we removed it in commit
871057d863 ("drop runc-dmz solution according to overlay solution")
the name is an anachronism and we should just give it a more
self-explanatory name.
So, call it libcontainer/exeseal because the purpose of the package is
to provide tools to seal /proc/self/exe against attackers.
Signed-off-by: Aleksa Sarai <cyphar@cyphar.com>
Commit 770728e1 added Scheduler field into both Config and Process,
but forgot to add a mechanism to actually use Process.Scheduler.
As a result, runc exec does not set Process.Scheduler ever.
Fix it, and a test case (which fails before the fix).
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
Commit bfbd0305b added IOPriority field into both Config and Process,
but forgot to add a mechanism to actually use Process.IOPriority.
As a result, runc exec does not set Process.IOPriority ever.
Fix it, and a test case (which fails before the fix).
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
Looking into old opened runc issues, I noticed #1663 is there without
any resolution, and wrote this simple test checking if we mangle hook's
argv[0] in any way.
Apparently we're good, but the test actually makes sense to have.
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
Historically, when HOME is not explicitly set in process.Env,
and UID to run as doesn't have a corresponding entry in container's
/etc/passwd, runc sets HOME=/ as a fallback.
Add the corresponding check, for the sake of backward compatibility
preservation.
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
This is to ensure that changes in Process.Env handling won't affect
StartContainer hook.
Reported-by: lfbzhm <lifubang@acmcoder.com>
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
Assigning a multi-line value to a bash variable should not be so complex.
While at it, slightly reformat create_runtime_hook.
No functional change.
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
Instead of having every test helper binary in its own directory, let's
use /tests/cmd/_bin as a destination directory.
This allows for simpler setup/cleanup.
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
Because we have the overlay solution, we can drop runc-dmz binary
solution since it has too many limitations.
Signed-off-by: lifubang <lifubang@acmcoder.com>
This reverts commit 65a1074c75.
We needed [1] because when we removed the bindfd logic in [2] we had not
yet moved the binary cloning logic to Go and thus it was necessary to
increase the memory limit in CI because the clone was happening after
joining the cgroup. However, [3] finally moved that code to Go and thus
the cloning is now done outside of the container's cgroup and thus is no
longer accounted as part of the container's memory usage at any point.
Now we can properly support running a simple container with lower memory
usage as we did before.
[1]: commit 65a1074c75 ("increase memory.max in cgroups.bats")
[2]: commit b999376fb2 ("nsenter: cloned_binary: remove bindfd logic entirely")
[3]: commit 0e9a3358f8 ("nsexec: migrate memfd /proc/self/exe logic to Go code")
Signed-off-by: lfbzhm <lifubang@acmcoder.com>
[cyphar: fixed commit messages]
Signed-off-by: Aleksa Sarai <cyphar@cyphar.com>
Commit b999376fb2 ("nsenter: cloned_binary: remove bindfd logic
entirely") removed the read-only bind-mount logic from our cloned binary
code because it wasn't really safe because a container with
CAP_SYS_ADMIN could remove the MS_RDONLY bit and get write access to
/proc/self/exe (even with user namespaces this could've been an issue
because it's not clear if the flags are locked).
However, copying a binary does seem to have a minor performance impact.
The only way to have no performance impact would be for the kernel to
block these write attempts, but barring that we could try to reduce the
overhead by coming up with a mount that cannot have it's read-only bits
cleared.
The "simplest" solution is to create a temporary overlayfs using
fsopen(2) which uses the directory where runc exists as a lowerdir,
ensuring that the container cannot access the underlying file -- and we
don't have to do any copies.
While fsopen(2) is not free because mount namespace cloning is usually
expensive (and so it seems like the difference would be marginal), some
basic performance testing seems to indicate there is a ~60% improvement
doing it this way and that it has effectively no overhead even when
compared to just using /proc/self/exe directly:
% hyperfine --warmup 50 \
> "./runc-noclone run -b bundle ctr" \
> "./runc-overlayfs run -b bundle ctr" \
> "./runc-memfd run -b bundle ctr"
Benchmark 1: ./runc-noclone run -b bundle ctr
Time (mean ± σ): 13.7 ms ± 0.9 ms [User: 6.0 ms, System: 10.9 ms]
Range (min … max): 11.3 ms … 16.1 ms 184 runs
Benchmark 2: ./runc-overlayfs run -b bundle ctr
Time (mean ± σ): 13.9 ms ± 0.9 ms [User: 6.2 ms, System: 10.8 ms]
Range (min … max): 11.8 ms … 16.0 ms 180 runs
Benchmark 3: ./runc-memfd run -b bundle ctr
Time (mean ± σ): 22.6 ms ± 1.3 ms [User: 5.7 ms, System: 20.7 ms]
Range (min … max): 19.9 ms … 26.5 ms 114 runs
Summary
./runc-noclone run -b bundle ctr ran
1.01 ± 0.09 times faster than ./runc-overlayfs run -b bundle ctr
1.65 ± 0.15 times faster than ./runc-memfd run -b bundle ctr
Signed-off-by: Aleksa Sarai <cyphar@cyphar.com>