rijndael: refactor to reduce number of #ifdefs and branches
[libgcrypt.git] / cipher / gost-s-box.c
1 /* gost-s-box.c - GOST 28147-89 S-Box expander
2  * Copyright (C) 2013 Dmitry Eremin-Solenikov
3  *
4  * This file is part of Libgcrypt.
5  *
6  * Libgcrypt is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU Lesser General Public License as
8  * published by the Free Software Foundation; either version 2.1 of
9  * the License, or (at your option) any later version.
10  *
11  * Libgcrypt is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with this program; if not, see <http://www.gnu.org/licenses/>.
18  */
19
20 #include <stdio.h>
21 #include <stdlib.h>
22
23 #define DIM(v) (sizeof(v)/sizeof((v)[0]))
24
25 struct gost_sbox
26 {
27   const char *name;
28   const char *oid;
29   unsigned char sbox[16*8];
30 } gost_sboxes[] = {
31   { "test_3411", "1.2.643.2.2.30.0", {
32       0x4, 0xE, 0x5, 0x7, 0x6, 0x4, 0xD, 0x1,
33       0xA, 0xB, 0x8, 0xD, 0xC, 0xB, 0xB, 0xF,
34       0x9, 0x4, 0x1, 0xA, 0x7, 0xA, 0x4, 0xD,
35       0x2, 0xC, 0xD, 0x1, 0x1, 0x0, 0x1, 0x0,
36
37       0xD, 0x6, 0xA, 0x0, 0x5, 0x7, 0x3, 0x5,
38       0x8, 0xD, 0x3, 0x8, 0xF, 0x2, 0xF, 0x7,
39       0x0, 0xF, 0x4, 0x9, 0xD, 0x1, 0x5, 0xA,
40       0xE, 0xA, 0x2, 0xF, 0x8, 0xD, 0x9, 0x4,
41
42       0x6, 0x2, 0xE, 0xE, 0x4, 0x3, 0x0, 0x9,
43       0xB, 0x3, 0xF, 0x4, 0xA, 0x6, 0xA, 0x2,
44       0x1, 0x8, 0xC, 0x6, 0x9, 0x8, 0xE, 0x3,
45       0xC, 0x1, 0x7, 0xC, 0xE, 0x5, 0x7, 0xE,
46
47       0x7, 0x0, 0x6, 0xB, 0x0, 0x9, 0x6, 0x6,
48       0xF, 0x7, 0x0, 0x2, 0x3, 0xC, 0x8, 0xB,
49       0x5, 0x5, 0x9, 0x5, 0xB, 0xF, 0x2, 0x8,
50       0x3, 0x9, 0xB, 0x3, 0x2, 0xE, 0xC, 0xC,
51     }
52   },
53   { "CryptoPro_3411", "1.2.643.2.2.30.1", {
54       0xA, 0x5, 0x7, 0x4, 0x7, 0x7, 0xD, 0x1,
55       0x4, 0xF, 0xF, 0xA, 0x6, 0x6, 0xE, 0x3,
56       0x5, 0x4, 0xC, 0x7, 0x4, 0x2, 0x4, 0xA,
57       0x6, 0x0, 0xE, 0xC, 0xB, 0x4, 0x1, 0x9,
58
59       0x8, 0x2, 0x9, 0x0, 0x9, 0xD, 0x7, 0x5,
60       0x1, 0xD, 0x4, 0xF, 0xC, 0x9, 0x0, 0xB,
61       0x3, 0xB, 0x1, 0x2, 0x2, 0xF, 0x5, 0x4,
62       0x7, 0x9, 0x0, 0x8, 0xA, 0x0, 0xA, 0xF,
63
64       0xD, 0x1, 0x3, 0xE, 0x1, 0xA, 0x3, 0x8,
65       0xC, 0x7, 0xB, 0x1, 0x8, 0x1, 0xC, 0x6,
66       0xE, 0x6, 0x5, 0x6, 0x0, 0x5, 0x8, 0x7,
67       0x0, 0x3, 0x2, 0x5, 0xE, 0xB, 0xF, 0xE,
68
69       0x9, 0xC, 0x6, 0xD, 0xF, 0x8, 0x6, 0xD,
70       0x2, 0xE, 0xA, 0xB, 0xD, 0xE, 0x2, 0x0,
71       0xB, 0xA, 0x8, 0x9, 0x3, 0xC, 0x9, 0x2,
72       0xF, 0x8, 0xD, 0x3, 0x5, 0x3, 0xB, 0xC,
73     }
74   },
75   { "Test_89", "1.2.643.2.2.31.0", {
76       0x4, 0xC, 0xD, 0xE, 0x3, 0x8, 0x9, 0xC,
77       0x2, 0x9, 0x8, 0x9, 0xE, 0xF, 0xB, 0x6,
78       0xF, 0xF, 0xE, 0xB, 0x5, 0x6, 0xC, 0x5,
79       0x5, 0xE, 0xC, 0x2, 0x9, 0xB, 0x0, 0x2,
80
81       0x9, 0x8, 0x7, 0x5, 0x6, 0x1, 0x3, 0xB,
82       0x1, 0x1, 0x3, 0xF, 0x8, 0x9, 0x6, 0x0,
83       0x0, 0x3, 0x9, 0x7, 0x0, 0xC, 0x7, 0x9,
84       0x8, 0xA, 0xA, 0x1, 0xD, 0x5, 0x5, 0xD,
85
86       0xE, 0x2, 0x1, 0x0, 0xA, 0xD, 0x4, 0x3,
87       0x3, 0x7, 0x5, 0xD, 0xB, 0x3, 0x8, 0xE,
88       0xB, 0x4, 0x2, 0xC, 0x7, 0x7, 0xE, 0x7,
89       0xC, 0xD, 0x4, 0x6, 0xC, 0xA, 0xF, 0xA,
90
91       0xD, 0x6, 0x6, 0xA, 0x2, 0x0, 0x1, 0xF,
92       0x7, 0x0, 0xF, 0x4, 0x1, 0xE, 0xA, 0x4,
93       0xA, 0xB, 0x0, 0x3, 0xF, 0x2, 0x2, 0x1,
94       0x6, 0x5, 0xB, 0x8, 0x4, 0x4, 0xD, 0x8,
95     }
96   },
97   { "CryptoPro_A", "1.2.643.2.2.31.1", {
98       0x9, 0x3, 0xE, 0xE, 0xB, 0x3, 0x1, 0xB,
99       0x6, 0x7, 0x4, 0x7, 0x5, 0xA, 0xD, 0xA,
100       0x3, 0xE, 0x6, 0xA, 0x1, 0xD, 0x2, 0xF,
101       0x2, 0x9, 0x2, 0xC, 0x9, 0xC, 0x9, 0x5,
102
103       0x8, 0x8, 0xB, 0xD, 0x8, 0x1, 0x7, 0x0,
104       0xB, 0xA, 0x3, 0x1, 0xD, 0x2, 0xA, 0xC,
105       0x1, 0xF, 0xD, 0x3, 0xF, 0x0, 0x6, 0xE,
106       0x7, 0x0, 0x8, 0x9, 0x0, 0xB, 0x0, 0x8,
107
108       0xA, 0x5, 0xC, 0x0, 0xE, 0x7, 0x8, 0x6,
109       0x4, 0x2, 0xF, 0x2, 0x4, 0x5, 0xC, 0x2,
110       0xE, 0x6, 0x5, 0xB, 0x2, 0x9, 0x4, 0x3,
111       0xF, 0xC, 0xA, 0x4, 0x3, 0x4, 0x5, 0x9,
112
113       0xC, 0xB, 0x0, 0xF, 0xC, 0x8, 0xF, 0x1,
114       0x0, 0x4, 0x7, 0x8, 0x7, 0xF, 0x3, 0x7,
115       0xD, 0xD, 0x1, 0x5, 0xA, 0xE, 0xB, 0xD,
116       0x5, 0x1, 0x9, 0x6, 0x6, 0x6, 0xE, 0x4,
117     }
118   },
119   { "CryptoPro_B", "1.2.643.2.2.31.2", {
120       0x8, 0x0, 0xE, 0x7, 0x2, 0x8, 0x5, 0x0,
121       0x4, 0x1, 0xC, 0x5, 0x7, 0x3, 0x2, 0x4,
122       0xB, 0x2, 0x0, 0x0, 0xC, 0x2, 0xA, 0xB,
123       0x1, 0xA, 0xA, 0xD, 0xF, 0x6, 0xB, 0xE,
124
125       0x3, 0x4, 0x9, 0xB, 0x9, 0x4, 0x9, 0x8,
126       0x5, 0xD, 0x2, 0x6, 0x5, 0xD, 0x1, 0x3,
127       0x0, 0x5, 0xD, 0x1, 0xA, 0xE, 0xC, 0x7,
128       0x9, 0xC, 0xB, 0x2, 0xB, 0xB, 0x3, 0x1,
129
130       0x2, 0x9, 0x7, 0x3, 0x1, 0xC, 0x7, 0xA,
131       0xE, 0x7, 0x5, 0xA, 0x4, 0x1, 0x4, 0x2,
132       0xA, 0x3, 0x8, 0xC, 0x0, 0x7, 0xD, 0x9,
133       0xC, 0xF, 0xF, 0xF, 0xD, 0xF, 0x0, 0x6,
134
135       0x6, 0x8, 0x6, 0xE, 0x8, 0x0, 0xF, 0xD,
136       0x7, 0x6, 0x1, 0x9, 0xE, 0x9, 0x8, 0x5,
137       0xF, 0xE, 0x4, 0x8, 0x3, 0x5, 0xE, 0xC,
138     }
139   },
140   { "CryptoPro_C", "1.2.643.2.2.31.3", {
141       0x1, 0x0, 0x8, 0x3, 0x8, 0xC, 0xA, 0x7,
142       0xB, 0x1, 0x2, 0x6, 0xD, 0x9, 0x9, 0x4,
143       0xC, 0x7, 0x5, 0x0, 0xB, 0xB, 0x6, 0x0,
144       0x2, 0xD, 0x0, 0x1, 0x0, 0x1, 0x8, 0x5,
145
146       0x9, 0xB, 0x4, 0x5, 0x4, 0x8, 0xD, 0xA,
147       0xD, 0x4, 0x9, 0xD, 0x5, 0xE, 0xE, 0x2,
148       0x0, 0x5, 0xF, 0xA, 0x1, 0x2, 0x2, 0xF,
149       0xF, 0x2, 0xA, 0x8, 0x2, 0x4, 0x0, 0xE,
150
151       0x4, 0x8, 0x3, 0xB, 0x9, 0x7, 0xF, 0xC,
152       0x5, 0xE, 0x7, 0x2, 0x3, 0x3, 0x3, 0x6,
153       0x8, 0xF, 0xC, 0x9, 0xC, 0x6, 0x5, 0x1,
154       0xE, 0xC, 0xD, 0x7, 0xE, 0x5, 0xB, 0xB,
155
156       0xA, 0x9, 0x6, 0xE, 0x6, 0xA, 0x4, 0xD,
157       0x7, 0xA, 0xE, 0xF, 0xF, 0x0, 0x1, 0x9,
158       0x6, 0x6, 0x1, 0xC, 0xA, 0xF, 0xC, 0x3,
159       0x3, 0x3, 0xB, 0x4, 0x7, 0xD, 0x7, 0x8,
160     }
161   },
162   { "CryptoPro_D", "1.2.643.2.2.31.4", {
163       0xF, 0xB, 0x1, 0x1, 0x0, 0x8, 0x3, 0x1,
164       0xC, 0x6, 0xC, 0x5, 0xC, 0x0, 0x0, 0xA,
165       0x2, 0x3, 0xB, 0xE, 0x8, 0xF, 0x6, 0x6,
166       0xA, 0x4, 0x0, 0xC, 0x9, 0x3, 0xF, 0x8,
167
168       0x6, 0xC, 0xF, 0xA, 0xD, 0x2, 0x1, 0xF,
169       0x4, 0xF, 0xE, 0x7, 0x2, 0x5, 0xE, 0xB,
170       0x5, 0xE, 0x6, 0x0, 0xA, 0xE, 0x9, 0x0,
171       0x0, 0x2, 0x5, 0xD, 0xB, 0xB, 0x2, 0x4,
172
173       0x7, 0x7, 0xA, 0x6, 0x7, 0x1, 0xD, 0xC,
174       0x9, 0xD, 0xD, 0x2, 0x3, 0xA, 0x8, 0x3,
175       0xE, 0x8, 0x4, 0xB, 0x6, 0x4, 0xC, 0x5,
176       0xD, 0x0, 0x8, 0x4, 0x5, 0x7, 0x4, 0x9,
177
178       0x1, 0x5, 0x9, 0x9, 0x4, 0xC, 0xB, 0x7,
179       0xB, 0xA, 0x3, 0x3, 0xE, 0x9, 0xA, 0xD,
180       0x8, 0x9, 0x7, 0xF, 0xF, 0xD, 0x5, 0x2,
181       0x3, 0x1, 0x2, 0x8, 0x1, 0x6, 0x7, 0xE,
182     }
183   },
184   { "TC26_A", "1.2.643.7.1.2.5.1.1", {
185       0xc, 0x6, 0xb, 0xc, 0x7, 0x5, 0x8, 0x1,
186       0x4, 0x8, 0x3, 0x8, 0xf, 0xd, 0xe, 0x7,
187       0x6, 0x2, 0x5, 0x2, 0x5, 0xf, 0x2, 0xe,
188       0x2, 0x3, 0x8, 0x1, 0xa, 0x6, 0x5, 0xd,
189
190       0xa, 0x9, 0x2, 0xd, 0x8, 0x9, 0x6, 0x0,
191       0x5, 0xa, 0xf, 0x4, 0x1, 0x2, 0x9, 0x5,
192       0xb, 0x5, 0xa, 0xf, 0x6, 0xc, 0x1, 0x8,
193       0x9, 0xc, 0xd, 0x6, 0xd, 0xa, 0xc, 0x3,
194
195       0xe, 0x1, 0xe, 0x7, 0x0, 0xb, 0xf, 0x4,
196       0x8, 0xe, 0x1, 0x0, 0x9, 0x7, 0x4, 0xf,
197       0xd, 0x4, 0x7, 0xa, 0x3, 0x8, 0xb, 0xa,
198       0x7, 0x7, 0x4, 0x5, 0xe, 0x1, 0x0, 0x6,
199
200       0x0, 0xb, 0xc, 0x3, 0xb, 0x4, 0xd, 0x9,
201       0x3, 0xd, 0x9, 0xe, 0x4, 0x3, 0xa, 0xc,
202       0xf, 0x0, 0x6, 0x9, 0x2, 0xe, 0x3, 0xb,
203       0x1, 0xf, 0x0, 0xb, 0xc, 0x0, 0x7, 0x2,
204     }
205   },
206 };
207
208 int main(int argc, char **argv)
209 {
210   unsigned int i, j, s;
211   FILE *f;
212
213   if (argc == 1)
214     f = stdin;
215   else
216     f = fopen(argv[1], "w");
217
218   if (!f)
219     {
220       perror("fopen");
221       exit(1);
222     }
223
224   for (s = 0; s < DIM(gost_sboxes); s++)
225     {
226       unsigned char *sbox = gost_sboxes[s].sbox;
227       fprintf (f, "static const u32 sbox_%s[4*256] =\n  {", gost_sboxes[s].name);
228       for (i = 0; i < 4; i++) {
229         fprintf (f,     "\n    /* %d */\n   ", i);
230         for (j = 0; j < 256; j++) {
231           unsigned int val;
232           if (j % 4 == 0 && j != 0)
233             fprintf (f, "\n   ");
234           val = sbox[ (j & 0xf) * 8 + 2 * i + 0] |
235                (sbox[ (j >> 4)  * 8 + 2 * i + 1] << 4);
236           val <<= (8*i);
237           val = (val << 11) | (val >> 21);
238           fprintf (f, " 0x%08x,", val);
239         }
240       }
241       fprintf (f, "\n  };\n\n");
242     }
243
244   fprintf (f, "static struct\n{\n  const char *oid;\n  const u32 *sbox;\n} gost_oid_map[] = {\n");
245
246   for (s = 0; s < DIM(gost_sboxes); s++)
247     {
248       fprintf (f, "  { \"%s\", sbox_%s },\n", gost_sboxes[s].oid, gost_sboxes[s].name );
249     }
250
251   fprintf(f, "  { NULL, NULL }\n};\n");
252
253   fclose (f);
254
255   return 0;
256 }