36#include "llvm/Analysis/ConstantFolding.h"
37#include "llvm/Analysis/ValueTracking.h"
38#include "llvm/IR/DataLayout.h"
39#include "llvm/IR/GlobalVariable.h"
40#include "llvm/IR/Instructions.h"
41#include "llvm/IR/Intrinsics.h"
42#include "llvm/IR/Type.h"
46using namespace CodeGen;
49 "Clang max alignment greater than what LLVM supports?");
51void CodeGenFunction::EmitDecl(
const Decl &
D) {
53 case Decl::BuiltinTemplate:
54 case Decl::TranslationUnit:
55 case Decl::ExternCContext:
57 case Decl::UnresolvedUsingTypename:
58 case Decl::ClassTemplateSpecialization:
59 case Decl::ClassTemplatePartialSpecialization:
60 case Decl::VarTemplateSpecialization:
61 case Decl::VarTemplatePartialSpecialization:
62 case Decl::TemplateTypeParm:
63 case Decl::UnresolvedUsingValue:
64 case Decl::NonTypeTemplateParm:
65 case Decl::CXXDeductionGuide:
67 case Decl::CXXConstructor:
68 case Decl::CXXDestructor:
69 case Decl::CXXConversion:
71 case Decl::MSProperty:
72 case Decl::IndirectField:
74 case Decl::ObjCAtDefsField:
76 case Decl::ImplicitParam:
77 case Decl::ClassTemplate:
78 case Decl::VarTemplate:
79 case Decl::FunctionTemplate:
80 case Decl::TypeAliasTemplate:
81 case Decl::TemplateTemplateParm:
82 case Decl::ObjCMethod:
83 case Decl::ObjCCategory:
84 case Decl::ObjCProtocol:
85 case Decl::ObjCInterface:
86 case Decl::ObjCCategoryImpl:
87 case Decl::ObjCImplementation:
88 case Decl::ObjCProperty:
89 case Decl::ObjCCompatibleAlias:
90 case Decl::PragmaComment:
91 case Decl::PragmaDetectMismatch:
92 case Decl::AccessSpec:
93 case Decl::LinkageSpec:
95 case Decl::ObjCPropertyImpl:
96 case Decl::FileScopeAsm:
97 case Decl::TopLevelStmt:
99 case Decl::FriendTemplate:
102 case Decl::UsingShadow:
103 case Decl::ConstructorUsingShadow:
104 case Decl::ObjCTypeParam:
106 case Decl::UnresolvedUsingIfExists:
107 case Decl::HLSLBuffer:
108 llvm_unreachable(
"Declaration should not be in declstmts!");
110 case Decl::CXXRecord:
118 DI->EmitAndRetainType(
getContext().getEnumType(cast<EnumDecl>(&
D)));
121 case Decl::EnumConstant:
122 case Decl::StaticAssert:
126 case Decl::UnnamedGlobalConstant:
127 case Decl::TemplateParamObject:
128 case Decl::OMPThreadPrivate:
129 case Decl::OMPAllocate:
130 case Decl::OMPCapturedExpr:
131 case Decl::OMPRequires:
134 case Decl::ImplicitConceptSpecialization:
135 case Decl::LifetimeExtendedTemporary:
136 case Decl::RequiresExprBody:
140 case Decl::NamespaceAlias:
142 DI->EmitNamespaceAlias(cast<NamespaceAliasDecl>(
D));
146 DI->EmitUsingDecl(cast<UsingDecl>(
D));
148 case Decl::UsingEnum:
150 DI->EmitUsingEnumDecl(cast<UsingEnumDecl>(
D));
152 case Decl::UsingPack:
153 for (
auto *Using : cast<UsingPackDecl>(
D).expansions())
156 case Decl::UsingDirective:
158 DI->EmitUsingDirective(cast<UsingDirectiveDecl>(
D));
161 case Decl::Decomposition: {
162 const VarDecl &VD = cast<VarDecl>(
D);
164 "Should not see file-scope variables inside a function!");
166 if (
auto *DD = dyn_cast<DecompositionDecl>(&VD))
167 for (
auto *B : DD->bindings())
168 if (
auto *HD = B->getHoldingVar())
173 case Decl::OMPDeclareReduction:
176 case Decl::OMPDeclareMapper:
180 case Decl::TypeAlias: {
181 QualType Ty = cast<TypedefNameDecl>(
D).getUnderlyingType();
183 DI->EmitAndRetainType(Ty);
194 if (
D.hasExternalStorage())
203 if (
D.getType()->isSamplerT())
206 llvm::GlobalValue::LinkageTypes
Linkage =
219 assert(
D.hasLocalStorage());
228 assert(!
D.isExternallyVisible() &&
"name shouldn't matter");
229 std::string ContextName;
231 if (
auto *CD = dyn_cast<CapturedDecl>(DC))
232 DC = cast<DeclContext>(CD->getNonClosureContext());
233 if (
const auto *FD = dyn_cast<FunctionDecl>(DC))
235 else if (
const auto *BD = dyn_cast<BlockDecl>(DC))
237 else if (
const auto *OMD = dyn_cast<ObjCMethodDecl>(DC))
238 ContextName = OMD->getSelector().getAsString();
240 llvm_unreachable(
"Unknown context for static var decl");
242 ContextName +=
"." +
D.getNameAsString();
252 if (llvm::Constant *ExistingGV = StaticLocalDeclMap[&
D])
271 llvm::Constant *
Init =
nullptr;
274 Init = llvm::UndefValue::get(LTy);
278 llvm::GlobalVariable *GV =
new llvm::GlobalVariable(
280 nullptr, llvm::GlobalVariable::NotThreadLocal, TargetAS);
281 GV->setAlignment(
getContext().getDeclAlign(&
D).getAsAlign());
284 GV->setComdat(TheModule.getOrInsertComdat(GV->getName()));
294 llvm::Constant *Addr = GV;
295 if (AS != ExpectedAS) {
297 *
this, GV, AS, ExpectedAS,
299 getContext().getTargetAddressSpace(ExpectedAS)));
310 if (isa<BlockDecl>(DC) || isa<CapturedDecl>(DC)) {
318 if (
const auto *CD = dyn_cast<CXXConstructorDecl>(DC))
320 else if (
const auto *DD = dyn_cast<CXXDestructorDecl>(DC))
322 else if (
const auto *FD = dyn_cast<FunctionDecl>(DC))
327 assert(isa<ObjCMethodDecl>(DC) &&
"unexpected parent code decl");
342llvm::GlobalVariable *
344 llvm::GlobalVariable *GV) {
346 llvm::Constant *
Init = emitter.tryEmitForInitializer(
D);
358 GV->setConstant(
false);
370 assert(VarSize == CstSize &&
"Emitted constant has unexpected size");
377 if (GV->getValueType() !=
Init->getType()) {
378 llvm::GlobalVariable *OldGV = GV;
380 GV =
new llvm::GlobalVariable(
382 OldGV->getLinkage(),
Init,
"",
383 OldGV, OldGV->getThreadLocalMode(),
384 OldGV->getType()->getPointerAddressSpace());
385 GV->setVisibility(OldGV->getVisibility());
386 GV->setDSOLocal(OldGV->isDSOLocal());
387 GV->setComdat(OldGV->getComdat());
393 OldGV->replaceAllUsesWith(GV);
396 OldGV->eraseFromParent();
403 D.getType().isConstantStorage(
getContext(),
true, !NeedsDtor));
404 GV->setInitializer(
Init);
406 emitter.finalize(GV);
419 llvm::GlobalValue::LinkageTypes
Linkage) {
429 setAddrOfLocalVar(&
D,
Address(addr, elemTy, alignment));
434 if (
D.getType()->isVariablyModifiedType())
438 llvm::Type *expectedType = addr->getType();
440 llvm::GlobalVariable *
var =
441 cast<llvm::GlobalVariable>(addr->stripPointerCasts());
450 if (
D.getInit() && !isCudaSharedVar)
458 if (
auto *SA =
D.
getAttr<PragmaClangBSSSectionAttr>())
459 var->addAttribute(
"bss-section", SA->getName());
460 if (
auto *SA =
D.
getAttr<PragmaClangDataSectionAttr>())
461 var->addAttribute(
"data-section", SA->getName());
462 if (
auto *SA =
D.
getAttr<PragmaClangRodataSectionAttr>())
463 var->addAttribute(
"rodata-section", SA->getName());
464 if (
auto *SA =
D.
getAttr<PragmaClangRelroSectionAttr>())
465 var->addAttribute(
"relro-section", SA->getName());
467 if (
const SectionAttr *SA =
D.
getAttr<SectionAttr>())
468 var->setSection(SA->getName());
483 llvm::Constant *castedAddr =
484 llvm::ConstantExpr::getPointerBitCastOrAddrSpaceCast(var, expectedType);
485 LocalDeclMap.find(&
D)->second =
Address(castedAddr, elemTy, alignment);
501 CodeGenFunction::Destroyer *destroyer,
502 bool useEHCleanupForArray)
503 : addr(addr),
type(
type), destroyer(destroyer),
504 useEHCleanupForArray(useEHCleanupForArray) {}
508 CodeGenFunction::Destroyer *destroyer;
509 bool useEHCleanupForArray;
513 bool useEHCleanupForArray =
514 flags.isForNormalCleanup() && this->useEHCleanupForArray;
520 template <
class Derived>
523 : NRVOFlag(NRVOFlag),
Loc(addr), Ty(
type) {}
525 llvm::Value *NRVOFlag;
531 bool NRVO = flags.isForNormalCleanup() && NRVOFlag;
533 llvm::BasicBlock *SkipDtorBB =
nullptr;
538 llvm::Value *DidNRVO =
540 CGF.
Builder.CreateCondBr(DidNRVO, SkipDtorBB, RunDtorBB);
544 static_cast<Derived *
>(
this)->emitDestructorCall(CGF);
549 virtual ~DestroyNRVOVariable() =
default;
552 struct DestroyNRVOVariableCXX final
553 : DestroyNRVOVariable<DestroyNRVOVariableCXX> {
556 : DestroyNRVOVariable<DestroyNRVOVariableCXX>(addr,
type, NRVOFlag),
568 struct DestroyNRVOVariableC final
569 : DestroyNRVOVariable<DestroyNRVOVariableC> {
571 : DestroyNRVOVariable<DestroyNRVOVariableC>(addr, Ty, NRVOFlag) {}
580 CallStackRestore(
Address Stack) : Stack(Stack) {}
581 bool isRedundantBeforeReturn()
override {
return true; }
589 std::pair<llvm::Value *, llvm::Value *> AddrSizePair;
590 KmpcAllocFree(
const std::pair<llvm::Value *, llvm::Value *> &AddrSizePair)
591 : AddrSizePair(AddrSizePair) {}
600 ExtendGCLifetime(
const VarDecl *var) : Var(*
var) {}
614 llvm::Constant *CleanupFn;
618 CallCleanupFunction(llvm::Constant *CleanupFn,
const CGFunctionInfo *Info,
620 : CleanupFn(CleanupFn), FnInfo(*Info), Var(*Var) {}
655 llvm_unreachable(
"present but none");
663 (var.hasAttr<ObjCPreciseLifetimeAttr>()
668 CGF.
pushDestroy(cleanupKind, addr, var.getType(), destroyer,
687 if (
const Expr *e = dyn_cast<Expr>(
s)) {
690 s = e = e->IgnoreParenCasts();
692 if (
const DeclRefExpr *ref = dyn_cast<DeclRefExpr>(e))
693 return (ref->getDecl() == &var);
694 if (
const BlockExpr *be = dyn_cast<BlockExpr>(e)) {
695 const BlockDecl *block = be->getBlockDecl();
696 for (
const auto &I : block->
captures()) {
697 if (I.getVariable() == &var)
703 for (
const Stmt *SubStmt :
s->children())
712 if (!
decl)
return false;
713 if (!isa<VarDecl>(
decl))
return false;
720 bool needsCast =
false;
727 case CK_BlockPointerToObjCPointerCast:
733 case CK_LValueToRValue: {
775 if (!
SanOpts.
has(SanitizerKind::NullabilityAssign))
784 SanitizerScope SanScope(
this);
786 llvm::Constant *StaticData[] = {
788 llvm::ConstantInt::get(
Int8Ty, 0),
791 SanitizerHandler::TypeMismatch, StaticData, RHS);
795 LValue lvalue,
bool capturedByInit) {
807 init = DIE->getExpr();
811 if (
auto *EWC = dyn_cast<ExprWithCleanups>(init)) {
812 CodeGenFunction::RunCleanupsScope
Scope(*
this);
820 bool accessedByInit =
false;
823 if (accessedByInit) {
826 if (capturedByInit) {
847 llvm::Value *value =
nullptr;
851 llvm_unreachable(
"present but none");
854 if (!
D || !isa<VarDecl>(
D) || !cast<VarDecl>(
D)->isARCPseudoStrong()) {
913 unsigned &NumStores) {
915 if (isa<llvm::ConstantAggregateZero>(
Init) ||
916 isa<llvm::ConstantPointerNull>(
Init) ||
917 isa<llvm::UndefValue>(
Init))
919 if (isa<llvm::ConstantInt>(
Init) || isa<llvm::ConstantFP>(
Init) ||
920 isa<llvm::ConstantVector>(
Init) || isa<llvm::BlockAddress>(
Init) ||
921 isa<llvm::ConstantExpr>(
Init))
922 return Init->isNullValue() || NumStores--;
925 if (isa<llvm::ConstantArray>(
Init) || isa<llvm::ConstantStruct>(
Init)) {
926 for (
unsigned i = 0, e =
Init->getNumOperands(); i != e; ++i) {
927 llvm::Constant *Elt = cast<llvm::Constant>(
Init->getOperand(i));
934 if (llvm::ConstantDataSequential *CDS =
935 dyn_cast<llvm::ConstantDataSequential>(
Init)) {
936 for (
unsigned i = 0, e = CDS->getNumElements(); i != e; ++i) {
937 llvm::Constant *Elt = CDS->getElementAsConstant(i);
954 assert(!
Init->isNullValue() && !isa<llvm::UndefValue>(
Init) &&
955 "called emitStoresForInitAfterBZero for zero or undef value.");
957 if (isa<llvm::ConstantInt>(
Init) || isa<llvm::ConstantFP>(
Init) ||
958 isa<llvm::ConstantVector>(
Init) || isa<llvm::BlockAddress>(
Init) ||
959 isa<llvm::ConstantExpr>(
Init)) {
960 auto *I = Builder.CreateStore(
Init,
Loc, isVolatile);
962 I->addAnnotationMetadata(
"auto-init");
966 if (llvm::ConstantDataSequential *CDS =
967 dyn_cast<llvm::ConstantDataSequential>(
Init)) {
968 for (
unsigned i = 0, e = CDS->getNumElements(); i != e; ++i) {
969 llvm::Constant *Elt = CDS->getElementAsConstant(i);
972 if (!Elt->isNullValue() && !isa<llvm::UndefValue>(Elt))
974 CGM, Elt, Builder.CreateConstInBoundsGEP2_32(
Loc, 0, i), isVolatile,
975 Builder, IsAutoInit);
980 assert((isa<llvm::ConstantStruct>(
Init) || isa<llvm::ConstantArray>(
Init)) &&
981 "Unknown value type!");
983 for (
unsigned i = 0, e =
Init->getNumOperands(); i != e; ++i) {
984 llvm::Constant *Elt = cast<llvm::Constant>(
Init->getOperand(i));
987 if (!Elt->isNullValue() && !isa<llvm::UndefValue>(Elt))
989 Builder.CreateConstInBoundsGEP2_32(
Loc, 0, i),
990 isVolatile, Builder, IsAutoInit);
998 uint64_t GlobalSize) {
1000 if (isa<llvm::ConstantAggregateZero>(
Init))
return true;
1006 unsigned StoreBudget = 6;
1007 uint64_t SizeLimit = 32;
1009 return GlobalSize > SizeLimit &&
1019 uint64_t GlobalSize,
1020 const llvm::DataLayout &DL) {
1021 uint64_t SizeLimit = 32;
1022 if (GlobalSize <= SizeLimit)
1024 return llvm::isBytewiseValue(
Init, DL);
1031 uint64_t GlobalByteSize) {
1033 uint64_t ByteSizeLimit = 64;
1036 if (GlobalByteSize <= ByteSizeLimit)
1046 if (isPattern == IsPattern::Yes)
1049 return llvm::Constant::getNullValue(Ty);
1053 llvm::Constant *constant);
1058 llvm::StructType *STy,
1059 llvm::Constant *constant) {
1061 const llvm::StructLayout *Layout = DL.getStructLayout(STy);
1062 llvm::Type *Int8Ty = llvm::IntegerType::getInt8Ty(CGM.
getLLVMContext());
1063 unsigned SizeSoFar = 0;
1065 bool NestedIntact =
true;
1066 for (
unsigned i = 0, e = STy->getNumElements(); i != e; i++) {
1067 unsigned CurOff = Layout->getElementOffset(i);
1068 if (SizeSoFar < CurOff) {
1069 assert(!STy->isPacked());
1070 auto *PadTy = llvm::ArrayType::get(Int8Ty, CurOff - SizeSoFar);
1073 llvm::Constant *CurOp;
1074 if (constant->isZeroValue())
1075 CurOp = llvm::Constant::getNullValue(STy->getElementType(i));
1077 CurOp = cast<llvm::Constant>(constant->getAggregateElement(i));
1080 NestedIntact =
false;
1081 Values.push_back(NewOp);
1082 SizeSoFar = CurOff + DL.getTypeAllocSize(CurOp->getType());
1084 unsigned TotalSize = Layout->getSizeInBytes();
1085 if (SizeSoFar < TotalSize) {
1086 auto *PadTy = llvm::ArrayType::get(Int8Ty, TotalSize - SizeSoFar);
1089 if (NestedIntact && Values.size() == STy->getNumElements())
1091 return llvm::ConstantStruct::getAnon(Values, STy->isPacked());
1097 llvm::Constant *constant) {
1098 llvm::Type *OrigTy = constant->getType();
1099 if (
const auto STy = dyn_cast<llvm::StructType>(OrigTy))
1101 if (
auto *ArrayTy = dyn_cast<llvm::ArrayType>(OrigTy)) {
1103 uint64_t Size = ArrayTy->getNumElements();
1106 llvm::Type *ElemTy = ArrayTy->getElementType();
1107 bool ZeroInitializer = constant->isNullValue();
1108 llvm::Constant *OpValue, *PaddedOp;
1109 if (ZeroInitializer) {
1110 OpValue = llvm::Constant::getNullValue(ElemTy);
1113 for (
unsigned Op = 0; Op != Size; ++Op) {
1114 if (!ZeroInitializer) {
1115 OpValue = constant->getAggregateElement(Op);
1118 Values.push_back(PaddedOp);
1120 auto *NewElemTy = Values[0]->getType();
1121 if (NewElemTy == ElemTy)
1123 auto *NewArrayTy = llvm::ArrayType::get(NewElemTy, Size);
1124 return llvm::ConstantArray::get(NewArrayTy, Values);
1133 llvm::Constant *Constant,
1135 auto FunctionName = [&](
const DeclContext *DC) -> std::string {
1136 if (
const auto *FD = dyn_cast<FunctionDecl>(DC)) {
1137 if (
const auto *CC = dyn_cast<CXXConstructorDecl>(FD))
1138 return CC->getNameAsString();
1139 if (
const auto *CD = dyn_cast<CXXDestructorDecl>(FD))
1140 return CD->getNameAsString();
1142 }
else if (
const auto *OM = dyn_cast<ObjCMethodDecl>(DC)) {
1143 return OM->getNameAsString();
1144 }
else if (isa<BlockDecl>(DC)) {
1146 }
else if (isa<CapturedDecl>(DC)) {
1147 return "<captured>";
1149 llvm_unreachable(
"expected a function or method");
1155 llvm::GlobalVariable *&CacheEntry = InitializerConstants[&
D];
1156 if (!CacheEntry || CacheEntry->getInitializer() != Constant) {
1157 auto *Ty = Constant->getType();
1158 bool isConstant =
true;
1159 llvm::GlobalVariable *InsertBefore =
nullptr;
1163 if (
D.hasGlobalStorage())
1166 Name = (
"__const." + FunctionName(DC) +
"." +
D.getName()).str();
1168 llvm_unreachable(
"local variable has no parent function or method");
1169 llvm::GlobalVariable *GV =
new llvm::GlobalVariable(
1170 getModule(), Ty, isConstant, llvm::GlobalValue::PrivateLinkage,
1171 Constant, Name, InsertBefore, llvm::GlobalValue::NotThreadLocal, AS);
1173 GV->setUnnamedAddr(llvm::GlobalValue::UnnamedAddr::Global);
1175 }
else if (CacheEntry->getAlignment() < uint64_t(Align.
getQuantity())) {
1176 CacheEntry->setAlignment(Align.
getAsAlign());
1179 return Address(CacheEntry, CacheEntry->getValueType(), Align);
1185 llvm::Constant *Constant,
1194 llvm::Constant *constant,
bool IsAutoInit) {
1195 auto *Ty = constant->getType();
1196 uint64_t ConstantSize = CGM.
getDataLayout().getTypeAllocSize(Ty);
1200 bool canDoSingleStore = Ty->isIntOrIntVectorTy() ||
1201 Ty->isPtrOrPtrVectorTy() || Ty->isFPOrFPVectorTy();
1202 if (canDoSingleStore) {
1203 auto *I = Builder.CreateStore(constant,
Loc, isVolatile);
1205 I->addAnnotationMetadata(
"auto-init");
1209 auto *SizeVal = llvm::ConstantInt::get(CGM.
IntPtrTy, ConstantSize);
1214 auto *I = Builder.CreateMemSet(
Loc, llvm::ConstantInt::get(CGM.
Int8Ty, 0),
1215 SizeVal, isVolatile);
1217 I->addAnnotationMetadata(
"auto-init");
1219 bool valueAlreadyCorrect =
1220 constant->isNullValue() || isa<llvm::UndefValue>(constant);
1221 if (!valueAlreadyCorrect) {
1222 Loc =
Loc.withElementType(Ty);
1230 llvm::Value *Pattern =
1233 uint64_t
Value = 0x00;
1234 if (!isa<llvm::UndefValue>(Pattern)) {
1235 const llvm::APInt &AP = cast<llvm::ConstantInt>(Pattern)->getValue();
1236 assert(AP.getBitWidth() <= 8);
1237 Value = AP.getLimitedValue();
1239 auto *I = Builder.CreateMemSet(
1240 Loc, llvm::ConstantInt::get(CGM.
Int8Ty,
Value), SizeVal, isVolatile);
1242 I->addAnnotationMetadata(
"auto-init");
1248 bool IsTrivialAutoVarInitPattern =
1252 if (
auto *STy = dyn_cast<llvm::StructType>(Ty)) {
1253 if (STy ==
Loc.getElementType() ||
1254 (STy !=
Loc.getElementType() && IsTrivialAutoVarInitPattern)) {
1255 const llvm::StructLayout *Layout =
1257 for (
unsigned i = 0; i != constant->getNumOperands(); i++) {
1260 Address EltPtr = Builder.CreateConstInBoundsByteGEP(
1261 Loc.withElementType(CGM.
Int8Ty), CurOff);
1263 constant->getAggregateElement(i), IsAutoInit);
1267 }
else if (
auto *ATy = dyn_cast<llvm::ArrayType>(Ty)) {
1268 if (ATy ==
Loc.getElementType() ||
1269 (ATy !=
Loc.getElementType() && IsTrivialAutoVarInitPattern)) {
1270 for (
unsigned i = 0; i != ATy->getNumElements(); i++) {
1271 Address EltPtr = Builder.CreateConstGEP(
1272 Loc.withElementType(ATy->getElementType()), i);
1274 constant->getAggregateElement(i), IsAutoInit);
1283 Builder.CreateMemCpy(
Loc,
1285 CGM,
D, Builder, constant,
Loc.getAlignment()),
1286 SizeVal, isVolatile);
1288 I->addAnnotationMetadata(
"auto-init");
1294 llvm::Type *ElTy =
Loc.getElementType();
1295 llvm::Constant *constant =
1304 llvm::Type *ElTy =
Loc.getElementType();
1307 assert(!isa<llvm::UndefValue>(constant));
1313 auto *Ty = constant->getType();
1314 if (isa<llvm::UndefValue>(constant))
1316 if (Ty->isStructTy() || Ty->isArrayTy() || Ty->isVectorTy())
1317 for (llvm::Use &Op : constant->operands())
1324 llvm::Constant *constant) {
1325 auto *Ty = constant->getType();
1326 if (isa<llvm::UndefValue>(constant))
1328 if (!(Ty->isStructTy() || Ty->isArrayTy() || Ty->isVectorTy()))
1333 for (
unsigned Op = 0, NumOp = constant->getNumOperands(); Op != NumOp; ++Op) {
1334 auto *OpValue = cast<llvm::Constant>(constant->getOperand(Op));
1337 if (Ty->isStructTy())
1338 return llvm::ConstantStruct::get(cast<llvm::StructType>(Ty), Values);
1339 if (Ty->isArrayTy())
1340 return llvm::ConstantArray::get(cast<llvm::ArrayType>(Ty), Values);
1341 assert(Ty->isVectorTy());
1342 return llvm::ConstantVector::get(Values);
1358 llvm::Value *Addr) {
1359 if (!ShouldEmitLifetimeMarkers)
1362 assert(Addr->getType()->getPointerAddressSpace() ==
1364 "Pointer should be in alloca address space");
1365 llvm::Value *SizeV = llvm::ConstantInt::get(
1369 C->setDoesNotThrow();
1374 assert(Addr->getType()->getPointerAddressSpace() ==
1376 "Pointer should be in alloca address space");
1379 C->setDoesNotThrow();
1391 while (
getContext().getAsVariableArrayType(Type1D)) {
1393 if (
auto *
C = dyn_cast<llvm::ConstantInt>(VlaSize.NumElts))
1397 Twine Name = Twine(
"__vla_expr") + Twine(VLAExprCounter++);
1399 StringRef NameRef = Name.toStringRef(Buffer);
1401 VLAExprNames.push_back(&Ident);
1405 Dimensions.emplace_back(SizeExprAddr.getPointer(),
1408 Type1D = VlaSize.Type;
1417 unsigned NameIdx = 0;
1418 for (
auto &VlaSize : Dimensions) {
1420 if (
auto *
C = dyn_cast<llvm::ConstantInt>(VlaSize.NumElts))
1421 MD = llvm::ConstantAsMetadata::get(
C);
1426 SizeTy->getScalarSizeInBits(),
false);
1431 ArtificialDecl->setImplicit();
1436 assert(MD &&
"No Size expression debug node created");
1443CodeGenFunction::AutoVarEmission
1450 AutoVarEmission emission(
D);
1452 bool isEscapingByRef =
D.isEscapingByref();
1453 emission.IsEscapingByRef = isEscapingByRef;
1475 bool NRVO =
getLangOpts().ElideConstructors &&
D.isNRVOVariable();
1478 address = OpenMPLocalAddr;
1479 AllocaAddr = OpenMPLocalAddr;
1492 getContext().getBaseElementType(Ty)->isObjCObjectPointerType()) &&
1493 D.getInit()->isConstantInitializer(
getContext(),
false)))) {
1511 assert(emission.wasEmittedAsGlobal());
1516 emission.IsConstantAggregate =
true;
1534 const auto *RD = RecordTy->getDecl();
1535 const auto *CXXRD = dyn_cast<CXXRecordDecl>(RD);
1536 if ((CXXRD && !CXXRD->hasTrivialDestructor()) ||
1537 RD->isNonTrivialToPrimitiveDestroy()) {
1554 llvm::Type *allocaTy;
1555 if (isEscapingByRef) {
1557 allocaTy = byrefInfo.Type;
1558 allocaAlignment = byrefInfo.ByrefAlignment;
1561 allocaAlignment = alignment;
1568 nullptr, &AllocaAddr);
1573 bool IsMSCatchParam =
1595 emission.SizeForLifetimeMarkers =
1599 assert(!emission.useLifetimeMarkers());
1610 bool VarAllocated =
false;
1613 if (RT.isDelayedVariableLengthDecl(*
this, &
D)) {
1615 std::pair<llvm::Value *, llvm::Value *> AddrSizePair =
1622 address =
Base.getAddress();
1630 VarAllocated =
true;
1634 if (!VarAllocated) {
1635 if (!DidCallStackSave) {
1640 llvm::Value *
V =
Builder.CreateStackSave();
1644 DidCallStackSave =
true;
1665 setAddrOfLocalVar(&
D, address);
1666 emission.Addr = address;
1667 emission.AllocaAddr = AllocaAddr;
1676 if (UsePointerValue) {
1688 if (emission.useLifetimeMarkers())
1690 emission.getOriginalAllocatedAddress(),
1691 emission.getSizeForLifetimeMarkers());
1701 if (
const Expr *
E = dyn_cast<Expr>(S))
1703 for (
const Stmt *SubStmt : S->children())
1716 if (
const BlockExpr *BE = dyn_cast<BlockExpr>(
E)) {
1718 for (
const auto &I :
Block->captures()) {
1719 if (I.getVariable() == &Var)
1727 if (
const StmtExpr *SE = dyn_cast<StmtExpr>(
E)) {
1729 for (
const auto *BI : CS->
body())
1730 if (
const auto *BIE = dyn_cast<Expr>(BI)) {
1734 else if (
const auto *DS = dyn_cast<DeclStmt>(BI)) {
1736 for (
const auto *I : DS->decls()) {
1737 if (
const auto *VD = dyn_cast<VarDecl>((I))) {
1768 !Construct->requiresZeroInitialization())
1774void CodeGenFunction::emitZeroOrPatternForAutoVarInit(
QualType type,
1778 auto trivialAutoVarInitMaxSize =
1781 bool isVolatile =
type.isVolatileQualified();
1782 if (!
Size.isZero()) {
1789 switch (trivialAutoVarInit) {
1791 llvm_unreachable(
"Uninitialized handled by caller");
1795 if (trivialAutoVarInitMaxSize > 0 &&
1796 allocSize > trivialAutoVarInitMaxSize)
1803 if (trivialAutoVarInitMaxSize > 0 &&
1804 allocSize > trivialAutoVarInitMaxSize)
1821 auto SizeVal = VlaSize.NumElts;
1823 switch (trivialAutoVarInit) {
1825 llvm_unreachable(
"Uninitialized handled by caller");
1830 if (!EltSize.
isOne())
1833 SizeVal, isVolatile);
1834 I->addAnnotationMetadata(
"auto-init");
1841 llvm::Type *ElTy =
Loc.getElementType();
1848 llvm::Value *IsZeroSizedVLA =
Builder.CreateICmpEQ(
1849 SizeVal, llvm::ConstantInt::get(SizeVal->getType(), 0),
1851 Builder.CreateCondBr(IsZeroSizedVLA, ContBB, SetupBB);
1853 if (!EltSize.
isOne())
1855 llvm::Value *BaseSizeInChars =
1859 Begin.emitRawPointer(*
this),
1860 SizeVal,
"vla.end");
1861 llvm::BasicBlock *OriginBB =
Builder.GetInsertBlock();
1863 llvm::PHINode *Cur =
Builder.CreatePHI(
Begin.getType(), 2,
"vla.cur");
1864 Cur->addIncoming(
Begin.emitRawPointer(*
this), OriginBB);
1865 CharUnits CurAlign =
Loc.getAlignment().alignmentOfArrayElement(EltSize);
1870 BaseSizeInChars, isVolatile);
1871 I->addAnnotationMetadata(
"auto-init");
1874 llvm::Value *Done =
Builder.CreateICmpEQ(Next, End,
"vla-init.isdone");
1875 Builder.CreateCondBr(Done, ContBB, LoopBB);
1876 Cur->addIncoming(Next, LoopBB);
1883 assert(emission.Variable &&
"emission was not valid!");
1886 if (emission.wasEmittedAsGlobal())
return;
1888 const VarDecl &
D = *emission.Variable;
1903 if (emission.IsEscapingByRef)
1910 type.isNonTrivialToPrimitiveDefaultInitialize() ==
1913 if (emission.IsEscapingByRef)
1922 bool capturedByInit =
1925 bool locIsByrefHeader = !capturedByInit;
1927 locIsByrefHeader ? emission.getObjectAddress(*
this) : emission.Addr;
1937 auto initializeWhatIsTechnicallyUninitialized = [&](
Address Loc) {
1938 if (trivialAutoVarInit ==
1943 if (emission.IsEscapingByRef && !locIsByrefHeader)
1946 return emitZeroOrPatternForAutoVarInit(
type,
D,
Loc);
1950 return initializeWhatIsTechnicallyUninitialized(
Loc);
1952 llvm::Constant *constant =
nullptr;
1953 if (emission.IsConstantAggregate ||
1954 D.mightBeUsableInConstantExpressions(
getContext())) {
1955 assert(!capturedByInit &&
"constant init contains a capturing block?");
1957 if (constant && !constant->isZeroValue() &&
1958 (trivialAutoVarInit !=
1974 if (
D.getType()->isBitIntType() &&
1980 D.getType(), constant->getType());
1981 constant = llvm::ConstantFoldLoadFromConst(
1987 if (trivialAutoVarInit !=
1997 if (!
D.getType()->isScalarType() || capturedByInit ||
1999 initializeWhatIsTechnicallyUninitialized(
Loc);
2007 if (!emission.IsConstantAggregate) {
2030 LValue lvalue,
bool capturedByInit) {
2033 if (
type->isReferenceType()) {
2052 if (
type->isAtomicType()) {
2056 if (isa<VarDecl>(
D))
2058 else if (
auto *FD = dyn_cast<FieldDecl>(
D))
2068 llvm_unreachable(
"bad evaluation kind");
2073 const CodeGenFunction::AutoVarEmission &emission,
2079 Address addr = emission.getObjectAddress(*
this);
2089 llvm_unreachable(
"no cleanup for trivially-destructible variable");
2094 if (emission.NRVOFlag) {
2095 assert(!
type->isArrayType());
2097 EHStack.pushCleanup<DestroyNRVOVariableCXX>(cleanupKind, addr,
type, dtor,
2105 if (
var->isARCPseudoStrong())
return;
2111 if (!
var->hasAttr<ObjCPreciseLifetimeAttr>())
2120 if (emission.NRVOFlag) {
2121 assert(!
type->isArrayType());
2122 EHStack.pushCleanup<DestroyNRVOVariableC>(cleanupKind, addr,
2123 emission.NRVOFlag,
type);
2134 bool useEHCleanup = (cleanupKind &
EHCleanup);
2135 EHStack.pushCleanup<DestroyObject>(cleanupKind, addr,
type, destroyer,
2140 assert(emission.Variable &&
"emission was not valid!");
2143 if (emission.wasEmittedAsGlobal())
return;
2149 const VarDecl &
D = *emission.Variable;
2157 D.
hasAttr<ObjCPreciseLifetimeAttr>()) {
2162 if (
const CleanupAttr *CA =
D.
getAttr<CleanupAttr>()) {
2166 assert(F &&
"Could not find function!");
2175 if (emission.IsEscapingByRef &&
2178 if (emission.Variable->getType().isObjCGCWeak())
2199 llvm_unreachable(
"Unknown DestructionKind");
2206 assert(dtorKind &&
"cannot push destructor for trivial type");
2216 assert(dtorKind &&
"cannot push destructor for trivial type");
2225 bool useEHCleanupForArray) {
2226 pushFullExprCleanup<DestroyObject>(cleanupKind, addr,
type,
2227 destroyer, useEHCleanupForArray);
2234 assert(dtorKind &&
"cannot push destructor for trivial type");
2243 bool useEHCleanupForArray) {
2244 llvm::Instruction *DominatingIP =
2246 pushDestroy(cleanupKind, addr,
type, destroyer, useEHCleanupForArray);
2252 EHStack.pushCleanup<CallStackRestore>(
Kind, SPMem);
2256 CleanupKind Kind, std::pair<llvm::Value *, llvm::Value *> AddrSizePair) {
2257 EHStack.pushCleanup<KmpcAllocFree>(
Kind, AddrSizePair);
2262 Destroyer *destroyer,
2263 bool useEHCleanupForArray) {
2273 useEHCleanupForArray);
2277 return pushCleanupAfterFullExprWithActiveFlag<DestroyObject>(
2279 useEHCleanupForArray);
2284 using ConditionalCleanupType =
2291 AllocaTrackerRAII DeactivationAllocas(*
this);
2294 pushCleanupAndDeferDeactivation<ConditionalCleanupType>(
2295 cleanupKind, SavedAddr,
type, destroyer, useEHCleanupForArray);
2299 cleanup.AddAuxAllocas(std::move(DeactivationAllocas).Take());
2307 pushCleanupAfterFullExprWithActiveFlag<ConditionalCleanupType>(
2308 cleanupKind, ActiveFlagForLifetimeExt, SavedAddr,
type, destroyer,
2309 useEHCleanupForArray);
2324 Destroyer *destroyer,
2325 bool useEHCleanupForArray) {
2328 return destroyer(*
this, addr,
type);
2337 bool checkZeroLength =
true;
2340 if (llvm::ConstantInt *constLength = dyn_cast<llvm::ConstantInt>(
length)) {
2342 if (constLength->isZero())
return;
2343 checkZeroLength =
false;
2350 checkZeroLength, useEHCleanupForArray);
2367 Destroyer *destroyer,
2368 bool checkZeroLength,
2369 bool useEHCleanup) {
2377 if (checkZeroLength) {
2378 llvm::Value *isEmpty =
Builder.CreateICmpEQ(begin, end,
2379 "arraydestroy.isempty");
2380 Builder.CreateCondBr(isEmpty, doneBB, bodyBB);
2384 llvm::BasicBlock *entryBB =
Builder.GetInsertBlock();
2386 llvm::PHINode *elementPast =
2387 Builder.CreatePHI(begin->getType(), 2,
"arraydestroy.elementPast");
2388 elementPast->addIncoming(end, entryBB);
2391 llvm::Value *negativeOne = llvm::ConstantInt::get(
SizeTy, -1,
true);
2394 llvmElementType, elementPast, negativeOne,
"arraydestroy.element");
2401 destroyer(*
this,
Address(element, llvmElementType, elementAlign),
2408 llvm::Value *done =
Builder.CreateICmpEQ(element, begin,
"arraydestroy.done");
2409 Builder.CreateCondBr(done, doneBB, bodyBB);
2410 elementPast->addIncoming(element,
Builder.GetInsertBlock());
2419 llvm::Value *begin, llvm::Value *end,
2425 unsigned arrayDepth = 0;
2434 llvm::Value *zero = llvm::ConstantInt::get(CGF.
SizeTy, 0);
2438 elemTy, begin, gepIndices,
"pad.arraybegin");
2440 elemTy, end, gepIndices,
"pad.arrayend");
2455 llvm::Value *ArrayBegin;
2456 llvm::Value *ArrayEnd;
2458 CodeGenFunction::Destroyer *Destroyer;
2461 RegularPartialArrayDestroy(llvm::Value *arrayBegin, llvm::Value *arrayEnd,
2463 CodeGenFunction::Destroyer *destroyer)
2464 : ArrayBegin(arrayBegin), ArrayEnd(arrayEnd),
2465 ElementType(elementType), Destroyer(destroyer),
2466 ElementAlign(elementAlign) {}
2470 ElementType, ElementAlign, Destroyer);
2478 llvm::Value *ArrayBegin;
2481 CodeGenFunction::Destroyer *Destroyer;
2484 IrregularPartialArrayDestroy(llvm::Value *arrayBegin,
2488 CodeGenFunction::Destroyer *destroyer)
2489 : ArrayBegin(arrayBegin), ArrayEndPointer(arrayEndPointer),
2490 ElementType(elementType), Destroyer(destroyer),
2491 ElementAlign(elementAlign) {}
2496 ElementType, ElementAlign, Destroyer);
2511 Destroyer *destroyer) {
2512 pushFullExprCleanup<IrregularPartialArrayDestroy>(
2514 elementAlign, destroyer);
2524 llvm::Value *arrayEnd,
2527 Destroyer *destroyer) {
2528 pushFullExprCleanup<RegularPartialArrayDestroy>(
EHCleanup,
2529 arrayBegin, arrayEnd,
2530 elementType, elementAlign,
2536 if (LifetimeStartFn)
2537 return LifetimeStartFn;
2538 LifetimeStartFn = llvm::Intrinsic::getDeclaration(&
getModule(),
2540 return LifetimeStartFn;
2546 return LifetimeEndFn;
2547 LifetimeEndFn = llvm::Intrinsic::getDeclaration(&
getModule(),
2549 return LifetimeEndFn;
2558 ConsumeARCParameter(llvm::Value *param,
2560 : Param(param), Precise(precise) {}
2575 bool NoDebugInfo =
false;
2577 assert((isa<ParmVarDecl>(
D) || isa<ImplicitParamDecl>(
D)) &&
2578 "Invalid argument to EmitParmDecl");
2582 if (!isa<llvm::GlobalValue>(Arg.getAnyValue()))
2583 Arg.getAnyValue()->setName(
D.getName());
2588 if (
auto IPD = dyn_cast<ImplicitParamDecl>(&
D)) {
2592 llvm::Value *
V = Arg.isIndirect()
2594 : Arg.getDirectValue();
2606 bool DoStore =
false;
2608 bool UseIndirectDebugAddress =
false;
2611 if (Arg.isIndirect()) {
2612 DeclPtr = Arg.getIndirectAddress();
2625 if (UseIndirectDebugAddress) {
2628 D.getName() +
".indirect_addr");
2635 if (SrcLangAS != DestLangAS) {
2636 assert(
getContext().getTargetAddressSpace(SrcLangAS) ==
2642 *
this,
V, SrcLangAS, DestLangAS,
T,
true),
2655 "unexpected destructor type");
2657 CalleeDestructedParamCleanups[cast<ParmVarDecl>(&
D)] =
2668 DeclPtr = OpenMPLocalAddr;
2669 AllocaPtr = DeclPtr;
2673 D.getName() +
".addr", &AllocaPtr);
2678 llvm::Value *ArgVal = (DoStore ? Arg.getDirectValue() :
nullptr);
2688 bool isConsumed =
D.
hasAttr<NSConsumedAttr>();
2691 if (
D.isARCPseudoStrong()) {
2693 "pseudo-strong variable isn't strong?");
2694 assert(qs.
hasConst() &&
"pseudo-strong variable should be const!");
2699 if (Arg.isIndirect() && !ArgVal)
2743 setAddrOfLocalVar(&
D, DeclPtr);
2751 if (
const auto *Var = dyn_cast_or_null<ParmVarDecl>(&
D))
2762 if (requiresReturnValueNullabilityCheck()) {
2765 SanitizerScope SanScope(
this);
2766 RetValNullabilityPrecondition =
2767 Builder.CreateAnd(RetValNullabilityPrecondition,
2768 Builder.CreateIsNotNull(Arg.getAnyValue()));
2775 if (!LangOpts.OpenMP || (!LangOpts.EmitAllDecls && !
D->
isUsed()))
2782 if (!LangOpts.OpenMP || LangOpts.OpenMPSimd ||
2783 (!LangOpts.EmitAllDecls && !
D->
isUsed()))
2793 for (
const Expr *
E :
D->varlists()) {
2794 const auto *DE = cast<DeclRefExpr>(
E);
2795 const auto *VD = cast<VarDecl>(DE->getDecl());
2818 if (Entry->getType()->getAddressSpace() == TargetAS)
2823 llvm::PointerType *PTy = llvm::PointerType::get(Ty, TargetAS);
2828 llvm::GlobalVariable *DummyGV =
new llvm::GlobalVariable(
2829 getModule(), Entry->getValueType(),
false,
2830 llvm::GlobalValue::CommonLinkage,
nullptr,
"dummy",
nullptr,
2831 llvm::GlobalVariable::NotThreadLocal, Entry->getAddressSpace());
2832 Entry->replaceAllUsesWith(DummyGV);
2834 Entry->mutateType(PTy);
2835 llvm::Constant *NewPtrForOldDecl =
2836 llvm::ConstantExpr::getPointerBitCastOrAddrSpaceCast(
2837 Entry, DummyGV->getType());
2841 DummyGV->replaceAllUsesWith(NewPtrForOldDecl);
2842 DummyGV->eraseFromParent();
2846std::optional<CharUnits>
2848 if (
const auto *AA = VD->
getAttr<OMPAllocateDeclAttr>()) {
2849 if (
Expr *Alignment = AA->getAlignment()) {
2850 unsigned UserAlign =
2851 Alignment->EvaluateKnownConstInt(
getContext()).getExtValue();
2859 std::max<unsigned>(UserAlign, NaturalAlign.
getQuantity()));
2862 return std::nullopt;
Defines the clang::ASTContext interface.
static void emitStoresForInitAfterBZero(CodeGenModule &CGM, llvm::Constant *Init, Address Loc, bool isVolatile, CGBuilderTy &Builder, bool IsAutoInit)
For inits that canEmitInitWithFewStoresAfterBZero returned true for, emit the scalar stores that woul...
static bool isCapturedBy(const VarDecl &, const Expr *)
Determines whether the given __block variable is potentially captured by the given expression.
static void emitPartialArrayDestroy(CodeGenFunction &CGF, llvm::Value *begin, llvm::Value *end, QualType type, CharUnits elementAlign, CodeGenFunction::Destroyer *destroyer)
Perform partial array destruction as if in an EH cleanup.
static void emitStoresForPatternInit(CodeGenModule &CGM, const VarDecl &D, Address Loc, bool isVolatile, CGBuilderTy &Builder)
static bool canEmitInitWithFewStoresAfterBZero(llvm::Constant *Init, unsigned &NumStores)
Decide whether we can emit the non-zero parts of the specified initializer with equal or fewer than N...
static llvm::Constant * patternOrZeroFor(CodeGenModule &CGM, IsPattern isPattern, llvm::Type *Ty)
Generate a constant filled with either a pattern or zeroes.
static llvm::Constant * constWithPadding(CodeGenModule &CGM, IsPattern isPattern, llvm::Constant *constant)
Replace all padding bytes in a given constant with either a pattern byte or 0x00.
static llvm::Value * shouldUseMemSetToInitialize(llvm::Constant *Init, uint64_t GlobalSize, const llvm::DataLayout &DL)
Decide whether we should use memset to initialize a local variable instead of using a memcpy from a c...
static std::string getStaticDeclName(CodeGenModule &CGM, const VarDecl &D)
static void emitStoresForConstant(CodeGenModule &CGM, const VarDecl &D, Address Loc, bool isVolatile, CGBuilderTy &Builder, llvm::Constant *constant, bool IsAutoInit)
static bool shouldSplitConstantStore(CodeGenModule &CGM, uint64_t GlobalByteSize)
Decide whether we want to split a constant structure or array store into a sequence of its fields' st...
static llvm::Constant * replaceUndef(CodeGenModule &CGM, IsPattern isPattern, llvm::Constant *constant)
static bool tryEmitARCCopyWeakInit(CodeGenFunction &CGF, const LValue &destLV, const Expr *init)
static bool shouldUseBZeroPlusStoresToInitialize(llvm::Constant *Init, uint64_t GlobalSize)
Decide whether we should use bzero plus some stores to initialize a local variable instead of using a...
static llvm::Constant * constStructWithPadding(CodeGenModule &CGM, IsPattern isPattern, llvm::StructType *STy, llvm::Constant *constant)
Helper function for constWithPadding() to deal with padding in structures.
static bool containsUndef(llvm::Constant *constant)
static bool isAccessedBy(const VarDecl &var, const Stmt *s)
static void EmitAutoVarWithLifetime(CodeGenFunction &CGF, const VarDecl &var, Address addr, Qualifiers::ObjCLifetime lifetime)
EmitAutoVarWithLifetime - Does the setup required for an automatic variable with lifetime.
static Address createUnnamedGlobalForMemcpyFrom(CodeGenModule &CGM, const VarDecl &D, CGBuilderTy &Builder, llvm::Constant *Constant, CharUnits Align)
static void emitStoresForZeroInit(CodeGenModule &CGM, const VarDecl &D, Address Loc, bool isVolatile, CGBuilderTy &Builder)
static void drillIntoBlockVariable(CodeGenFunction &CGF, LValue &lvalue, const VarDecl *var)
CodeGenFunction::ComplexPairTy ComplexPairTy
This file defines OpenMP nodes for declarative directives.
static const RecordType * getRecordType(QualType QT)
Checks that the passed in QualType either is of RecordType or points to RecordType.
static const NamedDecl * getDefinition(const Decl *D)
Defines the SourceManager interface.
__device__ __2f16 float __ockl_bool s
CharUnits getTypeAlignInChars(QualType T) const
Return the ABI-specified alignment of a (complete) type T, in characters.
QualType getPointerType(QualType T) const
Return the uniqued reference to the type for a pointer to the specified type.
const LangOptions & getLangOpts() const
QualType getIntTypeForBitwidth(unsigned DestWidth, unsigned Signed) const
getIntTypeForBitwidth - sets integer QualTy according to specified details: bitwidth,...
CharUnits getDeclAlign(const Decl *D, bool ForAlignof=false) const
Return a conservative estimate of the alignment of the specified decl D.
const ArrayType * getAsArrayType(QualType T) const
Type Query functions.
CharUnits getTypeSizeInChars(QualType T) const
Return the size of the specified (complete) type T, in characters.
const VariableArrayType * getAsVariableArrayType(QualType T) const
unsigned getTargetAddressSpace(LangAS AS) const
Represents an array type, per C99 6.7.5.2 - Array Declarators.
Represents a block literal declaration, which is like an unnamed FunctionDecl.
ArrayRef< Capture > captures() const
BlockExpr - Adaptor class for mixing a BlockDecl with expressions.
Represents a call to a C++ constructor.
Represents a C++ constructor within a class.
A use of a default initializer in a constructor or in aggregate initialization.
Represents a C++ destructor within a class.
CharUnits - This is an opaque type for sizes expressed in character units.
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...
bool isOne() const
isOne - Test whether the quantity equals one.
static CharUnits fromQuantity(QuantityType Quantity)
fromQuantity - Construct a CharUnits quantity from a raw integer type.
bool hasReducedDebugInfo() const
Check if type and variable info should be emitted.
ABIArgInfo - Helper class to encapsulate information about how a specific C type should be passed to ...
bool getIndirectByVal() const
Like RawAddress, an abstract representation of an aligned address, but the pointer contained in this ...
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.
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 ApplyDebugLocation CreateDefaultArtificial(CodeGenFunction &CGF, SourceLocation TemporaryLocation)
Apply TemporaryLocation if it is valid.
llvm::StoreInst * CreateStore(llvm::Value *Val, Address Addr, bool IsVolatile=false)
llvm::CallInst * CreateMemSet(Address Dest, llvm::Value *Value, llvm::Value *Size, bool IsVolatile=false)
llvm::LoadInst * CreateLoad(Address Addr, const llvm::Twine &Name="")
llvm::LoadInst * CreateFlagLoad(llvm::Value *Addr, const llvm::Twine &Name="")
Emit a load from an i1 flag variable.
llvm::CallInst * CreateMemCpy(Address Dest, Address Src, llvm::Value *Size, bool IsVolatile=false)
Address CreateInBoundsGEP(Address Addr, ArrayRef< llvm::Value * > IdxList, llvm::Type *ElementType, CharUnits Align, const Twine &Name="")
static CGCallee forDirect(llvm::Constant *functionPtr, const CGCalleeInfo &abstractInfo=CGCalleeInfo())
This class gathers all debug information during compilation and is responsible for emitting to llvm g...
void EmitGlobalVariable(llvm::GlobalVariable *GV, const VarDecl *Decl)
Emit information about a global variable.
Param2DILocTy & getParamDbgMappings()
llvm::DILocalVariable * EmitDeclareOfArgVariable(const VarDecl *Decl, llvm::Value *AI, unsigned ArgNo, CGBuilderTy &Builder, bool UsePointerValue=false)
Emit call to llvm.dbg.declare for an argument variable declaration.
llvm::DILocalVariable * EmitDeclareOfAutoVariable(const VarDecl *Decl, llvm::Value *AI, CGBuilderTy &Builder, const bool UsePointerValue=false)
Emit call to llvm.dbg.declare for an automatic variable declaration.
void setLocation(SourceLocation Loc)
Update the current source location.
void registerVLASizeExpression(QualType Ty, llvm::Metadata *SizeExpr)
Register VLA size expression debug node with the qualified type.
CGFunctionInfo - Class to encapsulate the information about a function definition.
const_arg_iterator arg_begin() const
MutableArrayRef< ArgInfo > arguments()
virtual void EmitWorkGroupLocalVarDecl(CodeGenFunction &CGF, const VarDecl &D)
Emit the IR required for a work-group-local variable declaration, and add an entry to CGF's LocalDecl...
Allows to disable automatic handling of functions used in target regions as those marked as omp decla...
virtual void getKmpcFreeShared(CodeGenFunction &CGF, const std::pair< llvm::Value *, llvm::Value * > &AddrSizePair)
Get call to __kmpc_free_shared.
void emitUserDefinedMapper(const OMPDeclareMapperDecl *D, CodeGenFunction *CGF=nullptr)
Emit the function for the user defined mapper construct.
virtual void processRequiresDirective(const OMPRequiresDecl *D)
Perform check on requires decl to ensure that target architecture supports unified addressing.
virtual std::pair< llvm::Value *, llvm::Value * > getKmpcAllocShared(CodeGenFunction &CGF, const VarDecl *VD)
Get call to __kmpc_alloc_shared.
virtual void emitUserDefinedReduction(CodeGenFunction *CGF, const OMPDeclareReductionDecl *D)
Emit code for the specified user defined reduction construct.
virtual Address getAddressOfLocalVariable(CodeGenFunction &CGF, const VarDecl *VD)
Gets the OpenMP-specific address of the local variable.
CallArgList - Type for representing both the value and type of arguments in a call.
void add(RValue rvalue, QualType type)
CodeGenFunction - This class organizes the per-function state that is used while generating LLVM code...
void emitAutoVarTypeCleanup(const AutoVarEmission &emission, QualType::DestructionKind dtorKind)
void enterByrefCleanup(CleanupKind Kind, Address Addr, BlockFieldFlags Flags, bool LoadBlockVarAddr, bool CanThrow)
Enter a cleanup to destroy a __block variable.
llvm::Value * EmitLifetimeStart(llvm::TypeSize Size, llvm::Value *Addr)
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.
static Destroyer destroyNonTrivialCStruct
static bool cxxDestructorCanThrow(QualType T)
Check if T is a C++ class that has a destructor that can throw.
SanitizerSet SanOpts
Sanitizers enabled for this function.
RawAddress createCleanupActiveFlag()
llvm::DenseMap< const VarDecl *, llvm::Value * > NRVOFlags
A mapping from NRVO variables to the flags used to indicate when the NRVO has been applied to this va...
void EmitARCMoveWeak(Address dst, Address src)
void EmitAutoVarDecl(const VarDecl &D)
EmitAutoVarDecl - Emit an auto variable declaration.
void EmitLifetimeEnd(llvm::Value *Size, llvm::Value *Addr)
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)
static bool hasScalarEvaluationKind(QualType T)
const BlockByrefInfo & getBlockByrefInfo(const VarDecl *var)
void EmitDecl(const Decl &D)
EmitDecl - Emit a declaration.
void pushIrregularPartialArrayCleanup(llvm::Value *arrayBegin, Address arrayEndPointer, QualType elementType, CharUnits elementAlignment, Destroyer *destroyer)
RawAddress CreateDefaultAlignTempAlloca(llvm::Type *Ty, const Twine &Name="tmp")
CreateDefaultAlignedTempAlloca - This creates an alloca with the default ABI alignment of the given L...
llvm::Value * emitArrayLength(const ArrayType *arrayType, QualType &baseType, Address &addr)
emitArrayLength - Compute the length of an array, even if it's a VLA, and drill down to the base elem...
VlaSizePair getVLASize(const VariableArrayType *vla)
Returns an LLVM value that corresponds to the size, in non-variably-sized elements,...
CleanupKind getARCCleanupKind()
Retrieves the default cleanup kind for an ARC cleanup.
bool CurFuncIsThunk
In C++, whether we are code generating a thunk.
void EmitCXXDestructorCall(const CXXDestructorDecl *D, CXXDtorType Type, bool ForVirtualBase, bool Delegating, Address This, QualType ThisTy)
LValue EmitLValue(const Expr *E, KnownNonNull_t IsKnownNonNull=NotKnownNonNull)
EmitLValue - Emit code to compute a designator that specifies the location of the expression.
void EmitExtendGCLifetime(llvm::Value *object)
EmitExtendGCLifetime - Given a pointer to an Objective-C object, make sure it survives garbage collec...
llvm::SmallVector< DeferredDeactivateCleanup > DeferredDeactivationCleanupStack
llvm::Value * EmitARCStoreWeak(Address addr, llvm::Value *value, bool ignored)
void EmitVariablyModifiedType(QualType Ty)
EmitVLASize - Capture all the sizes for the VLA expressions in the given variably-modified type and s...
llvm::BasicBlock * createBasicBlock(const Twine &name="", llvm::Function *parent=nullptr, llvm::BasicBlock *before=nullptr)
createBasicBlock - Create an LLVM basic block.
const LangOptions & getLangOpts() const
llvm::Constant * EmitCheckTypeDescriptor(QualType T)
Emit a description of a type in a format suitable for passing to a runtime sanitizer handler.
void pushEHDestroy(QualType::DestructionKind dtorKind, Address addr, QualType type)
void emitArrayDestroy(llvm::Value *begin, llvm::Value *end, QualType elementType, CharUnits elementAlign, Destroyer *destroyer, bool checkZeroLength, bool useEHCleanup)
void EmitBlock(llvm::BasicBlock *BB, bool IsFinished=false)
EmitBlock - Emit the given block.
void pushDestroyAndDeferDeactivation(QualType::DestructionKind dtorKind, Address addr, QualType type)
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...
const CodeGen::CGBlockInfo * BlockInfo
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,...
void EmitExprAsInit(const Expr *init, const ValueDecl *D, LValue lvalue, bool capturedByInit)
EmitExprAsInit - Emits the code necessary to initialize a location in memory with the given initializ...
void emitByrefStructureInit(const AutoVarEmission &emission)
ComplexPairTy EmitComplexExpr(const Expr *E, bool IgnoreReal=false, bool IgnoreImag=false)
EmitComplexExpr - Emit the computation of the specified expression of complex type,...
@ TCK_NonnullAssign
Checking the value assigned to a _Nonnull pointer. Must not be null.
llvm::Value * EmitARCStoreStrongCall(Address addr, llvm::Value *value, bool resultIgnored)
llvm::Type * ConvertTypeForMem(QualType T)
llvm::Value * EmitARCUnsafeUnretainedScalarExpr(const Expr *expr)
void EmitAutoVarInit(const AutoVarEmission &emission)
void EmitScalarInit(const Expr *init, const ValueDecl *D, LValue lvalue, bool capturedByInit)
DominatingValue< T >::saved_type saveValueInCond(T value)
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 EmitStaticVarDecl(const VarDecl &D, llvm::GlobalValue::LinkageTypes Linkage)
static Destroyer destroyCXXObject
void EmitVarAnnotations(const VarDecl *D, llvm::Value *V)
Emit local annotations for the local variable V, declared by D.
Destroyer * getDestroyer(QualType::DestructionKind destructionKind)
void EmitAtomicInit(Expr *E, LValue lvalue)
const TargetInfo & getTarget() const
bool isInConditionalBranch() const
isInConditionalBranch - Return true if we're currently emitting one branch or the other of a conditio...
void emitDestroy(Address addr, QualType type, Destroyer *destroyer, bool useEHCleanupForArray)
void EmitCXXGuardedInit(const VarDecl &D, llvm::GlobalVariable *DeclPtr, bool PerformInit)
Emit code in this function to perform a guarded variable initialization.
void EmitARCRelease(llvm::Value *value, ARCPreciseLifetime_t precise)
void initFullExprCleanupWithFlag(RawAddress ActiveFlag)
void EmitCheck(ArrayRef< std::pair< llvm::Value *, SanitizerMask > > 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...
void EmitARCCopyWeak(Address dst, Address src)
void setBlockContextParameter(const ImplicitParamDecl *D, unsigned argNum, llvm::Value *ptr)
void defaultInitNonTrivialCStructVar(LValue Dst)
bool HaveInsertPoint() const
HaveInsertPoint - True if an insertion point is defined.
llvm::Constant * EmitCheckSourceLocation(SourceLocation Loc)
Emit a description of a source location in a format suitable for passing to a runtime sanitizer handl...
bool isTrivialInitializer(const Expr *Init)
Determine whether the given initializer is trivial in the sense that it requires no code to be genera...
CGDebugInfo * getDebugInfo()
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 EmitDeclRefLValue(const DeclRefExpr *E)
AggValueSlot::Overlap_t getOverlapForFieldInit(const FieldDecl *FD)
Determine whether a field initialization may overlap some other object.
llvm::Value * EmitARCRetainAutoreleaseScalarExpr(const Expr *expr)
const TargetCodeGenInfo & getTargetHooks() const
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.
VlaSizePair getVLAElements1D(const VariableArrayType *vla)
Return the number of elements for a single dimension for the given array type.
void EmitVarDecl(const VarDecl &D)
EmitVarDecl - Emit a local variable declaration.
ASTContext & getContext() const
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...
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 Destroyer(CodeGenFunction &CGF, Address addr, QualType ty)
AutoVarEmission EmitAutoVarAlloca(const VarDecl &var)
void pushDestroy(QualType::DestructionKind dtorKind, Address addr, QualType type)
Address ReturnValuePointer
ReturnValuePointer - The temporary alloca to hold a pointer to sret.
void EmitAutoVarCleanups(const AutoVarEmission &emission)
llvm::GlobalVariable * AddInitializerToStaticVarDecl(const VarDecl &D, llvm::GlobalVariable *GV)
AddInitializerToStaticVarDecl - Add the initializer for 'D' to the global variable that has already b...
void PopCleanupBlock(bool FallThroughIsBranchThrough=false, bool ForDeactivation=false)
PopCleanupBlock - Will pop the cleanup entry on the stack and process all branch fixups.
static Destroyer destroyARCWeak
bool needsEHCleanup(QualType::DestructionKind kind)
Determines whether an EH cleanup is required to destroy a type with the given destruction kind.
CleanupKind getCleanupKind(QualType::DestructionKind kind)
llvm::Type * ConvertType(QualType T)
void EmitARCInitWeak(Address addr, llvm::Value *value)
static Destroyer destroyARCStrongPrecise
VarBypassDetector Bypasses
llvm::Value * EmitARCRetainNonBlock(llvm::Value *value)
void pushStackRestore(CleanupKind kind, Address SPMem)
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.
const CGFunctionInfo * CurFnInfo
void pushKmpcAllocFree(CleanupKind Kind, std::pair< llvm::Value *, llvm::Value * > AddrSizePair)
void EmitParmDecl(const VarDecl &D, ParamValue Arg, unsigned ArgNo)
EmitParmDecl - Emit a ParmVarDecl or an ImplicitParamDecl.
Address ReturnValue
ReturnValue - The temporary alloca to hold the return value.
static Destroyer destroyARCStrongImprecise
void EnsureInsertPoint()
EnsureInsertPoint - Ensure that an insertion point is defined so that emitted IR has a place to go.
llvm::LLVMContext & getLLVMContext()
llvm::Value * EmitScalarExpr(const Expr *E, bool IgnoreResultAssign=false)
EmitScalarExpr - Emit the computation of the specified expression of LLVM scalar type,...
void EmitAndRegisterVariableArrayDimensions(CGDebugInfo *DI, const VarDecl &D, bool EmitDebugInfo)
Emits the alloca and debug information for the size expressions for each dimension of an array.
llvm::Value * EmitARCRetainScalarExpr(const Expr *expr)
void pushRegularPartialArrayCleanup(llvm::Value *arrayBegin, llvm::Value *arrayEnd, QualType elementType, CharUnits elementAlignment, Destroyer *destroyer)
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...
bool hasLabelBeenSeenInCurrentScope() const
Return true if a label was seen in the current scope.
This class organizes the cross-function state that is used while generating LLVM code.
StringRef getBlockMangledName(GlobalDecl GD, const BlockDecl *BD)
void setGVProperties(llvm::GlobalValue *GV, GlobalDecl GD) const
Set visibility, dllimport/dllexport and dso_local.
llvm::Module & getModule() const
void setStaticLocalDeclAddress(const VarDecl *D, llvm::Constant *C)
llvm::Function * getLLVMLifetimeStartFn()
Lazily declare the @llvm.lifetime.start intrinsic.
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 * getNullPointer(llvm::PointerType *T, QualType QT)
Get target specific null pointer.
void ErrorUnsupported(const Stmt *S, const char *Type)
Print out an error that codegen doesn't support the specified stmt yet.
const LangOptions & getLangOpts() const
CharUnits getNaturalTypeAlignment(QualType T, LValueBaseInfo *BaseInfo=nullptr, TBAAAccessInfo *TBAAInfo=nullptr, bool forPointeeType=false)
CodeGenTypes & getTypes()
CGOpenCLRuntime & getOpenCLRuntime()
Return a reference to the configured OpenCL runtime.
void addUsedGlobal(llvm::GlobalValue *GV)
Add a global to a list to be added to the llvm.used metadata.
void EmitOMPAllocateDecl(const OMPAllocateDecl *D)
Emit a code for the allocate directive.
llvm::GlobalValue::LinkageTypes getLLVMLinkageVarDefinition(const VarDecl *VD)
Returns LLVM linkage for a declarator.
const llvm::DataLayout & getDataLayout() const
void addUsedOrCompilerUsedGlobal(llvm::GlobalValue *GV)
Add a global to a list to be added to the llvm.compiler.used metadata.
CGOpenMPRuntime & getOpenMPRuntime()
Return a reference to the configured OpenMP runtime.
SanitizerMetadata * getSanitizerMetadata()
llvm::Constant * getOrCreateStaticVarDecl(const VarDecl &D, llvm::GlobalValue::LinkageTypes Linkage)
llvm::Constant * GetAddrOfGlobal(GlobalDecl GD, ForDefinition_t IsForDefinition=NotForDefinition)
void AddGlobalAnnotations(const ValueDecl *D, llvm::GlobalValue *GV)
Add global annotations that are set on D, for the global GV.
void setTLSMode(llvm::GlobalValue *GV, const VarDecl &D) const
Set the TLS mode for the given LLVM GlobalValue for the thread-local variable declaration D.
ASTContext & getContext() const
void EmitOMPDeclareMapper(const OMPDeclareMapperDecl *D, CodeGenFunction *CGF=nullptr)
Emit a code for declare mapper construct.
llvm::Function * getLLVMLifetimeEndFn()
Lazily declare the @llvm.lifetime.end intrinsic.
bool supportsCOMDAT() const
void EmitOMPRequiresDecl(const OMPRequiresDecl *D)
Emit a code for requires directive.
const TargetCodeGenInfo & getTargetCodeGenInfo()
const CodeGenOptions & getCodeGenOpts() const
StringRef getMangledName(GlobalDecl GD)
std::optional< CharUnits > getOMPAllocateAlignment(const VarDecl *VD)
Return the alignment specified in an allocate directive, if present.
llvm::LLVMContext & getLLVMContext()
llvm::GlobalValue * GetGlobalValue(StringRef Ref)
void EmitOMPDeclareReduction(const OMPDeclareReductionDecl *D, CodeGenFunction *CGF=nullptr)
Emit a code for declare reduction construct.
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...
LangAS GetGlobalVarAddressSpace(const VarDecl *D)
Return the AST address space of the underlying global variable for D, as determined by its declaratio...
llvm::ConstantInt * getSize(CharUnits numChars)
Emit the given number of characters as a value of type size_t.
llvm::Type * convertTypeForLoadStore(QualType T, llvm::Type *LLVMTy=nullptr)
Given that T is a scalar type, return the IR type that should be used for load and store operations.
llvm::Type * ConvertTypeForMem(QualType T)
ConvertTypeForMem - Convert type T into a llvm::Type.
bool typeRequiresSplitIntoByteArray(QualType ASTTy, llvm::Type *LLVMTy=nullptr)
Check whether the given type needs to be laid out in memory using an opaque byte-array type because i...
const CGFunctionInfo & arrangeFunctionDeclaration(const FunctionDecl *FD)
Free functions are functions that are compatible with an ordinary C function pointer type.
llvm::Constant * tryEmitAbstractForInitializer(const VarDecl &D)
Try to emit the initializer of the given declaration as an abstract constant.
A cleanup scope which generates the cleanup blocks lazily.
Information for lazily generating a cleanup.
ConditionalCleanup stores the saved form of its parameters, then restores them and performs the clean...
stable_iterator stable_begin() const
Create a stable reference to the top of the EH stack.
iterator begin() const
Returns an iterator pointing to the innermost EH scope.
LValue - This represents an lvalue references.
llvm::Value * getPointer(CodeGenFunction &CGF) const
Address getAddress() const
void setNonGC(bool Value)
void setAddress(Address address)
Qualifiers::ObjCLifetime getObjCLifetime() const
RValue - This trivial value class is used to represent the result of an expression that is evaluated.
static RValue get(llvm::Value *V)
An abstract representation of an aligned address.
llvm::Value * getPointer() const
static RawAddress invalid()
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 void setTargetAttributes(const Decl *D, llvm::GlobalValue *GV, CodeGen::CodeGenModule &M) const
setTargetAttributes - Provides a convenient hook to handle extra target-specific attributes for the g...
bool IsBypassed(const VarDecl *D) const
Returns true if the variable declaration was by bypassed by any goto or switch statement.
CompoundStmt - This represents a group of statements like { stmt stmt }.
DeclContext - This is used only as base class of specific decl types that can act as declaration cont...
A reference to a declared variable, function, enum, etc.
Decl - This represents one declaration (or definition), e.g.
const DeclContext * getParentFunctionOrMethod(bool LexicalParent=false) const
If this decl is defined inside a function/method/block it returns the corresponding DeclContext,...
Decl * getNonClosureContext()
Find the innermost non-closure ancestor of this declaration, walking up through blocks,...
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()
This represents one expression.
Expr * IgnoreParenCasts() LLVM_READONLY
Skip past any parentheses and casts 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 isLValue() const
isLValue - True if this expression is an "l-value" according to the rules of the current language.
SourceLocation getExprLoc() const LLVM_READONLY
getExprLoc - Return the preferred location for the arrow when diagnosing a problem with a generic exp...
Represents a function declaration or definition.
GlobalDecl - represents a global declaration.
const Decl * getDecl() const
One of these records is kept for each identifier that is lexed.
IdentifierInfo & getOwn(StringRef Name)
Gets an IdentifierInfo for the given name without consulting external sources.
This represents '#pragma omp allocate ...' directive.
This represents '#pragma omp declare mapper ...' directive.
This represents '#pragma omp declare reduction ...' directive.
This represents '#pragma omp requires...' directive.
A (possibly-)qualified type.
@ DK_objc_strong_lifetime
@ PDIK_Struct
The type is a struct containing a field whose type is not PCK_Trivial.
LangAS getAddressSpace() const
Return the address space of this type.
bool isConstant(const ASTContext &Ctx) const
Qualifiers getQualifiers() const
Retrieve the set of qualifiers applied to this type.
Qualifiers::ObjCLifetime getObjCLifetime() const
Returns lifetime attribute of this type.
QualType getNonReferenceType() const
If Type is a reference type (e.g., const int&), returns the type that the reference refers to ("const...
QualType getUnqualifiedType() const
Retrieve the unqualified variant of the given type, removing as little sugar as possible.
bool isConstantStorage(const ASTContext &Ctx, bool ExcludeCtor, bool ExcludeDtor)
bool isPODType(const ASTContext &Context) const
Determine whether this is a Plain Old Data (POD) type (C++ 3.9p10).
The collection of all-type qualifiers we support.
@ 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.
ObjCLifetime getObjCLifetime() const
bool isParamDestroyedInCallee() const
A helper class that allows the use of isa/cast/dyncast to detect TagType objects of structs/unions/cl...
RecordDecl * getDecl() const
Scope - A scope is a transient data structure that is used while parsing the program.
static const uint64_t MaximumAlignment
Encodes a location in the source.
StmtExpr - This is the GNU Statement Expression extension: ({int X=4; X;}).
Stmt - This represents one statement.
bool isMicrosoft() const
Is this ABI an MSVC-compatible ABI?
TargetCXXABI getCXXABI() const
Get the C++ ABI currently in use.
bool isConstantSizeType() const
Return true if this is not a variable sized type, according to the rules of C99 6....
const T * castAs() const
Member-template castAs<specific type>.
bool isVariablyModifiedType() const
Whether this type is a variably-modified type (C99 6.7.5).
const T * getAs() const
Member-template getAs<specific type>'.
bool isRecordType() const
std::optional< NullabilityKind > getNullability() const
Determine the nullability of the given type.
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.
static VarDecl * Create(ASTContext &C, DeclContext *DC, SourceLocation StartLoc, SourceLocation IdLoc, const IdentifierInfo *Id, QualType T, TypeSourceInfo *TInfo, StorageClass S)
bool hasGlobalStorage() const
Returns true for all variables that do not have local storage.
const Expr * getInit() const
bool isLocalVarDecl() const
Returns true for local variable declarations other than parameters.
Defines the clang::TargetInfo interface.
@ Decl
The l-value was an access to a declared entity or something equivalently strong, like the address of ...
llvm::Constant * initializationPatternFor(CodeGenModule &, llvm::Type *)
@ NormalCleanup
Denotes a cleanup that should run when a scope is exited using normal control flow (falling off the e...
@ EHCleanup
Denotes a cleanup that should run when a scope is exited using exceptional control flow (a throw stat...
ARCPreciseLifetime_t
Does an ARC strong l-value have precise lifetime?
const internal::VariadicAllOfMatcher< Type > type
Matches Types in the clang AST.
const AstTypeMatcher< ArrayType > arrayType
Matches all kinds of arrays.
const internal::VariadicAllOfMatcher< Decl > decl
Matches declarations.
const internal::VariadicDynCastAllOfMatcher< Stmt, CastExpr > castExpr
Matches any cast nodes of Clang's AST.
constexpr Variable var(Literal L)
Returns the variable of L.
bool Zero(InterpState &S, CodePtr OpPC)
bool Null(InterpState &S, CodePtr OpPC, const Descriptor *Desc)
The JSON file list parser is used to communicate input to InstallAPI.
@ Ctor_Base
Base object ctor.
@ NonNull
Values of this type can never be null.
Linkage
Describes the different kinds of linkage (C++ [basic.link], C99 6.2.2) that an entity may have.
@ SD_Automatic
Automatic storage duration (most local variables).
@ Dtor_Base
Base object dtor.
@ Dtor_Complete
Complete object dtor.
LangAS
Defines the address space values used by the address space qualifier of QualType.
@ VK_LValue
An l-value expression is a reference to an object with independent storage.
const FunctionProtoType * T
@ ThreadPrivateVar
Parameter for Thread private variable.
float __ovld __cnfn length(float)
Return the length of vector p, i.e., sqrt(p.x2 + p.y 2 + ...)
static Address getAddressOfLocalVariable(CodeGenFunction &CGF, const VarDecl *VD)
Gets the OpenMP-specific address of the local variable /p VD.
llvm::IntegerType * Int64Ty
llvm::IntegerType * Int8Ty
i8, i16, i32, and i64
llvm::IntegerType * SizeTy
llvm::IntegerType * IntPtrTy
llvm::PointerType * Int8PtrTy
llvm::PointerType * AllocaInt8PtrTy
LangAS getASTAllocaAddressSpace() const
A metaprogramming class for ensuring that a value will dominate an arbitrary position in a function.
bool has(SanitizerMask K) const
Check if a certain (single) sanitizer is enabled.