思维导图
1> 使用消息队列完成两个进程之间相互通信
01.进程A
#include <my_head.h>
//定义消息结构体类型
struct msgbuf
{
long mtype;//消息类型
char mtext[1024];//消息正文
};
#define SIZE (sizeof(struct msgbuf)-sizeof(long))
int main(int argc, const char *argv[])
{
//1.创建key
key_t key=ftok("/",'t');
printf("key=%#x\n",key);
//2.创建消息队列
int msqid=msgget(key,IPC_CREAT|0664);
printf("msqid=%d\n",msqid);
//定义一个消息类型的容器
struct msgbuf buf;
//创建子线程
pid_t pid=fork();
if(pid>0)
{
//父进程发送
//3.向消息队列中写入数据
while(1)
{
printf("请输入消息类型:");
scanf("%ld",&buf.mtype);
printf("请输入要存放的数据:");
scanf("%s",buf.mtext);
getchar();
//将消息存放到消息队列里
msgsnd(msqid,&buf,SIZE,0);
printf("输入成功\n");
if(strcmp(buf.mtext,"quit")==0)
{
break;
}
}
waitpid(pid,NULL,0);
}else if(pid==0)//子进程接收
{
while(1)
{
msgrcv(msqid,&buf,SIZE,0,0);
printf("收到消息:%s\n",buf.mtext);
if(strcmp(buf.mtext,"quit")==0)
{
break;
}
}
exit(EXIT_SUCCESS);
}else
{
perror("fork error");
return -1;
}
return 0;
}
02.线程B
#include <my_head.h>
//定义消息结构体类型
struct msgbuf
{
long mtype;//消息类型
char mtext[1024];//消息正文
};
#define SIZE (sizeof(struct msgbuf)-sizeof(long))
int main(int argc, const char *argv[])
{
//1.创建key
key_t key=ftok("/",'t');
printf("key=%#x\n",key);
//2.创建消息队列
int msqid=msgget(key,IPC_CREAT|0664);
printf("msqid=%d\n",msqid);
//定义一个消息类型的容器
struct msgbuf buf;
//创建子线程
pid_t pid=fork();
if(pid==0)
{
//子进程发送
//3.向消息队列中写入数据
while(1)
{
printf("请输入消息类型:");
scanf("%ld",&buf.mtype);
printf("请输入要存放的数据:");
scanf("%s",buf.mtext);
getchar();
//将消息存放到消息队列里
msgsnd(msqid,&buf,SIZE,0);
printf("输入成功\n");
if(strcmp(buf.mtext,"quit")==0)
{
break;
}
}
exit(EXIT_SUCCESS);
}else if(pid>00)//父进程接收
{
while(1)
{
msgrcv(msqid,&buf,SIZE,0,0);
printf("收到消息:%s\n",buf.mtext);
if(strcmp(buf.mtext,"quit")==0)
{
break;
}
}
waitpid(pid,NULL,0);
}else
{
perror("fork error");
return -1;
}
//4.删除队列消息
if(msgctl(msqid,IPC_RMID,NULL)==-1)
{
perror("msgctl error");
return -1;
}
return 0;
}
2> 将信号通信相关代码重新实现一遍
01.发送端
#include <my_head.h>
//定义消息结构体类型
struct msgbuf
{
long mtype;//消息类型
char mtext[1024];//消息正文
};
#define SIZE (sizeof(struct msgbuf)-sizeof(long))
int main(int argc, const char *argv[])
{
//1.创建key
key_t key=ftok("/",'t');
printf("key=%#x\n",key);
//2.创建消息队列
int msqid=msgget(key,IPC_CREAT|0664);
printf("msqid=%d\n",msqid);
//定义一个消息类型的容器
struct msgbuf buf;
//3.向消息队列中写入数据
while(1)
{
printf("请输入消息类型:");
scanf("%ld",&buf.mtype);
printf("请输入要存放的数据:");
scanf("%s",buf.mtext);
getchar();
//将消息存放到消息队列里
msgsnd(msqid,&buf,SIZE,0);
printf("输入成功\n");
if(strcmp(buf.mtext,"quit")==0)
{
break;
}
}
return 0;
}
02.接收端
#include <my_head.h>
//定义消息结构体类型
struct msgbuf
{
long mtype;//消息类型
char mtext[1024];//消息正文
};
#define SIZE (sizeof(struct msgbuf)-sizeof(long))
int main(int argc, const char *argv[])
{
//1.创建key
key_t key=ftok("/",'t');
printf("key=%#x\n",key);
//2.创建消息队列
int msqid=msgget(key,IPC_CREAT|0664);
printf("msqid=%d\n",msqid);
//定义一个消息类型的容器
struct msgbuf buf;
//3.向消息队列中读取数据
while(1)
{
//读取数据
msgrcv(msqid,&buf,SIZE,0,0);
//第一个0表示无视类型,第二个0表示阻塞形式接收消息
printf("收到消息为:%s\n",buf.mtext);
if(strcmp(buf.mtext,"quit")==0)
{
break;
}
}
//4.删除消息队列
if(msgctl(msqid,IPC_RMID,NULL)==-1)
{
perror("msgctl error");
return -1;
}
return 0;
}
3> 将共享内存相关代码重新实现一遍
01.发送端
#include <my_head.h>
#define PAGE_SIZE 4096
int main(int argc, const char *argv[])
{
//1.创建key
key_t key=-1;
if((key=ftok("/",'k'))==-1)
{
perror("ftok error");
return -1;
}
printf("key=%#x\n",key);
//2.将物理内存创建出共享内存段
int shmid=0;
if((shmid=shmget(key,PAGE_SIZE,IPC_CREAT|0664))==-1)
{
perror("shmget error");
return -1;
}
printf("shmid=%d\n",shmid);
//3.将共享内存段映射到用户空间
char *addr=(char *)shmat(shmid,NULL,0);//第一个null表示让系统自动选择页的分段,0表示当前进程对共享内存具有读写的权限
if(addr==(void *)-1)
{
perror("shmat error");
return -1;
}
printf("addr=%p\n",addr);
//4.操作共享内存
while(1)
{
fgets(addr,PAGE_SIZE,stdin);
addr[strlen(addr)-1]='\0';
if(strcmp(addr,"quit")==0)
break;
}
//5.取消映射
if(shmdt(addr)==-1)
{
perror("shmat error");
return -1;
}
//6.删除共享内存
if((shmctl(shmid,IPC_RMID,NULL))==-1)
{
perror("shmctl error");
return -1;
}
return 0;
}
02.接收端
#include <my_head.h>
#define PAGE_SIZE 4096
int main(int argc, const char *argv[])
{
//1.创建key
key_t key=-1;
if((key=ftok("/",'k'))==-1)
{
perror("ftok error");
return -1;
}
printf("key=%#x\n",key);
//2.将物理内存创建出共享内存段
int shmid=0;
if((shmid=shmget(key,PAGE_SIZE,IPC_CREAT|0664))==-1)
{
perror("shmget error");
return -1;
}
printf("shmid=%d\n",shmid);
//3.将共享内存段映射到用户空间
char *addr=(char *)shmat(shmid,NULL,0);//第一个null表示让系统自动选择页的分段,0表示当前进程对共享内存具有读写的权限
if(addr==(void *)-1)
{
perror("shmat error");
return -1;
}
printf("addr=%p\n",addr);
//4.操作共享内存
while(1)
{
printf("共享内存段中的数据为:%s\n",addr);
if(strcmp(addr,"quit")==0)
break;
}
//5.取消映射
if(shmdt(addr)==-1)
{
perror("shmat error");
return -1;
}
//6.删除共享内存
if((shmctl(shmid,IPC_RMID,NULL))==-1)
{
perror("shmctl error");
return -1;
}
return 0;
}