xref: /llvm-project/llvm/test/CodeGen/RISCV/bfloat-convert.ll (revision 9122c5235ec85ce0c0ad337e862b006e7b349d84)
1; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 2
2; RUN: llc -mtriple=riscv32 -mattr=+zfbfmin -verify-machineinstrs \
3; RUN:   -target-abi ilp32f < %s | FileCheck -check-prefixes=CHECK32ZFBFMIN,RV32IZFBFMIN %s
4; RUN: llc -mtriple=riscv32 -mattr=+d,+zfbfmin -verify-machineinstrs \
5; RUN:   -target-abi ilp32d < %s | FileCheck -check-prefixes=CHECK32ZFBFMIN,R32IDZFBFMIN %s
6; RUN: llc -mtriple=riscv32 -mattr=+d -verify-machineinstrs \
7; RUN:   -target-abi ilp32d < %s | FileCheck -check-prefixes=RV32ID %s
8; RUN: llc -mtriple=riscv64 -mattr=+zfbfmin -verify-machineinstrs \
9; RUN:   -target-abi lp64f < %s | FileCheck -check-prefixes=CHECK64ZFBFMIN,RV64IZFBFMIN %s
10; RUN: llc -mtriple=riscv64 -mattr=+d,+zfbfmin -verify-machineinstrs \
11; RUN:   -target-abi lp64d < %s | FileCheck -check-prefixes=CHECK64ZFBFMIN,RV64IDZFBFMIN %s
12; RUN: llc -mtriple=riscv64 -mattr=+d -verify-machineinstrs \
13; RUN:   -target-abi lp64d < %s | FileCheck -check-prefixes=RV64ID %s
14
15; These tests descend from float-arith.ll, where each function was targeted at
16; a particular RISC-V FPU instruction.
17
18define i16 @fcvt_si_bf16(bfloat %a) nounwind {
19; CHECK32ZFBFMIN-LABEL: fcvt_si_bf16:
20; CHECK32ZFBFMIN:       # %bb.0:
21; CHECK32ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
22; CHECK32ZFBFMIN-NEXT:    fcvt.w.s a0, fa5, rtz
23; CHECK32ZFBFMIN-NEXT:    ret
24;
25; RV32ID-LABEL: fcvt_si_bf16:
26; RV32ID:       # %bb.0:
27; RV32ID-NEXT:    fmv.x.w a0, fa0
28; RV32ID-NEXT:    slli a0, a0, 16
29; RV32ID-NEXT:    fmv.w.x fa5, a0
30; RV32ID-NEXT:    fcvt.w.s a0, fa5, rtz
31; RV32ID-NEXT:    ret
32;
33; CHECK64ZFBFMIN-LABEL: fcvt_si_bf16:
34; CHECK64ZFBFMIN:       # %bb.0:
35; CHECK64ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
36; CHECK64ZFBFMIN-NEXT:    fcvt.l.s a0, fa5, rtz
37; CHECK64ZFBFMIN-NEXT:    ret
38;
39; RV64ID-LABEL: fcvt_si_bf16:
40; RV64ID:       # %bb.0:
41; RV64ID-NEXT:    fmv.x.w a0, fa0
42; RV64ID-NEXT:    slli a0, a0, 16
43; RV64ID-NEXT:    fmv.w.x fa5, a0
44; RV64ID-NEXT:    fcvt.l.s a0, fa5, rtz
45; RV64ID-NEXT:    ret
46  %1 = fptosi bfloat %a to i16
47  ret i16 %1
48}
49
50define i16 @fcvt_si_bf16_sat(bfloat %a) nounwind {
51; CHECK32ZFBFMIN-LABEL: fcvt_si_bf16_sat:
52; CHECK32ZFBFMIN:       # %bb.0: # %start
53; CHECK32ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
54; CHECK32ZFBFMIN-NEXT:    lui a0, %hi(.LCPI1_0)
55; CHECK32ZFBFMIN-NEXT:    feq.s a1, fa5, fa5
56; CHECK32ZFBFMIN-NEXT:    flw fa4, %lo(.LCPI1_0)(a0)
57; CHECK32ZFBFMIN-NEXT:    lui a0, 815104
58; CHECK32ZFBFMIN-NEXT:    fmv.w.x fa3, a0
59; CHECK32ZFBFMIN-NEXT:    fmax.s fa5, fa5, fa3
60; CHECK32ZFBFMIN-NEXT:    neg a0, a1
61; CHECK32ZFBFMIN-NEXT:    fmin.s fa5, fa5, fa4
62; CHECK32ZFBFMIN-NEXT:    fcvt.w.s a1, fa5, rtz
63; CHECK32ZFBFMIN-NEXT:    and a0, a0, a1
64; CHECK32ZFBFMIN-NEXT:    ret
65;
66; RV32ID-LABEL: fcvt_si_bf16_sat:
67; RV32ID:       # %bb.0: # %start
68; RV32ID-NEXT:    fmv.x.w a0, fa0
69; RV32ID-NEXT:    lui a1, 815104
70; RV32ID-NEXT:    fmv.w.x fa5, a1
71; RV32ID-NEXT:    lui a1, %hi(.LCPI1_0)
72; RV32ID-NEXT:    slli a0, a0, 16
73; RV32ID-NEXT:    flw fa4, %lo(.LCPI1_0)(a1)
74; RV32ID-NEXT:    fmv.w.x fa3, a0
75; RV32ID-NEXT:    feq.s a0, fa3, fa3
76; RV32ID-NEXT:    fmax.s fa5, fa3, fa5
77; RV32ID-NEXT:    neg a0, a0
78; RV32ID-NEXT:    fmin.s fa5, fa5, fa4
79; RV32ID-NEXT:    fcvt.w.s a1, fa5, rtz
80; RV32ID-NEXT:    and a0, a0, a1
81; RV32ID-NEXT:    ret
82;
83; CHECK64ZFBFMIN-LABEL: fcvt_si_bf16_sat:
84; CHECK64ZFBFMIN:       # %bb.0: # %start
85; CHECK64ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
86; CHECK64ZFBFMIN-NEXT:    lui a0, %hi(.LCPI1_0)
87; CHECK64ZFBFMIN-NEXT:    feq.s a1, fa5, fa5
88; CHECK64ZFBFMIN-NEXT:    flw fa4, %lo(.LCPI1_0)(a0)
89; CHECK64ZFBFMIN-NEXT:    lui a0, 815104
90; CHECK64ZFBFMIN-NEXT:    fmv.w.x fa3, a0
91; CHECK64ZFBFMIN-NEXT:    fmax.s fa5, fa5, fa3
92; CHECK64ZFBFMIN-NEXT:    neg a0, a1
93; CHECK64ZFBFMIN-NEXT:    fmin.s fa5, fa5, fa4
94; CHECK64ZFBFMIN-NEXT:    fcvt.l.s a1, fa5, rtz
95; CHECK64ZFBFMIN-NEXT:    and a0, a0, a1
96; CHECK64ZFBFMIN-NEXT:    ret
97;
98; RV64ID-LABEL: fcvt_si_bf16_sat:
99; RV64ID:       # %bb.0: # %start
100; RV64ID-NEXT:    fmv.x.w a0, fa0
101; RV64ID-NEXT:    lui a1, 815104
102; RV64ID-NEXT:    fmv.w.x fa5, a1
103; RV64ID-NEXT:    lui a1, %hi(.LCPI1_0)
104; RV64ID-NEXT:    slli a0, a0, 16
105; RV64ID-NEXT:    flw fa4, %lo(.LCPI1_0)(a1)
106; RV64ID-NEXT:    fmv.w.x fa3, a0
107; RV64ID-NEXT:    feq.s a0, fa3, fa3
108; RV64ID-NEXT:    fmax.s fa5, fa3, fa5
109; RV64ID-NEXT:    neg a0, a0
110; RV64ID-NEXT:    fmin.s fa5, fa5, fa4
111; RV64ID-NEXT:    fcvt.l.s a1, fa5, rtz
112; RV64ID-NEXT:    and a0, a0, a1
113; RV64ID-NEXT:    ret
114start:
115  %0 = tail call i16 @llvm.fptosi.sat.i16.bf16(bfloat %a)
116  ret i16 %0
117}
118declare i16 @llvm.fptosi.sat.i16.bf16(bfloat)
119
120define i16 @fcvt_ui_bf16(bfloat %a) nounwind {
121; CHECK32ZFBFMIN-LABEL: fcvt_ui_bf16:
122; CHECK32ZFBFMIN:       # %bb.0:
123; CHECK32ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
124; CHECK32ZFBFMIN-NEXT:    fcvt.w.s a0, fa5, rtz
125; CHECK32ZFBFMIN-NEXT:    ret
126;
127; RV32ID-LABEL: fcvt_ui_bf16:
128; RV32ID:       # %bb.0:
129; RV32ID-NEXT:    fmv.x.w a0, fa0
130; RV32ID-NEXT:    slli a0, a0, 16
131; RV32ID-NEXT:    fmv.w.x fa5, a0
132; RV32ID-NEXT:    fcvt.wu.s a0, fa5, rtz
133; RV32ID-NEXT:    ret
134;
135; CHECK64ZFBFMIN-LABEL: fcvt_ui_bf16:
136; CHECK64ZFBFMIN:       # %bb.0:
137; CHECK64ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
138; CHECK64ZFBFMIN-NEXT:    fcvt.l.s a0, fa5, rtz
139; CHECK64ZFBFMIN-NEXT:    ret
140;
141; RV64ID-LABEL: fcvt_ui_bf16:
142; RV64ID:       # %bb.0:
143; RV64ID-NEXT:    fmv.x.w a0, fa0
144; RV64ID-NEXT:    slli a0, a0, 16
145; RV64ID-NEXT:    fmv.w.x fa5, a0
146; RV64ID-NEXT:    fcvt.lu.s a0, fa5, rtz
147; RV64ID-NEXT:    ret
148  %1 = fptoui bfloat %a to i16
149  ret i16 %1
150}
151
152define i16 @fcvt_ui_bf16_sat(bfloat %a) nounwind {
153; CHECK32ZFBFMIN-LABEL: fcvt_ui_bf16_sat:
154; CHECK32ZFBFMIN:       # %bb.0: # %start
155; CHECK32ZFBFMIN-NEXT:    lui a0, %hi(.LCPI3_0)
156; CHECK32ZFBFMIN-NEXT:    flw fa5, %lo(.LCPI3_0)(a0)
157; CHECK32ZFBFMIN-NEXT:    fcvt.s.bf16 fa4, fa0
158; CHECK32ZFBFMIN-NEXT:    fmv.w.x fa3, zero
159; CHECK32ZFBFMIN-NEXT:    fmax.s fa4, fa4, fa3
160; CHECK32ZFBFMIN-NEXT:    fmin.s fa5, fa4, fa5
161; CHECK32ZFBFMIN-NEXT:    fcvt.wu.s a0, fa5, rtz
162; CHECK32ZFBFMIN-NEXT:    ret
163;
164; RV32ID-LABEL: fcvt_ui_bf16_sat:
165; RV32ID:       # %bb.0: # %start
166; RV32ID-NEXT:    lui a0, %hi(.LCPI3_0)
167; RV32ID-NEXT:    flw fa5, %lo(.LCPI3_0)(a0)
168; RV32ID-NEXT:    fmv.x.w a0, fa0
169; RV32ID-NEXT:    slli a0, a0, 16
170; RV32ID-NEXT:    fmv.w.x fa4, a0
171; RV32ID-NEXT:    fmv.w.x fa3, zero
172; RV32ID-NEXT:    fmax.s fa4, fa4, fa3
173; RV32ID-NEXT:    fmin.s fa5, fa4, fa5
174; RV32ID-NEXT:    fcvt.wu.s a0, fa5, rtz
175; RV32ID-NEXT:    ret
176;
177; CHECK64ZFBFMIN-LABEL: fcvt_ui_bf16_sat:
178; CHECK64ZFBFMIN:       # %bb.0: # %start
179; CHECK64ZFBFMIN-NEXT:    lui a0, %hi(.LCPI3_0)
180; CHECK64ZFBFMIN-NEXT:    flw fa5, %lo(.LCPI3_0)(a0)
181; CHECK64ZFBFMIN-NEXT:    fcvt.s.bf16 fa4, fa0
182; CHECK64ZFBFMIN-NEXT:    fmv.w.x fa3, zero
183; CHECK64ZFBFMIN-NEXT:    fmax.s fa4, fa4, fa3
184; CHECK64ZFBFMIN-NEXT:    fmin.s fa5, fa4, fa5
185; CHECK64ZFBFMIN-NEXT:    fcvt.lu.s a0, fa5, rtz
186; CHECK64ZFBFMIN-NEXT:    ret
187;
188; RV64ID-LABEL: fcvt_ui_bf16_sat:
189; RV64ID:       # %bb.0: # %start
190; RV64ID-NEXT:    lui a0, %hi(.LCPI3_0)
191; RV64ID-NEXT:    flw fa5, %lo(.LCPI3_0)(a0)
192; RV64ID-NEXT:    fmv.x.w a0, fa0
193; RV64ID-NEXT:    slli a0, a0, 16
194; RV64ID-NEXT:    fmv.w.x fa4, a0
195; RV64ID-NEXT:    fmv.w.x fa3, zero
196; RV64ID-NEXT:    fmax.s fa4, fa4, fa3
197; RV64ID-NEXT:    fmin.s fa5, fa4, fa5
198; RV64ID-NEXT:    fcvt.lu.s a0, fa5, rtz
199; RV64ID-NEXT:    ret
200start:
201  %0 = tail call i16 @llvm.fptoui.sat.i16.bf16(bfloat %a)
202  ret i16 %0
203}
204declare i16 @llvm.fptoui.sat.i16.bf16(bfloat)
205
206define i32 @fcvt_w_bf16(bfloat %a) nounwind {
207; CHECK32ZFBFMIN-LABEL: fcvt_w_bf16:
208; CHECK32ZFBFMIN:       # %bb.0:
209; CHECK32ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
210; CHECK32ZFBFMIN-NEXT:    fcvt.w.s a0, fa5, rtz
211; CHECK32ZFBFMIN-NEXT:    ret
212;
213; RV32ID-LABEL: fcvt_w_bf16:
214; RV32ID:       # %bb.0:
215; RV32ID-NEXT:    fmv.x.w a0, fa0
216; RV32ID-NEXT:    slli a0, a0, 16
217; RV32ID-NEXT:    fmv.w.x fa5, a0
218; RV32ID-NEXT:    fcvt.w.s a0, fa5, rtz
219; RV32ID-NEXT:    ret
220;
221; CHECK64ZFBFMIN-LABEL: fcvt_w_bf16:
222; CHECK64ZFBFMIN:       # %bb.0:
223; CHECK64ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
224; CHECK64ZFBFMIN-NEXT:    fcvt.w.s a0, fa5, rtz
225; CHECK64ZFBFMIN-NEXT:    ret
226;
227; RV64ID-LABEL: fcvt_w_bf16:
228; RV64ID:       # %bb.0:
229; RV64ID-NEXT:    fmv.x.w a0, fa0
230; RV64ID-NEXT:    slli a0, a0, 16
231; RV64ID-NEXT:    fmv.w.x fa5, a0
232; RV64ID-NEXT:    fcvt.l.s a0, fa5, rtz
233; RV64ID-NEXT:    ret
234  %1 = fptosi bfloat %a to i32
235  ret i32 %1
236}
237
238define i32 @fcvt_w_bf16_sat(bfloat %a) nounwind {
239; CHECK32ZFBFMIN-LABEL: fcvt_w_bf16_sat:
240; CHECK32ZFBFMIN:       # %bb.0: # %start
241; CHECK32ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
242; CHECK32ZFBFMIN-NEXT:    fcvt.w.s a0, fa5, rtz
243; CHECK32ZFBFMIN-NEXT:    feq.s a1, fa5, fa5
244; CHECK32ZFBFMIN-NEXT:    seqz a1, a1
245; CHECK32ZFBFMIN-NEXT:    addi a1, a1, -1
246; CHECK32ZFBFMIN-NEXT:    and a0, a1, a0
247; CHECK32ZFBFMIN-NEXT:    ret
248;
249; RV32ID-LABEL: fcvt_w_bf16_sat:
250; RV32ID:       # %bb.0: # %start
251; RV32ID-NEXT:    fmv.x.w a0, fa0
252; RV32ID-NEXT:    slli a0, a0, 16
253; RV32ID-NEXT:    fmv.w.x fa5, a0
254; RV32ID-NEXT:    fcvt.w.s a0, fa5, rtz
255; RV32ID-NEXT:    feq.s a1, fa5, fa5
256; RV32ID-NEXT:    seqz a1, a1
257; RV32ID-NEXT:    addi a1, a1, -1
258; RV32ID-NEXT:    and a0, a1, a0
259; RV32ID-NEXT:    ret
260;
261; CHECK64ZFBFMIN-LABEL: fcvt_w_bf16_sat:
262; CHECK64ZFBFMIN:       # %bb.0: # %start
263; CHECK64ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
264; CHECK64ZFBFMIN-NEXT:    fcvt.w.s a0, fa5, rtz
265; CHECK64ZFBFMIN-NEXT:    feq.s a1, fa5, fa5
266; CHECK64ZFBFMIN-NEXT:    seqz a1, a1
267; CHECK64ZFBFMIN-NEXT:    addi a1, a1, -1
268; CHECK64ZFBFMIN-NEXT:    and a0, a1, a0
269; CHECK64ZFBFMIN-NEXT:    ret
270;
271; RV64ID-LABEL: fcvt_w_bf16_sat:
272; RV64ID:       # %bb.0: # %start
273; RV64ID-NEXT:    fmv.x.w a0, fa0
274; RV64ID-NEXT:    slli a0, a0, 16
275; RV64ID-NEXT:    fmv.w.x fa5, a0
276; RV64ID-NEXT:    fcvt.w.s a0, fa5, rtz
277; RV64ID-NEXT:    feq.s a1, fa5, fa5
278; RV64ID-NEXT:    seqz a1, a1
279; RV64ID-NEXT:    addi a1, a1, -1
280; RV64ID-NEXT:    and a0, a1, a0
281; RV64ID-NEXT:    ret
282start:
283  %0 = tail call i32 @llvm.fptosi.sat.i32.bf16(bfloat %a)
284  ret i32 %0
285}
286declare i32 @llvm.fptosi.sat.i32.bf16(bfloat)
287
288define i32 @fcvt_wu_bf16(bfloat %a) nounwind {
289; CHECK32ZFBFMIN-LABEL: fcvt_wu_bf16:
290; CHECK32ZFBFMIN:       # %bb.0:
291; CHECK32ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
292; CHECK32ZFBFMIN-NEXT:    fcvt.wu.s a0, fa5, rtz
293; CHECK32ZFBFMIN-NEXT:    ret
294;
295; RV32ID-LABEL: fcvt_wu_bf16:
296; RV32ID:       # %bb.0:
297; RV32ID-NEXT:    fmv.x.w a0, fa0
298; RV32ID-NEXT:    slli a0, a0, 16
299; RV32ID-NEXT:    fmv.w.x fa5, a0
300; RV32ID-NEXT:    fcvt.wu.s a0, fa5, rtz
301; RV32ID-NEXT:    ret
302;
303; CHECK64ZFBFMIN-LABEL: fcvt_wu_bf16:
304; CHECK64ZFBFMIN:       # %bb.0:
305; CHECK64ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
306; CHECK64ZFBFMIN-NEXT:    fcvt.wu.s a0, fa5, rtz
307; CHECK64ZFBFMIN-NEXT:    ret
308;
309; RV64ID-LABEL: fcvt_wu_bf16:
310; RV64ID:       # %bb.0:
311; RV64ID-NEXT:    fmv.x.w a0, fa0
312; RV64ID-NEXT:    slli a0, a0, 16
313; RV64ID-NEXT:    fmv.w.x fa5, a0
314; RV64ID-NEXT:    fcvt.lu.s a0, fa5, rtz
315; RV64ID-NEXT:    ret
316  %1 = fptoui bfloat %a to i32
317  ret i32 %1
318}
319
320define i32 @fcvt_wu_bf16_multiple_use(bfloat %x, ptr %y) nounwind {
321; CHECK32ZFBFMIN-LABEL: fcvt_wu_bf16_multiple_use:
322; CHECK32ZFBFMIN:       # %bb.0:
323; CHECK32ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
324; CHECK32ZFBFMIN-NEXT:    fcvt.wu.s a0, fa5, rtz
325; CHECK32ZFBFMIN-NEXT:    seqz a1, a0
326; CHECK32ZFBFMIN-NEXT:    add a0, a0, a1
327; CHECK32ZFBFMIN-NEXT:    ret
328;
329; RV32ID-LABEL: fcvt_wu_bf16_multiple_use:
330; RV32ID:       # %bb.0:
331; RV32ID-NEXT:    fmv.x.w a0, fa0
332; RV32ID-NEXT:    slli a0, a0, 16
333; RV32ID-NEXT:    fmv.w.x fa5, a0
334; RV32ID-NEXT:    fcvt.wu.s a0, fa5, rtz
335; RV32ID-NEXT:    seqz a1, a0
336; RV32ID-NEXT:    add a0, a0, a1
337; RV32ID-NEXT:    ret
338;
339; CHECK64ZFBFMIN-LABEL: fcvt_wu_bf16_multiple_use:
340; CHECK64ZFBFMIN:       # %bb.0:
341; CHECK64ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
342; CHECK64ZFBFMIN-NEXT:    fcvt.wu.s a0, fa5, rtz
343; CHECK64ZFBFMIN-NEXT:    seqz a1, a0
344; CHECK64ZFBFMIN-NEXT:    add a0, a0, a1
345; CHECK64ZFBFMIN-NEXT:    ret
346;
347; RV64ID-LABEL: fcvt_wu_bf16_multiple_use:
348; RV64ID:       # %bb.0:
349; RV64ID-NEXT:    fmv.x.w a0, fa0
350; RV64ID-NEXT:    slli a0, a0, 16
351; RV64ID-NEXT:    fmv.w.x fa5, a0
352; RV64ID-NEXT:    fcvt.lu.s a0, fa5, rtz
353; RV64ID-NEXT:    seqz a1, a0
354; RV64ID-NEXT:    add a0, a0, a1
355; RV64ID-NEXT:    ret
356  %a = fptoui bfloat %x to i32
357  %b = icmp eq i32 %a, 0
358  %c = select i1 %b, i32 1, i32 %a
359  ret i32 %c
360}
361
362define i32 @fcvt_wu_bf16_sat(bfloat %a) nounwind {
363; CHECK32ZFBFMIN-LABEL: fcvt_wu_bf16_sat:
364; CHECK32ZFBFMIN:       # %bb.0: # %start
365; CHECK32ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
366; CHECK32ZFBFMIN-NEXT:    fcvt.wu.s a0, fa5, rtz
367; CHECK32ZFBFMIN-NEXT:    feq.s a1, fa5, fa5
368; CHECK32ZFBFMIN-NEXT:    seqz a1, a1
369; CHECK32ZFBFMIN-NEXT:    addi a1, a1, -1
370; CHECK32ZFBFMIN-NEXT:    and a0, a1, a0
371; CHECK32ZFBFMIN-NEXT:    ret
372;
373; RV32ID-LABEL: fcvt_wu_bf16_sat:
374; RV32ID:       # %bb.0: # %start
375; RV32ID-NEXT:    fmv.x.w a0, fa0
376; RV32ID-NEXT:    slli a0, a0, 16
377; RV32ID-NEXT:    fmv.w.x fa5, a0
378; RV32ID-NEXT:    fcvt.wu.s a0, fa5, rtz
379; RV32ID-NEXT:    feq.s a1, fa5, fa5
380; RV32ID-NEXT:    seqz a1, a1
381; RV32ID-NEXT:    addi a1, a1, -1
382; RV32ID-NEXT:    and a0, a1, a0
383; RV32ID-NEXT:    ret
384;
385; CHECK64ZFBFMIN-LABEL: fcvt_wu_bf16_sat:
386; CHECK64ZFBFMIN:       # %bb.0: # %start
387; CHECK64ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
388; CHECK64ZFBFMIN-NEXT:    fcvt.wu.s a0, fa5, rtz
389; CHECK64ZFBFMIN-NEXT:    feq.s a1, fa5, fa5
390; CHECK64ZFBFMIN-NEXT:    seqz a1, a1
391; CHECK64ZFBFMIN-NEXT:    addi a1, a1, -1
392; CHECK64ZFBFMIN-NEXT:    and a0, a0, a1
393; CHECK64ZFBFMIN-NEXT:    slli a0, a0, 32
394; CHECK64ZFBFMIN-NEXT:    srli a0, a0, 32
395; CHECK64ZFBFMIN-NEXT:    ret
396;
397; RV64ID-LABEL: fcvt_wu_bf16_sat:
398; RV64ID:       # %bb.0: # %start
399; RV64ID-NEXT:    fmv.x.w a0, fa0
400; RV64ID-NEXT:    slli a0, a0, 16
401; RV64ID-NEXT:    fmv.w.x fa5, a0
402; RV64ID-NEXT:    fcvt.wu.s a0, fa5, rtz
403; RV64ID-NEXT:    feq.s a1, fa5, fa5
404; RV64ID-NEXT:    seqz a1, a1
405; RV64ID-NEXT:    addi a1, a1, -1
406; RV64ID-NEXT:    and a0, a0, a1
407; RV64ID-NEXT:    slli a0, a0, 32
408; RV64ID-NEXT:    srli a0, a0, 32
409; RV64ID-NEXT:    ret
410start:
411  %0 = tail call i32 @llvm.fptoui.sat.i32.bf16(bfloat %a)
412  ret i32 %0
413}
414declare i32 @llvm.fptoui.sat.i32.bf16(bfloat)
415
416define i64 @fcvt_l_bf16(bfloat %a) nounwind {
417; CHECK32ZFBFMIN-LABEL: fcvt_l_bf16:
418; CHECK32ZFBFMIN:       # %bb.0:
419; CHECK32ZFBFMIN-NEXT:    addi sp, sp, -16
420; CHECK32ZFBFMIN-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
421; CHECK32ZFBFMIN-NEXT:    fcvt.s.bf16 fa0, fa0
422; CHECK32ZFBFMIN-NEXT:    call __fixsfdi
423; CHECK32ZFBFMIN-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
424; CHECK32ZFBFMIN-NEXT:    addi sp, sp, 16
425; CHECK32ZFBFMIN-NEXT:    ret
426;
427; RV32ID-LABEL: fcvt_l_bf16:
428; RV32ID:       # %bb.0:
429; RV32ID-NEXT:    addi sp, sp, -16
430; RV32ID-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
431; RV32ID-NEXT:    fmv.x.w a0, fa0
432; RV32ID-NEXT:    slli a0, a0, 16
433; RV32ID-NEXT:    fmv.w.x fa0, a0
434; RV32ID-NEXT:    call __fixsfdi
435; RV32ID-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
436; RV32ID-NEXT:    addi sp, sp, 16
437; RV32ID-NEXT:    ret
438;
439; CHECK64ZFBFMIN-LABEL: fcvt_l_bf16:
440; CHECK64ZFBFMIN:       # %bb.0:
441; CHECK64ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
442; CHECK64ZFBFMIN-NEXT:    fcvt.l.s a0, fa5, rtz
443; CHECK64ZFBFMIN-NEXT:    ret
444;
445; RV64ID-LABEL: fcvt_l_bf16:
446; RV64ID:       # %bb.0:
447; RV64ID-NEXT:    fmv.x.w a0, fa0
448; RV64ID-NEXT:    slli a0, a0, 16
449; RV64ID-NEXT:    fmv.w.x fa5, a0
450; RV64ID-NEXT:    fcvt.l.s a0, fa5, rtz
451; RV64ID-NEXT:    ret
452  %1 = fptosi bfloat %a to i64
453  ret i64 %1
454}
455
456define i64 @fcvt_l_bf16_sat(bfloat %a) nounwind {
457; RV32IZFBFMIN-LABEL: fcvt_l_bf16_sat:
458; RV32IZFBFMIN:       # %bb.0: # %start
459; RV32IZFBFMIN-NEXT:    addi sp, sp, -16
460; RV32IZFBFMIN-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
461; RV32IZFBFMIN-NEXT:    sw s0, 8(sp) # 4-byte Folded Spill
462; RV32IZFBFMIN-NEXT:    fsw fs0, 4(sp) # 4-byte Folded Spill
463; RV32IZFBFMIN-NEXT:    fcvt.s.bf16 fs0, fa0
464; RV32IZFBFMIN-NEXT:    lui a0, 913408
465; RV32IZFBFMIN-NEXT:    fmv.w.x fa5, a0
466; RV32IZFBFMIN-NEXT:    fle.s s0, fa5, fs0
467; RV32IZFBFMIN-NEXT:    fmv.s fa0, fs0
468; RV32IZFBFMIN-NEXT:    call __fixsfdi
469; RV32IZFBFMIN-NEXT:    lui a3, 524288
470; RV32IZFBFMIN-NEXT:    lui a2, 524288
471; RV32IZFBFMIN-NEXT:    beqz s0, .LBB10_2
472; RV32IZFBFMIN-NEXT:  # %bb.1: # %start
473; RV32IZFBFMIN-NEXT:    mv a2, a1
474; RV32IZFBFMIN-NEXT:  .LBB10_2: # %start
475; RV32IZFBFMIN-NEXT:    lui a1, %hi(.LCPI10_0)
476; RV32IZFBFMIN-NEXT:    flw fa5, %lo(.LCPI10_0)(a1)
477; RV32IZFBFMIN-NEXT:    flt.s a1, fa5, fs0
478; RV32IZFBFMIN-NEXT:    beqz a1, .LBB10_4
479; RV32IZFBFMIN-NEXT:  # %bb.3:
480; RV32IZFBFMIN-NEXT:    addi a2, a3, -1
481; RV32IZFBFMIN-NEXT:  .LBB10_4: # %start
482; RV32IZFBFMIN-NEXT:    feq.s a3, fs0, fs0
483; RV32IZFBFMIN-NEXT:    neg a4, a1
484; RV32IZFBFMIN-NEXT:    neg a1, s0
485; RV32IZFBFMIN-NEXT:    neg a3, a3
486; RV32IZFBFMIN-NEXT:    and a0, a1, a0
487; RV32IZFBFMIN-NEXT:    and a1, a3, a2
488; RV32IZFBFMIN-NEXT:    or a0, a4, a0
489; RV32IZFBFMIN-NEXT:    and a0, a3, a0
490; RV32IZFBFMIN-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
491; RV32IZFBFMIN-NEXT:    lw s0, 8(sp) # 4-byte Folded Reload
492; RV32IZFBFMIN-NEXT:    flw fs0, 4(sp) # 4-byte Folded Reload
493; RV32IZFBFMIN-NEXT:    addi sp, sp, 16
494; RV32IZFBFMIN-NEXT:    ret
495;
496; R32IDZFBFMIN-LABEL: fcvt_l_bf16_sat:
497; R32IDZFBFMIN:       # %bb.0: # %start
498; R32IDZFBFMIN-NEXT:    addi sp, sp, -16
499; R32IDZFBFMIN-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
500; R32IDZFBFMIN-NEXT:    sw s0, 8(sp) # 4-byte Folded Spill
501; R32IDZFBFMIN-NEXT:    fsd fs0, 0(sp) # 8-byte Folded Spill
502; R32IDZFBFMIN-NEXT:    fcvt.s.bf16 fs0, fa0
503; R32IDZFBFMIN-NEXT:    lui a0, 913408
504; R32IDZFBFMIN-NEXT:    fmv.w.x fa5, a0
505; R32IDZFBFMIN-NEXT:    fle.s s0, fa5, fs0
506; R32IDZFBFMIN-NEXT:    fmv.s fa0, fs0
507; R32IDZFBFMIN-NEXT:    call __fixsfdi
508; R32IDZFBFMIN-NEXT:    lui a3, 524288
509; R32IDZFBFMIN-NEXT:    lui a2, 524288
510; R32IDZFBFMIN-NEXT:    beqz s0, .LBB10_2
511; R32IDZFBFMIN-NEXT:  # %bb.1: # %start
512; R32IDZFBFMIN-NEXT:    mv a2, a1
513; R32IDZFBFMIN-NEXT:  .LBB10_2: # %start
514; R32IDZFBFMIN-NEXT:    lui a1, %hi(.LCPI10_0)
515; R32IDZFBFMIN-NEXT:    flw fa5, %lo(.LCPI10_0)(a1)
516; R32IDZFBFMIN-NEXT:    flt.s a1, fa5, fs0
517; R32IDZFBFMIN-NEXT:    beqz a1, .LBB10_4
518; R32IDZFBFMIN-NEXT:  # %bb.3:
519; R32IDZFBFMIN-NEXT:    addi a2, a3, -1
520; R32IDZFBFMIN-NEXT:  .LBB10_4: # %start
521; R32IDZFBFMIN-NEXT:    feq.s a3, fs0, fs0
522; R32IDZFBFMIN-NEXT:    neg a4, a1
523; R32IDZFBFMIN-NEXT:    neg a1, s0
524; R32IDZFBFMIN-NEXT:    neg a3, a3
525; R32IDZFBFMIN-NEXT:    and a0, a1, a0
526; R32IDZFBFMIN-NEXT:    and a1, a3, a2
527; R32IDZFBFMIN-NEXT:    or a0, a4, a0
528; R32IDZFBFMIN-NEXT:    and a0, a3, a0
529; R32IDZFBFMIN-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
530; R32IDZFBFMIN-NEXT:    lw s0, 8(sp) # 4-byte Folded Reload
531; R32IDZFBFMIN-NEXT:    fld fs0, 0(sp) # 8-byte Folded Reload
532; R32IDZFBFMIN-NEXT:    addi sp, sp, 16
533; R32IDZFBFMIN-NEXT:    ret
534;
535; RV32ID-LABEL: fcvt_l_bf16_sat:
536; RV32ID:       # %bb.0: # %start
537; RV32ID-NEXT:    addi sp, sp, -16
538; RV32ID-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
539; RV32ID-NEXT:    sw s0, 8(sp) # 4-byte Folded Spill
540; RV32ID-NEXT:    fsd fs0, 0(sp) # 8-byte Folded Spill
541; RV32ID-NEXT:    fmv.x.w a0, fa0
542; RV32ID-NEXT:    slli a0, a0, 16
543; RV32ID-NEXT:    fmv.w.x fs0, a0
544; RV32ID-NEXT:    lui a0, 913408
545; RV32ID-NEXT:    fmv.w.x fa5, a0
546; RV32ID-NEXT:    fle.s s0, fa5, fs0
547; RV32ID-NEXT:    fmv.s fa0, fs0
548; RV32ID-NEXT:    call __fixsfdi
549; RV32ID-NEXT:    lui a3, 524288
550; RV32ID-NEXT:    lui a2, 524288
551; RV32ID-NEXT:    beqz s0, .LBB10_2
552; RV32ID-NEXT:  # %bb.1: # %start
553; RV32ID-NEXT:    mv a2, a1
554; RV32ID-NEXT:  .LBB10_2: # %start
555; RV32ID-NEXT:    lui a1, %hi(.LCPI10_0)
556; RV32ID-NEXT:    flw fa5, %lo(.LCPI10_0)(a1)
557; RV32ID-NEXT:    flt.s a1, fa5, fs0
558; RV32ID-NEXT:    beqz a1, .LBB10_4
559; RV32ID-NEXT:  # %bb.3:
560; RV32ID-NEXT:    addi a2, a3, -1
561; RV32ID-NEXT:  .LBB10_4: # %start
562; RV32ID-NEXT:    feq.s a3, fs0, fs0
563; RV32ID-NEXT:    neg a4, a1
564; RV32ID-NEXT:    neg a1, s0
565; RV32ID-NEXT:    neg a3, a3
566; RV32ID-NEXT:    and a0, a1, a0
567; RV32ID-NEXT:    and a1, a3, a2
568; RV32ID-NEXT:    or a0, a4, a0
569; RV32ID-NEXT:    and a0, a3, a0
570; RV32ID-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
571; RV32ID-NEXT:    lw s0, 8(sp) # 4-byte Folded Reload
572; RV32ID-NEXT:    fld fs0, 0(sp) # 8-byte Folded Reload
573; RV32ID-NEXT:    addi sp, sp, 16
574; RV32ID-NEXT:    ret
575;
576; CHECK64ZFBFMIN-LABEL: fcvt_l_bf16_sat:
577; CHECK64ZFBFMIN:       # %bb.0: # %start
578; CHECK64ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
579; CHECK64ZFBFMIN-NEXT:    fcvt.l.s a0, fa5, rtz
580; CHECK64ZFBFMIN-NEXT:    feq.s a1, fa5, fa5
581; CHECK64ZFBFMIN-NEXT:    seqz a1, a1
582; CHECK64ZFBFMIN-NEXT:    addi a1, a1, -1
583; CHECK64ZFBFMIN-NEXT:    and a0, a1, a0
584; CHECK64ZFBFMIN-NEXT:    ret
585;
586; RV64ID-LABEL: fcvt_l_bf16_sat:
587; RV64ID:       # %bb.0: # %start
588; RV64ID-NEXT:    fmv.x.w a0, fa0
589; RV64ID-NEXT:    slli a0, a0, 16
590; RV64ID-NEXT:    fmv.w.x fa5, a0
591; RV64ID-NEXT:    fcvt.l.s a0, fa5, rtz
592; RV64ID-NEXT:    feq.s a1, fa5, fa5
593; RV64ID-NEXT:    seqz a1, a1
594; RV64ID-NEXT:    addi a1, a1, -1
595; RV64ID-NEXT:    and a0, a1, a0
596; RV64ID-NEXT:    ret
597start:
598  %0 = tail call i64 @llvm.fptosi.sat.i64.bf16(bfloat %a)
599  ret i64 %0
600}
601declare i64 @llvm.fptosi.sat.i64.bf16(bfloat)
602
603define i64 @fcvt_lu_bf16(bfloat %a) nounwind {
604; CHECK32ZFBFMIN-LABEL: fcvt_lu_bf16:
605; CHECK32ZFBFMIN:       # %bb.0:
606; CHECK32ZFBFMIN-NEXT:    addi sp, sp, -16
607; CHECK32ZFBFMIN-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
608; CHECK32ZFBFMIN-NEXT:    fcvt.s.bf16 fa0, fa0
609; CHECK32ZFBFMIN-NEXT:    call __fixunssfdi
610; CHECK32ZFBFMIN-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
611; CHECK32ZFBFMIN-NEXT:    addi sp, sp, 16
612; CHECK32ZFBFMIN-NEXT:    ret
613;
614; RV32ID-LABEL: fcvt_lu_bf16:
615; RV32ID:       # %bb.0:
616; RV32ID-NEXT:    addi sp, sp, -16
617; RV32ID-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
618; RV32ID-NEXT:    fmv.x.w a0, fa0
619; RV32ID-NEXT:    slli a0, a0, 16
620; RV32ID-NEXT:    fmv.w.x fa0, a0
621; RV32ID-NEXT:    call __fixunssfdi
622; RV32ID-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
623; RV32ID-NEXT:    addi sp, sp, 16
624; RV32ID-NEXT:    ret
625;
626; CHECK64ZFBFMIN-LABEL: fcvt_lu_bf16:
627; CHECK64ZFBFMIN:       # %bb.0:
628; CHECK64ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
629; CHECK64ZFBFMIN-NEXT:    fcvt.lu.s a0, fa5, rtz
630; CHECK64ZFBFMIN-NEXT:    ret
631;
632; RV64ID-LABEL: fcvt_lu_bf16:
633; RV64ID:       # %bb.0:
634; RV64ID-NEXT:    fmv.x.w a0, fa0
635; RV64ID-NEXT:    slli a0, a0, 16
636; RV64ID-NEXT:    fmv.w.x fa5, a0
637; RV64ID-NEXT:    fcvt.lu.s a0, fa5, rtz
638; RV64ID-NEXT:    ret
639  %1 = fptoui bfloat %a to i64
640  ret i64 %1
641}
642
643define i64 @fcvt_lu_bf16_sat(bfloat %a) nounwind {
644; CHECK32ZFBFMIN-LABEL: fcvt_lu_bf16_sat:
645; CHECK32ZFBFMIN:       # %bb.0: # %start
646; CHECK32ZFBFMIN-NEXT:    addi sp, sp, -16
647; CHECK32ZFBFMIN-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
648; CHECK32ZFBFMIN-NEXT:    sw s0, 8(sp) # 4-byte Folded Spill
649; CHECK32ZFBFMIN-NEXT:    sw s1, 4(sp) # 4-byte Folded Spill
650; CHECK32ZFBFMIN-NEXT:    lui a0, %hi(.LCPI12_0)
651; CHECK32ZFBFMIN-NEXT:    flw fa5, %lo(.LCPI12_0)(a0)
652; CHECK32ZFBFMIN-NEXT:    fcvt.s.bf16 fa0, fa0
653; CHECK32ZFBFMIN-NEXT:    fmv.w.x fa4, zero
654; CHECK32ZFBFMIN-NEXT:    fle.s a0, fa4, fa0
655; CHECK32ZFBFMIN-NEXT:    flt.s a1, fa5, fa0
656; CHECK32ZFBFMIN-NEXT:    neg s0, a1
657; CHECK32ZFBFMIN-NEXT:    neg s1, a0
658; CHECK32ZFBFMIN-NEXT:    call __fixunssfdi
659; CHECK32ZFBFMIN-NEXT:    and a0, s1, a0
660; CHECK32ZFBFMIN-NEXT:    and a1, s1, a1
661; CHECK32ZFBFMIN-NEXT:    or a0, s0, a0
662; CHECK32ZFBFMIN-NEXT:    or a1, s0, a1
663; CHECK32ZFBFMIN-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
664; CHECK32ZFBFMIN-NEXT:    lw s0, 8(sp) # 4-byte Folded Reload
665; CHECK32ZFBFMIN-NEXT:    lw s1, 4(sp) # 4-byte Folded Reload
666; CHECK32ZFBFMIN-NEXT:    addi sp, sp, 16
667; CHECK32ZFBFMIN-NEXT:    ret
668;
669; RV32ID-LABEL: fcvt_lu_bf16_sat:
670; RV32ID:       # %bb.0: # %start
671; RV32ID-NEXT:    addi sp, sp, -16
672; RV32ID-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
673; RV32ID-NEXT:    sw s0, 8(sp) # 4-byte Folded Spill
674; RV32ID-NEXT:    sw s1, 4(sp) # 4-byte Folded Spill
675; RV32ID-NEXT:    fmv.x.w a0, fa0
676; RV32ID-NEXT:    lui a1, %hi(.LCPI12_0)
677; RV32ID-NEXT:    fmv.w.x fa5, zero
678; RV32ID-NEXT:    flw fa4, %lo(.LCPI12_0)(a1)
679; RV32ID-NEXT:    slli a0, a0, 16
680; RV32ID-NEXT:    fmv.w.x fa0, a0
681; RV32ID-NEXT:    fle.s a0, fa5, fa0
682; RV32ID-NEXT:    flt.s a1, fa4, fa0
683; RV32ID-NEXT:    neg s0, a1
684; RV32ID-NEXT:    neg s1, a0
685; RV32ID-NEXT:    call __fixunssfdi
686; RV32ID-NEXT:    and a0, s1, a0
687; RV32ID-NEXT:    and a1, s1, a1
688; RV32ID-NEXT:    or a0, s0, a0
689; RV32ID-NEXT:    or a1, s0, a1
690; RV32ID-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
691; RV32ID-NEXT:    lw s0, 8(sp) # 4-byte Folded Reload
692; RV32ID-NEXT:    lw s1, 4(sp) # 4-byte Folded Reload
693; RV32ID-NEXT:    addi sp, sp, 16
694; RV32ID-NEXT:    ret
695;
696; CHECK64ZFBFMIN-LABEL: fcvt_lu_bf16_sat:
697; CHECK64ZFBFMIN:       # %bb.0: # %start
698; CHECK64ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
699; CHECK64ZFBFMIN-NEXT:    fcvt.lu.s a0, fa5, rtz
700; CHECK64ZFBFMIN-NEXT:    feq.s a1, fa5, fa5
701; CHECK64ZFBFMIN-NEXT:    seqz a1, a1
702; CHECK64ZFBFMIN-NEXT:    addi a1, a1, -1
703; CHECK64ZFBFMIN-NEXT:    and a0, a1, a0
704; CHECK64ZFBFMIN-NEXT:    ret
705;
706; RV64ID-LABEL: fcvt_lu_bf16_sat:
707; RV64ID:       # %bb.0: # %start
708; RV64ID-NEXT:    fmv.x.w a0, fa0
709; RV64ID-NEXT:    slli a0, a0, 16
710; RV64ID-NEXT:    fmv.w.x fa5, a0
711; RV64ID-NEXT:    fcvt.lu.s a0, fa5, rtz
712; RV64ID-NEXT:    feq.s a1, fa5, fa5
713; RV64ID-NEXT:    seqz a1, a1
714; RV64ID-NEXT:    addi a1, a1, -1
715; RV64ID-NEXT:    and a0, a1, a0
716; RV64ID-NEXT:    ret
717start:
718  %0 = tail call i64 @llvm.fptoui.sat.i64.bf16(bfloat %a)
719  ret i64 %0
720}
721declare i64 @llvm.fptoui.sat.i64.bf16(bfloat)
722
723define bfloat @fcvt_bf16_si(i16 %a) nounwind {
724; CHECK32ZFBFMIN-LABEL: fcvt_bf16_si:
725; CHECK32ZFBFMIN:       # %bb.0:
726; CHECK32ZFBFMIN-NEXT:    slli a0, a0, 16
727; CHECK32ZFBFMIN-NEXT:    srai a0, a0, 16
728; CHECK32ZFBFMIN-NEXT:    fcvt.s.w fa5, a0
729; CHECK32ZFBFMIN-NEXT:    fcvt.bf16.s fa0, fa5
730; CHECK32ZFBFMIN-NEXT:    ret
731;
732; RV32ID-LABEL: fcvt_bf16_si:
733; RV32ID:       # %bb.0:
734; RV32ID-NEXT:    addi sp, sp, -16
735; RV32ID-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
736; RV32ID-NEXT:    slli a0, a0, 16
737; RV32ID-NEXT:    srai a0, a0, 16
738; RV32ID-NEXT:    fcvt.s.w fa0, a0
739; RV32ID-NEXT:    call __truncsfbf2
740; RV32ID-NEXT:    fmv.x.w a0, fa0
741; RV32ID-NEXT:    lui a1, 1048560
742; RV32ID-NEXT:    or a0, a0, a1
743; RV32ID-NEXT:    fmv.w.x fa0, a0
744; RV32ID-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
745; RV32ID-NEXT:    addi sp, sp, 16
746; RV32ID-NEXT:    ret
747;
748; CHECK64ZFBFMIN-LABEL: fcvt_bf16_si:
749; CHECK64ZFBFMIN:       # %bb.0:
750; CHECK64ZFBFMIN-NEXT:    slli a0, a0, 48
751; CHECK64ZFBFMIN-NEXT:    srai a0, a0, 48
752; CHECK64ZFBFMIN-NEXT:    fcvt.s.w fa5, a0
753; CHECK64ZFBFMIN-NEXT:    fcvt.bf16.s fa0, fa5
754; CHECK64ZFBFMIN-NEXT:    ret
755;
756; RV64ID-LABEL: fcvt_bf16_si:
757; RV64ID:       # %bb.0:
758; RV64ID-NEXT:    addi sp, sp, -16
759; RV64ID-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
760; RV64ID-NEXT:    slli a0, a0, 48
761; RV64ID-NEXT:    srai a0, a0, 48
762; RV64ID-NEXT:    fcvt.s.w fa0, a0
763; RV64ID-NEXT:    call __truncsfbf2
764; RV64ID-NEXT:    fmv.x.w a0, fa0
765; RV64ID-NEXT:    lui a1, 1048560
766; RV64ID-NEXT:    or a0, a0, a1
767; RV64ID-NEXT:    fmv.w.x fa0, a0
768; RV64ID-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
769; RV64ID-NEXT:    addi sp, sp, 16
770; RV64ID-NEXT:    ret
771  %1 = sitofp i16 %a to bfloat
772  ret bfloat %1
773}
774
775define bfloat @fcvt_bf16_si_signext(i16 signext %a) nounwind {
776; CHECK32ZFBFMIN-LABEL: fcvt_bf16_si_signext:
777; CHECK32ZFBFMIN:       # %bb.0:
778; CHECK32ZFBFMIN-NEXT:    fcvt.s.w fa5, a0
779; CHECK32ZFBFMIN-NEXT:    fcvt.bf16.s fa0, fa5
780; CHECK32ZFBFMIN-NEXT:    ret
781;
782; RV32ID-LABEL: fcvt_bf16_si_signext:
783; RV32ID:       # %bb.0:
784; RV32ID-NEXT:    addi sp, sp, -16
785; RV32ID-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
786; RV32ID-NEXT:    fcvt.s.w fa0, a0
787; RV32ID-NEXT:    call __truncsfbf2
788; RV32ID-NEXT:    fmv.x.w a0, fa0
789; RV32ID-NEXT:    lui a1, 1048560
790; RV32ID-NEXT:    or a0, a0, a1
791; RV32ID-NEXT:    fmv.w.x fa0, a0
792; RV32ID-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
793; RV32ID-NEXT:    addi sp, sp, 16
794; RV32ID-NEXT:    ret
795;
796; CHECK64ZFBFMIN-LABEL: fcvt_bf16_si_signext:
797; CHECK64ZFBFMIN:       # %bb.0:
798; CHECK64ZFBFMIN-NEXT:    fcvt.s.w fa5, a0
799; CHECK64ZFBFMIN-NEXT:    fcvt.bf16.s fa0, fa5
800; CHECK64ZFBFMIN-NEXT:    ret
801;
802; RV64ID-LABEL: fcvt_bf16_si_signext:
803; RV64ID:       # %bb.0:
804; RV64ID-NEXT:    addi sp, sp, -16
805; RV64ID-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
806; RV64ID-NEXT:    fcvt.s.w fa0, a0
807; RV64ID-NEXT:    call __truncsfbf2
808; RV64ID-NEXT:    fmv.x.w a0, fa0
809; RV64ID-NEXT:    lui a1, 1048560
810; RV64ID-NEXT:    or a0, a0, a1
811; RV64ID-NEXT:    fmv.w.x fa0, a0
812; RV64ID-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
813; RV64ID-NEXT:    addi sp, sp, 16
814; RV64ID-NEXT:    ret
815  %1 = sitofp i16 %a to bfloat
816  ret bfloat %1
817}
818
819define bfloat @fcvt_bf16_ui(i16 %a) nounwind {
820; CHECK32ZFBFMIN-LABEL: fcvt_bf16_ui:
821; CHECK32ZFBFMIN:       # %bb.0:
822; CHECK32ZFBFMIN-NEXT:    slli a0, a0, 16
823; CHECK32ZFBFMIN-NEXT:    srli a0, a0, 16
824; CHECK32ZFBFMIN-NEXT:    fcvt.s.wu fa5, a0
825; CHECK32ZFBFMIN-NEXT:    fcvt.bf16.s fa0, fa5
826; CHECK32ZFBFMIN-NEXT:    ret
827;
828; RV32ID-LABEL: fcvt_bf16_ui:
829; RV32ID:       # %bb.0:
830; RV32ID-NEXT:    addi sp, sp, -16
831; RV32ID-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
832; RV32ID-NEXT:    slli a0, a0, 16
833; RV32ID-NEXT:    srli a0, a0, 16
834; RV32ID-NEXT:    fcvt.s.wu fa0, a0
835; RV32ID-NEXT:    call __truncsfbf2
836; RV32ID-NEXT:    fmv.x.w a0, fa0
837; RV32ID-NEXT:    lui a1, 1048560
838; RV32ID-NEXT:    or a0, a0, a1
839; RV32ID-NEXT:    fmv.w.x fa0, a0
840; RV32ID-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
841; RV32ID-NEXT:    addi sp, sp, 16
842; RV32ID-NEXT:    ret
843;
844; CHECK64ZFBFMIN-LABEL: fcvt_bf16_ui:
845; CHECK64ZFBFMIN:       # %bb.0:
846; CHECK64ZFBFMIN-NEXT:    slli a0, a0, 48
847; CHECK64ZFBFMIN-NEXT:    srli a0, a0, 48
848; CHECK64ZFBFMIN-NEXT:    fcvt.s.wu fa5, a0
849; CHECK64ZFBFMIN-NEXT:    fcvt.bf16.s fa0, fa5
850; CHECK64ZFBFMIN-NEXT:    ret
851;
852; RV64ID-LABEL: fcvt_bf16_ui:
853; RV64ID:       # %bb.0:
854; RV64ID-NEXT:    addi sp, sp, -16
855; RV64ID-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
856; RV64ID-NEXT:    slli a0, a0, 48
857; RV64ID-NEXT:    srli a0, a0, 48
858; RV64ID-NEXT:    fcvt.s.wu fa0, a0
859; RV64ID-NEXT:    call __truncsfbf2
860; RV64ID-NEXT:    fmv.x.w a0, fa0
861; RV64ID-NEXT:    lui a1, 1048560
862; RV64ID-NEXT:    or a0, a0, a1
863; RV64ID-NEXT:    fmv.w.x fa0, a0
864; RV64ID-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
865; RV64ID-NEXT:    addi sp, sp, 16
866; RV64ID-NEXT:    ret
867  %1 = uitofp i16 %a to bfloat
868  ret bfloat %1
869}
870
871define bfloat @fcvt_bf16_ui_zeroext(i16 zeroext %a) nounwind {
872; CHECK32ZFBFMIN-LABEL: fcvt_bf16_ui_zeroext:
873; CHECK32ZFBFMIN:       # %bb.0:
874; CHECK32ZFBFMIN-NEXT:    fcvt.s.wu fa5, a0
875; CHECK32ZFBFMIN-NEXT:    fcvt.bf16.s fa0, fa5
876; CHECK32ZFBFMIN-NEXT:    ret
877;
878; RV32ID-LABEL: fcvt_bf16_ui_zeroext:
879; RV32ID:       # %bb.0:
880; RV32ID-NEXT:    addi sp, sp, -16
881; RV32ID-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
882; RV32ID-NEXT:    fcvt.s.wu fa0, a0
883; RV32ID-NEXT:    call __truncsfbf2
884; RV32ID-NEXT:    fmv.x.w a0, fa0
885; RV32ID-NEXT:    lui a1, 1048560
886; RV32ID-NEXT:    or a0, a0, a1
887; RV32ID-NEXT:    fmv.w.x fa0, a0
888; RV32ID-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
889; RV32ID-NEXT:    addi sp, sp, 16
890; RV32ID-NEXT:    ret
891;
892; CHECK64ZFBFMIN-LABEL: fcvt_bf16_ui_zeroext:
893; CHECK64ZFBFMIN:       # %bb.0:
894; CHECK64ZFBFMIN-NEXT:    fcvt.s.wu fa5, a0
895; CHECK64ZFBFMIN-NEXT:    fcvt.bf16.s fa0, fa5
896; CHECK64ZFBFMIN-NEXT:    ret
897;
898; RV64ID-LABEL: fcvt_bf16_ui_zeroext:
899; RV64ID:       # %bb.0:
900; RV64ID-NEXT:    addi sp, sp, -16
901; RV64ID-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
902; RV64ID-NEXT:    fcvt.s.wu fa0, a0
903; RV64ID-NEXT:    call __truncsfbf2
904; RV64ID-NEXT:    fmv.x.w a0, fa0
905; RV64ID-NEXT:    lui a1, 1048560
906; RV64ID-NEXT:    or a0, a0, a1
907; RV64ID-NEXT:    fmv.w.x fa0, a0
908; RV64ID-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
909; RV64ID-NEXT:    addi sp, sp, 16
910; RV64ID-NEXT:    ret
911  %1 = uitofp i16 %a to bfloat
912  ret bfloat %1
913}
914
915define bfloat @fcvt_bf16_w(i32 %a) nounwind {
916; CHECK32ZFBFMIN-LABEL: fcvt_bf16_w:
917; CHECK32ZFBFMIN:       # %bb.0:
918; CHECK32ZFBFMIN-NEXT:    fcvt.s.w fa5, a0
919; CHECK32ZFBFMIN-NEXT:    fcvt.bf16.s fa0, fa5
920; CHECK32ZFBFMIN-NEXT:    ret
921;
922; RV32ID-LABEL: fcvt_bf16_w:
923; RV32ID:       # %bb.0:
924; RV32ID-NEXT:    addi sp, sp, -16
925; RV32ID-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
926; RV32ID-NEXT:    fcvt.s.w fa0, a0
927; RV32ID-NEXT:    call __truncsfbf2
928; RV32ID-NEXT:    fmv.x.w a0, fa0
929; RV32ID-NEXT:    lui a1, 1048560
930; RV32ID-NEXT:    or a0, a0, a1
931; RV32ID-NEXT:    fmv.w.x fa0, a0
932; RV32ID-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
933; RV32ID-NEXT:    addi sp, sp, 16
934; RV32ID-NEXT:    ret
935;
936; CHECK64ZFBFMIN-LABEL: fcvt_bf16_w:
937; CHECK64ZFBFMIN:       # %bb.0:
938; CHECK64ZFBFMIN-NEXT:    fcvt.s.w fa5, a0
939; CHECK64ZFBFMIN-NEXT:    fcvt.bf16.s fa0, fa5
940; CHECK64ZFBFMIN-NEXT:    ret
941;
942; RV64ID-LABEL: fcvt_bf16_w:
943; RV64ID:       # %bb.0:
944; RV64ID-NEXT:    addi sp, sp, -16
945; RV64ID-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
946; RV64ID-NEXT:    fcvt.s.w fa0, a0
947; RV64ID-NEXT:    call __truncsfbf2
948; RV64ID-NEXT:    fmv.x.w a0, fa0
949; RV64ID-NEXT:    lui a1, 1048560
950; RV64ID-NEXT:    or a0, a0, a1
951; RV64ID-NEXT:    fmv.w.x fa0, a0
952; RV64ID-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
953; RV64ID-NEXT:    addi sp, sp, 16
954; RV64ID-NEXT:    ret
955  %1 = sitofp i32 %a to bfloat
956  ret bfloat %1
957}
958
959define bfloat @fcvt_bf16_w_load(ptr %p) nounwind {
960; CHECK32ZFBFMIN-LABEL: fcvt_bf16_w_load:
961; CHECK32ZFBFMIN:       # %bb.0:
962; CHECK32ZFBFMIN-NEXT:    lw a0, 0(a0)
963; CHECK32ZFBFMIN-NEXT:    fcvt.s.w fa5, a0
964; CHECK32ZFBFMIN-NEXT:    fcvt.bf16.s fa0, fa5
965; CHECK32ZFBFMIN-NEXT:    ret
966;
967; RV32ID-LABEL: fcvt_bf16_w_load:
968; RV32ID:       # %bb.0:
969; RV32ID-NEXT:    addi sp, sp, -16
970; RV32ID-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
971; RV32ID-NEXT:    lw a0, 0(a0)
972; RV32ID-NEXT:    fcvt.s.w fa0, a0
973; RV32ID-NEXT:    call __truncsfbf2
974; RV32ID-NEXT:    fmv.x.w a0, fa0
975; RV32ID-NEXT:    lui a1, 1048560
976; RV32ID-NEXT:    or a0, a0, a1
977; RV32ID-NEXT:    fmv.w.x fa0, a0
978; RV32ID-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
979; RV32ID-NEXT:    addi sp, sp, 16
980; RV32ID-NEXT:    ret
981;
982; CHECK64ZFBFMIN-LABEL: fcvt_bf16_w_load:
983; CHECK64ZFBFMIN:       # %bb.0:
984; CHECK64ZFBFMIN-NEXT:    lw a0, 0(a0)
985; CHECK64ZFBFMIN-NEXT:    fcvt.s.w fa5, a0
986; CHECK64ZFBFMIN-NEXT:    fcvt.bf16.s fa0, fa5
987; CHECK64ZFBFMIN-NEXT:    ret
988;
989; RV64ID-LABEL: fcvt_bf16_w_load:
990; RV64ID:       # %bb.0:
991; RV64ID-NEXT:    addi sp, sp, -16
992; RV64ID-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
993; RV64ID-NEXT:    lw a0, 0(a0)
994; RV64ID-NEXT:    fcvt.s.w fa0, a0
995; RV64ID-NEXT:    call __truncsfbf2
996; RV64ID-NEXT:    fmv.x.w a0, fa0
997; RV64ID-NEXT:    lui a1, 1048560
998; RV64ID-NEXT:    or a0, a0, a1
999; RV64ID-NEXT:    fmv.w.x fa0, a0
1000; RV64ID-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
1001; RV64ID-NEXT:    addi sp, sp, 16
1002; RV64ID-NEXT:    ret
1003  %a = load i32, ptr %p
1004  %1 = sitofp i32 %a to bfloat
1005  ret bfloat %1
1006}
1007
1008define bfloat @fcvt_bf16_wu(i32 %a) nounwind {
1009; CHECK32ZFBFMIN-LABEL: fcvt_bf16_wu:
1010; CHECK32ZFBFMIN:       # %bb.0:
1011; CHECK32ZFBFMIN-NEXT:    fcvt.s.wu fa5, a0
1012; CHECK32ZFBFMIN-NEXT:    fcvt.bf16.s fa0, fa5
1013; CHECK32ZFBFMIN-NEXT:    ret
1014;
1015; RV32ID-LABEL: fcvt_bf16_wu:
1016; RV32ID:       # %bb.0:
1017; RV32ID-NEXT:    addi sp, sp, -16
1018; RV32ID-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
1019; RV32ID-NEXT:    fcvt.s.wu fa0, a0
1020; RV32ID-NEXT:    call __truncsfbf2
1021; RV32ID-NEXT:    fmv.x.w a0, fa0
1022; RV32ID-NEXT:    lui a1, 1048560
1023; RV32ID-NEXT:    or a0, a0, a1
1024; RV32ID-NEXT:    fmv.w.x fa0, a0
1025; RV32ID-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
1026; RV32ID-NEXT:    addi sp, sp, 16
1027; RV32ID-NEXT:    ret
1028;
1029; CHECK64ZFBFMIN-LABEL: fcvt_bf16_wu:
1030; CHECK64ZFBFMIN:       # %bb.0:
1031; CHECK64ZFBFMIN-NEXT:    fcvt.s.wu fa5, a0
1032; CHECK64ZFBFMIN-NEXT:    fcvt.bf16.s fa0, fa5
1033; CHECK64ZFBFMIN-NEXT:    ret
1034;
1035; RV64ID-LABEL: fcvt_bf16_wu:
1036; RV64ID:       # %bb.0:
1037; RV64ID-NEXT:    addi sp, sp, -16
1038; RV64ID-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
1039; RV64ID-NEXT:    fcvt.s.wu fa0, a0
1040; RV64ID-NEXT:    call __truncsfbf2
1041; RV64ID-NEXT:    fmv.x.w a0, fa0
1042; RV64ID-NEXT:    lui a1, 1048560
1043; RV64ID-NEXT:    or a0, a0, a1
1044; RV64ID-NEXT:    fmv.w.x fa0, a0
1045; RV64ID-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
1046; RV64ID-NEXT:    addi sp, sp, 16
1047; RV64ID-NEXT:    ret
1048  %1 = uitofp i32 %a to bfloat
1049  ret bfloat %1
1050}
1051
1052define bfloat @fcvt_bf16_wu_load(ptr %p) nounwind {
1053; CHECK32ZFBFMIN-LABEL: fcvt_bf16_wu_load:
1054; CHECK32ZFBFMIN:       # %bb.0:
1055; CHECK32ZFBFMIN-NEXT:    lw a0, 0(a0)
1056; CHECK32ZFBFMIN-NEXT:    fcvt.s.wu fa5, a0
1057; CHECK32ZFBFMIN-NEXT:    fcvt.bf16.s fa0, fa5
1058; CHECK32ZFBFMIN-NEXT:    ret
1059;
1060; RV32ID-LABEL: fcvt_bf16_wu_load:
1061; RV32ID:       # %bb.0:
1062; RV32ID-NEXT:    addi sp, sp, -16
1063; RV32ID-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
1064; RV32ID-NEXT:    lw a0, 0(a0)
1065; RV32ID-NEXT:    fcvt.s.wu fa0, a0
1066; RV32ID-NEXT:    call __truncsfbf2
1067; RV32ID-NEXT:    fmv.x.w a0, fa0
1068; RV32ID-NEXT:    lui a1, 1048560
1069; RV32ID-NEXT:    or a0, a0, a1
1070; RV32ID-NEXT:    fmv.w.x fa0, a0
1071; RV32ID-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
1072; RV32ID-NEXT:    addi sp, sp, 16
1073; RV32ID-NEXT:    ret
1074;
1075; CHECK64ZFBFMIN-LABEL: fcvt_bf16_wu_load:
1076; CHECK64ZFBFMIN:       # %bb.0:
1077; CHECK64ZFBFMIN-NEXT:    lwu a0, 0(a0)
1078; CHECK64ZFBFMIN-NEXT:    fcvt.s.wu fa5, a0
1079; CHECK64ZFBFMIN-NEXT:    fcvt.bf16.s fa0, fa5
1080; CHECK64ZFBFMIN-NEXT:    ret
1081;
1082; RV64ID-LABEL: fcvt_bf16_wu_load:
1083; RV64ID:       # %bb.0:
1084; RV64ID-NEXT:    addi sp, sp, -16
1085; RV64ID-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
1086; RV64ID-NEXT:    lwu a0, 0(a0)
1087; RV64ID-NEXT:    fcvt.s.wu fa0, a0
1088; RV64ID-NEXT:    call __truncsfbf2
1089; RV64ID-NEXT:    fmv.x.w a0, fa0
1090; RV64ID-NEXT:    lui a1, 1048560
1091; RV64ID-NEXT:    or a0, a0, a1
1092; RV64ID-NEXT:    fmv.w.x fa0, a0
1093; RV64ID-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
1094; RV64ID-NEXT:    addi sp, sp, 16
1095; RV64ID-NEXT:    ret
1096  %a = load i32, ptr %p
1097  %1 = uitofp i32 %a to bfloat
1098  ret bfloat %1
1099}
1100
1101; TODO: The following tests error on rv32 with zfbfmin enabled.
1102
1103; define bfloat @fcvt_bf16_l(i64 %a) nounwind {
1104;   %1 = sitofp i64 %a to bfloat
1105;   ret bfloat %1
1106; }
1107
1108; define bfloat @fcvt_bf16_lu(i64 %a) nounwind {
1109;   %1 = uitofp i64 %a to bfloat
1110;   ret bfloat %1
1111; }
1112
1113define bfloat @fcvt_bf16_s(float %a) nounwind {
1114; CHECK32ZFBFMIN-LABEL: fcvt_bf16_s:
1115; CHECK32ZFBFMIN:       # %bb.0:
1116; CHECK32ZFBFMIN-NEXT:    fcvt.bf16.s fa0, fa0
1117; CHECK32ZFBFMIN-NEXT:    ret
1118;
1119; RV32ID-LABEL: fcvt_bf16_s:
1120; RV32ID:       # %bb.0:
1121; RV32ID-NEXT:    addi sp, sp, -16
1122; RV32ID-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
1123; RV32ID-NEXT:    call __truncsfbf2
1124; RV32ID-NEXT:    fmv.x.w a0, fa0
1125; RV32ID-NEXT:    lui a1, 1048560
1126; RV32ID-NEXT:    or a0, a0, a1
1127; RV32ID-NEXT:    fmv.w.x fa0, a0
1128; RV32ID-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
1129; RV32ID-NEXT:    addi sp, sp, 16
1130; RV32ID-NEXT:    ret
1131;
1132; CHECK64ZFBFMIN-LABEL: fcvt_bf16_s:
1133; CHECK64ZFBFMIN:       # %bb.0:
1134; CHECK64ZFBFMIN-NEXT:    fcvt.bf16.s fa0, fa0
1135; CHECK64ZFBFMIN-NEXT:    ret
1136;
1137; RV64ID-LABEL: fcvt_bf16_s:
1138; RV64ID:       # %bb.0:
1139; RV64ID-NEXT:    addi sp, sp, -16
1140; RV64ID-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
1141; RV64ID-NEXT:    call __truncsfbf2
1142; RV64ID-NEXT:    fmv.x.w a0, fa0
1143; RV64ID-NEXT:    lui a1, 1048560
1144; RV64ID-NEXT:    or a0, a0, a1
1145; RV64ID-NEXT:    fmv.w.x fa0, a0
1146; RV64ID-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
1147; RV64ID-NEXT:    addi sp, sp, 16
1148; RV64ID-NEXT:    ret
1149  %1 = fptrunc float %a to bfloat
1150  ret bfloat %1
1151}
1152
1153define float @fcvt_s_bf16(bfloat %a) nounwind {
1154; CHECK32ZFBFMIN-LABEL: fcvt_s_bf16:
1155; CHECK32ZFBFMIN:       # %bb.0:
1156; CHECK32ZFBFMIN-NEXT:    fcvt.s.bf16 fa0, fa0
1157; CHECK32ZFBFMIN-NEXT:    ret
1158;
1159; RV32ID-LABEL: fcvt_s_bf16:
1160; RV32ID:       # %bb.0:
1161; RV32ID-NEXT:    fmv.x.w a0, fa0
1162; RV32ID-NEXT:    slli a0, a0, 16
1163; RV32ID-NEXT:    fmv.w.x fa0, a0
1164; RV32ID-NEXT:    ret
1165;
1166; CHECK64ZFBFMIN-LABEL: fcvt_s_bf16:
1167; CHECK64ZFBFMIN:       # %bb.0:
1168; CHECK64ZFBFMIN-NEXT:    fcvt.s.bf16 fa0, fa0
1169; CHECK64ZFBFMIN-NEXT:    ret
1170;
1171; RV64ID-LABEL: fcvt_s_bf16:
1172; RV64ID:       # %bb.0:
1173; RV64ID-NEXT:    fmv.x.w a0, fa0
1174; RV64ID-NEXT:    slli a0, a0, 16
1175; RV64ID-NEXT:    fmv.w.x fa0, a0
1176; RV64ID-NEXT:    ret
1177  %1 = fpext bfloat %a to float
1178  ret float %1
1179}
1180
1181define bfloat @fcvt_bf16_d(double %a) nounwind {
1182; RV32IZFBFMIN-LABEL: fcvt_bf16_d:
1183; RV32IZFBFMIN:       # %bb.0:
1184; RV32IZFBFMIN-NEXT:    addi sp, sp, -16
1185; RV32IZFBFMIN-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
1186; RV32IZFBFMIN-NEXT:    call __truncdfbf2
1187; RV32IZFBFMIN-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
1188; RV32IZFBFMIN-NEXT:    addi sp, sp, 16
1189; RV32IZFBFMIN-NEXT:    ret
1190;
1191; R32IDZFBFMIN-LABEL: fcvt_bf16_d:
1192; R32IDZFBFMIN:       # %bb.0:
1193; R32IDZFBFMIN-NEXT:    fcvt.s.d fa5, fa0
1194; R32IDZFBFMIN-NEXT:    fcvt.bf16.s fa0, fa5
1195; R32IDZFBFMIN-NEXT:    ret
1196;
1197; RV32ID-LABEL: fcvt_bf16_d:
1198; RV32ID:       # %bb.0:
1199; RV32ID-NEXT:    addi sp, sp, -16
1200; RV32ID-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
1201; RV32ID-NEXT:    call __truncdfbf2
1202; RV32ID-NEXT:    fmv.x.w a0, fa0
1203; RV32ID-NEXT:    lui a1, 1048560
1204; RV32ID-NEXT:    or a0, a0, a1
1205; RV32ID-NEXT:    fmv.w.x fa0, a0
1206; RV32ID-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
1207; RV32ID-NEXT:    addi sp, sp, 16
1208; RV32ID-NEXT:    ret
1209;
1210; RV64IZFBFMIN-LABEL: fcvt_bf16_d:
1211; RV64IZFBFMIN:       # %bb.0:
1212; RV64IZFBFMIN-NEXT:    addi sp, sp, -16
1213; RV64IZFBFMIN-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
1214; RV64IZFBFMIN-NEXT:    call __truncdfbf2
1215; RV64IZFBFMIN-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
1216; RV64IZFBFMIN-NEXT:    addi sp, sp, 16
1217; RV64IZFBFMIN-NEXT:    ret
1218;
1219; RV64IDZFBFMIN-LABEL: fcvt_bf16_d:
1220; RV64IDZFBFMIN:       # %bb.0:
1221; RV64IDZFBFMIN-NEXT:    fcvt.s.d fa5, fa0
1222; RV64IDZFBFMIN-NEXT:    fcvt.bf16.s fa0, fa5
1223; RV64IDZFBFMIN-NEXT:    ret
1224;
1225; RV64ID-LABEL: fcvt_bf16_d:
1226; RV64ID:       # %bb.0:
1227; RV64ID-NEXT:    addi sp, sp, -16
1228; RV64ID-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
1229; RV64ID-NEXT:    call __truncdfbf2
1230; RV64ID-NEXT:    fmv.x.w a0, fa0
1231; RV64ID-NEXT:    lui a1, 1048560
1232; RV64ID-NEXT:    or a0, a0, a1
1233; RV64ID-NEXT:    fmv.w.x fa0, a0
1234; RV64ID-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
1235; RV64ID-NEXT:    addi sp, sp, 16
1236; RV64ID-NEXT:    ret
1237  %1 = fptrunc double %a to bfloat
1238  ret bfloat %1
1239}
1240
1241define double @fcvt_d_bf16(bfloat %a) nounwind {
1242; RV32IZFBFMIN-LABEL: fcvt_d_bf16:
1243; RV32IZFBFMIN:       # %bb.0:
1244; RV32IZFBFMIN-NEXT:    addi sp, sp, -16
1245; RV32IZFBFMIN-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
1246; RV32IZFBFMIN-NEXT:    fcvt.s.bf16 fa0, fa0
1247; RV32IZFBFMIN-NEXT:    call __extendsfdf2
1248; RV32IZFBFMIN-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
1249; RV32IZFBFMIN-NEXT:    addi sp, sp, 16
1250; RV32IZFBFMIN-NEXT:    ret
1251;
1252; R32IDZFBFMIN-LABEL: fcvt_d_bf16:
1253; R32IDZFBFMIN:       # %bb.0:
1254; R32IDZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0, dyn
1255; R32IDZFBFMIN-NEXT:    fcvt.d.s fa0, fa5
1256; R32IDZFBFMIN-NEXT:    ret
1257;
1258; RV32ID-LABEL: fcvt_d_bf16:
1259; RV32ID:       # %bb.0:
1260; RV32ID-NEXT:    fmv.x.w a0, fa0
1261; RV32ID-NEXT:    slli a0, a0, 16
1262; RV32ID-NEXT:    fmv.w.x fa5, a0
1263; RV32ID-NEXT:    fcvt.d.s fa0, fa5
1264; RV32ID-NEXT:    ret
1265;
1266; RV64IZFBFMIN-LABEL: fcvt_d_bf16:
1267; RV64IZFBFMIN:       # %bb.0:
1268; RV64IZFBFMIN-NEXT:    addi sp, sp, -16
1269; RV64IZFBFMIN-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
1270; RV64IZFBFMIN-NEXT:    fcvt.s.bf16 fa0, fa0
1271; RV64IZFBFMIN-NEXT:    call __extendsfdf2
1272; RV64IZFBFMIN-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
1273; RV64IZFBFMIN-NEXT:    addi sp, sp, 16
1274; RV64IZFBFMIN-NEXT:    ret
1275;
1276; RV64IDZFBFMIN-LABEL: fcvt_d_bf16:
1277; RV64IDZFBFMIN:       # %bb.0:
1278; RV64IDZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0, dyn
1279; RV64IDZFBFMIN-NEXT:    fcvt.d.s fa0, fa5
1280; RV64IDZFBFMIN-NEXT:    ret
1281;
1282; RV64ID-LABEL: fcvt_d_bf16:
1283; RV64ID:       # %bb.0:
1284; RV64ID-NEXT:    fmv.x.w a0, fa0
1285; RV64ID-NEXT:    slli a0, a0, 16
1286; RV64ID-NEXT:    fmv.w.x fa5, a0
1287; RV64ID-NEXT:    fcvt.d.s fa0, fa5
1288; RV64ID-NEXT:    ret
1289  %1 = fpext bfloat %a to double
1290  ret double %1
1291}
1292
1293define bfloat @bitcast_bf16_i16(i16 %a) nounwind {
1294; CHECK32ZFBFMIN-LABEL: bitcast_bf16_i16:
1295; CHECK32ZFBFMIN:       # %bb.0:
1296; CHECK32ZFBFMIN-NEXT:    fmv.h.x fa0, a0
1297; CHECK32ZFBFMIN-NEXT:    ret
1298;
1299; RV32ID-LABEL: bitcast_bf16_i16:
1300; RV32ID:       # %bb.0:
1301; RV32ID-NEXT:    lui a1, 1048560
1302; RV32ID-NEXT:    or a0, a0, a1
1303; RV32ID-NEXT:    fmv.w.x fa0, a0
1304; RV32ID-NEXT:    ret
1305;
1306; CHECK64ZFBFMIN-LABEL: bitcast_bf16_i16:
1307; CHECK64ZFBFMIN:       # %bb.0:
1308; CHECK64ZFBFMIN-NEXT:    fmv.h.x fa0, a0
1309; CHECK64ZFBFMIN-NEXT:    ret
1310;
1311; RV64ID-LABEL: bitcast_bf16_i16:
1312; RV64ID:       # %bb.0:
1313; RV64ID-NEXT:    lui a1, 1048560
1314; RV64ID-NEXT:    or a0, a0, a1
1315; RV64ID-NEXT:    fmv.w.x fa0, a0
1316; RV64ID-NEXT:    ret
1317  %1 = bitcast i16 %a to bfloat
1318  ret bfloat %1
1319}
1320
1321define i16 @bitcast_i16_bf16(bfloat %a) nounwind {
1322; CHECK32ZFBFMIN-LABEL: bitcast_i16_bf16:
1323; CHECK32ZFBFMIN:       # %bb.0:
1324; CHECK32ZFBFMIN-NEXT:    fmv.x.h a0, fa0
1325; CHECK32ZFBFMIN-NEXT:    ret
1326;
1327; RV32ID-LABEL: bitcast_i16_bf16:
1328; RV32ID:       # %bb.0:
1329; RV32ID-NEXT:    fmv.x.w a0, fa0
1330; RV32ID-NEXT:    ret
1331;
1332; CHECK64ZFBFMIN-LABEL: bitcast_i16_bf16:
1333; CHECK64ZFBFMIN:       # %bb.0:
1334; CHECK64ZFBFMIN-NEXT:    fmv.x.h a0, fa0
1335; CHECK64ZFBFMIN-NEXT:    ret
1336;
1337; RV64ID-LABEL: bitcast_i16_bf16:
1338; RV64ID:       # %bb.0:
1339; RV64ID-NEXT:    fmv.x.w a0, fa0
1340; RV64ID-NEXT:    ret
1341  %1 = bitcast bfloat %a to i16
1342  ret i16 %1
1343}
1344
1345define signext i32 @fcvt_bf16_w_demanded_bits(i32 signext %0, ptr %1) nounwind {
1346; CHECK32ZFBFMIN-LABEL: fcvt_bf16_w_demanded_bits:
1347; CHECK32ZFBFMIN:       # %bb.0:
1348; CHECK32ZFBFMIN-NEXT:    addi a0, a0, 1
1349; CHECK32ZFBFMIN-NEXT:    fcvt.s.w fa5, a0
1350; CHECK32ZFBFMIN-NEXT:    fcvt.bf16.s fa5, fa5
1351; CHECK32ZFBFMIN-NEXT:    fsh fa5, 0(a1)
1352; CHECK32ZFBFMIN-NEXT:    ret
1353;
1354; RV32ID-LABEL: fcvt_bf16_w_demanded_bits:
1355; RV32ID:       # %bb.0:
1356; RV32ID-NEXT:    addi sp, sp, -16
1357; RV32ID-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
1358; RV32ID-NEXT:    sw s0, 8(sp) # 4-byte Folded Spill
1359; RV32ID-NEXT:    sw s1, 4(sp) # 4-byte Folded Spill
1360; RV32ID-NEXT:    mv s0, a1
1361; RV32ID-NEXT:    addi s1, a0, 1
1362; RV32ID-NEXT:    fcvt.s.w fa0, s1
1363; RV32ID-NEXT:    call __truncsfbf2
1364; RV32ID-NEXT:    fmv.x.w a0, fa0
1365; RV32ID-NEXT:    sh a0, 0(s0)
1366; RV32ID-NEXT:    mv a0, s1
1367; RV32ID-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
1368; RV32ID-NEXT:    lw s0, 8(sp) # 4-byte Folded Reload
1369; RV32ID-NEXT:    lw s1, 4(sp) # 4-byte Folded Reload
1370; RV32ID-NEXT:    addi sp, sp, 16
1371; RV32ID-NEXT:    ret
1372;
1373; CHECK64ZFBFMIN-LABEL: fcvt_bf16_w_demanded_bits:
1374; CHECK64ZFBFMIN:       # %bb.0:
1375; CHECK64ZFBFMIN-NEXT:    addiw a0, a0, 1
1376; CHECK64ZFBFMIN-NEXT:    fcvt.s.w fa5, a0
1377; CHECK64ZFBFMIN-NEXT:    fcvt.bf16.s fa5, fa5
1378; CHECK64ZFBFMIN-NEXT:    fsh fa5, 0(a1)
1379; CHECK64ZFBFMIN-NEXT:    ret
1380;
1381; RV64ID-LABEL: fcvt_bf16_w_demanded_bits:
1382; RV64ID:       # %bb.0:
1383; RV64ID-NEXT:    addi sp, sp, -32
1384; RV64ID-NEXT:    sd ra, 24(sp) # 8-byte Folded Spill
1385; RV64ID-NEXT:    sd s0, 16(sp) # 8-byte Folded Spill
1386; RV64ID-NEXT:    sd s1, 8(sp) # 8-byte Folded Spill
1387; RV64ID-NEXT:    mv s0, a1
1388; RV64ID-NEXT:    addiw s1, a0, 1
1389; RV64ID-NEXT:    fcvt.s.w fa0, s1
1390; RV64ID-NEXT:    call __truncsfbf2
1391; RV64ID-NEXT:    fmv.x.w a0, fa0
1392; RV64ID-NEXT:    sh a0, 0(s0)
1393; RV64ID-NEXT:    mv a0, s1
1394; RV64ID-NEXT:    ld ra, 24(sp) # 8-byte Folded Reload
1395; RV64ID-NEXT:    ld s0, 16(sp) # 8-byte Folded Reload
1396; RV64ID-NEXT:    ld s1, 8(sp) # 8-byte Folded Reload
1397; RV64ID-NEXT:    addi sp, sp, 32
1398; RV64ID-NEXT:    ret
1399  %3 = add i32 %0, 1
1400  %4 = sitofp i32 %3 to bfloat
1401  store bfloat %4, ptr %1, align 2
1402  ret i32 %3
1403}
1404
1405define signext i32 @fcvt_bf16_wu_demanded_bits(i32 signext %0, ptr %1) nounwind {
1406; CHECK32ZFBFMIN-LABEL: fcvt_bf16_wu_demanded_bits:
1407; CHECK32ZFBFMIN:       # %bb.0:
1408; CHECK32ZFBFMIN-NEXT:    addi a0, a0, 1
1409; CHECK32ZFBFMIN-NEXT:    fcvt.s.wu fa5, a0
1410; CHECK32ZFBFMIN-NEXT:    fcvt.bf16.s fa5, fa5
1411; CHECK32ZFBFMIN-NEXT:    fsh fa5, 0(a1)
1412; CHECK32ZFBFMIN-NEXT:    ret
1413;
1414; RV32ID-LABEL: fcvt_bf16_wu_demanded_bits:
1415; RV32ID:       # %bb.0:
1416; RV32ID-NEXT:    addi sp, sp, -16
1417; RV32ID-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
1418; RV32ID-NEXT:    sw s0, 8(sp) # 4-byte Folded Spill
1419; RV32ID-NEXT:    sw s1, 4(sp) # 4-byte Folded Spill
1420; RV32ID-NEXT:    mv s0, a1
1421; RV32ID-NEXT:    addi s1, a0, 1
1422; RV32ID-NEXT:    fcvt.s.wu fa0, s1
1423; RV32ID-NEXT:    call __truncsfbf2
1424; RV32ID-NEXT:    fmv.x.w a0, fa0
1425; RV32ID-NEXT:    sh a0, 0(s0)
1426; RV32ID-NEXT:    mv a0, s1
1427; RV32ID-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
1428; RV32ID-NEXT:    lw s0, 8(sp) # 4-byte Folded Reload
1429; RV32ID-NEXT:    lw s1, 4(sp) # 4-byte Folded Reload
1430; RV32ID-NEXT:    addi sp, sp, 16
1431; RV32ID-NEXT:    ret
1432;
1433; CHECK64ZFBFMIN-LABEL: fcvt_bf16_wu_demanded_bits:
1434; CHECK64ZFBFMIN:       # %bb.0:
1435; CHECK64ZFBFMIN-NEXT:    addiw a0, a0, 1
1436; CHECK64ZFBFMIN-NEXT:    fcvt.s.wu fa5, a0
1437; CHECK64ZFBFMIN-NEXT:    fcvt.bf16.s fa5, fa5
1438; CHECK64ZFBFMIN-NEXT:    fsh fa5, 0(a1)
1439; CHECK64ZFBFMIN-NEXT:    ret
1440;
1441; RV64ID-LABEL: fcvt_bf16_wu_demanded_bits:
1442; RV64ID:       # %bb.0:
1443; RV64ID-NEXT:    addi sp, sp, -32
1444; RV64ID-NEXT:    sd ra, 24(sp) # 8-byte Folded Spill
1445; RV64ID-NEXT:    sd s0, 16(sp) # 8-byte Folded Spill
1446; RV64ID-NEXT:    sd s1, 8(sp) # 8-byte Folded Spill
1447; RV64ID-NEXT:    mv s0, a1
1448; RV64ID-NEXT:    addiw s1, a0, 1
1449; RV64ID-NEXT:    fcvt.s.wu fa0, s1
1450; RV64ID-NEXT:    call __truncsfbf2
1451; RV64ID-NEXT:    fmv.x.w a0, fa0
1452; RV64ID-NEXT:    sh a0, 0(s0)
1453; RV64ID-NEXT:    mv a0, s1
1454; RV64ID-NEXT:    ld ra, 24(sp) # 8-byte Folded Reload
1455; RV64ID-NEXT:    ld s0, 16(sp) # 8-byte Folded Reload
1456; RV64ID-NEXT:    ld s1, 8(sp) # 8-byte Folded Reload
1457; RV64ID-NEXT:    addi sp, sp, 32
1458; RV64ID-NEXT:    ret
1459  %3 = add i32 %0, 1
1460  %4 = uitofp i32 %3 to bfloat
1461  store bfloat %4, ptr %1, align 2
1462  ret i32 %3
1463}
1464
1465define signext i8 @fcvt_w_s_i8(bfloat %a) nounwind {
1466; CHECK32ZFBFMIN-LABEL: fcvt_w_s_i8:
1467; CHECK32ZFBFMIN:       # %bb.0:
1468; CHECK32ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
1469; CHECK32ZFBFMIN-NEXT:    fcvt.w.s a0, fa5, rtz
1470; CHECK32ZFBFMIN-NEXT:    ret
1471;
1472; RV32ID-LABEL: fcvt_w_s_i8:
1473; RV32ID:       # %bb.0:
1474; RV32ID-NEXT:    fmv.x.w a0, fa0
1475; RV32ID-NEXT:    slli a0, a0, 16
1476; RV32ID-NEXT:    fmv.w.x fa5, a0
1477; RV32ID-NEXT:    fcvt.w.s a0, fa5, rtz
1478; RV32ID-NEXT:    ret
1479;
1480; CHECK64ZFBFMIN-LABEL: fcvt_w_s_i8:
1481; CHECK64ZFBFMIN:       # %bb.0:
1482; CHECK64ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
1483; CHECK64ZFBFMIN-NEXT:    fcvt.l.s a0, fa5, rtz
1484; CHECK64ZFBFMIN-NEXT:    ret
1485;
1486; RV64ID-LABEL: fcvt_w_s_i8:
1487; RV64ID:       # %bb.0:
1488; RV64ID-NEXT:    fmv.x.w a0, fa0
1489; RV64ID-NEXT:    slli a0, a0, 16
1490; RV64ID-NEXT:    fmv.w.x fa5, a0
1491; RV64ID-NEXT:    fcvt.l.s a0, fa5, rtz
1492; RV64ID-NEXT:    ret
1493  %1 = fptosi bfloat %a to i8
1494  ret i8 %1
1495}
1496
1497define signext i8 @fcvt_w_s_sat_i8(bfloat %a) nounwind {
1498; CHECK32ZFBFMIN-LABEL: fcvt_w_s_sat_i8:
1499; CHECK32ZFBFMIN:       # %bb.0: # %start
1500; CHECK32ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
1501; CHECK32ZFBFMIN-NEXT:    lui a0, 798720
1502; CHECK32ZFBFMIN-NEXT:    lui a1, 274400
1503; CHECK32ZFBFMIN-NEXT:    fmv.w.x fa4, a0
1504; CHECK32ZFBFMIN-NEXT:    feq.s a0, fa5, fa5
1505; CHECK32ZFBFMIN-NEXT:    neg a0, a0
1506; CHECK32ZFBFMIN-NEXT:    fmax.s fa5, fa5, fa4
1507; CHECK32ZFBFMIN-NEXT:    fmv.w.x fa4, a1
1508; CHECK32ZFBFMIN-NEXT:    fmin.s fa5, fa5, fa4
1509; CHECK32ZFBFMIN-NEXT:    fcvt.w.s a1, fa5, rtz
1510; CHECK32ZFBFMIN-NEXT:    and a0, a0, a1
1511; CHECK32ZFBFMIN-NEXT:    ret
1512;
1513; RV32ID-LABEL: fcvt_w_s_sat_i8:
1514; RV32ID:       # %bb.0: # %start
1515; RV32ID-NEXT:    fmv.x.w a0, fa0
1516; RV32ID-NEXT:    lui a1, 798720
1517; RV32ID-NEXT:    fmv.w.x fa5, a1
1518; RV32ID-NEXT:    lui a1, 274400
1519; RV32ID-NEXT:    slli a0, a0, 16
1520; RV32ID-NEXT:    fmv.w.x fa4, a0
1521; RV32ID-NEXT:    feq.s a0, fa4, fa4
1522; RV32ID-NEXT:    fmax.s fa5, fa4, fa5
1523; RV32ID-NEXT:    fmv.w.x fa4, a1
1524; RV32ID-NEXT:    neg a0, a0
1525; RV32ID-NEXT:    fmin.s fa5, fa5, fa4
1526; RV32ID-NEXT:    fcvt.w.s a1, fa5, rtz
1527; RV32ID-NEXT:    and a0, a0, a1
1528; RV32ID-NEXT:    ret
1529;
1530; CHECK64ZFBFMIN-LABEL: fcvt_w_s_sat_i8:
1531; CHECK64ZFBFMIN:       # %bb.0: # %start
1532; CHECK64ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
1533; CHECK64ZFBFMIN-NEXT:    lui a0, 798720
1534; CHECK64ZFBFMIN-NEXT:    lui a1, 274400
1535; CHECK64ZFBFMIN-NEXT:    fmv.w.x fa4, a0
1536; CHECK64ZFBFMIN-NEXT:    feq.s a0, fa5, fa5
1537; CHECK64ZFBFMIN-NEXT:    neg a0, a0
1538; CHECK64ZFBFMIN-NEXT:    fmax.s fa5, fa5, fa4
1539; CHECK64ZFBFMIN-NEXT:    fmv.w.x fa4, a1
1540; CHECK64ZFBFMIN-NEXT:    fmin.s fa5, fa5, fa4
1541; CHECK64ZFBFMIN-NEXT:    fcvt.l.s a1, fa5, rtz
1542; CHECK64ZFBFMIN-NEXT:    and a0, a0, a1
1543; CHECK64ZFBFMIN-NEXT:    ret
1544;
1545; RV64ID-LABEL: fcvt_w_s_sat_i8:
1546; RV64ID:       # %bb.0: # %start
1547; RV64ID-NEXT:    fmv.x.w a0, fa0
1548; RV64ID-NEXT:    lui a1, 798720
1549; RV64ID-NEXT:    fmv.w.x fa5, a1
1550; RV64ID-NEXT:    lui a1, 274400
1551; RV64ID-NEXT:    slli a0, a0, 16
1552; RV64ID-NEXT:    fmv.w.x fa4, a0
1553; RV64ID-NEXT:    feq.s a0, fa4, fa4
1554; RV64ID-NEXT:    fmax.s fa5, fa4, fa5
1555; RV64ID-NEXT:    fmv.w.x fa4, a1
1556; RV64ID-NEXT:    neg a0, a0
1557; RV64ID-NEXT:    fmin.s fa5, fa5, fa4
1558; RV64ID-NEXT:    fcvt.l.s a1, fa5, rtz
1559; RV64ID-NEXT:    and a0, a0, a1
1560; RV64ID-NEXT:    ret
1561start:
1562  %0 = tail call i8 @llvm.fptosi.sat.i8.bf16(bfloat %a)
1563  ret i8 %0
1564}
1565declare i8 @llvm.fptosi.sat.i8.bf16(bfloat)
1566
1567define zeroext i8 @fcvt_wu_s_i8(bfloat %a) nounwind {
1568; CHECK32ZFBFMIN-LABEL: fcvt_wu_s_i8:
1569; CHECK32ZFBFMIN:       # %bb.0:
1570; CHECK32ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
1571; CHECK32ZFBFMIN-NEXT:    fcvt.w.s a0, fa5, rtz
1572; CHECK32ZFBFMIN-NEXT:    ret
1573;
1574; RV32ID-LABEL: fcvt_wu_s_i8:
1575; RV32ID:       # %bb.0:
1576; RV32ID-NEXT:    fmv.x.w a0, fa0
1577; RV32ID-NEXT:    slli a0, a0, 16
1578; RV32ID-NEXT:    fmv.w.x fa5, a0
1579; RV32ID-NEXT:    fcvt.wu.s a0, fa5, rtz
1580; RV32ID-NEXT:    ret
1581;
1582; CHECK64ZFBFMIN-LABEL: fcvt_wu_s_i8:
1583; CHECK64ZFBFMIN:       # %bb.0:
1584; CHECK64ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
1585; CHECK64ZFBFMIN-NEXT:    fcvt.lu.s a0, fa5, rtz
1586; CHECK64ZFBFMIN-NEXT:    ret
1587;
1588; RV64ID-LABEL: fcvt_wu_s_i8:
1589; RV64ID:       # %bb.0:
1590; RV64ID-NEXT:    fmv.x.w a0, fa0
1591; RV64ID-NEXT:    slli a0, a0, 16
1592; RV64ID-NEXT:    fmv.w.x fa5, a0
1593; RV64ID-NEXT:    fcvt.lu.s a0, fa5, rtz
1594; RV64ID-NEXT:    ret
1595  %1 = fptoui bfloat %a to i8
1596  ret i8 %1
1597}
1598
1599define zeroext i8 @fcvt_wu_s_sat_i8(bfloat %a) nounwind {
1600; CHECK32ZFBFMIN-LABEL: fcvt_wu_s_sat_i8:
1601; CHECK32ZFBFMIN:       # %bb.0: # %start
1602; CHECK32ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
1603; CHECK32ZFBFMIN-NEXT:    fmv.w.x fa4, zero
1604; CHECK32ZFBFMIN-NEXT:    lui a0, 276464
1605; CHECK32ZFBFMIN-NEXT:    fmax.s fa5, fa5, fa4
1606; CHECK32ZFBFMIN-NEXT:    fmv.w.x fa4, a0
1607; CHECK32ZFBFMIN-NEXT:    fmin.s fa5, fa5, fa4
1608; CHECK32ZFBFMIN-NEXT:    fcvt.wu.s a0, fa5, rtz
1609; CHECK32ZFBFMIN-NEXT:    ret
1610;
1611; RV32ID-LABEL: fcvt_wu_s_sat_i8:
1612; RV32ID:       # %bb.0: # %start
1613; RV32ID-NEXT:    fmv.x.w a0, fa0
1614; RV32ID-NEXT:    fmv.w.x fa5, zero
1615; RV32ID-NEXT:    slli a0, a0, 16
1616; RV32ID-NEXT:    fmv.w.x fa4, a0
1617; RV32ID-NEXT:    lui a0, 276464
1618; RV32ID-NEXT:    fmax.s fa5, fa4, fa5
1619; RV32ID-NEXT:    fmv.w.x fa4, a0
1620; RV32ID-NEXT:    fmin.s fa5, fa5, fa4
1621; RV32ID-NEXT:    fcvt.wu.s a0, fa5, rtz
1622; RV32ID-NEXT:    ret
1623;
1624; CHECK64ZFBFMIN-LABEL: fcvt_wu_s_sat_i8:
1625; CHECK64ZFBFMIN:       # %bb.0: # %start
1626; CHECK64ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
1627; CHECK64ZFBFMIN-NEXT:    fmv.w.x fa4, zero
1628; CHECK64ZFBFMIN-NEXT:    lui a0, 276464
1629; CHECK64ZFBFMIN-NEXT:    fmax.s fa5, fa5, fa4
1630; CHECK64ZFBFMIN-NEXT:    fmv.w.x fa4, a0
1631; CHECK64ZFBFMIN-NEXT:    fmin.s fa5, fa5, fa4
1632; CHECK64ZFBFMIN-NEXT:    fcvt.lu.s a0, fa5, rtz
1633; CHECK64ZFBFMIN-NEXT:    ret
1634;
1635; RV64ID-LABEL: fcvt_wu_s_sat_i8:
1636; RV64ID:       # %bb.0: # %start
1637; RV64ID-NEXT:    fmv.x.w a0, fa0
1638; RV64ID-NEXT:    fmv.w.x fa5, zero
1639; RV64ID-NEXT:    slli a0, a0, 16
1640; RV64ID-NEXT:    fmv.w.x fa4, a0
1641; RV64ID-NEXT:    lui a0, 276464
1642; RV64ID-NEXT:    fmax.s fa5, fa4, fa5
1643; RV64ID-NEXT:    fmv.w.x fa4, a0
1644; RV64ID-NEXT:    fmin.s fa5, fa5, fa4
1645; RV64ID-NEXT:    fcvt.lu.s a0, fa5, rtz
1646; RV64ID-NEXT:    ret
1647start:
1648  %0 = tail call i8 @llvm.fptoui.sat.i8.bf16(bfloat %a)
1649  ret i8 %0
1650}
1651declare i8 @llvm.fptoui.sat.i8.bf16(bfloat)
1652
1653define zeroext i32 @fcvt_wu_bf16_sat_zext(bfloat %a) nounwind {
1654; CHECK32ZFBFMIN-LABEL: fcvt_wu_bf16_sat_zext:
1655; CHECK32ZFBFMIN:       # %bb.0: # %start
1656; CHECK32ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
1657; CHECK32ZFBFMIN-NEXT:    fcvt.wu.s a0, fa5, rtz
1658; CHECK32ZFBFMIN-NEXT:    feq.s a1, fa5, fa5
1659; CHECK32ZFBFMIN-NEXT:    seqz a1, a1
1660; CHECK32ZFBFMIN-NEXT:    addi a1, a1, -1
1661; CHECK32ZFBFMIN-NEXT:    and a0, a1, a0
1662; CHECK32ZFBFMIN-NEXT:    ret
1663;
1664; RV32ID-LABEL: fcvt_wu_bf16_sat_zext:
1665; RV32ID:       # %bb.0: # %start
1666; RV32ID-NEXT:    fmv.x.w a0, fa0
1667; RV32ID-NEXT:    slli a0, a0, 16
1668; RV32ID-NEXT:    fmv.w.x fa5, a0
1669; RV32ID-NEXT:    fcvt.wu.s a0, fa5, rtz
1670; RV32ID-NEXT:    feq.s a1, fa5, fa5
1671; RV32ID-NEXT:    seqz a1, a1
1672; RV32ID-NEXT:    addi a1, a1, -1
1673; RV32ID-NEXT:    and a0, a1, a0
1674; RV32ID-NEXT:    ret
1675;
1676; CHECK64ZFBFMIN-LABEL: fcvt_wu_bf16_sat_zext:
1677; CHECK64ZFBFMIN:       # %bb.0: # %start
1678; CHECK64ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
1679; CHECK64ZFBFMIN-NEXT:    fcvt.wu.s a0, fa5, rtz
1680; CHECK64ZFBFMIN-NEXT:    feq.s a1, fa5, fa5
1681; CHECK64ZFBFMIN-NEXT:    seqz a1, a1
1682; CHECK64ZFBFMIN-NEXT:    addi a1, a1, -1
1683; CHECK64ZFBFMIN-NEXT:    and a0, a0, a1
1684; CHECK64ZFBFMIN-NEXT:    slli a0, a0, 32
1685; CHECK64ZFBFMIN-NEXT:    srli a0, a0, 32
1686; CHECK64ZFBFMIN-NEXT:    ret
1687;
1688; RV64ID-LABEL: fcvt_wu_bf16_sat_zext:
1689; RV64ID:       # %bb.0: # %start
1690; RV64ID-NEXT:    fmv.x.w a0, fa0
1691; RV64ID-NEXT:    slli a0, a0, 16
1692; RV64ID-NEXT:    fmv.w.x fa5, a0
1693; RV64ID-NEXT:    fcvt.wu.s a0, fa5, rtz
1694; RV64ID-NEXT:    feq.s a1, fa5, fa5
1695; RV64ID-NEXT:    seqz a1, a1
1696; RV64ID-NEXT:    addi a1, a1, -1
1697; RV64ID-NEXT:    and a0, a0, a1
1698; RV64ID-NEXT:    slli a0, a0, 32
1699; RV64ID-NEXT:    srli a0, a0, 32
1700; RV64ID-NEXT:    ret
1701start:
1702  %0 = tail call i32 @llvm.fptoui.sat.i32.bf16(bfloat %a)
1703  ret i32 %0
1704}
1705
1706define signext i32 @fcvt_w_bf16_sat_sext(bfloat %a) nounwind {
1707; CHECK32ZFBFMIN-LABEL: fcvt_w_bf16_sat_sext:
1708; CHECK32ZFBFMIN:       # %bb.0: # %start
1709; CHECK32ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
1710; CHECK32ZFBFMIN-NEXT:    fcvt.w.s a0, fa5, rtz
1711; CHECK32ZFBFMIN-NEXT:    feq.s a1, fa5, fa5
1712; CHECK32ZFBFMIN-NEXT:    seqz a1, a1
1713; CHECK32ZFBFMIN-NEXT:    addi a1, a1, -1
1714; CHECK32ZFBFMIN-NEXT:    and a0, a1, a0
1715; CHECK32ZFBFMIN-NEXT:    ret
1716;
1717; RV32ID-LABEL: fcvt_w_bf16_sat_sext:
1718; RV32ID:       # %bb.0: # %start
1719; RV32ID-NEXT:    fmv.x.w a0, fa0
1720; RV32ID-NEXT:    slli a0, a0, 16
1721; RV32ID-NEXT:    fmv.w.x fa5, a0
1722; RV32ID-NEXT:    fcvt.w.s a0, fa5, rtz
1723; RV32ID-NEXT:    feq.s a1, fa5, fa5
1724; RV32ID-NEXT:    seqz a1, a1
1725; RV32ID-NEXT:    addi a1, a1, -1
1726; RV32ID-NEXT:    and a0, a1, a0
1727; RV32ID-NEXT:    ret
1728;
1729; CHECK64ZFBFMIN-LABEL: fcvt_w_bf16_sat_sext:
1730; CHECK64ZFBFMIN:       # %bb.0: # %start
1731; CHECK64ZFBFMIN-NEXT:    fcvt.s.bf16 fa5, fa0
1732; CHECK64ZFBFMIN-NEXT:    fcvt.w.s a0, fa5, rtz
1733; CHECK64ZFBFMIN-NEXT:    feq.s a1, fa5, fa5
1734; CHECK64ZFBFMIN-NEXT:    seqz a1, a1
1735; CHECK64ZFBFMIN-NEXT:    addi a1, a1, -1
1736; CHECK64ZFBFMIN-NEXT:    and a0, a1, a0
1737; CHECK64ZFBFMIN-NEXT:    ret
1738;
1739; RV64ID-LABEL: fcvt_w_bf16_sat_sext:
1740; RV64ID:       # %bb.0: # %start
1741; RV64ID-NEXT:    fmv.x.w a0, fa0
1742; RV64ID-NEXT:    slli a0, a0, 16
1743; RV64ID-NEXT:    fmv.w.x fa5, a0
1744; RV64ID-NEXT:    fcvt.w.s a0, fa5, rtz
1745; RV64ID-NEXT:    feq.s a1, fa5, fa5
1746; RV64ID-NEXT:    seqz a1, a1
1747; RV64ID-NEXT:    addi a1, a1, -1
1748; RV64ID-NEXT:    and a0, a1, a0
1749; RV64ID-NEXT:    ret
1750start:
1751  %0 = tail call i32 @llvm.fptosi.sat.i32.bf16(bfloat %a)
1752  ret i32 %0
1753}
1754