🔓 不分解因数,也能伪造 RSA 签名:一次让密码学家愣住的「绕路」
目录
- 一个 40 年的共识,被 1380 核心年撬开了一条缝
- 同态性质:RSA 数学里那把「双刃剑」
- 现场验证:我在 4GB 服务器上复现了「不拿私钥伪造签名」
- 谁在用「教科书 RSA」:盲签名与 HSM 的世界
- 从 2^65 到 2^119:数字背后的安全级别跳水
- 国内对照:等保、CA 体系,和一场正在进行的迁徙
- RSA 的黄昏,不是被量子计算机提前的
一个 40 年的共识,被 1380 核心年撬开了一条缝
先说结论:2026 年 9 月,一群密码学家用经典计算机(没有量子,没有 GPU),在 5 个月内伪造了 1024 位 RSA 签名——全程没有分解那个公开密钥的质因数。
这不是标题党。这是加州大学圣迭戈分校(UCSD)的 Nadia Heninger 团队和法国 Inria 的 Emmanuel Thomé 合作,在 eprint 2026/2131 论文里公布的真实结果。论文标题本身就透着一股「我们自己也觉得离谱」的味道:Nearly SNFS-Speed Signature Forgery Sans Factoring N——「几乎达到特殊数域筛速度、无需分解 N 的签名伪造」。
密码学界过去 40 年的共识是:RSA 的安全 = 大整数分解的难度。你想伪造签名?先分解出私钥。想分解 1024 位?按当前最快的通用数域筛(GNFS)估计,需要 50 万到 100 万核心年——那是只有国家级机构才掏得起的算力。
这篇论文展示的是另一条路:不分解,直接绕过去。
他们用的不是新算法。2007 年,Joux、Naccache 和 Thomé 就在论文里提出过这个理论构想——一个「几乎特殊数域筛」(√NFS)变体,可以在临时拿到一个裸 RSA 签名预言机(oracle)之后,以接近特殊数域筛(SNFS)的速度伪造签名。但 19 年来没人真正跑过它。它躺在论文里,像一条标注着「理论上存在」的捷径,所有人都知道,没人走过。
Heninger 团队把它走完了。结果:
| 阶段 | 成本 |
|---|---|
| 预计算(只依赖公钥 N) | ~1,200 核心年 |
| Oracle 查询阶段 | 2^32 次裸签名查询 |
| 离线伪造单个签名 | 180 核心年 |
| 总计 | 1,380 核心年(5 个月) |
对照:分解同一个 1024 位模数,需要 50 万到 100 万核心年。伪造比分解便宜了约 360–725 倍,2 到 3 个数量级。
Karsten Nohl(Allurity 创新主管,密码学专家)在接受 Ars Technica 采访时说得很直白:
「如果这个结果通过同行评审,那确实是概念上的突破。RSA 有多难破,一直被认为等同于分解大整数有多难——至少我们以前是这么想的。这篇研究说明,你可以在不破解密钥的情况下实际破解 RSA。」
同态性质:RSA 数学里那把「双刃剑」
要理解这次攻击,得先理解 RSA 签名里一个被大多数人忽略的数学性质:乘法同态。
RSA 签名是这么工作的:私钥持有者用私钥指数 d 对消息 m 计算 σ = m^d mod N。验证者用公钥 (N, e) 检查 σ^e ≡ m (mod N) 是否成立。
关键来了。因为 (m1 × m2)^d = m1^d × m2^d,所以:
σ(m1 × m2) = σ(m1) × σ(m2) (mod N)
也就是说:如果我拿到了 m1 的签名和 m2 的签名,我可以不用私钥,直接算出它们乘积的签名。 这就是乘法同态——一个在正常使用中无伤大雅、甚至被某些协议刻意利用的性质。
但在攻击者手里,它变成了杠杆。论文的攻击模型叫「延迟目标 RSA」(delayed-target RSA):攻击者在第一阶段可以临时访问一个裸 RSA 签名 oracle——任何输入 w,它返回 w^d mod N;第二阶段,攻击者拿到一个目标 t,失去 oracle 访问权,却要输出 t 的签名。
策略很优雅:攻击者把目标 t 表达成一组已知签名元素的乘积。预计算阶段(1200 核心年)先在数域里筛出一组「光滑关系」,把 t 分解成这些元素的组合;查询阶段(2^32 次)向 oracle 要这些元素的签名;离线阶段(180 核心年)用同态性质把它们乘起来——得到 t 的合法签名。
这就是为什么它被称为「malleability attack」(可塑性攻击):RSA 的签名在数学上是可以被「塑形」的。论文里那句最狠的话是:
攻击者可以有效地使用 oracle 查询,窃取等同于持有私钥的能力,而无需实际计算私钥。
用个不精确但传神的类比:这就像有人发现,只要你在银行柜台(oracle)面前晃一晃你的身份证复印件,他就能在你不给密码的情况下,把你账户里的钱转走——不是偷你的密码,是绕过「密码」这个概念本身。
现场验证:我在 4GB 服务器上复现了「不拿私钥伪造签名」
好,到我最喜欢的部分了。我肯定跑不了 1380 核心年——我这台 4GB 的小服务器连一个 GPU 都没有。但攻击的数学机制是可以验证的。我用 Python 复现了 RSA 同态性质 + oracle 组合攻击的核心逻辑:
验证 1:RSA 签名的乘法同态性质
演示模数 N = 193564115805169268940335100992813017433 (128 位)
σ(m1) = 167520477083546004853165160062538671528
σ(m2) = 55273873163981979223172299319180789449
直接签名 σ(m1*m2) = 185213495150085023902734131883149278787
组合签名 σ(m1)*σ(m2) = 185213495150085023902734131883149278787
同态性质成立: True ✅
然后是最关键的一步——攻击者没有私钥,只有 oracle:
验证 2:只有 oracle 没有私钥,也能伪造任意签名
目标消息 m_target = 14294492752826776815
拆解: m_target = a*b mod N, a=199225622973566, b=139922276530889931075762512450010824295
oracle 查询次数: 2 次(只需要 2 次!)
伪造签名 σ_forged = σ(a)*σ(b) mod N = 136233244994097723816873761170556162636
公钥验证通过(签名合法): True ✅
攻击者全程不知道私钥 d = 148774152636495207495548000885755291601
2 次 oracle 查询,伪造出一个通过公钥验证的合法签名,全程不知道私钥。
当然要诚实:我用的是 128 位模数做演示,论文打的是 1024 位真实攻击。我的版本能 2 次查询搞定,是因为「随机拆成两个因子」这个策略在演示规模下足够——真实攻击需要把 t 拆成几千个「光滑」元素,这才是 1200 核心年预计算的真正用途。但机制完全一致:乘法同态让签名可以被组合,组合的原料来自 oracle,私钥从头到尾没出现。
我的验证脚本只有 100 行,跑完不到 1 秒。论文跑了 5 个月。中间差的那 1380 个核心年,就是「把机制变成攻击」的距离。
谁在用「教科书 RSA」:盲签名与 HSM 的世界
现在的问题是:这个攻击对谁有效?
先说清楚一个关键限定:它只对「裸 RSA」(textbook RSA,无填充)的签名/解密 oracle 有效。 现代 RSA 绝大多数都用 PKCS#1 v1.5 或 PSS 填充——填充会破坏同态性质,把「可塑性」堵死。这也是论文和所有受访专家反复强调的:对绝大多数已部署 RSA 没有实际威胁。
但有三个例外,恰好都是裸 RSA 的忠实用户:
1. 硬件安全模块(HSM)的 PKCS#11 接口。 几乎所有企业级 HSM 都提供裸 RSA 操作接口——这本来是为了让应用层自己决定填充方案。但在攻击者眼里,这个接口就是一个完美的签名 oracle。论文团队实际就是用一个 HSM 作为签名 oracle 完成攻击的,演示了「黑盒 API 交互即可冒充 HSM,无需窃取密钥」。PCI DSS 等标准要求企业把私钥锁在 HSM 里,结果 HSM 的接口本身成了攻击通道。
2. 盲签名协议。 最著名的就是 Privacy Pass——Cloudflare 和 Apple 都在用的匿名认证协议。盲签名要求服务器对「被盲化」的消息签名(这样服务器不知道用户在请求什么),而盲化恰好需要裸 RSA。论文指出 Privacy Pass 类协议使用的 2048 位密钥,在这个攻击模型下安全级别只有 2^90,远低于要求的 112 位。攻击 Privacy Pass 需要攻破 Cloudflare/Apple 的服务器并生成 2^43 次签名——Heninger 说「听起来很多,但和 Cloudflare 公开说的一天网络流量是同一数量级」。
3. 遗留的 1024 位密钥。 NIST 2013 年就禁止生成 1024 位密钥,但允许「遗留使用」——就是还在验证旧签名。2026 年了,1024 位 RSA 依然活着。论文给 1024 位算出的安全级别是 2^65——比 80 位的要求低了 15 位。
从 2^65 到 2^119:数字背后的安全级别跳水
密码学的安全级别,说的是「破解需要 2^n 次运算」。128 位安全级别意味着 2^128 次运算——宇宙的原子数大约 10^80 ≈ 2^266,所以 2^128 是一个「物理上不可行」的尺度。
论文给出的新数字:
| 密钥长度 | 传统估计(基于分解) | 新攻击模型 | 降幅 |
|---|---|---|---|
| 1024 位 | 2^80 | 2^65 | 15 bits(3.2 万倍) |
| 2048 位 | 2^112 | 2^90 | 22 bits(400 万倍) |
| 4096 位 | ≥2^128 | 2^119 | ~9 bits |
最扎眼的是最后一行:4096 位 RSA,在这个攻击模型下,也不满足 128 位安全级别。 4096 位是目前 RSA 能给出的最高配置——很多高安全环境(银行、政务、军工)还在用它。如果这个结果成立,那「用更大的 RSA 密钥获得更多安全」这条路,在 oracle 模型下已经走到头了。
更要命的是论文的补充说明:他们全程手写代码,没用 AI、没用 GPU。 用上这些工具,「几乎肯定会进一步压低安全级别」。
不过也要保持冷静。Karsten Nohl 说得对:这是「学术意义上的可实践」,不是「脚本小子意义上的可实践」——需要 5 个月、1380 核心年、2^32 次 oracle 查询,还要先获得临时 oracle 访问权。这不是你我能干的事,甚至不是大多数国家级机构会轻易干的事。但它证明了:RSA 的安全性假设,比我们以为的要复杂得多。
国内对照:等保、CA 体系,和一场正在进行的迁徙
写到这里,我想起国内密码体系的几个对照点。
首先是「等保」与密评。 中国的等级保护制度(等保 2.0)和商用密码应用安全性评估(密评),对金融、政务、关键信息基础设施的密码算法有明确要求。银行的核心系统、政务云、社保、医保——这些系统的证书体系大量基于 RSA,很多还是 2048 位起步、部分核心系统用 4096 位。论文给 4096 位算出的 2^119,对这些系统的合规评审意味着什么?「达标」和「实际安全」之间,出现了一道论文级别的裂缝。
其次是 CA 体系。 全球 TLS 证书链的根证书,大部分还是 RSA 的。我在自己服务器上实测了一下:
本机 CA 信任库: 123 个证书, 其中 RSA 公钥 84 个 (68%)
SSH 主机密钥: 3072 位 RSA (ssh-rsa)
123 个受信任根证书里,68% 是 RSA。这就是 RSA 的真实存在感——不是「还有人在用」,是「几乎无处不在」。浏览器地址栏的小锁,绝大部分还是 RSA 在锁。
最后是「后量子迁移」的节奏。 中国密码管理局已经在推动 SM2/SM3/SM4 等国密算法的普及,SM2 本身就是基于椭圆曲线的,天然不依赖大整数分解假设。而国际上 NIST 计划 2030 年弃用 RSA、2035 年禁用。这篇论文等于给这个时间表加了一脚油门:不是量子计算机来了才需要走,经典计算本身就给出了理由。
RSA 的黄昏,不是被量子计算机提前的
有一个流传很广的说法:RSA 会死于量子计算机——Shor 算法能在多项式时间内分解大整数,量子计算一成熟,RSA 当场暴毙。所以「现在不用急,等量子计算机真来了再说」。
这篇论文给出了一个不同的视角:RSA 的黄昏不需要等量子计算机。 经典计算本身就藏着惊喜——只是过去几十年没人认真去找。论文作者在结论里写了段很诚实的话:
社区一直把注意力放在量子攻击上,经典密码分析则被认为几十年没有悬念。我们希望这次计算表明,RSA 的经典密码分析里仍然有惊喜可挖——如果早有人认真挖,我们可能更早就有理由退役 RSA。
回头看我那 100 行 Python 验证:乘法同态这个性质,从 RSA 发明那天就存在。它在教科书里躺了 40 多年,被当成「有趣的数学性质」——直到有人意识到,配上 oracle,它就是一把不需要钥匙的钥匙。
密码学的故事总是这样:「不可能」和「没想到」之间,往往只隔着一篇没人认真读的 2007 年论文。 1380 核心年撬开的那条缝,也许比量子计算机来得更早。
评论(0)
暂无评论,来写第一条吧~