From 0629601da1d163a059fa19004256961f8ecdeb78 Mon Sep 17 00:00:00 2001 From: Eelco Dolstra Date: Tue, 12 Jun 2018 17:26:36 +0200 Subject: Move EvalState from the stack to the heap EvalState contains a few counters (e.g. nrValues) that increase quickly enough that they end up being interpreted as pointers by the garbage collector. Moving it to the heap makes them invisible to the garbage collector. This reduces the max RSS doing 100 evaluations of nixos.tests.firefox.x86_64-linux.drvPath from 455 MiB to 292 MiB. Note: ideally, allocations would be much further up in the 64-bit address space to reduce the odds of an integer being misinterpreted as a pointer. Maybe we can use some linker magic to move the .bss segment to a higher address. --- src/nix-build/nix-build.cc | 28 ++++++++++++++-------------- 1 file changed, 14 insertions(+), 14 deletions(-) (limited to 'src/nix-build/nix-build.cc') diff --git a/src/nix-build/nix-build.cc b/src/nix-build/nix-build.cc index 21d99878a5..de0e9118fd 100755 --- a/src/nix-build/nix-build.cc +++ b/src/nix-build/nix-build.cc @@ -239,10 +239,10 @@ void mainWrapped(int argc, char * * argv) auto store = openStore(); - EvalState state(myArgs.searchPath, store); - state.repair = repair; + auto state = std::make_unique(myArgs.searchPath, store); + state->repair = repair; - Bindings & autoArgs = *myArgs.getAutoArgs(state); + Bindings & autoArgs = *myArgs.getAutoArgs(*state); if (packages) { std::ostringstream joined; @@ -268,7 +268,7 @@ void mainWrapped(int argc, char * * argv) std::vector exprs; if (readStdin) - exprs = {state.parseStdin()}; + exprs = {state->parseStdin()}; else for (auto i : left) { auto absolute = i; @@ -276,13 +276,13 @@ void mainWrapped(int argc, char * * argv) absolute = canonPath(absPath(i), true); } catch (Error e) {}; if (fromArgs) - exprs.push_back(state.parseExprFromString(i, absPath("."))); + exprs.push_back(state->parseExprFromString(i, absPath("."))); else if (store->isStorePath(absolute) && std::regex_match(absolute, std::regex(".*\\.drv(!.*)?"))) - drvs.push_back(DrvInfo(state, store, absolute)); + drvs.push_back(DrvInfo(*state, store, absolute)); else /* If we're in a #! script, interpret filenames relative to the script. */ - exprs.push_back(state.parseExprFromFile(resolveExprPath(state.checkSourcePath(lookupFileArg(state, + exprs.push_back(state->parseExprFromFile(resolveExprPath(state->checkSourcePath(lookupFileArg(*state, inShebang && !packages ? absPath(i, absPath(dirOf(script))) : i))))); } @@ -291,12 +291,12 @@ void mainWrapped(int argc, char * * argv) for (auto e : exprs) { Value vRoot; - state.eval(e, vRoot); + state->eval(e, vRoot); for (auto & i : attrPaths) { - Value & v(*findAlongAttrPath(state, i, autoArgs, vRoot)); - state.forceValue(v); - getDerivations(state, v, "", autoArgs, drvs, false); + Value & v(*findAlongAttrPath(*state, i, autoArgs, vRoot)); + state->forceValue(v); + getDerivations(*state, v, "", autoArgs, drvs, false); } } @@ -332,12 +332,12 @@ void mainWrapped(int argc, char * * argv) if (shell == "") { try { - auto expr = state.parseExprFromString("(import {}).bashInteractive", absPath(".")); + auto expr = state->parseExprFromString("(import {}).bashInteractive", absPath(".")); Value v; - state.eval(expr, v); + state->eval(expr, v); - auto drv = getDerivation(state, v, false); + auto drv = getDerivation(*state, v, false); if (!drv) throw Error("the 'bashInteractive' attribute in did not evaluate to a derivation"); -- cgit 1.4.1