Maison > développement back-end > tutoriel php > Linux - sémaphore de communication inter-processus

Linux - sémaphore de communication inter-processus

黄舟
Libérer: 2023-03-04 22:42:01
original
1252 Les gens l'ont consulté

1. Qu'est-ce qu'un sémaphore ?
C'est un compteur utilisé pour décrire le nombre de certaines ressources. Il réalise la communication de processus en contrôlant d'autres ressources de communication. Il est responsable de l'exclusion mutuelle des données, de la synchronisation, etc. au cours de ce processus. L'exclusion mutuelle signifie qu'un seul processus de A et B s'exécute pendant la même période. synchrone. Autrement dit, une fois le processus A terminé, le processus B est ensuite terminé et il existe un certain ordre d'exécution.

2. Principe de fonctionnement
Deux modes de fonctionnement, fonctionnement P et fonctionnement V.

Opération P (c'est-à-dire demander des ressources et le sémaphore est réduit de un)

Opération V (libérer des ressources et le sémaphore est augmenté de un)

3. ipcs -s Afficher semid

ipcrm -s id Supprimer l'identifiant

4. Fonctions principales
shmget Créer un sémaphore

shmctl Supprimer

shmop Opération P/V

Prototype de fonction : int semop(int sem_id,struct sembuf *sops,size_t nsops);

sem_id est créé via la fonction shmget

struct sembuf * paramètre sops sops Pointe vers un tableau de structures, chaque structure sembuf correspond à une opération de signal. La structure est la suivante

struct sembuf
{
unsigned short sem_num;//sem_num是信号集中的索引,0代表第一个,1,代表第二个。。。 
short sem_op; //操作类型,1 -->V操作,-1-->P操作
short sem_flg; //操作标志 
 };
Copier après la connexion

Il existe deux types de drapeaux sem_flg : IPC_NOWAIT ou SEM_UNDO. Si l'opération spécifie SEM_UNDO (je lui ai donné 0 ci-dessous), elle annulera automatiquement le processus à la fin.
nsops est le nombre de sops
~~ ~~~~~~~~~~ ~~~~********** le nom de la fonction homme peut voir l'utilisation de la fonction** ** ******~~~~~~~~~~~~~~~~~~

5. Implémentation du code
comm.h

#pragma once  
   #include<stdio.h>  
   #include<stdlib.h>  
   #include<unistd.h>  
   #include<sys/types.h>  
   #include<sys/ipc.h>  
   #include<sys/sem.h>  
   #define _PATH_ "."  
   #define _PROG_ID_ 0x6675  
    
   union semun  
   {  
      int val;  
      struct semid_ds *buf;   
      unsigned short *array;  
      struct seminfo *__buf;  
  };  
  int creatSem(int nsems);  
  int get_Sem();  
  int initSem(int sem_id,int Which);  
  int destroySem(int sem_id);  
  int V_Sem(int sem_id,int which);  
  int P_Sem(int sem_id,int which);  
  static int op_Sem(int sem_id,int op,int which);
Copier après la connexion

comm.c

#include"comm.h"  
   int creatSem(int nsems)  
   {  
       key_t  _key=ftok(_PATH_,_PROG_ID_);  
       if(_key<0)  
       {  
           perror("ftok");  
           return -1;  
       }  
      umask(0);  
      int sem_Flg=IPC_CREAT|IPC_EXCL|0666;  
      int sem_id=semget(_key,nsems,sem_Flg);  
      if(sem_id<0)  
      {  
          perror("semget");  
          return -1;  
      }  
      return sem_id;  
  }  
    
  int get_Sem()  
  {  
      key_t k=ftok(_PATH_,_PROG_ID_);  
      return semget(k,0,0);  
  }  
  static int op_Sem(int sem_id,int op,int which)  
  {  
      struct sembuf sem;  
      sem.sem_num=which;  
      sem.sem_op=op;  
      sem.sem_flg=0;  
      return semop(sem_id,&sem,1);  
    
  }  
    
  int initSem(int sem_id,int Which)  
  {  
      union semun _semum;  
      _semum.val=1;  
     int ret= semctl(sem_id,Which,SETVAL,_semum);  
     if(ret==-1)  
     {  
             perror("semctl");  
             return ret;  
     }  
     return ret;  
  }  
  int P_Sem(int sem_id,int which)  
  {  
      int ret=op_Sem(sem_id,-1,which);  
      if(ret==-1)  
     {  
          perror("p_sem");  
          return -1;  
      }  
          return ret;  
    
 }  
  int V_Sem(int sem_id,int which)  
  {  
      int ret=op_Sem(sem_id,1,which);  
      if(ret==-1)  
      {  
          perror("V_Sem");  
          return ret;  
      }  
      return ret;  
  }  
    
  int destroySem(int sem_id)  
  {  
      int ret=semctl(sem_id,0,IPC_RMID,NULL);  
      if(ret==-1)  
      {  
          perror("semtrl");  
          return -1;  
      }  
      return ret;  
    
  }
Copier après la connexion

my_shm.c

#include"comm.h"  
   int main()  
   {  
        int sem_id=creatSem(1);  
       initSem(sem_id,0);  
       pid_t id=fork();  
       if(id<0)  
       {  
           perror("for");  
          return -1;  
      }  
      else if(id==0)  
      {  
          int sem_id=get_Sem();  
          while(1)  
         {  
    
              P_Sem(sem_id,0);  
              printf("A");  
              fflush(stdout);  
              sleep(1);  
              printf("A");  
              fflush(stdout);  
              sleep(2);  
              V_Sem(sem_id,0);  
          }  
    
      }else  
      {  
          while(1)  
          {  
              P_Sem(sem_id,0);  
              printf("B");  
              fflush(stdout);  
              sleep(1);  
              printf("B");  
              fflush(stdout);  
              sleep(1);  
              V_Sem(sem_id,0);  
          }  
          waitpid(id,NULL,0);  
      }  
    
  }
Copier après la connexion

Avant d'utiliser le sémaphore (comme indiqué ci-dessous), vous pouvez voir que le les résultats d'impression sont aléatoires.

Linux - sémaphore de communication inter-processus

Après avoir ajouté le sémaphore (comme indiqué ci-dessous) (tous apparaissent par paires car ils s'excluent mutuellement)

Linux - sémaphore de communication inter-processus

Ce qui précède est le contenu de Linux-Inter-process Communication-Semaphore. Pour plus de contenu connexe, veuillez faire attention au site Web PHP chinois (www.php.cn) !


Étiquettes associées:
source:php.cn
Déclaration de ce site Web
Le contenu de cet article est volontairement contribué par les internautes et les droits d'auteur appartiennent à l'auteur original. Ce site n'assume aucune responsabilité légale correspondante. Si vous trouvez un contenu suspecté de plagiat ou de contrefaçon, veuillez contacter admin@php.cn
Tutoriels populaires
Plus>
Derniers téléchargements
Plus>
effets Web
Code source du site Web
Matériel du site Web
Modèle frontal