• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1/*
2 * Copyright (c) 2008 Mans Rullgard <mans@mansr.com>
3 *
4 * This file is part of FFmpeg.
5 *
6 * FFmpeg is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
10 *
11 * FFmpeg is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14 * Lesser General Public License for more details.
15 *
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with FFmpeg; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
19 */
20
21#include "libavutil/arm/asm.S"
22#include "neon.S"
23
24        /* H.264 loop filter */
25
26.macro  h264_loop_filter_start
27        ldr             r12, [sp]
28        tst             r2,  r2
29        ldr             r12, [r12]
30        it              ne
31        tstne           r3,  r3
32        vmov.32         d24[0], r12
33        and             r12, r12, r12, lsl #16
34        it              eq
35        bxeq            lr
36        ands            r12, r12, r12, lsl #8
37        it              lt
38        bxlt            lr
39.endm
40
41.macro  h264_loop_filter_luma
42        vdup.8          q11, r2         @ alpha
43        vmovl.u8        q12, d24
44        vabd.u8         q6,  q8,  q0    @ abs(p0 - q0)
45        vmovl.u16       q12, d24
46        vabd.u8         q14, q9,  q8    @ abs(p1 - p0)
47        vsli.16         q12, q12, #8
48        vabd.u8         q15, q1,  q0    @ abs(q1 - q0)
49        vsli.32         q12, q12, #16
50        vclt.u8         q6,  q6,  q11   @ < alpha
51        vdup.8          q11, r3         @ beta
52        vclt.s8         q7,  q12, #0
53        vclt.u8         q14, q14, q11   @ < beta
54        vclt.u8         q15, q15, q11   @ < beta
55        vbic            q6,  q6,  q7
56        vabd.u8         q4,  q10, q8    @ abs(p2 - p0)
57        vand            q6,  q6,  q14
58        vabd.u8         q5,  q2,  q0    @ abs(q2 - q0)
59        vclt.u8         q4,  q4,  q11   @ < beta
60        vand            q6,  q6,  q15
61        vclt.u8         q5,  q5,  q11   @ < beta
62        vand            q4,  q4,  q6
63        vand            q5,  q5,  q6
64        vand            q12, q12, q6
65        vrhadd.u8       q14, q8,  q0
66        vsub.i8         q6,  q12, q4
67        vqadd.u8        q7,  q9,  q12
68        vhadd.u8        q10, q10, q14
69        vsub.i8         q6,  q6,  q5
70        vhadd.u8        q14, q2,  q14
71        vmin.u8         q7,  q7,  q10
72        vqsub.u8        q11, q9,  q12
73        vqadd.u8        q2,  q1,  q12
74        vmax.u8         q7,  q7,  q11
75        vqsub.u8        q11, q1,  q12
76        vmin.u8         q14, q2,  q14
77        vmovl.u8        q2,  d0
78        vmax.u8         q14, q14, q11
79        vmovl.u8        q10, d1
80        vsubw.u8        q2,  q2,  d16
81        vsubw.u8        q10, q10, d17
82        vshl.i16        q2,  q2,  #2
83        vshl.i16        q10, q10, #2
84        vaddw.u8        q2,  q2,  d18
85        vaddw.u8        q10, q10, d19
86        vsubw.u8        q2,  q2,  d2
87        vsubw.u8        q10, q10, d3
88        vrshrn.i16      d4,  q2,  #3
89        vrshrn.i16      d5,  q10, #3
90        vbsl            q4,  q7,  q9
91        vbsl            q5,  q14, q1
92        vneg.s8         q7,  q6
93        vmovl.u8        q14, d16
94        vmin.s8         q2,  q2,  q6
95        vmovl.u8        q6,  d17
96        vmax.s8         q2,  q2,  q7
97        vmovl.u8        q11, d0
98        vmovl.u8        q12, d1
99        vaddw.s8        q14, q14, d4
100        vaddw.s8        q6,  q6,  d5
101        vsubw.s8        q11, q11, d4
102        vsubw.s8        q12, q12, d5
103        vqmovun.s16     d16, q14
104        vqmovun.s16     d17, q6
105        vqmovun.s16     d0,  q11
106        vqmovun.s16     d1,  q12
107.endm
108
109function ff_h264_v_loop_filter_luma_neon, export=1
110        h264_loop_filter_start
111
112        vld1.8          {d0, d1},  [r0,:128], r1
113        vld1.8          {d2, d3},  [r0,:128], r1
114        vld1.8          {d4, d5},  [r0,:128], r1
115        sub             r0,  r0,  r1, lsl #2
116        sub             r0,  r0,  r1, lsl #1
117        vld1.8          {d20,d21}, [r0,:128], r1
118        vld1.8          {d18,d19}, [r0,:128], r1
119        vld1.8          {d16,d17}, [r0,:128], r1
120
121        vpush           {d8-d15}
122
123        h264_loop_filter_luma
124
125        sub             r0,  r0,  r1, lsl #1
126        vst1.8          {d8, d9},  [r0,:128], r1
127        vst1.8          {d16,d17}, [r0,:128], r1
128        vst1.8          {d0, d1},  [r0,:128], r1
129        vst1.8          {d10,d11}, [r0,:128]
130
131        vpop            {d8-d15}
132        bx              lr
133endfunc
134
135function ff_h264_h_loop_filter_luma_neon, export=1
136        h264_loop_filter_start
137
138        sub             r0,  r0,  #4
139        vld1.8          {d6},  [r0], r1
140        vld1.8          {d20}, [r0], r1
141        vld1.8          {d18}, [r0], r1
142        vld1.8          {d16}, [r0], r1
143        vld1.8          {d0},  [r0], r1
144        vld1.8          {d2},  [r0], r1
145        vld1.8          {d4},  [r0], r1
146        vld1.8          {d26}, [r0], r1
147        vld1.8          {d7},  [r0], r1
148        vld1.8          {d21}, [r0], r1
149        vld1.8          {d19}, [r0], r1
150        vld1.8          {d17}, [r0], r1
151        vld1.8          {d1},  [r0], r1
152        vld1.8          {d3},  [r0], r1
153        vld1.8          {d5},  [r0], r1
154        vld1.8          {d27}, [r0], r1
155
156        transpose_8x8   q3, q10, q9, q8, q0, q1, q2, q13
157
158        vpush           {d8-d15}
159
160        h264_loop_filter_luma
161
162        transpose_4x4   q4, q8, q0, q5
163
164        sub             r0,  r0,  r1, lsl #4
165        add             r0,  r0,  #2
166        vst1.32         {d8[0]},  [r0], r1
167        vst1.32         {d16[0]}, [r0], r1
168        vst1.32         {d0[0]},  [r0], r1
169        vst1.32         {d10[0]}, [r0], r1
170        vst1.32         {d8[1]},  [r0], r1
171        vst1.32         {d16[1]}, [r0], r1
172        vst1.32         {d0[1]},  [r0], r1
173        vst1.32         {d10[1]}, [r0], r1
174        vst1.32         {d9[0]},  [r0], r1
175        vst1.32         {d17[0]}, [r0], r1
176        vst1.32         {d1[0]},  [r0], r1
177        vst1.32         {d11[0]}, [r0], r1
178        vst1.32         {d9[1]},  [r0], r1
179        vst1.32         {d17[1]}, [r0], r1
180        vst1.32         {d1[1]},  [r0], r1
181        vst1.32         {d11[1]}, [r0], r1
182
183        vpop            {d8-d15}
184        bx              lr
185endfunc
186
187.macro  h264_loop_filter_chroma
188        vdup.8          d22, r2         @ alpha
189        vmovl.u8        q12, d24
190        vabd.u8         d26, d16, d0    @ abs(p0 - q0)
191        vmovl.u8        q2,  d0
192        vabd.u8         d28, d18, d16   @ abs(p1 - p0)
193        vsubw.u8        q2,  q2,  d16
194        vsli.16         d24, d24, #8
195        vshl.i16        q2,  q2,  #2
196        vabd.u8         d30, d2,  d0    @ abs(q1 - q0)
197        vaddw.u8        q2,  q2,  d18
198        vclt.u8         d26, d26, d22   @ < alpha
199        vsubw.u8        q2,  q2,  d2
200        vdup.8          d22, r3         @ beta
201        vrshrn.i16      d4,  q2,  #3
202        vclt.u8         d28, d28, d22   @ < beta
203        vclt.u8         d30, d30, d22   @ < beta
204        vmin.s8         d4,  d4,  d24
205        vneg.s8         d25, d24
206        vand            d26, d26, d28
207        vmax.s8         d4,  d4,  d25
208        vand            d26, d26, d30
209        vmovl.u8        q11, d0
210        vand            d4,  d4,  d26
211        vmovl.u8        q14, d16
212        vaddw.s8        q14, q14, d4
213        vsubw.s8        q11, q11, d4
214        vqmovun.s16     d16, q14
215        vqmovun.s16     d0,  q11
216.endm
217
218function ff_h264_v_loop_filter_chroma_neon, export=1
219        h264_loop_filter_start
220
221        sub             r0,  r0,  r1, lsl #1
222        vld1.8          {d18}, [r0,:64], r1
223        vld1.8          {d16}, [r0,:64], r1
224        vld1.8          {d0},  [r0,:64], r1
225        vld1.8          {d2},  [r0,:64]
226
227        h264_loop_filter_chroma
228
229        sub             r0,  r0,  r1, lsl #1
230        vst1.8          {d16}, [r0,:64], r1
231        vst1.8          {d0},  [r0,:64], r1
232
233        bx              lr
234endfunc
235
236function ff_h264_h_loop_filter_chroma_neon, export=1
237        h264_loop_filter_start
238
239        sub             r0,  r0,  #2
240h_loop_filter_chroma420:
241        vld1.32         {d18[0]}, [r0], r1
242        vld1.32         {d16[0]}, [r0], r1
243        vld1.32         {d0[0]},  [r0], r1
244        vld1.32         {d2[0]},  [r0], r1
245        vld1.32         {d18[1]}, [r0], r1
246        vld1.32         {d16[1]}, [r0], r1
247        vld1.32         {d0[1]},  [r0], r1
248        vld1.32         {d2[1]},  [r0], r1
249
250        vtrn.16         d18, d0
251        vtrn.16         d16, d2
252        vtrn.8          d18, d16
253        vtrn.8          d0,  d2
254
255        h264_loop_filter_chroma
256
257        vtrn.16         d18, d0
258        vtrn.16         d16, d2
259        vtrn.8          d18, d16
260        vtrn.8          d0,  d2
261
262        sub             r0,  r0,  r1, lsl #3
263        vst1.32         {d18[0]}, [r0], r1
264        vst1.32         {d16[0]}, [r0], r1
265        vst1.32         {d0[0]},  [r0], r1
266        vst1.32         {d2[0]},  [r0], r1
267        vst1.32         {d18[1]}, [r0], r1
268        vst1.32         {d16[1]}, [r0], r1
269        vst1.32         {d0[1]},  [r0], r1
270        vst1.32         {d2[1]},  [r0], r1
271
272        bx              lr
273endfunc
274
275function ff_h264_h_loop_filter_chroma422_neon, export=1
276        h264_loop_filter_start
277        push            {r4, lr}
278        add             r4,  r0,  r1
279        add             r1,  r1,  r1
280        sub             r0,  r0,  #2
281
282        bl              h_loop_filter_chroma420
283
284        ldr             r12, [sp, #8]
285        ldr             r12, [r12]
286        vmov.32         d24[0], r12
287        sub             r0,  r4,  #2
288
289        bl              h_loop_filter_chroma420
290        pop             {r4, pc}
291endfunc
292
293@ Biweighted prediction
294
295.macro  biweight_16     macs, macd
296        vdup.8          d0,  r4
297        vdup.8          d1,  r5
298        vmov            q2,  q8
299        vmov            q3,  q8
3001:      subs            r3,  r3,  #2
301        vld1.8          {d20-d21},[r0,:128], r2
302        \macd           q2,  d0,  d20
303        pld             [r0]
304        \macd           q3,  d0,  d21
305        vld1.8          {d22-d23},[r1,:128], r2
306        \macs           q2,  d1,  d22
307        pld             [r1]
308        \macs           q3,  d1,  d23
309        vmov            q12, q8
310        vld1.8          {d28-d29},[r0,:128], r2
311        vmov            q13, q8
312        \macd           q12, d0,  d28
313        pld             [r0]
314        \macd           q13, d0,  d29
315        vld1.8          {d30-d31},[r1,:128], r2
316        \macs           q12, d1,  d30
317        pld             [r1]
318        \macs           q13, d1,  d31
319        vshl.s16        q2,  q2,  q9
320        vshl.s16        q3,  q3,  q9
321        vqmovun.s16     d4,  q2
322        vqmovun.s16     d5,  q3
323        vshl.s16        q12, q12, q9
324        vshl.s16        q13, q13, q9
325        vqmovun.s16     d24, q12
326        vqmovun.s16     d25, q13
327        vmov            q3,  q8
328        vst1.8          {d4- d5}, [r6,:128], r2
329        vmov            q2,  q8
330        vst1.8          {d24-d25},[r6,:128], r2
331        bne             1b
332        pop             {r4-r6, pc}
333.endm
334
335.macro  biweight_8      macs, macd
336        vdup.8          d0,  r4
337        vdup.8          d1,  r5
338        vmov            q1,  q8
339        vmov            q10, q8
3401:      subs            r3,  r3,  #2
341        vld1.8          {d4},[r0,:64], r2
342        \macd           q1,  d0,  d4
343        pld             [r0]
344        vld1.8          {d5},[r1,:64], r2
345        \macs           q1,  d1,  d5
346        pld             [r1]
347        vld1.8          {d6},[r0,:64], r2
348        \macd           q10, d0,  d6
349        pld             [r0]
350        vld1.8          {d7},[r1,:64], r2
351        \macs           q10, d1,  d7
352        pld             [r1]
353        vshl.s16        q1,  q1,  q9
354        vqmovun.s16     d2,  q1
355        vshl.s16        q10, q10, q9
356        vqmovun.s16     d4,  q10
357        vmov            q10, q8
358        vst1.8          {d2},[r6,:64], r2
359        vmov            q1,  q8
360        vst1.8          {d4},[r6,:64], r2
361        bne             1b
362        pop             {r4-r6, pc}
363.endm
364
365.macro  biweight_4      macs, macd
366        vdup.8          d0,  r4
367        vdup.8          d1,  r5
368        vmov            q1,  q8
369        vmov            q10, q8
3701:      subs            r3,  r3,  #4
371        vld1.32         {d4[0]},[r0,:32], r2
372        vld1.32         {d4[1]},[r0,:32], r2
373        \macd           q1,  d0,  d4
374        pld             [r0]
375        vld1.32         {d5[0]},[r1,:32], r2
376        vld1.32         {d5[1]},[r1,:32], r2
377        \macs           q1,  d1,  d5
378        pld             [r1]
379        blt             2f
380        vld1.32         {d6[0]},[r0,:32], r2
381        vld1.32         {d6[1]},[r0,:32], r2
382        \macd           q10, d0,  d6
383        pld             [r0]
384        vld1.32         {d7[0]},[r1,:32], r2
385        vld1.32         {d7[1]},[r1,:32], r2
386        \macs           q10, d1,  d7
387        pld             [r1]
388        vshl.s16        q1,  q1,  q9
389        vqmovun.s16     d2,  q1
390        vshl.s16        q10, q10, q9
391        vqmovun.s16     d4,  q10
392        vmov            q10, q8
393        vst1.32         {d2[0]},[r6,:32], r2
394        vst1.32         {d2[1]},[r6,:32], r2
395        vmov            q1,  q8
396        vst1.32         {d4[0]},[r6,:32], r2
397        vst1.32         {d4[1]},[r6,:32], r2
398        bne             1b
399        pop             {r4-r6, pc}
4002:      vshl.s16        q1,  q1,  q9
401        vqmovun.s16     d2,  q1
402        vst1.32         {d2[0]},[r6,:32], r2
403        vst1.32         {d2[1]},[r6,:32], r2
404        pop             {r4-r6, pc}
405.endm
406
407.macro  biweight_func   w
408function ff_biweight_h264_pixels_\w\()_neon, export=1
409        push            {r4-r6, lr}
410        ldr             r12, [sp, #16]
411        add             r4,  sp,  #20
412        ldm             r4,  {r4-r6}
413        lsr             lr,  r4,  #31
414        add             r6,  r6,  #1
415        eors            lr,  lr,  r5,  lsr #30
416        orr             r6,  r6,  #1
417        vdup.16         q9,  r12
418        lsl             r6,  r6,  r12
419        vmvn            q9,  q9
420        vdup.16         q8,  r6
421        mov             r6,  r0
422        beq             10f
423        subs            lr,  lr,  #1
424        beq             20f
425        subs            lr,  lr,  #1
426        beq             30f
427        b               40f
42810:     biweight_\w     vmlal.u8, vmlal.u8
42920:     rsb             r4,  r4,  #0
430        biweight_\w     vmlal.u8, vmlsl.u8
43130:     rsb             r4,  r4,  #0
432        rsb             r5,  r5,  #0
433        biweight_\w     vmlsl.u8, vmlsl.u8
43440:     rsb             r5,  r5,  #0
435        biweight_\w     vmlsl.u8, vmlal.u8
436endfunc
437.endm
438
439        biweight_func   16
440        biweight_func   8
441        biweight_func   4
442
443@ Weighted prediction
444
445.macro  weight_16       add
446        vdup.8          d0,  r12
4471:      subs            r2,  r2,  #2
448        vld1.8          {d20-d21},[r0,:128], r1
449        vmull.u8        q2,  d0,  d20
450        pld             [r0]
451        vmull.u8        q3,  d0,  d21
452        vld1.8          {d28-d29},[r0,:128], r1
453        vmull.u8        q12, d0,  d28
454        pld             [r0]
455        vmull.u8        q13, d0,  d29
456        \add            q2,  q8,  q2
457        vrshl.s16       q2,  q2,  q9
458        \add            q3,  q8,  q3
459        vrshl.s16       q3,  q3,  q9
460        vqmovun.s16     d4,  q2
461        vqmovun.s16     d5,  q3
462        \add            q12, q8,  q12
463        vrshl.s16       q12, q12, q9
464        \add            q13, q8,  q13
465        vrshl.s16       q13, q13, q9
466        vqmovun.s16     d24, q12
467        vqmovun.s16     d25, q13
468        vst1.8          {d4- d5}, [r4,:128], r1
469        vst1.8          {d24-d25},[r4,:128], r1
470        bne             1b
471        pop             {r4, pc}
472.endm
473
474.macro  weight_8        add
475        vdup.8          d0,  r12
4761:      subs            r2,  r2,  #2
477        vld1.8          {d4},[r0,:64], r1
478        vmull.u8        q1,  d0,  d4
479        pld             [r0]
480        vld1.8          {d6},[r0,:64], r1
481        vmull.u8        q10, d0,  d6
482        \add            q1,  q8,  q1
483        pld             [r0]
484        vrshl.s16       q1,  q1,  q9
485        vqmovun.s16     d2,  q1
486        \add            q10, q8,  q10
487        vrshl.s16       q10, q10, q9
488        vqmovun.s16     d4,  q10
489        vst1.8          {d2},[r4,:64], r1
490        vst1.8          {d4},[r4,:64], r1
491        bne             1b
492        pop             {r4, pc}
493.endm
494
495.macro  weight_4        add
496        vdup.8          d0,  r12
497        vmov            q1,  q8
498        vmov            q10, q8
4991:      subs            r2,  r2,  #4
500        vld1.32         {d4[0]},[r0,:32], r1
501        vld1.32         {d4[1]},[r0,:32], r1
502        vmull.u8        q1,  d0,  d4
503        pld             [r0]
504        blt             2f
505        vld1.32         {d6[0]},[r0,:32], r1
506        vld1.32         {d6[1]},[r0,:32], r1
507        vmull.u8        q10, d0,  d6
508        pld             [r0]
509        \add            q1,  q8,  q1
510        vrshl.s16       q1,  q1,  q9
511        vqmovun.s16     d2,  q1
512        \add            q10, q8,  q10
513        vrshl.s16       q10, q10, q9
514        vqmovun.s16     d4,  q10
515        vmov            q10, q8
516        vst1.32         {d2[0]},[r4,:32], r1
517        vst1.32         {d2[1]},[r4,:32], r1
518        vmov            q1,  q8
519        vst1.32         {d4[0]},[r4,:32], r1
520        vst1.32         {d4[1]},[r4,:32], r1
521        bne             1b
522        pop             {r4, pc}
5232:      \add            q1,  q8,  q1
524        vrshl.s16       q1,  q1,  q9
525        vqmovun.s16     d2,  q1
526        vst1.32         {d2[0]},[r4,:32], r1
527        vst1.32         {d2[1]},[r4,:32], r1
528        pop             {r4, pc}
529.endm
530
531.macro  weight_func     w
532function ff_weight_h264_pixels_\w\()_neon, export=1
533        push            {r4, lr}
534        ldr             r12, [sp, #8]
535        ldr             r4,  [sp, #12]
536        cmp             r3,  #1
537        lsl             r4,  r4,  r3
538        vdup.16         q8,  r4
539        mov             r4,  r0
540        ble             20f
541        rsb             lr,  r3,  #1
542        vdup.16         q9,  lr
543        cmp             r12, #0
544        blt             10f
545        weight_\w       vhadd.s16
54610:     rsb             r12, r12, #0
547        weight_\w       vhsub.s16
54820:     rsb             lr,  r3,  #0
549        vdup.16         q9,  lr
550        cmp             r12, #0
551        blt             10f
552        weight_\w       vadd.s16
55310:     rsb             r12, r12, #0
554        weight_\w       vsub.s16
555endfunc
556.endm
557
558        weight_func     16
559        weight_func     8
560        weight_func     4
561