789 lines
13 KiB
LLVM
789 lines
13 KiB
LLVM
|
; RUN: llc -verify-machineinstrs < %s -mtriple=powerpc64-unknown-linux-gnu | FileCheck %s
|
||
|
; RUN: llc -verify-machineinstrs < %s -mtriple=powerpc64le-unknown-linux-gnu | FileCheck %s
|
||
|
|
||
|
; Test cases for compare elimination in PPCMIPeephole pass
|
||
|
|
||
|
define void @func1(i32 signext %a) {
|
||
|
; We should have only one compare instruction
|
||
|
; CHECK-LABEL: @func1
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp eq i32 %a, 100
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp slt i32 %a, 100
|
||
|
br i1 %cmp1, label %if.then2, label %if.end3
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func2(i32 signext %a) {
|
||
|
; CHECK-LABEL: @func2
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp slt i32 %a, 100
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp eq i32 %a, 100
|
||
|
br i1 %cmp1, label %if.end3, label %if.then2
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func3(i32 signext %a) {
|
||
|
; CHECK-LABEL: @func3
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp sgt i32 %a, 100
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp eq i32 %a, 100
|
||
|
br i1 %cmp1, label %if.then2, label %if.end3
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func4(i32 zeroext %a) {
|
||
|
; CHECK-LABEL: @func4
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp eq i32 %a, 100
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp ult i32 %a, 100
|
||
|
br i1 %cmp1, label %if.then2, label %if.end3
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func5(i32 zeroext %a) {
|
||
|
; CHECK-LABEL: @func5
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp ult i32 %a, 100
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp eq i32 %a, 100
|
||
|
br i1 %cmp1, label %if.end3, label %if.then2
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func6(i32 zeroext %a) {
|
||
|
; CHECK-LABEL: @func6
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp ugt i32 %a, 100
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp eq i32 %a, 100
|
||
|
br i1 %cmp1, label %if.then2, label %if.end3
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func7(i64 %a) {
|
||
|
; CHECK-LABEL: @func7
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp eq i64 %a, 100
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp slt i64 %a, 100
|
||
|
br i1 %cmp1, label %if.then2, label %if.end3
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func8(i64 %a) {
|
||
|
; CHECK-LABEL: @func8
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp slt i64 %a, 100
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp eq i64 %a, 100
|
||
|
br i1 %cmp1, label %if.end3, label %if.then2
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func9(i64 %a) {
|
||
|
; CHECK-LABEL: @func9
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp sgt i64 %a, 100
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp eq i64 %a, 100
|
||
|
br i1 %cmp1, label %if.then2, label %if.end3
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func10(i64 %a) {
|
||
|
; CHECK-LABEL: @func10
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp eq i64 %a, 100
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp ult i64 %a, 100
|
||
|
br i1 %cmp1, label %if.then2, label %if.end3
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func11(i64 %a) {
|
||
|
; CHECK-LABEL: @func11
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp ult i64 %a, 100
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp eq i64 %a, 100
|
||
|
br i1 %cmp1, label %if.end3, label %if.then2
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func12(i64 %a) {
|
||
|
; CHECK-LABEL: @func12
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp ugt i64 %a, 100
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp eq i64 %a, 100
|
||
|
br i1 %cmp1, label %if.then2, label %if.end3
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func13(i32 signext %a, i32 signext %b) {
|
||
|
; CHECK-LABEL: @func13
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp eq i32 %a, %b
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp slt i32 %a, %b
|
||
|
br i1 %cmp1, label %if.then2, label %if.end3
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func14(i32 signext %a, i32 signext %b) {
|
||
|
; CHECK-LABEL: @func14
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp slt i32 %a, %b
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp sgt i32 %a, %b
|
||
|
br i1 %cmp1, label %if.then2, label %if.end3
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func15(i32 signext %a, i32 signext %b) {
|
||
|
; CHECK-LABEL: @func15
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp slt i32 %b, %a
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp eq i32 %a, %b
|
||
|
br i1 %cmp1, label %if.then2, label %if.end3
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func16(i32 zeroext %a, i32 zeroext %b) {
|
||
|
; CHECK-LABEL: @func16
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp eq i32 %a, %b
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp ult i32 %a, %b
|
||
|
br i1 %cmp1, label %if.then2, label %if.end3
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func17(i32 zeroext %a, i32 zeroext %b) {
|
||
|
; CHECK-LABEL: @func17
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp ult i32 %a, %b
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp ugt i32 %a, %b
|
||
|
br i1 %cmp1, label %if.then2, label %if.end3
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func18(i32 zeroext %a, i32 zeroext %b) {
|
||
|
; CHECK-LABEL: @func18
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp ult i32 %b, %a
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp eq i32 %a, %b
|
||
|
br i1 %cmp1, label %if.then2, label %if.end3
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func19(i64 %a, i64 %b) {
|
||
|
; CHECK-LABEL: @func19
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp eq i64 %a, %b
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp slt i64 %a, %b
|
||
|
br i1 %cmp1, label %if.then2, label %if.end3
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func20(i64 %a, i64 %b) {
|
||
|
; CHECK-LABEL: @func20
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp slt i64 %a, %b
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp sgt i64 %a, %b
|
||
|
br i1 %cmp1, label %if.then2, label %if.end3
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func21(i64 %a, i64 %b) {
|
||
|
; CHECK-LABEL: @func21
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp slt i64 %b, %a
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp eq i64 %a, %b
|
||
|
br i1 %cmp1, label %if.then2, label %if.end3
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func22(i64 %a, i64 %b) {
|
||
|
; CHECK-LABEL: @func22
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp eq i64 %a, %b
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp ult i64 %a, %b
|
||
|
br i1 %cmp1, label %if.then2, label %if.end3
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func23(i64 %a, i64 %b) {
|
||
|
; CHECK-LABEL: @func23
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp ult i64 %a, %b
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp ugt i64 %a, %b
|
||
|
br i1 %cmp1, label %if.then2, label %if.end3
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func24(i64 %a, i64 %b) {
|
||
|
; CHECK-LABEL: @func24
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp ult i64 %b, %a
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp eq i64 %a, %b
|
||
|
br i1 %cmp1, label %if.then2, label %if.end3
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func25(i64 %a, i64 %b) {
|
||
|
; CHECK-LABEL: @func25
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp slt i64 %b, %a
|
||
|
br i1 %cmp, label %if.then, label %if.else, !prof !1
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end6
|
||
|
|
||
|
if.else:
|
||
|
%cmp2 = icmp eq i64 %a, %b
|
||
|
br i1 %cmp2, label %if.then4, label %if.else5
|
||
|
|
||
|
if.then4:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end6
|
||
|
|
||
|
if.else5:
|
||
|
tail call void @dummy3()
|
||
|
br label %if.end6
|
||
|
|
||
|
if.end6:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
|
||
|
define void @func26(i32 signext %a) {
|
||
|
; CHECK-LABEL: @func26
|
||
|
; CHECK: cmp
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp sgt i32 %a, 0
|
||
|
br i1 %cmp, label %if.then, label %if.else, !prof !2
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end9
|
||
|
|
||
|
if.else:
|
||
|
%cmp2 = icmp eq i32 %a, 0
|
||
|
br i1 %cmp2, label %if.then7, label %if.else8, !prof !2
|
||
|
|
||
|
if.then7:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end9
|
||
|
|
||
|
if.else8:
|
||
|
tail call void @dummy3()
|
||
|
br label %if.end9
|
||
|
|
||
|
if.end9:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
@g1 = external local_unnamed_addr global i32, align 4
|
||
|
@g2 = external local_unnamed_addr global i32, align 4
|
||
|
|
||
|
define void @func27(i32 signext %a) {
|
||
|
; CHECK-LABEL: @func27
|
||
|
; CHECK: cmp
|
||
|
; CHECK: beq
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: bgelr
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp eq i32 %a, 0
|
||
|
br i1 %cmp, label %if.end3.sink.split, label %if.else
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp slt i32 %a, 0
|
||
|
br i1 %cmp1, label %if.end3.sink.split, label %if.end
|
||
|
|
||
|
if.end3.sink.split:
|
||
|
%g2.sink = phi i32* [ @g2, %if.else ], [ @g1, %entry ]
|
||
|
store i32 0, i32* %g2.sink, align 4
|
||
|
br label %if.end
|
||
|
|
||
|
if.end:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
; partially redundant case
|
||
|
define void @func28(i32 signext %a) {
|
||
|
; CHECK-LABEL: @func28
|
||
|
; CHECK: cmplwi [[REG1:[0-9]+]], [[REG2:[0-9]+]]
|
||
|
; CHECK: .[[LABEL2:[A-Z0-9_]+]]:
|
||
|
; CHECK: cmpwi [[REG1]], [[REG2]]
|
||
|
; CHECK: ble 0, .[[LABEL1:[A-Z0-9_]+]]
|
||
|
; CHECK-NOT: cmp
|
||
|
; CHECK: bne 0, .[[LABEL2]]
|
||
|
; CHECK: bl dummy1
|
||
|
; CHECK: b .[[LABEL2]]
|
||
|
; CHECK: .[[LABEL1]]:
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
br label %do.body
|
||
|
|
||
|
do.body:
|
||
|
%a.addr.0 = phi i32 [ %a, %entry ], [ %call, %if.end ]
|
||
|
%cmp = icmp eq i32 %a.addr.0, 0
|
||
|
br i1 %cmp, label %if.then, label %if.end
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1() #2
|
||
|
br label %if.end
|
||
|
|
||
|
if.end:
|
||
|
%call = tail call signext i32 @func(i32 signext %a.addr.0) #2
|
||
|
%cmp1 = icmp sgt i32 %call, 0
|
||
|
br i1 %cmp1, label %do.body, label %do.end
|
||
|
|
||
|
do.end:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
define void @func29(i32 signext %a) {
|
||
|
; We cannot merge two compares due to difference in sign extension behaviors.
|
||
|
; equivalent C code example:
|
||
|
; int a = .. ;
|
||
|
; if (a == -1) dummy1();
|
||
|
; if (a == (uint16_t)-1) dummy2();
|
||
|
|
||
|
; CHECK-LABEL: @func29
|
||
|
; CHECK: cmp
|
||
|
; CHECK: cmp
|
||
|
; CHECK: blr
|
||
|
entry:
|
||
|
%cmp = icmp eq i32 %a, -1
|
||
|
br i1 %cmp, label %if.then, label %if.else
|
||
|
|
||
|
if.then:
|
||
|
tail call void @dummy1()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.else:
|
||
|
%cmp1 = icmp eq i32 %a, 65535
|
||
|
br i1 %cmp1, label %if.then2, label %if.end3
|
||
|
|
||
|
if.then2:
|
||
|
tail call void @dummy2()
|
||
|
br label %if.end3
|
||
|
|
||
|
if.end3:
|
||
|
ret void
|
||
|
}
|
||
|
|
||
|
declare void @dummy1()
|
||
|
declare void @dummy2()
|
||
|
declare void @dummy3()
|
||
|
declare signext i32 @func(i32 signext)
|
||
|
|
||
|
!1 = !{!"branch_weights", i32 2000, i32 1}
|
||
|
!2 = !{!"branch_weights", i32 1, i32 2000}
|