libutil: allow graceful dropping of Pool::Handle
not needed yet, but returning a resource from the exception handling path that has ownership of a handle is currently not well-supported. we could also add a default constructor to Handle, but then we would also need to change the pool reference to a pointer. eventually that should be done since now resources can be swapped between pools with clever moves, but since that's not a problem yet we won't do it now. Change-Id: I26eb06581f7be34569e9e67a33da736128d167af
This commit is contained in:
parent
73507a7167
commit
f402c45cfa
1 changed files with 20 additions and 9 deletions
|
@ -108,6 +108,19 @@ public:
|
||||||
|
|
||||||
Handle(Pool & pool, std::shared_ptr<R> r) : pool(pool), r(r) { }
|
Handle(Pool & pool, std::shared_ptr<R> r) : pool(pool), r(r) { }
|
||||||
|
|
||||||
|
void drop(bool stillValid)
|
||||||
|
{
|
||||||
|
{
|
||||||
|
auto state_(pool.state.lock());
|
||||||
|
if (stillValid)
|
||||||
|
state_->idle.emplace_back(std::move(r));
|
||||||
|
assert(state_->inUse);
|
||||||
|
state_->inUse--;
|
||||||
|
}
|
||||||
|
pool.wakeup.notify_one();
|
||||||
|
r = nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
public:
|
public:
|
||||||
Handle(Handle && h) : pool(h.pool), r(h.r) { h.r.reset(); }
|
Handle(Handle && h) : pool(h.pool), r(h.r) { h.r.reset(); }
|
||||||
|
|
||||||
|
@ -115,15 +128,13 @@ public:
|
||||||
|
|
||||||
~Handle()
|
~Handle()
|
||||||
{
|
{
|
||||||
if (!r) return;
|
if (r)
|
||||||
{
|
drop(std::uncaught_exceptions() == 0);
|
||||||
auto state_(pool.state.lock());
|
|
||||||
if (!std::uncaught_exceptions())
|
|
||||||
state_->idle.push_back(ref<R>(r));
|
|
||||||
assert(state_->inUse);
|
|
||||||
state_->inUse--;
|
|
||||||
}
|
}
|
||||||
pool.wakeup.notify_one();
|
|
||||||
|
void release()
|
||||||
|
{
|
||||||
|
drop(true);
|
||||||
}
|
}
|
||||||
|
|
||||||
R * operator -> () { return &*r; }
|
R * operator -> () { return &*r; }
|
||||||
|
|
Loading…
Reference in a new issue