一、共享記憶體ipc原理
共享記憶體程序間通訊機制主要用於實現程序間大量資料的傳輸,共享記憶體是在記憶體中單獨開闢的一段記憶體空間,這段記憶體空間有自己特有的資料結構,包括訪問許可權、大小和最近訪問時間。
資料結構定義如下:
struct shmid_ds ;
兩個程序在使用此共享記憶體空間之前,需要在程序位址空間與共享記憶體空間之間建立聯絡,即將共享記憶體空間掛載到程序中。並且在使用共享記憶體進行資料的訪問時,需要對空間進行同步操作,這個可以使用訊號量機制完成。
系統對共享記憶體做了以下限制:
#define shmmin 1 /* min shared seg size (bytes) */
#define shmmni 4096 /* max num of segs system wide */
#define shmmax (ulong_max - (1ul << 24)) /* max shared seg size (bytes) */
#define shmall (ulong_max - (1ul << 24)) /* max shm system wide (pages) */
#define shmseg shmmni /* max shared segs per process */
二、共享記憶體的管理
1、建立共享記憶體
函式原型:
int shmget(key_t key, size_t size, int shm***)
函式傳入值:
key
0(ipc_private):會建立新共享記憶體物件
大於0的32位整數:視引數shm***來確定操作。通常要求此值**於ftok返回的ipc鍵值
size
大於0的整數:新建的共享記憶體大小,以位元組為單位
0:只獲取共享記憶體時指定為0
shm***
0:取共享記憶體識別符號,若不存在則函式會報錯
ipc_creat:當shm***&ipc_creat為真時,如果核心中不存在鍵值與key相等的共享記憶體,則新建乙個共享記憶體;如果存在這樣的共享記憶體,返回此共享記憶體的識別符號
ipc_creat|ipc_excl:如果核心中不存在鍵值 與key相等的共享記憶體,則新建乙個共享記憶體;如果存在這樣的共享記憶體則報錯
函式返回值:
成功:返回共享記憶體的識別符號
出錯:-1,錯誤原因存於error中
2、共享記憶體控制
函式原型:
int shmctl(int shmid, int cmd, struct shmid_ds *buf)
函式傳入值:
shmid
共享記憶體識別符號
cmd
ipc_stat:得到共享記憶體的狀態,把共享記憶體的shmid_ds結構複製到buf中
ipc_set:改變共享記憶體的狀態,把buf所指的shmid_ds結構中的uid、gid、mode複製到共享記憶體的shmid_ds結構內
ipc_rmid:刪除這片共享記憶體
buf
共享記憶體管理結構體。具體說明參見共享記憶體核心結構定義部分
函式返回值
成功:0
出錯:-1,錯誤原因存於error中
3、對映共享記憶體物件
函式原型:
void *shmat(int shmid, const void *shmaddr, int shm***)
函式傳入值:
shmid
共享記憶體識別符號
shmaddr
指定共享記憶體出現在程序記憶體位址的什麼位置,直接指定為null讓核心自己決定乙個合適的位址位置
shm***
shm_rdonly:為唯讀模式,其他為讀寫模式
4、分離共享記憶體物件
函式原型:
int shmdt(const void *shmaddr)
函式返回值:
成功:0
出錯:-1,錯誤原因存於error中
三、使用共享記憶體進行程序間通訊的例項
1、傳送端程序
/*
*使用共享記憶體進行程序間的通訊,並運用訊號量機制實現同步
*此為資訊的傳送者
*/#include
#include
#include
#include
#include
#include
#include
#include
int main(int argc , char* argv)
if(semctl(semid , 0 , setval , 0) == -1) //設定初始值為0
exit(exit_failure) ;
}shid = shmget((key_t)654321 , (size_t)2048 , 0600 | ipc_creat) ; //建立共享記憶體(或讀id)
if(shid == -1)
sharem = shmat(shid , null , 0) ; //掛載共享記憶體到當前程序
if(sharem == null)
while(running)
}if(strcmp(sharem , "end") == 0)
}shmdt(sharem) ; //解掛
return
0 ;}
2、接收端程序
/*
*使用共享記憶體進行程序間的通訊,並運用訊號量機制實現同步
*此為資訊的接收者
*/#include
#include
#include
#include
#include
#include
#include
#include
int main(int argc , char* argv)
shid = shmget((key_t)654321 , (size_t)2048 , 0600 | ipc_creat) ; //建立共享記憶體(或讀id)
if(shid == -1)
sharem = shmat(shid , null , 0) ; //掛載共享記憶體到當前程序
if(sharem == null)
while(running)
printf("%s\n" , sharem) ;
}if(strcmp(sharem , "end") == 0)
}shmdt(sharem) ; //解掛
if(shmctl(shid , ipc_rmid , 0) != 0) //刪除共享記憶體
if(semctl(semid , ipc_rmid , 0) != 0) //刪除訊號量
return
0 ;}
3、我們可以檢視執行結果
傳送端:
接收端:
可以看到順利通訊(:
linuxC多程序通訊systemv 共享記憶體
共享記憶體通訊限制 舉例 獲取共享記憶體物件的id int shmget key t key,size t size,int shm 對映共享記憶體 void shmat int shmid,const void shmaddr,int shm 解除記憶體對映 int shmdt const voi...
system V 程序間通訊 訊息佇列
程序間通訊,顧名思義就是程序和程序通訊,也就是程序a和程序b可以訪問核心的同一塊空間乙個放資料,乙個取資料,那麼這兩個程序就完成通訊通訊了。訊息佇列也有管道一樣的不足 1.每個訊息的最大長度是有上限的msgmax位元組,每個訊息佇列的總位元組數是有上限的msgmnb,系統中訊息佇列的總數是有上限的m...
Ubuntu下Linux程序間通訊 共享記憶體
linux提供了多種程序間通訊的方法,常見有管道 匿名 fifo 有名管道 訊息佇列 訊號量 共享記憶體,socket通訊。linux程序間通訊 匿名管道 linux程序間通訊 fifo 有名管道 linux程序間通訊 訊息佇列 linux程序間通訊 訊號量 linux程序間通訊 共享記憶體 5.共...