软件版本:VIVADO2017.4 操作系统:WIN10 64bit 硬件平台:适用米联客 ZYNQ系列开发板 米联客(MSXBO)论坛:www.osrc.cn答疑解惑专栏开通,欢迎大家给我提问!! 22.2概述 本课在AXI_DMA_LOOP 环路测试架构的基础上,在DATA FIFO端加入FPGA代码,对FIFO写,实现将PL端数据通过DMA发送给PS功能。 22.2 FPGA BD工程 在上图中,红色标记是需要引出到顶层模块用于PL部分编写用户控制逻辑的信号。 22.2.1 ZYNQ IP的设置 增加一路FCK_CLK1 为100MHZ(也可以设置其他频率)并且引出到外部提供verilog编程时钟。 22.2.2 FIFO的设置双击S_AXIS设置参数 设置如下 双击FIFO 进行如下设置 22.2.3 DMA的设置勾选DMA读写通道,设置Width of Buffer Length Register为23 22.2.4 GPIO的配置双击axi_gpio_0。设置如下图所示 22.3 FPGA 的发送代码always@(posedge FCLK_CLK0) begin if(!peripheral_aresetn) begin S_AXIS_tvalid <= 1'b0; S_AXIS_tdata <= 32'd0; S_AXIS_tlast <= 1'b0; state <=0; end else begin case(state) 0: begin if(gpio_tri_o_0&& S_AXIS_tready) begin S_AXIS_tvalid <= 1'b1; state <= 1; end else begin S_AXIS_tvalid <= 1'b0; state <= 0; end end 1:begin if(S_AXIS_tready) begin S_AXIS_tdata <= S_AXIS_tdata + 1'b1; if(S_AXIS_tdata == 16'd510) begin S_AXIS_tlast <= 1'b1; state <= 2; end else begin S_AXIS_tlast <= 1'b0; state <= 1; end end else begin S_AXIS_tdata <= S_AXIS_tdata; state <= 1; end end 2:begin if(!S_AXIS_tready) begin S_AXIS_tvalid <= 1'b1; S_AXIS_tlast <= 1'b1; S_AXIS_tdata <= S_AXIS_tdata; state <= 2; end else begin S_AXIS_tvalid <= 1'b0; S_AXIS_tlast <= 1'b0; S_AXIS_tdata <= 32'd0; state <= 0; end end default: state <=0; endcase end end |
22.4 PS部分 在main.c源码中,实现了数据DMA的测速,并且通过串口打印出来。为了实现测试,增加了定时间中断,定时器每过0.5S中断一次。 中断初始化函数,如下 init_intr_sys函数 int init_intr_sys(void) { DMA_Intr_Init(&AxiDma,0);//initial interrupt system Timer_init(&Timer,TIMER_LOAD_VALUE,0); 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 Timer_Setup_Intr_System(&Intc,&Timer,TIMER_IRPT_INTR); DMA_Intr_Enable(&Intc,&AxiDma); } |
DMA读测速的部分的原理是计数DMA读传输的次数,然后每过2秒,计算一次速度。通过串口打印测速。 测试代码 if(RxDone) { //确保cache的数据都进入DDR Xil_DCacheInvalidateRange((u32)RxBufferPtr, MAX_PKT_LEN); RxDone=0; RX_ready=1; RX_success++; }
if(TxDone) { TxDone=0; TX_ready=1; TX_success++; } if(usec==2) {
usec=0;
xil_printf("RX=%d\r\n",RX_success); speed_rx = MAX_PKT_LEN*RX_success/1024/1024; sprintf(speed_r,"RX_sp=%.2fMB/S",speed_rx); xil_printf("%s\r\n",speed_r);
xil_printf("TX=%d\r\n",TX_success); speed_tx = MAX_PKT_LEN*TX_success/1024/1024; sprintf(speed_t,"TX_sp=%.2fMB/S",speed_tx); xil_printf("%s\r\n",speed_t);
RX_success=0; TX_success=0;
} |
定时器中断在《ZYNQ 定时器中断实验》已经详细讲解过,至于DMA中断《AXI_DMA_LOOP 环路测试》中也已经详细讲解,不在过多复述。 22.5 验证测试串口打印输出: 观察内存中的数据 |