MEMCHECK TIPS

  • Execute until the program terminates. Memcheck identifies numerous leaks upon conclusion.
  • Prioritize testing an optimized version initially. An unoptimized version exhibits distinct errors.
  • Employ personalized memory handling? Import valgrind/valgrind.h and resort to standard malloc and free if RUNNING_ON_VALGRIND macro evaluates to true.
  • Opt for customized alloc functions? Notify valgrind of their usage via VALGRIND_MALLOCLIKE_BLOCK + VALGRIND_FREELIKE_BLOCK.

MEMCHECK

Valgrind provides a suite of debugging tools to increase performance and fix problems with your programs. Memcheck is one of the more commonly used tools. This tool helps find memory-related errors that might cause your program to crash or leak memory.

Make sure you compile your program with -g to generate debugging symbols. Both GDB and Valgrind use these symbols to show line numbers in error messages. For more on compilation, see the gcc wiki.

Compile with debugging symbols.

g++ -Wall -std=c++11 -g program.cpp -o program

The MemCheck tool in Valgrind runs by default, so you don’t have to specify --tool=memcheck when running Valgrind. However, you can use the option to be explicit.

Detect common memory errors in ./program.

valgrind ./program args
valgrind --tool=memcheck ./program args

Detect memory errors and memory leaks.

valgrind --leak-check=yes ./program

Run with more verbose for helpful error messages.

valgrind --tool=memcheck --leak-check=full ./program

Take longer and trace the origin of uninitialized values.

valgrind --leak-check=yes --track-origins=yes ./program

Detect unclosed file descriptors.

valgrind --track-fds=yes ./program

Produce a xtmemory.kcg file.
Install KCachegrind to examine it.
It shows a visual backtrace of places in the code that leaked memory.

valgrind --xtree-memory=full --leak-check=yes ./program

Run silently.
Return a failure exit code if errors are found, rather than ./program exit code.
Useful in automated tests.

valgrind --error-exitcode=1 ./program

MEMCHECK ERRORS

Use of an uninitialized variable.
Memcheck prints the backtrace where the value was used.
--track-origins=yes can find where it came from.

Conditional jump or move depends on the uninitialized value(s)
    at 0x402DFA94: _IO_vfprintf (_itoa.h:49)
    by 0x402E8476: _IO_printf (printf.c:36)
    by 0x8048472: main (tests/manuel1.c:8)

Read from memory that is not allocated.
In this case in unused stack memory below the stack.
Often Memcheck can say β€œin freed memory” etc.

Invalid read of size 4
    at 0x40F6BBCC: (within /usr/lib/libpng.so.2.1.0.9)
    ...
Address 0xBFFFF0E0 is not stack'd, malloc'd or free'd

Other common errors detected are invalid pointers in system calls, double frees, mixing new/free, overlapping memcpy and realloc(0).