query-replace-regexp undo: Update next-replacement after undo

* lisp/replace.el (perform-replace):
Rename the local binding to not shadow next-replacement.
Update next-replacement after undo (Bug#37287).

* test/lisp/replace-tests.el (query-replace-undo-bug37287): Add test.
(query-replace-undo-bug37073): Tweak this test.
This commit is contained in:
Tino Calancha 2019-09-09 08:21:18 +02:00
parent c596be08f7
commit 30c4f35a6f
2 changed files with 25 additions and 7 deletions

View file

@ -2584,7 +2584,7 @@ It must return a string."
(num-replacements 0)
(nocasify t) ; Undo must preserve case (Bug#31073).
search-string
next-replacement)
last-replacement)
(while (and (< stack-idx stack-len)
stack
(or (null replaced) last-was-act-and-show))
@ -2595,9 +2595,9 @@ It must return a string."
;; Bind swapped values
;; (search-string <--> replacement)
search-string (nth (if replaced 4 3) elt)
next-replacement (nth (if replaced 3 4) elt)
last-replacement (nth (if replaced 3 4) elt)
search-string-replaced search-string
next-replacement-replaced next-replacement
last-replacement-replaced last-replacement
last-was-act-and-show nil)
(when (and (= stack-idx stack-len)
@ -2619,16 +2619,18 @@ It must return a string."
(match-data t (nth 2 elt)))
noedit
(replace-match-maybe-edit
next-replacement nocasify literal
last-replacement nocasify literal
noedit real-match-data backward)
replace-count (1- replace-count)
real-match-data
(save-excursion
(goto-char (match-beginning 0))
(if regexp-flag
(looking-at next-replacement)
(looking-at (regexp-quote next-replacement)))
(looking-at last-replacement)
(looking-at (regexp-quote last-replacement)))
(match-data t (nth 2 elt))))
(when regexp-flag
(setq next-replacement (nth 4 elt)))
;; Set replaced nil to keep in loop
(when (eq def 'undo-all)
(setq replaced nil

View file

@ -463,7 +463,9 @@ Return the last evalled form in BODY."
(should
(replace-tests-with-undo
input "theorem \\([0-9]+\\)"
"theorem \\\\ref{theo_\\1}"
'(replace-eval-replacement
replace-quote
(format "theorem \\\\ref{theo_%d}" (1+ (string-to-number (match-string 1)))))
((?\s . (1 2)) (?U . (3)))
?q
(string= input (buffer-string)))))
@ -479,4 +481,18 @@ Return the last evalled form in BODY."
?q
(string= expected (buffer-string))))))
(ert-deftest query-replace-undo-bug37287 ()
"Test for https://debbugs.gnu.org/37287 ."
(let ((input "foo-1\nfoo-2\nfoo-3")
(expected "foo-2\nfoo-2\nfoo-3"))
(should
(replace-tests-with-undo
input "\\([0-9]\\)"
'(replace-eval-replacement
replace-quote
(format "%d" (1+ (string-to-number (match-string 1)))))
((?\s . (1 2 4)) (?U . (3)))
?q
(string= expected (buffer-string))))))
;;; replace-tests.el ends here