perl-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From Joe Schaefer <joe+gm...@sunstarsys.com>
Subject Re: [apr] dropping Apache2/ subdir for APR::*
Date Fri, 02 Jul 2004 02:11:17 GMT
Stas Bekman <stas@stason.org> writes:

[...]

> There are going to be various tricky bugs to figure out with the new
> things. I just had one when I tried:
> 
> perl -MApache2 -MAPR::Pool -MAPR::PerlIO -le '; open my $fh, "<:APR",
> "/tmp/xxx", APR::Pool->new; print <$fh>'
> APR::PerlIO::read: (9) Bad file descriptor at -e line ...
> 
> it took me time to figure out that the pool has gone out of scope and
> was destroyed by the time read was attempted. 

Yup- it took me a few reads to even understand the problem
you had :-).

> This fixed the problem:
> 
> perl -MApache2 -MAPR::Pool -MAPR::PerlIO -le '; my $p =
> APR::Pool->new; open my $fh, "<:APR", "/tmp/xxx", $p; print <$fh>'
> 
> tricky. We may need to have much more defending code if we don't want
> to get a rain of bug reports. And writing it is not trivial at all :(
> 
> so in the case of open() we probably need to increment the refcount
> of the pool object and decrement it on close and hope that we don't
> get a leak anywhere. 

The problem is the same for any pool-derived object,
e.g. 

  #! perl
  use Apache2;
  use APR::Pool;
  use Apache::Request;
  my $req = Apache::Request->new(APR::Pool->new);
  print $req->param; #KaBoom!

In apreq we don't currently tag the pool SV that constructed us,
so a DESTROY method can't decrement it.  We could change that in 
apreq2,but doing that throughout mp2 might be messy.

Is it possible to do something within APR::Pool 
to address this?  Maybe calling APR::Pool->new()
can dish out pool objects from an internal list:

  package APR::Pool;
  sub new {
        my $parent = shift;
        if (!ref $parent) {
            my $pool = <new APR::Pool object>;
            push @INTERNAL_POOL_LIST, $pool;
            return $pool;
        }
  ...

  sub DESTROY {
        my $pool = shift;
        if (!ref $pool) {
            pop @INTERNAL_POOL_LIST;
        }
  }


Here somebody would need to call APR::Pool->DESTROY
to actually relinquish the last pool.  Conway's OOP
book discusses the "flyweight pattern", which probably 
has much better ideas than this.

-- 
Joe Schaefer


---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@perl.apache.org
For additional commands, e-mail: dev-help@perl.apache.org


Mime
View raw message