On Sun, May 12, 2002 at 01:10:03AM -0400, Allen Smith wrote:
> On May 11, 11:28pm, Joshua N Pritikin wrote:
> > That means that Event probably has a reference counting bug.
> 
> Sigh... yes. I am wondering myself about a couple things in ev.c:
>       A. pe_event_invoke. Callbacks only return values via calling
>          "unloop('value')", not returning something, right? Thus the
>          G_VOID? Then why not also G_DISCARD?

Look at the source code for call_sv in perl.c.  The only things that
G_DISCARD does is turn on the ENTER/SAVETMPS FREETMPS/LEAVE pair.
This is already done in _loop() so we don't need to do it again.
i tried adding G_DISCARD and it doesn't make any difference.

>       B. pe_event_release decreases the refcount for ev->mysv; the same
>          happens in event_2sv thanks to the "sv_2mortal", which
>          compensates for the SvREFCNT_inc. But ev->mysv is a
>          reference. What decreases the refcount to the thing it's
>          referring to?

When the rv is destroyed then it does a SvREFCNT_dec on the SV to which
it is pointing.  See the doc for newSVrv -- the sv is created with
a refcnt=1, so this should work.  You can verify it with $Event::DebugLevel=3;
which turns on a warning "Event=0x%x '%s' destroyed (SV=0x%x)".

Oops, this warning isn't getting triggered.  Well, here is one memory leak.
i don't know why this stopped working.

>          That sv gets created _again_ anytime ev->mysv is 0,
>          which it will be if the event has gone through pe_event_release
>          (whether or not ev->mysv is freed...).

Correct.

> SV *event_2sv(pe_event *ev) { /**MAKE FAST**/
>     if (!ev->mysv) {
>         SV *rv = newSV(0);
>         SV *sv = newSVrv(rv,0);
>         sv_bless(rv, ev->vtbl->stash);
>         sv_setiv(sv, (IV)ev);
>         ev->mysv = rv;
> 
>         if (WaDEBUGx(ev->up) >= 4) {
>             STRLEN n_a;
>             warn("Event=0x%x '%s' wrapped with SV=0x%x",
>                  ev, SvPV(ev->up->desc, n_a), SvRV(ev->mysv));
>         }
>     }
>     return SvREFCNT_inc(sv_2mortal(ev->mysv));
> }

But if the SvREFCNT_inc is removed then we get:

  "Attempt to free unreferenced scalar ..."

i don't have much time but i'll try to look at this today.

-- 
Victory to the Divine Mother!!         after all,
  http://sahajayoga.org                  http://why-compete.org

Reply via email to