#include "iostream" #include "string" #include "math.h" using namespace std; typedef char byte; //初始化四个数 long A=0X67452301l; long B=0XEFCDAB89l; long C=0X98BADCFEl; long D=0X10325476l; long F(long x, long y, long z){ return ((x & y) | ((~x) & z)) &0x0ffffffffl; } long G(long x, long y, long z){ return ((x & z) | (y & (~z))) &0x0ffffffffl; } long H(long x, long y, long z){ return (x ^ y ^ z) &0x0ffffffffl; } long I(long x, long y, long z){ return (y ^ (x | (~z))) &0x0ffffffffl; } long FF(long a, long b, long c, long d, long Mj, long s, long ti) { a = (a + F(b, c, d) + Mj + ti) & 0xffffffffl; a = ( a << s) | (a >> (32 - s)); a += b; return (a&0xFFFFFFFFL); } long GG(long a, long b, long c, long d, int Mj, int s, int ti){ a = (a + G(b, c, d) + Mj + ti) & 0xffffffffl; a = ( a << s) | (a >> (32 - s)); a += b; return (a&0xFFFFFFFFL); } long HH(long a, long b, long c, long d, int Mj, int s, int ti){ a = (a + H(b, c, d) + Mj + ti) & 0xffffffffl; a = ( a << s) | (a >> (32 - s)); a += b; return (a&0xFFFFFFFFL); } long II(long a, long b, long c, long d, int Mj, int s, int ti){ a = (a + I(b, c, d) + Mj + ti) & 0xffffffffl; a = ( a << s) | (a >> (32 - s)); a += b; return (a&0xFFFFFFFFL); } void Loops(int group[16]){ long a = A, b = B, c = C, d = D; //第一轮循环 a = FF(a,b,c,d,group[0],7,0xd76aa478); d = FF(d,a,b,c,group[1],12,0xe8c7b756); c = FF(c,d,a,b,group[2],17,0x242070db); b = FF(b,c,d,a,group[3],22,0xc1bdceee); a = FF(a,b,c,d,group[4],7,0xf57c0faf); d = FF(d,a,b,c,group[5],12,0x4787c62a); c = FF(c,d,a,b,group[6],17,0xa8304613); b = FF(b,c,d,a,group[7],22,0xfd469501); a = FF(a,b,c,d,group[8],7,0x698098d8); d = FF(d,a,b,c,group[9],12,0x8b44f7af); c = FF(c,d,a,b,group[10],17,0xffff5bb1); b = FF(b,c,d,a,group[11],22,0x895cd7be); a = FF(a,b,c,d,group[12],7,0x6b901122); d = FF(d,a,b,c,group[13],12,0xfd987193); c = FF(c,d,a,b,group[14],17,0xa679438e); b = FF(b,c,d,a,group[15],22,0x49b40821); //第二轮循环 a = GG(a,b,c,d,group[1], 5,0xf61e2562); d = GG(d,a,b,c,group[6], 9,0xc040b340); c = GG(c,d,a,b,group[11],14,0x265e5a51); b = GG(b,c,d,a,group[0], 20,0xe9b6c7aa); a = GG(a,b,c,d,group[5], 5,0xd62f105d); d = GG(d,a,b,c,group[10],9,0x02441453); c = GG(c,d,a,b,group[15],14,0xd8a1e681); b = GG(b,c,d,a,group[4], 20,0xe7d3fbc8); a = GG(a,b,c,d,group[9], 5,0x21e1cde6); d = GG(d,a,b,c,group[14],9,0xc33707d6); c = GG(c,d,a,b,group[3], 14,0xf4d50d87); b = GG(b,c,d,a,group[8], 20,0x455a14ed); a = GG(a,b,c,d,group[13],5,0xa9e3e905); d = GG(d,a,b,c,group[2], 9,0xfcefa3f8); c = GG(c,d,a,b,group[7], 14,0x676f02d9); b = GG(b,c,d,a,group[12],20,0x8d2a4c8a); //第三轮循环 a = HH(a,b,c,d,group[5],4,0xfffa3942); d = HH(d,a,b,c,group[8],11,0x8771f681); c = HH(c,d,a,b,group[11],16,0x6d9d6122); b = HH(b,c,d,a,group[14],23,0xfde5380c); a = HH(a,b,c,d,group[1],4,0xa4beea44); d = HH(d,a,b,c,group[4],11,0x4bdecfa9); c = HH(c,d,a,b,group[7],16,0xf6bb4b60); b = HH(b,c,d,a,group[10],23,0xbebfbc70); a = HH(a,b,c,d,group[13],4,0x289b7ec6); d = HH(d,a,b,c,group[0],11,0xeaa127fa); c = HH(c,d,a,b,group[3],16,0xd4ef3085); b = HH(b,c,d,a,group[6],23,0x04881d05); a = HH(a,b,c,d,group[9],4,0xd9d4d039); d = HH(d,a,b,c,group[12],11,0xe6db99e5); c = HH(c,d,a,b,group[15],16,0x1fa27cf8); b = HH(b,c,d,a,group[2],23,0xc4ac5665); //第四轮循环 a = II(a,b,c,d,group[0],6,0xf4292244); d = II(d,a,b,c,group[7],10,0x432aff97); c = II(c,d,a,b,group[14],15,0xab9423a7); b = II(b,c,d,a,group[5],21,0xfc93a039); a = II(a,b,c,d,group[12],6,0x655b59c3); d = II(d,a,b,c,group[3],10,0x8f0ccc92); c = II(c,d,a,b,group[10],15,0xffeff47d); b = II(b,c,d,a,group[1],21,0x85845dd1); a = II(a,b,c,d,group[8],6,0x6fa87e4f); d = II(d,a,b,c,group[15],10,0xfe2ce6e0); c = II(c,d,a,b,group[6],15,0xa3014314); b = II(b,c,d,a,group[13],21,0x4e0811a1); a = II(a,b,c,d,group[4],6,0xf7537e82); d = II(d,a,b,c,group[11],10,0xbd3af235); c = II(c,d,a,b,group[2],15,0x2ad7d2bb); b = II(b,c,d,a,group[9],21,0xeb86d391); //把运算后结果写回去 A += a , B += b, C += c, D += d; A &= 0xffffffff; B &= 0xffffffff; C &= 0xffffffff; D &= 0xffffffff; } //根据循环后ABCD的值得到MD5码 string getMdCode(){ string codes[16]={"0","1","2","3","4","5","6","7","8","9","A","B","C","D","E","F"}; string code = ""; long a = A, b = B, c = C, d = D; for (int i = 0; i < 4; i++){ int tmp = a & 0x0f; string first = codes[tmp]; a >>= 4; tmp = a & 0x0f; string second = codes[tmp]; code += (second + first); a >>= 4; } for (int i = 0; i < 4; i++){ int tmp = b & 0x0f; string first = codes[tmp]; b >>= 4; tmp = b & 0x0f; string second = codes[tmp]; code += (second + first); b >>= 4; } for (int i = 0; i < 4; i++){ int tmp = c & 0x0f; string first = codes[tmp]; c >>= 4; tmp = a & 0x0f; string second = codes[tmp]; code += (second + first); c >>= 4; } for (int i = 0; i < 4; i++){ int tmp = d & 0x0f; string first = codes[tmp]; d >>= 4; tmp = d & 0x0f; string second = codes[tmp]; code += (second + first); d >>= 4; } A=0X67452301l; B=0XEFCDAB89l; C=0X98BADCFEl; D=0X10325476l; return code; } int bitToUnsign(int b){ return b < 0 ? b & 0x7f + 128:b; } //将64个字节划分成16组,每小组4个字节 int* divideGroup(byte *bytes, int n){ int *group = new int[16]; for (int i = 0; i < 16; i++){ int a1 = bitToUnsign((int)bytes[n+4*i]); int a2 = (bitToUnsign((int)bytes[n+4*i+1]) << 8); int a3 = (bitToUnsign((int)bytes[n+4*i+2]) << 16); int a4 = (bitToUnsign((int)bytes[n+4*i+3]) << 24); group[i] = a1 | a2 | a3 | a4; } return group; } //根据输入信息来返回该信息对应的MD5码 string md5(string s){ long length = s.length(); byte *ch = new byte[length + 1]; for (int i = 0; i < length; i++){ //将string转化为byte的数组 ch[i] = (byte)s[i]; } long groupLength = length / 64; for (int i = 0; i < groupLength; i++){ Loops(divideGroup(ch,i * 64)); //先分组,然后再进行循环处理 } int remain = length % 64; //剩余的字节 byte rest[128]; long bitLength = length << 3; //信息总共有多少位 if (remain <=56){ for (int i = 0; i < remain; i++){ rest[i] = ch[length - remain + i]; } if (remain < 56){ rest[remain] = (byte)(-128);//补1 for (int i = 1; i < 56 - remain; i++){ //补0,直到为56个字节(448位) rest[remain + i] = 0; } } for (int i = 56; i < 64; i++){ //补长度 rest[i] = (byte)(bitLength & 0xff); bitLength = bitLength >> 8; } Loops(divideGroup(rest, 0)); } else { //多于56个字节,则先补到120字节,再用剩余的八个字节来储存长度 rest[remain] = (-128); //补1 for (int i = remain + 1; i < 120; i++) { //补0 rest[i] = 0; } for (int i = 120; i < 128; i++){ //补长度 rest[i] = (byte)(bitLength & 0xff); bitLength >>= 8; } Loops(divideGroup(rest, 0)); Loops(divideGroup(rest, 64)); } //根据运算后的ABCD返回其MD5码 return getMdCode(); } int main(int argc, char * argcs[]){ string s = ""; cout << md5(s) << endl; s = "a"; cout << md5(s) << endl; s = "abc"; cout << md5(s) << endl; return 0; }