Valgrind告诉我,我在尝试免费阅读阵列之后。然而,根据valgrind的说法,阵列比我尝试读取它的时间晚两行!我很困惑。
这是valgrind错误:
==21632== Invalid read of size 8
==21632== at 0x400D73: hDump (Lex1.c:91)
==21632== by 0x400B19: process (mainLex.c:66)
==21632== by 0x400A7C: main (mainLex.c:41)
==21632== Address 0x51f3490 is 0 bytes inside a block of size 24 free'd
==21632== at 0x4C29577: free (in /usr/lib64/valgrind/vgpreload_memcheck-amd64-linux.so)
==21632== by 0x400B7E: freeList (mainLex.c:81)
==21632== by 0x400A88: main (mainLex.c:43)
==21632==
==21632== Invalid read of size 1
这是mainLex.c:
int main (int argc, char *argv[])
{
int ncmd = 1; // Command number
char *line; // Initial command line
char *cmd; // Command after history expansion
int status; // Status of expansion
token *list; // Linked list of tokens in command
void process (token *);
void freeList (token *);
for (;;) {
printf ("(%d)$ ", ncmd); // Prompt for command
if ((line = getLine(stdin)) == NULL) // Read line
break; // Break on end of file
cmd = hExpand (line, &status); // Expand line
free (line);
if (status > 0) // Substitution?
fputs (cmd, stdout); // Print expanded line
else if (status < 0)
fputs ("substitution failed\n", stderr);
list = lex (cmd); // Lex line into tokens
free (cmd);
if (list == NULL) // Empty token list?
continue;
hRemember (ncmd, list); // Remember command
if (status >= 0) // No substitution error?
process (list); // Process token list (This is line 41)
freeList (list); // Free token list (This is line 43)
ncmd++; // Adjust prompt
}
hClear(); // Free all storage
return 0;
}
// -- PROCESS MODULE -------------------------------------------------------
// Print list of tokens LIST
void process(struct token *list)
{
struct token *p;
void freeList (token *);
for (p = list; p != NULL; p = p->next) { // Walk down linked list
printf ("%s:%d ", p->text, p->type); // printing token and type
}
putchar ('\n'); // Terminate line
// history command dumps most recent 9 commands
if (list && !strcmp (list->text, "history"))
hDump(9); //Line 66
// hclear command clears history
else if (list && !strcmp (list->text, "hclear"))
hClear();
}
// Free list of tokens LIST
void freeList (token *list)
{
token *p, *pnext;
for (p = list; p; p = pnext) {
pnext = p->next;
free(p->text);
free(p); //Line 81
}
}
编辑:getLine是顶部#include部分中的一个单独函数,我没有包含它。我还添加了额外的行号,并且会在一秒内包含一个最小的例子。
此外,这里是hDump的代码:( llist是一个全局静态数据结构)
void hDump (int n)
{
token *current;
for (int j=0; j<n; j++)
{
if (llist->prev!=NULL)
{
llist=llist->prev;
}
}
for (int i=0; i<n; i++)
{
llist=llist->nextcmd;
printf("%6d ", llist->num);
current=llist->cmmd;
if (current == NULL)
{
continue;
}
else
{
printf("%s ", current->text);
}
while(current->next!=NULL) //Line 91
{
current=current->next;
printf("%s ", current->text);
}
printf("\n");
}
}