Maison  >  Article  >  Tutoriel système  >  Analyser le saint patron de Linux

Analyser le saint patron de Linux

PHPz
PHPzavant
2024-04-29 12:28:13498parcourir
La différence entre le processus d'arrière-plan et le processus démon
    Les plus grandes différences sont les suivantes :
  • (a) Le processus démon s'est complètement séparé de la console du terminal, mais le programme d'arrière-plan ne s'est pas complètement séparé du terminal (les résultats seront toujours envoyés au terminal avant la fermeture du terminal) ;
  • (b) Le processus démon ne sera pas affecté lors de la fermeture de la console du terminal, mais le programme en arrière-plan s'arrêtera lorsque l'utilisateur quittera. Il doit être exécuté dans la commande et le format nohup pour éviter cet impact ;
  • (c) Le groupe de session, le répertoire courant et les descripteurs de fichiers du démon sont indépendants. L'exécution en arrière-plan n'est qu'un fork du terminal pour permettre au programme de s'exécuter en arrière-plan. Rien n'a changé ;
  • .

Analyser le saint patron de Linux

Caractéristiques du démon

Le démon est un processus spécial qui s'exécute en arrière-plan. Il est séparé du terminal, empêchant ainsi le processus d'être interrompu par des signaux générés par n'importe quel terminal, et les informations générées lors de l'exécution du processus ne sont affichées sur aucun terminal. . Un processus démon exécute périodiquement certaines tâches ou attend le traitement de certains événements qui se produisent. La plupart des serveurs Linux sont implémentés à l'aide de processus démon.

Points clés de la programmation démon
    1. Le blindage de certains signaux liés au fonctionnement du terminal de contrôle vise à empêcher que le terminal de contrôle ne soit gêné lors de sa sortie ou ne se bloque avant que le processus démon ne démarre normalement. le code s'affiche comme ci-dessous :
      /* 处理可能的终端信号 */
      signal(SIGTTOU, SIG_IGN);
      signal(SIGTTIN, SIG_IGN);
      signal(SIGTSTP, SIG_IGN);
      signal(SIGHUP , SIG_IGN);
      
    2. Exécuter en arrière-plan.
      /* 是父进程,结束父进程,子进程继续 */
      if(fork())
          exit(0);
      
    3. Gagnez le contrôle du terminal et du groupe de processus :
      • (1) Un processus appartient à un groupe de processus, et le numéro de groupe de processus (PGID) est le numéro de processus (PID) du responsable du processus
      • (2) Les processus d'un même groupe de processus partagent un terminal de contrôle Par défaut, ce terminal de contrôle est le terminal sur lequel le processus a été créé
      • .
      • (3) Le terminal de contrôle et le groupe de processus associés à un processus sont généralement hérités du processus parent. Par conséquent, le processus enfant est toujours affecté par le terminal du processus parent, car les signaux générés par le terminal seront envoyés à tous. processus dans le groupe de processus de premier plan.

      Pour les raisons ci-dessus, il est nécessaire de supprimer complètement l'influence du terminal sur le processus enfant. Il est nécessaire d'appeler setsid() pour que le processus enfant soit le nouveau leader de session.

      setsid();
      Une fois l'appel setsid() réussi, le processus appelant cette fonction devient le nouveau leader de session et le nouveau leader de processus, et est séparé du groupe de processus d'origine. En raison de l'exclusivité du processus de session sur le terminal de contrôle, le processus est en même temps détaché du terminal de contrôle.

    4. Pour interdire au processus de rouvrir le terminal de contrôle, la méthode utilisée consiste à créer à nouveau un processus enfant et à laisser le processus parent se terminer. Le processus enfant n'est plus le leader de la session, atteignant ainsi l'objectif. le code s'affiche comme ci-dessous :
      /* 结束第一子进程,第二子进程继续 */
      if(fork())
          exit(0);
      
    5. Fermez les descripteurs de fichiers ouverts. Étant donné qu'un processus hérite des descripteurs de fichiers ouverts du processus parent qui l'a créé, ils ne sont généralement plus nécessaires. S'il n'est pas fermé, les ressources système seront gaspillées. le code s'affiche comme ci-dessous :
      #define NOFILE  256
      
      for(i=0; i
    6. Modifiez le répertoire de travail actuel. Lorsqu'un processus est actif, le système de fichiers contenant son répertoire de travail ne peut pas être démonté. Par conséquent, vous devez remplacer le répertoire de travail du démon par un répertoire approprié. le code s'affiche comme ci-dessous :
      chdir("/tmp");
    7. Réinitialiser le masque de création de fichier. Un processus hérite du masque de création de fichier du processus parent qui l'a créé. Il peut modifier les autorisations d'accès aux fichiers créés par le démon. le code s'affiche comme ci-dessous :
      umask(0);
      
    8. Gérer le signal SIGCHLD (signal de sortie du processus enfant). Si vous n'attendez pas la fin du processus enfant, le processus enfant deviendra un processus zombie et occupera les ressources du noyau système.
      /* 将子进程退出信号设为SIG_IGN,让系统帮助回收进程资源 */
      signal(SIGCHLD, SIG_IGN);
    9. Le code global est le suivant :

      #define NOFILE      256
      
      void DaemonMode()
      {
          int num = 0;
          int fd0, fd1, fd2;
      
          /* 屏蔽可能的信号 */
          signal(SIGTTOU, SIG_IGN);
          signal(SIGTTIN, SIG_IGN);
          signal(SIGTSTP, SIG_IGN);
          signal(SIGHUP , SIG_IGN);
      
          if(fork())
              exit(0);
      
          setsid();
      
          if(fork())
              exit(0);
      
          chdir("/tmp/httpd");
      
          umask(0);
      
          for(; num

Ajout de la fonction setsid() :
Si le processus appelant est déjà le leader d'un groupe de processus, cette fonction renvoie une erreur. Afin d'éviter cette situation, fork() est généralement appelé pour créer un processus enfant, puis son processus parent est terminé, tandis que le processus enfant continue, et cette fonction est appelée dans le processus enfant.

Si le processus appelant cette fonction n'est pas un leader de groupe de processus, cette fonction créera une nouvelle session et le processus appelant la fonction setsid() deviendra le processus leader de la nouvelle session et sera séparé du groupe de session et du processus. groupe de son processus parent. La session étant exclusive au terminal de contrôle, le processus est simultanément détaché du terminal de contrôle.

Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!

Déclaration:
Cet article est reproduit dans:. en cas de violation, veuillez contacter admin@php.cn Supprimer