0 Replies Latest reply on Nov 4, 2020 5:03 PM by MoTa_728816

    A study of using PSoC 4 DMA's dual descriptors (CY8CKIT-044)

    MoTa_728816

      Hi,

       

      As you know, the DMA of PSoC 4 has 2 descriptors to implement PING-PONG, or back-to-back buffering translation.

      So I was expecting to configure them for two different translations, which will result utilizing a DMA channel just like they were a couple of DMA channels.

       

      In my previous study, I used 8 DMA channels to implement ADC-DMA-UART for displaying human readable hexadecimal strings.

      A study of simple ADC and DMA and UART (CY8CKIT-044)

      020-data-flow.JPG

      This time I tried to combine each ADC_RAW_H and ADC_RAW_L,  DMA_H_ADR and DMA_L_ADR into one DMA with 2 descriptors.

      And also I merged 4 DMAs used to send the result output into one DMA, but it required another DMA to transfer the char addresses into the result string,

      I ended up 4 DMAs total, and 3 of them are using two descriptors.

      030-data-flow.JPG

      Actually I have been trying to use this dual descriptor feature since I tried to write a simple oscilloscope sample.

      A study of simple oscilloscope using ADC and DMA (CY8CKIT-044) version 1

       

      But somehow I have managed to keep failing to use this feature.

      This time I decided to challenge this for good, it took me more than a whole week though...

       

      Although I could not find explicit description(s) how to do this.

      Following is how I could make it work.

       

      I use DMA_ASC for a sample.

      (1) Obviously I "Number of descriptors" needs to be 2

      034-DMA_ADC_Config1.JPG

      (2) Descriptor 0 Configuration

      Transfer mode: Entire descriptor chain per trigger

      Post completion actions: "Chain to descriptor 1" (This is automatically checked.)

      035-DMA_ASC_Config_desc0.JPG

      (3) Descriptor 1 Configuration

      Transfer mode: Entire descriptor per trigger

      Post completion actions: Chain to descriptor 0

      Note: For me this configuration was hard to come up with.

      036-DMA_ASC_Config_desc1.JPG

       

      Since descriptor 0 works without farther configuration, it took me very long time and many trials to figure out that

      descriptor 1 needs to be manually validated

       

      So initialization for this DMA_ASC looks like

      ====================

          DMA_ASC_Start((void *)h_char, (void *)(&CYDMA_DESCR_BASE.descriptor[DMA_STR_CHANNEL][0].src)) ;

          DMA_ASC_SetSrcAddress(1, (void *)l_char);

          DMA_ASC_SetDstAddress(1, (void *)(&CYDMA_DESCR_BASE.descriptor[DMA_STR_CHANNEL][1].src)) ;

          CyDmaValidateDescriptor(DMA_ASC_CHANNEL, 1) ;

      ====================

       

      With above modification(s), the schematic was modified

       

      from  the previous schematic

      012-schematic.JPG

      to the current schematic

      032-schematic.JPG

       

      Pins

      033-Pins.JPG

       

      Tera Term log

      031-TeraTerm-log.JPG

       

      main.c

      ========================

      #include "project.h"

      #include "stdio.h"

      #include "ascii_byte_table.h"

       

      uint32_t h_char_address = (uint32_t) ascii_h ;

      uint32_t l_char_address = (uint32_t) ascii_l ;

       

      uint8_t *h_char = (void *)&h_char_address ;

      uint8_t *l_char = (void *)&l_char_address ;

       

      char out_str[7] = { '0', 'x', 'H', 'L', '\n', '\r', '\0' } ;

       

      void init_hardware(void)

      {   

          CyGlobalIntEnable; /* Enable global interrupts. */   

         

          UART_Start() ;

         

          ADC_Start() ;

         

          DMA_UART_Start((void *)out_str, (void *)UART_TX_FIFO_WR_PTR) ;

        

          DMA_STR_Start((void*)h_char, (void *)(&out_str[2])) ;

          DMA_STR_SetSrcAddress(1, (void *)l_char);

          DMA_STR_SetDstAddress(1, (void *)(&out_str[3])) ;

          CyDmaValidateDescriptor(DMA_STR_CHANNEL, 1) ;

         

          DMA_ASC_Start((void *)h_char, (void *)(&CYDMA_DESCR_BASE.descriptor[DMA_STR_CHANNEL][0].src)) ;

          DMA_ASC_SetSrcAddress(1, (void *)l_char);

          DMA_ASC_SetDstAddress(1, (void *)(&CYDMA_DESCR_BASE.descriptor[DMA_STR_CHANNEL][1].src)) ;

          CyDmaValidateDescriptor(DMA_ASC_CHANNEL, 1) ;

       

       

          DMA_ADC_Start((void *)ADC_SAR_CHAN0_RESULT_PTR, (void *)h_char) ;

          DMA_ADC_SetSrcAddress(1, (void *)h_char) ;

          DMA_ADC_SetDstAddress(1, (void *)l_char) ;

          CyDmaValidateDescriptor(DMA_ADC_CHANNEL, 1) ;

      }

       

      int main(void)

      {   

          init_hardware() ;

         

          UART_UartPutString("\x1b[2J\x1b[;H") ;

          UART_UartPutString("ADC-DMA-UART 2-descriptors Test\n\r") ;

         

          Timer_Start() ;

             

          for(;;)

          {

          }

      }

      ========================

       

      ascii_byte_table.h

      ========================

      #ifndef _ASCII_BYTE_TABLE_H_

      #define _ASCII_BYTE_TABLE_H_

      #include "project.h"

         

      extern const uint8_t ascii_h[256] ;

      extern const uint8_t ascii_l[256] ;

       

       

      #endif

      ========================

       

      ascii_byte_table.c

      ========================

      #include "project.h"

      #include "ascii_byte_table.h"

       

      const uint8_t ascii_h[256]

      __ALIGNED(0x100u)

      = {

      '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0',

      '1', '1', '1', '1', '1', '1', '1', '1', '1', '1', '1', '1', '1', '1', '1', '1',

      '2', '2', '2', '2', '2', '2', '2', '2', '2', '2', '2', '2', '2', '2', '2', '2',

      '3', '3', '3', '3', '3', '3', '3', '3', '3', '3', '3', '3', '3', '3', '3', '3',

      '4', '4', '4', '4', '4', '4', '4', '4', '4', '4', '4', '4', '4', '4', '4', '4',

      '5', '5', '5', '5', '5', '5', '5', '5', '5', '5', '5', '5', '5', '5', '5', '5',

      '6', '6', '6', '6', '6', '6', '6', '6', '6', '6', '6', '6', '6', '6', '6', '6',

      '7', '7', '7', '7', '7', '7', '7', '7', '7', '7', '7', '7', '7', '7', '7', '7',

      '8', '8', '8', '8', '8', '8', '8', '8', '8', '8', '8', '8', '8', '8', '8', '8',

      '9', '9', '9', '9', '9', '9', '9', '9', '9', '9', '9', '9', '9', '9', '9', '9',

      'A', 'A', 'A', 'A', 'A', 'A', 'A', 'A', 'A', 'A', 'A', 'A', 'A', 'A', 'A', 'A',

      'B', 'B', 'B', 'B', 'B', 'B', 'B', 'B', 'B', 'B', 'B', 'B', 'B', 'B', 'B', 'B',

      'C', 'C', 'C', 'C', 'C', 'C', 'C', 'C', 'C', 'C', 'C', 'C', 'C', 'C', 'C', 'C',

      'D', 'D', 'D', 'D', 'D', 'D', 'D', 'D', 'D', 'D', 'D', 'D', 'D', 'D', 'D', 'D',

      'E', 'E', 'E', 'E', 'E', 'E', 'E', 'E', 'E', 'E', 'E', 'E', 'E', 'E', 'E', 'E',

      'F', 'F', 'F', 'F', 'F', 'F', 'F', 'F', 'F', 'F', 'F', 'F', 'F', 'F', 'F', 'F'

      } ;

       

      const uint8_t ascii_l[256]

      __ALIGNED(0x100u)

      = {

      '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F',

      '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F',

      '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F',

      '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F',

      '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F',

      '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F',

      '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F',

      '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F',

      '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F',

      '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F',

      '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F',

      '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F',

      '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F',

      '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F',

      '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F',

      '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F'

      } ;

      ========================

       

      moto