Refactor 'maint time' command statistics.
[deliverable/binutils-gdb.git] / gdb / top.c
index 14a7c56856de16cdcbc46f41de58c8b5e62db2c0..93447fe9aa919c9edebf6742b30103ef7a13efb3 100644 (file)
--- a/gdb/top.c
+++ b/gdb/top.c
@@ -1,14 +1,14 @@
 /* Top level stuff for GDB, the GNU debugger.
 
    Copyright (C) 1986, 1987, 1988, 1989, 1990, 1991, 1992, 1993, 1994, 1995,
 /* Top level stuff for GDB, the GNU debugger.
 
    Copyright (C) 1986, 1987, 1988, 1989, 1990, 1991, 1992, 1993, 1994, 1995,
-   1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007
-   Free Software Foundation, Inc.
+   1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007,
+   2008, 2009, 2010 Free Software Foundation, Inc.
 
    This file is part of GDB.
 
    This program is free software; you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
 
    This file is part of GDB.
 
    This program is free software; you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
-   the Free Software Foundation; either version 2 of the License, or
+   the Free Software Foundation; either version 3 of the License, or
    (at your option) any later version.
 
    This program is distributed in the hope that it will be useful,
    (at your option) any later version.
 
    This program is distributed in the hope that it will be useful,
@@ -17,9 +17,7 @@
    GNU General Public License for more details.
 
    You should have received a copy of the GNU General Public License
    GNU General Public License for more details.
 
    You should have received a copy of the GNU General Public License
-   along with this program; if not, write to the Free Software
-   Foundation, Inc., 51 Franklin Street, Fifth Floor,
-   Boston, MA 02110-1301, USA.  */
+   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
 
 #include "defs.h"
 #include "gdbcmd.h"
 
 #include "defs.h"
 #include "gdbcmd.h"
@@ -48,6 +46,7 @@
 #include "gdb_assert.h"
 #include "main.h"
 #include "event-loop.h"
 #include "gdb_assert.h"
 #include "main.h"
 #include "event-loop.h"
+#include "gdbthread.h"
 
 /* readline include files */
 #include "readline/readline.h"
 
 /* readline include files */
 #include "readline/readline.h"
@@ -133,9 +132,6 @@ void (*window_hook) (FILE *, char *);
 int epoch_interface;
 int xgdb_verbose;
 
 int epoch_interface;
 int xgdb_verbose;
 
-/* gdb prints this when reading a command interactively */
-static char *gdb_prompt_string;        /* the global prompt string */
-
 /* Buffer used for reading command lines, and the size
    allocated for it so far.  */
 
 /* Buffer used for reading command lines, and the size
    allocated for it so far.  */
 
@@ -183,26 +179,11 @@ int remote_timeout = 2;
 
 int remote_debug = 0;
 
 
 int remote_debug = 0;
 
-/* Non-zero means the target is running. Note: this is different from
-   saying that there is an active target and we are stopped at a
-   breakpoint, for instance. This is a real indicator whether the
-   target is off and running, which gdb is doing something else. */
-int target_executing = 0;
-
 /* Sbrk location on entry to main.  Used for statistics only.  */
 #ifdef HAVE_SBRK
 char *lim_at_start;
 #endif
 
 /* Sbrk location on entry to main.  Used for statistics only.  */
 #ifdef HAVE_SBRK
 char *lim_at_start;
 #endif
 
-/* Signal to catch ^Z typed while reading a command: SIGTSTP or SIGCONT.  */
-
-#ifndef STOP_SIGNAL
-#ifdef SIGTSTP
-#define STOP_SIGNAL SIGTSTP
-static void stop_sig (int);
-#endif
-#endif
-
 /* Hooks for alternate command interfaces.  */
 
 /* Called after most modules have been initialized, but before taking users
 /* Hooks for alternate command interfaces.  */
 
 /* Called after most modules have been initialized, but before taking users
@@ -253,13 +234,6 @@ void (*deprecated_readline_begin_hook) (char *, ...);
 char *(*deprecated_readline_hook) (char *);
 void (*deprecated_readline_end_hook) (void);
 
 char *(*deprecated_readline_hook) (char *);
 void (*deprecated_readline_end_hook) (void);
 
-/* Called as appropriate to notify the interface of the specified breakpoint
-   conditions.  */
-
-void (*deprecated_create_breakpoint_hook) (struct breakpoint * bpt);
-void (*deprecated_delete_breakpoint_hook) (struct breakpoint * bpt);
-void (*deprecated_modify_breakpoint_hook) (struct breakpoint * bpt);
-
 /* Called as appropriate to notify the interface that we have attached
    to or detached from an already running process. */
 
 /* Called as appropriate to notify the interface that we have attached
    to or detached from an already running process. */
 
@@ -276,14 +250,12 @@ void (*deprecated_interactive_hook) (void);
    that several registers have changed (see value_assign). */
 void (*deprecated_register_changed_hook) (int regno);
 
    that several registers have changed (see value_assign). */
 void (*deprecated_register_changed_hook) (int regno);
 
-/* Tell the GUI someone changed LEN bytes of memory at ADDR */
-void (*deprecated_memory_changed_hook) (CORE_ADDR addr, int len);
-
 /* Called when going to wait for the target.  Usually allows the GUI to run
    while waiting for target events.  */
 
 ptid_t (*deprecated_target_wait_hook) (ptid_t ptid,
 /* Called when going to wait for the target.  Usually allows the GUI to run
    while waiting for target events.  */
 
 ptid_t (*deprecated_target_wait_hook) (ptid_t ptid,
-                                      struct target_waitstatus * status);
+                                      struct target_waitstatus *status,
+                                      int options);
 
 /* Used by UI as a wrapper around command execution.  May do various things
    like enabling/disabling buttons, etc...  */
 
 /* Used by UI as a wrapper around command execution.  May do various things
    like enabling/disabling buttons, etc...  */
@@ -300,11 +272,6 @@ void (*deprecated_set_hook) (struct cmd_list_element * c);
 
 void (*deprecated_context_hook) (int id);
 
 
 void (*deprecated_context_hook) (int id);
 
-/* Takes control from error ().  Typically used to prevent longjmps out of the
-   middle of the GUI.  Usually used in conjunction with a catch routine.  */
-
-void (*deprecated_error_hook) (void);
-
 /* Handler for SIGHUP.  */
 
 #ifdef SIGHUP
 /* Handler for SIGHUP.  */
 
 #ifdef SIGHUP
@@ -331,7 +298,7 @@ quit_cover (void *s)
 /* NOTE 1999-04-29: This variable will be static again, once we modify
    gdb to use the event loop as the default command loop and we merge
    event-top.c into this file, top.c */
 /* NOTE 1999-04-29: This variable will be static again, once we modify
    gdb to use the event loop as the default command loop and we merge
    event-top.c into this file, top.c */
-/* static */ char *source_file_name;
+/* static */ const char *source_file_name;
 
 /* Clean up on error during a "source" command (or execution of a
    user-defined command).  */
 
 /* Clean up on error during a "source" command (or execution of a
    user-defined command).  */
@@ -366,7 +333,20 @@ do_chdir_cleanup (void *old_dir)
 }
 #endif
 
 }
 #endif
 
-/* Execute the line P as a command.
+void
+prepare_execute_command (void)
+{
+  free_all_values ();
+
+  /* With multiple threads running while the one we're examining is stopped,
+     the dcache can get stale without us being able to detect it.
+     For the duration of the command, though, use the dcache to help
+     things like backtrace.  */
+  if (non_stop)
+    target_dcache_invalidate ();
+}
+
+/* Execute the line P as a command, in the current user context.
    Pass FROM_TTY as second argument to the defining function.  */
 
 void
    Pass FROM_TTY as second argument to the defining function.  */
 
 void
@@ -376,8 +356,8 @@ execute_command (char *p, int from_tty)
   enum language flang;
   static int warned = 0;
   char *line;
   enum language flang;
   static int warned = 0;
   char *line;
-  
-  free_all_values ();
+
+  prepare_execute_command ();
 
   /* Force cleanup of any alloca areas if using C alloca instead of
      a builtin alloca.  */
 
   /* Force cleanup of any alloca areas if using C alloca instead of
      a builtin alloca.  */
@@ -387,7 +367,7 @@ execute_command (char *p, int from_tty)
   if (p == NULL)
     return;
 
   if (p == NULL)
     return;
 
-  serial_log_command (p);
+  target_log_command (p);
 
   while (*p == ' ' || *p == '\t')
     p++;
 
   while (*p == ' ' || *p == '\t')
     p++;
@@ -401,15 +381,6 @@ execute_command (char *p, int from_tty)
 
       c = lookup_cmd (&p, cmdlist, "", 0, 1);
 
 
       c = lookup_cmd (&p, cmdlist, "", 0, 1);
 
-      /* If the target is running, we allow only a limited set of
-         commands. */
-      if (target_can_async_p () && target_executing)
-       if (strcmp (c->name, "help") != 0
-           && strcmp (c->name, "pwd") != 0
-           && strcmp (c->name, "show") != 0
-           && strcmp (c->name, "stop") != 0)
-         error (_("Cannot execute this command while the target is running."));
-
       /* Pass null arg rather than an empty one.  */
       arg = *p ? p : 0;
 
       /* Pass null arg rather than an empty one.  */
       arg = *p ? p : 0;
 
@@ -455,10 +426,13 @@ execute_command (char *p, int from_tty)
 
     }
 
 
     }
 
-  /* Tell the user if the language has changed (except first time).  */
+  /* Tell the user if the language has changed (except first time).
+     First make sure that a new frame has been selected, in case this
+     command or the hooks changed the program state.  */
+  deprecated_safe_get_selected_frame ();
   if (current_language != expected_language)
     {
   if (current_language != expected_language)
     {
-      if (language_mode == language_mode_auto)
+      if (language_mode == language_mode_auto && info_verbose)
        {
          language_info (1);    /* Print what changed.  */
        }
        {
          language_info (1);    /* Print what changed.  */
        }
@@ -471,7 +445,7 @@ execute_command (char *p, int from_tty)
   /* FIXME:  This should be cacheing the frame and only running when
      the frame changes.  */
 
   /* FIXME:  This should be cacheing the frame and only running when
      the frame changes.  */
 
-  if (target_has_stack)
+  if (has_stack_frames ())
     {
       flang = get_frame_language ();
       if (!warned
     {
       flang = get_frame_language ();
       if (!warned
@@ -493,12 +467,6 @@ command_loop (void)
   struct cleanup *old_chain;
   char *command;
   int stdin_is_tty = ISATTY (stdin);
   struct cleanup *old_chain;
   char *command;
   int stdin_is_tty = ISATTY (stdin);
-  long time_at_cmd_start;
-#ifdef HAVE_SBRK
-  long space_at_cmd_start = 0;
-#endif
-  extern int display_time;
-  extern int display_space;
 
   while (instream && !feof (instream))
     {
 
   while (instream && !feof (instream))
     {
@@ -517,75 +485,12 @@ command_loop (void)
       if (command == 0)
        return;
 
       if (command == 0)
        return;
 
-      time_at_cmd_start = get_run_time ();
-
-      if (display_space)
-       {
-#ifdef HAVE_SBRK
-         char *lim = (char *) sbrk (0);
-         space_at_cmd_start = lim - lim_at_start;
-#endif
-       }
+      make_command_stats_cleanup (1);
 
       execute_command (command, instream == stdin);
 
       execute_command (command, instream == stdin);
-      /* Do any commands attached to breakpoint we stopped at.  */
-      bpstat_do_actions (&stop_bpstat);
-      do_cleanups (old_chain);
 
 
-      if (display_time)
-       {
-         long cmd_time = get_run_time () - time_at_cmd_start;
-
-         printf_unfiltered (_("Command execution time: %ld.%06ld\n"),
-                            cmd_time / 1000000, cmd_time % 1000000);
-       }
-
-      if (display_space)
-       {
-#ifdef HAVE_SBRK
-         char *lim = (char *) sbrk (0);
-         long space_now = lim - lim_at_start;
-         long space_diff = space_now - space_at_cmd_start;
-
-         printf_unfiltered (_("Space used: %ld (%c%ld for this command)\n"),
-                            space_now,
-                            (space_diff >= 0 ? '+' : '-'),
-                            space_diff);
-#endif
-       }
-    }
-}
-
-/* Read commands from `instream' and execute them until end of file or
-   error reading instream. This command loop doesnt care about any
-   such things as displaying time and space usage. If the user asks
-   for those, they won't work. */
-void
-simplified_command_loop (char *(*read_input_func) (char *),
-                        void (*execute_command_func) (char *, int))
-{
-  struct cleanup *old_chain;
-  char *command;
-  int stdin_is_tty = ISATTY (stdin);
-
-  while (instream && !feof (instream))
-    {
-      quit_flag = 0;
-      if (instream == stdin && stdin_is_tty)
-       reinitialize_more_filter ();
-      old_chain = make_cleanup (null_cleanup, 0);
-
-      /* Get a command-line. */
-      command = (*read_input_func) (instream == stdin ?
-                                   get_prompt () : (char *) NULL);
-
-      if (command == 0)
-       return;
-
-      (*execute_command_func) (command, instream == stdin);
-
-      /* Do any commands attached to breakpoint we stopped at.  */
-      bpstat_do_actions (&stop_bpstat);
+      /* Do any commands attached to breakpoint we are stopped at.  */
+      bpstat_do_actions ();
 
       do_cleanups (old_chain);
     }
 
       do_cleanups (old_chain);
     }
@@ -816,57 +721,6 @@ gdb_readline_wrapper (char *prompt)
 }
 
 \f
 }
 
 \f
-#ifdef STOP_SIGNAL
-static void
-stop_sig (int signo)
-{
-#if STOP_SIGNAL == SIGTSTP
-  signal (SIGTSTP, SIG_DFL);
-#if HAVE_SIGPROCMASK
-  {
-    sigset_t zero;
-
-    sigemptyset (&zero);
-    sigprocmask (SIG_SETMASK, &zero, 0);
-  }
-#elif HAVE_SIGSETMASK
-  sigsetmask (0);
-#endif
-  kill (getpid (), SIGTSTP);
-  signal (SIGTSTP, stop_sig);
-#else
-  signal (STOP_SIGNAL, stop_sig);
-#endif
-  printf_unfiltered ("%s", get_prompt ());
-  gdb_flush (gdb_stdout);
-
-  /* Forget about any previous command -- null line now will do nothing.  */
-  dont_repeat ();
-}
-#endif /* STOP_SIGNAL */
-
-/* Initialize signal handlers. */
-static void
-float_handler (int signo)
-{
-  /* This message is based on ANSI C, section 4.7.  Note that integer
-     divide by zero causes this, so "float" is a misnomer.  */
-  signal (SIGFPE, float_handler);
-  error (_("Erroneous arithmetic operation."));
-}
-
-static void
-do_nothing (int signo)
-{
-  /* Under System V the default disposition of a signal is reinstated after
-     the signal is caught and delivered to an application process.  On such
-     systems one must restore the replacement signal handler if one wishes
-     to continue handling the signal in one's program.  On BSD systems this
-     is not needed but it is harmless, and it simplifies the code to just do
-     it unconditionally. */
-  signal (signo, do_nothing);
-}
-
 /* The current saved history number from operate-and-get-next.
    This is -1 if not valid.  */
 static int operate_saved_history = -1;
 /* The current saved history number from operate-and-get-next.
    This is -1 if not valid.  */
 static int operate_saved_history = -1;
@@ -877,6 +731,7 @@ static void
 gdb_rl_operate_and_get_next_completion (void)
 {
   int delta = where_history () - operate_saved_history;
 gdb_rl_operate_and_get_next_completion (void)
 {
   int delta = where_history () - operate_saved_history;
+
   /* The `key' argument to rl_get_previous_history is ignored.  */
   rl_get_previous_history (delta, 0);
   operate_saved_history = -1;
   /* The `key' argument to rl_get_previous_history is ignored.  */
   rl_get_previous_history (delta, 0);
   operate_saved_history = -1;
@@ -1093,8 +948,8 @@ command_line_input (char *prompt_arg, int repeat, char *annotation_suffix)
            }
          strcpy (linebuffer, history_value);
          p = linebuffer + strlen (linebuffer);
            }
          strcpy (linebuffer, history_value);
          p = linebuffer + strlen (linebuffer);
-         xfree (history_value);
        }
        }
+      xfree (history_value);
     }
 
   /* If we just got an empty line, and that is supposed
     }
 
   /* If we just got an empty line, and that is supposed
@@ -1145,11 +1000,11 @@ print_gdb_version (struct ui_file *stream)
      program to parse, and is just canonical program name and version
      number, which starts after last space. */
 
      program to parse, and is just canonical program name and version
      number, which starts after last space. */
 
-  fprintf_filtered (stream, "GNU gdb %s\n", version);
+  fprintf_filtered (stream, "GNU gdb %s%s\n", PKGVERSION, version);
 
   /* Second line is a copyright notice. */
 
 
   /* Second line is a copyright notice. */
 
-  fprintf_filtered (stream, "Copyright (C) 2007 Free Software Foundation, Inc.\n");
+  fprintf_filtered (stream, "Copyright (C) 2010 Free Software Foundation, Inc.\n");
 
   /* Following the copyright is a brief statement that the program is
      free software, that users are free to copy and change it on
 
   /* Following the copyright is a brief statement that the program is
      free software, that users are free to copy and change it on
@@ -1157,10 +1012,10 @@ print_gdb_version (struct ui_file *stream)
      there is no warranty. */
 
   fprintf_filtered (stream, "\
      there is no warranty. */
 
   fprintf_filtered (stream, "\
-GDB is free software, covered by the GNU General Public License, and you are\n\
-welcome to change it and/or distribute copies of it under certain conditions.\n\
-Type \"show copying\" to see the conditions.\n\
-There is absolutely no warranty for GDB.  Type \"show warranty\" for details.\n");
+License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>\n\
+This is free software: you are free to change and redistribute it.\n\
+There is NO WARRANTY, to the extent permitted by law.  Type \"show copying\"\n\
+and \"show warranty\" for details.\n");
 
   /* After the required info we print the configuration information. */
 
 
   /* After the required info we print the configuration information. */
 
@@ -1174,6 +1029,13 @@ There is absolutely no warranty for GDB.  Type \"show warranty\" for details.\n"
       fprintf_filtered (stream, "%s", host_name);
     }
   fprintf_filtered (stream, "\".");
       fprintf_filtered (stream, "%s", host_name);
     }
   fprintf_filtered (stream, "\".");
+
+  if (REPORT_BUGS_TO[0])
+    {
+      fprintf_filtered (stream, 
+                       _("\nFor bug reporting instructions, please see:\n"));
+      fprintf_filtered (stream, "%s.", REPORT_BUGS_TO);
+    }
 }
 \f
 /* get_prompt: access method for the GDB prompt string.  */
 }
 \f
 /* get_prompt: access method for the GDB prompt string.  */
@@ -1188,64 +1050,127 @@ void
 set_prompt (char *s)
 {
 /* ??rehrauer: I don't know why this fails, since it looks as though
 set_prompt (char *s)
 {
 /* ??rehrauer: I don't know why this fails, since it looks as though
-   assignments to prompt are wrapped in calls to savestring...
+   assignments to prompt are wrapped in calls to xstrdup...
    if (prompt != NULL)
    xfree (prompt);
  */
    if (prompt != NULL)
    xfree (prompt);
  */
-  PROMPT (0) = savestring (s, strlen (s));
+  PROMPT (0) = xstrdup (s);
 }
 \f
 
 }
 \f
 
+struct qt_args
+{
+  char *args;
+  int from_tty;
+};
+
+/* Callback for iterate_over_inferiors.  Kills or detaches the given
+   inferior, depending on how we originally gained control of it.  */
+
+static int
+kill_or_detach (struct inferior *inf, void *args)
+{
+  struct qt_args *qt = args;
+  struct thread_info *thread;
+
+  if (inf->pid == 0)
+    return 0;
+
+  thread = any_thread_of_process (inf->pid);
+  if (thread != NULL)
+    {
+      switch_to_thread (thread->ptid);
+
+      /* Leave core files alone.  */
+      if (target_has_execution)
+       {
+         if (inf->attach_flag)
+           target_detach (qt->args, qt->from_tty);
+         else
+           target_kill ();
+       }
+    }
+
+  return 0;
+}
+
+/* Callback for iterate_over_inferiors.  Prints info about what GDB
+   will do to each inferior on a "quit".  ARG points to a struct
+   ui_out where output is to be collected.  */
+
+static int
+print_inferior_quit_action (struct inferior *inf, void *arg)
+{
+  struct ui_file *stb = arg;
+
+  if (inf->pid == 0)
+    return 0;
+
+  if (inf->attach_flag)
+    fprintf_filtered (stb,
+                     _("\tInferior %d [%s] will be detached.\n"), inf->num,
+                     target_pid_to_str (pid_to_ptid (inf->pid)));
+  else
+    fprintf_filtered (stb,
+                     _("\tInferior %d [%s] will be killed.\n"), inf->num,
+                     target_pid_to_str (pid_to_ptid (inf->pid)));
+
+  return 0;
+}
+
 /* If necessary, make the user confirm that we should quit.  Return
    non-zero if we should quit, zero if we shouldn't.  */
 
 int
 quit_confirm (void)
 {
 /* If necessary, make the user confirm that we should quit.  Return
    non-zero if we should quit, zero if we shouldn't.  */
 
 int
 quit_confirm (void)
 {
-  if (! ptid_equal (inferior_ptid, null_ptid) && target_has_execution)
-    {
-      char *s;
-
-      /* This is something of a hack.  But there's no reliable way to
-         see if a GUI is running.  The `use_windows' variable doesn't
-         cut it.  */
-      if (deprecated_init_ui_hook)
-       s = "A debugging session is active.\nDo you still want to close the debugger?";
-      else if (attach_flag)
-       s = "The program is running.  Quit anyway (and detach it)? ";
-      else
-       s = "The program is running.  Exit anyway? ";
+  struct ui_file *stb;
+  struct cleanup *old_chain;
+  char *str;
+  int qr;
+
+  /* Don't even ask if we're only debugging a core file inferior.  */
+  if (!have_live_inferiors ())
+    return 1;
 
 
-      if (!query ("%s", s))
-       return 0;
+  /* Build the query string as a single string.  */
+  stb = mem_fileopen ();
+  old_chain = make_cleanup_ui_file_delete (stb);
+
+  /* This is something of a hack.  But there's no reliable way to see
+     if a GUI is running.  The `use_windows' variable doesn't cut
+     it.  */
+  if (deprecated_init_ui_hook)
+    fprintf_filtered (stb, _("A debugging session is active.\n"
+                            "Do you still want to close the debugger?"));
+  else
+    {
+      fprintf_filtered (stb, _("A debugging session is active.\n\n"));
+      iterate_over_inferiors (print_inferior_quit_action, stb);
+      fprintf_filtered (stb, _("\nQuit anyway? "));
     }
 
     }
 
-  return 1;
+  str = ui_file_xstrdup (stb, NULL);
+  make_cleanup (xfree, str);
+
+  qr = query ("%s", str);
+  do_cleanups (old_chain);
+  return qr;
 }
 
 /* Helper routine for quit_force that requires error handling.  */
 
 }
 
 /* Helper routine for quit_force that requires error handling.  */
 
-struct qt_args
-{
-  char *args;
-  int from_tty;
-};
-
 static int
 quit_target (void *arg)
 {
   struct qt_args *qt = (struct qt_args *)arg;
 
 static int
 quit_target (void *arg)
 {
   struct qt_args *qt = (struct qt_args *)arg;
 
-  if (! ptid_equal (inferior_ptid, null_ptid) && target_has_execution)
-    {
-      if (attach_flag)
-        target_detach (qt->args, qt->from_tty);
-      else
-        target_kill ();
-    }
+  /* Kill or detach all inferiors.  */
+  iterate_over_inferiors (kill_or_detach, qt);
 
 
-  /* UDI wants this, to kill the TIP.  */
-  target_close (&current_target, 1);
+  /* Give all pushed targets a chance to do minimal cleanup, and pop
+     them all out.  */
+  pop_all_targets (1);
 
   /* Save the history information if it is appropriate to do so.  */
   if (write_history_p && history_filename)
 
   /* Save the history information if it is appropriate to do so.  */
   if (write_history_p && history_filename)
@@ -1285,12 +1210,38 @@ quit_force (char *args, int from_tty)
   exit (exit_code);
 }
 
   exit (exit_code);
 }
 
+/* If OFF, the debugger will run in non-interactive mode, which means
+   that it will automatically select the default answer to all the
+   queries made to the user.  If ON, gdb will wait for the user to
+   answer all queries.  If AUTO, gdb will determine whether to run
+   in interactive mode or not depending on whether stdin is a terminal
+   or not.  */
+static enum auto_boolean interactive_mode = AUTO_BOOLEAN_AUTO;
+
+/* Implement the "show interactive-mode" option.  */
+
+static void
+show_interactive_mode (struct ui_file *file, int from_tty,
+                       struct cmd_list_element *c,
+                       const char *value)
+{
+  if (interactive_mode == AUTO_BOOLEAN_AUTO)
+    fprintf_filtered (file, "\
+Debugger's interactive mode is %s (currently %s).\n",
+                      value, input_from_terminal_p () ? "on" : "off");
+  else
+    fprintf_filtered (file, "Debugger's interactive mode is %s.\n", value);
+}
+
 /* Returns whether GDB is running on a terminal and input is
    currently coming from that terminal.  */
 
 int
 input_from_terminal_p (void)
 {
 /* Returns whether GDB is running on a terminal and input is
    currently coming from that terminal.  */
 
 int
 input_from_terminal_p (void)
 {
+  if (interactive_mode != AUTO_BOOLEAN_AUTO)
+    return interactive_mode == AUTO_BOOLEAN_TRUE;
+
   if (gdb_has_a_terminal () && instream == stdin)
     return 1;
 
   if (gdb_has_a_terminal () && instream == stdin)
     return 1;
 
@@ -1459,7 +1410,7 @@ init_history (void)
 
   tmpenv = getenv ("GDBHISTFILE");
   if (tmpenv)
 
   tmpenv = getenv ("GDBHISTFILE");
   if (tmpenv)
-    history_filename = savestring (tmpenv, strlen (tmpenv));
+    history_filename = xstrdup (tmpenv);
   else if (!history_filename)
     {
       /* We include the current directory so that if the user changes
   else if (!history_filename)
     {
       /* We include the current directory so that if the user changes
@@ -1511,19 +1462,17 @@ Notification of completion for asynchronous execution commands is %s.\n"),
 static void
 init_main (void)
 {
 static void
 init_main (void)
 {
-  struct cmd_list_element *c;
-
   /* initialize the prompt stack to a simple "(gdb) " prompt or to
      whatever the DEFAULT_PROMPT is.  */
   the_prompts.top = 0;
   PREFIX (0) = "";
   /* initialize the prompt stack to a simple "(gdb) " prompt or to
      whatever the DEFAULT_PROMPT is.  */
   the_prompts.top = 0;
   PREFIX (0) = "";
-  PROMPT (0) = savestring (DEFAULT_PROMPT, strlen (DEFAULT_PROMPT));
+  PROMPT (0) = xstrdup (DEFAULT_PROMPT);
   SUFFIX (0) = "";
   /* Set things up for annotation_level > 1, if the user ever decides
      to use it.  */
   async_annotation_suffix = "prompt";
   /* Set the variable associated with the setshow prompt command.  */
   SUFFIX (0) = "";
   /* Set things up for annotation_level > 1, if the user ever decides
      to use it.  */
   async_annotation_suffix = "prompt";
   /* Set the variable associated with the setshow prompt command.  */
-  new_async_prompt = savestring (PROMPT (0), strlen (PROMPT (0)));
+  new_async_prompt = xstrdup (PROMPT (0));
 
   /* If gdb was started with --annotate=2, this is equivalent to the
      user entering the command 'set annotate 2' at the gdb prompt, so
 
   /* If gdb was started with --annotate=2, this is equivalent to the
      user entering the command 'set annotate 2' at the gdb prompt, so
@@ -1537,6 +1486,7 @@ init_main (void)
   write_history_p = 0;
 
   /* Setup important stuff for command line editing.  */
   write_history_p = 0;
 
   /* Setup important stuff for command line editing.  */
+  rl_completion_word_break_hook = gdb_completion_word_break_characters;
   rl_completion_entry_function = readline_line_completion_function;
   rl_completer_word_break_characters = default_word_break_characters ();
   rl_completer_quote_characters = get_gdb_completer_quote_characters ();
   rl_completion_entry_function = readline_line_completion_function;
   rl_completer_word_break_characters = default_word_break_characters ();
   rl_completer_quote_characters = get_gdb_completer_quote_characters ();
@@ -1620,6 +1570,27 @@ Use \"on\" to enable the notification, and \"off\" to disable it."),
                           NULL,
                           show_exec_done_display_p,
                           &setlist, &showlist);
                           NULL,
                           show_exec_done_display_p,
                           &setlist, &showlist);
+
+  add_setshow_auto_boolean_cmd ("interactive-mode", class_support,
+                                &interactive_mode, _("\
+Set whether GDB should run in interactive mode or not"), _("\
+Show whether GDB runs in interactive mode"), _("\
+If on, run in interactive mode and wait for the user to answer\n\
+all queries.  If off, run in non-interactive mode and automatically\n\
+assume the default answer to all queries.  If auto (the default),\n\
+determine which mode to use based on the standard input settings"),
+                        NULL,
+                        show_interactive_mode,
+                        &setlist, &showlist);
+
+  add_setshow_filename_cmd ("data-directory", class_maintenance,
+                           &gdb_datadir, _("Set GDB's data directory."),
+                           _("Show GDB's data directory."),
+                           _("\
+When set, GDB uses the specified path to search for data files."),
+                           NULL, NULL,
+                           &setlist,
+                           &showlist);
 }
 
 void
 }
 
 void
@@ -1630,9 +1601,6 @@ gdb_init (char *argv0)
 
   /* Run the init function of each source file */
 
 
   /* Run the init function of each source file */
 
-  getcwd (gdb_dirbuf, sizeof (gdb_dirbuf));
-  current_directory = gdb_dirbuf;
-
 #ifdef __MSDOS__
   /* Make sure we return to the original directory upon exit, come
      what may, since the OS doesn't do that for us.  */
 #ifdef __MSDOS__
   /* Make sure we return to the original directory upon exit, come
      what may, since the OS doesn't do that for us.  */
@@ -1643,6 +1611,13 @@ gdb_init (char *argv0)
   initialize_targets ();       /* Setup target_terminal macros for utils.c */
   initialize_utils ();         /* Make errors and warnings possible */
   initialize_all_files ();
   initialize_targets ();       /* Setup target_terminal macros for utils.c */
   initialize_utils ();         /* Make errors and warnings possible */
   initialize_all_files ();
+  /* This creates the current_program_space.  Do this after all the
+     _initialize_foo routines have had a chance to install their
+     per-sspace data keys.  Also do this before
+     initialize_current_architecture is called, because it accesses
+     exec_bfd of the current program space.  */
+  initialize_progspace ();
+  initialize_inferiors ();
   initialize_current_architecture ();
   init_cli_cmds();
   init_main ();                        /* But that omits this file!  Do it now */
   initialize_current_architecture ();
   init_cli_cmds();
   init_main ();                        /* But that omits this file!  Do it now */
This page took 0.03232 seconds and 4 git commands to generate.