1. 程式人生 > >MD5科普(二):MD5演算法詳解/如何改進MD5演算法?

MD5科普(二):MD5演算法詳解/如何改進MD5演算法?

原文連結:https://www.6zou.net/tech/md5_how_to_do.html

一、MD5演算法的實現

MD5演算法簡述:

MD5是輸入不定長度資訊,輸出固定長度128-bits的演演算法。

經過程式流程,生成四個32位資料,最後聯合起來成為一個128-bits雜湊。

基本方式為,求餘、取餘、調整長度、與連結變數進行迴圈運算。

MD5相對MD4所作的改進:

1. 增加了第四輪;

2. 每一步均有唯一的加法常數;

3. 為減弱第二輪中函式g的對稱性從(x&y)|(x&z)|(y&z)變為(x&z)|(y&(~z));

4. 第一步加上了上一步的結果,這將引起更快的雪崩效應;

5. 改變了第二輪和第三輪中訪問訊息子分組的次序,使其更不相似;

6. 近似優化了每一輪中的迴圈左移位移量以實現更快的雪崩效應。各輪的位移量互不相同。
MD5演算法第一步:位填充

在MD5演算法中,首先需要對資訊進行填充,使其位長對512求餘的結果等於448。

因此,資訊的位長將被擴充套件至N*512+448(bits),即N*64+56個位元組(bytes),其中N為一個正整數。

填充的方法如下:

在資訊的後面填充一個1和無數個0,直到滿足上面的條件時才停止用0對資訊的填充。

然後,在這個結果後面附加一個以64位二進位制表示的填充前資訊長度。

經過這兩步的處理,現在的資訊的位長=N*512+448+64=(N+1)*512(bits),即長度恰好是512的整數倍。這樣做的原因是為滿足後面處理中對資訊長度的要求。

MD5演算法第二步:迴圈運算

MD5中有四個32位被稱作連結變數(Chaining Variable)的整數引數,

他們分別為:

A=0x67452301

B=0xefcdab89

C=0x98badcfe

D=0x10325476

當設定好這四個連結變數後,就開始進入演算法的四輪迴圈運算。

迴圈的次數是資訊中512位資訊分組的數目(第一步中提到的N*512的N個組)。

將上面四個連結變數A、B、C、D分別複製到另外四個變數中:a、b、c、d。

主迴圈共有四輪,每輪迴圈都很相似。第一輪進行16次操作。每次操作對a、b、c、d中的其中三個作一次非線性函式運算,然後將所得結果加上第四個變數,文字的一個子分組和一個常數。

再將所得結果向左環移一個不定的數,並加上a、b、c或d中之一。最後用該結果取代a、b、c或d中之一。

以一下是每次操作中用到的四個非線性函式(每輪一個):

F(X,Y,Z) = (X&Y)|((~X)&Z)

G(X,Y,Z) = (X&Z)|(Y&(~Z))

H(X,Y,Z) = X^Y^Z

I(X,Y,Z) = Y^(X|(~Z))

(&是與,|是或,~是非,^是異或)

這四個函式的說明:如果X、Y和Z的對應位是獨立和均勻的,那麼結果的每一位也應是獨立和均勻的。

函式F是一個逐位運算的函式。即:如果X,那麼Y,否則Z。

函式H是逐位奇偶操作符。

假設Mn(M0…M15)表示訊息的第n個子分組, 常數ti是4294967296*abs(sin(i))的整數部分(i: 1到64,單位:弧度,4294967296: 2的32次方)

FF(a, b, c, d, Mn, s, ti) 表示 a = b + ((a + F(b, c, d) + Mn + ti) << s)

GG(a, b, c, d, Mn, s, ti) 表示 a = b + ((a + G(b, c, d) + Mn + ti) << s)

HH(a, b, c, d, Mn, s, ti) 表示 a = b + ((a + H(b, c, d) + Mn + ti) << s)

II(a, b, c, d, Mn, s, ti) 表示 a = b + ((a + I(b, c, d) + Mn + ti) << s)

這四輪(64步)分別是:

第一輪
FF(a, b, c, d, M0, 7, 0xd76aa478)
FF(d, a, b, c, M1, 12, 0xe8c7b756)
FF(c, d, a, b, M2, 17, 0x242070db)
FF(b, c, d, a, M3, 22, 0xc1bdceee)
FF(a, b, c, d, M4, 7, 0xf57c0faf)
FF(d, a, b, c, M5, 12, 0x4787c62a)
FF(c, d, a, b, M6, 17, 0xa8304613)
FF(b, c, d, a, M7, 22, 0xfd469501)
FF(a, b, c, d, M8, 7, 0x698098d8)
FF(d, a, b, c, M9, 12, 0x8b44f7af)
FF(c, d, a, b, M10, 17, 0xffff5bb1)
FF(b, c, d, a, M11, 22, 0x895cd7be)
FF(a, b, c, d, M12, 7, 0x6b901122)
FF(d, a, b, c, M13, 12, 0xfd987193)
FF(c, d, a, b, M14, 17, 0xa679438e)
FF(b, c, d, a, M15, 22, 0x49b40821)
第二輪
GG(a, b, c, d, M1, 5, 0xf61e2562)
GG(d, a, b, c, M6, 9, 0xc040b340)
GG(c, d, a, b, M11, 14, 0x265e5a51)
GG(b, c, d, a, M0, 20, 0xe9b6c7aa)
GG(a, b, c, d, M5, 5, 0xd62f105d)
GG(d, a, b, c, M10, 9, 0x02441453)
GG(c, d, a, b, M15, 14, 0xd8a1e681)
GG(b, c, d, a, M4, 20, 0xe7d3fbc8)
GG(a, b, c, d, M9, 5, 0x21e1cde6)
GG(d, a, b, c, M14, 9, 0xc33707d6)
GG(c, d, a, b, M3, 14, 0xf4d50d87)
GG(b, c, d, a, M8, 20, 0x455a14ed)
GG(a, b, c, d, M13, 5, 0xa9e3e905)
GG(d, a, b, c, M2, 9, 0xfcefa3f8)
GG(c, d, a, b, M7, 14, 0x676f02d9)
GG(b, c, d, a, M12, 20, 0x8d2a4c8a)
第三輪
HH(a, b, c, d, M5, 4, 0xfffa3942)
HH(d, a, b, c, M8, 11, 0x8771f681)
HH(c, d, a, b, M11, 16, 0x6d9d6122)
HH(b, c, d, a, M14, 23, 0xfde5380c)
HH(a, b, c, d, M1, 4, 0xa4beea44)
HH(d, a, b, c, M4, 11, 0x4bdecfa9)
HH(c, d, a, b, M7, 16, 0xf6bb4b60)
HH(b, c, d, a, M10, 23, 0xbebfbc70)
HH(a, b, c, d, M13, 4, 0x289b7ec6)
HH(d, a, b, c, M0, 11, 0xeaa127fa)
HH(c, d, a, b, M3, 16, 0xd4ef3085)
HH(b, c, d, a, M6, 23, 0x04881d05)
HH(a, b, c, d, M9, 4, 0xd9d4d039)
HH(d, a, b, c, M12, 11, 0xe6db99e5)
HH(c, d, a, b, M15, 16, 0x1fa27cf8)
HH(b, c, d, a, M2, 23, 0xc4ac5665)
第四輪
II(a, b, c, d, M0, 6, 0xf4292244)
II(d, a, b, c, M7, 10, 0x432aff97)
II(c, d, a, b, M14, 15, 0xab9423a7)
II(b, c, d, a, M5, 21, 0xfc93a039)
II(a, b, c, d, M12, 6, 0x655b59c3)
II(d, a, b, c, M3, 10, 0x8f0ccc92)
II(c, d, a, b, M10, 15, 0xffeff47d)
II(b, c, d, a, M1, 21, 0x85845dd1)
II(a, b, c, d, M8, 6, 0x6fa87e4f)
II(d, a, b, c, M15, 10, 0xfe2ce6e0)
II(c, d, a, b, M6, 15, 0xa3014314)
II(b, c, d, a, M13, 21, 0x4e0811a1)
II(a, b, c, d, M4, 6, 0xf7537e82)
II(d, a, b, c, M11, 10, 0xbd3af235)
II(c, d, a, b, M2, 15, 0x2ad7d2bb)
II(b, c, d, a, M9, 21, 0xeb86d391)

在第i步中,ti是4294967296*abs(sin(i))的整數部分,i的單位是弧度。(4294967296等於2的32次方)

所有這些完成之後,將A、B、C、D分別加上a、b、c、d。

然後用下一分組資料繼續執行演算法,迴圈結束後生成四個32-bits資料,然後聯合起來成為一個128-bits雜湊。

二、MD5演算法的修改

MD5中有四個32位被稱作連結變數(Chaining Variable)的整數引數,他們分別為:

A=0x67452301

B=0xefcdab89

C=0x98badcfe

D=0x10325476

我們可以把這四個16進位制的值看做是初始種子,後面進行一系列的異或、求模等的運算,對每個分組執行4*16次。

那麼只要我們修改初始值就會變成另外一種的MD5雜湊演算法。

用途:假如資料庫中MD5雜湊被獲取,用原始MD5演算法+字典的爆破方式是查不到該MD5雜湊的。

注意:隨意修改有可能導致更容易出現不同字串加密結果相同的情況(即術語所說的碰撞更容易產生),但是用於常規中小網站密碼加密足矣。