Could anybody give me an example of configuring microcontroller to use with aic20k codec (dma in scatter-gather mode, 2 channels)?
This thread has been locked.
If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.
There are some examples
#define SLAVE_ADDRESS 0x40 // slave address for I2C bus uint8_t cof_regs[14]; // array just for reading of cofidec's registers // item for the one register of cofidec typedef struct { uint32_t cof; // channel uint32_t reg; // number of register uint32_t val; // value } T_COF_CONF; // configuration: T_COF_CONF conf[] = { {0x40, 3, 0x01}, {0x40, 5, 0x0E}, {0x40, 6, 0x04}, {0x41, 1, 0x49}, {0x41, 2, 0x20}, {0x41, 3, 0x01}, {0x41, 3, 0x47}, {0x41, 3, 0x80}, {0x41, 3, 0xC0}, {0x41, 4, 0x99}, {0x41, 4, 0x29}, {0x41, 5, 0x0E}, {0x41, 5, 0x40}, {0x41, 5, 0xBF}, {0x41, 5, 0xC0}, {0x41, 6, 0x04}, {0x41, 6, 0x82} }; // cofidec's reset subroutine void cof_reset(bool state) { if(state) GPIOPinWrite(GPIO_PORTB_BASE, GPIO_PIN_5, GPIO_PIN_5); else GPIOPinWrite(GPIO_PORTB_BASE, GPIO_PIN_5, 0); } // ----(beg)----------------------------- I2C section ----------------------------------- // just for completion transaction on errors void i2c_errors_process(uint32_t error) { I2CMasterControl(I2C1_MASTER_BASE, I2C_MASTER_CMD_BURST_RECEIVE_ERROR_STOP); while(I2CMasterBusy(I2C1_MASTER_BASE)); } // initial function void i2c_init() { SysCtlPeripheralEnable(SYSCTL_PERIPH_I2C1); SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOA); // Configure the pin muxing for I2C0 functions on port A6 and A7. // This step is not necessary if your part does not support pin muxing. GPIOPinConfigure(GPIO_PA6_I2C1SCL); GPIOPinConfigure(GPIO_PA7_I2C1SDA); // Select the I2C function for these pins. This function will also // configure the GPIO pins pins for I2C operation, setting them to // open-drain operation with weak pull-ups GPIOPinTypeI2CSCL(GPIO_PORTA_BASE, GPIO_PIN_6); GPIOPinTypeI2C(GPIO_PORTA_BASE, GPIO_PIN_7); // Enable and initialize the I2C0 master module. Use the system clock for // the I2C0 module. The last parameter sets the I2C data transfer rate. // If false the data rate is set to 100kbps and if true the data rate will // be set to 400kbps. I2CMasterInitExpClk(I2C1_MASTER_BASE, SysCtlClockGet(), false); // Enable the I2C0 master module I2CMasterEnable(I2C1_MASTER_BASE); // Tell the master module what address it will place on the bus when // communicating with the slave I2CMasterSlaveAddrSet(I2C1_MASTER_BASE, SLAVE_ADDRESS, false); } // write full set of configuration words into cofidec void i2c_write_reg_device(uint8_t device, uint8_t reg, uint8_t data) { I2CMasterSlaveAddrSet(I2C1_MASTER_BASE, device, false); // set WRITE bit! I2CMasterDataPut(I2C1_MASTER_BASE, reg); I2CMasterControl(I2C1_MASTER_BASE, I2C_MASTER_CMD_BURST_SEND_START); while(I2CMasterBusy(I2C1_MASTER_BASE)); if(I2CMasterErr(I2C1_MASTER_BASE) != I2C_MASTER_ERR_NONE) { i2c_errors_process(1); } I2CMasterDataPut(I2C1_MASTER_BASE, data); I2CMasterControl(I2C1_MASTER_BASE, I2C_MASTER_CMD_BURST_SEND_FINISH); while(I2CMasterBusy(I2C1_MASTER_BASE)); if(I2CMasterErr(I2C1_MASTER_BASE) != I2C_MASTER_ERR_NONE) { i2c_errors_process(1); } } // just for reading registers int i2c_read_reg(uint8_t reg, uint8_t *data) { I2CMasterSlaveAddrSet(I2C1_MASTER_BASE, SLAVE_ADDRESS, false); // set WRITE bit! I2CMasterDataPut(I2C1_MASTER_BASE, reg); I2CMasterControl(I2C1_MASTER_BASE, I2C_MASTER_CMD_SINGLE_SEND); while(I2CMasterBusy(I2C1_MASTER_BASE)); if(I2CMasterErr(I2C1_MASTER_BASE) != I2C_MASTER_ERR_NONE) { i2c_errors_process(1); return -1; } I2CMasterSlaveAddrSet(I2C1_MASTER_BASE, SLAVE_ADDRESS, true); // set WRITE bit! I2CMasterControl(I2C1_MASTER_BASE, I2C_MASTER_CMD_SINGLE_RECEIVE); while(I2CMasterBusy(I2C1_MASTER_BASE)); if(I2CMasterErr(I2C1_MASTER_BASE) != I2C_MASTER_ERR_NONE) { i2c_errors_process(2); } *data = I2CMasterDataGet(I2C1_MASTER_BASE); return 0; } // ----(end)----------------------------- I2C section ----------------------------------- // init cofidec void cof_init() { int i; cof_reset(0); {uint32_t delay = 1000000; while(delay--);} cof_reset(1); {uint32_t delay = 1000000; while(delay--);} for(i=0; i<sizeof(conf)/sizeof(T_COF_CONF); i++) { i2c_write_reg_device(conf[i].cof, conf[i].reg, conf[i].val); } {uint32_t delay = 1000; while(delay--);} } // if you want you can read all registers back into the array cof_regs[] void read_cof_regs() { i2c_read_reg(1, &cof_regs[0]); i2c_read_reg(2, &cof_regs[1]); i2c_read_reg(3, &cof_regs[2]); i2c_read_reg(3, &cof_regs[3]); i2c_read_reg(3, &cof_regs[4]); i2c_read_reg(3, &cof_regs[5]); //i2c_read_regs(3, &cof_regs[5], 2); //i2c_read_regs(4, &cof_regs[7], 2); i2c_read_reg(4, &cof_regs[6]); //i2c_read_reg(5, &cof_regs[7]); i2c_read_reg(5, &cof_regs[7]); i2c_read_reg(5, &cof_regs[8]); i2c_read_reg(5, &cof_regs[9]); i2c_read_reg(5, &cof_regs[10]); //i2c_read_regs(5, &cof_regs[11], 2); i2c_read_reg(6, &cof_regs[11]); i2c_read_reg(6, &cof_regs[12]); } // ---------------------- the part of the main initialization ---------------- void HwSetup(void) { // cofidec reset pin SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOB); GPIOPinTypeGPIOOutput(GPIO_PORTB_BASE, GPIO_PIN_5); // I2C init i2c_init(); // cofidec init cof_init(); // I2S init spi_init(); } // ---(beg)-------------------------- I2S section ------------------------------- // ---(end)-------------------------- I2S section -------------------------------
#include <stdint.h> #include <stdbool.h> #include <string.h> #include "inc/hw_types.h" #include "inc/hw_memmap.h" #include "inc/hw_ints.h" #include "inc/hw_ssi.h" #include "driverlib/sysctl.h" #include "driverlib/gpio.h" #include "driverlib/ssi.h" #include "driverlib/interrupt.h" #include "driverlib/pin_map.h" #include "driverlib/udma.h" #include "spi.h" #include "bsp.h" #include "system.h" #pragma data_alignment=1024 unsigned char ucControlTable[1024]; // you can use these samples to output sinus through your cofidec /*int16_t sin_buf[VOC_BUF_LEN] = { 0, 6180, 11756, 16180, 19021, 20000, 19021, 16180, 11756, 6180, 0, -6180, -11756, -16180, -19021, -20000, -19021, -16180, -11756, -6180, 0, 6180, 11756, 16180, 19021, 20000, 19021, 16180, 11756, 6180, 0, -6180, -11756, -16180, -19021, -20000, -19021, -16180, -11756, -6180, 0, 6180, 11756, 16180, 19021, 20000, 19021, 16180, 11756, 6180, 0, -6180, -11756, -16180, -19021, -20000, -19021, -16180, -11756, -6180, 0, 6180, 11756, 16180, 19021, 20000, 19021, 16180, 11756, 6180, 0, -6180, -11756, -16180, -19021, -20000, -19021, -16180, -11756, -6180, 0, 6180, 11756, 16180, 19021, 20000, 19021, 16180, 11756, 6180, 0, -6180, -11756, -16180, -19021, -20000, -19021, -16180, -11756, -6180, 0, 6180, 11756, 16180, 19021, 20000, 19021, 16180, 11756, 6180, 0, -6180, -11756, -16180, -19021, -20000, -19021, -16180, -11756, -6180, 0, 6180, 11756, 16180, 19021, 20000, 19021, 16180, 11756, 6180, 0, -6180, -11756, -16180, -19021, -20000, -19021, -16180, -11756, -6180, 0, 6180, 11756, 16180, 19021, 20000, 19021, 16180, 11756, 6180, 0, -6180, -11756, -16180, -19021, -20000, -19021, -16180, -11756, -6180 };*/ int16_t voc_buf_rx[16*VOC_BUF_LEN]; int16_t *p_voc_buf_rx = voc_buf_rx; int16_t *p_voc_buf_end = voc_buf_rx + 16*VOC_BUF_LEN; int16_t voc_buf_rx_1[2*VOC_BUF_LEN]; int16_t voc_buf_tx_1[2*VOC_BUF_LEN]; int16_t voc_buf_rx_2[2*VOC_BUF_LEN]; int16_t voc_buf_tx_2[2*VOC_BUF_LEN]; int16_t proc_buf[2][VOC_BUF_LEN]; int i_rd = 0, i_wr = 0; void spi_init(void) { unsigned long delay; memset(voc_buf_rx_1, 0, sizeof(voc_buf_rx_1)); memset(voc_buf_rx_2, 0, sizeof(voc_buf_rx_2)); SysCtlPeripheralEnable(SYSCTL_PERIPH_SSI3); SysCtlPeripheralEnable(SYSCTL_PERIPH_UDMA); SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOD); uDMAEnable(); uDMAControlBaseSet(ucControlTable); GPIOPinConfigure(GPIO_PD0_SSI3CLK); GPIOPinConfigure(GPIO_PD1_SSI3FSS); GPIOPinConfigure(GPIO_PD2_SSI3RX); GPIOPinConfigure(GPIO_PD3_SSI3TX); GPIOPinTypeSSI(GPIO_PORTD_BASE, GPIO_PIN_0 | GPIO_PIN_1 | GPIO_PIN_2 | GPIO_PIN_3); GPIOPadConfigSet(GPIO_PORTD_BASE, GPIO_PIN_2, GPIO_STRENGTH_8MA, GPIO_PIN_TYPE_STD); for(delay=0; delay<10000; delay++); SSIConfigSetExpClk( SSI3_BASE, 80000000UL, SSI_FRF_TI, SSI_MODE_SLAVE, 10000000, 16); uDMAChannelDisable(UDMA_CHANNEL_SSI3RX); uDMAChannelAssign(UDMA_CH14_SSI3RX); uDMAChannelDisable(UDMA_CHANNEL_SSI3TX); uDMAChannelAssign(UDMA_CH15_SSI3TX); // Init DMA-channel for SPI-RX uDMAChannelAttributeEnable( UDMA_CHANNEL_SSI3RX, UDMA_ATTR_ALTSELECT); uDMAChannelAttributeDisable( UDMA_CHANNEL_SSI3RX, UDMA_ATTR_USEBURST | UDMA_ATTR_HIGH_PRIORITY | UDMA_ATTR_REQMASK); // Init DMA-channel for SPI-TX uDMAChannelAttributeEnable( UDMA_CHANNEL_SSI3TX, UDMA_ATTR_ALTSELECT); uDMAChannelAttributeDisable( UDMA_CHANNEL_SSI3TX, UDMA_ATTR_USEBURST | UDMA_ATTR_HIGH_PRIORITY | UDMA_ATTR_REQMASK); uDMAChannelControlSet(UDMA_CHANNEL_SSI3RX | UDMA_PRI_SELECT, UDMA_SIZE_16 | UDMA_SRC_INC_NONE | UDMA_DST_INC_16 | UDMA_ARB_1); uDMAChannelControlSet(UDMA_CHANNEL_SSI3RX | UDMA_ALT_SELECT, UDMA_SIZE_16 | UDMA_SRC_INC_NONE | UDMA_DST_INC_16 | UDMA_ARB_1); uDMAChannelTransferSet(UDMA_CHANNEL_SSI3RX | UDMA_PRI_SELECT, UDMA_MODE_PINGPONG, (void*)(SSI3_BASE + SSI_O_DR), (void*)voc_buf_rx_1, VOC_BUF_LEN); uDMAChannelTransferSet(UDMA_CHANNEL_SSI3RX | UDMA_ALT_SELECT, UDMA_MODE_PINGPONG, (void*)(SSI3_BASE + SSI_O_DR), (void*)voc_buf_rx_2, VOC_BUF_LEN); uDMAChannelControlSet(UDMA_CHANNEL_SSI3TX | UDMA_PRI_SELECT, UDMA_SIZE_16 | UDMA_SRC_INC_16 | UDMA_DST_INC_NONE | UDMA_ARB_1); uDMAChannelControlSet(UDMA_CHANNEL_SSI3TX | UDMA_ALT_SELECT, UDMA_SIZE_16 | UDMA_SRC_INC_16 | UDMA_DST_INC_NONE | UDMA_ARB_1); uDMAChannelTransferSet(UDMA_CHANNEL_SSI3TX | UDMA_PRI_SELECT, UDMA_MODE_PINGPONG, (void*)voc_buf_tx_1, (void*)(SSI3_BASE + SSI_O_DR), VOC_BUF_LEN); uDMAChannelTransferSet(UDMA_CHANNEL_SSI3TX | UDMA_ALT_SELECT, UDMA_MODE_PINGPONG, (void*)voc_buf_tx_2, (void*)(SSI3_BASE + SSI_O_DR), VOC_BUF_LEN); uDMAChannelEnable(UDMA_CHANNEL_SSI3RX | UDMA_PRI_SELECT); uDMAChannelEnable(UDMA_CHANNEL_SSI3TX | UDMA_PRI_SELECT); SSIDMAEnable(SSI3_BASE, SSI_DMA_RX | SSI_DMA_TX); SSIEnable(SSI3_BASE); SSIIntClear(SSI3_BASE, SSI_DMA_RX | SSI_DMA_TX); SSIIntEnable(SSI3_BASE, SSI_DMA_RX | SSI_DMA_TX); IntEnable(INT_SSI3); } void store_buf(int16_t *data, int size) { if((p_voc_buf_rx + size) < p_voc_buf_end) { memcpy(p_voc_buf_rx, data, size*sizeof(int16_t)); p_voc_buf_rx += size; } else { asm(" nop"); } } void SSI3_Handler(void) { uint32_t ui32Status; uint32_t ui32Mode[4]; extern void put_semaphore(int16_t *buf); extern void put_semaphore_dac(int16_t *buf); ui32Status = SSIIntStatus(SSI3_BASE, 1); SSIIntClear(SSI3_BASE, ui32Status); ui32Mode[0] = uDMAChannelModeGet(UDMA_CHANNEL_SSI3RX | UDMA_PRI_SELECT); ui32Mode[1] = uDMAChannelModeGet(UDMA_CHANNEL_SSI3RX | UDMA_ALT_SELECT); ui32Mode[2] = uDMAChannelModeGet(UDMA_CHANNEL_SSI3TX | UDMA_PRI_SELECT); ui32Mode[3] = uDMAChannelModeGet(UDMA_CHANNEL_SSI3TX | UDMA_ALT_SELECT); if(ui32Mode[0] == UDMA_MODE_STOP) // ���� ����������� ���������� �� ������ 1-��� ������... { uDMAChannelTransferSet(UDMA_CHANNEL_SSI3RX | UDMA_PRI_SELECT, UDMA_MODE_PINGPONG, (void*)(SSI3_BASE + SSI_O_DR), (void*)voc_buf_rx_1, VOC_BUF_LEN); put_semaphore(voc_buf_rx_1); } if(ui32Mode[1] == UDMA_MODE_STOP) // ���� ����������� ���������� �� ������ 2-��� ������... { uDMAChannelTransferSet(UDMA_CHANNEL_SSI3RX | UDMA_ALT_SELECT, UDMA_MODE_PINGPONG, (void*)(SSI3_BASE + SSI_O_DR), (void*)voc_buf_rx_2, VOC_BUF_LEN); put_semaphore(voc_buf_rx_2); } if(ui32Mode[2] == UDMA_MODE_STOP) // ���� ����������� ���������� �� �������� 1-��� ������... { uDMAChannelTransferSet(UDMA_CHANNEL_SSI3TX | UDMA_PRI_SELECT, UDMA_MODE_PINGPONG, (void*)voc_buf_tx_1, (void*)(SSI3_BASE + SSI_O_DR), VOC_BUF_LEN); put_semaphore_dac(voc_buf_tx_1); } if(ui32Mode[3] == UDMA_MODE_STOP) // ���� ����������� ���������� �� �������� 2-��� ������... { uDMAChannelTransferSet(UDMA_CHANNEL_SSI3TX | UDMA_ALT_SELECT, UDMA_MODE_PINGPONG, (void*)voc_buf_tx_2, (void*)(SSI3_BASE + SSI_O_DR), VOC_BUF_LEN); put_semaphore_dac(voc_buf_tx_2); } if(ui32Mode[0] != ui32Mode[1]) { asm(" nop"); } }