| ; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py | |
| ; Test intrinsic 'is_fpclass'. | |
| ; | |
| ; RUN: llc < %s -mtriple=s390x-linux-gnu | FileCheck %s | |
| declare i1 @llvm.is.fpclass.f16(half, i32) | |
| declare i1 @llvm.is.fpclass.f32(float, i32) | |
| declare i1 @llvm.is.fpclass.f64(double, i32) | |
| declare i1 @llvm.is.fpclass.f128(fp128, i32) | |
| define i1 @isnan_h(half %x) { | |
| ; CHECK-LABEL: isnan_h: | |
| ; CHECK: # %bb.0: | |
| ; CHECK-NEXT: # kill: def $f0h killed $f0h def $f0d | |
| ; CHECK-NEXT: lgdr %r0, %f0 | |
| ; CHECK-NEXT: risbg %r0, %r0, 49, 191, 16 | |
| ; CHECK-NEXT: chi %r0, 31744 | |
| ; CHECK-NEXT: ipm %r0 | |
| ; CHECK-NEXT: risbg %r2, %r0, 63, 191, 35 | |
| ; CHECK-NEXT: # kill: def $r2l killed $r2l killed $r2d | |
| ; CHECK-NEXT: br %r14 | |
| %1 = call i1 @llvm.is.fpclass.f16(half %x, i32 3) ; nan | |
| ret i1 %1 | |
| } | |
| define i1 @isnan_f(float %x) { | |
| ; CHECK-LABEL: isnan_f: | |
| ; CHECK: # %bb.0: | |
| ; CHECK-NEXT: tceb %f0, 15 | |
| ; CHECK-NEXT: ipm %r2 | |
| ; CHECK-NEXT: srl %r2, 28 | |
| ; CHECK-NEXT: br %r14 | |
| %1 = call i1 @llvm.is.fpclass.f32(float %x, i32 3) ; nan | |
| ret i1 %1 | |
| } | |
| define i1 @isnan_d(double %x) { | |
| ; CHECK-LABEL: isnan_d: | |
| ; CHECK: # %bb.0: | |
| ; CHECK-NEXT: tcdb %f0, 15 | |
| ; CHECK-NEXT: ipm %r2 | |
| ; CHECK-NEXT: srl %r2, 28 | |
| ; CHECK-NEXT: br %r14 | |
| %1 = call i1 @llvm.is.fpclass.f64(double %x, i32 3) ; nan | |
| ret i1 %1 | |
| } | |
| define i1 @isnan_x(fp128 %x) { | |
| ; CHECK-LABEL: isnan_x: | |
| ; CHECK: # %bb.0: | |
| ; CHECK-NEXT: ld %f0, 0(%r2) | |
| ; CHECK-NEXT: ld %f2, 8(%r2) | |
| ; CHECK-NEXT: tcxb %f0, 15 | |
| ; CHECK-NEXT: ipm %r2 | |
| ; CHECK-NEXT: srl %r2, 28 | |
| ; CHECK-NEXT: br %r14 | |
| %1 = call i1 @llvm.is.fpclass.f128(fp128 %x, i32 3) ; nan | |
| ret i1 %1 | |
| } | |
| define i1 @isqnan_f(float %x) { | |
| ; CHECK-LABEL: isqnan_f: | |
| ; CHECK: # %bb.0: | |
| ; CHECK-NEXT: tceb %f0, 12 | |
| ; CHECK-NEXT: ipm %r2 | |
| ; CHECK-NEXT: srl %r2, 28 | |
| ; CHECK-NEXT: br %r14 | |
| %1 = call i1 @llvm.is.fpclass.f32(float %x, i32 2) ; qnan | |
| ret i1 %1 | |
| } | |
| define i1 @issnan_f(float %x) { | |
| ; CHECK-LABEL: issnan_f: | |
| ; CHECK: # %bb.0: | |
| ; CHECK-NEXT: tceb %f0, 3 | |
| ; CHECK-NEXT: ipm %r2 | |
| ; CHECK-NEXT: srl %r2, 28 | |
| ; CHECK-NEXT: br %r14 | |
| %1 = call i1 @llvm.is.fpclass.f32(float %x, i32 1) ; snan | |
| ret i1 %1 | |
| } | |
| define i1 @isinf_f(float %x) { | |
| ; CHECK-LABEL: isinf_f: | |
| ; CHECK: # %bb.0: | |
| ; CHECK-NEXT: tceb %f0, 48 | |
| ; CHECK-NEXT: ipm %r2 | |
| ; CHECK-NEXT: srl %r2, 28 | |
| ; CHECK-NEXT: br %r14 | |
| %1 = call i1 @llvm.is.fpclass.f32(float %x, i32 516) ; 0x204 = "inf" | |
| ret i1 %1 | |
| } | |
| define i1 @isposinf_f(float %x) { | |
| ; CHECK-LABEL: isposinf_f: | |
| ; CHECK: # %bb.0: | |
| ; CHECK-NEXT: tceb %f0, 32 | |
| ; CHECK-NEXT: ipm %r2 | |
| ; CHECK-NEXT: srl %r2, 28 | |
| ; CHECK-NEXT: br %r14 | |
| %1 = call i1 @llvm.is.fpclass.f32(float %x, i32 512) ; 0x200 = "+inf" | |
| ret i1 %1 | |
| } | |
| define i1 @isneginf_f(float %x) { | |
| ; CHECK-LABEL: isneginf_f: | |
| ; CHECK: # %bb.0: | |
| ; CHECK-NEXT: tceb %f0, 16 | |
| ; CHECK-NEXT: ipm %r2 | |
| ; CHECK-NEXT: srl %r2, 28 | |
| ; CHECK-NEXT: br %r14 | |
| %1 = call i1 @llvm.is.fpclass.f32(float %x, i32 4) ; "-inf" | |
| ret i1 %1 | |
| } | |
| define i1 @isfinite_f(float %x) { | |
| ; CHECK-LABEL: isfinite_f: | |
| ; CHECK: # %bb.0: | |
| ; CHECK-NEXT: tceb %f0, 4032 | |
| ; CHECK-NEXT: ipm %r2 | |
| ; CHECK-NEXT: srl %r2, 28 | |
| ; CHECK-NEXT: br %r14 | |
| %1 = call i1 @llvm.is.fpclass.f32(float %x, i32 504) ; 0x1f8 = "finite" | |
| ret i1 %1 | |
| } | |
| define i1 @isposfinite_f(float %x) { | |
| ; CHECK-LABEL: isposfinite_f: | |
| ; CHECK: # %bb.0: | |
| ; CHECK-NEXT: tceb %f0, 2688 | |
| ; CHECK-NEXT: ipm %r2 | |
| ; CHECK-NEXT: srl %r2, 28 | |
| ; CHECK-NEXT: br %r14 | |
| %1 = call i1 @llvm.is.fpclass.f32(float %x, i32 448) ; 0x1c0 = "+finite" | |
| ret i1 %1 | |
| } | |
| define i1 @isnegfinite_f(float %x) { | |
| ; CHECK-LABEL: isnegfinite_f: | |
| ; CHECK: # %bb.0: | |
| ; CHECK-NEXT: tceb %f0, 1344 | |
| ; CHECK-NEXT: ipm %r2 | |
| ; CHECK-NEXT: srl %r2, 28 | |
| ; CHECK-NEXT: br %r14 | |
| %1 = call i1 @llvm.is.fpclass.f32(float %x, i32 56) ; 0x38 = "-finite" | |
| ret i1 %1 | |
| } | |
| define i1 @isnotfinite_f(float %x) { | |
| ; CHECK-LABEL: isnotfinite_f: | |
| ; CHECK: # %bb.0: | |
| ; CHECK-NEXT: tceb %f0, 63 | |
| ; CHECK-NEXT: ipm %r2 | |
| ; CHECK-NEXT: srl %r2, 28 | |
| ; CHECK-NEXT: br %r14 | |
| %1 = call i1 @llvm.is.fpclass.f32(float %x, i32 519) ; ox207 = "inf|nan" | |
| ret i1 %1 | |
| } | |
| define i1 @isnormal_h(half %x) { | |
| ; CHECK-LABEL: isnormal_h: | |
| ; CHECK: # %bb.0: | |
| ; CHECK-NEXT: # kill: def $f0h killed $f0h def $f0d | |
| ; CHECK-NEXT: lgdr %r0, %f0 | |
| ; CHECK-NEXT: risbg %r0, %r0, 49, 191, 16 | |
| ; CHECK-NEXT: ahi %r0, -1024 | |
| ; CHECK-NEXT: llhr %r0, %r0 | |
| ; CHECK-NEXT: chi %r0, 30720 | |
| ; CHECK-NEXT: ipm %r0 | |
| ; CHECK-NEXT: risbg %r2, %r0, 63, 191, 36 | |
| ; CHECK-NEXT: # kill: def $r2l killed $r2l killed $r2d | |
| ; CHECK-NEXT: br %r14 | |
| %1 = call i1 @llvm.is.fpclass.f16(half %x, i32 264) ; 0x108 = normal | |
| ret i1 %1 | |
| } | |
| define i1 @isnormal_f(float %x) { | |
| ; CHECK-LABEL: isnormal_f: | |
| ; CHECK: # %bb.0: | |
| ; CHECK-NEXT: tceb %f0, 768 | |
| ; CHECK-NEXT: ipm %r2 | |
| ; CHECK-NEXT: srl %r2, 28 | |
| ; CHECK-NEXT: br %r14 | |
| %1 = call i1 @llvm.is.fpclass.f32(float %x, i32 264) ; 0x108 = normal | |
| ret i1 %1 | |
| } | |
| define i1 @isnormal_d(double %x) { | |
| ; CHECK-LABEL: isnormal_d: | |
| ; CHECK: # %bb.0: | |
| ; CHECK-NEXT: tcdb %f0, 768 | |
| ; CHECK-NEXT: ipm %r2 | |
| ; CHECK-NEXT: srl %r2, 28 | |
| ; CHECK-NEXT: br %r14 | |
| %1 = call i1 @llvm.is.fpclass.f64(double %x, i32 264) ; 0x108 = normal | |
| ret i1 %1 | |
| } | |
| define i1 @issubnormal_h(half %x) { | |
| ; CHECK-LABEL: issubnormal_h: | |
| ; CHECK: # %bb.0: | |
| ; CHECK-NEXT: # kill: def $f0h killed $f0h def $f0d | |
| ; CHECK-NEXT: lgdr %r0, %f0 | |
| ; CHECK-NEXT: risbg %r0, %r0, 49, 191, 16 | |
| ; CHECK-NEXT: ahi %r0, -1 | |
| ; CHECK-NEXT: clfi %r0, 1023 | |
| ; CHECK-NEXT: ipm %r0 | |
| ; CHECK-NEXT: risbg %r2, %r0, 63, 191, 36 | |
| ; CHECK-NEXT: # kill: def $r2l killed $r2l killed $r2d | |
| ; CHECK-NEXT: br %r14 | |
| %1 = call i1 @llvm.is.fpclass.f16(half %x, i32 144) ; 0x90 = subnormal | |
| ret i1 %1 | |
| } | |
| define i1 @issubnormal_f(float %x) { | |
| ; CHECK-LABEL: issubnormal_f: | |
| ; CHECK: # %bb.0: | |
| ; CHECK-NEXT: tceb %f0, 192 | |
| ; CHECK-NEXT: ipm %r2 | |
| ; CHECK-NEXT: srl %r2, 28 | |
| ; CHECK-NEXT: br %r14 | |
| %1 = call i1 @llvm.is.fpclass.f32(float %x, i32 144) ; 0x90 = subnormal | |
| ret i1 %1 | |
| } | |
| define i1 @issubnormal_d(double %x) { | |
| ; CHECK-LABEL: issubnormal_d: | |
| ; CHECK: # %bb.0: | |
| ; CHECK-NEXT: tcdb %f0, 192 | |
| ; CHECK-NEXT: ipm %r2 | |
| ; CHECK-NEXT: srl %r2, 28 | |
| ; CHECK-NEXT: br %r14 | |
| %1 = call i1 @llvm.is.fpclass.f64(double %x, i32 144) ; 0x90 = subnormal | |
| ret i1 %1 | |
| } |