# About cleanup of subrequests

**URL:** <https://www.ruby-forum.com/t/about-cleanup-of-subrequests/199254>\
**Category:** NGINX\
**Created:** [November 17, 2010, 9:13am UTC](https://www.ruby-forum.com/t/about-cleanup-of-subrequests/199254 "2010-11-17T09:13:02Z")\
**Posts on this page:** 4\
**Page:** 1

<div class="post-metadata">

**Author:** ![okkezSS](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/o/85f322/32.png) [@okkezSS](https://www.ruby-forum.com/u/okkezSS)\
**Post date:** [November 17, 2010, 9:13am UTC](https://www.ruby-forum.com/t/about-cleanup-of-subrequests/199254/1 "2010-11-17T09:13:02Z")

</div>

HI,ALL

I have written a nginx module which may produce thousands of  
subrequests.Each subrequest may connect to the upstream and fetch  
data.  
Like map-reduce, my module map the main request to many subrequest and  
reduce the datas fetched from upstreams.

So,the problem comes. Since nginx free the memory when the main  
request ends, all my subrequest can’t be cleaned up until the main  
request finished.  
The memory that subrequests occupied will become very large.

Can somebody tell me how can free the memory which subrequests applied  
when this subrequest finished?

Thanks

–  
Regards  
LF Chieu

---

<div class="post-metadata">

**Author:** ![Chieu](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/c/54ee81/32.png) [@Chieu](https://www.ruby-forum.com/u/Chieu)\
**Post date:** [November 17, 2010, 9:34am UTC](https://www.ruby-forum.com/t/about-cleanup-of-subrequests/199254/2 "2010-11-17T09:34:23Z")

</div>

To agentzh,

I had read your lua, echo module.

I think the location.capture of lua module, and echo\_location\_async of  
echo module may cause this problem, too

For example:

location /main {  
echo\_reset\_timer;

```
  # subrequests in parallel
  echo_location_async /sub1;
  echo_location_async /sub2;
 ...
  echo_location_async /subn;

  echo "took $echo_timer_elapsed sec for total.";

```

}

If there are many “echo\_location\_async /subX”, echo subrequest will  
occupy some memory. Lots of memory will not be free in time.  
So,if /main is requested a lot , the system memory will be run out.

Am I right? And what’s your opinion?

Thanks

2010/11/17 Chieu [removed\_email\_address@domain.invalid](mailto:removed_email_address@domain.invalid):

---

<div class="post-metadata">

**Author:** ![Chieu](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/c/54ee81/32.png) [@Chieu](https://www.ruby-forum.com/u/Chieu)\
**Post date:** [November 17, 2010, 3:45pm UTC](https://www.ruby-forum.com/t/about-cleanup-of-subrequests/199254/3 "2010-11-17T15:45:54Z")

</div>

Thanks for your apply.

I tried the way to use single pool for each subrequest. But I found  
it’s can’t work for lots of things.

The memory I want to free is the data fethed from upstream,that is  
from proxy module.

I tried to use ngx\_pfree to free the memory, but I can’t find the  
callback which i can register to do this work.  
so, I want to know is there any callback handler to set to ngx\_pfree  
the output data.

Before,I used ngx\_pfree in ngx\_http\_post\_subrequest\_t-\>handler. But  
I’m wrong because the output data may not be sent over.

To Agentzh, I found in echo module ,that pr-\>write\_event\_handler is  
set in ngx\_http\_post\_subrequest\_t-\>handler.  
So, I just guess maybe I can set the pr-\>write\_event\_handler, which do  
ngx\_pfree, in ngx\_http\_post\_subrequest\_t-\>handler, just like the echo  
module did.

2010/11/17 agentzh [removed\_email\_address@domain.invalid](mailto:removed_email_address@domain.invalid):

---

<div class="post-metadata">

**Author:** ![Chieu](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/c/54ee81/32.png) [@Chieu](https://www.ruby-forum.com/u/Chieu)\
**Post date:** [November 17, 2010, 1:35pm UTC](https://www.ruby-forum.com/t/about-cleanup-of-subrequests/199254/4 "2010-11-17T13:35:37Z")

</div>

On Wed, Nov 17, 2010 at 4:33 PM, Chieu [removed\_email\_address@domain.invalid](mailto:removed_email_address@domain.invalid) wrote:

> To agentzh,

I’ve cc’d the nginx-devel mailing list, BTW.

> I had read your lua, echo module.
> 
> I think the location.capture of lua module, and echo\_location\_async of  
> echo module may cause this problem, too

By design (well, I mean by Igor S.'s design), nginx subrequests do  
share the same memory pool with the main request (see the definition  
of the ngx\_http\_subrequest function). So I think an assumption here is  
that a main request does not take a _lot_ of subrequests, at least  
usually 😉

If it is your user data in each subrequest that takes up too much  
room, you can explicitly free them by making an ngx\_pfree call, as  
long as those chunks are big enough (nginx’s memory pool will ignore  
small chunks and thus save some CPU cycles).

> echo “took $echo\_timer\_elapsed sec for total.”;  
> }
> 
> If there are many “echo\_location\_async /subX”, echo subrequest will  
> occupy some memory. Lots of memory will not be free in time.  
> So,if /main is requested a lot , the system memory will be run out.

Fortunately in almost all of _our_ web apps, “n” in your example is  
quite small, usually 2 or 3, and 5 at most 🙂

> Am I right? And what’s your opinion?

I think in theory you can explicitly force each subrequest created by  
yourself to use a separate memory pool such that when a subrequest  
finalizes, it can free up its own pool as soon as possible. But I  
haven’t done that myself and it’s very likely some parts of the nginx  
core relies on the assumption that subrequest’s memory chunks do have  
an identical lifetime as all of its parent requests. I’m not sure. And  
I myself, for example, have used this assumption in our ngx\_lua module  
to capture subrequest response headers for the ngx.location.capture  
Lua interface 😉

Cheers,  
-agentzh
