用一段话理解哈希
密码学哈希函数接受任意实用长度的输入,并产出固定大小的指纹,称为摘要(digest)。对 SHA-256 而言,摘要是 256 比特——通常显示为 64 个十六进制字符。相同输入总是得到相同摘要。输入哪怕只翻转一个比特,也会得到完全不同的摘要。设计良好的哈希无法仅凭摘要反推出原始输入。
SHA-256 属于由美国国家标准与技术研究院(NIST)设计的 SHA-2 家族。它仍是完整性校验、数字签名、接近区块链的协议,以及密码存储(需配合正确的密钥派生)中的主力——绝不要把裸露、无盐的密码哈希当作存储方案。
请用 SHA-2 哈希工具 对短字符串做哈希,再改一个字符;摘要应看起来毫无关联。
对 SHA-256 而言「有效」意味着什么
密码学家用若干目标评估哈希函数:
原像抗性。 给定摘要,应难以找到任何哈希到该摘要的输入。
第二原像抗性。 给定特定输入,应难以找到具有相同摘要的另一输入。
抗碰撞。 应难以找到任意两个共享同一摘要的不同输入。
以当今公开知识与硬件而言,SHA-256 在这些性质上被认为是强的。该地位是经验性的、由研究驱动;一旦出现实用攻击,算法就会退役。MD5 与 SHA-1 就是曾常用、后来在抗碰撞上被削弱的例子。
Merkle–Damgård 结构(直觉)
SHA-256 以 512 比特块处理消息。内部维护八个 32 比特工作变量,构成 256 比特状态。每个块经过带常量日程与按位运算(旋转、移位、choice、majority)的压缩函数。最后一块之后,状态即为摘要。
处理前会对消息做填充,使其长度适配块结构,并附加原始比特长度。填充确保不同长度、否则可能对齐不佳的消息仍产生不同的内部日程。
日常使用不必手写这些轮次。理解哈希是迭代且感知长度的,有助于解释流式 API:库可在文件分块到达时更新运行状态,再一次性终结。
Hex、Base64 与二进制摘要
摘要本质是二进制。人类通常打印为十六进制以便阅读。有些 API 返回 Base64。两者表示相同的 32 字节。比较两套系统的摘要时,先规范化大小写(hex 常为小写)与编码,再断定哈希不同。
除非协议明确定义截断形式且你理解强度下降,否则切勿在安全敏感比较中截断 SHA-256 摘要。截断会缩小碰撞与原像的搜索空间。
完整性校验
经典流程:
- 通过可信渠道(HTTPS 下载页、已签名的发行说明)发布文件及其 SHA-256 摘要。
- 下载后在本地计算摘要。
- 比较两个摘要;若一致,则文件字节与发布者所哈希的一致。
这能发现意外损坏与多种篡改,_前提是_已发布摘要本身可信。若攻击者能在被攻破的镜像上同时替换文件与摘要,仍可欺骗你。把哈希与签名配对(或从另一可信来源下载摘要)可堵住该缺口。
密码存储:不要单独哈希
用原始 SHA-256 哈希密码不够。攻击者会对无盐哈希使用字典、彩虹表与 GPU 集群。现代做法使用基于密码的密钥派生函数,如 Argon2、scrypt 或 bcrypt,为每条凭证使用唯一盐,并按成本调参。
SHA-256 仍会出现在某些构造_内部_(例如 HMAC-SHA-256,或某些 KDF 的构件),但应用层规则不变:不要把 SHA256(password) 存成认证密钥。
HMAC 与带密钥哈希
HMAC-SHA-256 把密钥与 SHA-256 结合,生成消息认证码。与裸哈希不同,HMAC 让共享密钥的双方验证消息未被改动,且由知晓密钥者生成。API 常用 HMAC 签署 webhook 负载。
密钥必须保密。在不保护密钥的情况下公开 HMAC 摘要,只对没有密钥的一方提供完整性——不是对全世界。
数字签名与证书
公钥签名通常先哈希消息,再对摘要签名。SHA-256 广泛用于 TLS 证书与软件签名。当证书声明与 RSA 或 ECDSA 一起使用 SHA-256 时,哈希是大消息与数学签名运算之间的桥梁。
性能与硬件
SHA-256 在通用 CPU 上很快,有硬件加速时更快(例如 Intel SHA 扩展或专用硅)。哈希数 GB 文件时,流式与原生实现比微调 JavaScript 循环更重要。浏览器中,Web Crypto API 能高效提供 SHA-256;可用时优先于纯 JS 移植。
速度对完整性检查是优点,对密码哈希则是警示:快速哈希也帮攻击者,因此专用密码 KDF 会故意变慢。
在 SHA-2 尺寸间选择
SHA-2 包括 SHA-224、SHA-256、SHA-384、SHA-512 及截断变体。SHA-256 是许多 Web 与 DevOps 任务的默认选择。在 64 位平台上,尽管摘要更大,SHA-512 对大输入可能更快。当标准指定特定尺寸时,请遵循协议要求。
SHA-3 是另一家族(Keccak 海绵构造)。它不是 SHA-2 的即插即用「升级名」;仅在设计要求时再迁移。
常见错误
- 把 SHA-256 当加密。 摘要不可逆;它们不隐藏需要恢复的数据。
- 用对 locale 敏感的字符串工具比较摘要。 在时序泄漏要紧的安全敏感相等检查中,使用常量时间比较。
- 在未规范化的情况下哈希可变结构化数据。 JSON 键序与空白即使语义相同也可能改变哈希。若需要文档的稳定摘要,请先规范化。
- 假定抗碰撞永远成立。 在长寿命系统中规划算法敏捷性:在每个摘要旁存储算法标识。
安全地实验
学习时哈希公开样例字符串与开源文件校验和。除非信任执行环境,否则避免把生产密钥、私钥或个人文档贴到第三方站点。浏览器本地工具可降低随意实验的暴露面。
Tool Plaza 上的 SHA-2 工具 可用于确认你所用语言的标准库是否与测试向量的已知摘要一致。
小结
SHA-256 将任意数据映射为 256 比特摘要,对反演与碰撞具有很强的实用抗性。用它做完整性、作为 HMAC 与签名的构件,以及正确设计的密码 KDF 内部——不要当作独立密码库。理解编码(hex vs Base64),认证发布摘要的渠道,并保持算法标识灵活,以便在密码学最佳实践变化时系统仍可演进。