22 #include "llvm/IR/IntrinsicInst.h" 23 #include "llvm/Support/Format.h" 24 #include "llvm/Transforms/Utils/Cloning.h" 28 using namespace clang;
29 using namespace CodeGen;
32 : CGM(CGM), VTContext(CGM.getContext().getVTableContext()) {}
40 llvm::raw_svector_ostream Out(Name);
42 getCXXABI().getMangleContext().mangleCXXDtorThunk(DD, GD.
getDtorType(),
45 getCXXABI().getMangleContext().mangleThunk(MD, Thunk, Out);
47 llvm::Type *Ty = getTypes().GetFunctionTypeForVTable(GD);
48 return GetOrCreateLLVMFunction(Name, Ty, GD,
true,
53 const ThunkInfo &Thunk, llvm::Function *Fn) {
58 llvm::Function *ThunkFn,
bool ForVTable,
69 ThunkFn->setComdat(CGM.
getModule().getOrInsertComdat(ThunkFn->getName()));
77 (isa<PointerType>(typeL) && isa<PointerType>(typeR)) ||
78 (isa<ReferenceType>(typeL) && isa<ReferenceType>(typeR))));
88 llvm::BasicBlock *AdjustNull =
nullptr;
89 llvm::BasicBlock *AdjustNotNull =
nullptr;
90 llvm::BasicBlock *AdjustEnd =
nullptr;
100 CGF.
Builder.CreateCondBr(IsNull, AdjustNull, AdjustNotNull);
107 Address(ReturnValue, ClassAlign),
110 if (NullCheckValue) {
111 CGF.
Builder.CreateBr(AdjustEnd);
113 CGF.
Builder.CreateBr(AdjustEnd);
116 llvm::PHINode *PHI = CGF.
Builder.CreatePHI(ReturnValue->getType(), 2);
117 PHI->addIncoming(ReturnValue, AdjustNotNull);
118 PHI->addIncoming(llvm::Constant::getNullValue(ReturnValue->getType()),
132 llvm::ValueToValueMapTy &VMap) {
134 auto *DIS = Fn->getSubprogram();
137 auto *NewDIS = DIS->replaceWithDistinct(DIS->clone());
138 VMap.MD()[DIS].reset(NewDIS);
142 for (
auto &BB : Fn->getBasicBlockList()) {
144 if (
auto *DII = dyn_cast<llvm::DbgInfoIntrinsic>(&I)) {
145 auto *DILocal = DII->getVariable();
146 if (!DILocal->isResolved())
175 QualType ResultType = FPT->getReturnType();
181 llvm::Function *BaseFn = cast<llvm::Function>(Callee);
184 llvm::ValueToValueMapTy VMap;
189 llvm::Function *NewFn = llvm::CloneFunction(BaseFn, VMap);
190 Fn->replaceAllUsesWith(NewFn);
192 Fn->eraseFromParent();
199 llvm::Function::arg_iterator AI = Fn->arg_begin();
206 llvm::BasicBlock *EntryBB = &Fn->front();
207 llvm::BasicBlock::iterator ThisStore =
208 std::find_if(EntryBB->begin(), EntryBB->end(), [&](llvm::Instruction &I) {
209 return isa<llvm::StoreInst>(I) &&
212 assert(ThisStore != EntryBB->end() &&
213 "Store of this should be in entry block?");
215 Builder.SetInsertPoint(&*ThisStore);
218 ThisStore->setOperand(0, AdjustedThisPtr);
222 for (llvm::BasicBlock &BB : *Fn) {
223 llvm::Instruction *
T = BB.getTerminator();
224 if (isa<llvm::ReturnInst>(T)) {
226 T->eraseFromParent();
227 Builder.SetInsertPoint(&BB);
240 assert(!CurGD.getDecl() &&
"CurGD was already set!");
242 CurFuncIsThunk =
true;
261 if (isa<CXXDestructorDecl>(MD))
266 StartFunction(
GlobalDecl(), ResultType, Fn, FnInfo, FunctionArgs,
273 CXXThisValue = CXXABIThisValue;
281 CurCodeDecl =
nullptr;
282 CurFuncDecl =
nullptr;
289 assert(isa<CXXMethodDecl>(CurGD.getDecl()) &&
290 "Please use a new CGF for this thunk");
291 const CXXMethodDecl *MD = cast<CXXMethodDecl>(CurGD.getDecl());
296 *
this, LoadCXXThisAddress(), Thunk->
This)
299 if (CurFnInfo->usesInAlloca()) {
305 MD,
"non-trivial argument copy for return-adjusting thunk");
307 EmitMustTailThunk(MD, AdjustedThisPtr, CalleePtr);
316 if (isa<CXXDestructorDecl>(MD))
320 unsigned PrefixArgs = CallArgs.size() - 1;
331 assert(CallFnInfo.getRegParm() == CurFnInfo->getRegParm() &&
332 CallFnInfo.isNoReturn() == CurFnInfo->isNoReturn() &&
333 CallFnInfo.getCallingConvention() == CurFnInfo->getCallingConvention());
334 assert(isa<CXXDestructorDecl>(MD) ||
335 similar(CallFnInfo.getReturnInfo(), CallFnInfo.getReturnType(),
336 CurFnInfo->getReturnInfo(), CurFnInfo->getReturnType()));
337 assert(CallFnInfo.arg_size() == CurFnInfo->arg_size());
338 for (
unsigned i = 0, e = CurFnInfo->arg_size(); i != e; ++i)
339 assert(
similar(CallFnInfo.arg_begin()[i].info,
340 CallFnInfo.arg_begin()[i].type,
341 CurFnInfo->arg_begin()[i].info,
342 CurFnInfo->arg_begin()[i].type));
354 !hasScalarEvaluationKind(CurFnInfo->getReturnType()))
358 llvm::Instruction *CallOrInvoke;
360 RValue RV = EmitCall(*CurFnInfo, Callee, Slot, CallArgs, &CallOrInvoke);
365 else if (llvm::CallInst* Call = dyn_cast<llvm::CallInst>(CallOrInvoke))
366 Call->setTailCallKind(llvm::CallInst::TCK_Tail);
373 AutoreleaseResult =
false;
386 for (llvm::Argument &A : CurFn->args())
390 const ABIArgInfo &ThisAI = CurFnInfo->arg_begin()->info;
392 const ABIArgInfo &RetAI = CurFnInfo->getReturnInfo();
394 llvm::Type *ThisType = Args[ThisArgNo]->getType();
395 if (ThisType != AdjustedThisPtr->getType())
396 AdjustedThisPtr = Builder.CreateBitCast(AdjustedThisPtr, ThisType);
397 Args[ThisArgNo] = AdjustedThisPtr;
399 assert(ThisAI.
isInAlloca() &&
"this is passed directly or inalloca");
400 Address ThisAddr = GetAddrOfLocalVar(CXXABIThisDecl);
401 llvm::Type *ThisType = ThisAddr.getElementType();
402 if (ThisType != AdjustedThisPtr->getType())
403 AdjustedThisPtr = Builder.CreateBitCast(AdjustedThisPtr, ThisType);
404 Builder.CreateStore(AdjustedThisPtr, ThisAddr);
409 llvm::CallInst *Call = Builder.CreateCall(CalleePtr, Args);
410 Call->setTailCallKind(llvm::CallInst::TCK_MustTail);
414 llvm::AttributeList Attrs;
417 Call->setAttributes(Attrs);
418 Call->setCallingConv(static_cast<llvm::CallingConv::ID>(CallingConv));
420 if (Call->getType()->isVoidTy())
421 Builder.CreateRetVoid();
423 Builder.CreateRet(Call);
427 EmitBlock(createBasicBlock());
434 StartThunk(Fn, GD, FnInfo);
444 EmitCallAndReturnForThunk(Callee, &Thunk);
453 llvm::GlobalValue *Entry;
456 if (llvm::ConstantExpr *CE = dyn_cast<llvm::ConstantExpr>(C)) {
457 assert(CE->getOpcode() == llvm::Instruction::BitCast);
458 Entry = cast<llvm::GlobalValue>(CE->getOperand(0));
460 Entry = cast<llvm::GlobalValue>(C);
465 if (Entry->getType()->getElementType() !=
467 llvm::GlobalValue *OldThunkFn = Entry;
470 assert(OldThunkFn->isDeclaration() &&
471 "Shouldn't replace non-declaration");
474 OldThunkFn->setName(StringRef());
478 if (!OldThunkFn->use_empty()) {
479 llvm::Constant *NewPtrForOldDecl =
480 llvm::ConstantExpr::getBitCast(Entry, OldThunkFn->getType());
481 OldThunkFn->replaceAllUsesWith(NewPtrForOldDecl);
485 OldThunkFn->eraseFromParent();
488 llvm::Function *ThunkFn = cast<llvm::Function>(Entry);
490 bool UseAvailableExternallyLinkage = ForVTable && ABIHasKeyFunctions;
492 if (!ThunkFn->isDeclaration()) {
493 if (!ABIHasKeyFunctions || UseAvailableExternallyLinkage) {
504 if (ThunkFn->isVarArg()) {
510 if (UseAvailableExternallyLinkage)
522 void CodeGenVTables::maybeEmitThunkForVTable(
GlobalDecl GD,
538 emitThunk(GD, Thunk,
true);
553 if (!ThunkInfoVector)
556 for (
const ThunkInfo& Thunk : *ThunkInfoVector)
557 emitThunk(GD, Thunk,
false);
560 void CodeGenVTables::addVTableComponent(
562 unsigned idx, llvm::Constant *rtti,
unsigned &nextVTableThunkIndex) {
565 auto addOffsetConstant = [&](
CharUnits offset) {
566 builder.add(llvm::ConstantExpr::getIntToPtr(
567 llvm::ConstantInt::get(CGM.
PtrDiffTy, offset.getQuantity()),
571 switch (component.getKind()) {
573 return addOffsetConstant(component.getVCallOffset());
576 return addOffsetConstant(component.getVBaseOffset());
579 return addOffsetConstant(component.getOffsetToTop());
582 return builder.add(llvm::ConstantExpr::getBitCast(rtti, CGM.
Int8PtrTy));
590 switch (component.getKind()) {
592 llvm_unreachable(
"Unexpected vtable component kind");
594 GD = component.getFunctionDecl();
613 ? MD->
hasAttr<CUDADeviceAttr>()
614 : (MD->
hasAttr<CUDAHostAttr>() || !MD->
hasAttr<CUDADeviceAttr>());
616 return builder.addNullPointer(CGM.
Int8PtrTy);
620 auto getSpecialVirtualFn = [&](StringRef name) {
621 llvm::FunctionType *fnTy =
622 llvm::FunctionType::get(CGM.
VoidTy,
false);
624 if (
auto f = dyn_cast<llvm::Function>(fn))
625 f->setUnnamedAddr(llvm::GlobalValue::UnnamedAddr::Global);
626 return llvm::ConstantExpr::getBitCast(fn, CGM.
Int8PtrTy);
629 llvm::Constant *fnPtr;
632 if (cast<CXXMethodDecl>(GD.
getDecl())->isPure()) {
636 fnPtr = PureVirtualFn;
639 }
else if (cast<CXXMethodDecl>(GD.
getDecl())->isDeleted()) {
640 if (!DeletedVirtualFn)
643 fnPtr = DeletedVirtualFn;
646 }
else if (nextVTableThunkIndex < layout.
vtable_thunks().size() &&
648 auto &thunkInfo = layout.
vtable_thunks()[nextVTableThunkIndex].second;
650 maybeEmitThunkForVTable(GD, thunkInfo);
651 nextVTableThunkIndex++;
660 fnPtr = llvm::ConstantExpr::getBitCast(fnPtr, CGM.
Int8PtrTy);
666 return builder.addNullPointer(CGM.
Int8PtrTy);
669 llvm_unreachable(
"Unexpected vtable component kind");
674 for (
unsigned i = 0, e = layout.
getNumVTables(); i != e; ++i) {
683 llvm::Constant *rtti) {
684 unsigned nextVTableThunkIndex = 0;
685 for (
unsigned i = 0, e = layout.
getNumVTables(); i != e; ++i) {
689 for (
unsigned i = thisIndex; i != nextIndex; ++i) {
690 addVTableComponent(vtableElem, layout, i, rtti, nextVTableThunkIndex);
692 vtableElem.finishAndAddTo(builder);
696 llvm::GlobalVariable *
700 llvm::GlobalVariable::LinkageTypes
Linkage,
701 VTableAddressPointsMapTy& AddressPoints) {
703 DI->completeClassData(Base.
getBase());
705 std::unique_ptr<VTableLayout> VTLayout(
710 AddressPoints = VTLayout->getAddressPoints();
714 llvm::raw_svector_ostream Out(OutName);
718 StringRef Name = OutName.str();
727 if (Linkage == llvm::GlobalVariable::AvailableExternallyLinkage)
731 llvm::GlobalVariable *VTable =
736 VTable->setUnnamedAddr(llvm::GlobalValue::UnnamedAddr::Global);
745 components.finishAndSetAsInitializer(VTable);
761 llvm::GlobalVariable::LinkageTypes
769 if (keyFunction && !RD->
hasAttr<DLLImportAttr>()) {
774 keyFunction = cast<CXXMethodDecl>(def);
779 assert((def || CodeGenOpts.OptimizationLevel > 0 ||
781 "Shouldn't query vtable linkage without key function, " 782 "optimizations, or debug info");
783 if (!def && CodeGenOpts.OptimizationLevel > 0)
784 return llvm::GlobalVariable::AvailableExternallyLinkage;
788 llvm::GlobalVariable::LinkOnceODRLinkage :
795 llvm::GlobalVariable::LinkOnceODRLinkage :
800 llvm::GlobalVariable::WeakODRLinkage :
804 llvm_unreachable(
"Should not have been asked to emit this");
813 llvm::GlobalVariable::LinkageTypes DiscardableODRLinkage =
814 llvm::GlobalValue::LinkOnceODRLinkage;
815 llvm::GlobalVariable::LinkageTypes NonDiscardableODRLinkage =
816 llvm::GlobalValue::WeakODRLinkage;
817 if (RD->
hasAttr<DLLExportAttr>()) {
819 DiscardableODRLinkage = NonDiscardableODRLinkage;
820 }
else if (RD->
hasAttr<DLLImportAttr>()) {
822 DiscardableODRLinkage = llvm::GlobalVariable::AvailableExternallyLinkage;
823 NonDiscardableODRLinkage = llvm::GlobalVariable::AvailableExternallyLinkage;
830 return DiscardableODRLinkage;
835 if (getTarget().getCXXABI().isMicrosoft())
836 return DiscardableODRLinkage;
838 ? llvm::GlobalVariable::AvailableExternallyLinkage
842 return NonDiscardableODRLinkage;
845 llvm_unreachable(
"Invalid TemplateSpecializationKind!");
855 VTables.GenerateClassData(theClass);
861 DI->completeClassData(RD);
880 assert(RD->
isDynamicClass() &&
"Non-dynamic classes have no VTable.");
907 return !keyFunction->
hasBody();
926 void CodeGenModule::EmitDeferredVTables() {
930 size_t savedSize = DeferredVTables.size();
935 VTables.GenerateClassData(RD);
936 else if (shouldOpportunisticallyEmitVTables())
937 OpportunisticVTables.push_back(RD);
939 assert(savedSize == DeferredVTables.size() &&
940 "deferred extra vtables during vtable emission?");
941 DeferredVTables.clear();
949 if (RD->
hasAttr<LTOVisibilityPublicAttr>() || RD->
hasAttr<UuidAttr>())
952 if (getTriple().isOSBinFormatCOFF()) {
960 if (getCodeGenOpts().LTOVisibilityPublicStd) {
963 auto *D = cast<Decl>(DC);
965 if (isa<TranslationUnitDecl>(DC->getRedeclContext())) {
966 if (
auto *ND = dyn_cast<NamespaceDecl>(D))
968 if (II->isStr(
"std") || II->isStr(
"stdext"))
980 if (!getCodeGenOpts().LTOUnit)
986 typedef std::pair<const CXXRecordDecl *, unsigned> BSEntry;
987 std::vector<BSEntry> BitsetEntries;
990 BitsetEntries.push_back(
991 std::make_pair(AP.first.getBase(),
993 AP.second.AddressPointIndex));
996 std::sort(BitsetEntries.begin(), BitsetEntries.end(),
997 [
this](
const BSEntry &E1,
const BSEntry &E2) {
1002 llvm::raw_string_ostream O1(S1);
1003 getCXXABI().getMangleContext().mangleTypeName(
1004 QualType(E1.first->getTypeForDecl(), 0), O1);
1008 llvm::raw_string_ostream O2(S2);
1009 getCXXABI().getMangleContext().mangleTypeName(
1010 QualType(E2.first->getTypeForDecl(), 0), O2);
1018 return E1.second < E2.second;
1021 for (
auto BitsetEntry : BitsetEntries)
1022 AddVTableTypeMetadata(VTable, PointerWidth * BitsetEntry.second,
size_t getNumVTables() const
ReturnValueSlot - Contains the address where the return value of a function can be stored...
static const Decl * getCanonicalDecl(const Decl *D)
An instance of this class is created to represent a function declaration or definition.
External linkage, which indicates that the entity can be referred to from other translation units...
A (possibly-)qualified type.
bool ReturnTypeUsesSRet(const CGFunctionInfo &FI)
Return true iff the given type uses 'sret' when used as a return type.
CodeGenTypes & getTypes()
const CodeGenOptions & getCodeGenOpts() const
const AddressPointsMapTy & getAddressPoints() const
virtual void EmitReturnFromThunk(CodeGenFunction &CGF, RValue RV, QualType ResultType)
llvm::LLVMContext & getLLVMContext()
CXXDtorType getDtorType() const
virtual void addImplicitStructorParams(CodeGenFunction &CGF, QualType &ResTy, FunctionArgList &Params)=0
Insert any ABI-specific implicit parameters into the parameter list for a function.
The standard implementation of ConstantInitBuilder used in Clang.
CharUnits getClassPointerAlignment(const CXXRecordDecl *CD)
Returns the assumed alignment of an opaque pointer to the given class.
FunctionType - C99 6.7.5.3 - Function Declarators.
QualType getPointeeType() const
If this is a pointer, ObjC object pointer, or block pointer, this returns the respective pointee...
unsigned getNumVBases() const
Retrieves the number of virtual base classes of this class.
virtual const ThunkInfoVectorTy * getThunkInfo(GlobalDecl GD)
virtual llvm::Value * performThisAdjustment(CodeGenFunction &CGF, Address This, const ThisAdjustment &TA)=0
void setFunctionLinkage(GlobalDecl GD, llvm::Function *F)
virtual StringRef GetDeletedVirtualCallName()=0
Gets the deleted virtual member call name.
const TargetInfo & getTargetInfo() const
llvm::Function * GenerateVarArgsThunk(llvm::Function *Fn, const CGFunctionInfo &FnInfo, GlobalDecl GD, const ThunkInfo &Thunk)
bool isFuncTypeConvertible(const FunctionType *FT)
isFuncTypeConvertible - Utility to check whether a function type can be converted to an LLVM type (i...
bool HasHiddenLTOVisibility(const CXXRecordDecl *RD)
Returns whether the given record has hidden LTO visibility and therefore may participate in (single-m...
Objects with "hidden" visibility are not seen by the dynamic linker.
const T * getAs() const
Member-template getAs<specific type>'.
Visibility getVisibility() const
CGDebugInfo * getModuleDebugInfo()
bool supportsCOMDAT() const
This class gathers all debug information during compilation and is responsible for emitting to llvm g...
llvm::Value * getPointer() const
ParmVarDecl - Represents a parameter to a function.
Linkage
Describes the different kinds of linkage (C++ [basic.link], C99 6.2.2) that an entity may have...
CharUnits getBaseOffset() const
getBaseOffset - Returns the base class offset.
uint64_t getPointerWidth(unsigned AddrSpace) const
Return the width of pointers on this target, for the specified address space.
One of these records is kept for each identifier that is lexed.
TargetCXXABI getCXXABI() const
Get the C++ ABI currently in use.
Indirect - Pass the argument indirectly via a hidden pointer with the specified alignment (0 indicate...
CodeGenFunction - This class organizes the per-function state that is used while generating LLVM code...
static bool shouldEmitAvailableExternallyVTable(const CodeGenModule &CGM, const CXXRecordDecl *RD)
static void setThunkVisibility(CodeGenModule &CGM, const CXXMethodDecl *MD, const ThunkInfo &Thunk, llvm::Function *Fn)
bool isReferenceType() const
static void resolveTopLevelMetadata(llvm::Function *Fn, llvm::ValueToValueMapTy &VMap)
This function clones a function's DISubprogram node and enters it into a value map with the intent th...
llvm::Type * getVTableType(const VTableLayout &layout)
Returns the type of a vtable with the given layout.
The this pointer adjustment as well as an optional return adjustment for a thunk. ...
static ApplyDebugLocation CreateArtificial(CodeGenFunction &CGF)
Apply TemporaryLocation if it is valid.
ArrayRef< ParmVarDecl * > parameters() const
virtual void EmitInstanceFunctionProlog(CodeGenFunction &CGF)=0
Emit the ABI-specific prolog for the function.
ArrayRef< VTableComponent > vtable_components() const
QualType getThisType(ASTContext &C) const
Returns the type of the this pointer.
virtual void emitVTableDefinitions(CodeGenVTables &CGVT, const CXXRecordDecl *RD)=0
Emits the VTable definitions required for the given record type.
CharUnits - This is an opaque type for sizes expressed in character units.
virtual bool hasMostDerivedReturn(GlobalDecl GD) const
bool isVolatileQualified() const
Determine whether this type is volatile-qualified.
void ConstructAttributeList(StringRef Name, const CGFunctionInfo &Info, CGCalleeInfo CalleeInfo, llvm::AttributeList &Attrs, unsigned &CallingConv, bool AttrOnCallSite)
Get the LLVM attributes and calling convention to use for a particular function type.
ABIArgInfo - Helper class to encapsulate information about how a specific C type should be passed to ...
void setGlobalVisibility(llvm::GlobalValue *GV, const NamedDecl *D, ForDefinition_t IsForDefinition) const
Set the visibility for the given LLVM GlobalValue.
virtual bool canSpeculativelyEmitVTable(const CXXRecordDecl *RD) const =0
Determine whether it's possible to emit a vtable for RD, even though we do not know that the vtable h...
llvm::BasicBlock * createBasicBlock(const Twine &name="", llvm::Function *parent=nullptr, llvm::BasicBlock *before=nullptr)
createBasicBlock - Create an LLVM basic block.
ItaniumVTableContext & getItaniumVTableContext()
const CGFunctionInfo & arrangeGlobalDeclaration(GlobalDecl GD)
param_iterator param_begin()
llvm::Constant * CreateRuntimeFunction(llvm::FunctionType *Ty, StringRef Name, llvm::AttributeList ExtraAttrs=llvm::AttributeList(), bool Local=false)
Create a new runtime function with the specified type and name.
CXXRecordDecl * getAsCXXRecordDecl() const
Retrieves the CXXRecordDecl that this type refers to, either because the type is a RecordType or beca...
Represents a prototype with parameter type info, e.g.
bool isDynamicClass() const
ArrayBuilder beginArray(llvm::Type *eltTy=nullptr)
TemplateSpecializationKind getTemplateSpecializationKind() const
Determine whether this particular class is a specialization or instantiation of a class template or m...
RValue - This trivial value class is used to represent the result of an expression that is evaluated...
QuantityType getQuantity() const
getQuantity - Get the raw integer representation of this quantity.
bool isVTableExternal(const CXXRecordDecl *RD)
At this point in the translation unit, does it appear that can we rely on the vtable being defined el...
virtual bool HasThisReturn(GlobalDecl GD) const
Returns true if the given constructor or destructor is one of the kinds that the ABI says returns 'th...
bool hasKeyFunctions() const
Does this ABI use key functions? If so, class data such as the vtable is emitted with strong linkage ...
static void setThunkProperties(CodeGenModule &CGM, const ThunkInfo &Thunk, llvm::Function *ThunkFn, bool ForVTable, GlobalDecl GD)
static bool similar(const ABIArgInfo &infoL, CanQualType typeL, const ABIArgInfo &infoR, CanQualType typeR)
const FunctionProtoType * T
const T * castAs() const
Member-template castAs<specific type>.
static CGCallee forDirect(llvm::Constant *functionPtr, const CGCalleeInfo &abstractInfo=CGCalleeInfo())
Represents a C++ destructor within a class.
QualType getTagDeclType(const TagDecl *Decl) const
Return the unique reference to the type for the specified TagDecl (struct/union/class/enum) decl...
virtual StringRef GetPureVirtualCallName()=0
Gets the pure virtual member call function.
Linkage getLinkage() const
void add(RValue rvalue, QualType type, bool needscopy=false)
const CXXRecordDecl * getBase() const
getBase - Returns the base class declaration.
bool hasBody(const FunctionDecl *&Definition) const
Returns true if the function has a body (definition).
DeclContext * getParent()
getParent - Returns the containing DeclContext.
bool isExternallyVisible(Linkage L)
const TargetInfo & getTarget() const
This template specialization was implicitly instantiated from a template.
const LangOptions & getLangOpts() const
ASTContext & getContext() const
virtual void adjustCallArgsForDestructorThunk(CodeGenFunction &CGF, GlobalDecl GD, CallArgList &CallArgs)
void generateThunk(llvm::Function *Fn, const CGFunctionInfo &FnInfo, GlobalDecl GD, const ThunkInfo &Thunk)
Generate a thunk for the given method.
CallingConv
CallingConv - Specifies the calling convention that a function uses.
GlobalDecl - represents a global declaration.
llvm::GlobalVariable * CreateOrReplaceCXXRuntimeVariable(StringRef Name, llvm::Type *Ty, llvm::GlobalValue::LinkageTypes Linkage)
Will return a global variable of the given type.
llvm::Constant * GetAddrOfThunk(GlobalDecl GD, const ThunkInfo &Thunk)
Get the address of the thunk for the given global decl.
The l-value was considered opaque, so the alignment was determined from a type.
ArrayRef< VTableThunkTy > vtable_thunks() const
Encodes a location in the source.
QualType getReturnType() const
bool isSRetAfterThis() const
const Decl * getDecl() const
Represents a static or instance method of a struct/union/class.
llvm::Constant * GetAddrOfRTTIDescriptor(QualType Ty, bool ForEH=false)
Get the address of the RTTI descriptor for the given type.
CodeGenVTables(CodeGenModule &CGM)
void createVTableInitializer(ConstantStructBuilder &builder, const VTableLayout &layout, llvm::Constant *rtti)
Add vtable components for the given vtable layout to the given global initializer.
void SetLLVMFunctionAttributesForDefinition(const Decl *D, llvm::Function *F)
Set the LLVM function attributes which only apply to a function definition.
virtual void emitVirtualInheritanceTables(const CXXRecordDecl *RD)=0
Emit any tables needed to implement virtual inheritance.
All available information about a concrete callee.
MangleContext & getMangleContext()
Gets the mangle context.
This template specialization was instantiated from a template due to an explicit instantiation defini...
This template specialization was formed from a template-id but has not yet been declared, defined, or instantiated.
llvm::GlobalVariable * GenerateConstructionVTable(const CXXRecordDecl *RD, const BaseSubobject &Base, bool BaseIsVirtual, llvm::GlobalVariable::LinkageTypes Linkage, VTableAddressPointsMapTy &AddressPoints)
GenerateConstructionVTable - Generate a construction vtable for the given base subobject.
FunctionArgList - Type for representing both the decl and type of parameters to a function...
llvm::Value * getScalarVal() const
getScalarVal() - Return the Value* of this scalar value.
void ErrorUnsupported(const Stmt *S, const char *Type)
Print out an error that codegen doesn't support the specified stmt yet.
CGFunctionInfo - Class to encapsulate the information about a function definition.
This class organizes the cross-function state that is used while generating LLVM code.
Dataflow Directional Tag Classes.
ThisAdjustment This
The this pointer adjustment.
DeclContext - This is used only as base class of specific decl types that can act as declaration cont...
TemplateSpecializationKind getTemplateSpecializationKind() const
Determine what kind of template instantiation this function represents.
void EmitVTableTypeMetadata(llvm::GlobalVariable *VTable, const VTableLayout &VTLayout)
Emit type metadata for the given vtable using the given layout.
This template specialization was instantiated from a template due to an explicit instantiation declar...
const CXXRecordDecl * getParent() const
Returns the parent of this method declaration, which is the class in which this method is defined...
void buildThisParam(CodeGenFunction &CGF, FunctionArgList &Params)
Build a parameter variable suitable for 'this'.
TemplateSpecializationKind
Describes the kind of template specialization that a particular template specialization declaration r...
llvm::Module & getModule() const
void EmitThunks(GlobalDecl GD)
EmitThunks - Emit the associated thunks for the given global decl.
param_iterator param_end()
llvm::GlobalVariable::LinkageTypes getVTableLinkage(const CXXRecordDecl *RD)
Return the appropriate linkage for the vtable, VTT, and type information of the given class...
LinkageInfo getLinkageAndVisibility() const
Determines the linkage and visibility of this entity.
StructBuilder beginStruct(llvm::StructType *structTy=nullptr)
This template specialization was declared or defined by an explicit specialization (C++ [temp...
llvm::PointerType * Int8PtrTy
static bool shouldEmitVTableAtEndOfTranslationUnit(CodeGenModule &CGM, const CXXRecordDecl *RD)
Given that we're currently at the end of the translation unit, and we've emitted a reference to the v...
void GenerateClassData(const CXXRecordDecl *RD)
GenerateClassData - Generate all the class data required to be generated upon definition of a KeyFunc...
ReturnAdjustment Return
The return adjustment.
llvm::Constant * GetAddrOfFunction(GlobalDecl GD, llvm::Type *Ty=nullptr, bool ForVTable=false, bool DontDefer=false, ForDefinition_t IsForDefinition=NotForDefinition)
Return the address of the given function.
Internal linkage, which indicates that the entity can be referred to from within the translation unit...
void EmitBlock(llvm::BasicBlock *BB, bool IsFinished=false)
EmitBlock - Emit the given block.
void StartThunk(llvm::Function *Fn, GlobalDecl GD, const CGFunctionInfo &FnInfo)
bool isInlined() const
Determine whether this function should be inlined, because it is either marked "inline" or "constexpr...
llvm::Type * GetFunctionTypeForVTable(GlobalDecl GD)
GetFunctionTypeForVTable - Get the LLVM function type for use in a vtable, given a CXXMethodDecl...
llvm::IntegerType * PtrDiffTy
CharUnits toCharUnitsFromBits(int64_t BitSize) const
Convert a size in bits to a size in characters.
void EmitCallAndReturnForThunk(llvm::Constant *Callee, const ThunkInfo *Thunk)
static RValue PerformReturnAdjustment(CodeGenFunction &CGF, QualType ResultType, RValue RV, const ThunkInfo &Thunk)
const CXXMethodDecl * getCurrentKeyFunction(const CXXRecordDecl *RD)
Get our current best idea for the key function of the given record decl, or nullptr if there isn't on...
Represents a C++ struct/union/class.
A helper class of ConstantInitBuilder, used for building constant struct initializers.
size_t getVTableSize(size_t i) const
bool isMicrosoft() const
Is this ABI an MSVC-compatible ABI?
A pointer to the deleting destructor.
CGCXXABI & getCXXABI() const
static RValue get(llvm::Value *V)
static RequiredArgs forPrototypePlus(const FunctionProtoType *prototype, unsigned additional, const FunctionDecl *FD)
Compute the arguments required by the given formal prototype, given that there may be some additional...
virtual llvm::Value * performReturnAdjustment(CodeGenFunction &CGF, Address Ret, const ReturnAdjustment &RA)=0
static ApplyDebugLocation CreateEmpty(CodeGenFunction &CGF)
Set the IRBuilder to not attach debug locations.
CodeGenVTables & getVTables()
CallArgList - Type for representing both the value and type of arguments in a call.
const CGFunctionInfo & arrangeCXXMethodCall(const CallArgList &args, const FunctionProtoType *type, RequiredArgs required, unsigned numPrefixArgs)
Arrange a call to a C++ method, passing the given arguments.
const LangOptions & getLangOpts() const
A pointer to the complete destructor.
A helper class of ConstantInitBuilder, used for building constant array initializers.
size_t getVTableOffset(size_t i) const
An entry that is never used.
virtual void setThunkLinkage(llvm::Function *Thunk, bool ForVTable, GlobalDecl GD, bool ReturnAdjustment)=0
SourceLocation getLocation() const
bool isExternallyVisible() const
void EmitVTable(CXXRecordDecl *Class)
This is a callback from Sema to tell us that that a particular vtable is required to be emitted in th...
void EmitMustTailThunk(const CXXMethodDecl *MD, llvm::Value *AdjustedThisPtr, llvm::Value *Callee)
Emit a musttail call for a thunk with a potentially adjusted this pointer.
llvm::FunctionType * GetFunctionType(const CGFunctionInfo &Info)
GetFunctionType - Get the LLVM function type for.