从内部检测一个chroot监狱

如何检测没有root权限的chroot监狱? 假设一个标准的BSD或Linux系统。 我想到的最好的方法是查看“/”的inode值,并考虑是否合理低,但是我想要一个更准确的检测方法。

[edit 20080916 142430 EST]文件系统是不够的,因为复制像/ boot和/ dev这样的东西来欺骗被监禁的用户并不困难。

[edit 20080916 142950 EST]对于Linux系统来说,检查/ proc中的意外值是合理的,但是那些首先不支持/ proc的系统呢?

Solutions Collecting From Web of "从内部检测一个chroot监狱"

如果它是文件系统的根目录,那么inode对于/将始终为2,但是您可能会在完整的文件系统中进行chroot操作。 如果只是chroot(而不是其他的虚拟化),你可以运行mount和比较你所看到的安装的文件系统。 确认每个安装点都有inode 2。

防止这样的东西是重点。 如果你的代码应该在chroot中运行,那么在启动时设置一个标志。 如果你正在黑客攻击,请检查已知位置的几个常见事物,将/ etc中的文件计数在/ dev中。

在BSD系统上(与uname -a一起检查),proc应该始终存在。 检查/ proc / 1 / exe的dev / inode对(在该路径上使用stat,它不会跟随通过文本而是通过底层钩子的符号链接)匹配/ sbin / init。

检查inode#2的根目录也是一个不错的选择。

在大多数其他系统上,root用户可以通过尝试使用fchdir破解技巧来更快地找到它。 如果你去了chroot监狱的任何地方。

在具有root权限的Linux上,测试init进程的根目录是否是根目录。 尽管/proc/1/root始终是/proc/1/root一个符号链接,但是它跟随着“master”根目录(假设init进程不是chroot,但是很少这样做)。 如果/proc没有挂载,你可以打赌你在chroot。

 [ "$(stat -c %d:%i /)" != "$(stat -c %d:%i /proc/1/root/.)" ] # With ash/bash/ksh/zsh ! [ -x /proc/1/root/. ] || [ /proc/1/root/. -ef / ] 

这比查看/proc/1/exe更为精确,因为如果从上次启动以来init已经升级,或者chroot在主根文件系统上,并且init被硬链接在chroot之外,那么chroot可能会与chroot不同。

如果您没有root权限,可以查看/proc/1/mountinfo/proc/$$/mountinfo ( 在Linux内核文档中的filesystems/proc.txt中简要记录 )。 这个文件是世界可读的,并且在文件系统的进程视图中包含了很多关于每个挂载点的信息。 该文件中的路径受影响读取器进程的chroot限制(如果有的话)。 如果将/proc/1/mountinfo进程读入与全局根不同的文件系统(假设pid 1的根是全局根目录),则/proc/1/mountinfo不会出现/proc/1/mountinfo 。 如果读取/proc/1/mountinfo/proc/1/mountinfo到全局根文件系统上的一个目录,则/proc/1/mountinfo出现/proc/1/mountinfo ,但具有不同的装载标识。 顺便提一句,根域( $4 )表示chroot在主文件系统中的位置。 再次,这是特定于Linux的。

 [ "$(awk '$5=="/" {print $1}' </proc/1/mountinfo)" != "$(awk '$5=="/" {print $1}' </proc/$$/mountinfo)" ] 

如果你不在chroot中,那么inode将会永远是2.你可以使用

 stat -c %i / 

要么

 ls -id / 

Interresting,但我们试着找到chroot目录的路径。 请求stat哪些设备/位于:

 stat -c %04D / 

第一个字节是设备的主要字节,以免字节较小。 例如,0802表示主要8,次要1.如果您检入/ dev,您将看到此设备是/ dev / sda2。 如果你是root用户,你可以在你的chroot中直接创建对应的设备:

 mknode /tmp/root_dev b 8 1 

现在,让我们找到与我们的chroot关联的inode。 debugfs允许使用inode编号的文件列表内容。 例如, ls -id /返回923960:

 sudo debugfs /tmp/root_dev -R 'ls <923960>' 923960 (12) . 915821 (32) .. 5636100 (12) var 5636319 (12) lib 5636322 (12) usr 5636345 (12) tmp 5636346 (12) sys 5636347 (12) sbin 5636348 (12) run 5636349 (12) root 5636350 (12) proc 5636351 (12) mnt 5636352 (12) home 5636353 (12) dev 5636354 (12) boot 5636355 (12) bin 5636356 (12) etc 5638152 (16) selinux 5769366 (12) srv 5769367 (12) opt 5769375 (3832) media 

有趣的信息是inode ..条目:915821.我可以问它的内容:

 sudo debugfs /tmp/root_dev -R 'ls <915821>' 915821 (12) . 2 (12) .. 923960 (20) debian-jail 923961 (4052) other-jail 

debian-jail目录有inode 923960.因此,我的chroot目录的最后一个组件是debian-jail 。 现在我们来看父目录(inode 2):

 sudo debugfs /tmp/root_dev -R 'ls <2>' 2 (12) . 2 (12) .. 11 (20) lost+found 1046529 (12) home 130817 (12) etc 784897 (16) media 3603 (20) initrd.img 261633 (12) var 654081 (12) usr 392449 (12) sys 392450 (12) lib 784898 (12) root 915715 (12) sbin 1046530 (12) tmp 1046531 (12) bin 784899 (12) dev 392451 (12) mnt 915716 (12) run 12 (12) proc 1046532 (12) boot 13 (16) lib64 784945 (12) srv 915821 (12) opt 3604 (3796) vmlinuz 

名为opt目录具有inode 915821,inode 2是文件系统的根目录。 所以我的chroot目录是/opt/debian-jail 。 当然, /dev/sda1可能会挂载在另一个文件系统上。 你需要检查(使用lsof或直接挑选信息/proc )。

我认为这取决于你为什么会陷入困境,是否有任何努力掩饰了它。

我会检查/ proc,这些文件是自动生成的系统信息文件。 内核会将它们填充到根文件系统中,但它们可能不存在于chroot文件系统中。

如果根文件系统的/ proc已被绑定到chroot中的/ proc,那么该信息和chroot环境之间可能存在一些差异。 例如检查/ proc / mounts。

同样,检查/系统。

如果你用schroot输入了chroot,那么你可以检查$ debian_chroot的值。