1 //===--- TargetInfo.h - Expose information about the target -----*- C++ -*-===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 /// 9 /// \file 10 /// Defines the clang::TargetInfo interface. 11 /// 12 //===----------------------------------------------------------------------===// 13 14 #ifndef LLVM_CLANG_BASIC_TARGETINFO_H 15 #define LLVM_CLANG_BASIC_TARGETINFO_H 16 17 #include "clang/Basic/AddressSpaces.h" 18 #include "clang/Basic/BitmaskEnum.h" 19 #include "clang/Basic/CodeGenOptions.h" 20 #include "clang/Basic/LLVM.h" 21 #include "clang/Basic/LangOptions.h" 22 #include "clang/Basic/Specifiers.h" 23 #include "clang/Basic/TargetCXXABI.h" 24 #include "clang/Basic/TargetOptions.h" 25 #include "llvm/ADT/APFloat.h" 26 #include "llvm/ADT/APInt.h" 27 #include "llvm/ADT/ArrayRef.h" 28 #include "llvm/ADT/IntrusiveRefCntPtr.h" 29 #include "llvm/ADT/SmallSet.h" 30 #include "llvm/ADT/StringMap.h" 31 #include "llvm/ADT/StringRef.h" 32 #include "llvm/ADT/StringSet.h" 33 #include "llvm/Frontend/OpenMP/OMPGridValues.h" 34 #include "llvm/IR/DerivedTypes.h" 35 #include "llvm/Support/DataTypes.h" 36 #include "llvm/Support/Error.h" 37 #include "llvm/Support/VersionTuple.h" 38 #include "llvm/TargetParser/Triple.h" 39 #include <cassert> 40 #include <optional> 41 #include <string> 42 #include <vector> 43 44 namespace llvm { 45 struct fltSemantics; 46 } 47 48 namespace clang { 49 class DiagnosticsEngine; 50 class LangOptions; 51 class CodeGenOptions; 52 class MacroBuilder; 53 54 /// Contains information gathered from parsing the contents of TargetAttr. 55 struct ParsedTargetAttr { 56 std::vector<std::string> Features; 57 StringRef CPU; 58 StringRef Tune; 59 StringRef BranchProtection; 60 StringRef Duplicate; 61 bool operator ==(const ParsedTargetAttr &Other) const { 62 return Duplicate == Other.Duplicate && CPU == Other.CPU && 63 Tune == Other.Tune && BranchProtection == Other.BranchProtection && 64 Features == Other.Features; 65 } 66 }; 67 68 namespace Builtin { struct Info; } 69 70 enum class FloatModeKind { 71 NoFloat = 0, 72 Half = 1 << 0, 73 Float = 1 << 1, 74 Double = 1 << 2, 75 LongDouble = 1 << 3, 76 Float128 = 1 << 4, 77 Ibm128 = 1 << 5, 78 LLVM_MARK_AS_BITMASK_ENUM(Ibm128) 79 }; 80 81 /// Fields controlling how types are laid out in memory; these may need to 82 /// be copied for targets like AMDGPU that base their ABIs on an auxiliary 83 /// CPU target. 84 struct TransferrableTargetInfo { 85 unsigned char PointerWidth, PointerAlign; 86 unsigned char BoolWidth, BoolAlign; 87 unsigned char IntWidth, IntAlign; 88 unsigned char HalfWidth, HalfAlign; 89 unsigned char BFloat16Width, BFloat16Align; 90 unsigned char FloatWidth, FloatAlign; 91 unsigned char DoubleWidth, DoubleAlign; 92 unsigned char LongDoubleWidth, LongDoubleAlign, Float128Align, Ibm128Align; 93 unsigned char LargeArrayMinWidth, LargeArrayAlign; 94 unsigned char LongWidth, LongAlign; 95 unsigned char LongLongWidth, LongLongAlign; 96 unsigned char Int128Align; 97 98 // Fixed point bit widths 99 unsigned char ShortAccumWidth, ShortAccumAlign; 100 unsigned char AccumWidth, AccumAlign; 101 unsigned char LongAccumWidth, LongAccumAlign; 102 unsigned char ShortFractWidth, ShortFractAlign; 103 unsigned char FractWidth, FractAlign; 104 unsigned char LongFractWidth, LongFractAlign; 105 106 // If true, unsigned fixed point types have the same number of fractional bits 107 // as their signed counterparts, forcing the unsigned types to have one extra 108 // bit of padding. Otherwise, unsigned fixed point types have 109 // one more fractional bit than its corresponding signed type. This is false 110 // by default. 111 bool PaddingOnUnsignedFixedPoint; 112 113 // Fixed point integral and fractional bit sizes 114 // Saturated types share the same integral/fractional bits as their 115 // corresponding unsaturated types. 116 // For simplicity, the fractional bits in a _Fract type will be one less the 117 // width of that _Fract type. This leaves all signed _Fract types having no 118 // padding and unsigned _Fract types will only have 1 bit of padding after the 119 // sign if PaddingOnUnsignedFixedPoint is set. 120 unsigned char ShortAccumScale; 121 unsigned char AccumScale; 122 unsigned char LongAccumScale; 123 124 unsigned char DefaultAlignForAttributeAligned; 125 unsigned char MinGlobalAlign; 126 127 unsigned short SuitableAlign; 128 unsigned short NewAlign; 129 unsigned MaxVectorAlign; 130 unsigned MaxTLSAlign; 131 132 const llvm::fltSemantics *HalfFormat, *BFloat16Format, *FloatFormat, 133 *DoubleFormat, *LongDoubleFormat, *Float128Format, *Ibm128Format; 134 135 ///===---- Target Data Type Query Methods -------------------------------===// 136 enum IntType { 137 NoInt = 0, 138 SignedChar, 139 UnsignedChar, 140 SignedShort, 141 UnsignedShort, 142 SignedInt, 143 UnsignedInt, 144 SignedLong, 145 UnsignedLong, 146 SignedLongLong, 147 UnsignedLongLong 148 }; 149 150 protected: 151 IntType SizeType, IntMaxType, PtrDiffType, IntPtrType, WCharType, WIntType, 152 Char16Type, Char32Type, Int64Type, Int16Type, SigAtomicType, 153 ProcessIDType; 154 155 /// Whether Objective-C's built-in boolean type should be signed char. 156 /// 157 /// Otherwise, when this flag is not set, the normal built-in boolean type is 158 /// used. 159 LLVM_PREFERRED_TYPE(bool) 160 unsigned UseSignedCharForObjCBool : 1; 161 162 /// Control whether the alignment of bit-field types is respected when laying 163 /// out structures. If true, then the alignment of the bit-field type will be 164 /// used to (a) impact the alignment of the containing structure, and (b) 165 /// ensure that the individual bit-field will not straddle an alignment 166 /// boundary. 167 LLVM_PREFERRED_TYPE(bool) 168 unsigned UseBitFieldTypeAlignment : 1; 169 170 /// Whether zero length bitfields (e.g., int : 0;) force alignment of 171 /// the next bitfield. 172 /// 173 /// If the alignment of the zero length bitfield is greater than the member 174 /// that follows it, `bar', `bar' will be aligned as the type of the 175 /// zero-length bitfield. 176 LLVM_PREFERRED_TYPE(bool) 177 unsigned UseZeroLengthBitfieldAlignment : 1; 178 179 /// Whether zero length bitfield alignment is respected if they are the 180 /// leading members. 181 LLVM_PREFERRED_TYPE(bool) 182 unsigned UseLeadingZeroLengthBitfield : 1; 183 184 /// Whether explicit bit field alignment attributes are honored. 185 LLVM_PREFERRED_TYPE(bool) 186 unsigned UseExplicitBitFieldAlignment : 1; 187 188 /// If non-zero, specifies a fixed alignment value for bitfields that follow 189 /// zero length bitfield, regardless of the zero length bitfield type. 190 unsigned ZeroLengthBitfieldBoundary; 191 192 /// If non-zero, specifies a maximum alignment to truncate alignment 193 /// specified in the aligned attribute of a static variable to this value. 194 unsigned MaxAlignedAttribute; 195 }; 196 197 /// OpenCL type kinds. 198 enum OpenCLTypeKind : uint8_t { 199 OCLTK_Default, 200 OCLTK_ClkEvent, 201 OCLTK_Event, 202 OCLTK_Image, 203 OCLTK_Pipe, 204 OCLTK_Queue, 205 OCLTK_ReserveID, 206 OCLTK_Sampler, 207 }; 208 209 /// Exposes information about the current target. 210 /// 211 class TargetInfo : public TransferrableTargetInfo, 212 public RefCountedBase<TargetInfo> { 213 std::shared_ptr<TargetOptions> TargetOpts; 214 llvm::Triple Triple; 215 protected: 216 // Target values set by the ctor of the actual target implementation. Default 217 // values are specified by the TargetInfo constructor. 218 bool BigEndian; 219 bool TLSSupported; 220 bool VLASupported; 221 bool NoAsmVariants; // True if {|} are normal characters. 222 bool HasLegalHalfType; // True if the backend supports operations on the half 223 // LLVM IR type. 224 bool HalfArgsAndReturns; 225 bool HasFloat128; 226 bool HasFloat16; 227 bool HasBFloat16; 228 bool HasFullBFloat16; // True if the backend supports native bfloat16 229 // arithmetic. Used to determine excess precision 230 // support in the frontend. 231 bool HasIbm128; 232 bool HasLongDouble; 233 bool HasFPReturn; 234 bool HasStrictFP; 235 236 unsigned char MaxAtomicPromoteWidth, MaxAtomicInlineWidth; 237 std::string DataLayoutString; 238 const char *UserLabelPrefix; 239 const char *MCountName; 240 unsigned char RegParmMax, SSERegParmMax; 241 TargetCXXABI TheCXXABI; 242 const LangASMap *AddrSpaceMap; 243 244 mutable StringRef PlatformName; 245 mutable VersionTuple PlatformMinVersion; 246 247 LLVM_PREFERRED_TYPE(bool) 248 unsigned HasAlignMac68kSupport : 1; 249 LLVM_PREFERRED_TYPE(FloatModeKind) 250 unsigned RealTypeUsesObjCFPRetMask : llvm::BitWidth<FloatModeKind>; 251 LLVM_PREFERRED_TYPE(bool) 252 unsigned ComplexLongDoubleUsesFP2Ret : 1; 253 254 LLVM_PREFERRED_TYPE(bool) 255 unsigned HasBuiltinMSVaList : 1; 256 257 LLVM_PREFERRED_TYPE(bool) 258 unsigned IsRenderScriptTarget : 1; 259 260 LLVM_PREFERRED_TYPE(bool) 261 unsigned HasAArch64SVETypes : 1; 262 263 LLVM_PREFERRED_TYPE(bool) 264 unsigned HasRISCVVTypes : 1; 265 266 LLVM_PREFERRED_TYPE(bool) 267 unsigned AllowAMDGPUUnsafeFPAtomics : 1; 268 269 unsigned ARMCDECoprocMask : 8; 270 271 unsigned MaxOpenCLWorkGroupSize; 272 273 std::optional<unsigned> MaxBitIntWidth; 274 275 std::optional<llvm::Triple> DarwinTargetVariantTriple; 276 277 // TargetInfo Constructor. Default initializes all fields. 278 TargetInfo(const llvm::Triple &T); 279 280 // UserLabelPrefix must match DL's getGlobalPrefix() when interpreted 281 // as a DataLayout object. 282 void resetDataLayout(StringRef DL, const char *UserLabelPrefix = ""); 283 284 // Target features that are read-only and should not be disabled/enabled 285 // by command line options. Such features are for emitting predefined 286 // macros or checking availability of builtin functions and can be omitted 287 // in function attributes in IR. 288 llvm::StringSet<> ReadOnlyFeatures; 289 290 public: 291 /// Construct a target for the given options. 292 /// 293 /// \param Opts - The options to use to initialize the target. The target may 294 /// modify the options to canonicalize the target feature information to match 295 /// what the backend expects. 296 static TargetInfo * 297 CreateTargetInfo(DiagnosticsEngine &Diags, 298 const std::shared_ptr<TargetOptions> &Opts); 299 300 virtual ~TargetInfo(); 301 302 /// Retrieve the target options. getTargetOpts()303 TargetOptions &getTargetOpts() const { 304 assert(TargetOpts && "Missing target options"); 305 return *TargetOpts; 306 } 307 308 /// The different kinds of __builtin_va_list types defined by 309 /// the target implementation. 310 enum BuiltinVaListKind { 311 /// typedef char* __builtin_va_list; 312 CharPtrBuiltinVaList = 0, 313 314 /// typedef void* __builtin_va_list; 315 VoidPtrBuiltinVaList, 316 317 /// __builtin_va_list as defined by the AArch64 ABI 318 /// http://infocenter.arm.com/help/topic/com.arm.doc.ihi0055a/IHI0055A_aapcs64.pdf 319 AArch64ABIBuiltinVaList, 320 321 /// __builtin_va_list as defined by the PNaCl ABI: 322 /// http://www.chromium.org/nativeclient/pnacl/bitcode-abi#TOC-Machine-Types 323 PNaClABIBuiltinVaList, 324 325 /// __builtin_va_list as defined by the Power ABI: 326 /// https://www.power.org 327 /// /resources/downloads/Power-Arch-32-bit-ABI-supp-1.0-Embedded.pdf 328 PowerABIBuiltinVaList, 329 330 /// __builtin_va_list as defined by the x86-64 ABI: 331 /// http://refspecs.linuxbase.org/elf/x86_64-abi-0.21.pdf 332 X86_64ABIBuiltinVaList, 333 334 /// __builtin_va_list as defined by ARM AAPCS ABI 335 /// http://infocenter.arm.com 336 // /help/topic/com.arm.doc.ihi0042d/IHI0042D_aapcs.pdf 337 AAPCSABIBuiltinVaList, 338 339 // typedef struct __va_list_tag 340 // { 341 // long __gpr; 342 // long __fpr; 343 // void *__overflow_arg_area; 344 // void *__reg_save_area; 345 // } va_list[1]; 346 SystemZBuiltinVaList, 347 348 // typedef struct __va_list_tag { 349 // void *__current_saved_reg_area_pointer; 350 // void *__saved_reg_area_end_pointer; 351 // void *__overflow_area_pointer; 352 //} va_list; 353 HexagonBuiltinVaList 354 }; 355 356 protected: 357 /// Specify if mangling based on address space map should be used or 358 /// not for language specific address spaces 359 bool UseAddrSpaceMapMangling; 360 361 public: getSizeType()362 IntType getSizeType() const { return SizeType; } getSignedSizeType()363 IntType getSignedSizeType() const { 364 switch (SizeType) { 365 case UnsignedShort: 366 return SignedShort; 367 case UnsignedInt: 368 return SignedInt; 369 case UnsignedLong: 370 return SignedLong; 371 case UnsignedLongLong: 372 return SignedLongLong; 373 default: 374 llvm_unreachable("Invalid SizeType"); 375 } 376 } getIntMaxType()377 IntType getIntMaxType() const { return IntMaxType; } getUIntMaxType()378 IntType getUIntMaxType() const { 379 return getCorrespondingUnsignedType(IntMaxType); 380 } getPtrDiffType(LangAS AddrSpace)381 IntType getPtrDiffType(LangAS AddrSpace) const { 382 return AddrSpace == LangAS::Default ? PtrDiffType 383 : getPtrDiffTypeV(AddrSpace); 384 } getUnsignedPtrDiffType(LangAS AddrSpace)385 IntType getUnsignedPtrDiffType(LangAS AddrSpace) const { 386 return getCorrespondingUnsignedType(getPtrDiffType(AddrSpace)); 387 } getIntPtrType()388 IntType getIntPtrType() const { return IntPtrType; } getUIntPtrType()389 IntType getUIntPtrType() const { 390 return getCorrespondingUnsignedType(IntPtrType); 391 } getWCharType()392 IntType getWCharType() const { return WCharType; } getWIntType()393 IntType getWIntType() const { return WIntType; } getChar16Type()394 IntType getChar16Type() const { return Char16Type; } getChar32Type()395 IntType getChar32Type() const { return Char32Type; } getInt64Type()396 IntType getInt64Type() const { return Int64Type; } getUInt64Type()397 IntType getUInt64Type() const { 398 return getCorrespondingUnsignedType(Int64Type); 399 } getInt16Type()400 IntType getInt16Type() const { return Int16Type; } getUInt16Type()401 IntType getUInt16Type() const { 402 return getCorrespondingUnsignedType(Int16Type); 403 } getSigAtomicType()404 IntType getSigAtomicType() const { return SigAtomicType; } getProcessIDType()405 IntType getProcessIDType() const { return ProcessIDType; } 406 getCorrespondingUnsignedType(IntType T)407 static IntType getCorrespondingUnsignedType(IntType T) { 408 switch (T) { 409 case SignedChar: 410 return UnsignedChar; 411 case SignedShort: 412 return UnsignedShort; 413 case SignedInt: 414 return UnsignedInt; 415 case SignedLong: 416 return UnsignedLong; 417 case SignedLongLong: 418 return UnsignedLongLong; 419 default: 420 llvm_unreachable("Unexpected signed integer type"); 421 } 422 } 423 424 /// In the event this target uses the same number of fractional bits for its 425 /// unsigned types as it does with its signed counterparts, there will be 426 /// exactly one bit of padding. 427 /// Return true if unsigned fixed point types have padding for this target. doUnsignedFixedPointTypesHavePadding()428 bool doUnsignedFixedPointTypesHavePadding() const { 429 return PaddingOnUnsignedFixedPoint; 430 } 431 432 /// Return the width (in bits) of the specified integer type enum. 433 /// 434 /// For example, SignedInt -> getIntWidth(). 435 unsigned getTypeWidth(IntType T) const; 436 437 /// Return integer type with specified width. 438 virtual IntType getIntTypeByWidth(unsigned BitWidth, bool IsSigned) const; 439 440 /// Return the smallest integer type with at least the specified width. 441 virtual IntType getLeastIntTypeByWidth(unsigned BitWidth, 442 bool IsSigned) const; 443 444 /// Return floating point type with specified width. On PPC, there are 445 /// three possible types for 128-bit floating point: "PPC double-double", 446 /// IEEE 754R quad precision, and "long double" (which under the covers 447 /// is represented as one of those two). At this time, there is no support 448 /// for an explicit "PPC double-double" type (i.e. __ibm128) so we only 449 /// need to differentiate between "long double" and IEEE quad precision. 450 FloatModeKind getRealTypeByWidth(unsigned BitWidth, 451 FloatModeKind ExplicitType) const; 452 453 /// Return the alignment (in bits) of the specified integer type enum. 454 /// 455 /// For example, SignedInt -> getIntAlign(). 456 unsigned getTypeAlign(IntType T) const; 457 458 /// Returns true if the type is signed; false otherwise. 459 static bool isTypeSigned(IntType T); 460 461 /// Return the width of pointers on this target, for the 462 /// specified address space. getPointerWidth(LangAS AddrSpace)463 uint64_t getPointerWidth(LangAS AddrSpace) const { 464 return AddrSpace == LangAS::Default ? PointerWidth 465 : getPointerWidthV(AddrSpace); 466 } getPointerAlign(LangAS AddrSpace)467 uint64_t getPointerAlign(LangAS AddrSpace) const { 468 return AddrSpace == LangAS::Default ? PointerAlign 469 : getPointerAlignV(AddrSpace); 470 } 471 472 /// Return the maximum width of pointers on this target. getMaxPointerWidth()473 virtual uint64_t getMaxPointerWidth() const { 474 return PointerWidth; 475 } 476 477 /// Get integer value for null pointer. 478 /// \param AddrSpace address space of pointee in source language. getNullPointerValue(LangAS AddrSpace)479 virtual uint64_t getNullPointerValue(LangAS AddrSpace) const { return 0; } 480 481 /// Return the size of '_Bool' and C++ 'bool' for this target, in bits. getBoolWidth()482 unsigned getBoolWidth() const { return BoolWidth; } 483 484 /// Return the alignment of '_Bool' and C++ 'bool' for this target. getBoolAlign()485 unsigned getBoolAlign() const { return BoolAlign; } 486 getCharWidth()487 unsigned getCharWidth() const { return 8; } // FIXME getCharAlign()488 unsigned getCharAlign() const { return 8; } // FIXME 489 490 /// Return the size of 'signed short' and 'unsigned short' for this 491 /// target, in bits. getShortWidth()492 unsigned getShortWidth() const { return 16; } // FIXME 493 494 /// Return the alignment of 'signed short' and 'unsigned short' for 495 /// this target. getShortAlign()496 unsigned getShortAlign() const { return 16; } // FIXME 497 498 /// getIntWidth/Align - Return the size of 'signed int' and 'unsigned int' for 499 /// this target, in bits. getIntWidth()500 unsigned getIntWidth() const { return IntWidth; } getIntAlign()501 unsigned getIntAlign() const { return IntAlign; } 502 503 /// getLongWidth/Align - Return the size of 'signed long' and 'unsigned long' 504 /// for this target, in bits. getLongWidth()505 unsigned getLongWidth() const { return LongWidth; } getLongAlign()506 unsigned getLongAlign() const { return LongAlign; } 507 508 /// getLongLongWidth/Align - Return the size of 'signed long long' and 509 /// 'unsigned long long' for this target, in bits. getLongLongWidth()510 unsigned getLongLongWidth() const { return LongLongWidth; } getLongLongAlign()511 unsigned getLongLongAlign() const { return LongLongAlign; } 512 513 /// getInt128Align() - Returns the alignment of Int128. getInt128Align()514 unsigned getInt128Align() const { return Int128Align; } 515 516 /// getShortAccumWidth/Align - Return the size of 'signed short _Accum' and 517 /// 'unsigned short _Accum' for this target, in bits. getShortAccumWidth()518 unsigned getShortAccumWidth() const { return ShortAccumWidth; } getShortAccumAlign()519 unsigned getShortAccumAlign() const { return ShortAccumAlign; } 520 521 /// getAccumWidth/Align - Return the size of 'signed _Accum' and 522 /// 'unsigned _Accum' for this target, in bits. getAccumWidth()523 unsigned getAccumWidth() const { return AccumWidth; } getAccumAlign()524 unsigned getAccumAlign() const { return AccumAlign; } 525 526 /// getLongAccumWidth/Align - Return the size of 'signed long _Accum' and 527 /// 'unsigned long _Accum' for this target, in bits. getLongAccumWidth()528 unsigned getLongAccumWidth() const { return LongAccumWidth; } getLongAccumAlign()529 unsigned getLongAccumAlign() const { return LongAccumAlign; } 530 531 /// getShortFractWidth/Align - Return the size of 'signed short _Fract' and 532 /// 'unsigned short _Fract' for this target, in bits. getShortFractWidth()533 unsigned getShortFractWidth() const { return ShortFractWidth; } getShortFractAlign()534 unsigned getShortFractAlign() const { return ShortFractAlign; } 535 536 /// getFractWidth/Align - Return the size of 'signed _Fract' and 537 /// 'unsigned _Fract' for this target, in bits. getFractWidth()538 unsigned getFractWidth() const { return FractWidth; } getFractAlign()539 unsigned getFractAlign() const { return FractAlign; } 540 541 /// getLongFractWidth/Align - Return the size of 'signed long _Fract' and 542 /// 'unsigned long _Fract' for this target, in bits. getLongFractWidth()543 unsigned getLongFractWidth() const { return LongFractWidth; } getLongFractAlign()544 unsigned getLongFractAlign() const { return LongFractAlign; } 545 546 /// getShortAccumScale/IBits - Return the number of fractional/integral bits 547 /// in a 'signed short _Accum' type. getShortAccumScale()548 unsigned getShortAccumScale() const { return ShortAccumScale; } getShortAccumIBits()549 unsigned getShortAccumIBits() const { 550 return ShortAccumWidth - ShortAccumScale - 1; 551 } 552 553 /// getAccumScale/IBits - Return the number of fractional/integral bits 554 /// in a 'signed _Accum' type. getAccumScale()555 unsigned getAccumScale() const { return AccumScale; } getAccumIBits()556 unsigned getAccumIBits() const { return AccumWidth - AccumScale - 1; } 557 558 /// getLongAccumScale/IBits - Return the number of fractional/integral bits 559 /// in a 'signed long _Accum' type. getLongAccumScale()560 unsigned getLongAccumScale() const { return LongAccumScale; } getLongAccumIBits()561 unsigned getLongAccumIBits() const { 562 return LongAccumWidth - LongAccumScale - 1; 563 } 564 565 /// getUnsignedShortAccumScale/IBits - Return the number of 566 /// fractional/integral bits in a 'unsigned short _Accum' type. getUnsignedShortAccumScale()567 unsigned getUnsignedShortAccumScale() const { 568 return PaddingOnUnsignedFixedPoint ? ShortAccumScale : ShortAccumScale + 1; 569 } getUnsignedShortAccumIBits()570 unsigned getUnsignedShortAccumIBits() const { 571 return PaddingOnUnsignedFixedPoint 572 ? getShortAccumIBits() 573 : ShortAccumWidth - getUnsignedShortAccumScale(); 574 } 575 576 /// getUnsignedAccumScale/IBits - Return the number of fractional/integral 577 /// bits in a 'unsigned _Accum' type. getUnsignedAccumScale()578 unsigned getUnsignedAccumScale() const { 579 return PaddingOnUnsignedFixedPoint ? AccumScale : AccumScale + 1; 580 } getUnsignedAccumIBits()581 unsigned getUnsignedAccumIBits() const { 582 return PaddingOnUnsignedFixedPoint ? getAccumIBits() 583 : AccumWidth - getUnsignedAccumScale(); 584 } 585 586 /// getUnsignedLongAccumScale/IBits - Return the number of fractional/integral 587 /// bits in a 'unsigned long _Accum' type. getUnsignedLongAccumScale()588 unsigned getUnsignedLongAccumScale() const { 589 return PaddingOnUnsignedFixedPoint ? LongAccumScale : LongAccumScale + 1; 590 } getUnsignedLongAccumIBits()591 unsigned getUnsignedLongAccumIBits() const { 592 return PaddingOnUnsignedFixedPoint 593 ? getLongAccumIBits() 594 : LongAccumWidth - getUnsignedLongAccumScale(); 595 } 596 597 /// getShortFractScale - Return the number of fractional bits 598 /// in a 'signed short _Fract' type. getShortFractScale()599 unsigned getShortFractScale() const { return ShortFractWidth - 1; } 600 601 /// getFractScale - Return the number of fractional bits 602 /// in a 'signed _Fract' type. getFractScale()603 unsigned getFractScale() const { return FractWidth - 1; } 604 605 /// getLongFractScale - Return the number of fractional bits 606 /// in a 'signed long _Fract' type. getLongFractScale()607 unsigned getLongFractScale() const { return LongFractWidth - 1; } 608 609 /// getUnsignedShortFractScale - Return the number of fractional bits 610 /// in a 'unsigned short _Fract' type. getUnsignedShortFractScale()611 unsigned getUnsignedShortFractScale() const { 612 return PaddingOnUnsignedFixedPoint ? getShortFractScale() 613 : getShortFractScale() + 1; 614 } 615 616 /// getUnsignedFractScale - Return the number of fractional bits 617 /// in a 'unsigned _Fract' type. getUnsignedFractScale()618 unsigned getUnsignedFractScale() const { 619 return PaddingOnUnsignedFixedPoint ? getFractScale() : getFractScale() + 1; 620 } 621 622 /// getUnsignedLongFractScale - Return the number of fractional bits 623 /// in a 'unsigned long _Fract' type. getUnsignedLongFractScale()624 unsigned getUnsignedLongFractScale() const { 625 return PaddingOnUnsignedFixedPoint ? getLongFractScale() 626 : getLongFractScale() + 1; 627 } 628 629 /// Determine whether the __int128 type is supported on this target. hasInt128Type()630 virtual bool hasInt128Type() const { 631 return (getPointerWidth(LangAS::Default) >= 64) || 632 getTargetOpts().ForceEnableInt128; 633 } // FIXME 634 635 /// Determine whether the _BitInt type is supported on this target. This 636 /// limitation is put into place for ABI reasons. 637 /// FIXME: _BitInt is a required type in C23, so there's not much utility in 638 /// asking whether the target supported it or not; I think this should be 639 /// removed once backends have been alerted to the type and have had the 640 /// chance to do implementation work if needed. hasBitIntType()641 virtual bool hasBitIntType() const { 642 return false; 643 } 644 645 // Different targets may support a different maximum width for the _BitInt 646 // type, depending on what operations are supported. getMaxBitIntWidth()647 virtual size_t getMaxBitIntWidth() const { 648 // Consider -fexperimental-max-bitint-width= first. 649 if (MaxBitIntWidth) 650 return std::min<size_t>(*MaxBitIntWidth, llvm::IntegerType::MAX_INT_BITS); 651 652 // FIXME: this value should be llvm::IntegerType::MAX_INT_BITS, which is 653 // maximum bit width that LLVM claims its IR can support. However, most 654 // backends currently have a bug where they only support float to int 655 // conversion (and vice versa) on types that are <= 128 bits and crash 656 // otherwise. We're setting the max supported value to 128 to be 657 // conservative. 658 return 128; 659 } 660 661 /// Determine whether _Float16 is supported on this target. hasLegalHalfType()662 virtual bool hasLegalHalfType() const { return HasLegalHalfType; } 663 664 /// Whether half args and returns are supported. allowHalfArgsAndReturns()665 virtual bool allowHalfArgsAndReturns() const { return HalfArgsAndReturns; } 666 667 /// Determine whether the __float128 type is supported on this target. hasFloat128Type()668 virtual bool hasFloat128Type() const { return HasFloat128; } 669 670 /// Determine whether the _Float16 type is supported on this target. hasFloat16Type()671 virtual bool hasFloat16Type() const { return HasFloat16; } 672 673 /// Determine whether the _BFloat16 type is supported on this target. hasBFloat16Type()674 virtual bool hasBFloat16Type() const { 675 return HasBFloat16 || HasFullBFloat16; 676 } 677 678 /// Determine whether the BFloat type is fully supported on this target, i.e 679 /// arithemtic operations. hasFullBFloat16Type()680 virtual bool hasFullBFloat16Type() const { return HasFullBFloat16; } 681 682 /// Determine whether the __ibm128 type is supported on this target. hasIbm128Type()683 virtual bool hasIbm128Type() const { return HasIbm128; } 684 685 /// Determine whether the long double type is supported on this target. hasLongDoubleType()686 virtual bool hasLongDoubleType() const { return HasLongDouble; } 687 688 /// Determine whether return of a floating point value is supported 689 /// on this target. hasFPReturn()690 virtual bool hasFPReturn() const { return HasFPReturn; } 691 692 /// Determine whether constrained floating point is supported on this target. hasStrictFP()693 virtual bool hasStrictFP() const { return HasStrictFP; } 694 695 /// Return the alignment that is the largest alignment ever used for any 696 /// scalar/SIMD data type on the target machine you are compiling for 697 /// (including types with an extended alignment requirement). getSuitableAlign()698 unsigned getSuitableAlign() const { return SuitableAlign; } 699 700 /// Return the default alignment for __attribute__((aligned)) on 701 /// this target, to be used if no alignment value is specified. getDefaultAlignForAttributeAligned()702 unsigned getDefaultAlignForAttributeAligned() const { 703 return DefaultAlignForAttributeAligned; 704 } 705 706 /// getMinGlobalAlign - Return the minimum alignment of a global variable, 707 /// unless its alignment is explicitly reduced via attributes. getMinGlobalAlign(uint64_t)708 virtual unsigned getMinGlobalAlign (uint64_t) const { 709 return MinGlobalAlign; 710 } 711 712 /// Return the largest alignment for which a suitably-sized allocation with 713 /// '::operator new(size_t)' is guaranteed to produce a correctly-aligned 714 /// pointer. getNewAlign()715 unsigned getNewAlign() const { 716 return NewAlign ? NewAlign : std::max(LongDoubleAlign, LongLongAlign); 717 } 718 719 /// getWCharWidth/Align - Return the size of 'wchar_t' for this target, in 720 /// bits. getWCharWidth()721 unsigned getWCharWidth() const { return getTypeWidth(WCharType); } getWCharAlign()722 unsigned getWCharAlign() const { return getTypeAlign(WCharType); } 723 724 /// getChar16Width/Align - Return the size of 'char16_t' for this target, in 725 /// bits. getChar16Width()726 unsigned getChar16Width() const { return getTypeWidth(Char16Type); } getChar16Align()727 unsigned getChar16Align() const { return getTypeAlign(Char16Type); } 728 729 /// getChar32Width/Align - Return the size of 'char32_t' for this target, in 730 /// bits. getChar32Width()731 unsigned getChar32Width() const { return getTypeWidth(Char32Type); } getChar32Align()732 unsigned getChar32Align() const { return getTypeAlign(Char32Type); } 733 734 /// getHalfWidth/Align/Format - Return the size/align/format of 'half'. getHalfWidth()735 unsigned getHalfWidth() const { return HalfWidth; } getHalfAlign()736 unsigned getHalfAlign() const { return HalfAlign; } getHalfFormat()737 const llvm::fltSemantics &getHalfFormat() const { return *HalfFormat; } 738 739 /// getFloatWidth/Align/Format - Return the size/align/format of 'float'. getFloatWidth()740 unsigned getFloatWidth() const { return FloatWidth; } getFloatAlign()741 unsigned getFloatAlign() const { return FloatAlign; } getFloatFormat()742 const llvm::fltSemantics &getFloatFormat() const { return *FloatFormat; } 743 744 /// getBFloat16Width/Align/Format - Return the size/align/format of '__bf16'. getBFloat16Width()745 unsigned getBFloat16Width() const { return BFloat16Width; } getBFloat16Align()746 unsigned getBFloat16Align() const { return BFloat16Align; } getBFloat16Format()747 const llvm::fltSemantics &getBFloat16Format() const { return *BFloat16Format; } 748 749 /// getDoubleWidth/Align/Format - Return the size/align/format of 'double'. getDoubleWidth()750 unsigned getDoubleWidth() const { return DoubleWidth; } getDoubleAlign()751 unsigned getDoubleAlign() const { return DoubleAlign; } getDoubleFormat()752 const llvm::fltSemantics &getDoubleFormat() const { return *DoubleFormat; } 753 754 /// getLongDoubleWidth/Align/Format - Return the size/align/format of 'long 755 /// double'. getLongDoubleWidth()756 unsigned getLongDoubleWidth() const { return LongDoubleWidth; } getLongDoubleAlign()757 unsigned getLongDoubleAlign() const { return LongDoubleAlign; } getLongDoubleFormat()758 const llvm::fltSemantics &getLongDoubleFormat() const { 759 return *LongDoubleFormat; 760 } 761 762 /// getFloat128Width/Align/Format - Return the size/align/format of 763 /// '__float128'. getFloat128Width()764 unsigned getFloat128Width() const { return 128; } getFloat128Align()765 unsigned getFloat128Align() const { return Float128Align; } getFloat128Format()766 const llvm::fltSemantics &getFloat128Format() const { 767 return *Float128Format; 768 } 769 770 /// getIbm128Width/Align/Format - Return the size/align/format of 771 /// '__ibm128'. getIbm128Width()772 unsigned getIbm128Width() const { return 128; } getIbm128Align()773 unsigned getIbm128Align() const { return Ibm128Align; } getIbm128Format()774 const llvm::fltSemantics &getIbm128Format() const { return *Ibm128Format; } 775 776 /// Return the mangled code of long double. getLongDoubleMangling()777 virtual const char *getLongDoubleMangling() const { return "e"; } 778 779 /// Return the mangled code of __float128. getFloat128Mangling()780 virtual const char *getFloat128Mangling() const { return "g"; } 781 782 /// Return the mangled code of __ibm128. getIbm128Mangling()783 virtual const char *getIbm128Mangling() const { 784 llvm_unreachable("ibm128 not implemented on this target"); 785 } 786 787 /// Return the mangled code of bfloat. getBFloat16Mangling()788 virtual const char *getBFloat16Mangling() const { return "DF16b"; } 789 790 /// Return the value for the C99 FLT_EVAL_METHOD macro. getFPEvalMethod()791 virtual LangOptions::FPEvalMethodKind getFPEvalMethod() const { 792 return LangOptions::FPEvalMethodKind::FEM_Source; 793 } 794 supportSourceEvalMethod()795 virtual bool supportSourceEvalMethod() const { return true; } 796 797 // getLargeArrayMinWidth/Align - Return the minimum array size that is 798 // 'large' and its alignment. getLargeArrayMinWidth()799 unsigned getLargeArrayMinWidth() const { return LargeArrayMinWidth; } getLargeArrayAlign()800 unsigned getLargeArrayAlign() const { return LargeArrayAlign; } 801 802 /// Return the maximum width lock-free atomic operation which will 803 /// ever be supported for the given target getMaxAtomicPromoteWidth()804 unsigned getMaxAtomicPromoteWidth() const { return MaxAtomicPromoteWidth; } 805 /// Return the maximum width lock-free atomic operation which can be 806 /// inlined given the supported features of the given target. getMaxAtomicInlineWidth()807 unsigned getMaxAtomicInlineWidth() const { return MaxAtomicInlineWidth; } 808 /// Set the maximum inline or promote width lock-free atomic operation 809 /// for the given target. setMaxAtomicWidth()810 virtual void setMaxAtomicWidth() {} 811 /// Returns true if the given target supports lock-free atomic 812 /// operations at the specified width and alignment. hasBuiltinAtomic(uint64_t AtomicSizeInBits,uint64_t AlignmentInBits)813 virtual bool hasBuiltinAtomic(uint64_t AtomicSizeInBits, 814 uint64_t AlignmentInBits) const { 815 return AtomicSizeInBits <= AlignmentInBits && 816 AtomicSizeInBits <= getMaxAtomicInlineWidth() && 817 (AtomicSizeInBits <= getCharWidth() || 818 llvm::isPowerOf2_64(AtomicSizeInBits / getCharWidth())); 819 } 820 821 /// Return the maximum vector alignment supported for the given target. getMaxVectorAlign()822 unsigned getMaxVectorAlign() const { return MaxVectorAlign; } 823 getMaxOpenCLWorkGroupSize()824 unsigned getMaxOpenCLWorkGroupSize() const { return MaxOpenCLWorkGroupSize; } 825 826 /// Return the alignment (in bits) of the thrown exception object. This is 827 /// only meaningful for targets that allocate C++ exceptions in a system 828 /// runtime, such as those using the Itanium C++ ABI. getExnObjectAlignment()829 virtual unsigned getExnObjectAlignment() const { 830 // Itanium says that an _Unwind_Exception has to be "double-word" 831 // aligned (and thus the end of it is also so-aligned), meaning 16 832 // bytes. Of course, that was written for the actual Itanium, 833 // which is a 64-bit platform. Classically, the ABI doesn't really 834 // specify the alignment on other platforms, but in practice 835 // libUnwind declares the struct with __attribute__((aligned)), so 836 // we assume that alignment here. (It's generally 16 bytes, but 837 // some targets overwrite it.) 838 return getDefaultAlignForAttributeAligned(); 839 } 840 841 /// Return the size of intmax_t and uintmax_t for this target, in bits. getIntMaxTWidth()842 unsigned getIntMaxTWidth() const { 843 return getTypeWidth(IntMaxType); 844 } 845 846 // Return the size of unwind_word for this target. getUnwindWordWidth()847 virtual unsigned getUnwindWordWidth() const { 848 return getPointerWidth(LangAS::Default); 849 } 850 851 /// Return the "preferred" register width on this target. getRegisterWidth()852 virtual unsigned getRegisterWidth() const { 853 // Currently we assume the register width on the target matches the pointer 854 // width, we can introduce a new variable for this if/when some target wants 855 // it. 856 return PointerWidth; 857 } 858 859 /// \brief Returns the default value of the __USER_LABEL_PREFIX__ macro, 860 /// which is the prefix given to user symbols by default. 861 /// 862 /// On most platforms this is "", but it is "_" on some. getUserLabelPrefix()863 const char *getUserLabelPrefix() const { return UserLabelPrefix; } 864 865 /// Returns the name of the mcount instrumentation function. getMCountName()866 const char *getMCountName() const { 867 return MCountName; 868 } 869 870 /// Check if the Objective-C built-in boolean type should be signed 871 /// char. 872 /// 873 /// Otherwise, if this returns false, the normal built-in boolean type 874 /// should also be used for Objective-C. useSignedCharForObjCBool()875 bool useSignedCharForObjCBool() const { 876 return UseSignedCharForObjCBool; 877 } noSignedCharForObjCBool()878 void noSignedCharForObjCBool() { 879 UseSignedCharForObjCBool = false; 880 } 881 882 /// Check whether the alignment of bit-field types is respected 883 /// when laying out structures. useBitFieldTypeAlignment()884 bool useBitFieldTypeAlignment() const { 885 return UseBitFieldTypeAlignment; 886 } 887 888 /// Check whether zero length bitfields should force alignment of 889 /// the next member. useZeroLengthBitfieldAlignment()890 bool useZeroLengthBitfieldAlignment() const { 891 return UseZeroLengthBitfieldAlignment; 892 } 893 894 /// Check whether zero length bitfield alignment is respected if they are 895 /// leading members. useLeadingZeroLengthBitfield()896 bool useLeadingZeroLengthBitfield() const { 897 return UseLeadingZeroLengthBitfield; 898 } 899 900 /// Get the fixed alignment value in bits for a member that follows 901 /// a zero length bitfield. getZeroLengthBitfieldBoundary()902 unsigned getZeroLengthBitfieldBoundary() const { 903 return ZeroLengthBitfieldBoundary; 904 } 905 906 /// Get the maximum alignment in bits for a static variable with 907 /// aligned attribute. getMaxAlignedAttribute()908 unsigned getMaxAlignedAttribute() const { return MaxAlignedAttribute; } 909 910 /// Check whether explicit bitfield alignment attributes should be 911 // honored, as in "__attribute__((aligned(2))) int b : 1;". useExplicitBitFieldAlignment()912 bool useExplicitBitFieldAlignment() const { 913 return UseExplicitBitFieldAlignment; 914 } 915 916 /// Check whether this target support '\#pragma options align=mac68k'. hasAlignMac68kSupport()917 bool hasAlignMac68kSupport() const { 918 return HasAlignMac68kSupport; 919 } 920 921 /// Return the user string for the specified integer type enum. 922 /// 923 /// For example, SignedShort -> "short". 924 static const char *getTypeName(IntType T); 925 926 /// Return the constant suffix for the specified integer type enum. 927 /// 928 /// For example, SignedLong -> "L". 929 const char *getTypeConstantSuffix(IntType T) const; 930 931 /// Return the printf format modifier for the specified 932 /// integer type enum. 933 /// 934 /// For example, SignedLong -> "l". 935 static const char *getTypeFormatModifier(IntType T); 936 937 /// Check whether the given real type should use the "fpret" flavor of 938 /// Objective-C message passing on this target. useObjCFPRetForRealType(FloatModeKind T)939 bool useObjCFPRetForRealType(FloatModeKind T) const { 940 return (int)((FloatModeKind)RealTypeUsesObjCFPRetMask & T); 941 } 942 943 /// Check whether _Complex long double should use the "fp2ret" flavor 944 /// of Objective-C message passing on this target. useObjCFP2RetForComplexLongDouble()945 bool useObjCFP2RetForComplexLongDouble() const { 946 return ComplexLongDoubleUsesFP2Ret; 947 } 948 949 /// Check whether llvm intrinsics such as llvm.convert.to.fp16 should be used 950 /// to convert to and from __fp16. 951 /// FIXME: This function should be removed once all targets stop using the 952 /// conversion intrinsics. useFP16ConversionIntrinsics()953 virtual bool useFP16ConversionIntrinsics() const { 954 return true; 955 } 956 957 /// Specify if mangling based on address space map should be used or 958 /// not for language specific address spaces useAddressSpaceMapMangling()959 bool useAddressSpaceMapMangling() const { 960 return UseAddrSpaceMapMangling; 961 } 962 963 ///===---- Other target property query methods --------------------------===// 964 965 /// Appends the target-specific \#define values for this 966 /// target set to the specified buffer. 967 virtual void getTargetDefines(const LangOptions &Opts, 968 MacroBuilder &Builder) const = 0; 969 970 971 /// Return information about target-specific builtins for 972 /// the current primary target, and info about which builtins are non-portable 973 /// across the current set of primary and secondary targets. 974 virtual ArrayRef<Builtin::Info> getTargetBuiltins() const = 0; 975 976 /// Returns target-specific min and max values VScale_Range. 977 virtual std::optional<std::pair<unsigned, unsigned>> getVScaleRange(const LangOptions & LangOpts)978 getVScaleRange(const LangOptions &LangOpts) const { 979 return std::nullopt; 980 } 981 /// The __builtin_clz* and __builtin_ctz* built-in 982 /// functions are specified to have undefined results for zero inputs, but 983 /// on targets that support these operations in a way that provides 984 /// well-defined results for zero without loss of performance, it is a good 985 /// idea to avoid optimizing based on that undef behavior. isCLZForZeroUndef()986 virtual bool isCLZForZeroUndef() const { return true; } 987 988 /// Returns the kind of __builtin_va_list type that should be used 989 /// with this target. 990 virtual BuiltinVaListKind getBuiltinVaListKind() const = 0; 991 992 /// Returns whether or not type \c __builtin_ms_va_list type is 993 /// available on this target. hasBuiltinMSVaList()994 bool hasBuiltinMSVaList() const { return HasBuiltinMSVaList; } 995 996 /// Returns true for RenderScript. isRenderScriptTarget()997 bool isRenderScriptTarget() const { return IsRenderScriptTarget; } 998 999 /// Returns whether or not the AArch64 SVE built-in types are 1000 /// available on this target. hasAArch64SVETypes()1001 bool hasAArch64SVETypes() const { return HasAArch64SVETypes; } 1002 1003 /// Returns whether or not the RISC-V V built-in types are 1004 /// available on this target. hasRISCVVTypes()1005 bool hasRISCVVTypes() const { return HasRISCVVTypes; } 1006 1007 /// Returns whether or not the AMDGPU unsafe floating point atomics are 1008 /// allowed. allowAMDGPUUnsafeFPAtomics()1009 bool allowAMDGPUUnsafeFPAtomics() const { return AllowAMDGPUUnsafeFPAtomics; } 1010 1011 /// For ARM targets returns a mask defining which coprocessors are configured 1012 /// as Custom Datapath. getARMCDECoprocMask()1013 uint32_t getARMCDECoprocMask() const { return ARMCDECoprocMask; } 1014 1015 /// Returns whether the passed in string is a valid clobber in an 1016 /// inline asm statement. 1017 /// 1018 /// This is used by Sema. 1019 bool isValidClobber(StringRef Name) const; 1020 1021 /// Returns whether the passed in string is a valid register name 1022 /// according to GCC. 1023 /// 1024 /// This is used by Sema for inline asm statements. 1025 virtual bool isValidGCCRegisterName(StringRef Name) const; 1026 1027 /// Returns the "normalized" GCC register name. 1028 /// 1029 /// ReturnCannonical true will return the register name without any additions 1030 /// such as "{}" or "%" in it's canonical form, for example: 1031 /// ReturnCanonical = true and Name = "rax", will return "ax". 1032 StringRef getNormalizedGCCRegisterName(StringRef Name, 1033 bool ReturnCanonical = false) const; 1034 isSPRegName(StringRef)1035 virtual bool isSPRegName(StringRef) const { return false; } 1036 1037 /// Extracts a register from the passed constraint (if it is a 1038 /// single-register constraint) and the asm label expression related to a 1039 /// variable in the input or output list of an inline asm statement. 1040 /// 1041 /// This function is used by Sema in order to diagnose conflicts between 1042 /// the clobber list and the input/output lists. getConstraintRegister(StringRef Constraint,StringRef Expression)1043 virtual StringRef getConstraintRegister(StringRef Constraint, 1044 StringRef Expression) const { 1045 return ""; 1046 } 1047 1048 struct ConstraintInfo { 1049 enum { 1050 CI_None = 0x00, 1051 CI_AllowsMemory = 0x01, 1052 CI_AllowsRegister = 0x02, 1053 CI_ReadWrite = 0x04, // "+r" output constraint (read and write). 1054 CI_HasMatchingInput = 0x08, // This output operand has a matching input. 1055 CI_ImmediateConstant = 0x10, // This operand must be an immediate constant 1056 CI_EarlyClobber = 0x20, // "&" output constraint (early clobber). 1057 }; 1058 unsigned Flags; 1059 int TiedOperand; 1060 struct { 1061 int Min; 1062 int Max; 1063 bool isConstrained; 1064 } ImmRange; 1065 llvm::SmallSet<int, 4> ImmSet; 1066 1067 std::string ConstraintStr; // constraint: "=rm" 1068 std::string Name; // Operand name: [foo] with no []'s. 1069 public: ConstraintInfoConstraintInfo1070 ConstraintInfo(StringRef ConstraintStr, StringRef Name) 1071 : Flags(0), TiedOperand(-1), ConstraintStr(ConstraintStr.str()), 1072 Name(Name.str()) { 1073 ImmRange.Min = ImmRange.Max = 0; 1074 ImmRange.isConstrained = false; 1075 } 1076 getConstraintStrConstraintInfo1077 const std::string &getConstraintStr() const { return ConstraintStr; } getNameConstraintInfo1078 const std::string &getName() const { return Name; } isReadWriteConstraintInfo1079 bool isReadWrite() const { return (Flags & CI_ReadWrite) != 0; } earlyClobberConstraintInfo1080 bool earlyClobber() { return (Flags & CI_EarlyClobber) != 0; } allowsRegisterConstraintInfo1081 bool allowsRegister() const { return (Flags & CI_AllowsRegister) != 0; } allowsMemoryConstraintInfo1082 bool allowsMemory() const { return (Flags & CI_AllowsMemory) != 0; } 1083 1084 /// Return true if this output operand has a matching 1085 /// (tied) input operand. hasMatchingInputConstraintInfo1086 bool hasMatchingInput() const { return (Flags & CI_HasMatchingInput) != 0; } 1087 1088 /// Return true if this input operand is a matching 1089 /// constraint that ties it to an output operand. 1090 /// 1091 /// If this returns true then getTiedOperand will indicate which output 1092 /// operand this is tied to. hasTiedOperandConstraintInfo1093 bool hasTiedOperand() const { return TiedOperand != -1; } getTiedOperandConstraintInfo1094 unsigned getTiedOperand() const { 1095 assert(hasTiedOperand() && "Has no tied operand!"); 1096 return (unsigned)TiedOperand; 1097 } 1098 requiresImmediateConstantConstraintInfo1099 bool requiresImmediateConstant() const { 1100 return (Flags & CI_ImmediateConstant) != 0; 1101 } isValidAsmImmediateConstraintInfo1102 bool isValidAsmImmediate(const llvm::APInt &Value) const { 1103 if (!ImmSet.empty()) 1104 return Value.isSignedIntN(32) && ImmSet.contains(Value.getZExtValue()); 1105 return !ImmRange.isConstrained || 1106 (Value.sge(ImmRange.Min) && Value.sle(ImmRange.Max)); 1107 } 1108 setIsReadWriteConstraintInfo1109 void setIsReadWrite() { Flags |= CI_ReadWrite; } setEarlyClobberConstraintInfo1110 void setEarlyClobber() { Flags |= CI_EarlyClobber; } setAllowsMemoryConstraintInfo1111 void setAllowsMemory() { Flags |= CI_AllowsMemory; } setAllowsRegisterConstraintInfo1112 void setAllowsRegister() { Flags |= CI_AllowsRegister; } setHasMatchingInputConstraintInfo1113 void setHasMatchingInput() { Flags |= CI_HasMatchingInput; } setRequiresImmediateConstraintInfo1114 void setRequiresImmediate(int Min, int Max) { 1115 Flags |= CI_ImmediateConstant; 1116 ImmRange.Min = Min; 1117 ImmRange.Max = Max; 1118 ImmRange.isConstrained = true; 1119 } setRequiresImmediateConstraintInfo1120 void setRequiresImmediate(llvm::ArrayRef<int> Exacts) { 1121 Flags |= CI_ImmediateConstant; 1122 for (int Exact : Exacts) 1123 ImmSet.insert(Exact); 1124 } setRequiresImmediateConstraintInfo1125 void setRequiresImmediate(int Exact) { 1126 Flags |= CI_ImmediateConstant; 1127 ImmSet.insert(Exact); 1128 } setRequiresImmediateConstraintInfo1129 void setRequiresImmediate() { 1130 Flags |= CI_ImmediateConstant; 1131 } 1132 1133 /// Indicate that this is an input operand that is tied to 1134 /// the specified output operand. 1135 /// 1136 /// Copy over the various constraint information from the output. setTiedOperandConstraintInfo1137 void setTiedOperand(unsigned N, ConstraintInfo &Output) { 1138 Output.setHasMatchingInput(); 1139 Flags = Output.Flags; 1140 TiedOperand = N; 1141 // Don't copy Name or constraint string. 1142 } 1143 }; 1144 1145 /// Validate register name used for global register variables. 1146 /// 1147 /// This function returns true if the register passed in RegName can be used 1148 /// for global register variables on this target. In addition, it returns 1149 /// true in HasSizeMismatch if the size of the register doesn't match the 1150 /// variable size passed in RegSize. validateGlobalRegisterVariable(StringRef RegName,unsigned RegSize,bool & HasSizeMismatch)1151 virtual bool validateGlobalRegisterVariable(StringRef RegName, 1152 unsigned RegSize, 1153 bool &HasSizeMismatch) const { 1154 HasSizeMismatch = false; 1155 return true; 1156 } 1157 1158 // validateOutputConstraint, validateInputConstraint - Checks that 1159 // a constraint is valid and provides information about it. 1160 // FIXME: These should return a real error instead of just true/false. 1161 bool validateOutputConstraint(ConstraintInfo &Info) const; 1162 bool validateInputConstraint(MutableArrayRef<ConstraintInfo> OutputConstraints, 1163 ConstraintInfo &info) const; 1164 validateOutputSize(const llvm::StringMap<bool> & FeatureMap,StringRef,unsigned)1165 virtual bool validateOutputSize(const llvm::StringMap<bool> &FeatureMap, 1166 StringRef /*Constraint*/, 1167 unsigned /*Size*/) const { 1168 return true; 1169 } 1170 validateInputSize(const llvm::StringMap<bool> & FeatureMap,StringRef,unsigned)1171 virtual bool validateInputSize(const llvm::StringMap<bool> &FeatureMap, 1172 StringRef /*Constraint*/, 1173 unsigned /*Size*/) const { 1174 return true; 1175 } 1176 virtual bool validateConstraintModifier(StringRef,char,unsigned,std::string &)1177 validateConstraintModifier(StringRef /*Constraint*/, 1178 char /*Modifier*/, 1179 unsigned /*Size*/, 1180 std::string &/*SuggestedModifier*/) const { 1181 return true; 1182 } 1183 virtual bool 1184 validateAsmConstraint(const char *&Name, 1185 TargetInfo::ConstraintInfo &info) const = 0; 1186 1187 bool resolveSymbolicName(const char *&Name, 1188 ArrayRef<ConstraintInfo> OutputConstraints, 1189 unsigned &Index) const; 1190 1191 // Constraint parm will be left pointing at the last character of 1192 // the constraint. In practice, it won't be changed unless the 1193 // constraint is longer than one character. convertConstraint(const char * & Constraint)1194 virtual std::string convertConstraint(const char *&Constraint) const { 1195 // 'p' defaults to 'r', but can be overridden by targets. 1196 if (*Constraint == 'p') 1197 return std::string("r"); 1198 return std::string(1, *Constraint); 1199 } 1200 1201 /// Replace some escaped characters with another string based on 1202 /// target-specific rules handleAsmEscapedChar(char C)1203 virtual std::optional<std::string> handleAsmEscapedChar(char C) const { 1204 return std::nullopt; 1205 } 1206 1207 /// Returns a string of target-specific clobbers, in LLVM format. 1208 virtual std::string_view getClobbers() const = 0; 1209 1210 /// Returns true if NaN encoding is IEEE 754-2008. 1211 /// Only MIPS allows a different encoding. isNan2008()1212 virtual bool isNan2008() const { 1213 return true; 1214 } 1215 1216 /// Returns the target triple of the primary target. getTriple()1217 const llvm::Triple &getTriple() const { 1218 return Triple; 1219 } 1220 1221 /// Returns the target ID if supported. getTargetID()1222 virtual std::optional<std::string> getTargetID() const { 1223 return std::nullopt; 1224 } 1225 getDataLayoutString()1226 const char *getDataLayoutString() const { 1227 assert(!DataLayoutString.empty() && "Uninitialized DataLayout!"); 1228 return DataLayoutString.c_str(); 1229 } 1230 1231 struct GCCRegAlias { 1232 const char * const Aliases[5]; 1233 const char * const Register; 1234 }; 1235 1236 struct AddlRegName { 1237 const char * const Names[5]; 1238 const unsigned RegNum; 1239 }; 1240 1241 /// Does this target support "protected" visibility? 1242 /// 1243 /// Any target which dynamic libraries will naturally support 1244 /// something like "default" (meaning that the symbol is visible 1245 /// outside this shared object) and "hidden" (meaning that it isn't) 1246 /// visibilities, but "protected" is really an ELF-specific concept 1247 /// with weird semantics designed around the convenience of dynamic 1248 /// linker implementations. Which is not to suggest that there's 1249 /// consistent target-independent semantics for "default" visibility 1250 /// either; the entire thing is pretty badly mangled. hasProtectedVisibility()1251 virtual bool hasProtectedVisibility() const { return true; } 1252 1253 /// Does this target aim for semantic compatibility with 1254 /// Microsoft C++ code using dllimport/export attributes? shouldDLLImportComdatSymbols()1255 virtual bool shouldDLLImportComdatSymbols() const { 1256 return getTriple().isWindowsMSVCEnvironment() || 1257 getTriple().isWindowsItaniumEnvironment() || getTriple().isPS(); 1258 } 1259 1260 // Does this target have PS4 specific dllimport/export handling? hasPS4DLLImportExport()1261 virtual bool hasPS4DLLImportExport() const { 1262 return getTriple().isPS() || 1263 // Windows Itanium support allows for testing the SCEI flavour of 1264 // dllimport/export handling on a Windows system. 1265 (getTriple().isWindowsItaniumEnvironment() && 1266 getTriple().getVendor() == llvm::Triple::SCEI); 1267 } 1268 1269 /// Set forced language options. 1270 /// 1271 /// Apply changes to the target information with respect to certain 1272 /// language options which change the target configuration and adjust 1273 /// the language based on the target options where applicable. 1274 virtual void adjust(DiagnosticsEngine &Diags, LangOptions &Opts); 1275 1276 /// Initialize the map with the default set of target features for the 1277 /// CPU this should include all legal feature strings on the target. 1278 /// 1279 /// \return False on error (invalid features). 1280 virtual bool initFeatureMap(llvm::StringMap<bool> &Features, 1281 DiagnosticsEngine &Diags, StringRef CPU, 1282 const std::vector<std::string> &FeatureVec) const; 1283 1284 /// Get the ABI currently in use. getABI()1285 virtual StringRef getABI() const { return StringRef(); } 1286 1287 /// Get the C++ ABI currently in use. getCXXABI()1288 TargetCXXABI getCXXABI() const { 1289 return TheCXXABI; 1290 } 1291 1292 /// Target the specified CPU. 1293 /// 1294 /// \return False on error (invalid CPU name). setCPU(const std::string & Name)1295 virtual bool setCPU(const std::string &Name) { 1296 return false; 1297 } 1298 1299 /// Fill a SmallVectorImpl with the valid values to setCPU. fillValidCPUList(SmallVectorImpl<StringRef> & Values)1300 virtual void fillValidCPUList(SmallVectorImpl<StringRef> &Values) const {} 1301 1302 /// Fill a SmallVectorImpl with the valid values for tuning CPU. fillValidTuneCPUList(SmallVectorImpl<StringRef> & Values)1303 virtual void fillValidTuneCPUList(SmallVectorImpl<StringRef> &Values) const { 1304 fillValidCPUList(Values); 1305 } 1306 1307 /// Determine whether this TargetInfo supports the given CPU name. isValidCPUName(StringRef Name)1308 virtual bool isValidCPUName(StringRef Name) const { 1309 return true; 1310 } 1311 1312 /// Determine whether this TargetInfo supports the given CPU name for 1313 /// tuning. isValidTuneCPUName(StringRef Name)1314 virtual bool isValidTuneCPUName(StringRef Name) const { 1315 return isValidCPUName(Name); 1316 } 1317 1318 virtual ParsedTargetAttr parseTargetAttr(StringRef Str) const; 1319 1320 /// Determine whether this TargetInfo supports tune in target attribute. supportsTargetAttributeTune()1321 virtual bool supportsTargetAttributeTune() const { 1322 return false; 1323 } 1324 1325 /// Use the specified ABI. 1326 /// 1327 /// \return False on error (invalid ABI name). setABI(const std::string & Name)1328 virtual bool setABI(const std::string &Name) { 1329 return false; 1330 } 1331 1332 /// Use the specified unit for FP math. 1333 /// 1334 /// \return False on error (invalid unit name). setFPMath(StringRef Name)1335 virtual bool setFPMath(StringRef Name) { 1336 return false; 1337 } 1338 1339 /// Check if target has a given feature enabled hasFeatureEnabled(const llvm::StringMap<bool> & Features,StringRef Name)1340 virtual bool hasFeatureEnabled(const llvm::StringMap<bool> &Features, 1341 StringRef Name) const { 1342 return Features.lookup(Name); 1343 } 1344 1345 /// Enable or disable a specific target feature; 1346 /// the feature name must be valid. setFeatureEnabled(llvm::StringMap<bool> & Features,StringRef Name,bool Enabled)1347 virtual void setFeatureEnabled(llvm::StringMap<bool> &Features, 1348 StringRef Name, 1349 bool Enabled) const { 1350 Features[Name] = Enabled; 1351 } 1352 1353 /// Determine whether this TargetInfo supports the given feature. isValidFeatureName(StringRef Feature)1354 virtual bool isValidFeatureName(StringRef Feature) const { 1355 return true; 1356 } 1357 1358 /// Returns true if feature has an impact on target code 1359 /// generation. doesFeatureAffectCodeGen(StringRef Feature)1360 virtual bool doesFeatureAffectCodeGen(StringRef Feature) const { 1361 return true; 1362 } 1363 1364 /// For given feature return dependent ones. getFeatureDependencies(StringRef Feature)1365 virtual StringRef getFeatureDependencies(StringRef Feature) const { 1366 return StringRef(); 1367 } 1368 1369 struct BranchProtectionInfo { 1370 LangOptions::SignReturnAddressScopeKind SignReturnAddr = 1371 LangOptions::SignReturnAddressScopeKind::None; 1372 LangOptions::SignReturnAddressKeyKind SignKey = 1373 LangOptions::SignReturnAddressKeyKind::AKey; 1374 bool BranchTargetEnforcement = false; 1375 bool BranchProtectionPAuthLR = false; 1376 bool GuardedControlStack = false; 1377 }; 1378 1379 /// Determine if the Architecture in this TargetInfo supports branch 1380 /// protection isBranchProtectionSupportedArch(StringRef Arch)1381 virtual bool isBranchProtectionSupportedArch(StringRef Arch) const { 1382 return false; 1383 } 1384 1385 /// Determine if this TargetInfo supports the given branch protection 1386 /// specification validateBranchProtection(StringRef Spec,StringRef Arch,BranchProtectionInfo & BPI,StringRef & Err)1387 virtual bool validateBranchProtection(StringRef Spec, StringRef Arch, 1388 BranchProtectionInfo &BPI, 1389 StringRef &Err) const { 1390 Err = ""; 1391 return false; 1392 } 1393 1394 /// Perform initialization based on the user configured 1395 /// set of features (e.g., +sse4). 1396 /// 1397 /// The list is guaranteed to have at most one entry per feature. 1398 /// 1399 /// The target may modify the features list, to change which options are 1400 /// passed onwards to the backend. 1401 /// FIXME: This part should be fixed so that we can change handleTargetFeatures 1402 /// to merely a TargetInfo initialization routine. 1403 /// 1404 /// \return False on error. handleTargetFeatures(std::vector<std::string> & Features,DiagnosticsEngine & Diags)1405 virtual bool handleTargetFeatures(std::vector<std::string> &Features, 1406 DiagnosticsEngine &Diags) { 1407 return true; 1408 } 1409 1410 /// Determine whether the given target has the given feature. hasFeature(StringRef Feature)1411 virtual bool hasFeature(StringRef Feature) const { 1412 return false; 1413 } 1414 1415 /// Determine whether the given target feature is read only. isReadOnlyFeature(StringRef Feature)1416 bool isReadOnlyFeature(StringRef Feature) const { 1417 return ReadOnlyFeatures.count(Feature); 1418 } 1419 1420 /// Identify whether this target supports multiversioning of functions, 1421 /// which requires support for cpu_supports and cpu_is functionality. supportsMultiVersioning()1422 bool supportsMultiVersioning() const { 1423 return getTriple().isX86() || getTriple().isAArch64(); 1424 } 1425 1426 /// Identify whether this target supports IFuncs. supportsIFunc()1427 bool supportsIFunc() const { 1428 if (getTriple().isOSBinFormatMachO()) 1429 return true; 1430 return getTriple().isOSBinFormatELF() && 1431 ((getTriple().isOSLinux() && !getTriple().isMusl()) || 1432 getTriple().isOSFreeBSD()); 1433 } 1434 1435 // Validate the contents of the __builtin_cpu_supports(const char*) 1436 // argument. validateCpuSupports(StringRef Name)1437 virtual bool validateCpuSupports(StringRef Name) const { return false; } 1438 1439 // Return the target-specific priority for features/cpus/vendors so 1440 // that they can be properly sorted for checking. multiVersionSortPriority(StringRef Name)1441 virtual unsigned multiVersionSortPriority(StringRef Name) const { 1442 return 0; 1443 } 1444 1445 // Return the target-specific cost for feature 1446 // that taken into account in priority sorting. multiVersionFeatureCost()1447 virtual unsigned multiVersionFeatureCost() const { return 0; } 1448 1449 // Validate the contents of the __builtin_cpu_is(const char*) 1450 // argument. validateCpuIs(StringRef Name)1451 virtual bool validateCpuIs(StringRef Name) const { return false; } 1452 1453 // Validate a cpu_dispatch/cpu_specific CPU option, which is a different list 1454 // from cpu_is, since it checks via features rather than CPUs directly. validateCPUSpecificCPUDispatch(StringRef Name)1455 virtual bool validateCPUSpecificCPUDispatch(StringRef Name) const { 1456 return false; 1457 } 1458 1459 // Get the character to be added for mangling purposes for cpu_specific. CPUSpecificManglingCharacter(StringRef Name)1460 virtual char CPUSpecificManglingCharacter(StringRef Name) const { 1461 llvm_unreachable( 1462 "cpu_specific Multiversioning not implemented on this target"); 1463 } 1464 1465 // Get the value for the 'tune-cpu' flag for a cpu_specific variant with the 1466 // programmer-specified 'Name'. getCPUSpecificTuneName(StringRef Name)1467 virtual StringRef getCPUSpecificTuneName(StringRef Name) const { 1468 llvm_unreachable( 1469 "cpu_specific Multiversioning not implemented on this target"); 1470 } 1471 1472 // Get a list of the features that make up the CPU option for 1473 // cpu_specific/cpu_dispatch so that it can be passed to llvm as optimization 1474 // options. getCPUSpecificCPUDispatchFeatures(StringRef Name,llvm::SmallVectorImpl<StringRef> & Features)1475 virtual void getCPUSpecificCPUDispatchFeatures( 1476 StringRef Name, llvm::SmallVectorImpl<StringRef> &Features) const { 1477 llvm_unreachable( 1478 "cpu_specific Multiversioning not implemented on this target"); 1479 } 1480 1481 // Get the cache line size of a given cpu. This method switches over 1482 // the given cpu and returns "std::nullopt" if the CPU is not found. getCPUCacheLineSize()1483 virtual std::optional<unsigned> getCPUCacheLineSize() const { 1484 return std::nullopt; 1485 } 1486 1487 // Returns maximal number of args passed in registers. getRegParmMax()1488 unsigned getRegParmMax() const { 1489 assert(RegParmMax < 7 && "RegParmMax value is larger than AST can handle"); 1490 return RegParmMax; 1491 } 1492 1493 /// Whether the target supports thread-local storage. isTLSSupported()1494 bool isTLSSupported() const { 1495 return TLSSupported; 1496 } 1497 1498 /// Return the maximum alignment (in bits) of a TLS variable 1499 /// 1500 /// Gets the maximum alignment (in bits) of a TLS variable on this target. 1501 /// Returns zero if there is no such constraint. getMaxTLSAlign()1502 unsigned getMaxTLSAlign() const { return MaxTLSAlign; } 1503 1504 /// Whether target supports variable-length arrays. isVLASupported()1505 bool isVLASupported() const { return VLASupported; } 1506 1507 /// Whether the target supports SEH __try. isSEHTrySupported()1508 bool isSEHTrySupported() const { 1509 return getTriple().isOSWindows() && 1510 (getTriple().isX86() || 1511 getTriple().getArch() == llvm::Triple::aarch64); 1512 } 1513 1514 /// Return true if {|} are normal characters in the asm string. 1515 /// 1516 /// If this returns false (the default), then {abc|xyz} is syntax 1517 /// that says that when compiling for asm variant #0, "abc" should be 1518 /// generated, but when compiling for asm variant #1, "xyz" should be 1519 /// generated. hasNoAsmVariants()1520 bool hasNoAsmVariants() const { 1521 return NoAsmVariants; 1522 } 1523 1524 /// Return the register number that __builtin_eh_return_regno would 1525 /// return with the specified argument. 1526 /// This corresponds with TargetLowering's getExceptionPointerRegister 1527 /// and getExceptionSelectorRegister in the backend. getEHDataRegisterNumber(unsigned RegNo)1528 virtual int getEHDataRegisterNumber(unsigned RegNo) const { 1529 return -1; 1530 } 1531 1532 /// Return the section to use for C++ static initialization functions. getStaticInitSectionSpecifier()1533 virtual const char *getStaticInitSectionSpecifier() const { 1534 return nullptr; 1535 } 1536 getAddressSpaceMap()1537 const LangASMap &getAddressSpaceMap() const { return *AddrSpaceMap; } getTargetAddressSpace(LangAS AS)1538 unsigned getTargetAddressSpace(LangAS AS) const { 1539 if (isTargetAddressSpace(AS)) 1540 return toTargetAddressSpace(AS); 1541 return getAddressSpaceMap()[(unsigned)AS]; 1542 } 1543 1544 /// Map from the address space field in builtin description strings to the 1545 /// language address space. getOpenCLBuiltinAddressSpace(unsigned AS)1546 virtual LangAS getOpenCLBuiltinAddressSpace(unsigned AS) const { 1547 return getLangASFromTargetAS(AS); 1548 } 1549 1550 /// Map from the address space field in builtin description strings to the 1551 /// language address space. getCUDABuiltinAddressSpace(unsigned AS)1552 virtual LangAS getCUDABuiltinAddressSpace(unsigned AS) const { 1553 return getLangASFromTargetAS(AS); 1554 } 1555 1556 /// Return an AST address space which can be used opportunistically 1557 /// for constant global memory. It must be possible to convert pointers into 1558 /// this address space to LangAS::Default. If no such address space exists, 1559 /// this may return std::nullopt, and such optimizations will be disabled. getConstantAddressSpace()1560 virtual std::optional<LangAS> getConstantAddressSpace() const { 1561 return LangAS::Default; 1562 } 1563 1564 // access target-specific GPU grid values that must be consistent between 1565 // host RTL (plugin), deviceRTL and clang. getGridValue()1566 virtual const llvm::omp::GV &getGridValue() const { 1567 llvm_unreachable("getGridValue not implemented on this target"); 1568 } 1569 1570 /// Retrieve the name of the platform as it is used in the 1571 /// availability attribute. getPlatformName()1572 StringRef getPlatformName() const { return PlatformName; } 1573 1574 /// Retrieve the minimum desired version of the platform, to 1575 /// which the program should be compiled. getPlatformMinVersion()1576 VersionTuple getPlatformMinVersion() const { return PlatformMinVersion; } 1577 isBigEndian()1578 bool isBigEndian() const { return BigEndian; } isLittleEndian()1579 bool isLittleEndian() const { return !BigEndian; } 1580 1581 /// Whether the option -fextend-arguments={32,64} is supported on the target. supportsExtendIntArgs()1582 virtual bool supportsExtendIntArgs() const { return false; } 1583 1584 /// Controls if __arithmetic_fence is supported in the targeted backend. checkArithmeticFenceSupported()1585 virtual bool checkArithmeticFenceSupported() const { return false; } 1586 1587 /// Gets the default calling convention for the given target and 1588 /// declaration context. getDefaultCallingConv()1589 virtual CallingConv getDefaultCallingConv() const { 1590 // Not all targets will specify an explicit calling convention that we can 1591 // express. This will always do the right thing, even though it's not 1592 // an explicit calling convention. 1593 return CC_C; 1594 } 1595 1596 enum CallingConvCheckResult { 1597 CCCR_OK, 1598 CCCR_Warning, 1599 CCCR_Ignore, 1600 CCCR_Error, 1601 }; 1602 1603 /// Determines whether a given calling convention is valid for the 1604 /// target. A calling convention can either be accepted, produce a warning 1605 /// and be substituted with the default calling convention, or (someday) 1606 /// produce an error (such as using thiscall on a non-instance function). checkCallingConvention(CallingConv CC)1607 virtual CallingConvCheckResult checkCallingConvention(CallingConv CC) const { 1608 switch (CC) { 1609 default: 1610 return CCCR_Warning; 1611 case CC_C: 1612 return CCCR_OK; 1613 } 1614 } 1615 1616 enum CallingConvKind { 1617 CCK_Default, 1618 CCK_ClangABI4OrPS4, 1619 CCK_MicrosoftWin64 1620 }; 1621 1622 virtual CallingConvKind getCallingConvKind(bool ClangABICompat4) const; 1623 1624 /// Controls whether explicitly defaulted (`= default`) special member 1625 /// functions disqualify something from being POD-for-the-purposes-of-layout. 1626 /// Historically, Clang didn't consider these acceptable for POD, but GCC 1627 /// does. So in newer Clang ABIs they are acceptable for POD to be compatible 1628 /// with GCC/Itanium ABI, and remains disqualifying for targets that need 1629 /// Clang backwards compatibility rather than GCC/Itanium ABI compatibility. 1630 virtual bool areDefaultedSMFStillPOD(const LangOptions&) const; 1631 1632 /// Controls if __builtin_longjmp / __builtin_setjmp can be lowered to 1633 /// llvm.eh.sjlj.longjmp / llvm.eh.sjlj.setjmp. hasSjLjLowering()1634 virtual bool hasSjLjLowering() const { 1635 return false; 1636 } 1637 1638 /// Check if the target supports CFProtection branch. 1639 virtual bool 1640 checkCFProtectionBranchSupported(DiagnosticsEngine &Diags) const; 1641 1642 /// Check if the target supports CFProtection return. 1643 virtual bool 1644 checkCFProtectionReturnSupported(DiagnosticsEngine &Diags) const; 1645 1646 /// Whether target allows to overalign ABI-specified preferred alignment allowsLargerPreferedTypeAlignment()1647 virtual bool allowsLargerPreferedTypeAlignment() const { return true; } 1648 1649 /// Whether target defaults to the `power` alignment rules of AIX. defaultsToAIXPowerAlignment()1650 virtual bool defaultsToAIXPowerAlignment() const { return false; } 1651 1652 /// Set supported OpenCL extensions and optional core features. setSupportedOpenCLOpts()1653 virtual void setSupportedOpenCLOpts() {} 1654 1655 virtual void supportAllOpenCLOpts(bool V = true) { 1656 #define OPENCLEXTNAME(Ext) \ 1657 setFeatureEnabled(getTargetOpts().OpenCLFeaturesMap, #Ext, V); 1658 #include "clang/Basic/OpenCLExtensions.def" 1659 } 1660 1661 /// Set supported OpenCL extensions as written on command line setCommandLineOpenCLOpts()1662 virtual void setCommandLineOpenCLOpts() { 1663 for (const auto &Ext : getTargetOpts().OpenCLExtensionsAsWritten) { 1664 bool IsPrefixed = (Ext[0] == '+' || Ext[0] == '-'); 1665 std::string Name = IsPrefixed ? Ext.substr(1) : Ext; 1666 bool V = IsPrefixed ? Ext[0] == '+' : true; 1667 1668 if (Name == "all") { 1669 supportAllOpenCLOpts(V); 1670 continue; 1671 } 1672 1673 getTargetOpts().OpenCLFeaturesMap[Name] = V; 1674 } 1675 } 1676 1677 /// Get supported OpenCL extensions and optional core features. getSupportedOpenCLOpts()1678 llvm::StringMap<bool> &getSupportedOpenCLOpts() { 1679 return getTargetOpts().OpenCLFeaturesMap; 1680 } 1681 1682 /// Get const supported OpenCL extensions and optional core features. getSupportedOpenCLOpts()1683 const llvm::StringMap<bool> &getSupportedOpenCLOpts() const { 1684 return getTargetOpts().OpenCLFeaturesMap; 1685 } 1686 1687 /// Get address space for OpenCL type. 1688 virtual LangAS getOpenCLTypeAddrSpace(OpenCLTypeKind TK) const; 1689 1690 /// \returns Target specific vtbl ptr address space. getVtblPtrAddressSpace()1691 virtual unsigned getVtblPtrAddressSpace() const { 1692 return 0; 1693 } 1694 1695 /// \returns If a target requires an address within a target specific address 1696 /// space \p AddressSpace to be converted in order to be used, then return the 1697 /// corresponding target specific DWARF address space. 1698 /// 1699 /// \returns Otherwise return std::nullopt and no conversion will be emitted 1700 /// in the DWARF. getDWARFAddressSpace(unsigned AddressSpace)1701 virtual std::optional<unsigned> getDWARFAddressSpace(unsigned AddressSpace) 1702 const { 1703 return std::nullopt; 1704 } 1705 1706 /// \returns The version of the SDK which was used during the compilation if 1707 /// one was specified, or an empty version otherwise. getSDKVersion()1708 const llvm::VersionTuple &getSDKVersion() const { 1709 return getTargetOpts().SDKVersion; 1710 } 1711 1712 /// Check the target is valid after it is fully initialized. validateTarget(DiagnosticsEngine & Diags)1713 virtual bool validateTarget(DiagnosticsEngine &Diags) const { 1714 return true; 1715 } 1716 1717 /// Check that OpenCL target has valid options setting based on OpenCL 1718 /// version. 1719 virtual bool validateOpenCLTarget(const LangOptions &Opts, 1720 DiagnosticsEngine &Diags) const; 1721 setAuxTarget(const TargetInfo * Aux)1722 virtual void setAuxTarget(const TargetInfo *Aux) {} 1723 1724 /// Whether target allows debuginfo types for decl only variables/functions. allowDebugInfoForExternalRef()1725 virtual bool allowDebugInfoForExternalRef() const { return false; } 1726 1727 /// Returns the darwin target variant triple, the variant of the deployment 1728 /// target for which the code is being compiled. getDarwinTargetVariantTriple()1729 const llvm::Triple *getDarwinTargetVariantTriple() const { 1730 return DarwinTargetVariantTriple ? &*DarwinTargetVariantTriple : nullptr; 1731 } 1732 1733 /// Returns the version of the darwin target variant SDK which was used during 1734 /// the compilation if one was specified, or an empty version otherwise. getDarwinTargetVariantSDKVersion()1735 const std::optional<VersionTuple> getDarwinTargetVariantSDKVersion() const { 1736 return !getTargetOpts().DarwinTargetVariantSDKVersion.empty() 1737 ? getTargetOpts().DarwinTargetVariantSDKVersion 1738 : std::optional<VersionTuple>(); 1739 } 1740 1741 /// Whether to support HIP image/texture API's. hasHIPImageSupport()1742 virtual bool hasHIPImageSupport() const { return true; } 1743 1744 protected: 1745 /// Copy type and layout related info. 1746 void copyAuxTarget(const TargetInfo *Aux); getPointerWidthV(LangAS AddrSpace)1747 virtual uint64_t getPointerWidthV(LangAS AddrSpace) const { 1748 return PointerWidth; 1749 } getPointerAlignV(LangAS AddrSpace)1750 virtual uint64_t getPointerAlignV(LangAS AddrSpace) const { 1751 return PointerAlign; 1752 } getPtrDiffTypeV(LangAS AddrSpace)1753 virtual enum IntType getPtrDiffTypeV(LangAS AddrSpace) const { 1754 return PtrDiffType; 1755 } 1756 virtual ArrayRef<const char *> getGCCRegNames() const = 0; 1757 virtual ArrayRef<GCCRegAlias> getGCCRegAliases() const = 0; getGCCAddlRegNames()1758 virtual ArrayRef<AddlRegName> getGCCAddlRegNames() const { 1759 return std::nullopt; 1760 } 1761 1762 private: 1763 // Assert the values for the fractional and integral bits for each fixed point 1764 // type follow the restrictions given in clause 6.2.6.3 of N1169. 1765 void CheckFixedPointBits() const; 1766 }; 1767 1768 } // end namespace clang 1769 1770 #endif 1771