这一篇在干嘛?

FPGA 是 SRAM 工艺器件——断电即失忆,每次上电都要从 Flash 把位流(Bitstream,描述你逻辑设计的二进制文件)搬进芯片,这个过程叫加载(Configuration,配置)。本篇讲安路 EF2/EF3/EG4 的全部加载方式:MSPI 主动加载、Dual/Multi Boot 双保险、从动串行/并行,以及最实用的两块:加载失败怎么排查、量产在线升级怎么做。IO 特性前置篇见:硬件接口(一)硬件接口(二),Flash 细节见:硬件接口(四)

加载模式总览与启动方式

MSPI:最常用的主动加载

MSPI 加载速度与时间计算

Dual Boot 与 Multi Boot

从动串行(SS)

从动并行(SP)

加载失败排查

在线升级

SVF 与 AJE 文件

加载模式总览与启动方式

先分清两代器件的加载模式配置方法,这不一样

  • EF2、EF3(内置 Flash):加载模式由 **Flash 里的位流参数(TD 软件选项)**决定,绝大部分场景用 MSPI 模式(从内部 Flash 加载)——因为它 Flash 都合封好了,没必要折腾别的。
  • EG4、PH1(外挂 Flash):加载模式由专用 MSEL 管脚的电平(外部上下拉电阻决定高低)配置。常用模式:MSPI、从动串行(SS)、从动并行(SP)。手册给出 EG4X 的 MSEL 编码:
配置引脚名类型SS:从动串行SP:从动并行MSPI:主动 SPIMP:主动并行 (X8)JTAG
M[1:0]复用11100100XX

比赛用的 EG4S20 属于 EG4 系:MSEL 接成 “01” 就是 MSPI。还有一条保底规则:不管选哪种模式,JTAG 口永远可以加载 FPGA——所以板上务必预留 JTAG 插座(还支持菊花链,一 households 条链挂多颗器件)。

什么事件会触发一次加载?四个入口:

  1. 上电触发 POR(Power-On Reset,上电复位)——最常见,插电就加载;
  2. PROGRAMN 管脚输入低脉冲——外部强制重载(见第二篇的复位按键电路);
  3. JTAG 输入 Refresh 指令——调试器软件按钮本质也是这个;
  4. FPGA 逻辑调用 Multi-Boot 原语,给 rebootn 送低电平——让 FPGA 自己决定”我要重启换逻辑”(后面 Multi Boot 细讲)。

怎么判断加载成功?两个手段:看 DONE 管脚是否拉高(最直接,可点 LED);或者从系统层面验证——通过 FPGA 内部逻辑是否在工作来判断,比如上位机读写一个 FPGA 寄存器。

MSPI:最常用的主动加载

MSPI(Master SPI,主动串行外设接口)模式的”主动”是相对 FPGA 说的:

  • 位流存在 SPI 接口的 Flash 里;
  • FPGA 工作在主模式(Master):FPGA 自己产生时钟,主动从 Flash 里把位流读出来;
  • EG4、PH1 需要外挂一颗 SPI Flash 芯片,并把 MSEL 配置为 MSPI 模式;
  • EF2、EF3 把 Flash Die 直接合封进芯片,而且合封 Flash 的容量都装得下两份位流(这是 Dual Boot 的硬件基础),加载模式的配置参数存在 Flash 起始部分。

EF2/EF3 合封结构:FPGA Die 与 Flash Die 在同一封装内通过片内 SPI 总线互连

这张手册示意图展示 EF2/EF3 的合封:左边是 1.5~9.2K LEs 的 FPGA Die,右边是 Flash Die,两者在同一封装里用 SPI 总线相连。对外看不到 Flash 芯片,省面积也更难被仿制。

EG4X 的 MSPI 模式连接:MSEL[1:0]=01,FPGA 作为 SPI 主机从外部 Flash 读位流

这张是 EG4X 的 MSPI 连接:MSEL[1:0] 用上下拉电阻配成 “01”,FPGA 上电后作为 SPI 主机,从外挂 Flash 读位流。画原理图时 Flash 的 CS/SCLK/MOSI/MISO 必须接在手册指定的专用配置管脚上,不能随便挑 IO。

MSPI 加载速度与时间计算

加载不是瞬间完成的,系统有”上电到可用”的时间指标时就得算加载时间。可调参数有三个维度:

  • 位宽:MSPIx1 / MSPIx2 / MSPIx4(单、双、四线 SPI);
  • 时钟频率 MCLK:EF2、EF3 可选 2.5~24MHz;EG4 可选 2.5~16MHz
  • 计算公式:加载时间 = 位流长度 ÷ 时钟频率 ÷ 加载位宽

TD 软件里的配置项(boot_mode 选 mspix1/x2/x4;mclk_freq_div 选时钟频率):

OptionDescriptionSelection
hswapen加载过程 IO 上拉开关enable √
boot_mode加载模式选择mspix4 √(可选 mp/mspix1/mspix2/mspix4/sp/ss)
mclk_freq_divMCLK 分频2.5~24MHz 多档

带着算一遍(手册实测表,位流 159×8 Kbit = 1272 Kbit,MCLK 2.5MHz):

位流长度 (Kbit)时钟 (MHz)位宽实测时间 (ms)计算时间 (ms)
159×82.54126.8127.2
159×82.52250.8254.4
159×82.51498.8508.8

以 x4 为例:1272 Kbit ÷ 2.5 MHz ÷ 4 = 127.2ms,和实测 126.8ms 几乎重合——公式可信。同样的位流,x4 比 x1 快整整 4 倍(127ms vs 499ms),所以位宽能开 x4 就开 x4

两个隐藏坑(手册备注展开):

  1. MCLK 由 FPGA 内部 OSC(振荡器)分频得到,而 OSC 本身有 30% 频率偏差——所以加载时间也会有 ±30% 的漂移。算系统上电时间指标时要留余量,别把 127ms 当死数用。
  2. 早期 TD 软件频率可选范围偏大,为了批量可靠性,最高几档频率已被禁用——别死磕最高频率,稳比快重要。

Dual Boot 与 Multi Boot

Flash 里只有一份位流,升级写坏就变砖——双保险机制应运而生。

**Dual Boot(双备份启动)**特性:

  • 在 MSPI 模式下工作,且 MSPI 模式自动包含 Dual Boot(不用额外开关);
  • SPI Flash 存两份位流:Primary(主)区域和 Golden(黄金/安全)区域
  • Primary 起始地址固定 0x000000;Golden 的起始地址由指针向量决定,指针本身的存放地址固定(如 EF2 为 0x040000),指针指向的地址理论上可调,但建议用 TD 生成的默认值不要乱改(EF2 默认指向 0x041000);
Dual Boot Flash 地图内容
0x000000Primary 位流
0x040000Golden 地址(指针)
0x041000Golden 位流
  • 工作流程:先加载 Primary → 失败则跳去加载 Golden → Golden 也失败再回头加载 Primary……如此循环。始终找不到合法位流时,INITN 管脚上能观察到连续脉冲——这是”我在空转找位流”的求救信号。

用法定位:Dual Boot 是为在线升级的可靠性服务的——Golden 区域预先烧入一份保底位流,在线升级过程只动 Primary,绝不擦写 Golden。这样升级中途断电、写坏数据,芯片至少还能从 Golden 启动,保住”还能再次升级”的底线。另注意:加载成功后,逻辑代码自己无法直接判断是从哪个区域启动的

**Multi Boot(多重启动)**是更灵活的进阶版:

  • 同样在 MSPI 模式下工作,但要调用 MBOOT 原语,由用户逻辑代码控制重新加载的时机和目标位流的地址;
  • 三个参数调整加载起始地址:ADDR_SOURCE_SEL、STATIC_ADDR、dynamic_addr
  • rebootn:重启控制信号,低有效,低电平至少维持 2500ns
  • 重要差异:Multi Boot 加载失败后 FPGA 会挂死,不会自动回落到 Primary 区域——灵活的代价是没有 Golden 兜底,用在能保证位流可靠性的场景。

从动串行(SS)

从”FPGA 当主机”翻转到”FPGA 当从机”:位流由外部主机(MCU/CPU)提供,FPGA 只负责接收。SS(Slave Serial,从动串行)单芯片模式

  • 主机通过 SCLK、DIN 两个信号把位流送进 FPGA,SCLK 上升沿采样
  • 注意文件位序差异:bin 文件每个字节高位(MSB)先送,rbf 文件每个字节低位(LSB)先送——发错了整片位流全错;
  • 配置出错:FPGA 把 INITN 拉低表示加载失败;DONE 拉高表示配置完成;
  • 级联模式:多颗 FPGA 可串成一条链,多个位流文件分别读取发送,也可合并为一个文件连续发送;文件切换时 PROGRAMN、SCLK 状态保持不变

从动串行配置时序:PROGRAMN 低脉冲 T_program_b,等 INITN 拉高后才送数,SCLK 上升沿采样 DIN,最后 DONE 拉高

这张时序图是 SS 模式的”交通规则”全图,重点看四个时间参数:T_program_b(PROGRAMN 低脉冲宽度,太短无效)、T_init_b(PROGRAMN 释放后到 INITN 拉高的初始化时间,INITN 没拉高前绝不能发数据)、T_dsu/T_dh(DIN 相对 SCLK 的建立/保持时间)、T_cl/T_ch(SCLK 低/高电平宽度)。DONE 在数据末尾拉高,之后进入 User mode。

从动串行级联连接:MCU 的 CCLK/DIN 驱动第一片 EG4X,其 DOUT 接下一片 DIN 形成菊花链

这张是 SS 级联接线图:MCU 发 CCLK、DIN,第一片 EG4X 收完自己的位流后从 DOUT 把后续数据转发给下一片的 DIN(菊花链);PROGRAMN/INIT_B/DONE 三条状态线全链共享,VCCIO 上有上拉。不同器件的 T_program_b、T_init_b 数值不同,混链时要以最慢的器件为准,并注意建立保持时间。

从动并行(SP)

SP(Slave Parallel,从动并行)模式——把串行改成 8 位并行,加载速度更快:

  • FPGA 作为从器件,通过 SCLK + DATA[7:0] 8 位总线收位流,SCLK 上升沿采样;
  • 片选 CSN:0 允许写入数据,1 禁止写入
  • 文件处理:bin 文件按字节直发接 DIN[7:0];rbf 文件每个字节的 bit 顺序要颠倒再发(又是位序坑);
  • 出错拉低 INITN、完成拉高 DONE,与 SS 相同;
  • 级联两种玩法:①多个位流合并为一个文件连续发送,用 CSI/CSO 串接实现级联(前一片的 CSO 接下一片的 CSI);②多文件分别发送,主机出多个片选 CS 分别接各片的 CSI。多颗 FPGA 加载过程中 PROGRAMN、SCLK 保持不变。

从动并行配置时序:在 SS 时序基础上增加 CSN 片选与 8 位 DATA 总线

这张时序图比 SS 多了 CSN 和 DATA[7:0]:CSN 拉低后数据才有效,同样要遵守 T_program_b → 等 INITN 高 → 按 T_dsu/T_dh 送数 → DONE 拉高的流程。

从动并行级联连接:CPU/外部主机通过 DATA[7:0]/CSN/CLK 驱动两片 EG4X,M[1:0]=10,CSI/CSO 菊花链接

这张是 SP 级联接线图:主机 DATA[7:0] 总线挂两片 FPGA,第一片 CSO_B 接第二片 CSI_B;两片 M[1:0] 都接 “10”(SP 模式),PROGRAMN/INIT/DONE 共享。SS 和 SP 的备注完全一致:注意 T_program_b 脉宽、等 INITN 拉高再发数、关注 T_dsu/T_dh 建立保持时间

常见坑:INITN 还没拉高就开始发位流

从串/从并模式最经典的加载失败原因:主机看到 PROGRAMN 变高就立刻发数据,但 FPGA 初始化还没完成(INITN 尚未拉高),数据全被丢弃。正确流程:PROGRAMN 拉高 → 等 INITN 拉高 → 开始送数 → DONE 拉高后还要补若干时钟(bin 文件尾部有 Dummy 字节)。

加载失败排查

这部分是 FAE 实战经验的浓缩,按模式分开看。

MSPI 模式排查

  • 用 JTAG 回读 Flash 内容,与原始 bin 文件逐字节比较——位流不能有任何 bit 错误(一个 bit 错可能就加载失败或跑飞);
  • 检查电源、PROGRAMN、INITN、DONE 等配置管脚的硬件连接与电平;
  • 降低 MCLK 频率再试——老 TD 版本最高几档频率本来就有风险。

从串、从并模式排查

  • PROGRAMN 变高后必须等 INITN 变高才能写数据;
  • DONE 变高后还要继续送 SCLK,直到唤醒状态机走完——bin 文件结尾有 Dummy 字节,加载失败可以试着再补一些时钟
  • 核对 CCLK 与 DI 的建立保持时间,以及 bin/rbf 的 bit 位序
  • 加载过程中电源跌落 → 电源供电能力不足;
  • PROGRAMN、MSEL 等模式配置管脚出现中间电平或毛刺 → 加载失败(MSEL 是三态编码信号,中间电平可能读错模式);
  • 加载时钟信号质量:JTAG 的 TCK、从串从并的 SCLK 要求边沿单调无回沟,20%~80% 幅度时间小于 10ns,建议时钟源端串 33Ω 电阻改善阻抗匹配。

神器:监测 INITN 管脚做故障定位——INITN 的行为就像体温计,不同”病症”曲线不同:

INITN 表现诊断方向
不跟随 PROGRAMN 变高查各路供电电源;电源正常则芯片可能已损坏
变高后不再变低,但 FPGA 没工作可能是 DONE 后还需继续补送 SCLK
再次拉低的时刻固定查:数据是否在 INITN 拉高前就发了?bit 位序对吗?MSEL 模式配对了吗?
再次拉低的时刻不固定查:电源跌落/纹波?PROGRAMN 毛刺?TCK、SCLK 信号质量?数据时序;从并模式的 RW、CS

在线升级

产品出厂后要远程/本地更新逻辑,这就是在线升级。按器件类型分两条路线:

EG4(MSPI 外接 Flash)——升级通道可以绕开 FPGA:

  • 主设备 CPU 拿到新位流后,直接访问 SPI 接口更新 Flash,完全不经过 FPGA(FPGA 该干嘛干嘛,甚至可以挂掉不影响升级);
  • 或者通过 JTAG 接口操作 SPI Flash,执行 SVF/AJE 文件(见下一节);
  • 或者通过 FPGA 逻辑代码操作 SPI Flash,用桥接逻辑对外提供 UART、SPI、I2C、LocalBus、Ethernet 等接口。

EF2、EF3(MSPI 内置 Flash)——Flash 在片内,外部 CPU 摸不到,只能借道:

  • 通过 JTAG 接口操作 SPI Flash,执行 SVF/AJE 文件;
  • 或通过 FPGA 逻辑代码操作片内 Flash,桥接出 UART、SPI、I2C、LocalBus 等接口(具体原语见硬件接口(四))。

SPI 从动模式(SP/SS):主设备 CPU 拿到新位流后直接重新加载 FPGA 即可。

必须记住的升级安全设计:Flash 编程是先擦除再写入,且擦除按块进行——升级流程若被意外打断(断电、复位)或写入错误数据,Primary 区域的位流可能不完整。所以经由 FPGA 逻辑升级时必须结合 Dual Boot:Golden 区域永不擦写,Primary 坏了至少还能从 Golden 启动,保住一条能再次升级的”生命线”。

SVF 与 AJE 文件

做在线升级工具前,先认识两种”JTAG 指令脚本”文件。

SVF(Serial Vector Format,串行向量格式):IEEE 1149.1 边界扫描编程及测试的事实业界标准语言,所有可编程器件厂商都支持。本质是用文本描述的 JTAG 指令集合,不同内容的 SVF 实现不同功能(编程、校验、擦除……)。用法:通过 TD 的 Device Chain 工具,输入 bit 文件输出 SVF 文件;SVF 支持 JTAG 菊花链。打开一个 SVF 你会看到类似这样的文本:

// Disable Dual boot loop
SIR 8 TDI (80) ;
SDR 64 TDI (00800000000000a5);
RUNTEST 200 TCK ;
// Loading device with 'bypass' instruction
SIR 8 TDI (ff) ;

每行就是一条 JTAG 操作:SIR 写指令寄存器、SDR 写数据寄存器、RUNTEST 跑指定数量的时钟。

AJE(Anlogic JTAG Embedded):可以看作二进制版的 SVF——由 SVF 文件转换生成,JTAG 指令内容完全相同。为什么要转成二进制?给嵌入式 CPU 用:

  • 文件尺寸大幅变小,减小对 CPU 存储空间的占用;
  • 二进制格式便于 CPU 解析,执行效率高;
  • 官方提供转换工具 svf2aje.exe
  • 还提供 CPU 侧参考代码,实现”用普通 IO 模拟 JTAG 时序 + 执行 AJE 文件”的功能——这就是”没有 USB-Blaster 也能升级”的方案。

另有一个 TDE 格式,与 AJE 类似但 CPU 处理代码有差异,兼容 Lattice 的 VME 文件格式,新项目不推荐

调试经验(嵌入式 JTAG 升级开发必看):

  • 先跑最简单的 Check_Device SVF 文件——它能正常执行,说明你的模拟 JTAG 基础时序是对的,再上复杂的编程文件;
  • Flash 操作需要等待时间,延时过短会导致失败——务必校准 CPU 代码里的延时函数(擦除一个扇区可能要几百毫秒,不能想当然)。

本篇通关标准:

  • 能说出 EF2/EF3 与 EG4 加载模式配置方式的区别(Flash 内参数 vs MSEL 管脚)、MSPI 的主从关系,并用公式手算一个位流的加载时间(含 ±30% OSC 偏差意识)。
  • 能画出 Dual Boot 的 Flash 地图(Primary 0x000000 / 指针 0x040000 / Golden 0x041000)、叙述”Primary 失败转 Golden 循环尝试”的流程,并解释为什么在线升级必须保留 Golden。
  • 能从 INITN 的四种异常表现定位加载失败原因,说出”INITN 拉高才能发数、DONE 拉高后补时钟”两条铁律,以及 SVF→AJE 的用途与 Check_Device 调试法。