密碼學(xué)之Blowfish與Twofish
前言
Blowfish和 Twofish 都屬于block cipher的一種,發(fā)明這兩個(gè)算法的都是大神Bruce Schneier。Blowfish因?yàn)閗ey太短,不再被推薦使用。

一、Blowfish
Blowfish是一個(gè)64-bit block length, 16-round Feistel Network.
我們從master key 中提取18個(gè)subkey
以及根據(jù)master key生成個(gè)S-Box(Substitution Box):
然后流程如下:

其中的f函數(shù)如下:

Key schedule太復(fù)雜難以理解所以略過(guò)。
原文如下供參考:
1. Initialize first the P-array and then the four S-boxes, in order, with a fixed string. This string consists of the hexadecimal digits of pi (less the initial 3).
2. XOR P1 with the first 32 bits of the key, XOR P2 with the second 32-bits of the key, and so on for all bits of the key. Repeatedly cycle through the key bits
3. Encrypt the all-zero string with the Blowfish algorithm, using the subkeys described in steps (1) and (2).
4. Replace P1 and P2 with the output of step (3).
5. Encrypt the output of step (3) using the Blowfish algorithm with the modified subkeys.
6. Replace P3 and P4 with the output of step (5).
7. Continue the process, replacing all entries of the P-array, and then all four S-boxes in order, with the output of the continuously-changing Blowfish algorithm.

二、Twofish
Twofish是一個(gè)128-bit block length, 16-round Feistel Network. 使用key的長(zhǎng)度為128~256 bits.

其中,A,B,C,D都是32-bit的序列。
函數(shù)F如下:

其中函數(shù)g的計(jì)算過(guò)程如下:
首先將輸入的32-bit序列拆分成4個(gè)8-bit的序列. 每一個(gè)序列都通過(guò)一個(gè)S-Box,
. 接下來(lái)用一個(gè)4*4的MDS(Maximum Distance Separable)矩陣 over
,計(jì)算
,最后串聯(lián)z中四個(gè)元素
.
這里的MDS矩陣作者已經(jīng)給出:
01 EF 5B 5B
5B EF EF 01
EF 5B 01 EF
EF 01 EF 5B

三、Sub-key和S-Box的生成
twofish中一共用到40個(gè)sub-key,每一個(gè)都是32 bits.
首先將master key拆分為多個(gè)32-bit的子序列,這些子序列的數(shù)量由master key的長(zhǎng)度決定(128-bit的話就是4個(gè),256-bit的話就是8個(gè))。如果master key的長(zhǎng)度不夠則用padding補(bǔ)足。
然后將下標(biāo)分別為奇數(shù)和偶數(shù)的子序列分到2個(gè)不同的組中,這兩個(gè)組用來(lái)計(jì)算subkey。
然后將master key拆分為多個(gè)8-bit的子序列,然后每8個(gè)序列為一組,組成一個(gè)向量,然后讓一個(gè)
的RS矩陣和剛才的那個(gè)向量做矩陣的乘法運(yùn)算。
RS矩陣作者已經(jīng)給出:
01 A4 55 87 5A 58 DB 9E
A4 56 82 F3 1E C6 68 E5
02 A1 FC C1 47 AE 3D 19
A4 55 87 5A 58 DB 9E 03
上述計(jì)算得到的所有結(jié)果將歸到同一個(gè)組
里面,
將參與到S-BOX的運(yùn)算中:
,X為32-bit的輸入值。
Subkey的計(jì)算方式如下:
h函數(shù)太過(guò)于復(fù)雜,這里就列原圖了:

其中,分別為2個(gè)permutation運(yùn)算。
最后放上一段用Twofish加密的密文,代碼可參見(jiàn)——https://www.medo64.com/2016/01/twofish-in-csharp/
原文:Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.?
Key:199 247 109 46 240 141 51 38 36 125 108 51 213 170 204 36?
Op Mode:CBC?
密文:217 235 175 81 36 252 44 160 41 34 38 109 199 3 184 147 69 118 178 172 179 217 97 161 82 132 101 214 37 23 201 159 93 25 21 46 211 165 227 185 123 136 237 154 176 127 160 117 138 187 236 178 239 177 141 10 2 151 94 141 223 154 54 65 229 85 255 217 248 240 168 251 71 151 115 200 77 49 66 178 164 224 103 163 75 230 125 83 71 96 178 60 100 135 69 254 213 0 222 105 91 89 148 203 74 85 120 138 224 61 73 198 207 68 36 122 216 252 175 120 7 198 179 118 157 199 131 65 10 12 242 181 188 13 14 135 251 22 176 89 130 83 62 192 238 75 145 217 54 97 247 134 70 61 7 7 123 99 205 37 38 143 74 51 98 156 181 164 42 176 86 176 99 253 254 52 207 103 34 157 174 242 225 16 245 98 10 200 24 90 28 114 166 10 200 83 81 220 72 3 88 77 83 96 1 154 135 226 129 86 16 30 47 167 165 236 109 214 185 21 82 121 157 89 187 95 121 138 194 211 237 13 88 243 9 253 92 216 23 59 100 94 69 123 240 85 252 7 11 153 51 186 70 186 105 96
這里的每個(gè)數(shù)字都是十進(jìn)制下的數(shù)字,每個(gè)數(shù)字代表一個(gè)byte(范圍從0~255),例如199即11000111b
有關(guān)Twofish的分析實(shí)在是太多了(而且大多都非常專業(yè))讀不過(guò)來(lái)。
反正,這是一個(gè)安全的加密方案。

參考資料
Bruce Sctmeier - Description of a New Variable-Length Key, 64-Bit Block Cipher
Bruce Schneier, John Kelseyy, Doug Whitingz, David Wagnerx, Chris Hall - Two sh: A 128-Bit Block Cipher
Twofish in C# - https://www.medo64.com/2016/01/twofish-in-csharp/

THE END.