[FFmpeg-devel] [PATCH 04/11] x86: dcadsp: implement SSE lfe_dir
Christophe Gisquet
christophe.gisquet at gmail.com
Thu Feb 6 01:41:55 CET 2014
Results for Arrandale/Windows:
32: 1670 -> 316
64: 728 -> 298
---
libavcodec/x86/dcadsp.asm | 105 +++++++++++++++++++++++++++++++++++++++++++
libavcodec/x86/dcadsp_init.c | 6 +++
2 files changed, 111 insertions(+)
diff --git a/libavcodec/x86/dcadsp.asm b/libavcodec/x86/dcadsp.asm
index 03593ce..4a682be 100644
--- a/libavcodec/x86/dcadsp.asm
+++ b/libavcodec/x86/dcadsp.asm
@@ -88,3 +88,108 @@ INT8X8_FMUL_INT32 3
INIT_XMM sse4
INT8X8_FMUL_INT32 3
+
+; %1=v0/v1 %2=in1 %3=in2
+%macro FIR_LOOP 2-3
+.loop%1:
+%define va m1
+%define vb m2
+%if %1
+%define OFFSET 0
+%else
+%define OFFSET NUM_COEF*count
+%endif
+; for v0, incrementint and for v1, decrementing
+ mova va, [cf0q + OFFSET]
+ mova vb, [cf0q + OFFSET + 4*NUM_COEF]
+%if %0 == 3
+ mova m4, [cf0q + OFFSET + mmsize]
+ mova SCALE, [cf0q + OFFSET + 4*NUM_COEF + mmsize]
+%endif
+ mulps va, %2
+ mulps vb, %2
+%if %0 == 3
+ mulps m4, %3
+ mulps SCALE, %3
+ addps va, m4
+ addps vb, SCALE
+%endif
+ ; va = va1 va2 va3 va4
+ ; vb = vb1 vb2 vb3 vb4
+%if %1
+%define O1 vb
+%define O2 va
+%else
+%define O1 va
+%define O2 vb
+%endif
+ mova m4, O1
+ unpcklps O1, O2 ; va3 vb3 va4 vb4
+ unpckhps m4, O2 ; va1 vb1 va2 vb2
+ addps m4, O1 ; va1+3 vb1+3 va2+4 vb2+4
+ movhlps O2, m4 ; va1+3 vb1+3
+ addps O2, m4 ; va0..4 vb0..4
+%if %1
+ movh [outq + count], O2
+ sub cf0q, 8*NUM_COEF
+%else
+ movh [outq + count], O2
+%endif
+ add count, 8
+ jl .loop%1
+%endmacro
+
+; dca_lfe_fir(float *out, float *in, float *coefs, float scale)
+%macro DCA_LFE_FIR 1
+cglobal dca_lfe_fir%1, 3,3,6-%1, out, in, cf0, scale
+
+%if WIN64
+ SWAP 0, 3
+%endif
+%define SCALE m0
+%define IN1 m3
+%define IN2 m5
+%define count inq
+%define NUM_COEF 4*(2-%1)
+%define NUM_OUT 32*(%1+1)
+
+%if ARCH_X86_32
+ movss SCALE, scalem
+%endif
+
+ movu IN1, [inq + 4 - 1*mmsize]
+ shufps IN1, IN1, q0123
+%if %1 == 0
+ movu IN2, [inq + 4 - 2*mmsize]
+ shufps IN2, IN2, q0123
+%endif
+
+ mov count, -4*NUM_OUT
+ SPLATD SCALE
+ add cf0q, 4*NUM_COEF*NUM_OUT
+ add outq, 4*NUM_OUT
+ ; compute v0 first
+ mulps IN1, SCALE
+%if %1 == 0
+ mulps IN2, SCALE
+ FIR_LOOP 0, IN1, IN2
+%else
+ FIR_LOOP 0, IN1
+%endif
+ shufps IN1, IN1, q0123
+ mov count, -4*NUM_OUT
+ ; cf1 already correctly positioned
+ add outq, 4*NUM_OUT ; outq now at out2
+ sub cf0q, 8*NUM_COEF
+%if %1 == 0
+ shufps IN2, IN2, q0123
+ FIR_LOOP 1, IN2, IN1
+%else
+ FIR_LOOP 1, IN1
+%endif
+ RET
+%endmacro
+
+INIT_XMM sse
+DCA_LFE_FIR 0
+DCA_LFE_FIR 1
diff --git a/libavcodec/x86/dcadsp_init.c b/libavcodec/x86/dcadsp_init.c
index 39490a2..8376cc4 100644
--- a/libavcodec/x86/dcadsp_init.c
+++ b/libavcodec/x86/dcadsp_init.c
@@ -26,6 +26,10 @@
void ff_int8x8_fmul_int32_sse(float *dst, const int8_t *src, int scale);
void ff_int8x8_fmul_int32_sse2(float *dst, const int8_t *src, int scale);
void ff_int8x8_fmul_int32_sse4(float *dst, const int8_t *src, int scale);
+void ff_dca_lfe_fir0_sse(float *out, const float *in, const float *coefs,
+ float scale);
+void ff_dca_lfe_fir1_sse(float *out, const float *in, const float *coefs,
+ float scale);
av_cold void ff_dcadsp_init_x86(DCADSPContext *s)
{
@@ -35,6 +39,8 @@ av_cold void ff_dcadsp_init_x86(DCADSPContext *s)
#if ARCH_X86_32
s->int8x8_fmul_int32 = ff_int8x8_fmul_int32_sse;
#endif
+ s->lfe_fir[0] = ff_dca_lfe_fir0_sse;
+ s->lfe_fir[1] = ff_dca_lfe_fir1_sse;
}
if (EXTERNAL_SSE2(mm_flags)) {
--
1.8.0.msysgit.0
More information about the ffmpeg-devel
mailing list