httpd-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From Juan Rivera <Juan.Riv...@citrix.com>
Subject RE: EOS or FLUSH buckets
Date Tue, 10 Jun 2003 15:49:23 GMT
Greg,

Right, my module leaks memory because the core input and output filters
split the bucket brigades. So it keeps creating more and more bucket
brigades that are not released until the connection is gone.

First of all, I think the split in the core input filter (READBYTES) should
be optimized because all it is doing is splitting the brigade to concatenate
it into another brigade. Wouldn't be more efficient to do a "move buckets
from brigade ctx->b to b" and avoid creating a temporary brigade?

So for the output side, when I send a flush, it splits the brigade. If the
flush is the last bucket, this might not be necessary, what do you think?

On the topic of EOS, I think that if the last bucket is an EOS and is not a
keep alive connection it should not hold the data but it currently does.

Juan

-----Original Message-----
From: gregames@apache.org [mailto:gregames@apache.org] 
Sent: Tuesday, June 10, 2003 10:38 AM
To: dev@httpd.apache.org
Subject: Re: EOS or FLUSH buckets

Juan Rivera wrote:
> Here is why I'm asking. I wrote a SOCKS proxy module. It has two 
> connection records, one for the client and one for the backend server.
> 
> When I received data I pass it to the other side with a flush at the 
> end. It works fine with one problem. The core output filter splits the 
> brigade after the flush bucket creating a new bucket brigade. This 
> bucket brigade is never destroyed, consuming 16 bytes of memory 
> (apr_brigade.c: line 84). This may not be a problem for short lived 
> connection but it the connection is long lived the pool keeps getting 
> bigger and bigger. Is there any way around this?
> 
> So I though, I should use an EOS bucket instead (maybe not a good idea) 
> but I found that the core output filter was setting aside my buckets. 
> This section in core.c looks bogus to me:
> 
> Core.c line 3884:
> 
>         if (nbytes + flen < AP_MIN_BYTES_TO_WRITE
>             && ((!fd && !more && !APR_BUCKET_IS_FLUSH(last_e))
>                 || (APR_BUCKET_IS_EOS(last_e)
>                     && c->keepalive == AP_CONN_KEEPALIVE))) {
>                 /* set aside the buckets */
>                 }
> 
>         What is weird about this code is that if the last bucket in the 
> bridade is an EOS, this part: ((!fd && !more && 
> !APR_BUCKET_IS_FLUSH(last_e)) will return true as long as you are not 
> serving a file.
> 
>         But it seems that you want that to happen only if the connection 
> is a keep-alive connection. Right?

Juan,

Congratulations!  You have homed right in on one of the trickiest new parts
of 
Apache 2.0.  I believe the intention here is to hang on to the data across
HTTP 
connections, so we can take advantage of keepalives and pipelining and 
potentially pack more data into fewer TCP segments.  Usually what will
happen is 
that at the end of a request, we look for more inbound data (the next
request), 
don't find any, and send a FLUSH bucket which causes the network write.

> Any suggestions how to deal with this?

Deal with what? Are you saying that we leak memory with your SOCKS module?

Greg

Mime
View raw message