blob: 971c7c79213cc27ebf36d7aa9650aa16f88bce06 [file] [edit]
; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 6
; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx90a < %s | FileCheck %s
define i32 @select.hi32.sgpr.oeq(double inreg %x, double inreg %y, i32 inreg %a, i32 inreg %b) {
; CHECK-LABEL: select.hi32.sgpr.oeq:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: s_bitset0_b32 s17, 31
; CHECK-NEXT: s_andn2_b32 s19, s19, -2.0
; CHECK-NEXT: s_cmp_eq_u32 s17, s19
; CHECK-NEXT: s_cselect_b32 s4, s20, s21
; CHECK-NEXT: v_mov_b32_e32 v0, s4
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x7fffffff00000000 ; cannot be negative
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp oeq double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.sgpr.oeq.multiuse(double inreg %x, double inreg %y, i32 inreg %a, i32 inreg %b, i32 inreg %c, i32 inreg %d) {
; CHECK-LABEL: select.hi32.sgpr.oeq.multiuse:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: s_bitset0_b32 s17, 31
; CHECK-NEXT: s_andn2_b32 s19, s19, -2.0
; CHECK-NEXT: s_cmp_eq_u32 s17, s19
; CHECK-NEXT: s_cselect_b32 s4, s20, s21
; CHECK-NEXT: s_cselect_b32 s5, s22, s23
; CHECK-NEXT: s_add_i32 s4, s4, s5
; CHECK-NEXT: v_mov_b32_e32 v0, s4
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x7fffffff00000000 ; cannot be negative
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp oeq double %x.masked, %y.masked
%ab = select i1 %cmp, i32 %a, i32 %b
%cd = select i1 %cmp, i32 %c, i32 %d
%ret = add i32 %ab, %cd
ret i32 %ret
}
define i32 @select.hi32.sgpr.oeq.bad.zero(double inreg %x, double inreg %y, i32 inreg %a, i32 inreg %b) {
; CHECK-LABEL: select.hi32.sgpr.oeq.bad.zero:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: s_bitset0_b32 s19, 30
; CHECK-NEXT: s_mov_b32 s16, 0
; CHECK-NEXT: v_mov_b32_e32 v0, 0
; CHECK-NEXT: v_mov_b32_e32 v1, s19
; CHECK-NEXT: v_cmp_eq_f64_e32 vcc, s[16:17], v[0:1]
; CHECK-NEXT: s_and_b64 s[4:5], vcc, exec
; CHECK-NEXT: s_cselect_b32 s4, s20, s21
; CHECK-NEXT: v_mov_b32_e32 v0, s4
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0xffffffff00000000
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0xbfffffff00000000 ; cannot be NaN
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp oeq double %x.masked, %y.masked ; may compare +0 and -0
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.sgpr.oeq.bad.nan(double inreg %x, double inreg %y, i32 inreg %a, i32 inreg %b) {
; CHECK-LABEL: select.hi32.sgpr.oeq.bad.nan:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: s_mov_b32 s16, 0
; CHECK-NEXT: v_mov_b32_e32 v0, 0
; CHECK-NEXT: v_mov_b32_e32 v1, s19
; CHECK-NEXT: v_cmp_eq_f64_e32 vcc, s[16:17], v[0:1]
; CHECK-NEXT: s_and_b64 s[4:5], vcc, exec
; CHECK-NEXT: s_cselect_b32 s4, s20, s21
; CHECK-NEXT: v_mov_b32_e32 v0, s4
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0xffffffff00000000
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0xffffffff00000000
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp oeq double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.sgpr.ueq(double inreg %x, double inreg %y, i32 inreg %a, i32 inreg %b) {
; CHECK-LABEL: select.hi32.sgpr.ueq:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: s_andn2_b32 s17, s17, -2.0
; CHECK-NEXT: s_andn2_b32 s19, s19, -2.0
; CHECK-NEXT: s_cmp_eq_u32 s17, s19
; CHECK-NEXT: s_cselect_b32 s4, s20, s21
; CHECK-NEXT: v_mov_b32_e32 v0, s4
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp ueq double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.sgpr.ueq.bad.zero(double inreg %x, double inreg %y, i32 inreg %a, i32 inreg %b) {
; CHECK-LABEL: select.hi32.sgpr.ueq.bad.zero:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: s_bitset0_b32 s19, 30
; CHECK-NEXT: s_and_b32 s5, s17, 0xbfffffff
; CHECK-NEXT: s_mov_b32 s4, 0
; CHECK-NEXT: v_mov_b32_e32 v0, 0
; CHECK-NEXT: v_mov_b32_e32 v1, s19
; CHECK-NEXT: v_cmp_eq_f64_e32 vcc, s[4:5], v[0:1]
; CHECK-NEXT: s_and_b64 s[4:5], vcc, exec
; CHECK-NEXT: s_cselect_b32 s4, s20, s21
; CHECK-NEXT: v_mov_b32_e32 v0, s4
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0xbfffffff00000000 ; cannot be NaN
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0xbfffffff00000000 ; cannot be NaN
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp ueq double %x.masked, %y.masked ; may compare +0 and -0
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.sgpr.ueq.bad.nan(double inreg %x, double inreg %y, i32 inreg %a, i32 inreg %b) {
; CHECK-LABEL: select.hi32.sgpr.ueq.bad.nan:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: s_and_b32 s5, s17, 0xbfffffff
; CHECK-NEXT: s_mov_b32 s4, 0
; CHECK-NEXT: v_mov_b32_e32 v0, 0
; CHECK-NEXT: v_mov_b32_e32 v1, s19
; CHECK-NEXT: v_cmp_nlg_f64_e32 vcc, s[4:5], v[0:1]
; CHECK-NEXT: s_and_b64 s[4:5], vcc, exec
; CHECK-NEXT: s_cselect_b32 s4, s20, s21
; CHECK-NEXT: v_mov_b32_e32 v0, s4
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0xbfffffff00000000 ; cannot be NaN
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0xffffffff00000000
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp ueq double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.sgpr.olt.0(double inreg %x, double inreg %y, i32 inreg %a, i32 inreg %b) {
; CHECK-LABEL: select.hi32.sgpr.olt.0:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: s_bitset0_b32 s17, 31
; CHECK-NEXT: s_andn2_b32 s19, s19, -2.0
; CHECK-NEXT: s_cmp_lt_i32 s17, s19
; CHECK-NEXT: s_cselect_b32 s4, s20, s21
; CHECK-NEXT: v_mov_b32_e32 v0, s4
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.abs = call double @llvm.fabs(double %x) ; cannot be negative
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp olt double %x.abs, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.sgpr.olt.1(double inreg %x, double inreg %y, i32 inreg %a, i32 inreg %b) {
; CHECK-LABEL: select.hi32.sgpr.olt.1:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: s_bitset0_b32 s17, 31
; CHECK-NEXT: s_andn2_b32 s19, s19, -2.0
; CHECK-NEXT: s_cmp_le_i32 s17, s19
; CHECK-NEXT: s_cselect_b32 s4, s20, s21
; CHECK-NEXT: v_mov_b32_e32 v0, s4
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x7fffffff00000000 ; cannot be negative
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%y.i64.bump = or i64 %y.i64.masked, 1
%y.masked = bitcast i64 %y.i64.bump to double
%cmp = fcmp olt double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.sgpr.olt.bad.neg(double inreg %x, double inreg %y, i32 inreg %a, i32 inreg %b) {
; CHECK-LABEL: select.hi32.sgpr.olt.bad.neg:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: s_and_b32 s4, s19, 0x8fffffff
; CHECK-NEXT: v_mov_b32_e32 v0, 0
; CHECK-NEXT: v_mov_b32_e32 v1, s4
; CHECK-NEXT: v_cmp_lt_f64_e64 s[4:5], |s[16:17]|, v[0:1]
; CHECK-NEXT: s_and_b64 s[4:5], s[4:5], exec
; CHECK-NEXT: s_cselect_b32 s4, s20, s21
; CHECK-NEXT: v_mov_b32_e32 v0, s4
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.abs = call double @llvm.fabs(double %x) ; cannot be negative
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x8fffffff00000000 ; cannot be NaN, may be negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp olt double %x.abs, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.sgpr.olt.bad.nan(double inreg %x, double inreg %y, i32 inreg %a, i32 inreg %b) {
; CHECK-LABEL: select.hi32.sgpr.olt.bad.nan:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_mov_b32_e32 v0, s18
; CHECK-NEXT: v_mov_b32_e32 v1, s19
; CHECK-NEXT: v_cmp_lt_f64_e64 s[4:5], |s[16:17]|, |v[0:1]|
; CHECK-NEXT: s_and_b64 s[4:5], s[4:5], exec
; CHECK-NEXT: s_cselect_b32 s4, s20, s21
; CHECK-NEXT: v_mov_b32_e32 v0, s4
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.abs = call double @llvm.fabs(double %x) ; cannot be negative
%y.abs = call double @llvm.fabs(double %y) ; may be NaN
%cmp = fcmp olt double %x.abs, %y.abs
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.sgpr.ult.0(double inreg %x, double inreg %y, i32 inreg %a, i32 inreg %b) {
; CHECK-LABEL: select.hi32.sgpr.ult.0:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: s_andn2_b32 s17, s17, -2.0
; CHECK-NEXT: s_andn2_b32 s19, s19, -2.0
; CHECK-NEXT: s_cmp_lt_i32 s17, s19
; CHECK-NEXT: s_cselect_b32 s4, s20, s21
; CHECK-NEXT: v_mov_b32_e32 v0, s4
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x3fffffffffffffff ; cannot be NaN or negative
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp ult double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.sgpr.ult.1(double inreg %x, double inreg %y, i32 inreg %a, i32 inreg %b) {
; CHECK-LABEL: select.hi32.sgpr.ult.1:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: s_andn2_b32 s17, s17, -2.0
; CHECK-NEXT: s_andn2_b32 s19, s19, -2.0
; CHECK-NEXT: s_cmp_le_i32 s17, s19
; CHECK-NEXT: s_cselect_b32 s4, s20, s21
; CHECK-NEXT: v_mov_b32_e32 v0, s4
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%y.i64.bump = or i64 %y.i64.masked, 1
%y.masked = bitcast i64 %y.i64.bump to double
%cmp = fcmp ult double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.sgpr.ult.bad.0(double inreg %x, double inreg %y, i32 inreg %a, i32 inreg %b) {
; CHECK-LABEL: select.hi32.sgpr.ult.bad.0:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: s_andn2_b32 s19, s19, -2.0
; CHECK-NEXT: v_mov_b32_e32 v0, 0
; CHECK-NEXT: v_mov_b32_e32 v1, s19
; CHECK-NEXT: v_cmp_nge_f64_e64 s[4:5], |s[16:17]|, v[0:1]
; CHECK-NEXT: s_and_b64 s[4:5], s[4:5], exec
; CHECK-NEXT: s_cselect_b32 s4, s20, s21
; CHECK-NEXT: v_mov_b32_e32 v0, s4
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.abs = call double @llvm.fabs(double %x) ; cannot be negative
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp ult double %x.abs, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.sgpr.ult.bad.1(double inreg %x, double inreg %y, i32 inreg %a, i32 inreg %b) {
; CHECK-LABEL: select.hi32.sgpr.ult.bad.1:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: s_bitset0_b32 s19, 31
; CHECK-NEXT: s_andn2_b32 s17, s17, -2.0
; CHECK-NEXT: v_mov_b32_e32 v0, 0
; CHECK-NEXT: v_mov_b32_e32 v1, s19
; CHECK-NEXT: v_cmp_nge_f64_e32 vcc, s[16:17], v[0:1]
; CHECK-NEXT: s_and_b64 s[4:5], vcc, exec
; CHECK-NEXT: s_cselect_b32 s4, s20, s21
; CHECK-NEXT: v_mov_b32_e32 v0, s4
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x3fffffffffffffff ; cannot be NaN or negative
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x7fffffff00000000 ; cannot be negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp ult double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.sgpr.ole.0(double inreg %x, double inreg %y, i32 inreg %a, i32 inreg %b) {
; CHECK-LABEL: select.hi32.sgpr.ole.0:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: s_andn2_b32 s17, s17, -2.0
; CHECK-NEXT: s_andn2_b32 s19, s19, -2.0
; CHECK-NEXT: s_cmp_le_i32 s17, s19
; CHECK-NEXT: s_cselect_b32 s4, s20, s21
; CHECK-NEXT: v_mov_b32_e32 v0, s4
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x3fffffffffffffff ; cannot be NaN or negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp ole double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.sgpr.ole.1(double inreg %x, double inreg %y, i32 inreg %a, i32 inreg %b) {
; CHECK-LABEL: select.hi32.sgpr.ole.1:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: s_andn2_b32 s17, s17, -2.0
; CHECK-NEXT: s_andn2_b32 s19, s19, -2.0
; CHECK-NEXT: s_cmp_lt_i32 s17, s19
; CHECK-NEXT: s_cselect_b32 s4, s20, s21
; CHECK-NEXT: v_mov_b32_e32 v0, s4
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%x.i64.bump = or i64 %x.i64.masked, 1
%x.masked = bitcast i64 %x.i64.bump to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp ole double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.sgpr.ole.bad.0(double inreg %x, double inreg %y, i32 inreg %a, i32 inreg %b) {
; CHECK-LABEL: select.hi32.sgpr.ole.bad.0:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: s_andn2_b32 s19, s19, -2.0
; CHECK-NEXT: s_and_b32 s5, s17, 0x7fffffff
; CHECK-NEXT: s_mov_b32 s4, 0
; CHECK-NEXT: v_mov_b32_e32 v0, s18
; CHECK-NEXT: v_mov_b32_e32 v1, s19
; CHECK-NEXT: v_cmp_le_f64_e32 vcc, s[4:5], v[0:1]
; CHECK-NEXT: s_and_b64 s[4:5], vcc, exec
; CHECK-NEXT: s_cselect_b32 s4, s20, s21
; CHECK-NEXT: v_mov_b32_e32 v0, s4
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x7fffffff00000000 ; cannot be negative
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x3fffffffffffffff ; cannot be NaN or negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp ole double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.sgpr.ole.bad.1(double inreg %x, double inreg %y, i32 inreg %a, i32 inreg %b) {
; CHECK-LABEL: select.hi32.sgpr.ole.bad.1:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_mov_b32_e32 v0, s18
; CHECK-NEXT: v_mov_b32_e32 v1, s19
; CHECK-NEXT: s_and_b32 s5, s17, 0x3fffffff
; CHECK-NEXT: s_mov_b32 s4, 0
; CHECK-NEXT: v_cmp_le_f64_e64 s[4:5], s[4:5], |v[0:1]|
; CHECK-NEXT: s_and_b64 s[4:5], s[4:5], exec
; CHECK-NEXT: s_cselect_b32 s4, s20, s21
; CHECK-NEXT: v_mov_b32_e32 v0, s4
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%x.masked = bitcast i64 %x.i64.masked to double
%y.abs = call double @llvm.fabs(double %y) ; cannot be negative
%cmp = fcmp ole double %x.masked, %y.abs
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.sgpr.ule.0(double inreg %x, double inreg %y, i32 inreg %a, i32 inreg %b) {
; CHECK-LABEL: select.hi32.sgpr.ule.0:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: s_andn2_b32 s17, s17, -2.0
; CHECK-NEXT: s_bitset0_b32 s19, 31
; CHECK-NEXT: s_cmp_le_i32 s17, s19
; CHECK-NEXT: s_cselect_b32 s4, s20, s21
; CHECK-NEXT: v_mov_b32_e32 v0, s4
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%x.masked = bitcast i64 %x.i64.masked to double
%y.abs = call double @llvm.fabs(double %y) ; cannot be negative
%cmp = fcmp ule double %x.masked, %y.abs
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.sgpr.ule.1(double inreg %x, double inreg %y, i32 inreg %a, i32 inreg %b) {
; CHECK-LABEL: select.hi32.sgpr.ule.1:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: s_andn2_b32 s17, s17, -2.0
; CHECK-NEXT: s_bitset0_b32 s19, 31
; CHECK-NEXT: s_cmp_lt_i32 s17, s19
; CHECK-NEXT: s_cselect_b32 s4, s20, s21
; CHECK-NEXT: v_mov_b32_e32 v0, s4
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%x.i64.bump = or i64 %x.i64.masked, 1
%x.masked = bitcast i64 %x.i64.bump to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x7fffffff00000000 ; cannot negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp ule double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.sgpr.ule.bad(double inreg %x, double inreg %y, i32 inreg %a, i32 inreg %b) {
; CHECK-LABEL: select.hi32.sgpr.ule.bad:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_mov_b32_e32 v0, s18
; CHECK-NEXT: v_mov_b32_e32 v1, s19
; CHECK-NEXT: v_cmp_ngt_f64_e64 s[4:5], |s[16:17]|, |v[0:1]|
; CHECK-NEXT: s_and_b64 s[4:5], s[4:5], exec
; CHECK-NEXT: s_cselect_b32 s4, s20, s21
; CHECK-NEXT: v_mov_b32_e32 v0, s4
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.abs = call double @llvm.fabs(double %x) ; cannot be negative
%y.abs = call double @llvm.fabs(double %y) ; cannot be negative
%cmp = fcmp ule double %x.abs, %y.abs
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.vgpr.oeq(double %x, double %y, i32 %a, i32 %b) {
; CHECK-LABEL: select.hi32.vgpr.oeq:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_and_b32_e32 v0, 0x7fffffff, v1
; CHECK-NEXT: v_and_b32_e32 v1, 0x3fffffff, v3
; CHECK-NEXT: v_cmp_eq_u32_e32 vcc, v0, v1
; CHECK-NEXT: v_cndmask_b32_e32 v0, v5, v4, vcc
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x7fffffff00000000 ; cannot be negative
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp oeq double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.vgpr.oeq.multiuse(double %x, double %y, i32 %a, i32 %b, i32 %c, i32 %d) {
; CHECK-LABEL: select.hi32.vgpr.oeq.multiuse:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_and_b32_e32 v0, 0x7fffffff, v1
; CHECK-NEXT: v_and_b32_e32 v1, 0x3fffffff, v3
; CHECK-NEXT: v_cmp_eq_u32_e32 vcc, v0, v1
; CHECK-NEXT: v_cndmask_b32_e32 v0, v5, v4, vcc
; CHECK-NEXT: v_cndmask_b32_e32 v1, v7, v6, vcc
; CHECK-NEXT: v_add_u32_e32 v0, v0, v1
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x7fffffff00000000 ; cannot be negative
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp oeq double %x.masked, %y.masked
%ab = select i1 %cmp, i32 %a, i32 %b
%cd = select i1 %cmp, i32 %c, i32 %d
%ret = add i32 %ab, %cd
ret i32 %ret
}
define i32 @select.hi32.vgpr.oeq.bad.zero(double %x, double %y, i32 %a, i32 %b) {
; CHECK-LABEL: select.hi32.vgpr.oeq.bad.zero:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_mov_b32_e32 v0, 0
; CHECK-NEXT: v_and_b32_e32 v3, 0xbfffffff, v3
; CHECK-NEXT: v_mov_b32_e32 v2, v0
; CHECK-NEXT: v_cmp_eq_f64_e32 vcc, v[0:1], v[2:3]
; CHECK-NEXT: v_cndmask_b32_e32 v0, v5, v4, vcc
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0xffffffff00000000
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0xbfffffff00000000 ; cannot be NaN
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp oeq double %x.masked, %y.masked ; may compare +0 and -0
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.vgpr.oeq.bad.nan(double %x, double %y, i32 %a, i32 %b) {
; CHECK-LABEL: select.hi32.vgpr.oeq.bad.nan:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_mov_b32_e32 v0, 0
; CHECK-NEXT: v_mov_b32_e32 v2, v0
; CHECK-NEXT: v_cmp_eq_f64_e32 vcc, v[0:1], v[2:3]
; CHECK-NEXT: v_cndmask_b32_e32 v0, v5, v4, vcc
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0xffffffff00000000
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0xffffffff00000000
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp oeq double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.vgpr.ueq(double %x, double %y, i32 %a, i32 %b) {
; CHECK-LABEL: select.hi32.vgpr.ueq:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_and_b32_e32 v0, 0x3fffffff, v1
; CHECK-NEXT: v_and_b32_e32 v1, 0x3fffffff, v3
; CHECK-NEXT: v_cmp_eq_u32_e32 vcc, v0, v1
; CHECK-NEXT: v_cndmask_b32_e32 v0, v5, v4, vcc
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp ueq double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.vgpr.ueq.bad.zero(double %x, double %y, i32 %a, i32 %b) {
; CHECK-LABEL: select.hi32.vgpr.ueq.bad.zero:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_mov_b32_e32 v0, 0
; CHECK-NEXT: v_and_b32_e32 v1, 0xbfffffff, v1
; CHECK-NEXT: v_and_b32_e32 v3, 0xbfffffff, v3
; CHECK-NEXT: v_mov_b32_e32 v2, v0
; CHECK-NEXT: v_cmp_eq_f64_e32 vcc, v[0:1], v[2:3]
; CHECK-NEXT: v_cndmask_b32_e32 v0, v5, v4, vcc
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0xbfffffff00000000 ; cannot be NaN
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0xbfffffff00000000 ; cannot be NaN
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp ueq double %x.masked, %y.masked ; may compare +0 and -0
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.vgpr.ueq.bad.nan(double %x, double %y, i32 %a, i32 %b) {
; CHECK-LABEL: select.hi32.vgpr.ueq.bad.nan:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_mov_b32_e32 v0, 0
; CHECK-NEXT: v_and_b32_e32 v1, 0xbfffffff, v1
; CHECK-NEXT: v_mov_b32_e32 v2, v0
; CHECK-NEXT: v_cmp_nlg_f64_e32 vcc, v[0:1], v[2:3]
; CHECK-NEXT: v_cndmask_b32_e32 v0, v5, v4, vcc
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0xbfffffff00000000 ; cannot be NaN
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0xffffffff00000000
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp ueq double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.vgpr.olt.0(double %x, double %y, i32 %a, i32 %b) {
; CHECK-LABEL: select.hi32.vgpr.olt.0:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_and_b32_e32 v0, 0x7fffffff, v1
; CHECK-NEXT: v_and_b32_e32 v1, 0x3fffffff, v3
; CHECK-NEXT: v_cmp_lt_i32_e32 vcc, v0, v1
; CHECK-NEXT: v_cndmask_b32_e32 v0, v5, v4, vcc
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.abs = call double @llvm.fabs(double %x) ; cannot be negative
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp olt double %x.abs, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.vgpr.olt.1(double %x, double %y, i32 %a, i32 %b) {
; CHECK-LABEL: select.hi32.vgpr.olt.1:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_and_b32_e32 v0, 0x7fffffff, v1
; CHECK-NEXT: v_and_b32_e32 v1, 0x3fffffff, v3
; CHECK-NEXT: v_cmp_le_i32_e32 vcc, v0, v1
; CHECK-NEXT: v_cndmask_b32_e32 v0, v5, v4, vcc
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x7fffffff00000000 ; cannot be negative
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%y.i64.bump = or i64 %y.i64.masked, 1
%y.masked = bitcast i64 %y.i64.bump to double
%cmp = fcmp olt double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.vgpr.olt.bad.neg(double %x, double %y, i32 %a, i32 %b) {
; CHECK-LABEL: select.hi32.vgpr.olt.bad.neg:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_and_b32_e32 v3, 0x8fffffff, v3
; CHECK-NEXT: v_mov_b32_e32 v2, 0
; CHECK-NEXT: v_cmp_lt_f64_e64 vcc, |v[0:1]|, v[2:3]
; CHECK-NEXT: v_cndmask_b32_e32 v0, v5, v4, vcc
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.abs = call double @llvm.fabs(double %x) ; cannot be negative
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x8fffffff00000000 ; cannot be NaN, may be negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp olt double %x.abs, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.vgpr.olt.bad.nan(double %x, double %y, i32 %a, i32 %b) {
; CHECK-LABEL: select.hi32.vgpr.olt.bad.nan:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_cmp_lt_f64_e64 vcc, |v[0:1]|, |v[2:3]|
; CHECK-NEXT: v_cndmask_b32_e32 v0, v5, v4, vcc
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.abs = call double @llvm.fabs(double %x) ; cannot be negative
%y.abs = call double @llvm.fabs(double %y) ; may be NaN
%cmp = fcmp olt double %x.abs, %y.abs
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.vgpr.ult.0(double %x, double %y, i32 %a, i32 %b) {
; CHECK-LABEL: select.hi32.vgpr.ult.0:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_and_b32_e32 v0, 0x3fffffff, v1
; CHECK-NEXT: v_and_b32_e32 v1, 0x3fffffff, v3
; CHECK-NEXT: v_cmp_lt_i32_e32 vcc, v0, v1
; CHECK-NEXT: v_cndmask_b32_e32 v0, v5, v4, vcc
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x3fffffffffffffff ; cannot be NaN or negative
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp ult double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.vgpr.ult.1(double %x, double %y, i32 %a, i32 %b) {
; CHECK-LABEL: select.hi32.vgpr.ult.1:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_and_b32_e32 v0, 0x3fffffff, v1
; CHECK-NEXT: v_and_b32_e32 v1, 0x3fffffff, v3
; CHECK-NEXT: v_cmp_le_i32_e32 vcc, v0, v1
; CHECK-NEXT: v_cndmask_b32_e32 v0, v5, v4, vcc
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%y.i64.bump = or i64 %y.i64.masked, 1
%y.masked = bitcast i64 %y.i64.bump to double
%cmp = fcmp ult double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.vgpr.ult.bad.0(double %x, double %y, i32 %a, i32 %b) {
; CHECK-LABEL: select.hi32.vgpr.ult.bad.0:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_and_b32_e32 v3, 0x3fffffff, v3
; CHECK-NEXT: v_mov_b32_e32 v2, 0
; CHECK-NEXT: v_cmp_nge_f64_e64 vcc, |v[0:1]|, v[2:3]
; CHECK-NEXT: v_cndmask_b32_e32 v0, v5, v4, vcc
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.abs = call double @llvm.fabs(double %x) ; cannot be negative
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp ult double %x.abs, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.vgpr.ult.bad.1(double %x, double %y, i32 %a, i32 %b) {
; CHECK-LABEL: select.hi32.vgpr.ult.bad.1:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_and_b32_e32 v1, 0x3fffffff, v1
; CHECK-NEXT: v_and_b32_e32 v3, 0x7fffffff, v3
; CHECK-NEXT: v_mov_b32_e32 v2, 0
; CHECK-NEXT: v_cmp_nge_f64_e32 vcc, v[0:1], v[2:3]
; CHECK-NEXT: v_cndmask_b32_e32 v0, v5, v4, vcc
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x3fffffffffffffff ; cannot be NaN or negative
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x7fffffff00000000 ; cannot be negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp ult double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.vgpr.ole.0(double %x, double %y, i32 %a, i32 %b) {
; CHECK-LABEL: select.hi32.vgpr.ole.0:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_and_b32_e32 v0, 0x3fffffff, v1
; CHECK-NEXT: v_and_b32_e32 v1, 0x3fffffff, v3
; CHECK-NEXT: v_cmp_le_i32_e32 vcc, v0, v1
; CHECK-NEXT: v_cndmask_b32_e32 v0, v5, v4, vcc
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x3fffffffffffffff ; cannot be NaN or negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp ole double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.vgpr.ole.1(double %x, double %y, i32 %a, i32 %b) {
; CHECK-LABEL: select.hi32.vgpr.ole.1:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_and_b32_e32 v0, 0x3fffffff, v1
; CHECK-NEXT: v_and_b32_e32 v1, 0x3fffffff, v3
; CHECK-NEXT: v_cmp_lt_i32_e32 vcc, v0, v1
; CHECK-NEXT: v_cndmask_b32_e32 v0, v5, v4, vcc
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%x.i64.bump = or i64 %x.i64.masked, 1
%x.masked = bitcast i64 %x.i64.bump to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp ole double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.vgpr.ole.bad.0(double %x, double %y, i32 %a, i32 %b) {
; CHECK-LABEL: select.hi32.vgpr.ole.bad.0:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_and_b32_e32 v1, 0x7fffffff, v1
; CHECK-NEXT: v_mov_b32_e32 v0, 0
; CHECK-NEXT: v_and_b32_e32 v3, 0x3fffffff, v3
; CHECK-NEXT: v_cmp_le_f64_e32 vcc, v[0:1], v[2:3]
; CHECK-NEXT: v_cndmask_b32_e32 v0, v5, v4, vcc
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x7fffffff00000000 ; cannot be negative
%x.masked = bitcast i64 %x.i64.masked to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x3fffffffffffffff ; cannot be NaN or negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp ole double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.vgpr.ole.bad.1(double %x, double %y, i32 %a, i32 %b) {
; CHECK-LABEL: select.hi32.vgpr.ole.bad.1:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_and_b32_e32 v1, 0x3fffffff, v1
; CHECK-NEXT: v_mov_b32_e32 v0, 0
; CHECK-NEXT: v_cmp_le_f64_e64 vcc, v[0:1], |v[2:3]|
; CHECK-NEXT: v_cndmask_b32_e32 v0, v5, v4, vcc
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%x.masked = bitcast i64 %x.i64.masked to double
%y.abs = call double @llvm.fabs(double %y) ; cannot be negative
%cmp = fcmp ole double %x.masked, %y.abs
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.vgpr.ule.0(double %x, double %y, i32 %a, i32 %b) {
; CHECK-LABEL: select.hi32.vgpr.ule.0:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_and_b32_e32 v0, 0x3fffffff, v1
; CHECK-NEXT: v_and_b32_e32 v1, 0x7fffffff, v3
; CHECK-NEXT: v_cmp_le_i32_e32 vcc, v0, v1
; CHECK-NEXT: v_cndmask_b32_e32 v0, v5, v4, vcc
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%x.masked = bitcast i64 %x.i64.masked to double
%y.abs = call double @llvm.fabs(double %y) ; cannot be negative
%cmp = fcmp ule double %x.masked, %y.abs
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.vgpr.ule.1(double %x, double %y, i32 %a, i32 %b) {
; CHECK-LABEL: select.hi32.vgpr.ule.1:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_and_b32_e32 v0, 0x3fffffff, v1
; CHECK-NEXT: v_and_b32_e32 v1, 0x7fffffff, v3
; CHECK-NEXT: v_cmp_lt_i32_e32 vcc, v0, v1
; CHECK-NEXT: v_cndmask_b32_e32 v0, v5, v4, vcc
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.i64 = bitcast double %x to i64
%x.i64.masked = and i64 %x.i64, u0x3fffffff00000000 ; cannot be NaN or negative
%x.i64.bump = or i64 %x.i64.masked, 1
%x.masked = bitcast i64 %x.i64.bump to double
%y.i64 = bitcast double %y to i64
%y.i64.masked = and i64 %y.i64, u0x7fffffff00000000 ; cannot negative
%y.masked = bitcast i64 %y.i64.masked to double
%cmp = fcmp ule double %x.masked, %y.masked
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}
define i32 @select.hi32.vgpr.ule.bad(double %x, double %y, i32 %a, i32 %b) {
; CHECK-LABEL: select.hi32.vgpr.ule.bad:
; CHECK: ; %bb.0:
; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
; CHECK-NEXT: v_cmp_ngt_f64_e64 vcc, |v[0:1]|, |v[2:3]|
; CHECK-NEXT: v_cndmask_b32_e32 v0, v5, v4, vcc
; CHECK-NEXT: s_setpc_b64 s[30:31]
%x.abs = call double @llvm.fabs(double %x) ; cannot be negative
%y.abs = call double @llvm.fabs(double %y) ; cannot be negative
%cmp = fcmp ule double %x.abs, %y.abs
%ret = select i1 %cmp, i32 %a, i32 %b
ret i32 %ret
}