Mercurial > hg > xemacs-beta
comparison src/syntax.c @ 3252:a66d0a29e183
[xemacs-hg @ 2006-02-22 03:30:06 by stephent]
Fix out-of-order definition. <87fymcnkdu.fsf@tleepslib.sk.tsukuba.ac.jp>
author | stephent |
---|---|
date | Wed, 22 Feb 2006 03:30:08 +0000 |
parents | 2b8bb4938bb4 |
children | efa52de8c279 |
comparison
equal
deleted
inserted
replaced
3251:4ae19a15d5b0 | 3252:a66d0a29e183 |
---|---|
236 syntax_cache_table_was_changed (buf); | 236 syntax_cache_table_was_changed (buf); |
237 /* Indicate that this buffer now has a specified syntax table. */ | 237 /* Indicate that this buffer now has a specified syntax table. */ |
238 buf->local_var_flags |= XINT (buffer_local_flags.syntax_table); | 238 buf->local_var_flags |= XINT (buffer_local_flags.syntax_table); |
239 return syntax_table; | 239 return syntax_table; |
240 } | 240 } |
241 | |
242 | |
241 | 243 |
244 /* | |
245 * Syntax caching | |
246 */ | |
247 | |
248 /* syntax_cache object implementation */ | |
249 | |
250 static const struct memory_description syntax_cache_description_1 [] = { | |
251 { XD_LISP_OBJECT, offsetof (struct syntax_cache, object) }, | |
252 { XD_LISP_OBJECT, offsetof (struct syntax_cache, buffer) }, | |
253 { XD_LISP_OBJECT, offsetof (struct syntax_cache, syntax_table) }, | |
254 { XD_LISP_OBJECT, offsetof (struct syntax_cache, mirror_table) }, | |
255 { XD_LISP_OBJECT, offsetof (struct syntax_cache, start) }, | |
256 { XD_LISP_OBJECT, offsetof (struct syntax_cache, end) }, | |
257 { XD_END } | |
258 }; | |
259 | |
260 #ifdef NEW_GC | |
261 DEFINE_LRECORD_IMPLEMENTATION ("syntax-cache", syntax_cache, | |
262 1, /*dumpable-flag*/ | |
263 0, 0, 0, 0, 0, | |
264 syntax_cache_description_1, | |
265 Lisp_Syntax_Cache); | |
266 #else /* not NEW_GC */ | |
267 | |
268 const struct sized_memory_description syntax_cache_description = { | |
269 sizeof (struct syntax_cache), | |
270 syntax_cache_description_1 | |
271 }; | |
272 #endif /* not NEW_GC */ | |
273 | |
274 /* static syntax cache utilities */ | |
275 | |
276 static void | |
277 syntax_cache_table_was_changed (struct buffer *buf) | |
278 { | |
279 struct syntax_cache *cache = buf->syntax_cache; | |
280 if (cache->no_syntax_table_prop) | |
281 { | |
282 cache->syntax_table = | |
283 BUFFER_SYNTAX_TABLE (buf); | |
284 cache->mirror_table = | |
285 BUFFER_MIRROR_SYNTAX_TABLE (buf); | |
286 } | |
287 } | |
288 | |
289 static void | |
290 reset_buffer_syntax_cache_range (struct syntax_cache *cache, | |
291 Lisp_Object buffer, int infinite) | |
292 { | |
293 Fset_marker (cache->start, make_int (1), buffer); | |
294 Fset_marker (cache->end, make_int (1), buffer); | |
295 Fset_marker_insertion_type (cache->start, Qt); | |
296 Fset_marker_insertion_type (cache->end, Qnil); | |
297 /* #### Should we "cache->no_syntax_table_prop = 1;" here? */ | |
298 /* #### Cf comment on INFINITE in init_syntax_cache. -- sjt */ | |
299 if (infinite) | |
300 { | |
301 cache->prev_change = EMACS_INT_MIN; | |
302 cache->next_change = EMACS_INT_MAX; | |
303 } | |
304 else | |
305 { | |
306 cache->prev_change = -1; | |
307 cache->next_change = -1; | |
308 } | |
309 } | |
242 | 310 |
243 static void | 311 static void |
244 init_syntax_cache (struct syntax_cache *cache, Lisp_Object object, | 312 init_syntax_cache (struct syntax_cache *cache, Lisp_Object object, |
245 struct buffer *buffer, int infinite) | 313 struct buffer *buffer, int infinite) |
246 { | 314 { |
269 cache->prev_change = -1; | 337 cache->prev_change = -1; |
270 cache->next_change = -1; | 338 cache->next_change = -1; |
271 } | 339 } |
272 } | 340 } |
273 | 341 |
342 /* external syntax cache API */ | |
343 | |
274 /* #### This function and associated logic still needs work, and especially | 344 /* #### This function and associated logic still needs work, and especially |
275 documentation. */ | 345 documentation. */ |
276 struct syntax_cache * /* return CACHE or the cache of OBJECT */ | 346 struct syntax_cache * /* return CACHE or the cache of OBJECT */ |
277 setup_syntax_cache (struct syntax_cache *cache, /* syntax cache, may be NULL | 347 setup_syntax_cache (struct syntax_cache *cache, /* syntax cache, may be NULL |
278 if OBJECT is a buffer */ | 348 if OBJECT is a buffer */ |
314 | 384 |
315 struct syntax_cache * | 385 struct syntax_cache * |
316 setup_buffer_syntax_cache (struct buffer *buffer, Charxpos from, int count) | 386 setup_buffer_syntax_cache (struct buffer *buffer, Charxpos from, int count) |
317 { | 387 { |
318 return setup_syntax_cache (NULL, wrap_buffer (buffer), buffer, from, count); | 388 return setup_syntax_cache (NULL, wrap_buffer (buffer), buffer, from, count); |
319 } | |
320 | |
321 static const struct memory_description syntax_cache_description_1 [] = { | |
322 { XD_LISP_OBJECT, offsetof (struct syntax_cache, object) }, | |
323 { XD_LISP_OBJECT, offsetof (struct syntax_cache, buffer) }, | |
324 { XD_LISP_OBJECT, offsetof (struct syntax_cache, syntax_table) }, | |
325 { XD_LISP_OBJECT, offsetof (struct syntax_cache, mirror_table) }, | |
326 { XD_LISP_OBJECT, offsetof (struct syntax_cache, start) }, | |
327 { XD_LISP_OBJECT, offsetof (struct syntax_cache, end) }, | |
328 { XD_END } | |
329 }; | |
330 | |
331 #ifdef NEW_GC | |
332 DEFINE_LRECORD_IMPLEMENTATION ("syntax-cache", syntax_cache, | |
333 1, /*dumpable-flag*/ | |
334 0, 0, 0, 0, 0, | |
335 syntax_cache_description_1, | |
336 Lisp_Syntax_Cache); | |
337 #else /* not NEW_GC */ | |
338 | |
339 const struct sized_memory_description syntax_cache_description = { | |
340 sizeof (struct syntax_cache), | |
341 syntax_cache_description_1 | |
342 }; | |
343 #endif /* not NEW_GC */ | |
344 | |
345 void | |
346 mark_buffer_syntax_cache (struct buffer *buf) | |
347 { | |
348 struct syntax_cache *cache = buf->syntax_cache; | |
349 if (!cache) /* Vbuffer_defaults and such don't have caches */ | |
350 return; | |
351 mark_object (cache->object); | |
352 if (cache->buffer) | |
353 mark_object (wrap_buffer (cache->buffer)); | |
354 mark_object (cache->syntax_table); | |
355 mark_object (cache->mirror_table); | |
356 mark_object (cache->start); | |
357 mark_object (cache->end); | |
358 } | |
359 | |
360 static void | |
361 reset_buffer_syntax_cache_range (struct syntax_cache *cache, | |
362 Lisp_Object buffer, int infinite) | |
363 { | |
364 Fset_marker (cache->start, make_int (1), buffer); | |
365 Fset_marker (cache->end, make_int (1), buffer); | |
366 Fset_marker_insertion_type (cache->start, Qt); | |
367 Fset_marker_insertion_type (cache->end, Qnil); | |
368 /* #### Should we "cache->no_syntax_table_prop = 1;" here? */ | |
369 /* #### Cf comment on INFINITE in init_syntax_cache. -- sjt */ | |
370 if (infinite) | |
371 { | |
372 cache->prev_change = EMACS_INT_MIN; | |
373 cache->next_change = EMACS_INT_MAX; | |
374 } | |
375 else | |
376 { | |
377 cache->prev_change = -1; | |
378 cache->next_change = -1; | |
379 } | |
380 } | |
381 | |
382 void | |
383 init_buffer_syntax_cache (struct buffer *buf) | |
384 { | |
385 struct syntax_cache *cache; | |
386 #ifdef NEW_GC | |
387 buf->syntax_cache = alloc_lrecord_type (struct syntax_cache, | |
388 &lrecord_syntax_cache); | |
389 #else /* not NEW_GC */ | |
390 buf->syntax_cache = xnew_and_zero (struct syntax_cache); | |
391 #endif /* not NEW_GC */ | |
392 cache = buf->syntax_cache; | |
393 cache->object = wrap_buffer (buf); | |
394 cache->buffer = buf; | |
395 cache->no_syntax_table_prop = 1; | |
396 cache->syntax_table = BUFFER_SYNTAX_TABLE (cache->buffer); | |
397 cache->mirror_table = BUFFER_MIRROR_SYNTAX_TABLE (cache->buffer); | |
398 cache->start = Fmake_marker (); | |
399 cache->end = Fmake_marker (); | |
400 reset_buffer_syntax_cache_range (cache, cache->object, 0); | |
401 } | |
402 | |
403 /* finalize the syntax cache for BUF */ | |
404 void | |
405 uninit_buffer_syntax_cache (struct buffer *buf) | |
406 { | |
407 #ifdef NEW_GC | |
408 mc_free (buf->syntax_cache); | |
409 #else /* not NEW_GC */ | |
410 xfree (buf->syntax_cache, struct syntax_cache *); | |
411 #endif /* not NEW_GC */ | |
412 buf->syntax_cache = 0; | |
413 } | |
414 | |
415 | |
416 static void | |
417 syntax_cache_table_was_changed (struct buffer *buf) | |
418 { | |
419 struct syntax_cache *cache = buf->syntax_cache; | |
420 if (cache->no_syntax_table_prop) | |
421 { | |
422 cache->syntax_table = | |
423 BUFFER_SYNTAX_TABLE (buf); | |
424 cache->mirror_table = | |
425 BUFFER_MIRROR_SYNTAX_TABLE (buf); | |
426 } | |
427 } | |
428 | |
429 /* The syntax-table property on the range covered by EXTENT may be changing, | |
430 either because EXTENT has a syntax-table property and is being attached | |
431 or detached (this includes having its endpoints changed), or because | |
432 the value of EXTENT's syntax-table property is changing. */ | |
433 | |
434 void | |
435 signal_syntax_cache_extent_changed (EXTENT extent) | |
436 { | |
437 Lisp_Object buffer = Fextent_object (wrap_extent (extent)); | |
438 if (BUFFERP (buffer)) | |
439 { | |
440 /* This was getting called with the buffer's start and end null, eg in | |
441 cperl mode, which triggers an assert in byte_marker_position. Cf | |
442 thread rooted at <yxz7j7xzk97.fsf@gimli.holgi.priv> on xemacs-beta. | |
443 <yxzfymklb6p.fsf@gimli.holgi.priv> has a recipe, but you also need | |
444 to delete or type SPC to get the crash. | |
445 #### Delete this comment when setup_syntax_cache is made sane. */ | |
446 struct syntax_cache *cache = XBUFFER (buffer)->syntax_cache; | |
447 /* #### would this be slower or less accurate in character terms? */ | |
448 Bytexpos start = extent_endpoint_byte (extent, 0); | |
449 Bytexpos end = extent_endpoint_byte (extent, 1); | |
450 Bytexpos start2 = byte_marker_position (cache->start); | |
451 Bytexpos end2 = byte_marker_position (cache->end); | |
452 /* If the extent is entirely before or entirely after the cache | |
453 range, it doesn't overlap. Otherwise, invalidate the range. */ | |
454 if (!(end < start2 || start > end2)) | |
455 reset_buffer_syntax_cache_range (cache, buffer, 0); | |
456 } | |
457 } | |
458 | |
459 /* Extents have been adjusted for insertion or deletion, so we need to | |
460 refetch the start and end position of the extent */ | |
461 void | |
462 signal_syntax_cache_extent_adjust (struct buffer *buf) | |
463 { | |
464 struct syntax_cache *cache = buf->syntax_cache; | |
465 /* If the cache was invalid before, leave it that way. We only want | |
466 to update the limits of validity when they were actually valid. */ | |
467 if (cache->prev_change < 0) | |
468 return; | |
469 cache->prev_change = marker_position (cache->start); | |
470 cache->next_change = marker_position (cache->end); | |
471 } | 389 } |
472 | 390 |
473 /* | 391 /* |
474 Update syntax_cache to an appropriate setting for position POS | 392 Update syntax_cache to an appropriate setting for position POS |
475 | 393 |
577 #ifdef NOT_WORTH_THE_EFFORT | 495 #ifdef NOT_WORTH_THE_EFFORT |
578 update_mirror_syntax_if_dirty (cache->mirror_table); | 496 update_mirror_syntax_if_dirty (cache->mirror_table); |
579 #endif /* NOT_WORTH_THE_EFFORT */ | 497 #endif /* NOT_WORTH_THE_EFFORT */ |
580 } | 498 } |
581 } | 499 } |
500 | |
501 /* buffer-specific APIs used in buffer.c | |
502 #### This is really unclean; | |
503 the syntax cache should just be a LISP object */ | |
504 | |
505 void | |
506 mark_buffer_syntax_cache (struct buffer *buf) | |
507 { | |
508 struct syntax_cache *cache = buf->syntax_cache; | |
509 if (!cache) /* Vbuffer_defaults and such don't have caches */ | |
510 return; | |
511 mark_object (cache->object); | |
512 if (cache->buffer) | |
513 mark_object (wrap_buffer (cache->buffer)); | |
514 mark_object (cache->syntax_table); | |
515 mark_object (cache->mirror_table); | |
516 mark_object (cache->start); | |
517 mark_object (cache->end); | |
518 } | |
519 | |
520 void | |
521 init_buffer_syntax_cache (struct buffer *buf) | |
522 { | |
523 struct syntax_cache *cache; | |
524 #ifdef NEW_GC | |
525 buf->syntax_cache = alloc_lrecord_type (struct syntax_cache, | |
526 &lrecord_syntax_cache); | |
527 #else /* not NEW_GC */ | |
528 buf->syntax_cache = xnew_and_zero (struct syntax_cache); | |
529 #endif /* not NEW_GC */ | |
530 cache = buf->syntax_cache; | |
531 cache->object = wrap_buffer (buf); | |
532 cache->buffer = buf; | |
533 cache->no_syntax_table_prop = 1; | |
534 cache->syntax_table = BUFFER_SYNTAX_TABLE (cache->buffer); | |
535 cache->mirror_table = BUFFER_MIRROR_SYNTAX_TABLE (cache->buffer); | |
536 cache->start = Fmake_marker (); | |
537 cache->end = Fmake_marker (); | |
538 reset_buffer_syntax_cache_range (cache, cache->object, 0); | |
539 } | |
540 | |
541 /* finalize the syntax cache for BUF */ | |
542 | |
543 void | |
544 uninit_buffer_syntax_cache (struct buffer *buf) | |
545 { | |
546 #ifdef NEW_GC | |
547 mc_free (buf->syntax_cache); | |
548 #else /* not NEW_GC */ | |
549 xfree (buf->syntax_cache, struct syntax_cache *); | |
550 #endif /* not NEW_GC */ | |
551 buf->syntax_cache = 0; | |
552 } | |
553 | |
554 /* extent-specific APIs used in extents.c and insdel.c */ | |
555 | |
556 /* The syntax-table property on the range covered by EXTENT may be changing, | |
557 either because EXTENT has a syntax-table property and is being attached | |
558 or detached (this includes having its endpoints changed), or because | |
559 the value of EXTENT's syntax-table property is changing. */ | |
560 | |
561 void | |
562 signal_syntax_cache_extent_changed (EXTENT extent) | |
563 { | |
564 Lisp_Object buffer = Fextent_object (wrap_extent (extent)); | |
565 if (BUFFERP (buffer)) | |
566 { | |
567 /* This was getting called with the buffer's start and end null, eg in | |
568 cperl mode, which triggers an assert in byte_marker_position. Cf | |
569 thread rooted at <yxz7j7xzk97.fsf@gimli.holgi.priv> on xemacs-beta. | |
570 <yxzfymklb6p.fsf@gimli.holgi.priv> has a recipe, but you also need | |
571 to delete or type SPC to get the crash. | |
572 #### Delete this comment when setup_syntax_cache is made sane. */ | |
573 struct syntax_cache *cache = XBUFFER (buffer)->syntax_cache; | |
574 /* #### would this be slower or less accurate in character terms? */ | |
575 Bytexpos start = extent_endpoint_byte (extent, 0); | |
576 Bytexpos end = extent_endpoint_byte (extent, 1); | |
577 Bytexpos start2 = byte_marker_position (cache->start); | |
578 Bytexpos end2 = byte_marker_position (cache->end); | |
579 /* If the extent is entirely before or entirely after the cache | |
580 range, it doesn't overlap. Otherwise, invalidate the range. */ | |
581 if (!(end < start2 || start > end2)) | |
582 reset_buffer_syntax_cache_range (cache, buffer, 0); | |
583 } | |
584 } | |
585 | |
586 /* Extents have been adjusted for insertion or deletion, so we need to | |
587 refetch the start and end position of the extent */ | |
588 void | |
589 signal_syntax_cache_extent_adjust (struct buffer *buf) | |
590 { | |
591 struct syntax_cache *cache = buf->syntax_cache; | |
592 /* If the cache was invalid before, leave it that way. We only want | |
593 to update the limits of validity when they were actually valid. */ | |
594 if (cache->prev_change < 0) | |
595 return; | |
596 cache->prev_change = marker_position (cache->start); | |
597 cache->next_change = marker_position (cache->end); | |
598 } | |
599 | |
600 | |
582 | 601 |
583 /* Convert a letter which signifies a syntax code | 602 /* Convert a letter which signifies a syntax code |
584 into the code it signifies. | 603 into the code it signifies. |
585 This is used by modify-syntax-entry, and other things. */ | 604 This is used by modify-syntax-entry, and other things. */ |
586 | 605 |