Как связать команду оболочки с не дочерним процессом, завершающимся без состояния гонки?

При условии, что вы хотите перевести только A, B, C и G в 1, 2, 3 и 4, и что первый столбец никогда не содержит этих букв, вы можете упростить ответ bgStack15 до:

tr 'ABCG' '1234' < input > output
3
02.06.2017, 22:50
3 ответа

Вероятно, вы не хотите отслеживать процесс только на основе его PID. То есть, вероятно, вы имеете представление о том, что это за процесс. Почему бы вам не следить за содержимым /proc//cmdline и, как только оно перестанет существовать или перестанет соответствовать вашим ожиданиям, вы сможете выполнить свою команду/задание?

1
27.01.2020, 21:13

Предположим, что вы можете остановить процесс (например, с помощью ctrl+z, как вы упомянули), это нечестный метод имитации && prog2 (на самом деле, точнее ; prog2, так как статус выхода не будет проверяться, но его можно добавить).

Найдите PID. Откройте другой терминал и выполните

strace -f -e trace=exit_group -p $PID && prog2

. Затем возобновите процесс.

2
27.01.2020, 21:13

Возможно, специфично для -Linux, другие /procмогут вести себя по-другому, но в Linux вы можете сделать это:

(   # subshell to preserve CWD
    cd /proc/$pid || exit
    [ "$expected_path" = "$(readlink exe)" ] || exit # optional, and can do more checks
    while [ -d. ]; do sleep 1; done
)

Рабочий каталог перестанет быть действительным (, и этот .больше не будет существовать )после завершения процесса. Однако, если новый процесс принимает этот pid, он не снова становится действительным. Если процесс завершается (, а pid остается неиспользованным )до cd, тогда cdзавершается ошибкой, и подоболочка завершает работу. Если pid был повторно -использован до cd, то это будет успешно, но «необязательные» проверки (спасибо LJKims ), надеюсь, поймают его. Итак, пока чеки фиксируют эту очень короткую возможную гонку, условия гонки нет. Для проверки вы можете использовать что-то вроде:

# shell 1
$ sleep 10 &
[1] 26453
$ cd /proc/26453

# shell 2 (must be bash for BASHPID)
for ((i=0; i<200000; ++i)) do ( if [ 26453 -eq $BASHPID ]; then echo "I am have the pid — sleeping 60"; sleep 60; echo "done sleeping"; fi ); done
I have the pid — sleeping 60

# back to shell 1
[ -d. ]; echo $?
1

Таким образом, он по-прежнему замечает, что интересующий его сон вышел, несмотря на новый pid 26453.

3
27.01.2020, 21:13

Теги

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