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, Version 1.0 only 6 * (the "License"). You may not use this file except in compliance 7 * with the License. 8 * 9 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 10 * or http://www.opensolaris.org/os/licensing. 11 * See the License for the specific language governing permissions 12 * and limitations under the License. 13 * 14 * When distributing Covered Code, include this CDDL HEADER in each 15 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 16 * If applicable, add the following below this CDDL HEADER, with the 17 * fields enclosed by brackets "[]" replaced with your own identifying 18 * information: Portions Copyright [yyyy] [name of copyright owner] 19 * 20 * CDDL HEADER END 21 */ 22 23 /* 24 * Copyright 2005 Sun Microsystems, Inc. All rights reserved. 25 * Use is subject to license terms. 26 */ 27 28 /* Copyright (c) 1984, 1986, 1987, 1988, 1989 AT&T */ 29 /* All Rights Reserved */ 30 31 /* 32 * Portions of this source code were derived from Berkeley 4.3 BSD 33 * under license from the Regents of the University of California. 34 */ 35 36 #pragma ident "%Z%%M% %I% %E% SMI" 37 38 /* 39 * xcrypt.c: Hex encryption/decryption and utility routines 40 */ 41 42 #include <stdio.h> 43 #include <stdlib.h> 44 #include <sys/types.h> 45 #include <rpc/rpc.h> 46 #include <rpc/key_prot.h> /* for KEYCHECKSUMSIZE */ 47 #include <rpc/des_crypt.h> 48 #include <string.h> 49 #include <rpcsvc/nis_dhext.h> 50 #include <md5.h> 51 52 #define MD5HEXSIZE 32 53 54 extern int bin2hex(int len, unsigned char *binnum, char *hexnum); 55 extern int hex2bin(int len, char *hexnum, char *binnum); 56 static char hex[]; /* forward */ 57 static char hexval(); 58 59 int passwd2des(char *, char *); 60 static int weak_DES_key(des_block); 61 62 /* EXPORT DELETE START */ 63 /* 64 * For export control reasons, we want to limit the maximum size of 65 * data that can be encrypted or decrypted. We limit this to 1024 66 * bits of key data, which amounts to 128 bytes. 67 * 68 * For the extended DH project, we have increased it to 69 * 144 bytes (128key + 16checksum) to accomadate all the 128 bytes 70 * being used by the new 1024bit keys plus 16 bytes MD5 checksum. 71 * We discussed this with Sun's export control office and lawyers 72 * and we have reason to believe this is ok for export. 73 */ 74 #define MAX_KEY_CRYPT_LEN 144 75 /* EXPORT DELETE END */ 76 77 /* 78 * Encrypt a secret key given passwd 79 * The secret key is passed and returned in hex notation. 80 * Its length must be a multiple of 16 hex digits (64 bits). 81 */ 82 int 83 xencrypt(secret, passwd) 84 char *secret; 85 char *passwd; 86 { 87 /* EXPORT DELETE START */ 88 char key[8]; 89 char ivec[8]; 90 char *buf; 91 int err; 92 int len; 93 94 len = (int)strlen(secret) / 2; 95 if (len > MAX_KEY_CRYPT_LEN) 96 return (0); 97 buf = malloc((unsigned)len); 98 (void) hex2bin(len, secret, buf); 99 (void) passwd2des(passwd, key); 100 (void) memset(ivec, 0, 8); 101 102 err = cbc_crypt(key, buf, len, DES_ENCRYPT | DES_HW, ivec); 103 if (DES_FAILED(err)) { 104 free(buf); 105 return (0); 106 } 107 (void) bin2hex(len, (unsigned char *) buf, secret); 108 free(buf); 109 return (1); 110 #if 0 111 /* EXPORT DELETE END */ 112 return (0); 113 /* EXPORT DELETE START */ 114 #endif 115 /* EXPORT DELETE END */ 116 } 117 118 /* 119 * Decrypt secret key using passwd 120 * The secret key is passed and returned in hex notation. 121 * Once again, the length is a multiple of 16 hex digits 122 */ 123 int 124 xdecrypt(secret, passwd) 125 char *secret; 126 char *passwd; 127 { 128 /* EXPORT DELETE START */ 129 char key[8]; 130 char ivec[8]; 131 char *buf; 132 int err; 133 int len; 134 135 len = (int)strlen(secret) / 2; 136 if (len > MAX_KEY_CRYPT_LEN) 137 return (0); 138 buf = malloc((unsigned)len); 139 140 (void) hex2bin(len, secret, buf); 141 (void) passwd2des(passwd, key); 142 (void) memset(ivec, 0, 8); 143 144 err = cbc_crypt(key, buf, len, DES_DECRYPT | DES_HW, ivec); 145 if (DES_FAILED(err)) { 146 free(buf); 147 return (0); 148 } 149 (void) bin2hex(len, (unsigned char *) buf, secret); 150 free(buf); 151 return (1); 152 #if 0 153 /* EXPORT DELETE END */ 154 return (0); 155 /* EXPORT DELETE START */ 156 #endif 157 /* EXPORT DELETE END */ 158 } 159 160 /* 161 * Turn password into DES key 162 */ 163 int 164 passwd2des(pw, key) 165 char *pw; 166 char *key; 167 { 168 int i; 169 170 (void) memset(key, 0, 8); 171 for (i = 0; *pw; i = (i+1) % 8) { 172 key[i] ^= *pw++ << 1; 173 } 174 des_setparity(key); 175 return (1); 176 } 177 178 179 /* 180 * Hex to binary conversion 181 */ 182 int 183 hex2bin(len, hexnum, binnum) 184 int len; 185 char *hexnum; 186 char *binnum; 187 { 188 int i; 189 190 for (i = 0; i < len; i++) { 191 *binnum++ = 16 * hexval(hexnum[2 * i]) + 192 hexval(hexnum[2 * i + 1]); 193 } 194 return (1); 195 } 196 197 /* 198 * Binary to hex conversion 199 */ 200 int 201 bin2hex(len, binnum, hexnum) 202 int len; 203 unsigned char *binnum; 204 char *hexnum; 205 { 206 int i; 207 unsigned val; 208 209 for (i = 0; i < len; i++) { 210 val = binnum[i]; 211 hexnum[i*2] = hex[val >> 4]; 212 hexnum[i*2+1] = hex[val & 0xf]; 213 } 214 hexnum[len*2] = 0; 215 return (1); 216 } 217 218 static char hex[16] = { 219 '0', '1', '2', '3', '4', '5', '6', '7', 220 '8', '9', 'a', 'b', 'c', 'd', 'e', 'f', 221 }; 222 223 static char 224 hexval(c) 225 char c; 226 { 227 if (c >= '0' && c <= '9') { 228 return (c - '0'); 229 } else if (c >= 'a' && c <= 'z') { 230 return (c - 'a' + 10); 231 } else if (c >= 'A' && c <= 'Z') { 232 return (c - 'A' + 10); 233 } else { 234 return (-1); 235 } 236 } 237 238 /* 239 * Generic key length/algorithm version of xencrypt(). 240 * 241 * Encrypt a secret key given passwd. 242 * The secret key is passed in hex notation. 243 * Arg encrypted_secret will be set to point to the encrypted 244 * secret key (NUL term, hex notation). 245 * 246 * Its length must be a multiple of 16 hex digits (64 bits). 247 * 248 * For 192-0 (AUTH_DES), then encrypt using the same method as xencrypt(). 249 * 250 * If arg do_chksum is TRUE, append the checksum before the encrypt. 251 * For 192-0, the checksum is done the same as in xencrypt(). For 252 * bigger keys, MD5 is used. 253 * 254 * Arg netname can be NULL for 192-0. 255 */ 256 int 257 xencrypt_g( 258 char *secret, /* in */ 259 keylen_t keylen, /* in */ 260 algtype_t algtype, /* in */ 261 const char *passwd, /* in */ 262 const char netname[], /* in */ 263 char **encrypted_secret, /* out */ 264 bool_t do_chksum) /* in */ 265 { 266 /* EXPORT DELETE START */ 267 des_block key; 268 char ivec[8]; 269 char *binkeybuf; 270 int err; 271 const int classic_des = keylen == 192 && algtype == 0; 272 const int hexkeybytes = BITS2NIBBLES(keylen); 273 const int keychecksumsize = classic_des ? KEYCHECKSUMSIZE : MD5HEXSIZE; 274 const int binkeybytes = do_chksum ? keylen/8 + keychecksumsize/2 : 275 keylen/8; 276 const int bufsize = do_chksum ? hexkeybytes + keychecksumsize + 1 : 277 hexkeybytes + 1; 278 char *hexkeybuf; 279 280 if (!secret || !keylen || !passwd || !encrypted_secret) 281 return (0); 282 283 if ((hexkeybuf = malloc(bufsize)) == 0) 284 return (0); 285 286 (void) memcpy(hexkeybuf, secret, hexkeybytes); 287 if (do_chksum) 288 if (classic_des) { 289 (void) memcpy(hexkeybuf + hexkeybytes, secret, 290 keychecksumsize); 291 } else { 292 MD5_CTX md5_ctx; 293 char md5hexbuf[MD5HEXSIZE + 1] = {0}; 294 uint8_t digest[MD5HEXSIZE/2]; 295 296 MD5Init(&md5_ctx); 297 MD5Update(&md5_ctx, (unsigned char *)hexkeybuf, 298 hexkeybytes); 299 MD5Final(digest, &md5_ctx); 300 301 /* convert md5 binary digest to hex */ 302 (void) bin2hex(MD5HEXSIZE/2, digest, md5hexbuf); 303 304 /* append the hex md5 string to the end of the key */ 305 (void) memcpy(hexkeybuf + hexkeybytes, 306 (void *)md5hexbuf, MD5HEXSIZE); 307 } 308 hexkeybuf[bufsize - 1] = 0; 309 310 if (binkeybytes > MAX_KEY_CRYPT_LEN) { 311 free(hexkeybuf); 312 return (0); 313 } 314 if ((binkeybuf = malloc((unsigned)binkeybytes)) == 0) { 315 free(hexkeybuf); 316 return (0); 317 } 318 319 (void) hex2bin(binkeybytes, hexkeybuf, binkeybuf); 320 if (classic_des) 321 (void) passwd2des((char *)passwd, key.c); 322 else 323 if (netname) 324 (void) passwd2des_g(passwd, netname, 325 (int)strlen(netname), &key, FALSE); 326 else { 327 free(hexkeybuf); 328 return (0); 329 } 330 331 (void) memset(ivec, 0, 8); 332 333 err = cbc_crypt(key.c, binkeybuf, binkeybytes, DES_ENCRYPT | DES_HW, 334 ivec); 335 if (DES_FAILED(err)) { 336 free(hexkeybuf); 337 free(binkeybuf); 338 return (0); 339 } 340 (void) bin2hex(binkeybytes, (unsigned char *) binkeybuf, hexkeybuf); 341 free(binkeybuf); 342 *encrypted_secret = hexkeybuf; 343 return (1); 344 #if 0 345 /* EXPORT DELETE END */ 346 return (0); 347 /* EXPORT DELETE START */ 348 #endif 349 /* EXPORT DELETE END */ 350 } 351 352 /* 353 * Generic key len and alg type for version of xdecrypt. 354 * 355 * Decrypt secret key using passwd. The decrypted secret key 356 * *overwrites* the supplied encrypted secret key. 357 * The secret key is passed and returned in hex notation. 358 * Once again, the length is a multiple of 16 hex digits. 359 * 360 * If 'do_chksum' is TRUE, the 'secret' buffer is assumed to contain 361 * a checksum calculated by a call to xencrypt_g(). 362 * 363 * If keylen is 192 and algtype is 0, then decrypt the same way 364 * as xdecrypt(). 365 * 366 * Arg netname can be NULL for 192-0. 367 */ 368 int 369 xdecrypt_g( 370 char *secret, /* out */ 371 int keylen, /* in */ 372 int algtype, /* in */ 373 const char *passwd, /* in */ 374 const char netname[], /* in */ 375 bool_t do_chksum) /* in */ 376 { 377 /* EXPORT DELETE START */ 378 des_block key; 379 char ivec[8]; 380 char *buf; 381 int err; 382 int len; 383 const int classic_des = keylen == 192 && algtype == 0; 384 const int hexkeybytes = BITS2NIBBLES(keylen); 385 const int keychecksumsize = classic_des ? KEYCHECKSUMSIZE : MD5HEXSIZE; 386 387 len = (int)strlen(secret) / 2; 388 if (len > MAX_KEY_CRYPT_LEN) 389 return (0); 390 if ((buf = malloc((unsigned)len)) == 0) 391 return (0); 392 393 (void) hex2bin(len, secret, buf); 394 if (classic_des) 395 (void) passwd2des((char *)passwd, key.c); 396 else 397 if (netname) 398 (void) passwd2des_g(passwd, netname, 399 (int)strlen(netname), &key, FALSE); 400 else { 401 free(buf); 402 return (0); 403 } 404 (void) memset(ivec, 0, 8); 405 406 err = cbc_crypt(key.c, buf, len, DES_DECRYPT | DES_HW, ivec); 407 if (DES_FAILED(err)) { 408 free(buf); 409 return (0); 410 } 411 (void) bin2hex(len, (unsigned char *) buf, secret); 412 free(buf); 413 414 if (do_chksum) 415 if (classic_des) { 416 if (memcmp(secret, &(secret[hexkeybytes]), 417 keychecksumsize) != 0) { 418 secret[0] = 0; 419 return (0); 420 } 421 } else { 422 MD5_CTX md5_ctx; 423 char md5hexbuf[MD5HEXSIZE + 1] = {0}; 424 uint8_t digest[MD5HEXSIZE/2]; 425 426 MD5Init(&md5_ctx); 427 MD5Update(&md5_ctx, (unsigned char *)secret, 428 hexkeybytes); 429 MD5Final(digest, &md5_ctx); 430 431 /* convert md5 binary digest to hex */ 432 (void) bin2hex(MD5HEXSIZE/2, digest, md5hexbuf); 433 434 /* does the digest match the appended one? */ 435 if (memcmp(&(secret[hexkeybytes]), 436 md5hexbuf, MD5HEXSIZE) != 0) { 437 secret[0] = 0; 438 return (0); 439 } 440 } 441 442 secret[hexkeybytes] = '\0'; 443 444 return (1); 445 #if 0 446 /* EXPORT DELETE END */ 447 return (0); 448 /* EXPORT DELETE START */ 449 #endif 450 /* EXPORT DELETE END */ 451 } 452 453 454 /* 455 * Modified version of passwd2des(). passwd2des_g() uses the Kerberos 456 * RFC 1510 algorithm to generate a DES key from a user password 457 * and mix-in string. The mix-in is expected to be the netname. 458 * This function to be used only for extended Diffie-Hellman keys. 459 * 460 * If altarg is TRUE, reverse the concat of passwd and mix-in. 461 */ 462 int 463 passwd2des_g( 464 const char *pw, 465 const char *mixin, 466 int len, 467 des_block *key, /* out */ 468 bool_t altalg) 469 { 470 471 int i, j, incr = 1; 472 des_block ivec, tkey; 473 char *text; 474 int plen, tlen; 475 476 (void) memset(tkey.c, 0, 8); 477 (void) memset(ivec.c, 0, 8); 478 479 480 /* 481 * Concatentate the password and the mix-in string, fan-fold and XOR them 482 * to the required eight byte initial DES key. Since passwords can be 483 * expected to use mostly seven bit ASCII, left shift the password one 484 * bit in order to preserve as much key space as possible. 485 */ 486 487 #define KEYLEN sizeof (tkey.c) 488 plen = strlen(pw); 489 tlen = ((plen + len + (KEYLEN-1))/KEYLEN)*KEYLEN; 490 if ((text = malloc(tlen)) == NULL) { 491 return (0); 492 } 493 494 (void) memset(text, 0, tlen); 495 496 if (!altalg) { 497 498 /* 499 * Concatenate the password and the mix-in string, fan-fold and XOR them 500 * to the required eight byte initial DES key. Since passwords can be 501 * expected to use mostly seven bit ASCII, left shift the password one 502 * bit in order to preserve as much key space as possible. 503 */ 504 (void) memcpy(text, pw, plen); 505 (void) memcpy(&text[plen], mixin, len); 506 507 for (i = 0, j = 0; pw[j]; j++) { 508 tkey.c[i] ^= pw[j] << 1; 509 i += incr; 510 if (i == 8) { 511 i = 7; 512 incr = -incr; 513 } else if (i == -1) { 514 i = 0; 515 incr = -incr; 516 } 517 } 518 519 for (j = 0; j < len; j++) { 520 tkey.c[i] ^= mixin[j]; 521 i += incr; 522 if (i == 8) { 523 i = 7; 524 incr = -incr; 525 } else if (i == -1) { 526 i = 0; 527 incr = -incr; 528 } 529 } 530 } else { /* use alternative algorithm */ 531 (void) memcpy(text, mixin, len); 532 (void) memcpy(&text[len], pw, plen); 533 534 for (i = 0, j = 0; j < len; j++) { 535 tkey.c[i] ^= mixin[j]; 536 i += incr; 537 if (i == 8) { 538 i = 7; 539 incr = -incr; 540 } else if (i == -1) { 541 i = 0; 542 incr = -incr; 543 } 544 } 545 546 for (j = 0; pw[j]; j++) { 547 tkey.c[i] ^= pw[j] << 1; 548 i += incr; 549 if (i == 8) { 550 i = 7; 551 incr = -incr; 552 } else if (i == -1) { 553 i = 0; 554 incr = -incr; 555 } 556 } 557 } 558 des_setparity_g(&tkey); 559 560 /* 561 * Use the temporary key to produce a DES CBC checksum for the text 562 * string; cbc_crypt returns the checksum in the ivec. 563 */ 564 (void) cbc_crypt(tkey.c, text, tlen, DES_ENCRYPT|DES_HW, ivec.c); 565 des_setparity_g(&ivec); 566 free(text); 567 568 if (weak_DES_key(ivec)) { 569 ivec.c[7] ^= 0xf0; 570 /* 571 * XORing with 0xf0 preserves parity, so no need to check 572 * that again. 573 */ 574 } 575 576 (void) memcpy((*key).c, ivec.c, sizeof (ivec.c)); 577 578 return (1); 579 580 } 581 582 struct DESkey { 583 uint32_t h1; 584 uint32_t h2; 585 }; 586 587 /* 588 * Weak and semiweak keys from "Applied Cryptography", second edition, 589 * by Bruce Schneier, Wiley 1996. 590 */ 591 static struct DESkey weakDESkeys[] = { 592 /* Weak keys */ 593 {0x01010101, 0x01010101}, 594 {0x1f1f1f1f, 0x1f1f1f1f}, 595 {0xe0e0e0e0, 0xe0e0e0e0}, 596 {0xfefefefe, 0xfefefefe}, 597 /* Semiweak keys */ 598 {0x01fe01fe, 0x01fe01fe}, 599 {0x1fe01fe0, 0x0ef10ef1}, 600 {0x01e001e0, 0x01f101f1}, 601 {0x1ffe1ffe, 0x0efe0efe}, 602 {0x011f011f, 0x010e010e}, 603 {0xe0fee0fe, 0xf1fef1fe}, 604 {0xfe01fe01, 0xfe01fe01}, 605 {0xe01fe01f, 0xf10ef10e}, 606 {0xe001e001, 0xf101f101}, 607 {0xfe1ffe1f, 0xfe0efe0e}, 608 {0x1f011f01, 0x0e010e01}, 609 {0xfee0fee0, 0xfef1fef1} 610 }; 611 612 static int 613 weak_DES_key(des_block db) 614 { 615 int i; 616 617 for (i = 0; i < sizeof (weakDESkeys)/sizeof (struct DESkey); i++) { 618 if (weakDESkeys[i].h1 == db.key.high && 619 weakDESkeys[i].h2 == db.key.low) 620 return (1); 621 } 622 623 return (0); 624 } 625