Mercurial > emacs
comparison src/intervals.c @ 28269:fd13be8ae190
Changes towards better type safety regarding intervals, primarily
regarding the "parent" handle. These just separate out the different
usages based on the type of parent (interval vs lisp object); later
changes will do type checking and enforcement.
* intervals.h (NULL_INTERVAL): Cast to INTERVAL type.
(INT_LISPLIKE): New macro.
(NULL_INTERVAL_P): Use it.
(INTERVAL_HAS_PARENT, INTERVAL_HAS_OBJECT, SET_INTERVAL_PARENT,
SET_INTERVAL_OBJECT, INTERVAL_PARENT, COPY_INTERVAL_PARENT,
GET_INTERVAL_OBJECT, INTERVAL_PARENT_OR_NULL): New macros.
* alloc.c (make_interval, gc_sweep): Use new macros; eliminate all
explicit references to "parent" field of struct interval and
associated unclean type conversions.
* intervals.c (create_root_interval, root_interval, rotate_right,
rotate_left, balance_possible_root_interval, split_interval_right,
split_interval_left, interval_start_pos, find_interval,
next_interval, previous_interval, update_interval,
adjust_intervals_for_insertion, delete_node, delete_interval,
adjust_intervals_for_deletion, merge_interval_right,
merge_interval_left, reproduce_tree, graft_intervals_into_buffer,
copy_intervals_to_string): Likewise.
* intervals.h (AM_LEFT_CHILD, AM_RIGHT_CHILD, RESET_INTERVAL):
Likewise.
* syntax.c (update_syntax_table): Likewise.
* intervals.c (reproduce_tree_obj): New function, like
reproduce_tree but takes a Lisp_Object for the parent. Declare
with prototype.
(graft_intervals_into_buffer): Use it when appropriate.
(reproduce_tree): Declare with prototype.
(balance_possible_root_interval): Check that the parent is a lisp
object before trying to examine its type.
author | Ken Raeburn <raeburn@raeburn.org> |
---|---|
date | Wed, 22 Mar 2000 21:44:05 +0000 |
parents | abfcde8428cb |
children | 451721e784a8 |
comparison
equal
deleted
inserted
replaced
28268:33f65d22f2a8 | 28269:fd13be8ae190 |
---|---|
52 #define TMEM(sym, set) (CONSP (set) ? ! NILP (Fmemq (sym, set)) : ! NILP (set)) | 52 #define TMEM(sym, set) (CONSP (set) ? ! NILP (Fmemq (sym, set)) : ! NILP (set)) |
53 | 53 |
54 #define min(x, y) ((x) < (y) ? (x) : (y)) | 54 #define min(x, y) ((x) < (y) ? (x) : (y)) |
55 | 55 |
56 Lisp_Object merge_properties_sticky (); | 56 Lisp_Object merge_properties_sticky (); |
57 static INTERVAL reproduce_tree P_ ((INTERVAL, INTERVAL)); | |
58 static INTERVAL reproduce_tree_obj P_ ((INTERVAL, Lisp_Object)); | |
57 | 59 |
58 /* Utility functions for intervals. */ | 60 /* Utility functions for intervals. */ |
59 | 61 |
60 | 62 |
61 /* Create the root interval of some object, a buffer or string. */ | 63 /* Create the root interval of some object, a buffer or string. */ |
82 new->total_length = XSTRING (parent)->size; | 84 new->total_length = XSTRING (parent)->size; |
83 XSTRING (parent)->intervals = new; | 85 XSTRING (parent)->intervals = new; |
84 new->position = 0; | 86 new->position = 0; |
85 } | 87 } |
86 | 88 |
87 new->parent = (INTERVAL) XFASTINT (parent); | 89 SET_INTERVAL_OBJECT (new, parent); |
88 | 90 |
89 return new; | 91 return new; |
90 } | 92 } |
91 | 93 |
92 /* Make the interval TARGET have exactly the properties of SOURCE */ | 94 /* Make the interval TARGET have exactly the properties of SOURCE */ |
267 INTERVAL interval; | 269 INTERVAL interval; |
268 { | 270 { |
269 register INTERVAL i = interval; | 271 register INTERVAL i = interval; |
270 | 272 |
271 while (! ROOT_INTERVAL_P (i)) | 273 while (! ROOT_INTERVAL_P (i)) |
272 i = i->parent; | 274 i = INTERVAL_PARENT (i); |
273 | 275 |
274 return i; | 276 return i; |
275 } | 277 } |
276 #endif | 278 #endif |
277 | 279 |
294 | 296 |
295 /* Deal with any Parent of A; make it point to B. */ | 297 /* Deal with any Parent of A; make it point to B. */ |
296 if (! ROOT_INTERVAL_P (interval)) | 298 if (! ROOT_INTERVAL_P (interval)) |
297 { | 299 { |
298 if (AM_LEFT_CHILD (interval)) | 300 if (AM_LEFT_CHILD (interval)) |
299 interval->parent->left = B; | 301 INTERVAL_PARENT (interval)->left = B; |
300 else | 302 else |
301 interval->parent->right = B; | 303 INTERVAL_PARENT (interval)->right = B; |
302 } | 304 } |
303 B->parent = interval->parent; | 305 COPY_INTERVAL_PARENT (B, interval); |
304 | 306 |
305 /* Make B the parent of A */ | 307 /* Make B the parent of A */ |
306 i = B->right; | 308 i = B->right; |
307 B->right = interval; | 309 B->right = interval; |
308 interval->parent = B; | 310 SET_INTERVAL_PARENT (interval, B); |
309 | 311 |
310 /* Make A point to c */ | 312 /* Make A point to c */ |
311 interval->left = i; | 313 interval->left = i; |
312 if (! NULL_INTERVAL_P (i)) | 314 if (! NULL_INTERVAL_P (i)) |
313 i->parent = interval; | 315 SET_INTERVAL_PARENT (i, interval); |
314 | 316 |
315 /* A's total length is decreased by the length of B and its left child. */ | 317 /* A's total length is decreased by the length of B and its left child. */ |
316 interval->total_length -= B->total_length - LEFT_TOTAL_LENGTH (interval); | 318 interval->total_length -= B->total_length - LEFT_TOTAL_LENGTH (interval); |
317 | 319 |
318 /* B must have the same total length of A. */ | 320 /* B must have the same total length of A. */ |
340 | 342 |
341 /* Deal with any parent of A; make it point to B. */ | 343 /* Deal with any parent of A; make it point to B. */ |
342 if (! ROOT_INTERVAL_P (interval)) | 344 if (! ROOT_INTERVAL_P (interval)) |
343 { | 345 { |
344 if (AM_LEFT_CHILD (interval)) | 346 if (AM_LEFT_CHILD (interval)) |
345 interval->parent->left = B; | 347 INTERVAL_PARENT (interval)->left = B; |
346 else | 348 else |
347 interval->parent->right = B; | 349 INTERVAL_PARENT (interval)->right = B; |
348 } | 350 } |
349 B->parent = interval->parent; | 351 COPY_INTERVAL_PARENT (B, interval); |
350 | 352 |
351 /* Make B the parent of A */ | 353 /* Make B the parent of A */ |
352 i = B->left; | 354 i = B->left; |
353 B->left = interval; | 355 B->left = interval; |
354 interval->parent = B; | 356 SET_INTERVAL_PARENT (interval, B); |
355 | 357 |
356 /* Make A point to c */ | 358 /* Make A point to c */ |
357 interval->right = i; | 359 interval->right = i; |
358 if (! NULL_INTERVAL_P (i)) | 360 if (! NULL_INTERVAL_P (i)) |
359 i->parent = interval; | 361 SET_INTERVAL_PARENT (i, interval); |
360 | 362 |
361 /* A's total length is decreased by the length of B and its right child. */ | 363 /* A's total length is decreased by the length of B and its right child. */ |
362 interval->total_length -= B->total_length - RIGHT_TOTAL_LENGTH (interval); | 364 interval->total_length -= B->total_length - RIGHT_TOTAL_LENGTH (interval); |
363 | 365 |
364 /* B must have the same total length of A. */ | 366 /* B must have the same total length of A. */ |
409 static INLINE INTERVAL | 411 static INLINE INTERVAL |
410 balance_possible_root_interval (interval) | 412 balance_possible_root_interval (interval) |
411 register INTERVAL interval; | 413 register INTERVAL interval; |
412 { | 414 { |
413 Lisp_Object parent; | 415 Lisp_Object parent; |
414 | 416 int have_parent = 0; |
415 if (interval->parent == NULL_INTERVAL) | 417 |
418 if (!INTERVAL_HAS_OBJECT (interval) && !INTERVAL_HAS_PARENT (interval)) | |
416 return interval; | 419 return interval; |
417 | 420 |
418 XSETFASTINT (parent, (EMACS_INT) interval->parent); | 421 if (INTERVAL_HAS_OBJECT (interval)) |
422 { | |
423 have_parent = 1; | |
424 GET_INTERVAL_OBJECT (parent, interval); | |
425 } | |
419 interval = balance_an_interval (interval); | 426 interval = balance_an_interval (interval); |
420 | 427 |
421 if (BUFFERP (parent)) | 428 if (have_parent) |
422 BUF_INTERVALS (XBUFFER (parent)) = interval; | 429 { |
423 else if (STRINGP (parent)) | 430 if (BUFFERP (parent)) |
424 XSTRING (parent)->intervals = interval; | 431 BUF_INTERVALS (XBUFFER (parent)) = interval; |
432 else if (STRINGP (parent)) | |
433 XSTRING (parent)->intervals = interval; | |
434 } | |
425 | 435 |
426 return interval; | 436 return interval; |
427 } | 437 } |
428 | 438 |
429 /* Balance the interval tree TREE. Balancing is by weight | 439 /* Balance the interval tree TREE. Balancing is by weight |
474 INTERVAL new = make_interval (); | 484 INTERVAL new = make_interval (); |
475 int position = interval->position; | 485 int position = interval->position; |
476 int new_length = LENGTH (interval) - offset; | 486 int new_length = LENGTH (interval) - offset; |
477 | 487 |
478 new->position = position + offset; | 488 new->position = position + offset; |
479 new->parent = interval; | 489 SET_INTERVAL_PARENT (new, interval); |
480 | 490 |
481 if (NULL_RIGHT_CHILD (interval)) | 491 if (NULL_RIGHT_CHILD (interval)) |
482 { | 492 { |
483 interval->right = new; | 493 interval->right = new; |
484 new->total_length = new_length; | 494 new->total_length = new_length; |
485 } | 495 } |
486 else | 496 else |
487 { | 497 { |
488 /* Insert the new node between INTERVAL and its right child. */ | 498 /* Insert the new node between INTERVAL and its right child. */ |
489 new->right = interval->right; | 499 new->right = interval->right; |
490 interval->right->parent = new; | 500 SET_INTERVAL_PARENT (interval->right, new); |
491 interval->right = new; | 501 interval->right = new; |
492 new->total_length = new_length + new->right->total_length; | 502 new->total_length = new_length + new->right->total_length; |
493 balance_an_interval (new); | 503 balance_an_interval (new); |
494 } | 504 } |
495 | 505 |
519 INTERVAL new = make_interval (); | 529 INTERVAL new = make_interval (); |
520 int new_length = offset; | 530 int new_length = offset; |
521 | 531 |
522 new->position = interval->position; | 532 new->position = interval->position; |
523 interval->position = interval->position + offset; | 533 interval->position = interval->position + offset; |
524 new->parent = interval; | 534 SET_INTERVAL_PARENT (new, interval); |
525 | 535 |
526 if (NULL_LEFT_CHILD (interval)) | 536 if (NULL_LEFT_CHILD (interval)) |
527 { | 537 { |
528 interval->left = new; | 538 interval->left = new; |
529 new->total_length = new_length; | 539 new->total_length = new_length; |
530 } | 540 } |
531 else | 541 else |
532 { | 542 { |
533 /* Insert the new node between INTERVAL and its left child. */ | 543 /* Insert the new node between INTERVAL and its left child. */ |
534 new->left = interval->left; | 544 new->left = interval->left; |
535 new->left->parent = new; | 545 SET_INTERVAL_PARENT (new->left, new); |
536 interval->left = new; | 546 interval->left = new; |
537 new->total_length = new_length + new->left->total_length; | 547 new->total_length = new_length + new->left->total_length; |
538 balance_an_interval (new); | 548 balance_an_interval (new); |
539 } | 549 } |
540 | 550 |
558 Lisp_Object parent; | 568 Lisp_Object parent; |
559 | 569 |
560 if (NULL_INTERVAL_P (source)) | 570 if (NULL_INTERVAL_P (source)) |
561 return 0; | 571 return 0; |
562 | 572 |
563 XSETFASTINT (parent, (EMACS_INT) source->parent); | 573 GET_INTERVAL_OBJECT (parent, source); |
564 if (BUFFERP (parent)) | 574 if (BUFFERP (parent)) |
565 return BUF_BEG (XBUFFER (parent)); | 575 return BUF_BEG (XBUFFER (parent)); |
566 return 0; | 576 return 0; |
567 } | 577 } |
568 | 578 |
582 register int position; | 592 register int position; |
583 { | 593 { |
584 /* The distance from the left edge of the subtree at TREE | 594 /* The distance from the left edge of the subtree at TREE |
585 to POSITION. */ | 595 to POSITION. */ |
586 register int relative_position; | 596 register int relative_position; |
587 Lisp_Object parent; | |
588 | 597 |
589 if (NULL_INTERVAL_P (tree)) | 598 if (NULL_INTERVAL_P (tree)) |
590 return NULL_INTERVAL; | 599 return NULL_INTERVAL; |
591 | 600 |
592 XSETFASTINT (parent, (EMACS_INT) tree->parent); | |
593 relative_position = position; | 601 relative_position = position; |
594 if (BUFFERP (parent)) | 602 if (INTERVAL_HAS_OBJECT (tree)) |
595 relative_position -= BUF_BEG (XBUFFER (parent)); | 603 { |
604 Lisp_Object parent; | |
605 GET_INTERVAL_OBJECT (parent, tree); | |
606 if (BUFFERP (parent)) | |
607 relative_position -= BUF_BEG (XBUFFER (parent)); | |
608 } | |
596 | 609 |
597 if (relative_position > TOTAL_LENGTH (tree)) | 610 if (relative_position > TOTAL_LENGTH (tree)) |
598 abort (); /* Paranoia */ | 611 abort (); /* Paranoia */ |
599 | 612 |
600 tree = balance_possible_root_interval (tree); | 613 tree = balance_possible_root_interval (tree); |
651 | 664 |
652 while (! NULL_PARENT (i)) | 665 while (! NULL_PARENT (i)) |
653 { | 666 { |
654 if (AM_LEFT_CHILD (i)) | 667 if (AM_LEFT_CHILD (i)) |
655 { | 668 { |
656 i = i->parent; | 669 i = INTERVAL_PARENT (i); |
657 i->position = next_position; | 670 i->position = next_position; |
658 return i; | 671 return i; |
659 } | 672 } |
660 | 673 |
661 i = i->parent; | 674 i = INTERVAL_PARENT (i); |
662 } | 675 } |
663 | 676 |
664 return NULL_INTERVAL; | 677 return NULL_INTERVAL; |
665 } | 678 } |
666 | 679 |
690 i = interval; | 703 i = interval; |
691 while (! NULL_PARENT (i)) | 704 while (! NULL_PARENT (i)) |
692 { | 705 { |
693 if (AM_RIGHT_CHILD (i)) | 706 if (AM_RIGHT_CHILD (i)) |
694 { | 707 { |
695 i = i->parent; | 708 i = INTERVAL_PARENT (i); |
696 | 709 |
697 i->position = interval->position - LENGTH (i); | 710 i->position = interval->position - LENGTH (i); |
698 return i; | 711 return i; |
699 } | 712 } |
700 i = i->parent; | 713 i = INTERVAL_PARENT (i); |
701 } | 714 } |
702 | 715 |
703 return NULL_INTERVAL; | 716 return NULL_INTERVAL; |
704 } | 717 } |
705 | 718 |
726 i = i->left; /* Move to the left child */ | 739 i = i->left; /* Move to the left child */ |
727 } | 740 } |
728 else if (NULL_PARENT (i)) | 741 else if (NULL_PARENT (i)) |
729 error ("Point before start of properties"); | 742 error ("Point before start of properties"); |
730 else | 743 else |
731 i = i->parent; | 744 i = INTERVAL_PARENT (i); |
732 continue; | 745 continue; |
733 } | 746 } |
734 else if (pos >= INTERVAL_LAST_POS (i)) | 747 else if (pos >= INTERVAL_LAST_POS (i)) |
735 { | 748 { |
736 /* Move right. */ | 749 /* Move right. */ |
741 i = i->right; /* Move to the right child */ | 754 i = i->right; /* Move to the right child */ |
742 } | 755 } |
743 else if (NULL_PARENT (i)) | 756 else if (NULL_PARENT (i)) |
744 error ("Point after end of properties"); | 757 error ("Point after end of properties"); |
745 else | 758 else |
746 i = i->parent; | 759 i = INTERVAL_PARENT (i); |
747 continue; | 760 continue; |
748 } | 761 } |
749 else | 762 else |
750 return i; | 763 return i; |
751 } | 764 } |
836 int offset; | 849 int offset; |
837 | 850 |
838 if (TOTAL_LENGTH (tree) == 0) /* Paranoia */ | 851 if (TOTAL_LENGTH (tree) == 0) /* Paranoia */ |
839 abort (); | 852 abort (); |
840 | 853 |
841 XSETFASTINT (parent, (EMACS_INT) tree->parent); | 854 GET_INTERVAL_OBJECT (parent, tree); |
842 offset = (BUFFERP (parent) ? BUF_BEG (XBUFFER (parent)) : 0); | 855 offset = (BUFFERP (parent) ? BUF_BEG (XBUFFER (parent)) : 0); |
843 | 856 |
844 /* If inserting at point-max of a buffer, that position will be out | 857 /* If inserting at point-max of a buffer, that position will be out |
845 of range. Remember that buffer positions are 1-based. */ | 858 of range. Remember that buffer positions are 1-based. */ |
846 if (position >= TOTAL_LENGTH (tree) + offset) | 859 if (position >= TOTAL_LENGTH (tree) + offset) |
942 prev = previous_interval (i); | 955 prev = previous_interval (i); |
943 | 956 |
944 /* Even if we are positioned between intervals, we default | 957 /* Even if we are positioned between intervals, we default |
945 to the left one if it exists. We extend it now and split | 958 to the left one if it exists. We extend it now and split |
946 off a part later, if stickiness demands it. */ | 959 off a part later, if stickiness demands it. */ |
947 for (temp = prev ? prev : i;! NULL_INTERVAL_P (temp); temp = temp->parent) | 960 for (temp = prev ? prev : i; temp; temp = INTERVAL_PARENT_OR_NULL (temp)) |
948 { | 961 { |
949 temp->total_length += length; | 962 temp->total_length += length; |
950 temp = balance_possible_root_interval (temp); | 963 temp = balance_possible_root_interval (temp); |
951 } | 964 } |
952 | 965 |
998 } | 1011 } |
999 | 1012 |
1000 /* Otherwise just extend the interval. */ | 1013 /* Otherwise just extend the interval. */ |
1001 else | 1014 else |
1002 { | 1015 { |
1003 for (temp = i; ! NULL_INTERVAL_P (temp); temp = temp->parent) | 1016 for (temp = i; temp; temp = INTERVAL_PARENT_OR_NULL (temp)) |
1004 { | 1017 { |
1005 temp->total_length += length; | 1018 temp->total_length += length; |
1006 temp = balance_possible_root_interval (temp); | 1019 temp = balance_possible_root_interval (temp); |
1007 } | 1020 } |
1008 } | 1021 } |
1206 { | 1219 { |
1207 this = this->left; | 1220 this = this->left; |
1208 this->total_length += migrate_amt; | 1221 this->total_length += migrate_amt; |
1209 } | 1222 } |
1210 this->left = migrate; | 1223 this->left = migrate; |
1211 migrate->parent = this; | 1224 SET_INTERVAL_PARENT (migrate, this); |
1212 | 1225 |
1213 return i->right; | 1226 return i->right; |
1214 } | 1227 } |
1215 | 1228 |
1216 /* Delete interval I from its tree by calling `delete_node' | 1229 /* Delete interval I from its tree by calling `delete_node' |
1230 abort (); | 1243 abort (); |
1231 | 1244 |
1232 if (ROOT_INTERVAL_P (i)) | 1245 if (ROOT_INTERVAL_P (i)) |
1233 { | 1246 { |
1234 Lisp_Object owner; | 1247 Lisp_Object owner; |
1235 XSETFASTINT (owner, (EMACS_INT) i->parent); | 1248 GET_INTERVAL_OBJECT (owner, i); |
1236 parent = delete_node (i); | 1249 parent = delete_node (i); |
1237 if (! NULL_INTERVAL_P (parent)) | 1250 if (! NULL_INTERVAL_P (parent)) |
1238 parent->parent = (INTERVAL) XFASTINT (owner); | 1251 SET_INTERVAL_OBJECT (parent, owner); |
1239 | 1252 |
1240 if (BUFFERP (owner)) | 1253 if (BUFFERP (owner)) |
1241 BUF_INTERVALS (XBUFFER (owner)) = parent; | 1254 BUF_INTERVALS (XBUFFER (owner)) = parent; |
1242 else if (STRINGP (owner)) | 1255 else if (STRINGP (owner)) |
1243 XSTRING (owner)->intervals = parent; | 1256 XSTRING (owner)->intervals = parent; |
1245 abort (); | 1258 abort (); |
1246 | 1259 |
1247 return; | 1260 return; |
1248 } | 1261 } |
1249 | 1262 |
1250 parent = i->parent; | 1263 parent = INTERVAL_PARENT (i); |
1251 if (AM_LEFT_CHILD (i)) | 1264 if (AM_LEFT_CHILD (i)) |
1252 { | 1265 { |
1253 parent->left = delete_node (i); | 1266 parent->left = delete_node (i); |
1254 if (! NULL_INTERVAL_P (parent->left)) | 1267 if (! NULL_INTERVAL_P (parent->left)) |
1255 parent->left->parent = parent; | 1268 SET_INTERVAL_PARENT (parent->left, parent); |
1256 } | 1269 } |
1257 else | 1270 else |
1258 { | 1271 { |
1259 parent->right = delete_node (i); | 1272 parent->right = delete_node (i); |
1260 if (! NULL_INTERVAL_P (parent->right)) | 1273 if (! NULL_INTERVAL_P (parent->right)) |
1261 parent->right->parent = parent; | 1274 SET_INTERVAL_PARENT (parent->right, parent); |
1262 } | 1275 } |
1263 } | 1276 } |
1264 | 1277 |
1265 /* Find the interval in TREE corresponding to the relative position | 1278 /* Find the interval in TREE corresponding to the relative position |
1266 FROM and delete as much as possible of AMOUNT from that interval. | 1279 FROM and delete as much as possible of AMOUNT from that interval. |
1341 register int left_to_delete = length; | 1354 register int left_to_delete = length; |
1342 register INTERVAL tree = BUF_INTERVALS (buffer); | 1355 register INTERVAL tree = BUF_INTERVALS (buffer); |
1343 Lisp_Object parent; | 1356 Lisp_Object parent; |
1344 int offset; | 1357 int offset; |
1345 | 1358 |
1346 XSETFASTINT (parent, (EMACS_INT) tree->parent); | 1359 GET_INTERVAL_OBJECT (parent, tree); |
1347 offset = (BUFFERP (parent) ? BUF_BEG (XBUFFER (parent)) : 0); | 1360 offset = (BUFFERP (parent) ? BUF_BEG (XBUFFER (parent)) : 0); |
1348 | 1361 |
1349 if (NULL_INTERVAL_P (tree)) | 1362 if (NULL_INTERVAL_P (tree)) |
1350 return; | 1363 return; |
1351 | 1364 |
1438 while (! NULL_PARENT (successor)) /* It's above us. Subtract as | 1451 while (! NULL_PARENT (successor)) /* It's above us. Subtract as |
1439 we ascend. */ | 1452 we ascend. */ |
1440 { | 1453 { |
1441 if (AM_LEFT_CHILD (successor)) | 1454 if (AM_LEFT_CHILD (successor)) |
1442 { | 1455 { |
1443 successor = successor->parent; | 1456 successor = INTERVAL_PARENT (successor); |
1444 delete_interval (i); | 1457 delete_interval (i); |
1445 return successor; | 1458 return successor; |
1446 } | 1459 } |
1447 | 1460 |
1448 successor = successor->parent; | 1461 successor = INTERVAL_PARENT (successor); |
1449 successor->total_length -= absorb; | 1462 successor->total_length -= absorb; |
1450 } | 1463 } |
1451 | 1464 |
1452 /* This must be the rightmost or last interval and cannot | 1465 /* This must be the rightmost or last interval and cannot |
1453 be merged right. The caller should have known. */ | 1466 be merged right. The caller should have known. */ |
1491 while (! NULL_PARENT (predecessor)) /* It's above us. Go up, | 1504 while (! NULL_PARENT (predecessor)) /* It's above us. Go up, |
1492 subtracting ABSORB. */ | 1505 subtracting ABSORB. */ |
1493 { | 1506 { |
1494 if (AM_RIGHT_CHILD (predecessor)) | 1507 if (AM_RIGHT_CHILD (predecessor)) |
1495 { | 1508 { |
1496 predecessor = predecessor->parent; | 1509 predecessor = INTERVAL_PARENT (predecessor); |
1497 delete_interval (i); | 1510 delete_interval (i); |
1498 return predecessor; | 1511 return predecessor; |
1499 } | 1512 } |
1500 | 1513 |
1501 predecessor = predecessor->parent; | 1514 predecessor = INTERVAL_PARENT (predecessor); |
1502 predecessor->total_length -= absorb; | 1515 predecessor->total_length -= absorb; |
1503 } | 1516 } |
1504 | 1517 |
1505 /* This must be the leftmost or first interval and cannot | 1518 /* This must be the leftmost or first interval and cannot |
1506 be merged left. The caller should have known. */ | 1519 be merged left. The caller should have known. */ |
1518 { | 1531 { |
1519 register INTERVAL t = make_interval (); | 1532 register INTERVAL t = make_interval (); |
1520 | 1533 |
1521 bcopy (source, t, INTERVAL_SIZE); | 1534 bcopy (source, t, INTERVAL_SIZE); |
1522 copy_properties (source, t); | 1535 copy_properties (source, t); |
1523 t->parent = parent; | 1536 SET_INTERVAL_PARENT (t, parent); |
1537 if (! NULL_LEFT_CHILD (source)) | |
1538 t->left = reproduce_tree (source->left, t); | |
1539 if (! NULL_RIGHT_CHILD (source)) | |
1540 t->right = reproduce_tree (source->right, t); | |
1541 | |
1542 return t; | |
1543 } | |
1544 | |
1545 static INTERVAL | |
1546 reproduce_tree_obj (source, parent) | |
1547 INTERVAL source; | |
1548 Lisp_Object parent; | |
1549 { | |
1550 register INTERVAL t = make_interval (); | |
1551 | |
1552 bcopy (source, t, INTERVAL_SIZE); | |
1553 copy_properties (source, t); | |
1554 SET_INTERVAL_OBJECT (t, parent); | |
1524 if (! NULL_LEFT_CHILD (source)) | 1555 if (! NULL_LEFT_CHILD (source)) |
1525 t->left = reproduce_tree (source->left, t); | 1556 t->left = reproduce_tree (source->left, t); |
1526 if (! NULL_RIGHT_CHILD (source)) | 1557 if (! NULL_RIGHT_CHILD (source)) |
1527 t->right = reproduce_tree (source->right, t); | 1558 t->right = reproduce_tree (source->right, t); |
1528 | 1559 |
1652 simply copy over the interval structure. */ | 1683 simply copy over the interval structure. */ |
1653 if ((BUF_Z (buffer) - BUF_BEG (buffer)) == TOTAL_LENGTH (source)) | 1684 if ((BUF_Z (buffer) - BUF_BEG (buffer)) == TOTAL_LENGTH (source)) |
1654 { | 1685 { |
1655 Lisp_Object buf; | 1686 Lisp_Object buf; |
1656 XSETBUFFER (buf, buffer); | 1687 XSETBUFFER (buf, buffer); |
1657 BUF_INTERVALS (buffer) = reproduce_tree (source, buf); | 1688 BUF_INTERVALS (buffer) = reproduce_tree_obj (source, buf); |
1658 BUF_INTERVALS (buffer)->position = 1; | 1689 BUF_INTERVALS (buffer)->position = 1; |
1659 | 1690 |
1660 /* Explicitly free the old tree here? */ | 1691 /* Explicitly free the old tree here? */ |
1661 | 1692 |
1662 return; | 1693 return; |
1674 /* If the buffer contains only the new string, but | 1705 /* If the buffer contains only the new string, but |
1675 there was already some interval tree there, then it may be | 1706 there was already some interval tree there, then it may be |
1676 some zero length intervals. Eventually, do something clever | 1707 some zero length intervals. Eventually, do something clever |
1677 about inserting properly. For now, just waste the old intervals. */ | 1708 about inserting properly. For now, just waste the old intervals. */ |
1678 { | 1709 { |
1679 BUF_INTERVALS (buffer) = reproduce_tree (source, tree->parent); | 1710 BUF_INTERVALS (buffer) = reproduce_tree (source, INTERVAL_PARENT (tree)); |
1680 BUF_INTERVALS (buffer)->position = 1; | 1711 BUF_INTERVALS (buffer)->position = 1; |
1681 /* Explicitly free the old tree here. */ | 1712 /* Explicitly free the old tree here. */ |
1682 | 1713 |
1683 return; | 1714 return; |
1684 } | 1715 } |
2234 INTERVAL interval_copy = copy_intervals (BUF_INTERVALS (buffer), | 2265 INTERVAL interval_copy = copy_intervals (BUF_INTERVALS (buffer), |
2235 position, length); | 2266 position, length); |
2236 if (NULL_INTERVAL_P (interval_copy)) | 2267 if (NULL_INTERVAL_P (interval_copy)) |
2237 return; | 2268 return; |
2238 | 2269 |
2239 interval_copy->parent = (INTERVAL) XFASTINT (string); | 2270 SET_INTERVAL_OBJECT (interval_copy, string); |
2240 XSTRING (string)->intervals = interval_copy; | 2271 XSTRING (string)->intervals = interval_copy; |
2241 } | 2272 } |
2242 | 2273 |
2243 /* Return 1 if strings S1 and S2 have identical properties; 0 otherwise. | 2274 /* Return 1 if strings S1 and S2 have identical properties; 0 otherwise. |
2244 Assume they have identical characters. */ | 2275 Assume they have identical characters. */ |