1# RUN: llc -mtriple=aarch64 -run-pass=machine-outliner -machine-outliner-reruns=1 -verify-machineinstrs %s -o - | FileCheck %s --check-prefix TWO-RUNS 2# RUN: llc -mtriple=aarch64 -run-pass=machine-outliner -machine-outliner-reruns=0 -verify-machineinstrs %s -o - | FileCheck %s --check-prefix ONE-RUN 3# RUN: llc -mtriple=aarch64 -run-pass=machine-outliner -machine-outliner-reruns=3 -verify-machineinstrs %s -o - | FileCheck %s --check-prefix FOUR-RUNS 4 5# Example of Repeated Instruction Sequence - Iterative Machine Outlining 6# 7#; define void @"$s12"(...) { define i64 @"$s5” (...) { define void @"$s13"(...) { 8# ... ... ... 9# %8 = load i1, i1* %7 %8 = load i1, i1* %7 10# %9 = load i4, i4*, %6 %9 = load i4, i4*, %6 %9 = load i4, i4*, %6 11# store i4 %9, i4* %5 store i4 %9, i4* %5 store i4 %9, i4* %5 12# ... ... ... 13# } } } 14# 15# After machine outliner (1st time) 16# 17# define void @"$s12"(...) { define i64 @"$s5” (...) { define void @"$s13"(...) { 18# ... ... ... 19# %8 = load i1, i1* %7 %8 = load i1, i1* %7 20# call void @outlined_function_1_1 call void @outlined_function_1_1 call void @outlined_function_1_1 21# ... ... ... 22# } } } 23# 24# After machine outliner (2nd time) 25# 26# define void @"$s12"(...) { define i64 @"$s5” (...) { define void @"$s13"(...) { 27# ... ... ... 28# call void @outlined_function_2_1 call void @outlined_function_1_1 call void @outlined_function_2_1 29# ... ... ... 30# } } } 31# 32# Check whether machine outliner can further find the outlining opportunity after machine 33# outlining has performed. 34# 35--- | 36 declare void @foo() local_unnamed_addr 37 38 declare void @widget() local_unnamed_addr 39 40 ; Function Attrs: minsize noredzone optsize 41 define void @baz.14() #0 { 42 ret void 43 } 44 45 ; Function Attrs: minsize noredzone optsize 46 define void @baz.15() #0 { 47 ret void 48 } 49 50 ; Function Attrs: minsize noredzone optsize 51 define void @baz.16() #0 { 52 ret void 53 } 54 55 attributes #0 = { minsize noredzone optsize } 56... 57--- 58name: baz.14 59tracksRegLiveness: true 60stack: 61 - { id: 0, offset: -8, size: 8 } 62 - { id: 1, offset: -16, size: 8 } 63body: | 64 bb.0: 65 liveins: $x0, $x19, $lr 66 67 early-clobber $sp = frame-setup STPXpre killed $lr, killed $x19, $sp, -2 :: (store 8 into %stack.1), (store 8 into %stack.0) 68 frame-setup CFI_INSTRUCTION def_cfa_offset 16 69 frame-setup CFI_INSTRUCTION offset $w19, -8 70 frame-setup CFI_INSTRUCTION offset $w30, -16 71 renamable $x19 = COPY $x0 72 renamable $x0 = nuw ADDXri $x0, 48, 0 73 $x1 = ADDXri $sp, 0, 0 74 dead $w2 = MOVi32imm 33, implicit-def $x2 75 $x3 = COPY $xzr 76 BL @foo, csr_aarch64_aapcs, implicit-def dead $lr, implicit $sp, implicit $x0, implicit killed $x1, implicit killed $x2, implicit killed $x3, implicit-def $sp 77 $x0 = COPY killed renamable $x19 78 BL @widget, csr_aarch64_aapcs, implicit-def dead $lr, implicit $sp, implicit $x0, implicit-def $sp 79 early-clobber $sp, $lr, $x19 = frame-destroy LDPXpost $sp, 2 :: (load 8 from %stack.1), (load 8 from %stack.0) 80 RET_ReallyLR 81 82... 83--- 84name: baz.15 85tracksRegLiveness: true 86stack: 87 - { id: 0, offset: -8, size: 8 } 88 - { id: 1, offset: -16, size: 8 } 89body: | 90 bb.0: 91 liveins: $x0, $x19, $lr 92 93 early-clobber $sp = frame-setup STPXpre killed $lr, killed $x19, $sp, -2 :: (store 8 into %stack.1), (store 8 into %stack.0) 94 frame-setup CFI_INSTRUCTION def_cfa_offset 16 95 frame-setup CFI_INSTRUCTION offset $w19, -8 96 frame-setup CFI_INSTRUCTION offset $w30, -16 97 renamable $x19 = COPY $x0 98 renamable $x0 = nuw ADDXri killed renamable $x0, 16, 0 99 $x1 = ADDXri $sp, 0, 0 100 dead $w2 = MOVi32imm 33, implicit-def $x2 101 $x3 = COPY $xzr 102 BL @foo, csr_aarch64_aapcs, implicit-def dead $lr, implicit $sp, implicit $x0, implicit $x1, implicit killed $x2, implicit killed $x3, implicit-def $sp 103 $x0 = COPY killed renamable $x19 104 BL @widget, csr_aarch64_aapcs, implicit-def dead $lr, implicit $sp, implicit $x0, implicit-def $sp 105 early-clobber $sp, $lr, $x19 = frame-destroy LDPXpost $sp, 2 :: (load 8 from %stack.1), (load 8 from %stack.0) 106 RET_ReallyLR 107 108... 109--- 110name: baz.16 111tracksRegLiveness: true 112stack: 113 - { id: 0, offset: -8, size: 8 } 114 - { id: 1, offset: -16, size: 8 } 115body: | 116 bb.0: 117 liveins: $x0, $x19, $lr 118 119 early-clobber $sp = frame-setup STPXpre killed $lr, killed $x19, $sp, -2 :: (store 8 into %stack.1), (store 8 into %stack.0) 120 frame-setup CFI_INSTRUCTION def_cfa_offset 16 121 frame-setup CFI_INSTRUCTION offset $w19, -8 122 frame-setup CFI_INSTRUCTION offset $w30, -16 123 renamable $x19 = COPY $x0 124 renamable $x0 = nuw ADDXri $x0, 48, 0 125 $x1 = ADDXri $sp, 0, 0 126 dead $w2 = MOVi32imm 33, implicit-def $x2 127 $x3 = COPY $xzr 128 BL @foo, csr_aarch64_aapcs, implicit-def dead $lr, implicit $sp, implicit $x0, implicit killed $x1, implicit killed $x2, implicit killed $x3, implicit-def $sp 129 $x0 = COPY killed renamable $x19 130 BL @widget, csr_aarch64_aapcs, implicit-def dead $lr, implicit $sp, implicit $x0, implicit-def $sp 131 early-clobber $sp, $lr, $x19 = frame-destroy LDPXpost $sp, 2 :: (load 8 from %stack.1), (load 8 from %stack.0) 132 RET_ReallyLR 133 134... 135 136# TWO-RUNS: name: OUTLINED_FUNCTION_2_0 137# TWO-RUNS-DAG: bb.0: 138# TWO-RUNS-DAG: renamable $x19 = COPY $x0 139# TWO-RUNS-NEXT: renamable $x0 = nuw ADDXri $x0, 48, 0 140# TWO-RUNS-NEXT: TCRETURNdi @OUTLINED_FUNCTION_0, 0, implicit $sp 141# 142# The machine outliner is expected to stop at the 1st iteration for case ONE-RUN 143# since machine-outline-runs is specified as 1. 144# ONE-RUN-NOT: [[OUTLINED:OUTLINED_FUNCTION_2_[0-9]+]] 145# 146# The machine outliner is expected to stop at the 3rd iteration for case FOUR-RUNS 147# since the MIR has no change at the 3rd iteration. 148# FOUR-RUNS-NOT: [[OUTLINED:OUTLINED_FUNCTION_3_[0-9]+]] 149# FOUR-RUNS-NOT: [[OUTLINED:OUTLINED_FUNCTION_4_[0-9]+]] 150