der vollständigkeit halber wollte ich kurz erwähnen, dass ich nun doch die FFT von Chan (link siehe oben) verwende. kurze anleitung wie das geht:
ffft.S und ffft.h in den projektordner kopieren
ffft.h mit #include "ffft.h" einbinden
im makefile ffft.S bei ASM quellen hinzufügen
dann am besten erst mal testen, ob es kompliert werden kann. dann..
in der ffft.h die anzahl der samples festlegen und arrays deklarieren:
Code:
int16_t capture[FFT_N]; /* Wave captureing buffer */
complex_t bfly_buff[FFT_N]; /* FFT buffer */
uint16_t spektrum[FFT_N/2]; /* Spectrum output buffer */
eine interrupt service routine erstellen, ("position" habe ich global mit unsigned int position=0; deklariert):
Code:
ISR(SIG_ADC)
{
if(position>=FFT_N)return;
capture[position]=ADC - 32768;
position++;
}
den ADC im free running mode laufen lassen:
Code:
// free running ADC mode, f = ( 16MHz / prescaler 128 ) / 13 cycles per conversion = 9615Hz
// 8bit result in ADCH (we adjust left)
ADMUX=(1<<REFS0)|(1<<ADLAR);
ADCSRA=(1<<ADSC)|(1<<ADEN)|(1<<ADFR)|(1<<ADIE)|(1<<ADPS2)|(1<<ADPS1);
warum ADLAR (left adjust result) gesetzt werden muss, verstehe ich selber nicht so ganz.. verwendet wird nämlich (wie man in der ISR sieht) ADC, also der 16/10 bit wert.
nun kann man die FFT durchführen, dazu habe ich im main-loop folgenden code:
Code:
if(position==FFT_N)
{
fft_input(capture, bfly_buff);
fft_execute(bfly_buff);
fft_output(bfly_buff, spektrum);
position=0;
}
im array spektrum hat man nun die frequenzanteile des signals. der sample-buffer wird wieder gefüllt, sobald position auf 0 gesetzt ist.
vielleicht kann jemand mal was damit anfangen.
gruesse von der katz
Lesezeichen