上篇文章介绍了进程间的FIFO通信,FIFO通信属于有名管道通信,其能够用于任何进程间的数据通信。
今天介绍第三种进程通信方式—共享内存。

共享内存的概念

共享内存(share memory)是一种最为高效的进程间通信方式,是因为进程能够直接对内存进行读写,且不需要进行数据的保存与复制。
为了实现在多个进程间高效的数据通信,linux内核特地留下一块内存区,该内存区能够被需要的进程映射到自身的内存空间。因此,进程便能够直接对这块内存区进行读写操作。
共享内存的实现进程通信的原理图如下:

共享内存的实现步骤

共享内存的实现较为简单,一共分为两个步骤:
创建共享内存。通过函数shmget()从内存中获取一块共享内存区域,该函数返回值为共享内存的ID。映射共享内存。通过函数shmat()将上一步获取的共享内存映射到具体的内存空间。
NOTE:先创建共享内存,再将共享内存映射到每个进程中。
下图为一个简单的共享内存实现流程图:

共享内存的代码实现

下面是共享内存的代码实现(已在linux环境下编译通过):
//文件名shm.c #include#include#include#include#include#include#include#include#define MAX_BUFFER_LEN 1024 int main() { pid_t pid; int shm_id; char* shm_addr; char flag[] = "WROTE"; char buff[MAX_BUFFER_LEN]; int i = 0; memset(buff, 0, sizeof(buff)); shm_id = shmget(IPC_PRIVATE, MAX_BUFFER_LEN, 0666);//创建共享内存文件,并设置文件掩码 if(shm_id == -1) { printf("creat share memory fail.\n"); return 0; } else { printf("creat share memeory: %d\n", shm_id); } system("ipcs -m"); pid = fork();//创建子进程 if(pid == -1) { printf("creat child process fail.\n"); exit(1); } else if(pid == 0)//子进程进入该分支 { printf("this is child process.\n"); shm_addr = shmat(shm_id, 0, 0);//将共享内存映射到子进程 if(shm_addr == (void*)-1) { perror("child: shmat"); exit(1); } else { printf("child: attach shared-memory: %p\n", shm_addr); } system("ipcs -m"); while((strncmp(shm_addr, flag, strlen(flag))) && (i