gdb: add target_ops::supports_displaced_step
[deliverable/binutils-gdb.git] / gdb / tilegx-linux-tdep.c
index c7c6d9c54e9a5521c1d6ac601a8df989542bf748..e656187849cbe9c97cbef845ee92436939c28e64 100644 (file)
@@ -1,6 +1,6 @@
 /* Target-dependent code for GNU/Linux on Tilera TILE-Gx processors.
 
-   Copyright 2012 Free Software Foundation, Inc.
+   Copyright (C) 2012-2020 Free Software Foundation, Inc.
 
    This file is part of GDB.
 
@@ -28,6 +28,7 @@
 #include "tramp-frame.h"
 #include "trad-frame.h"
 #include "tilegx-tdep.h"
+#include "gdbarch.h"
 
 /* Signal trampoline support.  */
 
@@ -37,15 +38,24 @@ tilegx_linux_sigframe_init (const struct tramp_frame *self,
                            struct trad_frame_cache *this_cache,
                            CORE_ADDR func)
 {
-  CORE_ADDR pc = get_frame_register_unsigned (this_frame, 64);
   CORE_ADDR sp = get_frame_register_unsigned (this_frame, 54);
-  CORE_ADDR base = sp + 16;
+
+  /* Base address of register save area.  */
+  CORE_ADDR base = sp
+                   + 16    /* Skip ABI_SAVE_AREA.  */
+                   + 128   /* Skip SIGINFO.  */
+                   + 40;   /* Skip UCONTEXT.  */
+
+  /* Address of saved LR register (R56) which holds previous PC.  */
+  CORE_ADDR prev_pc = base + 56 * 8;
+
   int i;
 
   for (i = 0; i < 56; i++)
     trad_frame_set_reg_addr (this_cache, i, base + i * 8);
 
-  trad_frame_set_reg_value (this_cache, 64, pc);
+  trad_frame_set_reg_value (this_cache, 64,
+                            get_frame_memory_unsigned (this_frame, prev_pc, 8));
 
   /* Save a frame ID.  */
   trad_frame_set_id (this_cache, frame_id_build (base, func));
@@ -56,50 +66,42 @@ static const struct tramp_frame tilegx_linux_rt_sigframe =
   SIGTRAMP_FRAME,
   8,
   {
-    { 0x00045fe551483000, -1 }, /* { moveli r10, 139 } */
-    { 0x286b180051485000, -1 }, /* { swint1 } */
-    { TRAMP_SENTINEL_INSN, -1 }
+    { 0x00045fe551483000ULL, ULONGEST_MAX }, /* { moveli r10, 139 } */
+    { 0x286b180051485000ULL, ULONGEST_MAX }, /* { swint1 } */
+    { TRAMP_SENTINEL_INSN, ULONGEST_MAX }
   },
   tilegx_linux_sigframe_init
 };
 
-/* Supply raw registers from REGCACHE to REGS.  */
+/* Register map; must match struct pt_regs in "ptrace.h".  */
 
-static void
-tilegx_linux_supply_regset (const struct regset *regset,
-                           struct regcache *regcache,
-                           int regnum, const void *regs, size_t len)
-{
-  struct gdbarch *arch = get_regcache_arch (regcache);
-  const char *ptr = regs;
-  int i;
+static const struct regcache_map_entry tilegx_linux_regmap[] =
+  {
+    { TILEGX_NUM_EASY_REGS, TILEGX_FIRST_EASY_REGNUM, 8 },
+    { 1, TILEGX_PC_REGNUM, 8 },
+    { 1, TILEGX_FAULTNUM_REGNUM, 8 },
+    { 0 }
+  };
 
-  /* This logic must match that of struct pt_regs in "ptrace.h".  */
-  for (i = 0; i < TILEGX_NUM_EASY_REGS + 1; i++, ptr += tilegx_reg_size)
-    {
-      int gri = (i < TILEGX_NUM_EASY_REGS) ? i : TILEGX_PC_REGNUM;
-
-      if (regnum == gri || regnum == -1)
-       regcache_raw_supply (regcache, gri, ptr);
-    }
-}
+#define TILEGX_LINUX_SIZEOF_GREGSET (64 * 8)
 
 /* TILE-Gx Linux kernel register set.  */
-static struct regset tilegx_linux_regset =
+
+static const struct regset tilegx_linux_regset =
 {
-  NULL,
-  tilegx_linux_supply_regset
+  tilegx_linux_regmap,
+  regcache_supply_regset, regcache_collect_regset
 };
 
-static const struct regset *
-tilegx_regset_from_core_section (struct gdbarch *gdbarch,
-                                const char *sect_name,
-                                size_t sect_size)
-{
-  if (strcmp (sect_name, ".reg") == 0)
-    return &tilegx_linux_regset;
 
-  return NULL;
+static void
+tilegx_iterate_over_regset_sections (struct gdbarch *gdbarch,
+                                    iterate_over_regset_sections_cb *cb,
+                                    void *cb_data,
+                                    const struct regcache *regcache)
+{
+  cb (".reg", TILEGX_LINUX_SIZEOF_GREGSET, TILEGX_LINUX_SIZEOF_GREGSET,
+      &tilegx_linux_regset, NULL, cb_data);
 }
 
 /* OS specific initialization of gdbarch.  */
@@ -113,8 +115,8 @@ tilegx_linux_init_abi (struct gdbarch_info info, struct gdbarch *gdbarch)
 
   tramp_frame_prepend_unwinder (gdbarch, &tilegx_linux_rt_sigframe);
 
-  set_gdbarch_regset_from_core_section (gdbarch,
-                                       tilegx_regset_from_core_section);
+  set_gdbarch_iterate_over_regset_sections
+    (gdbarch, tilegx_iterate_over_regset_sections);
 
   /* GNU/Linux uses SVR4-style shared libraries.  */
   if (arch_size == 32)
@@ -131,15 +133,11 @@ tilegx_linux_init_abi (struct gdbarch_info info, struct gdbarch *gdbarch)
   /* Shared library handling.  */
   set_gdbarch_skip_trampoline_code (gdbarch, find_solib_trampoline_target);
   set_gdbarch_skip_solib_resolver (gdbarch, glibc_skip_solib_resolver);
-
-  set_gdbarch_get_siginfo_type (gdbarch, linux_get_siginfo_type);
 }
 
-/* Provide a prototype to silence -Wmissing-prototypes.  */
-extern initialize_file_ftype _initialize_tilegx_linux_tdep;
-
+void _initialize_tilegx_linux_tdep ();
 void
-_initialize_tilegx_linux_tdep (void)
+_initialize_tilegx_linux_tdep ()
 {
   gdbarch_register_osabi (bfd_arch_tilegx, bfd_mach_tilegx, GDB_OSABI_LINUX,
                          tilegx_linux_init_abi);
This page took 0.026094 seconds and 4 git commands to generate.