unshare 如何使在没有真正 root 的情况下使用 chroot 成为可能?

How unshare makes possible to use chroot without real root?

chroot 根据 manual. The unshare command uses chroot.

需要 CAP_SYS_CHROOT

命令 unshare -UrR newroot/ 将在没有 运行 的情况下像 root 一样工作,这是有道理的,因为 -r 标志使我们 root 在命名空间内,给我们 CAP_SYS_CHROOT 能力。

unshare -UR newroot/ 不需要 运行 作为 root 时,问题就开始了,而 unshare -U chroot newroot/ 会给我 Operation not permitted 错误。所以在第一个,我不要求在用户命名空间内 root,第二个是相同的,但试图手动完成。

检查 code,使用 -R 时唯一发生的事情是将 newroot 设置为 optarg,所以我不明白为什么在一个例子中这个有效,另一个无效。

发生这种情况是因为 unshare(2) 首先被调用,并且由于 -U 而将其作为标志之一传递给 CLONE_NEWUSER。关于该标志的手册注释:

Unshare the user namespace, so that the calling process is moved into a new user namespace which is not shared with any previously existing process. As with the child process created by clone(2) with the CLONE_NEWUSER flag, the caller obtains a full set of capabilities in the new namespace.

现在进程在新命名空间中拥有全套功能,它可以调用 chroot(2)。请注意,该调用发生在调用具有映射 ID 的进程之前,因此此时,该进程在新用户命名空间中仍然享有特权。在调用 execve 启动新进程时,这些功能将被删除。

这就是您的 chroot 命令失败的原因:因为它缺少权限,而 unshare 命令在调用任何进程之前仍然享有特权。