0

Is it possible for arduino Due to act as DMA-SPI-slave device which can exchange SPI data (uint16_t TX[10] and RX[10]) in triggered slave mode?

I have a setup in which time period is very short (~500uS/cycle). so I need to exchange data with another Microcontroller (acting as 'Master') within the mensioned time limit. Some other tasks are also to be processed. This is why I have to go for DMA and fast data transfer without intervension of processor. All the codes available are to be used in Master mode of SPI. Not a single one is in SLAVE mode. I wrote a code but I cannot implement a transfer triggered by SPI hardware. Also how to implement data transfer complete Interrupt after all 10 datas(16bit) have been transferred and received? Here is my initialization code:

    void DMAslaveBegin()
{
    // Configure the pins for SPI in peripheral mode
    PIO_Configure(
        g_APinDescription[PIN_SPI_MOSI].pPort,
        g_APinDescription[PIN_SPI_MOSI].ulPinType,
        g_APinDescription[PIN_SPI_MOSI].ulPin,
        g_APinDescription[PIN_SPI_MOSI].ulPinConfiguration);
    PIO_Configure(
        g_APinDescription[PIN_SPI_MISO].pPort,
        g_APinDescription[PIN_SPI_MISO].ulPinType,
        g_APinDescription[PIN_SPI_MISO].ulPin,
        g_APinDescription[PIN_SPI_MISO].ulPinConfiguration);
    PIO_Configure(
        g_APinDescription[PIN_SPI_SCK].pPort,
        g_APinDescription[PIN_SPI_SCK].ulPinType,
        g_APinDescription[PIN_SPI_SCK].ulPin,
        g_APinDescription[PIN_SPI_SCK].ulPinConfiguration);
    PIO_Configure(
        g_APinDescription[PIN_SPI_SS0].pPort,
        g_APinDescription[PIN_SPI_SS0].ulPinType,
        g_APinDescription[PIN_SPI_SS0].ulPin,
        g_APinDescription[PIN_SPI_SS0].ulPinConfiguration); 
    //pmc_enable_periph_clk(ID_SPI0);
#if USE_SAM3X_DMAC
    pmc_enable_periph_clk(ID_DMAC);
    DMAC_Disable();
    DMAC->DMAC_GCFG = DMAC_GCFG_ARB_CFG_FIXED;  //Fixed priority arbiter
    DMAC_Enable();

#if USE_SAM3X_BUS_MATRIX_FIX    // not active here
    MATRIX->MATRIX_WPMR = 0x4d415400;
    MATRIX->MATRIX_MCFG[1] = 1;         //Single Access
    MATRIX->MATRIX_MCFG[2] = 1;         //Single Access
    MATRIX->MATRIX_SCFG[0] = 0x01000010;
    MATRIX->MATRIX_SCFG[1] = 0x01000010;
    MATRIX->MATRIX_SCFG[7] = 0x01000010;

#endif  // USE_SAM3X_BUS_MATRIX_FIX
#endif  // USE_SAM3X_DMAC
    //  initialize SPI controller - Slave mode
    SPI.begin(_pin);
    SPI_Disable(SPI0);
    REG_SPI0_CR = SPI_CR_SWRST;     // reset SPI
    REG_SPI0_CR = SPI_CR_SPIEN;     // enable SPI
    REG_SPI0_MR = 0x10;              // DLYBCS=0, PCS=0, MODFDIS=1, PS=0, MSTR=0(slave)
    REG_SPI0_CSR = 0x80;            // DLYBCT=0, DLYBS=0, SCBR=0, 16 bit transfer, Mode 0/1
    REG_SPI0_IDR = ~SPI_IDR_RDRF;
    REG_SPI0_IER = SPI_IDR_RDRF;
    NVIC_EnableIRQ(SPI0_IRQn);
    SPI_Enable(SPI0);
}

Is this a valid condition for DMA? How can I utilize SPI ISR handler like system in DMA for my code so that the complete transaction (simultaneous Transmit & Receive) becomes fully automatic without processor utilization?

  • It is more than likely possible. However, we lowly Arduino users probably aren't knowledgeable enough about Atmel's SDK and the workings of the Due's MCU to give you the best answer. Your best source of information would probably be a dedicated Atmel ARM MCU forum. One that deals on a more professional level than Arduino. – Majenko Sep 12 at 18:52
  • Thanks. I'll post. but, does DMA callbacks on SPI interrupt? – souravg009 Sep 12 at 19:54
  • What does the datasheet / SDK API manual say? – Majenko Sep 12 at 19:56
  • PDC can employ Handler, but I couldn't find DMA Handler for SPI slave mode. The datasheet DMAC section is also messy. – souravg009 Sep 12 at 20:10
  • I don't think DMA really cares about what "mode" SPI is running in. – Majenko Sep 12 at 20:33
0

I think I have discovered a solution while searching: https://github.com/avrxml/asf/blob/master/sam/drivers/spi/spi_dmac_slave_example/spi_dmac_slave_example.c

It is an example for atmel's sam3X8EK. But the MCU cores are same. Though the code serves different purpose, we can manage to mold it in the direction we need. Only thing remained to do is to push an array through it. Fellows, what do you think?

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.