I 코드를 가지고 수행되어야하는 코드와 같은, 느낌표 부분에 선행하는 라인의 첫 번째 정수를 얻을 무엇임의 문자
else if ((strtolnum=(strtol(&oldline[b+1],NULL,10)))>0)
{
char* excl = malloc(3*sizeof(char));
excl[0]=oldline[b];
excl[1]=oldline[b+1];
for (int j = 0; j<strtolnum; j++)
{
llist=llist->nextcmd;
}
struct token *p1;
struct token *save1 = llist->cmmd;
char *arra1 = malloc(sizeof(char));
memset(arra1, '\0', 1);
for (p1 = llist->cmmd; p1 != NULL; p1 = p1->next) {
arra = realloc(arra1, strlen(arra1)+strlen(p1->text)+2);
strcat(arra, p1->text);
if (p1->next!=NULL)
{
strcat(arra1, " ");
}// printing token and type
}
printf("%s excl\n", excl); //Line 137
oldline=strreplace(oldline,excl,arra1); //Line 138
llist->cmmd=save1;
for (int j = 0; j<(f-strtolnum); j++)
{
llist=llist->nextcmd;
}
*status=1;
size_t a = sizeof(excl);
memset(excl,'\0', a);
}
! 3, 그리고 excl에 넣습니다 (그리고 나서 완벽하게 잘 작동하는 다른 것들을하십시오).
그러나 반복문을 두 번 이상 실행하면 excl에 printf를 시도 할 때 "! 3e"로 표시 될 때와 같이 끝에 excl이 종종 임의의 문자를가집니다. Valgrind는 다음과 같은 오류를 표시합니다.
==24878== Conditional jump or move depends on uninitialised value(s)
==24878== at 0x4E7AB5B: vfprintf (in /usr/lib64/libc-2.17.so)
==24878== by 0x4E83CD8: printf (in /usr/lib64/libc-2.17.so)
==24878== by 0x40130F: hExpand (Lex1.c:137)
==24878== by 0x400B6B: main (mainLex.c:27)
==24878==
==24878== Conditional jump or move depends on uninitialised value(s)
==24878== at 0x4C2B308: strlen (in /usr/lib64/valgrind/vgpreload_memcheck-amd64-linux.so)
==24878== by 0x4020D7: strreplace (Lex1.c:562)
==24878== by 0x40132C: hExpand (Lex1.c:138)
명백히 excl은 루프가 한 번 통과 한 후에 하나씩 초기화됩니다. 뭐가 잘못 되었 니?
자세한 내용은 cmmd가 토큰 유형의 데이터 구조이고 llist가 토큰을 포함하는 전역 정적 데이터 구조입니다.
'excl' 문자열을 null로 끝내지 않았습니다. 'malloc()'은 임의의 쓰레기를 반환합니다. –
다음 줄 : size_t a = sizeof (excl); memset (excl, '\ 0', a); excl 포인터의 4 바이트를 항상 0x00으로 설정합니다. 이로 인해 메모리 누수가 발생하고 excl은 메모리의 첫 번째 바이트를 가리 킵니다. 실제로 할당 된 메모리 (모든 경우에 3 바이트가됩니다)의 값을 지우려고하면 아마도 memset (excl, '\ 0', 3); – user3629249
@ user3629249 : 포인터 자체를 0으로 설정하지 않습니다. 포인터가 가리키는 메모리를 0으로 설정합니다. 포인터를 0으로 만들려면'memset (& excl, '\ 0', a);'를 호출해야합니다. –