35#include "llvm/ADT/STLExtras.h"
36#include "llvm/ADT/ScopeExit.h"
37#include "llvm/ADT/StringExtras.h"
38#include "llvm/IR/DataLayout.h"
39#include "llvm/IR/Intrinsics.h"
40#include "llvm/IR/LLVMContext.h"
41#include "llvm/IR/MDBuilder.h"
42#include "llvm/IR/MatrixBuilder.h"
43#include "llvm/Support/ConvertUTF.h"
44#include "llvm/Support/Endian.h"
45#include "llvm/Support/MathExtras.h"
46#include "llvm/Support/Path.h"
47#include "llvm/Support/xxhash.h"
48#include "llvm/Transforms/Utils/SanitizerStats.h"
55using namespace CodeGen;
61 "ubsan-guard-checks", llvm::cl::Optional,
62 llvm::cl::desc(
"Guard UBSAN checks with `llvm.allow.ubsan.check()`."));
88CodeGenFunction::CreateTempAllocaWithoutCast(llvm::Type *Ty,
CharUnits Align,
90 llvm::Value *ArraySize) {
100 llvm::Value *ArraySize,
104 *AllocaAddr = Alloca;
105 llvm::Value *
V = Alloca.getPointer();
112 llvm::IRBuilderBase::InsertPointGuard IPG(
Builder);
120 Builder.getPtrTy(DestAddrSpace),
true);
131 llvm::Value *ArraySize) {
132 llvm::AllocaInst *Alloca;
134 Alloca =
Builder.CreateAlloca(Ty, ArraySize, Name);
140 Allocas->Add(Alloca);
174 auto *ArrayTy = cast<llvm::ArrayType>(
Result.getElementType());
175 auto *VectorTy = llvm::FixedVectorType::get(ArrayTy->getElementType(),
176 ArrayTy->getNumElements());
207 CGFPOptionsRAII FPOptsRAII(*
this,
E);
225 if (
const auto *CondOp = dyn_cast<AbstractConditionalOperator>(
248 if (!ignoreResult && aggSlot.
isIgnored())
253 llvm_unreachable(
"bad evaluation kind");
295 llvm_unreachable(
"bad evaluation kind");
318 llvm_unreachable(
"bad evaluation kind");
358 bool Precise = isa_and_nonnull<VarDecl>(VD) &&
359 VD->
hasAttr<ObjCPreciseLifetimeAttr>();
380 llvm_unreachable(
"temporary cannot have dynamic storage duration");
382 llvm_unreachable(
"unknown storage duration");
390 auto *ClassDecl = cast<CXXRecordDecl>(RT->getDecl());
391 if (!ClassDecl->hasTrivialDestructor())
392 ReferenceTemporaryDtor = ClassDecl->getDestructor();
395 if (!ReferenceTemporaryDtor)
402 llvm::FunctionCallee CleanupFn;
403 llvm::Constant *CleanupArg;
409 CleanupArg = llvm::Constant::getNullValue(CGF.
Int8PtrTy);
413 CleanupArg = cast<llvm::Constant>(ReferenceTemporary.
emitRawPointer(CGF));
434 llvm_unreachable(
"temporary cannot have dynamic storage duration");
456 auto *GV =
new llvm::GlobalVariable(
458 llvm::GlobalValue::PrivateLinkage,
Init,
".ref.tmp",
nullptr,
459 llvm::GlobalValue::NotThreadLocal,
463 llvm::Constant *
C = GV;
465 C = TCG.performAddrSpaceCast(
467 llvm::PointerType::get(
471 return RawAddress(
C, GV->getValueType(), alignment);
480 llvm_unreachable(
"temporary can't have dynamic storage duration");
482 llvm_unreachable(
"unknown storage duration");
496 "Reference should never be pseudo-strong!");
504 if (
auto *Var = dyn_cast<llvm::GlobalVariable>(
Object.getPointer())) {
514 if (Var->hasInitializer())
523 default: llvm_unreachable(
"expected scalar or aggregate expression");
546 for (
const auto &Ignored : CommaLHSs)
549 if (
const auto *opaque = dyn_cast<OpaqueValueExpr>(
E)) {
550 if (opaque->getType()->isRecordType()) {
551 assert(Adjustments.empty());
559 if (
auto *Var = dyn_cast<llvm::GlobalVariable>(
560 Object.getPointer()->stripPointerCasts())) {
566 if (!Var->hasInitializer()) {
582 if (!ShouldEmitLifetimeMarkers)
592 ConditionalEvaluation *OldConditional =
nullptr;
593 CGBuilderTy::InsertPoint OldIP;
599 OldConditional = OutermostConditional;
600 OutermostConditional =
nullptr;
603 llvm::BasicBlock *
Block = OldConditional->getStartingBlock();
604 Builder.restoreIP(CGBuilderTy::InsertPoint(
605 Block, llvm::BasicBlock::iterator(
Block->back())));
615 if (OldConditional) {
616 OutermostConditional = OldConditional;
633 switch (Adjustment.Kind) {
637 Adjustment.DerivedToBase.BasePath->path_begin(),
638 Adjustment.DerivedToBase.BasePath->path_end(),
646 "materialized temporary field is not a simple lvalue");
687 const llvm::Constant *Elts) {
688 return cast<llvm::ConstantInt>(Elts->getAggregateElement(Idx))
695 Builder.CreateMul(Ptr, Builder.getInt64(0xbf58476d1ce4e5b9u));
697 Builder.CreateXor(A0, Builder.CreateLShr(A0, Builder.getInt64(31)));
698 return Builder.CreateXor(Acc, A1);
725 llvm::Value *ArraySize) {
732 if (Ptr->getType()->getPointerAddressSpace())
740 SanitizerScope SanScope(
this);
744 llvm::BasicBlock *Done =
nullptr;
749 auto PtrToAlloca = dyn_cast<llvm::AllocaInst>(Ptr->stripPointerCasts());
753 bool IsGuaranteedNonNull =
754 SkippedChecks.
has(SanitizerKind::Null) || PtrToAlloca;
756 if ((
SanOpts.
has(SanitizerKind::Null) || AllowNullPointers) &&
757 !IsGuaranteedNonNull) {
766 if (!IsGuaranteedNonNull) {
767 if (AllowNullPointers) {
772 Builder.CreateCondBr(IsNonNull, Rest, Done);
775 Checks.push_back(std::make_pair(IsNonNull, SanitizerKind::SO_Null));
781 !SkippedChecks.
has(SanitizerKind::ObjectSize) &&
784 llvm::Value *
Size = llvm::ConstantInt::get(
IntPtrTy, TySize);
789 llvm::Constant *ConstantSize = dyn_cast<llvm::Constant>(Size);
790 if (!ConstantSize || !ConstantSize->isNullValue()) {
796 llvm::Function *F =
CGM.
getIntrinsic(llvm::Intrinsic::objectsize, Tys);
798 llvm::Value *NullIsUnknown =
Builder.getFalse();
800 llvm::Value *LargeEnough =
Builder.CreateICmpUGE(
801 Builder.CreateCall(F, {Ptr, Min, NullIsUnknown, Dynamic}), Size);
803 std::make_pair(LargeEnough, SanitizerKind::SO_ObjectSize));
807 llvm::MaybeAlign AlignVal;
808 llvm::Value *PtrAsInt =
nullptr;
811 !SkippedChecks.
has(SanitizerKind::Alignment)) {
819 if (AlignVal && *AlignVal > llvm::Align(1) &&
820 (!PtrToAlloca || PtrToAlloca->getAlign() < *AlignVal)) {
822 llvm::Value *Align =
Builder.CreateAnd(
823 PtrAsInt, llvm::ConstantInt::get(
IntPtrTy, AlignVal->value() - 1));
824 llvm::Value *Aligned =
827 Checks.push_back(std::make_pair(Aligned, SanitizerKind::SO_Alignment));
831 if (Checks.size() > 0) {
832 llvm::Constant *StaticData[] = {
834 llvm::ConstantInt::get(
Int8Ty, AlignVal ? llvm::Log2(*AlignVal) : 1),
835 llvm::ConstantInt::get(
Int8Ty, TCK)};
836 EmitCheck(Checks, SanitizerHandler::TypeMismatch, StaticData,
837 PtrAsInt ? PtrAsInt : Ptr);
852 if (!IsGuaranteedNonNull) {
858 Builder.CreateCondBr(IsNonNull, VptrNotNull, Done);
864 llvm::raw_svector_ostream Out(MangledName);
872 llvm::Value *TypeHash =
873 llvm::ConstantInt::get(
Int64Ty, xxh3_64bits(Out.str()));
875 llvm::Type *VPtrTy = llvm::PointerType::get(
IntPtrTy, 0);
887 const int CacheSize = 128;
888 llvm::Type *HashTable = llvm::ArrayType::get(
IntPtrTy, CacheSize);
890 "__ubsan_vptr_type_cache");
891 llvm::Value *Slot =
Builder.CreateAnd(Hash,
894 llvm::Value *Indices[] = {
Builder.getInt32(0), Slot };
903 llvm::Value *EqualHash =
Builder.CreateICmpEQ(CacheVal, Hash);
904 llvm::Constant *StaticData[] = {
908 llvm::ConstantInt::get(
Int8Ty, TCK)
910 llvm::Value *DynamicData[] = { Ptr, Hash };
911 EmitCheck(std::make_pair(EqualHash, SanitizerKind::SO_Vptr),
912 SanitizerHandler::DynamicTypeCacheMiss, StaticData,
926 uint64_t EltSize =
C.getTypeSizeInChars(EltTy).getQuantity();
934 auto *ParamDecl = dyn_cast<ParmVarDecl>(ArrayDeclRef->getDecl());
938 auto *POSAttr = ParamDecl->getAttr<PassObjectSizeAttr>();
943 int POSType = POSAttr->getType();
944 if (POSType != 0 && POSType != 1)
948 auto PassedSizeIt = SizeArguments.find(ParamDecl);
949 if (PassedSizeIt == SizeArguments.end())
953 assert(LocalDeclMap.count(PassedSizeDecl) &&
"Passed size not loadable");
954 Address AddrOfSize = LocalDeclMap.find(PassedSizeDecl)->second;
957 llvm::Value *SizeOfElement =
958 llvm::ConstantInt::get(SizeInBytes->getType(), EltSize);
959 return Builder.CreateUDiv(SizeInBytes, SizeOfElement);
968 StrictFlexArraysLevel) {
971 IndexedType =
Base->getType();
972 return CGF.
Builder.getInt32(VT->getNumElements());
977 if (
const auto *CE = dyn_cast<CastExpr>(
Base)) {
978 if (CE->getCastKind() == CK_ArrayToPointerDecay &&
979 !CE->getSubExpr()->isFlexibleArrayMemberLike(CGF.
getContext(),
980 StrictFlexArraysLevel)) {
981 CodeGenFunction::SanitizerScope SanScope(&CGF);
983 IndexedType = CE->getSubExpr()->getType();
985 if (
const auto *CAT = dyn_cast<ConstantArrayType>(AT))
986 return CGF.
Builder.getInt(CAT->getSize());
988 if (
const auto *VAT = dyn_cast<VariableArrayType>(AT))
994 CodeGenFunction::SanitizerScope SanScope(&CGF);
996 QualType EltTy{
Base->getType()->getPointeeOrArrayElementType(), 0};
998 IndexedType =
Base->getType();
1023class StructAccessBase
1027 bool IsExpectedRecordDecl(
const Expr *
E)
const {
1035 StructAccessBase(
const RecordDecl *ExpectedRD) : ExpectedRD(ExpectedRD) {}
1058 const Expr *VisitStmt(
const Stmt *S) {
return nullptr; }
1074 return IsExpectedRecordDecl(
E) ?
E :
nullptr;
1077 if (IsExpectedRecordDecl(
E) &&
E->isArrow())
1079 const Expr *Res = Visit(
E->getBase());
1080 return !Res && IsExpectedRecordDecl(
E) ?
E : Res;
1083 return IsExpectedRecordDecl(
E) ?
E :
nullptr;
1086 return IsExpectedRecordDecl(
E) ?
E :
nullptr;
1090 if (IsExpectedRecordDecl(
E))
1092 return Visit(
E->getBase());
1095 if (
E->getCastKind() == CK_LValueToRValue)
1096 return IsExpectedRecordDecl(
E) ?
E :
nullptr;
1097 return Visit(
E->getSubExpr());
1100 return Visit(
E->getSubExpr());
1103 return Visit(
E->getSubExpr());
1106 return Visit(
E->getSubExpr());
1118 int64_t FieldNo = -1;
1127 Indices.emplace_back(CGF.
Builder.getInt32(FieldNo));
1136 Indices.emplace_back(CGF.
Builder.getInt32(FieldNo));
1150 const Expr *StructBase = StructAccessBase(RD).Visit(
Base);
1154 llvm::Value *Res =
nullptr;
1160 }
else if (StructBase->
isLValue()) {
1170 if (Indices.empty())
1173 Indices.push_back(
Builder.getInt32(0));
1176 RecIndicesTy(llvm::reverse(Indices)),
"counted_by.gep");
1196 llvm::Value *Index,
QualType IndexType,
1198 assert(
SanOpts.
has(SanitizerKind::ArrayBounds) &&
1199 "should not be called unless adding bounds checks");
1203 llvm::Value *Bound =
1212 QualType IndexedType,
bool Accessed) {
1216 SanitizerScope SanScope(
this);
1219 llvm::Value *IndexVal =
Builder.CreateIntCast(Index,
SizeTy, IndexSigned);
1220 llvm::Value *BoundVal =
Builder.CreateIntCast(Bound,
SizeTy,
false);
1222 llvm::Constant *StaticData[] = {
1227 llvm::Value *Check = Accessed ?
Builder.CreateICmpULT(IndexVal, BoundVal)
1228 :
Builder.CreateICmpULE(IndexVal, BoundVal);
1229 EmitCheck(std::make_pair(Check, SanitizerKind::SO_ArrayBounds),
1230 SanitizerHandler::OutOfBounds, StaticData, Index);
1235 bool isInc,
bool isPre) {
1238 llvm::Value *NextVal;
1239 if (isa<llvm::IntegerType>(InVal.first->getType())) {
1240 uint64_t AmountVal = isInc ? 1 : -1;
1241 NextVal = llvm::ConstantInt::get(InVal.first->getType(), AmountVal,
true);
1244 NextVal =
Builder.CreateAdd(InVal.first, NextVal, isInc ?
"inc" :
"dec");
1247 llvm::APFloat FVal(
getContext().getFloatTypeSemantics(ElemTy), 1);
1253 NextVal =
Builder.CreateFAdd(InVal.first, NextVal, isInc ?
"inc" :
"dec");
1266 return isPre ? IncVal : InVal;
1276 DI->EmitExplicitCastType(
E->
getType());
1293 if (
const CastExpr *CE = dyn_cast<CastExpr>(
E)) {
1294 if (
const auto *ECE = dyn_cast<ExplicitCastExpr>(CE))
1297 switch (CE->getCastKind()) {
1301 case CK_AddressSpaceConversion:
1302 if (
auto PtrTy = CE->getSubExpr()->getType()->getAs<
PointerType>()) {
1303 if (PtrTy->getPointeeType()->isVoidType())
1309 CE->getSubExpr(), &InnerBaseInfo, &InnerTBAAInfo, IsKnownNonNull);
1310 if (BaseInfo) *BaseInfo = InnerBaseInfo;
1311 if (TBAAInfo) *TBAAInfo = InnerTBAAInfo;
1313 if (isa<ExplicitCastExpr>(CE)) {
1317 E->
getType(), &TargetTypeBaseInfo, &TargetTypeTBAAInfo);
1330 if (CGF.
SanOpts.
has(SanitizerKind::CFIUnrelatedCast) &&
1331 CE->getCastKind() == CK_BitCast) {
1339 llvm::Type *ElemTy =
1342 if (CE->getCastKind() == CK_AddressSpaceConversion)
1351 case CK_ArrayToPointerDecay:
1355 case CK_UncheckedDerivedToBase:
1356 case CK_DerivedToBase: {
1363 CE->getSubExpr(), BaseInfo,
nullptr,
1365 CE->getCastKind() == CK_UncheckedDerivedToBase));
1366 auto Derived = CE->getSubExpr()->
getType()->getPointeeCXXRecordDecl();
1368 Addr, Derived, CE->path_begin(), CE->path_end(),
1381 if (UO->getOpcode() == UO_AddrOf) {
1390 if (
auto *
Call = dyn_cast<CallExpr>(
E)) {
1391 switch (
Call->getBuiltinCallee()) {
1394 case Builtin::BIaddressof:
1395 case Builtin::BI__addressof:
1396 case Builtin::BI__builtin_addressof: {
1410 true, BaseInfo, TBAAInfo, IsKnownNonNull);
1429 return Builder.CreateICmpNE(
V, llvm::Constant::getNullValue(
V->getType()));
1440 llvm::Value *
U = llvm::UndefValue::get(EltTy);
1455 llvm_unreachable(
"bad evaluation kind");
1475 while (!isa<CXXThisExpr>(
Base)) {
1477 if (isa<CXXDynamicCastExpr>(
Base))
1480 if (
const auto *CE = dyn_cast<CastExpr>(
Base)) {
1481 Base = CE->getSubExpr();
1482 }
else if (
const auto *PE = dyn_cast<ParenExpr>(
Base)) {
1483 Base = PE->getSubExpr();
1484 }
else if (
const auto *UO = dyn_cast<UnaryOperator>(
Base)) {
1485 if (UO->getOpcode() == UO_Extension)
1486 Base = UO->getSubExpr();
1498 if (
SanOpts.
has(SanitizerKind::ArrayBounds) && isa<ArraySubscriptExpr>(
E))
1504 if (
const auto *ME = dyn_cast<MemberExpr>(
E)) {
1507 SkippedChecks.
set(SanitizerKind::Alignment,
true);
1508 if (IsBaseCXXThis || isa<DeclRefExpr>(ME->getBase()))
1509 SkippedChecks.
set(SanitizerKind::Null,
true);
1537 E->
getExprLoc(), [&] { LV = EmitLValueHelper(E, IsKnownNonNull); });
1547 if (isa<OpaqueValueExpr>(SE))
1549 return cast<CallExpr>(SE)->getCallReturnType(Ctx)->
getPointeeType();
1552LValue CodeGenFunction::EmitLValueHelper(
const Expr *
E,
1558 case Expr::ObjCPropertyRefExprClass:
1559 llvm_unreachable(
"cannot emit a property reference directly");
1561 case Expr::ObjCSelectorExprClass:
1563 case Expr::ObjCIsaExprClass:
1565 case Expr::BinaryOperatorClass:
1567 case Expr::CompoundAssignOperatorClass: {
1570 Ty = AT->getValueType();
1575 case Expr::CallExprClass:
1576 case Expr::CXXMemberCallExprClass:
1577 case Expr::CXXOperatorCallExprClass:
1578 case Expr::UserDefinedLiteralClass:
1580 case Expr::CXXRewrittenBinaryOperatorClass:
1581 return EmitLValue(cast<CXXRewrittenBinaryOperator>(
E)->getSemanticForm(),
1583 case Expr::VAArgExprClass:
1585 case Expr::DeclRefExprClass:
1587 case Expr::ConstantExprClass: {
1593 return EmitLValue(cast<ConstantExpr>(
E)->getSubExpr(), IsKnownNonNull);
1595 case Expr::ParenExprClass:
1596 return EmitLValue(cast<ParenExpr>(
E)->getSubExpr(), IsKnownNonNull);
1597 case Expr::GenericSelectionExprClass:
1598 return EmitLValue(cast<GenericSelectionExpr>(
E)->getResultExpr(),
1600 case Expr::PredefinedExprClass:
1602 case Expr::StringLiteralClass:
1604 case Expr::ObjCEncodeExprClass:
1606 case Expr::PseudoObjectExprClass:
1608 case Expr::InitListExprClass:
1610 case Expr::CXXTemporaryObjectExprClass:
1611 case Expr::CXXConstructExprClass:
1613 case Expr::CXXBindTemporaryExprClass:
1615 case Expr::CXXUuidofExprClass:
1617 case Expr::LambdaExprClass:
1620 case Expr::ExprWithCleanupsClass: {
1621 const auto *cleanups = cast<ExprWithCleanups>(
E);
1622 RunCleanupsScope
Scope(*
this);
1629 Scope.ForceCleanup({&
V});
1639 case Expr::CXXDefaultArgExprClass: {
1640 auto *DAE = cast<CXXDefaultArgExpr>(
E);
1641 CXXDefaultArgExprScope
Scope(*
this, DAE);
1642 return EmitLValue(DAE->getExpr(), IsKnownNonNull);
1644 case Expr::CXXDefaultInitExprClass: {
1645 auto *DIE = cast<CXXDefaultInitExpr>(
E);
1646 CXXDefaultInitExprScope
Scope(*
this, DIE);
1647 return EmitLValue(DIE->getExpr(), IsKnownNonNull);
1649 case Expr::CXXTypeidExprClass:
1652 case Expr::ObjCMessageExprClass:
1654 case Expr::ObjCIvarRefExprClass:
1656 case Expr::StmtExprClass:
1658 case Expr::UnaryOperatorClass:
1660 case Expr::ArraySubscriptExprClass:
1662 case Expr::MatrixSubscriptExprClass:
1664 case Expr::ArraySectionExprClass:
1666 case Expr::ExtVectorElementExprClass:
1668 case Expr::CXXThisExprClass:
1670 case Expr::MemberExprClass:
1672 case Expr::CompoundLiteralExprClass:
1674 case Expr::ConditionalOperatorClass:
1676 case Expr::BinaryConditionalOperatorClass:
1678 case Expr::ChooseExprClass:
1679 return EmitLValue(cast<ChooseExpr>(
E)->getChosenSubExpr(), IsKnownNonNull);
1680 case Expr::OpaqueValueExprClass:
1682 case Expr::SubstNonTypeTemplateParmExprClass:
1683 return EmitLValue(cast<SubstNonTypeTemplateParmExpr>(
E)->getReplacement(),
1685 case Expr::ImplicitCastExprClass:
1686 case Expr::CStyleCastExprClass:
1687 case Expr::CXXFunctionalCastExprClass:
1688 case Expr::CXXStaticCastExprClass:
1689 case Expr::CXXDynamicCastExprClass:
1690 case Expr::CXXReinterpretCastExprClass:
1691 case Expr::CXXConstCastExprClass:
1692 case Expr::CXXAddrspaceCastExprClass:
1693 case Expr::ObjCBridgedCastExprClass:
1696 case Expr::MaterializeTemporaryExprClass:
1699 case Expr::CoawaitExprClass:
1701 case Expr::CoyieldExprClass:
1703 case Expr::PackIndexingExprClass:
1704 return EmitLValue(cast<PackIndexingExpr>(
E)->getSelectedExpr());
1705 case Expr::HLSLOutArgExprClass:
1706 llvm_unreachable(
"cannot emit a HLSL out argument directly");
1713 assert(
type.isCanonical());
1714 assert(!
type->isReferenceType());
1722 if (
const auto *RT = dyn_cast<RecordType>(
type))
1723 if (
const auto *RD = dyn_cast<CXXRecordDecl>(RT->getDecl()))
1724 if (RD->hasMutableFields() || !RD->isTrivial())
1745 if (
const auto *ref = dyn_cast<ReferenceType>(
type)) {
1761CodeGenFunction::ConstantEmission
1767 if (isa<ParmVarDecl>(value)) {
1769 }
else if (
auto *var = dyn_cast<VarDecl>(value)) {
1771 }
else if (isa<EnumConstantDecl>(value)) {
1776 if (CEK ==
CEK_None)
return ConstantEmission();
1779 bool resultIsReference;
1785 resultIsReference =
false;
1786 resultType = refExpr->
getType();
1791 resultIsReference =
true;
1792 resultType = value->
getType();
1796 return ConstantEmission();
1801 return ConstantEmission();
1812 auto *MD = dyn_cast_or_null<CXXMethodDecl>(
CurCodeDecl);
1813 if (
isLambdaMethod(MD) && MD->getOverloadedOperator() == OO_Call) {
1816 if (
const VarDecl *VD = dyn_cast<const VarDecl>(
D)) {
1817 if (!VD->hasAttr<CUDADeviceAttr>()) {
1818 return ConstantEmission();
1827 result.
Val, resultType);
1831 if (isa<VarDecl>(value)) {
1832 if (!
getContext().DeclMustBeEmitted(cast<VarDecl>(value)))
1835 assert(isa<EnumConstantDecl>(value));
1840 if (resultIsReference)
1858CodeGenFunction::ConstantEmission
1862 return ConstantEmission();
1866 const CodeGenFunction::ConstantEmission &Constant,
Expr *
E) {
1867 assert(Constant &&
"not a constant");
1868 if (Constant.isReference())
1872 return Constant.getValue();
1887 return ET->getDecl()->getIntegerType()->isBooleanType();
1896 llvm::APInt &
Min, llvm::APInt &End,
1897 bool StrictEnums,
bool IsBool) {
1899 bool IsRegularCPlusPlusEnum = CGF.
getLangOpts().CPlusPlus && StrictEnums &&
1901 if (!IsBool && !IsRegularCPlusPlusEnum)
1914llvm::MDNode *CodeGenFunction::getRangeForLoadFromType(
QualType Ty) {
1915 llvm::APInt
Min, End;
1921 return MDHelper.createRange(
Min, End);
1926 bool HasBoolCheck =
SanOpts.
has(SanitizerKind::Bool);
1927 bool HasEnumCheck =
SanOpts.
has(SanitizerKind::Enum);
1928 if (!HasBoolCheck && !HasEnumCheck)
1933 bool NeedsBoolCheck = HasBoolCheck && IsBool;
1934 bool NeedsEnumCheck = HasEnumCheck && Ty->
getAs<
EnumType>();
1935 if (!NeedsBoolCheck && !NeedsEnumCheck)
1942 cast<llvm::IntegerType>(
Value->
getType())->getBitWidth() == 1)
1945 if (NeedsEnumCheck &&
1949 llvm::APInt
Min, End;
1954 SanitizerScope SanScope(
this);
1958 Check =
Builder.CreateICmpULE(
Value, llvm::ConstantInt::get(Ctx, End));
1960 llvm::Value *Upper =
1961 Builder.CreateICmpSLE(
Value, llvm::ConstantInt::get(Ctx, End));
1962 llvm::Value *Lower =
1964 Check =
Builder.CreateAnd(Upper, Lower);
1969 NeedsEnumCheck ? SanitizerKind::SO_Enum : SanitizerKind::SO_Bool;
1970 EmitCheck(std::make_pair(Check, Kind), SanitizerHandler::LoadInvalidValue,
1980 bool isNontemporal) {
1981 if (
auto *GV = dyn_cast<llvm::GlobalValue>(Addr.
getBasePointer()))
1982 if (GV->isThreadLocal())
1988 if (ClangVecTy->isExtVectorBoolType()) {
1990 unsigned ValNumElems =
1991 cast<llvm::FixedVectorType>(ValTy)->getNumElements();
1994 const auto *RawIntTy = RawIntV->getType();
1995 assert(RawIntTy->isIntegerTy() &&
"compressed iN storage for bitvectors");
1997 auto *PaddedVecTy = llvm::FixedVectorType::get(
1998 Builder.getInt1Ty(), RawIntTy->getPrimitiveSizeInBits());
1999 llvm::Value *
V =
Builder.CreateBitCast(RawIntV, PaddedVecTy);
2012 if (VTy != NewVecTy) {
2015 unsigned OldNumElements = VTy->getNumElements();
2017 std::iota(Mask.begin(), Mask.end(), 0);
2018 V =
Builder.CreateShuffleVector(
V, Mask,
"extractVec");
2034 if (isNontemporal) {
2035 llvm::MDNode *
Node = llvm::MDNode::get(
2036 Load->getContext(), llvm::ConstantAsMetadata::get(
Builder.getInt32(1)));
2037 Load->setMetadata(llvm::LLVMContext::MD_nontemporal,
Node);
2046 if (llvm::MDNode *RangeInfo = getRangeForLoadFromType(Ty)) {
2047 Load->setMetadata(llvm::LLVMContext::MD_range, RangeInfo);
2048 Load->setMetadata(llvm::LLVMContext::MD_noundef,
2068 unsigned MemNumElems = StoreTy->getPrimitiveSizeInBits();
2085 auto *PaddedVecTy = llvm::FixedVectorType::get(
2086 Builder.getInt1Ty(), RawIntTy->getPrimitiveSizeInBits());
2090 unsigned ValNumElems = cast<llvm::FixedVectorType>(ValTy)->getNumElements();
2106 bool IsVector =
true) {
2107 auto *ArrayTy = dyn_cast<llvm::ArrayType>(Addr.
getElementType());
2108 if (ArrayTy && IsVector) {
2109 auto *VectorTy = llvm::FixedVectorType::get(ArrayTy->getElementType(),
2110 ArrayTy->getNumElements());
2114 auto *VectorTy = dyn_cast<llvm::VectorType>(Addr.
getElementType());
2115 if (VectorTy && !IsVector) {
2116 auto *ArrayTy = llvm::ArrayType::get(
2117 VectorTy->getElementType(),
2118 cast<llvm::FixedVectorType>(VectorTy)->getNumElements());
2132 value->getType()->isVectorTy());
2142 bool isInit,
bool isNontemporal) {
2143 if (
auto *GV = dyn_cast<llvm::GlobalValue>(Addr.
getBasePointer()))
2144 if (GV->isThreadLocal())
2152 if (
auto *VecTy = dyn_cast<llvm::FixedVectorType>(SrcTy)) {
2155 if (!ClangVecTy->isExtVectorBoolType() && VecTy != NewVecTy) {
2157 std::iota(Mask.begin(), Mask.begin() + VecTy->getNumElements(), 0);
2177 if (isNontemporal) {
2178 llvm::MDNode *
Node =
2179 llvm::MDNode::get(
Store->getContext(),
2180 llvm::ConstantAsMetadata::get(
Builder.getInt32(1)));
2181 Store->setMetadata(llvm::LLVMContext::MD_nontemporal,
Node);
2221 llvm_unreachable(
"bad evaluation kind");
2277 llvm::MatrixBuilder MB(
Builder);
2278 MB.CreateIndexAssumption(Idx, MatTy->getNumElementsFlattened());
2280 llvm::LoadInst *
Load =
2285 assert(LV.
isBitField() &&
"Unknown LValue type!");
2303 const unsigned StorageSize =
2306 assert(
static_cast<unsigned>(Offset + Info.
Size) <= StorageSize);
2307 unsigned HighBits = StorageSize - Offset - Info.
Size;
2309 Val =
Builder.CreateShl(Val, HighBits,
"bf.shl");
2310 if (Offset + HighBits)
2311 Val =
Builder.CreateAShr(Val, Offset + HighBits,
"bf.ashr");
2314 Val =
Builder.CreateLShr(Val, Offset,
"bf.lshr");
2315 if (
static_cast<unsigned>(Offset) + Info.
Size < StorageSize)
2317 Val, llvm::APInt::getLowBitsSet(StorageSize, Info.
Size),
"bf.clear");
2333 llvm::Type *DstTy = llvm::FixedVectorType::get(Vec->getType(), 1);
2335 Vec =
Builder.CreateInsertElement(DstTy, Vec, Zero,
"cast.splat");
2345 llvm::Value *Elt = llvm::ConstantInt::get(
SizeTy, InIdx);
2353 for (
unsigned i = 0; i != NumResultElts; ++i)
2356 Vec =
Builder.CreateShuffleVector(Vec, Mask);
2375 return VectorBasePtrPlusIx;
2381 "Bad type for register variable");
2382 llvm::MDNode *RegName = cast<llvm::MDNode>(
2383 cast<llvm::MetadataAsValue>(LV.
getGlobalReg())->getMetadata());
2387 llvm::Type *Ty = OrigTy;
2388 if (OrigTy->isPointerTy())
2390 llvm::Type *Types[] = { Ty };
2392 llvm::Function *F =
CGM.
getIntrinsic(llvm::Intrinsic::read_register, Types);
2394 F, llvm::MetadataAsValue::get(Ty->getContext(), RegName));
2395 if (OrigTy->isPointerTy())
2410 auto *IRStoreTy = dyn_cast<llvm::IntegerType>(Vec->getType());
2412 auto *IRVecTy = llvm::FixedVectorType::get(
2413 Builder.getInt1Ty(), IRStoreTy->getPrimitiveSizeInBits());
2414 Vec =
Builder.CreateBitCast(Vec, IRVecTy);
2421 if (
auto *EltTy = dyn_cast<llvm::FixedVectorType>(SrcVal->getType());
2422 EltTy && EltTy->getNumElements() == 1)
2423 SrcVal =
Builder.CreateBitCast(SrcVal, EltTy->getElementType());
2428 Vec =
Builder.CreateBitCast(Vec, IRStoreTy);
2447 llvm::MatrixBuilder MB(
Builder);
2448 MB.CreateIndexAssumption(Idx, MatTy->getNumElementsFlattened());
2458 assert(Dst.
isBitField() &&
"Unknown LValue type");
2466 llvm_unreachable(
"present but none");
2514 RHS =
Builder.CreatePtrToInt(RHS, ResultType,
"sub.ptr.rhs.cast");
2516 ResultType,
"sub.ptr.lhs.cast");
2517 llvm::Value *BytesBetween =
Builder.CreateSub(LHS, RHS,
"ivar.offset");
2528 assert(Src.
isScalar() &&
"Can't emit an agg store with this method");
2544 llvm::Value *MaskedVal = SrcVal;
2546 const bool UseVolatile =
2549 const unsigned StorageSize =
2554 if (StorageSize != Info.
Size) {
2555 assert(StorageSize > Info.
Size &&
"Invalid bitfield size.");
2562 SrcVal, llvm::APInt::getLowBitsSet(StorageSize, Info.
Size),
2566 SrcVal =
Builder.CreateShl(SrcVal, Offset,
"bf.shl");
2570 Val, ~llvm::APInt::getBitsSet(StorageSize, Offset, Offset + Info.
Size),
2574 SrcVal =
Builder.CreateOr(Val, SrcVal,
"bf.set");
2576 assert(Offset == 0);
2592 llvm::Value *ResultVal = MaskedVal;
2596 assert(Info.
Size <= StorageSize);
2597 unsigned HighBits = StorageSize - Info.
Size;
2599 ResultVal =
Builder.CreateShl(ResultVal, HighBits,
"bf.result.shl");
2600 ResultVal =
Builder.CreateAShr(ResultVal, HighBits,
"bf.result.ashr");
2618 "this should only occur for non-vector l-values");
2631 unsigned NumSrcElts = VTy->getNumElements();
2632 unsigned NumDstElts =
2633 cast<llvm::FixedVectorType>(Vec->getType())->getNumElements();
2634 if (NumDstElts == NumSrcElts) {
2639 for (
unsigned i = 0; i != NumSrcElts; ++i)
2642 Vec =
Builder.CreateShuffleVector(SrcVal, Mask);
2643 }
else if (NumDstElts > NumSrcElts) {
2649 for (
unsigned i = 0; i != NumSrcElts; ++i)
2650 ExtMask.push_back(i);
2651 ExtMask.resize(NumDstElts, -1);
2652 llvm::Value *ExtSrcVal =
Builder.CreateShuffleVector(SrcVal, ExtMask);
2655 for (
unsigned i = 0; i != NumDstElts; ++i)
2665 for (
unsigned i = 0; i != NumSrcElts; ++i)
2667 Vec =
Builder.CreateShuffleVector(Vec, ExtSrcVal, Mask);
2670 llvm_unreachable(
"unexpected shorten vector length");
2676 llvm::Value *Elt = llvm::ConstantInt::get(
SizeTy, InIdx);
2677 Vec =
Builder.CreateInsertElement(Vec, SrcVal, Elt);
2687 "Bad type for register variable");
2688 llvm::MDNode *RegName = cast<llvm::MDNode>(
2689 cast<llvm::MetadataAsValue>(Dst.
getGlobalReg())->getMetadata());
2690 assert(RegName &&
"Register LValue is not metadata");
2694 llvm::Type *Ty = OrigTy;
2695 if (OrigTy->isPointerTy())
2697 llvm::Type *Types[] = { Ty };
2699 llvm::Function *F =
CGM.
getIntrinsic(llvm::Intrinsic::write_register, Types);
2701 if (OrigTy->isPointerTy())
2704 F, {llvm::MetadataAsValue::get(Ty->getContext(), RegName),
Value});
2712 bool IsMemberAccess=
false) {
2716 if (isa<ObjCIvarRefExpr>(
E)) {
2729 auto *Exp = cast<ObjCIvarRefExpr>(
const_cast<Expr *
>(
E));
2735 if (
const auto *Exp = dyn_cast<DeclRefExpr>(
E)) {
2736 if (
const auto *VD = dyn_cast<VarDecl>(Exp->getDecl())) {
2737 if (VD->hasGlobalStorage()) {
2746 if (
const auto *Exp = dyn_cast<UnaryOperator>(
E)) {
2751 if (
const auto *Exp = dyn_cast<ParenExpr>(
E)) {
2765 if (
const auto *Exp = dyn_cast<GenericSelectionExpr>(
E)) {
2770 if (
const auto *Exp = dyn_cast<ImplicitCastExpr>(
E)) {
2775 if (
const auto *Exp = dyn_cast<CStyleCastExpr>(
E)) {
2780 if (
const auto *Exp = dyn_cast<ObjCBridgedCastExpr>(
E)) {
2785 if (
const auto *Exp = dyn_cast<ArraySubscriptExpr>(
E)) {
2798 if (
const auto *Exp = dyn_cast<MemberExpr>(
E)) {
2812 CGF, VD, Addr,
Loc);
2823 std::optional<OMPDeclareTargetDeclAttr::MapTypeTy> Res =
2824 OMPDeclareTargetDeclAttr::isDeclareTargetDeclaration(VD);
2828 if (!Res || ((*Res == OMPDeclareTargetDeclAttr::MT_To ||
2829 *Res == OMPDeclareTargetDeclAttr::MT_Enter) &&
2832 assert(((*Res == OMPDeclareTargetDeclAttr::MT_Link) ||
2833 ((*Res == OMPDeclareTargetDeclAttr::MT_To ||
2834 *Res == OMPDeclareTargetDeclAttr::MT_Enter) &&
2836 "Expected link clause OR to clause with unified memory enabled.");
2846 llvm::LoadInst *
Load =
2851 PointeeBaseInfo, PointeeTBAAInfo);
2860 PointeeBaseInfo, PointeeTBAAInfo);
2870 BaseInfo, TBAAInfo);
2900 V = CGF.
Builder.CreateThreadLocalAddress(
V);
2904 Address Addr(
V, RealVarTy, Alignment);
2908 VD->
hasAttr<OMPThreadPrivateDeclAttr>()) {
2923 if (FD->
hasAttr<WeakRefAttr>()) {
2942 llvm::Value *ThisValue) {
2955 AsmLabelAttr *
Asm = VD->
getAttr<AsmLabelAttr>();
2956 assert(
Asm->getLabel().size() < 64-Name.size() &&
2957 "Register name too big");
2958 Name.append(
Asm->getLabel());
2959 llvm::NamedMDNode *M =
2960 CGM.
getModule().getOrInsertNamedMetadata(Name);
2961 if (M->getNumOperands() == 0) {
2964 llvm::Metadata *Ops[] = {Str};
2971 llvm::MetadataAsValue::get(CGM.
getLLVMContext(), M->getOperand(0));
2985 if (
E->refersToEnclosingVariableOrCapture())
3014 case llvm::GlobalValue::ExternalLinkage:
3015 case llvm::GlobalValue::LinkOnceODRLinkage:
3016 case llvm::GlobalValue::WeakODRLinkage:
3017 case llvm::GlobalValue::InternalLinkage:
3018 case llvm::GlobalValue::PrivateLinkage:
3030 "should not emit an unevaluated operand");
3032 if (
const auto *VD = dyn_cast<VarDecl>(ND)) {
3035 VD->hasAttr<AsmLabelAttr>() && !VD->isLocalVarDecl())
3043 (VD->getType()->isReferenceType() ||
3045 VD->getAnyInitializer(VD);
3047 E->getLocation(), *VD->evaluateValue(), VD->
getType());
3048 assert(Val &&
"failed to emit constant expression");
3051 if (!VD->getType()->isReferenceType()) {
3056 auto *PTy = llvm::PointerType::get(
3057 VarTy,
getTypes().getTargetAddressSpace(VD->getType()));
3074 if (
E->refersToEnclosingVariableOrCapture()) {
3075 VD = VD->getCanonicalDecl();
3079 auto I = LocalDeclMap.find(VD);
3080 if (I != LocalDeclMap.end()) {
3082 if (VD->getType()->isReferenceType())
3121 assert((ND->
isUsed(
false) || !isa<VarDecl>(ND) ||
E->isNonOdrUse() ||
3122 !
E->getLocation().isValid()) &&
3123 "Should not use decl without marking it used!");
3125 if (ND->
hasAttr<WeakRefAttr>()) {
3126 const auto *VD = cast<ValueDecl>(ND);
3131 if (
const auto *VD = dyn_cast<VarDecl>(ND)) {
3133 if (VD->hasLinkage() || VD->isStaticDataMember())
3139 auto iter = LocalDeclMap.find(VD);
3140 if (iter != LocalDeclMap.end()) {
3141 addr = iter->second;
3145 }
else if (VD->isStaticLocal()) {
3153 llvm_unreachable(
"DeclRefExpr for Decl not entered in LocalDeclMap?");
3164 VD->hasAttr<OMPThreadPrivateDeclAttr>()) {
3171 bool isBlockByref = VD->isEscapingByref();
3181 bool isLocalStorage = VD->hasLocalStorage();
3183 bool NonGCable = isLocalStorage &&
3191 bool isImpreciseLifetime =
3192 (isLocalStorage && !VD->hasAttr<ObjCPreciseLifetimeAttr>());
3193 if (isImpreciseLifetime)
3199 if (
const auto *FD = dyn_cast<FunctionDecl>(ND))
3205 if (
const auto *BD = dyn_cast<BindingDecl>(ND)) {
3206 if (
E->refersToEnclosingVariableOrCapture()) {
3215 if (
const auto *GD = dyn_cast<MSGuidDecl>(ND))
3219 if (
const auto *TPO = dyn_cast<TemplateParamObjectDecl>(ND)) {
3223 if (AS !=
T.getAddressSpace()) {
3227 CGM, ATPO.getPointer(), AS,
T.getAddressSpace(), PtrTy);
3228 ATPO =
ConstantAddress(ASC, ATPO.getElementType(), ATPO.getAlignment());
3234 llvm_unreachable(
"Unhandled DeclRefExpr");
3239 if (
E->getOpcode() == UO_Extension)
3243 switch (
E->getOpcode()) {
3244 default: llvm_unreachable(
"Unknown unary operator lvalue!");
3247 assert(!
T.isNull() &&
"CodeGenFunction::EmitUnaryOpLValue: Illegal type");
3269 assert(LV.
isSimple() &&
"real/imag on non-ordinary l-value");
3273 if (
E->getOpcode() == UO_Real &&
3282 (
E->getOpcode() == UO_Real
3293 bool isInc =
E->getOpcode() == UO_PreInc;
3315 auto SL =
E->getFunctionName();
3316 assert(SL !=
nullptr &&
"No StringLiteral name in PredefinedExpr");
3317 StringRef FnName =
CurFn->getName();
3318 if (FnName.starts_with(
"\01"))
3319 FnName = FnName.substr(1);
3320 StringRef NameItems[] = {
3322 std::string GVName = llvm::join(NameItems, NameItems + 2,
".");
3323 if (
auto *BD = dyn_cast_or_null<BlockDecl>(
CurCodeDecl)) {
3324 std::string Name = std::string(SL->getString());
3325 if (!Name.empty()) {
3326 unsigned Discriminator =
3329 Name +=
"_" + Twine(Discriminator + 1).str();
3360 bool IsBitInt =
false;
3372 " non positive amount of bits in __BitInt type");
3374 " too many bits in __BitInt type");
3390 (
intptr_t)
T.getAsOpaquePtr(), StringRef(),
3391 StringRef(), {}, Buffer, {});
3396 char S[6] = {
'\0',
'\0',
'\0',
'\0',
'\0',
'\0'};
3399 llvm::support::endian::write32(S + 1, Bits,
3401 ? llvm::endianness::big
3402 : llvm::endianness::little);
3403 StringRef Str = StringRef(S,
sizeof(S) /
sizeof(
decltype(S[0])));
3407 llvm::Constant *Components[] = {
3411 llvm::Constant *Descriptor = llvm::ConstantStruct::getAnon(Components);
3413 auto *GV =
new llvm::GlobalVariable(
3415 true, llvm::GlobalVariable::PrivateLinkage, Descriptor);
3416 GV->setUnnamedAddr(llvm::GlobalValue::UnnamedAddr::Global);
3428 if (
V->getType() == TargetTy)
3433 if (
V->getType()->isFloatingPointTy()) {
3434 unsigned Bits =
V->getType()->getPrimitiveSizeInBits().getFixedValue();
3435 if (Bits <= TargetTy->getIntegerBitWidth())
3441 if (
V->getType()->isIntegerTy() &&
3442 V->getType()->getIntegerBitWidth() <= TargetTy->getIntegerBitWidth())
3443 return Builder.CreateZExt(
V, TargetTy);
3446 if (!
V->getType()->isPointerTy()) {
3451 return Builder.CreatePtrToInt(
V, TargetTy);
3471 int PathComponentsToStrip =
3473 if (PathComponentsToStrip < 0) {
3474 assert(PathComponentsToStrip !=
INT_MIN);
3475 int PathComponentsToKeep = -PathComponentsToStrip;
3476 auto I = llvm::sys::path::rbegin(FilenameString);
3477 auto E = llvm::sys::path::rend(FilenameString);
3478 while (I !=
E && --PathComponentsToKeep)
3481 FilenameString = FilenameString.substr(I -
E);
3482 }
else if (PathComponentsToStrip > 0) {
3483 auto I = llvm::sys::path::begin(FilenameString);
3484 auto E = llvm::sys::path::end(FilenameString);
3485 while (I !=
E && PathComponentsToStrip--)
3490 FilenameString.substr(I - llvm::sys::path::begin(FilenameString));
3492 FilenameString = llvm::sys::path::filename(FilenameString);
3498 cast<llvm::GlobalVariable>(
3499 FilenameGV.getPointer()->stripPointerCasts()));
3500 Filename = FilenameGV.getPointer();
3511 return llvm::ConstantStruct::getAnon(
Data);
3516enum class CheckRecoverableKind {
3527static CheckRecoverableKind
3529 if (Ordinal == SanitizerKind::SO_Vptr)
3530 return CheckRecoverableKind::AlwaysRecoverable;
3531 else if (Ordinal == SanitizerKind::SO_Return ||
3532 Ordinal == SanitizerKind::SO_Unreachable)
3533 return CheckRecoverableKind::Unrecoverable;
3535 return CheckRecoverableKind::Recoverable;
3539struct SanitizerHandlerInfo {
3540 char const *
const Name;
3546#define SANITIZER_CHECK(Enum, Name, Version) {#Name, Version},
3548#undef SANITIZER_CHECK
3552 llvm::FunctionType *FnType,
3555 CheckRecoverableKind RecoverKind,
bool IsFatal,
3556 llvm::BasicBlock *ContBB,
bool NoMerge) {
3557 assert(IsFatal || RecoverKind != CheckRecoverableKind::Unrecoverable);
3558 std::optional<ApplyDebugLocation> DL;
3559 if (!CGF.
Builder.getCurrentDebugLocation()) {
3563 bool NeedsAbortSuffix =
3564 IsFatal && RecoverKind != CheckRecoverableKind::Unrecoverable;
3567 const StringRef CheckName = CheckInfo.Name;
3568 std::string FnName =
"__ubsan_handle_" + CheckName.str();
3569 if (CheckInfo.Version && !MinimalRuntime)
3570 FnName +=
"_v" + llvm::utostr(CheckInfo.Version);
3572 FnName +=
"_minimal";
3573 if (NeedsAbortSuffix)
3576 !IsFatal || RecoverKind == CheckRecoverableKind::AlwaysRecoverable;
3580 B.addAttribute(llvm::Attribute::NoReturn)
3581 .addAttribute(llvm::Attribute::NoUnwind);
3583 B.addUWTableAttr(llvm::UWTableKind::Default);
3588 llvm::AttributeList::FunctionIndex, B),
3594 HandlerCall->addFnAttr(llvm::Attribute::NoMerge);
3596 HandlerCall->setDoesNotReturn();
3597 CGF.
Builder.CreateUnreachable();
3604 ArrayRef<std::pair<llvm::Value *, SanitizerKind::SanitizerOrdinal>> Checked,
3608 assert(Checked.size() > 0);
3609 assert(CheckHandler >= 0 &&
3613 llvm::Value *FatalCond =
nullptr;
3614 llvm::Value *RecoverableCond =
nullptr;
3615 llvm::Value *TrapCond =
nullptr;
3616 bool NoMerge =
false;
3617 for (
auto &[Check, Ord] : Checked) {
3623 Cond = Cond ?
Builder.CreateAnd(Cond, Check) : Check;
3630 llvm::Value *Allow =
3632 llvm::ConstantInt::get(
CGM.
Int8Ty, CheckHandler));
3634 for (llvm::Value **Cond : {&FatalCond, &RecoverableCond, &TrapCond}) {
3642 if (!FatalCond && !RecoverableCond)
3645 llvm::Value *JointCond;
3646 if (FatalCond && RecoverableCond)
3647 JointCond =
Builder.CreateAnd(FatalCond, RecoverableCond);
3649 JointCond = FatalCond ? FatalCond : RecoverableCond;
3655 for (
int i = 1, n = Checked.size(); i < n; ++i) {
3657 "All recoverable kinds in a single check must be same!");
3664 llvm::Instruction *Branch =
Builder.CreateCondBr(JointCond, Cont, Handlers);
3667 llvm::MDNode *
Node = MDHelper.createLikelyBranchWeights();
3668 Branch->setMetadata(llvm::LLVMContext::MD_prof,
Node);
3677 Args.reserve(DynamicArgs.size() + 1);
3678 ArgTypes.reserve(DynamicArgs.size() + 1);
3681 if (!StaticArgs.empty()) {
3682 llvm::Constant *Info = llvm::ConstantStruct::getAnon(StaticArgs);
3683 auto *InfoPtr =
new llvm::GlobalVariable(
3685 llvm::GlobalVariable::PrivateLinkage, Info,
"",
nullptr,
3686 llvm::GlobalVariable::NotThreadLocal,
3688 InfoPtr->setUnnamedAddr(llvm::GlobalValue::UnnamedAddr::Global);
3690 Args.push_back(InfoPtr);
3691 ArgTypes.push_back(Args.back()->getType());
3694 for (
size_t i = 0, n = DynamicArgs.size(); i != n; ++i) {
3700 llvm::FunctionType *FnType =
3701 llvm::FunctionType::get(
CGM.
VoidTy, ArgTypes,
false);
3703 if (!FatalCond || !RecoverableCond) {
3707 (FatalCond !=
nullptr), Cont, NoMerge);
3711 llvm::BasicBlock *NonFatalHandlerBB =
3714 Builder.CreateCondBr(FatalCond, NonFatalHandlerBB, FatalHandlerBB);
3717 NonFatalHandlerBB, NoMerge);
3728 llvm::ConstantInt *TypeId, llvm::Value *Ptr,
3733 llvm::BranchInst *BI =
Builder.CreateCondBr(Cond, Cont, CheckBB);
3736 llvm::MDNode *
Node = MDHelper.createLikelyBranchWeights();
3737 BI->setMetadata(llvm::LLVMContext::MD_prof,
Node);
3743 llvm::CallInst *CheckCall;
3744 llvm::FunctionCallee SlowPathFn;
3746 llvm::Constant *Info = llvm::ConstantStruct::getAnon(StaticArgs);
3748 new llvm::GlobalVariable(
CGM.
getModule(), Info->getType(),
false,
3749 llvm::GlobalVariable::PrivateLinkage, Info);
3750 InfoPtr->setUnnamedAddr(llvm::GlobalValue::UnnamedAddr::Global);
3754 "__cfi_slowpath_diag",
3757 CheckCall =
Builder.CreateCall(SlowPathFn, {TypeId, Ptr, InfoPtr});
3762 CheckCall =
Builder.CreateCall(SlowPathFn, {TypeId, Ptr});
3766 cast<llvm::GlobalValue>(SlowPathFn.getCallee()->stripPointerCasts()));
3767 CheckCall->setDoesNotThrow();
3777 QualType QInt64Ty =
C.getIntTypeForBitwidth(64,
false);
3784 FnArgs.push_back(&ArgCallsiteTypeId);
3785 FnArgs.push_back(&ArgAddr);
3786 FnArgs.push_back(&ArgCFICheckFailData);
3790 llvm::Function *F = llvm::Function::Create(
3792 llvm::GlobalValue::WeakAnyLinkage,
"__cfi_check", M);
3795 F->setAlignment(llvm::Align(4096));
3798 llvm::LLVMContext &Ctx = M->getContext();
3799 llvm::BasicBlock *BB = llvm::BasicBlock::Create(Ctx,
"entry", F);
3802 llvm::CallInst::Create(M->getFunction(
"__cfi_check_fail"), Args,
"", BB);
3803 llvm::ReturnInst::Create(Ctx,
nullptr, BB);
3814 SanitizerScope SanScope(
this);
3820 Args.push_back(&ArgData);
3821 Args.push_back(&ArgAddr);
3826 llvm::Function *F = llvm::Function::Create(
3828 llvm::GlobalValue::WeakODRLinkage,
"__cfi_check_fail", &
CGM.
getModule());
3832 F->setVisibility(llvm::GlobalValue::HiddenVisibility);
3850 llvm::Value *DataIsNotNullPtr =
3852 EmitTrapCheck(DataIsNotNullPtr, SanitizerHandler::CFICheckFail);
3854 llvm::StructType *SourceLocationTy =
3856 llvm::StructType *CfiCheckFailDataTy =
3865 llvm::Value *AllVtables = llvm::MetadataAsValue::get(
3868 llvm::Value *ValidVtable =
Builder.CreateZExt(
3870 {Addr, AllVtables}),
3873 const std::pair<int, SanitizerKind::SanitizerOrdinal> CheckKinds[] = {
3882 for (
auto CheckKindOrdinalPair : CheckKinds) {
3883 int Kind = CheckKindOrdinalPair.first;
3886 Builder.CreateICmpNE(CheckKind, llvm::ConstantInt::get(
Int8Ty, Kind));
3888 EmitCheck(std::make_pair(Cond, Ordinal), SanitizerHandler::CFICheckFail,
3889 {}, {
Data, Addr, ValidVtable});
3901 if (
SanOpts.
has(SanitizerKind::Unreachable)) {
3902 SanitizerScope SanScope(
this);
3904 SanitizerKind::SO_Unreachable),
3905 SanitizerHandler::BuiltinUnreachable,
3918 if ((
int)TrapBBs.size() <= CheckHandlerID)
3919 TrapBBs.resize(CheckHandlerID + 1);
3921 llvm::BasicBlock *&TrapBB = TrapBBs[CheckHandlerID];
3926 if (TrapBB && !NoMerge) {
3927 auto Call = TrapBB->begin();
3928 assert(isa<llvm::CallInst>(
Call) &&
"Expected call in trap BB");
3930 Call->applyMergedLocation(
Call->getDebugLoc(),
3931 Builder.getCurrentDebugLocation());
3932 Builder.CreateCondBr(Checked, Cont, TrapBB);
3935 Builder.CreateCondBr(Checked, Cont, TrapBB);
3938 llvm::CallInst *TrapCall =
3940 llvm::ConstantInt::get(
CGM.
Int8Ty, CheckHandlerID));
3943 auto A = llvm::Attribute::get(
getLLVMContext(),
"trap-func-name",
3945 TrapCall->addFnAttr(A);
3948 TrapCall->addFnAttr(llvm::Attribute::NoMerge);
3949 TrapCall->setDoesNotReturn();
3950 TrapCall->setDoesNotThrow();
3958 llvm::CallInst *TrapCall =
3962 auto A = llvm::Attribute::get(
getLLVMContext(),
"trap-func-name",
3964 TrapCall->addFnAttr(A);
3968 TrapCall->addFnAttr(llvm::Attribute::NoMerge);
3976 "Array to pointer decay must have array source type!");
3991 "Expected pointer to array");
4011 const auto *CE = dyn_cast<CastExpr>(
E);
4012 if (!CE || CE->getCastKind() != CK_ArrayToPointerDecay)
4024 llvm::Type *elemType,
4030 const llvm::Twine &name =
"arrayidx") {
4042 llvm::Type *elementType,
bool inbounds,
4045 const llvm::Twine &name =
"arrayidx") {
4060 if (
auto constantIdx = dyn_cast<llvm::ConstantInt>(idx)) {
4061 CharUnits offset = constantIdx->getZExtValue() * eltSize;
4080 return D &&
D->
hasAttr<BPFPreserveStaticOffsetAttr>();
4087 if (PointeeType.
isNull())
4100 llvm::Function *Fn =
4120 if (
const auto *ME = dyn_cast<MemberExpr>(
E))
4123 if (
const auto *DRE = dyn_cast<DeclRefExpr>(
E)) {
4124 const auto *VarDef = dyn_cast<VarDecl>(DRE->getDecl());
4128 const auto *PtrT = VarDef->getType()->getAs<
PointerType>();
4134 if (
const auto *RecT = dyn_cast<RecordType>(PointeeT))
4135 return RecT->getDecl()->
hasAttr<BPFPreserveAccessIndexAttr>();
4148 const llvm::Twine &name =
"arrayidx") {
4151 for (
auto *idx : indices.drop_back())
4152 assert(isa<llvm::ConstantInt>(idx) &&
4153 cast<llvm::ConstantInt>(idx)->isZero());
4170 llvm::Value *eltPtr;
4171 auto LastIndex = dyn_cast<llvm::ConstantInt>(indices.back());
4176 signedIndices, loc, eltAlign, name);
4180 unsigned idx = LastIndex->getZExtValue();
4181 llvm::DIType *DbgInfo =
nullptr;
4184 eltPtr = CGF.
Builder.CreatePreserveArrayAccessIndex(
4194 const FieldDecl *Field, int64_t &Offset) {
4197 unsigned FieldNo = 0;
4232 if (FD1OuterRec != FD2OuterRec)
4234 return std::optional<int64_t>();
4236 int64_t FD1Offset = 0;
4238 return std::optional<int64_t>();
4240 int64_t FD2Offset = 0;
4242 return std::optional<int64_t>();
4244 return std::make_optional<int64_t>(FD1Offset - FD2Offset);
4251 llvm::Value *IdxPre =
4253 bool SignedIndices =
false;
4254 auto EmitIdxAfterBase = [&, IdxPre](
bool Promote) -> llvm::Value * {
4256 if (
E->getLHS() !=
E->getIdx()) {
4257 assert(
E->getRHS() ==
E->getIdx() &&
"index was neither LHS nor RHS");
4263 SignedIndices |= IdxSigned;
4269 if (Promote && Idx->getType() !=
IntPtrTy)
4279 !isa<ExtVectorElementExpr>(
E->getBase())) {
4282 auto *Idx = EmitIdxAfterBase(
false);
4283 assert(LHS.
isSimple() &&
"Can only subscript lvalue vectors here!");
4291 if (isa<ExtVectorElementExpr>(
E->getBase())) {
4293 auto *Idx = EmitIdxAfterBase(
true);
4312 auto *Idx = EmitIdxAfterBase(
true);
4322 Idx =
Builder.CreateMul(Idx, numElements);
4324 Idx =
Builder.CreateNSWMul(Idx, numElements);
4336 auto *Idx = EmitIdxAfterBase(
true);
4339 llvm::Value *InterfaceSizeVal =
4340 llvm::ConstantInt::get(Idx->getType(), InterfaceSize.
getQuantity());
4342 llvm::Value *ScaledIdx =
Builder.CreateMul(Idx, InterfaceSizeVal);
4353 llvm::Value *EltPtr =
4355 ScaledIdx,
false, SignedIndices,
E->
getExprLoc());
4356 Addr =
Address(EltPtr, OrigBaseElemTy, EltAlign);
4362 assert(Array->getType()->isArrayType() &&
4363 "Array to pointer decay must have array source type!");
4367 if (
const auto *ASE = dyn_cast<ArraySubscriptExpr>(Array))
4371 auto *Idx = EmitIdxAfterBase(
true);
4373 if (
SanOpts.
has(SanitizerKind::ArrayBounds)) {
4384 if (
const auto *ME = dyn_cast<MemberExpr>(Array);
4390 if (std::optional<int64_t> Diff =
4399 llvm::Type *CountTy =
ConvertType(CountFD->getType());
4404 ".counted_by.load");
4408 Array->getType(), Accessed);
4417 *
this, ArrayLV.
getAddress(), {CGM.getSize(CharUnits::Zero()), Idx},
4425 auto *Idx = EmitIdxAfterBase(
true);
4453 !
E->isIncomplete() &&
4454 "incomplete matrix subscript expressions should be rejected during Sema");
4461 llvm::Value *NumRows =
Builder.getIntN(
4462 RowIdx->getType()->getScalarSizeInBits(),
4464 llvm::Value *FinalIdx =
4475 bool IsLowerBound) {
4477 if (
auto *ASE = dyn_cast<ArraySectionExpr>(
Base->IgnoreParenImpCasts())) {
4492 "Expected pointer to array");
4511 bool IsLowerBound) {
4513 assert(!
E->isOpenACCArraySection() &&
4514 "OpenACC Array section codegen not implemented");
4518 if (
auto *AT =
getContext().getAsArrayType(BaseTy))
4519 ResultExprTy = AT->getElementType();
4522 llvm::Value *Idx =
nullptr;
4523 if (IsLowerBound ||
E->getColonLocFirst().isInvalid()) {
4527 if (
auto *LowerBound =
E->getLowerBound()) {
4530 LowerBound->getType()->hasSignedIntegerRepresentation());
4532 Idx = llvm::ConstantInt::getNullValue(
IntPtrTy);
4538 auto *Length =
E->getLength();
4539 llvm::APSInt ConstLength;
4542 if (std::optional<llvm::APSInt> CL = Length->getIntegerConstantExpr(
C)) {
4546 auto *LowerBound =
E->getLowerBound();
4549 if (std::optional<llvm::APSInt> LB =
4550 LowerBound->getIntegerConstantExpr(
C)) {
4552 LowerBound =
nullptr;
4557 else if (!LowerBound)
4560 if (Length || LowerBound) {
4561 auto *LowerBoundVal =
4565 LowerBound->getType()->hasSignedIntegerRepresentation())
4566 : llvm::ConstantInt::get(
IntPtrTy, ConstLowerBound);
4571 Length->getType()->hasSignedIntegerRepresentation())
4572 : llvm::ConstantInt::get(
IntPtrTy, ConstLength);
4573 Idx =
Builder.CreateAdd(LowerBoundVal, LengthVal,
"lb_add_len",
4576 if (Length && LowerBound) {
4578 Idx, llvm::ConstantInt::get(
IntPtrTy, 1),
"idx_sub_1",
4582 Idx = llvm::ConstantInt::get(
IntPtrTy, ConstLength + ConstLowerBound);
4588 if (
auto *VAT =
C.getAsVariableArrayType(ArrayTy)) {
4589 Length = VAT->getSizeExpr();
4590 if (std::optional<llvm::APSInt> L = Length->getIntegerConstantExpr(
C)) {
4595 auto *CAT =
C.getAsConstantArrayType(ArrayTy);
4596 assert(CAT &&
"unexpected type for array initializer");
4597 ConstLength = CAT->getSize();
4600 auto *LengthVal =
Builder.CreateIntCast(
4602 Length->getType()->hasSignedIntegerRepresentation());
4604 LengthVal, llvm::ConstantInt::get(
IntPtrTy, 1),
"len_sub_1",
4609 Idx = llvm::ConstantInt::get(
IntPtrTy, ConstLength);
4618 if (
auto *VLA =
getContext().getAsVariableArrayType(ResultExprTy)) {
4624 BaseTy, VLA->getElementType(), IsLowerBound);
4633 Idx =
Builder.CreateMul(Idx, NumElements);
4635 Idx =
Builder.CreateNSWMul(Idx, NumElements);
4644 assert(Array->getType()->isArrayType() &&
4645 "Array to pointer decay must have array source type!");
4649 if (
const auto *ASE = dyn_cast<ArraySubscriptExpr>(Array))
4656 *
this, ArrayLV.
getAddress(), {CGM.getSize(CharUnits::Zero()), Idx},
4657 ResultExprTy, !
getLangOpts().isSignedOverflowDefined(),
4664 ResultExprTy, IsLowerBound);
4687 Base.getQuals().removeObjCGCAttr();
4696 "Result must be a vector");
4711 E->getEncodedElementAccess(Indices);
4713 if (
Base.isSimple()) {
4714 llvm::Constant *CV =
4719 assert(
Base.isExtVectorElt() &&
"Can only subscript lvalue vec elts here!");
4721 llvm::Constant *BaseElts =
Base.getExtVectorElts();
4724 for (
unsigned i = 0, e = Indices.size(); i != e; ++i)
4725 CElts.push_back(BaseElts->getAggregateElement(Indices[i]));
4726 llvm::Constant *CV = llvm::ConstantVector::get(CElts);
4737 Expr *BaseExpr =
E->getBase();
4748 SkippedChecks.
set(SanitizerKind::Alignment,
true);
4749 if (IsBaseCXXThis || isa<DeclRefExpr>(BaseExpr))
4750 SkippedChecks.
set(SanitizerKind::Null,
true);
4758 if (
auto *Field = dyn_cast<FieldDecl>(ND)) {
4773 if (
const auto *FD = dyn_cast<FunctionDecl>(ND))
4776 llvm_unreachable(
"Unhandled member declaration!");
4783 llvm::Value *ThisValue) {
4784 bool HasExplicitObjectParameter =
false;
4785 const auto *MD = dyn_cast_if_present<CXXMethodDecl>(
CurCodeDecl);
4787 HasExplicitObjectParameter = MD->isExplicitObjectMemberFunction();
4788 assert(MD->getParent()->isLambda());
4789 assert(MD->getParent() ==
Field->getParent());
4792 if (HasExplicitObjectParameter) {
4794 auto It = LocalDeclMap.find(
D);
4795 assert(It != LocalDeclMap.end() &&
"explicit parameter not loaded?");
4796 Address AddrOfExplicitObject = It->getSecond();
4797 if (
D->getType()->isReferenceType())
4802 D->getType().getNonReferenceType());
4805 auto *ThisTy =
D->getType().getNonReferenceType()->getAsCXXRecordDecl();
4806 auto *LambdaTy = cast<CXXRecordDecl>(
Field->getParent());
4807 if (ThisTy != LambdaTy) {
4810 LambdaLV.
getAddress(), ThisTy, BasePathArray.begin(),
4828 unsigned FieldIndex) {
4829 unsigned I = 0, Skipped = 0;
4832 if (I == FieldIndex)
4834 if (F->isUnnamedBitField())
4839 return FieldIndex - Skipped;
4848 if (Offset.isZero())
4889 if (RD->isDynamicClass())
4892 for (
const auto &
Base : RD->bases())
4939 llvm::Type *FieldIntTy = llvm::Type::getIntNTy(
getLLVMContext(), SS);
4975 assert(!FieldTBAAInfo.
Offset &&
4976 "Nonzero offset for an access with no base type!");
4989 FieldTBAAInfo.
Size =
4996 if (
auto *ClassDef = dyn_cast<CXXRecordDecl>(rec)) {
4998 ClassDef->isDynamicClass()) {
5059 if (field->
hasAttr<AnnotateAttr>())
5084 V =
V.withElementType(llvmType);
5097 if (
E->isFileScope()) {
5106 const Expr *InitExpr =
E->getInitializer();
5129 assert(
E->isTransparent() &&
"non-transparent glvalue init list");
5137 const Expr *Operand) {
5138 if (
auto *ThrowExpr = dyn_cast<CXXThrowExpr>(Operand->IgnoreParens())) {
5140 return std::nullopt;
5149std::optional<LValue> HandleConditionalOperatorLValueSimpleCase(
5151 const Expr *condExpr =
E->getCond();
5154 const Expr *Live =
E->getTrueExpr(), *Dead =
E->getFalseExpr();
5156 std::swap(Live, Dead);
5165 if (
auto *ThrowExpr = dyn_cast<CXXThrowExpr>(Live->
IgnoreParens())) {
5167 llvm::Type *ElemTy = CGF.
ConvertType(Dead->getType());
5176 return std::nullopt;
5178struct ConditionalInfo {
5179 llvm::BasicBlock *lhsBlock, *rhsBlock;
5180 std::optional<LValue> LHS, RHS;
5185template<
typename FuncTy>
5188 const FuncTy &BranchGenFunc) {
5194 CodeGenFunction::ConditionalEvaluation eval(CGF);
5202 Info.LHS = BranchGenFunc(CGF,
E->getTrueExpr());
5204 Info.lhsBlock = CGF.
Builder.GetInsertBlock();
5207 CGF.
Builder.CreateBr(endBlock);
5212 Info.RHS = BranchGenFunc(CGF,
E->getFalseExpr());
5214 Info.rhsBlock = CGF.
Builder.GetInsertBlock();
5226 "Unexpected conditional operator!");
5230 OpaqueValueMapping binding(*
this,
E);
5231 if (HandleConditionalOperatorLValueSimpleCase(*
this,
E))
5241 if (!
expr->isGLValue()) {
5244 "Unexpected conditional operator!");
5248 OpaqueValueMapping binding(*
this,
expr);
5249 if (std::optional<LValue> Res =
5250 HandleConditionalOperatorLValueSimpleCase(*
this,
expr))
5253 ConditionalInfo Info = EmitConditionalBlocks(
5258 if ((Info.LHS && !Info.LHS->isSimple()) ||
5259 (Info.RHS && !Info.RHS->isSimple()))
5262 if (Info.LHS && Info.RHS) {
5263 Address lhsAddr = Info.LHS->getAddress();
5264 Address rhsAddr = Info.RHS->getAddress();
5266 lhsAddr, rhsAddr, Info.lhsBlock, Info.rhsBlock,
5269 std::max(Info.LHS->getBaseInfo().getAlignmentSource(),
5270 Info.RHS->getBaseInfo().getAlignmentSource());
5272 Info.LHS->getTBAAInfo(), Info.RHS->getTBAAInfo());
5276 assert((Info.LHS || Info.RHS) &&
5277 "both operands of glvalue conditional are throw-expressions?");
5278 return Info.LHS ? *Info.LHS : *Info.RHS;
5290 switch (
E->getCastKind()) {
5293 case CK_LValueToRValueBitCast:
5294 case CK_ArrayToPointerDecay:
5295 case CK_FunctionToPointerDecay:
5296 case CK_NullToMemberPointer:
5297 case CK_NullToPointer:
5298 case CK_IntegralToPointer:
5299 case CK_PointerToIntegral:
5300 case CK_PointerToBoolean:
5301 case CK_IntegralCast:
5302 case CK_BooleanToSignedIntegral:
5303 case CK_IntegralToBoolean:
5304 case CK_IntegralToFloating:
5305 case CK_FloatingToIntegral:
5306 case CK_FloatingToBoolean:
5307 case CK_FloatingCast:
5308 case CK_FloatingRealToComplex:
5309 case CK_FloatingComplexToReal:
5310 case CK_FloatingComplexToBoolean:
5311 case CK_FloatingComplexCast:
5312 case CK_FloatingComplexToIntegralComplex:
5313 case CK_IntegralRealToComplex:
5314 case CK_IntegralComplexToReal:
5315 case CK_IntegralComplexToBoolean:
5316 case CK_IntegralComplexCast:
5317 case CK_IntegralComplexToFloatingComplex:
5318 case CK_DerivedToBaseMemberPointer:
5319 case CK_BaseToDerivedMemberPointer:
5320 case CK_MemberPointerToBoolean:
5321 case CK_ReinterpretMemberPointer:
5322 case CK_AnyPointerToBlockPointerCast:
5323 case CK_ARCProduceObject:
5324 case CK_ARCConsumeObject:
5325 case CK_ARCReclaimReturnedObject:
5326 case CK_ARCExtendBlockObject:
5327 case CK_CopyAndAutoreleaseBlockObject:
5328 case CK_IntToOCLSampler:
5329 case CK_FloatingToFixedPoint:
5330 case CK_FixedPointToFloating:
5331 case CK_FixedPointCast:
5332 case CK_FixedPointToBoolean:
5333 case CK_FixedPointToIntegral:
5334 case CK_IntegralToFixedPoint:
5336 case CK_HLSLVectorTruncation:
5337 case CK_HLSLArrayRValue:
5341 llvm_unreachable(
"dependent cast kind in IR gen!");
5343 case CK_BuiltinFnToFnPtr:
5344 llvm_unreachable(
"builtin functions are handled elsewhere");
5347 case CK_NonAtomicToAtomic:
5348 case CK_AtomicToNonAtomic:
5354 const auto *DCE = cast<CXXDynamicCastExpr>(
E);
5358 case CK_ConstructorConversion:
5359 case CK_UserDefinedConversion:
5360 case CK_CPointerToObjCPointerCast:
5361 case CK_BlockPointerToObjCPointerCast:
5362 case CK_LValueToRValue:
5371 if (
E->changesVolatileQualification())
5377 if (
V.getElementType() !=
T)
5384 case CK_UncheckedDerivedToBase:
5385 case CK_DerivedToBase: {
5386 const auto *DerivedClassTy =
5388 auto *DerivedClassDecl = cast<CXXRecordDecl>(DerivedClassTy->getDecl());
5395 This, DerivedClassDecl,
E->path_begin(),
E->path_end(),
5406 case CK_BaseToDerived: {
5408 auto *DerivedClassDecl = cast<CXXRecordDecl>(DerivedClassTy->getDecl());
5414 LV.
getAddress(), DerivedClassDecl,
E->path_begin(),
E->path_end(),
5423 if (
SanOpts.
has(SanitizerKind::CFIDerivedCast))
5431 case CK_LValueBitCast: {
5433 const auto *CE = cast<ExplicitCastExpr>(
E);
5440 if (
SanOpts.
has(SanitizerKind::CFIUnrelatedCast))
5448 case CK_AddressSpaceConversion: {
5459 case CK_ObjCObjectLValueCast: {
5465 case CK_ZeroToOCLOpaqueType:
5466 llvm_unreachable(
"NULL to OpenCL opaque type lvalue cast is not valid");
5468 case CK_VectorSplat: {
5476 llvm_unreachable(
"Unhandled lvalue cast kind?");
5484std::pair<LValue, LValue>
5499 return std::make_pair(BaseLV, TempLV);
5515 Args.
addWriteback(BaseLV, TmpAddr,
nullptr,
E->getWritebackCast(),
5525 llvm::DenseMap<const OpaqueValueExpr*,LValue>::iterator
5526 it = OpaqueLValues.find(e);
5528 if (it != OpaqueLValues.end())
5531 assert(e->
isUnique() &&
"LValue for a nonunique OVE hasn't been emitted");
5539 llvm::DenseMap<const OpaqueValueExpr*,RValue>::iterator
5540 it = OpaqueRValues.find(e);
5542 if (it != OpaqueRValues.end())
5545 assert(e->
isUnique() &&
"RValue for a nonunique OVE hasn't been emitted");
5570 llvm_unreachable(
"bad evaluation kind");
5579 llvm::CallBase **CallOrInvoke) {
5580 llvm::CallBase *CallOrInvokeStorage;
5581 if (!CallOrInvoke) {
5582 CallOrInvoke = &CallOrInvokeStorage;
5585 auto AddCoroElideSafeOnExit = llvm::make_scope_exit([&] {
5586 if (
E->isCoroElideSafe()) {
5587 auto *I = *CallOrInvoke;
5589 I->addFnAttr(llvm::Attribute::CoroElideSafe);
5597 if (
const auto *CE = dyn_cast<CXXMemberCallExpr>(
E))
5600 if (
const auto *CE = dyn_cast<CUDAKernelCallExpr>(
E))
5605 if (
const auto *CE = dyn_cast<CXXOperatorCallExpr>(
E))
5606 if (
const auto *MD =
5607 dyn_cast_if_present<CXXMethodDecl>(CE->getCalleeDecl());
5608 MD && MD->isImplicitObjectMemberFunction())
5623 nullptr, CallOrInvoke);
5629 llvm::CallBase **CallOrInvoke) {
5632 nullptr, CallOrInvoke);
5640 if (!PD->isInlineBuiltinDeclaration())
5649 std::string NoBuiltinFD = (
"no-builtin-" + FD->
getName()).str();
5650 std::string NoBuiltins =
"no-builtins";
5653 std::string FDInlineName = (Ident +
".inline").str();
5655 bool IsPredefinedLibFunction =
5657 bool HasAttributeNoBuiltin =
5658 CGF.
CurFn->getAttributes().hasFnAttr(NoBuiltinFD) ||
5659 CGF.
CurFn->getAttributes().hasFnAttr(NoBuiltins);
5663 if (CGF.
CurFn->getName() != FDInlineName &&
5666 llvm::Function *Fn = llvm::cast<llvm::Function>(CalleePtr);
5667 llvm::Module *M = Fn->getParent();
5668 llvm::Function *Clone = M->getFunction(FDInlineName);
5670 Clone = llvm::Function::Create(Fn->getFunctionType(),
5671 llvm::GlobalValue::InternalLinkage,
5672 Fn->getAddressSpace(), FDInlineName, M);
5673 Clone->addFnAttr(llvm::Attribute::AlwaysInline);
5684 else if (!IsPredefinedLibFunction || !HasAttributeNoBuiltin)
5690 FD->
hasAttr<CUDAGlobalAttr>())
5692 cast<llvm::GlobalValue>(CalleePtr->stripPointerCasts()));
5701 if (
auto ICE = dyn_cast<ImplicitCastExpr>(
E)) {
5702 if (ICE->getCastKind() == CK_FunctionToPointerDecay ||
5703 ICE->getCastKind() == CK_BuiltinFnToFnPtr) {
5708 }
else if (
auto DRE = dyn_cast<DeclRefExpr>(
E)) {
5709 if (
auto FD = dyn_cast<FunctionDecl>(DRE->getDecl())) {
5712 }
else if (
auto ME = dyn_cast<MemberExpr>(
E)) {
5713 if (
auto FD = dyn_cast<FunctionDecl>(ME->
getMemberDecl())) {
5719 }
else if (
auto NTTP = dyn_cast<SubstNonTypeTemplateParmExpr>(
E)) {
5723 }
else if (
auto PDE = dyn_cast<CXXPseudoDestructorExpr>(
E)) {
5728 llvm::Value *calleePtr;
5740 if (
const auto *VD =
5746 CGCallee callee(calleeInfo, calleePtr, pointerAuth);
5752 if (
E->getOpcode() == BO_Comma) {
5758 if (
E->getOpcode() == BO_PtrMemD ||
5759 E->getOpcode() == BO_PtrMemI)
5762 assert(
E->getOpcode() == BO_Assign &&
"unexpected binary l-value");
5804 llvm::Value *
Result =
nullptr;
5807 if (
SanOpts.
has(SanitizerKind::ImplicitBitfieldConversion))
5839 llvm_unreachable(
"bad evaluation kind");
5855 llvm::CallBase **CallOrInvoke) {
5862 assert(
E->getCallReturnType(
getContext())->isReferenceType() &&
5863 "Can't have a scalar return unless the return type is a "
5876 &&
"binding l-value to type which needs a temporary");
5913 assert(
E->getMethodDecl()->getReturnType()->isReferenceType() &&
5914 "Can't have a scalar return unless the return type is a "
5936 return Builder.CreateZExtOrTrunc(OffsetValue,
5941 llvm::Value *BaseValue,
5943 unsigned CVRQualifiers) {
5945 Ivar, CVRQualifiers);
5950 llvm::Value *BaseValue =
nullptr;
5951 const Expr *BaseExpr =
E->getBase();
5961 ObjectTy = BaseExpr->
getType();
5983 llvm::CallBase **CallOrInvoke,
5988 "Call must have function pointer type!");
5990 const Decl *TargetDecl =
5993 assert((!isa_and_present<FunctionDecl>(TargetDecl) ||
5994 !cast<FunctionDecl>(TargetDecl)->isImmediateFunction()) &&
5995 "trying to emit a call to an immediate function");
5999 auto PointeeType = cast<PointerType>(CalleeType)->getPointeeType();
6004 (!TargetDecl || !isa<FunctionDecl>(TargetDecl)) &&
6005 !isa<FunctionNoProtoType>(PointeeType)) {
6006 if (llvm::Constant *PrefixSig =
6008 SanitizerScope SanScope(
this);
6011 llvm::Type *PrefixSigType = PrefixSig->getType();
6012 llvm::StructType *PrefixStructTy = llvm::StructType::get(
6015 llvm::Value *CalleePtr =
Callee.getFunctionPointer();
6019 Address(CalleePtr, CalleePtr->getType(),
6022 Callee.getPointerAuthInfo(),
nullptr);
6035 llvm::Value *AlignedCalleePtr;
6037 llvm::Value *CalleeAddress =
6039 llvm::Value *Mask = llvm::ConstantInt::get(
IntPtrTy, ~1);
6040 llvm::Value *AlignedCalleeAddress =
6041 Builder.CreateAnd(CalleeAddress, Mask);
6043 Builder.CreateIntToPtr(AlignedCalleeAddress, CalleePtr->getType());
6045 AlignedCalleePtr = CalleePtr;
6048 llvm::Value *CalleePrefixStruct = AlignedCalleePtr;
6049 llvm::Value *CalleeSigPtr =
6051 llvm::Value *CalleeSig =
6053 llvm::Value *CalleeSigMatch =
Builder.CreateICmpEQ(CalleeSig, PrefixSig);
6057 Builder.CreateCondBr(CalleeSigMatch, TypeCheck, Cont);
6064 llvm::Value *CalleeTypeHashMatch =
6065 Builder.CreateICmpEQ(CalleeTypeHash, TypeHash);
6068 EmitCheck(std::make_pair(CalleeTypeHashMatch, SanitizerKind::SO_Function),
6069 SanitizerHandler::FunctionTypeMismatch, StaticData,
6077 const auto *FnType = cast<FunctionType>(PointeeType);
6082 (!TargetDecl || !isa<FunctionDecl>(TargetDecl))) {
6083 SanitizerScope SanScope(
this);
6092 llvm::Value *TypeId = llvm::MetadataAsValue::get(
getLLVMContext(), MD);
6094 llvm::Value *CalleePtr =
Callee.getFunctionPointer();
6095 llvm::Value *TypeTest =
Builder.CreateCall(
6099 llvm::Constant *StaticData[] = {
6106 CalleePtr, StaticData);
6108 EmitCheck(std::make_pair(TypeTest, SanitizerKind::SO_CFIICall),
6109 SanitizerHandler::CFICheckFail, StaticData,
6110 {CalleePtr, llvm::UndefValue::get(
IntPtrTy)});
6125 bool StaticOperator =
false;
6126 if (
auto *OCE = dyn_cast<CXXOperatorCallExpr>(
E)) {
6127 if (OCE->isAssignmentOp())
6130 switch (OCE->getOperator()) {
6132 case OO_GreaterGreater:
6144 if (
const auto *MD =
6145 dyn_cast_if_present<CXXMethodDecl>(OCE->getCalleeDecl());
6146 MD && MD->isStatic())
6147 StaticOperator =
true;
6151 if (StaticOperator) {
6157 EmitCallArgs(Args, dyn_cast<FunctionProtoType>(FnType), Arguments,
6158 E->getDirectCallee(), 0, Order);
6161 Args, FnType, Chain);
6164 *ResolvedFnInfo = &FnInfo;
6170 isa<CUDAKernelCallExpr>(
E) &&
6171 (!TargetDecl || !isa<FunctionDecl>(TargetDecl))) {
6172 llvm::Value *Handle =
Callee.getFunctionPointer();
6177 llvm::CallBase *LocalCallOrInvoke =
nullptr;
6184 if (
auto *CalleeDecl = dyn_cast_or_null<FunctionDecl>(TargetDecl)) {
6187 DI->EmitFuncDeclForCallSite(LocalCallOrInvoke,
6188 DI->getFunctionType(CalleeDecl, ResTy, Args),
6193 *CallOrInvoke = LocalCallOrInvoke;
6201 if (
E->getOpcode() == BO_PtrMemI) {
6216 return MakeAddrLValue(MemberAddr, MPT->getPointeeType(), BaseInfo, TBAAInfo);
6233 llvm_unreachable(
"bad evaluation kind");
6237 assert(Val->getType()->isFPOrFPVectorTy());
6238 if (Accuracy == 0.0 || !isa<llvm::Instruction>(Val))
6242 llvm::MDNode *
Node = MDHelper.createFPMath(Accuracy);
6244 cast<llvm::Instruction>(Val)->setMetadata(llvm::LLVMContext::MD_fpmath,
Node);
6248 llvm::Type *EltTy = Val->getType()->getScalarType();
6249 if (!EltTy->isFloatTy())
6269 llvm::Type *EltTy = Val->getType()->getScalarType();
6270 if (!EltTy->isFloatTy())
6290 struct LValueOrRValue {
6303 const Expr *resultExpr =
E->getResultExpr();
6304 LValueOrRValue result;
6307 i =
E->semantics_begin(), e =
E->semantics_end(); i != e; ++i) {
6308 const Expr *semantic = *i;
6312 if (
const auto *ov = dyn_cast<OpaqueValueExpr>(semantic)) {
6314 if (ov->isUnique()) {
6315 assert(ov != resultExpr &&
6316 "A unique OVE cannot be used as the result expression");
6322 typedef CodeGenFunction::OpaqueValueMappingData OVMA;
6324 if (ov == resultExpr && ov->
isPRValue() && !forLValue &&
6329 opaqueData = OVMA::bind(CGF, ov, LV);
6334 opaqueData = OVMA::bind(CGF, ov, ov->getSourceExpr());
6337 if (ov == resultExpr) {
6345 opaques.push_back(opaqueData);
6349 }
else if (semantic == resultExpr) {
6362 for (
unsigned i = 0, e = opaques.size(); i != e; ++i)
6363 opaques[i].unbind(CGF);
Defines the clang::ASTContext interface.
This file provides some common utility functions for processing Lambda related AST Constructs.
Defines enum values for all the target-independent builtin functions.
CodeGenFunction::ComplexPairTy ComplexPairTy
static void setObjCGCLValueClass(const ASTContext &Ctx, const Expr *E, LValue &LV, bool IsMemberAccess=false)
static LValue EmitGlobalNamedRegister(const VarDecl *VD, CodeGenModule &CGM)
Named Registers are named metadata pointing to the register name which will be read from/written to a...
static llvm::Value * emitHashMix(CGBuilderTy &Builder, llvm::Value *Acc, llvm::Value *Ptr)
static const Expr * isSimpleArrayDecayOperand(const Expr *E)
isSimpleArrayDecayOperand - If the specified expr is a simple decay from an array to pointer,...
static bool hasBooleanRepresentation(QualType Ty)
static bool getFieldOffsetInBits(CodeGenFunction &CGF, const RecordDecl *RD, const FieldDecl *Field, int64_t &Offset)
The offset of a field from the beginning of the record.
static bool hasBPFPreserveStaticOffset(const RecordDecl *D)
static Address emitAddrOfFieldStorage(CodeGenFunction &CGF, Address base, const FieldDecl *field)
Drill down to the storage of a field without walking into reference types.
ConstantEmissionKind
Can we constant-emit a load of a reference to a variable of the given type? This is different from pr...
static bool isConstantEmittableObjectType(QualType type)
Given an object of the given canonical type, can we safely copy a value out of it based on its initia...
static QualType getFixedSizeElementType(const ASTContext &ctx, const VariableArrayType *vla)
static LValue EmitCapturedFieldLValue(CodeGenFunction &CGF, const FieldDecl *FD, llvm::Value *ThisValue)
static std::optional< LValue > EmitLValueOrThrowExpression(CodeGenFunction &CGF, const Expr *Operand)
Emit the operand of a glvalue conditional operator.
static CheckRecoverableKind getRecoverableKind(SanitizerKind::SanitizerOrdinal Ordinal)
static llvm::Value * emitArraySubscriptGEP(CodeGenFunction &CGF, llvm::Type *elemType, llvm::Value *ptr, ArrayRef< llvm::Value * > indices, bool inbounds, bool signedIndices, SourceLocation loc, const llvm::Twine &name="arrayidx")
static LValue EmitFunctionDeclLValue(CodeGenFunction &CGF, const Expr *E, GlobalDecl GD)
static RawAddress MaybeConvertMatrixAddress(RawAddress Addr, CodeGenFunction &CGF, bool IsVector=true)
static LValueOrRValue emitPseudoObjectExpr(CodeGenFunction &CGF, const PseudoObjectExpr *E, bool forLValue, AggValueSlot slot)
static Address wrapWithBPFPreserveStaticOffset(CodeGenFunction &CGF, Address &Addr)
static DeclRefExpr * tryToConvertMemberExprToDeclRefExpr(CodeGenFunction &CGF, const MemberExpr *ME)
static llvm::Value * getArrayIndexingBound(CodeGenFunction &CGF, const Expr *Base, QualType &IndexedType, LangOptions::StrictFlexArraysLevelKind StrictFlexArraysLevel)
If Base is known to point to the start of an array, return the length of that array.
static RValue EmitLoadOfMatrixLValue(LValue LV, SourceLocation Loc, CodeGenFunction &CGF)
static ConstantEmissionKind checkVarTypeForConstantEmission(QualType type)
static QualType getConstantExprReferredType(const FullExpr *E, const ASTContext &Ctx)
static bool getRangeForType(CodeGenFunction &CGF, QualType Ty, llvm::APInt &Min, llvm::APInt &End, bool StrictEnums, bool IsBool)
static std::optional< int64_t > getOffsetDifferenceInBits(CodeGenFunction &CGF, const FieldDecl *FD1, const FieldDecl *FD2)
Returns the relative offset difference between FD1 and FD2.
static CGCallee EmitDirectCallee(CodeGenFunction &CGF, GlobalDecl GD)
static LValue EmitThreadPrivateVarDeclLValue(CodeGenFunction &CGF, const VarDecl *VD, QualType T, Address Addr, llvm::Type *RealVarTy, SourceLocation Loc)
static bool getGEPIndicesToField(CodeGenFunction &CGF, const RecordDecl *RD, const FieldDecl *Field, RecIndicesTy &Indices)
static bool OnlyHasInlineBuiltinDeclaration(const FunctionDecl *FD)
static LValue EmitGlobalVarDeclLValue(CodeGenFunction &CGF, const Expr *E, const VarDecl *VD)
static bool hasAnyVptr(const QualType Type, const ASTContext &Context)
static bool IsPreserveAIArrayBase(CodeGenFunction &CGF, const Expr *ArrayBase)
Given an array base, check whether its member access belongs to a record with preserve_access_index a...
static Address emitDeclTargetVarDeclLValue(CodeGenFunction &CGF, const VarDecl *VD, QualType T)
static bool canEmitSpuriousReferenceToVariable(CodeGenFunction &CGF, const DeclRefExpr *E, const VarDecl *VD)
Determine whether we can emit a reference to VD from the current context, despite not necessarily hav...
VariableTypeDescriptorKind
@ TK_Float
A floating-point type.
@ TK_Unknown
Any other type. The value representation is unspecified.
@ TK_Integer
An integer type.
@ TK_BitInt
An _BitInt(N) type.
static CharUnits getArrayElementAlign(CharUnits arrayAlign, llvm::Value *idx, CharUnits eltSize)
static RawAddress createReferenceTemporary(CodeGenFunction &CGF, const MaterializeTemporaryExpr *M, const Expr *Inner, RawAddress *Alloca=nullptr)
static bool isAAPCS(const TargetInfo &TargetInfo)
Helper method to check if the underlying ABI is AAPCS.
static void EmitStoreOfMatrixScalar(llvm::Value *value, LValue lvalue, bool isInit, CodeGenFunction &CGF)
static Address EmitPointerWithAlignment(const Expr *E, LValueBaseInfo *BaseInfo, TBAAAccessInfo *TBAAInfo, KnownNonNull_t IsKnownNonNull, CodeGenFunction &CGF)
static Address emitPreserveStructAccess(CodeGenFunction &CGF, LValue base, Address addr, const FieldDecl *field)
const SanitizerHandlerInfo SanitizerHandlers[]
static Address emitAddrOfZeroSizeField(CodeGenFunction &CGF, Address Base, const FieldDecl *Field)
Get the address of a zero-sized field within a record.
static void emitCheckHandlerCall(CodeGenFunction &CGF, llvm::FunctionType *FnType, ArrayRef< llvm::Value * > FnArgs, SanitizerHandler CheckHandler, CheckRecoverableKind RecoverKind, bool IsFatal, llvm::BasicBlock *ContBB, bool NoMerge)
static Address emitOMPArraySectionBase(CodeGenFunction &CGF, const Expr *Base, LValueBaseInfo &BaseInfo, TBAAAccessInfo &TBAAInfo, QualType BaseTy, QualType ElTy, bool IsLowerBound)
static void pushTemporaryCleanup(CodeGenFunction &CGF, const MaterializeTemporaryExpr *M, const Expr *E, Address ReferenceTemporary)
static const SanitizerMask AlwaysRecoverable
static const SanitizerMask Unrecoverable
static const RecordType * getRecordType(QualType QT)
Checks that the passed in QualType either is of RecordType or points to RecordType.
Defines the SourceManager interface.
static QualType getPointeeType(const MemRegion *R)
const LValueBase getLValueBase() const
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
SourceManager & getSourceManager()
CharUnits getTypeAlignInChars(QualType T) const
Return the ABI-specified alignment of a (complete) type T, in characters.
uint64_t getFieldOffset(const ValueDecl *FD) const
Get the offset of a FieldDecl or IndirectFieldDecl, in bits.
QualType getTagDeclType(const TagDecl *Decl) const
Return the unique reference to the type for the specified TagDecl (struct/union/class/enum) decl.
const ASTRecordLayout & getASTRecordLayout(const RecordDecl *D) const
Get or compute information about the layout of the specified record (struct/union/class) D,...
CanQualType getCanonicalType(QualType T) const
Return the canonical (structural) type corresponding to the specified potentially non-canonical type ...
QualType getPointerType(QualType T) const
Return the uniqued reference to the type for a pointer to the specified type.
Builtin::Context & BuiltinInfo
const LangOptions & getLangOpts() const
bool isTypeIgnoredBySanitizer(const SanitizerMask &Mask, const QualType &Ty) const
Check if a type can have its sanitizer instrumentation elided based on its presence within an ignorel...
QualType getPointerDiffType() const
Return the unique type for "ptrdiff_t" (C99 7.17) defined in <stddef.h>.
const NoSanitizeList & getNoSanitizeList() const
llvm::DenseMap< const CXXMethodDecl *, CXXCastPath > LambdaCastPaths
For capturing lambdas with an explicit object parameter whose type is derived from the lambda type,...
CharUnits getDeclAlign(const Decl *D, bool ForAlignof=false) const
Return a conservative estimate of the alignment of the specified decl D.
uint64_t getTypeSize(QualType T) const
Return the size of the specified (complete) type T, in bits.
CharUnits getTypeSizeInChars(QualType T) const
Return the size of the specified (complete) type T, in characters.
const VariableArrayType * getAsVariableArrayType(QualType T) const
CharUnits toCharUnitsFromBits(int64_t BitSize) const
Convert a size in bits to a size in characters.
unsigned getTargetAddressSpace(LangAS AS) const
uint64_t getCharWidth() const
Return the size of the character type, in bits.
ASTRecordLayout - This class contains layout information for one RecordDecl, which is a struct/union/...
uint64_t getFieldOffset(unsigned FieldNo) const
getFieldOffset - Get the offset of the given field index, in bits.
AbstractConditionalOperator - An abstract base class for ConditionalOperator and BinaryConditionalOpe...
This class represents BOTH the OpenMP Array Section and OpenACC 'subarray', with a boolean differenti...
static QualType getBaseOriginalType(const Expr *Base)
Return original type of the base expression for array section.
ArraySubscriptExpr - [C99 6.5.2.1] Array Subscripting.
Represents an array type, per C99 6.7.5.2 - Array Declarators.
QualType getElementType() const
A builtin binary operation expression such as "x + y" or "x <= y".
A fixed int type of a specified bitwidth.
bool isPredefinedLibFunction(unsigned ID) const
Determines whether this builtin is a predefined libc/libm function, such as "malloc",...
Represents binding an expression to a temporary.
Represents a call to a C++ constructor.
Represents a C++ destructor within a class.
Represents a C++ struct/union/class.
bool hasTrivialDestructor() const
Determine whether this class has a trivial destructor (C++ [class.dtor]p3)
bool isDynamicClass() const
bool hasDefinition() const
A C++ typeid expression (C++ [expr.typeid]), which gets the type_info that corresponds to the supplie...
A Microsoft C++ __uuidof expression, which gets the _GUID that corresponds to the supplied type or ex...
CallExpr - Represents a function call (C99 6.5.2.2, C++ [expr.call]).
CastExpr - Base class for type casts, including both implicit casts (ImplicitCastExpr) and explicit c...
CharUnits - This is an opaque type for sizes expressed in character units.
CharUnits alignmentAtOffset(CharUnits offset) const
Given that this is a non-zero alignment value, what is the alignment at the given offset?
llvm::MaybeAlign getAsMaybeAlign() const
getAsMaybeAlign - Returns Quantity as a valid llvm::Align or std::nullopt, Beware llvm::MaybeAlign as...
llvm::Align getAsAlign() const
getAsAlign - Returns Quantity as a valid llvm::Align, Beware llvm::Align assumes power of two 8-bit b...
QuantityType getQuantity() const
getQuantity - Get the raw integer representation of this quantity.
static CharUnits One()
One - Construct a CharUnits quantity of one.
CharUnits alignmentOfArrayElement(CharUnits elementSize) const
Given that this is the alignment of the first element of an array, return the minimum alignment of an...
static CharUnits fromQuantity(QuantityType Quantity)
fromQuantity - Construct a CharUnits quantity from a raw integer type.
static CharUnits Zero()
Zero - Construct a CharUnits quantity of zero.
SanitizerSet SanitizeMergeHandlers
Set of sanitizer checks that can merge handlers (smaller code size at the expense of debuggability).
PointerAuthOptions PointerAuth
Configuration for pointer-signing.
SanitizerSet SanitizeTrap
Set of sanitizer checks that trap rather than diagnose.
SanitizerSet SanitizeRecover
Set of sanitizer checks that are non-fatal (i.e.
std::string TrapFuncName
If not an empty string, trap intrinsics are lowered to calls to this function instead of to trap inst...
virtual llvm::FixedVectorType * getOptimalVectorMemoryType(llvm::FixedVectorType *T, const LangOptions &Opt) const
Returns the optimal vector memory type based on the given vector type.
Like RawAddress, an abstract representation of an aligned address, but the pointer contained in this ...
llvm::Value * getBasePointer() const
llvm::Value * emitRawPointer(CodeGenFunction &CGF) const
Return the pointer contained in this class after authenticating it and adding offset to it if necessa...
CharUnits getAlignment() const
llvm::Type * getElementType() const
Return the type of the values stored in this address.
Address withPointer(llvm::Value *NewPointer, KnownNonNull_t IsKnownNonNull) const
Return address with different pointer, but same element type and alignment.
Address withElementType(llvm::Type *ElemTy) const
Return address with different element type, but same pointer and alignment.
KnownNonNull_t isKnownNonNull() const
Whether the pointer is known not to be null.
Address setKnownNonNull()
void setAlignment(CharUnits Value)
void replaceBasePointer(llvm::Value *P)
This function is used in situations where the caller is doing some sort of opaque "laundering" of the...
llvm::PointerType * getType() const
Return the type of the pointer value.
static AggValueSlot ignored()
ignored - Returns an aggregate value slot indicating that the aggregate value is being ignored.
Address getAddress() const
void setExternallyDestructed(bool destructed=true)
static AggValueSlot forLValue(const LValue &LV, IsDestructed_t isDestructed, NeedsGCBarriers_t needsGC, IsAliased_t isAliased, Overlap_t mayOverlap, IsZeroed_t isZeroed=IsNotZeroed, IsSanitizerChecked_t isChecked=IsNotSanitizerChecked)
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.
A scoped helper to set the current debug location to the specified location or preferred location of ...
llvm::StoreInst * CreateStore(llvm::Value *Val, Address Addr, bool IsVolatile=false)
Address CreateConstInBoundsByteGEP(Address Addr, CharUnits Offset, const llvm::Twine &Name="")
Given a pointer to i8, adjust it by a given constant offset.
Address CreateGEP(CodeGenFunction &CGF, Address Addr, llvm::Value *Index, const llvm::Twine &Name="")
Address CreatePointerBitCastOrAddrSpaceCast(Address Addr, llvm::Type *Ty, llvm::Type *ElementTy, const llvm::Twine &Name="")
Address CreateConstGEP2_32(Address Addr, unsigned Idx0, unsigned Idx1, const llvm::Twine &Name="")
Address CreateConstArrayGEP(Address Addr, uint64_t Index, const llvm::Twine &Name="")
Given addr = [n x T]* ... produce name = getelementptr inbounds addr, i64 0, i64 index where i64 is a...
Address CreateStructGEP(Address Addr, unsigned Index, const llvm::Twine &Name="")
llvm::LoadInst * CreateLoad(Address Addr, const llvm::Twine &Name="")
Address CreatePreserveStructAccessIndex(Address Addr, unsigned Index, unsigned FieldIndex, llvm::MDNode *DbgInfo)
Address CreateLaunderInvariantGroup(Address Addr)
llvm::LoadInst * CreateAlignedLoad(llvm::Type *Ty, llvm::Value *Addr, CharUnits Align, const llvm::Twine &Name="")
Address CreatePreserveUnionAccessIndex(Address Addr, unsigned FieldIndex, llvm::MDNode *DbgInfo)
Address CreateStripInvariantGroup(Address Addr)
Address CreateAddrSpaceCast(Address Addr, llvm::Type *Ty, llvm::Type *ElementTy, const llvm::Twine &Name="")
Address CreateConstInBoundsGEP(Address Addr, uint64_t Index, const llvm::Twine &Name="")
Given addr = T* ... produce name = getelementptr inbounds addr, i64 index where i64 is actually the t...
Address CreateInBoundsGEP(Address Addr, ArrayRef< llvm::Value * > IdxList, llvm::Type *ElementType, CharUnits Align, const Twine &Name="")
virtual llvm::Function * getKernelStub(llvm::GlobalValue *Handle)=0
Get kernel stub by kernel handle.
virtual void registerGlobalDtor(CodeGenFunction &CGF, const VarDecl &D, llvm::FunctionCallee Dtor, llvm::Constant *Addr)=0
Emit code to force the execution of a destructor during global teardown.
virtual llvm::Value * EmitMemberPointerIsNotNull(CodeGenFunction &CGF, llvm::Value *MemPtr, const MemberPointerType *MPT)
Determine if a member pointer is non-null. Returns an i1.
virtual LValue EmitThreadLocalVarDeclLValue(CodeGenFunction &CGF, const VarDecl *VD, QualType LValType)=0
Emit a reference to a non-local thread_local variable (including triggering the initialization of all...
virtual bool usesThreadWrapperFunction(const VarDecl *VD) const =0
MangleContext & getMangleContext()
Gets the mangle context.
Abstract information about a function or function prototype.
const GlobalDecl getCalleeDecl() const
All available information about a concrete callee.
CGCalleeInfo getAbstractInfo() const
const CXXPseudoDestructorExpr * getPseudoDestructorExpr() const
bool isPseudoDestructor() const
static CGCallee forBuiltin(unsigned builtinID, const FunctionDecl *builtinDecl)
unsigned getBuiltinID() const
static CGCallee forDirect(llvm::Constant *functionPtr, const CGCalleeInfo &abstractInfo=CGCalleeInfo())
const FunctionDecl * getBuiltinDecl() const
static CGCallee forPseudoDestructor(const CXXPseudoDestructorExpr *E)
This class gathers all debug information during compilation and is responsible for emitting to llvm g...
llvm::DIType * getOrCreateStandaloneType(QualType Ty, SourceLocation Loc)
Emit standalone debug info for a type.
llvm::DIType * getOrCreateRecordType(QualType Ty, SourceLocation L)
Emit record type's standalone debug info.
CGFunctionInfo - Class to encapsulate the information about a function definition.
virtual void EmitObjCIvarAssign(CodeGen::CodeGenFunction &CGF, llvm::Value *src, Address dest, llvm::Value *ivarOffset)=0
virtual void EmitObjCWeakAssign(CodeGen::CodeGenFunction &CGF, llvm::Value *src, Address dest)=0
virtual LValue EmitObjCValueForIvar(CodeGen::CodeGenFunction &CGF, QualType ObjectTy, llvm::Value *BaseValue, const ObjCIvarDecl *Ivar, unsigned CVRQualifiers)=0
virtual llvm::Value * EmitIvarOffset(CodeGen::CodeGenFunction &CGF, const ObjCInterfaceDecl *Interface, const ObjCIvarDecl *Ivar)=0
virtual llvm::Value * EmitObjCWeakRead(CodeGen::CodeGenFunction &CGF, Address AddrWeakObj)=0
virtual Address GetAddrOfSelector(CodeGenFunction &CGF, Selector Sel)=0
Get the address of a selector for the specified name and type values.
virtual void EmitObjCStrongCastAssign(CodeGen::CodeGenFunction &CGF, llvm::Value *src, Address dest)=0
virtual void EmitObjCGlobalAssign(CodeGen::CodeGenFunction &CGF, llvm::Value *src, Address dest, bool threadlocal=false)=0
virtual Address getAddrOfThreadPrivate(CodeGenFunction &CGF, const VarDecl *VD, Address VDAddr, SourceLocation Loc)
Returns address of the threadprivate variable for the current thread.
virtual ConstantAddress getAddrOfDeclareTargetVar(const VarDecl *VD)
Returns the address of the variable marked as declare target with link clause OR as declare target wi...
bool hasRequiresUnifiedSharedMemory() const
Return whether the unified_shared_memory has been specified.
bool isNontemporalDecl(const ValueDecl *VD) const
Checks if the VD variable is marked as nontemporal declaration in current context.
virtual void checkAndEmitLastprivateConditional(CodeGenFunction &CGF, const Expr *LHS)
Checks if the provided LVal is lastprivate conditional and emits the code to update the value of the ...
CGRecordLayout - This class handles struct and union layout info while lowering AST types to LLVM typ...
const CGBitFieldInfo & getBitFieldInfo(const FieldDecl *FD) const
Return the BitFieldInfo that corresponds to the field FD.
unsigned getLLVMFieldNo(const FieldDecl *FD) const
Return llvm::StructType element number that corresponds to the field FD.
bool containsFieldDecl(const FieldDecl *FD) const
CallArgList - Type for representing both the value and type of arguments in a call.
void add(RValue rvalue, QualType type)
void addWriteback(LValue srcLV, Address temporary, llvm::Value *toUse, const Expr *writebackExpr=nullptr, llvm::Value *lifetimeSz=nullptr)
virtual llvm::Value * getContextValue() const
virtual const FieldDecl * lookup(const VarDecl *VD) const
Lookup the captured field decl for a variable.
static ConstantEmission forValue(llvm::Constant *C)
static ConstantEmission forReference(llvm::Constant *C)
static bool shouldBindAsLValue(const Expr *expr)
static OpaqueValueMappingData bind(CodeGenFunction &CGF, const OpaqueValueExpr *ov, const Expr *e)
static bool shouldBindAsLValue(const Expr *expr)
CodeGenFunction - This class organizes the per-function state that is used while generating LLVM code...
llvm::Value * EmitFromMemory(llvm::Value *Value, QualType Ty)
EmitFromMemory - Change a scalar value from its memory representation to its value representation.
LValue EmitOpaqueValueLValue(const OpaqueValueExpr *e)
RValue EmitLoadOfGlobalRegLValue(LValue LV)
LValue EmitObjCIvarRefLValue(const ObjCIvarRefExpr *E)
void FinishFunction(SourceLocation EndLoc=SourceLocation())
FinishFunction - Complete IR generation of the current function.
LValue EmitCompoundLiteralLValue(const CompoundLiteralExpr *E)
llvm::Value * EmitLifetimeStart(llvm::TypeSize Size, llvm::Value *Addr)
llvm::Value * GetVTablePtr(Address This, llvm::Type *VTableTy, const CXXRecordDecl *VTableClass, VTableAuthMode AuthMode=VTableAuthMode::Authenticate)
GetVTablePtr - Return the Value of the vtable pointer member pointed to by This.
Address EmitCXXMemberDataPointerAddress(const Expr *E, Address base, llvm::Value *memberPtr, const MemberPointerType *memberPtrType, LValueBaseInfo *BaseInfo=nullptr, TBAAAccessInfo *TBAAInfo=nullptr)
llvm::Value * EmitNonNullRValueCheck(RValue RV, QualType T)
Create a check that a scalar RValue is non-null.
static TypeEvaluationKind getEvaluationKind(QualType T)
getEvaluationKind - Return the TypeEvaluationKind of QualType T.
static bool ContainsLabel(const Stmt *S, bool IgnoreCaseStmts=false)
ContainsLabel - Return true if the statement contains a label in it.
LValue EmitCastLValue(const CastExpr *E)
void EmitBranchOnBoolExpr(const Expr *Cond, llvm::BasicBlock *TrueBlock, llvm::BasicBlock *FalseBlock, uint64_t TrueCount, Stmt::Likelihood LH=Stmt::LH_None, const Expr *ConditionalOp=nullptr)
EmitBranchOnBoolExpr - Emit a branch on a boolean condition (e.g.
llvm::CallInst * EmitTrapCall(llvm::Intrinsic::ID IntrID)
Emit a call to trap or debugtrap and attach function attribute "trap-func-name" if specified.
bool sanitizePerformTypeCheck() const
Whether any type-checking sanitizers are enabled.
void EmitSanitizerStatReport(llvm::SanitizerStatKind SSK)
SanitizerSet SanOpts
Sanitizers enabled for this function.
LValue EmitCoawaitLValue(const CoawaitExpr *E)
LValue getOrCreateOpaqueLValueMapping(const OpaqueValueExpr *e)
Given an opaque value expression, return its LValue mapping if it exists, otherwise create one.
LValue EmitAggExprToLValue(const Expr *E)
EmitAggExprToLValue - Emit the computation of the specified expression of aggregate type into a tempo...
RValue EmitBlockCallExpr(const CallExpr *E, ReturnValueSlot ReturnValue, llvm::CallBase **CallOrInvoke)
llvm::Value * EmitIvarOffsetAsPointerDiff(const ObjCInterfaceDecl *Interface, const ObjCIvarDecl *Ivar)
void EmitStoreThroughLValue(RValue Src, LValue Dst, bool isInit=false)
EmitStoreThroughLValue - Store the specified rvalue into the specified lvalue, where both are guarant...
void pushLifetimeExtendedDestroy(CleanupKind kind, Address addr, QualType type, Destroyer *destroyer, bool useEHCleanupForArray)
RValue EmitCUDAKernelCallExpr(const CUDAKernelCallExpr *E, ReturnValueSlot ReturnValue, llvm::CallBase **CallOrInvoke)
LValue EmitCompoundAssignmentLValue(const CompoundAssignOperator *E)
CGCapturedStmtInfo * CapturedStmtInfo
void EmitCallArgs(CallArgList &Args, PrototypeWrapper Prototype, llvm::iterator_range< CallExpr::const_arg_iterator > ArgRange, AbstractCallee AC=AbstractCallee(), unsigned ParamsToSkip=0, EvaluationOrder Order=EvaluationOrder::Default)
LValue EmitCallExprLValue(const CallExpr *E, llvm::CallBase **CallOrInvoke=nullptr)
void EmitBoundsCheck(const Expr *E, const Expr *Base, llvm::Value *Index, QualType IndexType, bool Accessed)
Emit a check that Base points into an array object, which we can access at index Index.
void EmitBitfieldConversionCheck(llvm::Value *Src, QualType SrcType, llvm::Value *Dst, QualType DstType, const CGBitFieldInfo &Info, SourceLocation Loc)
Emit a check that an [implicit] conversion of a bitfield.
void EmitTrapCheck(llvm::Value *Checked, SanitizerHandler CheckHandlerID, bool NoMerge=false)
Create a basic block that will call the trap intrinsic, and emit a conditional branch to it,...
LValue EmitHLSLArrayAssignLValue(const BinaryOperator *E)
bool inSuspendBlock() const
Address EmitLoadOfPointer(Address Ptr, const PointerType *PtrTy, LValueBaseInfo *BaseInfo=nullptr, TBAAAccessInfo *TBAAInfo=nullptr)
Load a pointer with type PtrTy stored at address Ptr.
RawAddress CreateDefaultAlignTempAlloca(llvm::Type *Ty, const Twine &Name="tmp")
CreateDefaultAlignedTempAlloca - This creates an alloca with the default ABI alignment of the given L...
VlaSizePair getVLASize(const VariableArrayType *vla)
Returns an LLVM value that corresponds to the size, in non-variably-sized elements,...
LValue EmitHLSLOutArgExpr(const HLSLOutArgExpr *E, CallArgList &Args, QualType Ty)
CleanupKind getARCCleanupKind()
Retrieves the default cleanup kind for an ARC cleanup.
RValue EmitRValueForField(LValue LV, const FieldDecl *FD, SourceLocation Loc)
LValue EmitLValue(const Expr *E, KnownNonNull_t IsKnownNonNull=NotKnownNonNull)
EmitLValue - Emit code to compute a designator that specifies the location of the expression.
void EmitVTablePtrCheckForCast(QualType T, Address Derived, bool MayBeNull, CFITypeCheckKind TCK, SourceLocation Loc)
Derived is the presumed address of an object of type T after a cast.
RValue EmitAtomicLoad(LValue LV, SourceLocation SL, AggValueSlot Slot=AggValueSlot::ignored())
llvm::Value * EmitIvarOffset(const ObjCInterfaceDecl *Interface, const ObjCIvarDecl *Ivar)
llvm::Value * EmitARCStoreWeak(Address addr, llvm::Value *value, bool ignored)
LValue EmitBinaryOperatorLValue(const BinaryOperator *E)
void EmitVariablyModifiedType(QualType Ty)
EmitVLASize - Capture all the sizes for the VLA expressions in the given variably-modified type and s...
RawAddress CreateTempAllocaWithoutCast(llvm::Type *Ty, CharUnits align, const Twine &Name="tmp", llvm::Value *ArraySize=nullptr)
llvm::BasicBlock * createBasicBlock(const Twine &name="", llvm::Function *parent=nullptr, llvm::BasicBlock *before=nullptr)
createBasicBlock - Create an LLVM basic block.
RValue EmitCXXPseudoDestructorExpr(const CXXPseudoDestructorExpr *E)
LValue EmitMaterializeTemporaryExpr(const MaterializeTemporaryExpr *E)
llvm::Value * EmitARCLoadWeakRetained(Address addr)
const LangOptions & getLangOpts() const
llvm::Value * LoadPassedObjectSize(const Expr *E, QualType EltTy)
If E references a parameter with pass_object_size info or a constant array size modifier,...
llvm::Value * EmitLoadOfCountedByField(const Expr *Base, const FieldDecl *FAMDecl, const FieldDecl *CountDecl)
Build an expression accessing the "counted_by" field.
llvm::Constant * EmitCheckTypeDescriptor(QualType T)
Emit a description of a type in a format suitable for passing to a runtime sanitizer handler.
LValue EmitLValueForFieldInitialization(LValue Base, const FieldDecl *Field)
EmitLValueForFieldInitialization - Like EmitLValueForField, except that if the Field is a reference,...
LValue EmitInitListLValue(const InitListExpr *E)
void EmitBlock(llvm::BasicBlock *BB, bool IsFinished=false)
EmitBlock - Emit the given block.
void EmitUnreachable(SourceLocation Loc)
Emit a reached-unreachable diagnostic if Loc is valid and runtime checking is enabled.
llvm::AllocaInst * CreateTempAlloca(llvm::Type *Ty, const Twine &Name="tmp", llvm::Value *ArraySize=nullptr)
CreateTempAlloca - This creates an alloca and inserts it into the entry block if ArraySize is nullptr...
Address makeNaturalAddressForPointer(llvm::Value *Ptr, QualType T, CharUnits Alignment=CharUnits::Zero(), bool ForPointeeType=false, LValueBaseInfo *BaseInfo=nullptr, TBAAAccessInfo *TBAAInfo=nullptr, KnownNonNull_t IsKnownNonNull=NotKnownNonNull)
Construct an address with the natural alignment of T.
Address EmitLoadOfReference(LValue RefLVal, LValueBaseInfo *PointeeBaseInfo=nullptr, TBAAAccessInfo *PointeeTBAAInfo=nullptr)
ComplexPairTy EmitComplexExpr(const Expr *E, bool IgnoreReal=false, bool IgnoreImag=false)
EmitComplexExpr - Emit the computation of the specified expression of complex type,...
RValue EmitLoadOfLValue(LValue V, SourceLocation Loc)
EmitLoadOfLValue - Given an expression that represents a value lvalue, this method emits the address ...
RValue convertTempToRValue(Address addr, QualType type, SourceLocation Loc)
Address EmitExtVectorElementLValue(LValue V)
void EmitAnyExprToMem(const Expr *E, Address Location, Qualifiers Quals, bool IsInitializer)
EmitAnyExprToMem - Emits the code necessary to evaluate an arbitrary expression into the given memory...
@ TCK_DowncastPointer
Checking the operand of a static_cast to a derived pointer type.
@ TCK_DowncastReference
Checking the operand of a static_cast to a derived reference type.
@ TCK_MemberAccess
Checking the object expression in a non-static data member access.
@ TCK_Store
Checking the destination of a store. Must be suitably sized and aligned.
@ TCK_UpcastToVirtualBase
Checking the operand of a cast to a virtual base object.
@ TCK_MemberCall
Checking the 'this' pointer for a call to a non-static member function.
@ TCK_DynamicOperation
Checking the operand of a dynamic_cast or a typeid expression.
@ TCK_ReferenceBinding
Checking the bound value in a reference binding.
@ TCK_Upcast
Checking the operand of a cast to a base object.
void SetDivFPAccuracy(llvm::Value *Val)
Set the minimum required accuracy of the given sqrt operation based on CodeGenOpts.
RValue EmitObjCMessageExpr(const ObjCMessageExpr *E, ReturnValueSlot Return=ReturnValueSlot())
void EmitIgnoredExpr(const Expr *E)
EmitIgnoredExpr - Emit an expression in a context which ignores the result.
bool InNoMergeAttributedStmt
True if the current statement has nomerge attribute.
LValue EmitUnsupportedLValue(const Expr *E, const char *Name)
EmitUnsupportedLValue - Emit a dummy l-value using the type of E and issue an ErrorUnsupported style ...
llvm::Type * ConvertTypeForMem(QualType T)
const Decl * CurCodeDecl
CurCodeDecl - This is the inner-most code context, which includes blocks.
llvm::AssertingVH< llvm::Instruction > AllocaInsertPt
AllocaInsertPoint - This is an instruction in the entry block before which we prefer to insert alloca...
void EmitScalarInit(const Expr *init, const ValueDecl *D, LValue lvalue, bool capturedByInit)
unsigned getDebugInfoFIndex(const RecordDecl *Rec, unsigned FieldIndex)
Get the record field index as represented in debug info.
LValue EmitLValueForField(LValue Base, const FieldDecl *Field)
LValue EmitCheckedLValue(const Expr *E, TypeCheckKind TCK)
Same as EmitLValue but additionally we generate checking code to guard against undefined behavior.
RawAddress CreateMemTemp(QualType T, const Twine &Name="tmp", RawAddress *Alloca=nullptr)
CreateMemTemp - Create a temporary memory object of the given type, with appropriate alignmen and cas...
void markStmtMaybeUsed(const Stmt *S)
static Destroyer destroyCXXObject
@ ForceLeftToRight
! Language semantics require left-to-right evaluation.
@ Default
! No language constraints on evaluation order.
@ ForceRightToLeft
! Language semantics require right-to-left evaluation.
Destroyer * getDestroyer(QualType::DestructionKind destructionKind)
RawAddress CreateMemTempWithoutCast(QualType T, const Twine &Name="tmp")
CreateMemTemp - Create a temporary memory object of the given type, with appropriate alignmen without...
void EmitStoreThroughBitfieldLValue(RValue Src, LValue Dst, llvm::Value **Result=nullptr)
EmitStoreThroughBitfieldLValue - Store Src into Dst with same constraints as EmitStoreThroughLValue.
void EmitCfiCheckStub()
Emit a stub for the cross-DSO CFI check function.
llvm::Value * EmitObjCConsumeObject(QualType T, llvm::Value *Ptr)
ConstantEmission tryEmitAsConstant(DeclRefExpr *refExpr)
llvm::Value * EmitARCLoadWeak(Address addr)
const TargetInfo & getTarget() const
LValue EmitCXXConstructLValue(const CXXConstructExpr *E)
bool isInConditionalBranch() const
isInConditionalBranch - Return true if we're currently emitting one branch or the other of a conditio...
llvm::Value * getTypeSize(QualType Ty)
Returns calculated size of the specified type.
std::pair< LValue, llvm::Value * > EmitARCStoreAutoreleasing(const BinaryOperator *e)
LValue EmitVAArgExprLValue(const VAArgExpr *E)
bool EmitScalarRangeCheck(llvm::Value *Value, QualType Ty, SourceLocation Loc)
Check if the scalar Value is within the valid range for the given type Ty.
llvm::Function * generateDestroyHelper(Address addr, QualType type, Destroyer *destroyer, bool useEHCleanupForArray, const VarDecl *VD)
Address EmitPointerWithAlignment(const Expr *Addr, LValueBaseInfo *BaseInfo=nullptr, TBAAAccessInfo *TBAAInfo=nullptr, KnownNonNull_t IsKnownNonNull=NotKnownNonNull)
EmitPointerWithAlignment - Given an expression with a pointer type, emit the value and compute our be...
llvm::Value * EmitMatrixIndexExpr(const Expr *E)
LValue EmitCoyieldLValue(const CoyieldExpr *E)
RValue EmitAnyExprToTemp(const Expr *E)
EmitAnyExprToTemp - Similarly to EmitAnyExpr(), however, the result will always be accessible even if...
void EmitComplexExprIntoLValue(const Expr *E, LValue dest, bool isInit)
EmitComplexExprIntoLValue - Emit the given expression of complex type and place its result into the s...
RValue EmitCXXMemberCallExpr(const CXXMemberCallExpr *E, ReturnValueSlot ReturnValue, llvm::CallBase **CallOrInvoke=nullptr)
Address EmitArrayToPointerDecay(const Expr *Array, LValueBaseInfo *BaseInfo=nullptr, TBAAAccessInfo *TBAAInfo=nullptr)
Address mergeAddressesInConditionalExpr(Address LHS, Address RHS, llvm::BasicBlock *LHSBlock, llvm::BasicBlock *RHSBlock, llvm::BasicBlock *MergeBlock, QualType MergedType)
LValue EmitUnaryOpLValue(const UnaryOperator *E)
ComplexPairTy EmitComplexPrePostIncDec(const UnaryOperator *E, LValue LV, bool isInc, bool isPre)
RValue EmitUnsupportedRValue(const Expr *E, const char *Name)
EmitUnsupportedRValue - Emit a dummy r-value using the type of E and issue an ErrorUnsupported style ...
static unsigned getAccessedFieldNo(unsigned Idx, const llvm::Constant *Elts)
getAccessedFieldNo - Given an encoded value and a result number, return the input field number being ...
void EmitCheck(ArrayRef< std::pair< llvm::Value *, SanitizerKind::SanitizerOrdinal > > Checked, SanitizerHandler Check, ArrayRef< llvm::Constant * > StaticArgs, ArrayRef< llvm::Value * > DynamicArgs)
Create a basic block that will either trap or call a handler function in the UBSan runtime with the p...
RValue EmitBuiltinExpr(const GlobalDecl GD, unsigned BuiltinID, const CallExpr *E, ReturnValueSlot ReturnValue)
RValue EmitAnyExpr(const Expr *E, AggValueSlot aggSlot=AggValueSlot::ignored(), bool ignoreResult=false)
EmitAnyExpr - Emit code to compute the specified expression which can have any type.
void EmitBoundsCheckImpl(const Expr *E, llvm::Value *Bound, llvm::Value *Index, QualType IndexType, QualType IndexedType, bool Accessed)
void StartFunction(GlobalDecl GD, QualType RetTy, llvm::Function *Fn, const CGFunctionInfo &FnInfo, const FunctionArgList &Args, SourceLocation Loc=SourceLocation(), SourceLocation StartLoc=SourceLocation())
Emit code for the start of a function.
void EmitCfiCheckFail()
Emit a cross-DSO CFI failure handling function.
AggValueSlot CreateAggTemp(QualType T, const Twine &Name="tmp", RawAddress *Alloca=nullptr)
CreateAggTemp - Create a temporary memory object for the given aggregate type.
RValue EmitLoadOfExtVectorElementLValue(LValue V)
ComplexPairTy EmitLoadOfComplex(LValue src, SourceLocation loc)
EmitLoadOfComplex - Load a complex number from the specified l-value.
static bool ShouldNullCheckClassCastValue(const CastExpr *Cast)
llvm::Value * EmitComplexToScalarConversion(ComplexPairTy Src, QualType SrcTy, QualType DstTy, SourceLocation Loc)
Emit a conversion from the specified complex type to the specified destination type,...
llvm::Constant * EmitCheckSourceLocation(SourceLocation Loc)
Emit a description of a source location in a format suitable for passing to a runtime sanitizer handl...
LValue EmitComplexAssignmentLValue(const BinaryOperator *E)
Emit an l-value for an assignment (simple or compound) of complex type.
void ErrorUnsupported(const Stmt *S, const char *Type)
ErrorUnsupported - Print out an error that codegen doesn't support the specified stmt yet.
CGDebugInfo * getDebugInfo()
LValue EmitObjCSelectorLValue(const ObjCSelectorExpr *E)
Address emitBlockByrefAddress(Address baseAddr, const VarDecl *V, bool followForward=true)
BuildBlockByrefAddress - Computes the location of the data in a variable which is declared as __block...
LValue EmitObjCEncodeExprLValue(const ObjCEncodeExpr *E)
Address emitAddrOfImagComponent(Address complex, QualType complexType)
LValue EmitDeclRefLValue(const DeclRefExpr *E)
const TargetCodeGenInfo & getTargetHooks() const
llvm::Value * emitBoolVecConversion(llvm::Value *SrcVec, unsigned NumElementsDst, const llvm::Twine &Name="")
LValue MakeNaturalAlignRawAddrLValue(llvm::Value *V, QualType T)
LValue EmitPredefinedLValue(const PredefinedExpr *E)
RValue EmitReferenceBindingToExpr(const Expr *E)
Emits a reference binding to the passed in expression.
void EmitAggExpr(const Expr *E, AggValueSlot AS)
EmitAggExpr - Emit the computation of the specified expression of aggregate type.
Address GetAddressOfDerivedClass(Address Value, const CXXRecordDecl *Derived, CastExpr::path_const_iterator PathBegin, CastExpr::path_const_iterator PathEnd, bool NullCheckValue)
void EmitStoreThroughExtVectorComponentLValue(RValue Src, LValue Dst)
RValue EmitSimpleCallExpr(const CallExpr *E, ReturnValueSlot ReturnValue, llvm::CallBase **CallOrInvoke=nullptr)
llvm::Value * EmitToMemory(llvm::Value *Value, QualType Ty)
EmitToMemory - Change a scalar value from its value representation to its in-memory representation.
llvm::Value * EmitCheckValue(llvm::Value *V)
Convert a value into a format suitable for passing to a runtime sanitizer handler.
void EmitCXXTemporary(const CXXTemporary *Temporary, QualType TempType, Address Ptr)
bool IsInPreservedAIRegion
True if CodeGen currently emits code inside presereved access index region.
llvm::Value * EmitARCRetain(QualType type, llvm::Value *value)
llvm::Value * authPointerToPointerCast(llvm::Value *ResultPtr, QualType SourceType, QualType DestType)
void SetSqrtFPAccuracy(llvm::Value *Val)
Set the minimum required accuracy of the given sqrt operation based on CodeGenOpts.
RValue EmitCall(const CGFunctionInfo &CallInfo, const CGCallee &Callee, ReturnValueSlot ReturnValue, const CallArgList &Args, llvm::CallBase **CallOrInvoke, bool IsMustTail, SourceLocation Loc, bool IsVirtualFunctionPointerThunk=false)
EmitCall - Generate a call of the given function, expecting the given result type,...
RValue EmitPseudoObjectRValue(const PseudoObjectExpr *e, AggValueSlot slot=AggValueSlot::ignored())
void EmitCfiSlowPathCheck(SanitizerKind::SanitizerOrdinal Ordinal, llvm::Value *Cond, llvm::ConstantInt *TypeId, llvm::Value *Ptr, ArrayRef< llvm::Constant * > StaticArgs)
Emit a slow path cross-DSO CFI check which calls __cfi_slowpath if Cond if false.
llvm::CallInst * EmitNounwindRuntimeCall(llvm::FunctionCallee callee, const Twine &name="")
ASTContext & getContext() const
llvm::Value * EmitARCStoreStrong(LValue lvalue, llvm::Value *value, bool resultIgnored)
LValue EmitObjCMessageExprLValue(const ObjCMessageExpr *E)
llvm::Value * EmitLoadOfScalar(Address Addr, bool Volatile, QualType Ty, SourceLocation Loc, AlignmentSource Source=AlignmentSource::Type, bool isNontemporal=false)
EmitLoadOfScalar - Load a scalar value from an address, taking care to appropriately convert from the...
CGCallee EmitCallee(const Expr *E)
void EmitNullabilityCheck(LValue LHS, llvm::Value *RHS, SourceLocation Loc)
Given an assignment *LHS = RHS, emit a test that checks if RHS is nonnull, if LHS is marked _Nonnull.
void EmitAggFinalDestCopy(QualType Type, AggValueSlot Dest, const LValue &Src, ExprValueKind SrcKind)
EmitAggFinalDestCopy - Emit copy of the specified aggregate into destination address.
void Destroyer(CodeGenFunction &CGF, Address addr, QualType ty)
LValue EmitLoadOfPointerLValue(Address Ptr, const PointerType *PtrTy)
std::pair< LValue, LValue > EmitHLSLOutArgLValues(const HLSLOutArgExpr *E, QualType Ty)
void EmitDeclRefExprDbgValue(const DeclRefExpr *E, const APValue &Init)
void EmitCXXThrowExpr(const CXXThrowExpr *E, bool KeepInsertionPoint=true)
llvm::Instruction * getPostAllocaInsertPoint()
Return PostAllocaInsertPt.
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 ...
LValue EmitMemberExpr(const MemberExpr *E)
void pushDestroy(QualType::DestructionKind dtorKind, Address addr, QualType type)
LValue EmitArraySubscriptExpr(const ArraySubscriptExpr *E, bool Accessed=false)
bool ConstantFoldsToSimpleInteger(const Expr *Cond, bool &Result, bool AllowLabels=false)
ConstantFoldsToSimpleInteger - If the specified expression does not fold to a constant,...
llvm::ConstantInt * getUBSanFunctionTypeHash(QualType T) const
Return a type hash constant for a function instrumented by -fsanitize=function.
llvm::Value * GetCountedByFieldExprGEP(const Expr *Base, const FieldDecl *FAMDecl, const FieldDecl *CountDecl)
static Destroyer destroyARCWeak
llvm::DenseMap< const ValueDecl *, FieldDecl * > LambdaCaptureFields
CleanupKind getCleanupKind(QualType::DestructionKind kind)
void EmitCXXConstructExpr(const CXXConstructExpr *E, AggValueSlot Dest)
RValue EmitCXXOperatorMemberCallExpr(const CXXOperatorCallExpr *E, const CXXMethodDecl *MD, ReturnValueSlot ReturnValue, llvm::CallBase **CallOrInvoke)
llvm::Type * ConvertType(QualType T)
llvm::Value * EmitCXXTypeidExpr(const CXXTypeidExpr *E)
Address GetAddrOfBlockDecl(const VarDecl *var)
CodeGenTypes & getTypes() const
void EmitARCInitWeak(Address addr, llvm::Value *value)
LValue EmitArraySectionExpr(const ArraySectionExpr *E, bool IsLowerBound=true)
bool IsSanitizerScope
True if CodeGen currently emits code implementing sanitizer checks.
LValue EmitCXXTypeidLValue(const CXXTypeidExpr *E)
void EmitStoreThroughGlobalRegLValue(RValue Src, LValue Dst)
Address EmitCXXUuidofExpr(const CXXUuidofExpr *E)
void EmitTypeCheck(TypeCheckKind TCK, SourceLocation Loc, LValue LV, QualType Type, SanitizerSet SkippedChecks=SanitizerSet(), llvm::Value *ArraySize=nullptr)
llvm::SmallVector< const ParmVarDecl *, 4 > FnArgs
Save Parameter Decl for coroutine.
QualType BuildFunctionArgList(GlobalDecl GD, FunctionArgList &Args)
LValue EmitStringLiteralLValue(const StringLiteral *E)
static Destroyer destroyARCStrongPrecise
llvm::Value * EvaluateExprAsBool(const Expr *E)
EvaluateExprAsBool - Perform the usual unary conversions on the specified expression and compare the ...
Address LoadCXXThisAddress()
llvm::Value * EmitWithOriginalRHSBitfieldAssignment(const BinaryOperator *E, llvm::Value **Previous, QualType *SrcType)
Retrieve the implicit cast expression of the rhs in a binary operator expression by passing pointers ...
llvm::Value * EmitCheckedInBoundsGEP(llvm::Type *ElemTy, llvm::Value *Ptr, ArrayRef< llvm::Value * > IdxList, bool SignedIndices, bool IsSubtraction, SourceLocation Loc, const Twine &Name="")
Same as IRBuilder::CreateInBoundsGEP, but additionally emits a check to detect undefined behavior whe...
llvm::Value * EmitObjCExtendObjectLifetime(QualType T, llvm::Value *Ptr)
llvm::Value * EmitDynamicCast(Address V, const CXXDynamicCastExpr *DCE)
uint64_t getProfileCount(const Stmt *S)
Get the profiler's count for the given statement.
LValue EmitMatrixSubscriptExpr(const MatrixSubscriptExpr *E)
LValue EmitPseudoObjectLValue(const PseudoObjectExpr *e)
static bool hasAggregateEvaluationKind(QualType T)
llvm::Value * EmitScalarPrePostIncDec(const UnaryOperator *E, LValue LV, bool isInc, bool isPre)
RawAddress CreateIRTemp(QualType T, const Twine &Name="tmp")
CreateIRTemp - Create a temporary IR object of the given type, with appropriate alignment.
void SetFPAccuracy(llvm::Value *Val, float Accuracy)
SetFPAccuracy - Set the minimum required accuracy of the given floating point operation,...
LValue MakeAddrLValue(Address Addr, QualType T, AlignmentSource Source=AlignmentSource::Type)
void EmitStoreOfComplex(ComplexPairTy V, LValue dest, bool isInit)
EmitStoreOfComplex - Store a complex number into the specified l-value.
LValue EmitLoadOfReferenceLValue(LValue RefLVal)
const CallExpr * MustTailCall
LValue MakeNaturalAlignAddrLValue(llvm::Value *V, QualType T, KnownNonNull_t IsKnownNonNull=NotKnownNonNull)
Address GetAddrOfLocalVar(const VarDecl *VD)
GetAddrOfLocalVar - Return the address of a local variable.
LValue EmitObjCIsaExpr(const ObjCIsaExpr *E)
void EmitAtomicStore(RValue rvalue, LValue lvalue, bool isInit)
void EmitInitializationToLValue(const Expr *E, LValue LV, AggValueSlot::IsZeroed_t IsZeroed=AggValueSlot::IsNotZeroed)
EmitInitializationToLValue - Emit an initializer to an LValue.
Address EmitFieldAnnotations(const FieldDecl *D, Address V)
Emit field annotations for the given field & value.
llvm::Value * EmitScalarConversion(llvm::Value *Src, QualType SrcTy, QualType DstTy, SourceLocation Loc)
Emit a conversion from the specified type to the specified destination type, both of which are LLVM s...
LValue EmitCXXUuidofLValue(const CXXUuidofExpr *E)
std::pair< llvm::Value *, llvm::Value * > ComplexPairTy
Address ReturnValue
ReturnValue - The temporary alloca to hold the return value.
static bool isNullPointerAllowed(TypeCheckKind TCK)
Determine whether the pointer type check TCK permits null pointers.
static Destroyer destroyARCStrongImprecise
RValue getOrCreateOpaqueRValueMapping(const OpaqueValueExpr *e)
Given an opaque value expression, return its RValue mapping if it exists, otherwise create one.
void EmitIgnoredConditionalOperator(const AbstractConditionalOperator *E)
RValue GetUndefRValue(QualType Ty)
GetUndefRValue - Get an appropriate 'undef' rvalue for the given type.
LValue EmitLValueForIvar(QualType ObjectTy, llvm::Value *Base, const ObjCIvarDecl *Ivar, unsigned CVRQualifiers)
llvm::Value * emitScalarConstant(const ConstantEmission &Constant, Expr *E)
LValue EmitStmtExprLValue(const StmtExpr *E)
RValue EmitCallExpr(const CallExpr *E, ReturnValueSlot ReturnValue=ReturnValueSlot(), llvm::CallBase **CallOrInvoke=nullptr)
void EnsureInsertPoint()
EnsureInsertPoint - Ensure that an insertion point is defined so that emitted IR has a place to go.
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 ...
llvm::LLVMContext & getLLVMContext()
llvm::Value * EmitScalarExpr(const Expr *E, bool IgnoreResultAssign=false)
EmitScalarExpr - Emit the computation of the specified expression of LLVM scalar type,...
bool LValueIsSuitableForInlineAtomic(LValue Src)
void incrementProfileCounter(const Stmt *S, llvm::Value *StepV=nullptr)
Increment the profiler's counter for the given statement by StepV.
RValue EmitLoadOfAnyValue(LValue V, AggValueSlot Slot=AggValueSlot::ignored(), SourceLocation Loc={})
Like EmitLoadOfLValue but also handles complex and aggregate types.
Address emitAddrOfRealComponent(Address complex, QualType complexType)
static bool isVptrCheckRequired(TypeCheckKind TCK, QualType Ty)
Determine whether the pointer type check TCK requires a vptr check.
LValue EmitComplexCompoundAssignmentLValue(const CompoundAssignOperator *E)
llvm::Type * convertTypeForLoadStore(QualType ASTTy, llvm::Type *LLVMTy=nullptr)
LValue EmitConditionalOperatorLValue(const AbstractConditionalOperator *E)
void EmitStoreOfScalar(llvm::Value *Value, Address Addr, bool Volatile, QualType Ty, AlignmentSource Source=AlignmentSource::Type, bool isInit=false, bool isNontemporal=false)
EmitStoreOfScalar - Store a scalar value to an address, taking care to appropriately convert from the...
LValue EmitExtVectorElementExpr(const ExtVectorElementExpr *E)
RValue EmitLoadOfBitfieldLValue(LValue LV, SourceLocation Loc)
LValue EmitCXXBindTemporaryLValue(const CXXBindTemporaryExpr *E)
LValue EmitPointerToDataMemberBinaryExpr(const BinaryOperator *E)
LValue EmitLValueForLambdaField(const FieldDecl *Field)
static bool IsWrappedCXXThis(const Expr *E)
Check if E is a C++ "this" pointer wrapped in value-preserving casts.
This class organizes the cross-function state that is used while generating LLVM code.
ConstantAddress GetAddrOfMSGuidDecl(const MSGuidDecl *GD)
Get the address of a GUID.
void EmitExplicitCastExprType(const ExplicitCastExpr *E, CodeGenFunction *CGF=nullptr)
Emit type info if type of an expression is a variably modified type.
void setDSOLocal(llvm::GlobalValue *GV) const
llvm::Module & getModule() const
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.
CGDebugInfo * getModuleDebugInfo()
ConstantAddress GetAddrOfConstantCompoundLiteral(const CompoundLiteralExpr *E)
Returns a pointer to a constant global variable for the given file-scope compound literal expression.
llvm::ConstantInt * CreateCrossDsoCfiTypeId(llvm::Metadata *MD)
Generate a cross-DSO type identifier for MD.
void setTypeDescriptorInMap(QualType Ty, llvm::Constant *C)
llvm::Constant * getRawFunctionPointer(GlobalDecl GD, llvm::Type *Ty=nullptr)
Return a function pointer for a reference to the given function.
llvm::FunctionCallee getAddrAndTypeOfCXXStructor(GlobalDecl GD, const CGFunctionInfo *FnInfo=nullptr, llvm::FunctionType *FnType=nullptr, bool DontDefer=false, ForDefinition_t IsForDefinition=NotForDefinition)
llvm::Constant * GetAddrOfRTTIDescriptor(QualType Ty, bool ForEH=false)
Get the address of the RTTI descriptor for the given type.
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.
Address createUnnamedGlobalFrom(const VarDecl &D, llvm::Constant *Constant, CharUnits Align)
llvm::Constant * getFunctionPointer(GlobalDecl GD, llvm::Type *Ty=nullptr)
Return the ABI-correct function pointer value for a reference to the given function.
const ABIInfo & getABIInfo()
DiagnosticsEngine & getDiags() const
void runWithSufficientStackSpace(SourceLocation Loc, llvm::function_ref< void()> Fn)
Run some code with "sufficient" stack space.
const LangOptions & getLangOpts() const
CGCUDARuntime & getCUDARuntime()
Return a reference to the configured CUDA runtime.
CharUnits getNaturalTypeAlignment(QualType T, LValueBaseInfo *BaseInfo=nullptr, TBAAAccessInfo *TBAAInfo=nullptr, bool forPointeeType=false)
CodeGenTypes & getTypes()
const TargetInfo & getTarget() const
llvm::Metadata * CreateMetadataIdentifierForType(QualType T)
Create a metadata identifier for the given type.
llvm::Constant * getTypeDescriptorFromMap(QualType Ty)
void addUsedGlobal(llvm::GlobalValue *GV)
Add a global to a list to be added to the llvm.used metadata.
llvm::MDNode * getTBAABaseTypeInfo(QualType QTy)
getTBAABaseTypeInfo - Get metadata that describes the given base access type.
llvm::GlobalValue::LinkageTypes getLLVMLinkageVarDefinition(const VarDecl *VD)
Returns LLVM linkage for a declarator.
const llvm::DataLayout & getDataLayout() const
CGCXXABI & getCXXABI() const
ConstantAddress GetWeakRefReference(const ValueDecl *VD)
Get a reference to the target of VD.
CGPointerAuthInfo getFunctionPointerAuthInfo(QualType T)
Return the abstract pointer authentication schema for a pointer to the given function type.
CGOpenMPRuntime & getOpenMPRuntime()
Return a reference to the configured OpenMP runtime.
SanitizerMetadata * getSanitizerMetadata()
llvm::Metadata * CreateMetadataIdentifierGeneralized(QualType T)
Create a metadata identifier for the generalization of the given type.
const llvm::Triple & getTriple() const
llvm::Constant * getOrCreateStaticVarDecl(const VarDecl &D, llvm::GlobalValue::LinkageTypes Linkage)
void DecorateInstructionWithTBAA(llvm::Instruction *Inst, TBAAAccessInfo TBAAInfo)
DecorateInstructionWithTBAA - Decorate the instruction with a TBAA tag.
TBAAAccessInfo getTBAAInfoForSubobject(LValue Base, QualType AccessType)
getTBAAInfoForSubobject - Get TBAA information for an access with a given base lvalue.
llvm::Constant * CreateRuntimeVariable(llvm::Type *Ty, StringRef Name)
Create a new runtime global variable with the specified type and name.
TBAAAccessInfo getTBAAAccessInfo(QualType AccessType)
getTBAAAccessInfo - Get TBAA information that describes an access to an object of the given type.
ConstantAddress GetAddrOfConstantStringFromLiteral(const StringLiteral *S, StringRef Name=".str")
Return a pointer to a constant array for the given string literal.
ASTContext & getContext() const
ConstantAddress GetAddrOfTemplateParamObject(const TemplateParamObjectDecl *TPO)
Get the address of a template parameter object.
TBAAAccessInfo mergeTBAAInfoForCast(TBAAAccessInfo SourceInfo, TBAAAccessInfo TargetInfo)
mergeTBAAInfoForCast - Get merged TBAA information for the purposes of type casts.
llvm::Constant * GetAddrOfGlobalVar(const VarDecl *D, llvm::Type *Ty=nullptr, ForDefinition_t IsForDefinition=NotForDefinition)
Return the llvm::Constant for the address of the given global variable.
llvm::MDNode * getTBAATypeInfo(QualType QTy)
getTBAATypeInfo - Get metadata used to describe accesses to objects of the given type.
const TargetCodeGenInfo & getTargetCodeGenInfo()
const CodeGenOptions & getCodeGenOpts() const
StringRef getMangledName(GlobalDecl GD)
CharUnits getNaturalPointeeTypeAlignment(QualType T, LValueBaseInfo *BaseInfo=nullptr, TBAAAccessInfo *TBAAInfo=nullptr)
TBAAAccessInfo mergeTBAAInfoForConditionalOperator(TBAAAccessInfo InfoA, TBAAAccessInfo InfoB)
mergeTBAAInfoForConditionalOperator - Get merged TBAA information for the purposes of conditional ope...
llvm::LLVMContext & getLLVMContext()
llvm::Function * getIntrinsic(unsigned IID, ArrayRef< llvm::Type * > Tys={})
CGObjCRuntime & getObjCRuntime()
Return a reference to the configured Objective-C runtime.
ConstantAddress GetAddrOfGlobalTemporary(const MaterializeTemporaryExpr *E, const Expr *Inner)
Returns a pointer to a global variable representing a temporary with static or thread storage duratio...
llvm::Constant * EmitNullConstant(QualType T)
Return the result of value-initializing the given type, i.e.
LangAS GetGlobalConstantAddressSpace() const
Return the AST address space of constant literal, which is used to emit the constant literal as globa...
void SetLLVMFunctionAttributes(GlobalDecl GD, const CGFunctionInfo &Info, llvm::Function *F, bool IsThunk)
Set the LLVM function attributes (sext, zext, etc).
CharUnits getMinimumObjectSize(QualType Ty)
Returns the minimum object size for an object of the given type.
void SetLLVMFunctionAttributesForDefinition(const Decl *D, llvm::Function *F)
Set the LLVM function attributes which only apply to a function definition.
ConstantAddress GetAddrOfConstantStringFromObjCEncode(const ObjCEncodeExpr *)
Return a pointer to a constant array for the given ObjCEncodeExpr node.
ConstantAddress GetAddrOfConstantCString(const std::string &Str, const char *GlobalName=nullptr)
Returns a pointer to a character array containing the literal and a terminating '\0' character.
void setCurrentStmt(const Stmt *S)
If the execution count for the current statement is known, record that as the current count.
llvm::Type * ConvertType(QualType T)
ConvertType - Convert type T into a llvm::Type.
const CGFunctionInfo & arrangeBuiltinFunctionDeclaration(QualType resultType, const FunctionArgList &args)
A builtin function is a freestanding function using the default C conventions.
const CGRecordLayout & getCGRecordLayout(const RecordDecl *)
getCGRecordLayout - Return record layout info for the given record decl.
llvm::Type * ConvertTypeForMem(QualType T)
ConvertTypeForMem - Convert type T into a llvm::Type.
const llvm::DataLayout & getDataLayout() const
const CGFunctionInfo & arrangeFreeFunctionCall(const CallArgList &Args, const FunctionType *Ty, bool ChainCall)
Figure out the rules for calling a function with the given formal type using the given arguments.
A specialization of Address that requires the address to be an LLVM Constant.
ConstantAddress withElementType(llvm::Type *ElemTy) const
llvm::Constant * getPointer() const
llvm::Constant * emitAbstract(const Expr *E, QualType T)
Emit the result of the given expression as an abstract constant, asserting that it succeeded.
llvm::Constant * tryEmitConstantExpr(const ConstantExpr *CE)
FunctionArgList - Type for representing both the decl and type of parameters to a function.
void mergeForCast(const LValueBaseInfo &Info)
AlignmentSource getAlignmentSource() const
LValue - This represents an lvalue references.
Expr * getBaseIvarExp() const
llvm::Constant * getExtVectorElts() const
static LValue MakeGlobalReg(llvm::Value *V, CharUnits alignment, QualType type)
void setObjCIvar(bool Value)
bool isObjCStrong() const
bool isGlobalObjCRef() const
void setObjCArray(bool Value)
bool isVolatileQualified() const
RValue asAggregateRValue() const
CharUnits getAlignment() const
llvm::Value * getPointer(CodeGenFunction &CGF) const
llvm::Value * getMatrixIdx() const
llvm::Value * getGlobalReg() const
static LValue MakeAddr(Address Addr, QualType type, ASTContext &Context, LValueBaseInfo BaseInfo, TBAAAccessInfo TBAAInfo)
const Qualifiers & getQuals() const
static LValue MakeExtVectorElt(Address Addr, llvm::Constant *Elts, QualType type, LValueBaseInfo BaseInfo, TBAAAccessInfo TBAAInfo)
Address getAddress() const
unsigned getVRQualifiers() const
void setThreadLocalRef(bool Value)
void setGlobalObjCRef(bool Value)
bool isExtVectorElt() const
llvm::Value * getVectorIdx() const
void setNontemporal(bool Value)
LValueBaseInfo getBaseInfo() const
void setARCPreciseLifetime(ARCPreciseLifetime_t value)
const CGBitFieldInfo & getBitFieldInfo() const
bool isThreadLocalRef() const
KnownNonNull_t isKnownNonNull() const
TBAAAccessInfo getTBAAInfo() const
void setNonGC(bool Value)
Address getVectorAddress() const
bool isNontemporal() const
static LValue MakeBitfield(Address Addr, const CGBitFieldInfo &Info, QualType type, LValueBaseInfo BaseInfo, TBAAAccessInfo TBAAInfo)
Create a new object to represent a bit-field access.
static LValue MakeVectorElt(Address vecAddress, llvm::Value *Idx, QualType type, LValueBaseInfo BaseInfo, TBAAAccessInfo TBAAInfo)
void setAddress(Address address)
void setBaseIvarExp(Expr *V)
Address getExtVectorAddress() const
static LValue MakeMatrixElt(Address matAddress, llvm::Value *Idx, QualType type, LValueBaseInfo BaseInfo, TBAAAccessInfo TBAAInfo)
Address getMatrixAddress() const
Address getBitFieldAddress() const
RValue - This trivial value class is used to represent the result of an expression that is evaluated.
static RValue get(llvm::Value *V)
static RValue getAggregate(Address addr, bool isVolatile=false)
Convert an Address to an RValue.
static RValue getComplex(llvm::Value *V1, llvm::Value *V2)
Address getAggregateAddress() const
getAggregateAddr() - Return the Value* of the address of the aggregate.
llvm::Value * getScalarVal() const
getScalarVal() - Return the Value* of this scalar value.
An abstract representation of an aligned address.
RawAddress withElementType(llvm::Type *ElemTy) const
Return address with different element type, but same pointer and alignment.
llvm::Type * getElementType() const
Return the type of the values stored in this address.
llvm::Value * getPointer() const
ReturnValueSlot - Contains the address where the return value of a function can be stored,...
Address performAddrSpaceCast(CodeGen::CodeGenFunction &CGF, Address Addr, LangAS SrcAddr, LangAS DestAddr, llvm::Type *DestTy, bool IsNonNull=false) const
virtual llvm::Constant * getUBSanFunctionSignature(CodeGen::CodeGenModule &CGM) const
Return a constant used by UBSan as a signature to identify functions possessing type information,...
Complex values, per C99 6.2.5p11.
QualType getElementType() const
CompoundLiteralExpr - [C99 6.5.2.5].
ConstStmtVisitor - This class implements a simple visitor for Stmt subclasses.
ConstantExpr - An expression that occurs in a constant context and optionally the result of evaluatin...
Represents a concrete matrix type with constant number of rows and columns.
unsigned getNumRows() const
Returns the number of rows in the matrix.
RecordDecl * getOuterLexicalRecordContext()
Retrieve the outermost lexically enclosing record context.
A reference to a declared variable, function, enum, etc.
bool refersToEnclosingVariableOrCapture() const
Does this DeclRefExpr refer to an enclosing local or a captured variable?
static DeclRefExpr * Create(const ASTContext &Context, NestedNameSpecifierLoc QualifierLoc, SourceLocation TemplateKWLoc, ValueDecl *D, bool RefersToEnclosingVariableOrCapture, SourceLocation NameLoc, QualType T, ExprValueKind VK, NamedDecl *FoundD=nullptr, const TemplateArgumentListInfo *TemplateArgs=nullptr, NonOdrUseReason NOUR=NOUR_None)
SourceLocation getLocation() const
Decl - This represents one declaration (or definition), e.g.
SourceLocation getLocation() const
bool isUsed(bool CheckUsedAttr=true) const
Whether any (re-)declaration of the entity was used, meaning that a definition is required.
DeclContext * getDeclContext()
void ConvertArgToString(ArgumentKind Kind, intptr_t Val, StringRef Modifier, StringRef Argument, ArrayRef< ArgumentValue > PrevArgs, SmallVectorImpl< char > &Output, ArrayRef< intptr_t > QualTypeVals) const
Converts a diagnostic argument (as an intptr_t) into the string that represents it.
bool isFixed() const
Returns true if this is an Objective-C, C++11, or Microsoft-style enumeration with a fixed underlying...
void getValueRange(llvm::APInt &Max, llvm::APInt &Min) const
Calculates the [Min,Max) values the enum can store based on the NumPositiveBits and NumNegativeBits.
A helper class that allows the use of isa/cast/dyncast to detect TagType objects of enums.
EnumDecl * getDecl() const
ExplicitCastExpr - An explicit cast written in the source code.
This represents one expression.
const Expr * skipRValueSubobjectAdjustments(SmallVectorImpl< const Expr * > &CommaLHS, SmallVectorImpl< SubobjectAdjustment > &Adjustments) const
Walk outwards from an expression we want to bind a reference to and find the expression whose lifetim...
Expr * IgnoreParenNoopCasts(const ASTContext &Ctx) LLVM_READONLY
Skip past any parentheses and casts which do not change the value (including ptr->int casts of the sa...
ExprValueKind getValueKind() const
getValueKind - The value kind that this expression produces.
Expr * IgnoreParenImpCasts() LLVM_READONLY
Skip past any parentheses and implicit casts which might surround this expression until reaching a fi...
Expr * IgnoreImplicit() LLVM_READONLY
Skip past any implicit AST nodes which might surround this expression until reaching a fixed point.
Expr * IgnoreParens() LLVM_READONLY
Skip past any parentheses which might surround this expression until reaching a fixed point.
bool EvaluateAsLValue(EvalResult &Result, const ASTContext &Ctx, bool InConstantContext=false) const
EvaluateAsLValue - Evaluate an expression to see if we can fold it to an lvalue with link time known ...
bool isLValue() const
isLValue - True if this expression is an "l-value" according to the rules of the current language.
bool EvaluateAsRValue(EvalResult &Result, const ASTContext &Ctx, bool InConstantContext=false) const
EvaluateAsRValue - Return true if this is a constant which we can fold to an rvalue using any crazy t...
Decl * getReferencedDeclOfCallee()
bool HasSideEffects(const ASTContext &Ctx, bool IncludePossibleEffects=true) const
HasSideEffects - This routine returns true for all those expressions which have any effect other than...
Expr * IgnoreImpCasts() LLVM_READONLY
Skip past any implicit casts which might surround this expression until reaching a fixed point.
SourceLocation getExprLoc() const LLVM_READONLY
getExprLoc - Return the preferred location for the arrow when diagnosing a problem with a generic exp...
bool refersToBitField() const
Returns true if this expression is a gl-value that potentially refers to a bit-field.
bool isFlexibleArrayMemberLike(ASTContext &Context, LangOptions::StrictFlexArraysLevelKind StrictFlexArraysLevel, bool IgnoreTemplateOrMacroSubstitution=false) const
Check whether this array fits the idiom of a flexible array member, depending on the value of -fstric...
bool isOBJCGCCandidate(ASTContext &Ctx) const
isOBJCGCCandidate - Return true if this expression may be used in a read/ write barrier.
ExtVectorElementExpr - This represents access to specific elements of a vector, and may occur on the ...
Represents a member of a struct/union/class.
bool isBitField() const
Determines whether this field is a bitfield.
unsigned getFieldIndex() const
Returns the index of this field within its record, as appropriate for passing to ASTRecordLayout::get...
const RecordDecl * getParent() const
Returns the parent of this field declaration, which is the struct in which this field is defined.
const FieldDecl * findCountedByField() const
Find the FieldDecl specified in a FAM's "counted_by" attribute.
FullExpr - Represents a "full-expression" node.
const Expr * getSubExpr() const
Represents a function declaration or definition.
unsigned getBuiltinID(bool ConsiderWrapperFunctions=false) const
Returns a value indicating whether this function corresponds to a builtin function.
Represents a prototype with parameter type info, e.g.
GlobalDecl - represents a global declaration.
const Decl * getDecl() const
This class represents temporary values used to represent inout and out arguments in HLSL.
Describes an C or C++ initializer list.
StrictFlexArraysLevelKind
SanitizerSet Sanitize
Set of enabled sanitizers.
virtual void mangleCXXRTTI(QualType T, raw_ostream &)=0
unsigned getBlockId(const BlockDecl *BD, bool Local)
Represents a prvalue temporary that is written into memory so that a reference can bind to it.
StorageDuration getStorageDuration() const
Retrieve the storage duration for the materialized temporary.
Expr * getSubExpr() const
Retrieve the temporary-generating subexpression whose value will be materialized into a glvalue.
ValueDecl * getExtendingDecl()
Get the declaration which triggered the lifetime-extension of this temporary, if any.
MatrixSubscriptExpr - Matrix subscript expression for the MatrixType extension.
MemberExpr - [C99 6.5.2.3] Structure and Union Members.
ValueDecl * getMemberDecl() const
Retrieve the member declaration to which this expression refers.
NonOdrUseReason isNonOdrUse() const
Is this expression a non-odr-use reference, and if so, why? This is only meaningful if the named memb...
SourceLocation getExprLoc() const LLVM_READONLY
A pointer to member type per C++ 8.3.3 - Pointers to members.
bool isObjCBOOLType(QualType T) const
Returns true if.
This represents a decl that may have a name.
StringRef getName() const
Get the name of identifier for this declaration as a StringRef.
A C++ nested-name-specifier augmented with source location information.
bool containsType(SanitizerMask Mask, StringRef MangledTypeName, StringRef Category=StringRef()) const
ObjCEncodeExpr, used for @encode in Objective-C.
Represents an ObjC class declaration.
ObjCIvarDecl - Represents an ObjC instance variable.
ObjCIvarRefExpr - A reference to an ObjC instance variable.
An expression that sends a message to the given Objective-C object or class.
Represents a class type in Objective C.
ObjCSelectorExpr used for @selector in Objective-C.
OpaqueValueExpr - An expression referring to an opaque object of a fixed type and value class.
Expr * getSourceExpr() const
The source expression of an opaque value expression is the expression which originally generated the ...
ParenExpr - This represents a parenthesized expression, e.g.
PointerType - C99 6.7.5.1 - Pointer Declarators.
QualType getPointeeType() const
[C99 6.4.2.2] - A predefined identifier such as func.
StringRef getIdentKindName() const
Represents an unpacked "presumed" location which can be presented to the user.
unsigned getColumn() const
Return the presumed column number of this location.
const char * getFilename() const
Return the presumed filename of this location.
unsigned getLine() const
Return the presumed line number of this location.
PseudoObjectExpr - An expression which accesses a pseudo-object l-value.
const Expr *const * const_semantics_iterator
A (possibly-)qualified type.
bool isVolatileQualified() const
Determine whether this type is volatile-qualified.
bool isNull() const
Return true if this QualType doesn't point to a type yet.
LangAS getAddressSpace() const
Return the address space of this type.
Qualifiers getQualifiers() const
Retrieve the set of qualifiers applied to this type.
Qualifiers::ObjCLifetime getObjCLifetime() const
Returns lifetime attribute of this type.
QualType getUnqualifiedType() const
Retrieve the unqualified variant of the given type, removing as little sugar as possible.
QualType withCVRQualifiers(unsigned CVR) const
DestructionKind isDestructedType() const
Returns a nonzero value if objects of this type require non-trivial work to clean up after.
bool isConstantStorage(const ASTContext &Ctx, bool ExcludeCtor, bool ExcludeDtor)
The collection of all-type qualifiers we support.
unsigned getCVRQualifiers() const
@ OCL_Strong
Assigning into this object requires the old value to be released and the new value to be retained.
@ OCL_ExplicitNone
This object can be modified without requiring retains or releases.
@ OCL_None
There is no lifetime qualification on this type.
@ OCL_Weak
Reading or writing from this object requires a barrier call.
@ OCL_Autoreleasing
Assigning into this object requires a lifetime extension.
void addCVRQualifiers(unsigned mask)
void addQualifiers(Qualifiers Q)
Add the qualifiers from the given set to this set.
void setAddressSpace(LangAS space)
ObjCLifetime getObjCLifetime() const
Represents a struct/union/class.
field_range fields() const
RecordDecl * getDefinition() const
Returns the RecordDecl that actually defines this struct/union/class.
A helper class that allows the use of isa/cast/dyncast to detect TagType objects of structs/unions/cl...
decl_type * getPreviousDecl()
Return the previous declaration of this declaration or NULL if this is the first declaration.
Scope - A scope is a transient data structure that is used while parsing the program.
Encodes a location in the source.
PresumedLoc getPresumedLoc(SourceLocation Loc, bool UseLineDirectives=true) const
Returns the "presumed" location of a SourceLocation specifies.
StmtExpr - This is the GNU Statement Expression extension: ({int X=4; X;}).
Stmt - This represents one statement.
StmtClass getStmtClass() const
SourceLocation getBeginLoc() const LLVM_READONLY
StringLiteral - This represents a string literal expression, e.g.
Exposes information about the current target.
const llvm::Triple & getTriple() const
Returns the target triple of the primary target.
virtual StringRef getABI() const
Get the ABI currently in use.
const Type * getTypeForDecl() const
The base class of the type hierarchy.
CXXRecordDecl * getAsCXXRecordDecl() const
Retrieves the CXXRecordDecl that this type refers to, either because the type is a RecordType or beca...
bool isBlockPointerType() const
bool isBooleanType() const
bool isSignedIntegerOrEnumerationType() const
Determines whether this is an integer type that is signed or an enumeration types whose underlying ty...
bool hasAttr(attr::Kind AK) const
Determine whether this type had the specified attribute applied to it (looking through top-level type...
bool isSignedIntegerType() const
Return true if this is an integer type that is signed, according to C99 6.2.5p4 [char,...
const ArrayType * castAsArrayTypeUnsafe() const
A variant of castAs<> for array type which silently discards qualifiers from the outermost type.
bool isConstantArrayType() const
bool isFunctionPointerType() const
bool isCountAttributedType() const
bool isArithmeticType() const
bool isConstantMatrixType() const
bool isPointerType() const
bool isIntegerType() const
isIntegerType() does not include complex integers (a GCC extension).
const T * castAs() const
Member-template castAs<specific type>.
bool isReferenceType() const
bool isVariableArrayType() const
QualType getPointeeType() const
If this is a pointer, ObjC object pointer, or block pointer, this returns the respective pointee.
bool isExtVectorBoolType() const
bool isBitIntType() const
bool isAnyComplexType() const
const Type * getBaseElementTypeUnsafe() const
Get the base element type of this type, potentially discarding type qualifiers.
bool isAtomicType() const
bool isVariablyModifiedType() const
Whether this type is a variably-modified type (C99 6.7.5).
bool isIncompleteType(NamedDecl **Def=nullptr) const
Types are partitioned into 3 broad categories (C99 6.2.5p1): object types, function types,...
bool isFunctionType() const
bool isObjCObjectPointerType() const
bool isVectorType() const
bool isFloatingType() const
bool isSubscriptableVectorType() const
const T * getAs() const
Member-template getAs<specific type>'.
const Type * getUnqualifiedDesugaredType() const
Return the specified type with any "sugar" removed from the type, removing any typedefs,...
bool isRecordType() const
RecordDecl * getAsRecordDecl() const
Retrieves the RecordDecl this type refers to.
UnaryOperator - This represents the unary-expression's (except sizeof and alignof),...
Represents a call to the builtin function __builtin_va_arg.
Represent the declaration of a variable (in which case it is an lvalue) a function (in which case it ...
Represents a variable declaration or definition.
TLSKind getTLSKind() const
VarDecl * getDefinition(ASTContext &)
Get the real (not just tentative) definition for this declaration.
bool hasLocalStorage() const
Returns true if a variable with function scope is a non-static local variable.
@ TLS_Dynamic
TLS with a dynamic initializer.
@ TLS_None
Not a TLS variable.
Represents a C array with a specified size that is not an integer-constant-expression.
Represents a GCC generic vector type.
unsigned getNumElements() const
AlignmentSource
The source of the alignment of an l-value; an expression of confidence in the alignment actually matc...
@ Decl
The l-value was an access to a declared entity or something equivalently strong, like the address of ...
bool isEmptyFieldForLayout(const ASTContext &Context, const FieldDecl *FD)
isEmptyFieldForLayout - Return true iff the field is "empty", that is, either a zero-width bit-field ...
@ EHCleanup
Denotes a cleanup that should run when a scope is exited using exceptional control flow (a throw stat...
static AlignmentSource getFieldAlignmentSource(AlignmentSource Source)
Given that the base address has the given alignment source, what's our confidence in the alignment of...
const internal::VariadicAllOfMatcher< Type > type
Matches Types in the clang AST.
const AstTypeMatcher< ArrayType > arrayType
Matches all kinds of arrays.
const internal::VariadicDynCastAllOfMatcher< Stmt, Expr > expr
Matches expressions.
const AstTypeMatcher< FunctionType > functionType
Matches FunctionType nodes.
constexpr Variable var(Literal L)
Returns the variable of L.
const void * Store
Store - This opaque type encapsulates an immutable mapping from locations to values.
bool This(InterpState &S, CodePtr OpPC)
bool Zero(InterpState &S, CodePtr OpPC)
bool IsNonNull(InterpState &S, CodePtr OpPC)
bool Load(InterpState &S, CodePtr OpPC)
bool Cast(InterpState &S, CodePtr OpPC)
The JSON file list parser is used to communicate input to InstallAPI.
@ OK_BitField
A bitfield object is a bitfield on a C or C++ record.
@ Asm
Assembly: we accept this only so that we can preprocess it.
StorageDuration
The storage duration for an object (per C++ [basic.stc]).
@ SD_Thread
Thread storage duration.
@ SD_Static
Static storage duration.
@ SD_FullExpression
Full-expression storage duration (for temporaries).
@ SD_Automatic
Automatic storage duration (most local variables).
@ SD_Dynamic
Dynamic storage duration.
@ Result
The result type of a method or function.
@ Dtor_Complete
Complete object dtor.
llvm::cl::opt< bool > ClSanitizeGuardChecks
const FunctionProtoType * T
LangAS getLangASFromTargetAS(unsigned TargetAS)
@ Interface
The "__interface" keyword introduces the elaborated-type-specifier.
bool isLambdaMethod(const DeclContext *DC)
@ Other
Other implicit parameter.
@ NOUR_Unevaluated
This name appears in an unevaluated operand.
@ NOUR_Constant
This name appears as a potential result of an lvalue-to-rvalue conversion that is a constant expressi...
__INTPTR_TYPE__ intptr_t
A signed integer type with the property that any valid pointer to void can be converted to this type,...
Structure with information about how a bitfield should be accessed.
CharUnits VolatileStorageOffset
The offset of the bitfield storage from the start of the struct.
unsigned VolatileOffset
The offset within a contiguous run of bitfields that are represented as a single "field" within the L...
unsigned Offset
The offset within a contiguous run of bitfields that are represented as a single "field" within the L...
unsigned VolatileStorageSize
The storage size in bits which should be used when accessing this bitfield.
unsigned Size
The total size of the bit-field, in bits.
unsigned StorageSize
The storage size in bits which should be used when accessing this bitfield.
unsigned IsSigned
Whether the bit-field is signed.
static Address getAddrOfThreadPrivate(CodeGenFunction &CGF, const VarDecl *VD, Address VDAddr, SourceLocation Loc)
Returns address of the threadprivate variable for the current thread.
llvm::PointerType * VoidPtrTy
llvm::IntegerType * Int64Ty
CharUnits getIntAlign() const
llvm::IntegerType * Int8Ty
i8, i16, i32, and i64
unsigned char PointerWidthInBits
The width of a pointer into the generic address space.
llvm::IntegerType * SizeTy
llvm::IntegerType * Int32Ty
llvm::IntegerType * IntPtrTy
llvm::PointerType * Int8PtrTy
llvm::PointerType * UnqualPtrTy
CharUnits getPointerAlign() const
LangAS getASTAllocaAddressSpace() const
llvm::MDNode * AccessType
AccessType - The final access type.
uint64_t Offset
Offset - The byte offset of the final access within the base one.
static TBAAAccessInfo getMayAliasInfo()
uint64_t Size
Size - The size of access, in bytes.
llvm::MDNode * BaseType
BaseType - The base/leading access type.
EvalResult is a struct with detailed info about an evaluated expression.
APValue Val
Val - This is the value the expression can be folded to.
bool HasSideEffects
Whether the evaluated expression has side effects.
PointerAuthSchema FunctionPointers
The ABI for C function pointers.
void set(SanitizerMask K, bool Value)
Enable or disable a certain (single) sanitizer.
bool has(SanitizerMask K) const
Check if a certain (single) sanitizer is enabled.
An adjustment to be made to the temporary created when emitting a reference binding,...
@ DerivedToBaseAdjustment
@ MemberPointerAdjustment