I want to pass a heap based array that contains sub arrays for arguments to a function that uses execvp
, why a heap based array, because I splitting user input into a list of arguments
int split(char * str, const char * token , char *** arr)
{
int c = 1;
char * ptr = strtok(str , token);
(*arr)[0] = malloc(1024);
strcpy((*arr)[0], "-c");
while (ptr != NULL)
{
(*arr)[c] = malloc(1024);
strcpy((*arr)[c], ptr);
c++;
*arr = realloc(*arr, sizeof(char*)*(c+1));
ptr = strtok(NULL, token);
}
(*arr)[c] = NULL;
return c;
}
int run(char * args[])
{
int link[2];
pid_t pid;
char foo[4096];
if (pipe(link)==-1)
return -1;
if ((pid = fork()) == -1)
return -1;
if(pid == 0){
dup2 (link[1], STDOUT_FILENO);
close(link[0]);
close(link[1]);
execvp("/bin/bash", args);
} else {
close(link[1]);
int nbytes = read(link[0], foo, sizeof(foo));
printf("Output: (%.*s)\n", nbytes, foo);
wait(NULL);
}
return 0;
}
int main()
{
char * tmp = malloc(1024);
/* list of pointers */
char ** arr = malloc(16);
/* buffer to hold user input */
char input[1024];
scanf("%[^\n]", input);
//printf("%s\n",input);
int x = split(input, " ", &arr);
for (int i=0; i<x;i++)
{
printf("%s ",arr[i]);
}
run(arr);
char * arr2[] = {getenv("SHELL"), "-c" ,"ls","-la", NULL};
run(arr2);
}
split
takes the user input and create a list of pointers where the first element is -c
and the last is NULL
and the user input is in the middle next it is being passed to the run
function that attempts to run the command with /bin/bash
but throws the error
ls -la
/usr/bin/ls: /usr/bin/ls: cannot execute binary file
-c ls -la Output: ()
where as if I where to create a stack based array of arrays then pass it to the run
function everything works fine and I get the directory listings
I used getenv
in the split
function and then passed the whole array to run
this way every thing is in the right order
int split(char * str, const char * token , char *** arr)
{
int c = 2;
char * ptr = strtok(str , token);
(*arr)[0] = malloc(1024);
/* added this as the first element in the array */
strcpy((*arr)[0], getenv("SHELL"));
(*arr)[1] = malloc(1024);
/* added this as the second element in the array */
strcpy((*arr)[1], "-c");
while (ptr != NULL)
{
(*arr)[c] = malloc(1024);
strcpy((*arr)[c], ptr);
c++;
*arr = realloc(*arr, sizeof(char*)*(c+1));
ptr = strtok(NULL, token);
}
(*arr)[c] = NULL;
return c;
}
int run(char * args[])
{
int link[2];
pid_t pid;
char foo[4096];
if (pipe(link)==-1)
return -1;
if ((pid = fork()) == -1)
return -1;
if(pid == 0){
dup2 (link[1], STDOUT_FILENO);
close(link[0]);
close(link[1]);
/* /bin/bash to args[0] */
execvp(args[0], args);
} else {
close(link[1]);
int nbytes = read(link[0], foo, sizeof(foo));
printf("Output: (%.*s)\n", nbytes, foo);
wait(NULL);
}
return 0;
}
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.