88#include "llvm/IR/IntrinsicsBPF.h"
99#define DEBUG_TYPE "bpf-abstract-member-access"
108 M, Intrinsic::bpf_passthrough, {
Input->getType(),
Input->getType()});
121class BPFAbstractMemberAccess final {
129 uint32_t AccessIndex;
130 MaybeAlign RecordAlignment;
134 typedef std::stack<std::pair<CallInst *, CallInfo>> CallInfoStack;
138 BPFPreserveArrayAI = 1,
139 BPFPreserveUnionAI = 2,
140 BPFPreserveStructAI = 3,
141 BPFPreserveFieldInfoAI = 4,
145 const DataLayout *DL =
nullptr;
148 static std::map<std::string, GlobalVariable *> GEPGlobals;
150 std::map<CallInst *, std::pair<CallInst *, CallInfo>> AIChain;
155 SmallMapVector<CallInst *, CallInfo, 4> BaseAICalls;
157 std::map<DICompositeType *, DIDerivedType *> AnonRecords;
159 void CheckAnonRecordType(DIDerivedType *ParentTy, DIType *Ty);
160 void CheckCompositeType(DIDerivedType *ParentTy, DICompositeType *CTy);
161 void CheckDerivedType(DIDerivedType *ParentTy, DIDerivedType *DTy);
162 void ResetMetadata(
struct CallInfo &CInfo);
166 void traceAICall(CallInst *
Call, CallInfo &ParentInfo);
167 void traceBitCast(BitCastInst *BitCast, CallInst *Parent,
168 CallInfo &ParentInfo);
169 void traceGEP(GetElementPtrInst *
GEP, CallInst *Parent,
170 CallInfo &ParentInfo);
173 bool IsPreserveDIAccessIndexCall(
const CallInst *
Call, CallInfo &Cinfo);
174 bool IsValidAIChain(
const MDNode *ParentMeta, uint32_t ParentAI,
175 const MDNode *ChildMeta);
176 bool removePreserveAccessIndexIntrinsic(
Function &
F);
177 bool HasPreserveFieldInfoCall(CallInfoStack &CallStack);
178 void GetStorageBitRange(DIDerivedType *MemberTy, Align RecordAlignment,
179 uint32_t &StartBitOffset, uint32_t &EndBitOffset);
180 uint32_t GetFieldInfo(uint32_t InfoKind, DICompositeType *CTy,
181 uint32_t AccessIndex, uint32_t PatchImm,
182 MaybeAlign RecordAlignment);
184 Value *computeBaseAndAccessKey(CallInst *
Call, CallInfo &CInfo,
185 std::string &AccessKey, MDNode *&BaseMeta);
186 MDNode *computeAccessKey(CallInst *
Call, CallInfo &CInfo,
187 std::string &AccessKey,
bool &IsInt32Ret);
188 bool transformGEPChain(CallInst *
Call, CallInfo &CInfo);
191std::map<std::string, GlobalVariable *> BPFAbstractMemberAccess::GEPGlobals;
194bool BPFAbstractMemberAccess::run(
Function &
F) {
195 LLVM_DEBUG(
dbgs() <<
"********** Abstract Member Accesses **********\n");
210 DISubprogram *
SP =
F.getSubprogram();
211 if (SP &&
SP->isDefinition()) {
212 for (DIType *Ty:
SP->getType()->getTypeArray())
213 CheckAnonRecordType(
nullptr, Ty);
214 for (
const MDNode *DN :
SP->getRetainedNodes()) {
216 CheckAnonRecordType(
nullptr, DV->getType());
221 return doTransformation(
F);
224void BPFAbstractMemberAccess::ResetMetadata(
struct CallInfo &CInfo) {
226 auto It = AnonRecords.find(Ty);
227 if (It != AnonRecords.end() && It->second !=
nullptr)
228 CInfo.Metadata = It->second;
232void BPFAbstractMemberAccess::CheckCompositeType(DIDerivedType *ParentTy,
233 DICompositeType *CTy) {
235 ParentTy->
getTag() != dwarf::DW_TAG_typedef)
238 auto [It,
Inserted] = AnonRecords.try_emplace(CTy, ParentTy);
242 if (!Inserted && It->second != ParentTy)
243 It->second =
nullptr;
246void BPFAbstractMemberAccess::CheckDerivedType(DIDerivedType *ParentTy,
247 DIDerivedType *DTy) {
248 DIType *
BaseType = DTy->getBaseType();
253 if (
Tag == dwarf::DW_TAG_pointer_type)
254 CheckAnonRecordType(
nullptr,
BaseType);
255 else if (
Tag == dwarf::DW_TAG_typedef)
258 CheckAnonRecordType(ParentTy,
BaseType);
261void BPFAbstractMemberAccess::CheckAnonRecordType(DIDerivedType *ParentTy,
267 return CheckCompositeType(ParentTy, CTy);
269 return CheckDerivedType(ParentTy, DTy);
273 if (Tag != dwarf::DW_TAG_typedef && Tag != dwarf::DW_TAG_const_type &&
274 Tag != dwarf::DW_TAG_volatile_type &&
275 Tag != dwarf::DW_TAG_restrict_type &&
276 Tag != dwarf::DW_TAG_member)
278 if (Tag == dwarf::DW_TAG_typedef && !skipTypedef)
287 Ty = DTy->getBaseType();
296 Ty = DTy->getBaseType();
304 for (
uint32_t I = StartDim;
I < Elements.size(); ++
I) {
306 if (Element->getTag() == dwarf::DW_TAG_subrange_type) {
309 DimSize *= CI->getSExtValue();
318 return Call->getParamElementType(0);
328bool BPFAbstractMemberAccess::IsPreserveDIAccessIndexCall(
const CallInst *
Call,
336 if (GV->getName().starts_with(
"llvm.preserve.array.access.index")) {
337 CInfo.Kind = BPFPreserveArrayAI;
338 CInfo.Metadata =
Call->
getMetadata(LLVMContext::MD_preserve_access_index);
340 report_fatal_error(
"Missing metadata for llvm.preserve.array.access.index intrinsic");
346 if (GV->getName().starts_with(
"llvm.preserve.union.access.index")) {
347 CInfo.Kind = BPFPreserveUnionAI;
348 CInfo.Metadata =
Call->
getMetadata(LLVMContext::MD_preserve_access_index);
350 report_fatal_error(
"Missing metadata for llvm.preserve.union.access.index intrinsic");
351 ResetMetadata(CInfo);
356 if (GV->getName().starts_with(
"llvm.preserve.struct.access.index")) {
357 CInfo.Kind = BPFPreserveStructAI;
358 CInfo.Metadata =
Call->
getMetadata(LLVMContext::MD_preserve_access_index);
360 report_fatal_error(
"Missing metadata for llvm.preserve.struct.access.index intrinsic");
361 ResetMetadata(CInfo);
367 if (GV->getName().starts_with(
"llvm.bpf.preserve.field.info")) {
368 CInfo.Kind = BPFPreserveFieldInfoAI;
369 CInfo.Metadata =
nullptr;
377 if (GV->getName().starts_with(
"llvm.bpf.preserve.type.info")) {
378 CInfo.Kind = BPFPreserveFieldInfoAI;
379 CInfo.Metadata =
Call->
getMetadata(LLVMContext::MD_preserve_access_index);
393 if (GV->getName().starts_with(
"llvm.bpf.preserve.enum.value")) {
394 CInfo.Kind = BPFPreserveFieldInfoAI;
395 CInfo.Metadata =
Call->
getMetadata(LLVMContext::MD_preserve_access_index);
414 if (DimensionIndex > 0)
423 Call->getArgOperand(0), IdxList,
424 "",
Call->getIterator());
426 Call->eraseFromParent();
438 Call->replaceAllUsesWith(
Call->getArgOperand(0));
439 Call->eraseFromParent();
442bool BPFAbstractMemberAccess::removePreserveAccessIndexIntrinsic(
Function &
F) {
443 std::vector<CallInst *> PreserveArrayIndexCalls;
444 std::vector<CallInst *> PreserveUnionIndexCalls;
445 std::vector<CallInst *> PreserveStructIndexCalls;
452 if (!IsPreserveDIAccessIndexCall(
Call, CInfo))
456 if (CInfo.Kind == BPFPreserveArrayAI)
457 PreserveArrayIndexCalls.push_back(
Call);
458 else if (CInfo.Kind == BPFPreserveUnionAI)
459 PreserveUnionIndexCalls.push_back(
Call);
461 PreserveStructIndexCalls.push_back(
Call);
487bool BPFAbstractMemberAccess::IsValidAIChain(
const MDNode *ParentType,
489 const MDNode *ChildType) {
503 if (PtrTy->getTag() != dwarf::DW_TAG_pointer_type)
511 assert(PTy && CTy &&
"ParentType or ChildType is null or not composite");
513 uint32_t PTyTag = PTy->getTag();
514 assert(PTyTag == dwarf::DW_TAG_array_type ||
515 PTyTag == dwarf::DW_TAG_structure_type ||
516 PTyTag == dwarf::DW_TAG_union_type);
518 uint32_t CTyTag = CTy->
getTag();
519 assert(CTyTag == dwarf::DW_TAG_array_type ||
520 CTyTag == dwarf::DW_TAG_structure_type ||
521 CTyTag == dwarf::DW_TAG_union_type);
524 if (PTyTag == dwarf::DW_TAG_array_type && PTyTag == CTyTag)
528 if (PTyTag == dwarf::DW_TAG_array_type)
529 Ty = PTy->getBaseType();
536void BPFAbstractMemberAccess::traceAICall(CallInst *
Call,
537 CallInfo &ParentInfo) {
544 traceBitCast(BI,
Call, ParentInfo);
548 if (IsPreserveDIAccessIndexCall(CI, ChildInfo) &&
549 IsValidAIChain(ParentInfo.Metadata, ParentInfo.AccessIndex,
550 ChildInfo.Metadata)) {
551 AIChain[CI] = std::make_pair(
Call, ParentInfo);
552 traceAICall(CI, ChildInfo);
554 BaseAICalls[
Call] = ParentInfo;
557 if (GI->hasAllZeroIndices())
558 traceGEP(GI,
Call, ParentInfo);
560 BaseAICalls[
Call] = ParentInfo;
562 BaseAICalls[
Call] = ParentInfo;
567void BPFAbstractMemberAccess::traceBitCast(BitCastInst *BitCast,
569 CallInfo &ParentInfo) {
570 for (User *U : BitCast->
users()) {
576 traceBitCast(BI, Parent, ParentInfo);
579 if (IsPreserveDIAccessIndexCall(CI, ChildInfo) &&
580 IsValidAIChain(ParentInfo.Metadata, ParentInfo.AccessIndex,
581 ChildInfo.Metadata)) {
582 AIChain[CI] = std::make_pair(Parent, ParentInfo);
583 traceAICall(CI, ChildInfo);
585 BaseAICalls[Parent] = ParentInfo;
588 if (GI->hasAllZeroIndices())
589 traceGEP(GI, Parent, ParentInfo);
591 BaseAICalls[Parent] = ParentInfo;
593 BaseAICalls[Parent] = ParentInfo;
598void BPFAbstractMemberAccess::traceGEP(GetElementPtrInst *
GEP, CallInst *Parent,
599 CallInfo &ParentInfo) {
600 for (User *U :
GEP->users()) {
606 traceBitCast(BI, Parent, ParentInfo);
609 if (IsPreserveDIAccessIndexCall(CI, ChildInfo) &&
610 IsValidAIChain(ParentInfo.Metadata, ParentInfo.AccessIndex,
611 ChildInfo.Metadata)) {
612 AIChain[CI] = std::make_pair(Parent, ParentInfo);
613 traceAICall(CI, ChildInfo);
615 BaseAICalls[Parent] = ParentInfo;
618 if (GI->hasAllZeroIndices())
619 traceGEP(GI, Parent, ParentInfo);
621 BaseAICalls[Parent] = ParentInfo;
623 BaseAICalls[Parent] = ParentInfo;
628void BPFAbstractMemberAccess::collectAICallChains(
Function &
F) {
636 if (!IsPreserveDIAccessIndexCall(
Call, CInfo) ||
637 AIChain.find(
Call) != AIChain.end())
640 traceAICall(
Call, CInfo);
645void BPFAbstractMemberAccess::GetStorageBitRange(DIDerivedType *MemberTy,
646 Align RecordAlignment,
647 uint32_t &StartBitOffset,
648 uint32_t &EndBitOffset) {
652 if (RecordAlignment > 8) {
655 if (MemberBitOffset / 64 != (MemberBitOffset + MemberBitSize) / 64)
657 "requiring too big alignment");
658 RecordAlignment =
Align(8);
661 uint32_t AlignBits = RecordAlignment.
value() * 8;
662 if (MemberBitSize > AlignBits)
664 "bitfield size greater than record alignment");
666 StartBitOffset = MemberBitOffset & ~(AlignBits - 1);
667 if ((StartBitOffset + AlignBits) < (MemberBitOffset + MemberBitSize))
669 "cross alignment boundary");
670 EndBitOffset = StartBitOffset + AlignBits;
673uint32_t BPFAbstractMemberAccess::GetFieldInfo(uint32_t InfoKind,
674 DICompositeType *CTy,
675 uint32_t AccessIndex,
677 MaybeAlign RecordAlignment) {
683 if (
Tag == dwarf::DW_TAG_array_type) {
686 (EltTy->getSizeInBits() >> 3);
687 }
else if (
Tag == dwarf::DW_TAG_structure_type) {
692 unsigned SBitOffset, NextSBitOffset;
693 GetStorageBitRange(MemberTy, *RecordAlignment, SBitOffset,
695 PatchImm += SBitOffset >> 3;
702 if (
Tag == dwarf::DW_TAG_array_type) {
704 return calcArraySize(CTy, 1) * (EltTy->getSizeInBits() >> 3);
709 return SizeInBits >> 3;
711 unsigned SBitOffset, NextSBitOffset;
712 GetStorageBitRange(MemberTy, *RecordAlignment, SBitOffset,
714 SizeInBits = NextSBitOffset - SBitOffset;
715 if (SizeInBits & (SizeInBits - 1))
717 return SizeInBits >> 3;
722 const DIType *BaseTy;
723 if (
Tag == dwarf::DW_TAG_array_type) {
738 if (!CompTy || CompTy->getTag() != dwarf::DW_TAG_enumeration_type)
743 uint32_t Encoding = BTy->getEncoding();
744 return (Encoding == dwarf::DW_ATE_signed || Encoding == dwarf::DW_ATE_signed_char);
753 DIDerivedType *MemberTy =
nullptr;
754 bool IsBitField =
false;
757 if (
Tag == dwarf::DW_TAG_array_type) {
769 return 64 - SizeInBits;
772 unsigned SBitOffset, NextSBitOffset;
773 GetStorageBitRange(MemberTy, *RecordAlignment, SBitOffset, NextSBitOffset);
774 if (NextSBitOffset - SBitOffset > 64)
779 return SBitOffset + 64 - OffsetInBits - SizeInBits;
781 return OffsetInBits + 64 - NextSBitOffset;
785 DIDerivedType *MemberTy =
nullptr;
786 bool IsBitField =
false;
788 if (
Tag == dwarf::DW_TAG_array_type) {
800 return 64 - SizeInBits;
803 unsigned SBitOffset, NextSBitOffset;
804 GetStorageBitRange(MemberTy, *RecordAlignment, SBitOffset, NextSBitOffset);
805 if (NextSBitOffset - SBitOffset > 64)
808 return 64 - SizeInBits;
814bool BPFAbstractMemberAccess::HasPreserveFieldInfoCall(CallInfoStack &CallStack) {
816 while (CallStack.size()) {
817 auto StackElem = CallStack.top();
818 if (StackElem.second.Kind == BPFPreserveFieldInfoAI)
828Value *BPFAbstractMemberAccess::computeBaseAndAccessKey(CallInst *
Call,
830 std::string &AccessKey,
834 CallInfoStack CallStack;
838 CallStack.push(std::make_pair(
Call, CInfo));
839 auto &Chain = AIChain[
Call];
840 CInfo = Chain.second;
854 uint32_t FirstIndex = 0;
855 uint32_t PatchImm = 0;
857 while (CallStack.size()) {
858 auto StackElem = CallStack.top();
859 Call = StackElem.first;
860 CInfo = StackElem.second;
868 if (CInfo.Kind == BPFPreserveUnionAI ||
869 CInfo.Kind == BPFPreserveStructAI) {
873 TypeMeta = PossibleTypeDef;
878 assert(CInfo.Kind == BPFPreserveArrayAI);
884 uint64_t AccessIndex = CInfo.AccessIndex;
886 DIType *BaseTy =
nullptr;
887 bool CheckElemType =
false;
904 CheckElemType =
true;
905 }
else if (CTy->
getTag() != dwarf::DW_TAG_array_type) {
906 FirstIndex += AccessIndex;
907 CheckElemType =
true;
916 if (HasPreserveFieldInfoCall(CallStack))
921 unsigned CTag = CTy->
getTag();
922 if (CTag == dwarf::DW_TAG_structure_type || CTag == dwarf::DW_TAG_union_type) {
925 if (HasPreserveFieldInfoCall(CallStack))
935 AccessKey += std::to_string(FirstIndex);
939 while (CallStack.size()) {
940 auto StackElem = CallStack.top();
941 CInfo = StackElem.second;
944 if (CInfo.Kind == BPFPreserveFieldInfoAI) {
953 if (CallStack.size()) {
954 auto StackElem2 = CallStack.top();
955 CallInfo CInfo2 = StackElem2.second;
956 if (CInfo2.Kind == BPFPreserveFieldInfoAI) {
958 assert(CallStack.size() == 1);
963 uint64_t AccessIndex = CInfo.AccessIndex;
964 MDNode *MDN = CInfo.Metadata;
968 uint64_t BTFIndex = AccessIndex;
969 if (CTy->
getTag() == dwarf::DW_TAG_structure_type) {
977 if (ElementOffset <
Offset ||
978 (ElementOffset ==
Offset &&
I < AccessIndex))
982 AccessKey +=
":" + std::to_string(BTFIndex);
984 PatchImm = GetFieldInfo(InfoKind, CTy, AccessIndex, PatchImm,
985 CInfo.RecordAlignment);
994 AccessKey =
"llvm." +
TypeName +
":" + std::to_string(InfoKind) +
":" +
995 std::to_string(PatchImm) +
"$" + AccessKey;
1000MDNode *BPFAbstractMemberAccess::computeAccessKey(CallInst *
Call,
1002 std::string &AccessKey,
1008 std::string AccessStr(
"0");
1023 const GlobalVariable *GV =
1028 StringRef ValueStr =
DA->getAsString();
1032 StringRef EnumeratorStr = ValueStr.
substr(0, Separator);
1037 assert(CTy->
getTag() == dwarf::DW_TAG_enumeration_type);
1041 if (
Enum->getName() == EnumeratorStr) {
1042 AccessStr = std::to_string(EnumIndex);
1049 StringRef EValueStr = ValueStr.
substr(Separator + 1);
1050 PatchImm = std::stoll(std::string(EValueStr));
1056 AccessKey =
"llvm." + Ty->
getName().
str() +
":" +
1057 std::to_string(CInfo.AccessIndex) + std::string(
":") +
1058 std::to_string(PatchImm) + std::string(
"$") + AccessStr;
1065bool BPFAbstractMemberAccess::transformGEPChain(CallInst *
Call,
1067 std::string AccessKey;
1072 IsInt32Ret = CInfo.Kind == BPFPreserveFieldInfoAI;
1073 if (CInfo.Kind == BPFPreserveFieldInfoAI && CInfo.Metadata) {
1074 TypeMeta = computeAccessKey(
Call, CInfo, AccessKey, IsInt32Ret);
1076 Base = computeBaseAndAccessKey(
Call, CInfo, AccessKey, TypeMeta);
1084 if (GEPGlobals.find(AccessKey) == GEPGlobals.end()) {
1085 IntegerType *VarType;
1087 VarType = Type::getInt32Ty(BB->
getContext());
1089 VarType = Type::getInt64Ty(BB->
getContext());
1091 GV =
new GlobalVariable(*M, VarType,
false, GlobalVariable::ExternalLinkage,
1092 nullptr, AccessKey);
1094 GV->
setMetadata(LLVMContext::MD_preserve_access_index, TypeMeta);
1095 GEPGlobals[AccessKey] = GV;
1097 GV = GEPGlobals[AccessKey];
1100 if (CInfo.Kind == BPFPreserveFieldInfoAI) {
1104 LDInst =
new LoadInst(Type::getInt32Ty(BB->
getContext()), GV,
"",
1107 LDInst =
new LoadInst(Type::getInt64Ty(BB->
getContext()), GV,
"",
1126 auto *LDInst =
new LoadInst(Type::getInt64Ty(BB->
getContext()), GV,
"",
1184bool BPFAbstractMemberAccess::doTransformation(
Function &
F) {
1185 bool Transformed =
false;
1190 collectAICallChains(
F);
1192 for (
auto &
C : BaseAICalls)
1193 Transformed = transformGEPChain(
C.first,
C.second) || Transformed;
1195 return removePreserveAccessIndexIntrinsic(
F) || Transformed;
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
static void replaceWithGEP(CallInst *Call, uint32_t DimensionIndex, uint32_t GEPIndex)
static uint64_t getConstant(const Value *IndexValue)
static Type * getBaseElementType(const CallInst *Call)
static uint32_t calcArraySize(const DICompositeType *CTy, uint32_t StartDim)
static bool SkipDIDerivedTag(unsigned Tag, bool skipTypedef)
static DIType * stripQualifiers(DIType *Ty, bool skipTypedef=true)
This file contains the layout of .BTF and .BTF.ext ELF sections.
static GCRegistry::Add< ShadowStackGC > C("shadow-stack", "Very portable GC for uncooperative code generators")
This file contains constants used for implementing Dwarf debug support.
Module.h This file contains the declarations for the Module class.
This header defines various interfaces for pass management in LLVM.
This file implements a map that provides insertion order iteration.
BaseType
A given derived pointer can have multiple base pointers through phi/selects.
This file defines the SmallVector class.
uint64_t getZExtValue() const
Get zero extended value.
PreservedAnalyses run(Function &F, FunctionAnalysisManager &AM)
static void removeArrayAccessCall(CallInst *Call)
static uint32_t SeqNum
llvm.bpf.passthrough builtin seq number
static void removeStructAccessCall(CallInst *Call)
@ PRESERVE_TYPE_INFO_EXISTENCE
@ MAX_PRESERVE_TYPE_INFO_FLAG
@ PRESERVE_TYPE_INFO_MATCH
static void removeUnionAccessCall(CallInst *Call)
@ PRESERVE_ENUM_VALUE_EXISTENCE
@ MAX_PRESERVE_ENUM_VALUE_FLAG
static Instruction * insertPassThrough(Module *M, BasicBlock *BB, Instruction *Input, Instruction *Before)
Insert a bpf passthrough builtin function.
static constexpr StringRef AmaAttr
The attribute attached to globals representing a field access.
LLVM Basic Block Representation.
LLVM_ABI LLVMContext & getContext() const
Get the context in which this basic block lives.
Value * getCalledOperand() const
Value * getArgOperand(unsigned i) const
This class represents a function call, abstracting a target machine's calling convention.
static CallInst * Create(FunctionType *Ty, Value *F, const Twine &NameStr="", InsertPosition InsertBefore=nullptr)
This is the shared class of boolean and integer constants.
const APInt & getValue() const
Return the constant as an APInt value reference.
This is an important base class in LLVM.
DINodeArray getElements() const
DIType * getBaseType() const
LLVM_ABI dwarf::Tag getTag() const
LLVM_ABI BoundType getCount() const
uint64_t getOffsetInBits() const
StringRef getName() const
uint64_t getSizeInBits() const
static GetElementPtrInst * Create(Type *PointeeType, Value *Ptr, ArrayRef< Value * > IdxList, const Twine &NameStr="", InsertPosition InsertBefore=nullptr)
static GetElementPtrInst * CreateInBounds(Type *PointeeType, Value *Ptr, ArrayRef< Value * > IdxList, const Twine &NameStr="", InsertPosition InsertBefore=nullptr)
Create an "inbounds" getelementptr.
LLVM_ABI void setMetadata(unsigned KindID, MDNode *Node)
Set a particular kind of metadata attachment.
const Constant * getInitializer() const
getInitializer - Return the initializer for this global variable.
bool hasInitializer() const
Definitions have initializers, declarations don't.
void addAttribute(Attribute::AttrKind Kind)
Add attribute to this global.
LLVM_ABI void insertBefore(InstListType::iterator InsertPos)
Insert an unlinked instruction into a basic block immediately before the specified position.
LLVM_ABI InstListType::iterator eraseFromParent()
This method unlinks 'this' from the containing basic block and deletes it.
MDNode * getMetadata(unsigned KindID) const
Get the metadata of given kind attached to this Instruction.
A Module instance is used to store all the information related to an LLVM module.
iterator_range< debug_compile_units_iterator > debug_compile_units() const
Return an iterator for all DICompileUnits listed in this Module's llvm.dbg.cu named metadata node and...
const DataLayout & getDataLayout() const
Get the data layout for the module's target platform.
static PreservedAnalyses none()
Convenience factory function for the empty preserved set.
static PreservedAnalyses all()
Construct a special preserved set that preserves all passes.
void push_back(const T &Elt)
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
std::string str() const
Get the contents as an std::string.
constexpr StringRef substr(size_t Start, size_t N=npos) const
Return a reference to the substring from [Start, Start + N).
constexpr bool empty() const
Check if the string is empty.
size_t find_first_of(char C, size_t From=0) const
Find the first character in the string that is C, or npos if not found.
const Triple & getTargetTriple() const
ArchType getArch() const
Get the parsed architecture type of this triple.
The instances of the Type class are immutable: once they are created, they are never changed.
static LLVM_ABI IntegerType * getInt32Ty(LLVMContext &C)
LLVM Value Representation.
LLVM_ABI void replaceAllUsesWith(Value *V)
Change all uses of this to point to a new Value.
iterator_range< user_iterator > users()
LLVM_ABI const Value * stripPointerCasts() const
Strip off pointer casts, all-zero GEPs and address space casts.
const ParentTy * getParent() const
self_iterator getIterator()
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
constexpr char Align[]
Key for Kernel::Arg::Metadata::mAlign.
constexpr char TypeName[]
Key for Kernel::Arg::Metadata::mTypeName.
InfoKind
Entry kind values for the .amdgpu.info section.
@ BasicBlock
Various leaf nodes.
LLVM_ABI Function * getOrInsertDeclaration(Module *M, ID id, ArrayRef< Type * > OverloadTys={})
Look up the Function declaration of the intrinsic id in the Module M.
Flag
These should be considered private to the implementation of the MCInstrDesc class.
DXILDebugInfoMap run(Module &M)
friend class Instruction
Iterator for Instructions in a `BasicBlock.
This is an optimization pass for GlobalISel generic memory operations.
decltype(auto) dyn_cast(const From &Val)
dyn_cast<X> - Return the argument parameter cast to the specified type.
RelativeUniformCounterPtr ValuesPtrExpr VTableAddr Value
auto dyn_cast_or_null(const Y &Val)
uint64_t getBTFRecordElementOffset(const DINode *Element)
Return the bit offset used to order an element of a BTF structure record.
LLVM_ABI raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
LLVM_ABI void report_fatal_error(Error Err, bool gen_crash_diag=true)
bool isa(const From &Val)
isa<X> - Return true if the parameter to the template is an instance of one of the template type argu...
decltype(auto) cast(const From &Val)
cast<X> - Return the argument parameter cast to the specified type.
AnalysisManager< Function > FunctionAnalysisManager
Convenience typedef for the Function analysis manager.
constexpr uint64_t value() const
This is a hole in the type system and should not be abused.