为什么在有 readdir 内核函数的情况下将 readdir 函数添加到 POSIX 库接口?

Why was a readdir function added to POSIX library interface when there is a readdir kernel function?

我惊讶地发现手册页中包含 readdir 的两个相互冲突变体的条目。

在 READDIR(2) 中,它明确声明您不想使用它:

This is not the function you are interested in. Look at readdir(3) for the POSIX conforming C library interface. This page documents the bare kernel system call interface, which is superseded by getdents(2).

我知道当另一个函数出现并更好地完成其工作时,一个函数可能会被弃用,但我不熟悉用户空间函数出现并替换同名内核函数的其他情况。是否有一个已知的原因选择走这条路而不是提出一个新的函数名称(正如手册页提到的 getdents 在取代 readdir 时所做的那样)。

编程界面POSIX稳定。您不会因为想要更有效地实现后端而不必要地替换其中的功能。 Linux 系统调用 readdir 从未实现 readdir 函数 因为它有错误的签名;它是用于实现 readdir 函数的旧的、低效的后端。当更好的后端出现时,它已经过时了。

你完全倒过来了:库函数 readdir(3) 早于 Linux 及其 readdir(2) 系统调用,而不是相反。

以这种方式命名系统调用当然是一个糟糕的决定,它背后可能有一个故事,但它现在几乎无关紧要,因为没有人使用它。

在 Unix 上,目录曾经是以特殊方式格式化的简单文件,读取它们的系统调用接口只是 read(2) [1]。后来的系统引入了像 getdirentries (44BSD) 和 getdents (SVR3) 这样的系统调用,但是他们不愿意也没有能力在一个接口上进行标准化,所以我们仍然停留在高层次上并且被打破了[2] readdir(3) 库函数作为读取目录的唯一标准接口。

[1] 在 BSD 等系统上,您仍然可以 cat 一个目录,至少在使用默认文件系统 (FFS) 时是这样。

[2] 它被破坏是因为它不是信号安全的,并且它 returns NULL 对于错误和 EOF,这意味着它可以安全使用的唯一方法首先将 errno 设置为 0,然后检查其 return 值和 errno。呸