使用管道和exec时出错。第二个命令不退出
代码将命令作为输入并执行它。管道也被处理。 问题是,假设我输入ls | grep x作为命令。grep进程不退出,因此程序停止。任何想法使用管道和exec时出错。第二个命令不退出,c,exec,piping,dup2,C,Exec,Piping,Dup2,代码将命令作为输入并执行它。管道也被处理。 问题是,假设我输入ls | grep x作为命令。grep进程不退出,因此程序停止。任何想法 #include <stdio.h> #include <unistd.h> #include <string.h> #include <signal.h> void parse(int *cont,char *command,char **exarg) { char *x=strchr(command,
#include <stdio.h>
#include <unistd.h>
#include <string.h>
#include <signal.h>
void parse(int *cont,char *command,char **exarg)
{
char *x=strchr(command,'&');
if(x!=NULL)
{
*cont=1;
*(--x)='\0';
}
x=strtok(command," ");
while(x!=NULL)
{
*exarg++=x;
x=strtok(NULL," ");
}
*exarg='\0';
}
int divide(char *cmd,char **cmdarr)
{
int i=0;
char *x;
x=strtok(cmd,"|");
while(x!=NULL)
{
i++;
*cmdarr++=x;
x=strtok(NULL,"|");
}
*cmdarr='\0';
return i;
}
void main()
{
pid_t pid;
int cont;
int i=0;
int orgnum;
char *cmdarr[50];
char c[50];
int p1[2];
int p2[2];
char *argument[50];
if(pipe(p1)<0)
printf("error\n");
if(pipe(p2)<0)
printf("error2\n");
for(;;)
{
printf("Enter the command:");
gets(c);
if(!strcmp("exit",c))
break;
orgnum=divide(c,cmdarr);
printf("%d\n",orgnum);
for(i=0;i<orgnum;i++)
{
pid=fork();
if(pid==0)
{
if(i==0)
{
close(p1[0]);
close(p1[1]);
close(p2[0]);
if((i+1)!=orgnum)
{
dup2(p2[1],STDOUT_FILENO);
dup2(p2[1],STDERR_FILENO);
}
close(p2[1]);
parse(&cont,cmdarr[i],argument);
if((execvp(argument[0],argument))<0)
{
printf("Wrong cmd");
exit(0);
}
}
else if(i>0)
{
if((i+1)%2==0)
{
close(p1[0]);
close(p2[1]);
dup2(p2[0],STDIN_FILENO);
close(p2[0]);
if((i+1)!=orgnum)
{
dup2(p1[1],STDOUT_FILENO);
dup2(p1[1],STDERR_FILENO);
}
close(p1[1]);
}
else if((i+1)%2==1)
{
close(p2[0]);
close(p1[1]);
dup2(p1[0],STDIN_FILENO);
close(p1[0]);
if((i+1)!=orgnum)
{
dup2(p2[1],STDOUT_FILENO);
dup2(p2[1],STDERR_FILENO);
}
close(p2[1]);
}
parse(&cont,cmdarr[i],argument);
if((execvp(argument[0],argument))<0)
{
printf("Wrng cmd");
exit(0);
}
}
}
else if(pid>0){
close(p1[0]);
close(p1[1]);
close(p2[0]);
close(p2[1]);
wait(NULL);}
}
}
}
#包括
#包括
#包括
#包括
无效解析(int*cont,char*command,char**exarg)
{
char*x=strchr(命令“&”);
如果(x!=NULL)
{
*cont=1;
*(-x)='\0';
}
x=strtok(命令“”);
while(x!=NULL)
{
*exarg++=x;
x=strtok(空,“”);
}
*exarg='\0';
}
整数除法(字符*cmd,字符**cmdarr)
{
int i=0;
char*x;
x=strtok(cmd,“|”);
while(x!=NULL)
{
i++;
*cmdarr++=x;
x=strtok(空,“|”);
}
*cmdarr='\0';
返回i;
}
void main()
{
pid_t pid;
内部控制;
int i=0;
内在组织;
char*cmdarr[50];
charc[50];
int p1[2];
int p2[2];
字符*参数[50];
如果(管道(p1),则有循环:
叉子
如果是孩子
exec
如果为父级,则为else
关闭管道
等待
当你有类似“ls | grep foo”的东西时
第1步:在child中执行ls,
然后关闭所有管道,并等待父级中的“ls”终止,
步骤2:在child中执行“grep”,并使用管道作为输入,但在步骤1中关闭它们。
是,因为步骤1中的流程没有使用管道。第二个流程“grep”是一个全新的子流程,作为(i=0;i)的循环