开发者

How to send a signal to a process in C?

开发者 https://www.devze.com 2023-04-11 20:40 出处:网络
I need to send a signal to a process and when the process receives this signal it doe开发者_Python百科s some things, how is this best achieved in C?The way to send a signal to a process is kill(pid, s

I need to send a signal to a process and when the process receives this signal it doe开发者_Python百科s some things, how is this best achieved in C?


The way to send a signal to a process is kill(pid, signal); However, you should be aware that signals are not a robust means of inter-process communication except for parent-to-direct-child messages due to inherent race conditions. Pipes, files, directories, named semaphores, sockets, shared memory, etc. all provide greatly superior approaches to inter-process communication.


If you happen to be on one of the Unix variants, the following man pages will help:

man 2 kill
man 2 signal
man 2 sigvec


kill + fork runnable POSIX example

Time for some fun:

#define _XOPEN_SOURCE 700
#include <assert.h>
#include <signal.h>
#include <stdbool.h> /* false */
#include <stdio.h> /* perror */
#include <stdlib.h> /* EXIT_SUCCESS, EXIT_FAILURE */
#include <sys/wait.h> /* wait, sleep */
#include <unistd.h> /* fork, write */

void signal_handler(int sig) {
    char s1[] = "SIGUSR1\n";
    char s2[] = "SIGUSR2\n";
    if (sig == SIGUSR1) {
        write(STDOUT_FILENO, s1, sizeof(s1));
    } else if (sig == SIGUSR2) {
        write(STDOUT_FILENO, s2, sizeof(s2));
    }
    signal(sig, signal_handler);
}

int main() {
    pid_t pid;

    signal(SIGUSR1, signal_handler);
    signal(SIGUSR2, signal_handler);
    pid = fork();
    if (pid == -1) {
        perror("fork");
        assert(false);
    } else {
        if (pid == 0) {
            while (1);
            exit(EXIT_SUCCESS);
        }
        while (1) {
            kill(pid, SIGUSR1);
            sleep(1);
            kill(pid, SIGUSR2);
            sleep(1);
        }
    }
    return EXIT_SUCCESS;
}

Compile and run:

gcc -std=c99 signal_fork.c
./a.out

Outcome:

SIGUSR1
SIGUSR2
SIGUSR1
SIGUSR2
....

But beware that there are many complexities when dealing with signals:

  • only certain functions can be called from signal handlers: Why only async-signal-safe functions can be called from signal handlers safely?
  • different functions have different behaviors when interrupted by signals: man 7 signal, SA_RESTART
  • global variables can only be accessed from the signal handler if they have type sig_atomic_t: How does sig_atomic_t actually work?

Tested in Ubuntu 17.10, GitHub upstream.

0

精彩评论

暂无评论...
验证码 换一张
取 消

关注公众号