📄 fdct_mmx_skal.asm
字号:
psubsw mm1, mm6 ; t6 = In1-In6
paddsw mm6, [%2+1*16] ; t1 = In1+In6
psubsw mm7, mm4 ; tm03 = t0-t3
psubsw mm6, mm5 ; tm12 = t1-t2
paddsw mm4, mm4 ; 2.t3
paddsw mm5, mm5 ; 2.t2
paddsw mm4, mm7 ; tp03 = t0+t3
paddsw mm5, mm6 ; tp12 = t1+t2
psllw mm2, %3+1 ; shift t5 (shift +1 to..
psllw mm1, %3+1 ; shift t6 ..compensate cos4/2)
psllw mm4, %3 ; shift t3
psllw mm5, %3 ; shift t2
psllw mm7, %3 ; shift t0
psllw mm6, %3 ; shift t1
psllw mm3, %3 ; shift t4
psllw mm0, %3 ; shift t7
psubsw mm4, mm5 ; out4 = tp03-tp12
psubsw mm1, mm2 ; mm1: t6-t5
paddsw mm5, mm5
paddsw mm2, mm2
paddsw mm5, mm4 ; out0 = tp03+tp12
movq [%1+4*16], mm4 ; => out4
paddsw mm2, mm1 ; mm2: t6+t5
movq [%1+0*16], mm5 ; => out0
movq mm4, [tan2] ; mm4 <= tan2
pmulhw mm4, mm7 ; tm03*tan2
movq mm5, [tan2] ; mm5 <= tan2
psubsw mm4, mm6 ; out6 = tm03*tan2 - tm12
pmulhw mm5, mm6 ; tm12*tan2
paddsw mm5, mm7 ; out2 = tm12*tan2 + tm03
movq mm6, [sqrt2]
movq mm7, [MMX_One]
pmulhw mm2, mm6 ; mm2: tp65 = (t6 + t5)*cos4
por mm5, mm7 ; correct out2
por mm4, mm7 ; correct out6
pmulhw mm1, mm6 ; mm1: tm65 = (t6 - t5)*cos4
por mm2, mm7 ; correct tp65
movq [%1+2*16], mm5 ; => out2
movq mm5, mm3 ; save t4
movq [%1+6*16], mm4 ; => out6
movq mm4, mm0 ; save t7
psubsw mm3, mm1 ; mm3: tm465 = t4 - tm65
psubsw mm0, mm2 ; mm0: tm765 = t7 - tp65
paddsw mm2, mm4 ; mm2: tp765 = t7 + tp65
paddsw mm1, mm5 ; mm1: tp465 = t4 + tm65
movq mm4, [tan3] ; tan3 - 1
movq mm5, [tan1] ; tan1
movq mm7, mm3 ; save tm465
pmulhw mm3, mm4 ; tm465*(tan3-1)
movq mm6, mm1 ; save tp465
pmulhw mm1, mm5 ; tp465*tan1
paddsw mm3, mm7 ; tm465*tan3
pmulhw mm4, mm0 ; tm765*(tan3-1)
paddsw mm4, mm0 ; tm765*tan3
pmulhw mm5, mm2 ; tp765*tan1
paddsw mm1, mm2 ; out1 = tp765 + tp465*tan1
psubsw mm0, mm3 ; out3 = tm765 - tm465*tan3
paddsw mm7, mm4 ; out5 = tm465 + tm765*tan3
psubsw mm5, mm6 ; out7 =-tp465 + tp765*tan1
movq [%1+1*16], mm1 ; => out1
movq [%1+3*16], mm0 ; => out3
movq [%1+5*16], mm7 ; => out5
movq [%1+7*16], mm5 ; => out7
%endmacro
;-----------------------------------------------------------------------------
; fMTX_MULT_XMM (~20c)
; %1=dst, %2=src, %3 = Coeffs, %4/%5=rounders
;-----------------------------------------------------------------------------
%macro fMTX_MULT_XMM 5
movq mm0, [%2 + 0] ; mm0 = [0123]
; the 'pshufw' below is the only SSE instruction.
; For MMX-only version, it should be emulated with
; some 'punpck' soup...
pshufw mm1, [%2 + 8], 00011011b ; mm1 = [7654]
movq mm7, mm0
paddsw mm0, mm1 ; mm0 = [a0 a1 a2 a3]
psubsw mm7, mm1 ; mm7 = [b0 b1 b2 b3]
movq mm1, mm0
punpckldq mm0, mm7 ; mm0 = [a0 a1 b0 b1]
punpckhdq mm1, mm7 ; mm1 = [b2 b3 a2 a3]
movq mm2, qword [%3 + 0] ; [ M00 M01 M16 M17]
movq mm3, qword [%3 + 8] ; [ M02 M03 M18 M19]
pmaddwd mm2, mm0 ; [a0.M00+a1.M01 | b0.M16+b1.M17]
movq mm4, qword [%3 + 16] ; [ M04 M05 M20 M21]
pmaddwd mm3, mm1 ; [a2.M02+a3.M03 | b2.M18+b3.M19]
movq mm5, qword [%3 + 24] ; [ M06 M07 M22 M23]
pmaddwd mm4, mm0 ; [a0.M04+a1.M05 | b0.M20+b1.M21]
movq mm6, qword [%3 + 32] ; [ M08 M09 M24 M25]
pmaddwd mm5, mm1 ; [a2.M06+a3.M07 | b2.M22+b3.M23]
movq mm7, qword [%3 + 40] ; [ M10 M11 M26 M27]
pmaddwd mm6, mm0 ; [a0.M08+a1.M09 | b0.M24+b1.M25]
paddd mm2, mm3 ; [ out0 | out1 ]
pmaddwd mm7, mm1 ; [a0.M10+a1.M11 | b0.M26+b1.M27]
psrad mm2, 16
pmaddwd mm0, qword [%3 + 48] ; [a0.M12+a1.M13 | b0.M28+b1.M29]
paddd mm4, mm5 ; [ out2 | out3 ]
pmaddwd mm1, qword [%3 + 56] ; [a0.M14+a1.M15 | b0.M30+b1.M31]
psrad mm4, 16
paddd mm6, mm7 ; [ out4 | out5 ]
psrad mm6, 16
paddd mm0, mm1 ; [ out6 | out7 ]
psrad mm0, 16
packssdw mm2, mm4 ; [ out0|out1|out2|out3 ]
paddsw mm2, [%4] ; Round
packssdw mm6, mm0 ; [ out4|out5|out6|out7 ]
paddsw mm6, [%5] ; Round
psraw mm2, 4 ; => [-2048, 2047]
psraw mm6, 4
movq [%1 + 0], mm2
movq [%1 + 8], mm6
%endmacro
;-----------------------------------------------------------------------------
; fMTX_MULT_MMX (~22c)
; %1=dst, %2=src, %3 = Coeffs, %4/%5=rounders
;-----------------------------------------------------------------------------
%macro fMTX_MULT_MMX 5
; MMX-only version (no 'pshufw'. ~10% overall slower than SSE)
movd mm1, [%2 + 8 + 4] ; [67..]
movq mm0, [%2 + 0] ; mm0 = [0123]
movq mm7, mm0
punpcklwd mm1, [%2 + 8] ; [6475]
movq mm2, mm1
psrlq mm1, 32 ; [75..]
punpcklwd mm1,mm2 ; [7654]
paddsw mm0, mm1 ; mm0 = [a0 a1 a2 a3]
psubsw mm7, mm1 ; mm7 = [b0 b1 b2 b3]
movq mm1, mm0
punpckldq mm0, mm7 ; mm0 = [a0 a1 b0 b1]
punpckhdq mm1, mm7 ; mm1 = [b2 b3 a2 a3]
movq mm2, qword [%3 + 0] ; [ M00 M01 M16 M17]
movq mm3, qword [%3 + 8] ; [ M02 M03 M18 M19]
pmaddwd mm2, mm0 ; [a0.M00+a1.M01 | b0.M16+b1.M17]
movq mm4, qword [%3 + 16] ; [ M04 M05 M20 M21]
pmaddwd mm3, mm1 ; [a2.M02+a3.M03 | b2.M18+b3.M19]
movq mm5, qword [%3 + 24] ; [ M06 M07 M22 M23]
pmaddwd mm4, mm0 ; [a0.M04+a1.M05 | b0.M20+b1.M21]
movq mm6, qword [%3 + 32] ; [ M08 M09 M24 M25]
pmaddwd mm5, mm1 ; [a2.M06+a3.M07 | b2.M22+b3.M23]
movq mm7, qword [%3 + 40] ; [ M10 M11 M26 M27]
pmaddwd mm6, mm0 ; [a0.M08+a1.M09 | b0.M24+b1.M25]
paddd mm2, mm3 ; [ out0 | out1 ]
pmaddwd mm7, mm1 ; [a0.M10+a1.M11 | b0.M26+b1.M27]
psrad mm2, 16
pmaddwd mm0, qword [%3 + 48] ; [a0.M12+a1.M13 | b0.M28+b1.M29]
paddd mm4, mm5 ; [ out2 | out3 ]
pmaddwd mm1, qword [%3 + 56] ; [a0.M14+a1.M15 | b0.M30+b1.M31]
psrad mm4, 16
paddd mm6, mm7 ; [ out4 | out5 ]
psrad mm6, 16
paddd mm0, mm1 ; [ out6 | out7 ]
psrad mm0, 16
packssdw mm2, mm4 ; [ out0|out1|out2|out3 ]
paddsw mm2, [%4] ; Round
packssdw mm6, mm0 ; [ out4|out5|out6|out7 ]
paddsw mm6, [%5] ; Round
psraw mm2, 4 ; => [-2048, 2047]
psraw mm6, 4
movq [%1 + 0], mm2
movq [%1 + 8], mm6
%endmacro
;-----------------------------------------------------------------------------
; MAKE_FDCT_FUNC
; %1 funcname, %2 macro for row dct
;-----------------------------------------------------------------------------
%macro MAKE_FDCT_FUNC 2
ALIGN 16
cglobal %1
%1:
%ifdef UNROLLED_LOOP
mov ecx, [esp + 4]
%else
push ebx
push edi
mov ecx, [esp + 8 + 4]
%endif
fLLM_PASS ecx+0, ecx+0, 3
fLLM_PASS ecx+8, ecx+8, 3
%ifdef UNROLLED_LOOP
%assign i 0
%rep 8
%2 ecx+i*16, ecx+i*16, fdct_table+i*64, fdct_rounding_1+i*8, fdct_rounding_2+i*8
%assign i i+1
%endrep
%else
mov eax, 8
mov edx, fdct_table
mov ebx, fdct_rounding_1
mov edi, fdct_rounding_2
.loop
%2 ecx, ecx, edx, ebx, edi
add eax, 2*16
add edx, 2*32
add ebx, 2*4
add edi, 2*4
dec eax
jne .loop
pop edi
pop ebx
%endif
ret
%endmacro
;=============================================================================
; Code
;=============================================================================
SECTION .text
;-----------------------------------------------------------------------------
; void fdct_mmx_skal(int16_t block[64]];
;-----------------------------------------------------------------------------
MAKE_FDCT_FUNC fdct_mmx_skal, fMTX_MULT_MMX
;-----------------------------------------------------------------------------
; void fdct_xmm_skal(int16_t block[64]];
;-----------------------------------------------------------------------------
MAKE_FDCT_FUNC fdct_xmm_skal, fMTX_MULT_XMM
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -