@@ -426,6 +426,49 @@ static bool AreNonOverlapSameBaseLoadAndStore(
426426 return LoadRange.intersectWith (StoreRange).isEmptySet ();
427427}
428428
429+ static Value *getAvailableLoadStore (Instruction *Inst, Value *Ptr,
430+ Type *AccessTy, bool AtLeastAtomic,
431+ const DataLayout &DL, bool *IsLoadCSE) {
432+ // If this is a load of Ptr, the loaded value is available.
433+ // (This is true even if the load is volatile or atomic, although
434+ // those cases are unlikely.)
435+ if (LoadInst *LI = dyn_cast<LoadInst>(Inst)) {
436+ if (AreEquivalentAddressValues (
437+ LI->getPointerOperand ()->stripPointerCasts (), Ptr) &&
438+ CastInst::isBitOrNoopPointerCastable (LI->getType (), AccessTy, DL)) {
439+ // We can value forward from an atomic to a non-atomic, but not the
440+ // other way around.
441+ if (LI->isAtomic () < AtLeastAtomic)
442+ return nullptr ;
443+
444+ if (IsLoadCSE)
445+ *IsLoadCSE = true ;
446+ return LI;
447+ }
448+ }
449+
450+ // If this is a store through Ptr, the value is available!
451+ // (This is true even if the store is volatile or atomic, although
452+ // those cases are unlikely.)
453+ if (StoreInst *SI = dyn_cast<StoreInst>(Inst)) {
454+ Value *StorePtr = SI->getPointerOperand ()->stripPointerCasts ();
455+ if (AreEquivalentAddressValues (StorePtr, Ptr) &&
456+ CastInst::isBitOrNoopPointerCastable (SI->getValueOperand ()->getType (),
457+ AccessTy, DL)) {
458+ // We can value forward from an atomic to a non-atomic, but not the
459+ // other way around.
460+ if (SI->isAtomic () < AtLeastAtomic)
461+ return nullptr ;
462+
463+ if (IsLoadCSE)
464+ *IsLoadCSE = false ;
465+ return SI->getOperand (0 );
466+ }
467+ }
468+
469+ return nullptr ;
470+ }
471+
429472Value *llvm::FindAvailablePtrLoadStore (Value *Ptr, Type *AccessTy,
430473 bool AtLeastAtomic, BasicBlock *ScanBB,
431474 BasicBlock::iterator &ScanFrom,
@@ -456,45 +499,16 @@ Value *llvm::FindAvailablePtrLoadStore(Value *Ptr, Type *AccessTy,
456499 return nullptr ;
457500
458501 --ScanFrom;
459- // If this is a load of Ptr, the loaded value is available.
460- // (This is true even if the load is volatile or atomic, although
461- // those cases are unlikely.)
462- if (LoadInst *LI = dyn_cast<LoadInst>(Inst))
463- if (AreEquivalentAddressValues (
464- LI->getPointerOperand ()->stripPointerCasts (), StrippedPtr) &&
465- CastInst::isBitOrNoopPointerCastable (LI->getType (), AccessTy, DL)) {
466-
467- // We can value forward from an atomic to a non-atomic, but not the
468- // other way around.
469- if (LI->isAtomic () < AtLeastAtomic)
470- return nullptr ;
471-
472- if (IsLoadCSE)
473- *IsLoadCSE = true ;
474- return LI;
475- }
502+
503+ if (Value *Available = getAvailableLoadStore (Inst, StrippedPtr, AccessTy,
504+ AtLeastAtomic, DL, IsLoadCSE))
505+ return Available;
476506
477507 // Try to get the store size for the type.
478508 auto AccessSize = LocationSize::precise (DL.getTypeStoreSize (AccessTy));
479509
480510 if (StoreInst *SI = dyn_cast<StoreInst>(Inst)) {
481511 Value *StorePtr = SI->getPointerOperand ()->stripPointerCasts ();
482- // If this is a store through Ptr, the value is available!
483- // (This is true even if the store is volatile or atomic, although
484- // those cases are unlikely.)
485- if (AreEquivalentAddressValues (StorePtr, StrippedPtr) &&
486- CastInst::isBitOrNoopPointerCastable (SI->getValueOperand ()->getType (),
487- AccessTy, DL)) {
488-
489- // We can value forward from an atomic to a non-atomic, but not the
490- // other way around.
491- if (SI->isAtomic () < AtLeastAtomic)
492- return nullptr ;
493-
494- if (IsLoadCSE)
495- *IsLoadCSE = false ;
496- return SI->getOperand (0 );
497- }
498512
499513 // If both StrippedPtr and StorePtr reach all the way to an alloca or
500514 // global and they are different, ignore the store. This is a trivial form
0 commit comments