1 /* TUI window generic functions.
3 Copyright (C) 1998-2017 Free Software Foundation, Inc.
5 Contributed by Hewlett-Packard Company.
7 This file is part of GDB.
9 This program is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 3 of the License, or
12 (at your option) any later version.
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
19 You should have received a copy of the GNU General Public License
20 along with this program. If not, see <http://www.gnu.org/licenses/>. */
22 /* This module contains procedures for handling tui window functions
23 like resize, scrolling, scrolling, changing focus, etc.
25 Author: Susan B. Macchia */
30 #include "breakpoint.h"
32 #include "cli/cli-cmds.h"
35 #include "event-loop.h"
38 #include "tui/tui-io.h"
39 #include "tui/tui-data.h"
40 #include "tui/tui-wingeneral.h"
41 #include "tui/tui-stack.h"
42 #include "tui/tui-regs.h"
43 #include "tui/tui-disasm.h"
44 #include "tui/tui-source.h"
45 #include "tui/tui-winsource.h"
46 #include "tui/tui-windata.h"
47 #include "tui/tui-win.h"
49 #include "gdb_curses.h"
51 #include "readline/readline.h"
55 /*******************************
57 ********************************/
58 static void make_visible_with_new_height (struct tui_win_info
*);
59 static void make_invisible_and_set_new_height (struct tui_win_info
*,
61 static enum tui_status
tui_adjust_win_heights (struct tui_win_info
*,
63 static int new_height_ok (struct tui_win_info
*, int);
64 static void tui_set_tab_width_command (const char *, int);
65 static void tui_refresh_all_command (const char *, int);
66 static void tui_set_win_height_command (const char *, int);
67 static void tui_all_windows_info (const char *, int);
68 static void tui_set_focus_command (const char *, int);
69 static void tui_scroll_forward_command (const char *, int);
70 static void tui_scroll_backward_command (const char *, int);
71 static void tui_scroll_left_command (const char *, int);
72 static void tui_scroll_right_command (const char *, int);
73 static void parse_scrolling_args (const char *,
74 struct tui_win_info
**,
78 /***************************************
80 ***************************************/
81 #define WIN_HEIGHT_USAGE "Usage: winheight <win_name> [+ | -] <#lines>\n"
82 #define XDBWIN_HEIGHT_USAGE "Usage: w <#lines>\n"
83 #define FOCUS_USAGE "Usage: focus {<win> | next | prev}\n"
85 /***************************************
87 ***************************************/
90 # define ACS_LRCORNER '+'
93 # define ACS_LLCORNER '+'
96 # define ACS_ULCORNER '+'
99 # define ACS_URCORNER '+'
102 # define ACS_HLINE '-'
105 # define ACS_VLINE '|'
108 /* Possible values for tui-border-kind variable. */
109 static const char *const tui_border_kind_enums
[] = {
116 /* Possible values for tui-border-mode and tui-active-border-mode. */
117 static const char *const tui_border_mode_enums
[] = {
134 /* Translation table for border-mode variables.
135 The list of values must be terminated by a NULL.
136 After the NULL value, an entry defines the default. */
137 struct tui_translate tui_border_mode_translate
[] = {
138 { "normal", A_NORMAL
},
139 { "standout", A_STANDOUT
},
140 { "reverse", A_REVERSE
},
142 { "half-standout", A_DIM
| A_STANDOUT
},
144 { "bold-standout", A_BOLD
| A_STANDOUT
},
146 { "normal", A_NORMAL
}
149 /* Translation tables for border-kind, one for each border
150 character (see wborder, border curses operations).
151 -1 is used to indicate the ACS because ACS characters
152 are determined at run time by curses (depends on terminal). */
153 struct tui_translate tui_border_kind_translate_vline
[] = {
161 struct tui_translate tui_border_kind_translate_hline
[] = {
169 struct tui_translate tui_border_kind_translate_ulcorner
[] = {
177 struct tui_translate tui_border_kind_translate_urcorner
[] = {
185 struct tui_translate tui_border_kind_translate_llcorner
[] = {
193 struct tui_translate tui_border_kind_translate_lrcorner
[] = {
202 /* Tui configuration variables controlled with set/show command. */
203 const char *tui_active_border_mode
= "bold-standout";
205 show_tui_active_border_mode (struct ui_file
*file
,
207 struct cmd_list_element
*c
,
210 fprintf_filtered (file
, _("\
211 The attribute mode to use for the active TUI window border is \"%s\".\n"),
215 const char *tui_border_mode
= "normal";
217 show_tui_border_mode (struct ui_file
*file
,
219 struct cmd_list_element
*c
,
222 fprintf_filtered (file
, _("\
223 The attribute mode to use for the TUI window borders is \"%s\".\n"),
227 const char *tui_border_kind
= "acs";
229 show_tui_border_kind (struct ui_file
*file
,
231 struct cmd_list_element
*c
,
234 fprintf_filtered (file
, _("The kind of border for TUI windows is \"%s\".\n"),
239 /* Tui internal configuration variables. These variables are updated
240 by tui_update_variables to reflect the tui configuration
242 chtype tui_border_vline
;
243 chtype tui_border_hline
;
244 chtype tui_border_ulcorner
;
245 chtype tui_border_urcorner
;
246 chtype tui_border_llcorner
;
247 chtype tui_border_lrcorner
;
249 int tui_border_attrs
;
250 int tui_active_border_attrs
;
252 /* Identify the item in the translation table.
253 When the item is not recognized, use the default entry. */
254 static struct tui_translate
*
255 translate (const char *name
, struct tui_translate
*table
)
259 if (name
&& strcmp (table
->name
, name
) == 0)
264 /* Not found, return default entry. */
269 /* Update the tui internal configuration according to gdb settings.
270 Returns 1 if the configuration has changed and the screen should
273 tui_update_variables (void)
276 struct tui_translate
*entry
;
278 entry
= translate (tui_border_mode
, tui_border_mode_translate
);
279 if (tui_border_attrs
!= entry
->value
)
281 tui_border_attrs
= entry
->value
;
284 entry
= translate (tui_active_border_mode
, tui_border_mode_translate
);
285 if (tui_active_border_attrs
!= entry
->value
)
287 tui_active_border_attrs
= entry
->value
;
291 /* If one corner changes, all characters are changed.
292 Only check the first one. The ACS characters are determined at
293 run time by curses terminal management. */
294 entry
= translate (tui_border_kind
, tui_border_kind_translate_lrcorner
);
295 if (tui_border_lrcorner
!= (chtype
) entry
->value
)
297 tui_border_lrcorner
= (entry
->value
< 0) ? ACS_LRCORNER
: entry
->value
;
300 entry
= translate (tui_border_kind
, tui_border_kind_translate_llcorner
);
301 tui_border_llcorner
= (entry
->value
< 0) ? ACS_LLCORNER
: entry
->value
;
303 entry
= translate (tui_border_kind
, tui_border_kind_translate_ulcorner
);
304 tui_border_ulcorner
= (entry
->value
< 0) ? ACS_ULCORNER
: entry
->value
;
306 entry
= translate (tui_border_kind
, tui_border_kind_translate_urcorner
);
307 tui_border_urcorner
= (entry
->value
< 0) ? ACS_URCORNER
: entry
->value
;
309 entry
= translate (tui_border_kind
, tui_border_kind_translate_hline
);
310 tui_border_hline
= (entry
->value
< 0) ? ACS_HLINE
: entry
->value
;
312 entry
= translate (tui_border_kind
, tui_border_kind_translate_vline
);
313 tui_border_vline
= (entry
->value
< 0) ? ACS_VLINE
: entry
->value
;
319 set_tui_cmd (const char *args
, int from_tty
)
324 show_tui_cmd (const char *args
, int from_tty
)
328 static struct cmd_list_element
*tuilist
;
331 tui_command (const char *args
, int from_tty
)
333 printf_unfiltered (_("\"tui\" must be followed by the name of a "
335 help_list (tuilist
, "tui ", all_commands
, gdb_stdout
);
338 struct cmd_list_element
**
339 tui_get_cmd_list (void)
342 add_prefix_cmd ("tui", class_tui
, tui_command
,
343 _("Text User Interface commands."),
344 &tuilist
, "tui ", 0, &cmdlist
);
348 /* The set_func hook of "set tui ..." commands that affect the window
349 borders on the TUI display. */
351 tui_set_var_cmd (const char *null_args
,
352 int from_tty
, struct cmd_list_element
*c
)
354 if (tui_update_variables () && tui_active
)
355 tui_rehighlight_all ();
358 /* Generic window name completion function. Complete window name pointed
359 to by TEXT and WORD. If INCLUDE_NEXT_PREV_P is true then the special
360 window names 'next' and 'prev' will also be considered as possible
361 completions of the window name. */
364 window_name_completer (completion_tracker
&tracker
,
365 int include_next_prev_p
,
366 const char *text
, const char *word
)
368 VEC (const_char_ptr
) *completion_name_vec
= NULL
;
371 for (win_type
= SRC_WIN
; win_type
< MAX_MAJOR_WINDOWS
; win_type
++)
373 const char *completion_name
= NULL
;
375 /* We can't focus on an invisible window. */
376 if (tui_win_list
[win_type
] == NULL
377 || !tui_win_list
[win_type
]->generic
.is_visible
)
380 completion_name
= tui_win_name (&tui_win_list
[win_type
]->generic
);
381 gdb_assert (completion_name
!= NULL
);
382 VEC_safe_push (const_char_ptr
, completion_name_vec
, completion_name
);
385 /* If no windows are considered visible then the TUI has not yet been
386 initialized. But still "focus src" and "focus cmd" will work because
387 invoking the focus command will entail initializing the TUI which sets the
388 default layout to SRC_COMMAND. */
389 if (VEC_length (const_char_ptr
, completion_name_vec
) == 0)
391 VEC_safe_push (const_char_ptr
, completion_name_vec
, SRC_NAME
);
392 VEC_safe_push (const_char_ptr
, completion_name_vec
, CMD_NAME
);
395 if (include_next_prev_p
)
397 VEC_safe_push (const_char_ptr
, completion_name_vec
, "next");
398 VEC_safe_push (const_char_ptr
, completion_name_vec
, "prev");
401 VEC_safe_push (const_char_ptr
, completion_name_vec
, NULL
);
402 complete_on_enum (tracker
,
403 VEC_address (const_char_ptr
, completion_name_vec
),
406 VEC_free (const_char_ptr
, completion_name_vec
);
409 /* Complete possible window names to focus on. TEXT is the complete text
410 entered so far, WORD is the word currently being completed. */
413 focus_completer (struct cmd_list_element
*ignore
,
414 completion_tracker
&tracker
,
415 const char *text
, const char *word
)
417 window_name_completer (tracker
, 1, text
, word
);
420 /* Complete possible window names for winheight command. TEXT is the
421 complete text entered so far, WORD is the word currently being
425 winheight_completer (struct cmd_list_element
*ignore
,
426 completion_tracker
&tracker
,
427 const char *text
, const char *word
)
429 /* The first word is the window name. That we can complete. Subsequent
430 words can't be completed. */
434 window_name_completer (tracker
, 0, text
, word
);
437 /* Function to initialize gdb commands, for tui window
441 _initialize_tui_win (void)
443 static struct cmd_list_element
*tui_setlist
;
444 static struct cmd_list_element
*tui_showlist
;
445 struct cmd_list_element
*cmd
;
447 /* Define the classes of commands.
448 They will appear in the help list in the reverse of this order. */
449 add_prefix_cmd ("tui", class_tui
, set_tui_cmd
,
450 _("TUI configuration variables"),
451 &tui_setlist
, "set tui ",
452 0 /* allow-unknown */, &setlist
);
453 add_prefix_cmd ("tui", class_tui
, show_tui_cmd
,
454 _("TUI configuration variables"),
455 &tui_showlist
, "show tui ",
456 0 /* allow-unknown */, &showlist
);
458 add_com ("refresh", class_tui
, tui_refresh_all_command
,
459 _("Refresh the terminal display.\n"));
460 add_com ("tabset", class_tui
, tui_set_tab_width_command
, _("\
461 Set the width (in characters) of tab stops.\n\
462 Usage: tabset <n>\n"));
463 cmd
= add_com ("winheight", class_tui
, tui_set_win_height_command
, _("\
464 Set or modify the height of a specified window.\n\
465 Usage: winheight <win_name> [+ | -] <#lines>\n\
467 src : the source window\n\
468 cmd : the command window\n\
469 asm : the disassembly window\n\
470 regs : the register display\n"));
471 add_com_alias ("wh", "winheight", class_tui
, 0);
472 set_cmd_completer (cmd
, winheight_completer
);
473 add_info ("win", tui_all_windows_info
,
474 _("List of all displayed windows.\n"));
475 cmd
= add_com ("focus", class_tui
, tui_set_focus_command
, _("\
476 Set focus to named window or next/prev window.\n\
477 Usage: focus {<win> | next | prev}\n\
478 Valid Window names are:\n\
479 src : the source window\n\
480 asm : the disassembly window\n\
481 regs : the register display\n\
482 cmd : the command window\n"));
483 add_com_alias ("fs", "focus", class_tui
, 0);
484 set_cmd_completer (cmd
, focus_completer
);
485 add_com ("+", class_tui
, tui_scroll_forward_command
, _("\
486 Scroll window forward.\n\
487 Usage: + [win] [n]\n"));
488 add_com ("-", class_tui
, tui_scroll_backward_command
, _("\
489 Scroll window backward.\n\
490 Usage: - [win] [n]\n"));
491 add_com ("<", class_tui
, tui_scroll_left_command
, _("\
492 Scroll window text to the left.\n\
493 Usage: < [win] [n]\n"));
494 add_com (">", class_tui
, tui_scroll_right_command
, _("\
495 Scroll window text to the right.\n\
496 Usage: > [win] [n]\n"));
498 /* Define the tui control variables. */
499 add_setshow_enum_cmd ("border-kind", no_class
, tui_border_kind_enums
,
500 &tui_border_kind
, _("\
501 Set the kind of border for TUI windows."), _("\
502 Show the kind of border for TUI windows."), _("\
503 This variable controls the border of TUI windows:\n\
504 space use a white space\n\
505 ascii use ascii characters + - | for the border\n\
506 acs use the Alternate Character Set"),
508 show_tui_border_kind
,
509 &tui_setlist
, &tui_showlist
);
511 add_setshow_enum_cmd ("border-mode", no_class
, tui_border_mode_enums
,
512 &tui_border_mode
, _("\
513 Set the attribute mode to use for the TUI window borders."), _("\
514 Show the attribute mode to use for the TUI window borders."), _("\
515 This variable controls the attributes to use for the window borders:\n\
516 normal normal display\n\
517 standout use highlight mode of terminal\n\
518 reverse use reverse video mode\n\
519 half use half bright\n\
520 half-standout use half bright and standout mode\n\
521 bold use extra bright or bold\n\
522 bold-standout use extra bright or bold with standout mode"),
524 show_tui_border_mode
,
525 &tui_setlist
, &tui_showlist
);
527 add_setshow_enum_cmd ("active-border-mode", no_class
, tui_border_mode_enums
,
528 &tui_active_border_mode
, _("\
529 Set the attribute mode to use for the active TUI window border."), _("\
530 Show the attribute mode to use for the active TUI window border."), _("\
531 This variable controls the attributes to use for the active window border:\n\
532 normal normal display\n\
533 standout use highlight mode of terminal\n\
534 reverse use reverse video mode\n\
535 half use half bright\n\
536 half-standout use half bright and standout mode\n\
537 bold use extra bright or bold\n\
538 bold-standout use extra bright or bold with standout mode"),
540 show_tui_active_border_mode
,
541 &tui_setlist
, &tui_showlist
);
544 /* Update gdb's knowledge of the terminal size. */
546 tui_update_gdb_sizes (void)
552 width
= TUI_CMD_WIN
->generic
.width
;
553 height
= TUI_CMD_WIN
->generic
.height
;
557 width
= tui_term_width ();
558 height
= tui_term_height ();
561 set_screen_width_and_height (width
, height
);
565 /* Set the logical focus to win_info. */
567 tui_set_win_focus_to (struct tui_win_info
*win_info
)
569 if (win_info
!= NULL
)
571 struct tui_win_info
*win_with_focus
= tui_win_with_focus ();
573 if (win_with_focus
!= NULL
574 && win_with_focus
->generic
.type
!= CMD_WIN
)
575 tui_unhighlight_win (win_with_focus
);
576 tui_set_win_with_focus (win_info
);
577 if (win_info
->generic
.type
!= CMD_WIN
)
578 tui_highlight_win (win_info
);
584 tui_scroll_forward (struct tui_win_info
*win_to_scroll
,
587 if (win_to_scroll
!= TUI_CMD_WIN
)
589 int _num_to_scroll
= num_to_scroll
;
591 if (num_to_scroll
== 0)
592 _num_to_scroll
= win_to_scroll
->generic
.height
- 3;
594 /* If we are scrolling the source or disassembly window, do a
595 "psuedo" scroll since not all of the source is in memory,
596 only what is in the viewport. If win_to_scroll is the
597 command window do nothing since the term should handle
599 if (win_to_scroll
== TUI_SRC_WIN
)
600 tui_vertical_source_scroll (FORWARD_SCROLL
, _num_to_scroll
);
601 else if (win_to_scroll
== TUI_DISASM_WIN
)
602 tui_vertical_disassem_scroll (FORWARD_SCROLL
, _num_to_scroll
);
603 else if (win_to_scroll
== TUI_DATA_WIN
)
604 tui_vertical_data_scroll (FORWARD_SCROLL
, _num_to_scroll
);
609 tui_scroll_backward (struct tui_win_info
*win_to_scroll
,
612 if (win_to_scroll
!= TUI_CMD_WIN
)
614 int _num_to_scroll
= num_to_scroll
;
616 if (num_to_scroll
== 0)
617 _num_to_scroll
= win_to_scroll
->generic
.height
- 3;
619 /* If we are scrolling the source or disassembly window, do a
620 "psuedo" scroll since not all of the source is in memory,
621 only what is in the viewport. If win_to_scroll is the
622 command window do nothing since the term should handle
624 if (win_to_scroll
== TUI_SRC_WIN
)
625 tui_vertical_source_scroll (BACKWARD_SCROLL
, _num_to_scroll
);
626 else if (win_to_scroll
== TUI_DISASM_WIN
)
627 tui_vertical_disassem_scroll (BACKWARD_SCROLL
, _num_to_scroll
);
628 else if (win_to_scroll
== TUI_DATA_WIN
)
629 tui_vertical_data_scroll (BACKWARD_SCROLL
, _num_to_scroll
);
635 tui_scroll_left (struct tui_win_info
*win_to_scroll
,
638 if (win_to_scroll
!= TUI_CMD_WIN
)
640 int _num_to_scroll
= num_to_scroll
;
642 if (_num_to_scroll
== 0)
645 /* If we are scrolling the source or disassembly window, do a
646 "psuedo" scroll since not all of the source is in memory,
647 only what is in the viewport. If win_to_scroll is the command
648 window do nothing since the term should handle it. */
649 if (win_to_scroll
== TUI_SRC_WIN
650 || win_to_scroll
== TUI_DISASM_WIN
)
651 tui_horizontal_source_scroll (win_to_scroll
, LEFT_SCROLL
,
658 tui_scroll_right (struct tui_win_info
*win_to_scroll
,
661 if (win_to_scroll
!= TUI_CMD_WIN
)
663 int _num_to_scroll
= num_to_scroll
;
665 if (_num_to_scroll
== 0)
668 /* If we are scrolling the source or disassembly window, do a
669 "psuedo" scroll since not all of the source is in memory,
670 only what is in the viewport. If win_to_scroll is the command
671 window do nothing since the term should handle it. */
672 if (win_to_scroll
== TUI_SRC_WIN
673 || win_to_scroll
== TUI_DISASM_WIN
)
674 tui_horizontal_source_scroll (win_to_scroll
, RIGHT_SCROLL
,
680 /* Scroll a window. Arguments are passed through a va_list. */
682 tui_scroll (enum tui_scroll_direction direction
,
683 struct tui_win_info
*win_to_scroll
,
689 tui_scroll_forward (win_to_scroll
, num_to_scroll
);
691 case BACKWARD_SCROLL
:
692 tui_scroll_backward (win_to_scroll
, num_to_scroll
);
695 tui_scroll_left (win_to_scroll
, num_to_scroll
);
698 tui_scroll_right (win_to_scroll
, num_to_scroll
);
707 tui_refresh_all_win (void)
711 clearok (curscr
, TRUE
);
712 tui_refresh_all (tui_win_list
);
713 for (type
= SRC_WIN
; type
< MAX_MAJOR_WINDOWS
; type
++)
715 if (tui_win_list
[type
]
716 && tui_win_list
[type
]->generic
.is_visible
)
722 tui_show_source_content (tui_win_list
[type
]);
723 tui_check_and_display_highlight_if_needed (tui_win_list
[type
]);
724 tui_erase_exec_info_content (tui_win_list
[type
]);
725 tui_update_exec_info (tui_win_list
[type
]);
728 tui_refresh_data_win ();
735 tui_show_locator_content ();
739 tui_rehighlight_all (void)
743 for (type
= SRC_WIN
; type
< MAX_MAJOR_WINDOWS
; type
++)
744 tui_check_and_display_highlight_if_needed (tui_win_list
[type
]);
747 /* Resize all the windows based on the terminal size. This function
748 gets called from within the readline sinwinch handler. */
750 tui_resize_all (void)
752 int height_diff
, width_diff
;
753 int screenheight
, screenwidth
;
755 rl_get_screen_size (&screenheight
, &screenwidth
);
756 width_diff
= screenwidth
- tui_term_width ();
757 height_diff
= screenheight
- tui_term_height ();
758 if (height_diff
|| width_diff
)
760 enum tui_layout_type cur_layout
= tui_current_layout ();
761 struct tui_win_info
*win_with_focus
= tui_win_with_focus ();
762 struct tui_win_info
*first_win
;
763 struct tui_win_info
*second_win
;
764 struct tui_gen_win_info
*locator
= tui_locator_win_info_ptr ();
766 int new_height
, split_diff
, cmd_split_diff
, num_wins_displayed
= 2;
768 #ifdef HAVE_RESIZE_TERM
769 resize_term (screenheight
, screenwidth
);
771 /* Turn keypad off while we resize. */
772 if (win_with_focus
!= TUI_CMD_WIN
)
773 keypad (TUI_CMD_WIN
->generic
.handle
, FALSE
);
774 tui_update_gdb_sizes ();
775 tui_set_term_height_to (screenheight
);
776 tui_set_term_width_to (screenwidth
);
777 if (cur_layout
== SRC_DISASSEM_COMMAND
778 || cur_layout
== SRC_DATA_COMMAND
779 || cur_layout
== DISASSEM_DATA_COMMAND
)
780 num_wins_displayed
++;
781 split_diff
= height_diff
/ num_wins_displayed
;
782 cmd_split_diff
= split_diff
;
783 if (height_diff
% num_wins_displayed
)
790 /* Now adjust each window. */
791 /* erase + clearok are used instead of a straightforward clear as
792 AIX 5.3 does not define clear. */
794 clearok (curscr
, TRUE
);
799 case DISASSEM_COMMAND
:
800 first_win
= (struct tui_win_info
*) (tui_source_windows ())->list
[0];
801 first_win
->generic
.width
+= width_diff
;
802 locator
->width
+= width_diff
;
803 /* Check for invalid heights. */
804 if (height_diff
== 0)
805 new_height
= first_win
->generic
.height
;
806 else if ((first_win
->generic
.height
+ split_diff
) >=
807 (screenheight
- MIN_CMD_WIN_HEIGHT
- 1))
808 new_height
= screenheight
- MIN_CMD_WIN_HEIGHT
- 1;
809 else if ((first_win
->generic
.height
+ split_diff
) <= 0)
810 new_height
= MIN_WIN_HEIGHT
;
812 new_height
= first_win
->generic
.height
+ split_diff
;
814 locator
->origin
.y
= new_height
+ 1;
815 make_invisible_and_set_new_height (first_win
, new_height
);
816 TUI_CMD_WIN
->generic
.origin
.y
= locator
->origin
.y
+ 1;
817 TUI_CMD_WIN
->generic
.width
+= width_diff
;
818 new_height
= screenheight
- TUI_CMD_WIN
->generic
.origin
.y
;
819 make_invisible_and_set_new_height (TUI_CMD_WIN
, new_height
);
820 make_visible_with_new_height (first_win
);
821 make_visible_with_new_height (TUI_CMD_WIN
);
822 if (first_win
->generic
.content_size
<= 0)
823 tui_erase_source_content (first_win
, EMPTY_SOURCE_PROMPT
);
826 if (cur_layout
== SRC_DISASSEM_COMMAND
)
828 first_win
= TUI_SRC_WIN
;
829 first_win
->generic
.width
+= width_diff
;
830 second_win
= TUI_DISASM_WIN
;
831 second_win
->generic
.width
+= width_diff
;
835 first_win
= TUI_DATA_WIN
;
836 first_win
->generic
.width
+= width_diff
;
837 second_win
= (struct tui_win_info
*)
838 (tui_source_windows ())->list
[0];
839 second_win
->generic
.width
+= width_diff
;
841 /* Change the first window's height/width. */
842 /* Check for invalid heights. */
843 if (height_diff
== 0)
844 new_height
= first_win
->generic
.height
;
845 else if ((first_win
->generic
.height
+
846 second_win
->generic
.height
+ (split_diff
* 2)) >=
847 (screenheight
- MIN_CMD_WIN_HEIGHT
- 1))
848 new_height
= (screenheight
- MIN_CMD_WIN_HEIGHT
- 1) / 2;
849 else if ((first_win
->generic
.height
+ split_diff
) <= 0)
850 new_height
= MIN_WIN_HEIGHT
;
852 new_height
= first_win
->generic
.height
+ split_diff
;
853 make_invisible_and_set_new_height (first_win
, new_height
);
855 locator
->width
+= width_diff
;
857 /* Change the second window's height/width. */
858 /* Check for invalid heights. */
859 if (height_diff
== 0)
860 new_height
= second_win
->generic
.height
;
861 else if ((first_win
->generic
.height
+
862 second_win
->generic
.height
+ (split_diff
* 2)) >=
863 (screenheight
- MIN_CMD_WIN_HEIGHT
- 1))
865 new_height
= screenheight
- MIN_CMD_WIN_HEIGHT
- 1;
867 new_height
= (new_height
/ 2) + 1;
871 else if ((second_win
->generic
.height
+ split_diff
) <= 0)
872 new_height
= MIN_WIN_HEIGHT
;
874 new_height
= second_win
->generic
.height
+ split_diff
;
875 second_win
->generic
.origin
.y
= first_win
->generic
.height
- 1;
876 make_invisible_and_set_new_height (second_win
, new_height
);
878 /* Change the command window's height/width. */
879 TUI_CMD_WIN
->generic
.origin
.y
= locator
->origin
.y
+ 1;
880 make_invisible_and_set_new_height (TUI_CMD_WIN
,
881 TUI_CMD_WIN
->generic
.height
883 make_visible_with_new_height (first_win
);
884 make_visible_with_new_height (second_win
);
885 make_visible_with_new_height (TUI_CMD_WIN
);
886 if (first_win
->generic
.content_size
<= 0)
887 tui_erase_source_content (first_win
, EMPTY_SOURCE_PROMPT
);
888 if (second_win
->generic
.content_size
<= 0)
889 tui_erase_source_content (second_win
, EMPTY_SOURCE_PROMPT
);
892 /* Now remove all invisible windows, and their content so that
893 they get created again when called for with the new size. */
894 for (win_type
= SRC_WIN
; (win_type
< MAX_MAJOR_WINDOWS
); win_type
++)
896 if (win_type
!= CMD_WIN
897 && (tui_win_list
[win_type
] != NULL
)
898 && !tui_win_list
[win_type
]->generic
.is_visible
)
900 tui_free_window (tui_win_list
[win_type
]);
901 tui_win_list
[win_type
] = NULL
;
904 /* Turn keypad back on, unless focus is in the command
906 if (win_with_focus
!= TUI_CMD_WIN
)
907 keypad (TUI_CMD_WIN
->generic
.handle
, TRUE
);
912 /* Token for use by TUI's asynchronous SIGWINCH handler. */
913 static struct async_signal_handler
*tui_sigwinch_token
;
915 /* TUI's SIGWINCH signal handler. */
917 tui_sigwinch_handler (int signal
)
919 mark_async_signal_handler (tui_sigwinch_token
);
920 tui_set_win_resized_to (TRUE
);
923 /* Callback for asynchronously resizing TUI following a SIGWINCH signal. */
925 tui_async_resize_screen (gdb_client_data arg
)
927 rl_resize_terminal ();
931 int screen_height
, screen_width
;
933 rl_get_screen_size (&screen_height
, &screen_width
);
934 set_screen_width_and_height (screen_width
, screen_height
);
936 /* win_resized is left set so that the next call to tui_enable()
937 resizes the TUI windows. */
941 tui_set_win_resized_to (FALSE
);
943 tui_refresh_all_win ();
944 tui_update_gdb_sizes ();
945 tui_redisplay_readline ();
950 /* Initialize TUI's SIGWINCH signal handler. Note that the handler is not
951 uninstalled when we exit TUI, so the handler should not assume that TUI is
954 tui_initialize_win (void)
958 = create_async_signal_handler (tui_async_resize_screen
, NULL
);
961 #ifdef HAVE_SIGACTION
962 struct sigaction old_winch
;
964 memset (&old_winch
, 0, sizeof (old_winch
));
965 old_winch
.sa_handler
= &tui_sigwinch_handler
;
967 old_winch
.sa_flags
= SA_RESTART
;
969 sigaction (SIGWINCH
, &old_winch
, NULL
);
971 signal (SIGWINCH
, &tui_sigwinch_handler
);
978 /*************************
979 ** STATIC LOCAL FUNCTIONS
980 **************************/
984 tui_scroll_forward_command (const char *arg
, int from_tty
)
986 int num_to_scroll
= 1;
987 struct tui_win_info
*win_to_scroll
;
989 /* Make sure the curses mode is enabled. */
991 if (arg
== (char *) NULL
)
992 parse_scrolling_args (arg
, &win_to_scroll
, (int *) NULL
);
994 parse_scrolling_args (arg
, &win_to_scroll
, &num_to_scroll
);
995 tui_scroll (FORWARD_SCROLL
, win_to_scroll
, num_to_scroll
);
1000 tui_scroll_backward_command (const char *arg
, int from_tty
)
1002 int num_to_scroll
= 1;
1003 struct tui_win_info
*win_to_scroll
;
1005 /* Make sure the curses mode is enabled. */
1007 if (arg
== (char *) NULL
)
1008 parse_scrolling_args (arg
, &win_to_scroll
, (int *) NULL
);
1010 parse_scrolling_args (arg
, &win_to_scroll
, &num_to_scroll
);
1011 tui_scroll (BACKWARD_SCROLL
, win_to_scroll
, num_to_scroll
);
1016 tui_scroll_left_command (const char *arg
, int from_tty
)
1019 struct tui_win_info
*win_to_scroll
;
1021 /* Make sure the curses mode is enabled. */
1023 parse_scrolling_args (arg
, &win_to_scroll
, &num_to_scroll
);
1024 tui_scroll (LEFT_SCROLL
, win_to_scroll
, num_to_scroll
);
1029 tui_scroll_right_command (const char *arg
, int from_tty
)
1032 struct tui_win_info
*win_to_scroll
;
1034 /* Make sure the curses mode is enabled. */
1036 parse_scrolling_args (arg
, &win_to_scroll
, &num_to_scroll
);
1037 tui_scroll (RIGHT_SCROLL
, win_to_scroll
, num_to_scroll
);
1041 /* Set focus to the window named by 'arg'. */
1043 tui_set_focus (const char *arg
, int from_tty
)
1045 if (arg
!= (char *) NULL
)
1047 char *buf_ptr
= (char *) xstrdup (arg
);
1049 struct tui_win_info
*win_info
= NULL
;
1051 for (i
= 0; (i
< strlen (buf_ptr
)); i
++)
1052 buf_ptr
[i
] = tolower (arg
[i
]);
1054 if (subset_compare (buf_ptr
, "next"))
1055 win_info
= tui_next_win (tui_win_with_focus ());
1056 else if (subset_compare (buf_ptr
, "prev"))
1057 win_info
= tui_prev_win (tui_win_with_focus ());
1059 win_info
= tui_partial_win_by_name (buf_ptr
);
1061 if (win_info
== (struct tui_win_info
*) NULL
1062 || !win_info
->generic
.is_visible
)
1063 warning (_("Invalid window specified. \n\
1064 The window name specified must be valid and visible.\n"));
1067 tui_set_win_focus_to (win_info
);
1068 keypad (TUI_CMD_WIN
->generic
.handle
, (win_info
!= TUI_CMD_WIN
));
1071 if (TUI_DATA_WIN
&& TUI_DATA_WIN
->generic
.is_visible
)
1072 tui_refresh_data_win ();
1074 printf_filtered (_("Focus set to %s window.\n"),
1075 tui_win_name (&tui_win_with_focus ()->generic
));
1078 warning (_("Incorrect Number of Arguments.\n%s"), FOCUS_USAGE
);
1082 tui_set_focus_command (const char *arg
, int from_tty
)
1084 /* Make sure the curses mode is enabled. */
1086 tui_set_focus (arg
, from_tty
);
1091 tui_all_windows_info (const char *arg
, int from_tty
)
1094 struct tui_win_info
*win_with_focus
= tui_win_with_focus ();
1096 for (type
= SRC_WIN
; (type
< MAX_MAJOR_WINDOWS
); type
++)
1097 if (tui_win_list
[type
]
1098 && tui_win_list
[type
]->generic
.is_visible
)
1100 if (win_with_focus
== tui_win_list
[type
])
1101 printf_filtered (" %s\t(%d lines) <has focus>\n",
1102 tui_win_name (&tui_win_list
[type
]->generic
),
1103 tui_win_list
[type
]->generic
.height
);
1105 printf_filtered (" %s\t(%d lines)\n",
1106 tui_win_name (&tui_win_list
[type
]->generic
),
1107 tui_win_list
[type
]->generic
.height
);
1113 tui_refresh_all_command (const char *arg
, int from_tty
)
1115 /* Make sure the curses mode is enabled. */
1118 tui_refresh_all_win ();
1122 /* Set the tab width of the specified window. */
1124 tui_set_tab_width_command (const char *arg
, int from_tty
)
1126 /* Make sure the curses mode is enabled. */
1128 if (arg
!= (char *) NULL
)
1135 tui_set_default_tab_len (ts
);
1136 /* We don't really change the height of any windows, but
1137 calling these 2 functions causes a complete regeneration
1138 and redisplay of the window's contents, which will take
1139 the new tab width into account. */
1140 if (tui_win_list
[SRC_WIN
]
1141 && tui_win_list
[SRC_WIN
]->generic
.is_visible
)
1143 make_invisible_and_set_new_height (TUI_SRC_WIN
,
1144 TUI_SRC_WIN
->generic
.height
);
1145 make_visible_with_new_height (TUI_SRC_WIN
);
1147 if (tui_win_list
[DISASSEM_WIN
]
1148 && tui_win_list
[DISASSEM_WIN
]->generic
.is_visible
)
1150 make_invisible_and_set_new_height (TUI_DISASM_WIN
,
1151 TUI_DISASM_WIN
->generic
.height
);
1152 make_visible_with_new_height (TUI_DISASM_WIN
);
1156 warning (_("Tab widths greater than 0 must be specified."));
1161 /* Set the height of the specified window. */
1163 tui_set_win_height (const char *arg
, int from_tty
)
1165 /* Make sure the curses mode is enabled. */
1167 if (arg
!= (char *) NULL
)
1169 std::string copy
= arg
;
1170 char *buf
= ©
[0];
1171 char *buf_ptr
= buf
;
1174 struct tui_win_info
*win_info
;
1177 buf_ptr
= strchr (buf_ptr
, ' ');
1178 if (buf_ptr
!= (char *) NULL
)
1180 *buf_ptr
= (char) 0;
1182 /* Validate the window name. */
1183 for (i
= 0; i
< strlen (wname
); i
++)
1184 wname
[i
] = tolower (wname
[i
]);
1185 win_info
= tui_partial_win_by_name (wname
);
1187 if (win_info
== (struct tui_win_info
*) NULL
1188 || !win_info
->generic
.is_visible
)
1189 warning (_("Invalid window specified. \n\
1190 The window name specified must be valid and visible.\n"));
1193 /* Process the size. */
1194 while (*(++buf_ptr
) == ' ')
1197 if (*buf_ptr
!= (char) 0)
1200 int fixed_size
= TRUE
;
1203 if (*buf_ptr
== '+' || *buf_ptr
== '-')
1205 if (*buf_ptr
== '-')
1210 input_no
= atoi (buf_ptr
);
1216 new_height
= input_no
;
1218 new_height
= win_info
->generic
.height
+ input_no
;
1220 /* Now change the window's height, and adjust
1221 all other windows around it. */
1222 if (tui_adjust_win_heights (win_info
,
1223 new_height
) == TUI_FAILURE
)
1224 warning (_("Invalid window height specified.\n%s"),
1227 tui_update_gdb_sizes ();
1230 warning (_("Invalid window height specified.\n%s"),
1236 printf_filtered (WIN_HEIGHT_USAGE
);
1239 printf_filtered (WIN_HEIGHT_USAGE
);
1242 /* Set the height of the specified window, with va_list. */
1244 tui_set_win_height_command (const char *arg
, int from_tty
)
1246 /* Make sure the curses mode is enabled. */
1248 tui_set_win_height (arg
, from_tty
);
1251 /* Function to adjust all window heights around the primary. */
1252 static enum tui_status
1253 tui_adjust_win_heights (struct tui_win_info
*primary_win_info
,
1256 enum tui_status status
= TUI_FAILURE
;
1258 if (new_height_ok (primary_win_info
, new_height
))
1260 status
= TUI_SUCCESS
;
1261 if (new_height
!= primary_win_info
->generic
.height
)
1264 struct tui_win_info
*win_info
;
1265 struct tui_gen_win_info
*locator
= tui_locator_win_info_ptr ();
1266 enum tui_layout_type cur_layout
= tui_current_layout ();
1268 diff
= (new_height
- primary_win_info
->generic
.height
) * (-1);
1269 if (cur_layout
== SRC_COMMAND
1270 || cur_layout
== DISASSEM_COMMAND
)
1272 struct tui_win_info
*src_win_info
;
1274 make_invisible_and_set_new_height (primary_win_info
, new_height
);
1275 if (primary_win_info
->generic
.type
== CMD_WIN
)
1277 win_info
= (tui_source_windows ())->list
[0];
1278 src_win_info
= win_info
;
1282 win_info
= tui_win_list
[CMD_WIN
];
1283 src_win_info
= primary_win_info
;
1285 make_invisible_and_set_new_height (win_info
,
1286 win_info
->generic
.height
+ diff
);
1287 TUI_CMD_WIN
->generic
.origin
.y
= locator
->origin
.y
+ 1;
1288 make_visible_with_new_height (win_info
);
1289 make_visible_with_new_height (primary_win_info
);
1290 if (src_win_info
->generic
.content_size
<= 0)
1291 tui_erase_source_content (src_win_info
, EMPTY_SOURCE_PROMPT
);
1295 struct tui_win_info
*first_win
;
1296 struct tui_win_info
*second_win
;
1298 if (cur_layout
== SRC_DISASSEM_COMMAND
)
1300 first_win
= TUI_SRC_WIN
;
1301 second_win
= TUI_DISASM_WIN
;
1305 first_win
= TUI_DATA_WIN
;
1306 second_win
= (tui_source_windows ())->list
[0];
1308 if (primary_win_info
== TUI_CMD_WIN
)
1309 { /* Split the change in height accross the 1st & 2nd
1310 windows, adjusting them as well. */
1311 /* Subtract the locator. */
1312 int first_split_diff
= diff
/ 2;
1313 int second_split_diff
= first_split_diff
;
1317 if (first_win
->generic
.height
>
1318 second_win
->generic
.height
)
1326 second_split_diff
--;
1328 second_split_diff
++;
1331 /* Make sure that the minimum hieghts are
1333 while ((first_win
->generic
.height
+ first_split_diff
) < 3)
1336 second_split_diff
--;
1338 while ((second_win
->generic
.height
+ second_split_diff
) < 3)
1340 second_split_diff
++;
1343 make_invisible_and_set_new_height (
1345 first_win
->generic
.height
+ first_split_diff
);
1346 second_win
->generic
.origin
.y
= first_win
->generic
.height
- 1;
1347 make_invisible_and_set_new_height (second_win
,
1348 second_win
->generic
.height
1349 + second_split_diff
);
1350 TUI_CMD_WIN
->generic
.origin
.y
= locator
->origin
.y
+ 1;
1351 make_invisible_and_set_new_height (TUI_CMD_WIN
, new_height
);
1355 if ((TUI_CMD_WIN
->generic
.height
+ diff
) < 1)
1356 { /* If there is no way to increase the command
1357 window take real estate from the 1st or 2nd
1359 if ((TUI_CMD_WIN
->generic
.height
+ diff
) < 1)
1363 for (i
= TUI_CMD_WIN
->generic
.height
+ diff
;
1365 if (primary_win_info
== first_win
)
1366 second_win
->generic
.height
--;
1368 first_win
->generic
.height
--;
1371 if (primary_win_info
== first_win
)
1372 make_invisible_and_set_new_height (first_win
, new_height
);
1374 make_invisible_and_set_new_height (
1376 first_win
->generic
.height
);
1377 second_win
->generic
.origin
.y
= first_win
->generic
.height
- 1;
1378 if (primary_win_info
== second_win
)
1379 make_invisible_and_set_new_height (second_win
, new_height
);
1381 make_invisible_and_set_new_height (
1382 second_win
, second_win
->generic
.height
);
1383 TUI_CMD_WIN
->generic
.origin
.y
= locator
->origin
.y
+ 1;
1384 if ((TUI_CMD_WIN
->generic
.height
+ diff
) < 1)
1385 make_invisible_and_set_new_height (TUI_CMD_WIN
, 1);
1387 make_invisible_and_set_new_height (TUI_CMD_WIN
,
1388 TUI_CMD_WIN
->generic
.height
+ diff
);
1390 make_visible_with_new_height (TUI_CMD_WIN
);
1391 make_visible_with_new_height (second_win
);
1392 make_visible_with_new_height (first_win
);
1393 if (first_win
->generic
.content_size
<= 0)
1394 tui_erase_source_content (first_win
, EMPTY_SOURCE_PROMPT
);
1395 if (second_win
->generic
.content_size
<= 0)
1396 tui_erase_source_content (second_win
, EMPTY_SOURCE_PROMPT
);
1405 /* Function make the target window (and auxillary windows associated
1406 with the targer) invisible, and set the new height and
1409 make_invisible_and_set_new_height (struct tui_win_info
*win_info
,
1413 struct tui_gen_win_info
*gen_win_info
;
1415 tui_make_invisible (&win_info
->generic
);
1416 win_info
->generic
.height
= height
;
1418 win_info
->generic
.viewport_height
= height
- 1;
1420 win_info
->generic
.viewport_height
= height
;
1421 if (win_info
!= TUI_CMD_WIN
)
1422 win_info
->generic
.viewport_height
--;
1424 /* Now deal with the auxillary windows associated with win_info. */
1425 switch (win_info
->generic
.type
)
1429 gen_win_info
= win_info
->detail
.source_info
.execution_info
;
1430 tui_make_invisible (gen_win_info
);
1431 gen_win_info
->height
= height
;
1432 gen_win_info
->origin
.y
= win_info
->generic
.origin
.y
;
1434 gen_win_info
->viewport_height
= height
- 1;
1436 gen_win_info
->viewport_height
= height
;
1437 if (win_info
!= TUI_CMD_WIN
)
1438 gen_win_info
->viewport_height
--;
1440 if (tui_win_has_locator (win_info
))
1442 gen_win_info
= tui_locator_win_info_ptr ();
1443 tui_make_invisible (gen_win_info
);
1444 gen_win_info
->origin
.y
= win_info
->generic
.origin
.y
+ height
;
1448 /* Delete all data item windows. */
1449 for (i
= 0; i
< win_info
->generic
.content_size
; i
++)
1451 gen_win_info
= (struct tui_gen_win_info
*)
1452 &((struct tui_win_element
*)
1453 win_info
->generic
.content
[i
])->which_element
.data_window
;
1454 tui_delete_win (gen_win_info
->handle
);
1455 gen_win_info
->handle
= NULL
;
1464 /* Function to make the windows with new heights visible. This means
1465 re-creating the windows' content since the window had to be
1466 destroyed to be made invisible. */
1468 make_visible_with_new_height (struct tui_win_info
*win_info
)
1472 tui_make_visible (&win_info
->generic
);
1473 tui_check_and_display_highlight_if_needed (win_info
);
1474 switch (win_info
->generic
.type
)
1478 tui_free_win_content (win_info
->detail
.source_info
.execution_info
);
1479 tui_make_visible (win_info
->detail
.source_info
.execution_info
);
1480 if (win_info
->generic
.content
!= NULL
)
1482 struct gdbarch
*gdbarch
= win_info
->detail
.source_info
.gdbarch
;
1483 struct tui_line_or_address line_or_addr
;
1484 struct symtab_and_line cursal
1485 = get_current_source_symtab_and_line ();
1487 line_or_addr
= win_info
->detail
.source_info
.start_line_or_addr
;
1488 tui_free_win_content (&win_info
->generic
);
1489 tui_update_source_window (win_info
, gdbarch
,
1490 cursal
.symtab
, line_or_addr
, TRUE
);
1492 else if (deprecated_safe_get_selected_frame () != NULL
)
1494 struct tui_line_or_address line
;
1495 struct symtab_and_line cursal
1496 = get_current_source_symtab_and_line ();
1497 struct frame_info
*frame
= deprecated_safe_get_selected_frame ();
1498 struct gdbarch
*gdbarch
= get_frame_arch (frame
);
1500 s
= find_pc_line_symtab (get_frame_pc (frame
));
1501 if (win_info
->generic
.type
== SRC_WIN
)
1503 line
.loa
= LOA_LINE
;
1504 line
.u
.line_no
= cursal
.line
;
1508 line
.loa
= LOA_ADDRESS
;
1509 find_line_pc (s
, cursal
.line
, &line
.u
.addr
);
1511 tui_update_source_window (win_info
, gdbarch
, s
, line
, TRUE
);
1513 if (tui_win_has_locator (win_info
))
1515 tui_make_visible (tui_locator_win_info_ptr ());
1516 tui_show_locator_content ();
1520 tui_display_all_data ();
1524 wresize (TUI_CMD_WIN
->generic
.handle
,
1525 TUI_CMD_WIN
->generic
.height
,
1526 TUI_CMD_WIN
->generic
.width
);
1528 mvwin (TUI_CMD_WIN
->generic
.handle
,
1529 TUI_CMD_WIN
->generic
.origin
.y
,
1530 TUI_CMD_WIN
->generic
.origin
.x
);
1531 wmove (win_info
->generic
.handle
, 0, 0);
1540 new_height_ok (struct tui_win_info
*primary_win_info
,
1543 int ok
= (new_height
< tui_term_height ());
1548 enum tui_layout_type cur_layout
= tui_current_layout ();
1550 diff
= (new_height
- primary_win_info
->generic
.height
) * (-1);
1551 if (cur_layout
== SRC_COMMAND
|| cur_layout
== DISASSEM_COMMAND
)
1553 ok
= ((primary_win_info
->generic
.type
== CMD_WIN
1554 && new_height
<= (tui_term_height () - 4)
1555 && new_height
>= MIN_CMD_WIN_HEIGHT
)
1556 || (primary_win_info
->generic
.type
!= CMD_WIN
1557 && new_height
<= (tui_term_height () - 2)
1558 && new_height
>= MIN_WIN_HEIGHT
));
1560 { /* Check the total height. */
1561 struct tui_win_info
*win_info
;
1563 if (primary_win_info
== TUI_CMD_WIN
)
1564 win_info
= (tui_source_windows ())->list
[0];
1566 win_info
= TUI_CMD_WIN
;
1568 (win_info
->generic
.height
+ diff
)) <= tui_term_height ());
1573 int cur_total_height
, total_height
, min_height
= 0;
1574 struct tui_win_info
*first_win
;
1575 struct tui_win_info
*second_win
;
1577 if (cur_layout
== SRC_DISASSEM_COMMAND
)
1579 first_win
= TUI_SRC_WIN
;
1580 second_win
= TUI_DISASM_WIN
;
1584 first_win
= TUI_DATA_WIN
;
1585 second_win
= (tui_source_windows ())->list
[0];
1587 /* We could simply add all the heights to obtain the same
1588 result but below is more explicit since we subtract 1 for
1589 the line that the first and second windows share, and add
1590 one for the locator. */
1591 total_height
= cur_total_height
=
1592 (first_win
->generic
.height
+ second_win
->generic
.height
- 1)
1593 + TUI_CMD_WIN
->generic
.height
+ 1; /* Locator. */
1594 if (primary_win_info
== TUI_CMD_WIN
)
1596 /* Locator included since first & second win share a line. */
1597 ok
= ((first_win
->generic
.height
+
1598 second_win
->generic
.height
+ diff
) >=
1599 (MIN_WIN_HEIGHT
* 2)
1600 && new_height
>= MIN_CMD_WIN_HEIGHT
);
1603 total_height
= new_height
+
1604 (first_win
->generic
.height
+
1605 second_win
->generic
.height
+ diff
);
1606 min_height
= MIN_CMD_WIN_HEIGHT
;
1611 min_height
= MIN_WIN_HEIGHT
;
1613 /* First see if we can increase/decrease the command
1614 window. And make sure that the command window is at
1616 ok
= ((TUI_CMD_WIN
->generic
.height
+ diff
) > 0);
1618 { /* Looks like we have to increase/decrease one of
1619 the other windows. */
1620 if (primary_win_info
== first_win
)
1621 ok
= (second_win
->generic
.height
+ diff
) >= min_height
;
1623 ok
= (first_win
->generic
.height
+ diff
) >= min_height
;
1627 if (primary_win_info
== first_win
)
1628 total_height
= new_height
+
1629 second_win
->generic
.height
+
1630 TUI_CMD_WIN
->generic
.height
+ diff
;
1632 total_height
= new_height
+
1633 first_win
->generic
.height
+
1634 TUI_CMD_WIN
->generic
.height
+ diff
;
1637 /* Now make sure that the proposed total height doesn't
1638 exceed the old total height. */
1640 ok
= (new_height
>= min_height
1641 && total_height
<= cur_total_height
);
1650 parse_scrolling_args (const char *arg
,
1651 struct tui_win_info
**win_to_scroll
,
1656 *win_to_scroll
= tui_win_with_focus ();
1658 /* First set up the default window to scroll, in case there is no
1660 if (arg
!= (char *) NULL
)
1664 /* Process the number of lines to scroll. */
1665 std::string copy
= arg
;
1667 if (isdigit (*buf_ptr
))
1672 buf_ptr
= strchr (buf_ptr
, ' ');
1673 if (buf_ptr
!= (char *) NULL
)
1675 *buf_ptr
= (char) 0;
1677 *num_to_scroll
= atoi (num_str
);
1680 else if (num_to_scroll
)
1681 *num_to_scroll
= atoi (num_str
);
1684 /* Process the window name if one is specified. */
1685 if (buf_ptr
!= (char *) NULL
)
1689 if (*buf_ptr
== ' ')
1690 while (*(++buf_ptr
) == ' ')
1693 if (*buf_ptr
!= (char) 0)
1695 /* Validate the window name. */
1696 for (char *p
= buf_ptr
; *p
!= '\0'; p
++)
1704 *win_to_scroll
= tui_partial_win_by_name (wname
);
1706 if (*win_to_scroll
== (struct tui_win_info
*) NULL
1707 || !(*win_to_scroll
)->generic
.is_visible
)
1708 error (_("Invalid window specified. \n\
1709 The window name specified must be valid and visible.\n"));
1710 else if (*win_to_scroll
== TUI_CMD_WIN
)
1711 *win_to_scroll
= (tui_source_windows ())->list
[0];