Add memtest support.
[syslinux-debian/hramrach.git] / com32 / cmenu / libmenu / des.c
blob37148b243795aad68a7fbbf3606e7aaae6420070
1 /*
2 * FreeSec: libcrypt for NetBSD
4 * Copyright (c) 1994 David Burren
5 * All rights reserved.
7 * Adapted for FreeBSD-2.0 by Geoffrey M. Rehmet
8 * this file should now *only* export crypt(), in order to make
9 * binaries of libcrypt exportable from the USA
11 * Adapted for FreeBSD-4.0 by Mark R V Murray
12 * this file should now *only* export crypt_des(), in order to make
13 * a module that can be optionally included in libcrypt.
15 * Adapted for pxelinux menu environment by Th.Gebhardt
16 * removed dependencies of standard C libs
17 * added LOWSPACE option (using common space for different arrays)
19 * Redistribution and use in source and binary forms, with or without
20 * modification, are permitted provided that the following conditions
21 * are met:
22 * 1. Redistributions of source code must retain the above copyright
23 * notice, this list of conditions and the following disclaimer.
24 * 2. Redistributions in binary form must reproduce the above copyright
25 * notice, this list of conditions and the following disclaimer in the
26 * documentation and/or other materials provided with the distribution.
27 * 3. Neither the name of the author nor the names of other contributors
28 * may be used to endorse or promote products derived from this software
29 * without specific prior written permission.
31 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
32 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
33 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
34 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
35 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
36 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
37 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
38 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
39 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
40 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
41 * SUCH DAMAGE.
43 * This is an original implementation of the DES and the crypt(3) interfaces
44 * by David Burren <davidb@werj.com.au>.
46 * An excellent reference on the underlying algorithm (and related
47 * algorithms) is:
49 * B. Schneier, Applied Cryptography: protocols, algorithms,
50 * and source code in C, John Wiley & Sons, 1994.
52 * Note that in that book's description of DES the lookups for the initial,
53 * pbox, and final permutations are inverted (this has been brought to the
54 * attention of the author). A list of errata for this book has been
55 * posted to the sci.crypt newsgroup by the author and is available for FTP.
57 * ARCHITECTURE ASSUMPTIONS:
58 * It is assumed that the 8-byte arrays passed by reference can be
59 * addressed as arrays of u_int32_t's (ie. the CPU is not picky about
60 * alignment).
63 #define LOWSPACE
65 #ifndef NULL
66 #define NULL ((void *) 0)
67 #endif
69 typedef unsigned long my_u_int32_t;
70 typedef unsigned char my_u_char_t;
72 /* Re-entrantify me -- all this junk needs to be in
73 * struct crypt_data to make this really reentrant... */
74 static my_u_char_t inv_key_perm[64];
75 static my_u_char_t inv_comp_perm[56];
76 static my_u_char_t u_sbox[8][64];
77 static my_u_char_t un_pbox[32];
78 static my_u_int32_t en_keysl[16], en_keysr[16];
79 static my_u_int32_t de_keysl[16], de_keysr[16];
81 #ifndef LOWSPACE
82 static my_u_int32_t ip_maskl[8][256], ip_maskr[8][256];
83 static my_u_int32_t fp_maskl[8][256], fp_maskr[8][256];
84 static my_u_int32_t key_perm_maskl[8][128], key_perm_maskr[8][128];
85 static my_u_int32_t comp_maskl[8][128], comp_maskr[8][128];
86 #endif
88 static my_u_int32_t saltbits;
89 static my_u_int32_t old_salt;
90 static my_u_int32_t old_rawkey0, old_rawkey1;
92 #ifdef LOWSPACE
93 static my_u_int32_t common[8][256];
94 #endif
96 /* Static stuff that stays resident and doesn't change after
97 * being initialized, and therefore doesn't need to be made
98 * reentrant. */
99 static my_u_char_t init_perm[64], final_perm[64];
100 static my_u_char_t m_sbox[4][4096];
102 #ifndef LOWSPACE
103 static my_u_int32_t psbox[4][256];
104 #endif
106 /* A pile of data */
107 static const my_u_char_t ascii64[] =
108 "./0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";
110 static const my_u_char_t IP[64] = {
111 58, 50, 42, 34, 26, 18, 10, 2, 60, 52, 44, 36, 28, 20, 12, 4,
112 62, 54, 46, 38, 30, 22, 14, 6, 64, 56, 48, 40, 32, 24, 16, 8,
113 57, 49, 41, 33, 25, 17, 9, 1, 59, 51, 43, 35, 27, 19, 11, 3,
114 61, 53, 45, 37, 29, 21, 13, 5, 63, 55, 47, 39, 31, 23, 15, 7
117 static const my_u_char_t key_perm[56] = {
118 57, 49, 41, 33, 25, 17, 9, 1, 58, 50, 42, 34, 26, 18,
119 10, 2, 59, 51, 43, 35, 27, 19, 11, 3, 60, 52, 44, 36,
120 63, 55, 47, 39, 31, 23, 15, 7, 62, 54, 46, 38, 30, 22,
121 14, 6, 61, 53, 45, 37, 29, 21, 13, 5, 28, 20, 12, 4
124 static const my_u_char_t key_shifts[16] = {
125 1, 1, 2, 2, 2, 2, 2, 2, 1, 2, 2, 2, 2, 2, 2, 1
128 static const my_u_char_t comp_perm[48] = {
129 14, 17, 11, 24, 1, 5, 3, 28, 15, 6, 21, 10,
130 23, 19, 12, 4, 26, 8, 16, 7, 27, 20, 13, 2,
131 41, 52, 31, 37, 47, 55, 30, 40, 51, 45, 33, 48,
132 44, 49, 39, 56, 34, 53, 46, 42, 50, 36, 29, 32
136 * No E box is used, as it's replaced by some ANDs, shifts, and ORs.
139 static const my_u_char_t sbox[8][64] = {
141 14, 4, 13, 1, 2, 15, 11, 8, 3, 10, 6, 12, 5, 9, 0, 7,
142 0, 15, 7, 4, 14, 2, 13, 1, 10, 6, 12, 11, 9, 5, 3, 8,
143 4, 1, 14, 8, 13, 6, 2, 11, 15, 12, 9, 7, 3, 10, 5, 0,
144 15, 12, 8, 2, 4, 9, 1, 7, 5, 11, 3, 14, 10, 0, 6, 13},
146 15, 1, 8, 14, 6, 11, 3, 4, 9, 7, 2, 13, 12, 0, 5, 10,
147 3, 13, 4, 7, 15, 2, 8, 14, 12, 0, 1, 10, 6, 9, 11, 5,
148 0, 14, 7, 11, 10, 4, 13, 1, 5, 8, 12, 6, 9, 3, 2, 15,
149 13, 8, 10, 1, 3, 15, 4, 2, 11, 6, 7, 12, 0, 5, 14, 9},
151 10, 0, 9, 14, 6, 3, 15, 5, 1, 13, 12, 7, 11, 4, 2, 8,
152 13, 7, 0, 9, 3, 4, 6, 10, 2, 8, 5, 14, 12, 11, 15, 1,
153 13, 6, 4, 9, 8, 15, 3, 0, 11, 1, 2, 12, 5, 10, 14, 7,
154 1, 10, 13, 0, 6, 9, 8, 7, 4, 15, 14, 3, 11, 5, 2, 12},
156 7, 13, 14, 3, 0, 6, 9, 10, 1, 2, 8, 5, 11, 12, 4, 15,
157 13, 8, 11, 5, 6, 15, 0, 3, 4, 7, 2, 12, 1, 10, 14, 9,
158 10, 6, 9, 0, 12, 11, 7, 13, 15, 1, 3, 14, 5, 2, 8, 4,
159 3, 15, 0, 6, 10, 1, 13, 8, 9, 4, 5, 11, 12, 7, 2, 14},
161 2, 12, 4, 1, 7, 10, 11, 6, 8, 5, 3, 15, 13, 0, 14, 9,
162 14, 11, 2, 12, 4, 7, 13, 1, 5, 0, 15, 10, 3, 9, 8, 6,
163 4, 2, 1, 11, 10, 13, 7, 8, 15, 9, 12, 5, 6, 3, 0, 14,
164 11, 8, 12, 7, 1, 14, 2, 13, 6, 15, 0, 9, 10, 4, 5, 3},
166 12, 1, 10, 15, 9, 2, 6, 8, 0, 13, 3, 4, 14, 7, 5, 11,
167 10, 15, 4, 2, 7, 12, 9, 5, 6, 1, 13, 14, 0, 11, 3, 8,
168 9, 14, 15, 5, 2, 8, 12, 3, 7, 0, 4, 10, 1, 13, 11, 6,
169 4, 3, 2, 12, 9, 5, 15, 10, 11, 14, 1, 7, 6, 0, 8, 13},
171 4, 11, 2, 14, 15, 0, 8, 13, 3, 12, 9, 7, 5, 10, 6, 1,
172 13, 0, 11, 7, 4, 9, 1, 10, 14, 3, 5, 12, 2, 15, 8, 6,
173 1, 4, 11, 13, 12, 3, 7, 14, 10, 15, 6, 8, 0, 5, 9, 2,
174 6, 11, 13, 8, 1, 4, 10, 7, 9, 5, 0, 15, 14, 2, 3, 12},
176 13, 2, 8, 4, 6, 15, 11, 1, 10, 9, 3, 14, 5, 0, 12, 7,
177 1, 15, 13, 8, 10, 3, 7, 4, 12, 5, 6, 11, 0, 14, 9, 2,
178 7, 11, 4, 1, 9, 12, 14, 2, 0, 6, 10, 13, 15, 3, 5, 8,
179 2, 1, 14, 7, 4, 10, 8, 13, 15, 12, 9, 0, 3, 5, 6, 11}
182 static const my_u_char_t pbox[32] = {
183 16, 7, 20, 21, 29, 12, 28, 17, 1, 15, 23, 26, 5, 18, 31, 10,
184 2, 8, 24, 14, 32, 27, 3, 9, 19, 13, 30, 6, 22, 11, 4, 25
187 static const my_u_int32_t bits32[32] = {
188 0x80000000, 0x40000000, 0x20000000, 0x10000000,
189 0x08000000, 0x04000000, 0x02000000, 0x01000000,
190 0x00800000, 0x00400000, 0x00200000, 0x00100000,
191 0x00080000, 0x00040000, 0x00020000, 0x00010000,
192 0x00008000, 0x00004000, 0x00002000, 0x00001000,
193 0x00000800, 0x00000400, 0x00000200, 0x00000100,
194 0x00000080, 0x00000040, 0x00000020, 0x00000010,
195 0x00000008, 0x00000004, 0x00000002, 0x00000001
198 static const my_u_int32_t bits28[28] = {
199 0x08000000, 0x04000000, 0x02000000, 0x01000000,
200 0x00800000, 0x00400000, 0x00200000, 0x00100000,
201 0x00080000, 0x00040000, 0x00020000, 0x00010000,
202 0x00008000, 0x00004000, 0x00002000, 0x00001000,
203 0x00000800, 0x00000400, 0x00000200, 0x00000100,
204 0x00000080, 0x00000040, 0x00000020, 0x00000010,
205 0x00000008, 0x00000004, 0x00000002, 0x00000001
208 static const my_u_int32_t bits24[24] = {
209 0x00800000, 0x00400000, 0x00200000, 0x00100000,
210 0x00080000, 0x00040000, 0x00020000, 0x00010000,
211 0x00008000, 0x00004000, 0x00002000, 0x00001000,
212 0x00000800, 0x00000400, 0x00000200, 0x00000100,
213 0x00000080, 0x00000040, 0x00000020, 0x00000010,
214 0x00000008, 0x00000004, 0x00000002, 0x00000001
217 static const my_u_char_t bits8[8] =
218 { 0x80, 0x40, 0x20, 0x10, 0x08, 0x04, 0x02, 0x01 };
219 // static const my_u_int32_t *bits28, *bits24;
221 static int ascii_to_bin(char ch)
223 if (ch > 'z')
224 return (0);
225 if (ch >= 'a')
226 return (ch - 'a' + 38);
227 if (ch > 'Z')
228 return (0);
229 if (ch >= 'A')
230 return (ch - 'A' + 12);
231 if (ch > '9')
232 return (0);
233 if (ch >= '.')
234 return (ch - '.');
235 return (0);
238 static void des_init(void)
241 #ifdef LOWSPACE
242 int i, j, b;
243 #else
244 int i, j, b, k, inbit, obit;
245 my_u_int32_t *p, *il, *ir, *fl, *fr;
246 #endif
247 static int des_initialised = 0;
249 if (des_initialised == 1)
250 return;
252 old_rawkey0 = old_rawkey1 = 0L;
253 saltbits = 0L;
254 old_salt = 0L;
255 // bits24 = (bits28 = bits32 + 4) + 4;
258 * Invert the S-boxes, reordering the input bits.
260 for (i = 0; i < 8; i++)
261 for (j = 0; j < 64; j++) {
262 b = (j & 0x20) | ((j & 1) << 4) | ((j >> 1) & 0xf);
263 u_sbox[i][j] = sbox[i][b];
267 * Convert the inverted S-boxes into 4 arrays of 8 bits.
268 * Each will handle 12 bits of the S-box input.
270 for (b = 0; b < 4; b++)
271 for (i = 0; i < 64; i++)
272 for (j = 0; j < 64; j++)
273 m_sbox[b][(i << 6) | j] =
274 (my_u_char_t) ((u_sbox[(b << 1)][i] << 4) |
275 u_sbox[(b << 1) + 1][j]);
278 * Set up the initial & final permutations into a useful form, and
279 * initialise the inverted key permutation.
281 for (i = 0; i < 64; i++) {
282 init_perm[final_perm[i] = IP[i] - 1] = (my_u_char_t) i;
283 inv_key_perm[i] = 255;
287 * Invert the key permutation and initialise the inverted key
288 * compression permutation.
290 for (i = 0; i < 56; i++) {
291 inv_key_perm[key_perm[i] - 1] = (my_u_char_t) i;
292 inv_comp_perm[i] = 255;
296 * Invert the key compression permutation.
298 for (i = 0; i < 48; i++) {
299 inv_comp_perm[comp_perm[i] - 1] = (my_u_char_t) i;
303 * Set up the OR-mask arrays for the initial and final permutations,
304 * and for the key initial and compression permutations.
307 #ifndef LOWSPACE
308 for (k = 0; k < 8; k++) {
309 for (i = 0; i < 256; i++) {
310 *(il = &ip_maskl[k][i]) = 0L;
311 *(ir = &ip_maskr[k][i]) = 0L;
312 *(fl = &fp_maskl[k][i]) = 0L;
313 *(fr = &fp_maskr[k][i]) = 0L;
314 for (j = 0; j < 8; j++) {
315 inbit = 8 * k + j;
316 if (i & bits8[j]) {
317 if ((obit = init_perm[inbit]) < 32)
318 *il |= bits32[obit];
319 else
320 *ir |= bits32[obit - 32];
321 if ((obit = final_perm[inbit]) < 32)
322 *fl |= bits32[obit];
323 else
324 *fr |= bits32[obit - 32];
328 for (i = 0; i < 128; i++) {
329 *(il = &key_perm_maskl[k][i]) = 0L;
330 *(ir = &key_perm_maskr[k][i]) = 0L;
331 for (j = 0; j < 7; j++) {
332 inbit = 8 * k + j;
333 if (i & bits8[j + 1]) {
334 if ((obit = inv_key_perm[inbit]) == 255)
335 continue;
336 if (obit < 28)
337 *il |= bits28[obit];
338 else
339 *ir |= bits28[obit - 28];
342 *(il = &comp_maskl[k][i]) = 0L;
343 *(ir = &comp_maskr[k][i]) = 0L;
344 for (j = 0; j < 7; j++) {
345 inbit = 7 * k + j;
346 if (i & bits8[j + 1]) {
347 if ((obit = inv_comp_perm[inbit]) == 255)
348 continue;
349 if (obit < 24)
350 *il |= bits24[obit];
351 else
352 *ir |= bits24[obit - 24];
357 #endif
360 * Invert the P-box permutation, and convert into OR-masks for
361 * handling the output of the S-box arrays setup above.
363 for (i = 0; i < 32; i++)
364 un_pbox[pbox[i] - 1] = (my_u_char_t) i;
366 #ifndef LOWSPACE
367 for (b = 0; b < 4; b++)
368 for (i = 0; i < 256; i++) {
369 *(p = &psbox[b][i]) = 0L;
370 for (j = 0; j < 8; j++) {
371 if (i & bits8[j])
372 *p |= bits32[un_pbox[8 * b + j]];
375 #endif
376 des_initialised = 1;
379 #ifdef LOWSPACE
381 static void setup_ip_maskl(void)
383 int i, j, k, inbit, obit;
384 my_u_int32_t *il;
386 for (k = 0; k < 8; k++) {
387 for (i = 0; i < 256; i++) {
388 *(il = &common[k][i]) = 0L;
389 for (j = 0; j < 8; j++) {
390 inbit = 8 * k + j;
391 if (i & bits8[j]) {
392 if ((obit = init_perm[inbit]) < 32)
393 *il |= bits32[obit];
400 static void setup_ip_maskr(void)
402 int i, j, k, inbit, obit;
403 my_u_int32_t *ir;
405 for (k = 0; k < 8; k++) {
406 for (i = 0; i < 256; i++) {
407 *(ir = &common[k][i]) = 0L;
408 for (j = 0; j < 8; j++) {
409 inbit = 8 * k + j;
410 if (i & bits8[j]) {
411 if ((obit = init_perm[inbit]) >= 32)
412 *ir |= bits32[obit - 32];
419 static void setup_fp_maskl(void)
421 int i, j, k, inbit, obit;
422 my_u_int32_t *fl;
424 for (k = 0; k < 8; k++) {
425 for (i = 0; i < 256; i++) {
426 *(fl = &common[k][i]) = 0L;
427 for (j = 0; j < 8; j++) {
428 inbit = 8 * k + j;
429 if (i & bits8[j]) {
430 if ((obit = final_perm[inbit]) < 32)
431 *fl |= bits32[obit];
438 static void setup_fp_maskr(void)
440 int i, j, k, inbit, obit;
441 my_u_int32_t *fr;
443 for (k = 0; k < 8; k++) {
444 for (i = 0; i < 256; i++) {
445 *(fr = &common[k][i]) = 0L;
446 for (j = 0; j < 8; j++) {
447 inbit = 8 * k + j;
448 if (i & bits8[j]) {
449 if ((obit = final_perm[inbit]) >= 32)
450 *fr |= bits32[obit - 32];
457 static void setup_key_perm_maskl(void)
459 int i, j, k, inbit, obit;
460 my_u_int32_t *il;
462 for (k = 0; k < 8; k++) {
463 for (i = 0; i < 128; i++) {
464 *(il = &common[k][i]) = 0L;
465 for (j = 0; j < 7; j++) {
466 inbit = 8 * k + j;
467 if (i & bits8[j + 1]) {
468 if ((obit = inv_key_perm[inbit]) == 255)
469 continue;
470 if (obit < 28)
471 *il |= bits28[obit];
478 static void setup_key_perm_maskr(void)
480 int i, j, k, inbit, obit;
481 my_u_int32_t *ir;
483 for (k = 0; k < 8; k++) {
484 for (i = 0; i < 128; i++) {
485 *(ir = &common[k][i]) = 0L;
486 for (j = 0; j < 7; j++) {
487 inbit = 8 * k + j;
488 if (i & bits8[j + 1]) {
489 if ((obit = inv_key_perm[inbit]) == 255)
490 continue;
491 if (obit >= 28)
492 *ir |= bits28[obit - 28];
499 static void setup_comp_maskl(void)
501 int i, j, k, inbit, obit;
502 my_u_int32_t *il;
504 for (k = 0; k < 8; k++) {
505 for (i = 0; i < 128; i++) {
506 *(il = &common[k][i]) = 0L;
507 for (j = 0; j < 7; j++) {
508 inbit = 7 * k + j;
509 if (i & bits8[j + 1]) {
510 if ((obit = inv_comp_perm[inbit]) == 255)
511 continue;
512 if (obit < 24)
513 *il |= bits24[obit];
520 static void setup_comp_maskr(void)
522 int i, j, k, inbit, obit;
523 my_u_int32_t *ir;
525 for (k = 0; k < 8; k++) {
526 for (i = 0; i < 128; i++) {
527 *(ir = &common[k][i]) = 0L;
528 for (j = 0; j < 7; j++) {
529 inbit = 7 * k + j;
530 if (i & bits8[j + 1]) {
531 if ((obit = inv_comp_perm[inbit]) == 255)
532 continue;
533 if (obit >= 24)
534 *ir |= bits24[obit - 24];
541 static void setup_psbox(void)
543 int i, j, b;
544 my_u_int32_t *p;
546 for (b = 0; b < 4; b++)
547 for (i = 0; i < 256; i++) {
548 *(p = &common[b][i]) = 0L;
549 for (j = 0; j < 8; j++) {
550 if (i & bits8[j])
551 *p |= bits32[un_pbox[8 * b + j]];
556 #endif
558 static void setup_salt(my_u_int32_t salt)
560 my_u_int32_t obit, saltbit;
561 int i;
563 if (salt == old_salt)
564 return;
565 old_salt = salt;
567 saltbits = 0L;
568 saltbit = 1;
569 obit = 0x800000;
570 for (i = 0; i < 24; i++) {
571 if (salt & saltbit)
572 saltbits |= obit;
573 saltbit <<= 1;
574 obit >>= 1;
578 static my_u_int32_t char_to_int(const char *key)
580 my_u_int32_t byte0, byte1, byte2, byte3;
581 byte0 = (my_u_int32_t) (my_u_char_t) key[0];
582 byte1 = (my_u_int32_t) (my_u_char_t) key[1];
583 byte2 = (my_u_int32_t) (my_u_char_t) key[2];
584 byte3 = (my_u_int32_t) (my_u_char_t) key[3];
586 return byte0 << 24 | byte1 << 16 | byte2 << 8 | byte3;
589 static int des_setkey(const char *key)
591 my_u_int32_t k0, k1, rawkey0, rawkey1;
592 int shifts, round;
594 des_init();
596 /* rawkey0 = ntohl(*(const my_u_int32_t *) key);
597 * rawkey1 = ntohl(*(const my_u_int32_t *) (key + 4));
600 rawkey0 = char_to_int(key);
601 rawkey1 = char_to_int(key + 4);
603 if ((rawkey0 | rawkey1)
604 && rawkey0 == old_rawkey0 && rawkey1 == old_rawkey1) {
606 * Already setup for this key.
607 * This optimisation fails on a zero key (which is weak and
608 * has bad parity anyway) in order to simplify the starting
609 * conditions.
611 return (0);
613 old_rawkey0 = rawkey0;
614 old_rawkey1 = rawkey1;
617 * Do key permutation and split into two 28-bit subkeys.
620 #ifdef LOWSPACE
621 setup_key_perm_maskl();
622 k0 = common[0][rawkey0 >> 25]
623 | common[1][(rawkey0 >> 17) & 0x7f]
624 | common[2][(rawkey0 >> 9) & 0x7f]
625 | common[3][(rawkey0 >> 1) & 0x7f]
626 | common[4][rawkey1 >> 25]
627 | common[5][(rawkey1 >> 17) & 0x7f]
628 | common[6][(rawkey1 >> 9) & 0x7f]
629 | common[7][(rawkey1 >> 1) & 0x7f];
630 setup_key_perm_maskr();
631 k1 = common[0][rawkey0 >> 25]
632 | common[1][(rawkey0 >> 17) & 0x7f]
633 | common[2][(rawkey0 >> 9) & 0x7f]
634 | common[3][(rawkey0 >> 1) & 0x7f]
635 | common[4][rawkey1 >> 25]
636 | common[5][(rawkey1 >> 17) & 0x7f]
637 | common[6][(rawkey1 >> 9) & 0x7f]
638 | common[7][(rawkey1 >> 1) & 0x7f];
639 #else
640 k0 = key_perm_maskl[0][rawkey0 >> 25]
641 | key_perm_maskl[1][(rawkey0 >> 17) & 0x7f]
642 | key_perm_maskl[2][(rawkey0 >> 9) & 0x7f]
643 | key_perm_maskl[3][(rawkey0 >> 1) & 0x7f]
644 | key_perm_maskl[4][rawkey1 >> 25]
645 | key_perm_maskl[5][(rawkey1 >> 17) & 0x7f]
646 | key_perm_maskl[6][(rawkey1 >> 9) & 0x7f]
647 | key_perm_maskl[7][(rawkey1 >> 1) & 0x7f];
648 k1 = key_perm_maskr[0][rawkey0 >> 25]
649 | key_perm_maskr[1][(rawkey0 >> 17) & 0x7f]
650 | key_perm_maskr[2][(rawkey0 >> 9) & 0x7f]
651 | key_perm_maskr[3][(rawkey0 >> 1) & 0x7f]
652 | key_perm_maskr[4][rawkey1 >> 25]
653 | key_perm_maskr[5][(rawkey1 >> 17) & 0x7f]
654 | key_perm_maskr[6][(rawkey1 >> 9) & 0x7f]
655 | key_perm_maskr[7][(rawkey1 >> 1) & 0x7f];
656 #endif
659 * Rotate subkeys and do compression permutation.
661 shifts = 0;
662 for (round = 0; round < 16; round++) {
663 my_u_int32_t t0, t1;
665 shifts += key_shifts[round];
667 t0 = (k0 << shifts) | (k0 >> (28 - shifts));
668 t1 = (k1 << shifts) | (k1 >> (28 - shifts));
670 #ifdef LOWSPACE
671 setup_comp_maskl();
672 de_keysl[15 - round] = en_keysl[round] = common[0][(t0 >> 21) & 0x7f]
673 | common[1][(t0 >> 14) & 0x7f]
674 | common[2][(t0 >> 7) & 0x7f]
675 | common[3][t0 & 0x7f]
676 | common[4][(t1 >> 21) & 0x7f]
677 | common[5][(t1 >> 14) & 0x7f]
678 | common[6][(t1 >> 7) & 0x7f]
679 | common[7][t1 & 0x7f];
681 setup_comp_maskr();
682 de_keysr[15 - round] = en_keysr[round] = common[0][(t0 >> 21) & 0x7f]
683 | common[1][(t0 >> 14) & 0x7f]
684 | common[2][(t0 >> 7) & 0x7f]
685 | common[3][t0 & 0x7f]
686 | common[4][(t1 >> 21) & 0x7f]
687 | common[5][(t1 >> 14) & 0x7f]
688 | common[6][(t1 >> 7) & 0x7f]
689 | common[7][t1 & 0x7f];
690 #else
691 de_keysl[15 - round] =
692 en_keysl[round] = comp_maskl[0][(t0 >> 21) & 0x7f]
693 | comp_maskl[1][(t0 >> 14) & 0x7f]
694 | comp_maskl[2][(t0 >> 7) & 0x7f]
695 | comp_maskl[3][t0 & 0x7f]
696 | comp_maskl[4][(t1 >> 21) & 0x7f]
697 | comp_maskl[5][(t1 >> 14) & 0x7f]
698 | comp_maskl[6][(t1 >> 7) & 0x7f]
699 | comp_maskl[7][t1 & 0x7f];
701 de_keysr[15 - round] =
702 en_keysr[round] = comp_maskr[0][(t0 >> 21) & 0x7f]
703 | comp_maskr[1][(t0 >> 14) & 0x7f]
704 | comp_maskr[2][(t0 >> 7) & 0x7f]
705 | comp_maskr[3][t0 & 0x7f]
706 | comp_maskr[4][(t1 >> 21) & 0x7f]
707 | comp_maskr[5][(t1 >> 14) & 0x7f]
708 | comp_maskr[6][(t1 >> 7) & 0x7f]
709 | comp_maskr[7][t1 & 0x7f];
710 #endif
712 return (0);
715 static int
716 do_des(my_u_int32_t l_in, my_u_int32_t r_in, my_u_int32_t * l_out,
717 my_u_int32_t * r_out, int count)
720 * l_in, r_in, l_out, and r_out are in pseudo-"big-endian" format.
722 my_u_int32_t l, r, *kl, *kr, *kl1, *kr1;
723 my_u_int32_t f, r48l, r48r;
724 int round;
726 if (count == 0) {
727 return (1);
728 } else if (count > 0) {
730 * Encrypting
732 kl1 = en_keysl;
733 kr1 = en_keysr;
734 } else {
736 * Decrypting
738 count = -count;
739 kl1 = de_keysl;
740 kr1 = de_keysr;
744 * Do initial permutation (IP).
747 #ifdef LOWSPACE
748 setup_ip_maskl();
749 l = common[0][l_in >> 24]
750 | common[1][(l_in >> 16) & 0xff]
751 | common[2][(l_in >> 8) & 0xff]
752 | common[3][l_in & 0xff]
753 | common[4][r_in >> 24]
754 | common[5][(r_in >> 16) & 0xff]
755 | common[6][(r_in >> 8) & 0xff]
756 | common[7][r_in & 0xff];
757 setup_ip_maskr();
758 r = common[0][l_in >> 24]
759 | common[1][(l_in >> 16) & 0xff]
760 | common[2][(l_in >> 8) & 0xff]
761 | common[3][l_in & 0xff]
762 | common[4][r_in >> 24]
763 | common[5][(r_in >> 16) & 0xff]
764 | common[6][(r_in >> 8) & 0xff]
765 | common[7][r_in & 0xff];
766 #else
767 l = ip_maskl[0][l_in >> 24]
768 | ip_maskl[1][(l_in >> 16) & 0xff]
769 | ip_maskl[2][(l_in >> 8) & 0xff]
770 | ip_maskl[3][l_in & 0xff]
771 | ip_maskl[4][r_in >> 24]
772 | ip_maskl[5][(r_in >> 16) & 0xff]
773 | ip_maskl[6][(r_in >> 8) & 0xff]
774 | ip_maskl[7][r_in & 0xff];
775 r = ip_maskr[0][l_in >> 24]
776 | ip_maskr[1][(l_in >> 16) & 0xff]
777 | ip_maskr[2][(l_in >> 8) & 0xff]
778 | ip_maskr[3][l_in & 0xff]
779 | ip_maskr[4][r_in >> 24]
780 | ip_maskr[5][(r_in >> 16) & 0xff]
781 | ip_maskr[6][(r_in >> 8) & 0xff]
782 | ip_maskr[7][r_in & 0xff];
783 #endif
785 while (count--) {
787 * Do each round.
789 kl = kl1;
790 kr = kr1;
791 round = 16;
792 while (round--) {
794 * Expand R to 48 bits (simulate the E-box).
796 r48l = ((r & 0x00000001) << 23)
797 | ((r & 0xf8000000) >> 9)
798 | ((r & 0x1f800000) >> 11)
799 | ((r & 0x01f80000) >> 13)
800 | ((r & 0x001f8000) >> 15);
802 r48r = ((r & 0x0001f800) << 7)
803 | ((r & 0x00001f80) << 5)
804 | ((r & 0x000001f8) << 3)
805 | ((r & 0x0000001f) << 1)
806 | ((r & 0x80000000) >> 31);
808 * Do salting for crypt() and friends, and
809 * XOR with the permuted key.
811 f = (r48l ^ r48r) & saltbits;
812 r48l ^= f ^ *kl++;
813 r48r ^= f ^ *kr++;
815 * Do sbox lookups (which shrink it back to 32 bits)
816 * and do the pbox permutation at the same time.
819 #ifdef LOWSPACE
820 setup_psbox();
821 f = common[0][m_sbox[0][r48l >> 12]]
822 | common[1][m_sbox[1][r48l & 0xfff]]
823 | common[2][m_sbox[2][r48r >> 12]]
824 | common[3][m_sbox[3][r48r & 0xfff]];
825 #else
826 f = psbox[0][m_sbox[0][r48l >> 12]]
827 | psbox[1][m_sbox[1][r48l & 0xfff]]
828 | psbox[2][m_sbox[2][r48r >> 12]]
829 | psbox[3][m_sbox[3][r48r & 0xfff]];
830 #endif
832 * Now that we've permuted things, complete f().
834 f ^= l;
835 l = r;
836 r = f;
838 r = l;
839 l = f;
842 * Do final permutation (inverse of IP).
845 #ifdef LOWSPACE
846 setup_fp_maskl();
847 *l_out = common[0][l >> 24]
848 | common[1][(l >> 16) & 0xff]
849 | common[2][(l >> 8) & 0xff]
850 | common[3][l & 0xff]
851 | common[4][r >> 24]
852 | common[5][(r >> 16) & 0xff]
853 | common[6][(r >> 8) & 0xff]
854 | common[7][r & 0xff];
855 setup_fp_maskr();
856 *r_out = common[0][l >> 24]
857 | common[1][(l >> 16) & 0xff]
858 | common[2][(l >> 8) & 0xff]
859 | common[3][l & 0xff]
860 | common[4][r >> 24]
861 | common[5][(r >> 16) & 0xff]
862 | common[6][(r >> 8) & 0xff]
863 | common[7][r & 0xff];
864 #else
865 *l_out = fp_maskl[0][l >> 24]
866 | fp_maskl[1][(l >> 16) & 0xff]
867 | fp_maskl[2][(l >> 8) & 0xff]
868 | fp_maskl[3][l & 0xff]
869 | fp_maskl[4][r >> 24]
870 | fp_maskl[5][(r >> 16) & 0xff]
871 | fp_maskl[6][(r >> 8) & 0xff]
872 | fp_maskl[7][r & 0xff];
873 *r_out = fp_maskr[0][l >> 24]
874 | fp_maskr[1][(l >> 16) & 0xff]
875 | fp_maskr[2][(l >> 8) & 0xff]
876 | fp_maskr[3][l & 0xff]
877 | fp_maskr[4][r >> 24]
878 | fp_maskr[5][(r >> 16) & 0xff]
879 | fp_maskr[6][(r >> 8) & 0xff]
880 | fp_maskr[7][r & 0xff];
881 #endif
882 return (0);
885 #if 0
886 static int des_cipher(const char *in, char *out, my_u_int32_t salt, int count)
888 my_u_int32_t l_out, r_out, rawl, rawr;
889 int retval;
890 union {
891 my_u_int32_t *ui32;
892 const char *c;
893 } trans;
895 des_init();
897 setup_salt(salt);
899 trans.c = in;
900 rawl = ntohl(*trans.ui32++);
901 rawr = ntohl(*trans.ui32);
903 retval = do_des(rawl, rawr, &l_out, &r_out, count);
905 trans.c = out;
906 *trans.ui32++ = htonl(l_out);
907 *trans.ui32 = htonl(r_out);
908 return (retval);
910 #endif
912 void setkey(const char *key)
914 int i, j;
915 char *p, packed_keys[8];
917 p = packed_keys;
919 for (i = 0; i < 8; i++) {
920 p[i] = 0;
921 for (j = 0; j < 8; j++)
922 if (*key++ & 1)
923 p[i] |= bits8[j];
925 des_setkey(p);
928 void encrypt(char *block, int flag)
930 my_u_int32_t io[2];
931 my_u_char_t *p;
932 int i, j;
934 des_init();
936 setup_salt(0L);
937 p = (my_u_char_t *)block;
938 for (i = 0; i < 2; i++) {
939 io[i] = 0L;
940 for (j = 0; j < 32; j++)
941 if (*p++ & 1)
942 io[i] |= bits32[j];
944 do_des(io[0], io[1], io, io + 1, flag ? -1 : 1);
945 for (i = 0; i < 2; i++)
946 for (j = 0; j < 32; j++)
947 block[(i << 5) | j] = (io[i] & bits32[j]) ? 1 : 0;
950 char *crypt(const char *key, const char *setting)
952 my_u_int32_t count, salt, l, r0, r1, keybuf[2];
953 my_u_char_t *p, *q;
954 static char output[21];
956 des_init();
959 * Copy the key, shifting each character up by one bit
960 * and padding with zeros.
962 q = (my_u_char_t *) keybuf;
963 while (q - (my_u_char_t *) keybuf - 8) {
964 *q++ = *key << 1;
965 if (*(q - 1))
966 key++;
968 if (des_setkey((char *)keybuf))
969 return (NULL);
971 #if 0
972 if (*setting == _PASSWORD_EFMT1) {
973 int i;
975 * "new"-style:
976 * setting - underscore, 4 bytes of count, 4 bytes of salt
977 * key - unlimited characters
979 for (i = 1, count = 0L; i < 5; i++)
980 count |= ascii_to_bin(setting[i]) << ((i - 1) * 6);
982 for (i = 5, salt = 0L; i < 9; i++)
983 salt |= ascii_to_bin(setting[i]) << ((i - 5) * 6);
985 while (*key) {
987 * Encrypt the key with itself.
989 if (des_cipher((char *)keybuf, (char *)keybuf, 0L, 1))
990 return (NULL);
992 * And XOR with the next 8 characters of the key.
994 q = (my_u_char_t *) keybuf;
995 while (q - (my_u_char_t *) keybuf - 8 && *key)
996 *q++ ^= *key++ << 1;
998 if (des_setkey((char *)keybuf))
999 return (NULL);
1001 strncpy(output, setting, 9);
1004 * Double check that we weren't given a short setting.
1005 * If we were, the above code will probably have created
1006 * wierd values for count and salt, but we don't really care.
1007 * Just make sure the output string doesn't have an extra
1008 * NUL in it.
1010 output[9] = '\0';
1011 p = (my_u_char_t *) output + strlen(output);
1012 } else
1013 #endif
1016 * "old"-style:
1017 * setting - 2 bytes of salt
1018 * key - up to 8 characters
1020 count = 25;
1022 salt = (ascii_to_bin(setting[1]) << 6)
1023 | ascii_to_bin(setting[0]);
1025 output[0] = setting[0];
1027 * If the encrypted password that the salt was extracted from
1028 * is only 1 character long, the salt will be corrupted. We
1029 * need to ensure that the output string doesn't have an extra
1030 * NUL in it!
1032 output[1] = setting[1] ? setting[1] : output[0];
1034 p = (my_u_char_t *) output + 2;
1036 setup_salt(salt);
1038 * Do it.
1040 if (do_des(0L, 0L, &r0, &r1, (int)count))
1041 return (NULL);
1043 * Now encode the result...
1045 l = (r0 >> 8);
1046 *p++ = ascii64[(l >> 18) & 0x3f];
1047 *p++ = ascii64[(l >> 12) & 0x3f];
1048 *p++ = ascii64[(l >> 6) & 0x3f];
1049 *p++ = ascii64[l & 0x3f];
1051 l = (r0 << 16) | ((r1 >> 16) & 0xffff);
1052 *p++ = ascii64[(l >> 18) & 0x3f];
1053 *p++ = ascii64[(l >> 12) & 0x3f];
1054 *p++ = ascii64[(l >> 6) & 0x3f];
1055 *p++ = ascii64[l & 0x3f];
1057 l = r1 << 2;
1058 *p++ = ascii64[(l >> 12) & 0x3f];
1059 *p++ = ascii64[(l >> 6) & 0x3f];
1060 *p++ = ascii64[l & 0x3f];
1061 *p = 0;
1063 return (output);