summaryrefslogtreecommitdiff
path: root/cpp/src
diff options
context:
space:
mode:
authorGordon Sim <gsim@apache.org>2007-11-09 15:35:49 +0000
committerGordon Sim <gsim@apache.org>2007-11-09 15:35:49 +0000
commit0d7bb38278803b6ac935c0f47edc8a641afa0e52 (patch)
tree56edd0709eef802eff5b72fc254d19571dab1b96 /cpp/src
parent13ef73c124a5797d069d162acc4336ed99d0e35a (diff)
downloadqpid-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.cpp3
-rw-r--r--cpp/src/qpid/sys/Serializer.h8
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); }
}