第2章 密码学基础与国密算法简介
密码学这东西,我在刚开始做审计日志的时候总觉得是“别人的事”。后来被客户问了一句“你的日志签名用的什么算法”,我才意识到不懂密码学根本没法设计可靠的审计系统。说白了,审计日志的安全根基,就扎在密码学算法上。
这一章我们只聊最核心的东西:对称/非对称加密、哈希函数,以及国密 SM2、SM3、SM4 的原理和用法。不废话,直接上干货。
2.1 密码学基础回顾
我习惯把密码学的基础分成三块,你想想看,所有安全场景都离不开它们:
- 对称加密:加密和解密用同一个密钥。快,适合大量数据。
- 非对称加密:有公钥和私钥,公钥加密私钥解密。慢,适合密钥交换和数字签名。
- 哈希函数:把任意长度数据变成固定长度的摘要。不可逆,用于完整性校验和密码存储。
2.2 国密算法概览
国密算法是国家密码管理局发布的标准,在审计日志场景中,我用得最多的是这三个:
| 算法 | 类型 | 密钥长度 | 主要用途(审计日志中) |
|---|---|---|---|
| SM2 | 非对称加密(椭圆曲线) | 256 位 | 数字签名、日志签名、密钥协商 |
| SM3 | 密码杂凑 | 输出 256 位 | 日志完整性哈希链、消息摘要 |
| SM4 | 对称分组密码 | 128 位 | 日志内容加密、密钥传输加密 |
为什么要用国密?合规是硬性要求。但更重要的是,它们的密码学强度经过严格论证,我个人觉得在同等安全级别下,SM2 的椭圆曲线比 RSA 更轻量,SM3 比 SHA-256 更安全,SM4 的硬件实现效率也很高。
2.3 算法原理简析
SM2
SM2 基于椭圆曲线离散对数问题。它的核心是:给定基点 G 和公钥 Q = d·G(d 是私钥),想从 Q 反推 d 极难。签名时,用户用私钥对消息哈希做运算,验证者用公钥验签。我曾经在改造一个老系统时,遇到签名长度变长的问题(SM2 签名是 64 字节,而 RSA 签名是 128 字节),反而节省了存储空间。
SM3
SM3 是密码杂凑算法,输出 256 位。算法结构类似 SHA-256,但增加了更复杂的消息扩展和压缩函数,抗碰撞性更强。在审计日志中,我常用 SM3 构造哈希链——每条日志记录包含前一条的 SM3 哈希值,这样任何篡改都会破坏链的连续性。
SM4
SM4 是 128 位分组密码,密钥长度也是 128 位。它采用 Feistel 结构,轮函数包含非线性变换(S 盒)和线性变换。加密速度非常快,适合加密大规模的日志数据。注意分组密码需要选择合适的工作模式,比如 GCM(伽罗瓦计数器模式)可以同时提供机密性和完整性校验。
关键点:在审计日志设计中,绝不使用 ECB 模式。同样的明文会得到同样的密文,攻击者能看出日志模式。我遇到过用 ECB 加密日志的场景,后期不得不全部重做。
2.4 在审计日志场景中的应用
把这些算法组合起来,就能搭建一套可靠的审计日志保护体系:
- 日志签名:使用 SM2 私钥对每条日志的 SM3 摘要签名,验证方用公钥验签。防伪造和抵赖。
- 日志加密:使用 SM4 对称密钥加密日志正文,然后用 SM2 公钥加密这个对称密钥(混合加密)。兼顾速度和安全性。
- 完整性链:每条日志的 SM3 摘要包含上一条日志的摘要,形成链式结构。任何篡改都会断裂。
我曾经犯过一个错:把 SM3 哈希和签名直接拼到一起,结果签名过程中哈希值被意外修改,导致验签失败。正确的做法是先计算 SM3 摘要,再对摘要签名,签名时要保证摘要不被中途篡改。
2.5 核心关系图
下面这张图帮你理清密码学基础与国密算法在审计日志中的角色:
2.6 几个实用建议
- 密钥管理比算法本身更重要。我曾经见过一家公司 SM2 私钥硬编码在配置文件里,直接用明文保存。再强的算法也白搭。
- SM4 一定要用认证加密模式,比如 GCM 或 CCM。审计日志如果只加密而不校验完整性,攻击者可以替换整个密文。我有一次安全审计就发现了这个问题。
- 哈希链的节点要包含时间戳和顺序号,否则单纯链式哈希容易遭到重放攻击。我习惯在每条日志的 SM3 输入中加入“前一条哈希 + 时间戳 + 日志内容”。
- 签名操作要原子化:计算哈希、签名、写入日志这三步必须是一个事务。失败就回滚,避免产生半条签名的日志。
我个人习惯在开发阶段先用 OpenSSL 测试国密算法的正确性,再用 GMSSL 或腾讯的国密库做生产部署。很多 bug 在算法封装层就能发现,别等上线再排查。