From: Yuan Fu <casouri@gmail.com>
To: martin rudalics <rudalics@gmx.at>
Cc: 40268@debbugs.gnu.org
Subject: bug#40268: 27.0.60; [PATCH] Unify and improve gdb-mi source window display
Date: Sun, 29 Mar 2020 13:27:12 -0400 [thread overview]
Message-ID: <FC089A49-C41F-44F2-9C08-B1EB021CE355@gmail.com> (raw)
In-Reply-To: <e74303fd-3ad3-e942-9860-e53225567d59@gmx.at>
[-- Attachment #1: Type: text/plain, Size: 690 bytes --]
> On Mar 29, 2020, at 5:01 AM, martin rudalics <rudalics@gmx.at> wrote:
>
> > From a user’s perspective, this change solves two problems: 1. The
> > behavior difference between jumping to break point and stepping (and
> > other command) 2. Gdb-mi opening more windows than I wanted for
> > displaying source files.
>
> The patch doesn't apply here. Searching for
>
> :group 'gdb
> :version "22.1")
>
> (defvar gdbmi-debug-mode nil
> "When non-nil, print the messages sent/received from GDB/MI in *Messages*.")
>
>
> fails.
>
> Thanks, martin
>
Ah, I see. I should have generate this patch against the latest history. This one should be ok.
Yuan
[-- Attachment #2: source-window.patch --]
[-- Type: application/octet-stream, Size: 9332 bytes --]
From 8fb48ccf1b2f3e03e782c6aed7273ede843bb9d1 Mon Sep 17 00:00:00 2001
From: Yuan Fu <casouri@gmail.com>
Date: Sun, 29 Mar 2020 10:20:53 -0400
Subject: [PATCH] Unify and improve gdb-mi source buffer display logic
Unify the behavior of source buffer display for gdb-mi. Before this
change, stepping and other gdb command handlers use 'gud-display-line'
and 'gdb-goto-breakpoint' uses 'gdb-display-source-buffer'. Now whenever
gdb-mi code tries to open a source buffer, 'gdb-display-source-buffer'
is used. Also, we simply the logic in 'gdb-display-source-buffer' and
add a feature to limit the maximum number of source windows.
* lisp/progmodes/gdb-mi.el (gdb-source-window): Remove variable,
change to 'gdb-source-window-list'.
(gdb-source-window-list): New variable.
(gdb-display-source-buffer-action,
gdb-max-source-window-count): New custom variable.
(gdb-init-1, gdb-setup-windows, gdb-save-window-configuration,
gdb-load-window-configuration, gdb-restore-windows): Use
'gdb-source-window' rather than 'gdb-source-window-list'.
(gdb-display-source-buffer): Use new logic.
(gdb-goto-breakpoint): Remove 'display-buffer'
and don't set 'gdb-source-buffer' anymore.
* lisp/progmodes/gud.el (gud-display-line): If used by gdb-mi, use
'gdb-display-source-buffer' rather than 'display-buffer'. Don't set
'gdb-source-buffer' anymore.
---
lisp/progmodes/gdb-mi.el | 73 +++++++++++++++++++++++++++++-----------
lisp/progmodes/gud.el | 12 +++----
2 files changed, 59 insertions(+), 26 deletions(-)
diff --git a/lisp/progmodes/gdb-mi.el b/lisp/progmodes/gdb-mi.el
index 7fb3687391..93012ad18d 100644
--- a/lisp/progmodes/gdb-mi.el
+++ b/lisp/progmodes/gdb-mi.el
@@ -224,7 +224,9 @@ gdb-handler-list
(defvar gdb-source-file-list nil
"List of source files for the current executable.")
(defvar gdb-first-done-or-error t)
-(defvar gdb-source-window nil)
+(defvar gdb-source-window-list nil
+ "List of windows used for displaying source files.
+Sorted in most recently visited first order.")
(defvar gdb-inferior-status nil)
(defvar gdb-continuation nil)
(defvar gdb-supports-non-stop nil)
@@ -645,6 +647,21 @@ gdb-default-window-configuration-file
:group 'gdb
:version "28.1")
+(defcustom gdb-display-source-buffer-action '(nil . ((inhibit-same-window . t)))
+ "`display-buffer' action used when GDB displaying a source buffer."
+ :type 'list
+ :group 'gdb
+ :version "28.1")
+
+(defcustom gdb-max-source-window-count 1
+ "Maximum number of source windows to use.
+Until there are such number of source windows on screen, GDB
+tries to open a new window when visiting a new source file; after
+that GDB starts to reuse existing source windows."
+ :type 'number
+ :group 'gdb
+ :version "28.1")
+
(defvar gdbmi-debug-mode nil
"When non-nil, print the messages sent/received from GDB/MI in *Messages*.")
@@ -984,7 +1001,7 @@ gdb-init-1
gdb-first-done-or-error t
gdb-buffer-fringe-width (car (window-fringes))
gdb-debug-log nil
- gdb-source-window nil
+ gdb-source-window-list nil
gdb-inferior-status nil
gdb-continuation nil
gdb-buf-publisher '()
@@ -2069,17 +2086,35 @@ gdb-show-stop-p
;; GDB frame (after up, down etc). If no GDB frame is visible but the last
;; visited breakpoint is, use that window.
(defun gdb-display-source-buffer (buffer)
- (let* ((last-window (if gud-last-last-frame
- (get-buffer-window
- (gud-find-file (car gud-last-last-frame)))))
- (source-window (or last-window
- (if (and gdb-source-window
- (window-live-p gdb-source-window))
- gdb-source-window))))
- (when source-window
- (setq gdb-source-window source-window)
- (set-window-buffer source-window buffer))
- source-window))
+ "Find a window to display BUFFER.
+Always find a window to display buffer, and return it."
+ ;; This function doesn't take care of setting up source window(s) at startup,
+ ;; that's handled by `gdb-setup-windows' (if `gdb-many-windows' is non-nil).
+ ;; If `buffer' is already shown in a window, use that window.
+ (or (get-buffer-window buffer)
+ (progn
+ ;; First, update the window list.
+ (setq gdb-source-window-list
+ (cl-remove-duplicates
+ (cl-remove-if-not (lambda (win) (and (window-live-p win)
+ (equal (window-frame win)
+ (selected-frame))))
+ gdb-source-window-list)
+ :test #'equal))
+ ;; Should we create a new window or reuse one?
+ (if (> gdb-max-source-window-count
+ (length gdb-source-window-list))
+ ;; Create a new window, push it to window list and return it.
+ (car (push (display-buffer buffer gdb-display-source-buffer-action)
+ gdb-source-window-list))
+ ;; Reuse a window, we use the oldest window and put that to
+ ;; the front of the window list.
+ (let ((last-win (car (last gdb-source-window-list)))
+ (rest (butlast gdb-source-window-list)))
+ (set-window-buffer last-win buffer)
+ (setq gdb-source-window-list
+ (cons last-win rest))
+ last-win)))))
(defun gdbmi-start-with (str offset match)
@@ -4064,9 +4099,7 @@ gdb-goto-breakpoint
(let* ((buffer (find-file-noselect
(if (file-exists-p file) file
(cdr (assoc bptno gdb-location-alist)))))
- (window (or (gdb-display-source-buffer buffer)
- (display-buffer buffer))))
- (setq gdb-source-window window)
+ (window (gdb-display-source-buffer buffer)))
(with-current-buffer buffer
(goto-char (point-min))
(forward-line (1- (string-to-number line)))
@@ -4715,7 +4748,7 @@ gdb-setup-windows
(select-window win2)
(set-window-buffer win2 (or (gdb-get-source-buffer)
(list-buffers-noselect)))
- (setq gdb-source-window (selected-window))
+ (setq gdb-source-window-list (list (selected-window)))
(let ((win4 (split-window-right)))
(gdb-set-window-buffer
(gdb-get-buffer-create 'gdb-inferior-io) nil win4))
@@ -4791,7 +4824,7 @@ gdb-save-window-configuration
(error "Unrecognized gdb buffer mode: %s" major-mode)))
;; Command buffer.
((derived-mode-p 'gud-mode) 'command)
- ((equal (selected-window) gdb-source-window) 'source)))
+ ((member (selected-window) gdb-source-window-list) 'source)))
(with-window-non-dedicated nil
(set-window-buffer nil placeholder)
(set-window-prev-buffers (selected-window) nil)
@@ -4834,7 +4867,7 @@ gdb-load-window-configuration
(pcase buffer-type
('source (when source-buffer
(set-window-buffer nil source-buffer)
- (setq gdb-source-window (selected-window))))
+ (push (selected-window) gdb-source-window-list)))
('command (switch-to-buffer gud-comint-buffer))
(_ (let ((buffer (gdb-get-buffer-create buffer-type)))
(with-window-non-dedicated nil
@@ -4875,7 +4908,7 @@ gdb-restore-windows
(if gud-last-last-frame
(gud-find-file (car gud-last-last-frame))
(gud-find-file gdb-main-file)))
- (setq gdb-source-window win)))))
+ (setq gdb-source-window-list (list win))))))
;; Called from `gud-sentinel' in gud.el:
(defun gdb-reset ()
diff --git a/lisp/progmodes/gud.el b/lisp/progmodes/gud.el
index 567f452b93..c9522bfe17 100644
--- a/lisp/progmodes/gud.el
+++ b/lisp/progmodes/gud.el
@@ -2826,9 +2826,11 @@ gud-display-line
(buffer
(with-current-buffer gud-comint-buffer
(gud-find-file true-file)))
- (window (and buffer
- (or (get-buffer-window buffer)
- (display-buffer buffer '(nil (inhibit-same-window . t))))))
+ (window (when buffer (if (eq gud-minor-mode 'gdbmi)
+ (gdb-display-source-buffer buffer)
+ ;; Gud still has the old behavior.
+ (or (get-buffer-window buffer)
+ (display-buffer buffer '(nil (inhibit-same-window . t)))))))
(pos))
(when buffer
(with-current-buffer buffer
@@ -2858,9 +2860,7 @@ gud-display-line
(widen)
(goto-char pos))))
(when window
- (set-window-point window gud-overlay-arrow-position)
- (if (eq gud-minor-mode 'gdbmi)
- (setq gdb-source-window window))))))
+ (set-window-point window gud-overlay-arrow-position)))))
;; The gud-call function must do the right thing whether its invoking
;; keystroke is from the GUD buffer itself (via major-mode binding)
--
2.25.1
next prev parent reply other threads:[~2020-03-29 17:27 UTC|newest]
Thread overview: 8+ messages / expand[flat|nested] mbox.gz Atom feed top
[not found] <310914cd-1822-3fe9-19ae-6e47f8e72072@gmx.at>
2020-03-28 4:03 ` bug#40268: 27.0.60; [PATCH] Unify and improve gdb-mi source window display Yuan Fu
2020-03-29 9:01 ` martin rudalics
2020-03-29 17:27 ` Yuan Fu [this message]
2020-03-31 9:15 ` martin rudalics
2020-04-04 20:29 ` Yuan Fu
2020-04-06 9:04 ` martin rudalics
2020-04-06 14:21 ` Yuan Fu
2020-04-14 1:09 ` bug#40268: Fwd: " Yuan Fu
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=FC089A49-C41F-44F2-9C08-B1EB021CE355@gmail.com \
--to=casouri@gmail.com \
--cc=40268@debbugs.gnu.org \
--cc=rudalics@gmx.at \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
Code repositories for project(s) associated with this external index
https://git.savannah.gnu.org/cgit/emacs.git
https://git.savannah.gnu.org/cgit/emacs/org-mode.git
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.