This post is older than 2 years and might not be relevant anymore
More Info: Consider searching for newer posts

Easy DMA ArrayList format for 32-bit buffer

Hello,

background: using Keil IDE, my own board that has a nRF52840 on it.  My goal is to create automatic DMA transfers from SPIM3 peripheral.

I am setting up EasyDMA with an ArrayList on my nRF52840 and have the following questions:

1.  Is this an acceptable way to declare the ArrayList? All of the examples I see have the buffer inside the structure using uint8_t as the data type

/* In my header file, I have the following code */

// ArrayList for EasyDMA 
typedef struct ArrayList
{
  uint32_t buffer;
} ArrayList_type;

extern ArrayList_type gADAS1000_ArrayList[12];	//12 32-bit arrays

/* In my C file, I have the following code */

ArrayList_type gADAS1000_ArrayList[12];	//12 32-bit arrays

2.  In the documentation, the reader and writer buffer are given specific memory addresses as shown below

uint8_t readerBuffer[READERBUFFER_SIZE] __at__ 0x20000000;
uint8_t writerBuffer[WRITERBUFFER_SIZE] __at__ 0x20000005;

   I tried to use this "__at__" instruction but my compiler and or IDE has an issue with it, see below.  Is this necessary?  I am currently seeing some data corruption with SPI transfers without     this statement..

Thank you very much in advance,

-E

  • Hi,

    1.  Is this an acceptable way to declare the ArrayList? All of the examples I see have the buffer inside the structure using uint8_t as the data type

    With ArrayList you basically just provide a large memory buffer, which can hold an array of transfers. How you treat that is up to you, but doing it like this makes sense.

    2.  In the documentation, the reader and writer buffer are given specific memory addresses as shown below

    In which documentation? I do not see any reason for that.

    I tried to use this "__at__" instruction but my compiler and or IDE has an issue with it, see below.  Is this necessary?

    No, I do not understand why it is necessary.

    I am currently seeing some data corruption with SPI transfers without     this statement..

    But not with it? How have you checked that the data is corrupted? Any part of it?

  • Hello Einar,

    Thank you for the responses.  See below additional comments

    1.  Good to know, thanks for confirming.

    2.  I am referring to the nRF52841 Product Spec, v1.1, pg 49 where easyDMA is described, there is an example there with the __at__ instruction being used.  I wanted to confirm if this was necessary, but from your response it seems it is not.

    There is also an errata nRF52840 Errata Rev C[198] that describes an issue with SPIM3 that requires instructions for allocation of RAM to SPIM3 transmit buffer.  So, I used the following code to address this errata:

    __attribute__((section("SPIM3_DMABUFFER")))
    volatile uint8_t gSPIM3_TX_BUFFER[48];

    3.  As far as the data corruption, the situation might require me to open a separate ticket to describe the issue if this does not fix it.  Here is what's going on; My goal is to stream data from external ADC to the serial port at 1Mbaud.  The ADC is sending a frame of 48 bytes every 500us using SPIM3 at 32 MHz and write that frame to the ArrayList I setup above using easyDMA.  Upon receiving SPIM3->EVENTS_END that indicates when all 48 bytes have been received, I setup PPI to start UARTE0->TASK_STARTTX.   The frame provided by the ADC has a format with 12 fixed headers every 32-bit word.  I am able to see this header format in the data when I send it out of the serial port and capture it, but specifically the data corruption is happening at the beginning of the stream whereby the location of the headers is no longer present.  This data corruption happens at the beginning of the data stream, then the format is fixed, then after a couple of thousand samples it gets corrupted again.  The length of the data corruption is between 8-20 bytes at the begging of the stream and then what seems permanently thereafter.

  • Hi,

    2. Yes. The key here is just to make sure that the RAM block for the SPI buffer is not used for anything else (so that the CPU will not access it during a transfer).

    3. I do not have enough insight in your code and project to see, but since erratum 198 can cause RAM corruption it would be good to double-check that your SPI buffer is "alone" in it's RAM block. 

Related