From 267bf99505c8522ff9e10ec56c195deb533da338 Mon Sep 17 00:00:00 2001 From: Ramana Radhakrishnan Date: Tue, 5 May 2009 11:41:32 +0000 Subject: [PATCH] Fix local branches for bl and blx. --- gas/ChangeLog | 22 +++ gas/config/tc-arm.c | 233 +++++++++++++++++++++++++++++--- gas/config/tc-arm.h | 19 ++- gas/testsuite/ChangeLog | 12 ++ gas/testsuite/gas/arm/bl-local-v4t.d | 19 +++ gas/testsuite/gas/arm/bl-local-v4t.s | 25 ++++ gas/testsuite/gas/arm/blx-local-thumb.l | 2 + gas/testsuite/gas/arm/blx-local.d | 32 +++-- gas/testsuite/gas/arm/blx-local.l | 3 + gas/testsuite/gas/arm/blx-local.s | 46 +++++-- 10 files changed, 374 insertions(+), 39 deletions(-) create mode 100644 gas/testsuite/gas/arm/bl-local-v4t.d create mode 100644 gas/testsuite/gas/arm/bl-local-v4t.s create mode 100644 gas/testsuite/gas/arm/blx-local-thumb.l create mode 100644 gas/testsuite/gas/arm/blx-local.l diff --git a/gas/ChangeLog b/gas/ChangeLog index e935809..1674d78 100644 --- a/gas/ChangeLog +++ b/gas/ChangeLog @@ -1,3 +1,25 @@ +2009-05-05 Ramana Radhakrishnan + + * config\tc-arm.h: Fix typo in comment. + (ARM_IS_FUNC): New macro. + (MD_APPLY_SYM_VALUE): Define. + + * config\tc-arm.c (do_blx): Retain BFD_RELOC_ARM_PCREL_BLX for + all versions of EABI. + (relax_branch): Do not relax for branches to ARM functions. + (md_pcrel_from_section): Set up base correctly for + BFD_RELOC_THUMB_PCREL_BLX, BFD_RELOC_THUMB_PCREL_CALL, + BFD_RELOC_THUMB_PCREL_BRANCH23, BFD_RELOC_ARM_PCREL_BLX + BFD_RELOC_ARM_PCREL_CALL. + (md_apply_fix): Flip bl to blx where possible. + Flip blx to bl where possible. + (arm_force_relocation): Force relocations for + BFD_RELOC_ARM_PCREL_JUMP, BFD_RELOC_ARM_PCREL_JUMP, + BFD_RELOC_ARM_PCREL_BLX, BFD_RELOC_THUMB_PCREL_BLX, + BFD_RELOC_THUMB_PCREL_BRANCH20, BFD_RELOC_THUMB_PCREL_BRANCH23, + BFD_RELOC_THUMB_PCREL_BRANCH25. + (arm_apply_sym_value): New function. + 2009-05-04 Tristan Gingold * config/tc-alpha.c: Also declare alpha_prologue_label for OBJ_EVAX. diff --git a/gas/config/tc-arm.c b/gas/config/tc-arm.c index 21de2b3..06253c9 100644 --- a/gas/config/tc-arm.c +++ b/gas/config/tc-arm.c @@ -6735,7 +6735,7 @@ encode_branch (int default_reloc) { constraint (inst.operands[0].imm != BFD_RELOC_ARM_PLT32, _("the only suffix valid here is '(plt)'")); - inst.reloc.type = BFD_RELOC_ARM_PLT32; + inst.reloc.type = BFD_RELOC_ARM_PLT32; } else { @@ -6794,15 +6794,12 @@ do_blx (void) else { /* Arg is an address; this instruction cannot be executed - conditionally, and the opcode must be adjusted. */ + conditionally, and the opcode must be adjusted. + We retain the BFD_RELOC_ARM_PCREL_BLX till the very end + where we generate out a BFD_RELOC_ARM_PCREL_CALL instead. */ constraint (inst.cond != COND_ALWAYS, BAD_COND); inst.instruction = 0xfa000000; -#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); + encode_branch (BFD_RELOC_ARM_PCREL_BLX); } } @@ -17461,6 +17458,12 @@ relax_branch (fragS *fragp, asection *sec, int bits, long stretch) || sec != S_GET_SEGMENT (fragp->fr_symbol)) return 4; +#ifdef OBJ_ELF + if (S_IS_DEFINED (fragp->fr_symbol) + && ARM_IS_FUNC (fragp->fr_symbol)) + return 4; +#endif + val = relaxed_symbol_addr (fragp, stretch); addr = fragp->fr_address + fragp->fr_fix + 4; val -= addr; @@ -18185,6 +18188,7 @@ md_pcrel_from_section (fixS * fixP, segT seg) ))) base = 0; + switch (fixP->fx_r_type) { /* PC relative addressing on the Thumb is slightly odd as the @@ -18206,21 +18210,43 @@ md_pcrel_from_section (fixS * fixP, segT seg) case BFD_RELOC_THUMB_PCREL_BRANCH9: case BFD_RELOC_THUMB_PCREL_BRANCH12: case BFD_RELOC_THUMB_PCREL_BRANCH20: - case BFD_RELOC_THUMB_PCREL_BRANCH23: case BFD_RELOC_THUMB_PCREL_BRANCH25: return base + 4; + case BFD_RELOC_THUMB_PCREL_BRANCH23: + if (fixP->fx_addsy + && ARM_IS_FUNC (fixP->fx_addsy) + && ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v5t)) + base = fixP->fx_where + fixP->fx_frag->fr_address; + return base + 4; + /* BLX is like branches above, but forces the low two bits of PC to zero. */ - case BFD_RELOC_THUMB_PCREL_BLX: + case BFD_RELOC_THUMB_PCREL_BLX: + if (fixP->fx_addsy + && THUMB_IS_FUNC (fixP->fx_addsy) + && ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v5t)) + base = fixP->fx_where + fixP->fx_frag->fr_address; return (base + 4) & ~3; /* 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_BLX: + if (fixP->fx_addsy + && ARM_IS_FUNC (fixP->fx_addsy) + && ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v5t)) + base = fixP->fx_where + fixP->fx_frag->fr_address; + return base + 8; + + case BFD_RELOC_ARM_PCREL_CALL: + if (fixP->fx_addsy + && THUMB_IS_FUNC (fixP->fx_addsy) + && ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v5t)) + base = fixP->fx_where + fixP->fx_frag->fr_address; + return base + 8; + 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 /* When handling fixups immediately, because we have already @@ -18239,6 +18265,7 @@ md_pcrel_from_section (fixS * fixP, segT seg) return base + 8; #endif + /* ARM mode loads relative to PC are also offset by +8. Unlike branches, the Windows CE loader *does* expect the relocation to take this into account. */ @@ -18982,14 +19009,41 @@ md_apply_fix (fixS * fixP, #ifdef OBJ_ELF case BFD_RELOC_ARM_PCREL_CALL: - newval = md_chars_to_number (buf, INSN_SIZE); - if ((newval & 0xf0000000) == 0xf0000000) - temp = 1; + + if (ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v5t) + && fixP->fx_addsy + && !S_IS_EXTERNAL (fixP->fx_addsy) + && (S_GET_SEGMENT (fixP->fx_addsy) == seg) + && THUMB_IS_FUNC (fixP->fx_addsy)) + /* Flip the bl to blx. This is a simple flip + bit here because we generate PCREL_CALL for + unconditional bls. */ + { + newval = md_chars_to_number (buf, INSN_SIZE); + newval = newval | 0x10000000; + md_number_to_chars (buf, newval, INSN_SIZE); + temp = 1; + fixP->fx_done = 1; + } else temp = 3; goto arm_branch_common; case BFD_RELOC_ARM_PCREL_JUMP: + if (ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v5t) + && fixP->fx_addsy + && !S_IS_EXTERNAL (fixP->fx_addsy) + && (S_GET_SEGMENT (fixP->fx_addsy) == seg) + && THUMB_IS_FUNC (fixP->fx_addsy)) + { + /* This would map to a bl, b, + b to a Thumb function. We + need to force a relocation for this particular + case. */ + newval = md_chars_to_number (buf, INSN_SIZE); + fixP->fx_done = 0; + } + case BFD_RELOC_ARM_PLT32: #endif case BFD_RELOC_ARM_PCREL_BRANCH: @@ -18997,7 +19051,30 @@ md_apply_fix (fixS * fixP, goto arm_branch_common; case BFD_RELOC_ARM_PCREL_BLX: + temp = 1; + if (ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v5t) + && fixP->fx_addsy + && !S_IS_EXTERNAL (fixP->fx_addsy) + && (S_GET_SEGMENT (fixP->fx_addsy) == seg) + && ARM_IS_FUNC (fixP->fx_addsy)) + { + /* Flip the blx to a bl and warn. */ + const char *name = S_GET_NAME (fixP->fx_addsy); + newval = 0xeb000000; + as_warn_where (fixP->fx_file, fixP->fx_line, + _("blx to '%s' an ARM ISA state function changed to bl"), + name); + md_number_to_chars (buf, newval, INSN_SIZE); + temp = 3; + fixP->fx_done = 1; + } + +#ifdef OBJ_ELF + if (EF_ARM_EABI_VERSION (meabi_flags) >= EF_ARM_EABI_VER4) + fixP->fx_r_type = BFD_RELOC_ARM_PCREL_CALL; +#endif + arm_branch_common: /* We are going to store value (shifted right by two) in the instruction, in a 24 bit, signed field. Bits 26 through 32 either @@ -19084,6 +19161,16 @@ md_apply_fix (fixS * fixP, break; case BFD_RELOC_THUMB_PCREL_BRANCH20: + if (fixP->fx_addsy + && (S_GET_SEGMENT (fixP->fx_addsy) == seg) + && !S_IS_EXTERNAL (fixP->fx_addsy) + && S_IS_DEFINED (fixP->fx_addsy) + && ARM_IS_FUNC (fixP->fx_addsy) + && ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v5t)) + { + /* Force a relocation for a branch 20 bits wide. */ + fixP->fx_done = 0; + } if ((value & ~0x1fffff) && ((value & ~0x1fffff) != ~0x1fffff)) as_bad_where (fixP->fx_file, fixP->fx_line, _("conditional branch out of range")); @@ -19109,7 +19196,57 @@ md_apply_fix (fixS * fixP, break; case BFD_RELOC_THUMB_PCREL_BLX: + + /* If there is a blx from a thumb state function to + another thumb function flip this to a bl and warn + about it. */ + + if (fixP->fx_addsy + && S_IS_DEFINED (fixP->fx_addsy) + && !S_IS_EXTERNAL (fixP->fx_addsy) + && (S_GET_SEGMENT (fixP->fx_addsy) == seg) + && THUMB_IS_FUNC (fixP->fx_addsy)) + { + const char *name = S_GET_NAME (fixP->fx_addsy); + as_warn_where (fixP->fx_file, fixP->fx_line, + _("blx to Thumb func '%s' from Thumb ISA state changed to bl"), + name); + newval = md_chars_to_number (buf + THUMB_SIZE, THUMB_SIZE); + newval = newval | 0x1000; + md_number_to_chars (buf+THUMB_SIZE, newval, THUMB_SIZE); + fixP->fx_r_type = BFD_RELOC_THUMB_PCREL_BRANCH23; + fixP->fx_done = 1; + } + + + goto thumb_bl_common; + case BFD_RELOC_THUMB_PCREL_BRANCH23: + + /* A bl from Thumb state ISA to an internal ARM state function + is converted to a blx. */ + if (fixP->fx_addsy + && (S_GET_SEGMENT (fixP->fx_addsy) == seg) + && !S_IS_EXTERNAL (fixP->fx_addsy) + && S_IS_DEFINED (fixP->fx_addsy) + && ARM_IS_FUNC (fixP->fx_addsy) + && ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v5t)) + { + newval = md_chars_to_number (buf + THUMB_SIZE, THUMB_SIZE); + newval = newval & ~0x1000; + md_number_to_chars (buf+THUMB_SIZE, newval, THUMB_SIZE); + fixP->fx_r_type = BFD_RELOC_THUMB_PCREL_BLX; + fixP->fx_done = 1; + } + + thumb_bl_common: + +#ifdef OBJ_ELF + if (EF_ARM_EABI_VERSION (meabi_flags) >= EF_ARM_EABI_VER4 && + fixP->fx_r_type == BFD_RELOC_THUMB_PCREL_BLX) + fixP->fx_r_type = BFD_RELOC_THUMB_PCREL_BRANCH23; +#endif + if ((value & ~0x3fffff) && ((value & ~0x3fffff) != ~0x3fffff)) as_bad_where (fixP->fx_file, fixP->fx_line, _("branch out of range")); @@ -19962,6 +20099,7 @@ arm_validate_fix (fixS * fixP) } #endif + int arm_force_relocation (struct fix * fixp) { @@ -19970,6 +20108,34 @@ arm_force_relocation (struct fix * fixp) return 1; #endif + /* In case we have a call or a branch to a function in ARM ISA mode from + a thumb function or vice-versa force the relocation. These relocations + are cleared off for some cores that might have blx and simple transformations + are possible. */ + +#ifdef OBJ_ELF + switch (fixp->fx_r_type) + { + case BFD_RELOC_ARM_PCREL_JUMP: + case BFD_RELOC_ARM_PCREL_CALL: + case BFD_RELOC_THUMB_PCREL_BLX: + if (THUMB_IS_FUNC (fixp->fx_addsy)) + return 1; + break; + + case BFD_RELOC_ARM_PCREL_BLX: + case BFD_RELOC_THUMB_PCREL_BRANCH25: + case BFD_RELOC_THUMB_PCREL_BRANCH20: + case BFD_RELOC_THUMB_PCREL_BRANCH23: + if (ARM_IS_FUNC (fixp->fx_addsy)) + return 1; + break; + + default: + break; + } +#endif + /* Resolve these relocations even if the symbol is extern or weak. */ if (fixp->fx_r_type == BFD_RELOC_ARM_IMMEDIATE || fixp->fx_r_type == BFD_RELOC_ARM_OFFSET_IMM @@ -20450,7 +20616,7 @@ md_begin (void) -mthumb-interwork Code supports ARM/Thumb interworking -m[no-]warn-deprecated Warn about deprecated features - + For now we will also provide support for: -mapcs-32 32-bit Program counter @@ -21608,4 +21774,39 @@ arm_convert_symbolic_attribute (const char *name) return -1; } + + +/* Apply sym value for relocations only in the case that + they are for local symbols and you have the respective + architectural feature for blx and simple switches. */ +int +arm_apply_sym_value (struct fix * fixP) +{ + if (fixP->fx_addsy + && ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v5t) + && !S_IS_EXTERNAL (fixP->fx_addsy)) + { + switch (fixP->fx_r_type) + { + case BFD_RELOC_ARM_PCREL_BLX: + case BFD_RELOC_THUMB_PCREL_BRANCH23: + if (ARM_IS_FUNC (fixP->fx_addsy)) + return 1; + break; + + case BFD_RELOC_ARM_PCREL_CALL: + case BFD_RELOC_THUMB_PCREL_BLX: + if (THUMB_IS_FUNC (fixP->fx_addsy)) + return 1; + break; + + default: + break; + } + + } + return 0; +} #endif /* OBJ_ELF */ + + diff --git a/gas/config/tc-arm.h b/gas/config/tc-arm.h index c6f6fd8..13bc86a 100644 --- a/gas/config/tc-arm.h +++ b/gas/config/tc-arm.h @@ -126,15 +126,24 @@ bfd_boolean arm_is_eabi (void); #ifdef OBJ_ELF /* For ELF objects THUMB_IS_FUNC is inferred from - ARM_IS_TUMB and the function type. */ + ARM_IS_THUMB and the function type. */ #define THUMB_IS_FUNC(s) \ ((arm_is_eabi () \ && (ARM_IS_THUMB (s)) \ && (symbol_get_bfdsym (s)->flags & BSF_FUNCTION)) \ || (ARM_GET_FLAG (s) & THUMB_FLAG_FUNC)) +#define ARM_IS_FUNC(s) \ + ((arm_is_eabi () \ + && !(ARM_IS_THUMB (s)) \ + /* && !(THUMB_FLAG_FUNC & ARM_GET_FLAG (s)) \ */ \ + && (symbol_get_bfdsym (s)->flags & BSF_FUNCTION))) + + #else #define THUMB_IS_FUNC(s) (ARM_GET_FLAG (s) & THUMB_FLAG_FUNC) +#define ARM_IS_FUNC(s) (!THUMB_IS_FUNC (s) \ + && (symbol_get_bfdsym (s)->flags & BSF_FUNCTION)) #endif #define ARM_SET_THUMB(s,t) ((t) ? ARM_SET_FLAG (s, ARM_FLAG_THUMB) : ARM_RESET_FLAG (s, ARM_FLAG_THUMB)) @@ -247,12 +256,17 @@ struct arm_segment_info_type # define EXTERN_FORCE_RELOC 1 # define tc_fix_adjustable(FIX) arm_fix_adjustable (FIX) +#endif + +#ifdef OBJ_ELF /* Values passed to md_apply_fix don't include the symbol value. */ -# define MD_APPLY_SYM_VALUE(FIX) 0 +# define MD_APPLY_SYM_VALUE(FIX) arm_apply_sym_value (FIX) #endif #ifdef OBJ_COFF # define TC_VALIDATE_FIX(FIX, SEGTYPE, LABEL) arm_validate_fix (FIX) +/* Values passed to md_apply_fix don't include the symbol value. */ +# define MD_APPLY_SYM_VALUE(FIX) 0 #endif #define MD_PCREL_FROM_SECTION(F,S) md_pcrel_from_section(F,S) @@ -290,4 +304,5 @@ void tc_pe_dwarf2_emit_offset (symbolS *, unsigned int); #ifdef OBJ_ELF #define CONVERT_SYMBOLIC_ATTRIBUTE(name) arm_convert_symbolic_attribute (name) extern int arm_convert_symbolic_attribute (const char *); +extern int arm_apply_sym_value (struct fix *); #endif diff --git a/gas/testsuite/ChangeLog b/gas/testsuite/ChangeLog index e7a526c..b25a40a 100644 --- a/gas/testsuite/ChangeLog +++ b/gas/testsuite/ChangeLog @@ -1,3 +1,15 @@ +2009-05-05 Ramana Radhakrishnan + + * gas\arm\bl-local-v4t.d: New file. + * gas\arm\bl-local-v4t.s: New file. + * gas\arm\blx-local.s: Update for branches and calls to local + functions. + * gas\arm\blx-local.d: Likewise. + * gas\arm\blx-local.l: New file. + * gas\arm\blx-local-thumb.l: New file. + * gas\arm\blx-local-thumb.s: New file. + * gas\arm\blx-local-thumb.d: New file. + 2009-05-01 Nathan Sidwell Daniel Jacobowitz diff --git a/gas/testsuite/gas/arm/bl-local-v4t.d b/gas/testsuite/gas/arm/bl-local-v4t.d new file mode 100644 index 0000000..b5af7fd --- /dev/null +++ b/gas/testsuite/gas/arm/bl-local-v4t.d @@ -0,0 +1,19 @@ +#name: bl local instructions for v4t. +#objdump: -drw --prefix-addresses --show-raw-insn +#skip: *-*-*coff *-*-pe *-*-wince *-*-*aout* *-*-netbsd *-*-riscix* +#as: +# stderr: blx-local-thumb.l + +.*: +file format .*arm.* +Disassembly of section .text: +0+00 <[^>]*> f7ff fffe bl 00+18 <[^>]*> 0: R_ARM_THM_CALL foo2 +0+1c <[^>]*> d004 beq.n 00+28 <[^>]*> +0+1e <[^>]*> e003 b.n 00+28 <[^>]*> +0+20 <[^>]*> f000 f808 bl 00+34 <[^>]*> +0+24 <[^>]*> f000 f802 bl 00+2c <[^>]*> +0+28 <[^>]*> 46c0 nop \(mov r8, r8\) +0+2a <[^>]*> 46c0 nop \(mov r8, r8\) +0+2c <[^>]*> 46c0 nop \(mov r8, r8\) + ... +0+30 <[^>]*> e1a00000 nop \(mov r0,r0\) +0+34 <[^>]*> e1a00000 nop \(mov r0,r0\) \ No newline at end of file diff --git a/gas/testsuite/gas/arm/bl-local-v4t.s b/gas/testsuite/gas/arm/bl-local-v4t.s new file mode 100644 index 0000000..4935344 --- /dev/null +++ b/gas/testsuite/gas/arm/bl-local-v4t.s @@ -0,0 +1,25 @@ + .text + .arch armv4t + .syntax unified + .thumb +one: + bl foo2 @ bl foo2 with reloc. + beq foo @ beq foo with reloc. + b foo @ branch foo with reloc. + bl fooundefarm + bl fooundefthumb + .thumb + .type foo, %function + .thumb_func +foo: + nop + nop +fooundefthumb: + nop + .type foo2, %function + .arm + .align 2 +foo2: + nop +fooundefarm: + nop diff --git a/gas/testsuite/gas/arm/blx-local-thumb.l b/gas/testsuite/gas/arm/blx-local-thumb.l new file mode 100644 index 0000000..588674c --- /dev/null +++ b/gas/testsuite/gas/arm/blx-local-thumb.l @@ -0,0 +1,2 @@ +[^;]*: Assembler messages: +[^;]*:6: Warning: blx to Thumb func 'foo' from Thumb ISA state changed to bl \ No newline at end of file diff --git a/gas/testsuite/gas/arm/blx-local.d b/gas/testsuite/gas/arm/blx-local.d index e187536..4b7d53a 100644 --- a/gas/testsuite/gas/arm/blx-local.d +++ b/gas/testsuite/gas/arm/blx-local.d @@ -1,15 +1,29 @@ #name: Local BLX instructions -#objdump: -dr --prefix-addresses --show-raw-insn +#objdump: -drw --prefix-addresses --show-raw-insn #skip: *-*-*coff *-*-pe *-*-wince *-*-*aout* *-*-netbsd *-*-riscix* #as: - -# Test assembler resolution of blx instructions. - +# stderr: blx-local.l +# Test assembler resolution of blx and bl instructions in ARM mode. .*: +file format .*arm.* Disassembly of section .text: - -0+00 <[^>]*> fa000000 blx 00+8 -0+04 <[^>]*> fbffffff blx 00+a -0+08 <[^>]*> 46c0 nop \(mov r8, r8\) -0+0a <[^>]*> 46c0 nop \(mov r8, r8\) +0+00 <[^>]*> fa000006 blx 00000020 +0+04 <[^>]*> eb000007 bl 00000028 +0+08 <[^>]*> fa000004 blx 00000020 +0+0c <[^>]*> eb000005 bl 00000028 +0+10 <[^>]*> fa00000b blx 00000044 +0+14 <[^>]*> eb00000a bl 00000044 +0+18 <[^>]*> fa000001 blx 00000024 +0+1c <[^>]*> eb000000 bl 00000024 +0+20 <[^>]*> 46c0 nop \(mov r8, r8\) +0+22 <[^>]*> 46c0 nop \(mov r8, r8\) +0+24 <[^>]*> 46c0 nop \(mov r8, r8\) +0+26 <[^>]*> 46c0 nop \(mov r8, r8\) +0+28 <[^>]*> 0bfffffd bleq 00000024 +0+2c <[^>]*> 0afffffc beq 00000024 +0+30 <[^>]*> eafffffb b 00000024 +0+34 <[^>]*> 0bfffffe bleq 00000020 34: R_ARM_JUMP24 foo +0+58 <[^>]*> 0afffffe beq 00000020 38: R_ARM_JUMP24 foo +0+5c <[^>]*> eafffffe b 00000020 3c: R_ARM_JUMP24 foo +0+60 <[^>]*> e1a00000 nop \(mov r0,r0\) +0+64 <[^>]*> e1a00000 nop \(mov r0,r0\) diff --git a/gas/testsuite/gas/arm/blx-local.l b/gas/testsuite/gas/arm/blx-local.l new file mode 100644 index 0000000..fcca464 --- /dev/null +++ b/gas/testsuite/gas/arm/blx-local.l @@ -0,0 +1,3 @@ +[^;]*: Assembler messages: +[^;]*:9: Warning: blx to 'foo2' an ARM ISA state function changed to bl + diff --git a/gas/testsuite/gas/arm/blx-local.s b/gas/testsuite/gas/arm/blx-local.s index c85a562..ed587c9 100644 --- a/gas/testsuite/gas/arm/blx-local.s +++ b/gas/testsuite/gas/arm/blx-local.s @@ -1,16 +1,38 @@ - .text - .arch armv5t - .arm -one: - blx foo - blx foo2 +# objdump: -fdrw --prefix-addresses --show-raw-insn +# not-target: *-*-*aout* *-*-pe - .thumb - .type foo, %function - .thumb_func + .text + .arch armv5t + .arm +one: + blx foo + blx foo2 + bl foo + bl foo2 + blx fooundefarm + bl fooundefarm + blx fooundefthumb + bl fooundefthumb + + .thumb + .type foo, %function + .thumb_func foo: - nop + nop + nop +fooundefthumb: + nop + + .align 2 .type foo2, %function - .thumb_func + .arm foo2: - nop + bleq fooundefthumb @no relocs + beq fooundefthumb @no relocs + b fooundefthumb @no relocs + bleq foo @ R_ARM_PCREL_JUMP + beq foo @ R_ARM_PCREL_JUMP + b foo @ R_ARM_PCREL_JUMP + nop +fooundefarm: + nop -- 2.7.4