[matplotlib-devel] memory leak: gtk.gdk.Pixbuf and gtk.gdk.GCX11 with gtkagg backend
Hi, I'm looking for memory leaks in a python application and found leaks in matplotlib. The application is graphic intensive. Each time it updates the screen, matplotlib allocates another 5-10 megabytes memory for the new gtk.gdk.Pixbuf and gtk.gdk.GCX11 while does not free up the buffers allocated for the previous content. I switched on garbage collection debugging with: import gc gc.enable() gc.set_debug(gc.DEBUG_LEAK) and tried to delete the leaking objects: --- ./lib/matplotlib/backends/backend_gtkagg.py 2008-06-23 04:09:29.0 +0200 ++ + /usr/lib/python2.4/site-packages/matplotlib-0.91.4-py2.4-linux-i686.egg/matplotlib/backends/backend_gtkagg.py 2008-10-02 00:05:32.0 +0200 @@ -3,6 +3,7 @@ """ from __future__ import division import os +import gc import matplotlib from matplotlib.figure import Figure @@ -82,8 +83,17 @@ h = int(ren.height) pixbuf = gtk.gdk.pixbuf_new_from_data( buf, gtk.gdk.COLORSPACE_RGB, True, 8, w, h, w*4) -pixmap.draw_pixbuf(pixmap.new_gc(), pixbuf, 0, 0, 0, 0, w, h, + g = pixmap.new_gc() +pixmap.draw_pixbuf(g, pixbuf, 0, 0, 0, 0, w, h, gtk.gdk.RGB_DITHER_NONE, 0, 0) + + print "XX", pixbuf, g,pixbuf.__grefcount__,g.__grefcount__ + print gc.get_referrers(pixbuf) + print gc.get_referrers(g) + del pixbuf + del g + gc.collect() + if DEBUG: print 'FigureCanvasGTKAgg.render_figure done' def blit(self, bbox=None): The __grefcount__ values are 1 but the memory is not freed up even after gc.collect(). - This SF.Net email is sponsored by the Moblin Your Move Developer's challenge Build the coolest Linux based applications with Moblin SDK & win great prizes Grand prize is a trip for two to an Open Source event anywhere in the world http://moblin-contest.org/redirect.php?banner_id=100&url=/ ___ Matplotlib-devel mailing list Matplotlib-devel@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/matplotlib-devel
Re: [matplotlib-devel] memory leak: gtk.gdk.Pixbuf and gtk.gdk.GCX11 with gtkagg backend
Mátyás János wrote: > Hi, > > I'm looking for memory leaks in a python application and found leaks in > matplotlib. The application is graphic intensive. Each time it updates > the screen, matplotlib allocates another 5-10 megabytes memory for the > new gtk.gdk.Pixbuf and gtk.gdk.GCX11 while does not free up the buffers > allocated for the previous content. > This sounds to me like a pygtk bug, not a matplotlib bug; a gtk object is hanging around after its reference has been deleted. What versions of gtk and pygtk are you using? This sounds dimly familiar. I don't know enough about gtk and pygtk to help, but I am sure the people who do know more will want to know the version. Eric > I switched on garbage collection debugging with: > > import gc > gc.enable() > gc.set_debug(gc.DEBUG_LEAK) > > and tried to delete the leaking objects: > > --- ./lib/matplotlib/backends/backend_gtkagg.py 2008-06-23 > 04:09:29.0 +0200 ++ > + > /usr/lib/python2.4/site-packages/matplotlib-0.91.4-py2.4-linux-i686.egg/matplotlib/backends/backend_gtkagg.py > 2008-10-02 00:05:32.0 +0200 @@ -3,6 +3,7 @@ """ > from __future__ import division > import os > +import gc > > import matplotlib > from matplotlib.figure import Figure > @@ -82,8 +83,17 @@ > h = int(ren.height) > pixbuf = gtk.gdk.pixbuf_new_from_data( > buf, gtk.gdk.COLORSPACE_RGB, True, 8, w, h, w*4) > -pixmap.draw_pixbuf(pixmap.new_gc(), pixbuf, 0, 0, 0, 0, w, h, > + g = pixmap.new_gc() > +pixmap.draw_pixbuf(g, pixbuf, 0, 0, 0, 0, w, h, > gtk.gdk.RGB_DITHER_NONE, 0, 0) > + > + print "XX", pixbuf, > g,pixbuf.__grefcount__,g.__grefcount__ > + print gc.get_referrers(pixbuf) > + print gc.get_referrers(g) > + del pixbuf > + del g > + gc.collect() > + > if DEBUG: print 'FigureCanvasGTKAgg.render_figure done' > > def blit(self, bbox=None): > > > The __grefcount__ values are 1 but the memory is not freed up even after > gc.collect(). > > - > This SF.Net email is sponsored by the Moblin Your Move Developer's challenge > Build the coolest Linux based applications with Moblin SDK & win great prizes > Grand prize is a trip for two to an Open Source event anywhere in the world > http://moblin-contest.org/redirect.php?banner_id=100&url=/ > ___ > Matplotlib-devel mailing list > Matplotlib-devel@lists.sourceforge.net > https://lists.sourceforge.net/lists/listinfo/matplotlib-devel - This SF.Net email is sponsored by the Moblin Your Move Developer's challenge Build the coolest Linux based applications with Moblin SDK & win great prizes Grand prize is a trip for two to an Open Source event anywhere in the world http://moblin-contest.org/redirect.php?banner_id=100&url=/ ___ Matplotlib-devel mailing list Matplotlib-devel@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/matplotlib-devel
Re: [matplotlib-devel] spy: ignore zero values in sparse matrix
Hi Eric, Sorry for the late reply. On Sep 27, 2008, at 8:56 PM, Eric Firing wrote: > Actually, I think the most logical thing would be to let the default > None give the old behavior, and require precision=0 to get the new > behavior. What do you think? Is it OK if I make this change? It > is more consistent with the old behavior. I'm ambivalent about this change. On one hand, I think it makes a lot more sense to have None give the old behavior and precision=0 to ignore zero values in the sparse array (then precision would be consistent for finite values and for zero). On the other hand, I think ignoring zero values should be the default behavior for sparse arrays (although, I definitely agree there should be the option to plot all assigned values). Would it be possible to make the change you suggest and also change the default precision value to 0? (see diff below) This change would also allow you to remove a lot of the special handling for precision=None, since precision=0 gives the same result (I didn't go this far in the diff below). > I also changed the behavior so that if a sparse array is input, with > no marker specifications, it simply makes a default marker plot > instead of raising an exception. Excellent idea. That behavior is much more user-friendly. Thanks, -Tony PS. Any comments on the small changes to the examples. Both changes are necessary for those examples to work on my computer (the shebang line throws an error when I run the code from my text editor). Index: matplotlib/lib/matplotlib/axes.py === --- matplotlib/lib/matplotlib/axes.py (revision 6141) +++ matplotlib/lib/matplotlib/axes.py (working copy) @@ -6648,7 +6648,7 @@ return Pxx, freqs, bins, im -def spy(self, Z, precision=None, marker=None, markersize=None, +def spy(self, Z, precision=0., marker=None, markersize=None, aspect='equal', **kwargs): """ call signature:: @@ -6731,14 +6731,11 @@ else: if hasattr(Z, 'tocoo'): c = Z.tocoo() -if precision == 0: +if precision is None: y = c.row x = c.col else: -if precision is None: -nonzero = c.data != 0. -else: -nonzero = np.absolute(c.data) > precision +nonzero = np.absolute(c.data) > precision y = c.row[nonzero] x = c.col[nonzero] else: Index: matplotlib/examples/pylab_examples/masked_demo.py === --- matplotlib/examples/pylab_examples/masked_demo.py (revision 6141) +++ matplotlib/examples/pylab_examples/masked_demo.py (working copy) @@ -1,4 +1,4 @@ -#!/bin/env python +#!/usr/bin/env python ''' Plot lines with points masked out. Index: matplotlib/examples/misc/rec_groupby_demo.py === --- matplotlib/examples/misc/rec_groupby_demo.py(revision 6141) +++ matplotlib/examples/misc/rec_groupby_demo.py(working copy) @@ -2,7 +2,7 @@ import matplotlib.mlab as mlab -r = mlab.csv2rec('data/aapl.csv') +r = mlab.csv2rec('../data/aapl.csv') r.sort() def daily_return(prices): - This SF.Net email is sponsored by the Moblin Your Move Developer's challenge Build the coolest Linux based applications with Moblin SDK & win great prizes Grand prize is a trip for two to an Open Source event anywhere in the world http://moblin-contest.org/redirect.php?banner_id=100&url=/ ___ Matplotlib-devel mailing list Matplotlib-devel@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/matplotlib-devel