I had not used the fft before, had used other in the package
refer to
http://www.keil.com/pack/doc/CMSIS/DSP/html/index.html
in particular : "Using the Library"
you must include <arm_math.h>
and have all the switches in to get the processor to do its fancy work.
In fact most people I see don't use the VFP switches so the micro is
often not using the FPU at all !
I am using
arm_cortexM7lfsp_math.lib (Little endian and Single Precision Floating
Point Unit on Cortex-M7)
F4 will use
arm_cortexM4lf_math.lib (Little endian and Floating Point Unit on Cortex-M4)
then refer to
http://www.keil.com/pack/doc/CMSIS/DSP/html/group___complex_f_f_t.html
in particular
http://www.keil.com/pack/doc/CMSIS/DSP/html/group___complex_f_f_t.html#gade0f9c4ff157b6b9c72a1eafd86ebf80
which is arm_cfft_f32()
for each different CONFIG
you only need one struct :
http://www.keil.com/pack/doc/CMSIS/DSP/html/structarm__cfft__instance__f32.html
the twiddle and BR tables must be initialized
I had to rename globals defines N and M as they clashed with CMIS or
soemthing else
so I renamed N to NSPF
(rom defines.h>
#define NSPF 80 /* number of samples per frame */
and M to M_PAFS
#define M_PAFS 320 /* pitch analysis frame size */
and because there are no spaces around variable names (David ! take
note ! . mutter mutter )
you need to go in every file and manually replace or not....
(if you just do a global find replace , the editor can't tell the
difference 'cause there are no spaces around variable names )
now, next thing :
there is an example here
http://www.keil.com/pack/doc/CMSIS/DSP/html/group___frequency_bin.html
in particular
http://www.keil.com/pack/doc/CMSIS/DSP/html/arm_fft_bin_example_f32_8c-example.html
you'll need to go through and change all the kiss_fft type decs in the
functions and their definitions (or macroize it all) .
everywhere you find
change it to arm_cfft_instance_f32
like the codec2 struct has references to kiss_fft you need to change
it to a arm_cfft_instance_f32 *
also all the instances kiss_fft_cpx type , when kiss_fft goes you need
to come up with something different
however in the code there is COMP type - this is a macro definition
that does a simialr job.
there is a mix of COMP type, which is two floats, and just float *
My command line flags :
gcc/arm-none-eabi/bin/as" --traditional-format -mcpu=cortex-m7
-mlittle-endian -mfloat-abi=softfp -mfpu=fpv5-sp-d16 -mthumb
"F:/projects/kkk/K15-001-TRAD/sw/rev1/K15-001 THUMB Debug/tmpa06908" -o
"K15-001 THUMB Debug/nlp.o"
linker (truncated)
gcc/arm-none-eabi/bin/ld" -X -ereset_handler --omagic
-defsym=__vfprintf=__vfprintf_float_long_long
-defsym=__vfscanf=__vfscanf_float_long_long_cc --fatal-warnings -EL
--gc-sections "-TF:/projects/kkk/K15-001-TRAD/sw/rev1/K15-001 THUMB
Debug/K15-001.ld" -Map "K15-001 THUMB Debug/K15-001.map" -u_vectors -o
"K15-001 THUMB Debug/K15-001.elf" --start-group "K15-001 THUMB
Debug/main.o" "K15-001 THUMB Debug/hw_init.o" "K15-001 THUMB Debug/si4460.o"
attached
some help
#include <assert.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <math.h>
#include <arm_math.h>
#define FFT_ENC 512
/* old codec 2 stuff */
#define FFT_DEC FFT_ENC
float __attribute__(( aligned(4))) twiddles[2*FFT_ENC];
uint16_t __attribute__(( aligned(4))) brtable[2*FFT_ENC];
arm_cfft_instance_f32 __attribute__(( aligned(4)))
FFT_fwd_cfg={FFT_ENC,twiddles,brtable,2*FFT_ENC};
void initFFTtables512(float * twiddleTableptr, uint16_t * bitReversalTableptr) {
/*
hacked from ARM pseudo code...
possibly could be pre computed and included as they are const
*/
assert(FFT_ENC == FFT_DEC);/* bonehead checks in the hack */
const uint32_t N = FFT_ENC;
assert(N == 512);/* must be */
#define log2NFFT512 9
const uint32_t logN2 = log2NFFT512;
int i,j,l;
uint32_t a[log2NFFT512];
uint16_t * y = bitReversalTableptr;
for(i = 0; i< N/2; i++)
{
twiddleTableptr[2*i]= cos(i * 2*PI/(float)N);
twiddleTableptr[2*i+1]= sin(i * 2*PI/(float)N);
}
/* init br tables from ARM website*/
for(l=1;l <= N/4;l++)
{
for(i=0;i<logN2;i++)
{
a[i]=l&(1<<i);
}
for(j=0; j<logN2; j++)
{
if (a[j]!=0)
y[l]+=(1<<((logN2-1)-j));
}
y[l] = y[l] >> 1;
}
}
do_it(arm_cfft_instance_f32 * fft_cfg) {
COMP src[FFT_ENC]; /* example out of the codec2 code
(source array) */
COMP * dst;
dst = src;
/* fill up SW_ */
/*
.
.
.*/
/* use it */
//was... kiss_fft_entry(fft_fwd_cfg, (kiss_fft_cpx_t *)src,
(kiss_fft_cpx_t *)dst);
const int ISINV=0;const int ISBITREV=0;
arm_cfft_f32(fft_cfg,(float *) (COMP *) src,ISINV,ISBITREV);
/* now, you can either rename all the variables beyond this or
just memcpy to the destination name*/
/* code that uses variable 'dst' */
}
/* some write the destinatuion fft result into a passed parameter */
dft_speech(arm_cfft_instance_f32 * fft_cfg, float Sw[], ...) {
COMP src[FFT_ENC]; /* example out of the codec2 code
(source array) */
/* fill up SW_ */
/*
.
.
.*/
/* use it */
//was... kiss_fft_entry(fft_fwd_cfg, (kiss_fft_cpx_t *)src,
(kiss_fft_cpx_t *)dst);
const int ISINV=0;const int ISBITREV=0;
arm_cfft_f32(fft_cfg,(float *) (COMP *) src,ISINV,ISBITREV);
/* now, you can either rename all the variables beyond this or
just memcpy to the destination name*/
memcpy(Sw,src,sizeof(COMP) * fft_fwd_cfg->fftLen);
/* code that uses variable 'dst' */
}
starthere() {
initFFTtables(twiddles,brtable);
codec2instance->fft_fwd_cfg = &FFT_fwd_cfg
do_it(codec2instance->fft_fwd_cfg);
}
------------------------------------------------------------------------------
_______________________________________________
Freetel-codec2 mailing list
Freetel-codec2@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/freetel-codec2