[ARM] Add support for -sp- FPUs and FPU none to TargetParser

These are added mainly for the benefit of clang, but this also means that they
are now allowed in .fpu directives and we emit the correct .fpu directive when
single-precision-only is used.

Differential Revision: http://reviews.llvm.org/D10238


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@239151 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
John Brawn 2015-06-05 13:31:19 +00:00
parent c1c9bc1df7
commit 272d7fdf42
6 changed files with 39 additions and 9 deletions

View File

@ -32,13 +32,16 @@ namespace ARM {
// FPU names. // FPU names.
enum FPUKind { enum FPUKind {
FK_INVALID = 0, FK_INVALID = 0,
FK_NONE,
FK_VFP, FK_VFP,
FK_VFPV2, FK_VFPV2,
FK_VFPV3, FK_VFPV3,
FK_VFPV3_D16, FK_VFPV3_D16,
FK_VFPV4, FK_VFPV4,
FK_VFPV4_D16, FK_VFPV4_D16,
FK_FPV4_SP_D16,
FK_FPV5_D16, FK_FPV5_D16,
FK_FPV5_SP_D16,
FK_FP_ARMV8, FK_FP_ARMV8,
FK_NEON, FK_NEON,
FK_NEON_VFPV4, FK_NEON_VFPV4,

View File

@ -33,13 +33,16 @@ struct {
ARM::FPURestriction Restriction; ARM::FPURestriction Restriction;
} FPUNames[] = { } FPUNames[] = {
{ "invalid", ARM::FK_INVALID, 0, ARM::NS_None, ARM::FR_None}, { "invalid", ARM::FK_INVALID, 0, ARM::NS_None, ARM::FR_None},
{ "none", ARM::FK_NONE, 0, ARM::NS_None, ARM::FR_None},
{ "vfp", ARM::FK_VFP, 2, ARM::NS_None, ARM::FR_None}, { "vfp", ARM::FK_VFP, 2, ARM::NS_None, ARM::FR_None},
{ "vfpv2", ARM::FK_VFPV2, 2, ARM::NS_None, ARM::FR_None}, { "vfpv2", ARM::FK_VFPV2, 2, ARM::NS_None, ARM::FR_None},
{ "vfpv3", ARM::FK_VFPV3, 3, ARM::NS_None, ARM::FR_None}, { "vfpv3", ARM::FK_VFPV3, 3, ARM::NS_None, ARM::FR_None},
{ "vfpv3-d16", ARM::FK_VFPV3_D16, 3, ARM::NS_None, ARM::FR_D16}, { "vfpv3-d16", ARM::FK_VFPV3_D16, 3, ARM::NS_None, ARM::FR_D16},
{ "vfpv4", ARM::FK_VFPV4, 4, ARM::NS_None, ARM::FR_None}, { "vfpv4", ARM::FK_VFPV4, 4, ARM::NS_None, ARM::FR_None},
{ "vfpv4-d16", ARM::FK_VFPV4_D16, 4, ARM::NS_None, ARM::FR_D16}, { "vfpv4-d16", ARM::FK_VFPV4_D16, 4, ARM::NS_None, ARM::FR_D16},
{ "fpv4-sp-d16", ARM::FK_FPV4_SP_D16, 4, ARM::NS_None, ARM::FR_SP_D16},
{ "fpv5-d16", ARM::FK_FPV5_D16, 5, ARM::NS_None, ARM::FR_D16}, { "fpv5-d16", ARM::FK_FPV5_D16, 5, ARM::NS_None, ARM::FR_D16},
{ "fpv5-sp-d16", ARM::FK_FPV5_SP_D16, 5, ARM::NS_None, ARM::FR_SP_D16},
{ "fp-armv8", ARM::FK_FP_ARMV8, 5, ARM::NS_None, ARM::FR_None}, { "fp-armv8", ARM::FK_FP_ARMV8, 5, ARM::NS_None, ARM::FR_None},
{ "neon", ARM::FK_NEON, 3, ARM::NS_Neon, ARM::FR_None}, { "neon", ARM::FK_NEON, 3, ARM::NS_Neon, ARM::FR_None},
{ "neon-vfpv4", ARM::FK_NEON_VFPV4, 4, ARM::NS_Neon, ARM::FR_None}, { "neon-vfpv4", ARM::FK_NEON_VFPV4, 4, ARM::NS_Neon, ARM::FR_None},
@ -376,10 +379,9 @@ StringRef ARMTargetParser::getFPUSynonym(StringRef FPU) {
.Case("vfp4", "vfpv4") .Case("vfp4", "vfpv4")
.Case("vfp3-d16", "vfpv3-d16") .Case("vfp3-d16", "vfpv3-d16")
.Case("vfp4-d16", "vfpv4-d16") .Case("vfp4-d16", "vfpv4-d16")
// FIXME: sp-16 is NOT the same as d16 .Cases("fp4-sp-d16", "vfpv4-sp-d16", "fpv4-sp-d16")
.Cases("fp4-sp-d16", "fpv4-sp-d16", "vfpv4-d16")
.Cases("fp4-dp-d16", "fpv4-dp-d16", "vfpv4-d16") .Cases("fp4-dp-d16", "fpv4-dp-d16", "vfpv4-d16")
.Cases("fp5-sp-d16", "fpv5-sp-d16", "fpv5-d16") .Case("fp5-sp-d16", "fpv5-sp-d16")
.Cases("fp5-dp-d16", "fpv5-dp-d16", "fpv5-d16") .Cases("fp5-dp-d16", "fpv5-dp-d16", "fpv5-d16")
// FIXME: Clang uses it, but it's bogus, since neon defaults to vfpv3. // FIXME: Clang uses it, but it's bogus, since neon defaults to vfpv3.
.Case("neon-vfpv3", "neon") .Case("neon-vfpv3", "neon")

View File

@ -640,9 +640,13 @@ void ARMAsmPrinter::emitAttributes() {
if (STI.hasFPARMv8()) if (STI.hasFPARMv8())
// FPv5 and FP-ARMv8 have the same instructions, so are modeled as one // FPv5 and FP-ARMv8 have the same instructions, so are modeled as one
// FPU, but there are two different names for it depending on the CPU. // FPU, but there are two different names for it depending on the CPU.
ATS.emitFPU(STI.hasD16() ? ARM::FK_FPV5_D16 : ARM::FK_FP_ARMV8); ATS.emitFPU(STI.hasD16()
? (STI.isFPOnlySP() ? ARM::FK_FPV5_SP_D16 : ARM::FK_FPV5_D16)
: ARM::FK_FP_ARMV8);
else if (STI.hasVFP4()) else if (STI.hasVFP4())
ATS.emitFPU(STI.hasD16() ? ARM::FK_VFPV4_D16 : ARM::FK_VFPV4); ATS.emitFPU(STI.hasD16()
? (STI.isFPOnlySP() ? ARM::FK_FPV4_SP_D16 : ARM::FK_VFPV4_D16)
: ARM::FK_VFPV4);
else if (STI.hasVFP3()) else if (STI.hasVFP3())
ATS.emitFPU(STI.hasD16() ? ARM::FK_VFPV3_D16 : ARM::FK_VFPV3); ATS.emitFPU(STI.hasD16() ? ARM::FK_VFPV3_D16 : ARM::FK_VFPV3);
else if (STI.hasVFP2()) else if (STI.hasVFP2())

View File

@ -810,6 +810,9 @@ void ARMTargetELFStreamer::emitFPUDefaultAttributes() {
/* OverwriteExisting= */ false); /* OverwriteExisting= */ false);
break; break;
// ABI_HardFP_use is handled in ARMAsmPrinter, so _SP_D16 is treated the same
// as _D16 here.
case ARM::FK_FPV4_SP_D16:
case ARM::FK_VFPV4_D16: case ARM::FK_VFPV4_D16:
setAttributeItem(ARMBuildAttrs::FP_arch, setAttributeItem(ARMBuildAttrs::FP_arch,
ARMBuildAttrs::AllowFPv4B, ARMBuildAttrs::AllowFPv4B,
@ -824,6 +827,7 @@ void ARMTargetELFStreamer::emitFPUDefaultAttributes() {
// FPV5_D16 is identical to FP_ARMV8 except for the number of D registers, so // FPV5_D16 is identical to FP_ARMV8 except for the number of D registers, so
// uses the FP_ARMV8_D16 build attribute. // uses the FP_ARMV8_D16 build attribute.
case ARM::FK_FPV5_SP_D16:
case ARM::FK_FPV5_D16: case ARM::FK_FPV5_D16:
setAttributeItem(ARMBuildAttrs::FP_arch, setAttributeItem(ARMBuildAttrs::FP_arch,
ARMBuildAttrs::AllowFPARMv8B, ARMBuildAttrs::AllowFPARMv8B,
@ -858,6 +862,7 @@ void ARMTargetELFStreamer::emitFPUDefaultAttributes() {
break; break;
case ARM::FK_SOFTVFP: case ARM::FK_SOFTVFP:
case ARM::FK_NONE:
break; break;
default: default:

View File

@ -923,7 +923,7 @@
; CORTEX-M4-SOFT: .eabi_attribute 7, 77 ; CORTEX-M4-SOFT: .eabi_attribute 7, 77
; CORTEX-M4-SOFT: .eabi_attribute 8, 0 ; CORTEX-M4-SOFT: .eabi_attribute 8, 0
; CORTEX-M4-SOFT: .eabi_attribute 9, 2 ; CORTEX-M4-SOFT: .eabi_attribute 9, 2
; CORTEX-M4-SOFT: .fpu vfpv4-d16 ; CORTEX-M4-SOFT: .fpu fpv4-sp-d16
; CORTEX-M4-SOFT-NOT: .eabi_attribute 19 ; CORTEX-M4-SOFT-NOT: .eabi_attribute 19
;; We default to IEEE 754 compliance ;; We default to IEEE 754 compliance
; CORTEX-M4-SOFT: .eabi_attribute 20, 1 ; CORTEX-M4-SOFT: .eabi_attribute 20, 1
@ -953,7 +953,7 @@
; CORTEX-M4-HARD: .eabi_attribute 7, 77 ; CORTEX-M4-HARD: .eabi_attribute 7, 77
; CORTEX-M4-HARD: .eabi_attribute 8, 0 ; CORTEX-M4-HARD: .eabi_attribute 8, 0
; CORTEX-M4-HARD: .eabi_attribute 9, 2 ; CORTEX-M4-HARD: .eabi_attribute 9, 2
; CORTEX-M4-HARD: .fpu vfpv4-d16 ; CORTEX-M4-HARD: .fpu fpv4-sp-d16
; CORTEX-M4-HARD-NOT: .eabi_attribute 19 ; CORTEX-M4-HARD-NOT: .eabi_attribute 19
;; We default to IEEE 754 compliance ;; We default to IEEE 754 compliance
; CORTEX-M4-HARD: .eabi_attribute 20, 1 ; CORTEX-M4-HARD: .eabi_attribute 20, 1
@ -984,7 +984,7 @@
; CORTEX-M7: .eabi_attribute 8, 0 ; CORTEX-M7: .eabi_attribute 8, 0
; CORTEX-M7: .eabi_attribute 9, 2 ; CORTEX-M7: .eabi_attribute 9, 2
; CORTEX-M7-SOFT-NOT: .fpu ; CORTEX-M7-SOFT-NOT: .fpu
; CORTEX-M7-SINGLE: .fpu fpv5-d16 ; CORTEX-M7-SINGLE: .fpu fpv5-sp-d16
; CORTEX-M7-DOUBLE: .fpu fpv5-d16 ; CORTEX-M7-DOUBLE: .fpu fpv5-d16
; CORTEX-M7: .eabi_attribute 17, 1 ; CORTEX-M7: .eabi_attribute 17, 1
; CORTEX-M7-NOT: .eabi_attribute 19 ; CORTEX-M7-NOT: .eabi_attribute 19

View File

@ -1,12 +1,28 @@
@ Check multiple .fpu directives. @ Check multiple .fpu directives.
@ The later .fpu directive should overwrite the earlier one. @ The later .fpu directive should overwrite the earlier one.
@ See also: directive-fpu-multiple2.s. @ We also check here that all the .fpu directives that we expect to work do work
@ RUN: llvm-mc -triple arm-eabi -filetype obj %s | llvm-readobj -arm-attributes \ @ RUN: llvm-mc -triple arm-eabi -filetype obj %s | llvm-readobj -arm-attributes \
@ RUN: | FileCheck %s -check-prefix CHECK-ATTR @ RUN: | FileCheck %s -check-prefix CHECK-ATTR
.fpu none
.fpu vfp
.fpu vfpv2
.fpu vfpv3
.fpu vfpv3-d16
.fpu vfpv4
.fpu vfpv4-d16
.fpu fpv4-sp-d16
.fpu fpv5-d16
.fpu fpv5-sp-d16
.fpu fp-armv8
.fpu neon .fpu neon
.fpu neon-vfpv4
.fpu neon-fp-armv8
.fpu crypto-neon-fp-armv8
.fpu softvfp
.fpu vfpv4 .fpu vfpv4
@ CHECK-ATTR: FileAttributes { @ CHECK-ATTR: FileAttributes {