花見 太郎 / Mbed OS Voise_control

Dependencies:   mbed-os-lychee

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers main.cpp Source File

main.cpp

00001 #include "mbed.h"
00002 #include "SdUsbConnect.h"
00003 #include "AUDIO_GRBoard.h"
00004 
00005 
00006 #define MOUNT_NAME             "storage"
00007 #define FINE_PATH              "/"MOUNT_NAME"/wav_rec.wav"
00008 
00009 
00010 
00011 #define SAMPLE_RATE            (8000)
00012 #define AUDIO_IN_BUF_SIZE      (2048)
00013 #define AUDIO_IN_BUF_NUM       (16)
00014 #define AUDIO_OUT_BUF_SIZE     (2048)
00015 #define AUDIO_OUT_BUF_NUM      (8)
00016 #define AUDIO_OUT_WAIT         ((AUDIO_OUT_BUF_SIZE * AUDIO_OUT_BUF_NUM / 4) * 1000 / SAMPLE_RATE)
00017 
00018 #define INFO_TYPE_OPEN         (0)
00019 #define INFO_TYPE_CLOSE        (1)
00020 #define INFO_TYPE_WRITE_DATA   (2)
00021 
00022 DigitalOut led1(LED1);
00023 DigitalOut led2(LED2);
00024 DigitalOut led3(LED3);
00025 DigitalOut led4(LED4);
00026 
00027 AUDIO_GRBoard audio(0x80, AUDIO_OUT_BUF_NUM - 1, AUDIO_IN_BUF_NUM); // I2S Codec
00028 int led_rec;
00029 int led_play;
00030 InterruptIn button_0(USER_BUTTON0);
00031 #if defined(TARGET_GR_LYCHEE)
00032 InterruptIn button_1(USER_BUTTON1);
00033 #endif
00034 static bool play_req = false;
00035 
00036 typedef struct {
00037     uint32_t info_type;
00038     void *   p_data;
00039     int32_t  result;
00040 } mail_t;
00041 Mail<mail_t, (AUDIO_IN_BUF_NUM + 2)> mail_box;
00042 
00043 static Thread audioInTask(osPriorityNormal, 1024 * 8);
00044 //4 bytes aligned! No cache memory
00045 #if defined(__ICCARM__)
00046 #pragma data_alignment=4
00047 static uint8_t audio_in_buf[AUDIO_IN_BUF_NUM][AUDIO_IN_BUF_SIZE]@ ".mirrorram";
00048 #pragma data_alignment=4
00049 static uint8_t audio_out_buf[AUDIO_OUT_BUF_NUM][AUDIO_OUT_BUF_SIZE]@ ".mirrorram";
00050 #else
00051 static uint8_t audio_in_buf[AUDIO_IN_BUF_NUM][AUDIO_IN_BUF_SIZE]__attribute((section("NC_BSS"),aligned(4)));
00052 static uint8_t audio_out_buf[AUDIO_OUT_BUF_NUM][AUDIO_OUT_BUF_SIZE]__attribute((section("NC_BSS"),aligned(4)));
00053 #endif
00054 
00055 // wav file header
00056 static const char wav_header_tbl[] = {
00057     0x52,0x49,0x46,0x46,0x00,0x00,0x00,0x00,0x57,0x41,0x56,0x45,0x66,0x6D,0x74,0x20,
00058     0x10,0x00,0x00,0x00,0x01,0x00,0x02,0x00,0x80,0xBB,0x00,0x00,0x00,0xEE,0x02,0x00,
00059     0x04,0x00,0x10,0x00,0x64,0x61,0x74,0x61,0x00,0x00,0x00,0x00
00060 };
00061 
00062 #if MBED_CONF_APP_LCD
00063 #include "EasyAttach_CameraAndLCD.h"
00064 
00065 #define FRAME_BUFFER_STRIDE    (((LCD_PIXEL_WIDTH * 2) + 31u) & ~31u)
00066 #define FRAME_BUFFER_HEIGHT    (LCD_PIXEL_HEIGHT)
00067 #if defined(__ICCARM__)
00068 #pragma data_alignment=32
00069 static uint8_t user_frame_buffer0[FRAME_BUFFER_STRIDE * FRAME_BUFFER_HEIGHT]@ ".mirrorram";
00070 #else
00071 static uint8_t user_frame_buffer0[FRAME_BUFFER_STRIDE * FRAME_BUFFER_HEIGHT]__attribute((section("NC_BSS"),aligned(32)));
00072 #endif
00073 DisplayBase Display;
00074 
00075 static void Start_LCD_Display(void) {
00076     DisplayBase::rect_t rect;
00077 
00078     memset(user_frame_buffer0, 0xFF, sizeof(user_frame_buffer0));
00079 
00080     rect.vs = 0;
00081     rect.vw = LCD_PIXEL_HEIGHT;
00082     rect.hs = 0;
00083     rect.hw = LCD_PIXEL_WIDTH;
00084     Display.Graphics_Read_Setting(
00085         DisplayBase::GRAPHICS_LAYER_0,
00086         (void *)user_frame_buffer0,
00087         FRAME_BUFFER_STRIDE,
00088         DisplayBase::GRAPHICS_FORMAT_RGB565,
00089         DisplayBase::WR_RD_WRSWA_32_16BIT,
00090         &rect
00091     );
00092     Display.Graphics_Start(DisplayBase::GRAPHICS_LAYER_0);
00093 
00094     Thread::wait(50);
00095     EasyAttach_LcdBacklight(true);
00096 }
00097 
00098 static void disp_audio_wave(int16_t * p_data, int32_t size, uint32_t color) {
00099     uint16_t * p_bottom_left_pos = (uint16_t *)&user_frame_buffer0[FRAME_BUFFER_STRIDE * (FRAME_BUFFER_HEIGHT - 1)];
00100     uint16_t * p_frame_buf;
00101     uint32_t x = 0;
00102     uint32_t data_pos;
00103     uint32_t data_pos_last = ((p_data[0] + 0x8000ul) >> 8) + 8;
00104     int loop_num;
00105 
00106     if (size < 0) {
00107         return;
00108     }
00109 
00110     memset(user_frame_buffer0, 0xFF, sizeof(user_frame_buffer0));
00111     for (int i = 0; i < size; i += 2) {
00112         data_pos = ((p_data[i] + 0x8000ul) >> 8) + 8;
00113         p_frame_buf = &p_bottom_left_pos[x];
00114 
00115         if (data_pos == data_pos_last) {
00116             loop_num = 3;
00117             p_frame_buf -= ((data_pos - 1) * LCD_PIXEL_WIDTH);
00118         } else if (data_pos > data_pos_last) {
00119             loop_num = data_pos - data_pos_last + 2;
00120             p_frame_buf -= (data_pos_last * LCD_PIXEL_WIDTH);
00121         } else {
00122             loop_num = data_pos_last - data_pos + 2;
00123             p_frame_buf -= ((data_pos - 1) * LCD_PIXEL_WIDTH);
00124         }
00125 
00126         for (int j = 0; j < loop_num; j++) {
00127             *p_frame_buf = color;
00128             p_frame_buf -= LCD_PIXEL_WIDTH;
00129         }
00130         data_pos_last = data_pos;
00131 
00132         x++;
00133         if (x >= LCD_PIXEL_WIDTH) {
00134             break;
00135         }
00136     }
00137 }
00138 
00139 
00140 static void callback_audio_write_end(void * p_data, int32_t result, void * p_app_data) {
00141     disp_audio_wave((int16_t *)p_data, result / 2, 0x07E0); // Green
00142 }
00143 #endif // MBED_CONF_APP_LCD
00144 
00145 static void send_mail(uint32_t info_type, void * p_data, int32_t result) {
00146     mail_t *mail = mail_box.alloc();
00147 
00148     if (mail != NULL) {
00149         mail->info_type = info_type;
00150         mail->p_data    = p_data;
00151         mail->result    = result;
00152         mail_box.put(mail);
00153     }
00154 }
00155 
00156 static void rec_start(void) {
00157     send_mail(INFO_TYPE_OPEN, NULL, 0);
00158 }
00159 
00160 static void rec_stop(void) {
00161     send_mail(INFO_TYPE_CLOSE, NULL, 0);
00162 }
00163 
00164 static void play_start(void) {
00165     play_req = true;
00166 }
00167 
00168 
00169 
00170 static void KNN(char *file_name, int dat_size)
00171 {
00172     double *cal_dat;
00173     double *com_dat;
00174     int record;
00175     int NUM_LIB=119;
00176     int class_num;
00177     double knn=10000000000;
00178     double temp=0;
00179     com_dat=(double*)malloc(sizeof(double)*dat_size);
00180     
00181     FILE *input_res,*compare_res;
00182     char *lib_name;
00183     input_res=fopen(file_name,"rb");
00184     for(int i=0;i<dat_size;i++)
00185     {
00186         fscanf(input_res,"lf",&cal_dat[i]);
00187     }
00188     fclose(input_res);
00189     
00190     for(int i=0;i<NUM_LIB;i++)
00191     {
00192         temp=0;
00193         sprintf(lib_name,"sample%03d.dat",i);
00194         compare_res=fopen(lib_name,"w");
00195         for(int i=0;i<dat_size;i++){
00196             fscanf(compare_res,"lf",&com_dat[i]);
00197         }
00198         for(int i=0;i<dat_size;i++)
00199         {
00200             temp+=pow((cal_dat[i]-com_dat[i]),2);
00201         }
00202         if (temp<knn)
00203         {
00204             knn=temp;
00205             record=i;
00206         }
00207     }
00208     if(0<record||record<=25||115<record||record<=119)
00209     //output is bird
00210     {
00211     class_num=1;
00212     led1=!led1;
00213                         }
00214     //output is monkey
00215     else if(25<record||record<=54)
00216     {
00217     class_num=2;
00218     led2=!led2;}
00219     //output is cat
00220     else if(54<record||record<=85||record==115)
00221     {
00222     class_num=3;
00223     led3=!led3;
00224                         }
00225     //output is dog
00226     else if(85<record||record<=114)
00227     {class_num=4;
00228      led4=!led4;
00229                         }
00230 
00231 }
00232 
00233 
00234 
00235 static void callback_audio_read_end(void * p_data, int32_t result, void * p_app_data) {
00236 #if MBED_CONF_APP_LCD
00237     if (led_play == 0) {
00238         uint32_t color;
00239 
00240         if (led_rec == 0) {
00241             color = 0x001F; // Blue
00242         } else {
00243             color = 0xF800; // Red
00244         }
00245         disp_audio_wave((int16_t *)p_data, result / 2, color);
00246     }
00247 #endif
00248     send_mail(INFO_TYPE_WRITE_DATA, p_data, result);
00249 }
00250 
00251 static void wire_data_4byte(uint32_t data, FILE * fp) {
00252     char work_buf[4];
00253 
00254     work_buf[0] = (uint8_t)(data >> 0);
00255     work_buf[1] = (uint8_t)(data >> 8);
00256     work_buf[2] = (uint8_t)(data >> 16);
00257     work_buf[3] = (uint8_t)(data >> 24);
00258     fwrite(work_buf, sizeof(char), 4, fp);
00259 }
00260 
00261 void audio_in_task(void) {
00262     FILE * wav_fp = NULL;
00263     uint32_t pcm_size = 0;
00264     rbsp_data_conf_t audio_read_data  = {&callback_audio_read_end, NULL};
00265 
00266     // Read buffer setting
00267     for (uint32_t i = 0; i < AUDIO_IN_BUF_NUM; i++) {
00268         if (audio.read(audio_in_buf[i], AUDIO_IN_BUF_SIZE, &audio_read_data) < 0) {
00269             printf("read error\n");
00270         }
00271     }
00272 
00273     while (1) {
00274         osEvent evt = mail_box.get();
00275         if (evt.status == osEventMail) {
00276             mail_t *mail = (mail_t *)evt.value.p;
00277 
00278             switch (mail->info_type) {
00279                 case INFO_TYPE_OPEN:
00280                     wav_fp = fopen(FINE_PATH, "wb");
00281                     if (wav_fp != NULL) {
00282                         led_rec  = 1;  // REC start
00283                         pcm_size = 0;
00284                         fwrite(wav_header_tbl, sizeof(char), sizeof(wav_header_tbl), wav_fp);
00285                     }
00286                     break;
00287 
00288                 case INFO_TYPE_CLOSE:
00289                     if (wav_fp != NULL) {
00290                         // Set "RIFF" ChunkSize
00291                         fseek(wav_fp, 4, SEEK_SET);
00292                         wire_data_4byte(sizeof(wav_header_tbl) - 8 + pcm_size, wav_fp);
00293                         // Set SampleRate
00294                         fseek(wav_fp, 24, SEEK_SET);
00295                         wire_data_4byte(SAMPLE_RATE, wav_fp);
00296                         // Set ByteRate
00297                         wire_data_4byte(SAMPLE_RATE * 2 * 2, wav_fp);
00298                         // Set "data" ChunkSize
00299                         fseek(wav_fp, 40, SEEK_SET);
00300                         wire_data_4byte(pcm_size, wav_fp);
00301                         fclose(wav_fp);
00302                         wav_fp = NULL;
00303                         led_rec = 0;  // REC end
00304 #if !defined(TARGET_GR_LYCHEE)
00305                         play_start();
00306 #endif
00307                     }
00308                     break;
00309 
00310                 case INFO_TYPE_WRITE_DATA:
00311                     if ((mail->result > 0) && (wav_fp != NULL)) {
00312                         pcm_size += mail->result;
00313                         fwrite(mail->p_data, sizeof(char), mail->result, wav_fp);
00314                     }
00315                     audio.read(mail->p_data, AUDIO_IN_BUF_SIZE, &audio_read_data);     // Resetting read buffer
00316                     break;
00317 
00318                 default:
00319                     // do nothing
00320                     break;
00321             }
00322             mail_box.free(mail);
00323         }
00324     }
00325 }
00326 
00327 int main() {
00328     
00329 int count=0;
00330 
00331 #if MBED_CONF_APP_LCD
00332     rbsp_data_conf_t audio_write_data = {&callback_audio_write_end, NULL};
00333 
00334     EasyAttach_Init(Display);
00335     Start_LCD_Display();
00336 #else
00337     rbsp_data_conf_t audio_write_data = {NULL, NULL};
00338 #endif
00339 
00340     // Microphone
00341     audio.micVolume(0.50);
00342     audio.outputVolume(0.50, 0.50);
00343     audio.power(true);
00344     audio.frequency(SAMPLE_RATE);
00345 
00346     SdUsbConnect storage(MOUNT_NAME);
00347     audioInTask.start(callback(audio_in_task));
00348 
00349     // button setting
00350     button_0.fall(&rec_start);
00351     button_0.rise(&rec_stop);
00352 #if defined(TARGET_GR_LYCHEE)
00353     button_1.fall(&play_start);
00354 #endif
00355 
00356     while (1) {
00357         storage.wait_connect();
00358 
00359         // Audio playback
00360         if (play_req != false) {
00361             while (led_rec == 1) {
00362                 Thread::wait(10); // Wait write end
00363             }
00364 
00365             size_t read_size = AUDIO_OUT_BUF_SIZE;
00366             uint32_t index = 0;
00367 
00368             play_req = false;
00369 #if(0)
00370             //KNN(FINE_PATH,);
00371             char test_name[32];
00372             sprintf(test_name,"/"MOUNT_NAME"/sample%03d.dat",count++);
00373             FILE *test_lib=fopen(test_name,"w");
00374              fseek(test_lib, sizeof(wav_header_tbl), SEEK_SET);
00375                 while (read_size == AUDIO_OUT_BUF_SIZE) {
00376                     read_size = fread(audio_out_buf[index], sizeof(char), AUDIO_OUT_BUF_SIZE, test_lib);
00377             fclose(test_name);
00378 #else
00379             led_play = 1;
00380             FILE * fp_rb = fopen(FINE_PATH, "rb");
00381 
00382             char test_name[32];
00383  //           sprintf(test_name,"/"MOUNT_NAME"/sample%03d.dat",count++);
00384             sprintf(test_name,"/"MOUNT_NAME"/recogniaze.dat");
00385             FILE *test_lib=fopen(test_name,"w");
00386 
00387 
00388             if (fp_rb != NULL) {
00389                 fseek(fp_rb, sizeof(wav_header_tbl), SEEK_SET);
00390                 while (read_size == AUDIO_OUT_BUF_SIZE) {
00391                     read_size = fread(audio_out_buf[index], sizeof(char), AUDIO_OUT_BUF_SIZE, fp_rb);
00392                     
00393    //                audio.write(audio_out_buf[index], read_size, &audio_write_data);
00394 
00395                    fwrite(audio_out_buf[index], sizeof(char), read_size, test_lib);
00396                    
00397 
00398                     
00399                     index++;
00400                     if (index >= AUDIO_OUT_BUF_NUM) {
00401                         index = 0;
00402                     }
00403                 }
00404                 fclose(fp_rb);
00405                 fclose(test_lib);
00406                 KNN("/"MOUNT_NAME"/recogniaze.dat",5000);
00407                
00408  //               Thread::wait(AUDIO_OUT_WAIT);
00409             }
00410             led_play = 0;
00411 #endif
00412         }
00413         Thread::wait(100);
00414               
00415 
00416     }
00417 }
00418