我确信这似乎是一个简单的问题,但我似乎无法向 Google 提出正确的问题。简而言之,我无法理解当给定文件系统在多个点安装时符号链接如何工作。
我一直遵循 FreeBSD 手册在我的小型家用服务器上设置应用程序监狱。一切都进展顺利,直到我遇到了设置主模板的倒数第二步。更具体地说,当我要发出以下命令时:
# cd /home/j/mroot
# mkdir s
# ln -s s/etc etc
# ln -s s/home home
# ln -s s/root root
# ln -s ../s/usr-local usr/local
# ln -s ../s/usr-X11R6 usr/X11R6
# ln -s ../../s/distfiles usr/ports/distfiles
# ln -s s/tmp tmp
# ln -s s/var var
现在,这些命令可以正常执行。我关心的是为什么。我知道主模板将以只读方式挂载,因此为多个 jail 挂载一个文件集没有问题。我感到困惑的是,鉴于主模板仅维护一组链接,操作系统如何知道要使用哪个服务的数据目录(/s 目录,为每个服务挂载读写)?假设我有两个服务,www 和 ftp。每个服务都将使用 /home/j/mroot 上的主模板(在 /home/j/ 上以只读方式挂载)并拥有自己的数据目录(位于 /home/js/;在 /home/j/ 上以读写方式挂载)。基于链接,文件系统如何知道它应该在一个 jail 中写入 www 数据目录,而在另一个 jail 中写入 ftp 数据目录?
另外,为什么某些链接需要“../”路径运算符?据我了解,这些运算符会让您退出当前目录并返回到文件系统的其他位置,这可能是无效路径?
如果这些问题很简单,我深表歉意。我的搜索没有找到任何结果,但我确实怀疑我可能只是问错了问题。作为参考,这里是特定 FreeBSD 手册页面的链接。
http://www.freebsd.org/doc/en/books/handbook/jails-application.html
提前感谢您的帮助。
答案1
好吧...让我们尝试回答这个问题。
设置和主/骨架目录
监狱系统的“根”目录是/home/j
。它包含 3 个以上的子目录:
/home/j/
|- mroot/ # The master (read-only) root directory
|- skel/ # The master (read-write) directory
|- js/ # Each jail will have a subdirectory here
# where its writable directories point to
|- <jail>/ # Each jail will have its own directory
现在mroot/
目录包含基本系统,因为你已经完成了制作安装词到该目录中。它将保留只读目录,例如bin/
和dev/
。所有可写目录(例如etc/
)将移动到该skel/
目录中。这是在第 14.5.1 节的步骤 3 中完成的。
到目前为止,还没有/home/j/mroot/etc/
文件夹(因为你移动了它),所以我们将为它创建一个符号链接。首先,我们将创建一个新的子目录s/
(短名称可能太短,因此很容易混淆)。这是在步骤 5 中完成的。文件夹的设置mroot/
现在看起来有点像这样。
/home/j/mroot/
|- s/ # Empty directory for writing to
|- etc # Symlink to s/etc/
|- home # Symlink to s/home/
|- ... # More symlinks are created
由于这些目录不存在,这些符号链接现在将被破坏。创建 jail 时将创建它们。
创建一个监狱
现在第三个文件夹(/home/j/js/
)将开始发挥作用。在这里,我们将为每个 jail 创建一个子目录来包含可写内容。
/home/j/js/
|- mail/
|- ns/
|- www/
将骨架目录(skel/
)复制到每个子目录中。
使用 nullfs 挂载,我们现在将所有内容绑定在一起。每个 jail 都会获得另一个目录。这些是 nullfs(只读)挂载/home/j/mroot
(15.5.2 中的第 1 步)。
/home/j/
|- mail/
|- ns/
|- www/
由于它们是挂载,进入这样的目录将带您到/home/j/mroot/
,尽管您的路径不会改变。每个 jail 都有一个可写的/etc/
文件夹,看起来是,/home/j/mail/etc/
但由于上面创建的挂载,它实际上是/home/j/mroot/etc/
。
但是,请记住,从一开始,这个文件夹就不再存在了。它被移动了,而是创建了一个符号链接。这个符号链接指向一个尚不存在的子文件夹/home/j/mroot/s/
。第二次 nullfs 挂载将修复此问题。
当创建指向/home/j/ns/s
的挂载时/home/js/ns
。此目标包含包含所有可写文件的骨架目录的副本。源/home/j/ns/s
实际上是/home/j/mroot/s
第一次挂载的结果。
例子
当 jail 访问 中的文件/etc/
(该文件应为可写)时,它实际上是/home/j/<jail>/etc/
在主机上访问。但是,由于/home/j/mroot/etc/
第一次挂载,这是一个挂载。但这个“目录”根本不是一个目录,它是一个符号链接/home/j/mroot/s/etc
,由于第二次挂载,它实际上是/home/js/ns/etc/
。
结论
我希望我成功地澄清了一点设置。一旦我再次理清思绪,我将重读我自己的答案,因为我仍然因为试图自己解决这个问题而头晕目眩!
答案2
这不完全是你想要的,但它可能会让你的生活更轻松埃兹贾伊尔。Ezjail 会自动创建监狱并对其进行模板化。