无名管道通信

无名管道pipe:

无名管道有读端和写端,并且读端只能读,写端只能写

       #include <unistd.h>

函数原型:

       int pipe(int pipefd[2]);

参数:

       pipefd[0]: 读

       pipefd[1]: 写

返回值:

       成功:0

       失败:-1

无名管道的特点:

a.没有名字,无法使用open()打开,只有文件描述符数组,不能使用lseek文件定位

b.只能用于亲缘进程之间(父子,兄弟,祖孙)通信(由父进程创建)

c.半双工工作方式,读写端是分开的,pipefd[0]为读端,pipefd[1]为写端,同一时刻,只能由一端写,另一端读

d.是一种特殊的文件,只存在于内存中,由内核进行管理,随进程生,随进程死

e.对于它的读写可以使用文件IO如read,write函数

f.没有办法保证写入数据的原子性(如果管道破裂,则数据丢失),管道缓冲区一有空闲区域,写进程就会试图向管道写入数据,如果读进程不读走管道缓冲区的数据,那么写操作将一直阻塞,

原子性:每一段数据都是独立的,不会被拆分,管道先进先出、顺序是有保证的,管道中的数据长度不是由实际的字符串长度决定,而是由写入的参数决定

g.无名管道的操作属于一次性操作,如果对无名管道进行读写操作,数据会被全部读走

单工:固定一种方向进行通信,广播(只能由A设备向B设备发送消息,不能由B向A发送)

半双工:方向不定,但是同一时间只能由一端发送到另一端,对讲机,(同一时间,只能由A设备向B设备发送消息,或者由B设备向A设备发送消息,否则就是自问自答)

全双工:通信方向都可以,同时可以发送也可以接收,电话

#include <stdio.h>
#include <unistd.h>
#include <string.h>
#include <sys/wait.h>
#include <stdlib.h>

int main(int argc, char const *argv[])
{
	// 定义无名管道的文件描述符
	int fd1[2];
	char rbuf[50], wbuf[50];
	// 创建无名管道
	int ret1 = pipe(fd1);
	//创建失败
	if(ret1==-1)
	{
		perror("pipe error\n");
		return -1;
	}
	// 创建子进程进行通信
	pid_t son = fork();
	if(son == 0) // 子进程
	{
		while(1)
		{
			//清空读端 写端
			bzero(wbuf, sizeof(wbuf));
			bzero(rbuf, sizeof(rbuf));
			// 事情1:子进程给父进程发送数据
			printf("请输入给父进程发送的数据:\n");
			scanf("%s", wbuf);
			//将数据写入无名管道
			write(fd1[1], wbuf, sizeof(wbuf));

			// 退出
			if(!strcmp(wbuf, "quit"))
				break;

			// 事情2:
			read(fd1[0], rbuf, sizeof(rbuf));
			printf("子进程接收到的数据:%s\n", rbuf);
			// 退出
			if(!strcmp(rbuf, "quit"))
				break;
			
		}
		// 退出子进程
		exit(0);
	}
	else if(son > 0) // 父进程
	{
		while(1)
		{
			bzero(wbuf, sizeof(wbuf));
			bzero(rbuf, sizeof(rbuf));
			// 事情1:父进程接收子进程发送的数据
			read(fd1[0], rbuf, sizeof(rbuf));
			printf("父进程接收到的数据:%s\n", rbuf);

			// 退出
			if(!strcmp(rbuf, "quit"))
				break;

			// 事情2:
			printf("请输入要给子进程发送的数据:\n");
			scanf("%s", wbuf);
			write(fd1[1], wbuf, sizeof(wbuf));
			// 退出
			if(!strcmp(wbuf, "quit"))
				break;
		}
	}
	// 等待子进程
	wait(NULL);
	// 关闭文件描述符
	close(fd1[0]);
	close(fd1[1]);
	
	
	return 0;
}

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值