diff libinterp/corefcn/interpreter.cc @ 29292:eb1e10abe9d5

use method in interpreter class to interrupt interpreter execution in GUI * interpreter.h, interpreter.cc (interpreter::interrupt): New function. * interpreter-qobject.h, interpreter-qobject.cc (interpreter_qobject::interrupt): New function. * octave-qobject.h, octave-qobject.cc (octave_qobject::interpreter_interrupt): New slot. * terminal-dock-widget.h, terminal-dock-widget.cc (): (terminal_dock_widget::terminal_dock_widget): Connect m_terminal interrupt_signal to oct_qobj interpreter_interrupt slot. (terminal_dock_widget::terminal_interrupt): Delete slot. Action is now performed in interpreter::interrupt method. (terminal_dock_widget::interrupt_signal): Delete signal.
author John W. Eaton <jwe@octave.org>
date Tue, 12 Jan 2021 21:01:42 -0500
parents 6dd456257d81
children 8784f20b9b8c
line wrap: on
line diff
--- a/libinterp/corefcn/interpreter.cc	Mon Jan 11 00:46:17 2021 -0500
+++ b/libinterp/corefcn/interpreter.cc	Tue Jan 12 21:01:42 2021 -0500
@@ -42,6 +42,7 @@
 #include "lo-blas-proto.h"
 #include "lo-error.h"
 #include "oct-env.h"
+#include "quit.h"
 #include "str-vec.h"
 #include "signal-wrappers.h"
 #include "unistd-wrappers.h"
@@ -1703,6 +1704,34 @@
     return m_evaluator.autoloaded_functions ();
   }
 
+  // May be used to send an interrupt signal to the the interpreter from
+  // another thread (for example, the GUI).
+
+  void interpreter::interrupt (void)
+  {
+    static int sigint = 0;
+    static bool first = true;
+
+    if (first)
+      {
+        octave_get_sig_number ("SIGINT", &sigint);
+        first = false;
+      }
+
+    // Send SIGINT to all other processes in our process group.  The
+    // signal handler for SIGINT will set a global variable indicating
+    // an interrupt has happened.  That variable is checked in many
+    // places in the Octave interpreter and eventually results in an
+    // interrupt_exception being thrown.  Finally, that exception is
+    // caught and returns control to one of the read-eval-print loops or
+    // to the server loop.  We use a signal instead of just setting the
+    // global variables here so that we will probably send interrupt
+    // signals to any subprocesses as well as interrupt execution of the
+    // interpreter.
+
+    octave_kill_wrapper (0, sigint);
+  }
+
   void interpreter::handle_exception (const execution_exception& ee)
   {
     m_error_system.save_exception (ee);