Как приостановить и возобновить процессы, как это делает bash

13

этот вопрос является продолжением: как приостановить и возобновить процессы

Я запустил firefox из сессии bash в gnome-терминал.

Дерево процессов выглядит так:

$ ps -e -o pid,ppid,cmd -H
 1828     1   gnome-terminal
26677  1828     bash
27980 26677       /bin/sh /usr/lib/firefox-3.6.15/firefox
27985 27980         /bin/sh /usr/lib/firefox-3.6.15/run-mozilla.sh /usr/lib/firefox-3.6.15/firefox-bin
27989 27985           /usr/lib/firefox-3.6.15/firefox-bin
28012 27989             /usr/lib/firefox-3.6.15/plugin-container /usr/lib/adobe-flashplugin/libflashplayer.so 27989 plugin true

Когда я нажму CTRL+Zна bash, он остановит Firefox. Когда я введу команду bg(или fg), она возобновит работу firefox. Это как и ожидалось.

Когда я запускаю команду kill -s SIGTSTP 27980в другом терминале, она напечатает строку [1]+ Stopped firefoxв первом терминале (точно так же, как когда я нажимаю CTRL+Z), но не приостанавливает firefox. Я полагаю, что это только приостанавливает сценарий оболочки.

Когда я запускаю команду kill -s SIGTSTP 27989(обратите внимание на PID) в другом терминале, он приостанавливает firefox. Первый терминал не принимает это к сведению.

Как bash приостанавливает все дерево процессов? это просто пересекает дерево и SIGTSTP всех детей?

lesmana
источник
2
См. Также Разница между группой процессов и работой? ,
Жиль "ТАК - перестань быть злым"
Вы должны добавить pgidв свою psкоманду, чтобы увидеть группы процессов, о которых говорит @geekosaur.
ниндзя

Ответы:

17

Рабочие места Shell живут в «технологических группах»; посмотрите на PGRPстолбец в расширенном psвыводе. Они используются как для контроля работы, так и для определения того, кто «владеет» терминалом (реальным или pty).

POSIX (взятый из System V) использует отрицательный идентификатор процесса для обозначения группы процессов, поскольку группа процессов идентифицируется первым процессом в группе («лидер группы процессов»). Таким образом, вы будете использовать psдля определения группы процессов, а затем kill -s TSTP "-$pgrp". (Попробуй ps -u"$USER" -opid,ppid,pgrp,cmd.)

В вашем дереве процессов группа процессов начинается с запускаемого firefoxсценарием bash, поэтому группа процессов будет 27980, а команда будет такой kill -s TSTP -27980.

Естественно, возобновить процесс группы, вопрос kill -s CONT -- -27980.

geekosaur
источник
7
Кстати, bashне делает, SIGTSTPкогда вы печатаете ^Z; Так как firefoxгруппа процессов является текущей группой процессов терминала, драйвер терминала (педантично, дисциплина линии) отправляет SIGTSTPвсе процессы в этой группе процессов. bashпросто waitpid()на нем (и на любой другой работе). Другие терминальные сигналы, такие как ^Cи ^\ работают так же. (meta: SE ненавидит этот ctrl-backslash ..)
geekosaur