From: Stefano Garzarella A "local" namespace can change its `child_ns_mode` sysctl to "global", allowing nested namespaces to access global CIDs. This can be exploited by an unprivileged user who gained CAP_NET_ADMIN through a user namespace. Prevent this by rejecting writes that attempt to set `child_ns_mode` to "global" when the current namespace's mode is "local". Fixes: eafb64f40ca4 ("vsock: add netns to vsock core") Cc: bobbyeshleman@meta.com Signed-off-by: Stefano Garzarella --- net/vmw_vsock/af_vsock.c | 15 ++++++++++++--- 1 file changed, 12 insertions(+), 3 deletions(-) diff --git a/net/vmw_vsock/af_vsock.c b/net/vmw_vsock/af_vsock.c index 3b629b4a0359..9880756d9eff 100644 --- a/net/vmw_vsock/af_vsock.c +++ b/net/vmw_vsock/af_vsock.c @@ -95,8 +95,9 @@ * the namespace's own ns_mode. * * Changing child_ns_mode only affects newly created namespaces, not the - * current namespace or existing children. At namespace creation, ns_mode - * is inherited from the parent's child_ns_mode. + * current namespace or existing children. A "local" namespace cannot set + * child_ns_mode to "global". At namespace creation, ns_mode is inherited + * from the parent's child_ns_mode. * * The init_net mode is "global" and cannot be modified. * @@ -2844,8 +2845,16 @@ static int vsock_net_child_mode_string(const struct ctl_table *table, int write, if (ret) return ret; - if (write) + if (write) { + /* Prevent a "local" namespace from escalating to "global", + * which would give nested namespaces access to global CIDs. + */ + if (vsock_net_mode(net) == VSOCK_NET_MODE_LOCAL && + new_mode == VSOCK_NET_MODE_GLOBAL) + return -EPERM; + vsock_net_set_child_mode(net, new_mode); + } return 0; } -- 2.53.0