* defs.h (read_command_lines, query_hook): Update prototypes.

(readline_begin_hook, readline_hook, readline_end_hook): Declare.
	* breakpoint.c (commands_command): Build message in temporary buffer
	and pass that, as well as tty control flag, to read_command_lines.
	* top.c (readline_begin_hook, readline_hook, readline_end_hook):
	Define here.
	(command_loop): Check for non-NULL instream before looping.
	(command_line_input): Use readline_hook when appropriate, to get
	user input from a GUI window.
	(read_next_line): Also build prompt if getting user input from a GUI.
	(recurse_read_control_structure): Fix typo in comment.
	(read_command_lines): Use passed in prompt and tty flag to decide how
	to build message.  Use readline_begin_hook when appropriate, to set
	up a GUI interaction window.  Just return head, whether NULL or not,
	after using readline_end_hook to complete GUI interaction.
	(define_command, document_command): Build message in a temporary
	buffer and pass it to read_command_lines, along with tty flag.
	* gdbtk.c (gdbtk_readline_begin, gdbtk_readline, gdbtk_readline_end):
	New functions.
	(tk_command_loop): Set instream to NULL to enable Tk user interaction.
	(gdbtk_init): Set readline_begin_hook, readline_hook,
	and readline_end_hook.
	* gdbtk.tcl (gdbtk_tcl_readline_begin, gdbtk_tcl_readline,
	gdbtk_tcl_readline_end): New functions.
	(tclsh): Pack scroll bar on right side of window, not left.
PR 9385
This commit is contained in:
Fred Fish 1996-05-20 02:05:55 +00:00
parent 4242ac27a5
commit 41756e56ee
5 changed files with 241 additions and 33 deletions

View File

@ -1,3 +1,34 @@
Sun May 19 16:49:37 1996 Fred Fish <fnf@cygnus.com>
* defs.h (read_command_lines, query_hook): Update prototypes.
(readline_begin_hook, readline_hook, readline_end_hook): Declare.
* breakpoint.c (commands_command): Build message in temporary buffer
and pass that, as well as tty control flag, to read_command_lines.
* top.c (readline_begin_hook, readline_hook, readline_end_hook):
Define here.
(command_loop): Check for non-NULL instream before looping.
(command_line_input): Use readline_hook when appropriate, to get
user input from a GUI window.
(read_next_line): Also build prompt if getting user input from a GUI.
(recurse_read_control_structure): Fix typo in comment.
(read_command_lines): Use passed in prompt and tty flag to decide how
to build message. Use readline_begin_hook when appropriate, to set
up a GUI interaction window. Just return head, whether NULL or not,
after using readline_end_hook to complete GUI interaction.
(define_command, document_command): Build message in a temporary
buffer and pass it to read_command_lines, along with tty flag.
start-sanitize-gdbtk
* gdbtk.c (gdbtk_readline_begin, gdbtk_readline, gdbtk_readline_end):
New functions.
(tk_command_loop): Set instream to NULL to enable Tk user interaction.
(gdbtk_init): Set readline_begin_hook, readline_hook,
and readline_end_hook.
* gdbtk.tcl (gdbtk_tcl_readline_begin, gdbtk_tcl_readline,
gdbtk_tcl_readline_end): New functions.
(tclsh): Pack scroll bar on right side of window, not left.
end-sanitize-gdbtk
Sat May 18 02:43:58 1996 Peter Schauer (pes@regent.e-technik.tu-muenchen.de)
* blockframe.c (frameless_look_for_prologue):

View File

@ -330,10 +330,9 @@ commands_command (arg, from_tty)
ALL_BREAKPOINTS (b)
if (b->number == bnum)
{
if (from_tty && input_from_terminal_p ())
printf_filtered ("Type commands for when breakpoint %d is hit, one per line.\n\
End with a line saying just \"end\".\n", bnum);
l = read_command_lines ();
char tmpbuf[128];
sprintf (tmpbuf, "Type commands for when breakpoint %d is hit, one per line.", bnum);
l = read_command_lines (tmpbuf, from_tty);
free_command_lines (&b->commands);
b->commands = l;
breakpoints_changed ();

View File

@ -183,6 +183,64 @@ gdbtk_query (query, args)
val = atol (interp->result);
return val;
}
/* VARARGS */
static void
#ifdef ANSI_PROTOTYPES
gdbtk_readline_begin (char *format, ...)
#else
gdbtk_readline_begin (va_alist)
va_dcl
#endif
{
va_list args;
char buf[200], *merge[2];
char *command;
#ifdef ANSI_PROTOTYPES
va_start (args, format);
#else
char *format;
va_start (args);
format = va_arg (args, char *);
#endif
vsprintf (buf, format, args);
merge[0] = "gdbtk_tcl_readline_begin";
merge[1] = buf;
command = Tcl_Merge (2, merge);
Tcl_Eval (interp, command);
free (command);
}
static char *
gdbtk_readline (prompt)
char *prompt;
{
char *merge[2];
char *command;
merge[0] = "gdbtk_tcl_readline";
merge[1] = prompt;
command = Tcl_Merge (2, merge);
if (Tcl_Eval (interp, command) == TCL_OK)
{
return (strdup (interp -> result));
}
else
{
gdbtk_fputs (interp -> result, gdb_stdout);
gdbtk_fputs ("\n", gdb_stdout);
return (NULL);
}
}
static void
gdbtk_readline_end ()
{
Tcl_Eval (interp, "gdbtk_tcl_readline_end");
}
static void
#ifdef ANSI_PROTOTYPES
@ -1117,6 +1175,10 @@ gdbtk_call_command (cmdblk, arg, from_tty)
static void
tk_command_loop ()
{
extern GDB_FILE *instream;
/* We no longer want to use stdin as the command input stream */
instream = NULL;
Tcl_Eval (interp, "gdbtk_tcl_preloop");
Tk_MainLoop ();
}
@ -1180,6 +1242,9 @@ gdbtk_init ()
interactive_hook = gdbtk_interactive;
target_wait_hook = gdbtk_wait;
call_command_hook = gdbtk_call_command;
readline_begin_hook = gdbtk_readline_begin;
readline_hook = gdbtk_readline;
readline_end_hook = gdbtk_readline_end;
/* Get the file descriptor for the X server */

View File

@ -265,6 +265,86 @@ proc gdbtk_tcl_breakpoint {action bpnum} {
${action}_breakpoint $bpnum $file $line $pc
}
#
# GDB Callback:
#
# gdbtk_tcl_readline_begin (message) - Notify Tk to open an interaction
# window and start gathering user input
#
# Description:
#
# GDB calls this to notify TK that it needs to open an interaction
# window, displaying the given message, and be prepared to accept
# calls to gdbtk_tcl_readline to gather user input.
proc gdbtk_tcl_readline_begin {message} {
global readline_text
# If another readline window already exists, just bring it to the front.
if {[winfo exists .rl]} {raise .rl ; return}
# Create top level frame with scrollbar and text widget.
toplevel .rl
wm title .rl "Interaction Window"
wm iconname .rl "Input"
message .rl.msg -text $message -aspect 7500 -justify left
text .rl.text -width 80 -height 20 -setgrid true -cursor hand2 \
-yscrollcommand {.rl.scroll set}
scrollbar .rl.scroll -command {.rl.text yview}
pack .rl.msg -side top -fill x
pack .rl.scroll -side right -fill y
pack .rl.text -side left -fill both -expand true
# When the user presses return, get the text from the command start mark to the
# current insert point, stash it in the readline text variable, and update the
# command start mark to the current insert point
bind .rl.text <Return> {
set readline_text [.rl.text get cmdstart {end - 1 char}]
.rl.text mark set cmdstart insert
}
bindtags .rl.text {.rl.text Text all}
}
#
# GDB Callback:
#
# gdbtk_tcl_readline (prompt) - Get one user input line
#
# Description:
#
# GDB calls this to get one line of input from the user interaction
# window, using "prompt" as the command line prompt.
proc gdbtk_tcl_readline {prompt} {
global readline_text
.rl.text insert end $prompt
.rl.text mark set cmdstart insert
.rl.text mark gravity cmdstart left
.rl.text see insert
# Make this window the current one for input.
focus .rl.text
grab .rl
tkwait variable readline_text
grab release .rl
return $readline_text
}
#
# GDB Callback:
#
# gdbtk_tcl_readline_end - Terminate a user interaction
#
# Description:
#
# GDB calls this when it is done getting interactive user input.
# Destroy the interaction window.
proc gdbtk_tcl_readline_end {} {
if {[winfo exists .rl]} { destroy .rl }
}
proc create_breakpoints_window {} {
global bpframe_lasty
@ -3149,8 +3229,8 @@ proc tclsh {} {
text .eval.text -width 80 -height 20 -setgrid true -cursor hand2 \
-yscrollcommand {.eval.scroll set}
scrollbar .eval.scroll -command {.eval.text yview}
pack .eval.scroll -side left -fill y
pack .eval.text -side right -fill both -expand true
pack .eval.scroll -side right -fill y
pack .eval.text -side left -fill both -expand true
# Insert the tcl_prompt and initialize the cmdstart mark
.eval.text insert insert $tcl_prompt

View File

@ -275,7 +275,7 @@ struct cmd_list_element *showchecklist;
/* stdio stream that command input is being read from. Set to stdin normally.
Set by source_command to the file we are sourcing. Set to NULL if we are
executing a user-defined command. */
executing a user-defined command or interacting via a GUI. */
FILE *instream;
@ -395,6 +395,21 @@ int (*query_hook) PARAMS (());
void (*flush_hook) PARAMS ((FILE *stream));
/* These three functions support getting lines of text from the user. They
are used in sequence. First readline_begin_hook is called with a text
string that might be (for example) a message for the user to type in a
sequence of commands to be executed at a breakpoint. If this function
calls back to a GUI, it might take this opportunity to pop up a text
interaction window with this message. Next, readline_hook is called
with a prompt that is emitted prior to collecting the user input.
It can be called multiple times. Finally, readline_end_hook is called
to notify the GUI that we are done with the interaction window and it
can close it. */
void (*readline_begin_hook) PARAMS ((char *, ...));
char * (*readline_hook) PARAMS ((char *));
void (*readline_end_hook) PARAMS ((void));
/* Called as appropriate to notify the interface of the specified breakpoint
conditions. */
@ -1237,7 +1252,7 @@ command_loop ()
extern int display_time;
extern int display_space;
while (!feof (instream))
while (instream && !feof (instream))
{
if (window_hook && instream == stdin)
(*window_hook) (instream, prompt);
@ -1962,11 +1977,18 @@ command_line_input (prrompt, repeat, annotation_suffix)
}
/* Don't use fancy stuff if not talking to stdin. */
if (command_editing_p && instream == stdin
&& ISATTY (instream))
rl = readline (local_prompt);
if (readline_hook && instream == NULL)
{
rl = (*readline_hook) (local_prompt);
}
else if (command_editing_p && instream == stdin && ISATTY (instream))
{
rl = readline (local_prompt);
}
else
rl = gdb_readline (local_prompt);
{
rl = gdb_readline (local_prompt);
}
if (annotation_level > 1 && instream == stdin)
{
@ -2138,7 +2160,7 @@ read_next_line (command)
error ("Control nesting too deep!\n");
/* Set a prompt based on the nesting of the control commands. */
if (instream == stdin)
if (instream == stdin || (instream == 0 && readline_hook != NULL))
{
for (i = 0; i < control_level; i++)
control_prompt[i] = ' ';
@ -2220,7 +2242,7 @@ read_next_line (command)
}
/* Recursively read in the control structures and create a command_line
tructure from them.
structure from them.
The parent_control parameter is the control structure in which the
following commands are nested. */
@ -2331,19 +2353,34 @@ recurse_read_control_structure (current_cmd)
return ret;
}
/* Read lines from the input stream and accumulate them in a chain of
struct command_line's, which is then returned. For input from a
terminal, the special command "end" is used to mark the end of the
input, and is not included in the returned chain of commands. */
/* Read lines from the input stream
and accumulate them in a chain of struct command_line's
which is then returned. */
#define END_MESSAGE "End with a line saying just \"end\"."
struct command_line *
read_command_lines ()
read_command_lines (prompt, from_tty)
char *prompt;
int from_tty;
{
struct command_line *head, *tail, *next;
struct cleanup *old_chain;
enum command_control_type ret;
enum misc_command_type val;
if (readline_begin_hook)
{
/* Note - intentional to merge messages with no newline */
(*readline_begin_hook) ("%s %s\n", prompt, END_MESSAGE);
}
else if (from_tty && input_from_terminal_p ())
{
printf_unfiltered ("%s\n%s\n", prompt, END_MESSAGE);
gdb_flush (gdb_stdout);
}
head = tail = NULL;
old_chain = NULL;
@ -2397,13 +2434,16 @@ read_command_lines ()
if (ret != invalid_control)
{
discard_cleanups (old_chain);
return head;
}
else
do_cleanups (old_chain);
}
return NULL;
if (readline_end_hook)
{
(*readline_end_hook) ();
}
return (head);
}
/* Free a chain of struct command_line's. */
@ -2579,6 +2619,7 @@ define_command (comname, from_tty)
register struct command_line *cmds;
register struct cmd_list_element *c, *newc, *hookc = 0;
char *tem = comname;
char tmpbuf[128];
#define HOOK_STRING "hook-"
#define HOOK_LEN 5
@ -2626,15 +2667,9 @@ define_command (comname, from_tty)
for (tem = comname; *tem; tem++)
if (isupper(*tem)) *tem = tolower(*tem);
if (from_tty)
{
printf_unfiltered ("Type commands for definition of \"%s\".\n\
End with a line saying just \"end\".\n", comname);
gdb_flush (gdb_stdout);
}
control_level = 0;
cmds = read_command_lines ();
sprintf (tmpbuf, "Type commands for definition of \"%s\".", comname);
cmds = read_command_lines (tmpbuf, from_tty);
if (c && c->class == class_user)
free_command_lines (&c->user_commands);
@ -2661,6 +2696,7 @@ document_command (comname, from_tty)
struct command_line *doclines;
register struct cmd_list_element *c;
char *tem = comname;
char tmpbuf[128];
validate_comname (comname);
@ -2669,11 +2705,8 @@ document_command (comname, from_tty)
if (c->class != class_user)
error ("Command \"%s\" is built-in.", comname);
if (from_tty)
printf_unfiltered ("Type documentation for \"%s\".\n\
End with a line saying just \"end\".\n", comname);
doclines = read_command_lines ();
sprintf (tmpbuf, "Type documentation for \"%s\".", comname);
doclines = read_command_lines (tmpbuf, from_tty);
if (c->doc) free (c->doc);