signal
Задает обработку сигнала прерывания.
Внимание
Не используйте этот метод для завершения работы приложения Microsoft Store, за исключением сценариев тестирования или отладки. Программные или пользовательские способы закрытия приложения Магазина запрещены в соответствии с политиками Microsoft Store. Дополнительные сведения см. в разделе жизненного цикла приложений UWP.
Синтаксис
void __cdecl *signal(int sig, int (*func)(int, int));
Параметры
sig
Значение сигнала.
func
Второй параметр — это указатель на выполняемую функцию. Первый параметр — это значение сигнала, а второй — подкод, который можно использовать при первом параметре SIGFPE
.
Возвращаемое значение
signal
возвращает предыдущее значение func, связанное с заданным сигналом. Например, если предыдущее значение функции func
было SIG_IGN
, то возвращаемое значение также равно SIG_IGN
. Возвращаемое значение SIG_ERR
отображает ошибку; в этом случае для errno
устанавливается значение EINVAL
.
Дополнительные сведения о кодах возврата см. в разделе errno
, _doserrno
_sys_errlist
и _sys_nerr
.
Замечания
Функция signal
позволяет процессу выбрать один из нескольких способов обработки сигнала прерывания от операционной системы. Аргумент sig
— это прерывание, на которое signal
отвечает; оно должно быть одной из следующих констант манифеста, определенных в SIGNAL.H
.
Значение sig |
Description |
---|---|
SIGABRT |
Аварийное завершение |
SIGFPE |
Ошибка с плавающей запятой |
SIGILL |
Недопустимая инструкция |
SIGINT |
Сигнал CTRL + C |
SIGSEGV |
Недопустимый класс хранения |
SIGTERM |
Запрос на завершение |
Если sig
это не одно из указанных выше значений, вызывается обработчик недопустимых параметров, как определено в проверке параметров. Если выполнение может быть продолжено, эта функция задает для errno
значение EINVAL
и возвращает SIG_ERR
.
По умолчанию signal
завершает вызывающую программу с кодом выхода 3, независимо от значения sig
.
Примечание.
SIGINT
не поддерживается ни одним приложением Win32. Когда происходит прерывание CTRL + C, операционные системы Win32 создают новый поток специально для обработки такого прерывания. Это может привести к тому, что однопоточное приложение, например в UNIX, становится многопоточным и вызывает непредвиденное поведение.
Аргумент func
— это адрес обработчика сигнала, который вы пишете, или к одной из предопределенных констант SIG_DFL
действий сигнала или SIG_IGN
, которые также определены в SIGNAL.H. Если func
это функция, она устанавливается в качестве обработчика сигнала для заданного сигнала. Прототип обработчика сигнала требуется один формальный аргумент sig
типа int
. В случае прерывания операционная система предоставляет фактический аргумент с помощью sig
; аргумент является сигналом, который вызвал прерывание. Поэтому можно использовать шесть констант манифеста (перечисленных в приведенной выше таблице) в обработчике сигнала, чтобы определить, какое прерывание произошло, и предпринять соответствующие действия. Например, можно вызвать функцию signal
дважды, чтобы назначить один и тот же обработчик двум различным сигналам, и затем проверять аргумент sig
в обработчике для выполнения различных действий в зависимости от полученного сигнала.
Если вы тестируете исключения с плавающей запятой (SIGFPE
), func
указывает на функцию, которая принимает необязательный второй аргумент, который является одной из нескольких констант манифеста, определенных в FLOAT.H
форме FPE_xxx
. SIGFPE
При возникновении сигнала можно проверить значение второго аргумента, чтобы определить тип исключения с плавающей запятой, а затем выполнить соответствующее действие. Этот аргумент и его возможные значения являются расширениями Майкрософт.
Для исключений с плавающей запятой значение func
не сбрасывается при получении сигнала. Для восстановления после исключений в операциях с плавающей запятой заключайте такие операции в конструкции try/except. Также можно восстановить с помощью setjmp
longjmp
. В любом случае вызывающий процесс продолжает выполнение, а значение состояния операции с плавающей запятой в процессе остается неопределенным.
Если обработчик сигнала возвращается, вызывающий процесс возобновляет выполнение сразу после точки, в которой он получил сигнал прерывания независимо от типа сигнала или режима работы.
Перед выполнением указанной функцией для func
устанавливается значение SIG_DFL
. Следующий сигнал прерывания обрабатывается так же, как это было описано для SIG_DFL
, если только промежуточный вызов signal
не указывает иное. Эту особенность можно использовать для сброса сигналов в вызванной функции.
Так как подпрограммы обработчика сигналов часто вызываются асинхронно при прерывании, функция обработчика сигналов может контролировать, когда операция во время выполнения неполна и в неизвестном состоянии. В следующем списке указаны ограничения, которые определяют, какие функции могут использоваться в подпрограмме обработчика сигнала.
Не выдавать низкоуровневые подпрограммы ввода-вывода
STDIO.H
(например,printf
илиfread
).Не вызывайте подпрограммы кучи или любую подпрограмму, которая использует подпрограммы кучи (например, ,
malloc
_strdup
или_putenv
). Дополнительные сведения см. в разделеmalloc
.Не используйте какую-либо функцию, которая создает системный вызов (например,
_getcwd
илиtime
).Не используйте
longjmp
, если прерывание не вызвано исключением с плавающей запятой (тsig
. е. ).SIGFPE
В этом случае вначале следует инициализировать пакет операций с плавающей запятой с помощью вызова функции_fpreset
.Не используйте подпрограммы наложения.
Программа должна содержать код с плавающей запятой, если это необходимо для ловушки SIGFPE
исключения с помощью функции. Если у вашей программы нет кода с плавающей запятой и требуется код обработки сигналов во время выполнения, просто объявите изменяющийся двойной и инициализировать его до нуля:
volatile double d = 0.0f;
SIGTERM
Сигналы SIGILL
не создаются в Windows. Они включены для совместимости ANSI. Таким образом, можно задать обработчики сигналов для этих сигналов, используя их, signal
и вы также можете явно создать эти сигналы путем вызова raise
.
Параметры сигнала не сохраняются в разреженных процессах, созданных вызовами _exec
или _spawn
функциями. В новом процессе параметры сигнала сбрасываются в значения по умолчанию.
Требования
Маршрут | Обязательный заголовок |
---|---|
signal |
<signal.h> |
Дополнительные сведения о совместимости см. в разделе Совместимость.
Пример
В следующем примере показано, как использовать функцию signal
для добавления пользовательского поведения в сигнал SIGABRT
. Дополнительные сведения о поведении прерывания см. в статье _set_abort_behavior
.
// crt_signal.c
// compile with: /EHsc /W4
// Use signal to attach a signal handler to the abort routine
#include <stdlib.h>
#include <signal.h>
void SignalHandler(int signal)
{
if (signal == SIGABRT) {
// abort signal handler code
} else {
// ...
}
}
int main()
{
typedef void (*SignalHandlerPointer)(int);
SignalHandlerPointer previousHandler;
previousHandler = signal(SIGABRT, SignalHandler);
abort();
}
Выходные данные зависят от используемой версии среды выполнения, будь то консоль или приложение Windows, а также параметры реестра Windows. Для консольного приложения может быть отправлено следующее сообщение в stderr:
Debug Error!
Program: c:\Projects\crt_signal\Debug\crt_signal.exe
R6010
- abort() has been called
См. также
Управление процессами и средой
abort
_exec
, _wexec
функции
exit
, , _Exit
_exit
_fpreset
_spawn
, _wspawn
функции