RemoteStore: Add option to drop old connections from the pool
This is a hack to make hydra-queue-runner free its temproots periodically, thereby ensuring that garbage collection of the corresponding paths is not blocked until the queue runner is restarted. It would be better if temproots could be released earlier than at process exit. I started working on a RAII object returned by functions like addToStore() that releases temproots. However, this would be a pretty massive change so I gave up on it for now.
This commit is contained in:
parent
308ecf6361
commit
89dc62c174
3 changed files with 31 additions and 1 deletions
|
@ -45,7 +45,13 @@ RemoteStore::RemoteStore(const Params & params)
|
||||||
, connections(make_ref<Pool<Connection>>(
|
, connections(make_ref<Pool<Connection>>(
|
||||||
std::max(1, (int) maxConnections),
|
std::max(1, (int) maxConnections),
|
||||||
[this]() { return openConnectionWrapper(); },
|
[this]() { return openConnectionWrapper(); },
|
||||||
[](const ref<Connection> & r) { return r->to.good() && r->from.good(); }
|
[this](const ref<Connection> & r) {
|
||||||
|
return
|
||||||
|
r->to.good()
|
||||||
|
&& r->from.good()
|
||||||
|
&& std::chrono::duration_cast<std::chrono::seconds>(
|
||||||
|
std::chrono::steady_clock::now() - r->startTime).count() < maxConnectionAge;
|
||||||
|
}
|
||||||
))
|
))
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
@ -106,6 +112,8 @@ ref<RemoteStore::Connection> UDSRemoteStore::openConnection()
|
||||||
conn->from.fd = conn->fd.get();
|
conn->from.fd = conn->fd.get();
|
||||||
conn->to.fd = conn->fd.get();
|
conn->to.fd = conn->fd.get();
|
||||||
|
|
||||||
|
conn->startTime = std::chrono::steady_clock::now();
|
||||||
|
|
||||||
initConnection(*conn);
|
initConnection(*conn);
|
||||||
|
|
||||||
return conn;
|
return conn;
|
||||||
|
@ -619,6 +627,12 @@ void RemoteStore::connect()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void RemoteStore::flushBadConnections()
|
||||||
|
{
|
||||||
|
connections->flushBad();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
RemoteStore::Connection::~Connection()
|
RemoteStore::Connection::~Connection()
|
||||||
{
|
{
|
||||||
try {
|
try {
|
||||||
|
|
|
@ -25,6 +25,9 @@ public:
|
||||||
const Setting<int> maxConnections{(Store*) this, 1,
|
const Setting<int> maxConnections{(Store*) this, 1,
|
||||||
"max-connections", "maximum number of concurrent connections to the Nix daemon"};
|
"max-connections", "maximum number of concurrent connections to the Nix daemon"};
|
||||||
|
|
||||||
|
const Setting<unsigned int> maxConnectionAge{(Store*) this, std::numeric_limits<unsigned int>::max(),
|
||||||
|
"max-connection-age", "number of seconds to reuse a connection"};
|
||||||
|
|
||||||
RemoteStore(const Params & params);
|
RemoteStore(const Params & params);
|
||||||
|
|
||||||
/* Implementations of abstract store API methods. */
|
/* Implementations of abstract store API methods. */
|
||||||
|
@ -95,6 +98,8 @@ public:
|
||||||
|
|
||||||
void connect() override;
|
void connect() override;
|
||||||
|
|
||||||
|
void flushBadConnections();
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
|
|
||||||
struct Connection
|
struct Connection
|
||||||
|
@ -102,6 +107,7 @@ protected:
|
||||||
FdSink to;
|
FdSink to;
|
||||||
FdSource from;
|
FdSource from;
|
||||||
unsigned int daemonVersion;
|
unsigned int daemonVersion;
|
||||||
|
std::chrono::time_point<std::chrono::steady_clock> startTime;
|
||||||
|
|
||||||
virtual ~Connection();
|
virtual ~Connection();
|
||||||
|
|
||||||
|
|
|
@ -168,6 +168,16 @@ public:
|
||||||
{
|
{
|
||||||
return state.lock()->max;
|
return state.lock()->max;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void flushBad()
|
||||||
|
{
|
||||||
|
auto state_(state.lock());
|
||||||
|
std::vector<ref<R>> left;
|
||||||
|
for (auto & p : state_->idle)
|
||||||
|
if (validator(p))
|
||||||
|
left.push_back(p);
|
||||||
|
std::swap(state_->idle, left);
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue