管道
unix系统PIC的古老形式,int pipe(int fd[2]) , 完成进程间通信。
fd[1] 写 fd[0]读
代码
// unix 环境高级攻防
#include "apue.h"
#include <sys/wait.h>
#define DEF_PAGER "/bin/more"
int main(int argc ,char * argv[]){
int n;
int fd[2];
pid_t pid;
char * pager , *argv0;
char line[MAXLINE];
FILE * fp;
if((fp= fopen(argv[1] , "r"))==NULL){
printf("can't open %s ",argv[1]);
exit(1);
}
if(pipe(fd) < 0){
printf("pipe error");
exit(1);
}
if((pid = fork()) < 0){
printf("fork error");
exit(1);
}
else if(pid > 0){
close(fd[0]);//关闭读端
//从文件中读取数据,写入写端
while( fgets(line , MAXLINE , fp)!= NULL ){
n = strlen(line);
if(write(fd[1] , line , n)!= n ){
err_sys("write error");
}
}
if (ferror(fp))
err_sys("fget error");
close(fd[1]);
if(waitpid(pid, NULL , 0) < 0)
err_sys("waitpid error");
exit(0);
}
else {
close(fd[1]); 关闭写端
if (fd[0] != STDIN_FILENO){
if(dup2(fd[0],STDIN_FILENO )!= STDIN_FILENO)
err_sys("dup2 error");
} 将读端重定位到标准输入
if((pager = getenv("PAGER")) == NULL)
pager = DEF_PAGER;
if((argv0 = strrchr(pager , '/'))!=NULL)
argv0++;
//使用pager 分页标准输入的数据
if(execl(pager , argv0 , (char * )0 ) < 0)
err_sys("execl error ");
}
exit(0);
}
popen函数
###popen() 函数
#include "apue.h"
#include <sys/wait.h>
#define PAGER "${PAGER:-more}"
int main(int argc , char * argv[]){
char line[MAXLINE];
FILE * fpin , * fpout;
if(argc !=2 )
err_quit("usage:");
if((fpin = fopen(argv[1] , "r"))== NULL)
err_sys("can't open %s ",argv[1]);
if((fpout = popen(PAGER , "w"))==NULL)
err_sys("popen error");
while(fgets(line,MAXLINE ,fpin)!=NULL)
{
if(fputs(line , fpout)==EOF)
err_sys("error");
}
if(ferror(fpin))
err_sys("gets error");
if(pclose(fpout)==-1)
err_sys("pclose error");
return 0;
}
同理可得,该函数fpin 函数打开文件,写入fpout ,fpout将内容输入到PAGER,然后打印。