Skip to content

MD5 已经不安全了,为什么还到处在用 ​

「MD5 不安全,别用了」——这话没错,但下载页上给的校验值至今很多还是 MD5。两件事其实不矛盾,因为它们防的根本不是同一种问题。

「文件哈希校验」工具页初始界面:选择文件 / 参数配置 / 哈希算法 / MD5 / SHA-1 / SHA-256 / SHA-512 / 期望哈希值(可选) / 实时预览;页头标签「浏览器本地执行 · 免费」

打开「文件哈希校验」看到的初始界面。在浏览器本地完成、数据不离开浏览器,免费。

先分清两种威胁 ​

意外损坏:文件在传输或存储中出错。网络丢包、硬盘坏道、下载中断后续传错位。这种错误是随机的,没有智能,不会挑算法的弱点。

恶意篡改:有人故意改了文件,还要让校验值看起来没变。这是有目标、有算力的对手。

MD5 挡得住第一种,挡不住第二种。而下载页给校验值,绝大多数时候要解决的就是第一种。

MD5 到底怎么被攻破的 ​

需要区分两类攻击,它们的严重程度差很远:

攻击类型含义MD5 现状
碰撞攻击攻击者自己构造两个哈希相同的文件已被攻破,普通电脑几秒可完成
原像攻击给定一个哈希值,反推出能产生它的文件仍未被有效攻破

关键区别是:碰撞攻击要求攻击者能同时控制两个文件。他可以造出「正常版」和「带后门版」两个哈希相同的程序,把正常版拿去送检,把带后门版发给你。

但如果文件是别人给定的、他改不了原文件——比如官方发布的安装包已经存在、哈希已经公布——他没法凭空造出一个哈希相同的恶意文件。这就是为什么 MD5 用于校验已公布文件的完整性时,实际风险远小于标题党说的那样。

即便如此,SHA-256 的计算成本在今天已经低到可以忽略,新场景没有任何理由继续选 MD5。

三个算法怎么选 ​

算法输出长度状态建议
MD5128 位(32 个十六进制字符)碰撞已攻破仅用于校验意外损坏;兼容旧系统
SHA-1160 位(40 个字符)碰撞已攻破(2017 年)不要用于新场景
SHA-256256 位(64 个字符)安全默认选它

一句话:新场景一律 SHA-256;遇到只给 MD5 的下载页,算 MD5 对一下也比不校验强。

校验值对不上,先别慌 ​

实际操作中,校验失败十有八九不是被篡改了,而是这几种情况:

下载不完整。 最常见。文件大小对不上就基本可以确定,重新下载即可。

比错了对象。 有些发布页同时给出压缩包和解压后文件的哈希,或者给了多个平台的版本。确认你算的和页面上标的是同一个文件。

换行符被改写。 文本文件在 Windows 和 Linux 之间传递时,如果经过了会转换换行符的工具(某些 Git 配置、FTP 的文本模式),内容变了哈希自然就变了。二进制文件不受影响。

大小写差异。 十六进制哈希值大小写不敏感,A3F 和 a3f 是同一个值。有些工具输出大写、有些小写,肉眼比对时容易看岔。

一个常见的误用:拿它存密码 ​

顺带说一个和文件校验无关、但同源的错误:用 MD5(或 SHA-256)存用户密码。

问题不在于算法被攻破,而在于它们太快了。哈希算法为文件校验而设计,追求的就是快——一台普通显卡每秒能算几十亿次 SHA-256。这个优点用在密码上就成了致命缺点:攻击者拿到数据库后,可以用同样的速度暴力穷举。

密码要用专门的慢哈希:bcrypt、scrypt、Argon2。它们故意设计得慢且吃内存,并且每个密码配一份随机盐,让预先算好的彩虹表失效。

所以「用 SHA-256 代替 MD5 存密码」并没有解决问题,只是把一个快算法换成了另一个快算法。

怎么算 ​

文件哈希校验 一次性给出 MD5、SHA-1、SHA-256 三个值,也可以直接粘贴官网给的校验值做比对——工具会告诉你匹配与否,不用自己盯着 64 个字符逐位对。

计算在浏览器本地完成,文件不上传。这对校验类工具是必要的:为了验证一个文件没被动过而先把它上传到某个服务器,本身就与目的相悖。

校验只能证明文件与发布者公布的一致。如果发布渠道本身被入侵、连哈希值一起被替换,校验也无能为力——所以哈希值要从可信来源获取,最好与文件本身不同源。

最后更新:2026-09-05