为什么 CDPATH 不能按照手册中的说明工作?

Jde*_*eBP 5 shell bash ksh zsh dash

Bourne Again shell 手册说:cd dir

[…]CDPATH搜索dir 中的每个目录名称。[...] 如果dir以斜杠 ( /)开头,CDPATH则不使用。

Z shell 手册说:cd arg

否则,如果arg以斜杠开头,则尝试更改到arg给出的目录。

如果arg不以斜杠开头,则行为取决于当前目录是否.出现在 shell 参数中包含的目录列表中cdpath。[…] 如果 .出现在cdpath,则cdpath严格按顺序搜索,以便.仅在适当的点进行尝试。

POSIX 普通 shell 手册说CDPATH

PATH那些不以/incd命令开头的目录的工作方式相同。

Debian Almquist shell 手册说cd

如果 [...]CDPATH设置了 shell 变量并且目录名称不以斜杠开头,则将在 中列出的目录中CDPATH搜索指定目录。

'93 Korn shell 手册说:cd arg

如果arg以 a 开头,/则不使用搜索路径。否则,将在路径中的每个目录中搜索arg

MirBSD Korn shell 手册说CDPATH

它的工作方式与PATH那些不以/incd命令开头的目录相同。

除了 '93 Korn shell 的一个例外,这些实际上都不是这样的:

% 导出 CDPATH=/tmp:
% mkdir wibble /tmp/wibble
% ksh93 -c 'cd ./wibble'
/tmp/wibble
% dash -c 'cd ./wibble ; 密码
/home/JdeBP/wibble
% bash -c 'cd ./wibble ; 密码
/home/JdeBP/wibble
% mksh -c 'cd ./wibble ; 密码
/home/JdeBP/wibble
% lksh -c 'cd ./wibble ; 密码
/home/JdeBP/wibble
% 豪华 -c 'cd ./wibble ; 密码
/home/JdeBP/wibble
% zsh -c 'cd ./wibble ; 密码
/home/JdeBP/wibble
% 

/tmp/./wibble存在并且是一个目录,但只有 '93 Korn shell 正在搜索CDPATH并找到它。其余的不是。

为什么不?

Jde*_*eBP 7

因为说明书是错的

'93 Korn shell 也是错误的。

1997 年的单一 Unix 规范说:

如果目录操作数不以斜线(开始/)字符,并且所述第一组成部分不是点或点-点,cd将搜索目录相对于彼此在指定的目录CDPATH的变量,在列出的顺序。

2016 年单一 Unix 规范以不同的、稍微多余的方式说明了同样的问题:

3. 如果目录操作数以 <slash> 字符开头,则设置curpath为操作数并继续执行步骤 7。

4. 如果目录操作数的第一个组成部分是点或点-点,则继续执行步骤 6。

[…]

6. 设置curpath为目录操作数。

没有一个手册提到关于.and的部分..,但这就是除了 '93 Korn shell 之外的每个 shell 实际在做的事情,尽管他们的手册是这样说的:

% 导出 CDPATH=/tmp:
% lksh -c 'cd wibble'
/tmp/wibble
% dash -c 'cd wibble'
/tmp/wibble
% 豪华 -c 'cd wibble'
/tmp/wibble
% bash -c 'cd wibble'
/tmp/wibble
% mksh -c 'cd wibble'
/tmp/wibble
% zsh -c 'cd wibble ; 密码
/tmp/wibble
%