This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

TMS320C6416 FFT Problems

I am using c6416 dsp and CCS 4.2.1.0004  compiler. I want to use the DSPLIB (C64 DSPLIB for

SPRA884 version 1.0) to do FFT. Bottom is the example code. My problem is that the FFT output is

not correct especially around the DC. As you can see at the figure bellow. The output of the real

part should be zero but it is up to -63. I change the different input but the result that the noise

arround DC is still large (up to -120). Is this normal ? Thanks!

 

/* ======================================================================== */

/*  TEXAS INSTRUMENTS, INC.                                                 */

/*                                                                          */

/*  DSPLIB Application Note Example (DSP_fft16x16t)                         */

/*                                                                          */

/*      Release:        Version 1.0                                         */

/*                                                                          */

/*  This file contains proprietary intellectual property of Texas           */

/*  Instruments, Inc.  Its source and binary codes are protected by         */

/*  various copyrights, and portions may also be protected by patents or    */

/*  other legal protections.                                                */

/*                                                                          */

/* ------------------------------------------------------------------------ */

/*          Copyright (C) 2003 Texas Instruments, Incorporated.             */

/*                          All Rights Reserved.                            */

/* ======================================================================== */

 

#include <stdio.h>

#include <stdlib.h>

#include <csl.h>

#include <csl_timer.h>

#include <math.h>

 

/* ======================================================================== */

/* Include the DSPLIB header file                                           */

/* ======================================================================== */

#include "dsp_fft16x16t.h"

 

/* ======================================================================== */

/* Macro definition                                                         */

/* ======================================================================== */

#define PI  (3.141592654)

#define NN  (512)

 

/* ======================================================================== */

/* Input and output arrays                                                  */

/* ======================================================================== */

#pragma DATA_ALIGN(x, 8)     

#pragma DATA_ALIGN(y, 8)

#pragma DATA_ALIGN(w, 8)

short x[2*NN];           

short w[2*NN];           

short y[2*NN];           

short xx[2*NN];          

 

/* ======================================================================== */

/*  D2S -- Truncate a 'double' to a 'short', with clamping.                 */

/* ======================================================================== */

static short d2s(double d)

{

    if (d >=  32767.0) return  32767;

    if (d <= -32768.0) return -32768;

    return (short)d;

}

 

/* ======================================================================== */

/*  GEN_TWIDDLE -- Generate twiddle factors for fft16x16t().                */

/*                                                                          */

/*  USAGE                                                                   */

/*      This routine is called as follows:                                  */

/*                                                                          */

/*          int gen_twiddle_fft16x16t(short *w, int n, double scale)        */

/*                                                                          */

/*          short  *w     Pointer to twiddle-factor array                   */

/*          int    n      Size of FFT                                       */

/*          double scale  Scale factor to apply to values.                  */

/*                                                                          */

/*      The routine will generate the twiddle-factors directly into the     */

/*      array you specify.  The array needs to be approximately 2*N         */

/*      elements long.  (The actual size, which is slightly smaller, is     */

/*      returned by the function.)                                          */

/* ======================================================================== */

int gen_twiddle_fft16x16t(short *w, int n, double scale)

{

    int i, j, k;

 

    for (j = 1, k = 0; j < n >> 2; j = j << 2)

    {

        for (i = 0; i < n >> 2; i += j << 1)

        {

            w[k + 11] = d2s(scale * cos(6.0 * PI * (i + j) / n));

            w[k + 10] = d2s(scale * sin(6.0 * PI * (i + j) / n));

            w[k +  9] = d2s(scale * cos(6.0 * PI * (i    ) / n));

            w[k +  8] = d2s(scale * sin(6.0 * PI * (i    ) / n));

 

            w[k +  7] = d2s(scale * cos(4.0 * PI * (i + j) / n));

            w[k +  6] = d2s(scale * sin(4.0 * PI * (i + j) / n));

            w[k +  5] = d2s(scale * cos(4.0 * PI * (i    ) / n));

            w[k +  4] = d2s(scale * sin(4.0 * PI * (i    ) / n));

 

            w[k +  3] = d2s(scale * cos(2.0 * PI * (i + j) / n));

            w[k +  2] = d2s(scale * sin(2.0 * PI * (i + j) / n));

            w[k +  1] = d2s(scale * cos(2.0 * PI * (i    ) / n));

            w[k +  0] = d2s(scale * sin(2.0 * PI * (i    ) / n));

 

            k += 12;

        }

    }

 

    return k;

}

 

/* ======================================================================== */

/*  NAME                                                                    */

/*     main                                                                 */

/*                                                                          */

/*  RIVISION HISTORY                                                        */

/*     30-Jun-2002 Initial revision                                         */

/*     31-Dec-2002 Improved benchmarking                                    */

/*                                                                          */

/*  USAGE                                                                   */

/*     void main ();                                                        */

/*     This program is to show how to use DSP_fft16x16t()                   */

/*     when data are in L2SRAM.                                             */

/*                                                                          */

/*  DESCRIPTION                                                             */

/*     First, function call overhead for timer functions is measured.       */

/*     Then, the execution cycles for the target function is measured.      */

/*     Finally, the timer function call overhead is excluded from the       */

/*     execution cycles measured.                                           */

/*     The cycle count measured will include L1P/D miss overhead as well as */

/*     function call overhead.                                              */

/*                                                                          */

/*  ASSUMPTIONS                                                             */

/*     The benchmarking code assumes C64x, e.g., 1 count = 8 CPU cycles.    */

/*                                                                          */

/* ------------------------------------------------------------------------ */

/*            Copyright (c) 2003 Texas Instruments, Incorporated.           */

/*                           All Rights Reserved.                           */

/* ======================================================================== */

 

void main(void)

{

    int i; 

    short F1 = 10, F2 = 40;          /* Input frequencies                   */

    int start, stop, overhead, diff;

    TIMER_Handle hTimer;

 

    /* ==================================================================== */

    /* Initialize Chip Support Library                                      */

    /* ==================================================================== */

    CSL_init();

 

    /* ==================================================================== */

    /* Generate Q.15 input data                                             */

    /* ==================================================================== */

    for(i=0; i<NN; i++) 

    {

        xx[2*i] = x[2*i] = 32767./(2*NN) * (sin(2*PI*F2*i/NN) 

                         + sin(2*PI*F1*i/NN) ); 

        xx[2*i+1] = x[2*i+1] = 0;  

    }

 

    /* ==================================================================== */

    /* Generate twiddle factors                                             */

    /* ==================================================================== */

gen_twiddle_fft16x16t(w, NN, 32767.);

 

    /* ==================================================================== */

    /* Configure a timer.                                                   */

    /* ==================================================================== */

    hTimer = TIMER_open(TIMER_DEVANY,0);   

    TIMER_configArgs(hTimer, 0x000002C0, 0xFFFFFFFF, 0x00000000);

 

    /* ==================================================================== */

    /*  Compute the overhead of calling the timer.                          */

    /* ==================================================================== */

    start = TIMER_getCount(hTimer); /* called twice to avoid L1D miss.      */

    start = TIMER_getCount(hTimer);        

    stop  = TIMER_getCount(hTimer);        

    overhead = stop - start;

 

    /* ==================================================================== */

    /* Measure the time                                                     */

    /* ==================================================================== */

    start = TIMER_getCount(hTimer);        

    DSP_fft16x16t(w, NN, x, y);            

    diff = TIMER_getCount(hTimer) - start - overhead; 

 

    /* ==================================================================== */

    /* Print the result                                                     */

    /* ==================================================================== */

    printf("Total cycles including L1P/D miss overhead = %d\n", diff*8);

    printf("Check the result with the Graph menu.\n"

           "* Input\n"

           "Start address: xx\n"

  "Acquisition buffer size: 512\n"

           "Index increment: 2\n"

           "Display data size: 512\n"

           "DSP data type: 16-bit signed integer\n"

           "* Output\n"

           "Start address: y\n"

           "Acquisition buffer size: 1024\n"

           "Index increment: 1\n"

           "Display data size: 1024\n"

           "DSP data type: 16-bit signed integer\n" );

 

    TIMER_close(hTimer);

}

 

/* ======================================================================== */

/*  End of file: fft16x16t_main.c                                           */

/* ======================================================================== */