]> Gitweb @ Texas Instruments - Open Source Git Repositories - git.TI.com/gitweb - ep-processor-libraries/dsplib.git/blob - ti/dsplib/src/DSPF_sp_fftSPxSP/c674/DSPF_sp_fftSPxSP_d.c
DSPLIB: optimized signal processing functions for TI DSPs
[ep-processor-libraries/dsplib.git] / ti / dsplib / src / DSPF_sp_fftSPxSP / c674 / DSPF_sp_fftSPxSP_d.c
1 /* ======================================================================== */
2 /* DSPF_sp_fftSPxSP_d.c -- Complex Forward FFT with Mixed Radix             */
3 /*                Driver code; tests kernel and reports result in stdout    */
4 /*                                                                          */
5 /* Rev 0.0.3                                                                */
6 /*                                                                          */
7 /* Copyright (C) 2011 Texas Instruments Incorporated - http://www.ti.com/   */ 
8 /*                                                                          */
9 /*                                                                          */
10 /*  Redistribution and use in source and binary forms, with or without      */
11 /*  modification, are permitted provided that the following conditions      */
12 /*  are met:                                                                */
13 /*                                                                          */
14 /*    Redistributions of source code must retain the above copyright        */
15 /*    notice, this list of conditions and the following disclaimer.         */
16 /*                                                                          */
17 /*    Redistributions in binary form must reproduce the above copyright     */
18 /*    notice, this list of conditions and the following disclaimer in the   */
19 /*    documentation and/or other materials provided with the                */
20 /*    distribution.                                                         */
21 /*                                                                          */
22 /*    Neither the name of Texas Instruments Incorporated nor the names of   */
23 /*    its contributors may be used to endorse or promote products derived   */
24 /*    from this software without specific prior written permission.         */
25 /*                                                                          */
26 /*  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS     */
27 /*  "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT       */
28 /*  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR   */
29 /*  A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT    */
30 /*  OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,   */
31 /*  SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT        */
32 /*  LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,   */
33 /*  DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY   */
34 /*  THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT     */
35 /*  (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE   */
36 /*  OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.    */
37 /*                                                                          */
38 /* ======================================================================== */
40 #include <stdio.h>
41 #include <time.h>
42 #include <stdlib.h>
43 #include <limits.h>
44 #include <math.h>
45 #include <c6x.h>
47 #include "DSPF_sp_fftSPxSP.h"
48 #include "DSPF_sp_fftSPxSP_cn.h"
50 /* Defines */
51 #if defined(__TI_EABI__)
52 #define kernel_size _kernel_size
53 #endif
55 extern char kernel_size;
56 #define CYCLE_FORMULA_NX_PT1  128
57 #define CYCLE_FORMULA_NX_PT2  256
58 #define FORMULA_SIZE          2
59 int     form_cycle [FORMULA_SIZE];
61 void DSPF_sp_fftSPxSP(int N, float *ptr_x, float *ptr_w, float *ptr_y, unsigned char *brev, int n_min, int offset, int n_max);
63 void tw_gen (float *w, int n);
64 int fltcmp (const float *y1, const float *y2, int n, float tol);
65 void dft (int N, float x[], float y[]);
67 /* ======================================================================== */
68 /*  Kernel-specific alignments                                              */
69 /* ======================================================================== */
70 #pragma DATA_ALIGN(x_i, 8);
71 #pragma DATA_ALIGN(x_cn, 8);
73 #pragma DATA_ALIGN(w, 8);
74 #pragma DATA_ALIGN(y_i, 8);
75 #pragma DATA_ALIGN(y_cn, 8);
76 #pragma DATA_ALIGN(brev, 8);
78 /* ======================================================================== */
79 /*  Parameters of fixed dataset.                                            */
80 /* ======================================================================== */
81 #define MAXN (256)
82 #define M    (2*MAXN)
83 #define PAD  (16)
85 /* ======================================================================== */
86 /*  Initialized arrays with fixed test data.                                */
87 /* ======================================================================== */
89 float x_i[M + 2 * PAD];
90 float x_cn[M + 2 * PAD];
92 float w[M + 2 * PAD];
94 float y_i[M + 2 * PAD];
95 float y_cn[M + 2 * PAD];
97 /* ======================================================================== */
98 /*  Generate pointers to skip beyond array padding                          */
99 /* ======================================================================== */
100 float *const ptr_x_i  = x_i  + PAD;
101 float *const ptr_x_cn = x_cn + PAD;
103 float *const ptr_w = w + PAD;
105 float *const ptr_y_i  = y_i  + PAD;
106 float *const ptr_y_cn = y_cn + PAD;
108 unsigned char brev[64] = {
109     0x0, 0x20, 0x10, 0x30, 0x8, 0x28, 0x18, 0x38,
110     0x4, 0x24, 0x14, 0x34, 0xc, 0x2c, 0x1c, 0x3c,
111     0x2, 0x22, 0x12, 0x32, 0xa, 0x2a, 0x1a, 0x3a,
112     0x6, 0x26, 0x16, 0x36, 0xe, 0x2e, 0x1e, 0x3e,
113     0x1, 0x21, 0x11, 0x31, 0x9, 0x29, 0x19, 0x39,
114     0x5, 0x25, 0x15, 0x35, 0xd, 0x2d, 0x1d, 0x3d,
115     0x3, 0x23, 0x13, 0x33, 0xb, 0x2b, 0x1b, 0x3b,
116     0x7, 0x27, 0x17, 0x37, 0xf, 0x2f, 0x1f, 0x3f
117 };
119 /* ======================================================================== */
120 /*  MAIN -- Top level driver for the test.                                  */
121 /* ======================================================================== */
123 int main ()
125     int i, j, rad, N, k;
126     clock_t t_start, t_stop, t_overhead, t_opt, t_cn;
127     float pct_diff, max_pct_diff = 0;
129     for (N = 8, k = 1; N <= MAXN; N = N * 2, k++)
130     {
132         memset (x_i,  0x55, sizeof (x_i) );
133         memset (x_cn, 0x55, sizeof (x_cn));
135         /* ---------------------------------------------------------------- */
136         /* Initialize input vector temporarily.                             */
137         /* ---------------------------------------------------------------- */
138         for (i = 0; i < N; i++)
139         {
140             x_cn[PAD + 2 * i]     = sin (2 * 3.1415 *  50 * i / (double) N);
141             x_cn[PAD + 2 * i + 1] = sin (2 * 3.1415 * 100 * i / (double) N);
142             x_i[PAD + 2 * i]      = x_cn[PAD + 2 * i];
143             x_i[PAD + 2 * i + 1]  = x_cn[PAD + 2 * i + 1];
144         }
146         /* ---------------------------------------------------------------- */
147         /* Force uninitialized arrays to fixed values.                      */
148         /* ---------------------------------------------------------------- */
149         memset (y_i,  0xA5, sizeof (y_i) );
150         memset (y_cn, 0xA5, sizeof (y_cn));
152         /* ---------------------------------------------------------------- */
153         /* Initialize timer for clock */
154         TSCL= 0,TSCH=0;
155         /* Compute the overhead of calling _itoll(TSCH, TSCL) twice to get timing info */
156         /* ---------------------------------------------------------------- */
157         t_start = _itoll(TSCH, TSCL);
158         t_stop = _itoll(TSCH, TSCL);
159         t_overhead = t_stop - t_start;
161         /* ---------------------------------------------------------------- */
162         /* Generate twiddle factors.                                        */
163         /* ---------------------------------------------------------------- */
164         j = 0;
165         for (i = 0; i <= 31; i++)
166             if ((N & (1 << i)) == 0)
167                 j++;
168             else
169                 break;
171         if (j % 2 == 0)
172             rad = 4;
173         else
174             rad = 2;
176         tw_gen (ptr_w, N);
178         printf("DSPF_sp_fftSPxSP\tIter#: %d\t", k);
179         t_start = _itoll(TSCH, TSCL);
180         DSPF_sp_fftSPxSP_cn (N, &ptr_x_cn[0], &ptr_w[0], ptr_y_cn, brev, rad, 0, N);
181         t_stop = _itoll(TSCH, TSCL);
182         t_cn = (t_stop - t_start) - t_overhead;
184         t_start = _itoll(TSCH, TSCL);
185         DSPF_sp_fftSPxSP( N, &ptr_x_i[0], &ptr_w[0], ptr_y_i, brev, rad, 0, N);
186         t_stop = _itoll(TSCH, TSCL);
187         t_opt = (t_stop - t_start) - t_overhead;
189         /* ---------------------------------------------------------------- */
190         /* compute percent difference and track max difference              */  
191         /* ---------------------------------------------------------------- */
192         for(i=0; i<N; i++) {
193           pct_diff = (ptr_y_cn[i] - ptr_y_i[i]) / ptr_y_cn[i] * 100.0;
194           if (pct_diff < 0) pct_diff *= -1;
195           if (pct_diff > max_pct_diff) max_pct_diff = pct_diff;
196         }
197         if (max_pct_diff > 0.001)
198             printf("Result Failure  max_pct_diff = %f", max_pct_diff);
199         else
200             printf("Result Successful ");
202         printf("\tN = %d\tradix = %d\tnatC: %d\toptC: %d\n", N, rad, t_cn, t_opt);
204         if (N == CYCLE_FORMULA_NX_PT1)
205           form_cycle[0] = t_opt;
206         if (N == CYCLE_FORMULA_NX_PT2)
207           form_cycle[1] = t_opt;
208     }
210     /* Provide memory information */
211 #ifdef __TI_COMPILER_VERSION__            // for TI compiler only
212     printf("Memory:  %d bytes\n", &kernel_size);
213 #endif
215     /* Provide profiling information */
216     printf("Cycles:  %d (N=128) %d (N=256)\n", form_cycle[0], form_cycle[1]);
219 /* Function for generating Specialized sequence of twiddle factors */
220 void tw_gen (float *w, int n)
222     int i, j, k;
223     double x_t, y_t, theta1, theta2, theta3;
224     const double PI = 3.141592654;
226     for (j = 1, k = 0; j <= n >> 2; j = j << 2)
227     {
228         for (i = 0; i < n >> 2; i += j)
229         {
230             theta1 = 2 * PI * i / n;
231             x_t = cos (theta1);
232             y_t = sin (theta1);
233             w[k] = (float) x_t;
234             w[k + 1] = (float) y_t;
236             theta2 = 4 * PI * i / n;
237             x_t = cos (theta2);
238             y_t = sin (theta2);
239             w[k + 2] = (float) x_t;
240             w[k + 3] = (float) y_t;
242             theta3 = 6 * PI * i / n;
243             x_t = cos (theta3);
244             y_t = sin (theta3);
245             w[k + 4] = (float) x_t;
246             w[k + 5] = (float) y_t;
247             k += 6;
248         }
249     }
252 /* ======================================================================= */
253 /*  End of file:  DSPF_sp_fftSPxSP_d.c                                     */
254 /* ----------------------------------------------------------------------- */
255 /*            Copyright (c) 2011 Texas Instruments, Incorporated.          */
256 /*                           All Rights Reserved.                          */
257 /* ======================================================================= */