/* Dynamic architecture support for GDB, the GNU debugger.
- Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007
- Free Software Foundation, Inc.
+ Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007,
+ 2008 Free Software Foundation, Inc.
This file is part of GDB.
#include "gdbcore.h"
#include "osabi.h"
#include "target-descriptions.h"
+#include "objfiles.h"
#include "version.h"
#include "floatformat.h"
+struct displaced_step_closure *
+simple_displaced_step_copy_insn (struct gdbarch *gdbarch,
+ CORE_ADDR from, CORE_ADDR to,
+ struct regcache *regs)
+{
+ size_t len = gdbarch_max_insn_length (gdbarch);
+ gdb_byte *buf = xmalloc (len);
+
+ read_memory (from, buf, len);
+ write_memory (to, buf, len);
+
+ if (debug_displaced)
+ {
+ fprintf_unfiltered (gdb_stdlog, "displaced: copy 0x%s->0x%s: ",
+ paddr_nz (from), paddr_nz (to));
+ displaced_step_dump_bytes (gdb_stdlog, buf, len);
+ }
+
+ return (struct displaced_step_closure *) buf;
+}
+
+
+void
+simple_displaced_step_free_closure (struct gdbarch *gdbarch,
+ struct displaced_step_closure *closure)
+{
+ xfree (closure);
+}
+
+
+CORE_ADDR
+displaced_step_at_entry_point (struct gdbarch *gdbarch)
+{
+ CORE_ADDR addr;
+ int bp_len;
+
+ addr = entry_point_address ();
+
+ /* Make certain that the address points at real code, and not a
+ function descriptor. */
+ addr = gdbarch_convert_from_func_ptr_addr (gdbarch, addr, ¤t_target);
+
+ /* Inferior calls also use the entry point as a breakpoint location.
+ We don't want displaced stepping to interfere with those
+ breakpoints, so leave space. */
+ gdbarch_breakpoint_from_pc (gdbarch, &addr, &bp_len);
+ addr += bp_len * 2;
+
+ return addr;
+}
+
int
-legacy_register_sim_regno (int regnum)
+legacy_register_sim_regno (struct gdbarch *gdbarch, int regnum)
{
/* Only makes sense to supply raw registers. */
- gdb_assert (regnum >= 0 && regnum < gdbarch_num_regs (current_gdbarch));
+ gdb_assert (regnum >= 0 && regnum < gdbarch_num_regs (gdbarch));
/* NOTE: cagney/2002-05-13: The old code did it this way and it is
suspected that some GDB/SIM combinations may rely on this
behavour. The default should be one2one_register_sim_regno
(below). */
- if (gdbarch_register_name (current_gdbarch, regnum) != NULL
- && gdbarch_register_name (current_gdbarch, regnum)[0] != '\0')
+ if (gdbarch_register_name (gdbarch, regnum) != NULL
+ && gdbarch_register_name (gdbarch, regnum)[0] != '\0')
return regnum;
else
return LEGACY_SIM_REGNO_IGNORE;
/* Misc helper functions for targets. */
CORE_ADDR
-core_addr_identity (CORE_ADDR addr)
+core_addr_identity (struct gdbarch *gdbarch, CORE_ADDR addr)
{
return addr;
}
}
int
-no_op_reg_to_regnum (int reg)
+no_op_reg_to_regnum (struct gdbarch *gdbarch, int reg)
{
return reg;
}
int
gdbarch_update_p (struct gdbarch_info info)
{
- struct gdbarch *new_gdbarch = gdbarch_find_by_info (info);
+ struct gdbarch *new_gdbarch;
+
+ /* Check for the current file. */
+ if (info.abfd == NULL)
+ info.abfd = exec_bfd;
+ if (info.abfd == NULL)
+ info.abfd = core_bfd;
+
+ /* Check for the current target description. */
+ if (info.target_desc == NULL)
+ info.target_desc = target_current_description ();
+
+ new_gdbarch = gdbarch_find_by_info (info);
/* If there no architecture by that name, reject the request. */
if (new_gdbarch == NULL)
/* If it is the same old architecture, accept the request (but don't
swap anything). */
- if (new_gdbarch == current_gdbarch)
+ if (new_gdbarch == target_gdbarch)
{
if (gdbarch_debug)
fprintf_unfiltered (gdb_stdlog, "gdbarch_update_p: "
struct gdbarch *
gdbarch_from_bfd (bfd *abfd)
{
- struct gdbarch *old_gdbarch = current_gdbarch;
- struct gdbarch *new_gdbarch;
struct gdbarch_info info;
-
- /* If we call gdbarch_find_by_info without filling in info.abfd,
- then it will use the global exec_bfd. That's fine if we don't
- have one of those either. And that's the only time we should
- reach here with a NULL ABFD argument - when we are discarding
- the executable. */
- gdb_assert (abfd != NULL || exec_bfd == NULL);
-
gdbarch_info_init (&info);
info.abfd = abfd;
return gdbarch_find_by_info (info);
void
set_gdbarch_from_file (bfd *abfd)
{
+ struct gdbarch_info info;
struct gdbarch *gdbarch;
- gdbarch = gdbarch_from_bfd (abfd);
+ gdbarch_info_init (&info);
+ info.abfd = abfd;
+ info.target_desc = target_current_description ();
+ gdbarch = gdbarch_find_by_info (info);
+
if (gdbarch == NULL)
error (_("Architecture of file not recognized."));
deprecated_current_gdbarch_select_hack (gdbarch);
}
info.byte_order = default_byte_order;
+ info.byte_order_for_code = info.byte_order;
if (! gdbarch_update_p (info))
internal_error (__FILE__, __LINE__,
{
memset (info, 0, sizeof (struct gdbarch_info));
info->byte_order = BFD_ENDIAN_UNKNOWN;
+ info->byte_order_for_code = info->byte_order;
info->osabi = GDB_OSABI_UNINITIALIZED;
}
void
gdbarch_info_fill (struct gdbarch_info *info)
{
- /* Check for the current file. */
- if (info->abfd == NULL)
- info->abfd = exec_bfd;
- if (info->abfd == NULL)
- info->abfd = core_bfd;
-
- /* Check for the current target description. */
- if (info->target_desc == NULL)
- info->target_desc = target_current_description ();
-
/* "(gdb) set architecture ...". */
if (info->bfd_arch_info == NULL
&& target_architecture_user)
/* From the default. */
if (info->byte_order == BFD_ENDIAN_UNKNOWN)
info->byte_order = default_byte_order;
+ info->byte_order_for_code = info->byte_order;
/* "(gdb) set osabi ...". Handled by gdbarch_lookup_osabi. */
if (info->osabi == GDB_OSABI_UNINITIALIZED)