Subject: bug#7728: 24.0.50; GDB backtrace from abort

From: martin rudalics <[email-masked]>
Date: Wed, 12 Jan 2011 08:54:17 +0100

>>  2) Change the code of Fset_window_configuration and Fselect_window,
 >>     to have some other way of preventing the latter from storing point
 >>     in the old selected window, without setting selected_window to
 >>     nil.
 >
 > That sounds like a better solution.  E.g. move the code of
 > Fselect_window to another function, add a third argument to it
 > specifying whether to swap-out point in selected_window, and make
 > Fset_window_configuration call that new internal function.

The

       /* Store the current buffer's actual point into the
	 old selected window.  It belongs to that window,
	 and when the window is not selected, must be in the window.  */
       if (!NILP (selected_window))
	{
	  ow = XWINDOW (selected_window);
	  if (! NILP (ow->buffer))
	    ...

part of Fselect_window should be executed _before_ the

       sf = SELECTED_FRAME ();
       if (XFRAME (WINDOW_FRAME (w)) != sf)
	{
	  ...

part, so the selected window would have been already set.  Unfortunately
this would make not_selected_before false when Fselect_window is called
back by Fselect_frame and the remaining parts of Fselect_window starting
with

   Fset_buffer (w->buffer);

   if (NILP (norecord))
   ...

would not get executed in that case.  Probably, there should be a common
subroutine of Fselect_window and Fselect_frame such that the two won't
have to call each other mutually.  (That common subroutine would have to
be robust in the sense that it can't call back neither Fselect_frame nor
Fselect_window.)

 > But maybe Fselect_frame should simply not be run in this case.

If I understand Eli's backtrace correctly, the problem was caused within
the following part of Fset_window_configuration

       selected_window = Qnil;

       /* Arrange *not* to restore point in the buffer that was
	 current when the window configuration was saved.  */
       if (EQ (XWINDOW (data->current_window)->buffer, new_current_buffer))
	set_marker_restricted (XWINDOW (data->current_window)->pointm,
			       make_number (old_point),
			       XWINDOW (data->current_window)->buffer);

       Fselect_window (data->current_window, Qnil);

so apparently the frame of data->current_window is _not_ the selected
frame.  Would you select the window and keep the old frame selected?

martin