为什么普通用户可以通过运行“podman unshare chown”来放弃文件/文件夹?

为什么普通用户可以通过运行“podman unshare chown”来放弃文件/文件夹?

chown我认为,通常情况下,普通用户是不允许在没有 的情况下通过运行来泄露文件或目录的sudo。unix.stackexchange 上提出了一个问题并给出了答案:为什么普通用户无法chown访问文件?。我明白了为什么这样设计。

最近我开始玩无根 Podman。然后我了解到,例如,我可以运行

podman unshare chown -R 1111:1111 folder/

将文件夹的所有权更改folder为另一个用户/组(在上面的例子中,它将101110:101110默认在主机上)。

/etc/subid从某种意义上说,它打破了前面提到的限制。为什么允许这样做?这会导致一些潜在的安全问题吗?(root 用户在分配命名空间时可能应该小心谨慎?)

我只是个业余爱好者,所有东西都是在自己的笔记本电脑上运行的。所以我不需要太担心这个。不过,我只是出于好奇才想问这个问题。

答案1

总结:rootless podman 需要newuidmapnewgidmap它们是 setuid root 二进制文件,允许引导无根容器的操作。

回答提出的问题:

一切uid:gid通过使用无根容器可以创建的值首先已经为给定用户保留。它们没有被赠送,因为那些额外的uid:gid通过检查(永不重叠的)内容,可以轻松地将值关联回单个原始用户/etc/subuid/etc/subgid

长示例,后面附有解释。


以下是执行与 OP 相同命令的低级工具,可在每个标准 Linux 系统上使用(例如 Debian、RHEL(>= 7.7)等):

1号航站楼:

user@host$ stat -c '%u:%g %n' folder/a folder
1000:1000 folder/a
1000:1000 folder
user@host$ chown -R 1111:1111 folder/
chown: changing ownership of 'folder/a': Operation not permitted
chown: changing ownership of 'folder/': Operation not permitted
user@host$ id -u; id -g
1000
1000
user@host$ unshare -U
nobody@host$ echo $$
11893
nobody@host$ id -u; id -g
65534
65534
nobody@host$ chown -R 1111:1111 folder/
chown: changing ownership of 'folder/a': Invalid argument
chown: changing ownership of 'folder/': Invalid argument

请注意,错误现在甚至不再相同(请参阅下文)。

航站楼2:

user@host$ grep ^user: /etc/subuid /etc/subgid
/etc/subuid:user:1410720:65536
/etc/subgid:user:1410720:65536
user@host$ newuidmap 11893 0 1000 1 1 1410721 65535
user@host$ newgidmap 11893 0 1000 1 1 1410721 65535

上述命令将用户的真实 ID 和 GID(除了子 ID 和子 GID 之外,它们也是有效的)映射为 root 在其新创建的用户命名空间(其唯一成员是 shell 进程(命令从其运行))中,并将(几乎)整个分配的子 ID 和子 GID 范围也映射到它。由于它只能对 uid 执行一次,对 gid 执行一次,因此必须一次性完成。

再次在终端 1 上:

nobody@host$ id -u; id -g; exec bash
0
0
root@host# 
root@host# chown -v -R 1111:1111 folder/
changed ownership of 'folder/a' from root:root to 1111:1111
changed ownership of 'folder/' from root:root to 1111:1111

在终端2上:

user@host$ stat -c '%u:%g %n' folder/a folder
1411831:1411831 folder/a
1411831:1411831 folder

其中我们有 1411831-1111=1410720

对于 OP 的情况,考虑到 101110-1111=99999,更有可能的是,podman做过也映射第一个 subuid(为 1),给出 101110-1111+1=100000,因此 100000 是给定用户的可能值/etc/subuid/etc/subgid无论如何,您明白了。

为什么这样做有效?原因很简单:newuidmapnewgidmap是 setuid root 命令,或者至少具有足够的功能以便能够正常工作。它们是辅助工具,允许普通用户创建简单的用户命名空间以使用其分配的映射,这些映射在/etc/subuid/etc/subgid帐户最初创建的时间。

user@host$ stat -c %A /usr/bin/newuidmap /usr/bin/newgidmap
-rwsr-xr-x
-rwsr-xr-x

现在整个系列uid:gid从主机映射到用户命名空间,可用于此用户命名空间中的正常操作。因此,在此用户命名空间内,其根用户可以将值从范围内的任何值更改为范围内的其他值。大多数情况下,范围是 65536 个条目的片段(或者对于 podman 来说可能是 1+65536=65537),但主机有 2^32-1 的范围可用于此。不是用户命名空间:

1号航站楼:

root@host# chown 66000 folder
chown: changing ownership of 'folder': Invalid argument

未映射,以前没有进行任何映射时也出现过类似的错误。

请注意,正如故障排除,rootless podman 确实使用newuidmap并且newgidmap

9) 运行无根 Podman 命令时缺少 Newuidmap

Rootless Podman 需要安装 newuidmap 和 newgidmap 程序。

有关 uid 映射的更多内部工作原理,请参阅用户命名空间手册页。

相关内容