7#define DEBUG_TYPE "vncoerce"
20 if (StoredTy == LoadTy)
24 TypeSize MinStoreSize =
DL.getTypeSizeInBits(StoredTy);
25 TypeSize LoadSize =
DL.getTypeSizeInBits(LoadTy);
27 MinStoreSize == LoadSize)
39 const auto &Attrs =
F->getAttributes().getFnAttrs();
40 unsigned MinVScale = Attrs.getVScaleRangeMin();
59 if (StoredNI != LoadNI) {
64 return CI->isNullValue();
66 }
else if (StoredNI && LoadNI &&
75 if (StoredNI && (StoredTy->
isScalableTy() || MinStoreSize != LoadSize))
93 "precondition violation - materialization can't fail");
109 TypeSize StoredValSize =
DL.getTypeSizeInBits(StoredValTy);
110 TypeSize LoadedValSize =
DL.getTypeSizeInBits(LoadedTy);
113 if (StoredValSize == LoadedValSize) {
120 StoredValTy =
DL.getIntPtrType(StoredValTy);
124 Type *TypeToCastTo = LoadedTy;
126 TypeToCastTo =
DL.getIntPtrType(TypeToCastTo);
128 if (StoredValTy != TypeToCastTo)
146 "canCoerceMustAliasedValueToLoad fail");
150 StoredValTy =
DL.getIntPtrType(StoredValTy);
162 if (
DL.isBigEndian()) {
163 uint64_t ShiftAmt =
DL.getTypeStoreSizeInBits(StoredValTy).getFixedValue() -
164 DL.getTypeStoreSizeInBits(LoadedTy).getFixedValue();
166 StoredVal, ConstantInt::get(StoredVal->
getType(), ShiftAmt));
173 if (LoadedTy != NewIntTy) {
205 int64_t StoreOffset = 0, LoadOffset = 0;
209 if (StoreBase != LoadBase)
212 uint64_t LoadSize =
DL.getTypeSizeInBits(LoadTy).getFixedValue();
214 if ((WriteSizeInBits & 7) | (LoadSize & 7))
216 uint64_t StoreSize = WriteSizeInBits / 8;
223 if (StoreOffset > LoadOffset ||
224 StoreOffset + int64_t(StoreSize) < LoadOffset + int64_t(LoadSize))
229 return LoadOffset - StoreOffset;
282 if (!CI || !CI->isZero())
310 unsigned IndexSize =
DL.getIndexTypeSizeInBits(Src->getType());
333 assert(
Offset == 0 &&
"Expected a zero offset for scalable types");
348 (
DL.getTypeSizeInBits(SrcVal->
getType()).getFixedValue() + 7) / 8;
349 uint64_t LoadSize = (
DL.getTypeSizeInBits(LoadTy).getFixedValue() + 7) / 8;
354 Builder.CreatePtrToInt(SrcVal,
DL.getIntPtrType(SrcVal->
getType()));
361 if (
DL.isLittleEndian())
364 ShiftAmt = (StoreSize - LoadSize -
Offset) * 8;
366 SrcVal = Builder.CreateLShr(SrcVal,
367 ConstantInt::get(SrcVal->
getType(), ShiftAmt));
369 if (LoadSize != StoreSize)
370 SrcVal = Builder.CreateTruncOrBitCast(SrcVal,
380 TypeSize LoadSize =
DL.getTypeStoreSize(LoadTy);
384 F->getAttributes().getFnAttrs().getVScaleRangeMin());
386 "Expected Offset + LoadSize <= SrcValSize");
389 "Expected offset of zero and LoadSize <= SrcValSize");
399 unsigned SrcValSize =
DL.getTypeStoreSize(SrcVal->
getType()).getFixedValue();
400 unsigned LoadSize =
DL.getTypeStoreSize(LoadTy).getFixedValue();
412 uint64_t LoadSize =
DL.getTypeSizeInBits(LoadTy).getFixedValue() / 8;
420 Value *Val = MSI->getValue();
427 for (
unsigned NumBytesSet = 1; NumBytesSet != LoadSize;) {
429 if (NumBytesSet * 2 <= LoadSize) {
430 Value *ShVal = Builder.CreateShl(
431 Val, ConstantInt::get(Val->
getType(), NumBytesSet * 8));
432 Val = Builder.CreateOr(Val, ShVal);
439 Builder.CreateShl(Val, ConstantInt::get(Val->
getType(), 1 * 8));
440 Val = Builder.CreateOr(OneElt, ShVal);
451 unsigned IndexSize =
DL.getIndexTypeSizeInBits(Src->getType());
459 uint64_t LoadSize =
DL.getTypeSizeInBits(LoadTy).getFixedValue() / 8;
468 Val = ConstantInt::get(Ctx,
APInt::getSplat(LoadSize * 8, Val->getValue()));
475 unsigned IndexSize =
DL.getIndexTypeSizeInBits(Src->getType());
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
Class for arbitrary precision integers.
static LLVM_ABI APInt getSplat(unsigned NewLen, const APInt &V)
Return a value containing V broadcasted over NewLen bits.
This is the shared class of boolean and integer constants.
uint64_t getZExtValue() const
Return the constant as a 64-bit unsigned integer value after it has been zero extended as appropriate...
This is an important base class in LLVM.
A parsed version of the target data layout string in and methods for querying it.
bool isConstant() const
If the value is a global constant, its value is immutable throughout the runtime execution of the pro...
bool hasDefinitiveInitializer() const
hasDefinitiveInitializer - Whether the global variable has an initializer, and any other instances of...
Common base class shared among various IRBuilders.
Value * CreateIntToPtr(Value *V, Type *DestTy, const Twine &Name="")
Value * CreateLShr(Value *LHS, Value *RHS, const Twine &Name="", bool isExact=false)
ConstantInt * getInt64(uint64_t C)
Get a constant 64-bit value.
LLVM_ABI CallInst * CreateIntrinsic(Intrinsic::ID ID, ArrayRef< Type * > Types, ArrayRef< Value * > Args, FMFSource FMFSource={}, const Twine &Name="")
Create a call to intrinsic ID with Args, mangled using Types.
Value * CreateBitCast(Value *V, Type *DestTy, const Twine &Name="")
Value * CreatePtrToInt(Value *V, Type *DestTy, const Twine &Name="")
Value * CreateTruncOrBitCast(Value *V, Type *DestTy, const Twine &Name="")
This provides a uniform API for creating instructions and inserting them into a basic block: either a...
LLVM_ABI const Function * getFunction() const
Return the function this instruction belongs to.
static LLVM_ABI IntegerType * get(LLVMContext &C, unsigned NumBits)
This static method is the primary way of constructing an IntegerType.
This is an important class for using LLVM in a threaded context.
An instruction for reading from memory.
Value * getPointerOperand()
This is the common base class for memset/memcpy/memmove.
This class wraps the llvm.memset and llvm.memset.inline intrinsics.
Value * getSource() const
This is just like getRawSource, but it strips off any cast instructions that feed it,...
This class wraps the llvm.memcpy/memmove intrinsics.
An instruction for storing to memory.
Value * getValueOperand()
Value * getPointerOperand()
static constexpr TypeSize getFixed(ScalarTy ExactSize)
The instances of the Type class are immutable: once they are created, they are never changed.
LLVM_ABI bool isScalableTy(SmallPtrSetImpl< const Type * > &Visited) const
Return true if this is a type whose size is a known multiple of vscale.
bool isPointerTy() const
True if this is an instance of PointerType.
LLVM_ABI unsigned getPointerAddressSpace() const
Get the address space of this pointer or pointer vector type.
Type * getScalarType() const
If this is a vector type, return the element type, otherwise return 'this'.
bool isTargetExtTy() const
Return true if this is a target extension type.
LLVMContext & getContext() const
Return the LLVMContext in which this type was uniqued.
bool isPtrOrPtrVectorTy() const
Return true if this is a pointer type or a vector of pointer types.
bool isIntegerTy() const
True if this is an instance of IntegerType.
LLVM Value Representation.
Type * getType() const
All values are typed, get the type of this value.
static constexpr bool isKnownLE(const FixedOrScalableQuantity &LHS, const FixedOrScalableQuantity &RHS)
constexpr bool isScalable() const
Returns whether the quantity is scaled by a runtime quantity (vscale).
constexpr ScalarTy getKnownMinValue() const
Returns the minimum value this quantity can represent.
static constexpr bool isKnownGE(const FixedOrScalableQuantity &LHS, const FixedOrScalableQuantity &RHS)
@ C
The default llvm calling convention, compatible with C.
static int analyzeLoadFromClobberingWrite(Type *LoadTy, Value *LoadPtr, Value *WritePtr, uint64_t WriteSizeInBits, const DataLayout &DL)
This function is called when we have a memdep query of a load that ends up being a clobbering memory ...
static Value * getStoreValueForLoadHelper(Value *SrcVal, unsigned Offset, Type *LoadTy, IRBuilderBase &Builder, const DataLayout &DL)
int analyzeLoadFromClobberingStore(Type *LoadTy, Value *LoadPtr, StoreInst *DepSI, const DataLayout &DL)
This function determines whether a value for the pointer LoadPtr can be extracted from the store at D...
Value * getMemInstValueForLoad(MemIntrinsic *SrcInst, unsigned Offset, Type *LoadTy, Instruction *InsertPt, const DataLayout &DL)
If analyzeLoadFromClobberingMemInst returned an offset, this function can be used to actually perform...
Constant * getConstantValueForLoad(Constant *SrcVal, unsigned Offset, Type *LoadTy, const DataLayout &DL)
Value * coerceAvailableValueToLoadType(Value *StoredVal, Type *LoadedTy, IRBuilderBase &IRB, Function *F)
If we saw a store of a value to memory, and then a load from a must-aliased pointer of a different ty...
int analyzeLoadFromClobberingLoad(Type *LoadTy, Value *LoadPtr, LoadInst *DepLI, const DataLayout &DL)
This function determines whether a value for the pointer LoadPtr can be extracted from the load at De...
Constant * getConstantMemInstValueForLoad(MemIntrinsic *SrcInst, unsigned Offset, Type *LoadTy, const DataLayout &DL)
Value * getValueForLoad(Value *SrcVal, unsigned Offset, Type *LoadTy, Instruction *InsertPt, Function *F)
If analyzeLoadFromClobberingStore/Load returned an offset, this function can be used to actually perf...
int analyzeLoadFromClobberingMemInst(Type *LoadTy, Value *LoadPtr, MemIntrinsic *DepMI, const DataLayout &DL)
This function determines whether a value for the pointer LoadPtr can be extracted from the memory int...
static bool isFirstClassAggregateOrScalableType(Type *Ty)
bool canCoerceMustAliasedValueToLoad(Value *StoredVal, Type *LoadTy, Function *F)
Return true if CoerceAvailableValueToLoadType would succeed if it was called.
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.
Value * GetPointerBaseWithConstantOffset(Value *Ptr, int64_t &Offset, const DataLayout &DL, bool AllowNonInbounds=true)
Analyze the specified pointer to see if it can be expressed as a base pointer plus a constant offset.
LLVM_ABI Constant * ConstantFoldConstant(const Constant *C, const DataLayout &DL, const TargetLibraryInfo *TLI=nullptr)
ConstantFoldConstant - Fold the constant using the specified DataLayout.
LLVM_ABI Constant * ConstantFoldLoadFromConst(Constant *C, Type *Ty, const APInt &Offset, const DataLayout &DL)
Extract value of C at the given Offset reinterpreted as Ty.
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...
uint64_t alignTo(uint64_t Size, Align A)
Returns a multiple of A needed to store Size bytes.
decltype(auto) cast(const From &Val)
cast<X> - Return the argument parameter cast to the specified type.
LLVM_ABI Constant * ConstantFoldLoadFromConstPtr(Constant *C, Type *Ty, APInt Offset, const DataLayout &DL)
Return the value that a load from C with offset Offset would produce if it is constant and determinab...
LLVM_ABI const Value * getUnderlyingObject(const Value *V, unsigned MaxLookup=MaxLookupSearchDepth)
This method strips off any GEP address adjustments, pointer casts or llvm.threadlocal....