如果启动后台进程然后注销,它将继续运行吗?


29

在与同事长时间讨论之后问这个问题,我真的很想在此澄清一下。

我启动了后台进程,方法是将“ &” 添加到命令行,或者通过将其停止CTRL-Z并以“ bg” 在后台恢复。然后我注销。

怎么了?

我们非常确定它应该被SIGHUP杀死,但这没有发生。再次登录后,该进程愉快地运行,并pstree显示出该进程已被采纳init

这是预期的行为吗?

但是,如果是的话,该nohup命令的目的是什么?看起来无论有没有这个过程,进程都不会被杀死……


编辑1

一些更多的细节:

  • 该命令是从SSH会话而不是从物理控制台启动的。
  • 该命令在没有 nohup和/或&;的情况下启动。然后将其CTRL-Z与暂停,并在与一起恢复后台bg
  • ssh会话没有删除。实际注销(“ exit”命令)。
  • 该过程是scp文件复制操作。
  • 再次登录后,pstree显示进程正在运行并且是的子进程init

编辑2

为了更清楚地说明问题:将进程置于后台(使用&bg)使其SIGHUPnohup命令一样被忽略吗?


编辑3

我尝试手动发送一个SIGHUPto scp:它退出了,所以它绝对不会忽略该信号。

然后,我再次尝试启动它,将其置于后台并注销:它被“采纳” init并保持运行,并且重新登录后在此找到了它。

我现在很困惑。好像没有SIGHUP发出任何注销消息。


我在那里没有看到任何有关控制台I / O的信息,这也会使事情恶化。您是否把事情转移1>/dev/null 2>&1了,例如重击等等?
艾利·佩恩

不,我没有。SCP当然不需要标准输入...而且标准输出似乎也不是问题。
Massimo 2010年

是否将您的外壳程序作为登录外壳程序执行会改变性能,在这里可能就是这种情况。
华纳

做过其他测试;我在这里总结:serverfault.com/questions/117152
Massimo 2010年

Answers:


20

找到答案。

对于BASH,这取决于huponexitshell选项,可以使用内置shopt命令查看和/或设置该选项。

看起来该选项默认情况下是关闭的,至少在基于RedHat的系统上是这样。

BASH手册页上的更多信息:

默认情况下,在收到SIGHUP时,shell退出。退出之前,交互式外壳程序会将SIGHUP重新发送给所有正在运行或已停止的作业。已停止的作业将发送给SIGCONT,以确保它们收到了SIGHUP。为了防止外壳将信号发送到特定作业,应使用内置的disown将其从作业表中删除(请参阅下面的SHELL BUILTIN COMMANDS),或使用disown -h标记为不接收SIGHUP。

如果已经用shopt设置了huponexit shell选项,则在退出交互式登录shell时,bash会向所有作业发送SIGHUP。


2
这是一个愚蠢的默认值,但是我的胆量告诉我这是一个RH错误而不是bash。顺便说一句,使用zsh可以使用&!作为放弃的捷径,与&分叉的过程确实令人叹为观止。
尔根·斯特罗贝尔

7

我同意Warner的观点,只是想补充一点,您可以使用内置的“ disown”命令阻止Shell发送SIGHUP。bash手册页包含了很好的描述。


4

您可以使用命令nohup启动命令并将输出重定向到nohup输出文件。从nohup手册页:

nohup - run a command immune to hangups, with output to a non-tty

另一个选项是使用screen命令。使用屏幕的好处是您可以稍后重新连接到该过程。


为什么要下票?使用nohup和screen是避免在注销时终止进程的完全可接受的方法。还有其他的,但是这两种工作。这是怎么回事?
Jim

2
我认为这是一个很好的观点,但问题是关于为什么他的程序没有被杀死,不是“如何防止它们被杀死”。
CarpeNoctem'2

2

当您将一个进程派生到后台时,它仍然是执行它的外壳程序的子进程。

在外壳下运行的所有子进程在退出时都会发送SIGHUP。性能会因实际情况而略有不同,具体情况请参见bash的联机帮助页。其他外壳可能具有类似的描述。

Apache和其他守护程序通常会在SIGHUP上重新加载配置。用户空间实用程序通常会消失。链接到信号的应用程序性能可能对应用程序是唯一的。


因此,在这种情况下,该过程应该刚刚收到了SIGHUP,对吗?也许它只是忽略了它,我会检查。
Massimo 2010年

对,就是这样。我相信情况就是如此。如果您真的怀疑所记录的性能,可以破解一些脚本来捕获信号并记录下来。
华纳2010年

0

程序是什么?早期发布1中描述的性能是准确的。

某些脚本功能和过程可能会捕获信号。而循环可能像疯了似的逃跑。

看到:

SSH会话中断-命令是否继续执行?

在下午4:22编辑1

从bash手册页:

The shell exits by default upon receipt of a SIGHUP.   Before  exiting,
an  interactive  shell  resends  the  SIGHUP  to  all  jobs, running or
topped.

初步研究1显示,OpenSSH可能会忽略SIGHUP,甚至可能会忽略其他信号。


那个帖子实际上让我发问。有关详细信息,请参见上面的编辑。
Massimo 2010年

2
另一个线程中的答案听起来像是您需要阅读所使用的SCP命令并查看其对SIGHUP的响应
mfinni 2010年

而且,“ nohup”适用于您知道会因SIGHUP而死的命令,并且您不希望它们死掉。
mfinni

手册页只是没有说明。我会尝试杀死它
Massimo 2010年

-1

如果您没有通过诸如之类的工具启动该命令screen,那么在会话结束时,与该会话相关的所有作业/任务也会执行。


那正是我在想的,除了...他们只是没有。
Massimo 2010年

他们每次执行完您所描述的内容后...也许取决于您使用的外壳?
沃伦

-1他们不这样做;答案不是那么简单。我只是测试了一个在后台启动的简单shell脚本;它循环并发送输出到临时文件。我退出终端后,它继续运行(如tail -f临时文件所示。在使用bash的CentOS 7.1机器上。)
Mike S

@MikeS-请示范。我从未见过您描述的行为
沃伦(Warren)2015年

@warren-请参阅我对serverfault.com/questions/117152/…的回答。请注意,许多人声称行为与您所描述的不同。确实,Massimo发布正是因为他的过程继续。
Mike S
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.