when a filter or sentinel tries to modify it.
priority; Those functions have their own extern declaration. */
int emacs_priority;
+/* If non-zero a filter or a sentinel is running. Tested to save the match
+ data on the first attempt to change it inside asynchronous code. */
+int running_asynch_code;
+
#ifdef BSD_PGRPS
/* See sysdep.c. */
extern int inherited_pgroup;
init_alloc ();
init_eval ();
init_data ();
+ running_asynch_code = 0;
#ifdef MSDOS
/* Call early 'cause init_environment needs it. */
/* defined in search.c */
extern Lisp_Object Fstring_match ();
extern Lisp_Object Fscan_buffer ();
+extern void restore_match_data ();
/* defined in minibuf.c */
extern int noninteractive;
/* Nonzero means don't do use window-system-specific display code */
extern int inhibit_window_system;
+/* Nonzero means that a filter or a sentinel is running. */
+extern int running_asynch_code;
/* defined in process.c */
extern Lisp_Object Fget_process (), Fget_buffer_process (), Fprocessp ();
specbind (Qinhibit_quit, Qt);
specbind (Qlast_nonmenu_event, Qt);
+ running_asynch_code = 1;
internal_condition_case_1 (read_process_output_call,
Fcons (outstream,
Fcons (proc,
- Fcons (make_string (chars, nchars),
+ Fcons (make_string (chars,
+ nchars),
Qnil))),
!NILP (Vdebug_on_error) ? Qnil : Qerror,
read_process_output_error_handler);
+ running_asynch_code = 0;
+ restore_match_data ();
/* Handling the process output should not deactivate the mark. */
Vdeactivate_mark = odeactivate;
specbind (Qinhibit_quit, Qt);
specbind (Qlast_nonmenu_event, Qt);
+ running_asynch_code = 1;
internal_condition_case_1 (read_process_output_call,
Fcons (sentinel,
Fcons (proc, Fcons (reason, Qnil))),
!NILP (Vdebug_on_error) ? Qnil : Qerror,
exec_sentinel_error_handler);
+ running_asynch_code = 0;
+ restore_match_data ();
Vdeactivate_mark = odeactivate;
if (! EQ (Fcurrent_buffer (), obuffer))
register int i;
struct re_pattern_buffer *bufp;
+ if (running_asynch_code)
+ save_search_regs ();
+
CHECK_STRING (string, 0);
bufp = compile_pattern (string, &search_regs,
(!NILP (current_buffer->case_fold_search)
int s;
struct re_pattern_buffer *bufp;
+ if (running_asynch_code)
+ save_search_regs ();
+
CHECK_STRING (regexp, 0);
CHECK_STRING (string, 1);
unsigned char *p1, *p2;
int s1, s2;
+ if (running_asynch_code)
+ save_search_regs ();
+
/* Null string is found at starting position. */
if (len == 0)
{
register int i;
register Lisp_Object marker;
+ if (running_asynch_code)
+ save_search_regs ();
+
if (!CONSP (list) && !NILP (list))
list = wrong_type_argument (Qconsp, list);
return Qnil;
}
+/* If non-zero the match data have been saved in saved_search_regs
+ during the execution of a sentinel or filter. */
+static int search_regs_saved = 0;
+static struct re_registers saved_search_regs;
+
+/* Called from Flooking_at, Fstring_match, search_buffer, Fstore_match_data
+ if asynchronous code (filter or sentinel) is running. */
+static void
+save_search_regs ()
+{
+ if (!search_regs_saved)
+ {
+ saved_search_regs.num_regs = search_regs.num_regs;
+ saved_search_regs.start = search_regs.start;
+ saved_search_regs.end = search_regs.end;
+ search_regs.num_regs = 0;
+
+ search_regs_saved = 1;
+ }
+}
+
+/* Called upon exit from filters and sentinels. */
+void
+restore_match_data ()
+{
+ if (search_regs_saved)
+ {
+ if (search_regs.num_regs > 0)
+ {
+ xfree (search_regs.start);
+ xfree (search_regs.end);
+ }
+ search_regs.num_regs = saved_search_regs.num_regs;
+ search_regs.start = saved_search_regs.start;
+ search_regs.end = saved_search_regs.end;
+
+ search_regs_saved = 0;
+ }
+}
+
/* Quote a string to inactivate reg-expr chars */
DEFUN ("regexp-quote", Fregexp_quote, Sregexp_quote, 1, 1, 0,