apr-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From "Sander Striker" <s.stri...@striker.nl>
Subject apr_pool_create_core_ex, WAS: Re: svn commit: r647384 - in /apr/apr/trunk: CHANGES include/apr_pools.h memory/unix/apr_pools.c
Date Tue, 08 Jul 2008 10:15:20 GMT
On Mon, Jul 7, 2008 at 8:07 AM, Mladen Turk <mturk@apache.org> wrote:
> Sander Striker wrote:
>> I checked on the archives, as I stumbled over the code and wondered
>> what the heck it was for.  I don't seem to find a response as to what
>> this functionality is actually needed for.  In case I missed it, could you
>> point me to it?  If I didn't miss it, because there is nothing there,
>> could
>> you please follow up to Joe's earlier question?
> Sorry for the late answer. I was on the vacation ;)

Vacation goodness; can't argue with that.

> I think I already explained the purpose and usage of create_core_ex.

Like I said, I couldn't find it.  But thanks for taking the time to do so again.

> Unlike traditional pool it creates standalone pool (and allocator if
> provided at creation time).

If *not* provided at creation time.  Why not use the global allocator
in that case?  If the user really needs a separate allocator, it's two
extra lines.  The allocator declaration and a call to
apr_allocator_create, which makes it explicit.

> The usage addresses two main common concepts:
> 1. Temporary memory pools that are commonly used inside loops
>   and are used as create/alloc*n/destroy
>   Since create_core_ex doesn't lock the parent (or global) pool
>   during create/destroy this is performance upgrade.

Well, the idea would be to have the create and destroy outside the
loop, and alloc*n within.  In constructs with nested loops, throw in
an apr_pool_clear.

> 2. Using pools with high level languages like Java that have
>   strict garbage collection. APR Objects in that case can be
>   directly bound to the java object without the need to sync the
>   GC with the pool maintenance. Since those languages ensure that
>   the object destroy method will be called, but in random order
>   there is no need to create any back reference to parent pool.

But it doesn't hurt, apart from locking.

> Just to give you an overview of the problems with that in heavily
> multithreaded environment like JVM where GC and occur in parallel,
> are the long JNI calls in which case the apr_terminate needs to be
> protected by the sync method so that it gets called *only* when all
> functions exits. In any other case we might end up with zombie
> memory (child pool) in the middle of the function call.

apr_terminate should always be ensured to be called last.  Orphaning
pools may work around your immediate problems, today, but for any
operation post apr_terminate() all bets are off.  It could well break
in the future.

> We have that problem in Tomcat Native, so a simple high CPU usage
> can lead to a JVM core during connector shutdown/restart. JVM can
> decide to cleanup the our apr socket object at some later time when
> the parent was already destroyed. To solve this issue we would need
> to create internal tree that would map apr_pool parent/child dependency
> 1:1, protect the access and maintain it, as well as having an atomic counter
> of number of JNI functions currently executing.
> With detached pools we don't need that and the memory will still
> be released by calling pool_destroy in objects finalize method.

At the cost of having an allocator per pool.

> This breaks the single root pool presumption, so the API has to be used
> only in well defined environments where for each create_core_ex the
> corresponding destroy will be always called.

The thing that throws me is the choice of naming.  'orphaned' and
'unmanaged', would have been more descriptive than 'core'.

At the very least the docstring should be updated with a big fat
warning saying not to use it unless you know what you are doing.  And
maybe mention the typical use case of being in an environment with GC.
 Right now, there is nothing in the docstring to protect an
unsuspected user that thinks 'core' is a cool term and a better (more
convenient) API.



View raw message