llvm.org GIT mirror llvm / afefcdb
[ARM] add target arch definitions for 8.1-M and MVE This adds: - LLVM subtarget features to make all the new instructions conditional on, - CPU and FPU names for use on clang's command line, with default FPUs set so that "armv8.1-m.main+fp" and "armv8.1-m.main+fp.dp" will select the right FPU features, - architecture extension names "mve" and "mve.fp", - ABI build attribute support for v8.1-M (a new value for Tag_CPU_arch) and MVE (a new actual tag). Patch mostly by Simon Tatham. Differential Revision: https://reviews.llvm.org/D60698 git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@362090 91177308-0d34-0410-b5e6-96231b3b80d8 Sjoerd Meijer 2 months ago
17 changed file(s) with 154 addition(s) and 8 deletion(s). Raw diff Collapse all Expand all
108108 ARMSubArch_v8r,
109109 ARMSubArch_v8m_baseline,
110110 ARMSubArch_v8m_mainline,
111 ARMSubArch_v8_1m_mainline,
111112 ARMSubArch_v7,
112113 ARMSubArch_v7em,
113114 ARMSubArch_v7m,
5252 uint32_t &Offset);
5353 void Advanced_SIMD_arch(ARMBuildAttrs::AttrType Tag, const uint8_t *Data,
5454 uint32_t &Offset);
55 void MVE_arch(ARMBuildAttrs::AttrType Tag, const uint8_t *Data,
56 uint32_t &Offset);
5557 void PCS_config(ARMBuildAttrs::AttrType Tag, const uint8_t *Data,
5658 uint32_t &Offset);
5759 void ABI_PCS_R9_use(ARMBuildAttrs::AttrType Tag, const uint8_t *Data,
6666 MPextension_use = 42, // recoded from 70 (ABI r2.08)
6767 DIV_use = 44,
6868 DSP_extension = 46,
69 MVE_arch = 48,
6970 also_compatible_with = 65,
7071 conformance = 67,
7172 Virtualization_use = 68,
109110 v8_R = 15, // e.g. Cortex R52
110111 v8_M_Base= 16, // v8_M_Base AArch32
111112 v8_M_Main= 17, // v8_M_Main AArch32
113 v8_1_M_Main=21, // v8_1_M_Main AArch32
112114 };
113115
114116 enum CPUArchProfile { // (=7), uleb128
150152 AllowNeonARMv8 = 3, // ARM v8-A SIMD was permitted
151153 AllowNeonARMv8_1a = 4,// ARM v8.1-A SIMD was permitted (RDMA)
152154
155 // Tag_MVE_arch, (=48), uleb128
156 AllowMVEInteger = 1, // integer-only MVE was permitted
157 AllowMVEIntegerAndFloat = 2, // both integer and floating point MVE were permitted
158
153159 // Tag_ABI_PCS_R9_use, (=14), uleb128
154160 R9IsGPR = 0, // R9 used as v6 (just another callee-saved register)
155161 R9IsSB = 1, // R9 used as a global static base rgister
3030 ARM_FPU("fpv5-d16", FK_FPV5_D16, FPUVersion::VFPV5, NeonSupportLevel::None, FPURestriction::D16)
3131 ARM_FPU("fpv5-sp-d16", FK_FPV5_SP_D16, FPUVersion::VFPV5, NeonSupportLevel::None, FPURestriction::SP_D16)
3232 ARM_FPU("fp-armv8", FK_FP_ARMV8, FPUVersion::VFPV5, NeonSupportLevel::None, FPURestriction::None)
33 ARM_FPU("fp-armv8-fullfp16-d16", FK_FP_ARMV8_FULLFP16_D16, FPUVersion::VFPV5_FULLFP16, NeonSupportLevel::None, FPURestriction::D16)
34 ARM_FPU("fp-armv8-fullfp16-sp-d16", FK_FP_ARMV8_FULLFP16_SP_D16, FPUVersion::VFPV5_FULLFP16, NeonSupportLevel::None, FPURestriction::SP_D16)
3335 ARM_FPU("neon", FK_NEON, FPUVersion::VFPV3, NeonSupportLevel::Neon, FPURestriction::None)
3436 ARM_FPU("neon-fp16", FK_NEON_FP16, FPUVersion::VFPV3_FP16, NeonSupportLevel::Neon, FPURestriction::None)
3537 ARM_FPU("neon-vfpv4", FK_NEON_VFPV4, FPUVersion::VFPV4, NeonSupportLevel::Neon, FPURestriction::None)
117119 ARMBuildAttrs::CPUArch::v8_M_Base, FK_NONE, ARM::AEK_HWDIVTHUMB)
118120 ARM_ARCH("armv8-m.main", ARMV8MMainline, "8-M.Mainline", "v8m.main",
119121 ARMBuildAttrs::CPUArch::v8_M_Main, FK_FPV5_D16, ARM::AEK_HWDIVTHUMB)
122 ARM_ARCH("armv8.1-m.main", ARMV8_1MMainline, "8.1-M.Mainline", "v8.1m.main",
123 ARMBuildAttrs::CPUArch::v8_1_M_Main, FK_FP_ARMV8_FULLFP16_SP_D16, ARM::AEK_HWDIVTHUMB | ARM::AEK_RAS)
120124 // Non-standard Arch names.
121125 ARM_ARCH("iwmmxt", IWMMXT, "iwmmxt", "", ARMBuildAttrs::CPUArch::v5TE,
122126 FK_NONE, ARM::AEK_NONE)
143147 ARM_ARCH_EXT_NAME("dotprod", ARM::AEK_DOTPROD, "+dotprod","-dotprod")
144148 ARM_ARCH_EXT_NAME("dsp", ARM::AEK_DSP, "+dsp", "-dsp")
145149 ARM_ARCH_EXT_NAME("fp", ARM::AEK_FP, nullptr, nullptr)
150 ARM_ARCH_EXT_NAME("mve", ARM::AEK_SIMD, "+mve", "-mve")
151 ARM_ARCH_EXT_NAME("mve.fp", (ARM::AEK_SIMD | ARM::AEK_FP), "+mve.fp", "-mve.fp")
146152 ARM_ARCH_EXT_NAME("idiv", (ARM::AEK_HWDIVARM | ARM::AEK_HWDIVTHUMB), nullptr, nullptr)
147153 ARM_ARCH_EXT_NAME("mp", ARM::AEK_MP, nullptr, nullptr)
148154 ARM_ARCH_EXT_NAME("simd", ARM::AEK_SIMD, nullptr, nullptr)
4949 AEK_SVE2SM4 = 1 << 21,
5050 AEK_SVE2SHA3 = 1 << 22,
5151 AEK_BITPERM = 1 << 23,
52 AEK_FP_DP = 1 << 24,
5253 // Unsupported extensions.
5354 AEK_OS = 0x8000000,
5455 AEK_IWMMXT = 0x10000000,
130131 VFPV3,
131132 VFPV3_FP16,
132133 VFPV4,
133 VFPV5
134 VFPV5,
135 VFPV5_FULLFP16,
134136 };
135137
136138 // An FPU name restricts the FPU in one of three ways:
229229 }
230230 }
231231
232 if (Attributes.hasAttribute(ARMBuildAttrs::MVE_arch)) {
233 switch(Attributes.getAttributeValue(ARMBuildAttrs::MVE_arch)) {
234 default:
235 break;
236 case ARMBuildAttrs::Not_Allowed:
237 Features.AddFeature("mve", false);
238 Features.AddFeature("mve.fp", false);
239 break;
240 case ARMBuildAttrs::AllowMVEInteger:
241 Features.AddFeature("mve.fp", false);
242 Features.AddFeature("mve");
243 break;
244 case ARMBuildAttrs::AllowMVEIntegerAndFloat:
245 Features.AddFeature("mve.fp");
246 break;
247 }
248 }
249
232250 if (Attributes.hasAttribute(ARMBuildAttrs::DIV_use)) {
233251 switch(Attributes.getAttributeValue(ARMBuildAttrs::DIV_use)) {
234252 default:
3636 ATTRIBUTE_HANDLER(FP_arch),
3737 ATTRIBUTE_HANDLER(WMMX_arch),
3838 ATTRIBUTE_HANDLER(Advanced_SIMD_arch),
39 ATTRIBUTE_HANDLER(MVE_arch),
3940 ATTRIBUTE_HANDLER(PCS_config),
4041 ATTRIBUTE_HANDLER(ABI_PCS_R9_use),
4142 ATTRIBUTE_HANDLER(ABI_PCS_RW_data),
131132 static const char *const Strings[] = {
132133 "Pre-v4", "ARM v4", "ARM v4T", "ARM v5T", "ARM v5TE", "ARM v5TEJ", "ARM v6",
133134 "ARM v6KZ", "ARM v6T2", "ARM v6K", "ARM v7", "ARM v6-M", "ARM v6S-M",
134 "ARM v7E-M", "ARM v8"
135 "ARM v7E-M", "ARM v8", nullptr,
136 "ARM v8-M Baseline", "ARM v8-M Mainline", nullptr, nullptr, nullptr,
137 "ARM v8.1-M Mainline"
135138 };
136139
137140 uint64_t Value = ParseInteger(Data, Offset);
204207 uint32_t &Offset) {
205208 static const char *const Strings[] = {
206209 "Not Permitted", "NEONv1", "NEONv2+FMA", "ARMv8-a NEON", "ARMv8.1-a NEON"
210 };
211
212 uint64_t Value = ParseInteger(Data, Offset);
213 StringRef ValueDesc =
214 (Value < array_lengthof(Strings)) ? Strings[Value] : nullptr;
215 PrintAttribute(Tag, Value, ValueDesc);
216 }
217
218 void ARMAttributeParser::MVE_arch(AttrType Tag, const uint8_t *Data,
219 uint32_t &Offset) {
220 static const char *const Strings[] = {
221 "Not Permitted", "MVE integer", "MVE integer and float"
207222 };
208223
209224 uint64_t Value = ParseInteger(Data, Offset);
2727 { ARMBuildAttrs::FP_arch, "Tag_FP_arch" },
2828 { ARMBuildAttrs::WMMX_arch, "Tag_WMMX_arch" },
2929 { ARMBuildAttrs::Advanced_SIMD_arch, "Tag_Advanced_SIMD_arch" },
30 { ARMBuildAttrs::MVE_arch, "Tag_MVE_arch" },
3031 { ARMBuildAttrs::PCS_config, "Tag_PCS_config" },
3132 { ARMBuildAttrs::ABI_PCS_R9_use, "Tag_ABI_PCS_R9_use" },
3233 { ARMBuildAttrs::ABI_PCS_RW_data, "Tag_ABI_PCS_RW_data" },
7676 case ArchKind::ARMV8R:
7777 case ArchKind::ARMV8MBaseline:
7878 case ArchKind::ARMV8MMainline:
79 case ArchKind::ARMV8_1MMainline:
7980 return 8;
8081 case ArchKind::INVALID:
8182 return 0;
9293 case ArchKind::ARMV7EM:
9394 case ArchKind::ARMV8MMainline:
9495 case ArchKind::ARMV8MBaseline:
96 case ArchKind::ARMV8_1MMainline:
9597 return ProfileKind::M;
9698 case ArchKind::ARMV7R:
9799 case ArchKind::ARMV8R:
150152 .Case("v8r", "v8-r")
151153 .Case("v8m.base", "v8-m.base")
152154 .Case("v8m.main", "v8-m.main")
155 .Case("v8.1m.main", "v8.1-m.main")
153156 .Default(Arch);
154157 }
155158
163166 // higher. We also have to make sure to disable fp16 when vfp4 is disabled,
164167 // as +vfp4 implies +fp16 but -vfp4 does not imply -fp16.
165168 switch (FPUNames[FPUKind].FPUVer) {
169 case FPUVersion::VFPV5_FULLFP16:
170 Features.push_back("+fp-armv8");
171 Features.push_back("+fullfp16");
172 break;
166173 case FPUVersion::VFPV5:
167174 Features.push_back("+fp-armv8");
168175 break;
624624 return Triple::ARMSubArch_v8m_baseline;
625625 case ARM::ArchKind::ARMV8MMainline:
626626 return Triple::ARMSubArch_v8m_mainline;
627 case ARM::ArchKind::ARMV8_1MMainline:
628 return Triple::ARMSubArch_v8_1m_mainline;
627629 default:
628630 return Triple::NoSubArch;
629631 }
496496 def HasV8_5aOps : SubtargetFeature<"v8.5a", "HasV8_5aOps", "true",
497497 "Support ARM v8.5a instructions",
498498 [HasV8_4aOps, FeatureSB]>;
499
500 def HasV8_1MMainlineOps : SubtargetFeature<
501 "v8.1m.main", "HasV8_1MMainlineOps", "true",
502 "Support ARM v8-1M Mainline instructions",
503 [HasV8MMainlineOps]>;
504 def HasMVEIntegerOps : SubtargetFeature<
505 "mve", "HasMVEIntegerOps", "true",
506 "Support M-Class Vector Extension with integer ops",
507 [HasV8_1MMainlineOps, FeatureDSP, FeatureFPRegs16, FeatureFPRegs64]>;
508 def HasMVEFloatOps : SubtargetFeature<
509 "mve.fp", "HasMVEFloatOps", "true",
510 "Support M-Class Vector Extension with integer and floating ops",
511 [HasMVEIntegerOps, FeatureFPARMv8_D16_SP, FeatureFullFP16]>;
499512
500513 //===----------------------------------------------------------------------===//
501514 // ARM Processor subtarget features.
782795 FeatureAcquireRelease,
783796 FeatureMClass]>;
784797
798 def ARMv81mMainline : Architecture<"armv8.1-m.main", "ARMv81mMainline",
799 [HasV8_1MMainlineOps,
800 FeatureNoARM,
801 ModeThumb,
802 FeatureDB,
803 FeatureHWDivThumb,
804 Feature8MSecExt,
805 FeatureAcquireRelease,
806 FeatureMClass,
807 FeatureRAS]>;
808
785809 // Aliases
786810 def IWMMXT : Architecture<"iwmmxt", "ARMv5te", [ARMv5te]>;
787811 def IWMMXT2 : Architecture<"iwmmxt2", "ARMv5te", [ARMv5te]>;
2525 def HasV8MMainline : Predicate<"Subtarget->hasV8MMainlineOps()">,
2626 AssemblerPredicate<"HasV8MMainlineOps",
2727 "armv8m.main">;
28 def HasV8_1MMainline : Predicate<"Subtarget->hasV8_1MMainlineOps()">,
29 AssemblerPredicate<"HasV8_1MMainlineOps",
30 "armv8.1m.main">;
31 def HasMVEInt : Predicate<"Subtarget->hasMVEIntegerOps()">,
32 AssemblerPredicate<"HasMVEIntegerOps",
33 "mve">;
34 def HasMVEFloat : Predicate<"Subtarget->hasMVEFloatOps()">,
35 AssemblerPredicate<"HasMVEFloatOps",
36 "mve.fp">;
2837 def HasFPRegs : Predicate<"Subtarget->hasFPRegs()">,
2938 AssemblerPredicate<"FeatureFPRegs",
3039 "fp registers">;
3443 def HasFPRegs64 : Predicate<"Subtarget->hasFPRegs64()">,
3544 AssemblerPredicate<"FeatureFPRegs64",
3645 "64-bit fp registers">;
46 def HasFPRegsV8_1M : Predicate<"Subtarget->hasFPRegs() && Subtarget->hasV8_1MMainlineOps()">,
47 AssemblerPredicate<"FeatureFPRegs,HasV8_1MMainlineOps",
48 "armv8.1m.main with FP or MVE">;
3749 def HasV6T2 : Predicate<"Subtarget->hasV6T2Ops()">,
3850 AssemblerPredicate<"HasV6T2Ops", "armv6t2">;
3951 def NoV6T2 : Predicate<"!Subtarget->hasV6T2Ops()">;
109109 ARMv8a,
110110 ARMv8mBaseline,
111111 ARMv8mMainline,
112 ARMv8r
112 ARMv8r,
113 ARMv81mMainline,
113114 };
114115
115116 public:
156157 bool HasV8_5aOps = false;
157158 bool HasV8MBaselineOps = false;
158159 bool HasV8MMainlineOps = false;
160 bool HasV8_1MMainlineOps = false;
161 bool HasMVEIntegerOps = false;
162 bool HasMVEFloatOps = false;
159163
160164 /// HasVFPv2, HasVFPv3, HasVFPv4, HasFPARMv8, HasNEON - Specify what
161165 /// floating point ISAs are supported.
568572 bool hasV8_5aOps() const { return HasV8_5aOps; }
569573 bool hasV8MBaselineOps() const { return HasV8MBaselineOps; }
570574 bool hasV8MMainlineOps() const { return HasV8MMainlineOps; }
575 bool hasV8_1MMainlineOps() const { return HasV8_1MMainlineOps; }
576 bool hasMVEIntegerOps() const { return HasMVEIntegerOps; }
577 bool hasMVEFloatOps() const { return HasMVEFloatOps; }
571578 bool hasFPRegs() const { return HasFPRegs; }
572579 bool hasFPRegs16() const { return HasFPRegs16; }
573580 bool hasFPRegs64() const { return HasFPRegs64; }
123123 if (STI.hasFeature(ARM::FeatureRClass))
124124 return ARMBuildAttrs::v8_R;
125125 return ARMBuildAttrs::v8_A;
126 } else if (STI.hasFeature(ARM::HasV8MMainlineOps))
126 } else if (STI.hasFeature(ARM::HasV8_1MMainlineOps))
127 return ARMBuildAttrs::v8_1_M_Main;
128 else if (STI.hasFeature(ARM::HasV8MMainlineOps))
127129 return ARMBuildAttrs::v8_M_Main;
128130 else if (STI.hasFeature(ARM::HasV7Ops)) {
129131 if (STI.hasFeature(ARM::FeatureMClass) && STI.hasFeature(ARM::FeatureDSP))
261263 if (STI.hasFeature(ARM::FeatureMP))
262264 emitAttribute(ARMBuildAttrs::MPextension_use, ARMBuildAttrs::AllowMP);
263265
266 if (STI.hasFeature(ARM::HasMVEFloatOps))
267 emitAttribute(ARMBuildAttrs::MVE_arch, ARMBuildAttrs::AllowMVEIntegerAndFloat);
268 else if (STI.hasFeature(ARM::HasMVEIntegerOps))
269 emitAttribute(ARMBuildAttrs::MVE_arch, ARMBuildAttrs::AllowMVEInteger);
270
264271 // Hardware divide in ARM mode is part of base arch, starting from ARMv8.
265272 // If only Thumb hwdiv is present, it must also be in base arch (ARMv7-R/M).
266273 // It is not possible to produce DisallowDIV: if hwdiv is present in the base
239239 ; RUN: llc < %s -mtriple=thumbv8-none-none-eabi -mcpu=cortex-m33 -mattr=+strict-align | FileCheck %s --check-prefix=STRICT-ALIGN
240240 ; RUN: llc < %s -mtriple=thumbv8-none-none-eabi -mcpu=cortex-m35p | FileCheck %s --check-prefix=NO-STRICT-ALIGN
241241 ; RUN: llc < %s -mtriple=thumbv8-none-none-eabi -mcpu=cortex-m35p -mattr=+strict-align | FileCheck %s --check-prefix=STRICT-ALIGN
242 ; RUN: llc < %s -mtriple=thumbv8.1m.main-none-none-eabi | FileCheck %s --check-prefix=ARMv81M-MAIN
243 ; RUN: llc < %s -mtriple=thumbv8.1m.main-none-none-eabi -mattr=+mve | FileCheck %s --check-prefix=ARMv81M-MAIN-MVEINT
244 ; RUN: llc < %s -mtriple=thumbv8.1m.main-none-none-eabi -mattr=+mve.fp | FileCheck %s --check-prefix=ARMv81M-MAIN-MVEFP
242245
243246 ; CPU-SUPPORTED-NOT: is not a recognized processor for this target
244247
17681771 ; ARMv8R: .eabi_attribute 38, 1 @ Tag_ABI_FP_16bit_format
17691772 ; ARMv8R: .eabi_attribute 14, 0 @ Tag_ABI_PCS_R9_use
17701773
1774 ; ARMv81M-MAIN: .eabi_attribute 6, 21 @ Tag_CPU_arch
1775 ; ARMv81M-MAIN-NOT: .eabi_attribute 48
1776 ; ARMv81M-MAIN-MVEINT: .eabi_attribute 6, 21 @ Tag_CPU_arch
1777 ; ARMv81M-MAIN-MVEINT: .eabi_attribute 48, 1 @ Tag_MVE_arch
1778 ; ARMv81M-MAIN-MVEFP: .eabi_attribute 6, 21 @ Tag_CPU_arch
1779 ; ARMv81M-MAIN-MVEFP: .eabi_attribute 48, 2 @ Tag_MVE_arch
17711780 define i32 @f(i64 %z) {
17721781 ret i32 0
17731782 }
7474 ARMBuildAttrs::v6S_M));
7575 EXPECT_TRUE(testBuildAttr(6, 13, ARMBuildAttrs::CPU_arch,
7676 ARMBuildAttrs::v7E_M));
77 EXPECT_TRUE(testBuildAttr(6, 14, ARMBuildAttrs::CPU_arch,
78 ARMBuildAttrs::v8_A));
79 EXPECT_TRUE(testBuildAttr(6, 15, ARMBuildAttrs::CPU_arch,
80 ARMBuildAttrs::v8_R));
81 EXPECT_TRUE(testBuildAttr(6, 16, ARMBuildAttrs::CPU_arch,
82 ARMBuildAttrs::v8_M_Base));
83 EXPECT_TRUE(testBuildAttr(6, 17, ARMBuildAttrs::CPU_arch,
84 ARMBuildAttrs::v8_M_Main));
85 EXPECT_TRUE(testBuildAttr(6, 21, ARMBuildAttrs::CPU_arch,
86 ARMBuildAttrs::v8_1_M_Main));
7787 }
7888
7989 TEST(CPUArchProfileBuildAttr, testBuildAttr) {
158168 ARMBuildAttrs::AllowHPFP));
159169 }
160170
171 TEST(MVEBuildAttr, testBuildAttr) {
172 EXPECT_TRUE(testTagString(48, "Tag_MVE_arch"));
173 EXPECT_TRUE(testBuildAttr(48, 0, ARMBuildAttrs::MVE_arch,
174 ARMBuildAttrs::Not_Allowed));
175 EXPECT_TRUE(testBuildAttr(48, 1, ARMBuildAttrs::MVE_arch,
176 ARMBuildAttrs::AllowMVEInteger));
177 EXPECT_TRUE(testBuildAttr(48, 2, ARMBuildAttrs::MVE_arch,
178 ARMBuildAttrs::AllowMVEIntegerAndFloat));
179 }
180
161181 TEST(CPUAlignBuildAttr, testBuildAttr) {
162182 EXPECT_TRUE(testTagString(34, "Tag_CPU_unaligned_access"));
163183 EXPECT_TRUE(testBuildAttr(34, 0, ARMBuildAttrs::CPU_unaligned_access,
2626 "armv8l", "armv8.1-a", "armv8.1a", "armv8.2-a", "armv8.2a",
2727 "armv8.3-a", "armv8.3a", "armv8.4-a", "armv8.4a", "armv8.5-a",
2828 "armv8.5a", "armv8-r", "armv8r", "armv8-m.base", "armv8m.base",
29 "armv8-m.main", "armv8m.main", "iwmmxt", "iwmmxt2", "xscale"
29 "armv8-m.main", "armv8m.main", "iwmmxt", "iwmmxt2", "xscale",
30 "armv8.1-m.main",
3031 };
3132
3233 bool testARMCPU(StringRef CPUName, StringRef ExpectedArch,
417418 testARMArch("armv8-m.main", "generic", "v8m.main",
418419 ARMBuildAttrs::CPUArch::v8_M_Main));
419420 EXPECT_TRUE(
421 testARMArch("armv8.1-m.main", "generic", "v8.1m.main",
422 ARMBuildAttrs::CPUArch::v8_1_M_Main));
423 EXPECT_TRUE(
420424 testARMArch("iwmmxt", "iwmmxt", "",
421425 ARMBuildAttrs::CPUArch::v5TE));
422426 EXPECT_TRUE(
568572 unsigned Extensions = ARM::AEK_CRC | ARM::AEK_CRYPTO | ARM::AEK_DSP |
569573 ARM::AEK_HWDIVARM | ARM::AEK_HWDIVTHUMB | ARM::AEK_MP |
570574 ARM::AEK_SEC | ARM::AEK_VIRT | ARM::AEK_RAS | ARM::AEK_FP16 |
571 ARM::AEK_FP16FML;
575 ARM::AEK_FP16FML | ARM::AEK_FP_DP;
572576
573577 for (unsigned i = 0; i <= Extensions; i++)
574578 EXPECT_TRUE(i == 0 ? !ARM::getExtensionFeatures(i, Features)
604608 {"iwmmxt2", "noiwmmxt2", nullptr, nullptr},
605609 {"maverick", "maverick", nullptr, nullptr},
606610 {"xscale", "noxscale", nullptr, nullptr},
607 {"sb", "nosb", "+sb", "-sb"}};
611 {"sb", "nosb", "+sb", "-sb"},
612 {"mve", "nomve", "+mve", "-mve"},
613 {"mve.fp", "nomve.fp", "+mve.fp", "-mve.fp"}};
608614
609615 for (unsigned i = 0; i < array_lengthof(ArchExt); i++) {
610616 EXPECT_EQ(StringRef(ArchExt[i][2]), ARM::getArchExtFeature(ArchExt[i][0]));
627633 "v7", "v7a", "v7ve", "v7hl", "v7l", "v7-r", "v7r", "v7-m",
628634 "v7m", "v7k", "v7s", "v7e-m", "v7em", "v8-a", "v8", "v8a",
629635 "v8l", "v8.1-a", "v8.1a", "v8.2-a", "v8.2a", "v8.3-a", "v8.3a", "v8.4-a",
630 "v8.4a", "v8.5-a","v8.5a", "v8-r"
636 "v8.4a", "v8.5-a","v8.5a", "v8-r", "v8m.base", "v8m.main", "v8.1m.main"
631637 };
632638
633639 for (unsigned i = 0; i < array_lengthof(Arch); i++) {
676682 case ARM::ArchKind::ARMV7EM:
677683 case ARM::ArchKind::ARMV8MMainline:
678684 case ARM::ArchKind::ARMV8MBaseline:
685 case ARM::ArchKind::ARMV8_1MMainline:
679686 EXPECT_EQ(ARM::ProfileKind::M, ARM::parseArchProfile(ARMArch[i]));
680687 break;
681688 case ARM::ArchKind::ARMV7R: