From 4df216cd62180e2e1965c7bb31837696d8aa4cf3 Mon Sep 17 00:00:00 2001 From: Brendon Cahoon Date: Fri, 12 Apr 2019 16:37:12 +0000 Subject: [PATCH] [Hexagon] Fix reuse bug in Vector Loop Carried Reuse pass The Hexagon Vector Loop Carried Reuse pass was allowing reuse between two shufflevectors with different masks. The reason is that the masks are not instruction objects, so the code that checks each operand just skipped over the operands. This patch fixes the bug by checking if the operands are the same when they are not instruction objects. If the objects are not the same, then the code assumes that reuse cannot occur. Differential Revision: https://reviews.llvm.org/D60019 llvm-svn: 358292 --- .../Hexagon/HexagonVectorLoopCarriedReuse.cpp | 15 ++++++++--- ...xagon_vector_loop_carried_reuse_invalid.ll | 27 +++++++++++++++++++ 2 files changed, 38 insertions(+), 4 deletions(-) create mode 100644 llvm/test/CodeGen/Hexagon/hexagon_vector_loop_carried_reuse_invalid.ll diff --git a/llvm/lib/Target/Hexagon/HexagonVectorLoopCarriedReuse.cpp b/llvm/lib/Target/Hexagon/HexagonVectorLoopCarriedReuse.cpp index b3ef3e487280..7236dd283b83 100644 --- a/llvm/lib/Target/Hexagon/HexagonVectorLoopCarriedReuse.cpp +++ b/llvm/lib/Target/Hexagon/HexagonVectorLoopCarriedReuse.cpp @@ -429,11 +429,18 @@ void HexagonVectorLoopCarriedReuse::findValueToReuse() { for (int OpNo = 0; OpNo < NumOperands; ++OpNo) { Value *Op = I->getOperand(OpNo); - Instruction *OpInst = dyn_cast(Op); - if (!OpInst) - continue; - Value *BEOp = BEUser->getOperand(OpNo); + + Instruction *OpInst = dyn_cast(Op); + if (!OpInst) { + if (Op == BEOp) + continue; + // Do not allow reuse to occur when the operands may be different + // values. + BEUser = nullptr; + break; + } + Instruction *BEOpInst = dyn_cast(BEOp); if (!isDepChainBtwn(OpInst, BEOpInst, Iters)) { diff --git a/llvm/test/CodeGen/Hexagon/hexagon_vector_loop_carried_reuse_invalid.ll b/llvm/test/CodeGen/Hexagon/hexagon_vector_loop_carried_reuse_invalid.ll new file mode 100644 index 000000000000..b440dba66f67 --- /dev/null +++ b/llvm/test/CodeGen/Hexagon/hexagon_vector_loop_carried_reuse_invalid.ll @@ -0,0 +1,27 @@ +; RUN: opt -hexagon-vlcr < %s -S | FileCheck %s + +; Test that reuse doesn't occur due to two shufflevectors with different masks. + +; CHECK-NOT: extract.h.hexagon.vlcr + +define dso_local void @test() local_unnamed_addr #0 { +entry: + %0 = tail call <64 x i32> @llvm.hexagon.V6.vunpackuh.128B(<32 x i32> undef) + br i1 undef, label %for.end, label %for.body + +for.body: + %a = phi <64 x i32> [ %1, %for.body ], [ %0, %entry ] + %extract.h = shufflevector <64 x i32> %a, <64 x i32> undef, <32 x i32> + %1 = tail call <64 x i32> @llvm.hexagon.V6.vaddw.dv.128B(<64 x i32> undef, <64 x i32> undef) + %extract.l = shufflevector <64 x i32> %1, <64 x i32> undef, <32 x i32> + br label %for.body + +for.end: + ret void +} + +declare <64 x i32> @llvm.hexagon.V6.vunpackuh.128B(<32 x i32>) #1 +declare <64 x i32> @llvm.hexagon.V6.vaddw.dv.128B(<64 x i32>, <64 x i32>) #1 + +attributes #0 = { "use-soft-float"="false" } +attributes #1 = { nounwind readnone }