brintos

brintos / llvm-project-archived public Read only

0
0
Text · 60.4 KiB · d7f36c0 Raw
1839 lines · cpp
1//===--- AArch64.cpp - Implement AArch64 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-exception6//7//===----------------------------------------------------------------------===//8//9// This file implements AArch64 TargetInfo objects.10//11//===----------------------------------------------------------------------===//12 13#include "AArch64.h"14#include "clang/Basic/Diagnostic.h"15#include "clang/Basic/LangOptions.h"16#include "clang/Basic/TargetBuiltins.h"17#include "clang/Basic/TargetInfo.h"18#include "llvm/ADT/APSInt.h"19#include "llvm/ADT/ArrayRef.h"20#include "llvm/ADT/StringSwitch.h"21#include "llvm/TargetParser/AArch64TargetParser.h"22#include "llvm/TargetParser/ARMTargetParserCommon.h"23#include <optional>24 25using namespace clang;26using namespace clang::targets;27 28static constexpr int NumNeonBuiltins =29    NEON::FirstFp16Builtin - Builtin::FirstTSBuiltin;30static constexpr int NumFp16Builtins =31    NEON::FirstTSBuiltin - NEON::FirstFp16Builtin;32static constexpr int NumSVEBuiltins =33    SVE::FirstNeonBridgeBuiltin - NEON::FirstTSBuiltin;34static constexpr int NumSVENeonBridgeBuiltins =35    SVE::FirstTSBuiltin - SVE::FirstNeonBridgeBuiltin;36static constexpr int NumSMEBuiltins = SME::FirstTSBuiltin - SVE::FirstTSBuiltin;37static constexpr int NumAArch64Builtins =38    AArch64::LastTSBuiltin - SME::FirstTSBuiltin;39static constexpr int NumBuiltins =40    AArch64::LastTSBuiltin - Builtin::FirstTSBuiltin;41static_assert(NumBuiltins ==42              (NumNeonBuiltins + NumFp16Builtins + NumSVEBuiltins +43               NumSVENeonBridgeBuiltins + NumSMEBuiltins + NumAArch64Builtins));44 45namespace clang {46namespace NEON {47#define GET_NEON_BUILTIN_STR_TABLE48#include "clang/Basic/arm_neon.inc"49#undef GET_NEON_BUILTIN_STR_TABLE50 51static constexpr std::array<Builtin::Info, NumNeonBuiltins> BuiltinInfos = {52#define GET_NEON_BUILTIN_INFOS53#include "clang/Basic/arm_neon.inc"54#undef GET_NEON_BUILTIN_INFOS55};56 57namespace FP16 {58#define GET_NEON_BUILTIN_STR_TABLE59#include "clang/Basic/arm_fp16.inc"60#undef GET_NEON_BUILTIN_STR_TABLE61 62static constexpr std::array<Builtin::Info, NumFp16Builtins> BuiltinInfos = {63#define GET_NEON_BUILTIN_INFOS64#include "clang/Basic/arm_fp16.inc"65#undef GET_NEON_BUILTIN_INFOS66};67} // namespace FP1668} // namespace NEON69 70namespace SVE {71#define GET_SVE_BUILTIN_STR_TABLE72#include "clang/Basic/arm_sve_builtins.inc"73#undef GET_SVE_BUILTIN_STR_TABLE74 75static constexpr std::array<Builtin::Info, NumSVEBuiltins> BuiltinInfos = {76#define GET_SVE_BUILTIN_INFOS77#include "clang/Basic/arm_sve_builtins.inc"78#undef GET_SVE_BUILTIN_INFOS79};80} // namespace SVE81 82namespace SME {83#define GET_SME_BUILTIN_STR_TABLE84#include "clang/Basic/arm_sme_builtins.inc"85#undef GET_SME_BUILTIN_STR_TABLE86 87static constexpr std::array<Builtin::Info, NumSMEBuiltins> BuiltinInfos = {88#define GET_SME_BUILTIN_INFOS89#include "clang/Basic/arm_sme_builtins.inc"90#undef GET_SME_BUILTIN_INFOS91};92} // namespace SME93} // namespace clang94 95static constexpr llvm::StringTable BuiltinSVENeonBridgeStrings =96    CLANG_BUILTIN_STR_TABLE_START97#define TARGET_BUILTIN CLANG_TARGET_BUILTIN_STR_TABLE98#define GET_SVE_BUILTINS99#include "clang/Basic/BuiltinsAArch64NeonSVEBridge.def"100#undef GET_SVE_BUILTINS101#undef TARGET_BUILTIN102    ;103static constexpr llvm::StringTable BuiltinAArch64Strings =104    CLANG_BUILTIN_STR_TABLE_START105#define BUILTIN CLANG_BUILTIN_STR_TABLE106#define TARGET_BUILTIN CLANG_TARGET_BUILTIN_STR_TABLE107#define TARGET_HEADER_BUILTIN CLANG_TARGET_HEADER_BUILTIN_STR_TABLE108#include "clang/Basic/BuiltinsAArch64.def"109    ;110 111static constexpr auto BuiltinSVENeonBridgeInfos =112    Builtin::MakeInfos<NumSVENeonBridgeBuiltins>({113#define TARGET_BUILTIN CLANG_TARGET_BUILTIN_ENTRY114#define GET_SVE_BUILTINS115#include "clang/Basic/BuiltinsAArch64NeonSVEBridge.def"116#undef GET_SVE_BUILTINS117#undef TARGET_BUILTIN118    });119static constexpr auto BuiltinAArch64Infos =120    Builtin::MakeInfos<NumAArch64Builtins>({121#define BUILTIN CLANG_BUILTIN_ENTRY122#define TARGET_BUILTIN CLANG_TARGET_BUILTIN_ENTRY123#define LANGBUILTIN CLANG_LANGBUILTIN_ENTRY124#define TARGET_HEADER_BUILTIN CLANG_TARGET_HEADER_BUILTIN_ENTRY125#include "clang/Basic/BuiltinsAArch64.def"126    });127 128AArch64TargetInfo::AArch64TargetInfo(const llvm::Triple &Triple,129                                     const TargetOptions &Opts)130    : TargetInfo(Triple), ABI("aapcs") {131  if (getTriple().isOSOpenBSD()) {132    Int64Type = SignedLongLong;133    IntMaxType = SignedLongLong;134  } else {135    if (!getTriple().isOSDarwin() && !getTriple().isOSNetBSD())136      WCharType = UnsignedInt;137 138    Int64Type = SignedLong;139    IntMaxType = SignedLong;140  }141 142  AddrSpaceMap = &ARM64AddrSpaceMap;143 144  // All AArch64 implementations support ARMv8 FP, which makes half a legal type.145  HasFastHalfType = true;146  HalfArgsAndReturns = true;147  HasFloat16 = true;148  HasStrictFP = true;149 150  if (Triple.isArch64Bit())151    LongWidth = LongAlign = PointerWidth = PointerAlign = 64;152  else153    LongWidth = LongAlign = PointerWidth = PointerAlign = 32;154 155  BitIntMaxAlign = 128;156  MaxVectorAlign = 128;157  MaxAtomicInlineWidth = 128;158  MaxAtomicPromoteWidth = 128;159 160  LongDoubleWidth = LongDoubleAlign = SuitableAlign = 128;161  LongDoubleFormat = &llvm::APFloat::IEEEquad();162 163  BFloat16Width = BFloat16Align = 16;164  BFloat16Format = &llvm::APFloat::BFloat();165 166  // Make __builtin_ms_va_list available.167  HasBuiltinMSVaList = true;168 169  // Make the Neon ACLE and SVE types available.  Note that this deliberately170  // doesn't depend on SveMode, since in principle it should be possible to turn171  // SVE on and off within a translation unit.  It should also be possible172  // to compile the global declaration:173  //174  // __SVInt8_t *ptr;175  //176  // even without SVE.177  HasAArch64ACLETypes = true;178 179  // {} in inline assembly are neon specifiers, not assembly variant180  // specifiers.181  NoAsmVariants = true;182 183  // AAPCS gives rules for bitfields. 7.1.7 says: "The container type184  // contributes to the alignment of the containing aggregate in the same way185  // a plain (non bit-field) member of that type would, without exception for186  // zero-sized or anonymous bit-fields."187  assert(UseBitFieldTypeAlignment && "bitfields affect type alignment");188  UseZeroLengthBitfieldAlignment = true;189 190  // AAPCS64 allows any "fundamental integer data type" to be used for191  // over-sized bitfields, which includes 128-bit integers.192  LargestOverSizedBitfieldContainer = 128;193 194  HasUnalignedAccess = true;195 196  // AArch64 targets default to using the ARM C++ ABI.197  TheCXXABI.set(TargetCXXABI::GenericAArch64);198 199  if (Triple.getOS() == llvm::Triple::Linux)200    this->MCountName = "\01_mcount";201  else if (Triple.getOS() == llvm::Triple::UnknownOS)202    this->MCountName =203        Opts.EABIVersion == llvm::EABI::GNU ? "\01_mcount" : "mcount";204}205 206StringRef AArch64TargetInfo::getABI() const { return ABI; }207 208bool AArch64TargetInfo::setABI(const std::string &Name) {209  if (Name != "aapcs" && Name != "aapcs-soft" && Name != "darwinpcs")210    return false;211 212  ABI = Name;213  return true;214}215 216bool AArch64TargetInfo::validateTarget(DiagnosticsEngine &Diags) const {217  if (hasFeature("fp") && ABI == "aapcs-soft") {218    // aapcs-soft is not allowed for targets with an FPU, to avoid there being219    // two incomatible ABIs.220    Diags.Report(diag::err_target_unsupported_abi_with_fpu) << ABI;221    return false;222  }223  return true;224}225 226bool AArch64TargetInfo::validateGlobalRegisterVariable(227    StringRef RegName, unsigned RegSize, bool &HasSizeMismatch) const {228  if (RegName == "sp") {229    HasSizeMismatch = RegSize != 64;230    return true;231  }232  if (RegName.starts_with("w"))233    HasSizeMismatch = RegSize != 32;234  else if (RegName.starts_with("x"))235    HasSizeMismatch = RegSize != 64;236  else237    return false;238  StringRef RegNum = RegName.drop_front();239  // Check if the register is reserved. See also240  // AArch64TargetLowering::getRegisterByName().241  return RegNum == "0" ||242         (RegNum == "18" &&243          llvm::AArch64::isX18ReservedByDefault(getTriple())) ||244         getTargetOpts().FeatureMap.lookup(("reserve-x" + RegNum).str());245}246 247bool AArch64TargetInfo::validateBranchProtection(StringRef Spec, StringRef,248                                                 BranchProtectionInfo &BPI,249                                                 const LangOptions &LO,250                                                 StringRef &Err) const {251  llvm::ARM::ParsedBranchProtection PBP;252  if (!llvm::ARM::parseBranchProtection(Spec, PBP, Err, HasPAuthLR))253    return false;254 255  // GCS is currently untested with ptrauth-returns, but enabling this could be256  // allowed in future after testing with a suitable system.257  if (LO.PointerAuthReturns &&258      (PBP.Scope != "none" || PBP.BranchProtectionPAuthLR ||259       PBP.GuardedControlStack))260    return false;261 262  BPI.SignReturnAddr =263      llvm::StringSwitch<LangOptions::SignReturnAddressScopeKind>(PBP.Scope)264          .Case("non-leaf", LangOptions::SignReturnAddressScopeKind::NonLeaf)265          .Case("all", LangOptions::SignReturnAddressScopeKind::All)266          .Default(LangOptions::SignReturnAddressScopeKind::None);267 268  if (PBP.Key == "a_key")269    BPI.SignKey = LangOptions::SignReturnAddressKeyKind::AKey;270  else271    BPI.SignKey = LangOptions::SignReturnAddressKeyKind::BKey;272 273  BPI.BranchTargetEnforcement = PBP.BranchTargetEnforcement;274  BPI.BranchProtectionPAuthLR = PBP.BranchProtectionPAuthLR;275  BPI.GuardedControlStack = PBP.GuardedControlStack;276  return true;277}278 279bool AArch64TargetInfo::isValidCPUName(StringRef Name) const {280  return llvm::AArch64::parseCpu(Name).has_value();281}282 283bool AArch64TargetInfo::setCPU(const std::string &Name) {284  return isValidCPUName(Name);285}286 287void AArch64TargetInfo::fillValidCPUList(288    SmallVectorImpl<StringRef> &Values) const {289  llvm::AArch64::fillValidCPUArchList(Values);290}291 292void AArch64TargetInfo::getTargetDefinesARMV81A(const LangOptions &Opts,293                                                MacroBuilder &Builder) const {294  Builder.defineMacro("__ARM_FEATURE_QRDMX", "1");295}296 297void AArch64TargetInfo::getTargetDefinesARMV82A(const LangOptions &Opts,298                                                MacroBuilder &Builder) const {299  // Also include the ARMv8.1 defines300  getTargetDefinesARMV81A(Opts, Builder);301}302 303void AArch64TargetInfo::getTargetDefinesARMV83A(const LangOptions &Opts,304                                                MacroBuilder &Builder) const {305  Builder.defineMacro("__ARM_FEATURE_COMPLEX", "1");306  Builder.defineMacro("__ARM_FEATURE_JCVT", "1");307  // Also include the Armv8.2 defines308  getTargetDefinesARMV82A(Opts, Builder);309}310 311void AArch64TargetInfo::getTargetDefinesARMV84A(const LangOptions &Opts,312                                                MacroBuilder &Builder) const {313  // Also include the Armv8.3 defines314  getTargetDefinesARMV83A(Opts, Builder);315}316 317void AArch64TargetInfo::getTargetDefinesARMV85A(const LangOptions &Opts,318                                                MacroBuilder &Builder) const {319  Builder.defineMacro("__ARM_FEATURE_FRINT", "1");320  // Also include the Armv8.4 defines321  getTargetDefinesARMV84A(Opts, Builder);322}323 324void AArch64TargetInfo::getTargetDefinesARMV86A(const LangOptions &Opts,325                                                MacroBuilder &Builder) const {326  // Also include the Armv8.5 defines327  // FIXME: Armv8.6 makes the following extensions mandatory:328  // - __ARM_FEATURE_BF16329  // - __ARM_FEATURE_MATMUL_INT8330  // Handle them here.331  getTargetDefinesARMV85A(Opts, Builder);332}333 334void AArch64TargetInfo::getTargetDefinesARMV87A(const LangOptions &Opts,335                                                MacroBuilder &Builder) const {336  // Also include the Armv8.6 defines337  getTargetDefinesARMV86A(Opts, Builder);338}339 340void AArch64TargetInfo::getTargetDefinesARMV88A(const LangOptions &Opts,341                                                MacroBuilder &Builder) const {342  // Also include the Armv8.7 defines343  getTargetDefinesARMV87A(Opts, Builder);344}345 346void AArch64TargetInfo::getTargetDefinesARMV89A(const LangOptions &Opts,347                                                MacroBuilder &Builder) const {348  // Also include the Armv8.8 defines349  getTargetDefinesARMV88A(Opts, Builder);350}351 352void AArch64TargetInfo::getTargetDefinesARMV9A(const LangOptions &Opts,353                                               MacroBuilder &Builder) const {354  // Armv9-A maps to Armv8.5-A355  getTargetDefinesARMV85A(Opts, Builder);356}357 358void AArch64TargetInfo::getTargetDefinesARMV91A(const LangOptions &Opts,359                                                MacroBuilder &Builder) const {360  // Armv9.1-A maps to Armv8.6-A361  getTargetDefinesARMV86A(Opts, Builder);362}363 364void AArch64TargetInfo::getTargetDefinesARMV92A(const LangOptions &Opts,365                                                MacroBuilder &Builder) const {366  // Armv9.2-A maps to Armv8.7-A367  getTargetDefinesARMV87A(Opts, Builder);368}369 370void AArch64TargetInfo::getTargetDefinesARMV93A(const LangOptions &Opts,371                                                MacroBuilder &Builder) const {372  // Armv9.3-A maps to Armv8.8-A373  getTargetDefinesARMV88A(Opts, Builder);374}375 376void AArch64TargetInfo::getTargetDefinesARMV94A(const LangOptions &Opts,377                                                MacroBuilder &Builder) const {378  // Armv9.4-A maps to Armv8.9-A379  getTargetDefinesARMV89A(Opts, Builder);380}381 382void AArch64TargetInfo::getTargetDefinesARMV95A(const LangOptions &Opts,383                                                MacroBuilder &Builder) const {384  // Armv9.5-A does not have a v8.* equivalent, but is a superset of v9.4-A.385  getTargetDefinesARMV94A(Opts, Builder);386}387 388void AArch64TargetInfo::getTargetDefinesARMV96A(const LangOptions &Opts,389                                                MacroBuilder &Builder) const {390  // Armv9.6-A does not have a v8.* equivalent, but is a superset of v9.5-A.391  getTargetDefinesARMV95A(Opts, Builder);392}393 394void AArch64TargetInfo::getTargetDefinesARMV97A(const LangOptions &Opts,395                                                MacroBuilder &Builder) const {396  // Armv9.7-A does not have a v8.* equivalent, but is a superset of v9.6-A.397  getTargetDefinesARMV96A(Opts, Builder);398}399 400void AArch64TargetInfo::getTargetDefines(const LangOptions &Opts,401                                         MacroBuilder &Builder) const {402  // Target identification.403  if (getTriple().isWindowsArm64EC()) {404    // Define the same set of macros as would be defined on x86_64 to ensure that405    // ARM64EC datatype layouts match those of x86_64 compiled code406    Builder.defineMacro("__amd64__");407    Builder.defineMacro("__amd64");408    Builder.defineMacro("__x86_64");409    Builder.defineMacro("__x86_64__");410    Builder.defineMacro("__arm64ec__");411  } else {412    Builder.defineMacro("__aarch64__");413  }414 415  // Inline assembly supports AArch64 flag outputs.416  Builder.defineMacro("__GCC_ASM_FLAG_OUTPUTS__");417 418  std::string CodeModel = getTargetOpts().CodeModel;419  if (CodeModel == "default")420    CodeModel = "small";421  for (char &c : CodeModel)422    c = toupper(c);423  Builder.defineMacro("__AARCH64_CMODEL_" + CodeModel + "__");424 425  // ACLE predefines. Many can only have one possible value on v8 AArch64.426  Builder.defineMacro("__ARM_ACLE_VERSION(year, quarter, patch)",427                      "(100 * (year) + 10 * (quarter) + (patch))");428#define ARM_ACLE_VERSION(Y, Q, P) (100 * (Y) + 10 * (Q) + (P))429  Builder.defineMacro("__ARM_ACLE", Twine(ARM_ACLE_VERSION(2024, 2, 0)));430  Builder.defineMacro("__FUNCTION_MULTI_VERSIONING_SUPPORT_LEVEL",431                      Twine(ARM_ACLE_VERSION(2024, 3, 0)));432#undef ARM_ACLE_VERSION433  Builder.defineMacro("__ARM_ARCH",434                      std::to_string(ArchInfo->Version.getMajor()));435  Builder.defineMacro("__ARM_ARCH_PROFILE",436                      std::string("'") + (char)ArchInfo->Profile + "'");437 438  Builder.defineMacro("__ARM_64BIT_STATE", "1");439  Builder.defineMacro("__ARM_PCS_AAPCS64", "1");440  Builder.defineMacro("__ARM_ARCH_ISA_A64", "1");441 442  Builder.defineMacro("__ARM_FEATURE_CLZ", "1");443  Builder.defineMacro("__ARM_FEATURE_FMA", "1");444  Builder.defineMacro("__ARM_FEATURE_LDREX", "0xF");445  Builder.defineMacro("__ARM_FEATURE_IDIV", "1"); // As specified in ACLE446  Builder.defineMacro("__ARM_FEATURE_DIV");       // For backwards compatibility447  Builder.defineMacro("__ARM_FEATURE_NUMERIC_MAXMIN", "1");448  Builder.defineMacro("__ARM_FEATURE_DIRECTED_ROUNDING", "1");449 450  Builder.defineMacro("__ARM_ALIGN_MAX_STACK_PWR", "4");451 452  // These macros are set when Clang can parse declarations with these453  // attributes.454  Builder.defineMacro("__ARM_STATE_ZA", "1");455  Builder.defineMacro("__ARM_STATE_ZT0", "1");456 457  // 0xe implies support for half, single and double precision operations.458  if (FPU & FPUMode)459    Builder.defineMacro("__ARM_FP", "0xE");460 461  // PCS specifies this for SysV variants, which is all we support. Other ABIs462  // may choose __ARM_FP16_FORMAT_ALTERNATIVE.463  Builder.defineMacro("__ARM_FP16_FORMAT_IEEE", "1");464  Builder.defineMacro("__ARM_FP16_ARGS", "1");465 466  // Clang supports arm_neon_sve_bridge.h467  Builder.defineMacro("__ARM_NEON_SVE_BRIDGE", "1");468 469  if (Opts.UnsafeFPMath)470    Builder.defineMacro("__ARM_FP_FAST", "1");471 472  Builder.defineMacro("__ARM_SIZEOF_WCHAR_T",473                      Twine(Opts.WCharSize ? Opts.WCharSize : 4));474 475  Builder.defineMacro("__ARM_SIZEOF_MINIMAL_ENUM", Opts.ShortEnums ? "1" : "4");476 477  if (FPU & NeonMode) {478    Builder.defineMacro("__ARM_NEON", "1");479    // 64-bit NEON supports half, single and double precision operations.480    Builder.defineMacro("__ARM_NEON_FP", "0xE");481  }482 483  if (FPU & SveMode)484    Builder.defineMacro("__ARM_FEATURE_SVE", "1");485 486  if (HasSVE2)487    Builder.defineMacro("__ARM_FEATURE_SVE2", "1");488 489  if (HasSVE2p1)490    Builder.defineMacro("__ARM_FEATURE_SVE2p1", "1");491 492  if (HasSVE2 && HasSVEAES)493    Builder.defineMacro("__ARM_FEATURE_SVE2_AES", "1");494 495  if (HasSVE2 && HasSVEBitPerm)496    Builder.defineMacro("__ARM_FEATURE_SVE2_BITPERM", "1");497 498  if (HasSVE2 && HasSVE2SHA3)499    Builder.defineMacro("__ARM_FEATURE_SVE2_SHA3", "1");500 501  if (HasSVE2 && HasSVE2SM4)502    Builder.defineMacro("__ARM_FEATURE_SVE2_SM4", "1");503 504  if (HasSVEB16B16)505    Builder.defineMacro("__ARM_FEATURE_SVE_B16B16", "1");506 507  if (HasSME) {508    Builder.defineMacro("__ARM_FEATURE_SME");509    Builder.defineMacro("__ARM_FEATURE_LOCALLY_STREAMING", "1");510  }511 512  if (HasSME2)513    Builder.defineMacro("__ARM_FEATURE_SME2", "1");514 515  if (HasSME2p1)516    Builder.defineMacro("__ARM_FEATURE_SME2p1", "1");517 518  if (HasSMEF16F16)519    Builder.defineMacro("__ARM_FEATURE_SME_F16F16", "1");520 521  if (HasSMEB16B16)522    Builder.defineMacro("__ARM_FEATURE_SME_B16B16", "1");523 524  if (HasFP8)525    Builder.defineMacro("__ARM_FEATURE_FP8", "1");526 527  if (HasFP8FMA)528    Builder.defineMacro("__ARM_FEATURE_FP8FMA", "1");529 530  if (HasFP8DOT2)531    Builder.defineMacro("__ARM_FEATURE_FP8DOT2", "1");532 533  if (HasFP8DOT4)534    Builder.defineMacro("__ARM_FEATURE_FP8DOT4", "1");535 536  if (HasSSVE_FP8DOT2)537    Builder.defineMacro("__ARM_FEATURE_SSVE_FP8DOT2", "1");538 539  if (HasSSVE_FP8DOT4)540    Builder.defineMacro("__ARM_FEATURE_SSVE_FP8DOT4", "1");541 542  if (HasSSVE_FP8FMA)543    Builder.defineMacro("__ARM_FEATURE_SSVE_FP8FMA", "1");544 545  if (HasSME_F8F32)546    Builder.defineMacro("__ARM_FEATURE_SME_F8F32", "1");547 548  if (HasSME_F8F16)549    Builder.defineMacro("__ARM_FEATURE_SME_F8F16", "1");550 551  if (HasCRC)552    Builder.defineMacro("__ARM_FEATURE_CRC32", "1");553 554  if (HasCSSC)555    Builder.defineMacro("__ARM_FEATURE_CSSC", "1");556 557  if (HasRCPC3)558    Builder.defineMacro("__ARM_FEATURE_RCPC", "3");559  else if (HasRCPC)560    Builder.defineMacro("__ARM_FEATURE_RCPC", "1");561 562  if (HasFMV)563    Builder.defineMacro("__HAVE_FUNCTION_MULTI_VERSIONING", "1");564 565  // The __ARM_FEATURE_CRYPTO is deprecated in favor of finer grained feature566  // macros for AES, SHA2, SHA3 and SM4567  if (HasAES && HasSHA2)568    Builder.defineMacro("__ARM_FEATURE_CRYPTO", "1");569 570  if (HasAES)571    Builder.defineMacro("__ARM_FEATURE_AES", "1");572 573  if (HasSHA2)574    Builder.defineMacro("__ARM_FEATURE_SHA2", "1");575 576  if (HasSHA3) {577    Builder.defineMacro("__ARM_FEATURE_SHA3", "1");578    Builder.defineMacro("__ARM_FEATURE_SHA512", "1");579  }580 581  if (HasSM4) {582    Builder.defineMacro("__ARM_FEATURE_SM3", "1");583    Builder.defineMacro("__ARM_FEATURE_SM4", "1");584  }585 586  if (HasPAuth)587    Builder.defineMacro("__ARM_FEATURE_PAUTH", "1");588 589  if (HasPAuthLR)590    Builder.defineMacro("__ARM_FEATURE_PAUTH_LR", "1");591 592  if (HasBTI)593    Builder.defineMacro("__ARM_FEATURE_BTI", "1");594 595  if (HasUnalignedAccess)596    Builder.defineMacro("__ARM_FEATURE_UNALIGNED", "1");597 598  if ((FPU & NeonMode) && HasFullFP16)599    Builder.defineMacro("__ARM_FEATURE_FP16_VECTOR_ARITHMETIC", "1");600  if (HasFullFP16)601   Builder.defineMacro("__ARM_FEATURE_FP16_SCALAR_ARITHMETIC", "1");602 603  if (HasDotProd)604    Builder.defineMacro("__ARM_FEATURE_DOTPROD", "1");605 606  if (HasMTE)607    Builder.defineMacro("__ARM_FEATURE_MEMORY_TAGGING", "1");608 609  if (HasMatMul)610    Builder.defineMacro("__ARM_FEATURE_MATMUL_INT8", "1");611 612  if (HasLSE)613    Builder.defineMacro("__ARM_FEATURE_ATOMICS", "1");614 615  if (HasBFloat16) {616    Builder.defineMacro("__ARM_FEATURE_BF16", "1");617    Builder.defineMacro("__ARM_FEATURE_BF16_VECTOR_ARITHMETIC", "1");618    Builder.defineMacro("__ARM_BF16_FORMAT_ALTERNATIVE", "1");619    Builder.defineMacro("__ARM_FEATURE_BF16_SCALAR_ARITHMETIC", "1");620  }621 622  if ((FPU & SveMode) && HasBFloat16) {623    Builder.defineMacro("__ARM_FEATURE_SVE_BF16", "1");624  }625 626  if ((FPU & SveMode) && HasMatmulFP64)627    Builder.defineMacro("__ARM_FEATURE_SVE_MATMUL_FP64", "1");628 629  if ((FPU & SveMode) && HasMatmulFP32)630    Builder.defineMacro("__ARM_FEATURE_SVE_MATMUL_FP32", "1");631 632  if ((FPU & SveMode) && HasMatMul)633    Builder.defineMacro("__ARM_FEATURE_SVE_MATMUL_INT8", "1");634 635  if ((FPU & NeonMode) && HasFP16FML)636    Builder.defineMacro("__ARM_FEATURE_FP16_FML", "1");637 638  if (Opts.hasSignReturnAddress()) {639    // Bitmask:640    // 0: Protection using the A key641    // 1: Protection using the B key642    // 2: Protection including leaf functions643    // 3: Protection using PC as a diversifier644    unsigned Value = 0;645 646    if (Opts.isSignReturnAddressWithAKey())647      Value |= (1 << 0);648    else649      Value |= (1 << 1);650 651    if (Opts.isSignReturnAddressScopeAll())652      Value |= (1 << 2);653 654    if (Opts.BranchProtectionPAuthLR)655      Value |= (1 << 3);656 657    Builder.defineMacro("__ARM_FEATURE_PAC_DEFAULT", std::to_string(Value));658  }659 660  if (Opts.BranchTargetEnforcement)661    Builder.defineMacro("__ARM_FEATURE_BTI_DEFAULT", "1");662 663  if (Opts.GuardedControlStack)664    Builder.defineMacro("__ARM_FEATURE_GCS_DEFAULT", "1");665 666  if (HasLS64)667    Builder.defineMacro("__ARM_FEATURE_LS64", "1");668 669  if (HasRandGen)670    Builder.defineMacro("__ARM_FEATURE_RNG", "1");671 672  if (HasMOPS)673    Builder.defineMacro("__ARM_FEATURE_MOPS", "1");674 675  if (HasD128)676    Builder.defineMacro("__ARM_FEATURE_SYSREG128", "1");677 678  if (HasGCS)679    Builder.defineMacro("__ARM_FEATURE_GCS", "1");680 681  if (*ArchInfo == llvm::AArch64::ARMV8_1A)682    getTargetDefinesARMV81A(Opts, Builder);683  else if (*ArchInfo == llvm::AArch64::ARMV8_2A)684    getTargetDefinesARMV82A(Opts, Builder);685  else if (*ArchInfo == llvm::AArch64::ARMV8_3A)686    getTargetDefinesARMV83A(Opts, Builder);687  else if (*ArchInfo == llvm::AArch64::ARMV8_4A)688    getTargetDefinesARMV84A(Opts, Builder);689  else if (*ArchInfo == llvm::AArch64::ARMV8_5A)690    getTargetDefinesARMV85A(Opts, Builder);691  else if (*ArchInfo == llvm::AArch64::ARMV8_6A)692    getTargetDefinesARMV86A(Opts, Builder);693  else if (*ArchInfo == llvm::AArch64::ARMV8_7A)694    getTargetDefinesARMV87A(Opts, Builder);695  else if (*ArchInfo == llvm::AArch64::ARMV8_8A)696    getTargetDefinesARMV88A(Opts, Builder);697  else if (*ArchInfo == llvm::AArch64::ARMV8_9A)698    getTargetDefinesARMV89A(Opts, Builder);699  else if (*ArchInfo == llvm::AArch64::ARMV9A)700    getTargetDefinesARMV9A(Opts, Builder);701  else if (*ArchInfo == llvm::AArch64::ARMV9_1A)702    getTargetDefinesARMV91A(Opts, Builder);703  else if (*ArchInfo == llvm::AArch64::ARMV9_2A)704    getTargetDefinesARMV92A(Opts, Builder);705  else if (*ArchInfo == llvm::AArch64::ARMV9_3A)706    getTargetDefinesARMV93A(Opts, Builder);707  else if (*ArchInfo == llvm::AArch64::ARMV9_4A)708    getTargetDefinesARMV94A(Opts, Builder);709  else if (*ArchInfo == llvm::AArch64::ARMV9_5A)710    getTargetDefinesARMV95A(Opts, Builder);711  else if (*ArchInfo == llvm::AArch64::ARMV9_6A)712    getTargetDefinesARMV96A(Opts, Builder);713  else if (*ArchInfo == llvm::AArch64::ARMV9_7A)714    getTargetDefinesARMV97A(Opts, Builder);715 716  // All of the __sync_(bool|val)_compare_and_swap_(1|2|4|8|16) builtins work.717  Builder.defineMacro("__GCC_HAVE_SYNC_COMPARE_AND_SWAP_1");718  Builder.defineMacro("__GCC_HAVE_SYNC_COMPARE_AND_SWAP_2");719  Builder.defineMacro("__GCC_HAVE_SYNC_COMPARE_AND_SWAP_4");720  Builder.defineMacro("__GCC_HAVE_SYNC_COMPARE_AND_SWAP_8");721  Builder.defineMacro("__GCC_HAVE_SYNC_COMPARE_AND_SWAP_16");722 723  // Allow detection of fast FMA support.724  Builder.defineMacro("__FP_FAST_FMA", "1");725  Builder.defineMacro("__FP_FAST_FMAF", "1");726 727  // C/C++ operators work on both VLS and VLA SVE types728  if (FPU & SveMode)729    Builder.defineMacro("__ARM_FEATURE_SVE_VECTOR_OPERATORS", "2");730 731  if (Opts.VScaleMin && Opts.VScaleMin == Opts.VScaleMax) {732    Builder.defineMacro("__ARM_FEATURE_SVE_BITS", Twine(Opts.VScaleMin * 128));733  }734}735 736llvm::SmallVector<Builtin::InfosShard>737AArch64TargetInfo::getTargetBuiltins() const {738  return {739      {&NEON::BuiltinStrings, NEON::BuiltinInfos, "__builtin_neon_"},740      {&NEON::FP16::BuiltinStrings, NEON::FP16::BuiltinInfos,741       "__builtin_neon_"},742      {&SVE::BuiltinStrings, SVE::BuiltinInfos, "__builtin_sve_"},743      {&BuiltinSVENeonBridgeStrings, BuiltinSVENeonBridgeInfos},744      {&SME::BuiltinStrings, SME::BuiltinInfos, "__builtin_sme_"},745      {&BuiltinAArch64Strings, BuiltinAArch64Infos},746  };747}748 749std::optional<std::pair<unsigned, unsigned>>750AArch64TargetInfo::getVScaleRange(const LangOptions &LangOpts,751                                  ArmStreamingKind Mode,752                                  llvm::StringMap<bool> *FeatureMap) const {753  if (Mode == ArmStreamingKind::NotStreaming &&754      (LangOpts.VScaleMin || LangOpts.VScaleMax))755    return std::pair<unsigned, unsigned>(756        LangOpts.VScaleMin ? LangOpts.VScaleMin : 1,757        LangOpts.VScaleMax ? LangOpts.VScaleMax : 16);758 759  if (Mode == ArmStreamingKind::Streaming &&760      (LangOpts.VScaleStreamingMin || LangOpts.VScaleStreamingMax))761    return std::pair<unsigned, unsigned>(762        LangOpts.VScaleStreamingMin ? LangOpts.VScaleStreamingMin : 1,763        LangOpts.VScaleStreamingMax ? LangOpts.VScaleStreamingMax : 16);764 765  if (Mode == ArmStreamingKind::StreamingCompatible &&766      ((LangOpts.VScaleMin && LangOpts.VScaleStreamingMin) ||767       (LangOpts.VScaleMax && LangOpts.VScaleStreamingMax))) {768    unsigned Min =769        std::min(LangOpts.VScaleMin ? LangOpts.VScaleMin : 1,770                 LangOpts.VScaleStreamingMin ? LangOpts.VScaleStreamingMin : 1);771    unsigned Max = std::max(772        LangOpts.VScaleMax ? LangOpts.VScaleMax : 16,773        LangOpts.VScaleStreamingMax ? LangOpts.VScaleStreamingMax : 16);774    return std::pair(Min, Max);775  }776 777  if (hasFeature("sve") || (FeatureMap && (FeatureMap->lookup("sve"))))778    return std::pair<unsigned, unsigned>(1, 16);779 780  if (Mode == ArmStreamingKind::Streaming &&781      (hasFeature("sme") || (FeatureMap && (FeatureMap->lookup("sme")))))782    return std::pair<unsigned, unsigned>(1, 16);783 784  return std::nullopt;785}786 787llvm::APInt788AArch64TargetInfo::getFMVPriority(ArrayRef<StringRef> Features) const {789  return llvm::AArch64::getFMVPriority(Features);790}791 792bool AArch64TargetInfo::doesFeatureAffectCodeGen(StringRef Name) const {793  // FMV extensions which imply no backend features do not affect codegen.794  if (auto Ext = llvm::AArch64::parseFMVExtension(Name))795    return Ext->ID.has_value();796  return false;797}798 799bool AArch64TargetInfo::validateCpuSupports(StringRef FeatureStr) const {800  // CPU features might be separated by '+', extract them and check801  llvm::SmallVector<StringRef, 8> Features;802  FeatureStr.split(Features, "+");803  for (auto &Feature : Features)804    if (!llvm::AArch64::parseFMVExtension(Feature.trim()).has_value())805      return false;806  return true;807}808 809bool AArch64TargetInfo::hasFeature(StringRef Feature) const {810  return llvm::StringSwitch<bool>(Feature)811      .Cases({"aarch64", "arm64", "arm"}, true)812      .Case("fmv", HasFMV)813      .Case("fp", FPU & FPUMode)814      .Cases({"neon", "simd"}, FPU & NeonMode)815      .Case("jscvt", HasJSCVT)816      .Case("fcma", HasFCMA)817      .Case("rng", HasRandGen)818      .Case("flagm", HasFlagM)819      .Case("flagm2", HasAlternativeNZCV)820      .Case("fp16fml", HasFP16FML)821      .Case("dotprod", HasDotProd)822      .Case("sm4", HasSM4)823      .Case("rdm", HasRDM)824      .Case("lse", HasLSE)825      .Case("crc", HasCRC)826      .Case("cssc", HasCSSC)827      .Case("sha2", HasSHA2)828      .Case("sha3", HasSHA3)829      .Cases({"aes", "pmull"}, HasAES)830      .Cases({"fp16", "fullfp16"}, HasFullFP16)831      .Case("dit", HasDIT)832      .Case("dpb", HasCCPP)833      .Case("dpb2", HasCCDP)834      .Case("rcpc", HasRCPC)835      .Case("frintts", HasFRInt3264)836      .Case("i8mm", HasMatMul)837      .Case("bf16", HasBFloat16)838      .Case("sve", FPU & SveMode)839      .Case("sve-b16b16", HasSVEB16B16)840      .Case("f32mm", FPU & SveMode && HasMatmulFP32)841      .Case("f64mm", FPU & SveMode && HasMatmulFP64)842      .Case("sve2", FPU & SveMode && HasSVE2)843      .Case("sve-aes", HasSVEAES)844      .Case("sve-bitperm", FPU & HasSVEBitPerm)845      .Case("sve2-sha3", FPU & SveMode && HasSVE2SHA3)846      .Case("sve2-sm4", FPU & SveMode && HasSVE2SM4)847      .Case("sve2p1", FPU & SveMode && HasSVE2p1)848      .Case("sme", HasSME)849      .Case("sme2", HasSME2)850      .Case("sme2p1", HasSME2p1)851      .Case("sme-f64f64", HasSMEF64F64)852      .Case("sme-i16i64", HasSMEI16I64)853      .Case("sme-fa64", HasSMEFA64)854      .Case("sme-f16f16", HasSMEF16F16)855      .Case("sme-b16b16", HasSMEB16B16)856      .Case("memtag", HasMTE)857      .Case("sb", HasSB)858      .Case("predres", HasPredRes)859      .Cases({"ssbs", "ssbs2"}, HasSSBS)860      .Case("bti", HasBTI)861      .Cases({"ls64", "ls64_v", "ls64_accdata"}, HasLS64)862      .Case("wfxt", HasWFxT)863      .Case("rcpc3", HasRCPC3)864      .Case("fp8", HasFP8)865      .Case("fp8fma", HasFP8FMA)866      .Case("fp8dot2", HasFP8DOT2)867      .Case("fp8dot4", HasFP8DOT4)868      .Case("ssve-fp8dot2", HasSSVE_FP8DOT2)869      .Case("ssve-fp8dot4", HasSSVE_FP8DOT4)870      .Case("ssve-fp8fma", HasSSVE_FP8FMA)871      .Case("sme-f8f32", HasSME_F8F32)872      .Case("sme-f8f16", HasSME_F8F16)873      .Default(false);874}875 876void AArch64TargetInfo::setFeatureEnabled(llvm::StringMap<bool> &Features,877                                          StringRef Name, bool Enabled) const {878  Features[Name] = Enabled;879  // If the feature is an architecture feature (like v8.2a), add all previous880  // architecture versions and any dependant target features.881  const std::optional<llvm::AArch64::ArchInfo> ArchInfo =882      llvm::AArch64::ArchInfo::findBySubArch(Name);883 884  if (!ArchInfo)885    return; // Not an architecture, nothing more to do.886 887  // Disabling an architecture feature does not affect dependent features888  if (!Enabled)889    return;890 891  for (const auto *OtherArch : llvm::AArch64::ArchInfos)892    if (ArchInfo->implies(*OtherArch))893      Features[OtherArch->getSubArch()] = true;894 895  // Set any features implied by the architecture896  std::vector<StringRef> CPUFeats;897  if (llvm::AArch64::getExtensionFeatures(ArchInfo->DefaultExts, CPUFeats)) {898    for (auto F : CPUFeats) {899      assert(F[0] == '+' && "Expected + in target feature!");900      Features[F.drop_front(1)] = true;901    }902  }903}904 905bool AArch64TargetInfo::handleTargetFeatures(std::vector<std::string> &Features,906                                             DiagnosticsEngine &Diags) {907  for (const auto &Feature : Features) {908    if (Feature == "-fp-armv8")909      HasNoFP = true;910    if (Feature == "-neon")911      HasNoNeon = true;912    if (Feature == "-sve")913      HasNoSVE = true;914 915    if (Feature == "+neon" || Feature == "+fp-armv8")916      FPU |= NeonMode;917    if (Feature == "+jscvt") {918      HasJSCVT = true;919      FPU |= NeonMode;920    }921    if (Feature == "+fcma") {922      HasFCMA = true;923      FPU |= NeonMode;924    }925 926    if (Feature == "+sve") {927      FPU |= NeonMode;928      FPU |= SveMode;929      HasFullFP16 = true;930    }931    if (Feature == "+sve2") {932      FPU |= NeonMode;933      FPU |= SveMode;934      HasFullFP16 = true;935      HasSVE2 = true;936    }937    if (Feature == "+sve2p1") {938      FPU |= NeonMode;939      FPU |= SveMode;940      HasFullFP16 = true;941      HasSVE2 = true;942      HasSVE2p1 = true;943    }944    if (Feature == "+sve-aes") {945      FPU |= NeonMode;946      HasFullFP16 = true;947      HasSVEAES = true;948    }949    if (Feature == "+sve2-sha3") {950      FPU |= NeonMode;951      FPU |= SveMode;952      HasFullFP16 = true;953      HasSVE2 = true;954      HasSVE2SHA3 = true;955    }956    if (Feature == "+sve2-sm4") {957      FPU |= NeonMode;958      FPU |= SveMode;959      HasFullFP16 = true;960      HasSVE2 = true;961      HasSVE2SM4 = true;962    }963    if (Feature == "+sve-b16b16")964      HasSVEB16B16 = true;965    if (Feature == "+sve-bitperm") {966      FPU |= NeonMode;967      HasFullFP16 = true;968      HasSVEBitPerm = true;969    }970    if (Feature == "+f32mm") {971      FPU |= NeonMode;972      FPU |= SveMode;973      HasFullFP16 = true;974      HasMatmulFP32 = true;975    }976    if (Feature == "+f64mm") {977      FPU |= NeonMode;978      FPU |= SveMode;979      HasFullFP16 = true;980      HasMatmulFP64 = true;981    }982    if (Feature == "+sme") {983      HasSME = true;984      HasBFloat16 = true;985      HasFullFP16 = true;986    }987    if (Feature == "+sme2") {988      HasSME = true;989      HasSME2 = true;990      HasBFloat16 = true;991      HasFullFP16 = true;992    }993    if (Feature == "+sme2p1") {994      HasSME = true;995      HasSME2 = true;996      HasSME2p1 = true;997      HasBFloat16 = true;998      HasFullFP16 = true;999    }1000    if (Feature == "+sme-f64f64") {1001      HasSME = true;1002      HasSMEF64F64 = true;1003      HasBFloat16 = true;1004      HasFullFP16 = true;1005    }1006    if (Feature == "+sme-i16i64") {1007      HasSME = true;1008      HasSMEI16I64 = true;1009      HasBFloat16 = true;1010      HasFullFP16 = true;1011    }1012    if (Feature == "+sme-fa64") {1013      FPU |= NeonMode;1014      FPU |= SveMode;1015      HasSME = true;1016      HasSVE2 = true;1017      HasSMEFA64 = true;1018    }1019    if (Feature == "+sme-f16f16") {1020      HasSME = true;1021      HasSME2 = true;1022      HasBFloat16 = true;1023      HasFullFP16 = true;1024      HasSMEF16F16 = true;1025    }1026    if (Feature == "+sme-b16b16") {1027      HasSME = true;1028      HasSME2 = true;1029      HasBFloat16 = true;1030      HasFullFP16 = true;1031      HasSVEB16B16 = true;1032      HasSMEB16B16 = true;1033    }1034 1035    if (Feature == "+fp8")1036      HasFP8 = true;1037    if (Feature == "+fp8fma")1038      HasFP8FMA = true;1039    if (Feature == "+fp8dot2")1040      HasFP8DOT2 = true;1041    if (Feature == "+fp8dot4")1042      HasFP8DOT4 = true;1043    if (Feature == "+ssve-fp8dot2")1044      HasSSVE_FP8DOT2 = true;1045    if (Feature == "+ssve-fp8dot4")1046      HasSSVE_FP8DOT4 = true;1047    if (Feature == "+ssve-fp8fma")1048      HasSSVE_FP8FMA = true;1049    if (Feature == "+sme-f8f32")1050      HasSME_F8F32 = true;1051    if (Feature == "+sme-f8f16")1052      HasSME_F8F16 = true;1053    if (Feature == "+sb")1054      HasSB = true;1055    if (Feature == "+predres")1056      HasPredRes = true;1057    if (Feature == "+ssbs")1058      HasSSBS = true;1059    if (Feature == "+bti")1060      HasBTI = true;1061    if (Feature == "+wfxt")1062      HasWFxT = true;1063    if (Feature == "-fmv")1064      HasFMV = false;1065    if (Feature == "+crc")1066      HasCRC = true;1067    if (Feature == "+rcpc")1068      HasRCPC = true;1069    if (Feature == "+aes") {1070      FPU |= NeonMode;1071      HasAES = true;1072    }1073    if (Feature == "+sha2") {1074      FPU |= NeonMode;1075      HasSHA2 = true;1076    }1077    if (Feature == "+sha3") {1078      FPU |= NeonMode;1079      HasSHA2 = true;1080      HasSHA3 = true;1081    }1082    if (Feature == "+rdm") {1083      FPU |= NeonMode;1084      HasRDM = true;1085    }1086    if (Feature == "+dit")1087      HasDIT = true;1088    if (Feature == "+cccp")1089      HasCCPP = true;1090    if (Feature == "+ccdp") {1091      HasCCPP = true;1092      HasCCDP = true;1093    }1094    if (Feature == "+fptoint")1095      HasFRInt3264 = true;1096    if (Feature == "+sm4") {1097      FPU |= NeonMode;1098      HasSM4 = true;1099    }1100    if (Feature == "+strict-align")1101      HasUnalignedAccess = false;1102 1103    // All predecessor archs are added but select the latest one for ArchKind.1104    if (Feature == "+v8a" && ArchInfo->Version < llvm::AArch64::ARMV8A.Version)1105      ArchInfo = &llvm::AArch64::ARMV8A;1106    if (Feature == "+v8.1a" &&1107        ArchInfo->Version < llvm::AArch64::ARMV8_1A.Version)1108      ArchInfo = &llvm::AArch64::ARMV8_1A;1109    if (Feature == "+v8.2a" &&1110        ArchInfo->Version < llvm::AArch64::ARMV8_2A.Version)1111      ArchInfo = &llvm::AArch64::ARMV8_2A;1112    if (Feature == "+v8.3a" &&1113        ArchInfo->Version < llvm::AArch64::ARMV8_3A.Version)1114      ArchInfo = &llvm::AArch64::ARMV8_3A;1115    if (Feature == "+v8.4a" &&1116        ArchInfo->Version < llvm::AArch64::ARMV8_4A.Version)1117      ArchInfo = &llvm::AArch64::ARMV8_4A;1118    if (Feature == "+v8.5a" &&1119        ArchInfo->Version < llvm::AArch64::ARMV8_5A.Version)1120      ArchInfo = &llvm::AArch64::ARMV8_5A;1121    if (Feature == "+v8.6a" &&1122        ArchInfo->Version < llvm::AArch64::ARMV8_6A.Version)1123      ArchInfo = &llvm::AArch64::ARMV8_6A;1124    if (Feature == "+v8.7a" &&1125        ArchInfo->Version < llvm::AArch64::ARMV8_7A.Version)1126      ArchInfo = &llvm::AArch64::ARMV8_7A;1127    if (Feature == "+v8.8a" &&1128        ArchInfo->Version < llvm::AArch64::ARMV8_8A.Version)1129      ArchInfo = &llvm::AArch64::ARMV8_8A;1130    if (Feature == "+v8.9a" &&1131        ArchInfo->Version < llvm::AArch64::ARMV8_9A.Version)1132      ArchInfo = &llvm::AArch64::ARMV8_9A;1133    if (Feature == "+v9a" && ArchInfo->Version < llvm::AArch64::ARMV9A.Version)1134      ArchInfo = &llvm::AArch64::ARMV9A;1135    if (Feature == "+v9.1a" &&1136        ArchInfo->Version < llvm::AArch64::ARMV9_1A.Version)1137      ArchInfo = &llvm::AArch64::ARMV9_1A;1138    if (Feature == "+v9.2a" &&1139        ArchInfo->Version < llvm::AArch64::ARMV9_2A.Version)1140      ArchInfo = &llvm::AArch64::ARMV9_2A;1141    if (Feature == "+v9.3a" &&1142        ArchInfo->Version < llvm::AArch64::ARMV9_3A.Version)1143      ArchInfo = &llvm::AArch64::ARMV9_3A;1144    if (Feature == "+v9.4a" &&1145        ArchInfo->Version < llvm::AArch64::ARMV9_4A.Version)1146      ArchInfo = &llvm::AArch64::ARMV9_4A;1147    if (Feature == "+v9.5a" &&1148        ArchInfo->Version < llvm::AArch64::ARMV9_5A.Version)1149      ArchInfo = &llvm::AArch64::ARMV9_5A;1150    if (Feature == "+v9.6a" &&1151        ArchInfo->Version < llvm::AArch64::ARMV9_6A.Version)1152      ArchInfo = &llvm::AArch64::ARMV9_6A;1153    if (Feature == "+v9.7a" &&1154        ArchInfo->Version < llvm::AArch64::ARMV9_7A.Version)1155      ArchInfo = &llvm::AArch64::ARMV9_7A;1156    if (Feature == "+v8r")1157      ArchInfo = &llvm::AArch64::ARMV8R;1158    if (Feature == "+fullfp16") {1159      FPU |= NeonMode;1160      HasFullFP16 = true;1161    }1162    if (Feature == "+dotprod") {1163      FPU |= NeonMode;1164      HasDotProd = true;1165    }1166    if (Feature == "+fp16fml") {1167      FPU |= NeonMode;1168      HasFullFP16 = true;1169      HasFP16FML = true;1170    }1171    if (Feature == "+mte")1172      HasMTE = true;1173    if (Feature == "+pauth")1174      HasPAuth = true;1175    if (Feature == "+i8mm")1176      HasMatMul = true;1177    if (Feature == "+bf16")1178      HasBFloat16 = true;1179    if (Feature == "+lse")1180      HasLSE = true;1181    if (Feature == "+ls64")1182      HasLS64 = true;1183    if (Feature == "+rand")1184      HasRandGen = true;1185    if (Feature == "+flagm")1186      HasFlagM = true;1187    if (Feature == "+altnzcv") {1188      HasFlagM = true;1189      HasAlternativeNZCV = true;1190    }1191    if (Feature == "+mops")1192      HasMOPS = true;1193    if (Feature == "+d128")1194      HasD128 = true;1195    if (Feature == "+gcs")1196      HasGCS = true;1197    if (Feature == "+rcpc3")1198      HasRCPC3 = true;1199    if (Feature == "+pauth-lr") {1200      HasPAuthLR = true;1201      HasPAuth = true;1202    }1203    if (Feature == "+cssc")1204      HasCSSC = true;1205  }1206 1207  // Check features that are manually disabled by command line options.1208  // This needs to be checked after architecture-related features are handled,1209  // making sure they are properly disabled when required.1210  for (const auto &Feature : Features) {1211    if (Feature == "-d128")1212      HasD128 = false;1213  }1214 1215  setDataLayout();1216 1217  if (HasNoFP) {1218    FPU &= ~FPUMode;1219    FPU &= ~NeonMode;1220    FPU &= ~SveMode;1221  }1222  if (HasNoNeon) {1223    FPU &= ~NeonMode;1224    FPU &= ~SveMode;1225  }1226  if (HasNoSVE)1227    FPU &= ~SveMode;1228 1229  return true;1230}1231 1232// Parse AArch64 Target attributes, which are a comma separated list of:1233//  "arch=<arch>" - parsed to features as per -march=..1234//  "cpu=<cpu>" - parsed to features as per -mcpu=.., with CPU set to <cpu>1235//  "tune=<cpu>" - TuneCPU set to <cpu>1236//  "feature", "no-feature" - Add (or remove) feature.1237//  "+feature", "+nofeature" - Add (or remove) feature.1238//1239// A feature may correspond to an Extension (anything with a corresponding1240// AEK_), in which case an ExtensionSet is used to parse it and expand its1241// dependencies. If the feature does not yield a successful parse then it1242// is passed through.1243ParsedTargetAttr AArch64TargetInfo::parseTargetAttr(StringRef Features) const {1244  ParsedTargetAttr Ret;1245  if (Features == "default")1246    return Ret;1247  SmallVector<StringRef, 1> AttrFeatures;1248  Features.split(AttrFeatures, ",");1249  bool FoundArch = false;1250 1251  auto SplitAndAddFeatures = [](StringRef FeatString,1252                                std::vector<std::string> &Features,1253                                llvm::AArch64::ExtensionSet &FeatureBits) {1254    SmallVector<StringRef, 8> SplitFeatures;1255    FeatString.split(SplitFeatures, StringRef("+"), -1, false);1256    for (StringRef Feature : SplitFeatures) {1257      if (FeatureBits.parseModifier(Feature))1258        continue;1259      // Pass through anything that failed to parse so that we can emit1260      // diagnostics, as well as valid internal feature names.1261      //1262      // FIXME: We should consider rejecting internal feature names like1263      //        neon, v8a, etc.1264      // FIXME: We should consider emitting diagnostics here.1265      if (Feature.starts_with("no"))1266        Features.push_back("-" + Feature.drop_front(2).str());1267      else1268        Features.push_back("+" + Feature.str());1269    }1270  };1271 1272  llvm::AArch64::ExtensionSet FeatureBits;1273  // Reconstruct the bitset from the command line option features.1274  FeatureBits.reconstructFromParsedFeatures(getTargetOpts().FeaturesAsWritten,1275                                            Ret.Features);1276 1277  for (auto &Feature : AttrFeatures) {1278    Feature = Feature.trim();1279    if (Feature.starts_with("fpmath="))1280      continue;1281 1282    if (Feature.starts_with("branch-protection=")) {1283      Ret.BranchProtection = Feature.split('=').second.trim();1284      continue;1285    }1286 1287    if (Feature.starts_with("arch=")) {1288      if (FoundArch)1289        Ret.Duplicate = "arch=";1290      FoundArch = true;1291      std::pair<StringRef, StringRef> Split =1292          Feature.split("=").second.trim().split("+");1293      const llvm::AArch64::ArchInfo *AI = llvm::AArch64::parseArch(Split.first);1294 1295      // Parse the architecture version, adding the required features to1296      // Ret.Features.1297      if (!AI)1298        continue;1299      FeatureBits.addArchDefaults(*AI);1300      // Add any extra features, after the +1301      SplitAndAddFeatures(Split.second, Ret.Features, FeatureBits);1302    } else if (Feature.starts_with("cpu=")) {1303      if (!Ret.CPU.empty())1304        Ret.Duplicate = "cpu=";1305      else {1306        // Split the cpu string into "cpu=", "cortex-a710" and any remaining1307        // "+feat" features.1308        std::pair<StringRef, StringRef> Split =1309            Feature.split("=").second.trim().split("+");1310        Ret.CPU = Split.first;1311        if (auto CpuInfo = llvm::AArch64::parseCpu(Ret.CPU)) {1312          FeatureBits.addCPUDefaults(*CpuInfo);1313          SplitAndAddFeatures(Split.second, Ret.Features, FeatureBits);1314        }1315      }1316    } else if (Feature.starts_with("tune=")) {1317      if (!Ret.Tune.empty())1318        Ret.Duplicate = "tune=";1319      else1320        Ret.Tune = Feature.split("=").second.trim();1321    } else if (Feature.starts_with("+")) {1322      SplitAndAddFeatures(Feature, Ret.Features, FeatureBits);1323    } else {1324      if (FeatureBits.parseModifier(Feature, /* AllowNoDashForm = */ true))1325        continue;1326      // Pass through anything that failed to parse so that we can emit1327      // diagnostics, as well as valid internal feature names.1328      //1329      // FIXME: We should consider rejecting internal feature names like1330      //        neon, v8a, etc.1331      // FIXME: We should consider emitting diagnostics here.1332      if (Feature.starts_with("no-"))1333        Ret.Features.push_back("-" + Feature.drop_front(3).str());1334      else1335        Ret.Features.push_back("+" + Feature.str());1336    }1337  }1338  FeatureBits.toLLVMFeatureList(Ret.Features);1339  return Ret;1340}1341 1342bool AArch64TargetInfo::hasBFloat16Type() const {1343  return true;1344}1345 1346TargetInfo::CallingConvCheckResult1347AArch64TargetInfo::checkCallingConvention(CallingConv CC) const {1348  switch (CC) {1349  case CC_C:1350  case CC_Swift:1351  case CC_SwiftAsync:1352  case CC_PreserveMost:1353  case CC_PreserveAll:1354  case CC_PreserveNone:1355  case CC_DeviceKernel:1356  case CC_AArch64VectorCall:1357  case CC_AArch64SVEPCS:1358  case CC_Win64:1359    return CCCR_OK;1360  default:1361    return CCCR_Warning;1362  }1363}1364 1365bool AArch64TargetInfo::isCLZForZeroUndef() const { return false; }1366 1367TargetInfo::BuiltinVaListKind AArch64TargetInfo::getBuiltinVaListKind() const {1368  return TargetInfo::AArch64ABIBuiltinVaList;1369}1370 1371const char *const AArch64TargetInfo::GCCRegNames[] = {1372    // clang-format off1373 1374    // 32-bit Integer registers1375    "w0", "w1", "w2", "w3", "w4", "w5", "w6", "w7", "w8", "w9", "w10", "w11",1376    "w12", "w13", "w14", "w15", "w16", "w17", "w18", "w19", "w20", "w21", "w22",1377    "w23", "w24", "w25", "w26", "w27", "w28", "w29", "w30", "wsp",1378 1379    // 64-bit Integer registers1380    "x0", "x1", "x2", "x3", "x4", "x5", "x6", "x7", "x8", "x9", "x10", "x11",1381    "x12", "x13", "x14", "x15", "x16", "x17", "x18", "x19", "x20", "x21", "x22",1382    "x23", "x24", "x25", "x26", "x27", "x28", "fp", "lr", "sp",1383 1384    // 32-bit floating point regsisters1385    "s0", "s1", "s2", "s3", "s4", "s5", "s6", "s7", "s8", "s9", "s10", "s11",1386    "s12", "s13", "s14", "s15", "s16", "s17", "s18", "s19", "s20", "s21", "s22",1387    "s23", "s24", "s25", "s26", "s27", "s28", "s29", "s30", "s31",1388 1389    // 64-bit floating point regsisters1390    "d0", "d1", "d2", "d3", "d4", "d5", "d6", "d7", "d8", "d9", "d10", "d11",1391    "d12", "d13", "d14", "d15", "d16", "d17", "d18", "d19", "d20", "d21", "d22",1392    "d23", "d24", "d25", "d26", "d27", "d28", "d29", "d30", "d31",1393 1394    // Neon vector registers1395    "v0", "v1", "v2", "v3", "v4", "v5", "v6", "v7", "v8", "v9", "v10", "v11",1396    "v12", "v13", "v14", "v15", "v16", "v17", "v18", "v19", "v20", "v21", "v22",1397    "v23", "v24", "v25", "v26", "v27", "v28", "v29", "v30", "v31",1398 1399    // SVE vector registers1400    "z0",  "z1",  "z2",  "z3",  "z4",  "z5",  "z6",  "z7",  "z8",  "z9",  "z10",1401    "z11", "z12", "z13", "z14", "z15", "z16", "z17", "z18", "z19", "z20", "z21",1402    "z22", "z23", "z24", "z25", "z26", "z27", "z28", "z29", "z30", "z31",1403 1404    // SVE predicate registers1405    "p0",  "p1",  "p2",  "p3",  "p4",  "p5",  "p6",  "p7",  "p8",  "p9",  "p10",1406    "p11", "p12", "p13", "p14", "p15",1407 1408    // SVE predicate-as-counter registers1409    "pn0",  "pn1",  "pn2",  "pn3",  "pn4",  "pn5",  "pn6",  "pn7",  "pn8",1410    "pn9",  "pn10", "pn11", "pn12", "pn13", "pn14", "pn15",1411 1412    // SME registers1413    "za", "zt0",1414 1415    // clang-format on1416};1417 1418ArrayRef<const char *> AArch64TargetInfo::getGCCRegNames() const {1419  return llvm::ArrayRef(GCCRegNames);1420}1421 1422const TargetInfo::GCCRegAlias AArch64TargetInfo::GCCRegAliases[] = {1423    {{"w31"}, "wsp"},1424    {{"x31"}, "sp"},1425    // GCC rN registers are aliases of xN registers.1426    {{"r0"}, "x0"},1427    {{"r1"}, "x1"},1428    {{"r2"}, "x2"},1429    {{"r3"}, "x3"},1430    {{"r4"}, "x4"},1431    {{"r5"}, "x5"},1432    {{"r6"}, "x6"},1433    {{"r7"}, "x7"},1434    {{"r8"}, "x8"},1435    {{"r9"}, "x9"},1436    {{"r10"}, "x10"},1437    {{"r11"}, "x11"},1438    {{"r12"}, "x12"},1439    {{"r13"}, "x13"},1440    {{"r14"}, "x14"},1441    {{"r15"}, "x15"},1442    {{"r16"}, "x16"},1443    {{"r17"}, "x17"},1444    {{"r18"}, "x18"},1445    {{"r19"}, "x19"},1446    {{"r20"}, "x20"},1447    {{"r21"}, "x21"},1448    {{"r22"}, "x22"},1449    {{"r23"}, "x23"},1450    {{"r24"}, "x24"},1451    {{"r25"}, "x25"},1452    {{"r26"}, "x26"},1453    {{"r27"}, "x27"},1454    {{"r28"}, "x28"},1455    {{"r29", "x29"}, "fp"},1456    {{"r30", "x30"}, "lr"},1457    // The S/D/Q and W/X registers overlap, but aren't really aliases; we1458    // don't want to substitute one of these for a different-sized one.1459};1460 1461ArrayRef<TargetInfo::GCCRegAlias> AArch64TargetInfo::getGCCRegAliases() const {1462  return llvm::ArrayRef(GCCRegAliases);1463}1464 1465// Returns the length of cc constraint.1466static unsigned matchAsmCCConstraint(const char *Name) {1467  constexpr unsigned len = 5;1468  auto RV = llvm::StringSwitch<unsigned>(Name)1469                .Case("@cceq", len)1470                .Case("@ccne", len)1471                .Case("@cchs", len)1472                .Case("@cccs", len)1473                .Case("@cccc", len)1474                .Case("@cclo", len)1475                .Case("@ccmi", len)1476                .Case("@ccpl", len)1477                .Case("@ccvs", len)1478                .Case("@ccvc", len)1479                .Case("@cchi", len)1480                .Case("@ccls", len)1481                .Case("@ccge", len)1482                .Case("@cclt", len)1483                .Case("@ccgt", len)1484                .Case("@ccle", len)1485                .Default(0);1486  return RV;1487}1488 1489std::string1490AArch64TargetInfo::convertConstraint(const char *&Constraint) const {1491  std::string R;1492  switch (*Constraint) {1493  case 'U': // Three-character constraint; add "@3" hint for later parsing.1494    R = std::string("@3") + std::string(Constraint, 3);1495    Constraint += 2;1496    break;1497  case '@':1498    if (const unsigned Len = matchAsmCCConstraint(Constraint)) {1499      std::string Converted = "{" + std::string(Constraint, Len) + "}";1500      Constraint += Len - 1;1501      return Converted;1502    }1503    return std::string(1, *Constraint);1504  default:1505    R = TargetInfo::convertConstraint(Constraint);1506    break;1507  }1508  return R;1509}1510 1511bool AArch64TargetInfo::validateAsmConstraint(1512    const char *&Name, TargetInfo::ConstraintInfo &Info) const {1513  switch (*Name) {1514  default:1515    return false;1516  case 'w': // Floating point and SIMD registers (V0-V31)1517    Info.setAllowsRegister();1518    return true;1519  case 'I': // Constant that can be used with an ADD instruction1520  case 'J': // Constant that can be used with a SUB instruction1521  case 'K': // Constant that can be used with a 32-bit logical instruction1522  case 'L': // Constant that can be used with a 64-bit logical instruction1523  case 'M': // Constant that can be used as a 32-bit MOV immediate1524  case 'N': // Constant that can be used as a 64-bit MOV immediate1525  case 'Y': // Floating point constant zero1526  case 'Z': // Integer constant zero1527    return true;1528  case 'Q': // A memory reference with base register and no offset1529    Info.setAllowsMemory();1530    return true;1531  case 'S': // A symbolic address1532    Info.setAllowsRegister();1533    return true;1534  case 'U':1535    if (Name[1] == 'p' &&1536        (Name[2] == 'l' || Name[2] == 'a' || Name[2] == 'h')) {1537      // SVE predicate registers ("Upa"=P0-15, "Upl"=P0-P7, "Uph"=P8-P15)1538      Info.setAllowsRegister();1539      Name += 2;1540      return true;1541    }1542    if (Name[1] == 'c' && (Name[2] == 'i' || Name[2] == 'j')) {1543      // Gpr registers ("Uci"=w8-11, "Ucj"=w12-15)1544      Info.setAllowsRegister();1545      Name += 2;1546      return true;1547    }1548    // Ump: A memory address suitable for ldp/stp in SI, DI, SF and DF modes.1549    // Utf: A memory address suitable for ldp/stp in TF mode.1550    // Usa: An absolute symbolic address.1551    // Ush: The high part (bits 32:12) of a pc-relative symbolic address.1552 1553    // Better to return an error saying that it's an unrecognised constraint1554    // even if this is a valid constraint in gcc.1555    return false;1556  case 'z': // Zero register, wzr or xzr1557    Info.setAllowsRegister();1558    return true;1559  case 'x': // Floating point and SIMD registers (V0-V15)1560    Info.setAllowsRegister();1561    return true;1562  case 'y': // SVE registers (V0-V7)1563    Info.setAllowsRegister();1564    return true;1565  case '@':1566    // CC condition1567    if (const unsigned Len = matchAsmCCConstraint(Name)) {1568      Name += Len - 1;1569      Info.setAllowsRegister();1570      Info.setOutputOperandBounds(0, 2);1571      return true;1572    }1573  }1574  return false;1575}1576 1577bool AArch64TargetInfo::validateConstraintModifier(1578    StringRef Constraint, char Modifier, unsigned Size,1579    std::string &SuggestedModifier) const {1580  // Strip off constraint modifiers.1581  Constraint = Constraint.ltrim("=+&");1582 1583  switch (Constraint[0]) {1584  default:1585    return true;1586  case 'z':1587  case 'r': {1588    switch (Modifier) {1589    case 'x':1590    case 'w':1591      // For now assume that the person knows what they're1592      // doing with the modifier.1593      return true;1594    default:1595      // By default an 'r' constraint will be in the 'x'1596      // registers.1597      if (Size == 64)1598        return true;1599 1600      if (Size == 512)1601        return HasLS64;1602 1603      SuggestedModifier = "w";1604      return false;1605    }1606  }1607  }1608}1609 1610std::string_view AArch64TargetInfo::getClobbers() const { return ""; }1611 1612int AArch64TargetInfo::getEHDataRegisterNumber(unsigned RegNo) const {1613  if (RegNo == 0)1614    return 0;1615  if (RegNo == 1)1616    return 1;1617  return -1;1618}1619 1620bool AArch64TargetInfo::validatePointerAuthKey(1621    const llvm::APSInt &value) const {1622  return 0 <= value && value <= 3;1623}1624 1625bool AArch64TargetInfo::hasInt128Type() const { return true; }1626 1627AArch64leTargetInfo::AArch64leTargetInfo(const llvm::Triple &Triple,1628                                         const TargetOptions &Opts)1629    : AArch64TargetInfo(Triple, Opts) {}1630 1631void AArch64leTargetInfo::setDataLayout() {1632  if (getTriple().isOSBinFormatMachO()) {1633    if(getTriple().isArch32Bit())1634      resetDataLayout("e-m:o-p:32:32-p270:32:32-p271:32:32-p272:64:64-i64:64-"1635                      "i128:128-n32:64-S128-Fn32",1636                      "_");1637    else1638      resetDataLayout("e-m:o-p270:32:32-p271:32:32-p272:64:64-i64:64-i128:128-"1639                      "n32:64-S128-Fn32",1640                      "_");1641  } else1642    resetDataLayout("e-m:e-p270:32:32-p271:32:32-p272:64:64-i8:8:32-i16:16:32-"1643                    "i64:64-i128:128-n32:64-S128-Fn32");1644}1645 1646void AArch64leTargetInfo::getTargetDefines(const LangOptions &Opts,1647                                           MacroBuilder &Builder) const {1648  Builder.defineMacro("__AARCH64EL__");1649  AArch64TargetInfo::getTargetDefines(Opts, Builder);1650}1651 1652AArch64beTargetInfo::AArch64beTargetInfo(const llvm::Triple &Triple,1653                                         const TargetOptions &Opts)1654    : AArch64TargetInfo(Triple, Opts) {}1655 1656void AArch64beTargetInfo::getTargetDefines(const LangOptions &Opts,1657                                           MacroBuilder &Builder) const {1658  Builder.defineMacro("__AARCH64EB__");1659  Builder.defineMacro("__AARCH_BIG_ENDIAN");1660  Builder.defineMacro("__ARM_BIG_ENDIAN");1661  AArch64TargetInfo::getTargetDefines(Opts, Builder);1662}1663 1664void AArch64beTargetInfo::setDataLayout() {1665  assert(!getTriple().isOSBinFormatMachO());1666  resetDataLayout("E-m:e-p270:32:32-p271:32:32-p272:64:64-i8:8:32-i16:16:32-"1667                  "i64:64-i128:128-n32:64-S128-Fn32");1668}1669 1670WindowsARM64TargetInfo::WindowsARM64TargetInfo(const llvm::Triple &Triple,1671                                               const TargetOptions &Opts)1672    : WindowsTargetInfo<AArch64leTargetInfo>(Triple, Opts), Triple(Triple) {1673 1674  // This is an LLP64 platform.1675  // int:4, long:4, long long:8, long double:8.1676  IntWidth = IntAlign = 32;1677  LongWidth = LongAlign = 32;1678  DoubleAlign = LongLongAlign = 64;1679  LongDoubleWidth = LongDoubleAlign = 64;1680  LongDoubleFormat = &llvm::APFloat::IEEEdouble();1681  IntMaxType = SignedLongLong;1682  Int64Type = SignedLongLong;1683  SizeType = UnsignedLongLong;1684  PtrDiffType = SignedLongLong;1685  IntPtrType = SignedLongLong;1686}1687 1688void WindowsARM64TargetInfo::setDataLayout() {1689  resetDataLayout(Triple.isOSBinFormatMachO()1690                      ? "e-m:o-p270:32:32-p271:32:32-p272:64:64-i64:64-i128:"1691                        "128-n32:64-S128-Fn32"1692                      : "e-m:w-p270:32:32-p271:32:32-p272:64:64-p:64:64-i32:32-"1693                        "i64:64-i128:128-n32:64-S128-Fn32",1694                  Triple.isOSBinFormatMachO() ? "_" : "");1695}1696 1697TargetInfo::BuiltinVaListKind1698WindowsARM64TargetInfo::getBuiltinVaListKind() const {1699  return TargetInfo::CharPtrBuiltinVaList;1700}1701 1702TargetInfo::CallingConvCheckResult1703WindowsARM64TargetInfo::checkCallingConvention(CallingConv CC) const {1704  switch (CC) {1705  case CC_X86VectorCall:1706    if (getTriple().isWindowsArm64EC())1707      return CCCR_OK;1708    return CCCR_Ignore;1709  case CC_X86StdCall:1710  case CC_X86ThisCall:1711  case CC_X86FastCall:1712    return CCCR_Ignore;1713  case CC_C:1714  case CC_DeviceKernel:1715  case CC_PreserveMost:1716  case CC_PreserveAll:1717  case CC_PreserveNone:1718  case CC_Swift:1719  case CC_SwiftAsync:1720  case CC_Win64:1721    return CCCR_OK;1722  default:1723    return CCCR_Warning;1724  }1725}1726 1727MicrosoftARM64TargetInfo::MicrosoftARM64TargetInfo(const llvm::Triple &Triple,1728                                                   const TargetOptions &Opts)1729    : WindowsARM64TargetInfo(Triple, Opts) {1730  TheCXXABI.set(TargetCXXABI::Microsoft);1731}1732 1733void MicrosoftARM64TargetInfo::getTargetDefines(const LangOptions &Opts,1734                                                MacroBuilder &Builder) const {1735  WindowsARM64TargetInfo::getTargetDefines(Opts, Builder);1736  if (getTriple().isWindowsArm64EC()) {1737    Builder.defineMacro("_M_X64", "100");1738    Builder.defineMacro("_M_AMD64", "100");1739    Builder.defineMacro("_M_ARM64EC", "1");1740  } else {1741    Builder.defineMacro("_M_ARM64", "1");1742  }1743}1744 1745TargetInfo::CallingConvKind1746MicrosoftARM64TargetInfo::getCallingConvKind(bool ClangABICompat4) const {1747  return CCK_MicrosoftWin64;1748}1749 1750unsigned MicrosoftARM64TargetInfo::getMinGlobalAlign(uint64_t TypeSize,1751                                                     bool HasNonWeakDef) const {1752  unsigned Align =1753      WindowsARM64TargetInfo::getMinGlobalAlign(TypeSize, HasNonWeakDef);1754 1755  // MSVC does size based alignment for arm64 based on alignment section in1756  // below document, replicate that to keep alignment consistent with object1757  // files compiled by MSVC.1758  // https://docs.microsoft.com/en-us/cpp/build/arm64-windows-abi-conventions1759  if (TypeSize >= 512) {              // TypeSize >= 64 bytes1760    Align = std::max(Align, 128u);    // align type at least 16 bytes1761  } else if (TypeSize >= 64) {        // TypeSize >= 8 bytes1762    Align = std::max(Align, 64u);     // align type at least 8 butes1763  } else if (TypeSize >= 16) {        // TypeSize >= 2 bytes1764    Align = std::max(Align, 32u);     // align type at least 4 bytes1765  }1766  return Align;1767}1768 1769MinGWARM64TargetInfo::MinGWARM64TargetInfo(const llvm::Triple &Triple,1770                                           const TargetOptions &Opts)1771    : WindowsARM64TargetInfo(Triple, Opts) {1772  TheCXXABI.set(TargetCXXABI::GenericAArch64);1773}1774 1775AppleMachOAArch64TargetInfo::AppleMachOAArch64TargetInfo(1776    const llvm::Triple &Triple, const TargetOptions &Opts)1777    : AppleMachOTargetInfo<AArch64leTargetInfo>(Triple, Opts) {}1778 1779DarwinAArch64TargetInfo::DarwinAArch64TargetInfo(const llvm::Triple &Triple,1780                                                 const TargetOptions &Opts)1781    : DarwinTargetInfo<AArch64leTargetInfo>(Triple, Opts) {1782  Int64Type = SignedLongLong;1783  if (getTriple().isArch32Bit())1784    IntMaxType = SignedLongLong;1785 1786  WCharType = SignedInt;1787  UseSignedCharForObjCBool = false;1788 1789  LongDoubleWidth = LongDoubleAlign = SuitableAlign = 64;1790  LongDoubleFormat = &llvm::APFloat::IEEEdouble();1791 1792  UseZeroLengthBitfieldAlignment = false;1793 1794  if (getTriple().isArch32Bit()) {1795    UseBitFieldTypeAlignment = false;1796    ZeroLengthBitfieldBoundary = 32;1797    UseZeroLengthBitfieldAlignment = true;1798    TheCXXABI.set(TargetCXXABI::WatchOS);1799  } else1800    TheCXXABI.set(TargetCXXABI::AppleARM64);1801}1802 1803void clang::targets::getAppleMachOAArch64Defines(MacroBuilder &Builder,1804                                                 const LangOptions &Opts,1805                                                 const llvm::Triple &Triple) {1806  Builder.defineMacro("__AARCH64_SIMD__");1807  if (Triple.isArch32Bit())1808    Builder.defineMacro("__ARM64_ARCH_8_32__");1809  else1810    Builder.defineMacro("__ARM64_ARCH_8__");1811  Builder.defineMacro("__ARM_NEON__");1812  Builder.defineMacro("__REGISTER_PREFIX__", "");1813  Builder.defineMacro("__arm64", "1");1814  Builder.defineMacro("__arm64__", "1");1815 1816  if (Triple.isArm64e())1817    Builder.defineMacro("__arm64e__", "1");1818}1819 1820void AppleMachOAArch64TargetInfo::getOSDefines(const LangOptions &Opts,1821                                               const llvm::Triple &Triple,1822                                               MacroBuilder &Builder) const {1823  getAppleMachOAArch64Defines(Builder, Opts, Triple);1824  AppleMachOTargetInfo<AArch64leTargetInfo>::getOSDefines(Opts, Triple,1825                                                          Builder);1826}1827 1828void DarwinAArch64TargetInfo::getOSDefines(const LangOptions &Opts,1829                                           const llvm::Triple &Triple,1830                                           MacroBuilder &Builder) const {1831  getAppleMachOAArch64Defines(Builder, Opts, Triple);1832  DarwinTargetInfo<AArch64leTargetInfo>::getOSDefines(Opts, Triple, Builder);1833}1834 1835TargetInfo::BuiltinVaListKind1836DarwinAArch64TargetInfo::getBuiltinVaListKind() const {1837  return TargetInfo::CharPtrBuiltinVaList;1838}1839