消息队列基础

来源:互联网 发布:党卫军和国防军 知乎 编辑:程序博客网 时间:2024/06/05 03:48
###消息队列基础
    ##消息队列
        比喻:回转寿司、按优先级进行(让列宁同志先走)
        本质:内核链表
    
    ##POSIX消息队列
        接口
            头文件:mqueue.h
            库: rt librt.so    real time
            结构体: struct mq_attr
                消息队列属性
                        mq_flags【标志】:
                            在mq_open时被初始化;在mq_setattr设置;其值为0或者O_NONBLOCK;
                mq_maxmsg【队列的消息个数最大值】:
                    只能在mq_open时被初始化
                mq_msgsize【队列每个消息的最大值】:
                    只能在mq_open时被初始化
                mq_curmsgs【当前队列消息长度】:
                    在mq_getattr获取
        函数【八大操作】
            创建消息队列:mqd_t mq_open(const char *name,int oflag,mode_t mode,struct mq_attr* attr);
                name:posix IPC名字
                oflag:标志:O_CREAT【没有该对象则创建】、O_EXCL【如果O_CREAT指定,但name不存在,就返回错误】、O_NONBLOCK【以非阻塞方式打开消息队列】、O_RDONLY【只读】、O_RDWR【读写】、O_WRONLY【只写】
                mode:权限:S_IWUSR【用户/属主写】、S_IRUSR【用户/属主读】、S_IWGRP【组成员写】、S_IRGRP【组成员读】、S_IWOTH【其他用户写】、S_IROTH【其他用户读】
                attr:队列属性:【阻塞】attr.mq_flag =  0;【非阻塞】attr.mq_flag = NONBLOCK
                返回值:-1【出错】、其他【消息队列描述符】
            删除消息队列:int mq_unlink(const char* name);
                name:posix IPC名字
                返回值:-1【出错】、0【成功】
            打开消息队列:mqd_t mq_open(const char* name,int oflag);
                name:posix IPC名字
                oflag:标志:【只读】O_RDONLY、【读写】O_RDWR、【只写】O_WRONLY
                返回值:-1【出错】、其他【描述符】
            关闭消息队列:int mq_close(mqd_t mqdes,struct mq_attr,*newattr,struct mq_attr *oldattr);
                mqdes:消息队列描述符
                newattr:新属性;只设置mq_flags{0;NONBLOCK}
                oldattr:旧属性
                返回值:-1【出错】、0【成功】
            获取消息队列属性:int mq_getattr(mqd_t mqdes,struct mq_attr *attr);
                mqdes:消息队列描述符
                attr:属性
                返回值:-1【出错】、0【成功】
            发送消息:int mq_send(mqd_t mqdes,const char *msg_ptr,size_t msg_len,unsigned msg_prio);
                msg_ptr:消息的指针
                msg_len:消息长度【不能大于属性值mq_msgsize的值】
                msg_prio:优先级【消息在队列中将按照优先级大小顺序来排列消息】
**消息队列已满,mq_send()函数将阻塞,直到有可用空间再次允许放置消息;如果O_NONBLOCK被指定,mq_send()那么将不会阻塞,而是返回EAGAIN错误
            接收消息:ssize_t mq_receive(mqd_t mqdes,char* msg_ptr,size_t msg_len,unsigned *msg_prio);
                msg_ptr:消息的指针
                msg_len:消息长度【不能大于属性值mq_msgsize的值】
                msg_prio:优先级【消息在队列中将按照优先级大小顺序来排列消息】
                返回值:-1【出错】、正数【接收到的消息长度】
**如果队列空,mq_recieve()函数将阻塞,直到消息队列中有新的消息;如果O_NONBLOCK被指定,mq_receive()那么将不会阻塞,而是返回EAGAIN错误
        查看
            man mq_overview
            ls /dev/mqueue
            cat /dev/mqueue/PIC名字
    ##System V消息队列
        接口
            头文件:sys/msg.h
            结构体:自定义消息缓冲区结构msgbuf
                mtype【消息类型】:必须是long;必须是结构体第一个变量
                mtext【消息数据】:可以随意定义
            函数
                消息获取:int msgget(key_t key,int msgflg)
                    key:IPC键
                        key_t ftok(char* path,int id)
                            path:地址
                            id:IP
                        IPC_PRIVATE:通常用于亲缘进程
                    msgflg
                        IPC_CREAT【创建】
                        IPC_CREAT|IPC_EXCL
                        权限:可使用八进制数字
                            MSG_R【用户读】:0400
                            MSG_W【用户写】:0200
                            MSG_R>>3【组读】:0040
                            MSG_W>>3【组写】:0020
                            MSG_R>>6【其他读】:0004
                            MSG_W>>6【其他写】:0002
                    返回值:非负整数【消息队列标识】、-1【失败】
                消息发送:int msgsnd(int msgid,const void* msgptr,size_t msgsz,int msgflg)
                    msgid:消息队列标识
                    msgptr:消息结构体
                        一个长整型成员变量开始的结构体,消息结构体模板:
                            struct test_message{
                                long mtype;/*must>0*/
                                char mtext;/*data*/
                            };
                    msgsz【消息长度】:不包括长整型变量
                    msgflg【控制函数行为】:0【忽略】、IPC_NOWAIT【如果消息队列为空,则返回一个ENOMSG,并将控制权交回调用函数的进程】、MSG_NOERROR【如果函数取得的消息长度大于msgsz,将只返回msgsz长度的信息,剩下的部分被丢弃了】、MSG_EXCEPT【当msgtype>0时接收类型不等于msgtype的第一条消息】
                    返回值:0【成功】、-1【失败】
                消息接受:int msgrcv(int msgid,void *msgptr,size_t msgsz,long int msgtype,int msgflg)
                    msggid【消息队列标识】
                    msgptr【消息结构体】:以一个长整型成员变量开始的结构体
                        struct test_message{
                            long int message_type;
                            /*The data you wish to transfer*/
                        }
                    msgsz【消息长度】:不包括长整型变量
                    msgtype【接收类型】:0【获取队列中的第一个消息】、大于0【获取具有相同消息类型的第一个信息】、小于0【获取类型等于或小于msgtype的绝对值中最小的一个消息】
                    msgflg【控制函数行为】:0【忽略】、IPC_NOWAIT【如果消息队列为空,则返回一个ENOMSG,并将控制权交回调用函数的进程】、MSG_NOERROR【如果函数取得的消息长度大于msgsz,将只返回msgsz长度的信息,剩下的部分被丢弃了】、MSG_EXCEPT【当msgtype>0时接收类型不等于msgtype的第一条消息】
                    返回值:非负整数【接受到的消息长度】、-1【失败】
                消息控制:int msggctl(int msgqid,int cmd,struct msqid_ds *buf)
                    msqid【消息队列标识符】
                    cmd:IPC_STAT【获取当前消息队列控制信息】、IPC_SET【设置当前消息队列控制信息】、IPC_RMID【删除消息队列】
                    buf【消息队列模式结构】:msg_perm.mode【消息队列读写模式】、msg_qbytes【队列最大大小】、msg_cbytes【当前队列大小】、msg_qnum【当前队列消息数】
                    返回值:0【成功】、-1【失败】
*实例:删除消息        msgctl(msgqid,IPC_RM,NULL)
            查看:ipcs


                    
           

原创粉丝点击