В tokenize_pipe
вы делаете
args2[i][args_size2] = token;
без инициализации args2[i]
Один способ - в _pipe
заменить
char** commands[MAX_ARGS];
на
char* commands[MAX_ARGS][MAX_ARGS];
и в tokenize_pipe
для замены
статический символ ** args2 [MAX_ARGS];
by
static char* args2[MAX_ARGS][MAX_ARGS];
Но, конечно, при использовании больших массивов рассмотрите возможность использования динамических массивов, используя malloc затем realloc для их изменения.
Вот предложение, где tokenize_pipe
возвращает трехмерный массив, где все выделено, я также продублирую токены.NULL используется для обозначения конца строк и столбцов
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
char*** tokenize_pipe(char* input)
{
char *** r = malloc(1);
size_t nCommands = 0;
char * savePtrCmds;
char * fullcmd = strtok_r(input, "|", &savePtrCmds);
while (fullcmd != NULL) {
char ** tokens = malloc(1);
size_t nTokens = 0;
char * token = strtok(fullcmd, " ");
while (token != 0) {
tokens = realloc(tokens, (nTokens + 2) * sizeof(char *));
tokens[nTokens++] = strdup(token); /* also duplicate the token to allows input to disapear */
token = strtok(NULL, " ");
}
tokens[nTokens] = NULL;
r = realloc(r, (nCommands + 2) * sizeof(char **));
r[nCommands++] = tokens;
fullcmd = strtok_r(NULL, "|", &savePtrCmds);
}
r[nCommands] = NULL;
return r;
}
int main()
{
char *** r;
{
char input[] = "command1 arg | command2 arg2 | command3 arg3 arg4";
r = tokenize_pipe(input);
}
/* here input does not exist anymore */
/* debug */
for (char *** pcmds = r; *pcmds; ++pcmds) {
for (char ** pcmd = *pcmds; *pcmd; ++pcmd)
printf("%s ", *pcmd);
putchar('\n');
}
/* free resources */
for (char *** pcmds = r; *pcmds; ++pcmds) {
for (char ** pcmd = *pcmds; *pcmd; ++pcmd)
free(*pcmd);
free(*pcmds);
}
free(r);
return 0;
}
Компиляция и выполнение:
pi@raspberrypi:/tmp $ gcc -pedantic -Wall -Wextra t.c
pi@raspberrypi:/tmp $ ./a.out
command1 arg
command2 arg2
command3 arg3 arg4
Выполнение в valgrind :
==7301== Memcheck, a memory error detector
==7301== Copyright (C) 2002-2017, and GNU GPL'd, by Julian Seward et al.
==7301== Using Valgrind-3.13.0 and LibVEX; rerun with -h for copyright info
==7301== Command: ./a.out
==7301==
command1 arg
command2 arg2
command3 arg3 arg4
==7301==
==7301== HEAP SUMMARY:
==7301== in use at exit: 0 bytes in 0 blocks
==7301== total heap usage: 22 allocs, 22 frees, 1,186 bytes allocated
==7301==
==7301== All heap blocks were freed -- no leaks are possible
==7301==
==7301== For counts of detected and suppressed errors, rerun with: -v
==7301== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 6 from 3)