]> git.sesse.net Git - ffmpeg/blob - libavutil/x86/x86util.asm
Merge commit '094a7405e5d8463d7d167d893e04934ec1a84ecd'
[ffmpeg] / libavutil / x86 / x86util.asm
1 ;*****************************************************************************
2 ;* x86util.asm
3 ;*****************************************************************************
4 ;* Copyright (C) 2008-2010 x264 project
5 ;*
6 ;* Authors: Loren Merritt <lorenm@u.washington.edu>
7 ;*          Holger Lubitz <holger@lubitz.org>
8 ;*
9 ;* This file is part of FFmpeg.
10 ;*
11 ;* FFmpeg is free software; you can redistribute it and/or
12 ;* modify it under the terms of the GNU Lesser General Public
13 ;* License as published by the Free Software Foundation; either
14 ;* version 2.1 of the License, or (at your option) any later version.
15 ;*
16 ;* FFmpeg is distributed in the hope that it will be useful,
17 ;* but WITHOUT ANY WARRANTY; without even the implied warranty of
18 ;* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
19 ;* Lesser General Public License for more details.
20 ;*
21 ;* You should have received a copy of the GNU Lesser General Public
22 ;* License along with FFmpeg; if not, write to the Free Software
23 ;* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
24 ;******************************************************************************
25
26 %define program_name ff
27 %define cpuflags_mmxext cpuflags_mmx2
28
29 %include "libavutil/x86/x86inc.asm"
30
31 %macro SBUTTERFLY 4
32 %if avx_enabled == 0
33     mova      m%4, m%2
34     punpckl%1 m%2, m%3
35     punpckh%1 m%4, m%3
36 %else
37     punpckh%1 m%4, m%2, m%3
38     punpckl%1 m%2, m%3
39 %endif
40     SWAP %3, %4
41 %endmacro
42
43 %macro SBUTTERFLY2 4
44     punpckl%1 m%4, m%2, m%3
45     punpckh%1 m%2, m%2, m%3
46     SWAP %2, %4, %3
47 %endmacro
48
49 %macro SBUTTERFLYPS 3
50     unpcklps m%3, m%1, m%2
51     unpckhps m%1, m%1, m%2
52     SWAP %1, %3, %2
53 %endmacro
54
55 %macro TRANSPOSE4x4B 5
56     SBUTTERFLY bw, %1, %2, %5
57     SBUTTERFLY bw, %3, %4, %5
58     SBUTTERFLY wd, %1, %3, %5
59     SBUTTERFLY wd, %2, %4, %5
60     SWAP %2, %3
61 %endmacro
62
63 %macro TRANSPOSE4x4W 5
64     SBUTTERFLY wd, %1, %2, %5
65     SBUTTERFLY wd, %3, %4, %5
66     SBUTTERFLY dq, %1, %3, %5
67     SBUTTERFLY dq, %2, %4, %5
68     SWAP %2, %3
69 %endmacro
70
71 %macro TRANSPOSE2x4x4W 5
72     SBUTTERFLY wd,  %1, %2, %5
73     SBUTTERFLY wd,  %3, %4, %5
74     SBUTTERFLY dq,  %1, %3, %5
75     SBUTTERFLY dq,  %2, %4, %5
76     SBUTTERFLY qdq, %1, %2, %5
77     SBUTTERFLY qdq, %3, %4, %5
78 %endmacro
79
80 %macro TRANSPOSE4x4D 5
81     SBUTTERFLY dq,  %1, %2, %5
82     SBUTTERFLY dq,  %3, %4, %5
83     SBUTTERFLY qdq, %1, %3, %5
84     SBUTTERFLY qdq, %2, %4, %5
85     SWAP %2, %3
86 %endmacro
87
88 ; identical behavior to TRANSPOSE4x4D, but using SSE1 float ops
89 %macro TRANSPOSE4x4PS 5
90     SBUTTERFLYPS %1, %2, %5
91     SBUTTERFLYPS %3, %4, %5
92     movlhps m%5, m%1, m%3
93     movhlps m%3, m%1
94     SWAP %5, %1
95     movlhps m%5, m%2, m%4
96     movhlps m%4, m%2
97     SWAP %5, %2, %3
98 %endmacro
99
100 %macro TRANSPOSE8x8W 9-11
101 %if ARCH_X86_64
102     SBUTTERFLY wd,  %1, %2, %9
103     SBUTTERFLY wd,  %3, %4, %9
104     SBUTTERFLY wd,  %5, %6, %9
105     SBUTTERFLY wd,  %7, %8, %9
106     SBUTTERFLY dq,  %1, %3, %9
107     SBUTTERFLY dq,  %2, %4, %9
108     SBUTTERFLY dq,  %5, %7, %9
109     SBUTTERFLY dq,  %6, %8, %9
110     SBUTTERFLY qdq, %1, %5, %9
111     SBUTTERFLY qdq, %2, %6, %9
112     SBUTTERFLY qdq, %3, %7, %9
113     SBUTTERFLY qdq, %4, %8, %9
114     SWAP %2, %5
115     SWAP %4, %7
116 %else
117 ; in:  m0..m7, unless %11 in which case m6 is in %9
118 ; out: m0..m7, unless %11 in which case m4 is in %10
119 ; spills into %9 and %10
120 %if %0<11
121     movdqa %9, m%7
122 %endif
123     SBUTTERFLY wd,  %1, %2, %7
124     movdqa %10, m%2
125     movdqa m%7, %9
126     SBUTTERFLY wd,  %3, %4, %2
127     SBUTTERFLY wd,  %5, %6, %2
128     SBUTTERFLY wd,  %7, %8, %2
129     SBUTTERFLY dq,  %1, %3, %2
130     movdqa %9, m%3
131     movdqa m%2, %10
132     SBUTTERFLY dq,  %2, %4, %3
133     SBUTTERFLY dq,  %5, %7, %3
134     SBUTTERFLY dq,  %6, %8, %3
135     SBUTTERFLY qdq, %1, %5, %3
136     SBUTTERFLY qdq, %2, %6, %3
137     movdqa %10, m%2
138     movdqa m%3, %9
139     SBUTTERFLY qdq, %3, %7, %2
140     SBUTTERFLY qdq, %4, %8, %2
141     SWAP %2, %5
142     SWAP %4, %7
143 %if %0<11
144     movdqa m%5, %10
145 %endif
146 %endif
147 %endmacro
148
149 ; PABSW macro assumes %1 != %2, while ABS1/2 macros work in-place
150 %macro PABSW 2
151 %if cpuflag(ssse3)
152     pabsw      %1, %2
153 %elif cpuflag(mmxext)
154     pxor    %1, %1
155     psubw   %1, %2
156     pmaxsw  %1, %2
157 %else
158     pxor       %1, %1
159     pcmpgtw    %1, %2
160     pxor       %2, %1
161     psubw      %2, %1
162     SWAP       %1, %2
163 %endif
164 %endmacro
165
166 %macro PSIGNW_MMX 2
167     pxor       %1, %2
168     psubw      %1, %2
169 %endmacro
170
171 %macro PSIGNW_SSSE3 2
172     psignw     %1, %2
173 %endmacro
174
175 %macro ABS1 2
176 %if cpuflag(ssse3)
177     pabsw   %1, %1
178 %elif cpuflag(mmxext) ; a, tmp
179     pxor    %2, %2
180     psubw   %2, %1
181     pmaxsw  %1, %2
182 %else ; a, tmp
183     pxor       %2, %2
184     pcmpgtw    %2, %1
185     pxor       %1, %2
186     psubw      %1, %2
187 %endif
188 %endmacro
189
190 %macro ABS2 4
191 %if cpuflag(ssse3)
192     pabsw   %1, %1
193     pabsw   %2, %2
194 %elif cpuflag(mmxext) ; a, b, tmp0, tmp1
195     pxor    %3, %3
196     pxor    %4, %4
197     psubw   %3, %1
198     psubw   %4, %2
199     pmaxsw  %1, %3
200     pmaxsw  %2, %4
201 %else ; a, b, tmp0, tmp1
202     pxor       %3, %3
203     pxor       %4, %4
204     pcmpgtw    %3, %1
205     pcmpgtw    %4, %2
206     pxor       %1, %3
207     pxor       %2, %4
208     psubw      %1, %3
209     psubw      %2, %4
210 %endif
211 %endmacro
212
213 %macro ABSB 2 ; source mmreg, temp mmreg (unused for ssse3)
214 %if cpuflag(ssse3)
215     pabsb   %1, %1
216 %else
217     pxor    %2, %2
218     psubb   %2, %1
219     pminub  %1, %2
220 %endif
221 %endmacro
222
223 %macro ABSB2_MMX 4
224     pxor    %3, %3
225     pxor    %4, %4
226     psubb   %3, %1
227     psubb   %4, %2
228     pminub  %1, %3
229     pminub  %2, %4
230 %endmacro
231
232 %macro ABSD2_MMX 4
233     pxor    %3, %3
234     pxor    %4, %4
235     pcmpgtd %3, %1
236     pcmpgtd %4, %2
237     pxor    %1, %3
238     pxor    %2, %4
239     psubd   %1, %3
240     psubd   %2, %4
241 %endmacro
242
243 %macro ABSB2_SSSE3 4
244     pabsb   %1, %1
245     pabsb   %2, %2
246 %endmacro
247
248 %macro ABS4 6
249     ABS2 %1, %2, %5, %6
250     ABS2 %3, %4, %5, %6
251 %endmacro
252
253 %define ABSB2 ABSB2_MMX
254
255 %macro SPLATB_LOAD 3
256 %if cpuflag(ssse3)
257     movd      %1, [%2-3]
258     pshufb    %1, %3
259 %else
260     movd      %1, [%2-3] ;to avoid crossing a cacheline
261     punpcklbw %1, %1
262     SPLATW    %1, %1, 3
263 %endif
264 %endmacro
265
266 %macro SPLATB_REG 3
267 %if cpuflag(ssse3)
268     movd      %1, %2d
269     pshufb    %1, %3
270 %else
271     movd      %1, %2d
272     punpcklbw %1, %1
273     SPLATW    %1, %1, 0
274 %endif
275 %endmacro
276
277 %macro PALIGNR 4-5
278 %if cpuflag(ssse3)
279 %if %0==5
280     palignr %1, %2, %3, %4
281 %else
282     palignr %1, %2, %3
283 %endif
284 %elif cpuflag(mmx) ; [dst,] src1, src2, imm, tmp
285     %define %%dst %1
286 %if %0==5
287 %ifnidn %1, %2
288     mova    %%dst, %2
289 %endif
290     %rotate 1
291 %endif
292 %ifnidn %4, %2
293     mova    %4, %2
294 %endif
295 %if mmsize==8
296     psllq   %%dst, (8-%3)*8
297     psrlq   %4, %3*8
298 %else
299     pslldq  %%dst, 16-%3
300     psrldq  %4, %3
301 %endif
302     por     %%dst, %4
303 %endif
304 %endmacro
305
306 %macro PSHUFLW 1+
307     %if mmsize == 8
308         pshufw %1
309     %else
310         pshuflw %1
311     %endif
312 %endmacro
313
314 %macro PSWAPD 2
315 %if cpuflag(mmxext)
316     pshufw    %1, %2, q1032
317 %elif cpuflag(3dnowext)
318     pswapd    %1, %2
319 %elif cpuflag(3dnow)
320     movq      %1, %2
321     psrlq     %1, 32
322     punpckldq %1, %2
323 %endif
324 %endmacro
325
326 %macro DEINTB 5 ; mask, reg1, mask, reg2, optional src to fill masks from
327 %ifnum %5
328     pand   m%3, m%5, m%4 ; src .. y6 .. y4
329     pand   m%1, m%5, m%2 ; dst .. y6 .. y4
330 %else
331     mova   m%1, %5
332     pand   m%3, m%1, m%4 ; src .. y6 .. y4
333     pand   m%1, m%1, m%2 ; dst .. y6 .. y4
334 %endif
335     psrlw  m%2, 8        ; dst .. y7 .. y5
336     psrlw  m%4, 8        ; src .. y7 .. y5
337 %endmacro
338
339 %macro SUMSUB_BA 3-4
340 %if %0==3
341     padd%1  m%2, m%3
342     padd%1  m%3, m%3
343     psub%1  m%3, m%2
344 %else
345 %if avx_enabled == 0
346     mova    m%4, m%2
347     padd%1  m%2, m%3
348     psub%1  m%3, m%4
349 %else
350     padd%1  m%4, m%2, m%3
351     psub%1  m%3, m%2
352     SWAP    %2, %4
353 %endif
354 %endif
355 %endmacro
356
357 %macro SUMSUB_BADC 5-6
358 %if %0==6
359     SUMSUB_BA %1, %2, %3, %6
360     SUMSUB_BA %1, %4, %5, %6
361 %else
362     padd%1  m%2, m%3
363     padd%1  m%4, m%5
364     padd%1  m%3, m%3
365     padd%1  m%5, m%5
366     psub%1  m%3, m%2
367     psub%1  m%5, m%4
368 %endif
369 %endmacro
370
371 %macro SUMSUB2_AB 4
372 %ifnum %3
373     psub%1  m%4, m%2, m%3
374     psub%1  m%4, m%3
375     padd%1  m%2, m%2
376     padd%1  m%2, m%3
377 %else
378     mova    m%4, m%2
379     padd%1  m%2, m%2
380     padd%1  m%2, %3
381     psub%1  m%4, %3
382     psub%1  m%4, %3
383 %endif
384 %endmacro
385
386 %macro SUMSUB2_BA 4
387 %if avx_enabled == 0
388     mova    m%4, m%2
389     padd%1  m%2, m%3
390     padd%1  m%2, m%3
391     psub%1  m%3, m%4
392     psub%1  m%3, m%4
393 %else
394     padd%1  m%4, m%2, m%3
395     padd%1  m%4, m%3
396     psub%1  m%3, m%2
397     psub%1  m%3, m%2
398     SWAP     %2,  %4
399 %endif
400 %endmacro
401
402 %macro SUMSUBD2_AB 5
403 %ifnum %4
404     psra%1  m%5, m%2, 1  ; %3: %3>>1
405     psra%1  m%4, m%3, 1  ; %2: %2>>1
406     padd%1  m%4, m%2     ; %3: %3>>1+%2
407     psub%1  m%5, m%3     ; %2: %2>>1-%3
408     SWAP     %2, %5
409     SWAP     %3, %4
410 %else
411     mova    %5, m%2
412     mova    %4, m%3
413     psra%1  m%3, 1  ; %3: %3>>1
414     psra%1  m%2, 1  ; %2: %2>>1
415     padd%1  m%3, %5 ; %3: %3>>1+%2
416     psub%1  m%2, %4 ; %2: %2>>1-%3
417 %endif
418 %endmacro
419
420 %macro DCT4_1D 5
421 %ifnum %5
422     SUMSUB_BADC w, %4, %1, %3, %2, %5
423     SUMSUB_BA   w, %3, %4, %5
424     SUMSUB2_AB  w, %1, %2, %5
425     SWAP %1, %3, %4, %5, %2
426 %else
427     SUMSUB_BADC w, %4, %1, %3, %2
428     SUMSUB_BA   w, %3, %4
429     mova     [%5], m%2
430     SUMSUB2_AB  w, %1, [%5], %2
431     SWAP %1, %3, %4, %2
432 %endif
433 %endmacro
434
435 %macro IDCT4_1D 6-7
436 %ifnum %6
437     SUMSUBD2_AB %1, %3, %5, %7, %6
438     ; %3: %3>>1-%5 %5: %3+%5>>1
439     SUMSUB_BA   %1, %4, %2, %7
440     ; %4: %2+%4 %2: %2-%4
441     SUMSUB_BADC %1, %5, %4, %3, %2, %7
442     ; %5: %2+%4 + (%3+%5>>1)
443     ; %4: %2+%4 - (%3+%5>>1)
444     ; %3: %2-%4 + (%3>>1-%5)
445     ; %2: %2-%4 - (%3>>1-%5)
446 %else
447 %ifidn %1, w
448     SUMSUBD2_AB %1, %3, %5, [%6], [%6+16]
449 %else
450     SUMSUBD2_AB %1, %3, %5, [%6], [%6+32]
451 %endif
452     SUMSUB_BA   %1, %4, %2
453     SUMSUB_BADC %1, %5, %4, %3, %2
454 %endif
455     SWAP %2, %5, %4
456     ; %2: %2+%4 + (%3+%5>>1) row0
457     ; %3: %2-%4 + (%3>>1-%5) row1
458     ; %4: %2-%4 - (%3>>1-%5) row2
459     ; %5: %2+%4 - (%3+%5>>1) row3
460 %endmacro
461
462
463 %macro LOAD_DIFF 5
464 %ifidn %3, none
465     movh       %1, %4
466     movh       %2, %5
467     punpcklbw  %1, %2
468     punpcklbw  %2, %2
469     psubw      %1, %2
470 %else
471     movh       %1, %4
472     punpcklbw  %1, %3
473     movh       %2, %5
474     punpcklbw  %2, %3
475     psubw      %1, %2
476 %endif
477 %endmacro
478
479 %macro STORE_DCT 6
480     movq   [%5+%6+ 0], m%1
481     movq   [%5+%6+ 8], m%2
482     movq   [%5+%6+16], m%3
483     movq   [%5+%6+24], m%4
484     movhps [%5+%6+32], m%1
485     movhps [%5+%6+40], m%2
486     movhps [%5+%6+48], m%3
487     movhps [%5+%6+56], m%4
488 %endmacro
489
490 %macro LOAD_DIFF_8x4P 7-10 r0,r2,0 ; 4x dest, 2x temp, 2x pointer, increment?
491     LOAD_DIFF m%1, m%5, m%7, [%8],      [%9]
492     LOAD_DIFF m%2, m%6, m%7, [%8+r1],   [%9+r3]
493     LOAD_DIFF m%3, m%5, m%7, [%8+2*r1], [%9+2*r3]
494     LOAD_DIFF m%4, m%6, m%7, [%8+r4],   [%9+r5]
495 %if %10
496     lea %8, [%8+4*r1]
497     lea %9, [%9+4*r3]
498 %endif
499 %endmacro
500
501 %macro DIFFx2 6-7
502     movh       %3, %5
503     punpcklbw  %3, %4
504     psraw      %1, 6
505     paddsw     %1, %3
506     movh       %3, %6
507     punpcklbw  %3, %4
508     psraw      %2, 6
509     paddsw     %2, %3
510     packuswb   %2, %1
511 %endmacro
512
513 %macro STORE_DIFF 4
514     movh       %2, %4
515     punpcklbw  %2, %3
516     psraw      %1, 6
517     paddsw     %1, %2
518     packuswb   %1, %1
519     movh       %4, %1
520 %endmacro
521
522 %macro STORE_DIFFx2 8 ; add1, add2, reg1, reg2, zero, shift, source, stride
523     movh       %3, [%7]
524     movh       %4, [%7+%8]
525     psraw      %1, %6
526     psraw      %2, %6
527     punpcklbw  %3, %5
528     punpcklbw  %4, %5
529     paddw      %3, %1
530     paddw      %4, %2
531     packuswb   %3, %5
532     packuswb   %4, %5
533     movh     [%7], %3
534     movh  [%7+%8], %4
535 %endmacro
536
537 %macro PMINUB 3 ; dst, src, ignored
538 %if cpuflag(mmxext)
539     pminub   %1, %2
540 %else ; dst, src, tmp
541     mova     %3, %1
542     psubusb  %3, %2
543     psubb    %1, %3
544 %endif
545 %endmacro
546
547 %macro SPLATW 2-3 0
548 %if mmsize == 16
549     pshuflw    %1, %2, (%3)*0x55
550     punpcklqdq %1, %1
551 %elif cpuflag(mmxext)
552     pshufw     %1, %2, (%3)*0x55
553 %else
554     %ifnidn %1, %2
555         mova       %1, %2
556     %endif
557     %if %3 & 2
558         punpckhwd  %1, %1
559     %else
560         punpcklwd  %1, %1
561     %endif
562     %if %3 & 1
563         punpckhwd  %1, %1
564     %else
565         punpcklwd  %1, %1
566     %endif
567 %endif
568 %endmacro
569
570 %macro SPLATD 1
571 %if mmsize == 8
572     punpckldq  %1, %1
573 %elif cpuflag(sse2)
574     pshufd  %1, %1, 0
575 %elif cpuflag(sse)
576     shufps  %1, %1, 0
577 %endif
578 %endmacro
579
580 %macro CLIPW 3 ;(dst, min, max)
581     pmaxsw %1, %2
582     pminsw %1, %3
583 %endmacro
584
585 %macro PMINSD_MMX 3 ; dst, src, tmp
586     mova      %3, %2
587     pcmpgtd   %3, %1
588     pxor      %1, %2
589     pand      %1, %3
590     pxor      %1, %2
591 %endmacro
592
593 %macro PMAXSD_MMX 3 ; dst, src, tmp
594     mova      %3, %1
595     pcmpgtd   %3, %2
596     pand      %1, %3
597     pandn     %3, %2
598     por       %1, %3
599 %endmacro
600
601 %macro CLIPD_MMX 3-4 ; src/dst, min, max, tmp
602     PMINSD_MMX %1, %3, %4
603     PMAXSD_MMX %1, %2, %4
604 %endmacro
605
606 %macro CLIPD_SSE2 3-4 ; src/dst, min (float), max (float), unused
607     cvtdq2ps  %1, %1
608     minps     %1, %3
609     maxps     %1, %2
610     cvtps2dq  %1, %1
611 %endmacro
612
613 %macro CLIPD_SSE41 3-4 ;  src/dst, min, max, unused
614     pminsd  %1, %3
615     pmaxsd  %1, %2
616 %endmacro
617
618 %macro VBROADCASTSS 2 ; dst xmm/ymm, src m32
619 %if cpuflag(avx)
620     vbroadcastss %1, %2
621 %else ; sse
622     movss        %1, %2
623     shufps       %1, %1, 0
624 %endif
625 %endmacro
626
627 %macro VBROADCASTSD 2 ; dst xmm/ymm, src m64
628 %if cpuflag(avx) && mmsize == 32
629     vbroadcastsd %1, %2
630 %elif cpuflag(sse3)
631     movddup      %1, %2
632 %else ; sse2
633     movsd        %1, %2
634     movlhps      %1, %1
635 %endif
636 %endmacro
637
638 %macro SHUFFLE_MASK_W 8
639     %rep 8
640         %if %1>=0x80
641             db %1, %1
642         %else
643             db %1*2
644             db %1*2+1
645         %endif
646         %rotate 1
647     %endrep
648 %endmacro
649
650 %macro PMOVSXWD 2; dst, src
651 %if cpuflag(sse4)
652     pmovsxwd     %1, %2
653 %else
654     %ifnidn %1, %2
655     mova         %1, %2
656     %endif
657     punpcklwd    %1, %1
658     psrad        %1, 16
659 %endif
660 %endmacro