We have detected your current browser version is not the latest one. Xilinx.com uses the latest web technologies to bring you the best online experience possible. Please upgrade to a Xilinx.com supported browser:Chrome, Firefox, Internet Explorer 11, Safari. Thank you!

Showing results for 
Search instead for 
Did you mean: 
Visitor fnc
Registered: ‎07-22-2019

DMA decode error


I'm having issues with the CDMA IP when trying to send data to a custom AXI Full Interface. The CDMA fails with an error status of 0x40 which means it has a decode error in the address.

I have a custom IP, named GP_Filter_Accelerator, with an AXI Full interface on port S01 and a Zynq PS which are connected in a block diagram. I have followed the SimplePoll Example from Xilinx documentation, so everything should work, but it doesn't.

I'm really lost and I need to proceed with the design, so any help will be really apreciated.

Thanks in advance.

xilinx-forum.pngBlock diagram












xilinx-forum-2.pngAddress map
































The code I've used for the Zynq PS is the one shown below:

#include "platform.h"
#include "xparameters.h"
#include "xaxicdma.h"


#define BUFFER_SIZE			64	// Length of the buffers for DMA transfer
#define RESET_LOOP_COUNT	10	// Number of times to check reset is done

/************************** Function Prototypes ******************************/
int init_cdma_ctrl();
static int doTransfer(XAxiCdma *instancePtr, int length, int retries);
int xAxiCdma_Poll(u16 deviceId, int numberOfTransfers, int numberOfTries);
static int checkData(u32 *srcPtr, u32 *dstPtr, int length);

/************************** Variable Definitions *****************************/
// Instance of the XAxiCdma
static XAxiCdma axiCdmaInstance;

// Source and Destination buffer for DMA transfer
volatile static u32 srcBuffer[BUFFER_SIZE] __attribute__ ((aligned (32)));
volatile static u32 *dstBuffer __attribute__ ((aligned (32)));

// Shared variables used to test the callback
volatile static int done = 0;	// DMA transfer is done
volatile static int error = 0;	// DMA Error occurs

int main() {

    xil_printf("\r\r\n*** START ***\r\r\n");

	int result = init_cdma_ctrl();

    xil_printf("\r\n***  END  ***\r\r\n");
	return result;

int init_cdma_ctrl() {

	int status;
	const int numOfTries = 10;

	int deviceID = DMA_CTRL_DEVICE_ID;
	int numOfTransfer = 1;
	dstBuffer = (u32 *) AXI_S01_BUFFER;

	xil_printf("\r\n[I] init_cdma_ctrl: starting transfer routines... \r\n\r\n");

	// Run the polling transfer method
	status = xAxiCdma_Poll(deviceID, numOfTransfer, numOfTries);
	if (status != XST_SUCCESS) {
		xil_printf("[E] init_cdma_ctrl: xAxiCdma_Poll failed!\r\n");
		return XST_FAILURE;

	xil_printf("\r\n[I] init_cdma_ctrl: transfer successful! \r\n");
	return XST_SUCCESS;


int xAxiCdma_Poll(u16 deviceId, int numberOfTransfers, int numberOfTries) {

	XAxiCdma_Config *cfgPtr;
	int status;

	// Initialize the XAxiCdma device
	cfgPtr = XAxiCdma_LookupConfig(deviceId);
	if (!cfgPtr) {
		xil_printf("[E] LookupConfig failed!\r\n");
		return XST_FAILURE;

	status = XAxiCdma_CfgInitialize(&axiCdmaInstance, cfgPtr, cfgPtr->BaseAddress);
	if (status != XST_SUCCESS) {
		xil_printf("[E] CfgInitialize failed!\r\n");
		return XST_FAILURE;

	// Disable interrupts, we use polling mode
	XAxiCdma_IntrDisable(&axiCdmaInstance, XAXICDMA_XR_IRQ_ALL_MASK);

	for (int i = 0; i < numberOfTransfers; ++i) {
		xil_printf("[I] ====== Transfer #%d ======\r\n", i);
		status = doTransfer(&axiCdmaInstance, BUFFER_SIZE, numberOfTries);
		if (status != XST_SUCCESS) {
			xil_printf("[E] Transfer failed!\r\n");
			return XST_FAILURE;

	return XST_SUCCESS;

static int doTransfer(XAxiCdma *instancePtr, int length, int retries) {

	int status;
	u32  *srcPtr;
	u32  *dstPtr;

	// Initialize the source buffer bytes with a pattern and the
	// the destination buffer bytes to zero
	srcPtr = (u32 *) srcBuffer;
	dstPtr = (u32 *) dstBuffer;
	xil_printf("[I] SrcPtr = 0x%x :: DstPtr = 0x%x\r\n", srcPtr, dstPtr);

	for (int i = 0; i < BUFFER_SIZE; ++i) {
		srcPtr[i] = i & 0xFF;

	// Flush the SrcBuffer before the DMA transfer, in case the Data Cache is enabled
	Xil_DCacheFlushRange((UINTPTR)&srcBuffer, length);
#ifdef __aarch64__
	Xil_DCacheFlushRange((UINTPTR)&dstBuffer, length);

	// Try to start the DMA transfer
	while (retries) {
		status = XAxiCdma_SimpleTransfer(instancePtr, (UINTPTR)srcBuffer,
			(UINTPTR)dstBuffer, length, NULL, NULL);
		if (status == XST_SUCCESS) {

	// Return failure if failed to submit the transfer
	if (!retries) {
		xil_printf("[E] XAxiCdma_SimpleTransfer failed!\r\n");
		return XST_FAILURE;

	// Wait until the DMA transfer is done
	while (XAxiCdma_IsBusy(instancePtr)) {

	//This is a poll method and error conditions not cleared by the driver.
	error = XAxiCdma_GetError(instancePtr);
	xil_printf("[I] GetError from XAxiCdma 0x%x\r\n", error);
	if (error != 0x0) {
		int timeOut = RESET_LOOP_COUNT;

		// Need to reset the hardware to restore to the correct state
		while (timeOut) {
			if (XAxiCdma_ResetIsDone(instancePtr)) {

		return XST_FAILURE;

	// Transfer has been completed successfully, check data
	status = checkData(srcPtr, dstPtr, length);
	if (status != XST_SUCCESS) {
		xil_printf("[E] Check data failed!\r\n");
		return XST_FAILURE;

	return XST_SUCCESS;

static int checkData(u32 *srcPtr, u32 *dstPtr, int length) {

	// Invalidate the DestBuffer before receiving the data, in case the
	// Data Cache is enabled
#ifndef __aarch64__
	Xil_DCacheInvalidateRange((UINTPTR)dstPtr, length);

	for (int i = 0; i < length; ++i) {
		xil_printf("[I] checkData %d: 0x%x\t%d\r\n", i, dstPtr+i, dstPtr[i]);
		if ( dstPtr[i] != srcPtr[i]) {
			return XST_FAILURE;

	return XST_SUCCESS;
0 Kudos