~ubuntu-branches/debian/sid/botan/sid

« back to all changes in this revision

Viewing changes to src/twofish.cpp

  • Committer: Package Import Robot
  • Author(s): Laszlo Boszormenyi (GCS)
  • Date: 2018-03-01 22:23:25 UTC
  • mfrom: (1.2.2)
  • Revision ID: package-import@ubuntu.com-20180301222325-7p7vc45gu3hta34d
Tags: 2.4.0-2
* Don't remove .doctrees from the manual if it doesn't exist.
* Don't specify parallel to debhelper.

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
/*************************************************
2
 
* Twofish Source File                            *
3
 
* (C) 1999-2007 The Botan Project                *
4
 
*************************************************/
5
 
 
6
 
#include <botan/twofish.h>
7
 
#include <botan/bit_ops.h>
8
 
 
9
 
namespace Botan {
10
 
 
11
 
/*************************************************
12
 
* Twofish Encryption                             *
13
 
*************************************************/
14
 
void Twofish::enc(const byte in[], byte out[]) const
15
 
   {
16
 
   u32bit A = make_u32bit(in[ 3], in[ 2], in[ 1], in[ 0]),
17
 
          B = make_u32bit(in[ 7], in[ 6], in[ 5], in[ 4]),
18
 
          C = make_u32bit(in[11], in[10], in[ 9], in[ 8]),
19
 
          D = make_u32bit(in[15], in[14], in[13], in[12]);
20
 
 
21
 
   A ^= round_key[0]; B ^= round_key[1]; C ^= round_key[2]; D ^= round_key[3];
22
 
 
23
 
   for(u32bit j = 0; j != 16; j += 2)
24
 
      {
25
 
      u32bit X, Y;
26
 
 
27
 
      X = SBox0[get_byte(3, A)] ^ SBox1[get_byte(2, A)] ^
28
 
          SBox2[get_byte(1, A)] ^ SBox3[get_byte(0, A)];
29
 
      Y = SBox0[get_byte(0, B)] ^ SBox1[get_byte(3, B)] ^
30
 
          SBox2[get_byte(2, B)] ^ SBox3[get_byte(1, B)];
31
 
      X += Y;
32
 
      Y += X + round_key[2*j + 9];
33
 
      X += round_key[2*j + 8];
34
 
 
35
 
      C = rotate_right(C ^ X, 1);
36
 
      D = rotate_left(D, 1) ^ Y;
37
 
 
38
 
      X = SBox0[get_byte(3, C)] ^ SBox1[get_byte(2, C)] ^
39
 
          SBox2[get_byte(1, C)] ^ SBox3[get_byte(0, C)];
40
 
      Y = SBox0[get_byte(0, D)] ^ SBox1[get_byte(3, D)] ^
41
 
          SBox2[get_byte(2, D)] ^ SBox3[get_byte(1, D)];
42
 
      X += Y;
43
 
      Y += X + round_key[2*j + 11];
44
 
      X += round_key[2*j + 10];
45
 
 
46
 
      A = rotate_right(A ^ X, 1);
47
 
      B = rotate_left(B, 1) ^ Y;
48
 
      }
49
 
 
50
 
   C ^= round_key[4]; D ^= round_key[5]; A ^= round_key[6]; B ^= round_key[7];
51
 
 
52
 
   out[ 0] = get_byte(3, C); out[ 1] = get_byte(2, C);
53
 
   out[ 2] = get_byte(1, C); out[ 3] = get_byte(0, C);
54
 
   out[ 4] = get_byte(3, D); out[ 5] = get_byte(2, D);
55
 
   out[ 6] = get_byte(1, D); out[ 7] = get_byte(0, D);
56
 
   out[ 8] = get_byte(3, A); out[ 9] = get_byte(2, A);
57
 
   out[10] = get_byte(1, A); out[11] = get_byte(0, A);
58
 
   out[12] = get_byte(3, B); out[13] = get_byte(2, B);
59
 
   out[14] = get_byte(1, B); out[15] = get_byte(0, B);
60
 
   }
61
 
 
62
 
/*************************************************
63
 
* Twofish Decryption                             *
64
 
*************************************************/
65
 
void Twofish::dec(const byte in[], byte out[]) const
66
 
   {
67
 
   u32bit A = make_u32bit(in[ 3], in[ 2], in[ 1], in[ 0]),
68
 
          B = make_u32bit(in[ 7], in[ 6], in[ 5], in[ 4]),
69
 
          C = make_u32bit(in[11], in[10], in[ 9], in[ 8]),
70
 
          D = make_u32bit(in[15], in[14], in[13], in[12]);
71
 
 
72
 
   A ^= round_key[4]; B ^= round_key[5]; C ^= round_key[6]; D ^= round_key[7];
73
 
 
74
 
   for(u32bit j = 0; j != 16; j += 2)
75
 
      {
76
 
      u32bit X, Y;
77
 
 
78
 
      X = SBox0[get_byte(3, A)] ^ SBox1[get_byte(2, A)] ^
79
 
          SBox2[get_byte(1, A)] ^ SBox3[get_byte(0, A)];
80
 
      Y = SBox0[get_byte(0, B)] ^ SBox1[get_byte(3, B)] ^
81
 
          SBox2[get_byte(2, B)] ^ SBox3[get_byte(1, B)];
82
 
      X += Y;
83
 
      Y += X + round_key[39 - 2*j];
84
 
      X += round_key[38 - 2*j];
85
 
 
86
 
      C = rotate_left(C, 1) ^ X;
87
 
      D = rotate_right(D ^ Y, 1);
88
 
 
89
 
      X = SBox0[get_byte(3, C)] ^ SBox1[get_byte(2, C)] ^
90
 
          SBox2[get_byte(1, C)] ^ SBox3[get_byte(0, C)];
91
 
      Y = SBox0[get_byte(0, D)] ^ SBox1[get_byte(3, D)] ^
92
 
          SBox2[get_byte(2, D)] ^ SBox3[get_byte(1, D)];
93
 
      X += Y;
94
 
      Y += X + round_key[37 - 2*j];
95
 
      X += round_key[36 - 2*j];
96
 
 
97
 
      A = rotate_left(A, 1) ^ X;
98
 
      B = rotate_right(B ^ Y, 1);
99
 
      }
100
 
 
101
 
   C ^= round_key[0]; D ^= round_key[1]; A ^= round_key[2]; B ^= round_key[3];
102
 
 
103
 
   out[ 0] = get_byte(3, C); out[ 1] = get_byte(2, C);
104
 
   out[ 2] = get_byte(1, C); out[ 3] = get_byte(0, C);
105
 
   out[ 4] = get_byte(3, D); out[ 5] = get_byte(2, D);
106
 
   out[ 6] = get_byte(1, D); out[ 7] = get_byte(0, D);
107
 
   out[ 8] = get_byte(3, A); out[ 9] = get_byte(2, A);
108
 
   out[10] = get_byte(1, A); out[11] = get_byte(0, A);
109
 
   out[12] = get_byte(3, B); out[13] = get_byte(2, B);
110
 
   out[14] = get_byte(1, B); out[15] = get_byte(0, B);
111
 
   }
112
 
 
113
 
/*************************************************
114
 
* Twofish Key Schedule                           *
115
 
*************************************************/
116
 
void Twofish::key(const byte key[], u32bit length)
117
 
   {
118
 
   SecureBuffer<byte, 16> S;
119
 
 
120
 
   for(u32bit j = 0; j != length; ++j)
121
 
      rs_mul(S + 4*(j/8), key[j], j);
122
 
 
123
 
   if(length == 16)
124
 
      {
125
 
      for(u32bit j = 0; j != 256; ++j)
126
 
         {
127
 
         SBox0[j] = MDS0[Q0[Q0[j]^S[ 0]]^S[ 4]];
128
 
         SBox1[j] = MDS1[Q0[Q1[j]^S[ 1]]^S[ 5]];
129
 
         SBox2[j] = MDS2[Q1[Q0[j]^S[ 2]]^S[ 6]];
130
 
         SBox3[j] = MDS3[Q1[Q1[j]^S[ 3]]^S[ 7]];
131
 
         }
132
 
      for(u32bit j = 0; j != 40; j += 2)
133
 
         {
134
 
         u32bit X = MDS0[Q0[Q0[j  ]^key[ 8]]^key[ 0]] ^
135
 
                    MDS1[Q0[Q1[j  ]^key[ 9]]^key[ 1]] ^
136
 
                    MDS2[Q1[Q0[j  ]^key[10]]^key[ 2]] ^
137
 
                    MDS3[Q1[Q1[j  ]^key[11]]^key[ 3]];
138
 
         u32bit Y = MDS0[Q0[Q0[j+1]^key[12]]^key[ 4]] ^
139
 
                    MDS1[Q0[Q1[j+1]^key[13]]^key[ 5]] ^
140
 
                    MDS2[Q1[Q0[j+1]^key[14]]^key[ 6]] ^
141
 
                    MDS3[Q1[Q1[j+1]^key[15]]^key[ 7]];
142
 
         Y = rotate_left(Y, 8); X += Y; Y += X;
143
 
         round_key[j] = X; round_key[j+1] = rotate_left(Y, 9);
144
 
         }
145
 
      }
146
 
   else if(length == 24)
147
 
      {
148
 
      for(u32bit j = 0; j != 256; ++j)
149
 
         {
150
 
         SBox0[j] = MDS0[Q0[Q0[Q1[j]^S[ 0]]^S[ 4]]^S[ 8]];
151
 
         SBox1[j] = MDS1[Q0[Q1[Q1[j]^S[ 1]]^S[ 5]]^S[ 9]];
152
 
         SBox2[j] = MDS2[Q1[Q0[Q0[j]^S[ 2]]^S[ 6]]^S[10]];
153
 
         SBox3[j] = MDS3[Q1[Q1[Q0[j]^S[ 3]]^S[ 7]]^S[11]];
154
 
         }
155
 
      for(u32bit j = 0; j != 40; j += 2)
156
 
         {
157
 
         u32bit X = MDS0[Q0[Q0[Q1[j  ]^key[16]]^key[ 8]]^key[ 0]] ^
158
 
                    MDS1[Q0[Q1[Q1[j  ]^key[17]]^key[ 9]]^key[ 1]] ^
159
 
                    MDS2[Q1[Q0[Q0[j  ]^key[18]]^key[10]]^key[ 2]] ^
160
 
                    MDS3[Q1[Q1[Q0[j  ]^key[19]]^key[11]]^key[ 3]];
161
 
         u32bit Y = MDS0[Q0[Q0[Q1[j+1]^key[20]]^key[12]]^key[ 4]] ^
162
 
                    MDS1[Q0[Q1[Q1[j+1]^key[21]]^key[13]]^key[ 5]] ^
163
 
                    MDS2[Q1[Q0[Q0[j+1]^key[22]]^key[14]]^key[ 6]] ^
164
 
                    MDS3[Q1[Q1[Q0[j+1]^key[23]]^key[15]]^key[ 7]];
165
 
         Y = rotate_left(Y, 8); X += Y; Y += X;
166
 
         round_key[j] = X; round_key[j+1] = rotate_left(Y, 9);
167
 
         }
168
 
      }
169
 
   else if(length == 32)
170
 
      {
171
 
      for(u32bit j = 0; j != 256; ++j)
172
 
         {
173
 
         SBox0[j] = MDS0[Q0[Q0[Q1[Q1[j]^S[ 0]]^S[ 4]]^S[ 8]]^S[12]];
174
 
         SBox1[j] = MDS1[Q0[Q1[Q1[Q0[j]^S[ 1]]^S[ 5]]^S[ 9]]^S[13]];
175
 
         SBox2[j] = MDS2[Q1[Q0[Q0[Q0[j]^S[ 2]]^S[ 6]]^S[10]]^S[14]];
176
 
         SBox3[j] = MDS3[Q1[Q1[Q0[Q1[j]^S[ 3]]^S[ 7]]^S[11]]^S[15]];
177
 
         }
178
 
      for(u32bit j = 0; j != 40; j += 2)
179
 
         {
180
 
         u32bit X = MDS0[Q0[Q0[Q1[Q1[j  ]^key[24]]^key[16]]^key[ 8]]^key[ 0]] ^
181
 
                    MDS1[Q0[Q1[Q1[Q0[j  ]^key[25]]^key[17]]^key[ 9]]^key[ 1]] ^
182
 
                    MDS2[Q1[Q0[Q0[Q0[j  ]^key[26]]^key[18]]^key[10]]^key[ 2]] ^
183
 
                    MDS3[Q1[Q1[Q0[Q1[j  ]^key[27]]^key[19]]^key[11]]^key[ 3]];
184
 
         u32bit Y = MDS0[Q0[Q0[Q1[Q1[j+1]^key[28]]^key[20]]^key[12]]^key[ 4]] ^
185
 
                    MDS1[Q0[Q1[Q1[Q0[j+1]^key[29]]^key[21]]^key[13]]^key[ 5]] ^
186
 
                    MDS2[Q1[Q0[Q0[Q0[j+1]^key[30]]^key[22]]^key[14]]^key[ 6]] ^
187
 
                    MDS3[Q1[Q1[Q0[Q1[j+1]^key[31]]^key[23]]^key[15]]^key[ 7]];
188
 
         Y = rotate_left(Y, 8); X += Y; Y += X;
189
 
         round_key[j] = X; round_key[j+1] = rotate_left(Y, 9);
190
 
         }
191
 
      }
192
 
   }
193
 
 
194
 
/*************************************************
195
 
* Do one column of the RS matrix multiplcation   *
196
 
*************************************************/
197
 
void Twofish::rs_mul(byte S[4], byte key, u32bit offset)
198
 
   {
199
 
   if(key)
200
 
      {
201
 
      byte X = POLY_TO_EXP[key - 1];
202
 
 
203
 
      byte RS1 = RS[(4*offset  ) % 32];
204
 
      byte RS2 = RS[(4*offset+1) % 32];
205
 
      byte RS3 = RS[(4*offset+2) % 32];
206
 
      byte RS4 = RS[(4*offset+3) % 32];
207
 
 
208
 
      S[0] ^= EXP_TO_POLY[(X + POLY_TO_EXP[RS1 - 1]) % 255];
209
 
      S[1] ^= EXP_TO_POLY[(X + POLY_TO_EXP[RS2 - 1]) % 255];
210
 
      S[2] ^= EXP_TO_POLY[(X + POLY_TO_EXP[RS3 - 1]) % 255];
211
 
      S[3] ^= EXP_TO_POLY[(X + POLY_TO_EXP[RS4 - 1]) % 255];
212
 
      }
213
 
   }
214
 
 
215
 
/*************************************************
216
 
* Clear memory of sensitive data                 *
217
 
*************************************************/
218
 
void Twofish::clear() throw()
219
 
   {
220
 
   SBox0.clear();
221
 
   SBox1.clear();
222
 
   SBox2.clear();
223
 
   SBox3.clear();
224
 
   round_key.clear();
225
 
   }
226
 
 
227
 
}