我正在用C开发一个shell命令,使用命令execv时遇到问题。我在main中有一个while(1),所以它应该是一个无限循环,但是如果我将/ bin / ls作为命令引入,则提示显示文件和文件夹,然后停止。
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include <errno.h>
#include <sys/types.h>
#include <sys/wait.h>
#define MAX_LENGTH 256
#define DEFAULT_STRING_LENGTH 256
#define MAX_PARAMETERS 16
void initParams(char *** params);
void read_command(char *** params);
void freeParams(char *** params);
void type_prompt();
int comprobarSalir(char ***cadena);
int main(){
int salir = 0;
do{
char ** params;
type_prompt();
fflush(stdout);
initParams (& params);
read_command (& params);
salir = comprobarSalir(& params);
if(comprobarSalir(¶ms)==0){
if(execv(params[0], params) == -1){
printf("%s,%s",params[0],params[1]);
printf("Error al ejecutar el comando ' %s': %s\n", params [0], strerror(errno));
freeParams (& params);
}
}
}while(1);
}
void read_command(char *** args) {
char input [256], *substr;
int n = 0;
fgets(input , sizeof(input), stdin);
input[strlen(input) -1] = '\0';
substr = strtok(input , " ");
if (substr != NULL)
memcpy ((* args)[n], substr , strlen(substr));
else
(*args)[n] = NULL;
n++;
while ((* args)[n-1] != NULL) {
substr = strtok(NULL , " ");
if (substr != NULL)
memcpy ((* args)[n], substr , strlen(substr));
else
(*args)[n] = NULL;
n++;
}
}
void freeParams(char *** params){
int i;
char ** parameter;
for (i=0; i<MAX_PARAMETERS; i++) {
parameter = ((* params) +i);
if (* parameter != NULL) free(* parameter);
}
free(* params);
*params = NULL;
}
void initParams(char *** params) {
int i, j;
char ** parameter;
*params = (char **) malloc(sizeof(parameter) * MAX_PARAMETERS);
for (i = 0; i<MAX_PARAMETERS; i++) {
parameter = (* params) + i;
*parameter = (char*) malloc(DEFAULT_STRING_LENGTH);
for (j = 0; j<DEFAULT_STRING_LENGTH; j++) *((* parameter)+j) = '\0';
}
}
void type_prompt(){
char cwd[MAX_LENGTH];
getcwd(cwd, sizeof(cwd));
printf("%s$ ",cwd);
}
int comprobarSalir(char ***cadena){
int salir = 0;
char* exit = "exit";
if(***cadena==*exit){
salir = 1231;
}
return salir;
}
答案 0 :(得分:2)
execv
用不同的程序替换调用它的进程。
由于当前进程现在正在运行另一个程序(ls
),当然它的循环将不再继续。
如果您希望在调用execv
后继续运行流程,则需要使用fork()
来创建子流程;检查您是父母还是孩子,并仅在孩子中致电execv
。此时,如果您希望父级等待ls
的副本完成,您可以在父级中使用wait()
来执行此操作,并确定子级是成功还是失败。