Чтение онлайн

ЖАНРЫ

Linux программирование в примерах

Роббинс Арнольд

Шрифт:

int sigfillset(sigset_t *set)

Полностью заполняет набор сигналов. По возвращении

*set
содержит все сигналы, определенные системой. Возвращает 0 в случае успеха и -1 при ошибке.

int sigaddset(sigset_t *set, int signum)

Добавляет

signum
к маске сигналов процесса в
*set
. Возвращает 0 в случае успеха и -1 при ошибке.

int sigdelset(sigset_t *set, int signum)

Удаляет

signum
из маски сигналов процесса в
*set
. Возвращает 0 в случае успеха и -1 при ошибке.

int sigismember(const sigset_t *set, int signum)

Возвращает true/false,

если
signum
присутствует или не присутствует в
*set
.

Перед выполнением с переменной

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

10.6.3. Управление маской сигналов:

sigprocmask
и др.

Маска сигналов процесса вначале пуста - заблокированных сигналов нет. (Это упрощение; см. раздел 10.9 «Сигналы, передающиеся через

fork
и
exec
.) Три функции позволяют работать непосредственно с маской сигналов процесса:

#include <signal.h> /* POSIX */

int sigprocmask(int how, const sigset_t *set, sigset_t *oldset);

int sigpending(sigset_t *set);

int sigsuspend(const sigset_t *set);

Функции следующие:

int sigprocmask(int how, const sigset_t *set, sigset_t *oldset)

Если

oldset
не равен
NULL
, получается маска сигналов текущего процесса и помещается в
*oldset
. Затем маска сигналов процесса обновляется в соответствии с содержимым
set
и значением
how
, который должен иметь одно из следующих значений:

SIG_BLOCK
Объединить сигналы в
*set
с маской сигналов текущего процесса. Новая маска является объединением текущей маски и
*set
.

SIG_UNBLOCK
Удалить сигналы в
*set
из маски сигналов процесса. Это не представляет проблемы, если
*set
содержит сигнал, который не содержится в текущей маске сигналов процесса.

SIG_SETMASK
Заменить маску сигналов процесса содержимым
*set
.

Если

set
равен
NULL
, a
oldset
— нет, значение
how
неважно. Эта комбинация получает маску сигналов текущего процесса, не меняя ее. (Это явно выражено в стандарте POSIX, но не ясно из справочной страницы GNU/Linux.)

int sigpending(sigset_t *set)

Эта функция позволяет увидеть, какие сигналы ожидают решения; т.е.

*set
заполнен этими сигналами, которые были посланы, но они еще не доставлены, поскольку заблокированы.

int sigsuspend(const sigset_t *set)

Эта функция временно заменяет маску сигналов процесса содержимым

*set
, а затем приостанавливает
процесс, пока сигнал не будет получен. По определению, заставить функцию вернуться может только сигнал, не находящийся в
*set
(см. раздел 10.7 «Сигналы для межпроцессного взаимодействия).

10.6.4. Перехват сигналов:

sigaction

Наконец мы готовы взглянуть на функцию

sigaction
. Эта функция сложна, и мы намеренно опускаем множество деталей, которые предназначены для специального использования. Стандарт POSIX и справочная страница sigaction(2) предоставляют все подробности, хотя вы должны тщательно прочесть и то, и другое, чтобы полностью все усвоить.

#include <signal.h> /* POSIX */

int sigaction(int signum, const struct sigaction *act, struct sigaction *oldact);

Аргументы следующие:

int signum

Интересующий сигнал, как в случае с другими функциями обработки сигналов.

const struct sigaction *act

Определение нового обработчика для сигнала

signum
.

struct sigaction *oldact

Определение текущего обработчика. Если не

NULL
, система до установки
*act
заполняет
*oldact
.
*act
может быть
NULL
, в этом случае
*oldact
заполняется, но больше ничего не меняется.

Таким образом,

sigaction
и устанавливает новый обработчик, и получает старый за одно действие.
struct sigaction
выглядит следующим образом.

/* ПРИМЕЧАНИЕ: Порядок в структуре может варьировать. Могут быть

также и другие поля! */

struct sigaction {

 sigset_t sa_mask; /* Дополнительные сигналы для блокирования */

 int sa_flags; /* Контролирует поведение */

 void (*sa_handler)(int);

/* Может образовать объединение с sa_sigaction */

 void (*sa_sigaction)(int, siginfo_t*, void*);

/* Может образовать объединение с sa_handler */

}

Поля следующие:

sigset_t sa_mask

Набор дополнительных сигналов для блокирования при запуске функции обработчика. Таким образом, когда вызывается обработчик, общий набор заблокированных сигналов является объединением сигналов в маске процесса, сигналов в

act->mask
и, если
SA_NODEFER
сброшен,
signum
.

int sa_flags

Флаги, контролирующие обработку сигнала ядром. См. обсуждение далее.

void (*sa_handler)(int)

Указатель на «традиционную» функцию обработчика. У нее такой же прототип (возвращаемый тип и список параметров), как у функции обработчика для

signal
,
bsd_signal
и
sigset
.

void (*sa_sigaction)(int, siginfo_t*, void*)

Указатель на функцию обработчика «нового стиля». Функция принимает три аргумента, которые вскоре будут описаны.

Поделиться с друзьями: