|
@ -1,11 +1,27 @@ |
|
|
#include <string.h> |
|
|
#include <string.h> |
|
|
|
|
|
#include <stdlib.h> |
|
|
#include "platform_internal.h" |
|
|
#include "platform_internal.h" |
|
|
#include "spi.h" |
|
|
#include "spi.h" |
|
|
|
|
|
|
|
|
|
|
|
#define TXBUF_SIZE (1024) |
|
|
|
|
|
#define RXBUF_SIZE (1024) |
|
|
|
|
|
|
|
|
typedef struct __spi_handle *spi_t; |
|
|
typedef struct __spi_handle *spi_t; |
|
|
struct __spi_handle { |
|
|
struct __spi_handle { |
|
|
MCBSP_Handle spi; |
|
|
MCBSP_Handle spi; |
|
|
int bits; |
|
|
int bits; |
|
|
|
|
|
|
|
|
|
|
|
/* tx */ |
|
|
|
|
|
EDMA_Handle xh; |
|
|
|
|
|
void (*xnotify)(void *args); |
|
|
|
|
|
void *xargs; |
|
|
|
|
|
char xbuf[TXBUF_SIZE]; |
|
|
|
|
|
|
|
|
|
|
|
/* rx */ |
|
|
|
|
|
EDMA_Handle rh; |
|
|
|
|
|
void (*rnotify)(void *args); |
|
|
|
|
|
void *rargs; |
|
|
|
|
|
char rbuf[RXBUF_SIZE]; |
|
|
}; |
|
|
}; |
|
|
|
|
|
|
|
|
static struct __spi_handle __spi_devs[_MCBSP_PORT_CNT]; |
|
|
static struct __spi_handle __spi_devs[_MCBSP_PORT_CNT]; |
|
@ -15,6 +31,33 @@ void spi_lowlevel_init() |
|
|
memset(__spi_devs, 0, sizeof __spi_devs); |
|
|
memset(__spi_devs, 0, sizeof __spi_devs); |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
static spi_t __find_spi_with_xtcc(int tccNum) |
|
|
|
|
|
{ |
|
|
|
|
|
int i; |
|
|
|
|
|
spi_t spi; |
|
|
|
|
|
for (i = 0; i < _MCBSP_PORT_CNT; ++i) { |
|
|
|
|
|
spi = &__spi_devs[i]; |
|
|
|
|
|
if (MCBSP_getXmtEventId(spi->spi) == tccNum) { |
|
|
|
|
|
return spi; |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
return NULL; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
static void __tx_notify(int tccNum) |
|
|
|
|
|
{ |
|
|
|
|
|
spi_t spi; |
|
|
|
|
|
|
|
|
|
|
|
EDMA_intClear(tccNum); |
|
|
|
|
|
|
|
|
|
|
|
spi = __find_spi_with_xtcc(tccNum); |
|
|
|
|
|
if (spi) { |
|
|
|
|
|
EDMA_disableChannel(spi->xh); |
|
|
|
|
|
if (spi->xnotify) |
|
|
|
|
|
spi->xnotify(spi->xargs); |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
static Uint32 __parse_to_dlen1(int bits) |
|
|
static Uint32 __parse_to_dlen1(int bits) |
|
|
{ |
|
|
{ |
|
|
Uint32 dlen1; |
|
|
Uint32 dlen1; |
|
@ -45,7 +88,6 @@ static Uint32 __parse_to_dlen1(int bits) |
|
|
return (dlen1); |
|
|
return (dlen1); |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
int i2s_slave_open(int dev_id, int bits) |
|
|
int i2s_slave_open(int dev_id, int bits) |
|
|
{ |
|
|
{ |
|
|
MCBSP_Config mbconf; |
|
|
MCBSP_Config mbconf; |
|
@ -160,8 +202,7 @@ int i2s_slave_open(int dev_id, int bits) |
|
|
MCBSP_config(handle, &mbconf); |
|
|
MCBSP_config(handle, &mbconf); |
|
|
|
|
|
|
|
|
//Enable McBSP in steps
|
|
|
//Enable McBSP in steps
|
|
|
MCBSP_start(handle, |
|
|
MCBSP_start(handle, MCBSP_RCV_START | MCBSP_XMIT_START | MCBSP_SRGR_START | MCBSP_SRGR_FRAMESYNC, |
|
|
MCBSP_RCV_START | MCBSP_XMIT_START | MCBSP_SRGR_START | MCBSP_SRGR_FRAMESYNC, |
|
|
|
|
|
MCBSP_SRGR_DEFAULT_DELAY); |
|
|
MCBSP_SRGR_DEFAULT_DELAY); |
|
|
return 0; |
|
|
return 0; |
|
|
} |
|
|
} |
|
@ -400,6 +441,86 @@ int spi_write(int dev_id, const void *buf, int len) |
|
|
return (len); |
|
|
return (len); |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
int spi_edma_write(int dev_id, const void *buf, int len, void (*notify)(void *args), void *args) |
|
|
|
|
|
{ |
|
|
|
|
|
spi_t spi; |
|
|
|
|
|
Uint32 esize; |
|
|
|
|
|
EDMA_Config edma_conf; |
|
|
|
|
|
int slen, xevent; |
|
|
|
|
|
|
|
|
|
|
|
if ((spi = __get_active_device(dev_id)) == NULL) { |
|
|
|
|
|
return -2; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
spi = &__spi_devs[dev_id]; |
|
|
|
|
|
if (len > TXBUF_SIZE) { |
|
|
|
|
|
len = TXBUF_SIZE; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
slen = len; |
|
|
|
|
|
memcpy(spi->xbuf, buf, len); |
|
|
|
|
|
|
|
|
|
|
|
switch (spi->bits) { |
|
|
|
|
|
case 8: |
|
|
|
|
|
esize = EDMA_OPT_ESIZE_8BIT; |
|
|
|
|
|
break; |
|
|
|
|
|
case 12: |
|
|
|
|
|
case 16: |
|
|
|
|
|
esize = EDMA_OPT_ESIZE_16BIT; |
|
|
|
|
|
len /= 2; |
|
|
|
|
|
break; |
|
|
|
|
|
case 20: |
|
|
|
|
|
case 24: |
|
|
|
|
|
case 32: |
|
|
|
|
|
esize = EDMA_OPT_ESIZE_32BIT; |
|
|
|
|
|
len /= 4; |
|
|
|
|
|
break; |
|
|
|
|
|
default: |
|
|
|
|
|
return (-2); |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
CACHE_wbL2(spi->xbuf, len, CACHE_WAIT); |
|
|
|
|
|
|
|
|
|
|
|
xevent = MCBSP_getXmtEventId(spi->spi); |
|
|
|
|
|
|
|
|
|
|
|
edma_conf.opt = EDMA_OPT_RMK( |
|
|
|
|
|
EDMA_OPT_PRI_MEDIUM, |
|
|
|
|
|
esize, |
|
|
|
|
|
EDMA_OPT_2DS_NO, |
|
|
|
|
|
EDMA_OPT_SUM_INC, |
|
|
|
|
|
EDMA_OPT_2DD_NO, |
|
|
|
|
|
EDMA_OPT_DUM_NONE, |
|
|
|
|
|
EDMA_OPT_TCINT_YES, |
|
|
|
|
|
EDMA_OPT_TCC_OF(xevent), |
|
|
|
|
|
EDMA_OPT_TCCM_OF(xevent >> 4), |
|
|
|
|
|
EDMA_OPT_ATCINT_NO, |
|
|
|
|
|
EDMA_OPT_ATCC_OF(0), |
|
|
|
|
|
EDMA_OPT_PDTS_DEFAULT, |
|
|
|
|
|
EDMA_OPT_PDTS_DEFAULT, |
|
|
|
|
|
EDMA_OPT_LINK_NO, |
|
|
|
|
|
EDMA_OPT_FS_NO |
|
|
|
|
|
); |
|
|
|
|
|
edma_conf.src = EDMA_SRC_RMK((Uint32)(spi->xbuf)); |
|
|
|
|
|
edma_conf.cnt = EDMA_CNT_RMK(0, len); |
|
|
|
|
|
edma_conf.dst = EDMA_DST_OF(MCBSP_getXmtAddr(spi->spi)); |
|
|
|
|
|
edma_conf.idx = EDMA_IDX_RMK(0, 0); |
|
|
|
|
|
edma_conf.rld = EDMA_RLD_RMK(0, 0); |
|
|
|
|
|
|
|
|
|
|
|
spi->xnotify = notify; |
|
|
|
|
|
spi->xargs = args; |
|
|
|
|
|
|
|
|
|
|
|
if (spi->xh == NULL) |
|
|
|
|
|
spi->xh = EDMA_open(xevent, 0); |
|
|
|
|
|
|
|
|
|
|
|
edma_attach_tcc_irq(xevent, __tx_notify); |
|
|
|
|
|
|
|
|
|
|
|
EDMA_config(spi->xh, &edma_conf); |
|
|
|
|
|
|
|
|
|
|
|
EDMA_enableChannel(spi->xh); |
|
|
|
|
|
|
|
|
|
|
|
return (slen); |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
static int __read_u8(spi_t spi, Uint8 *buf, int len) |
|
|
static int __read_u8(spi_t spi, Uint8 *buf, int len) |
|
|
{ |
|
|
{ |
|
|
int i; |
|
|
int i; |
|
|