forked from OSchip/llvm-project
[VirtualInst] Derive correct use kind of PHI operands. NFC.
VirtualUse::create is only called for MemoryKind::Value, but its consistency nonetheless checked in verifyUses(). PHI uses are always inter-stmt dependencies, which was not considered by the constructor method. The virtual and non-virtual execution paths were the same, such that verifyUses did not encounter any inconsistencies. llvm-svn: 323283
This commit is contained in:
parent
03bb127569
commit
1ed2bc5266
|
|
@ -99,7 +99,10 @@ public:
|
||||||
/// @return The VirtualUse representing the same use as @p U.
|
/// @return The VirtualUse representing the same use as @p U.
|
||||||
static VirtualUse create(Scop *S, const Use &U, LoopInfo *LI, bool Virtual);
|
static VirtualUse create(Scop *S, const Use &U, LoopInfo *LI, bool Virtual);
|
||||||
|
|
||||||
/// Get a VirtualUse for any kind of use of a value within a statement.
|
/// Get a VirtualUse for uses within statements.
|
||||||
|
///
|
||||||
|
/// It is assumed that the user is not a PHINode. Such uses are always
|
||||||
|
/// VirtualUse::Inter unless in a regions statement.
|
||||||
///
|
///
|
||||||
/// @param S The Scop object.
|
/// @param S The Scop object.
|
||||||
/// @param UserStmt The statement in which @p Val is used. Can be nullptr, in
|
/// @param UserStmt The statement in which @p Val is used. Can be nullptr, in
|
||||||
|
|
|
||||||
|
|
@ -21,13 +21,33 @@ using namespace llvm;
|
||||||
VirtualUse VirtualUse ::create(Scop *S, const Use &U, LoopInfo *LI,
|
VirtualUse VirtualUse ::create(Scop *S, const Use &U, LoopInfo *LI,
|
||||||
bool Virtual) {
|
bool Virtual) {
|
||||||
auto *UserBB = getUseBlock(U);
|
auto *UserBB = getUseBlock(U);
|
||||||
|
Loop *UserScope = LI->getLoopFor(UserBB);
|
||||||
Instruction *UI = dyn_cast<Instruction>(U.getUser());
|
Instruction *UI = dyn_cast<Instruction>(U.getUser());
|
||||||
ScopStmt *UserStmt = nullptr;
|
ScopStmt *UserStmt = S->getStmtFor(UI);
|
||||||
if (PHINode *PHI = dyn_cast<PHINode>(UI))
|
|
||||||
UserStmt = S->getLastStmtFor(PHI->getIncomingBlock(U));
|
// Uses by PHI nodes are always reading values written by other statements,
|
||||||
else
|
// except it is within a region statement.
|
||||||
UserStmt = S->getStmtFor(UI);
|
if (PHINode *PHI = dyn_cast<PHINode>(UI)) {
|
||||||
auto *UserScope = LI->getLoopFor(UserBB);
|
// Handle PHI in exit block.
|
||||||
|
if (S->getRegion().getExit() == PHI->getParent())
|
||||||
|
return VirtualUse(UserStmt, U.get(), Inter, nullptr, nullptr);
|
||||||
|
|
||||||
|
if (UserStmt->getEntryBlock() != PHI->getParent())
|
||||||
|
return VirtualUse(UserStmt, U.get(), Intra, nullptr, nullptr);
|
||||||
|
|
||||||
|
// The MemoryAccess is expected to be set if @p Virtual is true.
|
||||||
|
MemoryAccess *IncomingMA = nullptr;
|
||||||
|
if (Virtual) {
|
||||||
|
if (const ScopArrayInfo *SAI =
|
||||||
|
S->getScopArrayInfoOrNull(PHI, MemoryKind::PHI)) {
|
||||||
|
IncomingMA = S->getPHIRead(SAI);
|
||||||
|
assert(IncomingMA->getStatement() == UserStmt);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return VirtualUse(UserStmt, U.get(), Inter, nullptr, IncomingMA);
|
||||||
|
}
|
||||||
|
|
||||||
return create(S, UserStmt, UserScope, U.get(), Virtual);
|
return create(S, UserStmt, UserScope, U.get(), Virtual);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue