可替代Vivado的开源编译工具链
笔者曾经使用 Digital IDE 在 VSCode 中进行文件编辑并使用 Vivado 进行综合、布线和生成比特流。近来笔者苦于 Vivado 编译过程过慢而希望寻找速度更快的(开源)解决方案。在 Gemini 和 Claude 的帮助下成功部署。笔者使用的是基于 Xilinx xc7a35tfgg484-2 芯片的开发板。
需求清单
部署
对于 xc7a35tfgg484-2 型号的 Xilinx 开发板,目前有完善的全开源解决方案:
- 综合与布线:Yosys + nextpnr-xilinx
- 比特流生成:nextpnr-xilinx
- 烧录:openFPGALoader
其中第一步与第二步暂无 Windows 下的解决方案,但有完善的 docker 镜像 regymm/openxc7。openFPGALoader 可以通过 MSYS2 在 Windows 上安装。MSYS2 是一个在 Windows 上模拟 Unix 命令行和环境的模拟器。烧录时,默认的下载器驱动可能无法被 openFPGALoader 识别,需要使用 Zadig 换一下驱动。
环境准备
安装 Docker
略
安装 MSYS2
MSYS2 是一个在 Windows 上模拟 Unix 命令行和环境的模拟器,openFPGALoader 依赖于它来提供类 Unix 的环境和工具链。
推荐使用 Scoop 安装
1 | scoop install msys2 |
或者直接从 MSYS2 官网 下载安装包,安装后将 msys2.exe 所在目录加入环境变量 PATH。
安装 openFPGALoader
安装完 MSYS2 后,进入 MSYS2 终端
1 | msys2 -mingw64 |
首次进入时 MSYS2 可能会更新它的包管理器。待它更新完成后,安装 openFPGALoader
1 | pacman -S mingw-w64-x86_64-openFPGALoader |
安装 Zadig
Zadig 是一个 Windows 下的 USB 驱动安装工具,可以用来替换默认的 USB 驱动,使 openFPGALoader 能够识别开发板。
推荐使用 Scoop 安装
1 | scoop bucket add nonportable |
或者直接从 Zadig 官网下载。下载的 exe 文件可以直接运行,无需安装。
编译步骤
笔者的项目结构如下
1 | ./ |
启动 Docker 容器
docker/docker-compose.yml 定义了一个基于 regymm/openxc7 镜像的服务,挂载了 docker/ 的父目录(即项目根目录)到容器内的 /mnt/workspace 目录。文件内容如下
1 | services: |
在项目根目录下运行以下命令启动 Docker 容器
1 | docker compose -f docker/docker-compose.yml up -d |
在所有工作完毕后,可以运行以下命令停止 Docker 容器
1 | docker compose -f .\docker\docker-compose.yml down |
编译
编译脚本 docker/compile.sh 定义了综合、布线和比特流生成的步骤。脚本内容如下
1 |
|
脚本前部定义了一些变量,可以根据自己的项目结构和文件名进行修改:
PROJ_NAME:项目名称,编译输出文件将保存在$BUILD_DIR/$PROJ_NAME/目录下TOP_MODULE:顶层模块名称SRC_FILE:Verilog 源文件路径,可以使用通配符XDC_FILE:约束文件路径BUILD_DIR:编译输出的根目录
需要注意的是,脚本硬编码了 Xilinx xc7a35tfgg484-2 这个型号的芯片,用户如果使用其他型号的芯片,需要修改脚本中的相关参数和路径。
脚本修改完成后,执行以下命令在 Docker 容器内运行编译脚本。第一次编译时会生成一个芯片架构数据库文件 xc7a35t.bin,这个过程可能会比较慢,但后续编译会直接使用这个文件,不需要重复生成。
1 | docker exec -it fpga_openxc7_env "docker/compile.sh" |
最终生成的比特流文件 design.bit 将保存在 $BUILD_DIR/$PROJ_NAME/ 目录下,可以使用 openFPGALoader 烧录到 FPGA 上。
烧录
将开发板连接到电脑。首先检查 openFPGALoader 是否能够识别开发板
1 | msys2 -mingw64 -c "openFPGALoader --detect" |
正常输出应类似
1 | empty |
如果输出显示没有找到设备,需要使用 Zadig 替换默认的 USB 驱动。打开 Zadig,菜单栏 Option 中选择 List All Devices,然后在设备列表中找到对应的设备(通常是一个 FTDI 设备,名称通常是 Logic_CPU),它具有 Interface 0 和 Interface 1 两个接口。一般 Interface 0 是 JTAG 接口,用于烧录,Interface 1 是 UART 接口,用于串口通信。选择 Interface 0,点击 Replace Driver 按钮,将它的驱动替换为 WinUSB 即可。Interface 1 的驱动保持不变。驱动替换后,在 Windows 设备管理器中对应的接口会从“端口”变成“通用串形总线设备”。如后续希望将驱动改回默认的 FTDI 驱动,在 Windows 设备管理器中找到对应的接口,右键选择卸载设备,并勾选“尝试删除此设备的驱动程序”,卸载后重新插拔开发板即可。
更换驱动后再次运行 msys2 -mingw64 -c "openFPGALoader --detect",即可正确识别开发板。然后运行以下命令烧录比特流到 FPGA 上
1 | msys2 -mingw64 -c "openFPGALoader <path_to_your_bitstream>" |
其中 <path_to_your_bitstream> 替换成实际的比特流文件路径,按照笔者的项目结构即为 build/my_fpga_project/design.bit。
局限
- 目前的开源时序数据库大多是基于逆向工程估算的,它在极限高频时序驱动优化上的精度暂时还比不上商业版的 Vivado。如果设计的系统运行时钟频率非常高(超过百兆赫兹),在开源的
nextpnr阶段可能会面临稍大的时序闭合挑战。但对于大部分常规设计,这套开源工具链组合已经可以提供无缝端到端体验。 - 这套开源工具链还不能支持大多数 Vivado IP 核。



