/*
 * FIR filter
 * using interrupt to execute FIR code
 */

//#define S16
#define F32

#include "L138_LCDK_aic3106_init.h"

#include "bp16.txt"	// Coefficients file for band-pass FIR filter centered @ Fs/2/4
					/// quindi 1 kHz per 8 kHz

static short samples[FIR_FILTER_SIZE]; /* Retains values between calls */
static int j = 0; /* Index into input array; retains value between calls */


// in vectors_intr.asm, l'interrupt # 4 viene mappato su questa routine
interrupt void interrupt4(void)
{
short i, input;

#ifdef S16
//short accum;  // togliendo lo scalaggio finale, si vede che qualcosa viene fatto
int accum;
//long accum; // no, e' un 64 bit!!
#endif
#ifdef F32
  float accum;
#endif

input = input_left_sample(); // input from ADC
samples[j] = input;

// NB affinche' il compilatore usi software pipelining bisogna dirgli di ottimizzare, almeno con "2"

accum = 0;
for ( i = 0 ; i < FIR_FILTER_SIZE ; i++)
{

#ifdef S16
	accum +=  samples[j] * filter_mask[i];
#endif

#ifdef F32
	accum +=  ( ((float) samples[j] * filter_mask[i]));
#endif

/* Next item in circular buffer */
j=(j+1)%(FIR_FILTER_SIZE);

}

#ifdef S16
accum=accum/10000; // poiche' i coefficienti erano stati scalati di un fattore 10000
#endif

j=(j+1)%(FIR_FILTER_SIZE); // prepares for the next sample

output_left_sample((short)(accum));  // output to DAC
return;
}



int main(void)
{
// in L138_LCDK_aic3106_init.c, il codec e' associato all'interrupt # 4 (linea 653)
	L138_initialise_intr(FS_8000_HZ,ADC_GAIN_0DB,DAC_ATTEN_0DB,LCDK_LINE_INPUT);
//	L138_initialise_intr(FS_24000_HZ,ADC_GAIN_0DB,DAC_ATTEN_0DB,LCDK_LINE_INPUT);
  while(1);
}
