diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/libcmd/installables.cc | 38 | ||||
-rw-r--r-- | src/libcmd/repl.cc | 8 | ||||
-rw-r--r-- | src/libexpr/primops.cc | 29 | ||||
-rw-r--r-- | src/libmain/shared.cc | 11 | ||||
-rw-r--r-- | src/libstore/build/local-derivation-goal.cc | 5 | ||||
-rw-r--r-- | src/libutil/signals.cc | 9 | ||||
-rw-r--r-- | src/libutil/signals.hh | 2 |
7 files changed, 66 insertions, 36 deletions
diff --git a/src/libcmd/installables.cc b/src/libcmd/installables.cc index dca17555a..2c18653e4 100644 --- a/src/libcmd/installables.cc +++ b/src/libcmd/installables.cc @@ -547,6 +547,37 @@ std::vector<BuiltPathWithResult> Installable::build( return res; } +static void throwBuildErrors( + std::vector<KeyedBuildResult> & buildResults, + const Store & store) +{ + std::vector<KeyedBuildResult> failed; + for (auto & buildResult : buildResults) { + if (!buildResult.success()) { + failed.push_back(buildResult); + } + } + + auto failedResult = failed.begin(); + if (failedResult != failed.end()) { + if (failed.size() == 1) { + failedResult->rethrow(); + } else { + StringSet failedPaths; + for (; failedResult != failed.end(); failedResult++) { + if (!failedResult->errorMsg.empty()) { + logError(ErrorInfo{ + .level = lvlError, + .msg = failedResult->errorMsg, + }); + } + failedPaths.insert(failedResult->path.to_string(store)); + } + throw Error("build of %s failed", concatStringsSep(", ", quoteStrings(failedPaths))); + } + } +} + std::vector<std::pair<ref<Installable>, BuiltPathWithResult>> Installable::build2( ref<Store> evalStore, ref<Store> store, @@ -608,10 +639,9 @@ std::vector<std::pair<ref<Installable>, BuiltPathWithResult>> Installable::build if (settings.printMissing) printMissing(store, pathsToBuild, lvlInfo); - for (auto & buildResult : store->buildPathsWithResults(pathsToBuild, bMode, evalStore)) { - if (!buildResult.success()) - buildResult.rethrow(); - + auto buildResults = store->buildPathsWithResults(pathsToBuild, bMode, evalStore); + throwBuildErrors(buildResults, *store); + for (auto & buildResult : buildResults) { for (auto & aux : backmap[buildResult.path]) { std::visit(overloaded { [&](const DerivedPath::Built & bfd) { diff --git a/src/libcmd/repl.cc b/src/libcmd/repl.cc index 696bb3c12..525c25560 100644 --- a/src/libcmd/repl.cc +++ b/src/libcmd/repl.cc @@ -141,7 +141,11 @@ struct NixRepl * Note: This is `shared_ptr` to avoid garbage collection. */ std::shared_ptr<Value *> replOverlaysEvalFunction = + #if HAVE_BOEHMGC std::allocate_shared<Value *>(traceable_allocator<Value *>(), nullptr); + #else + std::make_shared<Value *>(nullptr); + #endif /** * Get the `info` AttrSet that's passed as the first argument to each @@ -262,6 +266,8 @@ ReplExitStatus NixRepl::mainLoop() std::string input; while (true) { + _isInterrupted = false; + // When continuing input from previous lines, don't print a prompt, just align to the same // number of chars as the prompt. if (!interacter->getLine(input, input.empty() ? ReplPromptType::ReplPrompt : ReplPromptType::ContinuationPrompt)) { @@ -424,8 +430,6 @@ ProcessLineResult NixRepl::processLine(std::string line) if (line.empty()) return ProcessLineResult::PromptAgain; - _isInterrupted = false; - std::string command, arg; if (line[0] == ':') { diff --git a/src/libexpr/primops.cc b/src/libexpr/primops.cc index 33a2688f1..e36b800c3 100644 --- a/src/libexpr/primops.cc +++ b/src/libexpr/primops.cc @@ -4355,10 +4355,13 @@ void EvalState::createBaseEnv() .doc = R"( Legacy version of Nix. Always returns "2.18.3-lix" on Lix. - To determine if features exist, Nix scripts should instead use direct - means of feature detection, such as checking for existence of - builtins they want to use. Doing so allows for much better compatibility - across implementations. + Code in the Nix language should use other means of feature detection + like detecting the presence of builtins, rather than trying to find + the version of the Nix implementation, as there may be other Nix + implementations with different feature combinations. + + If the feature you want to write compatibility code for cannot be + detected by any means, please file a Lix bug. )", }); @@ -4377,15 +4380,23 @@ void EvalState::createBaseEnv() )", }); - /* Language version. This should be increased every time a new - language feature gets added. It's not necessary to increase it - when primops get added, because you can just use `builtins ? - primOp' to check. */ + /* Legacy language version. + * This is fixed at 6, and will never change in the future on Lix. + * A better language versioning construct needs to be built instead. */ v.mkInt(6); addConstant("__langVersion", v, { .type = nInt, .doc = R"( - The current version of the Nix language. + The legacy version of the Nix language. Always is `6` on Lix, + matching Nix 2.18. + + Code in the Nix language should use other means of feature detection + like detecting the presence of builtins, rather than trying to find + the version of the Nix implementation, as there may be other Nix + implementations with different feature combinations. + + If the feature you want to write compatibility code for cannot be + detected by any means, please file a Lix bug. )", }); diff --git a/src/libmain/shared.cc b/src/libmain/shared.cc index 9d4dd41ed..96ecbac8f 100644 --- a/src/libmain/shared.cc +++ b/src/libmain/shared.cc @@ -320,16 +320,7 @@ int handleExceptions(const std::string & programName, std::function<void()> fun) std::string error = ANSI_RED "error:" ANSI_NORMAL " "; try { - try { - fun(); - } catch (...) { - /* Subtle: we have to make sure that any `interrupted' - condition is discharged before we reach printMsg() - below, since otherwise it will throw an (uncaught) - exception. */ - setInterruptThrown(); - throw; - } + fun(); } catch (Exit & e) { return e.status; } catch (UsageError & e) { diff --git a/src/libstore/build/local-derivation-goal.cc b/src/libstore/build/local-derivation-goal.cc index e7a1e0147..3429afafa 100644 --- a/src/libstore/build/local-derivation-goal.cc +++ b/src/libstore/build/local-derivation-goal.cc @@ -174,6 +174,10 @@ void LocalDerivationGoal::killSandbox(bool getStats) void LocalDerivationGoal::tryLocalBuild() { +#if __APPLE__ + additionalSandboxProfile = parsedDrv->getStringAttr("__sandboxProfile").value_or(""); +#endif + unsigned int curBuilds = worker.getNrLocalBuilds(); if (curBuilds >= settings.maxBuildJobs) { state = &DerivationGoal::tryToBuild; @@ -192,7 +196,6 @@ void LocalDerivationGoal::tryLocalBuild() throw Error("derivation '%s' has '__noChroot' set, " "but that's not allowed when 'sandbox' is 'true'", worker.store.printStorePath(drvPath)); #if __APPLE__ - additionalSandboxProfile = parsedDrv->getStringAttr("__sandboxProfile").value_or(""); if (additionalSandboxProfile != "") throw Error("derivation '%s' specifies a sandbox profile, " "but this is only allowed when 'sandbox' is 'relaxed'", worker.store.printStorePath(drvPath)); diff --git a/src/libutil/signals.cc b/src/libutil/signals.cc index f5c79b325..41fdc9dc8 100644 --- a/src/libutil/signals.cc +++ b/src/libutil/signals.cc @@ -9,21 +9,14 @@ namespace nix { std::atomic<bool> _isInterrupted = false; -static thread_local bool interruptThrown = false; thread_local std::function<bool()> interruptCheck; -void setInterruptThrown() -{ - interruptThrown = true; -} - void _interrupted() { /* Block user interrupts while an exception is being handled. Throwing an exception while another exception is being handled kills the program! */ - if (!interruptThrown && !std::uncaught_exceptions()) { - interruptThrown = true; + if (!std::uncaught_exceptions()) { throw Interrupted("interrupted by the user"); } } diff --git a/src/libutil/signals.hh b/src/libutil/signals.hh index c58dc37cf..71593df95 100644 --- a/src/libutil/signals.hh +++ b/src/libutil/signals.hh @@ -22,8 +22,6 @@ extern std::atomic<bool> _isInterrupted; extern thread_local std::function<bool()> interruptCheck; -void setInterruptThrown(); - void _interrupted(); void inline checkInterrupt() |