LINUX 进程通信研究
Linux实现进程间通信的方法有PIPE,FIFO管道,消息队列,信号量,内存共享等几中方法。在LINUX进程通信中,PIPE因为简单,并且是半双工的通信,用的较多。FIFO可以在PIPE上发展而来,并实现了双向的通信机制,可以用于不同的祖先进程之间的通信。
消息队列是基于一个共享实现多进程的通信需要,并且可以传输大量的数据,每个进程都可以到共享队列中获取数据。
基于LINUX IPC MESSAGE QUEUE 的研究实现了一个多进程通信的程序。程序执行环境在REDHAT LINUX 9.0, gcc-2.95.
程序分两部分,一部分是一个后台程序bgt,它负责对其他进程的应答工作,另一部分是一个询问程序ogt。询问内容较简单,但实现了MESSAGE QUEUE IPC的完全框架,对以后的开发有较有意义的积累。
Back Ground Task 实现,我叫它bgt
Bgt.c
#include <stdio.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/fcntl.h>
#include <sys/ipc.h>
#include <sys/msg.h>
#include <unistd.h>
#include <signal.h>
#include "comm.h"
static int msg_que_id = -1;
void catch_sig_term(int signo)
{
int rev;
rev = msgctl(msg_que_id, IPC_RMID, 0);
if(rev<0){
printf("Remove the queue fail./n");
exit(-1);
}
printf("Remove the queue ok/n");
exit(0);
}
int main()
{
struct my_msg rece_msg, send_msg;
int rece_len, send_len, result;
struct sigaction action;
int num;
msg_que_id = msgget(MY_IPC_KEY, IPC_CREAT|0666);
if(msg_que_id<0){
printf("Create ipc queue fail");
exit(-1);
}
action.sa_handler = catch_sig_term;
sigemptyset(&action.sa_mask);
action.sa_flags = 0;
sigaction(SIGTERM, &action, NULL);
action.sa_handler = SIG_IGN;
sigemptyset(&action.sa_mask);
action.sa_flags = 0;
sigaction(SIGINT, &action, NULL);
sigaction(SIGQUIT, &action, NULL);
sigaction(SIGHUP, &action, NULL);
while(1){
rece_len = msgrcv(msg_que_id, &rece_msg, (sizeof(struct my_msg)- sizeof(long)), MYINPUT, 0);
if(rece_len<0){
printf("bgt receive message error/n");
raise(SIGTERM);
}
send_msg.m_type = rece_msg.process_id;
num = rece_msg.m_buf[0];
switch(num){
case 1:
send_msg.m_buf[0] = 1;
break;
case 2:
send_msg.m_buf[0] = 2;
break;
case 3:
send_msg.m_buf[0] = 3;
break;
default:
;
}
send_len = sizeof(int) + sizeof(int);
result = msgsnd(msg_que_id, &send_msg, send_len, 0);
if(result<0){
printf("bgt send message fail./n");
raise(SIGTERM);
}
}
return 0;
}
这个程序是询问程序, 可以同时运行多个程序进行询问,后台程序BGT,会发相应的回音。
Ogt.c
#include <stdio.h>
#include <sys/types.h>
#include <sys/ipc.h>
#include <sys/msg.h>
#include <signal.h>
#include <unistd.h>
#include "comm.h"
static int msg_que_id = -1;
int main(int argc, char *argv[])
{
int result, send_len, rece_len;
struct my_msg send_msg, rece_msg;
int question_num;
msg_que_id = msgget(MY_IPC_KEY, 0);
if(msg_que_id<0){
printf("Message queue use error./n");
exit(-1);
}
while(1){
printf("/n/n----------------------------- LinDa Documnet ------------------------------/n/n");
printf(" You now enter LinDa Document, you must be valid./n Any contract LinDa./n Thanks./n/n");
printf("You can ask 3 questions:/n");
printf(" 1. How many firends LinDa have?/n");
printf(" 2. How much money LinDa spend one day?/n");
printf(" 3. what is LinDa like?/n/n");
printf("Please select question number 1, 2 or 3./n");
scanf("%d", &question_num);
send_msg.m_type = MYINPUT;
send_msg.process_id = getpid();
send_msg.m_buf[0] = question_num;
send_len = sizeof(int) + sizeof(int);
result = msgsnd(msg_que_id, &send_msg, send_len, 0);
if(result<0){
printf("ogt send message fail./n");
exit(-1);
}
rece_len = msgrcv(msg_que_id, &rece_msg, (sizeof(struct my_msg) - sizeof(long)), getpid(), 0);
if(rece_len<0){
printf("ogt receive message fail./n");
exit(-1);
}
switch(rece_msg.m_buf[0]){
case 1:
printf("LinDa have a lot of firends./n");
exit(0);
case 2:
printf("LinDa spend about 10 RMB./n");
exit(0);
case 3:
printf("LinDa like life./n");
exit(0);
default:
;
}
}
return 0;
}
执行程序很简单,进入到程序
make
./bgt &
./ogt
可能出现三种情况,如下:
第一种情况:
----------------------------- LinDa Documnet ------------------------------
You now enter LinDa Document, you must be valid.
Any contract LinDa.
Thanks.
You can ask 3 questions:
1. How many firends LinDa have?
2. How much money LinDa spend one day?
3. what is LinDa like?
Please select question number 1, 2 or 3.
1
LinDa have a lot of firends.
第二中情况:
[root@localhost linda]# ./ogt
----------------------------- LinDa Documnet ------------------------------
You now enter LinDa Document, you must be valid.
Any contract LinDa.
Thanks.
You can ask 3 questions:
1. How many firends LinDa have?
2. How much money LinDa spend one day?
3. what is LinDa like?
Please select question number 1, 2 or 3.
2
LinDa spend about 10 RMB.
第三种情况:
[root@localhost linda]# ./ogt
----------------------------- LinDa Documnet ------------------------------
You now enter LinDa Document, you must be valid.
Any contract LinDa.
Thanks.
You can ask 3 questions:
1. How many firends LinDa have?
2. How much money LinDa spend one day?
3. what is LinDa like?
Please select question number 1, 2 or 3.
3
LinDa like life.
Linda
2004.2