【Linux】进程间通讯---消息队列

    技术2022-07-11  68

    消息队列:

    消息:类型+数据,队列:先进先出(优先级队列)信号量、消息队列、共享内存都通过内核对象(操作系统内核中)共享,系统中所有进程的用户空间是独立的,内核空间是共享的

    消息队列相关函数:

    1、msgget函数:创建一个新的消息队列或打开一个已有的消息队列

    int magget( (key_t)key , int flag );

    返回值:成功返回内核对象的ID值,失败返回-1key:用户标识,如果多个进程想通过同一个消息队列完成数据通信,则每个进程使用相同的key值创建或者获取相同一个消息队列的内核对象ID值。flag:操作标志,IPC_CREAT,如果不存在就创建,存在就获取

    2、msgctl函数:读写消息队列要求无法满足时不阻塞

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

    msqid:消息队列标识符cmd:执行的控制命令,既要执行的操作,IPC_RMID删除消息队列,IPC_STAT获得msqid的消息队列头数据到buf中

    buf:临时的 msqid_ds 结构体类型的变量。用于存储读取的消息队列属性或需要修改的消息队列属性。

    3、msgsnd函数:向消息队列中发送一条消息

    int msgsnd(int msqid, const void *msgp, size_t msgsz, int msgflg);

    msgsnd()成功返回0,失败返回-1msqid:消息队列标识父msgp:存放发送给队列的消息的结构 struct msgbuf { long mtype;//消息类型 ,必须大于1 char mtext[1];//消息数据,字符数组 };

    msgsz:指定mtext中的有效数据的长度,要发送消息的大小,不含消息类型占用的4个字节,即mtext的长度

    msgflg:一般设为0,可以设置IPC_NOWAIT,当消息队列满时,msgsnd将会阻塞,直到消息能写进消息队列

    4、msgrcv()函数:从消息队列接受一条消息(一次只能获取一条消息)

    ssize_t msgrcv(int msqid, void *msgp, size_t msgsz, long msgtyp,int msgflg);

    成功返回mtext中接收到的长度数据,失败返回-1其他参数与msgsnd函数相同msgtyp:指定接受消息的类型,类型可以为0;0:接收第一个消息;小于0:接收类型等于msgtyp的第一个消;大于0:接收类型等于或者小于msgtyp绝对值的第一个消息msgflg:一般设为0,可以设置IPC_NOWAIT

     

    代码实现:

    //msg.h //系统未定义这一类型 #pragma once #include<stdio.h> #include<stdlib.h> #include<unistd.h> #include<string.h> #include<assert.h> #include<sys/msg.h> typedef struct msgdata { long mtype;//消息的大小 char mdata[128]; }MsgData; //msgB.c #include"./msg.h" int main() { int msgid = msgget((key_t)1234, IPC_CREAT | 0664); assert(msgid != -1); MsgData data; memset(&data, 0, sizeof(data)); msgrcv(msgid, &data, 127, 100, 0); printf("%d:%s\n", data.mtype, data.mdata); exit(0); } //msgA.c #include"./msg.h" int main() { MsgData data; memset(&data, 0, sizeof(data));//将data中的值初始化为0 data.mtype = 100; strcpy(data.mdata, "hello"); int msgid = msgget((key_t)1234, IPC_CREAT || 0664); assert(msgid != -1); msgsnd(msgid, &data, strlen(data.mdata),0); exit(0); }

     

    Processed: 0.015, SQL: 9