nix-shell: Use bashInteractive from <nixpkgs>
This adds about 0.1s to nix-shell runtime in the case where bashInteractive already exists. See discussion at https://github.com/NixOS/nixpkgs/issues/27493.
This commit is contained in:
parent
57a30e101b
commit
c94f3d5575
5 changed files with 54 additions and 13 deletions
|
@ -267,15 +267,14 @@ static bool getDerivation(EvalState & state, Value & v,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
bool getDerivation(EvalState & state, Value & v, DrvInfo & drv,
|
std::experimental::optional<DrvInfo> getDerivation(EvalState & state, Value & v,
|
||||||
bool ignoreAssertionFailures)
|
bool ignoreAssertionFailures)
|
||||||
{
|
{
|
||||||
Done done;
|
Done done;
|
||||||
DrvInfos drvs;
|
DrvInfos drvs;
|
||||||
getDerivation(state, v, "", drvs, done, ignoreAssertionFailures);
|
getDerivation(state, v, "", drvs, done, ignoreAssertionFailures);
|
||||||
if (drvs.size() != 1) return false;
|
if (drvs.size() != 1) return {};
|
||||||
drv = drvs.front();
|
return std::move(drvs.front());
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -75,10 +75,10 @@ typedef list<DrvInfo> DrvInfos;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
/* If value `v' denotes a derivation, store information about the
|
/* If value `v' denotes a derivation, return a DrvInfo object
|
||||||
derivation in `drv' and return true. Otherwise, return false. */
|
describing it. Otherwise return nothing. */
|
||||||
bool getDerivation(EvalState & state, Value & v, DrvInfo & drv,
|
std::experimental::optional<DrvInfo> getDerivation(EvalState & state,
|
||||||
bool ignoreAssertionFailures);
|
Value & v, bool ignoreAssertionFailures);
|
||||||
|
|
||||||
void getDerivations(EvalState & state, Value & v, const string & pathPrefix,
|
void getDerivations(EvalState & state, Value & v, const string & pathPrefix,
|
||||||
Bindings & autoArgs, DrvInfos & drvs,
|
Bindings & autoArgs, DrvInfos & drvs,
|
||||||
|
|
|
@ -4,6 +4,6 @@ nix-build_DIR := $(d)
|
||||||
|
|
||||||
nix-build_SOURCES := $(d)/nix-build.cc
|
nix-build_SOURCES := $(d)/nix-build.cc
|
||||||
|
|
||||||
nix-build_LIBS = libmain libstore libutil libformat
|
nix-build_LIBS = libmain libexpr libstore libutil libformat
|
||||||
|
|
||||||
$(eval $(call install-symlink, nix-build, $(bindir)/nix-shell))
|
$(eval $(call install-symlink, nix-build, $(bindir)/nix-shell))
|
||||||
|
|
|
@ -13,6 +13,8 @@
|
||||||
#include "affinity.hh"
|
#include "affinity.hh"
|
||||||
#include "util.hh"
|
#include "util.hh"
|
||||||
#include "shared.hh"
|
#include "shared.hh"
|
||||||
|
#include "eval.hh"
|
||||||
|
#include "get-drvs.hh"
|
||||||
|
|
||||||
using namespace nix;
|
using namespace nix;
|
||||||
using namespace std::string_literals;
|
using namespace std::string_literals;
|
||||||
|
@ -75,6 +77,8 @@ int main(int argc, char ** argv)
|
||||||
{
|
{
|
||||||
return handleExceptions(argv[0], [&]() {
|
return handleExceptions(argv[0], [&]() {
|
||||||
initNix();
|
initNix();
|
||||||
|
initGC();
|
||||||
|
|
||||||
auto store = openStore();
|
auto store = openStore();
|
||||||
auto dryRun = false;
|
auto dryRun = false;
|
||||||
auto verbose = false;
|
auto verbose = false;
|
||||||
|
@ -88,6 +92,7 @@ int main(int argc, char ** argv)
|
||||||
Strings instArgs;
|
Strings instArgs;
|
||||||
Strings buildArgs;
|
Strings buildArgs;
|
||||||
Strings exprs;
|
Strings exprs;
|
||||||
|
Strings searchPath;
|
||||||
|
|
||||||
auto shell = getEnv("SHELL", "/bin/sh");
|
auto shell = getEnv("SHELL", "/bin/sh");
|
||||||
std::string envCommand; // interactive shell
|
std::string envCommand; // interactive shell
|
||||||
|
@ -320,6 +325,8 @@ int main(int argc, char ** argv)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
EvalState state(searchPath, store);
|
||||||
|
|
||||||
if (packages && fromArgs) {
|
if (packages && fromArgs) {
|
||||||
throw UsageError("‘-p’ and ‘-E’ are mutually exclusive");
|
throw UsageError("‘-p’ and ‘-E’ are mutually exclusive");
|
||||||
}
|
}
|
||||||
|
@ -465,7 +472,42 @@ int main(int argc, char ** argv)
|
||||||
|
|
||||||
auto envPtrs = stringsToCharPtrs(envStrs);
|
auto envPtrs = stringsToCharPtrs(envStrs);
|
||||||
|
|
||||||
auto shell = getEnv("NIX_BUILD_SHELL", "bash");
|
auto shell = getEnv("NIX_BUILD_SHELL", "");
|
||||||
|
|
||||||
|
if (shell == "") {
|
||||||
|
|
||||||
|
try {
|
||||||
|
|
||||||
|
auto expr = state.parseExprFromString("(import <nixpkgs> {}).bashInteractive", absPath("."));
|
||||||
|
|
||||||
|
Value v;
|
||||||
|
state.eval(expr, v);
|
||||||
|
|
||||||
|
auto drv = getDerivation(state, v, false);
|
||||||
|
if (!drv)
|
||||||
|
throw Error("the ‘bashInteractive’ attribute in <nixpkgs> did not evaluate to a derivation");
|
||||||
|
|
||||||
|
auto drvPath = drv->queryDrvPath();
|
||||||
|
|
||||||
|
unsigned long long downloadSize, narSize;
|
||||||
|
PathSet willBuild, willSubstitute, unknown;
|
||||||
|
store->queryMissing({drvPath},
|
||||||
|
willBuild, willSubstitute, unknown, downloadSize, narSize);
|
||||||
|
|
||||||
|
if (settings.printMissing)
|
||||||
|
printMissing(ref<Store>(store), willBuild, willSubstitute, unknown, downloadSize, narSize);
|
||||||
|
|
||||||
|
store->buildPaths({drvPath});
|
||||||
|
|
||||||
|
shell = drv->queryOutPath() + "/bin/bash";
|
||||||
|
if (!pathExists(shell))
|
||||||
|
throw Error("expected shell ‘%s’ to exist, but it doesn't", shell);
|
||||||
|
|
||||||
|
} catch (Error & e) {
|
||||||
|
printError("warning: %s; will use bash from your environment", e.what());
|
||||||
|
shell = "bash";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
environ = envPtrs.data();
|
environ = envPtrs.data();
|
||||||
|
|
||||||
|
|
|
@ -292,10 +292,10 @@ bool isVarName(const string & s)
|
||||||
|
|
||||||
|
|
||||||
Path NixRepl::getDerivationPath(Value & v) {
|
Path NixRepl::getDerivationPath(Value & v) {
|
||||||
DrvInfo drvInfo(state);
|
auto drvInfo = getDerivation(state, v, false);
|
||||||
if (!getDerivation(state, v, drvInfo, false))
|
if (!drvInfo)
|
||||||
throw Error("expression does not evaluate to a derivation, so I can't build it");
|
throw Error("expression does not evaluate to a derivation, so I can't build it");
|
||||||
Path drvPath = drvInfo.queryDrvPath();
|
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");
|
throw Error("expression did not evaluate to a valid derivation");
|
||||||
return drvPath;
|
return drvPath;
|
||||||
|
|
Loading…
Reference in a new issue