diff options
author | Gordon Sim <gsim@apache.org> | 2007-11-09 15:35:49 +0000 |
---|---|---|
committer | Gordon Sim <gsim@apache.org> | 2007-11-09 15:35:49 +0000 |
commit | 0d7bb38278803b6ac935c0f47edc8a641afa0e52 (patch) | |
tree | 56edd0709eef802eff5b72fc254d19571dab1b96 /cpp/src | |
parent | 13ef73c124a5797d069d162acc4336ed99d0e35a (diff) | |
download | qpid-python-0d7bb38278803b6ac935c0f47edc8a641afa0e52.tar.gz |
Fix race in destruction of serializer.
git-svn-id: https://svn.apache.org/repos/asf/incubator/qpid/trunk/qpid@593569 13f79535-47bb-0310-9956-ffa450edef68
Diffstat (limited to 'cpp/src')
-rw-r--r-- | cpp/src/qpid/sys/Serializer.cpp | 3 | ||||
-rw-r--r-- | cpp/src/qpid/sys/Serializer.h | 8 |
2 files changed, 7 insertions, 4 deletions
diff --git a/cpp/src/qpid/sys/Serializer.cpp b/cpp/src/qpid/sys/Serializer.cpp index 76dfaa6f6a..6d6caff5a1 100644 --- a/cpp/src/qpid/sys/Serializer.cpp +++ b/cpp/src/qpid/sys/Serializer.cpp @@ -36,9 +36,10 @@ SerializerBase::SerializerBase(bool allowImmediate, VoidFn0 notifyDispatchFn) notifyDispatch = boost::bind(&SerializerBase::notifyWorker, this); } -SerializerBase::~SerializerBase() { +void SerializerBase::shutdown() { { Mutex::ScopedLock l(lock); + if (state == SHUTDOWN) return; state = SHUTDOWN; lock.notify(); } diff --git a/cpp/src/qpid/sys/Serializer.h b/cpp/src/qpid/sys/Serializer.h index 7bb3b07ae0..9d4f13eb9b 100644 --- a/cpp/src/qpid/sys/Serializer.h +++ b/cpp/src/qpid/sys/Serializer.h @@ -46,7 +46,7 @@ class SerializerBase : private boost::noncopyable, private Runnable /** @see Serializer::Serializer */ SerializerBase(bool immediate=true, VoidFn0 notifyDispatch=VoidFn0()); - virtual ~SerializerBase(); + virtual ~SerializerBase() { shutdown(); } virtual void dispatch() = 0; protected: @@ -57,6 +57,7 @@ class SerializerBase : private boost::noncopyable, private Runnable SHUTDOWN ///< SerailizerBase is being destroyed. }; + void shutdown(); void notifyWorker(); void run(); virtual bool empty() = 0; @@ -101,7 +102,8 @@ class Serializer : public SerializerBase { */ Serializer(bool immediate=true, VoidFn0 notifyDispatch=VoidFn0()) : SerializerBase(immediate, notifyDispatch) {} - + + ~Serializer() { shutdown(); } /** * Task may be executed immediately in the calling thread if there * are no other tasks pending or executing and the "immediate" @@ -166,11 +168,11 @@ void Serializer<Task>::dispatch() { template <class Task> void Serializer<Task>::dispatch(Task& task) { - Mutex::ScopedUnlock u(lock); // Preconditions: lock is held, state is EXECUTING or DISPATCHING assert(state != IDLE); assert(state != SHUTDOWN); assert(state == EXECUTING || state == DISPATCHING); + Mutex::ScopedUnlock u(lock); // No exceptions allowed in task. try { task(); } catch (...) { assert(0); } } |