1 /*
2  * Copyright (C) 2020 Linux Studio Plugins Project <https://lsp-plug.in/>
3  *           (C) 2020 Vladimir Sadovnikov <sadko4u@gmail.com>
4  *
5  * This file is part of lsp-plugins
6  * Created on: 19 нояб. 2016 г.
7  *
8  * lsp-plugins is free software: you can redistribute it and/or modify
9  * it under the terms of the GNU Lesser General Public License as published by
10  * the Free Software Foundation, either version 3 of the License, or
11  * any later version.
12  *
13  * lsp-plugins 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 Lesser General Public License for more details.
17  *
18  * You should have received a copy of the GNU Lesser General Public License
19  * along with lsp-plugins. If not, see <https://www.gnu.org/licenses/>.
20  */
21 
22 #ifndef DSP_ARCH_NATIVE_RESAMPLING_H_
23 #define DSP_ARCH_NATIVE_RESAMPLING_H_
24 
25 #ifndef __DSP_NATIVE_IMPL
26     #error "This header should not be included directly"
27 #endif /* __DSP_NATIVE_IMPL */
28 
29 /*
30 
31     #include <stdio.h>
32     #include <math.h>
33 
34     // Number of lobes
35     #define KERNEL_SIZE     4
36     // Oversampling times
37     #define KERNEL_TIMES    2
38     // Number of samples to generate
39     #define KERNEL_MAX      64
40 
41     double kernel[KERNEL_MAX];
42 
43     int main(void)
44     {
45         ssize_t leaf = KERNEL_SIZE * KERNEL_TIMES;
46         ssize_t dots = leaf * 2 + 1;
47 
48         for (ssize_t i=0; i<KERNEL_MAX; ++i)
49         {
50             double xx = double(i - leaf) / double(KERNEL_TIMES);
51 
52             if (i >= dots)
53                 kernel[i] = 0.0;
54             else if (i == leaf)
55                 kernel[i] = 1.0;
56             else
57             {
58                 double px = M_PI * xx;
59                 kernel[i] = (double(KERNEL_SIZE) * sin(px) * sin(px / double(KERNEL_SIZE))) / (px * px);
60             }
61         }
62 
63         printf("leaf=%d, dots=%d, kernel_size=%d, kernel_times=%d\n", int(leaf), int(dots), KERNEL_SIZE, KERNEL_TIMES);
64         for (ssize_t i=0; i<KERNEL_MAX; ++i)
65             printf("%s%.16ff,\n", (kernel[i] >= 0.0) ? "+" : "", kernel[i]);
66 
67         printf("code:\n");
68         for (ssize_t i=0; i<KERNEL_MAX; ++i)
69         {
70             double v = kernel[i];
71             if (fabs(v) < 1e-6)
72                 continue;
73 
74             const char *s = (i >= 10) ? "    " : "     ";
75 
76             if (v > 0.0)
77                 printf("dst[%d]%s+= %.16ff * s;\n", int(i), s, v);
78             else
79                 printf("dst[%d]%s-= %.16ff * s;\n", int(i), s, -v);
80         }
81 
82         return 0;
83     }
84 
85 
86  */
87 
88 namespace native
89 {
lanczos_resample_2x2(float * dst,const float * src,size_t count)90     void lanczos_resample_2x2(float *dst, const float *src, size_t count)
91     {
92         while (count--)
93         {
94             float s     = *(src++);
95 
96             // Apply Lanczos 2x2 kernel
97             dst[1]     -= 0.0636843520278618f * s;
98             dst[3]     += 0.5731591682507563f * s;
99             dst[4]     += s;
100             dst[5]     += 0.5731591682507563f * s;
101             dst[7]     -= 0.0636843520278618f * s;
102 
103             // Move destination buffer
104             dst        += 2;
105         }
106     }
107 
lanczos_resample_2x3(float * dst,const float * src,size_t count)108     void lanczos_resample_2x3(float *dst, const float *src, size_t count)
109     {
110         while (count--)
111         {
112             float s     = *(src++);
113 
114             // Apply Lanczos 2x3 kernel
115             dst[1]     += 0.0243170840741611f * s;
116             dst[3]     -= 0.1350949115231170f * s;
117             dst[5]     += 0.6079271018540265f * s;
118             dst[6]     += s;
119             dst[7]     += 0.6079271018540265f * s;
120             dst[9]     -= 0.1350949115231170f * s;
121             dst[11]    += 0.0243170840741611f * s;
122 
123             // Move destination buffer
124             dst        += 2;
125         }
126     }
127 
lanczos_resample_2x4(float * dst,const float * src,size_t count)128     void lanczos_resample_2x4(float *dst, const float *src, size_t count)
129     {
130         while (count--)
131         {
132             float s     = *(src++);
133 
134             // Apply Lanczos 2x3 kernel
135             dst[1]     -= 0.0126608778212387f * s;
136             dst[3]     += 0.0599094833772629f * s;
137             dst[5]     -= 0.1664152316035080f * s;
138             dst[7]     += 0.6203830132406946f * s;
139             dst[8]     += 1.0000000000000000f * s;
140             dst[9]     += 0.6203830132406946f * s;
141             dst[11]    -= 0.1664152316035080f * s;
142             dst[13]    += 0.0599094833772629f * s;
143             dst[15]    -= 0.0126608778212387f * s;
144 
145             // Move destination buffer
146             dst        += 2;
147         }
148     }
149 
lanczos_resample_3x2(float * dst,const float * src,size_t count)150     void lanczos_resample_3x2(float *dst, const float *src, size_t count)
151     {
152         while (count--)
153         {
154             float s     = *(src++);
155 
156             // Apply Lanczos 3x2 kernel
157             dst[1]     -= 0.0315888188312782f * s;
158             dst[2]     -= 0.0854897486982225f * s;
159             dst[4]     += 0.3419589947928900f * s;
160             dst[5]     += 0.7897204707819555f * s;
161             dst[6]     += s;
162             dst[7]     += 0.7897204707819555f * s;
163             dst[8]     += 0.3419589947928900f * s;
164             dst[10]    -= 0.0854897486982225f * s;
165             dst[11]    -= 0.0315888188312782f * s;
166 
167             // Move destination buffer
168             dst        += 3;
169         }
170     }
171 
lanczos_resample_3x3(float * dst,const float * src,size_t count)172     void lanczos_resample_3x3(float *dst, const float *src, size_t count)
173     {
174         while (count--)
175         {
176             float s     = *(src++);
177 
178             // Apply Lanczos 3x3 kernel
179             dst[1]     += 0.0126609519658153f * s;
180             dst[2]     += 0.0310789306368038f * s;
181             dst[4]     -= 0.0933267410806225f * s;
182             dst[5]     -= 0.1458230329384726f * s;
183             dst[7]     += 0.3807169003008463f * s;
184             dst[8]     += 0.8103009258121772f * s;
185             dst[9]     += s;
186             dst[10]    += 0.8103009258121772f * s;
187             dst[11]    += 0.3807169003008463f * s;
188             dst[13]    -= 0.1458230329384726f * s;
189             dst[14]    -= 0.0933267410806225f * s;
190             dst[16]    += 0.0310789306368038f * s;
191             dst[17]    += 0.0126609519658153f * s;
192 
193             // Move destination buffer
194             dst        += 3;
195         }
196     }
197 
lanczos_resample_3x4(float * dst,const float * src,size_t count)198     void lanczos_resample_3x4(float *dst, const float *src, size_t count)
199     {
200         while (count--)
201         {
202             float s     = *(src++);
203 
204             // Apply Lanczos 3x3 kernel
205             dst[1]     -= 0.0067568495254777f * s;
206             dst[2]     -= 0.0157944094156391f * s;
207             dst[4]     += 0.0427448743491113f * s;
208             dst[5]     += 0.0622703182267308f * s;
209             dst[7]     -= 0.1220498237243924f * s;
210             dst[8]     -= 0.1709794973964449f * s;
211             dst[10]    += 0.3948602353909778f * s;
212             dst[11]    += 0.8175787925827955f * s;
213             dst[12]    += 1.0000000000000000f * s;
214             dst[13]    += 0.8175787925827955f * s;
215             dst[14]    += 0.3948602353909778f * s;
216             dst[16]    -= 0.1709794973964449f * s;
217             dst[17]    -= 0.1220498237243924f * s;
218             dst[19]    += 0.0622703182267308f * s;
219             dst[20]    += 0.0427448743491113f * s;
220             dst[22]    -= 0.0157944094156391f * s;
221             dst[23]    -= 0.0067568495254777f * s;
222 
223             // Move destination buffer
224             dst        += 3;
225         }
226     }
227 
lanczos_resample_4x2(float * dst,const float * src,size_t count)228     void lanczos_resample_4x2(float *dst, const float *src, size_t count)
229     {
230         while (count--)
231         {
232             float s     = *(src++);
233 
234             // Apply Lanczos 4x2 kernel
235             dst[1]     -= 0.0179051851263444f * s;
236             dst[2]     -= 0.0636843520278618f * s;
237             dst[3]     -= 0.0847248039068907f * s;
238             dst[5]     += 0.2353466775191407f * s;
239             dst[6]     += 0.5731591682507563f * s;
240             dst[7]     += 0.8773540711908775f * s;
241             dst[8]     += s;
242             dst[9]     += 0.8773540711908775f * s;
243             dst[10]    += 0.5731591682507563f * s;
244             dst[11]    += 0.2353466775191407f * s;
245             dst[13]    -= 0.0847248039068907f * s;
246             dst[14]    -= 0.0636843520278618f * s;
247             dst[15]    -= 0.0179051851263444f * s;
248 
249             // Move destination buffer
250             dst        += 4;
251         }
252     }
253 
lanczos_resample_4x3(float * dst,const float * src,size_t count)254     void lanczos_resample_4x3(float *dst, const float *src, size_t count)
255     {
256         while (count--)
257         {
258             float s     = *(src++);
259 
260             // Apply Lanczos 4x3 kernel
261             dst[1]     += 0.0073559260471942f * s;
262             dst[2]     += 0.0243170840741611f * s;
263             dst[3]     += 0.0300210914495816f * s;
264             dst[5]     -= 0.0677913359005429f * s;
265             dst[6]     -= 0.1350949115231170f * s;
266             dst[7]     -= 0.1328710183650640f * s;
267             dst[9]     += 0.2701898230462341f * s;
268             dst[10]    += 0.6079271018540265f * s;
269             dst[11]    += 0.8900670517104946f * s;
270             dst[12]    += s;
271             dst[13]    += 0.8900670517104946f * s;
272             dst[14]    += 0.6079271018540265f * s;
273             dst[15]    += 0.2701898230462341f * s;
274             dst[17]    -= 0.1328710183650640f * s;
275             dst[18]    -= 0.1350949115231170f * s;
276             dst[19]    -= 0.0677913359005429f * s;
277             dst[21]    += 0.0300210914495816f * s;
278             dst[22]    += 0.0243170840741611f * s;
279             dst[23]    += 0.0073559260471942f * s;
280 
281             // Move destination buffer
282             dst        += 4;
283         }
284     }
285 
lanczos_resample_4x4(float * dst,const float * src,size_t count)286     void lanczos_resample_4x4(float *dst, const float *src, size_t count)
287     {
288         while (count--)
289         {
290             float s     = *(src++);
291 
292             // Apply Lanczos 4x3 kernel
293             dst[1]     -= 0.0039757442382413f * s;
294             dst[2]     -= 0.0126608778212387f * s;
295             dst[3]     -= 0.0150736176408234f * s;
296 
297             dst[5]     += 0.0315083921595442f * s;
298             dst[6]     += 0.0599094833772629f * s;
299             dst[7]     += 0.0555206000541729f * s;
300 
301             dst[9]     -= 0.0917789511099593f * s;
302             dst[10]    -= 0.1664152316035080f * s;
303             dst[11]    -= 0.1525006180521938f * s;
304 
305             dst[13]    += 0.2830490423665725f * s;
306             dst[14]    += 0.6203830132406946f * s;
307             dst[15]    += 0.8945424536042901f * s;
308 
309             dst[16]    += 1.0000000000000000f * s;
310 
311             dst[17]    += 0.8945424536042901f * s;
312             dst[18]    += 0.6203830132406946f * s;
313             dst[19]    += 0.2830490423665725f * s;
314 
315             dst[21]    -= 0.1525006180521938f * s;
316             dst[22]    -= 0.1664152316035080f * s;
317             dst[23]    -= 0.0917789511099593f * s;
318 
319             dst[25]    += 0.0555206000541729f * s;
320             dst[26]    += 0.0599094833772629f * s;
321             dst[27]    += 0.0315083921595442f * s;
322 
323             dst[29]    -= 0.0150736176408234f * s;
324             dst[30]    -= 0.0126608778212387f * s;
325             dst[31]    -= 0.0039757442382413f * s;
326 
327             // Move destination buffer
328             dst        += 4;
329         }
330     }
331 
lanczos_resample_6x2(float * dst,const float * src,size_t count)332     void lanczos_resample_6x2(float *dst, const float *src, size_t count)
333     {
334         while (count--)
335         {
336             float s     = *(src++);
337 
338             // Apply Lanczos 6x2 kernel
339             dst[1]     -= 0.0078021377848166f * s;
340             dst[2]     -= 0.0315888188312782f * s;
341             dst[3]     -= 0.0636843520278618f * s;
342             dst[4]     -= 0.0854897486982225f * s;
343             dst[5]     -= 0.0719035699814534f * s;
344 
345             dst[7]     += 0.1409309971636486f * s;
346             dst[8]     += 0.3419589947928900f * s;
347             dst[9]     += 0.5731591682507563f * s;
348             dst[10]    += 0.7897204707819555f * s;
349             dst[11]    += 0.9440586719628122f * s;
350 
351             dst[12]    += s;
352 
353             dst[13]    += 0.9440586719628122f * s;
354             dst[14]    += 0.7897204707819555f * s;
355             dst[15]    += 0.5731591682507563f * s;
356             dst[16]    += 0.3419589947928900f * s;
357             dst[17]    += 0.1409309971636486f * s;
358 
359             dst[19]    -= 0.0719035699814534f * s;
360             dst[20]    -= 0.0854897486982225f * s;
361             dst[21]    -= 0.0636843520278618f * s;
362             dst[22]    -= 0.0315888188312782f * s;
363             dst[23]    -= 0.0078021377848166f * s;
364 
365             // Move destination buffer
366             dst        += 6;
367         }
368     }
369 
lanczos_resample_6x3(float * dst,const float * src,size_t count)370     void lanczos_resample_6x3(float *dst, const float *src, size_t count)
371     {
372         while (count--)
373         {
374             float s     = *(src++);
375 
376             // Apply Lanczos 6x3 kernel
377             dst[1]     += 0.0032875048460955f * s;
378             dst[2]     += 0.0126609519658153f * s;
379             dst[3]     += 0.0243170840741611f * s;
380             dst[4]     += 0.0310789306368038f * s;
381             dst[5]     += 0.0248005479513036f * s;
382 
383             dst[7]     -= 0.0424907562338176f * s;
384             dst[8]     -= 0.0933267410806225f * s;
385             dst[9]     -= 0.1350949115231170f * s;
386             dst[10]    -= 0.1458230329384726f * s;
387             dst[11]    -= 0.1049261531488149f * s;
388 
389             dst[13]    += 0.1676517041508127f * s;
390             dst[14]    += 0.3807169003008463f * s;
391             dst[15]    += 0.6079271018540265f * s;
392             dst[16]    += 0.8103009258121772f * s;
393             dst[17]    += 0.9500889005216107f * s;
394 
395             dst[18]    += s;
396 
397             dst[19]    += 0.9500889005216107f * s;
398             dst[20]    += 0.8103009258121772f * s;
399             dst[21]    += 0.6079271018540265f * s;
400             dst[22]    += 0.3807169003008463f * s;
401             dst[23]    += 0.1676517041508127f * s;
402 
403             dst[25]    -= 0.1049261531488149f * s;
404             dst[26]    -= 0.1458230329384726f * s;
405             dst[27]    -= 0.1350949115231170f * s;
406             dst[28]    -= 0.0933267410806225f * s;
407             dst[29]    -= 0.0424907562338176f * s;
408 
409             dst[31]    += 0.0248005479513036f * s;
410             dst[32]    += 0.0310789306368038f * s;
411             dst[33]    += 0.0243170840741611f * s;
412             dst[34]    += 0.0126609519658153f * s;
413             dst[35]    += 0.0032875048460955f * s;
414 
415             // Move destination buffer
416             dst        += 6;
417         }
418     }
419 
lanczos_resample_6x4(float * dst,const float * src,size_t count)420     void lanczos_resample_6x4(float *dst, const float *src, size_t count)
421     {
422         while (count--)
423         {
424             float s     = *(src++);
425 
426             // Apply Lanczos 6x3 kernel
427             dst[1]     -= 0.0018000092949500f * s;
428             dst[2]     -= 0.0067568495254777f * s;
429             dst[3]     -= 0.0126608778212387f * s;
430             dst[4]     -= 0.0157944094156391f * s;
431             dst[5]     -= 0.0123019137260206f * s;
432 
433             dst[7]     += 0.0200263389720192f * s;
434             dst[8]     += 0.0427448743491113f * s;
435             dst[9]     += 0.0599094833772629f * s;
436             dst[10]    += 0.0622703182267308f * s;
437             dst[11]    += 0.0427971267140625f * s;
438 
439             dst[13]    -= 0.0597744992948478f * s;
440             dst[14]    -= 0.1220498237243924f * s;
441             dst[15]    -= 0.1664152316035080f * s;
442             dst[16]    -= 0.1709794973964449f * s;
443             dst[17]    -= 0.1181145298553785f * s;
444 
445             dst[19]    += 0.1776396342037379f * s;
446             dst[20]    += 0.3948602353909778f * s;
447             dst[21]    += 0.6203830132406946f * s;
448             dst[22]    += 0.8175787925827955f * s;
449             dst[23]    += 0.9522049170285306f * s;
450 
451             dst[24]    += 1.0000000000000000f * s;
452 
453             dst[25]    += 0.9522049170285306f * s;
454             dst[26]    += 0.8175787925827955f * s;
455             dst[27]    += 0.6203830132406946f * s;
456             dst[28]    += 0.3948602353909778f * s;
457             dst[29]    += 0.1776396342037379f * s;
458 
459             dst[31]    -= 0.1181145298553785f * s;
460             dst[32]    -= 0.1709794973964449f * s;
461             dst[33]    -= 0.1664152316035080f * s;
462             dst[34]    -= 0.1220498237243924f * s;
463             dst[35]    -= 0.0597744992948478f * s;
464 
465             dst[37]    += 0.0427971267140625f * s;
466             dst[38]    += 0.0622703182267308f * s;
467             dst[39]    += 0.0599094833772629f * s;
468             dst[40]    += 0.0427448743491113f * s;
469             dst[41]    += 0.0200263389720192f * s;
470 
471             dst[43]    -= 0.0123019137260206f * s;
472             dst[44]    -= 0.0157944094156391f * s;
473             dst[45]    -= 0.0126608778212387f * s;
474             dst[46]    -= 0.0067568495254777f * s;
475             dst[47]    -= 0.0018000092949500f * s;
476 
477             // Move destination buffer
478             dst        += 6;
479         }
480     }
481 
lanczos_resample_8x2(float * dst,const float * src,size_t count)482     void lanczos_resample_8x2(float *dst, const float *src, size_t count)
483     {
484         while (count--)
485         {
486             float s     = *(src++);
487 
488             // Apply Lanczos 8x2 kernel
489             dst[1]     -= 0.0043033145538298f * s;
490             dst[2]     -= 0.0179051851263444f * s;
491             dst[3]     -= 0.0393892611124141f * s;
492             dst[4]     -= 0.0636843520278618f * s;
493             dst[5]     -= 0.0823353965569232f * s;
494             dst[6]     -= 0.0847248039068907f * s;
495             dst[7]     -= 0.0600950644541902f * s;
496 
497             dst[9]     += 0.0993408208324369f * s;
498             dst[10]    += 0.2353466775191407f * s;
499             dst[11]    += 0.3985033193355084f * s;
500             dst[12]    += 0.5731591682507563f * s;
501             dst[13]    += 0.7396427919997760f * s;
502             dst[14]    += 0.8773540711908775f * s;
503             dst[15]    += 0.9682457746117045f * s;
504 
505             dst[16]    += s;
506 
507             dst[17]    += 0.9682457746117045f * s;
508             dst[18]    += 0.8773540711908775f * s;
509             dst[19]    += 0.7396427919997760f * s;
510             dst[20]    += 0.5731591682507563f * s;
511             dst[21]    += 0.3985033193355084f * s;
512             dst[22]    += 0.2353466775191407f * s;
513             dst[23]    += 0.0993408208324369f * s;
514 
515             dst[25]    -= 0.0600950644541902f * s;
516             dst[26]    -= 0.0847248039068907f * s;
517             dst[27]    -= 0.0823353965569232f * s;
518             dst[28]    -= 0.0636843520278618f * s;
519             dst[29]    -= 0.0393892611124141f * s;
520             dst[30]    -= 0.0179051851263444f * s;
521             dst[31]    -= 0.0043033145538298f * s;
522 
523             // Move destination buffer
524             dst        += 8;
525         }
526     }
527 
lanczos_resample_8x3(float * dst,const float * src,size_t count)528     void lanczos_resample_8x3(float *dst, const float *src, size_t count)
529     {
530         while (count--)
531         {
532             float s     = *(src++);
533 
534             // Apply Lanczos 8x3 kernel
535             dst[1]     += 0.0018368899607481f * s;
536             dst[2]     += 0.0073559260471942f * s;
537             dst[3]     += 0.0155961678435580f * s;
538             dst[4]     += 0.0243170840741611f * s;
539             dst[5]     += 0.0303079634725070f * s;
540             dst[6]     += 0.0300210914495816f * s;
541             dst[7]     += 0.0204366616947175f * s;
542 
543             dst[9]     -= 0.0305684889733737f * s;
544             dst[10]    -= 0.0677913359005429f * s;
545             dst[11]    -= 0.1054383717904384f * s;
546             dst[12]    -= 0.1350949115231170f * s;
547             dst[13]    -= 0.1472651639056537f * s;
548             dst[14]    -= 0.1328710183650640f * s;
549             dst[15]    -= 0.0849124693704824f * s;
550 
551             dst[17]    += 0.1205345965259870f * s;
552             dst[18]    += 0.2701898230462341f * s;
553             dst[19]    += 0.4376469925430009f * s;
554             dst[20]    += 0.6079271018540265f * s;
555             dst[21]    += 0.7642122243343417f * s;
556             dst[22]    += 0.8900670517104946f * s;
557             dst[23]    += 0.9717147892357163f * s;
558 
559             dst[24]    += s;
560 
561             dst[25]    += 0.9717147892357163f * s;
562             dst[26]    += 0.8900670517104946f * s;
563             dst[27]    += 0.7642122243343417f * s;
564             dst[28]    += 0.6079271018540265f * s;
565             dst[29]    += 0.4376469925430009f * s;
566             dst[30]    += 0.2701898230462341f * s;
567             dst[31]    += 0.1205345965259870f * s;
568 
569             dst[33]    -= 0.0849124693704824f * s;
570             dst[34]    -= 0.1328710183650640f * s;
571             dst[35]    -= 0.1472651639056537f * s;
572             dst[36]    -= 0.1350949115231170f * s;
573             dst[37]    -= 0.1054383717904384f * s;
574             dst[38]    -= 0.0677913359005429f * s;
575             dst[39]    -= 0.0305684889733737f * s;
576 
577             dst[41]    += 0.0204366616947175f * s;
578             dst[42]    += 0.0300210914495816f * s;
579             dst[43]    += 0.0303079634725070f * s;
580             dst[44]    += 0.0243170840741611f * s;
581             dst[45]    += 0.0155961678435580f * s;
582             dst[46]    += 0.0073559260471942f * s;
583             dst[47]    += 0.0018368899607481f * s;
584 
585             // Move destination buffer
586             dst        += 8;
587         }
588     }
589 
lanczos_resample_8x4(float * dst,const float * src,size_t count)590     void lanczos_resample_8x4(float *dst, const float *src, size_t count)
591     {
592         while (count--)
593         {
594             float s     = *(src++);
595 
596             // Apply Lanczos 8x3 kernel
597             dst[1]     -= 0.0010124148822791f * s;
598             dst[2]     -= 0.0039757442382413f * s;
599             dst[3]     -= 0.0082714887261119f * s;
600             dst[4]     -= 0.0126608778212387f * s;
601             dst[5]     -= 0.0154958216565010f * s;
602             dst[6]     -= 0.0150736176408234f * s;
603             dst[7]     -= 0.0100753105205530f * s;
604 
605             dst[9]     += 0.0145047275409824f * s;
606             dst[10]    += 0.0315083921595442f * s;
607             dst[11]    += 0.0479233082326825f * s;
608             dst[12]    += 0.0599094833772629f * s;
609             dst[13]    += 0.0635233253590927f * s;
610             dst[14]    += 0.0555206000541729f * s;
611             dst[15]    += 0.0341810767869351f * s;
612 
613             dst[17]    -= 0.0439036941841078f * s;
614             dst[18]    -= 0.0917789511099593f * s;
615             dst[19]    -= 0.1356918370096595f * s;
616             dst[20]    -= 0.1664152316035080f * s;
617             dst[21]    -= 0.1746626357901899f * s;
618             dst[22]    -= 0.1525006180521938f * s;
619             dst[23]    -= 0.0947284057923417f * s;
620 
621             dst[25]    += 0.1285116137825641f * s;
622             dst[26]    += 0.2830490423665725f * s;
623             dst[27]    += 0.4518581595035692f * s;
624             dst[28]    += 0.6203830132406946f * s;
625             dst[29]    += 0.7729246687400148f * s;
626             dst[30]    += 0.8945424536042901f * s;
627             dst[31]    += 0.9729307018702211f * s;
628 
629             dst[32]    += 1.0000000000000000f * s;
630 
631             dst[33]    += 0.9729307018702211f * s;
632             dst[34]    += 0.8945424536042901f * s;
633             dst[35]    += 0.7729246687400148f * s;
634             dst[36]    += 0.6203830132406946f * s;
635             dst[37]    += 0.4518581595035692f * s;
636             dst[38]    += 0.2830490423665725f * s;
637             dst[39]    += 0.1285116137825641f * s;
638 
639             dst[41]    -= 0.0947284057923417f * s;
640             dst[42]    -= 0.1525006180521938f * s;
641             dst[43]    -= 0.1746626357901899f * s;
642             dst[44]    -= 0.1664152316035080f * s;
643             dst[45]    -= 0.1356918370096595f * s;
644             dst[46]    -= 0.0917789511099593f * s;
645             dst[47]    -= 0.0439036941841078f * s;
646 
647             dst[49]    += 0.0341810767869351f * s;
648             dst[50]    += 0.0555206000541729f * s;
649             dst[51]    += 0.0635233253590927f * s;
650             dst[52]    += 0.0599094833772629f * s;
651             dst[53]    += 0.0479233082326825f * s;
652             dst[54]    += 0.0315083921595442f * s;
653             dst[55]    += 0.0145047275409824f * s;
654 
655             dst[57]    -= 0.0100753105205530f * s;
656             dst[58]    -= 0.0150736176408234f * s;
657             dst[59]    -= 0.0154958216565010f * s;
658             dst[60]    -= 0.0126608778212387f * s;
659             dst[61]    -= 0.0082714887261119f * s;
660             dst[62]    -= 0.0039757442382413f * s;
661             dst[63]    -= 0.0010124148822791f * s;
662 
663             // Move destination buffer
664             dst        += 8;
665         }
666     }
667 
downsample_2x(float * dst,const float * src,size_t count)668     void downsample_2x(float *dst, const float *src, size_t count)
669     {
670         while (count--)
671         {
672             *dst    = *src;
673             dst     ++;
674             src     += 2;
675         }
676     }
677 
downsample_3x(float * dst,const float * src,size_t count)678     void downsample_3x(float *dst, const float *src, size_t count)
679     {
680         while (count--)
681         {
682             *dst    = *src;
683             dst     ++;
684             src     += 3;
685         }
686     }
687 
downsample_4x(float * dst,const float * src,size_t count)688     void downsample_4x(float *dst, const float *src, size_t count)
689     {
690         while (count--)
691         {
692             *dst    = *src;
693             dst     ++;
694             src     += 4;
695         }
696     }
697 
downsample_6x(float * dst,const float * src,size_t count)698     void downsample_6x(float *dst, const float *src, size_t count)
699     {
700         while (count--)
701         {
702             *dst    = *src;
703             dst     ++;
704             src     += 6;
705         }
706     }
707 
downsample_8x(float * dst,const float * src,size_t count)708     void downsample_8x(float *dst, const float *src, size_t count)
709     {
710         while (count--)
711         {
712             *dst    = *src;
713             dst     ++;
714             src     += 8;
715         }
716     }
717 }
718 
719 #endif /* DSP_ARCH_NATIVE_RESAMPLING_H_ */
720