md5入门

md5入门

什么是md5

md5算法

1.填充
填充输入信息至N*512+448(即填充后的位数模512得448)
填充内容为一个1和若干个0,即第一个为1其他都是0
填充完毕后,添加一个64位的字段,字段表示的是原字段长度(单位是位,bit),如果原字段长度超过64位(即输入信息长度超过4EB,1EB=1024PB,但是就现在来说这是几乎不可能的),就取低64位。 
这样就使得信息长度为N*512+448+64=(N+1)*512。

2.初始化变量
四个幻数:
A=0x01234567,
B=0x89ABCDEF,
C=0xFEDCBA98,
D=0x76543210。

3.运算
1.每一分组的算法流程如下:
(1)第一分组需要将上面四个链接变量复制到另外四个变量中:A到a,B到b,C到c,D到d。
(2)从第二分组开始的变量为上一分组的运算结果,即A = a, B = b, C = c, D = d。
2.循环的次数是分组的个数(N+1)
3.将每一512字节细分成16个小组,每个小组64位(8个字节)
4.定义一些运算:
&是与,|是或,~是非,^是异或,<<是循环移位

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))
FF(a,b,c,d,Mj,s,ti)表示a=b+((a+F(b,c,d)+Mj+ti)<<s)  
GG(a,b,c,d,Mj,s,ti)表示a=b+((a+G(b,c,d)+Mj+ti)<<s)  
HH(a,b,c,d,Mj,s,ti)表示a=b+((a+H(b,c,d)+Mj+ti)<<s)  
II(a,b,c,d,Mj,s,ti)表示a=b+((a+I(b,c,d)+Mj+ti)<<s)  

5.四轮运算分别是:

第一轮  
 a=FF(a,b,c,d,M0,7,0xd76aa478)  
 b=FF(d,a,b,c,M1,12,0xe8c7b756)  
 c=FF(c,d,a,b,M2,17,0x242070db)  
 d=FF(b,c,d,a,M3,22,0xc1bdceee)  
 a=FF(a,b,c,d,M4,7,0xf57c0faf)  
 b=FF(d,a,b,c,M5,12,0x4787c62a)  
 c=FF(c,d,a,b,M6,17,0xa8304613)  
 d=FF(b,c,d,a,M7,22,0xfd469501)  
 a=FF(a,b,c,d,M8,7,0x698098d8)  
 b=FF(d,a,b,c,M9,12,0x8b44f7af)  
 c=FF(c,d,a,b,M10,17,0xffff5bb1)  
 d=FF(b,c,d,a,M11,22,0x895cd7be)  
 a=FF(a,b,c,d,M12,7,0x6b901122)  
 b=FF(d,a,b,c,M13,12,0xfd987193)  
 c=FF(c,d,a,b,M14,17,0xa679438e)  
 d=FF(b,c,d,a,M15,22,0x49b40821)  

 第二轮  
 a=GG(a,b,c,d,M1,5,0xf61e2562)  
 b=GG(d,a,b,c,M6,9,0xc040b340)  
 c=GG(c,d,a,b,M11,14,0x265e5a51)  
 d=GG(b,c,d,a,M0,20,0xe9b6c7aa)  
 a=GG(a,b,c,d,M5,5,0xd62f105d)  
 b=GG(d,a,b,c,M10,9,0x02441453)  
 c=GG(c,d,a,b,M15,14,0xd8a1e681)  
 d=GG(b,c,d,a,M4,20,0xe7d3fbc8)  
 a=GG(a,b,c,d,M9,5,0x21e1cde6)  
 b=GG(d,a,b,c,M14,9,0xc33707d6)  
 c=GG(c,d,a,b,M3,14,0xf4d50d87)  
 d=GG(b,c,d,a,M8,20,0x455a14ed)  
 a=GG(a,b,c,d,M13,5,0xa9e3e905)  
 b=GG(d,a,b,c,M2,9,0xfcefa3f8)  
 c=GG(c,d,a,b,M7,14,0x676f02d9)  
 d=GG(b,c,d,a,M12,20,0x8d2a4c8a)  

 第三轮  
 a=HH(a,b,c,d,M5,4,0xfffa3942)  
 b=HH(d,a,b,c,M8,11,0x8771f681)  
 c=HH(c,d,a,b,M11,16,0x6d9d6122)  
 d=HH(b,c,d,a,M14,23,0xfde5380c)  
 a=HH(a,b,c,d,M1,4,0xa4beea44)  
 b=HH(d,a,b,c,M4,11,0x4bdecfa9)  
 c=HH(c,d,a,b,M7,16,0xf6bb4b60)  
 d=HH(b,c,d,a,M10,23,0xbebfbc70)  
 a=HH(a,b,c,d,M13,4,0x289b7ec6)  
 b=HH(d,a,b,c,M0,11,0xeaa127fa)  
 c=HH(c,d,a,b,M3,16,0xd4ef3085)  
 d=HH(b,c,d,a,M6,23,0x04881d05)  
 a=HH(a,b,c,d,M9,4,0xd9d4d039)  
 b=HH(d,a,b,c,M12,11,0xe6db99e5)  
 c=HH(c,d,a,b,M15,16,0x1fa27cf8)  
 d=HH(b,c,d,a,M2,23,0xc4ac5665)  

 第四轮  
 a=II(a,b,c,d,M0,6,0xf4292244)  
 b=II(d,a,b,c,M7,10,0x432aff97)  
 c=II(c,d,a,b,M14,15,0xab9423a7)  
 d=II(b,c,d,a,M5,21,0xfc93a039)  
 a=II(a,b,c,d,M12,6,0x655b59c3)  
 b=II(d,a,b,c,M3,10,0x8f0ccc92)  
 c=II(c,d,a,b,M10,15,0xffeff47d)  
 d=II(b,c,d,a,M1,21,0x85845dd1)  
 a=II(a,b,c,d,M8,6,0x6fa87e4f)  
 b=II(d,a,b,c,M15,10,0xfe2ce6e0)  
 c=II(c,d,a,b,M6,15,0xa3014314)  
 d=II(b,c,d,a,M13,21,0x4e0811a1)  
 a=II(a,b,c,d,M4,6,0xf7537e82)  
 b=II(d,a,b,c,M11,10,0xbd3af235)  
 c=II(c,d,a,b,M2,15,0x2ad7d2bb)  
 d=II(b,c,d,a,M9,21,0xeb86d391) 

6.每轮循环后,将A,B,C,D分别加上a,b,c,d,然后进入下一循环。

 

 

 工作,日常对接API,大多数接口都要求有签名字段,安全需要吧,绝大多数签名要用到MD5,今天就被一个demo坑了,其实是自己不够了解MD5,对方用的java,我用的PHP。

    一半签名是拼拼参数,有直接拼的,有的还要加上&=这鬼符号,我平时用php,想偷懒用个http_build_query生成临时字符串A,这方法处理会将字符串A进行url加密,后面再用到拼好的字符串A进行md5时,得到的签名也就不能用了,所以还是循环着拼一拼吧,还要记得把后面的&去掉。。。

    这还没到我今天的坑,我看了对方的签名描述,有点懵逼。这样的:

    其他的都好说,这个转16进制什么鬼,我之前从没见过,问下度娘,发现java大神们都是这样写的,但是我不知道为什么要这样干,搜到的全是如何转换成16进制,这一点比较郁闷。等熟悉java的朋友指导一下吧,嘿嘿。

    那就从MD5定义看吧,可以问度娘,太长了,我就记得个生成128位的信息摘要,java有封装好的信息摘要类,具体用法我就不说了,没用过,过程是这样的:

把生成的信息摘要存在bytes数组,byte类型长度8位,每个byte可以生成两个16进制字符(高位都是0的要在生成的字符前补0,还要注意整数是32位长度,每个byte跟0xff按位与),这样就有16个byte了,然后把这些byte转成16进制的,这样就得到32个16进制字符,这是大家常见的MD5,还有16位长度的MD5字符,是吧32位的前8位,后8位去掉了:

    那就照着java的思路来吧,我把字符串md5之后,又拆成一个个字符,转成16进制,在拼成字符串,进行签名的最后一步,base64编码。调用了下对方的接口,喜闻乐见的签名错误,我还问对方怎么回事,他看了我的签名,说你这base64编码后的字符长度就不对(我后来才知道base64编码的长度有规律的,⌈n/3⌉*4,⌈⌉是向上取整,n是原字符长度,用java的基本功还是好啊)

    后来知道了php的md5方法,就是把字符串转成32位16进制字符串了,真是尴尬。

$tmp = md5($str);

    我之前是把32位字符再转成16进制(生成64位的字符),再base64,最后字符长度是88位。正确长度的是44(32位md5字符串base64一下)。

    记录一下,看来自己每天用的,其实有很多都不理解,都只是会用而已。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值