gdb: xtensa-linux: add call0 support
authorMax Filippov <jcmvbkbc@gmail.com>
Fri, 18 Nov 2016 17:48:01 +0000 (09:48 -0800)
committerMax Filippov <jcmvbkbc@gmail.com>
Mon, 27 Mar 2017 19:58:52 +0000 (12:58 -0700)
Correctly handle a0- registers. This allows debugging call0 code in
linux natively.
The register structure is the same for windowed and call0 ABIs because
currently linux kernel internally requires windowed registers, so they are
always present.

gdb/
2017-03-27  Max Filippov  <jcmvbkbc@gmail.com>

* xtensa-linux-nat.c (fill_gregset): Call regcache_raw_collect
for a single specified register or for all registers in
a0_base..a0_base + C0_NREGS range.
(supply_gregset_reg): Call regcache_raw_supply for a single
specified register or for all registers in a0_base..a0_base +
C0_NREGS range.

gdb/ChangeLog
gdb/xtensa-linux-nat.c

index 5687fada5b50458c1bf5df1090d78710dbb21736..2faf4897a596f57f75861da396ab9399cc6bda2a 100644 (file)
@@ -1,3 +1,12 @@
+2017-03-27  Max Filippov  <jcmvbkbc@gmail.com>
+
+       * xtensa-linux-nat.c (fill_gregset): Call regcache_raw_collect
+       for a single specified register or for all registers in
+       a0_base..a0_base + C0_NREGS range.
+       (supply_gregset_reg): Call regcache_raw_supply for a single
+       specified register or for all registers in a0_base..a0_base +
+       C0_NREGS range.
+
 2017-03-27  Max Filippov  <jcmvbkbc@gmail.com>
 
        * arch/xtensa.h (C0_NREGS): Add definition.
index 69c7eefa664b1d5f6070be027520f0a2cb8cc835..a4b001e86b9342e547ced715640dea9a8db08bd2 100644 (file)
@@ -94,6 +94,20 @@ fill_gregset (const struct regcache *regcache,
                              gdbarch_tdep (gdbarch)->ar_base + i,
                              &regs->ar[i]);
     }
+  if (regnum >= gdbarch_tdep (gdbarch)->a0_base
+      && regnum < gdbarch_tdep (gdbarch)->a0_base + C0_NREGS)
+    regcache_raw_collect (regcache, regnum,
+                         &regs->ar[(4 * regs->windowbase + regnum
+                                    - gdbarch_tdep (gdbarch)->a0_base)
+                         % gdbarch_tdep (gdbarch)->num_aregs]);
+  else if (regnum == -1)
+    {
+      for (i = 0; i < C0_NREGS; ++i)
+       regcache_raw_collect (regcache,
+                             gdbarch_tdep (gdbarch)->a0_base + i,
+                             &regs->ar[(4 * regs->windowbase + i)
+                             % gdbarch_tdep (gdbarch)->num_aregs]);
+    }
 }
 
 static void
@@ -146,6 +160,20 @@ supply_gregset_reg (struct regcache *regcache,
                              gdbarch_tdep (gdbarch)->ar_base + i,
                              &regs->ar[i]);
     }
+  if (regnum >= gdbarch_tdep (gdbarch)->a0_base
+      && regnum < gdbarch_tdep (gdbarch)->a0_base + C0_NREGS)
+    regcache_raw_supply (regcache, regnum,
+                        &regs->ar[(4 * regs->windowbase + regnum
+                                   - gdbarch_tdep (gdbarch)->a0_base)
+                        % gdbarch_tdep (gdbarch)->num_aregs]);
+  else if (regnum == -1)
+    {
+      for (i = 0; i < C0_NREGS; ++i)
+       regcache_raw_supply (regcache,
+                            gdbarch_tdep (gdbarch)->a0_base + i,
+                            &regs->ar[(4 * regs->windowbase + i)
+                            % gdbarch_tdep (gdbarch)->num_aregs]);
+    }
 }
 
 void