1 /* TUI window generic functions.
3 Copyright 1998, 1999, 2000, 2001, 2002 Free Software Foundation,
6 Contributed by Hewlett-Packard Company.
8 This file is part of GDB.
10 This program is free software; you can redistribute it and/or modify
11 it under the terms of the GNU General Public License as published by
12 the Free Software Foundation; either version 2 of the License, or
13 (at your option) any later version.
15 This program is distributed in the hope that it will be useful,
16 but WITHOUT ANY WARRANTY; without even the implied warranty of
17 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 GNU General Public License for more details.
20 You should have received a copy of the GNU General Public License
21 along with this program; if not, write to the Free Software
22 Foundation, Inc., 59 Temple Place - Suite 330,
23 Boston, MA 02111-1307, USA. */
25 /* This module contains procedures for handling tui window functions
26 like resize, scrolling, scrolling, changing focus, etc.
28 Author: Susan B. Macchia */
30 /* FIXME: cagney/2002-02-28: The GDB coding standard indicates that
31 "defs.h" should be included first. Unfortunatly some systems
32 (currently Debian GNU/Linux) include the <stdbool.h> via <curses.h>
33 and they clash with "bfd.h"'s definiton of true/false. The correct
34 fix is to remove true/false from "bfd.h", however, until that
35 happens, hack around it by including "config.h" and <curses.h>
52 #include "breakpoint.h"
54 #include "cli/cli-cmds.h"
58 #include "tuiGeneralWin.h"
61 #include "tuiDisassem.h"
62 #include "tuiSource.h"
63 #include "tuiSourceWin.h"
64 #include "tuiDataWin.h"
66 /*******************************
67 ** External Declarations
68 ********************************/
69 extern void init_page_info ();
71 /*******************************
73 ********************************/
74 static void _makeVisibleWithNewHeight (TuiWinInfoPtr
);
75 static void _makeInvisibleAndSetNewHeight (TuiWinInfoPtr
, int);
76 static TuiStatus
_tuiAdjustWinHeights (TuiWinInfoPtr
, int);
77 static int _newHeightOk (TuiWinInfoPtr
, int);
78 static void _tuiSetTabWidth_command (char *, int);
79 static void _tuiRefreshAll_command (char *, int);
80 static void _tuiSetWinHeight_command (char *, int);
81 static void _tuiXDBsetWinHeight_command (char *, int);
82 static void _tuiAllWindowsInfo (char *, int);
83 static void _tuiSetFocus_command (char *, int);
84 static void _tuiScrollForward_command (char *, int);
85 static void _tuiScrollBackward_command (char *, int);
86 static void _tuiScrollLeft_command (char *, int);
87 static void _tuiScrollRight_command (char *, int);
88 static void _parseScrollingArgs (char *, TuiWinInfoPtr
*, int *);
91 /***************************************
93 ***************************************/
94 #define WIN_HEIGHT_USAGE "Usage: winheight <win_name> [+ | -] <#lines>\n"
95 #define XDBWIN_HEIGHT_USAGE "Usage: w <#lines>\n"
96 #define FOCUS_USAGE "Usage: focus {<win> | next | prev}\n"
98 /***************************************
100 ***************************************/
102 /* Possible values for tui-border-kind variable. */
103 static const char *tui_border_kind_enums
[] = {
110 /* Possible values for tui-border-mode and tui-active-border-mode. */
111 static const char *tui_border_mode_enums
[] = {
128 /* Translation table for border-mode variables.
129 The list of values must be terminated by a NULL.
130 After the NULL value, an entry defines the default. */
131 struct tui_translate tui_border_mode_translate
[] = {
132 { "normal", A_NORMAL
},
133 { "standout", A_STANDOUT
},
134 { "reverse", A_REVERSE
},
136 { "half-standout", A_DIM
| A_STANDOUT
},
138 { "bold-standout", A_BOLD
| A_STANDOUT
},
140 { "normal", A_NORMAL
}
143 /* Translation tables for border-kind, one for each border
144 character (see wborder, border curses operations).
145 -1 is used to indicate the ACS because ACS characters
146 are determined at run time by curses (depends on terminal). */
147 struct tui_translate tui_border_kind_translate_vline
[] = {
155 struct tui_translate tui_border_kind_translate_hline
[] = {
163 struct tui_translate tui_border_kind_translate_ulcorner
[] = {
171 struct tui_translate tui_border_kind_translate_urcorner
[] = {
179 struct tui_translate tui_border_kind_translate_llcorner
[] = {
187 struct tui_translate tui_border_kind_translate_lrcorner
[] = {
196 /* Tui configuration variables controlled with set/show command. */
197 const char *tui_active_border_mode
= "bold-standout";
198 const char *tui_border_mode
= "normal";
199 const char *tui_border_kind
= "acs";
201 /* Tui internal configuration variables. These variables are
202 updated by tui_update_variables to reflect the tui configuration
204 chtype tui_border_vline
;
205 chtype tui_border_hline
;
206 chtype tui_border_ulcorner
;
207 chtype tui_border_urcorner
;
208 chtype tui_border_llcorner
;
209 chtype tui_border_lrcorner
;
211 int tui_border_attrs
;
212 int tui_active_border_attrs
;
214 /* Identify the item in the translation table.
215 When the item is not recognized, use the default entry. */
216 static struct tui_translate
*
217 translate (const char *name
, struct tui_translate
*table
)
221 if (name
&& strcmp (table
->name
, name
) == 0)
226 /* Not found, return default entry. */
231 /* Update the tui internal configuration according to gdb settings.
232 Returns 1 if the configuration has changed and the screen should
235 tui_update_variables ()
238 struct tui_translate
*entry
;
240 entry
= translate (tui_border_mode
, tui_border_mode_translate
);
241 if (tui_border_attrs
!= entry
->value
)
243 tui_border_attrs
= entry
->value
;
246 entry
= translate (tui_active_border_mode
, tui_border_mode_translate
);
247 if (tui_active_border_attrs
!= entry
->value
)
249 tui_active_border_attrs
= entry
->value
;
253 /* If one corner changes, all characters are changed.
254 Only check the first one. The ACS characters are determined at
255 run time by curses terminal management. */
256 entry
= translate (tui_border_kind
, tui_border_kind_translate_lrcorner
);
257 if (tui_border_lrcorner
!= (chtype
) entry
->value
)
259 tui_border_lrcorner
= (entry
->value
< 0) ? ACS_LRCORNER
: entry
->value
;
262 entry
= translate (tui_border_kind
, tui_border_kind_translate_llcorner
);
263 tui_border_llcorner
= (entry
->value
< 0) ? ACS_LLCORNER
: entry
->value
;
265 entry
= translate (tui_border_kind
, tui_border_kind_translate_ulcorner
);
266 tui_border_ulcorner
= (entry
->value
< 0) ? ACS_ULCORNER
: entry
->value
;
268 entry
= translate (tui_border_kind
, tui_border_kind_translate_urcorner
);
269 tui_border_urcorner
= (entry
->value
< 0) ? ACS_URCORNER
: entry
->value
;
271 entry
= translate (tui_border_kind
, tui_border_kind_translate_hline
);
272 tui_border_hline
= (entry
->value
< 0) ? ACS_HLINE
: entry
->value
;
274 entry
= translate (tui_border_kind
, tui_border_kind_translate_vline
);
275 tui_border_vline
= (entry
->value
< 0) ? ACS_VLINE
: entry
->value
;
281 set_tui_cmd (char *args
, int from_tty
)
286 show_tui_cmd (char *args
, int from_tty
)
291 ** _initialize_tuiWin().
292 ** Function to initialize gdb commands, for tui window manipulation.
295 _initialize_tuiWin (void)
297 struct cmd_list_element
*c
;
298 static struct cmd_list_element
*tui_setlist
;
299 static struct cmd_list_element
*tui_showlist
;
301 /* Define the classes of commands.
302 They will appear in the help list in the reverse of this order. */
303 add_cmd ("tui", class_tui
, NULL
,
304 "Text User Interface commands.",
307 add_prefix_cmd ("tui", class_tui
, set_tui_cmd
,
308 "TUI configuration variables",
309 &tui_setlist
, "set tui ",
310 0/*allow-unknown*/, &setlist
);
311 add_prefix_cmd ("tui", class_tui
, show_tui_cmd
,
312 "TUI configuration variables",
313 &tui_showlist
, "show tui ",
314 0/*allow-unknown*/, &showlist
);
316 add_com ("refresh", class_tui
, _tuiRefreshAll_command
,
317 "Refresh the terminal display.\n");
319 add_com_alias ("U", "refresh", class_tui
, 0);
320 add_com ("tabset", class_tui
, _tuiSetTabWidth_command
,
321 "Set the width (in characters) of tab stops.\n\
322 Usage: tabset <n>\n");
323 add_com ("winheight", class_tui
, _tuiSetWinHeight_command
,
324 "Set the height of a specified window.\n\
325 Usage: winheight <win_name> [+ | -] <#lines>\n\
327 src : the source window\n\
328 cmd : the command window\n\
329 asm : the disassembly window\n\
330 regs : the register display\n");
331 add_com_alias ("wh", "winheight", class_tui
, 0);
332 add_info ("win", _tuiAllWindowsInfo
,
333 "List of all displayed windows.\n");
334 add_com ("focus", class_tui
, _tuiSetFocus_command
,
335 "Set focus to named window or next/prev window.\n\
336 Usage: focus {<win> | next | prev}\n\
337 Valid Window names are:\n\
338 src : the source window\n\
339 asm : the disassembly window\n\
340 regs : the register display\n\
341 cmd : the command window\n");
342 add_com_alias ("fs", "focus", class_tui
, 0);
343 add_com ("+", class_tui
, _tuiScrollForward_command
,
344 "Scroll window forward.\nUsage: + [win] [n]\n");
345 add_com ("-", class_tui
, _tuiScrollBackward_command
,
346 "Scroll window backward.\nUsage: - [win] [n]\n");
347 add_com ("<", class_tui
, _tuiScrollLeft_command
,
348 "Scroll window forward.\nUsage: < [win] [n]\n");
349 add_com (">", class_tui
, _tuiScrollRight_command
,
350 "Scroll window backward.\nUsage: > [win] [n]\n");
352 add_com ("w", class_xdb
, _tuiXDBsetWinHeight_command
,
353 "XDB compatibility command for setting the height of a command window.\n\
354 Usage: w <#lines>\n");
356 /* Define the tui control variables. */
358 ("border-kind", no_class
,
359 tui_border_kind_enums
, &tui_border_kind
,
360 "Set the kind of border for TUI windows.\n"
361 "This variable controls the border of TUI windows:\n"
362 "space use a white space\n"
363 "ascii use ascii characters + - | for the border\n"
364 "acs use the Alternate Character Set\n",
366 add_show_from_set (c
, &tui_showlist
);
369 ("border-mode", no_class
,
370 tui_border_mode_enums
, &tui_border_mode
,
371 "Set the attribute mode to use for the TUI window borders.\n"
372 "This variable controls the attributes to use for the window borders:\n"
373 "normal normal display\n"
374 "standout use highlight mode of terminal\n"
375 "reverse use reverse video mode\n"
376 "half use half bright\n"
377 "half-standout use half bright and standout mode\n"
378 "bold use extra bright or bold\n"
379 "bold-standout use extra bright or bold with standout mode\n",
381 add_show_from_set (c
, &tui_showlist
);
384 ("active-border-mode", no_class
,
385 tui_border_mode_enums
, &tui_active_border_mode
,
386 "Set the attribute mode to use for the active TUI window border.\n"
387 "This variable controls the attributes to use for the active window border:\n"
388 "normal normal display\n"
389 "standout use highlight mode of terminal\n"
390 "reverse use reverse video mode\n"
391 "half use half bright\n"
392 "half-standout use half bright and standout mode\n"
393 "bold use extra bright or bold\n"
394 "bold-standout use extra bright or bold with standout mode\n",
396 add_show_from_set (c
, &tui_showlist
);
401 ** tuiClearWinFocusFrom
402 ** Clear the logical focus from winInfo
405 tuiClearWinFocusFrom (TuiWinInfoPtr winInfo
)
407 if (m_winPtrNotNull (winInfo
))
409 if (winInfo
->generic
.type
!= CMD_WIN
)
410 unhighlightWin (winInfo
);
411 tuiSetWinWithFocus ((TuiWinInfoPtr
) NULL
);
415 } /* tuiClearWinFocusFrom */
419 ** tuiClearWinFocus().
420 ** Clear the window that has focus.
423 tuiClearWinFocus (void)
425 tuiClearWinFocusFrom (tuiWinWithFocus ());
428 } /* tuiClearWinFocus */
433 ** Set the logical focus to winInfo
436 tuiSetWinFocusTo (TuiWinInfoPtr winInfo
)
438 if (m_winPtrNotNull (winInfo
))
440 TuiWinInfoPtr winWithFocus
= tuiWinWithFocus ();
442 if (m_winPtrNotNull (winWithFocus
) &&
443 winWithFocus
->generic
.type
!= CMD_WIN
)
444 unhighlightWin (winWithFocus
);
445 tuiSetWinWithFocus (winInfo
);
446 if (winInfo
->generic
.type
!= CMD_WIN
)
447 highlightWin (winInfo
);
451 } /* tuiSetWinFocusTo */
455 ** tuiScrollForward().
458 tuiScrollForward (TuiWinInfoPtr winToScroll
, int numToScroll
)
460 if (winToScroll
!= cmdWin
)
462 int _numToScroll
= numToScroll
;
464 if (numToScroll
== 0)
465 _numToScroll
= winToScroll
->generic
.height
- 3;
467 ** If we are scrolling the source or disassembly window, do a
468 ** "psuedo" scroll since not all of the source is in memory,
469 ** only what is in the viewport. If winToScroll is the
470 ** command window do nothing since the term should handle it.
472 if (winToScroll
== srcWin
)
473 tuiVerticalSourceScroll (FORWARD_SCROLL
, _numToScroll
);
474 else if (winToScroll
== disassemWin
)
475 tuiVerticalDisassemScroll (FORWARD_SCROLL
, _numToScroll
);
476 else if (winToScroll
== dataWin
)
477 tuiVerticalDataScroll (FORWARD_SCROLL
, _numToScroll
);
481 } /* tuiScrollForward */
485 ** tuiScrollBackward().
488 tuiScrollBackward (TuiWinInfoPtr winToScroll
, int numToScroll
)
490 if (winToScroll
!= cmdWin
)
492 int _numToScroll
= numToScroll
;
494 if (numToScroll
== 0)
495 _numToScroll
= winToScroll
->generic
.height
- 3;
497 ** If we are scrolling the source or disassembly window, do a
498 ** "psuedo" scroll since not all of the source is in memory,
499 ** only what is in the viewport. If winToScroll is the
500 ** command window do nothing since the term should handle it.
502 if (winToScroll
== srcWin
)
503 tuiVerticalSourceScroll (BACKWARD_SCROLL
, _numToScroll
);
504 else if (winToScroll
== disassemWin
)
505 tuiVerticalDisassemScroll (BACKWARD_SCROLL
, _numToScroll
);
506 else if (winToScroll
== dataWin
)
507 tuiVerticalDataScroll (BACKWARD_SCROLL
, _numToScroll
);
510 } /* tuiScrollBackward */
517 tuiScrollLeft (TuiWinInfoPtr winToScroll
, int numToScroll
)
519 if (winToScroll
!= cmdWin
)
521 int _numToScroll
= numToScroll
;
523 if (_numToScroll
== 0)
526 ** If we are scrolling the source or disassembly window, do a
527 ** "psuedo" scroll since not all of the source is in memory,
528 ** only what is in the viewport. If winToScroll is the
529 ** command window do nothing since the term should handle it.
531 if (winToScroll
== srcWin
|| winToScroll
== disassemWin
)
532 tuiHorizontalSourceScroll (winToScroll
, LEFT_SCROLL
, _numToScroll
);
535 } /* tuiScrollLeft */
542 tuiScrollRight (TuiWinInfoPtr winToScroll
, int numToScroll
)
544 if (winToScroll
!= cmdWin
)
546 int _numToScroll
= numToScroll
;
548 if (_numToScroll
== 0)
551 ** If we are scrolling the source or disassembly window, do a
552 ** "psuedo" scroll since not all of the source is in memory,
553 ** only what is in the viewport. If winToScroll is the
554 ** command window do nothing since the term should handle it.
556 if (winToScroll
== srcWin
|| winToScroll
== disassemWin
)
557 tuiHorizontalSourceScroll (winToScroll
, RIGHT_SCROLL
, _numToScroll
);
560 } /* tuiScrollRight */
565 ** Scroll a window. Arguments are passed through a va_list.
568 tui_scroll (TuiScrollDirection direction
,
569 TuiWinInfoPtr winToScroll
,
575 tuiScrollForward (winToScroll
, numToScroll
);
577 case BACKWARD_SCROLL
:
578 tuiScrollBackward (winToScroll
, numToScroll
);
581 tuiScrollLeft (winToScroll
, numToScroll
);
584 tuiScrollRight (winToScroll
, numToScroll
);
600 clearok (curscr
, TRUE
);
601 refreshAll (winList
);
602 for (type
= SRC_WIN
; type
< MAX_MAJOR_WINDOWS
; type
++)
604 if (winList
[type
] && winList
[type
]->generic
.isVisible
)
610 tuiClearWin (&winList
[type
]->generic
);
611 if (winList
[type
]->detail
.sourceInfo
.hasLocator
)
612 tuiClearLocatorDisplay ();
613 tuiShowSourceContent (winList
[type
]);
614 checkAndDisplayHighlightIfNeeded (winList
[type
]);
615 tuiEraseExecInfoContent (winList
[type
]);
616 tuiUpdateExecInfo (winList
[type
]);
619 tuiRefreshDataWin ();
626 tuiClearLocatorDisplay ();
627 tuiShowLocatorContent ();
630 } /* tuiRefreshAll */
635 ** Resize all the windows based on the the terminal size. This
636 ** function gets called from within the readline sinwinch handler.
641 int heightDiff
, widthDiff
;
642 extern int screenheight
, screenwidth
; /* in readline */
644 widthDiff
= screenwidth
- termWidth ();
645 heightDiff
= screenheight
- termHeight ();
646 if (heightDiff
|| widthDiff
)
648 TuiLayoutType curLayout
= currentLayout ();
649 TuiWinInfoPtr winWithFocus
= tuiWinWithFocus ();
650 TuiWinInfoPtr firstWin
, secondWin
;
651 TuiGenWinInfoPtr locator
= locatorWinInfoPtr ();
653 int i
, newHeight
, splitDiff
, cmdSplitDiff
, numWinsDisplayed
= 2;
655 /* turn keypad off while we resize */
656 if (winWithFocus
!= cmdWin
)
657 keypad (cmdWin
->generic
.handle
, FALSE
);
659 setTermHeightTo (screenheight
);
660 setTermWidthTo (screenwidth
);
661 if (curLayout
== SRC_DISASSEM_COMMAND
||
662 curLayout
== SRC_DATA_COMMAND
|| curLayout
== DISASSEM_DATA_COMMAND
)
664 splitDiff
= heightDiff
/ numWinsDisplayed
;
665 cmdSplitDiff
= splitDiff
;
666 if (heightDiff
% numWinsDisplayed
)
673 /* now adjust each window */
679 case DISASSEM_COMMAND
:
680 firstWin
= (TuiWinInfoPtr
) (sourceWindows ())->list
[0];
681 firstWin
->generic
.width
+= widthDiff
;
682 locator
->width
+= widthDiff
;
683 /* check for invalid heights */
685 newHeight
= firstWin
->generic
.height
;
686 else if ((firstWin
->generic
.height
+ splitDiff
) >=
687 (screenheight
- MIN_CMD_WIN_HEIGHT
- 1))
688 newHeight
= screenheight
- MIN_CMD_WIN_HEIGHT
- 1;
689 else if ((firstWin
->generic
.height
+ splitDiff
) <= 0)
690 newHeight
= MIN_WIN_HEIGHT
;
692 newHeight
= firstWin
->generic
.height
+ splitDiff
;
694 _makeInvisibleAndSetNewHeight (firstWin
, newHeight
);
695 cmdWin
->generic
.origin
.y
= locator
->origin
.y
+ 1;
696 cmdWin
->generic
.width
+= widthDiff
;
697 newHeight
= screenheight
- cmdWin
->generic
.origin
.y
;
698 _makeInvisibleAndSetNewHeight (cmdWin
, newHeight
);
699 _makeVisibleWithNewHeight (firstWin
);
700 _makeVisibleWithNewHeight (cmdWin
);
701 if (firstWin
->generic
.contentSize
<= 0)
702 tuiEraseSourceContent (firstWin
, EMPTY_SOURCE_PROMPT
);
705 if (curLayout
== SRC_DISASSEM_COMMAND
)
708 firstWin
->generic
.width
+= widthDiff
;
709 secondWin
= disassemWin
;
710 secondWin
->generic
.width
+= widthDiff
;
715 firstWin
->generic
.width
+= widthDiff
;
716 secondWin
= (TuiWinInfoPtr
) (sourceWindows ())->list
[0];
717 secondWin
->generic
.width
+= widthDiff
;
719 /* Change the first window's height/width */
720 /* check for invalid heights */
722 newHeight
= firstWin
->generic
.height
;
723 else if ((firstWin
->generic
.height
+
724 secondWin
->generic
.height
+ (splitDiff
* 2)) >=
725 (screenheight
- MIN_CMD_WIN_HEIGHT
- 1))
726 newHeight
= (screenheight
- MIN_CMD_WIN_HEIGHT
- 1) / 2;
727 else if ((firstWin
->generic
.height
+ splitDiff
) <= 0)
728 newHeight
= MIN_WIN_HEIGHT
;
730 newHeight
= firstWin
->generic
.height
+ splitDiff
;
731 _makeInvisibleAndSetNewHeight (firstWin
, newHeight
);
733 if (firstWin
== dataWin
&& widthDiff
!= 0)
734 firstWin
->detail
.dataDisplayInfo
.regsColumnCount
=
735 tuiCalculateRegsColumnCount (
736 firstWin
->detail
.dataDisplayInfo
.regsDisplayType
);
737 locator
->width
+= widthDiff
;
739 /* Change the second window's height/width */
740 /* check for invalid heights */
742 newHeight
= secondWin
->generic
.height
;
743 else if ((firstWin
->generic
.height
+
744 secondWin
->generic
.height
+ (splitDiff
* 2)) >=
745 (screenheight
- MIN_CMD_WIN_HEIGHT
- 1))
747 newHeight
= screenheight
- MIN_CMD_WIN_HEIGHT
- 1;
749 newHeight
= (newHeight
/ 2) + 1;
753 else if ((secondWin
->generic
.height
+ splitDiff
) <= 0)
754 newHeight
= MIN_WIN_HEIGHT
;
756 newHeight
= secondWin
->generic
.height
+ splitDiff
;
757 secondWin
->generic
.origin
.y
= firstWin
->generic
.height
- 1;
758 _makeInvisibleAndSetNewHeight (secondWin
, newHeight
);
760 /* Change the command window's height/width */
761 cmdWin
->generic
.origin
.y
= locator
->origin
.y
+ 1;
762 _makeInvisibleAndSetNewHeight (
763 cmdWin
, cmdWin
->generic
.height
+ cmdSplitDiff
);
764 _makeVisibleWithNewHeight (firstWin
);
765 _makeVisibleWithNewHeight (secondWin
);
766 _makeVisibleWithNewHeight (cmdWin
);
767 if (firstWin
->generic
.contentSize
<= 0)
768 tuiEraseSourceContent (firstWin
, EMPTY_SOURCE_PROMPT
);
769 if (secondWin
->generic
.contentSize
<= 0)
770 tuiEraseSourceContent (secondWin
, EMPTY_SOURCE_PROMPT
);
774 ** Now remove all invisible windows, and their content so that they get
775 ** created again when called for with the new size
777 for (winType
= SRC_WIN
; (winType
< MAX_MAJOR_WINDOWS
); winType
++)
779 if (winType
!= CMD_WIN
&& m_winPtrNotNull (winList
[winType
]) &&
780 !winList
[winType
]->generic
.isVisible
)
782 freeWindow (winList
[winType
]);
783 winList
[winType
] = (TuiWinInfoPtr
) NULL
;
786 tuiSetWinResizedTo (TRUE
);
787 /* turn keypad back on, unless focus is in the command window */
788 if (winWithFocus
!= cmdWin
)
789 keypad (cmdWin
->generic
.handle
, TRUE
);
796 ** tuiSigwinchHandler()
797 ** SIGWINCH signal handler for the tui. This signal handler is
798 ** always called, even when the readline package clears signals
799 ** because it is set as the old_sigwinch() (TUI only)
802 tuiSigwinchHandler (int signal
)
805 ** Say that a resize was done so that the readline can do it
806 ** later when appropriate.
808 tuiSetWinResizedTo (TRUE
);
811 } /* tuiSigwinchHandler */
815 /*************************
816 ** STATIC LOCAL FUNCTIONS
817 **************************/
821 ** _tuiScrollForward_command().
824 _tuiScrollForward_command (char *arg
, int fromTTY
)
827 TuiWinInfoPtr winToScroll
;
829 /* Make sure the curses mode is enabled. */
831 if (arg
== (char *) NULL
)
832 _parseScrollingArgs (arg
, &winToScroll
, (int *) NULL
);
834 _parseScrollingArgs (arg
, &winToScroll
, &numToScroll
);
835 tui_scroll (FORWARD_SCROLL
, winToScroll
, numToScroll
);
840 ** _tuiScrollBackward_command().
843 _tuiScrollBackward_command (char *arg
, int fromTTY
)
846 TuiWinInfoPtr winToScroll
;
848 /* Make sure the curses mode is enabled. */
850 if (arg
== (char *) NULL
)
851 _parseScrollingArgs (arg
, &winToScroll
, (int *) NULL
);
853 _parseScrollingArgs (arg
, &winToScroll
, &numToScroll
);
854 tui_scroll (BACKWARD_SCROLL
, winToScroll
, numToScroll
);
859 ** _tuiScrollLeft_command().
862 _tuiScrollLeft_command (char *arg
, int fromTTY
)
865 TuiWinInfoPtr winToScroll
;
867 /* Make sure the curses mode is enabled. */
869 _parseScrollingArgs (arg
, &winToScroll
, &numToScroll
);
870 tui_scroll (LEFT_SCROLL
, winToScroll
, numToScroll
);
875 ** _tuiScrollRight_command().
878 _tuiScrollRight_command (char *arg
, int fromTTY
)
881 TuiWinInfoPtr winToScroll
;
883 /* Make sure the curses mode is enabled. */
885 _parseScrollingArgs (arg
, &winToScroll
, &numToScroll
);
886 tui_scroll (RIGHT_SCROLL
, winToScroll
, numToScroll
);
892 ** Set focus to the window named by 'arg'
895 _tuiSetFocus (char *arg
, int fromTTY
)
897 if (arg
!= (char *) NULL
)
899 char *bufPtr
= (char *) xstrdup (arg
);
901 TuiWinInfoPtr winInfo
= (TuiWinInfoPtr
) NULL
;
903 for (i
= 0; (i
< strlen (bufPtr
)); i
++)
904 bufPtr
[i
] = toupper (arg
[i
]);
906 if (subset_compare (bufPtr
, "NEXT"))
907 winInfo
= tuiNextWin (tuiWinWithFocus ());
908 else if (subset_compare (bufPtr
, "PREV"))
909 winInfo
= tuiPrevWin (tuiWinWithFocus ());
911 winInfo
= partialWinByName (bufPtr
);
913 if (winInfo
== (TuiWinInfoPtr
) NULL
|| !winInfo
->generic
.isVisible
)
914 warning ("Invalid window specified. \n\
915 The window name specified must be valid and visible.\n");
918 tuiSetWinFocusTo (winInfo
);
919 keypad (cmdWin
->generic
.handle
, (winInfo
!= cmdWin
));
922 if (dataWin
&& dataWin
->generic
.isVisible
)
923 tuiRefreshDataWin ();
925 printf_filtered ("Focus set to %s window.\n",
926 winName ((TuiGenWinInfoPtr
) tuiWinWithFocus ()));
929 warning ("Incorrect Number of Arguments.\n%s", FOCUS_USAGE
);
935 ** _tuiSetFocus_command()
938 _tuiSetFocus_command (char *arg
, int fromTTY
)
940 /* Make sure the curses mode is enabled. */
942 _tuiSetFocus (arg
, fromTTY
);
947 ** _tuiAllWindowsInfo().
950 _tuiAllWindowsInfo (char *arg
, int fromTTY
)
953 TuiWinInfoPtr winWithFocus
= tuiWinWithFocus ();
955 for (type
= SRC_WIN
; (type
< MAX_MAJOR_WINDOWS
); type
++)
956 if (winList
[type
]->generic
.isVisible
)
958 if (winWithFocus
== winList
[type
])
959 printf_filtered (" %s\t(%d lines) <has focus>\n",
960 winName (&winList
[type
]->generic
),
961 winList
[type
]->generic
.height
);
963 printf_filtered (" %s\t(%d lines)\n",
964 winName (&winList
[type
]->generic
),
965 winList
[type
]->generic
.height
);
969 } /* _tuiAllWindowsInfo */
973 ** _tuiRefreshAll_command().
976 _tuiRefreshAll_command (char *arg
, int fromTTY
)
978 /* Make sure the curses mode is enabled. */
986 ** _tuiSetWinTabWidth_command().
987 ** Set the height of the specified window.
990 _tuiSetTabWidth_command (char *arg
, int fromTTY
)
992 /* Make sure the curses mode is enabled. */
994 if (arg
!= (char *) NULL
)
1000 tuiSetDefaultTabLen (ts
);
1002 warning ("Tab widths greater than 0 must be specified.\n");
1006 } /* _tuiSetTabWidth_command */
1010 ** _tuiSetWinHeight().
1011 ** Set the height of the specified window.
1014 _tuiSetWinHeight (char *arg
, int fromTTY
)
1016 /* Make sure the curses mode is enabled. */
1018 if (arg
!= (char *) NULL
)
1020 char *buf
= xstrdup (arg
);
1022 char *wname
= (char *) NULL
;
1024 TuiWinInfoPtr winInfo
;
1027 bufPtr
= strchr (bufPtr
, ' ');
1028 if (bufPtr
!= (char *) NULL
)
1033 ** Validate the window name
1035 for (i
= 0; i
< strlen (wname
); i
++)
1036 wname
[i
] = toupper (wname
[i
]);
1037 winInfo
= partialWinByName (wname
);
1039 if (winInfo
== (TuiWinInfoPtr
) NULL
|| !winInfo
->generic
.isVisible
)
1040 warning ("Invalid window specified. \n\
1041 The window name specified must be valid and visible.\n");
1044 /* Process the size */
1045 while (*(++bufPtr
) == ' ')
1048 if (*bufPtr
!= (char) 0)
1051 int fixedSize
= TRUE
;
1054 if (*bufPtr
== '+' || *bufPtr
== '-')
1061 inputNo
= atoi (bufPtr
);
1067 newHeight
= inputNo
;
1069 newHeight
= winInfo
->generic
.height
+ inputNo
;
1071 ** Now change the window's height, and adjust all
1072 ** other windows around it
1074 if (_tuiAdjustWinHeights (winInfo
,
1075 newHeight
) == TUI_FAILURE
)
1076 warning ("Invalid window height specified.\n%s",
1082 warning ("Invalid window height specified.\n%s",
1088 printf_filtered (WIN_HEIGHT_USAGE
);
1090 if (buf
!= (char *) NULL
)
1094 printf_filtered (WIN_HEIGHT_USAGE
);
1097 } /* _tuiSetWinHeight */
1100 ** _tuiSetWinHeight_command().
1101 ** Set the height of the specified window, with va_list.
1104 _tuiSetWinHeight_command (char *arg
, int fromTTY
)
1106 /* Make sure the curses mode is enabled. */
1108 _tuiSetWinHeight (arg
, fromTTY
);
1113 ** _tuiXDBsetWinHeight().
1114 ** XDB Compatibility command for setting the window height. This will
1115 ** increase or decrease the command window by the specified amount.
1118 _tuiXDBsetWinHeight (char *arg
, int fromTTY
)
1120 /* Make sure the curses mode is enabled. */
1122 if (arg
!= (char *) NULL
)
1124 int inputNo
= atoi (arg
);
1127 { /* Add 1 for the locator */
1128 int newHeight
= termHeight () - (inputNo
+ 1);
1130 if (!_newHeightOk (winList
[CMD_WIN
], newHeight
) ||
1131 _tuiAdjustWinHeights (winList
[CMD_WIN
],
1132 newHeight
) == TUI_FAILURE
)
1133 warning ("Invalid window height specified.\n%s",
1134 XDBWIN_HEIGHT_USAGE
);
1137 warning ("Invalid window height specified.\n%s",
1138 XDBWIN_HEIGHT_USAGE
);
1141 warning ("Invalid window height specified.\n%s", XDBWIN_HEIGHT_USAGE
);
1144 } /* _tuiXDBsetWinHeight */
1147 ** _tuiSetWinHeight_command().
1148 ** Set the height of the specified window, with va_list.
1151 _tuiXDBsetWinHeight_command (char *arg
, int fromTTY
)
1153 _tuiXDBsetWinHeight (arg
, fromTTY
);
1158 ** _tuiAdjustWinHeights().
1159 ** Function to adjust all window heights around the primary
1162 _tuiAdjustWinHeights (TuiWinInfoPtr primaryWinInfo
, int newHeight
)
1164 TuiStatus status
= TUI_FAILURE
;
1166 if (_newHeightOk (primaryWinInfo
, newHeight
))
1168 status
= TUI_SUCCESS
;
1169 if (newHeight
!= primaryWinInfo
->generic
.height
)
1172 TuiWinInfoPtr winInfo
;
1173 TuiGenWinInfoPtr locator
= locatorWinInfoPtr ();
1174 TuiLayoutType curLayout
= currentLayout ();
1176 diff
= (newHeight
- primaryWinInfo
->generic
.height
) * (-1);
1177 if (curLayout
== SRC_COMMAND
|| curLayout
== DISASSEM_COMMAND
)
1179 TuiWinInfoPtr srcWinInfo
;
1181 _makeInvisibleAndSetNewHeight (primaryWinInfo
, newHeight
);
1182 if (primaryWinInfo
->generic
.type
== CMD_WIN
)
1184 winInfo
= (TuiWinInfoPtr
) (sourceWindows ())->list
[0];
1185 srcWinInfo
= winInfo
;
1189 winInfo
= winList
[CMD_WIN
];
1190 srcWinInfo
= primaryWinInfo
;
1192 _makeInvisibleAndSetNewHeight (winInfo
,
1193 winInfo
->generic
.height
+ diff
);
1194 cmdWin
->generic
.origin
.y
= locator
->origin
.y
+ 1;
1195 _makeVisibleWithNewHeight (winInfo
);
1196 _makeVisibleWithNewHeight (primaryWinInfo
);
1197 if (srcWinInfo
->generic
.contentSize
<= 0)
1198 tuiEraseSourceContent (srcWinInfo
, EMPTY_SOURCE_PROMPT
);
1202 TuiWinInfoPtr firstWin
, secondWin
;
1204 if (curLayout
== SRC_DISASSEM_COMMAND
)
1207 secondWin
= disassemWin
;
1212 secondWin
= (TuiWinInfoPtr
) (sourceWindows ())->list
[0];
1214 if (primaryWinInfo
== cmdWin
)
1216 ** Split the change in height accross the 1st & 2nd windows
1217 ** adjusting them as well.
1219 int firstSplitDiff
= diff
/ 2; /* subtract the locator */
1220 int secondSplitDiff
= firstSplitDiff
;
1224 if (firstWin
->generic
.height
>
1225 secondWin
->generic
.height
)
1238 /* make sure that the minimum hieghts are honored */
1239 while ((firstWin
->generic
.height
+ firstSplitDiff
) < 3)
1244 while ((secondWin
->generic
.height
+ secondSplitDiff
) < 3)
1249 _makeInvisibleAndSetNewHeight (
1251 firstWin
->generic
.height
+ firstSplitDiff
);
1252 secondWin
->generic
.origin
.y
= firstWin
->generic
.height
- 1;
1253 _makeInvisibleAndSetNewHeight (
1254 secondWin
, secondWin
->generic
.height
+ secondSplitDiff
);
1255 cmdWin
->generic
.origin
.y
= locator
->origin
.y
+ 1;
1256 _makeInvisibleAndSetNewHeight (cmdWin
, newHeight
);
1260 if ((cmdWin
->generic
.height
+ diff
) < 1)
1262 ** If there is no way to increase the command window
1263 ** take real estate from the 1st or 2nd window.
1265 if ((cmdWin
->generic
.height
+ diff
) < 1)
1268 for (i
= cmdWin
->generic
.height
+ diff
;
1270 if (primaryWinInfo
== firstWin
)
1271 secondWin
->generic
.height
--;
1273 firstWin
->generic
.height
--;
1276 if (primaryWinInfo
== firstWin
)
1277 _makeInvisibleAndSetNewHeight (firstWin
, newHeight
);
1279 _makeInvisibleAndSetNewHeight (
1281 firstWin
->generic
.height
);
1282 secondWin
->generic
.origin
.y
= firstWin
->generic
.height
- 1;
1283 if (primaryWinInfo
== secondWin
)
1284 _makeInvisibleAndSetNewHeight (secondWin
, newHeight
);
1286 _makeInvisibleAndSetNewHeight (
1287 secondWin
, secondWin
->generic
.height
);
1288 cmdWin
->generic
.origin
.y
= locator
->origin
.y
+ 1;
1289 if ((cmdWin
->generic
.height
+ diff
) < 1)
1290 _makeInvisibleAndSetNewHeight (cmdWin
, 1);
1292 _makeInvisibleAndSetNewHeight (
1293 cmdWin
, cmdWin
->generic
.height
+ diff
);
1295 _makeVisibleWithNewHeight (cmdWin
);
1296 _makeVisibleWithNewHeight (secondWin
);
1297 _makeVisibleWithNewHeight (firstWin
);
1298 if (firstWin
->generic
.contentSize
<= 0)
1299 tuiEraseSourceContent (firstWin
, EMPTY_SOURCE_PROMPT
);
1300 if (secondWin
->generic
.contentSize
<= 0)
1301 tuiEraseSourceContent (secondWin
, EMPTY_SOURCE_PROMPT
);
1307 } /* _tuiAdjustWinHeights */
1311 ** _makeInvisibleAndSetNewHeight().
1312 ** Function make the target window (and auxillary windows associated
1313 ** with the targer) invisible, and set the new height and location.
1316 _makeInvisibleAndSetNewHeight (TuiWinInfoPtr winInfo
, int height
)
1320 TuiGenWinInfoPtr genWinInfo
;
1323 m_beInvisible (&winInfo
->generic
);
1324 winInfo
->generic
.height
= height
;
1326 winInfo
->generic
.viewportHeight
= height
- 1;
1328 winInfo
->generic
.viewportHeight
= height
;
1329 if (winInfo
!= cmdWin
)
1330 winInfo
->generic
.viewportHeight
--;
1332 /* Now deal with the auxillary windows associated with winInfo */
1333 switch (winInfo
->generic
.type
)
1337 genWinInfo
= winInfo
->detail
.sourceInfo
.executionInfo
;
1338 m_beInvisible (genWinInfo
);
1339 genWinInfo
->height
= height
;
1340 genWinInfo
->origin
.y
= winInfo
->generic
.origin
.y
;
1342 genWinInfo
->viewportHeight
= height
- 1;
1344 genWinInfo
->viewportHeight
= height
;
1345 if (winInfo
!= cmdWin
)
1346 genWinInfo
->viewportHeight
--;
1348 if (m_hasLocator (winInfo
))
1350 genWinInfo
= locatorWinInfoPtr ();
1351 m_beInvisible (genWinInfo
);
1352 genWinInfo
->origin
.y
= winInfo
->generic
.origin
.y
+ height
;
1356 /* delete all data item windows */
1357 for (i
= 0; i
< winInfo
->generic
.contentSize
; i
++)
1359 genWinInfo
= (TuiGenWinInfoPtr
) & ((TuiWinElementPtr
)
1360 winInfo
->generic
.content
[i
])->whichElement
.dataWindow
;
1361 tuiDelwin (genWinInfo
->handle
);
1362 genWinInfo
->handle
= (WINDOW
*) NULL
;
1370 } /* _makeInvisibleAndSetNewHeight */
1374 ** _makeVisibleWithNewHeight().
1375 ** Function to make the windows with new heights visible.
1376 ** This means re-creating the windows' content since the window
1377 ** had to be destroyed to be made invisible.
1380 _makeVisibleWithNewHeight (TuiWinInfoPtr winInfo
)
1385 m_beVisible (&winInfo
->generic
);
1386 checkAndDisplayHighlightIfNeeded (winInfo
);
1387 switch (winInfo
->generic
.type
)
1391 freeWinContent (winInfo
->detail
.sourceInfo
.executionInfo
);
1392 m_beVisible (winInfo
->detail
.sourceInfo
.executionInfo
);
1393 if (winInfo
->generic
.content
!= (OpaquePtr
) NULL
)
1395 TuiLineOrAddress lineOrAddr
;
1397 if (winInfo
->generic
.type
== SRC_WIN
)
1399 winInfo
->detail
.sourceInfo
.startLineOrAddr
.lineNo
;
1402 winInfo
->detail
.sourceInfo
.startLineOrAddr
.addr
;
1403 freeWinContent (&winInfo
->generic
);
1404 tuiUpdateSourceWindow (winInfo
,
1405 current_source_symtab
, lineOrAddr
, TRUE
);
1407 else if (selected_frame
!= (struct frame_info
*) NULL
)
1409 TuiLineOrAddress line
;
1410 extern int current_source_line
;
1412 s
= find_pc_symtab (selected_frame
->pc
);
1413 if (winInfo
->generic
.type
== SRC_WIN
)
1414 line
.lineNo
= current_source_line
;
1417 find_line_pc (s
, current_source_line
, &line
.addr
);
1419 tuiUpdateSourceWindow (winInfo
, s
, line
, TRUE
);
1421 if (m_hasLocator (winInfo
))
1423 m_beVisible (locatorWinInfoPtr ());
1424 tuiClearLocatorDisplay ();
1425 tuiShowLocatorContent ();
1429 tuiDisplayAllData ();
1432 winInfo
->detail
.commandInfo
.curLine
= 0;
1433 winInfo
->detail
.commandInfo
.curch
= 0;
1434 wmove (winInfo
->generic
.handle
,
1435 winInfo
->detail
.commandInfo
.curLine
,
1436 winInfo
->detail
.commandInfo
.curch
);
1443 } /* _makeVisibleWithNewHeight */
1447 _newHeightOk (TuiWinInfoPtr primaryWinInfo
, int newHeight
)
1449 int ok
= (newHeight
< termHeight ());
1453 int diff
, curHeight
;
1454 TuiLayoutType curLayout
= currentLayout ();
1456 diff
= (newHeight
- primaryWinInfo
->generic
.height
) * (-1);
1457 if (curLayout
== SRC_COMMAND
|| curLayout
== DISASSEM_COMMAND
)
1459 ok
= ((primaryWinInfo
->generic
.type
== CMD_WIN
&&
1460 newHeight
<= (termHeight () - 4) &&
1461 newHeight
>= MIN_CMD_WIN_HEIGHT
) ||
1462 (primaryWinInfo
->generic
.type
!= CMD_WIN
&&
1463 newHeight
<= (termHeight () - 2) &&
1464 newHeight
>= MIN_WIN_HEIGHT
));
1466 { /* check the total height */
1467 TuiWinInfoPtr winInfo
;
1469 if (primaryWinInfo
== cmdWin
)
1470 winInfo
= (TuiWinInfoPtr
) (sourceWindows ())->list
[0];
1474 (winInfo
->generic
.height
+ diff
)) <= termHeight ());
1479 int curTotalHeight
, totalHeight
, minHeight
;
1480 TuiWinInfoPtr firstWin
, secondWin
;
1482 if (curLayout
== SRC_DISASSEM_COMMAND
)
1485 secondWin
= disassemWin
;
1490 secondWin
= (TuiWinInfoPtr
) (sourceWindows ())->list
[0];
1493 ** We could simply add all the heights to obtain the same result
1494 ** but below is more explicit since we subtract 1 for the
1495 ** line that the first and second windows share, and add one
1499 (firstWin
->generic
.height
+ secondWin
->generic
.height
- 1)
1500 + cmdWin
->generic
.height
+ 1 /*locator */ ;
1501 if (primaryWinInfo
== cmdWin
)
1503 /* locator included since first & second win share a line */
1504 ok
= ((firstWin
->generic
.height
+
1505 secondWin
->generic
.height
+ diff
) >=
1506 (MIN_WIN_HEIGHT
* 2) &&
1507 newHeight
>= MIN_CMD_WIN_HEIGHT
);
1510 totalHeight
= newHeight
+ (firstWin
->generic
.height
+
1511 secondWin
->generic
.height
+ diff
);
1512 minHeight
= MIN_CMD_WIN_HEIGHT
;
1517 minHeight
= MIN_WIN_HEIGHT
;
1519 ** First see if we can increase/decrease the command
1520 ** window. And make sure that the command window is
1523 ok
= ((cmdWin
->generic
.height
+ diff
) > 0);
1526 ** Looks like we have to increase/decrease one of
1527 ** the other windows
1529 if (primaryWinInfo
== firstWin
)
1530 ok
= (secondWin
->generic
.height
+ diff
) >= minHeight
;
1532 ok
= (firstWin
->generic
.height
+ diff
) >= minHeight
;
1536 if (primaryWinInfo
== firstWin
)
1537 totalHeight
= newHeight
+
1538 secondWin
->generic
.height
+
1539 cmdWin
->generic
.height
+ diff
;
1541 totalHeight
= newHeight
+
1542 firstWin
->generic
.height
+
1543 cmdWin
->generic
.height
+ diff
;
1547 ** Now make sure that the proposed total height doesn't exceed
1548 ** the old total height.
1551 ok
= (newHeight
>= minHeight
&& totalHeight
<= curTotalHeight
);
1556 } /* _newHeightOk */
1560 ** _parseScrollingArgs().
1563 _parseScrollingArgs (char *arg
, TuiWinInfoPtr
* winToScroll
, int *numToScroll
)
1567 *winToScroll
= tuiWinWithFocus ();
1570 ** First set up the default window to scroll, in case there is no
1573 if (arg
!= (char *) NULL
)
1577 /* process the number of lines to scroll */
1578 buf
= bufPtr
= xstrdup (arg
);
1579 if (isdigit (*bufPtr
))
1584 bufPtr
= strchr (bufPtr
, ' ');
1585 if (bufPtr
!= (char *) NULL
)
1589 *numToScroll
= atoi (numStr
);
1592 else if (numToScroll
)
1593 *numToScroll
= atoi (numStr
);
1596 /* process the window name if one is specified */
1597 if (bufPtr
!= (char *) NULL
)
1603 while (*(++bufPtr
) == ' ')
1606 if (*bufPtr
!= (char) 0)
1611 /* Validate the window name */
1612 for (i
= 0; i
< strlen (wname
); i
++)
1613 wname
[i
] = toupper (wname
[i
]);
1614 *winToScroll
= partialWinByName (wname
);
1616 if (*winToScroll
== (TuiWinInfoPtr
) NULL
||
1617 !(*winToScroll
)->generic
.isVisible
)
1618 warning ("Invalid window specified. \n\
1619 The window name specified must be valid and visible.\n");
1620 else if (*winToScroll
== cmdWin
)
1621 *winToScroll
= (TuiWinInfoPtr
) (sourceWindows ())->list
[0];
1627 } /* _parseScrollingArgs */