diff --git a/doc/manual/rl-next/repl-interrupt.md b/doc/manual/rl-next/repl-interrupt.md new file mode 100644 index 000000000..61a8ab71e --- /dev/null +++ b/doc/manual/rl-next/repl-interrupt.md @@ -0,0 +1,8 @@ +--- +synopsis: Interrupting builds in the REPL works more than once +cls: 1097 +--- + +Builds in the REPL can be interrupted by pressing Ctrl+C. +Previously, this only worked once per REPL session; further attempts would be ignored. +This issue is now fixed, so that builds can be canceled consistently. diff --git a/src/libmain/shared.cc b/src/libmain/shared.cc index 9d4dd41ed..96ecbac8f 100644 --- a/src/libmain/shared.cc +++ b/src/libmain/shared.cc @@ -320,16 +320,7 @@ int handleExceptions(const std::string & programName, std::function fun) std::string error = ANSI_RED "error:" ANSI_NORMAL " "; try { - try { - fun(); - } catch (...) { - /* Subtle: we have to make sure that any `interrupted' - condition is discharged before we reach printMsg() - below, since otherwise it will throw an (uncaught) - exception. */ - setInterruptThrown(); - throw; - } + fun(); } catch (Exit & e) { return e.status; } catch (UsageError & e) { diff --git a/src/libutil/signals.cc b/src/libutil/signals.cc index f5c79b325..41fdc9dc8 100644 --- a/src/libutil/signals.cc +++ b/src/libutil/signals.cc @@ -9,21 +9,14 @@ namespace nix { std::atomic _isInterrupted = false; -static thread_local bool interruptThrown = false; thread_local std::function interruptCheck; -void setInterruptThrown() -{ - interruptThrown = true; -} - void _interrupted() { /* Block user interrupts while an exception is being handled. Throwing an exception while another exception is being handled kills the program! */ - if (!interruptThrown && !std::uncaught_exceptions()) { - interruptThrown = true; + if (!std::uncaught_exceptions()) { throw Interrupted("interrupted by the user"); } } diff --git a/src/libutil/signals.hh b/src/libutil/signals.hh index c58dc37cf..71593df95 100644 --- a/src/libutil/signals.hh +++ b/src/libutil/signals.hh @@ -22,8 +22,6 @@ extern std::atomic _isInterrupted; extern thread_local std::function interruptCheck; -void setInterruptThrown(); - void _interrupted(); void inline checkInterrupt()