[英]Why is execvp() executing twice using fork()?
I am implementing a shell. 我正在实现一个外壳。
When attempting a command other than changing directories, execvp()
runs, the child terminates and a new child is created. 当尝试更改目录以外的命令时, execvp()
运行,该子级终止并创建一个新的子级。 When I change directories, the child does not terminate and a new child is created. 当我更改目录时,该子级不会终止,并且会创建一个新的子级。 Here is a sample of my code: 这是我的代码示例:
for(;;) {
printf("bash: ");
parse();
...
pid_t pid = fork()
if (pid == 0)
if (!strcmp(line[0], "cd"))
if (!line[1]) (void) chdir(getenv("HOME"));
else (void) chdir(line[1]);
else execvp(line[0], line);
...
if (pid > 0) {
while (pid == wait(NULL));
printf("%d terminated.\n", pid);
}
}
cd ../; ls;
runs correctly, except I have to Ctrl+D
twice to end the program. 运行正常,除了必须两次Ctrl+D
结束程序。
Though, if I pipe the same information (ie. mybash < chdirtest
), it runs correctly once, terminates the child, runs again except in the original directly, then terminates the final child. 但是,如果我传递相同的信息(即mybash < chdirtest
),则它将正确运行一次,终止子项,直接在原始文件中再次运行,然后终止最终子项。
cd
should not be invoked through a child process, the shell itself should change its current directory (that's the property of an internal command: modify the process of the shell itself). 不应通过子进程调用cd
,shell本身应更改其当前目录(这是内部命令的属性:修改shell本身的进程)。
A (primitve) shell should looks like: (primitve)shell应该看起来像:
for(;;) {
printf("bash: ");
parse();
// realize internal commands (here "cd")
if (!strcmp(line[0], "cd")) {
if (!line[1]) (void) chdir(getenv("HOME"));
else (void) chdir(line[1]);
continue; // jump back to read another command
}
// realize external commands
pid_t pid = fork()
if (pid == 0) {
execvp(line[0], line);
exit(EXIT_FAILURE); // wrong exec
}
// synchro on child
if (pid > 0) {
while (pid == wait(NULL));
printf("%d terminated.\n", pid);
}
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.