diff libinterp/corefcn/toplev.cc @ 25284:78fb24bdd8bb stable

unblock async signals before executing subprocess (bug #53635) * sighandlers.cc (sigint_handler): Delete. (generic_sig_handler): Handle sigint and sigbreak here. (catch_interrupts): Use generic_sig_handler instead of sigint_handler. (F__show_signal_mask__): New function. * signal-wrappers.h, signal-wrappers.c (octave_alloc_signal_mask, octave_free_signal_mask, octave_get_signal_mask, octave_set_signal_mask): New functions. * toplev.cc (get_signal_mask, restore_signal_mask): New static functions. (Fsystem): Save signal mask. Unblock async signals before executing subprocess. Use unwind_protect frame to restore previous mask.
author John W. Eaton <jwe@octave.org>
date Thu, 19 Apr 2018 01:58:44 -0400
parents 6652d3823428
children cb1606f78f6b 9771111f04f4
line wrap: on
line diff
--- a/libinterp/corefcn/toplev.cc	Wed Apr 18 15:18:47 2018 -0400
+++ b/libinterp/corefcn/toplev.cc	Thu Apr 19 01:58:44 2018 -0400
@@ -42,6 +42,7 @@
 #include "oct-fftw.h"
 #include "oct-locbuf.h"
 #include "oct-syscalls.h"
+#include "signal-wrappers.h"
 #include "str-vec.h"
 #include "wait-for-input.h"
 
@@ -149,6 +150,28 @@
   return retval;
 }
 
+// Combine alloc+get in one action.
+
+static void *
+get_signal_mask (void)
+{
+  void *mask = octave_alloc_signal_mask ();
+
+  octave_get_signal_mask (mask);
+
+  return mask;
+}
+
+// Combine set+free in one action.
+
+static void
+restore_signal_mask (void *mask)
+{
+  octave_set_signal_mask (mask);
+
+  octave_free_signal_mask (mask);
+}
+
 enum system_exec_type { et_sync, et_async };
 
 DEFUN (system, args, nargout,
@@ -232,9 +255,6 @@
 
   octave_value_list retval;
 
-  // FIXME: Is this unwind_protect frame needed anymore (12/16/15)?
-  octave::unwind_protect frame;
-
   bool return_output = (nargin == 1 && nargout > 1);
 
   if (nargin > 1)
@@ -260,6 +280,12 @@
     cmd_str = '"' + cmd_str + '"';
 #endif
 
+  octave::unwind_protect frame;
+
+  frame.add_fcn (restore_signal_mask, get_signal_mask ());
+
+  octave_unblock_async_signals ();
+
   if (type == et_async)
     retval(0) = octave_async_system_wrapper (cmd_str.c_str ());
   else if (return_output)