]> git.sesse.net Git - x264/blob - common/arm/dct-a.S
Much faster weightp
[x264] / common / arm / dct-a.S
1 /*****************************************************************************
2  * dct-a.S: h264 encoder library
3  *****************************************************************************
4  * Copyright (C) 2009 x264 project
5  *
6  * Authors: David Conrad <lessen42@gmail.com>
7  *
8  * This program is free software; you can redistribute it and/or modify
9  * it under the terms of the GNU General Public License as published by
10  * the Free Software Foundation; either version 2 of the License, or
11  * (at your option) any later version.
12  *
13  * This program 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
16  * GNU General Public License for more details.
17  *
18  * You should have received a copy of the GNU General Public License
19  * along with this program; if not, write to the Free Software
20  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02111, USA.
21  *****************************************************************************/
22
23 #include "asm.S"
24
25 .fpu neon
26
27 .section .rodata
28 .align 4
29
30 scan4x4_frame:
31 .byte    0,1,   8,9,   2,3,   4,5
32 .byte    2,3,   8,9,  16,17, 10,11
33 .byte   12,13,  6,7,  14,15, 20,21
34 .byte   10,11, 12,13,  6,7,  14,15
35
36 .text
37
38 // sum = a + (b>>shift)   sub = (a>>shift) - b
39 .macro SUMSUB_SHR shift sum sub a b t0 t1
40     vshr.s16    \t0,  \b, #\shift
41     vshr.s16    \t1,  \a, #\shift
42     vadd.s16    \sum, \a, \t0
43     vsub.s16    \sub, \t1, \b
44 .endm
45
46 // sum = (a>>shift) + b   sub = a - (b>>shift)
47 .macro SUMSUB_SHR2 shift sum sub a b t0 t1
48     vshr.s16    \t0,  \a, #\shift
49     vshr.s16    \t1,  \b, #\shift
50     vadd.s16    \sum, \t0, \b
51     vsub.s16    \sub, \a, \t1
52 .endm
53
54 // a += 1.5*ma   b -= 1.5*mb
55 .macro SUMSUB_15 a b ma mb t0 t1
56     vshr.s16    \t0, \ma, #1
57     vshr.s16    \t1, \mb, #1
58     vadd.s16    \t0, \t0, \ma
59     vadd.s16    \t1, \t1, \mb
60     vadd.s16    \a,  \a,  \t0
61     vsub.s16    \b,  \b,  \t1
62 .endm
63
64
65 function x264_dct4x4dc_neon
66     vld1.64         {d0-d3}, [r0,:128]
67     SUMSUB_ABCD     d4, d5, d6, d7, d0, d1, d2, d3
68     SUMSUB_ABCD     d0, d2, d3, d1, d4, d6, d5, d7
69
70     vmov.s16        d31, #1
71     HADAMARD        1, sumsub, q2, q3, q0, q1
72     vtrn.32         d4,  d5
73     vadd.s16        d16, d4,  d31
74     vtrn.32         d6,  d7
75     vadd.s16        d17, d6,  d31
76     vrhadd.s16      d0,  d4,  d5
77     vhsub.s16       d1,  d16, d5
78     vhsub.s16       d2,  d17, d7
79     vrhadd.s16      d3,  d6,  d7
80     vst1.64         {d0-d3}, [r0,:128]
81     bx              lr
82 .endfunc
83
84 function x264_idct4x4dc_neon
85     vld1.64         {d0-d3}, [r0,:128]
86     SUMSUB_ABCD     d4, d5, d6, d7, d0, d1, d2, d3
87     SUMSUB_ABCD     d0, d2, d3, d1, d4, d6, d5, d7
88
89     HADAMARD        1, sumsub, q2, q3, q0, q1
90     HADAMARD        2, sumsub, d0, d1, d4, d5
91     HADAMARD        2, sumsub, d3, d2, d6, d7
92     vst1.64         {d0-d3}, [r0,:128]
93     bx              lr
94 .endfunc
95
96
97 .macro DCT_1D d0 d1 d2 d3  d4 d5 d6 d7
98     SUMSUB_AB       \d1, \d6, \d5, \d6
99     SUMSUB_AB       \d3, \d7, \d4, \d7
100     vadd.s16        \d0, \d3, \d1
101     vadd.s16        \d4, \d7, \d7
102     vadd.s16        \d5, \d6, \d6
103     vsub.s16        \d2, \d3, \d1
104     vadd.s16        \d1, \d4, \d6
105     vsub.s16        \d3, \d7, \d5
106 .endm
107
108 function x264_sub4x4_dct_neon
109     mov             r3, #FENC_STRIDE
110     mov             ip, #FDEC_STRIDE
111     vld1.32         {d0[]}, [r1,:32], r3
112     vld1.32         {d1[]}, [r2,:32], ip
113     vld1.32         {d2[]}, [r1,:32], r3
114     vsubl.u8        q8,  d0,  d1
115     vld1.32         {d3[]}, [r2,:32], ip
116     vld1.32         {d4[]}, [r1,:32], r3
117     vsubl.u8        q9,  d2,  d3
118     vld1.32         {d5[]}, [r2,:32], ip
119     vld1.32         {d6[]}, [r1,:32], r3
120     vsubl.u8        q10, d4,  d5
121     vld1.32         {d7[]}, [r2,:32], ip
122     vsubl.u8        q11, d6,  d7
123
124     DCT_1D          d0, d1, d2, d3, d16, d18, d20, d22
125     TRANSPOSE4x4_16 d0, d1, d2, d3
126     DCT_1D          d4, d5, d6, d7, d0, d1, d2, d3
127     vst1.64         {d4-d7}, [r0,:128]
128     bx              lr
129 .endfunc
130
131 function x264_sub8x4_dct_neon
132     vld1.64         {d0}, [r1,:64], r3
133     vld1.64         {d1}, [r2,:64], ip
134     vsubl.u8        q8,  d0,  d1
135     vld1.64         {d2}, [r1,:64], r3
136     vld1.64         {d3}, [r2,:64], ip
137     vsubl.u8        q9,  d2,  d3
138     vld1.64         {d4}, [r1,:64], r3
139     vld1.64         {d5}, [r2,:64], ip
140     vsubl.u8        q10, d4,  d5
141     vld1.64         {d6}, [r1,:64], r3
142     vld1.64         {d7}, [r2,:64], ip
143     vsubl.u8        q11, d6,  d7
144
145     DCT_1D          q0, q1, q2, q3,  q8, q9, q10, q11
146     TRANSPOSE4x4_16 q0, q1, q2, q3
147
148     SUMSUB_AB       q8,  q12, q0,  q3
149     SUMSUB_AB       q9,  q10, q1,  q2
150     vadd.i16        q13, q12, q12
151     vadd.i16        q11, q10, q10
152     vadd.i16        d0,  d16, d18
153     vadd.i16        d1,  d26, d20
154     vsub.i16        d2,  d16, d18
155     vsub.i16        d3,  d24, d22
156     vst1.64         {d0-d1}, [r0,:128]!
157     vadd.i16        d4,  d17, d19
158     vadd.i16        d5,  d27, d21
159     vst1.64         {d2-d3}, [r0,:128]!
160     vsub.i16        d6,  d17, d19
161     vsub.i16        d7,  d25, d23
162     vst1.64         {d4-d5}, [r0,:128]!
163     vst1.64         {d6-d7}, [r0,:128]!
164     bx              lr
165 .endfunc
166
167 function x264_sub8x8_dct_neon
168     push            {lr}
169     mov             r3, #FENC_STRIDE
170     mov             ip, #FDEC_STRIDE
171     bl              x264_sub8x4_dct_neon
172     pop             {lr}
173     b               x264_sub8x4_dct_neon
174 .endfunc
175
176 function x264_sub16x16_dct_neon
177     push            {lr}
178     mov             r3, #FENC_STRIDE
179     mov             ip, #FDEC_STRIDE
180     bl              x264_sub8x4_dct_neon
181     bl              x264_sub8x4_dct_neon
182     sub             r1, r1, #8*FENC_STRIDE-8
183     sub             r2, r2, #8*FDEC_STRIDE-8
184     bl              x264_sub8x4_dct_neon
185     bl              x264_sub8x4_dct_neon
186     sub             r1, r1, #8
187     sub             r2, r2, #8
188     bl              x264_sub8x4_dct_neon
189     bl              x264_sub8x4_dct_neon
190     sub             r1, r1, #8*FENC_STRIDE-8
191     sub             r2, r2, #8*FDEC_STRIDE-8
192     bl              x264_sub8x4_dct_neon
193     pop             {lr}
194     b               x264_sub8x4_dct_neon
195 .endfunc
196
197
198 .macro DCT8_1D type
199     SUMSUB_AB       q2,  q1,  q11, q12  // s34/d34
200     SUMSUB_AB       q3,  q11, q10, q13  // s25/d25
201     SUMSUB_AB       q13, q10, q9,  q14  // s16/d16
202     SUMSUB_AB       q14, q8,  q8,  q15  // s07/d07
203
204     SUMSUB_AB       q9,  q2,  q14, q2   // a0/a2
205     SUMSUB_AB       q12, q14, q13, q3   // a1/a3
206
207     SUMSUB_AB       q3,  q13, q8,  q1   // a6/a5
208     vshr.s16        q0,  q10, #1
209     vshr.s16        q15, q11, #1
210     vadd.s16        q0,  q0,  q10
211     vadd.s16        q15, q15, q11
212     vsub.s16        q3,  q3,  q0
213     vsub.s16        q13, q13, q15
214
215     SUMSUB_AB       q0,  q15, q10, q11  // a4/a7
216     vshr.s16        q10, q8,  #1
217     vshr.s16        q11, q1,  #1
218     vadd.s16        q10, q10, q8
219     vadd.s16        q11, q11, q1
220     vadd.s16        q10, q0,  q10
221     vadd.s16        q15, q15, q11
222
223     SUMSUB_AB       q8,  q12, q9,  q12
224     SUMSUB_SHR   2, q9,  q15, q10, q15,  q0, q1
225     SUMSUB_SHR   1, q10, q14, q2,  q14,  q0, q1
226     SUMSUB_SHR2  2, q11, q13, q3,  q13,  q0, q1
227 .endm
228
229 function x264_sub8x8_dct8_neon
230     mov             r3, #FENC_STRIDE
231     mov             ip, #FDEC_STRIDE
232     vld1.64         {d16}, [r1,:64], r3
233     vld1.64         {d17}, [r2,:64], ip
234     vsubl.u8        q8,  d16, d17
235     vld1.64         {d18}, [r1,:64], r3
236     vld1.64         {d19}, [r2,:64], ip
237     vsubl.u8        q9,  d18, d19
238     vld1.64         {d20}, [r1,:64], r3
239     vld1.64         {d21}, [r2,:64], ip
240     vsubl.u8        q10, d20, d21
241     vld1.64         {d22}, [r1,:64], r3
242     vld1.64         {d23}, [r2,:64], ip
243     vsubl.u8        q11, d22, d23
244     vld1.64         {d24}, [r1,:64], r3
245     vld1.64         {d25}, [r2,:64], ip
246     vsubl.u8        q12, d24, d25
247     vld1.64         {d26}, [r1,:64], r3
248     vld1.64         {d27}, [r2,:64], ip
249     vsubl.u8        q13, d26, d27
250     vld1.64         {d28}, [r1,:64], r3
251     vld1.64         {d29}, [r2,:64], ip
252     vsubl.u8        q14, d28, d29
253     vld1.64         {d30}, [r1,:64], r3
254     vld1.64         {d31}, [r2,:64], ip
255     vsubl.u8        q15, d30, d31
256
257     DCT8_1D row
258     vswp            d17, d24    // 8, 12
259     vswp            d21, d28    // 10,14
260     vtrn.32         q8,  q10
261     vtrn.32         q12, q14
262
263     vswp            d19, d26    // 9, 13
264     vswp            d23, d30    // 11,15
265     vtrn.32         q9,  q11
266     vtrn.32         q13, q15
267
268     vtrn.16         q10, q11
269     vtrn.16         q12, q13
270     vtrn.16         q8,  q9
271     vtrn.16         q14, q15
272     DCT8_1D col
273
274     vst1.64         {d16-d19}, [r0,:128]!
275     vst1.64         {d20-d23}, [r0,:128]!
276     vst1.64         {d24-d27}, [r0,:128]!
277     vst1.64         {d28-d31}, [r0,:128]!
278     bx              lr
279 .endfunc
280
281 function x264_sub16x16_dct8_neon
282     push            {lr}
283     bl              x264_sub8x8_dct8_neon
284     sub             r1,  r1,  #FENC_STRIDE*8 - 8
285     sub             r2,  r2,  #FDEC_STRIDE*8 - 8
286     bl              x264_sub8x8_dct8_neon
287     sub             r1,  r1,  #8
288     sub             r2,  r2,  #8
289     bl              x264_sub8x8_dct8_neon
290     pop             {lr}
291     sub             r1,  r1,  #FENC_STRIDE*8 - 8
292     sub             r2,  r2,  #FDEC_STRIDE*8 - 8
293     b               x264_sub8x8_dct8_neon
294 .endfunc
295
296
297 // First part of IDCT (minus final SUMSUB_BA)
298 .macro IDCT_1D d4 d5 d6 d7 d0 d1 d2 d3
299     SUMSUB_AB       \d4, \d5, \d0, \d2
300     vshr.s16        \d7, \d1, #1
301     vshr.s16        \d6, \d3, #1
302     vsub.s16        \d7, \d7, \d3
303     vadd.s16        \d6, \d6, \d1
304 .endm
305
306 function x264_add4x4_idct_neon
307     mov             r2, #FDEC_STRIDE
308     vld1.64         {d0-d3}, [r1,:128]
309
310     IDCT_1D         d4, d5, d6, d7, d0, d1, d2, d3
311     vld1.32         {d30[0]}, [r0,:32], r2
312     SUMSUB_AB       q0, q1, q2, q3
313
314     TRANSPOSE4x4_16 d0, d1, d3, d2
315
316     IDCT_1D         d4, d5, d6, d7, d0, d1, d3, d2
317     vld1.32         {d30[1]}, [r0,:32], r2
318     SUMSUB_AB       q0, q1, q2, q3
319
320     vrshr.s16       q0, q0, #6
321     vld1.32         {d31[1]}, [r0,:32], r2
322     vrshr.s16       q1, q1, #6
323     vld1.32         {d31[0]}, [r0,:32], r2
324
325     sub             r0, r0, r2, lsl #2
326     vaddw.u8        q0, q0, d30
327     vaddw.u8        q1, q1, d31
328     vqmovun.s16     d0, q0
329     vqmovun.s16     d2, q1
330
331     vst1.32         {d0[0]}, [r0,:32], r2
332     vst1.32         {d0[1]}, [r0,:32], r2
333     vst1.32         {d2[1]}, [r0,:32], r2
334     vst1.32         {d2[0]}, [r0,:32], r2
335     bx              lr
336 .endfunc
337
338 function x264_add8x4_idct_neon
339     vld1.64         {d0-d3}, [r1,:128]!
340     IDCT_1D         d16, d18, d20, d22, d0, d1, d2, d3
341     vld1.64         {d4-d7}, [r1,:128]!
342     IDCT_1D         d17, d19, d21, d23, d4, d5, d6, d7
343     SUMSUB_AB       q0,  q3,  q8,  q10
344     SUMSUB_AB       q1,  q2,  q9,  q11
345
346     TRANSPOSE4x4_16 q0,  q1,  q2,  q3
347
348     IDCT_1D         q8,  q9,  q10, q11, q0, q1, q2, q3
349     SUMSUB_AB       q0,  q3,  q8,  q10
350     SUMSUB_AB       q1,  q2,  q9,  q11
351
352     vrshr.s16       q0,  q0,  #6
353     vld1.32         {d28}, [r0,:64], r2
354     vrshr.s16       q1,  q1,  #6
355     vld1.32         {d29}, [r0,:64], r2
356     vrshr.s16       q2,  q2,  #6
357     vld1.32         {d30}, [r0,:64], r2
358     vrshr.s16       q3,  q3,  #6
359     vld1.32         {d31}, [r0,:64], r2
360
361     sub             r0,  r0,  r2,  lsl #2
362     vaddw.u8        q0,  q0,  d28
363     vaddw.u8        q1,  q1,  d29
364     vaddw.u8        q2,  q2,  d30
365     vaddw.u8        q3,  q3,  d31
366
367     vqmovun.s16     d0,  q0
368     vqmovun.s16     d1,  q1
369     vst1.32         {d0}, [r0,:64], r2
370     vqmovun.s16     d2,  q2
371     vst1.32         {d1}, [r0,:64], r2
372     vqmovun.s16     d3,  q3
373     vst1.32         {d2}, [r0,:64], r2
374     vst1.32         {d3}, [r0,:64], r2
375     bx              lr
376 .endfunc
377
378 function x264_add8x8_idct_neon
379     mov             r2, #FDEC_STRIDE
380     mov             ip, lr
381     bl              x264_add8x4_idct_neon
382     mov             lr, ip
383     b               x264_add8x4_idct_neon
384 .endfunc
385
386 function x264_add16x16_idct_neon
387     mov             r2, #FDEC_STRIDE
388     mov             ip, lr
389     bl              x264_add8x4_idct_neon
390     bl              x264_add8x4_idct_neon
391     sub             r0, r0, #8*FDEC_STRIDE-8
392     bl              x264_add8x4_idct_neon
393     bl              x264_add8x4_idct_neon
394     sub             r0, r0, #8
395     bl              x264_add8x4_idct_neon
396     bl              x264_add8x4_idct_neon
397     sub             r0, r0, #8*FDEC_STRIDE-8
398     bl              x264_add8x4_idct_neon
399     mov             lr, ip
400     b               x264_add8x4_idct_neon
401 .endfunc
402
403
404 .macro IDCT8_1D type
405 .ifc \type, col
406     vswp            d21, d28
407 .endif
408     SUMSUB_AB       q0,  q1,  q8,  q12              // a0/a2
409 .ifc \type, row
410     vld1.64         {d28-d31}, [r1,:128]!
411 .else
412     vswp            d19, d26
413 .endif
414     SUMSUB_SHR   1, q2,  q3,  q10, q14,  q8, q12    // a6/a4
415 .ifc \type, col
416     vswp            d23, d30
417 .endif
418     SUMSUB_AB       q8,  q10, q13, q11
419     SUMSUB_15       q8,  q10, q9,  q15,  q12, q14   // a7/a1
420     SUMSUB_AB       q14, q15, q15, q9
421     SUMSUB_15       q15, q14, q13, q11,  q12, q9    // a5/a3
422
423     SUMSUB_SHR   2, q13, q14, q14, q15,  q11, q9    // b3/b5
424     SUMSUB_SHR2  2, q12, q15, q8,  q10,  q11, q9    // b1/b7
425
426     SUMSUB_AB       q10, q2,  q0,  q2               // b0/b6
427     SUMSUB_AB       q11, q3,  q1,  q3               // b2/b4
428
429     SUMSUB_AB       q8,  q15, q10, q15
430     SUMSUB_AB       q9,  q14, q11, q14
431     SUMSUB_AB       q10, q13, q3,  q13
432 .ifc \type, row
433     vtrn.16         q8,  q9
434 .endif
435     SUMSUB_AB       q11, q12, q2,  q12
436 .endm
437
438 function x264_add8x8_idct8_neon
439     mov             r2,  #FDEC_STRIDE
440     vld1.64         {d16-d19}, [r1,:128]!
441     vld1.64         {d20-d23}, [r1,:128]!
442     vld1.64         {d24-d27}, [r1,:128]!
443
444     IDCT8_1D row
445     vtrn.16         q10, q11
446     vtrn.16         q12, q13
447     vtrn.16         q14, q15
448     vtrn.32         q8,  q10
449     vtrn.32         q9,  q11
450     vtrn.32         q12, q14
451     vtrn.32         q13, q15
452     vswp            d17, d24
453     IDCT8_1D col
454
455     vld1.64         {d0}, [r0,:64], r2
456     vrshr.s16       q8,  q8,  #6
457     vld1.64         {d1}, [r0,:64], r2
458     vrshr.s16       q9,  q9,  #6
459     vld1.64         {d2}, [r0,:64], r2
460     vrshr.s16       q10, q10, #6
461     vld1.64         {d3}, [r0,:64], r2
462     vrshr.s16       q11, q11, #6
463     vld1.64         {d4}, [r0,:64], r2
464     vrshr.s16       q12, q12, #6
465     vld1.64         {d5}, [r0,:64], r2
466     vrshr.s16       q13, q13, #6
467     vld1.64         {d6}, [r0,:64], r2
468     vrshr.s16       q14, q14, #6
469     vld1.64         {d7}, [r0,:64], r2
470     vrshr.s16       q15, q15, #6
471     sub             r0,  r0,  r2,  lsl #3
472
473     vaddw.u8        q8,  q8,  d0
474     vaddw.u8        q9,  q9,  d1
475     vaddw.u8        q10, q10, d2
476     vqmovun.s16     d0,  q8
477     vqmovun.s16     d1,  q9
478     vqmovun.s16     d2,  q10
479     vaddw.u8        q11, q11, d3
480     vst1.64         {d0}, [r0,:64], r2
481     vaddw.u8        q12, q12, d4
482     vst1.64         {d1}, [r0,:64], r2
483     vaddw.u8        q13, q13, d5
484     vst1.64         {d2}, [r0,:64], r2
485     vqmovun.s16     d3,  q11
486     vqmovun.s16     d4,  q12
487     vaddw.u8        q14, q14, d6
488     vaddw.u8        q15, q15, d7
489     vst1.64         {d3}, [r0,:64], r2
490     vqmovun.s16     d5,  q13
491     vst1.64         {d4}, [r0,:64], r2
492     vqmovun.s16     d6,  q14
493     vqmovun.s16     d7,  q15
494     vst1.64         {d5}, [r0,:64], r2
495     vst1.64         {d6}, [r0,:64], r2
496     vst1.64         {d7}, [r0,:64], r2
497     bx              lr
498 .endfunc
499
500 function x264_add16x16_idct8_neon
501     mov             ip,  lr
502     bl              x264_add8x8_idct8_neon
503     sub             r0,  r0,  #8*FDEC_STRIDE-8
504     bl              x264_add8x8_idct8_neon
505     sub             r0,  r0,  #8
506     bl              x264_add8x8_idct8_neon
507     sub             r0,  r0,  #8*FDEC_STRIDE-8
508     mov             lr,  ip
509     b               x264_add8x8_idct8_neon
510 .endfunc
511
512
513 function x264_add8x8_idct_dc_neon
514     mov             r2,  #FDEC_STRIDE
515     vld1.64         {d16}, [r1,:64]
516     vrshr.s16       d16, d16, #6
517     vld1.64         {d0}, [r0,:64], r2
518     vmov.i16        q15, #0
519     vld1.64         {d1}, [r0,:64], r2
520     vld1.64         {d2}, [r0,:64], r2
521     vdup.16         d20, d16[0]
522     vld1.64         {d3}, [r0,:64], r2
523     vdup.16         d21, d16[1]
524     vld1.64         {d4}, [r0,:64], r2
525     vdup.16         d22, d16[2]
526     vld1.64         {d5}, [r0,:64], r2
527     vdup.16         d23, d16[3]
528     vld1.64         {d6}, [r0,:64], r2
529     vsub.s16        q12, q15, q10
530     vld1.64         {d7}, [r0,:64], r2
531     vsub.s16        q13, q15, q11
532
533     sub             r0,  r0,  #8*FDEC_STRIDE
534
535     vqmovun.s16     d20, q10
536     vqmovun.s16     d22, q11
537     vqmovun.s16     d24, q12
538     vqmovun.s16     d26, q13
539
540     vmov            d21, d20
541     vqadd.u8        q0,  q0,  q10
542     vmov            d23, d22
543     vqadd.u8        q1,  q1,  q10
544     vmov            d25, d24
545     vqadd.u8        q2,  q2,  q11
546     vmov            d27, d26
547     vqadd.u8        q3,  q3,  q11
548     vqsub.u8        q0,  q0,  q12
549     vqsub.u8        q1,  q1,  q12
550     vqsub.u8        q2,  q2,  q13
551
552     vst1.64         {d0}, [r0,:64], r2
553     vqsub.u8        q3,  q3,  q13
554     vst1.64         {d1}, [r0,:64], r2
555     vst1.64         {d2}, [r0,:64], r2
556     vst1.64         {d3}, [r0,:64], r2
557     vst1.64         {d4}, [r0,:64], r2
558     vst1.64         {d5}, [r0,:64], r2
559     vst1.64         {d6}, [r0,:64], r2
560     vst1.64         {d7}, [r0,:64], r2
561     bx              lr
562 .endfunc
563
564 .macro ADD16x4_IDCT_DC dc
565     vld1.64         {d16-d17}, [r0,:128], r3
566     vld1.64         {d18-d19}, [r0,:128], r3
567     vdup.16         d4,  \dc[0]
568     vdup.16         d5,  \dc[1]
569     vld1.64         {d20-d21}, [r0,:128], r3
570     vdup.16         d6,  \dc[2]
571     vdup.16         d7,  \dc[3]
572     vld1.64         {d22-d23}, [r0,:128], r3
573     vsub.s16        q12, q15, q2
574     vsub.s16        q13, q15, q3
575
576     vqmovun.s16     d4,  q2
577     vqmovun.s16     d5,  q3
578     vqmovun.s16     d6,  q12
579     vqmovun.s16     d7,  q13
580
581     vqadd.u8        q8,  q8,  q2
582     vqadd.u8        q9,  q9,  q2
583     vqadd.u8        q10, q10, q2
584     vqadd.u8        q11, q11, q2
585
586     vqsub.u8        q8,  q8,  q3
587     vqsub.u8        q9,  q9,  q3
588     vqsub.u8        q10, q10, q3
589     vst1.64         {d16-d17}, [r2,:128], r3
590     vqsub.u8        q11, q11, q3
591     vst1.64         {d18-d19}, [r2,:128], r3
592     vst1.64         {d20-d21}, [r2,:128], r3
593     vst1.64         {d22-d23}, [r2,:128], r3
594 .endm
595
596 function x264_add16x16_idct_dc_neon
597     mov             r2,  r0
598     mov             r3,  #FDEC_STRIDE
599     vmov.i16        q15, #0
600
601     vld1.64         {d0-d3}, [r1,:64]
602     vrshr.s16       q0, #6
603     vrshr.s16       q1, #6
604
605     ADD16x4_IDCT_DC d0
606     ADD16x4_IDCT_DC d1
607     ADD16x4_IDCT_DC d2
608     ADD16x4_IDCT_DC d3
609     bx              lr
610 .endfunc
611
612 function x264_sub8x8_dct_dc_neon
613     mov             r3,  #FENC_STRIDE
614     mov             ip,  #FDEC_STRIDE
615     vld1.64         {d16}, [r1,:64], r3
616     vld1.64         {d17}, [r2,:64], ip
617     vsubl.u8        q8,  d16, d17
618     vld1.64         {d18}, [r1,:64], r3
619     vld1.64         {d19}, [r2,:64], ip
620     vsubl.u8        q9,  d18, d19
621     vld1.64         {d20}, [r1,:64], r3
622     vld1.64         {d21}, [r2,:64], ip
623     vsubl.u8        q10, d20, d21
624     vld1.64         {d22}, [r1,:64], r3
625     vadd.s16        q0,  q8,  q9
626     vld1.64         {d23}, [r2,:64], ip
627     vsubl.u8        q11, d22, d23
628     vld1.64         {d24}, [r1,:64], r3
629     vadd.s16        q0,  q0,  q10
630     vld1.64         {d25}, [r2,:64], ip
631     vsubl.u8        q12, d24, d25
632     vld1.64         {d26}, [r1,:64], r3
633     vadd.s16        q0,  q0,  q11
634     vld1.64         {d27}, [r2,:64], ip
635     vsubl.u8        q13, d26, d27
636     vld1.64         {d28}, [r1,:64], r3
637     vld1.64         {d29}, [r2,:64], ip
638     vsubl.u8        q14, d28, d29
639     vld1.64         {d30}, [r1,:64], r3
640     vadd.s16        q1,  q12, q13
641     vld1.64         {d31}, [r2,:64], ip
642     vpadd.s16       d0,  d0,  d1
643     vadd.s16        q1,  q1,  q14
644     vsubl.u8        q15, d30, d31
645     vadd.s16        q1,  q1,  q15
646     vpadd.s16       d2,  d2,  d3
647     vpadd.s16       d0,  d0,  d2
648     vst1.64         {d0}, [r0,:64]
649     bx              lr
650 .endfunc
651
652
653 function x264_zigzag_scan_4x4_frame_neon
654     movrel      r2, scan4x4_frame
655     vld1.64     {d0-d3},   [r1,:128]
656     vld1.64     {d16-d19}, [r2,:128]
657     vtbl.8      d4, {d0-d1}, d16
658     vtbl.8      d5, {d1-d3}, d17
659     vtbl.8      d6, {d0-d2}, d18
660     vtbl.8      d7, {d2-d3}, d19
661     vst1.64     {d4-d7},   [r0,:128]
662     bx          lr
663 .endfunc