Index: llvm/lib/Transforms/Scalar/LICM.cpp =================================================================== --- llvm/lib/Transforms/Scalar/LICM.cpp +++ llvm/lib/Transforms/Scalar/LICM.cpp @@ -141,7 +141,7 @@ static void hoist(Instruction &I, const DominatorTree *DT, const Loop *CurLoop, BasicBlock *Dest, ICFLoopSafetyInfo *SafetyInfo, MemorySSAUpdater *MSSAU, ScalarEvolution *SE, - OptimizationRemarkEmitter *ORE); + OptimizationRemarkEmitter *ORE, AAResults *AA); static bool sink(Instruction &I, LoopInfo *LI, DominatorTree *DT, const Loop *CurLoop, ICFLoopSafetyInfo *SafetyInfo, MemorySSAUpdater *MSSAU, OptimizationRemarkEmitter *ORE); @@ -814,7 +814,7 @@ I, DT, CurLoop, SafetyInfo, ORE, CurLoop->getLoopPreheader()->getTerminator())) { hoist(I, DT, CurLoop, CFH.getOrCreateHoistedBlock(BB), SafetyInfo, - MSSAU, SE, ORE); + MSSAU, SE, ORE, AA); HoistedInstructions.push_back(&I); Changed = true; continue; @@ -840,7 +840,7 @@ eraseInstruction(I, *SafetyInfo, CurAST, MSSAU); hoist(*ReciprocalDivisor, DT, CurLoop, CFH.getOrCreateHoistedBlock(BB), - SafetyInfo, MSSAU, SE, ORE); + SafetyInfo, MSSAU, SE, ORE, AA); HoistedInstructions.push_back(ReciprocalDivisor); Changed = true; continue; @@ -859,7 +859,7 @@ CurLoop->hasLoopInvariantOperands(&I) && MustExecuteWithoutWritesBefore(I)) { hoist(I, DT, CurLoop, CFH.getOrCreateHoistedBlock(BB), SafetyInfo, - MSSAU, SE, ORE); + MSSAU, SE, ORE, AA); HoistedInstructions.push_back(&I); Changed = true; continue; @@ -873,7 +873,7 @@ PN->setIncomingBlock( i, CFH.getOrCreateHoistedBlock(PN->getIncomingBlock(i))); hoist(*PN, DT, CurLoop, CFH.getOrCreateHoistedBlock(BB), SafetyInfo, - MSSAU, SE, ORE); + MSSAU, SE, ORE, AA); assert(DT->dominates(PN, BB) && "Conditional PHIs not expected"); Changed = true; continue; @@ -1632,7 +1632,7 @@ static void hoist(Instruction &I, const DominatorTree *DT, const Loop *CurLoop, BasicBlock *Dest, ICFLoopSafetyInfo *SafetyInfo, MemorySSAUpdater *MSSAU, ScalarEvolution *SE, - OptimizationRemarkEmitter *ORE) { + OptimizationRemarkEmitter *ORE, AAResults *AA) { LLVM_DEBUG(dbgs() << "LICM hoisting to " << Dest->getName() << ": " << I << "\n"); ORE->emit([&]() { @@ -1644,11 +1644,13 @@ // Conservatively strip all metadata on the instruction unless we were // guaranteed to execute I if we entered the loop, in which case the metadata // is valid in the loop preheader. + // This is also safe for loads on constant memory since the load result is always the same. if (I.hasMetadataOtherThanDebugLoc() && // The check on hasMetadataOtherThanDebugLoc is to prevent us from burning // time in isGuaranteedToExecute if we don't actually have anything to // drop. It is a compile time optimization, not required for correctness. - !SafetyInfo->isGuaranteedToExecute(I, DT, CurLoop)) + (!SafetyInfo->isGuaranteedToExecute(I, DT, CurLoop) || + (isa(I) && AA->pointsToConstantMemory(cast(I).getOperand(0))))) I.dropUnknownNonDebugMetadata(); if (isa(I))