Using DMA to transfer data from an FPGA FIFO¶
Objective¶
Describe how to use EDMA3 to transfer data from an FPGA FIFO to memory.
Background¶
An FPGA FIFO typically has a single memory/register where the first read gets the first data value, the next read of the same location gets the next value and so on.
A DMA transfer from the FPGA FIFO to memory has to be such that the source address stays the same while the destination address increments.
EDMA3 has a transfer mode called FIFO which does exactly this. There is a note in the Technical Reference Manual which indicates this is of limited value since it is only supported with certain devices.
NOTE: The constant addressing (CONST) mode has limited applicability. The EDMA is configured for the constant addressing mode (EDMA_TPCC_OPT_n[0] SAM / EDMA_TPCC_OPT_n[1] DAM = 1) only if the transfer source or destination (on-chip memory, off-chip memory controllers, slave peripherals) support the constant addressing mode. If the constant addressing mode is not supported, the similar logical transfer can be achieved using the increment (INCR) mode (EDMA_TPCC_OPT_n[0] SAM / EDMA_TPCC_OPT_n[1] DAM =0) by appropriately programming the count and indices values.
The FPGA through the GPMC is not one of the special devices that supports the constant addressing mode needed for the special FIFO transfer mode.
Using EDMA3 to transfer data from an FPGA FIFO¶
Since the FIFO mode is not available, the INCR mode needs to be used. While the name implies that source and destination addresses would be incremented, it is possible (as the note states) to set up a transfer which does not effectively increase the source.
There are several forms of DMAs possible using a variety of parameters. Please read the Technical Reference Manual chapter on the DMA Controllers to become familiar with the parameters and options available.
The simplest kind of transfer moves a number of bytes of memory from the source address to the destination address. In this simple case, the acnt would be the number of bytes to transfer and bcnt and ccnt would be 1. This would not do what is needed with a FIFO.
A slightly more complicated transfer would use the following parameters for a transfer of 128 16-bit samples from an FPGA FIFO to memory.
Parameter | Value | Comment |
acnt | 2 | This represents 1 16-bit sample from the FIFO |
bcnt | 128 | The number of samples |
ccnt | 1 | Simple transfers usually have a ccnt of 1 |
srcbidx | 0 | This makes the source address stay constant |
dstbidx | acnt | This advances the destination address |
srccidx | acnt * bcnt | |
dstcidx | acnt * bcnt | |
TransferParams | EDMA3_DRV_SYNC_AB | Use AB synchronized mode |
By using the AB synchronized mode, the DMA will consist of a set of bcnt transfers of acnt bytes each and between each small transfer of acnt bytes, the srcbidx and dstbidx values will be added to the original source and destination addresses respectively. The effect is that the source address stays the same since the srcbidx is 0 and the destination address increments as expected. The advantage of the AB synchronized mode is that all the little transfers of acnt bytes are done as a single DMA transaction. In other words, the code only has to start (i.e. trigger) the DMA once and there is only one transfer complete interrupt.
In the A synchronized mode, the dma engine needs to be triggered for each bcnt transfer (actually bcnt*ccnt). The AB synchronized mode avoids these multiple triggers so the number of triggers needed is just ccnt.
FIFO Address Alignment and FIFO width¶
When doing a DMA, the initial source and destination addresses need to be aligned on 32-byte boundaries. (lower 5 bits of the address must be 0).
This requirement is also present for the FIFO address within the FPGA address space. As an example, if the FPGA core providing the FIFO has memory addresses from 0x100 - 0x17F, possible FIFO addresses would be 0x120, 0x140, 0x160, 0x180, 0x1A0, 0x1C0, and 0x1E0.
While a FIFO width of 16-bits is shown in the example above, it is also possible to have a FIFO width of 32-bits by changing the acnt from 2 to 4. The values are still read as 16-bit values with 2 addresses for the 2 16-bit halves. The FPGA must have the least-significant bits in the lower address and the most-significant bits in the upper address. And the FIFO should be advanced when the most-significant bits or the upper address is read.
Moving data into an FPGA FIFO¶
If you want to transfer a block of bytes from memory to an FPGA FIFO, the same technique can be used but the srcbidx would be acnt and the dstbidx would be 0. This would allow the destination address to stay the same and the source address would change.
If you wanted to move data from one FIFO to another FIFO, then both srcbidx and dstbidx could be 0 so that neither address changes.
Go to top