You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@apr.apache.org by Aaron Bannert <aa...@ebuilt.com> on 2001/07/14 01:13:30 UTC

Threads and their Pools

It appears to me that APR threads (on unix) are automatically creating a
subpool, and then later destroying it only if/when apr_thread_exit() is
explicitly called. I have a few questions about threadproc/unix/thread.c:

1) How do we guarantee the child-pool is being destroyed? What happens
  if the thread just exits?
  (I don't see anywhere in httpd that is calling apr_thread_exit().)

2) Why are we forcing applications using APR's threads to use pools
  in the first place? Even if we require some sort of allocator to get
  memory from for the thread structures themselves, why are we forcing
  them to be child-pools?

-aaron


Re: Threads and their Pools

Posted by Aaron Bannert <aa...@ebuilt.com>.
Just for a little insight, this was promted while trying to sort through
the apr_thread_* API for use in "flood", the httpd-tester Justin and I
have been working on.

I was curious why apr_thread_exit() needed the apr_thread_t that it is
supposed to exit, since that is not typically something a thread has
direct access to. Then I realized that it was simply destroying the
pool that is a part of that apr_thread_t structure, and I became
suspicious.


I still don't see how a thread can call apr_thread_exit() for itself,
and I don't see any examples anywhere in httpd-2.0 or apr[-util].

-aaron


On Fri, Jul 13, 2001 at 04:13:30PM -0700, Aaron Bannert wrote:
> It appears to me that APR threads (on unix) are automatically creating a
> subpool, and then later destroying it only if/when apr_thread_exit() is
> explicitly called. I have a few questions about threadproc/unix/thread.c:
> 
> 1) How do we guarantee the child-pool is being destroyed? What happens
>   if the thread just exits?
>   (I don't see anywhere in httpd that is calling apr_thread_exit().)
> 
> 2) Why are we forcing applications using APR's threads to use pools
>   in the first place? Even if we require some sort of allocator to get
>   memory from for the thread structures themselves, why are we forcing
>   them to be child-pools?
> 
> -aaron


RE: Threads and their Pools

Posted by Sander Striker <st...@apache.org>.
>> APR threads should be allocating a sub-pool on all platforms.
> 
> This is where I disagree, but only slightly:
> 
> APR threads should be *using* a sub-pool on all platforms. I believe it
> should be the responsibility of the caller to define the lifetime
> of that thread and it's data, not the thread itself.

[...]
> I still think the subpool could be created outside of apr_thread_create,
> and passed in. This works well with the new SMS code, so threads that
> are created for specific purposes could be paired up with a particular
> SMS.

Well, actually it is much more convenient to create a subpool/sms in
apr_thread_create. This is because there is some administration that
needs to be done to get the dynamic locking going. The thread an
sms is created in, is the first thread registered. Once a second thread
is registered, the locking is activated, because then there are two
threads registered with that sms. So, the subpool/sms should be created
_in_ the new thread and the thread should register with the sms passed
into apr_thread_create. That way, all the memory management within
the thread can be virtually without locking.
Oh, and ofcourse, the thread needs to be unregistered at exit. This
could be through cleanup, or by the method described earlier on list.

[...]
> But why must threads be involved in subpool creation? Threads do have a
> lifetime, and therefore it makes sense to pass them a pool for 
> that purpose, but I don't see how threads need to be dictating other
> pools.

Well, the lifetime isn't any longer than the pool that is passed in, is it?
So, either way, the lifetime is dictated by the pool passed in, be it the
parent pool or a new subpool thereof.

Sander


Re: Threads and their Pools

Posted by Aaron Bannert <aa...@ebuilt.com>.
On Fri, Jul 13, 2001 at 04:57:05PM -0700, rbb@covalent.net wrote:
> 
> Okay, there are some naming conventions in this e-mail that make it very
> hard to determine what you are talking about.  There are thread pools and
> child pools, they are not the same thing.  A child pool is associated with
> a child process, a thread poo is associated with a thread.
> 
> > It appears to me that APR threads (on unix) are automatically creating a
> > subpool, and then later destroying it only if/when apr_thread_exit() is
> > explicitly called. I have a few questions about threadproc/unix/thread.c:
> 
> APR threads should be allocating a sub-pool on all platforms.

This is where I disagree, but only slightly:

APR threads should be *using* a sub-pool on all platforms. I believe it
should be the responsibility of the caller to define the lifetime
of that thread and it's data, not the thread itself.


> > 1) How do we guarantee the child-pool is being destroyed? What happens
> >   if the thread just exits?
> >   (I don't see anywhere in httpd that is calling apr_thread_exit().)
> 
> The thread pool is destroyed in one of two cases, when the thread kills
> itself using apr_thread_exit, or when the parent pool is cleaned.  The
> reason a separate thread pool is created, is because that allows the
> thread to register a cleanup with it's own pool.  That way, when the pool
> goes away, so does the thread, automagically.  At least, that was how it
> used to work.  I do not see the cleanup being registered right now.  :-(

That is a neat trick, but it causes all applications that wish to
use portable threads in APR to take on the processing bulk of child
pools. What happened to "lightweight" threads? ;)

I still think the subpool could be created outside of apr_thread_create,
and passed in. This works well with the new SMS code, so threads that
are created for specific purposes could be paired up with a particular
SMS.

> > 2) Why are we forcing applications using APR's threads to use pools
> >   in the first place? Even if we require some sort of allocator to get
> >   memory from for the thread structures themselves, why are we forcing
> >   them to be child-pools?
> 
> ALL APR functions use pools.  Ben (either Laurie or Hyde, I can't remember
> which) outlined why we do this sort of thing back when APR was first
> written.  I would need to review the archives to give a better answer than
> that.

But why must threads be involved in subpool creation? Threads do have a
lifetime, and therefore it makes sense to pass them a pool for that purpose,
but I don't see how threads need to be dictating other pools.

-aaron


Re: Threads and their Pools

Posted by Aaron Bannert <aa...@ebuilt.com>.
On Fri, Jul 13, 2001 at 04:33:51PM -0700, Justin Erenkrantz wrote:
> On Fri, Jul 13, 2001 at 07:20:26PM -0400, Cliff Woolley wrote:
> > Semi-related to this is something I was wondering about this morning when
> > I woke up, which is this: what happens if there's a per-thread allocator
> > (sms) that's used as the parent of all sms's in that thread, and some
> > portion of the code (maybe a module) running in that thread decides to
> > spawn off some child threads?  Clearly it cannot use the per-thread sms as
> > the parent sms for the pools created in the child threads.  Should it
> > start over with an apr_sms_std as the parent sms for all sms's in the
> > child thread?
> 
> Which is why Sander and I were tossing the idea of creating that in the
> apr_thread_create function.  Ideally, the apr_thread_create function
> would create a threads/trivial SMS parented by the global pool (std -
> which is malloc-based) for each thread.
> 
> (Aaron prolly hates this idea.  Actually, he's sitting behind me yelling
> at me for writing this...)
> 
> Now, I'm not sure how realistic this is, but that's my initial thought.
> -- justin

I suppose I have to reply now... *grin*

Instead of referencing the global pool (And breaking all the rules
of your first CS course where they said "don't use global variables")
all the time, why don't we allow whatever called "apr_thread_create" to
pass in the pool that the thread is to use directly, instead of passing
it one it is supposed to use as a parent.

Isn't the whole point of passing in an allocator resource (the apr_pool_t *pool
argument) to all the APR functions merely so that the *caller* of
our various APR functions can completely control the scope of the data
that is allocated during that call? When I call apr_pstrdup() with a pool,
I want that pool to define the lifetime of that memory, I don't want it to
allocate memory that goes out of scope at un undefined time before or
after apr_pstrdup() returns...

-aaron


Re: Threads and their Pools

Posted by Justin Erenkrantz <je...@ebuilt.com>.
On Fri, Jul 13, 2001 at 07:20:26PM -0400, Cliff Woolley wrote:
> Semi-related to this is something I was wondering about this morning when
> I woke up, which is this: what happens if there's a per-thread allocator
> (sms) that's used as the parent of all sms's in that thread, and some
> portion of the code (maybe a module) running in that thread decides to
> spawn off some child threads?  Clearly it cannot use the per-thread sms as
> the parent sms for the pools created in the child threads.  Should it
> start over with an apr_sms_std as the parent sms for all sms's in the
> child thread?

Which is why Sander and I were tossing the idea of creating that in the
apr_thread_create function.  Ideally, the apr_thread_create function
would create a threads/trivial SMS parented by the global pool (std -
which is malloc-based) for each thread.

(Aaron prolly hates this idea.  Actually, he's sitting behind me yelling
at me for writing this...)

Now, I'm not sure how realistic this is, but that's my initial thought.
-- justin


Re: Threads and their Pools

Posted by David Reid <dr...@jetnet.co.uk>.
> > It appears to me that APR threads (on unix) are automatically creating a
> > subpool, and then later destroying it only if/when apr_thread_exit() is
> > explicitly called. I have a few questions about
threadproc/unix/thread.c:
> >
> > 1) How do we guarantee the child-pool is being destroyed? What happens
> >   if the thread just exits?
> >   (I don't see anywhere in httpd that is calling apr_thread_exit().)
> >
> > 2) Why are we forcing applications using APR's threads to use pools
> >   in the first place? Even if we require some sort of allocator to get
> >   memory from for the thread structures themselves, why are we forcing
> >   them to be child-pools?
>
> Semi-related to this is something I was wondering about this morning when
> I woke up, which is this: what happens if there's a per-thread allocator
> (sms) that's used as the parent of all sms's in that thread, and some
> portion of the code (maybe a module) running in that thread decides to
> spawn off some child threads?  Clearly it cannot use the per-thread sms as
> the parent sms for the pools created in the child threads.  Should it
> start over with an apr_sms_std as the parent sms for all sms's in the
> child thread?

Hmm, good question.  Maybe it could use the sms's parent?  Although that
would depend on what the parent was whether that was clever. This is
something else that needs looking into...

BTW, what in hells name were you doing thinking about this as you woke up???
:)

david



Re: Threads and their Pools

Posted by Cliff Woolley <cl...@yahoo.com>.
On Fri, 13 Jul 2001, Aaron Bannert wrote:

> It appears to me that APR threads (on unix) are automatically creating a
> subpool, and then later destroying it only if/when apr_thread_exit() is
> explicitly called. I have a few questions about threadproc/unix/thread.c:
>
> 1) How do we guarantee the child-pool is being destroyed? What happens
>   if the thread just exits?
>   (I don't see anywhere in httpd that is calling apr_thread_exit().)
>
> 2) Why are we forcing applications using APR's threads to use pools
>   in the first place? Even if we require some sort of allocator to get
>   memory from for the thread structures themselves, why are we forcing
>   them to be child-pools?

Semi-related to this is something I was wondering about this morning when
I woke up, which is this: what happens if there's a per-thread allocator
(sms) that's used as the parent of all sms's in that thread, and some
portion of the code (maybe a module) running in that thread decides to
spawn off some child threads?  Clearly it cannot use the per-thread sms as
the parent sms for the pools created in the child threads.  Should it
start over with an apr_sms_std as the parent sms for all sms's in the
child thread?

--Cliff


--------------------------------------------------------------
   Cliff Woolley
   cliffwoolley@yahoo.com
   Charlottesville, VA



Re: Threads and their Pools

Posted by rb...@covalent.net.
Okay, there are some naming conventions in this e-mail that make it very
hard to determine what you are talking about.  There are thread pools and
child pools, they are not the same thing.  A child pool is associated with
a child process, a thread poo is associated with a thread.

> It appears to me that APR threads (on unix) are automatically creating a
> subpool, and then later destroying it only if/when apr_thread_exit() is
> explicitly called. I have a few questions about threadproc/unix/thread.c:

APR threads should be allocating a sub-pool on all platforms.

> 1) How do we guarantee the child-pool is being destroyed? What happens
>   if the thread just exits?
>   (I don't see anywhere in httpd that is calling apr_thread_exit().)

The thread pool is destroyed in one of two cases, when the thread kills
itself using apr_thread_exit, or when the parent pool is cleaned.  The
reason a separate thread pool is created, is because that allows the
thread to register a cleanup with it's own pool.  That way, when the pool
goes away, so does the thread, automagically.  At least, that was how it
used to work.  I do not see the cleanup being registered right now.  :-(

> 2) Why are we forcing applications using APR's threads to use pools
>   in the first place? Even if we require some sort of allocator to get
>   memory from for the thread structures themselves, why are we forcing
>   them to be child-pools?

ALL APR functions use pools.  Ben (either Laurie or Hyde, I can't remember
which) outlined why we do this sort of thing back when APR was first
written.  I would need to review the archives to give a better answer than
that.

Ryan

_____________________________________________________________________________
Ryan Bloom                        	rbb@apache.org
Covalent Technologies			rbb@covalent.net
-----------------------------------------------------------------------------