Aug 04 2026 Off 摘要 SPI NOR Flash 作为嵌入式设备、物联网终端及安全芯片的关键非易失性存储介质,存储着固件、引导代码、密钥与证书等敏感信息。然而,其物理擦除机制与文件系统的逻辑删除之间存在根本性的鸿沟:逻辑删除仅清除索引,而实际数据仍残留在存储单元中,直到被显式擦除或覆写。更严峻的是,即使执行了整片擦除,攻击者仍可通过物理读出未分配块、提取磨损均衡映射表或利用电压毛刺使擦除命令提前终止,恢复出厂密钥与证书,甚至还原已删除的固件映像。 SPI NOR NOR Flash 的存储结构SPI NOR Flash 内部存储阵列由扇区(Sector,通常 4KB)、块(Block,32KB/64KB)或整个芯片组成。NOR 支持随机读取,但写入前必须将目标区域擦除为全 0xFF。擦除操作以扇区或块为单位,通过特定的命令序列(如 Write Enable + Sector Erase)触发,由内部状态机执行,耗时数百毫秒至秒级。擦除操作本质上是将浮栅上的电子移出,使存储单元回到初始状态。但擦除并非瞬时完成:在状态机执行期间,如果电源不稳定或收到非法命令,擦除可能被中断,导致部分区域未被完全擦除,原有数据仍有残留。安全擦除的误区许多安全应用信赖整片擦除(Bulk Erase)命令可以彻底清除所有数据。但实际上,Bulk Erase 的执行时间较长(典型值为数十秒),期间芯片可通过外部引脚(如 RESET# 或 CS#)被中断。 Command (C7h/60h) | v +----+ CS# _____| |___________________________________________________/\_______ <-->(1) <-->(3) t_CSS t_CSH +--+ +--+ +--+ +--+ +--+ SCK __| |__| |__| |__| |_. . .__| |_________________________________ (2) 1 2 3 4 8 (8个时钟) (无时钟/内部高阻或忽略) --+-----------------+--+ +--+ SI | MSB LSB | | XXXXXX | | (输入阶段完成) +-----------------+--+ +--+ SO ================================== (High-Impedance / 准备内部自擦除) | v [内部 Bulk Erase 正在进行中...] WIP (Write In Progress) = 1 异常提前拉高!(不符合规范的时序) +--------------------+ CS# ---------------------------------------------| |___ <-->(4) 非法中断脉冲 / 提前拉高 攻击者可以在擦除开始后的极短时间内将 CS# 拉高或触发硬件复位,终止擦除序列,此时部分或大部分存储单元尚未被擦除,原始数据原样保留。此外,对于被标记为“坏块”或保留区域(如 OTP 区域、安全寄存器),标准擦除命令可能不会覆盖,而这些区域常被厂商用于存储校准数据、序列号或密钥。攻击者通过 SFDP(Serial Flash Discoverable Parameters)表可以查询这些保留区域的地址与大小,然后直接读取。 数据残留与恢复路径 逻辑删除与物理残留嵌入式设备的文件系统(如 JFFS2、UBIFS)在删除文件时通常仅修改 inode 或 FTL 映射表,实际数据页仍保留原有内容,直到垃圾回收或磨损均衡将其复用。在设备生命周期内,如果这些“脏页”未被新的写入覆盖,攻击者可以绕过文件系统,直接读取 Flash 阵列,恢复已删除的配置、证书甚至私钥。磨损均衡映射表的泄露NAND Flash 通常使用 FTL 管理坏块与磨损均衡,但现代 SPI NOR 也开始集成有限的磨损均衡逻辑或由软件 FTL 管理。FTL 的映射表将逻辑地址转换为物理地址,其本身也存储在 NOR 的某个区域。 如果攻击者能提取该映射表,就能知晓哪些物理块存储了敏感逻辑地址的数据,从而绕开文件系统的安全机制进行定向恢复。保留区域与 SFDP 查询SFDP 是 JEDEC JESD216 标准,提供 Flash 芯片功能与参数的标准发现机制。通过读取 SFDP 表,可以获取芯片容量、擦除大小、电源要求等信息。更关键的是,某些厂商在 SFDP 的参数表中声明了“Security Register”或“Unique ID”区域的位置。这些区域可能不受批量擦除影响,并存储有设备唯一密钥或工厂配置。攻击者可以通过标准 SPI 命令直接读取这些保留区域,提取密钥。 利用电压毛刺中断擦除 电压毛刺攻击原理电压毛刺(Voltage Glitching)是一种硬件攻击技术,通过在芯片电源引脚引入一个短暂的低压脉冲,使内部逻辑发生瞬态错误。对于 SPI NOR,在 Bulk Erase 命令执行期间注入毛刺,可导致内部状态机异常复位或跳过部分擦除循环,使擦除操作提前“成功”返回,但实际上并未擦除所有页。攻击者随后可以正常读取这些残留数据。实验实现使用 ChipWhisperer-Lite 或 PicoEMP 等开源故障注入工具,结合 Bus Pirate 进行 SPI 通信,可以搭建一套完整的擦除中断实验环境。流程如下:编程 SPI NOR 写入已知模式数据。发送 Bulk Erase 命令,同时启动毛刺发生器。在擦除开始后的几毫秒内,向电源引脚注入一个宽度为 10–100 ns 的负向毛刺。重新读取芯片,对比是否仍保留原始数据。 物理读出与安全擦除验证 使用 Bus Pirate 读取 SPI NOR #!/usr/bin/env python3 # spi_nor_dump.py — 通过 Bus Pirate 读取 SPI NOR 内容 import serial import time ser = serial.Serial('/dev/ttyUSB0', 115200, timeout=1) defenter_binary_mode(): ser.write(b'\x00' * 20) # 进入 Bitbang 模式 time.sleep(0.5) ser.write(b'\x01') # 模式选择 time.sleep(0.1) defread_jedec_id(): ser.write(b'\x9F') # JEDEC ID 命令 time.sleep(0.01) return ser.read(3) defread_data(addr, length): cmd = bytes([0x03, (addr >> 16) & 0xFF, (addr >> 8) & 0xFF, addr & 0xFF]) ser.write(cmd) time.sleep(0.01) return ser.read(length) defmain(): enter_binary_mode() jedec = read_jedec_id() print(f"JEDEC ID: {jedec.hex()}") # 读取前 256 字节(包含固件头部) data = read_data(0, 256) print(f"First 256 bytes:\n{data.hex()}") if __name__ == "__main__": main() 说明:此脚本通过 Bus Pirate 的串口接口发送 SPI 命令,读取 JEDEC ID 和指定地址的数据。攻击者可利用此方法读取未擦除的残留数据,或读取安全寄存器区域。安全擦除的正确方法安全擦除应当:先覆写随机数据多次(至少 3 次),然后执行整片擦除,并读取验证。代码示例: defsecure_erase(): # 1. 写入随机数据覆盖整个芯片 block_size = 65536 total_size = 2 * 1024 * 1024# 2 MB chip for addr in range(0, total_size, block_size): write_enable() random_data = bytes([int.from_bytes(os.urandom(1), 'big') for _ in range(block_size)]) page_program(addr, random_data) wait_ready() # 2. Bulk Erase write_enable() ser.write(b'\xC7') # Bulk Erase time.sleep(60) # 等待足够时间 wait_ready() # 3. 验证全 0xFF for addr in range(0, total_size, block_size): data = read_data(addr, block_size) if any(b != 0xFFfor b in data): print(f"Erase failed at {addr:#x}") 检测与防御 硬件防护锁定 OTP 区域:通过状态寄存器将安全区域设为只读或禁止读出,仅允许在特定模式下访问。电压监控与复位:添加电源监控电路,在电压异常时立即复位芯片,防止毛刺攻击。物理防拆:使用环氧树脂封装 Flash 芯片,增加物理接触难度。软件防护全磁盘加密(FDE):对所有写入 Flash 的数据进行加密,即使被物理读出也无法解析。安全启动与签名验证:确保固件未被篡改,但无法防止数据被读出。定期刷新敏感数据:在设备生命周期内,定期对存储敏感数据的扇区执行覆写并擦除,缩短残留窗口。 结语 SPI NOR Flash幽灵源于其物理特性与安全假设之间的根本冲突:逻辑删除无法替代物理擦除,而物理擦除又未必彻底。攻击者凭借几十元钱的工具和几分钟的物理接触,就能让已逝的数据复活,提取出厂密钥与固件。从 SFDP 的参数表到电压毛刺的瞬间中断,每一个看似无害的命令都可能成为泄露的缝隙。 Post navigation Previous PostPrevious D-Bus 语义投毒Next PostNext Matter 智能家居的分布式信任崩溃