system V 消息队列的用法

来源:互联网 发布:java项目遇到最大困难 编辑:程序博客网 时间:2024/06/13 13:05

system消息队列,说白了就是内核维护的队列,这个队列的元素是进程发出的一些字符串。通过消息队列,可以实现进程间消息的传递。


对于每个消息队列,内核都维护了下面这个数据结构

struct msqid_ds {struct ipc_permmsg_perm;//存一些权限,创建信息之类的struct msg*msg_first;//ptr to first message on queuestruct msg*msg_last;//ptr to last message on queuemsglen_t msg_cbytes;//current # bytes on queuemsgqnum_t msg_qnum;//current # of message on queuemsglen_t msg_qbytes;   <span style="white-space:pre"></span>//max \# of bytes allowed on queuepid_t msg_lspid;//pid of last msgsndpid_t msg_lrpid;//pid of last msgrcvtime_tmsg_stime;//time of last msgsnd()time_t msg_rtime;//time of last msgrcv()time_t msg_ctime;//time of last msgctl()};


其实吧,这东西会用就行了,也就是4个API而已

1.msgget()函数-------建立消息队列

#include<sys/msg.h>int msgget(key_t key,int oflag);//若成功返回非负标识符,否则返回-1;

其中 key_t 要么是ftok()的返回值,要么是常量IPC_PRIVATE(0),要么是你随便填的一个非负数.

差别在于:系统通过key值确定你要使用哪个消息队列,两个进程想要使用消息队列通信,必须使用相同的key。

ftok(char * pathname,int id)函数可以通过一致的pathname和id很方便的构造出key;

IPC_PRIVATE 意为私有的,用这个参数得到的消息队列,只能通过fork()在本进程和子进程间使用 注;IPC_PRIVATE值为0

随便填一个非负数,你记住它就行了,在你想要通信的进程的msgget函数中填入相同的数,即可快活的使用消息队列,但!但!!但!!!这么填的话很有可能别的不相干的进程的msgget参数也是这个值,后果就是,这个消息队列中充斥着不同的信息,自己的消息被别的进程读了,别的进程的消息可能又被自己读了,。,。


oflag参数,基本就是: 权限位,IPC_CREAT,IPC_EXCL;

IPC_CREAT 如果消息队列不存在,就创建它。IPC_CREAT一般都与权限位异或,比如 0666|IPC_CREAT

IPC_EXCL 如果消息队列已存在,msgget返回 -1;


2.msgsnd()函数 ------发送消息

#include<sys/msg.h>int msgsnd(int msqid,const void *ptr,size_t length,int flag);//成功返回0,失败返回-1



msqid 消息队列标识符 是 msgget()的返回值
ptr 指向了消息结构体,模板如下

struct msgbuf {long mtype; // mssage type must be > 0 char mtext[length];// mssage data };

ptr指向一个long 长整型数,表示消息类型,紧跟其后的就是消息。

length 表示消息类型之后的,消息正文的长度。

flag只有两个参数 0 或 IPC_NOWAIT(非阻塞);


3.msgrcv()函数 -----接收消息

#include <sys/msg.h>ssize_t msgrcv(int msqid,void *ptr,size_t length,long type ,int flag);//若成功,返回成功读入的消息正文的字节数,否则返回-1


msqid : 消息队列标识符;

ptr :指向msgbuf结构体的指针;

length  :消息的正文长度 ,不包括消息类型long 

type; 接收类型, type  == 0 返回该队列第一个消息;

type > 0 返回消息类型等于type的第一个消息

type < 0 返回小于等于type绝对值的,最小的消息类型的第一个消息

flag: IPC_NOWAIT 非阻塞

do nothing

1 0