C library functions -sigsuspend()

C Standard Library - <signal.h>

sigsuspendThe function is a function in the C standard library, used to temporarily replace the current signal mask and suspend the process until a signal is caught. It is often used to implement atomic signal waiting, that is, no signals are lost while waiting for a signal.

Syntax

int sigsuspend(const sigset_t *mask);

Parameter

  • const sigset_t *mask: Pointer to the new signal mask.sigsuspendUse this signal mask to replace the current signal mask, and restore the original signal mask after catching a signal.

Return Value

  • sigsuspendThe function always returns -1, and willerrnoSet toEINTR, indicating that the function was interrupted by a signal.

Example

The following is a use ofsigsuspendExample program for a function waiting for a specific signal. The program sets up a signal handler, then usessigsuspendSuspends the process until a signal is caught.

Example

#include <stdio.h>
#include <signal.h>
#include <unistd.h>

volatile sig_atomic_t flag = 0;

// Custom signal handling function
void handle_sigint(int sig) {
    printf("Caught signal %d\n", sig);
    flag = 1;
}

int main() {
    struct sigaction sa;
    sigset_t new_mask, old_mask, wait_mask;

    // Set the handler for SIGINT to handle_sigint
    sa.sa_handler = handle_sigint;
    sigemptyset(&sa.sa_mask);
    sa.sa_flags = 0;
    if (sigaction(SIGINT, &sa, NULL) == -1) {
        perror("sigaction");
        return 1;
    }

    // Initialize signal set
    sigemptyset(&new_mask);
    sigaddset(&new_mask, SIGINT);

    // Block SIGINT signal
    if (sigprocmask(SIG_BLOCK, &new_mask, &old_mask) == -1) {
        perror("sigprocmask");
        return 1;
    }

    // Initialize wait signal set
    sigemptyset(&wait_mask);

    printf("Waiting for SIGINT...\n");

    // Use sigsuspend to suspend the process and wait for a signal
    while (!flag) {
        if (sigsuspend(&wait_mask) != -1) {
            perror("sigsuspend");
            return 1;
        }
    }

    // Restore the original signal mask
    if (sigprocmask(SIG_SETMASK, &old_mask, NULL) == -1) {
        perror("sigprocmask");
        return 1;
    }

    printf("Exiting...\n");

    return 0;
}

Assuming the program is compiled and run, the output will be:

Waiting for SIGINT...

When Ctrl+C is pressed (sendingSIGINTsignal), the output will be:

Caught signal 2
Exiting...

The program caughtSIGINTsignal, and the signal handler was executedhandle_sigint, setflagto 1, causing the main loop to terminate and exit the program.

Explanation

  • sigset_t new_mask, old_mask, wait_mask;: defines three signal sets, used to control the signal mask.
  • UsagesigprocmaskFunction blockingSIGINTsignal, and saves the original signal mask.
  • UsagesigsuspendThe function suspends the process and waits for a signal.sigsuspendTemporarily replaces the current signal mask withwait_mask, and restore the original signal mask after catching the signal.
  • After catching the signal, restore the original signal mask and continue program execution.

Notes

  • sigsuspendOften used to implement a reliable signal waiting mechanism, avoiding signal loss during the masking period.
  • Signal handler functions should be as short as possible, because other signals are blocked while a signal is being handled. A long-running signal handler may affect the real-time performance of the program.

C Standard Library - <signal.h>

other extensions