2009-07-15 8 views
5

내 프로그램이이 (main.c를)과 같다 :의 malloc, 문자열 포인터 및 Valgrind의

#include <stdlib.h> 
#include <stdio.h> 
void main(){ 
    char *first="hello "; 
    char *second="world!"; 
    char *seq=(char *)malloc((strlen(first)+1)*sizeof(char)); 
    strcat(strcpy(seq,first),second); 
    printf("%s\n",seq); 
    free(seq); 
} 

내가 도구 Valgrind의와 디버깅, 그것은 말했다 $ (즉 : Valgrind의 --tool = memcheck --leak-check = full --track-origins = yes ./main) :

==5118== Memcheck, a memory error detector. 
==5118== Copyright (C) 2002-2008, and GNU GPL'd, by Julian Seward et al. 
==5118== Using LibVEX rev 1884, a library for dynamic binary translation. 
==5118== Copyright (C) 2004-2008, and GNU GPL'd, by OpenWorks LLP. 
==5118== Using valgrind-3.4.1, a dynamic binary instrumentation framework. 
==5118== Copyright (C) 2000-2008, and GNU GPL'd, by Julian Seward et al. 
==5118== For more details, rerun with: -v 
==5118== 
==5118== Invalid write of size 1 
==5118== at 0x402575B: strcat (in /usr/lib/valgrind/x86-linux/vgpreload_memcheck.so) 
==5118== by 0x80484EB: main (main.c:7) 
==5118== Address 0x418a02f is 0 bytes after a block of size 7 alloc'd 
==5118== at 0x402522D: malloc (in /usr/lib/valgrind/x86-linux/vgpreload_memcheck.so) 
==5118== by 0x80484C3: main (main.c:6) 
==5118== 
==5118== Invalid write of size 1 
==5118== at 0x4025777: strcat (in /usr/lib/valgrind/x86-linux/vgpreload_memcheck.so) 
==5118== by 0x80484EB: main (main.c:7) 
==5118== Address 0x418a034 is 5 bytes after a block of size 7 alloc'd 
==5118== at 0x402522D: malloc (in /usr/lib/valgrind/x86-linux/vgpreload_memcheck.so) 
==5118== by 0x80484C3: main (main.c:6) 
==5118== 
==5118== Invalid read of size 1 
==5118== at 0x4025963: strlen (in /usr/lib/valgrind/x86-linux/vgpreload_memcheck.so) 
==5118== by 0x40A0FA4: puts (in /lib/libc-2.10.1.so) 
==5118== by 0x80484F7: main (main.c:8) 
==5118== Address 0x418a02f is 0 bytes after a block of size 7 alloc'd 
==5118== at 0x402522D: malloc (in /usr/lib/valgrind/x86-linux/vgpreload_memcheck.so) 
==5118== by 0x80484C3: main (main.c:6) 
==5118== 
==5118== Invalid read of size 1 
==5118== at 0x40ACEFE: _IO_default_xsputn (in /lib/libc-2.10.1.so) 
==5118== by 0x40AA3D0: [email protected]@GLIBC_2.1 (in /lib/libc-2.10.1.so) 
==5118== by 0x40A1020: puts (in /lib/libc-2.10.1.so) 
==5118== by 0x80484F7: main (main.c:8) 
==5118== Address 0x418a02f is 0 bytes after a block of size 7 alloc'd 
==5118== at 0x402522D: malloc (in /usr/lib/valgrind/x86-linux/vgpreload_memcheck.so) 
==5118== by 0x80484C3: main (main.c:6) 
hello world! 
==5118== 
==5118== ERROR SUMMARY: 17 errors from 4 contexts (suppressed: 13 from 1) 
==5118== malloc/free: in use at exit: 7 bytes in 1 blocks. 
==5118== malloc/free: 1 allocs, 0 frees, 7 bytes allocated. 
==5118== For counts of detected errors, rerun with: -v 
==5118== searching for pointers to 1 not-freed blocks. 
==5118== checked 47,492 bytes. 
==5118== 
==5118== 
==5118== 7 bytes in 1 blocks are definitely lost in loss record 1 of 1 
==5118== at 0x402522D: malloc (in /usr/lib/valgrind/x86-linux/vgpreload_memcheck.so) 
==5118== by 0x80484C3: main (main.c:6) 
==5118== 
==5118== LEAK SUMMARY: 
==5118== definitely lost: 7 bytes in 1 blocks. 
==5118==  possibly lost: 0 bytes in 0 blocks. 
==5118== still reachable: 0 bytes in 0 blocks. 
==5118==   suppressed: 0 bytes in 0 blocks. 

누가 그것을 어떻게 수정해야하는지 말해 줄 수있는 사람은 누구입니까?

답변

17
char *seq=(char *)malloc((strlen(first)+1)*sizeof(char)); 

'첫 번째'크기의 문자열에 대해 메모리를 할당하고 있습니다.

strcat(strcpy(seq,first),second); 

그리고 나서 첫 번째와 두 번째를 모두 맞추려고합니다. 그것은 결코 작동하지 않을 것입니다. strcat은 더 많은 메모리를 생성하지 않으므로,이를 malloc에 포함시켜야합니다. 그 일부가 일부가 혼란을 고려, 변경의 경우에 유형에 대한 EXPLICT 수 어쨌든 그것을 가지고 싶은 1이 보장 될 때

There is no need to cast the result of malloc in pure C.

sizeof(char)을 할 필요 없습니다.

+1

C에서 malloc()의 반환 값을 캐스팅 할 필요가 없습니다. 또한, 'sizeof (char)'는 항상'1'입니다. – Christoph

2

seq에서 첫 번째 공간 만 할당합니다.

1

seq는 (strlen (first) +1) * sizeof (char) 길이로 연결 문자열을 처음 + 초간 유지하기에 충분하지 않습니다.() 두 번째의 strcpy (서열, 제)

strcat와;

-1

I는 해당 광고를 볼 수 있었다

은 틀을 잘못 붙이지 않았습니다. 그 이유는 적절한 소스를 제공하지 않는 문자열 연결을 수행하고 있기 때문입니다. 위의 구문을 2 행으로 seggregate하면 ​​정상적으로 작동합니다.

strcpy (seq, first); strcat (seq, second);

문자열 복사를 수행 할 때 "first"에서 "seq"까지 문자열을 복사하기 때문입니다. 자, 문자열 연결을 위해 적절한 소스를 찾을 수 없으므로 [소스가 "seq"라는 것을 특별히 언급하지 않았다는 것을 기억하십시오], 잘못된 쓰기 메모리 누수 문제가 발생합니다.

희망 사항은 질문을 명확히하기를 바랍니다. 동일한 추가 정보가 필요한 경우 되돌려주십시오.

+0

또한 위에서 언급했듯이 다른 사람들은 "초"를 저장하기 위해 seq에 적절한 메모리를 할당해야합니다. –

+0

'strcpy()'는 첫 번째 인자를 반환하므로'strcat (strcpy (seq, first), scond)'는'strcpy (seq, fiest);와 같습니다. strcat (seq, second);'. –

3

malloc()에 해당하는 free()은 어디입니까?

+0

하하, 나는 그것을 잃어 버렸고, 나는 단지 strcpy와 strcat의 오류를 보여주고 싶다. 물론, 저는 무료 (seq)를 추가해야합니다; 모두 똑같은 감사합니다. –

+0

'main()'이 – Christoph

+1

을 반환 한 후 메모리가 OS에 의해 암시 적으로 free'd되었습니다. 와우 - 왜 나는'free() '를 호출해야합니까?:-) – Justicle