diff --git a/Makefile.am b/Makefile.am index a2dff75c74..b4e6bbcb29 100644 --- a/Makefile.am +++ b/Makefile.am @@ -200,6 +200,7 @@ PYTHON_TESTS = tests/test_capabilities.py \ tests/test_devices.py \ tests/test_hostname.py \ tests/test_limits.py \ + tests/test_oci_features.py \ tests/test_mounts.py \ tests/test_paths.py \ tests/test_pid.py \ diff --git a/tests/test_oci_features.py b/tests/test_oci_features.py new file mode 100644 index 0000000000..d8b270c929 --- /dev/null +++ b/tests/test_oci_features.py @@ -0,0 +1,229 @@ +#!/bin/env python3 +# crun - OCI runtime written in C +# +# crun is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2 of the License, or +# (at your option) any later version. +# +# crun is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with crun. If not, see . + +import subprocess +import json +from tests_utils import * + +expected_features = { + "ociVersionMin": "1.0.0", + "ociVersionMax": "1.1.0-rc.3", + "hooks": [ + "prestart", + "createRuntime", + "createContainer", + "startContainer", + "poststart", + "poststop" + ], + "mountOptions": [ + "rw", + "rrw", + "ro", + "rro", + "rdirsync", + "rdiratime", + "rnodev", + "rnorelatime", + "nodiratime", + "rnodiratime", + "diratime", + "rnoatime", + "rnomand", + "ratime", + "rmand", + "mand", + "idmap", + "noatime", + "nomand", + "dirsync", + "rnosuid", + "atime", + "rnoexec", + "nodev", + "rbind", + "norelatime", + "bind", + "rnostrictatime", + "strictatime", + "rstrictatime", + "rprivate", + "rsuid", + "remount", + "suid", + "nostrictatime", + "rrelatime", + "nosuid", + "noexec", + "rslave", + "dev", + "rdev", + "rsync", + "relatime", + "sync", + "shared", + "rshared", + "unbindable", + "runbindable", + "defaults", + "async", + "rasync", + "private", + "tmpcopyup", + "rexec", + "exec", + "slave" + ], + "linux": { + "namespaces": [ + "cgroup", + "ipc", + "mount", + "network", + "pid", + "user", + "uts" + ], + "capabilities": [ + "CAP_CHOWN", + "CAP_DAC_OVERRIDE", + "CAP_DAC_READ_SEARCH", + "CAP_FOWNER", + "CAP_FSETID", + "CAP_KILL", + "CAP_SETGID", + "CAP_SETUID", + "CAP_SETPCAP", + "CAP_LINUX_IMMUTABLE", + "CAP_NET_BIND_SERVICE", + "CAP_NET_BROADCAST", + "CAP_NET_ADMIN", + "CAP_NET_RAW", + "CAP_IPC_LOCK", + "CAP_IPC_OWNER", + "CAP_SYS_MODULE", + "CAP_SYS_RAWIO", + "CAP_SYS_CHROOT", + "CAP_SYS_PTRACE", + "CAP_SYS_PACCT", + "CAP_SYS_ADMIN", + "CAP_SYS_BOOT", + "CAP_SYS_NICE", + "CAP_SYS_RESOURCE", + "CAP_SYS_TIME", + "CAP_SYS_TTY_CONFIG", + "CAP_MKNOD", + "CAP_LEASE", + "CAP_AUDIT_WRITE", + "CAP_AUDIT_CONTROL", + "CAP_SETFCAP", + "CAP_MAC_OVERRIDE", + "CAP_MAC_ADMIN", + "CAP_SYSLOG", + "CAP_WAKE_ALARM", + "CAP_BLOCK_SUSPEND", + "CAP_AUDIT_READ", + "CAP_PERFMON", + "CAP_BPF", + "CAP_CHECKPOINT_RESTORE" + ], + "cgroup": { + "v1": True, + "v2": True, + "systemd": True, + "systemdUser": True + }, + "seccomp": { + "enabled": True, + "actions": [ + "SCMP_ACT_ALLOW", + "SCMP_ACT_ERRNO", + "SCMP_ACT_KILL", + "SCMP_ACT_KILL_PROCESS", + "SCMP_ACT_KILL_THREAD", + "SCMP_ACT_LOG", + "SCMP_ACT_NOTIFY", + "SCMP_ACT_TRACE", + "SCMP_ACT_TRAP" + ], + "operators": [ + "SCMP_CMP_NE", + "SCMP_CMP_LT", + "SCMP_CMP_LE", + "SCMP_CMP_EQ", + "SCMP_CMP_GE", + "SCMP_CMP_GT", + "SCMP_CMP_MASKED_EQ" + ], + "archs": [ + "SCMP_ARCH_AARCH64", + "SCMP_ARCH_ARM", + "SCMP_ARCH_MIPS", + "SCMP_ARCH_MIPS64", + "SCMP_ARCH_MIPS64N32", + "SCMP_ARCH_MIPSEL", + "SCMP_ARCH_MIPSEL64", + "SCMP_ARCH_MIPSEL64N32", + "SCMP_ARCH_PPC", + "SCMP_ARCH_PPC64", + "SCMP_ARCH_PPC64LE", + "SCMP_ARCH_RISCV64", + "SCMP_ARCH_S390", + "SCMP_ARCH_S390X", + "SCMP_ARCH_X32", + "SCMP_ARCH_X86", + "SCMP_ARCH_X86_64" + ] + }, + "apparmor": { + "enabled": True + }, + "selinux": { + "enabled": True + } + }, + "annotations": { + "io.github.seccomp.libseccomp.version": "2.5.3", + "org.opencontainers.runc.checkpoint.enabled": True, + "run.oci.crun.checkpoint.enabled": True, + "io.github.containers.crun.commit": "0da15fb20f5ef55166e679862a0a7cca5fe6021a", + "io.github.containers.crun.version": "1.8.5.0.0.0.30-7da99" + } +} + +def test_crun_features(): + try: + output = run_crun_command(["features"]) + features = json.loads(output) + if features == expected_features: + return 0 + else: + print("Features mismatch!") + print("Expected:") + print(json.dumps(expected_features, indent=4)) + print("Actual:") + print(json.dumps(features, indent=4)) + return -1 + except Exception as e: + print("Error running crun features:", str(e)) + return -1 + +all_tests = { + "crun-features" : test_crun_features, +} + +if __name__ == "__main__": + tests_main(all_tests)