1 //===--- TargetCXXABI.h - C++ ABI Target Configuration ----------*- C++ -*-===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 /// 10 /// \file 11 /// \brief Defines the TargetCXXABI class, which abstracts details of the 12 /// C++ ABI that we're targeting. 13 /// 14 //===----------------------------------------------------------------------===// 15 16 #ifndef LLVM_CLANG_BASIC_TARGETCXXABI_H 17 #define LLVM_CLANG_BASIC_TARGETCXXABI_H 18 19 #include "llvm/ADT/Triple.h" 20 #include "llvm/Support/ErrorHandling.h" 21 22 namespace clang { 23 24 /// \brief The basic abstraction for the target C++ ABI. 25 class TargetCXXABI { 26 public: 27 /// \brief The basic C++ ABI kind. 28 enum Kind { 29 /// The generic Itanium ABI is the standard ABI of most open-source 30 /// and Unix-like platforms. It is the primary ABI targeted by 31 /// many compilers, including Clang and GCC. 32 /// 33 /// It is documented here: 34 /// http://www.codesourcery.com/public/cxx-abi/ 35 GenericItanium, 36 37 /// The generic ARM ABI is a modified version of the Itanium ABI 38 /// proposed by ARM for use on ARM-based platforms. 39 /// 40 /// These changes include: 41 /// - the representation of member function pointers is adjusted 42 /// to not conflict with the 'thumb' bit of ARM function pointers; 43 /// - constructors and destructors return 'this'; 44 /// - guard variables are smaller; 45 /// - inline functions are never key functions; 46 /// - array cookies have a slightly different layout; 47 /// - additional convenience functions are specified; 48 /// - and more! 49 /// 50 /// It is documented here: 51 /// http://infocenter.arm.com 52 /// /help/topic/com.arm.doc.ihi0041c/IHI0041C_cppabi.pdf 53 GenericARM, 54 55 /// The iOS ABI is a partial implementation of the ARM ABI. 56 /// Several of the features of the ARM ABI were not fully implemented 57 /// in the compilers that iOS was launched with. 58 /// 59 /// Essentially, the iOS ABI includes the ARM changes to: 60 /// - member function pointers, 61 /// - guard variables, 62 /// - array cookies, and 63 /// - constructor/destructor signatures. 64 iOS, 65 66 /// The iOS 64-bit ABI is follows ARM's published 64-bit ABI more 67 /// closely, but we don't guarantee to follow it perfectly. 68 /// 69 /// It is documented here: 70 /// http://infocenter.arm.com 71 /// /help/topic/com.arm.doc.ihi0059a/IHI0059A_cppabi64.pdf 72 iOS64, 73 74 /// The generic AArch64 ABI is also a modified version of the Itanium ABI, 75 /// but it has fewer divergences than the 32-bit ARM ABI. 76 /// 77 /// The relevant changes from the generic ABI in this case are: 78 /// - representation of member function pointers adjusted as in ARM. 79 /// - guard variables are smaller. 80 GenericAArch64, 81 82 /// The generic Mips ABI is a modified version of the Itanium ABI. 83 /// 84 /// At the moment, only change from the generic ABI in this case is: 85 /// - representation of member function pointers adjusted as in ARM. 86 GenericMIPS, 87 88 /// The Microsoft ABI is the ABI used by Microsoft Visual Studio (and 89 /// compatible compilers). 90 /// 91 /// FIXME: should this be split into Win32 and Win64 variants? 92 /// 93 /// Only scattered and incomplete official documentation exists. 94 Microsoft 95 }; 96 97 private: 98 // Right now, this class is passed around as a cheap value type. 99 // If you add more members, especially non-POD members, please 100 // audit the users to pass it by reference instead. 101 Kind TheKind; 102 103 public: 104 /// A bogus initialization of the platform ABI. TargetCXXABI()105 TargetCXXABI() : TheKind(GenericItanium) {} 106 TargetCXXABI(Kind kind)107 TargetCXXABI(Kind kind) : TheKind(kind) {} 108 set(Kind kind)109 void set(Kind kind) { 110 TheKind = kind; 111 } 112 getKind()113 Kind getKind() const { return TheKind; } 114 115 /// \brief Does this ABI generally fall into the Itanium family of ABIs? isItaniumFamily()116 bool isItaniumFamily() const { 117 switch (getKind()) { 118 case GenericAArch64: 119 case GenericItanium: 120 case GenericARM: 121 case iOS: 122 case iOS64: 123 case GenericMIPS: 124 return true; 125 126 case Microsoft: 127 return false; 128 } 129 llvm_unreachable("bad ABI kind"); 130 } 131 132 /// \brief Is this ABI an MSVC-compatible ABI? isMicrosoft()133 bool isMicrosoft() const { 134 switch (getKind()) { 135 case GenericAArch64: 136 case GenericItanium: 137 case GenericARM: 138 case iOS: 139 case iOS64: 140 case GenericMIPS: 141 return false; 142 143 case Microsoft: 144 return true; 145 } 146 llvm_unreachable("bad ABI kind"); 147 } 148 149 /// \brief Is the default C++ member function calling convention 150 /// the same as the default calling convention? isMemberFunctionCCDefault()151 bool isMemberFunctionCCDefault() const { 152 // Right now, this is always false for Microsoft. 153 return !isMicrosoft(); 154 } 155 156 /// Are arguments to a call destroyed left to right in the callee? 157 /// This is a fundamental language change, since it implies that objects 158 /// passed by value do *not* live to the end of the full expression. 159 /// Temporaries passed to a function taking a const reference live to the end 160 /// of the full expression as usual. Both the caller and the callee must 161 /// have access to the destructor, while only the caller needs the 162 /// destructor if this is false. areArgsDestroyedLeftToRightInCallee()163 bool areArgsDestroyedLeftToRightInCallee() const { 164 return isMicrosoft(); 165 } 166 167 /// \brief Does this ABI have different entrypoints for complete-object 168 /// and base-subobject constructors? hasConstructorVariants()169 bool hasConstructorVariants() const { 170 return isItaniumFamily(); 171 } 172 173 /// \brief Does this ABI allow virtual bases to be primary base classes? hasPrimaryVBases()174 bool hasPrimaryVBases() const { 175 return isItaniumFamily(); 176 } 177 178 /// \brief Does this ABI use key functions? If so, class data such as the 179 /// vtable is emitted with strong linkage by the TU containing the key 180 /// function. hasKeyFunctions()181 bool hasKeyFunctions() const { 182 return isItaniumFamily(); 183 } 184 185 /// \brief Can an out-of-line inline function serve as a key function? 186 /// 187 /// This flag is only useful in ABIs where type data (for example, 188 /// v-tables and type_info objects) are emitted only after processing 189 /// the definition of a special "key" virtual function. (This is safe 190 /// because the ODR requires that every virtual function be defined 191 /// somewhere in a program.) This usually permits such data to be 192 /// emitted in only a single object file, as opposed to redundantly 193 /// in every object file that requires it. 194 /// 195 /// One simple and common definition of "key function" is the first 196 /// virtual function in the class definition which is not defined there. 197 /// This rule works very well when that function has a non-inline 198 /// definition in some non-header file. Unfortunately, when that 199 /// function is defined inline, this rule requires the type data 200 /// to be emitted weakly, as if there were no key function. 201 /// 202 /// The ARM ABI observes that the ODR provides an additional guarantee: 203 /// a virtual function is always ODR-used, so if it is defined inline, 204 /// that definition must appear in every translation unit that defines 205 /// the class. Therefore, there is no reason to allow such functions 206 /// to serve as key functions. 207 /// 208 /// Because this changes the rules for emitting type data, 209 /// it can cause type data to be emitted with both weak and strong 210 /// linkage, which is not allowed on all platforms. Therefore, 211 /// exploiting this observation requires an ABI break and cannot be 212 /// done on a generic Itanium platform. canKeyFunctionBeInline()213 bool canKeyFunctionBeInline() const { 214 switch (getKind()) { 215 case GenericARM: 216 case iOS64: 217 return false; 218 219 case GenericAArch64: 220 case GenericItanium: 221 case iOS: // old iOS compilers did not follow this rule 222 case Microsoft: 223 case GenericMIPS: 224 return true; 225 } 226 llvm_unreachable("bad ABI kind"); 227 } 228 229 /// When is record layout allowed to allocate objects in the tail 230 /// padding of a base class? 231 /// 232 /// This decision cannot be changed without breaking platform ABI 233 /// compatibility, and yet it is tied to language guarantees which 234 /// the committee has so far seen fit to strengthen no less than 235 /// three separate times: 236 /// - originally, there were no restrictions at all; 237 /// - C++98 declared that objects could not be allocated in the 238 /// tail padding of a POD type; 239 /// - C++03 extended the definition of POD to include classes 240 /// containing member pointers; and 241 /// - C++11 greatly broadened the definition of POD to include 242 /// all trivial standard-layout classes. 243 /// Each of these changes technically took several existing 244 /// platforms and made them permanently non-conformant. 245 enum TailPaddingUseRules { 246 /// The tail-padding of a base class is always theoretically 247 /// available, even if it's POD. This is not strictly conforming 248 /// in any language mode. 249 AlwaysUseTailPadding, 250 251 /// Only allocate objects in the tail padding of a base class if 252 /// the base class is not POD according to the rules of C++ TR1. 253 /// This is non-strictly conforming in C++11 mode. 254 UseTailPaddingUnlessPOD03, 255 256 /// Only allocate objects in the tail padding of a base class if 257 /// the base class is not POD according to the rules of C++11. 258 UseTailPaddingUnlessPOD11 259 }; getTailPaddingUseRules()260 TailPaddingUseRules getTailPaddingUseRules() const { 261 switch (getKind()) { 262 // To preserve binary compatibility, the generic Itanium ABI has 263 // permanently locked the definition of POD to the rules of C++ TR1, 264 // and that trickles down to all the derived ABIs. 265 case GenericItanium: 266 case GenericAArch64: 267 case GenericARM: 268 case iOS: 269 case GenericMIPS: 270 return UseTailPaddingUnlessPOD03; 271 272 // iOS on ARM64 uses the C++11 POD rules. It does not honor the 273 // Itanium exception about classes with over-large bitfields. 274 case iOS64: 275 return UseTailPaddingUnlessPOD11; 276 277 // MSVC always allocates fields in the tail-padding of a base class 278 // subobject, even if they're POD. 279 case Microsoft: 280 return AlwaysUseTailPadding; 281 } 282 llvm_unreachable("bad ABI kind"); 283 } 284 285 /// Try to parse an ABI name, returning false on error. 286 bool tryParse(llvm::StringRef name); 287 288 friend bool operator==(const TargetCXXABI &left, const TargetCXXABI &right) { 289 return left.getKind() == right.getKind(); 290 } 291 292 friend bool operator!=(const TargetCXXABI &left, const TargetCXXABI &right) { 293 return !(left == right); 294 } 295 }; 296 297 } // end namespace clang 298 299 #endif 300