Как фоновый процесс может знать свой собственный PID?

Это может быть хитро, потому что у Вас могут быть отдельные экземпляры того же процесса, это живет независимо. Например, серверы, слушающие на различных портах или сервисах, работающих как различные пользователи. Для различения эти экземпляры необходимо присвоить каждому из них уникальный тег. Тег часто является файлом, но это может быть локальный сокет в абстрактном пространстве имен, порте TCP, и т.д. — любой уникальный идентификатор сделает. Когда тег является файлом, это может быть регулярный файл, содержащий идентификатор процесса (pidfile), или именованный канал или сокет, что файл слушает на и т.д. Идеально, тег является коммуникационной конечной точкой, которая позволяет клиентам соединяться с тем процессом.

Каждые из этих различных видов результатов тегов по-другому проверки, ищете ли экземпляр Вы, в порядке. Например, с локальным сокетом файла, попытайтесь соединиться с ним и запустить процесс, если нет никакого процесса, слушающего на том сокете. Если тег является pidfile, проверьте, существует ли процесс с тем идентификатором процесса, но остерегайтесь этого, это хрупко, с тех пор, если процесс умер, может быть несвязанный процесс, который снова использовал его идентификатор. Остерегайтесь этого, если два клиента пытаются достигнуть, процесс в скором времени структурируют, они могли бы и найти, что процесс не существует и обе попытки запустить его; правильно защита от этого состояния состязания может быть хитрой.

Легче управлять экземплярами, когда они все запускаются тем же процессом супервизора, и тот процесс супервизора обнаруживает, когда экземпляры умирают, и реагирует соответственно. Много сервисных программ мониторинга, которые могут сделать это.

Если программа не отвечает на известной коммуникационной конечной точке, и ею не управляет программа супервизора, тег бедного человека является pidfile: файл, содержащий идентификатор процесса. При запуске процесса запишите pid в файл с заранее подготовленным именем. При необходимости в процессе для существования, считайте pidfile и посмотрите, существует ли процесс с тем pid. Когда Вы уничтожаете процесс, стираете pidfile. Самая существенная проблема с безнадзорным pidfile состоит в том, что, если процесс умирает, его pid может быть снова использован некоторым несвязанным процессом. Необходимо, по крайней мере, проверить имя процесса или исполняемый файл процесса, чтобы гарантировать, что Вы говорите с правильным процессом. Много вариантов Unix имеют команду pgrep: pgrep SOMENAME перечисляет процессы, имя которых содержит SOMENAME как подстроку, с дополнительными опциями ограничить конкретным пользователем, потребовать точного совпадения, измениться, какое из нескольких возможных понятий “имени процесса” используется, и т.д.

5
03.04.2015, 02:04
2 ответа

С помощью bash:

echo "$BASHPID"

вы получите pid процесса, который оценивает, что команда echo

Заметьте, что (например, после включения -n echo) это не обязательно то же самое, что pid процесса, который является командой , выполняющейся , которая эхо.

bash (или любая оболочка) делает свой собственный суп с процессами. Не всегда полезно пытаться угадать, какой процесс что делает.

$ readlink -f /proc/self "/proc/$BASHPID"
/proc/30868
/proc/30747
$ (readlink -f /proc/self "/proc/$BASHPID")
/proc/30869
/proc/30869

Во втором случае readlink выполняется в том же самом процессе, который интерпретировал командную строку, потому что это последняя команда, выполняемая в этой оболочке (поэтому bash оптимизирует fork()).

Эквивалент zsh находится в модуле zsh/system:

$ zmodload zsh/system
$ echo $$ $sysparams[pid]
5155 5155
$ (echo $$ $sysparams[pid])
5155 30979

(zsh также раскрывает родительский фид подсхемы в $sysparams[ppid]).

Portably, вы можете сделать:

pid=$(sh -c 'echo "$PPID"')

Все оболочки должны работать так, чтобы sh как прямое дочернее звено подоболочки интерпретировало эту командную строку, так что sh $PPID должен быть именно этой подоболочкой.

6
27.01.2020, 20:32

$ BashPid может быть то, что вы ищете.

BashPid

расширяется до идентификатора процесса текущего процесса Bash. Это отличается от $$ при определенных обстоятельствах, таких как подвелые, которые делают не требуется повторно инициализировать Bash.

В отличие от $$

($$) расширяется до идентификатора процесса оболочки. В () подпункте, это Расширяется к идентификатору процесса призывающей оболочки, а не подполей.

http://www.gnu.org/software/bash/manual/bashref.html#bash-variables

9
27.01.2020, 20:32

Теги

Похожие вопросы