引用wiki的定義,散列函數(shù)(或散列算法,英語:Hash Function)是一種從任何一種數(shù)據(jù)中創(chuàng)建小的數(shù)字“指紋”的方法。該函數(shù)將數(shù)據(jù)打亂混合,重新創(chuàng)建一個(gè)叫做散列值的指紋。散列值通常用來代表一個(gè)短的隨機(jī)字母和數(shù)字組成的字符串。好的散列函數(shù)在輸入域中很少出現(xiàn)散列沖突。在散列表和數(shù)據(jù)處理中,不抑制沖突來區(qū)別數(shù)據(jù),會(huì)使得數(shù)據(jù)庫記錄更難找到。(具體專業(yè)術(shù)語請自行度娘)
MD5是單向散列算法的一種,全稱是Message-Digest Algorithm 5(信息-摘要算法),經(jīng)MD2、MD3和MD4發(fā)展而來。這里所謂單向,只能向后計(jì)算最終值,不能通過反向計(jì)算出初始值。
MD5的性質(zhì):
輸入任意長度的信息,經(jīng)過處理,輸出為128位的信息(數(shù)字指紋)
不同的輸入得到的不同的結(jié)果(唯一性)
根據(jù)128位的輸出結(jié)果不可能反推出輸入的信息(不可逆)
MD5算法步驟:
1、補(bǔ)位
首先要進(jìn)行補(bǔ)位,使得補(bǔ)位后信息的長度對512求余為448。即數(shù)據(jù)擴(kuò)展至
K*512+448(bit),即K*64+56(byte),K為自然數(shù)。具體補(bǔ)位操作:先補(bǔ)一個(gè)1,后面補(bǔ)0至滿足上述要求。最少要補(bǔ)1bit,最多補(bǔ)512bit。
2、補(bǔ)長度
在K*64+56(byte)的基礎(chǔ)上補(bǔ)上8byte,這8byte是用來保存原始信息的長度。
3、初始化MD緩沖器
用一個(gè)四個(gè)32位的緩沖器(A,B,C,D)進(jìn)行MD5值的計(jì)算,初始化使用的是十六進(jìn)制,注意低字節(jié)在前:
word A: 01 23 45 67
word B: 89 ab cd ef
word C: fe dc ba 98
word D: 76 54 32 10
由于內(nèi)存存儲(chǔ)方向和平時(shí)書寫是相反的,所以定義的時(shí)候應(yīng)該是:
#define A 0x67452301UL
#define B 0xEFCDAB89UL
#define C 0x98BADCFEUL
#define D 0x10325476UL
4、輔助函數(shù)與加密函數(shù)
首先定義4個(gè)輔助函數(shù):
#define F( X, Y, Z ) ( ( (X) & (Y) ) | ( (~(X)) & (Z) ) )
#define G( X, Y, Z ) ( ( (X) & (Z) ) | ( (Y) & (~(Z)) ) )
#define H( X, Y, Z ) ( (X) ^ (Y) ^ (Z) )
#define I( X, Y, Z ) ( (Y) ^ ( (X) | (~(Z)) ) )
然后定義4個(gè)加密函數(shù):
#define ROTATE_LEFT(x, n) (((x) << (n)) | ((x) >> (32-(n))))
#define FF(a, b, c, d, x, s, ac) {
(a) += F ((b), (c), (d)) + (x) + ac;
(a) = ROTATE_LEFT ((a), (s));
(a) += (b);
}
#define GG(a, b, c, d, x, s, ac) {
(a) += G ((b), (c), (d)) + (x) + ac;
(a) = ROTATE_LEFT ((a), (s));
(a) += (b);
}
#define HH(a, b, c, d, x, s, ac) {
(a) += H ((b), (c), (d)) + (x) + ac;
(a) = ROTATE_LEFT ((a), (s));
(a) += (b);
}
#define II(a, b, c, d, x, s, ac) {
(a) += I ((b), (c), (d)) + (x) + ac;
(a) = ROTATE_LEFT ((a), (s));
(a) += (b);
}
具體C++實(shí)現(xiàn)算法下載