Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Python - Memory Leak

I'm working on solving a memory leak in my Python application.

Here's the thing - it really only appears to happen on Windows Server 2008 (not R2) but not earlier versions of Windows, and it also doesn't look like it's happening on Linux (although I haven't done nearly as much testing on Linux).

To troubleshoot it, I set up debugging on the garbage collector:

gc.set_debug(gc.DEBUG_UNCOLLECTABLE | gc.DEBUG_INSTANCES | gc.DEBUG_OBJECTS)

Then, periodically, I log the contents of gc.garbage.

Thing is, gc.garbage is always empty, yet my memory usage goes up and up and up.

Very puzzling.

like image 423
Dave Avatar asked Apr 20 '10 21:04

Dave


People also ask

Can Python have memory leaks?

The Python program, just like other programming languages, experiences memory leaks. Memory leaks in Python happen if the garbage collector doesn't clean and eliminate the unreferenced or unused data from Python.

How do I find a memory leak in Python?

You can detect memory leaks in Python by monitoring your Python app's performance via an Application Performance Monitoring tool such as Scout APM. Once you detect a memory leak, there are multiple ways to solve it.

How do I check for memory leaks?

The primary tools for detecting memory leaks are the C/C++ debugger and the C Run-time Library (CRT) debug heap functions. The #define statement maps a base version of the CRT heap functions to the corresponding debug version. If you leave out the #define statement, the memory leak dump will be less detailed.

Can memory leaks be fixed?

In most cases, you can fix the Windows 10 memory leak issues yourself. You can close resource-intensive apps, disable certain startup apps, and perform similar tasks to fix a memory leak.


2 Answers

If there's never any garbage in gc.garbage, then I'm not sure what you're trying to do by enabling GC debugging. Sure, it'll tell you which objects are considered for cleanup, but that's not particularly interesting if you end up with no circular references that can't be cleaned up.

If your program is using more and more memory according to the OS, there can generally be four different cases at play:

  1. Your application is storing more and more things, keeping references to each one so they don't get collected.
  2. Your application is creating circular references between objects that can't be cleaned up by the gc module (typically because one of them has a __del__ method.)
  3. Your application is freeing (and re-using) memory, but the OS doesn't want the memory re-used, so it keeps allocating new blocks of memory.
  4. The leak is a real memory leak but in a C/C++ extension module your code is using.

From your description it sounds like it's unlikely to be #1 (as it would behave the same on any OS) and apparently not #2 either (since there's nothing in gc.garbage.) Considering #3, Windows (in general) has a memory allocator that's notoriously bad with fragmented allocations, but Python works around this with its obmalloc frontend for malloc(). It may still be an issue specific in Windows Server 2008 system libraries that make it look like your application is using more and more memory, though. Or it may be a case of #4, a C/C++ extension module, or a DLL used by Python or an extension module, with a memory leak.

like image 192
Thomas Wouters Avatar answered Sep 20 '22 13:09

Thomas Wouters


In general, the first culprit for memory leaks in python is to be found in C extensions.
Do you use any of them?

Furthermore, you say the issue happens only on 2008; I would then check extensions for any incompatibility, because with Vista and 2008 there were quite a lot of small changes that caused issues on that field.
As and alternative, try to execute your application in Windows compatibility mode, choosing Windows XP - this could help solving the issue, especially if it's related to changes in the security.

like image 21
rob Avatar answered Sep 19 '22 13:09

rob