Skip to content

Commit 8b824f3

Browse files
authored
[PowerPC] Avoid working on deleted node in ext bool trunc combine (#160050)
This code was already creating HandleSDNodes to handle the case where a node gets replaced with an equivalent node. However, the code before the handles are created also performs RAUW operations, which can end up CSEing and deleting nodes. Fix this issue by moving the handle creation earlier. Fixes #160040.
1 parent 89d79b6 commit 8b824f3

File tree

2 files changed

+30
-4
lines changed

2 files changed

+30
-4
lines changed

llvm/lib/Target/PowerPC/PPCISelLowering.cpp

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -15411,6 +15411,12 @@ SDValue PPCTargetLowering::DAGCombineExtBoolTrunc(SDNode *N,
1541115411
}
1541215412
}
1541315413

15414+
// Convert PromOps to handles before doing any RAUW operations, as these
15415+
// may CSE with existing nodes, deleting the originals.
15416+
std::list<HandleSDNode> PromOpHandles;
15417+
for (auto &PromOp : PromOps)
15418+
PromOpHandles.emplace_back(PromOp);
15419+
1541415420
// Replace all inputs, either with the truncation operand, or a
1541515421
// truncation or extension to the final output type.
1541615422
for (unsigned i = 0, ie = Inputs.size(); i != ie; ++i) {
@@ -15434,10 +15440,6 @@ SDValue PPCTargetLowering::DAGCombineExtBoolTrunc(SDNode *N,
1543415440
DAG.getAnyExtOrTrunc(InSrc, dl, N->getValueType(0)));
1543515441
}
1543615442

15437-
std::list<HandleSDNode> PromOpHandles;
15438-
for (auto &PromOp : PromOps)
15439-
PromOpHandles.emplace_back(PromOp);
15440-
1544115443
// Replace all operations (these are all the same, but have a different
1544215444
// (promoted) return type). DAG.getNode will validate that the types of
1544315445
// a binary operator match, so go through the list in reverse so that
Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 6
2+
; RUN: llc -mtriple=powerpc64le-unknown-linux-gnu < %s | FileCheck %s
3+
4+
; Make sure this does not crash.
5+
define i32 @test(i32 %arg) {
6+
; CHECK-LABEL: test:
7+
; CHECK: # %bb.0:
8+
; CHECK-NEXT: rlwinm 4, 3, 13, 19, 19
9+
; CHECK-NEXT: rlwinm 3, 3, 2, 30, 30
10+
; CHECK-NEXT: xori 4, 4, 4096
11+
; CHECK-NEXT: xori 3, 3, 2
12+
; CHECK-NEXT: rlwimi 3, 4, 0, 31, 29
13+
; CHECK-NEXT: blr
14+
%icmp = icmp sgt i32 %arg, -1
15+
%select = select i1 %icmp, i16 1, i16 0
16+
%select1 = select i1 %icmp, i16 16384, i16 0
17+
%lshr = lshr i16 %select1, 1
18+
%zext = zext i16 %lshr to i32
19+
%lshr2 = lshr i32 %zext, 1
20+
%shl = shl i16 %select, 1
21+
%zext3 = zext i16 %shl to i32
22+
%or = or i32 %lshr2, %zext3
23+
ret i32 %or
24+
}

0 commit comments

Comments
 (0)