std:: signal
|
헤더 파일에 정의됨
<csignal>
|
||
|
/* signal-handler */
*
signal
(
int
sig,
/* signal-handler */
*
handler
)
;
|
(1) | |
|
extern
"C"
using
/* signal-handler */
=
void
(
int
)
;
|
(2) | ( exposition only* ) |
시그널 sig 의 처리를 변경합니다. handler 에 따라 시그널을 무시하거나, 기본값으로 설정하거나, 사용자 정의 함수로 처리할 수 있습니다.
시그널 핸들러가 함수로 설정되고 시그널이 발생할 때, 시그널 핸들러 시작 전에 std :: signal ( sig, SIG_DFL ) 가 즉시 실행되는지는 구현에 따라 정의됩니다. 또한 구현은 시그널 핸들러가 실행되는 동안 일부 구현 정의된 시그널 집합이 발생하는 것을 방지할 수 있습니다.
일부 시그널에 대해서는 구현체가 프로그램 시작 시 std :: signal ( sig, SIG_IGN ) 를 호출할 수 있습니다. 나머지 시그널에 대해서는 구현체가 반드시 std :: signal ( sig, SIG_DFL ) 를 호출해야 합니다.
(참고: POSIX는 이러한 구현 정의 동작들을 표준화하기 위해
sigaction
을 도입했습니다)
목차 |
매개변수
| sig | - |
시그널 핸들러를 설정할 시그널. 구현에서 정의된 값이거나 다음 값 중 하나일 수 있습니다:
|
||||||
| handler | - |
시그널 핸들러. 다음 중 하나여야 합니다:
|
반환값
성공 시 이전 시그널 핸들러 또는 SIG_ERR 반환 (일부 구현에서는 시그널 핸들러 설정이 비활성화될 수 있음).
시그널 핸들러
사용자 정의 함수가 시그널 핸들러로 설치될 때 다음과 같은 제한 사항이 적용됩니다.
|
시그널 핸들러가 std::abort 나 std::raise 의 결과로 호출되지 않은 경우(비동기 시그널), 다음 중 하나라도 해당되면 동작은 정의되지 않습니다:
|
(C++17 이전) |
|
단순 락프리 원자 연산 은 <atomic> 또는 <stdatomic.h> (C++23부터) 의 함수 f 의 호출로서, 다음 조건을 만족합니다:
어떤 시그널 핸들러가 다음 중 어떤 것을 수행하면 동작은 정의되지 않습니다:
|
(C++17부터) |
사용자 정의 함수가 SIGFPE , SIGILL , SIGSEGV 또는 계산 예외를 지정하는 다른 구현 정의 시그널을 처리하는 동안 반환되면, 동작은 정의되지 않습니다.
시그널 핸들러가 std::abort 또는 std::raise (동기식 시그널)의 결과로 호출된 경우, 시그널 핸들러가 std::raise 를 호출하면 그 동작은 정의되지 않습니다.
|
시그널 핸들러 진입 시, 부동 소수점 환경 의 상태와 모든 객체의 값은 다음을 제외하고는 지정되지 않는다:
시그널 핸들러에서 반환될 때, 시그널 핸들러에 의해 수정된 객체 중 volatile std:: sig_atomic_t 또는 lock-free std::atomic 이 아닌 객체의 값은 불확정적이다. |
(C++14 이전) | ||
|
시그널 핸들러가
std::raise
호출의 결과로 (동기적으로) 실행되는 경우, 핸들러의 실행은
volatile std:: sig_atomic_t 타입의 동일한 객체에 대한 두 접근이 동일한 스레드에서 발생하면, 하나 이상이 시그널 핸들러 내에서 발생하더라도 데이터 경쟁이 발생하지 않는다. 각 시그널 핸들러 호출에 대해, 시그널 핸들러를 호출하는 스레드가 수행한 평가는 A와 B 두 그룹으로 나눌 수 있으며, B의 평가가 A의 평가보다 먼저 발생하지 않으며 , 이러한 volatile std:: sig_atomic_t 객체의 평가는 A의 모든 평가가 시그널 핸들러 실행보다 먼저 발생하고 , 시그널 핸들러 실행이 B의 모든 평가보다 먼저 발생한 것처럼 값을 취한다. |
(C++14부터) |
참고 사항
POSIX는
signal
이 thread-safe해야 하며,
모든 signal handler에서 호출될 수 있는 async-signal-safe 라이브러리 함수 목록을 명시합니다
.
시그널 핸들러는 C 링크age 를 가질 것으로 예상되며, 일반적으로 C와 C++의 공통 부분집합 기능만 사용해야 합니다. 그러나 일반적인 구현에서는 C++ 링크age를 가진 함수가 시그널 핸들러로 사용되는 것을 허용합니다.
예제
#include <csignal> #include <iostream> namespace { volatile std::sig_atomic_t gSignalStatus; } void signal_handler(int signal) { gSignalStatus = signal; } int main() { // 시그널 핸들러 설치 std::signal(SIGINT, signal_handler); std::cout << "SignalValue: " << gSignalStatus << '\n'; std::cout << "Sending signal: " << SIGINT << '\n'; std::raise(SIGINT); std::cout << "SignalValue: " << gSignalStatus << '\n'; }
가능한 출력:
SignalValue: 0 Sending signal: 2 SignalValue: 2
참조문헌
- C++23 표준 (ISO/IEC 14882:2024):
-
- 17.13.5 시그널 핸들러 [support.signal]
- C++20 표준(ISO/IEC 14882:2020):
-
- 17.13.5 시그널 핸들러 [support.signal]
- C++17 표준(ISO/IEC 14882:2017):
-
- 21.10.4 시그널 핸들러 [support.signal]
결함 보고서
다음의 동작 변경 결함 보고서들은 이전에 발표된 C++ 표준에 소급 적용되었습니다.
| DR | 적용 대상 | 게시된 동작 | 올바른 동작 |
|---|---|---|---|
| LWG 3756 | C++17 | std::atomic_flag 가 시그널 안전(signal-safe)한지 여부가 불명확했음 | 시그널 안전함 |
참고 항목
|
특정 시그널에 대한 시그널 핸들러를 실행함
(함수) |
|
|
(C++11)
|
동일 스레드에서 실행되는 스레드와 시그널 핸들러 간의 펜스
(함수) |
|
C 문서
for
signal
|
|