diff --git a/llvm/lib/Target/AArch64/AArch64InstrInfo.cpp b/llvm/lib/Target/AArch64/AArch64InstrInfo.cpp index 5420545cc3cec..9a8e9294aa861 100644 --- a/llvm/lib/Target/AArch64/AArch64InstrInfo.cpp +++ b/llvm/lib/Target/AArch64/AArch64InstrInfo.cpp @@ -9585,10 +9585,15 @@ AArch64InstrInfo::getOutlinableRanges(MachineBasicBlock &MBB, }; auto SaveRangeIfNonEmpty = [&RangeLen, &Ranges, &RangeBegin, &RangeEnd]() { // At least one unsafe register is not dead. We do not want to outline at - // this point. If it is long enough to outline from, save the range - // [RangeBegin, RangeEnd). - if (RangeLen > 1) - Ranges.push_back(std::make_pair(RangeBegin, RangeEnd)); + // this point. If it is long enough to outline from and does not cross a + // bundle boundary, save the range [RangeBegin, RangeEnd). + if (RangeLen <= 1) + return; + if (!RangeBegin.isEnd() && RangeBegin->isBundledWithPred()) + return; + if (!RangeEnd.isEnd() && RangeEnd->isBundledWithPred()) + return; + Ranges.emplace_back(RangeBegin, RangeEnd); }; // Find the first point where all unsafe registers are dead. // FIND: <-- end of first potential range diff --git a/llvm/test/CodeGen/AArch64/machine-outliner-safe-range-in-middle.mir b/llvm/test/CodeGen/AArch64/machine-outliner-safe-range-in-middle.mir index 23811425101fd..b99ca25a5432d 100644 --- a/llvm/test/CodeGen/AArch64/machine-outliner-safe-range-in-middle.mir +++ b/llvm/test/CodeGen/AArch64/machine-outliner-safe-range-in-middle.mir @@ -16,27 +16,53 @@ body: | ; CHECK-NEXT: {{ $}} ; CHECK-NEXT: BL @OUTLINED_FUNCTION_0, implicit-def $lr, implicit $sp, implicit-def $lr, implicit-def $x0, implicit-def $x1, implicit-def $x2, implicit-def $x3, implicit-def $x16, implicit $x0, implicit $sp ; CHECK-NEXT: $x9 = ADDXri $x16, 16, 0 - ; CHECK-NEXT: $x16 = ADDXri killed $x16, 16, 0 + ; CHECK-NEXT: $x16 = ADDXri killed $x16, 16, 1 ; CHECK-NEXT: BL @OUTLINED_FUNCTION_0, implicit-def $lr, implicit $sp, implicit-def $lr, implicit-def $x0, implicit-def $x1, implicit-def $x2, implicit-def $x3, implicit-def $x16, implicit $x0, implicit $sp ; CHECK-NEXT: $x9 = ADDXri $x9, 16, 0 - ; CHECK-NEXT: $x16 = ADDXri killed $x16, 16, 0 + ; CHECK-NEXT: $x16 = ADDXri killed $x16, 16, 2 ; CHECK-NEXT: RET undef $x9 $x0 = ADDXri $x0, 0, 0 $x1 = ADDXri $x0, 1, 0 $x2 = ADDXri $x0, 2, 0 $x3 = ADDXri $x0, 3, 0 - - ; End safe range $x16 = ADDXri $x0, 16, 0 $x9 = ADDXri $x16, 16, 0 - $x16 = ADDXri killed $x16, 16, 0 - + $x16 = ADDXri killed $x16, 16, 1 + ; End safe range $x0 = ADDXri $x0, 0, 0 $x1 = ADDXri $x0, 1, 0 $x2 = ADDXri $x0, 2, 0 $x3 = ADDXri $x0, 3, 0 - ; End safe range $x16 = ADDXri $x0, 16, 0 $x9 = ADDXri $x9, 16, 0 - $x16 = ADDXri killed $x16, 16, 0 + $x16 = ADDXri killed $x16, 16, 2 + ; End safe range RET undef $x9 +... +--- +name: unsafe_range_bundle +tracksRegLiveness: true +machineFunctionInfo: + hasRedZone: false +body: | + bb.0: + liveins: $x0 + ; CHECK-LABEL: name: unsafe_range_bundle + ; CHECK: liveins: $x0 + ; CHECK-NEXT: {{ $}} + ; CHECK-NEXT: $x0 = ADDXri $x0, 0, 0 + ; CHECK-NEXT: $x16 = ADDXri $x0, 16, 0 + ; CHECK-NEXT: BUNDLE { + ; CHECK-NEXT: $x16 = ADDXri killed $x16, 16, 3 + ; CHECK-NEXT: $x1 = ADDXri $x0, 0, 0 + ; CHECK-NEXT: } + ; CHECK-NEXT: RET undef $x9 + $x0 = ADDXri $x0, 0, 0 + $x16 = ADDXri $x0, 16, 0 + BUNDLE { ; Bundle crosses a safe range + $x16 = ADDXri killed $x16, 16, 3 + ; End safe range + $x1 = ADDXri $x0, 0, 0 + } + RET undef $x9 +...