aboutsummaryrefslogtreecommitdiff
path: root/gdb/mips-tdep.c
diff options
context:
space:
mode:
authorMaciej W. Rozycki <macro@linux-mips.org>2012-06-11 10:11:14 +0000
committerMaciej W. Rozycki <macro@linux-mips.org>2012-06-11 10:11:14 +0000
commit2e81047f911b9181987439ec157dc3ed1e567393 (patch)
tree051151454be91e45c0a35d05b2f0b08b7a6c0234 /gdb/mips-tdep.c
parentc7a8dbf91f37df83dd9153f0a540a34d710d5f73 (diff)
downloadgdb-2e81047f911b9181987439ec157dc3ed1e567393.zip
gdb-2e81047f911b9181987439ec157dc3ed1e567393.tar.gz
gdb-2e81047f911b9181987439ec157dc3ed1e567393.tar.bz2
* mips-tdep.c (mips_push_dummy_code): Handle microMIPS code.
Diffstat (limited to 'gdb/mips-tdep.c')
-rw-r--r--gdb/mips-tdep.c13
1 files changed, 10 insertions, 3 deletions
diff --git a/gdb/mips-tdep.c b/gdb/mips-tdep.c
index 4c000e7..0439989 100644
--- a/gdb/mips-tdep.c
+++ b/gdb/mips-tdep.c
@@ -4197,11 +4197,18 @@ mips_push_dummy_code (struct gdbarch *gdbarch, CORE_ADDR sp,
CORE_ADDR *real_pc, CORE_ADDR *bp_addr,
struct regcache *regcache)
{
- CORE_ADDR nop_addr;
static gdb_byte nop_insn[] = { 0, 0, 0, 0 };
+ CORE_ADDR nop_addr;
+ CORE_ADDR bp_slot;
/* Reserve enough room on the stack for our breakpoint instruction. */
- *bp_addr = sp - sizeof (nop_insn);
+ bp_slot = sp - sizeof (nop_insn);
+
+ /* Return to microMIPS mode if calling microMIPS code to avoid
+ triggering an address error exception on processors that only
+ support microMIPS execution. */
+ *bp_addr = (mips_pc_is_micromips (gdbarch, funaddr)
+ ? make_compact_addr (bp_slot) : bp_slot);
/* The breakpoint layer automatically adjusts the address of
breakpoints inserted in a branch delay slot. With enough
@@ -4210,7 +4217,7 @@ mips_push_dummy_code (struct gdbarch *gdbarch, CORE_ADDR sp,
trigger the adjustement, and break the function call entirely.
So, we reserve those 4 bytes and write a nop instruction
to prevent that from happening. */
- nop_addr = *bp_addr - sizeof (nop_insn);
+ nop_addr = bp_slot - sizeof (nop_insn);
write_memory (nop_addr, nop_insn, sizeof (nop_insn));
sp = mips_frame_align (gdbarch, nop_addr);