APUE学习笔记7——进程间通信
1 管道
管道一般是一种半双工的进程间通信方式,只能够在具有公共祖先的进程之间使用,比如一个管道由一个进程创建,然后该进程调用fork,之后父、子进程就可以使用该管道。
管道是调用pipe函数创建的。
#include <unistd.h> int pipe(int filedes[]);
/*返回值:成功返回0,出错则返回-1*/
/*经由参数filedes返回两个文件描述符,filedes[0]为读方式打开,filedes[1]则为写方式打开*/
/*进程数据从filedes[1]输出到管道,再从filedes[0]输入到进程*/
调用fork之后做什么取决于想要数据流的方向。对于从父进程到子进程的管道,父进程关闭fd[0],子进程关闭fd[1]。相反的,对于从子进程到父进程的管道,父进程关闭fd[1],子进程关闭fd[0]。

当管道的一端被关闭后,下列两条规则起作用:
- 当读一个写端已经被关闭的管道时,在所有数据被读取之后,read返回0,以指示达到了文件结束处。
- 当写一个读端已经被关闭的管道时,则产生信号SIGPIPE。如果忽略该信号或者捕捉该信号并从其处理函数返回,则write返回-1,errno被置为EPIPE。
常量PIPE_BUF规定了内核中管道缓冲区的大小。
一个简单的进程通讯程序:
#include <unistd.h>
#include <stdlib.h>
#include <stdio.h>
#define MAX 16
int main(void){ int fd[];
pid_t pid;
char line[MAX]; if(pipe(fd) < ){ //初始化管道
printf("pipe error");
exit();
} if(pid = fork() < ){
printf("fork error");
exit();
}else if(pid != ) { //父进程
close(fd[]);
write(fd[], "hello!", );
}else{ //子进程
close(fd[]);
read(fd[], line, MAX);
printf(line);
} exit();
}
2 popen和pclose函数
标准I/O库提供了两个管道函数popen和pclose。这两个函数实现的操作是:创建一个管道,调用fork产生一个子进程,关闭管道的不使用端,exec执行一个shell以运行命令,然后等待命令终止。
#inlcude <stdio.h> FILE *popen(const char *cmdstring, const char *type);
/*返回值:成功返回文件指针,出错返回NULL*/ int pclose(FILE *fp);
/*返回值:cmdstring执行后的终止状态,出错返回-1*/
如果type是“r”,则popen返回的文件指针指向cmdstring的标准输出。如果type是“w”,则popen返回的文件指针指向cmdstring的标准输入。
cmdstring由系统shell按下列方式执行:
#sh -c cmdstring
3 FIFO
FIFO有时被称为命名管道。普通管道只能由相关进程使用,这些相关进程的共同祖先进程创建了这个管道。但是通过FIFO,不相关的进程也能交换数据。
创建FIFO类似于创建文件,实际上FIFO的路径名存在文件系统中。
#include <sys/stat.h> int mkfifo(const char *pathname, mode_t mode);
/*返回值:成功返回0,出错返回-1*/
mkfifo函数中mode参数与open函数中的mode参数相同。创建了FIFO之后就可以用open函数打开它。一般的文件I/O函数(如close、read、write、unlink等)都可以用于FIFO。
打开FIFO时,非阻塞标志(O_NONBLOCK)产生下列影响:
- 默认情况(不指定O_NONBLOCK),一个进程以读的方式open FIFO会阻塞,一直到另一个进程以写的方式open该FIFO。类似的,一个进程以写的方式open FIFO会阻塞,一直到另一个进程以读的方式open该FIFO。
- 如果指定了O_NONBLOCK,则一个进程以读的方式open FIFO会立即返回。但是,如果没有其他进程以读的方式open FIFO,则一个进程以写的方式open FIFO将出错返回-1,并将errno置为ENXIO。
FIFO有下面两种用途:
- FIFO由shell命令使用以便将数据从一个管道线传送到另一条管道线,无需创建中间临时文件。
- FIFO用于客户进程-服务器进程之间传输数据。
4 消息队列、信号量和共享存储器
消息队列、信号量和共享存储器统称为XSI IPC。每个内核之中的IPC结构都用一个非负整数的标识符加以应用。与文件描述符不同,IPC标识符不是一个小的整数。当一个IPC结构被创建,以后又被删除时,与这种结构相关的标识符加1,直至到达最大值然后归零。
(未完待续)
APUE学习笔记7——进程间通信的更多相关文章
- APUE学习笔记——10.9 信号发送函数kill、 raise、alarm、pause
转载注明出处:Windeal学习笔记 kil和raise kill()用来向进程或进程组发送信号 raise()用来向自身进程发送信号. #include <signal.h> int k ...
- APUE学习笔记3_文件IO
APUE学习笔记3_文件IO Unix中的文件IO函数主要包括以下几个:open().read().write().lseek().close()等.这类I/O函数也被称为不带缓冲的I/O,标准I/O ...
- apue学习笔记(第十七章 高级进程间通信)
本章介绍一种高级IPC---UNIX域套接字机制,并说明它的应用方法 UNIX域套接字 UNIX域套接字用于在同一台计算机上运行的进程(无关进程)之间的(全双工)通信.相比于因特网套接字,UNIX域套 ...
- apue学习笔记(第十五章 进程间通信)
本章将说明进程之间相互通信的其它技术----进程间通信(IPC) 管道 管道只能在具有公共祖先的两个进程之间只用.通常,一个管道由一个进程创建,在进程调用fork后,这个管道就能在父进程和子进程之间使 ...
- apue学习笔记(第一章UNIX基础知识)
总所周知,UNIX环境高级编程是一本很经典的书,之前我粗略的看了一遍,感觉理解得不够深入. 听说写博客可以提高自己的水平,因此趁着这个机会我想把它重新看一遍,并把每一章的笔记写在博客里面. 我学习的时 ...
- APUE学习笔记-一些准备
从开始看APUE已经有快一个星期了,由于正好赶上这几天清明节放假,难得有了三天空闲假期可以不受打扰的学习APUE,现在已经看完前六章了,里面的大部分例程也都亲自编写,调试过了.但总觉得这样学过就忘,因 ...
- APUE学习笔记(2):lseek()练习与文件洞
对于lseek函数早在大一的C语言课上就有接触,但是几乎没有使用过,只记得是和文件偏移操作相关的 看了APUE上的示例,又使用od工具查看了内容,果然很神奇,很新鲜 figure3.2.c [c] # ...
- APUE学习笔记(1):APUE运行环境
APUE全称<Advanced Programming in the UNIX Environment>(UNIX环境高级编程) 书中例子大都使用作者自己写的头文件,所以需要解决一下,还好 ...
- apue学习笔记(第十六章 网络IPC:套接字)
本章将考察不同计算机(通过网络连接)上的进程相互通信的机制:网络进程间通信. 套接字描述符 正如使用文件描述符访问文件,应用程序用套接字描述符访问套接字. 许多处理文件描述符函数(如read和writ ...
随机推荐
- RxSwift學習教程之基礎篇
前言 我們在 iOS 開發過程中,幾乎無時無刻都要面對異步事件的處理.例如,按鍵點擊.數據保存..音頻後臺播放.交互動畫展示.這些事件並不具備特定時序性,甚至它們可能同時發生. 雖然 Apple 提供 ...
- 优动漫PAINT动画创作功能介绍
优动漫PAINT也就是我们常说的clip studio paint(CSP)的中文版本,它是一款功能强大的漫画.插画绘制软件,它搭载了绘制漫画和插画所需的所有功能,包括丰富的笔工具.超强的笔压感应和手 ...
- Co-prime HDU - 4135_容斥计数
Code: #include<cstdio> #include<cstring> #include<cmath> #include<iostream> ...
- 洛谷P1540 机器翻译 水题 模拟
注意一下细节,尤其是更新minv时不要更新错. Code: #include<vector> #include<iostream> #include<cstdio> ...
- 关闭浏览器 清除session
捕获关闭浏览器的事件 关于关闭IE清空session的总结 Session过期会清楚session 还可以手动清除session实现关闭浏览器时清除session的方法
- python面向对象的三大特性之一多态
多态 多态的特性是调用不同的子类将会产生不同的行为,而无需明确知道这个子类实际上是什么 说白了就是,不同的对象调用相同的方法,产生不同的行为 例如:s1是字符串类型,w1是列表,两个完全不同的对象,他 ...
- vue 动态添加路由 require.context()
之前的写法 'use strict' import Vue from 'vue' import MessageBroadcast from 'page/MessageBroadcast' import ...
- 训练1-W
有一个长度为n(n<=100)的数列,该数列定义为从2开始的递增有序偶数,现在要求你按照顺序每m个数求出一个平均值,如果最后不足m个,则以实际数量求平均值.编程输出该平均值序列. Input 输 ...
- nyoj254-编号统计
编号统计 时间限制:2000 ms | 内存限制:65535 KB 难度:2 描述 zyc最近比较无聊,于是他想去做一次无聊的统计一下.他把全校同学的地址都统计了一下(zyc都将地址转化成了编码) ...
- CentOS 7下搭建高可用集群
一 .安装集群软件 必须软件pcs,pacemaker,corosync,fence-agents-all,如果需要配置相关服务,也要安装对应的软件. 二.配置防火墙1.禁止防火墙和selinux# ...