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.

CC3200MODLAUNCHXL: Problem during implementing SPI using DMA

Part Number: CC3200MODLAUNCHXL

Hi,

I am trying to transmit100 bytes of data using SPI from CC3200(as Master) to NRF52(Slave). I tried to implement SPI using SPI.h library of Energia. and I found that data transfer was going successfully. I tried to implement SPI using DMA. I followed several of E2E posts and have written a code successfully. I was able to transfer a total of 33 bytes of data at max. When I do a transfer of more than 33 bytes I found that after 33 bytes it is just transferring 0 (or may not be transfering data after 33rd byte at all) as on receiving side I was getting 0 in place of my data. 

This is my code:

#include <driverlib/udma.h>
#include <driverlib/spi.h>
#include <driverlib/prcm.h>
#include "udma_if.h"
#include "inc/hw_mcspi.h"

#define NBYTES 100
#define SPIhz  1000000

volatile int spidone;

void SPIisr() {
    uint32_t status = MAP_SPIIntStatus(GSPI_BASE,true);
    MAP_SPIIntClear(GSPI_BASE,SPI_INT_EOW);
        MAP_SPIIntClear(GSPI_BASE,status);
            spidone = 1;
            MAP_SPICSDisable(GSPI_BASE);
}

void SPIinit() {
    MAP_PRCMPeripheralClkEnable(PRCM_GSPI, PRCM_RUN_MODE_CLK);

     MAP_PinTypeSPI(PIN_05, PIN_MODE_7);  // SCLK pin 7
     MAP_PinTypeSPI(PIN_06, PIN_MODE_7);  // MISO pin 14
     MAP_PinTypeSPI(PIN_07, PIN_MODE_7);  // MOSI pin 15
     MAP_PinTypeSPI(PIN_08, PIN_MODE_7);  //  CS  pin 18

     MAP_SPIReset(GSPI_BASE);
     UDMAInit();
     MAP_SPIConfigSetExpClk(GSPI_BASE,MAP_PRCMPeripheralClockGet(PRCM_GSPI),
                      SPIhz,SPI_MODE_MASTER,SPI_SUB_MODE_0,
                      (SPI_SW_CTRL_CS |
                      SPI_4PIN_MODE |
                      SPI_TURBO_OFF |
                      SPI_CS_ACTIVELOW |
                      SPI_WL_8));

     MAP_SPIWordCountSet(GSPI_BASE, NBYTES);
     MAP_SPIFIFOLevelSet(GSPI_BASE, 1, 1);
     MAP_SPIFIFOEnable(GSPI_BASE, SPI_RX_FIFO);
     MAP_SPIFIFOEnable(GSPI_BASE, SPI_TX_FIFO);
     MAP_SPIDmaEnable(GSPI_BASE,SPI_RX_DMA);
     MAP_SPIDmaEnable(GSPI_BASE,SPI_TX_DMA);
     MAP_SPIIntRegister(GSPI_BASE,SPIisr);
     MAP_SPIIntEnable(GSPI_BASE, SPI_INT_EOW);
     MAP_SPIEnable(GSPI_BASE);
     Serial.println("SPI Initialization Completed");
}

void spi_transfer(uint8_t* tx, uint8_t* rx)
{
  Serial.println("DMA transfer setting up");
  spidone = 0;
  SetupTransfer(UDMA_CH31_GSPI_TX,
                UDMA_MODE_BASIC,
                sizeof(tx),
                UDMA_SIZE_8,
                NBYTES,
                tx,
                UDMA_SRC_INC_8,
                (void *)(GSPI_BASE + MCSPI_O_TX0),
                UDMA_DST_INC_NONE);

 // Serial.println("waiting for SPI done");
  MAP_SPICSEnable(GSPI_BASE);
//  while (!spidone) {
//    Serial.print(".");
//  }
//

  Serial.println("DMA transfer completed");
}

uint8_t rxbuf[NBYTES]={0};
uint8_t txbuf[NBYTES];
uint8_t test[NBYTES]={1};
uint8_t test1[NBYTES]={2};
int i = 0;
void setup()
{
  Serial.begin(115200);
  SPIinit();
  for(int j=0;j<NBYTES;j++){
      test[j]=1;
      test1[j]=2;
  }

}

void loop()
{

    for (int k = 0; k < NBYTES; k++) {
      txbuf[k] = i+k+10;
    }
  spi_transfer(txbuf, rxbuf);
  delay(2000);
//  spi_transfer(test, rxbuf);
//  delay(1000);
//  spi_transfer(test1, rxbuf);
//  delay(1000);
  i++;
}

I couldn't understand where am I wrong?

  • Hi Laxmi,

    What are you getting on your slave device? In your code, you have a txbuf that you are first filling with sequential data. Does the slave receive 33 bytes of the sequence from the beginning and then it gets zeroes afterwards, or does it skip bytes? Also, have you taken a logic analyzer and checked the SPI lines coming out of the CC3200 to see if the behavior of the slave matches up with the values being transferred by the CC3200?

    There are a few things which you can try in your code and see if it helps things:

    1. Move the SPIEnable() out of SPI init and into spi_transfer(), right before your SPICSEnable().
    2. Try making another SetupTransfer() call alongside the one setting up the TX DMA and setup a RX DMA transfer into rxbuf. 
    3. For your SetupTransfer() calls, the ulArbSize parameter cannot be NBYTES. The arbitration size must be a power of two. Furthermore, you should be using the UDMA_ARB_X macros. An arbitration size of 1 is appropriate given your FIFO depth of 1.

    Regards,

    Michael