28 #include "llvm/IR/Intrinsics.h" 29 #include "llvm/IR/Metadata.h" 30 #include "llvm/Transforms/Utils/SanitizerStats.h" 32 using namespace clang;
33 using namespace CodeGen;
50 return layout.getNonVirtualAlignment();
64 CharUnits expectedVBaseAlign = baseLayout.getNonVirtualAlignment();
77 return std::min(actualBaseAlign, expectedTargetAlign);
80 CharUnits expectedBaseAlign = baseLayout.getNonVirtualAlignment();
100 if (actualBaseAlign >= expectedBaseAlign) {
101 return expectedTargetAlign;
107 return std::min(actualBaseAlign, expectedTargetAlign);
111 assert(CurFuncDecl &&
"loading 'this' without a func declaration?");
112 assert(isa<CXXMethodDecl>(CurFuncDecl));
115 if (CXXThisAlignment.isZero()) {
119 auto RD = cast<CXXMethodDecl>(CurFuncDecl)->getParent();
120 CXXThisAlignment = CGM.getClassPointerAlignment(RD);
123 return Address(LoadCXXThis(), CXXThisAlignment);
137 CGM.getCXXABI().EmitMemberDataPointerAddress(*
this, E, base,
138 memberPtr, memberPtrType);
141 CharUnits memberAlign = getNaturalTypeAlignment(memberType, BaseInfo,
147 return Address(ptr, memberAlign);
160 assert(!Base->
isVirtual() &&
"Should not see virtual bases here!");
165 const auto *BaseDecl =
169 Offset += Layout.getBaseClassOffset(BaseDecl);
181 assert(PathBegin != PathEnd &&
"Base path should not be empty!");
191 return llvm::ConstantInt::get(PtrDiffTy, Offset.
getQuantity());
203 bool BaseIsVirtual) {
218 if (!Offset.isZero()) {
219 V = Builder.CreateElementBitCast(V,
Int8Ty);
220 V = Builder.CreateConstInBoundsByteGEP(V, Offset);
222 V = Builder.CreateElementBitCast(V, ConvertType(Base));
234 assert(!nonVirtualOffset.
isZero() || virtualOffset !=
nullptr);
238 if (!nonVirtualOffset.
isZero()) {
239 baseOffset = llvm::ConstantInt::get(CGF.
PtrDiffTy,
242 baseOffset = CGF.
Builder.CreateAdd(virtualOffset, baseOffset);
245 baseOffset = virtualOffset;
250 unsigned AddrSpace = ptr->getType()->getPointerAddressSpace();
252 ptr = CGF.
Builder.CreateInBoundsGEP(ptr, baseOffset,
"add.ptr");
258 assert(nearestVBase &&
"virtual offset without vbase?");
260 derivedClass, nearestVBase);
266 return Address(ptr, alignment);
274 assert(PathBegin != PathEnd &&
"Base path should not be empty!");
283 if ((*Start)->isVirtual()) {
284 VBase = cast<CXXRecordDecl>(
285 (*Start)->getType()->castAs<
RecordType>()->getDecl());
292 CharUnits NonVirtualOffset = CGM.computeNonVirtualBaseClassOffset(
293 VBase ? VBase : Derived, Start, PathEnd);
298 if (VBase && Derived->
hasAttr<FinalAttr>()) {
301 NonVirtualOffset += vBaseOffset;
307 ConvertType((PathEnd[-1])->getType())
308 ->getPointerTo(Value.
getType()->getPointerAddressSpace());
311 CharUnits DerivedAlign = CGM.getClassPointerAlignment(Derived);
315 if (NonVirtualOffset.
isZero() && !VBase) {
316 if (sanitizePerformTypeCheck()) {
319 EmitTypeCheck(TCK_Upcast, Loc, Value.
getPointer(),
320 DerivedTy, DerivedAlign, SkippedChecks);
322 return Builder.CreateBitCast(Value, BasePtrTy);
325 llvm::BasicBlock *origBB =
nullptr;
326 llvm::BasicBlock *endBB =
nullptr;
330 if (NullCheckValue) {
331 origBB = Builder.GetInsertBlock();
332 llvm::BasicBlock *notNullBB = createBasicBlock(
"cast.notnull");
333 endBB = createBasicBlock(
"cast.end");
336 Builder.CreateCondBr(isNull, endBB, notNullBB);
337 EmitBlock(notNullBB);
340 if (sanitizePerformTypeCheck()) {
343 EmitTypeCheck(VBase ? TCK_UpcastToVirtualBase : TCK_Upcast, Loc,
344 Value.
getPointer(), DerivedTy, DerivedAlign, SkippedChecks);
351 CGM.getCXXABI().GetVirtualBaseClassOffset(*
this, Value, Derived, VBase);
356 VirtualOffset, Derived, VBase);
359 Value = Builder.CreateBitCast(Value, BasePtrTy);
362 if (NullCheckValue) {
363 llvm::BasicBlock *notNullBB = Builder.GetInsertBlock();
364 Builder.CreateBr(endBB);
367 llvm::PHINode *PHI = Builder.CreatePHI(BasePtrTy, 2,
"cast.result");
368 PHI->addIncoming(Value.
getPointer(), notNullBB);
369 PHI->addIncoming(llvm::Constant::getNullValue(BasePtrTy), origBB);
381 bool NullCheckValue) {
382 assert(PathBegin != PathEnd &&
"Base path should not be empty!");
387 BaseAddr.
getPointer()->getType()->getPointerAddressSpace();
388 llvm::Type *DerivedPtrTy = ConvertType(DerivedTy)->getPointerTo(AddrSpace);
391 CGM.GetNonVirtualBaseClassOffset(Derived, PathBegin, PathEnd);
393 if (!NonVirtualOffset) {
395 return Builder.CreateBitCast(BaseAddr, DerivedPtrTy);
398 llvm::BasicBlock *CastNull =
nullptr;
399 llvm::BasicBlock *CastNotNull =
nullptr;
400 llvm::BasicBlock *CastEnd =
nullptr;
402 if (NullCheckValue) {
403 CastNull = createBasicBlock(
"cast.null");
404 CastNotNull = createBasicBlock(
"cast.notnull");
405 CastEnd = createBasicBlock(
"cast.end");
408 Builder.CreateCondBr(IsNull, CastNull, CastNotNull);
409 EmitBlock(CastNotNull);
414 Value = Builder.CreateInBoundsGEP(Value, Builder.CreateNeg(NonVirtualOffset),
418 Value = Builder.CreateBitCast(Value, DerivedPtrTy);
421 if (NullCheckValue) {
422 Builder.CreateBr(CastEnd);
424 Builder.CreateBr(CastEnd);
427 llvm::PHINode *PHI = Builder.CreatePHI(Value->getType(), 2);
428 PHI->addIncoming(Value, CastNotNull);
429 PHI->addIncoming(llvm::Constant::getNullValue(Value->getType()), CastNull);
433 return Address(Value, CGM.getClassPointerAlignment(Derived));
439 if (!CGM.getCXXABI().NeedsVTTParameter(GD)) {
444 const CXXRecordDecl *RD = cast<CXXMethodDecl>(CurCodeDecl)->getParent();
449 uint64_t SubVTTIndex;
454 }
else if (RD == Base) {
457 assert(!CGM.getCXXABI().NeedsVTTParameter(CurGD) &&
458 "doing no-op VTT offset in base dtor/ctor?");
459 assert(!ForVirtualBase &&
"Can't have same class as virtual base!");
468 CGM.getVTables().getSubVTTIndex(RD,
BaseSubobject(Base, BaseOffset));
469 assert(SubVTTIndex != 0 &&
"Sub-VTT index must be greater than zero!");
472 if (CGM.getCXXABI().NeedsVTTParameter(CurGD)) {
475 VTT = Builder.CreateConstInBoundsGEP1_64(VTT, SubVTTIndex);
478 VTT = CGM.getVTables().GetAddrOfVTT(RD);
479 VTT = Builder.CreateConstInBoundsGEP2_64(VTT, 0, SubVTTIndex);
491 : BaseClass(Base), BaseIsVirtual(BaseIsVirtual) {}
503 DerivedClass, BaseClass,
506 false, Addr, ThisTy);
517 DynamicThisUseChecker(
const ASTContext &C) : super(C), UsesThis(
false) {}
524 void VisitCXXThisExpr(
const CXXThisExpr *E) { UsesThis =
true; }
529 DynamicThisUseChecker Checker(C);
531 return Checker.UsesThis;
538 "Must have base initializer!");
543 const auto *BaseClassDecl =
571 !BaseClassDecl->hasTrivialDestructor())
578 if (!(CD && CD->isCopyOrMoveConstructor()) &&
600 for (
const auto *I : IndirectField->
chain())
614 "Must have member initializer!");
615 assert(MemberInit->
getInit() &&
"Must have initializer!");
619 QualType FieldType = Field->getType();
647 unsigned SrcArgIndex =
672 switch (getEvaluationKind(FieldType)) {
675 EmitExprAsInit(Init, Field, LHS,
false);
678 EmitStoreThroughLValue(RHS, LHS);
682 EmitComplexExprIntoLValue(Init, LHS,
true);
691 EmitAggExpr(Init, Slot);
699 if (needsEHCleanup(dtorKind))
700 pushEHDestroy(dtorKind, LHS.
getAddress(*
this), FieldType);
758 Prologue ? cast<CXXConstructorDecl>(CurGD.getDecl())->getParent()
759 : cast<CXXDestructorDecl>(CurGD.getDecl())->getParent();
762 struct SizeAndOffset {
767 unsigned PtrSize = CGM.getDataLayout().getPointerSizeInBits();
776 size_t NumFields = 0;
777 for (
const auto *Field : ClassDecl->
fields()) {
779 std::pair<CharUnits, CharUnits> FieldInfo =
782 assert(NumFields < SSV.size());
786 assert(NumFields == SSV.size());
787 if (SSV.size() <= 1)
return;
792 llvm::FunctionType *FTy =
793 llvm::FunctionType::get(CGM.VoidTy, Args,
false);
794 llvm::FunctionCallee F = CGM.CreateRuntimeFunction(
795 FTy, Prologue ?
"__asan_poison_intra_object_redzone" 796 :
"__asan_unpoison_intra_object_redzone");
799 ThisPtr = Builder.CreatePtrToInt(ThisPtr, IntPtrTy);
803 for (
size_t i = 0; i < SSV.size(); i++) {
804 uint64_t AsanAlignment = 8;
805 uint64_t NextField = i == SSV.size() - 1 ? TypeSize : SSV[i + 1].Offset;
806 uint64_t PoisonSize = NextField - SSV[i].Offset - SSV[i].Size;
807 uint64_t EndOffset = SSV[i].Offset + SSV[i].Size;
808 if (PoisonSize < AsanAlignment || !SSV[i].Size ||
809 (NextField % AsanAlignment) != 0)
812 F, {Builder.CreateAdd(ThisPtr, Builder.getIntN(PtrSize, EndOffset)),
813 Builder.getIntN(PtrSize, PoisonSize)});
819 EmitAsanPrologueOrEpilogue(
true);
823 assert((CGM.getTarget().getCXXABI().hasConstructorVariants() ||
825 "can only generate complete ctor for this ABI");
829 if (CtorType ==
Ctor_Complete && IsConstructorDelegationValid(Ctor) &&
830 CGM.getTarget().getCXXABI().hasConstructorVariants()) {
837 assert(Definition == Ctor &&
"emitting wrong constructor body");
841 bool IsTryBody = (Body && isa<CXXTryStmt>(Body));
843 EnterCXXTryStmt(*cast<CXXTryStmt>(Body),
true);
845 incrementProfileCounter(Body);
854 EmitCtorPrologue(Ctor, CtorType, Args);
858 EmitStmt(cast<CXXTryStmt>(Body)->getTryBlock());
869 ExitCXXTryStmt(*cast<CXXTryStmt>(Body),
true);
877 class CopyingValueRepresentation {
880 : CGF(CGF), OldSanOpts(CGF.
SanOpts) {
884 ~CopyingValueRepresentation() {
894 class FieldMemcpyizer {
898 : CGF(CGF), ClassDecl(ClassDecl), SrcRec(SrcRec),
900 FirstField(
nullptr), LastField(
nullptr), FirstFieldOffset(0),
901 LastFieldOffset(0), LastAddedFieldIndex(0) {}
903 bool isMemcpyableField(
FieldDecl *F)
const {
922 CharUnits getMemcpySize(uint64_t FirstByteOffset)
const {
924 unsigned LastFieldSize =
925 LastField->isBitField()
926 ? LastField->getBitWidthValue(Ctx)
929 uint64_t MemcpySizeBits = LastFieldOffset + LastFieldSize -
942 uint64_t FirstByteOffset;
943 if (FirstField->isBitField()) {
951 FirstByteOffset = FirstFieldOffset;
954 CharUnits MemcpySize = getMemcpySize(FirstByteOffset);
971 FirstField =
nullptr;
980 llvm::PointerType *DPT = DestPtr.
getType();
982 llvm::Type::getInt8PtrTy(CGF.
getLLVMContext(), DPT->getAddressSpace());
985 llvm::PointerType *SPT = SrcPtr.
getType();
987 llvm::Type::getInt8PtrTy(CGF.
getLLVMContext(), SPT->getAddressSpace());
996 FirstFieldOffset = RecLayout.getFieldOffset(F->
getFieldIndex());
997 LastFieldOffset = FirstFieldOffset;
1007 "Cannot aggregate fields out of order.");
1013 uint64_t FOffset = RecLayout.getFieldOffset(F->
getFieldIndex());
1014 if (FOffset < FirstFieldOffset) {
1016 FirstFieldOffset = FOffset;
1017 }
else if (FOffset >= LastFieldOffset) {
1019 LastFieldOffset = FOffset;
1027 uint64_t FirstFieldOffset, LastFieldOffset;
1028 unsigned LastAddedFieldIndex;
1031 class ConstructorMemcpyizer :
public FieldMemcpyizer {
1046 if (!MemcpyableCtor)
1049 assert(Field &&
"No field for member init.");
1060 if (!isMemcpyableField(Field))
1070 : FieldMemcpyizer(CGF, CD->
getParent(), getTrivialCopySource(CGF, CD, Args)),
1071 ConstructorDecl(CD),
1078 if (isMemberInitMemcpyable(MemberInit)) {
1079 AggregatedInits.push_back(MemberInit);
1080 addMemcpyableField(MemberInit->
getMember());
1082 emitAggregatedInits();
1084 ConstructorDecl, Args);
1088 void emitAggregatedInits() {
1089 if (AggregatedInits.size() <= 1) {
1092 if (!AggregatedInits.empty()) {
1093 CopyingValueRepresentation CVR(CGF);
1095 AggregatedInits[0], ConstructorDecl, Args);
1096 AggregatedInits.clear();
1102 pushEHDestructors();
1104 AggregatedInits.clear();
1107 void pushEHDestructors() {
1112 for (
unsigned i = 0; i < AggregatedInits.size(); ++i) {
1125 emitAggregatedInits();
1130 bool MemcpyableCtor;
1135 class AssignmentMemcpyizer :
public FieldMemcpyizer {
1140 if (!AssignmentsMemcpyable)
1144 if (BO->getOpcode() != BO_Assign)
1150 if (!Field || !isMemcpyableField(Field))
1152 Stmt *RHS = BO->getRHS();
1154 RHS = EC->getSubExpr();
1157 if (
MemberExpr *ME2 = dyn_cast<MemberExpr>(RHS)) {
1158 if (ME2->getMemberDecl() == Field)
1170 if (!Field || !isMemcpyableField(Field))
1173 if (!Arg0 || Field != dyn_cast<FieldDecl>(Arg0->
getMemberDecl()))
1176 }
else if (
CallExpr *CE = dyn_cast<CallExpr>(S)) {
1178 if (!FD || FD->
getBuiltinID() != Builtin::BI__builtin_memcpy)
1180 Expr *DstPtr = CE->getArg(0);
1182 DstPtr = DC->getSubExpr();
1184 if (!DUO || DUO->
getOpcode() != UO_AddrOf)
1190 if (!Field || !isMemcpyableField(Field))
1192 Expr *SrcPtr = CE->getArg(1);
1194 SrcPtr = SC->getSubExpr();
1196 if (!SUO || SUO->
getOpcode() != UO_AddrOf)
1199 if (!ME2 || Field != dyn_cast<FieldDecl>(ME2->
getMemberDecl()))
1207 bool AssignmentsMemcpyable;
1213 : FieldMemcpyizer(CGF, AD->
getParent(), Args[Args.size() - 1]),
1215 assert(Args.size() == 2);
1218 void emitAssignment(
Stmt *S) {
1221 addMemcpyableField(F);
1222 AggregatedStmts.push_back(S);
1224 emitAggregatedStmts();
1229 void emitAggregatedStmts() {
1230 if (AggregatedStmts.size() <= 1) {
1231 if (!AggregatedStmts.empty()) {
1232 CopyingValueRepresentation CVR(CGF);
1239 AggregatedStmts.clear();
1243 emitAggregatedStmts();
1250 const auto *BaseClassDecl =
1252 return BaseClassDecl->isDynamicClass();
1261 return EmitDelegatingCXXConstructorCall(CD, Args);
1275 bool ConstructVBases = CtorType !=
Ctor_Base &&
1282 llvm::BasicBlock *BaseCtorContinueBB =
nullptr;
1283 if (ConstructVBases &&
1284 !CGM.getTarget().getCXXABI().hasConstructorVariants()) {
1285 BaseCtorContinueBB =
1286 CGM.getCXXABI().EmitCtorCompleteObjectHandler(*
this, ClassDecl);
1287 assert(BaseCtorContinueBB);
1291 for (; B != E && (*B)->isBaseInitializer() && (*B)->isBaseVirtual(); B++) {
1292 if (!ConstructVBases)
1294 if (CGM.getCodeGenOpts().StrictVTablePointers &&
1295 CGM.getCodeGenOpts().OptimizationLevel > 0 &&
1297 CXXThisValue = Builder.CreateLaunderInvariantGroup(LoadCXXThis());
1301 if (BaseCtorContinueBB) {
1303 Builder.CreateBr(BaseCtorContinueBB);
1304 EmitBlock(BaseCtorContinueBB);
1308 for (; B != E && (*B)->isBaseInitializer(); B++) {
1309 assert(!(*B)->isBaseVirtual());
1311 if (CGM.getCodeGenOpts().StrictVTablePointers &&
1312 CGM.getCodeGenOpts().OptimizationLevel > 0 &&
1314 CXXThisValue = Builder.CreateLaunderInvariantGroup(LoadCXXThis());
1318 CXXThisValue = OldThis;
1320 InitializeVTablePointers(ClassDecl);
1324 ConstructorMemcpyizer CM(*
this, CD, Args);
1325 for (; B != E; B++) {
1329 "Delegating initializer on non-delegating constructor");
1330 CM.addMemberInitializer(Member);
1351 for (
const auto *Field : BaseClassDecl->
fields())
1356 for (
const auto &I : BaseClassDecl->
bases()) {
1361 cast<CXXRecordDecl>(I.getType()->castAs<
RecordType>()->getDecl());
1363 MostDerivedClassDecl))
1367 if (BaseClassDecl == MostDerivedClassDecl) {
1369 for (
const auto &I : BaseClassDecl->
vbases()) {
1371 cast<CXXRecordDecl>(I.getType()->castAs<
RecordType>()->getDecl());
1373 MostDerivedClassDecl))
1412 for (
const auto *Field : ClassDecl->
fields())
1430 llvm::CallInst *TrapCall = EmitTrapCall(llvm::Intrinsic::trap);
1431 TrapCall->setDoesNotReturn();
1432 TrapCall->setDoesNotThrow();
1433 Builder.CreateUnreachable();
1434 Builder.ClearInsertionPoint();
1440 incrementProfileCounter(Body);
1449 if (HaveInsertPoint()) {
1452 false, LoadCXXThisAddress(), ThisTy);
1459 bool isTryBody = (Body && isa<CXXTryStmt>(Body));
1461 EnterCXXTryStmt(*cast<CXXTryStmt>(Body),
true);
1462 EmitAsanPrologueOrEpilogue(
false);
1473 case Dtor_Comdat: llvm_unreachable(
"not expecting a COMDAT");
1474 case Dtor_Deleting: llvm_unreachable(
"already handled deleting case");
1478 "can't emit a dtor without a body for non-Microsoft ABIs");
1485 EmitCXXDestructorCall(Dtor,
Dtor_Base,
false,
1486 false, LoadCXXThisAddress(), ThisTy);
1503 if (CGM.getCodeGenOpts().StrictVTablePointers &&
1504 CGM.getCodeGenOpts().OptimizationLevel > 0)
1505 CXXThisValue = Builder.CreateLaunderInvariantGroup(LoadCXXThis());
1506 InitializeVTablePointers(Dtor->
getParent());
1510 EmitStmt(cast<CXXTryStmt>(Body)->getTryBlock());
1514 assert(Dtor->
isImplicit() &&
"bodyless dtor not implicit");
1520 CurFn->addFnAttr(llvm::Attribute::AlwaysInline);
1530 ExitCXXTryStmt(*cast<CXXTryStmt>(Body),
true);
1534 const CXXMethodDecl *AssignOp = cast<CXXMethodDecl>(CurGD.getDecl());
1536 assert(isa<CompoundStmt>(RootS) &&
1537 "Body of an implicit assignment operator should be compound stmt.");
1538 const CompoundStmt *RootCS = cast<CompoundStmt>(RootS);
1542 incrementProfileCounter(RootCS);
1543 AssignmentMemcpyizer AM(*
this, AssignOp, Args);
1544 for (
auto *I : RootCS->
body())
1545 AM.emitAssignment(I);
1565 LoadThisForDtorDelete(CGF, Dtor),
1572 bool ReturnAfterDelete) {
1576 = CGF.
Builder.CreateIsNull(ShouldDeleteCondition);
1577 CGF.
Builder.CreateCondBr(ShouldCallDelete, continueBB, callDeleteBB);
1583 LoadThisForDtorDelete(CGF, Dtor),
1586 ReturnAfterDelete &&
1587 "unexpected value for ReturnAfterDelete");
1588 if (ReturnAfterDelete)
1591 CGF.
Builder.CreateBr(continueBB);
1600 CallDtorDeleteConditional(
llvm::Value *ShouldDeleteCondition)
1601 : ShouldDeleteCondition(ShouldDeleteCondition) {
1602 assert(ShouldDeleteCondition !=
nullptr);
1606 EmitConditionalDtorDeleteCall(CGF, ShouldDeleteCondition,
1614 bool useEHCleanupForArray;
1618 bool useEHCleanupForArray)
1619 : field(field), destroyer(destroyer),
1620 useEHCleanupForArray(useEHCleanupForArray) {}
1631 flags.isForNormalCleanup() && useEHCleanupForArray);
1641 llvm::ConstantInt::get(CGF.
SizeTy, PoisonSize)};
1645 llvm::FunctionType *FnType =
1646 llvm::FunctionType::get(CGF.
VoidTy, ArgTypes,
false);
1647 llvm::FunctionCallee Fn =
1670 CGF.
CurFn->addFnAttr(
"disable-tail-calls",
"true");
1675 unsigned fieldIndex = 0;
1676 int startIndex = -1;
1683 startIndex = fieldIndex;
1690 }
else if (startIndex >= 0) {
1692 PoisonMembers(CGF, startIndex, fieldIndex);
1706 unsigned layoutEndOffset) {
1711 llvm::ConstantInt *OffsetSizePtr = llvm::ConstantInt::get(
1733 if (PoisonSize == 0)
1736 EmitSanitizerDtorCallback(CGF, OffsetPtr, PoisonSize);
1758 EmitSanitizerDtorCallback(CGF, VTablePtr, PoisonSize);
1772 "Should not emit dtor epilogue for non-exported trivial dtor!");
1778 "operator delete missing - EnterDtorCleanups");
1779 if (CXXStructorImplicitParamValue) {
1783 EmitConditionalDtorDeleteCall(*
this, CXXStructorImplicitParamValue,
1786 EHStack.pushCleanup<CallDtorDeleteConditional>(
1792 LoadThisForDtorDelete(*
this, DD),
1794 EmitBranchThroughCleanup(ReturnBlock);
1812 if (CGM.getCodeGenOpts().SanitizeMemoryUseAfterDtor &&
1813 SanOpts.has(SanitizerKind::Memory) && ClassDecl->
getNumVBases() &&
1819 for (
const auto &
Base : ClassDecl->
vbases()) {
1820 auto *BaseClassDecl =
1821 cast<CXXRecordDecl>(
Base.getType()->castAs<
RecordType>()->getDecl());
1824 if (BaseClassDecl->hasTrivialDestructor())
1838 if (CGM.getCodeGenOpts().SanitizeMemoryUseAfterDtor &&
1839 SanOpts.has(SanitizerKind::Memory) && !ClassDecl->
getNumVBases() &&
1844 for (
const auto &
Base : ClassDecl->
bases()) {
1846 if (
Base.isVirtual())
1862 if (CGM.getCodeGenOpts().SanitizeMemoryUseAfterDtor &&
1863 SanOpts.has(SanitizerKind::Memory))
1867 for (
const auto *Field : ClassDecl->
fields()) {
1870 if (!dtorKind)
continue;
1876 CleanupKind cleanupKind = getCleanupKind(dtorKind);
1877 EHStack.pushCleanup<DestroyField>(cleanupKind, Field,
1878 getDestroyer(dtorKind),
1894 bool zeroInitialize) {
1897 emitArrayLength(arrayType, elementType, arrayBegin);
1899 EmitCXXAggrConstructorCall(ctor, numElements, arrayBegin, E,
1900 NewPointerIsChecked, zeroInitialize);
1916 bool NewPointerIsChecked,
1917 bool zeroInitialize) {
1923 llvm::BranchInst *zeroCheckBranch =
nullptr;
1926 llvm::ConstantInt *constantCount
1927 = dyn_cast<llvm::ConstantInt>(numElements);
1928 if (constantCount) {
1930 if (constantCount->isZero())
return;
1934 llvm::BasicBlock *loopBB = createBasicBlock(
"new.ctorloop");
1935 llvm::Value *iszero = Builder.CreateIsNull(numElements,
"isempty");
1936 zeroCheckBranch = Builder.CreateCondBr(iszero, loopBB, loopBB);
1942 llvm::Value *arrayEnd = Builder.CreateInBoundsGEP(arrayBegin, numElements,
1946 llvm::BasicBlock *entryBB = Builder.GetInsertBlock();
1947 llvm::BasicBlock *loopBB = createBasicBlock(
"arrayctor.loop");
1949 llvm::PHINode *cur = Builder.CreatePHI(arrayBegin->getType(), 2,
1951 cur->addIncoming(arrayBegin, entryBB);
1969 EmitNullInitialization(curAddr, type);
1986 Destroyer *destroyer = destroyCXXObject;
1987 pushRegularPartialArrayCleanup(arrayBegin, cur, type, eltAlignment,
2002 Builder.CreateInBoundsGEP(cur, llvm::ConstantInt::get(
SizeTy, 1),
2004 cur->addIncoming(next, Builder.GetInsertBlock());
2007 llvm::Value *done = Builder.CreateICmpEQ(next, arrayEnd,
"arrayctor.done");
2008 llvm::BasicBlock *contBB = createBasicBlock(
"arrayctor.cont");
2009 Builder.CreateCondBr(done, contBB, loopBB);
2012 if (zeroCheckBranch) zeroCheckBranch->setSuccessor(0, contBB);
2023 assert(!dtor->isTrivial());
2030 bool ForVirtualBase,
2041 if (SlotAS != ThisAS) {
2044 ThisPtr->getType()->getPointerElementType()->getPointerTo(TargetThisAS);
2045 ThisPtr = getTargetHooks().performAddrSpaceCast(*
this, This.
getPointer(),
2046 ThisAS, SlotAS, NewType);
2056 assert(E->
getNumArgs() == 1 &&
"unexpected argcount for trivial ctor");
2059 LValue Src = EmitLValue(Arg);
2061 LValue Dest = MakeAddrLValue(This, DestTy);
2062 EmitAggregateCopyCtor(Dest, Src, ThisAVS.
mayOverlap());
2069 ? EvaluationOrder::ForceLeftToRight
2074 EmitCXXConstructorCall(D, Type, ForVirtualBase, Delegating, This, Args,
2105 bool ForVirtualBase,
2111 bool NewPointerIsChecked) {
2114 if (!NewPointerIsChecked)
2119 assert(Args.size() == 1 &&
"trivial default ctor with args");
2127 assert(Args.size() == 2 &&
"unexpected argcount for trivial ctor");
2130 Address Src(Args[1].getRValue(*this).getScalarVal(),
2131 getNaturalTypeAlignment(SrcTy));
2132 LValue SrcLVal = MakeAddrLValue(Src, SrcTy);
2134 LValue DestLVal = MakeAddrLValue(This, DestTy);
2135 EmitAggregateCopyCtor(DestLVal, SrcLVal, Overlap);
2139 bool PassPrototypeArgs =
true;
2144 EmitInlinedInheritingCXXConstructorCall(D, Type, ForVirtualBase,
2152 CGM.getCXXABI().addImplicitConstructorArgs(*
this, D, Type, ForVirtualBase,
2156 llvm::Constant *CalleePtr = CGM.getAddrOfCXXStructor(
GlobalDecl(D, Type));
2157 const CGFunctionInfo &Info = CGM.getTypes().arrangeCXXConstructorCall(
2158 Args, D, Type, ExtraArgs.
Prefix, ExtraArgs.
Suffix, PassPrototypeArgs);
2173 if (CGM.getCodeGenOpts().OptimizationLevel > 0 &&
2175 CGM.getCXXABI().canSpeculativelyEmitVTable(ClassDecl) &&
2176 CGM.getCodeGenOpts().StrictVTablePointers)
2177 EmitVTableAssumptionLoads(ClassDecl, This);
2187 if (InheritedFromVBase &&
2188 CGM.getTarget().getCXXABI().hasConstructorVariants()) {
2193 Args.push_back(ThisArg);
2194 }
else if (!CXXInheritedCtorInitExprArgs.empty()) {
2196 assert(CXXInheritedCtorInitExprArgs.size() >= D->
getNumParams() &&
2197 "wrong number of parameters for inherited constructor call");
2198 Args = CXXInheritedCtorInitExprArgs;
2202 Args.push_back(ThisArg);
2203 const auto *OuterCtor = cast<CXXConstructorDecl>(CurCodeDecl);
2204 assert(OuterCtor->getNumParams() == D->
getNumParams());
2205 assert(!OuterCtor->isVariadic() &&
"should have been inlined");
2207 for (
const auto *Param : OuterCtor->parameters()) {
2209 OuterCtor->getParamDecl(Param->getFunctionScopeIndex())->getType(),
2211 EmitDelegateCallArg(Args, Param, E->
getLocation());
2214 if (Param->hasAttr<PassObjectSizeAttr>()) {
2215 auto *POSParam = SizeArguments[Param];
2216 assert(POSParam &&
"missing pass_object_size value for forwarding");
2217 EmitDelegateCallArg(Args, POSParam, E->
getLocation());
2222 EmitCXXConstructorCall(D,
Ctor_Base, ForVirtualBase,
false,
2236 CXXInheritedCtorInitExprArgs = Args;
2239 QualType RetType = BuildFunctionArgList(CurGD, Params);
2243 CGM.getCXXABI().addImplicitConstructorArgs(*
this, Ctor, CtorType,
2244 ForVirtualBase, Delegating, Args);
2247 assert(Args.size() >= Params.size() &&
"too few arguments for call");
2248 for (
unsigned I = 0, N = Args.size(); I != N; ++I) {
2249 if (I < Params.size() && isa<ImplicitParamDecl>(Params[I])) {
2250 const RValue &RV = Args[I].getRValue(*
this);
2251 assert(!RV.
isComplex() &&
"complex indirect params not supported");
2255 EmitParmDecl(*Params[I], Val, I + 1);
2263 ReturnValue = CreateIRTemp(RetType,
"retval.inhctor");
2265 CGM.getCXXABI().EmitInstanceFunctionProlog(*
this);
2266 CXXThisValue = CXXABIThisValue;
2269 EmitCtorPrologue(Ctor, CtorType, Params);
2281 if (!NonVirtualOffset.
isZero())
2289 Builder.CreateICmpEQ(VPtrValue, VTableGlobal,
"cmp.vtables");
2290 Builder.CreateAssumption(Cmp);
2295 if (CGM.getCXXABI().doStructorsInitializeVPtrs(ClassDecl))
2296 for (
const VPtr &Vptr : getVTablePointers(ClassDecl))
2297 EmitVTableAssumptionLoad(Vptr, This);
2313 llvm::Type *t = CGM.getTypes().ConvertType(QT);
2314 Src = Builder.CreateBitCast(Src, t);
2334 FunctionArgList::const_iterator I = Args.begin(), E = Args.end();
2335 assert(I != E &&
"no parameters to constructor");
2344 if (CGM.getCXXABI().NeedsVTTParameter(CurGD)) {
2345 assert(I != E &&
"cannot skip vtt parameter, already done with args");
2346 assert((*I)->getType()->isPointerType() &&
2347 "skipping parameter not of vtt type");
2352 for (; I != E; ++I) {
2355 EmitDelegateCallArg(DelegateArgs, param, Loc);
2358 EmitCXXConstructorCall(Ctor, CtorType,
false,
2359 true, This, DelegateArgs,
2372 : Dtor(D), Addr(Addr),
Type(Type) {}
2377 QualType ThisTy = Dtor->getThisObjectType();
2379 true, Addr, ThisTy);
2389 Address ThisPtr = LoadCXXThisAddress();
2404 if (CGM.getLangOpts().Exceptions && !ClassDecl->hasTrivialDestructor()) {
2408 EHStack.pushCleanup<CallDelegatingCtorDtor>(
EHCleanup,
2409 ClassDecl->getDestructor(),
2416 bool ForVirtualBase,
2419 CGM.getCXXABI().EmitDestructorCall(*
this, DD, Type, ForVirtualBase,
2420 Delegating, This, ThisTy);
2430 : Dtor(D), Addr(Addr), Ty(Ty) {}
2447 if (!ClassDecl)
return;
2451 assert(D && D->
isUsed() &&
"destructor not marked as used!");
2452 PushDestructorCleanup(D, T, Addr);
2458 CGM.getCXXABI().getVTableAddressPointInStructor(
2461 if (!VTableAddressPoint)
2468 if (CGM.getCXXABI().isVirtualOffsetNeededForVTableField(*
this, Vptr)) {
2472 VirtualOffset = CGM.getCXXABI().GetVirtualBaseClassOffset(
2481 Address VTableField = LoadCXXThisAddress();
2483 if (!NonVirtualOffset.
isZero() || VirtualOffset)
2485 *
this, VTableField, NonVirtualOffset, VirtualOffset, Vptr.
VTableClass,
2491 llvm::FunctionType::get(CGM.Int32Ty,
true)
2494 VTableField = Builder.CreateBitCast(VTableField, VTablePtrTy->getPointerTo());
2495 VTableAddressPoint = Builder.CreateBitCast(VTableAddressPoint, VTablePtrTy);
2497 llvm::StoreInst *
Store = Builder.CreateStore(VTableAddressPoint, VTableField);
2498 TBAAAccessInfo TBAAInfo = CGM.getTBAAVTablePtrAccessInfo(VTablePtrTy);
2499 CGM.DecorateInstructionWithTBAA(Store, TBAAInfo);
2500 if (CGM.getCodeGenOpts().OptimizationLevel > 0 &&
2501 CGM.getCodeGenOpts().StrictVTablePointers)
2502 CGM.DecorateInstructionWithInvariantGroup(Store, Vptr.
VTableClass);
2512 false, VTableClass, VBases,
2520 bool BaseIsNonVirtualPrimaryBase,
2526 if (!BaseIsNonVirtualPrimaryBase) {
2528 VPtr Vptr = {Base, NearestVBase, OffsetFromNearestVBase, VTableClass};
2529 Vptrs.push_back(Vptr);
2535 for (
const auto &I : RD->
bases()) {
2537 cast<CXXRecordDecl>(I.getType()->castAs<
RecordType>()->getDecl());
2540 if (!BaseDecl->isDynamicClass())
2545 bool BaseDeclIsNonVirtualPrimaryBase;
2547 if (I.isVirtual()) {
2549 if (!VBases.insert(BaseDecl).second)
2557 BaseDeclIsNonVirtualPrimaryBase =
false;
2562 BaseOffsetFromNearestVBase =
2564 BaseDeclIsNonVirtualPrimaryBase = Layout.
getPrimaryBase() == BaseDecl;
2569 I.isVirtual() ? BaseDecl : NearestVBase, BaseOffsetFromNearestVBase,
2570 BaseDeclIsNonVirtualPrimaryBase, VTableClass, VBases, Vptrs);
2580 if (CGM.getCXXABI().doStructorsInitializeVPtrs(RD))
2581 for (
const VPtr &Vptr : getVTablePointers(RD))
2582 InitializeVTablePointer(Vptr);
2585 CGM.getCXXABI().initializeHiddenVirtualInheritanceMembers(*
this, RD);
2591 Address VTablePtrSrc = Builder.CreateElementBitCast(This, VTableTy);
2592 llvm::Instruction *VTable = Builder.CreateLoad(VTablePtrSrc,
"vtable");
2593 TBAAAccessInfo TBAAInfo = CGM.getTBAAVTablePtrAccessInfo(VTableTy);
2594 CGM.DecorateInstructionWithTBAA(VTable, TBAAInfo);
2596 if (CGM.getCodeGenOpts().OptimizationLevel > 0 &&
2597 CGM.getCodeGenOpts().StrictVTablePointers)
2598 CGM.DecorateInstructionWithInvariantGroup(VTable, RD);
2624 if (MD->isVirtual()) {
2628 if (isa<CXXDestructorDecl>(MD) && MD->isImplicit())
2641 if (SanOpts.has(SanitizerKind::CFIVCall))
2643 else if (CGM.getCodeGenOpts().WholeProgramVTables &&
2644 CGM.HasHiddenLTOVisibility(RD)) {
2645 llvm::Metadata *MD =
2648 llvm::MetadataAsValue::get(CGM.getLLVMContext(), MD);
2652 Builder.CreateCall(CGM.getIntrinsic(llvm::Intrinsic::type_test),
2653 {CastedVTable, TypeId});
2654 Builder.CreateCall(CGM.getIntrinsic(llvm::Intrinsic::assume), TypeTest);
2662 if (!SanOpts.has(SanitizerKind::CFICastStrict))
2665 EmitVTablePtrCheck(RD, VTable, TCK, Loc);
2680 const CXXRecordDecl *ClassDecl = cast<CXXRecordDecl>(ClassTy->getDecl());
2685 if (!SanOpts.has(SanitizerKind::CFICastStrict))
2688 llvm::BasicBlock *ContBlock =
nullptr;
2692 Builder.CreateIsNotNull(Derived,
"cast.nonnull");
2694 llvm::BasicBlock *CheckBlock = createBasicBlock(
"cast.check");
2695 ContBlock = createBasicBlock(
"cast.cont");
2697 Builder.CreateCondBr(DerivedNotNull, CheckBlock, ContBlock);
2699 EmitBlock(CheckBlock);
2703 std::tie(VTable, ClassDecl) = CGM.getCXXABI().LoadVTablePtr(
2706 EmitVTablePtrCheck(ClassDecl, VTable, TCK, Loc);
2709 Builder.CreateBr(ContBlock);
2710 EmitBlock(ContBlock);
2718 if (!CGM.getCodeGenOpts().SanitizeCfiCrossDso &&
2719 !CGM.HasHiddenLTOVisibility(RD))
2723 llvm::SanitizerStatKind SSK;
2726 M = SanitizerKind::CFIVCall;
2727 SSK = llvm::SanStat_CFI_VCall;
2730 M = SanitizerKind::CFINVCall;
2731 SSK = llvm::SanStat_CFI_NVCall;
2733 case CFITCK_DerivedCast:
2734 M = SanitizerKind::CFIDerivedCast;
2735 SSK = llvm::SanStat_CFI_DerivedCast;
2737 case CFITCK_UnrelatedCast:
2738 M = SanitizerKind::CFIUnrelatedCast;
2739 SSK = llvm::SanStat_CFI_UnrelatedCast;
2742 case CFITCK_NVMFCall:
2743 case CFITCK_VMFCall:
2744 llvm_unreachable(
"unexpected sanitizer kind");
2748 if (
getContext().getSanitizerBlacklist().isBlacklistedType(M, TypeName))
2752 EmitSanitizerStatReport(SSK);
2754 llvm::Metadata *MD =
2760 CGM.getIntrinsic(llvm::Intrinsic::type_test), {CastedVTable, TypeId});
2762 llvm::Constant *StaticData[] = {
2763 llvm::ConstantInt::get(
Int8Ty, TCK),
2764 EmitCheckSourceLocation(Loc),
2768 auto CrossDsoTypeId = CGM.CreateCrossDsoCfiTypeId(MD);
2769 if (CGM.getCodeGenOpts().SanitizeCfiCrossDso && CrossDsoTypeId) {
2770 EmitCfiSlowPathCheck(M, TypeTest, CrossDsoTypeId, CastedVTable, StaticData);
2774 if (CGM.getCodeGenOpts().SanitizeTrap.has(M)) {
2775 EmitTrapCheck(TypeTest);
2779 llvm::Value *AllVtables = llvm::MetadataAsValue::get(
2780 CGM.getLLVMContext(),
2781 llvm::MDString::get(CGM.getLLVMContext(),
"all-vtables"));
2783 CGM.getIntrinsic(llvm::Intrinsic::type_test), {CastedVTable, AllVtables});
2784 EmitCheck(std::make_pair(TypeTest, M), SanitizerHandler::CFICheckFail,
2785 StaticData, {CastedVTable, ValidVtable});
2789 if (!CGM.getCodeGenOpts().WholeProgramVTables ||
2790 !CGM.HasHiddenLTOVisibility(RD))
2793 if (CGM.getCodeGenOpts().VirtualFunctionElimination)
2796 if (!SanOpts.has(SanitizerKind::CFIVCall) ||
2797 !CGM.getCodeGenOpts().SanitizeTrap.has(SanitizerKind::CFIVCall))
2802 SanitizerKind::CFIVCall, TypeName);
2809 EmitSanitizerStatReport(llvm::SanStat_CFI_VCall);
2811 llvm::Metadata *MD =
2813 llvm::Value *TypeId = llvm::MetadataAsValue::get(CGM.getLLVMContext(), MD);
2817 CGM.getIntrinsic(llvm::Intrinsic::type_checked_load),
2818 {CastedVTable, llvm::ConstantInt::get(
Int32Ty, VTableByteOffset),
2820 llvm::Value *CheckResult = Builder.CreateExtractValue(CheckedLoad, 1);
2823 if (SanOpts.has(SanitizerKind::CFIVCall) &&
2825 SanitizerKind::CFIVCall, TypeName)) {
2826 EmitCheck(std::make_pair(CheckResult, SanitizerKind::CFIVCall),
2827 SanitizerHandler::CFICheckFail, {}, {});
2830 return Builder.CreateBitCast(
2831 Builder.CreateExtractValue(CheckedLoad, 0),
2832 cast<llvm::PointerType>(VTable->getType())->getElementType());
2840 CGM.getTypes().arrangeCXXMethodDeclaration(callOperator);
2841 llvm::Constant *calleePtr =
2842 CGM.GetAddrOfFunction(
GlobalDecl(callOperator),
2843 CGM.getTypes().GetFunctionType(calleeFnInfo));
2850 if (!resultType->isVoidType() &&
2861 RValue RV = EmitCall(calleeFnInfo, callee, returnSlot, callArgs);
2864 if (!resultType->isVoidType() && returnSlot.
isNull()) {
2865 if (
getLangOpts().ObjCAutoRefCount && resultType->isObjCRetainableType()) {
2868 EmitReturnOfRValue(RV, resultType);
2870 EmitBranchThroughCleanup(ReturnBlock);
2874 const BlockDecl *BD = BlockInfo->getBlockDecl();
2883 CGM.ErrorUnsupported(CurCodeDecl,
"lambda conversion to variadic function");
2891 Address ThisPtr = GetAddrOfBlockDecl(variable);
2896 EmitDelegateCallArg(CallArgs, param, param->getBeginLoc());
2899 "generic lambda interconversion to block not implemented");
2900 EmitForwardingCallToLambda(CallOp, CallArgs);
2915 EmitDelegateCallArg(CallArgs, Param, Param->getBeginLoc());
2924 void *InsertPos =
nullptr;
2927 assert(CorrespondingCallOpSpecialization);
2928 CallOp = cast<CXXMethodDecl>(CorrespondingCallOpSpecialization);
2930 EmitForwardingCallToLambda(CallOp, CallArgs);
2937 CGM.ErrorUnsupported(MD,
"lambda conversion to variadic function");
2941 EmitLambdaDelegatingInvokeBody(MD);
bool isBaseInitializer() const
Determine whether this initializer is initializing a base class.
ReturnValueSlot - Contains the address where the return value of a function can be stored...
void EnterDtorCleanups(const CXXDestructorDecl *Dtor, CXXDtorType Type)
EnterDtorCleanups - Enter the cleanups necessary to complete the given phase of destruction for a des...
Represents a function declaration or definition.
LValue MakeNaturalAlignPointeeAddrLValue(llvm::Value *V, QualType T)
Given a value of type T* that may not be to a complete object, construct an l-value with the natural ...
Address getAddress() const
Expr * getInit() const
Get the initializer.
void EmitDelegateCXXConstructorCall(const CXXConstructorDecl *Ctor, CXXCtorType CtorType, const FunctionArgList &Args, SourceLocation Loc)
A (possibly-)qualified type.
const CGBitFieldInfo & getBitFieldInfo(const FieldDecl *FD) const
Return the BitFieldInfo that corresponds to the field FD.
Address EmitCXXMemberDataPointerAddress(const Expr *E, Address base, llvm::Value *memberPtr, const MemberPointerType *memberPtrType, LValueBaseInfo *BaseInfo=nullptr, TBAAAccessInfo *TBAAInfo=nullptr)
Emit the address of a field using a member data pointer.
void EmitCtorPrologue(const CXXConstructorDecl *CD, CXXCtorType Type, FunctionArgList &Args)
EmitCtorPrologue - This routine generates necessary code to initialize base classes and non-static da...
bool isPODType(const ASTContext &Context) const
Determine whether this is a Plain Old Data (POD) type (C++ 3.9p10).
CodeGenTypes & getTypes()
ValueDecl * getMemberDecl() const
Retrieve the member declaration to which this expression refers.
unsigned getNumBases() const
Retrieves the number of base classes of this class.
CGRecordLayout - This class handles struct and union layout info while lowering AST types to LLVM typ...
bool isBlacklistedType(SanitizerMask Mask, StringRef MangledTypeName, StringRef Category=StringRef()) const
FunctionDecl * findSpecialization(ArrayRef< TemplateArgument > Args, void *&InsertPos)
Return the specialization with the provided arguments if it exists, otherwise return the insertion po...
capture_const_iterator capture_begin() const
llvm::LLVMContext & getLLVMContext()
CharUnits getClassPointerAlignment(const CXXRecordDecl *CD)
Returns the assumed alignment of an opaque pointer to the given class.
const ASTRecordLayout & getASTRecordLayout(const RecordDecl *D) const
Get or compute information about the layout of the specified record (struct/union/class) D...
Stmt - This represents one statement.
Address GetAddressOfDirectBaseInCompleteClass(Address Value, const CXXRecordDecl *Derived, const CXXRecordDecl *Base, bool BaseIsVirtual)
GetAddressOfBaseOfCompleteClass - Convert the given pointer to a complete class to the given direct b...
QualType getPointeeType() const
If this is a pointer, ObjC object pointer, or block pointer, this returns the respective pointee...
CharUnits getBaseClassOffset(const CXXRecordDecl *Base) const
getBaseClassOffset - Get the offset, in chars, for the given base class.
unsigned getNumVBases() const
Retrieves the number of virtual base classes of this class.
QualType getThisType() const
Return the type of the this pointer.
Address GetAddressOfDerivedClass(Address Value, const CXXRecordDecl *Derived, CastExpr::path_const_iterator PathBegin, CastExpr::path_const_iterator PathEnd, bool NullCheckValue)
Checking the 'this' pointer for a constructor call.
const Type * getTypeForDecl() const
const Decl * CurCodeDecl
CurCodeDecl - This is the inner-most code context, which includes blocks.
bool isVirtual() const
Determines whether the base class is a virtual base class (or not).
Defines the C++ template declaration subclasses.
void EmitLambdaStaticInvokeBody(const CXXMethodDecl *MD)
unsigned getFieldIndex() const
Returns the index of this field within its record, as appropriate for passing to ASTRecordLayout::get...
QualType getNonReferenceType() const
If Type is a reference type (e.g., const int&), returns the type that the reference refers to ("const...
llvm::Value * LoadCXXThis()
LoadCXXThis - Load the value of 'this'.
const RecordDecl * getParent() const
Returns the parent of this field declaration, which is the struct in which this field is defined...
static bool isMemcpyEquivalentSpecialMember(const CXXMethodDecl *D)
The base class of the type hierarchy.
Expr * getOperatorDeleteThisArg() const
Represents an array type, per C99 6.7.5.2 - Array Declarators.
Represents a call to a C++ constructor.
bool isZero() const
isZero - Test whether the quantity equals zero.
SourceLocation getEndLoc() const LLVM_READONLY
CharUnits getAlignment() const
getAlignment - Get the record alignment in characters.
LValue EmitLValueForFieldInitialization(LValue Base, const FieldDecl *Field)
EmitLValueForFieldInitialization - Like EmitLValueForField, except that if the Field is a reference...
llvm::IntegerType * Int8Ty
i8, i16, i32, and i64
Represents a C++ constructor within a class.
bool isCompleteDefinition() const
Return true if this decl has its body fully specified.
const RecordType * getAsUnionType() const
NOTE: getAs*ArrayType are methods on ASTContext.
bool isDefaultConstructor() const
Whether this constructor is a default constructor (C++ [class.ctor]p5), which can be used to default-...
bool isIndirectMemberInitializer() const
const CXXBaseSpecifier *const * path_const_iterator
Address GetAddrOfLocalVar(const VarDecl *VD)
GetAddrOfLocalVar - Return the address of a local variable.
bool ReturnValue(const T &V, APValue &R)
Convers a value to an APValue.
Represents a variable declaration or definition.
RAII object to set/unset CodeGenFunction::IsSanitizerScope.
const T * getAs() const
Member-template getAs<specific type>'.
bool This(InterpState &S, CodePtr OpPC)
AggValueSlot::Overlap_t getOverlapForFieldInit(const FieldDecl *FD)
Determine whether a field initialization may overlap some other object.
const void * Store
Store - This opaque type encapsulates an immutable mapping from locations to values.
LangAS
Defines the address space values used by the address space qualifier of QualType. ...
void EmitCXXDestructorCall(const CXXDestructorDecl *D, CXXDtorType Type, bool ForVirtualBase, bool Delegating, Address This, QualType ThisTy)
llvm::Value * GetVTTParameter(GlobalDecl GD, bool ForVirtualBase, bool Delegating)
GetVTTParameter - Return the VTT parameter that should be passed to a base constructor/destructor wit...
llvm::Value * getPointer() const
void emitImplicitAssignmentOperatorBody(FunctionArgList &Args)
The collection of all-type qualifiers we support.
void add(RValue rvalue, QualType type)
bool mayInsertExtraPadding(bool EmitRemark=false) const
Whether we are allowed to insert extra padding between fields.
bool isMoveAssignmentOperator() const
Determine whether this is a move assignment operator.
CharUnits getBaseOffset() const
getBaseOffset - Returns the base class offset.
static const CXXRecordDecl * LeastDerivedClassWithSameLayout(const CXXRecordDecl *RD)
const TargetInfo & getTarget() const
bool usesInAlloca() const
Return true if this function uses inalloca arguments.
TargetCXXABI getCXXABI() const
Get the C++ ABI currently in use.
void emitDestroy(Address addr, QualType type, Destroyer *destroyer, bool useEHCleanupForArray)
emitDestroy - Immediately perform the destruction of the given object.
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...
llvm::Type * ConvertType(QualType T)
ConvertType - Convert type T into a llvm::Type.
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
bool hasTrivialBody() const
Returns whether the function has a trivial body that does not require any specific codegen...
const CXXRecordDecl * NearestVBase
llvm::SmallPtrSet< const CXXRecordDecl *, 4 > VisitedVirtualBasesSetTy
void EmitSynthesizedCXXCopyCtorCall(const CXXConstructorDecl *D, Address This, Address Src, const CXXConstructExpr *E)
field_range fields() const
bool isVolatileQualified() const
Represents a member of a struct/union/class.
bool ShouldEmitVTableTypeCheckedLoad(const CXXRecordDecl *RD)
Returns whether we should perform a type checked load when loading a virtual function for virtual cal...
llvm::IntegerType * SizeTy
bool isReferenceType() const
void pushEHDestroy(QualType::DestructionKind dtorKind, Address addr, QualType type)
pushEHDestroy - Push the standard destructor for the given type as an EH-only cleanup.
void EmitVTablePtrCheck(const CXXRecordDecl *RD, llvm::Value *VTable, CFITypeCheckKind TCK, SourceLocation Loc)
EmitVTablePtrCheck - Emit a check that VTable is a valid virtual table for RD using llvm...
InheritedConstructor getInheritedConstructor() const
Get the constructor that this inheriting constructor is based on.
Denotes a cleanup that should run when a scope is exited using exceptional control flow (a throw stat...
static AggValueSlot forAddr(Address addr, Qualifiers quals, IsDestructed_t isDestructed, NeedsGCBarriers_t needsGC, IsAliased_t isAliased, Overlap_t mayOverlap, IsZeroed_t isZeroed=IsNotZeroed, IsSanitizerChecked_t isChecked=IsNotSanitizerChecked)
forAddr - Make a slot for an aggregate value.
static CharUnits Zero()
Zero - Construct a CharUnits quantity of zero.
CharUnits getVBaseClassOffset(const CXXRecordDecl *VBase) const
getVBaseClassOffset - Get the offset, in chars, for the given base class.
void EmitLambdaDelegatingInvokeBody(const CXXMethodDecl *MD)
ArrayRef< ParmVarDecl * > parameters() const
void EmitInitializerForField(FieldDecl *Field, LValue LHS, Expr *Init)
CharUnits getDynamicOffsetAlignment(CharUnits ActualAlign, const CXXRecordDecl *Class, CharUnits ExpectedTargetAlign)
Given a class pointer with an actual known alignment, and the expected alignment of an object at a dy...
void EmitInheritedCXXConstructorCall(const CXXConstructorDecl *D, bool ForVirtualBase, Address This, bool InheritedFromVBase, const CXXInheritedCtorInitExpr *E)
Emit a call to a constructor inherited from a base class, passing the current constructor's arguments...
void EmitCXXAggrConstructorCall(const CXXConstructorDecl *D, const ArrayType *ArrayTy, Address ArrayPtr, const CXXConstructExpr *E, bool NewPointerIsChecked, bool ZeroInitialization=false)
EmitCXXAggrConstructorCall - Emit a loop to call a particular constructor for each of several members...
bool isBitField() const
Determines whether this field is a bitfield.
bool isDelegatingConstructor() const
Determine whether this constructor is a delegating constructor.
Stmt * getBody(const FunctionDecl *&Definition) const
Retrieve the body (definition) of the function.
bool isBaseVirtual() const
Returns whether the base is virtual or not.
CharUnits - This is an opaque type for sizes expressed in character units.
void EmitTypeMetadataCodeForVCall(const CXXRecordDecl *RD, llvm::Value *VTable, SourceLocation Loc)
If whole-program virtual table optimization is enabled, emit an assumption that VTable is a member of...
bool isTriviallyCopyableType(const ASTContext &Context) const
Return true if this is a trivially copyable type (C++0x [basic.types]p9)
FunctionTemplateDecl * getDescribedFunctionTemplate() const
Retrieves the function template that is described by this function declaration.
CharUnits StorageOffset
The offset of the bitfield storage from the start of the struct.
ArrayRef< NamedDecl * > chain() const
unsigned char PointerWidthInBits
The width of a pointer into the generic address space.
CharUnits getAlignment() const
Return the alignment of this pointer.
llvm::PointerType * VoidPtrTy
A builtin binary operation expression such as "x + y" or "x <= y".
bool needsEHCleanup(QualType::DestructionKind kind)
Determines whether an EH cleanup is required to destroy a type with the given destruction kind...
CXXCtorType getCtorType() const
const CGFunctionInfo & arrangeCXXConstructorCall(const CallArgList &Args, const CXXConstructorDecl *D, CXXCtorType CtorKind, unsigned ExtraPrefixArgs, unsigned ExtraSuffixArgs, bool PassProtoArgs=true)
Arrange a call to a C++ method, passing the given arguments.
LangAS getAddressSpace() const
llvm::CallInst * CreateMemCpy(Address Dest, Address Src, llvm::Value *Size, bool IsVolatile=false)
const Type * getClass() const
Scope - A scope is a transient data structure that is used while parsing the program.
const Type * getTypePtr() const
Retrieves a pointer to the underlying (unqualified) type.
void EmitDeleteCall(const FunctionDecl *DeleteFD, llvm::Value *Ptr, QualType DeleteTy, llvm::Value *NumElements=nullptr, CharUnits CookieSize=CharUnits())
param_type_iterator param_type_begin() const
llvm::BasicBlock * createBasicBlock(const Twine &name="", llvm::Function *parent=nullptr, llvm::BasicBlock *before=nullptr)
createBasicBlock - Create an LLVM basic block.
bool isAnyMemberInitializer() const
base_class_iterator bases_begin()
void ForceCleanup(std::initializer_list< llvm::Value **> ValuesToReload={})
Force the emission of cleanups now, instead of waiting until this object is destroyed.
FieldDecl * getAnyMember() const
bool hasTrivialDestructor() const
Determine whether this class has a trivial destructor (C++ [class.dtor]p3)
GlobalDecl CurGD
CurGD - The GlobalDecl for the current function being compiled.
CharUnits getPointerAlign() const
CXXDestructorDecl * getDestructor() const
Returns the destructor decl for this class.
FieldDecl * getMember() const
If this is a member initializer, returns the declaration of the non-static data member being initiali...
unsigned getBuiltinID(bool ConsiderWrapperFunctions=false) const
Returns a value indicating whether this function corresponds to a builtin function.
bool isAbstract() const
Determine whether this class has a pure virtual function.
static bool BaseInitializerUsesThis(ASTContext &C, const Expr *Init)
Address getAggregateAddress() const
getAggregateAddr() - Return the Value* of the address of the aggregate.
init_iterator init_begin()
Retrieve an iterator to the first initializer.
bool isAnonymousStructOrUnion() const
Whether this is an anonymous struct or union.
Represents the this expression in C++.
LValue EmitLValueForField(LValue Base, const FieldDecl *Field)
CanQualType getReturnType() const
static CharUnits One()
One - Construct a CharUnits quantity of one.
CompoundStmt - This represents a group of statements like { stmt stmt }.
CXXRecordDecl * getAsCXXRecordDecl() const
Retrieves the CXXRecordDecl that this type refers to, either because the type is a RecordType or beca...
ASTContext & getContext() const
Represents a prototype with parameter type info, e.g.
bool isDynamicClass() const
CXXConstructorDecl * getConstructor() const
Get the constructor that this expression will (ultimately) call.
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.
static void EmitLValueForAnyFieldInitialization(CodeGenFunction &CGF, CXXCtorInitializer *MemberInit, LValue &LHS)
CXXCtorInitializer *const * init_const_iterator
Iterates through the member/base initializer list.
ASTRecordLayout - This class contains layout information for one RecordDecl, which is a struct/union/...
llvm::Value * GetVTablePtr(Address This, llvm::Type *VTableTy, const CXXRecordDecl *VTableClass)
GetVTablePtr - Return the Value of the vtable pointer member pointed to by This.
CXXDtorType
C++ destructor types.
Represents a block literal declaration, which is like an unnamed FunctionDecl.
This represents one expression.
static AggValueSlot forLValue(const LValue &LV, CodeGenFunction &CGF, IsDestructed_t isDestructed, NeedsGCBarriers_t needsGC, IsAliased_t isAliased, Overlap_t mayOverlap, IsZeroed_t isZeroed=IsNotZeroed, IsSanitizerChecked_t isChecked=IsNotSanitizerChecked)
bool isCopyOrMoveConstructor(unsigned &TypeQuals) const
Determine whether this is a copy or move constructor.
bool isVariadic() const
Whether this function is variadic.
bool isDefaulted() const
Whether this function is defaulted per C++0x.
Address getAddress(CodeGenFunction &CGF) const
Qualifiers getQualifiers() const
Enters a new scope for capturing cleanups, all of which will be executed once the scope is exited...
void EmitVTableAssumptionLoad(const VPtr &vptr, Address This)
Emit assumption that vptr load == global vtable.
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.
bool isSanitizerChecked() const
bool isImplicit() const
isImplicit - Indicates whether the declaration was implicitly generated by the implementation.
const TemplateArgumentList * getTemplateSpecializationArgs() const
Retrieve the template arguments used to produce this function template specialization from the primar...
QualType getTagDeclType(const TagDecl *Decl) const
Return the unique reference to the type for the specified TagDecl (struct/union/class/enum) decl...
void EmitLambdaBlockInvokeBody()
llvm::PointerType * getType() const
Return the type of the pointer value.
const CXXRecordDecl * getPrimaryBase() const
getPrimaryBase - Get the primary base for this record.
unsigned getFieldCount() const
getFieldCount - Get the number of fields in the layout.
void EmitAsanPrologueOrEpilogue(bool Prologue)
const AstTypeMatcher< ArrayType > arrayType
Matches all kinds of arrays.
bool isFunctionTemplateSpecialization() const
Determine whether this function is a function template specialization.
llvm::LLVMContext & getLLVMContext()
const CXXRecordDecl * getBase() const
getBase - Returns the base class declaration.
bool isPolymorphic() const
Whether this class is polymorphic (C++ [class.virtual]), which means that the class contains or inher...
llvm::IntegerType * Int32Ty
void EmitConstructorBody(FunctionArgList &Args)
EmitConstructorBody - Emits the body of the current constructor.
CharUnits alignmentOfArrayElement(CharUnits elementSize) const
Given that this is the alignment of the first element of an array, return the minimum alignment of an...
LValue MakeNaturalAlignAddrLValue(llvm::Value *V, QualType T)
QualType getRecordType(const RecordDecl *Decl) const
A scoped helper to set the current debug location to an inlined location.
void EmitForwardingCallToLambda(const CXXMethodDecl *LambdaCallOperator, CallArgList &CallArgs)
UnaryOperator - This represents the unary-expression's (except sizeof and alignof), the postinc/postdec operators from postfix-expression, and various extensions.
const TargetInfo & getTarget() const
QualType getTypeDeclType(const TypeDecl *Decl, const TypeDecl *PrevDecl=nullptr) const
Return the unique reference to the type for the specified type declaration.
bool isTrivial() const
Whether this function is "trivial" in some specialized C++ senses.
const LangOptions & getLangOpts() const
ASTContext & getContext() const
The COMDAT used for dtors.
const SanitizerBlacklist & getSanitizerBlacklist() const
GlobalDecl - represents a global declaration.
std::pair< CharUnits, CharUnits > getTypeInfoDataSizeInChars(QualType T) const
void EmitCXXConstructorCall(const CXXConstructorDecl *D, CXXCtorType Type, bool ForVirtualBase, bool Delegating, AggValueSlot ThisAVS, const CXXConstructExpr *E)
The l-value was considered opaque, so the alignment was determined from a type.
RecordDecl * getDecl() const
static bool CanSkipVTablePointerInitialization(CodeGenFunction &CGF, const CXXDestructorDecl *Dtor)
CanSkipVTablePointerInitialization - Check whether we need to initialize any vtable pointers before c...
uint64_t getFieldOffset(unsigned FieldNo) const
getFieldOffset - Get the offset of the given field index, in bits.
static void EmitBaseInitializer(CodeGenFunction &CGF, const CXXRecordDecl *ClassDecl, CXXCtorInitializer *BaseInit)
void set(SanitizerMask K, bool Value)
Enable or disable a certain (single) sanitizer.
Enumerates target-specific builtins in their own namespaces within namespace clang.
Address CreateBitCast(Address Addr, llvm::Type *Ty, const llvm::Twine &Name="")
Represents a call to an inherited base class constructor from an inheriting constructor.
void PushDestructorCleanup(QualType T, Address Addr)
PushDestructorCleanup - Push a cleanup to call the complete-object destructor of an object of the giv...
Encodes a location in the source.
QualType getReturnType() const
LangAS getAddressSpace() const
Return the address space of this type.
Expr * getSubExpr() const
void EmitVTableAssumptionLoads(const CXXRecordDecl *ClassDecl, Address This)
Emit assumption load for all bases.
bool inheritingCtorHasParams(const InheritedConstructor &Inherited, CXXCtorType Type)
Determine if a C++ inheriting constructor should have parameters matching those of its inherited cons...
Represents a call to a member function that may be written either with member call syntax (e...
const Decl * getDecl() const
init_iterator init_end()
Retrieve an iterator past the last initializer.
A scoped helper to set the current debug location to the specified location or preferred location of ...
QualType getBaseElementType(const ArrayType *VAT) const
Return the innermost element type of an array type.
Represents a static or instance method of a struct/union/class.
const ConstantArrayType * getAsConstantArrayType(QualType T) const
void EmitStmt(const Stmt *S, ArrayRef< const Attr *> Attrs=None)
EmitStmt - Emit the code for the statement.
virtual size_t getSrcArgforCopyCtor(const CXXConstructorDecl *, FunctionArgList &Args) const =0
const ParmVarDecl * getParamDecl(unsigned i) const
SanitizerSet SanOpts
Sanitizers enabled for this function.
bool isGenericLambda() const
Determine whether this class describes a generic lambda function object (i.e.
ImplicitCastExpr - Allows us to explicitly represent implicit type conversions, which have no direct ...
DestructionKind isDestructedType() const
Returns a nonzero value if objects of this type require non-trivial work to clean up after...
All available information about a concrete callee.
bool isUsed(bool CheckUsedAttr=true) const
Whether any (re-)declaration of the entity was used, meaning that a definition is required...
void EmitInlinedInheritingCXXConstructorCall(const CXXConstructorDecl *Ctor, CXXCtorType CtorType, bool ForVirtualBase, bool Delegating, CallArgList &Args)
Emit a call to an inheriting constructor (that is, one that invokes a constructor inherited from a ba...
CXXCtorType
C++ constructor types.
SourceLocation getExprLoc() const LLVM_READONLY
getExprLoc - Return the preferred location for the arrow when diagnosing a problem with a generic exp...
std::pair< CharUnits, CharUnits > getTypeInfoInChars(const Type *T) const
SourceLocation getLocation() const LLVM_READONLY
void InitializeVTablePointer(const VPtr &vptr)
Initialize the vtable pointer of the given subobject.
llvm::Value * EmitScalarExpr(const Expr *E, bool IgnoreResultAssign=false)
EmitScalarExpr - Emit the computation of the specified expression of LLVM scalar type, returning the result.
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.
CGFunctionInfo - Class to encapsulate the information about a function definition.
CharUnits alignmentAtOffset(CharUnits offset) const
Given that this is a non-zero alignment value, what is the alignment at the given offset...
Dataflow Directional Tag Classes.
CXXMethodDecl * getLambdaCallOperator() const
Retrieve the lambda call operator of the closure type if this is a closure type.
void EmitVTablePtrCheckForCast(QualType T, llvm::Value *Derived, bool MayBeNull, CFITypeCheckKind TCK, SourceLocation Loc)
Derived is the presumed address of an object of type T after a cast.
AggValueSlot::Overlap_t getOverlapForBaseInit(const CXXRecordDecl *RD, const CXXRecordDecl *BaseRD, bool IsVirtual)
Determine whether a base class initialization may overlap some other object.
static bool canEmitDelegateCallArgs(CodeGenFunction &CGF, const CXXConstructorDecl *Ctor, CXXCtorType Type, CallArgList &Args)
A scope within which we are constructing the fields of an object which might use a CXXDefaultInitExpr...
Represents a field injected from an anonymous union/struct into the parent scope. ...
SourceLocation getSourceLocation() const
Determine the source location of the initializer.
llvm::LoadInst * CreateLoad(Address Addr, const llvm::Twine &Name="")
llvm::IntegerType * IntPtrTy
void EmitDelegatingCXXConstructorCall(const CXXConstructorDecl *Ctor, const FunctionArgList &Args)
bool areArgsDestroyedLeftToRightInCallee() const
Are arguments to a call destroyed left to right in the callee? This is a fundamental language change...
const CXXRecordDecl * getParent() const
Return the parent of this method declaration, which is the class in which this method is defined...
bool isListInitialization() const
Whether this constructor call was written as list-initialization.
void InitializeVTablePointers(const CXXRecordDecl *ClassDecl)
const Type * getBaseClass() const
If this is a base class initializer, returns the type of the base class.
llvm::FunctionCallee CreateRuntimeFunction(llvm::FunctionType *Ty, StringRef Name, llvm::AttributeList ExtraAttrs=llvm::AttributeList(), bool Local=false, bool AssumeConvergent=false)
Create or return a runtime function declaration with the specified type and name. ...
A pointer to member type per C++ 8.3.3 - Pointers to members.
bool isCopyAssignmentOperator() const
Determine whether this is a copy-assignment operator, regardless of whether it was declared implicitl...
bool hasObjCLifetime() const
bool isDestroyingOperatorDelete() const
Determine whether this is a destroying operator delete.
ConstEvaluatedExprVisitor - This class visits 'const Expr *'s.
CharUnits getVBaseAlignment(CharUnits DerivedAlign, const CXXRecordDecl *Derived, const CXXRecordDecl *VBase)
Returns the assumed alignment of a virtual base of a class.
LValue MakeAddrLValue(Address Addr, QualType T, AlignmentSource Source=AlignmentSource::Type)
void EmitAggExpr(const Expr *E, AggValueSlot AS)
EmitAggExpr - Emit the computation of the specified expression of aggregate type. ...
JumpDest ReturnBlock
ReturnBlock - Unified return block.
const FunctionDecl * getOperatorDelete() const
A helper class that allows the use of isa/cast/dyncast to detect TagType objects of structs/unions/cl...
CharUnits OffsetFromNearestVBase
CodeGenTypes & getTypes() const
Represents a C++ base or member initializer.
Address getBitFieldAddress() const
IndirectFieldDecl * getIndirectMember() const
llvm::Type * getElementType() const
Return the type of the values stored in this address.
uint64_t getCharWidth() const
Return the size of the character type, in bits.
llvm::PointerType * Int8PtrTy
QualType getThisObjectType() const
Return the type of the object pointed by this.
llvm::Constant * GetNonVirtualBaseClassOffset(const CXXRecordDecl *ClassDecl, CastExpr::path_const_iterator PathBegin, CastExpr::path_const_iterator PathEnd)
Returns the offset from a derived class to a class.
Expr * getArg(unsigned Arg)
Return the specified argument.
void EmitBlock(llvm::BasicBlock *BB, bool IsFinished=false)
EmitBlock - Emit the given block.
ABIArgInfo & getReturnInfo()
Represents a base class of a C++ class.
VPtrsVector getVTablePointers(const CXXRecordDecl *VTableClass)
CanQualType getCanonicalType(QualType T) const
Return the canonical (structural) type corresponding to the specified potentially non-canonical type ...
Address LoadCXXThisAddress()
A template argument list.
llvm::IntegerType * PtrDiffTy
CharUnits toCharUnitsFromBits(int64_t BitSize) const
Convert a size in bits to a size in characters.
Overlap_t mayOverlap() const
int64_t toBits(CharUnits CharSize) const
Convert a size in characters to a size in bits.
MemberExpr - [C99 6.5.2.3] Structure and Union Members.
static void EmitMemberInitializer(CodeGenFunction &CGF, const CXXRecordDecl *ClassDecl, CXXCtorInitializer *MemberInit, const CXXConstructorDecl *Constructor, FunctionArgList &Args)
Represents a C++ struct/union/class.
static Destroyer destroyCXXObject
Qualifiers getQualifiers() const
Retrieve the set of qualifiers applied to this type.
static bool IsConstructorDelegationValid(const CXXConstructorDecl *Ctor)
Checks whether the given constructor is a valid subject for the complete-to-base constructor delegati...
CharUnits getNonVirtualSize() const
getNonVirtualSize - Get the non-virtual size (in chars) of an object, which is the size of the object...
QualType getPointerType(QualType T) const
Return the uniqued reference to the type for a pointer to the specified type.
SourceRange getSourceRange() const LLVM_READONLY
SourceLocation tokens are not useful in isolation - they are low level value objects created/interpre...
__DEVICE__ int min(int __a, int __b)
void EmitVTablePtrCheckForCall(const CXXRecordDecl *RD, llvm::Value *VTable, CFITypeCheckKind TCK, SourceLocation Loc)
EmitVTablePtrCheckForCall - Virtual method MD is being called via VTable.
CallExpr - Represents a function call (C99 6.5.2.2, C++ [expr.call]).
CharUnits computeNonVirtualBaseClassOffset(const CXXRecordDecl *DerivedClass, CastExpr::path_const_iterator Start, CastExpr::path_const_iterator End)
static bool isInitializerOfDynamicClass(const CXXCtorInitializer *BaseInit)
CGCXXABI & getCXXABI() const
std::string getQualifiedNameAsString() const
static Address ApplyNonVirtualAndVirtualOffset(CodeGenFunction &CGF, Address addr, CharUnits nonVirtualOffset, llvm::Value *virtualOffset, const CXXRecordDecl *derivedClass, const CXXRecordDecl *nearestVBase)
Struct with all information about dynamic [sub]class needed to set vptr.
void EmitAggregateCopy(LValue Dest, LValue Src, QualType EltTy, AggValueSlot::Overlap_t MayOverlap, bool isVolatile=false)
EmitAggregateCopy - Emit an aggregate copy.
static RValue get(llvm::Value *V)
ArrayRef< ParmVarDecl * > parameters() const
void EmitDestructorBody(FunctionArgList &Args)
EmitDestructorBody - Emits the body of the current destructor.
void EmitBranchThroughCleanup(JumpDest Dest)
EmitBranchThroughCleanup - Emit a branch from the current insert block through the normal cleanup han...
bool Null(InterpState &S, CodePtr OpPC)
const CXXRecordDecl * VTableClass
unsigned getNumArgs() const
Return the number of arguments to the constructor call.
LValue - This represents an lvalue references.
Information for lazily generating a cleanup.
static bool HasTrivialDestructorBody(ASTContext &Context, const CXXRecordDecl *BaseClassDecl, const CXXRecordDecl *MostDerivedClassDecl)
Notes how many arguments were added to the beginning (Prefix) and ending (Suffix) of an arg list...
const LangOptions & getLangOpts() const
unsigned getTargetAddressSpace(QualType T) const
llvm::CallInst * EmitNounwindRuntimeCall(llvm::FunctionCallee callee, const Twine &name="")
unsigned getNumParams() const
Return the number of parameters this function must have based on its FunctionType.
bool isZeroSize(const ASTContext &Ctx) const
Determine if this field is a subobject of zero size, that is, either a zero-length bit-field or a fie...
const CGRecordLayout & getCGRecordLayout(const RecordDecl *)
getCGRecordLayout - Return record layout info for the given record decl.
Address GetAddressOfBaseClass(Address Value, const CXXRecordDecl *Derived, CastExpr::path_const_iterator PathBegin, CastExpr::path_const_iterator PathEnd, bool NullCheckValue, SourceLocation Loc)
GetAddressOfBaseClass - This function will add the necessary delta to the load of 'this' and returns ...
CallArgList - Type for representing both the value and type of arguments in a call.
const LangOptions & getLangOpts() const
base_class_range vbases()
Represents the canonical version of C arrays with a specified constant size.
Declaration of a template function.
static bool FieldHasTrivialDestructorBody(ASTContext &Context, const FieldDecl *Field)
llvm::Value * EmitVTableTypeCheckedLoad(const CXXRecordDecl *RD, llvm::Value *VTable, uint64_t VTableByteOffset)
Emit a type checked load from the given vtable.
QualType getPointeeType() const
Structure with information about how a bitfield should be accessed.
void Destroyer(CodeGenFunction &CGF, Address addr, QualType ty)
method_range methods() const
QualType getType() const
Retrieves the type of the base class.