Memory leaks are a killer of long running applications - memory usage keeps growing until finally the memory supply is exhausted and it's "game over". If you’re lucky the system recognizes your application is at fault and terminates it. If you’re unlucky, the system itself will crash.
Memory leaks happen when processes allocate memory and forget to release it. C and C++ developers, we know this type of memory as heap memory obtained by calls to malloc or new, for example. Fortran90 coders know this as allocatable memory - and use the allocateprimitive.
Allocatable memory is great but the infinite memory machine does not exist so you must take care to release the memory when you are done with it - allowing your application to reuse it the next time it needs some memory.
When you forget to deallocate, you’ve made a leak. If allocation happens repeatedly without being deallocated - your application will fail! C and C++ users know particularly well that allocations happen everywhere - so finding the leak can be a challenge.
One of my applications is dying - I know it’s due to memory exhaustion because “top” shows consumption growing, the machine is starting to whirr and grind at the disk as the swap memory kicks in, and finally the machine drops off the planet.
I fire up my favourite debugger - Arm DDT - it has a great built-in memory leak detector. This finds the most prominent leaks, and lets you fix them. I simply tick the “Memory Debugging” option when starting to debug the application.
After a few minutes, I pull up a chart to see how my memory is doing. This is a multi-process application using the MPI library - and one of the processes looks to be using more memory than the others.
Something big is stirring on Process 0
Arm DDT remembers the stack trace for each allocation, so that you can pinpoint which part of your code is wasting memory. I click on the largest block in bar chart (Packet::allocate on Process 0) to bring up the details.
Pinpointed!
That was handy - I know how large the allocation is and where it came from. I click again and Arm DDT leaps to the source code of my application!
The line of allocation
Things are clear straight away.
Packet object “p” is allocating memory - and the memory is used but when “p” goes out of scope it never calls deallocate. That was clumsy but it is easy to fix now, thanks to Arm DDT!
Read more about what the memory debugger can help with by visiting the memory debugging in Arm DDT page.