blob: 67358e8354a05b46946317942e96cea67df0d6d1 [file] [edit]
; Tests that BasicBlockMatchingAndInference matches the blocks of a Propeller
; CFG profile to machine basic blocks by their BB IDs, without BB hashes in the
; profile, and infers the hot and cold clusters from the matched weights.
;
; Test 1: Blocks #0, #1 and #3 are hot; block #2 goes to the cold section.
; RUN: echo 'v1' > %t1
; RUN: echo 'f foo' >> %t1
; RUN: echo 'g 0:100,1:100,2:0 1:100,3:100 2:0,3:0 3:100' >> %t1
; RUN: llc < %s -O0 -mtriple=x86_64-pc-linux -function-sections -basic-block-sections=%t1 -basic-block-section-match-infer -propeller-match-bbid | \
; RUN: FileCheck %s --check-prefixes=CHECK,BBID1
;
; Test 2: Blocks #0, #2 and #3 are hot; block #1 goes to the cold section.
; RUN: echo 'v1' > %t2
; RUN: echo 'f foo' >> %t2
; RUN: echo 'g 0:100,1:0,2:100 1:0,3:0 2:100,3:100 3:100' >> %t2
; RUN: llc < %s -O0 -mtriple=x86_64-pc-linux -function-sections -basic-block-sections=%t2 -basic-block-section-match-infer -propeller-match-bbid | \
; RUN: FileCheck %s --check-prefixes=CHECK,BBID2
;
; Test 3: With hash matching, the profile without BB hashes matches no blocks,
; so foo is not split.
; RUN: llc < %s -O0 -mtriple=x86_64-pc-linux -function-sections -basic-block-sections=%t1 -basic-block-section-match-infer -propeller-match-bbid=false | \
; RUN: FileCheck %s --check-prefixes=CHECK,HASH
;
; Test 4: Blocks are matched by their base IDs, so the counts of clone #2.1 in
; the profile apply to block #2, giving the same clusters as Test 2.
; RUN: echo 'v1' > %t4
; RUN: echo 'f foo' >> %t4
; RUN: echo 'g 0:100,1:0,2.1:100 1:0,3:0 2.1:100,3:100 3:100' >> %t4
; RUN: llc < %s -O0 -mtriple=x86_64-pc-linux -function-sections -basic-block-sections=%t4 -basic-block-section-match-infer -propeller-match-bbid | \
; RUN: FileCheck %s --check-prefixes=CHECK,BBID2
define void @foo(i1 zeroext %0) nounwind {
%2 = alloca i8, align 1
%3 = zext i1 %0 to i8
store i8 %3, ptr %2, align 1
%4 = load i8, ptr %2, align 1
%5 = trunc i8 %4 to i1
br i1 %5, label %6, label %8
6: ; preds = %1
%7 = call i32 @bar()
br label %10
8: ; preds = %1
%9 = call i32 @baz()
br label %10
10: ; preds = %8, %6
ret void
}
; qux has no CFG profile, so it keeps its layout and is never split.
define void @qux(i1 %c) nounwind {
br i1 %c, label %a, label %b
a:
%r = call i32 @bar()
br label %b
b:
ret void
}
declare i32 @bar()
declare i32 @baz()
; CHECK: .section .text.foo,"ax",@progbits
; CHECK-LABEL: foo:
; BBID1: je foo.cold
; BBID1-NEXT: # %bb.1:
; BBID1-NEXT: callq bar@PLT
; BBID2: jne foo.cold
; BBID2-NEXT: # %bb.2:
; BBID2-NEXT: callq baz@PLT
; BBID1-NEXT: .LBB0_3:
; BBID2-NEXT: .LBB0_3:
; BBID1: .section .text.split.foo,"ax",@progbits
; BBID2: .section .text.split.foo,"ax",@progbits
; BBID1-NEXT: foo.cold:
; BBID2-NEXT: foo.cold:
; BBID1-NEXT: callq baz@PLT
; BBID2-NEXT: callq bar@PLT
; HASH: je .LBB0_2
; HASH: callq bar@PLT
; HASH: callq baz@PLT
; HASH-NOT: .text.split.foo
; CHECK: .section .text.qux,"ax",@progbits
; CHECK-LABEL: qux:
; CHECK-NOT: .text.split.qux