在zsh与bash中的`bg`命令之前略有不同

时间:2012-03-30 19:44:34

标签: bash shell zsh

今天我发现了一个奇怪的行为,我希望我可以得到一些指示。

这就是我正在做的......

如果至少有一个进程已在后台运行,我会中断( Ctrl + Z )前台进程,然后将其放在后台bg

以下是zsh中的结果:

$ some-long-running-command
^Z
zsh: suspended  some-long-running-command
$ bg
[2]  - continued  some-long-running-command
$ jobs
[1]  + running    other-command-previously-run
[2]  - running    some-long-running-command
$

以下是bash中的内容:

$ other-command-previously-run &
[1] 12345
$ some-long-running-command
^Z
[2]+  Stopped                 some-long-running-command
$ bg
[2]+ some-long-running-command &
$ jobs
[1]-  Running                 other-command-previously-run &
[2]+  Running                 some-long-running-command &
$ 

那么bash为什么bg将进程放在后台,fg作为“当前”进程(由“+”表示,如果zsh运行则会恢复),而fg将“其他”流程设置为当前流程?我找不到任何文件表明行为会有所不同......有趣的是,如果你在^Z中执行了多个bg + zsh + {{1}},那么“当前”流程选择将“翻转”。

有没有人见过这个?

1 个答案:

答案 0 :(得分:3)

我可以在bashzsh中重现此行为。

我的TL; DR回答:您在bash中看到的行为已被记录。你在zsh中看到的行为不是(我发现的),而且我有一个理论,这可能是错误的。


<强>击

Bash Manual,第7节“作业控制基础知识”描述了内置bg的行为:

  

符号'%%'和'%+'是指当前作业的shell概念,它是在前台或在后台启动时停止的最后一个作业。

因此,从bash的角度来看,当前作业最后一个作业要么停在前台,要么在后台启动。这解释了问题中注意到的行为:

  

那么为什么bash会将进程置于背景中,并将bg作为“当前”进程


<强> ZSH : 我无法为zsh解释这一点。 JOBS部分zsh下的+解释了-jobs bg的含义:

  

%%当前工作。
  %+相当于'%%'   % - 以前的工作。

,但是,解释fg^Zprevious对于将其降级为{{1} }或current

我的理论,我还要通过纠缠irc.freenode.net#zsh中的好人来验证,zsh使用“当前进程堆栈”; bgcurrent进程推送到队列末尾。这样可以在玩三个过程时看到:


simont@charmander ~/repositories/SOTesting/bg
  $ one.sh&                                                                                 [1:52:41]
[1] 98369

simont@charmander ~/repositories/SOTesting/bg
  $ two.sh&                                                                                 [1:52:49]
[2] 99293

simont@charmander ~/repositories/SOTesting/bg
  $ three.sh                                                                                [1:52:51]
^Z
[3]  + 973 suspended  three.sh

simont@charmander ~/repositories/SOTesting/bg
  $ jobs                                                                                    [1:52:55]
[1]    running    one.sh
[2]  - running    two.sh
[3]  + suspended  three.sh

simont@charmander ~/repositories/SOTesting/bg
  $ bg                                                                                      [1:52:57]
[3]  - 973 continued  three.sh

simont@charmander ~/repositories/SOTesting/bg
  $ jobs                                                                                    [1:52:59]
[1]    running    one.sh
[2]  + running    two.sh
[3]  - running    three.sh

正如我们在这里看到的那样,onetwo被推倒在理论堆栈上。最后执行的three(?)是current process,由+输出中的jobs表示。
暂停three后,它仍然是当前流程,但在bg之后,它会被推送到previous流程和two,成为流程中的“顶级”流程“stack”成为新的current进程。

然而,这是猜想;就像我说的那样,我没有证据证明这一点,老实说,man zsh*页面有点复杂;我可能错过了一些东西。