Reputation: 41
We are trying to figure out memory leaks in a C++ application running on Linux. We are using Valgrind 3.6.0 and have been able to get few "definitely lost" stacks. In the report, it also gave total number of "definitely lost" bytes.
The fix that we had to include was this: changed delete ptr
to delete[] ptr
where ptr
is pointing to an array of locations on heap.
Please note that ptr was holding good amount of memory. And we had fixed many other deletions similarly. Hence, we were expecting leaks to reduce.
But after the fix, strangely Valgrind still reported the same number of leaks as before, in the summary.
==00:00:15:13.661 14014== LEAK SUMMARY:
==00:00:15:13.661 14014== definitely lost: 236 bytes in 8 blocks
==00:00:15:13.661 14014== indirectly lost: 22,113 bytes in 17 blocks
==00:00:15:13.662 14014== possibly lost: 695,006 bytes in 47 blocks
==00:00:15:13.662 14014== still reachable: 2,056,059 bytes in 732 blocks
==00:00:15:13.662 14014== suppressed: 0 bytes in 0 blocks
Can someone shed some light on this behavior of Valgrind? We are using all the right options to invoke mem_check tool etc.
Upvotes: 1
Views: 664
Reputation: 9220
The answer is that the block that was being freed with the wrong sort of delete
was never included in the leak report in the first place because valgrind
realised that wrong sort of delete
was used and reported that and freed up the whole block.
We can see this effect with a simple program:
int main(int argc, char **argv)
{
int *x = new int[20];
delete x;
return x != 0;
}
Which, when run under valgrind
, reports:
==12212== Mismatched free() / delete / delete []
==12212== at 0x61DCD1FC: operator delete(void*) (in /usr/lib64/valgrind/vgpreload_memcheck-amd64-linux.so)
==12212== by 0x4005AC: main (x.c:7 in /tmp/x)
==12212== Address 0x61fd4040 is 0 bytes inside a block of size 80 alloc'd
==12212== at 0x61DCD967: operator new[](unsigned long) (in /usr/lib64/valgrind/vgpreload_memcheck-amd64-linux.so)
==12212== by 0x40059C: main (x.c:5 in /tmp/x)
==12212==
==12212==
==12212== HEAP SUMMARY:
==12212== in use at exit: 0 bytes in 0 blocks
==12212== total heap usage: 1 allocs, 1 frees, 80 bytes allocated
==12212==
==12212== All heap blocks were freed -- no leaks are possible
So it has told you about the wrong sort of delete
being used but then reported no leaks because it has in fact freed the whole block once it realised your mistake.
The things it is reporting as leaks are things you haven't tried to free at all, and if you read the leak report which should have preceded that leak summary then valgrind
will have told you exactly where all the leaked memory was allocated and you should be able to track those leaks down and fix them.
Upvotes: 1