我是 Linux 新手。当我将文件设置为只读时,我仍然可以删除该文件。我在网上读到删除文件取决于它所在文件夹的权限。
为了清楚起见,假设我有一个目录 test(具有所有权限),其中有一个只读文件“abc.txt”。即使这个文件是只读的,我也可以轻松删除它。
现在考虑这样的情况:我有一个正在测试的名为“sub”的子目录。该目录是只读的。当我想删除这个子目录时,它会抛出一个错误,指出无法删除这个目录。
在 Linux 中,目录也被视为文件。但只读文件与只读目录的行为有所不同。
这是什么原因呢?
答案1
因为 Unix 就是这样定义的,并且 POSIX 需要这种行为。 Linux 试图兼容 Unix 和 POSIX。
您可能对什么有一些误解文件是(注意,Unix 和 Windows 上的并不完全相同)。顺便说一句,它们对很多人来说都很重要系统调用(列于系统调用(2)),有几个系统调用给出文件描述符从文件路径(另请参见路径分辨率(7))。与其他一些操作系统相比,文件(在 Linux 或 Unix 或 POSIX 系统上)不仅具有一姓名(或小路):有些文件没有名称,有些文件有多个名称;事实上,大多数文件都有一个名称。
请记住,文件是一个抽象为...提供用户空间(和应用-包括公用事业程序-运行于流程)由操作系统内核。系统调用是程序(以及运行它们的进程)与内核交互的唯一方式。
您的磁盘不知道文件(但您的操作系统知道)。磁盘仅包含字节块。您的操作系统将它们理解为文件
文件(在 Unix 和 Linux 上)是一个索引节点。也可以看看索引节点(7)。索引节点包含有关该文件的元数据(您可以使用以下命令进行查询)统计数据(2)等
fstat
...) - 包括类型、创建时间、权限、所有权、大小等 - 并包含(或更常见的是指向)文件数据(字节序列)。
但删除只读目录不会有任何问题。
A目录是一种特殊类型的文件(除了普通文件和目录之外还有其他类型的文件,例如先进先出(7)-s,符号链接(7)-s 等)。它包含一个将字符串映射到 inode 的字典。这种情况的发生方式因每种文件系统类型而异。使用打开目录(3)(以及稍后closedir
)和读取目录(3)阅读它。
....它所在文件夹的权限...
误解。文件夹在 Linux 上不存在(它们是图形用户界面人工制品有时由您显示的桌面环境),您可能正在谈论目录。文件系统包含各种类型的文件(包括目录和符号链接)。
给定的 inode 可以出现在一些目录(你可能会说一个文件可以有一些路径,那么它们都具有相同的“权力”和相似的“角色”)。使用链接(2)系统调用 - 也许通过ln(1)命令 - 用于向文件添加一些附加路径。使用取消链接(2)用于删除文件路径的系统调用。在某些情况下,索引节点可以存在而不出现在任何目录中。一个常见的情况(用于实现临时文件)是当您创建文件时 -eg 使用创造(2)或open
然后unlink
(或删除(3))紧接着该文件(例如在同一进程中,但可能不是)。
当某个 inode 变得无法访问时(因为没有打开的文件描述符,并且在某些目录中不再提及它),内核会删除该 inode(以及与其相关的数据块)。
当您“删除”文件时(例如使用房间(1)实用程序),/bin/rm
程序(以及运行该命令的进程)只是使用unlink
(并且您正在写入包含名称和 inode 之间的某些映射的目录)。如果没有更多“指向”该索引节点,那么它确实会被删除。由于内核正在写入目录,因此它要求您的进程具有写入权限。也可以看看凭证(7)。
需要一个目录目录(2)待制作,并且目录(2)被删除(从其父级):如果您使用取消链接(2)要删除它,将会失败EISDIR
。但目录(2)要求目录为空(因为内核要求文件层次结构是有向无环图, 和循环引用被某种形式禁止引用计数)。mkdir
和系统调用都处理目录的rmdir
魔法 .
和条目。..
但删除只读目录不会有任何问题。为什么这个东西不依赖父目录呢?
一般情况下确实如此(但是粘性位目录上有一些特定的含义)。
关于编辑的问题
在您编辑的问题中,您声称(不正确,或者缺少一些重要细节):
现在考虑这样的情况:我有一个名为
sub
under 的子目录test
。该目录是只读的。当我想删除这个子目录时,它会抛出一个错误,指出无法删除这个目录。
我无法重现您的主张(请提供一些MCVE)。为了便于阅读,我正在考虑目录testdir
而subdir
不是你的名字(但这不会改变任何东西;但是你的名字test
很容易混淆测试(1))
% /bin/mkdir testdir
% /bin/mkdir testdir/subdir
% /bin/ls -la testdir
total 12
drwxr-xr-x 3 basile basile 4096 Apr 24 13:09 .
drwxr-xr-x 6 basile basile 4096 Apr 24 13:08 ..
drwxr-xr-x 2 basile basile 4096 Apr 24 13:09 subdir
% /bin/chmod a-w testdir/subdir
% /bin/ls -la testdir
total 12
drwxr-xr-x 3 basile basile 4096 Apr 24 13:09 .
drwxr-xr-x 6 basile basile 4096 Apr 24 13:08 ..
dr-xr-xr-x 2 basile basile 4096 Apr 24 13:09 subdir
% /bin/rmdir testdir/subdir
% /bin/ls -la testdir
total 8
drwxr-xr-x 2 basile basile 4096 Apr 24 13:14 .
drwxr-xr-x 6 basile basile 4096 Apr 24 13:08 ..
请记住目录(1)(它使用目录(2)系统调用)要求删除的目录为空,并且某些文件(名称以点开头)可能被您的 shell 或ls
.列出已删除目录的所有文件ls -a
你可能会读到操作系统:三个简单的部分
答案2
不可以,如果目录的父目录是只读的,则无法删除该目录。自己尝试一下:
$ cd /tmp
$ mkdir -p /tmp/readonly1/readonly2
$ chmod 555 /tmp/readonly1/readonly2 /tmp/readonly1 # dr-xr-xr-x
$ rmdir /tmp/readonly1/readonly2
rmdir: failed to remove '/tmp/readonly1/readonly2': Permission denied
强行删除也无济于事:
$ rm -rf /tmp/readonly1/readonly2
rm: cannot remove '/tmp/readonly1/readonly2': Permission denied
$ rm -rf /tmp/readonly1
rm: cannot remove '/tmp/readonly1/readonly2': Permission denied
$ chmod 755 /tmp/readonly1/readonly2 # drwxr-xr-x
$ rm -rf /tmp/readonly1
rm: cannot remove '/tmp/readonly1/readonly2': Permission denied
但是一旦你使readonly1
目录可写,你就可以删除它的子目录readonly2
:
$ chmod 555 /tmp/readonly1/readonly2 # dr-xr-xr-x
$ chmod 755 /tmp/readonly1 # drwxr-xr-x
$ rmdir /tmp/readonly1/readonly2
$ rmdir /tmp/readonly1 #... or just rm -rf /tmp/readonly1 all at once
$ ls /tmp/readonly1
ls: cannot access '/tmp/readonly1': No such file or directory