From mboxrd@z Thu Jan 1 00:00:00 1970 Path: news.gmane.io!.POSTED.blaine.gmane.org!not-for-mail From: Alan Mackenzie Newsgroups: gmane.emacs.bugs Subject: bug#64152: 29.0.92; 'redirect-frame-focus' is broken Date: Tue, 20 Jun 2023 16:48:29 +0000 Message-ID: References: <2b6a6e28-ad0f-0842-fae0-e869e57ac807@gmx.at> <83pm5s94ej.fsf@gnu.org> <02c0ca92732d5c781368@heytings.org> <83sfan74fk.fsf@gnu.org> Mime-Version: 1.0 Content-Type: text/plain; charset=us-ascii Injection-Info: ciao.gmane.io; posting-host="blaine.gmane.org:116.202.254.214"; logging-data="5842"; mail-complaints-to="usenet@ciao.gmane.io" Cc: 64152@debbugs.gnu.org, Gregory Heytings , acm@muc.de To: Eli Zaretskii , Martin Rudalics Original-X-From: bug-gnu-emacs-bounces+geb-bug-gnu-emacs=m.gmane-mx.org@gnu.org Tue Jun 20 18:49:27 2023 Return-path: Envelope-to: geb-bug-gnu-emacs@m.gmane-mx.org Original-Received: from lists.gnu.org ([209.51.188.17]) by ciao.gmane.io with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.92) (envelope-from ) id 1qBeXn-0001HU-GQ for geb-bug-gnu-emacs@m.gmane-mx.org; Tue, 20 Jun 2023 18:49:27 +0200 Original-Received: from localhost ([::1] helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1qBeXR-00019y-3N; Tue, 20 Jun 2023 12:49:05 -0400 Original-Received: from eggs.gnu.org ([2001:470:142:3::10]) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1qBeXP-00018S-7f for bug-gnu-emacs@gnu.org; Tue, 20 Jun 2023 12:49:03 -0400 Original-Received: from debbugs.gnu.org ([209.51.188.43]) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_128_GCM_SHA256:128) (Exim 4.90_1) (envelope-from ) id 1qBeXO-0004Pp-VU for bug-gnu-emacs@gnu.org; Tue, 20 Jun 2023 12:49:02 -0400 Original-Received: from Debian-debbugs by debbugs.gnu.org with local (Exim 4.84_2) (envelope-from ) id 1qBeXO-0002CI-HN for bug-gnu-emacs@gnu.org; Tue, 20 Jun 2023 12:49:02 -0400 X-Loop: help-debbugs@gnu.org Resent-From: Alan Mackenzie Original-Sender: "Debbugs-submit" Resent-CC: bug-gnu-emacs@gnu.org Resent-Date: Tue, 20 Jun 2023 16:49:02 +0000 Resent-Message-ID: Resent-Sender: help-debbugs@gnu.org X-GNU-PR-Message: followup 64152 X-GNU-PR-Package: emacs Original-Received: via spool by 64152-submit@debbugs.gnu.org id=B64152.16872797198415 (code B ref 64152); Tue, 20 Jun 2023 16:49:02 +0000 Original-Received: (at 64152) by debbugs.gnu.org; 20 Jun 2023 16:48:39 +0000 Original-Received: from localhost ([127.0.0.1]:59672 helo=debbugs.gnu.org) by debbugs.gnu.org with esmtp (Exim 4.84_2) (envelope-from ) id 1qBeX0-0002Be-Pg for submit@debbugs.gnu.org; Tue, 20 Jun 2023 12:48:39 -0400 Original-Received: from mx3.muc.de ([193.149.48.5]:39633) by debbugs.gnu.org with esmtp (Exim 4.84_2) (envelope-from ) id 1qBeWy-0002BP-2K for 64152@debbugs.gnu.org; Tue, 20 Jun 2023 12:48:37 -0400 Original-Received: (qmail 2305 invoked by uid 3782); 20 Jun 2023 18:48:29 +0200 Original-Received: from acm.muc.de (pd953af84.dip0.t-ipconnect.de [217.83.175.132]) (using STARTTLS) by colin.muc.de (tmda-ofmipd) with ESMTP; Tue, 20 Jun 2023 18:48:29 +0200 Original-Received: (qmail 24202 invoked by uid 1000); 20 Jun 2023 16:48:29 -0000 Content-Disposition: inline In-Reply-To: <83sfan74fk.fsf@gnu.org> X-Submission-Agent: TMDA/1.3.x (Ph3nix) X-Primary-Address: acm@muc.de X-BeenThere: debbugs-submit@debbugs.gnu.org X-Mailman-Version: 2.1.18 Precedence: list X-BeenThere: bug-gnu-emacs@gnu.org List-Id: "Bug reports for GNU Emacs, the Swiss army knife of text editors" List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: bug-gnu-emacs-bounces+geb-bug-gnu-emacs=m.gmane-mx.org@gnu.org Original-Sender: bug-gnu-emacs-bounces+geb-bug-gnu-emacs=m.gmane-mx.org@gnu.org Xref: news.gmane.io gmane.emacs.bugs:263770 Archived-At: Hello, Eli and Martin. On Mon, Jun 19, 2023 at 20:22:23 +0300, Eli Zaretskii wrote: > > Date: Mon, 19 Jun 2023 14:26:22 +0000 > > From: Gregory Heytings > > cc: martin rudalics , 64152@debbugs.gnu.org > > >> That change has immediate consequences for interactions based on > > >> read_minibuf. With emacs -Q evaluate (make-frame '((minibuffer . > > >> nil))) and in the frame created thusly type C-x C-f. At this time it > > >> is impossible to access the minibuffer-less frame using C-x o, C-x 5 o, > > >> the window manager's Alt-TAB or any other key combination. All these > > >> key combinations used to work in the given configuration ever since. > > >> With a minibuffer-only frames setup, the minibuffer window has become > > >> "modal". > > > This works in Emacs 28, so the minibuffer-follows-selected-frame changes > > > aren't the culprit. Bisection will be appreciated. > > The culprit is 9cd72b02b6. > Thanks. > Alan, could you please look into fixing this? Perhaps the recipe > posted by Martin explains the rationale for having that "obscure, > obsolete code" you removed? > This is a regression in Emacs 29, so we should try fixing it on the > emacs-29 branch. The following patch partially reverts: commit 9cd72b02b67e92e89b83791b66fe40c4b50d8357 Author: Alan Mackenzie Date: Thu Jul 7 15:38:09 2022 +0000 Remove obscure, obsolete code from do_switch_frame (it doesn't restore an "#if 0 .... #else" and its "#endif"). It also reverts: commit 0508d7c4d6637d63a823b66e9f87ab54c2e73b09 Author: Alan Mackenzie Date: Fri Jul 8 20:19:03 2022 +0000 Remove now unused parameter TRACK from do_switch_frame. .. An extra argument (for this TRACK) had to be added into x_try_restore_frame in xterm.c. I'm not sure, at the moment, whether this patch unfixes any other bugs. It runs through make check without problems. Martin, would you please try out this patch. Just as a matter of interest, bug #56305 (29.0.50; 'yes-or-no-p' deselects minibuffer frame) is still open. diff --git a/src/frame.c b/src/frame.c index 38a6583605c..fc6a3459482 100644 --- a/src/frame.c +++ b/src/frame.c @@ -1444,6 +1444,10 @@ DEFUN ("make-terminal-frame", Fmake_terminal_frame, Smake_terminal_frame, If FRAME is a switch-frame event `(switch-frame FRAME1)', use FRAME1 as frame. + If TRACK is non-zero and the frame that currently has the focus + redirects its focus to the selected frame, redirect that focused + frame's focus to FRAME instead. + FOR_DELETION non-zero means that the selected frame is being deleted, which includes the possibility that the frame's terminal is dead. @@ -1451,7 +1455,7 @@ DEFUN ("make-terminal-frame", Fmake_terminal_frame, Smake_terminal_frame, The value of NORECORD is passed as argument to Fselect_window. */ Lisp_Object -do_switch_frame (Lisp_Object frame, int for_deletion, Lisp_Object norecord) +do_switch_frame (Lisp_Object frame, int track, int for_deletion, Lisp_Object norecord) { struct frame *sf = SELECTED_FRAME (), *f; @@ -1473,6 +1477,44 @@ do_switch_frame (Lisp_Object frame, int for_deletion, Lisp_Object norecord) else if (f == sf) return frame; + /* If the frame with GUI focus has had it's Emacs focus redirected + toward the currently selected frame, we should change the + redirection to point to the newly selected frame. This means + that if the focus is redirected from a minibufferless frame to a + surrogate minibuffer frame, we can use `other-window' to switch + between all the frames using that minibuffer frame, and the focus + redirection will follow us around. This code is necessary when + we have a minibufferless frame using the MB in another (normal) + frame (bug#64152) (ACM, 2023-06-20). */ +#ifdef HAVE_WINDOW_SYSTEM + if (track && FRAME_WINDOW_P (f) && FRAME_TERMINAL (f)->get_focus_frame) + { + Lisp_Object gfocus; /* The frame which still has focus on the + current terminal, according to the GUI + system. */ + Lisp_Object focus; /* The frame to which Emacs has redirected + the focus from `gfocus'. This might be a + frame with a minibuffer when `gfocus' + doesn't have a MB. */ + + gfocus = FRAME_TERMINAL (f)->get_focus_frame (f); + if (FRAMEP (gfocus)) + { + focus = FRAME_FOCUS_FRAME (XFRAME (gfocus)); + if (FRAMEP (focus) && XFRAME (focus) == SELECTED_FRAME ()) + /* Redirect frame focus also when FRAME has its minibuffer + window on the selected frame (see Bug#24500). + + Don't do that: It causes redirection problem with a + separate minibuffer frame (Bug#24803) and problems + when updating the cursor on such frames. + || (NILP (focus) + && EQ (FRAME_MINIBUF_WINDOW (f), sf->selected_window))) */ + Fredirect_frame_focus (gfocus, frame); + } + } +#endif /* HAVE_X_WINDOWS */ + if (!for_deletion && FRAME_HAS_MINIBUF_P (sf)) resize_mini_window (XWINDOW (FRAME_MINIBUF_WINDOW (sf)), 1); @@ -1574,7 +1616,7 @@ DEFUN ("select-frame", Fselect_frame, Sselect_frame, 1, 2, "e", /* Do not select a tooltip frame (Bug#47207). */ error ("Cannot select a tooltip frame"); else - return do_switch_frame (frame, 0, norecord); + return do_switch_frame (frame, 1, 0, norecord); } DEFUN ("handle-switch-frame", Fhandle_switch_frame, @@ -1590,7 +1632,7 @@ DEFUN ("handle-switch-frame", Fhandle_switch_frame, kset_prefix_arg (current_kboard, Vcurrent_prefix_arg); run_hook (Qmouse_leave_buffer_hook); - return do_switch_frame (event, 0, Qnil); + return do_switch_frame (event, 0, 0, Qnil); } DEFUN ("selected-frame", Fselected_frame, Sselected_frame, 0, 0, 0, @@ -2108,7 +2150,7 @@ delete_frame (Lisp_Object frame, Lisp_Object force) Fraise_frame (frame1); #endif - do_switch_frame (frame1, 1, Qnil); + do_switch_frame (frame1, 0, 1, Qnil); sf = SELECTED_FRAME (); } else diff --git a/src/keyboard.c b/src/keyboard.c index b1ccf4acde4..99f886821e2 100644 --- a/src/keyboard.c +++ b/src/keyboard.c @@ -11561,7 +11561,7 @@ quit_throw_to_read_char (bool from_signal) if (FRAMEP (internal_last_event_frame) && !EQ (internal_last_event_frame, selected_frame)) do_switch_frame (make_lispy_switch_frame (internal_last_event_frame), - 0, Qnil); + 0, 0, Qnil); sys_longjmp (getcjmp, 1); } diff --git a/src/lisp.h b/src/lisp.h index 9c02d975a74..bf91a1559bf 100644 --- a/src/lisp.h +++ b/src/lisp.h @@ -4878,7 +4878,7 @@ fast_c_string_match_ignore_case (Lisp_Object regexp, /* Defined in frame.c. */ extern void store_frame_param (struct frame *, Lisp_Object, Lisp_Object); extern void store_in_alist (Lisp_Object *, Lisp_Object, Lisp_Object); -extern Lisp_Object do_switch_frame (Lisp_Object, int, Lisp_Object); +extern Lisp_Object do_switch_frame (Lisp_Object, int, int, Lisp_Object); extern Lisp_Object get_frame_param (struct frame *, Lisp_Object); extern void frames_discard_buffer (Lisp_Object); extern void init_frame_once (void); diff --git a/src/minibuf.c b/src/minibuf.c index bcb7eb9375d..6e54d8c3ba5 100644 --- a/src/minibuf.c +++ b/src/minibuf.c @@ -1125,8 +1125,8 @@ read_minibuf_unwind (void) found: if (!EQ (exp_MB_frame, saved_selected_frame) && !NILP (exp_MB_frame)) - do_switch_frame (exp_MB_frame, 0, Qt); /* This also sets - minibuf_window */ + do_switch_frame (exp_MB_frame, 0, 0, Qt); /* This also sets + minibuf_window */ /* To keep things predictable, in case it matters, let's be in the minibuffer when we reset the relevant variables. Don't depend on @@ -1238,7 +1238,7 @@ read_minibuf_unwind (void) /* Restore the selected frame. */ if (!EQ (exp_MB_frame, saved_selected_frame) && !NILP (exp_MB_frame)) - do_switch_frame (saved_selected_frame, 0, Qt); + do_switch_frame (saved_selected_frame, 0, 0, Qt); } /* Replace the expired minibuffer in frame exp_MB_frame with the next less diff --git a/src/window.c b/src/window.c index 0efd6813f8d..1dc977626b3 100644 --- a/src/window.c +++ b/src/window.c @@ -7399,7 +7399,7 @@ DEFUN ("set-window-configuration", Fset_window_configuration, do_switch_frame (NILP (dont_set_frame) ? data->selected_frame : old_frame - , 0, Qnil); + , 0, 0, Qnil); } FRAME_WINDOW_CHANGE (f) = true; diff --git a/src/xterm.c b/src/xterm.c index e981a36fa9c..5840b15bcb7 100644 --- a/src/xterm.c +++ b/src/xterm.c @@ -25792,7 +25792,7 @@ x_try_restore_frame (void) FOR_EACH_FRAME (tail, frame) { - if (!NILP (do_switch_frame (frame, 1, Qnil))) + if (!NILP (do_switch_frame (frame, 0, 1, Qnil))) return; } } -- Alan Mackenzie (Nuremberg, Germany).