CGObjCMac.cpp revision 8b2926c23645627d60d62667fc0e7a310e40815e
1//===------- CGObjCMac.cpp - Interface to Apple Objective-C Runtime -------===// 2// 3// The LLVM Compiler Infrastructure 4// 5// This file is distributed under the University of Illinois Open Source 6// License. See LICENSE.TXT for details. 7// 8//===----------------------------------------------------------------------===// 9// 10// This provides Objective-C code generation targetting the Apple runtime. 11// 12//===----------------------------------------------------------------------===// 13 14#include "CGObjCRuntime.h" 15 16#include "CodeGenModule.h" 17#include "CodeGenFunction.h" 18#include "clang/AST/ASTContext.h" 19#include "clang/AST/Decl.h" 20#include "clang/AST/DeclObjC.h" 21#include "clang/AST/RecordLayout.h" 22#include "clang/AST/StmtObjC.h" 23#include "clang/Basic/LangOptions.h" 24 25#include "llvm/Intrinsics.h" 26#include "llvm/Module.h" 27#include "llvm/ADT/DenseSet.h" 28#include "llvm/Target/TargetData.h" 29#include <sstream> 30 31using namespace clang; 32using namespace CodeGen; 33 34// Common CGObjCRuntime functions, these don't belong here, but they 35// don't belong in CGObjCRuntime either so we will live with it for 36// now. 37 38static const llvm::StructType * 39GetConcreteClassStruct(CodeGen::CodeGenModule &CGM, 40 const ObjCInterfaceDecl *OID) { 41 assert(!OID->isForwardDecl() && "Invalid interface decl!"); 42 const RecordDecl *RD = CGM.getContext().addRecordToClass(OID); 43 return cast<llvm::StructType>(CGM.getTypes().ConvertTagDeclType(RD)); 44} 45 46/// FindIvarInterface - Find the interface containing the ivar. 47/// 48/// FIXME: We shouldn't need to do this, the containing context should 49/// be fixed. 50static const ObjCInterfaceDecl *FindIvarInterface(ASTContext &Context, 51 const ObjCInterfaceDecl *OID, 52 const ObjCIvarDecl *OIVD, 53 unsigned &Index) { 54 const ObjCInterfaceDecl *Super = OID->getSuperClass(); 55 56 // FIXME: The index here is closely tied to how 57 // ASTContext::getObjCLayout is implemented. This should be fixed to 58 // get the information from the layout directly. 59 Index = 0; 60 for (ObjCInterfaceDecl::ivar_iterator IVI = OID->ivar_begin(), 61 IVE = OID->ivar_end(); IVI != IVE; ++IVI, ++Index) 62 if (OIVD == *IVI) 63 return OID; 64 65 // Also look in synthesized ivars. 66 for (ObjCInterfaceDecl::prop_iterator I = OID->prop_begin(Context), 67 E = OID->prop_end(Context); I != E; ++I) { 68 if (ObjCIvarDecl *Ivar = (*I)->getPropertyIvarDecl()) { 69 if (OIVD == Ivar) 70 return OID; 71 ++Index; 72 } 73 } 74 75 // Otherwise check in the super class. 76 if (Super) 77 return FindIvarInterface(Context, Super, OIVD, Index); 78 79 return 0; 80} 81 82static uint64_t LookupFieldBitOffset(CodeGen::CodeGenModule &CGM, 83 const ObjCInterfaceDecl *OID, 84 const ObjCImplementationDecl *ID, 85 const ObjCIvarDecl *Ivar) { 86 unsigned Index; 87 const ObjCInterfaceDecl *Container = 88 FindIvarInterface(CGM.getContext(), OID, Ivar, Index); 89 assert(Container && "Unable to find ivar container"); 90 91 // If we know have an implementation (and the ivar is in it) then 92 // look up in the implementation layout. 93 const ASTRecordLayout *RL; 94 if (ID && ID->getClassInterface() == Container) 95 RL = &CGM.getContext().getASTObjCImplementationLayout(ID); 96 else 97 RL = &CGM.getContext().getASTObjCInterfaceLayout(Container); 98 return RL->getFieldOffset(Index); 99} 100 101uint64_t CGObjCRuntime::ComputeIvarBaseOffset(CodeGen::CodeGenModule &CGM, 102 const ObjCInterfaceDecl *OID, 103 const ObjCIvarDecl *Ivar) { 104 return LookupFieldBitOffset(CGM, OID, 0, Ivar) / 8; 105} 106 107uint64_t CGObjCRuntime::ComputeIvarBaseOffset(CodeGen::CodeGenModule &CGM, 108 const ObjCImplementationDecl *OID, 109 const ObjCIvarDecl *Ivar) { 110 return LookupFieldBitOffset(CGM, OID->getClassInterface(), OID, Ivar) / 8; 111} 112 113LValue CGObjCRuntime::EmitValueForIvarAtOffset(CodeGen::CodeGenFunction &CGF, 114 const ObjCInterfaceDecl *OID, 115 llvm::Value *BaseValue, 116 const ObjCIvarDecl *Ivar, 117 unsigned CVRQualifiers, 118 llvm::Value *Offset) { 119 // Compute (type*) ( (char *) BaseValue + Offset) 120 llvm::Type *I8Ptr = llvm::PointerType::getUnqual(llvm::Type::Int8Ty); 121 QualType IvarTy = Ivar->getType(); 122 const llvm::Type *LTy = CGF.CGM.getTypes().ConvertTypeForMem(IvarTy); 123 llvm::Value *V = CGF.Builder.CreateBitCast(BaseValue, I8Ptr); 124 V = CGF.Builder.CreateGEP(V, Offset, "add.ptr"); 125 V = CGF.Builder.CreateBitCast(V, llvm::PointerType::getUnqual(LTy)); 126 127 if (Ivar->isBitField()) { 128 // We need to compute the bit offset for the bit-field, the offset 129 // is to the byte. Note, there is a subtle invariant here: we can 130 // only call this routine on non-sythesized ivars but we may be 131 // called for synthesized ivars. However, a synthesized ivar can 132 // never be a bit-field so this is safe. 133 uint64_t BitOffset = LookupFieldBitOffset(CGF.CGM, OID, 0, Ivar) % 8; 134 135 uint64_t BitFieldSize = 136 Ivar->getBitWidth()->EvaluateAsInt(CGF.getContext()).getZExtValue(); 137 return LValue::MakeBitfield(V, BitOffset, BitFieldSize, 138 IvarTy->isSignedIntegerType(), 139 IvarTy.getCVRQualifiers()|CVRQualifiers); 140 } 141 142 LValue LV = LValue::MakeAddr(V, IvarTy.getCVRQualifiers()|CVRQualifiers, 143 CGF.CGM.getContext().getObjCGCAttrKind(IvarTy)); 144 LValue::SetObjCIvar(LV, true); 145 return LV; 146} 147 148/// 149 150namespace { 151 152 typedef std::vector<llvm::Constant*> ConstantVector; 153 154 // FIXME: We should find a nicer way to make the labels for 155 // metadata, string concatenation is lame. 156 157class ObjCCommonTypesHelper { 158protected: 159 CodeGen::CodeGenModule &CGM; 160 161public: 162 const llvm::Type *ShortTy, *IntTy, *LongTy, *LongLongTy; 163 const llvm::Type *Int8PtrTy; 164 165 /// ObjectPtrTy - LLVM type for object handles (typeof(id)) 166 const llvm::Type *ObjectPtrTy; 167 168 /// PtrObjectPtrTy - LLVM type for id * 169 const llvm::Type *PtrObjectPtrTy; 170 171 /// SelectorPtrTy - LLVM type for selector handles (typeof(SEL)) 172 const llvm::Type *SelectorPtrTy; 173 /// ProtocolPtrTy - LLVM type for external protocol handles 174 /// (typeof(Protocol)) 175 const llvm::Type *ExternalProtocolPtrTy; 176 177 // SuperCTy - clang type for struct objc_super. 178 QualType SuperCTy; 179 // SuperPtrCTy - clang type for struct objc_super *. 180 QualType SuperPtrCTy; 181 182 /// SuperTy - LLVM type for struct objc_super. 183 const llvm::StructType *SuperTy; 184 /// SuperPtrTy - LLVM type for struct objc_super *. 185 const llvm::Type *SuperPtrTy; 186 187 /// PropertyTy - LLVM type for struct objc_property (struct _prop_t 188 /// in GCC parlance). 189 const llvm::StructType *PropertyTy; 190 191 /// PropertyListTy - LLVM type for struct objc_property_list 192 /// (_prop_list_t in GCC parlance). 193 const llvm::StructType *PropertyListTy; 194 /// PropertyListPtrTy - LLVM type for struct objc_property_list*. 195 const llvm::Type *PropertyListPtrTy; 196 197 // MethodTy - LLVM type for struct objc_method. 198 const llvm::StructType *MethodTy; 199 200 /// CacheTy - LLVM type for struct objc_cache. 201 const llvm::Type *CacheTy; 202 /// CachePtrTy - LLVM type for struct objc_cache *. 203 const llvm::Type *CachePtrTy; 204 205 llvm::Constant *getGetPropertyFn() { 206 CodeGen::CodeGenTypes &Types = CGM.getTypes(); 207 ASTContext &Ctx = CGM.getContext(); 208 // id objc_getProperty (id, SEL, ptrdiff_t, bool) 209 llvm::SmallVector<QualType,16> Params; 210 QualType IdType = Ctx.getObjCIdType(); 211 QualType SelType = Ctx.getObjCSelType(); 212 Params.push_back(IdType); 213 Params.push_back(SelType); 214 Params.push_back(Ctx.LongTy); 215 Params.push_back(Ctx.BoolTy); 216 const llvm::FunctionType *FTy = 217 Types.GetFunctionType(Types.getFunctionInfo(IdType, Params), false); 218 return CGM.CreateRuntimeFunction(FTy, "objc_getProperty"); 219 } 220 221 llvm::Constant *getSetPropertyFn() { 222 CodeGen::CodeGenTypes &Types = CGM.getTypes(); 223 ASTContext &Ctx = CGM.getContext(); 224 // void objc_setProperty (id, SEL, ptrdiff_t, id, bool, bool) 225 llvm::SmallVector<QualType,16> Params; 226 QualType IdType = Ctx.getObjCIdType(); 227 QualType SelType = Ctx.getObjCSelType(); 228 Params.push_back(IdType); 229 Params.push_back(SelType); 230 Params.push_back(Ctx.LongTy); 231 Params.push_back(IdType); 232 Params.push_back(Ctx.BoolTy); 233 Params.push_back(Ctx.BoolTy); 234 const llvm::FunctionType *FTy = 235 Types.GetFunctionType(Types.getFunctionInfo(Ctx.VoidTy, Params), false); 236 return CGM.CreateRuntimeFunction(FTy, "objc_setProperty"); 237 } 238 239 llvm::Constant *getEnumerationMutationFn() { 240 // void objc_enumerationMutation (id) 241 std::vector<const llvm::Type*> Args; 242 Args.push_back(ObjectPtrTy); 243 llvm::FunctionType *FTy = 244 llvm::FunctionType::get(llvm::Type::VoidTy, Args, false); 245 return CGM.CreateRuntimeFunction(FTy, "objc_enumerationMutation"); 246 } 247 248 /// GcReadWeakFn -- LLVM objc_read_weak (id *src) function. 249 llvm::Constant *getGcReadWeakFn() { 250 // id objc_read_weak (id *) 251 std::vector<const llvm::Type*> Args; 252 Args.push_back(ObjectPtrTy->getPointerTo()); 253 llvm::FunctionType *FTy = llvm::FunctionType::get(ObjectPtrTy, Args, false); 254 return CGM.CreateRuntimeFunction(FTy, "objc_read_weak"); 255 } 256 257 /// GcAssignWeakFn -- LLVM objc_assign_weak function. 258 llvm::Constant *getGcAssignWeakFn() { 259 // id objc_assign_weak (id, id *) 260 std::vector<const llvm::Type*> Args(1, ObjectPtrTy); 261 Args.push_back(ObjectPtrTy->getPointerTo()); 262 llvm::FunctionType *FTy = 263 llvm::FunctionType::get(ObjectPtrTy, Args, false); 264 return CGM.CreateRuntimeFunction(FTy, "objc_assign_weak"); 265 } 266 267 /// GcAssignGlobalFn -- LLVM objc_assign_global function. 268 llvm::Constant *getGcAssignGlobalFn() { 269 // id objc_assign_global(id, id *) 270 std::vector<const llvm::Type*> Args(1, ObjectPtrTy); 271 Args.push_back(ObjectPtrTy->getPointerTo()); 272 llvm::FunctionType *FTy = llvm::FunctionType::get(ObjectPtrTy, Args, false); 273 return CGM.CreateRuntimeFunction(FTy, "objc_assign_global"); 274 } 275 276 /// GcAssignIvarFn -- LLVM objc_assign_ivar function. 277 llvm::Constant *getGcAssignIvarFn() { 278 // id objc_assign_ivar(id, id *) 279 std::vector<const llvm::Type*> Args(1, ObjectPtrTy); 280 Args.push_back(ObjectPtrTy->getPointerTo()); 281 llvm::FunctionType *FTy = llvm::FunctionType::get(ObjectPtrTy, Args, false); 282 return CGM.CreateRuntimeFunction(FTy, "objc_assign_ivar"); 283 } 284 285 /// GcAssignStrongCastFn -- LLVM objc_assign_strongCast function. 286 llvm::Constant *getGcAssignStrongCastFn() { 287 // id objc_assign_global(id, id *) 288 std::vector<const llvm::Type*> Args(1, ObjectPtrTy); 289 Args.push_back(ObjectPtrTy->getPointerTo()); 290 llvm::FunctionType *FTy = llvm::FunctionType::get(ObjectPtrTy, Args, false); 291 return CGM.CreateRuntimeFunction(FTy, "objc_assign_strongCast"); 292 } 293 294 /// ExceptionThrowFn - LLVM objc_exception_throw function. 295 llvm::Constant *getExceptionThrowFn() { 296 // void objc_exception_throw(id) 297 std::vector<const llvm::Type*> Args(1, ObjectPtrTy); 298 llvm::FunctionType *FTy = 299 llvm::FunctionType::get(llvm::Type::VoidTy, Args, false); 300 return CGM.CreateRuntimeFunction(FTy, "objc_exception_throw"); 301 } 302 303 /// SyncEnterFn - LLVM object_sync_enter function. 304 llvm::Constant *getSyncEnterFn() { 305 // void objc_sync_enter (id) 306 std::vector<const llvm::Type*> Args(1, ObjectPtrTy); 307 llvm::FunctionType *FTy = 308 llvm::FunctionType::get(llvm::Type::VoidTy, Args, false); 309 return CGM.CreateRuntimeFunction(FTy, "objc_sync_enter"); 310 } 311 312 /// SyncExitFn - LLVM object_sync_exit function. 313 llvm::Constant *getSyncExitFn() { 314 // void objc_sync_exit (id) 315 std::vector<const llvm::Type*> Args(1, ObjectPtrTy); 316 llvm::FunctionType *FTy = 317 llvm::FunctionType::get(llvm::Type::VoidTy, Args, false); 318 return CGM.CreateRuntimeFunction(FTy, "objc_sync_exit"); 319 } 320 321 ObjCCommonTypesHelper(CodeGen::CodeGenModule &cgm); 322 ~ObjCCommonTypesHelper(){} 323}; 324 325/// ObjCTypesHelper - Helper class that encapsulates lazy 326/// construction of varies types used during ObjC generation. 327class ObjCTypesHelper : public ObjCCommonTypesHelper { 328private: 329 330 llvm::Constant *getMessageSendFn() { 331 // id objc_msgSend (id, SEL, ...) 332 std::vector<const llvm::Type*> Params; 333 Params.push_back(ObjectPtrTy); 334 Params.push_back(SelectorPtrTy); 335 return 336 CGM.CreateRuntimeFunction(llvm::FunctionType::get(ObjectPtrTy, 337 Params, true), 338 "objc_msgSend"); 339 } 340 341 llvm::Constant *getMessageSendStretFn() { 342 // id objc_msgSend_stret (id, SEL, ...) 343 std::vector<const llvm::Type*> Params; 344 Params.push_back(ObjectPtrTy); 345 Params.push_back(SelectorPtrTy); 346 return 347 CGM.CreateRuntimeFunction(llvm::FunctionType::get(llvm::Type::VoidTy, 348 Params, true), 349 "objc_msgSend_stret"); 350 351 } 352 353 llvm::Constant *getMessageSendFpretFn() { 354 // FIXME: This should be long double on x86_64? 355 // [double | long double] objc_msgSend_fpret(id self, SEL op, ...) 356 std::vector<const llvm::Type*> Params; 357 Params.push_back(ObjectPtrTy); 358 Params.push_back(SelectorPtrTy); 359 return 360 CGM.CreateRuntimeFunction(llvm::FunctionType::get(llvm::Type::DoubleTy, 361 Params, 362 true), 363 "objc_msgSend_fpret"); 364 365 } 366 367 llvm::Constant *getMessageSendSuperFn() { 368 // id objc_msgSendSuper(struct objc_super *super, SEL op, ...) 369 std::vector<const llvm::Type*> Params; 370 Params.push_back(SuperPtrTy); 371 Params.push_back(SelectorPtrTy); 372 return CGM.CreateRuntimeFunction(llvm::FunctionType::get(ObjectPtrTy, 373 Params, true), 374 "objc_msgSendSuper"); 375 } 376 llvm::Constant *getMessageSendSuperStretFn() { 377 // void objc_msgSendSuper_stret(void * stretAddr, struct objc_super *super, 378 // SEL op, ...) 379 std::vector<const llvm::Type*> Params; 380 Params.push_back(Int8PtrTy); 381 Params.push_back(SuperPtrTy); 382 Params.push_back(SelectorPtrTy); 383 return CGM.CreateRuntimeFunction(llvm::FunctionType::get(llvm::Type::VoidTy, 384 Params, true), 385 "objc_msgSendSuper_stret"); 386 } 387 388 llvm::Constant *getMessageSendSuperFpretFn() { 389 // There is no objc_msgSendSuper_fpret? How can that work? 390 return getMessageSendSuperFn(); 391 } 392 393public: 394 /// SymtabTy - LLVM type for struct objc_symtab. 395 const llvm::StructType *SymtabTy; 396 /// SymtabPtrTy - LLVM type for struct objc_symtab *. 397 const llvm::Type *SymtabPtrTy; 398 /// ModuleTy - LLVM type for struct objc_module. 399 const llvm::StructType *ModuleTy; 400 401 /// ProtocolTy - LLVM type for struct objc_protocol. 402 const llvm::StructType *ProtocolTy; 403 /// ProtocolPtrTy - LLVM type for struct objc_protocol *. 404 const llvm::Type *ProtocolPtrTy; 405 /// ProtocolExtensionTy - LLVM type for struct 406 /// objc_protocol_extension. 407 const llvm::StructType *ProtocolExtensionTy; 408 /// ProtocolExtensionTy - LLVM type for struct 409 /// objc_protocol_extension *. 410 const llvm::Type *ProtocolExtensionPtrTy; 411 /// MethodDescriptionTy - LLVM type for struct 412 /// objc_method_description. 413 const llvm::StructType *MethodDescriptionTy; 414 /// MethodDescriptionListTy - LLVM type for struct 415 /// objc_method_description_list. 416 const llvm::StructType *MethodDescriptionListTy; 417 /// MethodDescriptionListPtrTy - LLVM type for struct 418 /// objc_method_description_list *. 419 const llvm::Type *MethodDescriptionListPtrTy; 420 /// ProtocolListTy - LLVM type for struct objc_property_list. 421 const llvm::Type *ProtocolListTy; 422 /// ProtocolListPtrTy - LLVM type for struct objc_property_list*. 423 const llvm::Type *ProtocolListPtrTy; 424 /// CategoryTy - LLVM type for struct objc_category. 425 const llvm::StructType *CategoryTy; 426 /// ClassTy - LLVM type for struct objc_class. 427 const llvm::StructType *ClassTy; 428 /// ClassPtrTy - LLVM type for struct objc_class *. 429 const llvm::Type *ClassPtrTy; 430 /// ClassExtensionTy - LLVM type for struct objc_class_ext. 431 const llvm::StructType *ClassExtensionTy; 432 /// ClassExtensionPtrTy - LLVM type for struct objc_class_ext *. 433 const llvm::Type *ClassExtensionPtrTy; 434 // IvarTy - LLVM type for struct objc_ivar. 435 const llvm::StructType *IvarTy; 436 /// IvarListTy - LLVM type for struct objc_ivar_list. 437 const llvm::Type *IvarListTy; 438 /// IvarListPtrTy - LLVM type for struct objc_ivar_list *. 439 const llvm::Type *IvarListPtrTy; 440 /// MethodListTy - LLVM type for struct objc_method_list. 441 const llvm::Type *MethodListTy; 442 /// MethodListPtrTy - LLVM type for struct objc_method_list *. 443 const llvm::Type *MethodListPtrTy; 444 445 /// ExceptionDataTy - LLVM type for struct _objc_exception_data. 446 const llvm::Type *ExceptionDataTy; 447 448 /// ExceptionTryEnterFn - LLVM objc_exception_try_enter function. 449 llvm::Constant *getExceptionTryEnterFn() { 450 std::vector<const llvm::Type*> Params; 451 Params.push_back(llvm::PointerType::getUnqual(ExceptionDataTy)); 452 return CGM.CreateRuntimeFunction(llvm::FunctionType::get(llvm::Type::VoidTy, 453 Params, false), 454 "objc_exception_try_enter"); 455 } 456 457 /// ExceptionTryExitFn - LLVM objc_exception_try_exit function. 458 llvm::Constant *getExceptionTryExitFn() { 459 std::vector<const llvm::Type*> Params; 460 Params.push_back(llvm::PointerType::getUnqual(ExceptionDataTy)); 461 return CGM.CreateRuntimeFunction(llvm::FunctionType::get(llvm::Type::VoidTy, 462 Params, false), 463 "objc_exception_try_exit"); 464 } 465 466 /// ExceptionExtractFn - LLVM objc_exception_extract function. 467 llvm::Constant *getExceptionExtractFn() { 468 std::vector<const llvm::Type*> Params; 469 Params.push_back(llvm::PointerType::getUnqual(ExceptionDataTy)); 470 return CGM.CreateRuntimeFunction(llvm::FunctionType::get(ObjectPtrTy, 471 Params, false), 472 "objc_exception_extract"); 473 474 } 475 476 /// ExceptionMatchFn - LLVM objc_exception_match function. 477 llvm::Constant *getExceptionMatchFn() { 478 std::vector<const llvm::Type*> Params; 479 Params.push_back(ClassPtrTy); 480 Params.push_back(ObjectPtrTy); 481 return CGM.CreateRuntimeFunction(llvm::FunctionType::get(llvm::Type::Int32Ty, 482 Params, false), 483 "objc_exception_match"); 484 485 } 486 487 /// SetJmpFn - LLVM _setjmp function. 488 llvm::Constant *getSetJmpFn() { 489 std::vector<const llvm::Type*> Params; 490 Params.push_back(llvm::PointerType::getUnqual(llvm::Type::Int32Ty)); 491 return 492 CGM.CreateRuntimeFunction(llvm::FunctionType::get(llvm::Type::Int32Ty, 493 Params, false), 494 "_setjmp"); 495 496 } 497 498public: 499 ObjCTypesHelper(CodeGen::CodeGenModule &cgm); 500 ~ObjCTypesHelper() {} 501 502 503 llvm::Constant *getSendFn(bool IsSuper) { 504 return IsSuper ? getMessageSendSuperFn() : getMessageSendFn(); 505 } 506 507 llvm::Constant *getSendStretFn(bool IsSuper) { 508 return IsSuper ? getMessageSendSuperStretFn() : getMessageSendStretFn(); 509 } 510 511 llvm::Constant *getSendFpretFn(bool IsSuper) { 512 return IsSuper ? getMessageSendSuperFpretFn() : getMessageSendFpretFn(); 513 } 514}; 515 516/// ObjCNonFragileABITypesHelper - will have all types needed by objective-c's 517/// modern abi 518class ObjCNonFragileABITypesHelper : public ObjCCommonTypesHelper { 519public: 520 521 // MethodListnfABITy - LLVM for struct _method_list_t 522 const llvm::StructType *MethodListnfABITy; 523 524 // MethodListnfABIPtrTy - LLVM for struct _method_list_t* 525 const llvm::Type *MethodListnfABIPtrTy; 526 527 // ProtocolnfABITy = LLVM for struct _protocol_t 528 const llvm::StructType *ProtocolnfABITy; 529 530 // ProtocolnfABIPtrTy = LLVM for struct _protocol_t* 531 const llvm::Type *ProtocolnfABIPtrTy; 532 533 // ProtocolListnfABITy - LLVM for struct _objc_protocol_list 534 const llvm::StructType *ProtocolListnfABITy; 535 536 // ProtocolListnfABIPtrTy - LLVM for struct _objc_protocol_list* 537 const llvm::Type *ProtocolListnfABIPtrTy; 538 539 // ClassnfABITy - LLVM for struct _class_t 540 const llvm::StructType *ClassnfABITy; 541 542 // ClassnfABIPtrTy - LLVM for struct _class_t* 543 const llvm::Type *ClassnfABIPtrTy; 544 545 // IvarnfABITy - LLVM for struct _ivar_t 546 const llvm::StructType *IvarnfABITy; 547 548 // IvarListnfABITy - LLVM for struct _ivar_list_t 549 const llvm::StructType *IvarListnfABITy; 550 551 // IvarListnfABIPtrTy = LLVM for struct _ivar_list_t* 552 const llvm::Type *IvarListnfABIPtrTy; 553 554 // ClassRonfABITy - LLVM for struct _class_ro_t 555 const llvm::StructType *ClassRonfABITy; 556 557 // ImpnfABITy - LLVM for id (*)(id, SEL, ...) 558 const llvm::Type *ImpnfABITy; 559 560 // CategorynfABITy - LLVM for struct _category_t 561 const llvm::StructType *CategorynfABITy; 562 563 // New types for nonfragile abi messaging. 564 565 // MessageRefTy - LLVM for: 566 // struct _message_ref_t { 567 // IMP messenger; 568 // SEL name; 569 // }; 570 const llvm::StructType *MessageRefTy; 571 // MessageRefCTy - clang type for struct _message_ref_t 572 QualType MessageRefCTy; 573 574 // MessageRefPtrTy - LLVM for struct _message_ref_t* 575 const llvm::Type *MessageRefPtrTy; 576 // MessageRefCPtrTy - clang type for struct _message_ref_t* 577 QualType MessageRefCPtrTy; 578 579 // MessengerTy - Type of the messenger (shown as IMP above) 580 const llvm::FunctionType *MessengerTy; 581 582 // SuperMessageRefTy - LLVM for: 583 // struct _super_message_ref_t { 584 // SUPER_IMP messenger; 585 // SEL name; 586 // }; 587 const llvm::StructType *SuperMessageRefTy; 588 589 // SuperMessageRefPtrTy - LLVM for struct _super_message_ref_t* 590 const llvm::Type *SuperMessageRefPtrTy; 591 592 llvm::Constant *getMessageSendFixupFn() { 593 // id objc_msgSend_fixup(id, struct message_ref_t*, ...) 594 std::vector<const llvm::Type*> Params; 595 Params.push_back(ObjectPtrTy); 596 Params.push_back(MessageRefPtrTy); 597 return CGM.CreateRuntimeFunction(llvm::FunctionType::get(ObjectPtrTy, 598 Params, true), 599 "objc_msgSend_fixup"); 600 } 601 602 llvm::Constant *getMessageSendFpretFixupFn() { 603 // id objc_msgSend_fpret_fixup(id, struct message_ref_t*, ...) 604 std::vector<const llvm::Type*> Params; 605 Params.push_back(ObjectPtrTy); 606 Params.push_back(MessageRefPtrTy); 607 return CGM.CreateRuntimeFunction(llvm::FunctionType::get(ObjectPtrTy, 608 Params, true), 609 "objc_msgSend_fpret_fixup"); 610 } 611 612 llvm::Constant *getMessageSendStretFixupFn() { 613 // id objc_msgSend_stret_fixup(id, struct message_ref_t*, ...) 614 std::vector<const llvm::Type*> Params; 615 Params.push_back(ObjectPtrTy); 616 Params.push_back(MessageRefPtrTy); 617 return CGM.CreateRuntimeFunction(llvm::FunctionType::get(ObjectPtrTy, 618 Params, true), 619 "objc_msgSend_stret_fixup"); 620 } 621 622 llvm::Constant *getMessageSendIdFixupFn() { 623 // id objc_msgSendId_fixup(id, struct message_ref_t*, ...) 624 std::vector<const llvm::Type*> Params; 625 Params.push_back(ObjectPtrTy); 626 Params.push_back(MessageRefPtrTy); 627 return CGM.CreateRuntimeFunction(llvm::FunctionType::get(ObjectPtrTy, 628 Params, true), 629 "objc_msgSendId_fixup"); 630 } 631 632 llvm::Constant *getMessageSendIdStretFixupFn() { 633 // id objc_msgSendId_stret_fixup(id, struct message_ref_t*, ...) 634 std::vector<const llvm::Type*> Params; 635 Params.push_back(ObjectPtrTy); 636 Params.push_back(MessageRefPtrTy); 637 return CGM.CreateRuntimeFunction(llvm::FunctionType::get(ObjectPtrTy, 638 Params, true), 639 "objc_msgSendId_stret_fixup"); 640 } 641 llvm::Constant *getMessageSendSuper2FixupFn() { 642 // id objc_msgSendSuper2_fixup (struct objc_super *, 643 // struct _super_message_ref_t*, ...) 644 std::vector<const llvm::Type*> Params; 645 Params.push_back(SuperPtrTy); 646 Params.push_back(SuperMessageRefPtrTy); 647 return CGM.CreateRuntimeFunction(llvm::FunctionType::get(ObjectPtrTy, 648 Params, true), 649 "objc_msgSendSuper2_fixup"); 650 } 651 652 llvm::Constant *getMessageSendSuper2StretFixupFn() { 653 // id objc_msgSendSuper2_stret_fixup(struct objc_super *, 654 // struct _super_message_ref_t*, ...) 655 std::vector<const llvm::Type*> Params; 656 Params.push_back(SuperPtrTy); 657 Params.push_back(SuperMessageRefPtrTy); 658 return CGM.CreateRuntimeFunction(llvm::FunctionType::get(ObjectPtrTy, 659 Params, true), 660 "objc_msgSendSuper2_stret_fixup"); 661 } 662 663 664 665 /// EHPersonalityPtr - LLVM value for an i8* to the Objective-C 666 /// exception personality function. 667 llvm::Value *getEHPersonalityPtr() { 668 llvm::Constant *Personality = 669 CGM.CreateRuntimeFunction(llvm::FunctionType::get(llvm::Type::Int32Ty, 670 std::vector<const llvm::Type*>(), 671 true), 672 "__objc_personality_v0"); 673 return llvm::ConstantExpr::getBitCast(Personality, Int8PtrTy); 674 } 675 676 llvm::Constant *getUnwindResumeOrRethrowFn() { 677 std::vector<const llvm::Type*> Params; 678 Params.push_back(Int8PtrTy); 679 return CGM.CreateRuntimeFunction(llvm::FunctionType::get(llvm::Type::VoidTy, 680 Params, false), 681 "_Unwind_Resume_or_Rethrow"); 682 } 683 684 llvm::Constant *getObjCEndCatchFn() { 685 std::vector<const llvm::Type*> Params; 686 return CGM.CreateRuntimeFunction(llvm::FunctionType::get(llvm::Type::VoidTy, 687 Params, false), 688 "objc_end_catch"); 689 690 } 691 692 llvm::Constant *getObjCBeginCatchFn() { 693 std::vector<const llvm::Type*> Params; 694 Params.push_back(Int8PtrTy); 695 return CGM.CreateRuntimeFunction(llvm::FunctionType::get(Int8PtrTy, 696 Params, false), 697 "objc_begin_catch"); 698 } 699 700 const llvm::StructType *EHTypeTy; 701 const llvm::Type *EHTypePtrTy; 702 703 ObjCNonFragileABITypesHelper(CodeGen::CodeGenModule &cgm); 704 ~ObjCNonFragileABITypesHelper(){} 705}; 706 707class CGObjCCommonMac : public CodeGen::CGObjCRuntime { 708public: 709 // FIXME - accessibility 710 class GC_IVAR { 711 public: 712 unsigned ivar_bytepos; 713 unsigned ivar_size; 714 GC_IVAR(unsigned bytepos = 0, unsigned size = 0) 715 : ivar_bytepos(bytepos), ivar_size(size) {} 716 717 // Allow sorting based on byte pos. 718 bool operator<(const GC_IVAR &b) const { 719 return ivar_bytepos < b.ivar_bytepos; 720 } 721 }; 722 723 class SKIP_SCAN { 724 public: 725 unsigned skip; 726 unsigned scan; 727 SKIP_SCAN(unsigned _skip = 0, unsigned _scan = 0) 728 : skip(_skip), scan(_scan) {} 729 }; 730 731protected: 732 CodeGen::CodeGenModule &CGM; 733 // FIXME! May not be needing this after all. 734 unsigned ObjCABI; 735 736 // gc ivar layout bitmap calculation helper caches. 737 llvm::SmallVector<GC_IVAR, 16> SkipIvars; 738 llvm::SmallVector<GC_IVAR, 16> IvarsInfo; 739 740 /// LazySymbols - Symbols to generate a lazy reference for. See 741 /// DefinedSymbols and FinishModule(). 742 std::set<IdentifierInfo*> LazySymbols; 743 744 /// DefinedSymbols - External symbols which are defined by this 745 /// module. The symbols in this list and LazySymbols are used to add 746 /// special linker symbols which ensure that Objective-C modules are 747 /// linked properly. 748 std::set<IdentifierInfo*> DefinedSymbols; 749 750 /// ClassNames - uniqued class names. 751 llvm::DenseMap<IdentifierInfo*, llvm::GlobalVariable*> ClassNames; 752 753 /// MethodVarNames - uniqued method variable names. 754 llvm::DenseMap<Selector, llvm::GlobalVariable*> MethodVarNames; 755 756 /// MethodVarTypes - uniqued method type signatures. We have to use 757 /// a StringMap here because have no other unique reference. 758 llvm::StringMap<llvm::GlobalVariable*> MethodVarTypes; 759 760 /// MethodDefinitions - map of methods which have been defined in 761 /// this translation unit. 762 llvm::DenseMap<const ObjCMethodDecl*, llvm::Function*> MethodDefinitions; 763 764 /// PropertyNames - uniqued method variable names. 765 llvm::DenseMap<IdentifierInfo*, llvm::GlobalVariable*> PropertyNames; 766 767 /// ClassReferences - uniqued class references. 768 llvm::DenseMap<IdentifierInfo*, llvm::GlobalVariable*> ClassReferences; 769 770 /// SelectorReferences - uniqued selector references. 771 llvm::DenseMap<Selector, llvm::GlobalVariable*> SelectorReferences; 772 773 /// Protocols - Protocols for which an objc_protocol structure has 774 /// been emitted. Forward declarations are handled by creating an 775 /// empty structure whose initializer is filled in when/if defined. 776 llvm::DenseMap<IdentifierInfo*, llvm::GlobalVariable*> Protocols; 777 778 /// DefinedProtocols - Protocols which have actually been 779 /// defined. We should not need this, see FIXME in GenerateProtocol. 780 llvm::DenseSet<IdentifierInfo*> DefinedProtocols; 781 782 /// DefinedClasses - List of defined classes. 783 std::vector<llvm::GlobalValue*> DefinedClasses; 784 785 /// DefinedCategories - List of defined categories. 786 std::vector<llvm::GlobalValue*> DefinedCategories; 787 788 /// UsedGlobals - List of globals to pack into the llvm.used metadata 789 /// to prevent them from being clobbered. 790 std::vector<llvm::GlobalVariable*> UsedGlobals; 791 792 /// GetNameForMethod - Return a name for the given method. 793 /// \param[out] NameOut - The return value. 794 void GetNameForMethod(const ObjCMethodDecl *OMD, 795 const ObjCContainerDecl *CD, 796 std::string &NameOut); 797 798 /// GetMethodVarName - Return a unique constant for the given 799 /// selector's name. The return value has type char *. 800 llvm::Constant *GetMethodVarName(Selector Sel); 801 llvm::Constant *GetMethodVarName(IdentifierInfo *Ident); 802 llvm::Constant *GetMethodVarName(const std::string &Name); 803 804 /// GetMethodVarType - Return a unique constant for the given 805 /// selector's name. The return value has type char *. 806 807 // FIXME: This is a horrible name. 808 llvm::Constant *GetMethodVarType(const ObjCMethodDecl *D); 809 llvm::Constant *GetMethodVarType(const FieldDecl *D); 810 811 /// GetPropertyName - Return a unique constant for the given 812 /// name. The return value has type char *. 813 llvm::Constant *GetPropertyName(IdentifierInfo *Ident); 814 815 // FIXME: This can be dropped once string functions are unified. 816 llvm::Constant *GetPropertyTypeString(const ObjCPropertyDecl *PD, 817 const Decl *Container); 818 819 /// GetClassName - Return a unique constant for the given selector's 820 /// name. The return value has type char *. 821 llvm::Constant *GetClassName(IdentifierInfo *Ident); 822 823 /// BuildIvarLayout - Builds ivar layout bitmap for the class 824 /// implementation for the __strong or __weak case. 825 /// 826 llvm::Constant *BuildIvarLayout(const ObjCImplementationDecl *OI, 827 bool ForStrongLayout); 828 829 void BuildAggrIvarLayout(const ObjCInterfaceDecl *OI, 830 const llvm::StructLayout *Layout, 831 const RecordDecl *RD, 832 const llvm::SmallVectorImpl<FieldDecl*> &RecFields, 833 unsigned int BytePos, bool ForStrongLayout, 834 bool &HasUnion); 835 836 /// GetIvarLayoutName - Returns a unique constant for the given 837 /// ivar layout bitmap. 838 llvm::Constant *GetIvarLayoutName(IdentifierInfo *Ident, 839 const ObjCCommonTypesHelper &ObjCTypes); 840 841 /// EmitPropertyList - Emit the given property list. The return 842 /// value has type PropertyListPtrTy. 843 llvm::Constant *EmitPropertyList(const std::string &Name, 844 const Decl *Container, 845 const ObjCContainerDecl *OCD, 846 const ObjCCommonTypesHelper &ObjCTypes); 847 848 /// GetProtocolRef - Return a reference to the internal protocol 849 /// description, creating an empty one if it has not been 850 /// defined. The return value has type ProtocolPtrTy. 851 llvm::Constant *GetProtocolRef(const ObjCProtocolDecl *PD); 852 853 /// GetFieldBaseOffset - return's field byte offset. 854 uint64_t GetFieldBaseOffset(const ObjCInterfaceDecl *OI, 855 const llvm::StructLayout *Layout, 856 const FieldDecl *Field); 857 858 /// CreateMetadataVar - Create a global variable with internal 859 /// linkage for use by the Objective-C runtime. 860 /// 861 /// This is a convenience wrapper which not only creates the 862 /// variable, but also sets the section and alignment and adds the 863 /// global to the UsedGlobals list. 864 /// 865 /// \param Name - The variable name. 866 /// \param Init - The variable initializer; this is also used to 867 /// define the type of the variable. 868 /// \param Section - The section the variable should go into, or 0. 869 /// \param Align - The alignment for the variable, or 0. 870 /// \param AddToUsed - Whether the variable should be added to 871 /// "llvm.used". 872 llvm::GlobalVariable *CreateMetadataVar(const std::string &Name, 873 llvm::Constant *Init, 874 const char *Section, 875 unsigned Align, 876 bool AddToUsed); 877 878 /// GetNamedIvarList - Return the list of ivars in the interface 879 /// itself (not including super classes and not including unnamed 880 /// bitfields). 881 /// 882 /// For the non-fragile ABI, this also includes synthesized property 883 /// ivars. 884 void GetNamedIvarList(const ObjCInterfaceDecl *OID, 885 llvm::SmallVector<ObjCIvarDecl*, 16> &Res) const; 886 887public: 888 CGObjCCommonMac(CodeGen::CodeGenModule &cgm) : CGM(cgm) 889 { } 890 891 virtual llvm::Constant *GenerateConstantString(const ObjCStringLiteral *SL); 892 893 virtual llvm::Function *GenerateMethod(const ObjCMethodDecl *OMD, 894 const ObjCContainerDecl *CD=0); 895 896 virtual void GenerateProtocol(const ObjCProtocolDecl *PD); 897 898 /// GetOrEmitProtocol - Get the protocol object for the given 899 /// declaration, emitting it if necessary. The return value has type 900 /// ProtocolPtrTy. 901 virtual llvm::Constant *GetOrEmitProtocol(const ObjCProtocolDecl *PD)=0; 902 903 /// GetOrEmitProtocolRef - Get a forward reference to the protocol 904 /// object for the given declaration, emitting it if needed. These 905 /// forward references will be filled in with empty bodies if no 906 /// definition is seen. The return value has type ProtocolPtrTy. 907 virtual llvm::Constant *GetOrEmitProtocolRef(const ObjCProtocolDecl *PD)=0; 908}; 909 910class CGObjCMac : public CGObjCCommonMac { 911private: 912 ObjCTypesHelper ObjCTypes; 913 /// EmitImageInfo - Emit the image info marker used to encode some module 914 /// level information. 915 void EmitImageInfo(); 916 917 /// EmitModuleInfo - Another marker encoding module level 918 /// information. 919 void EmitModuleInfo(); 920 921 /// EmitModuleSymols - Emit module symbols, the list of defined 922 /// classes and categories. The result has type SymtabPtrTy. 923 llvm::Constant *EmitModuleSymbols(); 924 925 /// FinishModule - Write out global data structures at the end of 926 /// processing a translation unit. 927 void FinishModule(); 928 929 /// EmitClassExtension - Generate the class extension structure used 930 /// to store the weak ivar layout and properties. The return value 931 /// has type ClassExtensionPtrTy. 932 llvm::Constant *EmitClassExtension(const ObjCImplementationDecl *ID); 933 934 /// EmitClassRef - Return a Value*, of type ObjCTypes.ClassPtrTy, 935 /// for the given class. 936 llvm::Value *EmitClassRef(CGBuilderTy &Builder, 937 const ObjCInterfaceDecl *ID); 938 939 CodeGen::RValue EmitMessageSend(CodeGen::CodeGenFunction &CGF, 940 QualType ResultType, 941 Selector Sel, 942 llvm::Value *Arg0, 943 QualType Arg0Ty, 944 bool IsSuper, 945 const CallArgList &CallArgs); 946 947 /// EmitIvarList - Emit the ivar list for the given 948 /// implementation. If ForClass is true the list of class ivars 949 /// (i.e. metaclass ivars) is emitted, otherwise the list of 950 /// interface ivars will be emitted. The return value has type 951 /// IvarListPtrTy. 952 llvm::Constant *EmitIvarList(const ObjCImplementationDecl *ID, 953 bool ForClass); 954 955 /// EmitMetaClass - Emit a forward reference to the class structure 956 /// for the metaclass of the given interface. The return value has 957 /// type ClassPtrTy. 958 llvm::Constant *EmitMetaClassRef(const ObjCInterfaceDecl *ID); 959 960 /// EmitMetaClass - Emit a class structure for the metaclass of the 961 /// given implementation. The return value has type ClassPtrTy. 962 llvm::Constant *EmitMetaClass(const ObjCImplementationDecl *ID, 963 llvm::Constant *Protocols, 964 const ConstantVector &Methods); 965 966 llvm::Constant *GetMethodConstant(const ObjCMethodDecl *MD); 967 968 llvm::Constant *GetMethodDescriptionConstant(const ObjCMethodDecl *MD); 969 970 /// EmitMethodList - Emit the method list for the given 971 /// implementation. The return value has type MethodListPtrTy. 972 llvm::Constant *EmitMethodList(const std::string &Name, 973 const char *Section, 974 const ConstantVector &Methods); 975 976 /// EmitMethodDescList - Emit a method description list for a list of 977 /// method declarations. 978 /// - TypeName: The name for the type containing the methods. 979 /// - IsProtocol: True iff these methods are for a protocol. 980 /// - ClassMethds: True iff these are class methods. 981 /// - Required: When true, only "required" methods are 982 /// listed. Similarly, when false only "optional" methods are 983 /// listed. For classes this should always be true. 984 /// - begin, end: The method list to output. 985 /// 986 /// The return value has type MethodDescriptionListPtrTy. 987 llvm::Constant *EmitMethodDescList(const std::string &Name, 988 const char *Section, 989 const ConstantVector &Methods); 990 991 /// GetOrEmitProtocol - Get the protocol object for the given 992 /// declaration, emitting it if necessary. The return value has type 993 /// ProtocolPtrTy. 994 virtual llvm::Constant *GetOrEmitProtocol(const ObjCProtocolDecl *PD); 995 996 /// GetOrEmitProtocolRef - Get a forward reference to the protocol 997 /// object for the given declaration, emitting it if needed. These 998 /// forward references will be filled in with empty bodies if no 999 /// definition is seen. The return value has type ProtocolPtrTy. 1000 virtual llvm::Constant *GetOrEmitProtocolRef(const ObjCProtocolDecl *PD); 1001 1002 /// EmitProtocolExtension - Generate the protocol extension 1003 /// structure used to store optional instance and class methods, and 1004 /// protocol properties. The return value has type 1005 /// ProtocolExtensionPtrTy. 1006 llvm::Constant * 1007 EmitProtocolExtension(const ObjCProtocolDecl *PD, 1008 const ConstantVector &OptInstanceMethods, 1009 const ConstantVector &OptClassMethods); 1010 1011 /// EmitProtocolList - Generate the list of referenced 1012 /// protocols. The return value has type ProtocolListPtrTy. 1013 llvm::Constant *EmitProtocolList(const std::string &Name, 1014 ObjCProtocolDecl::protocol_iterator begin, 1015 ObjCProtocolDecl::protocol_iterator end); 1016 1017 /// EmitSelector - Return a Value*, of type ObjCTypes.SelectorPtrTy, 1018 /// for the given selector. 1019 llvm::Value *EmitSelector(CGBuilderTy &Builder, Selector Sel); 1020 1021 public: 1022 CGObjCMac(CodeGen::CodeGenModule &cgm); 1023 1024 virtual llvm::Function *ModuleInitFunction(); 1025 1026 virtual CodeGen::RValue GenerateMessageSend(CodeGen::CodeGenFunction &CGF, 1027 QualType ResultType, 1028 Selector Sel, 1029 llvm::Value *Receiver, 1030 bool IsClassMessage, 1031 const CallArgList &CallArgs); 1032 1033 virtual CodeGen::RValue 1034 GenerateMessageSendSuper(CodeGen::CodeGenFunction &CGF, 1035 QualType ResultType, 1036 Selector Sel, 1037 const ObjCInterfaceDecl *Class, 1038 bool isCategoryImpl, 1039 llvm::Value *Receiver, 1040 bool IsClassMessage, 1041 const CallArgList &CallArgs); 1042 1043 virtual llvm::Value *GetClass(CGBuilderTy &Builder, 1044 const ObjCInterfaceDecl *ID); 1045 1046 virtual llvm::Value *GetSelector(CGBuilderTy &Builder, Selector Sel); 1047 1048 virtual void GenerateCategory(const ObjCCategoryImplDecl *CMD); 1049 1050 virtual void GenerateClass(const ObjCImplementationDecl *ClassDecl); 1051 1052 virtual llvm::Value *GenerateProtocolRef(CGBuilderTy &Builder, 1053 const ObjCProtocolDecl *PD); 1054 1055 virtual llvm::Constant *GetPropertyGetFunction(); 1056 virtual llvm::Constant *GetPropertySetFunction(); 1057 virtual llvm::Constant *EnumerationMutationFunction(); 1058 1059 virtual void EmitTryOrSynchronizedStmt(CodeGen::CodeGenFunction &CGF, 1060 const Stmt &S); 1061 virtual void EmitThrowStmt(CodeGen::CodeGenFunction &CGF, 1062 const ObjCAtThrowStmt &S); 1063 virtual llvm::Value * EmitObjCWeakRead(CodeGen::CodeGenFunction &CGF, 1064 llvm::Value *AddrWeakObj); 1065 virtual void EmitObjCWeakAssign(CodeGen::CodeGenFunction &CGF, 1066 llvm::Value *src, llvm::Value *dst); 1067 virtual void EmitObjCGlobalAssign(CodeGen::CodeGenFunction &CGF, 1068 llvm::Value *src, llvm::Value *dest); 1069 virtual void EmitObjCIvarAssign(CodeGen::CodeGenFunction &CGF, 1070 llvm::Value *src, llvm::Value *dest); 1071 virtual void EmitObjCStrongCastAssign(CodeGen::CodeGenFunction &CGF, 1072 llvm::Value *src, llvm::Value *dest); 1073 1074 virtual LValue EmitObjCValueForIvar(CodeGen::CodeGenFunction &CGF, 1075 QualType ObjectTy, 1076 llvm::Value *BaseValue, 1077 const ObjCIvarDecl *Ivar, 1078 unsigned CVRQualifiers); 1079 virtual llvm::Value *EmitIvarOffset(CodeGen::CodeGenFunction &CGF, 1080 const ObjCInterfaceDecl *Interface, 1081 const ObjCIvarDecl *Ivar); 1082}; 1083 1084class CGObjCNonFragileABIMac : public CGObjCCommonMac { 1085private: 1086 ObjCNonFragileABITypesHelper ObjCTypes; 1087 llvm::GlobalVariable* ObjCEmptyCacheVar; 1088 llvm::GlobalVariable* ObjCEmptyVtableVar; 1089 1090 /// SuperClassReferences - uniqued super class references. 1091 llvm::DenseMap<IdentifierInfo*, llvm::GlobalVariable*> SuperClassReferences; 1092 1093 /// MetaClassReferences - uniqued meta class references. 1094 llvm::DenseMap<IdentifierInfo*, llvm::GlobalVariable*> MetaClassReferences; 1095 1096 /// EHTypeReferences - uniqued class ehtype references. 1097 llvm::DenseMap<IdentifierInfo*, llvm::GlobalVariable*> EHTypeReferences; 1098 1099 /// FinishNonFragileABIModule - Write out global data structures at the end of 1100 /// processing a translation unit. 1101 void FinishNonFragileABIModule(); 1102 1103 llvm::GlobalVariable * BuildClassRoTInitializer(unsigned flags, 1104 unsigned InstanceStart, 1105 unsigned InstanceSize, 1106 const ObjCImplementationDecl *ID); 1107 llvm::GlobalVariable * BuildClassMetaData(std::string &ClassName, 1108 llvm::Constant *IsAGV, 1109 llvm::Constant *SuperClassGV, 1110 llvm::Constant *ClassRoGV, 1111 bool HiddenVisibility); 1112 1113 llvm::Constant *GetMethodConstant(const ObjCMethodDecl *MD); 1114 1115 llvm::Constant *GetMethodDescriptionConstant(const ObjCMethodDecl *MD); 1116 1117 /// EmitMethodList - Emit the method list for the given 1118 /// implementation. The return value has type MethodListnfABITy. 1119 llvm::Constant *EmitMethodList(const std::string &Name, 1120 const char *Section, 1121 const ConstantVector &Methods); 1122 /// EmitIvarList - Emit the ivar list for the given 1123 /// implementation. If ForClass is true the list of class ivars 1124 /// (i.e. metaclass ivars) is emitted, otherwise the list of 1125 /// interface ivars will be emitted. The return value has type 1126 /// IvarListnfABIPtrTy. 1127 llvm::Constant *EmitIvarList(const ObjCImplementationDecl *ID); 1128 1129 llvm::Constant *EmitIvarOffsetVar(const ObjCInterfaceDecl *ID, 1130 const ObjCIvarDecl *Ivar, 1131 unsigned long int offset); 1132 1133 /// GetOrEmitProtocol - Get the protocol object for the given 1134 /// declaration, emitting it if necessary. The return value has type 1135 /// ProtocolPtrTy. 1136 virtual llvm::Constant *GetOrEmitProtocol(const ObjCProtocolDecl *PD); 1137 1138 /// GetOrEmitProtocolRef - Get a forward reference to the protocol 1139 /// object for the given declaration, emitting it if needed. These 1140 /// forward references will be filled in with empty bodies if no 1141 /// definition is seen. The return value has type ProtocolPtrTy. 1142 virtual llvm::Constant *GetOrEmitProtocolRef(const ObjCProtocolDecl *PD); 1143 1144 /// EmitProtocolList - Generate the list of referenced 1145 /// protocols. The return value has type ProtocolListPtrTy. 1146 llvm::Constant *EmitProtocolList(const std::string &Name, 1147 ObjCProtocolDecl::protocol_iterator begin, 1148 ObjCProtocolDecl::protocol_iterator end); 1149 1150 CodeGen::RValue EmitMessageSend(CodeGen::CodeGenFunction &CGF, 1151 QualType ResultType, 1152 Selector Sel, 1153 llvm::Value *Receiver, 1154 QualType Arg0Ty, 1155 bool IsSuper, 1156 const CallArgList &CallArgs); 1157 1158 /// GetClassGlobal - Return the global variable for the Objective-C 1159 /// class of the given name. 1160 llvm::GlobalVariable *GetClassGlobal(const std::string &Name); 1161 1162 /// EmitClassRef - Return a Value*, of type ObjCTypes.ClassPtrTy, 1163 /// for the given class reference. 1164 llvm::Value *EmitClassRef(CGBuilderTy &Builder, 1165 const ObjCInterfaceDecl *ID); 1166 1167 /// EmitSuperClassRef - Return a Value*, of type ObjCTypes.ClassPtrTy, 1168 /// for the given super class reference. 1169 llvm::Value *EmitSuperClassRef(CGBuilderTy &Builder, 1170 const ObjCInterfaceDecl *ID); 1171 1172 /// EmitMetaClassRef - Return a Value * of the address of _class_t 1173 /// meta-data 1174 llvm::Value *EmitMetaClassRef(CGBuilderTy &Builder, 1175 const ObjCInterfaceDecl *ID); 1176 1177 /// ObjCIvarOffsetVariable - Returns the ivar offset variable for 1178 /// the given ivar. 1179 /// 1180 llvm::GlobalVariable * ObjCIvarOffsetVariable( 1181 const ObjCInterfaceDecl *ID, 1182 const ObjCIvarDecl *Ivar); 1183 1184 /// EmitSelector - Return a Value*, of type ObjCTypes.SelectorPtrTy, 1185 /// for the given selector. 1186 llvm::Value *EmitSelector(CGBuilderTy &Builder, Selector Sel); 1187 1188 /// GetInterfaceEHType - Get the cached ehtype for the given Objective-C 1189 /// interface. The return value has type EHTypePtrTy. 1190 llvm::Value *GetInterfaceEHType(const ObjCInterfaceDecl *ID, 1191 bool ForDefinition); 1192 1193 const char *getMetaclassSymbolPrefix() const { 1194 return "OBJC_METACLASS_$_"; 1195 } 1196 1197 const char *getClassSymbolPrefix() const { 1198 return "OBJC_CLASS_$_"; 1199 } 1200 1201 void GetClassSizeInfo(const ObjCImplementationDecl *OID, 1202 uint32_t &InstanceStart, 1203 uint32_t &InstanceSize); 1204 1205public: 1206 CGObjCNonFragileABIMac(CodeGen::CodeGenModule &cgm); 1207 // FIXME. All stubs for now! 1208 virtual llvm::Function *ModuleInitFunction(); 1209 1210 virtual CodeGen::RValue GenerateMessageSend(CodeGen::CodeGenFunction &CGF, 1211 QualType ResultType, 1212 Selector Sel, 1213 llvm::Value *Receiver, 1214 bool IsClassMessage, 1215 const CallArgList &CallArgs); 1216 1217 virtual CodeGen::RValue 1218 GenerateMessageSendSuper(CodeGen::CodeGenFunction &CGF, 1219 QualType ResultType, 1220 Selector Sel, 1221 const ObjCInterfaceDecl *Class, 1222 bool isCategoryImpl, 1223 llvm::Value *Receiver, 1224 bool IsClassMessage, 1225 const CallArgList &CallArgs); 1226 1227 virtual llvm::Value *GetClass(CGBuilderTy &Builder, 1228 const ObjCInterfaceDecl *ID); 1229 1230 virtual llvm::Value *GetSelector(CGBuilderTy &Builder, Selector Sel) 1231 { return EmitSelector(Builder, Sel); } 1232 1233 virtual void GenerateCategory(const ObjCCategoryImplDecl *CMD); 1234 1235 virtual void GenerateClass(const ObjCImplementationDecl *ClassDecl); 1236 virtual llvm::Value *GenerateProtocolRef(CGBuilderTy &Builder, 1237 const ObjCProtocolDecl *PD); 1238 1239 virtual llvm::Constant *GetPropertyGetFunction() { 1240 return ObjCTypes.getGetPropertyFn(); 1241 } 1242 virtual llvm::Constant *GetPropertySetFunction() { 1243 return ObjCTypes.getSetPropertyFn(); 1244 } 1245 virtual llvm::Constant *EnumerationMutationFunction() { 1246 return ObjCTypes.getEnumerationMutationFn(); 1247 } 1248 1249 virtual void EmitTryOrSynchronizedStmt(CodeGen::CodeGenFunction &CGF, 1250 const Stmt &S); 1251 virtual void EmitThrowStmt(CodeGen::CodeGenFunction &CGF, 1252 const ObjCAtThrowStmt &S); 1253 virtual llvm::Value * EmitObjCWeakRead(CodeGen::CodeGenFunction &CGF, 1254 llvm::Value *AddrWeakObj); 1255 virtual void EmitObjCWeakAssign(CodeGen::CodeGenFunction &CGF, 1256 llvm::Value *src, llvm::Value *dst); 1257 virtual void EmitObjCGlobalAssign(CodeGen::CodeGenFunction &CGF, 1258 llvm::Value *src, llvm::Value *dest); 1259 virtual void EmitObjCIvarAssign(CodeGen::CodeGenFunction &CGF, 1260 llvm::Value *src, llvm::Value *dest); 1261 virtual void EmitObjCStrongCastAssign(CodeGen::CodeGenFunction &CGF, 1262 llvm::Value *src, llvm::Value *dest); 1263 virtual LValue EmitObjCValueForIvar(CodeGen::CodeGenFunction &CGF, 1264 QualType ObjectTy, 1265 llvm::Value *BaseValue, 1266 const ObjCIvarDecl *Ivar, 1267 unsigned CVRQualifiers); 1268 virtual llvm::Value *EmitIvarOffset(CodeGen::CodeGenFunction &CGF, 1269 const ObjCInterfaceDecl *Interface, 1270 const ObjCIvarDecl *Ivar); 1271}; 1272 1273} // end anonymous namespace 1274 1275/* *** Helper Functions *** */ 1276 1277/// getConstantGEP() - Help routine to construct simple GEPs. 1278static llvm::Constant *getConstantGEP(llvm::Constant *C, 1279 unsigned idx0, 1280 unsigned idx1) { 1281 llvm::Value *Idxs[] = { 1282 llvm::ConstantInt::get(llvm::Type::Int32Ty, idx0), 1283 llvm::ConstantInt::get(llvm::Type::Int32Ty, idx1) 1284 }; 1285 return llvm::ConstantExpr::getGetElementPtr(C, Idxs, 2); 1286} 1287 1288/// hasObjCExceptionAttribute - Return true if this class or any super 1289/// class has the __objc_exception__ attribute. 1290static bool hasObjCExceptionAttribute(const ObjCInterfaceDecl *OID) { 1291 if (OID->hasAttr<ObjCExceptionAttr>()) 1292 return true; 1293 if (const ObjCInterfaceDecl *Super = OID->getSuperClass()) 1294 return hasObjCExceptionAttribute(Super); 1295 return false; 1296} 1297 1298/* *** CGObjCMac Public Interface *** */ 1299 1300CGObjCMac::CGObjCMac(CodeGen::CodeGenModule &cgm) : CGObjCCommonMac(cgm), 1301 ObjCTypes(cgm) 1302{ 1303 ObjCABI = 1; 1304 EmitImageInfo(); 1305} 1306 1307/// GetClass - Return a reference to the class for the given interface 1308/// decl. 1309llvm::Value *CGObjCMac::GetClass(CGBuilderTy &Builder, 1310 const ObjCInterfaceDecl *ID) { 1311 return EmitClassRef(Builder, ID); 1312} 1313 1314/// GetSelector - Return the pointer to the unique'd string for this selector. 1315llvm::Value *CGObjCMac::GetSelector(CGBuilderTy &Builder, Selector Sel) { 1316 return EmitSelector(Builder, Sel); 1317} 1318 1319/// Generate a constant CFString object. 1320/* 1321 struct __builtin_CFString { 1322 const int *isa; // point to __CFConstantStringClassReference 1323 int flags; 1324 const char *str; 1325 long length; 1326 }; 1327*/ 1328 1329llvm::Constant *CGObjCCommonMac::GenerateConstantString( 1330 const ObjCStringLiteral *SL) { 1331 return CGM.GetAddrOfConstantCFString(SL->getString()); 1332} 1333 1334/// Generates a message send where the super is the receiver. This is 1335/// a message send to self with special delivery semantics indicating 1336/// which class's method should be called. 1337CodeGen::RValue 1338CGObjCMac::GenerateMessageSendSuper(CodeGen::CodeGenFunction &CGF, 1339 QualType ResultType, 1340 Selector Sel, 1341 const ObjCInterfaceDecl *Class, 1342 bool isCategoryImpl, 1343 llvm::Value *Receiver, 1344 bool IsClassMessage, 1345 const CodeGen::CallArgList &CallArgs) { 1346 // Create and init a super structure; this is a (receiver, class) 1347 // pair we will pass to objc_msgSendSuper. 1348 llvm::Value *ObjCSuper = 1349 CGF.Builder.CreateAlloca(ObjCTypes.SuperTy, 0, "objc_super"); 1350 llvm::Value *ReceiverAsObject = 1351 CGF.Builder.CreateBitCast(Receiver, ObjCTypes.ObjectPtrTy); 1352 CGF.Builder.CreateStore(ReceiverAsObject, 1353 CGF.Builder.CreateStructGEP(ObjCSuper, 0)); 1354 1355 // If this is a class message the metaclass is passed as the target. 1356 llvm::Value *Target; 1357 if (IsClassMessage) { 1358 if (isCategoryImpl) { 1359 // Message sent to 'super' in a class method defined in a category 1360 // implementation requires an odd treatment. 1361 // If we are in a class method, we must retrieve the 1362 // _metaclass_ for the current class, pointed at by 1363 // the class's "isa" pointer. The following assumes that 1364 // isa" is the first ivar in a class (which it must be). 1365 Target = EmitClassRef(CGF.Builder, Class->getSuperClass()); 1366 Target = CGF.Builder.CreateStructGEP(Target, 0); 1367 Target = CGF.Builder.CreateLoad(Target); 1368 } 1369 else { 1370 llvm::Value *MetaClassPtr = EmitMetaClassRef(Class); 1371 llvm::Value *SuperPtr = CGF.Builder.CreateStructGEP(MetaClassPtr, 1); 1372 llvm::Value *Super = CGF.Builder.CreateLoad(SuperPtr); 1373 Target = Super; 1374 } 1375 } else { 1376 Target = EmitClassRef(CGF.Builder, Class->getSuperClass()); 1377 } 1378 // FIXME: We shouldn't need to do this cast, rectify the ASTContext 1379 // and ObjCTypes types. 1380 const llvm::Type *ClassTy = 1381 CGM.getTypes().ConvertType(CGF.getContext().getObjCClassType()); 1382 Target = CGF.Builder.CreateBitCast(Target, ClassTy); 1383 CGF.Builder.CreateStore(Target, 1384 CGF.Builder.CreateStructGEP(ObjCSuper, 1)); 1385 1386 return EmitMessageSend(CGF, ResultType, Sel, 1387 ObjCSuper, ObjCTypes.SuperPtrCTy, 1388 true, CallArgs); 1389} 1390 1391/// Generate code for a message send expression. 1392CodeGen::RValue CGObjCMac::GenerateMessageSend(CodeGen::CodeGenFunction &CGF, 1393 QualType ResultType, 1394 Selector Sel, 1395 llvm::Value *Receiver, 1396 bool IsClassMessage, 1397 const CallArgList &CallArgs) { 1398 return EmitMessageSend(CGF, ResultType, Sel, 1399 Receiver, CGF.getContext().getObjCIdType(), 1400 false, CallArgs); 1401} 1402 1403CodeGen::RValue CGObjCMac::EmitMessageSend(CodeGen::CodeGenFunction &CGF, 1404 QualType ResultType, 1405 Selector Sel, 1406 llvm::Value *Arg0, 1407 QualType Arg0Ty, 1408 bool IsSuper, 1409 const CallArgList &CallArgs) { 1410 CallArgList ActualArgs; 1411 if (!IsSuper) 1412 Arg0 = CGF.Builder.CreateBitCast(Arg0, ObjCTypes.ObjectPtrTy, "tmp"); 1413 ActualArgs.push_back(std::make_pair(RValue::get(Arg0), Arg0Ty)); 1414 ActualArgs.push_back(std::make_pair(RValue::get(EmitSelector(CGF.Builder, 1415 Sel)), 1416 CGF.getContext().getObjCSelType())); 1417 ActualArgs.insert(ActualArgs.end(), CallArgs.begin(), CallArgs.end()); 1418 1419 CodeGenTypes &Types = CGM.getTypes(); 1420 const CGFunctionInfo &FnInfo = Types.getFunctionInfo(ResultType, ActualArgs); 1421 // FIXME. vararg flag must be true when this API is used for 64bit code gen. 1422 const llvm::FunctionType *FTy = Types.GetFunctionType(FnInfo, false); 1423 1424 llvm::Constant *Fn; 1425 if (CGM.ReturnTypeUsesSret(FnInfo)) { 1426 Fn = ObjCTypes.getSendStretFn(IsSuper); 1427 } else if (ResultType->isFloatingType()) { 1428 // FIXME: Sadly, this is wrong. This actually depends on the 1429 // architecture. This happens to be right for x86-32 though. 1430 Fn = ObjCTypes.getSendFpretFn(IsSuper); 1431 } else { 1432 Fn = ObjCTypes.getSendFn(IsSuper); 1433 } 1434 Fn = llvm::ConstantExpr::getBitCast(Fn, llvm::PointerType::getUnqual(FTy)); 1435 return CGF.EmitCall(FnInfo, Fn, ActualArgs); 1436} 1437 1438llvm::Value *CGObjCMac::GenerateProtocolRef(CGBuilderTy &Builder, 1439 const ObjCProtocolDecl *PD) { 1440 // FIXME: I don't understand why gcc generates this, or where it is 1441 // resolved. Investigate. Its also wasteful to look this up over and 1442 // over. 1443 LazySymbols.insert(&CGM.getContext().Idents.get("Protocol")); 1444 1445 return llvm::ConstantExpr::getBitCast(GetProtocolRef(PD), 1446 ObjCTypes.ExternalProtocolPtrTy); 1447} 1448 1449void CGObjCCommonMac::GenerateProtocol(const ObjCProtocolDecl *PD) { 1450 // FIXME: We shouldn't need this, the protocol decl should contain 1451 // enough information to tell us whether this was a declaration or a 1452 // definition. 1453 DefinedProtocols.insert(PD->getIdentifier()); 1454 1455 // If we have generated a forward reference to this protocol, emit 1456 // it now. Otherwise do nothing, the protocol objects are lazily 1457 // emitted. 1458 if (Protocols.count(PD->getIdentifier())) 1459 GetOrEmitProtocol(PD); 1460} 1461 1462llvm::Constant *CGObjCCommonMac::GetProtocolRef(const ObjCProtocolDecl *PD) { 1463 if (DefinedProtocols.count(PD->getIdentifier())) 1464 return GetOrEmitProtocol(PD); 1465 return GetOrEmitProtocolRef(PD); 1466} 1467 1468/* 1469 // APPLE LOCAL radar 4585769 - Objective-C 1.0 extensions 1470 struct _objc_protocol { 1471 struct _objc_protocol_extension *isa; 1472 char *protocol_name; 1473 struct _objc_protocol_list *protocol_list; 1474 struct _objc__method_prototype_list *instance_methods; 1475 struct _objc__method_prototype_list *class_methods 1476 }; 1477 1478 See EmitProtocolExtension(). 1479*/ 1480llvm::Constant *CGObjCMac::GetOrEmitProtocol(const ObjCProtocolDecl *PD) { 1481 llvm::GlobalVariable *&Entry = Protocols[PD->getIdentifier()]; 1482 1483 // Early exit if a defining object has already been generated. 1484 if (Entry && Entry->hasInitializer()) 1485 return Entry; 1486 1487 // FIXME: I don't understand why gcc generates this, or where it is 1488 // resolved. Investigate. Its also wasteful to look this up over and 1489 // over. 1490 LazySymbols.insert(&CGM.getContext().Idents.get("Protocol")); 1491 1492 const char *ProtocolName = PD->getNameAsCString(); 1493 1494 // Construct method lists. 1495 std::vector<llvm::Constant*> InstanceMethods, ClassMethods; 1496 std::vector<llvm::Constant*> OptInstanceMethods, OptClassMethods; 1497 for (ObjCProtocolDecl::instmeth_iterator 1498 i = PD->instmeth_begin(CGM.getContext()), 1499 e = PD->instmeth_end(CGM.getContext()); i != e; ++i) { 1500 ObjCMethodDecl *MD = *i; 1501 llvm::Constant *C = GetMethodDescriptionConstant(MD); 1502 if (MD->getImplementationControl() == ObjCMethodDecl::Optional) { 1503 OptInstanceMethods.push_back(C); 1504 } else { 1505 InstanceMethods.push_back(C); 1506 } 1507 } 1508 1509 for (ObjCProtocolDecl::classmeth_iterator 1510 i = PD->classmeth_begin(CGM.getContext()), 1511 e = PD->classmeth_end(CGM.getContext()); i != e; ++i) { 1512 ObjCMethodDecl *MD = *i; 1513 llvm::Constant *C = GetMethodDescriptionConstant(MD); 1514 if (MD->getImplementationControl() == ObjCMethodDecl::Optional) { 1515 OptClassMethods.push_back(C); 1516 } else { 1517 ClassMethods.push_back(C); 1518 } 1519 } 1520 1521 std::vector<llvm::Constant*> Values(5); 1522 Values[0] = EmitProtocolExtension(PD, OptInstanceMethods, OptClassMethods); 1523 Values[1] = GetClassName(PD->getIdentifier()); 1524 Values[2] = 1525 EmitProtocolList("\01L_OBJC_PROTOCOL_REFS_" + PD->getNameAsString(), 1526 PD->protocol_begin(), 1527 PD->protocol_end()); 1528 Values[3] = 1529 EmitMethodDescList("\01L_OBJC_PROTOCOL_INSTANCE_METHODS_" 1530 + PD->getNameAsString(), 1531 "__OBJC,__cat_inst_meth,regular,no_dead_strip", 1532 InstanceMethods); 1533 Values[4] = 1534 EmitMethodDescList("\01L_OBJC_PROTOCOL_CLASS_METHODS_" 1535 + PD->getNameAsString(), 1536 "__OBJC,__cat_cls_meth,regular,no_dead_strip", 1537 ClassMethods); 1538 llvm::Constant *Init = llvm::ConstantStruct::get(ObjCTypes.ProtocolTy, 1539 Values); 1540 1541 if (Entry) { 1542 // Already created, fix the linkage and update the initializer. 1543 Entry->setLinkage(llvm::GlobalValue::InternalLinkage); 1544 Entry->setInitializer(Init); 1545 } else { 1546 Entry = 1547 new llvm::GlobalVariable(ObjCTypes.ProtocolTy, false, 1548 llvm::GlobalValue::InternalLinkage, 1549 Init, 1550 std::string("\01L_OBJC_PROTOCOL_")+ProtocolName, 1551 &CGM.getModule()); 1552 Entry->setSection("__OBJC,__protocol,regular,no_dead_strip"); 1553 Entry->setAlignment(4); 1554 UsedGlobals.push_back(Entry); 1555 // FIXME: Is this necessary? Why only for protocol? 1556 Entry->setAlignment(4); 1557 } 1558 1559 return Entry; 1560} 1561 1562llvm::Constant *CGObjCMac::GetOrEmitProtocolRef(const ObjCProtocolDecl *PD) { 1563 llvm::GlobalVariable *&Entry = Protocols[PD->getIdentifier()]; 1564 1565 if (!Entry) { 1566 // We use the initializer as a marker of whether this is a forward 1567 // reference or not. At module finalization we add the empty 1568 // contents for protocols which were referenced but never defined. 1569 Entry = 1570 new llvm::GlobalVariable(ObjCTypes.ProtocolTy, false, 1571 llvm::GlobalValue::ExternalLinkage, 1572 0, 1573 "\01L_OBJC_PROTOCOL_" + PD->getNameAsString(), 1574 &CGM.getModule()); 1575 Entry->setSection("__OBJC,__protocol,regular,no_dead_strip"); 1576 Entry->setAlignment(4); 1577 UsedGlobals.push_back(Entry); 1578 // FIXME: Is this necessary? Why only for protocol? 1579 Entry->setAlignment(4); 1580 } 1581 1582 return Entry; 1583} 1584 1585/* 1586 struct _objc_protocol_extension { 1587 uint32_t size; 1588 struct objc_method_description_list *optional_instance_methods; 1589 struct objc_method_description_list *optional_class_methods; 1590 struct objc_property_list *instance_properties; 1591 }; 1592*/ 1593llvm::Constant * 1594CGObjCMac::EmitProtocolExtension(const ObjCProtocolDecl *PD, 1595 const ConstantVector &OptInstanceMethods, 1596 const ConstantVector &OptClassMethods) { 1597 uint64_t Size = 1598 CGM.getTargetData().getTypePaddedSize(ObjCTypes.ProtocolExtensionTy); 1599 std::vector<llvm::Constant*> Values(4); 1600 Values[0] = llvm::ConstantInt::get(ObjCTypes.IntTy, Size); 1601 Values[1] = 1602 EmitMethodDescList("\01L_OBJC_PROTOCOL_INSTANCE_METHODS_OPT_" 1603 + PD->getNameAsString(), 1604 "__OBJC,__cat_inst_meth,regular,no_dead_strip", 1605 OptInstanceMethods); 1606 Values[2] = 1607 EmitMethodDescList("\01L_OBJC_PROTOCOL_CLASS_METHODS_OPT_" 1608 + PD->getNameAsString(), 1609 "__OBJC,__cat_cls_meth,regular,no_dead_strip", 1610 OptClassMethods); 1611 Values[3] = EmitPropertyList("\01L_OBJC_$_PROP_PROTO_LIST_" + 1612 PD->getNameAsString(), 1613 0, PD, ObjCTypes); 1614 1615 // Return null if no extension bits are used. 1616 if (Values[1]->isNullValue() && Values[2]->isNullValue() && 1617 Values[3]->isNullValue()) 1618 return llvm::Constant::getNullValue(ObjCTypes.ProtocolExtensionPtrTy); 1619 1620 llvm::Constant *Init = 1621 llvm::ConstantStruct::get(ObjCTypes.ProtocolExtensionTy, Values); 1622 1623 // No special section, but goes in llvm.used 1624 return CreateMetadataVar("\01L_OBJC_PROTOCOLEXT_" + PD->getNameAsString(), 1625 Init, 1626 0, 0, true); 1627} 1628 1629/* 1630 struct objc_protocol_list { 1631 struct objc_protocol_list *next; 1632 long count; 1633 Protocol *list[]; 1634 }; 1635*/ 1636llvm::Constant * 1637CGObjCMac::EmitProtocolList(const std::string &Name, 1638 ObjCProtocolDecl::protocol_iterator begin, 1639 ObjCProtocolDecl::protocol_iterator end) { 1640 std::vector<llvm::Constant*> ProtocolRefs; 1641 1642 for (; begin != end; ++begin) 1643 ProtocolRefs.push_back(GetProtocolRef(*begin)); 1644 1645 // Just return null for empty protocol lists 1646 if (ProtocolRefs.empty()) 1647 return llvm::Constant::getNullValue(ObjCTypes.ProtocolListPtrTy); 1648 1649 // This list is null terminated. 1650 ProtocolRefs.push_back(llvm::Constant::getNullValue(ObjCTypes.ProtocolPtrTy)); 1651 1652 std::vector<llvm::Constant*> Values(3); 1653 // This field is only used by the runtime. 1654 Values[0] = llvm::Constant::getNullValue(ObjCTypes.ProtocolListPtrTy); 1655 Values[1] = llvm::ConstantInt::get(ObjCTypes.LongTy, ProtocolRefs.size() - 1); 1656 Values[2] = 1657 llvm::ConstantArray::get(llvm::ArrayType::get(ObjCTypes.ProtocolPtrTy, 1658 ProtocolRefs.size()), 1659 ProtocolRefs); 1660 1661 llvm::Constant *Init = llvm::ConstantStruct::get(Values); 1662 llvm::GlobalVariable *GV = 1663 CreateMetadataVar(Name, Init, "__OBJC,__cat_cls_meth,regular,no_dead_strip", 1664 4, false); 1665 return llvm::ConstantExpr::getBitCast(GV, ObjCTypes.ProtocolListPtrTy); 1666} 1667 1668/* 1669 struct _objc_property { 1670 const char * const name; 1671 const char * const attributes; 1672 }; 1673 1674 struct _objc_property_list { 1675 uint32_t entsize; // sizeof (struct _objc_property) 1676 uint32_t prop_count; 1677 struct _objc_property[prop_count]; 1678 }; 1679*/ 1680llvm::Constant *CGObjCCommonMac::EmitPropertyList(const std::string &Name, 1681 const Decl *Container, 1682 const ObjCContainerDecl *OCD, 1683 const ObjCCommonTypesHelper &ObjCTypes) { 1684 std::vector<llvm::Constant*> Properties, Prop(2); 1685 for (ObjCContainerDecl::prop_iterator I = OCD->prop_begin(CGM.getContext()), 1686 E = OCD->prop_end(CGM.getContext()); I != E; ++I) { 1687 const ObjCPropertyDecl *PD = *I; 1688 Prop[0] = GetPropertyName(PD->getIdentifier()); 1689 Prop[1] = GetPropertyTypeString(PD, Container); 1690 Properties.push_back(llvm::ConstantStruct::get(ObjCTypes.PropertyTy, 1691 Prop)); 1692 } 1693 1694 // Return null for empty list. 1695 if (Properties.empty()) 1696 return llvm::Constant::getNullValue(ObjCTypes.PropertyListPtrTy); 1697 1698 unsigned PropertySize = 1699 CGM.getTargetData().getTypePaddedSize(ObjCTypes.PropertyTy); 1700 std::vector<llvm::Constant*> Values(3); 1701 Values[0] = llvm::ConstantInt::get(ObjCTypes.IntTy, PropertySize); 1702 Values[1] = llvm::ConstantInt::get(ObjCTypes.IntTy, Properties.size()); 1703 llvm::ArrayType *AT = llvm::ArrayType::get(ObjCTypes.PropertyTy, 1704 Properties.size()); 1705 Values[2] = llvm::ConstantArray::get(AT, Properties); 1706 llvm::Constant *Init = llvm::ConstantStruct::get(Values); 1707 1708 llvm::GlobalVariable *GV = 1709 CreateMetadataVar(Name, Init, 1710 (ObjCABI == 2) ? "__DATA, __objc_const" : 1711 "__OBJC,__property,regular,no_dead_strip", 1712 (ObjCABI == 2) ? 8 : 4, 1713 true); 1714 return llvm::ConstantExpr::getBitCast(GV, ObjCTypes.PropertyListPtrTy); 1715} 1716 1717/* 1718 struct objc_method_description_list { 1719 int count; 1720 struct objc_method_description list[]; 1721 }; 1722*/ 1723llvm::Constant * 1724CGObjCMac::GetMethodDescriptionConstant(const ObjCMethodDecl *MD) { 1725 std::vector<llvm::Constant*> Desc(2); 1726 Desc[0] = llvm::ConstantExpr::getBitCast(GetMethodVarName(MD->getSelector()), 1727 ObjCTypes.SelectorPtrTy); 1728 Desc[1] = GetMethodVarType(MD); 1729 return llvm::ConstantStruct::get(ObjCTypes.MethodDescriptionTy, 1730 Desc); 1731} 1732 1733llvm::Constant *CGObjCMac::EmitMethodDescList(const std::string &Name, 1734 const char *Section, 1735 const ConstantVector &Methods) { 1736 // Return null for empty list. 1737 if (Methods.empty()) 1738 return llvm::Constant::getNullValue(ObjCTypes.MethodDescriptionListPtrTy); 1739 1740 std::vector<llvm::Constant*> Values(2); 1741 Values[0] = llvm::ConstantInt::get(ObjCTypes.IntTy, Methods.size()); 1742 llvm::ArrayType *AT = llvm::ArrayType::get(ObjCTypes.MethodDescriptionTy, 1743 Methods.size()); 1744 Values[1] = llvm::ConstantArray::get(AT, Methods); 1745 llvm::Constant *Init = llvm::ConstantStruct::get(Values); 1746 1747 llvm::GlobalVariable *GV = CreateMetadataVar(Name, Init, Section, 4, true); 1748 return llvm::ConstantExpr::getBitCast(GV, 1749 ObjCTypes.MethodDescriptionListPtrTy); 1750} 1751 1752/* 1753 struct _objc_category { 1754 char *category_name; 1755 char *class_name; 1756 struct _objc_method_list *instance_methods; 1757 struct _objc_method_list *class_methods; 1758 struct _objc_protocol_list *protocols; 1759 uint32_t size; // <rdar://4585769> 1760 struct _objc_property_list *instance_properties; 1761 }; 1762 */ 1763void CGObjCMac::GenerateCategory(const ObjCCategoryImplDecl *OCD) { 1764 unsigned Size = CGM.getTargetData().getTypePaddedSize(ObjCTypes.CategoryTy); 1765 1766 // FIXME: This is poor design, the OCD should have a pointer to the 1767 // category decl. Additionally, note that Category can be null for 1768 // the @implementation w/o an @interface case. Sema should just 1769 // create one for us as it does for @implementation so everyone else 1770 // can live life under a clear blue sky. 1771 const ObjCInterfaceDecl *Interface = OCD->getClassInterface(); 1772 const ObjCCategoryDecl *Category = 1773 Interface->FindCategoryDeclaration(OCD->getIdentifier()); 1774 std::string ExtName(Interface->getNameAsString() + "_" + 1775 OCD->getNameAsString()); 1776 1777 std::vector<llvm::Constant*> InstanceMethods, ClassMethods; 1778 for (ObjCCategoryImplDecl::instmeth_iterator 1779 i = OCD->instmeth_begin(CGM.getContext()), 1780 e = OCD->instmeth_end(CGM.getContext()); i != e; ++i) { 1781 // Instance methods should always be defined. 1782 InstanceMethods.push_back(GetMethodConstant(*i)); 1783 } 1784 for (ObjCCategoryImplDecl::classmeth_iterator 1785 i = OCD->classmeth_begin(CGM.getContext()), 1786 e = OCD->classmeth_end(CGM.getContext()); i != e; ++i) { 1787 // Class methods should always be defined. 1788 ClassMethods.push_back(GetMethodConstant(*i)); 1789 } 1790 1791 std::vector<llvm::Constant*> Values(7); 1792 Values[0] = GetClassName(OCD->getIdentifier()); 1793 Values[1] = GetClassName(Interface->getIdentifier()); 1794 LazySymbols.insert(Interface->getIdentifier()); 1795 Values[2] = 1796 EmitMethodList(std::string("\01L_OBJC_CATEGORY_INSTANCE_METHODS_") + 1797 ExtName, 1798 "__OBJC,__cat_inst_meth,regular,no_dead_strip", 1799 InstanceMethods); 1800 Values[3] = 1801 EmitMethodList(std::string("\01L_OBJC_CATEGORY_CLASS_METHODS_") + ExtName, 1802 "__OBJC,__cat_cls_meth,regular,no_dead_strip", 1803 ClassMethods); 1804 if (Category) { 1805 Values[4] = 1806 EmitProtocolList(std::string("\01L_OBJC_CATEGORY_PROTOCOLS_") + ExtName, 1807 Category->protocol_begin(), 1808 Category->protocol_end()); 1809 } else { 1810 Values[4] = llvm::Constant::getNullValue(ObjCTypes.ProtocolListPtrTy); 1811 } 1812 Values[5] = llvm::ConstantInt::get(ObjCTypes.IntTy, Size); 1813 1814 // If there is no category @interface then there can be no properties. 1815 if (Category) { 1816 Values[6] = EmitPropertyList(std::string("\01l_OBJC_$_PROP_LIST_") + ExtName, 1817 OCD, Category, ObjCTypes); 1818 } else { 1819 Values[6] = llvm::Constant::getNullValue(ObjCTypes.PropertyListPtrTy); 1820 } 1821 1822 llvm::Constant *Init = llvm::ConstantStruct::get(ObjCTypes.CategoryTy, 1823 Values); 1824 1825 llvm::GlobalVariable *GV = 1826 CreateMetadataVar(std::string("\01L_OBJC_CATEGORY_")+ExtName, Init, 1827 "__OBJC,__category,regular,no_dead_strip", 1828 4, true); 1829 DefinedCategories.push_back(GV); 1830} 1831 1832// FIXME: Get from somewhere? 1833enum ClassFlags { 1834 eClassFlags_Factory = 0x00001, 1835 eClassFlags_Meta = 0x00002, 1836 // <rdr://5142207> 1837 eClassFlags_HasCXXStructors = 0x02000, 1838 eClassFlags_Hidden = 0x20000, 1839 eClassFlags_ABI2_Hidden = 0x00010, 1840 eClassFlags_ABI2_HasCXXStructors = 0x00004 // <rdr://4923634> 1841}; 1842 1843/* 1844 struct _objc_class { 1845 Class isa; 1846 Class super_class; 1847 const char *name; 1848 long version; 1849 long info; 1850 long instance_size; 1851 struct _objc_ivar_list *ivars; 1852 struct _objc_method_list *methods; 1853 struct _objc_cache *cache; 1854 struct _objc_protocol_list *protocols; 1855 // Objective-C 1.0 extensions (<rdr://4585769>) 1856 const char *ivar_layout; 1857 struct _objc_class_ext *ext; 1858 }; 1859 1860 See EmitClassExtension(); 1861 */ 1862void CGObjCMac::GenerateClass(const ObjCImplementationDecl *ID) { 1863 DefinedSymbols.insert(ID->getIdentifier()); 1864 1865 std::string ClassName = ID->getNameAsString(); 1866 // FIXME: Gross 1867 ObjCInterfaceDecl *Interface = 1868 const_cast<ObjCInterfaceDecl*>(ID->getClassInterface()); 1869 llvm::Constant *Protocols = 1870 EmitProtocolList("\01L_OBJC_CLASS_PROTOCOLS_" + ID->getNameAsString(), 1871 Interface->protocol_begin(), 1872 Interface->protocol_end()); 1873 unsigned Flags = eClassFlags_Factory; 1874 unsigned Size = 1875 CGM.getContext().getASTObjCImplementationLayout(ID).getSize() / 8; 1876 1877 // FIXME: Set CXX-structors flag. 1878 if (CGM.getDeclVisibilityMode(ID->getClassInterface()) == LangOptions::Hidden) 1879 Flags |= eClassFlags_Hidden; 1880 1881 std::vector<llvm::Constant*> InstanceMethods, ClassMethods; 1882 for (ObjCImplementationDecl::instmeth_iterator 1883 i = ID->instmeth_begin(CGM.getContext()), 1884 e = ID->instmeth_end(CGM.getContext()); i != e; ++i) { 1885 // Instance methods should always be defined. 1886 InstanceMethods.push_back(GetMethodConstant(*i)); 1887 } 1888 for (ObjCImplementationDecl::classmeth_iterator 1889 i = ID->classmeth_begin(CGM.getContext()), 1890 e = ID->classmeth_end(CGM.getContext()); i != e; ++i) { 1891 // Class methods should always be defined. 1892 ClassMethods.push_back(GetMethodConstant(*i)); 1893 } 1894 1895 for (ObjCImplementationDecl::propimpl_iterator 1896 i = ID->propimpl_begin(CGM.getContext()), 1897 e = ID->propimpl_end(CGM.getContext()); i != e; ++i) { 1898 ObjCPropertyImplDecl *PID = *i; 1899 1900 if (PID->getPropertyImplementation() == ObjCPropertyImplDecl::Synthesize) { 1901 ObjCPropertyDecl *PD = PID->getPropertyDecl(); 1902 1903 if (ObjCMethodDecl *MD = PD->getGetterMethodDecl()) 1904 if (llvm::Constant *C = GetMethodConstant(MD)) 1905 InstanceMethods.push_back(C); 1906 if (ObjCMethodDecl *MD = PD->getSetterMethodDecl()) 1907 if (llvm::Constant *C = GetMethodConstant(MD)) 1908 InstanceMethods.push_back(C); 1909 } 1910 } 1911 1912 std::vector<llvm::Constant*> Values(12); 1913 Values[ 0] = EmitMetaClass(ID, Protocols, ClassMethods); 1914 if (ObjCInterfaceDecl *Super = Interface->getSuperClass()) { 1915 // Record a reference to the super class. 1916 LazySymbols.insert(Super->getIdentifier()); 1917 1918 Values[ 1] = 1919 llvm::ConstantExpr::getBitCast(GetClassName(Super->getIdentifier()), 1920 ObjCTypes.ClassPtrTy); 1921 } else { 1922 Values[ 1] = llvm::Constant::getNullValue(ObjCTypes.ClassPtrTy); 1923 } 1924 Values[ 2] = GetClassName(ID->getIdentifier()); 1925 // Version is always 0. 1926 Values[ 3] = llvm::ConstantInt::get(ObjCTypes.LongTy, 0); 1927 Values[ 4] = llvm::ConstantInt::get(ObjCTypes.LongTy, Flags); 1928 Values[ 5] = llvm::ConstantInt::get(ObjCTypes.LongTy, Size); 1929 Values[ 6] = EmitIvarList(ID, false); 1930 Values[ 7] = 1931 EmitMethodList("\01L_OBJC_INSTANCE_METHODS_" + ID->getNameAsString(), 1932 "__OBJC,__inst_meth,regular,no_dead_strip", 1933 InstanceMethods); 1934 // cache is always NULL. 1935 Values[ 8] = llvm::Constant::getNullValue(ObjCTypes.CachePtrTy); 1936 Values[ 9] = Protocols; 1937 Values[10] = BuildIvarLayout(ID, true); 1938 Values[11] = EmitClassExtension(ID); 1939 llvm::Constant *Init = llvm::ConstantStruct::get(ObjCTypes.ClassTy, 1940 Values); 1941 1942 llvm::GlobalVariable *GV = 1943 CreateMetadataVar(std::string("\01L_OBJC_CLASS_")+ClassName, Init, 1944 "__OBJC,__class,regular,no_dead_strip", 1945 4, true); 1946 DefinedClasses.push_back(GV); 1947} 1948 1949llvm::Constant *CGObjCMac::EmitMetaClass(const ObjCImplementationDecl *ID, 1950 llvm::Constant *Protocols, 1951 const ConstantVector &Methods) { 1952 unsigned Flags = eClassFlags_Meta; 1953 unsigned Size = CGM.getTargetData().getTypePaddedSize(ObjCTypes.ClassTy); 1954 1955 if (CGM.getDeclVisibilityMode(ID->getClassInterface()) == LangOptions::Hidden) 1956 Flags |= eClassFlags_Hidden; 1957 1958 std::vector<llvm::Constant*> Values(12); 1959 // The isa for the metaclass is the root of the hierarchy. 1960 const ObjCInterfaceDecl *Root = ID->getClassInterface(); 1961 while (const ObjCInterfaceDecl *Super = Root->getSuperClass()) 1962 Root = Super; 1963 Values[ 0] = 1964 llvm::ConstantExpr::getBitCast(GetClassName(Root->getIdentifier()), 1965 ObjCTypes.ClassPtrTy); 1966 // The super class for the metaclass is emitted as the name of the 1967 // super class. The runtime fixes this up to point to the 1968 // *metaclass* for the super class. 1969 if (ObjCInterfaceDecl *Super = ID->getClassInterface()->getSuperClass()) { 1970 Values[ 1] = 1971 llvm::ConstantExpr::getBitCast(GetClassName(Super->getIdentifier()), 1972 ObjCTypes.ClassPtrTy); 1973 } else { 1974 Values[ 1] = llvm::Constant::getNullValue(ObjCTypes.ClassPtrTy); 1975 } 1976 Values[ 2] = GetClassName(ID->getIdentifier()); 1977 // Version is always 0. 1978 Values[ 3] = llvm::ConstantInt::get(ObjCTypes.LongTy, 0); 1979 Values[ 4] = llvm::ConstantInt::get(ObjCTypes.LongTy, Flags); 1980 Values[ 5] = llvm::ConstantInt::get(ObjCTypes.LongTy, Size); 1981 Values[ 6] = EmitIvarList(ID, true); 1982 Values[ 7] = 1983 EmitMethodList("\01L_OBJC_CLASS_METHODS_" + ID->getNameAsString(), 1984 "__OBJC,__cls_meth,regular,no_dead_strip", 1985 Methods); 1986 // cache is always NULL. 1987 Values[ 8] = llvm::Constant::getNullValue(ObjCTypes.CachePtrTy); 1988 Values[ 9] = Protocols; 1989 // ivar_layout for metaclass is always NULL. 1990 Values[10] = llvm::Constant::getNullValue(ObjCTypes.Int8PtrTy); 1991 // The class extension is always unused for metaclasses. 1992 Values[11] = llvm::Constant::getNullValue(ObjCTypes.ClassExtensionPtrTy); 1993 llvm::Constant *Init = llvm::ConstantStruct::get(ObjCTypes.ClassTy, 1994 Values); 1995 1996 std::string Name("\01L_OBJC_METACLASS_"); 1997 Name += ID->getNameAsCString(); 1998 1999 // Check for a forward reference. 2000 llvm::GlobalVariable *GV = CGM.getModule().getGlobalVariable(Name); 2001 if (GV) { 2002 assert(GV->getType()->getElementType() == ObjCTypes.ClassTy && 2003 "Forward metaclass reference has incorrect type."); 2004 GV->setLinkage(llvm::GlobalValue::InternalLinkage); 2005 GV->setInitializer(Init); 2006 } else { 2007 GV = new llvm::GlobalVariable(ObjCTypes.ClassTy, false, 2008 llvm::GlobalValue::InternalLinkage, 2009 Init, Name, 2010 &CGM.getModule()); 2011 } 2012 GV->setSection("__OBJC,__meta_class,regular,no_dead_strip"); 2013 GV->setAlignment(4); 2014 UsedGlobals.push_back(GV); 2015 2016 return GV; 2017} 2018 2019llvm::Constant *CGObjCMac::EmitMetaClassRef(const ObjCInterfaceDecl *ID) { 2020 std::string Name = "\01L_OBJC_METACLASS_" + ID->getNameAsString(); 2021 2022 // FIXME: Should we look these up somewhere other than the 2023 // module. Its a bit silly since we only generate these while 2024 // processing an implementation, so exactly one pointer would work 2025 // if know when we entered/exitted an implementation block. 2026 2027 // Check for an existing forward reference. 2028 // Previously, metaclass with internal linkage may have been defined. 2029 // pass 'true' as 2nd argument so it is returned. 2030 if (llvm::GlobalVariable *GV = CGM.getModule().getGlobalVariable(Name, true)) { 2031 assert(GV->getType()->getElementType() == ObjCTypes.ClassTy && 2032 "Forward metaclass reference has incorrect type."); 2033 return GV; 2034 } else { 2035 // Generate as an external reference to keep a consistent 2036 // module. This will be patched up when we emit the metaclass. 2037 return new llvm::GlobalVariable(ObjCTypes.ClassTy, false, 2038 llvm::GlobalValue::ExternalLinkage, 2039 0, 2040 Name, 2041 &CGM.getModule()); 2042 } 2043} 2044 2045/* 2046 struct objc_class_ext { 2047 uint32_t size; 2048 const char *weak_ivar_layout; 2049 struct _objc_property_list *properties; 2050 }; 2051*/ 2052llvm::Constant * 2053CGObjCMac::EmitClassExtension(const ObjCImplementationDecl *ID) { 2054 uint64_t Size = 2055 CGM.getTargetData().getTypePaddedSize(ObjCTypes.ClassExtensionTy); 2056 2057 std::vector<llvm::Constant*> Values(3); 2058 Values[0] = llvm::ConstantInt::get(ObjCTypes.IntTy, Size); 2059 Values[1] = BuildIvarLayout(ID, false); 2060 Values[2] = EmitPropertyList("\01l_OBJC_$_PROP_LIST_" + ID->getNameAsString(), 2061 ID, ID->getClassInterface(), ObjCTypes); 2062 2063 // Return null if no extension bits are used. 2064 if (Values[1]->isNullValue() && Values[2]->isNullValue()) 2065 return llvm::Constant::getNullValue(ObjCTypes.ClassExtensionPtrTy); 2066 2067 llvm::Constant *Init = 2068 llvm::ConstantStruct::get(ObjCTypes.ClassExtensionTy, Values); 2069 return CreateMetadataVar("\01L_OBJC_CLASSEXT_" + ID->getNameAsString(), 2070 Init, "__OBJC,__class_ext,regular,no_dead_strip", 2071 4, true); 2072} 2073 2074/// getInterfaceDeclForIvar - Get the interface declaration node where 2075/// this ivar is declared in. 2076/// FIXME. Ideally, this info should be in the ivar node. But currently 2077/// it is not and prevailing wisdom is that ASTs should not have more 2078/// info than is absolutely needed, even though this info reflects the 2079/// source language. 2080/// 2081static const ObjCInterfaceDecl *getInterfaceDeclForIvar( 2082 const ObjCInterfaceDecl *OI, 2083 const ObjCIvarDecl *IVD, 2084 ASTContext &Context) { 2085 if (!OI) 2086 return 0; 2087 assert(isa<ObjCInterfaceDecl>(OI) && "OI is not an interface"); 2088 for (ObjCInterfaceDecl::ivar_iterator I = OI->ivar_begin(), 2089 E = OI->ivar_end(); I != E; ++I) 2090 if ((*I)->getIdentifier() == IVD->getIdentifier()) 2091 return OI; 2092 // look into properties. 2093 for (ObjCInterfaceDecl::prop_iterator I = OI->prop_begin(Context), 2094 E = OI->prop_end(Context); I != E; ++I) { 2095 ObjCPropertyDecl *PDecl = (*I); 2096 if (ObjCIvarDecl *IV = PDecl->getPropertyIvarDecl()) 2097 if (IV->getIdentifier() == IVD->getIdentifier()) 2098 return OI; 2099 } 2100 return getInterfaceDeclForIvar(OI->getSuperClass(), IVD, Context); 2101} 2102 2103/* 2104 struct objc_ivar { 2105 char *ivar_name; 2106 char *ivar_type; 2107 int ivar_offset; 2108 }; 2109 2110 struct objc_ivar_list { 2111 int ivar_count; 2112 struct objc_ivar list[count]; 2113 }; 2114 */ 2115llvm::Constant *CGObjCMac::EmitIvarList(const ObjCImplementationDecl *ID, 2116 bool ForClass) { 2117 std::vector<llvm::Constant*> Ivars, Ivar(3); 2118 2119 // When emitting the root class GCC emits ivar entries for the 2120 // actual class structure. It is not clear if we need to follow this 2121 // behavior; for now lets try and get away with not doing it. If so, 2122 // the cleanest solution would be to make up an ObjCInterfaceDecl 2123 // for the class. 2124 if (ForClass) 2125 return llvm::Constant::getNullValue(ObjCTypes.IvarListPtrTy); 2126 2127 ObjCInterfaceDecl *OID = 2128 const_cast<ObjCInterfaceDecl*>(ID->getClassInterface()); 2129 2130 llvm::SmallVector<ObjCIvarDecl*, 16> OIvars; 2131 GetNamedIvarList(OID, OIvars); 2132 2133 for (unsigned i = 0, e = OIvars.size(); i != e; ++i) { 2134 ObjCIvarDecl *IVD = OIvars[i]; 2135 Ivar[0] = GetMethodVarName(IVD->getIdentifier()); 2136 Ivar[1] = GetMethodVarType(IVD); 2137 Ivar[2] = llvm::ConstantInt::get(ObjCTypes.IntTy, 2138 ComputeIvarBaseOffset(CGM, OID, IVD)); 2139 Ivars.push_back(llvm::ConstantStruct::get(ObjCTypes.IvarTy, Ivar)); 2140 } 2141 2142 // Return null for empty list. 2143 if (Ivars.empty()) 2144 return llvm::Constant::getNullValue(ObjCTypes.IvarListPtrTy); 2145 2146 std::vector<llvm::Constant*> Values(2); 2147 Values[0] = llvm::ConstantInt::get(ObjCTypes.IntTy, Ivars.size()); 2148 llvm::ArrayType *AT = llvm::ArrayType::get(ObjCTypes.IvarTy, 2149 Ivars.size()); 2150 Values[1] = llvm::ConstantArray::get(AT, Ivars); 2151 llvm::Constant *Init = llvm::ConstantStruct::get(Values); 2152 2153 llvm::GlobalVariable *GV; 2154 if (ForClass) 2155 GV = CreateMetadataVar("\01L_OBJC_CLASS_VARIABLES_" + ID->getNameAsString(), 2156 Init, "__OBJC,__class_vars,regular,no_dead_strip", 2157 4, true); 2158 else 2159 GV = CreateMetadataVar("\01L_OBJC_INSTANCE_VARIABLES_" 2160 + ID->getNameAsString(), 2161 Init, "__OBJC,__instance_vars,regular,no_dead_strip", 2162 4, true); 2163 return llvm::ConstantExpr::getBitCast(GV, ObjCTypes.IvarListPtrTy); 2164} 2165 2166/* 2167 struct objc_method { 2168 SEL method_name; 2169 char *method_types; 2170 void *method; 2171 }; 2172 2173 struct objc_method_list { 2174 struct objc_method_list *obsolete; 2175 int count; 2176 struct objc_method methods_list[count]; 2177 }; 2178*/ 2179 2180/// GetMethodConstant - Return a struct objc_method constant for the 2181/// given method if it has been defined. The result is null if the 2182/// method has not been defined. The return value has type MethodPtrTy. 2183llvm::Constant *CGObjCMac::GetMethodConstant(const ObjCMethodDecl *MD) { 2184 // FIXME: Use DenseMap::lookup 2185 llvm::Function *Fn = MethodDefinitions[MD]; 2186 if (!Fn) 2187 return 0; 2188 2189 std::vector<llvm::Constant*> Method(3); 2190 Method[0] = 2191 llvm::ConstantExpr::getBitCast(GetMethodVarName(MD->getSelector()), 2192 ObjCTypes.SelectorPtrTy); 2193 Method[1] = GetMethodVarType(MD); 2194 Method[2] = llvm::ConstantExpr::getBitCast(Fn, ObjCTypes.Int8PtrTy); 2195 return llvm::ConstantStruct::get(ObjCTypes.MethodTy, Method); 2196} 2197 2198llvm::Constant *CGObjCMac::EmitMethodList(const std::string &Name, 2199 const char *Section, 2200 const ConstantVector &Methods) { 2201 // Return null for empty list. 2202 if (Methods.empty()) 2203 return llvm::Constant::getNullValue(ObjCTypes.MethodListPtrTy); 2204 2205 std::vector<llvm::Constant*> Values(3); 2206 Values[0] = llvm::Constant::getNullValue(ObjCTypes.Int8PtrTy); 2207 Values[1] = llvm::ConstantInt::get(ObjCTypes.IntTy, Methods.size()); 2208 llvm::ArrayType *AT = llvm::ArrayType::get(ObjCTypes.MethodTy, 2209 Methods.size()); 2210 Values[2] = llvm::ConstantArray::get(AT, Methods); 2211 llvm::Constant *Init = llvm::ConstantStruct::get(Values); 2212 2213 llvm::GlobalVariable *GV = CreateMetadataVar(Name, Init, Section, 4, true); 2214 return llvm::ConstantExpr::getBitCast(GV, 2215 ObjCTypes.MethodListPtrTy); 2216} 2217 2218llvm::Function *CGObjCCommonMac::GenerateMethod(const ObjCMethodDecl *OMD, 2219 const ObjCContainerDecl *CD) { 2220 std::string Name; 2221 GetNameForMethod(OMD, CD, Name); 2222 2223 CodeGenTypes &Types = CGM.getTypes(); 2224 const llvm::FunctionType *MethodTy = 2225 Types.GetFunctionType(Types.getFunctionInfo(OMD), OMD->isVariadic()); 2226 llvm::Function *Method = 2227 llvm::Function::Create(MethodTy, 2228 llvm::GlobalValue::InternalLinkage, 2229 Name, 2230 &CGM.getModule()); 2231 MethodDefinitions.insert(std::make_pair(OMD, Method)); 2232 2233 return Method; 2234} 2235 2236/// GetFieldBaseOffset - return the field's byte offset. 2237uint64_t CGObjCCommonMac::GetFieldBaseOffset(const ObjCInterfaceDecl *OI, 2238 const llvm::StructLayout *Layout, 2239 const FieldDecl *Field) { 2240 // Is this a C struct? 2241 if (!OI) 2242 return Layout->getElementOffset(CGM.getTypes().getLLVMFieldNo(Field)); 2243 return ComputeIvarBaseOffset(CGM, OI, cast<ObjCIvarDecl>(Field)); 2244} 2245 2246llvm::GlobalVariable * 2247CGObjCCommonMac::CreateMetadataVar(const std::string &Name, 2248 llvm::Constant *Init, 2249 const char *Section, 2250 unsigned Align, 2251 bool AddToUsed) { 2252 const llvm::Type *Ty = Init->getType(); 2253 llvm::GlobalVariable *GV = 2254 new llvm::GlobalVariable(Ty, false, 2255 llvm::GlobalValue::InternalLinkage, 2256 Init, 2257 Name, 2258 &CGM.getModule()); 2259 if (Section) 2260 GV->setSection(Section); 2261 if (Align) 2262 GV->setAlignment(Align); 2263 if (AddToUsed) 2264 UsedGlobals.push_back(GV); 2265 return GV; 2266} 2267 2268llvm::Function *CGObjCMac::ModuleInitFunction() { 2269 // Abuse this interface function as a place to finalize. 2270 FinishModule(); 2271 2272 return NULL; 2273} 2274 2275llvm::Constant *CGObjCMac::GetPropertyGetFunction() { 2276 return ObjCTypes.getGetPropertyFn(); 2277} 2278 2279llvm::Constant *CGObjCMac::GetPropertySetFunction() { 2280 return ObjCTypes.getSetPropertyFn(); 2281} 2282 2283llvm::Constant *CGObjCMac::EnumerationMutationFunction() { 2284 return ObjCTypes.getEnumerationMutationFn(); 2285} 2286 2287/* 2288 2289Objective-C setjmp-longjmp (sjlj) Exception Handling 2290-- 2291 2292The basic framework for a @try-catch-finally is as follows: 2293{ 2294 objc_exception_data d; 2295 id _rethrow = null; 2296 bool _call_try_exit = true; 2297 2298 objc_exception_try_enter(&d); 2299 if (!setjmp(d.jmp_buf)) { 2300 ... try body ... 2301 } else { 2302 // exception path 2303 id _caught = objc_exception_extract(&d); 2304 2305 // enter new try scope for handlers 2306 if (!setjmp(d.jmp_buf)) { 2307 ... match exception and execute catch blocks ... 2308 2309 // fell off end, rethrow. 2310 _rethrow = _caught; 2311 ... jump-through-finally to finally_rethrow ... 2312 } else { 2313 // exception in catch block 2314 _rethrow = objc_exception_extract(&d); 2315 _call_try_exit = false; 2316 ... jump-through-finally to finally_rethrow ... 2317 } 2318 } 2319 ... jump-through-finally to finally_end ... 2320 2321finally: 2322 if (_call_try_exit) 2323 objc_exception_try_exit(&d); 2324 2325 ... finally block .... 2326 ... dispatch to finally destination ... 2327 2328finally_rethrow: 2329 objc_exception_throw(_rethrow); 2330 2331finally_end: 2332} 2333 2334This framework differs slightly from the one gcc uses, in that gcc 2335uses _rethrow to determine if objc_exception_try_exit should be called 2336and if the object should be rethrown. This breaks in the face of 2337throwing nil and introduces unnecessary branches. 2338 2339We specialize this framework for a few particular circumstances: 2340 2341 - If there are no catch blocks, then we avoid emitting the second 2342 exception handling context. 2343 2344 - If there is a catch-all catch block (i.e. @catch(...) or @catch(id 2345 e)) we avoid emitting the code to rethrow an uncaught exception. 2346 2347 - FIXME: If there is no @finally block we can do a few more 2348 simplifications. 2349 2350Rethrows and Jumps-Through-Finally 2351-- 2352 2353Support for implicit rethrows and jumping through the finally block is 2354handled by storing the current exception-handling context in 2355ObjCEHStack. 2356 2357In order to implement proper @finally semantics, we support one basic 2358mechanism for jumping through the finally block to an arbitrary 2359destination. Constructs which generate exits from a @try or @catch 2360block use this mechanism to implement the proper semantics by chaining 2361jumps, as necessary. 2362 2363This mechanism works like the one used for indirect goto: we 2364arbitrarily assign an ID to each destination and store the ID for the 2365destination in a variable prior to entering the finally block. At the 2366end of the finally block we simply create a switch to the proper 2367destination. 2368 2369Code gen for @synchronized(expr) stmt; 2370Effectively generating code for: 2371objc_sync_enter(expr); 2372@try stmt @finally { objc_sync_exit(expr); } 2373*/ 2374 2375void CGObjCMac::EmitTryOrSynchronizedStmt(CodeGen::CodeGenFunction &CGF, 2376 const Stmt &S) { 2377 bool isTry = isa<ObjCAtTryStmt>(S); 2378 // Create various blocks we refer to for handling @finally. 2379 llvm::BasicBlock *FinallyBlock = CGF.createBasicBlock("finally"); 2380 llvm::BasicBlock *FinallyExit = CGF.createBasicBlock("finally.exit"); 2381 llvm::BasicBlock *FinallyNoExit = CGF.createBasicBlock("finally.noexit"); 2382 llvm::BasicBlock *FinallyRethrow = CGF.createBasicBlock("finally.throw"); 2383 llvm::BasicBlock *FinallyEnd = CGF.createBasicBlock("finally.end"); 2384 2385 // For @synchronized, call objc_sync_enter(sync.expr). The 2386 // evaluation of the expression must occur before we enter the 2387 // @synchronized. We can safely avoid a temp here because jumps into 2388 // @synchronized are illegal & this will dominate uses. 2389 llvm::Value *SyncArg = 0; 2390 if (!isTry) { 2391 SyncArg = 2392 CGF.EmitScalarExpr(cast<ObjCAtSynchronizedStmt>(S).getSynchExpr()); 2393 SyncArg = CGF.Builder.CreateBitCast(SyncArg, ObjCTypes.ObjectPtrTy); 2394 CGF.Builder.CreateCall(ObjCTypes.getSyncEnterFn(), SyncArg); 2395 } 2396 2397 // Push an EH context entry, used for handling rethrows and jumps 2398 // through finally. 2399 CGF.PushCleanupBlock(FinallyBlock); 2400 2401 CGF.ObjCEHValueStack.push_back(0); 2402 2403 // Allocate memory for the exception data and rethrow pointer. 2404 llvm::Value *ExceptionData = CGF.CreateTempAlloca(ObjCTypes.ExceptionDataTy, 2405 "exceptiondata.ptr"); 2406 llvm::Value *RethrowPtr = CGF.CreateTempAlloca(ObjCTypes.ObjectPtrTy, 2407 "_rethrow"); 2408 llvm::Value *CallTryExitPtr = CGF.CreateTempAlloca(llvm::Type::Int1Ty, 2409 "_call_try_exit"); 2410 CGF.Builder.CreateStore(llvm::ConstantInt::getTrue(), CallTryExitPtr); 2411 2412 // Enter a new try block and call setjmp. 2413 CGF.Builder.CreateCall(ObjCTypes.getExceptionTryEnterFn(), ExceptionData); 2414 llvm::Value *JmpBufPtr = CGF.Builder.CreateStructGEP(ExceptionData, 0, 2415 "jmpbufarray"); 2416 JmpBufPtr = CGF.Builder.CreateStructGEP(JmpBufPtr, 0, "tmp"); 2417 llvm::Value *SetJmpResult = CGF.Builder.CreateCall(ObjCTypes.getSetJmpFn(), 2418 JmpBufPtr, "result"); 2419 2420 llvm::BasicBlock *TryBlock = CGF.createBasicBlock("try"); 2421 llvm::BasicBlock *TryHandler = CGF.createBasicBlock("try.handler"); 2422 CGF.Builder.CreateCondBr(CGF.Builder.CreateIsNotNull(SetJmpResult, "threw"), 2423 TryHandler, TryBlock); 2424 2425 // Emit the @try block. 2426 CGF.EmitBlock(TryBlock); 2427 CGF.EmitStmt(isTry ? cast<ObjCAtTryStmt>(S).getTryBody() 2428 : cast<ObjCAtSynchronizedStmt>(S).getSynchBody()); 2429 CGF.EmitBranchThroughCleanup(FinallyEnd); 2430 2431 // Emit the "exception in @try" block. 2432 CGF.EmitBlock(TryHandler); 2433 2434 // Retrieve the exception object. We may emit multiple blocks but 2435 // nothing can cross this so the value is already in SSA form. 2436 llvm::Value *Caught = 2437 CGF.Builder.CreateCall(ObjCTypes.getExceptionExtractFn(), 2438 ExceptionData, "caught"); 2439 CGF.ObjCEHValueStack.back() = Caught; 2440 if (!isTry) 2441 { 2442 CGF.Builder.CreateStore(Caught, RethrowPtr); 2443 CGF.Builder.CreateStore(llvm::ConstantInt::getFalse(), CallTryExitPtr); 2444 CGF.EmitBranchThroughCleanup(FinallyRethrow); 2445 } 2446 else if (const ObjCAtCatchStmt* CatchStmt = 2447 cast<ObjCAtTryStmt>(S).getCatchStmts()) 2448 { 2449 // Enter a new exception try block (in case a @catch block throws 2450 // an exception). 2451 CGF.Builder.CreateCall(ObjCTypes.getExceptionTryEnterFn(), ExceptionData); 2452 2453 llvm::Value *SetJmpResult = CGF.Builder.CreateCall(ObjCTypes.getSetJmpFn(), 2454 JmpBufPtr, "result"); 2455 llvm::Value *Threw = CGF.Builder.CreateIsNotNull(SetJmpResult, "threw"); 2456 2457 llvm::BasicBlock *CatchBlock = CGF.createBasicBlock("catch"); 2458 llvm::BasicBlock *CatchHandler = CGF.createBasicBlock("catch.handler"); 2459 CGF.Builder.CreateCondBr(Threw, CatchHandler, CatchBlock); 2460 2461 CGF.EmitBlock(CatchBlock); 2462 2463 // Handle catch list. As a special case we check if everything is 2464 // matched and avoid generating code for falling off the end if 2465 // so. 2466 bool AllMatched = false; 2467 for (; CatchStmt; CatchStmt = CatchStmt->getNextCatchStmt()) { 2468 llvm::BasicBlock *NextCatchBlock = CGF.createBasicBlock("catch"); 2469 2470 const ParmVarDecl *CatchParam = CatchStmt->getCatchParamDecl(); 2471 const PointerType *PT = 0; 2472 2473 // catch(...) always matches. 2474 if (!CatchParam) { 2475 AllMatched = true; 2476 } else { 2477 PT = CatchParam->getType()->getAsPointerType(); 2478 2479 // catch(id e) always matches. 2480 // FIXME: For the time being we also match id<X>; this should 2481 // be rejected by Sema instead. 2482 if ((PT && CGF.getContext().isObjCIdStructType(PT->getPointeeType())) || 2483 CatchParam->getType()->isObjCQualifiedIdType()) 2484 AllMatched = true; 2485 } 2486 2487 if (AllMatched) { 2488 if (CatchParam) { 2489 CGF.EmitLocalBlockVarDecl(*CatchParam); 2490 assert(CGF.HaveInsertPoint() && "DeclStmt destroyed insert point?"); 2491 CGF.Builder.CreateStore(Caught, CGF.GetAddrOfLocalVar(CatchParam)); 2492 } 2493 2494 CGF.EmitStmt(CatchStmt->getCatchBody()); 2495 CGF.EmitBranchThroughCleanup(FinallyEnd); 2496 break; 2497 } 2498 2499 assert(PT && "Unexpected non-pointer type in @catch"); 2500 QualType T = PT->getPointeeType(); 2501 const ObjCInterfaceType *ObjCType = T->getAsObjCInterfaceType(); 2502 assert(ObjCType && "Catch parameter must have Objective-C type!"); 2503 2504 // Check if the @catch block matches the exception object. 2505 llvm::Value *Class = EmitClassRef(CGF.Builder, ObjCType->getDecl()); 2506 2507 llvm::Value *Match = 2508 CGF.Builder.CreateCall2(ObjCTypes.getExceptionMatchFn(), 2509 Class, Caught, "match"); 2510 2511 llvm::BasicBlock *MatchedBlock = CGF.createBasicBlock("matched"); 2512 2513 CGF.Builder.CreateCondBr(CGF.Builder.CreateIsNotNull(Match, "matched"), 2514 MatchedBlock, NextCatchBlock); 2515 2516 // Emit the @catch block. 2517 CGF.EmitBlock(MatchedBlock); 2518 CGF.EmitLocalBlockVarDecl(*CatchParam); 2519 assert(CGF.HaveInsertPoint() && "DeclStmt destroyed insert point?"); 2520 2521 llvm::Value *Tmp = 2522 CGF.Builder.CreateBitCast(Caught, CGF.ConvertType(CatchParam->getType()), 2523 "tmp"); 2524 CGF.Builder.CreateStore(Tmp, CGF.GetAddrOfLocalVar(CatchParam)); 2525 2526 CGF.EmitStmt(CatchStmt->getCatchBody()); 2527 CGF.EmitBranchThroughCleanup(FinallyEnd); 2528 2529 CGF.EmitBlock(NextCatchBlock); 2530 } 2531 2532 if (!AllMatched) { 2533 // None of the handlers caught the exception, so store it to be 2534 // rethrown at the end of the @finally block. 2535 CGF.Builder.CreateStore(Caught, RethrowPtr); 2536 CGF.EmitBranchThroughCleanup(FinallyRethrow); 2537 } 2538 2539 // Emit the exception handler for the @catch blocks. 2540 CGF.EmitBlock(CatchHandler); 2541 CGF.Builder.CreateStore( 2542 CGF.Builder.CreateCall(ObjCTypes.getExceptionExtractFn(), 2543 ExceptionData), 2544 RethrowPtr); 2545 CGF.Builder.CreateStore(llvm::ConstantInt::getFalse(), CallTryExitPtr); 2546 CGF.EmitBranchThroughCleanup(FinallyRethrow); 2547 } else { 2548 CGF.Builder.CreateStore(Caught, RethrowPtr); 2549 CGF.Builder.CreateStore(llvm::ConstantInt::getFalse(), CallTryExitPtr); 2550 CGF.EmitBranchThroughCleanup(FinallyRethrow); 2551 } 2552 2553 // Pop the exception-handling stack entry. It is important to do 2554 // this now, because the code in the @finally block is not in this 2555 // context. 2556 CodeGenFunction::CleanupBlockInfo Info = CGF.PopCleanupBlock(); 2557 2558 CGF.ObjCEHValueStack.pop_back(); 2559 2560 // Emit the @finally block. 2561 CGF.EmitBlock(FinallyBlock); 2562 llvm::Value* CallTryExit = CGF.Builder.CreateLoad(CallTryExitPtr, "tmp"); 2563 2564 CGF.Builder.CreateCondBr(CallTryExit, FinallyExit, FinallyNoExit); 2565 2566 CGF.EmitBlock(FinallyExit); 2567 CGF.Builder.CreateCall(ObjCTypes.getExceptionTryExitFn(), ExceptionData); 2568 2569 CGF.EmitBlock(FinallyNoExit); 2570 if (isTry) { 2571 if (const ObjCAtFinallyStmt* FinallyStmt = 2572 cast<ObjCAtTryStmt>(S).getFinallyStmt()) 2573 CGF.EmitStmt(FinallyStmt->getFinallyBody()); 2574 } else { 2575 // Emit objc_sync_exit(expr); as finally's sole statement for 2576 // @synchronized. 2577 CGF.Builder.CreateCall(ObjCTypes.getSyncExitFn(), SyncArg); 2578 } 2579 2580 // Emit the switch block 2581 if (Info.SwitchBlock) 2582 CGF.EmitBlock(Info.SwitchBlock); 2583 if (Info.EndBlock) 2584 CGF.EmitBlock(Info.EndBlock); 2585 2586 CGF.EmitBlock(FinallyRethrow); 2587 CGF.Builder.CreateCall(ObjCTypes.getExceptionThrowFn(), 2588 CGF.Builder.CreateLoad(RethrowPtr)); 2589 CGF.Builder.CreateUnreachable(); 2590 2591 CGF.EmitBlock(FinallyEnd); 2592} 2593 2594void CGObjCMac::EmitThrowStmt(CodeGen::CodeGenFunction &CGF, 2595 const ObjCAtThrowStmt &S) { 2596 llvm::Value *ExceptionAsObject; 2597 2598 if (const Expr *ThrowExpr = S.getThrowExpr()) { 2599 llvm::Value *Exception = CGF.EmitScalarExpr(ThrowExpr); 2600 ExceptionAsObject = 2601 CGF.Builder.CreateBitCast(Exception, ObjCTypes.ObjectPtrTy, "tmp"); 2602 } else { 2603 assert((!CGF.ObjCEHValueStack.empty() && CGF.ObjCEHValueStack.back()) && 2604 "Unexpected rethrow outside @catch block."); 2605 ExceptionAsObject = CGF.ObjCEHValueStack.back(); 2606 } 2607 2608 CGF.Builder.CreateCall(ObjCTypes.getExceptionThrowFn(), ExceptionAsObject); 2609 CGF.Builder.CreateUnreachable(); 2610 2611 // Clear the insertion point to indicate we are in unreachable code. 2612 CGF.Builder.ClearInsertionPoint(); 2613} 2614 2615/// EmitObjCWeakRead - Code gen for loading value of a __weak 2616/// object: objc_read_weak (id *src) 2617/// 2618llvm::Value * CGObjCMac::EmitObjCWeakRead(CodeGen::CodeGenFunction &CGF, 2619 llvm::Value *AddrWeakObj) 2620{ 2621 const llvm::Type* DestTy = 2622 cast<llvm::PointerType>(AddrWeakObj->getType())->getElementType(); 2623 AddrWeakObj = CGF.Builder.CreateBitCast(AddrWeakObj, ObjCTypes.PtrObjectPtrTy); 2624 llvm::Value *read_weak = CGF.Builder.CreateCall(ObjCTypes.getGcReadWeakFn(), 2625 AddrWeakObj, "weakread"); 2626 read_weak = CGF.Builder.CreateBitCast(read_weak, DestTy); 2627 return read_weak; 2628} 2629 2630/// EmitObjCWeakAssign - Code gen for assigning to a __weak object. 2631/// objc_assign_weak (id src, id *dst) 2632/// 2633void CGObjCMac::EmitObjCWeakAssign(CodeGen::CodeGenFunction &CGF, 2634 llvm::Value *src, llvm::Value *dst) 2635{ 2636 const llvm::Type * SrcTy = src->getType(); 2637 if (!isa<llvm::PointerType>(SrcTy)) { 2638 unsigned Size = CGM.getTargetData().getTypePaddedSize(SrcTy); 2639 assert(Size <= 8 && "does not support size > 8"); 2640 src = (Size == 4) ? CGF.Builder.CreateBitCast(src, ObjCTypes.IntTy) 2641 : CGF.Builder.CreateBitCast(src, ObjCTypes.LongLongTy); 2642 src = CGF.Builder.CreateIntToPtr(src, ObjCTypes.Int8PtrTy); 2643 } 2644 src = CGF.Builder.CreateBitCast(src, ObjCTypes.ObjectPtrTy); 2645 dst = CGF.Builder.CreateBitCast(dst, ObjCTypes.PtrObjectPtrTy); 2646 CGF.Builder.CreateCall2(ObjCTypes.getGcAssignWeakFn(), 2647 src, dst, "weakassign"); 2648 return; 2649} 2650 2651/// EmitObjCGlobalAssign - Code gen for assigning to a __strong object. 2652/// objc_assign_global (id src, id *dst) 2653/// 2654void CGObjCMac::EmitObjCGlobalAssign(CodeGen::CodeGenFunction &CGF, 2655 llvm::Value *src, llvm::Value *dst) 2656{ 2657 const llvm::Type * SrcTy = src->getType(); 2658 if (!isa<llvm::PointerType>(SrcTy)) { 2659 unsigned Size = CGM.getTargetData().getTypePaddedSize(SrcTy); 2660 assert(Size <= 8 && "does not support size > 8"); 2661 src = (Size == 4) ? CGF.Builder.CreateBitCast(src, ObjCTypes.IntTy) 2662 : CGF.Builder.CreateBitCast(src, ObjCTypes.LongLongTy); 2663 src = CGF.Builder.CreateIntToPtr(src, ObjCTypes.Int8PtrTy); 2664 } 2665 src = CGF.Builder.CreateBitCast(src, ObjCTypes.ObjectPtrTy); 2666 dst = CGF.Builder.CreateBitCast(dst, ObjCTypes.PtrObjectPtrTy); 2667 CGF.Builder.CreateCall2(ObjCTypes.getGcAssignGlobalFn(), 2668 src, dst, "globalassign"); 2669 return; 2670} 2671 2672/// EmitObjCIvarAssign - Code gen for assigning to a __strong object. 2673/// objc_assign_ivar (id src, id *dst) 2674/// 2675void CGObjCMac::EmitObjCIvarAssign(CodeGen::CodeGenFunction &CGF, 2676 llvm::Value *src, llvm::Value *dst) 2677{ 2678 const llvm::Type * SrcTy = src->getType(); 2679 if (!isa<llvm::PointerType>(SrcTy)) { 2680 unsigned Size = CGM.getTargetData().getTypePaddedSize(SrcTy); 2681 assert(Size <= 8 && "does not support size > 8"); 2682 src = (Size == 4) ? CGF.Builder.CreateBitCast(src, ObjCTypes.IntTy) 2683 : CGF.Builder.CreateBitCast(src, ObjCTypes.LongLongTy); 2684 src = CGF.Builder.CreateIntToPtr(src, ObjCTypes.Int8PtrTy); 2685 } 2686 src = CGF.Builder.CreateBitCast(src, ObjCTypes.ObjectPtrTy); 2687 dst = CGF.Builder.CreateBitCast(dst, ObjCTypes.PtrObjectPtrTy); 2688 CGF.Builder.CreateCall2(ObjCTypes.getGcAssignIvarFn(), 2689 src, dst, "assignivar"); 2690 return; 2691} 2692 2693/// EmitObjCStrongCastAssign - Code gen for assigning to a __strong cast object. 2694/// objc_assign_strongCast (id src, id *dst) 2695/// 2696void CGObjCMac::EmitObjCStrongCastAssign(CodeGen::CodeGenFunction &CGF, 2697 llvm::Value *src, llvm::Value *dst) 2698{ 2699 const llvm::Type * SrcTy = src->getType(); 2700 if (!isa<llvm::PointerType>(SrcTy)) { 2701 unsigned Size = CGM.getTargetData().getTypePaddedSize(SrcTy); 2702 assert(Size <= 8 && "does not support size > 8"); 2703 src = (Size == 4) ? CGF.Builder.CreateBitCast(src, ObjCTypes.IntTy) 2704 : CGF.Builder.CreateBitCast(src, ObjCTypes.LongLongTy); 2705 src = CGF.Builder.CreateIntToPtr(src, ObjCTypes.Int8PtrTy); 2706 } 2707 src = CGF.Builder.CreateBitCast(src, ObjCTypes.ObjectPtrTy); 2708 dst = CGF.Builder.CreateBitCast(dst, ObjCTypes.PtrObjectPtrTy); 2709 CGF.Builder.CreateCall2(ObjCTypes.getGcAssignStrongCastFn(), 2710 src, dst, "weakassign"); 2711 return; 2712} 2713 2714/// EmitObjCValueForIvar - Code Gen for ivar reference. 2715/// 2716LValue CGObjCMac::EmitObjCValueForIvar(CodeGen::CodeGenFunction &CGF, 2717 QualType ObjectTy, 2718 llvm::Value *BaseValue, 2719 const ObjCIvarDecl *Ivar, 2720 unsigned CVRQualifiers) { 2721 const ObjCInterfaceDecl *ID = ObjectTy->getAsObjCInterfaceType()->getDecl(); 2722 return EmitValueForIvarAtOffset(CGF, ID, BaseValue, Ivar, CVRQualifiers, 2723 EmitIvarOffset(CGF, ID, Ivar)); 2724} 2725 2726llvm::Value *CGObjCMac::EmitIvarOffset(CodeGen::CodeGenFunction &CGF, 2727 const ObjCInterfaceDecl *Interface, 2728 const ObjCIvarDecl *Ivar) { 2729 uint64_t Offset = ComputeIvarBaseOffset(CGM, Interface, Ivar); 2730 return llvm::ConstantInt::get( 2731 CGM.getTypes().ConvertType(CGM.getContext().LongTy), 2732 Offset); 2733} 2734 2735/* *** Private Interface *** */ 2736 2737/// EmitImageInfo - Emit the image info marker used to encode some module 2738/// level information. 2739/// 2740/// See: <rdr://4810609&4810587&4810587> 2741/// struct IMAGE_INFO { 2742/// unsigned version; 2743/// unsigned flags; 2744/// }; 2745enum ImageInfoFlags { 2746 eImageInfo_FixAndContinue = (1 << 0), // FIXME: Not sure what 2747 // this implies. 2748 eImageInfo_GarbageCollected = (1 << 1), 2749 eImageInfo_GCOnly = (1 << 2), 2750 eImageInfo_OptimizedByDyld = (1 << 3), // FIXME: When is this set. 2751 2752 // A flag indicating that the module has no instances of an 2753 // @synthesize of a superclass variable. <rdar://problem/6803242> 2754 eImageInfo_CorrectedSynthesize = (1 << 4) 2755}; 2756 2757void CGObjCMac::EmitImageInfo() { 2758 unsigned version = 0; // Version is unused? 2759 unsigned flags = 0; 2760 2761 // FIXME: Fix and continue? 2762 if (CGM.getLangOptions().getGCMode() != LangOptions::NonGC) 2763 flags |= eImageInfo_GarbageCollected; 2764 if (CGM.getLangOptions().getGCMode() == LangOptions::GCOnly) 2765 flags |= eImageInfo_GCOnly; 2766 2767 // We never allow @synthesize of a superclass property. 2768 flags |= eImageInfo_CorrectedSynthesize; 2769 2770 // Emitted as int[2]; 2771 llvm::Constant *values[2] = { 2772 llvm::ConstantInt::get(llvm::Type::Int32Ty, version), 2773 llvm::ConstantInt::get(llvm::Type::Int32Ty, flags) 2774 }; 2775 llvm::ArrayType *AT = llvm::ArrayType::get(llvm::Type::Int32Ty, 2); 2776 2777 const char *Section; 2778 if (ObjCABI == 1) 2779 Section = "__OBJC, __image_info,regular"; 2780 else 2781 Section = "__DATA, __objc_imageinfo, regular, no_dead_strip"; 2782 llvm::GlobalVariable *GV = 2783 CreateMetadataVar("\01L_OBJC_IMAGE_INFO", 2784 llvm::ConstantArray::get(AT, values, 2), 2785 Section, 2786 0, 2787 true); 2788 GV->setConstant(true); 2789} 2790 2791 2792// struct objc_module { 2793// unsigned long version; 2794// unsigned long size; 2795// const char *name; 2796// Symtab symtab; 2797// }; 2798 2799// FIXME: Get from somewhere 2800static const int ModuleVersion = 7; 2801 2802void CGObjCMac::EmitModuleInfo() { 2803 uint64_t Size = CGM.getTargetData().getTypePaddedSize(ObjCTypes.ModuleTy); 2804 2805 std::vector<llvm::Constant*> Values(4); 2806 Values[0] = llvm::ConstantInt::get(ObjCTypes.LongTy, ModuleVersion); 2807 Values[1] = llvm::ConstantInt::get(ObjCTypes.LongTy, Size); 2808 // This used to be the filename, now it is unused. <rdr://4327263> 2809 Values[2] = GetClassName(&CGM.getContext().Idents.get("")); 2810 Values[3] = EmitModuleSymbols(); 2811 CreateMetadataVar("\01L_OBJC_MODULES", 2812 llvm::ConstantStruct::get(ObjCTypes.ModuleTy, Values), 2813 "__OBJC,__module_info,regular,no_dead_strip", 2814 4, true); 2815} 2816 2817llvm::Constant *CGObjCMac::EmitModuleSymbols() { 2818 unsigned NumClasses = DefinedClasses.size(); 2819 unsigned NumCategories = DefinedCategories.size(); 2820 2821 // Return null if no symbols were defined. 2822 if (!NumClasses && !NumCategories) 2823 return llvm::Constant::getNullValue(ObjCTypes.SymtabPtrTy); 2824 2825 std::vector<llvm::Constant*> Values(5); 2826 Values[0] = llvm::ConstantInt::get(ObjCTypes.LongTy, 0); 2827 Values[1] = llvm::Constant::getNullValue(ObjCTypes.SelectorPtrTy); 2828 Values[2] = llvm::ConstantInt::get(ObjCTypes.ShortTy, NumClasses); 2829 Values[3] = llvm::ConstantInt::get(ObjCTypes.ShortTy, NumCategories); 2830 2831 // The runtime expects exactly the list of defined classes followed 2832 // by the list of defined categories, in a single array. 2833 std::vector<llvm::Constant*> Symbols(NumClasses + NumCategories); 2834 for (unsigned i=0; i<NumClasses; i++) 2835 Symbols[i] = llvm::ConstantExpr::getBitCast(DefinedClasses[i], 2836 ObjCTypes.Int8PtrTy); 2837 for (unsigned i=0; i<NumCategories; i++) 2838 Symbols[NumClasses + i] = 2839 llvm::ConstantExpr::getBitCast(DefinedCategories[i], 2840 ObjCTypes.Int8PtrTy); 2841 2842 Values[4] = 2843 llvm::ConstantArray::get(llvm::ArrayType::get(ObjCTypes.Int8PtrTy, 2844 NumClasses + NumCategories), 2845 Symbols); 2846 2847 llvm::Constant *Init = llvm::ConstantStruct::get(Values); 2848 2849 llvm::GlobalVariable *GV = 2850 CreateMetadataVar("\01L_OBJC_SYMBOLS", Init, 2851 "__OBJC,__symbols,regular,no_dead_strip", 2852 4, true); 2853 return llvm::ConstantExpr::getBitCast(GV, ObjCTypes.SymtabPtrTy); 2854} 2855 2856llvm::Value *CGObjCMac::EmitClassRef(CGBuilderTy &Builder, 2857 const ObjCInterfaceDecl *ID) { 2858 LazySymbols.insert(ID->getIdentifier()); 2859 2860 llvm::GlobalVariable *&Entry = ClassReferences[ID->getIdentifier()]; 2861 2862 if (!Entry) { 2863 llvm::Constant *Casted = 2864 llvm::ConstantExpr::getBitCast(GetClassName(ID->getIdentifier()), 2865 ObjCTypes.ClassPtrTy); 2866 Entry = 2867 CreateMetadataVar("\01L_OBJC_CLASS_REFERENCES_", Casted, 2868 "__OBJC,__cls_refs,literal_pointers,no_dead_strip", 2869 4, true); 2870 } 2871 2872 return Builder.CreateLoad(Entry, false, "tmp"); 2873} 2874 2875llvm::Value *CGObjCMac::EmitSelector(CGBuilderTy &Builder, Selector Sel) { 2876 llvm::GlobalVariable *&Entry = SelectorReferences[Sel]; 2877 2878 if (!Entry) { 2879 llvm::Constant *Casted = 2880 llvm::ConstantExpr::getBitCast(GetMethodVarName(Sel), 2881 ObjCTypes.SelectorPtrTy); 2882 Entry = 2883 CreateMetadataVar("\01L_OBJC_SELECTOR_REFERENCES_", Casted, 2884 "__OBJC,__message_refs,literal_pointers,no_dead_strip", 2885 4, true); 2886 } 2887 2888 return Builder.CreateLoad(Entry, false, "tmp"); 2889} 2890 2891llvm::Constant *CGObjCCommonMac::GetClassName(IdentifierInfo *Ident) { 2892 llvm::GlobalVariable *&Entry = ClassNames[Ident]; 2893 2894 if (!Entry) 2895 Entry = CreateMetadataVar("\01L_OBJC_CLASS_NAME_", 2896 llvm::ConstantArray::get(Ident->getName()), 2897 "__TEXT,__cstring,cstring_literals", 2898 1, true); 2899 2900 return getConstantGEP(Entry, 0, 0); 2901} 2902 2903/// GetIvarLayoutName - Returns a unique constant for the given 2904/// ivar layout bitmap. 2905llvm::Constant *CGObjCCommonMac::GetIvarLayoutName(IdentifierInfo *Ident, 2906 const ObjCCommonTypesHelper &ObjCTypes) { 2907 return llvm::Constant::getNullValue(ObjCTypes.Int8PtrTy); 2908} 2909 2910void CGObjCCommonMac::BuildAggrIvarLayout(const ObjCInterfaceDecl *OI, 2911 const llvm::StructLayout *Layout, 2912 const RecordDecl *RD, 2913 const llvm::SmallVectorImpl<FieldDecl*> &RecFields, 2914 unsigned int BytePos, bool ForStrongLayout, 2915 bool &HasUnion) { 2916 bool IsUnion = (RD && RD->isUnion()); 2917 uint64_t MaxUnionIvarSize = 0; 2918 uint64_t MaxSkippedUnionIvarSize = 0; 2919 FieldDecl *MaxField = 0; 2920 FieldDecl *MaxSkippedField = 0; 2921 FieldDecl *LastFieldBitfield = 0; 2922 2923 unsigned base = 0; 2924 if (RecFields.empty()) 2925 return; 2926 if (IsUnion) 2927 base = BytePos + GetFieldBaseOffset(OI, Layout, RecFields[0]); 2928 unsigned WordSizeInBits = CGM.getContext().Target.getPointerWidth(0); 2929 unsigned ByteSizeInBits = CGM.getContext().Target.getCharWidth(); 2930 2931 llvm::SmallVector<FieldDecl*, 16> TmpRecFields; 2932 2933 for (unsigned i = 0, e = RecFields.size(); i != e; ++i) { 2934 FieldDecl *Field = RecFields[i]; 2935 // Skip over unnamed or bitfields 2936 if (!Field->getIdentifier() || Field->isBitField()) { 2937 LastFieldBitfield = Field; 2938 continue; 2939 } 2940 LastFieldBitfield = 0; 2941 QualType FQT = Field->getType(); 2942 if (FQT->isRecordType() || FQT->isUnionType()) { 2943 if (FQT->isUnionType()) 2944 HasUnion = true; 2945 2946 const RecordType *RT = FQT->getAsRecordType(); 2947 const RecordDecl *RD = RT->getDecl(); 2948 // FIXME - Find a more efficient way of passing records down. 2949 TmpRecFields.append(RD->field_begin(CGM.getContext()), 2950 RD->field_end(CGM.getContext())); 2951 const llvm::Type *Ty = CGM.getTypes().ConvertType(FQT); 2952 const llvm::StructLayout *RecLayout = 2953 CGM.getTargetData().getStructLayout(cast<llvm::StructType>(Ty)); 2954 2955 BuildAggrIvarLayout(0, RecLayout, RD, TmpRecFields, 2956 BytePos + GetFieldBaseOffset(OI, Layout, Field), 2957 ForStrongLayout, HasUnion); 2958 TmpRecFields.clear(); 2959 continue; 2960 } 2961 2962 if (const ArrayType *Array = CGM.getContext().getAsArrayType(FQT)) { 2963 const ConstantArrayType *CArray = 2964 dyn_cast_or_null<ConstantArrayType>(Array); 2965 uint64_t ElCount = CArray->getSize().getZExtValue(); 2966 assert(CArray && "only array with know element size is supported"); 2967 FQT = CArray->getElementType(); 2968 while (const ArrayType *Array = CGM.getContext().getAsArrayType(FQT)) { 2969 const ConstantArrayType *CArray = 2970 dyn_cast_or_null<ConstantArrayType>(Array); 2971 ElCount *= CArray->getSize().getZExtValue(); 2972 FQT = CArray->getElementType(); 2973 } 2974 2975 assert(!FQT->isUnionType() && 2976 "layout for array of unions not supported"); 2977 if (FQT->isRecordType()) { 2978 int OldIndex = IvarsInfo.size() - 1; 2979 int OldSkIndex = SkipIvars.size() -1; 2980 2981 // FIXME - Use a common routine with the above! 2982 const RecordType *RT = FQT->getAsRecordType(); 2983 const RecordDecl *RD = RT->getDecl(); 2984 // FIXME - Find a more efficiant way of passing records down. 2985 TmpRecFields.append(RD->field_begin(CGM.getContext()), 2986 RD->field_end(CGM.getContext())); 2987 const llvm::Type *Ty = CGM.getTypes().ConvertType(FQT); 2988 const llvm::StructLayout *RecLayout = 2989 CGM.getTargetData().getStructLayout(cast<llvm::StructType>(Ty)); 2990 2991 BuildAggrIvarLayout(0, RecLayout, RD, 2992 TmpRecFields, 2993 BytePos + GetFieldBaseOffset(OI, Layout, Field), 2994 ForStrongLayout, HasUnion); 2995 TmpRecFields.clear(); 2996 2997 // Replicate layout information for each array element. Note that 2998 // one element is already done. 2999 uint64_t ElIx = 1; 3000 for (int FirstIndex = IvarsInfo.size() - 1, 3001 FirstSkIndex = SkipIvars.size() - 1 ;ElIx < ElCount; ElIx++) { 3002 uint64_t Size = CGM.getContext().getTypeSize(RT)/ByteSizeInBits; 3003 for (int i = OldIndex+1; i <= FirstIndex; ++i) 3004 IvarsInfo.push_back(GC_IVAR(IvarsInfo[i].ivar_bytepos + Size*ElIx, 3005 IvarsInfo[i].ivar_size)); 3006 for (int i = OldSkIndex+1; i <= FirstSkIndex; ++i) 3007 SkipIvars.push_back(GC_IVAR(SkipIvars[i].ivar_bytepos + Size*ElIx, 3008 SkipIvars[i].ivar_size)); 3009 } 3010 continue; 3011 } 3012 } 3013 // At this point, we are done with Record/Union and array there of. 3014 // For other arrays we are down to its element type. 3015 QualType::GCAttrTypes GCAttr = QualType::GCNone; 3016 do { 3017 if (FQT.isObjCGCStrong() || FQT.isObjCGCWeak()) { 3018 GCAttr = FQT.isObjCGCStrong() ? QualType::Strong : QualType::Weak; 3019 break; 3020 } else if (CGM.getContext().isObjCObjectPointerType(FQT)) { 3021 GCAttr = QualType::Strong; 3022 break; 3023 } else if (const PointerType *PT = FQT->getAsPointerType()) { 3024 FQT = PT->getPointeeType(); 3025 } else { 3026 break; 3027 } 3028 } while (true); 3029 3030 unsigned FieldSize = CGM.getContext().getTypeSize(Field->getType()); 3031 if ((ForStrongLayout && GCAttr == QualType::Strong) 3032 || (!ForStrongLayout && GCAttr == QualType::Weak)) { 3033 if (IsUnion) { 3034 uint64_t UnionIvarSize = FieldSize / WordSizeInBits; 3035 if (UnionIvarSize > MaxUnionIvarSize) { 3036 MaxUnionIvarSize = UnionIvarSize; 3037 MaxField = Field; 3038 } 3039 } else { 3040 IvarsInfo.push_back(GC_IVAR(BytePos + GetFieldBaseOffset(OI, Layout, 3041 Field), 3042 FieldSize / WordSizeInBits)); 3043 } 3044 } else if ((ForStrongLayout && 3045 (GCAttr == QualType::GCNone || GCAttr == QualType::Weak)) 3046 || (!ForStrongLayout && GCAttr != QualType::Weak)) { 3047 if (IsUnion) { 3048 // FIXME: Why the asymmetry? We divide by word size in bits on 3049 // other side. 3050 uint64_t UnionIvarSize = FieldSize; 3051 if (UnionIvarSize > MaxSkippedUnionIvarSize) { 3052 MaxSkippedUnionIvarSize = UnionIvarSize; 3053 MaxSkippedField = Field; 3054 } 3055 } else { 3056 // FIXME: Why the asymmetry, we divide by byte size in bits here? 3057 SkipIvars.push_back(GC_IVAR(BytePos + GetFieldBaseOffset(OI, Layout, 3058 Field), 3059 FieldSize / ByteSizeInBits)); 3060 } 3061 } 3062 } 3063 if (LastFieldBitfield) { 3064 // Last field was a bitfield. Must update skip info. 3065 Expr *BitWidth = LastFieldBitfield->getBitWidth(); 3066 uint64_t BitFieldSize = 3067 BitWidth->EvaluateAsInt(CGM.getContext()).getZExtValue(); 3068 GC_IVAR skivar; 3069 skivar.ivar_bytepos = BytePos + GetFieldBaseOffset(OI, Layout, 3070 LastFieldBitfield); 3071 skivar.ivar_size = (BitFieldSize / ByteSizeInBits) 3072 + ((BitFieldSize % ByteSizeInBits) != 0); 3073 SkipIvars.push_back(skivar); 3074 } 3075 3076 if (MaxField) 3077 IvarsInfo.push_back(GC_IVAR(BytePos + GetFieldBaseOffset(OI, Layout, 3078 MaxField), 3079 MaxUnionIvarSize)); 3080 if (MaxSkippedField) 3081 SkipIvars.push_back(GC_IVAR(BytePos + GetFieldBaseOffset(OI, Layout, 3082 MaxSkippedField), 3083 MaxSkippedUnionIvarSize)); 3084} 3085 3086/// BuildIvarLayout - Builds ivar layout bitmap for the class 3087/// implementation for the __strong or __weak case. 3088/// The layout map displays which words in ivar list must be skipped 3089/// and which must be scanned by GC (see below). String is built of bytes. 3090/// Each byte is divided up in two nibbles (4-bit each). Left nibble is count 3091/// of words to skip and right nibble is count of words to scan. So, each 3092/// nibble represents up to 15 workds to skip or scan. Skipping the rest is 3093/// represented by a 0x00 byte which also ends the string. 3094/// 1. when ForStrongLayout is true, following ivars are scanned: 3095/// - id, Class 3096/// - object * 3097/// - __strong anything 3098/// 3099/// 2. When ForStrongLayout is false, following ivars are scanned: 3100/// - __weak anything 3101/// 3102llvm::Constant *CGObjCCommonMac::BuildIvarLayout( 3103 const ObjCImplementationDecl *OMD, 3104 bool ForStrongLayout) { 3105 bool hasUnion = false; 3106 3107 unsigned int WordsToScan, WordsToSkip; 3108 const llvm::Type *PtrTy = llvm::PointerType::getUnqual(llvm::Type::Int8Ty); 3109 if (CGM.getLangOptions().getGCMode() == LangOptions::NonGC) 3110 return llvm::Constant::getNullValue(PtrTy); 3111 3112 llvm::SmallVector<FieldDecl*, 32> RecFields; 3113 const ObjCInterfaceDecl *OI = OMD->getClassInterface(); 3114 CGM.getContext().CollectObjCIvars(OI, RecFields); 3115 if (RecFields.empty()) 3116 return llvm::Constant::getNullValue(PtrTy); 3117 3118 SkipIvars.clear(); 3119 IvarsInfo.clear(); 3120 3121 const llvm::StructLayout *Layout = 3122 CGM.getTargetData().getStructLayout(GetConcreteClassStruct(CGM, OI)); 3123 BuildAggrIvarLayout(OI, Layout, 0, RecFields, 0, ForStrongLayout, hasUnion); 3124 if (IvarsInfo.empty()) 3125 return llvm::Constant::getNullValue(PtrTy); 3126 3127 // Sort on byte position in case we encounterred a union nested in 3128 // the ivar list. 3129 if (hasUnion && !IvarsInfo.empty()) 3130 std::sort(IvarsInfo.begin(), IvarsInfo.end()); 3131 if (hasUnion && !SkipIvars.empty()) 3132 std::sort(SkipIvars.begin(), SkipIvars.end()); 3133 3134 // Build the string of skip/scan nibbles 3135 llvm::SmallVector<SKIP_SCAN, 32> SkipScanIvars; 3136 unsigned int WordSize = 3137 CGM.getTypes().getTargetData().getTypePaddedSize(PtrTy); 3138 if (IvarsInfo[0].ivar_bytepos == 0) { 3139 WordsToSkip = 0; 3140 WordsToScan = IvarsInfo[0].ivar_size; 3141 } 3142 else { 3143 WordsToSkip = IvarsInfo[0].ivar_bytepos/WordSize; 3144 WordsToScan = IvarsInfo[0].ivar_size; 3145 } 3146 for (unsigned int i=1, Last=IvarsInfo.size(); i != Last; i++) 3147 { 3148 unsigned int TailPrevGCObjC = 3149 IvarsInfo[i-1].ivar_bytepos + IvarsInfo[i-1].ivar_size * WordSize; 3150 if (IvarsInfo[i].ivar_bytepos == TailPrevGCObjC) 3151 { 3152 // consecutive 'scanned' object pointers. 3153 WordsToScan += IvarsInfo[i].ivar_size; 3154 } 3155 else 3156 { 3157 // Skip over 'gc'able object pointer which lay over each other. 3158 if (TailPrevGCObjC > IvarsInfo[i].ivar_bytepos) 3159 continue; 3160 // Must skip over 1 or more words. We save current skip/scan values 3161 // and start a new pair. 3162 SKIP_SCAN SkScan; 3163 SkScan.skip = WordsToSkip; 3164 SkScan.scan = WordsToScan; 3165 SkipScanIvars.push_back(SkScan); 3166 3167 // Skip the hole. 3168 SkScan.skip = (IvarsInfo[i].ivar_bytepos - TailPrevGCObjC) / WordSize; 3169 SkScan.scan = 0; 3170 SkipScanIvars.push_back(SkScan); 3171 WordsToSkip = 0; 3172 WordsToScan = IvarsInfo[i].ivar_size; 3173 } 3174 } 3175 if (WordsToScan > 0) 3176 { 3177 SKIP_SCAN SkScan; 3178 SkScan.skip = WordsToSkip; 3179 SkScan.scan = WordsToScan; 3180 SkipScanIvars.push_back(SkScan); 3181 } 3182 3183 bool BytesSkipped = false; 3184 if (!SkipIvars.empty()) 3185 { 3186 unsigned int LastIndex = SkipIvars.size()-1; 3187 int LastByteSkipped = 3188 SkipIvars[LastIndex].ivar_bytepos + SkipIvars[LastIndex].ivar_size; 3189 LastIndex = IvarsInfo.size()-1; 3190 int LastByteScanned = 3191 IvarsInfo[LastIndex].ivar_bytepos + 3192 IvarsInfo[LastIndex].ivar_size * WordSize; 3193 BytesSkipped = (LastByteSkipped > LastByteScanned); 3194 // Compute number of bytes to skip at the tail end of the last ivar scanned. 3195 if (BytesSkipped) 3196 { 3197 unsigned int TotalWords = (LastByteSkipped + (WordSize -1)) / WordSize; 3198 SKIP_SCAN SkScan; 3199 SkScan.skip = TotalWords - (LastByteScanned/WordSize); 3200 SkScan.scan = 0; 3201 SkipScanIvars.push_back(SkScan); 3202 } 3203 } 3204 // Mini optimization of nibbles such that an 0xM0 followed by 0x0N is produced 3205 // as 0xMN. 3206 int SkipScan = SkipScanIvars.size()-1; 3207 for (int i = 0; i <= SkipScan; i++) 3208 { 3209 if ((i < SkipScan) && SkipScanIvars[i].skip && SkipScanIvars[i].scan == 0 3210 && SkipScanIvars[i+1].skip == 0 && SkipScanIvars[i+1].scan) { 3211 // 0xM0 followed by 0x0N detected. 3212 SkipScanIvars[i].scan = SkipScanIvars[i+1].scan; 3213 for (int j = i+1; j < SkipScan; j++) 3214 SkipScanIvars[j] = SkipScanIvars[j+1]; 3215 --SkipScan; 3216 } 3217 } 3218 3219 // Generate the string. 3220 std::string BitMap; 3221 for (int i = 0; i <= SkipScan; i++) 3222 { 3223 unsigned char byte; 3224 unsigned int skip_small = SkipScanIvars[i].skip % 0xf; 3225 unsigned int scan_small = SkipScanIvars[i].scan % 0xf; 3226 unsigned int skip_big = SkipScanIvars[i].skip / 0xf; 3227 unsigned int scan_big = SkipScanIvars[i].scan / 0xf; 3228 3229 if (skip_small > 0 || skip_big > 0) 3230 BytesSkipped = true; 3231 // first skip big. 3232 for (unsigned int ix = 0; ix < skip_big; ix++) 3233 BitMap += (unsigned char)(0xf0); 3234 3235 // next (skip small, scan) 3236 if (skip_small) 3237 { 3238 byte = skip_small << 4; 3239 if (scan_big > 0) 3240 { 3241 byte |= 0xf; 3242 --scan_big; 3243 } 3244 else if (scan_small) 3245 { 3246 byte |= scan_small; 3247 scan_small = 0; 3248 } 3249 BitMap += byte; 3250 } 3251 // next scan big 3252 for (unsigned int ix = 0; ix < scan_big; ix++) 3253 BitMap += (unsigned char)(0x0f); 3254 // last scan small 3255 if (scan_small) 3256 { 3257 byte = scan_small; 3258 BitMap += byte; 3259 } 3260 } 3261 // null terminate string. 3262 unsigned char zero = 0; 3263 BitMap += zero; 3264 3265 if (CGM.getLangOptions().ObjCGCBitmapPrint) { 3266 printf("\n%s ivar layout for class '%s': ", 3267 ForStrongLayout ? "strong" : "weak", 3268 OMD->getClassInterface()->getNameAsCString()); 3269 const unsigned char *s = (unsigned char*)BitMap.c_str(); 3270 for (unsigned i = 0; i < BitMap.size(); i++) 3271 if (!(s[i] & 0xf0)) 3272 printf("0x0%x%s", s[i], s[i] != 0 ? ", " : ""); 3273 else 3274 printf("0x%x%s", s[i], s[i] != 0 ? ", " : ""); 3275 printf("\n"); 3276 } 3277 3278 // if ivar_layout bitmap is all 1 bits (nothing skipped) then use NULL as 3279 // final layout. 3280 if (ForStrongLayout && !BytesSkipped) 3281 return llvm::Constant::getNullValue(PtrTy); 3282 llvm::GlobalVariable * Entry = CreateMetadataVar("\01L_OBJC_CLASS_NAME_", 3283 llvm::ConstantArray::get(BitMap.c_str()), 3284 "__TEXT,__cstring,cstring_literals", 3285 1, true); 3286 return getConstantGEP(Entry, 0, 0); 3287} 3288 3289llvm::Constant *CGObjCCommonMac::GetMethodVarName(Selector Sel) { 3290 llvm::GlobalVariable *&Entry = MethodVarNames[Sel]; 3291 3292 // FIXME: Avoid std::string copying. 3293 if (!Entry) 3294 Entry = CreateMetadataVar("\01L_OBJC_METH_VAR_NAME_", 3295 llvm::ConstantArray::get(Sel.getAsString()), 3296 "__TEXT,__cstring,cstring_literals", 3297 1, true); 3298 3299 return getConstantGEP(Entry, 0, 0); 3300} 3301 3302// FIXME: Merge into a single cstring creation function. 3303llvm::Constant *CGObjCCommonMac::GetMethodVarName(IdentifierInfo *ID) { 3304 return GetMethodVarName(CGM.getContext().Selectors.getNullarySelector(ID)); 3305} 3306 3307// FIXME: Merge into a single cstring creation function. 3308llvm::Constant *CGObjCCommonMac::GetMethodVarName(const std::string &Name) { 3309 return GetMethodVarName(&CGM.getContext().Idents.get(Name)); 3310} 3311 3312llvm::Constant *CGObjCCommonMac::GetMethodVarType(const FieldDecl *Field) { 3313 std::string TypeStr; 3314 CGM.getContext().getObjCEncodingForType(Field->getType(), TypeStr, Field); 3315 3316 llvm::GlobalVariable *&Entry = MethodVarTypes[TypeStr]; 3317 3318 if (!Entry) 3319 Entry = CreateMetadataVar("\01L_OBJC_METH_VAR_TYPE_", 3320 llvm::ConstantArray::get(TypeStr), 3321 "__TEXT,__cstring,cstring_literals", 3322 1, true); 3323 3324 return getConstantGEP(Entry, 0, 0); 3325} 3326 3327llvm::Constant *CGObjCCommonMac::GetMethodVarType(const ObjCMethodDecl *D) { 3328 std::string TypeStr; 3329 CGM.getContext().getObjCEncodingForMethodDecl(const_cast<ObjCMethodDecl*>(D), 3330 TypeStr); 3331 3332 llvm::GlobalVariable *&Entry = MethodVarTypes[TypeStr]; 3333 3334 if (!Entry) 3335 Entry = CreateMetadataVar("\01L_OBJC_METH_VAR_TYPE_", 3336 llvm::ConstantArray::get(TypeStr), 3337 "__TEXT,__cstring,cstring_literals", 3338 1, true); 3339 3340 return getConstantGEP(Entry, 0, 0); 3341} 3342 3343// FIXME: Merge into a single cstring creation function. 3344llvm::Constant *CGObjCCommonMac::GetPropertyName(IdentifierInfo *Ident) { 3345 llvm::GlobalVariable *&Entry = PropertyNames[Ident]; 3346 3347 if (!Entry) 3348 Entry = CreateMetadataVar("\01L_OBJC_PROP_NAME_ATTR_", 3349 llvm::ConstantArray::get(Ident->getName()), 3350 "__TEXT,__cstring,cstring_literals", 3351 1, true); 3352 3353 return getConstantGEP(Entry, 0, 0); 3354} 3355 3356// FIXME: Merge into a single cstring creation function. 3357// FIXME: This Decl should be more precise. 3358llvm::Constant * 3359 CGObjCCommonMac::GetPropertyTypeString(const ObjCPropertyDecl *PD, 3360 const Decl *Container) { 3361 std::string TypeStr; 3362 CGM.getContext().getObjCEncodingForPropertyDecl(PD, Container, TypeStr); 3363 return GetPropertyName(&CGM.getContext().Idents.get(TypeStr)); 3364} 3365 3366void CGObjCCommonMac::GetNameForMethod(const ObjCMethodDecl *D, 3367 const ObjCContainerDecl *CD, 3368 std::string &NameOut) { 3369 NameOut = '\01'; 3370 NameOut += (D->isInstanceMethod() ? '-' : '+'); 3371 NameOut += '['; 3372 assert (CD && "Missing container decl in GetNameForMethod"); 3373 NameOut += CD->getNameAsString(); 3374 if (const ObjCCategoryImplDecl *CID = 3375 dyn_cast<ObjCCategoryImplDecl>(D->getDeclContext())) { 3376 NameOut += '('; 3377 NameOut += CID->getNameAsString(); 3378 NameOut+= ')'; 3379 } 3380 NameOut += ' '; 3381 NameOut += D->getSelector().getAsString(); 3382 NameOut += ']'; 3383} 3384 3385void CGObjCMac::FinishModule() { 3386 EmitModuleInfo(); 3387 3388 // Emit the dummy bodies for any protocols which were referenced but 3389 // never defined. 3390 for (llvm::DenseMap<IdentifierInfo*, llvm::GlobalVariable*>::iterator 3391 i = Protocols.begin(), e = Protocols.end(); i != e; ++i) { 3392 if (i->second->hasInitializer()) 3393 continue; 3394 3395 std::vector<llvm::Constant*> Values(5); 3396 Values[0] = llvm::Constant::getNullValue(ObjCTypes.ProtocolExtensionPtrTy); 3397 Values[1] = GetClassName(i->first); 3398 Values[2] = llvm::Constant::getNullValue(ObjCTypes.ProtocolListPtrTy); 3399 Values[3] = Values[4] = 3400 llvm::Constant::getNullValue(ObjCTypes.MethodDescriptionListPtrTy); 3401 i->second->setLinkage(llvm::GlobalValue::InternalLinkage); 3402 i->second->setInitializer(llvm::ConstantStruct::get(ObjCTypes.ProtocolTy, 3403 Values)); 3404 } 3405 3406 std::vector<llvm::Constant*> Used; 3407 for (std::vector<llvm::GlobalVariable*>::iterator i = UsedGlobals.begin(), 3408 e = UsedGlobals.end(); i != e; ++i) { 3409 Used.push_back(llvm::ConstantExpr::getBitCast(*i, ObjCTypes.Int8PtrTy)); 3410 } 3411 3412 llvm::ArrayType *AT = llvm::ArrayType::get(ObjCTypes.Int8PtrTy, Used.size()); 3413 llvm::GlobalValue *GV = 3414 new llvm::GlobalVariable(AT, false, 3415 llvm::GlobalValue::AppendingLinkage, 3416 llvm::ConstantArray::get(AT, Used), 3417 "llvm.used", 3418 &CGM.getModule()); 3419 3420 GV->setSection("llvm.metadata"); 3421 3422 // Add assembler directives to add lazy undefined symbol references 3423 // for classes which are referenced but not defined. This is 3424 // important for correct linker interaction. 3425 3426 // FIXME: Uh, this isn't particularly portable. 3427 std::stringstream s; 3428 3429 if (!CGM.getModule().getModuleInlineAsm().empty()) 3430 s << "\n"; 3431 3432 for (std::set<IdentifierInfo*>::iterator i = LazySymbols.begin(), 3433 e = LazySymbols.end(); i != e; ++i) { 3434 s << "\t.lazy_reference .objc_class_name_" << (*i)->getName() << "\n"; 3435 } 3436 for (std::set<IdentifierInfo*>::iterator i = DefinedSymbols.begin(), 3437 e = DefinedSymbols.end(); i != e; ++i) { 3438 s << "\t.objc_class_name_" << (*i)->getName() << "=0\n" 3439 << "\t.globl .objc_class_name_" << (*i)->getName() << "\n"; 3440 } 3441 3442 CGM.getModule().appendModuleInlineAsm(s.str()); 3443} 3444 3445CGObjCNonFragileABIMac::CGObjCNonFragileABIMac(CodeGen::CodeGenModule &cgm) 3446 : CGObjCCommonMac(cgm), 3447 ObjCTypes(cgm) 3448{ 3449 ObjCEmptyCacheVar = ObjCEmptyVtableVar = NULL; 3450 ObjCABI = 2; 3451} 3452 3453/* *** */ 3454 3455ObjCCommonTypesHelper::ObjCCommonTypesHelper(CodeGen::CodeGenModule &cgm) 3456: CGM(cgm) 3457{ 3458 CodeGen::CodeGenTypes &Types = CGM.getTypes(); 3459 ASTContext &Ctx = CGM.getContext(); 3460 3461 ShortTy = Types.ConvertType(Ctx.ShortTy); 3462 IntTy = Types.ConvertType(Ctx.IntTy); 3463 LongTy = Types.ConvertType(Ctx.LongTy); 3464 LongLongTy = Types.ConvertType(Ctx.LongLongTy); 3465 Int8PtrTy = llvm::PointerType::getUnqual(llvm::Type::Int8Ty); 3466 3467 ObjectPtrTy = Types.ConvertType(Ctx.getObjCIdType()); 3468 PtrObjectPtrTy = llvm::PointerType::getUnqual(ObjectPtrTy); 3469 SelectorPtrTy = Types.ConvertType(Ctx.getObjCSelType()); 3470 3471 // FIXME: It would be nice to unify this with the opaque type, so 3472 // that the IR comes out a bit cleaner. 3473 const llvm::Type *T = Types.ConvertType(Ctx.getObjCProtoType()); 3474 ExternalProtocolPtrTy = llvm::PointerType::getUnqual(T); 3475 3476 // I'm not sure I like this. The implicit coordination is a bit 3477 // gross. We should solve this in a reasonable fashion because this 3478 // is a pretty common task (match some runtime data structure with 3479 // an LLVM data structure). 3480 3481 // FIXME: This is leaked. 3482 // FIXME: Merge with rewriter code? 3483 3484 // struct _objc_super { 3485 // id self; 3486 // Class cls; 3487 // } 3488 RecordDecl *RD = RecordDecl::Create(Ctx, TagDecl::TK_struct, 0, 3489 SourceLocation(), 3490 &Ctx.Idents.get("_objc_super")); 3491 RD->addDecl(Ctx, FieldDecl::Create(Ctx, RD, SourceLocation(), 0, 3492 Ctx.getObjCIdType(), 0, false)); 3493 RD->addDecl(Ctx, FieldDecl::Create(Ctx, RD, SourceLocation(), 0, 3494 Ctx.getObjCClassType(), 0, false)); 3495 RD->completeDefinition(Ctx); 3496 3497 SuperCTy = Ctx.getTagDeclType(RD); 3498 SuperPtrCTy = Ctx.getPointerType(SuperCTy); 3499 3500 SuperTy = cast<llvm::StructType>(Types.ConvertType(SuperCTy)); 3501 SuperPtrTy = llvm::PointerType::getUnqual(SuperTy); 3502 3503 // struct _prop_t { 3504 // char *name; 3505 // char *attributes; 3506 // } 3507 PropertyTy = llvm::StructType::get(Int8PtrTy, Int8PtrTy, NULL); 3508 CGM.getModule().addTypeName("struct._prop_t", 3509 PropertyTy); 3510 3511 // struct _prop_list_t { 3512 // uint32_t entsize; // sizeof(struct _prop_t) 3513 // uint32_t count_of_properties; 3514 // struct _prop_t prop_list[count_of_properties]; 3515 // } 3516 PropertyListTy = llvm::StructType::get(IntTy, 3517 IntTy, 3518 llvm::ArrayType::get(PropertyTy, 0), 3519 NULL); 3520 CGM.getModule().addTypeName("struct._prop_list_t", 3521 PropertyListTy); 3522 // struct _prop_list_t * 3523 PropertyListPtrTy = llvm::PointerType::getUnqual(PropertyListTy); 3524 3525 // struct _objc_method { 3526 // SEL _cmd; 3527 // char *method_type; 3528 // char *_imp; 3529 // } 3530 MethodTy = llvm::StructType::get(SelectorPtrTy, 3531 Int8PtrTy, 3532 Int8PtrTy, 3533 NULL); 3534 CGM.getModule().addTypeName("struct._objc_method", MethodTy); 3535 3536 // struct _objc_cache * 3537 CacheTy = llvm::OpaqueType::get(); 3538 CGM.getModule().addTypeName("struct._objc_cache", CacheTy); 3539 CachePtrTy = llvm::PointerType::getUnqual(CacheTy); 3540} 3541 3542ObjCTypesHelper::ObjCTypesHelper(CodeGen::CodeGenModule &cgm) 3543 : ObjCCommonTypesHelper(cgm) 3544{ 3545 // struct _objc_method_description { 3546 // SEL name; 3547 // char *types; 3548 // } 3549 MethodDescriptionTy = 3550 llvm::StructType::get(SelectorPtrTy, 3551 Int8PtrTy, 3552 NULL); 3553 CGM.getModule().addTypeName("struct._objc_method_description", 3554 MethodDescriptionTy); 3555 3556 // struct _objc_method_description_list { 3557 // int count; 3558 // struct _objc_method_description[1]; 3559 // } 3560 MethodDescriptionListTy = 3561 llvm::StructType::get(IntTy, 3562 llvm::ArrayType::get(MethodDescriptionTy, 0), 3563 NULL); 3564 CGM.getModule().addTypeName("struct._objc_method_description_list", 3565 MethodDescriptionListTy); 3566 3567 // struct _objc_method_description_list * 3568 MethodDescriptionListPtrTy = 3569 llvm::PointerType::getUnqual(MethodDescriptionListTy); 3570 3571 // Protocol description structures 3572 3573 // struct _objc_protocol_extension { 3574 // uint32_t size; // sizeof(struct _objc_protocol_extension) 3575 // struct _objc_method_description_list *optional_instance_methods; 3576 // struct _objc_method_description_list *optional_class_methods; 3577 // struct _objc_property_list *instance_properties; 3578 // } 3579 ProtocolExtensionTy = 3580 llvm::StructType::get(IntTy, 3581 MethodDescriptionListPtrTy, 3582 MethodDescriptionListPtrTy, 3583 PropertyListPtrTy, 3584 NULL); 3585 CGM.getModule().addTypeName("struct._objc_protocol_extension", 3586 ProtocolExtensionTy); 3587 3588 // struct _objc_protocol_extension * 3589 ProtocolExtensionPtrTy = llvm::PointerType::getUnqual(ProtocolExtensionTy); 3590 3591 // Handle recursive construction of Protocol and ProtocolList types 3592 3593 llvm::PATypeHolder ProtocolTyHolder = llvm::OpaqueType::get(); 3594 llvm::PATypeHolder ProtocolListTyHolder = llvm::OpaqueType::get(); 3595 3596 const llvm::Type *T = 3597 llvm::StructType::get(llvm::PointerType::getUnqual(ProtocolListTyHolder), 3598 LongTy, 3599 llvm::ArrayType::get(ProtocolTyHolder, 0), 3600 NULL); 3601 cast<llvm::OpaqueType>(ProtocolListTyHolder.get())->refineAbstractTypeTo(T); 3602 3603 // struct _objc_protocol { 3604 // struct _objc_protocol_extension *isa; 3605 // char *protocol_name; 3606 // struct _objc_protocol **_objc_protocol_list; 3607 // struct _objc_method_description_list *instance_methods; 3608 // struct _objc_method_description_list *class_methods; 3609 // } 3610 T = llvm::StructType::get(ProtocolExtensionPtrTy, 3611 Int8PtrTy, 3612 llvm::PointerType::getUnqual(ProtocolListTyHolder), 3613 MethodDescriptionListPtrTy, 3614 MethodDescriptionListPtrTy, 3615 NULL); 3616 cast<llvm::OpaqueType>(ProtocolTyHolder.get())->refineAbstractTypeTo(T); 3617 3618 ProtocolListTy = cast<llvm::StructType>(ProtocolListTyHolder.get()); 3619 CGM.getModule().addTypeName("struct._objc_protocol_list", 3620 ProtocolListTy); 3621 // struct _objc_protocol_list * 3622 ProtocolListPtrTy = llvm::PointerType::getUnqual(ProtocolListTy); 3623 3624 ProtocolTy = cast<llvm::StructType>(ProtocolTyHolder.get()); 3625 CGM.getModule().addTypeName("struct._objc_protocol", ProtocolTy); 3626 ProtocolPtrTy = llvm::PointerType::getUnqual(ProtocolTy); 3627 3628 // Class description structures 3629 3630 // struct _objc_ivar { 3631 // char *ivar_name; 3632 // char *ivar_type; 3633 // int ivar_offset; 3634 // } 3635 IvarTy = llvm::StructType::get(Int8PtrTy, 3636 Int8PtrTy, 3637 IntTy, 3638 NULL); 3639 CGM.getModule().addTypeName("struct._objc_ivar", IvarTy); 3640 3641 // struct _objc_ivar_list * 3642 IvarListTy = llvm::OpaqueType::get(); 3643 CGM.getModule().addTypeName("struct._objc_ivar_list", IvarListTy); 3644 IvarListPtrTy = llvm::PointerType::getUnqual(IvarListTy); 3645 3646 // struct _objc_method_list * 3647 MethodListTy = llvm::OpaqueType::get(); 3648 CGM.getModule().addTypeName("struct._objc_method_list", MethodListTy); 3649 MethodListPtrTy = llvm::PointerType::getUnqual(MethodListTy); 3650 3651 // struct _objc_class_extension * 3652 ClassExtensionTy = 3653 llvm::StructType::get(IntTy, 3654 Int8PtrTy, 3655 PropertyListPtrTy, 3656 NULL); 3657 CGM.getModule().addTypeName("struct._objc_class_extension", ClassExtensionTy); 3658 ClassExtensionPtrTy = llvm::PointerType::getUnqual(ClassExtensionTy); 3659 3660 llvm::PATypeHolder ClassTyHolder = llvm::OpaqueType::get(); 3661 3662 // struct _objc_class { 3663 // Class isa; 3664 // Class super_class; 3665 // char *name; 3666 // long version; 3667 // long info; 3668 // long instance_size; 3669 // struct _objc_ivar_list *ivars; 3670 // struct _objc_method_list *methods; 3671 // struct _objc_cache *cache; 3672 // struct _objc_protocol_list *protocols; 3673 // char *ivar_layout; 3674 // struct _objc_class_ext *ext; 3675 // }; 3676 T = llvm::StructType::get(llvm::PointerType::getUnqual(ClassTyHolder), 3677 llvm::PointerType::getUnqual(ClassTyHolder), 3678 Int8PtrTy, 3679 LongTy, 3680 LongTy, 3681 LongTy, 3682 IvarListPtrTy, 3683 MethodListPtrTy, 3684 CachePtrTy, 3685 ProtocolListPtrTy, 3686 Int8PtrTy, 3687 ClassExtensionPtrTy, 3688 NULL); 3689 cast<llvm::OpaqueType>(ClassTyHolder.get())->refineAbstractTypeTo(T); 3690 3691 ClassTy = cast<llvm::StructType>(ClassTyHolder.get()); 3692 CGM.getModule().addTypeName("struct._objc_class", ClassTy); 3693 ClassPtrTy = llvm::PointerType::getUnqual(ClassTy); 3694 3695 // struct _objc_category { 3696 // char *category_name; 3697 // char *class_name; 3698 // struct _objc_method_list *instance_method; 3699 // struct _objc_method_list *class_method; 3700 // uint32_t size; // sizeof(struct _objc_category) 3701 // struct _objc_property_list *instance_properties;// category's @property 3702 // } 3703 CategoryTy = llvm::StructType::get(Int8PtrTy, 3704 Int8PtrTy, 3705 MethodListPtrTy, 3706 MethodListPtrTy, 3707 ProtocolListPtrTy, 3708 IntTy, 3709 PropertyListPtrTy, 3710 NULL); 3711 CGM.getModule().addTypeName("struct._objc_category", CategoryTy); 3712 3713 // Global metadata structures 3714 3715 // struct _objc_symtab { 3716 // long sel_ref_cnt; 3717 // SEL *refs; 3718 // short cls_def_cnt; 3719 // short cat_def_cnt; 3720 // char *defs[cls_def_cnt + cat_def_cnt]; 3721 // } 3722 SymtabTy = llvm::StructType::get(LongTy, 3723 SelectorPtrTy, 3724 ShortTy, 3725 ShortTy, 3726 llvm::ArrayType::get(Int8PtrTy, 0), 3727 NULL); 3728 CGM.getModule().addTypeName("struct._objc_symtab", SymtabTy); 3729 SymtabPtrTy = llvm::PointerType::getUnqual(SymtabTy); 3730 3731 // struct _objc_module { 3732 // long version; 3733 // long size; // sizeof(struct _objc_module) 3734 // char *name; 3735 // struct _objc_symtab* symtab; 3736 // } 3737 ModuleTy = 3738 llvm::StructType::get(LongTy, 3739 LongTy, 3740 Int8PtrTy, 3741 SymtabPtrTy, 3742 NULL); 3743 CGM.getModule().addTypeName("struct._objc_module", ModuleTy); 3744 3745 3746 // FIXME: This is the size of the setjmp buffer and should be 3747 // target specific. 18 is what's used on 32-bit X86. 3748 uint64_t SetJmpBufferSize = 18; 3749 3750 // Exceptions 3751 const llvm::Type *StackPtrTy = 3752 llvm::ArrayType::get(llvm::PointerType::getUnqual(llvm::Type::Int8Ty), 4); 3753 3754 ExceptionDataTy = 3755 llvm::StructType::get(llvm::ArrayType::get(llvm::Type::Int32Ty, 3756 SetJmpBufferSize), 3757 StackPtrTy, NULL); 3758 CGM.getModule().addTypeName("struct._objc_exception_data", 3759 ExceptionDataTy); 3760 3761} 3762 3763ObjCNonFragileABITypesHelper::ObjCNonFragileABITypesHelper(CodeGen::CodeGenModule &cgm) 3764: ObjCCommonTypesHelper(cgm) 3765{ 3766 // struct _method_list_t { 3767 // uint32_t entsize; // sizeof(struct _objc_method) 3768 // uint32_t method_count; 3769 // struct _objc_method method_list[method_count]; 3770 // } 3771 MethodListnfABITy = llvm::StructType::get(IntTy, 3772 IntTy, 3773 llvm::ArrayType::get(MethodTy, 0), 3774 NULL); 3775 CGM.getModule().addTypeName("struct.__method_list_t", 3776 MethodListnfABITy); 3777 // struct method_list_t * 3778 MethodListnfABIPtrTy = llvm::PointerType::getUnqual(MethodListnfABITy); 3779 3780 // struct _protocol_t { 3781 // id isa; // NULL 3782 // const char * const protocol_name; 3783 // const struct _protocol_list_t * protocol_list; // super protocols 3784 // const struct method_list_t * const instance_methods; 3785 // const struct method_list_t * const class_methods; 3786 // const struct method_list_t *optionalInstanceMethods; 3787 // const struct method_list_t *optionalClassMethods; 3788 // const struct _prop_list_t * properties; 3789 // const uint32_t size; // sizeof(struct _protocol_t) 3790 // const uint32_t flags; // = 0 3791 // } 3792 3793 // Holder for struct _protocol_list_t * 3794 llvm::PATypeHolder ProtocolListTyHolder = llvm::OpaqueType::get(); 3795 3796 ProtocolnfABITy = llvm::StructType::get(ObjectPtrTy, 3797 Int8PtrTy, 3798 llvm::PointerType::getUnqual( 3799 ProtocolListTyHolder), 3800 MethodListnfABIPtrTy, 3801 MethodListnfABIPtrTy, 3802 MethodListnfABIPtrTy, 3803 MethodListnfABIPtrTy, 3804 PropertyListPtrTy, 3805 IntTy, 3806 IntTy, 3807 NULL); 3808 CGM.getModule().addTypeName("struct._protocol_t", 3809 ProtocolnfABITy); 3810 3811 // struct _protocol_t* 3812 ProtocolnfABIPtrTy = llvm::PointerType::getUnqual(ProtocolnfABITy); 3813 3814 // struct _protocol_list_t { 3815 // long protocol_count; // Note, this is 32/64 bit 3816 // struct _protocol_t *[protocol_count]; 3817 // } 3818 ProtocolListnfABITy = llvm::StructType::get(LongTy, 3819 llvm::ArrayType::get( 3820 ProtocolnfABIPtrTy, 0), 3821 NULL); 3822 CGM.getModule().addTypeName("struct._objc_protocol_list", 3823 ProtocolListnfABITy); 3824 cast<llvm::OpaqueType>(ProtocolListTyHolder.get())->refineAbstractTypeTo( 3825 ProtocolListnfABITy); 3826 3827 // struct _objc_protocol_list* 3828 ProtocolListnfABIPtrTy = llvm::PointerType::getUnqual(ProtocolListnfABITy); 3829 3830 // struct _ivar_t { 3831 // unsigned long int *offset; // pointer to ivar offset location 3832 // char *name; 3833 // char *type; 3834 // uint32_t alignment; 3835 // uint32_t size; 3836 // } 3837 IvarnfABITy = llvm::StructType::get(llvm::PointerType::getUnqual(LongTy), 3838 Int8PtrTy, 3839 Int8PtrTy, 3840 IntTy, 3841 IntTy, 3842 NULL); 3843 CGM.getModule().addTypeName("struct._ivar_t", IvarnfABITy); 3844 3845 // struct _ivar_list_t { 3846 // uint32 entsize; // sizeof(struct _ivar_t) 3847 // uint32 count; 3848 // struct _iver_t list[count]; 3849 // } 3850 IvarListnfABITy = llvm::StructType::get(IntTy, 3851 IntTy, 3852 llvm::ArrayType::get( 3853 IvarnfABITy, 0), 3854 NULL); 3855 CGM.getModule().addTypeName("struct._ivar_list_t", IvarListnfABITy); 3856 3857 IvarListnfABIPtrTy = llvm::PointerType::getUnqual(IvarListnfABITy); 3858 3859 // struct _class_ro_t { 3860 // uint32_t const flags; 3861 // uint32_t const instanceStart; 3862 // uint32_t const instanceSize; 3863 // uint32_t const reserved; // only when building for 64bit targets 3864 // const uint8_t * const ivarLayout; 3865 // const char *const name; 3866 // const struct _method_list_t * const baseMethods; 3867 // const struct _objc_protocol_list *const baseProtocols; 3868 // const struct _ivar_list_t *const ivars; 3869 // const uint8_t * const weakIvarLayout; 3870 // const struct _prop_list_t * const properties; 3871 // } 3872 3873 // FIXME. Add 'reserved' field in 64bit abi mode! 3874 ClassRonfABITy = llvm::StructType::get(IntTy, 3875 IntTy, 3876 IntTy, 3877 Int8PtrTy, 3878 Int8PtrTy, 3879 MethodListnfABIPtrTy, 3880 ProtocolListnfABIPtrTy, 3881 IvarListnfABIPtrTy, 3882 Int8PtrTy, 3883 PropertyListPtrTy, 3884 NULL); 3885 CGM.getModule().addTypeName("struct._class_ro_t", 3886 ClassRonfABITy); 3887 3888 // ImpnfABITy - LLVM for id (*)(id, SEL, ...) 3889 std::vector<const llvm::Type*> Params; 3890 Params.push_back(ObjectPtrTy); 3891 Params.push_back(SelectorPtrTy); 3892 ImpnfABITy = llvm::PointerType::getUnqual( 3893 llvm::FunctionType::get(ObjectPtrTy, Params, false)); 3894 3895 // struct _class_t { 3896 // struct _class_t *isa; 3897 // struct _class_t * const superclass; 3898 // void *cache; 3899 // IMP *vtable; 3900 // struct class_ro_t *ro; 3901 // } 3902 3903 llvm::PATypeHolder ClassTyHolder = llvm::OpaqueType::get(); 3904 ClassnfABITy = llvm::StructType::get(llvm::PointerType::getUnqual(ClassTyHolder), 3905 llvm::PointerType::getUnqual(ClassTyHolder), 3906 CachePtrTy, 3907 llvm::PointerType::getUnqual(ImpnfABITy), 3908 llvm::PointerType::getUnqual( 3909 ClassRonfABITy), 3910 NULL); 3911 CGM.getModule().addTypeName("struct._class_t", ClassnfABITy); 3912 3913 cast<llvm::OpaqueType>(ClassTyHolder.get())->refineAbstractTypeTo( 3914 ClassnfABITy); 3915 3916 // LLVM for struct _class_t * 3917 ClassnfABIPtrTy = llvm::PointerType::getUnqual(ClassnfABITy); 3918 3919 // struct _category_t { 3920 // const char * const name; 3921 // struct _class_t *const cls; 3922 // const struct _method_list_t * const instance_methods; 3923 // const struct _method_list_t * const class_methods; 3924 // const struct _protocol_list_t * const protocols; 3925 // const struct _prop_list_t * const properties; 3926 // } 3927 CategorynfABITy = llvm::StructType::get(Int8PtrTy, 3928 ClassnfABIPtrTy, 3929 MethodListnfABIPtrTy, 3930 MethodListnfABIPtrTy, 3931 ProtocolListnfABIPtrTy, 3932 PropertyListPtrTy, 3933 NULL); 3934 CGM.getModule().addTypeName("struct._category_t", CategorynfABITy); 3935 3936 // New types for nonfragile abi messaging. 3937 CodeGen::CodeGenTypes &Types = CGM.getTypes(); 3938 ASTContext &Ctx = CGM.getContext(); 3939 3940 // MessageRefTy - LLVM for: 3941 // struct _message_ref_t { 3942 // IMP messenger; 3943 // SEL name; 3944 // }; 3945 3946 // First the clang type for struct _message_ref_t 3947 RecordDecl *RD = RecordDecl::Create(Ctx, TagDecl::TK_struct, 0, 3948 SourceLocation(), 3949 &Ctx.Idents.get("_message_ref_t")); 3950 RD->addDecl(Ctx, FieldDecl::Create(Ctx, RD, SourceLocation(), 0, 3951 Ctx.VoidPtrTy, 0, false)); 3952 RD->addDecl(Ctx, FieldDecl::Create(Ctx, RD, SourceLocation(), 0, 3953 Ctx.getObjCSelType(), 0, false)); 3954 RD->completeDefinition(Ctx); 3955 3956 MessageRefCTy = Ctx.getTagDeclType(RD); 3957 MessageRefCPtrTy = Ctx.getPointerType(MessageRefCTy); 3958 MessageRefTy = cast<llvm::StructType>(Types.ConvertType(MessageRefCTy)); 3959 3960 // MessageRefPtrTy - LLVM for struct _message_ref_t* 3961 MessageRefPtrTy = llvm::PointerType::getUnqual(MessageRefTy); 3962 3963 // SuperMessageRefTy - LLVM for: 3964 // struct _super_message_ref_t { 3965 // SUPER_IMP messenger; 3966 // SEL name; 3967 // }; 3968 SuperMessageRefTy = llvm::StructType::get(ImpnfABITy, 3969 SelectorPtrTy, 3970 NULL); 3971 CGM.getModule().addTypeName("struct._super_message_ref_t", SuperMessageRefTy); 3972 3973 // SuperMessageRefPtrTy - LLVM for struct _super_message_ref_t* 3974 SuperMessageRefPtrTy = llvm::PointerType::getUnqual(SuperMessageRefTy); 3975 3976 3977 // struct objc_typeinfo { 3978 // const void** vtable; // objc_ehtype_vtable + 2 3979 // const char* name; // c++ typeinfo string 3980 // Class cls; 3981 // }; 3982 EHTypeTy = llvm::StructType::get(llvm::PointerType::getUnqual(Int8PtrTy), 3983 Int8PtrTy, 3984 ClassnfABIPtrTy, 3985 NULL); 3986 CGM.getModule().addTypeName("struct._objc_typeinfo", EHTypeTy); 3987 EHTypePtrTy = llvm::PointerType::getUnqual(EHTypeTy); 3988} 3989 3990llvm::Function *CGObjCNonFragileABIMac::ModuleInitFunction() { 3991 FinishNonFragileABIModule(); 3992 3993 return NULL; 3994} 3995 3996void CGObjCNonFragileABIMac::FinishNonFragileABIModule() { 3997 // nonfragile abi has no module definition. 3998 3999 // Build list of all implemented classe addresses in array 4000 // L_OBJC_LABEL_CLASS_$. 4001 // FIXME. Also generate in L_OBJC_LABEL_NONLAZY_CLASS_$ 4002 // list of 'nonlazy' implementations (defined as those with a +load{} 4003 // method!!). 4004 unsigned NumClasses = DefinedClasses.size(); 4005 if (NumClasses) { 4006 std::vector<llvm::Constant*> Symbols(NumClasses); 4007 for (unsigned i=0; i<NumClasses; i++) 4008 Symbols[i] = llvm::ConstantExpr::getBitCast(DefinedClasses[i], 4009 ObjCTypes.Int8PtrTy); 4010 llvm::Constant* Init = 4011 llvm::ConstantArray::get(llvm::ArrayType::get(ObjCTypes.Int8PtrTy, 4012 NumClasses), 4013 Symbols); 4014 4015 llvm::GlobalVariable *GV = 4016 new llvm::GlobalVariable(Init->getType(), false, 4017 llvm::GlobalValue::InternalLinkage, 4018 Init, 4019 "\01L_OBJC_LABEL_CLASS_$", 4020 &CGM.getModule()); 4021 GV->setAlignment(8); 4022 GV->setSection("__DATA, __objc_classlist, regular, no_dead_strip"); 4023 UsedGlobals.push_back(GV); 4024 } 4025 4026 // Build list of all implemented category addresses in array 4027 // L_OBJC_LABEL_CATEGORY_$. 4028 // FIXME. Also generate in L_OBJC_LABEL_NONLAZY_CATEGORY_$ 4029 // list of 'nonlazy' category implementations (defined as those with a +load{} 4030 // method!!). 4031 unsigned NumCategory = DefinedCategories.size(); 4032 if (NumCategory) { 4033 std::vector<llvm::Constant*> Symbols(NumCategory); 4034 for (unsigned i=0; i<NumCategory; i++) 4035 Symbols[i] = llvm::ConstantExpr::getBitCast(DefinedCategories[i], 4036 ObjCTypes.Int8PtrTy); 4037 llvm::Constant* Init = 4038 llvm::ConstantArray::get(llvm::ArrayType::get(ObjCTypes.Int8PtrTy, 4039 NumCategory), 4040 Symbols); 4041 4042 llvm::GlobalVariable *GV = 4043 new llvm::GlobalVariable(Init->getType(), false, 4044 llvm::GlobalValue::InternalLinkage, 4045 Init, 4046 "\01L_OBJC_LABEL_CATEGORY_$", 4047 &CGM.getModule()); 4048 GV->setAlignment(8); 4049 GV->setSection("__DATA, __objc_catlist, regular, no_dead_strip"); 4050 UsedGlobals.push_back(GV); 4051 } 4052 4053 // static int L_OBJC_IMAGE_INFO[2] = { 0, flags }; 4054 // FIXME. flags can be 0 | 1 | 2 | 6. For now just use 0 4055 std::vector<llvm::Constant*> Values(2); 4056 Values[0] = llvm::ConstantInt::get(ObjCTypes.IntTy, 0); 4057 unsigned int flags = 0; 4058 // FIXME: Fix and continue? 4059 if (CGM.getLangOptions().getGCMode() != LangOptions::NonGC) 4060 flags |= eImageInfo_GarbageCollected; 4061 if (CGM.getLangOptions().getGCMode() == LangOptions::GCOnly) 4062 flags |= eImageInfo_GCOnly; 4063 Values[1] = llvm::ConstantInt::get(ObjCTypes.IntTy, flags); 4064 llvm::Constant* Init = llvm::ConstantArray::get( 4065 llvm::ArrayType::get(ObjCTypes.IntTy, 2), 4066 Values); 4067 llvm::GlobalVariable *IMGV = 4068 new llvm::GlobalVariable(Init->getType(), false, 4069 llvm::GlobalValue::InternalLinkage, 4070 Init, 4071 "\01L_OBJC_IMAGE_INFO", 4072 &CGM.getModule()); 4073 IMGV->setSection("__DATA, __objc_imageinfo, regular, no_dead_strip"); 4074 IMGV->setConstant(true); 4075 UsedGlobals.push_back(IMGV); 4076 4077 std::vector<llvm::Constant*> Used; 4078 4079 for (std::vector<llvm::GlobalVariable*>::iterator i = UsedGlobals.begin(), 4080 e = UsedGlobals.end(); i != e; ++i) { 4081 Used.push_back(llvm::ConstantExpr::getBitCast(*i, ObjCTypes.Int8PtrTy)); 4082 } 4083 4084 llvm::ArrayType *AT = llvm::ArrayType::get(ObjCTypes.Int8PtrTy, Used.size()); 4085 llvm::GlobalValue *GV = 4086 new llvm::GlobalVariable(AT, false, 4087 llvm::GlobalValue::AppendingLinkage, 4088 llvm::ConstantArray::get(AT, Used), 4089 "llvm.used", 4090 &CGM.getModule()); 4091 4092 GV->setSection("llvm.metadata"); 4093 4094} 4095 4096// Metadata flags 4097enum MetaDataDlags { 4098 CLS = 0x0, 4099 CLS_META = 0x1, 4100 CLS_ROOT = 0x2, 4101 OBJC2_CLS_HIDDEN = 0x10, 4102 CLS_EXCEPTION = 0x20 4103}; 4104/// BuildClassRoTInitializer - generate meta-data for: 4105/// struct _class_ro_t { 4106/// uint32_t const flags; 4107/// uint32_t const instanceStart; 4108/// uint32_t const instanceSize; 4109/// uint32_t const reserved; // only when building for 64bit targets 4110/// const uint8_t * const ivarLayout; 4111/// const char *const name; 4112/// const struct _method_list_t * const baseMethods; 4113/// const struct _protocol_list_t *const baseProtocols; 4114/// const struct _ivar_list_t *const ivars; 4115/// const uint8_t * const weakIvarLayout; 4116/// const struct _prop_list_t * const properties; 4117/// } 4118/// 4119llvm::GlobalVariable * CGObjCNonFragileABIMac::BuildClassRoTInitializer( 4120 unsigned flags, 4121 unsigned InstanceStart, 4122 unsigned InstanceSize, 4123 const ObjCImplementationDecl *ID) { 4124 std::string ClassName = ID->getNameAsString(); 4125 std::vector<llvm::Constant*> Values(10); // 11 for 64bit targets! 4126 Values[ 0] = llvm::ConstantInt::get(ObjCTypes.IntTy, flags); 4127 Values[ 1] = llvm::ConstantInt::get(ObjCTypes.IntTy, InstanceStart); 4128 Values[ 2] = llvm::ConstantInt::get(ObjCTypes.IntTy, InstanceSize); 4129 // FIXME. For 64bit targets add 0 here. 4130 Values[ 3] = (flags & CLS_META) ? GetIvarLayoutName(0, ObjCTypes) 4131 : BuildIvarLayout(ID, true); 4132 Values[ 4] = GetClassName(ID->getIdentifier()); 4133 // const struct _method_list_t * const baseMethods; 4134 std::vector<llvm::Constant*> Methods; 4135 std::string MethodListName("\01l_OBJC_$_"); 4136 if (flags & CLS_META) { 4137 MethodListName += "CLASS_METHODS_" + ID->getNameAsString(); 4138 for (ObjCImplementationDecl::classmeth_iterator 4139 i = ID->classmeth_begin(CGM.getContext()), 4140 e = ID->classmeth_end(CGM.getContext()); i != e; ++i) { 4141 // Class methods should always be defined. 4142 Methods.push_back(GetMethodConstant(*i)); 4143 } 4144 } else { 4145 MethodListName += "INSTANCE_METHODS_" + ID->getNameAsString(); 4146 for (ObjCImplementationDecl::instmeth_iterator 4147 i = ID->instmeth_begin(CGM.getContext()), 4148 e = ID->instmeth_end(CGM.getContext()); i != e; ++i) { 4149 // Instance methods should always be defined. 4150 Methods.push_back(GetMethodConstant(*i)); 4151 } 4152 for (ObjCImplementationDecl::propimpl_iterator 4153 i = ID->propimpl_begin(CGM.getContext()), 4154 e = ID->propimpl_end(CGM.getContext()); i != e; ++i) { 4155 ObjCPropertyImplDecl *PID = *i; 4156 4157 if (PID->getPropertyImplementation() == ObjCPropertyImplDecl::Synthesize){ 4158 ObjCPropertyDecl *PD = PID->getPropertyDecl(); 4159 4160 if (ObjCMethodDecl *MD = PD->getGetterMethodDecl()) 4161 if (llvm::Constant *C = GetMethodConstant(MD)) 4162 Methods.push_back(C); 4163 if (ObjCMethodDecl *MD = PD->getSetterMethodDecl()) 4164 if (llvm::Constant *C = GetMethodConstant(MD)) 4165 Methods.push_back(C); 4166 } 4167 } 4168 } 4169 Values[ 5] = EmitMethodList(MethodListName, 4170 "__DATA, __objc_const", Methods); 4171 4172 const ObjCInterfaceDecl *OID = ID->getClassInterface(); 4173 assert(OID && "CGObjCNonFragileABIMac::BuildClassRoTInitializer"); 4174 Values[ 6] = EmitProtocolList("\01l_OBJC_CLASS_PROTOCOLS_$_" 4175 + OID->getNameAsString(), 4176 OID->protocol_begin(), 4177 OID->protocol_end()); 4178 4179 if (flags & CLS_META) 4180 Values[ 7] = llvm::Constant::getNullValue(ObjCTypes.IvarListnfABIPtrTy); 4181 else 4182 Values[ 7] = EmitIvarList(ID); 4183 Values[ 8] = (flags & CLS_META) ? GetIvarLayoutName(0, ObjCTypes) 4184 : BuildIvarLayout(ID, false); 4185 if (flags & CLS_META) 4186 Values[ 9] = llvm::Constant::getNullValue(ObjCTypes.PropertyListPtrTy); 4187 else 4188 Values[ 9] = 4189 EmitPropertyList( 4190 "\01l_OBJC_$_PROP_LIST_" + ID->getNameAsString(), 4191 ID, ID->getClassInterface(), ObjCTypes); 4192 llvm::Constant *Init = llvm::ConstantStruct::get(ObjCTypes.ClassRonfABITy, 4193 Values); 4194 llvm::GlobalVariable *CLASS_RO_GV = 4195 new llvm::GlobalVariable(ObjCTypes.ClassRonfABITy, false, 4196 llvm::GlobalValue::InternalLinkage, 4197 Init, 4198 (flags & CLS_META) ? 4199 std::string("\01l_OBJC_METACLASS_RO_$_")+ClassName : 4200 std::string("\01l_OBJC_CLASS_RO_$_")+ClassName, 4201 &CGM.getModule()); 4202 CLASS_RO_GV->setAlignment( 4203 CGM.getTargetData().getPrefTypeAlignment(ObjCTypes.ClassRonfABITy)); 4204 CLASS_RO_GV->setSection("__DATA, __objc_const"); 4205 return CLASS_RO_GV; 4206 4207} 4208 4209/// BuildClassMetaData - This routine defines that to-level meta-data 4210/// for the given ClassName for: 4211/// struct _class_t { 4212/// struct _class_t *isa; 4213/// struct _class_t * const superclass; 4214/// void *cache; 4215/// IMP *vtable; 4216/// struct class_ro_t *ro; 4217/// } 4218/// 4219llvm::GlobalVariable * CGObjCNonFragileABIMac::BuildClassMetaData( 4220 std::string &ClassName, 4221 llvm::Constant *IsAGV, 4222 llvm::Constant *SuperClassGV, 4223 llvm::Constant *ClassRoGV, 4224 bool HiddenVisibility) { 4225 std::vector<llvm::Constant*> Values(5); 4226 Values[0] = IsAGV; 4227 Values[1] = SuperClassGV 4228 ? SuperClassGV 4229 : llvm::Constant::getNullValue(ObjCTypes.ClassnfABIPtrTy); 4230 Values[2] = ObjCEmptyCacheVar; // &ObjCEmptyCacheVar 4231 Values[3] = ObjCEmptyVtableVar; // &ObjCEmptyVtableVar 4232 Values[4] = ClassRoGV; // &CLASS_RO_GV 4233 llvm::Constant *Init = llvm::ConstantStruct::get(ObjCTypes.ClassnfABITy, 4234 Values); 4235 llvm::GlobalVariable *GV = GetClassGlobal(ClassName); 4236 GV->setInitializer(Init); 4237 GV->setSection("__DATA, __objc_data"); 4238 GV->setAlignment( 4239 CGM.getTargetData().getPrefTypeAlignment(ObjCTypes.ClassnfABITy)); 4240 if (HiddenVisibility) 4241 GV->setVisibility(llvm::GlobalValue::HiddenVisibility); 4242 return GV; 4243} 4244 4245void CGObjCNonFragileABIMac::GetClassSizeInfo(const ObjCImplementationDecl *OID, 4246 uint32_t &InstanceStart, 4247 uint32_t &InstanceSize) { 4248 // Find first and last (non-padding) ivars in this interface. 4249 4250 // FIXME: Use iterator. 4251 llvm::SmallVector<ObjCIvarDecl*, 16> OIvars; 4252 GetNamedIvarList(OID->getClassInterface(), OIvars); 4253 4254 if (OIvars.empty()) { 4255 InstanceStart = InstanceSize = 0; 4256 return; 4257 } 4258 4259 const ObjCIvarDecl *First = OIvars.front(); 4260 const ObjCIvarDecl *Last = OIvars.back(); 4261 4262 InstanceStart = ComputeIvarBaseOffset(CGM, OID, First); 4263 const llvm::Type *FieldTy = 4264 CGM.getTypes().ConvertTypeForMem(Last->getType()); 4265 unsigned Size = CGM.getTargetData().getTypePaddedSize(FieldTy); 4266// FIXME. This breaks compatibility with llvm-gcc-4.2 (but makes it compatible 4267// with gcc-4.2). We postpone this for now. 4268#if 0 4269 if (Last->isBitField()) { 4270 Expr *BitWidth = Last->getBitWidth(); 4271 uint64_t BitFieldSize = 4272 BitWidth->EvaluateAsInt(CGM.getContext()).getZExtValue(); 4273 Size = (BitFieldSize / 8) + ((BitFieldSize % 8) != 0); 4274 } 4275#endif 4276 InstanceSize = ComputeIvarBaseOffset(CGM, OID, Last) + Size; 4277} 4278 4279void CGObjCNonFragileABIMac::GenerateClass(const ObjCImplementationDecl *ID) { 4280 std::string ClassName = ID->getNameAsString(); 4281 if (!ObjCEmptyCacheVar) { 4282 ObjCEmptyCacheVar = new llvm::GlobalVariable( 4283 ObjCTypes.CacheTy, 4284 false, 4285 llvm::GlobalValue::ExternalLinkage, 4286 0, 4287 "_objc_empty_cache", 4288 &CGM.getModule()); 4289 4290 ObjCEmptyVtableVar = new llvm::GlobalVariable( 4291 ObjCTypes.ImpnfABITy, 4292 false, 4293 llvm::GlobalValue::ExternalLinkage, 4294 0, 4295 "_objc_empty_vtable", 4296 &CGM.getModule()); 4297 } 4298 assert(ID->getClassInterface() && 4299 "CGObjCNonFragileABIMac::GenerateClass - class is 0"); 4300 // FIXME: Is this correct (that meta class size is never computed)? 4301 uint32_t InstanceStart = 4302 CGM.getTargetData().getTypePaddedSize(ObjCTypes.ClassnfABITy); 4303 uint32_t InstanceSize = InstanceStart; 4304 uint32_t flags = CLS_META; 4305 std::string ObjCMetaClassName(getMetaclassSymbolPrefix()); 4306 std::string ObjCClassName(getClassSymbolPrefix()); 4307 4308 llvm::GlobalVariable *SuperClassGV, *IsAGV; 4309 4310 bool classIsHidden = 4311 CGM.getDeclVisibilityMode(ID->getClassInterface()) == LangOptions::Hidden; 4312 if (classIsHidden) 4313 flags |= OBJC2_CLS_HIDDEN; 4314 if (!ID->getClassInterface()->getSuperClass()) { 4315 // class is root 4316 flags |= CLS_ROOT; 4317 SuperClassGV = GetClassGlobal(ObjCClassName + ClassName); 4318 IsAGV = GetClassGlobal(ObjCMetaClassName + ClassName); 4319 } else { 4320 // Has a root. Current class is not a root. 4321 const ObjCInterfaceDecl *Root = ID->getClassInterface(); 4322 while (const ObjCInterfaceDecl *Super = Root->getSuperClass()) 4323 Root = Super; 4324 IsAGV = GetClassGlobal(ObjCMetaClassName + Root->getNameAsString()); 4325 // work on super class metadata symbol. 4326 std::string SuperClassName = 4327 ObjCMetaClassName + ID->getClassInterface()->getSuperClass()->getNameAsString(); 4328 SuperClassGV = GetClassGlobal(SuperClassName); 4329 } 4330 llvm::GlobalVariable *CLASS_RO_GV = BuildClassRoTInitializer(flags, 4331 InstanceStart, 4332 InstanceSize,ID); 4333 std::string TClassName = ObjCMetaClassName + ClassName; 4334 llvm::GlobalVariable *MetaTClass = 4335 BuildClassMetaData(TClassName, IsAGV, SuperClassGV, CLASS_RO_GV, 4336 classIsHidden); 4337 4338 // Metadata for the class 4339 flags = CLS; 4340 if (classIsHidden) 4341 flags |= OBJC2_CLS_HIDDEN; 4342 4343 if (hasObjCExceptionAttribute(ID->getClassInterface())) 4344 flags |= CLS_EXCEPTION; 4345 4346 if (!ID->getClassInterface()->getSuperClass()) { 4347 flags |= CLS_ROOT; 4348 SuperClassGV = 0; 4349 } else { 4350 // Has a root. Current class is not a root. 4351 std::string RootClassName = 4352 ID->getClassInterface()->getSuperClass()->getNameAsString(); 4353 SuperClassGV = GetClassGlobal(ObjCClassName + RootClassName); 4354 } 4355 GetClassSizeInfo(ID, InstanceStart, InstanceSize); 4356 CLASS_RO_GV = BuildClassRoTInitializer(flags, 4357 InstanceStart, 4358 InstanceSize, 4359 ID); 4360 4361 TClassName = ObjCClassName + ClassName; 4362 llvm::GlobalVariable *ClassMD = 4363 BuildClassMetaData(TClassName, MetaTClass, SuperClassGV, CLASS_RO_GV, 4364 classIsHidden); 4365 DefinedClasses.push_back(ClassMD); 4366 4367 // Force the definition of the EHType if necessary. 4368 if (flags & CLS_EXCEPTION) 4369 GetInterfaceEHType(ID->getClassInterface(), true); 4370} 4371 4372/// GenerateProtocolRef - This routine is called to generate code for 4373/// a protocol reference expression; as in: 4374/// @code 4375/// @protocol(Proto1); 4376/// @endcode 4377/// It generates a weak reference to l_OBJC_PROTOCOL_REFERENCE_$_Proto1 4378/// which will hold address of the protocol meta-data. 4379/// 4380llvm::Value *CGObjCNonFragileABIMac::GenerateProtocolRef(CGBuilderTy &Builder, 4381 const ObjCProtocolDecl *PD) { 4382 4383 // This routine is called for @protocol only. So, we must build definition 4384 // of protocol's meta-data (not a reference to it!) 4385 // 4386 llvm::Constant *Init = llvm::ConstantExpr::getBitCast(GetOrEmitProtocol(PD), 4387 ObjCTypes.ExternalProtocolPtrTy); 4388 4389 std::string ProtocolName("\01l_OBJC_PROTOCOL_REFERENCE_$_"); 4390 ProtocolName += PD->getNameAsCString(); 4391 4392 llvm::GlobalVariable *PTGV = CGM.getModule().getGlobalVariable(ProtocolName); 4393 if (PTGV) 4394 return Builder.CreateLoad(PTGV, false, "tmp"); 4395 PTGV = new llvm::GlobalVariable( 4396 Init->getType(), false, 4397 llvm::GlobalValue::WeakAnyLinkage, 4398 Init, 4399 ProtocolName, 4400 &CGM.getModule()); 4401 PTGV->setSection("__DATA, __objc_protorefs, coalesced, no_dead_strip"); 4402 PTGV->setVisibility(llvm::GlobalValue::HiddenVisibility); 4403 UsedGlobals.push_back(PTGV); 4404 return Builder.CreateLoad(PTGV, false, "tmp"); 4405} 4406 4407/// GenerateCategory - Build metadata for a category implementation. 4408/// struct _category_t { 4409/// const char * const name; 4410/// struct _class_t *const cls; 4411/// const struct _method_list_t * const instance_methods; 4412/// const struct _method_list_t * const class_methods; 4413/// const struct _protocol_list_t * const protocols; 4414/// const struct _prop_list_t * const properties; 4415/// } 4416/// 4417void CGObjCNonFragileABIMac::GenerateCategory(const ObjCCategoryImplDecl *OCD) 4418{ 4419 const ObjCInterfaceDecl *Interface = OCD->getClassInterface(); 4420 const char *Prefix = "\01l_OBJC_$_CATEGORY_"; 4421 std::string ExtCatName(Prefix + Interface->getNameAsString()+ 4422 "_$_" + OCD->getNameAsString()); 4423 std::string ExtClassName(getClassSymbolPrefix() + 4424 Interface->getNameAsString()); 4425 4426 std::vector<llvm::Constant*> Values(6); 4427 Values[0] = GetClassName(OCD->getIdentifier()); 4428 // meta-class entry symbol 4429 llvm::GlobalVariable *ClassGV = GetClassGlobal(ExtClassName); 4430 Values[1] = ClassGV; 4431 std::vector<llvm::Constant*> Methods; 4432 std::string MethodListName(Prefix); 4433 MethodListName += "INSTANCE_METHODS_" + Interface->getNameAsString() + 4434 "_$_" + OCD->getNameAsString(); 4435 4436 for (ObjCCategoryImplDecl::instmeth_iterator 4437 i = OCD->instmeth_begin(CGM.getContext()), 4438 e = OCD->instmeth_end(CGM.getContext()); i != e; ++i) { 4439 // Instance methods should always be defined. 4440 Methods.push_back(GetMethodConstant(*i)); 4441 } 4442 4443 Values[2] = EmitMethodList(MethodListName, 4444 "__DATA, __objc_const", 4445 Methods); 4446 4447 MethodListName = Prefix; 4448 MethodListName += "CLASS_METHODS_" + Interface->getNameAsString() + "_$_" + 4449 OCD->getNameAsString(); 4450 Methods.clear(); 4451 for (ObjCCategoryImplDecl::classmeth_iterator 4452 i = OCD->classmeth_begin(CGM.getContext()), 4453 e = OCD->classmeth_end(CGM.getContext()); i != e; ++i) { 4454 // Class methods should always be defined. 4455 Methods.push_back(GetMethodConstant(*i)); 4456 } 4457 4458 Values[3] = EmitMethodList(MethodListName, 4459 "__DATA, __objc_const", 4460 Methods); 4461 const ObjCCategoryDecl *Category = 4462 Interface->FindCategoryDeclaration(OCD->getIdentifier()); 4463 if (Category) { 4464 std::string ExtName(Interface->getNameAsString() + "_$_" + 4465 OCD->getNameAsString()); 4466 Values[4] = EmitProtocolList("\01l_OBJC_CATEGORY_PROTOCOLS_$_" 4467 + Interface->getNameAsString() + "_$_" 4468 + Category->getNameAsString(), 4469 Category->protocol_begin(), 4470 Category->protocol_end()); 4471 Values[5] = 4472 EmitPropertyList(std::string("\01l_OBJC_$_PROP_LIST_") + ExtName, 4473 OCD, Category, ObjCTypes); 4474 } 4475 else { 4476 Values[4] = llvm::Constant::getNullValue(ObjCTypes.ProtocolListnfABIPtrTy); 4477 Values[5] = llvm::Constant::getNullValue(ObjCTypes.PropertyListPtrTy); 4478 } 4479 4480 llvm::Constant *Init = 4481 llvm::ConstantStruct::get(ObjCTypes.CategorynfABITy, 4482 Values); 4483 llvm::GlobalVariable *GCATV 4484 = new llvm::GlobalVariable(ObjCTypes.CategorynfABITy, 4485 false, 4486 llvm::GlobalValue::InternalLinkage, 4487 Init, 4488 ExtCatName, 4489 &CGM.getModule()); 4490 GCATV->setAlignment( 4491 CGM.getTargetData().getPrefTypeAlignment(ObjCTypes.CategorynfABITy)); 4492 GCATV->setSection("__DATA, __objc_const"); 4493 UsedGlobals.push_back(GCATV); 4494 DefinedCategories.push_back(GCATV); 4495} 4496 4497/// GetMethodConstant - Return a struct objc_method constant for the 4498/// given method if it has been defined. The result is null if the 4499/// method has not been defined. The return value has type MethodPtrTy. 4500llvm::Constant *CGObjCNonFragileABIMac::GetMethodConstant( 4501 const ObjCMethodDecl *MD) { 4502 // FIXME: Use DenseMap::lookup 4503 llvm::Function *Fn = MethodDefinitions[MD]; 4504 if (!Fn) 4505 return 0; 4506 4507 std::vector<llvm::Constant*> Method(3); 4508 Method[0] = 4509 llvm::ConstantExpr::getBitCast(GetMethodVarName(MD->getSelector()), 4510 ObjCTypes.SelectorPtrTy); 4511 Method[1] = GetMethodVarType(MD); 4512 Method[2] = llvm::ConstantExpr::getBitCast(Fn, ObjCTypes.Int8PtrTy); 4513 return llvm::ConstantStruct::get(ObjCTypes.MethodTy, Method); 4514} 4515 4516/// EmitMethodList - Build meta-data for method declarations 4517/// struct _method_list_t { 4518/// uint32_t entsize; // sizeof(struct _objc_method) 4519/// uint32_t method_count; 4520/// struct _objc_method method_list[method_count]; 4521/// } 4522/// 4523llvm::Constant *CGObjCNonFragileABIMac::EmitMethodList( 4524 const std::string &Name, 4525 const char *Section, 4526 const ConstantVector &Methods) { 4527 // Return null for empty list. 4528 if (Methods.empty()) 4529 return llvm::Constant::getNullValue(ObjCTypes.MethodListnfABIPtrTy); 4530 4531 std::vector<llvm::Constant*> Values(3); 4532 // sizeof(struct _objc_method) 4533 unsigned Size = CGM.getTargetData().getTypePaddedSize(ObjCTypes.MethodTy); 4534 Values[0] = llvm::ConstantInt::get(ObjCTypes.IntTy, Size); 4535 // method_count 4536 Values[1] = llvm::ConstantInt::get(ObjCTypes.IntTy, Methods.size()); 4537 llvm::ArrayType *AT = llvm::ArrayType::get(ObjCTypes.MethodTy, 4538 Methods.size()); 4539 Values[2] = llvm::ConstantArray::get(AT, Methods); 4540 llvm::Constant *Init = llvm::ConstantStruct::get(Values); 4541 4542 llvm::GlobalVariable *GV = 4543 new llvm::GlobalVariable(Init->getType(), false, 4544 llvm::GlobalValue::InternalLinkage, 4545 Init, 4546 Name, 4547 &CGM.getModule()); 4548 GV->setAlignment( 4549 CGM.getTargetData().getPrefTypeAlignment(Init->getType())); 4550 GV->setSection(Section); 4551 UsedGlobals.push_back(GV); 4552 return llvm::ConstantExpr::getBitCast(GV, 4553 ObjCTypes.MethodListnfABIPtrTy); 4554} 4555 4556/// ObjCIvarOffsetVariable - Returns the ivar offset variable for 4557/// the given ivar. 4558/// 4559llvm::GlobalVariable * CGObjCNonFragileABIMac::ObjCIvarOffsetVariable( 4560 const ObjCInterfaceDecl *ID, 4561 const ObjCIvarDecl *Ivar) { 4562 std::string Name = "OBJC_IVAR_$_" + 4563 getInterfaceDeclForIvar(ID, Ivar, CGM.getContext())->getNameAsString() + 4564 '.' + Ivar->getNameAsString(); 4565 llvm::GlobalVariable *IvarOffsetGV = 4566 CGM.getModule().getGlobalVariable(Name); 4567 if (!IvarOffsetGV) 4568 IvarOffsetGV = 4569 new llvm::GlobalVariable(ObjCTypes.LongTy, 4570 false, 4571 llvm::GlobalValue::ExternalLinkage, 4572 0, 4573 Name, 4574 &CGM.getModule()); 4575 return IvarOffsetGV; 4576} 4577 4578llvm::Constant * CGObjCNonFragileABIMac::EmitIvarOffsetVar( 4579 const ObjCInterfaceDecl *ID, 4580 const ObjCIvarDecl *Ivar, 4581 unsigned long int Offset) { 4582 llvm::GlobalVariable *IvarOffsetGV = ObjCIvarOffsetVariable(ID, Ivar); 4583 IvarOffsetGV->setInitializer(llvm::ConstantInt::get(ObjCTypes.LongTy, 4584 Offset)); 4585 IvarOffsetGV->setAlignment( 4586 CGM.getTargetData().getPrefTypeAlignment(ObjCTypes.LongTy)); 4587 4588 // FIXME: This matches gcc, but shouldn't the visibility be set on 4589 // the use as well (i.e., in ObjCIvarOffsetVariable). 4590 if (Ivar->getAccessControl() == ObjCIvarDecl::Private || 4591 Ivar->getAccessControl() == ObjCIvarDecl::Package || 4592 CGM.getDeclVisibilityMode(ID) == LangOptions::Hidden) 4593 IvarOffsetGV->setVisibility(llvm::GlobalValue::HiddenVisibility); 4594 else 4595 IvarOffsetGV->setVisibility(llvm::GlobalValue::DefaultVisibility); 4596 IvarOffsetGV->setSection("__DATA, __objc_const"); 4597 return IvarOffsetGV; 4598} 4599 4600/// EmitIvarList - Emit the ivar list for the given 4601/// implementation. The return value has type 4602/// IvarListnfABIPtrTy. 4603/// struct _ivar_t { 4604/// unsigned long int *offset; // pointer to ivar offset location 4605/// char *name; 4606/// char *type; 4607/// uint32_t alignment; 4608/// uint32_t size; 4609/// } 4610/// struct _ivar_list_t { 4611/// uint32 entsize; // sizeof(struct _ivar_t) 4612/// uint32 count; 4613/// struct _iver_t list[count]; 4614/// } 4615/// 4616 4617void CGObjCCommonMac::GetNamedIvarList(const ObjCInterfaceDecl *OID, 4618 llvm::SmallVector<ObjCIvarDecl*, 16> &Res) const { 4619 for (ObjCInterfaceDecl::ivar_iterator I = OID->ivar_begin(), 4620 E = OID->ivar_end(); I != E; ++I) { 4621 // Ignore unnamed bit-fields. 4622 if (!(*I)->getDeclName()) 4623 continue; 4624 4625 Res.push_back(*I); 4626 } 4627 4628 for (ObjCInterfaceDecl::prop_iterator I = OID->prop_begin(CGM.getContext()), 4629 E = OID->prop_end(CGM.getContext()); I != E; ++I) 4630 if (ObjCIvarDecl *IV = (*I)->getPropertyIvarDecl()) 4631 Res.push_back(IV); 4632} 4633 4634llvm::Constant *CGObjCNonFragileABIMac::EmitIvarList( 4635 const ObjCImplementationDecl *ID) { 4636 4637 std::vector<llvm::Constant*> Ivars, Ivar(5); 4638 4639 const ObjCInterfaceDecl *OID = ID->getClassInterface(); 4640 assert(OID && "CGObjCNonFragileABIMac::EmitIvarList - null interface"); 4641 4642 // FIXME. Consolidate this with similar code in GenerateClass. 4643 4644 // Collect declared and synthesized ivars in a small vector. 4645 llvm::SmallVector<ObjCIvarDecl*, 16> OIvars; 4646 GetNamedIvarList(OID, OIvars); 4647 4648 for (unsigned i = 0, e = OIvars.size(); i != e; ++i) { 4649 ObjCIvarDecl *IVD = OIvars[i]; 4650 Ivar[0] = EmitIvarOffsetVar(ID->getClassInterface(), IVD, 4651 ComputeIvarBaseOffset(CGM, ID, IVD)); 4652 Ivar[1] = GetMethodVarName(IVD->getIdentifier()); 4653 Ivar[2] = GetMethodVarType(IVD); 4654 const llvm::Type *FieldTy = 4655 CGM.getTypes().ConvertTypeForMem(IVD->getType()); 4656 unsigned Size = CGM.getTargetData().getTypePaddedSize(FieldTy); 4657 unsigned Align = CGM.getContext().getPreferredTypeAlign( 4658 IVD->getType().getTypePtr()) >> 3; 4659 Align = llvm::Log2_32(Align); 4660 Ivar[3] = llvm::ConstantInt::get(ObjCTypes.IntTy, Align); 4661 // NOTE. Size of a bitfield does not match gcc's, because of the 4662 // way bitfields are treated special in each. But I am told that 4663 // 'size' for bitfield ivars is ignored by the runtime so it does 4664 // not matter. If it matters, there is enough info to get the 4665 // bitfield right! 4666 Ivar[4] = llvm::ConstantInt::get(ObjCTypes.IntTy, Size); 4667 Ivars.push_back(llvm::ConstantStruct::get(ObjCTypes.IvarnfABITy, Ivar)); 4668 } 4669 // Return null for empty list. 4670 if (Ivars.empty()) 4671 return llvm::Constant::getNullValue(ObjCTypes.IvarListnfABIPtrTy); 4672 std::vector<llvm::Constant*> Values(3); 4673 unsigned Size = CGM.getTargetData().getTypePaddedSize(ObjCTypes.IvarnfABITy); 4674 Values[0] = llvm::ConstantInt::get(ObjCTypes.IntTy, Size); 4675 Values[1] = llvm::ConstantInt::get(ObjCTypes.IntTy, Ivars.size()); 4676 llvm::ArrayType *AT = llvm::ArrayType::get(ObjCTypes.IvarnfABITy, 4677 Ivars.size()); 4678 Values[2] = llvm::ConstantArray::get(AT, Ivars); 4679 llvm::Constant *Init = llvm::ConstantStruct::get(Values); 4680 const char *Prefix = "\01l_OBJC_$_INSTANCE_VARIABLES_"; 4681 llvm::GlobalVariable *GV = 4682 new llvm::GlobalVariable(Init->getType(), false, 4683 llvm::GlobalValue::InternalLinkage, 4684 Init, 4685 Prefix + OID->getNameAsString(), 4686 &CGM.getModule()); 4687 GV->setAlignment( 4688 CGM.getTargetData().getPrefTypeAlignment(Init->getType())); 4689 GV->setSection("__DATA, __objc_const"); 4690 4691 UsedGlobals.push_back(GV); 4692 return llvm::ConstantExpr::getBitCast(GV, 4693 ObjCTypes.IvarListnfABIPtrTy); 4694} 4695 4696llvm::Constant *CGObjCNonFragileABIMac::GetOrEmitProtocolRef( 4697 const ObjCProtocolDecl *PD) { 4698 llvm::GlobalVariable *&Entry = Protocols[PD->getIdentifier()]; 4699 4700 if (!Entry) { 4701 // We use the initializer as a marker of whether this is a forward 4702 // reference or not. At module finalization we add the empty 4703 // contents for protocols which were referenced but never defined. 4704 Entry = 4705 new llvm::GlobalVariable(ObjCTypes.ProtocolnfABITy, false, 4706 llvm::GlobalValue::ExternalLinkage, 4707 0, 4708 "\01l_OBJC_PROTOCOL_$_" + PD->getNameAsString(), 4709 &CGM.getModule()); 4710 Entry->setSection("__DATA,__datacoal_nt,coalesced"); 4711 UsedGlobals.push_back(Entry); 4712 } 4713 4714 return Entry; 4715} 4716 4717/// GetOrEmitProtocol - Generate the protocol meta-data: 4718/// @code 4719/// struct _protocol_t { 4720/// id isa; // NULL 4721/// const char * const protocol_name; 4722/// const struct _protocol_list_t * protocol_list; // super protocols 4723/// const struct method_list_t * const instance_methods; 4724/// const struct method_list_t * const class_methods; 4725/// const struct method_list_t *optionalInstanceMethods; 4726/// const struct method_list_t *optionalClassMethods; 4727/// const struct _prop_list_t * properties; 4728/// const uint32_t size; // sizeof(struct _protocol_t) 4729/// const uint32_t flags; // = 0 4730/// } 4731/// @endcode 4732/// 4733 4734llvm::Constant *CGObjCNonFragileABIMac::GetOrEmitProtocol( 4735 const ObjCProtocolDecl *PD) { 4736 llvm::GlobalVariable *&Entry = Protocols[PD->getIdentifier()]; 4737 4738 // Early exit if a defining object has already been generated. 4739 if (Entry && Entry->hasInitializer()) 4740 return Entry; 4741 4742 const char *ProtocolName = PD->getNameAsCString(); 4743 4744 // Construct method lists. 4745 std::vector<llvm::Constant*> InstanceMethods, ClassMethods; 4746 std::vector<llvm::Constant*> OptInstanceMethods, OptClassMethods; 4747 for (ObjCProtocolDecl::instmeth_iterator 4748 i = PD->instmeth_begin(CGM.getContext()), 4749 e = PD->instmeth_end(CGM.getContext()); 4750 i != e; ++i) { 4751 ObjCMethodDecl *MD = *i; 4752 llvm::Constant *C = GetMethodDescriptionConstant(MD); 4753 if (MD->getImplementationControl() == ObjCMethodDecl::Optional) { 4754 OptInstanceMethods.push_back(C); 4755 } else { 4756 InstanceMethods.push_back(C); 4757 } 4758 } 4759 4760 for (ObjCProtocolDecl::classmeth_iterator 4761 i = PD->classmeth_begin(CGM.getContext()), 4762 e = PD->classmeth_end(CGM.getContext()); 4763 i != e; ++i) { 4764 ObjCMethodDecl *MD = *i; 4765 llvm::Constant *C = GetMethodDescriptionConstant(MD); 4766 if (MD->getImplementationControl() == ObjCMethodDecl::Optional) { 4767 OptClassMethods.push_back(C); 4768 } else { 4769 ClassMethods.push_back(C); 4770 } 4771 } 4772 4773 std::vector<llvm::Constant*> Values(10); 4774 // isa is NULL 4775 Values[0] = llvm::Constant::getNullValue(ObjCTypes.ObjectPtrTy); 4776 Values[1] = GetClassName(PD->getIdentifier()); 4777 Values[2] = EmitProtocolList( 4778 "\01l_OBJC_$_PROTOCOL_REFS_" + PD->getNameAsString(), 4779 PD->protocol_begin(), 4780 PD->protocol_end()); 4781 4782 Values[3] = EmitMethodList("\01l_OBJC_$_PROTOCOL_INSTANCE_METHODS_" 4783 + PD->getNameAsString(), 4784 "__DATA, __objc_const", 4785 InstanceMethods); 4786 Values[4] = EmitMethodList("\01l_OBJC_$_PROTOCOL_CLASS_METHODS_" 4787 + PD->getNameAsString(), 4788 "__DATA, __objc_const", 4789 ClassMethods); 4790 Values[5] = EmitMethodList("\01l_OBJC_$_PROTOCOL_INSTANCE_METHODS_OPT_" 4791 + PD->getNameAsString(), 4792 "__DATA, __objc_const", 4793 OptInstanceMethods); 4794 Values[6] = EmitMethodList("\01l_OBJC_$_PROTOCOL_CLASS_METHODS_OPT_" 4795 + PD->getNameAsString(), 4796 "__DATA, __objc_const", 4797 OptClassMethods); 4798 Values[7] = EmitPropertyList("\01l_OBJC_$_PROP_LIST_" + PD->getNameAsString(), 4799 0, PD, ObjCTypes); 4800 uint32_t Size = 4801 CGM.getTargetData().getTypePaddedSize(ObjCTypes.ProtocolnfABITy); 4802 Values[8] = llvm::ConstantInt::get(ObjCTypes.IntTy, Size); 4803 Values[9] = llvm::Constant::getNullValue(ObjCTypes.IntTy); 4804 llvm::Constant *Init = llvm::ConstantStruct::get(ObjCTypes.ProtocolnfABITy, 4805 Values); 4806 4807 if (Entry) { 4808 // Already created, fix the linkage and update the initializer. 4809 Entry->setLinkage(llvm::GlobalValue::WeakAnyLinkage); 4810 Entry->setInitializer(Init); 4811 } else { 4812 Entry = 4813 new llvm::GlobalVariable(ObjCTypes.ProtocolnfABITy, false, 4814 llvm::GlobalValue::WeakAnyLinkage, 4815 Init, 4816 std::string("\01l_OBJC_PROTOCOL_$_")+ProtocolName, 4817 &CGM.getModule()); 4818 Entry->setAlignment( 4819 CGM.getTargetData().getPrefTypeAlignment(ObjCTypes.ProtocolnfABITy)); 4820 Entry->setSection("__DATA,__datacoal_nt,coalesced"); 4821 } 4822 Entry->setVisibility(llvm::GlobalValue::HiddenVisibility); 4823 4824 // Use this protocol meta-data to build protocol list table in section 4825 // __DATA, __objc_protolist 4826 llvm::GlobalVariable *PTGV = new llvm::GlobalVariable( 4827 ObjCTypes.ProtocolnfABIPtrTy, false, 4828 llvm::GlobalValue::WeakAnyLinkage, 4829 Entry, 4830 std::string("\01l_OBJC_LABEL_PROTOCOL_$_") 4831 +ProtocolName, 4832 &CGM.getModule()); 4833 PTGV->setAlignment( 4834 CGM.getTargetData().getPrefTypeAlignment(ObjCTypes.ProtocolnfABIPtrTy)); 4835 PTGV->setSection("__DATA, __objc_protolist, coalesced, no_dead_strip"); 4836 PTGV->setVisibility(llvm::GlobalValue::HiddenVisibility); 4837 UsedGlobals.push_back(PTGV); 4838 return Entry; 4839} 4840 4841/// EmitProtocolList - Generate protocol list meta-data: 4842/// @code 4843/// struct _protocol_list_t { 4844/// long protocol_count; // Note, this is 32/64 bit 4845/// struct _protocol_t[protocol_count]; 4846/// } 4847/// @endcode 4848/// 4849llvm::Constant * 4850CGObjCNonFragileABIMac::EmitProtocolList(const std::string &Name, 4851 ObjCProtocolDecl::protocol_iterator begin, 4852 ObjCProtocolDecl::protocol_iterator end) { 4853 std::vector<llvm::Constant*> ProtocolRefs; 4854 4855 // Just return null for empty protocol lists 4856 if (begin == end) 4857 return llvm::Constant::getNullValue(ObjCTypes.ProtocolListnfABIPtrTy); 4858 4859 // FIXME: We shouldn't need to do this lookup here, should we? 4860 llvm::GlobalVariable *GV = CGM.getModule().getGlobalVariable(Name, true); 4861 if (GV) 4862 return llvm::ConstantExpr::getBitCast(GV, 4863 ObjCTypes.ProtocolListnfABIPtrTy); 4864 4865 for (; begin != end; ++begin) 4866 ProtocolRefs.push_back(GetProtocolRef(*begin)); // Implemented??? 4867 4868 // This list is null terminated. 4869 ProtocolRefs.push_back(llvm::Constant::getNullValue( 4870 ObjCTypes.ProtocolnfABIPtrTy)); 4871 4872 std::vector<llvm::Constant*> Values(2); 4873 Values[0] = llvm::ConstantInt::get(ObjCTypes.LongTy, ProtocolRefs.size() - 1); 4874 Values[1] = 4875 llvm::ConstantArray::get(llvm::ArrayType::get(ObjCTypes.ProtocolnfABIPtrTy, 4876 ProtocolRefs.size()), 4877 ProtocolRefs); 4878 4879 llvm::Constant *Init = llvm::ConstantStruct::get(Values); 4880 GV = new llvm::GlobalVariable(Init->getType(), false, 4881 llvm::GlobalValue::InternalLinkage, 4882 Init, 4883 Name, 4884 &CGM.getModule()); 4885 GV->setSection("__DATA, __objc_const"); 4886 GV->setAlignment( 4887 CGM.getTargetData().getPrefTypeAlignment(Init->getType())); 4888 UsedGlobals.push_back(GV); 4889 return llvm::ConstantExpr::getBitCast(GV, 4890 ObjCTypes.ProtocolListnfABIPtrTy); 4891} 4892 4893/// GetMethodDescriptionConstant - This routine build following meta-data: 4894/// struct _objc_method { 4895/// SEL _cmd; 4896/// char *method_type; 4897/// char *_imp; 4898/// } 4899 4900llvm::Constant * 4901CGObjCNonFragileABIMac::GetMethodDescriptionConstant(const ObjCMethodDecl *MD) { 4902 std::vector<llvm::Constant*> Desc(3); 4903 Desc[0] = llvm::ConstantExpr::getBitCast(GetMethodVarName(MD->getSelector()), 4904 ObjCTypes.SelectorPtrTy); 4905 Desc[1] = GetMethodVarType(MD); 4906 // Protocol methods have no implementation. So, this entry is always NULL. 4907 Desc[2] = llvm::Constant::getNullValue(ObjCTypes.Int8PtrTy); 4908 return llvm::ConstantStruct::get(ObjCTypes.MethodTy, Desc); 4909} 4910 4911/// EmitObjCValueForIvar - Code Gen for nonfragile ivar reference. 4912/// This code gen. amounts to generating code for: 4913/// @code 4914/// (type *)((char *)base + _OBJC_IVAR_$_.ivar; 4915/// @encode 4916/// 4917LValue CGObjCNonFragileABIMac::EmitObjCValueForIvar( 4918 CodeGen::CodeGenFunction &CGF, 4919 QualType ObjectTy, 4920 llvm::Value *BaseValue, 4921 const ObjCIvarDecl *Ivar, 4922 unsigned CVRQualifiers) { 4923 const ObjCInterfaceDecl *ID = ObjectTy->getAsObjCInterfaceType()->getDecl(); 4924 return EmitValueForIvarAtOffset(CGF, ID, BaseValue, Ivar, CVRQualifiers, 4925 EmitIvarOffset(CGF, ID, Ivar)); 4926} 4927 4928llvm::Value *CGObjCNonFragileABIMac::EmitIvarOffset( 4929 CodeGen::CodeGenFunction &CGF, 4930 const ObjCInterfaceDecl *Interface, 4931 const ObjCIvarDecl *Ivar) { 4932 return CGF.Builder.CreateLoad(ObjCIvarOffsetVariable(Interface, Ivar), 4933 false, "ivar"); 4934} 4935 4936CodeGen::RValue CGObjCNonFragileABIMac::EmitMessageSend( 4937 CodeGen::CodeGenFunction &CGF, 4938 QualType ResultType, 4939 Selector Sel, 4940 llvm::Value *Receiver, 4941 QualType Arg0Ty, 4942 bool IsSuper, 4943 const CallArgList &CallArgs) { 4944 // FIXME. Even though IsSuper is passes. This function doese not 4945 // handle calls to 'super' receivers. 4946 CodeGenTypes &Types = CGM.getTypes(); 4947 llvm::Value *Arg0 = Receiver; 4948 if (!IsSuper) 4949 Arg0 = CGF.Builder.CreateBitCast(Arg0, ObjCTypes.ObjectPtrTy, "tmp"); 4950 4951 // Find the message function name. 4952 // FIXME. This is too much work to get the ABI-specific result type 4953 // needed to find the message name. 4954 const CGFunctionInfo &FnInfo = Types.getFunctionInfo(ResultType, 4955 llvm::SmallVector<QualType, 16>()); 4956 llvm::Constant *Fn = 0; 4957 std::string Name("\01l_"); 4958 if (CGM.ReturnTypeUsesSret(FnInfo)) { 4959#if 0 4960 // unlike what is documented. gcc never generates this API!! 4961 if (Receiver->getType() == ObjCTypes.ObjectPtrTy) { 4962 Fn = ObjCTypes.getMessageSendIdStretFixupFn(); 4963 // FIXME. Is there a better way of getting these names. 4964 // They are available in RuntimeFunctions vector pair. 4965 Name += "objc_msgSendId_stret_fixup"; 4966 } 4967 else 4968#endif 4969 if (IsSuper) { 4970 Fn = ObjCTypes.getMessageSendSuper2StretFixupFn(); 4971 Name += "objc_msgSendSuper2_stret_fixup"; 4972 } 4973 else 4974 { 4975 Fn = ObjCTypes.getMessageSendStretFixupFn(); 4976 Name += "objc_msgSend_stret_fixup"; 4977 } 4978 } 4979 else if (!IsSuper && ResultType->isFloatingType()) { 4980 if (const BuiltinType *BT = ResultType->getAsBuiltinType()) { 4981 BuiltinType::Kind k = BT->getKind(); 4982 if (k == BuiltinType::LongDouble) { 4983 Fn = ObjCTypes.getMessageSendFpretFixupFn(); 4984 Name += "objc_msgSend_fpret_fixup"; 4985 } 4986 else { 4987 Fn = ObjCTypes.getMessageSendFixupFn(); 4988 Name += "objc_msgSend_fixup"; 4989 } 4990 } 4991 } 4992 else { 4993#if 0 4994// unlike what is documented. gcc never generates this API!! 4995 if (Receiver->getType() == ObjCTypes.ObjectPtrTy) { 4996 Fn = ObjCTypes.getMessageSendIdFixupFn(); 4997 Name += "objc_msgSendId_fixup"; 4998 } 4999 else 5000#endif 5001 if (IsSuper) { 5002 Fn = ObjCTypes.getMessageSendSuper2FixupFn(); 5003 Name += "objc_msgSendSuper2_fixup"; 5004 } 5005 else 5006 { 5007 Fn = ObjCTypes.getMessageSendFixupFn(); 5008 Name += "objc_msgSend_fixup"; 5009 } 5010 } 5011 assert(Fn && "CGObjCNonFragileABIMac::EmitMessageSend"); 5012 Name += '_'; 5013 std::string SelName(Sel.getAsString()); 5014 // Replace all ':' in selector name with '_' ouch! 5015 for(unsigned i = 0; i < SelName.size(); i++) 5016 if (SelName[i] == ':') 5017 SelName[i] = '_'; 5018 Name += SelName; 5019 llvm::GlobalVariable *GV = CGM.getModule().getGlobalVariable(Name); 5020 if (!GV) { 5021 // Build message ref table entry. 5022 std::vector<llvm::Constant*> Values(2); 5023 Values[0] = Fn; 5024 Values[1] = GetMethodVarName(Sel); 5025 llvm::Constant *Init = llvm::ConstantStruct::get(Values); 5026 GV = new llvm::GlobalVariable(Init->getType(), false, 5027 llvm::GlobalValue::WeakAnyLinkage, 5028 Init, 5029 Name, 5030 &CGM.getModule()); 5031 GV->setVisibility(llvm::GlobalValue::HiddenVisibility); 5032 GV->setAlignment(16); 5033 GV->setSection("__DATA, __objc_msgrefs, coalesced"); 5034 } 5035 llvm::Value *Arg1 = CGF.Builder.CreateBitCast(GV, ObjCTypes.MessageRefPtrTy); 5036 5037 CallArgList ActualArgs; 5038 ActualArgs.push_back(std::make_pair(RValue::get(Arg0), Arg0Ty)); 5039 ActualArgs.push_back(std::make_pair(RValue::get(Arg1), 5040 ObjCTypes.MessageRefCPtrTy)); 5041 ActualArgs.insert(ActualArgs.end(), CallArgs.begin(), CallArgs.end()); 5042 const CGFunctionInfo &FnInfo1 = Types.getFunctionInfo(ResultType, ActualArgs); 5043 llvm::Value *Callee = CGF.Builder.CreateStructGEP(Arg1, 0); 5044 Callee = CGF.Builder.CreateLoad(Callee); 5045 const llvm::FunctionType *FTy = Types.GetFunctionType(FnInfo1, true); 5046 Callee = CGF.Builder.CreateBitCast(Callee, 5047 llvm::PointerType::getUnqual(FTy)); 5048 return CGF.EmitCall(FnInfo1, Callee, ActualArgs); 5049} 5050 5051/// Generate code for a message send expression in the nonfragile abi. 5052CodeGen::RValue CGObjCNonFragileABIMac::GenerateMessageSend( 5053 CodeGen::CodeGenFunction &CGF, 5054 QualType ResultType, 5055 Selector Sel, 5056 llvm::Value *Receiver, 5057 bool IsClassMessage, 5058 const CallArgList &CallArgs) { 5059 return EmitMessageSend(CGF, ResultType, Sel, 5060 Receiver, CGF.getContext().getObjCIdType(), 5061 false, CallArgs); 5062} 5063 5064llvm::GlobalVariable * 5065CGObjCNonFragileABIMac::GetClassGlobal(const std::string &Name) { 5066 llvm::GlobalVariable *GV = CGM.getModule().getGlobalVariable(Name); 5067 5068 if (!GV) { 5069 GV = new llvm::GlobalVariable(ObjCTypes.ClassnfABITy, false, 5070 llvm::GlobalValue::ExternalLinkage, 5071 0, Name, &CGM.getModule()); 5072 } 5073 5074 return GV; 5075} 5076 5077llvm::Value *CGObjCNonFragileABIMac::EmitClassRef(CGBuilderTy &Builder, 5078 const ObjCInterfaceDecl *ID) { 5079 llvm::GlobalVariable *&Entry = ClassReferences[ID->getIdentifier()]; 5080 5081 if (!Entry) { 5082 std::string ClassName(getClassSymbolPrefix() + ID->getNameAsString()); 5083 llvm::GlobalVariable *ClassGV = GetClassGlobal(ClassName); 5084 Entry = 5085 new llvm::GlobalVariable(ObjCTypes.ClassnfABIPtrTy, false, 5086 llvm::GlobalValue::InternalLinkage, 5087 ClassGV, 5088 "\01L_OBJC_CLASSLIST_REFERENCES_$_", 5089 &CGM.getModule()); 5090 Entry->setAlignment( 5091 CGM.getTargetData().getPrefTypeAlignment( 5092 ObjCTypes.ClassnfABIPtrTy)); 5093 Entry->setSection("__DATA, __objc_classrefs, regular, no_dead_strip"); 5094 UsedGlobals.push_back(Entry); 5095 } 5096 5097 return Builder.CreateLoad(Entry, false, "tmp"); 5098} 5099 5100llvm::Value * 5101CGObjCNonFragileABIMac::EmitSuperClassRef(CGBuilderTy &Builder, 5102 const ObjCInterfaceDecl *ID) { 5103 llvm::GlobalVariable *&Entry = SuperClassReferences[ID->getIdentifier()]; 5104 5105 if (!Entry) { 5106 std::string ClassName(getClassSymbolPrefix() + ID->getNameAsString()); 5107 llvm::GlobalVariable *ClassGV = GetClassGlobal(ClassName); 5108 Entry = 5109 new llvm::GlobalVariable(ObjCTypes.ClassnfABIPtrTy, false, 5110 llvm::GlobalValue::InternalLinkage, 5111 ClassGV, 5112 "\01L_OBJC_CLASSLIST_SUP_REFS_$_", 5113 &CGM.getModule()); 5114 Entry->setAlignment( 5115 CGM.getTargetData().getPrefTypeAlignment( 5116 ObjCTypes.ClassnfABIPtrTy)); 5117 Entry->setSection("__DATA, __objc_superrefs, regular, no_dead_strip"); 5118 UsedGlobals.push_back(Entry); 5119 } 5120 5121 return Builder.CreateLoad(Entry, false, "tmp"); 5122} 5123 5124/// EmitMetaClassRef - Return a Value * of the address of _class_t 5125/// meta-data 5126/// 5127llvm::Value *CGObjCNonFragileABIMac::EmitMetaClassRef(CGBuilderTy &Builder, 5128 const ObjCInterfaceDecl *ID) { 5129 llvm::GlobalVariable * &Entry = MetaClassReferences[ID->getIdentifier()]; 5130 if (Entry) 5131 return Builder.CreateLoad(Entry, false, "tmp"); 5132 5133 std::string MetaClassName(getMetaclassSymbolPrefix() + ID->getNameAsString()); 5134 llvm::GlobalVariable *MetaClassGV = GetClassGlobal(MetaClassName); 5135 Entry = 5136 new llvm::GlobalVariable(ObjCTypes.ClassnfABIPtrTy, false, 5137 llvm::GlobalValue::InternalLinkage, 5138 MetaClassGV, 5139 "\01L_OBJC_CLASSLIST_SUP_REFS_$_", 5140 &CGM.getModule()); 5141 Entry->setAlignment( 5142 CGM.getTargetData().getPrefTypeAlignment( 5143 ObjCTypes.ClassnfABIPtrTy)); 5144 5145 Entry->setSection("__DATA, __objc_superrefs, regular, no_dead_strip"); 5146 UsedGlobals.push_back(Entry); 5147 5148 return Builder.CreateLoad(Entry, false, "tmp"); 5149} 5150 5151/// GetClass - Return a reference to the class for the given interface 5152/// decl. 5153llvm::Value *CGObjCNonFragileABIMac::GetClass(CGBuilderTy &Builder, 5154 const ObjCInterfaceDecl *ID) { 5155 return EmitClassRef(Builder, ID); 5156} 5157 5158/// Generates a message send where the super is the receiver. This is 5159/// a message send to self with special delivery semantics indicating 5160/// which class's method should be called. 5161CodeGen::RValue 5162CGObjCNonFragileABIMac::GenerateMessageSendSuper(CodeGen::CodeGenFunction &CGF, 5163 QualType ResultType, 5164 Selector Sel, 5165 const ObjCInterfaceDecl *Class, 5166 bool isCategoryImpl, 5167 llvm::Value *Receiver, 5168 bool IsClassMessage, 5169 const CodeGen::CallArgList &CallArgs) { 5170 // ... 5171 // Create and init a super structure; this is a (receiver, class) 5172 // pair we will pass to objc_msgSendSuper. 5173 llvm::Value *ObjCSuper = 5174 CGF.Builder.CreateAlloca(ObjCTypes.SuperTy, 0, "objc_super"); 5175 5176 llvm::Value *ReceiverAsObject = 5177 CGF.Builder.CreateBitCast(Receiver, ObjCTypes.ObjectPtrTy); 5178 CGF.Builder.CreateStore(ReceiverAsObject, 5179 CGF.Builder.CreateStructGEP(ObjCSuper, 0)); 5180 5181 // If this is a class message the metaclass is passed as the target. 5182 llvm::Value *Target; 5183 if (IsClassMessage) { 5184 if (isCategoryImpl) { 5185 // Message sent to "super' in a class method defined in 5186 // a category implementation. 5187 Target = EmitClassRef(CGF.Builder, Class); 5188 Target = CGF.Builder.CreateStructGEP(Target, 0); 5189 Target = CGF.Builder.CreateLoad(Target); 5190 } 5191 else 5192 Target = EmitMetaClassRef(CGF.Builder, Class); 5193 } 5194 else 5195 Target = EmitSuperClassRef(CGF.Builder, Class); 5196 5197 // FIXME: We shouldn't need to do this cast, rectify the ASTContext 5198 // and ObjCTypes types. 5199 const llvm::Type *ClassTy = 5200 CGM.getTypes().ConvertType(CGF.getContext().getObjCClassType()); 5201 Target = CGF.Builder.CreateBitCast(Target, ClassTy); 5202 CGF.Builder.CreateStore(Target, 5203 CGF.Builder.CreateStructGEP(ObjCSuper, 1)); 5204 5205 return EmitMessageSend(CGF, ResultType, Sel, 5206 ObjCSuper, ObjCTypes.SuperPtrCTy, 5207 true, CallArgs); 5208} 5209 5210llvm::Value *CGObjCNonFragileABIMac::EmitSelector(CGBuilderTy &Builder, 5211 Selector Sel) { 5212 llvm::GlobalVariable *&Entry = SelectorReferences[Sel]; 5213 5214 if (!Entry) { 5215 llvm::Constant *Casted = 5216 llvm::ConstantExpr::getBitCast(GetMethodVarName(Sel), 5217 ObjCTypes.SelectorPtrTy); 5218 Entry = 5219 new llvm::GlobalVariable(ObjCTypes.SelectorPtrTy, false, 5220 llvm::GlobalValue::InternalLinkage, 5221 Casted, "\01L_OBJC_SELECTOR_REFERENCES_", 5222 &CGM.getModule()); 5223 Entry->setSection("__DATA,__objc_selrefs,literal_pointers,no_dead_strip"); 5224 UsedGlobals.push_back(Entry); 5225 } 5226 5227 return Builder.CreateLoad(Entry, false, "tmp"); 5228} 5229/// EmitObjCIvarAssign - Code gen for assigning to a __strong object. 5230/// objc_assign_ivar (id src, id *dst) 5231/// 5232void CGObjCNonFragileABIMac::EmitObjCIvarAssign(CodeGen::CodeGenFunction &CGF, 5233 llvm::Value *src, llvm::Value *dst) 5234{ 5235 const llvm::Type * SrcTy = src->getType(); 5236 if (!isa<llvm::PointerType>(SrcTy)) { 5237 unsigned Size = CGM.getTargetData().getTypePaddedSize(SrcTy); 5238 assert(Size <= 8 && "does not support size > 8"); 5239 src = (Size == 4 ? CGF.Builder.CreateBitCast(src, ObjCTypes.IntTy) 5240 : CGF.Builder.CreateBitCast(src, ObjCTypes.LongTy)); 5241 src = CGF.Builder.CreateIntToPtr(src, ObjCTypes.Int8PtrTy); 5242 } 5243 src = CGF.Builder.CreateBitCast(src, ObjCTypes.ObjectPtrTy); 5244 dst = CGF.Builder.CreateBitCast(dst, ObjCTypes.PtrObjectPtrTy); 5245 CGF.Builder.CreateCall2(ObjCTypes.getGcAssignIvarFn(), 5246 src, dst, "assignivar"); 5247 return; 5248} 5249 5250/// EmitObjCStrongCastAssign - Code gen for assigning to a __strong cast object. 5251/// objc_assign_strongCast (id src, id *dst) 5252/// 5253void CGObjCNonFragileABIMac::EmitObjCStrongCastAssign( 5254 CodeGen::CodeGenFunction &CGF, 5255 llvm::Value *src, llvm::Value *dst) 5256{ 5257 const llvm::Type * SrcTy = src->getType(); 5258 if (!isa<llvm::PointerType>(SrcTy)) { 5259 unsigned Size = CGM.getTargetData().getTypePaddedSize(SrcTy); 5260 assert(Size <= 8 && "does not support size > 8"); 5261 src = (Size == 4 ? CGF.Builder.CreateBitCast(src, ObjCTypes.IntTy) 5262 : CGF.Builder.CreateBitCast(src, ObjCTypes.LongTy)); 5263 src = CGF.Builder.CreateIntToPtr(src, ObjCTypes.Int8PtrTy); 5264 } 5265 src = CGF.Builder.CreateBitCast(src, ObjCTypes.ObjectPtrTy); 5266 dst = CGF.Builder.CreateBitCast(dst, ObjCTypes.PtrObjectPtrTy); 5267 CGF.Builder.CreateCall2(ObjCTypes.getGcAssignStrongCastFn(), 5268 src, dst, "weakassign"); 5269 return; 5270} 5271 5272/// EmitObjCWeakRead - Code gen for loading value of a __weak 5273/// object: objc_read_weak (id *src) 5274/// 5275llvm::Value * CGObjCNonFragileABIMac::EmitObjCWeakRead( 5276 CodeGen::CodeGenFunction &CGF, 5277 llvm::Value *AddrWeakObj) 5278{ 5279 const llvm::Type* DestTy = 5280 cast<llvm::PointerType>(AddrWeakObj->getType())->getElementType(); 5281 AddrWeakObj = CGF.Builder.CreateBitCast(AddrWeakObj, ObjCTypes.PtrObjectPtrTy); 5282 llvm::Value *read_weak = CGF.Builder.CreateCall(ObjCTypes.getGcReadWeakFn(), 5283 AddrWeakObj, "weakread"); 5284 read_weak = CGF.Builder.CreateBitCast(read_weak, DestTy); 5285 return read_weak; 5286} 5287 5288/// EmitObjCWeakAssign - Code gen for assigning to a __weak object. 5289/// objc_assign_weak (id src, id *dst) 5290/// 5291void CGObjCNonFragileABIMac::EmitObjCWeakAssign(CodeGen::CodeGenFunction &CGF, 5292 llvm::Value *src, llvm::Value *dst) 5293{ 5294 const llvm::Type * SrcTy = src->getType(); 5295 if (!isa<llvm::PointerType>(SrcTy)) { 5296 unsigned Size = CGM.getTargetData().getTypePaddedSize(SrcTy); 5297 assert(Size <= 8 && "does not support size > 8"); 5298 src = (Size == 4 ? CGF.Builder.CreateBitCast(src, ObjCTypes.IntTy) 5299 : CGF.Builder.CreateBitCast(src, ObjCTypes.LongTy)); 5300 src = CGF.Builder.CreateIntToPtr(src, ObjCTypes.Int8PtrTy); 5301 } 5302 src = CGF.Builder.CreateBitCast(src, ObjCTypes.ObjectPtrTy); 5303 dst = CGF.Builder.CreateBitCast(dst, ObjCTypes.PtrObjectPtrTy); 5304 CGF.Builder.CreateCall2(ObjCTypes.getGcAssignWeakFn(), 5305 src, dst, "weakassign"); 5306 return; 5307} 5308 5309/// EmitObjCGlobalAssign - Code gen for assigning to a __strong object. 5310/// objc_assign_global (id src, id *dst) 5311/// 5312void CGObjCNonFragileABIMac::EmitObjCGlobalAssign(CodeGen::CodeGenFunction &CGF, 5313 llvm::Value *src, llvm::Value *dst) 5314{ 5315 const llvm::Type * SrcTy = src->getType(); 5316 if (!isa<llvm::PointerType>(SrcTy)) { 5317 unsigned Size = CGM.getTargetData().getTypePaddedSize(SrcTy); 5318 assert(Size <= 8 && "does not support size > 8"); 5319 src = (Size == 4 ? CGF.Builder.CreateBitCast(src, ObjCTypes.IntTy) 5320 : CGF.Builder.CreateBitCast(src, ObjCTypes.LongTy)); 5321 src = CGF.Builder.CreateIntToPtr(src, ObjCTypes.Int8PtrTy); 5322 } 5323 src = CGF.Builder.CreateBitCast(src, ObjCTypes.ObjectPtrTy); 5324 dst = CGF.Builder.CreateBitCast(dst, ObjCTypes.PtrObjectPtrTy); 5325 CGF.Builder.CreateCall2(ObjCTypes.getGcAssignGlobalFn(), 5326 src, dst, "globalassign"); 5327 return; 5328} 5329 5330void 5331CGObjCNonFragileABIMac::EmitTryOrSynchronizedStmt(CodeGen::CodeGenFunction &CGF, 5332 const Stmt &S) { 5333 bool isTry = isa<ObjCAtTryStmt>(S); 5334 llvm::BasicBlock *TryBlock = CGF.createBasicBlock("try"); 5335 llvm::BasicBlock *PrevLandingPad = CGF.getInvokeDest(); 5336 llvm::BasicBlock *TryHandler = CGF.createBasicBlock("try.handler"); 5337 llvm::BasicBlock *FinallyBlock = CGF.createBasicBlock("finally"); 5338 llvm::BasicBlock *FinallyRethrow = CGF.createBasicBlock("finally.throw"); 5339 llvm::BasicBlock *FinallyEnd = CGF.createBasicBlock("finally.end"); 5340 5341 // For @synchronized, call objc_sync_enter(sync.expr). The 5342 // evaluation of the expression must occur before we enter the 5343 // @synchronized. We can safely avoid a temp here because jumps into 5344 // @synchronized are illegal & this will dominate uses. 5345 llvm::Value *SyncArg = 0; 5346 if (!isTry) { 5347 SyncArg = 5348 CGF.EmitScalarExpr(cast<ObjCAtSynchronizedStmt>(S).getSynchExpr()); 5349 SyncArg = CGF.Builder.CreateBitCast(SyncArg, ObjCTypes.ObjectPtrTy); 5350 CGF.Builder.CreateCall(ObjCTypes.getSyncEnterFn(), SyncArg); 5351 } 5352 5353 // Push an EH context entry, used for handling rethrows and jumps 5354 // through finally. 5355 CGF.PushCleanupBlock(FinallyBlock); 5356 5357 CGF.setInvokeDest(TryHandler); 5358 5359 CGF.EmitBlock(TryBlock); 5360 CGF.EmitStmt(isTry ? cast<ObjCAtTryStmt>(S).getTryBody() 5361 : cast<ObjCAtSynchronizedStmt>(S).getSynchBody()); 5362 CGF.EmitBranchThroughCleanup(FinallyEnd); 5363 5364 // Emit the exception handler. 5365 5366 CGF.EmitBlock(TryHandler); 5367 5368 llvm::Value *llvm_eh_exception = 5369 CGF.CGM.getIntrinsic(llvm::Intrinsic::eh_exception); 5370 llvm::Value *llvm_eh_selector_i64 = 5371 CGF.CGM.getIntrinsic(llvm::Intrinsic::eh_selector_i64); 5372 llvm::Value *llvm_eh_typeid_for_i64 = 5373 CGF.CGM.getIntrinsic(llvm::Intrinsic::eh_typeid_for_i64); 5374 llvm::Value *Exc = CGF.Builder.CreateCall(llvm_eh_exception, "exc"); 5375 llvm::Value *RethrowPtr = CGF.CreateTempAlloca(Exc->getType(), "_rethrow"); 5376 5377 llvm::SmallVector<llvm::Value*, 8> SelectorArgs; 5378 SelectorArgs.push_back(Exc); 5379 SelectorArgs.push_back(ObjCTypes.getEHPersonalityPtr()); 5380 5381 // Construct the lists of (type, catch body) to handle. 5382 llvm::SmallVector<std::pair<const ParmVarDecl*, const Stmt*>, 8> Handlers; 5383 bool HasCatchAll = false; 5384 if (isTry) { 5385 if (const ObjCAtCatchStmt* CatchStmt = 5386 cast<ObjCAtTryStmt>(S).getCatchStmts()) { 5387 for (; CatchStmt; CatchStmt = CatchStmt->getNextCatchStmt()) { 5388 const ParmVarDecl *CatchDecl = CatchStmt->getCatchParamDecl(); 5389 Handlers.push_back(std::make_pair(CatchDecl, CatchStmt->getCatchBody())); 5390 5391 // catch(...) always matches. 5392 if (!CatchDecl) { 5393 // Use i8* null here to signal this is a catch all, not a cleanup. 5394 llvm::Value *Null = llvm::Constant::getNullValue(ObjCTypes.Int8PtrTy); 5395 SelectorArgs.push_back(Null); 5396 HasCatchAll = true; 5397 break; 5398 } 5399 5400 if (CGF.getContext().isObjCIdType(CatchDecl->getType()) || 5401 CatchDecl->getType()->isObjCQualifiedIdType()) { 5402 llvm::Value *IDEHType = 5403 CGM.getModule().getGlobalVariable("OBJC_EHTYPE_id"); 5404 if (!IDEHType) 5405 IDEHType = 5406 new llvm::GlobalVariable(ObjCTypes.EHTypeTy, false, 5407 llvm::GlobalValue::ExternalLinkage, 5408 0, "OBJC_EHTYPE_id", &CGM.getModule()); 5409 SelectorArgs.push_back(IDEHType); 5410 HasCatchAll = true; 5411 break; 5412 } 5413 5414 // All other types should be Objective-C interface pointer types. 5415 const PointerType *PT = CatchDecl->getType()->getAsPointerType(); 5416 assert(PT && "Invalid @catch type."); 5417 const ObjCInterfaceType *IT = 5418 PT->getPointeeType()->getAsObjCInterfaceType(); 5419 assert(IT && "Invalid @catch type."); 5420 llvm::Value *EHType = GetInterfaceEHType(IT->getDecl(), false); 5421 SelectorArgs.push_back(EHType); 5422 } 5423 } 5424 } 5425 5426 // We use a cleanup unless there was already a catch all. 5427 if (!HasCatchAll) { 5428 SelectorArgs.push_back(llvm::ConstantInt::get(llvm::Type::Int32Ty, 0)); 5429 Handlers.push_back(std::make_pair((const ParmVarDecl*) 0, (const Stmt*) 0)); 5430 } 5431 5432 llvm::Value *Selector = 5433 CGF.Builder.CreateCall(llvm_eh_selector_i64, 5434 SelectorArgs.begin(), SelectorArgs.end(), 5435 "selector"); 5436 for (unsigned i = 0, e = Handlers.size(); i != e; ++i) { 5437 const ParmVarDecl *CatchParam = Handlers[i].first; 5438 const Stmt *CatchBody = Handlers[i].second; 5439 5440 llvm::BasicBlock *Next = 0; 5441 5442 // The last handler always matches. 5443 if (i + 1 != e) { 5444 assert(CatchParam && "Only last handler can be a catch all."); 5445 5446 llvm::BasicBlock *Match = CGF.createBasicBlock("match"); 5447 Next = CGF.createBasicBlock("catch.next"); 5448 llvm::Value *Id = 5449 CGF.Builder.CreateCall(llvm_eh_typeid_for_i64, 5450 CGF.Builder.CreateBitCast(SelectorArgs[i+2], 5451 ObjCTypes.Int8PtrTy)); 5452 CGF.Builder.CreateCondBr(CGF.Builder.CreateICmpEQ(Selector, Id), 5453 Match, Next); 5454 5455 CGF.EmitBlock(Match); 5456 } 5457 5458 if (CatchBody) { 5459 llvm::BasicBlock *MatchEnd = CGF.createBasicBlock("match.end"); 5460 llvm::BasicBlock *MatchHandler = CGF.createBasicBlock("match.handler"); 5461 5462 // Cleanups must call objc_end_catch. 5463 // 5464 // FIXME: It seems incorrect for objc_begin_catch to be inside 5465 // this context, but this matches gcc. 5466 CGF.PushCleanupBlock(MatchEnd); 5467 CGF.setInvokeDest(MatchHandler); 5468 5469 llvm::Value *ExcObject = 5470 CGF.Builder.CreateCall(ObjCTypes.getObjCBeginCatchFn(), Exc); 5471 5472 // Bind the catch parameter if it exists. 5473 if (CatchParam) { 5474 ExcObject = 5475 CGF.Builder.CreateBitCast(ExcObject, 5476 CGF.ConvertType(CatchParam->getType())); 5477 // CatchParam is a ParmVarDecl because of the grammar 5478 // construction used to handle this, but for codegen purposes 5479 // we treat this as a local decl. 5480 CGF.EmitLocalBlockVarDecl(*CatchParam); 5481 CGF.Builder.CreateStore(ExcObject, CGF.GetAddrOfLocalVar(CatchParam)); 5482 } 5483 5484 CGF.ObjCEHValueStack.push_back(ExcObject); 5485 CGF.EmitStmt(CatchBody); 5486 CGF.ObjCEHValueStack.pop_back(); 5487 5488 CGF.EmitBranchThroughCleanup(FinallyEnd); 5489 5490 CGF.EmitBlock(MatchHandler); 5491 5492 llvm::Value *Exc = CGF.Builder.CreateCall(llvm_eh_exception, "exc"); 5493 // We are required to emit this call to satisfy LLVM, even 5494 // though we don't use the result. 5495 llvm::SmallVector<llvm::Value*, 8> Args; 5496 Args.push_back(Exc); 5497 Args.push_back(ObjCTypes.getEHPersonalityPtr()); 5498 Args.push_back(llvm::ConstantInt::get(llvm::Type::Int32Ty, 5499 0)); 5500 CGF.Builder.CreateCall(llvm_eh_selector_i64, Args.begin(), Args.end()); 5501 CGF.Builder.CreateStore(Exc, RethrowPtr); 5502 CGF.EmitBranchThroughCleanup(FinallyRethrow); 5503 5504 CodeGenFunction::CleanupBlockInfo Info = CGF.PopCleanupBlock(); 5505 5506 CGF.EmitBlock(MatchEnd); 5507 5508 // Unfortunately, we also have to generate another EH frame here 5509 // in case this throws. 5510 llvm::BasicBlock *MatchEndHandler = 5511 CGF.createBasicBlock("match.end.handler"); 5512 llvm::BasicBlock *Cont = CGF.createBasicBlock("invoke.cont"); 5513 CGF.Builder.CreateInvoke(ObjCTypes.getObjCEndCatchFn(), 5514 Cont, MatchEndHandler, 5515 Args.begin(), Args.begin()); 5516 5517 CGF.EmitBlock(Cont); 5518 if (Info.SwitchBlock) 5519 CGF.EmitBlock(Info.SwitchBlock); 5520 if (Info.EndBlock) 5521 CGF.EmitBlock(Info.EndBlock); 5522 5523 CGF.EmitBlock(MatchEndHandler); 5524 Exc = CGF.Builder.CreateCall(llvm_eh_exception, "exc"); 5525 // We are required to emit this call to satisfy LLVM, even 5526 // though we don't use the result. 5527 Args.clear(); 5528 Args.push_back(Exc); 5529 Args.push_back(ObjCTypes.getEHPersonalityPtr()); 5530 Args.push_back(llvm::ConstantInt::get(llvm::Type::Int32Ty, 5531 0)); 5532 CGF.Builder.CreateCall(llvm_eh_selector_i64, Args.begin(), Args.end()); 5533 CGF.Builder.CreateStore(Exc, RethrowPtr); 5534 CGF.EmitBranchThroughCleanup(FinallyRethrow); 5535 5536 if (Next) 5537 CGF.EmitBlock(Next); 5538 } else { 5539 assert(!Next && "catchup should be last handler."); 5540 5541 CGF.Builder.CreateStore(Exc, RethrowPtr); 5542 CGF.EmitBranchThroughCleanup(FinallyRethrow); 5543 } 5544 } 5545 5546 // Pop the cleanup entry, the @finally is outside this cleanup 5547 // scope. 5548 CodeGenFunction::CleanupBlockInfo Info = CGF.PopCleanupBlock(); 5549 CGF.setInvokeDest(PrevLandingPad); 5550 5551 CGF.EmitBlock(FinallyBlock); 5552 5553 if (isTry) { 5554 if (const ObjCAtFinallyStmt* FinallyStmt = 5555 cast<ObjCAtTryStmt>(S).getFinallyStmt()) 5556 CGF.EmitStmt(FinallyStmt->getFinallyBody()); 5557 } else { 5558 // Emit 'objc_sync_exit(expr)' as finally's sole statement for 5559 // @synchronized. 5560 CGF.Builder.CreateCall(ObjCTypes.getSyncExitFn(), SyncArg); 5561 } 5562 5563 if (Info.SwitchBlock) 5564 CGF.EmitBlock(Info.SwitchBlock); 5565 if (Info.EndBlock) 5566 CGF.EmitBlock(Info.EndBlock); 5567 5568 // Branch around the rethrow code. 5569 CGF.EmitBranch(FinallyEnd); 5570 5571 CGF.EmitBlock(FinallyRethrow); 5572 CGF.Builder.CreateCall(ObjCTypes.getUnwindResumeOrRethrowFn(), 5573 CGF.Builder.CreateLoad(RethrowPtr)); 5574 CGF.Builder.CreateUnreachable(); 5575 5576 CGF.EmitBlock(FinallyEnd); 5577} 5578 5579/// EmitThrowStmt - Generate code for a throw statement. 5580void CGObjCNonFragileABIMac::EmitThrowStmt(CodeGen::CodeGenFunction &CGF, 5581 const ObjCAtThrowStmt &S) { 5582 llvm::Value *Exception; 5583 if (const Expr *ThrowExpr = S.getThrowExpr()) { 5584 Exception = CGF.EmitScalarExpr(ThrowExpr); 5585 } else { 5586 assert((!CGF.ObjCEHValueStack.empty() && CGF.ObjCEHValueStack.back()) && 5587 "Unexpected rethrow outside @catch block."); 5588 Exception = CGF.ObjCEHValueStack.back(); 5589 } 5590 5591 llvm::Value *ExceptionAsObject = 5592 CGF.Builder.CreateBitCast(Exception, ObjCTypes.ObjectPtrTy, "tmp"); 5593 llvm::BasicBlock *InvokeDest = CGF.getInvokeDest(); 5594 if (InvokeDest) { 5595 llvm::BasicBlock *Cont = CGF.createBasicBlock("invoke.cont"); 5596 CGF.Builder.CreateInvoke(ObjCTypes.getExceptionThrowFn(), 5597 Cont, InvokeDest, 5598 &ExceptionAsObject, &ExceptionAsObject + 1); 5599 CGF.EmitBlock(Cont); 5600 } else 5601 CGF.Builder.CreateCall(ObjCTypes.getExceptionThrowFn(), ExceptionAsObject); 5602 CGF.Builder.CreateUnreachable(); 5603 5604 // Clear the insertion point to indicate we are in unreachable code. 5605 CGF.Builder.ClearInsertionPoint(); 5606} 5607 5608llvm::Value * 5609CGObjCNonFragileABIMac::GetInterfaceEHType(const ObjCInterfaceDecl *ID, 5610 bool ForDefinition) { 5611 llvm::GlobalVariable * &Entry = EHTypeReferences[ID->getIdentifier()]; 5612 5613 // If we don't need a definition, return the entry if found or check 5614 // if we use an external reference. 5615 if (!ForDefinition) { 5616 if (Entry) 5617 return Entry; 5618 5619 // If this type (or a super class) has the __objc_exception__ 5620 // attribute, emit an external reference. 5621 if (hasObjCExceptionAttribute(ID)) 5622 return Entry = 5623 new llvm::GlobalVariable(ObjCTypes.EHTypeTy, false, 5624 llvm::GlobalValue::ExternalLinkage, 5625 0, 5626 (std::string("OBJC_EHTYPE_$_") + 5627 ID->getIdentifier()->getName()), 5628 &CGM.getModule()); 5629 } 5630 5631 // Otherwise we need to either make a new entry or fill in the 5632 // initializer. 5633 assert((!Entry || !Entry->hasInitializer()) && "Duplicate EHType definition"); 5634 std::string ClassName(getClassSymbolPrefix() + ID->getNameAsString()); 5635 std::string VTableName = "objc_ehtype_vtable"; 5636 llvm::GlobalVariable *VTableGV = 5637 CGM.getModule().getGlobalVariable(VTableName); 5638 if (!VTableGV) 5639 VTableGV = new llvm::GlobalVariable(ObjCTypes.Int8PtrTy, false, 5640 llvm::GlobalValue::ExternalLinkage, 5641 0, VTableName, &CGM.getModule()); 5642 5643 llvm::Value *VTableIdx = llvm::ConstantInt::get(llvm::Type::Int32Ty, 2); 5644 5645 std::vector<llvm::Constant*> Values(3); 5646 Values[0] = llvm::ConstantExpr::getGetElementPtr(VTableGV, &VTableIdx, 1); 5647 Values[1] = GetClassName(ID->getIdentifier()); 5648 Values[2] = GetClassGlobal(ClassName); 5649 llvm::Constant *Init = llvm::ConstantStruct::get(ObjCTypes.EHTypeTy, Values); 5650 5651 if (Entry) { 5652 Entry->setInitializer(Init); 5653 } else { 5654 Entry = new llvm::GlobalVariable(ObjCTypes.EHTypeTy, false, 5655 llvm::GlobalValue::WeakAnyLinkage, 5656 Init, 5657 (std::string("OBJC_EHTYPE_$_") + 5658 ID->getIdentifier()->getName()), 5659 &CGM.getModule()); 5660 } 5661 5662 if (CGM.getLangOptions().getVisibilityMode() == LangOptions::Hidden) 5663 Entry->setVisibility(llvm::GlobalValue::HiddenVisibility); 5664 Entry->setAlignment(8); 5665 5666 if (ForDefinition) { 5667 Entry->setSection("__DATA,__objc_const"); 5668 Entry->setLinkage(llvm::GlobalValue::ExternalLinkage); 5669 } else { 5670 Entry->setSection("__DATA,__datacoal_nt,coalesced"); 5671 } 5672 5673 return Entry; 5674} 5675 5676/* *** */ 5677 5678CodeGen::CGObjCRuntime * 5679CodeGen::CreateMacObjCRuntime(CodeGen::CodeGenModule &CGM) { 5680 return new CGObjCMac(CGM); 5681} 5682 5683CodeGen::CGObjCRuntime * 5684CodeGen::CreateMacNonFragileABIObjCRuntime(CodeGen::CodeGenModule &CGM) { 5685 return new CGObjCNonFragileABIMac(CGM); 5686} 5687