$B%j%9%H(B2-6-2.txt

$B"#%j%9%H(B2-6-2$B"#(B

$B!|%a%$%s!!(Bmain.cpp

#include "mbed.h"
#include "sub.hpp"
#include "notch.hpp"
#include "fft1.hpp"

float in1[16], out1[16], in2[16], out2[16];
        
int main(){
    common_setup();
    int fft_counter1 = 0;
    int fft_counter2 = 0;
    xbee.baud(38400);
    xbee.attach(&rx_fifoset, xbee.RxIrq);
    timer_setup.attach_us(&timer_interrupt, 5); // 5usec
    while(1){
        tx_fifo_check();
        if(timer_value[1] > 19){ // 0.1msec sampling
            timer_value[1] = 0;
            data1 = (float)gain * (analog_value2.read() - 0.5f);  // A/D in (3)
            data2 = (float)gain * (analog_value3.read() - 0.5f);  // A/D in (4)
            if(data1 < 0) data1 = -data1; // always detection ON
            if(notch_1 != 0) data1 = notch_filter1(data1);
            if(max_count != 0) data1 = move_mean_calc1(data1);
            if(data2 < 0) data2 = -data2; // always detection ON
            if(notch_2 != 0) data2 = notch_filter2(data2);
            if(max_count != 0) data2 = move_mean_calc2(data2);
        }
        if(timer_value[2] > 199){ // 1msec sampling
            timer_value[2] = 0;
            in1[fft_counter1] = data1;            
            if(++fft_counter1 > 15){
                fft_counter1 = 0;
                fft1(in1, out1);
                int summ = 0;
                for(int i=0; i<7; i++) { summ = summ + (uint16_t)((out1[2*i]+out1[2*i+1]) * 7.9) << ((6-i)*3); }
                tx_message(0x000000 + summ);
            }
        }
        if(timer_value[3] > 199){ // 1msec sampling
            timer_value[3] = 0;         
            in2[fft_counter2] = data2;
            if(++fft_counter2 > 15){
                fft_counter2 = 0;
                fft1(in2, out2);
                int summ = 0;
                for(int i=0; i<7; i++) { summ = summ + (uint16_t)((out2[2*i]+out2[2*i+1]) * 7.9) << ((6-i)*3); }
                tx_message(0x400000 + summ);
            }
        }
        if(timer_value[0] > 199999){ // 1000msec
            timer_value[0] = 0;
            myled = !myled;
        }
        if(rx_fifo_check() == 1){
            int sum = 0;
            for (int i=0; i<6; i++) sum += conv_hex(raw_data[i])<<(4*(5-i));
            tx_message(sum); // Echo Back 
            if(sum>>16 == 0x80){
                switch((sum & 0xff00)>>8){
                    case 0x00:
                        break;
                    case 0x01:
                        gain = sum & 0x0f;
                        break;
                    case 0x02:
                        max_count = sum & 0x7f;
                        if (max_count>100) max_count = 100;
                        sum_clear();
                        break;
                    case 0x03:
                        notch_1 = sum & 0x01;
                        break;
                    case 0x04:
                        notch_2 = sum & 0x01;
                        break;
                    case 0x05:
                        coef_set(sum & 0x3f);
                        break;
                    case 0x06:
                        break;
                }
            }
        }        
    }
}

$B!|%5%V(B sub.hpp

unsigned char rxFIFO[256], txFIFO[256], raw_data[6];
unsigned char rx_top, rx_end, tx_top, tx_end, phase;
float mean_sum1, mean_sum2, ad_data1[101], ad_data2[101];
int timer_value[6], max_count, gain, ad_pointer1, ad_pointer2;
float a1, a2, b1, c0, y1[3], y2[3];
int notch_1, notch_2;
float data1, data2, data3;
const float _60Hz_a1 = 1.936768, _60Hz_a2 = -0.939101, _60Hz_b1 = -1.998579, _60Hz_c0 = 1.642174;
const float _50Hz_a1 = 1.937188, _50Hz_a2 = -0.939101, _50Hz_b1 = -1.999013, _50Hz_c0 = 1.938304;

RawSerial xbee(PA_2, PA_3);
Ticker timer_setup;
AnalogIn analog_value0(A0);
AnalogIn analog_value1(A1);
AnalogIn analog_value2(A2);
AnalogIn analog_value3(A3);
DigitalOut myled(LED1);

void sum_clear(){
    for (int i=0; i<101; i++) ad_data1[i] = ad_data2[i] = 0;
    ad_pointer1 = ad_pointer2 = mean_sum1 = mean_sum2 = 0;
}

void coef_set(int herz){
    if(herz < 55){
        a1 = _50Hz_a1;
        a2 = _50Hz_a2;
        b1 = _50Hz_b1;
        c0 = _50Hz_c0;
    }
    else{
        a1 = _60Hz_a1;
        a2 = _60Hz_a2;
        b1 = _60Hz_b1;
        c0 = _60Hz_c0;
    }
    for (int i=0; i<3; i++) y1[i] = y2[i] = 0;
}
void common_setup(){
    rx_top = rx_end = tx_top = tx_end = phase = 0;
    max_count = 100;
    gain = 7;
    sum_clear();
    notch_1 = notch_2 = 1;
    coef_set(60);
    for(int i=0; i<6; i++) timer_value[i] = 0;
    timer_value[3] = 100;
}

void timer_interrupt(){
    for(int i=0; i<6; i++) timer_value[i]++;
}

void tx_fifo_check(){
    if(xbee.writeable() == 1){
        if(tx_top != tx_end){
            xbee.putc(txFIFO[tx_end]);
            ++tx_end &= 255;
        }
    }
}

int rx_fifo_check(){
    if(rx_top != rx_end){
        unsigned char data = rxFIFO[rx_end];
        ++rx_end &= 255;
        if (data < 33){
            phase = 0;
            return(1);
        }
        raw_data[phase] = data;
        if(++phase > 5) phase = 0;
        return(0);
    }
    return(0);
}

void rx_fifoset(void){
    rxFIFO[rx_top] = xbee.getc();
    ++rx_top &= 255;
}

void tx_fifoset(unsigned char data){
    txFIFO[tx_top] = data;
    ++tx_top &= 255;
}

unsigned char hex_conv(unsigned char data){
    data &= 15;
    if(data < 10) return(data+48);
    else return(data+55);
}

unsigned char conv_hex(unsigned char data){
    if((data > 47) && (data < 58)) return(data-48);
    else if((data > 64) && (data < 71)) return(data-55);
    return(0);
}

void tx_message(int data){
    for (int i=0; i<6; i++) tx_fifoset(hex_conv((data>>(4*(5-i))) & 15));
    tx_fifoset(13);
}

float move_mean_calc1(float data){
    mean_sum1 = mean_sum1 - ad_data1[ad_pointer1] + data;
    ad_data1[ad_pointer1] = data;
    ad_pointer1++;
    if(ad_pointer1 == max_count) ad_pointer1 = 0;
    return(mean_sum1 / (float)max_count);
}

float move_mean_calc2(float data){
    mean_sum2 = mean_sum2 - ad_data2[ad_pointer2] + data;
    ad_data2[ad_pointer2] = data;
    ad_pointer2++;
    if(ad_pointer2 == max_count) ad_pointer2 = 0;
    return(mean_sum2 / (float)max_count);
}

$B!|%5%V(B fft1.hpp

// http://www.mit.edu/~emin/source_code/fft/index.html

#define SIN_2PI_16 0.38268343236508978
#define SIN_4PI_16 0.707106781186547460
#define SIN_6PI_16 0.923879532511286740
#define C_P_S_2PI_16 1.30656296487637660
#define C_M_S_2PI_16 0.54119610014619690
#define C_P_S_6PI_16 1.3065629648763766
#define C_M_S_6PI_16 -0.54119610014619690

void fft1(float input[16],float output[16] ) {
  float temp, out0, out1, out2, out3, out4, out5, out6, out7, out8;
  float out9,out10,out11,out12,out13,out14,out15;

  out0=input[0]+input[8]; /* output[0 through 7] is the data that we */
  out1=input[1]+input[9]; /* take the 8 point real FFT of. */
  out2=input[2]+input[10];
  out3=input[3]+input[11];
  out4=input[4]+input[12];
  out5=input[5]+input[13];
  out6=input[6]+input[14];
  out7=input[7]+input[15];
  out8=input[0]-input[8];   /* inputs 8,9,10,11 are */
  out9=input[1]-input[9];   /* the Real part of the */
  out10=input[2]-input[10]; /* 4 point Complex FFT inputs.*/
  out11=input[3]-input[11]; 
  out12=input[12]-input[4]; /* outputs 12,13,14,15 are */
  out13=input[13]-input[5]; /* the Imaginary pars of  */
  out14=input[14]-input[6]; /* the 4 point Complex FFT inputs.*/
  out15=input[15]-input[7];
  temp=(out13-out9)*(SIN_2PI_16); 
  out9=out9*(C_P_S_2PI_16)+temp; 
  out13=out13*(C_M_S_2PI_16)+temp;
  out14*=(SIN_4PI_16);
  out10*=(SIN_4PI_16);
  out14=out14-out10;
  out10=out14+out10+out10;
  temp=(out15-out11)*(SIN_6PI_16);
  out11=out11*(C_P_S_6PI_16)+temp;
  out15=out15*(C_M_S_6PI_16)+temp;
  out8+=out10;
  out10=out8-out10-out10;
  out12+=out14;
  out14=out12-out14-out14;
  out9+=out11;
  out11=out9-out11-out11;
  out13+=out15;
  out15=out13-out15-out15;
  output[1]=out8+out9;
  output[7]=out8-out9;
  output[9]=out12+out13;
  output[15]=out13-out12;  
  output[5]=out10+out15;    /* implicit multiplies by */
  output[13]=out14-out11;   /* a twiddle factor of -j */                            
  output[3]=out10-out15;    /* implicit multiplies by */
  output[11]=-out14-out11;  /* a twiddle factor of -j */    
  out0=out0+out4;
  out4=out0-out4-out4;
  out1=out1+out5;
  out5=out1-out5-out5;
  out2+=out6;
  out6=out2-out6-out6;
  out3+=out7;
  out7=out3-out7-out7;  
  output[0]=out0+out2;
  output[4]=out0-out2;
  out1+=out3;
  output[12]=out3+out3-out1;
  output[0]+=out1;          /* Real Part of X[0] */
  output[8]=output[0]-out1-out1; /*Real Part of X[4] */
  out5*=SIN_4PI_16;
  out7*=SIN_4PI_16;
  out5=out5-out7;
  out7=out5+out7+out7;
  output[14]=out6-out7;     /* Imag Part of X[5] */
  output[2]=out5+out4;      /* Real Part of X[7] */
  output[6]=out4-out5;      /*Real Part of X[5] */
  output[10]=-out7-out6; /* Imag Part of X[7] */
}

$B!|%5%V(B notch.hpp

($B%j%9%H(B2-5-5$B$HF1$8(B)

========================
mbed$B%5%$%H(B
http://developer.mbed.org/users/nagasm/code/CQ_nagasm_11_FFT1/
$B$K$F8x3+Cf(B
========================
