* Recursive edits in `save-excursion'
@ 2006-09-25 3:57 Stuart D. Herring
2006-09-29 2:15 ` Richard Stallman
0 siblings, 1 reply; 4+ messages in thread
From: Stuart D. Herring @ 2006-09-25 3:57 UTC (permalink / raw)
I find that I get unexpected results from multiple recursive edits in
`save-excursion' forms in one command (e.g., evaluating
(list (save-excursion (recursive-edit) (current-buffer)) (save-excursion
(recursive-edit) (current-buffer)))
and, during each recursive edit, selecting some different buffer). The
first time, `current-buffer' returns the buffer selected during the
recursive edit, but the second time the buffer that was current when the
evaluation began is returned. Similar things happen with `point-marker'
in place of `current-buffer', which is how I found this. Is this a bug,
or is it just some consequence of interaction between the (recursive)
command loop and `save-excursion' that I don't understand?
Thanks,
Davis
PS - The "Recent Input" below is everything from "emacs -Q", so can be
used as a precise test case.
In GNU Emacs 22.0.50.1 (i686-pc-linux-gnu, Motif Version 2.2.2)
of 2006-09-24 on callahan
X server distributor `The XFree86 Project, Inc', version 11.0.40300000
configured using `configure '--with-x-toolkit=motif' '--with-xpm'
'--with-jpeg' '--with-tiff' '--with-gif' '--with-png' '--with-x''
Important settings:
value of $LC_ALL: nil
value of $LC_COLLATE: nil
value of $LC_CTYPE: nil
value of $LC_MESSAGES: nil
value of $LC_MONETARY: nil
value of $LC_NUMERIC: nil
value of $LC_TIME: nil
value of $LANG: en_US.UTF-8
locale-coding-system: utf-8
default-enable-multibyte-characters: t
Major mode: Fundamental
Minor modes in effect:
tooltip-mode: t
tool-bar-mode: t
mouse-wheel-mode: t
menu-bar-mode: t
file-name-shadow-mode: t
global-font-lock-mode: t
blink-cursor-mode: t
unify-8859-on-encoding-mode: t
utf-translate-cjk-mode: t
auto-compression-mode: t
line-number-mode: t
Recent input:
C-x b a <return> C-x b b <return> C-x b * s c r <tab>
<return> ( l i s t SPC ( s a v e - e x c u r s i o
n SPC ( r e c u r s i v e - e d i t ) S-SPC ( c u r
r e n t - b u f f e r ) ) C-- C-M-k C-y SPC C-y ) C-x
C-e C-x b a <return> C-M-c C-x b b <return> C-M-c <help-echo>
<help-echo> <help-echo> <help-echo> <menu-bar> <help-menu>
<report-emacs-bug>
Recent messages:
(emacs -Q)
For information about the GNU Project and its goals, type C-h C-p.
Mark set [2 times]
(#<buffer a> #<buffer *scratch*>)
Loading emacsbug...
Loading regexp-opt...done
Loading emacsbug...done
--
This product is sold by volume, not by mass. If it appears too dense or
too sparse, it is because mass-energy conversion has occurred during
shipping.
^ permalink raw reply [flat|nested] 4+ messages in thread
* Re: Recursive edits in `save-excursion'
2006-09-25 3:57 Recursive edits in `save-excursion' Stuart D. Herring
@ 2006-09-29 2:15 ` Richard Stallman
2006-09-29 23:13 ` Stuart D. Herring
0 siblings, 1 reply; 4+ messages in thread
From: Richard Stallman @ 2006-09-29 2:15 UTC (permalink / raw)
Cc: emacs-devel
The explanation for this is that save-excursion saves the current
buffer, but what you set when you switch buffers is the selected
window's buffer. save-excursion does not restore that. The first
save-excursion restores the original current buffer but doesn't
switch to it. The second recursive edit notices that the current
buffer isn't the same one you've switched to, so it arranges to
save and restore the current buffer.
I will document this.
^ permalink raw reply [flat|nested] 4+ messages in thread
* Re: Recursive edits in `save-excursion'
2006-09-29 2:15 ` Richard Stallman
@ 2006-09-29 23:13 ` Stuart D. Herring
2006-10-01 0:03 ` Richard Stallman
0 siblings, 1 reply; 4+ messages in thread
From: Stuart D. Herring @ 2006-09-29 23:13 UTC (permalink / raw)
Cc: emacs-devel
> The explanation for this is that save-excursion saves the current
> buffer, but what you set when you switch buffers is the selected
> window's buffer. save-excursion does not restore that. The first
> save-excursion restores the original current buffer but doesn't
> switch to it. The second recursive edit notices that the current
> buffer isn't the same one you've switched to, so it arranges to
> save and restore the current buffer.
So -- just to make sure that I understand correctly -- `recursive-edit'
acts like it was implemented as follows?
(defun recursive-edit ()
"..."
(let ((obuf (unless (eq (current-buffer) (window-buffer))
(current-buffer)))
(set-buffer (window-buffer))
(unwind-protect
(if (eq (catch 'exit (command-loop) nil) t) (signal 'quit nil))
(if (obuf (set-buffer obuf))))))
In other words, it acts like it is a `save-excursion' embedded if and only
if the current buffer and current window's buffer differ? So you could
defeat this by doing something like what follows?
(save-excursion (set-buffer (window-buffer)) (recursive-edit) ...)
My concern is not which buffer is current around this form, or in which
buffer the `recursive-edit' starts, but just that the `...' be evaluated
with the buffer current that was current when the recursive edit was
exited.
I also wonder if it would be profitable to use the original form, but
calling `window-buffer' instead of `current-buffer'?
(save-excursion (recursive-edit) (window-buffer))
A quick test with the 21.3 I have in front of me seems to support my
theory (both of the modified examples work as I would expect). Assuming
I'm correct that they work reliably, is there a reason to prefer one or
the other?
Thanks,
Davis
--
This product is sold by volume, not by mass. If it appears too dense or
too sparse, it is because mass-energy conversion has occurred during
shipping.
^ permalink raw reply [flat|nested] 4+ messages in thread
end of thread, other threads:[~2006-10-01 0:03 UTC | newest]
Thread overview: 4+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2006-09-25 3:57 Recursive edits in `save-excursion' Stuart D. Herring
2006-09-29 2:15 ` Richard Stallman
2006-09-29 23:13 ` Stuart D. Herring
2006-10-01 0:03 ` Richard Stallman
Code repositories for project(s) associated with this public inbox
https://git.savannah.gnu.org/cgit/emacs.git
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).