1 ; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 2
2 ; RUN: llc -amdgpu-scalarize-global-loads=false -mtriple=r600 -mcpu=redwood < %s | FileCheck -check-prefix=R600 %s
4 ; Run with unsafe-fp-math to make sure nothing tries to turn this into 1 / rsqrt(x)
6 define amdgpu_kernel void @v_safe_fsqrt_f32(ptr addrspace(1) %out, ptr addrspace(1) %in) {
7 ; R600-LABEL: v_safe_fsqrt_f32:
9 ; R600-NEXT: ALU 0, @8, KC0[CB0:0-32], KC1[]
11 ; R600-NEXT: ALU 3, @9, KC0[CB0:0-32], KC1[]
12 ; R600-NEXT: MEM_RAT_CACHELESS STORE_RAW T0.X, T1.X, 1
15 ; R600-NEXT: Fetch clause starting at 6:
16 ; R600-NEXT: VTX_READ_32 T0.X, T0.X, 0, #1
17 ; R600-NEXT: ALU clause starting at 8:
18 ; R600-NEXT: MOV * T0.X, KC0[2].Z,
19 ; R600-NEXT: ALU clause starting at 9:
20 ; R600-NEXT: RECIPSQRT_IEEE * T0.X, T0.X,
21 ; R600-NEXT: LSHR T1.X, KC0[2].Y, literal.x,
22 ; R600-NEXT: RECIP_IEEE * T0.X, PS,
23 ; R600-NEXT: 2(2.802597e-45), 0(0.000000e+00)
24 %r0 = load float, ptr addrspace(1) %in
25 %r1 = call float @llvm.sqrt.f32(float %r0)
26 store float %r1, ptr addrspace(1) %out
30 define amdgpu_kernel void @v_unsafe_fsqrt_f32(ptr addrspace(1) %out, ptr addrspace(1) %in) #1 {
31 ; R600-LABEL: v_unsafe_fsqrt_f32:
33 ; R600-NEXT: ALU 0, @8, KC0[CB0:0-32], KC1[]
35 ; R600-NEXT: ALU 3, @9, KC0[CB0:0-32], KC1[]
36 ; R600-NEXT: MEM_RAT_CACHELESS STORE_RAW T0.X, T1.X, 1
39 ; R600-NEXT: Fetch clause starting at 6:
40 ; R600-NEXT: VTX_READ_32 T0.X, T0.X, 0, #1
41 ; R600-NEXT: ALU clause starting at 8:
42 ; R600-NEXT: MOV * T0.X, KC0[2].Z,
43 ; R600-NEXT: ALU clause starting at 9:
44 ; R600-NEXT: RECIPSQRT_IEEE * T0.X, T0.X,
45 ; R600-NEXT: LSHR T1.X, KC0[2].Y, literal.x,
46 ; R600-NEXT: RECIP_IEEE * T0.X, PS,
47 ; R600-NEXT: 2(2.802597e-45), 0(0.000000e+00)
48 %r0 = load float, ptr addrspace(1) %in
49 %r1 = call float @llvm.sqrt.f32(float %r0)
50 store float %r1, ptr addrspace(1) %out
54 define amdgpu_kernel void @s_sqrt_f32(ptr addrspace(1) %out, float %in) {
55 ; R600-LABEL: s_sqrt_f32:
56 ; R600: ; %bb.0: ; %entry
57 ; R600-NEXT: ALU 3, @4, KC0[CB0:0-32], KC1[]
58 ; R600-NEXT: MEM_RAT_CACHELESS STORE_RAW T0.X, T1.X, 1
61 ; R600-NEXT: ALU clause starting at 4:
62 ; R600-NEXT: RECIPSQRT_IEEE * T0.X, KC0[2].Z,
63 ; R600-NEXT: LSHR T1.X, KC0[2].Y, literal.x,
64 ; R600-NEXT: RECIP_IEEE * T0.X, PS,
65 ; R600-NEXT: 2(2.802597e-45), 0(0.000000e+00)
67 %fdiv = call float @llvm.sqrt.f32(float %in)
68 store float %fdiv, ptr addrspace(1) %out
72 define amdgpu_kernel void @s_sqrt_v2f32(ptr addrspace(1) %out, <2 x float> %in) {
73 ; R600-LABEL: s_sqrt_v2f32:
74 ; R600: ; %bb.0: ; %entry
75 ; R600-NEXT: ALU 5, @4, KC0[CB0:0-32], KC1[]
76 ; R600-NEXT: MEM_RAT_CACHELESS STORE_RAW T0.XY, T1.X, 1
79 ; R600-NEXT: ALU clause starting at 4:
80 ; R600-NEXT: RECIPSQRT_IEEE * T0.X, KC0[2].W,
81 ; R600-NEXT: RECIPSQRT_IEEE * T0.Y, KC0[3].X,
82 ; R600-NEXT: RECIP_IEEE * T0.Y, PS,
83 ; R600-NEXT: LSHR T1.X, KC0[2].Y, literal.x,
84 ; R600-NEXT: RECIP_IEEE * T0.X, T0.X,
85 ; R600-NEXT: 2(2.802597e-45), 0(0.000000e+00)
87 %fdiv = call <2 x float> @llvm.sqrt.v2f32(<2 x float> %in)
88 store <2 x float> %fdiv, ptr addrspace(1) %out
92 define amdgpu_kernel void @s_sqrt_v4f32(ptr addrspace(1) %out, <4 x float> %in) {
93 ; R600-LABEL: s_sqrt_v4f32:
94 ; R600: ; %bb.0: ; %entry
95 ; R600-NEXT: ALU 9, @4, KC0[CB0:0-32], KC1[]
96 ; R600-NEXT: MEM_RAT_CACHELESS STORE_RAW T0.XYZW, T1.X, 1
99 ; R600-NEXT: ALU clause starting at 4:
100 ; R600-NEXT: RECIPSQRT_IEEE * T0.X, KC0[3].Y,
101 ; R600-NEXT: RECIPSQRT_IEEE * T0.Y, KC0[3].Z,
102 ; R600-NEXT: RECIPSQRT_IEEE * T0.Z, KC0[3].W,
103 ; R600-NEXT: RECIPSQRT_IEEE * T0.W, KC0[4].X,
104 ; R600-NEXT: RECIP_IEEE * T0.W, PS,
105 ; R600-NEXT: RECIP_IEEE * T0.Z, T0.Z,
106 ; R600-NEXT: RECIP_IEEE * T0.Y, T0.Y,
107 ; R600-NEXT: LSHR T1.X, KC0[2].Y, literal.x,
108 ; R600-NEXT: RECIP_IEEE * T0.X, T0.X,
109 ; R600-NEXT: 2(2.802597e-45), 0(0.000000e+00)
111 %fdiv = call <4 x float> @llvm.sqrt.v4f32(<4 x float> %in)
112 store <4 x float> %fdiv, ptr addrspace(1) %out
116 define amdgpu_kernel void @elim_redun_check_neg0(ptr addrspace(1) %out, float %in) {
117 ; R600-LABEL: elim_redun_check_neg0:
118 ; R600: ; %bb.0: ; %entry
119 ; R600-NEXT: ALU 3, @4, KC0[CB0:0-32], KC1[]
120 ; R600-NEXT: MEM_RAT_CACHELESS STORE_RAW T0.X, T1.X, 1
123 ; R600-NEXT: ALU clause starting at 4:
124 ; R600-NEXT: RECIPSQRT_IEEE * T0.X, KC0[2].Z,
125 ; R600-NEXT: LSHR T1.X, KC0[2].Y, literal.x,
126 ; R600-NEXT: RECIP_IEEE * T0.X, PS,
127 ; R600-NEXT: 2(2.802597e-45), 0(0.000000e+00)
129 %sqrt = call float @llvm.sqrt.f32(float %in)
130 %cmp = fcmp olt float %in, -0.000000e+00
131 %res = select i1 %cmp, float 0x7FF8000000000000, float %sqrt
132 store float %res, ptr addrspace(1) %out
136 define amdgpu_kernel void @elim_redun_check_pos0(ptr addrspace(1) %out, float %in) {
137 ; R600-LABEL: elim_redun_check_pos0:
138 ; R600: ; %bb.0: ; %entry
139 ; R600-NEXT: ALU 3, @4, KC0[CB0:0-32], KC1[]
140 ; R600-NEXT: MEM_RAT_CACHELESS STORE_RAW T0.X, T1.X, 1
143 ; R600-NEXT: ALU clause starting at 4:
144 ; R600-NEXT: RECIPSQRT_IEEE * T0.X, KC0[2].Z,
145 ; R600-NEXT: LSHR T1.X, KC0[2].Y, literal.x,
146 ; R600-NEXT: RECIP_IEEE * T0.X, PS,
147 ; R600-NEXT: 2(2.802597e-45), 0(0.000000e+00)
149 %sqrt = call float @llvm.sqrt.f32(float %in)
150 %cmp = fcmp olt float %in, 0.000000e+00
151 %res = select i1 %cmp, float 0x7FF8000000000000, float %sqrt
152 store float %res, ptr addrspace(1) %out
156 define amdgpu_kernel void @elim_redun_check_ult(ptr addrspace(1) %out, float %in) {
157 ; R600-LABEL: elim_redun_check_ult:
158 ; R600: ; %bb.0: ; %entry
159 ; R600-NEXT: ALU 3, @4, KC0[CB0:0-32], KC1[]
160 ; R600-NEXT: MEM_RAT_CACHELESS STORE_RAW T0.X, T1.X, 1
163 ; R600-NEXT: ALU clause starting at 4:
164 ; R600-NEXT: RECIPSQRT_IEEE * T0.X, KC0[2].Z,
165 ; R600-NEXT: LSHR T1.X, KC0[2].Y, literal.x,
166 ; R600-NEXT: RECIP_IEEE * T0.X, PS,
167 ; R600-NEXT: 2(2.802597e-45), 0(0.000000e+00)
169 %sqrt = call float @llvm.sqrt.f32(float %in)
170 %cmp = fcmp ult float %in, -0.000000e+00
171 %res = select i1 %cmp, float 0x7FF8000000000000, float %sqrt
172 store float %res, ptr addrspace(1) %out
176 define amdgpu_kernel void @elim_redun_check_v2(ptr addrspace(1) %out, <2 x float> %in) {
177 ; R600-LABEL: elim_redun_check_v2:
178 ; R600: ; %bb.0: ; %entry
179 ; R600-NEXT: ALU 5, @4, KC0[CB0:0-32], KC1[]
180 ; R600-NEXT: MEM_RAT_CACHELESS STORE_RAW T0.XY, T1.X, 1
183 ; R600-NEXT: ALU clause starting at 4:
184 ; R600-NEXT: RECIPSQRT_IEEE * T0.X, KC0[2].W,
185 ; R600-NEXT: RECIPSQRT_IEEE * T0.Y, KC0[3].X,
186 ; R600-NEXT: RECIP_IEEE * T0.Y, PS,
187 ; R600-NEXT: LSHR T1.X, KC0[2].Y, literal.x,
188 ; R600-NEXT: RECIP_IEEE * T0.X, T0.X,
189 ; R600-NEXT: 2(2.802597e-45), 0(0.000000e+00)
191 %sqrt = call <2 x float> @llvm.sqrt.v2f32(<2 x float> %in)
192 %cmp = fcmp olt <2 x float> %in, <float -0.000000e+00, float -0.000000e+00>
193 %res = select <2 x i1> %cmp, <2 x float> <float 0x7FF8000000000000, float 0x7FF8000000000000>, <2 x float> %sqrt
194 store <2 x float> %res, ptr addrspace(1) %out
198 define amdgpu_kernel void @elim_redun_check_v2_ult(ptr addrspace(1) %out, <2 x float> %in) {
199 ; R600-LABEL: elim_redun_check_v2_ult:
200 ; R600: ; %bb.0: ; %entry
201 ; R600-NEXT: ALU 5, @4, KC0[CB0:0-32], KC1[]
202 ; R600-NEXT: MEM_RAT_CACHELESS STORE_RAW T0.XY, T1.X, 1
205 ; R600-NEXT: ALU clause starting at 4:
206 ; R600-NEXT: RECIPSQRT_IEEE * T0.X, KC0[2].W,
207 ; R600-NEXT: RECIPSQRT_IEEE * T0.Y, KC0[3].X,
208 ; R600-NEXT: RECIP_IEEE * T0.Y, PS,
209 ; R600-NEXT: LSHR T1.X, KC0[2].Y, literal.x,
210 ; R600-NEXT: RECIP_IEEE * T0.X, T0.X,
211 ; R600-NEXT: 2(2.802597e-45), 0(0.000000e+00)
213 %sqrt = call <2 x float> @llvm.sqrt.v2f32(<2 x float> %in)
214 %cmp = fcmp ult <2 x float> %in, <float -0.000000e+00, float -0.000000e+00>
215 %res = select <2 x i1> %cmp, <2 x float> <float 0x7FF8000000000000, float 0x7FF8000000000000>, <2 x float> %sqrt
216 store <2 x float> %res, ptr addrspace(1) %out
220 define amdgpu_kernel void @recip_sqrt(ptr addrspace(1) %out, float %src) nounwind {
221 ; R600-LABEL: recip_sqrt:
223 ; R600-NEXT: ALU 2, @4, KC0[CB0:0-32], KC1[]
224 ; R600-NEXT: MEM_RAT_CACHELESS STORE_RAW T1.X, T0.X, 1
227 ; R600-NEXT: ALU clause starting at 4:
228 ; R600-NEXT: LSHR T0.X, KC0[2].Y, literal.x,
229 ; R600-NEXT: RECIPSQRT_IEEE * T1.X, KC0[2].Z,
230 ; R600-NEXT: 2(2.802597e-45), 0(0.000000e+00)
231 %sqrt = call float @llvm.sqrt.f32(float %src)
232 %recipsqrt = fdiv fast float 1.0, %sqrt
233 store float %recipsqrt, ptr addrspace(1) %out, align 4
237 declare float @llvm.sqrt.f32(float %in) #0
238 declare <2 x float> @llvm.sqrt.v2f32(<2 x float> %in) #0
239 declare <4 x float> @llvm.sqrt.v4f32(<4 x float> %in) #0
241 attributes #0 = { nounwind readnone }
242 attributes #1 = { nounwind "unsafe-fp-math"="true" }