管道实现交互

这几天在做测试,用脚本比较容易些。

但是在此过程中遇到一些问题,也引发出对管道的重新思考。微笑


脚本需要实现的功能描述:

1,循环上100次

2,每次,都需要运行一个服务器上的程序(就叫J程序吧)微笑

                都需要输入密码


问题:

这里需要从脚本里往J里输入密码,这里我不会。

我的问题集中在,怎么往标准输入中写入数据。

好,我在脚本中这样写的:

“password" >/dev/fd/0

但shell把“password" 当做命令来处理。我想它可能是,用exec来执行“password" 的。难过

然后,echo “password" >/dev/fd/0

还是不行,直接打印出来了。大哭


===================================================================================


1,验证为什么不行

我想原因是什么?shell那么常用,不应该不会有这么一个东东的。

接着我写了一个c语言的程序,来验证,echo “password" >/dev/fd/0为什么没写到子程序的标准输入里。

#include <stdio.h>
#include <unistd.h>
void main()
{
        pid_t   pid;
        char s[10] = {0};
        if ((pid = fork()) == 0) {
                // child
                scanf ("%s", s);
                printf ("%s\n", s);
                while (1);
        } else {
                // parent
                scanf ("%s", s);
                printf ("-----%s\n", s);
                while (1);
        }
}
这里得到的启示是:父子程序对fd其实也存在抢占的,如果父进程先得到标准输入,那么他会把标准输入队列里的东东拿干净。。。原来如此。。。偷笑


2,寻找另外的出路

管道,试了

echo "password" | J
成功了。


3,为什么

要弄懂为什么就要确定问题是什么:

①什么是管道

这是在网上找的管道的实现

#include <stdio.h>
#include <unistd.h>

int fd[2];

char *argv[] = {"ls", (char*)0};
char *envp[] = {"PATH=/bin", 0};
char *argv2[] = {"wc", (char*)0};
char *envp2[] = {"PATH=/bin", 0};

void run_ls()
{
	dup2(fd[1], 1);
	close (fd[0]);
	close (fd[1]);
	execve("/bin/ls", argv, envp);
}

void run_wc()
{
	dup2(fd[0], 0);
	close (fd[0]);
	close (fd[1]);
	execve("/usr/bin/wc", argv2, envp2);
}

int main()
{
	pipe(fd);
	if (fork() == 0) {
		run_ls(); 
	} else {
		run_wc(); // 如果标准输入没有东东的话,就会阻塞。所以不用考虑父子进程谁先执行。
	}
	return 0;
}

解决了。


4,后续:

后面还有很多内容要学习,比如高级一点的expect等,高级一点的进程间通信的概念。

最近有很多东西,要学习,这里的后续放到有空的时候吧。


5,重定向也能实现往进程中传数据的功能

echo "1 2 3" > file.txt

wc < file.txt

注意,这里重定向的话,一定是命令或者执行程序写在前面。不能写成: file.txt > wc。


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章