为什么 Linux shell 上的高退出代码 (>= 256) 无法按预期工作?

rug*_*ugk 6 shell bash zsh exit exit-status

我发现了一个奇怪的行为(可以在我的系统上使用 zsh 和 bash 重现):

$ # here everything is still normal
$ bash -c 'exit 1';echo $?
1
$ bash -c 'exit 255';echo $?
255
$ zsh -c 'exit 255';echo $?
255
$ # now it get's crazy
$ bash -c 'exit 256';echo $?
0
$ zsh -c 'exit 256';echo $?
0
$ # (leaving away zsh for now, it is always reproducible with both)
$ bash -c 'exit 257';echo $?
1
$ bash -c 'exit 267';echo $?
11
Run Code Online (Sandbox Code Playgroud)

所以256之后又开始从1开始计数。但为什么?

bash 手册页没有表明有最大数量:

   exit [n]
          Cause  the  shell  to exit with a status of n.  If n is omitted,
          the exit status is that of the last command executed.  A trap on
          EXIT is executed before the shell terminates.
Run Code Online (Sandbox Code Playgroud)

这是一种非常令人困惑的行为。如果程序依赖于此,可能会导致大问题。

那么为什么会发生这种情况呢?为什么没有记录下来?

x64、Fedora 26

PSk*_*cik 6

退出系统函数手册中有记载:

status 的值可以是 0、EXIT_SUCCESS、EXIT_FAILURE、[CX] [Option Start] 或任何其他值,但只有最低有效的 8 位(即 status & 0377)可供等待的父进程使用。[选项结束]

Linux 似乎非常严格地遵守该标准,并且只允许最后 8 位通过。