38#include "llvm/ABI/FunctionInfo.h"
39#include "llvm/ABI/IRTypeMapper.h"
40#include "llvm/ABI/TargetInfo.h"
41#include "llvm/ABI/Types.h"
42#include "llvm/ADT/STLExtras.h"
43#include "llvm/ADT/StringExtras.h"
44#include "llvm/Analysis/ValueTracking.h"
45#include "llvm/IR/Assumptions.h"
46#include "llvm/IR/AttributeMask.h"
47#include "llvm/IR/Attributes.h"
48#include "llvm/IR/CallingConv.h"
49#include "llvm/IR/DataLayout.h"
50#include "llvm/IR/DebugInfoMetadata.h"
51#include "llvm/IR/InlineAsm.h"
52#include "llvm/IR/IntrinsicInst.h"
53#include "llvm/IR/Intrinsics.h"
54#include "llvm/IR/Type.h"
55#include "llvm/Transforms/Utils/Local.h"
68 if (Target.getTriple().isSPIROrSPIRV())
69 return llvm::CallingConv::SPIR_FUNC;
70 return llvm::CallingConv::C;
72 return llvm::CallingConv::X86_StdCall;
74 return llvm::CallingConv::X86_FastCall;
76 return llvm::CallingConv::X86_RegCall;
78 return llvm::CallingConv::X86_ThisCall;
80 return llvm::CallingConv::Win64;
82 return llvm::CallingConv::X86_64_SysV;
84 return llvm::CallingConv::ARM_AAPCS;
86 return llvm::CallingConv::ARM_AAPCS_VFP;
88 return llvm::CallingConv::Intel_OCL_BI;
91 return llvm::CallingConv::C;
94 return llvm::CallingConv::X86_VectorCall;
96 return llvm::CallingConv::AArch64_VectorCall;
98 return llvm::CallingConv::AArch64_SVE_VectorCall;
100 return CGM.getTargetCodeGenInfo().getDeviceKernelCallingConv();
102 return llvm::CallingConv::PreserveMost;
104 return llvm::CallingConv::PreserveAll;
106 return llvm::CallingConv::Swift;
108 return llvm::CallingConv::SwiftTail;
110 return llvm::CallingConv::M68k_RTD;
112 return llvm::CallingConv::PreserveNone;
116#define CC_VLS_CASE(ABI_VLEN) \
117 case CC_RISCVVLSCall_##ABI_VLEN: \
118 return llvm::CallingConv::RISCV_VLSCall_##ABI_VLEN;
133 llvm_unreachable(
"unhandled calling convention");
144 RecTy = Context.getCanonicalTagType(RD);
146 RecTy = Context.VoidTy;
151 return Context.getPointerType(RecTy);
177 assert(paramInfos.size() <= prefixArgs);
178 assert(proto->
getNumParams() + prefixArgs <= totalArgs);
180 paramInfos.reserve(totalArgs);
183 paramInfos.resize(prefixArgs);
187 paramInfos.push_back(ParamInfo);
189 if (ParamInfo.hasPassObjectSize())
190 paramInfos.emplace_back();
193 assert(paramInfos.size() <= totalArgs &&
194 "Did we forget to insert pass_object_size args?");
196 paramInfos.resize(totalArgs);
206 if (!FPT->hasExtParameterInfos()) {
207 assert(paramInfos.empty() &&
208 "We have paramInfos, but the prototype doesn't?");
209 prefix.append(FPT->param_type_begin(), FPT->param_type_end());
213 unsigned PrefixSize = prefix.size();
217 prefix.reserve(prefix.size() + FPT->getNumParams());
219 auto ExtInfos = FPT->getExtParameterInfos();
220 assert(ExtInfos.size() == FPT->getNumParams());
221 for (
unsigned I = 0, E = FPT->getNumParams(); I != E; ++I) {
222 prefix.push_back(FPT->getParamType(I));
223 if (ExtInfos[I].hasPassObjectSize())
248 FTP->getExtInfo(), paramInfos,
Required,
259 return ::arrangeLLVMFunctionInfo(*
this,
false, argTypes,
264 bool IsTargetDefaultMSABI) {
269 if (D->
hasAttr<FastCallAttr>())
275 if (D->
hasAttr<ThisCallAttr>())
278 if (D->
hasAttr<VectorCallAttr>())
284 if (PcsAttr *PCS = D->
getAttr<PcsAttr>())
287 if (D->
hasAttr<AArch64VectorPcsAttr>())
290 if (D->
hasAttr<AArch64SVEPcsAttr>())
293 if (D->
hasAttr<DeviceKernelAttr>())
296 if (D->
hasAttr<IntelOclBiccAttr>())
305 if (D->
hasAttr<PreserveMostAttr>())
308 if (D->
hasAttr<PreserveAllAttr>())
314 if (D->
hasAttr<PreserveNoneAttr>())
317 if (D->
hasAttr<RISCVVectorCCAttr>())
320 if (RISCVVLSCCAttr *PCS = D->
getAttr<RISCVVLSCCAttr>()) {
321 switch (PCS->getVectorWidth()) {
323 llvm_unreachable(
"Invalid RISC-V VLS ABI VLEN");
324#define CC_VLS_CASE(ABI_VLEN) \
326 return CC_RISCVVLSCall_##ABI_VLEN;
364 CanonicalFTP.getTypePtr(), argTypes.size());
367 CanonicalFTP->getReturnType().getUnqualifiedType(),
369 paramInfos, required, MD);
375 if (FD->
hasAttr<CUDAGlobalAttr>()) {
407 argTypes, prototype->getExtInfo(), paramInfos,
417 !Target.getCXXABI().hasConstructorVariants();
430 bool PassParams =
true;
432 if (
auto *CD = dyn_cast<CXXConstructorDecl>(MD)) {
435 if (
auto Inherited = CD->getInheritedConstructor())
447 if (!paramInfos.empty()) {
450 paramInfos.insert(paramInfos.begin() + 1, AddedArgs.
Prefix,
453 paramInfos.append(AddedArgs.
Suffix,
458 (PassParams && MD->isVariadic() ?
RequiredArgs(argTypes.size())
464 ? CGM.getContext().VoidPtrTy
467 argTypes, extInfo, paramInfos, required, MD);
473 for (
auto &arg : args)
481 for (
auto &arg : args)
488 unsigned totalArgs) {
506 unsigned ExtraPrefixArgs,
unsigned ExtraSuffixArgs,
509 for (
const auto &Arg : args)
510 ArgTypes.push_back(Context.getCanonicalParamType(Arg.Ty));
513 unsigned TotalPrefixArgs = 1 + ExtraPrefixArgs;
518 FPT, TotalPrefixArgs + ExtraSuffixArgs)
524 ? CGM.getContext().VoidPtrTy
531 if (PassProtoArgs && FPT->hasExtParameterInfos()) {
538 ArgTypes, Info, ParamInfos,
Required,
548 if (MD->isImplicitObjectMemberFunction())
556 if (DeviceKernelAttr::isOpenCLSpelling(FD->
getAttr<DeviceKernelAttr>()) &&
559 CGM.getTargetCodeGenInfo().setOCLKernelStubCallingConvention(FT);
567 {}, noProto->getExtInfo(), {},
601 argTys.push_back(Context.getCanonicalParamType(receiverType));
603 argTys.push_back(Context.getCanonicalParamType(Context.getObjCSelType()));
605 argTys.push_back(Context.getCanonicalParamType(I->getType()));
607 I->hasAttr<NoEscapeAttr>());
608 extParamInfos.push_back(extParamInfo);
612 bool IsTargetDefaultMSABI =
618 if (
getContext().getLangOpts().ObjCAutoRefCount &&
619 MD->
hasAttr<NSReturnsRetainedAttr>())
657 assert(MD->
isVirtual() &&
"only methods have thunks");
674 ArgTys.push_back(*FTP->param_type_begin());
676 ArgTys.push_back(Context.IntTy);
677 CallingConv CC = Context.getDefaultCallingConvention(
689 unsigned numExtraRequiredArgs,
bool chainCall,
691 assert(args.size() >= numExtraRequiredArgs);
701 if (proto->isVariadic())
704 if (proto->hasExtParameterInfos())
718 for (
const auto &arg : args)
723 paramInfos, required, ABIInfoFD);
734 chainCall ? 1 : 0, chainCall, ABIInfoFD);
766 for (
const auto &Arg : args)
767 argTypes.push_back(Context.getCanonicalParamType(Arg.Ty));
809 assert(numPrefixArgs + 1 <= args.size() &&
810 "Emitting a call with less args than the required prefix?");
821 paramInfos, required, ABIInfoFD);
833 assert(signature.
arg_size() <= args.size());
834 unsigned X86ABIAVXLevel =
835 CGM.getABIInfo().getX86ABIAVXLevel(ABIInfoFD, signature.
getExtInfo());
836 if (signature.
arg_size() == args.size() &&
842 if (!sigParamInfos.empty()) {
843 paramInfos.append(sigParamInfos.begin(), sigParamInfos.end());
844 paramInfos.resize(args.size());
882 return "IndirectAliased";
888 return "CoerceAndExpand";
890 return "TargetSpecific";
894 llvm_unreachable(
"Unknown kind");
900 MappedArgTypes.reserve(FI.
arg_size());
902 MappedArgTypes.push_back(AbiMapper->convertType(Arg.type));
905 llvm::abi::RequiredArgs AbiRequired = llvm::abi::RequiredArgs::All;
907 AbiRequired = llvm::abi::RequiredArgs(
Required.getNumRequiredArgs());
909 auto AbiFI = llvm::abi::FunctionInfo::create(
911 MappedArgTypes, AbiRequired);
920 auto ConvertABIArgInfo = [&](
ABIArgInfo &Target,
923 auto Check = [&](
bool Cond, llvm::function_ref<void()> MessageFn) {
927 llvm::dbgs() <<
"For return value of type ";
929 llvm::dbgs() <<
"For argument " << ArgNo <<
" of type ";
930 llvm::dbgs() <<
Type <<
": ";
932 llvm::dbgs() <<
"\n";
935 auto CheckSimple = [&](
auto TargetVal,
auto ResVal, StringRef What) {
936 Check(TargetVal == ResVal, [&]() {
937 llvm::dbgs() << What <<
" mismatch (expected: " << TargetVal
938 <<
", given: " << ResVal <<
")";
943 Check(Target.getKind() == Res.
getKind(), [&]() {
944 llvm::dbgs() <<
"Kind mismatch (expected: "
945 << abiKindToString(Target.getKind())
946 <<
", given: " << abiKindToString(Res.getKind()) <<
")";
951 llvm::Type *TargetType = Target.getCoerceToType();
958 Check(TargetType == ResType, [&]() {
959 llvm::dbgs() <<
"CoerceToType mismatch (expected: " << *TargetType
960 <<
", given: " << *ResType <<
")";
966 CheckSimple(Target.isSignExt(), Res.
isSignExt(),
"SignExt");
967 CheckSimple(Target.isZeroExt(), Res.
isZeroExt(),
"ZeroExt");
970 CheckSimple(Target.getDirectAlign(), Res.
getDirectAlign(),
"DirectAlign");
984 "IndirectAddrSpace");
988 llvm::dbgs() <<
"IndirectAlign mismatch (expected: "
989 << Target.getIndirectAlign().getQuantity()
990 <<
", given: " << Res.getIndirectAlign().getQuantity()
1001 auto ConvertABIArgInfo =
1003 int ArgNo) { Target = convertABIArgInfo(AbiInfo,
Type); };
1006 ConvertABIArgInfo(FI.
getReturnInfo(), AbiFI->getReturnInfo(),
1010 for (
auto [CGArg, AbiArg] :
1011 llvm::zip_equal(FI.
arguments(), AbiFI->arguments()))
1012 ConvertABIArgInfo(CGArg.info, AbiArg.Info, CGArg.type, ArgNo++);
1015ABIArgInfo CodeGenModule::convertABIArgInfo(
const llvm::abi::ArgInfo &AbiInfo,
1017 switch (AbiInfo.getKind()) {
1018 case llvm::abi::ArgInfo::Direct: {
1019 llvm::Type *CoercedType =
nullptr;
1020 if (AbiInfo.getCoerceToType())
1021 CoercedType = AbiReverseMapper->convertType(AbiInfo.getCoerceToType());
1023 CoercedType = getTypes().ConvertType(
Type);
1024 unsigned DirectAlign = 0;
1025 if (llvm::MaybeAlign Align = AbiInfo.getDirectAlign())
1026 DirectAlign = Align->value();
1031 AbiInfo.getCanBeFlattened(), DirectAlign);
1033 case llvm::abi::ArgInfo::Extend: {
1034 llvm::Type *CoercedType =
nullptr;
1035 if (AbiInfo.getCoerceToType())
1036 CoercedType = AbiReverseMapper->convertType(AbiInfo.getCoerceToType());
1038 CoercedType = getTypes().ConvertType(
Type);
1044 if (AbiInfo.isSignExt())
1046 if (AbiInfo.isZeroExt())
1050 case llvm::abi::ArgInfo::Indirect: {
1054 AbiInfo.getIndirectByVal(),
1055 AbiInfo.getIndirectRealign());
1057 case llvm::abi::ArgInfo::IndirectAliased: {
1059 CharUnits Alignment =
1062 AbiInfo.getIndirectAddrSpace(),
1063 AbiInfo.getIndirectRealign());
1065 case llvm::abi::ArgInfo::Ignore:
1068 llvm_unreachable(
"Unexpected llvm::abi::ArgInfo kind");
1079 assert(llvm::all_of(argTypes,
1083 llvm::FoldingSetNodeID ID;
1088 bool isDelegateCall =
1090 unsigned X86ABIAVXLevel = CGM.getABIInfo().getX86ABIAVXLevel(ABIInfoFD, info);
1094 paramInfos, required, resultType, argTypes);
1104 llvm::FoldingSetNodeID ID;
1106 X86ABIAVXLevel, info, paramInfos, required,
1107 resultType, argTypes);
1109 llvm::FoldingSetInsertToken InsertToken;
1114 unsigned CC = ClangCallConvToLLVMCallConv(info.getCC());
1118 X86ABIAVXLevel, info, paramInfos, resultType,
1119 argTypes, required);
1120 FunctionInfos.insert(FI, InsertToken);
1122 bool inserted = FunctionsBeingProcessed.insert(FI).second;
1124 assert(inserted &&
"Recursively being processed?");
1128 (CC == llvm::CallingConv::SPIR_KERNEL || CC == llvm::CallingConv::C)) {
1133 assert(CC != llvm::CallingConv::C || getContext().getLangOpts().
OpenCL);
1137 }
else if (CGM.shouldUseLLVMABILowering(CC)) {
1138 CGM.computeABIInfoUsingLib(*FI);
1140 CGM.getABIInfo().computeInfo(*FI);
1151 if (I.info.canHaveCoerceToType() && I.info.getCoerceToType() ==
nullptr)
1152 I.info.setCoerceToType(ConvertType(I.type));
1154 bool erased = FunctionsBeingProcessed.erase(FI);
1156 assert(erased &&
"Not in set?");
1162 unsigned llvmCC,
bool instanceMethod,
bool chainCall,
bool delegateCall,
1166 assert(paramInfos.empty() || paramInfos.size() == argTypes.size());
1170 void *buffer =
operator new(totalSizeToAlloc<ArgInfo, ExtParameterInfo>(
1171 argTypes.size() + 1, paramInfos.size()));
1173 CGFunctionInfo *FI =
new (buffer) CGFunctionInfo();
1174 FI->CallingConvention = llvmCC;
1175 FI->EffectiveCallingConvention = llvmCC;
1176 FI->ASTCallingConvention = info.getCC();
1177 FI->InstanceMethod = instanceMethod;
1178 FI->ChainCall = chainCall;
1179 FI->DelegateCall = delegateCall;
1180 FI->CmseNSCall = info.getCmseNSCall();
1181 FI->NoReturn = info.getNoReturn();
1182 FI->ReturnsRetained = info.getProducesResult();
1183 FI->NoCallerSavedRegs = info.getNoCallerSavedRegs();
1184 FI->NoCfCheck = info.getNoCfCheck();
1185 FI->Required = required;
1186 FI->HasRegParm = info.getHasRegParm();
1187 FI->RegParm = info.getRegParm();
1188 FI->X86ABIAVXLevel = X86ABIAVXLevel;
1189 FI->ArgStruct =
nullptr;
1190 FI->ArgStructAlign = 0;
1191 FI->NumArgs = argTypes.size();
1192 FI->HasExtParameterInfos = !paramInfos.empty();
1193 FI->getArgsBuffer()[0].
type = resultType;
1194 FI->MaxVectorWidth = 0;
1195 for (
unsigned i = 0, e = argTypes.size(); i != e; ++i)
1196 FI->getArgsBuffer()[i + 1].
type = argTypes[i];
1197 for (
unsigned i = 0, e = paramInfos.size(); i != e; ++i)
1198 FI->getExtParameterInfosBuffer()[i] = paramInfos[i];
1208struct TypeExpansion {
1209 enum TypeExpansionKind {
1221 const TypeExpansionKind Kind;
1223 TypeExpansion(TypeExpansionKind K) : Kind(K) {}
1224 virtual ~TypeExpansion() {}
1227struct ConstantArrayExpansion : TypeExpansion {
1231 ConstantArrayExpansion(QualType EltTy, uint64_t NumElts)
1232 : TypeExpansion(TEK_ConstantArray), EltTy(EltTy), NumElts(NumElts) {}
1233 static bool classof(
const TypeExpansion *TE) {
1234 return TE->Kind == TEK_ConstantArray;
1238struct RecordExpansion : TypeExpansion {
1239 SmallVector<const CXXBaseSpecifier *, 1> Bases;
1241 SmallVector<const FieldDecl *, 1> Fields;
1243 RecordExpansion(SmallVector<const CXXBaseSpecifier *, 1> &&Bases,
1244 SmallVector<const FieldDecl *, 1> &&Fields)
1245 : TypeExpansion(TEK_Record), Bases(std::move(Bases)),
1246 Fields(std::move(Fields)) {}
1247 static bool classof(
const TypeExpansion *TE) {
1248 return TE->Kind == TEK_Record;
1252struct ComplexExpansion : TypeExpansion {
1255 ComplexExpansion(QualType EltTy) : TypeExpansion(
TEK_Complex), EltTy(EltTy) {}
1256 static bool classof(
const TypeExpansion *TE) {
1261struct NoExpansion : TypeExpansion {
1262 NoExpansion() : TypeExpansion(TEK_None) {}
1263 static bool classof(
const TypeExpansion *TE) {
return TE->Kind == TEK_None; }
1267static std::unique_ptr<TypeExpansion>
1270 return std::make_unique<ConstantArrayExpansion>(AT->getElementType(),
1276 assert(!RD->hasFlexibleArrayMember() &&
1277 "Cannot expand structure with flexible array.");
1278 if (RD->isUnion()) {
1284 for (
const auto *FD : RD->fields()) {
1285 if (FD->isZeroLengthBitField())
1287 assert(!FD->isBitField() &&
1288 "Cannot expand structure with bit-field members.");
1289 CharUnits FieldSize = Context.getTypeSizeInChars(FD->getType());
1290 if (UnionSize < FieldSize) {
1291 UnionSize = FieldSize;
1296 Fields.push_back(LargestFD);
1298 if (
const auto *CXXRD = dyn_cast<CXXRecordDecl>(RD)) {
1299 assert(!CXXRD->isDynamicClass() &&
1300 "cannot expand vtable pointers in dynamic classes");
1301 llvm::append_range(Bases, llvm::make_pointer_range(CXXRD->bases()));
1304 for (
const auto *FD : RD->fields()) {
1305 if (FD->isZeroLengthBitField())
1307 assert(!FD->isBitField() &&
1308 "Cannot expand structure with bit-field members.");
1309 Fields.push_back(FD);
1312 return std::make_unique<RecordExpansion>(std::move(Bases),
1316 return std::make_unique<ComplexExpansion>(CT->getElementType());
1318 return std::make_unique<NoExpansion>();
1323 if (
auto CAExp = dyn_cast<ConstantArrayExpansion>(Exp.get())) {
1326 if (
auto RExp = dyn_cast<RecordExpansion>(Exp.get())) {
1328 for (
auto BS : RExp->Bases)
1330 for (
auto FD : RExp->Fields)
1343 if (
auto CAExp = dyn_cast<ConstantArrayExpansion>(Exp.get())) {
1344 for (
int i = 0, n = CAExp->NumElts; i < n; i++) {
1347 }
else if (
auto RExp = dyn_cast<RecordExpansion>(Exp.get())) {
1348 for (
auto BS : RExp->Bases)
1350 for (
auto FD : RExp->Fields)
1352 }
else if (
auto CExp = dyn_cast<ComplexExpansion>(Exp.get())) {
1363 ConstantArrayExpansion *CAE,
1365 llvm::function_ref<
void(
Address)> Fn) {
1366 for (
int i = 0, n = CAE->NumElts; i < n; i++) {
1372void CodeGenFunction::ExpandTypeFromArgs(QualType Ty, LValue LV,
1373 llvm::Function::arg_iterator &AI) {
1374 assert(LV.isSimple() &&
1375 "Unexpected non-simple lvalue during struct expansion.");
1378 if (
auto CAExp = dyn_cast<ConstantArrayExpansion>(Exp.get())) {
1380 *
this, CAExp, LV.getAddress(), [&](Address EltAddr) {
1381 LValue LV = MakeAddrLValue(EltAddr, CAExp->EltTy);
1382 ExpandTypeFromArgs(CAExp->EltTy, LV, AI);
1384 }
else if (
auto RExp = dyn_cast<RecordExpansion>(Exp.get())) {
1386 for (
const CXXBaseSpecifier *BS : RExp->Bases) {
1390 false, SourceLocation());
1391 LValue SubLV = MakeAddrLValue(Base, BS->
getType());
1394 ExpandTypeFromArgs(BS->
getType(), SubLV, AI);
1396 for (
auto FD : RExp->Fields) {
1398 LValue SubLV = EmitLValueForFieldInitialization(LV, FD);
1399 ExpandTypeFromArgs(FD->getType(), SubLV, AI);
1402 auto realValue = &*AI++;
1403 auto imagValue = &*AI++;
1404 EmitStoreOfComplex(
ComplexPairTy(realValue, imagValue), LV,
true);
1409 llvm::Value *Arg = &*AI++;
1410 if (LV.isBitField()) {
1416 if (Arg->getType()->isPointerTy()) {
1418 Arg = Builder.CreateBitCast(Arg,
Addr.getElementType());
1420 EmitStoreOfScalar(Arg, LV);
1425void CodeGenFunction::ExpandTypeToArgs(
1426 QualType Ty, CallArg Arg, llvm::FunctionType *IRFuncTy,
1427 SmallVectorImpl<llvm::Value *> &IRCallArgs,
unsigned &IRCallArgPos) {
1429 if (
auto CAExp = dyn_cast<ConstantArrayExpansion>(Exp.get())) {
1434 CallArg(convertTempToRValue(EltAddr, CAExp->EltTy, SourceLocation()),
1436 ExpandTypeToArgs(CAExp->EltTy, EltArg, IRFuncTy, IRCallArgs,
1439 }
else if (
auto RExp = dyn_cast<RecordExpansion>(Exp.get())) {
1442 for (
const CXXBaseSpecifier *BS : RExp->Bases) {
1446 false, SourceLocation());
1450 ExpandTypeToArgs(BS->
getType(), BaseArg, IRFuncTy, IRCallArgs,
1454 LValue LV = MakeAddrLValue(This, Ty);
1455 for (
auto FD : RExp->Fields) {
1457 CallArg(EmitRValueForField(LV, FD, SourceLocation()), FD->getType());
1458 ExpandTypeToArgs(FD->getType(), FldArg, IRFuncTy, IRCallArgs,
1463 IRCallArgs[IRCallArgPos++] = CV.first;
1464 IRCallArgs[IRCallArgPos++] = CV.second;
1468 assert(RV.isScalar() &&
1469 "Unexpected non-scalar rvalue during struct expansion.");
1472 llvm::Value *
V = RV.getScalarVal();
1473 if (IRCallArgPos < IRFuncTy->getNumParams() &&
1474 V->getType() != IRFuncTy->getParamType(IRCallArgPos))
1475 V = Builder.CreateBitCast(
V, IRFuncTy->getParamType(IRCallArgPos));
1477 IRCallArgs[IRCallArgPos++] =
V;
1485 const Twine &Name =
"tmp") {
1498 llvm::StructType *SrcSTy,
1502 if (SrcSTy->getNumElements() == 0)
1511 uint64_t FirstEltSize = CGF.
CGM.
getDataLayout().getTypeStoreSize(FirstElt);
1512 if (FirstEltSize < DstSize &&
1521 if (llvm::StructType *SrcSTy = dyn_cast<llvm::StructType>(SrcTy))
1536 if (Val->getType() == Ty)
1542 return CGF.
Builder.CreateBitCast(Val, Ty,
"coerce.val");
1548 llvm::Type *DestIntTy = Ty;
1552 if (Val->getType() != DestIntTy) {
1554 if (DL.isBigEndian()) {
1557 uint64_t SrcSize = DL.getTypeSizeInBits(Val->getType());
1558 uint64_t DstSize = DL.getTypeSizeInBits(DestIntTy);
1560 if (SrcSize > DstSize) {
1561 Val = CGF.
Builder.CreateLShr(Val, SrcSize - DstSize,
"coerce.highbits");
1562 Val = CGF.
Builder.CreateTrunc(Val, DestIntTy,
"coerce.val.ii");
1564 Val = CGF.
Builder.CreateZExt(Val, DestIntTy,
"coerce.val.ii");
1565 Val = CGF.
Builder.CreateShl(Val, DstSize - SrcSize,
"coerce.highbits");
1569 Val = CGF.
Builder.CreateIntCast(Val, DestIntTy,
false,
"coerce.val.ii");
1574 Val = CGF.
Builder.CreateIntToPtr(Val, Ty,
"coerce.val.ip");
1581 if (PFPFields.empty())
1584 auto LoadCoercedField = [&](
CharUnits Offset,
1585 llvm::Type *FieldType) -> llvm::Value * {
1590 if (!PFPFields.empty() && PFPFields[0].Offset == Offset) {
1594 FieldVal = CGF.
Builder.CreatePtrToInt(FieldVal, FieldType);
1595 PFPFields.erase(PFPFields.begin());
1612 Val = CGF.
Builder.CreatePtrToInt(Val, Ty);
1616 auto *ET = AT->getElementType();
1620 llvm::Value *Val = llvm::PoisonValue::get(AT);
1621 for (
unsigned Idx = 0; Idx != AT->getNumElements(); ++Idx, Offset += WordSize)
1622 Val = CGF.
Builder.CreateInsertValue(Val, LoadCoercedField(Offset, ET), Idx);
1646 if (llvm::StructType *SrcSTy = dyn_cast<llvm::StructType>(SrcTy)) {
1648 DstSize.getFixedValue(), CGF);
1663 if (!SrcSize.isScalable() && !DstSize.isScalable() &&
1664 SrcSize.getFixedValue() >= DstSize.getFixedValue()) {
1678 if (
auto *ScalableDstTy = dyn_cast<llvm::ScalableVectorType>(Ty)) {
1679 if (
auto *FixedSrcTy = dyn_cast<llvm::FixedVectorType>(SrcTy)) {
1682 if (ScalableDstTy->getElementType()->isIntegerTy(1) &&
1683 FixedSrcTy->getElementType()->isIntegerTy(8)) {
1684 ScalableDstTy = llvm::ScalableVectorType::get(
1685 FixedSrcTy->getElementType(),
1687 ScalableDstTy->getElementCount().getKnownMinValue(), 8));
1689 if (ScalableDstTy->getElementType() == FixedSrcTy->getElementType()) {
1691 auto *PoisonVec = llvm::PoisonValue::get(ScalableDstTy);
1693 ScalableDstTy, PoisonVec, Load, uint64_t(0),
"cast.scalable");
1695 llvm::VectorType::getWithSizeAndScalar(ScalableDstTy, Ty));
1696 if (
Result->getType() != ScalableDstTy)
1698 if (
Result->getType() != Ty)
1711 llvm::ConstantInt::get(CGF.
IntPtrTy, SrcSize.getKnownMinValue()));
1718 if (PFPFields.empty())
1721 llvm::Type *SrcTy = Src->getType();
1722 auto StoreCoercedField = [&](
CharUnits Offset, llvm::Value *FieldVal) {
1723 if (!PFPFields.empty() && PFPFields[0].Offset == Offset) {
1728 PFPFields.erase(PFPFields.begin());
1748 auto *ET = AT->getElementType();
1752 for (
unsigned i = 0; i != AT->getNumElements(); ++i, Offset += WordSize)
1753 StoreCoercedField(Offset, CGF.
Builder.CreateExtractValue(Src, i));
1759 Address Dst, llvm::TypeSize DstSize,
1760 bool DstIsVolatile) {
1764 llvm::Type *SrcTy = Src->getType();
1765 llvm::TypeSize SrcSize =
CGM.getDataLayout().getTypeAllocSize(SrcTy);
1771 if (llvm::StructType *DstSTy =
1773 assert(!SrcSize.isScalable());
1775 SrcSize.getFixedValue(), *
this);
1782 if (SrcSize.isScalable() || SrcSize <= DstSize) {
1783 if (SrcTy->isIntegerTy() && Dst.
getElementType()->isPointerTy() &&
1787 auto *I =
Builder.CreateStore(Src, Dst, DstIsVolatile);
1789 }
else if (llvm::StructType *STy =
1790 dyn_cast<llvm::StructType>(Src->getType())) {
1793 for (
unsigned i = 0, e = STy->getNumElements(); i != e; ++i) {
1795 llvm::Value *Elt =
Builder.CreateExtractValue(Src, i);
1796 auto *I =
Builder.CreateStore(Elt, EltPtr, DstIsVolatile);
1804 }
else if (SrcTy->isIntegerTy()) {
1806 llvm::Type *DstIntTy =
Builder.getIntNTy(DstSize.getFixedValue() * 8);
1823 Builder.CreateStore(Src, Tmp);
1824 auto *I =
Builder.CreateMemCpy(
1834 if (
unsigned offset = info.getDirectOffset()) {
1843static std::pair<llvm::Value *, bool>
1845 llvm::ScalableVectorType *FromTy, llvm::Value *
V,
1846 StringRef Name =
"") {
1849 if (FromTy->getElementType()->isIntegerTy(1) &&
1850 ToTy->getElementType() == CGF.
Builder.getInt8Ty()) {
1851 if (!FromTy->getElementCount().isKnownMultipleOf(8)) {
1852 FromTy = llvm::ScalableVectorType::get(
1853 FromTy->getElementType(),
1854 llvm::alignTo<8>(FromTy->getElementCount().getKnownMinValue()));
1855 llvm::Value *ZeroVec = llvm::Constant::getNullValue(FromTy);
1856 V = CGF.
Builder.CreateInsertVector(FromTy, ZeroVec,
V, uint64_t(0));
1858 FromTy = llvm::ScalableVectorType::get(
1859 ToTy->getElementType(),
1860 FromTy->getElementCount().getKnownMinValue() / 8);
1861 V = CGF.
Builder.CreateBitCast(
V, FromTy);
1863 if (FromTy->getElementType() == ToTy->getElementType()) {
1864 V->setName(Name +
".coerce");
1865 V = CGF.
Builder.CreateExtractVector(ToTy,
V, uint64_t(0),
"cast.fixed");
1875class ClangToLLVMArgMapping {
1876 static const unsigned InvalidIndex = ~0U;
1877 unsigned InallocaArgNo;
1879 unsigned TotalIRArgs;
1883 unsigned PaddingArgIndex;
1886 unsigned FirstArgIndex;
1887 unsigned NumberOfArgs;
1890 : PaddingArgIndex(InvalidIndex), FirstArgIndex(InvalidIndex),
1894 SmallVector<IRArgs, 8> ArgInfo;
1897 ClangToLLVMArgMapping(
const ASTContext &Context,
const CGFunctionInfo &FI,
1898 bool OnlyRequiredArgs =
false)
1899 : InallocaArgNo(InvalidIndex), SRetArgNo(InvalidIndex), TotalIRArgs(0),
1900 ArgInfo(OnlyRequiredArgs ? FI.getNumRequiredArgs() : FI.arg_size()) {
1901 construct(Context, FI, OnlyRequiredArgs);
1904 bool hasInallocaArg()
const {
return InallocaArgNo != InvalidIndex; }
1905 unsigned getInallocaArgNo()
const {
1906 assert(hasInallocaArg());
1907 return InallocaArgNo;
1910 bool hasSRetArg()
const {
return SRetArgNo != InvalidIndex; }
1911 unsigned getSRetArgNo()
const {
1912 assert(hasSRetArg());
1916 unsigned totalIRArgs()
const {
return TotalIRArgs; }
1918 bool hasPaddingArg(
unsigned ArgNo)
const {
1919 assert(ArgNo < ArgInfo.size());
1920 return ArgInfo[ArgNo].PaddingArgIndex != InvalidIndex;
1922 unsigned getPaddingArgNo(
unsigned ArgNo)
const {
1923 assert(hasPaddingArg(ArgNo));
1924 return ArgInfo[ArgNo].PaddingArgIndex;
1929 std::pair<unsigned, unsigned> getIRArgs(
unsigned ArgNo)
const {
1930 assert(ArgNo < ArgInfo.size());
1931 return std::make_pair(ArgInfo[ArgNo].FirstArgIndex,
1932 ArgInfo[ArgNo].NumberOfArgs);
1936 void construct(
const ASTContext &Context,
const CGFunctionInfo &FI,
1937 bool OnlyRequiredArgs);
1940void ClangToLLVMArgMapping::construct(
const ASTContext &Context,
1941 const CGFunctionInfo &FI,
1942 bool OnlyRequiredArgs) {
1943 unsigned IRArgNo = 0;
1944 bool SwapThisWithSRet =
false;
1949 SRetArgNo = SwapThisWithSRet ? 1 : IRArgNo++;
1957 QualType ArgType = I->type;
1958 const ABIArgInfo &AI = I->info;
1960 auto &IRArgs = ArgInfo[ArgNo];
1963 IRArgs.PaddingArgIndex = IRArgNo++;
1970 llvm::StructType *STy = dyn_cast<llvm::StructType>(AI.
getCoerceToType());
1972 IRArgs.NumberOfArgs = STy->getNumElements();
1974 IRArgs.NumberOfArgs = 1;
1980 IRArgs.NumberOfArgs = 1;
1985 IRArgs.NumberOfArgs = 0;
1995 if (IRArgs.NumberOfArgs > 0) {
1996 IRArgs.FirstArgIndex = IRArgNo;
1997 IRArgNo += IRArgs.NumberOfArgs;
2002 if (IRArgNo == 1 && SwapThisWithSRet)
2005 assert(ArgNo == ArgInfo.size());
2008 InallocaArgNo = IRArgNo++;
2010 TotalIRArgs = IRArgNo;
2018 return RI.
isIndirect() || (RI.isInAlloca() && RI.getInAllocaSRet());
2033 switch (BT->getKind()) {
2036 case BuiltinType::Float:
2038 case BuiltinType::Double:
2040 case BuiltinType::LongDouble:
2051 if (BT->getKind() == BuiltinType::LongDouble)
2052 return getTarget().useObjCFP2RetForComplexLongDouble();
2066 bool Inserted = FunctionsBeingProcessed.insert(&FI).second;
2068 assert(Inserted &&
"Recursively being processed?");
2070 llvm::Type *resultType =
nullptr;
2075 llvm_unreachable(
"Invalid ABI kind for return argument");
2087 unsigned addressSpace = CGM.getTypes().getTargetAddressSpace(ret);
2088 resultType = llvm::PointerType::get(
getLLVMContext(), addressSpace);
2104 ClangToLLVMArgMapping IRFunctionArgs(
getContext(), FI,
true);
2108 if (IRFunctionArgs.hasSRetArg()) {
2109 ArgTypes[IRFunctionArgs.getSRetArgNo()] = llvm::PointerType::get(
2114 if (IRFunctionArgs.hasInallocaArg())
2115 ArgTypes[IRFunctionArgs.getInallocaArgNo()] =
2122 for (; it != ie; ++it, ++ArgNo) {
2126 if (IRFunctionArgs.hasPaddingArg(ArgNo))
2127 ArgTypes[IRFunctionArgs.getPaddingArgNo(ArgNo)] =
2130 unsigned FirstIRArg, NumIRArgs;
2131 std::tie(FirstIRArg, NumIRArgs) = IRFunctionArgs.getIRArgs(ArgNo);
2136 assert(NumIRArgs == 0);
2140 assert(NumIRArgs == 1);
2142 ArgTypes[FirstIRArg] = llvm::PointerType::get(
2146 assert(NumIRArgs == 1);
2147 ArgTypes[FirstIRArg] = llvm::PointerType::get(
2156 llvm::StructType *st = dyn_cast<llvm::StructType>(argType);
2158 assert(NumIRArgs == st->getNumElements());
2159 for (
unsigned i = 0, e = st->getNumElements(); i != e; ++i)
2160 ArgTypes[FirstIRArg + i] = st->getElementType(i);
2162 assert(NumIRArgs == 1);
2163 ArgTypes[FirstIRArg] = argType;
2169 auto ArgTypesIter = ArgTypes.begin() + FirstIRArg;
2171 *ArgTypesIter++ = EltTy;
2173 assert(ArgTypesIter == ArgTypes.begin() + FirstIRArg + NumIRArgs);
2178 auto ArgTypesIter = ArgTypes.begin() + FirstIRArg;
2180 assert(ArgTypesIter == ArgTypes.begin() + FirstIRArg + NumIRArgs);
2185 bool Erased = FunctionsBeingProcessed.erase(&FI);
2187 assert(Erased &&
"Not in set?");
2189 return llvm::FunctionType::get(resultType, ArgTypes, FI.
isVariadic());
2203 llvm::AttrBuilder &FuncAttrs,
2210 FuncAttrs.addAttribute(llvm::Attribute::NoUnwind);
2214 FuncAttrs.addAttribute(
"aarch64_pstate_sm_enabled");
2216 FuncAttrs.addAttribute(
"aarch64_pstate_sm_compatible");
2218 FuncAttrs.addAttribute(
"aarch64_za_state_agnostic");
2222 FuncAttrs.addAttribute(
"aarch64_preserves_za");
2224 FuncAttrs.addAttribute(
"aarch64_in_za");
2226 FuncAttrs.addAttribute(
"aarch64_out_za");
2228 FuncAttrs.addAttribute(
"aarch64_inout_za");
2232 FuncAttrs.addAttribute(
"aarch64_preserves_zt0");
2234 FuncAttrs.addAttribute(
"aarch64_in_zt0");
2236 FuncAttrs.addAttribute(
"aarch64_out_zt0");
2238 FuncAttrs.addAttribute(
"aarch64_inout_zt0");
2242 const Decl *Callee) {
2248 for (
const OMPAssumeAttr *AA : Callee->specific_attrs<OMPAssumeAttr>())
2249 AA->getAssumption().split(Attrs,
",");
2252 FuncAttrs.addAttribute(llvm::AssumptionAttrKey,
2253 llvm::join(Attrs.begin(), Attrs.end(),
","));
2260 if (
const RecordType *RT =
2262 if (
const auto *ClassDecl = dyn_cast<CXXRecordDecl>(RT->getDecl()))
2263 return ClassDecl->hasTrivialDestructor();
2269 const Decl *TargetDecl) {
2275 if (
Module.getLangOpts().Sanitize.has(SanitizerKind::Memory))
2279 if (!
Module.getLangOpts().CPlusPlus)
2282 if (
const FunctionDecl *FDecl = dyn_cast<FunctionDecl>(TargetDecl)) {
2283 if (FDecl->isExternC())
2285 }
else if (
const VarDecl *VDecl = dyn_cast<VarDecl>(TargetDecl)) {
2287 if (VDecl->isExternC())
2295 return Module.getCodeGenOpts().StrictReturn ||
2296 !
Module.MayDropFunctionReturn(
Module.getContext(), RetTy) ||
2297 Module.getLangOpts().Sanitize.has(SanitizerKind::Return);
2304 llvm::DenormalMode FP32DenormalMode,
2305 llvm::AttrBuilder &FuncAttrs) {
2306 llvm::DenormalFPEnv FPEnv(FPDenormalMode, FP32DenormalMode);
2307 if (FPEnv != llvm::DenormalFPEnv::getDefault())
2308 FuncAttrs.addDenormalFPEnvAttr(FPEnv);
2316 llvm::AttrBuilder &FuncAttrs) {
2322 StringRef Name,
bool HasOptnone,
const CodeGenOptions &CodeGenOpts,
2324 llvm::AttrBuilder &FuncAttrs) {
2327 if (CodeGenOpts.OptimizeSize)
2328 FuncAttrs.addAttribute(llvm::Attribute::OptimizeForSize);
2329 if (CodeGenOpts.OptimizeSize == 2)
2330 FuncAttrs.addAttribute(llvm::Attribute::MinSize);
2333 if (CodeGenOpts.DisableRedZone)
2334 FuncAttrs.addAttribute(llvm::Attribute::NoRedZone);
2335 if (CodeGenOpts.IndirectTlsSegRefs)
2336 FuncAttrs.addAttribute(
"indirect-tls-seg-refs");
2337 if (CodeGenOpts.NoImplicitFloat)
2338 FuncAttrs.addAttribute(llvm::Attribute::NoImplicitFloat);
2340 if (AttrOnCallSite) {
2345 FuncAttrs.addAttribute(llvm::Attribute::NoBuiltin);
2347 FuncAttrs.addAttribute(
"trap-func-name", CodeGenOpts.
TrapFuncName);
2349 switch (CodeGenOpts.getFramePointer()) {
2357 FuncAttrs.addAttribute(
"frame-pointer",
2359 CodeGenOpts.getFramePointer()));
2362 if (CodeGenOpts.LessPreciseFPMAD)
2363 FuncAttrs.addAttribute(
"less-precise-fpmad",
"true");
2365 if (CodeGenOpts.NullPointerIsValid)
2366 FuncAttrs.addAttribute(llvm::Attribute::NullPointerIsValid);
2369 FuncAttrs.addAttribute(
"no-trapping-math",
"true");
2373 if (CodeGenOpts.SoftFloat)
2374 FuncAttrs.addAttribute(
"use-soft-float",
"true");
2375 FuncAttrs.addAttribute(
"stack-protector-buffer-size",
2376 llvm::utostr(CodeGenOpts.SSPBufferSize));
2377 if (LangOpts.NoSignedZero)
2378 FuncAttrs.addAttribute(
"no-signed-zeros-fp-math",
"true");
2381 const std::vector<std::string> &Recips = CodeGenOpts.
Reciprocals;
2382 if (!Recips.empty())
2383 FuncAttrs.addAttribute(
"reciprocal-estimates", llvm::join(Recips,
","));
2387 FuncAttrs.addAttribute(
"prefer-vector-width",
2390 if (CodeGenOpts.StackRealignment)
2391 FuncAttrs.addAttribute(
"stackrealign");
2392 if (CodeGenOpts.Backchain)
2393 FuncAttrs.addAttribute(
"backchain");
2394 if (CodeGenOpts.EnableSegmentedStacks)
2395 FuncAttrs.addAttribute(
"split-stack");
2397 if (CodeGenOpts.SpeculativeLoadHardening)
2398 FuncAttrs.addAttribute(llvm::Attribute::SpeculativeLoadHardening);
2401 switch (CodeGenOpts.getZeroCallUsedRegs()) {
2402 case llvm::ZeroCallUsedRegs::ZeroCallUsedRegsKind::Skip:
2403 FuncAttrs.removeAttribute(
"zero-call-used-regs");
2405 case llvm::ZeroCallUsedRegs::ZeroCallUsedRegsKind::UsedGPRArg:
2406 FuncAttrs.addAttribute(
"zero-call-used-regs",
"used-gpr-arg");
2408 case llvm::ZeroCallUsedRegs::ZeroCallUsedRegsKind::UsedGPR:
2409 FuncAttrs.addAttribute(
"zero-call-used-regs",
"used-gpr");
2411 case llvm::ZeroCallUsedRegs::ZeroCallUsedRegsKind::UsedArg:
2412 FuncAttrs.addAttribute(
"zero-call-used-regs",
"used-arg");
2414 case llvm::ZeroCallUsedRegs::ZeroCallUsedRegsKind::Used:
2415 FuncAttrs.addAttribute(
"zero-call-used-regs",
"used");
2417 case llvm::ZeroCallUsedRegs::ZeroCallUsedRegsKind::AllGPRArg:
2418 FuncAttrs.addAttribute(
"zero-call-used-regs",
"all-gpr-arg");
2420 case llvm::ZeroCallUsedRegs::ZeroCallUsedRegsKind::AllGPR:
2421 FuncAttrs.addAttribute(
"zero-call-used-regs",
"all-gpr");
2423 case llvm::ZeroCallUsedRegs::ZeroCallUsedRegsKind::AllArg:
2424 FuncAttrs.addAttribute(
"zero-call-used-regs",
"all-arg");
2426 case llvm::ZeroCallUsedRegs::ZeroCallUsedRegsKind::All:
2427 FuncAttrs.addAttribute(
"zero-call-used-regs",
"all");
2438 FuncAttrs.addAttribute(llvm::Attribute::Convergent);
2443 if ((LangOpts.CUDA && LangOpts.CUDAIsDevice) || LangOpts.OpenCL ||
2444 LangOpts.SYCLIsDevice) {
2445 FuncAttrs.addAttribute(llvm::Attribute::NoUnwind);
2448 if (CodeGenOpts.SaveRegParams && !AttrOnCallSite)
2449 FuncAttrs.addAttribute(
"save-reg-params");
2452 StringRef Var,
Value;
2454 FuncAttrs.addAttribute(Var,
Value);
2468 const llvm::Function &F,
2470 auto FFeatures = F.getFnAttribute(
"target-features");
2472 llvm::StringSet<> MergedNames;
2474 MergedFeatures.reserve(TargetOpts.
Features.size());
2476 auto AddUnmergedFeatures = [&](
auto &&FeatureRange) {
2477 for (StringRef
Feature : FeatureRange) {
2481 StringRef Name =
Feature.drop_front(1);
2482 bool Merged = !MergedNames.insert(Name).second;
2484 MergedFeatures.push_back(
Feature);
2488 if (FFeatures.isValid())
2489 AddUnmergedFeatures(llvm::split(FFeatures.getValueAsString(),
','));
2490 AddUnmergedFeatures(TargetOpts.
Features);
2492 if (!MergedFeatures.empty()) {
2493 llvm::sort(MergedFeatures);
2494 FuncAttr.addAttribute(
"target-features", llvm::join(MergedFeatures,
","));
2501 bool WillInternalize) {
2503 llvm::AttrBuilder FuncAttrs(F.getContext());
2506 if (!TargetOpts.
CPU.empty())
2507 FuncAttrs.addAttribute(
"target-cpu", TargetOpts.
CPU);
2508 if (!TargetOpts.
TuneCPU.empty())
2509 FuncAttrs.addAttribute(
"tune-cpu", TargetOpts.
TuneCPU);
2512 CodeGenOpts, LangOpts,
2515 if (!WillInternalize && F.isInterposable()) {
2520 F.addFnAttrs(FuncAttrs);
2524 llvm::AttributeMask AttrsToRemove;
2528 llvm::DenormalFPEnv MergedFPEnv =
2529 OptsFPEnv.mergeCalleeMode(F.getDenormalFPEnv());
2531 if (MergedFPEnv == llvm::DenormalFPEnv::getDefault()) {
2532 AttrsToRemove.addAttribute(llvm::Attribute::DenormalFPEnv);
2535 FuncAttrs.addDenormalFPEnvAttr(MergedFPEnv);
2538 F.removeFnAttrs(AttrsToRemove);
2542 F.addFnAttrs(FuncAttrs);
2545void CodeGenModule::getTrivialDefaultFunctionAttributes(
2546 StringRef Name,
bool HasOptnone,
bool AttrOnCallSite,
2547 llvm::AttrBuilder &FuncAttrs) {
2549 getLangOpts(), AttrOnCallSite,
2553void CodeGenModule::getDefaultFunctionAttributes(StringRef Name,
2555 bool AttrOnCallSite,
2556 llvm::AttrBuilder &FuncAttrs) {
2560 if (!AttrOnCallSite)
2566 if (!AttrOnCallSite)
2571 llvm::AttrBuilder &attrs) {
2572 getDefaultFunctionAttributes(
"",
false,
2574 GetCPUAndFeaturesAttributes(
GlobalDecl(), attrs);
2579 const NoBuiltinAttr *NBA =
nullptr) {
2580 auto AddNoBuiltinAttr = [&FuncAttrs](StringRef BuiltinName) {
2582 AttributeName +=
"no-builtin-";
2583 AttributeName += BuiltinName;
2584 FuncAttrs.addAttribute(AttributeName);
2588 if (LangOpts.NoBuiltin) {
2590 FuncAttrs.addAttribute(
"no-builtins");
2604 if (llvm::is_contained(NBA->builtinNames(),
"*")) {
2605 FuncAttrs.addAttribute(
"no-builtins");
2610 llvm::for_each(NBA->builtinNames(), AddNoBuiltinAttr);
2614 const llvm::DataLayout &DL,
const ABIArgInfo &AI,
2615 bool CheckCoerce =
true) {
2622 if (!DL.typeSizeEqualsStoreSize(Ty))
2629 if (llvm::TypeSize::isKnownGT(DL.getTypeSizeInBits(CoerceTy),
2630 DL.getTypeSizeInBits(Ty)))
2654 if (
const MatrixType *Matrix = dyn_cast<MatrixType>(QTy))
2665 unsigned NumRequiredArgs,
unsigned ArgNo) {
2666 const auto *FD = dyn_cast_or_null<FunctionDecl>(TargetDecl);
2671 if (ArgNo >= NumRequiredArgs)
2675 if (ArgNo < FD->getNumParams()) {
2676 const ParmVarDecl *Param = FD->getParamDecl(ArgNo);
2677 if (Param && Param->hasAttr<MaybeUndefAttr>())
2694 if (llvm::AttributeFuncs::isNoFPClassCompatibleType(IRTy))
2697 if (llvm::StructType *ST = dyn_cast<llvm::StructType>(IRTy)) {
2699 llvm::all_of(ST->elements(),
2700 llvm::AttributeFuncs::isNoFPClassCompatibleType);
2708 llvm::AttributeList &Attrs) {
2709 if (Attrs.getMemoryEffects().getModRef() == llvm::ModRefInfo::NoModRef) {
2710 Attrs = Attrs.removeFnAttribute(
getLLVMContext(), llvm::Attribute::Memory);
2711 llvm::Attribute MemoryAttr = llvm::Attribute::getWithMemoryEffects(
2737 llvm::AttributeList &AttrList,
2739 bool AttrOnCallSite,
bool IsThunk) {
2747 FuncAttrs.addAttribute(llvm::Attribute::NoReturn);
2749 FuncAttrs.addAttribute(
"cmse_nonsecure_call");
2760 bool HasOptnone =
false;
2762 const NoBuiltinAttr *NBA =
nullptr;
2766 std::optional<llvm::Attribute::AttrKind> MemAttrForPtrArgs;
2767 bool AddedPotentialArgAccess =
false;
2768 auto AddPotentialArgAccess = [&]() {
2769 AddedPotentialArgAccess =
true;
2770 llvm::Attribute A = FuncAttrs.getAttribute(llvm::Attribute::Memory);
2772 FuncAttrs.addMemoryAttr(A.getMemoryEffects() |
2773 llvm::MemoryEffects::argMemOnly());
2780 if (TargetDecl->
hasAttr<ReturnsTwiceAttr>())
2781 FuncAttrs.addAttribute(llvm::Attribute::ReturnsTwice);
2782 if (TargetDecl->
hasAttr<NoThrowAttr>())
2783 FuncAttrs.addAttribute(llvm::Attribute::NoUnwind);
2784 if (TargetDecl->
hasAttr<NoReturnAttr>())
2785 FuncAttrs.addAttribute(llvm::Attribute::NoReturn);
2786 if (TargetDecl->
hasAttr<ColdAttr>())
2787 FuncAttrs.addAttribute(llvm::Attribute::Cold);
2788 if (TargetDecl->
hasAttr<HotAttr>())
2789 FuncAttrs.addAttribute(llvm::Attribute::Hot);
2790 if (TargetDecl->
hasAttr<NoDuplicateAttr>())
2791 FuncAttrs.addAttribute(llvm::Attribute::NoDuplicate);
2792 if (TargetDecl->
hasAttr<ConvergentAttr>())
2793 FuncAttrs.addAttribute(llvm::Attribute::Convergent);
2795 if (
const FunctionDecl *Fn = dyn_cast<FunctionDecl>(TargetDecl)) {
2798 if (AttrOnCallSite && Fn->isReplaceableGlobalAllocationFunction()) {
2801 Fn->getDeclName().isAnyOperatorNew())
2802 RetAttrs.addAttribute(llvm::Attribute::NoAlias);
2805 const bool IsVirtualCall = MD && MD->
isVirtual();
2808 if (!(AttrOnCallSite && IsVirtualCall)) {
2809 if (Fn->isNoReturn())
2810 FuncAttrs.addAttribute(llvm::Attribute::NoReturn);
2811 NBA = Fn->getAttr<NoBuiltinAttr>();
2818 if (AttrOnCallSite && TargetDecl->
hasAttr<NoMergeAttr>())
2819 FuncAttrs.addAttribute(llvm::Attribute::NoMerge);
2823 if (TargetDecl->
hasAttr<ConstAttr>()) {
2824 FuncAttrs.addMemoryAttr(llvm::MemoryEffects::none());
2825 FuncAttrs.addAttribute(llvm::Attribute::NoUnwind);
2828 FuncAttrs.addAttribute(llvm::Attribute::WillReturn);
2829 MemAttrForPtrArgs = llvm::Attribute::ReadNone;
2830 }
else if (TargetDecl->
hasAttr<PureAttr>()) {
2831 FuncAttrs.addMemoryAttr(llvm::MemoryEffects::readOnly());
2832 FuncAttrs.addAttribute(llvm::Attribute::NoUnwind);
2834 FuncAttrs.addAttribute(llvm::Attribute::WillReturn);
2835 MemAttrForPtrArgs = llvm::Attribute::ReadOnly;
2836 }
else if (TargetDecl->
hasAttr<NoAliasAttr>()) {
2837 FuncAttrs.addMemoryAttr(llvm::MemoryEffects::inaccessibleOrArgMemOnly());
2838 FuncAttrs.addAttribute(llvm::Attribute::NoUnwind);
2840 if (
const auto *RA = TargetDecl->
getAttr<RestrictAttr>();
2841 RA && RA->getDeallocator() ==
nullptr)
2842 RetAttrs.addAttribute(llvm::Attribute::NoAlias);
2843 if (TargetDecl->
hasAttr<ReturnsNonNullAttr>() &&
2844 !CodeGenOpts.NullPointerIsValid)
2845 RetAttrs.addAttribute(llvm::Attribute::NonNull);
2846 if (TargetDecl->
hasAttr<AnyX86NoCallerSavedRegistersAttr>())
2847 FuncAttrs.addAttribute(
"no_caller_saved_registers");
2848 if (TargetDecl->
hasAttr<AnyX86NoCfCheckAttr>())
2849 FuncAttrs.addAttribute(llvm::Attribute::NoCfCheck);
2850 if (TargetDecl->
hasAttr<LeafAttr>())
2851 FuncAttrs.addAttribute(llvm::Attribute::NoCallback);
2852 if (TargetDecl->
hasAttr<BPFFastCallAttr>())
2853 FuncAttrs.addAttribute(
"bpf_fastcall");
2855 HasOptnone = TargetDecl->
hasAttr<OptimizeNoneAttr>();
2856 if (
auto *AllocSize = TargetDecl->
getAttr<AllocSizeAttr>()) {
2857 std::optional<unsigned> NumElemsParam;
2858 if (AllocSize->getNumElemsParam().isValid())
2859 NumElemsParam = AllocSize->getNumElemsParam().getLLVMIndex();
2860 FuncAttrs.addAllocSizeAttr(AllocSize->getElemSizeParam().getLLVMIndex(),
2870 FuncAttrs.addAttribute(
"uniform-work-group-size");
2872 if (TargetDecl->
hasAttr<ArmLocallyStreamingAttr>())
2873 FuncAttrs.addAttribute(
"aarch64_pstate_sm_body");
2875 if (
auto *ModularFormat = TargetDecl->
getAttr<ModularFormatAttr>()) {
2876 FormatAttr *Format = TargetDecl->
getAttr<FormatAttr>();
2877 StringRef
Type = Format->getType()->getName();
2878 std::string FormatIdx = std::to_string(Format->getFormatIdx());
2879 std::string FirstArg = std::to_string(Format->getFirstArg());
2881 Type, FormatIdx, FirstArg,
2882 ModularFormat->getModularImplFn()->getName(),
2883 ModularFormat->getImplName()};
2884 llvm::append_range(Args, ModularFormat->aspects());
2885 FuncAttrs.addAttribute(
"modular-format", llvm::join(Args,
","));
2898 getDefaultFunctionAttributes(Name, HasOptnone, AttrOnCallSite, FuncAttrs);
2903 if (TargetDecl->
hasAttr<NoSpeculativeLoadHardeningAttr>())
2904 FuncAttrs.removeAttribute(llvm::Attribute::SpeculativeLoadHardening);
2905 if (TargetDecl->
hasAttr<SpeculativeLoadHardeningAttr>())
2906 FuncAttrs.addAttribute(llvm::Attribute::SpeculativeLoadHardening);
2907 if (TargetDecl->
hasAttr<NoSplitStackAttr>())
2908 FuncAttrs.removeAttribute(
"split-stack");
2909 if (TargetDecl->
hasAttr<ZeroCallUsedRegsAttr>()) {
2912 TargetDecl->
getAttr<ZeroCallUsedRegsAttr>()->getZeroCallUsedRegs();
2913 FuncAttrs.removeAttribute(
"zero-call-used-regs");
2914 FuncAttrs.addAttribute(
2915 "zero-call-used-regs",
2916 ZeroCallUsedRegsAttr::ConvertZeroCallUsedRegsKindToStr(Kind));
2923 if (CodeGenOpts.NoPLT) {
2924 if (
auto *Fn = dyn_cast<FunctionDecl>(TargetDecl)) {
2925 if (!Fn->isDefined() && !AttrOnCallSite) {
2926 FuncAttrs.addAttribute(llvm::Attribute::NonLazyBind);
2931 if (TargetDecl->
hasAttr<NoConvergentAttr>())
2932 FuncAttrs.removeAttribute(llvm::Attribute::Convergent);
2937 if (TargetDecl && CodeGenOpts.UniqueInternalLinkageNames) {
2938 if (
const auto *FD = dyn_cast_or_null<FunctionDecl>(TargetDecl)) {
2939 if (!FD->isExternallyVisible())
2940 FuncAttrs.addAttribute(
"sample-profile-suffix-elision-policy",
2947 if (!AttrOnCallSite) {
2948 if (TargetDecl && TargetDecl->
hasAttr<CmseNSEntryAttr>())
2949 FuncAttrs.addAttribute(
"cmse_nonsecure_entry");
2952 auto shouldDisableTailCalls = [&] {
2954 if (CodeGenOpts.DisableTailCalls)
2960 if (TargetDecl->
hasAttr<DisableTailCallsAttr>() ||
2961 TargetDecl->
hasAttr<AnyX86InterruptAttr>())
2964 if (CodeGenOpts.NoEscapingBlockTailCalls) {
2965 if (
const auto *BD = dyn_cast<BlockDecl>(TargetDecl))
2966 if (!BD->doesNotEscape())
2972 if (shouldDisableTailCalls())
2973 FuncAttrs.addAttribute(
"disable-tail-calls",
"true");
2978 static const llvm::StringSet<> ReturnsTwiceFn{
2979 "_setjmpex",
"setjmp",
"_setjmp",
"vfork",
2980 "sigsetjmp",
"__sigsetjmp",
"savectx",
"getcontext"};
2981 if (ReturnsTwiceFn.contains(Name))
2982 FuncAttrs.addAttribute(llvm::Attribute::ReturnsTwice);
2986 GetCPUAndFeaturesAttributes(CalleeInfo.
getCalleeDecl(), FuncAttrs);
2989 if (!MSHotPatchFunctions.empty()) {
2990 bool IsHotPatched = llvm::binary_search(MSHotPatchFunctions, Name);
2992 FuncAttrs.addAttribute(
"marked_for_windows_hot_patching");
2997 if (CodeGenOpts.isLoaderReplaceableFunctionName(Name))
2998 FuncAttrs.addAttribute(
"loader-replaceable");
3001 ClangToLLVMArgMapping IRFunctionArgs(
getContext(), FI);
3008 if (CodeGenOpts.EnableNoundefAttrs &&
3012 RetAttrs.addAttribute(llvm::Attribute::NoUndef);
3018 RetAttrs.addAttribute(llvm::Attribute::SExt);
3020 RetAttrs.addAttribute(llvm::Attribute::ZExt);
3022 RetAttrs.addAttribute(llvm::Attribute::NoExt);
3027 RetAttrs.addAttribute(llvm::Attribute::InReg);
3030 RetAttrs.addNoFPClassAttr(
3040 AddPotentialArgAccess();
3049 llvm_unreachable(
"Invalid ABI kind for return argument");
3057 RetAttrs.addDereferenceableAttr(
3059 if (
getTypes().getTargetAddressSpace(PTy) == 0 &&
3060 !CodeGenOpts.NullPointerIsValid)
3061 RetAttrs.addAttribute(llvm::Attribute::NonNull);
3063 llvm::Align Alignment =
3065 RetAttrs.addAlignmentAttr(Alignment);
3070 bool hasUsedSRet =
false;
3072 for (
unsigned I = 0; I < IRFunctionArgs.totalIRArgs(); ++I)
3076 if (IRFunctionArgs.hasSRetArg()) {
3077 llvm::AttrBuilder &SRETAttrs = ArgAttrs[IRFunctionArgs.getSRetArgNo()];
3078 SRETAttrs.addStructRetAttr(
getTypes().ConvertTypeForMem(RetTy));
3079 SRETAttrs.addAttribute(llvm::Attribute::Writable);
3080 SRETAttrs.addAttribute(llvm::Attribute::DeadOnUnwind);
3083 SRETAttrs.addAttribute(llvm::Attribute::InReg);
3088 if (IRFunctionArgs.hasInallocaArg()) {
3089 ArgAttrs[IRFunctionArgs.getInallocaArgNo()].addInAllocaAttr(
3099 auto IRArgs = IRFunctionArgs.getIRArgs(0);
3101 assert(IRArgs.second == 1 &&
"Expected only a single `this` pointer.");
3103 llvm::AttrBuilder &Attrs = ArgAttrs[IRArgs.first];
3108 if (!CodeGenOpts.NullPointerIsValid &&
3110 Attrs.addAttribute(llvm::Attribute::NonNull);
3111 Attrs.addDereferenceableAttr(ThisSz);
3117 Attrs.addDereferenceableOrNullAttr(ThisSz);
3120 llvm::Align Alignment =
3124 Attrs.addAlignmentAttr(Alignment);
3126 const auto *DD = dyn_cast_if_present<CXXDestructorDecl>(
3140 CodeGenOpts.StrictLifetimes) {
3142 dyn_cast<CXXRecordDecl>(DD->getDeclContext());
3146 Attrs.addDeadOnReturnAttr(llvm::DeadOnReturnInfo(
3147 Context.getASTRecordLayout(ClassDecl).getDataSize().getQuantity()));
3153 I != E; ++I, ++ArgNo) {
3159 if (IRFunctionArgs.hasPaddingArg(ArgNo)) {
3161 ArgAttrs[IRFunctionArgs.getPaddingArgNo(ArgNo)].addAttribute(
3162 llvm::Attribute::InReg);
3167 if (CodeGenOpts.EnableNoundefAttrs &&
3169 Attrs.addAttribute(llvm::Attribute::NoUndef);
3178 Attrs.addAttribute(llvm::Attribute::SExt);
3180 Attrs.addAttribute(llvm::Attribute::ZExt);
3182 Attrs.addAttribute(llvm::Attribute::NoExt);
3187 Attrs.addAttribute(llvm::Attribute::Nest);
3189 Attrs.addAttribute(llvm::Attribute::InReg);
3190 Attrs.addStackAlignmentAttr(llvm::MaybeAlign(AI.
getDirectAlign()));
3193 Attrs.addNoFPClassAttr(
3198 "Pass-by-value parameter has incomplete definition?");
3201 Attrs.addAttribute(llvm::Attribute::InReg);
3213 Attrs.addByValAttr(
getTypes().ConvertTypeForMem(ParamType));
3221 Attrs.addDeadOnReturnAttr(llvm::DeadOnReturnInfo());
3226 if (CodeGenOpts.PassByValueIsNoAlias &&
Decl &&
3227 Decl->getArgPassingRestrictions() ==
3231 Attrs.addAttribute(llvm::Attribute::NoAlias);
3261 Attrs.addAttribute(llvm::Attribute::NoFreeObj);
3262 Attrs.addDereferenceableAttr(
3263 Context.getTypeSizeInChars(ParamType).getQuantity());
3267 AddPotentialArgAccess();
3272 Attrs.addByRefAttr(
getTypes().ConvertTypeForMem(ParamType));
3283 AddPotentialArgAccess();
3291 if (
getTypes().getTargetAddressSpace(PTy) == 0 &&
3292 !CodeGenOpts.NullPointerIsValid)
3293 Attrs.addAttribute(llvm::Attribute::NonNull);
3295 llvm::Align Alignment =
3297 Attrs.addAlignmentAttr(Alignment);
3306 DeviceKernelAttr::isOpenCLSpelling(
3307 TargetDecl->
getAttr<DeviceKernelAttr>()) &&
3311 llvm::Align Alignment =
3313 Attrs.addAlignmentAttr(Alignment);
3320 Attrs.addAttribute(llvm::Attribute::NoAlias);
3329 Attrs.addStructRetAttr(
getTypes().ConvertTypeForMem(ParamType));
3334 Attrs.addAttribute(llvm::Attribute::NoAlias);
3338 if (!PTy->isIncompleteType() && PTy->isConstantSizeType()) {
3339 auto info =
getContext().getTypeInfoInChars(PTy);
3340 Attrs.addDereferenceableAttr(info.Width.getQuantity());
3341 Attrs.addAlignmentAttr(info.Align.getAsAlign());
3347 Attrs.addAttribute(llvm::Attribute::SwiftError);
3351 Attrs.addAttribute(llvm::Attribute::SwiftSelf);
3355 Attrs.addAttribute(llvm::Attribute::SwiftAsync);
3360 Attrs.addCapturesAttr(
3361 llvm::CaptureInfo(llvm::CaptureComponents::Address));
3363 if (Attrs.hasAttributes()) {
3364 unsigned FirstIRArg, NumIRArgs;
3365 std::tie(FirstIRArg, NumIRArgs) = IRFunctionArgs.getIRArgs(ArgNo);
3366 for (
unsigned i = 0; i < NumIRArgs; i++)
3367 ArgAttrs[FirstIRArg + i].merge(Attrs);
3375 AddPotentialArgAccess();
3378 if (AddedPotentialArgAccess && MemAttrForPtrArgs) {
3382 I != E; ++I, ++ArgNo) {
3383 if (I->info.isDirect() || I->info.isExpand() ||
3384 I->info.isCoerceAndExpand()) {
3385 unsigned FirstIRArg, NumIRArgs;
3386 std::tie(FirstIRArg, NumIRArgs) = IRFunctionArgs.getIRArgs(ArgNo);
3387 for (
unsigned i = FirstIRArg; i < FirstIRArg + NumIRArgs; ++i) {
3394 if (i < FunctionType->getNumParams() &&
3396 ArgAttrs[i].addAttribute(*MemAttrForPtrArgs);
3404 for (
const llvm::AttrBuilder &Attrs : ArgAttrs)
3405 ArgAttrSets.push_back(llvm::AttributeSet::get(
getLLVMContext(), Attrs));
3407 AttrList = llvm::AttributeList::get(
3409 llvm::AttributeSet::get(
getLLVMContext(), RetAttrs), ArgAttrSets);
3416 llvm::Value *value) {
3417 llvm::Type *varType = CGF.
ConvertType(var->getType());
3421 if (value->getType() == varType)
3424 assert((varType->isIntegerTy() || varType->isFloatingPointTy()) &&
3425 "unexpected promotion type");
3428 return CGF.
Builder.CreateTrunc(value, varType,
"arg.unpromote");
3430 return CGF.
Builder.CreateFPCast(value, varType,
"arg.unpromote");
3436 QualType ArgType,
unsigned ArgNo) {
3444 if (!ArgType->isAnyPointerType() && !ArgType->isBlockPointerType())
3448 if (
auto ParmNNAttr = PVD->
getAttr<NonNullAttr>())
3455 if (NNAttr->isNonNull(ArgNo))
3462struct CopyBackSwiftError final : EHScopeStack::Cleanup {
3465 CopyBackSwiftError(Address temp, Address arg) : Temp(temp), Arg(
arg) {}
3466 void Emit(CodeGenFunction &CGF, Flags flags)
override {
3485 if (FD->hasImplicitReturnZero()) {
3486 QualType RetTy = FD->getReturnType().getUnqualifiedType();
3487 llvm::Type *LLVMTy =
CGM.getTypes().ConvertType(RetTy);
3488 llvm::Constant *
Zero = llvm::Constant::getNullValue(LLVMTy);
3496 ClangToLLVMArgMapping IRFunctionArgs(
CGM.getContext(), FI);
3497 assert(Fn->arg_size() == IRFunctionArgs.totalIRArgs());
3502 if (IRFunctionArgs.hasInallocaArg())
3503 ArgStruct =
Address(Fn->getArg(IRFunctionArgs.getInallocaArgNo()),
3507 if (IRFunctionArgs.hasSRetArg()) {
3508 auto AI = Fn->getArg(IRFunctionArgs.getSRetArgNo());
3509 AI->setName(
"agg.result");
3510 AI->addAttr(llvm::Attribute::NoAlias);
3517 ArgVals.reserve(Args.size());
3523 assert(FI.
arg_size() == Args.size() &&
3524 "Mismatch between function signature & arguments.");
3527 for (FunctionArgList::const_iterator i = Args.begin(), e = Args.end(); i != e;
3528 ++i, ++info_it, ++ArgNo) {
3541 unsigned FirstIRArg, NumIRArgs;
3542 std::tie(FirstIRArg, NumIRArgs) = IRFunctionArgs.getIRArgs(ArgNo);
3546 assert(NumIRArgs == 0);
3559 assert(NumIRArgs == 1);
3582 llvm::ConstantInt::get(
IntPtrTy, Size.getQuantity()));
3583 ParamAddr = AlignedTemp;
3600 auto AI = Fn->getArg(FirstIRArg);
3608 assert(NumIRArgs == 1);
3610 if (
const ParmVarDecl *PVD = dyn_cast<ParmVarDecl>(Arg)) {
3613 PVD->getFunctionScopeIndex()) &&
3614 !
CGM.getCodeGenOpts().NullPointerIsValid)
3615 AI->addAttr(llvm::Attribute::NonNull);
3617 QualType OTy = PVD->getOriginalType();
3618 if (
const auto *ArrTy =
getContext().getAsConstantArrayType(OTy)) {
3624 QualType ETy = ArrTy->getElementType();
3625 llvm::Align Alignment =
3626 CGM.getNaturalTypeAlignment(ETy).getAsAlign();
3628 .addAlignmentAttr(Alignment));
3629 uint64_t ArrSize = ArrTy->getZExtSize();
3633 Attrs.addDereferenceableAttr(
3634 getContext().getTypeSizeInChars(ETy).getQuantity() *
3636 AI->addAttrs(Attrs);
3637 }
else if (
getContext().getTargetInfo().getNullPointerValue(
3639 !
CGM.getCodeGenOpts().NullPointerIsValid) {
3640 AI->addAttr(llvm::Attribute::NonNull);
3643 }
else if (
const auto *ArrTy =
3649 QualType ETy = ArrTy->getElementType();
3650 llvm::Align Alignment =
3651 CGM.getNaturalTypeAlignment(ETy).getAsAlign();
3653 .addAlignmentAttr(Alignment));
3654 if (!
getTypes().getTargetAddressSpace(ETy) &&
3655 !
CGM.getCodeGenOpts().NullPointerIsValid)
3656 AI->addAttr(llvm::Attribute::NonNull);
3661 const auto *AVAttr = PVD->getAttr<AlignValueAttr>();
3664 AVAttr = TOTy->getDecl()->getAttr<AlignValueAttr>();
3665 if (AVAttr && !
SanOpts.has(SanitizerKind::Alignment)) {
3669 llvm::ConstantInt *AlignmentCI =
3671 uint64_t AlignmentInt =
3672 AlignmentCI->getLimitedValue(llvm::Value::MaximumAlignment);
3673 if (AI->getParamAlign().valueOrOne() < AlignmentInt) {
3674 AI->removeAttr(llvm::Attribute::AttrKind::Alignment);
3676 .addAlignmentAttr(llvm::Align(AlignmentInt)));
3683 AI->addAttr(llvm::Attribute::NoAlias);
3691 assert(NumIRArgs == 1);
3695 llvm::Value *
V = AI;
3703 V, pointeeTy,
getContext().getTypeAlignInChars(pointeeTy));
3704 llvm::Value *incomingErrorValue =
Builder.CreateLoad(arg);
3705 Builder.CreateStore(incomingErrorValue, temp);
3726 if (
V->getType() != LTy)
3737 if (
auto *VecTyTo = dyn_cast<llvm::FixedVectorType>(
ConvertType(Ty))) {
3738 llvm::Value *ArgVal = Fn->getArg(FirstIRArg);
3739 if (
auto *VecTyFrom =
3740 dyn_cast<llvm::ScalableVectorType>(ArgVal->getType())) {
3742 *
this, VecTyTo, VecTyFrom, ArgVal, Arg->
getName());
3744 assert(NumIRArgs == 1);
3751 llvm::StructType *STy =
3762 STy->getNumElements() > 1) {
3763 llvm::TypeSize StructSize =
CGM.getDataLayout().getTypeAllocSize(STy);
3764 llvm::TypeSize PtrElementSize =
3765 CGM.getDataLayout().getTypeAllocSize(Ptr.getElementType());
3766 if (StructSize.isScalable()) {
3767 assert(STy->containsHomogeneousScalableVectorTypes() &&
3768 "ABI only supports structure with homogeneous scalable vector "
3770 assert(StructSize == PtrElementSize &&
3771 "Only allow non-fractional movement of structure with"
3772 "homogeneous scalable vector type");
3773 assert(STy->getNumElements() == NumIRArgs);
3775 llvm::Value *LoadedStructValue = llvm::PoisonValue::get(STy);
3776 for (
unsigned i = 0, e = STy->getNumElements(); i != e; ++i) {
3777 auto *AI = Fn->getArg(FirstIRArg + i);
3778 AI->setName(Arg->
getName() +
".coerce" + Twine(i));
3780 Builder.CreateInsertValue(LoadedStructValue, AI, i);
3783 Builder.CreateStore(LoadedStructValue, Ptr);
3785 uint64_t SrcSize = StructSize.getFixedValue();
3786 uint64_t DstSize = PtrElementSize.getFixedValue();
3789 if (SrcSize <= DstSize) {
3790 AddrToStoreInto = Ptr.withElementType(STy);
3796 assert(STy->getNumElements() == NumIRArgs);
3797 for (
unsigned i = 0, e = STy->getNumElements(); i != e; ++i) {
3798 auto AI = Fn->getArg(FirstIRArg + i);
3799 AI->setName(Arg->
getName() +
".coerce" + Twine(i));
3801 Builder.CreateStore(AI, EltPtr);
3804 if (SrcSize > DstSize) {
3805 Builder.CreateMemCpy(Ptr, AddrToStoreInto, DstSize);
3817 assert(NumIRArgs == 1);
3818 auto AI = Fn->getArg(FirstIRArg);
3819 AI->setName(Arg->
getName() +
".coerce");
3822 llvm::TypeSize::getFixed(
3823 getContext().getTypeSizeInChars(Ty).getQuantity() -
3849 auto *unpaddedStruct = dyn_cast<llvm::StructType>(unpaddedCoercionType);
3853 unsigned argIndex = FirstIRArg;
3854 unsigned unpaddedIndex = 0;
3855 for (
unsigned i = 0, e = coercionType->getNumElements(); i != e; ++i) {
3856 llvm::Type *eltType = coercionType->getElementType(i);
3860 auto eltAddr =
Builder.CreateStructGEP(alloca, i);
3861 llvm::Value *elt = Fn->getArg(argIndex++);
3863 auto paramType = unpaddedStruct
3864 ? unpaddedStruct->getElementType(unpaddedIndex++)
3865 : unpaddedCoercionType;
3867 if (
auto *VecTyTo = dyn_cast<llvm::FixedVectorType>(eltType)) {
3868 if (
auto *VecTyFrom = dyn_cast<llvm::ScalableVectorType>(paramType)) {
3871 *
this, VecTyTo, VecTyFrom, elt, elt->getName());
3872 assert(Extracted &&
"Unexpected scalable to fixed vector coercion");
3875 Builder.CreateStore(elt, eltAddr);
3877 assert(argIndex == FirstIRArg + NumIRArgs);
3890 auto FnArgIter = Fn->arg_begin() + FirstIRArg;
3891 ExpandTypeFromArgs(Ty, LV, FnArgIter);
3892 assert(FnArgIter == Fn->arg_begin() + FirstIRArg + NumIRArgs);
3893 for (
unsigned i = 0, e = NumIRArgs; i != e; ++i) {
3894 auto AI = Fn->getArg(FirstIRArg + i);
3895 AI->setName(Arg->
getName() +
"." + Twine(i));
3901 auto *AI = Fn->getArg(FirstIRArg);
3902 AI->setName(Arg->
getName() +
".target_coerce");
3906 CGM.getABIInfo().createCoercedStore(AI, Ptr, ArgI,
false, *
this);
3920 assert(NumIRArgs == 0);
3933 if (
getTarget().getCXXABI().areArgsDestroyedLeftToRightInCallee()) {
3934 for (
int I = Args.size() - 1; I >= 0; --I)
3937 for (
unsigned I = 0, E = Args.size(); I != E; ++I)
3943 while (insn->use_empty()) {
3944 llvm::BitCastInst *bitcast = dyn_cast<llvm::BitCastInst>(insn);
3950 bitcast->eraseFromParent();
3956 llvm::Value *result) {
3958 llvm::BasicBlock *BB = CGF.
Builder.GetInsertBlock();
3961 if (&BB->back() != result)
3964 llvm::Type *resultType = result->getType();
3973 while (llvm::BitCastInst *bitcast = dyn_cast<llvm::BitCastInst>(generator)) {
3979 if (generator->getNextNode() != bitcast)
3982 InstsToKill.push_back(bitcast);
3989 llvm::CallInst *call = dyn_cast<llvm::CallInst>(generator);
3993 bool doRetainAutorelease;
3996 doRetainAutorelease =
true;
3997 }
else if (call->getCalledOperand() ==
3999 doRetainAutorelease =
false;
4007 llvm::Instruction *prev = call->getPrevNode();
4010 prev = prev->getPrevNode();
4016 InstsToKill.push_back(prev);
4022 result = call->getArgOperand(0);
4023 InstsToKill.push_back(call);
4027 while (llvm::BitCastInst *bitcast = dyn_cast<llvm::BitCastInst>(result)) {
4028 if (!bitcast->hasOneUse())
4030 InstsToKill.push_back(bitcast);
4031 result = bitcast->getOperand(0);
4035 for (
auto *I : InstsToKill)
4036 I->eraseFromParent();
4039 if (doRetainAutorelease)
4043 return CGF.
Builder.CreateBitCast(result, resultType);
4048 llvm::Value *result) {
4051 dyn_cast_or_null<ObjCMethodDecl>(CGF.
CurCodeDecl);
4060 llvm::CallInst *retainCall = dyn_cast<llvm::CallInst>(result);
4061 if (!retainCall || retainCall->getCalledOperand() !=
4066 llvm::Value *retainedValue = retainCall->getArgOperand(0);
4067 llvm::LoadInst *load =
4068 dyn_cast<llvm::LoadInst>(retainedValue->stripPointerCasts());
4069 if (!load || load->isAtomic() || load->isVolatile() ||
4076 llvm::Type *resultType = result->getType();
4078 assert(retainCall->use_empty());
4079 retainCall->eraseFromParent();
4082 return CGF.
Builder.CreateBitCast(load, resultType);
4089 llvm::Value *result) {
4112 auto GetStoreIfValid = [&CGF,
4113 ReturnValuePtr](llvm::User *
U) -> llvm::StoreInst * {
4114 auto *SI = dyn_cast<llvm::StoreInst>(
U);
4115 if (!SI || SI->getPointerOperand() != ReturnValuePtr ||
4121 assert(!SI->isAtomic() &&
4129 if (!ReturnValuePtr->hasOneUse()) {
4130 llvm::BasicBlock *IP = CGF.
Builder.GetInsertBlock();
4136 const llvm::Instruction *LoadIntoFakeUse =
nullptr;
4137 for (llvm::Instruction &I : llvm::reverse(*IP)) {
4141 if (LoadIntoFakeUse == &I)
4145 if (
auto *II = dyn_cast<llvm::IntrinsicInst>(&I)) {
4146 if (II->getIntrinsicID() == llvm::Intrinsic::lifetime_end)
4149 if (II->getIntrinsicID() == llvm::Intrinsic::fake_use) {
4150 LoadIntoFakeUse = dyn_cast<llvm::Instruction>(II->getArgOperand(0));
4154 return GetStoreIfValid(&I);
4159 llvm::StoreInst *store = GetStoreIfValid(ReturnValuePtr->user_back());
4165 llvm::BasicBlock *StoreBB = store->getParent();
4166 llvm::BasicBlock *IP = CGF.
Builder.GetInsertBlock();
4168 while (IP != StoreBB) {
4169 if (!SeenBBs.insert(IP).second || !(IP = IP->getSinglePredecessor()))
4185 int BitWidth,
int CharWidth) {
4186 assert(CharWidth <= 64);
4187 assert(
static_cast<unsigned>(BitWidth) <= Bits.size() * CharWidth);
4190 if (BitOffset >= CharWidth) {
4191 Pos += BitOffset / CharWidth;
4192 BitOffset = BitOffset % CharWidth;
4195 const uint64_t
Used = (uint64_t(1) << CharWidth) - 1;
4196 if (BitOffset + BitWidth >= CharWidth) {
4197 Bits[Pos++] |= (
Used << BitOffset) &
Used;
4198 BitWidth -= CharWidth - BitOffset;
4202 while (BitWidth >= CharWidth) {
4204 BitWidth -= CharWidth;
4208 Bits[Pos++] |= (
Used >> (CharWidth - BitWidth)) << BitOffset;
4216 int StorageSize,
int BitOffset,
int BitWidth,
4217 int CharWidth,
bool BigEndian) {
4220 setBitRange(TmpBits, BitOffset, BitWidth, CharWidth);
4223 std::reverse(TmpBits.begin(), TmpBits.end());
4225 for (uint64_t
V : TmpBits)
4226 Bits[StorageOffset++] |=
V;
4229static void setUsedBits(CodeGenModule &, QualType,
int,
4230 SmallVectorImpl<uint64_t> &);
4272 QualType ETy = Context.getBaseElementType(ATy);
4273 int Size = Context.getTypeSizeInChars(ETy).getQuantity();
4277 for (
int I = 0, N = Context.getConstantArrayElementCount(ATy); I < N; ++I) {
4278 auto Src = TmpBits.begin();
4279 auto Dst = Bits.begin() + Offset + I * Size;
4280 for (
int J = 0; J < Size; ++J)
4293 if (
const auto *ATy = Context.getAsConstantArrayType(QTy))
4296 int Size = Context.getTypeSizeInChars(QTy).getQuantity();
4300 std::fill_n(Bits.begin() + Offset, Size,
4301 (uint64_t(1) << Context.getCharWidth()) - 1);
4305 int Pos,
int Size,
int CharWidth,
4310 for (
auto P = Bits.begin() + Pos, E = Bits.begin() + Pos + Size; P != E;
4312 Mask = (Mask << CharWidth) | *P;
4314 auto P = Bits.begin() + Pos + Size, End = Bits.begin() + Pos;
4316 Mask = (Mask << CharWidth) | *--P;
4325 llvm::IntegerType *ITy,
4327 assert(Src->getType() == ITy);
4328 assert(ITy->getScalarSizeInBits() <= 64);
4330 const llvm::DataLayout &DataLayout =
CGM.getDataLayout();
4331 int Size = DataLayout.getTypeStoreSize(ITy);
4335 int CharWidth =
CGM.getContext().getCharWidth();
4339 return Builder.CreateAnd(Src, Mask,
"cmse.clear");
4345 llvm::ArrayType *ATy,
4347 const llvm::DataLayout &DataLayout =
CGM.getDataLayout();
4348 int Size = DataLayout.getTypeStoreSize(ATy);
4353 int CharWidth =
CGM.getContext().getCharWidth();
4355 ATy->getArrayElementType()->getScalarSizeInBits() / CharWidth;
4357 llvm::Value *R = llvm::PoisonValue::get(ATy);
4358 for (
int I = 0, N = ATy->getArrayNumElements(); I != N; ++I) {
4360 DataLayout.isBigEndian());
4361 MaskIndex += CharsPerElt;
4362 llvm::Value *T0 =
Builder.CreateExtractValue(Src, I);
4363 llvm::Value *T1 =
Builder.CreateAnd(T0, Mask,
"cmse.clear");
4364 R =
Builder.CreateInsertValue(R, T1, I);
4372 uint64_t RetKeyInstructionsSourceAtom) {
4387 auto *I =
Builder.CreateRetVoid();
4388 if (RetKeyInstructionsSourceAtom)
4395 llvm::DebugLoc RetDbgLoc;
4396 llvm::Value *RV =
nullptr;
4406 llvm::Function::arg_iterator EI =
CurFn->arg_end();
4408 llvm::Value *ArgStruct = &*EI;
4409 llvm::Value *SRet =
Builder.CreateStructGEP(
4418 auto AI =
CurFn->arg_begin();
4436 CGM.getNaturalTypeAlignment(RetTy, &BaseInfo, &TBAAInfo);
4463 RetDbgLoc = SI->getDebugLoc();
4465 RV = SI->getValueOperand();
4466 SI->eraseFromParent();
4489 if (
auto *FD = dyn_cast<FunctionDecl>(
CurCodeDecl))
4490 RT = FD->getReturnType();
4491 else if (
auto *MD = dyn_cast<ObjCMethodDecl>(
CurCodeDecl))
4492 RT = MD->getReturnType();
4494 RT =
BlockInfo->BlockExpression->getFunctionType()->getReturnType();
4496 llvm_unreachable(
"Unexpected function/method type");
4512 auto *unpaddedStruct = dyn_cast<llvm::StructType>(unpaddedCoercionType);
4517 unsigned unpaddedIndex = 0;
4518 for (
unsigned i = 0, e = coercionType->getNumElements(); i != e; ++i) {
4519 auto coercedEltType = coercionType->getElementType(i);
4523 auto eltAddr =
Builder.CreateStructGEP(addr, i);
4526 unpaddedStruct ? unpaddedStruct->getElementType(unpaddedIndex++)
4527 : unpaddedCoercionType,
4529 results.push_back(elt);
4533 if (results.size() == 1) {
4541 RV = llvm::PoisonValue::get(returnType);
4542 for (
unsigned i = 0, e = results.size(); i != e; ++i) {
4543 RV =
Builder.CreateInsertValue(RV, results[i], i);
4550 RV =
CGM.getABIInfo().createCoercedLoad(
V, RetAI, *
this);
4555 llvm_unreachable(
"Invalid ABI kind for return argument");
4558 llvm::Instruction *Ret;
4564 auto *ITy = dyn_cast<llvm::IntegerType>(RV->getType());
4571 Ret =
Builder.CreateRetVoid();
4575 Ret->setDebugLoc(std::move(RetDbgLoc));
4577 llvm::Value *Backup = RV ? Ret->getOperand(0) :
nullptr;
4578 if (RetKeyInstructionsSourceAtom)
4594 ReturnsNonNullAttr *RetNNAttr =
nullptr;
4595 if (
SanOpts.has(SanitizerKind::ReturnsNonnullAttribute))
4596 RetNNAttr =
CurCodeDecl->getAttr<ReturnsNonNullAttr>();
4598 if (!RetNNAttr && !requiresReturnValueNullabilityCheck())
4606 assert(!requiresReturnValueNullabilityCheck() &&
4607 "Cannot check nullability and the nonnull attribute");
4608 AttrLoc = RetNNAttr->getLocation();
4609 CheckKind = SanitizerKind::SO_ReturnsNonnullAttribute;
4610 Handler = SanitizerHandler::NonnullReturn;
4612 if (
auto *DD = dyn_cast<DeclaratorDecl>(
CurCodeDecl))
4613 if (
auto *TSI = DD->getTypeSourceInfo())
4615 AttrLoc = FTL.getReturnLoc().findNullabilityLoc();
4616 CheckKind = SanitizerKind::SO_NullabilityReturn;
4617 Handler = SanitizerHandler::NullabilityReturn;
4626 llvm::Value *SLocPtr =
Builder.CreateLoad(ReturnLocation,
"return.sloc.load");
4627 llvm::Value *CanNullCheck =
Builder.CreateIsNotNull(SLocPtr);
4628 if (requiresReturnValueNullabilityCheck())
4630 Builder.CreateAnd(CanNullCheck, RetValNullabilityPrecondition);
4631 Builder.CreateCondBr(CanNullCheck, Check, NoCheck);
4635 llvm::Value *Cond =
Builder.CreateIsNotNull(RV);
4637 llvm::Value *DynamicData[] = {SLocPtr};
4638 EmitCheck(std::make_pair(Cond, CheckKind), Handler, StaticData, DynamicData);
4657 llvm::Type *IRPtrTy = llvm::PointerType::getUnqual(CGF.
getLLVMContext());
4658 llvm::Value *Placeholder = llvm::PoisonValue::get(IRPtrTy);
4683 if (
type->isReferenceType()) {
4692 param->
hasAttr<NSConsumedAttr>() &&
type->isObjCRetainableType()) {
4693 llvm::Value *ptr =
Builder.CreateLoad(local);
4696 Builder.CreateStore(null, local);
4707 type->castAsRecordDecl()->isParamDestroyedInCallee() &&
4711 assert(cleanup.isValid() &&
4712 "cleanup for callee-destructed param not recorded");
4714 llvm::Instruction *isActive =
Builder.CreateUnreachable();
4720 return llvm::isa_and_nonnull<llvm::ConstantPointerNull>(addr);
4730 const LValue &srcLV = writeback.
Source;
4731 Address srcAddr = srcLV.getAddress();
4733 "shouldn't have writeback for provably null argument");
4741 llvm::BasicBlock *contBB =
nullptr;
4747 if (!provablyNonNull) {
4752 CGF.
Builder.CreateCondBr(isNull, contBB, writebackBB);
4761 "icr.writeback-cast");
4770 if (writeback.
ToUse) {
4795 if (!provablyNonNull)
4804 for (
const auto &I : llvm::reverse(Cleanups)) {
4806 I.IsActiveIP->eraseFromParent();
4812 if (uop->getOpcode() == UO_AddrOf)
4813 return uop->getSubExpr();
4838 Address srcAddr = srcLV.getAddress();
4843 llvm::PointerType *destType =
4845 llvm::Type *destElemType =
4872 llvm::BasicBlock *contBB =
nullptr;
4873 llvm::BasicBlock *originBB =
nullptr;
4876 llvm::Value *finalArgument;
4880 if (provablyNonNull) {
4885 finalArgument = CGF.
Builder.CreateSelect(
4886 isNull, llvm::ConstantPointerNull::get(destType),
4892 originBB = CGF.
Builder.GetInsertBlock();
4895 CGF.
Builder.CreateCondBr(isNull, contBB, copyBB);
4897 condEval.
begin(CGF);
4901 llvm::Value *valueToUse =
nullptr;
4909 src = CGF.
Builder.CreateBitCast(src, destElemType,
"icr.cast");
4926 if (shouldCopy && !provablyNonNull) {
4927 llvm::BasicBlock *copyBB = CGF.
Builder.GetInsertBlock();
4932 llvm::PHINode *phiToUse =
4933 CGF.
Builder.CreatePHI(valueToUse->getType(), 2,
"icr.to-use");
4934 phiToUse->addIncoming(valueToUse, copyBB);
4935 phiToUse->addIncoming(llvm::PoisonValue::get(valueToUse->getType()),
4937 valueToUse = phiToUse;
4951 StackBase = CGF.
Builder.CreateStackSave(
"inalloca.save");
4957 CGF.
Builder.CreateStackRestore(StackBase);
4964 if (!AC.
getDecl() || !(
SanOpts.has(SanitizerKind::NonnullAttribute) ||
4965 SanOpts.has(SanitizerKind::NullabilityArg)))
4970 unsigned ArgNo = PVD ? PVD->getFunctionScopeIndex() : ParmNum;
4973 const NonNullAttr *NNAttr =
nullptr;
4974 if (
SanOpts.has(SanitizerKind::NonnullAttribute))
4977 bool CanCheckNullability =
false;
4978 if (
SanOpts.has(SanitizerKind::NullabilityArg) && !NNAttr && PVD &&
4979 !PVD->getType()->isRecordType()) {
4980 auto Nullability = PVD->getType()->getNullability();
4981 CanCheckNullability = Nullability &&
4983 PVD->getTypeSourceInfo();
4986 if (!NNAttr && !CanCheckNullability)
4993 AttrLoc = NNAttr->getLocation();
4994 CheckKind = SanitizerKind::SO_NonnullAttribute;
4995 Handler = SanitizerHandler::NonnullArg;
4997 AttrLoc = PVD->getTypeSourceInfo()->getTypeLoc().findNullabilityLoc();
4998 CheckKind = SanitizerKind::SO_NullabilityArg;
4999 Handler = SanitizerHandler::NullabilityArg;
5004 llvm::Constant *StaticData[] = {
5007 llvm::ConstantInt::get(
Int32Ty, ArgNo + 1),
5009 EmitCheck(std::make_pair(Cond, CheckKind), Handler, StaticData, {});
5015 if (!AC.
getDecl() || !(
SanOpts.has(SanitizerKind::NonnullAttribute) ||
5016 SanOpts.has(SanitizerKind::NullabilityArg)))
5035 return llvm::any_of(ArgTypes, [&](
QualType Ty) {
5046 return classDecl->getTypeParamListAsWritten();
5050 return catDecl->getTypeParamList();
5060 llvm::iterator_range<CallExpr::const_arg_iterator> ArgRange,
5064 assert((ParamsToSkip == 0 ||
Prototype.P) &&
5065 "Can't skip parameters if type info is not provided");
5075 bool IsVariadic =
false;
5077 const auto *MD = dyn_cast<const ObjCMethodDecl *>(
Prototype.P);
5079 IsVariadic = MD->isVariadic();
5081 MD,
CGM.getTarget().getTriple().isOSWindows());
5082 ArgTypes.assign(MD->param_type_begin() + ParamsToSkip,
5083 MD->param_type_end());
5086 IsVariadic = FPT->isVariadic();
5087 ExplicitCC = FPT->getExtInfo().getCC();
5088 ArgTypes.assign(FPT->param_type_begin() + ParamsToSkip,
5089 FPT->param_type_end());
5097 assert(Arg != ArgRange.end() &&
"Running over edge of argument list!");
5099 QualType ArgTy = (*Arg)->getType();
5100 if (
const auto *OBT = ParamTy->
getAs<OverflowBehaviorType>())
5101 ParamTy = OBT->getUnderlyingType();
5102 if (
const auto *OBT = ArgTy->
getAs<OverflowBehaviorType>())
5103 ArgTy = OBT->getUnderlyingType();
5106 getContext().getCanonicalType(ParamTy).getTypePtr() ==
5107 getContext().getCanonicalType(ArgTy).getTypePtr()) &&
5108 "type mismatch in call argument!");
5114 assert((Arg == ArgRange.end() || IsVariadic) &&
5115 "Extra arguments in non-variadic function!");
5120 for (
auto *A : llvm::drop_begin(ArgRange, ArgTypes.size()))
5121 ArgTypes.push_back(IsVariadic ? getVarArgType(A) : A->getType());
5122 assert((
int)ArgTypes.size() == (ArgRange.end() - ArgRange.begin()));
5130 CGM.getTarget().getCXXABI().areArgsDestroyedLeftToRightInCallee()
5134 auto MaybeEmitImplicitObjectSize = [&](
unsigned I,
const Expr *Arg,
5143 auto SizeTy = Context.getSizeType();
5145 assert(EmittedArg.getScalarVal() &&
"We emitted nothing for the arg?");
5146 llvm::Value *
V = evaluateOrEmitBuiltinObjectSize(
5147 Arg, PS->getType(),
T, EmittedArg.getScalarVal(), PS->isDynamic());
5152 std::swap(Args.back(), *(&Args.back() - 1));
5158 "inalloca only supported on x86");
5163 size_t CallArgsStart = Args.size();
5164 for (
unsigned I = 0, E = ArgTypes.size(); I != E; ++I) {
5165 unsigned Idx = LeftToRight ? I : E - I - 1;
5167 unsigned InitialArgSize = Args.size();
5171 getContext().hasSameUnqualifiedType((*Arg)->getType(),
5175 "Argument and parameter types don't match");
5179 assert(InitialArgSize + 1 == Args.size() &&
5180 "The code below depends on only adding one arg per EmitCallArg");
5181 (void)InitialArgSize;
5184 if (!Args.back().hasLValue()) {
5185 RValue RVArg = Args.back().getKnownRValue();
5187 ParamsToSkip + Idx);
5191 MaybeEmitImplicitObjectSize(Idx, *Arg, RVArg);
5198 std::reverse(Args.begin() + CallArgsStart, Args.end());
5207struct DestroyUnpassedArg final : EHScopeStack::Cleanup {
5217 assert(!Dtor->isTrivial());
5240 if (!HasLV &&
RV.isScalar())
5242 else if (!HasLV &&
RV.isComplex())
5245 auto Addr = HasLV ?
LV.getAddress() :
RV.getAggregateAddress();
5249 HasLV ?
LV.isVolatileQualified()
5250 :
RV.isVolatileQualified());
5262 std::optional<DisableDebugLocationUpdates> Dis;
5266 dyn_cast<ObjCIndirectCopyRestoreExpr>(E)) {
5280 "reference binding to unmaterialized r-value!");
5292 if (
type->isRecordType() &&
5293 type->castAsRecordDecl()->isParamDestroyedInCallee()) {
5300 bool DestroyedInCallee =
true, NeedsCleanup =
true;
5301 if (
const auto *RD =
type->getAsCXXRecordDecl())
5302 DestroyedInCallee = RD->hasNonTrivialDestructor();
5304 NeedsCleanup =
type.isDestructedType();
5306 if (DestroyedInCallee)
5313 if (DestroyedInCallee && NeedsCleanup) {
5320 llvm::Instruction *IsActive =
5327 if (HasAggregateEvalKind) {
5328 auto *ICE = dyn_cast<ImplicitCastExpr>(E);
5329 if (ICE && ICE->getCastKind() == CK_LValueToRValue &&
5330 ICE->getSubExpr()->getType().getAddressSpace() !=
5332 !
type->isArrayParameterType() && !
type.isNonTrivialToPrimitiveCopy()) {
5343QualType CodeGenFunction::getVarArgType(
const Expr *Arg) {
5347 if (!getTarget().
getTriple().isOSWindows())
5351 getContext().getTypeSize(Arg->
getType()) <
5355 return getContext().getIntPtrType();
5363void CodeGenFunction::AddObjCARCExceptionMetadata(llvm::Instruction *Inst) {
5364 if (CGM.getCodeGenOpts().OptimizationLevel != 0 &&
5365 !CGM.getCodeGenOpts().ObjCAutoRefCountExceptions)
5366 Inst->setMetadata(
"clang.arc.no_objc_arc_exceptions",
5367 CGM.getNoObjCARCExceptionsMetadata());
5373 const llvm::Twine &name) {
5374 return EmitNounwindRuntimeCall(callee, ArrayRef<llvm::Value *>(), name);
5380 ArrayRef<Address> args,
5381 const llvm::Twine &name) {
5382 SmallVector<llvm::Value *, 3> values;
5383 for (
auto arg : args)
5384 values.push_back(
arg.emitRawPointer(*
this));
5385 return EmitNounwindRuntimeCall(callee, values, name);
5390 ArrayRef<llvm::Value *> args,
5391 const llvm::Twine &name) {
5392 llvm::CallInst *call = EmitRuntimeCall(callee, args, name);
5393 call->setDoesNotThrow();
5400 const llvm::Twine &name) {
5401 return EmitRuntimeCall(callee, {},
name);
5406SmallVector<llvm::OperandBundleDef, 1>
5415 if (
auto *CalleeFn = dyn_cast<llvm::Function>(Callee->stripPointerCasts())) {
5416 if (CalleeFn->isIntrinsic() && CalleeFn->doesNotThrow()) {
5417 auto IID = CalleeFn->getIntrinsicID();
5418 if (!llvm::IntrinsicInst::mayLowerToFunctionCall(IID))
5431 const llvm::Twine &name) {
5432 llvm::CallInst *call = Builder.CreateCall(
5433 callee, args, getBundlesForFunclet(callee.getCallee()), name);
5434 call->setCallingConv(getRuntimeCC());
5436 if (CGM.shouldEmitConvergenceTokens() && call->isConvergent())
5442 const llvm::Twine &Name) {
5443 return EmitIntrinsicCall(ID, {}, {}, Name);
5447 ArrayRef<llvm::Value *> Args,
5448 const llvm::Twine &Name) {
5449 return EmitIntrinsicCall(ID, {}, Args, Name);
5453 ArrayRef<llvm::Type *> Types,
5454 ArrayRef<llvm::Value *> Args,
5455 const llvm::Twine &Name) {
5457 llvm::Intrinsic::getOrInsertDeclaration(&CGM.getModule(), ID, Types);
5458 llvm::CallInst *
Call =
5459 Builder.CreateCall(F, Args, getBundlesForFunclet(F), Name);
5460 if (CGM.shouldEmitConvergenceTokens() &&
Call->isConvergent())
5466 ArrayRef<llvm::Value *> Args,
5468 const llvm::Twine &Name) {
5469 SmallVector<llvm::Type *> ArgTys;
5470 ArgTys.reserve(Args.size());
5471 for (llvm::Value *Arg : Args)
5472 ArgTys.push_back(Arg->
getType());
5473 llvm::Function *F = llvm::Intrinsic::getOrInsertDeclaration(
5474 &CGM.getModule(), ID, RetTy, ArgTys);
5475 llvm::CallInst *
Call =
5476 Builder.CreateCall(F, Args, getBundlesForFunclet(F), Name);
5477 if (CGM.shouldEmitConvergenceTokens() &&
Call->isConvergent())
5489 llvm::InvokeInst *invoke =
Builder.CreateInvoke(
5491 invoke->setDoesNotReturn();
5494 llvm::CallInst *call =
Builder.CreateCall(callee, args, BundleList);
5495 call->setDoesNotReturn();
5504 const Twine &name) {
5512 const Twine &name) {
5522 const Twine &Name) {
5527 llvm::CallBase *Inst;
5529 Inst =
Builder.CreateCall(Callee, Args, BundleList, Name);
5532 Inst =
Builder.CreateInvoke(Callee, ContBB, InvokeDest, Args, BundleList,
5539 if (
CGM.getLangOpts().ObjCAutoRefCount)
5540 AddObjCARCExceptionMetadata(Inst);
5545void CodeGenFunction::deferPlaceholderReplacement(llvm::Instruction *Old,
5547 DeferredReplacements.push_back(
5548 std::make_pair(llvm::WeakTrackingVH(Old),
New));
5555[[nodiscard]] llvm::AttributeList
5556maybeRaiseRetAlignmentAttribute(llvm::LLVMContext &Ctx,
5557 const llvm::AttributeList &Attrs,
5558 llvm::Align NewAlign) {
5559 llvm::Align CurAlign = Attrs.getRetAlignment().valueOrOne();
5560 if (CurAlign >= NewAlign)
5562 llvm::Attribute AlignAttr = llvm::Attribute::getWithAlignment(Ctx, NewAlign);
5563 return Attrs.removeRetAttribute(Ctx, llvm::Attribute::AttrKind::Alignment)
5564 .addRetAttribute(Ctx, AlignAttr);
5567template <
typename AlignedAttrTy>
class AbstractAssumeAlignedAttrEmitter {
5572 const AlignedAttrTy *AA =
nullptr;
5574 llvm::Value *Alignment =
nullptr;
5575 llvm::ConstantInt *OffsetCI =
nullptr;
5581 AA = FuncDecl->
getAttr<AlignedAttrTy>();
5586 [[nodiscard]] llvm::AttributeList
5587 TryEmitAsCallSiteAttribute(
const llvm::AttributeList &Attrs) {
5588 if (!AA || OffsetCI || CGF.
SanOpts.
has(SanitizerKind::Alignment))
5590 const auto *AlignmentCI = dyn_cast<llvm::ConstantInt>(Alignment);
5595 if (!AlignmentCI->getValue().isPowerOf2())
5597 llvm::AttributeList NewAttrs = maybeRaiseRetAlignmentAttribute(
5600 AlignmentCI->getLimitedValue(llvm::Value::MaximumAlignment)));
5608 void EmitAsAnAssumption(SourceLocation Loc, QualType RetTy, RValue &Ret) {
5612 AA->getLocation(), Alignment, OffsetCI);
5618class AssumeAlignedAttrEmitter final
5619 :
public AbstractAssumeAlignedAttrEmitter<AssumeAlignedAttr> {
5621 AssumeAlignedAttrEmitter(CodeGenFunction &CGF_,
const Decl *FuncDecl)
5622 : AbstractAssumeAlignedAttrEmitter(CGF_, FuncDecl) {
5627 if (Expr *Offset = AA->getOffset()) {
5629 if (OffsetCI->isNullValue())
5636class AllocAlignAttrEmitter final
5637 :
public AbstractAssumeAlignedAttrEmitter<AllocAlignAttr> {
5639 AllocAlignAttrEmitter(CodeGenFunction &CGF_,
const Decl *FuncDecl,
5640 const CallArgList &CallArgs)
5641 : AbstractAssumeAlignedAttrEmitter(CGF_, FuncDecl) {
5645 Alignment = CallArgs[AA->getParamIndex().getLLVMIndex()]
5654 if (
auto *VT = dyn_cast<llvm::VectorType>(Ty))
5655 return VT->getPrimitiveSizeInBits().getKnownMinValue();
5656 if (
auto *AT = dyn_cast<llvm::ArrayType>(Ty))
5659 unsigned MaxVectorWidth = 0;
5660 if (
auto *ST = dyn_cast<llvm::StructType>(Ty))
5661 for (
auto *I : ST->elements())
5663 return MaxVectorWidth;
5670 llvm::CallBase **callOrInvoke,
bool IsMustTail,
5672 bool IsVirtualFunctionPointerThunk) {
5675 assert(Callee.isOrdinary() || Callee.isVirtual());
5682 llvm::FunctionType *IRFuncTy =
getTypes().GetFunctionType(CallInfo);
5684 const Decl *TargetDecl = Callee.getAbstractInfo().getCalleeDecl().getDecl();
5685 if (
const FunctionDecl *FD = dyn_cast_or_null<FunctionDecl>(TargetDecl)) {
5692 if ((TargetDecl->
hasAttr<AlwaysInlineAttr>() &&
5693 (TargetDecl->
hasAttr<TargetAttr>() ||
5697 TargetDecl->
hasAttr<TargetAttr>())))
5704 const FunctionDecl *CalleeDecl = dyn_cast_or_null<FunctionDecl>(TargetDecl);
5705 CGM.getTargetCodeGenInfo().checkFunctionCallABI(
CGM, Loc, CallerDecl,
5706 CalleeDecl, CallArgs, RetTy);
5713 if (llvm::StructType *ArgStruct = CallInfo.
getArgStruct()) {
5714 const llvm::DataLayout &DL =
CGM.getDataLayout();
5716 llvm::AllocaInst *AI;
5718 IP = IP->getNextNode();
5719 AI =
new llvm::AllocaInst(ArgStruct, DL.getAllocaAddrSpace(),
"argmem",
5725 AI->setAlignment(Align.getAsAlign());
5726 AI->setUsedWithInAlloca(
true);
5727 assert(AI->isUsedWithInAlloca() && !AI->isStaticAlloca());
5728 ArgMemory =
RawAddress(AI, ArgStruct, Align);
5731 ClangToLLVMArgMapping IRFunctionArgs(
CGM.getContext(), CallInfo);
5739 bool NeedSRetLifetimeEnd =
false;
5745 if ((IsVirtualFunctionPointerThunk || IsMustTail) && RetAI.
isIndirect()) {
5747 IRFunctionArgs.getSRetArgNo(),
5755 if (NeedSRetLifetimeEnd)
5756 SRetAlloca = SRetPtr;
5759 if (IRFunctionArgs.hasSRetArg()) {
5772 IRCallArgs[IRFunctionArgs.getSRetArgNo()] =
5790 assert(CallInfo.
arg_size() == CallArgs.size() &&
5791 "Mismatch between function signature & arguments.");
5794 for (CallArgList::const_iterator I = CallArgs.begin(), E = CallArgs.end();
5795 I != E; ++I, ++info_it, ++ArgNo) {
5799 if (IRFunctionArgs.hasPaddingArg(ArgNo))
5800 IRCallArgs[IRFunctionArgs.getPaddingArgNo(ArgNo)] =
5803 unsigned FirstIRArg, NumIRArgs;
5804 std::tie(FirstIRArg, NumIRArgs) = IRFunctionArgs.getIRArgs(ArgNo);
5806 bool ArgHasMaybeUndefAttr =
5811 assert(NumIRArgs == 0);
5813 if (I->isAggregate()) {
5815 ? I->getKnownLValue().getAddress()
5816 : I->getKnownRValue().getAggregateAddress();
5817 llvm::Instruction *Placeholder =
5822 CGBuilderTy::InsertPoint IP =
Builder.saveIP();
5823 Builder.SetInsertPoint(Placeholder);
5837 deferPlaceholderReplacement(Placeholder,
Addr.getPointer());
5842 I->Ty,
getContext().getTypeAlignInChars(I->Ty),
5843 "indirect-arg-temp");
5844 I->copyInto(*
this,
Addr);
5853 I->copyInto(*
this,
Addr);
5860 assert(NumIRArgs == 1);
5861 if (I->isAggregate()) {
5871 ? I->getKnownLValue().getAddress()
5872 : I->getKnownRValue().getAggregateAddress();
5874 const llvm::DataLayout *TD = &
CGM.getDataLayout();
5876 assert((FirstIRArg >= IRFuncTy->getNumParams() ||
5877 IRFuncTy->getParamType(FirstIRArg)->getPointerAddressSpace() ==
5878 TD->getAllocaAddrSpace()) &&
5879 "indirect argument must be in alloca address space");
5881 bool NeedCopy =
false;
5882 if (
Addr.getAlignment() < Align &&
5883 llvm::getOrEnforceKnownAlignment(
Addr.emitRawPointer(*
this),
5887 }
else if (I->hasLValue()) {
5888 auto LV = I->getKnownLValue();
5893 if (!isByValOrRef ||
5894 (LV.getAlignment() <
getContext().getTypeAlignInChars(I->Ty))) {
5898 if (isByValOrRef &&
Addr.getType()->getAddressSpace() !=
5907 auto *
T = llvm::PointerType::get(
CGM.getLLVMContext(),
5915 if (ArgHasMaybeUndefAttr)
5916 Val =
Builder.CreateFreeze(Val);
5917 IRCallArgs[FirstIRArg] = Val;
5920 }
else if (I->getType()->isArrayParameterType()) {
5926 IRCallArgs[FirstIRArg] = I->getKnownRValue().getScalarVal();
5935 if (ArgHasMaybeUndefAttr)
5936 Val =
Builder.CreateFreeze(Val);
5937 IRCallArgs[FirstIRArg] = Val;
5942 CallLifetimeEndAfterCall.emplace_back(AI);
5945 I->copyInto(*
this, AI);
5950 assert(NumIRArgs == 0);
5958 assert(NumIRArgs == 1);
5960 if (!I->isAggregate())
5961 V = I->getKnownRValue().getScalarVal();
5964 I->hasLValue() ? I->getKnownLValue().getAddress()
5965 : I->getKnownRValue().getAggregateAddress());
5971 assert(!swiftErrorTemp.
isValid() &&
"multiple swifterror args");
5975 V, pointeeTy,
getContext().getTypeAlignInChars(pointeeTy));
5982 llvm::Value *errorValue =
Builder.CreateLoad(swiftErrorArg);
5983 Builder.CreateStore(errorValue, swiftErrorTemp);
5988 V->getType()->isIntegerTy())
5995 if (FirstIRArg < IRFuncTy->getNumParams() &&
5996 V->getType() != IRFuncTy->getParamType(FirstIRArg)) {
5997 assert(
V->getType()->isPointerTy() &&
"Only pointers can mismatch!");
6001 if (ArgHasMaybeUndefAttr)
6003 IRCallArgs[FirstIRArg] =
V;
6007 llvm::StructType *STy =
6012 if (!I->isAggregate()) {
6014 I->copyInto(*
this, Src);
6016 Src = I->hasLValue() ? I->getKnownLValue().getAddress()
6017 : I->getKnownRValue().getAggregateAddress();
6027 llvm::TypeSize SrcTypeSize =
6028 CGM.getDataLayout().getTypeAllocSize(SrcTy);
6029 llvm::TypeSize DstTypeSize =
CGM.getDataLayout().getTypeAllocSize(STy);
6030 if (SrcTypeSize.isScalable()) {
6031 assert(STy->containsHomogeneousScalableVectorTypes() &&
6032 "ABI only supports structure with homogeneous scalable vector "
6034 assert(SrcTypeSize == DstTypeSize &&
6035 "Only allow non-fractional movement of structure with "
6036 "homogeneous scalable vector type");
6037 assert(NumIRArgs == STy->getNumElements());
6039 llvm::Value *StoredStructValue =
6041 for (
unsigned i = 0, e = STy->getNumElements(); i != e; ++i) {
6042 llvm::Value *Extract =
Builder.CreateExtractValue(
6043 StoredStructValue, i, Src.
getName() +
".extract" + Twine(i));
6044 IRCallArgs[FirstIRArg + i] = Extract;
6047 uint64_t SrcSize = SrcTypeSize.getFixedValue();
6048 uint64_t DstSize = DstTypeSize.getFixedValue();
6049 bool HasPFPFields =
getContext().hasPFPFields(I->Ty);
6055 if (HasPFPFields || SrcSize < DstSize) {
6066 Builder.CreateMemCpy(TempAlloca, Src, SrcSize);
6072 assert(NumIRArgs == STy->getNumElements());
6073 for (
unsigned i = 0, e = STy->getNumElements(); i != e; ++i) {
6075 llvm::Value *LI =
Builder.CreateLoad(EltPtr);
6076 if (ArgHasMaybeUndefAttr)
6077 LI =
Builder.CreateFreeze(LI);
6078 IRCallArgs[FirstIRArg + i] = LI;
6083 assert(NumIRArgs == 1);
6091 auto *ATy = dyn_cast<llvm::ArrayType>(Load->getType());
6096 if (ArgHasMaybeUndefAttr)
6097 Load =
Builder.CreateFreeze(Load);
6098 IRCallArgs[FirstIRArg] = Load;
6106 auto layout =
CGM.getDataLayout().getStructLayout(coercionType);
6108 auto *unpaddedStruct = dyn_cast<llvm::StructType>(unpaddedCoercionType);
6112 bool NeedLifetimeEnd =
false;
6113 if (I->isAggregate()) {
6114 addr = I->hasLValue() ? I->getKnownLValue().getAddress()
6115 : I->getKnownRValue().getAggregateAddress();
6118 RValue RV = I->getKnownRValue();
6122 auto scalarAlign =
CGM.getDataLayout().getPrefTypeAlign(scalarType);
6127 layout->getAlignment(), scalarAlign)),
6129 nullptr, &AllocaAddr);
6137 unsigned IRArgPos = FirstIRArg;
6138 unsigned unpaddedIndex = 0;
6139 for (
unsigned i = 0, e = coercionType->getNumElements(); i != e; ++i) {
6140 llvm::Type *eltType = coercionType->getElementType(i);
6147 : unpaddedCoercionType,
6149 if (ArgHasMaybeUndefAttr)
6150 elt =
Builder.CreateFreeze(elt);
6151 IRCallArgs[IRArgPos++] = elt;
6153 assert(IRArgPos == FirstIRArg + NumIRArgs);
6155 if (NeedLifetimeEnd)
6161 unsigned IRArgPos = FirstIRArg;
6162 ExpandTypeToArgs(I->Ty, *I, IRFuncTy, IRCallArgs, IRArgPos);
6163 assert(IRArgPos == FirstIRArg + NumIRArgs);
6169 if (!I->isAggregate()) {
6171 I->copyInto(*
this, Src);
6173 Src = I->hasLValue() ? I->getKnownLValue().getAddress()
6174 : I->getKnownRValue().getAggregateAddress();
6180 CGM.getABIInfo().createCoercedLoad(Src, ArgInfo, *
this);
6181 IRCallArgs[FirstIRArg] = Load;
6187 const CGCallee &ConcreteCallee = Callee.prepareConcreteCallee(*
this);
6193 assert(IRFunctionArgs.hasInallocaArg());
6194 IRCallArgs[IRFunctionArgs.getInallocaArgNo()] = Arg;
6205 auto simplifyVariadicCallee = [](llvm::FunctionType *CalleeFT,
6206 llvm::Value *Ptr) -> llvm::Function * {
6207 if (!CalleeFT->isVarArg())
6211 if (llvm::ConstantExpr *CE = dyn_cast<llvm::ConstantExpr>(Ptr)) {
6212 if (CE->getOpcode() == llvm::Instruction::BitCast)
6213 Ptr = CE->getOperand(0);
6216 llvm::Function *OrigFn = dyn_cast<llvm::Function>(Ptr);
6220 llvm::FunctionType *OrigFT = OrigFn->getFunctionType();
6224 if (OrigFT->isVarArg() ||
6225 OrigFT->getNumParams() != CalleeFT->getNumParams() ||
6226 OrigFT->getReturnType() != CalleeFT->getReturnType())
6229 for (
unsigned i = 0, e = OrigFT->getNumParams(); i != e; ++i)
6230 if (OrigFT->getParamType(i) != CalleeFT->getParamType(i))
6236 if (llvm::Function *OrigFn = simplifyVariadicCallee(IRFuncTy, CalleePtr)) {
6238 IRFuncTy = OrigFn->getFunctionType();
6249 for (
unsigned i = 0; i < IRCallArgs.size(); ++i)
6250 LargestVectorWidth = std::max(LargestVectorWidth,
6255 llvm::AttributeList Attrs;
6256 CGM.ConstructAttributeList(CalleePtr->getName(), CallInfo,
6261 if (
CallingConv == llvm::CallingConv::X86_VectorCall &&
6263 CGM.Error(Loc,
"__vectorcall calling convention is not currently "
6268 if (FD->hasAttr<StrictFPAttr>())
6270 Attrs = Attrs.addFnAttribute(
getLLVMContext(), llvm::Attribute::StrictFP);
6275 if (FD->hasAttr<OptimizeNoneAttr>() &&
getLangOpts().FastMath)
6276 CGM.AdjustMemoryAttribute(CalleePtr->getName(), Callee.getAbstractInfo(),
6281 Attrs = Attrs.addFnAttribute(
getLLVMContext(), llvm::Attribute::NoMerge);
6285 Attrs = Attrs.addFnAttribute(
getLLVMContext(), llvm::Attribute::NoInline);
6290 !
CGM.getTargetCodeGenInfo().wouldInliningViolateFunctionCallABI(
6291 CallerDecl, CalleeDecl))
6293 Attrs.addFnAttribute(
getLLVMContext(), llvm::Attribute::AlwaysInline);
6298 Attrs.removeFnAttribute(
getLLVMContext(), llvm::Attribute::Convergent);
6307 !(TargetDecl && TargetDecl->
hasAttr<NoInlineAttr>()) &&
6308 !
CGM.getTargetCodeGenInfo().wouldInliningViolateFunctionCallABI(
6309 CallerDecl, CalleeDecl)) {
6311 Attrs.addFnAttribute(
getLLVMContext(), llvm::Attribute::AlwaysInline);
6316 Attrs = Attrs.addFnAttribute(
getLLVMContext(), llvm::Attribute::NoInline);
6323 CannotThrow =
false;
6332 CannotThrow = Attrs.hasFnAttr(llvm::Attribute::NoUnwind);
6334 if (
auto *FPtr = dyn_cast<llvm::Function>(CalleePtr))
6335 if (FPtr->hasFnAttribute(llvm::Attribute::NoUnwind))
6346 if (NeedSRetLifetimeEnd)
6354 if (
SanOpts.has(SanitizerKind::KCFI) &&
6355 !isa_and_nonnull<FunctionDecl>(TargetDecl))
6362 if (FD->hasAttr<StrictFPAttr>())
6364 Attrs = Attrs.addFnAttribute(
getLLVMContext(), llvm::Attribute::StrictFP);
6366 AssumeAlignedAttrEmitter AssumeAlignedAttrEmitter(*
this, TargetDecl);
6367 Attrs = AssumeAlignedAttrEmitter.TryEmitAsCallSiteAttribute(Attrs);
6369 AllocAlignAttrEmitter AllocAlignAttrEmitter(*
this, TargetDecl, CallArgs);
6370 Attrs = AllocAlignAttrEmitter.TryEmitAsCallSiteAttribute(Attrs);
6375 CI =
Builder.CreateCall(IRFuncTy, CalleePtr, IRCallArgs, BundleList);
6378 CI =
Builder.CreateInvoke(IRFuncTy, CalleePtr, Cont, InvokeDest, IRCallArgs,
6382 if (CI->getCalledFunction() && CI->getCalledFunction()->hasName() &&
6383 CI->getCalledFunction()->getName().starts_with(
"_Z4sqrt")) {
6388 if (
CGM.getCodeGenOpts().CallGraphSection) {
6392 else if (
const auto *FPT =
6393 Callee.getAbstractInfo().getCalleeFunctionProtoType())
6395 else if (
const auto *FT =
6396 Callee.getAbstractInfo().getCalleeFunctionType())
6400 "Cannot find the callee type to generate callee_type metadata.");
6443 for (
const CallArg &Arg : CallArgs)
6444 ParamTypes.push_back(Arg.
getType());
6445 CST =
CGM.ReconstructCallGraphPrototype(FNPT, ParamTypes);
6448 llvm::Metadata *MD =
6449 CGM.CreateMetadataIdentifierForCallGraphType(CST);
6451 if (
auto *MDS = dyn_cast_or_null<llvm::MDString>(MD))
6452 TypeStr = MDS->getString();
6454 CGM.getDiags().Report(Loc, diag::warn_cgs_no_proto) << CST << TypeStr;
6456 CGM.createCalleeTypeMetadataForIcall(CST, *callOrInvoke);
6464 if (
const auto *FD = dyn_cast_or_null<FunctionDecl>(
CurFuncDecl)) {
6465 if (
const auto *A = FD->getAttr<CFGuardAttr>()) {
6466 if (A->getGuard() == CFGuardAttr::GuardArg::nocf &&
6467 !CI->getCalledFunction())
6473 CI->setAttributes(Attrs);
6474 CI->setCallingConv(
static_cast<llvm::CallingConv::ID
>(
CallingConv));
6478 if (!CI->getType()->isVoidTy())
6479 CI->setName(
"call");
6481 if (
CGM.shouldEmitConvergenceTokens() && CI->isConvergent())
6482 CI = addConvergenceControlToken(CI);
6485 LargestVectorWidth =
6491 if (!CI->getCalledFunction())
6492 PGO->valueProfile(
Builder, llvm::IPVK_IndirectCallTarget, CI, CalleePtr);
6496 if (
CGM.getLangOpts().ObjCAutoRefCount)
6497 AddObjCARCExceptionMetadata(CI);
6500 bool IsPPC =
getTarget().getTriple().isPPC();
6501 bool IsMIPS =
getTarget().getTriple().isMIPS();
6502 bool HasMips16 =
false;
6505 HasMips16 = TargetOpts.
FeatureMap.lookup(
"mips16");
6507 HasMips16 = llvm::is_contained(TargetOpts.
Features,
"+mips16");
6509 if (llvm::CallInst *
Call = dyn_cast<llvm::CallInst>(CI)) {
6510 if (TargetDecl && TargetDecl->
hasAttr<NotTailCalledAttr>())
6511 Call->setTailCallKind(llvm::CallInst::TCK_NoTail);
6512 else if (IsMustTail) {
6515 CGM.getDiags().Report(Loc, diag::err_aix_musttail_unsupported);
6518 CGM.getDiags().Report(Loc, diag::err_ppc_impossible_musttail) << 0;
6519 else if (
Call->isIndirectCall())
6520 CGM.getDiags().Report(Loc, diag::err_ppc_impossible_musttail) << 1;
6521 else if (isa_and_nonnull<FunctionDecl>(TargetDecl)) {
6526 CGM.addUndefinedGlobalForTailCall(
6529 llvm::GlobalValue::LinkageTypes
Linkage =
CGM.getFunctionLinkage(
6531 if (llvm::GlobalValue::isWeakForLinker(
Linkage) ||
6532 llvm::GlobalValue::isDiscardableIfUnused(
Linkage))
6533 CGM.getDiags().Report(Loc, diag::err_ppc_impossible_musttail)
6541 CGM.getDiags().Report(Loc, diag::err_mips_impossible_musttail) << 0;
6542 else if (
const auto *FD = dyn_cast_or_null<FunctionDecl>(TargetDecl))
6543 CGM.addUndefinedGlobalForTailCall({FD, Loc});
6545 Call->setTailCallKind(llvm::CallInst::TCK_MustTail);
6559 bool NeedSrcLoc = TargetDecl->
hasAttr<ErrorAttr>();
6560 if (!NeedSrcLoc &&
CGM.getCodeGenOpts().ShowInliningChain) {
6561 if (
const auto *FD = dyn_cast<FunctionDecl>(TargetDecl))
6562 NeedSrcLoc = FD->isInlined() || FD->hasAttr<AlwaysInlineAttr>() ||
6564 FD->isInAnonymousNamespace();
6568 auto *MD = llvm::ConstantAsMetadata::get(
Line);
6569 CI->setMetadata(
"srcloc", llvm::MDNode::get(
getLLVMContext(), {MD}));
6578 if (CI->doesNotReturn()) {
6579 if (NeedSRetLifetimeEnd)
6583 if (
SanOpts.has(SanitizerKind::Unreachable)) {
6586 if (
auto *F = CI->getCalledFunction())
6587 F->removeFnAttr(llvm::Attribute::NoReturn);
6588 CI->removeFnAttr(llvm::Attribute::NoReturn);
6592 if (
SanOpts.hasOneOf(SanitizerKind::Address |
6593 SanitizerKind::KernelAddress)) {
6595 llvm::IRBuilder<>::InsertPointGuard IPGuard(
Builder);
6597 auto *FnType = llvm::FunctionType::get(
CGM.VoidTy,
false);
6598 llvm::FunctionCallee Fn =
6599 CGM.CreateRuntimeFunction(FnType,
"__asan_handle_no_return");
6605 Builder.ClearInsertionPoint();
6627 if (CI->doesNotThrow())
6630 diag::err_musttail_noexcept_mismatch);
6633 if (
auto *Cleanup = dyn_cast<EHCleanupScope>(&*it)) {
6636 if (Cleanup->isFakeUse()) {
6637 CGBuilderTy::InsertPointGuard IPG(
Builder);
6639 Cleanup->getCleanup()->Emit(*
this, EHScopeStack::Cleanup::Flags());
6642 if (Cleanup->isRedundantBeforeReturn())
6645 CGM.ErrorUnsupported(
MustTailCall,
"tail call skipping over cleanups");
6647 if (CI->getType()->isVoidTy())
6651 Builder.ClearInsertionPoint();
6657 if (swiftErrorTemp.
isValid()) {
6658 llvm::Value *errorResult =
Builder.CreateLoad(swiftErrorTemp);
6659 Builder.CreateStore(errorResult, swiftErrorArg);
6676 if (IsVirtualFunctionPointerThunk) {
6689 unsigned unpaddedIndex = 0;
6690 for (
unsigned i = 0, e = coercionType->getNumElements(); i != e; ++i) {
6691 llvm::Type *eltType = coercionType->getElementType(i);
6695 llvm::Value *elt = CI;
6696 if (requiresExtract)
6697 elt =
Builder.CreateExtractValue(elt, unpaddedIndex++);
6699 assert(unpaddedIndex == 0);
6700 Builder.CreateStore(elt, eltAddr);
6708 if (NeedSRetLifetimeEnd)
6725 llvm::Value *Real =
Builder.CreateExtractValue(CI, 0);
6726 llvm::Value *Imag =
Builder.CreateExtractValue(CI, 1);
6734 llvm::Value *
V = CI;
6735 if (
V->getType() != RetIRTy)
6745 if (
auto *FixedDstTy = dyn_cast<llvm::FixedVectorType>(RetIRTy)) {
6746 llvm::Value *
V = CI;
6747 if (
auto *ScalableSrcTy =
6748 dyn_cast<llvm::ScalableVectorType>(
V->getType())) {
6749 if (FixedDstTy->getElementType() ==
6750 ScalableSrcTy->getElementType()) {
6751 V =
Builder.CreateExtractVector(FixedDstTy,
V, uint64_t(0),
6761 getContext().getTypeInfoDataSizeInChars(RetTy).Width.getQuantity();
6765 DestIsVolatile =
false;
6766 DestSize =
getContext().getTypeSizeInChars(RetTy).getQuantity();
6776 CI, RetTy, StorePtr,
6790 DestIsVolatile =
false;
6792 CGM.getABIInfo().createCoercedStore(CI, StorePtr, RetAI, DestIsVolatile,
6799 llvm_unreachable(
"Invalid ABI kind for return argument");
6802 llvm_unreachable(
"Unhandled ABIArgInfo::Kind");
6807 if (Ret.isScalar() && TargetDecl) {
6808 AssumeAlignedAttrEmitter.EmitAsAnAssumption(Loc, RetTy, Ret);
6809 AllocAlignAttrEmitter.EmitAsAnAssumption(Loc, RetTy, Ret);
6827 if (CalleeDecl && !CalleeDecl->
hasAttr<NoDebugAttr>() &&
6828 DI->getCallSiteRelatedAttrs() != llvm::DINode::FlagZero) {
6829 CodeGenFunction CalleeCGF(
CGM);
6831 Callee.getAbstractInfo().getCalleeDecl();
6832 CalleeCGF.
CurGD = CalleeGlobalDecl;
6835 DI->EmitFuncDeclForCallSite(
6836 CI, DI->getFunctionType(CalleeDecl, ResTy, Args), CalleeGlobalDecl);
6839 DI->addCallTargetIfVirtual(CalleeDecl, CI);
6860 VAListAddr =
VE->isMicrosoftABI()
6867 if (
VE->isMicrosoftABI())
6868 return CGM.getABIInfo().EmitMSVAArg(*
this, VAListAddr, Ty, Slot);
6870 return CGM.getABIInfo().EmitZOSVAArg(*
this, VAListAddr, Ty, Slot);
6871 return CGM.getABIInfo().EmitVAArg(*
this, VAListAddr, Ty, Slot);
6876 CGF.disableDebugInfo();
6880 CGF.enableDebugInfo();
static ExtParameterInfoList getExtParameterInfosForCall(const FunctionProtoType *proto, unsigned prefixArgs, unsigned totalArgs)
static bool isInAllocaArgument(CGCXXABI &ABI, QualType type)
static uint64_t buildMultiCharMask(const SmallVectorImpl< uint64_t > &Bits, int Pos, int Size, int CharWidth, bool BigEndian)
static llvm::Value * tryRemoveRetainOfSelf(CodeGenFunction &CGF, llvm::Value *result)
If this is a +1 of the value of an immutable 'self', remove it.
static CanQualType GetReturnType(QualType RetTy)
Returns the "extra-canonicalized" return type, which discards qualifiers on the return type.
static const NonNullAttr * getNonNullAttr(const Decl *FD, const ParmVarDecl *PVD, QualType ArgType, unsigned ArgNo)
Returns the attribute (either parameter attribute, or function attribute), which declares argument Ar...
static CanQualTypeList getArgTypesForCall(ASTContext &ctx, const CallArgList &args)
static Address emitAddressAtOffset(CodeGenFunction &CGF, Address addr, const ABIArgInfo &info)
static const char * abiKindToString(ABIArgInfo::Kind K)
static AggValueSlot createPlaceholderSlot(CodeGenFunction &CGF, QualType Ty)
static CallingConv getCallingConventionForDecl(const ObjCMethodDecl *D, bool IsTargetDefaultMSABI)
static void setBitRange(SmallVectorImpl< uint64_t > &Bits, int BitOffset, int BitWidth, int CharWidth)
static bool isProvablyNull(llvm::Value *addr)
static void AddAttributesFromFunctionProtoType(ASTContext &Ctx, llvm::AttrBuilder &FuncAttrs, const FunctionProtoType *FPT)
static void eraseUnusedBitCasts(llvm::Instruction *insn)
static bool isObjCMethodWithTypeParams(const ObjCMethodDecl *method)
static void emitWritebackArg(CodeGenFunction &CGF, CallArgList &args, const ObjCIndirectCopyRestoreExpr *CRE)
Emit an argument that's being passed call-by-writeback.
static void overrideFunctionFeaturesWithTargetFeatures(llvm::AttrBuilder &FuncAttr, const llvm::Function &F, const TargetOptions &TargetOpts)
Merges target-features from \TargetOpts and \F, and sets the result in \FuncAttr.
static llvm::Value * CreatePFPCoercedLoad(Address Src, QualType SrcFETy, llvm::Type *Ty, CodeGenFunction &CGF)
static int getExpansionSize(QualType Ty, const ASTContext &Context)
static bool DetermineNoUndef(QualType QTy, CodeGenTypes &Types, const llvm::DataLayout &DL, const ABIArgInfo &AI, bool CheckCoerce=true)
static const Expr * maybeGetUnaryAddrOfOperand(const Expr *E)
static void deactivateArgCleanupsBeforeCall(CodeGenFunction &CGF, const CallArgList &CallArgs)
static bool isProvablyNonNull(Address Addr, CodeGenFunction &CGF)
static llvm::Value * emitArgumentDemotion(CodeGenFunction &CGF, const VarDecl *var, llvm::Value *value)
An argument came in as a promoted argument; demote it back to its declared type.
SmallVector< CanQualType, 16 > CanQualTypeList
static std::pair< llvm::Value *, bool > CoerceScalableToFixed(CodeGenFunction &CGF, llvm::FixedVectorType *ToTy, llvm::ScalableVectorType *FromTy, llvm::Value *V, StringRef Name="")
static const CGFunctionInfo & arrangeLLVMFunctionInfo(CodeGenTypes &CGT, bool instanceMethod, SmallVectorImpl< CanQualType > &prefix, CanQual< FunctionProtoType > FTP)
Arrange the LLVM function layout for a value of the given function type, on top of any implicit param...
static llvm::Value * CreateCoercedLoad(Address Src, QualType SrcFETy, llvm::Type *Ty, CodeGenFunction &CGF)
CreateCoercedLoad - Create a load from.
static void addExtParameterInfosForCall(llvm::SmallVectorImpl< FunctionProtoType::ExtParameterInfo > ¶mInfos, const FunctionProtoType *proto, unsigned prefixArgs, unsigned totalArgs)
static bool canApplyNoFPClass(const ABIArgInfo &AI, QualType ParamType, bool IsReturn)
Test if it's legal to apply nofpclass for the given parameter type and it's lowered IR type.
static void getTrivialDefaultFunctionAttributes(StringRef Name, bool HasOptnone, const CodeGenOptions &CodeGenOpts, const LangOptions &LangOpts, bool AttrOnCallSite, llvm::AttrBuilder &FuncAttrs)
static void forConstantArrayExpansion(CodeGenFunction &CGF, ConstantArrayExpansion *CAE, Address BaseAddr, llvm::function_ref< void(Address)> Fn)
static bool IsArgumentMaybeUndef(const Decl *TargetDecl, unsigned NumRequiredArgs, unsigned ArgNo)
Check if the argument of a function has maybe_undef attribute.
static bool hasInAllocaArgs(CodeGenModule &CGM, CallingConv ExplicitCC, ArrayRef< QualType > ArgTypes)
static std::unique_ptr< TypeExpansion > getTypeExpansion(QualType Ty, const ASTContext &Context)
SmallVector< FunctionProtoType::ExtParameterInfo, 16 > ExtParameterInfoList
static RawAddress CreateTempAllocaForCoercion(CodeGenFunction &CGF, llvm::Type *Ty, CharUnits MinAlign, const Twine &Name="tmp")
Create a temporary allocation for the purposes of coercion.
static void setUsedBits(CodeGenModule &, QualType, int, SmallVectorImpl< uint64_t > &)
static llvm::StoreInst * findDominatingStoreToReturnValue(CodeGenFunction &CGF)
Heuristically search for a dominating store to the return-value slot.
static llvm::Value * tryEmitFusedAutoreleaseOfResult(CodeGenFunction &CGF, llvm::Value *result)
Try to emit a fused autorelease of a return result.
static Address EnterStructPointerForCoercedAccess(Address SrcPtr, llvm::StructType *SrcSTy, uint64_t DstSize, CodeGenFunction &CGF)
EnterStructPointerForCoercedAccess - Given a struct pointer that we are accessing some number of byte...
static llvm::Value * emitAutoreleaseOfResult(CodeGenFunction &CGF, llvm::Value *result)
Emit an ARC autorelease of the result of a function.
static void emitWriteback(CodeGenFunction &CGF, const CallArgList::Writeback &writeback)
Emit the actual writing-back of a writeback.
static bool HasStrictReturn(const CodeGenModule &Module, QualType RetTy, const Decl *TargetDecl)
static CanQualTypeList getArgTypesForDeclaration(ASTContext &ctx, const FunctionArgList &args)
static void addMergableDefaultFunctionAttributes(const CodeGenOptions &CodeGenOpts, llvm::AttrBuilder &FuncAttrs)
Add default attributes to a function, which have merge semantics under -mlink-builtin-bitcode and sho...
static bool CreatePFPCoercedStore(llvm::Value *Src, QualType SrcFETy, Address Dst, CodeGenFunction &CGF)
static llvm::Value * CoerceIntOrPtrToIntOrPtr(llvm::Value *Val, llvm::Type *Ty, CodeGenFunction &CGF)
CoerceIntOrPtrToIntOrPtr - Convert a value Val to the specific Ty where both are either integers or p...
static void AddAttributesFromOMPAssumes(llvm::AttrBuilder &FuncAttrs, const Decl *Callee)
static unsigned getMaxVectorWidth(const llvm::Type *Ty)
CodeGenFunction::ComplexPairTy ComplexPairTy
static void setCUDAKernelCallingConvention(CanQualType &funcTy, CIRGenModule &cgm, const FunctionDecl *fd)
Set calling convention for CUDA/HIP kernel.
static void addNoBuiltinAttributes(mlir::MLIRContext &ctx, mlir::NamedAttrList &attrs, const LangOptions &langOpts, const NoBuiltinAttr *nba=nullptr)
static void addDenormalModeAttrs(llvm::DenormalMode fpDenormalMode, llvm::DenormalMode fp32DenormalMode, mlir::NamedAttrList &attrs)
Add denormal-fp-math and denormal-fp-math-f32 as appropriate for the requested denormal behavior,...
static void appendParameterTypes(const CIRGenTypes &cgt, SmallVectorImpl< CanQualType > &prefix, CanQual< FunctionProtoType > fpt)
Adds the formal parameters in FPT to the given prefix.
static const CIRGenFunctionInfo & arrangeFreeFunctionLikeCall(CIRGenTypes &cgt, CIRGenModule &cgm, const CallArgList &args, const FunctionType *fnType)
Defines the C++ Decl subclasses, other than those for templates (found in DeclTemplate....
Result
Implement __builtin_bit_cast and related operations.
#define CC_VLS_CASE(ABI_VLEN)
static bool hasFeature(StringRef Feature, const LangOptions &LangOpts, const TargetInfo &Target)
Determine whether a translation unit built using the current language options has the given feature.
static StringRef getTriple(const Command &Job)
Maps Clang QualType instances to corresponding LLVM ABI type representations.
static QualType getPointeeType(const MemRegion *R)
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
CanQualType getCanonicalParamType(QualType T) const
Return the canonical parameter type corresponding to the specific potentially non-canonical one.
CanQualType getCanonicalSizeType() const
const TargetInfo & getTargetInfo() const
CharUnits toCharUnitsFromBits(int64_t BitSize) const
Convert a size in bits to a size in characters.
std::vector< PFPField > findPFPFields(QualType Ty) const
Returns a list of PFP fields for the given type, including subfields in bases or other fields,...
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.
Represents an array type, per C99 6.7.5.2 - Array Declarators.
Attr - This represents one attribute.
This class is used for builtin types like 'int'.
QualType getType() const
Retrieves the type of the base class.
Represents a C++ constructor within a class.
Represents a C++ destructor within a class.
Represents a static or instance method of a struct/union/class.
bool isImplicitObjectMemberFunction() const
[C++2b][dcl.fct]/p7 An implicit object member function is a non-static member function without an exp...
const CXXRecordDecl * getParent() const
Return the parent of this method declaration, which is the class in which this method is defined.
Qualifiers getMethodQualifiers() const
Represents a C++ struct/union/class.
CXXDestructorDecl * getDestructor() const
Returns the destructor decl for this class.
unsigned getNumVBases() const
Retrieves the number of virtual base classes of this class.
CallExpr - Represents a function call (C99 6.5.2.2, C++ [expr.call]).
SourceLocation getBeginLoc() const
ConstExprIterator const_arg_iterator
Represents a canonical, potentially-qualified type.
static CanQual< Type > CreateUnsafe(QualType Other)
CanProxy< U > castAs() const
CanQual< T > getUnqualifiedType() const
Retrieve the unqualified form of this type.
CanProxy< U > getAs() const
Retrieve a canonical type pointer with a different static type, upcasting or downcasting as needed.
const T * getTypePtr() const
Retrieve the underlying type pointer, which refers to a canonical type.
CharUnits - This is an opaque type for sizes expressed in character units.
bool isZero() const
isZero - Test whether the quantity equals zero.
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 fromQuantity(QuantityType Quantity)
fromQuantity - Construct a CharUnits quantity from a raw integer type.
static CharUnits Zero()
Zero - Construct a CharUnits quantity of zero.
CodeGenOptions - Track various options which control how the code is optimized and passed to the back...
llvm::DenormalMode FPDenormalMode
The floating-point denormal mode to use.
static StringRef getFramePointerKindName(FramePointerKind Kind)
std::vector< std::string > Reciprocals
llvm::DenormalMode FP32DenormalMode
The floating-point denormal mode to use, for float.
std::string TrapFuncName
If not an empty string, trap intrinsics are lowered to calls to this function instead of to trap inst...
std::vector< std::string > DefaultFunctionAttrs
std::string PreferVectorWidth
The preferred width for auto-vectorization transforms.
ABIArgInfo - Helper class to encapsulate information about how a specific C type should be passed to ...
static ABIArgInfo getZeroExtend(QualType Ty, llvm::Type *T=nullptr, llvm::Type *Padding=nullptr)
unsigned getInAllocaFieldIndex() const
static ABIArgInfo getSignExtend(QualType Ty, llvm::Type *T=nullptr, llvm::Type *Padding=nullptr)
bool getIndirectByVal() const
llvm::StructType * getCoerceAndExpandType() const
bool getIndirectRealign() const
static ABIArgInfo getIgnore()
void setCoerceToType(llvm::Type *T)
llvm::Type * getUnpaddedCoerceAndExpandType() const
bool getCanBeFlattened() const
unsigned getDirectOffset() const
static bool isPaddingForCoerceAndExpand(llvm::Type *eltType)
bool getInAllocaSRet() const
Return true if this field of an inalloca struct should be returned to implement a struct return calli...
llvm::Type * getPaddingType() const
bool getPaddingInReg() const
unsigned getDirectAlign() const
unsigned getIndirectAddrSpace() const
static ABIArgInfo getDirect(llvm::Type *T=nullptr, unsigned Offset=0, llvm::Type *Padding=nullptr, bool CanBeFlattened=true, unsigned Align=0)
@ Extend
Extend - Valid only for integer argument types.
@ Ignore
Ignore - Ignore the argument (treat as void).
@ IndirectAliased
IndirectAliased - Similar to Indirect, but the pointer may be to an object that is otherwise referenc...
@ Expand
Expand - Only valid for aggregate argument types.
@ TargetSpecific
TargetSpecific - Some argument types are passed as target specific types such as RISC-V's tuple type,...
@ InAlloca
InAlloca - Pass the argument directly using the LLVM inalloca attribute.
@ Indirect
Indirect - Pass the argument indirectly via a hidden pointer with the specified alignment (0 indicate...
@ CoerceAndExpand
CoerceAndExpand - Only valid for aggregate argument types.
@ Direct
Direct - Pass the argument directly using the normal converted LLVM type, or by coercing to another s...
static ABIArgInfo getExtend(QualType Ty, llvm::Type *T=nullptr, llvm::Type *Padding=nullptr)
static ABIArgInfo getIndirect(CharUnits Alignment, unsigned AddrSpace, bool ByVal=true, bool Realign=false, llvm::Type *Padding=nullptr)
ArrayRef< llvm::Type * > getCoerceAndExpandTypeSequence() const
static ABIArgInfo getIndirectAliased(CharUnits Alignment, unsigned AddrSpace, bool Realign=false, llvm::Type *Padding=nullptr)
Pass this in memory using the IR byref attribute.
bool isCoerceAndExpand() const
unsigned getInAllocaIndirect() const
llvm::Type * getCoerceToType() const
bool isIndirectAliased() const
bool isSRetAfterThis() const
bool canHaveCoerceToType() const
CharUnits getIndirectAlign() const
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.
unsigned getAddressSpace() const
Return the address space that this address resides in.
KnownNonNull_t isKnownNonNull() const
Whether the pointer is known not to be null.
llvm::StringRef getName() const
Return the IR name of the pointer value.
Address getAddress() const
void setExternallyDestructed(bool destructed=true)
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.
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.
llvm::Value * CreateIsNull(Address Addr, const Twine &Name="")
Address CreateConstGEP2_32(Address Addr, unsigned Idx0, unsigned Idx1, const llvm::Twine &Name="")
Address CreateStructGEP(Address Addr, unsigned Index, const llvm::Twine &Name="")
llvm::LoadInst * CreateLoad(Address Addr, const llvm::Twine &Name="")
llvm::CallInst * CreateMemCpy(Address Dest, Address Src, llvm::Value *Size, bool IsVolatile=false)
llvm::LoadInst * CreateAlignedLoad(llvm::Type *Ty, llvm::Value *Addr, CharUnits Align, const llvm::Twine &Name="")
Implements C++ ABI-specific code generation functions.
virtual bool hasMostDerivedReturn(GlobalDecl GD) const
virtual bool HasThisReturn(GlobalDecl GD) const
Returns true if the given constructor or destructor is one of the kinds that the ABI says returns 'th...
@ RAA_DirectInMemory
Pass it on the stack using its defined layout.
virtual CGCallee getVirtualFunctionPointer(CodeGenFunction &CGF, GlobalDecl GD, Address This, llvm::Type *Ty, SourceLocation Loc)=0
Build a virtual function pointer in the ABI-specific way.
virtual RecordArgABI getRecordArgABI(const CXXRecordDecl *RD) const =0
Returns how an argument of the given record type should be passed.
virtual const CXXRecordDecl * getThisArgumentTypeForMethod(GlobalDecl GD)
Get the type of the implicit "this" parameter used by a method.
virtual AddedStructorArgCounts buildStructorSignature(GlobalDecl GD, SmallVectorImpl< CanQualType > &ArgTys)=0
Build the signature of the given constructor or destructor variant by adding any required parameters.
Abstract information about a function or function prototype.
const GlobalDecl getCalleeDecl() const
const FunctionProtoType * getCalleeFunctionProtoType() const
All available information about a concrete callee.
CGCallee prepareConcreteCallee(CodeGenFunction &CGF) const
If this is a delayed callee computation of some sort, prepare a concrete callee.
Address getThisAddress() const
const CallExpr * getVirtualCallExpr() const
llvm::Value * getFunctionPointer() const
llvm::FunctionType * getVirtualFunctionType() const
const CGPointerAuthInfo & getPointerAuthInfo() const
GlobalDecl getVirtualMethodDecl() const
This class gathers all debug information during compilation and is responsible for emitting to llvm g...
CGFunctionInfo - Class to encapsulate the information about a function definition.
bool usesInAlloca() const
Return true if this function uses inalloca arguments.
FunctionType::ExtInfo getExtInfo() const
bool isInstanceMethod() const
ABIArgInfo & getReturnInfo()
bool isReturnsRetained() const
In ARC, whether this function retains its return value.
unsigned getCallingConvention() const
getCallingConvention - Return the user specified calling convention, which has been translated into a...
void Profile(llvm::FoldingSetNodeID &ID)
const_arg_iterator arg_begin() const
ArrayRef< ExtParameterInfo > getExtParameterInfos() const
CanQualType getReturnType() const
static CGFunctionInfo * create(unsigned llvmCC, bool instanceMethod, bool chainCall, bool delegateCall, unsigned X86ABIAVXLevel, const FunctionType::ExtInfo &extInfo, ArrayRef< ExtParameterInfo > paramInfos, CanQualType resultType, ArrayRef< CanQualType > argTypes, RequiredArgs required)
const ArgInfo * const_arg_iterator
bool isCmseNSCall() const
bool isDelegateCall() const
MutableArrayRef< ArgInfo > arguments()
const_arg_iterator arg_end() const
unsigned getEffectiveCallingConvention() const
getEffectiveCallingConvention - Return the actual calling convention to use, which may depend on the ...
unsigned getX86ABIAVXLevel() const
ExtParameterInfo getExtParameterInfo(unsigned argIndex) const
CharUnits getArgStructAlignment() const
unsigned arg_size() const
RequiredArgs getRequiredArgs() const
unsigned getNumRequiredArgs() const
llvm::StructType * getArgStruct() const
Get the struct type used to represent all the arguments in memory.
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.
CallArgList - Type for representing both the value and type of arguments in a call.
void addWriteback(LValue srcLV, Address temporary, llvm::Value *toUse, const Expr *writebackExpr=nullptr)
llvm::Instruction * getStackBase() const
void addUncopiedAggregate(LValue LV, QualType type)
void addArgCleanupDeactivation(EHScopeStack::stable_iterator Cleanup, llvm::Instruction *IsActiveIP)
ArrayRef< CallArgCleanup > getCleanupsToDeactivate() const
bool hasWritebacks() const
void add(RValue rvalue, QualType type)
bool isUsingInAlloca() const
Returns if we're using an inalloca struct to pass arguments in memory.
void allocateArgumentMemory(CodeGenFunction &CGF)
void freeArgumentMemory(CodeGenFunction &CGF) const
writeback_const_range writebacks() const
An abstract representation of regular/ObjC call/message targets.
const ParmVarDecl * getParamDecl(unsigned I) const
const Decl * getDecl() const
unsigned getNumParams() const
bool hasFunctionDecl() const
An object to manage conditionally-evaluated expressions.
void begin(CodeGenFunction &CGF)
void end(CodeGenFunction &CGF)
static ParamValue forIndirect(Address addr)
static ParamValue forDirect(llvm::Value *value)
RAII object to set/unset CodeGenFunction::IsSanitizerScope.
CodeGenFunction - This class organizes the per-function state that is used while generating LLVM code...
EHScopeStack::stable_iterator CurrentCleanupScopeDepth
GlobalDecl CurGD
CurGD - The GlobalDecl for the current function being compiled.
llvm::Value * EmitARCRetainAutoreleaseReturnValue(llvm::Value *value)
Do a fused retain/autorelease of the given object.
llvm::Value * performAddrSpaceCast(llvm::Value *Src, llvm::Type *DestTy)
SanitizerSet SanOpts
Sanitizers enabled for this function.
void checkTargetFeatures(const CallExpr *E, const FunctionDecl *TargetDecl)
static bool hasScalarEvaluationKind(QualType T)
llvm::Type * ConvertType(QualType T)
bool isCleanupPadScope() const
Returns true while emitting a cleanuppad.
void addInstToNewSourceAtom(llvm::Instruction *KeyInstruction, llvm::Value *Backup)
Add KeyInstruction and an optional Backup instruction to a new atom group (See ApplyAtomGroup for mor...
llvm::CallBase * EmitCallOrInvoke(llvm::FunctionCallee Callee, ArrayRef< llvm::Value * > Args, const Twine &Name="")
Emits a call or invoke instruction to the given function, depending on the current state of the EH st...
void EmitNoreturnRuntimeCallOrInvoke(llvm::FunctionCallee callee, ArrayRef< llvm::Value * > args)
Emits a call or invoke to the given noreturn runtime function.
llvm::CallBase * EmitRuntimeCallOrInvoke(llvm::FunctionCallee callee, ArrayRef< llvm::Value * > args, const Twine &name="")
Emits a call or invoke instruction to the given runtime function.
void callCStructDestructor(LValue Dst)
ComplexPairTy EmitLoadOfComplex(LValue src, SourceLocation loc)
EmitLoadOfComplex - Load a complex number from the specified l-value.
llvm::Value * EmitARCAutoreleaseReturnValue(llvm::Value *value)
Autorelease the given object.
bool shouldUseFusedARCCalls()
bool CurFuncIsThunk
In C++, whether we are code generating a thunk.
bool isSEHTryScope() const
Returns true inside SEH __try blocks.
RValue convertTempToRValue(Address addr, QualType type, SourceLocation Loc)
Given the address of a temporary variable, produce an r-value of its type.
llvm::Constant * EmitCheckSourceLocation(SourceLocation Loc)
Emit a description of a source location in a format suitable for passing to a runtime sanitizer handl...
void SetSqrtFPAccuracy(llvm::Value *Val)
Set the minimum required accuracy of the given sqrt operation based on CodeGenOpts.
RValue EmitVAArg(VAArgExpr *VE, Address &VAListAddr, AggValueSlot Slot=AggValueSlot::ignored())
Generate code to get an argument from the passed in pointer and update it accordingly.
void EmitReturnValueCheck(llvm::Value *RV)
Emit a test that checks if the return value RV is nonnull.
llvm::Value * getAsNaturalPointerTo(Address Addr, QualType PointeeType)
void EmitDelegateCallArg(CallArgList &args, const VarDecl *param, SourceLocation loc)
EmitDelegateCallArg - We are performing a delegate call; that is, the current function is delegating ...
llvm::BasicBlock * createBasicBlock(const Twine &name="", llvm::Function *parent=nullptr, llvm::BasicBlock *before=nullptr)
createBasicBlock - Create an LLVM basic block.
void addInstToCurrentSourceAtom(llvm::Instruction *KeyInstruction, llvm::Value *Backup)
See CGDebugInfo::addInstToCurrentSourceAtom.
const LangOptions & getLangOpts() const
void addInstToSpecificSourceAtom(llvm::Instruction *KeyInstruction, llvm::Value *Backup, uint64_t Atom)
See CGDebugInfo::addInstToSpecificSourceAtom.
RValue EmitReferenceBindingToExpr(const Expr *E)
Emits a reference binding to the passed in expression.
LValue MakeNaturalAlignAddrLValue(llvm::Value *V, QualType T, KnownNonNull_t IsKnownNonNull=NotKnownNonNull)
bool InNoConvergentAttributedStmt
True if the current statement has noconvergent attribute.
void pushDestroy(QualType::DestructionKind dtorKind, Address addr, QualType type)
pushDestroy - Push the standard destructor for the given type as at least a normal cleanup.
const CodeGen::CGBlockInfo * BlockInfo
void EmitKCFIOperandBundle(const CGCallee &Callee, SmallVectorImpl< llvm::OperandBundleDef > &Bundles)
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.
void EmitCXXDestructorCall(const CXXDestructorDecl *D, CXXDtorType Type, bool ForVirtualBase, bool Delegating, Address This, QualType ThisTy)
bool InNoMergeAttributedStmt
True if the current statement has nomerge attribute.
const Decl * CurCodeDecl
CurCodeDecl - This is the inner-most code context, which includes blocks.
llvm::BasicBlock * getUnreachableBlock()
void EmitARCRelease(llvm::Value *value, ARCPreciseLifetime_t precise)
Release the given object.
bool currentFunctionUsesSEHTry() const
JumpDest ReturnBlock
ReturnBlock - Unified return block.
void CreateCoercedStore(llvm::Value *Src, QualType SrcFETy, Address Dst, llvm::TypeSize DstSize, bool DstIsVolatile)
Create a store to.
@ ForceLeftToRight
! Language semantics require left-to-right evaluation.
@ ForceRightToLeft
! Language semantics require right-to-left evaluation.
void EmitNonNullArgCheck(RValue RV, QualType ArgType, SourceLocation ArgLoc, AbstractCallee AC, unsigned ParmNum)
Create a check for a function parameter that may potentially be declared as non-null.
void EmitAggregateCopy(LValue Dest, LValue Src, QualType EltTy, AggValueSlot::Overlap_t MayOverlap, bool isVolatile=false)
EmitAggregateCopy - Emit an aggregate copy.
const TargetInfo & getTarget() const
LValue EmitHLSLOutArgExpr(const HLSLOutArgExpr *E, CallArgList &Args, QualType Ty)
void EmitWritebacks(const CallArgList &Args)
EmitWriteback - Emit callbacks for function.
void EmitIgnoredExpr(const Expr *E)
EmitIgnoredExpr - Emit an expression in a context which ignores the result.
RValue EmitLoadOfLValue(LValue V, SourceLocation Loc)
EmitLoadOfLValue - Given an expression that represents a value lvalue, this method emits the address ...
void DeactivateCleanupBlock(EHScopeStack::stable_iterator Cleanup, llvm::Instruction *DominatingIP)
DeactivateCleanupBlock - Deactivates the given cleanup block.
void pushFullExprCleanup(CleanupKind kind, As... A)
pushFullExprCleanup - Push a cleanup to be run at the end of the current full-expression.
llvm::BasicBlock * getInvokeDest()
void EmitCallArg(CallArgList &args, const Expr *E, QualType ArgType)
EmitCallArg - Emit a single call argument.
void EmitPointerAuthOperandBundle(const CGPointerAuthInfo &Info, SmallVectorImpl< llvm::OperandBundleDef > &Bundles)
void EmitCheck(ArrayRef< std::pair< llvm::Value *, SanitizerKind::SanitizerOrdinal > > Checked, SanitizerHandler Check, ArrayRef< llvm::Constant * > StaticArgs, ArrayRef< llvm::Value * > DynamicArgs, const TrapReason *TR=nullptr)
Create a basic block that will either trap or call a handler function in the UBSan runtime with the p...
AggValueSlot CreateAggTemp(QualType T, const Twine &Name="tmp", RawAddress *Alloca=nullptr)
CreateAggTemp - Create a temporary memory object for the given aggregate type.
llvm::CallInst * EmitIntrinsicCall(llvm::Intrinsic::ID ID, const Twine &Name="")
bool HaveInsertPoint() const
HaveInsertPoint - True if an insertion point is defined.
CGDebugInfo * getDebugInfo()
bool EmitLifetimeStart(llvm::Value *Addr)
Emit a lifetime.begin marker if some criteria are satisfied.
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...
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 EmitLifetimeEnd(llvm::Value *Addr)
RawAddress CreateMemTempWithoutCast(QualType T, const Twine &Name="tmp")
CreateMemTemp - Create a temporary memory object of the given type, with appropriate alignmen without...
bool InNoInlineAttributedStmt
True if the current statement has noinline attribute.
SmallVector< llvm::OperandBundleDef, 1 > getBundlesForFunclet(llvm::Value *Callee)
RValue EmitAnyExprToTemp(const Expr *E)
EmitAnyExprToTemp - Similarly to EmitAnyExpr(), however, the result will always be accessible even if...
llvm::CallInst * EmitNounwindRuntimeCall(llvm::FunctionCallee callee, const Twine &name="")
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 EmitStoreOfComplex(ComplexPairTy V, LValue dest, bool isInit)
EmitStoreOfComplex - Store a complex number into the specified l-value.
const Decl * CurFuncDecl
CurFuncDecl - Holds the Decl for the current outermost non-closure context.
void EmitFunctionProlog(const CGFunctionInfo &FI, llvm::Function *Fn, const FunctionArgList &Args)
EmitFunctionProlog - Emit the target specific LLVM code to load the arguments for the given function.
Address EmitAddressOfPFPField(Address RecordPtr, const PFPField &Field)
void EmitStoreThroughLValue(RValue Src, LValue Dst, bool isInit=false)
EmitStoreThroughLValue - Store the specified rvalue into the specified lvalue, where both are guarant...
Address EmitVAListRef(const Expr *E)
RValue GetUndefRValue(QualType Ty)
GetUndefRValue - Get an appropriate 'undef' rvalue for the given type.
void EmitParmDecl(const VarDecl &D, ParamValue Arg, unsigned ArgNo)
EmitParmDecl - Emit a ParmVarDecl or an ImplicitParamDecl.
bool AutoreleaseResult
In ARC, whether we should autorelease the return value.
llvm::CallInst * EmitRuntimeCall(llvm::FunctionCallee callee, const Twine &name="")
llvm::Value * EmitARCRetainNonBlock(llvm::Value *value)
Retain the given object, with normal retain semantics.
llvm::Type * ConvertTypeForMem(QualType T)
Address EmitZOSVAListRef(const Expr *E)
Emit a "reference" to a __builtin_zos_va_list; this is always the address of the expression,...
CodeGenTypes & getTypes() const
static TypeEvaluationKind getEvaluationKind(QualType T)
getEvaluationKind - Return the TypeEvaluationKind of QualType T.
bool InAlwaysInlineAttributedStmt
True if the current statement has always_inline attribute.
void EmitFunctionEpilog(const CGFunctionInfo &FI, bool EmitRetDbgLoc, SourceLocation EndLoc, uint64_t RetKeyInstructionsSourceAtom)
EmitFunctionEpilog - Emit the target specific LLVM code to return the given temporary.
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...
void EmitAggExpr(const Expr *E, AggValueSlot AS)
EmitAggExpr - Emit the computation of the specified expression of aggregate type.
Address EmitMSVAListRef(const Expr *E)
Emit a "reference" to a __builtin_ms_va_list; this is always the value of the expression,...
llvm::Value * EmitScalarExpr(const Expr *E, bool IgnoreResultAssign=false)
EmitScalarExpr - Emit the computation of the specified expression of LLVM scalar type,...
static bool hasAggregateEvaluationKind(QualType T)
void EmitCallArgs(CallArgList &Args, PrototypeWrapper Prototype, llvm::iterator_range< CallExpr::const_arg_iterator > ArgRange, AbstractCallee AC=AbstractCallee(), unsigned ParamsToSkip=0, EvaluationOrder Order=EvaluationOrder::Default)
EmitCallArgs - Emit call arguments for a function.
LValue MakeAddrLValue(Address Addr, QualType T, AlignmentSource Source=AlignmentSource::Type)
const CallExpr * MustTailCall
Address GetAddrOfLocalVar(const VarDecl *VD)
GetAddrOfLocalVar - Return the address of a local variable.
void EmitUnreachable(SourceLocation Loc)
Emit a reached-unreachable diagnostic if Loc is valid and runtime checking is enabled.
std::pair< llvm::Value *, llvm::Value * > ComplexPairTy
Address ReturnValue
ReturnValue - The temporary alloca to hold the return value.
LValue EmitLValue(const Expr *E, KnownNonNull_t IsKnownNonNull=NotKnownNonNull)
EmitLValue - Emit code to compute a designator that specifies the location of the expression.
llvm::Instruction * CurrentFuncletPad
void EnsureInsertPoint()
EnsureInsertPoint - Ensure that an insertion point is defined so that emitted IR has a place to go.
llvm::LLVMContext & getLLVMContext()
void emitAlignmentAssumption(llvm::Value *PtrValue, QualType Ty, SourceLocation Loc, SourceLocation AssumptionLoc, llvm::Value *Alignment, llvm::Value *OffsetValue=nullptr)
void EmitVariablyModifiedType(QualType Ty)
EmitVLASize - Capture all the sizes for the VLA expressions in the given variably-modified type and s...
llvm::Value * EmitNonNullRValueCheck(RValue RV, QualType T)
Create a check that a scalar RValue is non-null.
void EmitARCIntrinsicUse(ArrayRef< llvm::Value * > values)
Given a number of pointers, inform the optimizer that they're being intrinsically used up until this ...
llvm::Value * EmitCMSEClearRecord(llvm::Value *V, llvm::IntegerType *ITy, QualType RTy)
void PopCleanupBlock(bool FallThroughIsBranchThrough=false, bool ForDeactivation=false)
PopCleanupBlock - Will pop the cleanup entry on the stack and process all branch fixups.
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...
void EmitBlock(llvm::BasicBlock *BB, bool IsFinished=false)
EmitBlock - Emit the given block.
QualType BuildFunctionArgList(GlobalDecl GD, FunctionArgList &Args)
This class organizes the cross-function state that is used while generating LLVM code.
const ABIInfo & getABIInfo()
bool ReturnTypeUsesFPRet(QualType ResultType)
Return true iff the given type uses 'fpret' when used as a return type.
const LangOptions & getLangOpts() const
CharUnits getNaturalTypeAlignment(QualType T, LValueBaseInfo *BaseInfo=nullptr, TBAAAccessInfo *TBAAInfo=nullptr, bool forPointeeType=false)
CodeGenTypes & getTypes()
const TargetInfo & getTarget() const
void computeABIInfoUsingLib(CGFunctionInfo &FI)
Drive the experimental LLVMABI-based lowering path: map argument and return types into the LLVMABI li...
const llvm::DataLayout & getDataLayout() const
ObjCEntrypoints & getObjCEntrypoints() const
CGCXXABI & getCXXABI() const
bool ReturnTypeUsesFP2Ret(QualType ResultType)
Return true iff the given type uses 'fp2ret' when used as a return type.
bool ReturnSlotInterferesWithArgs(const CGFunctionInfo &FI)
Return true iff the given type uses an argument slot when 'sret' is used as a return type.
bool ReturnTypeHasInReg(const CGFunctionInfo &FI)
Return true iff the given type has inreg set.
void AdjustMemoryAttribute(StringRef Name, CGCalleeInfo CalleeInfo, llvm::AttributeList &Attrs)
Adjust Memory attribute to ensure that the BE gets the right attribute.
void ConstructAttributeList(StringRef Name, const CGFunctionInfo &Info, CGCalleeInfo CalleeInfo, llvm::AttributeList &Attrs, unsigned &CallingConv, bool AttrOnCallSite, bool IsThunk)
Get the LLVM attributes and calling convention to use for a particular function type.
const llvm::abi::TargetInfo & getLLVMABITargetInfo(llvm::abi::TypeBuilder &TB)
Lazily build and return the LLVMABI library's TargetInfo for the current target.
ASTContext & getContext() const
bool ReturnTypeUsesSRet(const CGFunctionInfo &FI)
Return true iff the given type uses 'sret' when used as a return type.
const TargetCodeGenInfo & getTargetCodeGenInfo()
const CodeGenOptions & getCodeGenOpts() const
void addDefaultFunctionDefinitionAttributes(llvm::AttrBuilder &attrs)
Like the overload taking a Function &, but intended specifically for frontends that want to build on ...
CharUnits getNaturalPointeeTypeAlignment(QualType T, LValueBaseInfo *BaseInfo=nullptr, TBAAAccessInfo *TBAAInfo=nullptr)
llvm::LLVMContext & getLLVMContext()
CharUnits getMinimumObjectSize(QualType Ty)
Returns the minimum object size for an object of the given type.
bool MayDropFunctionReturn(const ASTContext &Context, QualType ReturnType) const
Whether this function's return type has no side effects, and thus may be trivially discarded if it is...
This class organizes the cross-module state that is used while lowering AST types to LLVM types.
const CGFunctionInfo & arrangeLLVMFunctionInfo(CanQualType returnType, FnInfoOpts opts, ArrayRef< CanQualType > argTypes, FunctionType::ExtInfo info, ArrayRef< FunctionProtoType::ExtParameterInfo > paramInfos, RequiredArgs args, const FunctionDecl *ABIInfoFD)
"Arrange" the LLVM information for a call or type with the given signature.
const CGFunctionInfo & arrangeFreeFunctionCall(const CallArgList &Args, const FunctionType *Ty, bool ChainCall, const FunctionDecl *ABIInfoFD)
Figure out the rules for calling a function with the given formal type using the given arguments.
const CGFunctionInfo & arrangeCXXMethodType(const CXXRecordDecl *RD, const FunctionProtoType *FTP, const CXXMethodDecl *MD)
Arrange the argument and result information for a call to an unknown C++ non-static member function o...
const CGFunctionInfo & arrangeCXXConstructorCall(const CallArgList &Args, const CXXConstructorDecl *D, CXXCtorType CtorKind, unsigned ExtraPrefixArgs, unsigned ExtraSuffixArgs, const FunctionDecl *ABIInfoFD, bool PassProtoArgs=true)
Arrange a call to a C++ method, passing the given arguments.
llvm::Type * ConvertType(QualType T)
ConvertType - Convert type T into a llvm::Type.
CGCXXABI & getCXXABI() const
const CGFunctionInfo & arrangeCXXMethodCall(const CallArgList &args, const FunctionProtoType *type, RequiredArgs required, unsigned numPrefixArgs, const FunctionDecl *ABIInfoFD)
Arrange a call to a C++ method, passing the given arguments.
const CGFunctionInfo & arrangeCXXMethodDeclaration(const CXXMethodDecl *MD)
C++ methods have some special rules and also have implicit parameters.
ASTContext & getContext() const
const CGFunctionInfo & arrangeFreeFunctionType(CanQual< FunctionProtoType > Ty)
Arrange the argument and result information for a value of the given freestanding function type.
CanQualType DeriveThisType(const CXXRecordDecl *RD, const CXXMethodDecl *MD)
Derives the 'this' type for codegen purposes, i.e.
llvm::FunctionType * GetFunctionType(const CGFunctionInfo &Info)
GetFunctionType - Get the LLVM function type for.
bool inheritingCtorHasParams(const InheritedConstructor &Inherited, CXXCtorType Type)
Determine if a C++ inheriting constructor should have parameters matching those of its inherited cons...
bool isFuncTypeConvertible(const FunctionType *FT)
isFuncTypeConvertible - Utility to check whether a function type can be converted to an LLVM type (i....
const CGFunctionInfo & arrangeBlockFunctionCall(const CallArgList &args, const FunctionType *type)
A block function is essentially a free function with an extra implicit argument.
const CGFunctionInfo & arrangeBuiltinFunctionDeclaration(QualType resultType, const FunctionArgList &args)
A builtin function is a freestanding function using the default C conventions.
const CGFunctionInfo & arrangeUnprototypedObjCMessageSend(QualType returnType, const CallArgList &args)
const CGRecordLayout & getCGRecordLayout(const RecordDecl *)
getCGRecordLayout - Return record layout info for the given record decl.
void getExpandedTypes(QualType Ty, SmallVectorImpl< llvm::Type * >::iterator &TI)
getExpandedTypes - Expand the type
llvm::Type * ConvertTypeForMem(QualType T)
ConvertTypeForMem - Convert type T into a llvm::Type.
const CGFunctionInfo & arrangeObjCMethodDeclaration(const ObjCMethodDecl *MD)
Objective-C methods are C functions with some implicit parameters.
llvm::LLVMContext & getLLVMContext()
const CGFunctionInfo & arrangeDeviceKernelCallerDeclaration(QualType resultType, const FunctionArgList &args)
A device kernel caller function is an offload device entry point function with a target device depend...
const CGFunctionInfo & arrangeGlobalDeclaration(GlobalDecl GD)
const CGFunctionInfo & arrangeUnprototypedMustTailThunk(const CXXMethodDecl *MD)
Arrange a thunk that takes 'this' as the first parameter followed by varargs.
const CGFunctionInfo & arrangeBuiltinFunctionCall(QualType resultType, const CallArgList &args)
const CGFunctionInfo & arrangeBlockFunctionDeclaration(const FunctionProtoType *type, const FunctionArgList &args)
Block invocation functions are C functions with an implicit parameter.
unsigned ClangCallConvToLLVMCallConv(CallingConv CC)
Convert clang calling convention to LLVM callilng convention.
llvm::Type * GetFunctionTypeForVTable(GlobalDecl GD)
GetFunctionTypeForVTable - Get the LLVM function type for use in a vtable, given a CXXMethodDecl.
const CGFunctionInfo & arrangeCall(const CGFunctionInfo &declFI, const CallArgList &args, const FunctionDecl *ABIInfoFD)
Given a function info for a declaration, return the function info for a call with the given arguments...
const CGFunctionInfo & arrangeObjCMessageSendSignature(const ObjCMethodDecl *MD, QualType receiverType)
Arrange the argument and result information for the function type through which to perform a send to ...
const CGFunctionInfo & arrangeCXXStructorDeclaration(GlobalDecl GD)
const CGFunctionInfo & arrangeFunctionDeclaration(const GlobalDecl GD)
Free functions are functions that are compatible with an ordinary C function pointer type.
const CGFunctionInfo & arrangeMSCtorClosure(const CXXConstructorDecl *CD, CXXCtorType CT)
const CGFunctionInfo & arrangeNullaryFunction()
A nullary function is a freestanding function of type 'void ()'.
A saved depth on the scope stack.
FunctionArgList - Type for representing both the decl and type of parameters to a function.
LValue - This represents an lvalue references.
static LValue MakeAddr(Address Addr, QualType type, ASTContext &Context, LValueBaseInfo BaseInfo, TBAAAccessInfo TBAAInfo)
Address getAddress() 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.
std::pair< llvm::Value *, llvm::Value * > getComplexVal() const
getComplexVal - Return the real/imag components of this complex value.
An abstract representation of an aligned address.
CharUnits getAlignment() const
Return the alignment of this pointer.
llvm::Value * getPointer() const
static RawAddress invalid()
A class for recording the number of arguments that a function signature requires.
bool allowsOptionalArgs() const
unsigned getNumRequiredArgs() const
static RequiredArgs forPrototypePlus(const FunctionProtoType *prototype, unsigned additional)
Compute the arguments required by the given formal prototype, given that there may be some additional...
ReturnValueSlot - Contains the address where the return value of a function can be stored,...
virtual void setCUDAKernelCallingConvention(const FunctionType *&FT) const
static void initPointerAuthFnAttributes(const PointerAuthOptions &Opts, llvm::AttrBuilder &FuncAttrs)
static void initBranchProtectionFnAttributes(const TargetInfo::BranchProtectionInfo &BPI, llvm::AttrBuilder &FuncAttrs)
virtual bool isNoProtoCallVariadic(const CodeGen::CallArgList &args, const FunctionNoProtoType *fnType) const
Determine whether a call to an unprototyped functions under the given calling convention should use t...
Complex values, per C99 6.2.5p11.
Represents the canonical version of C arrays with a specified constant size.
bool constructsVirtualBase() const
Returns true if the constructed base class is a virtual base class subobject of this declaration's cl...
DeclContext - This is used only as base class of specific decl types that can act as declaration cont...
Decl - This represents one declaration (or definition), e.g.
const FunctionType * getFunctionType(bool BlocksToo=true) const
Looks through the Decl's underlying type to extract a FunctionType when possible.
llvm::iterator_range< specific_attr_iterator< T > > specific_attrs() const
DeclContext * getDeclContext()
SourceLocation getBeginLoc() const LLVM_READONLY
This represents one expression.
Expr * IgnoreParens() LLVM_READONLY
Skip past any parentheses which might surround this expression until reaching a fixed point.
@ NPC_ValueDependentIsNotNull
Specifies that a value-dependent expression should be considered to never be a null pointer constant.
ExprObjectKind getObjectKind() const
getObjectKind - The object kind that this expression produces.
NullPointerConstantKind isNullPointerConstant(ASTContext &Ctx, NullPointerConstantValueDependence NPC) const
isNullPointerConstant - C99 6.3.2.3p3 - Test if this reduces down to a Null pointer constant.
Represents a member of a struct/union/class.
bool isBitField() const
Determines whether this field is a bitfield.
bool isUnnamedBitField() const
Determines whether this is an unnamed bitfield.
bool isZeroLengthBitField() const
Is this a zero-length bit-field?
Represents a function declaration or definition.
Represents a K&R-style 'int foo()' function, which has no information available about its arguments.
Represents a prototype with parameter type info, e.g.
ExceptionSpecificationType getExceptionSpecType() const
Get the kind of exception specification on this function.
unsigned getNumParams() const
unsigned getAArch64SMEAttributes() const
Return a bitmask describing the SME attributes on the function type, see AArch64SMETypeAttributes for...
bool isNothrow(bool ResultIfDependent=false) const
Determine whether this function type has a non-throwing exception specification.
ArrayRef< ExtParameterInfo > getExtParameterInfos() const
bool hasExtParameterInfos() const
Is there any interesting extra information for any of the parameters of this function type?
Wrapper for source info for functions.
A class which abstracts out some details necessary for making a call.
ExtInfo withCallingConv(CallingConv cc) const
ExtInfo withProducesResult(bool producesResult) const
Interesting information about a specific parameter that can't simply be reflected in parameter's type...
ParameterABI getABI() const
Return the ABI treatment of this parameter.
ExtParameterInfo withIsNoEscape(bool NoEscape) const
FunctionType - C99 6.7.5.3 - Function Declarators.
ExtInfo getExtInfo() const
@ SME_PStateSMEnabledMask
@ SME_PStateSMCompatibleMask
@ SME_AgnosticZAStateMask
static ArmStateValue getArmZT0State(unsigned AttrBits)
static ArmStateValue getArmZAState(unsigned AttrBits)
QualType getReturnType() const
GlobalDecl - represents a global declaration.
CXXCtorType getCtorType() const
KernelReferenceKind getKernelReferenceKind() const
CXXDtorType getDtorType() const
const Decl * getDecl() const
This class represents temporary values used to represent inout and out arguments in HLSL.
Description of a constructor that was inherited from a base class.
ConstructorUsingShadowDecl * getShadowDecl() const
@ FPE_Ignore
Assume that floating-point exceptions are masked.
Keeps track of the various options that can be enabled, which controls the dialect of C or C++ that i...
std::vector< std::string > NoBuiltinFuncs
A list of all -fno-builtin-* function names (e.g., memset).
FPExceptionModeKind getDefaultExceptionMode() const
bool isNoBuiltinFunc(StringRef Name) const
Is this a libc/libm function that is no longer recognized as a builtin because a -fno-builtin-* optio...
bool assumeFunctionsAreConvergent() const
Represents a point when the lifetime of an automatic object ends.
Represents a matrix type, as defined in the Matrix Types clang extensions.
Describes a module or submodule.
StringRef getName() const
Get the name of identifier for this declaration as a StringRef.
ObjCCategoryDecl - Represents a category declaration.
ObjCIndirectCopyRestoreExpr - Represents the passing of a function argument by indirect copy-restore ...
bool shouldCopy() const
shouldCopy - True if we should do the 'copy' part of the copy-restore.
Represents an ObjC class declaration.
ObjCMethodDecl - Represents an instance or class method declaration.
ImplicitParamDecl * getSelfDecl() const
ArrayRef< ParmVarDecl * > parameters() const
bool isDirectMethod() const
True if the method is tagged as objc_direct.
QualType getReturnType() const
Represents a parameter to a function.
PointerType - C99 6.7.5.1 - Pointer Declarators.
A (possibly-)qualified type.
bool isRestrictQualified() const
Determine whether this type is restrict-qualified.
bool isTriviallyCopyableType(const ASTContext &Context) const
Return true if this is a trivially copyable type (C++0x [basic.types]p9)
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.
QualType getNonReferenceType() const
If Type is a reference type (e.g., const int&), returns the type that the reference refers to ("const...
QualType getCanonicalType() const
bool isConstQualified() const
Determine whether this type is const-qualified.
DestructionKind isDestructedType() const
Returns a nonzero value if objects of this type require non-trivial work to clean up after.
@ OCL_Strong
Assigning into this object requires the old value to be released and the new value to be retained.
LangAS getAddressSpace() const
Represents a struct/union/class.
field_iterator field_end() const
bool isParamDestroyedInCallee() const
RecordDecl * getDefinition() const
Returns the RecordDecl that actually defines this struct/union/class.
field_iterator field_begin() const
Base for LValueReferenceType and RValueReferenceType.
Encodes a location in the source.
UIntTy getRawEncoding() const
When a SourceLocation itself cannot be used, this returns an (opaque) 32-bit integer encoding for it.
bool isMicrosoft() const
Is this ABI an MSVC-compatible ABI?
const llvm::Triple & getTriple() const
Returns the target triple of the primary target.
TargetCXXABI getCXXABI() const
Get the C++ ABI currently in use.
Options for controlling the target.
std::vector< std::string > Features
The list of target specific features to enable or disable – this should be a list of strings starting...
std::string TuneCPU
If given, the name of the target CPU to tune code for.
std::string CPU
If given, the name of the target CPU to generate code for.
llvm::StringMap< bool > FeatureMap
The map of which features have been enabled disabled based on the command line.
The base class of the type hierarchy.
bool isIncompleteArrayType() const
CXXRecordDecl * getAsCXXRecordDecl() const
Retrieves the CXXRecordDecl that this type refers to, either because the type is a RecordType or beca...
RecordDecl * getAsRecordDecl() const
Retrieves the RecordDecl this type refers to.
bool isConstantSizeType() const
Return true if this is not a variable sized type, according to the rules of C99 6....
bool isPointerType() const
CanQualType getCanonicalTypeUnqualified() 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 isScalarType() const
QualType getPointeeType() const
If this is a pointer, ObjC object pointer, or block pointer, this returns the respective pointee.
bool isBitIntType() const
RecordDecl * castAsRecordDecl() const
bool isMemberPointerType() const
bool isFunctionProtoType() const
bool isVariablyModifiedType() const
Whether this type is a variably-modified type (C99 6.7.5).
bool isObjectType() const
Determine whether this type is an object type.
bool isIncompleteType(NamedDecl **Def=nullptr) const
Types are partitioned into 3 broad categories (C99 6.2.5p1): object types, function types,...
bool hasFloatingRepresentation() const
Determine whether this type has a floating-point representation of some sort, e.g....
const T * getAsCanonical() const
If this type is canonically the specified type, return its canonical type cast to that specified type...
const T * castAsCanonical() const
Return this type's canonical type cast to the specified type.
const T * getAs() const
Member-template getAs<specific type>'.
bool isNullPtrType() const
bool isRecordType() const
bool isObjCRetainableType() const
UnaryOperator - This represents the unary-expression's (except sizeof and alignof),...
Represents a call to the builtin function __builtin_va_arg.
Represents a variable declaration or definition.
QualType::DestructionKind needsDestruction(const ASTContext &Ctx) const
Would the destruction of this variable have any effect, and if so, what kind?
Represents a GCC generic vector type.
Defines the clang::TargetInfo interface.
CanQual< FunctionProtoType > getFormalType(const CXXMethodDecl *MD)
Returns the canonical formal type of the given C++ method.
llvm::FPClassTest getNoFPClassTestMask(const LangOptions &LangOpts)
Returns the set of floating-point value kinds that the language options promise never reach a functio...
void computeABIInfo(CodeGenModule &CGM, CGFunctionInfo &FI)
Compute the ABI information of a swiftcall function.
@ Type
The l-value was considered opaque, so the alignment was determined from a type.
@ Decl
The l-value was an access to a declared entity or something equivalently strong, like the address of ...
void computeSPIRKernelABIInfo(CodeGenModule &CGM, CGFunctionInfo &FI)
@ NormalCleanup
Denotes a cleanup that should run when a scope is exited using normal control flow (falling off the e...
void mergeDefaultFunctionDefinitionAttributes(llvm::Function &F, const CodeGenOptions &CodeGenOpts, const LangOptions &LangOpts, const TargetOptions &TargetOpts, bool WillInternalize)
Adds attributes to F according to our CodeGenOpts and LangOpts, as though we had emitted it ourselves...
QualType useFirstFieldIfTransparentUnion(QualType Ty)
Pass transparent unions as if they were the type of the first element.
bool isEmptyRecord(ASTContext &Context, QualType T, bool AllowArrays, bool AsIfNoUniqueAddr=false)
isEmptyRecord - Return true iff a structure contains only empty fields.
const internal::VariadicAllOfMatcher< Type > type
Matches Types in the clang AST.
PRESERVE_NONE bool Ret(InterpState &S)
bool This(InterpState &S, CodePtr OpPC)
@ Address
A pointer to a ValueDecl.
Top level wrappers for InstallAPI frontend operations.
CanQual< Type > CanQualType
Represents a canonical, potentially-qualified type.
CXXCtorType
C++ constructor types.
@ Ctor_DefaultClosure
Default closure variant of a ctor.
@ Ctor_CopyingClosure
Copying closure variant of a ctor.
@ Ctor_Complete
Complete object ctor.
bool isa(CodeGen::Address addr)
static bool classof(const OMPClause *T)
bool isUnresolvedExceptionSpec(ExceptionSpecificationType ESpecType)
bool isInstanceMethod(const Decl *D)
@ NonNull
Values of this type can never be null.
@ OK_Ordinary
An ordinary object is located at an address in memory.
@ Vector
'vector' clause, allowed on 'loop', Combined, and 'routine' directives.
nullptr
This class represents a compute construct, representing a 'Kind' of ‘parallel’, 'serial',...
Linkage
Describes the different kinds of linkage (C++ [basic.link], C99 6.2.2) that an entity may have.
@ SwiftAsyncContext
This parameter (which must have pointer type) uses the special Swift asynchronous context-pointer ABI...
@ SwiftErrorResult
This parameter (which must have pointer-to-pointer type) uses the special Swift error-result ABI trea...
@ Ordinary
This parameter uses ordinary ABI rules for its type.
@ SwiftIndirectResult
This parameter (which must have pointer type) is a Swift indirect result parameter.
@ SwiftContext
This parameter (which must have pointer type) uses the special Swift context-pointer ABI treatment.
const FunctionProtoType * T
@ Dtor_VectorDeleting
Vector deleting dtor.
@ Dtor_Complete
Complete object dtor.
@ Dtor_Deleting
Deleting dtor.
@ CanPassInRegs
The argument of this type can be passed directly in registers.
CallingConv
CallingConv - Specifies the calling convention that a function uses.
U cast(CodeGen::Address addr)
@ Struct
The "struct" keyword introduces the elaborated-type-specifier.
__DEVICE__ _Tp arg(const std::complex< _Tp > &__c)
Structure with information about how a bitfield should be accessed.
CharUnits StorageOffset
The offset of the bitfield storage from the start of the struct.
unsigned Offset
The offset within a contiguous run of bitfields that are represented as a single "field" within the L...
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.
Similar to AddedStructorArgs, but only notes the number of additional arguments.
llvm::Value * ToUse
A value to "use" after the writeback, or null.
LValue Source
The original argument.
Address Temporary
The temporary alloca.
const Expr * WritebackExpr
An Expression (optional) that performs the writeback with any required casting.
LValue getKnownLValue() const
RValue getKnownRValue() const
void copyInto(CodeGenFunction &CGF, Address A) const
RValue getRValue(CodeGenFunction &CGF) const
llvm::PointerType * VoidPtrTy
llvm::IntegerType * Int64Ty
llvm::IntegerType * Int8Ty
i8, i16, i32, and i64
llvm::CallingConv::ID getRuntimeCC() const
llvm::IntegerType * SizeTy
llvm::IntegerType * Int32Ty
llvm::IntegerType * IntPtrTy
llvm::PointerType * Int8PtrTy
CharUnits getPointerAlign() const
~DisableDebugLocationUpdates()
DisableDebugLocationUpdates(CodeGenFunction &CGF)
static const EHPersonality & get(CodeGenModule &CGM, const FunctionDecl *FD)
llvm::Function * objc_retainAutoreleasedReturnValue
id objc_retainAutoreleasedReturnValue(id);
llvm::Function * objc_retain
id objc_retain(id);
llvm::InlineAsm * retainAutoreleasedReturnValueMarker
A void(void) inline asm to use to mark that the return value of a call will be immediately retain.
bool has(SanitizerMask K) const
Check if a certain (single) sanitizer is enabled.