Вопрос

У меня есть несколько вопросов о процессах-зомби

  • Каковы преимущества концепции зомби-процесса?
  • знать, что ядро ​​сохраняет (PID, статус завершения, информацию об использовании ресурсов) для процесса-зомби
    что означает «информация об использовании ресурсов»
  • как у зомби PPID() = 1, и он все еще зомби (init пожинает зомби, потому что по умолчанию он ждет())
    может кто-нибудь написать некоторый код C сделать зомби его родителем - Init?
  • могут ли зомби отказываться снять блокировку памяти??

заранее спасибо

Это было полезно?

Решение

-- Каковы преимущества концепции зомби-процесса?

Процесс-зомби — это просто pid, статус завершения и некоторая учетная информация, которая сохраняется до тех пор, пока родитель не воспользуется одним из процессов. wait семейство системных вызовов, чтобы получить его окончательный статус.Пока родитель не позвонит wait идентификатор дочернего процесса должен оставаться помеченным как используемый, чтобы его нельзя было назначить другому процессу.Если бы другому процессу был назначен переработанный pid, было бы трудно отличить его от предыдущих процессов, которые имели тот же самый pid.Один раз wait вызывается родителем и возвращает окончательный статус выхода. Можно предположить, что никто больше не будет искать дочерний элемент по этому идентификатору, поэтому теперь этот идентификатор можно использовать повторно.(Я думаю, что в Linux, если родитель оставляет SIGCHLD как SIG_IGN, ядро ​​не будет удерживать зомби, но перерегистрация расположения SIGCHLD как SIG_IGN не будет иметь такого же эффекта)

- знайте, что ядро ​​сохраняет (PID, статус завершения, информацию об использовании ресурсов) для процесса-зомби, что означает «информация об использовании ресурсов»

Часть этой информации представляет собой запуск программы:

time my_program

сообщу.Эти значения обычно передаются в структуре siginfo для SIGCHLD (это не совсем вызов wait), но также доступен при звонке на waitid форма системного вызова (в некоторых системах).Посмотри на man sigaction для получения информации об этой структуре.

-- как у зомби PPID() = 1, и он все еще зомби (init пожинает зомби, потому что по умолчанию он wait())

Зомби, чей ppid = 1, не должен оставаться зомби очень долго, потому что в этом должен пожинать плоды довольно быстро.Процесс останется зомби вскоре после своей смерти (либо через exit или необработанным сигналом, который убивает его) до тех пор, пока его родитель не вызовет wait и получает окончательный статус.Это означает, что даже если init ничего не делает, а вызывает init снова и снова, может пройти небольшой промежуток времени, когда процесс может проявиться как зомби.Если процессы отображаются как дочерние элементы в этом (0=ppid) в течение длительного времени (секунд), возможно, что-то не так.

-- может ли кто-нибудь написать код на C, чтобы сделать зомби, его родителем является Init?

Это неясно, но я думаю, вы хотите:

pid_t f = fork();
if (f > 0) {
    exit(0); // this is the parent dying, so the child will be an orphan
             // and get adopted by init
} else if (f == 0) {
    sleep(100); // This is the child doing something that takes enough time for
                // its parent to commit suicide (exit(0)) and then for you to
                // observe that it has now been adopted by init
    exit(0);    // And now it dyes as well, so init should reap its status, but
                // it may be a zombie for a short amount of time first.
} else /* error condition would be handled here */

-- могут ли зомби отказываться снять блокировку памяти??

Зомби ничего не могут удержать.Они теряют все свои страницы памяти, дескрипторы открытых файлов и т. д.Практически все, что операционная система может придумать, как освободить, должно быть освобождено.Было бы ошибкой не сделать этого, но помните, что ОС должна знать, что это что-то, что должно быть освобождено.Очень легко создать ресурсы в пользовательском пространстве, которые должны быть освобождены при выходе из строя программы, о которых ОС не знает, что они должны быть освобождены.

Другие советы

Процесс-зомби — это просто значение pid и статуса выхода.Pid не может быть освобожден, поскольку ресурс (pid) «принадлежит» родительскому элементу.Если бы он был выпущен, другому процессу мог бы быть назначен тот же pid, и тогда родительский процесс мог бы в конечном итоге отправлять сигналы несвязанному процессу;даже если родитель сначала подождал, чтобы определить, завершился ли дочерний процесс, избежать состояния гонки не было бы возможности.

Если вы хотите увидеть процесс-зомби в списке запущенных процессов, используйте это:

#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>

int main(void)
{
    pid_t p = fork();   // creates child process and stores the returned PID

    if (p != 0)         // executed by parent process
    {   sleep(1);       /* the child process terminates while the parent process sleeps,
                           the child then becomes a zombie process because the returned status
                           of the terminated child process isn't checked via a wait() */

        system("ps -eo pid,ppid,stat,cmd");  // prints a list of processes in your terminal

    }
    else        // executed by child process
    {
        exit(0);        // the child process terminates immediately
    }

    return 0;
}

Вы можете определить зомби-процесс по Z+ в списке:

screenshot of the zombie process

ПРИМЕЧАНИЕ:вам придется изменить код, если вы используете Windows.

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

Более долгоживущие процессы-зомби возникают, когда родительские процессы не вызывают системный вызов ожидания после завершения дочернего процесса.Одна из ситуаций, когда это происходит, — это когда родительский процесс плохо написан и просто пропускает вызов ожидания, или когда родительский процесс завершается раньше дочернего процесса, а новый родительский процесс не вызывает ожидание для него.Когда родительский процесс умирает раньше дочернего, ОС назначает дочернему процессу процесс «init» или PID 1.то естьПроцесс init «принимает» дочерний процесс и становится его родительским.Это означает, что теперь, когда дочерний процесс завершает работу, новый родительский процесс (init) должен вызвать wait, чтобы получить код выхода, иначе запись в таблице процессов останется навсегда, и он станет зомби.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top