Fix TEXTRELs in the ARM asm.
[profile/ivi/libvpx.git] / vp8 / common / arm / neon / vp8_subpixelvariance16x16s_neon.asm
1 ;
2 ;  Copyright (c) 2010 The WebM project authors. All Rights Reserved.
3 ;
4 ;  Use of this source code is governed by a BSD-style license
5 ;  that can be found in the LICENSE file in the root of the source
6 ;  tree. An additional intellectual property rights grant can be found
7 ;  in the file PATENTS.  All contributing project authors may
8 ;  be found in the AUTHORS file in the root of the source tree.
9 ;
10
11
12     EXPORT  |vp8_variance_halfpixvar16x16_h_neon|
13     EXPORT  |vp8_variance_halfpixvar16x16_v_neon|
14     EXPORT  |vp8_variance_halfpixvar16x16_hv_neon|
15     EXPORT  |vp8_sub_pixel_variance16x16s_neon|
16     ARM
17     REQUIRE8
18     PRESERVE8
19
20     AREA ||.text||, CODE, READONLY, ALIGN=2
21
22 ;================================================
23 ;unsigned int vp8_variance_halfpixvar16x16_h_neon
24 ;(
25 ;    unsigned char  *src_ptr, r0
26 ;    int  src_pixels_per_line,  r1
27 ;    unsigned char *dst_ptr,  r2
28 ;    int dst_pixels_per_line,   r3
29 ;    unsigned int *sse
30 ;);
31 ;================================================
32 |vp8_variance_halfpixvar16x16_h_neon| PROC
33     push            {lr}
34
35     mov             r12, #4                  ;loop counter
36     ldr             lr, [sp, #4]           ;load *sse from stack
37     vmov.i8         q8, #0                      ;q8 - sum
38     vmov.i8         q9, #0                      ;q9, q10 - sse
39     vmov.i8         q10, #0
40
41 ;First Pass: output_height lines x output_width columns (16x16)
42 vp8_filt_fpo16x16s_4_0_loop_neon
43     vld1.u8         {d0, d1, d2, d3}, [r0], r1      ;load src data
44     vld1.8          {q11}, [r2], r3
45     vld1.u8         {d4, d5, d6, d7}, [r0], r1
46     vld1.8          {q12}, [r2], r3
47     vld1.u8         {d8, d9, d10, d11}, [r0], r1
48     vld1.8          {q13}, [r2], r3
49     vld1.u8         {d12, d13, d14, d15}, [r0], r1
50
51     ;pld                [r0]
52     ;pld                [r0, r1]
53     ;pld                [r0, r1, lsl #1]
54
55     vext.8          q1, q0, q1, #1          ;construct src_ptr[1]
56     vext.8          q3, q2, q3, #1
57     vext.8          q5, q4, q5, #1
58     vext.8          q7, q6, q7, #1
59
60     vrhadd.u8       q0, q0, q1              ;(src_ptr[0]+src_ptr[1])/round/shift right 1
61     vld1.8          {q14}, [r2], r3
62     vrhadd.u8       q1, q2, q3
63     vrhadd.u8       q2, q4, q5
64     vrhadd.u8       q3, q6, q7
65
66     vsubl.u8        q4, d0, d22                 ;diff
67     vsubl.u8        q5, d1, d23
68     vsubl.u8        q6, d2, d24
69     vsubl.u8        q7, d3, d25
70     vsubl.u8        q0, d4, d26
71     vsubl.u8        q1, d5, d27
72     vsubl.u8        q2, d6, d28
73     vsubl.u8        q3, d7, d29
74
75     vpadal.s16      q8, q4                     ;sum
76     vmlal.s16       q9, d8, d8                ;sse
77     vmlal.s16       q10, d9, d9
78
79     subs            r12, r12, #1
80
81     vpadal.s16      q8, q5
82     vmlal.s16       q9, d10, d10
83     vmlal.s16       q10, d11, d11
84     vpadal.s16      q8, q6
85     vmlal.s16       q9, d12, d12
86     vmlal.s16       q10, d13, d13
87     vpadal.s16      q8, q7
88     vmlal.s16       q9, d14, d14
89     vmlal.s16       q10, d15, d15
90
91     vpadal.s16      q8, q0                     ;sum
92     vmlal.s16       q9, d0, d0                ;sse
93     vmlal.s16       q10, d1, d1
94     vpadal.s16      q8, q1
95     vmlal.s16       q9, d2, d2
96     vmlal.s16       q10, d3, d3
97     vpadal.s16      q8, q2
98     vmlal.s16       q9, d4, d4
99     vmlal.s16       q10, d5, d5
100     vpadal.s16      q8, q3
101     vmlal.s16       q9, d6, d6
102     vmlal.s16       q10, d7, d7
103
104     bne             vp8_filt_fpo16x16s_4_0_loop_neon
105
106     vadd.u32        q10, q9, q10                ;accumulate sse
107     vpaddl.s32      q0, q8                      ;accumulate sum
108
109     vpaddl.u32      q1, q10
110     vadd.s64        d0, d0, d1
111     vadd.u64        d1, d2, d3
112
113     vmull.s32       q5, d0, d0
114     vst1.32         {d1[0]}, [lr]               ;store sse
115     vshr.u32        d10, d10, #8
116     vsub.u32        d0, d1, d10
117
118     vmov.32         r0, d0[0]                   ;return
119     pop             {pc}
120     ENDP
121
122 ;================================================
123 ;unsigned int vp8_variance_halfpixvar16x16_v_neon
124 ;(
125 ;    unsigned char  *src_ptr, r0
126 ;    int  src_pixels_per_line,  r1
127 ;    unsigned char *dst_ptr,  r2
128 ;    int dst_pixels_per_line,   r3
129 ;    unsigned int *sse
130 ;);
131 ;================================================
132 |vp8_variance_halfpixvar16x16_v_neon| PROC
133     push            {lr}
134
135     mov             r12, #4                     ;loop counter
136
137     vld1.u8         {q0}, [r0], r1              ;load src data
138     ldr             lr, [sp, #4]                ;load *sse from stack
139
140     vmov.i8         q8, #0                      ;q8 - sum
141     vmov.i8         q9, #0                      ;q9, q10 - sse
142     vmov.i8         q10, #0
143
144 vp8_filt_spo16x16s_0_4_loop_neon
145     vld1.u8         {q2}, [r0], r1
146     vld1.8          {q1}, [r2], r3
147     vld1.u8         {q4}, [r0], r1
148     vld1.8          {q3}, [r2], r3
149     vld1.u8         {q6}, [r0], r1
150     vld1.8          {q5}, [r2], r3
151     vld1.u8         {q15}, [r0], r1
152
153     vrhadd.u8       q0, q0, q2
154     vld1.8          {q7}, [r2], r3
155     vrhadd.u8       q2, q2, q4
156     vrhadd.u8       q4, q4, q6
157     vrhadd.u8       q6, q6, q15
158
159     vsubl.u8        q11, d0, d2                 ;diff
160     vsubl.u8        q12, d1, d3
161     vsubl.u8        q13, d4, d6
162     vsubl.u8        q14, d5, d7
163     vsubl.u8        q0, d8, d10
164     vsubl.u8        q1, d9, d11
165     vsubl.u8        q2, d12, d14
166     vsubl.u8        q3, d13, d15
167
168     vpadal.s16      q8, q11                     ;sum
169     vmlal.s16       q9, d22, d22                ;sse
170     vmlal.s16       q10, d23, d23
171
172     subs            r12, r12, #1
173
174     vpadal.s16      q8, q12
175     vmlal.s16       q9, d24, d24
176     vmlal.s16       q10, d25, d25
177     vpadal.s16      q8, q13
178     vmlal.s16       q9, d26, d26
179     vmlal.s16       q10, d27, d27
180     vpadal.s16      q8, q14
181     vmlal.s16       q9, d28, d28
182     vmlal.s16       q10, d29, d29
183
184     vpadal.s16      q8, q0                     ;sum
185     vmlal.s16       q9, d0, d0                 ;sse
186     vmlal.s16       q10, d1, d1
187     vpadal.s16      q8, q1
188     vmlal.s16       q9, d2, d2
189     vmlal.s16       q10, d3, d3
190     vpadal.s16      q8, q2
191     vmlal.s16       q9, d4, d4
192     vmlal.s16       q10, d5, d5
193
194     vmov            q0, q15
195
196     vpadal.s16      q8, q3
197     vmlal.s16       q9, d6, d6
198     vmlal.s16       q10, d7, d7
199
200     bne             vp8_filt_spo16x16s_0_4_loop_neon
201
202     vadd.u32        q10, q9, q10                ;accumulate sse
203     vpaddl.s32      q0, q8                      ;accumulate sum
204
205     vpaddl.u32      q1, q10
206     vadd.s64        d0, d0, d1
207     vadd.u64        d1, d2, d3
208
209     vmull.s32       q5, d0, d0
210     vst1.32         {d1[0]}, [lr]               ;store sse
211     vshr.u32        d10, d10, #8
212     vsub.u32        d0, d1, d10
213
214     vmov.32         r0, d0[0]                   ;return
215     pop             {pc}
216     ENDP
217
218 ;================================================
219 ;unsigned int vp8_variance_halfpixvar16x16_hv_neon
220 ;(
221 ;    unsigned char  *src_ptr, r0
222 ;    int  src_pixels_per_line,  r1
223 ;    unsigned char *dst_ptr,  r2
224 ;    int dst_pixels_per_line,   r3
225 ;    unsigned int *sse
226 ;);
227 ;================================================
228 |vp8_variance_halfpixvar16x16_hv_neon| PROC
229     push            {lr}
230
231     vld1.u8         {d0, d1, d2, d3}, [r0], r1      ;load src data
232
233     ldr             lr, [sp, #4]           ;load *sse from stack
234     vmov.i8         q13, #0                      ;q8 - sum
235     vext.8          q1, q0, q1, #1          ;construct src_ptr[1]
236
237     vmov.i8         q14, #0                      ;q9, q10 - sse
238     vmov.i8         q15, #0
239
240     mov             r12, #4                  ;loop counter
241     vrhadd.u8       q0, q0, q1              ;(src_ptr[0]+src_ptr[1])/round/shift right 1
242
243 ;First Pass: output_height lines x output_width columns (17x16)
244 vp8_filt16x16s_4_4_loop_neon
245     vld1.u8         {d4, d5, d6, d7}, [r0], r1
246     vld1.u8         {d8, d9, d10, d11}, [r0], r1
247     vld1.u8         {d12, d13, d14, d15}, [r0], r1
248     vld1.u8         {d16, d17, d18, d19}, [r0], r1
249
250     ;pld                [r0]
251     ;pld                [r0, r1]
252     ;pld                [r0, r1, lsl #1]
253
254     vext.8          q3, q2, q3, #1          ;construct src_ptr[1]
255     vext.8          q5, q4, q5, #1
256     vext.8          q7, q6, q7, #1
257     vext.8          q9, q8, q9, #1
258
259     vrhadd.u8       q1, q2, q3              ;(src_ptr[0]+src_ptr[1])/round/shift right 1
260     vrhadd.u8       q2, q4, q5
261     vrhadd.u8       q3, q6, q7
262     vrhadd.u8       q4, q8, q9
263
264     vld1.8          {q5}, [r2], r3
265     vrhadd.u8       q0, q0, q1
266     vld1.8          {q6}, [r2], r3
267     vrhadd.u8       q1, q1, q2
268     vld1.8          {q7}, [r2], r3
269     vrhadd.u8       q2, q2, q3
270     vld1.8          {q8}, [r2], r3
271     vrhadd.u8       q3, q3, q4
272
273     vsubl.u8        q9, d0, d10                 ;diff
274     vsubl.u8        q10, d1, d11
275     vsubl.u8        q11, d2, d12
276     vsubl.u8        q12, d3, d13
277
278     vsubl.u8        q0, d4, d14                 ;diff
279     vsubl.u8        q1, d5, d15
280     vsubl.u8        q5, d6, d16
281     vsubl.u8        q6, d7, d17
282
283     vpadal.s16      q13, q9                     ;sum
284     vmlal.s16       q14, d18, d18                ;sse
285     vmlal.s16       q15, d19, d19
286
287     vpadal.s16      q13, q10                     ;sum
288     vmlal.s16       q14, d20, d20                ;sse
289     vmlal.s16       q15, d21, d21
290
291     vpadal.s16      q13, q11                     ;sum
292     vmlal.s16       q14, d22, d22                ;sse
293     vmlal.s16       q15, d23, d23
294
295     vpadal.s16      q13, q12                     ;sum
296     vmlal.s16       q14, d24, d24                ;sse
297     vmlal.s16       q15, d25, d25
298
299     subs            r12, r12, #1
300
301     vpadal.s16      q13, q0                     ;sum
302     vmlal.s16       q14, d0, d0                ;sse
303     vmlal.s16       q15, d1, d1
304
305     vpadal.s16      q13, q1                     ;sum
306     vmlal.s16       q14, d2, d2                ;sse
307     vmlal.s16       q15, d3, d3
308
309     vpadal.s16      q13, q5                     ;sum
310     vmlal.s16       q14, d10, d10                ;sse
311     vmlal.s16       q15, d11, d11
312
313     vmov            q0, q4
314
315     vpadal.s16      q13, q6                     ;sum
316     vmlal.s16       q14, d12, d12                ;sse
317     vmlal.s16       q15, d13, d13
318
319     bne             vp8_filt16x16s_4_4_loop_neon
320
321     vadd.u32        q15, q14, q15                ;accumulate sse
322     vpaddl.s32      q0, q13                      ;accumulate sum
323
324     vpaddl.u32      q1, q15
325     vadd.s64        d0, d0, d1
326     vadd.u64        d1, d2, d3
327
328     vmull.s32       q5, d0, d0
329     vst1.32         {d1[0]}, [lr]               ;store sse
330     vshr.u32        d10, d10, #8
331     vsub.u32        d0, d1, d10
332
333     vmov.32         r0, d0[0]                   ;return
334     pop             {pc}
335     ENDP
336
337 ;==============================
338 ; r0    unsigned char  *src_ptr,
339 ; r1    int  src_pixels_per_line,
340 ; r2    int  xoffset,
341 ; r3    int  yoffset,
342 ; stack unsigned char *dst_ptr,
343 ; stack int dst_pixels_per_line,
344 ; stack unsigned int *sse
345 ;note: in vp8_find_best_half_pixel_step()(called when 8<Speed<15), and first call of vp8_find_best_sub_pixel_step()
346 ;(called when speed<=8). xoffset/yoffset can only be 4 or 0, which means either by pass the filter,
347 ;or filter coeff is {64, 64}. This simplified program only works in this situation.
348 ;note: It happens that both xoffset and yoffset are zero. This can be handled in c code later.
349
350 |vp8_sub_pixel_variance16x16s_neon| PROC
351     push            {r4, lr}
352
353     ldr             r4, [sp, #8]            ;load *dst_ptr from stack
354     ldr             r12, [sp, #12]          ;load dst_pixels_per_line from stack
355     ldr             lr, [sp, #16]           ;load *sse from stack
356
357     cmp             r2, #0                  ;skip first_pass filter if xoffset=0
358     beq             secondpass_bfilter16x16s_only
359
360     cmp             r3, #0                  ;skip second_pass filter if yoffset=0
361     beq             firstpass_bfilter16x16s_only
362
363     vld1.u8         {d0, d1, d2, d3}, [r0], r1      ;load src data
364     sub             sp, sp, #256            ;reserve space on stack for temporary storage
365     vext.8          q1, q0, q1, #1          ;construct src_ptr[1]
366     mov             r3, sp
367     mov             r2, #4                  ;loop counter
368     vrhadd.u8       q0, q0, q1              ;(src_ptr[0]+src_ptr[1])/round/shift right 1
369
370 ;First Pass: output_height lines x output_width columns (17x16)
371 vp8e_filt_blk2d_fp16x16s_loop_neon
372     vld1.u8         {d4, d5, d6, d7}, [r0], r1
373     vld1.u8         {d8, d9, d10, d11}, [r0], r1
374     vld1.u8         {d12, d13, d14, d15}, [r0], r1
375     vld1.u8         {d16, d17, d18, d19}, [r0], r1
376
377     ;pld                [r0]
378     ;pld                [r0, r1]
379     ;pld                [r0, r1, lsl #1]
380
381     vext.8          q3, q2, q3, #1          ;construct src_ptr[1]
382     vext.8          q5, q4, q5, #1
383     vext.8          q7, q6, q7, #1
384     vext.8          q9, q8, q9, #1
385
386     vrhadd.u8       q1, q2, q3              ;(src_ptr[0]+src_ptr[1])/round/shift right 1
387     vrhadd.u8       q2, q4, q5
388     vrhadd.u8       q3, q6, q7
389     vrhadd.u8       q4, q8, q9
390
391     vrhadd.u8       q0, q0, q1
392     vrhadd.u8       q1, q1, q2
393     vrhadd.u8       q2, q2, q3
394     vrhadd.u8       q3, q3, q4
395
396     subs            r2, r2, #1
397     vst1.u8         {d0, d1 ,d2, d3}, [r3]!         ;store result
398     vmov            q0, q4
399     vst1.u8         {d4, d5, d6, d7}, [r3]!
400
401     bne             vp8e_filt_blk2d_fp16x16s_loop_neon
402
403     b               sub_pixel_variance16x16s_neon
404
405 ;--------------------
406 firstpass_bfilter16x16s_only
407     mov             r2, #2                  ;loop counter
408     sub             sp, sp, #256            ;reserve space on stack for temporary storage
409     mov             r3, sp
410
411 ;First Pass: output_height lines x output_width columns (16x16)
412 vp8e_filt_blk2d_fpo16x16s_loop_neon
413     vld1.u8         {d0, d1, d2, d3}, [r0], r1      ;load src data
414     vld1.u8         {d4, d5, d6, d7}, [r0], r1
415     vld1.u8         {d8, d9, d10, d11}, [r0], r1
416     vld1.u8         {d12, d13, d14, d15}, [r0], r1
417
418     ;pld                [r0]
419     ;pld                [r0, r1]
420     ;pld                [r0, r1, lsl #1]
421
422     vext.8          q1, q0, q1, #1          ;construct src_ptr[1]
423     vld1.u8         {d16, d17, d18, d19}, [r0], r1
424     vext.8          q3, q2, q3, #1
425     vld1.u8         {d20, d21, d22, d23}, [r0], r1
426     vext.8          q5, q4, q5, #1
427     vld1.u8         {d24, d25, d26, d27}, [r0], r1
428     vext.8          q7, q6, q7, #1
429     vld1.u8         {d28, d29, d30, d31}, [r0], r1
430     vext.8          q9, q8, q9, #1
431     vext.8          q11, q10, q11, #1
432     vext.8          q13, q12, q13, #1
433     vext.8          q15, q14, q15, #1
434
435     vrhadd.u8       q0, q0, q1              ;(src_ptr[0]+src_ptr[1])/round/shift right 1
436     vrhadd.u8       q1, q2, q3
437     vrhadd.u8       q2, q4, q5
438     vrhadd.u8       q3, q6, q7
439     vrhadd.u8       q4, q8, q9
440     vrhadd.u8       q5, q10, q11
441     vrhadd.u8       q6, q12, q13
442     vrhadd.u8       q7, q14, q15
443
444     subs            r2, r2, #1
445
446     vst1.u8         {d0, d1, d2, d3}, [r3]!         ;store result
447     vst1.u8         {d4, d5, d6, d7}, [r3]!
448     vst1.u8         {d8, d9, d10, d11}, [r3]!
449     vst1.u8         {d12, d13, d14, d15}, [r3]!
450
451     bne             vp8e_filt_blk2d_fpo16x16s_loop_neon
452
453     b               sub_pixel_variance16x16s_neon
454
455 ;---------------------
456 secondpass_bfilter16x16s_only
457     sub             sp, sp, #256            ;reserve space on stack for temporary storage
458
459     mov             r2, #2                  ;loop counter
460     vld1.u8         {d0, d1}, [r0], r1      ;load src data
461     mov             r3, sp
462
463 vp8e_filt_blk2d_spo16x16s_loop_neon
464     vld1.u8         {d2, d3}, [r0], r1
465     vld1.u8         {d4, d5}, [r0], r1
466     vld1.u8         {d6, d7}, [r0], r1
467     vld1.u8         {d8, d9}, [r0], r1
468
469     vrhadd.u8       q0, q0, q1
470     vld1.u8         {d10, d11}, [r0], r1
471     vrhadd.u8       q1, q1, q2
472     vld1.u8         {d12, d13}, [r0], r1
473     vrhadd.u8       q2, q2, q3
474     vld1.u8         {d14, d15}, [r0], r1
475     vrhadd.u8       q3, q3, q4
476     vld1.u8         {d16, d17}, [r0], r1
477     vrhadd.u8       q4, q4, q5
478     vrhadd.u8       q5, q5, q6
479     vrhadd.u8       q6, q6, q7
480     vrhadd.u8       q7, q7, q8
481
482     subs            r2, r2, #1
483
484     vst1.u8         {d0, d1, d2, d3}, [r3]!         ;store result
485     vmov            q0, q8
486     vst1.u8         {d4, d5, d6, d7}, [r3]!
487     vst1.u8         {d8, d9, d10, d11}, [r3]!           ;store result
488     vst1.u8         {d12, d13, d14, d15}, [r3]!
489
490     bne             vp8e_filt_blk2d_spo16x16s_loop_neon
491
492     b               sub_pixel_variance16x16s_neon
493
494 ;----------------------------
495 ;variance16x16
496 sub_pixel_variance16x16s_neon
497     vmov.i8         q8, #0                      ;q8 - sum
498     vmov.i8         q9, #0                      ;q9, q10 - sse
499     vmov.i8         q10, #0
500
501     sub             r3, r3, #256
502     mov             r2, #4
503
504 sub_pixel_variance16x16s_neon_loop
505     vld1.8          {q0}, [r3]!                 ;Load up source and reference
506     vld1.8          {q1}, [r4], r12
507     vld1.8          {q2}, [r3]!
508     vld1.8          {q3}, [r4], r12
509     vld1.8          {q4}, [r3]!
510     vld1.8          {q5}, [r4], r12
511     vld1.8          {q6}, [r3]!
512     vld1.8          {q7}, [r4], r12
513
514     vsubl.u8        q11, d0, d2                 ;diff
515     vsubl.u8        q12, d1, d3
516     vsubl.u8        q13, d4, d6
517     vsubl.u8        q14, d5, d7
518     vsubl.u8        q0, d8, d10
519     vsubl.u8        q1, d9, d11
520     vsubl.u8        q2, d12, d14
521     vsubl.u8        q3, d13, d15
522
523     vpadal.s16      q8, q11                     ;sum
524     vmlal.s16       q9, d22, d22                ;sse
525     vmlal.s16       q10, d23, d23
526
527     subs            r2, r2, #1
528
529     vpadal.s16      q8, q12
530     vmlal.s16       q9, d24, d24
531     vmlal.s16       q10, d25, d25
532     vpadal.s16      q8, q13
533     vmlal.s16       q9, d26, d26
534     vmlal.s16       q10, d27, d27
535     vpadal.s16      q8, q14
536     vmlal.s16       q9, d28, d28
537     vmlal.s16       q10, d29, d29
538
539     vpadal.s16      q8, q0                     ;sum
540     vmlal.s16       q9, d0, d0                ;sse
541     vmlal.s16       q10, d1, d1
542     vpadal.s16      q8, q1
543     vmlal.s16       q9, d2, d2
544     vmlal.s16       q10, d3, d3
545     vpadal.s16      q8, q2
546     vmlal.s16       q9, d4, d4
547     vmlal.s16       q10, d5, d5
548     vpadal.s16      q8, q3
549     vmlal.s16       q9, d6, d6
550     vmlal.s16       q10, d7, d7
551
552     bne             sub_pixel_variance16x16s_neon_loop
553
554     vadd.u32        q10, q9, q10                ;accumulate sse
555     vpaddl.s32      q0, q8                      ;accumulate sum
556
557     vpaddl.u32      q1, q10
558     vadd.s64        d0, d0, d1
559     vadd.u64        d1, d2, d3
560
561     vmull.s32       q5, d0, d0
562     vst1.32         {d1[0]}, [lr]               ;store sse
563     vshr.u32        d10, d10, #8
564     vsub.u32        d0, d1, d10
565
566     add             sp, sp, #256
567     vmov.32         r0, d0[0]                   ;return
568
569     pop             {r4, pc}
570     ENDP
571
572     END