sample and play see http://mbed.org/users/okini3939/notebook/I2S_TLV320AIC23B/

Dependencies:   I2SSlave TLV320 mbed

Fork of i2s_audio_echo by Suga koubou

main.cpp

Committer:
okini3939
Date:
2012-12-11
Revision:
1:2aeba027f61e
Parent:
0:68f7b69ecca0

File content as of revision 1:2aeba027f61e:

#include "mbed.h"
#include "TLV320.h"
#include "PRAM.h"

#define BLOCK_SIZE 64
#define BLOCK_NUM 3

#define MODE_STOP 0
#define MODE_REC 1
#define MODE_PLAY 2

Serial pc(USBTX, USBRX);

SPI _spi(p11, p12, p13);
PRAM memory(_spi, p14); // SPI PRAM

TLV320 audio(p9, p10, 0x34, p5, p6, p7, p8, p16); // I2S Codec

DigitalOut led1(LED1), led2(LED2), led3(LED3), led4(LED4);
DigitalIn play(p28), rec(p29), stop(p30);

volatile int mode = MODE_STOP;
volatile int addr_r, num_r;
volatile int addr_w, num_w;
int buf_r[BLOCK_NUM][BLOCK_SIZE / 4];
int buf_w[BLOCK_NUM][BLOCK_SIZE / 4];

volatile int mem_r, mem_w;
volatile int flg_r = -1, flg_w = -1;

extern "C" void HardFault_Handler() {
    register unsigned int _msp __asm("msp");
    printf("Hard Fault! address: %08x\r\n", *((unsigned int *)(_msp + 24)));
    printf("buf: %d %d %d\r\n", num_w, addr_w, mem_w);
    exit(-1);
}  

// interrupt TLV320 send/recv
void isr_audio () {
    int i;
    int buf[4];

    // I2S input
    audio.read();

    switch (mode) {
    case MODE_STOP:
        for (i = 0; i < 4; i ++) {
            buf[i] = audio.rxBuffer[i];
        }
        audio.write(buf, 0, 4);
        break;
        
    case MODE_REC:
        for (i = 0; i < 4; i ++) {
            buf[i] = audio.rxBuffer[i];
            buf_w[num_w][addr_w] = buf[i];
            addr_w ++;
        }
        if (addr_w >= BLOCK_SIZE / 4) {
            addr_w = 0;
            flg_w = num_w;
            num_w ++;
            if (num_w >= BLOCK_NUM) {
                num_w = 0;
            }
            led3 = 1;
        }
        audio.write(buf, 0, 4);
        break;

    case MODE_PLAY:
        for (i = 0; i < 4; i ++) {
            buf[i] = buf_r[num_r][addr_r];
            addr_r ++;
        }
        if (addr_r >= BLOCK_SIZE / 4) {
            addr_r = 0;
            num_r ++;
            if (num_r >= BLOCK_NUM) {
                num_r = 0;
            }
            flg_r = num_r + 1 < BLOCK_NUM ? num_r + 1 : 0;
            led4 = 1;
        }
        audio.write(buf, 0, 4);
        break;
    }

}

int main() {

    pc.baud(115200 * 8);
    rec.mode(PullUp);
    play.mode(PullUp);
    stop.mode(PullUp);

    audio.power(0x02); // mic off
    audio.outputVolume(1, 1); // headphone off
    audio.inputVolume(0.7, 0.7);
    audio.frequency(44100);
    audio.attach(&isr_audio);
    audio.start(RECEIVE);
    printf("Audio ready\r\n");
    led1 = 1;

    for (;;) {
        if (rec == 0 && mode == MODE_STOP) {
            printf("rec\r\n");
            addr_w = 0; num_w = 0;
            mem_w = 0;
            flg_w = -1;
            led2 = 1;
            mode = MODE_REC;
        }
        if (play == 0 && mode == MODE_STOP) {
            printf("play\r\n");
            addr_r = 0; num_r = 0;
            mem_r = 0;
            flg_r = 0;
            led2 = 1;
            mode = MODE_PLAY;
        }
        if (stop == 0 && mode != MODE_STOP) {
            printf("stop\r\n");
            led2 = 0;
            mode = MODE_STOP;
        }

        if (mode == MODE_PLAY) {
            if (mem_r >= mem_w) {
                printf("end\r\n");
                led2 = 0;
                mode = MODE_STOP;
            }
        }
        
        if (flg_w >= 0) {
//            printf("W %d %d\r\n", flg_w, mem_w);
            memory.write(BLOCK_SIZE * mem_w, (char *)buf_w[flg_w], BLOCK_SIZE);
            mem_w ++;
            flg_w = -1;
            led3 = 0;
        }
        if (flg_r >= 0) {
//            printf("R %d %d\r\n", flg_r, mem_r);
            memory.read(BLOCK_SIZE * mem_r, (char *)buf_r[flg_r], BLOCK_SIZE);
            mem_r ++;
            flg_r = -1;
            led4 = 0;
        }
    }

    audio.stop();
    printf("exit\r\n");
}