diff options
| author | Stefan Monnier | 2025-03-29 16:40:19 -0400 |
|---|---|---|
| committer | Stefan Monnier | 2025-03-29 17:49:49 -0400 |
| commit | 57da44fa702782e19cd9d60ea63ec2fd9ca48521 (patch) | |
| tree | 7182b458505348be363d9c0093a98a8b5043fb79 | |
| parent | 7c82cc8b975175aebbad1c43ec1cd98b3232f482 (diff) | |
| download | emacs-57da44fa702782e19cd9d60ea63ec2fd9ca48521.tar.gz emacs-57da44fa702782e19cd9d60ea63ec2fd9ca48521.zip | |
src/insdel.c (adjust_markers_for_replace): Fix insertion case
test/src/editfns-tests.el (editfns-tests--insert-via-replace): New test
| -rw-r--r-- | src/insdel.c | 19 | ||||
| -rw-r--r-- | test/src/editfns-tests.el | 14 |
2 files changed, 27 insertions, 6 deletions
diff --git a/src/insdel.c b/src/insdel.c index 20267265ab8..053b2d46380 100644 --- a/src/insdel.c +++ b/src/insdel.c | |||
| @@ -348,12 +348,20 @@ adjust_markers_for_replace (ptrdiff_t from, ptrdiff_t from_byte, | |||
| 348 | ptrdiff_t diff_chars = new_chars - old_chars; | 348 | ptrdiff_t diff_chars = new_chars - old_chars; |
| 349 | ptrdiff_t diff_bytes = new_bytes - old_bytes; | 349 | ptrdiff_t diff_bytes = new_bytes - old_bytes; |
| 350 | 350 | ||
| 351 | if (old_chars == 0) | ||
| 352 | { | ||
| 353 | /* Just an insertion: markers at FROM may need to move or not depending | ||
| 354 | on their marker type. Delegate this special case to | ||
| 355 | 'adjust_markers_for_insert' so the loop below can remain oblivious | ||
| 356 | to marker types. */ | ||
| 357 | adjust_markers_for_insert (from, from_byte, | ||
| 358 | from + new_chars, from_byte + new_bytes, | ||
| 359 | false); | ||
| 360 | return; | ||
| 361 | } | ||
| 362 | |||
| 351 | adjust_suspend_auto_hscroll (from, from + old_chars); | 363 | adjust_suspend_auto_hscroll (from, from + old_chars); |
| 352 | 364 | ||
| 353 | /* FIXME: When OLD_CHARS is 0, this "replacement" is really just an | ||
| 354 | insertion, but the behavior we provide here in that case is that of | ||
| 355 | `insert-before-markers` rather than that of `insert`. | ||
| 356 | Maybe not a bug, but not a feature either. */ | ||
| 357 | for (m = BUF_MARKERS (current_buffer); m; m = m->next) | 365 | for (m = BUF_MARKERS (current_buffer); m; m = m->next) |
| 358 | { | 366 | { |
| 359 | if (m->bytepos >= prev_to_byte) | 367 | if (m->bytepos >= prev_to_byte) |
| @@ -371,8 +379,7 @@ adjust_markers_for_replace (ptrdiff_t from, ptrdiff_t from_byte, | |||
| 371 | check_markers (); | 379 | check_markers (); |
| 372 | 380 | ||
| 373 | adjust_overlays_for_insert (from + old_chars, new_chars, true); | 381 | adjust_overlays_for_insert (from + old_chars, new_chars, true); |
| 374 | if (old_chars) | 382 | adjust_overlays_for_delete (from, old_chars); |
| 375 | adjust_overlays_for_delete (from, old_chars); | ||
| 376 | } | 383 | } |
| 377 | 384 | ||
| 378 | /* Starting at POS (BYTEPOS), find the byte position corresponding to | 385 | /* Starting at POS (BYTEPOS), find the byte position corresponding to |
diff --git a/test/src/editfns-tests.el b/test/src/editfns-tests.el index 3da9d4e8acd..2553ad3ec2c 100644 --- a/test/src/editfns-tests.el +++ b/test/src/editfns-tests.el | |||
| @@ -357,6 +357,20 @@ | |||
| 357 | (should (= m7a (+ (point-min) 7))))) | 357 | (should (= m7a (+ (point-min) 7))))) |
| 358 | (widen))))) | 358 | (widen))))) |
| 359 | 359 | ||
| 360 | (ert-deftest editfns-tests--insert-via-replace () | ||
| 361 | (with-temp-buffer | ||
| 362 | (insert "bar") | ||
| 363 | (goto-char (point-min)) | ||
| 364 | ;; Check that markers insertion type is respected when an insertion | ||
| 365 | ;; happens via a "replace" operation. | ||
| 366 | (let ((m1 (copy-marker (point) nil)) | ||
| 367 | (m2 (copy-marker (point) t))) | ||
| 368 | (looking-at "\\(\\)") | ||
| 369 | (replace-match "foo") | ||
| 370 | (should (equal "foobar" (buffer-string))) | ||
| 371 | (should (= (point-min) m1)) | ||
| 372 | (should (= (+ (point-min) 3) m2))))) | ||
| 373 | |||
| 360 | (ert-deftest delete-region-undo-markers-1 () | 374 | (ert-deftest delete-region-undo-markers-1 () |
| 361 | "Make sure we don't end up with freed markers reachable from Lisp." | 375 | "Make sure we don't end up with freed markers reachable from Lisp." |
| 362 | ;; https://debbugs.gnu.org/cgi/bugreport.cgi?bug=30931#40 | 376 | ;; https://debbugs.gnu.org/cgi/bugreport.cgi?bug=30931#40 |