1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
|
/*
* Copyright (c) 2008 Siarhei Siamashka <ssvb@users.sourceforge.net>
*
* This file is part of Libav.
*
* Libav is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* Libav is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with Libav; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*/
#include "config.h"
#include "asm.S"
/**
* Assume that len is a positive number and is multiple of 8
*/
@ void ff_vector_fmul_vfp(float *dst, const float *src0, const float *src1, int len)
function ff_vector_fmul_vfp, export=1
vpush {d8-d15}
fmrx r12, fpscr
orr r12, r12, #(3 << 16) /* set vector size to 4 */
fmxr fpscr, r12
vldmia r1!, {s0-s3}
vldmia r2!, {s8-s11}
vldmia r1!, {s4-s7}
vldmia r2!, {s12-s15}
vmul.f32 s8, s0, s8
1:
subs r3, r3, #16
vmul.f32 s12, s4, s12
itttt ge
vldmiage r1!, {s16-s19}
vldmiage r2!, {s24-s27}
vldmiage r1!, {s20-s23}
vldmiage r2!, {s28-s31}
it ge
vmulge.f32 s24, s16, s24
vstmia r0!, {s8-s11}
vstmia r0!, {s12-s15}
it ge
vmulge.f32 s28, s20, s28
itttt gt
vldmiagt r1!, {s0-s3}
vldmiagt r2!, {s8-s11}
vldmiagt r1!, {s4-s7}
vldmiagt r2!, {s12-s15}
ittt ge
vmulge.f32 s8, s0, s8
vstmiage r0!, {s24-s27}
vstmiage r0!, {s28-s31}
bgt 1b
bic r12, r12, #(7 << 16) /* set vector size back to 1 */
fmxr fpscr, r12
vpop {d8-d15}
bx lr
endfunc
/**
* ARM VFP implementation of 'vector_fmul_window_c' function
* Assume that len is a positive non-zero number
*/
@ void ff_vector_fmul_window_vfp(float *dst, const float *src0,
@ const float *src1, const float *win, int len)
function ff_vector_fmul_window_vfp, export=1
DST0 .req a1
SRC0 .req a2
SRC1 .req a3
WIN0 .req a4
LEN .req v1
DST1 .req v2
WIN1 .req v3
OLDFPSCR .req ip
push {v1-v3,lr}
ldr LEN, [sp, #4*4+0]
vpush {s16-s31}
fmrx OLDFPSCR, FPSCR
add DST1, DST0, LEN, lsl #3
add SRC1, SRC1, LEN, lsl #2
add WIN1, WIN0, LEN, lsl #3
tst LEN, #7
beq 4f @ common case: len is a multiple of 8
ldr lr, =0x03000000 @ RunFast mode, scalar mode
fmxr FPSCR, lr
tst LEN, #1
beq 1f
vldmdb WIN1!, {s0}
vldmia SRC0!, {s8}
vldmia WIN0!, {s16}
vmul.f s24, s0, s8
vldmdb SRC1!, {s20}
vmul.f s8, s16, s8
vmls.f s24, s16, s20
vmla.f s8, s0, s20
vstmia DST0!, {s24}
vstmdb DST1!, {s8}
1:
tst LEN, #2
beq 2f
vldmdb WIN1!, {s0}
vldmdb WIN1!, {s1}
vldmia SRC0!, {s8-s9}
vldmia WIN0!, {s16-s17}
vmul.f s24, s0, s8
vmul.f s25, s1, s9
vldmdb SRC1!, {s20}
vldmdb SRC1!, {s21}
vmul.f s8, s16, s8
vmul.f s9, s17, s9
vmls.f s24, s16, s20
vmls.f s25, s17, s21
vmla.f s8, s0, s20
vmla.f s9, s1, s21
vstmia DST0!, {s24-s25}
vstmdb DST1!, {s8}
vstmdb DST1!, {s9}
2:
tst LEN, #4
beq 3f
vldmdb WIN1!, {s0}
vldmdb WIN1!, {s1}
vldmdb WIN1!, {s2}
vldmdb WIN1!, {s3}
vldmia SRC0!, {s8-s11}
vldmia WIN0!, {s16-s19}
vmul.f s24, s0, s8
vmul.f s25, s1, s9
vmul.f s26, s2, s10
vmul.f s27, s3, s11
vldmdb SRC1!, {s20}
vldmdb SRC1!, {s21}
vldmdb SRC1!, {s22}
vldmdb SRC1!, {s23}
vmul.f s8, s16, s8
vmul.f s9, s17, s9
vmul.f s10, s18, s10
vmul.f s11, s19, s11
vmls.f s24, s16, s20
vmls.f s25, s17, s21
vmls.f s26, s18, s22
vmls.f s27, s19, s23
vmla.f s8, s0, s20
vmla.f s9, s1, s21
vmla.f s10, s2, s22
vmla.f s11, s3, s23
vstmia DST0!, {s24-s27}
vstmdb DST1!, {s8}
vstmdb DST1!, {s9}
vstmdb DST1!, {s10}
vstmdb DST1!, {s11}
3:
bics LEN, LEN, #7
beq 7f
4:
ldr lr, =0x03030000 @ RunFast mode, short vectors of length 4, stride 1
fmxr FPSCR, lr
vldmdb WIN1!, {s0}
vldmdb WIN1!, {s1}
vldmdb WIN1!, {s2}
vldmdb WIN1!, {s3}
vldmia SRC0!, {s8-s11}
vldmia WIN0!, {s16-s19}
vmul.f s24, s0, s8 @ vector * vector
vldmdb SRC1!, {s20}
vldmdb SRC1!, {s21}
vldmdb SRC1!, {s22}
vldmdb SRC1!, {s23}
vmul.f s8, s16, s8 @ vector * vector
vmls.f s24, s16, s20 @ vector * vector
vldmdb WIN1!, {s4}
vldmdb WIN1!, {s5}
vldmdb WIN1!, {s6}
vldmdb WIN1!, {s7}
vldmia SRC0!, {s12-s13}
vmla.f s8, s0, s20 @ vector * vector
vldmia SRC0!, {s14-s15}
subs LEN, LEN, #8
beq 6f
5: vldmia WIN0!, {s20-s23}
vmul.f s28, s4, s12 @ vector * vector
vstmia DST0!, {s24-s25}
vldmdb SRC1!, {s16}
vldmdb SRC1!, {s17}
vldmdb SRC1!, {s18}
vldmdb SRC1!, {s19}
vmul.f s12, s20, s12 @ vector * vector
vstmia DST0!, {s26-s27}
vstmdb DST1!, {s8}
vstmdb DST1!, {s9}
vstmdb DST1!, {s10}
vstmdb DST1!, {s11}
vmls.f s28, s20, s16 @ vector * vector
vldmdb WIN1!, {s0}
vldmdb WIN1!, {s1}
vldmdb WIN1!, {s2}
vldmdb WIN1!, {s3}
vldmia SRC0!, {s8-s9}
vmla.f s12, s4, s16 @ vector * vector
vldmia SRC0!, {s10-s11}
subs LEN, LEN, #8
vldmia WIN0!, {s16-s19}
vmul.f s24, s0, s8 @ vector * vector
vstmia DST0!, {s28-s29}
vldmdb SRC1!, {s20}
vldmdb SRC1!, {s21}
vldmdb SRC1!, {s22}
vldmdb SRC1!, {s23}
vmul.f s8, s16, s8 @ vector * vector
vstmia DST0!, {s30-s31}
vstmdb DST1!, {s12}
vstmdb DST1!, {s13}
vstmdb DST1!, {s14}
vstmdb DST1!, {s15}
vmls.f s24, s16, s20 @ vector * vector
vldmdb WIN1!, {s4}
vldmdb WIN1!, {s5}
vldmdb WIN1!, {s6}
vldmdb WIN1!, {s7}
vldmia SRC0!, {s12-s13}
vmla.f s8, s0, s20 @ vector * vector
vldmia SRC0!, {s14-s15}
bne 5b
6: vldmia WIN0!, {s20-s23}
vmul.f s28, s4, s12 @ vector * vector
vstmia DST0!, {s24-s25}
vldmdb SRC1!, {s16}
vldmdb SRC1!, {s17}
vldmdb SRC1!, {s18}
vldmdb SRC1!, {s19}
vmul.f s12, s20, s12 @ vector * vector
vstmia DST0!, {s26-s27}
vstmdb DST1!, {s8}
vstmdb DST1!, {s9}
vstmdb DST1!, {s10}
vstmdb DST1!, {s11}
vmls.f s28, s20, s16 @ vector * vector
vmla.f s12, s4, s16 @ vector * vector
vstmia DST0!, {s28-s31}
vstmdb DST1!, {s12}
vstmdb DST1!, {s13}
vstmdb DST1!, {s14}
vstmdb DST1!, {s15}
7:
fmxr FPSCR, OLDFPSCR
vpop {s16-s31}
pop {v1-v3,pc}
.unreq DST0
.unreq SRC0
.unreq SRC1
.unreq WIN0
.unreq LEN
.unreq OLDFPSCR
.unreq DST1
.unreq WIN1
endfunc
/**
* ARM VFP optimized implementation of 'vector_fmul_reverse_c' function.
* Assume that len is a positive number and is multiple of 8
*/
@ void ff_vector_fmul_reverse_vfp(float *dst, const float *src0,
@ const float *src1, int len)
function ff_vector_fmul_reverse_vfp, export=1
vpush {d8-d15}
add r2, r2, r3, lsl #2
vldmdb r2!, {s0-s3}
vldmia r1!, {s8-s11}
vldmdb r2!, {s4-s7}
vldmia r1!, {s12-s15}
vmul.f32 s8, s3, s8
vmul.f32 s9, s2, s9
vmul.f32 s10, s1, s10
vmul.f32 s11, s0, s11
1:
subs r3, r3, #16
it ge
vldmdbge r2!, {s16-s19}
vmul.f32 s12, s7, s12
it ge
vldmiage r1!, {s24-s27}
vmul.f32 s13, s6, s13
it ge
vldmdbge r2!, {s20-s23}
vmul.f32 s14, s5, s14
it ge
vldmiage r1!, {s28-s31}
vmul.f32 s15, s4, s15
it ge
vmulge.f32 s24, s19, s24
it gt
vldmdbgt r2!, {s0-s3}
it ge
vmulge.f32 s25, s18, s25
vstmia r0!, {s8-s13}
it ge
vmulge.f32 s26, s17, s26
it gt
vldmiagt r1!, {s8-s11}
itt ge
vmulge.f32 s27, s16, s27
vmulge.f32 s28, s23, s28
it gt
vldmdbgt r2!, {s4-s7}
it ge
vmulge.f32 s29, s22, s29
vstmia r0!, {s14-s15}
ittt ge
vmulge.f32 s30, s21, s30
vmulge.f32 s31, s20, s31
vmulge.f32 s8, s3, s8
it gt
vldmiagt r1!, {s12-s15}
itttt ge
vmulge.f32 s9, s2, s9
vmulge.f32 s10, s1, s10
vstmiage r0!, {s24-s27}
vmulge.f32 s11, s0, s11
it ge
vstmiage r0!, {s28-s31}
bgt 1b
vpop {d8-d15}
bx lr
endfunc
/**
* ARM VFP implementation of 'butterflies_float_c' function
* Assume that len is a positive non-zero number
*/
@ void ff_butterflies_float_vfp(float *restrict v1, float *restrict v2, int len)
function ff_butterflies_float_vfp, export=1
BASE1 .req a1
BASE2 .req a2
LEN .req a3
OLDFPSCR .req a4
vpush {s16-s31}
fmrx OLDFPSCR, FPSCR
tst LEN, #7
beq 4f @ common case: len is a multiple of 8
ldr ip, =0x03000000 @ RunFast mode, scalar mode
fmxr FPSCR, ip
tst LEN, #1
beq 1f
vldmia BASE1!, {s0}
vldmia BASE2!, {s8}
vadd.f s16, s0, s8
vsub.f s24, s0, s8
vstr s16, [BASE1, #0-4*1]
vstr s24, [BASE2, #0-4*1]
1:
tst LEN, #2
beq 2f
vldmia BASE1!, {s0-s1}
vldmia BASE2!, {s8-s9}
vadd.f s16, s0, s8
vadd.f s17, s1, s9
vsub.f s24, s0, s8
vsub.f s25, s1, s9
vstr d8, [BASE1, #0-8*1] @ s16,s17
vstr d12, [BASE2, #0-8*1] @ s24,s25
2:
tst LEN, #4
beq 3f
vldmia BASE1!, {s0-s1}
vldmia BASE2!, {s8-s9}
vldmia BASE1!, {s2-s3}
vldmia BASE2!, {s10-s11}
vadd.f s16, s0, s8
vadd.f s17, s1, s9
vsub.f s24, s0, s8
vsub.f s25, s1, s9
vadd.f s18, s2, s10
vadd.f s19, s3, s11
vsub.f s26, s2, s10
vsub.f s27, s3, s11
vstr d8, [BASE1, #0-16*1] @ s16,s17
vstr d12, [BASE2, #0-16*1] @ s24,s25
vstr d9, [BASE1, #8-16*1] @ s18,s19
vstr d13, [BASE2, #8-16*1] @ s26,s27
3:
bics LEN, LEN, #7
beq 7f
4:
ldr ip, =0x03030000 @ RunFast mode, short vectors of length 4, stride 1
fmxr FPSCR, ip
vldmia BASE1!, {s0-s1}
vldmia BASE2!, {s8-s9}
vldmia BASE1!, {s2-s3}
vldmia BASE2!, {s10-s11}
vadd.f s16, s0, s8
vldmia BASE1!, {s4-s5}
vldmia BASE2!, {s12-s13}
vldmia BASE1!, {s6-s7}
vldmia BASE2!, {s14-s15}
vsub.f s24, s0, s8
vadd.f s20, s4, s12
subs LEN, LEN, #8
beq 6f
5: vldmia BASE1!, {s0-s3}
vldmia BASE2!, {s8-s11}
vsub.f s28, s4, s12
vstr d8, [BASE1, #0-16*3] @ s16,s17
vstr d9, [BASE1, #8-16*3] @ s18,s19
vstr d12, [BASE2, #0-16*3] @ s24,s25
vstr d13, [BASE2, #8-16*3] @ s26,s27
vadd.f s16, s0, s8
vldmia BASE1!, {s4-s7}
vldmia BASE2!, {s12-s15}
vsub.f s24, s0, s8
vstr d10, [BASE1, #0-16*3] @ s20,s21
vstr d11, [BASE1, #8-16*3] @ s22,s23
vstr d14, [BASE2, #0-16*3] @ s28,s29
vstr d15, [BASE2, #8-16*3] @ s30,s31
vadd.f s20, s4, s12
subs LEN, LEN, #8
bne 5b
6: vsub.f s28, s4, s12
vstr d8, [BASE1, #0-16*2] @ s16,s17
vstr d9, [BASE1, #8-16*2] @ s18,s19
vstr d12, [BASE2, #0-16*2] @ s24,s25
vstr d13, [BASE2, #8-16*2] @ s26,s27
vstr d10, [BASE1, #0-16*1] @ s20,s21
vstr d11, [BASE1, #8-16*1] @ s22,s23
vstr d14, [BASE2, #0-16*1] @ s28,s29
vstr d15, [BASE2, #8-16*1] @ s30,s31
7:
fmxr FPSCR, OLDFPSCR
vpop {s16-s31}
bx lr
.unreq BASE1
.unreq BASE2
.unreq LEN
.unreq OLDFPSCR
endfunc
|