Mercurial > vim
diff src/regexp_nfa.c @ 29191:0af5fe160e4e v8.2.5115
patch 8.2.5115: search timeout is overrun with some patterns
Commit: https://github.com/vim/vim/commit/616592e0816d2d9f893fcd95e3e1e0fbc5893168
Author: Bram Moolenaar <Bram@vim.org>
Date: Fri Jun 17 15:17:10 2022 +0100
patch 8.2.5115: search timeout is overrun with some patterns
Problem: Search timeout is overrun with some patterns.
Solution: Check for timeout in more places. Make the flag volatile and
atomic. Use assert_inrange() to see what happened.
author | Bram Moolenaar <Bram@vim.org> |
---|---|
date | Fri, 17 Jun 2022 16:30:06 +0200 |
parents | b90bca860b5a |
children | c7aa0c46acd5 |
line wrap: on
line diff
--- a/src/regexp_nfa.c +++ b/src/regexp_nfa.c @@ -4237,6 +4237,27 @@ sub_equal(regsub_T *sub1, regsub_T *sub2 return TRUE; } +#ifdef FEAT_RELTIME +/* + * Check if we are past the time limit, if there is one. + */ + static int +nfa_did_time_out(void) +{ + if (*timeout_flag) + { + if (nfa_timed_out != NULL) + { + if (!*nfa_timed_out) + ch_log(NULL, "NFA regexp timed out"); + *nfa_timed_out = TRUE; + } + return TRUE; + } + return FALSE; +} +#endif + #ifdef ENABLE_LOG static void open_debug_log(int result) @@ -4451,7 +4472,7 @@ state_in_list( /* * Add "state" and possibly what follows to state list ".". * Returns "subs_arg", possibly copied into temp_subs. - * Returns NULL when recursiveness is too deep. + * Returns NULL when recursiveness is too deep or timed out. */ static regsubs_T * addstate( @@ -4480,6 +4501,11 @@ addstate( #endif static int depth = 0; +#ifdef FEAT_RELTIME + if (nfa_did_time_out()) + return NULL; +#endif + // This function is called recursively. When the depth is too much we run // out of stack and crash, limit recursiveness here. if (++depth >= 5000 || subs == NULL) @@ -5643,24 +5669,6 @@ find_match_text(colnr_T startcol, int re return 0L; } -#ifdef FEAT_RELTIME -/* - * Check if we are past the time limit, if there is one. - * To reduce overhead, only check one in "count" times. - */ - static int -nfa_did_time_out(void) -{ - if (*timeout_flag) - { - if (nfa_timed_out != NULL) - *nfa_timed_out = TRUE; - return TRUE; - } - return FALSE; -} -#endif - /* * Main matching routine. * @@ -5708,7 +5716,6 @@ nfa_regmatch( if (got_int) return FALSE; #ifdef FEAT_RELTIME - // Check relatively often here, since this is the toplevel matching. if (nfa_did_time_out()) return FALSE; #endif @@ -7109,7 +7116,6 @@ nextchar: if (got_int) break; #ifdef FEAT_RELTIME - // Check for timeout once in a twenty times to avoid overhead. if (nfa_did_time_out()) break; #endif