| ; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 6 | |
| ; RUN: llc -mtriple=mips-linux-gnu -mcpu=mips32r5 -mattr=+msa,+fp64 -verify-machineinstrs < %s | FileCheck %s --check-prefixes=ALL,MIPS32,MIPS32BE | |
| ; RUN: llc -mtriple=mipsel-linux-gnu -mcpu=mips32r5 -mattr=+msa,+fp64 -verify-machineinstrs < %s | FileCheck %s --check-prefixes=ALL,MIPS32,MIPS32LE | |
| ; RUN: llc -mtriple=mips64-linux-gnu -mcpu=mips64r5 -mattr=+msa -verify-machineinstrs < %s | FileCheck %s --check-prefixes=ALL,MIPS64,MIPS64BE | |
| ; RUN: llc -mtriple=mips64el-linux-gnu -mcpu=mips64r5 -mattr=+msa -verify-machineinstrs < %s | FileCheck %s --check-prefixes=ALL,MIPS64,MIPS64LE | |
| ; Scalar f16 is soft promoted, but v8f16 is a legal MSA type. Shuffle | |
| ; through v8i16 to preserve the half bits without introducing scalar f16. | |
| ; Also cover shuffles that are widened from v4f16. | |
| define <8 x half> @splat_v8f16(<8 x half> %a) { | |
| ; MIPS32-LABEL: splat_v8f16: | |
| ; MIPS32: # %bb.0: | |
| ; MIPS32-NEXT: addiu $sp, $sp, -32 | |
| ; MIPS32-NEXT: .cfi_def_cfa_offset 32 | |
| ; MIPS32-NEXT: sw $ra, 28($sp) # 4-byte Folded Spill | |
| ; MIPS32-NEXT: sw $fp, 24($sp) # 4-byte Folded Spill | |
| ; MIPS32-NEXT: .cfi_offset 31, -4 | |
| ; MIPS32-NEXT: .cfi_offset 30, -8 | |
| ; MIPS32-NEXT: move $fp, $sp | |
| ; MIPS32-NEXT: .cfi_def_cfa_register 30 | |
| ; MIPS32-NEXT: addiu $1, $zero, -16 | |
| ; MIPS32-NEXT: and $sp, $sp, $1 | |
| ; MIPS32-NEXT: sw $6, 0($sp) | |
| ; MIPS32-NEXT: ld.h $w0, 0($sp) | |
| ; MIPS32-NEXT: splati.h $w0, $w0[0] | |
| ; MIPS32-NEXT: st.h $w0, 0($4) | |
| ; MIPS32-NEXT: move $sp, $fp | |
| ; MIPS32-NEXT: lw $fp, 24($sp) # 4-byte Folded Reload | |
| ; MIPS32-NEXT: lw $ra, 28($sp) # 4-byte Folded Reload | |
| ; MIPS32-NEXT: jr $ra | |
| ; MIPS32-NEXT: addiu $sp, $sp, 32 | |
| ; | |
| ; MIPS64BE-LABEL: splat_v8f16: | |
| ; MIPS64BE: # %bb.0: | |
| ; MIPS64BE-NEXT: daddiu $sp, $sp, -16 | |
| ; MIPS64BE-NEXT: .cfi_def_cfa_offset 16 | |
| ; MIPS64BE-NEXT: sd $4, 0($sp) | |
| ; MIPS64BE-NEXT: ld.h $w0, 0($sp) | |
| ; MIPS64BE-NEXT: splati.h $w0, $w0[0] | |
| ; MIPS64BE-NEXT: shf.h $w0, $w0, 27 | |
| ; MIPS64BE-NEXT: copy_s.d $2, $w0[0] | |
| ; MIPS64BE-NEXT: copy_s.d $3, $w0[1] | |
| ; MIPS64BE-NEXT: jr $ra | |
| ; MIPS64BE-NEXT: daddiu $sp, $sp, 16 | |
| ; | |
| ; MIPS64LE-LABEL: splat_v8f16: | |
| ; MIPS64LE: # %bb.0: | |
| ; MIPS64LE-NEXT: daddiu $sp, $sp, -16 | |
| ; MIPS64LE-NEXT: .cfi_def_cfa_offset 16 | |
| ; MIPS64LE-NEXT: sd $4, 0($sp) | |
| ; MIPS64LE-NEXT: ld.h $w0, 0($sp) | |
| ; MIPS64LE-NEXT: splati.h $w0, $w0[0] | |
| ; MIPS64LE-NEXT: copy_s.d $2, $w0[0] | |
| ; MIPS64LE-NEXT: copy_s.d $3, $w0[1] | |
| ; MIPS64LE-NEXT: jr $ra | |
| ; MIPS64LE-NEXT: daddiu $sp, $sp, 16 | |
| %s = shufflevector <8 x half> %a, <8 x half> poison, <8 x i32> zeroinitializer | |
| ret <8 x half> %s | |
| } | |
| define void @reverse_v8f16(ptr %dst, ptr %src) { | |
| ; MIPS32-LABEL: reverse_v8f16: | |
| ; MIPS32: # %bb.0: | |
| ; MIPS32-NEXT: lui $1, %hi($CPI1_0) | |
| ; MIPS32-NEXT: addiu $1, $1, %lo($CPI1_0) | |
| ; MIPS32-NEXT: ld.h $w0, 0($5) | |
| ; MIPS32-NEXT: ld.h $w1, 0($1) | |
| ; MIPS32-NEXT: vshf.h $w1, $w0, $w0 | |
| ; MIPS32-NEXT: jr $ra | |
| ; MIPS32-NEXT: st.h $w1, 0($4) | |
| ; | |
| ; MIPS64-LABEL: reverse_v8f16: | |
| ; MIPS64: # %bb.0: | |
| ; MIPS64-NEXT: lui $1, %highest(.LCPI1_0) | |
| ; MIPS64-NEXT: daddiu $1, $1, %higher(.LCPI1_0) | |
| ; MIPS64-NEXT: dsll $1, $1, 16 | |
| ; MIPS64-NEXT: daddiu $1, $1, %hi(.LCPI1_0) | |
| ; MIPS64-NEXT: dsll $1, $1, 16 | |
| ; MIPS64-NEXT: daddiu $1, $1, %lo(.LCPI1_0) | |
| ; MIPS64-NEXT: ld.h $w0, 0($5) | |
| ; MIPS64-NEXT: ld.h $w1, 0($1) | |
| ; MIPS64-NEXT: vshf.h $w1, $w0, $w0 | |
| ; MIPS64-NEXT: jr $ra | |
| ; MIPS64-NEXT: st.h $w1, 0($4) | |
| %a = load <8 x half>, ptr %src | |
| %s = shufflevector <8 x half> %a, <8 x half> poison, <8 x i32> <i32 7, i32 6, i32 5, i32 4, i32 3, i32 2, i32 1, i32 0> | |
| store <8 x half> %s, ptr %dst | |
| ret void | |
| } | |
| define void @swap_v8f16(ptr %dst, ptr %src) { | |
| ; ALL-LABEL: swap_v8f16: | |
| ; ALL: # %bb.0: | |
| ; ALL-NEXT: ld.h $w0, 0($5) | |
| ; ALL-NEXT: shf.h $w0, $w0, 225 | |
| ; ALL-NEXT: jr $ra | |
| ; ALL-NEXT: st.h $w0, 0($4) | |
| %a = load <8 x half>, ptr %src | |
| %s = shufflevector <8 x half> %a, <8 x half> poison, <8 x i32> <i32 1, i32 0, i32 2, i32 3, i32 5, i32 4, i32 6, i32 7> | |
| store <8 x half> %s, ptr %dst | |
| ret void | |
| } | |
| define void @shuffle_v8f16(ptr %dst, ptr %src1, ptr %src2) { | |
| ; MIPS32-LABEL: shuffle_v8f16: | |
| ; MIPS32: # %bb.0: | |
| ; MIPS32-NEXT: lui $1, %hi($CPI3_0) | |
| ; MIPS32-NEXT: addiu $1, $1, %lo($CPI3_0) | |
| ; MIPS32-NEXT: ld.h $w0, 0($5) | |
| ; MIPS32-NEXT: ld.h $w1, 0($6) | |
| ; MIPS32-NEXT: ld.h $w2, 0($1) | |
| ; MIPS32-NEXT: vshf.h $w2, $w1, $w0 | |
| ; MIPS32-NEXT: jr $ra | |
| ; MIPS32-NEXT: st.h $w2, 0($4) | |
| ; | |
| ; MIPS64-LABEL: shuffle_v8f16: | |
| ; MIPS64: # %bb.0: | |
| ; MIPS64-NEXT: lui $1, %highest(.LCPI3_0) | |
| ; MIPS64-NEXT: daddiu $1, $1, %higher(.LCPI3_0) | |
| ; MIPS64-NEXT: dsll $1, $1, 16 | |
| ; MIPS64-NEXT: daddiu $1, $1, %hi(.LCPI3_0) | |
| ; MIPS64-NEXT: dsll $1, $1, 16 | |
| ; MIPS64-NEXT: daddiu $1, $1, %lo(.LCPI3_0) | |
| ; MIPS64-NEXT: ld.h $w0, 0($5) | |
| ; MIPS64-NEXT: ld.h $w1, 0($6) | |
| ; MIPS64-NEXT: ld.h $w2, 0($1) | |
| ; MIPS64-NEXT: vshf.h $w2, $w1, $w0 | |
| ; MIPS64-NEXT: jr $ra | |
| ; MIPS64-NEXT: st.h $w2, 0($4) | |
| %a = load <8 x half>, ptr %src1 | |
| %b = load <8 x half>, ptr %src2 | |
| %s = shufflevector <8 x half> %a, <8 x half> %b, <8 x i32> <i32 poison, i32 9, i32 2, i32 15, i32 0, i32 13, i32 6, i32 11> | |
| store <8 x half> %s, ptr %dst | |
| ret void | |
| } | |
| define <4 x half> @splat_v4f16(<4 x half> %a) { | |
| ; MIPS32BE-LABEL: splat_v4f16: | |
| ; MIPS32BE: # %bb.0: | |
| ; MIPS32BE-NEXT: addiu $sp, $sp, -32 | |
| ; MIPS32BE-NEXT: .cfi_def_cfa_offset 32 | |
| ; MIPS32BE-NEXT: sw $ra, 28($sp) # 4-byte Folded Spill | |
| ; MIPS32BE-NEXT: sw $fp, 24($sp) # 4-byte Folded Spill | |
| ; MIPS32BE-NEXT: .cfi_offset 31, -4 | |
| ; MIPS32BE-NEXT: .cfi_offset 30, -8 | |
| ; MIPS32BE-NEXT: move $fp, $sp | |
| ; MIPS32BE-NEXT: .cfi_def_cfa_register 30 | |
| ; MIPS32BE-NEXT: addiu $1, $zero, -16 | |
| ; MIPS32BE-NEXT: and $sp, $sp, $1 | |
| ; MIPS32BE-NEXT: sw $6, 0($sp) | |
| ; MIPS32BE-NEXT: ld.h $w0, 0($sp) | |
| ; MIPS32BE-NEXT: splati.h $w0, $w0[0] | |
| ; MIPS32BE-NEXT: shf.h $w0, $w0, 177 | |
| ; MIPS32BE-NEXT: copy_s.w $1, $w0[0] | |
| ; MIPS32BE-NEXT: copy_s.w $2, $w0[1] | |
| ; MIPS32BE-NEXT: sw $2, 4($4) | |
| ; MIPS32BE-NEXT: sw $1, 0($4) | |
| ; MIPS32BE-NEXT: move $sp, $fp | |
| ; MIPS32BE-NEXT: lw $fp, 24($sp) # 4-byte Folded Reload | |
| ; MIPS32BE-NEXT: lw $ra, 28($sp) # 4-byte Folded Reload | |
| ; MIPS32BE-NEXT: jr $ra | |
| ; MIPS32BE-NEXT: addiu $sp, $sp, 32 | |
| ; | |
| ; MIPS32LE-LABEL: splat_v4f16: | |
| ; MIPS32LE: # %bb.0: | |
| ; MIPS32LE-NEXT: addiu $sp, $sp, -32 | |
| ; MIPS32LE-NEXT: .cfi_def_cfa_offset 32 | |
| ; MIPS32LE-NEXT: sw $ra, 28($sp) # 4-byte Folded Spill | |
| ; MIPS32LE-NEXT: sw $fp, 24($sp) # 4-byte Folded Spill | |
| ; MIPS32LE-NEXT: .cfi_offset 31, -4 | |
| ; MIPS32LE-NEXT: .cfi_offset 30, -8 | |
| ; MIPS32LE-NEXT: move $fp, $sp | |
| ; MIPS32LE-NEXT: .cfi_def_cfa_register 30 | |
| ; MIPS32LE-NEXT: addiu $1, $zero, -16 | |
| ; MIPS32LE-NEXT: and $sp, $sp, $1 | |
| ; MIPS32LE-NEXT: sw $6, 0($sp) | |
| ; MIPS32LE-NEXT: ld.h $w0, 0($sp) | |
| ; MIPS32LE-NEXT: splati.h $w0, $w0[0] | |
| ; MIPS32LE-NEXT: copy_s.w $1, $w0[0] | |
| ; MIPS32LE-NEXT: copy_s.w $2, $w0[1] | |
| ; MIPS32LE-NEXT: sw $2, 4($4) | |
| ; MIPS32LE-NEXT: sw $1, 0($4) | |
| ; MIPS32LE-NEXT: move $sp, $fp | |
| ; MIPS32LE-NEXT: lw $fp, 24($sp) # 4-byte Folded Reload | |
| ; MIPS32LE-NEXT: lw $ra, 28($sp) # 4-byte Folded Reload | |
| ; MIPS32LE-NEXT: jr $ra | |
| ; MIPS32LE-NEXT: addiu $sp, $sp, 32 | |
| ; | |
| ; MIPS64BE-LABEL: splat_v4f16: | |
| ; MIPS64BE: # %bb.0: | |
| ; MIPS64BE-NEXT: daddiu $sp, $sp, -16 | |
| ; MIPS64BE-NEXT: .cfi_def_cfa_offset 16 | |
| ; MIPS64BE-NEXT: sd $4, 0($sp) | |
| ; MIPS64BE-NEXT: ld.h $w0, 0($sp) | |
| ; MIPS64BE-NEXT: splati.h $w0, $w0[0] | |
| ; MIPS64BE-NEXT: shf.h $w0, $w0, 27 | |
| ; MIPS64BE-NEXT: copy_s.d $2, $w0[0] | |
| ; MIPS64BE-NEXT: jr $ra | |
| ; MIPS64BE-NEXT: daddiu $sp, $sp, 16 | |
| ; | |
| ; MIPS64LE-LABEL: splat_v4f16: | |
| ; MIPS64LE: # %bb.0: | |
| ; MIPS64LE-NEXT: daddiu $sp, $sp, -16 | |
| ; MIPS64LE-NEXT: .cfi_def_cfa_offset 16 | |
| ; MIPS64LE-NEXT: sd $4, 0($sp) | |
| ; MIPS64LE-NEXT: ld.h $w0, 0($sp) | |
| ; MIPS64LE-NEXT: splati.h $w0, $w0[0] | |
| ; MIPS64LE-NEXT: copy_s.d $2, $w0[0] | |
| ; MIPS64LE-NEXT: jr $ra | |
| ; MIPS64LE-NEXT: daddiu $sp, $sp, 16 | |
| %s = shufflevector <4 x half> %a, <4 x half> poison, <4 x i32> zeroinitializer | |
| ret <4 x half> %s | |
| } | |
| define void @reverse_v4f16(ptr %dst, ptr %src) { | |
| ; MIPS32BE-LABEL: reverse_v4f16: | |
| ; MIPS32BE: # %bb.0: | |
| ; MIPS32BE-NEXT: addiu $sp, $sp, -32 | |
| ; MIPS32BE-NEXT: .cfi_def_cfa_offset 32 | |
| ; MIPS32BE-NEXT: sw $ra, 28($sp) # 4-byte Folded Spill | |
| ; MIPS32BE-NEXT: sw $fp, 24($sp) # 4-byte Folded Spill | |
| ; MIPS32BE-NEXT: .cfi_offset 31, -4 | |
| ; MIPS32BE-NEXT: .cfi_offset 30, -8 | |
| ; MIPS32BE-NEXT: move $fp, $sp | |
| ; MIPS32BE-NEXT: .cfi_def_cfa_register 30 | |
| ; MIPS32BE-NEXT: addiu $1, $zero, -16 | |
| ; MIPS32BE-NEXT: and $sp, $sp, $1 | |
| ; MIPS32BE-NEXT: lw $1, 4($5) | |
| ; MIPS32BE-NEXT: sw $1, 4($sp) | |
| ; MIPS32BE-NEXT: lw $1, 0($5) | |
| ; MIPS32BE-NEXT: sw $1, 0($sp) | |
| ; MIPS32BE-NEXT: ld.h $w0, 0($sp) | |
| ; MIPS32BE-NEXT: shf.h $w0, $w0, 27 | |
| ; MIPS32BE-NEXT: shf.h $w0, $w0, 177 | |
| ; MIPS32BE-NEXT: copy_s.w $1, $w0[1] | |
| ; MIPS32BE-NEXT: copy_s.w $2, $w0[0] | |
| ; MIPS32BE-NEXT: sw $2, 0($4) | |
| ; MIPS32BE-NEXT: sw $1, 4($4) | |
| ; MIPS32BE-NEXT: move $sp, $fp | |
| ; MIPS32BE-NEXT: lw $fp, 24($sp) # 4-byte Folded Reload | |
| ; MIPS32BE-NEXT: lw $ra, 28($sp) # 4-byte Folded Reload | |
| ; MIPS32BE-NEXT: jr $ra | |
| ; MIPS32BE-NEXT: addiu $sp, $sp, 32 | |
| ; | |
| ; MIPS32LE-LABEL: reverse_v4f16: | |
| ; MIPS32LE: # %bb.0: | |
| ; MIPS32LE-NEXT: addiu $sp, $sp, -32 | |
| ; MIPS32LE-NEXT: .cfi_def_cfa_offset 32 | |
| ; MIPS32LE-NEXT: sw $ra, 28($sp) # 4-byte Folded Spill | |
| ; MIPS32LE-NEXT: sw $fp, 24($sp) # 4-byte Folded Spill | |
| ; MIPS32LE-NEXT: .cfi_offset 31, -4 | |
| ; MIPS32LE-NEXT: .cfi_offset 30, -8 | |
| ; MIPS32LE-NEXT: move $fp, $sp | |
| ; MIPS32LE-NEXT: .cfi_def_cfa_register 30 | |
| ; MIPS32LE-NEXT: addiu $1, $zero, -16 | |
| ; MIPS32LE-NEXT: and $sp, $sp, $1 | |
| ; MIPS32LE-NEXT: lw $1, 4($5) | |
| ; MIPS32LE-NEXT: sw $1, 4($sp) | |
| ; MIPS32LE-NEXT: lw $1, 0($5) | |
| ; MIPS32LE-NEXT: sw $1, 0($sp) | |
| ; MIPS32LE-NEXT: ld.h $w0, 0($sp) | |
| ; MIPS32LE-NEXT: shf.h $w0, $w0, 27 | |
| ; MIPS32LE-NEXT: copy_s.w $1, $w0[1] | |
| ; MIPS32LE-NEXT: copy_s.w $2, $w0[0] | |
| ; MIPS32LE-NEXT: sw $2, 0($4) | |
| ; MIPS32LE-NEXT: sw $1, 4($4) | |
| ; MIPS32LE-NEXT: move $sp, $fp | |
| ; MIPS32LE-NEXT: lw $fp, 24($sp) # 4-byte Folded Reload | |
| ; MIPS32LE-NEXT: lw $ra, 28($sp) # 4-byte Folded Reload | |
| ; MIPS32LE-NEXT: jr $ra | |
| ; MIPS32LE-NEXT: addiu $sp, $sp, 32 | |
| ; | |
| ; MIPS64BE-LABEL: reverse_v4f16: | |
| ; MIPS64BE: # %bb.0: | |
| ; MIPS64BE-NEXT: daddiu $sp, $sp, -16 | |
| ; MIPS64BE-NEXT: .cfi_def_cfa_offset 16 | |
| ; MIPS64BE-NEXT: ld $1, 0($5) | |
| ; MIPS64BE-NEXT: sd $1, 0($sp) | |
| ; MIPS64BE-NEXT: ld.h $w0, 0($sp) | |
| ; MIPS64BE-NEXT: shf.h $w0, $w0, 27 | |
| ; MIPS64BE-NEXT: shf.h $w0, $w0, 27 | |
| ; MIPS64BE-NEXT: copy_s.d $1, $w0[0] | |
| ; MIPS64BE-NEXT: sd $1, 0($4) | |
| ; MIPS64BE-NEXT: jr $ra | |
| ; MIPS64BE-NEXT: daddiu $sp, $sp, 16 | |
| ; | |
| ; MIPS64LE-LABEL: reverse_v4f16: | |
| ; MIPS64LE: # %bb.0: | |
| ; MIPS64LE-NEXT: daddiu $sp, $sp, -16 | |
| ; MIPS64LE-NEXT: .cfi_def_cfa_offset 16 | |
| ; MIPS64LE-NEXT: ld $1, 0($5) | |
| ; MIPS64LE-NEXT: sd $1, 0($sp) | |
| ; MIPS64LE-NEXT: ld.h $w0, 0($sp) | |
| ; MIPS64LE-NEXT: shf.h $w0, $w0, 27 | |
| ; MIPS64LE-NEXT: copy_s.d $1, $w0[0] | |
| ; MIPS64LE-NEXT: sd $1, 0($4) | |
| ; MIPS64LE-NEXT: jr $ra | |
| ; MIPS64LE-NEXT: daddiu $sp, $sp, 16 | |
| %a = load <4 x half>, ptr %src | |
| %s = shufflevector <4 x half> %a, <4 x half> poison, <4 x i32> <i32 3, i32 2, i32 1, i32 0> | |
| store <4 x half> %s, ptr %dst | |
| ret void | |
| } |