diff options
author | Benoit Foucher <benoit@zeroc.com> | 2009-01-15 16:02:54 +0100 |
---|---|---|
committer | Benoit Foucher <benoit@zeroc.com> | 2009-01-15 16:02:54 +0100 |
commit | a10f33af6ee6298b4a7412a3819cc4818f086fa4 (patch) | |
tree | 7dc924b0692491a6419b81ae419b559ccef467cf /cpp | |
parent | bug 3266 - fix IceSSL/C++ for custom contexts (diff) | |
download | ice-a10f33af6ee6298b4a7412a3819cc4818f086fa4.tar.bz2 ice-a10f33af6ee6298b4a7412a3819cc4818f086fa4.tar.xz ice-a10f33af6ee6298b4a7412a3819cc4818f086fa4.zip |
- Fixed errorDetection test
- Fixed bug 3504, added locator request queue.
Diffstat (limited to 'cpp')
-rw-r--r-- | cpp/src/Ice/LocatorInfo.cpp | 446 | ||||
-rw-r--r-- | cpp/src/Ice/LocatorInfo.h | 51 | ||||
-rw-r--r-- | cpp/test/Ice/location/AllTests.cpp | 50 | ||||
-rw-r--r-- | cpp/test/Ice/location/Test.ice | 2 | ||||
-rw-r--r-- | cpp/test/Slice/errorDetection/IllegalIdentifier.ice | 42 | ||||
-rwxr-xr-x | cpp/test/Slice/errorDetection/run.py | 2 |
6 files changed, 452 insertions, 141 deletions
diff --git a/cpp/src/Ice/LocatorInfo.cpp b/cpp/src/Ice/LocatorInfo.cpp index 12d87e3dcab..0113f80a868 100644 --- a/cpp/src/Ice/LocatorInfo.cpp +++ b/cpp/src/Ice/LocatorInfo.cpp @@ -26,6 +26,174 @@ IceUtil::Shared* IceInternal::upCast(LocatorManager* p) { return p; } IceUtil::Shared* IceInternal::upCast(LocatorInfo* p) { return p; } IceUtil::Shared* IceInternal::upCast(LocatorTable* p) { return p; } +namespace +{ + +class ObjectRequest : public LocatorInfo::Request, public Ice::AMI_Locator_findObjectById +{ +public: + + ObjectRequest(const LocatorInfoPtr& locatorInfo, const Ice::Identity& id) : Request(locatorInfo), _id(id) + { + } + + virtual void ice_response(const Ice::ObjectPrx& proxy) + { + _locatorInfo->removeObjectRequest(_id); + response(proxy); + } + + virtual void ice_exception(const Ice::Exception& ex) + { + _locatorInfo->removeObjectRequest(_id); + exception(ex); + } + + virtual void send() + { + _locatorInfo->getLocator()->findObjectById_async(this, _id); + } + +private: + + const Ice::Identity _id; +}; + +class AdapterRequest : public LocatorInfo::Request, public Ice::AMI_Locator_findAdapterById +{ +public: + + AdapterRequest(const LocatorInfoPtr& locatorInfo, const string& id) : Request(locatorInfo), _id(id) + { + } + + virtual void ice_response(const Ice::ObjectPrx& proxy) + { + _locatorInfo->removeAdapterRequest(_id); + response(proxy); + } + + virtual void ice_exception(const Ice::Exception& ex) + { + _locatorInfo->removeAdapterRequest(_id); + exception(ex); + } + + virtual void send() + { + _locatorInfo->getLocator()->findAdapterById_async(this, _id); + } + +private: + + const string _id; +}; + +class ObjectRequestCallback : public LocatorInfo::RequestCallback +{ +public: + + virtual void + response(const LocatorInfoPtr& locatorInfo, const Ice::ObjectPrx& object) + { + locatorInfo->getWellKnownObjectEndpoints(_reference, object, _ttl, false, _callback); + } + + virtual void + exception(const LocatorInfoPtr& locatorInfo, const Ice::Exception& ex) + { + if(dynamic_cast<const Ice::CollocationOptimizationException*>(&ex)) + { + try + { + bool cached; + vector<EndpointIPtr> endpoints = locatorInfo->getEndpoints(_reference, _ttl, cached); + _callback->setEndpoints(endpoints, cached); + } + catch(const Ice::LocalException& e) + { + _callback->setException(e); + } + } + else + { + locatorInfo->getEndpointsException(_reference, ex, _callback); + } + } + + ObjectRequestCallback(const ReferencePtr& ref, int ttl, const LocatorInfo::GetEndpointsCallbackPtr& cb) : + _reference(ref), _ttl(ttl), _callback(cb) + { + } + +private: + + const ReferencePtr _reference; + int _ttl; + const LocatorInfo::GetEndpointsCallbackPtr _callback; +}; + +class AdapterRequestCallback : public LocatorInfo::RequestCallback +{ +public: + + virtual void + response(const LocatorInfoPtr& locatorInfo, const Ice::ObjectPrx& object) + { + vector<EndpointIPtr> endpoints; + if(object) + { + endpoints = object->__reference()->getEndpoints(); + if(!endpoints.empty()) + { + locatorInfo->getTable()->addAdapterEndpoints(_reference->getAdapterId(), endpoints); + } + } + + if(_reference->getInstance()->traceLevels()->location >= 1) + { + locatorInfo->getEndpointsTrace(_reference, endpoints, false); + } + + _callback->setEndpoints(endpoints, false); + } + + virtual void + exception(const LocatorInfoPtr& locatorInfo, const Ice::Exception& ex) + { + if(dynamic_cast<const Ice::CollocationOptimizationException*>(&ex)) + { + try + { + bool cached; + vector<EndpointIPtr> endpoints = locatorInfo->getEndpoints(_reference, _ttl, cached); + _callback->setEndpoints(endpoints, cached); + } + catch(const Ice::LocalException& e) + { + _callback->setException(e); + } + } + else + { + locatorInfo->getEndpointsException(_reference, ex, _callback); + } + } + + AdapterRequestCallback(const ReferencePtr& ref, int ttl, const LocatorInfo::GetEndpointsCallbackPtr& callback) : + _reference(ref), _ttl(ttl), _callback(callback) + { + } + +private: + + const ReferencePtr _reference; + const int _ttl; + const LocatorInfo::GetEndpointsCallbackPtr _callback; +}; + +} + IceInternal::LocatorManager::LocatorManager() : _tableHint(_table.end()) { @@ -238,6 +406,111 @@ IceInternal::LocatorTable::checkTTL(const IceUtil::Time& time, int ttl) const } } +void +IceInternal::LocatorInfo::Request::addCallback(const RequestCallbackPtr& callback) +{ + IceUtil::Monitor<IceUtil::Mutex>::Lock sync(_monitor); + if(_response) + { + callback->response(_locatorInfo, _proxy); + return; + } + else if(_exception.get()) + { + callback->exception(_locatorInfo, *_exception.get()); + return; + } + + _callbacks.push_back(callback); + + if(!_sent) + { + _sent = true; + try + { + send(); + } + catch(const Ice::Exception& ex) + { + sync.release(); + exception(ex); + sync.acquire(); + } + } +} + +Ice::ObjectPrx +IceInternal::LocatorInfo::Request::getProxy() +{ + IceUtil::Monitor<IceUtil::Mutex>::Lock sync(_monitor); + if(_response) + { + return _proxy; + } + else if(_exception.get()) + { + _exception->ice_throw(); + return 0; // Keep the compiler happy. + } + + if(!_sent) + { + _sent = true; + try + { + send(); + } + catch(const Ice::Exception& ex) + { + sync.release(); + exception(ex); + sync.acquire(); + } + } + + while(!_response && !_exception.get()) + { + _monitor.wait(); + } + + if(_exception.get()) + { + _exception->ice_throw(); + } + assert(_response); + return _proxy; +} + +IceInternal::LocatorInfo::Request::Request(const LocatorInfoPtr& locatorInfo) : + _locatorInfo(locatorInfo), _sent(false), _response(false) +{ +} + +void +IceInternal::LocatorInfo::Request::response(const Ice::ObjectPrx& proxy) +{ + IceUtil::Monitor<IceUtil::Mutex>::Lock sync(_monitor); + _response = true; + _proxy = proxy; + for(vector<RequestCallbackPtr>::const_iterator p = _callbacks.begin(); p != _callbacks.end(); ++p) + { + (*p)->response(_locatorInfo, proxy); + } + _monitor.notifyAll(); +} + +void +IceInternal::LocatorInfo::Request::exception(const Ice::Exception& ex) +{ + IceUtil::Monitor<IceUtil::Mutex>::Lock sync(_monitor); + _exception.reset(ex.ice_clone()); + for(vector<RequestCallbackPtr>::const_iterator p = _callbacks.begin(); p != _callbacks.end(); ++p) + { + (*p)->exception(_locatorInfo, ex); + } + _monitor.notifyAll(); +} + IceInternal::LocatorInfo::LocatorInfo(const LocatorPrx& locator, const LocatorTablePtr& table) : _locator(locator), _table(table) @@ -323,7 +596,8 @@ IceInternal::LocatorInfo::getEndpoints(const ReferencePtr& ref, int ttl, bool& c out << "adapter = " << ref->getAdapterId(); } - object = _locator->findAdapterById(ref->getAdapterId()); + RequestPtr request = getAdapterRequest(ref->getAdapterId()); + object = request->getProxy(); if(object) { endpoints = object->__reference()->getEndpoints(); @@ -345,7 +619,8 @@ IceInternal::LocatorInfo::getEndpoints(const ReferencePtr& ref, int ttl, bool& c } objectCached = false; - object = _locator->findObjectById(ref->getIdentity()); + RequestPtr request = getObjectRequest(ref->getIdentity()); + object = request->getProxy(); } bool endpointsCached = true; @@ -384,73 +659,6 @@ IceInternal::LocatorInfo::getEndpoints(const ReferencePtr& ref, int ttl, bool& c return endpoints; } -namespace IceInternal -{ - -class findAdapterByIdCallback : public AMI_Locator_findAdapterById -{ -public: - - virtual void - ice_response(const Ice::ObjectPrx& object) - { - vector<EndpointIPtr> endpoints; - if(object) - { - endpoints = object->__reference()->getEndpoints(); - if(!endpoints.empty()) - { - _table->addAdapterEndpoints(_reference->getAdapterId(), endpoints); - } - } - - if(_reference->getInstance()->traceLevels()->location >= 1) - { - _locatorInfo->getEndpointsTrace(_reference, endpoints, false); - } - - _callback->setEndpoints(endpoints, false); - } - - virtual void - ice_exception(const Ice::Exception& ex) - { - if(dynamic_cast<const Ice::CollocationOptimizationException*>(&ex)) - { - try - { - bool cached; - vector<EndpointIPtr> endpoints = _locatorInfo->getEndpoints(_reference, _ttl, cached); - _callback->setEndpoints(endpoints, cached); - } - catch(const Ice::LocalException& e) - { - _callback->setException(e); - } - } - else - { - _locatorInfo->getEndpointsException(_reference, ex, _callback); - } - } - - findAdapterByIdCallback(const LocatorInfoPtr& locatorInfo, const LocatorTablePtr& table, - const ReferencePtr& reference, int ttl, const LocatorInfo::GetEndpointsCallbackPtr& callback) : - _locatorInfo(locatorInfo), _table(table), _reference(reference), _ttl(ttl), _callback(callback) - { - } - -private: - - const LocatorInfoPtr _locatorInfo; - const LocatorTablePtr _table; - const ReferencePtr _reference; - const int _ttl; - const LocatorInfo::GetEndpointsCallbackPtr _callback; -}; - -}; - void IceInternal::LocatorInfo::getEndpoints(const ReferencePtr& ref, int ttl, const GetEndpointsCallbackPtr& callback) { @@ -474,8 +682,8 @@ IceInternal::LocatorInfo::getEndpoints(const ReferencePtr& ref, int ttl, const G // Search the adapter in the location service if we didn't // find it in the cache. // - _locator->findAdapterById_async( - new IceInternal::findAdapterByIdCallback(this, _table, ref, ttl, callback), adapterId); + RequestPtr request = getAdapterRequest(adapterId); + request->addCallback(new AdapterRequestCallback(ref, ttl, callback)); return; } else @@ -499,53 +707,8 @@ IceInternal::LocatorInfo::getEndpoints(const ReferencePtr& ref, int ttl, const G out << "searching for object by id" << "\nobject = " << instance->identityToString(ref->getIdentity()); } - class Callback : public Ice::AMI_Locator_findObjectById - { - public: - - virtual void - ice_response(const Ice::ObjectPrx& object) - { - _locatorInfo->getWellKnownObjectEndpoints(_reference, object, _ttl, false, _callback); - } - - virtual void - ice_exception(const Ice::Exception& ex) - { - if(dynamic_cast<const Ice::CollocationOptimizationException*>(&ex)) - { - try - { - bool cached; - vector<EndpointIPtr> endpoints = _locatorInfo->getEndpoints(_reference, _ttl, cached); - _callback->setEndpoints(endpoints, cached); - } - catch(const Ice::LocalException& e) - { - _callback->setException(e); - } - } - else - { - _locatorInfo->getEndpointsException(_reference, ex, _callback); - } - } - - Callback(const LocatorInfoPtr& locatorInfo, const ReferencePtr& reference, int ttl, - const GetEndpointsCallbackPtr& callback) : - _locatorInfo(locatorInfo), _reference(reference), _ttl(ttl), _callback(callback) - { - } - - private: - - const LocatorInfoPtr _locatorInfo; - const ReferencePtr _reference; - int _ttl; - const GetEndpointsCallbackPtr _callback; - }; - - _locator->findObjectById_async(new Callback(this, ref, ttl, callback), identity); + RequestPtr request = getObjectRequest(identity); + request->addCallback(new ObjectRequestCallback(ref, ttl, callback)); return; } else @@ -828,3 +991,50 @@ IceInternal::LocatorInfo::getEndpointsTrace(const ReferencePtr& ref, const vecto } } } + +IceInternal::LocatorInfo::RequestPtr +IceInternal::LocatorInfo::getAdapterRequest(const string& id) +{ + IceUtil::Mutex::Lock sync(*this); + map<string, RequestPtr>::const_iterator p = _adapterRequests.find(id); + if(p != _adapterRequests.end()) + { + return p->second; + } + + RequestPtr request = new AdapterRequest(this, id); + _adapterRequests.insert(make_pair(id, request)); + return request; +} + +void +IceInternal::LocatorInfo::removeAdapterRequest(const string& id) +{ + IceUtil::Mutex::Lock sync(*this); + assert(_adapterRequests.find(id) != _adapterRequests.end()); + _adapterRequests.erase(id); +} + +IceInternal::LocatorInfo::RequestPtr +IceInternal::LocatorInfo::getObjectRequest(const Ice::Identity& id) +{ + IceUtil::Mutex::Lock sync(*this); + map<Ice::Identity, RequestPtr>::const_iterator p = _objectRequests.find(id); + if(p != _objectRequests.end()) + { + return p->second; + } + + RequestPtr request = new ObjectRequest(this, id); + _objectRequests.insert(make_pair(id, request)); + return request; +} + +void +IceInternal::LocatorInfo::removeObjectRequest(const Ice::Identity& id) +{ + IceUtil::Mutex::Lock sync(*this); + assert(_objectRequests.find(id) != _objectRequests.end()); + _objectRequests.erase(id); +} + diff --git a/cpp/src/Ice/LocatorInfo.h b/cpp/src/Ice/LocatorInfo.h index ad8db69fe27..a4fe455a942 100644 --- a/cpp/src/Ice/LocatorInfo.h +++ b/cpp/src/Ice/LocatorInfo.h @@ -12,6 +12,7 @@ #include <IceUtil/Shared.h> #include <IceUtil/Mutex.h> +#include <IceUtil/Monitor.h> #include <IceUtil/Time.h> #include <Ice/LocatorInfoF.h> #include <Ice/LocatorF.h> @@ -71,6 +72,44 @@ class LocatorInfo : public IceUtil::Shared, public IceUtil::Mutex { public: + class RequestCallback : virtual public IceUtil::Shared + { + public: + + virtual void response(const LocatorInfoPtr&, const Ice::ObjectPrx&) = 0; + virtual void exception(const LocatorInfoPtr&, const Ice::Exception&) = 0; + }; + typedef IceUtil::Handle<RequestCallback> RequestCallbackPtr; + + class Request : virtual public IceUtil::Shared + { + public: + + void addCallback(const RequestCallbackPtr&); + Ice::ObjectPrx getProxy(); + + protected: + + Request(const LocatorInfoPtr&); + + void response(const Ice::ObjectPrx&); + void exception(const Ice::Exception&); + + virtual void send() = 0; + + const LocatorInfoPtr _locatorInfo; + + private: + + IceUtil::Monitor<IceUtil::Mutex> _monitor; + std::vector<RequestCallbackPtr> _callbacks; + bool _sent; + bool _response; + Ice::ObjectPrx _proxy; + std::auto_ptr<Ice::Exception> _exception; + }; + typedef IceUtil::Handle<Request> RequestPtr; + class GetEndpointsCallback : virtual public IceUtil::Shared { public: @@ -105,13 +144,25 @@ public: void getEndpointsException(const ReferencePtr&, const Ice::Exception&, const GetEndpointsCallbackPtr&); void getEndpointsTrace(const ReferencePtr&, const std::vector<EndpointIPtr>&, bool); + const LocatorTablePtr& getTable() { return _table; } + + RequestPtr getAdapterRequest(const std::string&); + void removeAdapterRequest(const std::string&); + + RequestPtr getObjectRequest(const Ice::Identity&); + void removeObjectRequest(const Ice::Identity&); + private: + void trace(const std::string&, const ReferencePtr&, const std::vector<EndpointIPtr>&); const Ice::LocatorPrx _locator; Ice::LocatorRegistryPrx _locatorRegistry; const LocatorTablePtr _table; + + std::map<std::string, RequestPtr> _adapterRequests; + std::map<Ice::Identity, RequestPtr> _objectRequests; }; } diff --git a/cpp/test/Ice/location/AllTests.cpp b/cpp/test/Ice/location/AllTests.cpp index 46b02be526b..77b8a09ec3a 100644 --- a/cpp/test/Ice/location/AllTests.cpp +++ b/cpp/test/Ice/location/AllTests.cpp @@ -288,6 +288,7 @@ allTests(const Ice::CommunicatorPtr& communicator, const string& ref) cout << "ok" << endl; cout << "testing proxy from server... " << flush; + obj = TestIntfPrx::checkedCast(communicator->stringToProxy("test@TestAdapter")); HelloPrx hello = obj->getHello(); test(hello->ice_getAdapterId() == "TestAdapter"); hello->sayHello(); @@ -296,7 +297,56 @@ allTests(const Ice::CommunicatorPtr& communicator, const string& ref) hello->sayHello(); cout << "ok" << endl; + cout << "testing locator request queuing... " << flush; + hello = obj->getReplicatedHello()->ice_locatorCacheTimeout(0)->ice_connectionCached(false); + count = locator->getRequestCount(); + hello->ice_ping(); + test(++count == locator->getRequestCount()); + for(int i = 0; i < 1000; i++) + { + class AMICallback : public Test::AMI_Hello_sayHello + { + public: + virtual void + ice_exception(const Ice::Exception&) + { + test(false); + } + + virtual void + ice_response() + { + } + }; + hello->sayHello_async(new AMICallback()); + } + test(locator->getRequestCount() > count && locator->getRequestCount() < count + 100); + count = locator->getRequestCount(); + hello = hello->ice_adapterId("unknown"); + for(int i = 0; i < 1000; i++) + { + class AMICallback : public Test::AMI_Hello_sayHello + { + public: + virtual void + ice_exception(const Ice::Exception& ex) + { + test(dynamic_cast<const Ice::NotRegisteredException*>(&ex)); + } + + virtual void + ice_response() + { + test(false); + } + }; + hello->sayHello_async(new AMICallback()); + } + test(locator->getRequestCount() > count && locator->getRequestCount() < count + 100); + cout << "ok" << endl; + cout << "testing proxy from server after shutdown... " << flush; + hello = obj->getReplicatedHello(); obj->shutdown(); manager->startServer(); hello->sayHello(); diff --git a/cpp/test/Ice/location/Test.ice b/cpp/test/Ice/location/Test.ice index f53b85e18aa..95702e5cd4d 100644 --- a/cpp/test/Ice/location/Test.ice +++ b/cpp/test/Ice/location/Test.ice @@ -39,7 +39,7 @@ interface ServerManager interface Hello { - void sayHello(); + ["ami"] void sayHello(); }; interface TestIntf diff --git a/cpp/test/Slice/errorDetection/IllegalIdentifier.ice b/cpp/test/Slice/errorDetection/IllegalIdentifier.ice index 2da89686467..d50ddb4afe1 100644 --- a/cpp/test/Slice/errorDetection/IllegalIdentifier.ice +++ b/cpp/test/Slice/errorDetection/IllegalIdentifier.ice @@ -1,21 +1,21 @@ -// **********************************************************************
-//
-// Copyright (c) 2003-2009 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.
-//
-// **********************************************************************
-
-
-//
-// Check that 'œ' is properly rejected in idenifiers
-//
-
-module Test
-{
- interface Œuvre
- {
- void cœur();
- };
-};
+// ********************************************************************** +// +// Copyright (c) 2003-2009 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. +// +// ********************************************************************** + + +// +// Check that 'œ' is properly rejected in idenifiers +// + +module Test +{ + interface Œuvre + { + void cœur(); + }; +}; diff --git a/cpp/test/Slice/errorDetection/run.py b/cpp/test/Slice/errorDetection/run.py index 769754c0b84..b10af237310 100755 --- a/cpp/test/Slice/errorDetection/run.py +++ b/cpp/test/Slice/errorDetection/run.py @@ -39,7 +39,7 @@ for file in files: else: command = slice2cpp + " -I. " + os.path.join(os.getcwd(), file); stdin, stdout, stderr = os.popen3(command) - lines1 = stdout.readlines() + lines1 = stderr.readlines() lines2 = open(os.path.join(os.getcwd(), regex1.sub(".err", file)), "r").readlines() if len(lines1) != len(lines2): print "failed!" |