软件版本:VIVADO2017.4
操作系统:Ubuntu16.4 64bit
硬件平台:适用米联客 ZYNQ系列开发板
米联客(MSXBO)论坛:www.osrc.cn答疑解惑专栏开通,欢迎大家给我提问!!
1.1 课程介绍
这一章开始主要介绍 XILINX FPGA PICE IP XDMA IP的使用。XDMA IP使用部分教程分LINUX 篇和WINDOWS篇两个部分。通过实战,面向应用,提供给大家 XILINX FPGA PCIE 应用解决方案。
本教程以MZ7035FA作为样机测试。在正式开始教程内容前,有必要把MZ7035FA开发板的特点说明下。这是一款高性价比的FPGA开发板。带PCIE接口,SFP光通信接口,3路千兆以太网口,2路SATA接口,1路HDMI输出,1路串口,1路TF卡接口。支持MSXBO(米联客)FEP标准扩展接口。采用的CPU型号为XC7Z035-FFG676。PL端搭载32bit 1024MB DDR3内存,PS端搭载32bit 1024MB DDR3内存,FPGA读写DDR支持的最大数据时钟为1600M,可以进行很多复杂的开发任务。
教程的内容完全适合其他开发板。如果读者使用过程中遇到问题,可以在我们讨论课程网页留言(米联客(MSXBO)论坛www.osrc.cn答疑解惑专栏开通,欢迎大家给我提问)。我们会在论坛上公布相关课程内容和源码。
1.2 XDMA 概述
Xilinx 提供的DMASubsystem for PCIExpressIP是一个高性能,可配置的适用于PCIE2.0,PCIE3.0 的SG 模式 DMA,提供用户可选择的 AXI4 接口或者 AXI4-Stream接口。一般情况下配置成 AXI4 接口可以加入到系统总线互联,适用于大数据量异步传输,通常情况都会使用到 DDR,AXI4-Stream 接口适用于低延迟数据流传输。
XDMA 是SGDMA,并非Block DMA,SG 模式下,主机会把要传输的数据组成链表的形式,然后将链表首地址通过BAR 传送给XDMA,XDMA 会根据链表结构首地址依次完成链表所指定的传输任务。
1.3 XDMA 提供如下接口:
- AXI4、AXI4-Stream,必须选择其中一个,用来数据传输
- AXI4-Lite Master,可选,用来实现PCIE BAR 地址到 AXI4-Lite 寄存器地址的映射,可用来读写用户逻辑寄
存器
- AXI4-Lite Slave,可选,用来将XDMA 内部寄存器开放给用户逻辑,用户逻辑可以通过此接口访问 XDMA
内部寄存器,不会映射到BAR
- AXI4 Bypass 接口,可选,用来实现PCIE 直通用户逻辑访问,可用于低延迟数据传输
1.4 XDMA IP 配置
Mode:配置模式,选择 Advanced 高级配置
Lane Width:MZ7035 支持X4
Max Link Speed:选择5.0GT/s 即PCIE2.0
Reference Clock :100MHZ,参考时钟 100M
DMA Interface Option:接口选择 AXI4 接口
AXI Data Width:128bit,即 AXI4 数据总线宽度为128bit
AXI Clock :125M,即AXI4 接口时钟为 125MHZ
PCIE ID 配置
我们配置成 Memory controller 让 IP 自动选择VID 等
PCIE BAR 配置,这里面的配置比较重要
首先使能 PCIE to AXI Lite Master Interface ,这样可以在主机一侧通过PCIE 来访问用户逻辑侧寄存器或者其他 AXI4-Lite 总线设备
映射空间选择 1M,当然用户也可以根据实际需要来自定义大小。
PCIE to AXI Translation:这个设置比较重要,通常情况下,主机侧PCIE BAR 地址与用户逻辑侧地址是不一样的, 这个设置就是进行BAR 地址到AXI 地址的转换,比如主机一侧 BAR 地址为0,IP 里面转换设置为 0x80000000, 则主机访问 BAR 地址 0 转换到AXI LIte 总线地址就是0x80000000
PCIE to DMA Interface :选择64bit 使能
DMA Bypass 暂时不用
PCIE 中断设置
User Interrupts:用户中断,XDMA 提供16 条中断线给用户逻辑,这里面可以配置使用几条中断线。
Legacy Interrupt:XDMA 支持 Legacy 中断
选择 MSI 中断
注意:MSI 中断和 MSI-X 中断只能选择一个,否则会报错,如果选择了 MSI 中断,则可以选择 Legacy 中断, 如果选择了 MSI-X 中断,那么 MSI 必须取消选择,同时Legacy 也必须选择None。此 IP 对于7 系列设置有这么 个问题,如果使用Ultrascale 系列,则可以全部选择
配置DMA 相关内容
Number of DMA Read Channel(H2C)和Number of DMA Write Channel(C2H)通道数,对于PCIE2.0 来说最大 只能选择 2,也就是 XDMA 可以提供最多两个独立的写通道和两个独立的读通道,独立的通道对于实际应用中 有很大的作用,在带宽允许的前提前,一个PCIE 可以实现多种不同的传输功能,并且互不影响。这里我们选择1
Number of Request IDs for Read (Write)channel :这个是每个通道设置允许最大的 outstanding 数量,按照默 认即可
配置完成以后,点击 Run Block Auto,可以看到之前的配置信息,如果有发现和目标配置不一样的,需要手动 修改,点击 OK,完成配置
配置完成以后,VIVADO 会自动进行必要的连接
到此为止,XDMA IP 配置就完成了只要再进行时钟和 GTP 约束即可。
1.5 MIG 7 SERIES 的配置
Step1:任单击 IP Catalog,选取 Memory Interface Generator(MIG 7 series)IP 添加到 Block design。双击 MIG 7 SERIES ,对这个 IP 进行配置。
双击生成的IP核
单击NEXT
继续单击NEXT
选择DDR3 单击NEXT
设置MIG 内核时钟频率为、内存型号、内存的数据位宽
设置MIG AXI4 最大支持的位宽,对于2片DDR 最大位宽为256bit
设置输入频率
系统和参考时钟时钟选择no buffer,MIG低电平复位
Step9:终端阻抗选择50hms,设置DCI
选择Fixed Pin Out
根据原理图手动填写PIN 脚定义,或者选择Read XDC/UCF直接读入pin脚定义,本课程下提供了MZ7035.ucf 的DDR 配置文件,直接读入既可。
填写完成后,先单击Validate再单击NEXT
继续单击NEXT
继续单击NEXT
继续单击NEXT
继续单击NEXT
最后单击Generate,至此MIG的配置完成
1.6 基础测试系统搭建
我们的测试目标是进行PCIE AXI4总线与外设进行读写操作,PCIE AXI4-Lite 总线进行用户逻辑寄存器或者其他 AXI4-Lite 总线设备访问操作。AXI4总线上挂载到MIG控制器DDR上去,实现对DDR的读写控制。
为此搭建系统为下图所示:
进行地址分配:
这里我们把挂在M_AXI上的DDR地址分配从0开始(对于widnows系统必须为0), M_AXI是需要进行DMA操作的。而M_AXI_LITE挂载的BRAM是需要进行BAR空间操作,所以地址设置为0x80000000和XMDA IP里面设置的地址对应。
1.7 LINUX下驱动程序编译\安装\测试
1.7.1 驱动编译和安装(下必须重新编译)
官方驱动包选择 2017 版本以后的,注意 2016 版本的有 BUG!!!
在终端进入到 xdma 目录,输入 make ,进行驱动编译
执行以下指令:
- Change directory to the driver directory.
cd driver
- Compile the kernel module driver.
make
- Change directory to the tests directory.
cd tests
- Compile the provided example software.
make
- Copy the provided driver rules from the etc directory to the
/etc/ directory on your system.
cp ../etc/udev/rules.d/* /etc/udev/rules.d/
关于驱动加载,这里有两点要说明一下,首先是在驱动加载之前,如果检测到系统中已经加载过驱动,那么它会将已经加载的驱动卸载,然后再加载。然后就是PCIe DMA的工作方式可以通过加载驱动传输参数进行修改。默认情况下DMA工作在中断模式,可以通过修改load_driver.sh脚本改为轮循模式如下图所示,但是可能驱动有问题,实际测试轮询模式有些程序无法正常执行,所以建议大家不要使用轮询模式。
在准备加载驱动前,确保你的开发板已经下载PCIE工程的bit文件,而且已经重启过电脑。好了,现在加载驱动。
./load_driver.sh
如下显示驱动安装成功
在终端执行命令:
./dma_from_device -d /dev/xdma0_c2h_0 -f ./test.bin -s 4096 -a 0 -c 1
./dma_to_device -d /dev/xdma0_h2c_0 -f ./test.bin -s 4096 -a 0 -c 1
-d:device 设备.
-f:file 文件
-s:size 大小
-a:addr 起始地址
-c:count
这两个操作分别是从板卡读 4096 Bytes 数据到文件 test.bin 以及从 test.bin 读出4096 Bytes 数据发送给板卡。