程序間通訊 訊息佇列

2021-08-15 03:16:41 字數 3340 閱讀 3248

程序間通訊——訊息佇列

什麼是訊息佇列?

訊息佇列就是提供了乙個程序向另乙個程序傳送乙個資料塊的方法,

其中每乙個資料塊都被認為有型別。接收者進、程接收的資料塊可以有不同的型別值,

通過傳送訊息來避免命名管道的同步和阻塞問題。

那麼訊息佇列和管道到底有什麼不同呢?

訊息佇列是基於訊息的,而管道是基於位元組流的;

訊息佇列的讀取不一定是先進先出的;

訊息佇列

是雙向通訊的,管道是單向通訊的;

訊息佇列可以在兩個沒有關係的程序之間通訊,而管道只能在兩個有血緣關係的程序之間通訊;

兩者又有一樣的不足:每個訊息的長度是有上限的,每個訊息的總位元組數是有限的,

系統中訊息佇列的總

數也是有

乙個上限的。

ipc(程序間通訊)物件的資料結構

核心會為每乙個ipc物件維護乙個資料結構

這兩個結構體只是讓大家了解一下,因為訊息佇列的底層使用鍊錶實現的,所以使用訊息佇列進行通訊,就是:乙個但程序在鍊錶鄰面放入結點,另外程序從鍊錶裡面取結點,但是如何保證每次取的結點就是我們想要的那個結點呢?其中ipc_perm結構體裡面,有乙個_key值,這個就是訊息佇列的唯一識別符號,我們在判斷訊息佇列時候,即使通過_key值來辨別訊息佇列的。

建立訊息佇列:msgget

int msgget(key_y key,int msgflage)

引數:①key: 此時的第乙個引數key是通過ftok函式建立

key_t ftok(const char* pathname,int proj_id);

pathname:帶路徑的檔名; proj_id:整數的工程號

返回值:成功返回key值,失敗返回-1

②msgflag:建立狀態

解釋:當把msgflag值傳:「ipc_creat」時候,呼叫msgget函式,系統就會為我們建立乙個新的消

息佇列,此時我們給出的key值已經存在的時候,此時就會把已經存在的訊息佇列的識別符號,

也就是:msgid傳過來;

當把msgflag值傳:「ipc_creat|ipc_excl」此時,當我們要建立的訊息佇列不存在時,就

會建立新的訊息佇列,當我們傳進來的key值已經存在的時候,此時就會報錯。 

返回值:成功則返回建立的訊息佇列的msgid,失敗則返回-1

使用**來建立兩個程序之間的相互通訊——訊息佇列

實現之前,學習幾個相關的知識點:

①我們知道管道的生命週期是隨程序的,也就是程序結束的時候,管道也就結束了,但是訊息佇列生命週期

是隨核心的,也就是說,當我們在程序結束的時候,沒有通過指令或者**去銷毀訊息佇列,那麼這個消

息佇列就會一直存在,直到我們重啟或者關機。

②在系統中檢視存在的訊息佇列命令:

ipcs :檢視系統中當前所有ipc資源

ipcs -q:檢視系統中已建立的訊息佇列

ipcrm -q ××××:銷毀指定的訊息佇列,××××代表msgid

③實現原理:我們在comm.h中把函式進行宣告,

在comm.c中對函式進行實現,然後在建立:server.c和client.c,模擬兩個程序,使得兩個程序

相互通訊,在server.c和client.c中加入comm.h使用實現的方法

下面是**:comm.h:

#ifndef _comm_h_

#define _comm_h_

#include#include#include#include#include"comm.c"

#define server_type 1

#define client_type 2

int creatmsgqueue();

int destorymsgqueue(int msgid);

int recvmsg(int msgid,int who,char* outmsg);

int sendmsg(int msgid,int who,const char* msg);

#endif

comm.c:
#include#include#include#include#include#define pathname "."

#define proj_id 0x6666

struct msgbuf;

static int commmsgqueue(int flags)

int msgid = 0;

if((msgid = msgget(_key,flags))<0)

return msgid;

}int creatmsgqueue()

int getmsgqueue()

int destorymsgqueue(int msgid)

}int sendmsg(int msgid,int who,const char* msg)

return 0;

}int recvmsg(int msgid,int who,char* outmsg)

strcpy(outmsg,_mb.mtext);

return 0;

}

server.c:

#include#include "comm.h"

int main()

} destorymsgqueue(msgid);

return 0;

}

client.c:

#include#include "comm.h"

int main()

recvmsg(msgid,server_type,buf);//因為和server通訊,所以接收server型別的資料

printf("server say#%s\n",buf);//把收到的資料列印出來

} return 0;

}

注意:在執行的時候,要注意幾點,因為訊息佇列在server.c建立的,所以要先去執行server.c檔案,

然後,server.c是先去收訊息,收訊息的狀態是阻塞式,所以此時在沒有執行client.c的時候,

server.c是執行介面都沒有的,每次執行結束之後,我們都要用指令去把剛才建立的訊息佇列銷毀掉,

不然在下一次執行**的時候,就會出現問題,我就是在這塊弄了半天。

tip:限於編者水平,文章難免有缺漏之處,歡迎指正。

程序間訊息佇列通訊

要保證server能夠接收client的訊息,就必須保證server的生成的msg的識別符號是一樣的,也就是兩個用的key是必須一樣的。msglucy.c include include include include include include include include include ...

程序間通訊(訊息佇列)

在嵌入式linux應用開發中,linux程序通訊的方式有6種,分別是管道 pipe 及有名管道 named pipe 訊號 signal 訊息佇列 msg 共享記憶體 shm 訊號量 和套接字 socket 在這我就簡單的描述一下程序通訊中的資訊佇列 msg 首先,訊息佇列的實現有重要的幾步 1 建...

程序間通訊 訊息佇列

有三種稱作xsi ipc的ipc 訊息佇列 訊號量以及 共享記憶體。它們只見有很多的相似之處。訊息佇列是訊息的鏈結表,儲存在核心中,由訊息佇列識別符號表示。它不同於管道,其生命週期是隨核心的。訊息佇列提供了 一種從 乙個程序向另 乙個程序傳送 乙個資料塊的 方法。每個資料塊都被認為是有 乙個型別,接...