并行 NOR Flash(PPI NOR)电路设计指南
异步 SRAM 类并行接口 · 8 / 16 位数据总线 · 非复用 / ADM 复用 · 页读与同步突发 · XIP 片内执行 · 多片位宽扩展与地址译码 | 编制日期 2026-09-21 | 版本号 Rev 1.0
0 · 文档说明
适用范围
- 本文针对并行 NOR Flash(Parallel NOR / PPI NOR / 异步 SRAM 类接口 NOR)的硬件电路设计,覆盖 1 Mb ~ 2 Gb 容量段,位宽 8 / 16 位,挂接在 MCU / SoC / FPGA 的外部存储器控制器(EMC / SMC / FMC / EBI / FSMC / Local Bus)上。
- 典型应用:XIP 片内执行(Bootloader / RTOS / 裸机代码)、字库与 UI 资源、固件镜像、配置与校准数据、工业与车载控制板。
- 内容含:选型对比、封装引脚、电气参数、异步/页/突发协议、命令集与 CFI、电源与上电时序、内联 SVG 原理图、等待周期计算、PCB Layout、信号完整性与端接、ESD 与可靠性、焊接生产、故障排查与检查清单。
- 不含文件系统与 Bootloader 软件框架。所有时序数值、命令码、封装球图一律以目标型号 datasheet 为准,本文数值仅为选型与估算的起点。
本系列其他文档
| 文档 | 器件类型 | 关注重点 |
|---|---|---|
| SPI NOR 电路设计指南 | 串行 NOR Flash | Quad/QPI 提速、dummy cycles、XIP、DPD 低功耗 |
| SPI NAND 电路设计指南 | 串行 NAND Flash | 页/块管理、片内 ECC、坏块表、主机 FTL |
| 并行NAND (PPI NAND) 电路设计指南 | 8/16 位并行 NAND | 宽总线时序、ECC 引擎、40+ 引脚 Layout |
| eMMC 电路设计指南 | eMMC 5.0/5.1 | HS200/HS400、1.8 V VCCQ、DS 选通与等长 |
| SD NAND 电路设计指南 | 贴片式 SD NAND | SPI/SDIO 双模式、无休眠指令、VCC 负载开关断电 |
| NAND MCP 电路设计指南 | 多芯片合封存储 | 多 die 与多 CE、双电源轨、HDI 扇出 |
| 并行NOR (PPI NOR) 电路设计指南 本文 | 并行 NOR Flash | 异步读时序、XIP、等待周期、总线扩展 |
| PSRAM 电路设计指南 | 伪静态 RAM | OPI/HyperBus、刷新与延迟周期、XIP 与帧缓存 |
| DDR2 电路设计指南 | DDR2 SDRAM | SSTL_18、T 分支拓扑、VTT 端接、ODT |
| DDR3 电路设计指南 | DDR3 / DDR3L | Fly-by 拓扑、write leveling、动态 ODT |
| DDR4 电路设计指南 | DDR4 SDRAM | POD12、bank group、DBI、2D 训练 |
| DDR5 电路设计指南 | DDR5 SDRAM | 双子通道、On-DIMM PMIC、DFE、同帧 ECC |
| EEPROM 电路设计指南 | EEPROM | I²C/SPI 接口、上拉电阻与总线电容、页写与写保护 |
需要随机读延迟确定、无坏块、无需 ECC、可直接 XIP,且主控本来就带外部总线、引脚不紧张 → 并行 NOR。优势是取指带宽最高、读延迟最小(首字 70 ~ 110 ns,页模式后续 20 ~ 25 ns/字);劣势是引脚消耗大(40 ~ 50 根)、PCB 面积与布线难度最高、每 Mb 成本高于 NAND、擦写慢。
主控没有外部总线或引脚紧张 → 退回 SPI NOR(8 引脚,Quad 50 ~ 100 MB/s);容量 > 256 MB 且成本敏感、可接受"先搬 RAM 再执行"→ 并行 NAND / eMMC / SPI NAND;频繁随机写 → PSRAM / EEPROM 做数据区,NOR 只放代码。
1 · 器件基础
1.1 定位与选型对比
| 维度 | 并行 NOR 本文 | SPI NOR | SPI NAND | 并行 NAND | PSRAM | SRAM |
|---|---|---|---|---|---|---|
| 接口 / 引脚数 | 异步 SRAM 类,40 ~ 50 根 | 4 ~ 6 根 | 6 根 | 8 / 16 位复用,28 ~ 48 根 | 6 根 / 40+ 根 | 并行 30 ~ 50 根 |
| 随机读延迟 | 70 ~ 110 ns(与 SRAM 同量级) | 首字节 60 ~ 100 ns + 指令开销 | 25 ~ 50 µs(页搬 SRAM) | 25 ~ 50 µs(页读) | 70 ~ 100 ns | 10 ~ 70 ns |
| 连续读带宽 | 18 ~ 160 MB/s(异步 → 同步突发) | 30 ~ 100 MB/s | 20 ~ 50 MB/s | 40 ~ 200 MB/s | 50 ~ 200 MB/s | 100 ~ 400 MB/s |
| XIP 能力 | 原生最优(地址直映射) | 好(需 cache / 预取) | 不可需影子 RAM | 不可需影子 RAM | 可以(易失) | 可以(易失) |
| 擦除粒度 | 扇区 4 KB ~ 128 KB | 4 KB / 32 KB / 64 KB | 块 128 KB | 块 128 KB ~ 1 MB | 无(字节写) | 无(字节写) |
| 坏块管理 / ECC | 都不需要 | 都不需要 | 需要 BBT + ECC | 需要 BBT + 硬件 ECC 4 ~ 40 bit | 不需要 | 不需要 |
| 容量范围 | 1 Mb ~ 2 Gb | 512 Kb ~ 2 Gb | 128 Mb ~ 4 Gb | 1 Gb ~ 64 Gb | 4 Mb ~ 256 Mb | 64 Kb ~ 64 Mb |
| 写入吞吐 | 0.1 ~ 1 MB/s(受擦除拖累) | 0.1 ~ 1 MB/s | 1 ~ 8 MB/s | 5 ~ 40 MB/s | 10 ~ 100 MB/s | 50 ~ 200 MB/s |
| 寿命 / 保持 | 10 万次 / 20 年 @ 85 ℃ | 10 万次 / 20 年 | 1 ~ 10 万次 / 5 ~ 10 年 | 0.3 ~ 10 万次 / 2 ~ 10 年 | 易失 | 易失 |
| 每 Mb 成本 | 高 | 中高 | 低 | 最低 | 中 | 最高 |
| PCB 难度 | 高宽总线、等长、SSO | 低 | 低 | 中 | 中 | 中 |
| 典型场景 | 工业 / 车载 XIP、无 DRAM 系统、高可靠启动 | MCU 启动、字库、日志 | 大容量数据、替代小 eMMC | 大容量存储、文件系统 | 低成本大 RAM、帧缓存 | 高速缓存、小容量暂存 |
| 厂商 | 代表系列 | 容量 | 位宽 | 速度等级 | 备注 |
|---|---|---|---|---|---|
| Infineon(原 Cypress / Spansion) | S29GL-P / -S / -R / -T、S29AL-J、S29JL-J | 128 Mb ~ 1 Gb | x8 / x16 | 90 / 100 / 110 ns,页读 25 ns | 市场存量最大,CFI 兼容性好;S / R 支持同步突发 |
| Micron(含原 Numonyx) | M29EW、M29W、MT28EW | 4 Mb ~ 1 Gb | x8 / x16 | 70 / 80 / 90 / 110 ns | M29EW 支持 ADM 复用与突发;MT28EW 为车规 |
| Macronix(旺宏) | MX29GL、MX29LV、MX29F、MX29VS | 1 Mb ~ 1 Gb | x8 / x16 | 70 ~ 120 ns | MX29GL 为 3 V 主流;MX29VS 支持突发 / 页读 |
| Winbond(华邦) | W29GL、W29CL | 32 Mb ~ 512 Mb | x8 / x16 | 90 / 110 ns | 与 S29GL 脚位 / 命令集高度兼容 |
| ISSI | IS29GL、IS29LV | 32 Mb ~ 512 Mb | x8 / x16 | 70 ~ 110 ns | 工业级宽温(-40 ~ +85 ℃)型号齐全 |
| GigaDevice(兆易创新) | 并行 NOR 系列 | 32 Mb ~ 512 Mb | x8 / x16 | 70 ~ 110 ns | 国产替代,引脚 / 命令兼容 S29GL 生态 |
| Numonyx(已并入 Micron) | M58W、M58BW | 8 Mb ~ 128 Mb | x8 / x16 | 70 ~ 90 ns | 存量设计常见,部分支持 VPP / ACC 加速编程 |
| 芯天下 XTX | XT29F(XT29F512ATSHGA / XT29F01GATSHGA);M29F(M29F512BTSJGA / M29F512BBGJGA / M29F01GBTSJGA / M29F01GBBGJGA / M29F02GBBGJGA) | 512 Mb ~ 2 Gb | x8 / x16 | 以 datasheet 为准 | 2.7 ~ 3.6 V;TSOP-56(14×20 mm)与 BGA-64 两种封装。当前均为 ES / UD 状态,量产前须确认转 MP 进度与送样窗口,并逐项核对命令集与球图 |
1.2 封装与引脚定义
| 封装 | 引脚 / 球数 | 本体尺寸 | 间距 | 适用容量 / 位宽 | Layout 要点 |
|---|---|---|---|---|---|
| TSOP-48 | 48 | 12.0 × 20.0 mm | 0.50 mm | x8 或 x16,≤ 256 Mb | 翼形引脚,可飞线调试;占用面积大 |
| TSOP-56 | 56 | 14.0 × 20.0 mm | 0.50 mm | x8 / x16,128 Mb ~ 1 Gb | 最主流;扇出简单,支持飞线与返修;XTX XT29F01GATSHGA(1 Gb)、XT29F512ATSHGA(512 Mb)、M29F512BTSJGA、M29F01GBTSJGA 即为此封装(14×20×1.2 mm) |
| SO-44 / SOP-44(宽体) | 44 | 28.5 × 12.6 mm | 1.27 mm | x8 / x16,≤ 32 Mb | 老设计 / 易手工焊接,面积最大 |
| BGA-64(TFBGA / LAE064 / LAA064) | 64 球 | 8 × 10 ~ 9 × 11 mm | 1.00 mm | x8 / x16,128 Mb ~ 1 Gb | 面积小、寄生小、利于高速;必须 X-Ray;XTX M29F512BBGJGA(512 Mb)、M29F01GBBGJGA(1 Gb)、M29F02GBBGJGA(2 Gb)为此封装 |
| BGA-56 / BGA-48 | 56 / 48 球 | 7 × 9 / 6 × 8 mm | 0.80 mm | x8 / x16,16 Mb ~ 512 Mb | 0.8 mm pitch 通常需 HDI 盲孔或盘中孔 |
| WSON 8 × 6 | 8 | 8 × 6 mm | 1.27 mm | 1.8 V 小容量 x8 | 底部散热焊盘接地并打散热过孔 |
| 信号 | 方向 | 类型 / 有效电平 | 说明与硬件处理 |
|---|---|---|---|
| A[max:0] | 输入 | — | 地址总线。x16 时 A0 为字地址最低位;x8 时由 DQ15 复用为 A-1。未用高位地址脚在小容量器件为 NC,按 datasheet 处理(多数可悬空,少数需接地) |
| DQ[15:0] | 双向 | 三态 | 数据总线。x8 时 DQ15→A-1、DQ[14:8] 内部高阻,可悬空(推荐各接 10 kΩ 弱上拉以固定电平降低功耗)。双向缓冲需注意方向控制延时 |
| CE# | 输入 | 低有效 | 片选。上电期间必须保持高;不用时经 10 kΩ 上拉到 VCC,防止浮空误选通导致总线冲突与额外功耗 |
| OE# | 输入 | 低有效 | 输出使能(读)。10 kΩ 上拉;与 WE# 不得同时为低(非法状态,可能触发意外命令) |
| WE# | 输入 | 低有效 | 写使能(命令 / 地址 / 数据锁存)。10 kΩ 上拉;上升沿锁存 |
| RY/BY# | 输出 | 开漏,低 = 忙 | 就绪 / 忙指示。必须外接 4.7 ~ 10 kΩ 上拉;可接 SoC 的 WAIT / IRQ 实现硬件握手;软件只做状态位轮询时可悬空 |
| RESET# | 输入 | 低有效 | 硬件复位。10 kΩ 上拉 + 100 nF 到地,或接系统复位 / 复位芯片;上电期间保持低可防止误写 |
| WP# / ACC | 输入 | 低有效 / 高压 | 硬件写保护(引导扇区)或编程加速电压(VHH ≈ 9 ~ 12 V)。不用时上拉到 VCC;作为 ACC 时必须接地或由专用电路驱动,切勿直接上拉 |
| BYTE# | 输入 | 低 = x8,高 = x16 | 位宽选择。16 位应用上拉到 VCC(10 kΩ),8 位应用下拉到地。关键浮空会导致位宽与字节序异常 |
| VCC | 电源 | 3 V:2.7 ~ 3.6 V;1.8 V:1.65 ~ 1.95 V | 内核与 I/O(单电源器件)。每颗 VCC 引脚配 100 nF,就近打地过孔 |
| VCCQ / VIO | 电源 | 1.65 ~ 1.95 V 或 2.7 ~ 3.6 V | 独立 I/O 电源(双电源器件)。VCCQ ≤ VCC 必须成立,否则可能闩锁 |
| VSS | 地 | — | 所有地引脚必须全部接完整地平面,每引脚至少一个地过孔 |
| NC / RFU / DNU | — | — | 无连接 / 保留 / 禁止使用。NC 悬空;RFU、DNU 按 datasheet 处理(多数要求悬空或接地,严禁上拉) |
| CLK / ADV# / WAIT | 混合 | 同步突发与 ADM 模式 | 仅同步突发 / 地址数据复用器件有。CLK 按时钟线规则走线;ADV# 下降沿锁存地址 |
1.3 关键电气参数
下表为典型值区间,跨厂商、跨工艺(90 / 65 / 45 nm)差异可达数倍,仅用于方案评估与 Layout 前期规划。必查定稿前用目标型号 datasheet 对应表格替换。
| 参数 | 符号 | 条件 | 最小 | 典型 | 最大 | 单位 |
|---|---|---|---|---|---|---|
| 内核电源(3 V 型) | VCC | — | 2.7 | 3.0 / 3.3 | 3.6 | V |
| 内核电源(1.8 V 型) | VCC | — | 1.65 | 1.8 | 1.95 | V |
| I/O 电源(双电源型) | VCCQ | 须 ≤ VCC | 1.65 | 1.8 / 3.3 | 3.6 | V |
| 读电流(异步) | ICC1 | CE#=VIL,5 MHz | — | 12 ~ 30 | 45 | mA |
| 读电流(突发 66 MHz) | ICC2 | — | — | 25 ~ 50 | 70 | mA |
| 编程 / 擦除电流 | ICC3/4 | 操作进行中 | — | 30 ~ 60 | 80 | mA |
| 待机电流 | ISB | CE#=VIH | — | 5 ~ 50 | 200 | µA |
| 深度掉电电流 | IDPD | RESET#=VSS±0.3 V | — | 1 ~ 15 | 30 | µA |
| 输入高 / 低电平(3 V) | VIH / VIL | TTL / CMOS | 2.0 / −0.5 | — | VCC+0.3 / 0.8 | V |
| 输出高 / 低电平 | VOH / VOL | IO = ±2 mA | 2.4 / — | — | — / 0.4 | V |
| 输出驱动能力 | IOL / IOH | — | 2 | 4 ~ 8 | 8 ~ 12 | mA |
| 引脚输入电容 | CIN / CIO | f = 1 MHz | — | 8 ~ 12 | 15 | pF |
| 读周期时间 | tRC | 异步随机读 | 70 | 90 / 110 | — | ns |
| 地址到数据有效 | tACC | = 速度等级 | — | 70 ~ 100 | 110 | ns |
| CE# 到数据有效 | tCE | — | — | — | 110 | ns |
| OE# 到数据有效 | tOE | — | — | 25 ~ 35 | 40 | ns |
| OE# 高到输出高阻 | tDF | — | — | 15 ~ 20 | 30 | ns |
| 写周期 / WE# 脉宽 | tWC / tWP | — | 70 / 35 | — | — | ns |
| 页模式后续字访问 | tPACC | 页内连续读 | — | 20 ~ 25 | 30 | ns |
| 同步突发时钟 | fCLK | — | — | 54 / 66 | 80 ~ 108 | MHz |
| 单字编程时间 | tWHWH1 | 解锁后单字 | — | 16 ~ 60 | 300 | µs |
| 写缓冲编程 | tWHWH2 | 32 / 64 字缓冲 | — | 48 ~ 300 | 1000 | µs |
| 扇区擦除时间 | tSE | 4 KB ~ 128 KB | — | 0.3 ~ 1.0 | 5 | s |
| 整片擦除时间 | tCHER | 128 Mb ~ 1 Gb | — | 30 ~ 120 | 480 | s |
| 擦写寿命 | — | 每扇区 | 100 000 | — | — | 次 |
| 数据保持 | — | TA ≤ 85 ℃ | 20 | — | — | 年 |
| 工作温度(工业 / 车规 Gr.1) | TA | AEC-Q100 | −40 | — | +85 / +125 | ℃ |
型号尾缀数字的含义因厂商而异:S29GL128S90T 的 90 表示 tACC = 90 ns;M29EW 的 -70 表示 70 ns;而某些系列的 -11 表示 110 ns(去掉小数点),MX29GL320E 里的 320 是容量而非速度。必须在 ordering information 表中确认速度码定义,不要靠型号数字猜。
2 · 接口与协议
并行 NOR 的外部行为与异步 SRAM 完全一致:地址直接映射,读操作只需拉低 CE#/OE# 即出数据,无需命令序列;只有编程 / 擦除 / CFI 才通过"解锁周期 + 命令码"的写序列注入。这种"读像 SRAM、写像命令"的双面性是硬件设计的核心。
2.1 异步 SRAM 类接口信号定义
| 信号组 | 成员 | 方向 | 关键时序参数 | 硬件要点 |
|---|---|---|---|---|
| 地址总线 | A[max:0](x16 时 A0 为字地址 LSB) | SoC → NOR | tRC、tACC、tOH | 单向;源端串阻;组内等长 ±25 mil |
| 数据总线 | DQ[15:0](x8 时 DQ7:0 + DQ15=A-1) | 双向 | tOE、tDF、tDS / tDH | 双向;务必避免总线冲突;x8 时 DQ[14:8] 悬空 |
| 片选 | CE# | SoC → NOR | tCE、tCP | 上拉;上电期间保持高 |
| 输出使能 | OE# | SoC → NOR | tOE、tDF | 上拉;与 WE# 互斥 |
| 写使能 | WE# | SoC → NOR | tWP、tDS、tDH | 上拉;上升沿锁存地址/数据 |
| 就绪 / 忙 | RY/BY# | NOR → SoC | tBUSY | 开漏,外加上拉 4.7 ~ 10 kΩ |
| 复位 | RESET# | SoC → NOR | tRP ≥ 500 ns、tRH ≥ 50 ns | 上拉 + 100 nF;建议接系统复位 |
| 写保护 | WP# / ACC | SoC → NOR | — | 上拉使能保护;作为 ACC 时须专用驱动 |
| 位宽 | BYTE# | SoC → NOR | tBVQV(切换后需等待) | 16 位上拉、8 位下拉,严禁浮空 |
| 同步突发附加 | CLK、ADV#、WAIT | 混合 | tCLK、tIACC | CLK 按时钟线处理;ADV# 锁存地址 |
2.2 非复用与地址数据复用(ADM)
| 模式 | 地址提供方式 | 引脚数(512 Mb x16) | 时序开销 | 适用场景 |
|---|---|---|---|---|
| 非复用(默认) | 独立地址线 A[25:0] 全程保持 | 26 + 16 + 6 + 电源 ≈ 52 | 无额外周期,tACC 即首字延迟 | 引脚充裕、追求最快 XIP;推荐首选 |
| ADM(复用) | DQ[15:0] 分时送地址,ADV# 下降沿锁存 | 16 + 6 + 电源 ≈ 26 | 随机读增加 1 ~ 2 个锁存周期(+20 ~ 40 ns) | 引脚受限的小封装、MCU 只有复用总线 |
| AADM(增强复用) | 复用 + 内部页缓存,突发时不再重复送地址 | 同 ADM | 首字 +锁存;页内后续无开销 | 复用总线 + 连续取指,兼顾引脚与带宽 |
【ADM 一个随机读周期的构成】
Cycle 1 : ADV#=L,DQ[15:0] 送地址低 16 位 → 锁存 Addr[15:0]
Cycle 2 : ADV#=L,DQ[15:0] 送高位地址(含 BA) → 锁存 Addr[max:16]
Cycle 3 : ADV#=H,等待 tIACC(初始访问延迟)
Cycle 4+: 连续输出数据(突发长度 4 / 8 / 16 / 32 或连续)
⇒ 随机读比非复用慢 25 % ~ 40 %,连续读几乎无差别
【设计建议】只要引脚够就用非复用;ADM 下 ADV# 与地址同组等长(±25 mil),
并满足 ADV# 到 DQ 的锁存保持时间 tAVH(典型 5 ~ 10 ns);
复用总线上若还挂 SRAM / PSRAM,三者 ADM 协议必须一致,否则 NOR 独占一个片选区。
2.3 读模式与带宽
| 读模式 | 首字延迟 | 后续字间隔 | 16 位带宽 | 要求 |
|---|---|---|---|---|
| 异步单字读 | 70 ~ 110 ns | 70 ~ 110 ns | 14.5 ~ 22.9 MB/s | 最简单;等待周期按 tACC 配 |
| 异步页读 | 70 ~ 110 ns | 20 ~ 25 ns | 64 ~ 80 MB/s(页内) | 页内保持 CE#/OE# 有效、高位地址不变 |
| 同步突发读(SDR) | 初始延迟 4 ~ 10 CLK | 1 个 CLK | 105 ~ 132 MB/s | 需 CLK、ADV#、WAIT;配置突发长度与初始延迟 |
| 连续线性突发 | 同突发 | 1 个 CLK | 同上,无页边界 | 适合长代码段预取 |
【带宽计算(16 位总线)】
异步单字:tRC=110 ns → 2 B / 110 ns = 18.2 MB/s;tRC=70 ns → 28.6 MB/s
异步页读:首字 90 ns + 15 × 25 ns = 465 ns / 32 B → 68.8 MB/s
同步突发 66 MHz:66 MHz × 2 B = 132 MB/s
4 字突发(8 B)效率:t = (6 + 4)/66 MHz = 151 ns → 52.9 MB/s
⇒ 突发长度越长,初始延迟摊薄越明显,XIP 建议 ≥ 16 字突发
【XIP 取指的有效带宽】即使总线 132 MB/s,若 I-Cache 未命中惩罚为 8 字填充:
有效带宽 ≈ 16 B / ((6+8)/66 MHz) = 75 MB/s
⇒ 提升 XIP 性能的优先级:① 开 I-Cache ② 增大突发长度 ③ 提高 CLK ④ 缩短 tACC
2.4 命令集
命令以"解锁周期 → 命令码 → 地址 / 数据"的写序列下达。解锁地址在 x8 与 x16 下不同,是最常见的软件 bug 来源。下表以 x16 模式为主。核对命令码基本一致,但地址与第 4 ~ 6 周期细节必须查表。
| 命令 | 周期 | 地址(x16) | 数据(x16) | 说明 |
|---|---|---|---|---|
| 读阵列 / 复位 | 1 | 任意 | 0x00F0(或 0x00FF) | 从 CFI / Autoselect / 状态模式退回读阵列;中止编程 / 擦除 |
| Autoselect(读 ID) | 3 | 0x555 / 0x2AA / 0x555 | 0x00AA / 0x0055 / 0x0090 | 进入后读 0x00 = 制造商 ID、0x01 = 设备 ID;发 Reset 退出 |
| CFI 查询 | 1 | 0x0055(x8:0x00AA) | 0x0098 | 进入后按偏移读查询表;写 0x00F0 退出 |
| 字 / 字节编程 | 4 | 0x555 / 0x2AA / 0x555 / PA | 0x00AA / 0x0055 / 0x00A0 / PD | PA = 编程字地址,PD = 数据 |
| 解锁旁路 / 旁路编程 / 旁路复位 | 2 | 0x555 / 0x2AA | 0x00AA / 0x0020 | 旁路后编程只需 2 周期(A0h + 数据),批量写省约 30 % 开销;0x90+0x00 退出 |
| 写缓冲编程 | 3 + N | 0x555 / SA / SA | 0x00AA / 0x0025 / (N−1) | 随后连续写 N 个字,最后写"缓冲编程确认"0x29 |
| 扇区 / 块擦除 | 6 | 0x555 / 0x2AA / 0x555 / 0x555 / 0x2AA / SA | 0x00AA / 0x0055 / 0x0080 / 0x00AA / 0x0055 / 0x0030 | SA = 扇区内任意地址 |
| 整片擦除 | 6 | 同上,末周期 | … / 0x0010 | 耗时 30 ~ 120 s |
| 擦除挂起 / 恢复 | 1 | 任意 | 0x00B0 / 0x0030 | 擦除中临时读其他扇区;挂起后 RY/BY# 释放 |
| 状态读 / 状态清除 | 1 | 任意 | 0x0070 / 0x0071 | 进入后读 DQ7~DQ0;0x71 清除 DQ5 错误标志 |
| 扇区保护 / 解保护 | 厂商自定义 | — | — | PPB / DYB / Password 机制,参见各厂商应用笔记 |
【解锁周期为什么是 0x555 / 0x2AA】AMD/Fujitsu 命令集(CFI Primary Command Set = 0x0002)的历史约定:
字节模式(x8):地址 0x555 写 0xAA,地址 0x2AA 写 0x55
字模式 (x16):地址 0x555 写 0x00AA,地址 0x2AA 写 0x0055
—— 注意:x16 模式下解锁地址不再除以 2,因为命令锁存比较的是"地址总线上的值",
而非"字节地址"。x16 器件 A[10:0] = 0x555 时,对应 SoC 字节地址 0xAAA。
#define NOR_BASE 0x0C000000u /* 片选基址(字节地址)*/
#define NOR_W(a) (*(volatile uint16_t *)(NOR_BASE + ((a) << 1)))
NOR_W(0x555) = 0x00AA; /* 解锁周期 1 */
多数 SoC 外部总线在 16 位模式下会自动右移 1 位输出地址,
故软件用"字地址"直接索引即可;务必用逻辑分析仪 / 示波器实测确认。
2.5 CFI / JEDEC ID 查询
CFI(JEDEC JEP137 / JESD68)让软件在运行时自动识别容量、页大小、擦除区块分布与时序,避免为每种型号硬编码。硬件上只需保证"能稳定读出一个字",CFI 就能工作;读不出 'QRY' 基本可断定是位宽 / 地址移位 / 时序三类硬件问题之一。下表偏移为 x16 字地址(x8 模式字节地址 = 偏移 × 2)。
| 偏移(x16 字地址) | 字段 | 典型值 | 解读 |
|---|---|---|---|
| 0x10 / 0x11 / 0x12 | 识别串 | 'Q' / 'R' / 'Y' | 0x51 / 0x52 / 0x59;读不到说明未进入 CFI 或位宽错 |
| 0x13 / 0x14 | Primary Command Set ID | 0x0002 | AMD / Fujitsu 标准;0x0001 = Intel 命令集 |
| 0x15 / 0x16 | 扩展表地址 | 0x0031 | 指向 Primary Extended Table |
| 0x1B / 0x1C | VCC 编程/擦除 最小 / 最大 | 0x27 / 0x36 | BCD 码:2.7 V / 3.6 V;电源设计必须落在窗口内 |
| 0x1F / 0x20 | 单字 / 缓冲编程典型超时 | 2N µs | 读出的值是指数 N |
| 0x21 / 0x22 | 块擦除 / 整片擦除典型超时 | 2N ms | 同理,单位 ms |
| 0x23 ~ 0x26 | 上述操作的最大超时倍率 | 2N × 典型 | 软件轮询超时必须按最大值设定 |
| 0x27 / 0x28 | 器件容量 | 2N 字节 | N = 25 → 32 MiB |
| 0x28 / 0x29 | 接口描述 | 0 / 1 / 2 | x8 only / x16 only / x8-x16 可切换(BYTE#) |
| 0x2A / 0x2B | 写缓冲最大字节数 | 2N | N = 6 → 64 字节 = 32 字 |
| 0x2C / 0x2D | 擦除区块区域数 | 1 ~ 4 | 不同大小扇区分为多个 region |
| 0x2E 起,每区 2 字 | 区块区域信息 | 块数−1 + 块大小/256 | 遍历得到完整擦除粒度表(如 8 KB × 8 + 64 KB × 254) |
【CFI 查询流程(16 位总线)】
static volatile uint16_t *const nor = (volatile uint16_t *)NOR_BASE;
static void nor_cmd(uint32_t wa, uint16_t d) { nor[wa] = d; }
void cfi_enter(void){ nor_cmd(0x0000, 0x00F0); nor_cmd(0x0055, 0x0098); }
void cfi_exit (void){ nor_cmd(0x0000, 0x00F0); } /* Reset 回到读阵列 */
int cfi_probe(struct cfi_info *p)
{
uint16_t q, r, y;
cfi_enter();
q = nor[0x10]; r = nor[0x11]; y = nor[0x12];
if (q != 'Q' || r != 'R' || y != 'Y') { cfi_exit(); return -1; }
p->size = 1u << (nor[0x27] & 0xFF); /* 2^N 字节 */
p->interface = nor[0x28]; /* 0=x8 / 1=x16 / 2=可切换 */
p->bufsize = 1u << (nor[0x2A] & 0xFF); /* 写缓冲字节数 */
p->regions = nor[0x2C] & 0xFF;
uint32_t off = 0x2E;
for (int i = 0; i < p->regions; i++) {
p->region[i].blocks = (nor[off] & 0xFFFF) + 1u;
p->region[i].size = (nor[off + 1] & 0xFFFF) * 256u; /* 0 表示 128 KB 特殊编码 */
if (p->region[i].size == 0) p->region[i].size = 131072u;
off += 2; /* 每区域 2 个(16 位)字 */
}
cfi_exit(); return 0;
}
【读不到 'QRY' 的排错三板斧】
① BYTE# 状态是否正确(应为 1 = x16);
② SoC 是否把字节地址右移 1 位输出到地址总线(16 位模式);
③ 等待周期是否足够 —— 先用 30 个等待周期试,成功后二分收敛;
④ 示波器看 CE#/OE#/WE# 是否真的产生低脉冲、地址线是否随周期翻转。
2.6 状态位轮询(DQ7 / DQ6 / DQ5 / DQ3 / DQ2 / DQ1)
| 位 | 名称 | 行为 | 软件处理 |
|---|---|---|---|
| DQ7 | Data# Polling | 操作进行中读出的是写入数据 DQ7 的反码,完成后读出真值 | 循环读同一地址直到 DQ7 与写入值一致;必须配合 DQ5 判错,否则器件损坏时死循环 |
| DQ6 | Toggle Bit 1 | 进行中连续读同一地址时 DQ6 在 0 / 1 间翻转,完成后停止 | 连续两次读,DQ6 相同即完成;与 DQ2 配合可区分"擦除中"与"擦除挂起" |
| DQ5 | 超时 / 错误标志 | 编程或擦除超时时置 1 | 置 1 后再读两次确认(DQ7/DQ6 可能仍在翻转),确认后发 Reset 0xF0 退出并上报失败 |
| DQ3 | 扇区擦除定时器 | 擦除命令下达后、真正开始擦除前 = 0;开始后 = 1 | 判断"是否还在 50 µs 擦除命令窗口内",多扇区连续擦除时使用 |
| DQ2 | Toggle Bit 2 | 擦除挂起期间 DQ2 持续翻转、DQ6 停止翻转 | 与 DQ6 组合是判断擦除挂起的唯一可靠判据 |
| DQ1 | 写缓冲放弃标志 | 写缓冲中写入不合法地址 / 跨页时置 1 | 置 1 表示本次缓冲编程作废,需重新发起 |
| RY/BY# | 硬件就绪引脚 | 开漏,忙 = 低电平 | 最省 CPU;可接 SoC 的 WAIT 引脚做硬件插入等待 |
【健壮的轮询模板(Data# Polling + Toggle Bit + DQ5 超时)】
int nor_wait_ready(volatile uint16_t *addr, uint16_t expect, uint32_t timeout_us)
{
uint16_t d1, d2; uint32_t t = 0;
while (t < timeout_us) {
d1 = *addr; d2 = *addr; /* 连续两次读判 DQ6 是否翻转 */
if (((d1 ^ d2) & 0x40) == 0) /* DQ6 一致 → 操作结束 */
return (((d1 ^ expect) & 0x80) == 0) ? 0 : -2;
if (d1 & 0x20) { /* DQ5 = 1 → 可能超时 */
d1 = *addr; d2 = *addr;
if (((d1 ^ d2) & 0x40) == 0 && ((d1 ^ expect) & 0x80) == 0) return 0;
addr[0] = 0x00F0; /* 复位回到读阵列 */
return -1;
}
delay_us(1); t++; /* 也可改轮询 RY/BY# 引脚省总线 */
}
return -3;
}
【轮询超时设定】T_poll = CFI 最大超时(0x23~0x26)× 2(余量)× 1.5(温度降额)
例:字编程最大 2^8 × 2^4 µs = 4096 µs → 轮询上限约 12 ms
扇区擦除最大 2^8 × 2^4 ms = 4096 ms → 轮询上限约 12 s
3 · 电源设计
3.1 电源域与 I/O 电平匹配
| 项目 | 3 V 单电源 | 1.8 V 单电源 | 双电源(VCC + VCCQ) |
|---|---|---|---|
| VCC | 2.7 ~ 3.6 V | 1.65 ~ 1.95 V | 2.7 ~ 3.6 V(或 1.7 ~ 2.0 V) |
| VCCQ / VIO | 与 VCC 同引脚 | 与 VCC 同引脚 | 1.65 ~ 1.95 V 或 2.7 ~ 3.6 V,必须 ≤ VCC |
| 容差(含纹波) | ±10 % | ±8 % | 各 ±10 % |
| 纹波上限 | 峰峰值 ≤ 100 mV(0 ~ 100 MHz);编程 / 擦除瞬态 ≤ 150 mV | ||
| 上电顺序 | — | — | VCC 先于或同时于 VCCQ;VCCQ 先上电可能闩锁 |
| 峰值电流 | 60 ~ 80 mA | 50 ~ 70 mA | VCC 60 mA / VCCQ 20 mA |
| LDO / DCDC 选型 | ≥ 200 mA 余量;VCCQ 可与 SoC 的 I/O 电源共享,但要单独去耦 | ||
| 1.8 V SoC ↔ 3 V NOR 方案 | 实现 | 优点 | 缺点 / 限制 | 适用 |
|---|---|---|---|---|
| ① 换 1.8 V 并行 NOR 首选 | VCC = 1.8 V | 无需转换器,成本 / 面积 / 时序最优 | 1.8 V 并行 NOR 可选型号与容量较少 | 新设计 |
| ② 双电源 NOR | VCC=3.3 V、VCCQ=1.8 V | 省去转换器 | 需两路电源;VCCQ 必须单独去耦 | SoC 有 1.8 V 电源时 |
| ③ 自动方向转换器 | TXS0108E / TXB0108 / LSF0108 × 4 ~ 6 片 | 无需 DIR 信号,布线简单 | 驱动弱;总线电容 < 70 pF;不适合 > 40 MHz 突发 | 异步低频读、少量信号 |
| ④ 方向可控收发器 推荐 | 74LVC16T245 / 74AVC32T245 / 74LVC4245 | 驱动强(24 ~ 32 mA),隔离总线电容 | 需 DIR 信号(由 OE# 生成);增加 3 ~ 10 ns 延时 | 16 位总线 + 页读 / 突发读 |
| ⑤ 电阻分压 | 3.3 V → 1.8 V 用 1 kΩ / 1.2 kΩ | 成本最低 | 仅适用 RESET#、WP# 等单向低速信号;噪声容限差 | 个别控制脚应急 |
把 3.3 V NOR 的 DQ 直接接到 1.8 V SoC 的 I/O 上"靠钳位二极管扛"。NOR 输出高电平 3.3 V 会通过 SoC I/O 的 ESD 二极管向 1.8 V 电源灌电流,长期工作会抬高 1.8 V 轨、损坏 I/O 或触发闩锁。电压差 > 0.3 V 就必须做电平转换。
3.2 去耦电容配置
| 位号 | 容值 / 封装 / 介质 | 数量 | 放置位置 | 作用 |
|---|---|---|---|---|
| C1 ~ Cn(高频) | 100 nF,0402(推荐)/ 0603,X7R ≥ 6.3 V | 每个 VCC 引脚 1 颗(TSOP-56 通常 1 ~ 2 个 VCC 脚;BGA-64 通常 2 ~ 3 个) | 距焊盘 ≤ 2 mm,过孔直接打在焊盘侧 | 抑制编程 / 擦除电荷泵高频电流 |
| CBULK1 | 4.7 µF,0603 / 0805,X5R / X6S ≥ 6.3 V | 每器件 1 颗 | 电源入口处,≤ 10 mm | 补充擦除瞬态(数十 ms 级) |
| CBULK2(可选) | 10 ~ 22 µF,0805 / 1206,X5R | 每电源域 1 颗 | 电源输出端 | 多器件共用电源 / 长走线时抑制 IR 压降 |
| CVCCQ | 100 nF,0402,X7R | 每个 VCCQ 引脚 1 颗 | 紧贴引脚 | I/O 同步开关噪声回路 |
| CRESET | 100 nF,0402,X7R | 1 颗 | RESET# 到地,配合 10 kΩ 上拉 | 上电复位延时(RC ≈ 1 ms)+ 滤除复位线毛刺 |
- 去耦回路面积(电容 → 电源引脚 → 地引脚 → 电容过孔)< 50 mm²;BGA 器件优先放在背面焊盘正下方。
- 禁止用 > 3 mm 的细走线连接电容(会引入 5 ~ 10 nH 电感,完全抵消去耦效果)。
- 注意直流偏压效应:X7R 0402 100 nF / 6.3 V 在 3.3 V 偏压下有效容值可能只剩 60 ~ 70 %,建议选 10 V 及以上耐压。
- VCC 主路径 ≥ 20 mil(0.5 mm),分支到引脚 ≥ 10 mil;整条路径压降 < 50 mV。
3.3 上电 / 掉电时序
| 时序参数 | 符号 | 典型要求 | 违反后果 | 硬件保障措施 |
|---|---|---|---|---|
| VCC 建立 → CE# 有效 | tVCS | ≥ 50 ~ 300 µs | 读出乱码、状态机锁死、误擦除 | CE# 上拉 + 上电软件延时;或用电源良好(PG)信号门控 CE# |
| RESET# 脉冲宽度 | tRP | ≥ 500 ns(建议 ≥ 1 µs) | 复位不彻底 | RC 复位(10 kΩ + 100 nF ≈ 1 ms)或复位芯片 |
| RESET# 释放 → 首次读 | tRH | ≥ 35 ~ 50 ns | 首次读失败 | 软件插入 ≥ 1 µs 延时 |
| VCC 有效 → 就绪 | tPU-READ | 典型 90 µs,最大 300 µs | 上电立刻读得无效数据 | 查询 RY/BY# 或延时 ≥ 500 µs |
| VCC 上升斜率 | — | 0.05 ~ 10 V/ms(部分器件有要求) | 过快触发闩锁,过慢 POR 异常 | 电源软启动;避免热插拔直接上电 |
| 掉电:CE# 失效先于 VCC 跌落 | tPD | ≥ 0,越大越安全 | 掉电毛刺被当成写命令,数据被改 | 电压监控在 VCC 跌到 2.7 V 前强制 CE#=1、RESET#=0 |
| 编程 / 擦除期间断电 | — | 禁止 | 扇区数据不确定 | ≥ 47 µF 储能维持 ≥ 10 ms,或备用电源完成当前操作 |
| 欠压锁定阈值 | VLKO | 下降 2.2 ~ 2.5 V / 上升 2.4 ~ 2.7 V | 低压编程数据不可靠 | 监控 VCC,低于 2.7 V 时禁止写操作 |
【掉电保护设计(针对"经常掉电丢数据")】
1) 硬件:电压监控芯片(TPS3839 / MCP130,阈值 2.93 V)输出经与门接到
CE# 上拉控制与 RESET#:VCC < 2.93 V → RESET#=0、CE#=1,禁止一切操作。
传播延时 5 ~ 20 µs,远快于 VCC 从 2.93 V 跌到 2.7 V 的时间。
2) 电源:3.3 V 轨放 ≥ 47 µF 储能,保证 ≥ 1 ms 安全窗口。
3) 软件:写前后校验;关键参数区双备份 + 序列号 + CRC;上电自检发现"半写"则回滚。
4) 布局:WP# 上拉,Bootloader 所在扇区设为硬件保护,即使掉电也擦不掉引导区。
3.4 待机与 DPD 低功耗
| 模式 | 进入条件 | 典型电流 | 退出时间 | 硬件注意 |
|---|---|---|---|---|
| 激活读(异步) | CE#=L,OE#=L | 12 ~ 30 mA | — | — |
| 激活读(同步突发) | CLK 运行 | 25 ~ 50 mA | — | 空闲时关 CLK 或退出突发模式 |
| 待机(Standby) | CE# = VIH | 5 ~ 50 µA | ≈ 100 ns | CE# 必须外部上拉,浮空时电流可达 mA 级 |
| 自动睡眠 | 地址保持 > tASSB(100 ns ~ 5 µs) | ≈ 待机水平 | 自动 | XIP 时会反复唤醒,以实测为准 |
| 深度掉电(DPD) | RESET# = VSS ± 0.3 V | 1 ~ 15 µA | 90 ~ 300 µs | DPD 期间不能读;XIP 系统会跑飞 |
| 整域断电 | 负载开关切断 VCC | ≈ 0 | 完整上电时序 | 需与 SoC I/O 状态协同,避免倒灌 |
代码正在 NOR 上执行时把 RESET# 拉低进入 DPD,CPU 下一个取指会读到无效数据而直接跑飞。正确做法:把"进入 DPD 的代码"与"唤醒后要执行的代码"放到片内 SRAM,进入前关中断并失效 I-Cache。
4 · 典型应用电路
4.1 3 V 系统 16 位非复用接法(推荐基准电路)
| 网络 | 连接 | 上 / 下拉 | 串联电阻 | 关键说明 |
|---|---|---|---|---|
| A[24:0] | SoC A[25:1] → NOR A[24:0] | 无 | 22 ~ 33 Ω(靠 SoC) | 16 位模式地址右移 1 位;未用高位地址脚按 datasheet 悬空 |
| DQ[15:0] | SoC DQ[15:0] ↔ NOR DQ[15:0] | 无 | 22 ~ 33 Ω(只串一颗) | 双向串阻不能两端各串,否则分压导致 VIL / VIH 违例 |
| CE# | SoC CS0# → NOR CE# | 10 kΩ 上拉 | 可选 33 Ω | 上电 / 复位期间保持高;与其他外设片选不得重叠 |
| OE# | SoC RD# → NOR OE# | 10 kΩ 上拉 | 可选 33 Ω | 与 WE# 硬件互斥;外接缓冲时注意方向切换死区 |
| WE# | SoC WR# → NOR WE# | 10 kΩ 上拉 | 可选 33 Ω | 上升沿锁存;tWP ≥ 35 ns 需在控制器中配置写脉冲宽度 |
| RESET# | GPIO 或系统复位 | 10 kΩ 上拉 + 100 nF 到地 | 无 | RC ≈ 1 ms;GPIO 控制时默认配置为输入 + 上拉 |
| WP#/ACC | 上拉(或 GPIO) | 10 kΩ 上拉 | 无 | 上拉 = 允许写,接地 = 保护引导扇区;作为 ACC 时严禁上拉到 VCC |
| RY/BY# | → SoC GPIO / WAIT | 4.7 ~ 10 kΩ 上拉(必须) | 可选 100 Ω | 开漏输出;接 WAIT 可实现硬件插入等待 |
| BYTE# | 上拉 VCC(16 位) | 10 kΩ 上拉 | 无 | 关键必须用电阻固定,绝不允许浮空或由未初始化 GPIO 驱动 |
| VCC / VCCQ | 3.3 V / 1.8 V | — | — | 每引脚 100 nF + 整器件 4.7 µF;VCCQ 不早于 VCC 上电 |
| VSS | 地平面 | — | — | 所有地引脚全部就近打地过孔,禁止串联接地 |
| NC / RFU | 悬空 | 无 | — | RFU / DNU 按 datasheet 处理,部分必须接地 |
4.2 8 位接法与 BYTE# 处理
16 位模式(BYTE#=1,推荐)
- BYTE# 经 10 kΩ 上拉到 VCC。
- SoC 地址 A[n:1] → NOR A[n−1:0],整体右移一位。
- DQ[15:0] 全部使用,一次读一个字(2 字节)。
- NOR 的 A0 是字地址最低位,不是字节地址。
- 小端系统:低字节在 DQ[7:0]、高字节在 DQ[15:8];大端 SoC 需在控制器中配置字节交换。
8 位模式(BYTE#=0)
- BYTE# 经 10 kΩ 下拉到 GND(保留电阻便于调试)。
- SoC 地址 A[n:1] → NOR A[n−1:0],仍右移一位。
- DQ15 变为 A-1(字节选择),接 SoC 的 A0。
- DQ[14:8] 内部高阻,可悬空;为降低噪声建议各接 10 kΩ 弱上拉。
- 容量不变但每次只取 1 字节,带宽减半;能 16 位就别用 8 位。
| 信号 | 16 位(BYTE#=1) | 8 位(BYTE#=0) | 硬件差异 |
|---|---|---|---|
| 地址总线 | SoC A[n:1] → NOR A[n−1:0] | 同上,另 SoC A0 → NOR DQ15(A-1) | 8 位模式多一根线接到 DQ15 |
| 数据总线 | DQ[15:0] 全部有效 | DQ[7:0] 有效;DQ[14:8] 高阻 | DQ[14:8] 悬空或弱上拉 |
| 字节选择 | 一次取 2 字节 | A-1 = 0 选偶字节,=1 选奇字节 | 注意 A-1 与 SoC 端序配置配合 |
| 位宽切换 | 运行中禁止动态切换:切换后需等待 tBVQV(典型数十 ns)并重新复位与配时序;用电阻固定最稳妥 | ||
4.3 电平转换器与总线缓冲
| 器件 | 通道 | 方向 | 驱动 | tpd | VCCA / VCCB | 适用 |
|---|---|---|---|---|---|---|
| 74LVC16T245 首选 | 16 | DIR 可控 | ±24 mA | 3.0 ~ 5.0 ns | 1.2 ~ 3.6 / 1.2 ~ 5.5 V | 16 位数据总线,支持页读 / 突发 |
| 74AVC32T245 | 32 | DIR 可控 | ±12 mA | 2.0 ~ 3.5 ns | 0.8 ~ 3.6 / 0.8 ~ 3.6 V | 延时更小,但驱动较弱 |
| 74LVC4245 | 8 | DIR 可控 | ±24 mA | 6 ~ 10 ns | 5 V / 3.3 V | 老设计 / 5 V 侧,延时偏大 |
| 74LVC16245 | 16 | DIR 可控 | ±24 mA | 2.5 ~ 4.5 ns | 单电源 1.65 ~ 3.6 V | 同电压域纯缓冲 / 隔离,不做转换 |
| TXS0108E | 8 | 自动方向 | 弱(≤ 20 mA) | 3 ~ 10 ns | 1.65 ~ 3.6 / 2.3 ~ 5.5 V | 异步低频,总线电容 < 70 pF |
| 74LVC1T45 | 1 | DIR 可控 | ±24 mA | 2.5 ns | 1.65 ~ 5.5 V | RY/BY#、RESET# 等单根控制线 |
① 方向切换死区:若 DIR 切换与 OE# 边沿竞争,可能出现"SoC 与 NOR 同时驱动总线"的瞬间短路,表现为电流尖峰与地弹。对策:DIR 直接用 OE# 产生(不经过额外逻辑),并在控制器中配置 OE# 无效到下一次 WE# 有效之间至少 1 个总线时钟的死区。
② 往返延时翻倍:SoC → 缓冲器 → NOR → 缓冲器 → SoC,地址与数据各经一次转换器,总延时增加 2 × tpd。计算等待周期时必须把 6 ~ 10 ns 计入,否则在 70 ns 器件上会偶发读错。