删除“。” 站在上面的时候

ano*_*nol 5 bash

在玩弄文件系统时,我尝试了以下操作:

mkdir a
cd a
rmdir .
Run Code Online (Sandbox Code Playgroud)

结果是:

rmdir: failed to remove ‘.’: Invalid argument
Run Code Online (Sandbox Code Playgroud)

好的,先生rmdir,让我智胜你:

rmdir ../a
Run Code Online (Sandbox Code Playgroud)

...好的。

什么?这次没有报错?

我还是终端说我在目录中a,但ls -a名单没有(没有.,也没有..),但ls ..pwd预期仍然工作。

我是不是像那些砍了自己的树枝还没有倒下的卡通人物之一?

如果我尝试

mkdir ../a
Run Code Online (Sandbox Code Playgroud)

它创建了一个目录a,但这仍然不是我所在的目录(ls -a .ls -a ../a显示不同的结果)。

如果我尝试用touch b它创建一个文件,它会回复:

touch: cannot touch ‘b’: No such file or directory
Run Code Online (Sandbox Code Playgroud)

但是touch .有效。

最后,一旦我离开我的目录,它就会消失,我无法返回。

编辑:有人可以解释一下这里发生了什么吗?这种情况有名字吗?这是文件系统和 Bash 之间的问题,还是 Bash 中的某些特殊硬编码行为?

Jde*_*eBP 9

这与 bash 无关。

这是几十年前的标准 Unix 行为。这是内核的标准行为,与 shell 无关。

要记住的重要一点是文件和目录不必有名称。只要文件或目录(a) 具有非零链接计数,(b) 被打开的文件描述符引用,或(c) 是进程的工作目录,它就会一直存在。(还有一些其他条件可以防止文件或目录消失,但它们与您在此处的问题无关。)

对于文件,您应该习惯于创建一个未命名的临时文件的想法,当最后一个打开的文件描述符关闭时,它会自动清除,方法是打开一个文件然后取消链接,使其链接计数降为零. (这掩盖了许多与此问题无关的安全相关细节。)

您还应该习惯这样的想法,即您可以取消链接某个进程具有打开文件描述符的文件,创建一个同名的新文件,它们将是两个不同的文件

您只是对目录做了同样的事情。您清空了目录并取消了它的链接,但它继续存在,直到它不再被打开的文件描述符引用并且不再是任何进程的工作目录。当您使用取消链接的相同名称创建新目录时,您有两个不同的目录

请注意,rmdir ../a如果指定的目录是任何进程的当前目录,则 SUS 允许失败。(这并不是为了给分层在 Windows NT 之上的 POSIX API 一个漏洞,正如一些人可能认为的那样。例如,在这种情况下,QNX 也无法调用。)您显然正在运行一个操作系统(在不存在的情况下)考虑根目录和挂载点(您的问题不涉及)选择其他允许的替代方案,即取消链接目录,删除...条目,并禁止创建新条目。

进一步阅读

  • “rmdir”开放组基本规范。IEEE 标准 1003.1。2013 年第 7 期。
  • “rmdir”QNX Neutrino 实时操作系统库参考。QNX 开发人员支持。