您的位置:首页 > 其它

进程间通信(五):共享内存

2015-05-11 23:21 169 查看

一.基本概念

共享内存允许进程共享一块存储区,数据不需要在进程之间复制,所以这是一种最快的IPC,适合大数据量的IPC,通常会使用信号量实现对共享存储区访问的同步。


二.api

int shmget(key_t key, size_t size, int flag)

根据key获取共享内存的标识符,与消息队列,信号量的函数类似,

此处size用来指定共享存储区的大小,创建时才有用;

int shmctl(int shmid, int cmd, struct shid_ds *buf)

根据cmd,实现对此共享内存信息的读取或者设置

cmd = IPC_RMID, 从系统中删除此共享存储段,如果有进程还在使用

此共享存储段,则直到最后一个使用此共享存储段的进程停止或者与

此段脱接才真正删除此存储段,注意这个地方与消息队列和信号量不

一样,消息队列和信号量都是立即生效;

void* shmat(int shmid, const void* addr, int flag)

获取此共享存储段的在本进程的地址

如果addr=0,内核会选择第一个可以用的地址,推荐使用此方式;

如果addr!=0, 将共享存储段落连接到指定的地址,如果flag指定了

SHM_RND, 会根据SHMLBA对addr取整;

int shmdt(void *addr);

使地址addr与共享存储段脱接,不再使用此共享存储段时应调用此函数

三.例子

code: shmem.c

1 #include<stdlib.h>
2 #include<string.h>
3 #include<stdio.h>
4 #include<sys/shm.h>
5 #include<sys/ipc.h>
6 #include<errno.h>
7 #include<unistd.h>
8
9 #define SHMEMPATH  "/tmp/sharemem"
10 #define SHM_SIZE 1024
11
12 int main(int argc, char* argv[])
13 {
14  int count = 0;
15  int bwrite = 0;
16  key_t key = ftok(SHMEMPATH,1);
17  char* shmptr = NULL;
18  int shmid;
19  shmid  = shmget(key, SHM_SIZE, IPC_CREAT | 0660);
20  if(shmid < 0)
21  {
22         printf("shmget err,errno:%d", errno);
23         exit(1);
24  }
25
26  if(argc > 1)
27  {
28         bwrite = 1;
29
30  }
31
32  shmptr = (char*)shmat(shmid, 0, 0);
33
34   if(bwrite)
35   {
36         memcpy(shmptr, argv[1],strlen(argv[1])+1);
37         printf("write into shm context:%s\n", argv[1]);
38   }
39  else
40   {
41         printf("context in shm:%s\n", shmptr);
42   }
43
44   if(shmdt((void*)shmptr) < 0)
45   {
46     printf("shmdt err !\n");
47   }
48   return 0;
49 }


把shmem.c编译成可执行文件shmbin,执行结果如下:

./shmbin “hello share memory”

write into shm context:hello share memory

./shmbin

context in shm:hello share memory
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: