clang API Documentation

CGObjCRuntime.h
Go to the documentation of this file.
00001 //===----- CGObjCRuntime.h - Interface to ObjC Runtimes ---------*- C++ -*-===//
00002 //
00003 //                     The LLVM Compiler Infrastructure
00004 //
00005 // This file is distributed under the University of Illinois Open Source
00006 // License. See LICENSE.TXT for details.
00007 //
00008 //===----------------------------------------------------------------------===//
00009 //
00010 // This provides an abstract class for Objective-C code generation.  Concrete
00011 // subclasses of this implement code generation for specific Objective-C
00012 // runtime libraries.
00013 //
00014 //===----------------------------------------------------------------------===//
00015 
00016 #ifndef LLVM_CLANG_LIB_CODEGEN_CGOBJCRUNTIME_H
00017 #define LLVM_CLANG_LIB_CODEGEN_CGOBJCRUNTIME_H
00018 #include "CGBuilder.h"
00019 #include "CGCall.h"
00020 #include "CGValue.h"
00021 #include "clang/AST/DeclObjC.h"
00022 #include "clang/Basic/IdentifierTable.h" // Selector
00023 
00024 namespace llvm {
00025   class Constant;
00026   class Function;
00027   class Module;
00028   class StructLayout;
00029   class StructType;
00030   class Type;
00031   class Value;
00032 }
00033 
00034 namespace clang {
00035 namespace CodeGen {
00036   class CodeGenFunction;
00037 }
00038 
00039   class FieldDecl;
00040   class ObjCAtTryStmt;
00041   class ObjCAtThrowStmt;
00042   class ObjCAtSynchronizedStmt;
00043   class ObjCContainerDecl;
00044   class ObjCCategoryImplDecl;
00045   class ObjCImplementationDecl;
00046   class ObjCInterfaceDecl;
00047   class ObjCMessageExpr;
00048   class ObjCMethodDecl;
00049   class ObjCProtocolDecl;
00050   class Selector;
00051   class ObjCIvarDecl;
00052   class ObjCStringLiteral;
00053   class BlockDeclRefExpr;
00054 
00055 namespace CodeGen {
00056   class CodeGenModule;
00057   class CGBlockInfo;
00058 
00059 // FIXME: Several methods should be pure virtual but aren't to avoid the
00060 // partially-implemented subclass breaking.
00061 
00062 /// Implements runtime-specific code generation functions.
00063 class CGObjCRuntime {
00064 protected:
00065   CodeGen::CodeGenModule &CGM;
00066   CGObjCRuntime(CodeGen::CodeGenModule &CGM) : CGM(CGM) {}
00067 
00068   // Utility functions for unified ivar access. These need to
00069   // eventually be folded into other places (the structure layout
00070   // code).
00071 
00072   /// Compute an offset to the given ivar, suitable for passing to
00073   /// EmitValueForIvarAtOffset.  Note that the correct handling of
00074   /// bit-fields is carefully coordinated by these two, use caution!
00075   ///
00076   /// The latter overload is suitable for computing the offset of a
00077   /// sythesized ivar.
00078   uint64_t ComputeIvarBaseOffset(CodeGen::CodeGenModule &CGM,
00079                                  const ObjCInterfaceDecl *OID,
00080                                  const ObjCIvarDecl *Ivar);
00081   uint64_t ComputeIvarBaseOffset(CodeGen::CodeGenModule &CGM,
00082                                  const ObjCImplementationDecl *OID,
00083                                  const ObjCIvarDecl *Ivar);
00084 
00085   LValue EmitValueForIvarAtOffset(CodeGen::CodeGenFunction &CGF,
00086                                   const ObjCInterfaceDecl *OID,
00087                                   llvm::Value *BaseValue,
00088                                   const ObjCIvarDecl *Ivar,
00089                                   unsigned CVRQualifiers,
00090                                   llvm::Value *Offset);
00091   /// Emits a try / catch statement.  This function is intended to be called by
00092   /// subclasses, and provides a generic mechanism for generating these, which
00093   /// should be usable by all runtimes.  The caller must provide the functions
00094   /// to call when entering and exiting a \@catch() block, and the function
00095   /// used to rethrow exceptions.  If the begin and end catch functions are
00096   /// NULL, then the function assumes that the EH personality function provides
00097   /// the thrown object directly.
00098   void EmitTryCatchStmt(CodeGenFunction &CGF,
00099                         const ObjCAtTryStmt &S,
00100                         llvm::Constant *beginCatchFn,
00101                         llvm::Constant *endCatchFn,
00102                         llvm::Constant *exceptionRethrowFn);
00103   /// Emits an \@synchronize() statement, using the \p syncEnterFn and
00104   /// \p syncExitFn arguments as the functions called to lock and unlock
00105   /// the object.  This function can be called by subclasses that use
00106   /// zero-cost exception handling.
00107   void EmitAtSynchronizedStmt(CodeGenFunction &CGF,
00108                             const ObjCAtSynchronizedStmt &S,
00109                             llvm::Function *syncEnterFn,
00110                             llvm::Function *syncExitFn);
00111 
00112 public:
00113   virtual ~CGObjCRuntime();
00114 
00115   /// Generate the function required to register all Objective-C components in
00116   /// this compilation unit with the runtime library.
00117   virtual llvm::Function *ModuleInitFunction() = 0;
00118 
00119   /// Get a selector for the specified name and type values. The
00120   /// return value should have the LLVM type for pointer-to
00121   /// ASTContext::getObjCSelType().
00122   virtual llvm::Value *GetSelector(CodeGenFunction &CGF,
00123                                    Selector Sel, bool lval=false) = 0;
00124 
00125   /// Get a typed selector.
00126   virtual llvm::Value *GetSelector(CodeGenFunction &CGF,
00127                                    const ObjCMethodDecl *Method) = 0;
00128 
00129   /// Get the type constant to catch for the given ObjC pointer type.
00130   /// This is used externally to implement catching ObjC types in C++.
00131   /// Runtimes which don't support this should add the appropriate
00132   /// error to Sema.
00133   virtual llvm::Constant *GetEHType(QualType T) = 0;
00134 
00135   /// Generate a constant string object.
00136   virtual llvm::Constant *GenerateConstantString(const StringLiteral *) = 0;
00137   
00138   /// Generate a category.  A category contains a list of methods (and
00139   /// accompanying metadata) and a list of protocols.
00140   virtual void GenerateCategory(const ObjCCategoryImplDecl *OCD) = 0;
00141 
00142   /// Generate a class structure for this class.
00143   virtual void GenerateClass(const ObjCImplementationDecl *OID) = 0;
00144 
00145   /// Register an class alias.
00146   virtual void RegisterAlias(const ObjCCompatibleAliasDecl *OAD) = 0;
00147 
00148   /// Generate an Objective-C message send operation.
00149   ///
00150   /// \param Method - The method being called, this may be null if synthesizing
00151   /// a property setter or getter.
00152   virtual CodeGen::RValue
00153   GenerateMessageSend(CodeGen::CodeGenFunction &CGF,
00154                       ReturnValueSlot ReturnSlot,
00155                       QualType ResultType,
00156                       Selector Sel,
00157                       llvm::Value *Receiver,
00158                       const CallArgList &CallArgs,
00159                       const ObjCInterfaceDecl *Class = nullptr,
00160                       const ObjCMethodDecl *Method = nullptr) = 0;
00161 
00162   /// Generate an Objective-C message send operation to the super
00163   /// class initiated in a method for Class and with the given Self
00164   /// object.
00165   ///
00166   /// \param Method - The method being called, this may be null if synthesizing
00167   /// a property setter or getter.
00168   virtual CodeGen::RValue
00169   GenerateMessageSendSuper(CodeGen::CodeGenFunction &CGF,
00170                            ReturnValueSlot ReturnSlot,
00171                            QualType ResultType,
00172                            Selector Sel,
00173                            const ObjCInterfaceDecl *Class,
00174                            bool isCategoryImpl,
00175                            llvm::Value *Self,
00176                            bool IsClassMessage,
00177                            const CallArgList &CallArgs,
00178                            const ObjCMethodDecl *Method = nullptr) = 0;
00179 
00180   /// Emit the code to return the named protocol as an object, as in a
00181   /// \@protocol expression.
00182   virtual llvm::Value *GenerateProtocolRef(CodeGenFunction &CGF,
00183                                            const ObjCProtocolDecl *OPD) = 0;
00184 
00185   /// Generate the named protocol.  Protocols contain method metadata but no
00186   /// implementations.
00187   virtual void GenerateProtocol(const ObjCProtocolDecl *OPD) = 0;
00188 
00189   /// Generate a function preamble for a method with the specified
00190   /// types.
00191 
00192   // FIXME: Current this just generates the Function definition, but really this
00193   // should also be generating the loads of the parameters, as the runtime
00194   // should have full control over how parameters are passed.
00195   virtual llvm::Function *GenerateMethod(const ObjCMethodDecl *OMD,
00196                                          const ObjCContainerDecl *CD) = 0;
00197 
00198   /// Return the runtime function for getting properties.
00199   virtual llvm::Constant *GetPropertyGetFunction() = 0;
00200 
00201   /// Return the runtime function for setting properties.
00202   virtual llvm::Constant *GetPropertySetFunction() = 0;
00203 
00204   /// Return the runtime function for optimized setting properties.
00205   virtual llvm::Constant *GetOptimizedPropertySetFunction(bool atomic, 
00206                                                           bool copy) = 0;
00207 
00208   // API for atomic copying of qualified aggregates in getter.
00209   virtual llvm::Constant *GetGetStructFunction() = 0;
00210   // API for atomic copying of qualified aggregates in setter.
00211   virtual llvm::Constant *GetSetStructFunction() = 0;
00212   /// API for atomic copying of qualified aggregates with non-trivial copy
00213   /// assignment (c++) in setter.
00214   virtual llvm::Constant *GetCppAtomicObjectSetFunction() = 0;
00215   /// API for atomic copying of qualified aggregates with non-trivial copy
00216   /// assignment (c++) in getter.
00217   virtual llvm::Constant *GetCppAtomicObjectGetFunction() = 0;
00218   
00219   /// GetClass - Return a reference to the class for the given
00220   /// interface decl.
00221   virtual llvm::Value *GetClass(CodeGenFunction &CGF,
00222                                 const ObjCInterfaceDecl *OID) = 0;
00223   
00224   
00225   virtual llvm::Value *EmitNSAutoreleasePoolClassRef(CodeGenFunction &CGF) {
00226     llvm_unreachable("autoreleasepool unsupported in this ABI");
00227   }
00228   
00229   /// EnumerationMutationFunction - Return the function that's called by the
00230   /// compiler when a mutation is detected during foreach iteration.
00231   virtual llvm::Constant *EnumerationMutationFunction() = 0;
00232 
00233   virtual void EmitSynchronizedStmt(CodeGen::CodeGenFunction &CGF,
00234                                     const ObjCAtSynchronizedStmt &S) = 0;
00235   virtual void EmitTryStmt(CodeGen::CodeGenFunction &CGF,
00236                            const ObjCAtTryStmt &S) = 0;
00237   virtual void EmitThrowStmt(CodeGen::CodeGenFunction &CGF,
00238                              const ObjCAtThrowStmt &S,
00239                              bool ClearInsertionPoint=true) = 0;
00240   virtual llvm::Value *EmitObjCWeakRead(CodeGen::CodeGenFunction &CGF,
00241                                         llvm::Value *AddrWeakObj) = 0;
00242   virtual void EmitObjCWeakAssign(CodeGen::CodeGenFunction &CGF,
00243                                   llvm::Value *src, llvm::Value *dest) = 0;
00244   virtual void EmitObjCGlobalAssign(CodeGen::CodeGenFunction &CGF,
00245                                     llvm::Value *src, llvm::Value *dest,
00246                                     bool threadlocal=false) = 0;
00247   virtual void EmitObjCIvarAssign(CodeGen::CodeGenFunction &CGF,
00248                                   llvm::Value *src, llvm::Value *dest,
00249                                   llvm::Value *ivarOffset) = 0;
00250   virtual void EmitObjCStrongCastAssign(CodeGen::CodeGenFunction &CGF,
00251                                         llvm::Value *src, llvm::Value *dest) = 0;
00252 
00253   virtual LValue EmitObjCValueForIvar(CodeGen::CodeGenFunction &CGF,
00254                                       QualType ObjectTy,
00255                                       llvm::Value *BaseValue,
00256                                       const ObjCIvarDecl *Ivar,
00257                                       unsigned CVRQualifiers) = 0;
00258   virtual llvm::Value *EmitIvarOffset(CodeGen::CodeGenFunction &CGF,
00259                                       const ObjCInterfaceDecl *Interface,
00260                                       const ObjCIvarDecl *Ivar) = 0;
00261   virtual void EmitGCMemmoveCollectable(CodeGen::CodeGenFunction &CGF,
00262                                         llvm::Value *DestPtr,
00263                                         llvm::Value *SrcPtr,
00264                                         llvm::Value *Size) = 0;
00265   virtual llvm::Constant *BuildGCBlockLayout(CodeGen::CodeGenModule &CGM,
00266                                   const CodeGen::CGBlockInfo &blockInfo) = 0;
00267   virtual llvm::Constant *BuildRCBlockLayout(CodeGen::CodeGenModule &CGM,
00268                                   const CodeGen::CGBlockInfo &blockInfo) = 0;
00269   virtual llvm::Constant *BuildByrefLayout(CodeGen::CodeGenModule &CGM,
00270                                            QualType T) = 0;
00271   virtual llvm::GlobalVariable *GetClassGlobal(const std::string &Name,
00272                                                bool Weak = false) = 0;
00273 
00274   struct MessageSendInfo {
00275     const CGFunctionInfo &CallInfo;
00276     llvm::PointerType *MessengerType;
00277 
00278     MessageSendInfo(const CGFunctionInfo &callInfo,
00279                     llvm::PointerType *messengerType)
00280       : CallInfo(callInfo), MessengerType(messengerType) {}
00281   };
00282 
00283   MessageSendInfo getMessageSendInfo(const ObjCMethodDecl *method,
00284                                      QualType resultType,
00285                                      CallArgList &callArgs);
00286 
00287   // FIXME: This probably shouldn't be here, but the code to compute
00288   // it is here.
00289   unsigned ComputeBitfieldBitOffset(CodeGen::CodeGenModule &CGM,
00290                                     const ObjCInterfaceDecl *ID,
00291                                     const ObjCIvarDecl *Ivar);
00292 };
00293 
00294 /// Creates an instance of an Objective-C runtime class.
00295 //TODO: This should include some way of selecting which runtime to target.
00296 CGObjCRuntime *CreateGNUObjCRuntime(CodeGenModule &CGM);
00297 CGObjCRuntime *CreateMacObjCRuntime(CodeGenModule &CGM);
00298 }
00299 }
00300 #endif