xref: /dflybsd-src/contrib/gdb-7/gdb/mi/mi-interp.c (revision de8e141f24382815c10a4012d209bbbf7abf1112)
15796c8dcSSimon Schubert /* MI Interpreter Definitions and Commands for GDB, the GNU debugger.
25796c8dcSSimon Schubert 
3*ef5ccd6cSJohn Marino    Copyright (C) 2002-2013 Free Software Foundation, Inc.
45796c8dcSSimon Schubert 
55796c8dcSSimon Schubert    This file is part of GDB.
65796c8dcSSimon Schubert 
75796c8dcSSimon Schubert    This program is free software; you can redistribute it and/or modify
85796c8dcSSimon Schubert    it under the terms of the GNU General Public License as published by
95796c8dcSSimon Schubert    the Free Software Foundation; either version 3 of the License, or
105796c8dcSSimon Schubert    (at your option) any later version.
115796c8dcSSimon Schubert 
125796c8dcSSimon Schubert    This program is distributed in the hope that it will be useful,
135796c8dcSSimon Schubert    but WITHOUT ANY WARRANTY; without even the implied warranty of
145796c8dcSSimon Schubert    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
155796c8dcSSimon Schubert    GNU General Public License for more details.
165796c8dcSSimon Schubert 
175796c8dcSSimon Schubert    You should have received a copy of the GNU General Public License
185796c8dcSSimon Schubert    along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
195796c8dcSSimon Schubert 
205796c8dcSSimon Schubert #include "defs.h"
215796c8dcSSimon Schubert #include "gdb_string.h"
225796c8dcSSimon Schubert #include "interps.h"
235796c8dcSSimon Schubert #include "event-top.h"
245796c8dcSSimon Schubert #include "event-loop.h"
255796c8dcSSimon Schubert #include "inferior.h"
265796c8dcSSimon Schubert #include "ui-out.h"
275796c8dcSSimon Schubert #include "top.h"
285796c8dcSSimon Schubert #include "exceptions.h"
295796c8dcSSimon Schubert #include "mi-main.h"
305796c8dcSSimon Schubert #include "mi-cmds.h"
315796c8dcSSimon Schubert #include "mi-out.h"
325796c8dcSSimon Schubert #include "mi-console.h"
335796c8dcSSimon Schubert #include "mi-common.h"
345796c8dcSSimon Schubert #include "observer.h"
355796c8dcSSimon Schubert #include "gdbthread.h"
365796c8dcSSimon Schubert #include "solist.h"
37a45ae5f8SJohn Marino #include "gdb.h"
38*ef5ccd6cSJohn Marino #include "objfiles.h"
39*ef5ccd6cSJohn Marino #include "tracepoint.h"
405796c8dcSSimon Schubert 
41*ef5ccd6cSJohn Marino /* These are the interpreter setup, etc. functions for the MI
42*ef5ccd6cSJohn Marino    interpreter.  */
43*ef5ccd6cSJohn Marino 
44*ef5ccd6cSJohn Marino static void mi_execute_command_wrapper (const char *cmd);
45*ef5ccd6cSJohn Marino static void mi_execute_command_input_handler (char *cmd);
465796c8dcSSimon Schubert static void mi_command_loop (int mi_version);
475796c8dcSSimon Schubert 
485796c8dcSSimon Schubert /* These are hooks that we put in place while doing interpreter_exec
49*ef5ccd6cSJohn Marino    so we can report interesting things that happened "behind the MI's
50*ef5ccd6cSJohn Marino    back" in this command.  */
51*ef5ccd6cSJohn Marino 
525796c8dcSSimon Schubert static int mi_interp_query_hook (const char *ctlstr, va_list ap)
53cf7f2e2dSJohn Marino   ATTRIBUTE_PRINTF (1, 0);
545796c8dcSSimon Schubert 
555796c8dcSSimon Schubert static void mi3_command_loop (void);
565796c8dcSSimon Schubert static void mi2_command_loop (void);
575796c8dcSSimon Schubert static void mi1_command_loop (void);
585796c8dcSSimon Schubert 
595796c8dcSSimon Schubert static void mi_insert_notify_hooks (void);
605796c8dcSSimon Schubert static void mi_remove_notify_hooks (void);
615796c8dcSSimon Schubert static void mi_on_normal_stop (struct bpstats *bs, int print_frame);
625796c8dcSSimon Schubert 
635796c8dcSSimon Schubert static void mi_new_thread (struct thread_info *t);
645796c8dcSSimon Schubert static void mi_thread_exit (struct thread_info *t, int silent);
65*ef5ccd6cSJohn Marino static void mi_record_changed (struct inferior*, int);
66cf7f2e2dSJohn Marino static void mi_inferior_added (struct inferior *inf);
67cf7f2e2dSJohn Marino static void mi_inferior_appeared (struct inferior *inf);
68cf7f2e2dSJohn Marino static void mi_inferior_exit (struct inferior *inf);
69cf7f2e2dSJohn Marino static void mi_inferior_removed (struct inferior *inf);
705796c8dcSSimon Schubert static void mi_on_resume (ptid_t ptid);
715796c8dcSSimon Schubert static void mi_solib_loaded (struct so_list *solib);
725796c8dcSSimon Schubert static void mi_solib_unloaded (struct so_list *solib);
735796c8dcSSimon Schubert static void mi_about_to_proceed (void);
74*ef5ccd6cSJohn Marino static void mi_traceframe_changed (int tfnum, int tpnum);
75*ef5ccd6cSJohn Marino static void mi_tsv_created (const struct trace_state_variable *tsv);
76*ef5ccd6cSJohn Marino static void mi_tsv_deleted (const struct trace_state_variable *tsv);
77*ef5ccd6cSJohn Marino static void mi_tsv_modified (const struct trace_state_variable *tsv);
78a45ae5f8SJohn Marino static void mi_breakpoint_created (struct breakpoint *b);
79a45ae5f8SJohn Marino static void mi_breakpoint_deleted (struct breakpoint *b);
80a45ae5f8SJohn Marino static void mi_breakpoint_modified (struct breakpoint *b);
81*ef5ccd6cSJohn Marino static void mi_command_param_changed (const char *param, const char *value);
82*ef5ccd6cSJohn Marino static void mi_memory_changed (struct inferior *inf, CORE_ADDR memaddr,
83*ef5ccd6cSJohn Marino 			       ssize_t len, const bfd_byte *myaddr);
845796c8dcSSimon Schubert 
85cf7f2e2dSJohn Marino static int report_initial_inferior (struct inferior *inf, void *closure);
86cf7f2e2dSJohn Marino 
875796c8dcSSimon Schubert static void *
mi_interpreter_init(struct interp * interp,int top_level)88a45ae5f8SJohn Marino mi_interpreter_init (struct interp *interp, int top_level)
895796c8dcSSimon Schubert {
905796c8dcSSimon Schubert   struct mi_interp *mi = XMALLOC (struct mi_interp);
91a45ae5f8SJohn Marino   const char *name;
92a45ae5f8SJohn Marino   int mi_version;
935796c8dcSSimon Schubert 
94*ef5ccd6cSJohn Marino   /* Assign the output channel created at startup to its own global,
95*ef5ccd6cSJohn Marino      so that we can create a console channel that encapsulates and
96*ef5ccd6cSJohn Marino      prefixes all gdb_output-type bits coming from the rest of the
97*ef5ccd6cSJohn Marino      debugger.  */
985796c8dcSSimon Schubert 
99*ef5ccd6cSJohn Marino   raw_stdout = gdb_stdout;
1005796c8dcSSimon Schubert 
101*ef5ccd6cSJohn Marino   /* Create MI console channels, each with a different prefix so they
102*ef5ccd6cSJohn Marino      can be distinguished.  */
1035796c8dcSSimon Schubert   mi->out = mi_console_file_new (raw_stdout, "~", '"');
1045796c8dcSSimon Schubert   mi->err = mi_console_file_new (raw_stdout, "&", '"');
1055796c8dcSSimon Schubert   mi->log = mi->err;
1065796c8dcSSimon Schubert   mi->targ = mi_console_file_new (raw_stdout, "@", '"');
1075796c8dcSSimon Schubert   mi->event_channel = mi_console_file_new (raw_stdout, "=", 0);
1085796c8dcSSimon Schubert 
109a45ae5f8SJohn Marino   name = interp_name (interp);
110a45ae5f8SJohn Marino   /* INTERP_MI selects the most recent released version.  "mi2" was
111a45ae5f8SJohn Marino      released as part of GDB 6.0.  */
112a45ae5f8SJohn Marino   if (strcmp (name, INTERP_MI) == 0)
113a45ae5f8SJohn Marino     mi_version = 2;
114a45ae5f8SJohn Marino   else if (strcmp (name, INTERP_MI1) == 0)
115a45ae5f8SJohn Marino     mi_version = 1;
116a45ae5f8SJohn Marino   else if (strcmp (name, INTERP_MI2) == 0)
117a45ae5f8SJohn Marino     mi_version = 2;
118a45ae5f8SJohn Marino   else if (strcmp (name, INTERP_MI3) == 0)
119a45ae5f8SJohn Marino     mi_version = 3;
120a45ae5f8SJohn Marino   else
121a45ae5f8SJohn Marino     gdb_assert_not_reached ("unhandled MI version");
122a45ae5f8SJohn Marino 
123a45ae5f8SJohn Marino   mi->uiout = mi_out_new (mi_version);
124a45ae5f8SJohn Marino 
1255796c8dcSSimon Schubert   if (top_level)
1265796c8dcSSimon Schubert     {
1275796c8dcSSimon Schubert       observer_attach_new_thread (mi_new_thread);
1285796c8dcSSimon Schubert       observer_attach_thread_exit (mi_thread_exit);
129cf7f2e2dSJohn Marino       observer_attach_inferior_added (mi_inferior_added);
130cf7f2e2dSJohn Marino       observer_attach_inferior_appeared (mi_inferior_appeared);
1315796c8dcSSimon Schubert       observer_attach_inferior_exit (mi_inferior_exit);
132cf7f2e2dSJohn Marino       observer_attach_inferior_removed (mi_inferior_removed);
133*ef5ccd6cSJohn Marino       observer_attach_record_changed (mi_record_changed);
1345796c8dcSSimon Schubert       observer_attach_normal_stop (mi_on_normal_stop);
1355796c8dcSSimon Schubert       observer_attach_target_resumed (mi_on_resume);
1365796c8dcSSimon Schubert       observer_attach_solib_loaded (mi_solib_loaded);
1375796c8dcSSimon Schubert       observer_attach_solib_unloaded (mi_solib_unloaded);
1385796c8dcSSimon Schubert       observer_attach_about_to_proceed (mi_about_to_proceed);
139*ef5ccd6cSJohn Marino       observer_attach_traceframe_changed (mi_traceframe_changed);
140*ef5ccd6cSJohn Marino       observer_attach_tsv_created (mi_tsv_created);
141*ef5ccd6cSJohn Marino       observer_attach_tsv_deleted (mi_tsv_deleted);
142*ef5ccd6cSJohn Marino       observer_attach_tsv_modified (mi_tsv_modified);
143a45ae5f8SJohn Marino       observer_attach_breakpoint_created (mi_breakpoint_created);
144a45ae5f8SJohn Marino       observer_attach_breakpoint_deleted (mi_breakpoint_deleted);
145a45ae5f8SJohn Marino       observer_attach_breakpoint_modified (mi_breakpoint_modified);
146*ef5ccd6cSJohn Marino       observer_attach_command_param_changed (mi_command_param_changed);
147*ef5ccd6cSJohn Marino       observer_attach_memory_changed (mi_memory_changed);
148cf7f2e2dSJohn Marino 
149*ef5ccd6cSJohn Marino       /* The initial inferior is created before this function is
150*ef5ccd6cSJohn Marino 	 called, so we need to report it explicitly.  Use iteration in
151*ef5ccd6cSJohn Marino 	 case future version of GDB creates more than one inferior
152*ef5ccd6cSJohn Marino 	 up-front.  */
153cf7f2e2dSJohn Marino       iterate_over_inferiors (report_initial_inferior, mi);
1545796c8dcSSimon Schubert     }
1555796c8dcSSimon Schubert 
1565796c8dcSSimon Schubert   return mi;
1575796c8dcSSimon Schubert }
1585796c8dcSSimon Schubert 
1595796c8dcSSimon Schubert static int
mi_interpreter_resume(void * data)1605796c8dcSSimon Schubert mi_interpreter_resume (void *data)
1615796c8dcSSimon Schubert {
1625796c8dcSSimon Schubert   struct mi_interp *mi = data;
1635796c8dcSSimon Schubert 
164*ef5ccd6cSJohn Marino   /* As per hack note in mi_interpreter_init, swap in the output
165*ef5ccd6cSJohn Marino      channels... */
1665796c8dcSSimon Schubert   gdb_setup_readline ();
1675796c8dcSSimon Schubert 
1685796c8dcSSimon Schubert   /* These overwrite some of the initialization done in
1695796c8dcSSimon Schubert      _intialize_event_loop.  */
1705796c8dcSSimon Schubert   call_readline = gdb_readline2;
171*ef5ccd6cSJohn Marino   input_handler = mi_execute_command_input_handler;
1725796c8dcSSimon Schubert   add_file_handler (input_fd, stdin_event_handler, 0);
1735796c8dcSSimon Schubert   async_command_editing_p = 0;
1745796c8dcSSimon Schubert   /* FIXME: This is a total hack for now.  PB's use of the MI
1755796c8dcSSimon Schubert      implicitly relies on a bug in the async support which allows
1765796c8dcSSimon Schubert      asynchronous commands to leak through the commmand loop.  The bug
1775796c8dcSSimon Schubert      involves (but is not limited to) the fact that sync_execution was
1785796c8dcSSimon Schubert      erroneously initialized to 0.  Duplicate by initializing it thus
1795796c8dcSSimon Schubert      here...  */
1805796c8dcSSimon Schubert   sync_execution = 0;
1815796c8dcSSimon Schubert 
1825796c8dcSSimon Schubert   gdb_stdout = mi->out;
183*ef5ccd6cSJohn Marino   /* Route error and log output through the MI.  */
1845796c8dcSSimon Schubert   gdb_stderr = mi->err;
1855796c8dcSSimon Schubert   gdb_stdlog = mi->log;
1865796c8dcSSimon Schubert   /* Route target output through the MI.  */
1875796c8dcSSimon Schubert   gdb_stdtarg = mi->targ;
1885796c8dcSSimon Schubert   /* Route target error through the MI as well.  */
1895796c8dcSSimon Schubert   gdb_stdtargerr = mi->targ;
1905796c8dcSSimon Schubert 
1915796c8dcSSimon Schubert   /* Replace all the hooks that we know about.  There really needs to
1925796c8dcSSimon Schubert      be a better way of doing this... */
1935796c8dcSSimon Schubert   clear_interpreter_hooks ();
1945796c8dcSSimon Schubert 
1955796c8dcSSimon Schubert   deprecated_show_load_progress = mi_load_progress;
1965796c8dcSSimon Schubert 
1975796c8dcSSimon Schubert   /* If we're _the_ interpreter, take control.  */
1985796c8dcSSimon Schubert   if (current_interp_named_p (INTERP_MI1))
1995796c8dcSSimon Schubert     deprecated_command_loop_hook = mi1_command_loop;
2005796c8dcSSimon Schubert   else if (current_interp_named_p (INTERP_MI2))
2015796c8dcSSimon Schubert     deprecated_command_loop_hook = mi2_command_loop;
2025796c8dcSSimon Schubert   else if (current_interp_named_p (INTERP_MI3))
2035796c8dcSSimon Schubert     deprecated_command_loop_hook = mi3_command_loop;
2045796c8dcSSimon Schubert   else
2055796c8dcSSimon Schubert     deprecated_command_loop_hook = mi2_command_loop;
2065796c8dcSSimon Schubert 
2075796c8dcSSimon Schubert   return 1;
2085796c8dcSSimon Schubert }
2095796c8dcSSimon Schubert 
2105796c8dcSSimon Schubert static int
mi_interpreter_suspend(void * data)2115796c8dcSSimon Schubert mi_interpreter_suspend (void *data)
2125796c8dcSSimon Schubert {
2135796c8dcSSimon Schubert   gdb_disable_readline ();
2145796c8dcSSimon Schubert   return 1;
2155796c8dcSSimon Schubert }
2165796c8dcSSimon Schubert 
2175796c8dcSSimon Schubert static struct gdb_exception
mi_interpreter_exec(void * data,const char * command)2185796c8dcSSimon Schubert mi_interpreter_exec (void *data, const char *command)
2195796c8dcSSimon Schubert {
220*ef5ccd6cSJohn Marino   mi_execute_command_wrapper (command);
2215796c8dcSSimon Schubert   return exception_none;
2225796c8dcSSimon Schubert }
2235796c8dcSSimon Schubert 
224*ef5ccd6cSJohn Marino /* Never display the default GDB prompt in MI case.  */
225*ef5ccd6cSJohn Marino 
2265796c8dcSSimon Schubert static int
mi_interpreter_prompt_p(void * data)2275796c8dcSSimon Schubert mi_interpreter_prompt_p (void *data)
2285796c8dcSSimon Schubert {
2295796c8dcSSimon Schubert   return 0;
2305796c8dcSSimon Schubert }
2315796c8dcSSimon Schubert 
2325796c8dcSSimon Schubert void
mi_cmd_interpreter_exec(char * command,char ** argv,int argc)2335796c8dcSSimon Schubert mi_cmd_interpreter_exec (char *command, char **argv, int argc)
2345796c8dcSSimon Schubert {
2355796c8dcSSimon Schubert   struct interp *interp_to_use;
2365796c8dcSSimon Schubert   int i;
2375796c8dcSSimon Schubert   char *mi_error_message = NULL;
2385796c8dcSSimon Schubert   struct cleanup *old_chain;
2395796c8dcSSimon Schubert 
2405796c8dcSSimon Schubert   if (argc < 2)
241c50c785cSJohn Marino     error (_("-interpreter-exec: "
242c50c785cSJohn Marino 	     "Usage: -interpreter-exec interp command"));
2435796c8dcSSimon Schubert 
2445796c8dcSSimon Schubert   interp_to_use = interp_lookup (argv[0]);
2455796c8dcSSimon Schubert   if (interp_to_use == NULL)
246c50c785cSJohn Marino     error (_("-interpreter-exec: could not find interpreter \"%s\""),
247c50c785cSJohn Marino 	   argv[0]);
2485796c8dcSSimon Schubert 
2495796c8dcSSimon Schubert   if (!interp_exec_p (interp_to_use))
250c50c785cSJohn Marino     error (_("-interpreter-exec: interpreter \"%s\" "
251c50c785cSJohn Marino 	     "does not support command execution"),
2525796c8dcSSimon Schubert 	      argv[0]);
2535796c8dcSSimon Schubert 
254*ef5ccd6cSJohn Marino   /* Insert the MI out hooks, making sure to also call the
255*ef5ccd6cSJohn Marino      interpreter's hooks if it has any.  */
256*ef5ccd6cSJohn Marino   /* KRS: We shouldn't need this... Events should be installed and
257*ef5ccd6cSJohn Marino      they should just ALWAYS fire something out down the MI
258*ef5ccd6cSJohn Marino      channel.  */
2595796c8dcSSimon Schubert   mi_insert_notify_hooks ();
2605796c8dcSSimon Schubert 
261*ef5ccd6cSJohn Marino   /* Now run the code.  */
2625796c8dcSSimon Schubert 
2635796c8dcSSimon Schubert   old_chain = make_cleanup (null_cleanup, 0);
2645796c8dcSSimon Schubert   for (i = 1; i < argc; i++)
2655796c8dcSSimon Schubert     {
2665796c8dcSSimon Schubert       struct gdb_exception e = interp_exec (interp_to_use, argv[i]);
267cf7f2e2dSJohn Marino 
2685796c8dcSSimon Schubert       if (e.reason < 0)
2695796c8dcSSimon Schubert 	{
2705796c8dcSSimon Schubert 	  mi_error_message = xstrdup (e.message);
2715796c8dcSSimon Schubert 	  make_cleanup (xfree, mi_error_message);
2725796c8dcSSimon Schubert 	  break;
2735796c8dcSSimon Schubert 	}
2745796c8dcSSimon Schubert     }
2755796c8dcSSimon Schubert 
2765796c8dcSSimon Schubert   mi_remove_notify_hooks ();
2775796c8dcSSimon Schubert 
2785796c8dcSSimon Schubert   if (mi_error_message != NULL)
2795796c8dcSSimon Schubert     error ("%s", mi_error_message);
2805796c8dcSSimon Schubert   do_cleanups (old_chain);
2815796c8dcSSimon Schubert }
2825796c8dcSSimon Schubert 
283*ef5ccd6cSJohn Marino /* This inserts a number of hooks that are meant to produce
284*ef5ccd6cSJohn Marino    async-notify ("=") MI messages while running commands in another
285*ef5ccd6cSJohn Marino    interpreter using mi_interpreter_exec.  The canonical use for this
286*ef5ccd6cSJohn Marino    is to allow access to the gdb CLI interpreter from within the MI,
287*ef5ccd6cSJohn Marino    while still producing MI style output when actions in the CLI
288*ef5ccd6cSJohn Marino    command change GDB's state.  */
2895796c8dcSSimon Schubert 
2905796c8dcSSimon Schubert static void
mi_insert_notify_hooks(void)2915796c8dcSSimon Schubert mi_insert_notify_hooks (void)
2925796c8dcSSimon Schubert {
2935796c8dcSSimon Schubert   deprecated_query_hook = mi_interp_query_hook;
2945796c8dcSSimon Schubert }
2955796c8dcSSimon Schubert 
2965796c8dcSSimon Schubert static void
mi_remove_notify_hooks(void)2975796c8dcSSimon Schubert mi_remove_notify_hooks (void)
2985796c8dcSSimon Schubert {
2995796c8dcSSimon Schubert   deprecated_query_hook = NULL;
3005796c8dcSSimon Schubert }
3015796c8dcSSimon Schubert 
3025796c8dcSSimon Schubert static int
mi_interp_query_hook(const char * ctlstr,va_list ap)3035796c8dcSSimon Schubert mi_interp_query_hook (const char *ctlstr, va_list ap)
3045796c8dcSSimon Schubert {
3055796c8dcSSimon Schubert   return 1;
3065796c8dcSSimon Schubert }
3075796c8dcSSimon Schubert 
3085796c8dcSSimon Schubert static void
mi_execute_command_wrapper(const char * cmd)309*ef5ccd6cSJohn Marino mi_execute_command_wrapper (const char *cmd)
3105796c8dcSSimon Schubert {
3115796c8dcSSimon Schubert   mi_execute_command (cmd, stdin == instream);
3125796c8dcSSimon Schubert }
3135796c8dcSSimon Schubert 
314*ef5ccd6cSJohn Marino /* mi_execute_command_wrapper wrapper suitable for INPUT_HANDLER.  */
315*ef5ccd6cSJohn Marino 
316*ef5ccd6cSJohn Marino static void
mi_execute_command_input_handler(char * cmd)317*ef5ccd6cSJohn Marino mi_execute_command_input_handler (char *cmd)
318*ef5ccd6cSJohn Marino {
319*ef5ccd6cSJohn Marino   mi_execute_command_wrapper (cmd);
320*ef5ccd6cSJohn Marino 
321*ef5ccd6cSJohn Marino   fputs_unfiltered ("(gdb) \n", raw_stdout);
322*ef5ccd6cSJohn Marino   gdb_flush (raw_stdout);
323*ef5ccd6cSJohn Marino }
324*ef5ccd6cSJohn Marino 
3255796c8dcSSimon Schubert static void
mi1_command_loop(void)3265796c8dcSSimon Schubert mi1_command_loop (void)
3275796c8dcSSimon Schubert {
3285796c8dcSSimon Schubert   mi_command_loop (1);
3295796c8dcSSimon Schubert }
3305796c8dcSSimon Schubert 
3315796c8dcSSimon Schubert static void
mi2_command_loop(void)3325796c8dcSSimon Schubert mi2_command_loop (void)
3335796c8dcSSimon Schubert {
3345796c8dcSSimon Schubert   mi_command_loop (2);
3355796c8dcSSimon Schubert }
3365796c8dcSSimon Schubert 
3375796c8dcSSimon Schubert static void
mi3_command_loop(void)3385796c8dcSSimon Schubert mi3_command_loop (void)
3395796c8dcSSimon Schubert {
3405796c8dcSSimon Schubert   mi_command_loop (3);
3415796c8dcSSimon Schubert }
3425796c8dcSSimon Schubert 
3435796c8dcSSimon Schubert static void
mi_command_loop(int mi_version)3445796c8dcSSimon Schubert mi_command_loop (int mi_version)
3455796c8dcSSimon Schubert {
3465796c8dcSSimon Schubert   /* Turn off 8 bit strings in quoted output.  Any character with the
3475796c8dcSSimon Schubert      high bit set is printed using C's octal format.  */
3485796c8dcSSimon Schubert   sevenbit_strings = 1;
349*ef5ccd6cSJohn Marino 
350*ef5ccd6cSJohn Marino   /* Tell the world that we're alive.  */
3515796c8dcSSimon Schubert   fputs_unfiltered ("(gdb) \n", raw_stdout);
3525796c8dcSSimon Schubert   gdb_flush (raw_stdout);
353*ef5ccd6cSJohn Marino 
3545796c8dcSSimon Schubert   start_event_loop ();
3555796c8dcSSimon Schubert }
3565796c8dcSSimon Schubert 
3575796c8dcSSimon Schubert static void
mi_new_thread(struct thread_info * t)3585796c8dcSSimon Schubert mi_new_thread (struct thread_info *t)
3595796c8dcSSimon Schubert {
3605796c8dcSSimon Schubert   struct mi_interp *mi = top_level_interpreter_data ();
361cf7f2e2dSJohn Marino   struct inferior *inf = find_inferior_pid (ptid_get_pid (t->ptid));
362cf7f2e2dSJohn Marino 
363cf7f2e2dSJohn Marino   gdb_assert (inf);
3645796c8dcSSimon Schubert 
3655796c8dcSSimon Schubert   fprintf_unfiltered (mi->event_channel,
366cf7f2e2dSJohn Marino 		      "thread-created,id=\"%d\",group-id=\"i%d\"",
367cf7f2e2dSJohn Marino 		      t->num, inf->num);
3685796c8dcSSimon Schubert   gdb_flush (mi->event_channel);
3695796c8dcSSimon Schubert }
3705796c8dcSSimon Schubert 
3715796c8dcSSimon Schubert static void
mi_thread_exit(struct thread_info * t,int silent)3725796c8dcSSimon Schubert mi_thread_exit (struct thread_info *t, int silent)
3735796c8dcSSimon Schubert {
3745796c8dcSSimon Schubert   struct mi_interp *mi;
375cf7f2e2dSJohn Marino   struct inferior *inf;
3765796c8dcSSimon Schubert 
3775796c8dcSSimon Schubert   if (silent)
3785796c8dcSSimon Schubert     return;
3795796c8dcSSimon Schubert 
380cf7f2e2dSJohn Marino   inf = find_inferior_pid (ptid_get_pid (t->ptid));
381cf7f2e2dSJohn Marino 
3825796c8dcSSimon Schubert   mi = top_level_interpreter_data ();
3835796c8dcSSimon Schubert   target_terminal_ours ();
3845796c8dcSSimon Schubert   fprintf_unfiltered (mi->event_channel,
385cf7f2e2dSJohn Marino 		      "thread-exited,id=\"%d\",group-id=\"i%d\"",
386cf7f2e2dSJohn Marino 		      t->num, inf->num);
3875796c8dcSSimon Schubert   gdb_flush (mi->event_channel);
3885796c8dcSSimon Schubert }
3895796c8dcSSimon Schubert 
390*ef5ccd6cSJohn Marino /* Emit notification on changing the state of record.  */
391*ef5ccd6cSJohn Marino 
392*ef5ccd6cSJohn Marino static void
mi_record_changed(struct inferior * inferior,int started)393*ef5ccd6cSJohn Marino mi_record_changed (struct inferior *inferior, int started)
394*ef5ccd6cSJohn Marino {
395*ef5ccd6cSJohn Marino   struct mi_interp *mi = top_level_interpreter_data ();
396*ef5ccd6cSJohn Marino 
397*ef5ccd6cSJohn Marino   fprintf_unfiltered (mi->event_channel,  "record-%s,thread-group=\"i%d\"",
398*ef5ccd6cSJohn Marino 		      started ? "started" : "stopped", inferior->num);
399*ef5ccd6cSJohn Marino 
400*ef5ccd6cSJohn Marino   gdb_flush (mi->event_channel);
401*ef5ccd6cSJohn Marino }
402*ef5ccd6cSJohn Marino 
4035796c8dcSSimon Schubert static void
mi_inferior_added(struct inferior * inf)404cf7f2e2dSJohn Marino mi_inferior_added (struct inferior *inf)
4055796c8dcSSimon Schubert {
4065796c8dcSSimon Schubert   struct mi_interp *mi = top_level_interpreter_data ();
407cf7f2e2dSJohn Marino 
4085796c8dcSSimon Schubert   target_terminal_ours ();
409cf7f2e2dSJohn Marino   fprintf_unfiltered (mi->event_channel,
410cf7f2e2dSJohn Marino 		      "thread-group-added,id=\"i%d\"",
411cf7f2e2dSJohn Marino 		      inf->num);
4125796c8dcSSimon Schubert   gdb_flush (mi->event_channel);
4135796c8dcSSimon Schubert }
4145796c8dcSSimon Schubert 
4155796c8dcSSimon Schubert static void
mi_inferior_appeared(struct inferior * inf)416cf7f2e2dSJohn Marino mi_inferior_appeared (struct inferior *inf)
4175796c8dcSSimon Schubert {
4185796c8dcSSimon Schubert   struct mi_interp *mi = top_level_interpreter_data ();
419cf7f2e2dSJohn Marino 
4205796c8dcSSimon Schubert   target_terminal_ours ();
421cf7f2e2dSJohn Marino   fprintf_unfiltered (mi->event_channel,
422cf7f2e2dSJohn Marino 		      "thread-group-started,id=\"i%d\",pid=\"%d\"",
423cf7f2e2dSJohn Marino 		      inf->num, inf->pid);
424cf7f2e2dSJohn Marino   gdb_flush (mi->event_channel);
425cf7f2e2dSJohn Marino }
426cf7f2e2dSJohn Marino 
427cf7f2e2dSJohn Marino static void
mi_inferior_exit(struct inferior * inf)428cf7f2e2dSJohn Marino mi_inferior_exit (struct inferior *inf)
429cf7f2e2dSJohn Marino {
430cf7f2e2dSJohn Marino   struct mi_interp *mi = top_level_interpreter_data ();
431cf7f2e2dSJohn Marino 
432cf7f2e2dSJohn Marino   target_terminal_ours ();
433c50c785cSJohn Marino   if (inf->has_exit_code)
434c50c785cSJohn Marino     fprintf_unfiltered (mi->event_channel,
435c50c785cSJohn Marino 			"thread-group-exited,id=\"i%d\",exit-code=\"%s\"",
436c50c785cSJohn Marino 			inf->num, int_string (inf->exit_code, 8, 0, 0, 1));
437c50c785cSJohn Marino   else
438c50c785cSJohn Marino     fprintf_unfiltered (mi->event_channel,
439c50c785cSJohn Marino 			"thread-group-exited,id=\"i%d\"", inf->num);
440c50c785cSJohn Marino 
441cf7f2e2dSJohn Marino   gdb_flush (mi->event_channel);
442cf7f2e2dSJohn Marino }
443cf7f2e2dSJohn Marino 
444cf7f2e2dSJohn Marino static void
mi_inferior_removed(struct inferior * inf)445cf7f2e2dSJohn Marino mi_inferior_removed (struct inferior *inf)
446cf7f2e2dSJohn Marino {
447cf7f2e2dSJohn Marino   struct mi_interp *mi = top_level_interpreter_data ();
448cf7f2e2dSJohn Marino 
449cf7f2e2dSJohn Marino   target_terminal_ours ();
450cf7f2e2dSJohn Marino   fprintf_unfiltered (mi->event_channel,
451cf7f2e2dSJohn Marino 		      "thread-group-removed,id=\"i%d\"",
452cf7f2e2dSJohn Marino 		      inf->num);
4535796c8dcSSimon Schubert   gdb_flush (mi->event_channel);
4545796c8dcSSimon Schubert }
4555796c8dcSSimon Schubert 
4565796c8dcSSimon Schubert static void
mi_on_normal_stop(struct bpstats * bs,int print_frame)4575796c8dcSSimon Schubert mi_on_normal_stop (struct bpstats *bs, int print_frame)
4585796c8dcSSimon Schubert {
4595796c8dcSSimon Schubert   /* Since this can be called when CLI command is executing,
4605796c8dcSSimon Schubert      using cli interpreter, be sure to use MI uiout for output,
4615796c8dcSSimon Schubert      not the current one.  */
4625796c8dcSSimon Schubert   struct ui_out *mi_uiout = interp_ui_out (top_level_interpreter ());
4635796c8dcSSimon Schubert 
4645796c8dcSSimon Schubert   if (print_frame)
4655796c8dcSSimon Schubert     {
466cf7f2e2dSJohn Marino       int core;
467cf7f2e2dSJohn Marino 
468a45ae5f8SJohn Marino       if (current_uiout != mi_uiout)
4695796c8dcSSimon Schubert 	{
470*ef5ccd6cSJohn Marino 	  /* The normal_stop function has printed frame information
471*ef5ccd6cSJohn Marino 	     into CLI uiout, or some other non-MI uiout.  There's no
472*ef5ccd6cSJohn Marino 	     way we can extract proper fields from random uiout
473*ef5ccd6cSJohn Marino 	     object, so we print the frame again.  In practice, this
474*ef5ccd6cSJohn Marino 	     can only happen when running a CLI command in MI.  */
475a45ae5f8SJohn Marino 	  struct ui_out *saved_uiout = current_uiout;
476a45ae5f8SJohn Marino 	  struct target_waitstatus last;
477a45ae5f8SJohn Marino 	  ptid_t last_ptid;
478cf7f2e2dSJohn Marino 
479a45ae5f8SJohn Marino 	  current_uiout = mi_uiout;
480a45ae5f8SJohn Marino 
481a45ae5f8SJohn Marino 	  get_last_target_status (&last_ptid, &last);
482a45ae5f8SJohn Marino 	  bpstat_print (bs, last.kind);
483a45ae5f8SJohn Marino 
4845796c8dcSSimon Schubert 	  print_stack_frame (get_selected_frame (NULL), 0, SRC_AND_LOC);
485a45ae5f8SJohn Marino 	  current_uiout = saved_uiout;
4865796c8dcSSimon Schubert 	}
4875796c8dcSSimon Schubert 
4885796c8dcSSimon Schubert       ui_out_field_int (mi_uiout, "thread-id",
4895796c8dcSSimon Schubert 			pid_to_thread_id (inferior_ptid));
4905796c8dcSSimon Schubert       if (non_stop)
4915796c8dcSSimon Schubert 	{
4925796c8dcSSimon Schubert 	  struct cleanup *back_to = make_cleanup_ui_out_list_begin_end
4935796c8dcSSimon Schubert 	    (mi_uiout, "stopped-threads");
494cf7f2e2dSJohn Marino 
4955796c8dcSSimon Schubert 	  ui_out_field_int (mi_uiout, NULL,
4965796c8dcSSimon Schubert 			    pid_to_thread_id (inferior_ptid));
4975796c8dcSSimon Schubert 	  do_cleanups (back_to);
4985796c8dcSSimon Schubert 	}
4995796c8dcSSimon Schubert       else
5005796c8dcSSimon Schubert 	ui_out_field_string (mi_uiout, "stopped-threads", "all");
501cf7f2e2dSJohn Marino 
502cf7f2e2dSJohn Marino       core = target_core_of_thread (inferior_ptid);
503cf7f2e2dSJohn Marino       if (core != -1)
504cf7f2e2dSJohn Marino 	ui_out_field_int (mi_uiout, "core", core);
5055796c8dcSSimon Schubert     }
5065796c8dcSSimon Schubert 
5075796c8dcSSimon Schubert   fputs_unfiltered ("*stopped", raw_stdout);
5085796c8dcSSimon Schubert   mi_out_put (mi_uiout, raw_stdout);
5095796c8dcSSimon Schubert   mi_out_rewind (mi_uiout);
5105796c8dcSSimon Schubert   mi_print_timing_maybe ();
5115796c8dcSSimon Schubert   fputs_unfiltered ("\n", raw_stdout);
5125796c8dcSSimon Schubert   gdb_flush (raw_stdout);
5135796c8dcSSimon Schubert }
5145796c8dcSSimon Schubert 
5155796c8dcSSimon Schubert static void
mi_about_to_proceed(void)5165796c8dcSSimon Schubert mi_about_to_proceed (void)
5175796c8dcSSimon Schubert {
5185796c8dcSSimon Schubert   /* Suppress output while calling an inferior function.  */
5195796c8dcSSimon Schubert 
5205796c8dcSSimon Schubert   if (!ptid_equal (inferior_ptid, null_ptid))
5215796c8dcSSimon Schubert     {
5225796c8dcSSimon Schubert       struct thread_info *tp = inferior_thread ();
523cf7f2e2dSJohn Marino 
524c50c785cSJohn Marino       if (tp->control.in_infcall)
5255796c8dcSSimon Schubert 	return;
5265796c8dcSSimon Schubert     }
5275796c8dcSSimon Schubert 
5285796c8dcSSimon Schubert   mi_proceeded = 1;
5295796c8dcSSimon Schubert }
5305796c8dcSSimon Schubert 
531*ef5ccd6cSJohn Marino /* When the element is non-zero, no MI notifications will be emitted in
532*ef5ccd6cSJohn Marino    response to the corresponding observers.  */
533*ef5ccd6cSJohn Marino 
534*ef5ccd6cSJohn Marino struct mi_suppress_notification mi_suppress_notification =
535*ef5ccd6cSJohn Marino   {
536*ef5ccd6cSJohn Marino     0,
537*ef5ccd6cSJohn Marino     0,
538*ef5ccd6cSJohn Marino     0,
539*ef5ccd6cSJohn Marino   };
540*ef5ccd6cSJohn Marino 
541*ef5ccd6cSJohn Marino /* Emit notification on changing a traceframe.  */
542*ef5ccd6cSJohn Marino 
543*ef5ccd6cSJohn Marino static void
mi_traceframe_changed(int tfnum,int tpnum)544*ef5ccd6cSJohn Marino mi_traceframe_changed (int tfnum, int tpnum)
545*ef5ccd6cSJohn Marino {
546*ef5ccd6cSJohn Marino   struct mi_interp *mi = top_level_interpreter_data ();
547*ef5ccd6cSJohn Marino 
548*ef5ccd6cSJohn Marino   if (mi_suppress_notification.traceframe)
549*ef5ccd6cSJohn Marino     return;
550*ef5ccd6cSJohn Marino 
551*ef5ccd6cSJohn Marino   target_terminal_ours ();
552*ef5ccd6cSJohn Marino 
553*ef5ccd6cSJohn Marino   if (tfnum >= 0)
554*ef5ccd6cSJohn Marino     fprintf_unfiltered (mi->event_channel, "traceframe-changed,"
555*ef5ccd6cSJohn Marino 			"num=\"%d\",tracepoint=\"%d\"\n",
556*ef5ccd6cSJohn Marino 			tfnum, tpnum);
557*ef5ccd6cSJohn Marino   else
558*ef5ccd6cSJohn Marino     fprintf_unfiltered (mi->event_channel, "traceframe-changed,end");
559*ef5ccd6cSJohn Marino 
560*ef5ccd6cSJohn Marino   gdb_flush (mi->event_channel);
561*ef5ccd6cSJohn Marino }
562*ef5ccd6cSJohn Marino 
563*ef5ccd6cSJohn Marino /* Emit notification on creating a trace state variable.  */
564*ef5ccd6cSJohn Marino 
565*ef5ccd6cSJohn Marino static void
mi_tsv_created(const struct trace_state_variable * tsv)566*ef5ccd6cSJohn Marino mi_tsv_created (const struct trace_state_variable *tsv)
567*ef5ccd6cSJohn Marino {
568*ef5ccd6cSJohn Marino   struct mi_interp *mi = top_level_interpreter_data ();
569*ef5ccd6cSJohn Marino 
570*ef5ccd6cSJohn Marino   target_terminal_ours ();
571*ef5ccd6cSJohn Marino 
572*ef5ccd6cSJohn Marino   fprintf_unfiltered (mi->event_channel, "tsv-created,"
573*ef5ccd6cSJohn Marino 		      "name=\"%s\",initial=\"%s\"\n",
574*ef5ccd6cSJohn Marino 		      tsv->name, plongest (tsv->initial_value));
575*ef5ccd6cSJohn Marino 
576*ef5ccd6cSJohn Marino   gdb_flush (mi->event_channel);
577*ef5ccd6cSJohn Marino }
578*ef5ccd6cSJohn Marino 
579*ef5ccd6cSJohn Marino /* Emit notification on deleting a trace state variable.  */
580*ef5ccd6cSJohn Marino 
581*ef5ccd6cSJohn Marino static void
mi_tsv_deleted(const struct trace_state_variable * tsv)582*ef5ccd6cSJohn Marino mi_tsv_deleted (const struct trace_state_variable *tsv)
583*ef5ccd6cSJohn Marino {
584*ef5ccd6cSJohn Marino   struct mi_interp *mi = top_level_interpreter_data ();
585*ef5ccd6cSJohn Marino 
586*ef5ccd6cSJohn Marino   target_terminal_ours ();
587*ef5ccd6cSJohn Marino 
588*ef5ccd6cSJohn Marino   if (tsv != NULL)
589*ef5ccd6cSJohn Marino     fprintf_unfiltered (mi->event_channel, "tsv-deleted,"
590*ef5ccd6cSJohn Marino 			"name=\"%s\"\n", tsv->name);
591*ef5ccd6cSJohn Marino   else
592*ef5ccd6cSJohn Marino     fprintf_unfiltered (mi->event_channel, "tsv-deleted\n");
593*ef5ccd6cSJohn Marino 
594*ef5ccd6cSJohn Marino   gdb_flush (mi->event_channel);
595*ef5ccd6cSJohn Marino }
596*ef5ccd6cSJohn Marino 
597*ef5ccd6cSJohn Marino /* Emit notification on modifying a trace state variable.  */
598*ef5ccd6cSJohn Marino 
599*ef5ccd6cSJohn Marino static void
mi_tsv_modified(const struct trace_state_variable * tsv)600*ef5ccd6cSJohn Marino mi_tsv_modified (const struct trace_state_variable *tsv)
601*ef5ccd6cSJohn Marino {
602*ef5ccd6cSJohn Marino   struct mi_interp *mi = top_level_interpreter_data ();
603*ef5ccd6cSJohn Marino   struct ui_out *mi_uiout = interp_ui_out (top_level_interpreter ());
604*ef5ccd6cSJohn Marino 
605*ef5ccd6cSJohn Marino   target_terminal_ours ();
606*ef5ccd6cSJohn Marino 
607*ef5ccd6cSJohn Marino   fprintf_unfiltered (mi->event_channel,
608*ef5ccd6cSJohn Marino 		      "tsv-modified");
609*ef5ccd6cSJohn Marino 
610*ef5ccd6cSJohn Marino   ui_out_redirect (mi_uiout, mi->event_channel);
611*ef5ccd6cSJohn Marino 
612*ef5ccd6cSJohn Marino   ui_out_field_string (mi_uiout, "name", tsv->name);
613*ef5ccd6cSJohn Marino   ui_out_field_string (mi_uiout, "initial",
614*ef5ccd6cSJohn Marino 		       plongest (tsv->initial_value));
615*ef5ccd6cSJohn Marino   if (tsv->value_known)
616*ef5ccd6cSJohn Marino     ui_out_field_string (mi_uiout, "current", plongest (tsv->value));
617*ef5ccd6cSJohn Marino 
618*ef5ccd6cSJohn Marino   ui_out_redirect (mi_uiout, NULL);
619*ef5ccd6cSJohn Marino 
620*ef5ccd6cSJohn Marino   gdb_flush (mi->event_channel);
621*ef5ccd6cSJohn Marino }
622a45ae5f8SJohn Marino 
623a45ae5f8SJohn Marino /* Emit notification about a created breakpoint.  */
624*ef5ccd6cSJohn Marino 
625a45ae5f8SJohn Marino static void
mi_breakpoint_created(struct breakpoint * b)626a45ae5f8SJohn Marino mi_breakpoint_created (struct breakpoint *b)
627a45ae5f8SJohn Marino {
628a45ae5f8SJohn Marino   struct mi_interp *mi = top_level_interpreter_data ();
629a45ae5f8SJohn Marino   struct ui_out *mi_uiout = interp_ui_out (top_level_interpreter ());
630*ef5ccd6cSJohn Marino   volatile struct gdb_exception e;
631a45ae5f8SJohn Marino 
632*ef5ccd6cSJohn Marino   if (mi_suppress_notification.breakpoint)
633a45ae5f8SJohn Marino     return;
634a45ae5f8SJohn Marino 
635a45ae5f8SJohn Marino   if (b->number <= 0)
636a45ae5f8SJohn Marino     return;
637a45ae5f8SJohn Marino 
638a45ae5f8SJohn Marino   target_terminal_ours ();
639a45ae5f8SJohn Marino   fprintf_unfiltered (mi->event_channel,
640a45ae5f8SJohn Marino 		      "breakpoint-created");
641a45ae5f8SJohn Marino   /* We want the output from gdb_breakpoint_query to go to
642*ef5ccd6cSJohn Marino      mi->event_channel.  One approach would be to just call
643*ef5ccd6cSJohn Marino      gdb_breakpoint_query, and then use mi_out_put to send the current
644*ef5ccd6cSJohn Marino      content of mi_outout into mi->event_channel.  However, that will
645*ef5ccd6cSJohn Marino      break if anything is output to mi_uiout prior to calling the
646*ef5ccd6cSJohn Marino      breakpoint_created notifications.  So, we use
647*ef5ccd6cSJohn Marino      ui_out_redirect.  */
648a45ae5f8SJohn Marino   ui_out_redirect (mi_uiout, mi->event_channel);
649a45ae5f8SJohn Marino   TRY_CATCH (e, RETURN_MASK_ERROR)
650a45ae5f8SJohn Marino     gdb_breakpoint_query (mi_uiout, b->number, NULL);
651a45ae5f8SJohn Marino   ui_out_redirect (mi_uiout, NULL);
652a45ae5f8SJohn Marino 
653a45ae5f8SJohn Marino   gdb_flush (mi->event_channel);
654a45ae5f8SJohn Marino }
655a45ae5f8SJohn Marino 
656a45ae5f8SJohn Marino /* Emit notification about deleted breakpoint.  */
657*ef5ccd6cSJohn Marino 
658a45ae5f8SJohn Marino static void
mi_breakpoint_deleted(struct breakpoint * b)659a45ae5f8SJohn Marino mi_breakpoint_deleted (struct breakpoint *b)
660a45ae5f8SJohn Marino {
661a45ae5f8SJohn Marino   struct mi_interp *mi = top_level_interpreter_data ();
662a45ae5f8SJohn Marino 
663*ef5ccd6cSJohn Marino   if (mi_suppress_notification.breakpoint)
664a45ae5f8SJohn Marino     return;
665a45ae5f8SJohn Marino 
666a45ae5f8SJohn Marino   if (b->number <= 0)
667a45ae5f8SJohn Marino     return;
668a45ae5f8SJohn Marino 
669a45ae5f8SJohn Marino   target_terminal_ours ();
670a45ae5f8SJohn Marino 
671a45ae5f8SJohn Marino   fprintf_unfiltered (mi->event_channel, "breakpoint-deleted,id=\"%d\"",
672a45ae5f8SJohn Marino 		      b->number);
673a45ae5f8SJohn Marino 
674a45ae5f8SJohn Marino   gdb_flush (mi->event_channel);
675a45ae5f8SJohn Marino }
676a45ae5f8SJohn Marino 
677a45ae5f8SJohn Marino /* Emit notification about modified breakpoint.  */
678*ef5ccd6cSJohn Marino 
679a45ae5f8SJohn Marino static void
mi_breakpoint_modified(struct breakpoint * b)680a45ae5f8SJohn Marino mi_breakpoint_modified (struct breakpoint *b)
681a45ae5f8SJohn Marino {
682a45ae5f8SJohn Marino   struct mi_interp *mi = top_level_interpreter_data ();
683a45ae5f8SJohn Marino   struct ui_out *mi_uiout = interp_ui_out (top_level_interpreter ());
684*ef5ccd6cSJohn Marino   volatile struct gdb_exception e;
685a45ae5f8SJohn Marino 
686*ef5ccd6cSJohn Marino   if (mi_suppress_notification.breakpoint)
687a45ae5f8SJohn Marino     return;
688a45ae5f8SJohn Marino 
689a45ae5f8SJohn Marino   if (b->number <= 0)
690a45ae5f8SJohn Marino     return;
691a45ae5f8SJohn Marino 
692a45ae5f8SJohn Marino   target_terminal_ours ();
693a45ae5f8SJohn Marino   fprintf_unfiltered (mi->event_channel,
694a45ae5f8SJohn Marino 		      "breakpoint-modified");
695a45ae5f8SJohn Marino   /* We want the output from gdb_breakpoint_query to go to
696*ef5ccd6cSJohn Marino      mi->event_channel.  One approach would be to just call
697*ef5ccd6cSJohn Marino      gdb_breakpoint_query, and then use mi_out_put to send the current
698*ef5ccd6cSJohn Marino      content of mi_outout into mi->event_channel.  However, that will
699*ef5ccd6cSJohn Marino      break if anything is output to mi_uiout prior to calling the
700*ef5ccd6cSJohn Marino      breakpoint_created notifications.  So, we use
701*ef5ccd6cSJohn Marino      ui_out_redirect.  */
702a45ae5f8SJohn Marino   ui_out_redirect (mi_uiout, mi->event_channel);
703a45ae5f8SJohn Marino   TRY_CATCH (e, RETURN_MASK_ERROR)
704a45ae5f8SJohn Marino     gdb_breakpoint_query (mi_uiout, b->number, NULL);
705a45ae5f8SJohn Marino   ui_out_redirect (mi_uiout, NULL);
706a45ae5f8SJohn Marino 
707a45ae5f8SJohn Marino   gdb_flush (mi->event_channel);
708a45ae5f8SJohn Marino }
709a45ae5f8SJohn Marino 
7105796c8dcSSimon Schubert static int
mi_output_running_pid(struct thread_info * info,void * arg)7115796c8dcSSimon Schubert mi_output_running_pid (struct thread_info *info, void *arg)
7125796c8dcSSimon Schubert {
7135796c8dcSSimon Schubert   ptid_t *ptid = arg;
7145796c8dcSSimon Schubert 
7155796c8dcSSimon Schubert   if (ptid_get_pid (*ptid) == ptid_get_pid (info->ptid))
7165796c8dcSSimon Schubert     fprintf_unfiltered (raw_stdout,
7175796c8dcSSimon Schubert 			"*running,thread-id=\"%d\"\n",
7185796c8dcSSimon Schubert 			info->num);
7195796c8dcSSimon Schubert 
7205796c8dcSSimon Schubert   return 0;
7215796c8dcSSimon Schubert }
7225796c8dcSSimon Schubert 
7235796c8dcSSimon Schubert static int
mi_inferior_count(struct inferior * inf,void * arg)7245796c8dcSSimon Schubert mi_inferior_count (struct inferior *inf, void *arg)
7255796c8dcSSimon Schubert {
7265796c8dcSSimon Schubert   if (inf->pid != 0)
7275796c8dcSSimon Schubert     {
7285796c8dcSSimon Schubert       int *count_p = arg;
7295796c8dcSSimon Schubert       (*count_p)++;
7305796c8dcSSimon Schubert     }
7315796c8dcSSimon Schubert 
7325796c8dcSSimon Schubert   return 0;
7335796c8dcSSimon Schubert }
7345796c8dcSSimon Schubert 
7355796c8dcSSimon Schubert static void
mi_on_resume(ptid_t ptid)7365796c8dcSSimon Schubert mi_on_resume (ptid_t ptid)
7375796c8dcSSimon Schubert {
7385796c8dcSSimon Schubert   struct thread_info *tp = NULL;
7395796c8dcSSimon Schubert 
7405796c8dcSSimon Schubert   if (ptid_equal (ptid, minus_one_ptid) || ptid_is_pid (ptid))
7415796c8dcSSimon Schubert     tp = inferior_thread ();
7425796c8dcSSimon Schubert   else
7435796c8dcSSimon Schubert     tp = find_thread_ptid (ptid);
7445796c8dcSSimon Schubert 
7455796c8dcSSimon Schubert   /* Suppress output while calling an inferior function.  */
746c50c785cSJohn Marino   if (tp->control.in_infcall)
7475796c8dcSSimon Schubert     return;
7485796c8dcSSimon Schubert 
7495796c8dcSSimon Schubert   /* To cater for older frontends, emit ^running, but do it only once
7505796c8dcSSimon Schubert      per each command.  We do it here, since at this point we know
7515796c8dcSSimon Schubert      that the target was successfully resumed, and in non-async mode,
7525796c8dcSSimon Schubert      we won't return back to MI interpreter code until the target
7535796c8dcSSimon Schubert      is done running, so delaying the output of "^running" until then
7545796c8dcSSimon Schubert      will make it impossible for frontend to know what's going on.
7555796c8dcSSimon Schubert 
7565796c8dcSSimon Schubert      In future (MI3), we'll be outputting "^done" here.  */
7575796c8dcSSimon Schubert   if (!running_result_record_printed && mi_proceeded)
7585796c8dcSSimon Schubert     {
759cf7f2e2dSJohn Marino       fprintf_unfiltered (raw_stdout, "%s^running\n",
760cf7f2e2dSJohn Marino 			  current_token ? current_token : "");
7615796c8dcSSimon Schubert     }
7625796c8dcSSimon Schubert 
7635796c8dcSSimon Schubert   if (PIDGET (ptid) == -1)
7645796c8dcSSimon Schubert     fprintf_unfiltered (raw_stdout, "*running,thread-id=\"all\"\n");
7655796c8dcSSimon Schubert   else if (ptid_is_pid (ptid))
7665796c8dcSSimon Schubert     {
7675796c8dcSSimon Schubert       int count = 0;
7685796c8dcSSimon Schubert 
7695796c8dcSSimon Schubert       /* Backwards compatibility.  If there's only one inferior,
7705796c8dcSSimon Schubert 	 output "all", otherwise, output each resumed thread
7715796c8dcSSimon Schubert 	 individually.  */
7725796c8dcSSimon Schubert       iterate_over_inferiors (mi_inferior_count, &count);
7735796c8dcSSimon Schubert 
7745796c8dcSSimon Schubert       if (count == 1)
7755796c8dcSSimon Schubert 	fprintf_unfiltered (raw_stdout, "*running,thread-id=\"all\"\n");
7765796c8dcSSimon Schubert       else
7775796c8dcSSimon Schubert 	iterate_over_threads (mi_output_running_pid, &ptid);
7785796c8dcSSimon Schubert     }
7795796c8dcSSimon Schubert   else
7805796c8dcSSimon Schubert     {
7815796c8dcSSimon Schubert       struct thread_info *ti = find_thread_ptid (ptid);
782cf7f2e2dSJohn Marino 
7835796c8dcSSimon Schubert       gdb_assert (ti);
7845796c8dcSSimon Schubert       fprintf_unfiltered (raw_stdout, "*running,thread-id=\"%d\"\n", ti->num);
7855796c8dcSSimon Schubert     }
7865796c8dcSSimon Schubert 
7875796c8dcSSimon Schubert   if (!running_result_record_printed && mi_proceeded)
7885796c8dcSSimon Schubert     {
7895796c8dcSSimon Schubert       running_result_record_printed = 1;
7905796c8dcSSimon Schubert       /* This is what gdb used to do historically -- printing prompt even if
7915796c8dcSSimon Schubert 	 it cannot actually accept any input.  This will be surely removed
7925796c8dcSSimon Schubert 	 for MI3, and may be removed even earler.  */
7935796c8dcSSimon Schubert       /* FIXME: review the use of target_is_async_p here -- is that
7945796c8dcSSimon Schubert 	 what we want? */
7955796c8dcSSimon Schubert       if (!target_is_async_p ())
7965796c8dcSSimon Schubert 	fputs_unfiltered ("(gdb) \n", raw_stdout);
7975796c8dcSSimon Schubert     }
7985796c8dcSSimon Schubert   gdb_flush (raw_stdout);
7995796c8dcSSimon Schubert }
8005796c8dcSSimon Schubert 
8015796c8dcSSimon Schubert static void
mi_solib_loaded(struct so_list * solib)8025796c8dcSSimon Schubert mi_solib_loaded (struct so_list *solib)
8035796c8dcSSimon Schubert {
8045796c8dcSSimon Schubert   struct mi_interp *mi = top_level_interpreter_data ();
805cf7f2e2dSJohn Marino 
8065796c8dcSSimon Schubert   target_terminal_ours ();
807*ef5ccd6cSJohn Marino   if (gdbarch_has_global_solist (target_gdbarch ()))
8085796c8dcSSimon Schubert     fprintf_unfiltered (mi->event_channel,
809cf7f2e2dSJohn Marino 			"library-loaded,id=\"%s\",target-name=\"%s\","
810cf7f2e2dSJohn Marino 			"host-name=\"%s\",symbols-loaded=\"%d\"",
8115796c8dcSSimon Schubert 			solib->so_original_name, solib->so_original_name,
8125796c8dcSSimon Schubert 			solib->so_name, solib->symbols_loaded);
813cf7f2e2dSJohn Marino   else
814cf7f2e2dSJohn Marino     fprintf_unfiltered (mi->event_channel,
815cf7f2e2dSJohn Marino 			"library-loaded,id=\"%s\",target-name=\"%s\","
816cf7f2e2dSJohn Marino 			"host-name=\"%s\",symbols-loaded=\"%d\","
817cf7f2e2dSJohn Marino 			"thread-group=\"i%d\"",
818cf7f2e2dSJohn Marino 			solib->so_original_name, solib->so_original_name,
819cf7f2e2dSJohn Marino 			solib->so_name, solib->symbols_loaded,
820cf7f2e2dSJohn Marino 			current_inferior ()->num);
821cf7f2e2dSJohn Marino 
8225796c8dcSSimon Schubert   gdb_flush (mi->event_channel);
8235796c8dcSSimon Schubert }
8245796c8dcSSimon Schubert 
8255796c8dcSSimon Schubert static void
mi_solib_unloaded(struct so_list * solib)8265796c8dcSSimon Schubert mi_solib_unloaded (struct so_list *solib)
8275796c8dcSSimon Schubert {
8285796c8dcSSimon Schubert   struct mi_interp *mi = top_level_interpreter_data ();
829cf7f2e2dSJohn Marino 
8305796c8dcSSimon Schubert   target_terminal_ours ();
831*ef5ccd6cSJohn Marino   if (gdbarch_has_global_solist (target_gdbarch ()))
8325796c8dcSSimon Schubert     fprintf_unfiltered (mi->event_channel,
833cf7f2e2dSJohn Marino 			"library-unloaded,id=\"%s\",target-name=\"%s\","
834cf7f2e2dSJohn Marino 			"host-name=\"%s\"",
8355796c8dcSSimon Schubert 			solib->so_original_name, solib->so_original_name,
8365796c8dcSSimon Schubert 			solib->so_name);
837cf7f2e2dSJohn Marino   else
838cf7f2e2dSJohn Marino     fprintf_unfiltered (mi->event_channel,
839cf7f2e2dSJohn Marino 			"library-unloaded,id=\"%s\",target-name=\"%s\","
840cf7f2e2dSJohn Marino 			"host-name=\"%s\",thread-group=\"i%d\"",
841cf7f2e2dSJohn Marino 			solib->so_original_name, solib->so_original_name,
842cf7f2e2dSJohn Marino 			solib->so_name, current_inferior ()->num);
843cf7f2e2dSJohn Marino 
8445796c8dcSSimon Schubert   gdb_flush (mi->event_channel);
8455796c8dcSSimon Schubert }
8465796c8dcSSimon Schubert 
847*ef5ccd6cSJohn Marino /* Emit notification about the command parameter change.  */
848*ef5ccd6cSJohn Marino 
849*ef5ccd6cSJohn Marino static void
mi_command_param_changed(const char * param,const char * value)850*ef5ccd6cSJohn Marino mi_command_param_changed (const char *param, const char *value)
851*ef5ccd6cSJohn Marino {
852*ef5ccd6cSJohn Marino   struct mi_interp *mi = top_level_interpreter_data ();
853*ef5ccd6cSJohn Marino   struct ui_out *mi_uiout = interp_ui_out (top_level_interpreter ());
854*ef5ccd6cSJohn Marino 
855*ef5ccd6cSJohn Marino   if (mi_suppress_notification.cmd_param_changed)
856*ef5ccd6cSJohn Marino     return;
857*ef5ccd6cSJohn Marino 
858*ef5ccd6cSJohn Marino   target_terminal_ours ();
859*ef5ccd6cSJohn Marino 
860*ef5ccd6cSJohn Marino   fprintf_unfiltered (mi->event_channel,
861*ef5ccd6cSJohn Marino 		      "cmd-param-changed");
862*ef5ccd6cSJohn Marino 
863*ef5ccd6cSJohn Marino   ui_out_redirect (mi_uiout, mi->event_channel);
864*ef5ccd6cSJohn Marino 
865*ef5ccd6cSJohn Marino   ui_out_field_string (mi_uiout, "param", param);
866*ef5ccd6cSJohn Marino   ui_out_field_string (mi_uiout, "value", value);
867*ef5ccd6cSJohn Marino 
868*ef5ccd6cSJohn Marino   ui_out_redirect (mi_uiout, NULL);
869*ef5ccd6cSJohn Marino 
870*ef5ccd6cSJohn Marino   gdb_flush (mi->event_channel);
871*ef5ccd6cSJohn Marino }
872*ef5ccd6cSJohn Marino 
873*ef5ccd6cSJohn Marino /* Emit notification about the target memory change.  */
874*ef5ccd6cSJohn Marino 
875*ef5ccd6cSJohn Marino static void
mi_memory_changed(struct inferior * inferior,CORE_ADDR memaddr,ssize_t len,const bfd_byte * myaddr)876*ef5ccd6cSJohn Marino mi_memory_changed (struct inferior *inferior, CORE_ADDR memaddr,
877*ef5ccd6cSJohn Marino 		   ssize_t len, const bfd_byte *myaddr)
878*ef5ccd6cSJohn Marino {
879*ef5ccd6cSJohn Marino   struct mi_interp *mi = top_level_interpreter_data ();
880*ef5ccd6cSJohn Marino   struct ui_out *mi_uiout = interp_ui_out (top_level_interpreter ());
881*ef5ccd6cSJohn Marino   struct obj_section *sec;
882*ef5ccd6cSJohn Marino 
883*ef5ccd6cSJohn Marino   if (mi_suppress_notification.memory)
884*ef5ccd6cSJohn Marino     return;
885*ef5ccd6cSJohn Marino 
886*ef5ccd6cSJohn Marino   target_terminal_ours ();
887*ef5ccd6cSJohn Marino 
888*ef5ccd6cSJohn Marino   fprintf_unfiltered (mi->event_channel,
889*ef5ccd6cSJohn Marino 		      "memory-changed");
890*ef5ccd6cSJohn Marino 
891*ef5ccd6cSJohn Marino   ui_out_redirect (mi_uiout, mi->event_channel);
892*ef5ccd6cSJohn Marino 
893*ef5ccd6cSJohn Marino   ui_out_field_fmt (mi_uiout, "thread-group", "i%d", inferior->num);
894*ef5ccd6cSJohn Marino   ui_out_field_core_addr (mi_uiout, "addr", target_gdbarch (), memaddr);
895*ef5ccd6cSJohn Marino   ui_out_field_fmt (mi_uiout, "len", "0x%zx", len);
896*ef5ccd6cSJohn Marino 
897*ef5ccd6cSJohn Marino   /* Append 'type=code' into notification if MEMADDR falls in the range of
898*ef5ccd6cSJohn Marino      sections contain code.  */
899*ef5ccd6cSJohn Marino   sec = find_pc_section (memaddr);
900*ef5ccd6cSJohn Marino   if (sec != NULL && sec->objfile != NULL)
901*ef5ccd6cSJohn Marino     {
902*ef5ccd6cSJohn Marino       flagword flags = bfd_get_section_flags (sec->objfile->obfd,
903*ef5ccd6cSJohn Marino 					      sec->the_bfd_section);
904*ef5ccd6cSJohn Marino 
905*ef5ccd6cSJohn Marino       if (flags & SEC_CODE)
906*ef5ccd6cSJohn Marino 	ui_out_field_string (mi_uiout, "type", "code");
907*ef5ccd6cSJohn Marino     }
908*ef5ccd6cSJohn Marino 
909*ef5ccd6cSJohn Marino   ui_out_redirect (mi_uiout, NULL);
910*ef5ccd6cSJohn Marino 
911*ef5ccd6cSJohn Marino   gdb_flush (mi->event_channel);
912*ef5ccd6cSJohn Marino }
913*ef5ccd6cSJohn Marino 
914cf7f2e2dSJohn Marino static int
report_initial_inferior(struct inferior * inf,void * closure)915cf7f2e2dSJohn Marino report_initial_inferior (struct inferior *inf, void *closure)
916cf7f2e2dSJohn Marino {
917cf7f2e2dSJohn Marino   /* This function is called from mi_intepreter_init, and since
918cf7f2e2dSJohn Marino      mi_inferior_added assumes that inferior is fully initialized
919cf7f2e2dSJohn Marino      and top_level_interpreter_data is set, we cannot call
920cf7f2e2dSJohn Marino      it here.  */
921cf7f2e2dSJohn Marino   struct mi_interp *mi = closure;
922cf7f2e2dSJohn Marino 
923cf7f2e2dSJohn Marino   target_terminal_ours ();
924cf7f2e2dSJohn Marino   fprintf_unfiltered (mi->event_channel,
925cf7f2e2dSJohn Marino 		      "thread-group-added,id=\"i%d\"",
926cf7f2e2dSJohn Marino 		      inf->num);
927cf7f2e2dSJohn Marino   gdb_flush (mi->event_channel);
928cf7f2e2dSJohn Marino   return 0;
929cf7f2e2dSJohn Marino }
9305796c8dcSSimon Schubert 
931a45ae5f8SJohn Marino static struct ui_out *
mi_ui_out(struct interp * interp)932a45ae5f8SJohn Marino mi_ui_out (struct interp *interp)
933a45ae5f8SJohn Marino {
934a45ae5f8SJohn Marino   struct mi_interp *mi = interp_data (interp);
935a45ae5f8SJohn Marino 
936a45ae5f8SJohn Marino   return mi->uiout;
937a45ae5f8SJohn Marino }
938a45ae5f8SJohn Marino 
939*ef5ccd6cSJohn Marino /* Save the original value of raw_stdout here when logging, so we can
940*ef5ccd6cSJohn Marino    restore correctly when done.  */
941*ef5ccd6cSJohn Marino 
942*ef5ccd6cSJohn Marino static struct ui_file *saved_raw_stdout;
943*ef5ccd6cSJohn Marino 
944*ef5ccd6cSJohn Marino /* Do MI-specific logging actions; save raw_stdout, and change all
945*ef5ccd6cSJohn Marino    the consoles to use the supplied ui-file(s).  */
946*ef5ccd6cSJohn Marino 
947*ef5ccd6cSJohn Marino static int
mi_set_logging(struct interp * interp,int start_log,struct ui_file * out,struct ui_file * logfile)948*ef5ccd6cSJohn Marino mi_set_logging (struct interp *interp, int start_log,
949*ef5ccd6cSJohn Marino 		struct ui_file *out, struct ui_file *logfile)
950*ef5ccd6cSJohn Marino {
951*ef5ccd6cSJohn Marino   struct mi_interp *mi = interp_data (interp);
952*ef5ccd6cSJohn Marino 
953*ef5ccd6cSJohn Marino   if (!mi)
954*ef5ccd6cSJohn Marino     return 0;
955*ef5ccd6cSJohn Marino 
956*ef5ccd6cSJohn Marino   if (start_log)
957*ef5ccd6cSJohn Marino     {
958*ef5ccd6cSJohn Marino       /* The tee created already is based on gdb_stdout, which for MI
959*ef5ccd6cSJohn Marino 	 is a console and so we end up in an infinite loop of console
960*ef5ccd6cSJohn Marino 	 writing to ui_file writing to console etc.  So discard the
961*ef5ccd6cSJohn Marino 	 existing tee (it hasn't been used yet, and MI won't ever use
962*ef5ccd6cSJohn Marino 	 it), and create one based on raw_stdout instead.  */
963*ef5ccd6cSJohn Marino       if (logfile)
964*ef5ccd6cSJohn Marino 	{
965*ef5ccd6cSJohn Marino 	  ui_file_delete (out);
966*ef5ccd6cSJohn Marino 	  out = tee_file_new (raw_stdout, 0, logfile, 0);
967*ef5ccd6cSJohn Marino 	}
968*ef5ccd6cSJohn Marino 
969*ef5ccd6cSJohn Marino       saved_raw_stdout = raw_stdout;
970*ef5ccd6cSJohn Marino       raw_stdout = out;
971*ef5ccd6cSJohn Marino     }
972*ef5ccd6cSJohn Marino   else
973*ef5ccd6cSJohn Marino     {
974*ef5ccd6cSJohn Marino       raw_stdout = saved_raw_stdout;
975*ef5ccd6cSJohn Marino       saved_raw_stdout = NULL;
976*ef5ccd6cSJohn Marino     }
977*ef5ccd6cSJohn Marino 
978*ef5ccd6cSJohn Marino   mi_console_set_raw (mi->out, raw_stdout);
979*ef5ccd6cSJohn Marino   mi_console_set_raw (mi->err, raw_stdout);
980*ef5ccd6cSJohn Marino   mi_console_set_raw (mi->log, raw_stdout);
981*ef5ccd6cSJohn Marino   mi_console_set_raw (mi->targ, raw_stdout);
982*ef5ccd6cSJohn Marino   mi_console_set_raw (mi->event_channel, raw_stdout);
983*ef5ccd6cSJohn Marino 
984*ef5ccd6cSJohn Marino   return 1;
985*ef5ccd6cSJohn Marino }
986*ef5ccd6cSJohn Marino 
9875796c8dcSSimon Schubert extern initialize_file_ftype _initialize_mi_interp; /* -Wmissing-prototypes */
9885796c8dcSSimon Schubert 
9895796c8dcSSimon Schubert void
_initialize_mi_interp(void)9905796c8dcSSimon Schubert _initialize_mi_interp (void)
9915796c8dcSSimon Schubert {
9925796c8dcSSimon Schubert   static const struct interp_procs procs =
9935796c8dcSSimon Schubert     {
9945796c8dcSSimon Schubert       mi_interpreter_init,	/* init_proc */
9955796c8dcSSimon Schubert       mi_interpreter_resume,	/* resume_proc */
9965796c8dcSSimon Schubert       mi_interpreter_suspend,	/* suspend_proc */
9975796c8dcSSimon Schubert       mi_interpreter_exec,	/* exec_proc */
998a45ae5f8SJohn Marino       mi_interpreter_prompt_p,	/* prompt_proc_p */
999*ef5ccd6cSJohn Marino       mi_ui_out, 		/* ui_out_proc */
1000*ef5ccd6cSJohn Marino       mi_set_logging		/* set_logging_proc */
10015796c8dcSSimon Schubert     };
10025796c8dcSSimon Schubert 
10035796c8dcSSimon Schubert   /* The various interpreter levels.  */
1004a45ae5f8SJohn Marino   interp_add (interp_new (INTERP_MI1, &procs));
1005a45ae5f8SJohn Marino   interp_add (interp_new (INTERP_MI2, &procs));
1006a45ae5f8SJohn Marino   interp_add (interp_new (INTERP_MI3, &procs));
1007a45ae5f8SJohn Marino   interp_add (interp_new (INTERP_MI, &procs));
10085796c8dcSSimon Schubert }
1009