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