mirror of
https://github.com/privatevoid-net/nix-super.git
synced 2024-11-22 22:16:16 +02:00
refactor: Extract EvalState::{runDebugRepl,canDebug}
This commit is contained in:
parent
da82d67022
commit
c07500e14d
4 changed files with 37 additions and 15 deletions
|
@ -73,12 +73,7 @@ EvalErrorBuilder<T>::addTrace(PosIdx pos, std::string_view formatString, const A
|
||||||
template<class T>
|
template<class T>
|
||||||
void EvalErrorBuilder<T>::debugThrow()
|
void EvalErrorBuilder<T>::debugThrow()
|
||||||
{
|
{
|
||||||
if (error.state.debugRepl && !error.state.debugTraces.empty()) {
|
error.state.runDebugRepl(&error);
|
||||||
const DebugTrace & last = error.state.debugTraces.front();
|
|
||||||
const Env * env = &last.env;
|
|
||||||
const Expr * expr = &last.expr;
|
|
||||||
error.state.runDebugRepl(&error, *env, *expr);
|
|
||||||
}
|
|
||||||
|
|
||||||
// `EvalState` is the only class that can construct an `EvalErrorBuilder`,
|
// `EvalState` is the only class that can construct an `EvalErrorBuilder`,
|
||||||
// and it does so in dynamic storage. This is the final method called on
|
// and it does so in dynamic storage. This is the final method called on
|
||||||
|
|
|
@ -785,6 +785,24 @@ public:
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
bool EvalState::canDebug()
|
||||||
|
{
|
||||||
|
return debugRepl && !debugTraces.empty();
|
||||||
|
}
|
||||||
|
|
||||||
|
void EvalState::runDebugRepl(const Error * error)
|
||||||
|
{
|
||||||
|
if (!canDebug())
|
||||||
|
return;
|
||||||
|
|
||||||
|
assert(!debugTraces.empty());
|
||||||
|
const DebugTrace & last = debugTraces.front();
|
||||||
|
const Env & env = last.env;
|
||||||
|
const Expr & expr = last.expr;
|
||||||
|
|
||||||
|
runDebugRepl(error, env, expr);
|
||||||
|
}
|
||||||
|
|
||||||
void EvalState::runDebugRepl(const Error * error, const Env & env, const Expr & expr)
|
void EvalState::runDebugRepl(const Error * error, const Env & env, const Expr & expr)
|
||||||
{
|
{
|
||||||
// Make sure we have a debugger to run and we're not already in a debugger.
|
// Make sure we have a debugger to run and we're not already in a debugger.
|
||||||
|
|
|
@ -276,6 +276,18 @@ public:
|
||||||
return std::shared_ptr<const StaticEnv>();;
|
return std::shared_ptr<const StaticEnv>();;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/** Whether a debug repl can be started. If `false`, `runDebugRepl(error)` will return without starting a repl. */
|
||||||
|
bool canDebug();
|
||||||
|
|
||||||
|
/** Use front of `debugTraces`; see `runDebugRepl(error,env,expr)` */
|
||||||
|
void runDebugRepl(const Error * error);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Run a debug repl with the given error, environment and expression.
|
||||||
|
* @param error The error to debug, may be nullptr.
|
||||||
|
* @param env The environment to debug, matching the expression.
|
||||||
|
* @param expr The expression to debug, matching the environment.
|
||||||
|
*/
|
||||||
void runDebugRepl(const Error * error, const Env & env, const Expr & expr);
|
void runDebugRepl(const Error * error, const Env & env, const Expr & expr);
|
||||||
|
|
||||||
template<class T, typename... Args>
|
template<class T, typename... Args>
|
||||||
|
|
|
@ -780,15 +780,14 @@ static RegisterPrimOp primop_break({
|
||||||
)",
|
)",
|
||||||
.fun = [](EvalState & state, const PosIdx pos, Value * * args, Value & v)
|
.fun = [](EvalState & state, const PosIdx pos, Value * * args, Value & v)
|
||||||
{
|
{
|
||||||
if (state.debugRepl && !state.debugTraces.empty()) {
|
if (state.canDebug()) {
|
||||||
auto error = Error(ErrorInfo {
|
auto error = Error(ErrorInfo {
|
||||||
.level = lvlInfo,
|
.level = lvlInfo,
|
||||||
.msg = HintFmt("breakpoint reached"),
|
.msg = HintFmt("breakpoint reached"),
|
||||||
.pos = state.positions[pos],
|
.pos = state.positions[pos],
|
||||||
});
|
});
|
||||||
|
|
||||||
auto & dt = state.debugTraces.front();
|
state.runDebugRepl(&error);
|
||||||
state.runDebugRepl(&error, dt.env, dt.expr);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Return the value we were passed.
|
// Return the value we were passed.
|
||||||
|
@ -1018,9 +1017,8 @@ static void prim_trace(EvalState & state, const PosIdx pos, Value * * args, Valu
|
||||||
printError("trace: %1%", args[0]->string_view());
|
printError("trace: %1%", args[0]->string_view());
|
||||||
else
|
else
|
||||||
printError("trace: %1%", ValuePrinter(state, *args[0]));
|
printError("trace: %1%", ValuePrinter(state, *args[0]));
|
||||||
if (evalSettings.builtinsTraceDebugger && state.debugRepl && !state.debugTraces.empty()) {
|
if (evalSettings.builtinsTraceDebugger) {
|
||||||
const DebugTrace & last = state.debugTraces.front();
|
state.runDebugRepl(nullptr);
|
||||||
state.runDebugRepl(nullptr, last.env, last.expr);
|
|
||||||
}
|
}
|
||||||
state.forceValue(*args[1], pos);
|
state.forceValue(*args[1], pos);
|
||||||
v = *args[1];
|
v = *args[1];
|
||||||
|
@ -1060,9 +1058,8 @@ static void prim_warn(EvalState & state, const PosIdx pos, Value * * args, Value
|
||||||
if (evalSettings.builtinsAbortOnWarn) {
|
if (evalSettings.builtinsAbortOnWarn) {
|
||||||
state.error<Abort>("aborting to reveal stack trace of warning, as abort-on-warn is set").debugThrow();
|
state.error<Abort>("aborting to reveal stack trace of warning, as abort-on-warn is set").debugThrow();
|
||||||
}
|
}
|
||||||
if ((evalSettings.builtinsTraceDebugger || evalSettings.builtinsDebuggerOnWarn) && state.debugRepl && !state.debugTraces.empty()) {
|
if (evalSettings.builtinsTraceDebugger || evalSettings.builtinsDebuggerOnWarn) {
|
||||||
const DebugTrace & last = state.debugTraces.front();
|
state.runDebugRepl(nullptr);
|
||||||
state.runDebugRepl(nullptr, last.env, last.expr);
|
|
||||||
}
|
}
|
||||||
state.forceValue(*args[1], pos);
|
state.forceValue(*args[1], pos);
|
||||||
v = *args[1];
|
v = *args[1];
|
||||||
|
|
Loading…
Reference in a new issue