Ожидание нескольких процессов, вывод кода выхода, если какой-либо процесс завершается

Ожидание нескольких процессов, вывод кода выхода, если какой-либо процесс завершается

Чего я пытаюсь добиться, так это того, что с помощью скрипта я запускаю 3 разных пользовательских приложения в режиме ожидания одновременно, и если какое-либо приложение завершает работу, выдаю оповещение через уведомление или печатаю код выхода.

Используемая система: Centos 6.8

решение1

Команда waitв bash(4.3 и новее) имеет -nопцию:

Если -nуказана эта опция, функция wait ожидает завершения любого задания и возвращает его статус завершения.

Это означает, что вы можете сделать

command1 &
command2 &
command3 &

wait -n
printf 'One command exited with exit code %d\n' "$?"

решение2

Вы можете использовать , wait -nчтобы дождаться завершения работы дочернего процесса, а затем проверить, выполняется ли все дочерние процессы kill -0, с помощью , чтобы узнать, какой из них только что завершился, например:

for f in 15 10 15; do
    sleep $f &
    PIDS+="$! "
done
wait -n
for f in $PIDS; do
    if ! kill -0 $f 2> /dev/null; then
        echo $f
    fi
done

wait -nвозвращает только статус выхода дочернего процесса, а не то, каким PIDон был.

решение3

Я думал о Bash's wait -n, но он не позволяет узнать, какой дочерний процесс завершился. Как насчет простого скрипта Perl?

#!/usr/bin/perl

use strict;
use warnings;
use POSIX ":sys_wait_h";

sub spawn(@) {
    my $pid = fork();
    die "fork: $!" if not defined $pid;
    if ($pid == 0) {
        exec @_ or die "exec: $!";
    }
    return $pid;
}

# Commands to run
my $p1 = spawn '/bin/bash -c "sleep 6; kill $$"';
my $p2 = spawn '/bin/bash -c "sleep 4; exit 4"';

print "spawned PIDs $p1 and $p2\n";

while ((my $child = waitpid(-1, 0)) > 0) {
    my $code = $? >> 8;
    my $status = $? & 0xff;
    printf "child %d finished with exit code %d (status/sig %d)\n", $child, $code, $status;
}

решение4

В bash 5.1 или более поздней версии вы можете сделать следующее:

while
  wait -np id
  status=$?
  [ -n "$id" ]
do
  echo "process of ID $id exited with status $status"
done
bash-5.2$ помогите подождите
ждать:ждать[-фн] [-p переменная] [идентификатор...]
    Дождитесь завершения задания и возврата статуса выхода.

    Ожидает каждый процесс, идентифицированный идентификатором, который может быть идентификатором процесса или
    Спецификация задания и сообщает о статусе его завершения. Если идентификатор не
    задано, ждет все активные в данный момент дочерние процессы и возвращает
    статус равен нулю. Если ID — спецификация задания, ждет все процессы
    в конвейере этой работы.

    Если указана опция -n, ждет одно задание из списка идентификаторов,
    или, если идентификаторы не указаны, для завершения следующего задания и возврата его
    статус выхода.

    Если указана опция -p, идентификатор процесса или задания
    для которого возвращается статус выхода, присваивается переменной VAR
    названный аргументом option. Переменная будет изначально не установлена, перед
    любое назначение. Это полезно только при указании опции -n.

    Если указана опция -f и включено управление заданиями, ждет
    указанный идентификатор для завершения, вместо того чтобы ждать, пока он изменит свой статус.

    Статус выхода:
    Возвращает статус последнего идентификатора; завершается ошибкой, если идентификатор недействителен или является недействительным
    указана опция или если указана опция -n и оболочка не имеет неожидаемых
    дети.

Связанный контент