Don't globally add to change-major-mode-hook.
[bpt/emacs.git] / src / search.c
index 7c8e58a..790f35f 100644 (file)
@@ -225,7 +225,7 @@ looking_at_1 (string, posix)
   CHECK_STRING (string, 0);
   bufp = compile_pattern (string, &search_regs,
                          (!NILP (current_buffer->case_fold_search)
-                          ? DOWNCASE_TABLE : 0),
+                          ? XCHAR_TABLE (DOWNCASE_TABLE)->contents : 0),
                          posix);
 
   immediate_quit = 1;
@@ -249,6 +249,8 @@ looking_at_1 (string, posix)
       s1 = ZV - BEGV;
       s2 = 0;
     }
+
+  re_match_object = Qnil;
   
   i = re_match_2 (bufp, (char *) p1, s1, (char *) p2, s2,
                  PT - BEGV, &search_regs,
@@ -322,9 +324,11 @@ string_match_1 (regexp, string, start, posix)
 
   bufp = compile_pattern (regexp, &search_regs,
                          (!NILP (current_buffer->case_fold_search)
-                          ? DOWNCASE_TABLE : 0),
+                          ? XCHAR_TABLE (DOWNCASE_TABLE)->contents : 0),
                          posix);
   immediate_quit = 1;
+  re_match_object = string;
+  
   val = re_search (bufp, (char *) XSTRING (string)->data,
                   XSTRING (string)->size, s, XSTRING (string)->size - s,
                   &search_regs);
@@ -374,6 +378,8 @@ fast_string_match (regexp, string)
 
   bufp = compile_pattern (regexp, 0, 0, 0);
   immediate_quit = 1;
+  re_match_object = string;
+  
   val = re_search (bufp, (char *) XSTRING (string)->data,
                   XSTRING (string)->size, 0, XSTRING (string)->size,
                   0);
@@ -388,7 +394,7 @@ fast_string_match (regexp, string)
 extern Lisp_Object Vascii_downcase_table;
 
 int
-fast_string_match_ignore_case (regexp, string)
+fast_c_string_match_ignore_case (regexp, string)
      Lisp_Object regexp;
      char *string;
 {
@@ -396,6 +402,7 @@ fast_string_match_ignore_case (regexp, string)
   struct re_pattern_buffer *bufp;
   int len = strlen (string);
 
+  re_match_object = Qt;
   bufp = compile_pattern (regexp, 0,
                          XCHAR_TABLE (Vascii_downcase_table)->contents, 0);
   immediate_quit = 1;
@@ -671,299 +678,6 @@ find_before_next_newline (from, to, cnt)
   return pos;
 }
 \f
-Lisp_Object skip_chars ();
-
-DEFUN ("skip-chars-forward", Fskip_chars_forward, Sskip_chars_forward, 1, 2, 0,
-  "Move point forward, stopping before a char not in STRING, or at pos LIM.\n\
-STRING is like the inside of a `[...]' in a regular expression\n\
-except that `]' is never special and `\\' quotes `^', `-' or `\\'.\n\
-Thus, with arg \"a-zA-Z\", this skips letters stopping before first nonletter.\n\
-With arg \"^a-zA-Z\", skips nonletters stopping before first letter.\n\
-Returns the distance traveled, either zero or positive.")
-  (string, lim)
-     Lisp_Object string, lim;
-{
-  return skip_chars (1, 0, string, lim);
-}
-
-DEFUN ("skip-chars-backward", Fskip_chars_backward, Sskip_chars_backward, 1, 2, 0,
-  "Move point backward, stopping after a char not in STRING, or at pos LIM.\n\
-See `skip-chars-forward' for details.\n\
-Returns the distance traveled, either zero or negative.")
-  (string, lim)
-     Lisp_Object string, lim;
-{
-  return skip_chars (0, 0, string, lim);
-}
-
-DEFUN ("skip-syntax-forward", Fskip_syntax_forward, Sskip_syntax_forward, 1, 2, 0,
-  "Move point forward across chars in specified syntax classes.\n\
-SYNTAX is a string of syntax code characters.\n\
-Stop before a char whose syntax is not in SYNTAX, or at position LIM.\n\
-If SYNTAX starts with ^, skip characters whose syntax is NOT in SYNTAX.\n\
-This function returns the distance traveled, either zero or positive.")
-  (syntax, lim)
-     Lisp_Object syntax, lim;
-{
-  return skip_chars (1, 1, syntax, lim);
-}
-
-DEFUN ("skip-syntax-backward", Fskip_syntax_backward, Sskip_syntax_backward, 1, 2, 0,
-  "Move point backward across chars in specified syntax classes.\n\
-SYNTAX is a string of syntax code characters.\n\
-Stop on reaching a char whose syntax is not in SYNTAX, or at position LIM.\n\
-If SYNTAX starts with ^, skip characters whose syntax is NOT in SYNTAX.\n\
-This function returns the distance traveled, either zero or negative.")
-  (syntax, lim)
-     Lisp_Object syntax, lim;
-{
-  return skip_chars (0, 1, syntax, lim);
-}
-
-Lisp_Object
-skip_chars (forwardp, syntaxp, string, lim)
-     int forwardp, syntaxp;
-     Lisp_Object string, lim;
-{
-  register unsigned char *p, *pend;
-  register unsigned int c;
-  register int ch;
-  unsigned char fastmap[0400];
-  /* If SYNTAXP is 0, STRING may contain multi-byte form of characters
-     of which codes don't fit in FASTMAP.  In that case, we set the
-     first byte of multibyte form (i.e. base leading-code) in FASTMAP
-     and set the actual ranges of characters in CHAR_RANGES.  In the
-     form "X-Y" of STRING, both X and Y must belong to the same
-     character set because a range striding across character sets is
-     meaningless.  */
-  int *char_ranges
-    = (int *) alloca (XSTRING (string)->size * (sizeof (int)) * 2);
-  int n_char_ranges = 0;
-  int negate = 0;
-  register int i;
-  int multibyte = !NILP (current_buffer->enable_multibyte_characters);
-
-  CHECK_STRING (string, 0);
-
-  if (NILP (lim))
-    XSETINT (lim, forwardp ? ZV : BEGV);
-  else
-    CHECK_NUMBER_COERCE_MARKER (lim, 1);
-
-  /* In any case, don't allow scan outside bounds of buffer.  */
-  /* jla turned this off, for no known reason.
-     bfox turned the ZV part on, and rms turned the
-     BEGV part back on.  */
-  if (XINT (lim) > ZV)
-    XSETFASTINT (lim, ZV);
-  if (XINT (lim) < BEGV)
-    XSETFASTINT (lim, BEGV);
-
-  p = XSTRING (string)->data;
-  pend = p + XSTRING (string)->size;
-  bzero (fastmap, sizeof fastmap);
-
-  if (p != pend && *p == '^')
-    {
-      negate = 1; p++;
-    }
-
-  /* Find the characters specified and set their elements of fastmap.
-     If syntaxp, each character counts as itself.
-     Otherwise, handle backslashes and ranges specially.  */
-
-  while (p != pend)
-    {
-      c = *p;
-      if (multibyte)
-       {
-         ch = STRING_CHAR (p, pend - p);
-         p += BYTES_BY_CHAR_HEAD (*p);
-       }
-      else
-       {
-         ch = c;
-         p++;
-       }
-      if (syntaxp)
-       fastmap[syntax_spec_code[c]] = 1;
-      else
-       {
-         if (c == '\\')
-           {
-             if (p == pend) break;
-             c = *p++;
-           }
-         if (p != pend && *p == '-')
-           {
-             unsigned int ch2;
-
-             p++;
-             if (p == pend) break;
-             if (SINGLE_BYTE_CHAR_P (ch))
-               while (c <= *p)
-                 {
-                   fastmap[c] = 1;
-                   c++;
-                 }
-             else
-               {
-                 fastmap[c] = 1; /* C is the base leading-code.  */
-                 ch2 = STRING_CHAR (p, pend - p);
-                 if (ch <= ch2)
-                   char_ranges[n_char_ranges++] = ch,
-                   char_ranges[n_char_ranges++] = ch2;
-               }
-             p += multibyte ? BYTES_BY_CHAR_HEAD (*p) : 1;
-           }
-         else
-           {
-             fastmap[c] = 1;
-             if (!SINGLE_BYTE_CHAR_P (ch))
-               char_ranges[n_char_ranges++] = ch,
-               char_ranges[n_char_ranges++] = ch;
-           }
-       }
-    }
-
-  /* If ^ was the first character, complement the fastmap.  In
-     addition, as all multibyte characters have possibility of
-     matching, set all entries for base leading codes, which is
-     harmless even if SYNTAXP is 1.  */
-
-  if (negate)
-    for (i = 0; i < sizeof fastmap; i++)
-      {
-       if (!multibyte || !BASE_LEADING_CODE_P (i))
-         fastmap[i] ^= 1;
-       else
-         fastmap[i] = 1;
-      }
-
-  {
-    int start_point = PT;
-    int pos = PT;
-
-    immediate_quit = 1;
-    if (syntaxp)
-      {
-       if (forwardp)
-         {
-           if (multibyte)
-             while (pos < XINT (lim)
-                    && fastmap[(int) SYNTAX (FETCH_CHAR (pos))])
-               INC_POS (pos);
-           else
-             while (pos < XINT (lim)
-                    && fastmap[(int) SYNTAX (FETCH_BYTE (pos))])
-               pos++;
-         }
-       else
-         {
-           if (multibyte)
-             while (pos > XINT (lim))
-               {
-                 int savepos = pos;
-                 DEC_POS (pos);
-                 if (!fastmap[(int) SYNTAX (FETCH_CHAR (pos))])
-                   {
-                     pos = savepos;
-                     break;
-                   }
-               }
-           else
-             while (pos > XINT (lim)
-                    && fastmap[(int) SYNTAX (FETCH_BYTE (pos - 1))])
-               pos--;
-         }
-      }
-    else
-      {
-       if (forwardp)
-         {
-           if (multibyte)
-             while (pos < XINT (lim) && fastmap[(c = FETCH_BYTE (pos))])
-               {
-                 if (!BASE_LEADING_CODE_P (c))
-                   pos++;
-                 else if (n_char_ranges)
-                   {
-                     /* We much check CHAR_RANGES for a multibyte
-                        character.  */
-                     ch = FETCH_MULTIBYTE_CHAR (pos);
-                     for (i = 0; i < n_char_ranges; i += 2)
-                       if ((ch >= char_ranges[i] && ch <= char_ranges[i + 1]))
-                         break;
-                     if (!(negate ^ (i < n_char_ranges)))
-                       break;
-
-                     INC_POS (pos);
-                   }
-                 else
-                   {
-                     if (!negate) break;
-                     INC_POS (pos);
-                   }
-               }
-           else
-             while (pos < XINT (lim) && fastmap[FETCH_BYTE (pos)])
-               pos++;
-         }
-       else
-         {
-           if (multibyte)
-             while (pos > XINT (lim))
-               {
-                 int savepos = pos;
-                 DEC_POS (pos);
-                 if (fastmap[(c = FETCH_BYTE (pos))])
-                   {
-                     if (!BASE_LEADING_CODE_P (c))
-                       ;
-                     else if (n_char_ranges)
-                       {
-                         /* We much check CHAR_RANGES for a multibyte
-                            character.  */
-                         ch = FETCH_MULTIBYTE_CHAR (pos);
-                         for (i = 0; i < n_char_ranges; i += 2)
-                           if (ch >= char_ranges[i] && ch <= char_ranges[i + 1])
-                             break;
-                         if (!(negate ^ (i < n_char_ranges)))
-                           {
-                             pos = savepos;
-                             break;
-                           }
-                       }
-                     else
-                       if (!negate)
-                         {
-                           pos = savepos;
-                           break;
-                         }
-                   }
-                 else
-                   {
-                     pos = savepos;
-                     break;
-                   }
-               }
-           else
-             while (pos > XINT (lim) && fastmap[FETCH_BYTE (pos - 1)])
-               pos--;
-         }
-      }
-    if (multibyte
-       /* INC_POS or DEC_POS might have moved POS over LIM.  */
-       && (forwardp ? (pos > XINT (lim)) : (pos < XINT (lim))))
-      pos = XINT (lim);
-
-    SET_PT (pos);
-    immediate_quit = 0;
-
-    return make_number (PT - start_point);
-  }
-}
-\f
 /* Subroutines of Lisp buffer search functions. */
 
 static Lisp_Object
@@ -1145,6 +859,8 @@ search_buffer (string, pos, lim, n, RE, trt, inverse_trt, posix)
          s1 = ZV - BEGV;
          s2 = 0;
        }
+      re_match_object = Qnil;
+  
       while (n < 0)
        {
          int val;
@@ -1229,7 +945,7 @@ search_buffer (string, pos, lim, n, RE, trt, inverse_trt, posix)
                len--;
                base_pat++;
              }
-           *pat++ = (trt ? trt[*base_pat++] : *base_pat++);
+           *pat++ = (trt ? XINT (trt[*base_pat++]) : *base_pat++);
          }
        len = pat - patbuf;
        pat = base_pat = patbuf;
@@ -1284,13 +1000,13 @@ search_buffer (string, pos, lim, n, RE, trt, inverse_trt, posix)
          if (i == dirlen) i = infinity;
          if (trt != 0)
            {
-             k = (j = trt[j]);
+             k = (j = XINT (trt[j]));
              if (i == infinity)
                stride_for_teases = BM_tab[j];
              BM_tab[j] = dirlen - i;
              /* A translation table is accompanied by its inverse -- see */
              /* comment following downcase_table for details */ 
-             while ((j = (unsigned char) inverse_trt[j]) != k)
+             while ((j = (unsigned char) XINT (inverse_trt[j])) != k)
                BM_tab[j] = dirlen - i;
            }
          else
@@ -1373,7 +1089,7 @@ search_buffer (string, pos, lim, n, RE, trt, inverse_trt, posix)
                  if (trt != 0)
                    {
                      while ((i -= direction) + direction != 0)
-                       if (pat[i] != trt[*(cursor -= direction)])
+                       if (pat[i] != XINT (trt[*(cursor -= direction)]))
                          break;
                    }
                  else
@@ -1434,7 +1150,7 @@ search_buffer (string, pos, lim, n, RE, trt, inverse_trt, posix)
                    {
                      pos -= direction;
                      if (pat[i] != (trt != 0
-                                    ? trt[FETCH_BYTE (pos)]
+                                    ? XINT (trt[FETCH_BYTE (pos)])
                                     : FETCH_BYTE (pos)))
                        break;
                    }
@@ -1707,6 +1423,7 @@ since only regular expressions have distinguished subexpressions.")
   register int c, prevc;
   int inslen;
   int sub;
+  int opoint, newpoint;
 
   CHECK_STRING (newtext, 0);
 
@@ -1900,11 +1617,18 @@ since only regular expressions have distinguished subexpressions.")
       return concat3 (before, newtext, after);
     }
 
+  /* Record point, the move (quietly) to the start of the match.  */
+  if (PT > search_regs.start[sub])
+    opoint = PT - ZV;
+  else
+    opoint = PT;
+
+  temp_set_point (search_regs.start[sub], current_buffer);
+
   /* We insert the replacement text before the old text, and then
      delete the original text.  This means that markers at the
      beginning or end of the original will float to the corresponding
      position in the replacement.  */
-  SET_PT (search_regs.start[sub]);
   if (!NILP (literal))
     Finsert_and_inherit (1, &newtext);
   else
@@ -1951,6 +1675,18 @@ since only regular expressions have distinguished subexpressions.")
     Fupcase_region (make_number (PT - inslen), make_number (PT));
   else if (case_action == cap_initial)
     Fupcase_initials_region (make_number (PT - inslen), make_number (PT));
+
+  newpoint = PT;
+
+  /* Put point back where it was in the text.  */
+  if (opoint <= 0)
+    temp_set_point (opoint + ZV, current_buffer);
+  else
+    temp_set_point (opoint, current_buffer);
+
+  /* Now move point "officially" to the start of the inserted replacement.  */
+  move_if_not_intangible (newpoint);
+  
   return Qnil;
 }
 \f
@@ -2273,10 +2009,6 @@ syms_of_search ()
   defsubr (&Sposix_looking_at);
   defsubr (&Sstring_match);
   defsubr (&Sposix_string_match);
-  defsubr (&Sskip_chars_forward);
-  defsubr (&Sskip_chars_backward);
-  defsubr (&Sskip_syntax_forward);
-  defsubr (&Sskip_syntax_backward);
   defsubr (&Ssearch_forward);
   defsubr (&Ssearch_backward);
   defsubr (&Sword_search_forward);