进程间通信(四)---- 共享内存

来源:互联网 发布:mysql终端查看数据库 编辑:程序博客网 时间:2024/06/09 18:11
共享内存机制是IPC机制中最快的通信方式,允许不同的进程访问同一块物理内存,通过这块内存进行进程间通信,进程的地址空间中有一部分称为共享区,而共享内存机制则是利用了这一部分的虚拟地址,通过使用共享区的虚拟地址,通过页表,MMU进行映射到某一物理内存上,而这块物理内存也通过同样的方法,被另一个进程所看到,这样就能进行进程间通信
由于共享内存机制可以直接通过正常的访问物理内存的方式(地址空间上的虚拟地址)进行访问共享内存空间,从而进行进程间通信,所以这样一来节约了从进程拷贝数据到内核,再从内核拷贝数据到进程这样一来一回的时间,所以效率大大提高
与消息队列,信号量一样,共享内存也是生命周期随内核的,但是共享内存并提供同步与互斥机制,所以一般要与信号量/记录锁/互斥量进行搭配使用

共享内存对应的接口如下:
int shmget(key_t key,int size,int flag);
函数功能:开辟一块共享内存或获取一块已分配的共享内存
参数:第一个参数由ftok()函数获得(当两个进程是父子进程,则可以赋值为IPC_PRIVATE);第二个参数表示开辟的共享内存的字节数(一般建议为4字节或4096字节的整数倍);第三个参数主要有两个宏(IPC_CREAT和IPC_EXCL),一般与对应权限(如:0640)进行按位或
返回值:若成功则返回对应共享内存的标识符,否则返回-1

void* shmat(int shmid,const void* addr,int flag);
函数功能:将指定共享内存与进程地址空间地址进行连接
参数:第一个参数表示指定的共享内存标识符;第二个参数表示指定的地址空间的虚拟地址(一般设为NULL,由系统进行选定,一般不自己进行指定);第三个参数表示本进程对该内存的操作模式,可以由两个取值:SHM_RND和SHM_RDONLY。SHM_RND为读写模式,SHM_RDONLY是只读模式。需要注意的是,共享内存的读写权限由它的属主、它的访问权限和当前进程的属主共同决定。如果当shmflg & SM_RDONLY为true时,即使该共享内存的访问权限允许写操作,它也不能被写入。该参数通常会被设为0
返回值:函数调用成功时,返回共享内存连接的起始虚拟地址,失败时返回-1

int shmdt(char* shmaddr);
函数功能:用于函数删除本进程对这块内存的使用,结束与这块共享内存的连接
参数:唯一参数表示对应虚拟地址
返回值:若成功返回0,否则返回-1
可以将shmat与shmdt类比于malloc/free

int shmctl(int shmid,int cmd,struct shmid_ds* buf);
函数功能:对指定共享内存进行操作
参数:第一个参数表示指定共享内存的标识符;第二个参数表示采取的操作(IPC_STAT 得到共享内存的状态:把shmid_ds结构中的数据设置为共享内存的当前关联值;IPC_SET 改变共享内存的状态:把共享内存的当前关联值设置为shmid_ds结构中给出的值;IPC_RMID 删除共享内存段);第三个参数表示一个结构体指针
返回值:若成功则返回0,否则返回-1

shmid_ds结构体如下:
struct shmid_ds
{
     uid_t shm_perm.uid;
     uid_t shm_perm.gid;
     uid_t shm_perm.mode;
}

参考博客如下:
http://blog.csdn.net/ljp1919/article/details/52605314
原创粉丝点击