前言
2026ciscn初赛有两道题都要用到rh256加密,但是比赛的时候都没写出来,虽然这个不是常规解法,但耐不住它劲啊。
工具与思路
所谓RH256加密,就是通过RSA算法加密,然后使用私钥对 payload 进行签名,并使用公钥来校验。这种签名方式的好处是,用于校验的公钥可以(相对)随意分发,黑客想要伪造 token 的话必须拿到私钥,而非对称加密的数学性质使得利用公钥计算出私钥的难度很高,所以伪造难度会高于SH256(对称算法加密)
核心原理是利用 python jwt 库的 CVE-2017-11424 将加密的公钥爆破出来,然后再解出私钥,就能实现 JWT 的伪造了。
获取公钥
寻找常见的公钥分发手段
- 首先可以关注一些常用路由,例如
publickey.pem、publickey.php、public.key等等,可能可以直接获取公钥 - 如果服务器使用了
jwk来分发公钥,则可以在 jwt Header 处找到公钥信息 - 会不会有开发人员蠢到把公钥硬编码到前端呢?emmm… 好像不能排除这个可能性(ciscn初赛还真这么干了)
利用 CVE-2017-11424 破解公钥
对于使用较旧版本 jwt 库的 python 服务,可以利用 CVE-2017-11424 来破解公钥。首先需要获取两个使用不同 payload 的 token,可以简单注册两个不同的用户来获取。然后利用工具 rsa_sign2n 尝试计算公钥
获得公钥后能进行的攻击
可以尝试篡改 Header 中的加密方式(alg 的值),将 RS256,改为 HS256。如果开发人员配置不当的话,服务器可能会将 RS256 使用的公钥作为 HS256 的密钥。此时我们利用获取的 publickey 对修改的 payload 进行签名,就有机会通过校验,达成 token 伪造的目标
获取私钥
可能的私钥泄露
- 通过各种信息搜集手段获取源码包后,可能在其中找到私钥文件或私钥的值
- 配合目录穿越等漏洞读取私钥文件
破解较弱密钥对的私钥
如果 RSA 中的 p/q 值选取不当,则会导致生成的密钥对容易被攻破。在获取有弱点的公钥后,能通过密码学手段计算出其私钥
那怎么判断拿到的公钥弱不弱呢?其实我也不太清楚,这里更多涉及到密码学的知识,如果队内有密码手的话可以请教一下,如果没有相应的知识支撑,其实我的建议是不管它到底弱不弱,先拿工具一把梭了再说
比较好用的工具有 RsaCtfTool,能通过多种算法来尝试破解 RSA
其他思路
- 有些 jwt 库支持 none 的校验模式,如果开发人员配置不当的话,可以篡改校验算法为 none,然后直接删除校验位,即可通过校验
- 当后端使用
jwk来分发公钥时,可以尝试修改 Header 中的公钥内容,然后使用对应的私钥进行签名
实战
2026ciscn初赛 Deprecated
赛后得知这道题是去年国赛的决赛原题,吃了年纪小的亏了
赛后复现docker复现了题目环境
尝试使用了这个奇妙小工具
命令
python .\jwt_forgery.py +两个jwt
爆破出公钥

它可能会生成不止一个公钥,这个时候就需要我们手动筛选了

一模一样!ohhhhh!!!!!
这道题后续就是伪造具备管理员权限的jwt,然后利用任意文件读取漏洞拿到flag
本题题解
[2025 长城杯 final 记录 | A day in AsaL1n](https://asal1n.github.io/2025/05/04/2025 CCB final/index.html#/)
部分信息可能已经过时









