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