2. 密码学基础

各位同学,咱们今天聊点硬核的。密码学这东西,说白了就是嵌入式安全的基石。你想想看,没有密码学,你的固件签名就是一张废纸,可信启动就是个笑话。

我个人习惯把密码学分成三块来理解:哈希算法、非对称加密、数字签名。这三者环环相扣,缺一不可。咱们一个一个来拆解。

1. 哈希算法:数据的「指纹」

哈希算法,说白了就是给数据算一个固定长度的摘要。不管你输入的是1个字节还是1个GB,输出都是256位(32字节)。这就是SHA256。

我在项目中遇到过一个问题:有同事问,为什么不用MD5?MD5更快啊。嗯,这里要注意——MD5已经被攻破了。2017年Google就演示了SHA1碰撞攻击。所以现在工业界,SHA256是底线。

SHA256的核心特性:

  • 单向性:从哈希值反推原始数据,理论上不可能
  • 抗碰撞性:找到两个不同数据产生相同哈希值,极其困难
  • 雪崩效应:输入改一个bit,输出一半以上的bit都会变

来看一个实际例子。假设你下载了一个固件包,怎么确认它没被篡改?

# 计算固件文件的SHA256哈希值
$ sha256sum firmware_v2.1.bin
a3f8b2c9d1e4f5a6b7c8d9e0f1a2b3c4d5e6f7a8b9c0d1e2f3a4b5c6d7e8f9a0  firmware_v2.1.bin

# 对比官方发布的哈希值
# 官方:a3f8b2c9d1e4f5a6b7c8d9e0f1a2b3c4d5e6f7a8b9c0d1e2f3a4b5c6d7e8f9a0
# 匹配!固件是完整的。

你可能会问:「哈希值本身会不会被篡改?」问得好。这就是为什么我们需要数字签名——哈希值必须被签名保护起来。

2. 非对称加密:公钥与私钥

非对称加密,名字听着吓人,其实逻辑很简单。你有一对钥匙:一把公开(公钥),一把私藏(私钥)。公钥加密的数据,只有私钥能解开。反过来,私钥加密的数据,公钥也能验证。

目前主流的有两种:RSA和ECC。

特性 RSA ECC(椭圆曲线)
密钥长度 2048位起 256位(相当于RSA 3072位)
计算速度 签名慢,验签快 签名快,验签也快
资源消耗 高 低
嵌入式适用性 一般 优秀

我个人习惯在资源受限的MCU上优先选ECC。为什么?你想想看,一个Cortex-M0的芯片,跑RSA 2048签名验证可能要几百毫秒,而ECC 256位只需要几十毫秒。这在启动阶段,差距就是天壤之别。

避坑指南:我曾经在一个项目里用了RSA 4096位密钥,结果发现芯片的RAM根本装不下那么大一个密钥结构体。后来改成ECC P-256,问题迎刃而解。所以选算法前,先看看你的芯片资源够不够。

3. 数字签名:哈希 + 非对称加密的组合拳

数字签名,说白了就是「用私钥给哈希值加密」。流程是这样的:

  1. 发送方计算固件的SHA256哈希值
  2. 发送方用自己的私钥对哈希值进行加密,得到签名
  3. 发送方把固件 + 签名一起发给接收方
  4. 接收方用发送方的公钥解密签名,得到哈希值A
  5. 接收方自己计算固件的哈希值B
  6. 比较A和B,一致则签名验证通过

这里有个关键点:签名不是加密整个固件,而是加密它的哈希值。为什么?因为非对称加密很慢,加密整个固件不现实。哈希值只有32字节,加密它很快。

注意:签名验证失败,不代表固件一定被篡改。也可能是密钥不匹配、算法参数不对、或者固件版本不一致。我曾经调试一个启动失败的问题,查了两天才发现是公钥烧录时字节序搞反了。嗯,这种低级错误,谁都会犯。

知识体系结构图

下面这张图,是我自己整理的密码学基础结构。你看一眼,就能明白这三者之间的关系。

密码学基础:可信启动核心知识体系 哈希算法 (SHA256) 非对称加密 (RSA/ECC) 数字签名 提供摘要 提供密钥对 核心特性 • 单向性:不可逆 • 抗碰撞:唯一性 • 雪崩效应:敏感 • 固定输出:256位 • 快速计算 核心特性 • 公钥加密,私钥解密 • 私钥签名,公钥验签 • RSA:成熟但资源消耗大 • ECC:高效,适合嵌入式 • 密钥长度与安全性正相关 核心特性 • 完整性验证 • 身份认证 • 不可否认性 • 防篡改 • 防重放攻击 三者结合 → 可信启动的密码学基础

实战中的选择建议

说了这么多理论,咱们落地到实际项目。我建议你记住这几条:

  • 哈希算法:无脑选SHA256。别碰MD5和SHA1,除非你在维护古董级产品。
  • 非对称加密:MCU资源紧张选ECC P-256,有硬件加速器或者性能充裕选RSA 2048。
  • 数字签名方案:推荐ECDSA(基于ECC的签名算法)或者RSA-PSS。前者省资源,后者兼容性好。

一个小技巧:我在做固件签名工具时,习惯把签名和固件分开存储。签名放在固件末尾的固定偏移处,这样bootloader读取时可以直接定位,不用解析整个固件结构。省时省力。

好了,密码学基础就聊到这儿。这些东西看着抽象,但你在实际做一次可信启动配置、写一次签名验证代码之后,就会觉得——哦,原来就这么回事。

可可精品资料库