linux 进程间通信(IPC)包括3种机制:消息队列、信号量、共享内存。消息队列和信号量均是内核空间的系统对象,经由它们

的数据需要在内核和用户空间进行额外的数据拷贝;而共享内存和访问它的所有应用程序均同处于用户空间,应用进程可以通过地址

映射的方式直接读写内存,从而获得非常高的通信效率。在GNU/Linux中所有的进程都有唯一的虚拟地址空间,而共享内存应用编程

接口API允许一个进程使用公共内存区段。 如果使用消息队列进行通信,那么一个进程要向队列中写入消息,这要引起从用户地址空

间向内核地址空间的一次复制,同样一个进程进行消息读取时也要进行一次复制,而共享内存的优点是完全省去了这些操作。两个不

同进程A、B共享内存的意思是,同一块物理内存被映射到进程A、B各自的进程地址空间。进程A可以即时看到进程B对共享内存中数

据的更新,反之亦然,因此通过共享内存映射到进程的虚拟地址空间,进程对其可以直接访问,避免了数据的复制过程。由于多个进程

共享同一块内存区域,必然需要某种同步机制,互斥锁和信号量

共享内存区的相关操作:

使用共享内存的流程:
   1.进程必须首先分配它。
   2.随后需要访问这个共享内存块的每一个进程都必须将这个共享内存绑定到自己的地址空间中。
   3.当完成通信之后,所有进程都将脱离共享内存,并且由一个进程释放该共享内存块。

#include <sys/ipc.h>
#include <sys/shm.h>
/*
创建一个新的内存共享区或者访问一个已经存在的共享内存区
返回共享内存区标识符
*/
int shmget(key_t key, size_t size, int shmflg);
/*
创建或打开一个共享内存区后,调用shmat把它连接到调用进程的地址空间
*/
void *shmat(int shmid, const void *shmaddr,int shmflg);
/*
当一个进程完成某个共享内存区的使用时,调用shmdt断开这个内存区
*/
int shmdt(const void *shmaddr);
/*
对内存区进行多种操作
cmd取值:
IPC_RMID:从系统中删除由shmid标识的共享内存区并拆除它
IPC_SET:给指定的共享内存区设置其shmid_ds结果成员
IPC_STAT:通过buff参数向调用者返回所指定共享内存区当前的shmid_ds结构
*/
int shmctl(int shmid, int cmd, struct shmid_ds *buf);

#include<sys/types>

#include<sys/ipc.h>

#include<sys/shm.h>

int shmget(key_t key, size_t size, int shmflg );

             参数:
                     key:ftok返回值或者IPC_PRIVATE
                     size:共享内存区大小( 字节为单位,if访问一个已经存在的,那么就是0 )
                     oflag:权限的组合

shmget()函数用于创建一个新的共享内存段,或者访问一个现有的共享内存段,它与消息队列以及信号集合对应的函数十分相似.如

果shmflg只为IPC_CREAT,shmget()或者将返回新创建的内存段标识符,或者返回早已存在于内核中的具有的相同关键字值(key)

的内存段的标识符;如果其同时为IPC_CREAT和IPC_EXCL,则如果该内存段不存在就创建一个新的内存段,如果早已存在,则此时

调用失败,并将返回-1.

#include<sys/types>

#include<sys/ipc.h>

#include<sys/shm.h>

void *shmat(int shmid,const void *shmaddr,int shmflg);

int shmdt(const void *shmaddr);

函数shmat()用来获取共享内存的地址,获取成功后,就可以像使用普通内存一样对其进行读写操作。

#include<sys/types>

#include<sys/ipc.h>

#include<sys/shm.h>

int shmdt(const void *shmaddr);

当某一个进程不再需要一个共享内存段时,它必须调用这个函数来断开与该内存段的连接

#include<sys/types>

#include<sys/ipc.h>

#include<sys/shm.h>

int shmctl(int shmid,int cmd,struct shmid_ds *buf);

共享内存控制函数,它的使用类似ioctl()的方式对共享内存进行操作:向共享内存的句柄发送命令,来完成某种命令

对于每个共享的内存区,内核维护如下的信息结构,定义在<sys/shm.h>头文件中。

 1 struct shmid_ds {
2   struct ipc_perm shm_perm;     /* operation perms */
3   int shm_segsz;            /* size of segment (bytes) */
4   time_t shm_atime;          /* last attach time */
5   time_t shm_dtime;          /* last detach time */
6   time_t shm_ctime;          /* last change time */
7   unsigned short shm_cpid;      /* pid of creator */
8   unsigned short shm_lpid;      /* pid of last operator */
9   short shm_nattch;          /* no. of current attaches */
10   /* the following are private */
11   unsigned short shm_npages;      /* size of segment (pages) */
12   unsigned long *shm_pages;       /* array of ptrs to frames -> SHMMAX */
13   struct vm_area_struct *attaches;   /* descriptors for attaches */
14 };

这里有点要注意,当我们调用shmdt()来删除共享内存段时,只是断开该进程与这个内存段的连接,而此时内核不一定就删除内存段,

结合上述,在成功完成了断开连接操作后,相关的shmid_ds结构的shm_nattch成员的值将减去1,如果这个值减到0,则内核将真正

删除该内存段。

linux编程之共享内存的更多相关文章

  1. Linux信号量同步共享内存实验.

    Linux信号量同步共享内存实验. Linux信号量同步共享内存实验. 简述 程序流程 信号量和共享内存的系统函数 信号量系统函数及接口 共享内存系统函数及接口 写程序 读程序 简述 本文主要内容是自 ...

  2. Linux环境进程间通信: 共享内存

    Linux环境进程间通信: 共享内存 第一部分 共享内存可以说是最有用的进程间通信方式,也是最快的IPC形式.两个不同进程A.B共享内存的意思是,同一块物理内存被映射到进程A.B各自的进程地址空间.进 ...

  3. Linux IPC之共享内存C 事例

    Linux IPC之共享内存 标签: linuxrandomnull工作 2011-08-25 11:52 4123人阅读 评论(0) 收藏 举报  分类: Linux(3)  读书札记(3)  版权 ...

  4. Linux进程间通信—使用共享内存

    Linux进程间通信-使用共享内存 转自: https://blog.csdn.net/ljianhui/article/details/10253345 下面将讲解进程间通信的另一种方式,使用共享内 ...

  5. Linux环境编程之共享内存区(一):共享内存区简单介绍

    共享内存区是可用IPC形式中最快的.一旦内存区映射到共享它的进程的地址空间,进程间数据的传递就不再涉及内核.然而往该共享内存区存放信息或从中取走信息的进程间通常须要某种形式的同步.不再涉及内核是指:进 ...

  6. linux网络编程之共享内存介绍

    今天是个好日子,洋人之节乃全球同庆,圣诞一来感觉就要过年了,不过今晚心情有点打折扣,给心爱的人打电话没有打通,本想在平安夜送上快乐的祝福给她,糟糕的心情让自己好像泄了气的皮球一样,无精打彩,心情灰暗, ...

  7. Linux IPC POSIX 共享内存

    模型 #include <unistd.h> //for fstat() #include <sys/types.h> //for fstat() #include <s ...

  8. Linux进程间通信之共享内存

    一,共享内存  内核管理一片物理内存,允许不同的进程同时映射,多个进程可以映射同一块内存,被多个进程同时映射的物理内存,即共享内存.  映射物理内存叫挂接,用完以后解除映射叫脱接. 1,共享内存的特点 ...

  9. Linux进程间通信——使用共享内存

    一.什么是共享内存 顾名思义,共享内存就是允许两个不相关的进程访问同一个逻辑内存.共享内存是在两个正在运行的进程之间共享和传递数据的一种非常有效的方式.不同进程之间共享的内存通常安排为同一段物理内存. ...

随机推荐

  1. [转]matlab语言中的assert断言函数

    MATLAB语言没有系统的断言函数,但有错误报告函数 error 和 warning.由于要求对参数的保护,需要对输入参数或处理过程中的一些状态进行判断,判断程序能否/是否需要继续执行.在matlab ...

  2. BZOJ 1406 密码箱(数论)

    很简洁的题目.求出x^2%n=1的所有x<=n的值. n<=2e9. 直接枚举x一定是超时的. 看看能不能化成有性质的式子. 有 (x+1)(x-1)%n==0,设n=a*b,那么一定有x ...

  3. JavaScript-序列化及转义

    1.  for循环: while循环: 2. 条件语句: 类似于if else的功能. name='1'; switch(name){ case:'1': console.log(123); brea ...

  4. BZOJ2659 [Beijing wc2012]算不出的算式 【数形结合】

    题目链接 BZOJ2659 题解 真没想到,, 观察式子 \[\sum\limits_{k = 1}^{\frac{p - 1}{2}} \lfloor \frac{kq}{p} \rfloor\] ...

  5. bzoj4870: [Shoi2017]组合数问题(DP+矩阵乘法优化)

    为了1A我居然写了个暴力对拍... 那个式子本质上是求nk个数里选j个数,且j%k==r的方案数. 所以把组合数的递推式写出来f[i][j]=f[i-1][j]+f[i-1][(j-1+k)%k].. ...

  6. [zhuan]Dalvik 分析 - Class加载篇

    http://blog.csdn.net/zhangyun438/article/details/17192787 内容如下: Java 源代码经过编译后会生成后缀为class的文件,也即字节码文件. ...

  7. 关于JavaScript的沙箱模式

    从语言学的角度上来说,允许代码无节制地使用全局变量,是最错误的选择之一.而更可怕的,就是一个变量"可能"成为全局的(在未知的时间与地点).但是这两项,却伴随JavaScript这门 ...

  8. Ubuntu中python多版本管理工具-pyenv

    ubuntu系统版本:16.04 # lsb_release -aNo LSB modules are available.Distributor ID: UbuntuDescription: Ubu ...

  9. HDU2896:病毒侵袭(AC自动机)

    病毒侵袭 Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Submis ...

  10. UVA:11183:Teen Girl Squad (有向图的最小生成树)

    Teen Girl Squad Description: You are part of a group of n teenage girls armed with cellphones. You h ...