Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Учеб.пос.СП.doc
Скачиваний:
28
Добавлен:
31.03.2015
Размер:
1.33 Mб
Скачать
    1. Завершение процесса и системные вызовы exit

Процесс заканчивает работу в четырех случаях:

  • при обращении к системному вызову exit. Возврат значения из функции main эквивалентен вызову exit с тем же самым значением. Выход из функции main без возвращаемого значения равносилен возврату значения 0;

  • при обращении к _exit или _Exit - двум разновидностям системного вызова exit;

  • при получении сигнала на завершение;

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

Между тремя разновидностями системного вызова exit существуют следующие различия:

  • _exit и _Exit ведут себя совершенно идентично, хотя _exit относится к Unix, а _Exit - к стандарту языка С;

  • exit - также определен стандартами языка С. Он делает то же самое, что и _exit, но кроме этого выполняет дополнительные операции по завершению процесса - вызывает функции, зарегистрированные обращением к atexit и выталкивает стандартные буферы ввода-вывода, как если бы были вызваны fflush или fclose.

Приведем краткое описание семейства функций exit:

_exit - завершает процесс без обращения к коду сборки мусора

#include <unistd.h>

void _exit(

int status /* код завершения */

);

/* В программу управления уже не возвращается */

_Exit - завершает процесс без обращения к коду сборки мусора

#include <stdlib.h>

void _Exit(

int status /* код завершения */

);

/* В программу управления уже не возвращается */

exit - завершает процесс с обращением к коду сборки мусора

#include < stdlib.h>

void exit(

int status /* код завершения */

);

/* В программу управления уже не возвращается */

Данные системные вызовы завершают работу процесса, обратившегося к нему, с кодом завершения, равным младшему байту аргумента status. Следующие побочные эффекты имеют место при любом варианте завершения процесса:

  • все открытые дескрипторы закрываются;

  • если процесс был управляющим процессом, то сеанс теряет свой управляющий терминал. Каждому процессу в сеансе передается сигнал SIGHUP, который приводит к завершению процессов;

  • родительский процесс извещается о завершении процесса-потомка через один из системных вызовов семейства wait;

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

Родительский процесс получает код завершения дочернего процесса через один из системных вызовов wait. Код завершения – это число в диапазоне от 0 до 255. Значение 0 соответствует коду успешного завершения, а ненулевое значение – какой-либо ошибке, код которой определяется самим завершившим работу приложением.

После того как процесс завершится, он прекращает свое исполнение, но остается в системе до тех пор, пока код завершения не будет передан процессу-предку. Если потомок не смог сообщить предку о своем завершении, он переходит в состояние зомби.