【问题标题】:multiprocess communications using message queue使用消息队列的多进程通信
【发布时间】:2013-11-01 03:02:56
【问题描述】:

我正在尝试实现类似于此示例的程序:

程序在4个进程之间传递一个整数,每个进程递减整数

每个进程都有自己的邮箱

每个进程都会检查其邮箱中的变量“计数器”,如果找到,它将递减它

然后它将计数器变量发送到下一个进程

但是程序中有一个错误,我找不到它。 请注意,这是一项作业,我只是在寻找可以帮助我找到错误的提示。

typedef struct {
    int counter;
    char data[256];
    int id; //id of the process that previously decremented the counter
} msg;



int main(int arqc, char *argv[]){
    int key=9;
    int id=0;
    pid_t  pid;
    int num=5;
    int    i, k;
    int arr[5];


    //create 5 forks
    if (arqc !=  2){
        num=5;
    }else{
        int ret = sscanf(argv[1], "%d", &num);
        if (ret != 1)return 0;
    }
    for(i=0 ; i<num ; i++){
        if ((pid = fork()) == -1) {
            fprintf(stderr, "can't fork, error %d\n", errno);
            exit(EXIT_FAILURE);
        }
        if (pid == 0) {
            id=i;
        }
        else {
            break;
        }
    }



    //process 1 to n comes here
    msg m;
    int boxid = msgget(id, 0600 | IPC_CREAT);
    arr[id]=boxid;
    int firstRun=1;

    //initiate the first move
    if((id==0)&&(firstRun==1)){
        m.counter = INIT_COUNTER;

        //send msg to next process
        msgsnd(arr[id], &m, sizeof(msg), 0); //send msg to own inbox
        firstRun=0;
    }



    while(1){
        //check inbox of current process
        int rec = msgrcv(arr[id], &m, sizeof(msg), 0, 0);

        printf("Im %d, counter is %d, rec is %d\n",id, m.counter, rec);


        int index;
        if(id==num){
            index=0;
        }else{
            index=id+1;
        }

        //send message to the next inbox
        int sent = msgsnd(arr[index], &m, sizeof(m), 0);

        printf( "Error opening file: %s\n", strerror( errno ) );

        sleep(1);
    }

}

【问题讨论】:

  • “有一个错误”是一个模糊的陈述。正如亚历山大所说,你必须提供更多关于你试图解决问题的细节。至少,您应该考虑一下您认为可能出错的地方。

标签: c linux fork message-queue


【解决方案1】:

首先,期望 SO 人群只为你解决(家庭作业?)问题而你不付出任何努力是不合理的。目前还不清楚什么问题出在程序当前的行为方式以及调试它的步骤。

抛开胡言乱语,我建议删除所有步骤,只留下两个参与者,并让它在这个简单的配置中工作。一旦它工作,添加另一个,确保它仍然工作等等。

【讨论】:

    【解决方案2】:

    您最初的 msgsnd 因参数无效而失败,一切都从那里得到解决。

    SysV 消息队列需要消息类型字段作为消息中的第一个字段,因此您需要执行类似的操作。

    typedef struct
    {
        long int  mtype;
        int counter;
        char data[256];
        int id; //id of the process that previously decremented the counter
    } msg;
    

    您还必须在发送之前将消息设置为某些内容并设置正确的长度。

    //initiate the first move
    if ((id == 0) && (firstRun == 1))
    {
        m.mtype = 100;
        m.counter = INIT_COUNTER;
        strncpy(m.data, "some kind of message is nice", sizeof(m.data));
        m.id = id;
    
        size_t msgsize = sizeof(msg) - sizeof(long int);
    
        //send msg to next process
        int sent = msgsnd(arr[id], &m, msgsize, 0); //send msg to own inbox
    
        if (sent == -1)
        {
            perror("msgsend");
            exit(1);
        }
    
        firstRun = 0;
    }
    

    您会遇到超出此范围的问题(例如,在 msgrcvs 上设置正确的大小),但这应该可以帮助您克服最初的困难。

    【讨论】:

      猜你喜欢
      • 2014-01-17
      • 2020-06-11
      • 2011-08-27
      • 2018-01-19
      • 2011-04-02
      • 1970-01-01
      • 2012-08-05
      • 2014-08-12
      • 2012-12-08
      相关资源
      最近更新 更多