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