Comment intercepter les signaux Linux? (en C)

Je dois intercepter et tracer les signaux de tous les fichiers binarys, comme le fait strace sous Linux. Je n’ai pas besoin d’une sortie aussi prolixe que la vraie strace. Je veux juste savoir comment cela fonctionne, comment puis-je intercepter les signaux et comment les retracer? Merci d’avance 🙂

    strace utilise l’appel système ptrace() pour le traçage, ce qui vous permet également d’intercepter (et éventuellement de manipuler) les signaux envoyés au processus.

    Voici un petit exemple:

     #include  #include  #include  #include  #include  #include  #include  int main(int argc, char **argv) { /* simple example, child is traced, uses alarm which causes a signal to be * set up */ pid_t child; child = fork(); if (child == 0) { ptrace(PTRACE_TRACEME, 0, NULL, NULL); alarm(3); while(1) { } exit(0); } /* parent */ while(1) { int wstatus; int signum; wait(&wstatus); if (WIFEXITED(wstatus) || WIFSIGNALED(wstatus)) break; signum = WSTOPSIG(wstatus); printf("child stopped with signal %d\n", signum); /* resume execution */ ptrace(PTRACE_CONT, child, NULL, signum); } return 0; } 

    Ceci est une implémentation simple:

    Mettez quelque part dans votre int main() plusieurs appels à signal() , un pour chaque signal que vous voulez capter. Le premier argument est le nom du signal. la seconde est la fonction de traitement du signal (plus bas):

      signal(SIGFPE, SignalHandler); signal(SIGILL, SignalHandler); signal(SIGINT, SignalHandler); signal(SIGSEGV, SignalHandler); signal(SIGTERM, SignalHandler); #ifndef WIN32 signal(SIGHUP, SignalHandler); signal(SIGQUIT, SignalHandler); signal(SIGKILL, SignalHandler); signal(SIGPIPE, SignalHandler); signal(SIGCHLD, SignalHandler); #endif 

    Maintenant, écrivez une fonction de signal. Il doit retourner void et accepter un int: void SignalHandler(int signal_number) :

     void SignalHandler(int signal_number) { printf("Received signal: %s\n", strsignal(signal_number); // Do something } 

    C’est tout! Vous pouvez également le tester en vous envoyant un signal avec la fonction raise(SIGNAL_NAME) ; Par exemple, essayez de raise(SIGTERM); !

    L’interception de signaux vers d’ autres processus est une chose à ne pas faire pour une raison autre que le débogage. C’est ce à quoi strace est destiné. Les processus doivent être capables de gérer leurs propres signaux.

    Inutile de dire que si vous écrivez un débogueur, comprenez ptrace ().