2.1 猜测为什么“passwd”,“chsh”,“su”,和“sudo”命令需要Set-UID机制,如果它们没有这些机制的话,会发生什么,如果你不熟悉这些程序,你可以通话阅读使用手册来熟悉它们,如果你拷贝这些命令到自己的目录下,这些程序就不会是Set-UID程序,运行这些拷贝的程序,观察将会发生什么。
从上面的截图可以看出:将passwd拷贝到/tmp/下,权限发生了变化(在原目录下suid位被设置),复件没有了修改密码的权限。
对于“chsh”,“su”,和“sudo”命令,把这些程序拷贝到用户目录下,同样不再具有root权限。
2.2.1 以root方式登录,拷贝/bin/zsh 到/tmp, 同时设置拷贝到tmp目录下的zsh为set-uid root权限,然后以普通用户登录,运行/tmp/zsh。你会得到root权限吗?请描述你的结果。
注意:这时候实验楼的password已经变成了刚才设置的密码。
普通用户运行tmp下的zsh获得了root权限
2.2.2 拷贝/bin/bash到/tmp目录,同时设置/tmp目录下的bash为Set-UID root权限,然后以普通用户登录,运行/tmp/bash。你会得到root权限吗?请描述你的结果。
运行tmp下的bash不能获得root权限
2.3 从上面步骤可以看出,/bin/bash有某种内在的保护机制可以阻止Set-UID机制的滥用。为了能够体验这种内在的保护机制出现之前的情形,我们打算使用另外一种shell程序——/bin/zsh。在一些linux的发行版中(比如Redora和Ubuntu),/bin/sh实际上是/bin/bash的符号链接。为了使用zsh,我们需要把/bin/sh链接到/bin/zsh。
下面的指令将会把默认的shell指向zsh:
$sudo su
Password:
#cd /bin
#rm sh
#ln -s zsh sh
2.4.1 你能够设置这个Set-UID程序运行你自己的代码而不是/bin/ls吗?如果你能的话,你的代码具有root权限吗?描述并解释你的观察。
普通用户运行test文件可以获得root权限
2.4.2 修改/bin/sh使得其返回到/bin/bash,重复上面的攻击,你仍然可以获得root权限吗?描述并解释你的观察。
修改sh连接回bash,运行test程序不能使普通用户获得root权限。
2.5.1 程序中有 q=0。程序会使用system()调用命令行。这个命令安全码?如果你是Bob,你能对系统的完整性妥协吗?你能重新移动一个对你没有写权限的文件吗?
并不能获得root权限
2.5.2 如果令q=1;刚才的攻击还会有效吗?请描述并解释你的观察。
将q=0改为q=1:
修改为q=1后,不会有效。前面步骤之所以有效,是因为system()函数调用/bin/sh,链接至zsh,具有root权限执行了cat file文件后,接着执行mv file file_new命令。
而当令q=1, execve()函数会把file; mv file file_new 看成是一个文件名,系统会提示不存在这个文件:
2.6.1 把myprog编译成一个普通用户下的程序在普通用户下运行
可见,它会使用LD_PRELOAD环境变量,重载sleep函数:
2.6.2 把myprog编译成一个Set-UID root的程序在普通用户下运行
在这种情况下,忽略LD_PRELOAD环境变量,不重载sleep函数,使用系统自带的sleep函数:
2.6.3 把myprog编译成一个Set-UID root的程序在root下运行
在这种情况下,使用LD_PRELOAD环境变量,使用重载的sleep函数:
2.6.4在一个普通用户下把myprog编译成一个Set-UID 普通用户的程序在另一个普通用户下运行
在这种情况下,不会重载sleep函数:
2.7 消除和清理特权
如图所示文件被修改了,原因在于设置uid前,zzz文件就已经被打开了。只要将语句setuid(getuid())移至调用open函数之前,就能避免这个问题。