iPXE
des.c
Go to the documentation of this file.
1/*
2 * Copyright (C) 2024 Michael Brown <mbrown@fensystems.co.uk>.
3 *
4 * This program is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU General Public License as
6 * published by the Free Software Foundation; either version 2 of the
7 * License, or any later version.
8 *
9 * This program is distributed in the hope that it will be useful, but
10 * WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * General Public License for more details.
13 *
14 * You should have received a copy of the GNU General Public License
15 * along with this program; if not, write to the Free Software
16 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
17 * 02110-1301, USA.
18 *
19 * You can also choose to distribute this program under the terms of
20 * the Unmodified Binary Distribution Licence (as given in the file
21 * COPYING.UBDL), provided that you have satisfied its requirements.
22 */
23
24FILE_LICENCE ( GPL2_OR_LATER_OR_UBDL );
25FILE_SECBOOT ( PERMITTED );
26
27/** @file
28 *
29 * DES algorithm
30 *
31 * DES was not designed to be implemented in software, and therefore
32 * contains a large number of bit permutation operations that are
33 * essentially free in hardware (requiring only wires, no gates) but
34 * expensive in software.
35 *
36 * Since DES is no longer used as a practical block cipher for large
37 * volumes of data, we optimise for code size, and do not attempt to
38 * obtain fast throughput.
39 *
40 * The algorithm is specified in NIST SP 800-67, downloadable from
41 * https://nvlpubs.nist.gov/nistpubs/SpecialPublications/NIST.SP.800-67r2.pdf
42 */
43
44#include <stdint.h>
45#include <string.h>
46#include <errno.h>
47#include <byteswap.h>
48#include <ipxe/rotate.h>
49#include <ipxe/crypto.h>
50#include <ipxe/ecb.h>
51#include <ipxe/cbc.h>
52#include <ipxe/init.h>
53#include <ipxe/des.h>
54
55/**
56 * DES shift schedule
57 *
58 * The DES shift schedule (ordered from round 16 down to round 1) is
59 * {1,2,2,2,2,2,2,1,2,2,2,2,2,2,1,1}. In binary, this may be
60 * represented as {1,10,10,10,10,10,10,1,10,10,10,10,10,10,1,1} and
61 * concatenated (without padding) to produce a single binary integer
62 * 1101010101010110101010101011 (equal to 0x0d556aab in hexadecimal).
63 *
64 * This integer may then be consumed LSB-first, where a 1 bit
65 * indicates a shift and the generation of a round key, and a 0 bit
66 * indicates a shift without the generation of a round key.
67 */
68#define DES_SCHEDULE 0x0d556aab
69
70/**
71 * Define an element pair in a DES S-box
72 *
73 * @v x Upper element of element pair
74 * @v y Lower element of element pair
75 *
76 * DES S-box elements are 4-bit values. We encode two values per
77 * byte, ordering the elements so that the six-bit input value may be
78 * used directly as a lookup index.
79 *
80 * Specifically, if the input value is {r1,c3,c2,c1,c0,r0}, where
81 * {r1,r0} is the table row index and {c3,c2,c1,c0} is the table
82 * column index (as used in the DES specification), then:
83 *
84 * - {r1,c3,c2,c1,c0} is the byte index into the table
85 *
86 * - (4*r0) is the required bit shift to extract the 4-bit value
87 */
88#define SBYTE( x, y ) ( ( (y) << 4 ) | (x) )
89
90/**
91 * Define a row pair in a DES S-box
92 *
93 * @v x0..xf Upper row of row pair
94 * @v y0..yf Lower row of row pair
95 */
96#define SBOX( x0, x1, x2, x3, x4, x5, x6, x7, x8, x9, xa, xb, xc, xd, xe, xf, \
97 y0, y1, y2, y3, y4, y5, y6, y7, y8, y9, ya, yb, yc, yd, ye, yf ) \
98 SBYTE ( x0, y0 ), SBYTE ( x1, y1 ), SBYTE ( x2, y2 ), SBYTE ( x3, y3 ),\
99 SBYTE ( x4, y4 ), SBYTE ( x5, y5 ), SBYTE ( x6, y6 ), SBYTE ( x7, y7 ),\
100 SBYTE ( x8, y8 ), SBYTE ( x9, y9 ), SBYTE ( xa, ya ), SBYTE ( xb, yb ),\
101 SBYTE ( xc, yc ), SBYTE ( xd, yd ), SBYTE ( xe, ye ), SBYTE ( xf, yf )
102
103/** DES S-boxes S1..S8 */
104static const uint8_t des_s[8][32] = { {
105 /* S1 */
106 SBOX ( 14, 4, 13, 1, 2, 15, 11, 8, 3, 10, 6, 12, 5, 9, 0, 7,
107 0, 15, 7, 4, 14, 2, 13, 1, 10, 6, 12, 11, 9, 5, 3, 8 ),
108 SBOX ( 4, 1, 14, 8, 13, 6, 2, 11, 15, 12, 9, 7, 3, 10, 5, 0,
109 15, 12, 8, 2, 4, 9, 1, 7, 5, 11, 3, 14, 10, 0, 6, 13 )
110}, {
111 /* S2 */
112 SBOX ( 15, 1, 8, 14, 6, 11, 3, 4, 9, 7, 2, 13, 12, 0, 5, 10,
113 3, 13, 4, 7, 15, 2, 8, 14, 12, 0, 1, 10, 6, 9, 11, 5 ),
114 SBOX ( 0, 14, 7, 11, 10, 4, 13, 1, 5, 8, 12, 6, 9, 3, 2, 15,
115 13, 8, 10, 1, 3, 15, 4, 2, 11, 6, 7, 12, 0, 5, 14, 9 )
116}, {
117 /* S3 */
118 SBOX ( 10, 0, 9, 14, 6, 3, 15, 5, 1, 13, 12, 7, 11, 4, 2, 8,
119 13, 7, 0, 9, 3, 4, 6, 10, 2, 8, 5, 14, 12, 11, 15, 1 ),
120 SBOX ( 13, 6, 4, 9, 8, 15, 3, 0, 11, 1, 2, 12, 5, 10, 14, 7,
121 1, 10, 13, 0, 6, 9, 8, 7, 4, 15, 14, 3, 11, 5, 2, 12 )
122}, {
123 /* S4 */
124 SBOX ( 7, 13, 14, 3, 0, 6, 9, 10, 1, 2, 8, 5, 11, 12, 4, 15,
125 13, 8, 11, 5, 6, 15, 0, 3, 4, 7, 2, 12, 1, 10, 14, 9 ),
126 SBOX ( 10, 6, 9, 0, 12, 11, 7, 13, 15, 1, 3, 14, 5, 2, 8, 4,
127 3, 15, 0, 6, 10, 1, 13, 8, 9, 4, 5, 11, 12, 7, 2, 14 )
128}, {
129 /* S5 */
130 SBOX ( 2, 12, 4, 1, 7, 10, 11, 6, 8, 5, 3, 15, 13, 0, 14, 9,
131 14, 11, 2, 12, 4, 7, 13, 1, 5, 0, 15, 10, 3, 9, 8, 6 ),
132 SBOX ( 4, 2, 1, 11, 10, 13, 7, 8, 15, 9, 12, 5, 6, 3, 0, 14,
133 11, 8, 12, 7, 1, 14, 2, 13, 6, 15, 0, 9, 10, 4, 5, 3 )
134}, {
135 /* S6 */
136 SBOX ( 12, 1, 10, 15, 9, 2, 6, 8, 0, 13, 3, 4, 14, 7, 5, 11,
137 10, 15, 4, 2, 7, 12, 9, 5, 6, 1, 13, 14, 0, 11, 3, 8 ),
138 SBOX ( 9, 14, 15, 5, 2, 8, 12, 3, 7, 0, 4, 10, 1, 13, 11, 6,
139 4, 3, 2, 12, 9, 5, 15, 10, 11, 14, 1, 7, 6, 0, 8, 13 )
140}, {
141 /* S7 */
142 SBOX ( 4, 11, 2, 14, 15, 0, 8, 13, 3, 12, 9, 7, 5, 10, 6, 1,
143 13, 0, 11, 7, 4, 9, 1, 10, 14, 3, 5, 12, 2, 15, 8, 6 ),
144 SBOX ( 1, 4, 11, 13, 12, 3, 7, 14, 10, 15, 6, 8, 0, 5, 9, 2,
145 6, 11, 13, 8, 1, 4, 10, 7, 9, 5, 0, 15, 14, 2, 3, 12 )
146}, {
147 /* S8 */
148 SBOX ( 13, 2, 8, 4, 6, 15, 11, 1, 10, 9, 3, 14, 5, 0, 12, 7,
149 1, 15, 13, 8, 10, 3, 7, 4, 12, 5, 6, 11, 0, 14, 9, 2 ),
150 SBOX ( 7, 11, 4, 1, 9, 12, 14, 2, 0, 6, 10, 13, 15, 3, 5, 8,
151 2, 1, 14, 7, 4, 10, 8, 13, 15, 12, 9, 0, 3, 5, 6, 11 )
152} };
153
154/**
155 * Define a bit index within permuted choice 2 (PC2)
156 *
157 * @v bit Bit index
158 *
159 * Permuted choice 2 (PC2) is used to select bits from a concatenated
160 * pair of 28-bit registers ("C" and "D") as part of the key schedule.
161 * We store these as 32-bit registers and so must add 4 to indexes
162 * above 28.
163 */
164#define DES_PC2( x ) ( (x) + ( ( (x) > 28 ) ? 4 : 0 ) )
165
166/**
167 * Define six bits of permuted choice 2 (PC2)
168 *
169 * @v r1:r0 Bits corresponding to S-box row index
170 * @v c3:c0 Bits corresponding to S-box column index
171 *
172 * There are 8 steps within a DES round (one step per S-box). Each
173 * step requires six bits of the round key, corresponding to the S-box
174 * input value {r1,c3,c2,c1,c0,r0}, where {r1,r0} is the table row
175 * index and {c3,c2,c1,c0} is the table column index.
176 *
177 * As an optimisation, we store the least significant of the 6 bits in
178 * the sign bit of a signed 8-bit value, and the remaining 5 bits in
179 * the least significant 5 bits of the 8-bit value. See the comments
180 * in des_sbox() for further details.
181 */
182#define DES_PC2R( r1, c3, c2, c1, c0, r0 ) \
183 DES_PC2 ( r0 ), /* LSB stored in sign bit */ \
184 DES_PC2 ( r0 ), /* Unused bit */ \
185 DES_PC2 ( r0 ), /* Unused bit */ \
186 DES_PC2 ( r1 ), /* Remaining 5 bits */ \
187 DES_PC2 ( c3 ), /* ... */ \
188 DES_PC2 ( c2 ), /* ... */ \
189 DES_PC2 ( c1 ), /* ... */ \
190 DES_PC2 ( c0 ) /* ... */
191
192/**
193 * A DES systematic permutation generator
194 *
195 * Many of the permutations used in DES comprise systematic bit
196 * patterns. We generate these permutations at runtime to save on
197 * code size.
198 */
200 /** Permutation */
202 /** Seed value */
204};
205
206/**
207 * Define a DES permutation generator
208 *
209 * @v PERMUTATION Permutation
210 * @v OFFSET Fixed input bit offset (0 or 1)
211 * @v INV<n> Input bit index bit <n> should be inverted
212 * @v BIT<n> Source bit for input bit index bit <n>
213 * @ret generator Permutation generator
214 */
215#define DES_GENERATOR( PERMUTATION, OFFSET, INV5, BIT5, INV4, BIT4, \
216 INV3, BIT3, INV2, BIT2, INV1, BIT1, INV0, BIT0 ) \
217 { \
218 .permutation = (PERMUTATION), \
219 .seed = ( ( (INV0) << 31 ) | ( (BIT0) << 28 ) | \
220 ( (INV1) << 27 ) | ( (BIT1) << 24 ) | \
221 ( (INV2) << 23 ) | ( (BIT2) << 20 ) | \
222 ( (INV3) << 19 ) | ( (BIT3) << 16 ) | \
223 ( (INV4) << 15 ) | ( (BIT4) << 12 ) | \
224 ( (INV5) << 11 ) | ( (BIT5) << 8 ) | \
225 ( ( uint32_t ) sizeof (PERMUTATION) - 1 ) | \
226 (OFFSET) ), \
227 }
228
229/** DES permuted choice 1 (PC1) "C" register */
230static uint8_t des_pc1c[29];
231
232/** DES permuted choice 1 (PC1) "D" register */
233static uint8_t des_pc1d[33];
234
235/** DES permuted choice 2 (PC2) */
236static const uint8_t des_pc2[65] = {
237 DES_PC2R ( 14, 17, 11, 24, 1, 5 ),
238 DES_PC2R ( 3, 28, 15, 6, 21, 10 ),
239 DES_PC2R ( 23, 19, 12, 4, 26, 8 ),
240 DES_PC2R ( 16, 7, 27, 20, 13, 2 ),
241 DES_PC2R ( 41, 52, 31, 37, 47, 55 ),
242 DES_PC2R ( 30, 40, 51, 45, 33, 48 ),
243 DES_PC2R ( 44, 49, 39, 56, 34, 53 ),
244 DES_PC2R ( 46, 42, 50, 36, 29, 32 ),
245 0 /* terminator */
246};
247
248/** DES initial permutation (IP) */
249static uint8_t des_ip[65];
250
251/** DES data permutation (P) */
252static const uint8_t des_p[33] = {
253 16, 7, 20, 21, 29, 12, 28, 17, 1, 15, 23, 26, 5, 18, 31, 10,
254 2, 8, 24, 14, 32, 27, 3, 9, 19, 13, 30, 6, 22, 11, 4, 25,
255 0 /* terminator */
256};
257
258/** DES final / inverse initial permutation (FP / IP^-1) */
259static uint8_t des_fp[65];
260
261/** DES permutation generators */
262static struct des_generator des_generators[] = {
263
264 /* The DES initial permutation transforms the bit index
265 * {x5,x4,x3,x2,x1,x0}+1 into {~x2,~x1,~x0,x4,x3,~x5}+1
266 */
267 DES_GENERATOR ( des_ip, 1, 1, 2, 1, 1, 1, 0, 0, 4, 0, 3, 1, 5 ),
268
269 /* The DES final permutation transforms the bit index
270 * {x5,x4,x3,x2,x1,x0}+1 into {~x0,x2,x1,~x5,~x4,~x3}+1
271 *
272 * There is an asymmetry in the DES block diagram for the last
273 * of the 16 rounds, which is functionally equivalent to
274 * performing 16 identical rounds and then swapping the left
275 * and right halves before applying the final permutation. We
276 * may therefore account for this asymmetry by inverting the
277 * MSB in each bit index, to point to the corresponding bit in
278 * the other half.
279 *
280 * This is equivalent to using a permutation that transforms
281 * {x5,x4,x3,x2,x1,x0}+1 into {x0,x2,x1,~x5,~x4,~x3}+1
282 */
283 DES_GENERATOR ( des_fp, 1, 0, 0, 0, 2, 0, 1, 1, 5, 1, 4, 1, 3 ),
284
285 /* The "C" half of DES permuted choice 1 (PC1) transforms the
286 * bit index {x5,x4,x3,x2,x1,x0}+1 into {~x2,~x1,~x0,x5,x4,x3}+1
287 */
288 DES_GENERATOR ( des_pc1c, 1, 1, 2, 1, 1, 1, 0, 0, 5, 0, 4, 0, 3 ),
289
290 /* The "D" half of DES permuted choice 1 (PC1) transforms the
291 * bit index {x5,x4,x3,x2,x1,x0}+1 into {~x2,~x1,~x0,~x5,~x4,~x3}+0
292 *
293 * Due to the idosyncratic design choice of using 28-bit
294 * registers in the DES key expansion schedule, the final four
295 * permutation values appear at indices [28:31] instead of
296 * [24:27]. This is adjusted for in @c des_setkey().
297 */
298 DES_GENERATOR ( des_pc1d, 0, 1, 2, 1, 1, 1, 0, 1, 5, 1, 4, 1, 3 ),
299};
300
301/**
302 * Generate DES permutation
303 *
304 * @v generator Generator
305 */
306static __attribute__ (( noinline )) void
307des_generate ( struct des_generator *generator ) {
308 uint8_t *permutation = generator->permutation;
309 uint32_t seed = generator->seed;
310 unsigned int index = 0;
311 uint8_t accum;
312 uint8_t bit;
313
314 /* Generate permutations
315 *
316 * This loop is optimised for code size on a
317 * register-constrained architecture such as i386.
318 */
319 do {
320 /* Rotate seed to access MSB's bit descriptor */
321 seed = ror32 ( seed, 8 );
322
323 /* Initialise accumulator with six flag bits */
324 accum = 0xfc;
325
326 /* Accumulate bits until all six flag bits are cleared */
327 do {
328 /* Extract specified bit from index. Use a
329 * rotation instead of a shift, since this
330 * will allow the mask to be elided.
331 */
332 bit = ror8 ( index, ( seed & 0x07 ) );
333 seed = ror32 ( seed, 3 );
334
335 /* Toggle bit if applicable */
336 bit ^= seed;
337 seed = ror32 ( seed, 1 );
338
339 /* Add bit to accumulator and clear one flag bit */
340 accum <<= 1;
341 accum |= ( bit & 0x01 );
342
343 } while ( accum & 0x80 );
344
345 /* Add constant offset if applicable */
346 accum += ( seed & 0x01 );
347
348 /* Store permutation */
349 permutation[index] = accum;
350
351 /* Loop until reaching length (which is always even) */
352 } while ( ++index < ( seed & 0xfe ) );
353 DBGC2 ( permutation, "DES generated permutation %p:\n", permutation );
355 ( ( seed & 0xfe ) + 1 /* zero terminator */ ) );
356}
357
358/**
359 * Initialise permutations
360 */
361static void des_init ( void ) {
362 unsigned int i;
363
364 /* Generate all generated permutations */
365 for ( i = 0 ; i < ( sizeof ( des_generators ) /
366 sizeof ( des_generators[0] ) ) ; i++ ) {
368 }
369}
370
371/** Initialisation function */
372struct init_fn des_init_fn __init_fn ( INIT_NORMAL ) = {
373 .name = "des",
374 .initialise = des_init,
375};
376
377/**
378 * Perform bit permutation
379 *
380 * @v permutation Bit permutation (zero-terminated)
381 * @v in Input value
382 * @v out Output value
383 */
384static void des_permute ( const uint8_t *permutation, const uint8_t *in,
385 uint8_t *out ) {
386 uint8_t mask = 0x80;
387 uint8_t accum = 0;
388 unsigned int bit;
389
390 /* Extract individual input bits to construct output value */
391 while ( ( bit = *(permutation++) ) ) {
392 bit--;
393 if ( in[ bit / 8 ] & ( 0x80 >> ( bit % 8 ) ) )
394 accum |= mask;
395 *out = accum;
396 mask = ror8 ( mask, 1 );
397 if ( mask == 0x80 ) {
398 out++;
399 accum = 0;
400 }
401 }
402}
403
404/**
405 * Perform DES S-box substitution
406 *
407 * @v in 32-bit input value (native endian)
408 * @v rkey 48-bit round key
409 * @ret out 32-bit output value (native endian)
410 */
411static uint32_t des_sbox ( uint32_t in, const union des_round_key *rkey ) {
412 uint32_t out = 0;
413 uint32_t lookup;
414 int32_t key;
415 uint8_t sub;
416 unsigned int i;
417
418 /* Perform input expansion, key addition, and S-box substitution */
419 for ( i = 0 ; i < 8 ; i++ ) {
420
421 /* Rotate input and output */
422 out = rol32 ( out, 4 );
423 in = rol32 ( in, 4 );
424
425 /* Extract step key from relevant 6 bits of round key
426 *
427 * The least significant of the 6 bits (corresponding
428 * to bit r0 in the S-box lookup index) is stored in
429 * the sign bit of the step key byte. It will
430 * therefore be propagated via sign extension to the
431 * MSB of the 32-bit step key.
432 *
433 * The remaining 5 of the 6 bits (corresponding to
434 * bits {r1,c3,c2,c1,c0} in the S-box lookup index)
435 * are stored in the least significant 5 bits of the
436 * step key byte and will end up in the least
437 * significant 5 bits of the 32-bit step key.
438 */
439 key = rkey->step[i];
440
441 /* Add step key to input to produce S-box lookup index
442 *
443 * We do not ever perform an explicit expansion of the
444 * input value from 32 to 48 bits. Instead, we rotate
445 * the 32-bit input value by 4 bits on each step, and
446 * extract the relevant 6 bits.
447 *
448 * The least significant of the 6 bits (corresponding
449 * to bit r0 in the S-box lookup index) is currently
450 * in the MSB of the 32-bit (rotated) input value.
451 *
452 * The remaining 5 of the 6 bits (corresponding to
453 * bits {r1,c3,c2,c1,c0} in the S-box lookup index)
454 * are currently in the least significant 5 bits of
455 * the 32-bit (rotated) input value.
456 *
457 * This aligns with the placement of the bits in the
458 * step key (see above), and we can therefore perform
459 * a single XOR to add the 6-bit step key to the
460 * relevant 6 bits of the input value.
461 */
462 lookup = ( in ^ key );
463
464 /* Look up S[i][in ^ key] from S-box
465 *
466 * We have bits {r1,c3,c2,c1,c0} in the least
467 * significant 5 bits of the lookup index, and so can
468 * use the masked lookup index directly as a byte
469 * index into the relevant S-box to extract the byte
470 * containing both {r1,c3,c2,c1,c0,'0'} and
471 * {r1,c3,c2,c1,c0,'1'}.
472 *
473 * We then use the MSB of the 32-bit lookup index to
474 * extract the relevant nibble for the full lookup
475 * index {r1,c3,c2,c1,c0,r0}.
476 */
477 sub = des_s[i][ lookup & 0x1f ];
478 sub >>= ( ( lookup >> 29 ) & 4 );
479 sub &= 0x0f;
480
481 /* Substitute S[i][input ^ key] into output */
482 out |= sub;
483 }
484
485 return out;
486}
487
488/**
489 * Perform a single DES round
490 *
491 * @v block DES block
492 * @v rkey 48-bit round key
493 */
494static void des_round ( union des_block *block,
495 const union des_round_key *rkey ) {
496 union des_dword sbox;
497 uint32_t left;
498 uint32_t right;
499
500 /* Extract left and right halves L[n-1] and R[n-1] */
501 left = block->left.dword;
502 right = block->right.dword;
503 DBGC2 ( block, "DES L=%08x R=%08x K=%08x%08x", be32_to_cpu ( left ),
504 be32_to_cpu ( right ), be32_to_cpu ( rkey->dword[0] ),
505 be32_to_cpu ( rkey->dword[1] ) );
506
507 /* L[n] = R[n-1] */
508 block->left.dword = right;
509
510 /* Calculate Feistel function f(R[n-1], K[n]) */
511 sbox.dword = cpu_to_be32 ( des_sbox ( be32_to_cpu ( right ), rkey ) );
512 des_permute ( des_p, sbox.byte, block->right.byte );
513
514 /* R[n] = L[n-1] + f(R[n-1], K[n]) */
515 block->right.dword ^= left;
516 DBGC2 ( block, " => L=%08x R=%08x\n",
517 be32_to_cpu ( block->left.dword ),
518 be32_to_cpu ( block->right.dword ) );
519}
520
521/**
522 * Perform all DES rounds
523 *
524 * @v in Input DES block
525 * @v out Output DES block
526 * @v rkey Starting 48-bit round key
527 * @v offset Byte offset between round keys
528 */
529static void des_rounds ( const union des_block *in, union des_block *out,
530 const union des_round_key *rkey,
531 ssize_t offset ) {
532 union des_block tmp;
533 unsigned int i;
534
535 /* Apply initial permutation */
536 des_permute ( des_ip, in->byte, tmp.byte );
537
538 /* Perform all DES rounds, consuming keys in the specified order */
539 for ( i = 0 ; i < DES_ROUNDS ; i++ ) {
540 des_round ( &tmp, rkey );
541 rkey = ( ( ( void * ) rkey ) + offset );
542 }
543
544 /* Apply final permutation */
545 DBGC ( &tmp, "DES %scrypted %08x%08x => ",
546 ( ( offset > 0 ) ? "en" : "de" ), be32_to_cpu ( in->dword[0] ),
547 be32_to_cpu ( in->dword[1] ) );
548 des_permute ( des_fp, tmp.byte, out->byte );
549 DBGC ( &tmp, "%08x%08x\n", be32_to_cpu ( out->dword[0] ),
550 be32_to_cpu ( out->dword[1] ) );
551}
552
553/**
554 * Rotate 28-bit word
555 *
556 * @v dword 28-bit dword value
557 * @ret dword Rotated 28-bit dword value
558 */
560 int32_t sdword;
561
562 /* Convert to native-endian */
563 sdword = be32_to_cpu ( dword );
564
565 /* Signed shift right by 4 places to copy bit 31 to bits 27:31 */
566 sdword >>= 4;
567
568 /* Rotate left */
569 sdword = rol32 ( sdword, 1 );
570
571 /* Shift left by 4 places to restore bit positions */
572 sdword <<= 4;
573
574 /* Convert back to big-endian */
575 dword = cpu_to_be32 ( sdword );
576
577 return dword;
578}
579
580/**
581 * Set key
582 *
583 * @v ctx Context
584 * @v key Key
585 * @v keylen Key length
586 * @ret rc Return status code
587 */
588static int des_setkey ( void *ctx, const void *key, size_t keylen ) {
589 struct des_context *des = ctx;
590 union des_round_key *rkey = des->rkey;
591 union des_block reg;
592 uint32_t schedule;
593
594 /* Validate key length */
595 if ( keylen != DES_BLOCKSIZE )
596 return -EINVAL;
597 DBGC ( des, "DES %p new key:\n", des );
598 DBGC_HDA ( des, 0, key, keylen );
599
600 /* Apply permuted choice 1 */
601 des_permute ( des_pc1c, key, reg.c.byte );
602 des_permute ( des_pc1d, key, reg.d.byte );
603 reg.d.byte[3] <<= 4; /* see comment for @c des_pc1d */
604 DBGC2 ( des, "DES %p C[ 0]=%07x D[ 0]=%07x\n",
605 des, ( be32_to_cpu ( reg.c.dword ) >> 4 ),
606 ( be32_to_cpu ( reg.d.dword ) >> 4 ) );
607
608 /* Generate round keys */
609 for ( schedule = DES_SCHEDULE ; schedule ; schedule >>= 1 ) {
610
611 /* Shift 28-bit words */
612 reg.c.dword = des_rol28 ( reg.c.dword );
613 reg.d.dword = des_rol28 ( reg.d.dword );
614
615 /* Skip rounds according to shift schedule */
616 if ( ! ( schedule & 1 ) )
617 continue;
618
619 /* Apply permuted choice 2 */
620 des_permute ( des_pc2, reg.byte, rkey->byte );
621 DBGC2 ( des, "DES %p C[%2zd]=%07x D[%2zd]=%07x K[%2zd]="
622 "%08x%08x\n", des, ( ( rkey - des->rkey ) + 1 ),
623 ( be32_to_cpu ( reg.c.dword ) >> 4 ),
624 ( ( rkey - des->rkey ) + 1 ),
625 ( be32_to_cpu ( reg.d.dword ) >> 4 ),
626 ( ( rkey - des->rkey ) + 1 ),
627 be32_to_cpu ( rkey->dword[0] ),
628 be32_to_cpu ( rkey->dword[1] ) );
629
630 /* Move to next key */
631 rkey++;
632 }
633
634 /* Sanity check */
635 assert ( rkey == &des->rkey[DES_ROUNDS] );
636
637 return 0;
638}
639
640/**
641 * Encrypt data
642 *
643 * @v ctx Context
644 * @v src Data to encrypt
645 * @v dst Buffer for encrypted data
646 * @v len Length of data
647 */
648static void des_encrypt ( void *ctx, const void *src, void *dst, size_t len ) {
649 struct des_context *des = ctx;
650
651 /* Sanity check */
652 assert ( len == DES_BLOCKSIZE );
653
654 /* Cipher using keys in forward direction */
655 des_rounds ( src, dst, &des->rkey[0], sizeof ( des->rkey[0] ) );
656}
657
658/**
659 * Decrypt data
660 *
661 * @v ctx Context
662 * @v src Data to decrypt
663 * @v dst Buffer for decrypted data
664 * @v len Length of data
665 */
666static void des_decrypt ( void *ctx, const void *src, void *dst, size_t len ) {
667 struct des_context *des = ctx;
668
669 /* Sanity check */
670 assert ( len == DES_BLOCKSIZE );
671
672 /* Cipher using keys in reverse direction */
673 des_rounds ( src, dst, &des->rkey[ DES_ROUNDS - 1 ],
674 -sizeof ( des->rkey[0] ) );
675}
676
677/** Basic DES algorithm */
679 .name = "des",
680 .ctxsize = sizeof ( struct des_context ),
681 .blocksize = DES_BLOCKSIZE,
682 .alignsize = 0,
683 .authsize = 0,
684 .setkey = des_setkey,
685 .setiv = cipher_null_setiv,
686 .encrypt = des_encrypt,
687 .decrypt = des_decrypt,
688 .auth = cipher_null_auth,
689};
690
691/* DES in Electronic Codebook mode */
694
695/* DES in Cipher Block Chaining mode */
union @162305117151260234136356364136041353210355154177 key
Sense key.
Definition scsi.h:3
struct golan_eq_context ctx
Definition CIB_PRM.h:0
__be32 in[4]
Definition CIB_PRM.h:7
__be32 out[4]
Definition CIB_PRM.h:8
unsigned int uint32_t
Definition stdint.h:12
signed int int32_t
Definition stdint.h:17
unsigned char uint8_t
Definition stdint.h:10
signed long ssize_t
Definition stdint.h:7
long index
Definition bigint.h:65
static const void * src
Definition string.h:48
#define assert(condition)
Assert a condition at run-time.
Definition assert.h:50
uint16_t offset
Offset to command line.
Definition bzimage.h:3
Cipher-block chaining.
#define CBC_CIPHER(_cbc_name, _cbc_cipher, _raw_cipher, _raw_context, _blocksize)
Create a cipher-block chaining mode of behaviour of an existing cipher.
Definition cbc.h:65
void cipher_null_setiv(void *ctx __unused, const void *iv __unused, size_t ivlen __unused)
Definition crypto_null.c:65
void cipher_null_auth(void *ctx __unused, void *auth __unused)
Definition crypto_null.c:80
static int des_setkey(void *ctx, const void *key, size_t keylen)
Set key.
Definition des.c:588
#define DES_GENERATOR(PERMUTATION, OFFSET, INV5, BIT5, INV4, BIT4, INV3, BIT3, INV2, BIT2, INV1, BIT1, INV0, BIT0)
Define a DES permutation generator.
Definition des.c:215
static void des_decrypt(void *ctx, const void *src, void *dst, size_t len)
Decrypt data.
Definition des.c:666
static uint32_t des_sbox(uint32_t in, const union des_round_key *rkey)
Perform DES S-box substitution.
Definition des.c:411
static void des_init(void)
Initialise permutations.
Definition des.c:361
static uint32_t des_rol28(uint32_t dword)
Rotate 28-bit word.
Definition des.c:559
static void des_permute(const uint8_t *permutation, const uint8_t *in, uint8_t *out)
Perform bit permutation.
Definition des.c:384
#define SBOX(x0, x1, x2, x3, x4, x5, x6, x7, x8, x9, xa, xb, xc, xd, xe, xf, y0, y1, y2, y3, y4, y5, y6, y7, y8, y9, ya, yb, yc, yd, ye, yf)
Define a row pair in a DES S-box.
Definition des.c:96
static uint8_t des_pc1c[29]
DES permuted choice 1 (PC1) "C" register.
Definition des.c:230
static const uint8_t des_s[8][32]
DES S-boxes S1..S8.
Definition des.c:104
static const uint8_t des_p[33]
DES data permutation (P)
Definition des.c:252
static void des_encrypt(void *ctx, const void *src, void *dst, size_t len)
Encrypt data.
Definition des.c:648
static void des_round(union des_block *block, const union des_round_key *rkey)
Perform a single DES round.
Definition des.c:494
struct cipher_algorithm des_algorithm
Basic DES algorithm.
Definition des.c:678
static struct des_generator des_generators[]
DES permutation generators.
Definition des.c:262
static void des_generate(struct des_generator *generator)
Generate DES permutation.
Definition des.c:307
#define DES_SCHEDULE
DES shift schedule.
Definition des.c:68
#define DES_PC2R(r1, c3, c2, c1, c0, r0)
Define six bits of permuted choice 2 (PC2)
Definition des.c:182
static uint8_t des_pc1d[33]
DES permuted choice 1 (PC1) "D" register.
Definition des.c:233
static uint8_t des_fp[65]
DES final / inverse initial permutation (FP / IP^-1)
Definition des.c:259
static uint8_t des_ip[65]
DES initial permutation (IP)
Definition des.c:249
static const uint8_t des_pc2[65]
DES permuted choice 2 (PC2)
Definition des.c:236
static void des_rounds(const union des_block *in, union des_block *out, const union des_round_key *rkey, ssize_t offset)
Perform all DES rounds.
Definition des.c:529
DES algorithm.
#define DES_BLOCKSIZE
DES blocksize.
Definition des.h:50
#define DES_ROUNDS
Number of DES rounds.
Definition des.h:77
struct cipher_algorithm des_cbc_algorithm
struct cipher_algorithm des_ecb_algorithm
ring len
Length.
Definition dwmac.h:226
Electronic codebook (ECB)
#define ECB_CIPHER(_ecb_name, _ecb_cipher, _raw_cipher, _raw_context, _blocksize)
Create a cipher-block chaining mode of behaviour of an existing cipher.
Definition ecb.h:29
Error codes.
#define DBGC2(...)
Definition compiler.h:522
#define DBGC2_HDA(...)
Definition compiler.h:523
#define DBGC(...)
Definition compiler.h:505
#define DBGC_HDA(...)
Definition compiler.h:506
#define INIT_NORMAL
Normal initialisation.
Definition init.h:32
#define FILE_LICENCE(_licence)
Declare a particular licence as applying to a file.
Definition compiler.h:896
#define EINVAL
Invalid argument.
Definition errno.h:429
#define FILE_SECBOOT(_status)
Declare a file's UEFI Secure Boot permission status.
Definition compiler.h:926
#define be32_to_cpu(value)
Definition byteswap.h:117
#define cpu_to_be32(value)
Definition byteswap.h:111
#define __attribute__(x)
Definition compiler.h:10
static unsigned int unsigned int bit
Definition bigint.h:392
Cryptographic API.
String functions.
#define __init_fn(init_order)
Declare an initialisation functon.
Definition init.h:24
unsigned long tmp
Definition linux_pci.h:65
uint8_t block[3][8]
DES-encrypted blocks.
Definition mschapv2.h:1
static unsigned int unsigned int reg
Definition myson.h:162
Bit operations.
unsigned long int dword
Definition smc9000.h:40
A cipher algorithm.
Definition crypto.h:51
DES context.
Definition des.h:80
union des_round_key rkey[DES_ROUNDS]
Round keys.
Definition des.h:82
A DES systematic permutation generator.
Definition des.c:199
uint32_t seed
Seed value.
Definition des.c:203
uint8_t * permutation
Permutation.
Definition des.c:201
An initialisation function.
Definition init.h:15
A DES 64-bit block.
Definition des.h:28
A DES 32-bit dword value.
Definition des.h:20
uint8_t byte[4]
Raw bytes.
Definition des.h:22
uint32_t dword
32-bit big-endian dword
Definition des.h:24
A DES round key.
Definition des.h:57
uint32_t dword[2]
32-bit big-endian dwords
Definition des.h:61
uint8_t byte[8]
Raw bytes.
Definition des.h:59
int8_t step[8]
6-bit step key byte
Definition des.h:73
static u32 ror32(u32 v, int bits)
Rotate 32-bit value right.
Definition wpa_tkip.c:162
static u32 rol32(u32 v, int bits)
Rotate 32-bit value left.
Definition wpa_tkip.c:174