读书人

linux过程通信(四)-共享内存+信号量

发布时间: 2012-07-02 17:46:22 作者: rapoo

linux进程通信(四)--共享内存+信号量

   1. /*server.c:向共享内存中写入People*/     2. #include <stdio.h>     3. #include <sys/types.h>     4. #include <sys/ipc.h>     5. #include <sys/sem.h>     6.      7. int main()     8. {     9.     struct People{    10.         char name[10];    11.         int age;    12.     };    13.         14.     int semid;    15.     int shmid;    16.     key_t semkey;    17.     key_t shmkey;    18.     semkey=ftok("server.c",0);    19.     shmkey=ftok("client.c",0);    20.         21.     /*创建共享内存和信号量的IPC*/    22.     semid=semget(semkey,1,0666|IPC_CREAT);    23.     if(semid==-1)    24.     printf("creat sem is fail\n");    25.     shmid=shmget(shmkey,1024,0666|IPC_CREAT);    26.     if(shmid==-1)    27.     printf("creat shm is fail\n");    28.         29.     /*设置信号量的初始值,就是资源个数*/    30.     union semun{    31.         int val;    32.         struct semid_ds *buf;    33.         ushort *array;    34.     }sem_u;    35.         36.     sem_u.val=1;    37.     semctl(semid,0,SETVAL,sem_u);    38.         39.     /*将共享内存映射到当前进程的地址中,之后直接对进程中的地址addr操作就是对共享内存操作*/    40.         41.     struct People * addr;    42.     addr=(struct People*)shmat(shmid,0,0);    43.     if(addr==(struct People*)-1)    44.     printf("shm shmat is fail\n");    45.         46.     /*信号量的P操作*/    47.     void p()    48.     {    49.         struct sembuf sem_p;    50.         sem_p.sem_num=0;    51.         sem_p.sem_op=-1;    52.         if(semop(semid,&sem_p,1)==-1)    53.         printf("p operation is fail\n");            54.     }    55.     56.     /*信号量的V操作*/    57.     void v()    58.     {    59.         struct sembuf sem_v;    60.         sem_v.sem_num=0;    61.         sem_v.sem_op=1;    62.         if(semop(semid,&sem_v,1)==-1)    63.         printf("v operation is fail\n");    64.     }    65.         66.     /*向共享内存写入数据*/    67.     p();    68.     strcpy((*addr).name,"xiaoming");    69. /* 注意:①此处只能给指针指向的地址直接赋值,不能在定义一个  struct People people_1;addr=&people_1; 因为addr在addr=(struct People*)shmat(shmid,0,0);时,已经由系统自动分配了一个地址,这个地址与共享内存相关联,所以不能改变这个指针的指向,否则他将不指向共享内存,无法完成通信了。   70. 注意:②给字符数组赋值的方法。刚才太虎了。。*/    71.     (*addr).age=10;    72.     v();    73.         74.     /*将共享内存与当前进程断开*/    75.     if(shmdt(addr)==-1)    76.     printf("shmdt is fail\n");      77.         78. }  


   1. /*client.c:从共享内存中读出People*/     2. #include <stdio.h>     3. #include <sys/types.h>     4. #include <sys/ipc.h>     5. #include <sys/sem.h>     6.      7. int main()     8. {     9.     int semid;    10.     int shmid;    11.     key_t semkey;    12.     key_t shmkey;    13.     semkey=ftok("server.c",0);    14.     shmkey=ftok("client.c",0);    15.         16.     struct People{    17.         char name[10];    18.         int age;    19.     };    20.     21.     /*读取共享内存和信号量的IPC*/      22.     semid=semget(semkey,0,0666);    23.     if(semid==-1)    24.     printf("creat sem is fail\n");    25.     shmid=shmget(shmkey,0,0666);    26.     if(shmid==-1)    27.     printf("creat shm is fail\n");    28.         29.     /*将共享内存映射到当前进程的地址中,之后直接对进程中的地址addr操作就是对共享内存操作*/    30.     struct People * addr;    31.     addr=(struct People*)shmat(shmid,0,0);    32.     if(addr==(struct People*)-1)    33.     printf("shm shmat is fail\n");    34.         35.     /*信号量的P操作*/    36.     void p()    37.     {    38.         struct sembuf sem_p;    39.         sem_p.sem_num=0;    40.         sem_p.sem_op=-1;    41.         if(semop(semid,&sem_p,1)==-1)    42.         printf("p operation is fail\n");            43.     }    44.         45.     /*信号量的V操作*/    46.     void v()    47.     {    48.         struct sembuf sem_v;    49.         sem_v.sem_num=0;    50.         sem_v.sem_op=1;    51.         if(semop(semid,&sem_v,1)==-1)    52.         printf("v operation is fail\n");    53.     }    54.         55.     /*从共享内存读出数据*/    56.     p();    57.     printf("name:%s\n",addr->name);    58.     printf("age:%d\n",addr->age);    59.     v();    60.         61.     /*将共享内存与当前进程断开*/    62.     if(shmdt(addr)==-1)    63.     printf("shmdt is fail\n");    64.         65.     /*IPC必须显示删除。否则会一直留存在系统中*/    66.     if(semctl(semid,0,IPC_RMID,0)==-1)    67.     printf("semctl delete error\n");    68.     if(shmctl(shmid,IPC_RMID,NULL)==-1)    69.     printf("shmctl delete error\n");    70. }  

读书人网 >UNIXLINUX

热点推荐