diff options
Diffstat (limited to 'cpp/demo/Ice/session/SessionFactoryI.cpp')
-rwxr-xr-x | cpp/demo/Ice/session/SessionFactoryI.cpp | 131 |
1 files changed, 131 insertions, 0 deletions
diff --git a/cpp/demo/Ice/session/SessionFactoryI.cpp b/cpp/demo/Ice/session/SessionFactoryI.cpp new file mode 100755 index 00000000000..eea03c46eec --- /dev/null +++ b/cpp/demo/Ice/session/SessionFactoryI.cpp @@ -0,0 +1,131 @@ +// ********************************************************************** +// +// Copyright (c) 2003-2005 ZeroC, Inc. All rights reserved. +// +// This copy of Ice is licensed to you under the terms described in the +// ICE_LICENSE file included in this distribution. +// +// ********************************************************************** + +#include <Ice/Ice.h> +#include <SessionFactoryI.h> + +using namespace std; +using namespace Demo; + +ReapThread::ReapThread(const SessionFactoryIPtr& Factory, const IceUtil::Time& timeout) : + _destroy(false), + _timeout(timeout), + _factory(Factory) +{ +} + +ReapThread::~ReapThread() +{ +} + +void +ReapThread::run() +{ + Lock sync(*this); + while(!_destroy) + { + timedWait(_timeout); + if(!_destroy) + { + assert(_factory); + _factory->reap(); + } + } +} + +void +ReapThread::destroy() +{ + Lock sync(*this); + _destroy = true; + notify(); + // Drop the cyclic reference count. + _factory = 0; +} + +SessionFactoryI::SessionFactoryI(const Ice::ObjectAdapterPtr& adapter) : + _adapter(adapter), + _timeout(IceUtil::Time::seconds(10)), + _reapThread(new ReapThread(this, _timeout)) +{ + _reapThread->start(); +} + +SessionFactoryI::~SessionFactoryI() +{ +} + +SessionPrx +SessionFactoryI::create(const Ice::Current& c) +{ + Lock sync(*this); + + SessionIPtr session = new SessionI(_adapter, _timeout); + SessionPrx proxy = SessionPrx::uncheckedCast(_adapter->addWithUUID(session)); + _sessions.push_back(make_pair(session, proxy->ice_getIdentity())); + return proxy; +} + +void +SessionFactoryI::shutdown(const ::Ice::Current& c) +{ + Lock sync(*this); + + cout << "Shutting down..." << endl; + c.adapter->getCommunicator()->shutdown(); +} + +void +SessionFactoryI::reap() +{ + Lock sync(*this); + + list<pair<SessionIPtr, Ice::Identity> >::iterator p = _sessions.begin(); + while(p != _sessions.end()) + { + if(p->first->destroyed()) + { + p->first->destroyCallback(); + _adapter->remove(p->second); + p = _sessions.erase(p); + } + else + { + ++p; + } + } +} + +void +SessionFactoryI::destroy() +{ + // + // XXX: There is an issue. This is called post after the + // communicator->waitForShutdown() has been called. Then it + // attempts to unregister each of the objects from the OA. This + // causes an ObjectAdapterDeactivatedException. I think you should + // be permitted to unregister objects even if the OA has been + // deactivated. Note the documentation in the slice doesn't say + // that you cannot call remove after the OA has been deactivated. + // + Lock sync(*this); + + _reapThread->destroy(); + _reapThread->getThreadControl().join(); + _reapThread = 0; + + for(list<pair<SessionIPtr, Ice::Identity> >::const_iterator p = _sessions.begin(); + p != _sessions.end(); + ++p) + { + p->first->destroyCallback(); + _adapter->remove(p->second); + } + _sessions.clear(); +} |