From 39087321811e81e26a1a47d6967df1088dcf0e95 Mon Sep 17 00:00:00 2001 From: Vincent Ambo Date: Tue, 19 May 2020 20:47:23 +0100 Subject: style(3p/nix): Final act in the brace-wrapping saga This last change set was generated by a full clang-tidy run (including compilation): clang-tidy -p ~/projects/nix-build/ \ -checks=-*,readability-braces-around-statements -fix src/*/*.cc Actually running clang-tidy requires some massaging to make it play nice with Nix + meson, I'll be adding a wrapper or something for that soon. --- third_party/default.nix | 1 + third_party/nix/default.nix | 1 + third_party/nix/src/build-remote/build-remote.cc | 17 +- third_party/nix/src/libexpr/attr-path.cc | 21 +- third_party/nix/src/libexpr/attr-set.cc | 3 +- third_party/nix/src/libexpr/common-eval-args.cc | 8 +- third_party/nix/src/libexpr/eval.cc | 155 ++++-- third_party/nix/src/libexpr/get-drvs.cc | 26 +- third_party/nix/src/libexpr/json-to-value.cc | 40 +- third_party/nix/src/libexpr/names.cc | 35 +- third_party/nix/src/libexpr/nixexpr.cc | 80 +-- third_party/nix/src/libexpr/primops.cc | 227 +++++--- third_party/nix/src/libexpr/value-to-json.cc | 3 +- third_party/nix/src/libexpr/value-to-xml.cc | 9 +- third_party/nix/src/libmain/shared.cc | 13 +- third_party/nix/src/libmain/stack.cc | 3 +- third_party/nix/src/libstore/binary-cache-store.cc | 23 +- third_party/nix/src/libstore/build.cc | 576 ++++++++++++++------- third_party/nix/src/libstore/crypto.cc | 6 +- third_party/nix/src/libstore/derivations.cc | 34 +- third_party/nix/src/libstore/download.cc | 75 ++- third_party/nix/src/libstore/export-import.cc | 9 +- third_party/nix/src/libstore/gc.cc | 95 ++-- third_party/nix/src/libstore/globals.cc | 32 +- third_party/nix/src/libstore/globals.hh | 15 +- .../nix/src/libstore/http-binary-cache-store.cc | 9 +- third_party/nix/src/libstore/legacy-ssh-store.cc | 18 +- .../nix/src/libstore/local-binary-cache-store.cc | 12 +- third_party/nix/src/libstore/local-fs-store.cc | 9 +- third_party/nix/src/libstore/local-store.cc | 171 +++--- third_party/nix/src/libstore/misc.cc | 58 ++- third_party/nix/src/libstore/nar-accessor.cc | 25 +- .../nix/src/libstore/nar-info-disk-cache.cc | 12 +- third_party/nix/src/libstore/nar-info.cc | 18 +- third_party/nix/src/libstore/optimise-store.cc | 12 +- third_party/nix/src/libstore/parsed-derivations.cc | 48 +- third_party/nix/src/libstore/pathlocks.cc | 25 +- third_party/nix/src/libstore/profiles.cc | 23 +- third_party/nix/src/libstore/references.cc | 6 +- third_party/nix/src/libstore/remote-fs-accessor.cc | 6 +- third_party/nix/src/libstore/remote-store.cc | 43 +- third_party/nix/src/libstore/sqlite.cc | 24 +- third_party/nix/src/libstore/ssh.cc | 21 +- third_party/nix/src/libstore/store-api.cc | 76 ++- third_party/nix/src/libutil/archive.cc | 47 +- third_party/nix/src/libutil/args.cc | 20 +- third_party/nix/src/libutil/compression.cc | 49 +- third_party/nix/src/libutil/config.cc | 58 ++- third_party/nix/src/libutil/hash.cc | 64 ++- third_party/nix/src/libutil/json.cc | 21 +- third_party/nix/src/libutil/serialise.cc | 14 +- third_party/nix/src/libutil/thread-pool.cc | 6 +- third_party/nix/src/libutil/util.cc | 203 +++++--- third_party/nix/src/libutil/xml-writer.cc | 21 +- third_party/nix/src/nix-build/nix-build.cc | 108 ++-- third_party/nix/src/nix-channel/nix-channel.cc | 30 +- .../src/nix-collect-garbage/nix-collect-garbage.cc | 20 +- .../nix/src/nix-copy-closure/nix-copy-closure.cc | 26 +- third_party/nix/src/nix-daemon/nix-daemon.cc | 120 +++-- third_party/nix/src/nix-env/nix-env.cc | 310 ++++++----- third_party/nix/src/nix-env/user-env.cc | 6 +- .../nix/src/nix-instantiate/nix-instantiate.cc | 60 ++- .../nix/src/nix-prefetch-url/nix-prefetch-url.cc | 57 +- third_party/nix/src/nix-store/nix-store.cc | 424 ++++++++------- third_party/nix/src/nix/build.cc | 6 +- third_party/nix/src/nix/cat.cc | 6 +- third_party/nix/src/nix/command.cc | 32 +- third_party/nix/src/nix/copy.cc | 3 +- third_party/nix/src/nix/doctor.cc | 12 +- third_party/nix/src/nix/edit.cc | 6 +- third_party/nix/src/nix/eval.cc | 3 +- third_party/nix/src/nix/hash.cc | 27 +- third_party/nix/src/nix/installables.cc | 64 ++- third_party/nix/src/nix/ls.cc | 12 +- third_party/nix/src/nix/main.cc | 12 +- third_party/nix/src/nix/path-info.cc | 6 +- third_party/nix/src/nix/repl.cc | 75 ++- third_party/nix/src/nix/run.cc | 37 +- third_party/nix/src/nix/search.cc | 6 +- third_party/nix/src/nix/show-config.cc | 3 +- third_party/nix/src/nix/sigs.cc | 15 +- third_party/nix/src/nix/upgrade-nix.cc | 18 +- third_party/nix/src/nix/verify.cc | 16 +- third_party/nix/src/nix/why-depends.cc | 13 +- 84 files changed, 2603 insertions(+), 1556 deletions(-) diff --git a/third_party/default.nix b/third_party/default.nix index 16d99cadf3..b48f405eba 100644 --- a/third_party/default.nix +++ b/third_party/default.nix @@ -33,6 +33,7 @@ let cairo cargo cgit + clang-tools clangStdenv clang_9 cmake diff --git a/third_party/nix/default.nix b/third_party/nix/default.nix index a62f16b4a2..263878cea4 100644 --- a/third_party/nix/default.nix +++ b/third_party/nix/default.nix @@ -20,6 +20,7 @@ in stdenv.mkDerivation { nativeBuildInputs = with pkgs; [ bison + clang-tools meson ninja pkgconfig diff --git a/third_party/nix/src/build-remote/build-remote.cc b/third_party/nix/src/build-remote/build-remote.cc index dd7aea9679..ef139c6bdc 100644 --- a/third_party/nix/src/build-remote/build-remote.cc +++ b/third_party/nix/src/build-remote/build-remote.cc @@ -39,10 +39,11 @@ static AutoCloseFD openSlotLock(const Machine& m, unsigned long long slot) { } static bool allSupportedLocally(const std::set& requiredFeatures) { - for (auto& feature : requiredFeatures) + for (auto& feature : requiredFeatures) { if (!settings.systemFeatures.get().count(feature)) { return false; } + } return true; } @@ -172,10 +173,11 @@ static int _main(int argc, char** argv) { } if (!bestSlotLock) { - if (rightType && !canBuildLocally) + if (rightType && !canBuildLocally) { std::cerr << "# postpone\n"; - else + } else { std::cerr << "# decline\n"; + } break; } @@ -194,8 +196,9 @@ static int _main(int argc, char** argv) { if (hasPrefix(bestMachine->storeUri, "ssh://")) { storeParams["max-connections"] = "1"; storeParams["log-fd"] = "4"; - if (bestMachine->sshKey != "") + if (bestMachine->sshKey != "") { storeParams["ssh-key"] = bestMachine->sshKey; + } } sshStore = openStore(bestMachine->storeUri, storeParams); @@ -254,15 +257,17 @@ static int _main(int argc, char** argv) { auto result = sshStore->buildDerivation(drvPath, drv); - if (!result.success()) + if (!result.success()) { throw Error("build of '%s' on '%s' failed: %s", drvPath, storeUri, result.errorMsg); + } PathSet missing; - for (auto& path : outputs) + for (auto& path : outputs) { if (!store->isValidPath(path)) { missing.insert(path); } + } if (!missing.empty()) { DLOG(INFO) << "copying outputs from '" << storeUri << "'"; diff --git a/third_party/nix/src/libexpr/attr-path.cc b/third_party/nix/src/libexpr/attr-path.cc index edab0b6df9..3d4e9c1e10 100644 --- a/third_party/nix/src/libexpr/attr-path.cc +++ b/third_party/nix/src/libexpr/attr-path.cc @@ -16,16 +16,18 @@ static Strings parseAttrPath(const string& s) { } else if (*i == '"') { ++i; while (1) { - if (i == s.end()) + if (i == s.end()) { throw Error(format("missing closing quote in selection path '%1%'") % s); + } if (*i == '"') { break; } cur.push_back(*i++); } - } else + } else { cur.push_back(*i); + } ++i; } if (!cur.empty()) { @@ -62,33 +64,38 @@ Value* findAlongAttrPath(EvalState& state, const string& attrPath, according to what is specified in the attrPath. */ if (apType == apAttr) { - if (v->type != tAttrs) + if (v->type != tAttrs) { throw TypeError(format("the expression selected by the selection path " "'%1%' should be a set but is %2%") % attrPath % showType(*v)); + } - if (attr.empty()) + if (attr.empty()) { throw Error(format("empty attribute name in selection path '%1%'") % attrPath); + } Bindings::iterator a = v->attrs->find(state.symbols.create(attr)); - if (a == v->attrs->end()) + if (a == v->attrs->end()) { throw Error( format("attribute '%1%' in selection path '%2%' not found") % attr % attrPath); + } v = &*a->value; } else if (apType == apIndex) { - if (!v->isList()) + if (!v->isList()) { throw TypeError(format("the expression selected by the selection path " "'%1%' should be a list but is %2%") % attrPath % showType(*v)); + } - if (attrIndex >= v->listSize()) + if (attrIndex >= v->listSize()) { throw Error( format("list index %1% in selection path '%2%' is out of range") % attrIndex % attrPath); + } v = v->listElems()[attrIndex]; } diff --git a/third_party/nix/src/libexpr/attr-set.cc b/third_party/nix/src/libexpr/attr-set.cc index d5bedbae43..fe1bf080ed 100644 --- a/third_party/nix/src/libexpr/attr-set.cc +++ b/third_party/nix/src/libexpr/attr-set.cc @@ -10,8 +10,9 @@ namespace nix { capacity. The space is implicitly reserved after the Bindings structure. */ Bindings* EvalState::allocBindings(size_t capacity) { - if (capacity > std::numeric_limits::max()) + if (capacity > std::numeric_limits::max()) { throw Error("attribute set of size %d is too big", capacity); + } return new (allocBytes(sizeof(Bindings) + sizeof(Attr) * capacity)) Bindings((Bindings::size_t)capacity); } diff --git a/third_party/nix/src/libexpr/common-eval-args.cc b/third_party/nix/src/libexpr/common-eval-args.cc index 8cd4bc56e5..7af4d6b276 100644 --- a/third_party/nix/src/libexpr/common-eval-args.cc +++ b/third_party/nix/src/libexpr/common-eval-args.cc @@ -36,11 +36,12 @@ Bindings* MixEvalArgs::getAutoArgs(EvalState& state) { Bindings* res = state.allocBindings(autoArgs.size()); for (auto& i : autoArgs) { Value* v = state.allocValue(); - if (i.second[0] == 'E') + if (i.second[0] == 'E') { state.mkThunk_( *v, state.parseExprFromString(string(i.second, 1), absPath("."))); - else + } else { mkString(*v, string(i.second, 1)); + } res->push_back(Attr(state.symbols.create(i.first), v)); } res->sort(); @@ -55,8 +56,9 @@ Path lookupFileArg(EvalState& state, string s) { } else if (s.size() > 2 && s.at(0) == '<' && s.at(s.size() - 1) == '>') { Path p = s.substr(1, s.size() - 2); return state.findFile(p); - } else + } else { return absPath(s); + } } } // namespace nix diff --git a/third_party/nix/src/libexpr/eval.cc b/third_party/nix/src/libexpr/eval.cc index 0ceb4d750b..c5329daf5f 100644 --- a/third_party/nix/src/libexpr/eval.cc +++ b/third_party/nix/src/libexpr/eval.cc @@ -62,17 +62,19 @@ static void printValue(std::ostream& str, std::set& active, break; case tString: str << "\""; - for (const char* i = v.string.s; *i; i++) - if (*i == '\"' || *i == '\\') + for (const char* i = v.string.s; *i; i++) { + if (*i == '\"' || *i == '\\') { str << "\\" << *i; - else if (*i == '\n') + } else if (*i == '\n') { str << "\\n"; - else if (*i == '\r') + } else if (*i == '\r') { str << "\\r"; - else if (*i == '\t') + } else if (*i == '\t') { str << "\\t"; - else + } else { str << *i; + } + } str << "\""; break; case tPath: @@ -281,7 +283,9 @@ static Strings parseNixPath(const string& s) { if (*p == ':') { if (isUri(std::string(start2, s.end()))) { ++p; - while (p != s.end() && *p != ':') ++p; + while (p != s.end() && *p != ':') { + ++p; + } } res.push_back(std::string(start, p)); if (p == s.end()) { @@ -361,8 +365,9 @@ EvalState::EvalState(const Strings& _searchPath, ref store) for (auto& path : closure) { allowedPaths->insert(path); } - } else + } else { allowedPaths->insert(r.second); + } } } @@ -400,9 +405,10 @@ Path EvalState::checkSourcePath(const Path& path_) { } } - if (!found) + if (!found) { throw RestrictedPathError( "access to path '%1%' is forbidden in restricted mode", abspath); + } /* Resolve symlinks. */ DLOG(INFO) << "checking access to '" << abspath << "'"; @@ -428,12 +434,14 @@ void EvalState::checkURI(const std::string& uri) { prefix. Thus, the prefix https://github.co does not permit access to https://github.com. Note: this allows 'http://' and 'https://' as prefixes for any http/https URI. */ - for (auto& prefix : evalSettings.allowedUris.get()) + for (auto& prefix : evalSettings.allowedUris.get()) { if (uri == prefix || (uri.size() > prefix.size() && prefix.size() > 0 && hasPrefix(uri, prefix) && - (prefix[prefix.size() - 1] == '/' || uri[prefix.size()] == '/'))) + (prefix[prefix.size() - 1] == '/' || uri[prefix.size()] == '/'))) { return; + } + } /* If the URI is a path, then check it against allowedPaths as well. */ @@ -600,9 +608,10 @@ inline Value* EvalState::lookupVar(Env* env, const ExprVar& var, bool noEval) { } return j->value; } - if (!env->prevWith) + if (!env->prevWith) { throwUndefinedVarError("undefined variable '%1%' at %2%", var.name, var.pos); + } for (size_t l = env->prevWith; l; --l, env = env->up) { ; } @@ -622,8 +631,9 @@ Value* EvalState::allocValue() { } Env& EvalState::allocEnv(size_t size) { - if (size > std::numeric_limits::max()) + if (size > std::numeric_limits::max()) { throw Error("environment size %d is too big", size); + } nrEnvs++; nrValuesInEnvs += size; @@ -669,8 +679,9 @@ void EvalState::mkPos(Value& v, Pos* pos) { mkInt(*allocAttr(v, sLine), pos->line); mkInt(*allocAttr(v, sColumn), pos->column); v.attrs->sort(); - } else + } else { mkNull(v); + } } /* Create a thunk for the delayed computation of the given expression @@ -823,8 +834,9 @@ void ExprAttrs::eval(EvalState& state, Env& env, Value& v) { if (hasOverrides && !i.second.inherited) { vAttr = state.allocValue(); mkThunk(*vAttr, env2, i.second.e); - } else + } else { vAttr = i.second.e->maybeThunk(state, i.second.inherited ? env : env2); + } env2.values[displ++] = vAttr; v.attrs->push_back(Attr(i.first, vAttr, &i.second.pos)); } @@ -850,16 +862,18 @@ void ExprAttrs::eval(EvalState& state, Env& env, Value& v) { if (j != attrs.end()) { (*newBnds)[j->second.displ] = i; env2.values[j->second.displ] = i.value; - } else + } else { newBnds->push_back(i); + } } newBnds->sort(); v.attrs = newBnds; } } else { - for (auto& i : attrs) + for (auto& i : attrs) { v.attrs->push_back( Attr(i.first, i.second.e->maybeThunk(state, env), &i.second.pos)); + } } /* Dynamic attrs apply *after* rec and __overrides. */ @@ -873,9 +887,10 @@ void ExprAttrs::eval(EvalState& state, Env& env, Value& v) { state.forceStringNoCtx(nameVal); Symbol nameSym = state.symbols.create(nameVal.string.s); Bindings::iterator j = v.attrs->find(nameSym); - if (j != v.attrs->end()) + if (j != v.attrs->end()) { throwEvalError("dynamic attribute '%1%' at %2% already defined at %3%", nameSym, i.pos, *j->pos); + } i.valueExpr->setName(nameSym); /* Keep sorted order so find can catch duplicates */ @@ -895,17 +910,19 @@ void ExprLet::eval(EvalState& state, Env& env, Value& v) { while the inherited attributes are evaluated in the original environment. */ size_t displ = 0; - for (auto& i : attrs->attrs) + for (auto& i : attrs->attrs) { env2.values[displ++] = i.second.e->maybeThunk(state, i.second.inherited ? env : env2); + } body->eval(state, env2, v); } void ExprList::eval(EvalState& state, Env& env, Value& v) { state.mkList(v, elems.size()); - for (size_t n = 0; n < elems.size(); ++n) + for (size_t n = 0; n < elems.size(); ++n) { v.listElems()[n] = elems[n]->maybeThunk(state, env); + } } void ExprVar::eval(EvalState& state, Env& env, Value& v) { @@ -919,10 +936,11 @@ static string showAttrPath(EvalState& state, Env& env, std::ostringstream out; bool first = true; for (auto& i : attrPath) { - if (!first) + if (!first) { out << '.'; - else + } else { first = false; + } try { out << getName(i, state, env); } catch (Error& e) { @@ -956,8 +974,9 @@ void ExprSelect::eval(EvalState& state, Env& env, Value& v) { } } else { state.forceAttrs(*vAttrs, pos); - if ((j = vAttrs->attrs->find(name)) == vAttrs->attrs->end()) + if ((j = vAttrs->attrs->find(name)) == vAttrs->attrs->end()) { throwEvalError("attribute '%1%' missing, at %2%", name, pos); + } } vAttrs = j->value; pos2 = j->pos; @@ -969,9 +988,10 @@ void ExprSelect::eval(EvalState& state, Env& env, Value& v) { state.forceValue(*vAttrs, (pos2 != NULL ? *pos2 : this->pos)); } catch (Error& e) { - if (pos2 && pos2->file != state.sDerivationNix) + if (pos2 && pos2->file != state.sDerivationNix) { addErrorPrefix(e, "while evaluating the attribute '%1%' at %2%:\n", showAttrPath(state, env, attrPath), *pos2); + } throw; } @@ -1112,9 +1132,10 @@ void EvalState::callFunction(Value& fun, Value& arg, Value& v, const Pos& pos) { for (auto& i : lambda.formals->formals) { Bindings::iterator j = arg.attrs->find(i.name); if (j == arg.attrs->end()) { - if (!i.def) + if (!i.def) { throwTypeError("%1% called without required argument '%2%', at %3%", lambda, i.name, pos); + } env2.values[displ++] = i.def->maybeThunk(*this, env2); } else { attrsUsed++; @@ -1127,11 +1148,13 @@ void EvalState::callFunction(Value& fun, Value& arg, Value& v, const Pos& pos) { if (!lambda.formals->ellipsis && attrsUsed != arg.attrs->size()) { /* Nope, so show the first unexpected argument to the user. */ - for (auto& i : *arg.attrs) + for (auto& i : *arg.attrs) { if (lambda.formals->argNames.find(i.name) == - lambda.formals->argNames.end()) + lambda.formals->argNames.end()) { throwTypeError("%1% called with unexpected argument '%2%', at %3%", lambda, i.name, pos); + } + } abort(); // can't happen } } @@ -1143,15 +1166,17 @@ void EvalState::callFunction(Value& fun, Value& arg, Value& v, const Pos& pos) { /* Evaluate the body. This is conditional on showTrace, because catching exceptions makes this function not tail-recursive. */ - if (settings.showTrace) try { + if (settings.showTrace) { + try { lambda.body->eval(*this, env2, v); } catch (Error& e) { addErrorPrefix(e, "while evaluating %1%, called from %2%:\n", lambda, pos); throw; } - else + } else { fun.lambda.fun->body->eval(*this, env2, v); + } } // Lifted out of callFunction() because it creates a temporary that @@ -1181,13 +1206,14 @@ void EvalState::autoCallFunction(Bindings& args, Value& fun, Value& res) { for (auto& i : fun.lambda.fun->formals->formals) { Bindings::iterator j = args.find(i.name); - if (j != args.end()) + if (j != args.end()) { actualArgs->attrs->push_back(*j); - else if (!i.def) + } else if (!i.def) { throwTypeError( "cannot auto-call a function that has an argument without a default " "value ('%1%')", i.name); + } } actualArgs->attrs->sort(); @@ -1278,10 +1304,11 @@ void ExprOpUpdate::eval(EvalState& state, Env& env, Value& v) { v.attrs->push_back(*j); ++i; ++j; - } else if (i->name < j->name) + } else if (i->name < j->name) { v.attrs->push_back(*i++); - else + } else { v.attrs->push_back(*j++); + } } while (i != v1.attrs->end()) { @@ -1364,20 +1391,23 @@ void ExprConcatStrings::eval(EvalState& state, Env& env, Value& v) { firstType = tFloat; nf = n; nf += vTmp.fpoint; - } else + } else { throwEvalError("cannot add %1% to an integer, at %2%", showType(vTmp), pos); + } } else if (firstType == tFloat) { if (vTmp.type == tInt) { nf += vTmp.integer; } else if (vTmp.type == tFloat) { nf += vTmp.fpoint; - } else + } else { throwEvalError("cannot add %1% to a float, at %2%", showType(vTmp), pos); - } else + } + } else { s << state.coerceToString(pos, vTmp, context, false, firstType == tString); + } } if (firstType == tInt) { @@ -1385,11 +1415,12 @@ void ExprConcatStrings::eval(EvalState& state, Env& env, Value& v) { } else if (firstType == tFloat) { mkFloat(v, nf); } else if (firstType == tPath) { - if (!context.empty()) + if (!context.empty()) { throwEvalError( "a string that refers to a store path cannot be appended to a path, " "at %1%", pos); + } auto path = canonPath(s.str()); mkPath(v, path.c_str()); } else { @@ -1415,13 +1446,15 @@ void EvalState::forceValueDeep(Value& v) { forceValue(v); if (v.type == tAttrs) { - for (auto& i : *v.attrs) try { + for (auto& i : *v.attrs) { + try { recurse(*i.value); } catch (Error& e) { addErrorPrefix(e, "while evaluating the attribute '%1%' at %2%:\n", i.name, *i.pos); throw; } + } } else if (v.isList()) { for (size_t n = 0; n < v.listSize(); ++n) { recurse(*v.listElems()[n]); @@ -1486,10 +1519,11 @@ string EvalState::forceString(Value& v, const Pos& pos) { } void copyContext(const Value& v, PathSet& context) { - if (v.string.context) + if (v.string.context) { for (const char** p = v.string.context; *p; ++p) { context.insert(*p); } + } } string EvalState::forceString(Value& v, PathSet& context, const Pos& pos) { @@ -1501,16 +1535,17 @@ string EvalState::forceString(Value& v, PathSet& context, const Pos& pos) { string EvalState::forceStringNoCtx(Value& v, const Pos& pos) { string s = forceString(v, pos); if (v.string.context) { - if (pos) + if (pos) { throwEvalError( "the string '%1%' is not allowed to refer to a store path (such as " "'%2%'), at %3%", v.string.s, v.string.context[0], pos); - else + } else { throwEvalError( "the string '%1%' is not allowed to refer to a store path (such as " "'%2%')", v.string.s, v.string.context[0]); + } } return s; } @@ -1567,13 +1602,15 @@ string EvalState::coerceToString(const Pos& pos, Value& v, PathSet& context, return *maybeString; } auto i = v.attrs->find(sOutPath); - if (i == v.attrs->end()) + if (i == v.attrs->end()) { throwTypeError("cannot coerce a set to a string, at %1%", pos); + } return coerceToString(pos, *i->value, context, coerceMore, copyToStore); } - if (v.type == tExternal) + if (v.type == tExternal) { return v.external->coerceToString(pos, context, coerceMore, copyToStore); + } if (coerceMore) { /* Note that `false' is represented as an empty string for @@ -1601,9 +1638,10 @@ string EvalState::coerceToString(const Pos& pos, Value& v, PathSet& context, copyToStore); if (n < v.listSize() - 1 /* !!! not quite correct */ - && - (!v.listElems()[n]->isList() || v.listElems()[n]->listSize() != 0)) + && (!v.listElems()[n]->isList() || + v.listElems()[n]->listSize() != 0)) { result += " "; + } } return result; } @@ -1613,13 +1651,14 @@ string EvalState::coerceToString(const Pos& pos, Value& v, PathSet& context, } string EvalState::copyPathToStore(PathSet& context, const Path& path) { - if (nix::isDerivation(path)) + if (nix::isDerivation(path)) { throwEvalError("file names are not allowed to end in '%1%'", drvExtension); + } Path dstPath; - if (srcToStore[path] != "") + if (srcToStore[path] != "") { dstPath = srcToStore[path]; - else { + } else { dstPath = settings.readOnlyMode ? store @@ -1638,9 +1677,10 @@ string EvalState::copyPathToStore(PathSet& context, const Path& path) { Path EvalState::coerceToPath(const Pos& pos, Value& v, PathSet& context) { string path = coerceToString(pos, v, context, false, false); - if (path == "" || path[0] != '/') + if (path == "" || path[0] != '/') { throwEvalError("string '%1%' doesn't represent an absolute path, at %2%", path, pos); + } return path; } @@ -1827,10 +1867,11 @@ void EvalState::printStats() { auto list = topObj.list("functions"); for (auto& i : functionCalls) { auto obj = list.object(); - if (i.first->name.set()) + if (i.first->name.set()) { obj.attr("name", (const string&)i.first->name); - else + } else { obj.attr("name", nullptr); + } if (i.first->pos) { obj.attr("file", (const string&)i.first->pos.file); obj.attr("line", i.first->pos.line); @@ -1885,10 +1926,11 @@ size_t valueSize(Value& v) { switch (v.type) { case tString: sz += doString(v.string.s); - if (v.string.context) + if (v.string.context) { for (const char** p = v.string.context; *p; ++p) { sz += doString(*p); } + } break; case tPath: sz += doString(v.path); @@ -1908,8 +1950,9 @@ size_t valueSize(Value& v) { if (seen.find(v.listElems()) == seen.end()) { seen.insert(v.listElems()); sz += v.listSize() * sizeof(Value*); - for (size_t n = 0; n < v.listSize(); ++n) + for (size_t n = 0; n < v.listSize(); ++n) { sz += doValue(*v.listElems()[n]); + } } break; case tThunk: @@ -1947,11 +1990,13 @@ size_t valueSize(Value& v) { size_t sz = sizeof(Env) + sizeof(Value*) * env.size; - if (env.type != Env::HasWithExpr) - for (size_t i = 0; i < env.size; ++i) + if (env.type != Env::HasWithExpr) { + for (size_t i = 0; i < env.size; ++i) { if (env.values[i]) { sz += doValue(*env.values[i]); } + } + } if (env.up) { sz += doEnv(*env.up); diff --git a/third_party/nix/src/libexpr/get-drvs.cc b/third_party/nix/src/libexpr/get-drvs.cc index 8897db4be9..c62e05d454 100644 --- a/third_party/nix/src/libexpr/get-drvs.cc +++ b/third_party/nix/src/libexpr/get-drvs.cc @@ -25,18 +25,20 @@ DrvInfo::DrvInfo(EvalState& state, ref store, name = storePathToName(drvPath); - if (spec.second.size() > 1) + if (spec.second.size() > 1) { throw Error( "building more than one derivation output is not supported, in '%s'", drvPathWithOutputs); + } outputName = spec.second.empty() ? get(drv.env, "outputName", "out") : *spec.second.begin(); auto i = drv.outputs.find(outputName); - if (i == drv.outputs.end()) + if (i == drv.outputs.end()) { throw Error("derivation '%s' does not have output '%s'", drvPath, outputName); + } outPath = i->second.path; } @@ -110,8 +112,9 @@ DrvInfo::Outputs DrvInfo::queryOutputs(bool onlyOutputsToInstall) { outputs[name] = state->coerceToPath(*outPath->pos, *outPath->value, context); } - } else + } else { outputs["out"] = queryOutPath(); + } } if (!onlyOutputsToInstall || !attrs) { return outputs; @@ -363,10 +366,11 @@ static void getDerivations(EvalState& state, Value& vIn, state.autoCallFunction(autoArgs, vIn, v); /* Process the expression. */ - if (!getDerivation(state, v, pathPrefix, drvs, done, ignoreAssertionFailures)) + if (!getDerivation(state, v, pathPrefix, drvs, done, + ignoreAssertionFailures)) { ; - else if (v.type == tAttrs) { + } else if (v.type == tAttrs) { /* !!! undocumented hackery to support combining channels in nix-env.cc. */ bool combineChannels = @@ -384,11 +388,11 @@ static void getDerivations(EvalState& state, Value& vIn, continue; } string pathPrefix2 = addToPath(pathPrefix, i->name); - if (combineChannels) + if (combineChannels) { getDerivations(state, *i->value, pathPrefix2, autoArgs, drvs, done, ignoreAssertionFailures); - else if (getDerivation(state, *i->value, pathPrefix2, drvs, done, - ignoreAssertionFailures)) { + } else if (getDerivation(state, *i->value, pathPrefix2, drvs, done, + ignoreAssertionFailures)) { /* If the value of this attribute is itself a set, should we recurse into it? => Only if it has a `recurseForDerivations = true' attribute. */ @@ -396,9 +400,10 @@ static void getDerivations(EvalState& state, Value& vIn, Bindings::iterator j = i->value->attrs->find( state.symbols.create("recurseForDerivations")); if (j != i->value->attrs->end() && - state.forceBool(*j->value, *j->pos)) + state.forceBool(*j->value, *j->pos)) { getDerivations(state, *i->value, pathPrefix2, autoArgs, drvs, done, ignoreAssertionFailures); + } } } } @@ -408,9 +413,10 @@ static void getDerivations(EvalState& state, Value& vIn, for (unsigned int n = 0; n < v.listSize(); ++n) { string pathPrefix2 = addToPath(pathPrefix, (format("%1%") % n).str()); if (getDerivation(state, *v.listElems()[n], pathPrefix2, drvs, done, - ignoreAssertionFailures)) + ignoreAssertionFailures)) { getDerivations(state, *v.listElems()[n], pathPrefix2, autoArgs, drvs, done, ignoreAssertionFailures); + } } } diff --git a/third_party/nix/src/libexpr/json-to-value.cc b/third_party/nix/src/libexpr/json-to-value.cc index 51d001d8a5..70628636e1 100644 --- a/third_party/nix/src/libexpr/json-to-value.cc +++ b/third_party/nix/src/libexpr/json-to-value.cc @@ -21,29 +21,30 @@ static string parseJSONString(const char*& s) { } if (*s == '\\') { s++; - if (*s == '"') + if (*s == '"') { res += '"'; - else if (*s == '\\') + } else if (*s == '\\') { res += '\\'; - else if (*s == '/') + } else if (*s == '/') { res += '/'; - else if (*s == '/') + } else if (*s == '/') { res += '/'; - else if (*s == 'b') + } else if (*s == 'b') { res += '\b'; - else if (*s == 'f') + } else if (*s == 'f') { res += '\f'; - else if (*s == 'n') + } else if (*s == 'n') { res += '\n'; - else if (*s == 'r') + } else if (*s == 'r') { res += '\r'; - else if (*s == 't') + } else if (*s == 't') { res += '\t'; - else if (*s == 'u') + } else if (*s == 'u') { throw JSONParseError( "\\u characters in JSON strings are currently not supported"); - else + } else { throw JSONParseError("invalid escaped character in JSON string"); + } s++; } else { res += *s++; @@ -76,8 +77,9 @@ static void parseJSON(EvalState& state, const char*& s, Value& v) { if (*s == ']') { break; } - if (*s != ',') + if (*s != ',') { throw JSONParseError("expected ',' or ']' after JSON array element"); + } s++; } s++; @@ -108,8 +110,9 @@ static void parseJSON(EvalState& state, const char*& s, Value& v) { if (*s == '}') { break; } - if (*s != ',') + if (*s != ',') { throw JSONParseError("expected ',' or '}' after JSON member"); + } s++; } state.mkAttrs(v, attrs.size()); @@ -137,10 +140,11 @@ static void parseJSON(EvalState& state, const char*& s, Value& v) { } try { - if (number_type == tFloat) + if (number_type == tFloat) { mkFloat(v, stod(tmp_number)); - else + } else { mkInt(v, stol(tmp_number)); + } } catch (std::invalid_argument& e) { throw JSONParseError("invalid JSON number"); } catch (std::out_of_range& e) { @@ -163,17 +167,19 @@ static void parseJSON(EvalState& state, const char*& s, Value& v) { mkNull(v); } - else + else { throw JSONParseError("unrecognised JSON value"); + } } void parseJSON(EvalState& state, const string& s_, Value& v) { const char* s = s_.c_str(); parseJSON(state, s, v); skipWhitespace(s); - if (*s) + if (*s) { throw JSONParseError( format("expected end-of-string while parsing JSON value: %1%") % s); + } } } // namespace nix diff --git a/third_party/nix/src/libexpr/names.cc b/third_party/nix/src/libexpr/names.cc index f83ed9fe64..184f30999e 100644 --- a/third_party/nix/src/libexpr/names.cc +++ b/third_party/nix/src/libexpr/names.cc @@ -25,9 +25,10 @@ DrvName::DrvName(const string& s) : hits(0) { bool DrvName::matches(DrvName& n) { if (name != "*") { - if (!regex) + if (!regex) { regex = std::unique_ptr( new std::regex(name, std::regex::extended)); + } if (!std::regex_match(n.name, *regex)) { return false; } @@ -41,7 +42,9 @@ bool DrvName::matches(DrvName& n) { string nextComponent(string::const_iterator& p, const string::const_iterator end) { /* Skip any dots and dashes (component separators). */ - while (p != end && (*p == '.' || *p == '-')) ++p; + while (p != end && (*p == '.' || *p == '-')) { + ++p; + } if (p == end) { return ""; @@ -51,10 +54,15 @@ string nextComponent(string::const_iterator& p, of digits. Otherwise, consume the longest sequence of non-digit, non-separator characters. */ string s; - if (isdigit(*p)) - while (p != end && isdigit(*p)) s += *p++; - else - while (p != end && (!isdigit(*p) && *p != '.' && *p != '-')) s += *p++; + if (isdigit(*p)) { + while (p != end && isdigit(*p)) { + s += *p++; + } + } else { + while (p != end && (!isdigit(*p) && *p != '.' && *p != '-')) { + s += *p++; + } + } return s; } @@ -65,14 +73,14 @@ static bool componentsLT(const string& c1, const string& c2) { if (c1Num && c2Num) { return n1 < n2; - } else if (c1 == "" && c2Num) + } else if (c1 == "" && c2Num) { return true; - else if (c1 == "pre" && c2 != "pre") + } else if (c1 == "pre" && c2 != "pre") { return true; - else if (c2 == "pre") + } else if (c2 == "pre") { return false; - /* Assume that `2.3a' < `2.3.1'. */ - else if (c2Num) { + /* Assume that `2.3a' < `2.3.1'. */ + } else if (c2Num) { return true; } else if (c1Num) { return false; @@ -88,10 +96,11 @@ int compareVersions(const string& v1, const string& v2) { while (p1 != v1.end() || p2 != v2.end()) { string c1 = nextComponent(p1, v1.end()); string c2 = nextComponent(p2, v2.end()); - if (componentsLT(c1, c2)) + if (componentsLT(c1, c2)) { return -1; - else if (componentsLT(c2, c1)) + } else if (componentsLT(c2, c1)) { return 1; + } } return 0; diff --git a/third_party/nix/src/libexpr/nixexpr.cc b/third_party/nix/src/libexpr/nixexpr.cc index bd171f8166..dc2c2b75e3 100644 --- a/third_party/nix/src/libexpr/nixexpr.cc +++ b/third_party/nix/src/libexpr/nixexpr.cc @@ -16,37 +16,40 @@ std::ostream& operator<<(std::ostream& str, const Expr& e) { static void showString(std::ostream& str, const string& s) { str << '"'; - for (auto c : (string)s) - if (c == '"' || c == '\\' || c == '$') + for (auto c : (string)s) { + if (c == '"' || c == '\\' || c == '$') { str << "\\" << c; - else if (c == '\n') + } else if (c == '\n') { str << "\\n"; - else if (c == '\r') + } else if (c == '\r') { str << "\\r"; - else if (c == '\t') + } else if (c == '\t') { str << "\\t"; - else + } else { str << c; + } + } str << '"'; } static void showId(std::ostream& str, const string& s) { - if (s.empty()) + if (s.empty()) { str << "\"\""; - else if (s == "if") // FIXME: handle other keywords + } else if (s == "if") { // FIXME: handle other keywords str << '"' << s << '"'; - else { + } else { char c = s[0]; if (!((c >= 'a' && c <= 'z') || (c >= 'A' && c <= 'Z') || c == '_')) { showString(str, s); return; } - for (auto c : s) + for (auto c : s) { if (!((c >= 'a' && c <= 'z') || (c >= 'A' && c <= 'Z') || (c >= '0' && c <= '9') || c == '_' || c == '\'' || c == '-')) { showString(str, s); return; } + } str << s; } } @@ -84,14 +87,17 @@ void ExprAttrs::show(std::ostream& str) const { str << "rec "; } str << "{ "; - for (auto& i : attrs) - if (i.second.inherited) + for (auto& i : attrs) { + if (i.second.inherited) { str << "inherit " << i.first << " " << "; "; - else + } else { str << i.first << " = " << *i.second.e << "; "; - for (auto& i : dynamicAttrs) + } + } + for (auto& i : dynamicAttrs) { str << "\"${" << *i.nameExpr << "}\" = " << *i.valueExpr << "; "; + } str << "}"; } @@ -109,10 +115,11 @@ void ExprLambda::show(std::ostream& str) const { str << "{ "; bool first = true; for (auto& i : formals->formals) { - if (first) + if (first) { first = false; - else + } else { str << ", "; + } str << i.name; if (i.def) { str << " ? " << *i.def; @@ -137,11 +144,13 @@ void ExprLambda::show(std::ostream& str) const { void ExprLet::show(std::ostream& str) const { str << "(let "; - for (auto& i : attrs->attrs) + for (auto& i : attrs->attrs) { if (i.second.inherited) { str << "inherit " << i.first << "; "; - } else + } else { str << i.first << " = " << *i.second.e << "; "; + } + } str << "in " << *body << ")"; } @@ -163,10 +172,11 @@ void ExprConcatStrings::show(std::ostream& str) const { bool first = true; str << "("; for (auto& i : *es) { - if (first) + if (first) { first = false; - else + } else { str << " + "; + } str << *i; } str << ")"; @@ -175,12 +185,13 @@ void ExprConcatStrings::show(std::ostream& str) const { void ExprPos::show(std::ostream& str) const { str << "__curPos"; } std::ostream& operator<<(std::ostream& str, const Pos& pos) { - if (!pos) + if (!pos) { str << "undefined position"; - else + } else { str << (format(ANSI_BOLD "%1%" ANSI_NORMAL ":%2%:%3%") % (string)pos.file % pos.line % pos.column) .str(); + } return str; } @@ -188,14 +199,16 @@ string showAttrPath(const AttrPath& attrPath) { std::ostringstream out; bool first = true; for (auto& i : attrPath) { - if (!first) + if (!first) { out << '.'; - else + } else { first = false; - if (i.symbol.set()) + } + if (i.symbol.set()) { out << i.symbol; - else + } else { out << "\"${" << *i.expr << "}\""; + } } return out.str(); } @@ -239,9 +252,10 @@ void ExprVar::bindVars(const StaticEnv& env) { /* Otherwise, the variable must be obtained from the nearest enclosing `with'. If there is no `with', then we can issue an "undefined variable" error now. */ - if (withLevel == -1) + if (withLevel == -1) { throw UndefinedVarError(format("undefined variable '%1%' at %2%") % name % pos); + } fromWith = true; this->level = withLevel; @@ -252,18 +266,20 @@ void ExprSelect::bindVars(const StaticEnv& env) { if (def) { def->bindVars(env); } - for (auto& i : attrPath) + for (auto& i : attrPath) { if (!i.symbol.set()) { i.expr->bindVars(env); } + } } void ExprOpHasAttr::bindVars(const StaticEnv& env) { e->bindVars(env); - for (auto& i : attrPath) + for (auto& i : attrPath) { if (!i.symbol.set()) { i.expr->bindVars(env); } + } } void ExprAttrs::bindVars(const StaticEnv& env) { @@ -315,10 +331,11 @@ void ExprLambda::bindVars(const StaticEnv& env) { newEnv.vars[i.name] = displ++; } - for (auto& i : formals->formals) + for (auto& i : formals->formals) { if (i.def) { i.def->bindVars(newEnv); } + } } body->bindVars(newEnv); @@ -332,8 +349,9 @@ void ExprLet::bindVars(const StaticEnv& env) { newEnv.vars[i.first] = i.second.displ = displ++; } - for (auto& i : attrs->attrs) + for (auto& i : attrs->attrs) { i.second.e->bindVars(i.second.inherited ? env : newEnv); + } body->bindVars(newEnv); } diff --git a/third_party/nix/src/libexpr/primops.cc b/third_party/nix/src/libexpr/primops.cc index 850d17a8f4..6835f03c8b 100644 --- a/third_party/nix/src/libexpr/primops.cc +++ b/third_party/nix/src/libexpr/primops.cc @@ -37,8 +37,9 @@ std::pair decodeContext(const string& s) { size_t index = s.find("!", 1); return std::pair(string(s, index + 1), string(s, 1, index - 1)); - } else + } else { return std::pair(s.at(0) == '/' ? s : string(s, 1), ""); + } } InvalidPathError::InvalidPathError(const Path& path) @@ -62,9 +63,10 @@ void EvalState::realiseContext(const PathSet& context) { if (allowedPaths) { auto drv = store->derivationFromPath(decoded.first); DerivationOutputs::iterator i = drv.outputs.find(decoded.second); - if (i == drv.outputs.end()) + if (i == drv.outputs.end()) { throw Error("derivation '%s' does not have an output named '%s'", decoded.first, decoded.second); + } allowedPaths->insert(i->second.path); } } @@ -74,10 +76,11 @@ void EvalState::realiseContext(const PathSet& context) { return; } - if (!evalSettings.enableImportFromDerivation) + if (!evalSettings.enableImportFromDerivation) { throw EvalError(format("attempted to realize '%1%' during evaluation but " "'allow-import-from-derivation' is false") % *(drvs.begin())); + } /* For performance, prefetch all substitute info. */ PathSet willBuild, willSubstitute, unknown; @@ -178,20 +181,22 @@ void prim_importNative(EvalState& state, const Pos& pos, Value** args, string sym = state.forceStringNoCtx(*args[1], pos); void* handle = dlopen(path.c_str(), RTLD_LAZY | RTLD_LOCAL); - if (!handle) + if (!handle) { throw EvalError(format("could not open '%1%': %2%") % path % dlerror()); + } dlerror(); ValueInitializer func = (ValueInitializer)dlsym(handle, sym.c_str()); if (!func) { char* message = dlerror(); - if (message) + if (message) { throw EvalError(format("could not load symbol '%1%' from '%2%': %3%") % sym % path % message); - else + } else { throw EvalError(format("symbol '%1%' from '%2%' resolved to NULL when a " "function pointer was expected") % sym % path); + } } (func)(state, v); @@ -356,9 +361,10 @@ struct CompareValues { if (v1->type == tInt && v2->type == tFloat) { return v1->integer < v2->fpoint; } - if (v1->type != v2->type) + if (v1->type != v2->type) { throw EvalError(format("cannot compare %1% with %2%") % showType(*v1) % showType(*v2)); + } switch (v1->type) { case tInt: return v1->integer < v2->integer; @@ -388,19 +394,22 @@ static void prim_genericClosure(EvalState& state, const Pos& pos, Value** args, /* Get the start set. */ Bindings::iterator startSet = args[0]->attrs->find(state.symbols.create("startSet")); - if (startSet == args[0]->attrs->end()) + if (startSet == args[0]->attrs->end()) { throw EvalError(format("attribute 'startSet' required, at %1%") % pos); + } state.forceList(*startSet->value, pos); ValueList workSet; - for (unsigned int n = 0; n < startSet->value->listSize(); ++n) + for (unsigned int n = 0; n < startSet->value->listSize(); ++n) { workSet.push_back(startSet->value->listElems()[n]); + } /* Get the operator. */ Bindings::iterator op = args[0]->attrs->find(state.symbols.create("operator")); - if (op == args[0]->attrs->end()) + if (op == args[0]->attrs->end()) { throw EvalError(format("attribute 'operator' required, at %1%") % pos); + } state.forceValue(*op->value); /* Construct the closure by applying the operator to element of @@ -417,8 +426,9 @@ static void prim_genericClosure(EvalState& state, const Pos& pos, Value** args, state.forceAttrs(*e, pos); Bindings::iterator key = e->attrs->find(state.symbols.create("key")); - if (key == e->attrs->end()) + if (key == e->attrs->end()) { throw EvalError(format("attribute 'key' required, at %1%") % pos); + } state.forceValue(*key->value); if (doneKeys.find(key->value) != doneKeys.end()) { @@ -551,8 +561,9 @@ static void prim_derivationStrict(EvalState& state, const Pos& pos, /* Figure out the name first (for stack backtraces). */ Bindings::iterator attr = args[0]->attrs->find(state.sName); - if (attr == args[0]->attrs->end()) + if (attr == args[0]->attrs->end()) { throw EvalError(format("required attribute 'name' missing, at %1%") % pos); + } string drvName; Pos& posDrvName(*attr->pos); try { @@ -568,8 +579,9 @@ static void prim_derivationStrict(EvalState& state, const Pos& pos, std::ostringstream jsonBuf; std::unique_ptr jsonObject; attr = args[0]->attrs->find(state.sStructuredAttrs); - if (attr != args[0]->attrs->end() && state.forceBool(*attr->value, pos)) + if (attr != args[0]->attrs->end() && state.forceBool(*attr->value, pos)) { jsonObject = std::make_unique(jsonBuf); + } /* Check whether null attributes should be ignored. */ bool ignoreNulls = false; @@ -597,37 +609,41 @@ static void prim_derivationStrict(EvalState& state, const Pos& pos, const string& key = i->name; auto handleHashMode = [&](const std::string& s) { - if (s == "recursive") + if (s == "recursive") { outputHashRecursive = true; - else if (s == "flat") + } else if (s == "flat") { outputHashRecursive = false; - else + } else { throw EvalError( "invalid value '%s' for 'outputHashMode' attribute, at %s", s, posDrvName); + } }; auto handleOutputs = [&](const Strings& ss) { outputs.clear(); for (auto& j : ss) { - if (outputs.find(j) != outputs.end()) + if (outputs.find(j) != outputs.end()) { throw EvalError(format("duplicate derivation output '%1%', at %2%") % j % posDrvName); + } /* !!! Check whether j is a valid attribute name. */ /* Derivations cannot be named ‘drv’, because then we'd have an attribute ‘drvPath’ in the resulting set. */ - if (j == "drv") + if (j == "drv") { throw EvalError( format("invalid derivation output name 'drv', at %1%") % posDrvName); + } outputs.insert(j); } - if (outputs.empty()) + if (outputs.empty()) { throw EvalError( format("derivation cannot have an empty set of outputs, at %1%") % posDrvName); + } }; try { @@ -660,41 +676,43 @@ static void prim_derivationStrict(EvalState& state, const Pos& pos, auto placeholder(jsonObject->placeholder(key)); printValueAsJSON(state, true, *i->value, placeholder, context); - if (i->name == state.sBuilder) + if (i->name == state.sBuilder) { drv.builder = state.forceString(*i->value, context, posDrvName); - else if (i->name == state.sSystem) + } else if (i->name == state.sSystem) { drv.platform = state.forceStringNoCtx(*i->value, posDrvName); - else if (i->name == state.sOutputHash) + } else if (i->name == state.sOutputHash) { outputHash = state.forceStringNoCtx(*i->value, posDrvName); - else if (i->name == state.sOutputHashAlgo) + } else if (i->name == state.sOutputHashAlgo) { outputHashAlgo = state.forceStringNoCtx(*i->value, posDrvName); - else if (i->name == state.sOutputHashMode) + } else if (i->name == state.sOutputHashMode) { handleHashMode(state.forceStringNoCtx(*i->value, posDrvName)); - else if (i->name == state.sOutputs) { + } else if (i->name == state.sOutputs) { /* Require ‘outputs’ to be a list of strings. */ state.forceList(*i->value, posDrvName); Strings ss; - for (unsigned int n = 0; n < i->value->listSize(); ++n) + for (unsigned int n = 0; n < i->value->listSize(); ++n) { ss.emplace_back(state.forceStringNoCtx(*i->value->listElems()[n], posDrvName)); + } handleOutputs(ss); } } else { auto s = state.coerceToString(posDrvName, *i->value, context, true); drv.env.emplace(key, s); - if (i->name == state.sBuilder) + if (i->name == state.sBuilder) { drv.builder = s; - else if (i->name == state.sSystem) + } else if (i->name == state.sSystem) { drv.platform = s; - else if (i->name == state.sOutputHash) + } else if (i->name == state.sOutputHash) { outputHash = s; - else if (i->name == state.sOutputHashAlgo) + } else if (i->name == state.sOutputHashAlgo) { outputHashAlgo = s; - else if (i->name == state.sOutputHashMode) + } else if (i->name == state.sOutputHashMode) { handleHashMode(s); - else if (i->name == state.sOutputs) + } else if (i->name == state.sOutputs) { handleOutputs(tokenizeString(s)); + } } } @@ -728,8 +746,9 @@ static void prim_derivationStrict(EvalState& state, const Pos& pos, state.store->computeFSClosure(string(path, 1), refs); for (auto& j : refs) { drv.inputSrcs.insert(j); - if (isDerivation(j)) + if (isDerivation(j)) { drv.inputDrvs[j] = state.store->queryDerivationOutputNames(j); + } } } @@ -740,31 +759,36 @@ static void prim_derivationStrict(EvalState& state, const Pos& pos, } /* Otherwise it's a source file. */ - else + else { drv.inputSrcs.insert(path); + } } /* Do we have all required attributes? */ - if (drv.builder == "") + if (drv.builder == "") { throw EvalError(format("required attribute 'builder' missing, at %1%") % posDrvName); - if (drv.platform == "") + } + if (drv.platform == "") { throw EvalError(format("required attribute 'system' missing, at %1%") % posDrvName); + } /* Check whether the derivation name is valid. */ checkStoreName(drvName); - if (isDerivation(drvName)) + if (isDerivation(drvName)) { throw EvalError( format("derivation names are not allowed to end in '%1%', at %2%") % drvExtension % posDrvName); + } if (outputHash) { /* Handle fixed-output derivations. */ - if (outputs.size() != 1 || *(outputs.begin()) != "out") + if (outputs.size() != 1 || *(outputs.begin()) != "out") { throw Error(format("multiple outputs are not supported in fixed-output " "derivations, at %1%") % posDrvName); + } HashType ht = outputHashAlgo.empty() ? htUnknown : parseHashType(outputHashAlgo); @@ -797,7 +821,7 @@ static void prim_derivationStrict(EvalState& state, const Pos& pos, path. */ Hash h = hashDerivationModulo(*state.store, drv); - for (auto& i : drv.outputs) + for (auto& i : drv.outputs) { if (i.second.path == "") { Path outPath = state.store->makeOutputPath(i.first, h, drvName); if (!jsonObject) { @@ -805,6 +829,7 @@ static void prim_derivationStrict(EvalState& state, const Pos& pos, } i.second.path = outPath; } + } } /* Write the resulting term into the Nix store directory. */ @@ -868,9 +893,10 @@ static void prim_storePath(EvalState& state, const Pos& pos, Value** args, if (!state.store->isStorePath(path)) { path = canonPath(path, true); } - if (!state.store->isInStore(path)) + if (!state.store->isInStore(path)) { throw EvalError(format("path '%1%' is not in the Nix store, at %2%") % path % pos); + } Path path2 = state.store->toStorePath(path); if (!settings.readOnlyMode) { state.store->ensurePath(path2); @@ -939,10 +965,11 @@ static void prim_readFile(EvalState& state, const Pos& pos, Value** args, path % e.path % pos); } string s = readFile(state.checkSourcePath(state.toRealPath(path, context))); - if (s.find((char)0) != string::npos) + if (s.find((char)0) != string::npos) { throw Error(format("the contents of the file '%1%' cannot be represented " "as a Nix string") % path); + } mkString(v, s.c_str()); } @@ -965,8 +992,9 @@ static void prim_findFile(EvalState& state, const Pos& pos, Value** args, } i = v2.attrs->find(state.symbols.create("path")); - if (i == v2.attrs->end()) + if (i == v2.attrs->end()) { throw EvalError(format("attribute 'path' missing, at %1%") % pos); + } PathSet context; string path = state.coerceToString(pos, *i->value, context, false, false); @@ -993,8 +1021,9 @@ static void prim_hashFile(EvalState& state, const Pos& pos, Value** args, Value& v) { string type = state.forceStringNoCtx(*args[0], pos); HashType ht = parseHashType(type); - if (ht == htUnknown) + if (ht == htUnknown) { throw Error(format("unknown hash type '%1%', at %2%") % type % pos); + } PathSet context; // discarded Path p = state.coerceToPath(pos, *args[1], context); @@ -1079,10 +1108,11 @@ static void prim_toFile(EvalState& state, const Pos& pos, Value** args, PathSet refs; for (auto path : context) { - if (path.at(0) != '/') + if (path.at(0) != '/') { throw EvalError(format("in 'toFile': the file '%1%' cannot refer to " "derivation outputs, at %2%") % name % pos); + } refs.insert(path); } @@ -1150,8 +1180,9 @@ static void addPath(EvalState& state, const Pos& pos, const string& name, "added from '%1%'") % path); } - } else + } else { dstPath = expectedStorePath; + } mkString(v, dstPath, {dstPath}); } @@ -1160,15 +1191,17 @@ static void prim_filterSource(EvalState& state, const Pos& pos, Value** args, Value& v) { PathSet context; Path path = state.coerceToPath(pos, *args[1], context); - if (!context.empty()) + if (!context.empty()) { throw EvalError(format("string '%1%' cannot refer to other paths, at %2%") % path % pos); + } state.forceValue(*args[0]); - if (args[0]->type != tLambda) + if (args[0]->type != tLambda) { throw TypeError(format("first argument in call to 'filterSource' is not a " "function but %1%, at %2%") % showType(*args[0]) % pos); + } addPath(state, pos, baseNameOf(path), path, args[0], true, Hash(), v); } @@ -1187,24 +1220,26 @@ static void prim_path(EvalState& state, const Pos& pos, Value** args, if (n == "path") { PathSet context; path = state.coerceToPath(*attr.pos, *attr.value, context); - if (!context.empty()) + if (!context.empty()) { throw EvalError( format("string '%1%' cannot refer to other paths, at %2%") % path % *attr.pos); - } else if (attr.name == state.sName) + } + } else if (attr.name == state.sName) { name = state.forceStringNoCtx(*attr.value, *attr.pos); - else if (n == "filter") { + } else if (n == "filter") { state.forceValue(*attr.value); filterFun = attr.value; - } else if (n == "recursive") + } else if (n == "recursive") { recursive = state.forceBool(*attr.value, *attr.pos); - else if (n == "sha256") + } else if (n == "sha256") { expectedHash = Hash(state.forceStringNoCtx(*attr.value, *attr.pos), htSHA256); - else + } else { throw EvalError( format("unsupported argument '%1%' to 'addPath', at %2%") % attr.name % *attr.pos); + } } if (path.empty()) { throw EvalError(format("'path' required, at %1%") % pos); @@ -1229,8 +1264,9 @@ static void prim_attrNames(EvalState& state, const Pos& pos, Value** args, state.mkList(v, args[0]->attrs->size()); size_t n = 0; - for (auto& i : *args[0]->attrs) + for (auto& i : *args[0]->attrs) { mkString(*(v.listElems()[n++] = state.allocValue()), i.name); + } std::sort(v.listElems(), v.listElems() + n, [](Value* v1, Value* v2) { return strcmp(v1->string.s, v2->string.s) < 0; @@ -1265,8 +1301,9 @@ void prim_getAttr(EvalState& state, const Pos& pos, Value** args, Value& v) { state.forceAttrs(*args[1], pos); // !!! Should we create a symbol here or just do a lookup? Bindings::iterator i = args[1]->attrs->find(state.symbols.create(attr)); - if (i == args[1]->attrs->end()) + if (i == args[1]->attrs->end()) { throw EvalError(format("attribute '%1%' missing, at %2%") % attr % pos); + } // !!! add to stack trace? if (state.countCalls && i->pos) { state.attrSelects[*i->pos]++; @@ -1345,21 +1382,23 @@ static void prim_listToAttrs(EvalState& state, const Pos& pos, Value** args, state.forceAttrs(v2, pos); Bindings::iterator j = v2.attrs->find(state.sName); - if (j == v2.attrs->end()) + if (j == v2.attrs->end()) { throw TypeError( format( "'name' attribute missing in a call to 'listToAttrs', at %1%") % pos); + } string name = state.forceStringNoCtx(*j->value, pos); Symbol sym = state.symbols.create(name); if (seen.find(sym) == seen.end()) { Bindings::iterator j2 = v2.attrs->find(state.symbols.create(state.sValue)); - if (j2 == v2.attrs->end()) + if (j2 == v2.attrs->end()) { throw TypeError(format("'value' attribute missing in a call to " "'listToAttrs', at %1%") % pos); + } v.attrs->push_back(Attr(sym, j2->value, j2->pos)); seen.insert(sym); @@ -1434,8 +1473,9 @@ static void prim_catAttrs(EvalState& state, const Pos& pos, Value** args, static void prim_functionArgs(EvalState& state, const Pos& pos, Value** args, Value& v) { state.forceValue(*args[0]); - if (args[0]->type != tLambda) + if (args[0]->type != tLambda) { throw TypeError(format("'functionArgs' requires a function, at %1%") % pos); + } if (!args[0]->lambda.fun->matchAttrs) { state.mkAttrs(v, 0); @@ -1443,9 +1483,10 @@ static void prim_functionArgs(EvalState& state, const Pos& pos, Value** args, } state.mkAttrs(v, args[0]->lambda.fun->formals->formals.size()); - for (auto& i : args[0]->lambda.fun->formals->formals) + for (auto& i : args[0]->lambda.fun->formals->formals) { // !!! should optimise booleans (allocate only once) mkBool(*state.allocAttr(v, i.name), i.def); + } v.attrs->sort(); } @@ -1479,8 +1520,9 @@ static void prim_isList(EvalState& state, const Pos& pos, Value** args, static void elemAt(EvalState& state, const Pos& pos, Value& list, int n, Value& v) { state.forceList(list, pos); - if (n < 0 || (unsigned int)n >= list.listSize()) + if (n < 0 || (unsigned int)n >= list.listSize()) { throw Error(format("list index %1% is out of bounds, at %2%") % n % pos); + } state.forceValue(*list.listElems()[n]); v = *list.listElems()[n]; } @@ -1503,8 +1545,9 @@ static void prim_head(EvalState& state, const Pos& pos, Value** args, static void prim_tail(EvalState& state, const Pos& pos, Value** args, Value& v) { state.forceList(*args[0], pos); - if (args[0]->listSize() == 0) + if (args[0]->listSize() == 0) { throw Error(format("'tail' called on an empty list, at %1%") % pos); + } state.mkList(v, args[0]->listSize() - 1); for (unsigned int n = 0; n < v.listSize(); ++n) { v.listElems()[n] = args[0]->listElems()[n + 1]; @@ -1637,9 +1680,10 @@ static void prim_genList(EvalState& state, const Pos& pos, Value** args, Value& v) { auto len = state.forceInt(*args[1], pos); - if (len < 0) + if (len < 0) { throw EvalError(format("cannot create list of size %1%, at %2%") % len % pos); + } state.mkList(v, len); @@ -1698,10 +1742,11 @@ static void prim_partition(EvalState& state, const Pos& pos, Value** args, state.forceValue(*vElem); Value res; state.callFunction(*args[0], *vElem, res, pos); - if (state.forceBool(res, pos)) + if (state.forceBool(res, pos)) { right.push_back(vElem); - else + } else { wrong.push_back(vElem); + } } state.mkAttrs(v, 2); @@ -1805,8 +1850,9 @@ static void prim_div(EvalState& state, const Pos& pos, Value** args, Value& v) { NixInt i1 = state.forceInt(*args[0], pos); NixInt i2 = state.forceInt(*args[1], pos); /* Avoid division overflow as it might raise SIGFPE. */ - if (i1 == std::numeric_limits::min() && i2 == -1) + if (i1 == std::numeric_limits::min() && i2 == -1) { throw EvalError(format("overflow in integer division, at %1%") % pos); + } mkInt(v, i1 / i2); } } @@ -1859,9 +1905,10 @@ static void prim_substring(EvalState& state, const Pos& pos, Value** args, PathSet context; string s = state.coerceToString(pos, *args[2], context); - if (start < 0) + if (start < 0) { throw EvalError(format("negative start position in 'substring', at %1%") % pos); + } mkString(v, (unsigned int)start >= s.size() ? "" : string(s, start, len), context); @@ -1879,8 +1926,9 @@ static void prim_hashString(EvalState& state, const Pos& pos, Value** args, Value& v) { string type = state.forceStringNoCtx(*args[0], pos); HashType ht = parseHashType(type); - if (ht == htUnknown) + if (ht == htUnknown) { throw Error(format("unknown hash type '%1%', at %2%") % type % pos); + } PathSet context; // discarded string s = state.forceString(*args[1], context, pos); @@ -1910,11 +1958,12 @@ static void prim_match(EvalState& state, const Pos& pos, Value** args, const size_t len = match.size() - 1; state.mkList(v, len); for (size_t i = 0; i < len; ++i) { - if (!match[i + 1].matched) + if (!match[i + 1].matched) { mkNull(*(v.listElems()[i] = state.allocValue())); - else + } else { mkString(*(v.listElems()[i] = state.allocValue()), match[i + 1].str().c_str()); + } } } catch (std::regex_error& e) { @@ -1969,11 +2018,12 @@ static void prim_split(EvalState& state, const Pos& pos, Value** args, // Start at 1, beacause the first match is the whole string. state.mkList(*elem, slen); for (size_t si = 0; si < slen; ++si) { - if (!match[si + 1].matched) + if (!match[si + 1].matched) { mkNull(*(elem->listElems()[si] = state.allocValue())); - else + } else { mkString(*(elem->listElems()[si] = state.allocValue()), match[si + 1].str().c_str()); + } } // Add a string for non-matched suffix characters. @@ -2023,15 +2073,17 @@ static void prim_replaceStrings(EvalState& state, const Pos& pos, Value** args, Value& v) { state.forceList(*args[0], pos); state.forceList(*args[1], pos); - if (args[0]->listSize() != args[1]->listSize()) + if (args[0]->listSize() != args[1]->listSize()) { throw EvalError(format("'from' and 'to' arguments to 'replaceStrings' have " "different lengths, at %1%") % pos); + } vector from; from.reserve(args[0]->listSize()); - for (unsigned int n = 0; n < args[0]->listSize(); ++n) + for (unsigned int n = 0; n < args[0]->listSize(); ++n) { from.push_back(state.forceString(*args[0]->listElems()[n], pos)); + } vector> to; to.reserve(args[1]->listSize()); @@ -2051,7 +2103,7 @@ static void prim_replaceStrings(EvalState& state, const Pos& pos, Value** args, bool found = false; auto i = from.begin(); auto j = to.begin(); - for (; i != from.end(); ++i, ++j) + for (; i != from.end(); ++i, ++j) { if (s.compare(p, i->size(), *i) == 0) { found = true; res += j->first; @@ -2069,6 +2121,7 @@ static void prim_replaceStrings(EvalState& state, const Pos& pos, Value** args, j->second.clear(); break; } + } if (!found) { if (p < s.size()) { res += s[p]; @@ -2139,20 +2192,22 @@ void fetch(EvalState& state, const Pos& pos, Value** args, Value& v, for (auto& attr : *args[0]->attrs) { string n(attr.name); - if (n == "url") + if (n == "url") { request.uri = state.forceStringNoCtx(*attr.value, *attr.pos); - else if (n == "sha256") + } else if (n == "sha256") { request.expectedHash = Hash(state.forceStringNoCtx(*attr.value, *attr.pos), htSHA256); - else if (n == "name") + } else if (n == "name") { request.name = state.forceStringNoCtx(*attr.value, *attr.pos); - else + } else { throw EvalError(format("unsupported argument '%1%' to '%2%', at %3%") % attr.name % who % attr.pos); + } } - if (request.uri.empty()) + if (request.uri.empty()) { throw EvalError(format("'url' argument required, at %1%") % pos); + } } else { request.uri = state.forceStringNoCtx(*args[0], pos); @@ -2160,9 +2215,10 @@ void fetch(EvalState& state, const Pos& pos, Value** args, Value& v, state.checkURI(request.uri); - if (evalSettings.pureEval && !request.expectedHash) + if (evalSettings.pureEval && !request.expectedHash) { throw Error("in pure evaluation mode, '%s' requires a 'sha256' argument", who); + } auto res = getDownloader()->downloadCached(state.store, request); @@ -2282,10 +2338,11 @@ void EvalState::createBaseEnv() { // Paths addPrimOp("__toPath", 1, prim_toPath); - if (evalSettings.pureEval) + if (evalSettings.pureEval) { addPurityError("__storePath"); - else + } else { addPrimOp("__storePath", 1, prim_storePath); + } addPrimOp("__pathExists", 1, prim_pathExists); addPrimOp("baseNameOf", 1, prim_baseNameOf); addPrimOp("dirOf", 1, prim_dirOf); @@ -2387,9 +2444,11 @@ void EvalState::createBaseEnv() { } addConstant("__nixPath", v); - if (RegisterPrimOp::primOps) - for (auto& primOp : *RegisterPrimOp::primOps) + if (RegisterPrimOp::primOps) { + for (auto& primOp : *RegisterPrimOp::primOps) { addPrimOp(std::get<0>(primOp), std::get<1>(primOp), std::get<2>(primOp)); + } + } /* Now that we've added all primops, sort the `builtins' set, because attribute lookups expect it to be sorted. */ diff --git a/third_party/nix/src/libexpr/value-to-json.cc b/third_party/nix/src/libexpr/value-to-json.cc index e4f1c28537..eaf0fca3d3 100644 --- a/third_party/nix/src/libexpr/value-to-json.cc +++ b/third_party/nix/src/libexpr/value-to-json.cc @@ -58,8 +58,9 @@ void printValueAsJSON(EvalState& state, bool strict, Value& v, auto placeholder(obj.placeholder(j)); printValueAsJSON(state, strict, *a.value, placeholder, context); } - } else + } else { printValueAsJSON(state, strict, *i->value, out, context); + } break; } diff --git a/third_party/nix/src/libexpr/value-to-xml.cc b/third_party/nix/src/libexpr/value-to-xml.cc index a03924aa63..44dede4875 100644 --- a/third_party/nix/src/libexpr/value-to-xml.cc +++ b/third_party/nix/src/libexpr/value-to-xml.cc @@ -94,8 +94,9 @@ static void printValueAsXML(EvalState& state, bool strict, bool location, if (strict) { state.forceValue(*a->value); } - if (a->value->type == tString) + if (a->value->type == tString) { xmlAttrs["drvPath"] = drvPath = a->value->string.s; + } } a = v.attrs->find(state.sOutPath); @@ -103,8 +104,9 @@ static void printValueAsXML(EvalState& state, bool strict, bool location, if (strict) { state.forceValue(*a->value); } - if (a->value->type == tString) + if (a->value->type == tString) { xmlAttrs["outPath"] = a->value->string.s; + } } XMLOpenElement _(doc, "derivation", xmlAttrs); @@ -112,8 +114,9 @@ static void printValueAsXML(EvalState& state, bool strict, bool location, if (drvPath != "" && drvsSeen.find(drvPath) == drvsSeen.end()) { drvsSeen.insert(drvPath); showAttrs(state, strict, location, *v.attrs, doc, context, drvsSeen); - } else + } else { doc.writeEmptyElement("repeated"); + } } else { diff --git a/third_party/nix/src/libmain/shared.cc b/third_party/nix/src/libmain/shared.cc index 3df83733ad..332bd5c4ca 100644 --- a/third_party/nix/src/libmain/shared.cc +++ b/third_party/nix/src/libmain/shared.cc @@ -233,7 +233,9 @@ bool LegacyArgs::processFlag(Strings::iterator& pos, Strings::iterator end) { return true; } bool res = parseArg(pos, end); - if (res) ++pos; + if (res) { + ++pos; + } return res; } @@ -244,8 +246,9 @@ bool LegacyArgs::processArgs(const Strings& args, bool finish) { assert(args.size() == 1); Strings ss(args); auto pos = ss.begin(); - if (!parseArg(pos, ss.end())) + if (!parseArg(pos, ss.end())) { throw UsageError(format("unexpected argument '%1%'") % args.front()); + } return true; } @@ -346,8 +349,9 @@ RunPager::RunPager() { toPager.create(); pid = startProcess([&]() { - if (dup2(toPager.readSide.get(), STDIN_FILENO) == -1) + if (dup2(toPager.readSide.get(), STDIN_FILENO) == -1) { throw SysError("dupping stdin"); + } if (!getenv("LESS")) { setenv("LESS", "FRSXMK", 1); } @@ -363,8 +367,9 @@ RunPager::RunPager() { pid.setKillSignal(SIGINT); - if (dup2(toPager.writeSide.get(), STDOUT_FILENO) == -1) + if (dup2(toPager.writeSide.get(), STDOUT_FILENO) == -1) { throw SysError("dupping stdout"); + } } RunPager::~RunPager() { diff --git a/third_party/nix/src/libmain/stack.cc b/third_party/nix/src/libmain/stack.cc index 0d5b91c163..27c16f5d1f 100644 --- a/third_party/nix/src/libmain/stack.cc +++ b/third_party/nix/src/libmain/stack.cc @@ -58,8 +58,9 @@ void detectStackOverflow() { throw Error("cannot allocate alternative stack"); } stack.ss_flags = 0; - if (sigaltstack(&stack, 0) == -1) + if (sigaltstack(&stack, 0) == -1) { throw SysError("cannot set alternative stack"); + } struct sigaction act; sigfillset(&act.sa_mask); diff --git a/third_party/nix/src/libstore/binary-cache-store.cc b/third_party/nix/src/libstore/binary-cache-store.cc index 625ea1e11e..10a0ddfc13 100644 --- a/third_party/nix/src/libstore/binary-cache-store.cc +++ b/third_party/nix/src/libstore/binary-cache-store.cc @@ -19,9 +19,10 @@ namespace nix { BinaryCacheStore::BinaryCacheStore(const Params& params) : Store(params) { - if (secretKeyFile != "") + if (secretKeyFile != "") { secretKey = std::unique_ptr(new SecretKey(readFile(secretKeyFile))); + } StringSink sink; sink << narVersionMagic1; @@ -44,10 +45,11 @@ void BinaryCacheStore::init() { auto name = line.substr(0, colon); auto value = trim(line.substr(colon + 1, std::string::npos)); if (name == "StoreDir") { - if (value != storeDir) + if (value != storeDir) { throw Error(format("binary cache '%s' is for Nix stores with prefix " "'%s', not '%s'") % getUri() % value % storeDir); + } } else if (name == "WantMassQuery") { wantMassQuery_ = value == "1"; } else if (name == "Priority") { @@ -108,9 +110,10 @@ void BinaryCacheStore::writeNarInfo(ref narInfo) { state_->pathInfoCache.upsert(hashPart, std::shared_ptr(narInfo)); } - if (diskCache) + if (diskCache) { diskCache->upsertNarInfo(getUri(), hashPart, std::shared_ptr(narInfo)); + } } void BinaryCacheStore::addToStore(const ValidPathInfo& info, @@ -123,7 +126,8 @@ void BinaryCacheStore::addToStore(const ValidPathInfo& info, /* Verify that all references are valid. This may do some .narinfo reads, but typically they'll already be cached. */ - for (auto& ref : info.references) try { + for (auto& ref : info.references) { + try { if (ref != info.path) { queryPathInfo(ref); } @@ -132,6 +136,7 @@ void BinaryCacheStore::addToStore(const ValidPathInfo& info, "reference '%s' is not valid") % info.path % ref); } + } assert(nar->compare(0, narMagic.size(), narMagic) == 0); @@ -140,10 +145,11 @@ void BinaryCacheStore::addToStore(const ValidPathInfo& info, narInfo->narSize = nar->size(); narInfo->narHash = hashString(htSHA256, *nar); - if (info.narHash && info.narHash != narInfo->narHash) + if (info.narHash && info.narHash != narInfo->narHash) { throw Error( format("refusing to copy corrupted path '%1%' to binary cache") % info.path); + } auto accessor_ = std::dynamic_pointer_cast(accessor); @@ -203,8 +209,9 @@ void BinaryCacheStore::addToStore(const ValidPathInfo& info, if (repair || !fileExists(narInfo->url)) { stats.narWrite++; upsertFile(narInfo->url, *narCompressed, "application/x-nix-nar"); - } else + } else { stats.narWriteAverted++; + } stats.narWriteBytes += nar->size(); stats.narWriteCompressedBytes += narCompressed->size(); @@ -349,9 +356,9 @@ void BinaryCacheStore::addSignatures(const Path& storePath, std::shared_ptr BinaryCacheStore::getBuildLog(const Path& path) { Path drvPath; - if (isDerivation(path)) + if (isDerivation(path)) { drvPath = path; - else { + } else { try { auto info = queryPathInfo(path); // FIXME: add a "Log" field to .narinfo diff --git a/third_party/nix/src/libstore/build.cc b/third_party/nix/src/libstore/build.cc index 7aa44b4755..b1f63a4fac 100644 --- a/third_party/nix/src/libstore/build.cc +++ b/third_party/nix/src/libstore/build.cc @@ -333,10 +333,11 @@ class Worker { void addToWeakGoals(WeakGoals& goals, GoalPtr p) { // FIXME: necessary? // FIXME: O(n) - for (auto& i : goals) + for (auto& i : goals) { if (i.lock() == p) { return; } + } goals.push_back(p); } @@ -369,10 +370,11 @@ void Goal::waiteeDone(GoalPtr waitee, ExitCode result) { remaining waitees. */ for (auto& goal : waitees) { WeakGoals waiters2; - for (auto& j : goal->waiters) + for (auto& j : goal->waiters) { if (j.lock() != shared_from_this()) { waiters2.push_back(j); } + } goal->waiters = waiters2; } waitees.clear(); @@ -416,19 +418,23 @@ static void commonChildInit(Pipe& logPipe) { } /* Dup the write side of the logger pipe into stderr. */ - if (dup2(logPipe.writeSide.get(), STDERR_FILENO) == -1) + if (dup2(logPipe.writeSide.get(), STDERR_FILENO) == -1) { throw SysError("cannot pipe standard error into log file"); + } /* Dup stderr to stdout. */ - if (dup2(STDERR_FILENO, STDOUT_FILENO) == -1) + if (dup2(STDERR_FILENO, STDOUT_FILENO) == -1) { throw SysError("cannot dup stderr into stdout"); + } /* Reroute stdin to /dev/null. */ int fdDevNull = open(pathNullDevice.c_str(), O_RDWR); - if (fdDevNull == -1) + if (fdDevNull == -1) { throw SysError(format("cannot open '%1%'") % pathNullDevice); - if (dup2(fdDevNull, STDIN_FILENO) == -1) + } + if (dup2(fdDevNull, STDIN_FILENO) == -1) { throw SysError("cannot dup null device into stdin"); + } close(fdDevNull); } @@ -444,10 +450,11 @@ void handleDiffHook(uid_t uid, uid_t gid, Path tryA, Path tryB, Path drvPath, diffHookOptions.chdir = "/"; auto diffRes = runProgram(diffHookOptions); - if (!statusOk(diffRes.first)) + if (!statusOk(diffRes.first)) { throw ExecError(diffRes.first, fmt("diff-hook program '%1%' %2%", diffHook, statusToString(diffRes.first))); + } if (diffRes.second != "") { LOG(ERROR) << chomp(diffRes.second); @@ -503,11 +510,12 @@ UserLock::UserLock() { /* Get the members of the build-users-group. */ struct group* gr = getgrnam(settings.buildUsersGroup.get().c_str()); - if (!gr) + if (!gr) { throw Error( format( "the group '%1%' specified in 'build-users-group' does not exist") % settings.buildUsersGroup); + } gid = gr->gr_gid; /* Copy the result of getgrnam. */ @@ -517,9 +525,10 @@ UserLock::UserLock() { users.push_back(*p); } - if (users.empty()) + if (users.empty()) { throw Error(format("the build users group '%1%' has no members") % settings.buildUsersGroup); + } /* Find a user account that isn't currently in use for another build. */ @@ -527,9 +536,10 @@ UserLock::UserLock() { DLOG(INFO) << "trying user " << i; struct passwd* pw = getpwnam(i.c_str()); - if (!pw) + if (!pw) { throw Error(format("the user '%1%' in the group '%2%' does not exist") % i % settings.buildUsersGroup); + } createDirs(settings.nixStateDir + "/userpool"); @@ -538,9 +548,10 @@ UserLock::UserLock() { { auto lockedPaths(lockedPaths_.lock()); - if (lockedPaths->count(fnUserLock)) + if (lockedPaths->count(fnUserLock)) { /* We already have a lock on this one. */ continue; + } lockedPaths->insert(fnUserLock); } @@ -557,9 +568,10 @@ UserLock::UserLock() { uid = pw->pw_uid; /* Sanity check... */ - if (uid == getuid() || uid == geteuid()) + if (uid == getuid() || uid == geteuid()) { throw Error(format("the Nix user should not be a member of '%1%'") % settings.buildUsersGroup); + } #if __linux__ /* Get the list of supplementary groups of this build user. This @@ -568,10 +580,11 @@ UserLock::UserLock() { int ngroups = supplementaryGIDs.size(); int err = getgrouplist(pw->pw_name, pw->pw_gid, supplementaryGIDs.data(), &ngroups); - if (err == -1) + if (err == -1) { throw Error( format("failed to get list of supplementary groups for '%1%'") % pw->pw_name); + } supplementaryGIDs.resize(ngroups); #endif @@ -673,8 +686,9 @@ HookInstance::HookInstance() { sink = FdSink(toHook.writeSide.get()); std::map settings; globalConfig.getSettings(settings); - for (auto& setting : settings) + for (auto& setting : settings) { sink << 1 << setting.first << setting.second.value; + } sink << 0; } @@ -696,8 +710,9 @@ typedef map StringRewrites; std::string rewriteStrings(std::string s, const StringRewrites& rewrites) { for (auto& i : rewrites) { size_t j = 0; - while ((j = s.find(i.first, j)) != string::npos) + while ((j = s.find(i.first, j)) != string::npos) { s.replace(j, i.first.size(), i.second); + } } return s; } @@ -1045,8 +1060,9 @@ void DerivationGoal::killChild() { ::kill(-pid, SIGKILL); /* ignore the result */ buildUser->kill(); pid.wait(); - } else + } else { pid.kill(); + } assert(pid == -1); } @@ -1070,12 +1086,14 @@ void DerivationGoal::addWantedOutputs(const StringSet& outputs) { if (outputs.empty()) { wantedOutputs.clear(); needRestart = true; - } else - for (auto& i : outputs) + } else { + for (auto& i : outputs) { if (wantedOutputs.find(i) == wantedOutputs.end()) { wantedOutputs.insert(i); needRestart = true; } + } + } } void DerivationGoal::getDerivation() { @@ -1140,15 +1158,18 @@ void DerivationGoal::haveDerivation() { /* We are first going to try to create the invalid output paths through substitutes. If that doesn't work, we'll build them. */ - if (settings.useSubstitutes && parsedDrv->substitutesAllowed()) - for (auto& i : invalidOutputs) + if (settings.useSubstitutes && parsedDrv->substitutesAllowed()) { + for (auto& i : invalidOutputs) { addWaitee(worker.makeSubstitutionGoal( i, buildMode == bmRepair ? Repair : NoRepair)); + } + } - if (waitees.empty()) /* to prevent hang (no wake-up event) */ + if (waitees.empty()) { /* to prevent hang (no wake-up event) */ outputsSubstituted(); - else + } else { state = &DerivationGoal::outputsSubstituted; + } } void DerivationGoal::outputsSubstituted() { @@ -1189,10 +1210,11 @@ void DerivationGoal::outputsSubstituted() { repairClosure(); return; } - if (buildMode == bmCheck && nrInvalid > 0) + if (buildMode == bmCheck && nrInvalid > 0) { throw Error(format("some outputs of '%1%' are not valid, so checking is " "not possible") % drvPath); + } /* Otherwise, at least one of the output paths could not be produced using a substitute. So we have to build instead. */ @@ -1202,26 +1224,30 @@ void DerivationGoal::outputsSubstituted() { wantedOutputs = PathSet(); /* The inputs must be built before we can build this goal. */ - if (useDerivation) - for (auto& i : dynamic_cast(drv.get())->inputDrvs) + if (useDerivation) { + for (auto& i : dynamic_cast(drv.get())->inputDrvs) { addWaitee(worker.makeDerivationGoal( i.first, i.second, buildMode == bmRepair ? bmRepair : bmNormal)); + } + } for (auto& i : drv->inputSrcs) { if (worker.store.isValidPath(i)) { continue; } - if (!settings.useSubstitutes) + if (!settings.useSubstitutes) { throw Error(format("dependency '%1%' of '%2%' does not exist, and " "substitution is disabled") % i % drvPath); + } addWaitee(worker.makeSubstitutionGoal(i)); } - if (waitees.empty()) /* to prevent hang (no wake-up event) */ + if (waitees.empty()) { /* to prevent hang (no wake-up event) */ inputsRealised(); - else + } else { state = &DerivationGoal::inputsRealised; + } } void DerivationGoal::repairClosure() { @@ -1252,13 +1278,14 @@ void DerivationGoal::repairClosure() { worker.store.computeFSClosure(drvPath, inputClosure); } std::map outputsToDrv; - for (auto& i : inputClosure) + for (auto& i : inputClosure) { if (isDerivation(i)) { Derivation drv = worker.store.derivationFromPath(i); for (auto& j : drv.outputs) { outputsToDrv[j.second.path] = i; } } + } /* Check each path (slow!). */ PathSet broken; @@ -1269,10 +1296,11 @@ void DerivationGoal::repairClosure() { LOG(ERROR) << "found corrupted or missing path '" << i << "' in the output closure of '" << drvPath << "'"; Path drvPath2 = outputsToDrv[i]; - if (drvPath2 == "") + if (drvPath2 == "") { addWaitee(worker.makeSubstitutionGoal(i, Repair)); - else + } else { addWaitee(worker.makeDerivationGoal(drvPath2, PathSet(), bmRepair)); + } } if (waitees.empty()) { @@ -1285,10 +1313,11 @@ void DerivationGoal::repairClosure() { void DerivationGoal::closureRepaired() { trace("closure repaired"); - if (nrFailed > 0) + if (nrFailed > 0) { throw Error(format("some paths in the output closure of derivation '%1%' " "could not be repaired") % drvPath); + } done(BuildResult::AlreadyValid); } @@ -1296,8 +1325,9 @@ void DerivationGoal::inputsRealised() { trace("all inputs realised"); if (nrFailed != 0) { - if (!useDerivation) + if (!useDerivation) { throw Error(format("some dependencies of '%1%' are missing") % drvPath); + } LOG(ERROR) << "cannot build derivation '" << drvPath << "': " << nrFailed << " dependencies couldn't be built"; done(BuildResult::DependencyFailed); @@ -1321,21 +1351,24 @@ void DerivationGoal::inputsRealised() { /* Determine the full set of input paths. */ /* First, the input derivations. */ - if (useDerivation) + if (useDerivation) { for (auto& i : dynamic_cast(drv.get())->inputDrvs) { /* Add the relevant output closures of the input derivation `i' as input paths. Only add the closures of output paths that are specified as inputs. */ assert(worker.store.isValidPath(i.first)); Derivation inDrv = worker.store.derivationFromPath(i.first); - for (auto& j : i.second) - if (inDrv.outputs.find(j) != inDrv.outputs.end()) + for (auto& j : i.second) { + if (inDrv.outputs.find(j) != inDrv.outputs.end()) { worker.store.computeFSClosure(inDrv.outputs[j].path, inputPaths); - else + } else { throw Error(format("derivation '%1%' requires non-existent output " "'%2%' from input derivation '%3%'") % drvPath % j % i.first); + } + } } + } /* Second, the input sources. */ worker.store.computeFSClosure(drv->inputSrcs, inputPaths); @@ -1369,8 +1402,9 @@ void DerivationGoal::tryToBuild() { goal can start a build, and if not, the main loop will sleep a few seconds and then retry this goal. */ PathSet lockFiles; - for (auto& outPath : drv->outputPaths()) + for (auto& outPath : drv->outputPaths()) { lockFiles.insert(worker.store.toRealPath(outPath)); + } if (!outputLocks.lockPaths(lockFiles, "", false)) { worker.waitForAWhile(shared_from_this()); @@ -1394,10 +1428,11 @@ void DerivationGoal::tryToBuild() { } missingPaths = drv->outputPaths(); - if (buildMode != bmCheck) + if (buildMode != bmCheck) { for (auto& i : validPaths) { missingPaths.erase(i); } + } /* If any of the outputs already exist but are not valid, delete them. */ @@ -1494,8 +1529,9 @@ void replaceValidPath(const Path& storePath, const Path tmpPath) { if (pathExists(storePath)) { rename(storePath.c_str(), oldPath.c_str()); } - if (rename(tmpPath.c_str(), storePath.c_str()) == -1) + if (rename(tmpPath.c_str(), storePath.c_str()) == -1) { throw SysError(format("moving '%1%' to '%2%'") % tmpPath % storePath); + } deletePath(oldPath); } @@ -1527,8 +1563,9 @@ MakeError(NotDeterministic, BuildError) if (hook) { hook->builderOut.readSide = -1; hook->fromHook.readSide = -1; - } else + } else { builderOut.readSide = -1; + } /* Close the log file. */ closeLogFile(); @@ -1557,21 +1594,26 @@ MakeError(NotDeterministic, BuildError) 8ULL * 1024 * 1024; // FIXME: make configurable struct statvfs st; if (statvfs(worker.store.realStoreDir.c_str(), &st) == 0 && - (unsigned long long)st.f_bavail * st.f_bsize < required) + (unsigned long long)st.f_bavail * st.f_bsize < required) { diskFull = true; + } if (statvfs(tmpDir.c_str(), &st) == 0 && - (unsigned long long)st.f_bavail * st.f_bsize < required) + (unsigned long long)st.f_bavail * st.f_bsize < required) { diskFull = true; + } #endif deleteTmpDir(false); /* Move paths out of the chroot for easier debugging of build failures. */ - if (useChroot && buildMode == bmNormal) - for (auto& i : missingPaths) - if (pathExists(chrootRootDir + i)) + if (useChroot && buildMode == bmNormal) { + for (auto& i : missingPaths) { + if (pathExists(chrootRootDir + i)) { rename((chrootRootDir + i).c_str(), i.c_str()); + } + } + } std::string msg = (format("builder for '%1%' %2%") % drvPath % statusToString(status)) @@ -1683,10 +1725,10 @@ MakeError(NotDeterministic, BuildError) BuildResult::Status st = BuildResult::MiscFailure; - if (hook && WIFEXITED(status) && WEXITSTATUS(status) == 101) + if (hook && WIFEXITED(status) && WEXITSTATUS(status) == 101) { st = BuildResult::TimedOut; - else if (hook && (!WIFEXITED(status) || WEXITSTATUS(status) != 100)) { + } else if (hook && (!WIFEXITED(status) || WEXITSTATUS(status) != 100)) { } else { @@ -1788,8 +1830,9 @@ HookReply DerivationGoal::tryBuildHook() { } void chmod_(const Path& path, mode_t mode) { - if (chmod(path.c_str(), mode) == -1) + if (chmod(path.c_str(), mode) == -1) { throw SysError(format("setting permissions on '%1%'") % path); + } } int childEntry(void* arg) { @@ -1802,18 +1845,20 @@ PathSet DerivationGoal::exportReferences(PathSet storePaths) { for (auto storePath : storePaths) { /* Check that the store path is valid. */ - if (!worker.store.isInStore(storePath)) + if (!worker.store.isInStore(storePath)) { throw BuildError( format("'exportReferencesGraph' contains a non-store path '%1%'") % storePath); + } storePath = worker.store.toStorePath(storePath); - if (!inputPaths.count(storePath)) + if (!inputPaths.count(storePath)) { throw BuildError( "cannot export references of path '%s' because it is not in the " "input closure of the derivation", storePath); + } worker.store.computeFSClosure(storePath, paths); } @@ -1827,8 +1872,9 @@ PathSet DerivationGoal::exportReferences(PathSet storePaths) { for (auto& j : paths2) { if (isDerivation(j)) { Derivation drv = worker.store.derivationFromPath(j); - for (auto& k : drv.outputs) + for (auto& k : drv.outputs) { worker.store.computeFSClosure(k.second.path, paths); + } } } @@ -1859,13 +1905,14 @@ static void preloadNSS() { void DerivationGoal::startBuilder() { /* Right platform? */ - if (!parsedDrv->canBuildLocally()) + if (!parsedDrv->canBuildLocally()) { throw Error( "a '%s' with features {%s} is required to build '%s', but I am a '%s' " "with features {%s}", drv->platform, concatStringsSep(", ", parsedDrv->getRequiredSystemFeatures()), drvPath, settings.thisSystem, concatStringsSep(", ", settings.systemFeatures)); + } if (drv->isBuiltin()) { preloadNSS(); @@ -1880,10 +1927,11 @@ void DerivationGoal::startBuilder() { { auto noChroot = parsedDrv->getBoolAttr("__noChroot"); if (settings.sandboxMode == smEnabled) { - if (noChroot) + if (noChroot) { throw Error(format("derivation '%1%' has '__noChroot' set, " "but that's not allowed when 'sandbox' is 'true'") % drvPath); + } #if __APPLE__ if (additionalSandboxProfile != "") throw Error( @@ -1892,10 +1940,11 @@ void DerivationGoal::startBuilder() { drvPath); #endif useChroot = true; - } else if (settings.sandboxMode == smDisabled) + } else if (settings.sandboxMode == smDisabled) { useChroot = false; - else if (settings.sandboxMode == smRelaxed) + } else if (settings.sandboxMode == smRelaxed) { useChroot = !fixedOutput && !noChroot; + } } if (worker.store.storeDir != worker.store.realStoreDir) { @@ -1932,8 +1981,9 @@ void DerivationGoal::startBuilder() { chownToBuilder(tmpDir); /* Substitute output placeholders with the actual output paths. */ - for (auto& output : drv->outputs) + for (auto& output : drv->outputs) { inputRewrites[hashPlaceholder(output.first)] = output.second.path; + } /* Construct the environment passed to the builder. */ initEnv(); @@ -1951,9 +2001,10 @@ void DerivationGoal::startBuilder() { fields are left empty. */ string s = get(drv->env, "exportReferencesGraph"); Strings ss = tokenizeString(s); - if (ss.size() % 2 != 0) + if (ss.size() % 2 != 0) { throw BuildError( format("odd number of tokens in 'exportReferencesGraph': '%1%'") % s); + } for (Strings::iterator i = ss.begin(); i != ss.end();) { string fileName = *i++; checkStoreName(fileName); /* !!! abuse of this function */ @@ -1985,23 +2036,27 @@ void DerivationGoal::startBuilder() { i.pop_back(); } size_t p = i.find('='); - if (p == string::npos) + if (p == string::npos) { dirsInChroot[i] = {i, optional}; - else + } else { dirsInChroot[string(i, 0, p)] = {string(i, p + 1), optional}; + } } dirsInChroot[tmpDirInSandbox] = tmpDir; /* Add the closure of store paths to the chroot. */ PathSet closure; - for (auto& i : dirsInChroot) try { - if (worker.store.isInStore(i.second.source)) + for (auto& i : dirsInChroot) { + try { + if (worker.store.isInStore(i.second.source)) { worker.store.computeFSClosure( worker.store.toStorePath(i.second.source), closure); + } } catch (InvalidPath& e) { } catch (Error& e) { throw Error(format("while processing 'sandbox-paths': %s") % e.what()); } + } for (auto& i : closure) { dirsInChroot[i] = i; } @@ -2027,10 +2082,11 @@ void DerivationGoal::startBuilder() { break; } } - if (!found) + if (!found) { throw Error(format("derivation '%1%' requested impure path '%2%', but " "it was not in allowed-impure-host-deps") % drvPath % i); + } dirsInChroot[i] = i; } @@ -2048,12 +2104,15 @@ void DerivationGoal::startBuilder() { DLOG(INFO) << "setting up chroot environment in '" << chrootRootDir << "'"; - if (mkdir(chrootRootDir.c_str(), 0750) == -1) + if (mkdir(chrootRootDir.c_str(), 0750) == -1) { throw SysError(format("cannot create '%1%'") % chrootRootDir); + } - if (buildUser && chown(chrootRootDir.c_str(), 0, buildUser->getGID()) == -1) + if (buildUser && + chown(chrootRootDir.c_str(), 0, buildUser->getGID()) == -1) { throw SysError(format("cannot change ownership of '%1%'") % chrootRootDir); + } /* Create a writable /tmp in the chroot. Many builders need this. (Of course they should really respect $TMPDIR @@ -2082,9 +2141,10 @@ void DerivationGoal::startBuilder() { .str()); /* Create /etc/hosts with localhost entry. */ - if (!fixedOutput) + if (!fixedOutput) { writeFile(chrootRootDir + "/etc/hosts", "127.0.0.1 localhost\n::1 localhost\n"); + } /* Make the closure of the inputs available in the chroot, rather than the whole Nix store. This prevents any access @@ -2098,18 +2158,20 @@ void DerivationGoal::startBuilder() { chmod_(chrootStoreDir, 01775); if (buildUser && - chown(chrootStoreDir.c_str(), 0, buildUser->getGID()) == -1) + chown(chrootStoreDir.c_str(), 0, buildUser->getGID()) == -1) { throw SysError(format("cannot change ownership of '%1%'") % chrootStoreDir); + } for (auto& i : inputPaths) { Path r = worker.store.toRealPath(i); struct stat st; - if (lstat(r.c_str(), &st)) + if (lstat(r.c_str(), &st)) { throw SysError(format("getting attributes of path '%1%'") % i); - if (S_ISDIR(st.st_mode)) + } + if (S_ISDIR(st.st_mode)) { dirsInChroot[i] = r; - else { + } else { Path p = chrootRootDir + i; DLOG(INFO) << "linking '" << p << "' to '" << r << "'"; if (link(r.c_str(), p.c_str()) == -1) { @@ -2117,8 +2179,9 @@ void DerivationGoal::startBuilder() { link count on a file (e.g. 32000 of ext3), which is quite possible after a `nix-store --optimise'. */ - if (errno != EMLINK) + if (errno != EMLINK) { throw SysError(format("linking '%1%' to '%2%'") % p % i); + } StringSink sink; dumpPath(r, sink); StringSource source(*sink.s); @@ -2145,8 +2208,9 @@ void DerivationGoal::startBuilder() { } if (needsHashRewrite()) { - if (pathExists(homeDir)) + if (pathExists(homeDir)) { throw Error(format("directory '%1%' exists; please remove it") % homeDir); + } /* We're not doing a chroot build, but we have some valid output paths. Since we can't just overwrite or delete @@ -2157,19 +2221,22 @@ void DerivationGoal::startBuilder() { corresponding to the valid outputs, and rewrite the contents of the new outputs to replace the dummy strings with the actual hashes. */ - if (validPaths.size() > 0) + if (validPaths.size() > 0) { for (auto& i : validPaths) { addHashRewrite(i); } + } /* If we're repairing, then we don't want to delete the corrupt outputs in advance. So rewrite them as well. */ - if (buildMode == bmRepair) - for (auto& i : missingPaths) + if (buildMode == bmRepair) { + for (auto& i : missingPaths) { if (worker.store.isValidPath(i) && pathExists(i)) { addHashRewrite(i); redirectedBadOutputs.insert(i); } + } + } } if (useChroot && settings.preBuildHook != "" && @@ -2196,10 +2263,11 @@ void DerivationGoal::startBuilder() { state = stBegin; } else { auto p = line.find('='); - if (p == string::npos) + if (p == string::npos) { dirsInChroot[line] = line; - else + } else { dirsInChroot[string(line, 0, p)] = string(line, p + 1); + } } } } @@ -2222,14 +2290,17 @@ void DerivationGoal::startBuilder() { std::string slaveName(ptsname(builderOut.readSide.get())); if (buildUser) { - if (chmod(slaveName.c_str(), 0600)) + if (chmod(slaveName.c_str(), 0600)) { throw SysError("changing mode of pseudoterminal slave"); + } - if (chown(slaveName.c_str(), buildUser->getUID(), 0)) + if (chown(slaveName.c_str(), buildUser->getUID(), 0)) { throw SysError("changing owner of pseudoterminal slave"); + } } else { - if (grantpt(builderOut.readSide.get())) + if (grantpt(builderOut.readSide.get())) { throw SysError("granting access to pseudoterminal slave"); + } } #if 0 @@ -2239,8 +2310,9 @@ void DerivationGoal::startBuilder() { dirsInChroot[slaveName] = {slaveName, false}; #endif - if (unlockpt(builderOut.readSide.get())) + if (unlockpt(builderOut.readSide.get())) { throw SysError("unlocking pseudoterminal"); + } builderOut.writeSide = open(slaveName.c_str(), O_RDWR | O_NOCTTY); if (!builderOut.writeSide) { @@ -2249,13 +2321,15 @@ void DerivationGoal::startBuilder() { // Put the pt into raw mode to prevent \n -> \r\n translation. struct termios term; - if (tcgetattr(builderOut.writeSide.get(), &term)) + if (tcgetattr(builderOut.writeSide.get(), &term)) { throw SysError("getting pseudoterminal attributes"); + } cfmakeraw(&term); - if (tcsetattr(builderOut.writeSide.get(), TCSANOW, &term)) + if (tcsetattr(builderOut.writeSide.get(), TCSANOW, &term)) { throw SysError("putting pseudoterminal into raw mode"); + } result.startTime = time(0); @@ -2316,8 +2390,9 @@ void DerivationGoal::startBuilder() { not seem to be a workaround for this. (But who can tell from reading user_namespaces(7)?) See also https://lwn.net/Articles/621612/. */ - if (getuid() == 0 && setgroups(0, 0) == -1) + if (getuid() == 0 && setgroups(0, 0) == -1) { throw SysError("setgroups failed"); + } size_t stackSize = 1 * 1024 * 1024; char* stack = @@ -2352,8 +2427,9 @@ void DerivationGoal::startBuilder() { parent. This is only done when sandbox-fallback is set to true (the default). */ if (child == -1 && (errno == EPERM || errno == EINVAL) && - settings.sandboxFallback) + settings.sandboxFallback) { _exit(1); + } if (child == -1) { throw SysError("cloning builder process"); } @@ -2368,8 +2444,9 @@ void DerivationGoal::startBuilder() { useChroot = false; initTmpDir(); goto fallback; - } else if (res != 0) + } else if (res != 0) { throw Error("unable to start build process"); + } userNamespaceSync.readSide = -1; @@ -2518,8 +2595,9 @@ void DerivationGoal::initEnv() { already know the cryptographic hash of the output). */ if (fixedOutput) { for (auto& i : - parsedDrv->getStringsAttr("impureEnvVars").value_or(Strings())) + parsedDrv->getStringsAttr("impureEnvVars").value_or(Strings())) { env[i] = getEnv(i); + } } /* Currently structured log messages piggyback on stderr, but we @@ -2543,8 +2621,9 @@ void DerivationGoal::writeStructuredAttrs() { /* Add an "outputs" object containing the output paths. */ nlohmann::json outputs; - for (auto& i : drv->outputs) + for (auto& i : drv->outputs) { outputs[i.first] = rewriteStrings(i.second.path, inputRewrites); + } json["outputs"] = outputs; /* Handle exportReferencesGraph. */ @@ -2592,8 +2671,9 @@ void DerivationGoal::writeStructuredAttrs() { return std::string("''"); } - if (value.is_boolean()) + if (value.is_boolean()) { return value.get() ? std::string("1") : std::string(""); + } return {}; }; @@ -2608,10 +2688,10 @@ void DerivationGoal::writeStructuredAttrs() { auto& value = i.value(); auto s = handleSimpleType(value); - if (s) + if (s) { jsonSh += fmt("declare %s=%s\n", i.key(), *s); - else if (value.is_array()) { + } else if (value.is_array()) { std::string s2; bool good = true; @@ -2657,8 +2737,9 @@ void DerivationGoal::chownToBuilder(const Path& path) { if (!buildUser) { return; } - if (chown(path.c_str(), buildUser->getUID(), buildUser->getGID()) == -1) + if (chown(path.c_str(), buildUser->getUID(), buildUser->getGID()) == -1) { throw SysError(format("cannot change ownership of '%1%'") % path); + } } void setupSeccomp() { @@ -2669,18 +2750,21 @@ void setupSeccomp() { #if HAVE_SECCOMP scmp_filter_ctx ctx; - if (!(ctx = seccomp_init(SCMP_ACT_ALLOW))) + if (!(ctx = seccomp_init(SCMP_ACT_ALLOW))) { throw SysError("unable to initialize seccomp mode 2"); + } Finally cleanup([&]() { seccomp_release(ctx); }); if (nativeSystem == "x86_64-linux" && - seccomp_arch_add(ctx, SCMP_ARCH_X86) != 0) + seccomp_arch_add(ctx, SCMP_ARCH_X86) != 0) { throw SysError("unable to add 32-bit seccomp architecture"); + } if (nativeSystem == "x86_64-linux" && - seccomp_arch_add(ctx, SCMP_ARCH_X32) != 0) + seccomp_arch_add(ctx, SCMP_ARCH_X32) != 0) { throw SysError("unable to add X32 seccomp architecture"); + } if (nativeSystem == "aarch64-linux" && seccomp_arch_add(ctx, SCMP_ARCH_ARM) != 0) { @@ -2692,18 +2776,21 @@ void setupSeccomp() { for (int perm : {S_ISUID, S_ISGID}) { if (seccomp_rule_add(ctx, SCMP_ACT_ERRNO(EPERM), SCMP_SYS(chmod), 1, SCMP_A1(SCMP_CMP_MASKED_EQ, (scmp_datum_t)perm, - (scmp_datum_t)perm)) != 0) + (scmp_datum_t)perm)) != 0) { throw SysError("unable to add seccomp rule"); + } if (seccomp_rule_add(ctx, SCMP_ACT_ERRNO(EPERM), SCMP_SYS(fchmod), 1, SCMP_A1(SCMP_CMP_MASKED_EQ, (scmp_datum_t)perm, - (scmp_datum_t)perm)) != 0) + (scmp_datum_t)perm)) != 0) { throw SysError("unable to add seccomp rule"); + } if (seccomp_rule_add(ctx, SCMP_ACT_ERRNO(EPERM), SCMP_SYS(fchmodat), 1, SCMP_A2(SCMP_CMP_MASKED_EQ, (scmp_datum_t)perm, - (scmp_datum_t)perm)) != 0) + (scmp_datum_t)perm)) != 0) { throw SysError("unable to add seccomp rule"); + } } /* Prevent builders from creating EAs or ACLs. Not all filesystems @@ -2714,15 +2801,18 @@ void setupSeccomp() { seccomp_rule_add(ctx, SCMP_ACT_ERRNO(ENOTSUP), SCMP_SYS(lsetxattr), 0) != 0 || seccomp_rule_add(ctx, SCMP_ACT_ERRNO(ENOTSUP), SCMP_SYS(fsetxattr), 0) != - 0) + 0) { throw SysError("unable to add seccomp rule"); + } if (seccomp_attr_set(ctx, SCMP_FLTATR_CTL_NNP, - settings.allowNewPrivileges ? 0 : 1) != 0) + settings.allowNewPrivileges ? 0 : 1) != 0) { throw SysError("unable to set 'no new privileges' seccomp attribute"); + } - if (seccomp_load(ctx) != 0) + if (seccomp_load(ctx) != 0) { throw SysError("unable to load seccomp BPF program"); + } #else throw Error( "seccomp is not supported on this platform; " @@ -2754,8 +2844,9 @@ void DerivationGoal::runChild() { (which may run under a different uid and/or in a sandbox). */ std::string netrcData; try { - if (drv->isBuiltin() && drv->builder == "builtin:fetchurl") + if (drv->isBuiltin() && drv->builder == "builtin:fetchurl") { netrcData = readFile(settings.netrcFile); + } } catch (SysError&) { } @@ -2763,8 +2854,9 @@ void DerivationGoal::runChild() { if (useChroot) { userNamespaceSync.writeSide = -1; - if (drainFD(userNamespaceSync.readSide.get()) != "1") + if (drainFD(userNamespaceSync.readSide.get()) != "1") { throw Error("user namespace initialisation failed"); + } userNamespaceSync.readSide = -1; @@ -2778,17 +2870,20 @@ void DerivationGoal::runChild() { struct ifreq ifr; strcpy(ifr.ifr_name, "lo"); ifr.ifr_flags = IFF_UP | IFF_LOOPBACK | IFF_RUNNING; - if (ioctl(fd.get(), SIOCSIFFLAGS, &ifr) == -1) + if (ioctl(fd.get(), SIOCSIFFLAGS, &ifr) == -1) { throw SysError("cannot set loopback interface flags"); + } } /* Set the hostname etc. to fixed values. */ char hostname[] = "localhost"; - if (sethostname(hostname, sizeof(hostname)) == -1) + if (sethostname(hostname, sizeof(hostname)) == -1) { throw SysError("cannot set host name"); + } char domainname[] = "(none)"; // kernel default - if (setdomainname(domainname, sizeof(domainname)) == -1) + if (setdomainname(domainname, sizeof(domainname)) == -1) { throw SysError("cannot set domain name"); + } /* Make all filesystems private. This is necessary because subtrees may have been mounted as "shared" @@ -2805,8 +2900,9 @@ void DerivationGoal::runChild() { /* Bind-mount chroot directory to itself, to treat it as a different filesystem from /, as needed for pivot_root. */ if (mount(chrootRootDir.c_str(), chrootRootDir.c_str(), 0, MS_BIND, 0) == - -1) + -1) { throw SysError(format("unable to bind mount '%1%'") % chrootRootDir); + } /* Set up a nearly empty /dev, unless the user asked to bind-mount the host /dev. */ @@ -2816,8 +2912,9 @@ void DerivationGoal::runChild() { createDirs(chrootRootDir + "/dev/pts"); ss.push_back("/dev/full"); if (settings.systemFeatures.get().count("kvm") && - pathExists("/dev/kvm")) + pathExists("/dev/kvm")) { ss.push_back("/dev/kvm"); + } ss.push_back("/dev/null"); ss.push_back("/dev/random"); ss.push_back("/dev/tty"); @@ -2844,8 +2941,9 @@ void DerivationGoal::runChild() { ss.push_back("/etc/services"); ss.push_back("/etc/hosts"); - if (pathExists("/var/run/nscd/socket")) + if (pathExists("/var/run/nscd/socket")) { ss.push_back("/var/run/nscd/socket"); + } } for (auto& i : ss) { @@ -2860,21 +2958,23 @@ void DerivationGoal::runChild() { DLOG(INFO) << "bind mounting '" << source << "' to '" << target << "'"; struct stat st; if (stat(source.c_str(), &st) == -1) { - if (optional && errno == ENOENT) + if (optional && errno == ENOENT) { return; - else + } else { throw SysError("getting attributes of path '%1%'", source); + } } - if (S_ISDIR(st.st_mode)) + if (S_ISDIR(st.st_mode)) { createDirs(target); - else { + } else { createDirs(dirOf(target)); writeFile(target, ""); } if (mount(source.c_str(), target.c_str(), "", MS_BIND | MS_REC, 0) == - -1) + -1) { throw SysError("bind mount from '%1%' to '%2%' failed", source, target); + } }; for (auto& i : dirsInChroot) { @@ -2886,15 +2986,18 @@ void DerivationGoal::runChild() { /* Bind a new instance of procfs on /proc. */ createDirs(chrootRootDir + "/proc"); - if (mount("none", (chrootRootDir + "/proc").c_str(), "proc", 0, 0) == -1) + if (mount("none", (chrootRootDir + "/proc").c_str(), "proc", 0, 0) == + -1) { throw SysError("mounting /proc"); + } /* Mount a new tmpfs on /dev/shm to ensure that whatever the builder puts in /dev/shm is cleaned up automatically. */ if (pathExists("/dev/shm") && mount("none", (chrootRootDir + "/dev/shm").c_str(), "tmpfs", 0, - fmt("size=%s", settings.sandboxShmSize).c_str()) == -1) + fmt("size=%s", settings.sandboxShmSize).c_str()) == -1) { throw SysError("mounting /dev/shm"); + } /* Mount a new devpts on /dev/pts. Note that this requires the kernel to be compiled with @@ -2920,26 +3023,32 @@ void DerivationGoal::runChild() { } /* Do the chroot(). */ - if (chdir(chrootRootDir.c_str()) == -1) + if (chdir(chrootRootDir.c_str()) == -1) { throw SysError(format("cannot change directory to '%1%'") % chrootRootDir); + } - if (mkdir("real-root", 0) == -1) + if (mkdir("real-root", 0) == -1) { throw SysError("cannot create real-root directory"); + } - if (pivot_root(".", "real-root") == -1) + if (pivot_root(".", "real-root") == -1) { throw SysError(format("cannot pivot old root directory onto '%1%'") % (chrootRootDir + "/real-root")); + } - if (chroot(".") == -1) + if (chroot(".") == -1) { throw SysError(format("cannot change root directory to '%1%'") % chrootRootDir); + } - if (umount2("real-root", MNT_DETACH) == -1) + if (umount2("real-root", MNT_DETACH) == -1) { throw SysError("cannot unmount real root filesystem"); + } - if (rmdir("real-root") == -1) + if (rmdir("real-root") == -1) { throw SysError("cannot remove real-root directory"); + } /* Switch to the sandbox uid/gid in the user namespace, which corresponds to the build user or calling user in @@ -2955,8 +3064,9 @@ void DerivationGoal::runChild() { } #endif - if (chdir(tmpDirInSandbox.c_str()) == -1) + if (chdir(tmpDirInSandbox.c_str()) == -1) { throw SysError(format("changing into '%1%'") % tmpDir); + } /* Close all other file descriptors. */ closeMostFDs({STDIN_FILENO, STDOUT_FILENO, STDERR_FILENO}); @@ -2970,8 +3080,9 @@ void DerivationGoal::runChild() { (settings.thisSystem == "x86_64-linux" || (!strcmp(utsbuf.sysname, "Linux") && !strcmp(utsbuf.machine, "x86_64")))) { - if (personality(PER_LINUX32) == -1) + if (personality(PER_LINUX32) == -1) { throw SysError("cannot set i686-linux personality"); + } } /* Impersonate a Linux 2.6 machine to get some determinism in @@ -3000,9 +3111,10 @@ void DerivationGoal::runChild() { /* Fill in the environment. */ Strings envStrs; - for (auto& i : env) + for (auto& i : env) { envStrs.push_back( rewriteStrings(i.first + "=" + i.second, inputRewrites)); + } /* If we are running in `build-users' mode, then switch to the user we allocated above. Make sure that we drop all root @@ -3015,16 +3127,19 @@ void DerivationGoal::runChild() { admins to specify groups such as "kvm". */ if (!buildUser->getSupplementaryGIDs().empty() && setgroups(buildUser->getSupplementaryGIDs().size(), - buildUser->getSupplementaryGIDs().data()) == -1) + buildUser->getSupplementaryGIDs().data()) == -1) { throw SysError("cannot set supplementary groups of build user"); + } if (setgid(buildUser->getGID()) == -1 || - getgid() != buildUser->getGID() || getegid() != buildUser->getGID()) + getgid() != buildUser->getGID() || getegid() != buildUser->getGID()) { throw SysError("setgid failed"); + } if (setuid(buildUser->getUID()) == -1 || - getuid() != buildUser->getUID() || geteuid() != buildUser->getUID()) + getuid() != buildUser->getUID() || geteuid() != buildUser->getUID()) { throw SysError("setuid failed"); + } } /* Fill in the arguments. */ @@ -3190,16 +3305,18 @@ void DerivationGoal::runChild() { if (drv->isBuiltin()) { try { BasicDerivation drv2(*drv); - for (auto& e : drv2.env) + for (auto& e : drv2.env) { e.second = rewriteStrings(e.second, inputRewrites); + } - if (drv->builder == "builtin:fetchurl") + if (drv->builder == "builtin:fetchurl") { builtinFetchurl(drv2, netrcData); - else if (drv->builder == "builtin:buildenv") + } else if (drv->builder == "builtin:buildenv") { builtinBuildenv(drv2); - else + } else { throw Error(format("unsupported builtin function '%1%'") % string(drv->builder, 8)); + } _exit(0); } catch (std::exception& e) { writeFull(STDERR_FILENO, "error: " + string(e.what()) + "\n"); @@ -3226,14 +3343,15 @@ PathSet parseReferenceSpecifiers(Store& store, const BasicDerivation& drv, const Strings& paths) { PathSet result; for (auto& i : paths) { - if (store.isStorePath(i)) + if (store.isStorePath(i)) { result.insert(i); - else if (drv.outputs.find(i) != drv.outputs.end()) + } else if (drv.outputs.find(i) != drv.outputs.end()) { result.insert(drv.outputs.find(i)->second.path); - else + } else { throw BuildError( format("derivation contains an illegal reference specifier '%1%'") % i); + } } return result; } @@ -3244,10 +3362,11 @@ void DerivationGoal::registerOutputs() { to do anything here. */ if (hook) { bool allValid = true; - for (auto& i : drv->outputs) + for (auto& i : drv->outputs) { if (!worker.store.isValidPath(i.second.path)) { allValid = false; } + } if (allValid) { return; } @@ -3281,14 +3400,15 @@ void DerivationGoal::registerOutputs() { actualPath = chrootRootDir + path; if (pathExists(actualPath)) { /* Move output paths from the chroot to the Nix store. */ - if (buildMode == bmRepair) + if (buildMode == bmRepair) { replaceValidPath(path, actualPath); - else if (buildMode != bmCheck && - rename(actualPath.c_str(), - worker.store.toRealPath(path).c_str()) == -1) + } else if (buildMode != bmCheck && + rename(actualPath.c_str(), + worker.store.toRealPath(path).c_str()) == -1) { throw SysError(format("moving build output '%1%' from the sandbox to " "the Nix store") % path); + } } if (buildMode != bmCheck) { actualPath = worker.store.toRealPath(path); @@ -3299,8 +3419,9 @@ void DerivationGoal::registerOutputs() { Path redirected = redirectedOutputs[path]; if (buildMode == bmRepair && redirectedBadOutputs.find(path) != redirectedBadOutputs.end() && - pathExists(redirected)) + pathExists(redirected)) { replaceValidPath(path, redirected); + } if (buildMode == bmCheck && redirected != "") { actualPath = redirected; } @@ -3308,10 +3429,11 @@ void DerivationGoal::registerOutputs() { struct stat st; if (lstat(actualPath.c_str(), &st) == -1) { - if (errno == ENOENT) + if (errno == ENOENT) { throw BuildError( format("builder for '%1%' failed to produce output path '%2%'") % drvPath % path); + } throw SysError(format("getting attributes of path '%1%'") % actualPath); } @@ -3321,10 +3443,11 @@ void DerivationGoal::registerOutputs() { build. Also, the output should be owned by the build user. */ if ((!S_ISLNK(st.st_mode) && (st.st_mode & (S_IWGRP | S_IWOTH))) || - (buildUser && st.st_uid != buildUser->getUID())) + (buildUser && st.st_uid != buildUser->getUID())) { throw BuildError(format("suspicious ownership or permission on '%1%'; " "rejecting this build output") % path); + } #endif /* Apply hash rewriting if necessary. */ @@ -3360,11 +3483,12 @@ void DerivationGoal::registerOutputs() { if (!recursive) { /* The output path should be a regular file without execute permission. */ - if (!S_ISREG(st.st_mode) || (st.st_mode & S_IXUSR) != 0) + if (!S_ISREG(st.st_mode) || (st.st_mode & S_IXUSR) != 0) { throw BuildError( format( "output path '%1%' should be a non-executable regular file") % path); + } } /* Check the hash. In hash mode, move the path produced by @@ -3386,20 +3510,23 @@ void DerivationGoal::registerOutputs() { Path actualDest = worker.store.toRealPath(dest); - if (worker.store.isValidPath(dest)) + if (worker.store.isValidPath(dest)) { std::rethrow_exception(delayedException); + } if (actualPath != actualDest) { PathLocks outputLocks({actualDest}); deletePath(actualDest); - if (rename(actualPath.c_str(), actualDest.c_str()) == -1) + if (rename(actualPath.c_str(), actualDest.c_str()) == -1) { throw SysError(format("moving '%1%' to '%2%'") % actualPath % dest); + } } path = dest; actualPath = actualDest; - } else + } else { assert(path == dest); + } info.ca = makeFixedOutputCA(recursive, h2); } @@ -3428,9 +3555,10 @@ void DerivationGoal::registerOutputs() { if (settings.runDiffHook || settings.keepFailed) { Path dst = worker.store.toRealPath(path + checkSuffix); deletePath(dst); - if (rename(actualPath.c_str(), dst.c_str())) + if (rename(actualPath.c_str(), dst.c_str())) { throw SysError(format("renaming '%1%' to '%2%'") % actualPath % dst); + } handleDiffHook(buildUser ? buildUser->getUID() : getuid(), buildUser ? buildUser->getGID() : getgid(), path, dst, @@ -3440,10 +3568,11 @@ void DerivationGoal::registerOutputs() { format("derivation '%1%' may not be deterministic: output '%2%' " "differs from '%3%'") % drvPath % path % dst); - } else + } else { throw NotDeterministic(format("derivation '%1%' may not be " "deterministic: output '%2%' differs") % drvPath % path); + } } /* Since we verified the build, it's now ultimately @@ -3461,10 +3590,11 @@ void DerivationGoal::registerOutputs() { paths. */ for (auto& i : inputPaths) { PathSet::iterator j = references.find(i); - if (j == references.end()) + if (j == references.end()) { DLOG(INFO) << "unreferenced input: '" << i << "'"; - else + } else { DLOG(INFO) << "referenced input: '" << i << "'"; + } } if (curRound == nrRounds) { @@ -3500,7 +3630,7 @@ void DerivationGoal::registerOutputs() { if (curRound > 1 && prevInfos != infos) { assert(prevInfos.size() == infos.size()); for (auto i = prevInfos.begin(), j = infos.begin(); i != prevInfos.end(); - ++i, ++j) + ++i, ++j) { if (!(*i == *j)) { result.isNonDeterministic = true; Path prev = i->second.path + checkSuffix; @@ -3524,6 +3654,7 @@ void DerivationGoal::registerOutputs() { LOG(ERROR) << msg; curRound = nrRounds; // we know enough, bail out early } + } } /* If this is the first round of several, then move the output out @@ -3534,8 +3665,9 @@ void DerivationGoal::registerOutputs() { Path prev = i.second.path + checkSuffix; deletePath(prev); Path dst = i.second.path + checkSuffix; - if (rename(i.second.path.c_str(), dst.c_str())) + if (rename(i.second.path.c_str(), dst.c_str())) { throw SysError(format("renaming '%1%' to '%2%'") % i.second.path % dst); + } } } @@ -3574,8 +3706,9 @@ void DerivationGoal::registerOutputs() { void DerivationGoal::checkOutputs( const std::map& outputs) { std::map outputsByPath; - for (auto& output : outputs) + for (auto& output : outputs) { outputsByPath.emplace(output.second.path, output.second); + } for (auto& output : outputs) { auto& outputName = output.first; @@ -3623,18 +3756,20 @@ void DerivationGoal::checkOutputs( }; auto applyChecks = [&](const Checks& checks) { - if (checks.maxSize && info.narSize > *checks.maxSize) + if (checks.maxSize && info.narSize > *checks.maxSize) { throw BuildError( "path '%s' is too large at %d bytes; limit is %d bytes", info.path, info.narSize, *checks.maxSize); + } if (checks.maxClosureSize) { uint64_t closureSize = getClosure(info.path).second; - if (closureSize > *checks.maxClosureSize) + if (closureSize > *checks.maxClosureSize) { throw BuildError( "closure of path '%s' is too large at %d bytes; limit is %d " "bytes", info.path, closureSize, *checks.maxClosureSize); + } } auto checkRefs = [&](const std::optional& value, bool allowed, @@ -3654,7 +3789,7 @@ void DerivationGoal::checkOutputs( PathSet badPaths; - for (auto& i : used) + for (auto& i : used) { if (allowed) { if (!spec.count(i)) { badPaths.insert(i); @@ -3664,6 +3799,7 @@ void DerivationGoal::checkOutputs( badPaths.insert(i); } } + } if (!badPaths.empty()) { string badPathsStr; @@ -3692,23 +3828,26 @@ void DerivationGoal::checkOutputs( Checks checks; auto maxSize = output->find("maxSize"); - if (maxSize != output->end()) + if (maxSize != output->end()) { checks.maxSize = maxSize->get(); + } auto maxClosureSize = output->find("maxClosureSize"); - if (maxClosureSize != output->end()) + if (maxClosureSize != output->end()) { checks.maxClosureSize = maxClosureSize->get(); + } auto get = [&](const std::string& name) -> std::optional { auto i = output->find(name); if (i != output->end()) { Strings res; for (auto j = i->begin(); j != i->end(); ++j) { - if (!j->is_string()) + if (!j->is_string()) { throw Error( "attribute '%s' of derivation '%s' must be a list of " "strings", name, drvPath); + } res.push_back(j->get()); } checks.disallowedRequisites = res; @@ -3759,16 +3898,18 @@ Path DerivationGoal::openLogFile() { fdLogFile = open(logFileName.c_str(), O_CREAT | O_WRONLY | O_TRUNC | O_CLOEXEC, 0666); - if (!fdLogFile) + if (!fdLogFile) { throw SysError(format("creating log file '%1%'") % logFileName); + } logFileSink = std::make_shared(fdLogFile.get()); - if (settings.compressLog) + if (settings.compressLog) { logSink = std::shared_ptr( makeCompressionSink("bzip2", *logFileSink)); - else + } else { logSink = logFileSink; + } return logFileName; } @@ -3792,8 +3933,9 @@ void DerivationGoal::deleteTmpDir(bool force) { if (settings.keepFailed && !force && !drv->isBuiltin()) { LOG(INFO) << "note: keeping build directory '" << tmpDir << "'"; chmod(tmpDir.c_str(), 0755); - } else + } else { deletePath(tmpDir); + } tmpDir = ""; } } @@ -3811,27 +3953,32 @@ void DerivationGoal::handleChildOutput(int fd, const string& data) { return; } - for (auto c : data) + for (auto c : data) { if (c == '\r') { currentLogLinePos = 0; } else if (c == '\n') { flushLine(); } else { - if (currentLogLinePos >= currentLogLine.size()) + if (currentLogLinePos >= currentLogLine.size()) { currentLogLine.resize(currentLogLinePos + 1); + } currentLogLine[currentLogLinePos++] = c; } + } - if (logSink) (*logSink)(data); + if (logSink) { + (*logSink)(data); + } } if (hook && fd == hook->fromHook.readSide.get()) { - for (auto c : data) + for (auto c : data) { if (c == '\n') { currentHookLine.clear(); } else { currentHookLine += c; } + } } } @@ -3843,9 +3990,10 @@ void DerivationGoal::handleEOF(int fd) { } void DerivationGoal::flushLine() { - if (settings.verboseBuild && (settings.printRepeatedBuilds || curRound == 1)) + if (settings.verboseBuild && + (settings.printRepeatedBuilds || curRound == 1)) { LOG(INFO) << currentLogLine; - else { + } else { logTail.push_back(currentLogLine); if (logTail.size() > settings.logLines) { logTail.pop_front(); @@ -3893,8 +4041,9 @@ void DerivationGoal::done(BuildResult::Status status, const string& msg) { if (result.status == BuildResult::TimedOut) { worker.timedOut = true; } - if (result.status == BuildResult::PermanentFailure) + if (result.status == BuildResult::PermanentFailure) { worker.permanentFailure = true; + } mcExpectedBuilds.reset(); mcRunningBuilds.reset(); @@ -4021,11 +4170,12 @@ void SubstitutionGoal::init() { return; } - if (settings.readOnlyMode) + if (settings.readOnlyMode) { throw Error( format( "cannot substitute path '%1%' - no write access to the Nix store") % storePath); + } subs = settings.useSubstitutes ? getDefaultSubstituters() : std::list>(); @@ -4110,14 +4260,17 @@ void SubstitutionGoal::tryNext() { /* To maintain the closure invariant, we first have to realise the paths referenced by this one. */ - for (auto& i : info->references) - if (i != storePath) /* ignore self-references */ + for (auto& i : info->references) { + if (i != storePath) { /* ignore self-references */ addWaitee(worker.makeSubstitutionGoal(i)); + } + } - if (waitees.empty()) /* to prevent hang (no wake-up event) */ + if (waitees.empty()) { /* to prevent hang (no wake-up event) */ referencesValid(); - else + } else { state = &SubstitutionGoal::referencesValid; + } } void SubstitutionGoal::referencesValid() { @@ -4131,9 +4284,11 @@ void SubstitutionGoal::referencesValid() { return; } - for (auto& i : info->references) - if (i != storePath) /* ignore self-references */ + for (auto& i : info->references) { + if (i != storePath) { /* ignore self-references */ assert(worker.store.isValidPath(i)); + } + } state = &SubstitutionGoal::tryToRun; worker.wakeUp(shared_from_this()); @@ -4304,14 +4459,16 @@ GoalPtr Worker::makeSubstitutionGoal(const Path& path, RepairFlag repair) { static void removeGoal(GoalPtr goal, WeakGoalMap& goalMap) { /* !!! inefficient */ - for (WeakGoalMap::iterator i = goalMap.begin(); i != goalMap.end();) + for (WeakGoalMap::iterator i = goalMap.begin(); i != goalMap.end();) { if (i->second.lock() == goal) { WeakGoalMap::iterator j = i; ++j; goalMap.erase(i); i = j; - } else + } else { ++i; + } + } } void Worker::removeGoal(GoalPtr goal) { @@ -4321,8 +4478,9 @@ void Worker::removeGoal(GoalPtr goal) { topGoals.erase(goal); /* If a top-level goal failed, then kill all other goals (unless keepGoing was set). */ - if (goal->getExitCode() == Goal::ecFailed && !settings.keepGoing) + if (goal->getExitCode() == Goal::ecFailed && !settings.keepGoing) { topGoals.clear(); + } } /* Wake up goals waiting for any goal to finish. */ @@ -4388,10 +4546,11 @@ void Worker::childTerminated(Goal* goal, bool wakeSleepers) { void Worker::waitForBuildSlot(GoalPtr goal) { DLOG(INFO) << "wait for build slot"; - if (getNrLocalBuilds() < settings.maxBuildJobs) + if (getNrLocalBuilds() < settings.maxBuildJobs) { wakeUp(goal); /* we can do it right away */ - else + } else { addToWeakGoals(wantingToBuild, goal); + } } void Worker::waitForAnyGoal(GoalPtr goal) { @@ -4441,13 +4600,14 @@ void Worker::run(const Goals& _topGoals) { } /* Wait for input. */ - if (!children.empty() || !waitingForAWhile.empty()) + if (!children.empty() || !waitingForAWhile.empty()) { waitForInput(); - else { - if (awake.empty() && 0 == settings.maxBuildJobs) + } else { + if (awake.empty() && 0 == settings.maxBuildJobs) { throw Error( "unable to start any build; either increase '--max-jobs' " "or enable remote builds"); + } assert(!awake.empty()); } } @@ -4478,19 +4638,22 @@ void Worker::waitForInput() { is a build timeout, then wait for input until the first deadline for any child. */ auto nearest = steady_time_point::max(); // nearest deadline - if (settings.minFree.get() != 0) + if (settings.minFree.get() != 0) { // Periodicallty wake up to see if we need to run the garbage collector. nearest = before + std::chrono::seconds(10); + } for (auto& i : children) { if (!i.respectTimeouts) { continue; } - if (0 != settings.maxSilentTime) + if (0 != settings.maxSilentTime) { nearest = std::min( nearest, i.lastOutput + std::chrono::seconds(settings.maxSilentTime)); - if (0 != settings.buildTimeout) + } + if (0 != settings.buildTimeout) { nearest = std::min( nearest, i.timeStarted + std::chrono::seconds(settings.buildTimeout)); + } } if (nearest != steady_time_point::max()) { timeout.tv_sec = std::max( @@ -4504,17 +4667,20 @@ void Worker::waitForInput() { up after a few seconds at most. */ if (!waitingForAWhile.empty()) { useTimeout = true; - if (lastWokenUp == steady_time_point::min()) + if (lastWokenUp == steady_time_point::min()) { DLOG(WARNING) << "waiting for locks or build slots..."; - if (lastWokenUp == steady_time_point::min() || lastWokenUp > before) + } + if (lastWokenUp == steady_time_point::min() || lastWokenUp > before) { lastWokenUp = before; + } timeout.tv_sec = std::max( 1L, (long)std::chrono::duration_cast( lastWokenUp + std::chrono::seconds(settings.pollInterval) - before) .count()); - } else + } else { lastWokenUp = steady_time_point::min(); + } if (useTimeout) { DLOG(INFO) << "sleeping " << timeout.tv_sec << " seconds"; @@ -4570,8 +4736,9 @@ void Worker::waitForInput() { goal->handleEOF(k); j->fds.erase(k); } else if (rd == -1) { - if (errno != EINTR) + if (errno != EINTR) { throw SysError("%s: read failed", goal->getName()); + } } else { DLOG(INFO) << goal->getName() << ": read " << rd << " bytes"; string data((char*)buffer.data(), rd); @@ -4676,12 +4843,14 @@ static void primeCache(Store& store, const PathSet& paths) { store.queryMissing(paths, willBuild, willSubstitute, unknown, downloadSize, narSize); - if (!willBuild.empty() && 0 == settings.maxBuildJobs && getMachines().empty()) + if (!willBuild.empty() && 0 == settings.maxBuildJobs && + getMachines().empty()) { throw Error( "%d derivations need to be built, but neither local builds " "('--max-jobs') " "nor remote builds ('--builders') are enabled", willBuild.size()); + } } void LocalStore::buildPaths(const PathSet& drvPaths, BuildMode buildMode) { @@ -4692,11 +4861,12 @@ void LocalStore::buildPaths(const PathSet& drvPaths, BuildMode buildMode) { Goals goals; for (auto& i : drvPaths) { DrvPathWithOutputs i2 = parseDrvPathWithOutputs(i); - if (isDerivation(i2.first)) + if (isDerivation(i2.first)) { goals.insert(worker.makeDerivationGoal(i2.first, i2.second, buildMode)); - else + } else { goals.insert(worker.makeSubstitutionGoal( i, buildMode == bmRepair ? Repair : NoRepair)); + } } worker.run(goals); @@ -4705,15 +4875,17 @@ void LocalStore::buildPaths(const PathSet& drvPaths, BuildMode buildMode) { for (auto& i : goals) { if (i->getExitCode() != Goal::ecSuccess) { DerivationGoal* i2 = dynamic_cast(i.get()); - if (i2) + if (i2) { failed.insert(i2->getDrvPath()); - else + } else { failed.insert(dynamic_cast(i.get())->getStorePath()); + } } } - if (!failed.empty()) + if (!failed.empty()) { throw Error(worker.exitStatus(), "build of %s failed", showPaths(failed)); + } } BuildResult LocalStore::buildDerivation(const Path& drvPath, @@ -4749,9 +4921,10 @@ void LocalStore::ensurePath(const Path& path) { worker.run(goals); - if (goal->getExitCode() != Goal::ecSuccess) + if (goal->getExitCode() != Goal::ecSuccess) { throw Error(worker.exitStatus(), "path '%s' does not exist and cannot be created", path); + } } void LocalStore::repairPath(const Path& path) { @@ -4769,8 +4942,9 @@ void LocalStore::repairPath(const Path& path) { goals.clear(); goals.insert(worker.makeDerivationGoal(deriver, StringSet(), bmRepair)); worker.run(goals); - } else + } else { throw Error(worker.exitStatus(), "cannot repair path '%s'", path); + } } } diff --git a/third_party/nix/src/libstore/crypto.cc b/third_party/nix/src/libstore/crypto.cc index 7a169107c1..f26cabdf6d 100644 --- a/third_party/nix/src/libstore/crypto.cc +++ b/third_party/nix/src/libstore/crypto.cc @@ -32,8 +32,9 @@ Key::Key(const string& s) { SecretKey::SecretKey(const string& s) : Key(s) { #if HAVE_SODIUM - if (key.size() != crypto_sign_SECRETKEYBYTES) + if (key.size() != crypto_sign_SECRETKEYBYTES) { throw Error("secret key is not valid"); + } #endif } @@ -69,8 +70,9 @@ PublicKey SecretKey::toPublicKey() const { PublicKey::PublicKey(const string& s) : Key(s) { #if HAVE_SODIUM - if (key.size() != crypto_sign_PUBLICKEYBYTES) + if (key.size() != crypto_sign_PUBLICKEYBYTES) { throw Error("public key is not valid"); + } #endif } diff --git a/third_party/nix/src/libstore/derivations.cc b/third_party/nix/src/libstore/derivations.cc index 51bcfbe1ce..1b6f160653 100644 --- a/third_party/nix/src/libstore/derivations.cc +++ b/third_party/nix/src/libstore/derivations.cc @@ -19,16 +19,18 @@ void DerivationOutput::parseHashInfo(bool& recursive, Hash& hash) const { } HashType hashType = parseHashType(algo); - if (hashType == htUnknown) + if (hashType == htUnknown) { throw Error(format("unknown hash algorithm '%1%'") % algo); + } hash = Hash(this->hash, hashType); } Path BasicDerivation::findOutput(const string& id) const { auto i = outputs.find(id); - if (i == outputs.end()) + if (i == outputs.end()) { throw Error(format("derivation has no output '%1%'") % id); + } return i->second.path; } @@ -57,8 +59,9 @@ Path writeDerivation(ref store, const Derivation& drv, static void expect(std::istream& str, const string& s) { char s2[s.size()]; str.read(s2, s.size()); - if (string(s2, s.size()) != s) + if (string(s2, s.size()) != s) { throw FormatError(format("expected string '%1%'") % s); + } } /* Read a C-style string from stream `str'. */ @@ -66,26 +69,30 @@ static string parseString(std::istream& str) { string res; expect(str, "\""); int c; - while ((c = str.get()) != '"') + while ((c = str.get()) != '"') { if (c == '\\') { c = str.get(); - if (c == 'n') + if (c == 'n') { res += '\n'; - else if (c == 'r') + } else if (c == 'r') { res += '\r'; - else if (c == 't') + } else if (c == 't') { res += '\t'; - else + } else { res += c; - } else + } + } else { res += c; + } + } return res; } static Path parsePath(std::istream& str) { string s = parseString(str); - if (s.size() == 0 || s[0] != '/') + if (s.size() == 0 || s[0] != '/') { throw FormatError(format("bad path '%1%' in derivation") % s); + } return s; } @@ -103,8 +110,9 @@ static bool endOfList(std::istream& str) { static StringSet parseStrings(std::istream& str, bool arePaths) { StringSet res; - while (!endOfList(str)) + while (!endOfList(str)) { res.insert(arePaths ? parsePath(str) : parseString(str)); + } return res; } @@ -147,7 +155,9 @@ static Derivation parseDerivation(const string& s) { /* Parse the builder arguments. */ expect(str, ",["); - while (!endOfList(str)) drv.args.push_back(parseString(str)); + while (!endOfList(str)) { + drv.args.push_back(parseString(str)); + } /* Parse the environment variables. */ expect(str, ",["); diff --git a/third_party/nix/src/libstore/download.cc b/third_party/nix/src/libstore/download.cc index fbc2069c08..4b90a37657 100644 --- a/third_party/nix/src/libstore/download.cc +++ b/third_party/nix/src/libstore/download.cc @@ -36,11 +36,12 @@ DownloadSettings downloadSettings; static GlobalConfig::Register r1(&downloadSettings); std::string resolveUri(const std::string& uri) { - if (uri.compare(0, 8, "channel:") == 0) + if (uri.compare(0, 8, "channel:") == 0) { return "https://nixos.org/channels/" + std::string(uri, 8) + "/nixexprs.tar.xz"; - else + } else { return uri; + } } struct CurlDownloader : public Downloader { @@ -92,18 +93,21 @@ struct CurlDownloader : public Downloader { writtenToSink += len; this->request.dataCallback((char*)data, len); } - } else + } else { this->result.data->append((char*)data, len); + } }) { LOG(INFO) << (request.data ? "uploading '" : "downloading '") << request.uri << "'"; - if (!request.expectedETag.empty()) + if (!request.expectedETag.empty()) { requestHeaders = curl_slist_append( requestHeaders, ("If-None-Match: " + request.expectedETag).c_str()); - if (!request.mimeType.empty()) + } + if (!request.mimeType.empty()) { requestHeaders = curl_slist_append( requestHeaders, ("Content-Type: " + request.mimeType).c_str()); + } } ~DownloadItem() { @@ -117,10 +121,11 @@ struct CurlDownloader : public Downloader { curl_slist_free_all(requestHeaders); } try { - if (!done) + if (!done) { fail(DownloadError( Interrupted, format("download of '%s' was interrupted") % request.uri)); + } } catch (...) { ignoreException(); } @@ -147,8 +152,9 @@ struct CurlDownloader : public Downloader { size_t realSize = size * nmemb; result.bodySize += realSize; - if (!decompressionSink) + if (!decompressionSink) { decompressionSink = makeDecompressionSink(encoding, finalSink); + } (*decompressionSink)((unsigned char*)contents, realSize); @@ -192,11 +198,12 @@ struct CurlDownloader : public Downloader { << "shutting down on 200 HTTP response with expected ETag"; return 0; } - } else if (name == "content-encoding") + } else if (name == "content-encoding") { encoding = trim(string(line, i + 1)); - else if (name == "accept-ranges" && - toLower(trim(std::string(line, i + 1))) == "bytes") + } else if (name == "accept-ranges" && + toLower(trim(std::string(line, i + 1))) == "bytes") { acceptRanges = true; + } } } return realSize; @@ -275,10 +282,11 @@ struct CurlDownloader : public Downloader { curl_easy_setopt(req, CURLOPT_PIPEWAIT, 1); #endif #if LIBCURL_VERSION_NUM >= 0x072f00 - if (downloadSettings.enableHttp2) + if (downloadSettings.enableHttp2) { curl_easy_setopt(req, CURLOPT_HTTP_VERSION, CURL_HTTP_VERSION_2TLS); - else + } else { curl_easy_setopt(req, CURLOPT_HTTP_VERSION, CURL_HTTP_VERSION_1_1); + } #endif curl_easy_setopt(req, CURLOPT_WRITEFUNCTION, DownloadItem::writeCallbackWrapper); @@ -306,8 +314,9 @@ struct CurlDownloader : public Downloader { } if (request.verifyTLS) { - if (settings.caFile != "") + if (settings.caFile != "") { curl_easy_setopt(req, CURLOPT_CAINFO, settings.caFile.c_str()); + } } else { curl_easy_setopt(req, CURLOPT_SSL_VERIFYPEER, 0); curl_easy_setopt(req, CURLOPT_SSL_VERIFYHOST, 0); @@ -362,14 +371,14 @@ struct CurlDownloader : public Downloader { httpStatus = 304; } - if (writeException) + if (writeException) { failEx(writeException); - else if (code == CURLE_OK && - (httpStatus == 200 || httpStatus == 201 || httpStatus == 204 || - httpStatus == 206 || httpStatus == 304 || - httpStatus == 226 /* FTP */ || - httpStatus == 0 /* other protocol */)) { + } else if (code == CURLE_OK && + (httpStatus == 200 || httpStatus == 201 || httpStatus == 204 || + httpStatus == 206 || httpStatus == 304 || + httpStatus == 226 /* FTP */ || + httpStatus == 0 /* other protocol */)) { result.cached = httpStatus == 304; done = true; callback(std::move(result)); @@ -464,8 +473,9 @@ struct CurlDownloader : public Downloader { embargo = std::chrono::steady_clock::now() + std::chrono::milliseconds(ms); downloader.enqueueItem(shared_from_this()); - } else + } else { fail(exc); + } } } }; @@ -548,10 +558,11 @@ struct CurlDownloader : public Downloader { /* Let curl do its thing. */ int running; CURLMcode mc = curl_multi_perform(curlm, &running); - if (mc != CURLM_OK) + if (mc != CURLM_OK) { throw nix::Error( format("unexpected error from curl_multi_perform(): %s") % curl_multi_strerror(mc)); + } /* Set the promises of any finished requests. */ CURLMsg* msg; @@ -584,9 +595,10 @@ struct CurlDownloader : public Downloader { : maxSleepTimeMs; DLOG(INFO) << "download thread waiting for " << sleepTimeMs << " ms"; mc = curl_multi_wait(curlm, extraFDs, 1, sleepTimeMs, &numfds); - if (mc != CURLM_OK) + if (mc != CURLM_OK) { throw nix::Error(format("unexpected error from curl_multi_wait(): %s") % curl_multi_strerror(mc)); + } nextWakeup = std::chrono::steady_clock::time_point(); @@ -596,8 +608,9 @@ struct CurlDownloader : public Downloader { if (extraFDs[0].revents & CURL_WAIT_POLLIN) { char buf[1024]; auto res = read(extraFDs[0].fd, buf, sizeof(buf)); - if (res == -1 && errno != EINTR) + if (res == -1 && errno != EINTR) { throw SysError("reading curl wakeup socket"); + } } std::vector> incoming; @@ -612,8 +625,9 @@ struct CurlDownloader : public Downloader { state->incoming.pop(); } else { if (nextWakeup == std::chrono::steady_clock::time_point() || - item->embargo < nextWakeup) + item->embargo < nextWakeup) { nextWakeup = item->embargo; + } break; } } @@ -643,22 +657,26 @@ struct CurlDownloader : public Downloader { { auto state(state_.lock()); - while (!state->incoming.empty()) state->incoming.pop(); + while (!state->incoming.empty()) { + state->incoming.pop(); + } state->quit = true; } } void enqueueItem(std::shared_ptr item) { if (item->request.data && !hasPrefix(item->request.uri, "http://") && - !hasPrefix(item->request.uri, "https://")) + !hasPrefix(item->request.uri, "https://")) { throw nix::Error("uploading to '%s' is not supported", item->request.uri); + } { auto state(state_.lock()); - if (state->quit) + if (state->quit) { throw nix::Error( "cannot enqueue download request because the download thread is " "shutting down"); + } state->incoming.push(item); } writeFull(wakeupPipe.writeSide.get(), " "); @@ -900,8 +918,9 @@ CachedDownloadResult Downloader::downloadCached( expectedETag = ss[1]; } } - } else + } else { storePath = ""; + } } if (!skip) { diff --git a/third_party/nix/src/libstore/export-import.cc b/third_party/nix/src/libstore/export-import.cc index 930ff90d26..6a1862492d 100644 --- a/third_party/nix/src/libstore/export-import.cc +++ b/third_party/nix/src/libstore/export-import.cc @@ -46,9 +46,10 @@ void Store::exportPath(const Path& path, Sink& sink) { filesystem corruption from spreading to other machines. Don't complain if the stored hash is zero (unknown). */ Hash hash = hashAndWriteSink.currentHash(); - if (hash != info->narHash && info->narHash != Hash(info->narHash.type)) + if (hash != info->narHash && info->narHash != Hash(info->narHash.type)) { throw Error(format("hash of path '%1%' has changed from '%2%' to '%3%'!") % path % info->narHash.to_string() % hash.to_string()); + } hashAndWriteSink << exportMagic << path << info->references << info->deriver << 0; @@ -62,17 +63,19 @@ Paths Store::importPaths(Source& source, std::shared_ptr accessor, if (n == 0) { break; } - if (n != 1) + if (n != 1) { throw Error( "input doesn't look like something created by 'nix-store --export'"); + } /* Extract the NAR from the source. */ TeeSink tee(source); parseDump(tee, tee.source); uint32_t magic = readInt(source); - if (magic != exportMagic) + if (magic != exportMagic) { throw Error("Nix archive cannot be imported; wrong format"); + } ValidPathInfo info; diff --git a/third_party/nix/src/libstore/gc.cc b/third_party/nix/src/libstore/gc.cc index c7f2a507d3..3e79e6c336 100644 --- a/third_party/nix/src/libstore/gc.cc +++ b/third_party/nix/src/libstore/gc.cc @@ -61,8 +61,9 @@ static void makeSymlink(const Path& link, const Path& target) { createSymlink(target, tempLink); /* Atomically replace the old one. */ - if (rename(tempLink.c_str(), link.c_str()) == -1) + if (rename(tempLink.c_str(), link.c_str()) == -1) { throw SysError(format("cannot rename '%1%' to '%2%'") % tempLink % link); + } } void LocalStore::syncWithGC() { AutoCloseFD fdGCLock = openGCLock(ltRead); } @@ -80,18 +81,21 @@ Path LocalFSStore::addPermRoot(const Path& _storePath, const Path& _gcRoot, Path gcRoot(canonPath(_gcRoot)); assertStorePath(storePath); - if (isInStore(gcRoot)) + if (isInStore(gcRoot)) { throw Error(format("creating a garbage collector root (%1%) in the Nix " "store is forbidden " "(are you running nix-build inside the store?)") % gcRoot); + } if (indirect) { /* Don't clobber the link if it already exists and doesn't point to the Nix store. */ - if (pathExists(gcRoot) && (!isLink(gcRoot) || !isInStore(readLink(gcRoot)))) + if (pathExists(gcRoot) && + (!isLink(gcRoot) || !isInStore(readLink(gcRoot)))) { throw Error(format("cannot create symlink '%1%'; already exists") % gcRoot); + } makeSymlink(gcRoot, storePath); addIndirectRoot(gcRoot); } @@ -101,16 +105,18 @@ Path LocalFSStore::addPermRoot(const Path& _storePath, const Path& _gcRoot, Path rootsDir = canonPath((format("%1%/%2%") % stateDir % gcRootsDir).str()); - if (string(gcRoot, 0, rootsDir.size() + 1) != rootsDir + "/") + if (string(gcRoot, 0, rootsDir.size() + 1) != rootsDir + "/") { throw Error(format("path '%1%' is not a valid garbage collector root; " "it's not in the directory '%2%'") % gcRoot % rootsDir); + } } - if (baseNameOf(gcRoot) == baseNameOf(storePath)) + if (baseNameOf(gcRoot) == baseNameOf(storePath)) { writeFile(gcRoot, ""); - else + } else { makeSymlink(gcRoot, storePath); + } } /* Check that the root can be found by the garbage collector. @@ -144,10 +150,11 @@ void LocalStore::addTempRoot(const Path& path) { while (1) { AutoCloseFD fdGCLock = openGCLock(ltRead); - if (pathExists(fnTempRoots)) + if (pathExists(fnTempRoots)) { /* It *must* be stale, since there can be no two processes with the same pid. */ unlink(fnTempRoots.c_str()); + } state->fdTempRoots = openLockFile(fnTempRoots, true); @@ -159,8 +166,9 @@ void LocalStore::addTempRoot(const Path& path) { /* Check whether the garbage collector didn't get in our way. */ struct stat st; - if (fstat(state->fdTempRoots.get(), &st) == -1) + if (fstat(state->fdTempRoots.get(), &st) == -1) { throw SysError(format("statting '%1%'") % fnTempRoots); + } if (st.st_size == 0) { break; } @@ -245,11 +253,12 @@ void LocalStore::findTempRoots(FDs& fds, Roots& tempRoots, bool censor) { void LocalStore::findRoots(const Path& path, unsigned char type, Roots& roots) { auto foundRoot = [&](const Path& path, const Path& target) { Path storePath = toStorePath(target); - if (isStorePath(storePath) && isValidPath(storePath)) + if (isStorePath(storePath) && isValidPath(storePath)) { roots[storePath].emplace(path); - else + } else { LOG(INFO) << "skipping invalid root from '" << path << "' to '" << storePath << "'"; + } }; try { @@ -258,8 +267,9 @@ void LocalStore::findRoots(const Path& path, unsigned char type, Roots& roots) { } if (type == DT_DIR) { - for (auto& i : readDirectory(path)) + for (auto& i : readDirectory(path)) { findRoots(path + "/" + i.name, i.type, roots); + } } else if (type == DT_LNK) { @@ -292,8 +302,9 @@ void LocalStore::findRoots(const Path& path, unsigned char type, Roots& roots) { else if (type == DT_REG) { Path storePath = storeDir + "/" + baseNameOf(path); - if (isStorePath(storePath) && isValidPath(storePath)) + if (isStorePath(storePath) && isValidPath(storePath)) { roots[storePath].emplace(path); + } } } @@ -395,8 +406,9 @@ void LocalStore::findRuntimeRoots(Roots& roots, bool censor) { } struct dirent* fd_ent; while (errno = 0, fd_ent = readdir(fdDir.get())) { - if (fd_ent->d_name[0] != '.') + if (fd_ent->d_name[0] != '.') { readProcLink(fmt("%s/%s", fdStr, fd_ent->d_name), unchecked); + } } if (errno) { if (errno == ESRCH) { @@ -412,8 +424,9 @@ void LocalStore::findRuntimeRoots(Roots& roots, bool censor) { readFile(mapFile, true), "\n"); for (const auto& line : mapLines) { auto match = std::smatch{}; - if (std::regex_match(line, match, mapRegex)) + if (std::regex_match(line, match, mapRegex)) { unchecked[match[1]].emplace(mapFile); + } } auto envFile = fmt("/proc/%s/environ", ent->d_name); @@ -421,8 +434,9 @@ void LocalStore::findRuntimeRoots(Roots& roots, bool censor) { auto env_end = std::sregex_iterator{}; for (auto i = std::sregex_iterator{envString.begin(), envString.end(), storePathRegex}; - i != env_end; ++i) + i != env_end; ++i) { unchecked[i->str()].emplace(envFile); + } } catch (SysError& e) { if (errno == ENOENT || errno == EACCES || errno == ESRCH) { continue; @@ -467,10 +481,11 @@ void LocalStore::findRuntimeRoots(Roots& roots, bool censor) { Path path = toStorePath(target); if (isStorePath(path) && isValidPath(path)) { DLOG(INFO) << "got additional root " << path; - if (censor) + if (censor) { roots[path].insert(censored); - else + } else { roots[path].insert(links.begin(), links.end()); + } } } } @@ -514,10 +529,11 @@ void LocalStore::deletePathRecursive(GCState& state, const Path& path) { if (isStorePath(path) && isValidPath(path)) { PathSet referrers; queryReferrers(path, referrers); - for (auto& i : referrers) + for (auto& i : referrers) { if (i != path) { deletePathRecursive(state, i); } + } size = queryPathInfo(path)->narSize; invalidatePathChecked(path); } @@ -546,12 +562,14 @@ void LocalStore::deletePathRecursive(GCState& state, const Path& path) { // if the path was not valid, need to determine the actual // size. try { - if (chmod(realPath.c_str(), st.st_mode | S_IWUSR) == -1) + if (chmod(realPath.c_str(), st.st_mode | S_IWUSR) == -1) { throw SysError(format("making '%1%' writable") % realPath); + } Path tmp = trashDir + "/" + baseNameOf(path); - if (rename(realPath.c_str(), tmp.c_str())) + if (rename(realPath.c_str(), tmp.c_str())) { throw SysError(format("unable to rename '%1%' to '%2%'") % realPath % tmp); + } state.bytesInvalidated += size; } catch (SysError& e) { if (e.errNo == ENOSPC) { @@ -560,8 +578,9 @@ void LocalStore::deletePathRecursive(GCState& state, const Path& path) { deleteGarbage(state, realPath); } } - } else + } else { deleteGarbage(state, realPath); + } if (state.results.bytesFreed + state.bytesInvalidated > state.options.maxFreed) { @@ -606,9 +625,11 @@ bool LocalStore::canReachRoot(GCState& state, PathSet& visited, don't delete the derivation if any of the outputs are alive. */ if (state.gcKeepDerivations && isDerivation(path)) { PathSet outputs = queryDerivationOutputs(path); - for (auto& i : outputs) - if (isValidPath(i) && queryPathInfo(i)->deriver == path) + for (auto& i : outputs) { + if (isValidPath(i) && queryPathInfo(i)->deriver == path) { incoming.insert(i); + } + } } /* If keep-outputs is set, then don't delete this path if there @@ -620,12 +641,14 @@ bool LocalStore::canReachRoot(GCState& state, PathSet& visited, } } - for (auto& i : incoming) - if (i != path) + for (auto& i : incoming) { + if (i != path) { if (canReachRoot(state, visited, i)) { state.alive.insert(path); return true; } + } + } return false; } @@ -701,8 +724,9 @@ void LocalStore::removeUnusedLinks(const GCState& state) { Path path = linksDir + "/" + name; struct stat st; - if (lstat(path.c_str(), &st) == -1) + if (lstat(path.c_str(), &st) == -1) { throw SysError(format("statting '%1%'") % path); + } if (st.st_nlink != 1) { actualSize += st.st_size; @@ -807,16 +831,18 @@ void LocalStore::collectGarbage(const GCOptions& options, GCResults& results) { for (auto& i : options.pathsToDelete) { assertStorePath(i); tryToDelete(state, i); - if (state.dead.find(i) == state.dead.end()) + if (state.dead.find(i) == state.dead.end()) { throw Error(format("cannot delete path '%1%' since it is still alive") % i); + } } } else if (options.maxFreed > 0) { - if (state.shouldDelete) + if (state.shouldDelete) { LOG(INFO) << "deleting garbage..."; - else + } else { LOG(ERROR) << "determining live/dead paths..."; + } try { AutoCloseDir dir(opendir(realStoreDir.c_str())); @@ -839,10 +865,11 @@ void LocalStore::collectGarbage(const GCOptions& options, GCResults& results) { continue; } Path path = storeDir + "/" + name; - if (isStorePath(path) && isValidPath(path)) + if (isStorePath(path) && isValidPath(path)) { entries.push_back(path); - else + } else { tryToDelete(state, path); + } } dir.reset(); @@ -897,8 +924,9 @@ void LocalStore::autoGC(bool sync) { static auto fakeFreeSpaceFile = getEnv("_NIX_TEST_FREE_SPACE_FILE", ""); auto getAvail = [this]() -> uint64_t { - if (!fakeFreeSpaceFile.empty()) + if (!fakeFreeSpaceFile.empty()) { return std::stoll(readFile(fakeFreeSpaceFile)); + } struct statvfs st; if (statvfs(realStoreDir.c_str(), &st)) { @@ -922,8 +950,9 @@ void LocalStore::autoGC(bool sync) { auto now = std::chrono::steady_clock::now(); if (now < state->lastGCCheck + - std::chrono::seconds(settings.minFreeCheckInterval)) + std::chrono::seconds(settings.minFreeCheckInterval)) { return; + } auto avail = getAvail(); diff --git a/third_party/nix/src/libstore/globals.cc b/third_party/nix/src/libstore/globals.cc index 19a0cde1ed..ade200f135 100644 --- a/third_party/nix/src/libstore/globals.cc +++ b/third_party/nix/src/libstore/globals.cc @@ -49,11 +49,12 @@ Settings::Settings() if (caFile == "") { for (auto& fn : {"/etc/ssl/certs/ca-certificates.crt", - "/nix/var/nix/profiles/default/etc/ssl/certs/ca-bundle.crt"}) + "/nix/var/nix/profiles/default/etc/ssl/certs/ca-bundle.crt"}) { if (pathExists(fn)) { caFile = fn; break; } + } } /* Backwards compatibility. */ @@ -112,26 +113,28 @@ const string nixVersion = PACKAGE_VERSION; template <> void BaseSetting::set(const std::string& str) { - if (str == "true") + if (str == "true") { value = smEnabled; - else if (str == "relaxed") + } else if (str == "relaxed") { value = smRelaxed; - else if (str == "false") + } else if (str == "false") { value = smDisabled; - else + } else { throw UsageError("option '%s' has invalid value '%s'", name, str); + } } template <> std::string BaseSetting::to_string() { - if (value == smEnabled) + if (value == smEnabled) { return "true"; - else if (value == smRelaxed) + } else if (value == smRelaxed) { return "relaxed"; - else if (value == smDisabled) + } else if (value == smDisabled) { return "false"; - else + } else { abort(); + } } template <> @@ -160,11 +163,12 @@ void BaseSetting::convertToArg(Args& args, } void MaxBuildJobsSetting::set(const std::string& str) { - if (str == "auto") + if (str == "auto") { value = std::max(1U, std::thread::hardware_concurrency()); - else if (!string2Int(str, value)) + } else if (!string2Int(str, value)) { throw UsageError( "configuration setting '%s' should be 'auto' or an integer", name); + } } void initPlugins() { @@ -172,8 +176,9 @@ void initPlugins() { Paths pluginFiles; try { auto ents = readDirectory(pluginFile); - for (const auto& ent : ents) + for (const auto& ent : ents) { pluginFiles.emplace_back(pluginFile + "/" + ent.name); + } } catch (SysError& e) { if (e.errNo != ENOTDIR) { throw; @@ -184,9 +189,10 @@ void initPlugins() { /* handle is purposefully leaked as there may be state in the DSO needed by the action of the plugin. */ void* handle = dlopen(file.c_str(), RTLD_LAZY | RTLD_LOCAL); - if (!handle) + if (!handle) { throw Error("could not dynamically open plugin file '%s': %s", file, dlerror()); + } } } diff --git a/third_party/nix/src/libstore/globals.hh b/third_party/nix/src/libstore/globals.hh index 7b4d614f7a..924e8a0165 100644 --- a/third_party/nix/src/libstore/globals.hh +++ b/third_party/nix/src/libstore/globals.hh @@ -408,17 +408,10 @@ class Settings : public Config { this, true, "print-missing", "Whether to print what paths need to be built or downloaded."}; - Setting preBuildHook { - this, -#if __APPLE__ - nixLibexecDir + "/nix/resolve-system-dependencies", -#else - "", -#endif - "pre-build-hook", - "A program to run just before a build to set derivation-specific build " - "settings." - }; + Setting preBuildHook{ + this, "", "pre-build-hook", + "A program to run just before a build to set derivation-specific build " + "settings."}; Setting postBuildHook{ this, "", "post-build-hook", diff --git a/third_party/nix/src/libstore/http-binary-cache-store.cc b/third_party/nix/src/libstore/http-binary-cache-store.cc index 2482b02c61..d3b551f08c 100644 --- a/third_party/nix/src/libstore/http-binary-cache-store.cc +++ b/third_party/nix/src/libstore/http-binary-cache-store.cc @@ -113,9 +113,10 @@ class HttpBinaryCacheStore : public BinaryCacheStore { try { getDownloader()->download(std::move(request), sink); } catch (DownloadError& e) { - if (e.error == Downloader::NotFound || e.error == Downloader::Forbidden) + if (e.error == Downloader::NotFound || e.error == Downloader::Forbidden) { throw NoSuchBinaryCacheFile( "file '%s' does not exist in binary cache '%s'", path, getUri()); + } maybeDisable(); throw; } @@ -137,8 +138,9 @@ class HttpBinaryCacheStore : public BinaryCacheStore { (*callbackPtr)(result.get().data); } catch (DownloadError& e) { if (e.error == Downloader::NotFound || - e.error == Downloader::Forbidden) + e.error == Downloader::Forbidden) { return (*callbackPtr)(std::shared_ptr()); + } maybeDisable(); callbackPtr->rethrow(); } catch (...) { @@ -154,8 +156,9 @@ static RegisterStoreImplementation regStore( if (std::string(uri, 0, 7) != "http://" && std::string(uri, 0, 8) != "https://" && (getEnv("_NIX_FORCE_HTTP_BINARY_CACHE_STORE") != "1" || - std::string(uri, 0, 7) != "file://")) + std::string(uri, 0, 7) != "file://")) { return 0; + } auto store = std::make_shared(params, uri); store->init(); return store; diff --git a/third_party/nix/src/libstore/legacy-ssh-store.cc b/third_party/nix/src/libstore/legacy-ssh-store.cc index 8510895d0b..0cfe1bfe5d 100644 --- a/third_party/nix/src/libstore/legacy-ssh-store.cc +++ b/third_party/nix/src/libstore/legacy-ssh-store.cc @@ -69,12 +69,14 @@ struct LegacySSHStore : public Store { conn->to.flush(); unsigned int magic = readInt(conn->from); - if (magic != SERVE_MAGIC_2) + if (magic != SERVE_MAGIC_2) { throw Error("protocol mismatch with 'nix-store --serve' on '%s'", host); + } conn->remoteVersion = readInt(conn->from); - if (GET_PROTOCOL_MAJOR(conn->remoteVersion) != 0x200) + if (GET_PROTOCOL_MAJOR(conn->remoteVersion) != 0x200) { throw Error("unsupported 'nix-store --serve' protocol version on '%s'", host); + } } catch (EndOfFile& e) { throw Error("cannot connect to '%1%'", host); @@ -160,9 +162,10 @@ struct LegacySSHStore : public Store { conn->to.flush(); } - if (readInt(conn->from) != 1) + if (readInt(conn->from) != 1) { throw Error( "failed to add path '%s' to remote host '%s', info.path, host"); + } } void narFromPath(const Path& path, Sink& sink) override { @@ -194,10 +197,12 @@ struct LegacySSHStore : public Store { conn->to << cmdBuildDerivation << drvPath << drv << settings.maxSilentTime << settings.buildTimeout; - if (GET_PROTOCOL_MINOR(conn->remoteVersion) >= 2) + if (GET_PROTOCOL_MINOR(conn->remoteVersion) >= 2) { conn->to << settings.maxLogSize; - if (GET_PROTOCOL_MINOR(conn->remoteVersion) >= 3) + } + if (GET_PROTOCOL_MINOR(conn->remoteVersion) >= 3) { conn->to << settings.buildRepeat << settings.enforceDeterminism; + } conn->to.flush(); @@ -205,9 +210,10 @@ struct LegacySSHStore : public Store { status.status = (BuildResult::Status)readInt(conn->from); conn->from >> status.errorMsg; - if (GET_PROTOCOL_MINOR(conn->remoteVersion) >= 3) + if (GET_PROTOCOL_MINOR(conn->remoteVersion) >= 3) { conn->from >> status.timesBuilt >> status.isNonDeterministic >> status.startTime >> status.stopTime; + } return status; } diff --git a/third_party/nix/src/libstore/local-binary-cache-store.cc b/third_party/nix/src/libstore/local-binary-cache-store.cc index 925fb34de4..29c74cedd8 100644 --- a/third_party/nix/src/libstore/local-binary-cache-store.cc +++ b/third_party/nix/src/libstore/local-binary-cache-store.cc @@ -26,9 +26,10 @@ class LocalBinaryCacheStore : public BinaryCacheStore { try { readFile(binaryCacheDir + "/" + path, sink); } catch (SysError& e) { - if (e.errNo == ENOENT) + if (e.errNo == ENOENT) { throw NoSuchBinaryCacheFile("file '%s' does not exist in binary cache", path); + } } } @@ -36,8 +37,9 @@ class LocalBinaryCacheStore : public BinaryCacheStore { PathSet paths; for (auto& entry : readDirectory(binaryCacheDir)) { - if (entry.name.size() != 40 || !hasSuffix(entry.name, ".narinfo")) + if (entry.name.size() != 40 || !hasSuffix(entry.name, ".narinfo")) { continue; + } paths.insert(storeDir + "/" + entry.name.substr(0, entry.name.size() - 8)); } @@ -55,8 +57,9 @@ static void atomicWrite(const Path& path, const std::string& s) { Path tmp = path + ".tmp." + std::to_string(getpid()); AutoDelete del(tmp, false); writeFile(tmp, s); - if (rename(tmp.c_str(), path.c_str())) + if (rename(tmp.c_str(), path.c_str())) { throw SysError(format("renaming '%1%' to '%2%'") % tmp % path); + } del.cancel(); } @@ -74,8 +77,9 @@ static RegisterStoreImplementation regStore( [](const std::string& uri, const Store::Params& params) -> std::shared_ptr { if (getEnv("_NIX_FORCE_HTTP_BINARY_CACHE_STORE") == "1" || - std::string(uri, 0, 7) != "file://") + std::string(uri, 0, 7) != "file://") { return 0; + } auto store = std::make_shared(params, std::string(uri, 7)); store->init(); diff --git a/third_party/nix/src/libstore/local-fs-store.cc b/third_party/nix/src/libstore/local-fs-store.cc index d9eaea2e93..bc282eac96 100644 --- a/third_party/nix/src/libstore/local-fs-store.cc +++ b/third_party/nix/src/libstore/local-fs-store.cc @@ -16,9 +16,10 @@ struct LocalStoreAccessor : public FSAccessor { Path toRealPath(const Path& path) { Path storePath = store->toStorePath(path); - if (!store->isValidPath(storePath)) + if (!store->isValidPath(storePath)) { throw InvalidPath(format("path '%1%' is not a valid store path") % storePath); + } return store->getRealStoreDir() + std::string(path, store->storeDir.size()); } @@ -27,13 +28,15 @@ struct LocalStoreAccessor : public FSAccessor { struct stat st; if (lstat(realPath.c_str(), &st)) { - if (errno == ENOENT || errno == ENOTDIR) + if (errno == ENOENT || errno == ENOTDIR) { return {Type::tMissing, 0, false}; + } throw SysError(format("getting status of '%1%'") % path); } - if (!S_ISREG(st.st_mode) && !S_ISDIR(st.st_mode) && !S_ISLNK(st.st_mode)) + if (!S_ISREG(st.st_mode) && !S_ISDIR(st.st_mode) && !S_ISLNK(st.st_mode)) { throw Error(format("file '%1%' has unsupported type") % path); + } return {S_ISREG(st.st_mode) ? Type::tRegular diff --git a/third_party/nix/src/libstore/local-store.cc b/third_party/nix/src/libstore/local-store.cc index 4c431b6b38..020813a356 100644 --- a/third_party/nix/src/libstore/local-store.cc +++ b/third_party/nix/src/libstore/local-store.cc @@ -73,8 +73,9 @@ LocalStore::LocalStore(const Params& params) for (auto& perUserDir : {profilesDir + "/per-user", gcRootsDir + "/per-user"}) { createDirs(perUserDir); - if (chmod(perUserDir.c_str(), 0755) == -1) + if (chmod(perUserDir.c_str(), 0755) == -1) { throw SysError("could not set permissions on '%s' to 755", perUserDir); + } } createUser(getUserName(), getuid()); @@ -90,18 +91,21 @@ LocalStore::LocalStore(const Params& params) << "' specified in 'build-users-group' does not exist"; } else { struct stat st; - if (stat(realStoreDir.c_str(), &st)) + if (stat(realStoreDir.c_str(), &st)) { throw SysError(format("getting attributes of path '%1%'") % realStoreDir); + } if (st.st_uid != 0 || st.st_gid != gr->gr_gid || (st.st_mode & ~S_IFMT) != perm) { - if (chown(realStoreDir.c_str(), 0, gr->gr_gid) == -1) + if (chown(realStoreDir.c_str(), 0, gr->gr_gid) == -1) { throw SysError(format("changing ownership of path '%1%'") % realStoreDir); - if (chmod(realStoreDir.c_str(), perm) == -1) + } + if (chmod(realStoreDir.c_str(), perm) == -1) { throw SysError(format("changing permissions on path '%1%'") % realStoreDir); + } } } } @@ -111,13 +115,15 @@ LocalStore::LocalStore(const Params& params) Path path = realStoreDir; struct stat st; while (path != "/") { - if (lstat(path.c_str(), &st)) + if (lstat(path.c_str(), &st)) { throw SysError(format("getting status of '%1%'") % path); - if (S_ISLNK(st.st_mode)) + } + if (S_ISLNK(st.st_mode)) { throw Error(format("the path '%1%' is a symlink; " "this is not allowed for the Nix store and its " "parent directories") % path); + } path = dirOf(path); } } @@ -168,17 +174,19 @@ LocalStore::LocalStore(const Params& params) openDB(*state, true); writeFile(schemaPath, (format("%1%") % nixSchemaVersion).str()); } else if (curSchema < nixSchemaVersion) { - if (curSchema < 5) + if (curSchema < 5) { throw Error( "Your Nix store has a database in Berkeley DB format,\n" "which is no longer supported. To convert to the new format,\n" "please upgrade Nix to version 0.12 first."); + } - if (curSchema < 6) + if (curSchema < 6) { throw Error( "Your Nix store has a database in flat file format,\n" "which is no longer supported. To convert to the new format,\n" "please upgrade Nix to version 1.11 first."); + } if (!lockFile(globalLock.get(), ltWrite, false)) { LOG(INFO) << "waiting for exclusive access to the Nix store..."; @@ -295,24 +303,27 @@ int LocalStore::getSchema() { int curSchema = 0; if (pathExists(schemaPath)) { string s = readFile(schemaPath); - if (!string2Int(s, curSchema)) + if (!string2Int(s, curSchema)) { throw Error(format("'%1%' is corrupt") % schemaPath); + } } return curSchema; } void LocalStore::openDB(State& state, bool create) { - if (access(dbDir.c_str(), R_OK | W_OK)) + if (access(dbDir.c_str(), R_OK | W_OK)) { throw SysError(format("Nix database directory '%1%' is not writable") % dbDir); + } /* Open the Nix database. */ string dbPath = dbDir + "/db.sqlite"; auto& db(state.db); if (sqlite3_open_v2(dbPath.c_str(), &db.db, SQLITE_OPEN_READWRITE | (create ? SQLITE_OPEN_CREATE : 0), - 0) != SQLITE_OK) + 0) != SQLITE_OK) { throw Error(format("cannot open Nix database '%1%'") % dbPath); + } #ifdef __CYGWIN__ /* The cygwin version of sqlite3 has a patch which calls @@ -354,15 +365,17 @@ void LocalStore::openDB(State& state, bool create) { } if (prevMode != mode && sqlite3_exec(db, ("pragma main.journal_mode = " + mode + ";").c_str(), 0, - 0, 0) != SQLITE_OK) + 0, 0) != SQLITE_OK) { throwSQLiteError(db, "setting journal mode"); + } /* Increase the auto-checkpoint interval to 40000 pages. This seems enough to ensure that instantiating the NixOS system derivation is done in a single fsync(). */ if (mode == "wal" && sqlite3_exec(db, "pragma wal_autocheckpoint = 40000;", 0, - 0, 0) != SQLITE_OK) + 0, 0) != SQLITE_OK) { throwSQLiteError(db, "setting autocheckpoint interval"); + } /* Initialise the database schema, if necessary. */ if (create) { @@ -382,15 +395,18 @@ void LocalStore::makeStoreWritable() { } /* Check if /nix/store is on a read-only mount. */ struct statvfs stat; - if (statvfs(realStoreDir.c_str(), &stat) != 0) + if (statvfs(realStoreDir.c_str(), &stat) != 0) { throw SysError("getting info about the Nix store mount point"); + } if (stat.f_flag & ST_RDONLY) { - if (unshare(CLONE_NEWNS) == -1) + if (unshare(CLONE_NEWNS) == -1) { throw SysError("setting up a private mount namespace"); + } - if (mount(0, realStoreDir.c_str(), "none", MS_REMOUNT | MS_BIND, 0) == -1) + if (mount(0, realStoreDir.c_str(), "none", MS_REMOUNT | MS_BIND, 0) == -1) { throw SysError(format("remounting %1% writable") % realStoreDir); + } } #endif } @@ -405,8 +421,9 @@ static void canonicaliseTimestampAndPermissions(const Path& path, if (mode != 0444 && mode != 0555) { mode = (st.st_mode & S_IFMT) | 0444 | (st.st_mode & S_IXUSR ? 0111 : 0); - if (chmod(path.c_str(), mode) == -1) + if (chmod(path.c_str(), mode) == -1) { throw SysError(format("changing mode of '%1%' to %2$o") % path % mode); + } } } @@ -417,20 +434,23 @@ static void canonicaliseTimestampAndPermissions(const Path& path, times[1].tv_sec = mtimeStore; times[1].tv_usec = 0; #if HAVE_LUTIMES - if (lutimes(path.c_str(), times) == -1) + if (lutimes(path.c_str(), times) == -1) { if (errno != ENOSYS || - (!S_ISLNK(st.st_mode) && utimes(path.c_str(), times) == -1)) + (!S_ISLNK(st.st_mode) && utimes(path.c_str(), times) == -1)) { #else if (!S_ISLNK(st.st_mode) && utimes(path.c_str(), times) == -1) #endif throw SysError(format("changing modification time of '%1%'") % path); - } + } + } + } // namespace nix } void canonicaliseTimestampAndPermissions(const Path& path) { struct stat st; - if (lstat(path.c_str(), &st)) + if (lstat(path.c_str(), &st)) { throw SysError(format("getting attributes of path '%1%'") % path); + } canonicaliseTimestampAndPermissions(path, st); } @@ -449,25 +469,29 @@ static void canonicalisePathMetaData_(const Path& path, uid_t fromUid, #endif struct stat st; - if (lstat(path.c_str(), &st)) + if (lstat(path.c_str(), &st)) { throw SysError(format("getting attributes of path '%1%'") % path); + } /* Really make sure that the path is of a supported type. */ - if (!(S_ISREG(st.st_mode) || S_ISDIR(st.st_mode) || S_ISLNK(st.st_mode))) + if (!(S_ISREG(st.st_mode) || S_ISDIR(st.st_mode) || S_ISLNK(st.st_mode))) { throw Error(format("file '%1%' has an unsupported type") % path); + } #if __linux__ /* Remove extended attributes / ACLs. */ ssize_t eaSize = llistxattr(path.c_str(), nullptr, 0); if (eaSize < 0) { - if (errno != ENOTSUP && errno != ENODATA) + if (errno != ENOTSUP && errno != ENODATA) { throw SysError("querying extended attributes of '%s'", path); + } } else if (eaSize > 0) { std::vector eaBuf(eaSize); - if ((eaSize = llistxattr(path.c_str(), eaBuf.data(), eaBuf.size())) < 0) + if ((eaSize = llistxattr(path.c_str(), eaBuf.data(), eaBuf.size())) < 0) { throw SysError("querying extended attributes of '%s'", path); + } for (auto& eaName : tokenizeString( std::string(eaBuf.data(), eaSize), std::string("\000", 1))) { @@ -476,9 +500,10 @@ static void canonicalisePathMetaData_(const Path& path, uid_t fromUid, if (eaName == "security.selinux") { continue; } - if (lremovexattr(path.c_str(), eaName.c_str()) == -1) + if (lremovexattr(path.c_str(), eaName.c_str()) == -1) { throw SysError("removing extended attribute '%s' from '%s'", eaName, path); + } } } #endif @@ -491,8 +516,9 @@ static void canonicalisePathMetaData_(const Path& path, uid_t fromUid, (i.e. "touch $out/foo; ln $out/foo $out/bar"). */ if (fromUid != (uid_t)-1 && st.st_uid != fromUid) { assert(!S_ISDIR(st.st_mode)); - if (inodesSeen.find(Inode(st.st_dev, st.st_ino)) == inodesSeen.end()) + if (inodesSeen.find(Inode(st.st_dev, st.st_ino)) == inodesSeen.end()) { throw BuildError(format("invalid ownership on file '%1%'") % path); + } mode_t mode = st.st_mode & ~S_IFMT; assert(S_ISLNK(st.st_mode) || (st.st_uid == geteuid() && (mode == 0444 || mode == 0555) && @@ -513,18 +539,20 @@ static void canonicalisePathMetaData_(const Path& path, uid_t fromUid, users group); we check for this case below. */ if (st.st_uid != geteuid()) { #if HAVE_LCHOWN - if (lchown(path.c_str(), geteuid(), getegid()) == -1) + if (lchown(path.c_str(), geteuid(), getegid()) == -1) { #else if (!S_ISLNK(st.st_mode) && chown(path.c_str(), geteuid(), getegid()) == -1) #endif throw SysError(format("changing owner of '%1%' to %2%") % path % geteuid()); + } } if (S_ISDIR(st.st_mode)) { DirEntries entries = readDirectory(path); - for (auto& i : entries) + for (auto& i : entries) { canonicalisePathMetaData_(path + "/" + i.name, fromUid, inodesSeen); + } } } @@ -535,8 +563,9 @@ void canonicalisePathMetaData(const Path& path, uid_t fromUid, /* On platforms that don't have lchown(), the top-level path can't be a symlink, since we can't change its ownership. */ struct stat st; - if (lstat(path.c_str(), &st)) + if (lstat(path.c_str(), &st)) { throw SysError(format("getting attributes of path '%1%'") % path); + } if (st.st_uid != geteuid()) { assert(S_ISLNK(st.st_mode)); @@ -557,10 +586,11 @@ void LocalStore::checkDerivationOutputs(const Path& drvPath, if (drv.isFixedOutput()) { DerivationOutputs::const_iterator out = drv.outputs.find("out"); - if (out == drv.outputs.end()) + if (out == drv.outputs.end()) { throw Error( format("derivation '%1%' does not have an output named 'out'") % drvPath); + } bool recursive; Hash h; @@ -569,11 +599,12 @@ void LocalStore::checkDerivationOutputs(const Path& drvPath, StringPairs::const_iterator j = drv.env.find("out"); if (out->second.path != outPath || j == drv.env.end() || - j->second != outPath) + j->second != outPath) { throw Error( format( "derivation '%1%' has incorrect output '%2%', should be '%3%'") % drvPath % out->second.path % outPath); + } } else { @@ -589,21 +620,23 @@ void LocalStore::checkDerivationOutputs(const Path& drvPath, Path outPath = makeOutputPath(i.first, h, drvName); StringPairs::const_iterator j = drv.env.find(i.first); if (i.second.path != outPath || j == drv.env.end() || - j->second != outPath) + j->second != outPath) { throw Error(format("derivation '%1%' has incorrect output '%2%', " "should be '%3%'") % drvPath % i.second.path % outPath); + } } } } uint64_t LocalStore::addValidPath(State& state, const ValidPathInfo& info, bool checkOutputs) { - if (info.ca != "" && !info.isContentAddressed(*this)) + if (info.ca != "" && !info.isContentAddressed(*this)) { throw Error( "cannot add path '%s' to the Nix store because it claims to be " "content-addressed but isn't", info.path); + } state.stmtRegisterValidPath .use()(info.path)(info.narHash.to_string(Base16))( @@ -697,8 +730,9 @@ void LocalStore::queryPathInfoUncached( /* Get the references. */ auto useQueryReferences(state->stmtQueryReferences.use()(info->id)); - while (useQueryReferences.next()) + while (useQueryReferences.next()) { info->references.insert(useQueryReferences.getStr(0)); + } return info; })); @@ -740,10 +774,11 @@ bool LocalStore::isValidPathUncached(const Path& path) { PathSet LocalStore::queryValidPaths(const PathSet& paths, SubstituteFlag maybeSubstitute) { PathSet res; - for (auto& i : paths) + for (auto& i : paths) { if (isValidPath(i)) { res.insert(i); } + } return res; } @@ -752,7 +787,9 @@ PathSet LocalStore::queryAllValidPaths() { auto state(_state.lock()); auto use(state->stmtQueryValidPaths.use()); PathSet res; - while (use.next()) res.insert(use.getStr(0)); + while (use.next()) { + res.insert(use.getStr(0)); + } return res; }); } @@ -761,8 +798,9 @@ void LocalStore::queryReferrers(State& state, const Path& path, PathSet& referrers) { auto useQueryReferrers(state.stmtQueryReferrers.use()(path)); - while (useQueryReferrers.next()) + while (useQueryReferrers.next()) { referrers.insert(useQueryReferrers.getStr(0)); + } } void LocalStore::queryReferrers(const Path& path, PathSet& referrers) { @@ -782,8 +820,9 @@ PathSet LocalStore::queryValidDerivers(const Path& path) { auto useQueryValidDerivers(state->stmtQueryValidDerivers.use()(path)); PathSet derivers; - while (useQueryValidDerivers.next()) + while (useQueryValidDerivers.next()) { derivers.insert(useQueryValidDerivers.getStr(1)); + } return derivers; }); @@ -797,8 +836,9 @@ PathSet LocalStore::queryDerivationOutputs(const Path& path) { queryValidPathId(*state, path))); PathSet outputs; - while (useQueryDerivationOutputs.next()) + while (useQueryDerivationOutputs.next()) { outputs.insert(useQueryDerivationOutputs.getStr(1)); + } return outputs; }); @@ -812,8 +852,9 @@ StringSet LocalStore::queryDerivationOutputNames(const Path& path) { queryValidPathId(*state, path))); StringSet outputNames; - while (useQueryDerivationOutputs.next()) + while (useQueryDerivationOutputs.next()) { outputNames.insert(useQueryDerivationOutputs.getStr(0)); + } return outputNames; }); @@ -865,11 +906,13 @@ PathSet LocalStore::querySubstitutablePaths(const PathSet& paths) { auto valid = sub->queryValidPaths(remaining); PathSet remaining2; - for (auto& path : remaining) - if (valid.count(path)) + for (auto& path : remaining) { + if (valid.count(path)) { res.insert(path); - else + } else { remaining2.insert(path); + } + } std::swap(remaining, remaining2); } @@ -935,24 +978,26 @@ void LocalStore::registerValidPaths(const ValidPathInfos& infos) { for (auto& i : infos) { assert(i.narHash.type == htSHA256); - if (isValidPath_(*state, i.path)) + if (isValidPath_(*state, i.path)) { updatePathInfo(*state, i); - else + } else { addValidPath(*state, i, false); + } paths.insert(i.path); } for (auto& i : infos) { auto referrer = queryValidPathId(*state, i.path); - for (auto& j : i.references) + for (auto& j : i.references) { state->stmtAddReference.use()(referrer)(queryValidPathId(*state, j)) .exec(); + } } /* Check that the derivation outputs are correct. We can't do this in addValidPath() above, because the references might not be valid yet. */ - for (auto& i : infos) + for (auto& i : infos) { if (isDerivation(i.path)) { // FIXME: inefficient; we already loaded the // derivation in addValidPath(). @@ -960,6 +1005,7 @@ void LocalStore::registerValidPaths(const ValidPathInfos& infos) { readDerivation(realStoreDir + "/" + baseNameOf(i.path)); checkDerivationOutputs(i.path, drv); } + } /* Do a topological sort of the paths. This will throw an error if a cycle is detected and roll back the @@ -989,8 +1035,9 @@ void LocalStore::invalidatePath(State& state, const Path& path) { const PublicKeys& LocalStore::getPublicKeys() { auto state(_state.lock()); - if (!state->publicKeys) + if (!state->publicKeys) { state->publicKeys = std::make_unique(getDefaultPublicKeys()); + } return *state->publicKeys; } @@ -1039,15 +1086,17 @@ void LocalStore::addToStore(const ValidPathInfo& info, Source& source, auto hashResult = hashSink.finish(); - if (hashResult.first != info.narHash) + if (hashResult.first != info.narHash) { throw Error( "hash mismatch importing path '%s';\n wanted: %s\n got: %s", info.path, info.narHash.to_string(), hashResult.first.to_string()); + } - if (hashResult.second != info.narSize) + if (hashResult.second != info.narSize) { throw Error( "size mismatch importing path '%s';\n wanted: %s\n got: %s", info.path, info.narSize, hashResult.second); + } autoGC(); @@ -1130,10 +1179,11 @@ Path LocalStore::addToStore(const string& name, const Path& _srcPath, method for very large paths, but `copyPath' is mainly used for small files. */ StringSink sink; - if (recursive) + if (recursive) { dumpPath(srcPath, sink, filter); - else + } else { sink.s = make_ref(readFile(srcPath)); + } return addToStoreFromDump(*sink.s, name, recursive, hashAlgo, repair); } @@ -1206,10 +1256,11 @@ void LocalStore::invalidatePathChecked(const Path& path) { PathSet referrers; queryReferrers(*state, path, referrers); referrers.erase(path); /* ignore self-references */ - if (!referrers.empty()) + if (!referrers.empty()) { throw PathInUse( format("cannot delete path '%1%' because it is in use by %2%") % path % showPaths(referrers)); + } invalidatePath(*state, path); } @@ -1238,8 +1289,9 @@ bool LocalStore::verifyStore(bool checkContents, RepairFlag repair) { fdGCLock = -1; - for (auto& i : validPaths2) + for (auto& i : validPaths2) { verifyPath(i, store, done, validPaths, repair, errors); + } /* Optionally, check the content hashes (slow). */ if (checkContents) { @@ -1328,13 +1380,14 @@ void LocalStore::verifyPath(const Path& path, const PathSet& store, bool canInvalidate = true; PathSet referrers; queryReferrers(path, referrers); - for (auto& i : referrers) + for (auto& i : referrers) { if (i != path) { verifyPath(i, store, done, validPaths, repair, errors); if (validPaths.find(i) != validPaths.end()) { canInvalidate = false; } } + } if (canInvalidate) { LOG(WARNING) << "path '" << path @@ -1463,10 +1516,12 @@ void LocalStore::createUser(const std::string& userName, uid_t userId) { for (auto& dir : {fmt("%s/profiles/per-user/%s", stateDir, userName), fmt("%s/gcroots/per-user/%s", stateDir, userName)}) { createDirs(dir); - if (chmod(dir.c_str(), 0755) == -1) + if (chmod(dir.c_str(), 0755) == -1) { throw SysError("changing permissions of directory '%s'", dir); - if (chown(dir.c_str(), userId, getgid()) == -1) + } + if (chown(dir.c_str(), userId, getgid()) == -1) { throw SysError("changing owner of directory '%s'", dir); + } } } diff --git a/third_party/nix/src/libstore/misc.cc b/third_party/nix/src/libstore/misc.cc index daed88cdc9..a82fc1251c 100644 --- a/third_party/nix/src/libstore/misc.cc +++ b/third_party/nix/src/libstore/misc.cc @@ -47,35 +47,44 @@ void Store::computeFSClosure(const PathSet& startPaths, PathSet& paths_, if (flipDirection) { PathSet referrers; queryReferrers(path, referrers); - for (auto& ref : referrers) + for (auto& ref : referrers) { if (ref != path) { enqueue(ref); } + } - if (includeOutputs) + if (includeOutputs) { for (auto& i : queryValidDerivers(path)) { enqueue(i); } + } - if (includeDerivers && isDerivation(path)) - for (auto& i : queryDerivationOutputs(path)) - if (isValidPath(i) && queryPathInfo(i)->deriver == path) + if (includeDerivers && isDerivation(path)) { + for (auto& i : queryDerivationOutputs(path)) { + if (isValidPath(i) && queryPathInfo(i)->deriver == path) { enqueue(i); + } + } + } } else { - for (auto& ref : info->references) + for (auto& ref : info->references) { if (ref != path) { enqueue(ref); } + } - if (includeOutputs && isDerivation(path)) - for (auto& i : queryDerivationOutputs(path)) + if (includeOutputs && isDerivation(path)) { + for (auto& i : queryDerivationOutputs(path)) { if (isValidPath(i)) { enqueue(i); } + } + } - if (includeDerivers && isValidPath(info->deriver)) + if (includeDerivers && isValidPath(info->deriver)) { enqueue(info->deriver); + } } { @@ -105,7 +114,9 @@ void Store::computeFSClosure(const PathSet& startPaths, PathSet& paths_, { auto state(state_.lock()); - while (state->pending) state.wait(done); + while (state->pending) { + state.wait(done); + } if (state->exc) { std::rethrow_exception(state->exc); } @@ -154,9 +165,10 @@ void Store::queryMissing(const PathSet& targets, PathSet& willBuild_, state->willBuild.insert(drvPath); } - for (auto& i : drv.inputDrvs) + for (auto& i : drv.inputDrvs) { pool.enqueue( std::bind(doPath, makeDrvPathWithOutputs(i.first, i.second))); + } }; auto checkOutput = [&](const Path& drvPath, ref drv, @@ -181,8 +193,9 @@ void Store::queryMissing(const PathSet& targets, PathSet& willBuild_, drvState->left--; drvState->outPaths.insert(outPath); if (!drvState->left) { - for (auto& path : drvState->outPaths) + for (auto& path : drvState->outPaths) { pool.enqueue(std::bind(doPath, path)); + } } } } @@ -211,20 +224,24 @@ void Store::queryMissing(const PathSet& targets, PathSet& willBuild_, ParsedDerivation parsedDrv(i2.first, drv); PathSet invalid; - for (auto& j : drv.outputs) - if (wantOutput(j.first, i2.second) && !isValidPath(j.second.path)) + for (auto& j : drv.outputs) { + if (wantOutput(j.first, i2.second) && !isValidPath(j.second.path)) { invalid.insert(j.second.path); + } + } if (invalid.empty()) { return; } if (settings.useSubstitutes && parsedDrv.substitutesAllowed()) { auto drvState = make_ref>(DrvState(invalid.size())); - for (auto& output : invalid) + for (auto& output : invalid) { pool.enqueue(std::bind(checkOutput, i2.first, make_ref(drv), output, drvState)); - } else + } + } else { mustBuildDrv(i2.first, drv); + } } else { if (isValidPath(path)) { @@ -250,8 +267,9 @@ void Store::queryMissing(const PathSet& targets, PathSet& willBuild_, state->narSize += info->second.narSize; } - for (auto& ref : info->second.references) + for (auto& ref : info->second.references) { pool.enqueue(std::bind(doPath, ref)); + } } }; @@ -269,10 +287,11 @@ Paths Store::topoSortPaths(const PathSet& paths) { std::function dfsVisit; dfsVisit = [&](const Path& path, const Path* parent) { - if (parents.find(path) != parents.end()) + if (parents.find(path) != parents.end()) { throw BuildError( format("cycle detected in the references of '%1%' from '%2%'") % path % *parent); + } if (visited.find(path) != visited.end()) { return; @@ -286,12 +305,13 @@ Paths Store::topoSortPaths(const PathSet& paths) { } catch (InvalidPath&) { } - for (auto& i : references) + for (auto& i : references) { /* Don't traverse into paths that don't exist. That can happen due to substitutes for non-existent paths. */ if (i != path && paths.find(i) != paths.end()) { dfsVisit(i, &path); } + } sorted.push_front(path); parents.erase(path); diff --git a/third_party/nix/src/libstore/nar-accessor.cc b/third_party/nix/src/libstore/nar-accessor.cc index 8a57179ab3..8be22ada2e 100644 --- a/third_party/nix/src/libstore/nar-accessor.cc +++ b/third_party/nix/src/libstore/nar-accessor.cc @@ -45,14 +45,17 @@ struct NarAccessor : public FSAccessor { void createMember(const Path& path, NarMember member) { size_t level = std::count(path.begin(), path.end(), '/'); - while (parents.size() > level) parents.pop(); + while (parents.size() > level) { + parents.pop(); + } if (parents.empty()) { acc.root = std::move(member); parents.push(&acc.root); } else { - if (parents.top()->type != FSAccessor::Type::tDirectory) + if (parents.top()->type != FSAccessor::Type::tDirectory) { throw Error("NAR file missing parent directory of path '%s'", path); + } auto result = parents.top()->children.emplace(baseNameOf(path), std::move(member)); parents.push(&result.first->second); @@ -118,8 +121,9 @@ struct NarAccessor : public FSAccessor { } else if (type == "symlink") { member.type = FSAccessor::Type::tSymlink; member.target = v.value("target", ""); - } else + } else { return; + } }; json v = json::parse(listing); @@ -157,8 +161,9 @@ struct NarAccessor : public FSAccessor { NarMember& get(const Path& path) { auto result = find(path); - if (result == nullptr) + if (result == nullptr) { throw Error("NAR file does not contain path '%1%'", path); + } return *result; } @@ -173,9 +178,10 @@ struct NarAccessor : public FSAccessor { StringSet readDirectory(const Path& path) override { auto i = get(path); - if (i.type != FSAccessor::Type::tDirectory) + if (i.type != FSAccessor::Type::tDirectory) { throw Error(format("path '%1%' inside NAR file is not a directory") % path); + } StringSet res; for (auto& child : i.children) { @@ -187,9 +193,10 @@ struct NarAccessor : public FSAccessor { std::string readFile(const Path& path) override { auto i = get(path); - if (i.type != FSAccessor::Type::tRegular) + if (i.type != FSAccessor::Type::tRegular) { throw Error(format("path '%1%' inside NAR file is not a regular file") % path); + } if (getNarBytes) { return getNarBytes(i.start, i.size); @@ -201,8 +208,9 @@ struct NarAccessor : public FSAccessor { std::string readLink(const Path& path) override { auto i = get(path); - if (i.type != FSAccessor::Type::tSymlink) + if (i.type != FSAccessor::Type::tSymlink) { throw Error(format("path '%1%' inside NAR file is not a symlink") % path); + } return i.target; } }; @@ -241,8 +249,9 @@ void listNar(JSONPlaceholder& res, ref accessor, const Path& path, if (recurse) { auto res3 = res2.placeholder(name); listNar(res3, accessor, path + "/" + name, true); - } else + } else { res2.object(name); + } } } break; diff --git a/third_party/nix/src/libstore/nar-info-disk-cache.cc b/third_party/nix/src/libstore/nar-info-disk-cache.cc index 6d9aeb129d..3adda508d0 100644 --- a/third_party/nix/src/libstore/nar-info-disk-cache.cc +++ b/third_party/nix/src/libstore/nar-info-disk-cache.cc @@ -76,8 +76,9 @@ class NarInfoDiskCacheImpl : public NarInfoDiskCache { state->db = SQLite(dbPath); - if (sqlite3_busy_timeout(state->db, 60 * 60 * 1000) != SQLITE_OK) + if (sqlite3_busy_timeout(state->db, 60 * 60 * 1000) != SQLITE_OK) { throwSQLiteError(state->db, "setting timeout"); + } // We can always reproduce the cache. state->db.exec("pragma synchronous = off"); @@ -224,12 +225,15 @@ class NarInfoDiskCacheImpl : public NarInfoDiskCache { narInfo->fileSize = queryNAR.getInt(5); narInfo->narHash = Hash(queryNAR.getStr(6)); narInfo->narSize = queryNAR.getInt(7); - for (auto& r : tokenizeString(queryNAR.getStr(8), " ")) + for (auto& r : tokenizeString(queryNAR.getStr(8), " ")) { narInfo->references.insert(cache.storeDir + "/" + r); - if (!queryNAR.isNull(9)) + } + if (!queryNAR.isNull(9)) { narInfo->deriver = cache.storeDir + "/" + queryNAR.getStr(9); - for (auto& sig : tokenizeString(queryNAR.getStr(10), " ")) + } + for (auto& sig : tokenizeString(queryNAR.getStr(10), " ")) { narInfo->sigs.insert(sig); + } narInfo->ca = queryNAR.getStr(11); return {oValid, narInfo}; diff --git a/third_party/nix/src/libstore/nar-info.cc b/third_party/nix/src/libstore/nar-info.cc index fa7d72c8ae..fee470fc7d 100644 --- a/third_party/nix/src/libstore/nar-info.cc +++ b/third_party/nix/src/libstore/nar-info.cc @@ -40,19 +40,19 @@ NarInfo::NarInfo(const Store& store, const std::string& s, corrupt(); } path = value; - } else if (name == "URL") + } else if (name == "URL") { url = value; - else if (name == "Compression") + } else if (name == "Compression") { compression = value; - else if (name == "FileHash") + } else if (name == "FileHash") { fileHash = parseHashField(value); - else if (name == "FileSize") { + } else if (name == "FileSize") { if (!string2Int(value, fileSize)) { corrupt(); } - } else if (name == "NarHash") + } else if (name == "NarHash") { narHash = parseHashField(value); - else if (name == "NarSize") { + } else if (name == "NarSize") { if (!string2Int(value, narSize)) { corrupt(); } @@ -76,11 +76,11 @@ NarInfo::NarInfo(const Store& store, const std::string& s, } deriver = p; } - } else if (name == "System") + } else if (name == "System") { system = value; - else if (name == "Sig") + } else if (name == "Sig") { sigs.insert(value); - else if (name == "CA") { + } else if (name == "CA") { if (!ca.empty()) { corrupt(); } diff --git a/third_party/nix/src/libstore/optimise-store.cc b/third_party/nix/src/libstore/optimise-store.cc index ad37190236..8c0f24d382 100644 --- a/third_party/nix/src/libstore/optimise-store.cc +++ b/third_party/nix/src/libstore/optimise-store.cc @@ -17,10 +17,12 @@ namespace nix { static void makeWritable(const Path& path) { struct stat st; - if (lstat(path.c_str(), &st)) + if (lstat(path.c_str(), &st)) { throw SysError(format("getting attributes of path '%1%'") % path); - if (chmod(path.c_str(), st.st_mode | S_IWUSR) == -1) + } + if (chmod(path.c_str(), st.st_mode | S_IWUSR) == -1) { throw SysError(format("changing writability of '%1%'") % path); + } } struct MakeReadOnly { @@ -98,8 +100,9 @@ void LocalStore::optimisePath_(OptimiseStats& stats, const Path& path, checkInterrupt(); struct stat st; - if (lstat(path.c_str(), &st)) + if (lstat(path.c_str(), &st)) { throw SysError(format("getting attributes of path '%1%'") % path); + } #if __APPLE__ /* HFS/macOS has some undocumented security feature disabling hardlinking for @@ -192,8 +195,9 @@ retry: /* Yes! We've seen a file with the same contents. Replace the current file with a hard link to that file. */ struct stat stLink; - if (lstat(linkPath.c_str(), &stLink)) + if (lstat(linkPath.c_str(), &stLink)) { throw SysError(format("getting attributes of path '%1%'") % linkPath); + } if (st.st_ino == stLink.st_ino) { DLOG(INFO) << path << " is already linked to " << linkPath; diff --git a/third_party/nix/src/libstore/parsed-derivations.cc b/third_party/nix/src/libstore/parsed-derivations.cc index 29133664fd..72ed36d32d 100644 --- a/third_party/nix/src/libstore/parsed-derivations.cc +++ b/third_party/nix/src/libstore/parsed-derivations.cc @@ -20,40 +20,44 @@ std::optional ParsedDerivation::getStringAttr( const std::string& name) const { if (structuredAttrs) { auto i = structuredAttrs->find(name); - if (i == structuredAttrs->end()) + if (i == structuredAttrs->end()) { return {}; - else { - if (!i->is_string()) + } else { + if (!i->is_string()) { throw Error("attribute '%s' of derivation '%s' must be a string", name, drvPath); + } return i->get(); } } else { auto i = drv.env.find(name); - if (i == drv.env.end()) + if (i == drv.env.end()) { return {}; - else + } else { return i->second; + } } } bool ParsedDerivation::getBoolAttr(const std::string& name, bool def) const { if (structuredAttrs) { auto i = structuredAttrs->find(name); - if (i == structuredAttrs->end()) + if (i == structuredAttrs->end()) { return def; - else { - if (!i->is_boolean()) + } else { + if (!i->is_boolean()) { throw Error("attribute '%s' of derivation '%s' must be a Boolean", name, drvPath); + } return i->get(); } } else { auto i = drv.env.find(name); - if (i == drv.env.end()) + if (i == drv.env.end()) { return def; - else + } else { return i->second == "1"; + } } } @@ -61,48 +65,54 @@ std::optional ParsedDerivation::getStringsAttr( const std::string& name) const { if (structuredAttrs) { auto i = structuredAttrs->find(name); - if (i == structuredAttrs->end()) + if (i == structuredAttrs->end()) { return {}; - else { - if (!i->is_array()) + } else { + if (!i->is_array()) { throw Error( "attribute '%s' of derivation '%s' must be a list of strings", name, drvPath); + } Strings res; for (auto j = i->begin(); j != i->end(); ++j) { - if (!j->is_string()) + if (!j->is_string()) { throw Error( "attribute '%s' of derivation '%s' must be a list of strings", name, drvPath); + } res.push_back(j->get()); } return res; } } else { auto i = drv.env.find(name); - if (i == drv.env.end()) + if (i == drv.env.end()) { return {}; - else + } else { return tokenizeString(i->second); + } } } StringSet ParsedDerivation::getRequiredSystemFeatures() const { StringSet res; - for (auto& i : getStringsAttr("requiredSystemFeatures").value_or(Strings())) + for (auto& i : getStringsAttr("requiredSystemFeatures").value_or(Strings())) { res.insert(i); + } return res; } bool ParsedDerivation::canBuildLocally() const { if (drv.platform != settings.thisSystem.get() && - !settings.extraPlatforms.get().count(drv.platform) && !drv.isBuiltin()) + !settings.extraPlatforms.get().count(drv.platform) && !drv.isBuiltin()) { return false; + } - for (auto& feature : getRequiredSystemFeatures()) + for (auto& feature : getRequiredSystemFeatures()) { if (!settings.systemFeatures.get().count(feature)) { return false; } + } return true; } diff --git a/third_party/nix/src/libstore/pathlocks.cc b/third_party/nix/src/libstore/pathlocks.cc index ffec3d7d7e..a0d7b721ec 100644 --- a/third_party/nix/src/libstore/pathlocks.cc +++ b/third_party/nix/src/libstore/pathlocks.cc @@ -18,8 +18,9 @@ AutoCloseFD openLockFile(const Path& path, bool create) { AutoCloseFD fd; fd = open(path.c_str(), O_CLOEXEC | O_RDWR | (create ? O_CREAT : 0), 0600); - if (!fd && (create || errno != ENOENT)) + if (!fd && (create || errno != ENOENT)) { throw SysError(format("opening lock file '%1%'") % path); + } return fd; } @@ -37,22 +38,24 @@ void deleteLockFile(const Path& path, int fd) { bool lockFile(int fd, LockType lockType, bool wait) { int type; - if (lockType == ltRead) + if (lockType == ltRead) { type = LOCK_SH; - else if (lockType == ltWrite) + } else if (lockType == ltWrite) { type = LOCK_EX; - else if (lockType == ltNone) + } else if (lockType == ltNone) { type = LOCK_UN; - else + } else { abort(); + } if (wait) { while (flock(fd, type) != 0) { checkInterrupt(); - if (errno != EINTR) + if (errno != EINTR) { throw SysError(format("acquiring/releasing lock")); - else + } else { return false; + } } } else { while (flock(fd, type | LOCK_NB) != 0) { @@ -118,16 +121,18 @@ bool PathLocks::lockPaths(const PathSet& paths, const string& waitMsg, /* Check that the lock file hasn't become stale (i.e., hasn't been unlinked). */ struct stat st; - if (fstat(fd.get(), &st) == -1) + if (fstat(fd.get(), &st) == -1) { throw SysError(format("statting lock file '%1%'") % lockPath); - if (st.st_size != 0) + } + if (st.st_size != 0) { /* This lock file has been unlinked, so we're holding a lock on a deleted file. This means that other processes may create and acquire a lock on `lockPath', and proceed. So we must retry. */ DLOG(INFO) << "open lock file '" << lockPath << "' has become stale"; - else + } else { break; + } } /* Use borrow so that the descriptor isn't closed. */ diff --git a/third_party/nix/src/libstore/profiles.cc b/third_party/nix/src/libstore/profiles.cc index 38d0972e44..38ad0c01e4 100644 --- a/third_party/nix/src/libstore/profiles.cc +++ b/third_party/nix/src/libstore/profiles.cc @@ -28,10 +28,11 @@ static int parseName(const string& profileName, const string& name) { return -1; } int n; - if (string2Int(string(s, 0, p), n) && n >= 0) + if (string2Int(string(s, 0, p), n) && n >= 0) { return n; - else + } else { return -1; + } } Generations findGenerations(Path profile, int& curGen) { @@ -47,8 +48,9 @@ Generations findGenerations(Path profile, int& curGen) { gen.path = profileDir + "/" + i.name; gen.number = n; struct stat st; - if (lstat(gen.path.c_str(), &st) != 0) + if (lstat(gen.path.c_str(), &st) != 0) { throw SysError(format("statting '%1%'") % gen.path); + } gen.creationTime = st.st_mtime; gens.push_back(gen); } @@ -105,8 +107,9 @@ Path createGeneration(ref store, Path profile, Path outPath) { } static void removeFile(const Path& path) { - if (remove(path.c_str()) == -1) + if (remove(path.c_str()) == -1) { throw SysError(format("cannot unlink '%1%'") % path); + } } void deleteGeneration(const Path& profile, unsigned int gen) { @@ -134,9 +137,10 @@ void deleteGenerations(const Path& profile, int curGen; Generations gens = findGenerations(profile, curGen); - if (gensToDelete.find(curGen) != gensToDelete.end()) + if (gensToDelete.find(curGen) != gensToDelete.end()) { throw Error(format("cannot delete current generation of profile %1%'") % profile); + } for (auto& i : gens) { if (gensToDelete.find(i.number) == gensToDelete.end()) { @@ -176,10 +180,11 @@ void deleteOldGenerations(const Path& profile, bool dryRun) { int curGen; Generations gens = findGenerations(profile, curGen); - for (auto& i : gens) + for (auto& i : gens) { if (i.number != curGen) { deleteGeneration2(profile, i.number, dryRun); } + } } void deleteGenerationsOlderThan(const Path& profile, time_t t, bool dryRun) { @@ -190,7 +195,7 @@ void deleteGenerationsOlderThan(const Path& profile, time_t t, bool dryRun) { Generations gens = findGenerations(profile, curGen); bool canDelete = false; - for (auto i = gens.rbegin(); i != gens.rend(); ++i) + for (auto i = gens.rbegin(); i != gens.rend(); ++i) { if (canDelete) { assert(i->creationTime < t); if (i->number != curGen) { @@ -203,6 +208,7 @@ void deleteGenerationsOlderThan(const Path& profile, time_t t, bool dryRun) { time. */ canDelete = true; } + } } void deleteGenerationsOlderThan(const Path& profile, const string& timeSpec, @@ -211,8 +217,9 @@ void deleteGenerationsOlderThan(const Path& profile, const string& timeSpec, string strDays = string(timeSpec, 0, timeSpec.size() - 1); int days; - if (!string2Int(strDays, days) || days < 1) + if (!string2Int(strDays, days) || days < 1) { throw Error(format("invalid number of days specifier '%1%'") % timeSpec); + } time_t oldTime = curTime - days * 24 * 3600; diff --git a/third_party/nix/src/libstore/references.cc b/third_party/nix/src/libstore/references.cc index a46bdc758f..64b997ce3e 100644 --- a/third_party/nix/src/libstore/references.cc +++ b/third_party/nix/src/libstore/references.cc @@ -21,20 +21,22 @@ static void search(const unsigned char* s, size_t len, StringSet& hashes, for (unsigned int i = 0; i < 256; ++i) { isBase32[i] = false; } - for (unsigned int i = 0; i < base32Chars.size(); ++i) + for (unsigned int i = 0; i < base32Chars.size(); ++i) { isBase32[(unsigned char)base32Chars[i]] = true; + } initialised = true; } for (size_t i = 0; i + refLength <= len;) { int j; bool match = true; - for (j = refLength - 1; j >= 0; --j) + for (j = refLength - 1; j >= 0; --j) { if (!isBase32[(unsigned char)s[i + j]]) { i += j + 1; match = false; break; } + } if (!match) { continue; } diff --git a/third_party/nix/src/libstore/remote-fs-accessor.cc b/third_party/nix/src/libstore/remote-fs-accessor.cc index 0b9bb805eb..819f54c161 100644 --- a/third_party/nix/src/libstore/remote-fs-accessor.cc +++ b/third_party/nix/src/libstore/remote-fs-accessor.cc @@ -48,9 +48,10 @@ std::pair, Path> RemoteFSAccessor::fetch(const Path& path_) { auto storePath = store->toStorePath(path); std::string restPath = std::string(path, storePath.size()); - if (!store->isValidPath(storePath)) + if (!store->isValidPath(storePath)) { throw InvalidPath(format("path '%1%' is not a valid store path") % storePath); + } auto i = nars.find(storePath); if (i != nars.end()) { @@ -73,8 +74,9 @@ std::pair, Path> RemoteFSAccessor::fetch(const Path& path_) { throw SysError("opening NAR cache file '%s'", cacheFile); } - if (lseek(fd.get(), offset, SEEK_SET) != (off_t)offset) + if (lseek(fd.get(), offset, SEEK_SET) != (off_t)offset) { throw SysError("seeking in '%s'", cacheFile); + } std::string buf(length, 0); readFull(fd.get(), (unsigned char*)buf.data(), length); diff --git a/third_party/nix/src/libstore/remote-store.cc b/third_party/nix/src/libstore/remote-store.cc index e6849cb160..b0025df98f 100644 --- a/third_party/nix/src/libstore/remote-store.cc +++ b/third_party/nix/src/libstore/remote-store.cc @@ -57,9 +57,10 @@ RemoteStore::RemoteStore(const Params& params) })) {} ref RemoteStore::openConnectionWrapper() { - if (failed) + if (failed) { throw Error("opening a connection to remote store '%s' previously failed", getUri()); + } try { return openConnection(); } catch (...) { @@ -105,12 +106,14 @@ ref UDSRemoteStore::openConnection() { struct sockaddr_un addr; addr.sun_family = AF_UNIX; - if (socketPath.size() + 1 >= sizeof(addr.sun_path)) + if (socketPath.size() + 1 >= sizeof(addr.sun_path)) { throw Error(format("socket path '%1%' is too long") % socketPath); + } strcpy(addr.sun_path, socketPath.c_str()); - if (::connect(conn->fd.get(), (struct sockaddr*)&addr, sizeof(addr)) == -1) + if (::connect(conn->fd.get(), (struct sockaddr*)&addr, sizeof(addr)) == -1) { throw SysError(format("cannot connect to daemon at '%1%'") % socketPath); + } conn->from.fd = conn->fd.get(); conn->to.fd = conn->fd.get(); @@ -134,18 +137,21 @@ void RemoteStore::initConnection(Connection& conn) { conn.from >> conn.daemonVersion; if (GET_PROTOCOL_MAJOR(conn.daemonVersion) != - GET_PROTOCOL_MAJOR(PROTOCOL_VERSION)) + GET_PROTOCOL_MAJOR(PROTOCOL_VERSION)) { throw Error("Nix daemon protocol version not supported"); - if (GET_PROTOCOL_MINOR(conn.daemonVersion) < 10) + } + if (GET_PROTOCOL_MINOR(conn.daemonVersion) < 10) { throw Error("the Nix daemon version is too old"); + } conn.to << PROTOCOL_VERSION; if (GET_PROTOCOL_MINOR(conn.daemonVersion) >= 14) { int cpu = sameMachine() && settings.lockCPU ? lockToCurrentCPU() : -1; - if (cpu != -1) + if (cpu != -1) { conn.to << 1 << cpu; - else + } else { conn.to << 0; + } } if (GET_PROTOCOL_MINOR(conn.daemonVersion) >= 11) { @@ -249,10 +255,11 @@ PathSet RemoteStore::queryValidPaths(const PathSet& paths, auto conn(getConnection()); if (GET_PROTOCOL_MINOR(conn->daemonVersion) < 12) { PathSet res; - for (auto& i : paths) + for (auto& i : paths) { if (isValidPath(i)) { res.insert(i); } + } return res; } else { conn->to << wopQueryValidPaths << paths; @@ -344,8 +351,9 @@ void RemoteStore::queryPathInfoUncached( conn.processStderr(); } catch (Error& e) { // Ugly backwards compatibility hack. - if (e.msg().find("is not valid") != std::string::npos) + if (e.msg().find("is not valid") != std::string::npos) { throw InvalidPath(e.what()); + } throw; } if (GET_PROTOCOL_MINOR(conn->daemonVersion) >= 17) { @@ -456,9 +464,10 @@ void RemoteStore::addToStore(const ValidPathInfo& info, Source& source, Path RemoteStore::addToStore(const string& name, const Path& _srcPath, bool recursive, HashType hashAlgo, PathFilter& filter, RepairFlag repair) { - if (repair) + if (repair) { throw Error( "repairing is not supported when building through the Nix daemon"); + } auto conn(getConnection()); @@ -483,10 +492,12 @@ Path RemoteStore::addToStore(const string& name, const Path& _srcPath, } catch (SysError& e) { /* Daemon closed while we were sending the path. Probably OOM or I/O error. */ - if (e.errNo == EPIPE) try { + if (e.errNo == EPIPE) { + try { conn.processStderr(); } catch (EndOfFile& e) { } + } throw; } @@ -495,9 +506,10 @@ Path RemoteStore::addToStore(const string& name, const Path& _srcPath, Path RemoteStore::addTextToStore(const string& name, const string& s, const PathSet& references, RepairFlag repair) { - if (repair) + if (repair) { throw Error( "repairing is not supported when building through the Nix daemon"); + } auto conn(getConnection()); conn->to << wopAddTextToStore << name << s << references; @@ -511,15 +523,16 @@ void RemoteStore::buildPaths(const PathSet& drvPaths, BuildMode buildMode) { conn->to << wopBuildPaths; if (GET_PROTOCOL_MINOR(conn->daemonVersion) >= 13) { conn->to << drvPaths; - if (GET_PROTOCOL_MINOR(conn->daemonVersion) >= 15) + if (GET_PROTOCOL_MINOR(conn->daemonVersion) >= 15) { conn->to << buildMode; - else + } else /* Old daemons did not take a 'buildMode' parameter, so we need to validate it here on the client side. */ - if (buildMode != bmNormal) + if (buildMode != bmNormal) { throw Error( "repairing or checking is not supported when building through the " "Nix daemon"); + } } else { /* For backwards compatibility with old daemons, strip output identifiers. */ diff --git a/third_party/nix/src/libstore/sqlite.cc b/third_party/nix/src/libstore/sqlite.cc index 5aa661afe0..f2650ed753 100644 --- a/third_party/nix/src/libstore/sqlite.cc +++ b/third_party/nix/src/libstore/sqlite.cc @@ -31,8 +31,9 @@ namespace nix { SQLite::SQLite(const Path& path) { if (sqlite3_open_v2(path.c_str(), &db, SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE, - 0) != SQLITE_OK) + 0) != SQLITE_OK) { throw Error(format("cannot open SQLite database '%s'") % path); + } } SQLite::~SQLite() { @@ -47,24 +48,27 @@ SQLite::~SQLite() { void SQLite::exec(const std::string& stmt) { retrySQLite([&]() { - if (sqlite3_exec(db, stmt.c_str(), 0, 0, 0) != SQLITE_OK) + if (sqlite3_exec(db, stmt.c_str(), 0, 0, 0) != SQLITE_OK) { throwSQLiteError(db, format("executing SQLite statement '%s'") % stmt); + } }); } void SQLiteStmt::create(sqlite3* db, const string& sql) { checkInterrupt(); assert(!stmt); - if (sqlite3_prepare_v2(db, sql.c_str(), -1, &stmt, 0) != SQLITE_OK) + if (sqlite3_prepare_v2(db, sql.c_str(), -1, &stmt, 0) != SQLITE_OK) { throwSQLiteError(db, fmt("creating statement '%s'", sql)); + } this->db = db; this->sql = sql; } SQLiteStmt::~SQLiteStmt() { try { - if (stmt && sqlite3_finalize(stmt) != SQLITE_OK) + if (stmt && sqlite3_finalize(stmt) != SQLITE_OK) { throwSQLiteError(db, fmt("finalizing statement '%s'", sql)); + } } catch (...) { ignoreException(); } @@ -83,8 +87,9 @@ SQLiteStmt::Use& SQLiteStmt::Use::operator()(const std::string& value, bool notNull) { if (notNull) { if (sqlite3_bind_text(stmt, curArg++, value.c_str(), -1, - SQLITE_TRANSIENT) != SQLITE_OK) + SQLITE_TRANSIENT) != SQLITE_OK) { throwSQLiteError(stmt.db, "binding argument"); + } } else { bind(); } @@ -93,8 +98,9 @@ SQLiteStmt::Use& SQLiteStmt::Use::operator()(const std::string& value, SQLiteStmt::Use& SQLiteStmt::Use::operator()(int64_t value, bool notNull) { if (notNull) { - if (sqlite3_bind_int64(stmt, curArg++, value) != SQLITE_OK) + if (sqlite3_bind_int64(stmt, curArg++, value) != SQLITE_OK) { throwSQLiteError(stmt.db, "binding argument"); + } } else { bind(); } @@ -113,14 +119,16 @@ int SQLiteStmt::Use::step() { return sqlite3_step(stmt); } void SQLiteStmt::Use::exec() { int r = step(); assert(r != SQLITE_ROW); - if (r != SQLITE_DONE) + if (r != SQLITE_DONE) { throwSQLiteError(stmt.db, fmt("executing SQLite statement '%s'", stmt.sql)); + } } bool SQLiteStmt::Use::next() { int r = step(); - if (r != SQLITE_DONE && r != SQLITE_ROW) + if (r != SQLITE_DONE && r != SQLITE_ROW) { throwSQLiteError(stmt.db, fmt("executing SQLite query '%s'", stmt.sql)); + } return r == SQLITE_ROW; } diff --git a/third_party/nix/src/libstore/ssh.cc b/third_party/nix/src/libstore/ssh.cc index 20add33c00..1783732a1d 100644 --- a/third_party/nix/src/libstore/ssh.cc +++ b/third_party/nix/src/libstore/ssh.cc @@ -10,13 +10,15 @@ SSHMaster::SSHMaster(const std::string& host, const std::string& keyFile, useMaster(useMaster && !fakeSSH), compress(compress), logFD(logFD) { - if (host == "" || hasPrefix(host, "-")) + if (host == "" || hasPrefix(host, "-")) { throw Error("invalid SSH host name '%s'", host); + } } void SSHMaster::addCommonSSHOpts(Strings& args) { - for (auto& i : tokenizeString(getEnv("NIX_SSHOPTS"))) + for (auto& i : tokenizeString(getEnv("NIX_SSHOPTS"))) { args.push_back(i); + } if (!keyFile.empty()) { args.insert(args.end(), {"-i", keyFile}); } @@ -44,12 +46,15 @@ std::unique_ptr SSHMaster::startCommand( close(in.writeSide.get()); close(out.readSide.get()); - if (dup2(in.readSide.get(), STDIN_FILENO) == -1) + if (dup2(in.readSide.get(), STDIN_FILENO) == -1) { throw SysError("duping over stdin"); - if (dup2(out.writeSide.get(), STDOUT_FILENO) == -1) + } + if (dup2(out.writeSide.get(), STDOUT_FILENO) == -1) { throw SysError("duping over stdout"); - if (logFD != -1 && dup2(logFD, STDERR_FILENO) == -1) + } + if (logFD != -1 && dup2(logFD, STDERR_FILENO) == -1) { throw SysError("duping over stderr"); + } Strings args; @@ -112,8 +117,9 @@ Path SSHMaster::startMaster() { close(out.readSide.get()); - if (dup2(out.writeSide.get(), STDOUT_FILENO) == -1) + if (dup2(out.writeSide.get(), STDOUT_FILENO) == -1) { throw SysError("duping over stdout"); + } Strings args = {"ssh", host.c_str(), "-M", "-N", @@ -136,8 +142,9 @@ Path SSHMaster::startMaster() { } catch (EndOfFile& e) { } - if (reply != "started") + if (reply != "started") { throw Error("failed to start SSH master connection to '%s'", host); + } return state->socketPath; } diff --git a/third_party/nix/src/libstore/store-api.cc b/third_party/nix/src/libstore/store-api.cc index 2a7b6a1ac4..7658a51100 100644 --- a/third_party/nix/src/libstore/store-api.cc +++ b/third_party/nix/src/libstore/store-api.cc @@ -25,18 +25,21 @@ bool Store::isStorePath(const Path& path) const { } void Store::assertStorePath(const Path& path) const { - if (!isStorePath(path)) + if (!isStorePath(path)) { throw Error(format("path '%1%' is not in the Nix store") % path); + } } Path Store::toStorePath(const Path& path) const { - if (!isInStore(path)) + if (!isInStore(path)) { throw Error(format("path '%1%' is not in the Nix store") % path); + } Path::size_type slash = path.find('/', storeDir.size() + 1); - if (slash == Path::npos) + if (slash == Path::npos) { return path; - else + } else { return Path(path, 0, slash); + } } Path Store::followLinksToStore(const Path& _path) const { @@ -48,8 +51,9 @@ Path Store::followLinksToStore(const Path& _path) const { string target = readLink(path); path = absPath(target, dirOf(path)); } - if (!isInStore(path)) + if (!isInStore(path)) { throw Error(format("path '%1%' is not in the Nix store") % path); + } return path; } @@ -86,17 +90,20 @@ void checkStoreName(const string& name) { /* Disallow names starting with a dot for possible security reasons (e.g., "." and ".."). */ - if (string(name, 0, 1) == ".") + if (string(name, 0, 1) == ".") { throw Error(baseError % "it is illegal to start the name with a period"); + } /* Disallow names longer than 211 characters. ext4’s max is 256, but we need extra space for the hash and .chroot extensions. */ - if (name.length() > 211) + if (name.length() > 211) { throw Error(baseError % "name must be less than 212 characters"); - for (auto& i : name) + } + for (auto& i : name) { if (!((i >= 'A' && i <= 'Z') || (i >= 'a' && i <= 'z') || (i >= '0' && i <= '9') || validChars.find(i) != string::npos)) { throw Error(baseError % (format("the '%1%' character is invalid") % i)); } + } } /* Store paths have the following form: @@ -261,9 +268,10 @@ bool Store::isValidPath(const Path& storePath) { bool valid = isValidPathUncached(storePath); - if (diskCache && !valid) + if (diskCache && !valid) { // FIXME: handle valid = true case. diskCache->upsertNarInfo(getUri(), hashPart, 0); + } return valid; } @@ -306,8 +314,9 @@ void Store::queryPathInfo(const Path& storePath, auto res = state.lock()->pathInfoCache.get(hashPart); if (res) { stats.narInfoReadAverted++; - if (!*res) + if (!*res) { throw InvalidPath(format("path '%s' is not valid") % storePath); + } return callback(ref(*res)); } } @@ -323,8 +332,9 @@ void Store::queryPathInfo(const Path& storePath, res.first == NarInfoDiskCache::oInvalid ? 0 : res.second); if (res.first == NarInfoDiskCache::oInvalid || (res.second->path != storePath && - storePathToName(storePath) != "")) + storePathToName(storePath) != "")) { throw InvalidPath(format("path '%s' is not valid") % storePath); + } } return callback(ref(res.second)); } @@ -483,8 +493,9 @@ void Store::pathInfoToJSON(JSONPlaceholder& jsonOut, const PathSet& storePaths, jsonPath.attr("deriver", info->deriver); } - if (info->registrationTime) + if (info->registrationTime) { jsonPath.attr("registrationTime", info->registrationTime); + } if (info->ultimate) { jsonPath.attr("ultimate", info->ultimate); @@ -504,12 +515,15 @@ void Store::pathInfoToJSON(JSONPlaceholder& jsonOut, const PathSet& storePaths, if (!narInfo->url.empty()) { jsonPath.attr("url", narInfo->url); } - if (narInfo->fileHash) + if (narInfo->fileHash) { jsonPath.attr("downloadHash", narInfo->fileHash.to_string()); - if (narInfo->fileSize) + } + if (narInfo->fileSize) { jsonPath.attr("downloadSize", narInfo->fileSize); - if (showClosureSize) + } + if (showClosureSize) { jsonPath.attr("closureDownloadSize", closureSizes.second); + } } } @@ -544,10 +558,11 @@ const Store::Stats& Store::getStats() { } void Store::buildPaths(const PathSet& paths, BuildMode buildMode) { - for (auto& path : paths) + for (auto& path : paths) { if (isDerivation(path)) { unsupported("buildPaths"); } + } if (queryValidPaths(paths).size() != paths.size()) { unsupported("buildPaths"); @@ -621,10 +636,11 @@ void copyPaths(ref srcStore, ref dstStore, PathSet valid = dstStore->queryValidPaths(storePaths, substitute); PathSet missing; - for (auto& path : storePaths) + for (auto& path : storePaths) { if (!valid.count(path)) { missing.insert(path); } + } if (missing.empty()) { return; @@ -729,10 +745,11 @@ string showPaths(const PathSet& paths) { } std::string ValidPathInfo::fingerprint() const { - if (narSize == 0 || !narHash) + if (narSize == 0 || !narHash) { throw Error(format("cannot calculate fingerprint of path '%s' because its " "size/hash is not known") % path); + } return "1;" + path + ";" + narHash.to_string(Base32) + ";" + std::to_string(narSize) + ";" + concatStringsSep(",", references); } @@ -749,10 +766,11 @@ bool ValidPathInfo::isContentAddressed(const Store& store) const { if (hasPrefix(ca, "text:")) { Hash hash(std::string(ca, 5)); - if (store.makeTextPath(storePathToName(path), hash, references) == path) + if (store.makeTextPath(storePathToName(path), hash, references) == path) { return true; - else + } else { warn(); + } } else if (hasPrefix(ca, "fixed:")) { @@ -760,10 +778,11 @@ bool ValidPathInfo::isContentAddressed(const Store& store) const { Hash hash(std::string(ca, recursive ? 8 : 6)); if (references.empty() && store.makeFixedOutputPath(recursive, hash, storePathToName(path)) == - path) + path) { return true; - else + } else { warn(); + } } return false; @@ -776,10 +795,11 @@ size_t ValidPathInfo::checkSignatures(const Store& store, } size_t good = 0; - for (auto& sig : sigs) + for (auto& sig : sigs) { if (checkSignature(publicKeys, sig)) { good++; } + } return good; } @@ -838,16 +858,18 @@ std::pair splitUriAndParams( std::string decoded; for (size_t i = 0; i < value.size();) { if (value[i] == '%') { - if (i + 2 >= value.size()) + if (i + 2 >= value.size()) { throw Error("invalid URI parameter '%s'", value); + } try { decoded += std::stoul(std::string(value, i + 1, 2), 0, 16); i += 3; } catch (...) { throw Error("invalid URI parameter '%s'", value); } - } else + } else { decoded += value[i++]; + } } params[s.substr(0, e)] = decoded; } @@ -880,9 +902,9 @@ StoreType getStoreType(const std::string& uri, const std::string& stateDir) { } else if (uri == "local" || hasPrefix(uri, "/")) { return tLocal; } else if (uri == "" || uri == "auto") { - if (access(stateDir.c_str(), R_OK | W_OK) == 0) + if (access(stateDir.c_str(), R_OK | W_OK) == 0) { return tLocal; - else if (pathExists(settings.nixDaemonSocketFile)) { + } else if (pathExists(settings.nixDaemonSocketFile)) { return tDaemon; } else { return tLocal; diff --git a/third_party/nix/src/libutil/archive.cc b/third_party/nix/src/libutil/archive.cc index a86170b315..855a3c4658 100644 --- a/third_party/nix/src/libutil/archive.cc +++ b/third_party/nix/src/libutil/archive.cc @@ -76,9 +76,10 @@ static void dump(const Path& path, Sink& sink, PathFilter& filter) { if (S_ISREG(st.st_mode)) { sink << "type" << "regular"; - if (st.st_mode & S_IXUSR) + if (st.st_mode & S_IXUSR) { sink << "executable" << ""; + } dumpContents(path, (size_t)st.st_size, sink); } @@ -89,7 +90,7 @@ static void dump(const Path& path, Sink& sink, PathFilter& filter) { /* If we're on a case-insensitive system like macOS, undo the case hack applied by restorePath(). */ std::map unhacked; - for (auto& i : readDirectory(path)) + for (auto& i : readDirectory(path)) { if (archiveSettings.useCaseHack) { string name(i.name); size_t pos = i.name.find(caseHackSuffix); @@ -99,14 +100,17 @@ static void dump(const Path& path, Sink& sink, PathFilter& filter) { name.erase(pos); } - if (unhacked.find(name) != unhacked.end()) + if (unhacked.find(name) != unhacked.end()) { throw Error(format("file name collision in between '%1%' and '%2%'") % (path + "/" + unhacked[name]) % (path + "/" + i.name)); + } unhacked[name] = i.name; - } else + } else { unhacked[i.name] = i.name; + } + } - for (auto& i : unhacked) + for (auto& i : unhacked) { if (filter(path + "/" + i.first)) { sink << "entry" << "(" @@ -114,15 +118,17 @@ static void dump(const Path& path, Sink& sink, PathFilter& filter) { dump(path + "/" + i.second, sink, filter); sink << ")"; } + } } - else if (S_ISLNK(st.st_mode)) + else if (S_ISLNK(st.st_mode)) { sink << "type" << "symlink" << "target" << readLink(path); - else + } else { throw Error(format("file '%1%' has an unsupported type") % path); + } sink << ")"; } @@ -222,8 +228,9 @@ static void parse(ParseSink& sink, Source& source, const Path& path) { type = tpSymlink; } - else + else { throw badArchive("unknown file type " + t); + } } @@ -258,8 +265,9 @@ static void parse(ParseSink& sink, Source& source, const Path& path) { name = readString(source); if (name.empty() || name == "." || name == ".." || name.find('/') != string::npos || - name.find((char)0) != string::npos) + name.find((char)0) != string::npos) { throw Error(format("NAR contains invalid file name '%1%'") % name); + } if (name <= prevName) { throw Error("NAR directory is not sorted"); } @@ -271,16 +279,18 @@ static void parse(ParseSink& sink, Source& source, const Path& path) { << name << "'"; name += caseHackSuffix; name += std::to_string(++i->second); - } else + } else { names[name] = 0; + } } } else if (s == "node") { if (s.empty()) { throw badArchive("entry name missing"); } parse(sink, source, path + "/" + name); - } else + } else { throw badArchive("unknown field " + s); + } } } @@ -289,8 +299,9 @@ static void parse(ParseSink& sink, Source& source, const Path& path) { sink.createSymlink(path, target); } - else + else { throw badArchive("unknown field " + s); + } } } @@ -302,8 +313,9 @@ void parseDump(ParseSink& sink, Source& source) { /* This generally means the integer at the start couldn't be decoded. Ignore and throw the exception below. */ } - if (version != narVersionMagic1) + if (version != narVersionMagic1) { throw badArchive("input doesn't look like a Nix archive"); + } parse(sink, source, ""); } @@ -313,8 +325,9 @@ struct RestoreSink : ParseSink { void createDirectory(const Path& path) { Path p = dstPath + path; - if (mkdir(p.c_str(), 0777) == -1) + if (mkdir(p.c_str(), 0777) == -1) { throw SysError(format("creating directory '%1%'") % p); + } }; void createRegularFile(const Path& path) { @@ -330,8 +343,9 @@ struct RestoreSink : ParseSink { if (fstat(fd.get(), &st) == -1) { throw SysError("fstat"); } - if (fchmod(fd.get(), st.st_mode | (S_IXUSR | S_IXGRP | S_IXOTH)) == -1) + if (fchmod(fd.get(), st.st_mode | (S_IXUSR | S_IXGRP | S_IXOTH)) == -1) { throw SysError("fchmod"); + } } void preallocateContents(unsigned long long len) { @@ -342,8 +356,9 @@ struct RestoreSink : ParseSink { filesystem doesn't support preallocation (e.g. on OpenSolaris). Since preallocation is just an optimisation, ignore it. */ - if (errno && errno != EINVAL && errno != EOPNOTSUPP && errno != ENOSYS) + if (errno && errno != EINVAL && errno != EOPNOTSUPP && errno != ENOSYS) { throw SysError(format("preallocating file of %1% bytes") % len); + } } #endif } diff --git a/third_party/nix/src/libutil/args.cc b/third_party/nix/src/libutil/args.cc index be1d915819..92343d88e5 100644 --- a/third_party/nix/src/libutil/args.cc +++ b/third_party/nix/src/libutil/args.cc @@ -30,13 +30,14 @@ void Args::parseCmdline(const Strings& _cmdline) { *pos = (string) "-" + arg[1]; auto next = pos; ++next; - for (unsigned int j = 2; j < arg.length(); j++) - if (isalpha(arg[j])) + for (unsigned int j = 2; j < arg.length(); j++) { + if (isalpha(arg[j])) { cmdline.insert(next, (string) "-" + arg[j]); - else { + } else { cmdline.insert(next, string(arg, j)); break; } + } arg = *pos; } @@ -44,8 +45,9 @@ void Args::parseCmdline(const Strings& _cmdline) { dashDash = true; ++pos; } else if (!dashDash && std::string(arg, 0, 1) == "-") { - if (!processFlag(pos, cmdline.end())) + if (!processFlag(pos, cmdline.end())) { throw UsageError(format("unrecognised flag '%1%'") % arg); + } } else { pendingArgs.push_back(*pos++); if (processArgs(pendingArgs, false)) { @@ -141,8 +143,9 @@ bool Args::processFlag(Strings::iterator& pos, Strings::iterator end) { bool Args::processArgs(const Strings& args, bool finish) { if (expectedArgs.empty()) { - if (!args.empty()) + if (!args.empty()) { throw UsageError(format("unexpected argument '%1%'") % args.front()); + } return true; } @@ -161,8 +164,9 @@ bool Args::processArgs(const Strings& args, bool finish) { res = true; } - if (finish && !expectedArgs.empty() && !expectedArgs.front().optional) + if (finish && !expectedArgs.empty() && !expectedArgs.front().optional) { throw UsageError("more arguments are required"); + } return res; } @@ -184,7 +188,9 @@ Strings argvToStrings(int argc, char** argv) { Strings args; argc--; argv++; - while (argc--) args.push_back(*argv++); + while (argc--) { + args.push_back(*argv++); + } return args; } diff --git a/third_party/nix/src/libutil/compression.cc b/third_party/nix/src/libutil/compression.cc index 219d9046fa..e13ffcec74 100644 --- a/third_party/nix/src/libutil/compression.cc +++ b/third_party/nix/src/libutil/compression.cc @@ -49,8 +49,9 @@ struct XzDecompressionSink : CompressionSink { XzDecompressionSink(Sink& nextSink) : nextSink(nextSink) { lzma_ret ret = lzma_stream_decoder(&strm, UINT64_MAX, LZMA_CONCATENATED); - if (ret != LZMA_OK) + if (ret != LZMA_OK) { throw CompressionError("unable to initialise lzma decoder"); + } strm.next_out = outbuf; strm.avail_out = sizeof(outbuf); @@ -71,8 +72,9 @@ struct XzDecompressionSink : CompressionSink { checkInterrupt(); lzma_ret ret = lzma_code(&strm, data ? LZMA_RUN : LZMA_FINISH); - if (ret != LZMA_OK && ret != LZMA_STREAM_END) + if (ret != LZMA_OK && ret != LZMA_STREAM_END) { throw CompressionError("error %d while decompressing xz file", ret); + } finished = ret == LZMA_STREAM_END; @@ -93,8 +95,9 @@ struct BzipDecompressionSink : ChunkedCompressionSink { BzipDecompressionSink(Sink& nextSink) : nextSink(nextSink) { memset(&strm, 0, sizeof(strm)); int ret = BZ2_bzDecompressInit(&strm, 0, 0); - if (ret != BZ_OK) + if (ret != BZ_OK) { throw CompressionError("unable to initialise bzip2 decoder"); + } strm.next_out = (char*)outbuf; strm.avail_out = sizeof(outbuf); @@ -117,8 +120,9 @@ struct BzipDecompressionSink : ChunkedCompressionSink { checkInterrupt(); int ret = BZ2_bzDecompress(&strm); - if (ret != BZ_OK && ret != BZ_STREAM_END) + if (ret != BZ_OK && ret != BZ_STREAM_END) { throw CompressionError("error while decompressing bzip2 file"); + } finished = ret == BZ_STREAM_END; @@ -160,8 +164,9 @@ struct BrotliDecompressionSink : ChunkedCompressionSink { checkInterrupt(); if (!BrotliDecoderDecompressStream(state, &avail_in, &next_in, &avail_out, - &next_out, nullptr)) + &next_out, nullptr)) { throw CompressionError("error while decompressing brotli file"); + } if (avail_out < sizeof(outbuf) || avail_in == 0) { nextSink(outbuf, sizeof(outbuf) - avail_out); @@ -184,16 +189,17 @@ ref decompress(const std::string& method, const std::string& in) { ref makeDecompressionSink(const std::string& method, Sink& nextSink) { - if (method == "none" || method == "") + if (method == "none" || method == "") { return make_ref(nextSink); - else if (method == "xz") + } else if (method == "xz") { return make_ref(nextSink); - else if (method == "bzip2") + } else if (method == "bzip2") { return make_ref(nextSink); - else if (method == "br") + } else if (method == "br") { return make_ref(nextSink); - else + } else { throw UnknownCompressionMethod("unknown compression method '%s'", method); + } } struct XzCompressionSink : CompressionSink { @@ -258,8 +264,9 @@ struct XzCompressionSink : CompressionSink { checkInterrupt(); lzma_ret ret = lzma_code(&strm, data ? LZMA_RUN : LZMA_FINISH); - if (ret != LZMA_OK && ret != LZMA_STREAM_END) + if (ret != LZMA_OK && ret != LZMA_STREAM_END) { throw CompressionError("error %d while compressing xz file", ret); + } finished = ret == LZMA_STREAM_END; @@ -280,8 +287,9 @@ struct BzipCompressionSink : ChunkedCompressionSink { BzipCompressionSink(Sink& nextSink) : nextSink(nextSink) { memset(&strm, 0, sizeof(strm)); int ret = BZ2_bzCompressInit(&strm, 9, 0, 30); - if (ret != BZ_OK) + if (ret != BZ_OK) { throw CompressionError("unable to initialise bzip2 encoder"); + } strm.next_out = (char*)outbuf; strm.avail_out = sizeof(outbuf); @@ -304,8 +312,9 @@ struct BzipCompressionSink : ChunkedCompressionSink { checkInterrupt(); int ret = BZ2_bzCompress(&strm, data ? BZ_RUN : BZ_FINISH); - if (ret != BZ_RUN_OK && ret != BZ_FINISH_OK && ret != BZ_STREAM_END) + if (ret != BZ_RUN_OK && ret != BZ_FINISH_OK && ret != BZ_STREAM_END) { throw CompressionError("error %d while compressing bzip2 file", ret); + } finished = ret == BZ_STREAM_END; @@ -349,8 +358,9 @@ struct BrotliCompressionSink : ChunkedCompressionSink { if (!BrotliEncoderCompressStream( state, data ? BROTLI_OPERATION_PROCESS : BROTLI_OPERATION_FINISH, - &avail_in, &next_in, &avail_out, &next_out, nullptr)) + &avail_in, &next_in, &avail_out, &next_out, nullptr)) { throw CompressionError("error while compressing brotli compression"); + } if (avail_out < sizeof(outbuf) || avail_in == 0) { nextSink(outbuf, sizeof(outbuf) - avail_out); @@ -365,17 +375,18 @@ struct BrotliCompressionSink : ChunkedCompressionSink { ref makeCompressionSink(const std::string& method, Sink& nextSink, const bool parallel) { - if (method == "none") + if (method == "none") { return make_ref(nextSink); - else if (method == "xz") + } else if (method == "xz") { return make_ref(nextSink, parallel); - else if (method == "bzip2") + } else if (method == "bzip2") { return make_ref(nextSink); - else if (method == "br") + } else if (method == "br") { return make_ref(nextSink); - else + } else { throw UnknownCompressionMethod(format("unknown compression method '%s'") % method); + } } ref compress(const std::string& method, const std::string& in, diff --git a/third_party/nix/src/libutil/config.cc b/third_party/nix/src/libutil/config.cc index 0b01f6ae8a..9c8c6cf4b2 100644 --- a/third_party/nix/src/libutil/config.cc +++ b/third_party/nix/src/libutil/config.cc @@ -21,8 +21,9 @@ bool Config::set(const std::string& name, const std::string& value) { void Config::addSetting(AbstractSetting* setting) { _settings.emplace(setting->name, Config::SettingData(false, setting)); - for (auto& alias : setting->aliases) + for (auto& alias : setting->aliases) { _settings.emplace(alias, Config::SettingData(true, setting)); + } bool set = false; @@ -68,11 +69,13 @@ void AbstractConfig::reapplyUnknownSettings() { void Config::getSettings(std::map& res, bool overridenOnly) { - for (auto& opt : _settings) + for (auto& opt : _settings) { if (!opt.second.isAlias && - (!overridenOnly || opt.second.setting->overriden)) + (!overridenOnly || opt.second.setting->overriden)) { res.emplace(opt.first, SettingInfo{opt.second.setting->to_string(), opt.second.setting->description}); + } + } } void AbstractConfig::applyConfigFile(const Path& path) { @@ -83,8 +86,9 @@ void AbstractConfig::applyConfigFile(const Path& path) { while (pos < contents.size()) { string line; - while (pos < contents.size() && contents[pos] != '\n') + while (pos < contents.size() && contents[pos] != '\n') { line += contents[pos++]; + } pos++; string::size_type hash = line.find('#'); @@ -97,23 +101,25 @@ void AbstractConfig::applyConfigFile(const Path& path) { continue; } - if (tokens.size() < 2) + if (tokens.size() < 2) { throw UsageError("illegal configuration line '%1%' in '%2%'", line, path); + } auto include = false; auto ignoreMissing = false; - if (tokens[0] == "include") + if (tokens[0] == "include") { include = true; - else if (tokens[0] == "!include") { + } else if (tokens[0] == "!include") { include = true; ignoreMissing = true; } if (include) { - if (tokens.size() != 2) + if (tokens.size() != 2) { throw UsageError("illegal configuration line '%1%' in '%2%'", line, path); + } auto p = absPath(tokens[1], dirOf(path)); if (pathExists(p)) { applyConfigFile(p); @@ -123,9 +129,10 @@ void AbstractConfig::applyConfigFile(const Path& path) { continue; } - if (tokens[1] != "=") + if (tokens[1] != "=") { throw UsageError("illegal configuration line '%1%' in '%2%'", line, path); + } string name = tokens[0]; @@ -146,20 +153,22 @@ void Config::resetOverriden() { } void Config::toJSON(JSONObject& out) { - for (auto& s : _settings) + for (auto& s : _settings) { if (!s.second.isAlias) { JSONObject out2(out.object(s.first)); out2.attr("description", s.second.setting->description); JSONPlaceholder out3(out2.placeholder("value")); s.second.setting->toJSON(out3); } + } } void Config::convertToArgs(Args& args, const std::string& category) { - for (auto& s : _settings) + for (auto& s : _settings) { if (!s.second.isAlias) { s.second.setting->convertToArg(args, category); } + } } AbstractSetting::AbstractSetting(const std::string& name, @@ -202,8 +211,9 @@ std::string BaseSetting::to_string() { template void BaseSetting::set(const std::string& str) { static_assert(std::is_integral::value, "Integer required."); - if (!string2Int(str, value)) + if (!string2Int(str, value)) { throw UsageError("setting '%s' has invalid value '%s'", name, str); + } } template @@ -214,12 +224,13 @@ std::string BaseSetting::to_string() { template <> void BaseSetting::set(const std::string& str) { - if (str == "true" || str == "yes" || str == "1") + if (str == "true" || str == "yes" || str == "1") { value = true; - else if (str == "false" || str == "no" || str == "0") + } else if (str == "false" || str == "no" || str == "0") { value = false; - else + } else { throw UsageError("Boolean setting '%s' has invalid value '%s'", name, str); + } } template <> @@ -290,19 +301,22 @@ template class BaseSetting; void PathSetting::set(const std::string& str) { if (str == "") { - if (allowEmpty) + if (allowEmpty) { value = ""; - else + } else { throw UsageError("setting '%s' cannot be empty", name); - } else + } + } else { value = canonPath(str); + } } bool GlobalConfig::set(const std::string& name, const std::string& value) { - for (auto& config : *configRegistrations) + for (auto& config : *configRegistrations) { if (config->set(name, value)) { return true; } + } unknownSettings.emplace(name, value); @@ -311,8 +325,9 @@ bool GlobalConfig::set(const std::string& name, const std::string& value) { void GlobalConfig::getSettings(std::map& res, bool overridenOnly) { - for (auto& config : *configRegistrations) + for (auto& config : *configRegistrations) { config->getSettings(res, overridenOnly); + } } void GlobalConfig::resetOverriden() { @@ -328,8 +343,9 @@ void GlobalConfig::toJSON(JSONObject& out) { } void GlobalConfig::convertToArgs(Args& args, const std::string& category) { - for (auto& config : *configRegistrations) + for (auto& config : *configRegistrations) { config->convertToArgs(args, category); + } } GlobalConfig globalConfig; diff --git a/third_party/nix/src/libutil/hash.cc b/third_party/nix/src/libutil/hash.cc index 0a0869dd4e..e33c76cc90 100644 --- a/third_party/nix/src/libutil/hash.cc +++ b/third_party/nix/src/libutil/hash.cc @@ -132,8 +132,9 @@ Hash::Hash(const std::string& s, HashType type) : type(type) { sep = s.find('-'); if (sep != string::npos) { isSRI = true; - } else if (type == htUnknown) + } else if (type == htUnknown) { throw BadHash("hash '%s' does not include a type", s); + } } if (sep != string::npos) { @@ -142,8 +143,9 @@ Hash::Hash(const std::string& s, HashType type) : type(type) { if (this->type == htUnknown) { throw BadHash("unknown hash type '%s'", hts); } - if (type != htUnknown && type != this->type) + if (type != htUnknown && type != this->type) { throw BadHash("hash '%s' should have type '%s'", s, printHashType(type)); + } pos = sep + 1; } @@ -175,10 +177,11 @@ Hash::Hash(const std::string& s, HashType type) : type(type) { for (unsigned int n = 0; n < size; ++n) { char c = s[pos + size - n - 1]; unsigned char digit; - for (digit = 0; digit < base32Chars.size(); ++digit) /* !!! slow */ + for (digit = 0; digit < base32Chars.size(); ++digit) { /* !!! slow */ if (base32Chars[digit] == c) { break; } + } if (digit >= 32) { throw BadHash("invalid base-32 hash '%s'", s); } @@ -199,15 +202,17 @@ Hash::Hash(const std::string& s, HashType type) : type(type) { else if (isSRI || size == base64Len()) { auto d = base64Decode(std::string(s, pos)); - if (d.size() != hashSize) + if (d.size() != hashSize) { throw BadHash("invalid %s hash '%s'", isSRI ? "SRI" : "base-64", s); + } assert(hashSize); memcpy(hash, d.data(), hashSize); } - else + else { throw BadHash("hash '%s' has wrong length for hash type '%s'", s, printHashType(type)); + } } union Ctx { @@ -218,37 +223,40 @@ union Ctx { }; static void start(HashType ht, Ctx& ctx) { - if (ht == htMD5) + if (ht == htMD5) { MD5_Init(&ctx.md5); - else if (ht == htSHA1) + } else if (ht == htSHA1) { SHA1_Init(&ctx.sha1); - else if (ht == htSHA256) + } else if (ht == htSHA256) { SHA256_Init(&ctx.sha256); - else if (ht == htSHA512) + } else if (ht == htSHA512) { SHA512_Init(&ctx.sha512); + } } static void update(HashType ht, Ctx& ctx, const unsigned char* bytes, size_t len) { - if (ht == htMD5) + if (ht == htMD5) { MD5_Update(&ctx.md5, bytes, len); - else if (ht == htSHA1) + } else if (ht == htSHA1) { SHA1_Update(&ctx.sha1, bytes, len); - else if (ht == htSHA256) + } else if (ht == htSHA256) { SHA256_Update(&ctx.sha256, bytes, len); - else if (ht == htSHA512) + } else if (ht == htSHA512) { SHA512_Update(&ctx.sha512, bytes, len); + } } static void finish(HashType ht, Ctx& ctx, unsigned char* hash) { - if (ht == htMD5) + if (ht == htMD5) { MD5_Final(hash, &ctx.md5); - else if (ht == htSHA1) + } else if (ht == htSHA1) { SHA1_Final(hash, &ctx.sha1); - else if (ht == htSHA256) + } else if (ht == htSHA256) { SHA256_Final(hash, &ctx.sha256); - else if (ht == htSHA512) + } else if (ht == htSHA512) { SHA512_Final(hash, &ctx.sha512); + } } Hash hashString(HashType ht, const string& s) { @@ -331,29 +339,31 @@ Hash compressHash(const Hash& hash, unsigned int newSize) { } HashType parseHashType(const string& s) { - if (s == "md5") + if (s == "md5") { return htMD5; - else if (s == "sha1") + } else if (s == "sha1") { return htSHA1; - else if (s == "sha256") + } else if (s == "sha256") { return htSHA256; - else if (s == "sha512") + } else if (s == "sha512") { return htSHA512; - else + } else { return htUnknown; + } } string printHashType(HashType ht) { - if (ht == htMD5) + if (ht == htMD5) { return "md5"; - else if (ht == htSHA1) + } else if (ht == htSHA1) { return "sha1"; - else if (ht == htSHA256) + } else if (ht == htSHA256) { return "sha256"; - else if (ht == htSHA512) + } else if (ht == htSHA512) { return "sha512"; - else + } else { abort(); + } } } // namespace nix diff --git a/third_party/nix/src/libutil/json.cc b/third_party/nix/src/libutil/json.cc index 7965f4725b..c5f52ae8ef 100644 --- a/third_party/nix/src/libutil/json.cc +++ b/third_party/nix/src/libutil/json.cc @@ -7,28 +7,31 @@ namespace nix { void toJSON(std::ostream& str, const char* start, const char* end) { str << '"'; - for (auto i = start; i != end; i++) - if (*i == '\"' || *i == '\\') + for (auto i = start; i != end; i++) { + if (*i == '\"' || *i == '\\') { str << '\\' << *i; - else if (*i == '\n') + } else if (*i == '\n') { str << "\\n"; - else if (*i == '\r') + } else if (*i == '\r') { str << "\\r"; - else if (*i == '\t') + } else if (*i == '\t') { str << "\\t"; - else if (*i >= 0 && *i < 32) + } else if (*i >= 0 && *i < 32) { str << "\\u" << std::setfill('0') << std::setw(4) << std::hex << (uint16_t)*i << std::dec; - else + } else { str << *i; + } + } str << '"'; } void toJSON(std::ostream& str, const char* s) { - if (!s) + if (!s) { str << "null"; - else + } else { toJSON(str, s, s + strlen(s)); + } } template <> diff --git a/third_party/nix/src/libutil/serialise.cc b/third_party/nix/src/libutil/serialise.cc index 760d19ed4c..b51ed2105b 100644 --- a/third_party/nix/src/libutil/serialise.cc +++ b/third_party/nix/src/libutil/serialise.cc @@ -173,7 +173,7 @@ std::unique_ptr sinkToSource(std::function fun, size_t pos = 0; size_t read(unsigned char* data, size_t len) override { - if (!coro) + if (!coro) { coro = coro_t::pull_type([&](coro_t::push_type& yield) { LambdaSink sink([&](const unsigned char* data, size_t len) { if (len) { @@ -182,6 +182,7 @@ std::unique_ptr sinkToSource(std::function fun, }); fun(sink); }); + } if (!*coro) { eof(); @@ -189,7 +190,9 @@ std::unique_ptr sinkToSource(std::function fun, } if (pos == cur.size()) { - if (!cur.empty()) (*coro)(); + if (!cur.empty()) { + (*coro)(); + } cur = coro->get(); pos = 0; } @@ -247,10 +250,11 @@ void readPadding(size_t len, Source& source) { unsigned char zero[8]; size_t n = 8 - (len % 8); source(zero, n); - for (unsigned int i = 0; i < n; i++) + for (unsigned int i = 0; i < n; i++) { if (zero[i]) { throw SerialisationError("non-zero padding"); } + } } } @@ -284,7 +288,9 @@ template T readStrings(Source& source) { auto count = readNum(source); T ss; - while (count--) ss.insert(ss.end(), readString(source)); + while (count--) { + ss.insert(ss.end(), readString(source)); + } return ss; } diff --git a/third_party/nix/src/libutil/thread-pool.cc b/third_party/nix/src/libutil/thread-pool.cc index a16f4c2b60..d0042c6df1 100644 --- a/third_party/nix/src/libutil/thread-pool.cc +++ b/third_party/nix/src/libutil/thread-pool.cc @@ -50,8 +50,9 @@ void ThreadPool::enqueue(const work_t& t) { state->pending.push(t); /* Note: process() also executes items, so count it as a worker. */ if (state->pending.size() > state->workers.size() + 1 && - state->workers.size() + 1 < maxThreads) + state->workers.size() + 1 < maxThreads) { state->workers.emplace_back(&ThreadPool::doWork, this, false); + } work.notify_one(); } @@ -111,8 +112,9 @@ void ThreadPool::doWork(bool mainThread) { std::rethrow_exception(exc); } catch (std::exception& e) { if (!dynamic_cast(&e) && - !dynamic_cast(&e)) + !dynamic_cast(&e)) { ignoreException(); + } } catch (...) { } } diff --git a/third_party/nix/src/libutil/util.cc b/third_party/nix/src/libutil/util.cc index 3cc8563a86..213a9a0d6a 100644 --- a/third_party/nix/src/libutil/util.cc +++ b/third_party/nix/src/libutil/util.cc @@ -60,9 +60,10 @@ std::map getEnv() { for (size_t i = 0; environ[i]; ++i) { auto s = environ[i]; auto eq = strchr(s, '='); - if (!eq) + if (!eq) { // invalid env, just keep going continue; + } env.emplace(std::string(s, eq), std::string(eq + 1)); } return env; @@ -91,18 +92,19 @@ Path absPath(Path path, Path dir) { if (buf == NULL) #else char buf[PATH_MAX]; - if (!getcwd(buf, sizeof(buf))) + if (!getcwd(buf, sizeof(buf))) { #endif throw SysError("cannot get cwd"); - dir = buf; + } + dir = buf; #ifdef __GNU__ - free(buf); + free(buf); #endif - } - path = dir + "/" + path; } - return canonPath(path); + path = dir + "/" + path; } +return canonPath(path); +} // namespace nix Path canonPath(const Path& path, bool resolveSymlinks) { assert(path != ""); @@ -122,7 +124,9 @@ Path canonPath(const Path& path, bool resolveSymlinks) { while (1) { /* Skip slashes. */ - while (i != end && *i == '/') i++; + while (i != end && *i == '/') { + i++; + } if (i == end) { break; } @@ -144,14 +148,17 @@ Path canonPath(const Path& path, bool resolveSymlinks) { /* Normal component; copy it. */ else { s += '/'; - while (i != end && *i != '/') s += *i++; + while (i != end && *i != '/') { + s += *i++; + } /* If s points to a symlink, resolve it and restart (since the symlink target might contain new symlinks). */ if (resolveSymlinks && isLink(s)) { - if (++followCount >= maxFollow) + if (++followCount >= maxFollow) { throw Error(format("infinite symlink recursion in path '%1%'") % path); + } temp = absPath(readLink(s), dirOf(s)) + string(i, end); i = temp.begin(); /* restart */ end = temp.end(); @@ -182,10 +189,11 @@ string baseNameOf(const Path& path) { } Path::size_type pos = path.rfind('/', last); - if (pos == string::npos) + if (pos == string::npos) { pos = 0; - else + } else { pos += 1; + } return string(path, pos, last - pos + 1); } @@ -201,8 +209,9 @@ bool isDirOrInDir(const Path& path, const Path& dir) { struct stat lstat(const Path& path) { struct stat st; - if (lstat(path.c_str(), &st)) + if (lstat(path.c_str(), &st)) { throw SysError(format("getting status of '%1%'") % path); + } return st; } @@ -213,8 +222,9 @@ bool pathExists(const Path& path) { if (!res) { return true; } - if (errno != ENOENT && errno != ENOTDIR) + if (errno != ENOENT && errno != ENOTDIR) { throw SysError(format("getting status of %1%") % path); + } return false; } @@ -224,13 +234,15 @@ Path readLink(const Path& path) { for (ssize_t bufSize = PATH_MAX / 4; true; bufSize += bufSize / 2) { buf.resize(bufSize); ssize_t rlSize = readlink(path.c_str(), buf.data(), bufSize); - if (rlSize == -1) - if (errno == EINVAL) + if (rlSize == -1) { + if (errno == EINVAL) { throw Error("'%1%' is not a symlink", path); - else + } else { throw SysError("reading symbolic link '%1%'", path); - else if (rlSize < bufSize) + } + } else if (rlSize < bufSize) { return string(buf.data(), rlSize); + } } } @@ -351,9 +363,9 @@ string readLine(int fd) { if (errno != EINTR) { throw SysError("reading a line"); } - } else if (rd == 0) + } else if (rd == 0) { throw EndOfFile("unexpected EOF reading a line"); - else { + } else { if (ch == '\n') { return s; } @@ -386,12 +398,14 @@ static void _deletePath(const Path& path, unsigned long long& bytesFreed) { /* Make the directory accessible. */ const auto PERM_MASK = S_IRUSR | S_IWUSR | S_IXUSR; if ((st.st_mode & PERM_MASK) != PERM_MASK) { - if (chmod(path.c_str(), st.st_mode | PERM_MASK) == -1) + if (chmod(path.c_str(), st.st_mode | PERM_MASK) == -1) { throw SysError(format("chmod '%1%'") % path); + } } - for (auto& i : readDirectory(path)) + for (auto& i : readDirectory(path)) { _deletePath(path + "/" + i.name, bytesFreed); + } } if (remove(path.c_str()) == -1) { @@ -418,11 +432,12 @@ static Path tempName(Path tmpRoot, const Path& prefix, bool includePid, int& counter) { tmpRoot = canonPath(tmpRoot.empty() ? getEnv("TMPDIR", "/tmp") : tmpRoot, true); - if (includePid) + if (includePid) { return (format("%1%/%2%-%3%-%4%") % tmpRoot % prefix % getpid() % counter++) .str(); - else + } else { return (format("%1%/%2%-%3%") % tmpRoot % prefix % counter++).str(); + } } Path createTempDir(const Path& tmpRoot, const Path& prefix, bool includePid, @@ -449,8 +464,9 @@ Path createTempDir(const Path& tmpRoot, const Path& prefix, bool includePid, #endif return tmpDir; } - if (errno != EEXIST) + if (errno != EEXIST) { throw SysError(format("creating directory '%1%'") % tmpDir); + } } } @@ -470,8 +486,9 @@ static Lazy getHome2([]() { struct passwd pwbuf; struct passwd* pw; if (getpwuid_r(geteuid(), &pwbuf, buf.data(), buf.size(), &pw) != 0 || - !pw || !pw->pw_dir || !pw->pw_dir[0]) + !pw || !pw->pw_dir || !pw->pw_dir[0]) { throw Error("cannot determine user's home directory"); + } homeDir = pw->pw_dir; } return homeDir; @@ -521,25 +538,29 @@ Paths createDirs(const Path& path) { struct stat st; if (lstat(path.c_str(), &st) == -1) { created = createDirs(dirOf(path)); - if (mkdir(path.c_str(), 0777) == -1 && errno != EEXIST) + if (mkdir(path.c_str(), 0777) == -1 && errno != EEXIST) { throw SysError(format("creating directory '%1%'") % path); + } st = lstat(path); created.push_back(path); } - if (S_ISLNK(st.st_mode) && stat(path.c_str(), &st) == -1) + if (S_ISLNK(st.st_mode) && stat(path.c_str(), &st) == -1) { throw SysError(format("statting symlink '%1%'") % path); + } - if (!S_ISDIR(st.st_mode)) + if (!S_ISDIR(st.st_mode)) { throw Error(format("'%1%' is not a directory") % path); + } return created; } void createSymlink(const Path& target, const Path& link) { - if (symlink(target.c_str(), link.c_str())) + if (symlink(target.c_str(), link.c_str())) { throw SysError(format("creating symlink from '%1%' to '%2%'") % link % target); + } } void replaceSymlink(const Path& target, const Path& link) { @@ -555,8 +576,9 @@ void replaceSymlink(const Path& target, const Path& link) { throw; } - if (rename(tmp.c_str(), link.c_str()) != 0) + if (rename(tmp.c_str(), link.c_str()) != 0) { throw SysError(format("renaming '%1%' to '%2%'") % tmp % link); + } break; } @@ -612,15 +634,17 @@ void drainFD(int fd, Sink& sink, bool block) { Finally finally([&]() { if (!block) { - if (fcntl(fd, F_SETFL, saved) == -1) + if (fcntl(fd, F_SETFL, saved) == -1) { throw SysError("making file descriptor blocking"); + } } }); if (!block) { saved = fcntl(fd, F_GETFL); - if (fcntl(fd, F_SETFL, saved | O_NONBLOCK) == -1) + if (fcntl(fd, F_SETFL, saved | O_NONBLOCK) == -1) { throw SysError("making file descriptor non-blocking"); + } } std::vector buf(64 * 1024); @@ -634,10 +658,11 @@ void drainFD(int fd, Sink& sink, bool block) { if (errno != EINTR) { throw SysError("reading from file"); } - } else if (rd == 0) + } else if (rd == 0) { break; - else + } else { sink(buf.data(), rd); + } } } @@ -656,8 +681,9 @@ AutoDelete::~AutoDelete() { if (recursive) { deletePath(path); } else { - if (remove(path.c_str()) == -1) + if (remove(path.c_str()) == -1) { throw SysError(format("cannot unlink '%1%'") % path); + } } } } catch (...) { @@ -700,8 +726,9 @@ int AutoCloseFD::get() const { return fd; } void AutoCloseFD::close() { if (fd != -1) { - if (::close(fd) == -1) /* This should never happen. */ + if (::close(fd) == -1) { /* This should never happen. */ throw SysError(format("closing file descriptor %1%") % fd); + } } } @@ -835,8 +862,9 @@ void killUser(uid_t uid) { if (errno == ESRCH) { break; } /* no more processes */ - if (errno != EINTR) + if (errno != EINTR) { throw SysError(format("cannot kill processes for uid '%1%'") % uid); + } } _exit(0); @@ -844,9 +872,10 @@ void killUser(uid_t uid) { options); int status = pid.wait(); - if (status != 0) + if (status != 0) { throw Error(format("cannot kill processes for uid '%1%': %2%") % uid % statusToString(status)); + } /* !!! We should really do some check to make sure that there are no processes left running under `uid', but there is no portable @@ -877,8 +906,9 @@ pid_t startProcess(std::function fun, const ProcessOptions& options) { auto wrapper = [&]() { try { #if __linux__ - if (options.dieWithParent && prctl(PR_SET_PDEATHSIG, SIGKILL) == -1) + if (options.dieWithParent && prctl(PR_SET_PDEATHSIG, SIGKILL) == -1) { throw SysError("setting death signal"); + } #endif restoreAffinity(); fun(); @@ -889,10 +919,11 @@ pid_t startProcess(std::function fun, const ProcessOptions& options) { } } catch (...) { } - if (options.runExitHandlers) + if (options.runExitHandlers) { exit(1); - else + } else { _exit(1); + } }; pid_t pid = doFork(options.allowVfork, wrapper); @@ -920,9 +951,10 @@ string runProgram(Path program, bool searchPath, const Strings& args, auto res = runProgram(opts); - if (!statusOk(res.first)) + if (!statusOk(res.first)) { throw ExecError(res.first, fmt("program '%1%' %2%", program, statusToString(res.first))); + } return res.second; } @@ -980,33 +1012,42 @@ void runProgram2(const RunOptions& options) { replaceEnv(*options.environment); } if (options.standardOut && - dup2(out.writeSide.get(), STDOUT_FILENO) == -1) + dup2(out.writeSide.get(), STDOUT_FILENO) == -1) { throw SysError("dupping stdout"); - if (options.mergeStderrToStdout) - if (dup2(STDOUT_FILENO, STDERR_FILENO) == -1) + } + if (options.mergeStderrToStdout) { + if (dup2(STDOUT_FILENO, STDERR_FILENO) == -1) { throw SysError("cannot dup stdout into stderr"); - if (source && dup2(in.readSide.get(), STDIN_FILENO) == -1) + } + } + if (source && dup2(in.readSide.get(), STDIN_FILENO) == -1) { throw SysError("dupping stdin"); + } - if (options.chdir && chdir((*options.chdir).c_str()) == -1) + if (options.chdir && chdir((*options.chdir).c_str()) == -1) { throw SysError("chdir failed"); - if (options.gid && setgid(*options.gid) == -1) + } + if (options.gid && setgid(*options.gid) == -1) { throw SysError("setgid failed"); + } /* Drop all other groups if we're setgid. */ - if (options.gid && setgroups(0, 0) == -1) + if (options.gid && setgroups(0, 0) == -1) { throw SysError("setgroups failed"); - if (options.uid && setuid(*options.uid) == -1) + } + if (options.uid && setuid(*options.uid) == -1) { throw SysError("setuid failed"); + } Strings args_(options.args); args_.push_front(options.program); restoreSignals(); - if (options.searchPath) + if (options.searchPath) { execvp(options.program.c_str(), stringsToCharPtrs(args_).data()); - else + } else { execv(options.program.c_str(), stringsToCharPtrs(args_).data()); + } throw SysError("executing '%1%'", options.program); }, @@ -1058,9 +1099,10 @@ void runProgram2(const RunOptions& options) { promise.get_future().get(); } - if (status) + if (status) { throw ExecError(status, fmt("program '%1%' %2%", options.program, statusToString(status))); + } } void closeMostFDs(const set& exceptions) { @@ -1080,17 +1122,19 @@ void closeMostFDs(const set& exceptions) { int maxFD = 0; maxFD = sysconf(_SC_OPEN_MAX); - for (int fd = 0; fd < maxFD; ++fd) + for (int fd = 0; fd < maxFD; ++fd) { if (!exceptions.count(fd)) { close(fd); } /* ignore result */ + } } void closeOnExec(int fd) { int prev; if ((prev = fcntl(fd, F_GETFD, 0)) == -1 || - fcntl(fd, F_SETFD, prev | FD_CLOEXEC) == -1) + fcntl(fd, F_SETFD, prev | FD_CLOEXEC) == -1) { throw SysError("setting close-on-exec flag"); + } } ////////////////////////////////////////////////////////////////////// @@ -1187,9 +1231,9 @@ string replaceStrings(const std::string& s, const std::string& from, string statusToString(int status) { if (!WIFEXITED(status) || WEXITSTATUS(status) != 0) { - if (WIFEXITED(status)) + if (WIFEXITED(status)) { return (format("failed with exit code %1%") % WEXITSTATUS(status)).str(); - else if (WIFSIGNALED(status)) { + } else if (WIFSIGNALED(status)) { int sig = WTERMSIG(status); #if HAVE_STRSIGNAL const char* description = strsignal(sig); @@ -1198,10 +1242,12 @@ string statusToString(int status) { #else return (format("failed due to signal %1%") % sig).str(); #endif - } else + } else { return "died abnormally"; - } else + } + } else { return "succeeded"; + } } bool statusOk(int status) { @@ -1227,11 +1273,13 @@ std::string toLower(const std::string& s) { std::string shellEscape(const std::string& s) { std::string r = "'"; - for (auto& i : s) - if (i == '\'') + for (auto& i : s) { + if (i == '\'') { r += "'\\''"; - else + } else { r += i; + } + } r += '\''; return r; } @@ -1259,9 +1307,13 @@ std::string filterANSIEscapes(const std::string& s, bool filterAll, if (i != s.end() && *i == '[') { e += *i++; // eat parameter bytes - while (i != s.end() && *i >= 0x30 && *i <= 0x3f) e += *i++; + while (i != s.end() && *i >= 0x30 && *i <= 0x3f) { + e += *i++; + } // eat intermediate bytes - while (i != s.end() && *i >= 0x20 && *i <= 0x2f) e += *i++; + while (i != s.end() && *i >= 0x20 && *i <= 0x2f) { + e += *i++; + } // eat final byte if (i != s.end() && *i >= 0x40 && *i <= 0x7e) { e += last = *i++; @@ -1287,11 +1339,11 @@ std::string filterANSIEscapes(const std::string& s, bool filterAll, } } - else if (*i == '\r') + else if (*i == '\r') { // do nothing for now i++; - else { + } else { t += *i++; w++; } @@ -1319,7 +1371,9 @@ string base64Encode(const string& s) { if (nbits) { res.push_back(base64Chars[data << (6 - nbits) & 0x3f]); } - while (res.size() % 4) res.push_back('='); + while (res.size() % 4) { + res.push_back('='); + } return res; } @@ -1395,10 +1449,10 @@ static void signalHandlerThread(sigset_t set) { int signal = 0; sigwait(&set, &signal); - if (signal == SIGINT || signal == SIGTERM || signal == SIGHUP) + if (signal == SIGINT || signal == SIGTERM || signal == SIGHUP) { triggerInterrupt(); - else if (signal == SIGWINCH) { + } else if (signal == SIGWINCH) { updateWindowSize(); } } @@ -1424,8 +1478,9 @@ static sigset_t savedSignalMask; void startSignalHandlerThread() { updateWindowSize(); - if (sigprocmask(SIG_BLOCK, nullptr, &savedSignalMask)) + if (sigprocmask(SIG_BLOCK, nullptr, &savedSignalMask)) { throw SysError("quering signal mask"); + } sigset_t set; sigemptyset(&set); @@ -1434,15 +1489,17 @@ void startSignalHandlerThread() { sigaddset(&set, SIGHUP); sigaddset(&set, SIGPIPE); sigaddset(&set, SIGWINCH); - if (pthread_sigmask(SIG_BLOCK, &set, nullptr)) + if (pthread_sigmask(SIG_BLOCK, &set, nullptr)) { throw SysError("blocking signals"); + } std::thread(signalHandlerThread, set).detach(); } void restoreSignals() { - if (sigprocmask(SIG_SETMASK, &savedSignalMask, nullptr)) + if (sigprocmask(SIG_SETMASK, &savedSignalMask, nullptr)) { throw SysError("restoring signals"); + } } /* RAII helper to automatically deregister a callback. */ diff --git a/third_party/nix/src/libutil/xml-writer.cc b/third_party/nix/src/libutil/xml-writer.cc index e07dd92f02..ed41286cc1 100644 --- a/third_party/nix/src/libutil/xml-writer.cc +++ b/third_party/nix/src/libutil/xml-writer.cc @@ -16,7 +16,9 @@ void XMLWriter::close() { if (closed) { return; } - while (!pendingElems.empty()) closeElement(); + while (!pendingElems.empty()) { + closeElement(); + } closed = true; } @@ -68,20 +70,21 @@ void XMLWriter::writeAttrs(const XMLAttrs& attrs) { output << " " << i.first << "=\""; for (size_t j = 0; j < i.second.size(); ++j) { char c = i.second[j]; - if (c == '"') + if (c == '"') { output << """; - else if (c == '<') + } else if (c == '<') { output << "<"; - else if (c == '>') + } else if (c == '>') { output << ">"; - else if (c == '&') + } else if (c == '&') { output << "&"; - /* Escape newlines to prevent attribute normalisation (see - XML spec, section 3.3.3. */ - else if (c == '\n') + /* Escape newlines to prevent attribute normalisation (see + XML spec, section 3.3.3. */ + } else if (c == '\n') { output << " "; - else + } else { output << c; + } } output << "\""; } diff --git a/third_party/nix/src/nix-build/nix-build.cc b/third_party/nix/src/nix-build/nix-build.cc index b5368a65db..bf20d50dbb 100644 --- a/third_party/nix/src/nix-build/nix-build.cc +++ b/third_party/nix/src/nix-build/nix-build.cc @@ -125,9 +125,11 @@ static void _main(int argc, char** argv) { line = chomp(line); std::smatch match; if (std::regex_match(line, match, - std::regex("^#!\\s*nix-shell (.*)$"))) - for (const auto& word : shellwords(match[1].str())) + std::regex("^#!\\s*nix-shell (.*)$"))) { + for (const auto& word : shellwords(match[1].str())) { args.push_back(word); + } + } } } } catch (SysError&) { @@ -145,63 +147,63 @@ static void _main(int argc, char** argv) { showManPage(myName); } - else if (*arg == "--version") + else if (*arg == "--version") { printVersion(myName); - else if (*arg == "--add-drv-link" || *arg == "--indirect") + } else if (*arg == "--add-drv-link" || *arg == "--indirect") { ; // obsolete - else if (*arg == "--no-out-link" || *arg == "--no-link") + } else if (*arg == "--no-out-link" || *arg == "--no-link") { outLink = (Path)tmpDir + "/result"; - else if (*arg == "--attr" || *arg == "-A") + } else if (*arg == "--attr" || *arg == "-A") { attrPaths.push_back(getArg(*arg, arg, end)); - else if (*arg == "--drv-link") + } else if (*arg == "--drv-link") { getArg(*arg, arg, end); // obsolete - else if (*arg == "--out-link" || *arg == "-o") + } else if (*arg == "--out-link" || *arg == "-o") { outLink = getArg(*arg, arg, end); - else if (*arg == "--add-root") + } else if (*arg == "--add-root") { gcRoot = getArg(*arg, arg, end); - else if (*arg == "--dry-run") + } else if (*arg == "--dry-run") { dryRun = true; - else if (*arg == "--repair") { + } else if (*arg == "--repair") { repair = Repair; buildMode = bmRepair; } - else if (*arg == "--run-env") // obsolete + else if (*arg == "--run-env") { // obsolete runEnv = true; - else if (*arg == "--command" || *arg == "--run") { + } else if (*arg == "--command" || *arg == "--run") { if (*arg == "--run") { interactive = false; } envCommand = getArg(*arg, arg, end) + "\nexit"; } - else if (*arg == "--check") + else if (*arg == "--check") { buildMode = bmCheck; - else if (*arg == "--exclude") + } else if (*arg == "--exclude") { envExclude.push_back(getArg(*arg, arg, end)); - else if (*arg == "--expr" || *arg == "-E") + } else if (*arg == "--expr" || *arg == "-E") { fromArgs = true; - else if (*arg == "--pure") + } else if (*arg == "--pure") { pure = true; - else if (*arg == "--impure") + } else if (*arg == "--impure") { pure = false; - else if (*arg == "--packages" || *arg == "-p") + } else if (*arg == "--packages" || *arg == "-p") { packages = true; - else if (inShebang && *arg == "-i") { + } else if (inShebang && *arg == "-i") { auto interpreter = getArg(*arg, arg, end); interactive = false; auto execArgs = ""; @@ -210,8 +212,9 @@ static void _main(int argc, char** argv) { // executes it unless it contains the string "perl" or "indir", // or (undocumented) argv[0] does not contain "perl". Exploit // the latter by doing "exec -a". - if (std::regex_search(interpreter, std::regex("perl"))) + if (std::regex_search(interpreter, std::regex("perl"))) { execArgs = "-a PERL"; + } std::ostringstream joined; for (const auto& i : savedArgs) { @@ -233,17 +236,18 @@ static void _main(int argc, char** argv) { } } - else if (*arg == "--keep") + else if (*arg == "--keep") { keepVars.insert(getArg(*arg, arg, end)); - else if (*arg == "-") + } else if (*arg == "-") { readStdin = true; - else if (*arg != "" && arg->at(0) == '-') + } else if (*arg != "" && arg->at(0) == '-') { return false; - else + } else { left.push_back(*arg); + } return true; }); @@ -252,8 +256,9 @@ static void _main(int argc, char** argv) { initPlugins(); - if (packages && fromArgs) + if (packages && fromArgs) { throw UsageError("'-p' and '-E' are mutually exclusive"); + } auto store = openStore(); @@ -290,22 +295,22 @@ static void _main(int argc, char** argv) { /* Parse the expressions. */ std::vector exprs; - if (readStdin) + if (readStdin) { exprs = {state->parseStdin()}; - else + } else { for (auto i : left) { - if (fromArgs) + if (fromArgs) { exprs.push_back(state->parseExprFromString(i, absPath("."))); - else { + } else { auto absolute = i; try { absolute = canonPath(absPath(i), true); } catch (Error& e) { }; if (store->isStorePath(absolute) && - std::regex_match(absolute, std::regex(".*\\.drv(!.*)?"))) + std::regex_match(absolute, std::regex(".*\\.drv(!.*)?"))) { drvs.push_back(DrvInfo(*state, store, absolute)); - else + } else { /* If we're in a #! script, interpret filenames relative to the script. */ exprs.push_back( @@ -313,8 +318,10 @@ static void _main(int argc, char** argv) { lookupFileArg(*state, inShebang && !packages ? absPath(i, absPath(dirOf(script))) : i))))); + } } } + } /* Evaluate them into derivations. */ if (attrPaths.empty()) { @@ -342,9 +349,10 @@ static void _main(int argc, char** argv) { store->queryMissing(paths, willBuild, willSubstitute, unknown, downloadSize, narSize); - if (settings.printMissing) + if (settings.printMissing) { printMissing(ref(store), willBuild, willSubstitute, unknown, downloadSize, narSize); + } if (!dryRun) { store->buildPaths(paths, buildMode); @@ -352,8 +360,9 @@ static void _main(int argc, char** argv) { }; if (runEnv) { - if (drvs.size() != 1) + if (drvs.size() != 1) { throw UsageError("nix-shell requires a single derivation"); + } auto& drvInfo = drvs.front(); auto drv = store->derivationFromPath(drvInfo.queryDrvPath()); @@ -374,10 +383,11 @@ static void _main(int argc, char** argv) { state->eval(expr, v); auto drv = getDerivation(*state, v, false); - if (!drv) + if (!drv) { throw Error( "the 'bashInteractive' attribute in did not evaluate " "to a derivation"); + } pathsToBuild.insert(drv->queryDrvPath()); @@ -390,13 +400,15 @@ static void _main(int argc, char** argv) { } // Build or fetch all dependencies of the derivation. - for (const auto& input : drv.inputDrvs) + for (const auto& input : drv.inputDrvs) { if (std::all_of(envExclude.cbegin(), envExclude.cend(), [&](const string& exclude) { return !std::regex_search(input.first, std::regex(exclude)); - })) + })) { pathsToBuild.insert(makeDrvPathWithOutputs(input.first, input.second)); + } + } for (const auto& src : drv.inputSrcs) { pathsToBuild.insert(src); } @@ -414,10 +426,11 @@ static void _main(int argc, char** argv) { if (pure) { decltype(env) newEnv; - for (auto& i : env) + for (auto& i : env) { if (keepVars.count(i.first)) { newEnv.emplace(i); } + } env = newEnv; // NixOS hack: prevent /etc/bashrc from sourcing /etc/profile. env["__ETC_PROFILE_SOURCED"] = "1"; @@ -433,15 +446,17 @@ static void _main(int argc, char** argv) { bool keepTmp = false; int fileNr = 0; - for (auto& var : drv.env) + for (auto& var : drv.env) { if (passAsFile.count(var.first)) { keepTmp = true; string fn = ".attr-" + std::to_string(fileNr++); Path p = (Path)tmpDir + "/" + fn; writeFile(p, var.second); env[var.first + "Path"] = p; - } else + } else { env[var.first] = var.second; + } + } restoreAffinity(); @@ -507,16 +522,17 @@ static void _main(int argc, char** argv) { auto outPath = drvInfo.queryOutPath(); auto outputName = drvInfo.queryOutputName(); - if (outputName == "") + if (outputName == "") { throw Error("derivation '%s' lacks an 'outputName' attribute", drvPath); + } pathsToBuild.insert(drvPath + "!" + outputName); std::string drvPrefix; auto i = drvPrefixes.find(drvPath); - if (i != drvPrefixes.end()) + if (i != drvPrefixes.end()) { drvPrefix = i->second; - else { + } else { drvPrefix = outLink; if (drvPrefixes.size()) { drvPrefix += fmt("-%d", drvPrefixes.size() + 1); @@ -539,9 +555,11 @@ static void _main(int argc, char** argv) { return; } - for (auto& symlink : resultSymlinks) - if (auto store2 = store.dynamic_pointer_cast()) + for (auto& symlink : resultSymlinks) { + if (auto store2 = store.dynamic_pointer_cast()) { store2->addPermRoot(symlink.second, absPath(symlink.first), true); + } + } for (auto& path : outPaths) { std::cout << path << '\n'; diff --git a/third_party/nix/src/nix-channel/nix-channel.cc b/third_party/nix/src/nix-channel/nix-channel.cc index ec72258b10..ae5e77e86d 100644 --- a/third_party/nix/src/nix-channel/nix-channel.cc +++ b/third_party/nix/src/nix-channel/nix-channel.cc @@ -40,18 +40,22 @@ static void readChannels() { static void writeChannels() { auto channelsFD = AutoCloseFD{open( channelsList.c_str(), O_WRONLY | O_CLOEXEC | O_CREAT | O_TRUNC, 0644)}; - if (!channelsFD) + if (!channelsFD) { throw SysError(format("opening '%1%' for writing") % channelsList); - for (const auto& channel : channels) + } + for (const auto& channel : channels) { writeFull(channelsFD.get(), channel.second + " " + channel.first + "\n"); + } } // Adds a channel. static void addChannel(const string& url, const string& name) { - if (!regex_search(url, std::regex("^(file|http|https)://"))) + if (!regex_search(url, std::regex("^(file|http|https)://"))) { throw Error(format("invalid channel URL '%1%'") % url); - if (!regex_search(name, std::regex("^[a-zA-Z0-9_][a-zA-Z0-9_\\.-]*$"))) + } + if (!regex_search(name, std::regex("^[a-zA-Z0-9_][a-zA-Z0-9_\\.-]*$"))) { throw Error(format("invalid channel identifier '%1%'") % name); + } readChannels(); channels[name] = url; writeChannels(); @@ -157,10 +161,12 @@ static void update(const StringSet& channelNames) { // Make the channels appear in nix-env. struct stat st; if (lstat(nixDefExpr.c_str(), &st) == 0) { - if (S_ISLNK(st.st_mode)) + if (S_ISLNK(st.st_mode)) { // old-skool ~/.nix-defexpr - if (unlink(nixDefExpr.c_str()) == -1) + if (unlink(nixDefExpr.c_str()) == -1) { throw SysError(format("unlinking %1%") % nixDefExpr); + } + } } else if (errno != ENOENT) { throw SysError(format("getting status of %1%") % nixDefExpr); } @@ -210,8 +216,9 @@ static int _main(int argc, char** argv) { case cNone: throw UsageError("no command specified"); case cAdd: - if (args.size() < 1 || args.size() > 2) + if (args.size() < 1 || args.size() > 2) { throw UsageError("'--add' requires one or two arguments"); + } { auto url = args[0]; std::string name; @@ -226,8 +233,9 @@ static int _main(int argc, char** argv) { } break; case cRemove: - if (args.size() != 1) + if (args.size() != 1) { throw UsageError("'--remove' requires one argument"); + } removeChannel(args[0]); break; case cList: @@ -235,15 +243,17 @@ static int _main(int argc, char** argv) { throw UsageError("'--list' expects no arguments"); } readChannels(); - for (const auto& channel : channels) + for (const auto& channel : channels) { std::cout << channel.first << ' ' << channel.second << '\n'; + } break; case cUpdate: update(StringSet(args.begin(), args.end())); break; case cRollback: - if (args.size() > 1) + if (args.size() > 1) { throw UsageError("'--rollback' has at most one argument"); + } Strings envArgs{"--profile", profile}; if (args.size() == 1) { envArgs.push_back("--switch-generation"); diff --git a/third_party/nix/src/nix-collect-garbage/nix-collect-garbage.cc b/third_party/nix/src/nix-collect-garbage/nix-collect-garbage.cc index 1b20386ff1..29c68e9637 100644 --- a/third_party/nix/src/nix-collect-garbage/nix-collect-garbage.cc +++ b/third_party/nix/src/nix-collect-garbage/nix-collect-garbage.cc @@ -42,10 +42,11 @@ void removeOldGenerations(std::string dir) { } if (link.find("link") != string::npos) { LOG(INFO) << "removing old generations of profile " << path; - if (deleteOlderThan != "") + if (deleteOlderThan != "") { deleteGenerationsOlderThan(path, deleteOlderThan, dryRun); - else + } else { deleteOldGenerations(path, dryRun); + } } } else if (type == DT_DIR) { removeOldGenerations(path); @@ -61,22 +62,23 @@ static int _main(int argc, char** argv) { parseCmdLine( argc, argv, [&](Strings::iterator& arg, const Strings::iterator& end) { - if (*arg == "--help") + if (*arg == "--help") { showManPage("nix-collect-garbage"); - else if (*arg == "--version") + } else if (*arg == "--version") { printVersion("nix-collect-garbage"); - else if (*arg == "--delete-old" || *arg == "-d") + } else if (*arg == "--delete-old" || *arg == "-d") { removeOld = true; - else if (*arg == "--delete-older-than") { + } else if (*arg == "--delete-older-than") { removeOld = true; deleteOlderThan = getArg(*arg, arg, end); - } else if (*arg == "--dry-run") + } else if (*arg == "--dry-run") { dryRun = true; - else if (*arg == "--max-freed") { + } else if (*arg == "--max-freed") { long long maxFreed = getIntArg(*arg, arg, end, true); options.maxFreed = maxFreed >= 0 ? maxFreed : 0; - } else + } else { return false; + } return true; }); diff --git a/third_party/nix/src/nix-copy-closure/nix-copy-closure.cc b/third_party/nix/src/nix-copy-closure/nix-copy-closure.cc index 2ec6a02136..67765a8cf7 100644 --- a/third_party/nix/src/nix-copy-closure/nix-copy-closure.cc +++ b/third_party/nix/src/nix-copy-closure/nix-copy-closure.cc @@ -18,32 +18,33 @@ static int _main(int argc, char** argv) { parseCmdLine( argc, argv, [&](Strings::iterator& arg, const Strings::iterator& end) { - if (*arg == "--help") + if (*arg == "--help") { showManPage("nix-copy-closure"); - else if (*arg == "--version") + } else if (*arg == "--version") { printVersion("nix-copy-closure"); - else if (*arg == "--gzip" || *arg == "--bzip2" || *arg == "--xz") { + } else if (*arg == "--gzip" || *arg == "--bzip2" || *arg == "--xz") { if (*arg != "--gzip") { LOG(WARNING) << "'" << *arg << "' is not implemented, falling back to gzip"; } gzip = true; - } else if (*arg == "--from") + } else if (*arg == "--from") { toMode = false; - else if (*arg == "--to") + } else if (*arg == "--to") { toMode = true; - else if (*arg == "--include-outputs") + } else if (*arg == "--include-outputs") { includeOutputs = true; - else if (*arg == "--show-progress") + } else if (*arg == "--show-progress") { LOG(WARNING) << "'--show-progress' is not implemented"; - else if (*arg == "--dry-run") + } else if (*arg == "--dry-run") { dryRun = true; - else if (*arg == "--use-substitutes" || *arg == "-s") + } else if (*arg == "--use-substitutes" || *arg == "-s") { useSubstitutes = Substitute; - else if (sshHost.empty()) + } else if (sshHost.empty()) { sshHost = *arg; - else + } else { storePaths.insert(*arg); + } return true; }); @@ -58,8 +59,9 @@ static int _main(int argc, char** argv) { auto from = toMode ? openStore() : openStore(remoteUri); PathSet storePaths2; - for (auto& path : storePaths) + for (auto& path : storePaths) { storePaths2.insert(from->followLinksToStorePath(path)); + } PathSet closure; from->computeFSClosure(storePaths2, closure, false, includeOutputs); diff --git a/third_party/nix/src/nix-daemon/nix-daemon.cc b/third_party/nix/src/nix-daemon/nix-daemon.cc index 34ea932fe9..4f71a0c36f 100644 --- a/third_party/nix/src/nix-daemon/nix-daemon.cc +++ b/third_party/nix/src/nix-daemon/nix-daemon.cc @@ -90,8 +90,9 @@ struct TunnelLogger { state->canSendStderr = false; throw; } - } else + } else { state->pendingMsgs.push_back(s); + } } void log(const FormatOrString& fs) { @@ -253,14 +254,15 @@ static void performOp(TunnelLogger* logger, ref store, bool trusted, Path path = readStorePath(*store, from); logger->startWork(); PathSet paths; - if (op == wopQueryReferences) + if (op == wopQueryReferences) { paths = store->queryPathInfo(path)->references; - else if (op == wopQueryReferrers) + } else if (op == wopQueryReferrers) { store->queryReferrers(path, paths); - else if (op == wopQueryValidDerivers) + } else if (op == wopQueryValidDerivers) { paths = store->queryValidDerivers(path); - else + } else { paths = store->queryDerivationOutputs(path); + } logger->stopWork(); to << paths; break; @@ -377,10 +379,11 @@ static void performOp(TunnelLogger* logger, ref store, bool trusted, /* Repairing is not atomic, so disallowed for "untrusted" clients. */ - if (mode == bmRepair && !trusted) + if (mode == bmRepair && !trusted) { throw Error( "repairing is not allowed because you are not in " "'trusted-users'"); + } } logger->startWork(); store->buildPaths(drvs, mode); @@ -451,10 +454,11 @@ static void performOp(TunnelLogger* logger, ref store, bool trusted, to << size; - for (auto& [target, links] : roots) + for (auto& [target, links] : roots) { for (auto& link : links) { to << link << target; } + } break; } @@ -472,8 +476,9 @@ static void performOp(TunnelLogger* logger, ref store, bool trusted, GCResults results; logger->startWork(); - if (options.ignoreLiveness) + if (options.ignoreLiveness) { throw Error("you are not allowed to ignore liveness"); + } store->collectGarbage(options, results); logger->stopWork(); @@ -522,30 +527,33 @@ static void performOp(TunnelLogger* logger, ref store, bool trusted, } Strings subs; auto ss = tokenizeString(value); - for (auto& s : ss) - if (trusted.count(s)) + for (auto& s : ss) { + if (trusted.count(s)) { subs.push_back(s); - else + } else { LOG(WARNING) << "ignoring untrusted substituter '" << s << "'"; + } + } res = subs; return true; }; try { - if (name == "ssh-auth-sock") // obsolete + if (name == "ssh-auth-sock") { // obsolete ; - else if (trusted || name == settings.buildTimeout.name || - name == "connect-timeout" || - (name == "builders" && value == "")) + } else if (trusted || name == settings.buildTimeout.name || + name == "connect-timeout" || + (name == "builders" && value == "")) { settings.set(name, value); - else if (setSubstituters(settings.substituters)) + } else if (setSubstituters(settings.substituters)) { ; - else if (setSubstituters(settings.extraSubstituters)) + } else if (setSubstituters(settings.extraSubstituters)) { ; - else + } else { LOG(WARNING) << "ignoring the user-specified setting '" << name << "', because it is a " << "restricted setting and you are not a trusted user"; + } } catch (UsageError& e) { LOG(WARNING) << e.what(); } @@ -562,9 +570,9 @@ static void performOp(TunnelLogger* logger, ref store, bool trusted, store->querySubstitutablePathInfos({path}, infos); logger->stopWork(); SubstitutablePathInfos::iterator i = infos.find(path); - if (i == infos.end()) + if (i == infos.end()) { to << 0; - else { + } else { to << 1 << i->second.deriver << i->second.references << i->second.downloadSize << i->second.narSize; } @@ -632,8 +640,9 @@ static void performOp(TunnelLogger* logger, ref store, bool trusted, bool checkContents, repair; from >> checkContents >> repair; logger->startWork(); - if (repair && !trusted) + if (repair && !trusted) { throw Error("you are not privileged to repair paths"); + } bool errors = store->verifyStore(checkContents, (RepairFlag)repair); logger->stopWork(); to << errors; @@ -746,8 +755,9 @@ static void processConnection(bool trusted, const std::string& userName, DLOG(INFO) << opCount << " operations"; }); - if (GET_PROTOCOL_MINOR(clientVersion) >= 14 && readInt(from)) + if (GET_PROTOCOL_MINOR(clientVersion) >= 14 && readInt(from)) { setAffinityTo(readInt(from)); + } readInt(from); // obsolete reserveSpace @@ -823,8 +833,9 @@ static void sigChldHandler(int sigNo) { // Ensure we don't modify errno of whatever we've interrupted auto saved_errno = errno; /* Reap all dead children. */ - while (waitpid(-1, 0, WNOHANG) > 0) + while (waitpid(-1, 0, WNOHANG) > 0) { ; + } errno = saved_errno; } @@ -833,8 +844,9 @@ static void setSigChldAction(bool autoReap) { act.sa_handler = autoReap ? sigChldHandler : SIG_DFL; sigfillset(&act.sa_mask); act.sa_flags = 0; - if (sigaction(SIGCHLD, &act, &oact)) + if (sigaction(SIGCHLD, &act, &oact)) { throw SysError("setting SIGCHLD handler"); + } } bool matchUser(const string& user, const string& group, const Strings& users) { @@ -846,7 +858,7 @@ bool matchUser(const string& user, const string& group, const Strings& users) { return true; } - for (auto& i : users) + for (auto& i : users) { if (string(i, 0, 1) == "@") { if (group == string(i, 1)) { return true; @@ -855,11 +867,13 @@ bool matchUser(const string& user, const string& group, const Strings& users) { if (!gr) { continue; } - for (char** mem = gr->gr_mem; *mem; mem++) + for (char** mem = gr->gr_mem; *mem; mem++) { if (user == string(*mem)) { return true; } + } } + } return false; } @@ -881,8 +895,9 @@ static PeerInfo getPeerInfo(int remote) { ucred cred; socklen_t credLen = sizeof(cred); - if (getsockopt(remote, SOL_SOCKET, SO_PEERCRED, &cred, &credLen) == -1) + if (getsockopt(remote, SOL_SOCKET, SO_PEERCRED, &cred, &credLen) == -1) { throw SysError("getting peer credentials"); + } peer = {true, cred.pid, true, cred.uid, true, cred.gid}; #elif defined(LOCAL_PEERCRED) @@ -918,8 +933,9 @@ static void daemonLoop(char** argv) { /* Handle socket-based activation by systemd. */ if (getEnv("LISTEN_FDS") != "") { if (getEnv("LISTEN_PID") != std::to_string(getpid()) || - getEnv("LISTEN_FDS") != "1") + getEnv("LISTEN_FDS") != "1") { throw Error("unexpected systemd environment variables"); + } fdSocket = SD_LISTEN_FDS_START; } @@ -938,14 +954,16 @@ static void daemonLoop(char** argv) { /* Urgh, sockaddr_un allows path names of only 108 characters. So chdir to the socket directory so that we can pass a relative path name. */ - if (chdir(dirOf(socketPath).c_str()) == -1) + if (chdir(dirOf(socketPath).c_str()) == -1) { throw SysError("cannot change current directory"); + } Path socketPathRel = "./" + baseNameOf(socketPath); struct sockaddr_un addr; addr.sun_family = AF_UNIX; - if (socketPathRel.size() >= sizeof(addr.sun_path)) + if (socketPathRel.size() >= sizeof(addr.sun_path)) { throw Error(format("socket path '%1%' is too long") % socketPathRel); + } strcpy(addr.sun_path, socketPathRel.c_str()); unlink(socketPath.c_str()); @@ -956,14 +974,17 @@ static void daemonLoop(char** argv) { mode_t oldMode = umask(0111); int res = bind(fdSocket.get(), (struct sockaddr*)&addr, sizeof(addr)); umask(oldMode); - if (res == -1) + if (res == -1) { throw SysError(format("cannot bind to socket '%1%'") % socketPath); + } - if (chdir("/") == -1) /* back to the root */ + if (chdir("/") == -1) { /* back to the root */ throw SysError("cannot change current directory"); + } - if (listen(fdSocket.get(), 5) == -1) + if (listen(fdSocket.get(), 5) == -1) { throw SysError(format("cannot listen on socket '%1%'") % socketPath); + } } closeOnExec(fdSocket.get()); @@ -1062,16 +1083,17 @@ static int _main(int argc, char** argv) { parseCmdLine(argc, argv, [&](Strings::iterator& arg, const Strings::iterator& end) { - if (*arg == "--daemon") + if (*arg == "--daemon") { ; /* ignored for backwards compatibility */ - else if (*arg == "--help") + } else if (*arg == "--help") { showManPage("nix-daemon"); - else if (*arg == "--version") + } else if (*arg == "--version") { printVersion("nix-daemon"); - else if (*arg == "--stdio") + } else if (*arg == "--stdio") { stdio = true; - else + } else { return false; + } return true; }); @@ -1087,20 +1109,23 @@ static int _main(int argc, char** argv) { } auto socketDir = dirOf(socketPath); - if (chdir(socketDir.c_str()) == -1) + if (chdir(socketDir.c_str()) == -1) { throw SysError(format("changing to socket directory '%1%'") % socketDir); + } auto socketName = baseNameOf(socketPath); auto addr = sockaddr_un{}; addr.sun_family = AF_UNIX; - if (socketName.size() + 1 >= sizeof(addr.sun_path)) + if (socketName.size() + 1 >= sizeof(addr.sun_path)) { throw Error(format("socket name %1% is too long") % socketName); + } strcpy(addr.sun_path, socketName.c_str()); - if (connect(s, (struct sockaddr*)&addr, sizeof(addr)) == -1) + if (connect(s, (struct sockaddr*)&addr, sizeof(addr)) == -1) { throw SysError(format("cannot connect to daemon at %1%") % socketPath); + } auto nfds = (s > STDIN_FILENO ? s : STDIN_FILENO) + 1; while (true) { @@ -1108,23 +1133,26 @@ static int _main(int argc, char** argv) { FD_ZERO(&fds); FD_SET(s, &fds); FD_SET(STDIN_FILENO, &fds); - if (select(nfds, &fds, nullptr, nullptr, nullptr) == -1) + if (select(nfds, &fds, nullptr, nullptr, nullptr) == -1) { throw SysError("waiting for data from client or server"); + } if (FD_ISSET(s, &fds)) { auto res = splice(s, nullptr, STDOUT_FILENO, nullptr, SSIZE_MAX, SPLICE_F_MOVE); - if (res == -1) + if (res == -1) { throw SysError("splicing data from daemon socket to stdout"); - else if (res == 0) + } else if (res == 0) { throw EndOfFile("unexpected EOF from daemon socket"); + } } if (FD_ISSET(STDIN_FILENO, &fds)) { auto res = splice(STDIN_FILENO, nullptr, s, nullptr, SSIZE_MAX, SPLICE_F_MOVE); - if (res == -1) + if (res == -1) { throw SysError("splicing data from stdin to daemon socket"); - else if (res == 0) + } else if (res == 0) { return 0; + } } } } else { diff --git a/third_party/nix/src/nix-env/nix-env.cc b/third_party/nix/src/nix-env/nix-env.cc index 5aa0a7d57e..2a4f94bfaf 100644 --- a/third_party/nix/src/nix-env/nix-env.cc +++ b/third_party/nix/src/nix-env/nix-env.cc @@ -60,22 +60,24 @@ struct Globals { typedef void (*Operation)(Globals& globals, Strings opFlags, Strings opArgs); static string needArg(Strings::iterator& i, Strings& args, const string& arg) { - if (i == args.end()) + if (i == args.end()) { throw UsageError(format("'%1%' requires an argument") % arg); + } return *i++; } static bool parseInstallSourceOptions(Globals& globals, Strings::iterator& i, Strings& args, const string& arg) { - if (arg == "--from-expression" || arg == "-E") + if (arg == "--from-expression" || arg == "-E") { globals.instSource.type = srcNixExprs; - else if (arg == "--from-profile") { + } else if (arg == "--from-profile") { globals.instSource.type = srcProfile; globals.instSource.profile = needArg(i, args, arg); - } else if (arg == "--attr" || arg == "-A") + } else if (arg == "--attr" || arg == "-A") { globals.instSource.type = srcAttrPath; - else + } else { return false; + } return true; } @@ -102,8 +104,9 @@ static void getAllExprs(EvalState& state, const Path& path, StringSet& attrs, Path path2 = path + "/" + i; struct stat st; - if (stat(path2.c_str(), &st) == -1) + if (stat(path2.c_str(), &st) == -1) { continue; // ignore dangling symlinks in ~/.nix-defexpr + } if (isNixExpr(path2, st) && (!S_ISREG(st.st_mode) || hasSuffix(path2, ".nix"))) { @@ -112,8 +115,9 @@ static void getAllExprs(EvalState& state, const Path& path, StringSet& attrs, `-A' option. Useful if you want to stick a Nix expression directly in ~/.nix-defexpr. */ string attrName = i; - if (hasSuffix(attrName, ".nix")) + if (hasSuffix(attrName, ".nix")) { attrName = string(attrName, 0, attrName.size() - 4); + } if (attrs.find(attrName) != attrs.end()) { LOG(WARNING) << "name collision in input Nix expressions, skipping '" << path2 << "'"; @@ -124,21 +128,24 @@ static void getAllExprs(EvalState& state, const Path& path, StringSet& attrs, Value& vFun = state.getBuiltin("import"); Value& vArg(*state.allocValue()); mkString(vArg, path2); - if (v.attrs->size() == v.attrs->capacity()) + if (v.attrs->size() == v.attrs->capacity()) { throw Error(format("too many Nix expressions in directory '%1%'") % path); + } mkApp(*state.allocAttr(v, state.symbols.create(attrName)), vFun, vArg); - } else if (S_ISDIR(st.st_mode)) + } else if (S_ISDIR(st.st_mode)) { /* `path2' is a directory (with no default.nix in it); recurse into it. */ getAllExprs(state, path2, attrs, v); + } } } static void loadSourceExpr(EvalState& state, const Path& path, Value& v) { struct stat st; - if (stat(path.c_str(), &st) == -1) + if (stat(path.c_str(), &st) == -1) { throw SysError(format("getting information about '%1%'") % path); + } if (isNixExpr(path, st)) { state.evalFile(path, v); @@ -159,8 +166,9 @@ static void loadSourceExpr(EvalState& state, const Path& path, Value& v) { v.attrs->sort(); } - else + else { throw Error("path '%s' is not a directory or a Nix expression", path); + } } static void loadDerivations(EvalState& state, Path nixExprPath, @@ -205,9 +213,11 @@ static bool isPrebuilt(EvalState& state, DrvInfo& elem) { static void checkSelectorUse(DrvNames& selectors) { /* Check that all selectors have been used. */ - for (auto& i : selectors) - if (i.hits == 0 && i.fullName != "*") + for (auto& i : selectors) { + if (i.hits == 0 && i.fullName != "*") { throw Error(format("selector '%1%' matches no derivations") % i.fullName); + } + } } static DrvInfos filterBySelector(EvalState& state, const DrvInfos& allElems, @@ -263,9 +273,10 @@ static DrvInfos filterBySelector(EvalState& state, const DrvInfos& allElems, if (d == 0) { d = comparePriorities(state, j.first, k->second.first); } - if (d == 0) + if (d == 0) { d = compareVersions(drvName.version, DrvName(k->second.first.queryName()).version); + } } if (d > 0) { @@ -279,21 +290,23 @@ static DrvInfos filterBySelector(EvalState& state, const DrvInfos& allElems, matches.clear(); for (auto& j : newest) { - if (multiple.find(j.second.first.queryName()) != multiple.end()) + if (multiple.find(j.second.first.queryName()) != multiple.end()) { LOG(WARNING) << "warning: there are multiple derivations named '" << j.second.first.queryName() << "'; using the first one"; + } matches.push_back(j.second); } } /* Insert only those elements in the final list that we haven't inserted before. */ - for (auto& j : matches) + for (auto& j : matches) { if (done.find(j.second) == done.end()) { done.insert(j.second); elems.push_back(j.first); } + } } checkSelectorUse(selectors); @@ -307,8 +320,9 @@ static void queryInstSources(EvalState& state, InstallSourceInfo& instSource, const Strings& args, DrvInfos& elems, bool newestOnly) { InstallSourceType type = instSource.type; - if (type == srcUnknown && args.size() > 0 && isPath(args.front())) + if (type == srcUnknown && args.size() > 0 && isPath(args.front())) { type = srcStorePaths; + } switch (type) { /* Get the available user environment elements from the @@ -369,10 +383,12 @@ static void queryInstSources(EvalState& state, InstallSourceInfo& instSource, elem.setOutPath( state.store->derivationFromPath(path).findOutput("out")); if (name.size() >= drvExtension.size() && - string(name, name.size() - drvExtension.size()) == drvExtension) + string(name, name.size() - drvExtension.size()) == drvExtension) { name = string(name, 0, name.size() - drvExtension.size()); - } else + } + } else { elem.setOutPath(path); + } elems.push_back(elem); } @@ -405,10 +421,11 @@ static void printMissing(EvalState& state, DrvInfos& elems) { PathSet targets; for (auto& i : elems) { Path drvPath = i.queryDrvPath(); - if (drvPath != "") + if (drvPath != "") { targets.insert(drvPath); - else + } else { targets.insert(i.queryOutPath()); + } } printMissing(state.store, targets); @@ -425,9 +442,11 @@ static void installDerivations(Globals& globals, const Strings& args, queryInstSources(*globals.state, globals.instSource, args, newElemsTmp, true); /* If --prebuilt-only is given, filter out source-only packages. */ - for (auto& i : newElemsTmp) - if (!globals.prebuiltOnly || isPrebuilt(*globals.state, i)) + for (auto& i : newElemsTmp) { + if (!globals.prebuiltOnly || isPrebuilt(*globals.state, i)) { newElems.push_back(i); + } + } StringSet newNames; for (auto& i : newElems) { @@ -454,10 +473,11 @@ static void installDerivations(Globals& globals, const Strings& args, for (auto& i : installedElems) { DrvName drvName(i.queryName()); if (!globals.preserveInstalled && - newNames.find(drvName.name) != newNames.end() && !keep(i)) + newNames.find(drvName.name) != newNames.end() && !keep(i)) { LOG(INFO) << "replacing old '" << i.queryName() << "'"; - else + } else { allElems.push_back(i); + } } for (auto& i : newElems) { @@ -472,22 +492,24 @@ static void installDerivations(Globals& globals, const Strings& args, } if (createUserEnv(*globals.state, allElems, profile, - settings.envKeepDerivations, lockToken)) + settings.envKeepDerivations, lockToken)) { break; + } } } static void opInstall(Globals& globals, Strings opFlags, Strings opArgs) { for (Strings::iterator i = opFlags.begin(); i != opFlags.end();) { string arg = *i++; - if (parseInstallSourceOptions(globals, i, opFlags, arg)) + if (parseInstallSourceOptions(globals, i, opFlags, arg)) { ; - else if (arg == "--preserve-installed" || arg == "-P") + } else if (arg == "--preserve-installed" || arg == "-P") { globals.preserveInstalled = true; - else if (arg == "--remove-all" || arg == "-r") + } else if (arg == "--remove-all" || arg == "-r") { globals.removeAll = true; - else + } else { throw UsageError(format("unknown flag '%1%'") % arg); + } } installDerivations(globals, opArgs, globals.profile); @@ -569,8 +591,9 @@ static void upgradeDerivations(Globals& globals, const Strings& args, LOG(INFO) << action << " '" << i.queryName() << "' to '" << bestElem->queryName() << "'"; newElems.push_back(*bestElem); - } else + } else { newElems.push_back(i); + } } catch (Error& e) { e.addPrefix( @@ -586,8 +609,9 @@ static void upgradeDerivations(Globals& globals, const Strings& args, } if (createUserEnv(*globals.state, newElems, globals.profile, - settings.envKeepDerivations, lockToken)) + settings.envKeepDerivations, lockToken)) { break; + } } } @@ -595,18 +619,19 @@ static void opUpgrade(Globals& globals, Strings opFlags, Strings opArgs) { UpgradeType upgradeType = utLt; for (Strings::iterator i = opFlags.begin(); i != opFlags.end();) { string arg = *i++; - if (parseInstallSourceOptions(globals, i, opFlags, arg)) + if (parseInstallSourceOptions(globals, i, opFlags, arg)) { ; - else if (arg == "--lt") + } else if (arg == "--lt") { upgradeType = utLt; - else if (arg == "--leq") + } else if (arg == "--leq") { upgradeType = utLeq; - else if (arg == "--eq") + } else if (arg == "--eq") { upgradeType = utEq; - else if (arg == "--always") + } else if (arg == "--always") { upgradeType = utAlways; - else + } else { throw UsageError(format("unknown flag '%1%'") % arg); + } } upgradeDerivations(globals, opArgs, upgradeType); @@ -620,10 +645,12 @@ static void setMetaFlag(EvalState& state, DrvInfo& drv, const string& name, } static void opSetFlag(Globals& globals, Strings opFlags, Strings opArgs) { - if (opFlags.size() > 0) + if (opFlags.size() > 0) { throw UsageError(format("unknown flag '%1%'") % opFlags.front()); - if (opArgs.size() < 2) + } + if (opArgs.size() < 2) { throw UsageError("not enough arguments to '--set-flag'"); + } Strings::iterator arg = opArgs.begin(); string flagName = *arg++; @@ -638,21 +665,23 @@ static void opSetFlag(Globals& globals, Strings opFlags, Strings opArgs) { /* Update all matching derivations. */ for (auto& i : installedElems) { DrvName drvName(i.queryName()); - for (auto& j : selectors) + for (auto& j : selectors) { if (j.matches(drvName)) { LOG(INFO) << "setting flag on '" << i.queryName() << "'"; j.hits++; setMetaFlag(*globals.state, i, flagName, flagValue); break; } + } } checkSelectorUse(selectors); /* Write the new user environment. */ if (createUserEnv(*globals.state, installedElems, globals.profile, - settings.envKeepDerivations, lockToken)) + settings.envKeepDerivations, lockToken)) { break; + } } } @@ -664,10 +693,11 @@ static void opSet(Globals& globals, Strings opFlags, Strings opArgs) { for (Strings::iterator i = opFlags.begin(); i != opFlags.end();) { string arg = *i++; - if (parseInstallSourceOptions(globals, i, opFlags, arg)) + if (parseInstallSourceOptions(globals, i, opFlags, arg)) { ; - else + } else { throw UsageError(format("unknown flag '%1%'") % arg); + } } DrvInfos elems; @@ -716,7 +746,7 @@ static void uninstallDerivations(Globals& globals, Strings& selectors, for (auto& i : installedElems) { DrvName drvName(i.queryName()); bool found = false; - for (auto& j : selectors) + for (auto& j : selectors) { /* !!! the repeated calls to followLinksToStorePath() are expensive, should pre-compute them. */ if ((isPath(j) && @@ -727,6 +757,7 @@ static void uninstallDerivations(Globals& globals, Strings& selectors, found = true; break; } + } if (!found) { newElems.push_back(i); } @@ -737,14 +768,16 @@ static void uninstallDerivations(Globals& globals, Strings& selectors, } if (createUserEnv(*globals.state, newElems, profile, - settings.envKeepDerivations, lockToken)) + settings.envKeepDerivations, lockToken)) { break; + } } } static void opUninstall(Globals& globals, Strings opFlags, Strings opArgs) { - if (opFlags.size() > 0) + if (opFlags.size() > 0) { throw UsageError(format("unknown flag '%1%'") % opFlags.front()); + } uninstallDerivations(globals, opArgs, globals.profile); } @@ -769,10 +802,11 @@ void printTable(Table& table) { assert(i.size() == nrColumns); Strings::iterator j; size_t column; - for (j = i.begin(), column = 0; j != i.end(); ++j, ++column) + for (j = i.begin(), column = 0; j != i.end(); ++j, ++column) { if (j->size() > widths[column]) { widths[column] = j->size(); } + } } for (auto& i : table) { @@ -782,8 +816,9 @@ void printTable(Table& table) { string s = *j; replace(s.begin(), s.end(), '\n', ' '); cout << s; - if (column < nrColumns - 1) + if (column < nrColumns - 1) { cout << string(widths[column] - s.size() + 2, ' '); + } } cout << std::endl; } @@ -818,8 +853,9 @@ static VersionDiff compareVersionAgainstSet(const DrvInfo& elem, version = name2.version; } else if (diff != cvGreater && diff != cvEqual && d > 0) { diff = cvLess; - if (version == "" || compareVersions(version, name2.version) < 0) + if (version == "" || compareVersions(version, name2.version) < 0) { version = name2.version; + } } } } @@ -877,48 +913,51 @@ static void opQuery(Globals& globals, Strings opFlags, Strings opArgs) { for (Strings::iterator i = opFlags.begin(); i != opFlags.end();) { string arg = *i++; - if (arg == "--status" || arg == "-s") + if (arg == "--status" || arg == "-s") { printStatus = true; - else if (arg == "--no-name") + } else if (arg == "--no-name") { printName = false; - else if (arg == "--system") + } else if (arg == "--system") { printSystem = true; - else if (arg == "--description") + } else if (arg == "--description") { printDescription = true; - else if (arg == "--compare-versions" || arg == "-c") + } else if (arg == "--compare-versions" || arg == "-c") { compareVersions = true; - else if (arg == "--drv-path") + } else if (arg == "--drv-path") { printDrvPath = true; - else if (arg == "--out-path") + } else if (arg == "--out-path") { printOutPath = true; - else if (arg == "--meta") + } else if (arg == "--meta") { printMeta = true; - else if (arg == "--installed") + } else if (arg == "--installed") { source = sInstalled; - else if (arg == "--available" || arg == "-a") + } else if (arg == "--available" || arg == "-a") { source = sAvailable; - else if (arg == "--xml") + } else if (arg == "--xml") { xmlOutput = true; - else if (arg == "--json") + } else if (arg == "--json") { jsonOutput = true; - else if (arg == "--attr-path" || arg == "-P") + } else if (arg == "--attr-path" || arg == "-P") { printAttrPath = true; - else if (arg == "--attr" || arg == "-A") + } else if (arg == "--attr" || arg == "-A") { attrPath = needArg(i, opFlags, arg); - else + } else { throw UsageError(format("unknown flag '%1%'") % arg); + } } /* Obtain derivation information from the specified source. */ DrvInfos availElems, installedElems; - if (source == sInstalled || compareVersions || printStatus) + if (source == sInstalled || compareVersions || printStatus) { installedElems = queryInstalled(*globals.state, globals.profile); + } - if (source == sAvailable || compareVersions) + if (source == sAvailable || compareVersions) { loadDerivations(*globals.state, globals.instSource.nixExprPath, globals.instSource.systemFilter, *globals.instSource.autoArgs, attrPath, availElems); + } DrvInfos elems_ = filterBySelector( *globals.state, source == sInstalled ? installedElems : availElems, @@ -948,13 +987,15 @@ static void opQuery(Globals& globals, Strings opFlags, Strings opArgs) { PathSet validPaths, substitutablePaths; if (printStatus || globals.prebuiltOnly) { PathSet paths; - for (auto& i : elems) try { + for (auto& i : elems) { + try { paths.insert(i.queryOutPath()); } catch (AssertionError& e) { DLOG(WARNING) << "skipping derivation named '" << i.queryName() << "' which gives an assertion failure"; i.setFailed(); } + } validPaths = globals.state->store->queryValidPaths(paths); substitutablePaths = globals.state->store->querySubstitutablePaths(paths); } @@ -984,8 +1025,10 @@ static void opQuery(Globals& globals, Strings opFlags, Strings opArgs) { if (globals.prebuiltOnly && validPaths.find(i.queryOutPath()) == validPaths.end() && - substitutablePaths.find(i.queryOutPath()) == substitutablePaths.end()) + substitutablePaths.find(i.queryOutPath()) == + substitutablePaths.end()) { continue; + } /* For table output. */ Strings columns; @@ -1003,15 +1046,17 @@ static void opQuery(Globals& globals, Strings opFlags, Strings opArgs) { attrs["installed"] = isInstalled ? "1" : "0"; attrs["valid"] = isValid ? "1" : "0"; attrs["substitutable"] = hasSubs ? "1" : "0"; - } else + } else { columns.push_back((string)(isInstalled ? "I" : "-") + (isValid ? "P" : "-") + (hasSubs ? "S" : "-")); + } } - if (xmlOutput) + if (xmlOutput) { attrs["attrPath"] = i.attrPath; - else if (printAttrPath) + } else if (printAttrPath) { columns.push_back(i.attrPath); + } if (xmlOutput) { auto drvName = DrvName(i.queryName()); @@ -1055,8 +1100,9 @@ static void opQuery(Globals& globals, Strings opFlags, Strings opArgs) { } } else { string column = (string) "" + ch + " " + version; - if (diff == cvGreater && tty) + if (diff == cvGreater && tty) { column = ANSI_RED + column + ANSI_NORMAL; + } columns.push_back(column); } } @@ -1065,8 +1111,9 @@ static void opQuery(Globals& globals, Strings opFlags, Strings opArgs) { if (i.querySystem() != "") { attrs["system"] = i.querySystem(); } - } else if (printSystem) + } else if (printSystem) { columns.push_back(i.querySystem()); + } if (printDrvPath) { string drvPath = i.queryDrvPath(); @@ -1074,8 +1121,9 @@ static void opQuery(Globals& globals, Strings opFlags, Strings opArgs) { if (drvPath != "") { attrs["drvPath"] = drvPath; } - } else + } else { columns.push_back(drvPath == "" ? "-" : drvPath); + } } if (printOutPath && !xmlOutput) { @@ -1100,8 +1148,9 @@ static void opQuery(Globals& globals, Strings opFlags, Strings opArgs) { if (descr != "") { attrs["description"] = descr; } - } else + } else { columns.push_back(descr); + } } if (xmlOutput) { @@ -1171,10 +1220,12 @@ static void opQuery(Globals& globals, Strings opFlags, Strings opArgs) { } } } - } else + } else { xml.writeEmptyElement("item", attrs); - } else + } + } else { table.push_back(columns); + } cout.flush(); @@ -1194,10 +1245,12 @@ static void opQuery(Globals& globals, Strings opFlags, Strings opArgs) { } static void opSwitchProfile(Globals& globals, Strings opFlags, Strings opArgs) { - if (opFlags.size() > 0) + if (opFlags.size() > 0) { throw UsageError(format("unknown flag '%1%'") % opFlags.front()); - if (opArgs.size() != 1) + } + if (opArgs.size() != 1) { throw UsageError(format("exactly one argument expected")); + } Path profile = absPath(opArgs.front()); Path profileLink = getHome() + "/.nix-profile"; @@ -1215,17 +1268,20 @@ static void switchGeneration(Globals& globals, int dstGen) { Generations gens = findGenerations(globals.profile, curGen); Generation dst; - for (auto& i : gens) + for (auto& i : gens) { if ((dstGen == prevGen && i.number < curGen) || - (dstGen >= 0 && i.number == dstGen)) + (dstGen >= 0 && i.number == dstGen)) { dst = i; + } + } if (!dst) { - if (dstGen == prevGen) + if (dstGen == prevGen) { throw Error(format("no generation older than the current (%1%) exists") % curGen); - else + } else { throw Error(format("generation %1% does not exist") % dstGen); + } } LOG(INFO) << "switching from generation " << curGen << " to " << dst.number; @@ -1239,21 +1295,25 @@ static void switchGeneration(Globals& globals, int dstGen) { static void opSwitchGeneration(Globals& globals, Strings opFlags, Strings opArgs) { - if (opFlags.size() > 0) + if (opFlags.size() > 0) { throw UsageError(format("unknown flag '%1%'") % opFlags.front()); - if (opArgs.size() != 1) + } + if (opArgs.size() != 1) { throw UsageError(format("exactly one argument expected")); + } int dstGen; - if (!string2Int(opArgs.front(), dstGen)) + if (!string2Int(opArgs.front(), dstGen)) { throw UsageError(format("expected a generation number")); + } switchGeneration(globals, dstGen); } static void opRollback(Globals& globals, Strings opFlags, Strings opArgs) { - if (opFlags.size() > 0) + if (opFlags.size() > 0) { throw UsageError(format("unknown flag '%1%'") % opFlags.front()); + } if (opArgs.size() != 0) { throw UsageError(format("no arguments expected")); } @@ -1263,8 +1323,9 @@ static void opRollback(Globals& globals, Strings opFlags, Strings opArgs) { static void opListGenerations(Globals& globals, Strings opFlags, Strings opArgs) { - if (opFlags.size() > 0) + if (opFlags.size() > 0) { throw UsageError(format("unknown flag '%1%'") % opFlags.front()); + } if (opArgs.size() != 0) { throw UsageError(format("no arguments expected")); } @@ -1291,29 +1352,33 @@ static void opListGenerations(Globals& globals, Strings opFlags, static void opDeleteGenerations(Globals& globals, Strings opFlags, Strings opArgs) { - if (opFlags.size() > 0) + if (opFlags.size() > 0) { throw UsageError(format("unknown flag '%1%'") % opFlags.front()); + } if (opArgs.size() == 1 && opArgs.front() == "old") { deleteOldGenerations(globals.profile, globals.dryRun); } else if (opArgs.size() == 1 && opArgs.front().find('d') != string::npos) { deleteGenerationsOlderThan(globals.profile, opArgs.front(), globals.dryRun); } else if (opArgs.size() == 1 && opArgs.front().find('+') != string::npos) { - if (opArgs.front().size() < 2) + if (opArgs.front().size() < 2) { throw Error(format("invalid number of generations ‘%1%’") % opArgs.front()); + } string str_max = string(opArgs.front(), 1, opArgs.front().size()); int max; - if (!string2Int(str_max, max) || max == 0) + if (!string2Int(str_max, max) || max == 0) { throw Error(format("invalid number of generations to keep ‘%1%’") % opArgs.front()); + } deleteGenerationsGreaterThan(globals.profile, max, globals.dryRun); } else { std::set gens; for (auto& i : opArgs) { unsigned int n; - if (!string2Int(i, n)) + if (!string2Int(i, n)) { throw UsageError(format("invalid generation number '%1%'") % i); + } gens.insert(n); } deleteGenerations(globals.profile, gens, globals.dryRun); @@ -1343,10 +1408,11 @@ static int _main(int argc, char** argv) { replaceSymlink(fmt("%s/profiles/per-user/%s/channels", settings.nixStateDir, getUserName()), globals.instSource.nixExprPath + "/channels"); - if (getuid() != 0) + if (getuid() != 0) { replaceSymlink( fmt("%s/profiles/per-user/root/channels", settings.nixStateDir), globals.instSource.nixExprPath + "/channels_root"); + } } catch (Error&) { } } @@ -1364,59 +1430,62 @@ static int _main(int argc, char** argv) { const Strings::iterator& end) { Operation oldOp = op; - if (*arg == "--help") + if (*arg == "--help") { showManPage("nix-env"); - else if (*arg == "--version") + } else if (*arg == "--version") { op = opVersion; - else if (*arg == "--install" || *arg == "-i") + } else if (*arg == "--install" || *arg == "-i") { op = opInstall; - else if (*arg == - "--force-name") // undocumented flag for nix-install-package + } else if (*arg == + "--force-name") { // undocumented flag for nix-install-package globals.forceName = getArg(*arg, arg, end); - else if (*arg == "--uninstall" || *arg == "-e") + } else if (*arg == "--uninstall" || *arg == "-e") { op = opUninstall; - else if (*arg == "--upgrade" || *arg == "-u") + } else if (*arg == "--upgrade" || *arg == "-u") { op = opUpgrade; - else if (*arg == "--set-flag") + } else if (*arg == "--set-flag") { op = opSetFlag; - else if (*arg == "--set") + } else if (*arg == "--set") { op = opSet; - else if (*arg == "--query" || *arg == "-q") + } else if (*arg == "--query" || *arg == "-q") { op = opQuery; - else if (*arg == "--profile" || *arg == "-p") + } else if (*arg == "--profile" || *arg == "-p") { globals.profile = absPath(getArg(*arg, arg, end)); - else if (*arg == "--file" || *arg == "-f") + } else if (*arg == "--file" || *arg == "-f") { file = getArg(*arg, arg, end); - else if (*arg == "--switch-profile" || *arg == "-S") + } else if (*arg == "--switch-profile" || *arg == "-S") { op = opSwitchProfile; - else if (*arg == "--switch-generation" || *arg == "-G") + } else if (*arg == "--switch-generation" || *arg == "-G") { op = opSwitchGeneration; - else if (*arg == "--rollback") + } else if (*arg == "--rollback") { op = opRollback; - else if (*arg == "--list-generations") + } else if (*arg == "--list-generations") { op = opListGenerations; - else if (*arg == "--delete-generations") + } else if (*arg == "--delete-generations") { op = opDeleteGenerations; - else if (*arg == "--dry-run") { + } else if (*arg == "--dry-run") { LOG(INFO) << "(dry run; not doing anything)"; globals.dryRun = true; - } else if (*arg == "--system-filter") + } else if (*arg == "--system-filter") { globals.instSource.systemFilter = getArg(*arg, arg, end); - else if (*arg == "--prebuilt-only" || *arg == "-b") + } else if (*arg == "--prebuilt-only" || *arg == "-b") { globals.prebuiltOnly = true; - else if (*arg == "--repair") + } else if (*arg == "--repair") { repair = Repair; - else if (*arg != "" && arg->at(0) == '-') { + } else if (*arg != "" && arg->at(0) == '-') { opFlags.push_back(*arg); /* FIXME: hacky */ if (*arg == "--from-profile" || - (op == opQuery && (*arg == "--attr" || *arg == "-A"))) + (op == opQuery && (*arg == "--attr" || *arg == "-A"))) { opFlags.push_back(getArg(*arg, arg, end)); - } else + } + } else { opArgs.push_back(*arg); + } - if (oldOp && oldOp != op) + if (oldOp && oldOp != op) { throw UsageError("only one operation may be specified"); + } return true; }); @@ -1435,8 +1504,9 @@ static int _main(int argc, char** argv) { std::shared_ptr(new EvalState(myArgs.searchPath, store)); globals.state->repair = repair; - if (file != "") + if (file != "") { globals.instSource.nixExprPath = lookupFileArg(*globals.state, file); + } globals.instSource.autoArgs = myArgs.getAutoArgs(*globals.state); diff --git a/third_party/nix/src/nix-env/user-env.cc b/third_party/nix/src/nix-env/user-env.cc index 0719c8a51d..d013f34b08 100644 --- a/third_party/nix/src/nix-env/user-env.cc +++ b/third_party/nix/src/nix-env/user-env.cc @@ -30,10 +30,11 @@ bool createUserEnv(EvalState& state, DrvInfos& elems, const Path& profile, /* Build the components in the user environment, if they don't exist already. */ PathSet drvsToBuild; - for (auto& i : elems) + for (auto& i : elems) { if (i.queryDrvPath() != "") { drvsToBuild.insert(i.queryDrvPath()); } + } DLOG(INFO) << "building user environment dependencies"; state.store->buildPaths(drvsToBuild, state.repair ? bmRepair : bmNormal); @@ -60,8 +61,9 @@ bool createUserEnv(EvalState& state, DrvInfos& elems, const Path& profile, mkString(*state.allocAttr(v, state.sSystem), system); } mkString(*state.allocAttr(v, state.sOutPath), i.queryOutPath()); - if (drvPath != "") + if (drvPath != "") { mkString(*state.allocAttr(v, state.sDrvPath), i.queryDrvPath()); + } // Copy each output meant for installation. DrvInfo::Outputs outputs = i.queryOutputs(true); diff --git a/third_party/nix/src/nix-instantiate/nix-instantiate.cc b/third_party/nix/src/nix-instantiate/nix-instantiate.cc index 20dcd7f42d..05f481906b 100644 --- a/third_party/nix/src/nix-instantiate/nix-instantiate.cc +++ b/third_party/nix/src/nix-instantiate/nix-instantiate.cc @@ -40,15 +40,16 @@ void processExpr(EvalState& state, const Strings& attrPaths, bool parseOnly, PathSet context; if (evalOnly) { Value vRes; - if (autoArgs.empty()) + if (autoArgs.empty()) { vRes = v; - else + } else { state.autoCallFunction(autoArgs, v, vRes); - if (output == okXML) + } + if (output == okXML) { printValueAsXML(state, strict, location, vRes, std::cout, context); - else if (output == okJSON) + } else if (output == okJSON) { printValueAsJSON(state, strict, vRes, std::cout, context); - else { + } else { if (strict) { state.forceValueDeep(vRes); } @@ -62,21 +63,23 @@ void processExpr(EvalState& state, const Strings& attrPaths, bool parseOnly, /* What output do we want? */ string outputName = i.queryOutputName(); - if (outputName == "") + if (outputName == "") { throw Error( format("derivation '%1%' lacks an 'outputName' attribute ") % drvPath); + } - if (gcRoot == "") + if (gcRoot == "") { printGCWarning(); - else { + } else { Path rootName = indirectRoot ? absPath(gcRoot) : gcRoot; if (++rootNr > 1) { rootName += "-" + std::to_string(rootNr); } auto store2 = state.store.dynamic_pointer_cast(); - if (store2) + if (store2) { drvPath = store2->addPermRoot(drvPath, rootName, indirectRoot); + } } std::cout << format("%1%%2%\n") % drvPath % (outputName != "out" ? "!" + outputName : ""); @@ -106,44 +109,45 @@ static int _main(int argc, char** argv) { MyArgs myArgs(baseNameOf(argv[0]), [&](Strings::iterator& arg, const Strings::iterator& end) { - if (*arg == "--help") + if (*arg == "--help") { showManPage("nix-instantiate"); - else if (*arg == "--version") + } else if (*arg == "--version") { printVersion("nix-instantiate"); - else if (*arg == "-") + } else if (*arg == "-") { readStdin = true; - else if (*arg == "--expr" || *arg == "-E") + } else if (*arg == "--expr" || *arg == "-E") { fromArgs = true; - else if (*arg == "--eval" || *arg == "--eval-only") + } else if (*arg == "--eval" || *arg == "--eval-only") { evalOnly = true; - else if (*arg == "--read-write-mode") + } else if (*arg == "--read-write-mode") { wantsReadWrite = true; - else if (*arg == "--parse" || *arg == "--parse-only") + } else if (*arg == "--parse" || *arg == "--parse-only") { parseOnly = evalOnly = true; - else if (*arg == "--find-file") + } else if (*arg == "--find-file") { findFile = true; - else if (*arg == "--attr" || *arg == "-A") + } else if (*arg == "--attr" || *arg == "-A") { attrPaths.push_back(getArg(*arg, arg, end)); - else if (*arg == "--add-root") + } else if (*arg == "--add-root") { gcRoot = getArg(*arg, arg, end); - else if (*arg == "--indirect") + } else if (*arg == "--indirect") { indirectRoot = true; - else if (*arg == "--xml") + } else if (*arg == "--xml") { outputKind = okXML; - else if (*arg == "--json") + } else if (*arg == "--json") { outputKind = okJSON; - else if (*arg == "--no-location") + } else if (*arg == "--no-location") { xmlOutputSourceLocation = false; - else if (*arg == "--strict") + } else if (*arg == "--strict") { strict = true; - else if (*arg == "--repair") + } else if (*arg == "--repair") { repair = Repair; - else if (*arg == "--dry-run") + } else if (*arg == "--dry-run") { settings.readOnlyMode = true; - else if (*arg != "" && arg->at(0) == '-') + } else if (*arg != "" && arg->at(0) == '-') { return false; - else + } else { files.push_back(*arg); + } return true; }); diff --git a/third_party/nix/src/nix-prefetch-url/nix-prefetch-url.cc b/third_party/nix/src/nix-prefetch-url/nix-prefetch-url.cc index 96d8540958..8c92af19d5 100644 --- a/third_party/nix/src/nix-prefetch-url/nix-prefetch-url.cc +++ b/third_party/nix/src/nix-prefetch-url/nix-prefetch-url.cc @@ -40,12 +40,14 @@ string resolveMirrorUri(EvalState& state, string uri) { state.forceAttrs(vMirrors); auto mirrorList = vMirrors.attrs->find(state.symbols.create(mirrorName)); - if (mirrorList == vMirrors.attrs->end()) + if (mirrorList == vMirrors.attrs->end()) { throw Error(format("unknown mirror name '%1%'") % mirrorName); + } state.forceList(*mirrorList->value); - if (mirrorList->value->listSize() < 1) + if (mirrorList->value->listSize() < 1) { throw Error(format("mirror URI '%1%' did not expand to anything") % uri); + } string mirror = state.forceString(*mirrorList->value->listElems()[0]); return mirror + (hasSuffix(mirror, "/") ? "" : "/") + string(s, p + 1); @@ -67,28 +69,30 @@ static int _main(int argc, char** argv) { MyArgs myArgs(baseNameOf(argv[0]), [&](Strings::iterator& arg, const Strings::iterator& end) { - if (*arg == "--help") + if (*arg == "--help") { showManPage("nix-prefetch-url"); - else if (*arg == "--version") + } else if (*arg == "--version") { printVersion("nix-prefetch-url"); - else if (*arg == "--type") { + } else if (*arg == "--type") { string s = getArg(*arg, arg, end); ht = parseHashType(s); - if (ht == htUnknown) + if (ht == htUnknown) { throw UsageError(format("unknown hash type '%1%'") % s); - } else if (*arg == "--print-path") + } + } else if (*arg == "--print-path") { printPath = true; - else if (*arg == "--attr" || *arg == "-A") { + } else if (*arg == "--attr" || *arg == "-A") { fromExpr = true; attrPath = getArg(*arg, arg, end); - } else if (*arg == "--unpack") + } else if (*arg == "--unpack") { unpack = true; - else if (*arg == "--name") + } else if (*arg == "--name") { name = getArg(*arg, arg, end); - else if (*arg != "" && arg->at(0) == '-') + } else if (*arg != "" && arg->at(0) == '-') { return false; - else + } else { args.push_back(*arg); + } return true; }); @@ -123,8 +127,9 @@ static int _main(int argc, char** argv) { /* Extract the URI. */ auto attr = v.attrs->find(state->symbols.create("urls")); - if (attr == v.attrs->end()) + if (attr == v.attrs->end()) { throw Error("attribute set does not contain a 'urls' attribute"); + } state->forceList(*attr->value); if (attr->value->listSize() < 1) { throw Error("'urls' list is empty"); @@ -133,10 +138,11 @@ static int _main(int argc, char** argv) { /* Extract the hash mode. */ attr = v.attrs->find(state->symbols.create("outputHashMode")); - if (attr == v.attrs->end()) + if (attr == v.attrs->end()) { LOG(WARNING) << "this does not look like a fetchurl call"; - else + } else { unpack = state->forceString(*attr->value) == "recursive"; + } /* Extract the name. */ if (name.empty()) { @@ -151,8 +157,9 @@ static int _main(int argc, char** argv) { if (name.empty()) { name = baseNameOf(uri); } - if (name.empty()) + if (name.empty()) { throw Error(format("cannot figure out file name for '%1%'") % uri); + } /* If an expected hash is given, the file may already exist in the store. */ @@ -161,10 +168,11 @@ static int _main(int argc, char** argv) { if (args.size() == 2) { expectedHash = Hash(args[1], ht); storePath = store->makeFixedOutputPath(unpack, expectedHash, name); - if (store->isValidPath(storePath)) + if (store->isValidPath(storePath)) { hash = expectedHash; - else + } else { storePath.clear(); + } } if (storePath.empty()) { @@ -193,27 +201,30 @@ static int _main(int argc, char** argv) { LOG(INFO) << "unpacking..."; Path unpacked = (Path)tmpDir + "/unpacked"; createDirs(unpacked); - if (hasSuffix(baseNameOf(uri), ".zip")) + if (hasSuffix(baseNameOf(uri), ".zip")) { runProgram("unzip", true, {"-qq", tmpFile, "-d", unpacked}); - else + } else { // FIXME: this requires GNU tar for decompression. runProgram("tar", true, {"xf", tmpFile, "-C", unpacked}); + } /* If the archive unpacks to a single file/directory, then use that as the top-level. */ auto entries = readDirectory(unpacked); - if (entries.size() == 1) + if (entries.size() == 1) { tmpFile = unpacked + "/" + entries[0].name; - else + } else { tmpFile = unpacked; + } } /* FIXME: inefficient; addToStore() will also hash this. */ hash = unpack ? hashPath(ht, tmpFile).first : hashFile(ht, tmpFile); - if (expectedHash != Hash(ht) && expectedHash != hash) + if (expectedHash != Hash(ht) && expectedHash != hash) { throw Error(format("hash mismatch for '%1%'") % uri); + } /* Copy the file to the Nix store. FIXME: if RemoteStore implemented addToStoreFromDump() and downloadFile() diff --git a/third_party/nix/src/nix-store/nix-store.cc b/third_party/nix/src/nix-store/nix-store.cc index 1df4b451e7..75cbae3f0f 100644 --- a/third_party/nix/src/nix-store/nix-store.cc +++ b/third_party/nix/src/nix-store/nix-store.cc @@ -38,8 +38,9 @@ static std::shared_ptr store; ref ensureLocalStore() { auto store2 = std::dynamic_pointer_cast(store); - if (!store2) + if (!store2) { throw Error("you don't have sufficient rights to use this command"); + } return ref(store2); } @@ -48,8 +49,9 @@ static Path useDeriver(Path path) { return path; } Path drvPath = store->queryPathInfo(path)->deriver; - if (drvPath == "") + if (drvPath == "") { throw Error(format("deriver of path '%1%' is not known") % path); + } return drvPath; } @@ -67,23 +69,25 @@ static PathSet realisePath(Path path, bool build = true) { Derivation drv = store->derivationFromPath(p.first); rootNr++; - if (p.second.empty()) + if (p.second.empty()) { for (auto& i : drv.outputs) { p.second.insert(i.first); } + } PathSet outputs; for (auto& j : p.second) { DerivationOutputs::iterator i = drv.outputs.find(j); - if (i == drv.outputs.end()) + if (i == drv.outputs.end()) { throw Error( format("derivation '%1%' does not have an output named '%2%'") % p.first % j); + } Path outPath = i->second.path; if (store2) { - if (gcRoot == "") + if (gcRoot == "") { printGCWarning(); - else { + } else { Path rootName = gcRoot; if (rootNr > 1) { rootName += "-" + std::to_string(rootNr); @@ -100,15 +104,16 @@ static PathSet realisePath(Path path, bool build = true) { } else { - if (build) + if (build) { store->ensurePath(path); - else if (!store->isValidPath(path)) + } else if (!store->isValidPath(path)) { throw Error(format("path '%1%' does not exist and cannot be created") % path); + } if (store2) { - if (gcRoot == "") + if (gcRoot == "") { printGCWarning(); - else { + } else { Path rootName = gcRoot; rootNr++; if (rootNr > 1) { @@ -127,17 +132,19 @@ static void opRealise(Strings opFlags, Strings opArgs) { BuildMode buildMode = bmNormal; bool ignoreUnknown = false; - for (auto& i : opFlags) - if (i == "--dry-run") + for (auto& i : opFlags) { + if (i == "--dry-run") { dryRun = true; - else if (i == "--repair") + } else if (i == "--repair") { buildMode = bmRepair; - else if (i == "--check") + } else if (i == "--check") { buildMode = bmCheck; - else if (i == "--ignore-unknown") + } else if (i == "--ignore-unknown") { ignoreUnknown = true; - else + } else { throw UsageError(format("unknown flag '%1%'") % i); + } + } Paths paths; for (auto& i : opArgs) { @@ -153,17 +160,19 @@ static void opRealise(Strings opFlags, Strings opArgs) { if (ignoreUnknown) { Paths paths2; - for (auto& i : paths) + for (auto& i : paths) { if (unknown.find(i) == unknown.end()) { paths2.push_back(i); } + } paths = paths2; unknown = PathSet(); } - if (settings.printMissing) + if (settings.printMissing) { printMissing(ref(store), willBuild, willSubstitute, unknown, downloadSize, narSize); + } if (dryRun) { return; @@ -172,14 +181,16 @@ static void opRealise(Strings opFlags, Strings opArgs) { /* Build all paths at the same time to exploit parallelism. */ store->buildPaths(PathSet(paths.begin(), paths.end()), buildMode); - if (!ignoreUnknown) + if (!ignoreUnknown) { for (auto& i : paths) { PathSet paths = realisePath(i, false); - if (!noOutput) + if (!noOutput) { for (auto& j : paths) { cout << format("%1%\n") % j; } + } } + } } /* Add files to the Nix store and print the resulting paths. */ @@ -188,8 +199,9 @@ static void opAdd(Strings opFlags, Strings opArgs) { throw UsageError("unknown flag"); } - for (auto& i : opArgs) + for (auto& i : opArgs) { cout << format("%1%\n") % store->addToStore(baseNameOf(i), i); + } } /* Preload the output of a fixed-output derivation into the Nix @@ -197,11 +209,13 @@ static void opAdd(Strings opFlags, Strings opArgs) { static void opAddFixed(Strings opFlags, Strings opArgs) { bool recursive = false; - for (auto& i : opFlags) - if (i == "--recursive") + for (auto& i : opFlags) { + if (i == "--recursive") { recursive = true; - else + } else { throw UsageError(format("unknown flag '%1%'") % i); + } + } if (opArgs.empty()) { throw UsageError("first argument must be hash algorithm"); @@ -210,23 +224,27 @@ static void opAddFixed(Strings opFlags, Strings opArgs) { HashType hashAlgo = parseHashType(opArgs.front()); opArgs.pop_front(); - for (auto& i : opArgs) + for (auto& i : opArgs) { cout << format("%1%\n") % store->addToStore(baseNameOf(i), i, recursive, hashAlgo); + } } /* Hack to support caching in `nix-prefetch-url'. */ static void opPrintFixedPath(Strings opFlags, Strings opArgs) { bool recursive = false; - for (auto i : opFlags) - if (i == "--recursive") + for (auto i : opFlags) { + if (i == "--recursive") { recursive = true; - else + } else { throw UsageError(format("unknown flag '%1%'") % i); + } + } - if (opArgs.size() != 3) + if (opArgs.size() != 3) { throw UsageError(format("'--print-fixed-path' requires three arguments")); + } Strings::iterator i = opArgs.begin(); HashType hashAlgo = parseHashType(*i++); @@ -249,8 +267,9 @@ static PathSet maybeUseOutputs(const Path& storePath, bool useOutput, outputs.insert(i.second.path); } return outputs; - } else + } else { return {storePath}; + } } /* Some code to print a tree representation of a derivation dependency @@ -316,50 +335,52 @@ static void opQuery(Strings opFlags, Strings opArgs) { for (auto& i : opFlags) { QueryType prev = query; - if (i == "--outputs") + if (i == "--outputs") { query = qOutputs; - else if (i == "--requisites" || i == "-R") + } else if (i == "--requisites" || i == "-R") { query = qRequisites; - else if (i == "--references") + } else if (i == "--references") { query = qReferences; - else if (i == "--referrers" || i == "--referers") + } else if (i == "--referrers" || i == "--referers") { query = qReferrers; - else if (i == "--referrers-closure" || i == "--referers-closure") + } else if (i == "--referrers-closure" || i == "--referers-closure") { query = qReferrersClosure; - else if (i == "--deriver" || i == "-d") + } else if (i == "--deriver" || i == "-d") { query = qDeriver; - else if (i == "--binding" || i == "-b") { + } else if (i == "--binding" || i == "-b") { if (opArgs.size() == 0) { throw UsageError("expected binding name"); } bindingName = opArgs.front(); opArgs.pop_front(); query = qBinding; - } else if (i == "--hash") + } else if (i == "--hash") { query = qHash; - else if (i == "--size") + } else if (i == "--size") { query = qSize; - else if (i == "--tree") + } else if (i == "--tree") { query = qTree; - else if (i == "--graph") + } else if (i == "--graph") { query = qGraph; - else if (i == "--graphml") + } else if (i == "--graphml") { query = qGraphML; - else if (i == "--resolve") + } else if (i == "--resolve") { query = qResolve; - else if (i == "--roots") + } else if (i == "--roots") { query = qRoots; - else if (i == "--use-output" || i == "-u") + } else if (i == "--use-output" || i == "-u") { useOutput = true; - else if (i == "--force-realise" || i == "--force-realize" || i == "-f") + } else if (i == "--force-realise" || i == "--force-realize" || i == "-f") { forceRealise = true; - else if (i == "--include-outputs") + } else if (i == "--include-outputs") { includeOutputs = true; - else + } else { throw UsageError(format("unknown flag '%1%'") % i); - if (prev != qDefault && prev != query) + } + if (prev != qDefault && prev != query) { throw UsageError(format("query type '%1%' conflicts with earlier flag") % i); + } } if (query == qDefault) { @@ -392,21 +413,24 @@ static void opQuery(Strings opFlags, Strings opArgs) { PathSet ps = maybeUseOutputs(store->followLinksToStorePath(i), useOutput, forceRealise); for (auto& j : ps) { - if (query == qRequisites) + if (query == qRequisites) { store->computeFSClosure(j, paths, false, includeOutputs); - else if (query == qReferences) { + } else if (query == qReferences) { for (auto& p : store->queryPathInfo(j)->references) { paths.insert(p); } - } else if (query == qReferrers) + } else if (query == qReferrers) { store->queryReferrers(j, paths); - else if (query == qReferrersClosure) + } else if (query == qReferrersClosure) { store->computeFSClosure(j, paths, true); + } } } Paths sorted = store->topoSortPaths(paths); - for (Paths::reverse_iterator i = sorted.rbegin(); i != sorted.rend(); ++i) + for (Paths::reverse_iterator i = sorted.rbegin(); i != sorted.rend(); + ++i) { cout << format("%s\n") % *i; + } break; } @@ -423,11 +447,12 @@ static void opQuery(Strings opFlags, Strings opArgs) { Path path = useDeriver(store->followLinksToStorePath(i)); Derivation drv = store->derivationFromPath(path); StringPairs::iterator j = drv.env.find(bindingName); - if (j == drv.env.end()) + if (j == drv.env.end()) { throw Error( format( "derivation '%1%' has no environment binding named '%2%'") % path % bindingName); + } cout << format("%1%\n") % j->second; } break; @@ -442,16 +467,18 @@ static void opQuery(Strings opFlags, Strings opArgs) { if (query == qHash) { assert(info->narHash.type == htSHA256); cout << fmt("%s\n", info->narHash.to_string(Base32)); - } else if (query == qSize) + } else if (query == qSize) { cout << fmt("%d\n", info->narSize); + } } } break; case qTree: { PathSet done; - for (auto& i : opArgs) + for (auto& i : opArgs) { printTree(store->followLinksToStorePath(i), "", "", done); + } break; } @@ -478,8 +505,9 @@ static void opQuery(Strings opFlags, Strings opArgs) { } case qResolve: { - for (auto& i : opArgs) + for (auto& i : opArgs) { cout << format("%1%\n") % store->followLinksToStorePath(i); + } break; } @@ -493,10 +521,13 @@ static void opQuery(Strings opFlags, Strings opArgs) { settings.gcKeepDerivations); } Roots roots = store->findRoots(false); - for (auto& [target, links] : roots) - if (referrers.find(target) != referrers.end()) - for (auto& link : links) + for (auto& [target, links] : roots) { + if (referrers.find(target) != referrers.end()) { + for (auto& link : links) { cout << format("%1% -> %2%\n") % link % target; + } + } + } break; } @@ -509,16 +540,18 @@ static void opPrintEnv(Strings opFlags, Strings opArgs) { if (!opFlags.empty()) { throw UsageError("unknown flag"); } - if (opArgs.size() != 1) + if (opArgs.size() != 1) { throw UsageError("'--print-env' requires one derivation store path"); + } Path drvPath = opArgs.front(); Derivation drv = store->derivationFromPath(drvPath); /* Print each environment variable in the derivation in a format that can be sourced by the shell. */ - for (auto& i : drv.env) + for (auto& i : drv.env) { cout << format("export %1%; %1%=%2%\n") % i.first % shellEscape(i.second); + } /* Also output the arguments. This doesn't preserve whitespace in arguments. */ @@ -544,8 +577,9 @@ static void opReadLog(Strings opFlags, Strings opArgs) { for (auto& i : opArgs) { auto path = store->followLinksToStorePath(i); auto log = store->getBuildLog(path); - if (!log) + if (!log) { throw Error("build log of derivation '%s' is not available", path); + } std::cout << *log; } } @@ -558,12 +592,14 @@ static void opDumpDB(Strings opFlags, Strings opArgs) { for (auto& i : opArgs) { i = store->followLinksToStorePath(i); } - for (auto& i : opArgs) + for (auto& i : opArgs) { cout << store->makeValidityRegistration({i}, true, true); + } } else { PathSet validPaths = store->queryAllValidPaths(); - for (auto& i : validPaths) + for (auto& i : validPaths) { cout << store->makeValidityRegistration({i}, true, true); + } } } @@ -607,13 +643,15 @@ static void opRegisterValidity(Strings opFlags, Strings opArgs) { bool reregister = false; // !!! maybe this should be the default bool hashGiven = false; - for (auto& i : opFlags) - if (i == "--reregister") + for (auto& i : opFlags) { + if (i == "--reregister") { reregister = true; - else if (i == "--hash-given") + } else if (i == "--hash-given") { hashGiven = true; - else + } else { throw UsageError(format("unknown flag '%1%'") % i); + } + } if (!opArgs.empty()) { throw UsageError("no arguments expected"); @@ -625,19 +663,22 @@ static void opRegisterValidity(Strings opFlags, Strings opArgs) { static void opCheckValidity(Strings opFlags, Strings opArgs) { bool printInvalid = false; - for (auto& i : opFlags) - if (i == "--print-invalid") + for (auto& i : opFlags) { + if (i == "--print-invalid") { printInvalid = true; - else + } else { throw UsageError(format("unknown flag '%1%'") % i); + } + } for (auto& i : opArgs) { Path path = store->followLinksToStorePath(i); if (!store->isValidPath(path)) { - if (printInvalid) + if (printInvalid) { cout << format("%1%\n") % path; - else + } else { throw Error(format("path '%1%' is not valid") % path); + } } } } @@ -650,20 +691,22 @@ static void opGC(Strings opFlags, Strings opArgs) { GCResults results; /* Do what? */ - for (auto i = opFlags.begin(); i != opFlags.end(); ++i) - if (*i == "--print-roots") + for (auto i = opFlags.begin(); i != opFlags.end(); ++i) { + if (*i == "--print-roots") { printRoots = true; - else if (*i == "--print-live") + } else if (*i == "--print-live") { options.action = GCOptions::gcReturnLive; - else if (*i == "--print-dead") + } else if (*i == "--print-dead") { options.action = GCOptions::gcReturnDead; - else if (*i == "--delete") + } else if (*i == "--delete") { options.action = GCOptions::gcDeleteDead; - else if (*i == "--max-freed") { + } else if (*i == "--max-freed") { long long maxFreed = getIntArg(*i, i, opFlags.end(), true); options.maxFreed = maxFreed >= 0 ? maxFreed : 0; - } else + } else { throw UsageError(format("bad sub-operation '%1%' in GC") % *i); + } + } if (!opArgs.empty()) { throw UsageError("no arguments expected"); @@ -673,22 +716,25 @@ static void opGC(Strings opFlags, Strings opArgs) { Roots roots = store->findRoots(false); std::set> roots2; // Transpose and sort the roots. - for (auto& [target, links] : roots) + for (auto& [target, links] : roots) { for (auto& link : links) { roots2.emplace(link, target); } - for (auto& [link, target] : roots2) + } + for (auto& [link, target] : roots2) { std::cout << link << " -> " << target << "\n"; + } } else { PrintFreed freed(options.action == GCOptions::gcDeleteDead, results); store->collectGarbage(options, results); - if (options.action != GCOptions::gcDeleteDead) + if (options.action != GCOptions::gcDeleteDead) { for (auto& i : results.paths) { cout << i << std::endl; } + } } } @@ -699,14 +745,17 @@ static void opDelete(Strings opFlags, Strings opArgs) { GCOptions options; options.action = GCOptions::gcDeleteSpecific; - for (auto& i : opFlags) - if (i == "--ignore-liveness") + for (auto& i : opFlags) { + if (i == "--ignore-liveness") { options.ignoreLiveness = true; - else + } else { throw UsageError(format("unknown flag '%1%'") % i); + } + } - for (auto& i : opArgs) + for (auto& i : opArgs) { options.pathsToDelete.insert(store->followLinksToStorePath(i)); + } GCResults results; PrintFreed freed(true, results); @@ -795,13 +844,15 @@ static void opVerify(Strings opFlags, Strings opArgs) { bool checkContents = false; RepairFlag repair = NoRepair; - for (auto& i : opFlags) - if (i == "--check-contents") + for (auto& i : opFlags) { + if (i == "--check-contents") { checkContents = true; - else if (i == "--repair") + } else if (i == "--repair") { repair = Repair; - else + } else { throw UsageError(format("unknown flag '%1%'") % i); + } + } if (store->verifyStore(checkContents, repair)) { LOG(WARNING) << "not all errors were fixed"; @@ -851,8 +902,9 @@ static void opRepairPath(Strings opFlags, Strings opArgs) { /* Optimise the disk space usage of the Nix store by hard-linking files with the same contents. */ static void opOptimise(Strings opFlags, Strings opArgs) { - if (!opArgs.empty() || !opFlags.empty()) + if (!opArgs.empty() || !opFlags.empty()) { throw UsageError("no arguments expected"); + } store->optimiseStore(); } @@ -860,11 +912,13 @@ static void opOptimise(Strings opFlags, Strings opArgs) { /* Serve the nix store in a way usable by a restricted ssh user. */ static void opServe(Strings opFlags, Strings opArgs) { bool writeAllowed = false; - for (auto& i : opFlags) - if (i == "--write") + for (auto& i : opFlags) { + if (i == "--write") { writeAllowed = true; - else + } else { throw UsageError(format("unknown flag '%1%'") % i); + } + } if (!opArgs.empty()) { throw UsageError("no arguments expected"); @@ -889,8 +943,9 @@ static void opServe(Strings opFlags, Strings opArgs) { settings.useSubstitutes = false; settings.maxSilentTime = readInt(in); settings.buildTimeout = readInt(in); - if (GET_PROTOCOL_MINOR(clientVersion) >= 2) + if (GET_PROTOCOL_MINOR(clientVersion) >= 2) { settings.maxLogSize = readNum(in); + } if (GET_PROTOCOL_MINOR(clientVersion) >= 3) { settings.buildRepeat = readInt(in); settings.enforceDeterminism = readInt(in); @@ -912,10 +967,11 @@ static void opServe(Strings opFlags, Strings opArgs) { bool lock = readInt(in); bool substitute = readInt(in); PathSet paths = readStorePaths(*store, in); - if (lock && writeAllowed) + if (lock && writeAllowed) { for (auto& path : paths) { store->addTempRoot(path); } + } /* If requested, substitute missing paths. This implements nix-copy-closure's --use-substitutes @@ -923,21 +979,24 @@ static void opServe(Strings opFlags, Strings opArgs) { if (substitute && writeAllowed) { /* Filter out .drv files (we don't want to build anything). */ PathSet paths2; - for (auto& path : paths) + for (auto& path : paths) { if (!isDerivation(path)) { paths2.insert(path); } + } unsigned long long downloadSize, narSize; PathSet willBuild, willSubstitute, unknown; store->queryMissing(PathSet(paths2.begin(), paths2.end()), willBuild, willSubstitute, unknown, downloadSize, narSize); /* FIXME: should use ensurePath(), but it only does one path at a time. */ - if (!willSubstitute.empty()) try { + if (!willSubstitute.empty()) { + try { store->buildPaths(willSubstitute); } catch (Error& e) { LOG(WARNING) << e.msg(); } + } } out << store->queryValidPaths(paths); @@ -954,9 +1013,10 @@ static void opServe(Strings opFlags, Strings opArgs) { // !!! Maybe we want compression? out << info->narSize // downloadSize << info->narSize; - if (GET_PROTOCOL_MINOR(clientVersion) >= 4) + if (GET_PROTOCOL_MINOR(clientVersion) >= 4) { out << (info->narHash ? info->narHash.to_string() : "") << info->ca << info->sigs; + } } catch (InvalidPath&) { } } @@ -1020,9 +1080,10 @@ static void opServe(Strings opFlags, Strings opArgs) { out << status.status << status.errorMsg; - if (GET_PROTOCOL_MINOR(clientVersion) >= 3) + if (GET_PROTOCOL_MINOR(clientVersion) >= 3) { out << status.timesBuilt << status.isNonDeterministic << status.startTime << status.stopTime; + } break; } @@ -1127,81 +1188,85 @@ static int _main(int argc, char** argv) { Strings opFlags, opArgs; Operation op = 0; - parseCmdLine( - argc, argv, [&](Strings::iterator& arg, const Strings::iterator& end) { - Operation oldOp = op; - - if (*arg == "--help") - showManPage("nix-store"); - else if (*arg == "--version") - op = opVersion; - else if (*arg == "--realise" || *arg == "--realize" || *arg == "-r") - op = opRealise; - else if (*arg == "--add" || *arg == "-A") - op = opAdd; - else if (*arg == "--add-fixed") - op = opAddFixed; - else if (*arg == "--print-fixed-path") - op = opPrintFixedPath; - else if (*arg == "--delete") - op = opDelete; - else if (*arg == "--query" || *arg == "-q") - op = opQuery; - else if (*arg == "--print-env") - op = opPrintEnv; - else if (*arg == "--read-log" || *arg == "-l") - op = opReadLog; - else if (*arg == "--dump-db") - op = opDumpDB; - else if (*arg == "--load-db") - op = opLoadDB; - else if (*arg == "--register-validity") - op = opRegisterValidity; - else if (*arg == "--check-validity") - op = opCheckValidity; - else if (*arg == "--gc") - op = opGC; - else if (*arg == "--dump") - op = opDump; - else if (*arg == "--restore") - op = opRestore; - else if (*arg == "--export") - op = opExport; - else if (*arg == "--import") - op = opImport; - else if (*arg == "--init") - op = opInit; - else if (*arg == "--verify") - op = opVerify; - else if (*arg == "--verify-path") - op = opVerifyPath; - else if (*arg == "--repair-path") - op = opRepairPath; - else if (*arg == "--optimise" || *arg == "--optimize") - op = opOptimise; - else if (*arg == "--serve") - op = opServe; - else if (*arg == "--generate-binary-cache-key") - op = opGenerateBinaryCacheKey; - else if (*arg == "--add-root") - gcRoot = absPath(getArg(*arg, arg, end)); - else if (*arg == "--indirect") - indirectRoot = true; - else if (*arg == "--no-output") - noOutput = true; - else if (*arg != "" && arg->at(0) == '-') { - opFlags.push_back(*arg); - if (*arg == "--max-freed" || *arg == "--max-links" || - *arg == "--max-atime") /* !!! hack */ - opFlags.push_back(getArg(*arg, arg, end)); - } else - opArgs.push_back(*arg); - - if (oldOp && oldOp != op) - throw UsageError("only one operation may be specified"); - - return true; - }); + parseCmdLine(argc, argv, + [&](Strings::iterator& arg, const Strings::iterator& end) { + Operation oldOp = op; + + if (*arg == "--help") { + showManPage("nix-store"); + } else if (*arg == "--version") { + op = opVersion; + } else if (*arg == "--realise" || *arg == "--realize" || + *arg == "-r") { + op = opRealise; + } else if (*arg == "--add" || *arg == "-A") { + op = opAdd; + } else if (*arg == "--add-fixed") { + op = opAddFixed; + } else if (*arg == "--print-fixed-path") { + op = opPrintFixedPath; + } else if (*arg == "--delete") { + op = opDelete; + } else if (*arg == "--query" || *arg == "-q") { + op = opQuery; + } else if (*arg == "--print-env") { + op = opPrintEnv; + } else if (*arg == "--read-log" || *arg == "-l") { + op = opReadLog; + } else if (*arg == "--dump-db") { + op = opDumpDB; + } else if (*arg == "--load-db") { + op = opLoadDB; + } else if (*arg == "--register-validity") { + op = opRegisterValidity; + } else if (*arg == "--check-validity") { + op = opCheckValidity; + } else if (*arg == "--gc") { + op = opGC; + } else if (*arg == "--dump") { + op = opDump; + } else if (*arg == "--restore") { + op = opRestore; + } else if (*arg == "--export") { + op = opExport; + } else if (*arg == "--import") { + op = opImport; + } else if (*arg == "--init") { + op = opInit; + } else if (*arg == "--verify") { + op = opVerify; + } else if (*arg == "--verify-path") { + op = opVerifyPath; + } else if (*arg == "--repair-path") { + op = opRepairPath; + } else if (*arg == "--optimise" || *arg == "--optimize") { + op = opOptimise; + } else if (*arg == "--serve") { + op = opServe; + } else if (*arg == "--generate-binary-cache-key") { + op = opGenerateBinaryCacheKey; + } else if (*arg == "--add-root") { + gcRoot = absPath(getArg(*arg, arg, end)); + } else if (*arg == "--indirect") { + indirectRoot = true; + } else if (*arg == "--no-output") { + noOutput = true; + } else if (*arg != "" && arg->at(0) == '-') { + opFlags.push_back(*arg); + if (*arg == "--max-freed" || *arg == "--max-links" || + *arg == "--max-atime") { /* !!! hack */ + opFlags.push_back(getArg(*arg, arg, end)); + } + } else { + opArgs.push_back(*arg); + } + + if (oldOp && oldOp != op) { + throw UsageError("only one operation may be specified"); + } + + return true; + }); initPlugins(); @@ -1209,8 +1274,9 @@ static int _main(int argc, char** argv) { throw UsageError("no operation specified"); } - if (op != opDump && op != opRestore) /* !!! hack */ + if (op != opDump && op != opRestore) { /* !!! hack */ store = openStore(); + } op(opFlags, opArgs); diff --git a/third_party/nix/src/nix/build.cc b/third_party/nix/src/nix/build.cc index 806be2b37a..0738821a89 100644 --- a/third_party/nix/src/nix/build.cc +++ b/third_party/nix/src/nix/build.cc @@ -47,8 +47,8 @@ struct CmdBuild : MixDryRun, InstallablesCommand { for (size_t i = 0; i < buildables.size(); ++i) { auto& b(buildables[i]); - if (outLink != "") - for (auto& output : b.outputs) + if (outLink != "") { + for (auto& output : b.outputs) { if (auto store2 = store.dynamic_pointer_cast()) { std::string symlink = outLink; if (i) { @@ -59,6 +59,8 @@ struct CmdBuild : MixDryRun, InstallablesCommand { } store2->addPermRoot(output.second, absPath(symlink), true); } + } + } } } }; diff --git a/third_party/nix/src/nix/cat.cc b/third_party/nix/src/nix/cat.cc index ea9fd0d942..9b2da929ac 100644 --- a/third_party/nix/src/nix/cat.cc +++ b/third_party/nix/src/nix/cat.cc @@ -10,10 +10,12 @@ struct MixCat : virtual Args { void cat(ref accessor) { auto st = accessor->stat(path); - if (st.type == FSAccessor::Type::tMissing) + if (st.type == FSAccessor::Type::tMissing) { throw Error(format("path '%1%' does not exist") % path); - if (st.type != FSAccessor::Type::tRegular) + } + if (st.type != FSAccessor::Type::tRegular) { throw Error(format("path '%1%' is not a regular file") % path); + } std::cout << accessor->readFile(path); } diff --git a/third_party/nix/src/nix/command.cc b/third_party/nix/src/nix/command.cc index 4c1220668c..b35fb1be98 100644 --- a/third_party/nix/src/nix/command.cc +++ b/third_party/nix/src/nix/command.cc @@ -14,10 +14,11 @@ void Command::printHelp(const string& programName, std::ostream& out) { if (!exs.empty()) { out << "\n"; out << "Examples:\n"; - for (auto& ex : exs) + for (auto& ex : exs) { out << "\n" << " " << ex.description << "\n" // FIXME: wrap << " $ " << ex.command << "\n"; + } } } @@ -26,8 +27,9 @@ MultiCommand::MultiCommand(const Commands& _commands) : commands(_commands) { "command", 1, true, [=](std::vector ss) { assert(!command); auto i = commands.find(ss[0]); - if (i == commands.end()) + if (i == commands.end()) { throw UsageError("'%s' is not a recognised command", ss[0]); + } command = i->second; }}); } @@ -50,8 +52,9 @@ void MultiCommand::printHelp(const string& programName, std::ostream& out) { Table2 table; for (auto& command : commands) { auto descr = command.second->description(); - if (!descr.empty()) + if (!descr.empty()) { table.push_back(std::make_pair(command.second->name(), descr)); + } } printTable(out, table); @@ -72,16 +75,19 @@ bool MultiCommand::processFlag(Strings::iterator& pos, Strings::iterator end) { } bool MultiCommand::processArgs(const Strings& args, bool finish) { - if (command) + if (command) { return command->processArgs(args, finish); - else + } else { return Args::processArgs(args, finish); + } } StoreCommand::StoreCommand() {} ref StoreCommand::getStore() { - if (!_store) _store = createStore(); + if (!_store) { + _store = createStore(); + } return ref(_store); } @@ -90,17 +96,18 @@ ref StoreCommand::createStore() { return openStore(); } void StoreCommand::run() { run(getStore()); } StorePathsCommand::StorePathsCommand(bool recursive) : recursive(recursive) { - if (recursive) + if (recursive) { mkFlag() .longName("no-recursive") .description("apply operation to specified paths only") .set(&this->recursive, false); - else + } else { mkFlag() .longName("recursive") .shortName('r') .description("apply operation to closure of the specified paths") .set(&this->recursive, true); + } mkFlag(0, "all", "apply operation to the entire store", &all); } @@ -109,16 +116,18 @@ void StorePathsCommand::run(ref store) { Paths storePaths; if (all) { - if (installables.size()) + if (installables.size()) { throw UsageError("'--all' does not expect arguments"); + } for (auto& p : store->queryAllValidPaths()) { storePaths.push_back(p); } } else { - for (auto& p : toStorePaths(store, NoBuild, installables)) + for (auto& p : toStorePaths(store, NoBuild, installables)) { storePaths.push_back(p); + } if (recursive) { PathSet closure; @@ -134,8 +143,9 @@ void StorePathsCommand::run(ref store) { void StorePathCommand::run(ref store) { auto storePaths = toStorePaths(store, NoBuild, installables); - if (storePaths.size() != 1) + if (storePaths.size() != 1) { throw UsageError("this command requires exactly one store path"); + } run(store, *storePaths.begin()); } diff --git a/third_party/nix/src/nix/copy.cc b/third_party/nix/src/nix/copy.cc index fe5e37363c..633fe399b4 100644 --- a/third_party/nix/src/nix/copy.cc +++ b/third_party/nix/src/nix/copy.cc @@ -72,8 +72,9 @@ struct CmdCopy : StorePathsCommand { } void run(ref srcStore, Paths storePaths) override { - if (srcUri.empty() && dstUri.empty()) + if (srcUri.empty() && dstUri.empty()) { throw UsageError("you must pass '--from' and/or '--to'"); + } ref dstStore = dstUri.empty() ? openStore() : openStore(dstUri); diff --git a/third_party/nix/src/nix/doctor.cc b/third_party/nix/src/nix/doctor.cc index cf59aabdbd..44ce2d9292 100644 --- a/third_party/nix/src/nix/doctor.cc +++ b/third_party/nix/src/nix/doctor.cc @@ -44,9 +44,11 @@ struct CmdDoctor : StoreCommand { bool checkNixInPath() { PathSet dirs; - for (auto& dir : tokenizeString(getEnv("PATH"), ":")) - if (pathExists(dir + "/nix-env")) + for (auto& dir : tokenizeString(getEnv("PATH"), ":")) { + if (pathExists(dir + "/nix-env")) { dirs.insert(dirOf(canonPath(dir + "/nix-env", true))); + } + } if (dirs.size() != 1) { std::cout << "Warning: multiple versions of nix found in PATH." @@ -73,11 +75,13 @@ struct CmdDoctor : StoreCommand { if (store->isStorePath(userEnv) && hasSuffix(userEnv, "user-environment")) { while (profileDir.find("/profiles/") == std::string::npos && - isLink(profileDir)) + isLink(profileDir)) { profileDir = absPath(readLink(profileDir), dirOf(profileDir)); + } - if (profileDir.find("/profiles/") == std::string::npos) + if (profileDir.find("/profiles/") == std::string::npos) { dirs.insert(dir); + } } } catch (SysError&) { } diff --git a/third_party/nix/src/nix/edit.cc b/third_party/nix/src/nix/edit.cc index 61d700592b..01c2ec7ef0 100644 --- a/third_party/nix/src/nix/edit.cc +++ b/third_party/nix/src/nix/edit.cc @@ -40,8 +40,9 @@ struct CmdEdit : InstallableCommand { DLOG(INFO) << "position is " << pos; auto colon = pos.rfind(':'); - if (colon == std::string::npos) + if (colon == std::string::npos) { throw Error("cannot parse meta.position attribute '%s'", pos); + } std::string filename(pos, 0, colon); int lineno; @@ -57,8 +58,9 @@ struct CmdEdit : InstallableCommand { if (editor.find("emacs") != std::string::npos || editor.find("nano") != std::string::npos || - editor.find("vim") != std::string::npos) + editor.find("vim") != std::string::npos) { args.push_back(fmt("+%d", lineno)); + } args.push_back(filename); diff --git a/third_party/nix/src/nix/eval.cc b/third_party/nix/src/nix/eval.cc index d84b86bc53..661d587d73 100644 --- a/third_party/nix/src/nix/eval.cc +++ b/third_party/nix/src/nix/eval.cc @@ -32,8 +32,9 @@ struct CmdEval : MixJSON, InstallableCommand { } void run(ref store) override { - if (raw && json) + if (raw && json) { throw UsageError("--raw and --json are mutually exclusive"); + } auto state = getEvalState(); diff --git a/third_party/nix/src/nix/hash.cc b/third_party/nix/src/nix/hash.cc index 77be77cfcd..39780532f8 100644 --- a/third_party/nix/src/nix/hash.cc +++ b/third_party/nix/src/nix/hash.cc @@ -73,8 +73,9 @@ struct CmdToBase : Command { } void run() override { - for (auto s : args) + for (auto s : args) { std::cout << fmt("%s\n", Hash(s, ht).to_string(base, base == SRI)); + } } }; @@ -94,29 +95,31 @@ static int compatNixHash(int argc, char** argv) { parseCmdLine(argc, argv, [&](Strings::iterator& arg, const Strings::iterator& end) { - if (*arg == "--help") + if (*arg == "--help") { showManPage("nix-hash"); - else if (*arg == "--version") + } else if (*arg == "--version") { printVersion("nix-hash"); - else if (*arg == "--flat") + } else if (*arg == "--flat") { flat = true; - else if (*arg == "--base32") + } else if (*arg == "--base32") { base32 = true; - else if (*arg == "--truncate") + } else if (*arg == "--truncate") { truncate = true; - else if (*arg == "--type") { + } else if (*arg == "--type") { string s = getArg(*arg, arg, end); ht = parseHashType(s); - if (ht == htUnknown) + if (ht == htUnknown) { throw UsageError(format("unknown hash type '%1%'") % s); - } else if (*arg == "--to-base16") + } + } else if (*arg == "--to-base16") { op = opTo16; - else if (*arg == "--to-base32") + } else if (*arg == "--to-base32") { op = opTo32; - else if (*arg != "" && arg->at(0) == '-') + } else if (*arg != "" && arg->at(0) == '-') { return false; - else + } else { ss.push_back(*arg); + } return true; }); diff --git a/third_party/nix/src/nix/installables.cc b/third_party/nix/src/nix/installables.cc index f400841b7c..8a7de8655b 100644 --- a/third_party/nix/src/nix/installables.cc +++ b/third_party/nix/src/nix/installables.cc @@ -30,10 +30,10 @@ Value* SourceExprCommand::getSourceExpr(EvalState& state) { vSourceExpr = state.allocValue(); - if (file != "") + if (file != "") { state.evalFile(lookupFileArg(state, file), *vSourceExpr); - else { + } else { /* Construct the installation source from $NIX_PATH. */ auto searchPath = state.getSearchPath(); @@ -60,14 +60,18 @@ Value* SourceExprCommand::getSourceExpr(EvalState& state) { state.getBuiltin("import"), *v2); }; - for (auto& i : searchPath) /* Hack to handle channels. */ + for (auto& i : searchPath) { /* Hack to handle channels. */ if (i.first.empty() && pathExists(i.second + "/manifest.nix")) { - for (auto& j : readDirectory(i.second)) + for (auto& j : readDirectory(i.second)) { if (j.name != "manifest.nix" && - pathExists(fmt("%s/%s/default.nix", i.second, j.name))) + pathExists(fmt("%s/%s/default.nix", i.second, j.name))) { addEntry(j.name); - } else + } + } + } else { addEntry(i.first); + } + } vSourceExpr->attrs->sort(); } @@ -76,18 +80,20 @@ Value* SourceExprCommand::getSourceExpr(EvalState& state) { } ref SourceExprCommand::getEvalState() { - if (!evalState) + if (!evalState) { evalState = std::make_shared(searchPath, getStore()); + } return ref(evalState); } Buildable Installable::toBuildable() { auto buildables = toBuildables(); - if (buildables.size() != 1) + if (buildables.size() != 1) { throw Error( "installable '%s' evaluates to %d derivations, where only one is " "expected", what(), buildables.size()); + } return std::move(buildables[0]); } @@ -127,9 +133,10 @@ struct InstallableValue : Installable { drvPaths.insert(b.drvPath); auto outputName = drv.queryOutputName(); - if (outputName == "") + if (outputName == "") { throw Error("derivation '%s' lacks an 'outputName' attribute", b.drvPath); + } b.outputs.emplace(outputName, drv.queryOutPath()); @@ -140,11 +147,13 @@ struct InstallableValue : Installable { // merge the buildables. if (drvPaths.size() == 1) { Buildable b{*drvPaths.begin()}; - for (auto& b2 : res) + for (auto& b2 : res) { b.outputs.insert(b2.outputs.begin(), b2.outputs.end()); + } return {b}; - } else + } else { return res; + } } }; @@ -200,21 +209,23 @@ static std::vector> parseInstallables( } for (auto& s : ss) { - if (s.compare(0, 1, "(") == 0) + if (s.compare(0, 1, "(") == 0) { result.push_back(std::make_shared(cmd, s)); - else if (s.find("/") != std::string::npos) { + } else if (s.find("/") != std::string::npos) { auto path = store->toStorePath(store->followLinksToStore(s)); - if (store->isStorePath(path)) + if (store->isStorePath(path)) { result.push_back(std::make_shared(path)); + } } - else if (s == "" || std::regex_match(s, attrPathRegex)) + else if (s == "" || std::regex_match(s, attrPathRegex)) { result.push_back(std::make_shared(cmd, s)); - else + } else { throw UsageError("don't know what to do with argument '%s'", s); + } } return result; @@ -248,10 +259,11 @@ Buildables build(ref store, RealiseMode mode, } pathsToBuild.insert(b.drvPath + "!" + concatStringsSep(",", outputNames)); - } else + } else { for (auto& output : b.outputs) { pathsToBuild.insert(output.second); } + } buildables.push_back(std::move(b)); } } @@ -269,10 +281,11 @@ PathSet toStorePaths(ref store, RealiseMode mode, std::vector> installables) { PathSet outPaths; - for (auto& b : build(store, mode, installables)) + for (auto& b : build(store, mode, installables)) { for (auto& output : b.outputs) { outPaths.insert(output.second); } + } return outPaths; } @@ -281,9 +294,10 @@ Path toStorePath(ref store, RealiseMode mode, std::shared_ptr installable) { auto paths = toStorePaths(store, mode, {installable}); - if (paths.size() != 1) + if (paths.size() != 1) { throw Error("argument '%s' should evaluate to one store path", installable->what()); + } return *paths.begin(); } @@ -293,22 +307,26 @@ PathSet toDerivations(ref store, bool useDeriver) { PathSet drvPaths; - for (auto& i : installables) + for (auto& i : installables) { for (auto& b : i->toBuildables()) { if (b.drvPath.empty()) { - if (!useDeriver) + if (!useDeriver) { throw Error("argument '%s' did not evaluate to a derivation", i->what()); + } for (auto& output : b.outputs) { auto derivers = store->queryValidDerivers(output.second); - if (derivers.empty()) + if (derivers.empty()) { throw Error("'%s' does not have a known deriver", i->what()); + } // FIXME: use all derivers? drvPaths.insert(*derivers.begin()); } - } else + } else { drvPaths.insert(b.drvPath); + } } + } return drvPaths; } diff --git a/third_party/nix/src/nix/ls.cc b/third_party/nix/src/nix/ls.cc index 62720b93a0..13b7bbbbb9 100644 --- a/third_party/nix/src/nix/ls.cc +++ b/third_party/nix/src/nix/ls.cc @@ -35,17 +35,20 @@ struct MixLs : virtual Args, MixJSON { ? "lrwxrwxrwx" : "dr-xr-xr-x"; std::cout << (format("%s %20d %s") % tp % st.fileSize % relPath); - if (st.type == FSAccessor::Type::tSymlink) + if (st.type == FSAccessor::Type::tSymlink) { std::cout << " -> " << accessor->readLink(curPath); + } std::cout << "\n"; - if (recursive && st.type == FSAccessor::Type::tDirectory) + if (recursive && st.type == FSAccessor::Type::tDirectory) { doPath(st, curPath, relPath, false); + } } else { std::cout << relPath << "\n"; if (recursive) { auto st = accessor->stat(curPath); - if (st.type == FSAccessor::Type::tDirectory) + if (st.type == FSAccessor::Type::tDirectory) { doPath(st, curPath, relPath, false); + } } } }; @@ -57,8 +60,9 @@ struct MixLs : virtual Args, MixJSON { for (auto& name : names) { showFile(curPath + "/" + name, relPath + "/" + name); } - } else + } else { showFile(curPath, relPath); + } }; auto st = accessor->stat(path); diff --git a/third_party/nix/src/nix/main.cc b/third_party/nix/src/nix/main.cc index 9dbe9b155b..23bc62887a 100644 --- a/third_party/nix/src/nix/main.cc +++ b/third_party/nix/src/nix/main.cc @@ -44,8 +44,9 @@ static bool haveInternet() { } } else if (i->ifa_addr->sa_family == AF_INET6) { if (!IN6_IS_ADDR_LOOPBACK(&((sockaddr_in6*)i->ifa_addr)->sin6_addr) && - !IN6_IS_ADDR_LINKLOCAL(&((sockaddr_in6*)i->ifa_addr)->sin6_addr)) + !IN6_IS_ADDR_LINKLOCAL(&((sockaddr_in6*)i->ifa_addr)->sin6_addr)) { return true; + } } } @@ -72,8 +73,9 @@ struct NixArgs : virtual MultiCommand, virtual MixCommonArgs { Table2 tbl; std::map settings; globalConfig.getSettings(settings); - for (const auto& s : settings) + for (const auto& s : settings) { tbl.emplace_back(s.first, s.second.description); + } printTable(std::cout, tbl); throw Exit(); }); @@ -159,13 +161,15 @@ void mainWrapped(int argc, char** argv) { if (!settings.useSubstitutes.overriden) { settings.useSubstitutes = false; } - if (!settings.tarballTtl.overriden) + if (!settings.tarballTtl.overriden) { settings.tarballTtl = std::numeric_limits::max(); + } if (!downloadSettings.tries.overriden) { downloadSettings.tries = 0; } - if (!downloadSettings.connectTimeout.overriden) + if (!downloadSettings.connectTimeout.overriden) { downloadSettings.connectTimeout = 1; + } } args.command->prepare(); diff --git a/third_party/nix/src/nix/path-info.cc b/third_party/nix/src/nix/path-info.cc index 9f155231d4..b871c45f1c 100644 --- a/third_party/nix/src/nix/path-info.cc +++ b/third_party/nix/src/nix/path-info.cc @@ -75,8 +75,9 @@ struct CmdPathInfo : StorePathsCommand, MixJSON { void run(ref store, Paths storePaths) override { size_t pathLen = 0; - for (auto& storePath : storePaths) + for (auto& storePath : storePaths) { pathLen = std::max(pathLen, storePath.size()); + } if (json) { JSONPlaceholder jsonRoot(std::cout); @@ -93,9 +94,10 @@ struct CmdPathInfo : StorePathsCommand, MixJSON { std::cout << storePath; - if (showSize || showClosureSize || showSigs) + if (showSize || showClosureSize || showSigs) { std::cout << std::string( std::max(0, (int)pathLen - (int)storePath.size()), ' '); + } if (showSize) { printSize(info->narSize); diff --git a/third_party/nix/src/nix/repl.cc b/third_party/nix/src/nix/repl.cc index f6b62d0ca2..80921f77dc 100644 --- a/third_party/nix/src/nix/repl.cc +++ b/third_party/nix/src/nix/repl.cc @@ -181,8 +181,9 @@ static char* completionCallback(char* s, int* match) { static int listPossibleCallback(char* s, char*** avp) { auto possible = curRepl->completePrefix(s); - if (possible.size() > (INT_MAX / sizeof(char*))) + if (possible.size() > (INT_MAX / sizeof(char*))) { throw Error("too many completions"); + } int ac = 0; char** vp = nullptr; @@ -190,7 +191,9 @@ static int listPossibleCallback(char* s, char*** avp) { auto check = [&](auto* p) { if (!p) { if (vp) { - while (--ac >= 0) free(vp[ac]); + while (--ac >= 0) { + free(vp[ac]); + } free(vp); } throw Error("allocation failure"); @@ -288,20 +291,24 @@ bool NixRepl::getLine(string& input, const std::string& prompt) { act.sa_handler = sigintHandler; sigfillset(&act.sa_mask); act.sa_flags = 0; - if (sigaction(SIGINT, &act, &old)) + if (sigaction(SIGINT, &act, &old)) { throw SysError("installing handler for SIGINT"); + } sigemptyset(&set); sigaddset(&set, SIGINT); - if (sigprocmask(SIG_UNBLOCK, &set, &savedSignalMask)) + if (sigprocmask(SIG_UNBLOCK, &set, &savedSignalMask)) { throw SysError("unblocking SIGINT"); + } }; auto restoreSignals = [&]() { - if (sigprocmask(SIG_SETMASK, &savedSignalMask, nullptr)) + if (sigprocmask(SIG_SETMASK, &savedSignalMask, nullptr)) { throw SysError("restoring signals"); + } - if (sigaction(SIGINT, &old, 0)) + if (sigaction(SIGINT, &old, 0)) { throw SysError("restoring handler for SIGINT"); + } }; setupSignals(); @@ -343,8 +350,9 @@ StringSet NixRepl::completePrefix(string prefix) { auto dir = std::string(cur, 0, slash); auto prefix2 = std::string(cur, slash + 1); for (auto& entry : readDirectory(dir == "" ? "/" : dir)) { - if (entry.name[0] != '.' && hasPrefix(entry.name, prefix2)) + if (entry.name[0] != '.' && hasPrefix(entry.name, prefix2)) { completions.insert(prev + dir + "/" + entry.name); + } } } catch (Error&) { } @@ -417,21 +425,25 @@ bool isVarName(const string& s) { if ((c >= '0' && c <= '9') || c == '-' || c == '\'') { return false; } - for (auto& i : s) + for (auto& i : s) { if (!((i >= 'a' && i <= 'z') || (i >= 'A' && i <= 'Z') || - (i >= '0' && i <= '9') || i == '_' || i == '-' || i == '\'')) + (i >= '0' && i <= '9') || i == '_' || i == '-' || i == '\'')) { return false; + } + } return true; } Path NixRepl::getDerivationPath(Value& v) { auto drvInfo = getDerivation(state, v, false); - if (!drvInfo) + if (!drvInfo) { throw Error( "expression does not evaluate to a derivation, so I can't build it"); + } Path drvPath = drvInfo->queryDrvPath(); - if (drvPath == "" || !state.store->isValidPath(drvPath)) + if (drvPath == "" || !state.store->isValidPath(drvPath)) { throw Error("expression did not evaluate to a valid derivation"); + } return drvPath; } @@ -520,9 +532,10 @@ bool NixRepl::processLine(string line) { std::cout << std::endl << "this derivation produced the following outputs:" << std::endl; - for (auto& i : drv.outputs) + for (auto& i : drv.outputs) { std::cout << format(" %1% -> %2%") % i.first % i.second.path << std::endl; + } } } else if (command == ":i") { runProgram(settings.nixBinDir + "/nix-env", Strings{"-i", drvPath}); @@ -537,13 +550,13 @@ bool NixRepl::processLine(string line) { printValue(std::cout, v, 1000000000) << std::endl; } - else if (command == ":q" || command == ":quit") + else if (command == ":q" || command == ":quit") { return false; - else if (command != "") + } else if (command != "") { throw Error(format("unknown command '%1%'") % command); - else { + } else { size_t p = line.find('='); string name; if (p != string::npos && p < line.size() && line[p + 1] != '=' && @@ -612,8 +625,9 @@ void NixRepl::addAttrsToScope(Value& attrs) { } void NixRepl::addVarToScope(const Symbol& name, Value& v) { - if (displ >= envSize) + if (displ >= envSize) { throw Error("environment full; cannot add more variables"); + } staticEnv.vars[name] = displ; env->values[displ++] = &v; varNames.insert((string)name); @@ -638,17 +652,19 @@ std::ostream& NixRepl::printValue(std::ostream& str, Value& v, std::ostream& printStringValue(std::ostream& str, const char* string) { str << "\""; - for (const char* i = string; *i; i++) - if (*i == '\"' || *i == '\\') + for (const char* i = string; *i; i++) { + if (*i == '\"' || *i == '\\') { str << "\\" << *i; - else if (*i == '\n') + } else if (*i == '\n') { str << "\\n"; - else if (*i == '\r') + } else if (*i == '\r') { str << "\\r"; - else if (*i == '\t') + } else if (*i == '\t') { str << "\\t"; - else + } else { str << *i; + } + } str << "\""; return str; } @@ -709,19 +725,21 @@ std::ostream& NixRepl::printValue(std::ostream& str, Value& v, } for (auto& i : sorted) { - if (isVarName(i.first)) + if (isVarName(i.first)) { str << i.first; - else + } else { printStringValue(str, i.first.c_str()); + } str << " = "; - if (seen.find(i.second) != seen.end()) + if (seen.find(i.second) != seen.end()) { str << "«repeated»"; - else + } else { try { printValue(str, *i.second, maxDepth - 1, seen); } catch (AssertionError& e) { str << ESC_RED "«error: " << e.msg() << "»" ESC_END; } + } str << "; "; } @@ -741,14 +759,15 @@ std::ostream& NixRepl::printValue(std::ostream& str, Value& v, str << "[ "; if (maxDepth > 0) { for (unsigned int n = 0; n < v.listSize(); ++n) { - if (seen.find(v.listElems()[n]) != seen.end()) + if (seen.find(v.listElems()[n]) != seen.end()) { str << "«repeated»"; - else + } else { try { printValue(str, *v.listElems()[n], maxDepth - 1, seen); } catch (AssertionError& e) { str << ESC_RED "«error: " << e.msg() << "»" ESC_END; } + } str << " "; } } else { diff --git a/third_party/nix/src/nix/run.cc b/third_party/nix/src/nix/run.cc index 64b883b9a3..523aa87472 100644 --- a/third_party/nix/src/nix/run.cc +++ b/third_party/nix/src/nix/run.cc @@ -31,8 +31,9 @@ struct CmdRun : InstallablesCommand { .labels({"command", "args"}) .arity(ArityAny) .handler([&](std::vector ss) { - if (ss.empty()) + if (ss.empty()) { throw UsageError("--command requires at least one argument"); + } command = ss; }); @@ -87,9 +88,10 @@ struct CmdRun : InstallablesCommand { auto accessor = store->getFSAccessor(); if (ignoreEnvironment) { - if (!unset.empty()) + if (!unset.empty()) { throw UsageError( "--unset does not make sense with --ignore-environment"); + } std::map kept; for (auto& var : keep) { @@ -106,9 +108,10 @@ struct CmdRun : InstallablesCommand { } } else { - if (!keep.empty()) + if (!keep.empty()) { throw UsageError( "--keep does not make sense without --ignore-environment"); + } for (auto& var : unset) { unsetenv(var.c_str()); @@ -191,17 +194,21 @@ void chrootHelper(int argc, char** argv) { std::string realStoreDir = argv[p++]; std::string cmd = argv[p++]; Strings args; - while (p < argc) args.push_back(argv[p++]); + while (p < argc) { + args.push_back(argv[p++]); + } #if __linux__ uid_t uid = getuid(); uid_t gid = getgid(); - if (unshare(CLONE_NEWUSER | CLONE_NEWNS) == -1) + if (unshare(CLONE_NEWUSER | CLONE_NEWNS) == -1) { /* Try with just CLONE_NEWNS in case user namespaces are specifically disabled. */ - if (unshare(CLONE_NEWNS) == -1) + if (unshare(CLONE_NEWNS) == -1) { throw SysError("setting up a private mount namespace"); + } + } /* Bind-mount realStoreDir on /nix/store. If the latter mount point doesn't already exists, we have to create a chroot @@ -218,8 +225,9 @@ void chrootHelper(int argc, char** argv) { createDirs(tmpDir + storeDir); if (mount(realStoreDir.c_str(), (tmpDir + storeDir).c_str(), "", MS_BIND, - 0) == -1) + 0) == -1) { throw SysError("mounting '%s' on '%s'", realStoreDir, storeDir); + } for (auto entry : readDirectory("/")) { auto src = "/" + entry.name; @@ -231,10 +239,12 @@ void chrootHelper(int argc, char** argv) { if (pathExists(dst)) { continue; } - if (mkdir(dst.c_str(), 0700) == -1) + if (mkdir(dst.c_str(), 0700) == -1) { throw SysError("creating directory '%s'", dst); - if (mount(src.c_str(), dst.c_str(), "", MS_BIND | MS_REC, 0) == -1) + } + if (mount(src.c_str(), dst.c_str(), "", MS_BIND | MS_REC, 0) == -1) { throw SysError("mounting '%s' on '%s'", src, dst); + } } char* cwd = getcwd(0, 0); @@ -243,14 +253,17 @@ void chrootHelper(int argc, char** argv) { } Finally freeCwd([&]() { free(cwd); }); - if (chroot(tmpDir.c_str()) == -1) + if (chroot(tmpDir.c_str()) == -1) { throw SysError(format("chrooting into '%s'") % tmpDir); + } - if (chdir(cwd) == -1) + if (chdir(cwd) == -1) { throw SysError(format("chdir to '%s' in chroot") % cwd); + } } else if (mount(realStoreDir.c_str(), storeDir.c_str(), "", MS_BIND, 0) == - -1) + -1) { throw SysError("mounting '%s' on '%s'", realStoreDir, storeDir); + } writeFile("/proc/self/setgroups", "deny"); writeFile("/proc/self/uid_map", fmt("%d %d %d", uid, uid, 1)); diff --git a/third_party/nix/src/nix/search.cc b/third_party/nix/src/nix/search.cc index 994fccd564..5978d197fe 100644 --- a/third_party/nix/src/nix/search.cc +++ b/third_party/nix/src/nix/search.cc @@ -251,13 +251,15 @@ struct CmdSearch : SourceExprCommand, MixJSON { } if (writeCache && - rename(tmpFile.c_str(), jsonCacheFileName.c_str()) == -1) + rename(tmpFile.c_str(), jsonCacheFileName.c_str()) == -1) { throw SysError("cannot rename '%s' to '%s'", tmpFile, jsonCacheFileName); + } } - if (results.size() == 0) + if (results.size() == 0) { throw Error("no results for the given search term(s)!"); + } RunPager pager; for (auto el : results) { diff --git a/third_party/nix/src/nix/show-config.cc b/third_party/nix/src/nix/show-config.cc index dba94732a9..85b3c330cd 100644 --- a/third_party/nix/src/nix/show-config.cc +++ b/third_party/nix/src/nix/show-config.cc @@ -21,8 +21,9 @@ struct CmdShowConfig : Command, MixJSON { } else { std::map settings; globalConfig.getSettings(settings); - for (auto& s : settings) + for (auto& s : settings) { std::cout << s.first + " = " + s.second.value + "\n"; + } } } }; diff --git a/third_party/nix/src/nix/sigs.cc b/third_party/nix/src/nix/sigs.cc index 0eb16b6829..eb99fc8ee5 100644 --- a/third_party/nix/src/nix/sigs.cc +++ b/third_party/nix/src/nix/sigs.cc @@ -31,8 +31,9 @@ struct CmdCopySigs : StorePathsCommand { } void run(ref store, Paths storePaths) override { - if (substituterUris.empty()) + if (substituterUris.empty()) { throw UsageError("you must specify at least one substituter using '-s'"); + } // FIXME: factor out commonality with MixVerify. std::vector> substituters; @@ -65,13 +66,15 @@ struct CmdCopySigs : StorePathsCommand { binary. */ if (info->narHash != info2->narHash || info->narSize != info2->narSize || - info->references != info2->references) + info->references != info2->references) { continue; + } - for (auto& sig : info2->sigs) + for (auto& sig : info2->sigs) { if (!info->sigs.count(sig)) { newSigs.insert(sig); } + } } catch (InvalidPath&) { } } @@ -84,8 +87,9 @@ struct CmdCopySigs : StorePathsCommand { // logger->incProgress(doneLabel); }; - for (auto& storePath : storePaths) + for (auto& storePath : storePaths) { pool.enqueue(std::bind(doPath, storePath)); + } pool.process(); @@ -112,8 +116,9 @@ struct CmdSignPaths : StorePathsCommand { std::string description() override { return "sign the specified paths"; } void run(ref store, Paths storePaths) override { - if (secretKeyFile.empty()) + if (secretKeyFile.empty()) { throw UsageError("you must specify a secret key file using '-k'"); + } SecretKey secretKey(readFile(secretKeyFile)); diff --git a/third_party/nix/src/nix/upgrade-nix.cc b/third_party/nix/src/nix/upgrade-nix.cc index 277d761ec5..dd11da0087 100644 --- a/third_party/nix/src/nix/upgrade-nix.cc +++ b/third_party/nix/src/nix/upgrade-nix.cc @@ -80,8 +80,9 @@ struct CmdUpgradeNix : MixDryRun, StoreCommand { LOG(INFO) << "verifying that '" << storePath << "' works..."; auto program = storePath + "/bin/nix-env"; auto s = runProgram(program, false, {"--version"}); - if (s.find("Nix") == std::string::npos) + if (s.find("Nix") == std::string::npos) { throw Error("could not verify that '%s' works", program); + } } { @@ -99,15 +100,17 @@ struct CmdUpgradeNix : MixDryRun, StoreCommand { Path getProfileDir(ref store) { Path where; - for (auto& dir : tokenizeString(getEnv("PATH"), ":")) + for (auto& dir : tokenizeString(getEnv("PATH"), ":")) { if (pathExists(dir + "/nix-env")) { where = dir; break; } + } - if (where == "") + if (where == "") { throw Error( "couldn't figure out how Nix is installed, so I can't upgrade it"); + } LOG(INFO) << "found Nix in '" << where << "'"; @@ -119,19 +122,22 @@ struct CmdUpgradeNix : MixDryRun, StoreCommand { // Resolve profile to /nix/var/nix/profiles/ link. while (canonPath(profileDir).find("/profiles/") == std::string::npos && - isLink(profileDir)) + isLink(profileDir)) { profileDir = readLink(profileDir); + } LOG(INFO) << "found profile '" << profileDir << "'"; Path userEnv = canonPath(profileDir, true); - if (baseNameOf(where) != "bin" || !hasSuffix(userEnv, "user-environment")) + if (baseNameOf(where) != "bin" || !hasSuffix(userEnv, "user-environment")) { throw Error("directory '%s' does not appear to be part of a Nix profile", where); + } - if (!store->isValidPath(userEnv)) + if (!store->isValidPath(userEnv)) { throw Error("directory '%s' is not in the Nix store", userEnv); + } return profileDir; } diff --git a/third_party/nix/src/nix/verify.cc b/third_party/nix/src/nix/verify.cc index 3585176ed3..6b74761ba7 100644 --- a/third_party/nix/src/nix/verify.cc +++ b/third_party/nix/src/nix/verify.cc @@ -94,10 +94,10 @@ struct CmdVerify : StorePathsCommand { if (!noTrust) { bool good = false; - if (info->ultimate && !sigsNeeded) + if (info->ultimate && !sigsNeeded) { good = true; - else { + } else { StringSet sigsSeen; size_t actualSigsNeeded = std::max(sigsNeeded, (size_t)1); size_t validSigs = 0; @@ -109,13 +109,15 @@ struct CmdVerify : StorePathsCommand { } sigsSeen.insert(sig); if (validSigs < ValidPathInfo::maxSigs && - info->checkSignature(publicKeys, sig)) + info->checkSignature(publicKeys, sig)) { validSigs++; + } } }; - if (info->isContentAddressed(*store)) + if (info->isContentAddressed(*store)) { validSigs = ValidPathInfo::maxSigs; + } doSigs(info->sigs); @@ -125,8 +127,9 @@ struct CmdVerify : StorePathsCommand { } try { auto info2 = store2->queryPathInfo(info->path); - if (info2->isContentAddressed(*store)) + if (info2->isContentAddressed(*store)) { validSigs = ValidPathInfo::maxSigs; + } doSigs(info2->sigs); } catch (InvalidPath&) { } catch (Error& e) { @@ -153,8 +156,9 @@ struct CmdVerify : StorePathsCommand { } }; - for (auto& storePath : storePaths) + for (auto& storePath : storePaths) { pool.enqueue(std::bind(doPath, storePath)); + } pool.process(); diff --git a/third_party/nix/src/nix/why-depends.cc b/third_party/nix/src/nix/why-depends.cc index 3744f4802a..baf27a6951 100644 --- a/third_party/nix/src/nix/why-depends.cc +++ b/third_party/nix/src/nix/why-depends.cc @@ -92,14 +92,16 @@ struct CmdWhyDepends : SourceExprCommand { std::map graph; - for (auto& path : closure) + for (auto& path : closure) { graph.emplace(path, Node{path, store->queryPathInfo(path)->references}); + } // Transpose the graph. - for (auto& node : graph) + for (auto& node : graph) { for (auto& ref : node.second.refs) { graph[ref].rrefs.insert(node.first); } + } /* Run Dijkstra's shortest path algorithm to get the distance of every path in the closure to 'dependency'. */ @@ -146,8 +148,10 @@ struct CmdWhyDepends : SourceExprCommand { node.visited ? "\e[38;5;244m" : "", firstPad != "" ? "=> " : "", node.path); - if (node.path == dependencyPath && !all && packagePath != dependencyPath) + if (node.path == dependencyPath && !all && + packagePath != dependencyPath) { throw BailOut(); + } if (node.visited) { return; @@ -216,10 +220,11 @@ struct CmdWhyDepends : SourceExprCommand { for (auto& hash : hashes) { auto pos = target.find(hash); - if (pos != std::string::npos) + if (pos != std::string::npos) { hits[hash].emplace_back( fmt("%s -> %s\n", p2, hilite(target, pos, storePathHashLen, getColour(hash)))); + } } } }; -- cgit 1.4.1