php經過消息隊列IPC跟C語言進程簡單通訊

 

<?php
function ftok2($pathname, $proj_id) { 
        $st = @stat($pathname); 
        if (!$st) { 
                return -1; 
        } 
        $key = sprintf("%u", (($st['ino'] & 0xffff) | (($st['dev'] & 0xff) << 16) | (($proj_id & 0xff) << 24)));
        return $key; 
}

$key = ftok2("/root/unix/wangyi/src/ipc/bin", "23");

if(msg_queue_exists($key)){
        $queue = msg_get_queue($key);

        $ret = msg_receive($queue, 0, $type, 1024, $msg, false, MSG_IPC_NOWAIT);

        var_dump($ret);
        var_dump($msg);
}
/**
 *  經過消息隊列使php腳本進行掃尾工做而後退出
 *  通常經過發送信號便可,但因爲consumer腳本收到信號會莫名的退出(尚未定位到緣由)
 */
#include <stdio.h>
#include <stdlib.h>
#include <sys/msg.h>
#include <signal.h> 
#include <sys/types.h>
#include <unistd.h>

/* global variables */
int msg_id = 0;

typedef struct{
        int type;
        char mtext[128];
} MSG;

void sig_handler(int signo)
{
        exit(0);
}

__attribute__((constructor)) void _construct(void)
{
        signal(SIGINT, sig_handler);
}

__attribute__((destructor)) void _destruct(void)
{
        //rm msg queue
        if(msg_id != 0){
                msgctl(msg_id, IPC_RMID, NULL);
        }
        printf("__destructor\n");
}

int main(int argc, char **argv)
{
        if(argc != 3){
                fprintf(stderr, "usage: %s 進程數 consumer腳本路徑\n", argv[0]);
                exit(1);
        }
        int p_num = atoi(argv[1]);
        if(p_num <= 0 || p_num > 96){
                fprintf(stderr, "1 <= 進程數 <= 96\n");
                exit(1);
        }
        //create msg queue
        key_t key = ftok("/root/unix/wangyi/src/ipc/bin", 23);
        if((msg_id = msgget(key, IPC_CREAT | IPC_EXCL | 0644)) < 0){
                perror("msgger error");
                exit(2);
        }
        //send msg
        int n;
        MSG m = {1, "php script exit"};
        for(n = 0; n < p_num; n++){
                if(msgsnd(msg_id, &m, sizeof(MSG) - sizeof(long), IPC_NOWAIT) < 0){
                        perror("msgsnd error");
                        exit(3);
                }
        }
        //wait php receive
        struct msqid_ds ds;
        while(1){
                if(msgctl(msg_id, IPC_STAT, &ds) < 0){
                        perror("msgctl error");
                        exit(4);
                }
                if(ds.msg_qnum == 0){
                        printf("所有腳步已經退出\n");
                        break;
                }else{
                        printf("已經有%d個腳本退出...\n", (p_num - (int)ds.msg_qnum));
                        sleep(1);
                }
        }


        return 0;
}
相關文章
相關標籤/搜索