aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authoreldritch horrors <pennae@lix.systems>2024-04-27 18:51:39 +0200
committereldritch horrors <pennae@lix.systems>2024-05-07 14:35:20 +0000
commit230860dbb8fc061fd55b98cedd134cdc5097ea69 (patch)
tree21d68a7d3276eef5f978bbf97f4dcf344700bb3c
parent29f93e1e0d405440b35f1aa7c601dc5f601f9a90 (diff)
libstore: limit CA realisation info substitution concurrency
this seems to be an oversight, considering that regular substitutions are concurrency-limited. while not particularly necessary at present, once we've removed the `Callback` based interfaces it will be needed. Change-Id: Ide2d08169fcc24752cbd07a1d33fb8482f7034f5
-rw-r--r--src/libstore/build/drv-output-substitution-goal.cc14
-rw-r--r--src/libstore/build/drv-output-substitution-goal.hh7
-rw-r--r--src/libstore/build/worker.hh1
3 files changed, 22 insertions, 0 deletions
diff --git a/src/libstore/build/drv-output-substitution-goal.cc b/src/libstore/build/drv-output-substitution-goal.cc
index b30957c84..0e85650a7 100644
--- a/src/libstore/build/drv-output-substitution-goal.cc
+++ b/src/libstore/build/drv-output-substitution-goal.cc
@@ -3,6 +3,7 @@
#include "worker.hh"
#include "substitution-goal.hh"
#include "callback.hh"
+#include "signals.hh"
namespace nix {
@@ -38,6 +39,18 @@ void DrvOutputSubstitutionGoal::tryNext()
{
trace("trying next substituter");
+ /* Make sure that we are allowed to start a substitution. Note that even
+ if maxSubstitutionJobs == 0, we still allow a substituter to run. This
+ prevents infinite waiting. */
+ if (worker.runningCASubstitutions >= std::max(1U, settings.maxSubstitutionJobs.get())) {
+ worker.waitForBuildSlot(shared_from_this());
+ return;
+ }
+
+ maintainRunningSubstitutions =
+ std::make_unique<MaintainCount<uint64_t>>(worker.runningCASubstitutions);
+ worker.updateProgress();
+
if (subs.size() == 0) {
/* None left. Terminate this goal and let someone else deal
with it. */
@@ -87,6 +100,7 @@ void DrvOutputSubstitutionGoal::tryNext()
void DrvOutputSubstitutionGoal::realisationFetched()
{
worker.childTerminated(this);
+ maintainRunningSubstitutions.reset();
try {
outputInfo = downloadState->promise.get_future().get();
diff --git a/src/libstore/build/drv-output-substitution-goal.hh b/src/libstore/build/drv-output-substitution-goal.hh
index da2426e5e..ab6fb796e 100644
--- a/src/libstore/build/drv-output-substitution-goal.hh
+++ b/src/libstore/build/drv-output-substitution-goal.hh
@@ -41,6 +41,13 @@ class DrvOutputSubstitutionGoal : public Goal {
*/
std::shared_ptr<Store> sub;
+ /**
+ * The substituter thread.
+ */
+ std::thread thr;
+
+ std::unique_ptr<MaintainCount<uint64_t>> maintainRunningSubstitutions;
+
struct DownloadState
{
Pipe outPipe;
diff --git a/src/libstore/build/worker.hh b/src/libstore/build/worker.hh
index 23ad87914..ba4cd88d7 100644
--- a/src/libstore/build/worker.hh
+++ b/src/libstore/build/worker.hh
@@ -166,6 +166,7 @@ public:
uint64_t doneSubstitutions = 0;
uint64_t failedSubstitutions = 0;
uint64_t runningSubstitutions = 0;
+ uint64_t runningCASubstitutions = 0;
uint64_t expectedDownloadSize = 0;
uint64_t doneDownloadSize = 0;
uint64_t expectedNarSize = 0;