我只是想知道为什么在安装了 sudo 的 Debian 系统上默认用户可以执行ls
但不能执行,ifconfig
因为二进制文件确实具有相同的权限:
-rwxr-xr-x 1 root root 114032 Jan 26 2013 /bin/ls
-rwxr-xr-x 1 root root 72296 Sep 7 2012 /sbin/ifconfig
所以我想一定有某种数据库或策略告诉系统谁可以执行命令,谁不能执行命令,但是我在哪里可以找到它?不可能,/etc/sudoers
因为在该文件中只定义了谁是 root sudoer,而谁又不只是这样:
%admin ALL=(ALL) ALL
john ALL=/usr/sbin/useradd, /usr/sbin/userdel, /usr/bin/passwd
那么john
就无法执行/sbin/ifconfig
,但是系统怎么知道他不被允许呢?
答案1
sudo
与这个小小的差异无关,限制更接近内核。你看,虽然每个人都有执行该程序的权利/sbin/ifconfig
,但并不意味着这个程序就会有有足够的权限以普通用户权限完成其工作。
基本上,通过 UNIX 权限设置,您有权/sbin/ifconfig
创建一个可执行代码为的进程。事实上,无论之后如何ls
以及如何ifconfig
表现,他们的过程是确实产生了。但是,ifconfig
将过早退出,因为执行它的用户授予的权限不够。引用弗兰克·托马斯的评论:
[它不能]抓取网卡对象
笔记:实际上您可能可以在ifconfig --help
没有特权的情况下运行。由于此操作不需要使用网卡,因此不会失败,也不需要 root 权限。
现在,如果您想更具体地了解哪些操作被ifconfig
低权限拒绝,您可能想strace
尝试一下。这是一个带有 的示例ls
。
strace - 跟踪系统调用和信号
这错误代码拒绝许可的值为 13 ( EACCES
)。通过使用strace
我可以找出触发了哪些系统调用EACCES
:
$ strace ls ~ 2>&1 | grep EACCES
# No output, I can read my home directory just fine.
$ strace ls /root 2>&1 | grep EACCES
openat(AT_FDCWD, "/root", O_RDONLY|O_NONBLOCK|O_DIRECTORY|O_CLOEXEC) = -1 EACCES (Permission denied)
在那里,您可以看到openat
系统调用失败。事实上,作为我当前的用户,我无权读取该/root
目录,因此当内核ls
尝试获取有关/root
.当ls
意识到openat
失败并返回EACCES
时,它只是告诉我:
ls: 无法打开目录 /root: 权限被拒绝
现在,由程序在系统调用失败时通知用户。例如,在 C 中:
if((rootdir = opendir("/root")) == NULL){
perror("myprogram");
exit(1);
}
在低权限的情况下,这将导致:
$ ./myprogram
myprogram: Permission denied
现在,如果您运行strace /sbin/ifconfig
,您将能够找出以ifconfig
您的用户身份运行时哪个系统调用被拒绝。这是我尝试关闭无线接口的示例:
$ strace ifconfig wlan0 down 2>&1 | grep EPERM
ioctl(4, SIOCSIFFLAGS, {ifr_name="wlan0", ???}) = -1 EPERM (Operation not permitted)
如您所见,ioctl
系统调用失败。在这种情况下,错误调用是EPERM
(1:不允许操作)。该ifconfig
程序会在以下位置警告您:它的setifflags
功能:
// ...
if (ioctl(s, SIOCSIFFLAGS, &ifreq) == -1)
err(EXIT_FAILURE, "SIOCSIFFLAGS");
// ...