Linux_C bc/利用2根管道让2进程通讯

 1 /* tingbc.c
 2  * use two pipe to execute the bc.
 3  * one pipe: todc[2] , another: fromdc[2]
 4  * child thread to do dc, parent do UI
 5  */
 6
 7 #include <stdio.h>
 8 #include <unistd.h>
 9 #include <string.h>
10 #define oops(x, n) {perror(x); exit(n);}
11
12 void be_dc(int todc[], int fromdc[]);
13 void be_bc(int todc[], int fromdc[]);
14 int main(void) {
15   int todc[2], fromdc[2], pid;
16   if(pipe(todc)==-1 || pipe(fromdc)==-1)
17     oops("pipe", 2);
18   if((pid=fork()) == -1)
19     oops("fork" ,3);
20   if(pid==0) {
21     be_dc(todc, fromdc);//child do dc
22   }else{
23     be_bc(todc, fromdc);//parent do UI
24     wait(NULL);
25   }
26   return 0;
27 }
28
29 void be_dc(int todc[], int fromdc[]){
30   //will do dc() , change the stdin to todc[1], change the stdout to fromdc[0]
31   close(todc[1]);
32   close(fromdc[0]);
33   if(dup2(todc[0], 0)==-1)
34     oops("could not redirect the stdin", 4);
35   if(dup2(fromdc[1], 1)==-1)
36     oops("could not redirct the stdout", 5);
37   close(todc[0]);
38   close(fromdc[1]);
39   execlp("dc", "dc", "-",NULL);
40   oops("exe",1);
41 }
42
43 void be_bc(int todc[], int fromdc[]){
44   //will do bc(), change the stdout to todc[1], and use the fromdc[0] to read the dc‘s result
45   char cmdbuf[BUFSIZ];
46   int c1, c2;
47   char operator;
48   FILE *fout, *fread;
49   close(todc[0]);   //donot need to todc out
50   close(fromdc[1]);  //donot need to fromdc in
51
52   fout=fdopen(todc[1],"w");  //write the todc[1]
53   fread=fdopen(fromdc[0],"r" );     //read the dc‘s result from fromdc[0]
54
55   while((printf("tinybc: ")) && (fgets(cmdbuf, BUFSIZ, stdin )!=-1)) {
56     if( sscanf(cmdbuf, "%d %c %d", &c1,&operator,&c2) !=3) {
57       printf("syntax error.\n");
58       continue;
59     }
60     printf("2u cin is %d %c %d\n", c1,operator,c2);
61     if(fprintf(fout, "%d\n%d\n%c\np\n", c1,c2,operator) == EOF)//在这里有问题,c1总是读不进去,一直是0.
62       oops("fprintf", 6);
63
64     fflush(fout);
65     if(fgets(cmdbuf, BUFSIZ, fread)==NULL)
66       break;
67     printf("%d %c %d = %s", c1, operator, c2, cmdbuf);
68   }
69   close(todc[0]);
70   close(fromdc[1]);
71 }

这里,在2个pipe使用时,要分清楚pipe[0],pipe[1]哪一个是读出哪一个是写入。

同时这里用到了sscanf函数。

/**********************************************************************************************/

sscanf(格式化字符串输入)
相关函数 scanf,fscanf
表头文件 #include<stdio.h>
定义函数 int sscanf (const char *str,const char * format,........);
函数说明 sscanf()会将参数 str 的字符串根据参数 format 字符串来转换并格
式化数据。格式转换形式请参考 scanf()
。转换后的结果存于对应
的参数内。
返回值
成功则返回参数数目,失败则返回-1,错误原因存于 errno 中。
范例
#include<stdio.h>
main()
{
int i;
unsigned int j;
char input[ ]=”10 0x1b aaaaaaaa bbbbbbbb”;
char s[5];
sscanf(input,”%d %x %5[a-z] %*s %f”,&i,&j,s,s);
printf(“%d %d %s\n”,i,j,s);
}

/***************************************************************************************/

fdopen函数

fdopen函数与fopen类是,返回一个FILE*类型值,不同的是此函数以文件描述符而非文件作为参数。

使用fopen的时候,将文件名作为参数传给它。fopen可以打开设备文件也可以打开常规的磁盘文件。如只知道文件描述符而不清楚文件名的时候可以使用fdopen。

使用fdopen使得对远端的进程的处理就如同处理常规文件一样

时间: 2024-10-25 12:32:16

Linux_C bc/利用2根管道让2进程通讯的相关文章

邮槽 匿名管道 命名管道 剪贴板 进程通讯 转自http://www.cnblogs.com/kzloser/archive/2012/11/04/2753367.html#

邮槽 通信流程: 服务器 客户端 注意: 邮槽是基于广播通信体系设计出来的,它采用无连接的不可靠的数据传输 邮槽可以实现一对多的单向通信,我们可以利用这个特点编写一个网络会议通知系统,而且实现这一的系统所需要编写的代码非常少.如果读者是项目经理,就可以给你手下每一位员工的机器上安装上这个系统中的邮槽服务器端程序,在你自己的机器上安装油槽的客户端程序,这样,当你想通知员工开会,就可以通过自己安装的邮槽客户端程序.将开会这个消息发送出去,因为机器上都安装了邮槽服务器端的程序,所以他们都能同时收到你发

Python 3 利用 subprocess 实现管道( pipe )交互操作读/写通信

这里我们用Windows下的shell来举例: from subprocess import * #因为是举例,就全部导入了 为了方便你理解,我们用一个很简单的一段代码来说明: 可以看见我们利用Popen实例化了一个p,创建了子程序cmd.exe,然后我们给他的的Stdin(标准输入流)Stdout(标准输出流); 同时使用了subprocess.PIPE 作为参数,这个是一个特殊值,用于表明这些通道要开放.(在Python3.5,加入了run()方法来进行更好的操作) 然后我们继续 这些信息是

利用HttpApplicaton请求管道防止SQL注入

HttpApplication通过事件管道的方式处理请求,注意对请求的数据过滤filter和根据请求的类型交由相应的处理程序Handler处理. 管道注入由两种一种实现接口IHttpModule,另一种直接Global类中添加方法. SQL注入网站安全的威胁,关防止的方法:一种不允许敏感数据请求,一种将敏感数据重字符串中过滤.要求针对所有的用户请求,所有在BeginRequest事件中处理(也可以说是一种AOP编程). CODE SQL注入处理类 public class SQLInjectio

记录一次被bc利用跳转过程分析

挖公司的项目站,发现站点一访问就直接跳转到了赌博站,有点懵逼,简单分析下hc利用过程: 公司项目站:http://***.com 当我访问它: 通过http:***.com直接跳转到了306648.com 查看burpsuite中的流量: 发现多个http://***.com的页面加载了这段代码: 拷贝下来: var hs='<scr';hs=hs+'ipt src="/';hs=hs+'js';hs=hs+'/com';hs=hs+'.js"></sc';hs=hs

Python--线程队列(queue)、multiprocessing模块(进程对列Queue、管道(pipe)、进程池)、协程

队列(queue) 队列只在多线程里有意义,是一种线程安全的数据结构. get与put方法 ''' 创建一个"队列"对象 import queue q = queue.Queue(maxsize = 10) queue.Queue类即是一个队列的同步实现.队列长度可为无限或者有限.可通过Queue的构造函数的可选参数maxsize来设定队列长度.如果maxsize小于1就表示队列长度无限. 将一个值放入队列中: q.put() 调用队列对象的put()方法在队尾插入一个项目.put()

构建根文件系统之init进程分析

busybox是ls.cp等命令的集合. 执行ls时,实际上是执行了busybox ls 执行cp时,实际上是执行了busybox cp 分析init程序之前,再让我们回想一下我们的目标:u-boot启动内核,内核启动应用程序,内核是怎样启动应用程序呢,内核启动了init进程,位于/sbin/init中.我们最终的目的是启动客户程序,也就是说假如你是做手机的,希望启动一个手机的程序,假如是做监控的,那么就启动一个监控的程序的.客户各有不同,但都使用了linux系统,那么怎样加以区分呢? init

C++ 利用socket实现TCP,UDP网络通讯

学习孙鑫老师的vc++深入浅出,有一段时间了,第一次接触socket说实话有点儿看不懂,第一次基本上是看他说一句我写一句完成的,第二次在看SOCKET多少有点儿感觉了,接下来我把利用SOCKET完成TCP和UDP两种通讯模式的流程和代码分享一下,希望对大家多少能有点儿帮助,有什么说的不对的欢迎各位大神指正. TCP TCP是点对点的通讯模式,数据传输质量高,对于传输数据完整性要求高的情况一般用TCP,具体到vc++中,一般选用的是服务器/客户端模式,socket实现TCP通讯在服务器端一般分为以

linux中用管道实现兄弟进程通信

1 使用fork函数创建两个子进程.在第一个子进程中发送消息到第二个子进程,第二个子进程都出来并处理. 2 在父进程中,不适用管道通信,所以什么不需要做直接关闭勒管道的两端 3 代码实现 1 #include <unistd.h> 2 #include <stdio.h> 3 #include <stdlib.h> 4 #include <limits.h> 5 #include <fcntl.h> 6 #include <sys/type

C/C++ 进程通讯(命名管道)

服务端代码: // pipe_server.cpp : 定义控制台应用程序的入口点. // #include "stdafx.h" #include <stdio.h> #include <windows.h> #include <ctime> int main(int argc, _TCHAR* argv[]) { srand(time(NULL)); char buf[256] = ""; DWORD rlen = 0; HA