为什么 execvp 仅适用于在我的 shell 中输入的第一个命令
Why does execvp only work for the first command entered in my shell?
#include <stdio.h>
#include <string.h>
#include <cstring>
#include <stdlib.h>
#include <unistd.h>
#include <fcntl.h>
#include <sys/wait.h>
char input[100];
#define DELIMITERS " tn"
char * tokens[100];
int numTokens = 0;
int i = 0;
int n = 0;
char * cmd;
// function prototype
void nonBuiltin(char * inputs[]);
void handlePipe(char * cmds[]);
// this breaks the input into tokens and returns them
char * tokenize(char input[100])
{
n = 0;
// grabs input and separates by delimiters until the char is null
for(cmd = strtok(input, DELIMITERS); cmd; cmd = strtok(NULL, DELIMITERS))
{
if(n >= 100)
{
break;
}
tokens[n++] = cmd;
numTokens++;
}
for(size_t i = 0; i != n; i++)
{
printf("Tokens %zu is %sn", i, tokens[i]);
}
return * tokens;
}
// handles the commands you enter
// checks if builtin or non builtin command
// if builtin, execute command
// else, send command to nonbuiltin function
void handleCommands(char * inputs)
{
// changes directory
if(strcmp(tokens[0], "cd") == 0)
{
int change = chdir(tokens[1]);
if(change == 0)
{
chdir(tokens[1]);
}
else
{
perror("Cannot find path specified...n");
}
}
// prints working directory
else if(strcmp(tokens[0], "pwd") == 0)
{
printf("Your current working directory is: %sn", getenv("PWD"));
}
// implements set command
else if(strcmp(tokens[0], "set") == 0)
{
// do this
}
// exits program
else if(strcmp(tokens[0], "exit") == 0)
{
printf("Now exiting...n");
exit(3);
}
// input contains a nonbuiltin command
// sends input to nonbuiltin function
else
{
printf("Your command is a nonbuilt-in commandn");
nonBuiltin(tokens);
}
}
void nonBuiltin(char * inputs[])
{
int fp;
int status;
// create a new process
pid_t pid;
pid = fork();
// process creation was unsuccessful
if(pid < 0)
{
perror("Fork unsuccessful...n");
exit(-1);
}
// child process
else if(pid == 0)
{
// printf("Fork successful...n");
if(numTokens >= 3)
{
for(int i = 0; i < numTokens; i++)
{
if(strcmp(tokens[i], "<") == 0)
{
tokens[i] = tokens[i+1];
fp = open(tokens[i], O_RDONLY, 0);
dup2(fp, 0);
execvp(tokens[0], tokens);
}
else if(strcmp(tokens[i], ">") == 0)
{
tokens[i] = tokens[i+1];
fp = open(tokens[i], O_WRONLY | O_CREAT | O_TRUNC, S_IWUSR | S_IRUSR | S_IRGRP | S_IWGRP);
dup2(fp, 1);
close(fp);
tokens[i]= NULL;
execvp(tokens[0], tokens);
}
else if(strcmp(tokens[i], "|") == 0)
{
tokens[i] = tokens[i+1];
handlePipe(tokens);
}
}
}
else
{
// printf("Nothing special as far as commands gon");
execvp(tokens[0], tokens);
}
}
// wait for child process to end
else
{
waitpid(-1, &status, WUNTRACED);
printf("the child process has now terminatedn");
// exit(0);
}
}
void handlePipe(char * cmds[])
{
printf("Initiate pipingn");
// file descriptors
int fd[2];
// fd[0] is the read end of pipe
// fd[1] is the write end of pipe
pipe(fd);
if(!fork())
{
// first close the write end
close(1);
// fd[1] can now take stdout
dup(fd[1]);
close(fd[0]);
execvp(cmds[0], cmds);
}
else
{
// close read end
close(0);
// fd[1] can now take stdin
dup(fd[0]);
close(fd[1]);
execvp(cmds[1], cmds);
}
}
// starts the program and asks the user to enter input
// loops until the user enters 'exit'
int main()
{
while(1)
{
printf("Enter a command...n");
fgets(input, 100, stdin);
handleCommands(tokenize(input));
}
}
当我运行我的 shell 程序时,我输入一个命令,如 ls 或 cat,然后 命令将正确执行。如果我在那之后运行另一个命令 第一,命令根本不会执行。它甚至可能是相同的 命令作为我输入的第一个命令,它仍然不会运行 第二次。未给出任何错误消息。它只是不输出什么 该命令调用它进行输出。我目前正在使用 execvp,我相信我目前正在传递参数,所以我不确定从这里开始。有人可以给我一些意见吗 为什么会这样?
只要你觉得合适(它在主循环中对我有用,尽管我会把设计留给你):
numTokens = 0;
您不会重置在标记化函数中递增的令牌数。使用全局变量很容易错过这样的小东西。
相关文章:
- 为什么它只打印双链接列表的第一个值,而我的程序却崩溃了
- std::find,返回所有找到的值的替代方法,而不仅仅是存在重复的向量的第一个值
- 如何仅读取文本文件中的第一个值
- 在C++中,如何在第一个"system()"结束后执行第二个"system()"?
- 如何设置默认参数以防用户不输入另一个参数
- 查找不在标准中的第一个值::设置<int>最小-最大值
- C++:忽略第一个 cin.ignore 之后的输入
- 在C++中打印多个矢量的第一个值
- C++去除前x个元素的有效方法,在不改变向量大小的情况下将第x+1个元素推到第一个
- C++第一个cout将不会打印
- 我们可以在第一个else-if条件结束后使用另一个else-if条件吗
- 为什么在我的程序中输入另一个输入会给我不同的结果
- OpenGL:第二个VBO破坏了第一个VBO
- 为什么第一个Dynamic_cast没有投射到基类?
- C++ 验证同一行上两个输入的第一个
- (C++)生成数组中的第一个p*n完美平方数(从键盘输入p和n)
- 输入后,我的程序似乎跳过了第一个IF语句,直接转到ELSE
- 当一长串字符传递给第一个 cin 时,为什么不暂停第二个 cin 上的输入?
- 当我超过第一个 getline() 的输入中的数组大小时,第二个 getline 或其他输入函数不起作用
- 为什么无论输入如何,我的第一个 "if" 语句都会执行?