xref: /freebsd/contrib/llvm-project/clang/lib/Basic/Targets/ARM.cpp (revision 580744621f33383027108364dcadad718df46ffe)
1 //===--- ARM.cpp - Implement ARM target feature support -------------------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 // This file implements ARM TargetInfo objects.
10 //
11 //===----------------------------------------------------------------------===//
12 
13 #include "ARM.h"
14 #include "clang/Basic/Builtins.h"
15 #include "clang/Basic/Diagnostic.h"
16 #include "clang/Basic/TargetBuiltins.h"
17 #include "llvm/ADT/StringExtras.h"
18 #include "llvm/ADT/StringRef.h"
19 #include "llvm/ADT/StringSwitch.h"
20 
21 using namespace clang;
22 using namespace clang::targets;
23 
24 void ARMTargetInfo::setABIAAPCS() {
25   IsAAPCS = true;
26 
27   DoubleAlign = LongLongAlign = LongDoubleAlign = SuitableAlign = 64;
28   const llvm::Triple &T = getTriple();
29 
30   bool IsNetBSD = T.isOSNetBSD();
31   bool IsOpenBSD = T.isOSOpenBSD();
32   if (!T.isOSWindows() && !IsNetBSD && !IsOpenBSD)
33     WCharType = UnsignedInt;
34 
35   UseBitFieldTypeAlignment = true;
36 
37   ZeroLengthBitfieldBoundary = 0;
38 
39   // Thumb1 add sp, #imm requires the immediate value be multiple of 4,
40   // so set preferred for small types to 32.
41   if (T.isOSBinFormatMachO()) {
42     resetDataLayout(BigEndian
43                         ? "E-m:o-p:32:32-Fi8-i64:64-v128:64:128-a:0:32-n32-S64"
44                         : "e-m:o-p:32:32-Fi8-i64:64-v128:64:128-a:0:32-n32-S64");
45   } else if (T.isOSWindows()) {
46     assert(!BigEndian && "Windows on ARM does not support big endian");
47     resetDataLayout("e"
48                     "-m:w"
49                     "-p:32:32"
50                     "-Fi8"
51                     "-i64:64"
52                     "-v128:64:128"
53                     "-a:0:32"
54                     "-n32"
55                     "-S64");
56   } else if (T.isOSNaCl()) {
57     assert(!BigEndian && "NaCl on ARM does not support big endian");
58     resetDataLayout("e-m:e-p:32:32-Fi8-i64:64-v128:64:128-a:0:32-n32-S128");
59   } else {
60     resetDataLayout(BigEndian
61                         ? "E-m:e-p:32:32-Fi8-i64:64-v128:64:128-a:0:32-n32-S64"
62                         : "e-m:e-p:32:32-Fi8-i64:64-v128:64:128-a:0:32-n32-S64");
63   }
64 
65   // FIXME: Enumerated types are variable width in straight AAPCS.
66 }
67 
68 void ARMTargetInfo::setABIAPCS(bool IsAAPCS16) {
69   const llvm::Triple &T = getTriple();
70 
71   IsAAPCS = false;
72 
73   if (IsAAPCS16)
74     DoubleAlign = LongLongAlign = LongDoubleAlign = SuitableAlign = 64;
75   else
76     DoubleAlign = LongLongAlign = LongDoubleAlign = SuitableAlign = 32;
77 
78   WCharType = SignedInt;
79 
80   // Do not respect the alignment of bit-field types when laying out
81   // structures. This corresponds to PCC_BITFIELD_TYPE_MATTERS in gcc.
82   UseBitFieldTypeAlignment = false;
83 
84   /// gcc forces the alignment to 4 bytes, regardless of the type of the
85   /// zero length bitfield.  This corresponds to EMPTY_FIELD_BOUNDARY in
86   /// gcc.
87   ZeroLengthBitfieldBoundary = 32;
88 
89   if (T.isOSBinFormatMachO() && IsAAPCS16) {
90     assert(!BigEndian && "AAPCS16 does not support big-endian");
91     resetDataLayout("e-m:o-p:32:32-Fi8-i64:64-a:0:32-n32-S128");
92   } else if (T.isOSBinFormatMachO())
93     resetDataLayout(
94         BigEndian
95             ? "E-m:o-p:32:32-Fi8-f64:32:64-v64:32:64-v128:32:128-a:0:32-n32-S32"
96             : "e-m:o-p:32:32-Fi8-f64:32:64-v64:32:64-v128:32:128-a:0:32-n32-S32");
97   else
98     resetDataLayout(
99         BigEndian
100             ? "E-m:e-p:32:32-Fi8-f64:32:64-v64:32:64-v128:32:128-a:0:32-n32-S32"
101             : "e-m:e-p:32:32-Fi8-f64:32:64-v64:32:64-v128:32:128-a:0:32-n32-S32");
102 
103   // FIXME: Override "preferred align" for double and long long.
104 }
105 
106 void ARMTargetInfo::setArchInfo() {
107   StringRef ArchName = getTriple().getArchName();
108 
109   ArchISA = llvm::ARM::parseArchISA(ArchName);
110   CPU = llvm::ARM::getDefaultCPU(ArchName);
111   llvm::ARM::ArchKind AK = llvm::ARM::parseArch(ArchName);
112   if (AK != llvm::ARM::ArchKind::INVALID)
113     ArchKind = AK;
114   setArchInfo(ArchKind);
115 }
116 
117 void ARMTargetInfo::setArchInfo(llvm::ARM::ArchKind Kind) {
118   StringRef SubArch;
119 
120   // cache TargetParser info
121   ArchKind = Kind;
122   SubArch = llvm::ARM::getSubArch(ArchKind);
123   ArchProfile = llvm::ARM::parseArchProfile(SubArch);
124   ArchVersion = llvm::ARM::parseArchVersion(SubArch);
125 
126   // cache CPU related strings
127   CPUAttr = getCPUAttr();
128   CPUProfile = getCPUProfile();
129 }
130 
131 void ARMTargetInfo::setAtomic() {
132   // when triple does not specify a sub arch,
133   // then we are not using inline atomics
134   bool ShouldUseInlineAtomic =
135       (ArchISA == llvm::ARM::ISAKind::ARM && ArchVersion >= 6) ||
136       (ArchISA == llvm::ARM::ISAKind::THUMB && ArchVersion >= 7);
137   // Cortex M does not support 8 byte atomics, while general Thumb2 does.
138   if (ArchProfile == llvm::ARM::ProfileKind::M) {
139     MaxAtomicPromoteWidth = 32;
140     if (ShouldUseInlineAtomic)
141       MaxAtomicInlineWidth = 32;
142   } else {
143     MaxAtomicPromoteWidth = 64;
144     if (ShouldUseInlineAtomic)
145       MaxAtomicInlineWidth = 64;
146   }
147 }
148 
149 bool ARMTargetInfo::hasMVE() const {
150   return ArchKind == llvm::ARM::ArchKind::ARMV8_1MMainline && MVE != 0;
151 }
152 
153 bool ARMTargetInfo::hasMVEFloat() const {
154   return hasMVE() && (MVE & MVE_FP);
155 }
156 
157 bool ARMTargetInfo::isThumb() const {
158   return ArchISA == llvm::ARM::ISAKind::THUMB;
159 }
160 
161 bool ARMTargetInfo::supportsThumb() const {
162   return CPUAttr.count('T') || ArchVersion >= 6;
163 }
164 
165 bool ARMTargetInfo::supportsThumb2() const {
166   return CPUAttr.equals("6T2") ||
167          (ArchVersion >= 7 && !CPUAttr.equals("8M_BASE"));
168 }
169 
170 StringRef ARMTargetInfo::getCPUAttr() const {
171   // For most sub-arches, the build attribute CPU name is enough.
172   // For Cortex variants, it's slightly different.
173   switch (ArchKind) {
174   default:
175     return llvm::ARM::getCPUAttr(ArchKind);
176   case llvm::ARM::ArchKind::ARMV6M:
177     return "6M";
178   case llvm::ARM::ArchKind::ARMV7S:
179     return "7S";
180   case llvm::ARM::ArchKind::ARMV7A:
181     return "7A";
182   case llvm::ARM::ArchKind::ARMV7R:
183     return "7R";
184   case llvm::ARM::ArchKind::ARMV7M:
185     return "7M";
186   case llvm::ARM::ArchKind::ARMV7EM:
187     return "7EM";
188   case llvm::ARM::ArchKind::ARMV7VE:
189     return "7VE";
190   case llvm::ARM::ArchKind::ARMV8A:
191     return "8A";
192   case llvm::ARM::ArchKind::ARMV8_1A:
193     return "8_1A";
194   case llvm::ARM::ArchKind::ARMV8_2A:
195     return "8_2A";
196   case llvm::ARM::ArchKind::ARMV8_3A:
197     return "8_3A";
198   case llvm::ARM::ArchKind::ARMV8_4A:
199     return "8_4A";
200   case llvm::ARM::ArchKind::ARMV8_5A:
201     return "8_5A";
202   case llvm::ARM::ArchKind::ARMV8MBaseline:
203     return "8M_BASE";
204   case llvm::ARM::ArchKind::ARMV8MMainline:
205     return "8M_MAIN";
206   case llvm::ARM::ArchKind::ARMV8R:
207     return "8R";
208   case llvm::ARM::ArchKind::ARMV8_1MMainline:
209     return "8_1M_MAIN";
210   }
211 }
212 
213 StringRef ARMTargetInfo::getCPUProfile() const {
214   switch (ArchProfile) {
215   case llvm::ARM::ProfileKind::A:
216     return "A";
217   case llvm::ARM::ProfileKind::R:
218     return "R";
219   case llvm::ARM::ProfileKind::M:
220     return "M";
221   default:
222     return "";
223   }
224 }
225 
226 ARMTargetInfo::ARMTargetInfo(const llvm::Triple &Triple,
227                              const TargetOptions &Opts)
228     : TargetInfo(Triple), FPMath(FP_Default), IsAAPCS(true), LDREX(0),
229       HW_FP(0) {
230   bool IsOpenBSD = Triple.isOSOpenBSD();
231   bool IsNetBSD = Triple.isOSNetBSD();
232 
233   // FIXME: the isOSBinFormatMachO is a workaround for identifying a Darwin-like
234   // environment where size_t is `unsigned long` rather than `unsigned int`
235 
236   PtrDiffType = IntPtrType =
237       (Triple.isOSDarwin() || Triple.isOSBinFormatMachO() || IsOpenBSD ||
238        IsNetBSD)
239           ? SignedLong
240           : SignedInt;
241 
242   SizeType = (Triple.isOSDarwin() || Triple.isOSBinFormatMachO() || IsOpenBSD ||
243               IsNetBSD)
244                  ? UnsignedLong
245                  : UnsignedInt;
246 
247   // ptrdiff_t is inconsistent on Darwin
248   if ((Triple.isOSDarwin() || Triple.isOSBinFormatMachO()) &&
249       !Triple.isWatchABI())
250     PtrDiffType = SignedInt;
251 
252   // Cache arch related info.
253   setArchInfo();
254 
255   // {} in inline assembly are neon specifiers, not assembly variant
256   // specifiers.
257   NoAsmVariants = true;
258 
259   // FIXME: This duplicates code from the driver that sets the -target-abi
260   // option - this code is used if -target-abi isn't passed and should
261   // be unified in some way.
262   if (Triple.isOSBinFormatMachO()) {
263     // The backend is hardwired to assume AAPCS for M-class processors, ensure
264     // the frontend matches that.
265     if (Triple.getEnvironment() == llvm::Triple::EABI ||
266         Triple.getOS() == llvm::Triple::UnknownOS ||
267         ArchProfile == llvm::ARM::ProfileKind::M) {
268       setABI("aapcs");
269     } else if (Triple.isWatchABI()) {
270       setABI("aapcs16");
271     } else {
272       setABI("apcs-gnu");
273     }
274   } else if (Triple.isOSWindows()) {
275     // FIXME: this is invalid for WindowsCE
276     setABI("aapcs");
277   } else {
278     // Select the default based on the platform.
279     switch (Triple.getEnvironment()) {
280     case llvm::Triple::Android:
281     case llvm::Triple::GNUEABI:
282     case llvm::Triple::GNUEABIHF:
283     case llvm::Triple::MuslEABI:
284     case llvm::Triple::MuslEABIHF:
285       setABI("aapcs-linux");
286       break;
287     case llvm::Triple::EABIHF:
288     case llvm::Triple::EABI:
289       setABI("aapcs");
290       break;
291     case llvm::Triple::GNU:
292       setABI("apcs-gnu");
293       break;
294     default:
295       if (IsNetBSD)
296         setABI("apcs-gnu");
297       else if (IsOpenBSD)
298         setABI("aapcs-linux");
299       else
300         setABI("aapcs");
301       break;
302     }
303   }
304 
305   // ARM targets default to using the ARM C++ ABI.
306   TheCXXABI.set(TargetCXXABI::GenericARM);
307 
308   // ARM has atomics up to 8 bytes
309   setAtomic();
310 
311   // Maximum alignment for ARM NEON data types should be 64-bits (AAPCS)
312   // as well the default alignment
313   if (IsAAPCS && (Triple.getEnvironment() != llvm::Triple::Android))
314     DefaultAlignForAttributeAligned = MaxVectorAlign = 64;
315 
316   // Do force alignment of members that follow zero length bitfields.  If
317   // the alignment of the zero-length bitfield is greater than the member
318   // that follows it, `bar', `bar' will be aligned as the  type of the
319   // zero length bitfield.
320   UseZeroLengthBitfieldAlignment = true;
321 
322   if (Triple.getOS() == llvm::Triple::Linux ||
323       Triple.getOS() == llvm::Triple::UnknownOS)
324     this->MCountName = Opts.EABIVersion == llvm::EABI::GNU
325                            ? "llvm.arm.gnu.eabi.mcount"
326                            : "\01mcount";
327 
328   SoftFloatABI = llvm::is_contained(Opts.FeaturesAsWritten, "+soft-float-abi");
329 }
330 
331 StringRef ARMTargetInfo::getABI() const { return ABI; }
332 
333 bool ARMTargetInfo::setABI(const std::string &Name) {
334   ABI = Name;
335 
336   // The defaults (above) are for AAPCS, check if we need to change them.
337   //
338   // FIXME: We need support for -meabi... we could just mangle it into the
339   // name.
340   if (Name == "apcs-gnu" || Name == "aapcs16") {
341     setABIAPCS(Name == "aapcs16");
342     return true;
343   }
344   if (Name == "aapcs" || Name == "aapcs-vfp" || Name == "aapcs-linux") {
345     setABIAAPCS();
346     return true;
347   }
348   return false;
349 }
350 
351 // FIXME: This should be based on Arch attributes, not CPU names.
352 bool ARMTargetInfo::initFeatureMap(
353     llvm::StringMap<bool> &Features, DiagnosticsEngine &Diags, StringRef CPU,
354     const std::vector<std::string> &FeaturesVec) const {
355 
356   std::string ArchFeature;
357   std::vector<StringRef> TargetFeatures;
358   llvm::ARM::ArchKind Arch = llvm::ARM::parseArch(getTriple().getArchName());
359 
360   // Map the base architecture to an appropriate target feature, so we don't
361   // rely on the target triple.
362   llvm::ARM::ArchKind CPUArch = llvm::ARM::parseCPUArch(CPU);
363   if (CPUArch == llvm::ARM::ArchKind::INVALID)
364     CPUArch = Arch;
365   if (CPUArch != llvm::ARM::ArchKind::INVALID) {
366     ArchFeature = ("+" + llvm::ARM::getArchName(CPUArch)).str();
367     TargetFeatures.push_back(ArchFeature);
368   }
369 
370   // get default FPU features
371   unsigned FPUKind = llvm::ARM::getDefaultFPU(CPU, Arch);
372   llvm::ARM::getFPUFeatures(FPUKind, TargetFeatures);
373 
374   // get default Extension features
375   unsigned Extensions = llvm::ARM::getDefaultExtensions(CPU, Arch);
376   llvm::ARM::getExtensionFeatures(Extensions, TargetFeatures);
377 
378   for (auto Feature : TargetFeatures)
379     if (Feature[0] == '+')
380       Features[Feature.drop_front(1)] = true;
381 
382   // Enable or disable thumb-mode explicitly per function to enable mixed
383   // ARM and Thumb code generation.
384   if (isThumb())
385     Features["thumb-mode"] = true;
386   else
387     Features["thumb-mode"] = false;
388 
389   // Convert user-provided arm and thumb GNU target attributes to
390   // [-|+]thumb-mode target features respectively.
391   std::vector<std::string> UpdatedFeaturesVec;
392   for (const auto &Feature : FeaturesVec) {
393     // Skip soft-float-abi; it's something we only use to initialize a bit of
394     // class state, and is otherwise unrecognized.
395     if (Feature == "+soft-float-abi")
396       continue;
397 
398     StringRef FixedFeature;
399     if (Feature == "+arm")
400       FixedFeature = "-thumb-mode";
401     else if (Feature == "+thumb")
402       FixedFeature = "+thumb-mode";
403     else
404       FixedFeature = Feature;
405     UpdatedFeaturesVec.push_back(FixedFeature.str());
406   }
407 
408   return TargetInfo::initFeatureMap(Features, Diags, CPU, UpdatedFeaturesVec);
409 }
410 
411 
412 bool ARMTargetInfo::handleTargetFeatures(std::vector<std::string> &Features,
413                                          DiagnosticsEngine &Diags) {
414   FPU = 0;
415   MVE = 0;
416   CRC = 0;
417   Crypto = 0;
418   DSP = 0;
419   Unaligned = 1;
420   SoftFloat = false;
421   // Note that SoftFloatABI is initialized in our constructor.
422   HWDiv = 0;
423   DotProd = 0;
424   HasFloat16 = true;
425 
426   // This does not diagnose illegal cases like having both
427   // "+vfpv2" and "+vfpv3" or having "+neon" and "-fp64".
428   for (const auto &Feature : Features) {
429     if (Feature == "+soft-float") {
430       SoftFloat = true;
431     } else if (Feature == "+vfp2sp" || Feature == "+vfp2") {
432       FPU |= VFP2FPU;
433       HW_FP |= HW_FP_SP;
434       if (Feature == "+vfp2")
435           HW_FP |= HW_FP_DP;
436     } else if (Feature == "+vfp3sp" || Feature == "+vfp3d16sp" ||
437                Feature == "+vfp3" || Feature == "+vfp3d16") {
438       FPU |= VFP3FPU;
439       HW_FP |= HW_FP_SP;
440       if (Feature == "+vfp3" || Feature == "+vfp3d16")
441           HW_FP |= HW_FP_DP;
442     } else if (Feature == "+vfp4sp" || Feature == "+vfp4d16sp" ||
443                Feature == "+vfp4" || Feature == "+vfp4d16") {
444       FPU |= VFP4FPU;
445       HW_FP |= HW_FP_SP | HW_FP_HP;
446       if (Feature == "+vfp4" || Feature == "+vfp4d16")
447           HW_FP |= HW_FP_DP;
448     } else if (Feature == "+fp-armv8sp" || Feature == "+fp-armv8d16sp" ||
449                Feature == "+fp-armv8" || Feature == "+fp-armv8d16") {
450       FPU |= FPARMV8;
451       HW_FP |= HW_FP_SP | HW_FP_HP;
452       if (Feature == "+fp-armv8" || Feature == "+fp-armv8d16")
453           HW_FP |= HW_FP_DP;
454     } else if (Feature == "+neon") {
455       FPU |= NeonFPU;
456       HW_FP |= HW_FP_SP;
457     } else if (Feature == "+hwdiv") {
458       HWDiv |= HWDivThumb;
459     } else if (Feature == "+hwdiv-arm") {
460       HWDiv |= HWDivARM;
461     } else if (Feature == "+crc") {
462       CRC = 1;
463     } else if (Feature == "+crypto") {
464       Crypto = 1;
465     } else if (Feature == "+dsp") {
466       DSP = 1;
467     } else if (Feature == "+fp64") {
468       HW_FP |= HW_FP_DP;
469     } else if (Feature == "+8msecext") {
470       if (CPUProfile != "M" || ArchVersion != 8) {
471         Diags.Report(diag::err_target_unsupported_mcmse) << CPU;
472         return false;
473       }
474     } else if (Feature == "+strict-align") {
475       Unaligned = 0;
476     } else if (Feature == "+fp16") {
477       HW_FP |= HW_FP_HP;
478     } else if (Feature == "+fullfp16") {
479       HasLegalHalfType = true;
480     } else if (Feature == "+dotprod") {
481       DotProd = true;
482     } else if (Feature == "+mve") {
483       DSP = 1;
484       MVE |= MVE_INT;
485     } else if (Feature == "+mve.fp") {
486       DSP = 1;
487       HasLegalHalfType = true;
488       FPU |= FPARMV8;
489       MVE |= MVE_INT | MVE_FP;
490       HW_FP |= HW_FP_SP | HW_FP_HP;
491     }
492   }
493 
494   switch (ArchVersion) {
495   case 6:
496     if (ArchProfile == llvm::ARM::ProfileKind::M)
497       LDREX = 0;
498     else if (ArchKind == llvm::ARM::ArchKind::ARMV6K)
499       LDREX = LDREX_D | LDREX_W | LDREX_H | LDREX_B;
500     else
501       LDREX = LDREX_W;
502     break;
503   case 7:
504     if (ArchProfile == llvm::ARM::ProfileKind::M)
505       LDREX = LDREX_W | LDREX_H | LDREX_B;
506     else
507       LDREX = LDREX_D | LDREX_W | LDREX_H | LDREX_B;
508     break;
509   case 8:
510     LDREX = LDREX_D | LDREX_W | LDREX_H | LDREX_B;
511   }
512 
513   if (!(FPU & NeonFPU) && FPMath == FP_Neon) {
514     Diags.Report(diag::err_target_unsupported_fpmath) << "neon";
515     return false;
516   }
517 
518   if (FPMath == FP_Neon)
519     Features.push_back("+neonfp");
520   else if (FPMath == FP_VFP)
521     Features.push_back("-neonfp");
522 
523   return true;
524 }
525 
526 bool ARMTargetInfo::hasFeature(StringRef Feature) const {
527   return llvm::StringSwitch<bool>(Feature)
528       .Case("arm", true)
529       .Case("aarch32", true)
530       .Case("softfloat", SoftFloat)
531       .Case("thumb", isThumb())
532       .Case("neon", (FPU & NeonFPU) && !SoftFloat)
533       .Case("vfp", FPU && !SoftFloat)
534       .Case("hwdiv", HWDiv & HWDivThumb)
535       .Case("hwdiv-arm", HWDiv & HWDivARM)
536       .Case("mve", hasMVE())
537       .Default(false);
538 }
539 
540 bool ARMTargetInfo::isValidCPUName(StringRef Name) const {
541   return Name == "generic" ||
542          llvm::ARM::parseCPUArch(Name) != llvm::ARM::ArchKind::INVALID;
543 }
544 
545 void ARMTargetInfo::fillValidCPUList(SmallVectorImpl<StringRef> &Values) const {
546   llvm::ARM::fillValidCPUArchList(Values);
547 }
548 
549 bool ARMTargetInfo::setCPU(const std::string &Name) {
550   if (Name != "generic")
551     setArchInfo(llvm::ARM::parseCPUArch(Name));
552 
553   if (ArchKind == llvm::ARM::ArchKind::INVALID)
554     return false;
555   setAtomic();
556   CPU = Name;
557   return true;
558 }
559 
560 bool ARMTargetInfo::setFPMath(StringRef Name) {
561   if (Name == "neon") {
562     FPMath = FP_Neon;
563     return true;
564   } else if (Name == "vfp" || Name == "vfp2" || Name == "vfp3" ||
565              Name == "vfp4") {
566     FPMath = FP_VFP;
567     return true;
568   }
569   return false;
570 }
571 
572 void ARMTargetInfo::getTargetDefinesARMV81A(const LangOptions &Opts,
573                                             MacroBuilder &Builder) const {
574   Builder.defineMacro("__ARM_FEATURE_QRDMX", "1");
575 }
576 
577 void ARMTargetInfo::getTargetDefinesARMV82A(const LangOptions &Opts,
578                                             MacroBuilder &Builder) const {
579   // Also include the ARMv8.1-A defines
580   getTargetDefinesARMV81A(Opts, Builder);
581 }
582 
583 void ARMTargetInfo::getTargetDefinesARMV83A(const LangOptions &Opts,
584                                             MacroBuilder &Builder) const {
585   // Also include the ARMv8.2-A defines
586   Builder.defineMacro("__ARM_FEATURE_COMPLEX", "1");
587   getTargetDefinesARMV82A(Opts, Builder);
588 }
589 
590 void ARMTargetInfo::getTargetDefines(const LangOptions &Opts,
591                                      MacroBuilder &Builder) const {
592   // Target identification.
593   Builder.defineMacro("__arm");
594   Builder.defineMacro("__arm__");
595   // For bare-metal none-eabi.
596   if (getTriple().getOS() == llvm::Triple::UnknownOS &&
597       (getTriple().getEnvironment() == llvm::Triple::EABI ||
598        getTriple().getEnvironment() == llvm::Triple::EABIHF))
599     Builder.defineMacro("__ELF__");
600 
601   // Target properties.
602   Builder.defineMacro("__REGISTER_PREFIX__", "");
603 
604   // Unfortunately, __ARM_ARCH_7K__ is now more of an ABI descriptor. The CPU
605   // happens to be Cortex-A7 though, so it should still get __ARM_ARCH_7A__.
606   if (getTriple().isWatchABI())
607     Builder.defineMacro("__ARM_ARCH_7K__", "2");
608 
609   if (!CPUAttr.empty())
610     Builder.defineMacro("__ARM_ARCH_" + CPUAttr + "__");
611 
612   // ACLE 6.4.1 ARM/Thumb instruction set architecture
613   // __ARM_ARCH is defined as an integer value indicating the current ARM ISA
614   Builder.defineMacro("__ARM_ARCH", Twine(ArchVersion));
615 
616   if (ArchVersion >= 8) {
617     // ACLE 6.5.7 Crypto Extension
618     if (Crypto)
619       Builder.defineMacro("__ARM_FEATURE_CRYPTO", "1");
620     // ACLE 6.5.8 CRC32 Extension
621     if (CRC)
622       Builder.defineMacro("__ARM_FEATURE_CRC32", "1");
623     // ACLE 6.5.10 Numeric Maximum and Minimum
624     Builder.defineMacro("__ARM_FEATURE_NUMERIC_MAXMIN", "1");
625     // ACLE 6.5.9 Directed Rounding
626     Builder.defineMacro("__ARM_FEATURE_DIRECTED_ROUNDING", "1");
627   }
628 
629   // __ARM_ARCH_ISA_ARM is defined to 1 if the core supports the ARM ISA.  It
630   // is not defined for the M-profile.
631   // NOTE that the default profile is assumed to be 'A'
632   if (CPUProfile.empty() || ArchProfile != llvm::ARM::ProfileKind::M)
633     Builder.defineMacro("__ARM_ARCH_ISA_ARM", "1");
634 
635   // __ARM_ARCH_ISA_THUMB is defined to 1 if the core supports the original
636   // Thumb ISA (including v6-M and v8-M Baseline).  It is set to 2 if the
637   // core supports the Thumb-2 ISA as found in the v6T2 architecture and all
638   // v7 and v8 architectures excluding v8-M Baseline.
639   if (supportsThumb2())
640     Builder.defineMacro("__ARM_ARCH_ISA_THUMB", "2");
641   else if (supportsThumb())
642     Builder.defineMacro("__ARM_ARCH_ISA_THUMB", "1");
643 
644   // __ARM_32BIT_STATE is defined to 1 if code is being generated for a 32-bit
645   // instruction set such as ARM or Thumb.
646   Builder.defineMacro("__ARM_32BIT_STATE", "1");
647 
648   // ACLE 6.4.2 Architectural Profile (A, R, M or pre-Cortex)
649 
650   // __ARM_ARCH_PROFILE is defined as 'A', 'R', 'M' or 'S', or unset.
651   if (!CPUProfile.empty())
652     Builder.defineMacro("__ARM_ARCH_PROFILE", "'" + CPUProfile + "'");
653 
654   // ACLE 6.4.3 Unaligned access supported in hardware
655   if (Unaligned)
656     Builder.defineMacro("__ARM_FEATURE_UNALIGNED", "1");
657 
658   // ACLE 6.4.4 LDREX/STREX
659   if (LDREX)
660     Builder.defineMacro("__ARM_FEATURE_LDREX", "0x" + Twine::utohexstr(LDREX));
661 
662   // ACLE 6.4.5 CLZ
663   if (ArchVersion == 5 || (ArchVersion == 6 && CPUProfile != "M") ||
664       ArchVersion > 6)
665     Builder.defineMacro("__ARM_FEATURE_CLZ", "1");
666 
667   // ACLE 6.5.1 Hardware Floating Point
668   if (HW_FP)
669     Builder.defineMacro("__ARM_FP", "0x" + Twine::utohexstr(HW_FP));
670 
671   // ACLE predefines.
672   Builder.defineMacro("__ARM_ACLE", "200");
673 
674   // FP16 support (we currently only support IEEE format).
675   Builder.defineMacro("__ARM_FP16_FORMAT_IEEE", "1");
676   Builder.defineMacro("__ARM_FP16_ARGS", "1");
677 
678   // ACLE 6.5.3 Fused multiply-accumulate (FMA)
679   if (ArchVersion >= 7 && (FPU & VFP4FPU))
680     Builder.defineMacro("__ARM_FEATURE_FMA", "1");
681 
682   // Subtarget options.
683 
684   // FIXME: It's more complicated than this and we don't really support
685   // interworking.
686   // Windows on ARM does not "support" interworking
687   if (5 <= ArchVersion && ArchVersion <= 8 && !getTriple().isOSWindows())
688     Builder.defineMacro("__THUMB_INTERWORK__");
689 
690   if (ABI == "aapcs" || ABI == "aapcs-linux" || ABI == "aapcs-vfp") {
691     // Embedded targets on Darwin follow AAPCS, but not EABI.
692     // Windows on ARM follows AAPCS VFP, but does not conform to EABI.
693     if (!getTriple().isOSBinFormatMachO() && !getTriple().isOSWindows())
694       Builder.defineMacro("__ARM_EABI__");
695     Builder.defineMacro("__ARM_PCS", "1");
696   }
697 
698   if ((!SoftFloat && !SoftFloatABI) || ABI == "aapcs-vfp" || ABI == "aapcs16")
699     Builder.defineMacro("__ARM_PCS_VFP", "1");
700 
701   if (SoftFloat)
702     Builder.defineMacro("__SOFTFP__");
703 
704   // ACLE position independent code macros.
705   if (Opts.ROPI)
706     Builder.defineMacro("__ARM_ROPI", "1");
707   if (Opts.RWPI)
708     Builder.defineMacro("__ARM_RWPI", "1");
709 
710   if (ArchKind == llvm::ARM::ArchKind::XSCALE)
711     Builder.defineMacro("__XSCALE__");
712 
713   if (isThumb()) {
714     Builder.defineMacro("__THUMBEL__");
715     Builder.defineMacro("__thumb__");
716     if (supportsThumb2())
717       Builder.defineMacro("__thumb2__");
718   }
719 
720   // ACLE 6.4.9 32-bit SIMD instructions
721   if ((CPUProfile != "M" && ArchVersion >= 6) || (CPUProfile == "M" && DSP))
722     Builder.defineMacro("__ARM_FEATURE_SIMD32", "1");
723 
724   // ACLE 6.4.10 Hardware Integer Divide
725   if (((HWDiv & HWDivThumb) && isThumb()) ||
726       ((HWDiv & HWDivARM) && !isThumb())) {
727     Builder.defineMacro("__ARM_FEATURE_IDIV", "1");
728     Builder.defineMacro("__ARM_ARCH_EXT_IDIV__", "1");
729   }
730 
731   // Note, this is always on in gcc, even though it doesn't make sense.
732   Builder.defineMacro("__APCS_32__");
733 
734   if (FPUModeIsVFP((FPUMode)FPU)) {
735     Builder.defineMacro("__VFP_FP__");
736     if (FPU & VFP2FPU)
737       Builder.defineMacro("__ARM_VFPV2__");
738     if (FPU & VFP3FPU)
739       Builder.defineMacro("__ARM_VFPV3__");
740     if (FPU & VFP4FPU)
741       Builder.defineMacro("__ARM_VFPV4__");
742     if (FPU & FPARMV8)
743       Builder.defineMacro("__ARM_FPV5__");
744   }
745 
746   // This only gets set when Neon instructions are actually available, unlike
747   // the VFP define, hence the soft float and arch check. This is subtly
748   // different from gcc, we follow the intent which was that it should be set
749   // when Neon instructions are actually available.
750   if ((FPU & NeonFPU) && !SoftFloat && ArchVersion >= 7) {
751     Builder.defineMacro("__ARM_NEON", "1");
752     Builder.defineMacro("__ARM_NEON__");
753     // current AArch32 NEON implementations do not support double-precision
754     // floating-point even when it is present in VFP.
755     Builder.defineMacro("__ARM_NEON_FP",
756                         "0x" + Twine::utohexstr(HW_FP & ~HW_FP_DP));
757   }
758 
759   if (hasMVE()) {
760     Builder.defineMacro("__ARM_FEATURE_MVE", hasMVEFloat() ? "3" : "1");
761   }
762 
763   Builder.defineMacro("__ARM_SIZEOF_WCHAR_T",
764                       Twine(Opts.WCharSize ? Opts.WCharSize : 4));
765 
766   Builder.defineMacro("__ARM_SIZEOF_MINIMAL_ENUM", Opts.ShortEnums ? "1" : "4");
767 
768   // CMSE
769   if (ArchVersion == 8 && ArchProfile == llvm::ARM::ProfileKind::M)
770     Builder.defineMacro("__ARM_FEATURE_CMSE", Opts.Cmse ? "3" : "1");
771 
772   if (ArchVersion >= 6 && CPUAttr != "6M" && CPUAttr != "8M_BASE") {
773     Builder.defineMacro("__GCC_HAVE_SYNC_COMPARE_AND_SWAP_1");
774     Builder.defineMacro("__GCC_HAVE_SYNC_COMPARE_AND_SWAP_2");
775     Builder.defineMacro("__GCC_HAVE_SYNC_COMPARE_AND_SWAP_4");
776     Builder.defineMacro("__GCC_HAVE_SYNC_COMPARE_AND_SWAP_8");
777   }
778 
779   // ACLE 6.4.7 DSP instructions
780   if (DSP) {
781     Builder.defineMacro("__ARM_FEATURE_DSP", "1");
782   }
783 
784   // ACLE 6.4.8 Saturation instructions
785   bool SAT = false;
786   if ((ArchVersion == 6 && CPUProfile != "M") || ArchVersion > 6) {
787     Builder.defineMacro("__ARM_FEATURE_SAT", "1");
788     SAT = true;
789   }
790 
791   // ACLE 6.4.6 Q (saturation) flag
792   if (DSP || SAT)
793     Builder.defineMacro("__ARM_FEATURE_QBIT", "1");
794 
795   if (Opts.UnsafeFPMath)
796     Builder.defineMacro("__ARM_FP_FAST", "1");
797 
798   // Armv8.2-A FP16 vector intrinsic
799   if ((FPU & NeonFPU) && HasLegalHalfType)
800     Builder.defineMacro("__ARM_FEATURE_FP16_VECTOR_ARITHMETIC", "1");
801 
802   // Armv8.2-A FP16 scalar intrinsics
803   if (HasLegalHalfType)
804     Builder.defineMacro("__ARM_FEATURE_FP16_SCALAR_ARITHMETIC", "1");
805 
806   // Armv8.2-A dot product intrinsics
807   if (DotProd)
808     Builder.defineMacro("__ARM_FEATURE_DOTPROD", "1");
809 
810   switch (ArchKind) {
811   default:
812     break;
813   case llvm::ARM::ArchKind::ARMV8_1A:
814     getTargetDefinesARMV81A(Opts, Builder);
815     break;
816   case llvm::ARM::ArchKind::ARMV8_2A:
817     getTargetDefinesARMV82A(Opts, Builder);
818     break;
819   case llvm::ARM::ArchKind::ARMV8_3A:
820   case llvm::ARM::ArchKind::ARMV8_4A:
821   case llvm::ARM::ArchKind::ARMV8_5A:
822     getTargetDefinesARMV83A(Opts, Builder);
823     break;
824   }
825 }
826 
827 const Builtin::Info ARMTargetInfo::BuiltinInfo[] = {
828 #define BUILTIN(ID, TYPE, ATTRS)                                               \
829   {#ID, TYPE, ATTRS, nullptr, ALL_LANGUAGES, nullptr},
830 #define LIBBUILTIN(ID, TYPE, ATTRS, HEADER)                                    \
831   {#ID, TYPE, ATTRS, HEADER, ALL_LANGUAGES, nullptr},
832 #include "clang/Basic/BuiltinsNEON.def"
833 
834 #define BUILTIN(ID, TYPE, ATTRS)                                               \
835   {#ID, TYPE, ATTRS, nullptr, ALL_LANGUAGES, nullptr},
836 #define LANGBUILTIN(ID, TYPE, ATTRS, LANG)                                     \
837   {#ID, TYPE, ATTRS, nullptr, LANG, nullptr},
838 #define LIBBUILTIN(ID, TYPE, ATTRS, HEADER)                                    \
839   {#ID, TYPE, ATTRS, HEADER, ALL_LANGUAGES, nullptr},
840 #define TARGET_HEADER_BUILTIN(ID, TYPE, ATTRS, HEADER, LANGS, FEATURE)         \
841   {#ID, TYPE, ATTRS, HEADER, LANGS, FEATURE},
842 #include "clang/Basic/BuiltinsARM.def"
843 };
844 
845 ArrayRef<Builtin::Info> ARMTargetInfo::getTargetBuiltins() const {
846   return llvm::makeArrayRef(BuiltinInfo, clang::ARM::LastTSBuiltin -
847                                              Builtin::FirstTSBuiltin);
848 }
849 
850 bool ARMTargetInfo::isCLZForZeroUndef() const { return false; }
851 TargetInfo::BuiltinVaListKind ARMTargetInfo::getBuiltinVaListKind() const {
852   return IsAAPCS
853              ? AAPCSABIBuiltinVaList
854              : (getTriple().isWatchABI() ? TargetInfo::CharPtrBuiltinVaList
855                                          : TargetInfo::VoidPtrBuiltinVaList);
856 }
857 
858 const char *const ARMTargetInfo::GCCRegNames[] = {
859     // Integer registers
860     "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "r10", "r11",
861     "r12", "sp", "lr", "pc",
862 
863     // Float registers
864     "s0", "s1", "s2", "s3", "s4", "s5", "s6", "s7", "s8", "s9", "s10", "s11",
865     "s12", "s13", "s14", "s15", "s16", "s17", "s18", "s19", "s20", "s21", "s22",
866     "s23", "s24", "s25", "s26", "s27", "s28", "s29", "s30", "s31",
867 
868     // Double registers
869     "d0", "d1", "d2", "d3", "d4", "d5", "d6", "d7", "d8", "d9", "d10", "d11",
870     "d12", "d13", "d14", "d15", "d16", "d17", "d18", "d19", "d20", "d21", "d22",
871     "d23", "d24", "d25", "d26", "d27", "d28", "d29", "d30", "d31",
872 
873     // Quad registers
874     "q0", "q1", "q2", "q3", "q4", "q5", "q6", "q7", "q8", "q9", "q10", "q11",
875     "q12", "q13", "q14", "q15"};
876 
877 ArrayRef<const char *> ARMTargetInfo::getGCCRegNames() const {
878   return llvm::makeArrayRef(GCCRegNames);
879 }
880 
881 const TargetInfo::GCCRegAlias ARMTargetInfo::GCCRegAliases[] = {
882     {{"a1"}, "r0"},  {{"a2"}, "r1"},        {{"a3"}, "r2"},  {{"a4"}, "r3"},
883     {{"v1"}, "r4"},  {{"v2"}, "r5"},        {{"v3"}, "r6"},  {{"v4"}, "r7"},
884     {{"v5"}, "r8"},  {{"v6", "rfp"}, "r9"}, {{"sl"}, "r10"}, {{"fp"}, "r11"},
885     {{"ip"}, "r12"}, {{"r13"}, "sp"},       {{"r14"}, "lr"}, {{"r15"}, "pc"},
886     // The S, D and Q registers overlap, but aren't really aliases; we
887     // don't want to substitute one of these for a different-sized one.
888 };
889 
890 ArrayRef<TargetInfo::GCCRegAlias> ARMTargetInfo::getGCCRegAliases() const {
891   return llvm::makeArrayRef(GCCRegAliases);
892 }
893 
894 bool ARMTargetInfo::validateAsmConstraint(
895     const char *&Name, TargetInfo::ConstraintInfo &Info) const {
896   switch (*Name) {
897   default:
898     break;
899   case 'l': // r0-r7 if thumb, r0-r15 if ARM
900     Info.setAllowsRegister();
901     return true;
902   case 'h': // r8-r15, thumb only
903     if (isThumb()) {
904       Info.setAllowsRegister();
905       return true;
906     }
907     break;
908   case 's': // An integer constant, but allowing only relocatable values.
909     return true;
910   case 't': // s0-s31, d0-d31, or q0-q15
911   case 'w': // s0-s15, d0-d7, or q0-q3
912   case 'x': // s0-s31, d0-d15, or q0-q7
913     Info.setAllowsRegister();
914     return true;
915   case 'j': // An immediate integer between 0 and 65535 (valid for MOVW)
916     // only available in ARMv6T2 and above
917     if (CPUAttr.equals("6T2") || ArchVersion >= 7) {
918       Info.setRequiresImmediate(0, 65535);
919       return true;
920     }
921     break;
922   case 'I':
923     if (isThumb()) {
924       if (!supportsThumb2())
925         Info.setRequiresImmediate(0, 255);
926       else
927         // FIXME: should check if immediate value would be valid for a Thumb2
928         // data-processing instruction
929         Info.setRequiresImmediate();
930     } else
931       // FIXME: should check if immediate value would be valid for an ARM
932       // data-processing instruction
933       Info.setRequiresImmediate();
934     return true;
935   case 'J':
936     if (isThumb() && !supportsThumb2())
937       Info.setRequiresImmediate(-255, -1);
938     else
939       Info.setRequiresImmediate(-4095, 4095);
940     return true;
941   case 'K':
942     if (isThumb()) {
943       if (!supportsThumb2())
944         // FIXME: should check if immediate value can be obtained from shifting
945         // a value between 0 and 255 left by any amount
946         Info.setRequiresImmediate();
947       else
948         // FIXME: should check if immediate value would be valid for a Thumb2
949         // data-processing instruction when inverted
950         Info.setRequiresImmediate();
951     } else
952       // FIXME: should check if immediate value would be valid for an ARM
953       // data-processing instruction when inverted
954       Info.setRequiresImmediate();
955     return true;
956   case 'L':
957     if (isThumb()) {
958       if (!supportsThumb2())
959         Info.setRequiresImmediate(-7, 7);
960       else
961         // FIXME: should check if immediate value would be valid for a Thumb2
962         // data-processing instruction when negated
963         Info.setRequiresImmediate();
964     } else
965       // FIXME: should check if immediate value  would be valid for an ARM
966       // data-processing instruction when negated
967       Info.setRequiresImmediate();
968     return true;
969   case 'M':
970     if (isThumb() && !supportsThumb2())
971       // FIXME: should check if immediate value is a multiple of 4 between 0 and
972       // 1020
973       Info.setRequiresImmediate();
974     else
975       // FIXME: should check if immediate value is a power of two or a integer
976       // between 0 and 32
977       Info.setRequiresImmediate();
978     return true;
979   case 'N':
980     // Thumb1 only
981     if (isThumb() && !supportsThumb2()) {
982       Info.setRequiresImmediate(0, 31);
983       return true;
984     }
985     break;
986   case 'O':
987     // Thumb1 only
988     if (isThumb() && !supportsThumb2()) {
989       // FIXME: should check if immediate value is a multiple of 4 between -508
990       // and 508
991       Info.setRequiresImmediate();
992       return true;
993     }
994     break;
995   case 'Q': // A memory address that is a single base register.
996     Info.setAllowsMemory();
997     return true;
998   case 'T':
999     switch (Name[1]) {
1000     default:
1001       break;
1002     case 'e': // Even general-purpose register
1003     case 'o': // Odd general-purpose register
1004       Info.setAllowsRegister();
1005       Name++;
1006       return true;
1007     }
1008     break;
1009   case 'U': // a memory reference...
1010     switch (Name[1]) {
1011     case 'q': // ...ARMV4 ldrsb
1012     case 'v': // ...VFP load/store (reg+constant offset)
1013     case 'y': // ...iWMMXt load/store
1014     case 't': // address valid for load/store opaque types wider
1015               // than 128-bits
1016     case 'n': // valid address for Neon doubleword vector load/store
1017     case 'm': // valid address for Neon element and structure load/store
1018     case 's': // valid address for non-offset loads/stores of quad-word
1019               // values in four ARM registers
1020       Info.setAllowsMemory();
1021       Name++;
1022       return true;
1023     }
1024     break;
1025   }
1026   return false;
1027 }
1028 
1029 std::string ARMTargetInfo::convertConstraint(const char *&Constraint) const {
1030   std::string R;
1031   switch (*Constraint) {
1032   case 'U': // Two-character constraint; add "^" hint for later parsing.
1033   case 'T':
1034     R = std::string("^") + std::string(Constraint, 2);
1035     Constraint++;
1036     break;
1037   case 'p': // 'p' should be translated to 'r' by default.
1038     R = std::string("r");
1039     break;
1040   default:
1041     return std::string(1, *Constraint);
1042   }
1043   return R;
1044 }
1045 
1046 bool ARMTargetInfo::validateConstraintModifier(
1047     StringRef Constraint, char Modifier, unsigned Size,
1048     std::string &SuggestedModifier) const {
1049   bool isOutput = (Constraint[0] == '=');
1050   bool isInOut = (Constraint[0] == '+');
1051 
1052   // Strip off constraint modifiers.
1053   while (Constraint[0] == '=' || Constraint[0] == '+' || Constraint[0] == '&')
1054     Constraint = Constraint.substr(1);
1055 
1056   switch (Constraint[0]) {
1057   default:
1058     break;
1059   case 'r': {
1060     switch (Modifier) {
1061     default:
1062       return (isInOut || isOutput || Size <= 64);
1063     case 'q':
1064       // A register of size 32 cannot fit a vector type.
1065       return false;
1066     }
1067   }
1068   }
1069 
1070   return true;
1071 }
1072 const char *ARMTargetInfo::getClobbers() const {
1073   // FIXME: Is this really right?
1074   return "";
1075 }
1076 
1077 TargetInfo::CallingConvCheckResult
1078 ARMTargetInfo::checkCallingConvention(CallingConv CC) const {
1079   switch (CC) {
1080   case CC_AAPCS:
1081   case CC_AAPCS_VFP:
1082   case CC_Swift:
1083   case CC_OpenCLKernel:
1084     return CCCR_OK;
1085   default:
1086     return CCCR_Warning;
1087   }
1088 }
1089 
1090 int ARMTargetInfo::getEHDataRegisterNumber(unsigned RegNo) const {
1091   if (RegNo == 0)
1092     return 0;
1093   if (RegNo == 1)
1094     return 1;
1095   return -1;
1096 }
1097 
1098 bool ARMTargetInfo::hasSjLjLowering() const { return true; }
1099 
1100 ARMleTargetInfo::ARMleTargetInfo(const llvm::Triple &Triple,
1101                                  const TargetOptions &Opts)
1102     : ARMTargetInfo(Triple, Opts) {}
1103 
1104 void ARMleTargetInfo::getTargetDefines(const LangOptions &Opts,
1105                                        MacroBuilder &Builder) const {
1106   Builder.defineMacro("__ARMEL__");
1107   ARMTargetInfo::getTargetDefines(Opts, Builder);
1108 }
1109 
1110 ARMbeTargetInfo::ARMbeTargetInfo(const llvm::Triple &Triple,
1111                                  const TargetOptions &Opts)
1112     : ARMTargetInfo(Triple, Opts) {}
1113 
1114 void ARMbeTargetInfo::getTargetDefines(const LangOptions &Opts,
1115                                        MacroBuilder &Builder) const {
1116   Builder.defineMacro("__ARMEB__");
1117   Builder.defineMacro("__ARM_BIG_ENDIAN");
1118   ARMTargetInfo::getTargetDefines(Opts, Builder);
1119 }
1120 
1121 WindowsARMTargetInfo::WindowsARMTargetInfo(const llvm::Triple &Triple,
1122                                            const TargetOptions &Opts)
1123     : WindowsTargetInfo<ARMleTargetInfo>(Triple, Opts), Triple(Triple) {
1124 }
1125 
1126 void WindowsARMTargetInfo::getVisualStudioDefines(const LangOptions &Opts,
1127                                                   MacroBuilder &Builder) const {
1128   // FIXME: this is invalid for WindowsCE
1129   Builder.defineMacro("_M_ARM_NT", "1");
1130   Builder.defineMacro("_M_ARMT", "_M_ARM");
1131   Builder.defineMacro("_M_THUMB", "_M_ARM");
1132 
1133   assert((Triple.getArch() == llvm::Triple::arm ||
1134           Triple.getArch() == llvm::Triple::thumb) &&
1135          "invalid architecture for Windows ARM target info");
1136   unsigned Offset = Triple.getArch() == llvm::Triple::arm ? 4 : 6;
1137   Builder.defineMacro("_M_ARM", Triple.getArchName().substr(Offset));
1138 
1139   // TODO map the complete set of values
1140   // 31: VFPv3 40: VFPv4
1141   Builder.defineMacro("_M_ARM_FP", "31");
1142 }
1143 
1144 TargetInfo::BuiltinVaListKind
1145 WindowsARMTargetInfo::getBuiltinVaListKind() const {
1146   return TargetInfo::CharPtrBuiltinVaList;
1147 }
1148 
1149 TargetInfo::CallingConvCheckResult
1150 WindowsARMTargetInfo::checkCallingConvention(CallingConv CC) const {
1151   switch (CC) {
1152   case CC_X86StdCall:
1153   case CC_X86ThisCall:
1154   case CC_X86FastCall:
1155   case CC_X86VectorCall:
1156     return CCCR_Ignore;
1157   case CC_C:
1158   case CC_OpenCLKernel:
1159   case CC_PreserveMost:
1160   case CC_PreserveAll:
1161   case CC_Swift:
1162     return CCCR_OK;
1163   default:
1164     return CCCR_Warning;
1165   }
1166 }
1167 
1168 // Windows ARM + Itanium C++ ABI Target
1169 ItaniumWindowsARMleTargetInfo::ItaniumWindowsARMleTargetInfo(
1170     const llvm::Triple &Triple, const TargetOptions &Opts)
1171     : WindowsARMTargetInfo(Triple, Opts) {
1172   TheCXXABI.set(TargetCXXABI::GenericARM);
1173 }
1174 
1175 void ItaniumWindowsARMleTargetInfo::getTargetDefines(
1176     const LangOptions &Opts, MacroBuilder &Builder) const {
1177   WindowsARMTargetInfo::getTargetDefines(Opts, Builder);
1178 
1179   if (Opts.MSVCCompat)
1180     WindowsARMTargetInfo::getVisualStudioDefines(Opts, Builder);
1181 }
1182 
1183 // Windows ARM, MS (C++) ABI
1184 MicrosoftARMleTargetInfo::MicrosoftARMleTargetInfo(const llvm::Triple &Triple,
1185                                                    const TargetOptions &Opts)
1186     : WindowsARMTargetInfo(Triple, Opts) {
1187   TheCXXABI.set(TargetCXXABI::Microsoft);
1188 }
1189 
1190 void MicrosoftARMleTargetInfo::getTargetDefines(const LangOptions &Opts,
1191                                                 MacroBuilder &Builder) const {
1192   WindowsARMTargetInfo::getTargetDefines(Opts, Builder);
1193   WindowsARMTargetInfo::getVisualStudioDefines(Opts, Builder);
1194 }
1195 
1196 MinGWARMTargetInfo::MinGWARMTargetInfo(const llvm::Triple &Triple,
1197                                        const TargetOptions &Opts)
1198     : WindowsARMTargetInfo(Triple, Opts) {
1199   TheCXXABI.set(TargetCXXABI::GenericARM);
1200 }
1201 
1202 void MinGWARMTargetInfo::getTargetDefines(const LangOptions &Opts,
1203                                           MacroBuilder &Builder) const {
1204   WindowsARMTargetInfo::getTargetDefines(Opts, Builder);
1205   Builder.defineMacro("_ARM_");
1206 }
1207 
1208 CygwinARMTargetInfo::CygwinARMTargetInfo(const llvm::Triple &Triple,
1209                                          const TargetOptions &Opts)
1210     : ARMleTargetInfo(Triple, Opts) {
1211   this->WCharType = TargetInfo::UnsignedShort;
1212   TLSSupported = false;
1213   DoubleAlign = LongLongAlign = 64;
1214   resetDataLayout("e-m:e-p:32:32-Fi8-i64:64-v128:64:128-a:0:32-n32-S64");
1215 }
1216 
1217 void CygwinARMTargetInfo::getTargetDefines(const LangOptions &Opts,
1218                                            MacroBuilder &Builder) const {
1219   ARMleTargetInfo::getTargetDefines(Opts, Builder);
1220   Builder.defineMacro("_ARM_");
1221   Builder.defineMacro("__CYGWIN__");
1222   Builder.defineMacro("__CYGWIN32__");
1223   DefineStd(Builder, "unix", Opts);
1224   if (Opts.CPlusPlus)
1225     Builder.defineMacro("_GNU_SOURCE");
1226 }
1227 
1228 DarwinARMTargetInfo::DarwinARMTargetInfo(const llvm::Triple &Triple,
1229                                          const TargetOptions &Opts)
1230     : DarwinTargetInfo<ARMleTargetInfo>(Triple, Opts) {
1231   HasAlignMac68kSupport = true;
1232   // iOS always has 64-bit atomic instructions.
1233   // FIXME: This should be based off of the target features in
1234   // ARMleTargetInfo.
1235   MaxAtomicInlineWidth = 64;
1236 
1237   if (Triple.isWatchABI()) {
1238     // Darwin on iOS uses a variant of the ARM C++ ABI.
1239     TheCXXABI.set(TargetCXXABI::WatchOS);
1240 
1241     // BOOL should be a real boolean on the new ABI
1242     UseSignedCharForObjCBool = false;
1243   } else
1244     TheCXXABI.set(TargetCXXABI::iOS);
1245 }
1246 
1247 void DarwinARMTargetInfo::getOSDefines(const LangOptions &Opts,
1248                                        const llvm::Triple &Triple,
1249                                        MacroBuilder &Builder) const {
1250   getDarwinDefines(Builder, Opts, Triple, PlatformName, PlatformMinVersion);
1251 }
1252 
1253 RenderScript32TargetInfo::RenderScript32TargetInfo(const llvm::Triple &Triple,
1254                                                    const TargetOptions &Opts)
1255     : ARMleTargetInfo(llvm::Triple("armv7", Triple.getVendorName(),
1256                                    Triple.getOSName(),
1257                                    Triple.getEnvironmentName()),
1258                       Opts) {
1259   IsRenderScriptTarget = true;
1260   LongWidth = LongAlign = 64;
1261 }
1262 
1263 void RenderScript32TargetInfo::getTargetDefines(const LangOptions &Opts,
1264                                                 MacroBuilder &Builder) const {
1265   Builder.defineMacro("__RENDERSCRIPT__");
1266   ARMleTargetInfo::getTargetDefines(Opts, Builder);
1267 }
1268