[FFmpeg-devel] [PATCH 7/7] lavc/flacenc: partially unroll loop in flac_enc_lpc_32

James Darnley james.darnley at gmail.com
Fri Feb 14 12:40:12 CET 2014


Now does 6 samples per iteration, up from 2.

>From 1.6 to 2.1 times faster again.  2.5 to 3.9 times faster overall.
Runtime is reduced by a further 4 to 17%.  Reduced by 9 to 65% overall.

Same conditions as previously.
---
 libavcodec/x86/flac_dsp_gpl.asm |   34 +++++++++++++++++++++++++++++-----
 1 files changed, 29 insertions(+), 5 deletions(-)

diff --git a/libavcodec/x86/flac_dsp_gpl.asm b/libavcodec/x86/flac_dsp_gpl.asm
index ed33b1a..b7196b9 100644
--- a/libavcodec/x86/flac_dsp_gpl.asm
+++ b/libavcodec/x86/flac_dsp_gpl.asm
@@ -127,11 +127,11 @@ RET
 
 INIT_XMM sse42
 %if ARCH_X86_64
-    cglobal flac_enc_lpc_32, 5, 7, 4, mmsize, res, smp, len, order, coefs, shift
+    cglobal flac_enc_lpc_32, 5, 7, 8, mmsize, res, smp, len, order, coefs, shift
     %define posj r5
     %define negj r6
 %else
-    cglobal flac_enc_lpc_32, 5, 6, 4, mmsize, res, smp, len, order, coefs, shift
+    cglobal flac_enc_lpc_32, 5, 6, 8, mmsize, res, smp, len, order, coefs, shift
     %define posj r2
     %define negj r5
 %endif
@@ -158,15 +158,25 @@ mova  [rsp],    m4 ; sign extend mask
 
 .looplen:
     pxor m0,   m0
+    pxor m4,   m4
+    pxor m6,   m6
     mov  posj, orderq
     xor  negj, negj
     .looporder:
         movd   m2,  [coefsq+posj*4] ; c = coefs[j]
         SPLATD m2
         movh   m1,  [smpq+negj*4-4] ; s = smp[i-j-1]
+        movh   m5,  [smpq+negj*4-4+mmsize/2]
+        movh   m7,  [smpq+negj*4-4+mmsize]
         pshufd m1,   m1, q3130
+        pshufd m5,   m5, q3130
+        pshufd m7,   m7, q3130
         pmuldq m1,   m2
+        pmuldq m5,   m2
+        pmuldq m7,   m2
         paddq  m0,   m1             ; p += c * s
+        paddq  m4,   m5
+        paddq  m6,   m7
 
         dec    negj
         inc    posj
@@ -174,14 +184,28 @@ mova  [rsp],    m4 ; sign extend mask
 
     pxor    m2,    m2
     HACK_PSRAQ m0, m3, [rsp], m2     ; p >>= shift
+    pxor    m2,    m2
+    HACK_PSRAQ m4, m3, [rsp], m2
+    pxor    m2,    m2
+    HACK_PSRAQ m6, m3, [rsp], m2
     CLIPQ   m0,   [pq_int_min], [pq_int_max], m2 ; clip(p >> shift)
+    CLIPQ   m4,   [pq_int_min], [pq_int_max], m2
+    CLIPQ   m6,   [pq_int_min], [pq_int_max], m2
     pshufd  m0,    m0, q0020 ; pack into first 2 dwords
+    pshufd  m4,    m4, q0020
+    pshufd  m6,    m6, q0020
     movh    m1,   [smpq]
+    movh    m5,   [smpq+mmsize/2]
+    movh    m7,   [smpq+mmsize]
     psubd   m1,    m0                ; smp[i] - p
+    psubd   m5,    m4
+    psubd   m7,    m6
     movh   [resq], m1                ; res[i] = smp[i] - (p >> shift)
+    movh   [resq+mmsize/2], m5
+    movh   [resq+mmsize], m7
 
-    add    resq,  mmsize/2
-    add    smpq,  mmsize/2
-    sub    lenmp, mmsize/8
+    add    resq,  (3*mmsize)/2
+    add    smpq,  (3*mmsize)/2
+    sub    lenmp, (3*mmsize)/8
 jg .looplen
 RET
-- 
1.7.9



More information about the ffmpeg-devel mailing list