Jump to content

Calligra/UsingValgrind

From KDE Community Wiki
Revision as of 00:39, 19 January 2011 by Nalvarez (talk | contribs) (fix tons of formatting)
(diff) ← Older revision | Latest revision (diff) | Newer revision → (diff)

Let's find a problem with valgrind.

Preparing your program

Compile your program with -g to include debugging information so that Memcheck's error messages include exact line numbers. Using -O0 is also a good idea, if you can tolerate the slowdown. With -O1 line numbers in error messages can be inaccurate, although generally speaking running Memcheck on code compiled at -O1 works fairly well. Use of -O2 and above is not recommended as Memcheck occasionally reports uninitialised-value errors which don't really exist.

Running your program under Memcheck

If you normally run your program like this:

myprog arg1 arg2

Use this command line:

valgrind --leak-check=yes myprog arg1 arg2

Memcheck is the default tool. The --leak-check option turns on the detailed memory leak detector. Your program will run much slower (eg. 20 to 30 times) than normal, and use a lot more memory. Memcheck will issue messages about memory errors and leaks that it detects.

Interpreting Memcheck's output

Here's an example C program, in a file called a.c, with a memory error and a memory leak.

#include <stdlib.h>
void f(void) {
   int* x = malloc(10 * sizeof(int)); x[10] = 0; // problem 1: heap block overrun
 } // problem 2: memory leak -- x not freed
 int main(void) {
    f(); return 0;
 }

Most error messages look like the following, which describes problem 1, the heap block overrun:

==19182== Invalid write of size 4
==19182== at 0x804838F: f (example.c:6)
==19182== by 0x80483AB: main (example.c:11)
==19182== Address 0x1BA45050 is 0 bytes after a block of size 40 alloc'd  
==19182== at 0x1B8FF5CD: malloc (vg_replace_malloc.c:130)
==19182== by 0x8048385: f (example.c:5)  
==19182== by 0x80483AB: main (example.c:11)

Things to notice

The first line ("Invalid write...") tells you what kind of error it is. Here, the program wrote to some memory it should not have due to a heap block overrun.

Some error messages have a second component which describes the memory address involved. This one shows that the written memory is just past the end of a block allocated with malloc() on line 5 of example.c.

Memory leak messages look like this:

==19182== 40 bytes in 1 blocks are definitely lost in loss record 1 of 1
==19182== at 0x1B8FF5CD: malloc (vg_replace_malloc.c:130)
==19182== by 0x8048385: f (a.c:5)
==19182== by 0x80483AB: main (a.c:11)

The stack trace tells you where the leaked memory was allocated. Memcheck cannot tell you why the memory leaked, unfortunately. (Ignore the "vg_replace_malloc.c", that's an implementation detail.)