繁体   English   中英

Valgrind 报告 memory 在标准输入的 getline 后释放指针上泄漏

[英]Valgrind reports memory leak on freed pointer after getline from stdin

有这个代码:

#include <stdlib.h>
#include <stdio.h>
void main()
{   
    char *line = calloc(1024, 1);
    size_t size = 0;
    getline(&line, &size, stdin);
    free(line);
}

Valgrind 抱怨:

==5931== HEAP SUMMARY:
==5931==     in use at exit: 1,024 bytes in 1 blocks
==5931==   total heap usage: 3 allocs, 2 frees, 2,168 bytes allocated
==5931== 
==5931== 1,024 bytes in 1 blocks are definitely lost in loss record 1 of 1
==5931==    at 0x4837B65: calloc (vg_replace_malloc.c:752)
==5931==    by 0x10916B: main (test.c:5)
==5931== 
==5931== LEAK SUMMARY:
==5931==    definitely lost: 1,024 bytes in 1 blocks

我看过其他相关的帖子,但找不到这个特殊情况的答案:/

这是一个 glibc 错误(或长期存在的 glibc 行为,取决于您如何看待它):

在 glibc 中很难修复,因为许多应用程序假定行指针在长度为零时不必初始化,如klutt原始回复中所示。 如果 glibc 在零长度情况下开始释放或以其他方式使用行指针,这将导致崩溃。

getlinecalloc都分配 memory。 如果您想使用getline ,请不要预先分配。 只需这样做:

int main(void)
{   
    char *line = NULL;
    size_t size = 0;
    getline(&line, &size, stdin);
    free(line);
}

一个提示是你如何调用getline 如果您发送line , function 将无法更改指针指向的内容。 但是现在你发送&line ,表示 function 想要重新分配 memory。

如果要预分配,请使用fgets而不是getline

此外, main不应为void function。

size 中包含的sizeline指向的当前分配的大小。 因此修复将是

#include <stdlib.h>
#include <stdio.h>
int main(void)
{   
    char *line = calloc(1024, 1);
    size_t size = 1024;
    getline(&line, &size, stdin);
    free(line);
}

没关系!

或者你可以做

char *line = NULL;
size_t size = 0;
getline(&line, &size, stdin);
free(line);

但它可能会为 1000 个字符长的行做一些额外的重新分配。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM