diff options
author | Nick Clifton <nickc@redhat.com> | 2001-03-06 22:33:47 +0000 |
---|---|---|
committer | Nick Clifton <nickc@redhat.com> | 2001-03-06 22:33:47 +0000 |
commit | 4f3c3dbb370a8c0c8b66710c5d0c2854c1bab4f5 (patch) | |
tree | 2042b5c453e962b76adfdd2eb4b67bd6899cfb55 /opcodes | |
parent | f8f3c6cc3747d01156af27c7cc74a4628755f4d0 (diff) | |
download | gdb-4f3c3dbb370a8c0c8b66710c5d0c2854c1bab4f5.zip gdb-4f3c3dbb370a8c0c8b66710c5d0c2854c1bab4f5.tar.gz gdb-4f3c3dbb370a8c0c8b66710c5d0c2854c1bab4f5.tar.bz2 |
Fix BLX(1) for Thumb
Diffstat (limited to 'opcodes')
-rw-r--r-- | opcodes/ChangeLog | 6 | ||||
-rw-r--r-- | opcodes/arm-dis.c | 25 |
2 files changed, 27 insertions, 4 deletions
diff --git a/opcodes/ChangeLog b/opcodes/ChangeLog index 5b21a5c..3677f2e 100644 --- a/opcodes/ChangeLog +++ b/opcodes/ChangeLog @@ -1,3 +1,9 @@ +2001-03-06 Nick Clifton <nickc@redhat.com> + + * arm-dis.c (print_insn_thumb): Compute destination address + of BLX(1) instruction by taking bit 1 from PC and not from bit + 0 of the offset. + 2001-03-06 Igor Shevlyakov <igor@windriver.com> * m68k-dis.c (print_insn_m68k): Recognize Coldfire CPUs diff --git a/opcodes/arm-dis.c b/opcodes/arm-dis.c index 686b18a..0681758 100644 --- a/opcodes/arm-dis.c +++ b/opcodes/arm-dis.c @@ -668,15 +668,32 @@ print_insn_thumb (pc, info, given) /* Special processing for Thumb 2 instruction BL sequence: */ if (!*c) /* Check for empty (not NULL) assembler string. */ { + long offset; + info->bytes_per_chunk = 4; info->bytes_per_line = 4; + + offset = BDISP23 (given); if ((given & 0x10000000) == 0) - func (stream, "blx\t"); + { + func (stream, "blx\t"); + + /* The spec says that bit 1 of the branch's destination + address comes from bit 1 of the instruction's + address and not from the offset in the instruction. */ + if (offset & 0x1) + { + /* func (stream, "*malformed!* "); */ + offset &= ~ 0x1; + } + + offset |= ((pc & 0x2) >> 1); + } else - func (stream, "bl\t"); - - info->print_address_func (BDISP23 (given) * 2 + pc + 4, info); + func (stream, "bl\t"); + + info->print_address_func (offset * 2 + pc + 4, info); return 4; } else |