| ; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 4 |
| ; RUN: llc -O0 -fast-isel -verify-machineinstrs -mtriple=arm64-eabi < %s | FileCheck --enable-var-scope %s |
| |
| ; Test fptosi |
| define i32 @fptosi_wh(half %a) nounwind ssp { |
| ; CHECK-LABEL: fptosi_wh: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: fcvt s0, h0 |
| ; CHECK-NEXT: fcvtzs w0, s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = fptosi half %a to i32 |
| ret i32 %conv |
| } |
| |
| ; Test fptoui |
| define i32 @fptoui_swh(half %a) nounwind ssp { |
| ; CHECK-LABEL: fptoui_swh: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: fcvt s0, h0 |
| ; CHECK-NEXT: fcvtzu w0, s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = fptoui half %a to i32 |
| ret i32 %conv |
| } |
| |
| ; Test sitofp |
| define half @sitofp_hw_i1(i1 %a) nounwind ssp { |
| ; CHECK-LABEL: sitofp_hw_i1: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: sbfx w8, w0, #0, #1 |
| ; CHECK-NEXT: scvtf s0, w8 |
| ; CHECK-NEXT: fcvt h0, s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = sitofp i1 %a to half |
| ret half %conv |
| } |
| |
| ; Test sitofp |
| define half @sitofp_hw_i8(i8 %a) nounwind ssp { |
| ; CHECK-LABEL: sitofp_hw_i8: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: sxtb w8, w0 |
| ; CHECK-NEXT: scvtf s0, w8 |
| ; CHECK-NEXT: fcvt h0, s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = sitofp i8 %a to half |
| ret half %conv |
| } |
| |
| ; Test sitofp |
| define half @sitofp_hw_i16(i16 %a) nounwind ssp { |
| ; CHECK-LABEL: sitofp_hw_i16: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: sxth w8, w0 |
| ; CHECK-NEXT: scvtf s0, w8 |
| ; CHECK-NEXT: fcvt h0, s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = sitofp i16 %a to half |
| ret half %conv |
| } |
| |
| ; Test sitofp |
| define half @sitofp_hw_i32(i32 %a) nounwind ssp { |
| ; CHECK-LABEL: sitofp_hw_i32: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: scvtf s0, w0 |
| ; CHECK-NEXT: fcvt h0, s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = sitofp i32 %a to half |
| ret half %conv |
| } |
| |
| ; Test sitofp |
| define half @sitofp_hx(i64 %a) nounwind ssp { |
| ; CHECK-LABEL: sitofp_hx: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: scvtf s0, x0 |
| ; CHECK-NEXT: fcvt h0, s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = sitofp i64 %a to half |
| ret half %conv |
| } |
| |
| ; Test uitofp |
| define half @uitofp_hw_i1(i1 %a) nounwind ssp { |
| ; CHECK-LABEL: uitofp_hw_i1: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: and w8, w0, #0x1 |
| ; CHECK-NEXT: ucvtf s0, w8 |
| ; CHECK-NEXT: fcvt h0, s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = uitofp i1 %a to half |
| ret half %conv |
| } |
| |
| ; Test uitofp |
| define half @uitofp_hw_i8(i8 %a) nounwind ssp { |
| ; CHECK-LABEL: uitofp_hw_i8: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: and w8, w0, #0xff |
| ; CHECK-NEXT: ucvtf s0, w8 |
| ; CHECK-NEXT: fcvt h0, s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = uitofp i8 %a to half |
| ret half %conv |
| } |
| |
| ; Test uitofp |
| define half @uitofp_hw_i16(i16 %a) nounwind ssp { |
| ; CHECK-LABEL: uitofp_hw_i16: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: and w8, w0, #0xffff |
| ; CHECK-NEXT: ucvtf s0, w8 |
| ; CHECK-NEXT: fcvt h0, s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = uitofp i16 %a to half |
| ret half %conv |
| } |
| |
| ; Test uitofp |
| define half @uitofp_hw_i32(i32 %a) nounwind ssp { |
| ; CHECK-LABEL: uitofp_hw_i32: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: ucvtf s0, w0 |
| ; CHECK-NEXT: fcvt h0, s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = uitofp i32 %a to half |
| ret half %conv |
| } |
| |
| ; Test uitofp |
| define half @uitofp_hx(i64 %a) nounwind ssp { |
| ; CHECK-LABEL: uitofp_hx: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: ucvtf s0, x0 |
| ; CHECK-NEXT: fcvt h0, s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = uitofp i64 %a to half |
| ret half %conv |
| } |
| |
| ; Test fptosi |
| define i32 @fptosi_bf(bfloat %a) nounwind ssp { |
| ; CHECK-LABEL: fptosi_bf: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: // kill: def $d0 killed $h0 |
| ; CHECK-NEXT: shll v0.4s, v0.4h, #16 |
| ; CHECK-NEXT: // kill: def $s0 killed $s0 killed $q0 |
| ; CHECK-NEXT: fcvtzs w0, s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = fptosi bfloat %a to i32 |
| ret i32 %conv |
| } |
| |
| ; Test fptoui |
| define i32 @fptoui_sbf(bfloat %a) nounwind ssp { |
| ; CHECK-LABEL: fptoui_sbf: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: // kill: def $d0 killed $h0 |
| ; CHECK-NEXT: shll v0.4s, v0.4h, #16 |
| ; CHECK-NEXT: // kill: def $s0 killed $s0 killed $q0 |
| ; CHECK-NEXT: fcvtzu w0, s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = fptoui bfloat %a to i32 |
| ret i32 %conv |
| } |
| |
| ; Test sitofp |
| define bfloat @sitofp_bf_i1(i1 %a) nounwind ssp { |
| ; CHECK-LABEL: sitofp_bf_i1: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: sbfx w8, w0, #0, #1 |
| ; CHECK-NEXT: scvtf s0, w8 |
| ; CHECK-NEXT: fmov w9, s0 |
| ; CHECK-NEXT: ubfx w8, w9, #16, #1 |
| ; CHECK-NEXT: add w8, w8, w9 |
| ; CHECK-NEXT: mov w9, #32767 // =0x7fff |
| ; CHECK-NEXT: add w8, w8, w9 |
| ; CHECK-NEXT: lsr w8, w8, #16 |
| ; CHECK-NEXT: fmov s0, w8 |
| ; CHECK-NEXT: // kill: def $h0 killed $h0 killed $s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = sitofp i1 %a to bfloat |
| ret bfloat %conv |
| } |
| |
| ; Test sitofp |
| define bfloat @sitofp_bf_i8(i8 %a) nounwind ssp { |
| ; CHECK-LABEL: sitofp_bf_i8: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: sxtb w8, w0 |
| ; CHECK-NEXT: scvtf s0, w8 |
| ; CHECK-NEXT: fmov w9, s0 |
| ; CHECK-NEXT: ubfx w8, w9, #16, #1 |
| ; CHECK-NEXT: add w8, w8, w9 |
| ; CHECK-NEXT: mov w9, #32767 // =0x7fff |
| ; CHECK-NEXT: add w8, w8, w9 |
| ; CHECK-NEXT: lsr w8, w8, #16 |
| ; CHECK-NEXT: fmov s0, w8 |
| ; CHECK-NEXT: // kill: def $h0 killed $h0 killed $s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = sitofp i8 %a to bfloat |
| ret bfloat %conv |
| } |
| |
| ; Test sitofp |
| define bfloat @sitofp_bf_i16(i16 %a) nounwind ssp { |
| ; CHECK-LABEL: sitofp_bf_i16: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: sxth w8, w0 |
| ; CHECK-NEXT: scvtf s0, w8 |
| ; CHECK-NEXT: fmov w9, s0 |
| ; CHECK-NEXT: ubfx w8, w9, #16, #1 |
| ; CHECK-NEXT: add w8, w8, w9 |
| ; CHECK-NEXT: mov w9, #32767 // =0x7fff |
| ; CHECK-NEXT: add w8, w8, w9 |
| ; CHECK-NEXT: lsr w8, w8, #16 |
| ; CHECK-NEXT: fmov s0, w8 |
| ; CHECK-NEXT: // kill: def $h0 killed $h0 killed $s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = sitofp i16 %a to bfloat |
| ret bfloat %conv |
| } |
| |
| ; Test sitofp |
| define bfloat @sitofp_bf_i32(i32 %a) nounwind ssp { |
| ; CHECK-LABEL: sitofp_bf_i32: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: scvtf d0, w0 |
| ; CHECK-NEXT: fcvtxn s0, d0 |
| ; CHECK-NEXT: fmov w9, s0 |
| ; CHECK-NEXT: ubfx w8, w9, #16, #1 |
| ; CHECK-NEXT: add w8, w8, w9 |
| ; CHECK-NEXT: mov w9, #32767 // =0x7fff |
| ; CHECK-NEXT: add w8, w8, w9 |
| ; CHECK-NEXT: lsr w8, w8, #16 |
| ; CHECK-NEXT: fmov s0, w8 |
| ; CHECK-NEXT: // kill: def $h0 killed $h0 killed $s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = sitofp i32 %a to bfloat |
| ret bfloat %conv |
| } |
| |
| ; Test sitofp |
| define bfloat @sitofp_bf_i164(i64 %a) nounwind ssp { |
| ; CHECK-LABEL: sitofp_bf_i164: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: subs x8, x0, #0 |
| ; CHECK-NEXT: cneg x10, x0, mi |
| ; CHECK-NEXT: and x8, x10, #0xfffffffffffff000 |
| ; CHECK-NEXT: lsr x9, x10, #53 |
| ; CHECK-NEXT: subs x9, x9, #0 |
| ; CHECK-NEXT: csel x8, x8, x10, ne |
| ; CHECK-NEXT: scvtf d0, x8 |
| ; CHECK-NEXT: fmov x8, d0 |
| ; CHECK-NEXT: and x9, x0, #0x8000000000000000 |
| ; CHECK-NEXT: orr x8, x8, x9 |
| ; CHECK-NEXT: cset w9, ne |
| ; CHECK-NEXT: ands x10, x10, #0xfff |
| ; CHECK-NEXT: csel w9, wzr, w9, eq |
| ; CHECK-NEXT: mov w9, w9 |
| ; CHECK-NEXT: // kill: def $x9 killed $w9 |
| ; CHECK-NEXT: orr x8, x8, x9 |
| ; CHECK-NEXT: fmov d0, x8 |
| ; CHECK-NEXT: fcvtxn s0, d0 |
| ; CHECK-NEXT: fmov w9, s0 |
| ; CHECK-NEXT: ubfx w8, w9, #16, #1 |
| ; CHECK-NEXT: add w8, w8, w9 |
| ; CHECK-NEXT: mov w9, #32767 // =0x7fff |
| ; CHECK-NEXT: add w8, w8, w9 |
| ; CHECK-NEXT: lsr w8, w8, #16 |
| ; CHECK-NEXT: fmov s0, w8 |
| ; CHECK-NEXT: // kill: def $h0 killed $h0 killed $s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = sitofp i64 %a to bfloat |
| ret bfloat %conv |
| } |
| |
| ; Test uitofp |
| define bfloat @uitofp_bf_i1(i1 %a) nounwind ssp { |
| ; CHECK-LABEL: uitofp_bf_i1: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: and w8, w0, #0x1 |
| ; CHECK-NEXT: ucvtf s0, w8 |
| ; CHECK-NEXT: fmov w9, s0 |
| ; CHECK-NEXT: ubfx w8, w9, #16, #1 |
| ; CHECK-NEXT: add w8, w8, w9 |
| ; CHECK-NEXT: mov w9, #32767 // =0x7fff |
| ; CHECK-NEXT: add w8, w8, w9 |
| ; CHECK-NEXT: lsr w8, w8, #16 |
| ; CHECK-NEXT: fmov s0, w8 |
| ; CHECK-NEXT: // kill: def $h0 killed $h0 killed $s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = uitofp i1 %a to bfloat |
| ret bfloat %conv |
| } |
| |
| ; Test uitofp |
| define bfloat @uitofp_bf_i8(i8 %a) nounwind ssp { |
| ; CHECK-LABEL: uitofp_bf_i8: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: and w8, w0, #0xff |
| ; CHECK-NEXT: ucvtf s0, w8 |
| ; CHECK-NEXT: fmov w9, s0 |
| ; CHECK-NEXT: ubfx w8, w9, #16, #1 |
| ; CHECK-NEXT: add w8, w8, w9 |
| ; CHECK-NEXT: mov w9, #32767 // =0x7fff |
| ; CHECK-NEXT: add w8, w8, w9 |
| ; CHECK-NEXT: lsr w8, w8, #16 |
| ; CHECK-NEXT: fmov s0, w8 |
| ; CHECK-NEXT: // kill: def $h0 killed $h0 killed $s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = uitofp i8 %a to bfloat |
| ret bfloat %conv |
| } |
| |
| ; Test uitofp |
| define bfloat @uitofp_bf_i16(i16 %a) nounwind ssp { |
| ; CHECK-LABEL: uitofp_bf_i16: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: and w8, w0, #0xffff |
| ; CHECK-NEXT: ucvtf s0, w8 |
| ; CHECK-NEXT: fmov w9, s0 |
| ; CHECK-NEXT: ubfx w8, w9, #16, #1 |
| ; CHECK-NEXT: add w8, w8, w9 |
| ; CHECK-NEXT: mov w9, #32767 // =0x7fff |
| ; CHECK-NEXT: add w8, w8, w9 |
| ; CHECK-NEXT: lsr w8, w8, #16 |
| ; CHECK-NEXT: fmov s0, w8 |
| ; CHECK-NEXT: // kill: def $h0 killed $h0 killed $s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = uitofp i16 %a to bfloat |
| ret bfloat %conv |
| } |
| |
| ; Test uitofp |
| define bfloat @uitofp_bf_i32(i32 %a) nounwind ssp { |
| ; CHECK-LABEL: uitofp_bf_i32: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: ucvtf d0, w0 |
| ; CHECK-NEXT: fcvtxn s0, d0 |
| ; CHECK-NEXT: fmov w9, s0 |
| ; CHECK-NEXT: ubfx w8, w9, #16, #1 |
| ; CHECK-NEXT: add w8, w8, w9 |
| ; CHECK-NEXT: mov w9, #32767 // =0x7fff |
| ; CHECK-NEXT: add w8, w8, w9 |
| ; CHECK-NEXT: lsr w8, w8, #16 |
| ; CHECK-NEXT: fmov s0, w8 |
| ; CHECK-NEXT: // kill: def $h0 killed $h0 killed $s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = uitofp i32 %a to bfloat |
| ret bfloat %conv |
| } |
| |
| ; Test uitofp |
| define bfloat @uitofp_bf_i64(i64 %a) nounwind ssp { |
| ; CHECK-LABEL: uitofp_bf_i64: |
| ; CHECK: // %bb.0: // %entry |
| ; CHECK-NEXT: and x8, x0, #0xfffffffffffff000 |
| ; CHECK-NEXT: lsr x9, x0, #53 |
| ; CHECK-NEXT: subs x9, x9, #0 |
| ; CHECK-NEXT: csel x8, x8, x0, ne |
| ; CHECK-NEXT: ucvtf d0, x8 |
| ; CHECK-NEXT: fmov x8, d0 |
| ; CHECK-NEXT: cset w9, ne |
| ; CHECK-NEXT: ands x10, x0, #0xfff |
| ; CHECK-NEXT: csel w9, wzr, w9, eq |
| ; CHECK-NEXT: mov w9, w9 |
| ; CHECK-NEXT: // kill: def $x9 killed $w9 |
| ; CHECK-NEXT: orr x8, x8, x9 |
| ; CHECK-NEXT: fmov d0, x8 |
| ; CHECK-NEXT: fcvtxn s0, d0 |
| ; CHECK-NEXT: fmov w9, s0 |
| ; CHECK-NEXT: ubfx w8, w9, #16, #1 |
| ; CHECK-NEXT: add w8, w8, w9 |
| ; CHECK-NEXT: mov w9, #32767 // =0x7fff |
| ; CHECK-NEXT: add w8, w8, w9 |
| ; CHECK-NEXT: lsr w8, w8, #16 |
| ; CHECK-NEXT: fmov s0, w8 |
| ; CHECK-NEXT: // kill: def $h0 killed $h0 killed $s0 |
| ; CHECK-NEXT: ret |
| entry: |
| %conv = uitofp i64 %a to bfloat |
| ret bfloat %conv |
| } |
| |
| |