SHA-256算法流程

SHA-256

输入消息:M

输出消息:256位(bit)hash值

步骤:

  1. 消息填充:M的长度 mod 512 = R,考虑R(R为输入消息长度按512bit进行分组后,最后一组的长度)

    • R < 448,在最后一组的末尾填充1个“1”及若干个“0”,使最后一组位数达到448;再在这448位的基础上填充64位,这64位是M的原始长度的二进制表示。
      1   0000... ⏟ 448 − R   输 入 消 息 的 长 度 的 二 进 制 ⏟ 64 b i t \underbrace{1\ 0000...}_{448-R}\ \underbrace{输入消息的长度的二进制}_{64bit} 448R 1 0000... 64bit

    • R >= 448,在最后一组的末尾填充1个“1”及若干个“0”,使最后一组位数达到512;再新增一组,添加448个“0”和64位消息M的原始长度的二进制表示。
      1   00... ⏟ 512 − R 000... ⏟ 448 b i t 输 入 消 息 的 长 度 的 二 进 制 ⏟ 64 b i t ⏟ 512 b i t \underbrace{1\ 00...}_{512-R} \quad \underbrace{\underbrace{000...}_{448bit}\underbrace{输入消息的长度的二进制}_{64bit}}_{512bit} 512R 1 00...512bit 448bit 000...64bit

  2. 系统给出8个32位寄存器:A,B,C,D,E,F,G,H,其初始值分别取自8个素数(2,3,5,7,11,13,17,19)的平方根的小数部分其二进制表示的前32位。例如: 2 = 1.4142135623... \sqrt{2}=1.4142135623... 2 =1.4142135623... 小数部分转为二进制 为 0.0110   1010   0000   1001   1110   0110   0101   1101... 0.0110 \ 1010 \ 0000 \ 1001 \ 1110 \ 0110 \ 0101 \ 1101... 0.0110 1010 0000 1001 1110 0110 0101 1101...即为 A = 0 x 6 a 09 e 667 A = 0x6a09e667 A=0x6a09e667;相应地,B,C,D,E,F,G,H的初始化用了同样的取值方法。最终,我们得到:
    A = 0 x 6 a 09 e 667 B = 0 x b b 67 a e 85 C = 0 x 3 c 6 e f 372 D = 0 x a 54 f f 53 a E = 0 x 510 e 527 f F = 0 x 9 b 05688 c G = 0 x 1 f 83 d 9 a b H = 0 x 5 b e 0 c d 19 A=0x6a09e667 \\ B=0xbb67ae85 \\ C=0x3c6ef372 \\ D=0xa54ff53a \\ E=0x510e527f \\ F=0x9b05688c \\ G=0x1f83d9ab \\ H=0x5be0cd19 \\ A=0x6a09e667B=0xbb67ae85C=0x3c6ef372D=0xa54ff53aE=0x510e527fF=0x9b05688cG=0x1f83d9abH=0x5be0cd19

  3. 首先,第一组以512位进行地分组进来后,再以32位为一组,分别保存为 W 0 , … , W 15 W_0,…,W_{15} W0W15

  4. 执行下列循环64次:

  • temp = A

  • A = ( T 1 + T 2 )   m o d   2 32 (T_1 + T_2) \ mod \ 2^{32} (T1+T2) mod 232

  • H = G

  • G = F

  • E = ( D + T 1 )   m o d   2 32 (D + T_1) \ mod \ 2^{32} (D+T1) mod 232

  • D = C

  • C = B

  • B = temp

    其中 T 1 、 T 2 T_1、T_2 T1T2操作定义为:
    T 1 = ( e 1 ( E ) + f 1 ( E , F , G ) + H + W t + K t )   m o d   2 32 T 2 = ( ( e 2 ( A ) + f 2 ( A , B , C ) )   m o d   2 32 e 1 ( E ) = ( E ≫ 6 ) ⊕ ( E ≫ 11 ) ⊕ ( E ≫ 25 ) e 2 ( A ) = ( A ≫ 2 ) ⊕ ( A ≫ 13 ) ⊕ ( A ≫ 22 ) f 1 ( E , F , G ) = ( E ∧ F ) ⊕ ( E ˉ ∧ G ) f 2 ( A , B , C ) = ( A ∧ B ) ⊕ ( A ∧ C ) ⊕ ( B ∧ C ) W t = W t − 16 + [ ( W t − 15 ≫ 7 ) ⊕ ( W t − 15 ≫ 18 ) ⊕ ( W t − 15 → 3 ) ] + W t − 7            + [ ( W t − 2 ≫ 17 ) ⊕ ( W t − 2 ≫ 19 ) ⊕ ( W t − 2 → 10 ) ] K t 的 生 成 方 法 为 取 前 64 个 素 数 ( 2 , 3 , 5 , 7 , … … ) 立 方 根 的 小 数 部 分 , 将 其 转 换 为 二 进 制 , 然 后 取 这 64 个 数 的 前 32 位 。 ( 即 : 我 们 可 以 把 K t 当 成 64 个 常 数 ) \begin{aligned} &T_1=(e_1 (E)+f_1 (E,F,G)+H+W_t+ K_t) \ mod \ 2^{32} \\ &T_2=((e_2 (A)+f_2 (A,B,C)) \ mod \ 2^{32} \\ \\ &e_1(E) = (E \gg 6) \oplus (E \gg 11) \oplus (E \gg 25) \\ &e_2(A) = (A \gg 2) \oplus (A \gg 13) \oplus (A \gg 22) \\ \\ &f_1(E,F,G) = (E \land F) \oplus (\bar{E} \land G) \\ &f_2(A,B,C) = (A \land B) \oplus (A \land C) \oplus (B \land C) \\ \\ &W_t = W_{t-16} + [(W_{t-15} \gg 7) \oplus (W_{t-15} \gg 18) \oplus (W_{t-15} \rarr 3)] + W_{t-7} \\ & \ \ \ \ \ \ \ \ \ \ + [(W_{t-2} \gg 17) \oplus (W_{t-2} \gg 19) \oplus (W_{t-2} \rarr 10)] \\ & K_t的生成方法为取前64个素数(2,3,5,7,……)立方根的小数部分,将其转换为二进制,\\ &然后取这64个数的前32位。(即:我们可以把K_t当成64个常数) \end{aligned} T1=(e1(E)+f1(E,F,G)+H+Wt+Kt) mod 232T2=((e2(A)+f2(A,B,C)) mod 232e1(E)=(E6)(E11)(E25)e2(A)=(A2)(A13)(A22)f1(E,F,G)=(EF)(EˉG)f2(A,B,C)=(AB)(AC)(BC)Wt=Wt16+[(Wt157)(Wt1518)(Wt153)]+Wt7          +[(Wt217)(Wt219)(Wt210)]Kt6423576432Kt64

    ≫ n \gg n n 表示循环右移 n n n 位, → n \rarr n n表示右移 n n n 位, E ˉ 表 示 E 按 位 取 补 \bar{E} 表示 E 按位取补 EˉE W 0 , … , W 15 W_0,…,W_{15} W0W15即为上述步骤3的512位的分组进来后再按32位为一组 512 ÷ 32 = 16 512 \div 32 = 16 512÷32=16 ,而 W 16 , … , W 63 W_{16},…,W_{63} W16W63根据上述公式生成。

  1. 经过步骤4,我们的A,B,C,D,E,F,G,H和第一组512位的分组一起进行一系列操作后与初始的值完全不同了。此时,消息M的第二个512位分组进入,与步骤4后生成的A,B,C,D,E,F,G,H一起,又循环执行步骤4的操作,……

  2. 当最后一组512位分组和前一组生成的A,B,C,D,E,F,G,H经过步骤4后,最终产生的A,B,C,D,E,F,G,H即为消息M的hash值。

总结

上述一系列操作我们可以发现,由于消息M的每一位都参与了运算,且后续操作的输入需要用到之前操作的输出。因此,如果消息M的某一位发生了改变,最终将导致得到的hash值与之前消息M未改变时的hash值完全不同。这也是Hash算法的性质之一。

你可能感兴趣的:(密码学)