aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorPaul Eggert2016-07-24 11:10:09 +0200
committerPaul Eggert2016-07-25 00:38:34 +0200
commit50cc08bf6e6cdc96dcdcbef388cf9cf76a15f81a (patch)
tree9cfd5f799262e0ba85d7213113bdb20302196e74 /src
parent2c2b0cd07c143e33af9f7237ef4819c28764a90f (diff)
downloademacs-50cc08bf6e6cdc96dcdcbef388cf9cf76a15f81a.tar.gz
emacs-50cc08bf6e6cdc96dcdcbef388cf9cf76a15f81a.zip
‘signal’ no longer returns
Although for decades ‘signal’ has been documented to not return, a corner case in the Lisp debugger causes ‘signal’ to return. Remove the corner case and adjust Emacs internals accordingly. An alternative would be to document the corner case, but this would complicate the Lisp API unnecessarily. (Bug#24047) * src/eval.c (signal_or_quit): New function, with most of the old contents of Fsignal. (quit): New function, which uses signal_or_quit and which might return. All keyboard-based callers of Fsignal (Qquit, Qnil) changed to use this new function instead. (Fsignal): Use signal_or_quit. Now _Noreturn. All callers changed. (xsignal): Move to lisp.h. * src/lisp.h (xsignal): Now an inline function, as it's now just an alias for Fsignal.
Diffstat (limited to 'src')
-rw-r--r--src/bytecode.c2
-rw-r--r--src/charset.c6
-rw-r--r--src/coding.c6
-rw-r--r--src/eval.c37
-rw-r--r--src/fileio.c2
-rw-r--r--src/keyboard.c6
-rw-r--r--src/lisp.h7
-rw-r--r--src/nsmenu.m2
-rw-r--r--src/term.c2
-rw-r--r--src/w32fns.c2
-rw-r--r--src/w32menu.c9
-rw-r--r--src/xfns.c6
-rw-r--r--src/xmenu.c6
13 files changed, 54 insertions, 39 deletions
diff --git a/src/bytecode.c b/src/bytecode.c
index 05bc9fcdb08..ee1b79f1826 100644
--- a/src/bytecode.c
+++ b/src/bytecode.c
@@ -386,7 +386,7 @@ relocate_byte_stack (void)
386 Vquit_flag = Qnil; \ 386 Vquit_flag = Qnil; \
387 if (EQ (Vthrow_on_input, flag)) \ 387 if (EQ (Vthrow_on_input, flag)) \
388 Fthrow (Vthrow_on_input, Qt); \ 388 Fthrow (Vthrow_on_input, Qt); \
389 Fsignal (Qquit, Qnil); \ 389 quit (); \
390 } \ 390 } \
391 else if (pending_signals) \ 391 else if (pending_signals) \
392 process_pending_signals (); \ 392 process_pending_signals (); \
diff --git a/src/charset.c b/src/charset.c
index 95a9c577d52..05469aa2650 100644
--- a/src/charset.c
+++ b/src/charset.c
@@ -843,9 +843,9 @@ usage: (define-charset-internal ...) */)
843 int nchars; 843 int nchars;
844 844
845 if (nargs != charset_arg_max) 845 if (nargs != charset_arg_max)
846 return Fsignal (Qwrong_number_of_arguments, 846 Fsignal (Qwrong_number_of_arguments,
847 Fcons (intern ("define-charset-internal"), 847 Fcons (intern ("define-charset-internal"),
848 make_number (nargs))); 848 make_number (nargs)));
849 849
850 attrs = Fmake_vector (make_number (charset_attr_max), Qnil); 850 attrs = Fmake_vector (make_number (charset_attr_max), Qnil);
851 851
diff --git a/src/coding.c b/src/coding.c
index 29c90f0a401..a8ddc817565 100644
--- a/src/coding.c
+++ b/src/coding.c
@@ -10546,9 +10546,9 @@ usage: (define-coding-system-internal ...) */)
10546 return Qnil; 10546 return Qnil;
10547 10547
10548 short_args: 10548 short_args:
10549 return Fsignal (Qwrong_number_of_arguments, 10549 Fsignal (Qwrong_number_of_arguments,
10550 Fcons (intern ("define-coding-system-internal"), 10550 Fcons (intern ("define-coding-system-internal"),
10551 make_number (nargs))); 10551 make_number (nargs)));
10552} 10552}
10553 10553
10554 10554
diff --git a/src/eval.c b/src/eval.c
index 72facd5db64..33b82f74b64 100644
--- a/src/eval.c
+++ b/src/eval.c
@@ -1431,6 +1431,7 @@ push_handler_nosignal (Lisp_Object tag_ch_val, enum handlertype handlertype)
1431} 1431}
1432 1432
1433 1433
1434static Lisp_Object signal_or_quit (Lisp_Object, Lisp_Object, bool);
1434static Lisp_Object find_handler_clause (Lisp_Object, Lisp_Object); 1435static Lisp_Object find_handler_clause (Lisp_Object, Lisp_Object);
1435static bool maybe_call_debugger (Lisp_Object conditions, Lisp_Object sig, 1436static bool maybe_call_debugger (Lisp_Object conditions, Lisp_Object sig,
1436 Lisp_Object data); 1437 Lisp_Object data);
@@ -1444,7 +1445,7 @@ process_quit_flag (void)
1444 Fkill_emacs (Qnil); 1445 Fkill_emacs (Qnil);
1445 if (EQ (Vthrow_on_input, flag)) 1446 if (EQ (Vthrow_on_input, flag))
1446 Fthrow (Vthrow_on_input, Qt); 1447 Fthrow (Vthrow_on_input, Qt);
1447 Fsignal (Qquit, Qnil); 1448 quit ();
1448} 1449}
1449 1450
1450DEFUN ("signal", Fsignal, Ssignal, 2, 2, 0, 1451DEFUN ("signal", Fsignal, Ssignal, 2, 2, 0,
@@ -1460,9 +1461,29 @@ DATA should be a list. Its elements are printed as part of the error message.
1460See Info anchor `(elisp)Definition of signal' for some details on how this 1461See Info anchor `(elisp)Definition of signal' for some details on how this
1461error message is constructed. 1462error message is constructed.
1462If the signal is handled, DATA is made available to the handler. 1463If the signal is handled, DATA is made available to the handler.
1463See also the function `condition-case'. */) 1464See also the function `condition-case'. */
1465 attributes: noreturn)
1464 (Lisp_Object error_symbol, Lisp_Object data) 1466 (Lisp_Object error_symbol, Lisp_Object data)
1465{ 1467{
1468 signal_or_quit (error_symbol, data, false);
1469 eassume (false);
1470}
1471
1472/* Quit, in response to a keyboard quit request. */
1473Lisp_Object
1474quit (void)
1475{
1476 return signal_or_quit (Qquit, Qnil, true);
1477}
1478
1479/* Signal an error, or quit. ERROR_SYMBOL and DATA are as with Fsignal.
1480 If KEYBOARD_QUIT, this is a quit; ERROR_SYMBOL should be
1481 Qquit and DATA should be Qnil, and this function may return.
1482 Otherwise this function is like Fsignal and does not return. */
1483
1484static Lisp_Object
1485signal_or_quit (Lisp_Object error_symbol, Lisp_Object data, bool keyboard_quit)
1486{
1466 /* When memory is full, ERROR-SYMBOL is nil, 1487 /* When memory is full, ERROR-SYMBOL is nil,
1467 and DATA is (REAL-ERROR-SYMBOL . REAL-DATA). 1488 and DATA is (REAL-ERROR-SYMBOL . REAL-DATA).
1468 That is a special case--don't do this in other situations. */ 1489 That is a special case--don't do this in other situations. */
@@ -1542,7 +1563,7 @@ See also the function `condition-case'. */)
1542 = maybe_call_debugger (conditions, error_symbol, data); 1563 = maybe_call_debugger (conditions, error_symbol, data);
1543 /* We can't return values to code which signaled an error, but we 1564 /* We can't return values to code which signaled an error, but we
1544 can continue code which has signaled a quit. */ 1565 can continue code which has signaled a quit. */
1545 if (debugger_called && EQ (real_error_symbol, Qquit)) 1566 if (keyboard_quit && debugger_called && EQ (real_error_symbol, Qquit))
1546 return Qnil; 1567 return Qnil;
1547 } 1568 }
1548 1569
@@ -1569,16 +1590,6 @@ See also the function `condition-case'. */)
1569 fatal ("%s", SDATA (string)); 1590 fatal ("%s", SDATA (string));
1570} 1591}
1571 1592
1572/* Internal version of Fsignal that never returns.
1573 Used for anything but Qquit (which can return from Fsignal). */
1574
1575void
1576xsignal (Lisp_Object error_symbol, Lisp_Object data)
1577{
1578 Fsignal (error_symbol, data);
1579 emacs_abort ();
1580}
1581
1582/* Like xsignal, but takes 0, 1, 2, or 3 args instead of a list. */ 1593/* Like xsignal, but takes 0, 1, 2, or 3 args instead of a list. */
1583 1594
1584void 1595void
diff --git a/src/fileio.c b/src/fileio.c
index b1f9d3cf73a..66ea761ca56 100644
--- a/src/fileio.c
+++ b/src/fileio.c
@@ -4513,7 +4513,7 @@ by calling `format-decode', which see. */)
4513 PT - BEG, Z - PT - inserted); 4513 PT - BEG, Z - PT - inserted);
4514 4514
4515 if (read_quit) 4515 if (read_quit)
4516 Fsignal (Qquit, Qnil); 4516 quit ();
4517 4517
4518 /* Retval needs to be dealt with in all cases consistently. */ 4518 /* Retval needs to be dealt with in all cases consistently. */
4519 if (NILP (val)) 4519 if (NILP (val))
diff --git a/src/keyboard.c b/src/keyboard.c
index 8901ff055e7..ed4968486c3 100644
--- a/src/keyboard.c
+++ b/src/keyboard.c
@@ -696,7 +696,7 @@ recursive_edit_1 (void)
696 696
697 val = command_loop (); 697 val = command_loop ();
698 if (EQ (val, Qt)) 698 if (EQ (val, Qt))
699 Fsignal (Qquit, Qnil); 699 quit ();
700 /* Handle throw from read_minibuf when using minibuffer 700 /* Handle throw from read_minibuf when using minibuffer
701 while it's active but we're in another window. */ 701 while it's active but we're in another window. */
702 if (STRINGP (val)) 702 if (STRINGP (val))
@@ -7581,7 +7581,7 @@ menu_item_eval_property_1 (Lisp_Object arg)
7581 /* If we got a quit from within the menu computation, 7581 /* If we got a quit from within the menu computation,
7582 quit all the way out of it. This takes care of C-] in the debugger. */ 7582 quit all the way out of it. This takes care of C-] in the debugger. */
7583 if (CONSP (arg) && EQ (XCAR (arg), Qquit)) 7583 if (CONSP (arg) && EQ (XCAR (arg), Qquit))
7584 Fsignal (Qquit, Qnil); 7584 quit ();
7585 7585
7586 return Qnil; 7586 return Qnil;
7587} 7587}
@@ -10407,7 +10407,7 @@ handle_interrupt (bool in_signal_handler)
10407 immediate_quit = false; 10407 immediate_quit = false;
10408 pthread_sigmask (SIG_SETMASK, &empty_mask, 0); 10408 pthread_sigmask (SIG_SETMASK, &empty_mask, 0);
10409 saved = gl_state; 10409 saved = gl_state;
10410 Fsignal (Qquit, Qnil); 10410 quit ();
10411 gl_state = saved; 10411 gl_state = saved;
10412 } 10412 }
10413 else 10413 else
diff --git a/src/lisp.h b/src/lisp.h
index 39877d7bb4d..089f3977cd2 100644
--- a/src/lisp.h
+++ b/src/lisp.h
@@ -3879,7 +3879,12 @@ extern void run_hook_with_args_2 (Lisp_Object, Lisp_Object, Lisp_Object);
3879extern Lisp_Object run_hook_with_args (ptrdiff_t nargs, Lisp_Object *args, 3879extern Lisp_Object run_hook_with_args (ptrdiff_t nargs, Lisp_Object *args,
3880 Lisp_Object (*funcall) 3880 Lisp_Object (*funcall)
3881 (ptrdiff_t nargs, Lisp_Object *args)); 3881 (ptrdiff_t nargs, Lisp_Object *args));
3882extern _Noreturn void xsignal (Lisp_Object, Lisp_Object); 3882extern Lisp_Object quit (void);
3883INLINE _Noreturn void
3884xsignal (Lisp_Object error_symbol, Lisp_Object data)
3885{
3886 Fsignal (error_symbol, data);
3887}
3883extern _Noreturn void xsignal0 (Lisp_Object); 3888extern _Noreturn void xsignal0 (Lisp_Object);
3884extern _Noreturn void xsignal1 (Lisp_Object, Lisp_Object); 3889extern _Noreturn void xsignal1 (Lisp_Object, Lisp_Object);
3885extern _Noreturn void xsignal2 (Lisp_Object, Lisp_Object, Lisp_Object); 3890extern _Noreturn void xsignal2 (Lisp_Object, Lisp_Object, Lisp_Object);
diff --git a/src/nsmenu.m b/src/nsmenu.m
index 83ded6daca3..d1f4b020bb0 100644
--- a/src/nsmenu.m
+++ b/src/nsmenu.m
@@ -1843,7 +1843,7 @@ ns_popup_dialog (struct frame *f, Lisp_Object header, Lisp_Object contents)
1843 1843
1844 if (EQ (ret, Qundefined) && window_closed) 1844 if (EQ (ret, Qundefined) && window_closed)
1845 /* Make close button pressed equivalent to C-g. */ 1845 /* Make close button pressed equivalent to C-g. */
1846 Fsignal (Qquit, Qnil); 1846 quit ();
1847 1847
1848 return ret; 1848 return ret;
1849} 1849}
diff --git a/src/term.c b/src/term.c
index 81908b370a5..d54ff115f9d 100644
--- a/src/term.c
+++ b/src/term.c
@@ -3759,7 +3759,7 @@ tty_menu_show (struct frame *f, int x, int y, int menuflags,
3759 /* Make "Cancel" equivalent to C-g unless FOR_CLICK (which means 3759 /* Make "Cancel" equivalent to C-g unless FOR_CLICK (which means
3760 the menu was invoked with a mouse event as POSITION). */ 3760 the menu was invoked with a mouse event as POSITION). */
3761 if (!(menuflags & MENU_FOR_CLICK)) 3761 if (!(menuflags & MENU_FOR_CLICK))
3762 Fsignal (Qquit, Qnil); 3762 quit ();
3763 break; 3763 break;
3764 } 3764 }
3765 3765
diff --git a/src/w32fns.c b/src/w32fns.c
index d6b54d19a19..584e311230e 100644
--- a/src/w32fns.c
+++ b/src/w32fns.c
@@ -7584,7 +7584,7 @@ value of DIR as in previous invocations; this is standard Windows behavior. */)
7584 7584
7585 /* Make "Cancel" equivalent to C-g. */ 7585 /* Make "Cancel" equivalent to C-g. */
7586 if (NILP (filename)) 7586 if (NILP (filename))
7587 Fsignal (Qquit, Qnil); 7587 quit ();
7588 7588
7589 return filename; 7589 return filename;
7590} 7590}
diff --git a/src/w32menu.c b/src/w32menu.c
index 13296d9d855..7c66360becd 100644
--- a/src/w32menu.c
+++ b/src/w32menu.c
@@ -827,7 +827,7 @@ w32_menu_show (struct frame *f, int x, int y, int menuflags,
827 { 827 {
828 unblock_input (); 828 unblock_input ();
829 /* Make "Cancel" equivalent to C-g. */ 829 /* Make "Cancel" equivalent to C-g. */
830 Fsignal (Qquit, Qnil); 830 quit ();
831 } 831 }
832 832
833 unblock_input (); 833 unblock_input ();
@@ -1019,7 +1019,7 @@ w32_dialog_show (struct frame *f, Lisp_Object title,
1019 } 1019 }
1020 else 1020 else
1021 /* Make "Cancel" equivalent to C-g. */ 1021 /* Make "Cancel" equivalent to C-g. */
1022 Fsignal (Qquit, Qnil); 1022 quit ();
1023 1023
1024 return Qnil; 1024 return Qnil;
1025} 1025}
@@ -1155,7 +1155,7 @@ simple_dialog_show (struct frame *f, Lisp_Object contents, Lisp_Object header)
1155 else if (answer == IDNO) 1155 else if (answer == IDNO)
1156 lispy_answer = build_string ("No"); 1156 lispy_answer = build_string ("No");
1157 else 1157 else
1158 Fsignal (Qquit, Qnil); 1158 quit ();
1159 1159
1160 for (temp = XCDR (contents); CONSP (temp); temp = XCDR (temp)) 1160 for (temp = XCDR (contents); CONSP (temp); temp = XCDR (temp))
1161 { 1161 {
@@ -1177,8 +1177,7 @@ simple_dialog_show (struct frame *f, Lisp_Object contents, Lisp_Object header)
1177 return value; 1177 return value;
1178 } 1178 }
1179 } 1179 }
1180 Fsignal (Qquit, Qnil); 1180 return quit ();
1181 return Qnil;
1182} 1181}
1183#endif /* !HAVE_DIALOGS */ 1182#endif /* !HAVE_DIALOGS */
1184 1183
diff --git a/src/xfns.c b/src/xfns.c
index 798dc49bef5..c44997b3d6f 100644
--- a/src/xfns.c
+++ b/src/xfns.c
@@ -6346,7 +6346,7 @@ value of DIR as in previous invocations; this is standard Windows behavior. */)
6346 6346
6347 /* Make "Cancel" equivalent to C-g. */ 6347 /* Make "Cancel" equivalent to C-g. */
6348 if (NILP (file)) 6348 if (NILP (file))
6349 Fsignal (Qquit, Qnil); 6349 quit ();
6350 6350
6351 decoded_file = DECODE_FILE (file); 6351 decoded_file = DECODE_FILE (file);
6352 6352
@@ -6418,7 +6418,7 @@ value of DIR as in previous invocations; this is standard Windows behavior. */)
6418 6418
6419 /* Make "Cancel" equivalent to C-g. */ 6419 /* Make "Cancel" equivalent to C-g. */
6420 if (NILP (file)) 6420 if (NILP (file))
6421 Fsignal (Qquit, Qnil); 6421 quit ();
6422 6422
6423 decoded_file = DECODE_FILE (file); 6423 decoded_file = DECODE_FILE (file);
6424 6424
@@ -6469,7 +6469,7 @@ nil, it defaults to the selected frame. */)
6469 unblock_input (); 6469 unblock_input ();
6470 6470
6471 if (NILP (font)) 6471 if (NILP (font))
6472 Fsignal (Qquit, Qnil); 6472 quit ();
6473 6473
6474 return unbind_to (count, font); 6474 return unbind_to (count, font);
6475} 6475}
diff --git a/src/xmenu.c b/src/xmenu.c
index 9e1a817946a..9ab7bdf971f 100644
--- a/src/xmenu.c
+++ b/src/xmenu.c
@@ -1649,7 +1649,7 @@ x_menu_show (struct frame *f, int x, int y, int menuflags,
1649 { 1649 {
1650 unblock_input (); 1650 unblock_input ();
1651 /* Make "Cancel" equivalent to C-g. */ 1651 /* Make "Cancel" equivalent to C-g. */
1652 Fsignal (Qquit, Qnil); 1652 quit ();
1653 } 1653 }
1654 1654
1655 unblock_input (); 1655 unblock_input ();
@@ -1913,7 +1913,7 @@ x_dialog_show (struct frame *f, Lisp_Object title,
1913 } 1913 }
1914 else 1914 else
1915 /* Make "Cancel" equivalent to C-g. */ 1915 /* Make "Cancel" equivalent to C-g. */
1916 Fsignal (Qquit, Qnil); 1916 quit ();
1917 1917
1918 return Qnil; 1918 return Qnil;
1919} 1919}
@@ -2304,7 +2304,7 @@ x_menu_show (struct frame *f, int x, int y, int menuflags,
2304 if (!(menuflags & MENU_FOR_CLICK)) 2304 if (!(menuflags & MENU_FOR_CLICK))
2305 { 2305 {
2306 unblock_input (); 2306 unblock_input ();
2307 Fsignal (Qquit, Qnil); 2307 quit ();
2308 } 2308 }
2309 break; 2309 break;
2310 } 2310 }