This is the mail archive of the
binutils@sourceware.org
mailing list for the binutils project.
[PATCH, ARM]: Fix diagnostics & disallow ARM instructions on V7M cores
- From: Julian Brown <julian at codesourcery dot com>
- To: binutils at sources dot redhat dot com
- Cc: Paul Brook <paul at codesourcery dot com>, Richard Earnshaw <Richard dot Earnshaw at arm dot com>, Julian Brown <julian at codesourcery dot com>
- Date: Thu, 11 May 2006 22:23:41 +0100
- Subject: [PATCH, ARM]: Fix diagnostics & disallow ARM instructions on V7M cores
Hi,
This patch fixes the case where the diagnostic on attempting to assemble
files containing ARM instructions on processors which don't support them
isn't very helpful (e.g. "instruction not supported -- `nop'"). Thumb
mode is made the default on such cores, and attempts to use the ".arm"
directive or ARM instructions is faulted.
Tested with "make check" with cross to arm-none-eabi, with a small test
case added.
OK to apply on mainline? CSL branch?
Cheers,
Julian
ChangeLog (gas):
* config/tc-arm.c (arm_thumb_only, arm_thumb_only_except): Add
static vars.
(md_assemble): Disable ARM instructions on non-ARM-supporting cores.
(autoselect_thumb_from_cpu_variant): New function. Switch on Thumb
mode automatically based on cpu variant.
(md_begin): Call above function.
(s_arm_cpu, s_arm_arch): Likewise.
ChangeLog (gas/testsuite):
* gas/arm/noarm.s: Add test for disabled ARM insns.
* gas/arm/noarm.d: Drive test for above.
* gas/arm/noarm.l: Expected error output.
ChangeLog (include/opcode):
* arm.h (THUMB_ONLY): New macro. Architectures which support only
Thumb instructions.
(THUMB_ONLY_EXCEPT): Bits set here negate the above cases.
Index: gas/config/tc-arm.c
===================================================================
RCS file: /cvs/src/src/gas/config/tc-arm.c,v
retrieving revision 1.250.2.15
diff -c -p -r1.250.2.15 tc-arm.c
*** gas/config/tc-arm.c 5 May 2006 18:31:28 -0000 1.250.2.15
--- gas/config/tc-arm.c 11 May 2006 21:13:09 -0000
*************** static const arm_feature_set fpu_neon_ex
*** 215,220 ****
--- 215,224 ----
static const arm_feature_set fpu_vfp_v3_or_neon_ext =
ARM_FEATURE (0, FPU_NEON_EXT_V1 | FPU_VFP_EXT_V3);
+ static const arm_feature_set arm_thumb_only = ARM_FEATURE (THUMB_ONLY, 0);
+ static const arm_feature_set arm_thumb_only_except =
+ ARM_FEATURE (THUMB_ONLY_EXCEPT, 0);
+
static int mfloat_abi_opt = -1;
/* Record user cpu selection for object attributes. */
static arm_feature_set selected_cpu = ARM_ARCH_NONE;
*************** md_assemble (char *str)
*** 13484,13490 ****
ARM_MERGE_FEATURE_SETS (thumb_arch_used, thumb_arch_used,
arm_ext_v6t2);
}
! else
{
/* Check that this instruction is supported for this CPU. */
if (!opcode->avariant ||
--- 13488,13495 ----
ARM_MERGE_FEATURE_SETS (thumb_arch_used, thumb_arch_used,
arm_ext_v6t2);
}
! else if (!ARM_CPU_HAS_FEATURE (cpu_variant, arm_thumb_only)
! || ARM_CPU_HAS_FEATURE (cpu_variant, arm_thumb_only_except))
{
/* Check that this instruction is supported for this CPU. */
if (!opcode->avariant ||
*************** md_assemble (char *str)
*** 13517,13522 ****
--- 13522,13532 ----
ARM_MERGE_FEATURE_SETS (arm_arch_used, arm_arch_used,
*opcode->avariant);
}
+ else
+ {
+ as_bad (_("attempt to use ARM instruction on Thumb-only core `%s'"), str);
+ return;
+ }
output_inst (str);
}
*************** set_constant_flonums (void)
*** 18296,18301 ****
--- 18306,18322 ----
abort ();
}
+ /* Auto-select Thumb mode if it's the only available instruction set for the
+ given architecture. */
+
+ static void
+ autoselect_thumb_from_cpu_variant (void)
+ {
+ if (ARM_CPU_HAS_FEATURE (cpu_variant, arm_thumb_only)
+ && !ARM_CPU_HAS_FEATURE (cpu_variant, arm_thumb_only_except))
+ opcode_select (16);
+ }
+
void
md_begin (void)
{
*************** md_begin (void)
*** 18396,18401 ****
--- 18417,18424 ----
ARM_MERGE_FEATURE_SETS (cpu_variant, *mcpu_cpu_opt, *mfpu_opt);
+ autoselect_thumb_from_cpu_variant ();
+
arm_arch_used = thumb_arch_used = arm_arch_none;
#if defined OBJ_COFF || defined OBJ_ELF
*************** s_arm_cpu (int ignored ATTRIBUTE_UNUSED)
*** 19457,19462 ****
--- 19480,19486 ----
selected_cpu_name[i] = 0;
}
ARM_MERGE_FEATURE_SETS (cpu_variant, *mcpu_cpu_opt, *mfpu_opt);
+ autoselect_thumb_from_cpu_variant ();
*input_line_pointer = saved_char;
demand_empty_rest_of_line ();
return;
*************** s_arm_arch (int ignored ATTRIBUTE_UNUSED
*** 19490,19495 ****
--- 19514,19520 ----
selected_cpu = opt->value;
strcpy(selected_cpu_name, opt->name);
ARM_MERGE_FEATURE_SETS (cpu_variant, *mcpu_cpu_opt, *mfpu_opt);
+ autoselect_thumb_from_cpu_variant ();
*input_line_pointer = saved_char;
demand_empty_rest_of_line ();
return;
Index: gas/testsuite/gas/arm/noarm.d
===================================================================
RCS file: gas/testsuite/gas/arm/noarm.d
diff -N gas/testsuite/gas/arm/noarm.d
*** /dev/null 1 Jan 1970 00:00:00 -0000
--- gas/testsuite/gas/arm/noarm.d 11 May 2006 21:13:09 -0000
***************
*** 0 ****
--- 1,3 ----
+ # name: Disallow ARM instructions on V7M
+ # as:
+ # error-output: noarm.l
Index: gas/testsuite/gas/arm/noarm.l
===================================================================
RCS file: gas/testsuite/gas/arm/noarm.l
diff -N gas/testsuite/gas/arm/noarm.l
*** /dev/null 1 Jan 1970 00:00:00 -0000
--- gas/testsuite/gas/arm/noarm.l 11 May 2006 21:13:09 -0000
***************
*** 0 ****
--- 1,3 ----
+ [^:]*: Assembler messages:
+ [^:]*:11: Error: selected processor does not support ARM opcodes
+ [^:]*:12: Error: attempt to use ARM instruction on Thumb-only core `nop'
Index: gas/testsuite/gas/arm/noarm.s
===================================================================
RCS file: gas/testsuite/gas/arm/noarm.s
diff -N gas/testsuite/gas/arm/noarm.s
*** /dev/null 1 Jan 1970 00:00:00 -0000
--- gas/testsuite/gas/arm/noarm.s 11 May 2006 21:13:09 -0000
***************
*** 0 ****
--- 1,12 ----
+ .arch armv7a
+ .syntax unified
+ .text
+ func:
+ nop
+ movw r0, #0
+
+ .arch armv7
+ nop
+ movw r0, #0
+ .arm
+ nop
Index: include/opcode/arm.h
===================================================================
RCS file: /cvs/src/src/include/opcode/arm.h,v
retrieving revision 1.9.2.1
diff -c -p -r1.9.2.1 arm.h
*** include/opcode/arm.h 3 Apr 2006 00:03:34 -0000 1.9.2.1
--- include/opcode/arm.h 11 May 2006 21:13:10 -0000
***************
*** 45,50 ****
--- 45,55 ----
#define ARM_EXT_V7R 0x00200000 /* Arm V7R. */
#define ARM_EXT_V7M 0x00400000 /* Arm V7M. */
+ /* A bitmask of architecture versions which support only Thumb instructions,
+ and exceptions containing bits which nullify that situation. */
+ #define THUMB_ONLY (ARM_EXT_V7 | ARM_EXT_V7M)
+ #define THUMB_ONLY_EXCEPT (ARM_EXT_V7A | ARM_EXT_V7R)
+
/* Co-processor space extensions. */
#define ARM_CEXT_XSCALE 0x00000001 /* Allow MIA etc. */
#define ARM_CEXT_MAVERICK 0x00000002 /* Use Cirrus/DSP coprocessor. */