diff options
Diffstat (limited to 'cpp/src')
-rw-r--r-- | cpp/src/Ice/ObjectAdapterFactory.cpp | 30 | ||||
-rw-r--r-- | cpp/src/Ice/ObjectAdapterFactory.h | 1 | ||||
-rw-r--r-- | cpp/src/Ice/ObjectAdapterI.cpp | 59 | ||||
-rw-r--r-- | cpp/src/Ice/ObjectAdapterI.h | 2 |
4 files changed, 63 insertions, 29 deletions
diff --git a/cpp/src/Ice/ObjectAdapterFactory.cpp b/cpp/src/Ice/ObjectAdapterFactory.cpp index 1fc6e3d88f4..54f673efa65 100644 --- a/cpp/src/Ice/ObjectAdapterFactory.cpp +++ b/cpp/src/Ice/ObjectAdapterFactory.cpp @@ -67,15 +67,6 @@ IceInternal::ObjectAdapterFactory::waitForShutdown() wait(); } - // - // If some other thread is currently shutting down, we wait - // until this thread is finished. - // - while(_waitForShutdown) - { - wait(); - } - _waitForShutdown = true; adapters = _adapters; } @@ -83,16 +74,6 @@ IceInternal::ObjectAdapterFactory::waitForShutdown() // Now we wait for deactivation of each object adapter. // for_each(adapters.begin(), adapters.end(), IceUtil::voidMemFun(&ObjectAdapter::waitForDeactivate)); - - { - IceUtil::Monitor<IceUtil::RecMutex>::Lock sync(*this); - - // - // Signal that waiting is complete. - // - _waitForShutdown = false; - notifyAll(); - } } bool @@ -115,13 +96,18 @@ IceInternal::ObjectAdapterFactory::destroy() { IceUtil::Monitor<IceUtil::RecMutex>::Lock sync(*this); - adapters.swap(_adapters); + adapters = _adapters; } // // Now we destroy each object adapter. // for_each(adapters.begin(), adapters.end(), IceUtil::voidMemFun(&ObjectAdapter::destroy)); + + { + IceUtil::Monitor<IceUtil::RecMutex>::Lock sync(*this); + _adapters.clear(); + } } ObjectAdapterPtr @@ -223,8 +209,7 @@ IceInternal::ObjectAdapterFactory::flushBatchRequests() const IceInternal::ObjectAdapterFactory::ObjectAdapterFactory(const InstancePtr& instance, const CommunicatorPtr& communicator) : _instance(instance), - _communicator(communicator), - _waitForShutdown(false) + _communicator(communicator) { } @@ -233,5 +218,4 @@ IceInternal::ObjectAdapterFactory::~ObjectAdapterFactory() assert(!_instance); assert(!_communicator); assert(_adapters.empty()); - assert(!_waitForShutdown); } diff --git a/cpp/src/Ice/ObjectAdapterFactory.h b/cpp/src/Ice/ObjectAdapterFactory.h index 0423522ca3d..e0c7e30ebee 100644 --- a/cpp/src/Ice/ObjectAdapterFactory.h +++ b/cpp/src/Ice/ObjectAdapterFactory.h @@ -43,7 +43,6 @@ private: ::Ice::CommunicatorPtr _communicator; std::set<std::string> _adapterNamesInUse; std::list<Ice::ObjectAdapterIPtr> _adapters; - bool _waitForShutdown; }; } diff --git a/cpp/src/Ice/ObjectAdapterI.cpp b/cpp/src/Ice/ObjectAdapterI.cpp index 2e6dfa913b3..6f3081d7ae6 100644 --- a/cpp/src/Ice/ObjectAdapterI.cpp +++ b/cpp/src/Ice/ObjectAdapterI.cpp @@ -72,6 +72,13 @@ Ice::ObjectAdapterI::activate() checkForDeactivation(); // + // If some threads are waiting on waitForHold(), we set this + // flag to ensure the threads will start again the wait for + // all the incoming connection factories. + // + _waitForHoldRetry = _waitForHold > 0; + + // // If the one off initializations of the adapter are already // done, we just need to activate the incoming connection // factories and we're done. @@ -158,12 +165,52 @@ Ice::ObjectAdapterI::hold() void Ice::ObjectAdapterI::waitForHold() { - IceUtil::Monitor<IceUtil::RecMutex>::Lock sync(*this); - - checkForDeactivation(); + while(true) + { + vector<IncomingConnectionFactoryPtr> incomingConnectionFactories; + { + IceUtil::Monitor<IceUtil::RecMutex>::Lock sync(*this); + + checkForDeactivation(); + + incomingConnectionFactories = _incomingConnectionFactories; - for_each(_incomingConnectionFactories.begin(), _incomingConnectionFactories.end(), - Ice::constVoidMemFun(&IncomingConnectionFactory::waitUntilHolding)); + ++_waitForHold; + } + + for_each(incomingConnectionFactories.begin(), incomingConnectionFactories.end(), + Ice::constVoidMemFun(&IncomingConnectionFactory::waitUntilHolding)); + + { + IceUtil::Monitor<IceUtil::RecMutex>::Lock sync(*this); + if(--_waitForHold == 0) + { + notifyAll(); + } + + // + // If we don't need to retry, we're done. Otherwise, we wait until + // all the waiters finish waiting on the connections and we try + // again waiting on all the conncetions. This is necessary in the + // case activate() is called by another thread while waitForHold() + // waits on the some connection, if we didn't retry, waitForHold() + // could return only after waiting on a subset of the connections. + // + if(!_waitForHoldRetry) + { + return; + } + else + { + while(_waitForHold > 0) + { + checkForDeactivation(); + wait(); + } + _waitForHoldRetry = false; + } + } + } } void @@ -795,6 +842,8 @@ Ice::ObjectAdapterI::ObjectAdapterI(const InstancePtr& instance, const Communica _name(name), _directCount(0), _waitForActivate(false), + _waitForHold(0), + _waitForHoldRetry(false), _destroying(false), _destroyed(false), _noConfig(noConfig) diff --git a/cpp/src/Ice/ObjectAdapterI.h b/cpp/src/Ice/ObjectAdapterI.h index 201be76287d..13866ba7f7e 100644 --- a/cpp/src/Ice/ObjectAdapterI.h +++ b/cpp/src/Ice/ObjectAdapterI.h @@ -129,6 +129,8 @@ private: IceInternal::LocatorInfoPtr _locatorInfo; int _directCount; // The number of direct proxies dispatching on this object adapter. bool _waitForActivate; + int _waitForHold; + bool _waitForHoldRetry; bool _destroying; bool _destroyed; bool _noConfig; |