]> git.sesse.net Git - ffmpeg/blob - libavutil/x86/float_dsp.asm
Merge commit '7a5f4f6853047eea74a6443d73f4d74d52b2799f'
[ffmpeg] / libavutil / x86 / float_dsp.asm
1 ;*****************************************************************************
2 ;* x86-optimized Float DSP functions
3 ;*
4 ;* Copyright 2006 Loren Merritt
5 ;*
6 ;* This file is part of FFmpeg.
7 ;*
8 ;* FFmpeg is free software; you can redistribute it and/or
9 ;* modify it under the terms of the GNU Lesser General Public
10 ;* License as published by the Free Software Foundation; either
11 ;* version 2.1 of the License, or (at your option) any later version.
12 ;*
13 ;* FFmpeg is distributed in the hope that it will be useful,
14 ;* but WITHOUT ANY WARRANTY; without even the implied warranty of
15 ;* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
16 ;* Lesser General Public License for more details.
17 ;*
18 ;* You should have received a copy of the GNU Lesser General Public
19 ;* License along with FFmpeg; if not, write to the Free Software
20 ;* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
21 ;******************************************************************************
22
23 %include "x86util.asm"
24
25 SECTION .text
26
27 ;-----------------------------------------------------------------------------
28 ; void vector_fmul(float *dst, const float *src0, const float *src1, int len)
29 ;-----------------------------------------------------------------------------
30 %macro VECTOR_FMUL 0
31 cglobal vector_fmul, 4,4,2, dst, src0, src1, len
32     lea       lenq, [lend*4 - 64]
33 ALIGN 16
34 .loop:
35 %assign a 0
36 %rep 32/mmsize
37     mova      m0,   [src0q + lenq + (a+0)*mmsize]
38     mova      m1,   [src0q + lenq + (a+1)*mmsize]
39     mulps     m0, m0, [src1q + lenq + (a+0)*mmsize]
40     mulps     m1, m1, [src1q + lenq + (a+1)*mmsize]
41     mova      [dstq + lenq + (a+0)*mmsize], m0
42     mova      [dstq + lenq + (a+1)*mmsize], m1
43 %assign a a+2
44 %endrep
45
46     sub       lenq, 64
47     jge       .loop
48     REP_RET
49 %endmacro
50
51 INIT_XMM sse
52 VECTOR_FMUL
53 %if HAVE_AVX_EXTERNAL
54 INIT_YMM avx
55 VECTOR_FMUL
56 %endif
57
58 ;------------------------------------------------------------------------------
59 ; void ff_vector_fmac_scalar(float *dst, const float *src, float mul, int len)
60 ;------------------------------------------------------------------------------
61
62 %macro VECTOR_FMAC_SCALAR 0
63 %if UNIX64
64 cglobal vector_fmac_scalar, 3,3,5, dst, src, len
65 %else
66 cglobal vector_fmac_scalar, 4,4,5, dst, src, mul, len
67 %endif
68 %if ARCH_X86_32
69     VBROADCASTSS m0, mulm
70 %else
71 %if WIN64
72     SWAP 0, 2
73 %endif
74     shufps      xm0, xm0, 0
75 %if cpuflag(avx)
76     vinsertf128  m0, m0, xm0, 1
77 %endif
78 %endif
79     lea    lenq, [lend*4-64]
80 .loop:
81 %if cpuflag(fma3)
82     mova     m1,     [dstq+lenq]
83     mova     m2,     [dstq+lenq+1*mmsize]
84     fmaddps  m1, m0, [srcq+lenq], m1
85     fmaddps  m2, m0, [srcq+lenq+1*mmsize], m2
86 %else ; cpuflag
87     mulps    m1, m0, [srcq+lenq]
88     mulps    m2, m0, [srcq+lenq+1*mmsize]
89 %if mmsize < 32
90     mulps    m3, m0, [srcq+lenq+2*mmsize]
91     mulps    m4, m0, [srcq+lenq+3*mmsize]
92 %endif ; mmsize
93     addps    m1, m1, [dstq+lenq]
94     addps    m2, m2, [dstq+lenq+1*mmsize]
95 %if mmsize < 32
96     addps    m3, m3, [dstq+lenq+2*mmsize]
97     addps    m4, m4, [dstq+lenq+3*mmsize]
98 %endif ; mmsize
99 %endif ; cpuflag
100     mova  [dstq+lenq], m1
101     mova  [dstq+lenq+1*mmsize], m2
102 %if mmsize < 32
103     mova  [dstq+lenq+2*mmsize], m3
104     mova  [dstq+lenq+3*mmsize], m4
105 %endif ; mmsize
106     sub    lenq, 64
107     jge .loop
108     REP_RET
109 %endmacro
110
111 INIT_XMM sse
112 VECTOR_FMAC_SCALAR
113 %if HAVE_AVX_EXTERNAL
114 INIT_YMM avx
115 VECTOR_FMAC_SCALAR
116 %endif
117 %if HAVE_FMA3_EXTERNAL
118 INIT_YMM fma3
119 VECTOR_FMAC_SCALAR
120 %endif
121
122 ;------------------------------------------------------------------------------
123 ; void ff_vector_fmul_scalar(float *dst, const float *src, float mul, int len)
124 ;------------------------------------------------------------------------------
125
126 %macro VECTOR_FMUL_SCALAR 0
127 %if UNIX64
128 cglobal vector_fmul_scalar, 3,3,2, dst, src, len
129 %else
130 cglobal vector_fmul_scalar, 4,4,3, dst, src, mul, len
131 %endif
132 %if ARCH_X86_32
133     movss    m0, mulm
134 %elif WIN64
135     SWAP 0, 2
136 %endif
137     shufps   m0, m0, 0
138     lea    lenq, [lend*4-mmsize]
139 .loop:
140     mova     m1, [srcq+lenq]
141     mulps    m1, m0
142     mova  [dstq+lenq], m1
143     sub    lenq, mmsize
144     jge .loop
145     REP_RET
146 %endmacro
147
148 INIT_XMM sse
149 VECTOR_FMUL_SCALAR
150
151 ;------------------------------------------------------------------------------
152 ; void ff_vector_dmul_scalar(double *dst, const double *src, double mul,
153 ;                            int len)
154 ;------------------------------------------------------------------------------
155
156 %macro VECTOR_DMUL_SCALAR 0
157 %if ARCH_X86_32
158 cglobal vector_dmul_scalar, 3,4,3, dst, src, mul, len, lenaddr
159     mov          lenq, lenaddrm
160 %elif UNIX64
161 cglobal vector_dmul_scalar, 3,3,3, dst, src, len
162 %else
163 cglobal vector_dmul_scalar, 4,4,3, dst, src, mul, len
164 %endif
165 %if ARCH_X86_32
166     VBROADCASTSD   m0, mulm
167 %else
168 %if WIN64
169     SWAP 0, 2
170 %endif
171     movlhps       xm0, xm0
172 %if cpuflag(avx)
173     vinsertf128   ym0, ym0, xm0, 1
174 %endif
175 %endif
176     lea          lenq, [lend*8-2*mmsize]
177 .loop:
178     mulpd          m1, m0, [srcq+lenq       ]
179     mulpd          m2, m0, [srcq+lenq+mmsize]
180     mova   [dstq+lenq       ], m1
181     mova   [dstq+lenq+mmsize], m2
182     sub          lenq, 2*mmsize
183     jge .loop
184     REP_RET
185 %endmacro
186
187 INIT_XMM sse2
188 VECTOR_DMUL_SCALAR
189 %if HAVE_AVX_EXTERNAL
190 INIT_YMM avx
191 VECTOR_DMUL_SCALAR
192 %endif
193
194 ;-----------------------------------------------------------------------------
195 ; vector_fmul_add(float *dst, const float *src0, const float *src1,
196 ;                 const float *src2, int len)
197 ;-----------------------------------------------------------------------------
198 %macro VECTOR_FMUL_ADD 0
199 cglobal vector_fmul_add, 5,5,4, dst, src0, src1, src2, len
200     lea       lenq, [lend*4 - 2*mmsize]
201 ALIGN 16
202 .loop:
203     mova    m0,   [src0q + lenq]
204     mova    m1,   [src0q + lenq + mmsize]
205 %if cpuflag(fma3)
206     mova    m2,     [src2q + lenq]
207     mova    m3,     [src2q + lenq + mmsize]
208     fmaddps m0, m0, [src1q + lenq], m2
209     fmaddps m1, m1, [src1q + lenq + mmsize], m3
210 %else
211     mulps   m0, m0, [src1q + lenq]
212     mulps   m1, m1, [src1q + lenq + mmsize]
213     addps   m0, m0, [src2q + lenq]
214     addps   m1, m1, [src2q + lenq + mmsize]
215 %endif
216     mova    [dstq + lenq], m0
217     mova    [dstq + lenq + mmsize], m1
218
219     sub     lenq,   2*mmsize
220     jge     .loop
221     REP_RET
222 %endmacro
223
224 INIT_XMM sse
225 VECTOR_FMUL_ADD
226 %if HAVE_AVX_EXTERNAL
227 INIT_YMM avx
228 VECTOR_FMUL_ADD
229 %endif
230 %if HAVE_FMA3_EXTERNAL
231 INIT_YMM fma3
232 VECTOR_FMUL_ADD
233 %endif
234
235 ;-----------------------------------------------------------------------------
236 ; void vector_fmul_reverse(float *dst, const float *src0, const float *src1,
237 ;                          int len)
238 ;-----------------------------------------------------------------------------
239 %macro VECTOR_FMUL_REVERSE 0
240 cglobal vector_fmul_reverse, 4,4,2, dst, src0, src1, len
241     lea       lenq, [lend*4 - 2*mmsize]
242 ALIGN 16
243 .loop:
244 %if cpuflag(avx)
245     vmovaps     xmm0, [src1q + 16]
246     vinsertf128 m0, m0, [src1q], 1
247     vshufps     m0, m0, m0, q0123
248     vmovaps     xmm1, [src1q + mmsize + 16]
249     vinsertf128 m1, m1, [src1q + mmsize], 1
250     vshufps     m1, m1, m1, q0123
251 %else
252     mova    m0, [src1q]
253     mova    m1, [src1q + mmsize]
254     shufps  m0, m0, q0123
255     shufps  m1, m1, q0123
256 %endif
257     mulps   m0, m0, [src0q + lenq + mmsize]
258     mulps   m1, m1, [src0q + lenq]
259     mova    [dstq + lenq + mmsize], m0
260     mova    [dstq + lenq], m1
261     add     src1q, 2*mmsize
262     sub     lenq,  2*mmsize
263     jge     .loop
264     REP_RET
265 %endmacro
266
267 INIT_XMM sse
268 VECTOR_FMUL_REVERSE
269 %if HAVE_AVX_EXTERNAL
270 INIT_YMM avx
271 VECTOR_FMUL_REVERSE
272 %endif
273
274 ; float scalarproduct_float_sse(const float *v1, const float *v2, int len)
275 INIT_XMM sse
276 cglobal scalarproduct_float, 3,3,2, v1, v2, offset
277     neg   offsetq
278     shl   offsetq, 2
279     sub       v1q, offsetq
280     sub       v2q, offsetq
281     xorps    xmm0, xmm0
282 .loop:
283     movaps   xmm1, [v1q+offsetq]
284     mulps    xmm1, [v2q+offsetq]
285     addps    xmm0, xmm1
286     add   offsetq, 16
287     js .loop
288     movhlps  xmm1, xmm0
289     addps    xmm0, xmm1
290     movss    xmm1, xmm0
291     shufps   xmm0, xmm0, 1
292     addss    xmm0, xmm1
293 %if ARCH_X86_64 == 0
294     movss     r0m,  xmm0
295     fld dword r0m
296 %endif
297     RET
298
299 ;-----------------------------------------------------------------------------
300 ; void ff_butterflies_float(float *src0, float *src1, int len);
301 ;-----------------------------------------------------------------------------
302 INIT_XMM sse
303 cglobal butterflies_float, 3,3,3, src0, src1, len
304 %if ARCH_X86_64
305     movsxd    lenq, lend
306 %endif
307     test      lenq, lenq
308     jz .end
309     shl       lenq, 2
310     add      src0q, lenq
311     add      src1q, lenq
312     neg       lenq
313 .loop:
314     mova        m0, [src0q + lenq]
315     mova        m1, [src1q + lenq]
316     subps       m2, m0, m1
317     addps       m0, m0, m1
318     mova        [src1q + lenq], m2
319     mova        [src0q + lenq], m0
320     add       lenq, mmsize
321     jl .loop
322 .end:
323     REP_RET