forked from lix-project/lix
Merge branch 'builtins.exec'
This commit is contained in:
commit
d299bd710a
|
@ -178,6 +178,58 @@ static void prim_importNative(EvalState & state, const Pos & pos, Value * * args
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* Execute a program and parse its output */
|
||||||
|
static void prim_exec(EvalState & state, const Pos & pos, Value * * args, Value & v)
|
||||||
|
{
|
||||||
|
state.forceAttrs(*args[0], pos);
|
||||||
|
auto sProgram = state.symbols.create("program");
|
||||||
|
auto sArguments = state.symbols.create("arguments");
|
||||||
|
PathSet context;
|
||||||
|
string program;
|
||||||
|
bool programSet = false;
|
||||||
|
Strings commandArgs;
|
||||||
|
for (auto & attr : *args[0]->attrs) {
|
||||||
|
if (attr.name == sProgram) {
|
||||||
|
program = state.coerceToString(*attr.pos, *attr.value, context, false, false);
|
||||||
|
programSet = true;
|
||||||
|
} else if (attr.name == sArguments) {
|
||||||
|
state.forceList(*attr.value, *attr.pos);
|
||||||
|
auto elems = attr.value->listElems();
|
||||||
|
for (unsigned int i = 0; i < attr.value->listSize(); ++i) {
|
||||||
|
commandArgs.emplace_back(state.coerceToString(*attr.pos, *elems[i], context, false, false));
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
throw EvalError(format("unexpected attribute ‘%1%’ in argument to builtins.exec, at %2%")
|
||||||
|
% attr.name % pos);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (!programSet) {
|
||||||
|
throw EvalError(format("attribute ‘programSet’ required, at %1%") % pos);
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
state.realiseContext(context);
|
||||||
|
} catch (InvalidPathError & e) {
|
||||||
|
throw EvalError(format("cannot execute ‘%1%’, since path ‘%2%’ is not valid, at %3%")
|
||||||
|
% program % e.path % pos);
|
||||||
|
}
|
||||||
|
|
||||||
|
auto output = runProgram(program, true, commandArgs);
|
||||||
|
Expr * parsed;
|
||||||
|
try {
|
||||||
|
parsed = state.parseExprFromString(output, pos.file);
|
||||||
|
} catch (Error & e) {
|
||||||
|
e.addPrefix(format("While parsing the output from ‘%1%’, at %2%\n") % program % pos);
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
state.eval(parsed, v);
|
||||||
|
} catch (Error & e) {
|
||||||
|
e.addPrefix(format("While evaluating the output from ‘%1%’, at %2%\n") % program % pos);
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/* Return a string representing the type of the expression. */
|
/* Return a string representing the type of the expression. */
|
||||||
static void prim_typeOf(EvalState & state, const Pos & pos, Value * * args, Value & v)
|
static void prim_typeOf(EvalState & state, const Pos & pos, Value * * args, Value & v)
|
||||||
{
|
{
|
||||||
|
@ -1903,8 +1955,10 @@ void EvalState::createBaseEnv()
|
||||||
mkApp(v, *baseEnv.values[baseEnvDispl - 1], *v2);
|
mkApp(v, *baseEnv.values[baseEnvDispl - 1], *v2);
|
||||||
forceValue(v);
|
forceValue(v);
|
||||||
addConstant("import", v);
|
addConstant("import", v);
|
||||||
if (settings.enableImportNative)
|
if (settings.enableNativeCode) {
|
||||||
addPrimOp("__importNative", 2, prim_importNative);
|
addPrimOp("__importNative", 2, prim_importNative);
|
||||||
|
addPrimOp("__exec", 1, prim_exec);
|
||||||
|
}
|
||||||
addPrimOp("__typeOf", 1, prim_typeOf);
|
addPrimOp("__typeOf", 1, prim_typeOf);
|
||||||
addPrimOp("isNull", 1, prim_isNull);
|
addPrimOp("isNull", 1, prim_isNull);
|
||||||
addPrimOp("__isFunction", 1, prim_isFunction);
|
addPrimOp("__isFunction", 1, prim_isFunction);
|
||||||
|
|
|
@ -67,7 +67,7 @@ Settings::Settings()
|
||||||
envKeepDerivations = false;
|
envKeepDerivations = false;
|
||||||
lockCPU = getEnv("NIX_AFFINITY_HACK", "1") == "1";
|
lockCPU = getEnv("NIX_AFFINITY_HACK", "1") == "1";
|
||||||
showTrace = false;
|
showTrace = false;
|
||||||
enableImportNative = false;
|
enableNativeCode = false;
|
||||||
netrcFile = fmt("%s/%s", nixConfDir, "netrc");
|
netrcFile = fmt("%s/%s", nixConfDir, "netrc");
|
||||||
caFile = getEnv("NIX_SSL_CERT_FILE", getEnv("SSL_CERT_FILE", "/etc/ssl/certs/ca-certificates.crt"));
|
caFile = getEnv("NIX_SSL_CERT_FILE", getEnv("SSL_CERT_FILE", "/etc/ssl/certs/ca-certificates.crt"));
|
||||||
enableImportFromDerivation = true;
|
enableImportFromDerivation = true;
|
||||||
|
@ -179,7 +179,7 @@ void Settings::update()
|
||||||
_get(envKeepDerivations, "env-keep-derivations");
|
_get(envKeepDerivations, "env-keep-derivations");
|
||||||
_get(sshSubstituterHosts, "ssh-substituter-hosts");
|
_get(sshSubstituterHosts, "ssh-substituter-hosts");
|
||||||
_get(useSshSubstituter, "use-ssh-substituter");
|
_get(useSshSubstituter, "use-ssh-substituter");
|
||||||
_get(enableImportNative, "allow-unsafe-native-code-during-evaluation");
|
_get(enableNativeCode, "allow-unsafe-native-code-during-evaluation");
|
||||||
_get(useCaseHack, "use-case-hack");
|
_get(useCaseHack, "use-case-hack");
|
||||||
_get(preBuildHook, "pre-build-hook");
|
_get(preBuildHook, "pre-build-hook");
|
||||||
_get(keepGoing, "keep-going");
|
_get(keepGoing, "keep-going");
|
||||||
|
|
|
@ -181,8 +181,8 @@ struct Settings {
|
||||||
/* Whether to show a stack trace if Nix evaluation fails. */
|
/* Whether to show a stack trace if Nix evaluation fails. */
|
||||||
bool showTrace;
|
bool showTrace;
|
||||||
|
|
||||||
/* Whether the importNative primop should be enabled */
|
/* Whether native-code enabling primops should be enabled */
|
||||||
bool enableImportNative;
|
bool enableNativeCode;
|
||||||
|
|
||||||
/* The hook to run just before a build to set derivation-specific
|
/* The hook to run just before a build to set derivation-specific
|
||||||
build settings */
|
build settings */
|
||||||
|
|
Loading…
Reference in a new issue