From: Nathan Sidwell Date: Wed, 1 Apr 2009 14:02:57 +0000 (+0000) Subject: * config/tc-arm.c (do_nop): Generate v6k nops whenever possible. X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=e7495e4595478f4547f3d2b0647514ae4221a692;p=binutils-gdb.git * config/tc-arm.c (do_nop): Generate v6k nops whenever possible. (arm_handle_align): Generate v6k ARM, thumb2 wide & narrow nops whenever possible. testsuite/ * gas/arm/align.s, gas/arm/align.d: New. * gas/arm/thumb32.d, gas/arm/arch6zk.d, gas/arm/arch6zk.s, arm/thumb2_relax.d: Adjust for align changes. --- diff --git a/gas/ChangeLog b/gas/ChangeLog index fee4807f91b..27e3fa6bbaa 100644 --- a/gas/ChangeLog +++ b/gas/ChangeLog @@ -1,3 +1,9 @@ +2009-04-01 Nathan Sidwell + + * config/tc-arm.c (do_nop): Generate v6k nops whenever possible. + (arm_handle_align): Generate v6k ARM, thumb2 wide & narrow nops + whenever possible. + 2009-03-31 Peter Bergner * config/tc-ppc.c (ppc_handle_align): Handle power7's group ending nop. diff --git a/gas/config/tc-arm.c b/gas/config/tc-arm.c index 98d8b7ffa3e..78215abccc1 100644 --- a/gas/config/tc-arm.c +++ b/gas/config/tc-arm.c @@ -7316,11 +7316,14 @@ do_mull (void) static void do_nop (void) { - if (inst.operands[0].present) + if (inst.operands[0].present + || ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v6k)) { /* Architectural NOP hints are CPSR sets with no bits selected. */ inst.instruction &= 0xf0000000; - inst.instruction |= 0x0320f000 + inst.operands[0].imm; + inst.instruction |= 0x0320f000; + if (inst.operands[0].present) + inst.instruction |= inst.operands[0].imm; } } @@ -17580,14 +17583,38 @@ md_section_align (segT segment ATTRIBUTE_UNUSED, void arm_handle_align (fragS * fragP) { - static char const arm_noop[4] = { 0x00, 0x00, 0xa0, 0xe1 }; - static char const thumb_noop[2] = { 0xc0, 0x46 }; - static char const arm_bigend_noop[4] = { 0xe1, 0xa0, 0x00, 0x00 }; - static char const thumb_bigend_noop[2] = { 0x46, 0xc0 }; - - int bytes, fix, noop_size; + static char const arm_noop[2][2][4] = + { + { /* ARMv1 */ + {0x00, 0x00, 0xa0, 0xe1}, /* LE */ + {0xe1, 0xa0, 0x00, 0x00}, /* BE */ + }, + { /* ARMv6k */ + {0x00, 0xf0, 0x20, 0xe3}, /* LE */ + {0xe3, 0x20, 0xf0, 0x00}, /* BE */ + }, + }; + static char const thumb_noop[2][2][2] = + { + { /* Thumb-1 */ + {0xc0, 0x46}, /* LE */ + {0x46, 0xc0}, /* BE */ + }, + { /* Thumb-2 */ + {0x00, 0xbf}, /* LE */ + {0xbf, 0x00} /* BE */ + } + }; + static char const wide_thumb_noop[2][4] = + { /* Wide Thumb-2 */ + {0xaf, 0xf3, 0x00, 0x80}, /* LE */ + {0xf3, 0xaf, 0x80, 0x00}, /* BE */ + }; + + unsigned bytes, fix, noop_size; char * p; const char * noop; + const char *narrow_noop = NULL; if (fragP->fr_type != rs_align_code) return; @@ -17603,21 +17630,24 @@ arm_handle_align (fragS * fragP) if (fragP->tc_frag_data & (~ MODE_RECORDED)) { - if (target_big_endian) - noop = thumb_bigend_noop; + if (ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v6t2)) + { + narrow_noop = thumb_noop[1][target_big_endian]; + noop = wide_thumb_noop[target_big_endian]; + } else - noop = thumb_noop; - noop_size = sizeof (thumb_noop); + noop = thumb_noop[0][target_big_endian]; + noop_size = 2; } else { - if (target_big_endian) - noop = arm_bigend_noop; - else - noop = arm_noop; - noop_size = sizeof (arm_noop); + noop = arm_noop[ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v6k) != 0] + [target_big_endian]; + noop_size = 4; } - + + fragP->fr_var = noop_size; + if (bytes & (noop_size - 1)) { fix = bytes & (noop_size - 1); @@ -17626,6 +17656,21 @@ arm_handle_align (fragS * fragP) bytes -= fix; } + if (narrow_noop) + { + if (bytes & noop_size) + { + /* Insert a narrow noop. */ + memcpy (p, narrow_noop, noop_size); + p += noop_size; + bytes -= noop_size; + fix += noop_size; + } + + /* Use wide noops for the remainder */ + noop_size = 4; + } + while (bytes >= noop_size) { memcpy (p, noop, noop_size); @@ -17635,7 +17680,6 @@ arm_handle_align (fragS * fragP) } fragP->fr_fix += fix; - fragP->fr_var = noop_size; } /* Called from md_do_align. Used to create an alignment diff --git a/gas/testsuite/ChangeLog b/gas/testsuite/ChangeLog index 82db4f0f475..62708ea680f 100644 --- a/gas/testsuite/ChangeLog +++ b/gas/testsuite/ChangeLog @@ -1,3 +1,9 @@ +2009-04-01 Nathan Sidwell + + * gas/arm/align.s, gas/arm/align.d: New. + * gas/arm/thumb32.d, gas/arm/arch6zk.d, gas/arm/arch6zk.s, + arm/thumb2_relax.d: Adjust for align changes. + 2009-03-31 Peter Bergner * gas/ppc/power7.d ("ori", ".p2align"): Add tests for group ending nop. diff --git a/gas/testsuite/gas/arm/align.d b/gas/testsuite/gas/arm/align.d new file mode 100644 index 00000000000..92aff426ce3 --- /dev/null +++ b/gas/testsuite/gas/arm/align.d @@ -0,0 +1,25 @@ +# name: ARM V6t2 Alignment +# as: -march=armv6kt2 +# objdump: -dr --prefix-addresses --show-raw-insn + +.*: +file format .*arm.* + +Disassembly of section .text: +0+000 <[^>]*> bf00 nop +0+002 <[^>]*> 4611 mov r1, r2 +0+004 <[^>]*> f3af 8000 nop.w +0+008 <[^>]*> f3af 8000 nop.w +0+00c <[^>]*> f3af 8000 nop.w +0+010 <[^>]*> 4611 mov r1, r2 +0+012 <[^>]*> bf00 nop +0+014 <[^>]*> f3af 8000 nop.w +0+018 <[^>]*> e320f000 nop \{0\} +0+01c <[^>]*> e1a01002 mov r1, r2 +0+020 <[^>]*> e1a01002 mov r1, r2 +0+024 <[^>]*> e320f000 nop \{0\} +0+028 <[^>]*> e320f000 nop \{0\} +0+02c <[^>]*> e320f000 nop \{0\} +0+030 <[^>]*> e320f000 nop \{0\} +0+034 <[^>]*> e320f000 nop \{0\} +0+038 <[^>]*> e320f000 nop \{0\} +0+03c <[^>]*> e320f000 nop \{0\} diff --git a/gas/testsuite/gas/arm/align.s b/gas/testsuite/gas/arm/align.s new file mode 100644 index 00000000000..43c73ca9a4c --- /dev/null +++ b/gas/testsuite/gas/arm/align.s @@ -0,0 +1,14 @@ + .syntax unified + .thumb + nop + mov r1,r2 + .p2align 4 + mov r1,r2 + .p2align 3 + + .arm + nop + mov r1,r2 + .p2align 4 + mov r1,r2 + .p2align 5 diff --git a/gas/testsuite/gas/arm/arch6zk.d b/gas/testsuite/gas/arm/arch6zk.d index e9dee215f4c..7903957e155 100644 --- a/gas/testsuite/gas/arm/arch6zk.d +++ b/gas/testsuite/gas/arm/arch6zk.d @@ -26,7 +26,4 @@ Disassembly of section .text: 0+048 <[^>]*> e320f001 ? yield 0+04c <[^>]*> e16ec371 ? smc 60465 0+050 <[^>]*> 11613c7e ? smcne 5070 -0+054 <[^>]*> e1a00000 ? nop[ ]+\(mov r0,r0\) -0+058 <[^>]*> e1a00000 ? nop[ ]+\(mov r0,r0\) -0+05c <[^>]*> e1a00000 ? nop[ ]+\(mov r0,r0\) - +#... diff --git a/gas/testsuite/gas/arm/arch6zk.s b/gas/testsuite/gas/arm/arch6zk.s index 93398675b82..19c2c6525a0 100644 --- a/gas/testsuite/gas/arm/arch6zk.s +++ b/gas/testsuite/gas/arm/arch6zk.s @@ -26,8 +26,5 @@ label: smc 0xec31 smcne 0x13ce - # Add three nop instructions to ensure that the - # output is 32-byte aligned as required for arm-aout. - nop - nop - nop + # Ensure output is 32-byte aligned as required for arm-aout. + .p2align 5 diff --git a/gas/testsuite/gas/arm/thumb2_relax.d b/gas/testsuite/gas/arm/thumb2_relax.d index 327ef42b534..46b68e5502d 100644 --- a/gas/testsuite/gas/arm/thumb2_relax.d +++ b/gas/testsuite/gas/arm/thumb2_relax.d @@ -20,7 +20,7 @@ Disassembly of section .text: 0+02e <[^>]+> f89f 800c ldrb.w r8, \[pc, #12\] ; 0+03c <[^>]+> 0+032 <[^>]+> f89f 100a ldrb.w r1, \[pc, #10\] ; 0+03e <[^>]+> 0+036 <[^>]+> f81f 1038 ldrb.w r1, \[pc, #-56\] ; 0+000 <[^>]+> -0+03a <[^>]+> 46c0 nop \(mov r8, r8\) +0+03a <[^>]+> bf00 nop 0+03c <[^>]+> bf00 nop 0+03e <[^>]+> f995 1000 ldrsb.w r1, \[r5\] 0+042 <[^>]+> f995 1023 ldrsb.w r1, \[r5, #35\] @@ -89,7 +89,7 @@ Disassembly of section .text: 0+126 <[^>]+> f8df 800c ldr.w r8, \[pc, #12\] ; 0+134 <[^>]+> 0+12a <[^>]+> f8df 100a ldr.w r1, \[pc, #10\] ; 0+136 <[^>]+> 0+12e <[^>]+> f85f 1036 ldr.w r1, \[pc, #-54\] ; 0+0fa <[^>]+> -0+132 <[^>]+> 46c0 nop \(mov r8, r8\) +0+132 <[^>]+> bf00 nop 0+134 <[^>]+> bf00 nop 0+136 <[^>]+> 7029 strb r1, \[r5, #0\] 0+138 <[^>]+> f885 1023 strb.w r1, \[r5, #35\] diff --git a/gas/testsuite/gas/arm/thumb32.d b/gas/testsuite/gas/arm/thumb32.d index 1e872413ad8..c508b2129e1 100644 --- a/gas/testsuite/gas/arm/thumb32.d +++ b/gas/testsuite/gas/arm/thumb32.d @@ -277,7 +277,7 @@ Disassembly of section .text: 0[0-9a-f]+ <[^>]+> e002 b\.n 0+358 <[^>]+> 0[0-9a-f]+ <[^>]+> e7d4 b\.n 0+2fe <[^>]+> 0[0-9a-f]+ <[^>]+> e000 b\.n 0+358 <[^>]+> -0[0-9a-f]+ <[^>]+> 46c0 nop \(mov r8, r8\) +0[0-9a-f]+ <[^>]+> bf00 nop 0[0-9a-f]+ <[^>]+> f43f affe beq\.w 0+358 <[^>]+> 0[0-9a-f]+ <[^>]+> f000 8058 beq\.w 0+410 <[^>]+> 0[0-9a-f]+ <[^>]+> f47f affa bne\.w 0+358 <[^>]+>