Guys, I'm preparing to write a FAT filing system for a sd card. However I must first setup the SPI bus. I've included an example below of the SPI1 (set as master) and SPI2 (set as slave) communicating. Ideally I want to configure the setup to send and receive on either on a single port/SPI bus. The example uses DMA transfers.
#define DMA_TRANS_SIZE 256 /** define the address of SPI master */ #define SPI_MASTER_BUS BUS(BUS_TYPE_SPI, 1) /** define the CS signal of SPI master */ #define SPI_MASTER_CS 3 /** define the bitrate of SPI master */ #define SPI_MASTER_BITRATE 1000 /** define the pins of SPI master */ #define SPI_MASTER_PINS PINS_SPI1_NPCS3_ALT /** define the address of SPI slave */ #define SPI_SLAVE_ADDR SPI2 /** define the pins of SPI slave */ #define SPI_SLAVE_PINS PINS_SPI2_NPCS0 /*---------------------------------------------------------------------------- * Local variables *----------------------------------------------------------------------------*/ /** data buffer for SPI master's receive */ CACHE_ALIGNED static uint8_t spi_buffer_master_tx[DMA_TRANS_SIZE]; /** data buffer for SPI slave's transfer */ CACHE_ALIGNED static uint8_t spi_buffer_slave_rx[DMA_TRANS_SIZE]; /** Pio pins for SPI slave */ static const struct _pin pins_spi_slave[] = SPI_SLAVE_PINS; /** descriptor for SPI master */ static const struct _bus_dev_cfg spi_master_dev = { .bus = SPI_MASTER_BUS, .spi_dev = { .chip_select = SPI_MASTER_CS, .bitrate = SPI_MASTER_BITRATE, .delay = { .bs = 0, .bct = 0, }, .spi_mode = SPID_MODE_0, }, }; static struct _spi_desc spi_slave_dev = { .addr = SPI_SLAVE_ADDR, .chip_select = 0, .transfer_mode = BUS_TRANSFER_MODE_DMA, }; /*---------------------------------------------------------------------------- * Local functions *----------------------------------------------------------------------------*/ /** * \brief Displays the user menu. */ static void _display_menu(void) { printf("\r\nMenu :\r\n"); printf("------\r\n"); printf(" s: Perform SPI transfer start\r\n"); printf(" h: Display menu \r\n\r\n"); } static int _spi_slave_transfer_callback(void* arg, void* arg2) { printf("Slave transfer complete\r\n"); return 0; } /** * \brief Start SPI slave transfer and SPI master receive. */ static void _spi_transfer(void) { int err; int i; struct _buffer master_buf = { .data = spi_buffer_master_tx, .size = DMA_TRANS_SIZE, .attr = BUS_BUF_ATTR_TX | BUS_SPI_BUF_ATTR_RELEASE_CS, }; struct _buffer slave_buf = { .data = spi_buffer_slave_rx, .size = DMA_TRANS_SIZE, .attr = BUS_BUF_ATTR_RX, }; struct _callback _cb = { .method = _spi_slave_transfer_callback, .arg = 0, }; for (i = 0; i < DMA_TRANS_SIZE; i++) spi_buffer_master_tx[i] = i; memset(spi_buffer_slave_rx, 0, DMA_TRANS_SIZE); bus_start_transaction(spi_master_dev.bus); printf("Slave receiving...\r\n"); err = spid_transfer(&spi_slave_dev, &slave_buf, 1, &_cb); if (err < 0) { trace_error("SPI: SLAVE: transfer failed.\r\n"); return; } printf("Master sending...\r\n"); bus_transfer(spi_master_dev.bus, spi_master_dev.spi_dev.chip_select, &master_buf, 1, NULL); bus_stop_transaction(spi_master_dev.bus); spid_wait_transfer(&spi_slave_dev); if (memcmp(spi_buffer_master_tx, spi_buffer_slave_rx, DMA_TRANS_SIZE)) { trace_error("SPI: received data does not match!\r\n"); return; } printf("Received data matched.\r\n"); } /*---------------------------------------------------------------------------- * Global functions *----------------------------------------------------------------------------*/ /** * \brief SPI slave Application entry point. * * \return Unused (ANSI-C compatibility). */ int main(void) { uint8_t key; /* Output example information */ console_example_info("SPI Slave Example"); /* Configure SPI slave */ pio_configure(pins_spi_slave, ARRAY_SIZE(pins_spi_slave)); spid_configure(&spi_slave_dev); spid_configure_master(&spi_slave_dev, false); spid_configure_cs(&spi_slave_dev, 0, 0, 0, 0, SPID_MODE_0); // DMA configuration bus_configure_slave(spi_master_dev.bus, &spi_master_dev); _display_menu(); while (1) { key = console_get_char(); switch (key) { case 'H': case 'h': _display_menu(); break; case 'S': case 's': _spi_transfer(); break; default: break; } } }
Could one of you kind fellas show me how to achieve reading and writing from the same SPI bus?