]> code.delx.au - gnu-emacs/blobdiff - src/syntax.c
Merge from emacs-23
[gnu-emacs] / src / syntax.c
index 8c5ebb96f285e7e94e9f76fa3b496edc76c86a32..9b707c6c3b771ec34a05d7ba00ca4c62e0caf2bb 100644 (file)
@@ -1,6 +1,6 @@
 /* GNU Emacs routines to deal with syntax tables; also word and list parsing.
    Copyright (C) 1985, 1987, 1993, 1994, 1995, 1997, 1998, 1999, 2001,
-                 2002, 2003, 2004, 2005, 2006, 2007, 2008
+                 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010
                  Free Software Foundation, Inc.
 
 This file is part of GNU Emacs.
@@ -21,6 +21,7 @@ along with GNU Emacs.  If not, see <http://www.gnu.org/licenses/>.  */
 
 #include <config.h>
 #include <ctype.h>
+#include <setjmp.h>
 #include "lisp.h"
 #include "commands.h"
 #include "buffer.h"
@@ -65,18 +66,20 @@ int open_paren_in_column_0_is_defun_start;
 
 struct lisp_parse_state
   {
-    int depth;         /* Depth at end of parsing.  */
-    int instring;      /* -1 if not within string, else desired terminator.  */
-    int incomment;     /* -1 if in unnestable comment else comment nesting */
-    int comstyle;      /* comment style a=0, or b=1, or ST_COMMENT_STYLE.  */
-    int quoted;                /* Nonzero if just after an escape char at end of parsing */
-    int thislevelstart;        /* Char number of most recent start-of-expression at current level */
-    int prevlevelstart; /* Char number of start of containing expression */
-    int location;      /* Char number at which parsing stopped.  */
-    int mindepth;      /* Minimum depth seen while scanning.  */
-    int comstr_start;  /* Position just after last comment/string starter.  */
-    Lisp_Object levelstarts;   /* Char numbers of starts-of-expression
-                                  of levels (starting from outermost).  */
+    int depth;    /* Depth at end of parsing.  */
+    int instring;  /* -1 if not within string, else desired terminator.  */
+    int incomment; /* -1 if in unnestable comment else comment nesting */
+    int comstyle;  /* comment style a=0, or b=1, or ST_COMMENT_STYLE.  */
+    int quoted;           /* Nonzero if just after an escape char at end of parsing */
+    int mindepth;  /* Minimum depth seen while scanning.  */
+    /* Char number of most recent start-of-expression at current level */
+    EMACS_INT thislevelstart;
+    /* Char number of start of containing expression */
+    EMACS_INT prevlevelstart;
+    EMACS_INT location;             /* Char number at which parsing stopped.  */
+    EMACS_INT comstr_start;  /* Position of last comment/string starter.  */
+    Lisp_Object levelstarts; /* Char numbers of starts-of-expression
+                               of levels (starting from outermost).  */
   };
 \f
 /* These variables are a cache for finding the start of a defun.
@@ -87,30 +90,26 @@ struct lisp_parse_state
    find_start_begv is the BEGV value when it was found.
    find_start_modiff is the value of MODIFF when it was found.  */
 
-static int find_start_pos;
-static int find_start_value;
-static int find_start_value_byte;
+static EMACS_INT find_start_pos;
+static EMACS_INT find_start_value;
+static EMACS_INT find_start_value_byte;
 static struct buffer *find_start_buffer;
-static int find_start_begv;
+static EMACS_INT find_start_begv;
 static int find_start_modiff;
 
 
-static int find_defun_start P_ ((int, int));
-static int back_comment P_ ((EMACS_INT, EMACS_INT, EMACS_INT, int, int,
-                            EMACS_INT *, EMACS_INT *));
-static int char_quoted P_ ((int, int));
-static Lisp_Object skip_chars P_ ((int, Lisp_Object, Lisp_Object, int));
-static Lisp_Object skip_syntaxes P_ ((int, Lisp_Object, Lisp_Object));
-static Lisp_Object scan_lists P_ ((EMACS_INT, EMACS_INT, EMACS_INT, int));
-static void scan_sexps_forward P_ ((struct lisp_parse_state *,
-                                   int, int, int, int,
-                                   int, Lisp_Object, int));
-static int in_classes P_ ((int, Lisp_Object));
+static Lisp_Object skip_chars (int, Lisp_Object, Lisp_Object, int);
+static Lisp_Object skip_syntaxes (int, Lisp_Object, Lisp_Object);
+static Lisp_Object scan_lists (EMACS_INT, EMACS_INT, EMACS_INT, int);
+static void scan_sexps_forward (struct lisp_parse_state *,
+                                EMACS_INT, EMACS_INT, EMACS_INT, int,
+                                int, Lisp_Object, int);
+static int in_classes (int, Lisp_Object);
 \f
 
 struct gl_state_s gl_state;            /* Global state of syntax parser.  */
 
-INTERVAL interval_of ();
+INTERVAL interval_of (int, Lisp_Object);
 #define INTERVALS_AT_ONCE 10           /* 1 + max-number of intervals
                                           to scan to property-change.  */
 
@@ -128,9 +127,7 @@ INTERVAL interval_of ();
    start/end of OBJECT.  */
 
 void
-update_syntax_table (charpos, count, init, object)
-     int charpos, count, init;
-     Lisp_Object object;
+update_syntax_table (int charpos, int count, int init, Lisp_Object object)
 {
   Lisp_Object tmp_table;
   int cnt = 0, invalidate = 1;
@@ -290,19 +287,17 @@ update_syntax_table (charpos, count, init, object)
    or after.  On return global syntax data is good for lookup at CHARPOS. */
 
 static int
-char_quoted (charpos, bytepos)
-     register int charpos, bytepos;
+char_quoted (EMACS_INT charpos, EMACS_INT bytepos)
 {
   register enum syntaxcode code;
-  register int beg = BEGV;
+  register EMACS_INT beg = BEGV;
   register int quoted = 0;
-  int orig = charpos;
-
-  DEC_BOTH (charpos, bytepos);
+  EMACS_INT orig = charpos;
 
-  while (charpos >= beg)
+  while (charpos > beg)
     {
       int c;
+      DEC_BOTH (charpos, bytepos);
 
       UPDATE_SYNTAX_TABLE_BACKWARD (charpos);
       c = FETCH_CHAR_AS_MULTIBYTE (bytepos);
@@ -310,7 +305,6 @@ char_quoted (charpos, bytepos)
       if (! (code == Scharquote || code == Sescape))
        break;
 
-      DEC_BOTH (charpos, bytepos);
       quoted = !quoted;
     }
 
@@ -321,9 +315,8 @@ char_quoted (charpos, bytepos)
 /* Return the bytepos one character after BYTEPOS.
    We assume that BYTEPOS is not at the end of the buffer.  */
 
-INLINE int
-inc_bytepos (bytepos)
-     int bytepos;
+INLINE EMACS_INT
+inc_bytepos (EMACS_INT bytepos)
 {
   if (NILP (current_buffer->enable_multibyte_characters))
     return bytepos + 1;
@@ -335,9 +328,8 @@ inc_bytepos (bytepos)
 /* Return the bytepos one character before BYTEPOS.
    We assume that BYTEPOS is not at the start of the buffer.  */
 
-INLINE int
-dec_bytepos (bytepos)
-     int bytepos;
+INLINE EMACS_INT
+dec_bytepos (EMACS_INT bytepos)
 {
   if (NILP (current_buffer->enable_multibyte_characters))
     return bytepos - 1;
@@ -346,7 +338,7 @@ dec_bytepos (bytepos)
   return bytepos;
 }
 \f
-/* Return a defun-start position before before POS and not too far before.
+/* Return a defun-start position before POS and not too far before.
    It should be the last one before POS, or nearly the last.
 
    When open_paren_in_column_0_is_defun_start is nonzero,
@@ -360,11 +352,10 @@ dec_bytepos (bytepos)
    valid on return from the subroutine, so the caller should explicitly
    update the global data.  */
 
-static int
-find_defun_start (pos, pos_byte)
-     int pos, pos_byte;
+static EMACS_INT
+find_defun_start (EMACS_INT pos, EMACS_INT pos_byte)
 {
-  int opoint = PT, opoint_byte = PT_BYTE;
+  EMACS_INT opoint = PT, opoint_byte = PT_BYTE;
 
   if (!open_paren_in_column_0_is_defun_start)
     {
@@ -389,8 +380,7 @@ find_defun_start (pos, pos_byte)
   /* We optimize syntax-table lookup for rare updates.  Thus we accept
      only those `^\s(' which are good in global _and_ text-property
      syntax-tables.  */
-  gl_state.current_syntax_table = current_buffer->syntax_table;
-  gl_state.use_global = 0;
+  SETUP_BUFFER_SYNTAX_TABLE ();
   while (PT > BEGV)
     {
       int c;
@@ -405,8 +395,7 @@ find_defun_start (pos, pos_byte)
          if (SYNTAX (c) == Sopen)
            break;
          /* Now fallback to the default value.  */
-         gl_state.current_syntax_table = current_buffer->syntax_table;
-         gl_state.use_global = 0;
+         SETUP_BUFFER_SYNTAX_TABLE ();
        }
       /* Move to beg of previous line.  */
       scan_newline (PT, PT_BYTE, BEGV, BEGV_BYTE, -2, 1);
@@ -428,8 +417,7 @@ find_defun_start (pos, pos_byte)
 /* Return the SYNTAX_COMEND_FIRST of the character before POS, POS_BYTE.  */
 
 static int
-prev_char_comend_first (pos, pos_byte)
-     int pos, pos_byte;
+prev_char_comend_first (int pos, int pos_byte)
 {
   int c, val;
 
@@ -471,10 +459,7 @@ prev_char_comend_first (pos, pos_byte)
    the returned value (or at FROM, if the search was not successful).  */
 
 static int
-back_comment (from, from_byte, stop, comnested, comstyle, charpos_ptr, bytepos_ptr)
-     EMACS_INT from, from_byte, stop;
-     int comnested, comstyle;
-     EMACS_INT *charpos_ptr, *bytepos_ptr;
+back_comment (EMACS_INT from, EMACS_INT from_byte, EMACS_INT stop, int comnested, int comstyle, EMACS_INT *charpos_ptr, EMACS_INT *bytepos_ptr)
 {
   /* Look back, counting the parity of string-quotes,
      and recording the comment-starters seen.
@@ -493,14 +478,14 @@ back_comment (from, from_byte, stop, comnested, comstyle, charpos_ptr, bytepos_p
      inside another comment).
      Test case:  { a (* b } c (* d *) */
   int comment_lossage = 0;
-  int comment_end = from;
-  int comment_end_byte = from_byte;
-  int comstart_pos = 0;
-  int comstart_byte;
+  EMACS_INT comment_end = from;
+  EMACS_INT comment_end_byte = from_byte;
+  EMACS_INT comstart_pos = 0;
+  EMACS_INT comstart_byte;
   /* Place where the containing defun starts,
      or 0 if we didn't come across it yet.  */
-  int defun_start = 0;
-  int defun_start_byte = 0;
+  EMACS_INT defun_start = 0;
+  EMACS_INT defun_start_byte = 0;
   register enum syntaxcode code;
   int nesting = 1;             /* current comment nesting */
   int c;
@@ -736,8 +721,7 @@ back_comment (from, from_byte, stop, comnested, comstyle, charpos_ptr, bytepos_p
 DEFUN ("syntax-table-p", Fsyntax_table_p, Ssyntax_table_p, 1, 1, 0,
        doc: /* Return t if OBJECT is a syntax table.
 Currently, any char-table counts as a syntax table.  */)
-     (object)
-     Lisp_Object object;
+  (Lisp_Object object)
 {
   if (CHAR_TABLE_P (object)
       && EQ (XCHAR_TABLE (object)->purpose, Qsyntax_table))
@@ -746,8 +730,7 @@ Currently, any char-table counts as a syntax table.  */)
 }
 
 static void
-check_syntax_table (obj)
-     Lisp_Object obj;
+check_syntax_table (Lisp_Object obj)
 {
   CHECK_TYPE (CHAR_TABLE_P (obj) && EQ (XCHAR_TABLE (obj)->purpose, Qsyntax_table),
              Qsyntax_table_p, obj);
@@ -756,7 +739,7 @@ check_syntax_table (obj)
 DEFUN ("syntax-table", Fsyntax_table, Ssyntax_table, 0, 0, 0,
        doc: /* Return the current syntax table.
 This is the one specified by the current buffer.  */)
-     ()
+  (void)
 {
   return current_buffer->syntax_table;
 }
@@ -765,7 +748,7 @@ DEFUN ("standard-syntax-table", Fstandard_syntax_table,
    Sstandard_syntax_table, 0, 0, 0,
        doc: /* Return the standard syntax table.
 This is the one used for new buffers.  */)
-     ()
+  (void)
 {
   return Vstandard_syntax_table;
 }
@@ -773,8 +756,7 @@ This is the one used for new buffers.  */)
 DEFUN ("copy-syntax-table", Fcopy_syntax_table, Scopy_syntax_table, 0, 1, 0,
        doc: /* Construct a new syntax table and return it.
 It is a copy of the TABLE, which defaults to the standard syntax table.  */)
-     (table)
-     Lisp_Object table;
+  (Lisp_Object table)
 {
   Lisp_Object copy;
 
@@ -800,8 +782,7 @@ It is a copy of the TABLE, which defaults to the standard syntax table.  */)
 DEFUN ("set-syntax-table", Fset_syntax_table, Sset_syntax_table, 1, 1, 0,
        doc: /* Select a new syntax table for the current buffer.
 One argument, a syntax table.  */)
-     (table)
-     Lisp_Object table;
+  (Lisp_Object table)
 {
   int idx;
   check_syntax_table (table);
@@ -856,32 +837,27 @@ static Lisp_Object Vsyntax_code_object;
 \f
 DEFUN ("char-syntax", Fchar_syntax, Schar_syntax, 1, 1, 0,
        doc: /* Return the syntax code of CHARACTER, described by a character.
-For example, if CHARACTER is a word constituent,
-the character `w' is returned.
+For example, if CHARACTER is a word constituent, the
+character `w' (119) is returned.
 The characters that correspond to various syntax codes
 are listed in the documentation of `modify-syntax-entry'.  */)
-     (character)
-     Lisp_Object character;
+  (Lisp_Object character)
 {
   int char_int;
-  gl_state.current_syntax_table = current_buffer->syntax_table;
-
-  gl_state.use_global = 0;
-  CHECK_NUMBER (character);
+  CHECK_CHARACTER (character);
   char_int = XINT (character);
+  SETUP_BUFFER_SYNTAX_TABLE ();
   return make_number (syntax_code_spec[(int) SYNTAX (char_int)]);
 }
 
 DEFUN ("matching-paren", Fmatching_paren, Smatching_paren, 1, 1, 0,
        doc: /* Return the matching parenthesis of CHARACTER, or nil if none.  */)
-     (character)
-     Lisp_Object character;
+  (Lisp_Object character)
 {
   int char_int, code;
-  gl_state.current_syntax_table = current_buffer->syntax_table;
-  gl_state.use_global = 0;
   CHECK_NUMBER (character);
   char_int = XINT (character);
+  SETUP_BUFFER_SYNTAX_TABLE ();
   code = SYNTAX (char_int);
   if (code == Sopen || code == Sclose)
     return SYNTAX_MATCH (char_int);
@@ -894,8 +870,7 @@ STRING should be a string as it is allowed as argument of
 `modify-syntax-entry'.  Value is the equivalent cons cell
 \(CODE . MATCHING-CHAR) that can be used as value of a `syntax-table'
 text property.  */)
-     (string)
-     Lisp_Object string;
+  (Lisp_Object string)
 {
   register const unsigned char *p;
   register enum syntaxcode code;
@@ -915,8 +890,7 @@ text property.  */)
   if (*p)
     {
       int len;
-      int character = (STRING_CHAR_AND_LENGTH
-                      (p, SBYTES (string) - 1, len));
+      int character = STRING_CHAR_AND_LENGTH (p, len);
       XSETINT (match, character);
       if (XFASTINT (match) == ' ')
        match = Qnil;
@@ -973,7 +947,7 @@ DEFUN ("modify-syntax-entry", Fmodify_syntax_entry, Smodify_syntax_entry, 2, 3,
 The syntax is changed only for table SYNTAX-TABLE, which defaults to
  the current buffer's syntax table.
 CHAR may be a cons (MIN . MAX), in which case, syntaxes of all characters
-in the range MIN and MAX are changed.
+in the range MIN to MAX are changed.
 The first character of NEWENTRY should be one of the following:
   Space or -  whitespace syntax.    w   word constituent.
   _           symbol constituent.   .   punctuation.
@@ -1006,9 +980,8 @@ this flag:
  p means CHAR is a prefix character for `backward-prefix-chars';
    such characters are treated as whitespace when they occur
    between expressions.
-usage: (modify-syntax-entry CHAR NEWENTRY &optional SYNTAX-TABLE) */)
-     (c, newentry, syntax_table)
-     Lisp_Object c, newentry, syntax_table;
+usage: (modify-syntax-entry CHAR NEWENTRY &optional SYNTAX-TABLE)  */)
+  (Lisp_Object c, Lisp_Object newentry, Lisp_Object syntax_table)
 {
   if (CONSP (c))
     {
@@ -1041,8 +1014,7 @@ usage: (modify-syntax-entry CHAR NEWENTRY &optional SYNTAX-TABLE) */)
 DEFUN ("internal-describe-syntax-value", Finternal_describe_syntax_value,
        Sinternal_describe_syntax_value, 1, 1, 0,
        doc: /* Insert a description of the internal syntax description SYNTAX at point.  */)
-     (syntax)
-     Lisp_Object syntax;
+  (Lisp_Object syntax)
 {
   register enum syntaxcode code;
   char desc, start1, start2, end1, end2, prefix, comstyle, comnested;
@@ -1195,8 +1167,7 @@ Lisp_Object Vfind_word_boundary_function_table;
    COUNT negative means scan backward and stop at word beginning.  */
 
 int
-scan_words (from, count)
-     register int from, count;
+scan_words (register int from, register int count)
 {
   register int beg = BEGV;
   register int end = ZV;
@@ -1253,7 +1224,7 @@ scan_words (from, count)
              if ((code != Sword
                   && (! words_include_escapes
                       || (code != Sescape && code != Scharquote)))
-                 || ! EQ (CHAR_TABLE_REF (Vchar_script_table, ch1), script))
+                 || word_boundary_p (ch0, ch1))
                break;
              INC_BOTH (from, from_byte);
              ch0 = ch1;
@@ -1306,7 +1277,7 @@ scan_words (from, count)
              if ((code != Sword
                   && (! words_include_escapes
                       || (code != Sescape && code != Scharquote)))
-                 || ! EQ (CHAR_TABLE_REF (Vchar_script_table, ch0), script))
+                 || word_boundary_p (ch0, ch1))
                {
                  INC_BOTH (from, from_byte);
                  break;
@@ -1328,8 +1299,7 @@ Normally returns t.
 If an edge of the buffer or a field boundary is reached, point is left there
 and the function returns nil.  Field boundaries are not noticed if
 `inhibit-field-text-motion' is non-nil.  */)
-     (arg)
-     Lisp_Object arg;
+  (Lisp_Object arg)
 {
   Lisp_Object tmp;
   int orig_val, val;
@@ -1352,20 +1322,19 @@ and the function returns nil.  Field boundaries are not noticed if
   return val == orig_val ? Qt : Qnil;
 }
 \f
-Lisp_Object skip_chars ();
+Lisp_Object skip_chars (int, Lisp_Object, Lisp_Object, int);
 
 DEFUN ("skip-chars-forward", Fskip_chars_forward, Sskip_chars_forward, 1, 2, 0,
        doc: /* Move point forward, stopping before a char not in STRING, or at pos LIM.
 STRING is like the inside of a `[...]' in a regular expression
 except that `]' is never special and `\\' quotes `^', `-' or `\\'
- (but not as the end of a range; quoting is never needed there).
+ (but not at the end of a range; quoting is never needed there).
 Thus, with arg "a-zA-Z", this skips letters stopping before first nonletter.
 With arg "^a-zA-Z", skips nonletters stopping before first letter.
 Char classes, e.g. `[:alpha:]', are supported.
 
 Returns the distance traveled, either zero or positive.  */)
-     (string, lim)
-     Lisp_Object string, lim;
+  (Lisp_Object string, Lisp_Object lim)
 {
   return skip_chars (1, string, lim, 1);
 }
@@ -1374,8 +1343,7 @@ DEFUN ("skip-chars-backward", Fskip_chars_backward, Sskip_chars_backward, 1, 2,
        doc: /* Move point backward, stopping after a char not in STRING, or at pos LIM.
 See `skip-chars-forward' for details.
 Returns the distance traveled, either zero or negative.  */)
-     (string, lim)
-     Lisp_Object string, lim;
+  (Lisp_Object string, Lisp_Object lim)
 {
   return skip_chars (0, string, lim, 1);
 }
@@ -1386,8 +1354,7 @@ SYNTAX is a string of syntax code characters.
 Stop before a char whose syntax is not in SYNTAX, or at position LIM.
 If SYNTAX starts with ^, skip characters whose syntax is NOT in SYNTAX.
 This function returns the distance traveled, either zero or positive.  */)
-     (syntax, lim)
-     Lisp_Object syntax, lim;
+  (Lisp_Object syntax, Lisp_Object lim)
 {
   return skip_syntaxes (1, syntax, lim);
 }
@@ -1398,17 +1365,13 @@ SYNTAX is a string of syntax code characters.
 Stop on reaching a char whose syntax is not in SYNTAX, or at position LIM.
 If SYNTAX starts with ^, skip characters whose syntax is NOT in SYNTAX.
 This function returns the distance traveled, either zero or negative.  */)
-     (syntax, lim)
-     Lisp_Object syntax, lim;
+  (Lisp_Object syntax, Lisp_Object lim)
 {
   return skip_syntaxes (0, syntax, lim);
 }
 
 static Lisp_Object
-skip_chars (forwardp, string, lim, handle_iso_classes)
-     int forwardp;
-     Lisp_Object string, lim;
-     int handle_iso_classes;
+skip_chars (int forwardp, Lisp_Object string, Lisp_Object lim, int handle_iso_classes)
 {
   register unsigned int c;
   unsigned char fastmap[0400];
@@ -1446,7 +1409,7 @@ skip_chars (forwardp, string, lim, handle_iso_classes)
               && (XINT (lim) - PT != CHAR_TO_BYTE (XINT (lim)) - PT_BYTE));
   string_multibyte = SBYTES (string) > SCHARS (string);
 
-  bzero (fastmap, sizeof fastmap);
+  memset (fastmap, 0, sizeof fastmap);
 
   str = SDATA (string);
   size_byte = SBYTES (string);
@@ -1495,7 +1458,7 @@ skip_chars (forwardp, string, lim, handle_iso_classes)
                  || *class_end != ':' || class_end[1] != ']')
                goto not_a_class_name;
 
-             bcopy (class_beg, class_name, class_end - class_beg);
+             memcpy (class_name, class_beg, class_end - class_beg);
              class_name[class_end - class_beg] = 0;
 
              cc = re_wctype (class_name);
@@ -1556,18 +1519,18 @@ skip_chars (forwardp, string, lim, handle_iso_classes)
          unsigned char fastmap2[0400];
          int range_start_byte, range_start_char;
 
-         bcopy (fastmap2 + 0200, fastmap + 0200, 0200);
-         bzero (fastmap + 0200, 0200);
+         memcpy (fastmap + 0200, fastmap2 + 0200, 0200);
+         memset (fastmap + 0200, 0, 0200);
          /* We are sure that this loop stops.  */
          for (i = 0200; ! fastmap2[i]; i++);
-         c = unibyte_char_to_multibyte (i);
+         c = BYTE8_TO_CHAR (i);
          fastmap[CHAR_LEADING_CODE (c)] = 1;
          range_start_byte = i;
          range_start_char = c;
          char_ranges = (int *) alloca (sizeof (int) * 128 * 2);
          for (i = 129; i < 0400; i++)
            {
-             c = unibyte_char_to_multibyte (i);
+             c = BYTE8_TO_CHAR (i);
              fastmap[CHAR_LEADING_CODE (c)] = 1;
              if (i - range_start_byte != c - range_start_char)
                {
@@ -1592,12 +1555,12 @@ skip_chars (forwardp, string, lim, handle_iso_classes)
          unsigned char leading_code;
 
          leading_code = str[i_byte];
-         c = STRING_CHAR_AND_LENGTH (str + i_byte, size_byte-i_byte, len);
+         c = STRING_CHAR_AND_LENGTH (str + i_byte, len);
          i_byte += len;
 
          if (handle_iso_classes && c == '['
              && i_byte < size_byte
-             && STRING_CHAR (str + i_byte, size_byte - i_byte) == ':')
+             && STRING_CHAR (str + i_byte) == ':')
            {
              const unsigned char *class_beg = str + i_byte + 1;
              const unsigned char *class_end = class_beg;
@@ -1617,7 +1580,7 @@ skip_chars (forwardp, string, lim, handle_iso_classes)
                  || *class_end != ':' || class_end[1] != ']')
                goto not_a_class_name_multibyte;
 
-             bcopy (class_beg, class_name, class_end - class_beg);
+             memcpy (class_name, class_beg, class_end - class_beg);
              class_name[class_end - class_beg] = 0;
 
              cc = re_wctype (class_name);
@@ -1637,8 +1600,7 @@ skip_chars (forwardp, string, lim, handle_iso_classes)
                break;
 
              leading_code = str[i_byte];
-             c = STRING_CHAR_AND_LENGTH (str + i_byte,
-                                         size_byte - i_byte, len);
+             c = STRING_CHAR_AND_LENGTH (str + i_byte, len);
              i_byte += len;
            }
          /* Treat `-' as range character only if another character
@@ -1654,15 +1616,14 @@ skip_chars (forwardp, string, lim, handle_iso_classes)
 
              /* Get the end of the range.  */
              leading_code2 = str[i_byte];
-             c2 = STRING_CHAR_AND_LENGTH (str + i_byte,
-                                          size_byte - i_byte, len);
+             c2 = STRING_CHAR_AND_LENGTH (str + i_byte, len);
              i_byte += len;
 
              if (c2 == '\\'
                  && i_byte < size_byte)
                {
                  leading_code2 = str[i_byte];
-                 c2 =STRING_CHAR_AND_LENGTH (str + i_byte, size_byte-i_byte, len);
+                 c2 =STRING_CHAR_AND_LENGTH (str + i_byte, len);
                  i_byte += len;
                }
 
@@ -1704,14 +1665,18 @@ skip_chars (forwardp, string, lim, handle_iso_classes)
 
       if (! multibyte && n_char_ranges > 0)
        {
-         bzero (fastmap + 0200, 0200);
+         memset (fastmap + 0200, 0, 0200);
          for (i = 0; i < n_char_ranges; i += 2)
            {
              int c1 = char_ranges[i];
              int c2 = char_ranges[i + 1];
 
              for (; c1 <= c2; c1++)
-               fastmap[CHAR_TO_BYTE8 (c1)] = 1;
+               {
+                 int b = CHAR_TO_BYTE_SAFE (c1);
+                 if (b >= 0)
+                   fastmap[b] = 1;
+               }
            }
        }
     }
@@ -1750,6 +1715,12 @@ skip_chars (forwardp, string, lim, handle_iso_classes)
       }
 
     immediate_quit = 1;
+    /* This code may look up syntax tables using macros that rely on the
+       gl_state object.  To make sure this object is not out of date,
+       let's initialize it manually.
+       We ignore syntax-table text-properties for now, since that's
+       what we've done in the past.  */
+    SETUP_BUFFER_SYNTAX_TABLE ();
     if (forwardp)
       {
        if (multibyte)
@@ -1764,7 +1735,7 @@ skip_chars (forwardp, string, lim, handle_iso_classes)
                  p = GAP_END_ADDR;
                  stop = endp;
                }
-             c = STRING_CHAR_AND_LENGTH (p, MAX_MULTIBYTE_LENGTH, nbytes);
+             c = STRING_CHAR_AND_LENGTH (p, nbytes);
              if (! NILP (iso_classes) && in_classes (c, iso_classes))
                {
                  if (negate)
@@ -1835,7 +1806,7 @@ skip_chars (forwardp, string, lim, handle_iso_classes)
                }
              prev_p = p;
              while (--p >= stop && ! CHAR_HEAD_P (*p));
-             c = STRING_CHAR (p, MAX_MULTIBYTE_LENGTH);
+             c = STRING_CHAR (p);
 
              if (! NILP (iso_classes) && in_classes (c, iso_classes))
                {
@@ -1894,9 +1865,7 @@ skip_chars (forwardp, string, lim, handle_iso_classes)
 
 
 static Lisp_Object
-skip_syntaxes (forwardp, string, lim)
-     int forwardp;
-     Lisp_Object string, lim;
+skip_syntaxes (int forwardp, Lisp_Object string, Lisp_Object lim)
 {
   register unsigned int c;
   unsigned char fastmap[0400];
@@ -1925,7 +1894,7 @@ skip_syntaxes (forwardp, string, lim)
   multibyte = (!NILP (current_buffer->enable_multibyte_characters)
               && (XINT (lim) - PT != CHAR_TO_BYTE (XINT (lim)) - PT_BYTE));
 
-  bzero (fastmap, sizeof fastmap);
+  memset (fastmap, 0, sizeof fastmap);
 
   if (SBYTES (string) > SCHARS (string))
     /* As this is very rare case (syntax spec is ASCII only), don't
@@ -1989,7 +1958,7 @@ skip_syntaxes (forwardp, string, lim)
                    p = GAP_END_ADDR;
                    stop = endp;
                  }
-               c = STRING_CHAR_AND_LENGTH (p, MAX_MULTIBYTE_LENGTH, nbytes);
+               c = STRING_CHAR_AND_LENGTH (p, nbytes);
                if (! fastmap[(int) SYNTAX (c)])
                  break;
                p += nbytes, pos++, pos_byte += nbytes;
@@ -2032,7 +2001,7 @@ skip_syntaxes (forwardp, string, lim)
                UPDATE_SYNTAX_TABLE_BACKWARD (pos - 1);
                prev_p = p;
                while (--p >= stop && ! CHAR_HEAD_P (*p));
-               c = STRING_CHAR (p, MAX_MULTIBYTE_LENGTH);
+               c = STRING_CHAR (p);
                if (! fastmap[(int) SYNTAX (c)])
                  break;
                pos--, pos_byte -= prev_p - p;
@@ -2069,13 +2038,11 @@ skip_syntaxes (forwardp, string, lim)
    integer which is its type according to re_wctype.  */
 
 static int
-in_classes (c, iso_classes)
-     int c;
-     Lisp_Object iso_classes;
+in_classes (int c, Lisp_Object iso_classes)
 {
   int fits_class = 0;
 
-  while (! NILP (iso_classes))
+  while (CONSP (iso_classes))
     {
       Lisp_Object elt;
       elt = XCAR (iso_classes);
@@ -2113,12 +2080,10 @@ in_classes (c, iso_classes)
    remains valid for forward search starting at the returned position. */
 
 static int
-forw_comment (from, from_byte, stop, nesting, style, prev_syntax,
-             charpos_ptr, bytepos_ptr, incomment_ptr)
-     EMACS_INT from, from_byte, stop;
-     int nesting, style, prev_syntax;
-     EMACS_INT *charpos_ptr, *bytepos_ptr;
-     int *incomment_ptr;
+forw_comment (EMACS_INT from, EMACS_INT from_byte, EMACS_INT stop,
+             int nesting, int style, int prev_syntax,
+             EMACS_INT *charpos_ptr, EMACS_INT *bytepos_ptr,
+             int *incomment_ptr)
 {
   register int c, c1;
   register enum syntaxcode code;
@@ -2215,8 +2180,7 @@ Stop scanning if we find something other than a comment or whitespace.
 Set point to where scanning stops.
 If COUNT comments are found as expected, with nothing except whitespace
 between them, return t; otherwise return nil.  */)
-     (count)
-     Lisp_Object count;
+  (Lisp_Object count)
 {
   register EMACS_INT from;
   EMACS_INT from_byte;
@@ -2424,10 +2388,7 @@ between them, return t; otherwise return nil.  */)
    ? SYNTAX (c) : Ssymbol)
 
 static Lisp_Object
-scan_lists (from, count, depth, sexpflag)
-     register EMACS_INT from;
-     EMACS_INT count, depth;
-     int sexpflag;
+scan_lists (register EMACS_INT from, EMACS_INT count, EMACS_INT depth, int sexpflag)
 {
   Lisp_Object val;
   register EMACS_INT stop = count > 0 ? ZV : BEGV;
@@ -2822,8 +2783,7 @@ Comments are ignored if `parse-sexp-ignore-comments' is non-nil.
 If the beginning or end of (the accessible part of) the buffer is reached
 and the depth is wrong, an error is signaled.
 If the depth is right but the count is not used up, nil is returned.  */)
-     (from, count, depth)
-     Lisp_Object from, count, depth;
+  (Lisp_Object from, Lisp_Object count, Lisp_Object depth)
 {
   CHECK_NUMBER (from);
   CHECK_NUMBER (count);
@@ -2843,8 +2803,7 @@ If the beginning or end of (the accessible part of) the buffer is reached
 in the middle of a parenthetical grouping, an error is signaled.
 If the beginning or end is reached between groupings
 but before count is used up, nil is returned.  */)
-     (from, count)
-     Lisp_Object from, count;
+  (Lisp_Object from, Lisp_Object count)
 {
   CHECK_NUMBER (from);
   CHECK_NUMBER (count);
@@ -2856,7 +2815,7 @@ DEFUN ("backward-prefix-chars", Fbackward_prefix_chars, Sbackward_prefix_chars,
        0, 0, 0,
        doc: /* Move point backward over any number of chars with prefix syntax.
 This includes chars with "quote" or "prefix" syntax (' or p).  */)
-     ()
+  (void)
 {
   int beg = BEGV;
   int opoint = PT;
@@ -2902,14 +2861,10 @@ This includes chars with "quote" or "prefix" syntax (' or p).  */)
    after the beginning of a string, or after the end of a string.  */
 
 static void
-scan_sexps_forward (stateptr, from, from_byte, end, targetdepth,
-                   stopbefore, oldstate, commentstop)
-     struct lisp_parse_state *stateptr;
-     register int from;
-     int from_byte;
-     int end, targetdepth, stopbefore;
-     Lisp_Object oldstate;
-     int commentstop;
+scan_sexps_forward (struct lisp_parse_state *stateptr,
+                   EMACS_INT from, EMACS_INT from_byte, EMACS_INT end,
+                   int targetdepth, int stopbefore,
+                   Lisp_Object oldstate, int commentstop)
 {
   struct lisp_parse_state state;
 
@@ -2926,8 +2881,8 @@ scan_sexps_forward (stateptr, from, from_byte, end, targetdepth,
   int mindepth;                /* Lowest DEPTH value seen.  */
   int start_quoted = 0;                /* Nonzero means starting after a char quote */
   Lisp_Object tem;
-  int prev_from;               /* Keep one character before FROM.  */
-  int prev_from_byte;
+  EMACS_INT prev_from;         /* Keep one character before FROM.  */
+  EMACS_INT prev_from_byte;
   int prev_from_syntax;
   int boundary_stop = commentstop == -1;
   int nofence;
@@ -3280,8 +3235,7 @@ Fifth arg OLDSTATE is a list like what this function returns.
 Sixth arg COMMENTSTOP non-nil means stop at the start of a comment.
  If it is symbol `syntax-table', stop after the start of a comment or a
  string, or after end of a comment or a string.  */)
-     (from, to, targetdepth, stopbefore, oldstate, commentstop)
-     Lisp_Object from, to, targetdepth, stopbefore, oldstate, commentstop;
+  (Lisp_Object from, Lisp_Object to, Lisp_Object targetdepth, Lisp_Object stopbefore, Lisp_Object oldstate, Lisp_Object commentstop)
 {
   struct lisp_parse_state state;
   int target;
@@ -3326,19 +3280,19 @@ Sixth arg COMMENTSTOP non-nil means stop at the start of a comment.
 }
 \f
 void
-init_syntax_once ()
+init_syntax_once (void)
 {
   register int i, c;
   Lisp_Object temp;
 
   /* This has to be done here, before we call Fmake_char_table.  */
-  Qsyntax_table = intern ("syntax-table");
+  Qsyntax_table = intern_c_string ("syntax-table");
   staticpro (&Qsyntax_table);
 
-  /* Intern this now in case it isn't already done.
+  /* Intern_C_String this now in case it isn't already done.
      Setting this variable twice is harmless.
      But don't staticpro it here--that is done in alloc.c.  */
-  Qchar_table_extra_slots = intern ("char-table-extra-slots");
+  Qchar_table_extra_slots = intern_c_string ("char-table-extra-slots");
 
   /* Create objects which can be shared among syntax tables.  */
   Vsyntax_code_object = Fmake_vector (make_number (Smax), Qnil);
@@ -3416,9 +3370,9 @@ init_syntax_once ()
 }
 
 void
-syms_of_syntax ()
+syms_of_syntax (void)
 {
-  Qsyntax_table_p = intern ("syntax-table-p");
+  Qsyntax_table_p = intern_c_string ("syntax-table-p");
   staticpro (&Qsyntax_table_p);
 
   staticpro (&Vsyntax_code_object);
@@ -3431,12 +3385,12 @@ syms_of_syntax ()
   /* Defined in regex.c */
   staticpro (&re_match_object);
 
-  Qscan_error = intern ("scan-error");
+  Qscan_error = intern_c_string ("scan-error");
   staticpro (&Qscan_error);
   Fput (Qscan_error, Qerror_conditions,
-       Fcons (Qscan_error, Fcons (Qerror, Qnil)));
+       pure_cons (Qscan_error, pure_cons (Qerror, Qnil)));
   Fput (Qscan_error, Qerror_message,
-       build_string ("Scan error"));
+       make_pure_c_string ("Scan error"));
 
   DEFVAR_BOOL ("parse-sexp-ignore-comments", &parse_sexp_ignore_comments,
               doc: /* Non-nil means `forward-sexp', etc., should treat comments as whitespace.  */);