dmaloop实验axi stream时序分析

DMALOOP实验,用来分析axi stream时序,先将原理图和实验ILA所折图展示如下:

dmaloopdemo实验是OK的,ILA中时序发现:
stream data fifo M_AXIS接口(即传给DMA的S2MM):传输时,先将tlast下拉,同时刻tvalid上拉,这两步做完,因tready恒=1,估计下一个时钟周期上升沿时总线就会认为开始传输数据了;结束时,因tvalid从第一次传输开始就一直=1,所以先上拉tlast,一个周期之后tvalid下拉,但要注意:tlast却没有下拉,始终还是=1,具体可以看https://my.oschina.net/u/4583591/blog/4701373中所说:“ master将TLAST拉高,TVALID拉低,传输结束”。
stream data fifo S_AXIS接口(即DMA的MM2S传给fifo),用来接收内存通过DMA下发来的数据,tvalid上拉表示数据开始传输,当DMA需要结束传输数据给stream data fifo时,首先上拉tlast,下个周期上升沿(B)将tvalid和tlast全部都下拉(我分析,应该是B上升沿之前,将数据放到总线上,此时判断出tlast==1,tvalid和tready都==1,所以B之后需要将tvalid和tlast都下拉)。main.c中代码如下:


/*
 *
 * www.osrc.cn
 * www.milinker.com
 * copyright by li yang mi lian dian zi www.osrc.cn
 * axi dma test
 *
*/

#include "dma_intr.h"
#include "sys_intr.h"


static XScuGic Intc; //GIC
static  XAxiDma AxiDma;

volatile u32 success;


int Tries = NUMBER_OF_TRANSFERS;
int i;
int Index;
u8 *TxBufferPtr= (u8 *)TX_BUFFER_BASE;
u8 *RxBufferPtr=(u8 *)RX_BUFFER_BASE;
u8 Value;


int axi_dma_test()
{
	int Status;
	TxDone = 0;
	RxDone = 0;
	Error = 0;

	xil_printf("\r\n----DMA Test----\r\n");

	xil_printf("PKT_LEN=%d\r\n",MAX_PKT_LEN);


	//while(1)
	for(i = 0; i < Tries; i ++)
	{
		Value = TEST_START_VALUE + (i & 0xFF);
		for(Index = 0; Index < MAX_PKT_LEN; Index ++) {
				TxBufferPtr[Index] = Value;

				Value = (Value + 1) & 0xFF;
		}

		/* Flush the SrcBuffer before the DMA transfer, in case the Data Cache
		 * is enabled
		 */
		Xil_DCacheFlushRange((u32)TxBufferPtr, MAX_PKT_LEN);

		Status = XAxiDma_SimpleTransfer(&AxiDma,(u32) RxBufferPtr,
					MAX_PKT_LEN, XAXIDMA_DEVICE_TO_DMA);

		if (Status != XST_SUCCESS) {
			return XST_FAILURE;
		}

		Status = XAxiDma_SimpleTransfer(&AxiDma,(u32) TxBufferPtr,
					MAX_PKT_LEN, XAXIDMA_DMA_TO_DEVICE);

		if (Status != XST_SUCCESS) {
			return XST_FAILURE;
		}

		/*
		 * Wait TX done and RX done
		 */
		while (!TxDone || !RxDone) {
				/* NOP */
		}

		success++;
		TxDone = 0;
		RxDone = 0;

		if (Error) {
			xil_printf("Failed test transmit%s done, "
			"receive%s done\r\n", TxDone? "":" not",
							RxDone? "":" not");
			goto Done;
		}
		/*
		 * Test finished, check data
		 */
		Status = DMA_CheckData(MAX_PKT_LEN, (TEST_START_VALUE + (i & 0xFF)));
		if (Status != XST_SUCCESS) {
			xil_printf("Data check failed\r\n");
			goto Done;
		}

	}
	xil_printf("AXI DMA interrupt example test passed\r\n");
	xil_printf("success=%d\r\n",success);
	/* Disable TX and RX Ring interrupts and return success */
	DMA_DisableIntrSystem(&Intc, TX_INTR_ID, RX_INTR_ID);
Done:
	xil_printf("--- Exiting Test --- \r\n");
	return XST_SUCCESS;

}

int init_intr_sys(void)
{
	DMA_Intr_Init(&AxiDma,0);//initial interrupt system
	Init_Intr_System(&Intc); // initial DMA interrupt system
	Setup_Intr_Exception(&Intc);
	DMA_Setup_Intr_System(&Intc,&AxiDma,TX_INTR_ID,RX_INTR_ID);//setup dma interrpt system
	DMA_Intr_Enable(&Intc,&AxiDma);
}

int main(void)
{

	init_intr_sys();
	axi_dma_test();

}


根据https://wenku.baidu.com/view/a2d9ed1900020740be1e650e52ea551811a6c945.html 中所说,“ready由从设置驱动,表示从设备下一个时钟周期上升沿到来时能够接收数据,注意:是下一个时钟上升沿时接收数据。tlast和数据一起传输。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章