一、国密算法概述:SM2/SM3/SM4 与国际算法的对比
各位同学,咱们这门课叫《国密算法下的证书链实践》。第一讲,我得先把地基打牢——聊聊国密算法到底是什么,它跟咱们熟悉的 RSA、ECDSA 这些国际算法有啥区别。
我入行那会儿,国内还在全面“跟跑”国际标准。后来在几个政务项目中,客户明确要求必须用国密,我才真正开始啃 SM2、SM3、SM4 的规范。说实话,刚开始觉得就是换了个曲线、换了个哈希,深入下去才发现,设计思路和工程坑点都不少。
1.1 国密标准体系概览
国密算法,全称是中国商用密码算法,由国家密码管理局发布。目前最核心的三个算法是:
- SM2:椭圆曲线公钥密码算法,用于签名、密钥交换和加密。
- SM3:密码杂凑算法,输出 256 位哈希值。
- SM4:分组对称加密算法,密钥长度 128 位。
它们共同构成了中国自主的密码体系。你想想看,以前做 PKI 证书链,底层全是 RSA + SHA-256 + AES。现在换成 SM2 + SM3 + SM4,整个链路都得跟着变。
核心要点:国密不是简单替换,而是从算法到协议、从证书格式到接口规范的全栈自主。做证书链实践,必须理解这三者如何协同工作。
1.2 SM2:椭圆曲线公钥算法
SM2 基于椭圆曲线密码学(ECC),但它不是简单照搬 ECDSA。我对比过两者的参数,SM2 使用的曲线是 sm2p256v1,一条 256 位的素域曲线。
| 对比项 | SM2 | ECDSA (P-256) | RSA-2048 |
|---|---|---|---|
| 密钥长度 | 256 位 | 256 位 | 2048 位 |
| 签名长度 | 64 字节 | 64 字节 | 256 字节 |
| 安全强度 | 128 位 | 128 位 | 112 位 |
| 签名算法 | SM2 签名(带 Z 值) | ECDSA | RSASSA-PKCS1-v1_5 |
这里有个关键区别:SM2 签名时,会先计算一个 Z 值(用户标识 + 曲线参数 + 公钥的哈希)。我刚开始做 SM2 证书时,没注意这个 Z 值,结果验签一直失败。后来翻规范才发现,SM2 的签名输入不是纯消息,而是 Z 值拼接消息。这个坑,我替你们踩过了。
避坑指南:SM2 签名验签时,务必确认用户标识(IDA)的默认值。国密规范中,IDA 默认是 "1234567812345678",但很多实现允许自定义。我曾经因为 IDA 不一致,排查了整整一个下午。
1.3 SM3:密码杂凑算法
SM3 的输出是 256 位,跟 SHA-256 长度一样。但算法结构不同——SM3 基于 Merkle-Damgård 结构,消息分组 512 位,压缩函数有 64 轮迭代。
我个人的习惯是,把 SM3 看作“中国版的 SHA-256”,但性能上略有差异。在 x86 平台上,SM3 软件实现比 SHA-256 慢 20%-30%;但在国产 CPU(如飞腾、鲲鹏)上,差距会缩小,甚至反超。
| 特性 | SM3 | SHA-256 |
|---|---|---|
| 输出长度 | 256 位 | 256 位 |
| 分组大小 | 512 位 | 512 位 |
| 压缩轮数 | 64 轮 | 64 轮 |
| 消息扩展 | 16→68 字 | 16→64 字 |
在证书链实践中,SM3 主要用于:
- 证书摘要计算(TBSCertificate 的哈希)
- SM2 签名中的 Z 值计算
- CRL 和 OCSP 响应中的摘要
1.4 SM4:分组对称加密算法
SM4 是国密体系里最“低调”的一个。它不像 SM2 那样有复杂的曲线参数,也不像 SM3 那样有独特的 Z 值逻辑。但它在证书链实践中同样重要——比如加密私钥、保护会话密钥。
SM4 是 128 位分组、128 位密钥的 Feistel 结构算法,轮数 32 轮。跟 AES-128 比,两者安全强度相当,但 SM4 的 S 盒和密钥扩展算法完全不同。
| 对比项 | SM4 | AES-128 |
|---|---|---|
| 分组大小 | 128 位 | 128 位 |
| 密钥长度 | 128 位 | 128 位 |
| 结构 | Feistel | SPN |
| 轮数 | 32 轮 | 10 轮 |
| 模式支持 | ECB/CBC/CTR/GCM | ECB/CBC/CTR/GCM |
注意:SM4 的 GCM 模式在国密标准中称为 SM4-GCM,但部分老旧实现只支持 ECB 和 CBC。做证书链时,如果涉及加密私钥,建议优先使用 SM4-GCM 或 SM4-CBC + HMAC-SM3,避免 ECB 模式带来的语义安全问题。
1.5 国密与国际算法的核心差异
说白了,国密不是“重新发明轮子”,而是在密码学原理不变的前提下,换了参数、换了曲线、换了 S 盒。但工程上,这些“换”会带来一系列连锁反应。
- 证书格式:国密证书使用 SM2 公钥,OID 为 1.2.156.10197.1.301。签名算法 OID 为 1.2.156.10197.1.501。这些 OID 在 X.509 证书中必须正确填写。
- 密钥对生成:SM2 密钥对生成比 RSA 快得多,但比 ECDSA 略慢(因为 SM2 的曲线参数验证更严格)。
- 性能表现:SM2 签名速度约为 RSA-2048 的 10 倍,验签速度约为 RSA 的 3 倍。SM3 哈希速度约为 SHA-256 的 80%。SM4 加解密速度约为 AES-128 的 90%。
我在一个电子政务项目中,需要将原有 RSA 证书链迁移到国密。最头疼的不是算法本身,而是兼容性——浏览器不支持 SM2,Java 原生库不支持 SM3,OpenSSL 需要打补丁。这些实战问题,后面章节我会详细讲。
1.6 国密算法体系结构图
下面这张图,我画出了国密算法在证书链中的位置和关系。你可以看到,SM2 负责签名和密钥交换,SM3 负责哈希,SM4 负责加密。三者通过证书和协议串联起来。
1.7 小结:为什么证书链必须理解这些?
做证书链实践,你不可能绕过算法层。证书的签名验证、摘要计算、私钥保护,每一步都依赖 SM2/SM3/SM4 的正确实现。
我记得有一次,客户反馈证书链验证失败。排查到最后,发现是 SM3 摘要计算时,输入数据多了一个换行符。这种问题,如果你不理解算法细节,根本无从下手。