>On Thu, 03 May 2007 14:11:39 -0400, [EMAIL PROTECTED] <[EMAIL PROTECTED]>
wrote:
> > class SomeClass
> > {
> >  OsMutex *lock;
> >  int someMember;

And  Andy Spitzer <[EMAIL PROTECTED]> replied

> A non static member variable "lock" can only be used to protect other
member
> variables of this object.  It cannot protect the object itself (as you
noted,
> if the object is destructed, so is the lock!).
>
> A second lock is required to protect the lifetime of the object.  Often
that
> lock would be a static member of the object.  As it is static, it doesn't
live
> within the object, and so is not subject to destruction.  Of course, that
means
> it serializes destruction of all objects of that class, not just this
particular one.
>
> Essentially, either a second lock is required, or one must be assured that
there are
> no other threads that could possibly access the object before it is
destructed.
> I believe that much of sipX uses the later approach, although it seems to
be an
> unwritten rule, and could possibly be violated.  Locking "yourself"  just
before
> destruction seems like a good idea, but as you so rightly pointed out, it
doesn't
> really work!

A *second* lock isn't really the answer. For this to work, any thread that
could be
preempted while holding a pointer or reference to a SomeClass instance would
need
to acquire the class static lock first. Once you've done that, the lock in
each
SomeClass instance serves no useful purpose, since it should only be
acquired by a
thread that has already acquired the class static lock. Having two locks
would just
add overhead and opportunities to foul-up. A single class static lock has a
drawback,
as now operations on different SomeClass instances can't be carried out in
parallel
by different threads.

Rather than using locking, lifetime issues are best handled by having a
clear ownership
policy for each object. Such as:

1. Exclusive Ownership - the thread that creates an object owns it and is
responsible
   for its deletion. Reference to the object is only passed to secondary
threads that are
   themselves owned by the thread that created the object: since both the
object and
   the secondary thread will be destroyed by the primary thread, it can
ensure the
   object lasts until the secondary thread has terminated (or at least
relinquished
   any references to the object). 

2. Transferred Ownership - Similar to exclusive ownership. At any given
time, only
   one thread owns the object, but a thread can transfer ownership of an
object to
   another thread (who then becomes responsible for deleting it). The
current owner
   can only transfer ownership if any secondary references it allowed have
already
   been relinquished. 

3. Shared Ownership - An object may be owned by several threads, and it is
deleted
   When the last reference to it is removed. This generally requires some
sort of
   reference counting implementation. 

So while I disagree with the idea of a second lock, I do agree with Andy's
statement
"one must be assured that there are no other threads that could possibly
access
the object before it is destructed. I believe that much of sipX uses the
later approach.

In other words, sipX is using an ownership policy, but maybe the policy
needs to be
made more explicit. 


Stephen C. Steel 


_______________________________________________
sipxtapi-dev mailing list
[email protected]
List Archive: http://list.sipfoundry.org/archive/sipxtapi-dev/

Reply via email to