Table of Contents
Valgrind
Purpose
Valgrind is a free (GPLv3 licensed) tool you can use to debug memory usage of your program.
For example, I use it to check if I have memory leaks in programs I write in C.
Download
You can go to valgrind.org and download the latest tarball of the Valgrind source code, or install the binary with your package manager.
If you want to compile it, download the tarball and untar it, then :
cd valgrind-*/
mkdir -v build
cd build
../configure
make
sudo make install
Usage
With your own programs
Let’s make this example interactive, we will write a program that allocates and free some memory.
cat << EOF > main.c
#include <stdlib.h>
int main(void)
{
void *a = malloc(1);
free(a);
return 0;
}
EOF
Now compile the program with the following :
gcc main.c
We can then use Valgrind to see if this program as any memory leak.
valgrind ./a.out
The lines that we are interested in are these ones :
==1838== HEAP SUMMARY:
==1838== in use at exit: 0 bytes in 0 blocks
==1838== total heap usage: 1 allocs, 1 frees, 1 bytes allocated
==1838==
==1838== All heap blocks were freed -- no leaks are possible
So we know for sure that this program don’t have any memory leak, but now remove the “free” statement at the end of the program, and recompile it.
sed -i '/free/d' ./main.c
gcc main.c
If you use Valgrind again, you will see these interesting lines :
==1901== LEAK SUMMARY:
==1901== definitely lost: 1 bytes in 1 blocks
Which means we forgot to free some memory in our program. We can use the --leak-check=full flag for more details.
==2173== 1 bytes in 1 blocks are definitely lost in loss record 1 of 1
==2173== at 0x484B8A8: malloc (vg_replace_malloc.c:447)
==2173== by 0x400118E: main (in /home/tutorial/valgrind/a.out)
We only have one malloc in our program, so it is really easy to find from where the memory leak occurs, but let’s suppose that we just can’t find which malloc isn’t freed, you can compile your program with debug info like so :
gcc -g main.c
Now Valgrind can specify the line.
==2197== 1 bytes in 1 blocks are definitely lost in loss record 1 of 1
==2197== at 0x484B8A8: malloc (vg_replace_malloc.c:447)
==2197== by 0x400118E: main (main.c:5)
Some notes
Valgrind executes your code in some kind of “““virtual””” CPU, so the program might run slower when debugging it with Valgrind.
You must know that recent CPU instructions might not be implemented in Valgrind, so if you have a recent CPU, and that you compile programs with optimization flags like -march=native, Valgrind will crash. All of your programs can’t be debugged by Valgrind if you compile glibc with -march=native as the standard library (that is used by all of your programs) will use CPU instructions that aren’t supported by Valgrind.
However, you can still use -mtune=native with for example -march=x86-64 as compatibility will ALL x86_64 CPU will be enabled.
What about MacOS/Windows
If you are on Windows, they advise to use Valgrind in WSL, for MacOS, the leaks programs should be already installed.
To search for memory leaks :
leaks --atExit -- ./a.out