使用 exec 重定向 stderr

Dar*_*ros 3 linux bash

我正在尝试将所有命令错误输出重定向到这样的文件:

exec 2>errlog.txt
Run Code Online (Sandbox Code Playgroud)

但是执行上面的行给我留下了一个“冻结”的终端——终端根本不响应我的输入。更有趣的是使用重定向标准输出exec效果很好。错误重定向有什么问题?

mos*_*svy 5

exec 2>errlog.txt
Run Code Online (Sandbox Code Playgroud)

如果您正在使用bash(而不是ksh93dash[1]),则不会冻结您的终端。这只会防止 shell 的提示和您输入的字符被回显。

但是您稍后可以从errlog.txt;-) 中检索它们,您可以通过盲目输入pwd<Enter>或轻松检查ls<Enter>:命令将正常工作并显示其输出。此外, ^C 和 ^Z 将按预期工作。

这里有两件事在起作用:

1)bash总是将其提示打印到 stderr,而不是控制终端。

2) bash 用来实现命令行编辑的readline 库将关闭终端上的echo 标志[2],并将用户输入的字符打印到stderr。

如果您使用 bash shell 启动bash --noediting(这将导致它不使用 readline 库),您输入的字符将被 tty 驱动程序回显,并且只有提示将转到重定向的 stderr。

对此的解决方法可能是使用tee和进程替换:

exec 2> >(trap '' INT; tee errlog.txt >/dev/tty)
Run Code Online (Sandbox Code Playgroud)

[1] 请参阅此处以解释为什么如果您这样做某些 shell 会严重失灵,以及为什么在zsh.

[2]参见c_lflag/ECHOtermios(3)手册页和stty echostty(1)用于说明。