changeset 71947:4bc25e59ebd1

(Vcommand_error_function): New variable. (syms_of_keyboard): Defvar it. (cmd_error_internal): Simplify, and handle Vcommand_error_function.
author Richard M. Stallman <rms@gnu.org>
date Mon, 17 Jul 2006 21:00:58 +0000
parents db54d1f64f25
children df5c12c54d24
files src/keyboard.c
diffstat 1 files changed, 44 insertions(+), 37 deletions(-) [+]
line wrap: on
line diff
--- a/src/keyboard.c	Mon Jul 17 21:00:08 2006 +0000
+++ b/src/keyboard.c	Mon Jul 17 21:00:58 2006 +0000
@@ -242,6 +242,9 @@
 /* Nonzero means C-g should cause immediate error-signal.  */
 int immediate_quit;
 
+/* The user's hook function for outputting an error message.  */
+Lisp_Object Vcommand_error_function;
+
 /* The user's ERASE setting.  */
 Lisp_Object Vtty_erase_char;
 
@@ -1230,52 +1233,47 @@
      Lisp_Object data;
      char *context;
 {
-  Lisp_Object stream;
-  int kill_emacs_p = 0;
   struct frame *sf = SELECTED_FRAME ();
 
-  Vquit_flag = Qnil;
-  Vinhibit_quit = Qt;
-  clear_message (1, 0);
-
-  /* If the window system or terminal frame hasn't been initialized
-     yet, or we're not interactive, it's best to dump this message out
-     to stderr and exit.  */
-  if (!sf->glyphs_initialized_p
-      /* This is the case of the frame dumped with Emacs, when we're
-	 running under a window system.  */
-      || (!NILP (Vwindow_system)
-	  && !inhibit_window_system
-	  && FRAME_TERMCAP_P (sf))
-      || noninteractive)
-    {
-      stream = Qexternal_debugging_output;
-      kill_emacs_p = 1;
-    }
-  else
-    {
-      Fdiscard_input ();
-      message_log_maybe_newline ();
-      bitch_at_user ();
-      stream = Qt;
-    }
-
   /* The immediate context is not interesting for Quits,
      since they are asyncronous.  */
   if (EQ (XCAR (data), Qquit))
     Vsignaling_function = Qnil;
 
-  print_error_message (data, stream, context, Vsignaling_function);
+  Vquit_flag = Qnil;
+  Vinhibit_quit = Qt;
+
+  /* Use user's specified output function if any.  */
+  if (!NILP (Vcommand_error_function))
+    call3 (Vcommand_error_function, data,
+	   build_string (context ? context : ""),
+	   Vsignaling_function);
+  /* If the window system or terminal frame hasn't been initialized
+     yet, or we're not interactive, write the message to stderr and exit.  */
+  else if (!sf->glyphs_initialized_p
+	   /* This is the case of the frame dumped with Emacs, when we're
+	      running under a window system.  */
+	   || (!NILP (Vwindow_system)
+	       && !inhibit_window_system
+	       && FRAME_TERMCAP_P (sf))
+	   || noninteractive)
+    {
+      print_error_message (data, Qexternal_debugging_output,
+			   context, Vsignaling_function);
+      Fterpri (Qexternal_debugging_output);
+      Fkill_emacs (make_number (-1));
+    }
+  else
+    {
+      clear_message (1, 0);
+      Fdiscard_input ();
+      message_log_maybe_newline ();
+      bitch_at_user ();
+
+      print_error_message (data, Qt, context, Vsignaling_function);
+    }
 
   Vsignaling_function = Qnil;
-
-  /* If the window system or terminal frame hasn't been initialized
-     yet, or we're in -batch mode, this error should cause Emacs to exit.  */
-  if (kill_emacs_p)
-    {
-      Fterpri (stream);
-      Fkill_emacs (make_number (-1));
-    }
 }
 
 Lisp_Object command_loop_1 ();
@@ -11484,6 +11482,15 @@
 peculiar kind of quitting.  */);
   Vthrow_on_input = Qnil;
 
+  DEFVAR_LISP ("command-error-function", &Vcommand_error_function,
+	       doc: /* If non-nil, function to output error messages.
+The arguments are the error data, a list of the form
+ (SIGNALED-CONDITIONS . SIGNAL-DATA)
+such as just as `condition-case' would bind its variable to,
+the context (a string which normally goes at the start of the message),
+and the Lisp function within which the error was signaled.  */);
+  Vcommand_error_function = Qnil;
+
   DEFVAR_LISP ("enable-disabled-menus-and-buttons",
 	       &Venable_disabled_menus_and_buttons,
 	       doc: /* If non-nil, don't ignore events produced by disabled menu items and tool-bar.