twinx memory leak

I think i narrowed down the memory leak i have been chasing for a while.
If i remove the call to twinx i get a slow leak, which would cause me trouble
after a very long time. With the call to twinx, however i am losing thousands of objects
at each loop.

Thanks,

Laurent

import pylab as PL
def looptest():
while(1):
fig=PL.figure(1)
ax=fig.add_subplot(211)
ax.set_position((0,0,0.9,0.45))
ax1=PL.twinx(ax)
t=range(1000)
st=[math.sin(x*0.01) for x in t]
ax.plot(t,st)
fig.clf()
PL.close(1)
gc.collect()
print “GC”
print len(gc.get_objects())
print len(gc.garbage)
looptest()

···

i forgot two imports.

import math
import gc
import pylab as PL

def looptest():
while(1):
fig=PL.figure(1)
ax=fig.add_subplot(211)
ax.set_position((0,0,0.9,0.45))
ax1=PL.twinx(ax)
t=range(1000)
st=[math.sin(x*0.01) for x in t]
ax.plot(t,st)
fig.clf()
PL.close(1)
gc.collect()
print “GC”
print len(gc.get_objects())
print len(gc.garbage)
looptest()

2008/7/11 laurent oget <laurent@…2078…>:

···

I think i narrowed down the memory leak i have been chasing for a while.
If i remove the call to twinx i get a slow leak, which would cause me trouble
after a very long time. With the call to twinx, however i am losing thousands of objects

at each loop.

Thanks,

Laurent

import pylab as PL
def looptest():
while(1):

    fig=PL.figure(1)
    ax=fig.add_subplot(211)
    ax.set_position((0,0,0.9,0.45))
    ax1=PL.twinx(ax)
    t=range(1000)
    st=[math.sin(x*0.01) for x in t]
    ax.plot(t,st)


    fig.clf()
    PL.close(1)
    gc.collect()
    print "GC"
    print len(gc.get_objects())
    print len(gc.garbage)

looptest()

Thanks for the report. So we can diagnose this, what version of matplotlib are you reporting this for?

Also, you may be interested in the following FAQ (and the one following it):

http://matplotlib.sourceforge.net/faq.html#LEAKS

Cheers,
Mike

laurent oget wrote:

···

i forgot two imports.

>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
import math
import gc
import pylab as PL

def looptest():
    while(1):
        fig=PL.figure(1)
        ax=fig.add_subplot(211)
        ax.set_position((0,0,0.9,0.45))
        ax1=PL.twinx(ax)
        t=range(1000)
        st=[math.sin(x*0.01) for x in t]
        ax.plot(t,st)
        fig.clf()
        PL.close(1)
        gc.collect()
        print "GC"
        print len(gc.get_objects())
        print len(gc.garbage)
looptest()
>>>>>>>>>>>>>>>>>>>>>>>>>>>>

2008/7/11 laurent oget <laurent@…2078… <mailto:laurent@…2078…>>:

    I think i narrowed down the memory leak i have been chasing for a
    while.
    If i remove the call to twinx i get a slow leak, which would cause
    me trouble
    after a very long time. With the call to twinx, however i am
    losing thousands of objects
    at each loop.

    Thanks,

    Laurent

    >>>>>>>>>>>>>>>>>>>>>>>>> import pylab as PL
    def looptest():
        while(1):
            fig=PL.figure(1)
            ax=fig.add_subplot(211)
            ax.set_position((0,0,0.9,0.45))
            ax1=PL.twinx(ax)
            t=range(1000)
            st=[math.sin(x*0.01) for x in t]
            ax.plot(t,st)
            fig.clf()
            PL.close(1)
            gc.collect()
            print "GC"
            print len(gc.get_objects())
            print len(gc.garbage)
    looptest()
    >>>>>>>>>>>>>>>>>>>>>>>>>>>

------------------------------------------------------------------------

-------------------------------------------------------------------------
Sponsored by: SourceForge.net Community Choice Awards: VOTE NOW!
Studies have shown that voting for your favorite open source project,
along with a healthy diet, reduces your potential for chronic lameness
and boredom. Vote Now at http://www.sourceforge.net/community/cca08
------------------------------------------------------------------------

_______________________________________________
Matplotlib-users mailing list
Matplotlib-users@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/matplotlib-users
  
--
Michael Droettboom
Science Software Branch
Operations and Engineering Division
Space Telescope Science Institute
Operated by AURA for NASA

Michael Droettboom wrote:

Thanks for the report. So we can diagnose this, what version of matplotlib are you reporting this for?

Also, you may be interested in the following FAQ (and the one following it):

http://matplotlib.sourceforge.net/faq.html#LEAKS

Hi,

   I tested this with the lastest svn, and I do also see a leak. But it's not related to twinx, but to pylab.close(). If I just comment out this one line, the memleak disappears ...

Manuel

···

Cheers,
Mike

laurent oget wrote:

i forgot two imports.

import math
import gc
import pylab as PL

def looptest():
    while(1):
        fig=PL.figure(1)
        ax=fig.add_subplot(211)
        ax.set_position((0,0,0.9,0.45))
        ax1=PL.twinx(ax)
        t=range(1000)
        st=[math.sin(x*0.01) for x in t]
        ax.plot(t,st)
        fig.clf()
        PL.close(1)
        gc.collect()
        print "GC"
        print len(gc.get_objects())
        print len(gc.garbage)
looptest()
2008/7/11 laurent oget <laurent@…2078… <mailto:laurent@…2078…>>:

    I think i narrowed down the memory leak i have been chasing for a
    while.
    If i remove the call to twinx i get a slow leak, which would cause
    me trouble
    after a very long time. With the call to twinx, however i am
    losing thousands of objects
    at each loop.

    Thanks,

    Laurent

    >>>>>>>>>>>>>>>>>>>>>>>>> import pylab as PL
    def looptest():
        while(1):
            fig=PL.figure(1)
            ax=fig.add_subplot(211)
            ax.set_position((0,0,0.9,0.45))
            ax1=PL.twinx(ax)
            t=range(1000)
            st=[math.sin(x*0.01) for x in t]
            ax.plot(t,st)
            fig.clf()
            PL.close(1)
            gc.collect()
            print "GC"
            print len(gc.get_objects())
            print len(gc.garbage)
    looptest()
    >>>>>>>>>>>>>>>>>>>>>>>>>>>

------------------------------------------------------------------------

-------------------------------------------------------------------------
Sponsored by: SourceForge.net Community Choice Awards: VOTE NOW!
Studies have shown that voting for your favorite open source project,
along with a healthy diet, reduces your potential for chronic lameness
and boredom. Vote Now at http://www.sourceforge.net/community/cca08
------------------------------------------------------------------------

_______________________________________________
Matplotlib-users mailing list
Matplotlib-users@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/matplotlib-users
  

Which backend?

Cheers,
Mike

Manuel Metz wrote:

···

Michael Droettboom wrote:

Thanks for the report. So we can diagnose this, what version of matplotlib are you reporting this for?

Also, you may be interested in the following FAQ (and the one following it):

http://matplotlib.sourceforge.net/faq.html#LEAKS

Hi,

  I tested this with the lastest svn, and I do also see a leak. But it's not related to twinx, but to pylab.close(). If I just comment out this one line, the memleak disappears ...

Manuel

Cheers,
Mike

laurent oget wrote:

i forgot two imports.

import math
import gc
import pylab as PL

def looptest():
    while(1):
        fig=PL.figure(1)
        ax=fig.add_subplot(211)
        ax.set_position((0,0,0.9,0.45))
        ax1=PL.twinx(ax)
        t=range(1000)
        st=[math.sin(x*0.01) for x in t]
        ax.plot(t,st)
        fig.clf()
        PL.close(1)
        gc.collect()
        print "GC"
        print len(gc.get_objects())
        print len(gc.garbage)
looptest()
2008/7/11 laurent oget <laurent@…2078… <mailto:laurent@…2078…>>:

    I think i narrowed down the memory leak i have been chasing for a
    while.
    If i remove the call to twinx i get a slow leak, which would cause
    me trouble
    after a very long time. With the call to twinx, however i am
    losing thousands of objects
    at each loop.

    Thanks,

    Laurent

    >>>>>>>>>>>>>>>>>>>>>>>>> import pylab as PL
    def looptest():
        while(1):
            fig=PL.figure(1)
            ax=fig.add_subplot(211)
            ax.set_position((0,0,0.9,0.45))
            ax1=PL.twinx(ax)
            t=range(1000)
            st=[math.sin(x*0.01) for x in t]
            ax.plot(t,st)
            fig.clf()
            PL.close(1)
            gc.collect()
            print "GC"
            print len(gc.get_objects())
            print len(gc.garbage)
    looptest()
    >>>>>>>>>>>>>>>>>>>>>>>>>>>

------------------------------------------------------------------------

-------------------------------------------------------------------------

Sponsored by: SourceForge.net Community Choice Awards: VOTE NOW!
Studies have shown that voting for your favorite open source project,
along with a healthy diet, reduces your potential for chronic lameness
and boredom. Vote Now at http://www.sourceforge.net/community/cca08
------------------------------------------------------------------------

_______________________________________________
Matplotlib-users mailing list
Matplotlib-users@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/matplotlib-users
  
--
Michael Droettboom
Science Software Branch
Operations and Engineering Division
Space Telescope Science Institute
Operated by AURA for NASA

Michael Droettboom wrote:

Which backend?

GTK, GTKAgg, TK, but not with any backend without a window: Agg, Cairo, PS, PDF, SVG ...

Cheers,
   Manuel

···

Cheers,
Mike

Manuel Metz wrote:

Michael Droettboom wrote:

Thanks for the report. So we can diagnose this, what version of matplotlib are you reporting this for?

Also, you may be interested in the following FAQ (and the one following it):

http://matplotlib.sourceforge.net/faq.html#LEAKS

Hi,

  I tested this with the lastest svn, and I do also see a leak. But it's not related to twinx, but to pylab.close(). If I just comment out this one line, the memleak disappears ...

Manuel

Cheers,
Mike

laurent oget wrote:

i forgot two imports.

import math
import gc
import pylab as PL

def looptest():
    while(1):
        fig=PL.figure(1)
        ax=fig.add_subplot(211)
        ax.set_position((0,0,0.9,0.45))
        ax1=PL.twinx(ax)
        t=range(1000)
        st=[math.sin(x*0.01) for x in t]
        ax.plot(t,st)
        fig.clf()
        PL.close(1)
        gc.collect()
        print "GC"
        print len(gc.get_objects())
        print len(gc.garbage)
looptest()
2008/7/11 laurent oget <laurent@…2078… <mailto:laurent@…2078…>>:

    I think i narrowed down the memory leak i have been chasing for a
    while.
    If i remove the call to twinx i get a slow leak, which would cause
    me trouble
    after a very long time. With the call to twinx, however i am
    losing thousands of objects
    at each loop.

    Thanks,

    Laurent

    >>>>>>>>>>>>>>>>>>>>>>>>> import pylab as PL
    def looptest():
        while(1):
            fig=PL.figure(1)
            ax=fig.add_subplot(211)
            ax.set_position((0,0,0.9,0.45))
            ax1=PL.twinx(ax)
            t=range(1000)
            st=[math.sin(x*0.01) for x in t]
            ax.plot(t,st)
            fig.clf()
            PL.close(1)
            gc.collect()
            print "GC"
            print len(gc.get_objects())
            print len(gc.garbage)
    looptest()
    >>>>>>>>>>>>>>>>>>>>>>>>>>>

------------------------------------------------------------------------

-------------------------------------------------------------------------

Sponsored by: SourceForge.net Community Choice Awards: VOTE NOW!
Studies have shown that voting for your favorite open source project,
along with a healthy diet, reduces your potential for chronic lameness
and boredom. Vote Now at http://www.sourceforge.net/community/cca08
------------------------------------------------------------------------

_______________________________________________
Matplotlib-users mailing list
Matplotlib-users@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/matplotlib-users
  

I can confirm this.

Commenting out "del Gcf.figs[num]" in Gcf.destroy (in _pylab_helpers.py) also seems to resolve the leak. But I have no idea why, so I won't commit it just yet. I don't have much time to look deeper now. Does anyone (who probably understands figure management better than me) have an idea what might cause this?

Cheers,
Mike

Manuel Metz wrote:

···

Michael Droettboom wrote:

Which backend?

GTK, GTKAgg, TK, but not with any backend without a window: Agg, Cairo, PS, PDF, SVG ...

Cheers,
  Manuel

Cheers,
Mike

Manuel Metz wrote:

Michael Droettboom wrote:

Thanks for the report. So we can diagnose this, what version of matplotlib are you reporting this for?

Also, you may be interested in the following FAQ (and the one following it):

http://matplotlib.sourceforge.net/faq.html#LEAKS

Hi,

  I tested this with the lastest svn, and I do also see a leak. But it's not related to twinx, but to pylab.close(). If I just comment out this one line, the memleak disappears ...

Manuel

Cheers,
Mike

laurent oget wrote:

i forgot two imports.

import math
import gc
import pylab as PL

def looptest():
    while(1):
        fig=PL.figure(1)
        ax=fig.add_subplot(211)
        ax.set_position((0,0,0.9,0.45))
        ax1=PL.twinx(ax)
        t=range(1000)
        st=[math.sin(x*0.01) for x in t]
        ax.plot(t,st)
        fig.clf()
        PL.close(1)
        gc.collect()
        print "GC"
        print len(gc.get_objects())
        print len(gc.garbage)
looptest()
2008/7/11 laurent oget <laurent@…2078… <mailto:laurent@…2078…>>:

    I think i narrowed down the memory leak i have been chasing for a
    while.
    If i remove the call to twinx i get a slow leak, which would cause
    me trouble
    after a very long time. With the call to twinx, however i am
    losing thousands of objects
    at each loop.

    Thanks,

    Laurent

    >>>>>>>>>>>>>>>>>>>>>>>>> import pylab as PL
    def looptest():
        while(1):
            fig=PL.figure(1)
            ax=fig.add_subplot(211)
            ax.set_position((0,0,0.9,0.45))
            ax1=PL.twinx(ax)
            t=range(1000)
            st=[math.sin(x*0.01) for x in t]
            ax.plot(t,st)
            fig.clf()
            PL.close(1)
            gc.collect()
            print "GC"
            print len(gc.get_objects())
            print len(gc.garbage)
    looptest()
    >>>>>>>>>>>>>>>>>>>>>>>>>>>

------------------------------------------------------------------------

-------------------------------------------------------------------------

Sponsored by: SourceForge.net Community Choice Awards: VOTE NOW!
Studies have shown that voting for your favorite open source project,
along with a healthy diet, reduces your potential for chronic lameness
and boredom. Vote Now at http://www.sourceforge.net/community/cca08
------------------------------------------------------------------------

_______________________________________________
Matplotlib-users mailing list
Matplotlib-users@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/matplotlib-users
  
--
Michael Droettboom
Science Software Branch
Operations and Engineering Division
Space Telescope Science Institute
Operated by AURA for NASA

Can you post the script you are using to test -- I am a little
confused from reading this thread by whether or not twinx is
implicated. Also, I saw that you committed some changes vis-a-vis the
twinx leak

  r5747 | mdboom | 2008-07-11 13:21:53 -0500 (Fri, 11 Jul 2008) | 2 lines

  Fix memory leak when using shared axes.

so I thought that part was resolved already...

JDH

···

On Mon, Jul 14, 2008 at 3:05 PM, Michael Droettboom <mdroe@...86...> wrote:

I can confirm this.

Commenting out "del Gcf.figs[num]" in Gcf.destroy (in _pylab_helpers.py)
also seems to resolve the leak. But I have no idea why, so I won't
commit it just yet. I don't have much time to look deeper now. Does
anyone (who probably understands figure management better than me) have
an idea what might cause this?

John Hunter wrote:

I can confirm this.

Commenting out "del Gcf.figs[num]" in Gcf.destroy (in _pylab_helpers.py)
also seems to resolve the leak. But I have no idea why, so I won't
commit it just yet. I don't have much time to look deeper now. Does
anyone (who probably understands figure management better than me) have
an idea what might cause this?

Can you post the script you are using to test -- I am a little
confused from reading this thread by whether or not twinx is
implicated. Also, I saw that you committed some changes vis-a-vis the
twinx leak

  r5747 | mdboom | 2008-07-11 13:21:53 -0500 (Fri, 11 Jul 2008) | 2 lines

  Fix memory leak when using shared axes.

so I thought that part was resolved already...

JDH

I use a modified version of the script Laurent Oget posted (see attachment). Here is the output if I don't comment out PL.close(1).

~/python/test$ python looptest.py -dGTK
0 GC 69354 69354 0 13854
100 GC 84354 150 0 15163
200 GC 99354 150 0 16306
300 GC 114354 150 0 17364
400 GC 129354 150 0 18576
~/python/test$ python looptest.py -dTK
0 GC 69521 69521 0 14065
100 GC 84521 150 0 15444
200 GC 99521 150 0 16581
300 GC 114521 150 0 17719
400 GC 129521 150 0 18715
~/python/test$ python looptest.py -dPS
0 GC 59307 59307 0 7705
100 GC 59307 0 0 8037
200 GC 59307 0 0 8038
300 GC 59307 0 0 8038
400 GC 59307 0 0 8038

(so for the window-less backend PS no objects are left)

And now I commented out the line PL.close(1):

~/python/test$ python looptest.py -dGTK
0 GC 69379 69379 0 13855
100 GC 69379 0 0 14253
200 GC 69379 0 0 14253
300 GC 69379 0 0 14253
400 GC 69379 0 0 14252

Manuel

looptest.py (787 Bytes)

···

On Mon, Jul 14, 2008 at 3:05 PM, Michael Droettboom <mdroe@...86...> wrote:

Yes, as of r5747 twinx (well, shared axes specifically) no longer leaks.

Manuel has discovered a seemingly generic leak that occurs when pyplot.close() is called and running a GUI backend. I can confirm his results with the script he last sent.

Cheers,
Mike

Manuel Metz wrote:

···

John Hunter wrote:

On Mon, Jul 14, 2008 at 3:05 PM, Michael Droettboom <mdroe@...86...> >> wrote:

I can confirm this.

Commenting out "del Gcf.figs[num]" in Gcf.destroy (in _pylab_helpers.py)
also seems to resolve the leak. But I have no idea why, so I won't
commit it just yet. I don't have much time to look deeper now. Does
anyone (who probably understands figure management better than me) have
an idea what might cause this?

Can you post the script you are using to test -- I am a little
confused from reading this thread by whether or not twinx is
implicated. Also, I saw that you committed some changes vis-a-vis the
twinx leak

  r5747 | mdboom | 2008-07-11 13:21:53 -0500 (Fri, 11 Jul 2008) | 2 lines

  Fix memory leak when using shared axes.

so I thought that part was resolved already...

JDH

I use a modified version of the script Laurent Oget posted (see attachment). Here is the output if I don't comment out PL.close(1).

~/python/test$ python looptest.py -dGTK
0 GC 69354 69354 0 13854
100 GC 84354 150 0 15163
200 GC 99354 150 0 16306
300 GC 114354 150 0 17364
400 GC 129354 150 0 18576
~/python/test$ python looptest.py -dTK
0 GC 69521 69521 0 14065
100 GC 84521 150 0 15444
200 GC 99521 150 0 16581
300 GC 114521 150 0 17719
400 GC 129521 150 0 18715
~/python/test$ python looptest.py -dPS
0 GC 59307 59307 0 7705
100 GC 59307 0 0 8037
200 GC 59307 0 0 8038
300 GC 59307 0 0 8038
400 GC 59307 0 0 8038

(so for the window-less backend PS no objects are left)

And now I commented out the line PL.close(1):

~/python/test$ python looptest.py -dGTK
0 GC 69379 69379 0 13855
100 GC 69379 0 0 14253
200 GC 69379 0 0 14253
300 GC 69379 0 0 14253
400 GC 69379 0 0 14252

Manuel

--
Michael Droettboom
Science Software Branch
Operations and Engineering Division
Space Telescope Science Institute
Operated by AURA for NASA

I am puzzled. Wasn’t the whole point of close() to avoid memory leaks?

Laurent

2008/7/15 Michael Droettboom <mdroe@…86…>:

···

Yes, as of r5747 twinx (well, shared axes specifically) no longer leaks.

Manuel has discovered a seemingly generic leak that occurs when

pyplot.close() is called and running a GUI backend. I can confirm his

results with the script he last sent.

Cheers,

Mike

Manuel Metz wrote:

John Hunter wrote:

On Mon, Jul 14, 2008 at 3:05 PM, Michael Droettboom <mdroe@…86…> > > >> wrote:

I can confirm this.

Commenting out “del Gcf.figs[num]” in Gcf.destroy (in

_pylab_helpers.py)

also seems to resolve the leak. But I have no idea why, so I won’t

commit it just yet. I don’t have much time to look deeper now. Does

anyone (who probably understands figure management better than me) have

an idea what might cause this?

Can you post the script you are using to test – I am a little

confused from reading this thread by whether or not twinx is

implicated. Also, I saw that you committed some changes vis-a-vis the

twinx leak

r5747 | mdboom | 2008-07-11 13:21:53 -0500 (Fri, 11 Jul 2008) | 2

lines

Fix memory leak when using shared axes.

so I thought that part was resolved already…

JDH

I use a modified version of the script Laurent Oget posted (see

attachment). Here is the output if I don’t comment out PL.close(1).

~/python/test$ python looptest.py -dGTK

0 GC 69354 69354 0 13854

100 GC 84354 150 0 15163

200 GC 99354 150 0 16306

300 GC 114354 150 0 17364

400 GC 129354 150 0 18576

~/python/test$ python looptest.py -dTK

0 GC 69521 69521 0 14065

100 GC 84521 150 0 15444

200 GC 99521 150 0 16581

300 GC 114521 150 0 17719

400 GC 129521 150 0 18715

~/python/test$ python looptest.py -dPS

0 GC 59307 59307 0 7705

100 GC 59307 0 0 8037

200 GC 59307 0 0 8038

300 GC 59307 0 0 8038

400 GC 59307 0 0 8038

(so for the window-less backend PS no objects are left)

And now I commented out the line PL.close(1):

~/python/test$ python looptest.py -dGTK

0 GC 69379 69379 0 13855

100 GC 69379 0 0 14253

200 GC 69379 0 0 14253

300 GC 69379 0 0 14253

400 GC 69379 0 0 14252

Manuel

Michael Droettboom

Science Software Branch

Operations and Engineering Division

Space Telescope Science Institute

Operated by AURA for NASA


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-users mailing list

Matplotlib-users@lists.sourceforge.net

https://lists.sourceforge.net/lists/listinfo/matplotlib-users

Yes, it should be. I'm further puzzled that removing "del Gcf.figs[num]" prevents the memory leak. There is some side effect that happens when all of the figures have been closed (I think it shuts down the GUI mainloop), that keeping at least one figure around at all times avoids. But I haven't been able to get to the bottom of that, just a half-supported theory at this point.

Cheers,
Mike

laurent oget wrote:

···

I am puzzled. Wasn't the whole point of close() to avoid memory leaks?

Laurent

2008/7/15 Michael Droettboom <mdroe@…86… <mailto:mdroe@…86…>>:

    Yes, as of r5747 twinx (well, shared axes specifically) no longer
    leaks.

    Manuel has discovered a seemingly generic leak that occurs when
    pyplot.close() is called and running a GUI backend. I can confirm his
    results with the script he last sent.

    Cheers,
    Mike

    Manuel Metz wrote:
    > John Hunter wrote:
    >> On Mon, Jul 14, 2008 at 3:05 PM, Michael Droettboom > <mdroe@…86… <mailto:mdroe@…86…>> > >> wrote:
    >>> I can confirm this.
    >>>
    >>> Commenting out "del Gcf.figs[num]" in Gcf.destroy (in
    >>> _pylab_helpers.py)
    >>> also seems to resolve the leak. But I have no idea why, so I
    won't
    >>> commit it just yet. I don't have much time to look deeper
    now. Does
    >>> anyone (who probably understands figure management better than
    me) have
    >>> an idea what might cause this?
    >>
    >> Can you post the script you are using to test – I am a little
    >> confused from reading this thread by whether or not twinx is
    >> implicated. Also, I saw that you committed some changes
    vis-a-vis the
    >> twinx leak
    >>
    >> r5747 | mdboom | 2008-07-11 13:21:53 -0500 (Fri, 11 Jul 2008) | 2
    >> lines
    >>
    >> Fix memory leak when using shared axes.
    >>
    >> so I thought that part was resolved already…
    >>
    >> JDH
    >
    > I use a modified version of the script Laurent Oget posted (see
    > attachment). Here is the output if I don't comment out PL.close(1).
    >
    > ~/python/test$ python looptest.py -dGTK
    > 0 GC 69354 69354 0 13854
    > 100 GC 84354 150 0 15163
    > 200 GC 99354 150 0 16306
    > 300 GC 114354 150 0 17364
    > 400 GC 129354 150 0 18576
    > ~/python/test$ python looptest.py -dTK
    > 0 GC 69521 69521 0 14065
    > 100 GC 84521 150 0 15444
    > 200 GC 99521 150 0 16581
    > 300 GC 114521 150 0 17719
    > 400 GC 129521 150 0 18715
    > ~/python/test$ python looptest.py -dPS
    > 0 GC 59307 59307 0 7705
    > 100 GC 59307 0 0 8037
    > 200 GC 59307 0 0 8038
    > 300 GC 59307 0 0 8038
    > 400 GC 59307 0 0 8038
    >
    > (so for the window-less backend PS no objects are left)
    >
    > And now I commented out the line PL.close(1):
    >
    > ~/python/test$ python looptest.py -dGTK
    > 0 GC 69379 69379 0 13855
    > 100 GC 69379 0 0 14253
    > 200 GC 69379 0 0 14253
    > 300 GC 69379 0 0 14253
    > 400 GC 69379 0 0 14252
    >
    > Manuel

    --
    Michael Droettboom
    Science Software Branch
    Operations and Engineering Division
    Space Telescope Science Institute
    Operated by AURA for NASA

    -------------------------------------------------------------------------
    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=/
    <http://moblin-contest.org/redirect.php?banner_id=100&url=/>
    _______________________________________________
    Matplotlib-users mailing list
    Matplotlib-users@lists.sourceforge.net
    <mailto:Matplotlib-users@lists.sourceforge.net>
    https://lists.sourceforge.net/lists/listinfo/matplotlib-users

--
Michael Droettboom
Science Software Branch
Operations and Engineering Division
Space Telescope Science Institute
Operated by AURA for NASA

Anyone have any thoughts on this? It seems like it's serious enough to try to resolve before the next bugfix release.

Cheers,
Mike

Michael Droettboom wrote:

···

Yes, it should be. I'm further puzzled that removing "del Gcf.figs[num]" prevents the memory leak. There is some side effect that happens when all of the figures have been closed (I think it shuts down the GUI mainloop), that keeping at least one figure around at all times avoids. But I haven't been able to get to the bottom of that, just a half-supported theory at this point.

Cheers,
Mike

laurent oget wrote:
  

I am puzzled. Wasn't the whole point of close() to avoid memory leaks?

Laurent

2008/7/15 Michael Droettboom <mdroe@…86… <mailto:mdroe@…86…>>:

    Yes, as of r5747 twinx (well, shared axes specifically) no longer
    leaks.

    Manuel has discovered a seemingly generic leak that occurs when
    pyplot.close() is called and running a GUI backend. I can confirm his
    results with the script he last sent.

    Cheers,
    Mike

    Manuel Metz wrote:
    > John Hunter wrote:
    >> On Mon, Jul 14, 2008 at 3:05 PM, Michael Droettboom >> <mdroe@…86… <mailto:mdroe@…86…>> >> >> wrote:
    >>> I can confirm this.
    >>>
    >>> Commenting out "del Gcf.figs[num]" in Gcf.destroy (in
    >>> _pylab_helpers.py)
    >>> also seems to resolve the leak. But I have no idea why, so I
    won't
    >>> commit it just yet. I don't have much time to look deeper
    now. Does
    >>> anyone (who probably understands figure management better than
    me) have
    >>> an idea what might cause this?
    >>
    >> Can you post the script you are using to test – I am a little
    >> confused from reading this thread by whether or not twinx is
    >> implicated. Also, I saw that you committed some changes
    vis-a-vis the
    >> twinx leak
    >>
    >> r5747 | mdboom | 2008-07-11 13:21:53 -0500 (Fri, 11 Jul 2008) | 2
    >> lines
    >>
    >> Fix memory leak when using shared axes.
    >>
    >> so I thought that part was resolved already…
    >>
    >> JDH
    >
    > I use a modified version of the script Laurent Oget posted (see
    > attachment). Here is the output if I don't comment out PL.close(1).
    >
    > ~/python/test$ python looptest.py -dGTK
    > 0 GC 69354 69354 0 13854
    > 100 GC 84354 150 0 15163
    > 200 GC 99354 150 0 16306
    > 300 GC 114354 150 0 17364
    > 400 GC 129354 150 0 18576
    > ~/python/test$ python looptest.py -dTK
    > 0 GC 69521 69521 0 14065
    > 100 GC 84521 150 0 15444
    > 200 GC 99521 150 0 16581
    > 300 GC 114521 150 0 17719
    > 400 GC 129521 150 0 18715
    > ~/python/test$ python looptest.py -dPS
    > 0 GC 59307 59307 0 7705
    > 100 GC 59307 0 0 8037
    > 200 GC 59307 0 0 8038
    > 300 GC 59307 0 0 8038
    > 400 GC 59307 0 0 8038
    >
    > (so for the window-less backend PS no objects are left)
    >
    > And now I commented out the line PL.close(1):
    >
    > ~/python/test$ python looptest.py -dGTK
    > 0 GC 69379 69379 0 13855
    > 100 GC 69379 0 0 14253
    > 200 GC 69379 0 0 14253
    > 300 GC 69379 0 0 14253
    > 400 GC 69379 0 0 14252
    >
    > Manuel

    --
    Michael Droettboom
    Science Software Branch
    Operations and Engineering Division
    Space Telescope Science Institute
    Operated by AURA for NASA

    -------------------------------------------------------------------------
    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=/
    <http://moblin-contest.org/redirect.php?banner_id=100&url=/>
    _______________________________________________
    Matplotlib-users mailing list
    Matplotlib-users@lists.sourceforge.net
    <mailto:Matplotlib-users@lists.sourceforge.net>
    https://lists.sourceforge.net/lists/listinfo/matplotlib-users

--
Michael Droettboom
Science Software Branch
Operations and Engineering Division
Space Telescope Science Institute
Operated by AURA for NASA

I think what we are seeing here is the known GUI figure canvas leak
(Michael, I think our offlist conversation about mainquit was a red
herring since removing that call doesn't help). We have found in the
past that creation of gtk canvases and tk canvases leak and this is
outside mpl. The reason that commenting out del Gcf.figs[num] "fixes"
the leak because it causes pyplot to simply reuse the figure rather
than re-call new_figure_manager. The chain of logic

_pylab_helpers.Gcf:

    def get_fig_manager(num):
        figManager = Gcf.figs.get(num, None)
        if figManager is not None: Gcf.set_active(figManager)
        return figManager

pyplot.figure

    figManager = _pylab_helpers.Gcf.get_fig_manager(num)
    if figManager is None:
        if get_backend().lower() == 'ps': dpi = 72

        figManager = new_figure_manager(num, figsize=figsize,
                                             dpi=dpi,
                                             facecolor=facecolor,
                                             edgecolor=edgecolor,
                                             frameon=frameon,
                                             FigureClass=FigureClass,
                                             **kwargs)

so when you do not del the figure number, the manager still lives in
the dictionary in Gcf and is returned by
_pylab_helpers.Gcf.get_fig_manager(num), and so subsequent calls to
new_figure_manager are not triggered (so the figure is not really
closed...)

So there is a bug here, but I am not sure it is in mpl -- I think it
is more likely to be in the GUI toolkits themselves, as we do not see
them in any of the mpl image backends. I don't think we need to hold
a release on this, since it is a known and existing problem with no
obvious mpl solution, though getting a reproducible test case that
just used the GUI code for submission to pygtk, tkinter, etc... would
be useful.

JDH

Michael and I just talked through this offlist, and it appears that
what is happening is that form any of the interactive backends, the
trigger to stop the GUI mainloop is when all the figures have been
closed. The typical use case in a script is to raise several GUI
figures and the program exits when all of them have been closed.
pylab otherwise doesn't know when to quit and return the shell prompt.
The backend first checks to see if you are in interactive mode, and
does not call main quit if you are, so this doesn't affect folks using
mpl in an ipython shell or other interactive sessions.

The only use case where it should arise is like the one in looptest,
where a script creates a GUI figure and then closes it in
non-interactive mode. Although there is a use case where this makes
sense (eg if we had a blocking show) where one would create a figure,
raise it, block, close it, rinse and repeat, this mode is not
currently supported in pylab (show would need to be smarter, though
with our new blocking input functions we might be able to attempt
this). This also does not affect applications since the close/destroy
handling is a pyplot construct.

Michael pointed out that the twinx problem was separate (and fixed) so
is unrelated to the close bug and can be removed from the looptest
test script.

There is a workaround for those who really need this functionality,
although it is unsupported currently, and that is simply to wrap the
close call in ion/ioff function calls to turn interaction on. The
interactive backends won't attempt to call mainquit if interactive
mode is on, so

        PL.ion()
        PL.close(1)
        PL.ioff()

blocks this leak

···

On Thu, Jul 17, 2008 at 12:42 PM, Michael Droettboom <mdroe@...86...> wrote:

Anyone have any thoughts on this? It seems like it's serious enough to try
to resolve before the next bugfix release.