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