1 Reply Latest reply on Oct 18, 2017 12:41 AM by miles.frain_2811046

    DMA write to multiple destinations from single source

    miles.frain_2811046

      I attached an example project of attempting to write values from a single ADC to two DACs.  The long-term goal is to insert a filter before the second DAC and compare the analog signals, but I'm keeping this example as simple as possible for troubleshooting.

       

      My strategy is to setup a chain of two TDs with the same source, but a different destination for each.

       

      The attached code example has two  scenarios. The first scenario only attempts to write to a single DAC, and this is successful. The second scenario attempts to write to both DACs, but only successfully writes to the second DAC, and the first DAC surprisingly remains unchanged.

       

      This thread seems somewhat related, although the code example links are unavailable.

      Multiple TD's for different destination adresses

       

      The above thread suggests setting-up two DMA channels with a single TD each, but it seems like it should also be possible to configure this with a single channel and multiple TDs.

        • 1. Re: DMA write to multiple destinations from single source
          miles.frain_2811046

          I'm trying to insert a code snippet of the configuration step below, but it's not being formatted correctly.

          I'm going through the "Insert > Syntax Highlighting > C++" menu, then pasting my raw text in the box, but it's adding extra line breaks, removing indentation, and creating tables, which are really difficult to delete or undo. I resorted to deleting my original post due to these code snippet formatting issues.

           

           

          const unsigned num_destinations = 2;
          
              
          
          if (num_destinations == 1)
          
          {
          
          // ----------------  First ADC input to DAC
          
          // This correctly copies to values to the first DAC
          
          
          
          /* Variable declarations for DMA_AdcToVdacs */
          
          uint8 DMA_AdcToVdacs_Chan;
          
          uint8 DMA_AdcToVdacs_TD[1];
          
          
          
          /* Iniitialize DMA channel */
          
          DMA_AdcToVdacs_Chan = DMA_AdcToVdacs_DmaInitialize(DMA_AdcToVdacs_BYTES_PER_BURST, DMA_AdcToVdacs_REQUEST_PER_BURST,
          
          HI16(DMA_AdcToVdacs_SRC_BASE), HI16(DMA_AdcToVdacs_DST_BASE));
          
          
          
          /* Allocate TD */
          
          DMA_AdcToVdacs_TD[0] = CyDmaTdAllocate();
          
          
          
          /* TD configuration setting */
          
          CyDmaTdSetConfiguration(DMA_AdcToVdacs_TD[0], 1u, DMA_INVALID_TD, DMA_AdcToVdacs__TD_TERMOUT_EN);
          
          
          
          /* Set Source and Destination address */
          
          CyDmaTdSetAddress(DMA_AdcToVdacs_TD[0], LO16((uint32)ADC_DelSig_1_DEC_SAMP_PTR),
          
          LO16((uint32)VDAC8_First_Data_PTR));
          
          
          
          /* TD initialization */
          
          CyDmaChSetInitialTd(DMA_AdcToVdacs_Chan, DMA_AdcToVdacs_TD[0]);
          
          
          
          /* Enable the DMA channel */
          
          CyDmaChEnable(DMA_AdcToVdacs_Chan, 1u);
          
          }
          
          else if (num_destinations == 2)
          
          {
          
          // ---------- Copy to two destinations - both DACs
          
          // This skips the first DAC and only copies values to the second DAC
          
          
          
          /* Variable declarations for DMA_AdcToVdacs */
          
          uint8 DMA_AdcToVdacs_Chan;
          
          uint8 DMA_AdcToVdacs_TD[2];
          
          
          
          /* Iniitialize DMA channel */
          
          DMA_AdcToVdacs_Chan = DMA_AdcToVdacs_DmaInitialize(DMA_AdcToVdacs_BYTES_PER_BURST, DMA_AdcToVdacs_REQUEST_PER_BURST,
          
          HI16(DMA_AdcToVdacs_SRC_BASE), HI16(DMA_AdcToVdacs_DST_BASE));
          
          
          
          /* Allocate TD */
          
          DMA_AdcToVdacs_TD[0] = CyDmaTdAllocate();
          
          DMA_AdcToVdacs_TD[1] = CyDmaTdAllocate();
          
          
          
          /* TD configuration setting */
          
          // Tried with the following changes:
          
          //   Replaced DMA_AdcToVdacs__TD_TERMOUT_EN with 0
          
          //   Replaced DMA_INVALID_TD with CY_DMA_DISABLE_TD
          
          CyDmaTdSetConfiguration(DMA_AdcToVdacs_TD[0], 1u, DMA_AdcToVdacs_TD[1], DMA_AdcToVdacs__TD_TERMOUT_EN);
          
          CyDmaTdSetConfiguration(DMA_AdcToVdacs_TD[1], 1u, DMA_INVALID_TD, DMA_AdcToVdacs__TD_TERMOUT_EN);
          
          
          
          /* Set Source and Destination address */
          
          CyDmaTdSetAddress(DMA_AdcToVdacs_TD[0], LO16((uint32)ADC_DelSig_1_DEC_SAMP_PTR),
          
          LO16((uint32)VDAC8_First_Data_PTR));
          
          
          
          CyDmaTdSetAddress(DMA_AdcToVdacs_TD[1], LO16((uint32)ADC_DelSig_1_DEC_SAMP_PTR),
          
          LO16((uint32)VDAC8_Second_Data_PTR));
          
          
          
          /* TD initialization */
          
          CyDmaChSetInitialTd(DMA_AdcToVdacs_Chan, DMA_AdcToVdacs_TD[0]);
          
          
          
          /* Enable the DMA channel */
          
          CyDmaChEnable(DMA_AdcToVdacs_Chan, 1u);
          
          }