diff options
author | Paul Brook <paul@codesourcery.com> | 2005-12-12 17:03:40 +0000 |
---|---|---|
committer | Paul Brook <paul@codesourcery.com> | 2005-12-12 17:03:40 +0000 |
commit | 39b41c9ca83ec4e504d90bd6e2137e67a27585e2 (patch) | |
tree | f013eec4e858d0da7385c4b83ce0181227ede26c /gas | |
parent | 4970f871a701ce55f5018f31bca1b478448c57ff (diff) | |
download | fsf-binutils-gdb-39b41c9ca83ec4e504d90bd6e2137e67a27585e2.zip fsf-binutils-gdb-39b41c9ca83ec4e504d90bd6e2137e67a27585e2.tar.gz fsf-binutils-gdb-39b41c9ca83ec4e504d90bd6e2137e67a27585e2.tar.bz2 |
2005-12-12 Paul Brook <paul@codesourcery.com>
bfd/
* bfd-in2.h: Regenerate.
* elf32-arm.c (elf32_arm_reloc_map): Add BFD_RELOC_ARM_PCREL_CALL and
BFD_RELOC_ARM_PCREL_JUMP.
(check_use_blx): New function.
(bfd_elf32_arm_process_before_allocation): Don't allocate glue if
using BLX.
(elf32_arm_final_link_relocate): Perform bl<->blx conversion for
R_ARM_CALL and R_ARM_THM.
(elf32_arm_get_eabi_attr_int): New function.
(elf32_arm_size_dynamic_sections): Call check_use_blx.
* libbfd.h: Regenerate.
* reloc.c: Add BFD_RELOC_ARM_PCREL_CALL and BFD_RELOC_ARM_PCREL_JUMP.
gas/
* config/tc-arm.c (do_branch): Generate EABI branch relocations.
(do_bl): New function.
(do_blx): Generate BFD_RELOC_ARM_PCREL_CALL relocation.
(do_t_blx): Generate BFD_RELOC_THUMB_PCREL_BRANCH23.
(insns): Use do_bl.
(md_pcrel_from_section): Add BFD_RELOC_ARM_PCREL_CALL and
BFD_RELOC_ARM_PCREL_JUMP.
(md_apply_fix): Merge BFD_RELOC_ARM_PCREL_BRANCH and
BFD_RELOC_ARM_PCREL_BLX cases. Handle BFD_RELOC_ARM_PCREL_CALL and
BFD_RELOC_ARM_PCREL_JUMP.
(tc_gen_reloc): Handle BFD_RELOC_ARM_PCREL_CALL and
BFD_RELOC_ARM_PCREL_JUMP.
gas/testsuite/
* gas/arm/pic.d: Allow R_ARM_CALL relocations.
include/elf/
* arm.h (elf32_arm_get_eabi_attr_int): Add prototype.
ld/testsuite/
* ld-arm/arm-call.d: New test.
* ld-arm/arm-call1.s: New file.
* ld-arm/arm-call1.s: New file.
* ld-arm/arm-elf.exp: Add arm-call and mixed-app-v5.
* ld-arm/arm.ld: Add .glue_7 and .ARM.attribues.
* ld-arm/mixed-app-v5.d: New file.
* ld-arm/mixed-app.r: Tweak expected output.
Diffstat (limited to 'gas')
-rw-r--r-- | gas/ChangeLog | 17 | ||||
-rw-r--r-- | gas/config/tc-arm.c | 90 | ||||
-rw-r--r-- | gas/testsuite/gas/arm/pic.d | 2 |
3 files changed, 76 insertions, 33 deletions
diff --git a/gas/ChangeLog b/gas/ChangeLog index 00d5415..6f310ea 100644 --- a/gas/ChangeLog +++ b/gas/ChangeLog @@ -1,3 +1,20 @@ +2005-12-12 Paul Brook <paul@codesourcery.com> + + * config/tc-arm.c (do_branch): Generate EABI branch relocations. + (do_bl): New function. + (do_blx): Generate BFD_RELOC_ARM_PCREL_CALL relocation. + (do_t_blx): Generate BFD_RELOC_THUMB_PCREL_BRANCH23. + (insns): Use do_bl. + (md_pcrel_from_section): Add BFD_RELOC_ARM_PCREL_CALL and + BFD_RELOC_ARM_PCREL_JUMP. + (md_apply_fix): Merge BFD_RELOC_ARM_PCREL_BRANCH and + BFD_RELOC_ARM_PCREL_BLX cases. Handle BFD_RELOC_ARM_PCREL_CALL and + BFD_RELOC_ARM_PCREL_JUMP. + (tc_gen_reloc): Handle BFD_RELOC_ARM_PCREL_CALL and + BFD_RELOC_ARM_PCREL_JUMP. + gas/testsuite/ + * gas/arm/pic.d: Allow R_ARM_CALL relocations. + 2005-12-12 Nathan Sidwell <nathan@codesourcery.com> * configure.in: Replace ms1 arch with mt arch. diff --git a/gas/config/tc-arm.c b/gas/config/tc-arm.c index 9f8e0e9..a2baa32 100644 --- a/gas/config/tc-arm.c +++ b/gas/config/tc-arm.c @@ -4610,7 +4610,28 @@ encode_branch (int default_reloc) static void do_branch (void) { - encode_branch (BFD_RELOC_ARM_PCREL_BRANCH); +#ifdef OBJ_ELF + if (EF_ARM_EABI_VERSION (meabi_flags) >= EF_ARM_EABI_VER4) + encode_branch (BFD_RELOC_ARM_PCREL_JUMP); + else +#endif + encode_branch (BFD_RELOC_ARM_PCREL_BRANCH); +} + +static void +do_bl (void) +{ +#ifdef OBJ_ELF + if (EF_ARM_EABI_VERSION (meabi_flags) >= EF_ARM_EABI_VER4) + { + if (inst.cond == COND_ALWAYS) + encode_branch (BFD_RELOC_ARM_PCREL_CALL); + else + encode_branch (BFD_RELOC_ARM_PCREL_JUMP); + } + else +#endif + encode_branch (BFD_RELOC_ARM_PCREL_BRANCH); } /* ARM V5 branch-link-exchange instruction (argument parse) @@ -4639,7 +4660,12 @@ do_blx (void) conditionally, and the opcode must be adjusted. */ constraint (inst.cond != COND_ALWAYS, BAD_COND); inst.instruction = 0xfa000000; - encode_branch (BFD_RELOC_ARM_PCREL_BLX); +#ifdef OBJ_ELF + if (EF_ARM_EABI_VERSION (meabi_flags) >= EF_ARM_EABI_VER4) + encode_branch (BFD_RELOC_ARM_PCREL_CALL); + else +#endif + encode_branch (BFD_RELOC_ARM_PCREL_BLX); } } @@ -6434,7 +6460,12 @@ do_t_blx (void) { /* No register. This must be BLX(1). */ inst.instruction = 0xf000e800; - inst.reloc.type = BFD_RELOC_THUMB_PCREL_BLX; +#ifdef OBJ_ELF + if (EF_ARM_EABI_VERSION (meabi_flags) >= EF_ARM_EABI_VER4) + inst.reloc.type = BFD_RELOC_THUMB_PCREL_BRANCH23; + else +#endif + inst.reloc.type = BFD_RELOC_THUMB_PCREL_BLX; inst.reloc.pc_rel = 1; } } @@ -8689,7 +8720,7 @@ static const struct asm_opcode insns[] = TCE(swi, f000000, df00, 1, (EXPi), swi, t_swi), tCE(b, a000000, b, 1, (EXPr), branch, t_branch), - TCE(bl, b000000, f000f800, 1, (EXPr), branch, t_branch23), + TCE(bl, b000000, f000f800, 1, (EXPr), bl, t_branch23), /* Pseudo ops. */ tCE(adr, 28f0000, adr, 2, (RR, EXP), adr, t_adr), @@ -10849,6 +10880,8 @@ md_pcrel_from_section (fixS * fixP, segT seg) /* ARM mode branches are offset by +8. However, the Windows CE loader expects the relocation not to take this into account. */ case BFD_RELOC_ARM_PCREL_BRANCH: + case BFD_RELOC_ARM_PCREL_CALL: + case BFD_RELOC_ARM_PCREL_JUMP: case BFD_RELOC_ARM_PCREL_BLX: case BFD_RELOC_ARM_PLT32: #ifdef TE_WINCE @@ -11457,15 +11490,30 @@ md_apply_fix (fixS * fixP, md_number_to_chars (buf, newval, INSN_SIZE); break; - case BFD_RELOC_ARM_PCREL_BRANCH: #ifdef OBJ_ELF + case BFD_RELOC_ARM_PCREL_CALL: + newval = md_chars_to_number (buf, INSN_SIZE); + if ((newval & 0xf0000000) == 0xf0000000) + temp = 1; + else + temp = 3; + goto arm_branch_common; + + case BFD_RELOC_ARM_PCREL_JUMP: case BFD_RELOC_ARM_PLT32: #endif + case BFD_RELOC_ARM_PCREL_BRANCH: + temp = 3; + goto arm_branch_common; + case BFD_RELOC_ARM_PCREL_BLX: + temp = 1; + arm_branch_common: /* We are going to store value (shifted right by two) in the - instruction, in a 24 bit, signed field. Bits 0 and 1 must be - clear, and bits 26 through 32 either all clear or all set. */ - if (value & 0x00000003) + instruction, in a 24 bit, signed field. Bits 26 through 32 either + all clear or all set and bit 0 must be clear. For B/BL bit 1 must + also be be clear. */ + if (value & temp) as_bad_where (fixP->fx_file, fixP->fx_line, _("misaligned branch destination")); if ((value & (offsetT)0xfe000000) != (offsetT)0 @@ -11481,30 +11529,6 @@ md_apply_fix (fixS * fixP, } break; - case BFD_RELOC_ARM_PCREL_BLX: - /* BLX allows bit 1 to be set in the branch destination, since - it targets a Thumb instruction which is only required to be - aligned modulo 2. Other constraints are as for B/BL. */ - if (value & 0x00000001) - as_bad_where (fixP->fx_file, fixP->fx_line, - _("misaligned BLX destination")); - if ((value & (offsetT)0xfe000000) != (offsetT)0 - && (value & (offsetT)0xfe000000) != (offsetT)0xfe000000) - as_bad_where (fixP->fx_file, fixP->fx_line, - _("branch out of range")); - - if (fixP->fx_done || !seg->use_rela_p) - { - offsetT hbit; - hbit = (value >> 1) & 1; - value = (value >> 2) & 0x00ffffff; - - newval = md_chars_to_number (buf, INSN_SIZE); - newval |= value | hbit << 24; - md_number_to_chars (buf, newval, INSN_SIZE); - } - break; - case BFD_RELOC_THUMB_PCREL_BRANCH7: /* CZB */ /* CZB can only branch forward. */ if (value & ~0x7e) @@ -11969,6 +11993,8 @@ tc_gen_reloc (asection * section ATTRIBUTE_UNUSED, case BFD_RELOC_ARM_TARGET2: case BFD_RELOC_ARM_TLS_LE32: case BFD_RELOC_ARM_TLS_LDO32: + case BFD_RELOC_ARM_PCREL_CALL: + case BFD_RELOC_ARM_PCREL_JUMP: code = fixp->fx_r_type; break; diff --git a/gas/testsuite/gas/arm/pic.d b/gas/testsuite/gas/arm/pic.d index 133614c..8eed71d 100644 --- a/gas/testsuite/gas/arm/pic.d +++ b/gas/testsuite/gas/arm/pic.d @@ -9,7 +9,7 @@ Disassembly of section .text: 00+0 <[^>]*> eb...... bl 00+. <[^>]*> - 0: R_ARM_PC24 foo.* + 0: R_ARM_(PC24|CALL) foo.* 00+4 <[^>]*> eb...... bl 0[0123456789abcdef]+ <[^>]*> 4: R_ARM_PLT32 foo \.\.\. |