3、非对称加密基础:公钥与私钥、RSA与ECC算法对比、密钥长度选择

聊固件签名,绕不开非对称加密。说白了,它就是一把「公开的锁」和一把「私藏的钥匙」。你想想看,我们给固件签名,本质上就是用私钥给固件打上一个「这玩意儿是我发的」的戳,别人用公钥一验就知道真假。

我刚开始接触这块时,总觉得概念绕。后来亲手配过一次密钥,才彻底搞明白。嗯,咱们今天就把这事掰扯清楚。

3.1 公钥与私钥:一对天生的搭档

非对称加密里,密钥是成对出现的。公钥可以公开,谁都能拿;私钥必须保密,只有你自己知道。它们的关系是:用公钥加密的数据,只有对应的私钥能解开;反过来,用私钥签名的数据,只有对应的公钥能验证。

这个特性,恰好满足了固件签名的核心需求:

  • 身份认证:私钥只有你持有,别人伪造不了签名。
  • 完整性校验:固件内容一旦被改,签名验证就会失败。
  • 不可抵赖性:你用私钥签了名,就不能说「这不是我干的」。
我的习惯:每次生成新密钥对,我都会把公钥单独导出一份,放在项目的「公开资料」目录里。私钥?嗯,直接锁进硬件安全模块(HSM),绝不碰磁盘。

3.2 RSA与ECC算法对比:老牌劲旅 vs 后起之秀

目前固件签名领域,RSA 和 ECC 是两大主流。我两种都用过,各有各的脾气。

3.2.1 RSA:成熟、稳定、但有点「胖」

RSA 基于大整数分解的数学难题。你给它一个足够大的合数,想把它拆成两个质数,难得很。RSA 的优点是算法公开、实现库多、兼容性极好。几乎所有芯片的 BootROM 都支持 RSA 验签。

但缺点也很明显——密钥和签名都很大。2048 位的 RSA 密钥,光公钥就 256 字节,签名也是 256 字节。这在资源受限的 IoT 设备上,是个不小的负担。

我曾经踩过的坑:有一款低端 MCU,Flash 只有 64KB。我把 RSA-2048 的公钥和验签代码塞进去后,留给应用的空间只剩不到 20KB。后来换成 ECC,才喘过气来。

3.2.2 ECC:短小精悍,后劲十足

ECC 基于椭圆曲线离散对数难题。同样的安全强度下,ECC 的密钥长度比 RSA 短得多。举个例子:ECC-256 的安全性与 RSA-3072 相当,但 ECC 的公钥只有 32 字节,签名也只有 64 字节左右。

这意味着什么?

  • 存储省:公钥和签名占用的 Flash 更少。
  • 传输快:固件包里的签名数据更小,升级耗时更短。
  • 算力要求低:ECC 的验签计算量比 RSA 小,尤其适合没有硬件加速器的 MCU。

不过 ECC 也有它的「小脾气」:曲线参数选错了会出大问题。比如使用 NIST 的 P-256 曲线,虽然业界广泛认可,但有些人担心它可能有后门。我个人更倾向 Curve25519(X25519/Ed25519),它设计更透明,实现也更安全。

3.2.3 对比表格:一目了然

对比维度 RSA-2048 ECC-256 (P-256) ECC-256 (Ed25519)
安全强度 112 位 128 位 128 位
公钥长度 256 字节 64 字节 32 字节
签名长度 256 字节 64 字节 64 字节
验签速度 较慢 较快 极快
硬件支持 非常广泛 广泛 逐渐普及
算法成熟度 极高 高 中高

3.3 密钥长度选择:不是越长越好

很多人觉得密钥越长越安全,其实不然。密钥长度要跟你的安全需求、硬件能力、业务场景匹配。

我见过有人给一个温湿度传感器配 RSA-4096,结果设备每次启动验签要等 3 秒。用户都以为设备死机了。你说这图啥?

3.3.1 安全等级与密钥长度的对应关系

业界有个共识:128 位的安全强度,对于绝大多数商业产品已经足够。对应到具体算法:

  • RSA:至少 2048 位,推荐 3072 位。
  • ECC:至少 256 位(如 P-256、Secp256k1),推荐 Curve25519。

如果你做的是金融级或军工级产品,可以考虑 RSA-4096 或 ECC-384。但说实话,对于固件签名这个场景,RSA-2048 或 ECC-256 已经能挡住绝大多数攻击。

我的建议:新项目优先选 ECC-256(Ed25519)。如果芯片 BootROM 只支持 RSA,那就用 RSA-2048。别为了「看起来更安全」而选 RSA-4096,那点安全增益抵不上性能损失。

3.3.2 密钥长度选择的决策树

为了帮你快速决策,我画了一张流程图。你可以根据自己项目的实际情况,顺着箭头找到合适的密钥长度。

密钥长度选择决策树 开始选择密钥长度 芯片 BootROM 支持 ECC 验签? 是 否 选 ECC-256 (Ed25519) 选 RSA-2048 验签快,存储省,推荐 验签慢,公钥大,兼容好 确定密钥长度,生成密钥对 说明:如果芯片支持 ECC,优先选 Ed25519;否则用 RSA-2048。安全强度足够,性能也平衡。

3.4 避坑指南:密钥长度选择的常见误区

最后,分享几个我亲眼见过的翻车案例。你注意避开。

  • 误区一:密钥越长越安全。RSA-4096 比 RSA-2048 安全吗?理论上是,但实际攻击者不会去硬解你的密钥,而是找别的漏洞。为了那点安全增益,牺牲性能和存储,不值当。
  • 误区二:ECC 一定比 RSA 快。ECC 的验签确实快,但签名生成反而比 RSA 慢。不过固件签名是离线操作,慢一点无所谓。验签才是关键路径。
  • 误区三:所有 ECC 曲线都一样。大错特错。有些曲线(比如 secp256r1)有专利问题,有些(比如 secp256k1)更适合区块链。我建议你优先用 Curve25519,它设计上就避免了侧信道攻击。
我曾经见过一个项目:团队选了 RSA-4096,结果设备启动验签花了 5 秒。用户投诉说「开机比冰箱还慢」。最后不得不紧急换方案,重新烧录 BootROM。嗯,选型阶段多花一小时,后面能省一周。