1 /*
2 * CDDL HEADER START
3 *
4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License (the "License").
6 * You may not use this file except in compliance with the License.
7 *
8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 * or http://www.opensolaris.org/os/licensing.
10 * See the License for the specific language governing permissions
11 * and limitations under the License.
12 *
13 * When distributing Covered Code, include this CDDL HEADER in each
14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 * If applicable, add the following below this CDDL HEADER, with the
16 * fields enclosed by brackets "[]" replaced with your own identifying
17 * information: Portions Copyright [yyyy] [name of copyright owner]
18 *
19 * CDDL HEADER END
20 */
21
22 /*
23 * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
24 * Use is subject to license terms.
25 */
26
27 /* Copyright (c) 1988 AT&T */
28 /* All Rights Reserved */
29
30 #pragma ident "%Z%%M% %I% %E% SMI"
31
32 #pragma weak _des_crypt = des_crypt
33 #pragma weak _des_encrypt = des_encrypt
34 #pragma weak _des_setkey = des_setkey
35
36 #include <sys/types.h>
37 #include <crypt.h>
38 #include "des_soft.h"
39
40 #include <stdlib.h>
41 #include <thread.h>
42 #include <pthread.h>
43 #include <sys/types.h>
44
45 /* EXPORT DELETE START */
46 /*
47 * This program implements the
48 * Proposed Federal Information Processing
49 * Data Encryption Standard.
50 * See Federal Register, March 17, 1975 (40FR12134)
51 */
52
53 /*
54 * Initial permutation,
55 */
56 static char IP[] = {
57 58, 50, 42, 34, 26, 18, 10, 2,
58 60, 52, 44, 36, 28, 20, 12, 4,
59 62, 54, 46, 38, 30, 22, 14, 6,
60 64, 56, 48, 40, 32, 24, 16, 8,
61 57, 49, 41, 33, 25, 17, 9, 1,
62 59, 51, 43, 35, 27, 19, 11, 3,
63 61, 53, 45, 37, 29, 21, 13, 5,
64 63, 55, 47, 39, 31, 23, 15, 7,
65 };
66
67 /*
68 * Final permutation, FP = IP^(-1)
69 */
70 static char FP[] = {
71 40, 8, 48, 16, 56, 24, 64, 32,
72 39, 7, 47, 15, 55, 23, 63, 31,
73 38, 6, 46, 14, 54, 22, 62, 30,
74 37, 5, 45, 13, 53, 21, 61, 29,
75 36, 4, 44, 12, 52, 20, 60, 28,
76 35, 3, 43, 11, 51, 19, 59, 27,
77 34, 2, 42, 10, 50, 18, 58, 26,
78 33, 1, 41, 9, 49, 17, 57, 25,
79 };
80
81 /*
82 * Permuted-choice 1 from the key bits
83 * to yield C and D.
84 * Note that bits 8, 16... are left out:
85 * They are intended for a parity check.
86 */
87 static char PC1_C[] = {
88 57, 49, 41, 33, 25, 17, 9,
89 1, 58, 50, 42, 34, 26, 18,
90 10, 2, 59, 51, 43, 35, 27,
91 19, 11, 3, 60, 52, 44, 36,
92 };
93
94 static char PC1_D[] = {
95 63, 55, 47, 39, 31, 23, 15,
96 7, 62, 54, 46, 38, 30, 22,
97 14, 6, 61, 53, 45, 37, 29,
98 21, 13, 5, 28, 20, 12, 4,
99 };
100
101 /*
102 * Sequence of shifts used for the key schedule.
103 */
104 static char shifts[] = {1, 1, 2, 2, 2, 2, 2, 2, 1, 2, 2, 2, 2, 2, 2, 1, };
105
106 /*
107 * Permuted-choice 2, to pick out the bits from
108 * the CD array that generate the key schedule.
109 */
110 static char PC2_C[] = {
111 14, 17, 11, 24, 1, 5,
112 3, 28, 15, 6, 21, 10,
113 23, 19, 12, 4, 26, 8,
114 16, 7, 27, 20, 13, 2,
115 };
116
117 static char PC2_D[] = {
118 41, 52, 31, 37, 47, 55,
119 30, 40, 51, 45, 33, 48,
120 44, 49, 39, 56, 34, 53,
121 46, 42, 50, 36, 29, 32,
122 };
123
124 /*
125 * The C and D arrays used to calculate the key schedule.
126 */
127
128 static char C[28];
129 static char D[28];
130 /*
131 * The key schedule.
132 * Generated from the key.
133 */
134 static char KS[16][48];
135
136 /*
137 * The E bit-selection table.
138 */
139 static char E[48];
140 static char e2[] = {
141 32, 1, 2, 3, 4, 5,
142 4, 5, 6, 7, 8, 9,
143 8, 9, 10, 11, 12, 13,
144 12, 13, 14, 15, 16, 17,
145 16, 17, 18, 19, 20, 21,
146 20, 21, 22, 23, 24, 25,
147 24, 25, 26, 27, 28, 29,
148 28, 29, 30, 31, 32, 1,
149 };
150
151 /*
152 * Set up the key schedule from the key.
153 */
154
155 static mutex_t lock = DEFAULTMUTEX;
156
157 /* EXPORT DELETE END */
158
159
160 static void
des_setkey_nolock(const char * key)161 des_setkey_nolock(const char *key)
162 {
163 /* EXPORT DELETE START */
164 int i, j, k;
165 char t;
166
167 /*
168 * First, generate C and D by permuting
169 * the key. The low order bit of each
170 * 8-bit char is not used, so C and D are only 28
171 * bits apiece.
172 */
173 for (i = 0; i < 28; i++) {
174 C[i] = key[PC1_C[i]-1];
175 D[i] = key[PC1_D[i]-1];
176 }
177 /*
178 * To generate Ki, rotate C and D according
179 * to schedule and pick up a permutation
180 * using PC2.
181 */
182 for (i = 0; i < 16; i++) {
183 /*
184 * rotate.
185 */
186 for (k = 0; k < shifts[i]; k++) {
187 t = C[0];
188 for (j = 0; j < 28-1; j++)
189 C[j] = C[j+1];
190 C[27] = (char)t;
191 t = D[0];
192 for (j = 0; j < 28-1; j++)
193 D[j] = D[j+1];
194 D[27] = (char)t;
195 }
196 /*
197 * get Ki. Note C and D are concatenated.
198 */
199 for (j = 0; j < 24; j++) {
200 KS[i][j] = C[PC2_C[j]-1];
201 KS[i][j+24] = D[PC2_D[j]-28-1];
202 }
203 }
204
205 for (i = 0; i < 48; i++)
206 E[i] = e2[i];
207 /* EXPORT DELETE END */
208 }
209
210 void
des_setkey(const char * key)211 des_setkey(const char *key)
212 {
213 /* EXPORT DELETE START */
214 (void) mutex_lock(&lock);
215 des_setkey_nolock(key);
216 (void) mutex_unlock(&lock);
217 /* EXPORT DELETE END */
218 }
219
220 /* EXPORT DELETE START */
221 /*
222 * The 8 selection functions.
223 * For some reason, they give a 0-origin
224 * index, unlike everything else.
225 */
226 static char S[8][64] = {
227 14, 4, 13, 1, 2, 15, 11, 8, 3, 10, 6, 12, 5, 9, 0, 7,
228 0, 15, 7, 4, 14, 2, 13, 1, 10, 6, 12, 11, 9, 5, 3, 8,
229 4, 1, 14, 8, 13, 6, 2, 11, 15, 12, 9, 7, 3, 10, 5, 0,
230 15, 12, 8, 2, 4, 9, 1, 7, 5, 11, 3, 14, 10, 0, 6, 13,
231
232 15, 1, 8, 14, 6, 11, 3, 4, 9, 7, 2, 13, 12, 0, 5, 10,
233 3, 13, 4, 7, 15, 2, 8, 14, 12, 0, 1, 10, 6, 9, 11, 5,
234 0, 14, 7, 11, 10, 4, 13, 1, 5, 8, 12, 6, 9, 3, 2, 15,
235 13, 8, 10, 1, 3, 15, 4, 2, 11, 6, 7, 12, 0, 5, 14, 9,
236
237 10, 0, 9, 14, 6, 3, 15, 5, 1, 13, 12, 7, 11, 4, 2, 8,
238 13, 7, 0, 9, 3, 4, 6, 10, 2, 8, 5, 14, 12, 11, 15, 1,
239 13, 6, 4, 9, 8, 15, 3, 0, 11, 1, 2, 12, 5, 10, 14, 7,
240 1, 10, 13, 0, 6, 9, 8, 7, 4, 15, 14, 3, 11, 5, 2, 12,
241
242 7, 13, 14, 3, 0, 6, 9, 10, 1, 2, 8, 5, 11, 12, 4, 15,
243 13, 8, 11, 5, 6, 15, 0, 3, 4, 7, 2, 12, 1, 10, 14, 9,
244 10, 6, 9, 0, 12, 11, 7, 13, 15, 1, 3, 14, 5, 2, 8, 4,
245 3, 15, 0, 6, 10, 1, 13, 8, 9, 4, 5, 11, 12, 7, 2, 14,
246
247 2, 12, 4, 1, 7, 10, 11, 6, 8, 5, 3, 15, 13, 0, 14, 9,
248 14, 11, 2, 12, 4, 7, 13, 1, 5, 0, 15, 10, 3, 9, 8, 6,
249 4, 2, 1, 11, 10, 13, 7, 8, 15, 9, 12, 5, 6, 3, 0, 14,
250 11, 8, 12, 7, 1, 14, 2, 13, 6, 15, 0, 9, 10, 4, 5, 3,
251
252 12, 1, 10, 15, 9, 2, 6, 8, 0, 13, 3, 4, 14, 7, 5, 11,
253 10, 15, 4, 2, 7, 12, 9, 5, 6, 1, 13, 14, 0, 11, 3, 8,
254 9, 14, 15, 5, 2, 8, 12, 3, 7, 0, 4, 10, 1, 13, 11, 6,
255 4, 3, 2, 12, 9, 5, 15, 10, 11, 14, 1, 7, 6, 0, 8, 13,
256
257 4, 11, 2, 14, 15, 0, 8, 13, 3, 12, 9, 7, 5, 10, 6, 1,
258 13, 0, 11, 7, 4, 9, 1, 10, 14, 3, 5, 12, 2, 15, 8, 6,
259 1, 4, 11, 13, 12, 3, 7, 14, 10, 15, 6, 8, 0, 5, 9, 2,
260 6, 11, 13, 8, 1, 4, 10, 7, 9, 5, 0, 15, 14, 2, 3, 12,
261
262 13, 2, 8, 4, 6, 15, 11, 1, 10, 9, 3, 14, 5, 0, 12, 7,
263 1, 15, 13, 8, 10, 3, 7, 4, 12, 5, 6, 11, 0, 14, 9, 2,
264 7, 11, 4, 1, 9, 12, 14, 2, 0, 6, 10, 13, 15, 3, 5, 8,
265 2, 1, 14, 7, 4, 10, 8, 13, 15, 12, 9, 0, 3, 5, 6, 11,
266 };
267
268 /*
269 * P is a permutation on the selected combination
270 * of the current L and key.
271 */
272 static char P[] = {
273 16, 7, 20, 21,
274 29, 12, 28, 17,
275 1, 15, 23, 26,
276 5, 18, 31, 10,
277 2, 8, 24, 14,
278 32, 27, 3, 9,
279 19, 13, 30, 6,
280 22, 11, 4, 25,
281 };
282
283 /*
284 * The current block, divided into 2 halves.
285 */
286 static char L[64];
287 static char tempL[32];
288 static char f[32];
289
290 /*
291 * The combination of the key and the input, before selection.
292 */
293 static char preS[48];
294
295 /*
296 * The payoff: encrypt a block.
297 */
298 /* EXPORT DELETE END */
299
300 static void
des_encrypt_nolock(char * block,int edflag)301 des_encrypt_nolock(char *block, int edflag)
302 {
303 /* EXPORT DELETE START */
304
305 if (edflag)
306 (void) _des_decrypt1(block, L, IP, &L[32],
307 preS, E, KS, S, f, tempL, P, FP);
308 else
309 (void) des_encrypt1(block, L, IP, &L[32],
310 preS, E, KS, S, f, tempL, P, FP);
311
312 /* EXPORT DELETE END */
313 }
314
315 void
des_encrypt(char * block,int edflag)316 des_encrypt(char *block, int edflag)
317 {
318 /* EXPORT DELETE START */
319 (void) mutex_lock(&lock);
320 des_encrypt_nolock(block, edflag);
321 (void) mutex_unlock(&lock);
322 /* EXPORT DELETE END */
323 }
324
325
326
327 #define IOBUF_SIZE 16
328
329 static char *
_get_iobuf(thread_key_t * keyp,unsigned size)330 _get_iobuf(thread_key_t *keyp, unsigned size)
331 {
332 char *iobuf;
333
334 if (thr_keycreate_once(keyp, free) != 0)
335 return (NULL);
336 iobuf = pthread_getspecific(*keyp);
337 if (iobuf == NULL) {
338 if (thr_setspecific(*keyp, (iobuf = malloc(size))) != 0) {
339 if (iobuf)
340 (void) free(iobuf);
341 iobuf = NULL;
342 }
343 }
344 return (iobuf);
345 }
346
347 char *
des_crypt(const char * pw,const char * salt)348 des_crypt(const char *pw, const char *salt)
349 {
350 /* EXPORT DELETE START */
351 int i, j;
352 char c, temp;
353 char block[66];
354 static thread_key_t key = THR_ONCE_KEY;
355 char *iobuf = _get_iobuf(&key, IOBUF_SIZE);
356
357 (void) mutex_lock(&lock);
358 for (i = 0; i < 66; i++)
359 block[i] = 0;
360 for (i = 0; (c = *pw) && (i < 64); pw++) {
361 for (j = 0; j < 7; j++, i++)
362 block[i] = (c>>(6-j)) & 01;
363 i++;
364 }
365
366 des_setkey_nolock(block);
367
368 for (i = 0; i < 66; i++)
369 block[i] = 0;
370
371 for (i = 0; i < 2; i++) {
372 c = *salt++;
373 iobuf[i] = (char)c;
374 if (c > 'Z')
375 c -= 6;
376 if (c > '9')
377 c -= 7;
378 c -= '.';
379 for (j = 0; j < 6; j++) {
380 if ((c>>j) & 01) {
381 temp = E[6*i+j];
382 E[6*i+j] = E[6*i+j+24];
383 E[6*i+j+24] = (char)temp;
384 }
385 }
386 }
387
388 for (i = 0; i < 25; i++)
389 (void) des_encrypt_nolock(block, 0);
390
391 for (i = 0; i < 11; i++) {
392 c = 0;
393 for (j = 0; j < 6; j++) {
394 c <<= 1;
395 c |= block[6*i+j];
396 }
397 c += '.';
398 if (c > '9')
399 c += 7;
400 if (c > 'Z')
401 c += 6;
402 iobuf[i+2] = (char)c;
403 }
404 iobuf[i+2] = 0;
405 if (iobuf[1] == 0)
406 iobuf[1] = iobuf[0];
407 (void) mutex_unlock(&lock);
408 return (iobuf);
409 #if 0
410 /* EXPORT DELETE END */
411 return (0);
412 /* EXPORT DELETE START */
413 #endif
414 /* EXPORT DELETE END */
415 }
416