]> git.ipfire.org Git - thirdparty/systemd.git/commitdiff
namespace-util: generalize namespace_type_supported()
authorMike Yuan <me@yhndnzj.com>
Fri, 18 Apr 2025 19:55:27 +0000 (21:55 +0200)
committerMike Yuan <me@yhndnzj.com>
Mon, 21 Apr 2025 14:54:37 +0000 (16:54 +0200)
src/basic/namespace-util.c
src/basic/namespace-util.h
src/core/exec-invoke.c
src/core/execute.c
src/core/namespace.c
src/core/namespace.h
src/core/socket.c
src/test/test-tables.c

index b4ef5941fb6e02cdec57ecbddfee88822fbf1520..e62737898b48d1f5f6330b1899532060968aa02d 100644 (file)
@@ -48,6 +48,13 @@ NamespaceType clone_flag_to_namespace_type(unsigned long clone_flag) {
         return _NAMESPACE_TYPE_INVALID;
 }
 
+bool namespace_type_supported(NamespaceType type) {
+        assert(type >= 0 && type < _NAMESPACE_TYPE_MAX);
+
+        const char *p = pid_namespace_path(0, type);
+        return access(p, F_OK) >= 0;
+}
+
 static int pidref_namespace_open_by_type_internal(const PidRef *pidref, NamespaceType type, bool *need_verify) {
         int r;
 
index 0c227e5adf0182731f0f6176f4ee6c07780d42bc..d7ac8156f94aec9115b07c203b2dacb6b17f4d5e 100644 (file)
@@ -28,6 +28,8 @@ extern const struct namespace_info {
 
 NamespaceType clone_flag_to_namespace_type(unsigned long clone_flag);
 
+bool namespace_type_supported(NamespaceType type);
+
 int pidref_namespace_open_by_type(const PidRef *pidref, NamespaceType type);
 int namespace_open_by_type(NamespaceType type);
 
index 0bf6c836013b5e7eac8e9acbed702376bf7d73b7..7b283eb485aced6ae6004d043f34d6dfdba667f6 100644 (file)
@@ -1820,7 +1820,7 @@ static int apply_protect_hostname(const ExecContext *c, const ExecParameters *p,
         if (c->protect_hostname == PROTECT_HOSTNAME_NO)
                 return 0;
 
-        if (ns_type_supported(NAMESPACE_UTS)) {
+        if (namespace_type_supported(NAMESPACE_UTS)) {
                 if (unshare(CLONE_NEWUTS) < 0) {
                         if (!ERRNO_IS_NOT_SUPPORTED(errno) && !ERRNO_IS_PRIVILEGE(errno)) {
                                 *ret_exit_status = EXIT_NAMESPACE;
@@ -4339,7 +4339,7 @@ static int setup_delegated_namespaces(
                  * own user namespace). We need CAP_NET_ADMIN to be able to configure the loopback device in
                  * the new network namespace. And if we don't have that, then we could only create a network
                  * namespace without the ability to set up "lo". Hence gracefully skip things then. */
-                if (ns_type_supported(NAMESPACE_NET) && have_effective_cap(CAP_NET_ADMIN) > 0) {
+                if (namespace_type_supported(NAMESPACE_NET) && have_effective_cap(CAP_NET_ADMIN) > 0) {
                         r = setup_shareable_ns(runtime->shared->netns_storage_socket, CLONE_NEWNET);
                         if (ERRNO_IS_NEG_PRIVILEGE(r))
                                 log_exec_notice_errno(context, params, r,
@@ -4361,7 +4361,7 @@ static int setup_delegated_namespaces(
             exec_namespace_is_delegated(context, params, have_cap_sys_admin, CLONE_NEWIPC) == delegate &&
             runtime->shared && runtime->shared->ipcns_storage_socket[0] >= 0) {
 
-                if (ns_type_supported(NAMESPACE_IPC)) {
+                if (namespace_type_supported(NAMESPACE_IPC)) {
                         r = setup_shareable_ns(runtime->shared->ipcns_storage_socket, CLONE_NEWIPC);
                         if (ERRNO_IS_NEG_PRIVILEGE(r))
                                 log_exec_warning_errno(context, params, r,
index 6f4baa1fbfd114eed4971d3a3e9abb90d2098d62..76ad7345ca07af2c65f9c01453726a7c2d3ad14d 100644 (file)
@@ -243,7 +243,7 @@ ProtectControlGroups exec_get_protect_control_groups(const ExecContext *context)
          * use cgroup namespace, we ignore the setting and do not unshare the namespace.
          * ProtectControlGroups=private and strict get downgraded to no and yes respectively. This ensures
          * that strict always gets a read-only mount of /sys/fs/cgroup/. */
-        if (needs_cgroup_namespace(context->protect_control_groups) && !ns_type_supported(NAMESPACE_CGROUP)) {
+        if (needs_cgroup_namespace(context->protect_control_groups) && !namespace_type_supported(NAMESPACE_CGROUP)) {
                 if (context->protect_control_groups == PROTECT_CONTROL_GROUPS_PRIVATE)
                         return PROTECT_CONTROL_GROUPS_NO;
                 if (context->protect_control_groups == PROTECT_CONTROL_GROUPS_STRICT)
@@ -273,7 +273,7 @@ bool exec_is_cgroup_mount_read_only(const ExecContext *context) {
 bool exec_needs_pid_namespace(const ExecContext *context) {
         assert(context);
 
-        return context->private_pids != PRIVATE_PIDS_NO && ns_type_supported(NAMESPACE_PID);
+        return context->private_pids != PRIVATE_PIDS_NO && namespace_type_supported(NAMESPACE_PID);
 }
 
 bool exec_needs_mount_namespace(
index 01d3c977d419aa63b1913bcb67363f7348afc384..efdd93ddf9db912c77ea3f11a0d393ef2a0179ff 100644 (file)
@@ -3263,17 +3263,6 @@ int open_shareable_ns_path(int ns_storage_socket[static 2], const char *path, un
         return 1;
 }
 
-bool ns_type_supported(NamespaceType type) {
-        const char *t, *ns_proc;
-
-        t = namespace_type_to_string(type);
-        if (!t) /* Don't know how to translate this? Then it's not supported */
-                return false;
-
-        ns_proc = strjoina("/proc/self/ns/", t);
-        return access(ns_proc, F_OK) == 0;
-}
-
 static const char *const protect_home_table[_PROTECT_HOME_MAX] = {
         [PROTECT_HOME_NO]        = "no",
         [PROTECT_HOME_YES]       = "yes",
@@ -3309,19 +3298,6 @@ static const char *const protect_control_groups_table[_PROTECT_CONTROL_GROUPS_MA
 
 DEFINE_STRING_TABLE_LOOKUP_WITH_BOOLEAN(protect_control_groups, ProtectControlGroups, PROTECT_CONTROL_GROUPS_YES);
 
-static const char* const namespace_type_table[] = {
-        [NAMESPACE_MOUNT]  = "mnt",
-        [NAMESPACE_CGROUP] = "cgroup",
-        [NAMESPACE_UTS]    = "uts",
-        [NAMESPACE_IPC]    = "ipc",
-        [NAMESPACE_USER]   = "user",
-        [NAMESPACE_PID]    = "pid",
-        [NAMESPACE_NET]    = "net",
-        [NAMESPACE_TIME]   = "time",
-};
-
-DEFINE_STRING_TABLE_LOOKUP(namespace_type, NamespaceType);
-
 static const char* const protect_proc_table[_PROTECT_PROC_MAX] = {
         [PROTECT_PROC_DEFAULT]    = "default",
         [PROTECT_PROC_NOACCESS]   = "noaccess",
index 069cdb831abda8c8d6e316583b49115ccfe16697..0ff9b4d730962e2facc24140d8a9b624a970d756 100644 (file)
@@ -258,8 +258,3 @@ int temporary_filesystem_add(TemporaryFileSystem **t, size_t *n,
 
 MountImage* mount_image_free_many(MountImage *m, size_t *n);
 int mount_image_add(MountImage **m, size_t *n, const MountImage *item);
-
-const char* namespace_type_to_string(NamespaceType t) _const_;
-NamespaceType namespace_type_from_string(const char *s) _pure_;
-
-bool ns_type_supported(NamespaceType type);
index e7e8584d81d5d09425756c72b32b9b4dd40056ea..861aaba3d44c38192c76a374c3eb0512a0cfd402 100644 (file)
@@ -1570,7 +1570,7 @@ static int socket_address_listen_in_cgroup(
                     s->exec_runtime->shared &&
                     s->exec_runtime->shared->netns_storage_socket[0] >= 0) {
 
-                        if (ns_type_supported(NAMESPACE_NET)) {
+                        if (namespace_type_supported(NAMESPACE_NET)) {
                                 r = setup_shareable_ns(s->exec_runtime->shared->netns_storage_socket, CLONE_NEWNET);
                                 if (r < 0) {
                                         log_unit_error_errno(UNIT(s), r, "Failed to join network namespace: %m");
index 142ddc48328eed2997183ab24bc13251119d79e1..1896391beebbc2300aa4df40eeb4486bf86bb16d 100644 (file)
@@ -82,7 +82,6 @@ int main(int argc, char **argv) {
         test_table(mount_result, MOUNT_RESULT);
         test_table(mount_state, MOUNT_STATE);
         test_table(name_policy, NAMEPOLICY);
-        test_table(namespace_type, NAMESPACE_TYPE);
         test_table(notify_access, NOTIFY_ACCESS);
         test_table(notify_state, NOTIFY_STATE);
         test_table(output_mode, OUTPUT_MODE);