为什么在 /usr/bin 中更改权限时某些应用程序停止工作?

ale*_*ail 6 osx permissions crash

在 OS X 上,我的一个朋友/usr/bin使用 Finder 递归地更改了权限,以便对所有人进行大写访问。

这是它的完成方式:

转到/usr/binFinder,然后在信息窗口底部设置权限:

Finder 更改权限

之后,您就不能再运行Terminal.app了。但是您仍然可以运行磁盘工具,这是在没有终端的情况下从中恢复所必需的。

这是您在这种情况下遇到的错误:

Last login: Fri Jul  4 15:39:24 on ttys001
login(27006,0x7fff78115310) malloc: *** error for object 0x7fceb3412cc0: pointer being freed was not allocated
*** set a breakpoint in malloc_error_break to debug
Run Code Online (Sandbox Code Playgroud)

幸运的是,我很快就在这里找到了一个提到这个问题的问题。

我的第一个想法是这是一个硬件问题(可能是硬盘驱动器/RAM/等中的一些随机损坏......)。

此错误与 中的错误权限/usr/bin有何关系?

在尝试处理损坏的系统以获得清晰的差异列表时,我得到了这个:

$ sudo -s
sudo: effective uid is not 0, is sudo installed setuid root?
Run Code Online (Sandbox Code Playgroud)

这是diskutil verifyPermissions(解决问题顺便说一句)的结果:

(太大了,这里就不贴了)

每行的格式如下:

Permissions differ on "usr/bin/sudo"; should be -r-s--x--x ; they are -rwxr-xrwx
Run Code Online (Sandbox Code Playgroud)

但我只留下了文件名、它应该拥有的权限和当前的权限:

http://pastie.org/9358204

Permissions differ on "usr/bin/login"; should be -r-sr-xr-x ; they are -rwxr-xrwx
Run Code Online (Sandbox Code Playgroud)

dam*_*ien 6

问题确实在于 Finder 修改权限的方式并不仅仅像人们想象的那样影响指示的位。出于某种原因,它将文件模式的第一个八进制清零,并且不影响可执行位。因此,一些重要项目得到他们setuid/setgidsticky比特剥离,这使得他们要么无用或行为不正常。

某些程序需要 setuid 位,/usr/bin/因为它们必须在比普通程序更低的级别上与系统交互。例如sudopasswdnewgrplogin需要超越权限给普通用户的那些,这就是为什么你需要一个密码来执行它们。如果你删除它们的 setuid 位,它们就不能完成它们的工作,这会导致它们过早退出甚至崩溃。

因此,例如,正确的权限/usr/bin/login4555or-r-sr-xr-x并且在您朋友的操作之后我们有0757or -rwxr-xrwx。该Terminal.app调用/usr/bin/login到您的用户连接到一个TTY(见man stty)和丢失的setuid位导致它失败。释放未分配的指针可能是与此相关的错误。在 OS X 10.6.8 上,我没有收到此指针错误,但Terminal.app在启动后立即退出,我找到了类似login[6647]: pam_open_session(): system errorin的条目/var/log/system.log

编辑。正如 Antoine Lecaille 在评论中提到的,使 Terminal.app 功能失调的一种简单方法是发出$ sudo chmod -s /usr/bin/login. 请注意,之后您甚至无法打开新窗口,因为这也依赖于登录调用。要撤消它,只需执行$ sudo chmod +s /usr/bin/login.


我测试了 Finder 对权限的影响如下:

$ # create a directory with the same permissions as /usr/bin
$ mkdir -m 755 test
$ sudo chown root:wheel test
$ ls -l | grep test
drwxr-xr-x 2 root     wheel    68 Jul  6 15:01 test
$ # create 4096 empty files with all possible permissions
$ cd test
$ sudo touch file_{0..7}{0..7}{0..7}{0..7}
$ for perms in {0..7}{0..7}{0..7}{0..7}; do sudo chmod $perms file_$perms; done
Run Code Online (Sandbox Code Playgroud)

for循环可能需要一分钟才能完成,因为chmod是缓慢的。在此之后,您在文件夹中拥有file_wxyz具有权限wxyz的文件test。例如

$ ls -l file_4555
-r-sr-xr-x 1 root wheel 0 Jul  6 15:02 file_4555
Run Code Online (Sandbox Code Playgroud)

现在,我们可以使用 Finder:$ open .Cmd+来拉动您朋友的特技并更改文件夹及其所有内容的权限,I然后执行您在帖子中解释的操作。我决定授予对组轮的读取权限和对每个人的读写权限。

现在让我们看看我们的文件发生了什么:以下管道列出目录,读出包含权限的列,对其进行排序并抑制重复行:

$ ls -l | awk '{print $1}' | sort -u
-rw-r--rw-
-rw-r--rwx
-rw-r-xrw-
-rw-r-xrwx
-rwxr--rw-
-rwxr--rwx
-rwxr-xrw-
-rwxr-xrwx
total
$ ls -l file_4555
-rwxr-xrwx 1 root wheel 0 Jul  6 15:02 file_4555
Run Code Online (Sandbox Code Playgroud)

如您所见,不再设置 setuid/setgid/sticky 位;所有文件的读写权限相同;并且权限现在仅在执行位上有所不同(其中有八种可能的组合)。