Subversion Repositories AFRtranscoder

Rev

Details | Last modification | View Log | RSS feed

Rev Author Line No. Line
2 mjames 1
/* ----------------------------------------------------------------------
2
 * Project:      CMSIS DSP Library
3
 * Title:        arm_cfft_radix2_f32.c
4
 * Description:  Radix-2 Decimation in Frequency CFFT & CIFFT Floating point processing function
5
 *
6
 * $Date:        27. January 2017
7
 * $Revision:    V.1.5.1
8
 *
9
 * Target Processor: Cortex-M cores
10
 * -------------------------------------------------------------------- */
11
/*
12
 * Copyright (C) 2010-2017 ARM Limited or its affiliates. All rights reserved.
13
 *
14
 * SPDX-License-Identifier: Apache-2.0
15
 *
16
 * Licensed under the Apache License, Version 2.0 (the License); you may
17
 * not use this file except in compliance with the License.
18
 * You may obtain a copy of the License at
19
 *
20
 * www.apache.org/licenses/LICENSE-2.0
21
 *
22
 * Unless required by applicable law or agreed to in writing, software
23
 * distributed under the License is distributed on an AS IS BASIS, WITHOUT
24
 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
25
 * See the License for the specific language governing permissions and
26
 * limitations under the License.
27
 */
28
 
29
#include "arm_math.h"
30
 
31
void arm_radix2_butterfly_f32(
32
  float32_t * pSrc,
33
  uint32_t fftLen,
34
  float32_t * pCoef,
35
  uint16_t twidCoefModifier);
36
 
37
void arm_radix2_butterfly_inverse_f32(
38
  float32_t * pSrc,
39
  uint32_t fftLen,
40
  float32_t * pCoef,
41
  uint16_t twidCoefModifier,
42
  float32_t onebyfftLen);
43
 
44
extern void arm_bitreversal_f32(
45
    float32_t * pSrc,
46
    uint16_t fftSize,
47
    uint16_t bitRevFactor,
48
    uint16_t * pBitRevTab);
49
 
50
/**
51
* @ingroup groupTransforms
52
*/
53
 
54
/**
55
* @addtogroup ComplexFFT
56
* @{
57
*/
58
 
59
/**
60
* @details
61
* @brief Radix-2 CFFT/CIFFT.
62
* @deprecated Do not use this function.  It has been superseded by \ref arm_cfft_f32 and will be removed
63
* in the future.
64
* @param[in]      *S    points to an instance of the floating-point Radix-2 CFFT/CIFFT structure.
65
* @param[in, out] *pSrc points to the complex data buffer of size <code>2*fftLen</code>. Processing occurs in-place.
66
* @return none.
67
*/
68
 
69
void arm_cfft_radix2_f32(
70
const arm_cfft_radix2_instance_f32 * S,
71
float32_t * pSrc)
72
{
73
 
74
   if (S->ifftFlag == 1U)
75
   {
76
      /*  Complex IFFT radix-2  */
77
      arm_radix2_butterfly_inverse_f32(pSrc, S->fftLen, S->pTwiddle,
78
      S->twidCoefModifier, S->onebyfftLen);
79
   }
80
   else
81
   {
82
      /*  Complex FFT radix-2  */
83
      arm_radix2_butterfly_f32(pSrc, S->fftLen, S->pTwiddle,
84
      S->twidCoefModifier);
85
   }
86
 
87
   if (S->bitReverseFlag == 1U)
88
   {
89
      /*  Bit Reversal */
90
      arm_bitreversal_f32(pSrc, S->fftLen, S->bitRevFactor, S->pBitRevTable);
91
   }
92
 
93
}
94
 
95
 
96
/**
97
* @} end of ComplexFFT group
98
*/
99
 
100
 
101
 
102
/* ----------------------------------------------------------------------
103
** Internal helper function used by the FFTs
104
** ------------------------------------------------------------------- */
105
 
106
/*
107
* @brief  Core function for the floating-point CFFT butterfly process.
108
* @param[in, out] *pSrc            points to the in-place buffer of floating-point data type.
109
* @param[in]      fftLen           length of the FFT.
110
* @param[in]      *pCoef           points to the twiddle coefficient buffer.
111
* @param[in]      twidCoefModifier twiddle coefficient modifier that supports different size FFTs with the same twiddle factor table.
112
* @return none.
113
*/
114
 
115
void arm_radix2_butterfly_f32(
116
float32_t * pSrc,
117
uint32_t fftLen,
118
float32_t * pCoef,
119
uint16_t twidCoefModifier)
120
{
121
 
122
   uint32_t i, j, k, l;
123
   uint32_t n1, n2, ia;
124
   float32_t xt, yt, cosVal, sinVal;
125
   float32_t p0, p1, p2, p3;
126
   float32_t a0, a1;
127
 
128
#if defined (ARM_MATH_DSP)
129
 
130
   /*  Initializations for the first stage */
131
   n2 = fftLen >> 1;
132
   ia = 0;
133
   i = 0;
134
 
135
   // loop for groups
136
   for (k = n2; k > 0; k--)
137
   {
138
      cosVal = pCoef[ia * 2];
139
      sinVal = pCoef[(ia * 2) + 1];
140
 
141
      /*  Twiddle coefficients index modifier */
142
      ia += twidCoefModifier;
143
 
144
      /*  index calculation for the input as, */
145
      /*  pSrc[i + 0], pSrc[i + fftLen/1] */
146
      l = i + n2;
147
 
148
      /*  Butterfly implementation */
149
      a0 = pSrc[2 * i] + pSrc[2 * l];
150
      xt = pSrc[2 * i] - pSrc[2 * l];
151
 
152
      yt = pSrc[2 * i + 1] - pSrc[2 * l + 1];
153
      a1 = pSrc[2 * l + 1] + pSrc[2 * i + 1];
154
 
155
      p0 = xt * cosVal;
156
      p1 = yt * sinVal;
157
      p2 = yt * cosVal;
158
      p3 = xt * sinVal;
159
 
160
      pSrc[2 * i]     = a0;
161
      pSrc[2 * i + 1] = a1;
162
 
163
      pSrc[2 * l]     = p0 + p1;
164
      pSrc[2 * l + 1] = p2 - p3;
165
 
166
      i++;
167
   }                             // groups loop end
168
 
169
   twidCoefModifier <<= 1U;
170
 
171
   // loop for stage
172
   for (k = n2; k > 2; k = k >> 1)
173
   {
174
      n1 = n2;
175
      n2 = n2 >> 1;
176
      ia = 0;
177
 
178
      // loop for groups
179
      j = 0;
180
      do
181
      {
182
         cosVal = pCoef[ia * 2];
183
         sinVal = pCoef[(ia * 2) + 1];
184
         ia += twidCoefModifier;
185
 
186
         // loop for butterfly
187
         i = j;
188
         do
189
         {
190
            l = i + n2;
191
            a0 = pSrc[2 * i] + pSrc[2 * l];
192
            xt = pSrc[2 * i] - pSrc[2 * l];
193
 
194
            yt = pSrc[2 * i + 1] - pSrc[2 * l + 1];
195
            a1 = pSrc[2 * l + 1] + pSrc[2 * i + 1];
196
 
197
            p0 = xt * cosVal;
198
            p1 = yt * sinVal;
199
            p2 = yt * cosVal;
200
            p3 = xt * sinVal;
201
 
202
            pSrc[2 * i] = a0;
203
            pSrc[2 * i + 1] = a1;
204
 
205
            pSrc[2 * l]     = p0 + p1;
206
            pSrc[2 * l + 1] = p2 - p3;
207
 
208
            i += n1;
209
         } while ( i < fftLen );                        // butterfly loop end
210
         j++;
211
      } while ( j < n2);                          // groups loop end
212
      twidCoefModifier <<= 1U;
213
   }                             // stages loop end
214
 
215
   // loop for butterfly
216
   for (i = 0; i < fftLen; i += 2)
217
   {
218
      a0 = pSrc[2 * i] + pSrc[2 * i + 2];
219
      xt = pSrc[2 * i] - pSrc[2 * i + 2];
220
 
221
      yt = pSrc[2 * i + 1] - pSrc[2 * i + 3];
222
      a1 = pSrc[2 * i + 3] + pSrc[2 * i + 1];
223
 
224
      pSrc[2 * i] = a0;
225
      pSrc[2 * i + 1] = a1;
226
      pSrc[2 * i + 2] = xt;
227
      pSrc[2 * i + 3] = yt;
228
   }                             // groups loop end
229
 
230
#else
231
 
232
   n2 = fftLen;
233
 
234
   // loop for stage
235
   for (k = fftLen; k > 1; k = k >> 1)
236
   {
237
      n1 = n2;
238
      n2 = n2 >> 1;
239
      ia = 0;
240
 
241
      // loop for groups
242
      j = 0;
243
      do
244
      {
245
         cosVal = pCoef[ia * 2];
246
         sinVal = pCoef[(ia * 2) + 1];
247
         ia += twidCoefModifier;
248
 
249
         // loop for butterfly
250
         i = j;
251
         do
252
         {
253
            l = i + n2;
254
            a0 = pSrc[2 * i] + pSrc[2 * l];
255
            xt = pSrc[2 * i] - pSrc[2 * l];
256
 
257
            yt = pSrc[2 * i + 1] - pSrc[2 * l + 1];
258
            a1 = pSrc[2 * l + 1] + pSrc[2 * i + 1];
259
 
260
            p0 = xt * cosVal;
261
            p1 = yt * sinVal;
262
            p2 = yt * cosVal;
263
            p3 = xt * sinVal;
264
 
265
            pSrc[2 * i] = a0;
266
            pSrc[2 * i + 1] = a1;
267
 
268
            pSrc[2 * l]     = p0 + p1;
269
            pSrc[2 * l + 1] = p2 - p3;
270
 
271
            i += n1;
272
         } while (i < fftLen);
273
         j++;
274
      } while (j < n2);
275
      twidCoefModifier <<= 1U;
276
   }
277
 
278
#endif //    #if defined (ARM_MATH_DSP)
279
 
280
}
281
 
282
 
283
void arm_radix2_butterfly_inverse_f32(
284
float32_t * pSrc,
285
uint32_t fftLen,
286
float32_t * pCoef,
287
uint16_t twidCoefModifier,
288
float32_t onebyfftLen)
289
{
290
 
291
   uint32_t i, j, k, l;
292
   uint32_t n1, n2, ia;
293
   float32_t xt, yt, cosVal, sinVal;
294
   float32_t p0, p1, p2, p3;
295
   float32_t a0, a1;
296
 
297
#if defined (ARM_MATH_DSP)
298
 
299
   n2 = fftLen >> 1;
300
   ia = 0;
301
 
302
   // loop for groups
303
   for (i = 0; i < n2; i++)
304
   {
305
      cosVal = pCoef[ia * 2];
306
      sinVal = pCoef[(ia * 2) + 1];
307
      ia += twidCoefModifier;
308
 
309
      l = i + n2;
310
      a0 = pSrc[2 * i] + pSrc[2 * l];
311
      xt = pSrc[2 * i] - pSrc[2 * l];
312
 
313
      yt = pSrc[2 * i + 1] - pSrc[2 * l + 1];
314
      a1 = pSrc[2 * l + 1] + pSrc[2 * i + 1];
315
 
316
      p0 = xt * cosVal;
317
      p1 = yt * sinVal;
318
      p2 = yt * cosVal;
319
      p3 = xt * sinVal;
320
 
321
      pSrc[2 * i] = a0;
322
      pSrc[2 * i + 1] = a1;
323
 
324
      pSrc[2 * l]     = p0 - p1;
325
      pSrc[2 * l + 1] = p2 + p3;
326
   }                             // groups loop end
327
 
328
   twidCoefModifier <<= 1U;
329
 
330
   // loop for stage
331
   for (k = fftLen / 2; k > 2; k = k >> 1)
332
   {
333
      n1 = n2;
334
      n2 = n2 >> 1;
335
      ia = 0;
336
 
337
      // loop for groups
338
      j = 0;
339
      do
340
      {
341
         cosVal = pCoef[ia * 2];
342
         sinVal = pCoef[(ia * 2) + 1];
343
         ia += twidCoefModifier;
344
 
345
         // loop for butterfly
346
         i = j;
347
         do
348
         {
349
            l = i + n2;
350
            a0 = pSrc[2 * i] + pSrc[2 * l];
351
            xt = pSrc[2 * i] - pSrc[2 * l];
352
 
353
            yt = pSrc[2 * i + 1] - pSrc[2 * l + 1];
354
            a1 = pSrc[2 * l + 1] + pSrc[2 * i + 1];
355
 
356
            p0 = xt * cosVal;
357
            p1 = yt * sinVal;
358
            p2 = yt * cosVal;
359
            p3 = xt * sinVal;
360
 
361
            pSrc[2 * i] = a0;
362
            pSrc[2 * i + 1] = a1;
363
 
364
            pSrc[2 * l]     = p0 - p1;
365
            pSrc[2 * l + 1] = p2 + p3;
366
 
367
            i += n1;
368
         } while ( i < fftLen );                 // butterfly loop end
369
         j++;
370
      } while (j < n2);                      // groups loop end
371
 
372
      twidCoefModifier <<= 1U;
373
   }                             // stages loop end
374
 
375
   // loop for butterfly
376
   for (i = 0; i < fftLen; i += 2)
377
   {
378
      a0 = pSrc[2 * i] + pSrc[2 * i + 2];
379
      xt = pSrc[2 * i] - pSrc[2 * i + 2];
380
 
381
      a1 = pSrc[2 * i + 3] + pSrc[2 * i + 1];
382
      yt = pSrc[2 * i + 1] - pSrc[2 * i + 3];
383
 
384
      p0 = a0 * onebyfftLen;
385
      p2 = xt * onebyfftLen;
386
      p1 = a1 * onebyfftLen;
387
      p3 = yt * onebyfftLen;
388
 
389
      pSrc[2 * i] = p0;
390
      pSrc[2 * i + 1] = p1;
391
      pSrc[2 * i + 2] = p2;
392
      pSrc[2 * i + 3] = p3;
393
   }                             // butterfly loop end
394
 
395
#else
396
 
397
   n2 = fftLen;
398
 
399
   // loop for stage
400
   for (k = fftLen; k > 2; k = k >> 1)
401
   {
402
      n1 = n2;
403
      n2 = n2 >> 1;
404
      ia = 0;
405
 
406
      // loop for groups
407
      j = 0;
408
      do
409
      {
410
         cosVal = pCoef[ia * 2];
411
         sinVal = pCoef[(ia * 2) + 1];
412
         ia = ia + twidCoefModifier;
413
 
414
         // loop for butterfly
415
         i = j;
416
         do
417
         {
418
            l = i + n2;
419
            a0 = pSrc[2 * i] + pSrc[2 * l];
420
            xt = pSrc[2 * i] - pSrc[2 * l];
421
 
422
            yt = pSrc[2 * i + 1] - pSrc[2 * l + 1];
423
            a1 = pSrc[2 * l + 1] + pSrc[2 * i + 1];
424
 
425
            p0 = xt * cosVal;
426
            p1 = yt * sinVal;
427
            p2 = yt * cosVal;
428
            p3 = xt * sinVal;
429
 
430
            pSrc[2 * i] = a0;
431
            pSrc[2 * i + 1] = a1;
432
 
433
            pSrc[2 * l]     = p0 - p1;
434
            pSrc[2 * l + 1] = p2 + p3;
435
 
436
            i += n1;
437
         } while ( i < fftLen );                    // butterfly loop end
438
         j++;
439
      } while ( j < n2 );                      // groups loop end
440
 
441
      twidCoefModifier = twidCoefModifier << 1U;
442
   }                             // stages loop end
443
 
444
   n1 = n2;
445
   n2 = n2 >> 1;
446
 
447
   // loop for butterfly
448
   for (i = 0; i < fftLen; i += n1)
449
   {
450
      l = i + n2;
451
 
452
      a0 = pSrc[2 * i] + pSrc[2 * l];
453
      xt = pSrc[2 * i] - pSrc[2 * l];
454
 
455
      a1 = pSrc[2 * l + 1] + pSrc[2 * i + 1];
456
      yt = pSrc[2 * i + 1] - pSrc[2 * l + 1];
457
 
458
      p0 = a0 * onebyfftLen;
459
      p2 = xt * onebyfftLen;
460
      p1 = a1 * onebyfftLen;
461
      p3 = yt * onebyfftLen;
462
 
463
      pSrc[2 * i] = p0;
464
      pSrc[2U * l] = p2;
465
 
466
      pSrc[2 * i + 1] = p1;
467
      pSrc[2U * l + 1U] = p3;
468
   }                             // butterfly loop end
469
 
470
#endif //      #if defined (ARM_MATH_DSP)
471
 
472
}