進程間通信(IPC)3 ------ 消息隊列 - 1

      消息隊列是一個存放在內核中的消息鏈表,由消息隊列標識符標識。

      向消息隊列發送消息時,必須組成合理的數據結構。Linux系統定義了一個模板數據結構msgbuf:

#include <linux/msg.h>
struct msgbuf{
      long mtype;
      char mtext[1];
};

      mtype字段代表消息類型。mtext字段指消息內容。


      消息隊列是隨着內核的存在而存在的,每個消息隊列在系統範圍內對應唯一的鍵值。要或得一個消息隊列的描述符,只需提供該消息隊列的鍵值即可,該鍵值通常由函數ftok返回。該函數原型:

#include <sys/types.h>
#include <sys/ipc.h>
key_t ftok(const char *pathname,int proj_id);

      ftok函數根據pathname和proj_id這兩個參數生成唯一的鍵值。pathname在系統中一定要存在且進程有權訪問,參數proj_id的取值範圍是1~255。執行成功會返回一個鍵值,失敗返回-1。

      ftok返回的鍵值可以提供給函數msgget。msgget()根據這個鍵值創建一個新的消息隊列或訪問一個已存在的消息隊列。msgget函數的原型:

#include <sys/msg.h>
int msgget(key_t key, int msgflg);

      參數key即爲ftok函數的返回值。msgflg是標誌參數,一般取值IPC_CREAT,表示創建一個消息隊列。

      創建消息隊列後,就可以對消息隊列進行讀寫了。函數msgsnd用於向消息隊列發送(寫)數據。

#include <sys/msg.h>
int msgsnd(int msgid, struct msgbuf *msgp, size_t msgsz, int msgflg);

      上述函數向msgid標識的消息隊列發送一個消息msgp。msgsz是消息的大小。msgflg爲操作標誌位。msgsnd函數成功返回0,失敗返回-1。


      以下程序演示如何向消息隊列發送消息:

#include <stdio.h>
#include <stdlib.h>
#include <sys/ipc.h>
#include <sys/msg.h>

#define BUF_SIZE	256
#define PROJ_ID		32
#define PATH_NAME	"."			//當前路徑

int main(void)
{
	/*用戶自定義消息緩衝*/
	struct mymsgbuf {
		long msgtype;
		char ctrlstring[BUF_SIZE];
	} msgbuffer;
	int		qid;    /*消息隊列標識符*/
	int		msglen;
	key_t	msgkey;

	/*獲取鍵值*/
	if((msgkey = ftok (PATH_NAME, PROJ_ID)) == -1)
	{
		perror ("ftok error!\n");
		exit (1);
	}

	/*創建消息隊列*/
	if((qid = msgget (msgkey, IPC_CREAT|0660)) == -1)
	{
		perror ("msgget error!\n");
		exit (1);
	}
	/*填充消息結構,發送到消息隊列*/
	msgbuffer. msgtype = 3;
	strcpy (msgbuffer.ctrlstring , "Hello,message queue");
	msglen = sizeof(msgbuffer) - 4;			//要發送的消息大小,不包含消息類型佔用的4個字節
	if(msgsnd (qid, &msgbuffer, msglen, 0) == -1)
	{
		perror ("msgget error!\n");
		exit (1);
	}

	exit(0);
}

      運行上述程序,即向消息隊列放入了一條消息,可以通過ipcs命令查看,執行結果如下:


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章