#include "asm.S"
.section .rodata
.align 4
.text
function x265_blockcopy_sp_4x4_neon
lsl r3, #1
.rept 2
vld1.u16 {q0}, [r2], r3
vld1.u16 {q1}, [r2], r3
vmovn.u16 d0, q0
vmovn.u16 d1, q1
vst1.u32 {d0[0]}, [r0], r1
vst1.u32 {d1[0]}, [r0], r1
.endr
bx lr
endfunc
function x265_blockcopy_sp_8x8_neon
lsl r3, #1
.rept 4
vld1.u16 {q0}, [r2], r3
vld1.u16 {q1}, [r2], r3
vmovn.u16 d0, q0
vmovn.u16 d1, q1
vst1.u8 {d0}, [r0], r1
vst1.u8 {d1}, [r0], r1
.endr
bx lr
endfunc
function x265_blockcopy_sp_16x16_neon
lsl r3, #1
.rept 8
vld1.u16 {q0, q1}, [r2], r3
vld1.u16 {q2, q3}, [r2], r3
vmovn.u16 d0, q0
vmovn.u16 d1, q1
vmovn.u16 d2, q2
vmovn.u16 d3, q3
vst1.u8 {q0}, [r0], r1
vst1.u8 {q1}, [r0], r1
.endr
bx lr
endfunc
function x265_blockcopy_sp_32x32_neon
mov r12, #4
lsl r3, #1
sub r3, #32
loop_csp32:
subs r12, #1
.rept 4
vld1.u16 {q0, q1}, [r2]!
vld1.u16 {q2, q3}, [r2], r3
vld1.u16 {q8, q9}, [r2]!
vld1.u16 {q10, q11}, [r2], r3
vmovn.u16 d0, q0
vmovn.u16 d1, q1
vmovn.u16 d2, q2
vmovn.u16 d3, q3
vmovn.u16 d4, q8
vmovn.u16 d5, q9
vmovn.u16 d6, q10
vmovn.u16 d7, q11
vst1.u8 {q0, q1}, [r0], r1
vst1.u8 {q2, q3}, [r0], r1
.endr
bne loop_csp32
bx lr
endfunc
function x265_blockcopy_sp_64x64_neon
mov r12, #16
lsl r3, #1
sub r3, #96
sub r1, #32
loop_csp64:
subs r12, #1
.rept 4
vld1.u16 {q0, q1}, [r2]!
vld1.u16 {q2, q3}, [r2]!
vld1.u16 {q8, q9}, [r2]!
vld1.u16 {q10, q11}, [r2], r3
vmovn.u16 d0, q0
vmovn.u16 d1, q1
vmovn.u16 d2, q2
vmovn.u16 d3, q3
vmovn.u16 d4, q8
vmovn.u16 d5, q9
vmovn.u16 d6, q10
vmovn.u16 d7, q11
vst1.u8 {q0, q1}, [r0]!
vst1.u8 {q2, q3}, [r0], r1
.endr
bne loop_csp64
bx lr
endfunc
function x265_blockcopy_ps_4x4_neon
lsl r1, #1
.rept 2
vld1.u8 {d0}, [r2], r3
vld1.u8 {d1}, [r2], r3
vmovl.u8 q1, d0
vmovl.u8 q2, d1
vst1.u16 {d2}, [r0], r1
vst1.u16 {d4}, [r0], r1
.endr
bx lr
endfunc
function x265_blockcopy_ps_8x8_neon
lsl r1, #1
.rept 4
vld1.u8 {d0}, [r2], r3
vld1.u8 {d1}, [r2], r3
vmovl.u8 q1, d0
vmovl.u8 q2, d1
vst1.u16 {q1}, [r0], r1
vst1.u16 {q2}, [r0], r1
.endr
bx lr
endfunc
function x265_blockcopy_ps_16x16_neon
lsl r1, #1
.rept 8
vld1.u8 {q0}, [r2], r3
vld1.u8 {q1}, [r2], r3
vmovl.u8 q8, d0
vmovl.u8 q9, d1
vmovl.u8 q10, d2
vmovl.u8 q11, d3
vst1.u16 {q8, q9}, [r0], r1
vst1.u16 {q10, q11}, [r0], r1
.endr
bx lr
endfunc
function x265_blockcopy_ps_32x32_neon
lsl r1, #1
sub r1, #32
mov r12, #4
loop_cps32:
subs r12, #1
.rept 4
vld1.u8 {q0, q1}, [r2], r3
vld1.u8 {q2, q3}, [r2], r3
vmovl.u8 q8, d0
vmovl.u8 q9, d1
vmovl.u8 q10, d2
vmovl.u8 q11, d3
vmovl.u8 q12, d4
vmovl.u8 q13, d5
vmovl.u8 q14, d6
vmovl.u8 q15, d7
vst1.u16 {q8, q9}, [r0]!
vst1.u16 {q10, q11}, [r0], r1
vst1.u16 {q12, q13}, [r0]!
vst1.u16 {q14, q15}, [r0], r1
.endr
bne loop_cps32
bx lr
endfunc
function x265_blockcopy_ps_64x64_neon
lsl r1, #1
sub r1, #96
sub r3, #32
mov r12, #16
loop_cps64:
subs r12, #1
.rept 4
vld1.u8 {q0, q1}, [r2]!
vld1.u8 {q2, q3}, [r2], r3
vmovl.u8 q8, d0
vmovl.u8 q9, d1
vmovl.u8 q10, d2
vmovl.u8 q11, d3
vmovl.u8 q12, d4
vmovl.u8 q13, d5
vmovl.u8 q14, d6
vmovl.u8 q15, d7
vst1.u16 {q8, q9}, [r0]!
vst1.u16 {q10, q11}, [r0]!
vst1.u16 {q12, q13}, [r0]!
vst1.u16 {q14, q15}, [r0], r1
.endr
bne loop_cps64
bx lr
endfunc
function x265_blockcopy_ss_4x4_neon
lsl r1, #1
lsl r3, #1
.rept 2
vld1.u16 {d0}, [r2], r3
vld1.u16 {d1}, [r2], r3
vst1.u16 {d0}, [r0], r1
vst1.u16 {d1}, [r0], r1
.endr
bx lr
endfunc
function x265_blockcopy_ss_8x8_neon
lsl r1, #1
lsl r3, #1
.rept 4
vld1.u16 {q0}, [r2], r3
vld1.u16 {q1}, [r2], r3
vst1.u16 {q0}, [r0], r1
vst1.u16 {q1}, [r0], r1
.endr
bx lr
endfunc
function x265_blockcopy_ss_16x16_neon
lsl r1, #1
lsl r3, #1
.rept 8
vld1.u16 {q0, q1}, [r2], r3
vld1.u16 {q2, q3}, [r2], r3
vst1.u16 {q0, q1}, [r0], r1
vst1.u16 {q2, q3}, [r0], r1
.endr
bx lr
endfunc
function x265_blockcopy_ss_32x32_neon
lsl r1, #1
lsl r3, #1
mov r12, #4
sub r1, #32
sub r3, #32
loop_css32:
subs r12, #1
.rept 8
vld1.u16 {q0, q1}, [r2]!
vld1.u16 {q2, q3}, [r2], r3
vst1.u16 {q0, q1}, [r0]!
vst1.u16 {q2, q3}, [r0], r1
.endr
bne loop_css32
bx lr
endfunc
function x265_blockcopy_ss_64x64_neon
lsl r1, #1
lsl r3, #1
mov r12, #8
sub r1, #96
sub r3, #96
loop_css64:
subs r12, #1
.rept 8
vld1.u16 {q0, q1}, [r2]!
vld1.u16 {q2, q3}, [r2]!
vld1.u16 {q8, q9}, [r2]!
vld1.u16 {q10, q11}, [r2], r3
vst1.u16 {q0, q1}, [r0]!
vst1.u16 {q2, q3}, [r0]!
vst1.u16 {q8, q9}, [r0]!
vst1.u16 {q10, q11}, [r0], r1
.endr
bne loop_css64
bx lr
endfunc
function x265_blockcopy_ss_4x8_neon
lsl r1, #1
lsl r3, #1
.rept 4
vld1.u16 {d0}, [r2], r3
vld1.u16 {d1}, [r2], r3
vst1.u16 {d0}, [r0], r1
vst1.u16 {d1}, [r0], r1
.endr
bx lr
endfunc
function x265_blockcopy_ss_8x16_neon
lsl r1, #1
lsl r3, #1
.rept 8
vld1.u16 {q0}, [r2], r3
vld1.u16 {q1}, [r2], r3
vst1.u16 {q0}, [r0], r1
vst1.u16 {q1}, [r0], r1
.endr
bx lr
endfunc
function x265_blockcopy_ss_16x32_neon
lsl r1, #1
lsl r3, #1
.rept 16
vld1.u16 {q0, q1}, [r2], r3
vld1.u16 {q2, q3}, [r2], r3
vst1.u16 {q0, q1}, [r0], r1
vst1.u16 {q2, q3}, [r0], r1
.endr
bx lr
endfunc
function x265_blockcopy_ss_32x64_neon
lsl r1, #1
lsl r3, #1
mov r12, #8
sub r1, #32
sub r3, #32
loop_css_32x64:
subs r12, #1
.rept 8
vld1.u16 {q0, q1}, [r2]!
vld1.u16 {q2, q3}, [r2], r3
vst1.u16 {q0, q1}, [r0]!
vst1.u16 {q2, q3}, [r0], r1
.endr
bne loop_css_32x64
bx lr
endfunc
function x265_blockcopy_ps_4x8_neon
lsl r1, #1
.rept 4
vld1.u8 {d0}, [r2], r3
vld1.u8 {d1}, [r2], r3
vmovl.u8 q1, d0
vmovl.u8 q2, d1
vst1.u16 {d2}, [r0], r1
vst1.u16 {d4}, [r0], r1
.endr
bx lr
endfunc
function x265_blockcopy_ps_8x16_neon
lsl r1, #1
.rept 8
vld1.u8 {d0}, [r2], r3
vld1.u8 {d1}, [r2], r3
vmovl.u8 q1, d0
vmovl.u8 q2, d1
vst1.u16 {q1}, [r0], r1
vst1.u16 {q2}, [r0], r1
.endr
bx lr
endfunc
function x265_blockcopy_ps_16x32_neon
lsl r1, #1
mov r12, #4
loop_cps_16x32:
subs r12, #1
.rept 4
vld1.u8 {q0}, [r2], r3
vld1.u8 {q1}, [r2], r3
vmovl.u8 q8, d0
vmovl.u8 q9, d1
vmovl.u8 q10, d2
vmovl.u8 q11, d3
vst1.u16 {q8, q9}, [r0], r1
vst1.u16 {q10, q11}, [r0], r1
.endr
bne loop_cps_16x32
bx lr
endfunc
function x265_blockcopy_ps_32x64_neon
lsl r1, #1
sub r1, #32
mov r12, #8
loop_cps_32x64:
subs r12, #1
.rept 4
vld1.u8 {q0, q1}, [r2], r3
vld1.u8 {q2, q3}, [r2], r3
vmovl.u8 q8, d0
vmovl.u8 q9, d1
vmovl.u8 q10, d2
vmovl.u8 q11, d3
vmovl.u8 q12, d4
vmovl.u8 q13, d5
vmovl.u8 q14, d6
vmovl.u8 q15, d7
vst1.u16 {q8, q9}, [r0]!
vst1.u16 {q10, q11}, [r0], r1
vst1.u16 {q12, q13}, [r0]!
vst1.u16 {q14, q15}, [r0], r1
.endr
bne loop_cps_32x64
bx lr
endfunc
function x265_blockcopy_sp_4x8_neon
lsl r3, #1
.rept 4
vld1.u16 {q0}, [r2], r3
vld1.u16 {q1}, [r2], r3
vmovn.u16 d0, q0
vmovn.u16 d1, q1
vst1.u32 {d0[0]}, [r0], r1
vst1.u32 {d1[0]}, [r0], r1
.endr
bx lr
endfunc
function x265_blockcopy_sp_8x16_neon
lsl r3, #1
.rept 8
vld1.u16 {q0}, [r2], r3
vld1.u16 {q1}, [r2], r3
vmovn.u16 d0, q0
vmovn.u16 d1, q1
vst1.u8 {d0}, [r0], r1
vst1.u8 {d1}, [r0], r1
.endr
bx lr
endfunc
function x265_blockcopy_sp_16x32_neon
lsl r3, #1
mov r12, #4
loop_csp_16x32:
subs r12, #1
.rept 4
vld1.u16 {q0, q1}, [r2], r3
vld1.u16 {q2, q3}, [r2], r3
vmovn.u16 d0, q0
vmovn.u16 d1, q1
vmovn.u16 d2, q2
vmovn.u16 d3, q3
vst1.u8 {q0}, [r0], r1
vst1.u8 {q1}, [r0], r1
.endr
bne loop_csp_16x32
bx lr
endfunc
function x265_blockcopy_sp_32x64_neon
mov r12, #8
lsl r3, #1
sub r3, #32
loop_csp_32x64:
subs r12, #1
.rept 4
vld1.u16 {q0, q1}, [r2]!
vld1.u16 {q2, q3}, [r2], r3
vld1.u16 {q8, q9}, [r2]!
vld1.u16 {q10, q11}, [r2], r3
vmovn.u16 d0, q0
vmovn.u16 d1, q1
vmovn.u16 d2, q2
vmovn.u16 d3, q3
vmovn.u16 d4, q8
vmovn.u16 d5, q9
vmovn.u16 d6, q10
vmovn.u16 d7, q11
vst1.u8 {q0, q1}, [r0], r1
vst1.u8 {q2, q3}, [r0], r1
.endr
bne loop_csp_32x64
bx lr
endfunc
function x265_blockfill_s_4x4_neon
vdup.u16 d0, r2
lsl r1, #1
.rept 4
vst1.16 {d0}, [r0], r1
.endr
bx lr
endfunc
function x265_blockfill_s_8x8_neon
vdup.u16 q0, r2
lsl r1, #1
.rept 8
vst1.16 {q0}, [r0], r1
.endr
bx lr
endfunc
function x265_blockfill_s_16x16_neon
vdup.u16 q0, r2
vmov q1, q0
lsl r1, #1
.rept 16
vst1.16 {q0, q1}, [r0], r1
.endr
bx lr
endfunc
function x265_blockfill_s_32x32_neon
vdup.u16 q0, r2
vmov q1, q0
lsl r1, #1
sub r1, #32
.rept 32
vst1.16 {q0, q1}, [r0]!
vst1.16 {q0, q1}, [r0], r1
.endr
bx lr
endfunc
function x265_copy_cnt_4_neon
lsl r2, #1
mov r12, #8
veor d4, d4
.rept 2
vld1.s16 {d0}, [r1], r2
vld1.s16 {d1}, [r1], r2
vclz.i16 d2, d0
vclz.i16 d3, d1
vshr.u16 q1, #4
vadd.u16 d2, d3
vadd.u16 d4, d2
vst1.s16 {d0}, [r0], r12
vst1.s16 {d1}, [r0], r12
.endr
vpadd.u16 d4, d4
vpadd.u16 d4, d4
vmov.u16 r12, d4[0]
rsb r0, r12, #16
bx lr
endfunc
function x265_copy_cnt_8_neon
lsl r2, #1
mov r12, #16
veor q8, q8
.rept 4
vld1.s16 {q0}, [r1], r2
vld1.s16 {q1}, [r1], r2
vclz.i16 q2, q0
vclz.i16 q3, q1
vshr.u16 q2, #4
vshr.u16 q3, #4
vadd.u16 q2, q3
vadd.u16 q8, q2
vst1.s16 {q0}, [r0], r12
vst1.s16 {q1}, [r0], r12
.endr
vadd.u16 d16, d17
vpadd.u16 d16, d16
vpadd.u16 d16, d16
vmov.u16 r12, d16[0]
rsb r0, r12, #64
bx lr
endfunc
function x265_copy_cnt_16_neon
lsl r2, #1
mov r12, #32
veor q2, q2
.rept 16
vld1.s16 {q0, q1}, [r1], r2
vst1.s16 {q0, q1}, [r0], r12
vclz.i16 q8, q0
vclz.i16 q9, q1
vshr.u16 q8, #4
vshr.u16 q9, #4
vadd.u16 q8, q9
vadd.u16 q2, q8
.endr
vadd.u16 d4, d5
vpadd.u16 d4, d4
vpadd.u16 d4, d4
vmov.u16 r12, d4[0]
rsb r0, r12, #256
bx lr
endfunc
function x265_copy_cnt_32_neon
lsl r2, #1
sub r2, #32
mov r12, #32
veor q12, q12
.rept 32
vld1.s16 {q0, q1}, [r1]!
vld1.s16 {q2, q3}, [r1], r2
vst1.s16 {q0, q1}, [r0]!
vst1.s16 {q2, q3}, [r0], r12
vclz.i16 q8, q0
vclz.i16 q9, q1
vclz.i16 q10, q2
vclz.i16 q11, q3
vshr.u16 q8, #4
vshr.u16 q9, #4
vshr.u16 q10, #4
vshr.u16 q11, #4
vadd.u16 q8, q9
vadd.u16 q10, q11
vadd.u16 q8, q10
vadd.u16 q12, q8
.endr
vadd.u16 d24, d25
vpadd.u16 d24, d24
vpadd.u16 d24, d24
vmov.u16 r12, d24[0]
rsb r0, r12, #1024
bx lr
endfunc
function x265_count_nonzero_4_neon
vld1.s16 {d0-d3}, [r0]
vceq.u16 q0, #0
vceq.u16 q1, #0
eor r1, r1
vtrn.8 q0, q1
vshr.u8 q0, #7
vadd.u8 d0, d1
vshr.u64 d1, d0, #32
vadd.u8 d0, d1
vmov.u32 r0, d0[0]
usad8 r0, r0, r1
rsb r0, #16
bx lr
endfunc
function x265_count_nonzero_8_neon
vldm r0, {q8-q15}
eor r1, r1
vceq.u16 q8, #0
vceq.u16 q9, #0
vceq.u16 q10, #0
vceq.u16 q11, #0
vceq.u16 q12, #0
vceq.u16 q13, #0
vceq.u16 q14, #0
vceq.u16 q15, #0
vtrn.8 q8, q9
vtrn.8 q10, q11
vtrn.8 q12, q13
vtrn.8 q14, q15
vadd.s8 q8, q10
vadd.s8 q12, q14
vadd.s8 q8, q12
vadd.s8 d16, d17
vshr.u64 d17, d16, #32
vadd.s8 d16, d17
vabs.s8 d16, d16
vmov.u32 r0, d16[0]
usad8 r0, r0, r1
rsb r0, #64
bx lr
endfunc
function x265_count_nonzero_16_neon
vldm r0!, {q8-q15}
eor r1, r1
vceq.u16 q8, #0
vceq.u16 q9, #0
vceq.u16 q10, #0
vceq.u16 q11, #0
vceq.u16 q12, #0
vceq.u16 q13, #0
vceq.u16 q14, #0
vceq.u16 q15, #0
vtrn.8 q8, q9
vtrn.8 q10, q11
vtrn.8 q12, q13
vtrn.8 q14, q15
vmov q0, q8
vmov q1, q10
vmov q2, q12
vmov q3, q14
.rept 3
vldm r0!, {q8-q15}
vceq.u16 q8, #0
vceq.u16 q9, #0
vceq.u16 q10, #0
vceq.u16 q11, #0
vceq.u16 q12, #0
vceq.u16 q13, #0
vceq.u16 q14, #0
vceq.u16 q15, #0
vtrn.8 q8, q9
vtrn.8 q10, q11
vtrn.8 q12, q13
vtrn.8 q14, q15
vadd.s8 q0, q8
vadd.s8 q1, q10
vadd.s8 q2, q12
vadd.s8 q3, q14
.endr
vadd.s8 q0, q1
vadd.s8 q2, q3
vadd.s8 q0, q2
vadd.s8 d0, d1
vshr.u64 d1, d0, #32
vadd.s8 d0, d1
vabs.s8 d0, d0
vmov.u32 r0, d0[0]
usad8 r0, r0, r1
rsb r0, #256
bx lr
endfunc
function x265_count_nonzero_32_neon
vldm r0!, {q8-q15}
vceq.u16 q8, #0
vceq.u16 q9, #0
vceq.u16 q10, #0
vceq.u16 q11, #0
vceq.u16 q12, #0
vceq.u16 q13, #0
vceq.u16 q14, #0
vceq.u16 q15, #0
vtrn.8 q8, q9
vtrn.8 q10, q11
vtrn.8 q12, q13
vtrn.8 q14, q15
mov r1, #15
vmov q0, q8
vmov q1, q10
vmov q2, q12
vmov q3, q14
.loop:
vldm r0!, {q8-q15}
subs r1, #1
vceq.u16 q8, #0
vceq.u16 q9, #0
vceq.u16 q10, #0
vceq.u16 q11, #0
vceq.u16 q12, #0
vceq.u16 q13, #0
vceq.u16 q14, #0
vceq.u16 q15, #0
vtrn.8 q8, q9
vtrn.8 q10, q11
vtrn.8 q12, q13
vtrn.8 q14, q15
vadd.s8 q0, q8
vadd.s8 q1, q10
vadd.s8 q2, q12
vadd.s8 q3, q14
bgt .loop
vadd.s8 q0, q1
vadd.s8 q2, q3
vadd.s8 q0, q2
vaddl.s8 q0, d0, d1
vadd.s16 d0, d1
vshr.u64 d1, d0, #32
vadd.s16 d0, d1
vabs.s16 d0, d0
vmov.u32 r0, d0[0]
uasx r0, r0, r0
mov r0, r0, lsr 16
rsb r0, #1024
bx lr
endfunc