该部分是配合DMA的写通道来仿真并确定实际使用过程中的带AXI4-stream接口的自定义IP核代码。
第一部分有提到,原example design在axi交换的时候存在两个问题。

  • 第一是从机的tready信号一定要先于主机的valid信号。
  • 第二是包传输的时候,存在tlast信号未被正确识别的问题,这个问题可以理解为最后一个数据主机这边在数据总线上更新了,且也标明了tlast标志,但未确认从机正确接收最后一个数据导致最后一个数据未被正确接收,从而包传输出错。

然而在实际使用的时候,上述错误发送的情况有时候是不成立的,这取决于从机axi协议的实际情况,例如本随笔中使用的DMA的写通道axi协议的实际情况就避免了第一个问题的发生,具体情况请看下文。
首先是DMA IP核的设置,这里是参考设置,只用到了写通道,表明传输方向为DEVICE TO DMA,即PL端的某个数据源向PS端的内存写入。
这里简单介绍一些参数详细意义

  • Width of Buffer Length Register:最大传输字节数,这里是14,即2^14个。
  • Address Width:实际内存地址宽度,例如我的PS端内存使用地址为0x0000_0000-0x7FFF_FFFF,那这里就填32。
  • Number of Channels:这里默认为1,不可选,只有选中上面的Enable Scatter Gather Engine和Enable Multi Channel Support,才可输入。
  • Memory Map Data Width:内存数据宽度,需与Stream Data Width匹配或更大。
  • Stream Data Width:定义AXI4-Stream接口的数据位宽(8~1024位),必须≤Memory Map Data Width。
  • Max Burst Size:最大突发传输长度,这里是16,意味着,一次最大传输16个32位数据,对应PS端那边为64个字节。

    然后我们打开example design并设置好如下仿真参数后,点击仿真


这里有四个要注意的地方

  • 1.在s2mm_prmry_reset_out_n 复位信号拉高一个周期之后,s_axis_s2mm_tready立即拉高。
  • 2.s_axis_s2mm_tvalid 要后于s_axis_s2mm_tready有效,且S2MM通道接收了四个32位数据32'h0000_0000、32'h01010101、32'h02020202、32'h03030303后s_axis_s2mm_tready立即拉低。
  • 3.在41个周期之后(可能数错,不确定是否固定)s_axis_s2mm_tready拉高继续数据传输。
  • 4.黄线代表一次突发传输中最后一个数据的传递,这里s_axis_s2mm_tlast是拉高的,代表包传输的最后一个数据。但是一包结束之后,S2MM通道发生了类似于第一个注意点的行为,即又拿了四个,可以理解为下一次突发传输的数据被提前传了四个数据。

当然实际在使用DMA来进行PS端和PL端交互的时候,会产生很多问题,这里贴几个网址

还有解决方案的网址,后面我会在实际仿真和测试解决方案之后(我目前已解决这个问题),给出一个详细的解释(时间稍长,请等待)