dev*_*per 5 c valgrind memory-leaks memory-management
我正在用C中的链表实现优先级队列,但是当我打印pop操作时却遇到内存泄漏。我还有另一个内存泄漏,我也试图找到它。
另外,我使用heapusageby d99kris代替Valgrind。
这是我使用时的堆摘要printf:
HEAP SUMMARY:
in use at exit: 4112 bytes in 2 blocks
total heap usage: 10 allocs, 17 frees, 4536 bytes allocated
peak heap usage: 4256 bytes allocated
16 bytes in 1 block(s) are lost, originally allocated at:
LEAK SUMMARY:
definitely lost: 4112 bytes in 2 blocks
Run Code Online (Sandbox Code Playgroud)
这是没有printf以下内容的堆摘要:
HEAP SUMMARY:
in use at exit: 16 bytes in 1 blocks
total heap usage: 9 allocs, 10 frees, 440 bytes allocated
peak heap usage: 256 bytes allocated
LEAK SUMMARY:
definitely lost: 16 bytes in 1 blocks
Run Code Online (Sandbox Code Playgroud)
我的pop功能:
void *prio_q_pop(struct prio_q *q) {
q->size--;
struct elem *temp = q->first;
(q->first) = (q->first)->next;
void *asd = temp->datei;
free(temp);
return asd;
}
Run Code Online (Sandbox Code Playgroud)
而我的main作用,我打电话printf
struct prio_q *queue;
char *s;
int i;
queue = prio_q_create();
push(queue, "Bye World", 0);
for (i = 0; i < 5; i++) {
s = prio_q_pop(queue);
//printf("%s\n", s);
}
s = prio_q_front(queue);
//printf("%s\n", s);
Run Code Online (Sandbox Code Playgroud)
原因
问题不是由我的代码引起的,它是内存检查器。以下程序泄漏1个块,堆使用2个alloc和4个free。
#include <stdio.h>
int main() {
printf("omer");
return 0;
}
Run Code Online (Sandbox Code Playgroud)
This is a false positive. If anything, the problem is that heapusage does not have good enough documentation. I recommend using a better leak checker like the leak sanitizer or Valgrind.
I created a file test.c.
#include <stdio.h>
int main(int argc, char **argv) {
puts("Hello, world!");
}
Run Code Online (Sandbox Code Playgroud)
With leak sanitizer, no errors.
$ cc -fsanitize=leak -g test.c $ ./a.out Hello, world!
With address sanitizer, no errors.
$ cc -fsanitize=address -g test.c $ ./a.out Hello, world!
With Valgrind, no errors.
$ cc -g test.c $ valgrind ./a.out ==189174== Memcheck, a memory error detector ==189174== Copyright (C) 2002-2017, and GNU GPL'd, by Julian Seward et al. ==189174== Using Valgrind-3.13.0 and LibVEX; rerun with -h for copyright info ==189174== Command: ./a.out ==189174== Hello, world! ==189174== ==189174== HEAP SUMMARY: ==189174== in use at exit: 0 bytes in 0 blocks ==189174== total heap usage: 1 allocs, 1 frees, 1,024 bytes allocated ==189174== ==189174== All heap blocks were freed -- no leaks are possible ==189174== ==189174== For counts of detected and suppressed errors, rerun with: -v ==189174== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 0 from 0)
With heapusage, a leak!
$ cc -g test.c $ ./heapusage ./a.out Hello, world! ==189005== Heapusage - https://github.com/d99kris/heapusage ==189005== ==189005== HEAP SUMMARY: ==189005== in use at exit: 1024 bytes in 1 blocks ==189005== total heap usage: 1 allocs, 0 frees, 1024 bytes allocated ==189005== peak heap usage: 1024 bytes allocated ==189005== ==189005== 1024 bytes in 1 block(s) are lost, originally allocated at: ==189005== at 0x00007f99f0de56a7: malloc + 49 ==189005== at 0x00007f99f0a96a32: _IO_file_doallocate + 114 ==189005== at 0x00007f99f0aa4a46: _IO_doallocbuf + 70 ==189005== at 0x00007f99f0aa3da8: _IO_file_overflow + 472 ==189005== at 0x00007f99f0aa2e86: _IO_file_xsputn + 182 ==189005== at 0x00007f99f0a99033: _IO_puts + 211 ==189005== at 0x000055f667ee7655: ==189005== at 0x00007f99f0a502b1: __libc_start_main + 241 ==189005== at 0x000055f667ee755a: ==189005== ==189005== LEAK SUMMARY: ==189005== definitely lost: 1024 bytes in 1 blocks ==189005==
Heapusage works by hooking malloc and free (and doesn't scan memory for pointers). Heapusage doesn't explain the advantages or disadvantages of this approach fully in the documentation. One advantage is that it's fast, but a disadvantage is that it's not precise.
In particular, I would call out heapusage as giving incorrect messages: the words "definitely lost" don't apply here!
If you want better error messages, use one of the tools recommended above: leak sanitizer or Valgrind (memcheck).
In general, I would also like to remind people that false positives are a fact of life with tools like these. Whether a program is "Valgrind clean" is a different question from whether the program is correct.
| 归档时间: |
|
| 查看次数: |
320 次 |
| 最近记录: |