1.术语解释:SHA1算法需要用到一系列的位运算,以下介绍位运算的符号表示:XOR 异或 A XOR BOR 或 A OR BAND 与 A AND BNOT 非 NOT A<< 左移 A>>n(n为常数,下同)>> 右移 A<
2.数据前期处理:当我们得到一个消息信息,需要对其进行一系列的处理,主要有补位、补长度及分块。 1)补位:令我们得到的消息为字符串'bob',我们先以字符为单位将其转换为十六进制Ascii码的排列。b--62,o--6f,b--62。即现在的消息信息为626f62。再将其转换为二进制排列,可得: 。可见,这是一个长度为24位的数据。现在进行补位操作,首先在我们的数据后加上一个1。得到: 1。目前的长度L=25,计算长度L对512的取余运算,及X=L%512,若X不等于448,就在数据末尾加上一个0,一直循环到X=448为止。此时数据的长度应为512的n倍加上448,即L'=512*n+448。补位结束。 2)补长度与分块:现在我们得到一个长度L为512*n+448位的二进制字符串,我们在这个二进制字符串的末尾添加上一个长度为64位的二进制字符串,用来表示原消息数据的长度,如上文中的'bob'长度为24位,其二进制表示: 如此,我们最终得到一个长度L''=512*n(即长度为512的倍数)的二进制字符串。最后,我们判断这个二进制字符串的长度是否大于512位(即n是否为1)。若大于512位,我们则需要将其分割为长度为512位的多个字符串,这里用M[i](M[0],M[1]……)表示。若不大于,则直接用M0保存。到此,补长度与分块结束。
3.算法需要的各常量的值及函数表达式: 1)常量: Kt = 0x5A827999 (0 <= t <= 19) Kt = 0x6ED9EBA1 (20 <= t <= 39) Kt = 0x8F1BBCDC (40 <= t <= 59) Kt = 0xCA62C1D6 (60 <= t <= 79) 2)函数表达式: ft(B,C,D) = (B AND C) OR ((NOT B) AND D) ( 0 <= t <= 19) ft(B,C,D) = B XOR C XOR D (20 <= t <= 39) ft(B,C,D) = (B AND C) OR (B AND D) OR (C AND D) (40 <= t <= 59) ft(B,C,D) = B XOR C XOR D (60 <= t <= 79).
4.算法: 1)缓冲区: 处理上述的二进制字符串需要一些缓冲区,下面我们详细列出各缓冲区的规格: a.32位的缓冲区5个:A,B,C,D,E b.32位的缓冲区80个:W[0]~W[79] c.32位的缓冲区5个:H[0]~H[4] d.32位的缓冲区1个:TEMP 首先我们将缓冲区H[]进行初始化赋值: H[0]=0x67452301 H[1]=0xEFCDAB89 H[2]=0x98BADCFE H[3]=0x10325476 H[4]=0xC3D2E1F0 2)针对每个M[i]进行循环: a.将M[i]从左到右分割为16个32位的字符串,转换为uint型的数值分别存储在缓冲区W[0]~W[15]中。 b.对于W[16]~W[79],我们进行如下循环: W[i] = S1(W[i-3] XOR W[i-8] XOR W[i- 14] XOR W[i-16]) 至此,我们的W[]缓冲区已经全部赋值完毕。 c.对缓冲区A,B,C,D,E分别进行赋值: A=H[0] B=H[1] C=H[2] D=H[3] E=H[4] d.对于W[0]~W[79],我们再进行如下循环: TEMP = S5(A) + ft(B,C,D) + E + W[i] + K[i] E=D D=C C=S30(B) B=A A=TEMP e.我们再对缓冲区H[]进行操作: H[0]=H[0]+A H[1]=H[1]+B H[2]=H[2]+C H[3]=H[3]+D H[4]=H[4]+E 3)如此完成每一个M[i]的循环后,最终得到的消息摘要为: H[0] H[1] H[2] H[3] H[4] 此处缓冲区H[]中的数值全部转换为16进制数用字符串形式表示,以上述格式排列即为我们最终计算出的消息摘要。