zoukankan      html  css  js  c++  java
  • Linux c 信号量

    信号量(通过进程通信实现进程间的同步)

              信号量(semaphore)信号灯

                     信号量是共享内存整数数组.根据需要定义指定的数组长度

                           信号量就是根据数组中的值,决定阻塞还是解除阻塞

    编程模型:

    1.       创建或者得到信号量 semget

    2.       初始化信号量中指定下标的值 semctl

    3.       根据信号量阻塞或者解除阻塞 semop

    4.       删除信号量 semctl

    案例:

           A:                                 B:

               创建信号量                          得到信号量

               初始化信号量                        解除阻塞

               根据信号量阻塞

               删除信号量

            int semget(key_t key,

                                       int nums,//信号量数组个数

                                       int flags);//信号量的创建标记

                                                                                 //创建IPC_CREAT|IPC_EXCL|0666

                                                                                 //打开0

                         返回:  -1:失败

                                   >=0:成功返回信号量的ID

             

             

                         int semctl(int semid,

                                              intnums,//对IPC_RMID无意义

                                              intcmd,//SETVAL(信号量值) IPC_RMID

                                              ...);//对IPC_RMID无意义

                 参数:   
    semid:信号集的标识符,即是信号表的索引。
    semnum:信号集的索引,用来存取信号集内的某个信号。
    cmd:需要执行的命令,有效值有 需要使用联合体semun赋值

                   

                union  semun{

                    int  val;

                    struct semid_ds *buf;

                    unsigned short  *array;

                    struct seminfo   *_buf;

                };//需要自己定义该联合体,根据需要定义,需要那个字段就可以只定义那个

                                                                                       

                         int semop(

                                       int semid,//信号量ID

                                       struct sembuf*op,//对信号量的操作.操作可以是数组多个

                                       size_tnums,//第二个参数的个数

                                );

                         返回:

                                       -1:时失败

                                        0:成功         

                         struct  sembuf

                         {

                                int sem_num;//下标

                                int sem_op;

                                int sem_flg;//建议为0.

                         }


                        sem_op:
    前提条件信号量是unsigned short int;
    不能<0.
    -:够减,则semop马上返回,不够减,则阻塞.
    +:执行+操作
    0:判定信号量>0,则阻塞,直到为0
                   控制进程的搭配方式:
    +(解除阻塞) -(阻塞)
    0(阻塞)     -(解除阻塞)

    代码:

    semA:

    #include<stdio.h>

    #include<unistd.h>

    #include<sys/ipc.h>

    #include<sys/sem.h>

    #include<stdlib.h>

    #include<signal.h>

    int  semid;

    void  deal(int s)

    {

    //4.删除信号量

    printf(“删除信号量…”);

    semctl(semid,0,IPC_RMID , 0);

    printf(“信号量已删除”);

    exit( -1 );

         

    }

    union  semun{

                    int  val;

                    struct semid_ds *buf;

                    unsigned short  *array;

                    struct seminfo   *_buf;

                };

    void  main()

    {

        

         key_t key;

         union semun  v; //2.2定义初始化值

         int r;

         //3.1定义一个操作结构体

         struct sembuf op[1]; //定义了两个操作

         signal(SIGINT , deal);

         //1.创建信号量

         key=ftok(“.” , 99);

         if(key == -1) printf(“ftok err :%m ”) ,exit(-1);

         semid=semget(kay,1 /*信号量数组个数*/ , IPC_CREAT | IPC_EXCL | 0666);

         if( semget == -1) printf(“get err %m ”) ,exit(-1);

        

         //2.初始化信号量

         //2.1定义一个联合体

         v.val=2;

         r=semctl(semid , 0 , SETVAL , v); //设置信号量的值

         if(r== -1) printf(“初始化失败:%m ”) , exit(-1);

         //3.对信号量阻塞操作

         op[0].sem_num=0;  //信号量的下标

         op[0].sem_op= 1;   //信号量操作单位与类型

         op[0].sem_flg=0;    //操作标记  IPC_NOWAIT(信号量值够不够减都返回 不阻塞)

                           //SEM_UNDO    建议为0;

         while(1)

    {

             r=semop(semid , op ,1);

             printf(“信号量阻塞-1”);

    }

            

    }

    //semop操作减一 ,信号量值大于0,semop执行返回,信号量值等于0时,semop操作阻塞等待,直到信号量值大于0,在进行该操作

    semB:

    #include<stdio.h>

    #include<unistd.h>

    #include<sys/ipc.h>

    #include<sys/sem.h>

    #include<stdlib.h>

    union  semun{

                    int  val;

                    struct semid_ds *buf;

                    unsigned short  *array;

                    struct seminfo   *_buf;

                };

    void  main()

    {

         int semid;

         key_t key;

         int r;

         //3.1定义一个操作结构体

         struct sembuf op[1]; //定义了两个操作

         signal(SIGINT , deal);

         //1.得到信号量

         key=ftok(“.” , 99);

         if(key == -1) printf(“ftok err :%m ”) ,exit(-1);

         semid=semget(kay,1 /*信号量数组个数*/ ,0);

         if( semget == -1) printf(“get err %m ”) ,exit(-1);

        

      

         //3.对信号量阻塞操作

         op[0].sem_num=0;  //信号量的下标

         op[0].sem_op= +1;   //信号量操作单位与类型

         op[0].sem_flg=0;    //操作标记  IPC_NOWAIT(信号量值够不够减都返回 不阻塞)

                           //SEM_UNDO    建议为0;

         while(1)

    {

             r=semop(semid , op ,1);

             sleep(1);

    }

           

    }

    //进程semA进行信号量阻塞-1  semB进行信号量接触阻塞+1 , semB进程控制semA进程的执行

                        

                                              

  • 相关阅读:
    Kotlin Coroutines不复杂, 我来帮你理一理
    Refresh design pattern
    Android App安装包瘦身计划
    Google IO 2019 Android 太长不看版
    Effective Java读书笔记完结啦
    探究高级的Kotlin Coroutines知识
    移动应用中的非功能性(跨职能)需求
    Android程序员的Flutter学习笔记
    如何正确使用Espresso来测试你的Android程序
    MVP模式, 开源库mosby的使用及代码分析
  • 原文地址:https://www.cnblogs.com/james1207/p/3290138.html
Copyright © 2011-2022 走看看