1 /* ----------------------------------------------------------------------
2 * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
4 * $Date: 17. January 2013
7 * Project: CMSIS DSP Library
8 * Title: arm_cfft_radix4_f32.c
10 * Description: Radix-4 Decimation in Frequency CFFT & CIFFT Floating point processing function
13 * Target Processor: Cortex-M4/Cortex-M3/Cortex-M0
15 * Redistribution and use in source and binary forms, with or without
16 * modification, are permitted provided that the following conditions
18 * - Redistributions of source code must retain the above copyright
19 * notice, this list of conditions and the following disclaimer.
20 * - Redistributions in binary form must reproduce the above copyright
21 * notice, this list of conditions and the following disclaimer in
22 * the documentation and/or other materials provided with the
24 * - Neither the name of ARM LIMITED nor the names of its contributors
25 * may be used to endorse or promote products derived from this
26 * software without specific prior written permission.
28 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
29 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
30 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
31 * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
32 * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
33 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
34 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
35 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
36 * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
37 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
38 * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
39 * POSSIBILITY OF SUCH DAMAGE.
40 * -------------------------------------------------------------------- */
44 extern void arm_bitreversal_f32(
47 uint16_t bitRevFactor,
48 uint16_t * pBitRevTab);
51 * @ingroup groupTransforms
54 /* ----------------------------------------------------------------------
55 ** Internal helper function used by the FFTs
56 ** ------------------------------------------------------------------- */
59 * @brief Core function for the floating-point CFFT butterfly process.
60 * @param[in, out] *pSrc points to the in-place buffer of floating-point data type.
61 * @param[in] fftLen length of the FFT.
62 * @param[in] *pCoef points to the twiddle coefficient buffer.
63 * @param[in] twidCoefModifier twiddle coefficient modifier that supports different size FFTs with the same twiddle factor table.
67 void arm_radix4_butterfly_f32(
71 uint16_t twidCoefModifier)
74 float32_t co1, co2, co3, si1, si2, si3;
75 uint32_t ia1, ia2, ia3;
76 uint32_t i0, i1, i2, i3;
77 uint32_t n1, n2, j, k;
79 #ifndef ARM_MATH_CM0_FAMILY_FAMILY
81 /* Run the below code for Cortex-M4 and Cortex-M3 */
83 float32_t xaIn, yaIn, xbIn, ybIn, xcIn, ycIn, xdIn, ydIn;
84 float32_t Xaplusc, Xbplusd, Yaplusc, Ybplusd, Xaminusc, Xbminusd, Yaminusc,
86 float32_t Xb12C_out, Yb12C_out, Xc12C_out, Yc12C_out, Xd12C_out, Yd12C_out;
87 float32_t Xb12_out, Yb12_out, Xc12_out, Yc12_out, Xd12_out, Yd12_out;
89 float32_t p0,p1,p2,p3,p4,p5;
90 float32_t a0,a1,a2,a3,a4,a5,a6,a7;
92 /* Initializations for the first stage */
103 /* Calculation of first stage */
106 /* index calculation for the input as, */
107 /* pSrc[i0 + 0], pSrc[i0 + fftLen/4], pSrc[i0 + fftLen/2], pSrc[i0 + 3fftLen/4] */
112 xaIn = pSrc[(2u * i0)];
113 yaIn = pSrc[(2u * i0) + 1u];
115 xbIn = pSrc[(2u * i1)];
116 ybIn = pSrc[(2u * i1) + 1u];
118 xcIn = pSrc[(2u * i2)];
119 ycIn = pSrc[(2u * i2) + 1u];
121 xdIn = pSrc[(2u * i3)];
122 ydIn = pSrc[(2u * i3) + 1u];
125 Xaplusc = xaIn + xcIn;
127 Xbplusd = xbIn + xdIn;
129 Yaplusc = yaIn + ycIn;
131 Ybplusd = ybIn + ydIn;
133 /* index calculation for the coefficients */
135 co2 = pCoef[ia2 * 2u];
136 si2 = pCoef[(ia2 * 2u) + 1u];
139 Xaminusc = xaIn - xcIn;
141 Xbminusd = xbIn - xdIn;
143 Yaminusc = yaIn - ycIn;
145 Ybminusd = ybIn - ydIn;
147 /* xa' = xa + xb + xc + xd */
148 pSrc[(2u * i0)] = Xaplusc + Xbplusd;
149 /* ya' = ya + yb + yc + yd */
150 pSrc[(2u * i0) + 1u] = Yaplusc + Ybplusd;
152 /* (xa - xc) + (yb - yd) */
153 Xb12C_out = (Xaminusc + Ybminusd);
154 /* (ya - yc) + (xb - xd) */
155 Yb12C_out = (Yaminusc - Xbminusd);
156 /* (xa + xc) - (xb + xd) */
157 Xc12C_out = (Xaplusc - Xbplusd);
158 /* (ya + yc) - (yb + yd) */
159 Yc12C_out = (Yaplusc - Ybplusd);
160 /* (xa - xc) - (yb - yd) */
161 Xd12C_out = (Xaminusc - Ybminusd);
162 /* (ya - yc) + (xb - xd) */
163 Yd12C_out = (Xbminusd + Yaminusc);
165 co1 = pCoef[ia1 * 2u];
166 si1 = pCoef[(ia1 * 2u) + 1u];
168 /* index calculation for the coefficients */
170 co3 = pCoef[ia3 * 2u];
171 si3 = pCoef[(ia3 * 2u) + 1u];
173 Xb12_out = Xb12C_out * co1;
174 Yb12_out = Yb12C_out * co1;
175 Xc12_out = Xc12C_out * co2;
176 Yc12_out = Yc12C_out * co2;
177 Xd12_out = Xd12C_out * co3;
178 Yd12_out = Yd12C_out * co3;
180 /* xb' = (xa+yb-xc-yd)co1 - (ya-xb-yc+xd)(si1) */
181 //Xb12_out -= Yb12C_out * si1;
182 p0 = Yb12C_out * si1;
183 /* yb' = (ya-xb-yc+xd)co1 + (xa+yb-xc-yd)(si1) */
184 //Yb12_out += Xb12C_out * si1;
185 p1 = Xb12C_out * si1;
186 /* xc' = (xa-xb+xc-xd)co2 - (ya-yb+yc-yd)(si2) */
187 //Xc12_out -= Yc12C_out * si2;
188 p2 = Yc12C_out * si2;
189 /* yc' = (ya-yb+yc-yd)co2 + (xa-xb+xc-xd)(si2) */
190 //Yc12_out += Xc12C_out * si2;
191 p3 = Xc12C_out * si2;
192 /* xd' = (xa-yb-xc+yd)co3 - (ya+xb-yc-xd)(si3) */
193 //Xd12_out -= Yd12C_out * si3;
194 p4 = Yd12C_out * si3;
195 /* yd' = (ya+xb-yc-xd)co3 + (xa-yb-xc+yd)(si3) */
196 //Yd12_out += Xd12C_out * si3;
197 p5 = Xd12C_out * si3;
206 /* xc' = (xa-xb+xc-xd)co2 + (ya-yb+yc-yd)(si2) */
207 pSrc[2u * i1] = Xc12_out;
209 /* yc' = (ya-yb+yc-yd)co2 - (xa-xb+xc-xd)(si2) */
210 pSrc[(2u * i1) + 1u] = Yc12_out;
212 /* xb' = (xa+yb-xc-yd)co1 + (ya-xb-yc+xd)(si1) */
213 pSrc[2u * i2] = Xb12_out;
215 /* yb' = (ya-xb-yc+xd)co1 - (xa+yb-xc-yd)(si1) */
216 pSrc[(2u * i2) + 1u] = Yb12_out;
218 /* xd' = (xa-yb-xc+yd)co3 + (ya+xb-yc-xd)(si3) */
219 pSrc[2u * i3] = Xd12_out;
221 /* yd' = (ya+xb-yc-xd)co3 - (xa-yb-xc+yd)(si3) */
222 pSrc[(2u * i3) + 1u] = Yd12_out;
224 /* Twiddle coefficients index modifier */
225 ia1 += twidCoefModifier;
227 /* Updating input index */
233 twidCoefModifier <<= 2u;
235 /* Calculation of second stage to excluding last stage */
236 for (k = fftLen >> 2u; k > 4u; k >>= 2u)
238 /* Initializations for the first stage */
243 /* Calculation of first stage */
247 /* index calculation for the coefficients */
250 co1 = pCoef[ia1 * 2u];
251 si1 = pCoef[(ia1 * 2u) + 1u];
252 co2 = pCoef[ia2 * 2u];
253 si2 = pCoef[(ia2 * 2u) + 1u];
254 co3 = pCoef[ia3 * 2u];
255 si3 = pCoef[(ia3 * 2u) + 1u];
257 /* Twiddle coefficients index modifier */
258 ia1 += twidCoefModifier;
263 /* index calculation for the input as, */
264 /* pSrc[i0 + 0], pSrc[i0 + fftLen/4], pSrc[i0 + fftLen/2], pSrc[i0 + 3fftLen/4] */
269 xaIn = pSrc[(2u * i0)];
270 yaIn = pSrc[(2u * i0) + 1u];
272 xbIn = pSrc[(2u * i1)];
273 ybIn = pSrc[(2u * i1) + 1u];
275 xcIn = pSrc[(2u * i2)];
276 ycIn = pSrc[(2u * i2) + 1u];
278 xdIn = pSrc[(2u * i3)];
279 ydIn = pSrc[(2u * i3) + 1u];
282 Xaminusc = xaIn - xcIn;
284 Xbminusd = xbIn - xdIn;
286 Yaminusc = yaIn - ycIn;
288 Ybminusd = ybIn - ydIn;
291 Xaplusc = xaIn + xcIn;
293 Xbplusd = xbIn + xdIn;
295 Yaplusc = yaIn + ycIn;
297 Ybplusd = ybIn + ydIn;
299 /* (xa - xc) + (yb - yd) */
300 Xb12C_out = (Xaminusc + Ybminusd);
301 /* (ya - yc) - (xb - xd) */
302 Yb12C_out = (Yaminusc - Xbminusd);
303 /* xa + xc -(xb + xd) */
304 Xc12C_out = (Xaplusc - Xbplusd);
305 /* (ya + yc) - (yb + yd) */
306 Yc12C_out = (Yaplusc - Ybplusd);
307 /* (xa - xc) - (yb - yd) */
308 Xd12C_out = (Xaminusc - Ybminusd);
309 /* (ya - yc) + (xb - xd) */
310 Yd12C_out = (Xbminusd + Yaminusc);
312 pSrc[(2u * i0)] = Xaplusc + Xbplusd;
313 pSrc[(2u * i0) + 1u] = Yaplusc + Ybplusd;
315 Xb12_out = Xb12C_out * co1;
316 Yb12_out = Yb12C_out * co1;
317 Xc12_out = Xc12C_out * co2;
318 Yc12_out = Yc12C_out * co2;
319 Xd12_out = Xd12C_out * co3;
320 Yd12_out = Yd12C_out * co3;
322 /* xb' = (xa+yb-xc-yd)co1 - (ya-xb-yc+xd)(si1) */
323 //Xb12_out -= Yb12C_out * si1;
324 p0 = Yb12C_out * si1;
325 /* yb' = (ya-xb-yc+xd)co1 + (xa+yb-xc-yd)(si1) */
326 //Yb12_out += Xb12C_out * si1;
327 p1 = Xb12C_out * si1;
328 /* xc' = (xa-xb+xc-xd)co2 - (ya-yb+yc-yd)(si2) */
329 //Xc12_out -= Yc12C_out * si2;
330 p2 = Yc12C_out * si2;
331 /* yc' = (ya-yb+yc-yd)co2 + (xa-xb+xc-xd)(si2) */
332 //Yc12_out += Xc12C_out * si2;
333 p3 = Xc12C_out * si2;
334 /* xd' = (xa-yb-xc+yd)co3 - (ya+xb-yc-xd)(si3) */
335 //Xd12_out -= Yd12C_out * si3;
336 p4 = Yd12C_out * si3;
337 /* yd' = (ya+xb-yc-xd)co3 + (xa-yb-xc+yd)(si3) */
338 //Yd12_out += Xd12C_out * si3;
339 p5 = Xd12C_out * si3;
348 /* xc' = (xa-xb+xc-xd)co2 + (ya-yb+yc-yd)(si2) */
349 pSrc[2u * i1] = Xc12_out;
351 /* yc' = (ya-yb+yc-yd)co2 - (xa-xb+xc-xd)(si2) */
352 pSrc[(2u * i1) + 1u] = Yc12_out;
354 /* xb' = (xa+yb-xc-yd)co1 + (ya-xb-yc+xd)(si1) */
355 pSrc[2u * i2] = Xb12_out;
357 /* yb' = (ya-xb-yc+xd)co1 - (xa+yb-xc-yd)(si1) */
358 pSrc[(2u * i2) + 1u] = Yb12_out;
360 /* xd' = (xa-yb-xc+yd)co3 + (ya+xb-yc-xd)(si3) */
361 pSrc[2u * i3] = Xd12_out;
363 /* yd' = (ya+xb-yc-xd)co3 - (xa-yb-xc+yd)(si3) */
364 pSrc[(2u * i3) + 1u] = Yd12_out;
367 } while(i0 < fftLen);
369 } while(j <= (n2 - 1u));
370 twidCoefModifier <<= 2u;
376 /* Calculations of last stage */
389 Xaplusc = xaIn + xcIn;
392 Xaminusc = xaIn - xcIn;
395 Yaplusc = yaIn + ycIn;
398 Yaminusc = yaIn - ycIn;
401 Xbplusd = xbIn + xdIn;
404 Ybplusd = ybIn + ydIn;
407 Xbminusd = xbIn - xdIn;
410 Ybminusd = ybIn - ydIn;
412 /* xa' = xa + xb + xc + xd */
413 a0 = (Xaplusc + Xbplusd);
414 /* ya' = ya + yb + yc + yd */
415 a1 = (Yaplusc + Ybplusd);
416 /* xc' = (xa-xb+xc-xd) */
417 a2 = (Xaplusc - Xbplusd);
418 /* yc' = (ya-yb+yc-yd) */
419 a3 = (Yaplusc - Ybplusd);
420 /* xb' = (xa+yb-xc-yd) */
421 a4 = (Xaminusc + Ybminusd);
422 /* yb' = (ya-xb-yc+xd) */
423 a5 = (Yaminusc - Xbminusd);
424 /* xd' = (xa-yb-xc+yd)) */
425 a6 = (Xaminusc - Ybminusd);
426 /* yd' = (ya+xb-yc-xd) */
427 a7 = (Xbminusd + Yaminusc);
438 /* increment pointer by 8 */
444 float32_t t1, t2, r1, r2, s1, s2;
446 /* Run the below code for Cortex-M0 */
448 /* Initializations for the fft calculation */
451 for (k = fftLen; k > 1u; k >>= 2u)
453 /* Initializations for the fft calculation */
458 /* FFT Calculation */
462 /* index calculation for the coefficients */
465 co1 = pCoef[ia1 * 2u];
466 si1 = pCoef[(ia1 * 2u) + 1u];
467 co2 = pCoef[ia2 * 2u];
468 si2 = pCoef[(ia2 * 2u) + 1u];
469 co3 = pCoef[ia3 * 2u];
470 si3 = pCoef[(ia3 * 2u) + 1u];
472 /* Twiddle coefficients index modifier */
473 ia1 = ia1 + twidCoefModifier;
478 /* index calculation for the input as, */
479 /* pSrc[i0 + 0], pSrc[i0 + fftLen/4], pSrc[i0 + fftLen/2], pSrc[i0 + 3fftLen/4] */
485 r1 = pSrc[(2u * i0)] + pSrc[(2u * i2)];
488 r2 = pSrc[(2u * i0)] - pSrc[(2u * i2)];
491 s1 = pSrc[(2u * i0) + 1u] + pSrc[(2u * i2) + 1u];
494 s2 = pSrc[(2u * i0) + 1u] - pSrc[(2u * i2) + 1u];
497 t1 = pSrc[2u * i1] + pSrc[2u * i3];
499 /* xa' = xa + xb + xc + xd */
500 pSrc[2u * i0] = r1 + t1;
502 /* xa + xc -(xb + xd) */
506 t2 = pSrc[(2u * i1) + 1u] + pSrc[(2u * i3) + 1u];
508 /* ya' = ya + yb + yc + yd */
509 pSrc[(2u * i0) + 1u] = s1 + t2;
511 /* (ya + yc) - (yb + yd) */
515 t1 = pSrc[(2u * i1) + 1u] - pSrc[(2u * i3) + 1u];
518 t2 = pSrc[2u * i1] - pSrc[2u * i3];
520 /* xc' = (xa-xb+xc-xd)co2 + (ya-yb+yc-yd)(si2) */
521 pSrc[2u * i1] = (r1 * co2) + (s1 * si2);
523 /* yc' = (ya-yb+yc-yd)co2 - (xa-xb+xc-xd)(si2) */
524 pSrc[(2u * i1) + 1u] = (s1 * co2) - (r1 * si2);
526 /* (xa - xc) + (yb - yd) */
529 /* (xa - xc) - (yb - yd) */
532 /* (ya - yc) - (xb - xd) */
535 /* (ya - yc) + (xb - xd) */
538 /* xb' = (xa+yb-xc-yd)co1 + (ya-xb-yc+xd)(si1) */
539 pSrc[2u * i2] = (r1 * co1) + (s1 * si1);
541 /* yb' = (ya-xb-yc+xd)co1 - (xa+yb-xc-yd)(si1) */
542 pSrc[(2u * i2) + 1u] = (s1 * co1) - (r1 * si1);
544 /* xd' = (xa-yb-xc+yd)co3 + (ya+xb-yc-xd)(si3) */
545 pSrc[2u * i3] = (r2 * co3) + (s2 * si3);
547 /* yd' = (ya+xb-yc-xd)co3 - (xa-yb-xc+yd)(si3) */
548 pSrc[(2u * i3) + 1u] = (s2 * co3) - (r2 * si3);
551 } while( i0 < fftLen);
553 } while(j <= (n2 - 1u));
554 twidCoefModifier <<= 2u;
557 #endif /* #ifndef ARM_MATH_CM0_FAMILY_FAMILY */
562 * @brief Core function for the floating-point CIFFT butterfly process.
563 * @param[in, out] *pSrc points to the in-place buffer of floating-point data type.
564 * @param[in] fftLen length of the FFT.
565 * @param[in] *pCoef points to twiddle coefficient buffer.
566 * @param[in] twidCoefModifier twiddle coefficient modifier that supports different size FFTs with the same twiddle factor table.
567 * @param[in] onebyfftLen value of 1/fftLen.
571 void arm_radix4_butterfly_inverse_f32(
575 uint16_t twidCoefModifier,
576 float32_t onebyfftLen)
578 float32_t co1, co2, co3, si1, si2, si3;
579 uint32_t ia1, ia2, ia3;
580 uint32_t i0, i1, i2, i3;
581 uint32_t n1, n2, j, k;
583 #ifndef ARM_MATH_CM0_FAMILY_FAMILY
585 float32_t xaIn, yaIn, xbIn, ybIn, xcIn, ycIn, xdIn, ydIn;
586 float32_t Xaplusc, Xbplusd, Yaplusc, Ybplusd, Xaminusc, Xbminusd, Yaminusc,
588 float32_t Xb12C_out, Yb12C_out, Xc12C_out, Yc12C_out, Xd12C_out, Yd12C_out;
589 float32_t Xb12_out, Yb12_out, Xc12_out, Yc12_out, Xd12_out, Yd12_out;
591 float32_t p0,p1,p2,p3,p4,p5,p6,p7;
592 float32_t a0,a1,a2,a3,a4,a5,a6,a7;
595 /* Initializations for the first stage */
606 /* Calculation of first stage */
609 /* index calculation for the input as, */
610 /* pSrc[i0 + 0], pSrc[i0 + fftLen/4], pSrc[i0 + fftLen/2], pSrc[i0 + 3fftLen/4] */
615 /* Butterfly implementation */
616 xaIn = pSrc[(2u * i0)];
617 yaIn = pSrc[(2u * i0) + 1u];
619 xcIn = pSrc[(2u * i2)];
620 ycIn = pSrc[(2u * i2) + 1u];
622 xbIn = pSrc[(2u * i1)];
623 ybIn = pSrc[(2u * i1) + 1u];
625 xdIn = pSrc[(2u * i3)];
626 ydIn = pSrc[(2u * i3) + 1u];
629 Xaplusc = xaIn + xcIn;
631 Xbplusd = xbIn + xdIn;
633 Yaplusc = yaIn + ycIn;
635 Ybplusd = ybIn + ydIn;
637 /* index calculation for the coefficients */
639 co2 = pCoef[ia2 * 2u];
640 si2 = pCoef[(ia2 * 2u) + 1u];
643 Xaminusc = xaIn - xcIn;
645 Xbminusd = xbIn - xdIn;
647 Yaminusc = yaIn - ycIn;
649 Ybminusd = ybIn - ydIn;
651 /* xa' = xa + xb + xc + xd */
652 pSrc[(2u * i0)] = Xaplusc + Xbplusd;
654 /* ya' = ya + yb + yc + yd */
655 pSrc[(2u * i0) + 1u] = Yaplusc + Ybplusd;
657 /* (xa - xc) - (yb - yd) */
658 Xb12C_out = (Xaminusc - Ybminusd);
659 /* (ya - yc) + (xb - xd) */
660 Yb12C_out = (Yaminusc + Xbminusd);
661 /* (xa + xc) - (xb + xd) */
662 Xc12C_out = (Xaplusc - Xbplusd);
663 /* (ya + yc) - (yb + yd) */
664 Yc12C_out = (Yaplusc - Ybplusd);
665 /* (xa - xc) + (yb - yd) */
666 Xd12C_out = (Xaminusc + Ybminusd);
667 /* (ya - yc) - (xb - xd) */
668 Yd12C_out = (Yaminusc - Xbminusd);
670 co1 = pCoef[ia1 * 2u];
671 si1 = pCoef[(ia1 * 2u) + 1u];
673 /* index calculation for the coefficients */
675 co3 = pCoef[ia3 * 2u];
676 si3 = pCoef[(ia3 * 2u) + 1u];
678 Xb12_out = Xb12C_out * co1;
679 Yb12_out = Yb12C_out * co1;
680 Xc12_out = Xc12C_out * co2;
681 Yc12_out = Yc12C_out * co2;
682 Xd12_out = Xd12C_out * co3;
683 Yd12_out = Yd12C_out * co3;
685 /* xb' = (xa+yb-xc-yd)co1 - (ya-xb-yc+xd)(si1) */
686 //Xb12_out -= Yb12C_out * si1;
687 p0 = Yb12C_out * si1;
688 /* yb' = (ya-xb-yc+xd)co1 + (xa+yb-xc-yd)(si1) */
689 //Yb12_out += Xb12C_out * si1;
690 p1 = Xb12C_out * si1;
691 /* xc' = (xa-xb+xc-xd)co2 - (ya-yb+yc-yd)(si2) */
692 //Xc12_out -= Yc12C_out * si2;
693 p2 = Yc12C_out * si2;
694 /* yc' = (ya-yb+yc-yd)co2 + (xa-xb+xc-xd)(si2) */
695 //Yc12_out += Xc12C_out * si2;
696 p3 = Xc12C_out * si2;
697 /* xd' = (xa-yb-xc+yd)co3 - (ya+xb-yc-xd)(si3) */
698 //Xd12_out -= Yd12C_out * si3;
699 p4 = Yd12C_out * si3;
700 /* yd' = (ya+xb-yc-xd)co3 + (xa-yb-xc+yd)(si3) */
701 //Yd12_out += Xd12C_out * si3;
702 p5 = Xd12C_out * si3;
711 /* xc' = (xa-xb+xc-xd)co2 - (ya-yb+yc-yd)(si2) */
712 pSrc[2u * i1] = Xc12_out;
714 /* yc' = (ya-yb+yc-yd)co2 + (xa-xb+xc-xd)(si2) */
715 pSrc[(2u * i1) + 1u] = Yc12_out;
717 /* xb' = (xa+yb-xc-yd)co1 - (ya-xb-yc+xd)(si1) */
718 pSrc[2u * i2] = Xb12_out;
720 /* yb' = (ya-xb-yc+xd)co1 + (xa+yb-xc-yd)(si1) */
721 pSrc[(2u * i2) + 1u] = Yb12_out;
723 /* xd' = (xa-yb-xc+yd)co3 - (ya+xb-yc-xd)(si3) */
724 pSrc[2u * i3] = Xd12_out;
726 /* yd' = (ya+xb-yc-xd)co3 + (xa-yb-xc+yd)(si3) */
727 pSrc[(2u * i3) + 1u] = Yd12_out;
729 /* Twiddle coefficients index modifier */
730 ia1 = ia1 + twidCoefModifier;
732 /* Updating input index */
737 twidCoefModifier <<= 2u;
739 /* Calculation of second stage to excluding last stage */
740 for (k = fftLen >> 2u; k > 4u; k >>= 2u)
742 /* Initializations for the first stage */
747 /* Calculation of first stage */
751 /* index calculation for the coefficients */
754 co1 = pCoef[ia1 * 2u];
755 si1 = pCoef[(ia1 * 2u) + 1u];
756 co2 = pCoef[ia2 * 2u];
757 si2 = pCoef[(ia2 * 2u) + 1u];
758 co3 = pCoef[ia3 * 2u];
759 si3 = pCoef[(ia3 * 2u) + 1u];
761 /* Twiddle coefficients index modifier */
762 ia1 = ia1 + twidCoefModifier;
767 /* index calculation for the input as, */
768 /* pSrc[i0 + 0], pSrc[i0 + fftLen/4], pSrc[i0 + fftLen/2], pSrc[i0 + 3fftLen/4] */
773 xaIn = pSrc[(2u * i0)];
774 yaIn = pSrc[(2u * i0) + 1u];
776 xbIn = pSrc[(2u * i1)];
777 ybIn = pSrc[(2u * i1) + 1u];
779 xcIn = pSrc[(2u * i2)];
780 ycIn = pSrc[(2u * i2) + 1u];
782 xdIn = pSrc[(2u * i3)];
783 ydIn = pSrc[(2u * i3) + 1u];
786 Xaminusc = xaIn - xcIn;
788 Xbminusd = xbIn - xdIn;
790 Yaminusc = yaIn - ycIn;
792 Ybminusd = ybIn - ydIn;
795 Xaplusc = xaIn + xcIn;
797 Xbplusd = xbIn + xdIn;
799 Yaplusc = yaIn + ycIn;
801 Ybplusd = ybIn + ydIn;
803 /* (xa - xc) - (yb - yd) */
804 Xb12C_out = (Xaminusc - Ybminusd);
805 /* (ya - yc) + (xb - xd) */
806 Yb12C_out = (Yaminusc + Xbminusd);
807 /* xa + xc -(xb + xd) */
808 Xc12C_out = (Xaplusc - Xbplusd);
809 /* (ya + yc) - (yb + yd) */
810 Yc12C_out = (Yaplusc - Ybplusd);
811 /* (xa - xc) + (yb - yd) */
812 Xd12C_out = (Xaminusc + Ybminusd);
813 /* (ya - yc) - (xb - xd) */
814 Yd12C_out = (Yaminusc - Xbminusd);
816 pSrc[(2u * i0)] = Xaplusc + Xbplusd;
817 pSrc[(2u * i0) + 1u] = Yaplusc + Ybplusd;
819 Xb12_out = Xb12C_out * co1;
820 Yb12_out = Yb12C_out * co1;
821 Xc12_out = Xc12C_out * co2;
822 Yc12_out = Yc12C_out * co2;
823 Xd12_out = Xd12C_out * co3;
824 Yd12_out = Yd12C_out * co3;
826 /* xb' = (xa+yb-xc-yd)co1 - (ya-xb-yc+xd)(si1) */
827 //Xb12_out -= Yb12C_out * si1;
828 p0 = Yb12C_out * si1;
829 /* yb' = (ya-xb-yc+xd)co1 + (xa+yb-xc-yd)(si1) */
830 //Yb12_out += Xb12C_out * si1;
831 p1 = Xb12C_out * si1;
832 /* xc' = (xa-xb+xc-xd)co2 - (ya-yb+yc-yd)(si2) */
833 //Xc12_out -= Yc12C_out * si2;
834 p2 = Yc12C_out * si2;
835 /* yc' = (ya-yb+yc-yd)co2 + (xa-xb+xc-xd)(si2) */
836 //Yc12_out += Xc12C_out * si2;
837 p3 = Xc12C_out * si2;
838 /* xd' = (xa-yb-xc+yd)co3 - (ya+xb-yc-xd)(si3) */
839 //Xd12_out -= Yd12C_out * si3;
840 p4 = Yd12C_out * si3;
841 /* yd' = (ya+xb-yc-xd)co3 + (xa-yb-xc+yd)(si3) */
842 //Yd12_out += Xd12C_out * si3;
843 p5 = Xd12C_out * si3;
852 /* xc' = (xa-xb+xc-xd)co2 - (ya-yb+yc-yd)(si2) */
853 pSrc[2u * i1] = Xc12_out;
855 /* yc' = (ya-yb+yc-yd)co2 + (xa-xb+xc-xd)(si2) */
856 pSrc[(2u * i1) + 1u] = Yc12_out;
858 /* xb' = (xa+yb-xc-yd)co1 - (ya-xb-yc+xd)(si1) */
859 pSrc[2u * i2] = Xb12_out;
861 /* yb' = (ya-xb-yc+xd)co1 + (xa+yb-xc-yd)(si1) */
862 pSrc[(2u * i2) + 1u] = Yb12_out;
864 /* xd' = (xa-yb-xc+yd)co3 - (ya+xb-yc-xd)(si3) */
865 pSrc[2u * i3] = Xd12_out;
867 /* yd' = (ya+xb-yc-xd)co3 + (xa-yb-xc+yd)(si3) */
868 pSrc[(2u * i3) + 1u] = Yd12_out;
871 } while(i0 < fftLen);
873 } while(j <= (n2 - 1u));
874 twidCoefModifier <<= 2u;
876 /* Initializations of last stage */
881 /* Calculations of last stage */
893 /* Butterfly implementation */
895 Xaplusc = xaIn + xcIn;
898 Xaminusc = xaIn - xcIn;
901 Yaplusc = yaIn + ycIn;
904 Yaminusc = yaIn - ycIn;
907 Xbplusd = xbIn + xdIn;
910 Ybplusd = ybIn + ydIn;
913 Xbminusd = xbIn - xdIn;
916 Ybminusd = ybIn - ydIn;
918 /* xa' = (xa+xb+xc+xd) * onebyfftLen */
919 a0 = (Xaplusc + Xbplusd);
920 /* ya' = (ya+yb+yc+yd) * onebyfftLen */
921 a1 = (Yaplusc + Ybplusd);
922 /* xc' = (xa-xb+xc-xd) * onebyfftLen */
923 a2 = (Xaplusc - Xbplusd);
924 /* yc' = (ya-yb+yc-yd) * onebyfftLen */
925 a3 = (Yaplusc - Ybplusd);
926 /* xb' = (xa-yb-xc+yd) * onebyfftLen */
927 a4 = (Xaminusc - Ybminusd);
928 /* yb' = (ya+xb-yc-xd) * onebyfftLen */
929 a5 = (Yaminusc + Xbminusd);
930 /* xd' = (xa-yb-xc+yd) * onebyfftLen */
931 a6 = (Xaminusc + Ybminusd);
932 /* yd' = (ya-xb-yc+xd) * onebyfftLen */
933 a7 = (Yaminusc - Xbminusd);
935 p0 = a0 * onebyfftLen;
936 p1 = a1 * onebyfftLen;
937 p2 = a2 * onebyfftLen;
938 p3 = a3 * onebyfftLen;
939 p4 = a4 * onebyfftLen;
940 p5 = a5 * onebyfftLen;
941 p6 = a6 * onebyfftLen;
942 p7 = a7 * onebyfftLen;
944 /* xa' = (xa+xb+xc+xd) * onebyfftLen */
946 /* ya' = (ya+yb+yc+yd) * onebyfftLen */
948 /* xc' = (xa-xb+xc-xd) * onebyfftLen */
950 /* yc' = (ya-yb+yc-yd) * onebyfftLen */
952 /* xb' = (xa-yb-xc+yd) * onebyfftLen */
954 /* yb' = (ya+xb-yc-xd) * onebyfftLen */
956 /* xd' = (xa-yb-xc+yd) * onebyfftLen */
958 /* yd' = (ya-xb-yc+xd) * onebyfftLen */
961 /* increment source pointer by 8 for next calculations */
968 float32_t t1, t2, r1, r2, s1, s2;
970 /* Run the below code for Cortex-M0 */
972 /* Initializations for the first stage */
976 /* Calculation of first stage */
977 for (k = fftLen; k > 4u; k >>= 2u)
979 /* Initializations for the first stage */
984 /* Calculation of first stage */
988 /* index calculation for the coefficients */
991 co1 = pCoef[ia1 * 2u];
992 si1 = pCoef[(ia1 * 2u) + 1u];
993 co2 = pCoef[ia2 * 2u];
994 si2 = pCoef[(ia2 * 2u) + 1u];
995 co3 = pCoef[ia3 * 2u];
996 si3 = pCoef[(ia3 * 2u) + 1u];
998 /* Twiddle coefficients index modifier */
999 ia1 = ia1 + twidCoefModifier;
1004 /* index calculation for the input as, */
1005 /* pSrc[i0 + 0], pSrc[i0 + fftLen/4], pSrc[i0 + fftLen/2], pSrc[i0 + 3fftLen/4] */
1011 r1 = pSrc[(2u * i0)] + pSrc[(2u * i2)];
1014 r2 = pSrc[(2u * i0)] - pSrc[(2u * i2)];
1017 s1 = pSrc[(2u * i0) + 1u] + pSrc[(2u * i2) + 1u];
1020 s2 = pSrc[(2u * i0) + 1u] - pSrc[(2u * i2) + 1u];
1023 t1 = pSrc[2u * i1] + pSrc[2u * i3];
1025 /* xa' = xa + xb + xc + xd */
1026 pSrc[2u * i0] = r1 + t1;
1028 /* xa + xc -(xb + xd) */
1032 t2 = pSrc[(2u * i1) + 1u] + pSrc[(2u * i3) + 1u];
1034 /* ya' = ya + yb + yc + yd */
1035 pSrc[(2u * i0) + 1u] = s1 + t2;
1037 /* (ya + yc) - (yb + yd) */
1041 t1 = pSrc[(2u * i1) + 1u] - pSrc[(2u * i3) + 1u];
1044 t2 = pSrc[2u * i1] - pSrc[2u * i3];
1046 /* xc' = (xa-xb+xc-xd)co2 - (ya-yb+yc-yd)(si2) */
1047 pSrc[2u * i1] = (r1 * co2) - (s1 * si2);
1049 /* yc' = (ya-yb+yc-yd)co2 + (xa-xb+xc-xd)(si2) */
1050 pSrc[(2u * i1) + 1u] = (s1 * co2) + (r1 * si2);
1052 /* (xa - xc) - (yb - yd) */
1055 /* (xa - xc) + (yb - yd) */
1058 /* (ya - yc) + (xb - xd) */
1061 /* (ya - yc) - (xb - xd) */
1064 /* xb' = (xa+yb-xc-yd)co1 - (ya-xb-yc+xd)(si1) */
1065 pSrc[2u * i2] = (r1 * co1) - (s1 * si1);
1067 /* yb' = (ya-xb-yc+xd)co1 + (xa+yb-xc-yd)(si1) */
1068 pSrc[(2u * i2) + 1u] = (s1 * co1) + (r1 * si1);
1070 /* xd' = (xa-yb-xc+yd)co3 - (ya+xb-yc-xd)(si3) */
1071 pSrc[2u * i3] = (r2 * co3) - (s2 * si3);
1073 /* yd' = (ya+xb-yc-xd)co3 + (xa-yb-xc+yd)(si3) */
1074 pSrc[(2u * i3) + 1u] = (s2 * co3) + (r2 * si3);
1077 } while( i0 < fftLen);
1079 } while(j <= (n2 - 1u));
1080 twidCoefModifier <<= 2u;
1082 /* Initializations of last stage */
1086 /* Calculations of last stage */
1087 for (i0 = 0u; i0 <= (fftLen - n1); i0 += n1)
1089 /* index calculation for the input as, */
1090 /* pSrc[i0 + 0], pSrc[i0 + fftLen/4], pSrc[i0 + fftLen/2], pSrc[i0 + 3fftLen/4] */
1095 /* Butterfly implementation */
1097 r1 = pSrc[2u * i0] + pSrc[2u * i2];
1100 r2 = pSrc[2u * i0] - pSrc[2u * i2];
1103 s1 = pSrc[(2u * i0) + 1u] + pSrc[(2u * i2) + 1u];
1106 s2 = pSrc[(2u * i0) + 1u] - pSrc[(2u * i2) + 1u];
1109 t1 = pSrc[2u * i1] + pSrc[2u * i3];
1111 /* xa' = xa + xb + xc + xd */
1112 pSrc[2u * i0] = (r1 + t1) * onebyfftLen;
1114 /* (xa + xb) - (xc + xd) */
1118 t2 = pSrc[(2u * i1) + 1u] + pSrc[(2u * i3) + 1u];
1120 /* ya' = ya + yb + yc + yd */
1121 pSrc[(2u * i0) + 1u] = (s1 + t2) * onebyfftLen;
1123 /* (ya + yc) - (yb + yd) */
1127 t1 = pSrc[(2u * i1) + 1u] - pSrc[(2u * i3) + 1u];
1130 t2 = pSrc[2u * i1] - pSrc[2u * i3];
1132 /* xc' = (xa-xb+xc-xd)co2 - (ya-yb+yc-yd)(si2) */
1133 pSrc[2u * i1] = r1 * onebyfftLen;
1135 /* yc' = (ya-yb+yc-yd)co2 + (xa-xb+xc-xd)(si2) */
1136 pSrc[(2u * i1) + 1u] = s1 * onebyfftLen;
1138 /* (xa - xc) - (yb-yd) */
1141 /* (xa - xc) + (yb-yd) */
1144 /* (ya - yc) + (xb-xd) */
1147 /* (ya - yc) - (xb-xd) */
1150 /* xb' = (xa+yb-xc-yd)co1 - (ya-xb-yc+xd)(si1) */
1151 pSrc[2u * i2] = r1 * onebyfftLen;
1153 /* yb' = (ya-xb-yc+xd)co1 + (xa+yb-xc-yd)(si1) */
1154 pSrc[(2u * i2) + 1u] = s1 * onebyfftLen;
1156 /* xd' = (xa-yb-xc+yd)co3 - (ya+xb-yc-xd)(si3) */
1157 pSrc[2u * i3] = r2 * onebyfftLen;
1159 /* yd' = (ya+xb-yc-xd)co3 + (xa-yb-xc+yd)(si3) */
1160 pSrc[(2u * i3) + 1u] = s2 * onebyfftLen;
1163 #endif /* #ifndef ARM_MATH_CM0_FAMILY_FAMILY */
1167 * @addtogroup ComplexFFT
1173 * @brief Processing function for the floating-point Radix-4 CFFT/CIFFT.
1174 * @deprecated Do not use this function. It has been superceded by \ref arm_cfft_f32 and will be removed
1176 * @param[in] *S points to an instance of the floating-point Radix-4 CFFT/CIFFT structure.
1177 * @param[in, out] *pSrc points to the complex data buffer of size <code>2*fftLen</code>. Processing occurs in-place.
1181 void arm_cfft_radix4_f32(
1182 const arm_cfft_radix4_instance_f32 * S,
1186 if(S->ifftFlag == 1u)
1188 /* Complex IFFT radix-4 */
1189 arm_radix4_butterfly_inverse_f32(pSrc, S->fftLen, S->pTwiddle,
1190 S->twidCoefModifier, S->onebyfftLen);
1194 /* Complex FFT radix-4 */
1195 arm_radix4_butterfly_f32(pSrc, S->fftLen, S->pTwiddle,
1196 S->twidCoefModifier);
1199 if(S->bitReverseFlag == 1u)
1202 arm_bitreversal_f32(pSrc, S->fftLen, S->bitRevFactor, S->pBitRevTable);
1208 * @} end of ComplexFFT group