Skip to content

Commit

Permalink
add sm3
Browse files Browse the repository at this point in the history
  • Loading branch information
kaisawind committed Oct 8, 2021
1 parent 15acefa commit b987104
Showing 1 changed file with 108 additions and 0 deletions.
108 changes: 108 additions & 0 deletions source/_posts/2021-10-05-sm3.md
@@ -0,0 +1,108 @@
---
layout: post
title: "SM3密码杂凑算法"
date: 2021-10-05 23:59:12
categories: [算法]
excerpt_separator: <!--more-->
---
SM3密码杂凑算法
<!--more-->

## 1. 填充

假设消息m 的长度为l 比特。首先将比特“1”添加到消息的末尾,再添加k 个“0”,k是满足l + 1 + k ≡ 448mod512 的最小的非负整数。然后再添加一个64位比特串,该比特串是长度l的二进制表示。

其中将bit转byte有$448bit = 56byte$,$512bit = 64byte$。
$l + 1 + k \equiv 448 mod 512$ 等于 $l + 1 + k \equiv 56 mod 64$
若$a \equiv b \mod p$,则对于任意的c,都有$(a + c) \equiv (b + c) \mod p$。
$$k \equiv (56 - 1 - l) \mod 64 \qquad 0 \le k \le 63$$

```go
// 填充go语言实现
// 1 byte end marker :: 0-63 padding bytes :: 8 byte length
tmp := [1 + 63 + 8]byte{0x80}
pad := (55 - len) % 64 // calculate number of padding bytes
binary.BigEndian.PutUint64(tmp[1+pad:], len<<3) // append length in bits
Write(tmp[:1+pad+8])
```

## 2. 迭代过程

将填充后的消息m′按512比特进行分组:m′ = B(0)B (1)· · · B(n−1)。

```go
for i := 0; i <= len(p)-BlockSize; i += BlockSize {
// eliminate bounds checks on p
q := p[i:]
q = q[:BlockSize:BlockSize]
}
```

## 3. 消息扩展

* a) 将消息分组B(i)划分为16个字W0, W1, · · ·, W15。
```go
for j := 0; j < 16; j++ {
w0[j] = binary.BigEndian.Uint32(q[4*j : 4*(j+1)])
}
```

* b)
$
FOR \quad j=16 \quad TO \quad 67 \\
\qquad W_j ← P1(W_{j−16} ⊕ W_{j−9} ⊕ (W_{j−3} ≪ 15)) ⊕ (W_{j−13} ≪ 7) ⊕ W_{j−6} \\
ENDFOR
$
```go
for j := 16; j < 68; j++ {
w0[j] = P1(w0[j-16]^w0[j-9]^bits.RotateLeft32(w0[j-3], 15)) ^ bits.RotateLeft32(w0[j-13], 7) ^ w0[j-6]
}
```

* c)
$
FOR \quad j=0 \quad TO \quad 63 \\
\qquad W'_j = W_j ⊕ W_{j+4} \\
ENDFOR
$

```go
for j := 0; j < 64; j++ {
w1[j] = w0[j] ^ w0[j+4]
}
```

## 4. 压缩函数

```go
A, B, C, D, E, F, G, H := a, b, c, d, e, f, g, h
for j := 0; j < 16; j++ {
SS1 := bits.RotateLeft32(bits.RotateLeft32(A, 12)+E+bits.RotateLeft32(0x79cc4519, j), 7)
SS2 := SS1 ^ bits.RotateLeft32(A, 12)
TT1 := FF0(A, B, C) + D + SS2 + w1[j]
TT2 := GG0(E, F, G) + H + SS1 + w0[j]
D = C
C = bits.RotateLeft32(B, 9)
B = A
A = TT1
H = G
G = bits.RotateLeft32(F, 19)
F = E
E = P0(TT2)
}
for j := 16; j < 64; j++ {
SS1 := bits.RotateLeft32(bits.RotateLeft32(A, 12)+E+bits.RotateLeft32(0x7a879d8a, j), 7)
SS2 := SS1 ^ bits.RotateLeft32(A, 12)
TT1 := FF1(A, B, C) + D + SS2 + w1[j]
TT2 := GG1(E, F, G) + H + SS1 + w0[j]
D = C
C = bits.RotateLeft32(B, 9)
B = A
A = TT1
H = G
G = bits.RotateLeft32(F, 19)
F = E
E = P0(TT2)
}
a, b, c, d, e, f, g, h = a^A, b^B, c^C, d^D, e^E, f^F, g^G, h^H
```

0 comments on commit b987104

Please sign in to comment.