密码技术(七、二)之单向散列函数
单向散列函数
——获取消息的“指纹”
MD4是由Rivest 于1990年设计的单向散列函数,能够产生128比特的散列值。不过,虽则Dobbertin提出寻找MD4散列碰撞方法,现在它已经不安全了。
MD5是由Rivest于1991年设计的单向散列函数,能够产生128比特的散列值。MD5的强抗碰撞性已经被攻破,也就是说,现在已经能够产生具备相同散列值的两条不同的消息,因此它也已经不安全了。
MD4和MD5的MD是消息摘要(Message Digest)的缩写。
SHA-1是由NIST(National Institue of Standards and Technology ,美国国家标准计算研究所)设计的一种能够产生160比特的散列值的单向散列函数。1993年别作为美国联邦信息处理标准规格发布的是SHA,1995年发布修订版FIPS PUB 180-1称为SHA-1。在《CRYPTREC密码清单》中,SHA-1已经被列入“可谨慎运用的密码清单”,即除了用于保持兼容性的目的以外,其他情况都不推荐使用。
SHA-256、SHA-384和SHA512都是由NIST设计的单向散列函数,它们的散列值长度分别为256比特、384比特和512比特。这些单向散列函数合起来统称为SHA-2,它们的消息长度也存在上限(SHA-256的上限近于2 64比特,SHA-384和SHA-512的上限接近于2 128比特 )。这些单词散列函数式于2002年和SHA-1一起作为FIPS PUB 180-2发布的。
SHA-1的强抗碰撞性已于2005年被攻破,也就是说,现在已经能够产生具备相同散列值的两条不同消息。不过SHA-2还尚未被攻破。
6种版本SHA-2
RIPEMD 是与1996年由Hans Dobbertin、Antoon Bosselaers 和Bart Preneel 设计的一种能够产生160比特的散列值单向散列函数。RIPEMD-160是欧盟RIPE项目所设计的RIPEMD单向散列函数的修订版。这一系列的函数还包括RIPEMD-128、RIPEMD-256、RIPEMD-320等其他一些版本。在《CRYPTREC密码清单》中,RIPEMD已经被列入“可谨慎运用的密码清单”,即除了用于保持兼容性的目的以外,其他情况都不推荐使用。
RIPEMD的强碰撞性已于2004年被攻破,但RIPEMD-160还尚未被攻破。比特币中使用的就是RIPEMD-160。
SHA-3(Secure Hash Algorithm-3)是一种作为新标准发布的单向散列函数算法,用来替代在理论上已经被找出攻击方法的SHA-1算法。全世界的企业和密码学家提交了SHA-3的候选方案很多,经过5年的选拔,最终在2013年正式确定了将Keccak算法作为SHA-3的标准。
Keccak最终被选为SHA-3的理由如下:
Keccak是一种被选定为SHA-3标准的单向散列函数算法。
Keccak可以生成任意长度的散列值,但是为了配合SHA-2的散列值长度,SHA-3标准中共规定了SHA3-224、SHA-3-256、SHA3-384、SHA3-512这4个版本。在输入数据的长度上限方面,SHA-1为2 64-1比特,SHA-2为2 128-1比特,而SHA-3则没有限制。
此外FIPS202中还规定了两个可输出任意长度散列值的函数(extendable-output function,XOF),分别为SHAKE128和SHAKE256。据说SHAKE这个名字取自Secure Hash Algorithm 与Keccak这几个单词。
Keccak采用了海绵结构,输入的数据在进行填充后,要经过 吸收阶段 和 挤出阶段 ,最终生成输出的散列值。
并且作为海绵结构的变形, Keccak中还提出了一种双共结构。
这里关于 Keccak的结构,不做过多解读,想详细了解,请参考原著;
暴力破解
任何文件中都或多或少存在具有一定的冗余性。利用文件的冗余性生产具有相同散列值的另一个文件,这就是一种针对单向散列函数的攻击。
在对密码进行暴力破解时,我们就是按照顺序改变密钥,如0、1、2、3.....然后分别用这些密钥进行解密的,对单向散列函数进行暴力破解也是如此,即每次都稍微改变一下消息的值,然后对这些消息求散列值。
现在我们在寻找的是一条具备特定散列值的消息,具备相同散列值的另一条不同的消息。这相当于一种 试图破解单向散列函数的“弱碰撞性”的攻击 。在这种情况下,暴力破解需要尝试的次数,可以根据散列值的长度计算出来,以SHA3-512为例,由于它的散列值长度为512比特,因此最多只需要尝试2^512次就能找到目标消息了,如此多的尝试次数在现实中是不可能完成的。
由于尝试次数纯粹是由散列值的长度决定的,因此散列值的长度越长的单向散列函数,其抵御暴力破解的能力也就越强。
找出具有指定散列值的消息的攻击方式分为两种,即“原像攻击”和“第二原像攻击”。 原像攻击 (Pre-Image Attack)是指定一个散列值,找出具有该散列值的任意消息; 第二原像攻击 (Second Pre-Image Attack)是指定一条消息1,找出另外一条消息2,消息2的散列值和消息1相同。
生日攻击
要找到散列值相同的两条消息,而散列值则可以是任意值。这样的攻击,一般称为 生日攻击 (birthday attack)或是 冲突攻击 (collision attack),这是一种 试图破解单向散列函数的“强碰撞性” 攻击。
我们以512比特的散列值为例,对单向散列函数进行暴力破解所需要的尝试次数2^512 次,而对同一单向散列函数进行生日攻击所需要尝试的次数2^256次,因此和暴力破解相比,生日攻击所尝试的次数要少的多。
单向散列函数能够辨别出“篡改”,但无法辨别出“伪装”。
当我们不仅需要确认文件的完整性,同时还需要确认这个文件是否真的属于他的,我们还需要认证。
该系列的主要内容来自《图解密码技术第三版》
我只是知识的搬运工
文章中的插图来源于原著
2023-08-15 广告