【Linux】进程间通信(IPC)之匿名管道和命名管道以及测试用例

本文介绍了Linux中的进程间通信(IPC)机制,重点关注匿名管道和命名管道。详细阐述了匿名管道的创建、使用及其特点,并通过示例展示了如何进行数据传输。同时,讨论了命名管道的创建、打开方式及其克服匿名管道限制的能力。文章还包含了关于进程等待的宏的描述,以及实际的通信代码示例。
摘要由CSDN通过智能技术生成


匿名管道(pipe)


管道是一种最基本的IPC机制,由pipe函数创建。


头文件:#include <unistd.h>

函数声明:int pipe( int pipefd[2] )



描述::调用 pipe() 函数时在内核中开辟一块称为管道的缓冲区用于通信。然后通过参数pipefd传出给用户程序两个描述符。pipefd[0] 指向管道的读端,pipefd[1]指向管道的写端。  管道在用户程序看来就像一个打开的文件。通过系统调用read()和write(), 在管道中传输数据。 pipe调用成功返回0,失败则返回-1.


文章的最后面有一些关于进程等待的宏描述。



示意图:

(1):父进程创建管道


(2):父进程调用fork()函数创建出子进程


(3):父进程关闭读端【close( pipefd[0])】,子进程关闭写端【close( pipefd[1])】




1.父进程调用pipe开辟管道,取得两个指向管道的文件描述符。

2.当父进程调用fork 创建子进程时,子进程会把父进程的文件描述符也一同拷贝过去。

3.父进程关闭读端,子进程关闭写端就可以实现父进程向子进程发送数据。。父进程关闭写端,子进程关闭读端。可以实现子进程向父进程写。

4.也就是说数据只能向一个方向流动。需要双向通信时,要建立起两个管道。


正常通信代码:

/*************************************************************************
#	> File Name: mypipe.c
# Author: HuoZG
# Created Time: Sat 25 Feb 2017 08:10:36 PM PST
 ************************************************************************/

#include<stdio.h>
#include<unistd.h>  // pipe()  fork()
#include<string.h>  // strlen()

int main()
{

	int mypipe[2] = {0, 0};// [0] read [1]  write

	if(pipe(mypipe) < 0)
	{
		printf("pipe erroe!\n");
		return 1;
	}

	pid_t id = fork();

	if(id < 0)
	{
		printf("fork error!\n");
		return 2;
	}
	else if (id == 0)
	{ // child -> write 
		close(mypipe[0]);  // close read 

		const char * msg = "Hello World!";
		int count = 5;

		while(count--)
		{
			write(mypipe[1], msg, strlen(msg) + 1);
		}

	   	close(mypipe[1]);
	}
	else
	{ // father -> read
		close(mypipe[1]);   // close write
		int buf[128];
		int count = 5;
		while(count--)
		{
			ssize_t _s = read(mypipe[0], buf, sizeof(buf));
			if( _s > 0)
			{ // read sucess
				printf("%d: child -> father: %s \n", 5-count ,buf);
			}
			else
			{
				printf("pipe write is close\n");
				break;
			}
		}	

		close(mypipe[0]);
	}
	return 0;
}

打印结果:




1、如果所有指向管道写端的文件描述符都关闭了,而仍然有进程从管道的读端读取数据,那么管道中剩余的数据都被读取后,再次read会返回零。

将代码修改为如下:子进程提前关闭写端,而父进程while(1)一直在读

#include<stdio.h>
#include<unistd.h>  // pipe()  fork()
#include<string.h>  // strlen()

int main()
{

	int mypipe[2] = {0, 0};// [0] read [1]  write

	if(pipe(mypipe) < 0)
	{
		printf("pipe erroe!\n");
		return 1;
	}

	pid_t id = fork();

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值