zsh:为什么即使我有“stty -tostop”,后台进程也会被挂起?

zsh:为什么即使我有“stty -tostop”,后台进程也会被挂起?

我喜欢我的后台进程自由地写入 tty。stty -tostop已经是我的 zsh 中的默认值(我不知道为什么,也许是因为 OhMyzsh?):

❯ stty -a |rg tostop                                                                                                      
isig icanon iexten echo echoe echok -echonl -noflsh -xcase -tostop -echoprt

但我仍然偶尔会暂停后台进程(这不是一致的行为,我不知道如何重现它):

[1]  + 3479064 suspended (tty output)

答案1

TCSETSW当进程不在终端的前台进程组中时TCSETS ioctl()(例如当使用tcsetattr()libc 函数时)来设置 tty 线路规则设置时(例如当从交互式 shell 在后台调用),无论是否tostop启用(这只影响到终端)。

$ stty echo &
[1] 290008
[1]  + suspended (tty output)  stty echo

有关详细信息,请参阅info libc SIGTTOUGNU 系统:

  • 宏:int SIGTTOU

    这与 类似SIGTTIN,但当后台作业中的进程尝试写入终端时生成或设置其模式。同样,默认操作是停止该进程。 如果设置了输出模式,SIGTTOU则仅在尝试写入终端时生成 TOSTOP

(强调我的)

我相信这不是唯一ioctl()可能导致这种情况的原因。粗略地看了一下Linux内核源代码,貌似TCXONCtcflow())、TCFLSHtcflush())也应该如此。

相关内容