1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131
|
; NOTE: Assertions have been autogenerated by utils/update_test_checks.py
; RUN: opt -S -passes=instcombine < %s | FileCheck %s
declare float @llvm.fabs.f32(float)
declare float @llvm.copysign.f32(float, float)
declare float @llvm.maxnum.f32(float, float)
declare <3 x double> @llvm.copysign.v3f64(<3 x double>, <3 x double>)
define float @positive_sign_arg(float %x) {
; CHECK-LABEL: @positive_sign_arg(
; CHECK-NEXT: [[R:%.*]] = call arcp float @llvm.fabs.f32(float [[X:%.*]])
; CHECK-NEXT: ret float [[R]]
;
%r = call arcp float @llvm.copysign.f32(float %x, float 0.0)
ret float %r
}
define <3 x double> @positive_sign_arg_vec_splat(<3 x double> %x) {
; CHECK-LABEL: @positive_sign_arg_vec_splat(
; CHECK-NEXT: [[R:%.*]] = call ninf <3 x double> @llvm.fabs.v3f64(<3 x double> [[X:%.*]])
; CHECK-NEXT: ret <3 x double> [[R]]
;
%r = call ninf <3 x double> @llvm.copysign.v3f64(<3 x double> %x, <3 x double> <double 42.0, double 42.0, double 42.0>)
ret <3 x double> %r
}
define float @negative_sign_arg(float %x) {
; CHECK-LABEL: @negative_sign_arg(
; CHECK-NEXT: [[TMP1:%.*]] = call nnan float @llvm.fabs.f32(float [[X:%.*]])
; CHECK-NEXT: [[R:%.*]] = fneg nnan float [[TMP1]]
; CHECK-NEXT: ret float [[R]]
;
%r = call nnan float @llvm.copysign.f32(float %x, float -0.0)
ret float %r
}
define <3 x double> @negative_sign_arg_vec_splat(<3 x double> %x) {
; CHECK-LABEL: @negative_sign_arg_vec_splat(
; CHECK-NEXT: [[TMP1:%.*]] = call fast <3 x double> @llvm.fabs.v3f64(<3 x double> [[X:%.*]])
; CHECK-NEXT: [[R:%.*]] = fneg fast <3 x double> [[TMP1]]
; CHECK-NEXT: ret <3 x double> [[R]]
;
%r = call fast <3 x double> @llvm.copysign.v3f64(<3 x double> %x, <3 x double> <double -42.0, double -42.0, double -42.0>)
ret <3 x double> %r
}
define float @known_positive_sign_arg(float %x, float %y) {
; CHECK-LABEL: @known_positive_sign_arg(
; CHECK-NEXT: [[R:%.*]] = call ninf float @llvm.fabs.f32(float [[X:%.*]])
; CHECK-NEXT: ret float [[R]]
;
%fabs = call float @llvm.fabs.f32(float %y)
%r = call ninf float @llvm.copysign.f32(float %x, float %fabs)
ret float %r
}
define <3 x double> @known_positive_sign_arg_vec(<3 x double> %x, <3 x i32> %y) {
; CHECK-LABEL: @known_positive_sign_arg_vec(
; CHECK-NEXT: [[R:%.*]] = call arcp <3 x double> @llvm.fabs.v3f64(<3 x double> [[X:%.*]])
; CHECK-NEXT: ret <3 x double> [[R]]
;
%yf = uitofp <3 x i32> %y to <3 x double>
%r = call arcp <3 x double> @llvm.copysign.v3f64(<3 x double> %x, <3 x double> %yf)
ret <3 x double> %r
}
; maxnum(-0.0, 0.0) can return -0.0.
define float @not_known_positive_sign_arg(float %x, float %y) {
; CHECK-LABEL: @not_known_positive_sign_arg(
; CHECK-NEXT: [[MAX:%.*]] = call float @llvm.maxnum.f32(float [[X:%.*]], float 0.000000e+00)
; CHECK-NEXT: [[R:%.*]] = call ninf float @llvm.copysign.f32(float [[Y:%.*]], float [[MAX]])
; CHECK-NEXT: ret float [[R]]
;
%max = call float @llvm.maxnum.f32(float %x, float 0.0)
%r = call ninf float @llvm.copysign.f32(float %y, float %max)
ret float %r
}
; The magnitude operand of the 1st copysign is irrelevant.
; copysign(x, copysign(y, z)) --> copysign(x, z)
define float @copysign_sign_arg(float %x, float %y, float %z) {
; CHECK-LABEL: @copysign_sign_arg(
; CHECK-NEXT: [[R:%.*]] = call float @llvm.copysign.f32(float [[X:%.*]], float [[Z:%.*]])
; CHECK-NEXT: ret float [[R]]
;
%s = call reassoc float @llvm.copysign.f32(float %y, float %z)
%r = call ninf float @llvm.copysign.f32(float %x, float %s)
ret float %r
}
define float @copysign_sign_arg_nnan(float %x, float %y, float %z) {
; CHECK-LABEL: @copysign_sign_arg_nnan(
; CHECK-NEXT: [[R:%.*]] = call nnan float @llvm.copysign.f32(float [[X:%.*]], float [[Z:%.*]])
; CHECK-NEXT: ret float [[R]]
;
%s = call nnan float @llvm.copysign.f32(float %y, float %z)
%r = call nnan float @llvm.copysign.f32(float %x, float %s)
ret float %r
}
define float @copysign_sign_arg_mixed(float %x, float %y, float %z) {
; CHECK-LABEL: @copysign_sign_arg_mixed(
; CHECK-NEXT: [[R:%.*]] = call nsz float @llvm.copysign.f32(float [[X:%.*]], float [[Z:%.*]])
; CHECK-NEXT: ret float [[R]]
;
%s = call ninf nsz float @llvm.copysign.f32(float %y, float %z)
%r = call nnan nsz float @llvm.copysign.f32(float %x, float %s)
ret float %r
}
define float @fneg_mag(float %x, float %y) {
; CHECK-LABEL: @fneg_mag(
; CHECK-NEXT: [[R:%.*]] = call float @llvm.copysign.f32(float [[X:%.*]], float [[Y:%.*]])
; CHECK-NEXT: ret float [[R]]
;
%n = fneg float %x
%r = call float @llvm.copysign.f32(float %n, float %y)
ret float %r
}
define float @fabs_mag(float %x, float %y) {
; CHECK-LABEL: @fabs_mag(
; CHECK-NEXT: [[R:%.*]] = call float @llvm.copysign.f32(float [[X:%.*]], float [[Y:%.*]])
; CHECK-NEXT: ret float [[R]]
;
%a = call float @llvm.fabs.f32(float %x)
%r = call float @llvm.copysign.f32(float %a, float %y)
ret float %r
}
|