LWN:管理文件系统在namespace中的UID映射!

探讨了在Linux系统中,通过用户命名空间实现ID-shifting的方法,包括shiftfs、shiftingbindmount以及一种新的解决方案,该方案允许更简单的ID映射,无需修改内核文件系统层代码。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

关注了就能看到更多这么棒的文章哦~

Filesystem UID mapping for user namespaces: yet another shiftfs

By Jonathan Corbet
February 17, 2020

原文来自:https://lwn.net/Articles/812504/

一直以来都有人在建议使用一个ID-shifting virtual filesystem(ID会变化的虚拟文件系统),可以在对底层的真实文件系统发起request的时候,先对user和group ID进行重新映射(remap)。不过这个建议仅在讨论阶段,没有进入mainline。相应的有两种实现,分别是shiftfs和shifting bind mount。现在有人又提出了一种新的解决方案,这种新方法理论上来说更加简单,基本没有修改kernel的文件系统层代码。

ID-shifting filesystem主要用在user namespace,它有许多有趣的特性,其中之一就是对于namespace内部的user ID和外部的user ID会进行映射。通常的用法是能够把某个进程在此namespace内部映射为root用户、而不需要给它在namespace之外的root权限。比如可以配置一个user namespace让它内部的ID 0就对应到外部的ID 10000,这样对ID区间进行设置之后,内部的ID 20就对应到外部的10020。这样user namespace就可以实现ID shifting了。

在使用了user namespace的系统之,经常需要把它们配置成不重叠的ID区间,从而确保在多个容器(container)之间的隔离。不过,通常来说大家不喜欢这种完全的隔离。James Bottomley创建shiftfs的目的就是希望能让user namespace内部的进程可以用root权限访问某个特定的文件系统。而本文提到的Christian Brauner的patch set所针对的应用场景则是希望让多个容器(container)可以访问同一个公用的文件系统,并且可以采用相同的user ID和group ID来访问这个文件系统。这两种方法其实都是希望能对user ID和group ID进行映射,不再使用这个namespace里面它本来的ID。

shiftfs是一个虚拟文件系统,在对UID和GID进行remapping(也就是加上哪个固定偏移量)的时候,实际上是把相关的操作请求传递给底层文件系统。后来出来的bind-mount方案则不需要改动每种文件系统的代码,而是把shift行为作为mount的一个参数来指定。Brauner的方案在2019 Linux Plumbers Conference会议上有过介绍,它把shift行为变成了user namespace自己的一个属性。

Linux和其他Unix类型的系统一样,它的进程都有绑定的user ID和group ID。通常人们认为这些ID是用来控制文件访问的,其实不完全是这样。Linux在访问文件系统的时候还维护了另一组user ID和groupd ID,这组ID可以通过setfsuid()和setfsgid()系统调用来改变(当然需要有权限改变)。这个功能很少有人用,所以一般来说文件系统中用到的的user ID和group ID(后面称之为filesystem ID, FSID)都跟我们通常说的ID(normal ID)是相等的。不过这两种ID在系统最初设计的时候就是分离开的,可以不一致。

user namespace在实现的时候需要知道这些filesystem ID(FSID),不过这个信息从来没有暴露到kernel以外。Brauner的patch set就是把这些FSID明确定下来,允许他们可以映射成跟normal ID不同的值。具体来说,它会针对这个user namespace内部运行的每个进程,在/proc下面创建两个新文件(fsuid_map和fsgid_map)。这些文件就好像现有的uid_map和gid_map文件一样,可以填写需要remap的ID范围,不过相应的它们是对FSID的修改而已。

举例来说,系统管理员可以在当前系统中把container内部从0开始的100个user ID,映射到container外部的10000-10100区域,只需要在uid_map里面写一句话:

    0 10000 100

缺省情况下,这个映射动作也会影响这个namespace的FSID,不过如果我们需要对FSID进行不同的映射,例如映射到20000开始,那么系统管理员可以在fsuid_map里面写如下内容:

    0 20000 100

这种方法比以前的方案都要简单,不过实现起来还是需要一个24段的patch set。这个改动可以把所有的ID映射都记录在同一个地方,不需要特殊的文件系统来支持,也不需要特殊的mount type,肯定有人很喜欢这个方案。

不过,这种实现方式有个很大的局限:FSID mapping是全局映射,会影响一个container内部文件系统的所有操作,无论是在访问哪个哪个文件系统。shiftfs或者bind-mount方案则可以针对不同的文件系统来进行不同的映射。这个小缺点具体是不是一个问题,主要取决于人们希望怎么使用这个功能。确实有可能有些用户希望能针对不同文件系统配置不同的访问权限,不过如果真的去实现的话,应该会相当复杂。

不过,目前还没有人提及这个需求。这组patch set才刚刚走到第二版,可能有许多潜在用户还没有看到它。对ID-shifting功能来说,后面的第三版很可能会是个很好的方案啦,让我们拭目以待吧。

全文完

LWN文章遵循CC BY-SA 4.0许可协议。

欢迎分享、转载及基于现有协议再创作~

长按下面二维码关注,关注LWN深度文章以及开源社区的各种新近言论~

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值