diff options
author | Benoit Foucher <benoit@zeroc.com> | 2006-09-12 09:01:35 +0000 |
---|---|---|
committer | Benoit Foucher <benoit@zeroc.com> | 2006-09-12 09:01:35 +0000 |
commit | d89514da858be06f7e44129bcd6675a46181208e (patch) | |
tree | 662073ca1e8a9b6e56e9914087da66a824b88d6c /cpp/src/IceGrid/Allocatable.cpp | |
parent | Minor Makefile tweak. (diff) | |
download | ice-d89514da858be06f7e44129bcd6675a46181208e.tar.bz2 ice-d89514da858be06f7e44129bcd6675a46181208e.tar.xz ice-d89514da858be06f7e44129bcd6675a46181208e.zip |
Fixes
Diffstat (limited to 'cpp/src/IceGrid/Allocatable.cpp')
-rw-r--r-- | cpp/src/IceGrid/Allocatable.cpp | 189 |
1 files changed, 102 insertions, 87 deletions
diff --git a/cpp/src/IceGrid/Allocatable.cpp b/cpp/src/IceGrid/Allocatable.cpp index df21a3fbfdb..4fa81c13583 100644 --- a/cpp/src/IceGrid/Allocatable.cpp +++ b/cpp/src/IceGrid/Allocatable.cpp @@ -205,7 +205,7 @@ Allocatable::tryAllocate(const AllocationRequestPtr& request, bool fromRelease) } } -bool +void Allocatable::release(const SessionIPtr& session, bool fromRelease) { bool isReleased = false; @@ -218,6 +218,7 @@ Allocatable::release(const SessionIPtr& session, bool fromRelease) { wait(); } + assert(!_releasing); } if(!_session || _session != session) @@ -230,93 +231,95 @@ Allocatable::release(const SessionIPtr& session, bool fromRelease) _session = 0; released(session); + + isReleased = true; - if(!_releasing) + if(!fromRelease && !_requests.empty()) { - if(!_requests.empty()) - { - assert(!_parent); - _releasing = true; // Prevent new allocations. - hasRequests = true; - } - - isReleased = true; + assert(!_parent); + _releasing = true; // Prevent new allocations. + hasRequests = true; } } } - if(_parent) + if(isReleased) { - return _parent->release(session, fromRelease); + releasedNoSync(session); } - if(hasRequests) + if(_parent) + { + _parent->release(session, fromRelease); + } + else if(!fromRelease) { - while(true) + if(hasRequests) { - AllocationRequestPtr request; - AllocatablePtr allocatable = dequeueAllocationAttempt(request); - if(!allocatable) + while(true) { - Lock sync(*this); - assert(_count == 0 && _requests.empty()); - _releasing = false; - notifyAll(); - return true; - } + AllocationRequestPtr request; + AllocatablePtr allocatable = dequeueAllocationAttempt(request); + if(!allocatable) + { + Lock sync(*this); + assert(_count == 0 && _requests.empty()); + _releasing = false; + notifyAll(); + return; + } - // - // Try to allocate the allocatable with the request or if - // there's no request, just notify the allocatable that it can - // be allocated again. - // - if(request && allocatable->allocate(request, true) || !request && allocatable->canTryAllocate()) - { - while(true) + // + // Try to allocate the allocatable with the request or if + // there's no request, just notify the allocatable that it can + // be allocated again. + // + if(request && allocatable->allocate(request, true) || !request && allocatable->canTryAllocate()) { + while(true) { - Lock sync(*this); - assert(_count); - - allocatable = 0; - request = 0; - - // - // Check if there's other requests from the session - // waiting to allocate this allocatable. - // - list<pair<AllocatablePtr, AllocationRequestPtr> >::iterator p = _requests.begin(); - while(p != _requests.end()) { - if(p->second && p->second->getSession() == _session) + Lock sync(*this); + assert(_count); + + allocatable = 0; + request = 0; + + // + // Check if there's other requests from the session + // waiting to allocate this allocatable. + // + list<pair<AllocatablePtr, AllocationRequestPtr> >::iterator p = _requests.begin(); + while(p != _requests.end()) { - allocatable = p->first; - request = p->second; - _requests.erase(p); - break; + if(p->second && p->second->getSession() == _session) + { + allocatable = p->first; + request = p->second; + _requests.erase(p); + break; + } + ++p; + } + if(!allocatable) + { + _releasing = false; + notifyAll(); + return; // We're done, the allocatable was released (but is allocated again)! } - ++p; - } - if(!allocatable) - { - _releasing = false; - notifyAll(); - return true; // We're done, the allocatable was released (but is allocated again)! } - } - assert(allocatable && request); - allocatable->allocate(request, true); + assert(allocatable && request); + allocatable->allocate(request, true); + } } } } + else if(isReleased) + { + canTryAllocate(); // Notify that this allocatable can be allocated. + } } - else if(isReleased) - { - canTryAllocate(); // Notify that this allocatable can be allocated. - return true; // The allocatable was released. - } - return false; } SessionIPtr @@ -383,7 +386,8 @@ Allocatable::allocate(const AllocationRequestPtr& request, bool tryAllocate, boo { return false; } - + + bool allocationCount = 0; try { Lock sync(*this); @@ -406,7 +410,7 @@ Allocatable::allocate(const AllocationRequestPtr& request, bool tryAllocate, boo assert(_count == 0); _session = request->getSession(); ++_count; - return true; // Allocated + allocationCount = _count; } } else if(_session == request->getSession()) @@ -416,7 +420,7 @@ Allocatable::allocate(const AllocationRequestPtr& request, bool tryAllocate, boo assert(_count > 0); ++_count; request->allocated(this, _session); - return true; // Allocated + allocationCount = _count; } } else @@ -440,12 +444,16 @@ Allocatable::allocate(const AllocationRequestPtr& request, bool tryAllocate, boo } throw ex; } - - if(_parent) + + if(allocationCount == 1) + { + allocatedNoSync(request->getSession()); + } + else if(allocationCount == 0 && _parent) { _parent->release(request->getSession(), fromRelease); } - return false; + return allocationCount > 0; } bool @@ -460,30 +468,37 @@ Allocatable::allocateFromChild(const AllocationRequestPtr& request, { return false; } - - Lock sync(*this); - if((!_session || _session == request->getSession()) && (fromRelease || !_releasing)) + + int allocationCount = 0; { - if(!_session) + Lock sync(*this); + if((!_session || _session == request->getSession()) && (fromRelease || !_releasing)) { - try - { - allocated(request->getSession()); - } - catch(const SessionDestroyedException&) + if(!_session) { - // Ignore + try + { + allocated(request->getSession()); + } + catch(const SessionDestroyedException&) + { + // Ignore + } } + _session = request->getSession(); + ++_count; + allocationCount = _count; + } + else + { + queueAllocationAttempt(child, request, tryAllocate); } - _session = request->getSession(); - ++_count; - return true; // Allocated } - else + + if(allocationCount == 1) { - queueAllocationAttempt(child, request, tryAllocate); + allocatedNoSync(request->getSession()); } - - return false; + return allocationCount > 0; } |