linux IPC之訊息佇列

2021-06-28 22:21:13 字數 2618 閱讀 9061

訊息佇列就是乙個訊息的鍊錶。可以把訊息看作乙個記錄,具有特定的格式以及特定的優先順序。對訊息佇列有寫許可權的程序可以向其中按照一定的規則新增新訊息;對訊息佇列有讀許可權的程序則可以從訊息佇列中讀走訊息。在linux系統中訊息佇列與鍵值一一對應。訊息佇列是通過鍊錶管理的,核心提供乙個struct msqid_ds *msgque[msgmni]向量維護核心的乙個訊息佇列列表,因此linux系統支援的最大訊息佇列數由msgque陣列大小來決定,每乙個msqid_ds表示乙個訊息佇列,並通過msqid_ds.msg_first、msg_last維護乙個先進先出的msg鍊錶佇列,當傳送乙個訊息到該訊息佇列時,把傳送的訊息構造成乙個msg結構物件,並新增到msqid_ds.msg_first、msg_last維護的鍊錶佇列,同樣,接收訊息的時候也是從msg鍊錶佇列尾部查詢到乙個msg_type匹配的msg節點,從鍊錶佇列中刪除該msg節點,並修改msqid_ds結構物件的資料。鍵值即是陣列msgque的索引。

msqid_ds 與msg相關的關係如下圖所示:

獲取鍵值

key_t ftok(char *pathname, char proj)

標頭檔案為」sys/ipc.h」。返回檔名對應的鍵值,失敗返回 -1。proj是訊息佇列名字,不能為空。fname是指定的檔名(已經存在的檔名)。需要有-t 的許可權,或用root許可權執行,通常設為/tmp。

建立/開啟訊息佇列

int msgget(key_t key, int msg***)

標頭檔案為sys/msg.h。key由ftok獲得。

msg***有:

ipc_creat 建立新的訊息佇列,應配有檔案許可權0666。

ipc_excl 與ipc_creat一同使用,表示如果要建立的訊息佇列已經存在,則返回錯誤。

ipc_nowait 讀寫訊息不阻塞。

當沒有與key相對應的訊息佇列並且msg***中包含了ipc_creat標誌 或 key的引數為ipc_private 時,建立乙個新的訊息佇列。

傳送訊息

int msgsnd(int msqid, struct msgbuf *msgp, int msgsz, int msg***)

向訊息佇列傳送一條訊息。引數msqid為訊息佇列的id,msgp為存放訊息的結構體。msgsz是訊息的長度,和陣列的大小不一樣哦。msg***為訊息標誌,通常為0,也可以為ipc_nowait。出錯返回 -1。

訊息格式

struct msgbuf ;

接收訊息

int msgrcv(int msqid, struct msgbuf *msgp, int msgsz, long msgtyp, int msg***)

引數msqid代表的訊息佇列中讀取乙個msgtyp型別的訊息,並把訊息儲存在msgp指定的msgbuf結構中。讀取後佇列中的訊息將會刪除。size為結構體中資料的大小,不要計算msgtyp。出錯返回 -1。

設定訊息佇列屬性

int msgctl ( int msgqid, int cmd, struct msqid_ds *buf );

引數:msgctl 系統呼叫對 msgqid 標識的訊息佇列執行 cmd 操作,系統定義了 3 種 cmd 操作: ipc_stat , ipc_set , ipc_rmid

ipc_stat : 該命令用來獲取訊息佇列對應的 msqid_ds 資料結構,並將其儲存到 buf 指定的位址空間。

ipc_set : 該命令用來設定訊息佇列的屬性,要設定的屬性儲存在buf中。

ipc_rmid : 從核心中刪除 msqid 標識的訊息佇列。

訊息傳送端:send.c

/*send.c*/

#include

#include

#include

#include

#include

#define msgkey 1024

struct msgstru

; main()

}

while (1)

} msgctl(msqid,ipc_rmid,0); //刪除訊息佇列

}

訊息接收端 receive.c

/*receive.c */

#include

#include

#include

#include

#include

#define msgkey 1024

struct msgstru

; /*子程序,監聽訊息佇列*/

void childproc()

/*接收訊息佇列*/

ret_value = msgrcv(msgid,&msgs,sizeof(struct msgstru),0,0);

printf("text=[%s] pid=[%d]\n",msgs.msgtext,getpid());

} return;

} void main()

}

Linux IPC 之訊息佇列

system v or posix 該使用哪個呢,這是個問題 相對而言,我更傾向於後者 posix mq posix mq 的概況看這裡 man mq overview 簡單的實現 include include include include define my mq name my test m...

Linux IPC 訊息佇列

systemv訊息佇列 為了便於程序之間通訊,我們可以使用管道通訊 systemv也提供了一些函式來實現程序的通訊.這就是訊息佇列.include int msgget key t key,int msg int msgsnd int msgid,struct msgbuf msgp,int msg...

linux IPC 訊息佇列 的核心限制

allocated queues 0 used headers 0 used space 0 bytes 對於 ipcs u 命令所顯示的ipc資源,如果要確定其限制,可以使用 ipcs l 命令 ipcs l shared memory limits max number of segments ...