[llvm] [Loads] Support dereference for non-constant offset (PR #149551)
via llvm-commits
llvm-commits at lists.llvm.org
Tue Sep 2 19:29:20 PDT 2025
================
@@ -368,32 +368,26 @@ bool llvm::isDereferenceableAndAlignedInLoop(
AccessSize = MaxPtrDiff;
AccessSizeSCEV = PtrDiff;
} else if (auto *MinAdd = dyn_cast<SCEVAddExpr>(AccessStart)) {
- if (MinAdd->getNumOperands() != 2)
+ const auto *NewBase = dyn_cast<SCEVUnknown>(SE.getPointerBase(MinAdd));
+ if (!NewBase)
return false;
- const auto *Offset = dyn_cast<SCEVConstant>(MinAdd->getOperand(0));
- const auto *NewBase = dyn_cast<SCEVUnknown>(MinAdd->getOperand(1));
- if (!Offset || !NewBase)
- return false;
-
- // The following code below assumes the offset is unsigned, but GEP
- // offsets are treated as signed so we can end up with a signed value
- // here too. For example, suppose the initial PHI value is (i8 255),
- // the offset will be treated as (i8 -1) and sign-extended to (i64 -1).
- if (Offset->getAPInt().isNegative())
+ auto *OffsetSCEV = SE.removePointerBase(MinAdd);
+ if (!SE.isKnownNonNegative(OffsetSCEV))
return false;
// For the moment, restrict ourselves to the case where the offset is a
// multiple of the requested alignment and the base is aligned.
// TODO: generalize if a case found which warrants
- if (Offset->getAPInt().urem(Alignment.value()) != 0)
+ if (SE.getMinTrailingZeros(OffsetSCEV) < Log2(Alignment))
return false;
bool Overflow = false;
- AccessSize = MaxPtrDiff.uadd_ov(Offset->getAPInt(), Overflow);
+ AccessSize =
+ MaxPtrDiff.uadd_ov(SE.getUnsignedRangeMax(OffsetSCEV), Overflow);
if (Overflow)
----------------
annamthomas wrote:
> But the addition of those must assume that either side take any value of the range, so even 0 - 1.
ah yes.
> Not sure if we would fare better if we kept things symbolicly
I'd tried using SCEV.willNotOverflow for the add at `SE.getAddExpr(PtrDiff, OffsetSCEV)` instead of the `uadd_ov`, but it hits on another limitation because the RHS is not a constant (it's OffsetSCEV: (16 + (4 * %iv.start)<nuw><nsw>)<nuw><nsw>).
Maybe fixing that limitation looks like the way forward.
https://github.com/llvm/llvm-project/pull/149551
More information about the llvm-commits
mailing list