diff --git a/lib/Target/PowerPC/PPCPreEmitPeephole.cpp b/lib/Target/PowerPC/PPCPreEmitPeephole.cpp index a4b4bf2973d..4ea714ff15f 100644 --- a/lib/Target/PowerPC/PPCPreEmitPeephole.cpp +++ b/lib/Target/PowerPC/PPCPreEmitPeephole.cpp @@ -109,6 +109,16 @@ namespace { // Track the operand that kill Reg. We would unset the kill flag of // the operand if there is a following redundant load immediate. int KillIdx = AfterBBI->findRegisterUseOperandIdx(Reg, true, TRI); + + // We can't just clear implicit kills, so if we encounter one, stop + // looking further. + if (KillIdx != -1 && AfterBBI->getOperand(KillIdx).isImplicit()) { + LLVM_DEBUG(dbgs() + << "Encountered an implicit kill, cannot proceed: "); + LLVM_DEBUG(AfterBBI->dump()); + break; + } + if (KillIdx != -1) { assert(!DeadOrKillToUnset && "Shouldn't kill same register twice"); DeadOrKillToUnset = &AfterBBI->getOperand(KillIdx); diff --git a/test/CodeGen/PowerPC/remove-redundant-li-skip-imp-kill.mir b/test/CodeGen/PowerPC/remove-redundant-li-skip-imp-kill.mir new file mode 100644 index 00000000000..78091d027ce --- /dev/null +++ b/test/CodeGen/PowerPC/remove-redundant-li-skip-imp-kill.mir @@ -0,0 +1,114 @@ +# NOTE: Assertions have been autogenerated by utils/update_mir_test_checks.py +# RUN: llc -mcpu=pwr9 -mtriple=powerpc64le-unknown-unknown -run-pass \ +# RUN: ppc-pre-emit-peephole %s -o - | FileCheck %s +--- | + ; ModuleID = 'a.ll' + source_filename = "a.ll" + target datalayout = "e-m:e-i64:64-n32:64" + + ; Function Attrs: nounwind + define dso_local signext i32 @b(i32 signext %a, i32* nocapture %b) local_unnamed_addr #0 { + entry: + %call = tail call signext i32 @g(i32 signext %a) + store i32 %call, i32* %b, align 4 + %call1 = tail call signext i32 @g(i32 signext %a) + ret i32 %call1 + } + + ; Function Attrs: nounwind + declare signext i32 @g(i32 signext) local_unnamed_addr #0 + + ; Function Attrs: nounwind + declare void @llvm.stackprotector(i8*, i8**) #0 + + attributes #0 = { nounwind } + +... +--- +name: b +alignment: 16 +exposesReturnsTwice: false +legalized: false +regBankSelected: false +selected: false +failedISel: false +tracksRegLiveness: true +hasWinCFI: false +registers: [] +liveins: + - { reg: '$x3', virtual-reg: '' } + - { reg: '$x4', virtual-reg: '' } +frameInfo: + isFrameAddressTaken: false + isReturnAddressTaken: false + hasStackMap: false + hasPatchPoint: false + stackSize: 64 + offsetAdjustment: 0 + maxAlignment: 1 + adjustsStack: true + hasCalls: true + stackProtector: '' + maxCallFrameSize: 32 + cvBytesOfCalleeSavedRegisters: 0 + hasOpaqueSPAdjustment: false + hasVAStart: false + hasMustTailInVarArgFunc: false + localFrameSize: 0 + savePoint: '' + restorePoint: '' +fixedStack: + - { id: 0, type: spill-slot, offset: -80, size: 8, alignment: 16, stack-id: default, + callee-saved-register: '$x30', callee-saved-restored: true, debug-info-variable: '', + debug-info-expression: '', debug-info-location: '' } + - { id: 1, type: spill-slot, offset: -88, size: 8, alignment: 8, stack-id: default, + callee-saved-register: '$x29', callee-saved-restored: true, debug-info-variable: '', + debug-info-expression: '', debug-info-location: '' } +stack: [] +callSites: [] +constants: [] +machineFunctionInfo: {} +body: | + bb.0.entry: + liveins: $x3, $x4, $x29, $x30 + + ; CHECK-LABEL: name: b + ; CHECK: liveins: $x3, $x4, $x29, $x30 + ; CHECK: $x0 = MFLR8 implicit $lr8 + ; CHECK: STD killed $x29, -24, $x1 :: (store 8 into %fixed-stack.0) + ; CHECK: STD killed $x30, -16, $x1 :: (store 8 into %fixed-stack.1, align 16) + ; CHECK: STD killed $x0, 16, $x1 + ; CHECK: $x1 = STDU $x1, -64, $x1 + ; CHECK: $x30 = OR8 killed $x4, $x4 + ; CHECK: dead $r4 = LI 10, implicit-def $x4 + ; CHECK: $x29 = OR8 $x3, $x3 + ; CHECK: BL8_NOP @g, csr_ppc64_r2_altivec, implicit-def dead $lr8, implicit $rm, implicit killed $x3, implicit killed $x4, implicit $x2, implicit-def $r1, implicit-def $x3 + ; CHECK: STW8 killed renamable $x3, 0, killed renamable $x30 :: (store 4 into %ir.b) + ; CHECK: $x3 = OR8 killed $x29, $x29 + ; CHECK: BL8_NOP @g, csr_ppc64_r2_altivec, implicit-def dead $lr8, implicit $rm, implicit killed $x3, implicit $x2, implicit-def $r1, implicit-def $x3 + ; CHECK: $x1 = ADDI8 $x1, 64 + ; CHECK: $x0 = LD 16, $x1 + ; CHECK: $x30 = LD -16, $x1 :: (load 8 from %fixed-stack.1, align 16) + ; CHECK: $x29 = LD -24, $x1 :: (load 8 from %fixed-stack.0) + ; CHECK: MTLR8 killed $x0, implicit-def $lr8 + ; CHECK: BLR8 implicit $lr8, implicit $rm, implicit killed $x3 + $x0 = MFLR8 implicit $lr8 + STD killed $x29, -24, $x1 :: (store 8 into %fixed-stack.1) + STD killed $x30, -16, $x1 :: (store 8 into %fixed-stack.0, align 16) + STD killed $x0, 16, $x1 + $x1 = STDU $x1, -64, $x1 + $x30 = OR8 killed $x4, $x4 + dead $r4 = LI 10, implicit-def $x4 + $x29 = OR8 $x3, $x3 + BL8_NOP @g, csr_ppc64_r2_altivec, implicit-def dead $lr8, implicit $rm, implicit killed $x3, implicit killed $x4, implicit $x2, implicit-def $r1, implicit-def $x3 + STW8 killed renamable $x3, 0, killed renamable $x30 :: (store 4 into %ir.b) + $x3 = OR8 killed $x29, $x29 + BL8_NOP @g, csr_ppc64_r2_altivec, implicit-def dead $lr8, implicit $rm, implicit killed $x3, implicit $x2, implicit-def $r1, implicit-def $x3 + $x1 = ADDI8 $x1, 64 + $x0 = LD 16, $x1 + $x30 = LD -16, $x1 :: (load 8 from %fixed-stack.0, align 16) + $x29 = LD -24, $x1 :: (load 8 from %fixed-stack.1) + MTLR8 killed $x0, implicit-def $lr8 + BLR8 implicit $lr8, implicit $rm, implicit killed $x3 + +...