1
0
mirror of https://github.com/RPCS3/llvm-mirror.git synced 2024-10-19 11:02:59 +02:00

[GVN] Remove stale entries in phitranslate cache when new phi is generated for PRE

When a new phi is generated for scalarpre of an expression, the phiTranslate cache
will become stale: Before PRE, the candidate expression must not be available in a
predecessor block, and phitranslate will cache the information. After PRE, the
expression will become available in all predecessor blocks, so the related entries
in phiTranslate cache becomes stale. The patch will simply remove the stale entries
so phiTranslate can be recomputed next time.

The stale entries in phitranslate cache will not affect correctness but will cause
missing PRE opportunity for later instructions.

Differential Revision: https://reviews.llvm.org/D36124

llvm-svn: 310421
This commit is contained in:
Wei Mi 2017-08-08 21:40:14 +00:00
parent 11f046ff78
commit 6484ea55e4
3 changed files with 60 additions and 0 deletions

View File

@ -111,6 +111,7 @@ public:
Value *LHS, Value *RHS);
uint32_t phiTranslate(const BasicBlock *BB, const BasicBlock *PhiBlock,
uint32_t Num, GVN &Gvn);
void eraseTranslateCacheEntry(uint32_t Num, const BasicBlock &CurrBlock);
bool exists(Value *V) const;
void add(Value *V, uint32_t num);
void clear();

View File

@ -1558,6 +1558,17 @@ uint32_t GVN::ValueTable::phiTranslateImpl(const BasicBlock *Pred,
return Num;
}
/// Erase stale entry from phiTranslate cache so phiTranslate can be computed
/// again.
void GVN::ValueTable::eraseTranslateCacheEntry(uint32_t Num,
const BasicBlock &CurrBlock) {
for (const BasicBlock *Pred : predecessors(&CurrBlock)) {
auto FindRes = PhiTranslateTable.find({Num, Pred});
if (FindRes != PhiTranslateTable.end())
PhiTranslateTable.erase(FindRes);
}
}
// In order to find a leader for a given value number at a
// specific basic block, we first obtain the list of all Values for that number,
// and then scan the list to find one whose block dominates the block in
@ -2210,6 +2221,9 @@ bool GVN::performScalarPRE(Instruction *CurInst) {
}
VN.add(Phi, ValNo);
// After creating a new PHI for ValNo, the phi translate result for ValNo will
// be changed, so erase the related stale entries in phi translate cache.
VN.eraseTranslateCacheEntry(ValNo, *CurrentBlock);
addToLeaderTable(ValNo, Phi, CurrentBlock);
Phi->setDebugLoc(CurInst->getDebugLoc());
CurInst->replaceAllUsesWith(Phi);

View File

@ -129,3 +129,48 @@ bb343:
critedge.loopexit:
unreachable
}
; Check sub expression will be pre transformed.
; CHECK-LABEL: @test5(
; CHECK: entry:
; CHECK: %sub.ptr.sub = sub i64 %sub.ptr.lhs.cast, %sub.ptr.rhs.cast
; CHECK: br i1 %cmp
; CHECK: if.then2:
; CHECK: %[[PTRTOINT:.*]] = ptrtoint i32* %add.ptr to i64
; CHECK: %[[SUB:.*]] = sub i64 %sub.ptr.lhs.cast, %[[PTRTOINT]]
; CHECK: br label %if.end3
; CHECK: if.end3:
; CHECK: %[[PREPHI:.*]] = phi i64 [ %sub.ptr.sub, %if.else ], [ %[[SUB]], %if.then2 ], [ %sub.ptr.sub, %entry ]
; CHECK: %[[DIV:.*]] = ashr exact i64 %[[PREPHI]], 2
; CHECK: ret i64 %[[DIV]]
declare void @bar(...) local_unnamed_addr #1
; Function Attrs: nounwind uwtable
define i64 @test5(i32* %start, i32* %e, i32 %n1, i32 %n2) local_unnamed_addr #0 {
entry:
%sub.ptr.lhs.cast = ptrtoint i32* %e to i64
%sub.ptr.rhs.cast = ptrtoint i32* %start to i64
%sub.ptr.sub = sub i64 %sub.ptr.lhs.cast, %sub.ptr.rhs.cast
%cmp = icmp sgt i64 %sub.ptr.sub, 4000
br i1 %cmp, label %if.then, label %if.end3
if.then: ; preds = %entry
%cmp1 = icmp sgt i32 %n1, %n2
br i1 %cmp1, label %if.then2, label %if.else
if.then2: ; preds = %if.then
%add.ptr = getelementptr inbounds i32, i32* %start, i64 800
br label %if.end3
if.else: ; preds = %if.then
tail call void (...) @bar() #2
br label %if.end3
if.end3: ; preds = %if.then2, %if.else, %entry
%p.0 = phi i32* [ %add.ptr, %if.then2 ], [ %start, %if.else ], [ %start, %entry ]
%sub.ptr.rhs.cast5 = ptrtoint i32* %p.0 to i64
%sub.ptr.sub6 = sub i64 %sub.ptr.lhs.cast, %sub.ptr.rhs.cast5
%sub.ptr.div7 = ashr exact i64 %sub.ptr.sub6, 2
ret i64 %sub.ptr.div7
}