Mercurial > hg > xemacs-beta
comparison src/syntax.c @ 70:131b0175ea99 r20-0b30
Import from CVS: tag r20-0b30
author | cvs |
---|---|
date | Mon, 13 Aug 2007 09:02:59 +0200 |
parents | 859a2309aef8 |
children | c7528f8e288d |
comparison
equal
deleted
inserted
replaced
69:804d1389bcd6 | 70:131b0175ea99 |
---|---|
19 the Free Software Foundation, Inc., 59 Temple Place - Suite 330, | 19 the Free Software Foundation, Inc., 59 Temple Place - Suite 330, |
20 Boston, MA 02111-1307, USA. */ | 20 Boston, MA 02111-1307, USA. */ |
21 | 21 |
22 /* Synched up with: FSF 19.28. */ | 22 /* Synched up with: FSF 19.28. */ |
23 | 23 |
24 /* This file has been Mule-ized. */ | |
25 | |
24 #include <config.h> | 26 #include <config.h> |
25 #include "lisp.h" | 27 #include "lisp.h" |
26 | 28 |
27 #include "buffer.h" | 29 #include "buffer.h" |
28 #include "commands.h" | 30 #include "commands.h" |
29 #include "insdel.h" | 31 #include "insdel.h" |
30 #include "syntax.h" | 32 #include "syntax.h" |
33 | |
34 /* Here is a comment from Ken'ichi HANDA <handa@etl.go.jp> | |
35 explaining the purpose of the Sextword syntax category: | |
36 | |
37 Japanese words are not separated by spaces, which makes finding word | |
38 boundaries very difficult. Theoretically it's impossible without | |
39 using natural language processing techniques. But, by defining | |
40 pseudo-words as below (much simplified for letting you understand it | |
41 easily) for Japanese, we can have a convenient forward-word function | |
42 for Japanese. | |
43 | |
44 A Japanese word is a sequence of characters that consists of | |
45 zero or more Kanji characters followed by zero or more | |
46 Hiragana characters. | |
47 | |
48 Then, the problem is that now we can't say that a sequence of | |
49 word-constituents makes up a WORD. For instance, both Hiragana "A" | |
50 and Kanji "KAN" are word-constituents but the sequence of these two | |
51 letters can't be a single word. | |
52 | |
53 So, we introduced Sextword for Japanese letters. A character of | |
54 Sextword is a word-constituent but a word boundary may exist between | |
55 two such characters. */ | |
56 | |
57 /* Mule 2.4 doesn't seem to have Sextword - I'm removing it -- mrb */ | |
31 | 58 |
32 Lisp_Object Qsyntax_table_p; | 59 Lisp_Object Qsyntax_table_p; |
33 | 60 |
34 int words_include_escapes; | 61 int words_include_escapes; |
35 | 62 |
89 | 116 |
90 static Bufpos | 117 static Bufpos |
91 find_defun_start (struct buffer *buf, Bufpos pos) | 118 find_defun_start (struct buffer *buf, Bufpos pos) |
92 { | 119 { |
93 Bufpos tem; | 120 Bufpos tem; |
94 Lisp_Object syntaxtab = buf->syntax_table; | 121 struct Lisp_Char_Table *mirrortab = XCHAR_TABLE (buf->mirror_syntax_table); |
95 | 122 |
96 /* Use previous finding, if it's valid and applies to this inquiry. */ | 123 /* Use previous finding, if it's valid and applies to this inquiry. */ |
97 if (buf == find_start_buffer | 124 if (buf == find_start_buffer |
98 /* Reuse the defun-start even if POS is a little farther on. | 125 /* Reuse the defun-start even if POS is a little farther on. |
99 POS might be in the next defun, but that's ok. | 126 POS might be in the next defun, but that's ok. |
108 tem = find_next_newline (buf, pos, -1); | 135 tem = find_next_newline (buf, pos, -1); |
109 | 136 |
110 while (tem > BUF_BEGV (buf)) | 137 while (tem > BUF_BEGV (buf)) |
111 { | 138 { |
112 /* Open-paren at start of line means we found our defun-start. */ | 139 /* Open-paren at start of line means we found our defun-start. */ |
113 if (SYNTAX (syntaxtab, BUF_FETCH_CHAR (buf, tem)) == Sopen) | 140 if (SYNTAX (mirrortab, BUF_FETCH_CHAR (buf, tem)) == Sopen) |
114 break; | 141 break; |
115 /* Move to beg of previous line. */ | 142 /* Move to beg of previous line. */ |
116 tem = find_next_newline (buf, tem, -2); | 143 tem = find_next_newline (buf, tem, -2); |
117 } | 144 } |
118 | 145 |
130 Return t if ARG is a syntax table. | 157 Return t if ARG is a syntax table. |
131 Any vector of 256 elements will do. | 158 Any vector of 256 elements will do. |
132 */ | 159 */ |
133 (obj)) | 160 (obj)) |
134 { | 161 { |
135 if (VECTORP (obj) && vector_length (XVECTOR (obj)) == 0400) | 162 if (CHAR_TABLEP (obj) && XCHAR_TABLE_TYPE (obj) == CHAR_TABLE_TYPE_SYNTAX) |
136 return Qt; | 163 return Qt; |
137 return Qnil; | 164 return Qnil; |
138 } | 165 } |
139 | 166 |
140 static Lisp_Object | 167 static Lisp_Object |
171 It is a copy of the TABLE, which defaults to the standard syntax table. | 198 It is a copy of the TABLE, which defaults to the standard syntax table. |
172 */ | 199 */ |
173 (table)) | 200 (table)) |
174 { | 201 { |
175 if (NILP (Vstandard_syntax_table)) | 202 if (NILP (Vstandard_syntax_table)) |
176 /* Can only be null during initialization */ | 203 return Fmake_char_table (Qsyntax); |
177 return make_vector (0400, Qzero); | |
178 | 204 |
179 table = check_syntax_table (table, Vstandard_syntax_table); | 205 table = check_syntax_table (table, Vstandard_syntax_table); |
180 return Fcopy_sequence (table); | 206 return Fcopy_char_table (table); |
181 } | 207 } |
182 | 208 |
183 DEFUN ("set-syntax-table", Fset_syntax_table, 1, 2, 0, /* | 209 DEFUN ("set-syntax-table", Fset_syntax_table, 1, 2, 0, /* |
184 Select a new syntax table for BUFFER. | 210 Select a new syntax table for BUFFER. |
185 One argument, a syntax table. | 211 One argument, a syntax table. |
188 (table, buffer)) | 214 (table, buffer)) |
189 { | 215 { |
190 struct buffer *buf = decode_buffer (buffer, 0); | 216 struct buffer *buf = decode_buffer (buffer, 0); |
191 table = check_syntax_table (table, Qnil); | 217 table = check_syntax_table (table, Qnil); |
192 buf->syntax_table = table; | 218 buf->syntax_table = table; |
219 buf->mirror_syntax_table = XCHAR_TABLE (table)->mirror_table; | |
193 /* Indicate that this buffer now has a specified syntax table. */ | 220 /* Indicate that this buffer now has a specified syntax table. */ |
194 buf->local_var_flags |= XINT (buffer_local_flags.syntax_table); | 221 buf->local_var_flags |= XINT (buffer_local_flags.syntax_table); |
195 return table; | 222 return table; |
196 } | 223 } |
197 | 224 |
198 /* Convert a letter which signifies a syntax code | 225 /* Convert a letter which signifies a syntax code |
199 into the code it signifies. | 226 into the code it signifies. |
200 This is used by modify-syntax-entry, and other things. */ | 227 This is used by modify-syntax-entry, and other things. */ |
201 | 228 |
202 CONST unsigned char syntax_spec_code[0400] = | 229 CONST unsigned char syntax_spec_code[0400] = |
203 { 0377, 0377, 0377, 0377, 0377, 0377, 0377, 0377, | 230 { 0377, 0377, 0377, 0377, 0377, 0377, 0377, 0377, |
204 0377, 0377, 0377, 0377, 0377, 0377, 0377, 0377, | 231 0377, 0377, 0377, 0377, 0377, 0377, 0377, 0377, |
205 0377, 0377, 0377, 0377, 0377, 0377, 0377, 0377, | 232 0377, 0377, 0377, 0377, 0377, 0377, 0377, 0377, |
206 0377, 0377, 0377, 0377, 0377, 0377, 0377, 0377, | 233 0377, 0377, 0377, 0377, 0377, 0377, 0377, 0377, |
207 (char) Swhitespace, 0377, (char) Sstring, 0377, | 234 (char) Swhitespace, 0377, (char) Sstring, 0377, |
208 (char) Smath, 0377, 0377, (char) Squote, | 235 (char) Smath, 0377, 0377, (char) Squote, |
209 (char) Sopen, (char) Sclose, 0377, 0377, | 236 (char) Sopen, (char) Sclose, 0377, 0377, |
210 0377, (char) Swhitespace, (char) Spunct, (char) Scharquote, | 237 0377, (char) Swhitespace, (char) Spunct, (char) Scharquote, |
211 0377, 0377, 0377, 0377, 0377, 0377, 0377, 0377, | 238 0377, 0377, 0377, 0377, 0377, 0377, 0377, 0377, |
212 0377, 0377, 0377, 0377, | 239 0377, 0377, 0377, 0377, |
213 (char) Scomment, 0377, (char) Sendcomment, 0377, | 240 (char) Scomment, 0377, (char) Sendcomment, 0377, |
214 (char) Sinherit, 0377, 0377, 0377, 0377, 0377, 0377, 0377, /* @, A ... */ | 241 (char) Sinherit, 0377, 0377, 0377, 0377, 0377, 0377, 0377, /* @, A ... */ |
215 0377, 0377, 0377, 0377, 0377, 0377, 0377, 0377, | 242 0377, 0377, 0377, 0377, 0377, 0377, 0377, 0377, |
216 0377, 0377, 0377, 0377, 0377, 0377, 0377, (char) Sword, | 243 0377, 0377, 0377, 0377, 0377, 0377, 0377, (char) Sword, |
217 0377, 0377, 0377, 0377, (char) Sescape, 0377, 0377, (char) Ssymbol, | 244 0377, 0377, 0377, 0377, (char) Sescape, 0377, 0377, (char) Ssymbol, |
218 0377, 0377, 0377, 0377, 0377, Sextword, 0377, 0377, /* `, a, ... */ | 245 0377, 0377, 0377, 0377, 0377, 0377, 0377, 0377, /* `, a, ... */ |
219 0377, 0377, 0377, 0377, 0377, 0377, 0377, 0377, | 246 0377, 0377, 0377, 0377, 0377, 0377, 0377, 0377, |
220 0377, 0377, 0377, 0377, 0377, 0377, 0377, (char) Sword, | 247 0377, 0377, 0377, 0377, 0377, 0377, 0377, (char) Sword, |
221 0377, 0377, 0377, 0377, 0377, 0377, 0377, 0377 | 248 0377, 0377, 0377, 0377, 0377, 0377, 0377, 0377 |
222 }; | 249 }; |
223 | 250 |
224 CONST unsigned char syntax_code_spec[] = | 251 CONST unsigned char syntax_code_spec[] = " .w_()'\"$\\/<>@"; |
225 { | |
226 ' ', '.', 'w', '_', '(', ')', '\'', '\"', '$', '\\', '/', '<', '>', '@', | |
227 'e', '\0' | |
228 }; | |
229 | 252 |
230 DEFUN ("syntax-designator-chars", Fsyntax_designator_chars, 0, 0, 0, /* | 253 DEFUN ("syntax-designator-chars", Fsyntax_designator_chars, 0, 0, 0, /* |
231 Return a string of the recognized syntax designator chars. | 254 Return a string of the recognized syntax designator chars. |
232 The chars are ordered by their internal syntax codes, which are | 255 The chars are ordered by their internal syntax codes, which are |
233 numbered starting at 0. | 256 numbered starting at 0. |
245 Optional second argument TABLE defaults to the current buffer's | 268 Optional second argument TABLE defaults to the current buffer's |
246 syntax table. | 269 syntax table. |
247 */ | 270 */ |
248 (ch, table)) | 271 (ch, table)) |
249 { | 272 { |
273 struct Lisp_Char_Table *mirrortab; | |
274 | |
250 CHECK_CHAR_COERCE_INT (ch); | 275 CHECK_CHAR_COERCE_INT (ch); |
251 table = check_syntax_table (table, current_buffer->syntax_table); | 276 table = check_syntax_table (table, current_buffer->syntax_table); |
252 | 277 mirrortab = XCHAR_TABLE (XCHAR_TABLE (table)->mirror_table); |
253 return make_int (syntax_code_spec[(int) SYNTAX (table, XINT (ch))]); | 278 return make_char (syntax_code_spec[(int) SYNTAX (mirrortab, XCHAR (ch))]); |
254 } | 279 } |
255 | 280 |
281 #ifdef MULE | |
282 | |
283 enum syntaxcode | |
284 charset_syntax (struct buffer *buf, Lisp_Object charset, int *multi_p_out) | |
285 { | |
286 *multi_p_out = 1; | |
287 /* #### get this right */ | |
288 return Spunct; | |
289 } | |
290 | |
291 #endif | |
256 | 292 |
257 Lisp_Object | 293 Lisp_Object |
258 syntax_match (Lisp_Object table, Emchar ch) | 294 syntax_match (Lisp_Object table, Emchar ch) |
259 { | 295 { |
260 unsigned char stringterm = ((SYNTAX_CODE (table, ch) >> 8) & 0377); | 296 Lisp_Object code = CHAR_TABLE_VALUE_UNSAFE (XCHAR_TABLE (table), ch); |
261 | 297 Lisp_Object code2 = code; |
262 if (stringterm == 0) | 298 |
299 if (CONSP (code)) | |
300 code2 = XCAR (code); | |
301 if (SYNTAX_FROM_CODE (XINT (code2)) == Sinherit) | |
302 code = CHAR_TABLE_VALUE_UNSAFE (XCHAR_TABLE (Vstandard_syntax_table), | |
303 ch); | |
304 if (CONSP (code)) | |
305 return XCDR (code); | |
306 else | |
263 return Qnil; | 307 return Qnil; |
264 else | |
265 return make_char (stringterm); | |
266 } | 308 } |
267 | 309 |
268 DEFUN ("matching-paren", Fmatching_paren, 1, 2, 0, /* | 310 DEFUN ("matching-paren", Fmatching_paren, 1, 2, 0, /* |
269 Return the matching parenthesis of CHAR, or nil if none. | 311 Return the matching parenthesis of CHAR, or nil if none. |
270 Optional second argument TABLE defaults to the current buffer's | 312 Optional second argument TABLE defaults to the current buffer's |
271 syntax table. | 313 syntax table. |
272 */ | 314 */ |
273 (ch, table)) | 315 (ch, table)) |
274 { | 316 { |
317 struct Lisp_Char_Table *mirrortab; | |
275 int code; | 318 int code; |
319 | |
276 CHECK_CHAR_COERCE_INT (ch); | 320 CHECK_CHAR_COERCE_INT (ch); |
277 | |
278 table = check_syntax_table (table, current_buffer->syntax_table); | 321 table = check_syntax_table (table, current_buffer->syntax_table); |
279 code = SYNTAX (table, XCHAR (ch)); | 322 mirrortab = XCHAR_TABLE (XCHAR_TABLE (table)->mirror_table); |
323 code = SYNTAX (mirrortab, XCHAR (ch)); | |
280 if (code == Sopen || code == Sclose || code == Sstring) | 324 if (code == Sopen || code == Sclose || code == Sstring) |
281 return syntax_match (table, XCHAR (ch)); | 325 return syntax_match (table, XCHAR (ch)); |
282 return Qnil; | 326 return Qnil; |
283 } | 327 } |
284 | 328 |
285 | 329 |
330 | |
331 INLINE int | |
332 word_constituent_p (struct buffer *buf, Bufpos pos, | |
333 struct Lisp_Char_Table *tab) | |
334 { | |
335 enum syntaxcode code = SYNTAX_UNSAFE (tab, BUF_FETCH_CHAR (buf, pos)); | |
336 return ((words_include_escapes && | |
337 (code == Sescape || code == Scharquote)) | |
338 || (code == Sword)); | |
339 } | |
340 | |
286 /* Return the position across COUNT words from FROM. | 341 /* Return the position across COUNT words from FROM. |
287 If that many words cannot be found before the end of the buffer, return 0. | 342 If that many words cannot be found before the end of the buffer, return 0. |
288 COUNT negative means scan backward and stop at word beginning. */ | 343 COUNT negative means scan backward and stop at word beginning. */ |
289 | 344 |
290 Bufpos | 345 Bufpos |
291 scan_words (struct buffer *buf, Bufpos from, int count) | 346 scan_words (struct buffer *buf, Bufpos from, int count) |
292 { | 347 { |
293 Bufpos beg = BUF_BEGV (buf); | 348 Bufpos limit = count > 0 ? BUF_ZV (buf) : BUF_BEGV (buf); |
294 Bufpos end = BUF_ZV (buf); | 349 struct Lisp_Char_Table *mirrortab = XCHAR_TABLE (buf->mirror_syntax_table); |
295 enum syntaxcode code; | |
296 Lisp_Object table = buf->syntax_table; | |
297 | |
298 while (count > 0) | 350 while (count > 0) |
299 { | 351 { |
300 QUIT; | 352 QUIT; |
301 | 353 |
302 while (1) | 354 while (1) |
303 { | 355 { |
304 Emchar ch; | 356 if (from == limit) |
305 if (from == end) | 357 return 0; |
306 { | 358 if (word_constituent_p (buf, from, mirrortab)) |
307 return 0; | |
308 } | |
309 ch = BUF_FETCH_CHAR (buf, from); | |
310 code = SYNTAX_UNSAFE (table, ch); | |
311 if (words_include_escapes | |
312 && (code == Sescape || code == Scharquote)) | |
313 break; | |
314 if (code == Sword || code == Sextword) | |
315 break; | 359 break; |
316 from++; | 360 from++; |
317 } | 361 } |
318 | 362 |
319 QUIT; | 363 QUIT; |
320 | 364 |
365 while ((from != limit) && word_constituent_p (buf, from, mirrortab)) | |
366 { | |
367 from++; | |
368 } | |
369 count--; | |
370 } | |
371 | |
372 while (count < 0) | |
373 { | |
374 QUIT; | |
375 | |
321 while (1) | 376 while (1) |
322 { | 377 { |
323 Emchar ch; | 378 if (from == limit) |
324 if (from == end) break; | 379 return 0; |
325 ch = BUF_FETCH_CHAR (buf, from); | 380 if (word_constituent_p (buf, from - 1, mirrortab)) |
326 code = SYNTAX_UNSAFE (table, ch); | |
327 if (!(words_include_escapes | |
328 && (code == Sescape || code == Scharquote))) | |
329 if (code != Sword && code != Sextword) | |
330 break; | |
331 from++; | |
332 } | |
333 | |
334 count--; | |
335 } | |
336 while (count < 0) | |
337 { | |
338 QUIT; | |
339 | |
340 while (1) | |
341 { | |
342 Emchar ch; | |
343 if (from == beg) | |
344 { | |
345 return 0; | |
346 } | |
347 ch = BUF_FETCH_CHAR (buf, from - 1); | |
348 code = SYNTAX_UNSAFE (table, ch); | |
349 if (words_include_escapes | |
350 && (code == Sescape || code == Scharquote)) | |
351 break; | |
352 if (code == Sword || code == Sextword) | |
353 break; | 381 break; |
354 from--; | 382 from--; |
355 } | 383 } |
356 | 384 |
357 QUIT; | 385 QUIT; |
358 | 386 |
359 while (1) | 387 while ((from != limit) && word_constituent_p (buf, from - 1, mirrortab)) |
360 { | 388 { |
361 Emchar ch; | |
362 if (from == beg) break; | |
363 ch = BUF_FETCH_CHAR (buf, from - 1); | |
364 code = SYNTAX_UNSAFE (table, ch); | |
365 if (!(words_include_escapes | |
366 && (code == Sescape || code == Scharquote))) | |
367 if (code != Sword && code != Sextword) | |
368 break; | |
369 from--; | 389 from--; |
370 } | 390 } |
371 count++; | 391 count++; |
372 } | 392 } |
373 | 393 |
405 static int | 425 static int |
406 find_start_of_comment (struct buffer *buf, Bufpos from, Bufpos stop, int mask) | 426 find_start_of_comment (struct buffer *buf, Bufpos from, Bufpos stop, int mask) |
407 { | 427 { |
408 Emchar c; | 428 Emchar c; |
409 enum syntaxcode code; | 429 enum syntaxcode code; |
410 Lisp_Object table = buf->syntax_table; | 430 struct Lisp_Char_Table *mirrortab = XCHAR_TABLE (buf->mirror_syntax_table); |
411 | 431 |
412 /* Look back, counting the parity of string-quotes, | 432 /* Look back, counting the parity of string-quotes, |
413 and recording the comment-starters seen. | 433 and recording the comment-starters seen. |
414 When we reach a safe place, assume that's not in a string; | 434 When we reach a safe place, assume that's not in a string; |
415 then step the main scan to the earliest comment-starter seen | 435 then step the main scan to the earliest comment-starter seen |
432 { | 452 { |
433 /* Move back and examine a character. */ | 453 /* Move back and examine a character. */ |
434 from--; | 454 from--; |
435 | 455 |
436 c = BUF_FETCH_CHAR (buf, from); | 456 c = BUF_FETCH_CHAR (buf, from); |
437 code = SYNTAX_UNSAFE (table, c); | 457 code = SYNTAX_UNSAFE (mirrortab, c); |
438 | 458 |
439 /* is this a 1-char comment end sequence? if so, try | 459 /* is this a 1-char comment end sequence? if so, try |
440 to see if style matches previously extracted mask */ | 460 to see if style matches previously extracted mask */ |
441 if (code == Sendcomment) | 461 if (code == Sendcomment) |
442 { | 462 { |
443 styles_match_p = SYNTAX_STYLES_MATCH_1CHAR_P (table, c, mask); | 463 styles_match_p = SYNTAX_STYLES_MATCH_1CHAR_P (mirrortab, c, mask); |
444 } | 464 } |
445 | 465 |
446 /* otherwise, is this a 2-char comment end sequence? */ | 466 /* otherwise, is this a 2-char comment end sequence? */ |
447 else if (from >= stop | 467 else if (from >= stop |
448 && SYNTAX_END_P (table, c, BUF_FETCH_CHAR (buf, from+1))) | 468 && SYNTAX_END_P (mirrortab, c, BUF_FETCH_CHAR (buf, from+1))) |
449 { | 469 { |
450 code = Sendcomment; | 470 code = Sendcomment; |
451 styles_match_p = | 471 styles_match_p = |
452 SYNTAX_STYLES_MATCH_END_P (table, c, | 472 SYNTAX_STYLES_MATCH_END_P (mirrortab, c, |
453 BUF_FETCH_CHAR (buf, from+1), | 473 BUF_FETCH_CHAR (buf, from+1), |
454 mask); | 474 mask); |
455 } | 475 } |
456 | 476 |
457 /* or are we looking at a 1-char comment start sequence | 477 /* or are we looking at a 1-char comment start sequence |
458 of the style matching mask? */ | 478 of the style matching mask? */ |
459 else if (code == Scomment | 479 else if (code == Scomment |
460 && SYNTAX_STYLES_MATCH_1CHAR_P (table, c, mask)) | 480 && SYNTAX_STYLES_MATCH_1CHAR_P (mirrortab, c, mask)) |
461 { | 481 { |
462 styles_match_p = 1; | 482 styles_match_p = 1; |
463 } | 483 } |
464 | 484 |
465 /* or possibly, a 2-char comment start sequence */ | 485 /* or possibly, a 2-char comment start sequence */ |
466 else if (from >= stop | 486 else if (from >= stop |
467 && SYNTAX_STYLES_MATCH_START_P (table, c, | 487 && SYNTAX_STYLES_MATCH_START_P (mirrortab, c, |
468 BUF_FETCH_CHAR (buf, from+1), | 488 BUF_FETCH_CHAR (buf, from+1), |
469 mask)) | 489 mask)) |
470 { | 490 { |
471 code = Scomment; | 491 code = Scomment; |
472 styles_match_p = 1; | 492 styles_match_p = 1; |
539 | 559 |
540 static Bufpos | 560 static Bufpos |
541 find_end_of_comment (struct buffer *buf, Bufpos from, Bufpos stop, int mask) | 561 find_end_of_comment (struct buffer *buf, Bufpos from, Bufpos stop, int mask) |
542 { | 562 { |
543 int c; | 563 int c; |
544 Lisp_Object table = buf->syntax_table; | 564 struct Lisp_Char_Table *mirrortab = XCHAR_TABLE (buf->mirror_syntax_table); |
545 | 565 |
546 while (1) | 566 while (1) |
547 { | 567 { |
548 if (from == stop) | 568 if (from == stop) |
549 { | 569 { |
550 return -1; | 570 return -1; |
551 } | 571 } |
552 c = BUF_FETCH_CHAR (buf, from); | 572 c = BUF_FETCH_CHAR (buf, from); |
553 if (SYNTAX_UNSAFE (table, c) == Sendcomment | 573 if (SYNTAX_UNSAFE (mirrortab, c) == Sendcomment |
554 && SYNTAX_STYLES_MATCH_1CHAR_P (table, c, mask)) | 574 && SYNTAX_STYLES_MATCH_1CHAR_P (mirrortab, c, mask)) |
555 /* we have encountered a comment end of the same style | 575 /* we have encountered a comment end of the same style |
556 as the comment sequence which began this comment | 576 as the comment sequence which began this comment |
557 section */ | 577 section */ |
558 break; | 578 break; |
559 | 579 |
560 from++; | 580 from++; |
561 if (from < stop | 581 if (from < stop |
562 && SYNTAX_STYLES_MATCH_END_P (table, c, | 582 && SYNTAX_STYLES_MATCH_END_P (mirrortab, c, |
563 BUF_FETCH_CHAR (buf, from), mask)) | 583 BUF_FETCH_CHAR (buf, from), mask)) |
564 /* we have encountered a comment end of the same style | 584 /* we have encountered a comment end of the same style |
565 as the comment sequence which began this comment | 585 as the comment sequence which began this comment |
566 section */ | 586 section */ |
567 { from++; break; } | 587 { from++; break; } |
592 Bufpos stop; | 612 Bufpos stop; |
593 Emchar c; | 613 Emchar c; |
594 enum syntaxcode code; | 614 enum syntaxcode code; |
595 int count; | 615 int count; |
596 struct buffer *buf = decode_buffer (buffer, 0); | 616 struct buffer *buf = decode_buffer (buffer, 0); |
597 Lisp_Object table = buf->syntax_table; | 617 struct Lisp_Char_Table *mirrortab = XCHAR_TABLE (buf->mirror_syntax_table); |
598 | 618 |
599 CHECK_INT (n); | 619 CHECK_INT (n); |
600 count = XINT (n); | 620 count = XINT (n); |
601 | 621 |
602 from = BUF_PT (buf); | 622 from = BUF_PT (buf); |
615 from++; | 635 from++; |
616 continue; | 636 continue; |
617 } | 637 } |
618 | 638 |
619 c = BUF_FETCH_CHAR (buf, from); | 639 c = BUF_FETCH_CHAR (buf, from); |
620 code = SYNTAX (table, c); | 640 code = SYNTAX (mirrortab, c); |
621 | 641 |
622 if (code == Scomment) | 642 if (code == Scomment) |
623 { | 643 { |
624 /* we have encountered a single character comment start | 644 /* we have encountered a single character comment start |
625 sequence, and we are ignoring all text inside comments. | 645 sequence, and we are ignoring all text inside comments. |
626 we must record the comment style this character begins | 646 we must record the comment style this character begins |
627 so that later, only a comment end of the same style actually | 647 so that later, only a comment end of the same style actually |
628 ends the comment section */ | 648 ends the comment section */ |
629 mask = SYNTAX_COMMENT_1CHAR_MASK (table, c); | 649 mask = SYNTAX_COMMENT_1CHAR_MASK (mirrortab, c); |
630 } | 650 } |
631 | 651 |
632 else if (from < stop | 652 else if (from < stop |
633 && SYNTAX_START_P (table, c, BUF_FETCH_CHAR (buf, from+1))) | 653 && SYNTAX_START_P (mirrortab, c, BUF_FETCH_CHAR (buf, from+1))) |
634 { | 654 { |
635 /* we have encountered a 2char comment start sequence and we | 655 /* we have encountered a 2char comment start sequence and we |
636 are ignoring all text inside comments. we must record | 656 are ignoring all text inside comments. we must record |
637 the comment style this sequence begins so that later, | 657 the comment style this sequence begins so that later, |
638 only a comment end of the same style actually ends | 658 only a comment end of the same style actually ends |
639 the comment section */ | 659 the comment section */ |
640 code = Scomment; | 660 code = Scomment; |
641 mask = SYNTAX_COMMENT_MASK_START (table, c, | 661 mask = SYNTAX_COMMENT_MASK_START (mirrortab, c, |
642 BUF_FETCH_CHAR (buf, from+1)); | 662 BUF_FETCH_CHAR (buf, from+1)); |
643 from++; | 663 from++; |
644 } | 664 } |
645 | 665 |
646 if (code == Scomment) | 666 if (code == Scomment) |
688 from--; | 708 from--; |
689 continue; | 709 continue; |
690 } | 710 } |
691 | 711 |
692 c = BUF_FETCH_CHAR (buf, from); | 712 c = BUF_FETCH_CHAR (buf, from); |
693 code = SYNTAX (table, c); | 713 code = SYNTAX (mirrortab, c); |
694 | 714 |
695 if (code == Sendcomment) | 715 if (code == Sendcomment) |
696 { | 716 { |
697 /* we have found a single char end comment. we must record | 717 /* we have found a single char end comment. we must record |
698 the comment style encountered so that later, we can match | 718 the comment style encountered so that later, we can match |
699 only the proper comment begin sequence of the same style */ | 719 only the proper comment begin sequence of the same style */ |
700 mask = SYNTAX_COMMENT_1CHAR_MASK (table, c); | 720 mask = SYNTAX_COMMENT_1CHAR_MASK (mirrortab, c); |
701 } | 721 } |
702 | 722 |
703 else if (from > stop | 723 else if (from > stop |
704 && SYNTAX_END_P (table, BUF_FETCH_CHAR (buf, from - 1), c) | 724 && SYNTAX_END_P (mirrortab, BUF_FETCH_CHAR (buf, from - 1), c) |
705 && !char_quoted (buf, from - 1)) | 725 && !char_quoted (buf, from - 1)) |
706 { | 726 { |
707 /* We must record the comment style encountered so that | 727 /* We must record the comment style encountered so that |
708 later, we can match only the proper comment begin | 728 later, we can match only the proper comment begin |
709 sequence of the same style. */ | 729 sequence of the same style. */ |
710 code = Sendcomment; | 730 code = Sendcomment; |
711 mask = SYNTAX_COMMENT_MASK_END (table, | 731 mask = SYNTAX_COMMENT_MASK_END (mirrortab, |
712 BUF_FETCH_CHAR (buf, from - 1), | 732 BUF_FETCH_CHAR (buf, from - 1), |
713 c); | 733 c); |
714 from--; | 734 from--; |
715 } | 735 } |
716 | 736 |
719 from = find_start_of_comment (buf, from, stop, mask); | 739 from = find_start_of_comment (buf, from, stop, mask); |
720 break; | 740 break; |
721 } | 741 } |
722 | 742 |
723 else if (code != Swhitespace | 743 else if (code != Swhitespace |
724 && SYNTAX (table, c) != Scomment | 744 && SYNTAX (mirrortab, c) != Scomment |
725 && SYNTAX (table, c) != Sendcomment) | 745 && SYNTAX (mirrortab, c) != Sendcomment) |
726 { | 746 { |
727 BUF_SET_PT (buf, from + 1); | 747 BUF_SET_PT (buf, from + 1); |
728 return Qnil; | 748 return Qnil; |
729 } | 749 } |
730 } | 750 } |
745 Emchar c; | 765 Emchar c; |
746 int quoted; | 766 int quoted; |
747 int mathexit = 0; | 767 int mathexit = 0; |
748 enum syntaxcode code; | 768 enum syntaxcode code; |
749 int min_depth = depth; /* Err out if depth gets less than this. */ | 769 int min_depth = depth; /* Err out if depth gets less than this. */ |
750 Lisp_Object table = buf->syntax_table; | 770 Lisp_Object syntaxtab = buf->syntax_table; |
771 struct Lisp_Char_Table *mirrortab = XCHAR_TABLE (buf->mirror_syntax_table); | |
751 | 772 |
752 if (depth > 0) min_depth = 0; | 773 if (depth > 0) min_depth = 0; |
753 | 774 |
754 while (count > 0) | 775 while (count > 0) |
755 { | 776 { |
759 while (from < stop) | 780 while (from < stop) |
760 { | 781 { |
761 int mask = 0; /* mask for finding matching comment style */ | 782 int mask = 0; /* mask for finding matching comment style */ |
762 | 783 |
763 c = BUF_FETCH_CHAR (buf, from); | 784 c = BUF_FETCH_CHAR (buf, from); |
764 code = SYNTAX_UNSAFE (table, c); | 785 code = SYNTAX_UNSAFE (mirrortab, c); |
765 from++; | 786 from++; |
766 | 787 |
767 /* a 1-char comment start sequence */ | 788 /* a 1-char comment start sequence */ |
768 if (code == Scomment && parse_sexp_ignore_comments) | 789 if (code == Scomment && parse_sexp_ignore_comments) |
769 { | 790 { |
770 mask = SYNTAX_COMMENT_1CHAR_MASK (table, c); | 791 mask = SYNTAX_COMMENT_1CHAR_MASK (mirrortab, c); |
771 } | 792 } |
772 | 793 |
773 /* else, a 2-char comment start sequence? */ | 794 /* else, a 2-char comment start sequence? */ |
774 else if (from < stop | 795 else if (from < stop |
775 && SYNTAX_START_P (table, c, BUF_FETCH_CHAR (buf, from)) | 796 && SYNTAX_START_P (mirrortab, c, BUF_FETCH_CHAR (buf, from)) |
776 && parse_sexp_ignore_comments) | 797 && parse_sexp_ignore_comments) |
777 { | 798 { |
778 /* we have encountered a comment start sequence and we | 799 /* we have encountered a comment start sequence and we |
779 are ignoring all text inside comments. we must record | 800 are ignoring all text inside comments. we must record |
780 the comment style this sequence begins so that later, | 801 the comment style this sequence begins so that later, |
781 only a comment end of the same style actually ends | 802 only a comment end of the same style actually ends |
782 the comment section */ | 803 the comment section */ |
783 code = Scomment; | 804 code = Scomment; |
784 mask = SYNTAX_COMMENT_MASK_START (table, c, | 805 mask = SYNTAX_COMMENT_MASK_START (mirrortab, c, |
785 BUF_FETCH_CHAR (buf, from)); | 806 BUF_FETCH_CHAR (buf, from)); |
786 from++; | 807 from++; |
787 } | 808 } |
788 | 809 |
789 if (SYNTAX_PREFIX_UNSAFE (table, c)) | 810 if (SYNTAX_PREFIX_UNSAFE (mirrortab, c)) |
790 continue; | 811 continue; |
791 | 812 |
792 switch (code) | 813 switch (code) |
793 { | 814 { |
794 case Sescape: | 815 case Sescape: |
795 case Scharquote: | 816 case Scharquote: |
796 if (from == stop) goto lose; | 817 if (from == stop) goto lose; |
797 from++; | 818 from++; |
798 /* treat following character as a word constituent */ | 819 /* treat following character as a word constituent */ |
799 case Sword: | 820 case Sword: |
800 case Sextword: | |
801 case Ssymbol: | 821 case Ssymbol: |
802 if (depth || !sexpflag) break; | 822 if (depth || !sexpflag) break; |
803 /* This word counts as a sexp; return at end of it. */ | 823 /* This word counts as a sexp; return at end of it. */ |
804 while (from < stop) | 824 while (from < stop) |
805 { | 825 { |
806 switch (SYNTAX (table, BUF_FETCH_CHAR (buf, from))) | 826 switch (SYNTAX (mirrortab, BUF_FETCH_CHAR (buf, from))) |
807 { | 827 { |
808 case Scharquote: | 828 case Scharquote: |
809 case Sescape: | 829 case Sescape: |
810 from++; | 830 from++; |
811 if (from == stop) goto lose; | 831 if (from == stop) goto lose; |
812 break; | 832 break; |
813 case Sword: | 833 case Sword: |
814 case Sextword: | |
815 case Ssymbol: | 834 case Ssymbol: |
816 case Squote: | 835 case Squote: |
817 break; | 836 break; |
818 default: | 837 default: |
819 goto done; | 838 goto done; |
868 | 887 |
869 case Sstring: | 888 case Sstring: |
870 { | 889 { |
871 /* XEmacs change: call syntax_match on character */ | 890 /* XEmacs change: call syntax_match on character */ |
872 Emchar ch = BUF_FETCH_CHAR (buf, from - 1); | 891 Emchar ch = BUF_FETCH_CHAR (buf, from - 1); |
873 Lisp_Object stermobj = syntax_match (table, ch); | 892 Lisp_Object stermobj = syntax_match (syntaxtab, ch); |
874 Emchar stringterm; | 893 Emchar stringterm; |
875 | 894 |
876 if (CHARP (stermobj)) | 895 if (CHARP (stermobj)) |
877 stringterm = XCHAR (stermobj); | 896 stringterm = XCHAR (stermobj); |
878 else | 897 else |
882 { | 901 { |
883 if (from >= stop) | 902 if (from >= stop) |
884 goto lose; | 903 goto lose; |
885 if (BUF_FETCH_CHAR (buf, from) == stringterm) | 904 if (BUF_FETCH_CHAR (buf, from) == stringterm) |
886 break; | 905 break; |
887 switch (SYNTAX (table, BUF_FETCH_CHAR (buf, from))) | 906 switch (SYNTAX (mirrortab, BUF_FETCH_CHAR (buf, from))) |
888 { | 907 { |
889 case Scharquote: | 908 case Scharquote: |
890 case Sescape: | 909 case Sescape: |
891 from++; | 910 from++; |
892 break; | 911 break; |
929 quoted = char_quoted (buf, from); | 948 quoted = char_quoted (buf, from); |
930 if (quoted) | 949 if (quoted) |
931 from--; | 950 from--; |
932 | 951 |
933 c = BUF_FETCH_CHAR (buf, from); | 952 c = BUF_FETCH_CHAR (buf, from); |
934 code = SYNTAX_UNSAFE (table, c); | 953 code = SYNTAX_UNSAFE (mirrortab, c); |
935 | 954 |
936 if (code == Sendcomment && parse_sexp_ignore_comments) | 955 if (code == Sendcomment && parse_sexp_ignore_comments) |
937 { | 956 { |
938 /* we have found a single char end comment. we must record | 957 /* we have found a single char end comment. we must record |
939 the comment style encountered so that later, we can match | 958 the comment style encountered so that later, we can match |
940 only the proper comment begin sequence of the same style */ | 959 only the proper comment begin sequence of the same style */ |
941 mask = SYNTAX_COMMENT_1CHAR_MASK (table, c); | 960 mask = SYNTAX_COMMENT_1CHAR_MASK (mirrortab, c); |
942 } | 961 } |
943 | 962 |
944 else if (from > stop | 963 else if (from > stop |
945 && SYNTAX_END_P (table, BUF_FETCH_CHAR (buf, from-1), c) | 964 && SYNTAX_END_P (mirrortab, BUF_FETCH_CHAR (buf, from-1), c) |
946 && !char_quoted (buf, from - 1) | 965 && !char_quoted (buf, from - 1) |
947 && parse_sexp_ignore_comments) | 966 && parse_sexp_ignore_comments) |
948 { | 967 { |
949 /* we must record the comment style encountered so that | 968 /* we must record the comment style encountered so that |
950 later, we can match only the proper comment begin | 969 later, we can match only the proper comment begin |
951 sequence of the same style */ | 970 sequence of the same style */ |
952 code = Sendcomment; | 971 code = Sendcomment; |
953 mask = SYNTAX_COMMENT_MASK_END (table, | 972 mask = SYNTAX_COMMENT_MASK_END (mirrortab, |
954 BUF_FETCH_CHAR (buf, from - 1), | 973 BUF_FETCH_CHAR (buf, from - 1), |
955 c); | 974 c); |
956 from--; | 975 from--; |
957 } | 976 } |
958 | 977 |
959 if (SYNTAX_PREFIX_UNSAFE (table, c)) | 978 if (SYNTAX_PREFIX_UNSAFE (mirrortab, c)) |
960 continue; | 979 continue; |
961 | 980 |
962 switch (((quoted) ? Sword : code)) | 981 switch (((quoted) ? Sword : code)) |
963 { | 982 { |
964 case Sword: | 983 case Sword: |
965 case Sextword: | |
966 case Ssymbol: | 984 case Ssymbol: |
967 if (depth || !sexpflag) break; | 985 if (depth || !sexpflag) break; |
968 /* This word counts as a sexp; count object finished after | 986 /* This word counts as a sexp; count object finished after |
969 passing it. */ | 987 passing it. */ |
970 while (from > stop) | 988 while (from > stop) |
974 | 992 |
975 if (quoted) | 993 if (quoted) |
976 from--; | 994 from--; |
977 if (! (quoted | 995 if (! (quoted |
978 || (syncode = | 996 || (syncode = |
979 SYNTAX (table, BUF_FETCH_CHAR (buf, from - 1))) | 997 SYNTAX (mirrortab, BUF_FETCH_CHAR (buf, from - 1))) |
980 == Sword | 998 == Sword |
981 || syncode == Sextword | |
982 || syncode == Ssymbol | 999 || syncode == Ssymbol |
983 || syncode == Squote)) | 1000 || syncode == Squote)) |
984 goto done2; | 1001 goto done2; |
985 from--; | 1002 from--; |
986 } | 1003 } |
1020 | 1037 |
1021 case Sstring: | 1038 case Sstring: |
1022 { | 1039 { |
1023 /* XEmacs change: call syntax_match() on character */ | 1040 /* XEmacs change: call syntax_match() on character */ |
1024 Emchar ch = BUF_FETCH_CHAR (buf, from); | 1041 Emchar ch = BUF_FETCH_CHAR (buf, from); |
1025 Lisp_Object stermobj = syntax_match (table, ch); | 1042 Lisp_Object stermobj = syntax_match (syntaxtab, ch); |
1026 Emchar stringterm; | 1043 Emchar stringterm; |
1027 | 1044 |
1028 if (CHARP (stermobj)) | 1045 if (CHARP (stermobj)) |
1029 stringterm = XCHAR (stermobj); | 1046 stringterm = XCHAR (stermobj); |
1030 else | 1047 else |
1068 char_quoted (struct buffer *buf, Bufpos pos) | 1085 char_quoted (struct buffer *buf, Bufpos pos) |
1069 { | 1086 { |
1070 enum syntaxcode code; | 1087 enum syntaxcode code; |
1071 Bufpos beg = BUF_BEGV (buf); | 1088 Bufpos beg = BUF_BEGV (buf); |
1072 int quoted = 0; | 1089 int quoted = 0; |
1073 Lisp_Object table = buf->syntax_table; | 1090 struct Lisp_Char_Table *mirrortab = XCHAR_TABLE (buf->mirror_syntax_table); |
1074 | 1091 |
1075 while (pos > beg | 1092 while (pos > beg |
1076 && ((code = SYNTAX (table, BUF_FETCH_CHAR (buf, pos - 1))) | 1093 && ((code = SYNTAX (mirrortab, BUF_FETCH_CHAR (buf, pos - 1))) |
1077 == Scharquote | 1094 == Scharquote |
1078 || code == Sescape)) | 1095 || code == Sescape)) |
1079 pos--, quoted = !quoted; | 1096 pos--, quoted = !quoted; |
1080 return quoted; | 1097 return quoted; |
1081 } | 1098 } |
1150 (buffer)) | 1167 (buffer)) |
1151 { | 1168 { |
1152 struct buffer *buf = decode_buffer (buffer, 0); | 1169 struct buffer *buf = decode_buffer (buffer, 0); |
1153 Bufpos beg = BUF_BEGV (buf); | 1170 Bufpos beg = BUF_BEGV (buf); |
1154 Bufpos pos = BUF_PT (buf); | 1171 Bufpos pos = BUF_PT (buf); |
1155 Lisp_Object table = buf->syntax_table; | 1172 struct Lisp_Char_Table *mirrortab = XCHAR_TABLE (buf->mirror_syntax_table); |
1156 | 1173 |
1157 while (pos > beg && !char_quoted (buf, pos - 1) | 1174 while (pos > beg && !char_quoted (buf, pos - 1) |
1158 && (SYNTAX (table, BUF_FETCH_CHAR (buf, pos - 1)) == Squote | 1175 && (SYNTAX (mirrortab, BUF_FETCH_CHAR (buf, pos - 1)) == Squote |
1159 || SYNTAX_PREFIX (table, BUF_FETCH_CHAR (buf, pos - 1)))) | 1176 || SYNTAX_PREFIX (mirrortab, BUF_FETCH_CHAR (buf, pos - 1)))) |
1160 pos--; | 1177 pos--; |
1161 | 1178 |
1162 BUF_SET_PT (buf, pos); | 1179 BUF_SET_PT (buf, pos); |
1163 | 1180 |
1164 return Qnil; | 1181 return Qnil; |
1187 int depth; /* Paren depth of current scanning location. | 1204 int depth; /* Paren depth of current scanning location. |
1188 level - levelstart equals this except | 1205 level - levelstart equals this except |
1189 when the depth becomes negative. */ | 1206 when the depth becomes negative. */ |
1190 int mindepth; /* Lowest DEPTH value seen. */ | 1207 int mindepth; /* Lowest DEPTH value seen. */ |
1191 int start_quoted = 0; /* Nonzero means starting after a char quote */ | 1208 int start_quoted = 0; /* Nonzero means starting after a char quote */ |
1192 Lisp_Object table = buf->syntax_table; | |
1193 Lisp_Object tem; | 1209 Lisp_Object tem; |
1194 int mask; /* comment mask */ | 1210 int mask; /* comment mask */ |
1211 Lisp_Object syntaxtab = buf->syntax_table; | |
1212 struct Lisp_Char_Table *mirrortab = XCHAR_TABLE (buf->mirror_syntax_table); | |
1195 | 1213 |
1196 if (NILP (oldstate)) | 1214 if (NILP (oldstate)) |
1197 { | 1215 { |
1198 depth = 0; | 1216 depth = 0; |
1199 state.instring = -1; | 1217 state.instring = -1; |
1250 | 1268 |
1251 while (from < end) | 1269 while (from < end) |
1252 { | 1270 { |
1253 QUIT; | 1271 QUIT; |
1254 | 1272 |
1255 code = SYNTAX (table, BUF_FETCH_CHAR (buf, from)); | 1273 code = SYNTAX (mirrortab, BUF_FETCH_CHAR (buf, from)); |
1256 from++; | 1274 from++; |
1257 | 1275 |
1258 if (code == Scomment) | 1276 if (code == Scomment) |
1259 { | 1277 { |
1260 /* record the comment style we have entered so that only the | 1278 /* record the comment style we have entered so that only the |
1261 comment-ender sequence (or single char) of the same style | 1279 comment-ender sequence (or single char) of the same style |
1262 actually terminates the comment section. */ | 1280 actually terminates the comment section. */ |
1263 mask = SYNTAX_COMMENT_1CHAR_MASK (table, | 1281 mask = SYNTAX_COMMENT_1CHAR_MASK (mirrortab, |
1264 BUF_FETCH_CHAR (buf, from-1)); | 1282 BUF_FETCH_CHAR (buf, from-1)); |
1265 state.comstyle = (mask == SYNTAX_COMMENT_STYLE_B); | 1283 state.comstyle = (mask == SYNTAX_COMMENT_STYLE_B); |
1266 state.comstart = from - 1; | 1284 state.comstart = from - 1; |
1267 } | 1285 } |
1268 | 1286 |
1269 else if (from < end && | 1287 else if (from < end && |
1270 SYNTAX_START_P (table, BUF_FETCH_CHAR (buf, from-1), | 1288 SYNTAX_START_P (mirrortab, BUF_FETCH_CHAR (buf, from-1), |
1271 BUF_FETCH_CHAR (buf, from))) | 1289 BUF_FETCH_CHAR (buf, from))) |
1272 { | 1290 { |
1273 /* Record the comment style we have entered so that only | 1291 /* Record the comment style we have entered so that only |
1274 the comment-end sequence of the same style actually | 1292 the comment-end sequence of the same style actually |
1275 terminates the comment section. */ | 1293 terminates the comment section. */ |
1276 code = Scomment; | 1294 code = Scomment; |
1277 mask = SYNTAX_COMMENT_MASK_START (table, | 1295 mask = SYNTAX_COMMENT_MASK_START (mirrortab, |
1278 BUF_FETCH_CHAR (buf, from-1), | 1296 BUF_FETCH_CHAR (buf, from-1), |
1279 BUF_FETCH_CHAR (buf, from)); | 1297 BUF_FETCH_CHAR (buf, from)); |
1280 state.comstyle = (mask == SYNTAX_COMMENT_STYLE_B); | 1298 state.comstyle = (mask == SYNTAX_COMMENT_STYLE_B); |
1281 state.comstart = from-1; | 1299 state.comstart = from-1; |
1282 from++; | 1300 from++; |
1283 } | 1301 } |
1284 | 1302 |
1285 if (SYNTAX_PREFIX (table, BUF_FETCH_CHAR (buf, from - 1))) | 1303 if (SYNTAX_PREFIX (mirrortab, BUF_FETCH_CHAR (buf, from - 1))) |
1286 continue; | 1304 continue; |
1287 switch (code) | 1305 switch (code) |
1288 { | 1306 { |
1289 case Sescape: | 1307 case Sescape: |
1290 case Scharquote: | 1308 case Scharquote: |
1294 if (from == end) goto endquoted; | 1312 if (from == end) goto endquoted; |
1295 from++; | 1313 from++; |
1296 goto symstarted; | 1314 goto symstarted; |
1297 /* treat following character as a word constituent */ | 1315 /* treat following character as a word constituent */ |
1298 case Sword: | 1316 case Sword: |
1299 case Sextword: | |
1300 case Ssymbol: | 1317 case Ssymbol: |
1301 if (stopbefore) goto stop; /* this arg means stop at sexp start */ | 1318 if (stopbefore) goto stop; /* this arg means stop at sexp start */ |
1302 curlevel->last = from - 1; | 1319 curlevel->last = from - 1; |
1303 symstarted: | 1320 symstarted: |
1304 while (from < end) | 1321 while (from < end) |
1305 { | 1322 { |
1306 switch (SYNTAX (table, BUF_FETCH_CHAR (buf, from))) | 1323 switch (SYNTAX (mirrortab, BUF_FETCH_CHAR (buf, from))) |
1307 { | 1324 { |
1308 case Scharquote: | 1325 case Scharquote: |
1309 case Sescape: | 1326 case Sescape: |
1310 from++; | 1327 from++; |
1311 if (from == end) goto endquoted; | 1328 if (from == end) goto endquoted; |
1312 break; | 1329 break; |
1313 case Sword: | 1330 case Sword: |
1314 case Sextword: | |
1315 case Ssymbol: | 1331 case Ssymbol: |
1316 case Squote: | 1332 case Squote: |
1317 break; | 1333 break; |
1318 default: | 1334 default: |
1319 goto symdone; | 1335 goto symdone; |
1351 curlevel->last = from - 1; | 1367 curlevel->last = from - 1; |
1352 if (++curlevel == endlevel) | 1368 if (++curlevel == endlevel) |
1353 error ("Nesting too deep for parser"); | 1369 error ("Nesting too deep for parser"); |
1354 curlevel->prev = -1; | 1370 curlevel->prev = -1; |
1355 curlevel->last = -1; | 1371 curlevel->last = -1; |
1356 if (targetdepth == depth) goto done; | 1372 if (!--targetdepth) goto done; |
1357 break; | 1373 break; |
1358 | 1374 |
1359 case Sclose: | 1375 case Sclose: |
1360 depth--; | 1376 depth--; |
1361 if (depth < mindepth) | 1377 if (depth < mindepth) |
1362 mindepth = depth; | 1378 mindepth = depth; |
1363 if (curlevel != levelstart) | 1379 if (curlevel != levelstart) |
1364 curlevel--; | 1380 curlevel--; |
1365 curlevel->prev = curlevel->last; | 1381 curlevel->prev = curlevel->last; |
1366 if (targetdepth == depth) goto done; | 1382 if (!++targetdepth) goto done; |
1367 break; | 1383 break; |
1368 | 1384 |
1369 case Sstring: | 1385 case Sstring: |
1370 { | 1386 { |
1371 Emchar ch; | 1387 Emchar ch; |
1372 if (stopbefore) goto stop; /* this arg means stop at sexp start */ | 1388 if (stopbefore) goto stop; /* this arg means stop at sexp start */ |
1373 curlevel->last = from - 1; | 1389 curlevel->last = from - 1; |
1374 /* XEmacs change: call syntax_match() on character */ | 1390 /* XEmacs change: call syntax_match() on character */ |
1375 ch = BUF_FETCH_CHAR (buf, from - 1); | 1391 ch = BUF_FETCH_CHAR (buf, from - 1); |
1376 { | 1392 { |
1377 Lisp_Object stermobj = syntax_match (table, ch); | 1393 Lisp_Object stermobj = syntax_match (syntaxtab, ch); |
1378 | 1394 |
1379 if (CHARP (stermobj)) | 1395 if (CHARP (stermobj)) |
1380 state.instring = XCHAR (stermobj); | 1396 state.instring = XCHAR (stermobj); |
1381 else | 1397 else |
1382 state.instring = ch; | 1398 state.instring = ch; |
1385 startinstring: | 1401 startinstring: |
1386 while (1) | 1402 while (1) |
1387 { | 1403 { |
1388 if (from >= end) goto done; | 1404 if (from >= end) goto done; |
1389 if (BUF_FETCH_CHAR (buf, from) == state.instring) break; | 1405 if (BUF_FETCH_CHAR (buf, from) == state.instring) break; |
1390 switch (SYNTAX (table, BUF_FETCH_CHAR (buf, from))) | 1406 switch (SYNTAX (mirrortab, BUF_FETCH_CHAR (buf, from))) |
1391 { | 1407 { |
1392 case Scharquote: | 1408 case Scharquote: |
1393 case Sescape: | 1409 case Sescape: |
1394 { | 1410 { |
1395 from++; | 1411 from++; |
1505 | 1521 |
1506 return (Flist (8, retval)); | 1522 return (Flist (8, retval)); |
1507 } | 1523 } |
1508 } | 1524 } |
1509 | 1525 |
1526 | |
1527 /* Updating of the mirror syntax table. | |
1528 | |
1529 Each syntax table has a corresponding mirror table in it. | |
1530 Whenever we make a change to a syntax table, we call | |
1531 update_syntax_table() on it. | |
1532 | |
1533 #### We really only need to map over the changed range. | |
1534 | |
1535 If we change the standard syntax table, we need to map over | |
1536 all tables because any of them could be inheriting from the | |
1537 standard syntax table. | |
1538 | |
1539 When `set-syntax-table' is called, we set the buffer's mirror | |
1540 syntax table as well. | |
1541 */ | |
1542 | |
1543 struct cmst_arg | |
1544 { | |
1545 Lisp_Object mirrortab; | |
1546 int check_inherit; | |
1547 }; | |
1548 | |
1549 static int | |
1550 cmst_mapfun (struct chartab_range *range, Lisp_Object val, void *arg) | |
1551 { | |
1552 struct cmst_arg *closure = (struct cmst_arg *) arg; | |
1553 | |
1554 if (CONSP (val)) | |
1555 val = XCAR (val); | |
1556 if (SYNTAX_FROM_CODE (XINT (val)) == Sinherit | |
1557 && closure->check_inherit) | |
1558 { | |
1559 struct cmst_arg recursive; | |
1560 | |
1561 recursive.mirrortab = closure->mirrortab; | |
1562 recursive.check_inherit = 0; | |
1563 map_char_table (XCHAR_TABLE (Vstandard_syntax_table), range, | |
1564 cmst_mapfun, &recursive); | |
1565 } | |
1566 else | |
1567 put_char_table (XCHAR_TABLE (closure->mirrortab), range, val); | |
1568 return 0; | |
1569 } | |
1570 | |
1571 static void | |
1572 update_just_this_syntax_table (struct Lisp_Char_Table *ct) | |
1573 { | |
1574 struct chartab_range range; | |
1575 struct cmst_arg arg; | |
1576 | |
1577 arg.mirrortab = ct->mirror_table; | |
1578 arg.check_inherit = (CHAR_TABLEP (Vstandard_syntax_table) | |
1579 && ct != XCHAR_TABLE (Vstandard_syntax_table)); | |
1580 range.type = CHARTAB_RANGE_ALL; | |
1581 map_char_table (ct, &range, cmst_mapfun, &arg); | |
1582 } | |
1583 | |
1584 /* Called from chartab.c when a change is made to a syntax table. | |
1585 If this is the standard syntax table, we need to recompute | |
1586 *all* syntax tables (yuck). Otherwise we just recompute this | |
1587 one. */ | |
1588 | |
1589 void | |
1590 update_syntax_table (struct Lisp_Char_Table *ct) | |
1591 { | |
1592 /* Don't be stymied at startup. */ | |
1593 if (CHAR_TABLEP (Vstandard_syntax_table) | |
1594 && ct == XCHAR_TABLE (Vstandard_syntax_table)) | |
1595 { | |
1596 Lisp_Object syntab; | |
1597 | |
1598 for (syntab = Vall_syntax_tables; !NILP (syntab); | |
1599 syntab = XCHAR_TABLE (syntab)->next_table) | |
1600 update_just_this_syntax_table (XCHAR_TABLE (syntab)); | |
1601 } | |
1602 else | |
1603 update_just_this_syntax_table (ct); | |
1604 } | |
1605 | |
1510 | 1606 |
1511 /************************************************************************/ | 1607 /************************************************************************/ |
1512 /* initialization */ | 1608 /* initialization */ |
1513 /************************************************************************/ | 1609 /************************************************************************/ |
1514 | 1610 |
1553 } | 1649 } |
1554 | 1650 |
1555 void | 1651 void |
1556 complex_vars_of_syntax (void) | 1652 complex_vars_of_syntax (void) |
1557 { | 1653 { |
1558 struct Lisp_Vector *v; | |
1559 int i; | |
1560 | |
1561 /* Set this now, so first buffer creation can refer to it. */ | 1654 /* Set this now, so first buffer creation can refer to it. */ |
1562 /* Make it nil before calling copy-syntax-table | 1655 /* Make it nil before calling copy-syntax-table |
1563 so that copy-syntax-table will know not to try to copy from garbage */ | 1656 so that copy-syntax-table will know not to try to copy from garbage */ |
1564 Vstandard_syntax_table = Qnil; | 1657 Vstandard_syntax_table = Qnil; |
1565 Vstandard_syntax_table = Fcopy_syntax_table (Qnil); | 1658 Vstandard_syntax_table = Fcopy_syntax_table (Qnil); |
1567 | 1660 |
1568 Vsyntax_designator_chars_string = make_pure_string (syntax_code_spec, | 1661 Vsyntax_designator_chars_string = make_pure_string (syntax_code_spec, |
1569 Smax, Qnil, 1); | 1662 Smax, Qnil, 1); |
1570 staticpro (&Vsyntax_designator_chars_string); | 1663 staticpro (&Vsyntax_designator_chars_string); |
1571 | 1664 |
1572 v = XVECTOR (Vstandard_syntax_table); | 1665 fill_char_table (XCHAR_TABLE (Vstandard_syntax_table), |
1573 | 1666 make_int (Spunct)); |
1574 for (i = 'a'; i <= 'z'; i++) | 1667 |
1575 v->contents[i] = make_int ((int) Sword); | |
1576 for (i = 'A'; i <= 'Z'; i++) | |
1577 v->contents[i] = make_int ((int) Sword); | |
1578 for (i = '0'; i <= '9'; i++) | |
1579 v->contents[i] = make_int ((int) Sword); | |
1580 v->contents['$'] = make_int ((int) Sword); | |
1581 v->contents['%'] = make_int ((int) Sword); | |
1582 | |
1583 v->contents['('] = make_int ((int) Sopen + (')' << 8)); | |
1584 v->contents[')'] = make_int ((int) Sclose + ('(' << 8)); | |
1585 v->contents['['] = make_int ((int) Sopen + (']' << 8)); | |
1586 v->contents[']'] = make_int ((int) Sclose + ('[' << 8)); | |
1587 v->contents['{'] = make_int ((int) Sopen + ('}' << 8)); | |
1588 v->contents['}'] = make_int ((int) Sclose + ('{' << 8)); | |
1589 v->contents['"'] = make_int ((int) Sstring); | |
1590 v->contents['\\'] = make_int ((int) Sescape); | |
1591 | |
1592 { | 1668 { |
1593 CONST char *p; | 1669 Emchar i; |
1594 | 1670 |
1595 for (p = "_-+*/&|<>="; *p; p++) | 1671 for (i = 0; i <= 32; i++) |
1596 v->contents[(int) *p] = make_int ((int) Ssymbol); | 1672 Fput_char_table (make_char (i), make_int ((int) Swhitespace), |
1673 Vstandard_syntax_table); | |
1674 for (i = 127; i <= 159; i++) | |
1675 Fput_char_table (make_char (i), make_int ((int) Swhitespace), | |
1676 Vstandard_syntax_table); | |
1677 | |
1678 for (i = 'a'; i <= 'z'; i++) | |
1679 Fput_char_table (make_char (i), make_int ((int) Sword), | |
1680 Vstandard_syntax_table); | |
1681 for (i = 'A'; i <= 'Z'; i++) | |
1682 Fput_char_table (make_char (i), make_int ((int) Sword), | |
1683 Vstandard_syntax_table); | |
1684 for (i = '0'; i <= '9'; i++) | |
1685 Fput_char_table (make_char (i), make_int ((int) Sword), | |
1686 Vstandard_syntax_table); | |
1687 Fput_char_table (make_char ('$'), make_int ((int) Sword), | |
1688 Vstandard_syntax_table); | |
1689 Fput_char_table (make_char ('%'), make_int ((int) Sword), | |
1690 Vstandard_syntax_table); | |
1691 | |
1692 { | |
1693 Fput_char_table (make_char ('('), Fcons (make_int ((int) Sopen), | |
1694 make_char (')')), | |
1695 Vstandard_syntax_table); | |
1696 Fput_char_table (make_char (')'), Fcons (make_int ((int) Sclose), | |
1697 make_char ('(')), | |
1698 Vstandard_syntax_table); | |
1699 Fput_char_table (make_char ('['), Fcons (make_int ((int) Sopen), | |
1700 make_char (']')), | |
1701 Vstandard_syntax_table); | |
1702 Fput_char_table (make_char (']'), Fcons (make_int ((int) Sclose), | |
1703 make_char ('[')), | |
1704 Vstandard_syntax_table); | |
1705 Fput_char_table (make_char ('{'), Fcons (make_int ((int) Sopen), | |
1706 make_char ('}')), | |
1707 Vstandard_syntax_table); | |
1708 Fput_char_table (make_char ('}'), Fcons (make_int ((int) Sclose), | |
1709 make_char ('{')), | |
1710 Vstandard_syntax_table); | |
1711 } | |
1712 | |
1713 Fput_char_table (make_char ('"'), make_int ((int) Sstring), | |
1714 Vstandard_syntax_table); | |
1715 Fput_char_table (make_char ('\\'), make_int ((int) Sescape), | |
1716 Vstandard_syntax_table); | |
1597 | 1717 |
1598 for (p = ".,;:?!#@~^'`"; *p; p++) | 1718 { |
1599 v->contents[(int) *p] = make_int ((int) Spunct); | 1719 CONST char *p; |
1720 for (p = "_-+*/&|<>="; *p; p++) | |
1721 Fput_char_table (make_char (*p), make_int ((int) Ssymbol), | |
1722 Vstandard_syntax_table); | |
1723 | |
1724 for (p = ".,;:?!#@~^'`"; *p; p++) | |
1725 Fput_char_table (make_char (*p), make_int ((int) Spunct), | |
1726 Vstandard_syntax_table); | |
1727 } | |
1600 } | 1728 } |
1601 } | 1729 } |