【发布时间】:2013-12-31 03:20:44
【问题描述】:
以下是两个函数,其中第一个函数根据计数值尝试为指针数组分配并随后重新分配内存。
第二个函数尝试将最后一个字符串连接到指针数组中的第一个字符串。
程序将要匹配的字符串数量和模式作为命令行参数,并且仅当在输入字符串中找到匹配模式时才调用第一个函数。
20 char **allocate_array_of_ptrs(char **str_array, /* pointer to the array of pointers */
21 char *str, /* pointer to the input string */
22 int count) /* count of matched strings */
23 {
24 char **temp = NULL; /* temporary pointer to realloc memory */
25
26 /* realloc based on count value */
27 temp = (char **)realloc(str_array, count * sizeof(char *));
28
29 int str_len = strlen(str);
30
31 /* if realloc is successful */
32 if (NULL != temp)
33 {
34 str_array = temp;
35
36 /* alloc memory for the string to be stored */
37 temp[count - 1] = (char *)calloc((str_len + 1), sizeof(char));
38 strcpy(temp[count - 1], str);
39 }
40
41 return str_array;
42 }
43
44 char **dmm_str_cat(char **str_array, /* pointer to the array of pointers */
45 int count) /* count of matched strings */
46 {
47 int i; /* iterator */
48 int total_str_len = 0; /* total length when all strings put together */
49 int str_len_of_first; /* string length of first string in the array */
50
51 if (count > 1)
52 {
53 str_len_of_first = strlen(str_array[0]);
54
55 for (i = 0; i < count; i++)
56 {
57 total_str_len += strlen(str_array[i]);
58 }
59 total_str_len += 1;
60
61 /* realloc memory to accomodate all matched strings onto first string */
62 str_array[0] = (char *)realloc(str_array[0], total_str_len * sizeof(char));
63
64 /* clearing the new allocated bytes */
65 for (i = (str_len_of_first + 1); i < total_str_len; i++)
66 {
67 str_array[0][i] = '\0';
68 }
69
70 /* concatenate from the last string onwards onto first string */
71 for (i = count - 1; i > 0; i--)
72 {
73 strcat(str_array[0], str_array[i]);
74 }
75 }
76
77 return str_array;
78 }
问题是当代码在valgrind下运行时,当3个字符串中有2个字符串不匹配模式'el'时,它会报告以下消息。其他组合也会报告类似的错误。
Enter string 1 : matter
Enter string 2 : matter
Enter string 3 : jello
Count of strings having matching pattern 'el' : 1
The matching strings are :
jello
==6244== Invalid read of size 8
==6244== at 0x400A74: main (dmm_main.c:86)
==6244== Address 0x4C33038 is 0 bytes after a block of size 8 alloc'd
==6244== at 0x4A05809: malloc (vg_replace_malloc.c:149)
==6244== by 0x4A05883: realloc (vg_replace_malloc.c:306)
==6244== by 0x400AE9: allocate_array_of_ptrs (dmm_functions.c:27)
==6244== by 0x4009B6: main (dmm_main.c:64)
==6244==
==6244== Invalid write of size 8
==6244== at 0x400A89: main (dmm_main.c:87)
==6244== Address 0x4C33038 is 0 bytes after a block of size 8 alloc'd
==6244== at 0x4A05809: malloc (vg_replace_malloc.c:149)
==6244== by 0x4A05883: realloc (vg_replace_malloc.c:306)
==6244== by 0x400AE9: allocate_array_of_ptrs (dmm_functions.c:27)
==6244== by 0x4009B6: main (dmm_main.c:64)
The concatenated string is : jello==6244==
==6244== ERROR SUMMARY: 2 errors from 2 contexts (suppressed: 4 from 1)
==6244== malloc/free: in use at exit: 0 bytes in 0 blocks.
==6244== malloc/free: 2 allocs, 2 frees, 14 bytes allocated.
==6244== For counts of detected errors, rerun with: -v
==6244== All heap blocks were freed -- no leaks are possible.
但是当有两个字符串匹配模式而一个不匹配时,valgrind 不会报告错误/泄漏。当所有字符串都与模式匹配时,就会报告肯定丢失了。
【问题讨论】:
-
感谢您提供的行号。 (编辑:Aaaaaand Streppel 出于某种原因删除了它们……>_
-
@Izmaki 对不起,我当时没有意识到他们会对问题的分析有所帮助。我刚刚回滚到第一个版本:-)
-
你是如何在你的 main 中调用函数 allocate_array_of_ptrs 的?看起来你的 str_array 指针对于 realloc 无效(例如局部变量的地址)
-
但是,如果 Valgrind (86&87) 引用的行不在帖子中,它们将无济于事。o
-
@alk : 86 free(str_array[i]); 87 str_array[i] = NULL; /* 这是一个从 0 到 (count - 1) 的 for 循环,我只在之前的调用之后在我的程序结束时执行此操作。 */