Я создаю оболочку и у меня возникли проблемы с системным вызовом 'execvp'. Я видел некоторые другие вопросы по этой теме, но они были расплывчатыми и, по-видимому, не были полностью решены (кто бы ни задавал вопросы, он не предоставил много информации и не получил хороших ответов).
Очевидно, у меня есть своя командная строка, и я я читаю пользовательский ввод со стандартного ввода, например
mysh some/path $ ps -a
, и я создаю массив args как char **, и сам массив работает (я думаю), поскольку, когда я распечатываю значения в своей функции, он показывает
args[0] = 'ps'
args[1] = '-a'
args[2] = '(null)'
Итак, я вызвать fork и execvp(cmnd, args) внутри моего процесса, где cmnd — это «ps», а args — как указано выше, а perror и т. д.
Я получаю
'Error: no such file or directory.'
Нужно ли вводить переменную $PATH? делать что-то еще странное?
Вот мой код для генерации массива args:
char ** get_args(char * cmnd) {
int index = 0;
char **args = (char **)emalloc(sizeof(char *));
char * copy = (char *) emalloc(sizeof(char)*(strlen(cmnd)));
strncpy(copy,cmnd,strlen(cmnd));
char * tok = strtok(copy," ");
while(tok != NULL) {
args[index] = (char *) emalloc(sizeof(char)*(strlen(tok)+1));
strncpy(args[index],tok,strlen(tok)+1);
index++;
tok = strtok(NULL," ");
args = (char**) erealloc(args,sizeof(char*)*(index+1));
}
args[index] = NULL;
return args;
}
(emalloc и errealloc — это просто malloc и realloc со встроенной проверкой ошибок)
Итак, я делаю следующее:
void exec_cmnd(char*cmnd, char**args) {
pid_t pid;
if((pid=fork())==0) {
execvp(cmnd, args);
perror("Error");
free(args);
free(cmnd);
exit(1);
}
else {
int ReturnCode;
while(pid!=wait(&ReturnCode)) {
;
}
}
}
И, как я сказал выше, когда execvp вызывается внутри моего процесса, он терпит неудачу, когда я предоставляю какие-либо аргументы, но работает без них (т.е. when argv == {'ps', NULL} )
Если вам нужна дополнительная информация, не стесняйтесь спрашивать. Мне нужно решить это.