10b57cec5SDimitry Andric //===--- Specifiers.h - Declaration and Type Specifiers ---------*- C++ -*-===// 20b57cec5SDimitry Andric // 30b57cec5SDimitry Andric // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 40b57cec5SDimitry Andric // See https://llvm.org/LICENSE.txt for license information. 50b57cec5SDimitry Andric // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 60b57cec5SDimitry Andric // 70b57cec5SDimitry Andric //===----------------------------------------------------------------------===// 80b57cec5SDimitry Andric /// 90b57cec5SDimitry Andric /// \file 100b57cec5SDimitry Andric /// Defines various enumerations that describe declaration and 110b57cec5SDimitry Andric /// type specifiers. 120b57cec5SDimitry Andric /// 130b57cec5SDimitry Andric //===----------------------------------------------------------------------===// 140b57cec5SDimitry Andric 150b57cec5SDimitry Andric #ifndef LLVM_CLANG_BASIC_SPECIFIERS_H 160b57cec5SDimitry Andric #define LLVM_CLANG_BASIC_SPECIFIERS_H 170b57cec5SDimitry Andric 180b57cec5SDimitry Andric #include "llvm/ADT/StringRef.h" 190b57cec5SDimitry Andric #include "llvm/Support/DataTypes.h" 200b57cec5SDimitry Andric #include "llvm/Support/ErrorHandling.h" 210b57cec5SDimitry Andric 2206c3fb27SDimitry Andric namespace llvm { 2306c3fb27SDimitry Andric class raw_ostream; 2406c3fb27SDimitry Andric } // namespace llvm 250b57cec5SDimitry Andric namespace clang { 260b57cec5SDimitry Andric 270b57cec5SDimitry Andric /// Define the meaning of possible values of the kind in ExplicitSpecifier. 280b57cec5SDimitry Andric enum class ExplicitSpecKind : unsigned { 290b57cec5SDimitry Andric ResolvedFalse, 300b57cec5SDimitry Andric ResolvedTrue, 310b57cec5SDimitry Andric Unresolved, 320b57cec5SDimitry Andric }; 330b57cec5SDimitry Andric 340b57cec5SDimitry Andric /// Define the kind of constexpr specifier. 35e8d8bef9SDimitry Andric enum class ConstexprSpecKind { Unspecified, Constexpr, Consteval, Constinit }; 360b57cec5SDimitry Andric 37bdd1243dSDimitry Andric /// In an if statement, this denotes whether the statement is 38349cc55cSDimitry Andric /// a constexpr or consteval if statement. 39349cc55cSDimitry Andric enum class IfStatementKind : unsigned { 40349cc55cSDimitry Andric Ordinary, 41349cc55cSDimitry Andric Constexpr, 42349cc55cSDimitry Andric ConstevalNonNegated, 43349cc55cSDimitry Andric ConstevalNegated 44349cc55cSDimitry Andric }; 45349cc55cSDimitry Andric 460b57cec5SDimitry Andric /// Specifies the width of a type, e.g., short, long, or long long. 47e8d8bef9SDimitry Andric enum class TypeSpecifierWidth { Unspecified, Short, Long, LongLong }; 480b57cec5SDimitry Andric 490b57cec5SDimitry Andric /// Specifies the signedness of a type, e.g., signed or unsigned. 50e8d8bef9SDimitry Andric enum class TypeSpecifierSign { Unspecified, Signed, Unsigned }; 510b57cec5SDimitry Andric 52e8d8bef9SDimitry Andric enum class TypeSpecifiersPipe { Unspecified, Pipe }; 530b57cec5SDimitry Andric 540b57cec5SDimitry Andric /// Specifies the kind of type. 550b57cec5SDimitry Andric enum TypeSpecifierType { 560b57cec5SDimitry Andric TST_unspecified, 570b57cec5SDimitry Andric TST_void, 580b57cec5SDimitry Andric TST_char, 590b57cec5SDimitry Andric TST_wchar, // C++ wchar_t 600b57cec5SDimitry Andric TST_char8, // C++20 char8_t (proposed) 610b57cec5SDimitry Andric TST_char16, // C++11 char16_t 620b57cec5SDimitry Andric TST_char32, // C++11 char32_t 630b57cec5SDimitry Andric TST_int, 640b57cec5SDimitry Andric TST_int128, 650eae32dcSDimitry Andric TST_bitint, // Bit-precise integer types. 660b57cec5SDimitry Andric TST_half, // OpenCL half, ARM NEON __fp16 670b57cec5SDimitry Andric TST_Float16, // C11 extension ISO/IEC TS 18661-3 680b57cec5SDimitry Andric TST_Accum, // ISO/IEC JTC1 SC22 WG14 N1169 Extension 690b57cec5SDimitry Andric TST_Fract, 705ffd83dbSDimitry Andric TST_BFloat16, 710b57cec5SDimitry Andric TST_float, 720b57cec5SDimitry Andric TST_double, 730b57cec5SDimitry Andric TST_float128, 74349cc55cSDimitry Andric TST_ibm128, 750b57cec5SDimitry Andric TST_bool, // _Bool 760b57cec5SDimitry Andric TST_decimal32, // _Decimal32 770b57cec5SDimitry Andric TST_decimal64, // _Decimal64 780b57cec5SDimitry Andric TST_decimal128, // _Decimal128 790b57cec5SDimitry Andric TST_enum, 800b57cec5SDimitry Andric TST_union, 810b57cec5SDimitry Andric TST_struct, 820b57cec5SDimitry Andric TST_class, // C++ class type 830b57cec5SDimitry Andric TST_interface, // C++ (Microsoft-specific) __interface type 840b57cec5SDimitry Andric TST_typename, // Typedef, C++ class-name or enum name, etc. 855f757f3fSDimitry Andric TST_typeofType, // C23 (and GNU extension) typeof(type-name) 865f757f3fSDimitry Andric TST_typeofExpr, // C23 (and GNU extension) typeof(expression) 875f757f3fSDimitry Andric TST_typeof_unqualType, // C23 typeof_unqual(type-name) 885f757f3fSDimitry Andric TST_typeof_unqualExpr, // C23 typeof_unqual(expression) 890b57cec5SDimitry Andric TST_decltype, // C++11 decltype 90bdd1243dSDimitry Andric #define TRANSFORM_TYPE_TRAIT_DEF(_, Trait) TST_##Trait, 91bdd1243dSDimitry Andric #include "clang/Basic/TransformTypeTraits.def" 920b57cec5SDimitry Andric TST_auto, // C++11 auto 930b57cec5SDimitry Andric TST_decltype_auto, // C++1y decltype(auto) 940b57cec5SDimitry Andric TST_auto_type, // __auto_type extension 950b57cec5SDimitry Andric TST_unknown_anytype, // __unknown_anytype extension 960b57cec5SDimitry Andric TST_atomic, // C11 _Atomic 970b57cec5SDimitry Andric #define GENERIC_IMAGE_TYPE(ImgType, Id) TST_##ImgType##_t, // OpenCL image types 980b57cec5SDimitry Andric #include "clang/Basic/OpenCLImageTypes.def" 990b57cec5SDimitry Andric TST_error // erroneous type 1000b57cec5SDimitry Andric }; 1010b57cec5SDimitry Andric 1020b57cec5SDimitry Andric /// Structure that packs information about the type specifiers that 1030b57cec5SDimitry Andric /// were written in a particular type specifier sequence. 1040b57cec5SDimitry Andric struct WrittenBuiltinSpecs { 105bdd1243dSDimitry Andric static_assert(TST_error < 1 << 7, "Type bitfield not wide enough for TST"); 1065f757f3fSDimitry Andric LLVM_PREFERRED_TYPE(TypeSpecifierType) 1075f757f3fSDimitry Andric unsigned Type : 7; 1085f757f3fSDimitry Andric LLVM_PREFERRED_TYPE(TypeSpecifierSign) 1095f757f3fSDimitry Andric unsigned Sign : 2; 1105f757f3fSDimitry Andric LLVM_PREFERRED_TYPE(TypeSpecifierWidth) 1115f757f3fSDimitry Andric unsigned Width : 2; 1125f757f3fSDimitry Andric LLVM_PREFERRED_TYPE(bool) 1130b57cec5SDimitry Andric unsigned ModeAttr : 1; 1140b57cec5SDimitry Andric }; 1150b57cec5SDimitry Andric 1160b57cec5SDimitry Andric /// A C++ access specifier (public, private, protected), plus the 1170b57cec5SDimitry Andric /// special value "none" which means different things in different contexts. 1180b57cec5SDimitry Andric enum AccessSpecifier { 1190b57cec5SDimitry Andric AS_public, 1200b57cec5SDimitry Andric AS_protected, 1210b57cec5SDimitry Andric AS_private, 1220b57cec5SDimitry Andric AS_none 1230b57cec5SDimitry Andric }; 1240b57cec5SDimitry Andric 1250b57cec5SDimitry Andric /// The categorization of expression values, currently following the 1260b57cec5SDimitry Andric /// C++11 scheme. 1270b57cec5SDimitry Andric enum ExprValueKind { 128fe6060f1SDimitry Andric /// A pr-value expression (in the C++11 taxonomy) 1290b57cec5SDimitry Andric /// produces a temporary value. 130fe6060f1SDimitry Andric VK_PRValue, 1310b57cec5SDimitry Andric 1320b57cec5SDimitry Andric /// An l-value expression is a reference to an object with 1330b57cec5SDimitry Andric /// independent storage. 1340b57cec5SDimitry Andric VK_LValue, 1350b57cec5SDimitry Andric 1360b57cec5SDimitry Andric /// An x-value expression is a reference to an object with 1370b57cec5SDimitry Andric /// independent storage but which can be "moved", i.e. 1380b57cec5SDimitry Andric /// efficiently cannibalized for its resources. 1390b57cec5SDimitry Andric VK_XValue 1400b57cec5SDimitry Andric }; 1410b57cec5SDimitry Andric 1420b57cec5SDimitry Andric /// A further classification of the kind of object referenced by an 1430b57cec5SDimitry Andric /// l-value or x-value. 1440b57cec5SDimitry Andric enum ExprObjectKind { 1450b57cec5SDimitry Andric /// An ordinary object is located at an address in memory. 1460b57cec5SDimitry Andric OK_Ordinary, 1470b57cec5SDimitry Andric 1480b57cec5SDimitry Andric /// A bitfield object is a bitfield on a C or C++ record. 1490b57cec5SDimitry Andric OK_BitField, 1500b57cec5SDimitry Andric 1510b57cec5SDimitry Andric /// A vector component is an element or range of elements on a vector. 1520b57cec5SDimitry Andric OK_VectorComponent, 1530b57cec5SDimitry Andric 1540b57cec5SDimitry Andric /// An Objective-C property is a logical field of an Objective-C 1550b57cec5SDimitry Andric /// object which is read and written via Objective-C method calls. 1560b57cec5SDimitry Andric OK_ObjCProperty, 1570b57cec5SDimitry Andric 1580b57cec5SDimitry Andric /// An Objective-C array/dictionary subscripting which reads an 1590b57cec5SDimitry Andric /// object or writes at the subscripted array/dictionary element via 1600b57cec5SDimitry Andric /// Objective-C method calls. 1615ffd83dbSDimitry Andric OK_ObjCSubscript, 1625ffd83dbSDimitry Andric 1635ffd83dbSDimitry Andric /// A matrix component is a single element of a matrix. 1645ffd83dbSDimitry Andric OK_MatrixComponent 1650b57cec5SDimitry Andric }; 1660b57cec5SDimitry Andric 1670b57cec5SDimitry Andric /// The reason why a DeclRefExpr does not constitute an odr-use. 1680b57cec5SDimitry Andric enum NonOdrUseReason { 1690b57cec5SDimitry Andric /// This is an odr-use. 1700b57cec5SDimitry Andric NOUR_None = 0, 1710b57cec5SDimitry Andric /// This name appears in an unevaluated operand. 1720b57cec5SDimitry Andric NOUR_Unevaluated, 1730b57cec5SDimitry Andric /// This name appears as a potential result of an lvalue-to-rvalue 1740b57cec5SDimitry Andric /// conversion that is a constant expression. 1750b57cec5SDimitry Andric NOUR_Constant, 1760b57cec5SDimitry Andric /// This name appears as a potential result of a discarded value 1770b57cec5SDimitry Andric /// expression. 1780b57cec5SDimitry Andric NOUR_Discarded, 1790b57cec5SDimitry Andric }; 1800b57cec5SDimitry Andric 1810b57cec5SDimitry Andric /// Describes the kind of template specialization that a 1820b57cec5SDimitry Andric /// particular template specialization declaration represents. 1830b57cec5SDimitry Andric enum TemplateSpecializationKind { 1840b57cec5SDimitry Andric /// This template specialization was formed from a template-id but 1850b57cec5SDimitry Andric /// has not yet been declared, defined, or instantiated. 1860b57cec5SDimitry Andric TSK_Undeclared = 0, 1870b57cec5SDimitry Andric /// This template specialization was implicitly instantiated from a 1880b57cec5SDimitry Andric /// template. (C++ [temp.inst]). 1890b57cec5SDimitry Andric TSK_ImplicitInstantiation, 1900b57cec5SDimitry Andric /// This template specialization was declared or defined by an 1910b57cec5SDimitry Andric /// explicit specialization (C++ [temp.expl.spec]) or partial 1920b57cec5SDimitry Andric /// specialization (C++ [temp.class.spec]). 1930b57cec5SDimitry Andric TSK_ExplicitSpecialization, 1940b57cec5SDimitry Andric /// This template specialization was instantiated from a template 1950b57cec5SDimitry Andric /// due to an explicit instantiation declaration request 1960b57cec5SDimitry Andric /// (C++11 [temp.explicit]). 1970b57cec5SDimitry Andric TSK_ExplicitInstantiationDeclaration, 1980b57cec5SDimitry Andric /// This template specialization was instantiated from a template 1990b57cec5SDimitry Andric /// due to an explicit instantiation definition request 2000b57cec5SDimitry Andric /// (C++ [temp.explicit]). 2010b57cec5SDimitry Andric TSK_ExplicitInstantiationDefinition 2020b57cec5SDimitry Andric }; 2030b57cec5SDimitry Andric 2040b57cec5SDimitry Andric /// Determine whether this template specialization kind refers 2050b57cec5SDimitry Andric /// to an instantiation of an entity (as opposed to a non-template or 2060b57cec5SDimitry Andric /// an explicit specialization). isTemplateInstantiation(TemplateSpecializationKind Kind)2070b57cec5SDimitry Andric inline bool isTemplateInstantiation(TemplateSpecializationKind Kind) { 2080b57cec5SDimitry Andric return Kind != TSK_Undeclared && Kind != TSK_ExplicitSpecialization; 2090b57cec5SDimitry Andric } 2100b57cec5SDimitry Andric 2110b57cec5SDimitry Andric /// True if this template specialization kind is an explicit 2120b57cec5SDimitry Andric /// specialization, explicit instantiation declaration, or explicit 2130b57cec5SDimitry Andric /// instantiation definition. isTemplateExplicitInstantiationOrSpecialization(TemplateSpecializationKind Kind)2140b57cec5SDimitry Andric inline bool isTemplateExplicitInstantiationOrSpecialization( 2150b57cec5SDimitry Andric TemplateSpecializationKind Kind) { 2160b57cec5SDimitry Andric switch (Kind) { 2170b57cec5SDimitry Andric case TSK_ExplicitSpecialization: 2180b57cec5SDimitry Andric case TSK_ExplicitInstantiationDeclaration: 2190b57cec5SDimitry Andric case TSK_ExplicitInstantiationDefinition: 2200b57cec5SDimitry Andric return true; 2210b57cec5SDimitry Andric 2220b57cec5SDimitry Andric case TSK_Undeclared: 2230b57cec5SDimitry Andric case TSK_ImplicitInstantiation: 2240b57cec5SDimitry Andric return false; 2250b57cec5SDimitry Andric } 2260b57cec5SDimitry Andric llvm_unreachable("bad template specialization kind"); 2270b57cec5SDimitry Andric } 2280b57cec5SDimitry Andric 2290b57cec5SDimitry Andric /// Thread storage-class-specifier. 2300b57cec5SDimitry Andric enum ThreadStorageClassSpecifier { 2310b57cec5SDimitry Andric TSCS_unspecified, 2320b57cec5SDimitry Andric /// GNU __thread. 2330b57cec5SDimitry Andric TSCS___thread, 2340b57cec5SDimitry Andric /// C++11 thread_local. Implies 'static' at block scope, but not at 2350b57cec5SDimitry Andric /// class scope. 2360b57cec5SDimitry Andric TSCS_thread_local, 2370b57cec5SDimitry Andric /// C11 _Thread_local. Must be combined with either 'static' or 'extern' 2380b57cec5SDimitry Andric /// if used at block scope. 2390b57cec5SDimitry Andric TSCS__Thread_local 2400b57cec5SDimitry Andric }; 2410b57cec5SDimitry Andric 2420b57cec5SDimitry Andric /// Storage classes. 2430b57cec5SDimitry Andric enum StorageClass { 2440b57cec5SDimitry Andric // These are legal on both functions and variables. 2450b57cec5SDimitry Andric SC_None, 2460b57cec5SDimitry Andric SC_Extern, 2470b57cec5SDimitry Andric SC_Static, 2480b57cec5SDimitry Andric SC_PrivateExtern, 2490b57cec5SDimitry Andric 2500b57cec5SDimitry Andric // These are only legal on variables. 2510b57cec5SDimitry Andric SC_Auto, 2520b57cec5SDimitry Andric SC_Register 2530b57cec5SDimitry Andric }; 2540b57cec5SDimitry Andric 2550b57cec5SDimitry Andric /// Checks whether the given storage class is legal for functions. isLegalForFunction(StorageClass SC)2560b57cec5SDimitry Andric inline bool isLegalForFunction(StorageClass SC) { 2570b57cec5SDimitry Andric return SC <= SC_PrivateExtern; 2580b57cec5SDimitry Andric } 2590b57cec5SDimitry Andric 2600b57cec5SDimitry Andric /// Checks whether the given storage class is legal for variables. isLegalForVariable(StorageClass SC)2610b57cec5SDimitry Andric inline bool isLegalForVariable(StorageClass SC) { 2620b57cec5SDimitry Andric return true; 2630b57cec5SDimitry Andric } 2640b57cec5SDimitry Andric 2650b57cec5SDimitry Andric /// In-class initialization styles for non-static data members. 2660b57cec5SDimitry Andric enum InClassInitStyle { 2670b57cec5SDimitry Andric ICIS_NoInit, ///< No in-class initializer. 2680b57cec5SDimitry Andric ICIS_CopyInit, ///< Copy initialization. 2690b57cec5SDimitry Andric ICIS_ListInit ///< Direct list-initialization. 2700b57cec5SDimitry Andric }; 2710b57cec5SDimitry Andric 2720b57cec5SDimitry Andric /// CallingConv - Specifies the calling convention that a function uses. 2730b57cec5SDimitry Andric enum CallingConv { 2740b57cec5SDimitry Andric CC_C, // __attribute__((cdecl)) 2750b57cec5SDimitry Andric CC_X86StdCall, // __attribute__((stdcall)) 2760b57cec5SDimitry Andric CC_X86FastCall, // __attribute__((fastcall)) 2770b57cec5SDimitry Andric CC_X86ThisCall, // __attribute__((thiscall)) 2780b57cec5SDimitry Andric CC_X86VectorCall, // __attribute__((vectorcall)) 2790b57cec5SDimitry Andric CC_X86Pascal, // __attribute__((pascal)) 2800b57cec5SDimitry Andric CC_Win64, // __attribute__((ms_abi)) 2810b57cec5SDimitry Andric CC_X86_64SysV, // __attribute__((sysv_abi)) 2820b57cec5SDimitry Andric CC_X86RegCall, // __attribute__((regcall)) 2830b57cec5SDimitry Andric CC_AAPCS, // __attribute__((pcs("aapcs"))) 2840b57cec5SDimitry Andric CC_AAPCS_VFP, // __attribute__((pcs("aapcs-vfp"))) 2850b57cec5SDimitry Andric CC_IntelOclBicc, // __attribute__((intel_ocl_bicc)) 2860b57cec5SDimitry Andric CC_SpirFunction, // default for OpenCL functions on SPIR target 2870b57cec5SDimitry Andric CC_OpenCLKernel, // inferred for OpenCL kernels 2880b57cec5SDimitry Andric CC_Swift, // __attribute__((swiftcall)) 289fe6060f1SDimitry Andric CC_SwiftAsync, // __attribute__((swiftasynccall)) 2900b57cec5SDimitry Andric CC_PreserveMost, // __attribute__((preserve_most)) 2910b57cec5SDimitry Andric CC_PreserveAll, // __attribute__((preserve_all)) 2920b57cec5SDimitry Andric CC_AArch64VectorCall, // __attribute__((aarch64_vector_pcs)) 29381ad6265SDimitry Andric CC_AArch64SVEPCS, // __attribute__((aarch64_sve_pcs)) 29481ad6265SDimitry Andric CC_AMDGPUKernelCall, // __attribute__((amdgpu_kernel)) 2955f757f3fSDimitry Andric CC_M68kRTD, // __attribute__((m68k_rtd)) 2960b57cec5SDimitry Andric }; 2970b57cec5SDimitry Andric 2980b57cec5SDimitry Andric /// Checks whether the given calling convention supports variadic 2990b57cec5SDimitry Andric /// calls. Unprototyped calls also use the variadic call rules. supportsVariadicCall(CallingConv CC)3000b57cec5SDimitry Andric inline bool supportsVariadicCall(CallingConv CC) { 3010b57cec5SDimitry Andric switch (CC) { 3020b57cec5SDimitry Andric case CC_X86StdCall: 3030b57cec5SDimitry Andric case CC_X86FastCall: 3040b57cec5SDimitry Andric case CC_X86ThisCall: 3050b57cec5SDimitry Andric case CC_X86RegCall: 3060b57cec5SDimitry Andric case CC_X86Pascal: 3070b57cec5SDimitry Andric case CC_X86VectorCall: 3080b57cec5SDimitry Andric case CC_SpirFunction: 3090b57cec5SDimitry Andric case CC_OpenCLKernel: 3100b57cec5SDimitry Andric case CC_Swift: 311fe6060f1SDimitry Andric case CC_SwiftAsync: 3125f757f3fSDimitry Andric case CC_M68kRTD: 3130b57cec5SDimitry Andric return false; 3140b57cec5SDimitry Andric default: 3150b57cec5SDimitry Andric return true; 3160b57cec5SDimitry Andric } 3170b57cec5SDimitry Andric } 3180b57cec5SDimitry Andric 3190b57cec5SDimitry Andric /// The storage duration for an object (per C++ [basic.stc]). 3200b57cec5SDimitry Andric enum StorageDuration { 3210b57cec5SDimitry Andric SD_FullExpression, ///< Full-expression storage duration (for temporaries). 3220b57cec5SDimitry Andric SD_Automatic, ///< Automatic storage duration (most local variables). 3230b57cec5SDimitry Andric SD_Thread, ///< Thread storage duration. 3240b57cec5SDimitry Andric SD_Static, ///< Static storage duration. 3250b57cec5SDimitry Andric SD_Dynamic ///< Dynamic storage duration. 3260b57cec5SDimitry Andric }; 3270b57cec5SDimitry Andric 3280b57cec5SDimitry Andric /// Describes the nullability of a particular type. 3290b57cec5SDimitry Andric enum class NullabilityKind : uint8_t { 3300b57cec5SDimitry Andric /// Values of this type can never be null. 3310b57cec5SDimitry Andric NonNull = 0, 3320b57cec5SDimitry Andric /// Values of this type can be null. 3330b57cec5SDimitry Andric Nullable, 3340b57cec5SDimitry Andric /// Whether values of this type can be null is (explicitly) 3350b57cec5SDimitry Andric /// unspecified. This captures a (fairly rare) case where we 3360b57cec5SDimitry Andric /// can't conclude anything about the nullability of the type even 3370b57cec5SDimitry Andric /// though it has been considered. 338e8d8bef9SDimitry Andric Unspecified, 339e8d8bef9SDimitry Andric // Generally behaves like Nullable, except when used in a block parameter 340e8d8bef9SDimitry Andric // that was imported into a swift async method. There, swift will assume 34181ad6265SDimitry Andric // that the parameter can get null even if no error occurred. _Nullable 342e8d8bef9SDimitry Andric // parameters are assumed to only get null on error. 343e8d8bef9SDimitry Andric NullableResult, 3440b57cec5SDimitry Andric }; 34506c3fb27SDimitry Andric /// Prints human-readable debug representation. 34606c3fb27SDimitry Andric llvm::raw_ostream &operator<<(llvm::raw_ostream&, NullabilityKind); 3470b57cec5SDimitry Andric 3480b57cec5SDimitry Andric /// Return true if \p L has a weaker nullability annotation than \p R. The 3490b57cec5SDimitry Andric /// ordering is: Unspecified < Nullable < NonNull. hasWeakerNullability(NullabilityKind L,NullabilityKind R)3500b57cec5SDimitry Andric inline bool hasWeakerNullability(NullabilityKind L, NullabilityKind R) { 3510b57cec5SDimitry Andric return uint8_t(L) > uint8_t(R); 3520b57cec5SDimitry Andric } 3530b57cec5SDimitry Andric 3540b57cec5SDimitry Andric /// Retrieve the spelling of the given nullability kind. 3550b57cec5SDimitry Andric llvm::StringRef getNullabilitySpelling(NullabilityKind kind, 3560b57cec5SDimitry Andric bool isContextSensitive = false); 3570b57cec5SDimitry Andric 3580b57cec5SDimitry Andric /// Kinds of parameter ABI. 3590b57cec5SDimitry Andric enum class ParameterABI { 3600b57cec5SDimitry Andric /// This parameter uses ordinary ABI rules for its type. 3610b57cec5SDimitry Andric Ordinary, 3620b57cec5SDimitry Andric 3630b57cec5SDimitry Andric /// This parameter (which must have pointer type) is a Swift 3640b57cec5SDimitry Andric /// indirect result parameter. 3650b57cec5SDimitry Andric SwiftIndirectResult, 3660b57cec5SDimitry Andric 3670b57cec5SDimitry Andric /// This parameter (which must have pointer-to-pointer type) uses 3680b57cec5SDimitry Andric /// the special Swift error-result ABI treatment. There can be at 3690b57cec5SDimitry Andric /// most one parameter on a given function that uses this treatment. 3700b57cec5SDimitry Andric SwiftErrorResult, 3710b57cec5SDimitry Andric 3720b57cec5SDimitry Andric /// This parameter (which must have pointer type) uses the special 3730b57cec5SDimitry Andric /// Swift context-pointer ABI treatment. There can be at 3740b57cec5SDimitry Andric /// most one parameter on a given function that uses this treatment. 375fe6060f1SDimitry Andric SwiftContext, 376fe6060f1SDimitry Andric 377fe6060f1SDimitry Andric /// This parameter (which must have pointer type) uses the special 378fe6060f1SDimitry Andric /// Swift asynchronous context-pointer ABI treatment. There can be at 379fe6060f1SDimitry Andric /// most one parameter on a given function that uses this treatment. 380fe6060f1SDimitry Andric SwiftAsyncContext, 3810b57cec5SDimitry Andric }; 3820b57cec5SDimitry Andric 383480093f4SDimitry Andric /// Assigned inheritance model for a class in the MS C++ ABI. Must match order 384480093f4SDimitry Andric /// of spellings in MSInheritanceAttr. 385480093f4SDimitry Andric enum class MSInheritanceModel { 386480093f4SDimitry Andric Single = 0, 387480093f4SDimitry Andric Multiple = 1, 388480093f4SDimitry Andric Virtual = 2, 389480093f4SDimitry Andric Unspecified = 3, 390480093f4SDimitry Andric }; 391480093f4SDimitry Andric 3920b57cec5SDimitry Andric llvm::StringRef getParameterABISpelling(ParameterABI kind); 3935ffd83dbSDimitry Andric getAccessSpelling(AccessSpecifier AS)3945ffd83dbSDimitry Andric inline llvm::StringRef getAccessSpelling(AccessSpecifier AS) { 3955ffd83dbSDimitry Andric switch (AS) { 3965ffd83dbSDimitry Andric case AccessSpecifier::AS_public: 3975ffd83dbSDimitry Andric return "public"; 3985ffd83dbSDimitry Andric case AccessSpecifier::AS_protected: 3995ffd83dbSDimitry Andric return "protected"; 4005ffd83dbSDimitry Andric case AccessSpecifier::AS_private: 4015ffd83dbSDimitry Andric return "private"; 4025ffd83dbSDimitry Andric case AccessSpecifier::AS_none: 4035ffd83dbSDimitry Andric return {}; 4045ffd83dbSDimitry Andric } 4055ffd83dbSDimitry Andric llvm_unreachable("Unknown AccessSpecifier"); 4065ffd83dbSDimitry Andric } 4070b57cec5SDimitry Andric } // end namespace clang 4080b57cec5SDimitry Andric 4090b57cec5SDimitry Andric #endif // LLVM_CLANG_BASIC_SPECIFIERS_H 410