OpenCores
URL https://opencores.org/ocsvn/openrisc/openrisc/trunk

Subversion Repositories openrisc

[/] [openrisc/] [trunk/] [gnu-old/] [gdb-7.1/] [gdb/] [inferior.c] - Diff between revs 834 and 842

Go to most recent revision | Only display areas with differences | Details | Blame | View Log

Rev 834 Rev 842
/* Multi-process control for GDB, the GNU debugger.
/* Multi-process control for GDB, the GNU debugger.
 
 
   Copyright (C) 2008, 2009, 2010 Free Software Foundation, Inc.
   Copyright (C) 2008, 2009, 2010 Free Software Foundation, Inc.
 
 
   This file is part of GDB.
   This file is part of GDB.
 
 
   This program is free software; you can redistribute it and/or modify
   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
   it under the terms of the GNU General Public License as published by
   the Free Software Foundation; either version 3 of the License, or
   the Free Software Foundation; either version 3 of the License, or
   (at your option) any later version.
   (at your option) any later version.
 
 
   This program is distributed in the hope that it will be useful,
   This program is distributed in the hope that it will be useful,
   but WITHOUT ANY WARRANTY; without even the implied warranty of
   but WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   GNU General Public License for more details.
   GNU General Public License for more details.
 
 
   You should have received a copy of the GNU General Public License
   You should have received a copy of the GNU General Public License
   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
 
 
#include "defs.h"
#include "defs.h"
#include "exec.h"
#include "exec.h"
#include "inferior.h"
#include "inferior.h"
#include "target.h"
#include "target.h"
#include "command.h"
#include "command.h"
#include "gdbcmd.h"
#include "gdbcmd.h"
#include "gdbthread.h"
#include "gdbthread.h"
#include "ui-out.h"
#include "ui-out.h"
#include "observer.h"
#include "observer.h"
#include "gdbthread.h"
#include "gdbthread.h"
#include "gdbcore.h"
#include "gdbcore.h"
#include "symfile.h"
#include "symfile.h"
#include "environ.h"
#include "environ.h"
 
 
void _initialize_inferiors (void);
void _initialize_inferiors (void);
 
 
static void inferior_alloc_data (struct inferior *inf);
static void inferior_alloc_data (struct inferior *inf);
static void inferior_free_data (struct inferior *inf);
static void inferior_free_data (struct inferior *inf);
 
 
struct inferior *inferior_list = NULL;
struct inferior *inferior_list = NULL;
static int highest_inferior_num;
static int highest_inferior_num;
 
 
/* Print notices on inferior events (attach, detach, etc.), set with
/* Print notices on inferior events (attach, detach, etc.), set with
   `set print inferior-events'.  */
   `set print inferior-events'.  */
static int print_inferior_events = 0;
static int print_inferior_events = 0;
 
 
/* The Current Inferior.  */
/* The Current Inferior.  */
static struct inferior *current_inferior_ = NULL;
static struct inferior *current_inferior_ = NULL;
 
 
struct inferior*
struct inferior*
current_inferior (void)
current_inferior (void)
{
{
  return current_inferior_;
  return current_inferior_;
}
}
 
 
void
void
set_current_inferior (struct inferior *inf)
set_current_inferior (struct inferior *inf)
{
{
  /* There's always an inferior.  */
  /* There's always an inferior.  */
  gdb_assert (inf != NULL);
  gdb_assert (inf != NULL);
 
 
  current_inferior_ = inf;
  current_inferior_ = inf;
}
}
 
 
/* A cleanups callback, helper for save_current_program_space
/* A cleanups callback, helper for save_current_program_space
   below.  */
   below.  */
 
 
static void
static void
restore_inferior (void *arg)
restore_inferior (void *arg)
{
{
  struct inferior *saved_inferior = arg;
  struct inferior *saved_inferior = arg;
  set_current_inferior (saved_inferior);
  set_current_inferior (saved_inferior);
}
}
 
 
/* Save the current program space so that it may be restored by a later
/* Save the current program space so that it may be restored by a later
   call to do_cleanups.  Returns the struct cleanup pointer needed for
   call to do_cleanups.  Returns the struct cleanup pointer needed for
   later doing the cleanup.  */
   later doing the cleanup.  */
 
 
struct cleanup *
struct cleanup *
save_current_inferior (void)
save_current_inferior (void)
{
{
  struct cleanup *old_chain = make_cleanup (restore_inferior,
  struct cleanup *old_chain = make_cleanup (restore_inferior,
                                            current_inferior_);
                                            current_inferior_);
  return old_chain;
  return old_chain;
}
}
 
 
static void
static void
free_inferior (struct inferior *inf)
free_inferior (struct inferior *inf)
{
{
  discard_all_inferior_continuations (inf);
  discard_all_inferior_continuations (inf);
  inferior_free_data (inf);
  inferior_free_data (inf);
  xfree (inf->args);
  xfree (inf->args);
  xfree (inf->terminal);
  xfree (inf->terminal);
  free_environ (inf->environment);
  free_environ (inf->environment);
  xfree (inf->private);
  xfree (inf->private);
  xfree (inf);
  xfree (inf);
}
}
 
 
void
void
init_inferior_list (void)
init_inferior_list (void)
{
{
  struct inferior *inf, *infnext;
  struct inferior *inf, *infnext;
 
 
  highest_inferior_num = 0;
  highest_inferior_num = 0;
  if (!inferior_list)
  if (!inferior_list)
    return;
    return;
 
 
  for (inf = inferior_list; inf; inf = infnext)
  for (inf = inferior_list; inf; inf = infnext)
    {
    {
      infnext = inf->next;
      infnext = inf->next;
      free_inferior (inf);
      free_inferior (inf);
    }
    }
 
 
  inferior_list = NULL;
  inferior_list = NULL;
}
}
 
 
struct inferior *
struct inferior *
add_inferior_silent (int pid)
add_inferior_silent (int pid)
{
{
  struct inferior *inf;
  struct inferior *inf;
 
 
  inf = xmalloc (sizeof (*inf));
  inf = xmalloc (sizeof (*inf));
  memset (inf, 0, sizeof (*inf));
  memset (inf, 0, sizeof (*inf));
  inf->pid = pid;
  inf->pid = pid;
 
 
  inf->stop_soon = NO_STOP_QUIETLY;
  inf->stop_soon = NO_STOP_QUIETLY;
 
 
  inf->num = ++highest_inferior_num;
  inf->num = ++highest_inferior_num;
  inf->next = inferior_list;
  inf->next = inferior_list;
  inferior_list = inf;
  inferior_list = inf;
 
 
  inf->environment = make_environ ();
  inf->environment = make_environ ();
  init_environ (inf->environment);
  init_environ (inf->environment);
 
 
  inferior_alloc_data (inf);
  inferior_alloc_data (inf);
 
 
  if (pid != 0)
  if (pid != 0)
    inferior_appeared (inf, pid);
    inferior_appeared (inf, pid);
 
 
  return inf;
  return inf;
}
}
 
 
struct inferior *
struct inferior *
add_inferior (int pid)
add_inferior (int pid)
{
{
  struct inferior *inf = add_inferior_silent (pid);
  struct inferior *inf = add_inferior_silent (pid);
 
 
  if (print_inferior_events)
  if (print_inferior_events)
    printf_unfiltered (_("[New inferior %d]\n"), pid);
    printf_unfiltered (_("[New inferior %d]\n"), pid);
 
 
  return inf;
  return inf;
}
}
 
 
struct delete_thread_of_inferior_arg
struct delete_thread_of_inferior_arg
{
{
  int pid;
  int pid;
  int silent;
  int silent;
};
};
 
 
static int
static int
delete_thread_of_inferior (struct thread_info *tp, void *data)
delete_thread_of_inferior (struct thread_info *tp, void *data)
{
{
  struct delete_thread_of_inferior_arg *arg = data;
  struct delete_thread_of_inferior_arg *arg = data;
 
 
  if (ptid_get_pid (tp->ptid) == arg->pid)
  if (ptid_get_pid (tp->ptid) == arg->pid)
    {
    {
      if (arg->silent)
      if (arg->silent)
        delete_thread_silent (tp->ptid);
        delete_thread_silent (tp->ptid);
      else
      else
        delete_thread (tp->ptid);
        delete_thread (tp->ptid);
    }
    }
 
 
  return 0;
  return 0;
}
}
 
 
void
void
delete_threads_of_inferior (int pid)
delete_threads_of_inferior (int pid)
{
{
  struct inferior *inf;
  struct inferior *inf;
  struct delete_thread_of_inferior_arg arg;
  struct delete_thread_of_inferior_arg arg;
 
 
  for (inf = inferior_list; inf; inf = inf->next)
  for (inf = inferior_list; inf; inf = inf->next)
    if (inf->pid == pid)
    if (inf->pid == pid)
      break;
      break;
 
 
  if (!inf)
  if (!inf)
    return;
    return;
 
 
  arg.pid = pid;
  arg.pid = pid;
  arg.silent = 1;
  arg.silent = 1;
 
 
  iterate_over_threads (delete_thread_of_inferior, &arg);
  iterate_over_threads (delete_thread_of_inferior, &arg);
}
}
 
 
/* If SILENT then be quiet -- don't announce a inferior death, or the
/* If SILENT then be quiet -- don't announce a inferior death, or the
   exit of its threads.  */
   exit of its threads.  */
 
 
static void
static void
delete_inferior_1 (struct inferior *todel, int silent)
delete_inferior_1 (struct inferior *todel, int silent)
{
{
  struct inferior *inf, *infprev;
  struct inferior *inf, *infprev;
  struct delete_thread_of_inferior_arg arg;
  struct delete_thread_of_inferior_arg arg;
 
 
  infprev = NULL;
  infprev = NULL;
 
 
  for (inf = inferior_list; inf; infprev = inf, inf = inf->next)
  for (inf = inferior_list; inf; infprev = inf, inf = inf->next)
    if (inf == todel)
    if (inf == todel)
      break;
      break;
 
 
  if (!inf)
  if (!inf)
    return;
    return;
 
 
  arg.pid = inf->pid;
  arg.pid = inf->pid;
  arg.silent = silent;
  arg.silent = silent;
 
 
  iterate_over_threads (delete_thread_of_inferior, &arg);
  iterate_over_threads (delete_thread_of_inferior, &arg);
 
 
  if (infprev)
  if (infprev)
    infprev->next = inf->next;
    infprev->next = inf->next;
  else
  else
    inferior_list = inf->next;
    inferior_list = inf->next;
 
 
  free_inferior (inf);
  free_inferior (inf);
}
}
 
 
void
void
delete_inferior (int pid)
delete_inferior (int pid)
{
{
  struct inferior *inf = find_inferior_pid (pid);
  struct inferior *inf = find_inferior_pid (pid);
 
 
  delete_inferior_1 (inf, 0);
  delete_inferior_1 (inf, 0);
 
 
  if (print_inferior_events)
  if (print_inferior_events)
    printf_unfiltered (_("[Inferior %d exited]\n"), pid);
    printf_unfiltered (_("[Inferior %d exited]\n"), pid);
}
}
 
 
void
void
delete_inferior_silent (int pid)
delete_inferior_silent (int pid)
{
{
  struct inferior *inf = find_inferior_pid (pid);
  struct inferior *inf = find_inferior_pid (pid);
 
 
  delete_inferior_1 (inf, 1);
  delete_inferior_1 (inf, 1);
}
}
 
 
 
 
/* If SILENT then be quiet -- don't announce a inferior exit, or the
/* If SILENT then be quiet -- don't announce a inferior exit, or the
   exit of its threads.  */
   exit of its threads.  */
 
 
static void
static void
exit_inferior_1 (struct inferior *inftoex, int silent)
exit_inferior_1 (struct inferior *inftoex, int silent)
{
{
  struct inferior *inf;
  struct inferior *inf;
  struct delete_thread_of_inferior_arg arg;
  struct delete_thread_of_inferior_arg arg;
 
 
  for (inf = inferior_list; inf; inf = inf->next)
  for (inf = inferior_list; inf; inf = inf->next)
    if (inf == inftoex)
    if (inf == inftoex)
      break;
      break;
 
 
  if (!inf)
  if (!inf)
    return;
    return;
 
 
  arg.pid = inf->pid;
  arg.pid = inf->pid;
  arg.silent = silent;
  arg.silent = silent;
 
 
  iterate_over_threads (delete_thread_of_inferior, &arg);
  iterate_over_threads (delete_thread_of_inferior, &arg);
 
 
  /* Notify the observers before removing the inferior from the list,
  /* Notify the observers before removing the inferior from the list,
     so that the observers have a chance to look it up.  */
     so that the observers have a chance to look it up.  */
  observer_notify_inferior_exit (inf->pid);
  observer_notify_inferior_exit (inf->pid);
 
 
  inf->pid = 0;
  inf->pid = 0;
  if (inf->vfork_parent != NULL)
  if (inf->vfork_parent != NULL)
    {
    {
      inf->vfork_parent->vfork_child = NULL;
      inf->vfork_parent->vfork_child = NULL;
      inf->vfork_parent = NULL;
      inf->vfork_parent = NULL;
    }
    }
}
}
 
 
void
void
exit_inferior (int pid)
exit_inferior (int pid)
{
{
  struct inferior *inf = find_inferior_pid (pid);
  struct inferior *inf = find_inferior_pid (pid);
  exit_inferior_1 (inf, 0);
  exit_inferior_1 (inf, 0);
 
 
  if (print_inferior_events)
  if (print_inferior_events)
    printf_unfiltered (_("[Inferior %d exited]\n"), pid);
    printf_unfiltered (_("[Inferior %d exited]\n"), pid);
}
}
 
 
void
void
exit_inferior_silent (int pid)
exit_inferior_silent (int pid)
{
{
  struct inferior *inf = find_inferior_pid (pid);
  struct inferior *inf = find_inferior_pid (pid);
  exit_inferior_1 (inf, 1);
  exit_inferior_1 (inf, 1);
}
}
 
 
void
void
exit_inferior_num_silent (int num)
exit_inferior_num_silent (int num)
{
{
  struct inferior *inf = find_inferior_id (num);
  struct inferior *inf = find_inferior_id (num);
 
 
  exit_inferior_1 (inf, 1);
  exit_inferior_1 (inf, 1);
}
}
 
 
void
void
detach_inferior (int pid)
detach_inferior (int pid)
{
{
  struct inferior *inf = find_inferior_pid (pid);
  struct inferior *inf = find_inferior_pid (pid);
  exit_inferior_1 (inf, 1);
  exit_inferior_1 (inf, 1);
 
 
  if (print_inferior_events)
  if (print_inferior_events)
    printf_unfiltered (_("[Inferior %d detached]\n"), pid);
    printf_unfiltered (_("[Inferior %d detached]\n"), pid);
}
}
 
 
void
void
inferior_appeared (struct inferior *inf, int pid)
inferior_appeared (struct inferior *inf, int pid)
{
{
  inf->pid = pid;
  inf->pid = pid;
 
 
  observer_notify_inferior_appeared (pid);
  observer_notify_inferior_appeared (pid);
}
}
 
 
void
void
discard_all_inferiors (void)
discard_all_inferiors (void)
{
{
  struct inferior *inf;
  struct inferior *inf;
 
 
  for (inf = inferior_list; inf; inf = inf->next)
  for (inf = inferior_list; inf; inf = inf->next)
    {
    {
      if (inf->pid != 0)
      if (inf->pid != 0)
        exit_inferior_silent (inf->pid);
        exit_inferior_silent (inf->pid);
    }
    }
}
}
 
 
struct inferior *
struct inferior *
find_inferior_id (int num)
find_inferior_id (int num)
{
{
  struct inferior *inf;
  struct inferior *inf;
 
 
  for (inf = inferior_list; inf; inf = inf->next)
  for (inf = inferior_list; inf; inf = inf->next)
    if (inf->num == num)
    if (inf->num == num)
      return inf;
      return inf;
 
 
  return NULL;
  return NULL;
}
}
 
 
struct inferior *
struct inferior *
find_inferior_pid (int pid)
find_inferior_pid (int pid)
{
{
  struct inferior *inf;
  struct inferior *inf;
 
 
  /* Looking for inferior pid == 0 is always wrong, and indicative of
  /* Looking for inferior pid == 0 is always wrong, and indicative of
     a bug somewhere else.  There may be more than one with pid == 0,
     a bug somewhere else.  There may be more than one with pid == 0,
     for instance.  */
     for instance.  */
  gdb_assert (pid != 0);
  gdb_assert (pid != 0);
 
 
  for (inf = inferior_list; inf; inf = inf->next)
  for (inf = inferior_list; inf; inf = inf->next)
    if (inf->pid == pid)
    if (inf->pid == pid)
      return inf;
      return inf;
 
 
  return NULL;
  return NULL;
}
}
 
 
/* Find an inferior bound to PSPACE.  */
/* Find an inferior bound to PSPACE.  */
 
 
struct inferior *
struct inferior *
find_inferior_for_program_space (struct program_space *pspace)
find_inferior_for_program_space (struct program_space *pspace)
{
{
  struct inferior *inf;
  struct inferior *inf;
 
 
  for (inf = inferior_list; inf != NULL; inf = inf->next)
  for (inf = inferior_list; inf != NULL; inf = inf->next)
    {
    {
      if (inf->pspace == pspace)
      if (inf->pspace == pspace)
        return inf;
        return inf;
    }
    }
 
 
  return NULL;
  return NULL;
}
}
 
 
struct inferior *
struct inferior *
iterate_over_inferiors (int (*callback) (struct inferior *, void *),
iterate_over_inferiors (int (*callback) (struct inferior *, void *),
                        void *data)
                        void *data)
{
{
  struct inferior *inf, *infnext;
  struct inferior *inf, *infnext;
 
 
  for (inf = inferior_list; inf; inf = infnext)
  for (inf = inferior_list; inf; inf = infnext)
    {
    {
      infnext = inf->next;
      infnext = inf->next;
      if ((*callback) (inf, data))
      if ((*callback) (inf, data))
        return inf;
        return inf;
    }
    }
 
 
  return NULL;
  return NULL;
}
}
 
 
int
int
valid_gdb_inferior_id (int num)
valid_gdb_inferior_id (int num)
{
{
  struct inferior *inf;
  struct inferior *inf;
 
 
  for (inf = inferior_list; inf; inf = inf->next)
  for (inf = inferior_list; inf; inf = inf->next)
    if (inf->num == num)
    if (inf->num == num)
      return 1;
      return 1;
 
 
  return 0;
  return 0;
}
}
 
 
int
int
pid_to_gdb_inferior_id (int pid)
pid_to_gdb_inferior_id (int pid)
{
{
  struct inferior *inf;
  struct inferior *inf;
 
 
  for (inf = inferior_list; inf; inf = inf->next)
  for (inf = inferior_list; inf; inf = inf->next)
    if (inf->pid == pid)
    if (inf->pid == pid)
      return inf->num;
      return inf->num;
 
 
  return 0;
  return 0;
}
}
 
 
int
int
gdb_inferior_id_to_pid (int num)
gdb_inferior_id_to_pid (int num)
{
{
  struct inferior *inferior = find_inferior_id (num);
  struct inferior *inferior = find_inferior_id (num);
  if (inferior)
  if (inferior)
    return inferior->pid;
    return inferior->pid;
  else
  else
    return -1;
    return -1;
}
}
 
 
int
int
in_inferior_list (int pid)
in_inferior_list (int pid)
{
{
  struct inferior *inf;
  struct inferior *inf;
 
 
  for (inf = inferior_list; inf; inf = inf->next)
  for (inf = inferior_list; inf; inf = inf->next)
    if (inf->pid == pid)
    if (inf->pid == pid)
      return 1;
      return 1;
 
 
  return 0;
  return 0;
}
}
 
 
int
int
have_inferiors (void)
have_inferiors (void)
{
{
  struct inferior *inf;
  struct inferior *inf;
 
 
  for (inf = inferior_list; inf; inf = inf->next)
  for (inf = inferior_list; inf; inf = inf->next)
    if (inf->pid != 0)
    if (inf->pid != 0)
      return 1;
      return 1;
 
 
  return 0;
  return 0;
}
}
 
 
int
int
have_live_inferiors (void)
have_live_inferiors (void)
{
{
  struct target_ops *t;
  struct target_ops *t;
 
 
  /* The check on stratum suffices, as GDB doesn't currently support
  /* The check on stratum suffices, as GDB doesn't currently support
     multiple target interfaces.  */
     multiple target interfaces.  */
  if (have_inferiors ())
  if (have_inferiors ())
    for (t = current_target.beneath; t != NULL; t = t->beneath)
    for (t = current_target.beneath; t != NULL; t = t->beneath)
      if (t->to_stratum == process_stratum)
      if (t->to_stratum == process_stratum)
        return 1;
        return 1;
 
 
  return 0;
  return 0;
}
}
 
 
/* Prune away automatically added program spaces that aren't required
/* Prune away automatically added program spaces that aren't required
   anymore.  */
   anymore.  */
 
 
void
void
prune_inferiors (void)
prune_inferiors (void)
{
{
  struct inferior *ss, **ss_link;
  struct inferior *ss, **ss_link;
  struct inferior *current = current_inferior ();
  struct inferior *current = current_inferior ();
 
 
  ss = inferior_list;
  ss = inferior_list;
  ss_link = &inferior_list;
  ss_link = &inferior_list;
  while (ss)
  while (ss)
    {
    {
      if (ss == current
      if (ss == current
          || !ss->removable
          || !ss->removable
          || ss->pid != 0)
          || ss->pid != 0)
        {
        {
          ss_link = &ss->next;
          ss_link = &ss->next;
          ss = *ss_link;
          ss = *ss_link;
          continue;
          continue;
        }
        }
 
 
      *ss_link = ss->next;
      *ss_link = ss->next;
      delete_inferior_1 (ss, 1);
      delete_inferior_1 (ss, 1);
      ss = *ss_link;
      ss = *ss_link;
    }
    }
 
 
  prune_program_spaces ();
  prune_program_spaces ();
}
}
 
 
/* Simply returns the count of inferiors.  */
/* Simply returns the count of inferiors.  */
 
 
int
int
number_of_inferiors (void)
number_of_inferiors (void)
{
{
  struct inferior *inf;
  struct inferior *inf;
  int count = 0;
  int count = 0;
 
 
  for (inf = inferior_list; inf != NULL; inf = inf->next)
  for (inf = inferior_list; inf != NULL; inf = inf->next)
    count++;
    count++;
 
 
  return count;
  return count;
}
}
 
 
/* Prints the list of inferiors and their details on UIOUT.  This is a
/* Prints the list of inferiors and their details on UIOUT.  This is a
   version of 'info_inferior_command' suitable for use from MI.
   version of 'info_inferior_command' suitable for use from MI.
 
 
   If REQUESTED_INFERIOR is not -1, it's the GDB id of the inferior that
   If REQUESTED_INFERIOR is not -1, it's the GDB id of the inferior that
   should be printed.  Otherwise, all inferiors are printed.  */
   should be printed.  Otherwise, all inferiors are printed.  */
void
void
print_inferior (struct ui_out *uiout, int requested_inferior)
print_inferior (struct ui_out *uiout, int requested_inferior)
{
{
  struct inferior *inf;
  struct inferior *inf;
  struct cleanup *old_chain;
  struct cleanup *old_chain;
  int inf_count = 0;
  int inf_count = 0;
 
 
  /* Compute number of inferiors we will print.  */
  /* Compute number of inferiors we will print.  */
  for (inf = inferior_list; inf; inf = inf->next)
  for (inf = inferior_list; inf; inf = inf->next)
    {
    {
      struct cleanup *chain2;
      struct cleanup *chain2;
 
 
      if (requested_inferior != -1 && inf->num != requested_inferior)
      if (requested_inferior != -1 && inf->num != requested_inferior)
        continue;
        continue;
 
 
      ++inf_count;
      ++inf_count;
    }
    }
 
 
  if (inf_count == 0)
  if (inf_count == 0)
    {
    {
      ui_out_message (uiout, 0, "No inferiors.\n");
      ui_out_message (uiout, 0, "No inferiors.\n");
      return;
      return;
    }
    }
 
 
  old_chain = make_cleanup_ui_out_table_begin_end (uiout, 4, inf_count,
  old_chain = make_cleanup_ui_out_table_begin_end (uiout, 4, inf_count,
                                                   "inferiors");
                                                   "inferiors");
  ui_out_table_header (uiout, 1, ui_left, "current", "");
  ui_out_table_header (uiout, 1, ui_left, "current", "");
  ui_out_table_header (uiout, 4, ui_left, "number", "Num");
  ui_out_table_header (uiout, 4, ui_left, "number", "Num");
  ui_out_table_header (uiout, 17, ui_left, "target-id", "Description");
  ui_out_table_header (uiout, 17, ui_left, "target-id", "Description");
  ui_out_table_header (uiout, 17, ui_left, "exec", "Executable");
  ui_out_table_header (uiout, 17, ui_left, "exec", "Executable");
 
 
  ui_out_table_body (uiout);
  ui_out_table_body (uiout);
  for (inf = inferior_list; inf; inf = inf->next)
  for (inf = inferior_list; inf; inf = inf->next)
    {
    {
      struct cleanup *chain2;
      struct cleanup *chain2;
 
 
      if (requested_inferior != -1 && inf->num != requested_inferior)
      if (requested_inferior != -1 && inf->num != requested_inferior)
        continue;
        continue;
 
 
      chain2 = make_cleanup_ui_out_tuple_begin_end (uiout, NULL);
      chain2 = make_cleanup_ui_out_tuple_begin_end (uiout, NULL);
 
 
      if (inf == current_inferior ())
      if (inf == current_inferior ())
        ui_out_field_string (uiout, "current", "*");
        ui_out_field_string (uiout, "current", "*");
      else
      else
        ui_out_field_skip (uiout, "current");
        ui_out_field_skip (uiout, "current");
 
 
      ui_out_field_int (uiout, "number", inf->num);
      ui_out_field_int (uiout, "number", inf->num);
 
 
      if (inf->pid)
      if (inf->pid)
        ui_out_field_string (uiout, "target-id",
        ui_out_field_string (uiout, "target-id",
                             target_pid_to_str (pid_to_ptid (inf->pid)));
                             target_pid_to_str (pid_to_ptid (inf->pid)));
      else
      else
        ui_out_field_string (uiout, "target-id", "<null>");
        ui_out_field_string (uiout, "target-id", "<null>");
 
 
      if (inf->pspace->ebfd)
      if (inf->pspace->ebfd)
        ui_out_field_string (uiout, "exec",
        ui_out_field_string (uiout, "exec",
                             bfd_get_filename (inf->pspace->ebfd));
                             bfd_get_filename (inf->pspace->ebfd));
      else
      else
        ui_out_field_skip (uiout, "exec");
        ui_out_field_skip (uiout, "exec");
 
 
      /* Print extra info that isn't really fit to always present in
      /* Print extra info that isn't really fit to always present in
         tabular form.  Currently we print the vfork parent/child
         tabular form.  Currently we print the vfork parent/child
         relationships, if any.  */
         relationships, if any.  */
      if (inf->vfork_parent)
      if (inf->vfork_parent)
        {
        {
          ui_out_text (uiout, _("\n\tis vfork child of inferior "));
          ui_out_text (uiout, _("\n\tis vfork child of inferior "));
          ui_out_field_int (uiout, "vfork-parent", inf->vfork_parent->num);
          ui_out_field_int (uiout, "vfork-parent", inf->vfork_parent->num);
        }
        }
      if (inf->vfork_child)
      if (inf->vfork_child)
        {
        {
          ui_out_text (uiout, _("\n\tis vfork parent of inferior "));
          ui_out_text (uiout, _("\n\tis vfork parent of inferior "));
          ui_out_field_int (uiout, "vfork-child", inf->vfork_child->num);
          ui_out_field_int (uiout, "vfork-child", inf->vfork_child->num);
        }
        }
 
 
      ui_out_text (uiout, "\n");
      ui_out_text (uiout, "\n");
      do_cleanups (chain2);
      do_cleanups (chain2);
    }
    }
 
 
  do_cleanups (old_chain);
  do_cleanups (old_chain);
}
}
 
 
static void
static void
detach_inferior_command (char *args, int from_tty)
detach_inferior_command (char *args, int from_tty)
{
{
  int num, pid;
  int num, pid;
  struct thread_info *tp;
  struct thread_info *tp;
 
 
  if (!args || !*args)
  if (!args || !*args)
    error (_("Requires argument (inferior id to detach)"));
    error (_("Requires argument (inferior id to detach)"));
 
 
  num = parse_and_eval_long (args);
  num = parse_and_eval_long (args);
 
 
  if (!valid_gdb_inferior_id (num))
  if (!valid_gdb_inferior_id (num))
    error (_("Inferior ID %d not known."), num);
    error (_("Inferior ID %d not known."), num);
 
 
  pid = gdb_inferior_id_to_pid (num);
  pid = gdb_inferior_id_to_pid (num);
 
 
  tp = any_thread_of_process (pid);
  tp = any_thread_of_process (pid);
  if (!tp)
  if (!tp)
    error (_("Inferior has no threads."));
    error (_("Inferior has no threads."));
 
 
  switch_to_thread (tp->ptid);
  switch_to_thread (tp->ptid);
 
 
  detach_command (NULL, from_tty);
  detach_command (NULL, from_tty);
}
}
 
 
static void
static void
kill_inferior_command (char *args, int from_tty)
kill_inferior_command (char *args, int from_tty)
{
{
  int num, pid;
  int num, pid;
  struct thread_info *tp;
  struct thread_info *tp;
 
 
  if (!args || !*args)
  if (!args || !*args)
    error (_("Requires argument (inferior id to kill)"));
    error (_("Requires argument (inferior id to kill)"));
 
 
  num = parse_and_eval_long (args);
  num = parse_and_eval_long (args);
 
 
  if (!valid_gdb_inferior_id (num))
  if (!valid_gdb_inferior_id (num))
    error (_("Inferior ID %d not known."), num);
    error (_("Inferior ID %d not known."), num);
 
 
  pid = gdb_inferior_id_to_pid (num);
  pid = gdb_inferior_id_to_pid (num);
 
 
  tp = any_thread_of_process (pid);
  tp = any_thread_of_process (pid);
  if (!tp)
  if (!tp)
    error (_("Inferior has no threads."));
    error (_("Inferior has no threads."));
 
 
  switch_to_thread (tp->ptid);
  switch_to_thread (tp->ptid);
 
 
  target_kill ();
  target_kill ();
 
 
  bfd_cache_close_all ();
  bfd_cache_close_all ();
}
}
 
 
static void
static void
inferior_command (char *args, int from_tty)
inferior_command (char *args, int from_tty)
{
{
  struct inferior *inf;
  struct inferior *inf;
  int num;
  int num;
 
 
  num = parse_and_eval_long (args);
  num = parse_and_eval_long (args);
 
 
  inf = find_inferior_id (num);
  inf = find_inferior_id (num);
  if (inf == NULL)
  if (inf == NULL)
    error (_("Inferior ID %d not known."), num);
    error (_("Inferior ID %d not known."), num);
 
 
  printf_filtered (_("[Switching to inferior %d [%s] (%s)]\n"),
  printf_filtered (_("[Switching to inferior %d [%s] (%s)]\n"),
                   inf->num,
                   inf->num,
                   target_pid_to_str (pid_to_ptid (inf->pid)),
                   target_pid_to_str (pid_to_ptid (inf->pid)),
                   (inf->pspace->ebfd
                   (inf->pspace->ebfd
                    ? bfd_get_filename (inf->pspace->ebfd)
                    ? bfd_get_filename (inf->pspace->ebfd)
                    : _("<noexec>")));
                    : _("<noexec>")));
 
 
  if (inf->pid != 0)
  if (inf->pid != 0)
    {
    {
      if (inf->pid != ptid_get_pid (inferior_ptid))
      if (inf->pid != ptid_get_pid (inferior_ptid))
        {
        {
          struct thread_info *tp;
          struct thread_info *tp;
 
 
          tp = any_thread_of_process (inf->pid);
          tp = any_thread_of_process (inf->pid);
          if (!tp)
          if (!tp)
            error (_("Inferior has no threads."));
            error (_("Inferior has no threads."));
 
 
          switch_to_thread (tp->ptid);
          switch_to_thread (tp->ptid);
        }
        }
 
 
      printf_filtered (_("[Switching to thread %d (%s)] "),
      printf_filtered (_("[Switching to thread %d (%s)] "),
                       pid_to_thread_id (inferior_ptid),
                       pid_to_thread_id (inferior_ptid),
                       target_pid_to_str (inferior_ptid));
                       target_pid_to_str (inferior_ptid));
    }
    }
  else
  else
    {
    {
      struct inferior *inf;
      struct inferior *inf;
 
 
      inf = find_inferior_id (num);
      inf = find_inferior_id (num);
      set_current_inferior (inf);
      set_current_inferior (inf);
      switch_to_thread (null_ptid);
      switch_to_thread (null_ptid);
      set_current_program_space (inf->pspace);
      set_current_program_space (inf->pspace);
    }
    }
 
 
  if (inf->pid != 0 && is_running (inferior_ptid))
  if (inf->pid != 0 && is_running (inferior_ptid))
    ui_out_text (uiout, "(running)\n");
    ui_out_text (uiout, "(running)\n");
  else if (inf->pid != 0)
  else if (inf->pid != 0)
    {
    {
      ui_out_text (uiout, "\n");
      ui_out_text (uiout, "\n");
      print_stack_frame (get_selected_frame (NULL), 1, SRC_AND_LOC);
      print_stack_frame (get_selected_frame (NULL), 1, SRC_AND_LOC);
    }
    }
}
}
 
 
/* Print information about currently known inferiors.  */
/* Print information about currently known inferiors.  */
 
 
static void
static void
info_inferiors_command (char *args, int from_tty)
info_inferiors_command (char *args, int from_tty)
{
{
  int requested = -1;
  int requested = -1;
 
 
  if (args && *args)
  if (args && *args)
    {
    {
      requested = parse_and_eval_long (args);
      requested = parse_and_eval_long (args);
      if (!valid_gdb_inferior_id (requested))
      if (!valid_gdb_inferior_id (requested))
        error (_("Inferior ID %d not known."), requested);
        error (_("Inferior ID %d not known."), requested);
    }
    }
 
 
  print_inferior (uiout, requested);
  print_inferior (uiout, requested);
}
}
 
 
/* remove-inferior ID */
/* remove-inferior ID */
 
 
void
void
remove_inferior_command (char *args, int from_tty)
remove_inferior_command (char *args, int from_tty)
{
{
  int num;
  int num;
  struct inferior *inf;
  struct inferior *inf;
 
 
  num = parse_and_eval_long (args);
  num = parse_and_eval_long (args);
  inf = find_inferior_id (num);
  inf = find_inferior_id (num);
 
 
  if (inf == NULL)
  if (inf == NULL)
    error (_("Inferior ID %d not known."), num);
    error (_("Inferior ID %d not known."), num);
 
 
  if (inf == current_inferior ())
  if (inf == current_inferior ())
    error (_("Can not remove current symbol inferior."));
    error (_("Can not remove current symbol inferior."));
 
 
  delete_inferior_1 (inf, 1);
  delete_inferior_1 (inf, 1);
}
}
 
 
 
 
/* add-inferior [-copies N] [-exec FILENAME]  */
/* add-inferior [-copies N] [-exec FILENAME]  */
 
 
void
void
add_inferior_command (char *args, int from_tty)
add_inferior_command (char *args, int from_tty)
{
{
  int i, copies = 1;
  int i, copies = 1;
  char *exec = NULL;
  char *exec = NULL;
  char **argv;
  char **argv;
  struct cleanup *old_chain = make_cleanup (null_cleanup, NULL);
  struct cleanup *old_chain = make_cleanup (null_cleanup, NULL);
 
 
  if (args)
  if (args)
    {
    {
      argv = gdb_buildargv (args);
      argv = gdb_buildargv (args);
      make_cleanup_freeargv (argv);
      make_cleanup_freeargv (argv);
 
 
      for (; *argv != NULL; argv++)
      for (; *argv != NULL; argv++)
        {
        {
          if (**argv == '-')
          if (**argv == '-')
            {
            {
              if (strcmp (*argv, "-copies") == 0)
              if (strcmp (*argv, "-copies") == 0)
                {
                {
                  ++argv;
                  ++argv;
                  if (!*argv)
                  if (!*argv)
                    error (_("No argument to -copies"));
                    error (_("No argument to -copies"));
                  copies = parse_and_eval_long (*argv);
                  copies = parse_and_eval_long (*argv);
                }
                }
              else if (strcmp (*argv, "-exec") == 0)
              else if (strcmp (*argv, "-exec") == 0)
                {
                {
                  ++argv;
                  ++argv;
                  if (!*argv)
                  if (!*argv)
                    error (_("No argument to -exec"));
                    error (_("No argument to -exec"));
                  exec = *argv;
                  exec = *argv;
                }
                }
            }
            }
          else
          else
            error (_("Invalid argument"));
            error (_("Invalid argument"));
        }
        }
    }
    }
 
 
  save_current_space_and_thread ();
  save_current_space_and_thread ();
 
 
  for (i = 0; i < copies; ++i)
  for (i = 0; i < copies; ++i)
    {
    {
      struct address_space *aspace;
      struct address_space *aspace;
      struct program_space *pspace;
      struct program_space *pspace;
      struct inferior *inf;
      struct inferior *inf;
 
 
      /* If all inferiors share an address space on this system, this
      /* If all inferiors share an address space on this system, this
         doesn't really return a new address space; otherwise, it
         doesn't really return a new address space; otherwise, it
         really does.  */
         really does.  */
      aspace = maybe_new_address_space ();
      aspace = maybe_new_address_space ();
      pspace = add_program_space (aspace);
      pspace = add_program_space (aspace);
      inf = add_inferior (0);
      inf = add_inferior (0);
      inf->pspace = pspace;
      inf->pspace = pspace;
      inf->aspace = pspace->aspace;
      inf->aspace = pspace->aspace;
 
 
      printf_filtered (_("Added inferior %d\n"), inf->num);
      printf_filtered (_("Added inferior %d\n"), inf->num);
 
 
      if (exec != NULL)
      if (exec != NULL)
        {
        {
          /* Switch over temporarily, while reading executable and
          /* Switch over temporarily, while reading executable and
             symbols.q  */
             symbols.q  */
          set_current_program_space (pspace);
          set_current_program_space (pspace);
          set_current_inferior (inf);
          set_current_inferior (inf);
          switch_to_thread (null_ptid);
          switch_to_thread (null_ptid);
 
 
          exec_file_attach (exec, from_tty);
          exec_file_attach (exec, from_tty);
          symbol_file_add_main (exec, from_tty);
          symbol_file_add_main (exec, from_tty);
        }
        }
    }
    }
 
 
  do_cleanups (old_chain);
  do_cleanups (old_chain);
}
}
 
 
/* clone-inferior [-copies N] [ID] */
/* clone-inferior [-copies N] [ID] */
 
 
void
void
clone_inferior_command (char *args, int from_tty)
clone_inferior_command (char *args, int from_tty)
{
{
  int i, copies = 1;
  int i, copies = 1;
  char **argv;
  char **argv;
  struct inferior *orginf = NULL;
  struct inferior *orginf = NULL;
  struct cleanup *old_chain = make_cleanup (null_cleanup, NULL);
  struct cleanup *old_chain = make_cleanup (null_cleanup, NULL);
 
 
  if (args)
  if (args)
    {
    {
      argv = gdb_buildargv (args);
      argv = gdb_buildargv (args);
      make_cleanup_freeargv (argv);
      make_cleanup_freeargv (argv);
 
 
      for (; *argv != NULL; argv++)
      for (; *argv != NULL; argv++)
        {
        {
          if (**argv == '-')
          if (**argv == '-')
            {
            {
              if (strcmp (*argv, "-copies") == 0)
              if (strcmp (*argv, "-copies") == 0)
                {
                {
                  ++argv;
                  ++argv;
                  if (!*argv)
                  if (!*argv)
                    error (_("No argument to -copies"));
                    error (_("No argument to -copies"));
                  copies = parse_and_eval_long (*argv);
                  copies = parse_and_eval_long (*argv);
 
 
                  if (copies < 0)
                  if (copies < 0)
                    error (_("Invalid copies number"));
                    error (_("Invalid copies number"));
                }
                }
            }
            }
          else
          else
            {
            {
              if (orginf == NULL)
              if (orginf == NULL)
                {
                {
                  int num;
                  int num;
 
 
                  /* The first non-option (-) argument specified the
                  /* The first non-option (-) argument specified the
                     program space ID.  */
                     program space ID.  */
                  num = parse_and_eval_long (*argv);
                  num = parse_and_eval_long (*argv);
                  orginf = find_inferior_id (num);
                  orginf = find_inferior_id (num);
 
 
                  if (orginf == NULL)
                  if (orginf == NULL)
                    error (_("Inferior ID %d not known."), num);
                    error (_("Inferior ID %d not known."), num);
                  continue;
                  continue;
                }
                }
              else
              else
                error (_("Invalid argument"));
                error (_("Invalid argument"));
            }
            }
        }
        }
    }
    }
 
 
  /* If no inferior id was specified, then the user wants to clone the
  /* If no inferior id was specified, then the user wants to clone the
     current inferior.  */
     current inferior.  */
  if (orginf == NULL)
  if (orginf == NULL)
    orginf = current_inferior ();
    orginf = current_inferior ();
 
 
  save_current_space_and_thread ();
  save_current_space_and_thread ();
 
 
  for (i = 0; i < copies; ++i)
  for (i = 0; i < copies; ++i)
    {
    {
      struct address_space *aspace;
      struct address_space *aspace;
      struct program_space *pspace;
      struct program_space *pspace;
      struct inferior *inf;
      struct inferior *inf;
 
 
      /* If all inferiors share an address space on this system, this
      /* If all inferiors share an address space on this system, this
         doesn't really return a new address space; otherwise, it
         doesn't really return a new address space; otherwise, it
         really does.  */
         really does.  */
      aspace = maybe_new_address_space ();
      aspace = maybe_new_address_space ();
      pspace = add_program_space (aspace);
      pspace = add_program_space (aspace);
      inf = add_inferior (0);
      inf = add_inferior (0);
      inf->pspace = pspace;
      inf->pspace = pspace;
      inf->aspace = pspace->aspace;
      inf->aspace = pspace->aspace;
 
 
      printf_filtered (_("Added inferior %d.\n"), inf->num);
      printf_filtered (_("Added inferior %d.\n"), inf->num);
 
 
      set_current_inferior (inf);
      set_current_inferior (inf);
      switch_to_thread (null_ptid);
      switch_to_thread (null_ptid);
      clone_program_space (pspace, orginf->pspace);
      clone_program_space (pspace, orginf->pspace);
    }
    }
 
 
  do_cleanups (old_chain);
  do_cleanups (old_chain);
}
}
 
 
/* Print notices when new inferiors are created and die.  */
/* Print notices when new inferiors are created and die.  */
static void
static void
show_print_inferior_events (struct ui_file *file, int from_tty,
show_print_inferior_events (struct ui_file *file, int from_tty,
                           struct cmd_list_element *c, const char *value)
                           struct cmd_list_element *c, const char *value)
{
{
  fprintf_filtered (file, _("Printing of inferior events is %s.\n"), value);
  fprintf_filtered (file, _("Printing of inferior events is %s.\n"), value);
}
}
 
 


 
 
/* Keep a registry of per-inferior data-pointers required by other GDB
/* Keep a registry of per-inferior data-pointers required by other GDB
   modules.  */
   modules.  */
 
 
struct inferior_data
struct inferior_data
{
{
  unsigned index;
  unsigned index;
  void (*cleanup) (struct inferior *, void *);
  void (*cleanup) (struct inferior *, void *);
};
};
 
 
struct inferior_data_registration
struct inferior_data_registration
{
{
  struct inferior_data *data;
  struct inferior_data *data;
  struct inferior_data_registration *next;
  struct inferior_data_registration *next;
};
};
 
 
struct inferior_data_registry
struct inferior_data_registry
{
{
  struct inferior_data_registration *registrations;
  struct inferior_data_registration *registrations;
  unsigned num_registrations;
  unsigned num_registrations;
};
};
 
 
static struct inferior_data_registry inferior_data_registry
static struct inferior_data_registry inferior_data_registry
  = { NULL, 0 };
  = { NULL, 0 };
 
 
const struct inferior_data *
const struct inferior_data *
register_inferior_data_with_cleanup
register_inferior_data_with_cleanup
  (void (*cleanup) (struct inferior *, void *))
  (void (*cleanup) (struct inferior *, void *))
{
{
  struct inferior_data_registration **curr;
  struct inferior_data_registration **curr;
 
 
  /* Append new registration.  */
  /* Append new registration.  */
  for (curr = &inferior_data_registry.registrations;
  for (curr = &inferior_data_registry.registrations;
       *curr != NULL; curr = &(*curr)->next);
       *curr != NULL; curr = &(*curr)->next);
 
 
  *curr = XMALLOC (struct inferior_data_registration);
  *curr = XMALLOC (struct inferior_data_registration);
  (*curr)->next = NULL;
  (*curr)->next = NULL;
  (*curr)->data = XMALLOC (struct inferior_data);
  (*curr)->data = XMALLOC (struct inferior_data);
  (*curr)->data->index = inferior_data_registry.num_registrations++;
  (*curr)->data->index = inferior_data_registry.num_registrations++;
  (*curr)->data->cleanup = cleanup;
  (*curr)->data->cleanup = cleanup;
 
 
  return (*curr)->data;
  return (*curr)->data;
}
}
 
 
const struct inferior_data *
const struct inferior_data *
register_inferior_data (void)
register_inferior_data (void)
{
{
  return register_inferior_data_with_cleanup (NULL);
  return register_inferior_data_with_cleanup (NULL);
}
}
 
 
static void
static void
inferior_alloc_data (struct inferior *inf)
inferior_alloc_data (struct inferior *inf)
{
{
  gdb_assert (inf->data == NULL);
  gdb_assert (inf->data == NULL);
  inf->num_data = inferior_data_registry.num_registrations;
  inf->num_data = inferior_data_registry.num_registrations;
  inf->data = XCALLOC (inf->num_data, void *);
  inf->data = XCALLOC (inf->num_data, void *);
}
}
 
 
static void
static void
inferior_free_data (struct inferior *inf)
inferior_free_data (struct inferior *inf)
{
{
  gdb_assert (inf->data != NULL);
  gdb_assert (inf->data != NULL);
  clear_inferior_data (inf);
  clear_inferior_data (inf);
  xfree (inf->data);
  xfree (inf->data);
  inf->data = NULL;
  inf->data = NULL;
}
}
 
 
void
void
clear_inferior_data (struct inferior *inf)
clear_inferior_data (struct inferior *inf)
{
{
  struct inferior_data_registration *registration;
  struct inferior_data_registration *registration;
  int i;
  int i;
 
 
  gdb_assert (inf->data != NULL);
  gdb_assert (inf->data != NULL);
 
 
  for (registration = inferior_data_registry.registrations, i = 0;
  for (registration = inferior_data_registry.registrations, i = 0;
       i < inf->num_data;
       i < inf->num_data;
       registration = registration->next, i++)
       registration = registration->next, i++)
    if (inf->data[i] != NULL && registration->data->cleanup)
    if (inf->data[i] != NULL && registration->data->cleanup)
      registration->data->cleanup (inf, inf->data[i]);
      registration->data->cleanup (inf, inf->data[i]);
 
 
  memset (inf->data, 0, inf->num_data * sizeof (void *));
  memset (inf->data, 0, inf->num_data * sizeof (void *));
}
}
 
 
void
void
set_inferior_data (struct inferior *inf,
set_inferior_data (struct inferior *inf,
                       const struct inferior_data *data,
                       const struct inferior_data *data,
                       void *value)
                       void *value)
{
{
  gdb_assert (data->index < inf->num_data);
  gdb_assert (data->index < inf->num_data);
  inf->data[data->index] = value;
  inf->data[data->index] = value;
}
}
 
 
void *
void *
inferior_data (struct inferior *inf, const struct inferior_data *data)
inferior_data (struct inferior *inf, const struct inferior_data *data)
{
{
  gdb_assert (data->index < inf->num_data);
  gdb_assert (data->index < inf->num_data);
  return inf->data[data->index];
  return inf->data[data->index];
}
}
 
 
void
void
initialize_inferiors (void)
initialize_inferiors (void)
{
{
  /* There's always one inferior.  Note that this function isn't an
  /* There's always one inferior.  Note that this function isn't an
     automatic _initialize_foo function, since other _initialize_foo
     automatic _initialize_foo function, since other _initialize_foo
     routines may need to install their per-inferior data keys.  We
     routines may need to install their per-inferior data keys.  We
     can only allocate an inferior when all those modules have done
     can only allocate an inferior when all those modules have done
     that.  Do this after initialize_progspace, due to the
     that.  Do this after initialize_progspace, due to the
     current_program_space reference.  */
     current_program_space reference.  */
  current_inferior_ = add_inferior (0);
  current_inferior_ = add_inferior (0);
  current_inferior_->pspace = current_program_space;
  current_inferior_->pspace = current_program_space;
  current_inferior_->aspace = current_program_space->aspace;
  current_inferior_->aspace = current_program_space->aspace;
 
 
  add_info ("inferiors", info_inferiors_command,
  add_info ("inferiors", info_inferiors_command,
            _("IDs of currently known inferiors."));
            _("IDs of currently known inferiors."));
 
 
  add_com ("add-inferior", no_class, add_inferior_command, _("\
  add_com ("add-inferior", no_class, add_inferior_command, _("\
Add a new inferior.\n\
Add a new inferior.\n\
Usage: add-inferior [-copies <N>] [-exec <FILENAME>]\n\
Usage: add-inferior [-copies <N>] [-exec <FILENAME>]\n\
N is the optional number of inferior to add, default is 1.\n\
N is the optional number of inferior to add, default is 1.\n\
FILENAME is the file name of the executable to use\n\
FILENAME is the file name of the executable to use\n\
as main program."));
as main program."));
 
 
  add_com ("remove-inferior", no_class, remove_inferior_command, _("\
  add_com ("remove-inferior", no_class, remove_inferior_command, _("\
Remove inferior ID.\n\
Remove inferior ID.\n\
Usage: remove-inferior ID"));
Usage: remove-inferior ID"));
 
 
  add_com ("clone-inferior", no_class, clone_inferior_command, _("\
  add_com ("clone-inferior", no_class, clone_inferior_command, _("\
Clone inferior ID.\n\
Clone inferior ID.\n\
Usage: clone-inferior [-copies <N>] [ID]\n\
Usage: clone-inferior [-copies <N>] [ID]\n\
Add N copies of inferior ID.  The new inferior has the same\n\
Add N copies of inferior ID.  The new inferior has the same\n\
executable loaded as the copied inferior.  If -copies is not specified,\n\
executable loaded as the copied inferior.  If -copies is not specified,\n\
adds 1 copy.  If ID is not specified, it is the current inferior\n\
adds 1 copy.  If ID is not specified, it is the current inferior\n\
that is cloned."));
that is cloned."));
 
 
  add_cmd ("inferior", class_run, detach_inferior_command, _("\
  add_cmd ("inferior", class_run, detach_inferior_command, _("\
Detach from inferior ID."),
Detach from inferior ID."),
           &detachlist);
           &detachlist);
 
 
  add_cmd ("inferior", class_run, kill_inferior_command, _("\
  add_cmd ("inferior", class_run, kill_inferior_command, _("\
Kill inferior ID."),
Kill inferior ID."),
           &killlist);
           &killlist);
 
 
  add_cmd ("inferior", class_run, inferior_command, _("\
  add_cmd ("inferior", class_run, inferior_command, _("\
Use this command to switch between inferiors.\n\
Use this command to switch between inferiors.\n\
The new inferior ID must be currently known."),
The new inferior ID must be currently known."),
           &cmdlist);
           &cmdlist);
 
 
  add_setshow_boolean_cmd ("inferior-events", no_class,
  add_setshow_boolean_cmd ("inferior-events", no_class,
         &print_inferior_events, _("\
         &print_inferior_events, _("\
Set printing of inferior events (e.g., inferior start and exit)."), _("\
Set printing of inferior events (e.g., inferior start and exit)."), _("\
Show printing of inferior events (e.g., inferior start and exit)."), NULL,
Show printing of inferior events (e.g., inferior start and exit)."), NULL,
         NULL,
         NULL,
         show_print_inferior_events,
         show_print_inferior_events,
         &setprintlist, &showprintlist);
         &setprintlist, &showprintlist);
 
 
}
}
 
 

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.