Linux 内核是否检查 inode 上的文件权限或打开的文件描述?

Linux 内核是否检查 inode 上的文件权限或打开的文件描述?

我写了这段测试代码,发现这个程序即使在运行时取消了读取权限,也始终能成功读取文件getchar()

#include <stdio.h>
#include <fcntl.h>
#include <unistd.h>
#include <stdint.h>
#include <sys/types.h> 
int main(){
    int f = open("a.txt",O_RDONLY);
    uint8_t data[200];
    printf("Got %d from read", pread(f, (void *)data, 200, 0));
    getchar();
    printf("Got %d from read", pread(f, (void *)data, 200, 0));
}

这个程序打印了

读完得9分

两次,即使我chmod a-r a.txt在暂停期间使用。

我很确定我只是一个普通用户,我的进程没有 CAP_DAC_OVERRIDE;为什么第二个不pread()返回任何错误?

我的猜测是,在进行读/写时,内核仅检查打开文件描述的文件权限,该文件描述是使用 创建的open(),并且即使我更改了底层文件系统上的文件权限也不会更改。

我的猜测正确吗?

额外问题:

  • 如果我是对的,那么 mmaped 区域怎么样?

  • 当我读/写/执行该映射区域时,内核是否只检查页表中记录的权限?

  • 存储在文件系统中的真正 inode 数据是否仅在创建打开文件描述和 mmap 区域时使用?

答案1

是的,仅在开放时检查权限并记录。因此,无论您是否能够写入文件,都无法写入以只读访问方式打开的文件描述符。

内核查阅内存中的索引节点而不是存储在文件系统中的索引节点。它们的不同之处在于打开文件的引用计数,并且挂载点获取已挂载文件的索引节点。

如果我是对的,那么 mmaped 区域怎么样?

相同的。 (传递给的 PROT_* 标志mmap()相当于传递给的 O_RDWR / O_RDONLY / O_WRONLY 标志open())。

当我读/写/执行该映射区域时,内核是否只检查页表中记录的权限?

我不确定它什么时候可以检查页表中记录的权限:-)。据我了解你的问题:是的。

存储在文件系统中的真正 inode 数据是否仅在创建打开文件描述和 mmap 区域时使用?

还检查元数据操作的 inode 权限,例如mkdir()open()与 O_CREAT 类似)。

并且不要忘记chdir(),这与任何调用都不同open()。 (或者至少,它与open()当前 Linux 上的任何调用不同)。

我不确定 SELinux 特定的权限。

相关内容