2017-03-03 106 views
0

我想在两个进程之间发送消息。但我得到的时候我尝试发送带有msgsnd()msgsnd没有权限错误

创建消息队列

const char* MSG_QUEUE = "/tmp/msg_queue"; 

int file = open(MSG_QUEUE, O_CREAT | O_RDWR | O_APPEND, 0755); 
close(file); 
key_t key = ftok(MSG_QUEUE, 1); 
errno = 0; 
msg_queue = msgget(key, IPC_CREAT); 
if(msg_queue == -1) { 
    M_DEBUG("Error %s\r\n", strerror(errno)); 
} 

消息结构

struct feld_msg_s { 
    long id; 
    char mtext[5]; 
}; 

发送消息

一个 EACCES错误
struct feld_msg_s a_msg = {1, "Test"}; 
errno = 0; 
int ret = msgsnd(msg_queue, &a_msg, sizeof(a_msg.mtext), 0); 
if(ret == -1) { 
    if(errno == EACCES) { 
     printf("\r\n NO PERMISSION\r\n"); 
    } else { 
     printf("msgsnd ERROR!: %s\r\n", strerror(errno)); 
    } 
} 
中的msgsnd的联机帮助

写入

EACCES调用进程没有对消息队列中读取权限,并且不具备CAP_IPC_OWNER能力。

所以我添加了setcap命令

sudo setcap CAP_SETFCAP,CAP_IPC_OWNER+epi /home/mvollmer/build-APP-Desktop_Qt_5_6_1_GCC_64bit-Debug/APP 

我已经与getcap检查,如果应用程序有能力的以下功能。没关系。但我仍然收到没有权限错误。

使用root权限执行应用程序时,它的工作!

有一件事很奇怪,尽管msgget成功了ipcs不显示任何消息队列。

那么我的错在哪里?

我使用Linux Mint的

其它问题:是否可以使用其他数据类型,然后在MSG结构字符或消息限制为字符串?

+1

试试这个'msg_queue = msgget(key,IPC_CREAT | 0666)' – Arash

+0

与此我得到一个EACCES当'msgget'被调用。当我删除文件'/ tmp/msg_queue''msgget'和'msgsnd'成功时......谢谢!但为什么?! – mvollmer

+0

这很奇怪..现在每次都有效。删除文件并添加|后0666到msgget标志。 和消息队列现在用ipcs显示! 非常感谢你 – mvollmer

回答

0

您需要阅读手册页。每the POSIX msgget() standard

提要

#include <sys/msg.h> 

int msgget(key_t key, int msgflg); [Option End] 

说明

...

  • 的低位9位msg_perm.mode应设置为msgflg的低9位。

因此,该代码

msg_queue = msgget(key, IPC_CREAT); 

具有 “低阶msgflg的9位” 的所有设置为零。因此消息队列模式也全部为0 - 对任何人都没有权限。