1 /*- 2 * Copyright (c) 1991, 1993 3 * The Regents of the University of California. All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * 1. Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in the 12 * documentation and/or other materials provided with the distribution. 13 * 3. All advertising materials mentioning features or use of this software 14 * must display the following acknowledgement: 15 * This product includes software developed by the University of 16 * California, Berkeley and its contributors. 17 * 4. Neither the name of the University nor the names of its contributors 18 * may be used to endorse or promote products derived from this software 19 * without specific prior written permission. 20 * 21 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 22 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 23 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 24 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 25 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 26 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 27 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 28 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 29 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 30 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 31 * SUCH DAMAGE. 32 */ 33 34 #ifndef lint 35 #if 0 36 static const char sccsid[] = "@(#)encrypt.c 8.2 (Berkeley) 5/30/95"; 37 #else 38 static const char rcsid[] = 39 "$FreeBSD$"; 40 #endif 41 #endif /* not lint */ 42 43 /* 44 * Copyright (C) 1990 by the Massachusetts Institute of Technology 45 * 46 * Export of this software from the United States of America is assumed 47 * to require a specific license from the United States Government. 48 * It is the responsibility of any person or organization contemplating 49 * export to obtain such a license before exporting. 50 * 51 * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and 52 * distribute this software and its documentation for any purpose and 53 * without fee is hereby granted, provided that the above copyright 54 * notice appear in all copies and that both that copyright notice and 55 * this permission notice appear in supporting documentation, and that 56 * the name of M.I.T. not be used in advertising or publicity pertaining 57 * to distribution of the software without specific, written prior 58 * permission. M.I.T. makes no representations about the suitability of 59 * this software for any purpose. It is provided "as is" without express 60 * or implied warranty. 61 */ 62 63 #ifdef ENCRYPTION 64 65 #define ENCRYPT_NAMES 66 #include <stdio.h> 67 #include <arpa/telnet.h> 68 69 #include "encrypt.h" 70 #include "misc.h" 71 72 #ifdef __STDC__ 73 #include <stdlib.h> 74 #endif 75 #ifdef NO_STRING_H 76 #include <strings.h> 77 #else 78 #include <string.h> 79 #endif 80 81 /* 82 * These functions pointers point to the current routines 83 * for encrypting and decrypting data. 84 */ 85 void (*encrypt_output) P((unsigned char *, int)); 86 int (*decrypt_input) P((int)); 87 88 int EncryptType(char *type, char *mode); 89 int EncryptStart(char *mode); 90 int EncryptStop(char *mode); 91 int EncryptStartInput(void); 92 int EncryptStartOutput(void); 93 int EncryptStopInput(void); 94 int EncryptStopOutput(void); 95 96 int Ambiguous(char **s); 97 int isprefix(char *s1, char *s2); 98 char **genget(char *name, char **table, int stlen); 99 100 int encrypt_debug_mode = 0; 101 static int decrypt_mode = 0; 102 static int encrypt_mode = 0; 103 static int encrypt_verbose = 0; 104 static int autoencrypt = 0; 105 static int autodecrypt = 0; 106 static int havesessionkey = 0; 107 static int Server = 0; 108 static char *Name = "Noname"; 109 110 #define typemask(x) ((x) > 0 ? 1 << ((x)-1) : 0) 111 112 static long i_support_encrypt = 0 113 #ifdef DES_ENCRYPTION 114 | typemask(ENCTYPE_DES_CFB64) | typemask(ENCTYPE_DES_OFB64) 115 #endif 116 |0; 117 static long i_support_decrypt = 0 118 #ifdef DES_ENCRYPTION 119 | typemask(ENCTYPE_DES_CFB64) | typemask(ENCTYPE_DES_OFB64) 120 #endif 121 |0; 122 123 static long i_wont_support_encrypt = 0; 124 static long i_wont_support_decrypt = 0; 125 #define I_SUPPORT_ENCRYPT (i_support_encrypt & ~i_wont_support_encrypt) 126 #define I_SUPPORT_DECRYPT (i_support_decrypt & ~i_wont_support_decrypt) 127 128 static long remote_supports_encrypt = 0; 129 static long remote_supports_decrypt = 0; 130 131 static Encryptions encryptions[] = { 132 #ifdef DES_ENCRYPTION 133 { "DES_CFB64", ENCTYPE_DES_CFB64, 134 cfb64_encrypt, 135 cfb64_decrypt, 136 cfb64_init, 137 cfb64_start, 138 cfb64_is, 139 cfb64_reply, 140 cfb64_session, 141 cfb64_keyid, 142 cfb64_printsub }, 143 { "DES_OFB64", ENCTYPE_DES_OFB64, 144 ofb64_encrypt, 145 ofb64_decrypt, 146 ofb64_init, 147 ofb64_start, 148 ofb64_is, 149 ofb64_reply, 150 ofb64_session, 151 ofb64_keyid, 152 ofb64_printsub }, 153 #endif /* DES_ENCRYPTION */ 154 { 0, }, 155 }; 156 157 static unsigned char str_send[64] = { IAC, SB, TELOPT_ENCRYPT, 158 ENCRYPT_SUPPORT }; 159 static unsigned char str_suplen = 0; 160 static unsigned char str_start[72] = { IAC, SB, TELOPT_ENCRYPT }; 161 static unsigned char str_end[] = { IAC, SB, TELOPT_ENCRYPT, 0, IAC, SE }; 162 163 Encryptions * 164 findencryption(type) 165 int type; 166 { 167 Encryptions *ep = encryptions; 168 169 if (!(I_SUPPORT_ENCRYPT & remote_supports_decrypt & typemask(type))) 170 return(0); 171 while (ep->type && ep->type != type) 172 ++ep; 173 return(ep->type ? ep : 0); 174 } 175 176 Encryptions * 177 finddecryption(type) 178 int type; 179 { 180 Encryptions *ep = encryptions; 181 182 if (!(I_SUPPORT_DECRYPT & remote_supports_encrypt & typemask(type))) 183 return(0); 184 while (ep->type && ep->type != type) 185 ++ep; 186 return(ep->type ? ep : 0); 187 } 188 189 #define MAXKEYLEN 64 190 191 static struct key_info { 192 unsigned char keyid[MAXKEYLEN]; 193 int keylen; 194 int dir; 195 int *modep; 196 Encryptions *(*getcrypt)(); 197 } ki[2] = { 198 { { 0 }, 0, DIR_ENCRYPT, &encrypt_mode, findencryption }, 199 { { 0 }, 0, DIR_DECRYPT, &decrypt_mode, finddecryption }, 200 }; 201 202 static void encrypt_keyid(struct key_info *kp, unsigned char *keyid, int len); 203 204 void 205 encrypt_init(name, server) 206 char *name; 207 int server; 208 { 209 Encryptions *ep = encryptions; 210 211 Name = name; 212 Server = server; 213 i_support_encrypt = i_support_decrypt = 0; 214 remote_supports_encrypt = remote_supports_decrypt = 0; 215 encrypt_mode = 0; 216 decrypt_mode = 0; 217 encrypt_output = 0; 218 decrypt_input = 0; 219 #ifdef notdef 220 encrypt_verbose = !server; 221 #endif 222 223 str_suplen = 4; 224 225 while (ep->type) { 226 if (encrypt_debug_mode) 227 printf(">>>%s: I will support %s\r\n", 228 Name, ENCTYPE_NAME(ep->type)); 229 i_support_encrypt |= typemask(ep->type); 230 i_support_decrypt |= typemask(ep->type); 231 if ((i_wont_support_decrypt & typemask(ep->type)) == 0) 232 if ((str_send[str_suplen++] = ep->type) == IAC) 233 str_send[str_suplen++] = IAC; 234 if (ep->init) 235 (*ep->init)(Server); 236 ++ep; 237 } 238 str_send[str_suplen++] = IAC; 239 str_send[str_suplen++] = SE; 240 } 241 242 void 243 encrypt_list_types() 244 { 245 Encryptions *ep = encryptions; 246 247 printf("Valid encryption types:\n"); 248 while (ep->type) { 249 printf("\t%s (%d)\r\n", ENCTYPE_NAME(ep->type), ep->type); 250 ++ep; 251 } 252 } 253 254 int 255 EncryptEnable(type, mode) 256 char *type, *mode; 257 { 258 if (isprefix(type, "help") || isprefix(type, "?")) { 259 printf("Usage: encrypt enable <type> [input|output]\n"); 260 encrypt_list_types(); 261 return(0); 262 } 263 if (EncryptType(type, mode)) 264 return(EncryptStart(mode)); 265 return(0); 266 } 267 268 int 269 EncryptDisable(type, mode) 270 char *type, *mode; 271 { 272 register Encryptions *ep; 273 int ret = 0; 274 275 if (isprefix(type, "help") || isprefix(type, "?")) { 276 printf("Usage: encrypt disable <type> [input|output]\n"); 277 encrypt_list_types(); 278 } else if ((ep = (Encryptions *)genget(type, (char **)encryptions, 279 sizeof(Encryptions))) == 0) { 280 printf("%s: invalid encryption type\n", type); 281 } else if (Ambiguous((char **)ep)) { 282 printf("Ambiguous type '%s'\n", type); 283 } else { 284 if ((mode == 0) || (isprefix(mode, "input") ? 1 : 0)) { 285 if (decrypt_mode == ep->type) 286 EncryptStopInput(); 287 i_wont_support_decrypt |= typemask(ep->type); 288 ret = 1; 289 } 290 if ((mode == 0) || (isprefix(mode, "output"))) { 291 if (encrypt_mode == ep->type) 292 EncryptStopOutput(); 293 i_wont_support_encrypt |= typemask(ep->type); 294 ret = 1; 295 } 296 if (ret == 0) 297 printf("%s: invalid encryption mode\n", mode); 298 } 299 return(ret); 300 } 301 302 int 303 EncryptType(type, mode) 304 char *type; 305 char *mode; 306 { 307 register Encryptions *ep; 308 int ret = 0; 309 310 if (isprefix(type, "help") || isprefix(type, "?")) { 311 printf("Usage: encrypt type <type> [input|output]\n"); 312 encrypt_list_types(); 313 } else if ((ep = (Encryptions *)genget(type, (char **)encryptions, 314 sizeof(Encryptions))) == 0) { 315 printf("%s: invalid encryption type\n", type); 316 } else if (Ambiguous((char **)ep)) { 317 printf("Ambiguous type '%s'\n", type); 318 } else { 319 if ((mode == 0) || isprefix(mode, "input")) { 320 decrypt_mode = ep->type; 321 i_wont_support_decrypt &= ~typemask(ep->type); 322 ret = 1; 323 } 324 if ((mode == 0) || isprefix(mode, "output")) { 325 encrypt_mode = ep->type; 326 i_wont_support_encrypt &= ~typemask(ep->type); 327 ret = 1; 328 } 329 if (ret == 0) 330 printf("%s: invalid encryption mode\n", mode); 331 } 332 return(ret); 333 } 334 335 int 336 EncryptStart(mode) 337 char *mode; 338 { 339 register int ret = 0; 340 if (mode) { 341 if (isprefix(mode, "input")) 342 return(EncryptStartInput()); 343 if (isprefix(mode, "output")) 344 return(EncryptStartOutput()); 345 if (isprefix(mode, "help") || isprefix(mode, "?")) { 346 printf("Usage: encrypt start [input|output]\n"); 347 return(0); 348 } 349 printf("%s: invalid encryption mode 'encrypt start ?' for help\n", mode); 350 return(0); 351 } 352 ret += EncryptStartInput(); 353 ret += EncryptStartOutput(); 354 return(ret); 355 } 356 357 int 358 EncryptStartInput() 359 { 360 if (decrypt_mode) { 361 encrypt_send_request_start(); 362 return(1); 363 } 364 printf("No previous decryption mode, decryption not enabled\r\n"); 365 return(0); 366 } 367 368 int 369 EncryptStartOutput() 370 { 371 if (encrypt_mode) { 372 encrypt_start_output(encrypt_mode); 373 return(1); 374 } 375 printf("No previous encryption mode, encryption not enabled\r\n"); 376 return(0); 377 } 378 379 int 380 EncryptStop(mode) 381 char *mode; 382 { 383 int ret = 0; 384 if (mode) { 385 if (isprefix(mode, "input")) 386 return(EncryptStopInput()); 387 if (isprefix(mode, "output")) 388 return(EncryptStopOutput()); 389 if (isprefix(mode, "help") || isprefix(mode, "?")) { 390 printf("Usage: encrypt stop [input|output]\n"); 391 return(0); 392 } 393 printf("%s: invalid encryption mode 'encrypt stop ?' for help\n", mode); 394 return(0); 395 } 396 ret += EncryptStopInput(); 397 ret += EncryptStopOutput(); 398 return(ret); 399 } 400 401 int 402 EncryptStopInput() 403 { 404 encrypt_send_request_end(); 405 return(1); 406 } 407 408 int 409 EncryptStopOutput() 410 { 411 encrypt_send_end(); 412 return(1); 413 } 414 415 void 416 encrypt_display() 417 { 418 if (encrypt_output) 419 printf("Currently encrypting output with %s\r\n", 420 ENCTYPE_NAME(encrypt_mode)); 421 if (decrypt_input) 422 printf("Currently decrypting input with %s\r\n", 423 ENCTYPE_NAME(decrypt_mode)); 424 } 425 426 int 427 EncryptStatus() 428 { 429 if (encrypt_output) 430 printf("Currently encrypting output with %s\r\n", 431 ENCTYPE_NAME(encrypt_mode)); 432 else if (encrypt_mode) { 433 printf("Currently output is clear text.\r\n"); 434 printf("Last encryption mode was %s\r\n", 435 ENCTYPE_NAME(encrypt_mode)); 436 } 437 if (decrypt_input) { 438 printf("Currently decrypting input with %s\r\n", 439 ENCTYPE_NAME(decrypt_mode)); 440 } else if (decrypt_mode) { 441 printf("Currently input is clear text.\r\n"); 442 printf("Last decryption mode was %s\r\n", 443 ENCTYPE_NAME(decrypt_mode)); 444 } 445 return 1; 446 } 447 448 void 449 encrypt_send_support() 450 { 451 if (str_suplen) { 452 /* 453 * If the user has requested that decryption start 454 * immediatly, then send a "REQUEST START" before 455 * we negotiate the type. 456 */ 457 if (!Server && autodecrypt) 458 encrypt_send_request_start(); 459 net_write(str_send, str_suplen); 460 printsub('>', &str_send[2], str_suplen - 2); 461 str_suplen = 0; 462 } 463 } 464 465 int 466 EncryptDebug(on) 467 int on; 468 { 469 if (on < 0) 470 encrypt_debug_mode ^= 1; 471 else 472 encrypt_debug_mode = on; 473 printf("Encryption debugging %s\r\n", 474 encrypt_debug_mode ? "enabled" : "disabled"); 475 return(1); 476 } 477 478 int 479 EncryptVerbose(on) 480 int on; 481 { 482 if (on < 0) 483 encrypt_verbose ^= 1; 484 else 485 encrypt_verbose = on; 486 printf("Encryption %s verbose\r\n", 487 encrypt_verbose ? "is" : "is not"); 488 return(1); 489 } 490 491 int 492 EncryptAutoEnc(on) 493 int on; 494 { 495 encrypt_auto(on); 496 printf("Automatic encryption of output is %s\r\n", 497 autoencrypt ? "enabled" : "disabled"); 498 return(1); 499 } 500 501 int 502 EncryptAutoDec(on) 503 int on; 504 { 505 decrypt_auto(on); 506 printf("Automatic decryption of input is %s\r\n", 507 autodecrypt ? "enabled" : "disabled"); 508 return(1); 509 } 510 511 /* 512 * Called when ENCRYPT SUPPORT is received. 513 */ 514 void 515 encrypt_support(typelist, cnt) 516 unsigned char *typelist; 517 int cnt; 518 { 519 register int type, use_type = 0; 520 Encryptions *ep; 521 522 /* 523 * Forget anything the other side has previously told us. 524 */ 525 remote_supports_decrypt = 0; 526 527 while (cnt-- > 0) { 528 type = *typelist++; 529 if (encrypt_debug_mode) 530 printf(">>>%s: He is supporting %s (%d)\r\n", 531 Name, 532 ENCTYPE_NAME(type), type); 533 if ((type < ENCTYPE_CNT) && 534 (I_SUPPORT_ENCRYPT & typemask(type))) { 535 remote_supports_decrypt |= typemask(type); 536 if (use_type == 0) 537 use_type = type; 538 } 539 } 540 if (use_type) { 541 ep = findencryption(use_type); 542 if (!ep) 543 return; 544 type = ep->start ? (*ep->start)(DIR_ENCRYPT, Server) : 0; 545 if (encrypt_debug_mode) 546 printf(">>>%s: (*ep->start)() returned %d\r\n", 547 Name, type); 548 if (type < 0) 549 return; 550 encrypt_mode = use_type; 551 if (type == 0) 552 encrypt_start_output(use_type); 553 } 554 } 555 556 void 557 encrypt_is(data, cnt) 558 unsigned char *data; 559 int cnt; 560 { 561 Encryptions *ep; 562 register int type, ret; 563 564 if (--cnt < 0) 565 return; 566 type = *data++; 567 if (type < ENCTYPE_CNT) 568 remote_supports_encrypt |= typemask(type); 569 if (!(ep = finddecryption(type))) { 570 if (encrypt_debug_mode) 571 printf(">>>%s: Can't find type %s (%d) for initial negotiation\r\n", 572 Name, 573 ENCTYPE_NAME_OK(type) 574 ? ENCTYPE_NAME(type) : "(unknown)", 575 type); 576 return; 577 } 578 if (!ep->is) { 579 if (encrypt_debug_mode) 580 printf(">>>%s: No initial negotiation needed for type %s (%d)\r\n", 581 Name, 582 ENCTYPE_NAME_OK(type) 583 ? ENCTYPE_NAME(type) : "(unknown)", 584 type); 585 ret = 0; 586 } else { 587 ret = (*ep->is)(data, cnt); 588 if (encrypt_debug_mode) 589 printf("(*ep->is)(%p, %d) returned %s(%d)\n", data, cnt, 590 (ret < 0) ? "FAIL " : 591 (ret == 0) ? "SUCCESS " : "MORE_TO_DO ", ret); 592 } 593 if (ret < 0) { 594 autodecrypt = 0; 595 } else { 596 decrypt_mode = type; 597 if (ret == 0 && autodecrypt) 598 encrypt_send_request_start(); 599 } 600 } 601 602 void 603 encrypt_reply(data, cnt) 604 unsigned char *data; 605 int cnt; 606 { 607 Encryptions *ep; 608 register int ret, type; 609 610 if (--cnt < 0) 611 return; 612 type = *data++; 613 if (!(ep = findencryption(type))) { 614 if (encrypt_debug_mode) 615 printf(">>>%s: Can't find type %s (%d) for initial negotiation\r\n", 616 Name, 617 ENCTYPE_NAME_OK(type) 618 ? ENCTYPE_NAME(type) : "(unknown)", 619 type); 620 return; 621 } 622 if (!ep->reply) { 623 if (encrypt_debug_mode) 624 printf(">>>%s: No initial negotiation needed for type %s (%d)\r\n", 625 Name, 626 ENCTYPE_NAME_OK(type) 627 ? ENCTYPE_NAME(type) : "(unknown)", 628 type); 629 ret = 0; 630 } else { 631 ret = (*ep->reply)(data, cnt); 632 if (encrypt_debug_mode) 633 printf("(*ep->reply)(%p, %d) returned %s(%d)\n", 634 data, cnt, 635 (ret < 0) ? "FAIL " : 636 (ret == 0) ? "SUCCESS " : "MORE_TO_DO ", ret); 637 } 638 if (encrypt_debug_mode) 639 printf(">>>%s: encrypt_reply returned %d\n", Name, ret); 640 if (ret < 0) { 641 autoencrypt = 0; 642 } else { 643 encrypt_mode = type; 644 if (ret == 0 && autoencrypt) 645 encrypt_start_output(type); 646 } 647 } 648 649 /* 650 * Called when a ENCRYPT START command is received. 651 */ 652 void 653 encrypt_start(data, cnt) 654 unsigned char *data; 655 int cnt; 656 { 657 Encryptions *ep; 658 659 if (!decrypt_mode) { 660 /* 661 * Something is wrong. We should not get a START 662 * command without having already picked our 663 * decryption scheme. Send a REQUEST-END to 664 * attempt to clear the channel... 665 */ 666 printf("%s: Warning, Cannot decrypt input stream!!!\r\n", Name); 667 encrypt_send_request_end(); 668 return; 669 } 670 671 if ((ep = finddecryption(decrypt_mode))) { 672 decrypt_input = ep->input; 673 if (encrypt_verbose) 674 printf("[ Input is now decrypted with type %s ]\r\n", 675 ENCTYPE_NAME(decrypt_mode)); 676 if (encrypt_debug_mode) 677 printf(">>>%s: Start to decrypt input with type %s\r\n", 678 Name, ENCTYPE_NAME(decrypt_mode)); 679 } else { 680 printf("%s: Warning, Cannot decrypt type %s (%d)!!!\r\n", 681 Name, 682 ENCTYPE_NAME_OK(decrypt_mode) 683 ? ENCTYPE_NAME(decrypt_mode) 684 : "(unknown)", 685 decrypt_mode); 686 encrypt_send_request_end(); 687 } 688 } 689 690 void 691 encrypt_session_key(key, server) 692 Session_Key *key; 693 int server; 694 { 695 Encryptions *ep = encryptions; 696 697 havesessionkey = 1; 698 699 while (ep->type) { 700 if (ep->session) 701 (*ep->session)(key, server); 702 #ifdef notdef 703 if (!encrypt_output && autoencrypt && !server) 704 encrypt_start_output(ep->type); 705 if (!decrypt_input && autodecrypt && !server) 706 encrypt_send_request_start(); 707 #endif 708 ++ep; 709 } 710 } 711 712 /* 713 * Called when ENCRYPT END is received. 714 */ 715 void 716 encrypt_end() 717 { 718 decrypt_input = 0; 719 if (encrypt_debug_mode) 720 printf(">>>%s: Input is back to clear text\r\n", Name); 721 if (encrypt_verbose) 722 printf("[ Input is now clear text ]\r\n"); 723 } 724 725 /* 726 * Called when ENCRYPT REQUEST-END is received. 727 */ 728 void 729 encrypt_request_end() 730 { 731 encrypt_send_end(); 732 } 733 734 /* 735 * Called when ENCRYPT REQUEST-START is received. If we receive 736 * this before a type is picked, then that indicates that the 737 * other side wants us to start encrypting data as soon as we 738 * can. 739 */ 740 void 741 encrypt_request_start(data, cnt) 742 unsigned char *data; 743 int cnt; 744 { 745 if (encrypt_mode == 0) { 746 if (Server) 747 autoencrypt = 1; 748 return; 749 } 750 encrypt_start_output(encrypt_mode); 751 } 752 753 static unsigned char str_keyid[(MAXKEYLEN*2)+5] = { IAC, SB, TELOPT_ENCRYPT }; 754 755 void 756 encrypt_enc_keyid(keyid, len) 757 unsigned char *keyid; 758 int len; 759 { 760 encrypt_keyid(&ki[1], keyid, len); 761 } 762 763 void 764 encrypt_dec_keyid(keyid, len) 765 unsigned char *keyid; 766 int len; 767 { 768 encrypt_keyid(&ki[0], keyid, len); 769 } 770 771 void 772 encrypt_keyid(kp, keyid, len) 773 struct key_info *kp; 774 unsigned char *keyid; 775 int len; 776 { 777 Encryptions *ep; 778 int dir = kp->dir; 779 register int ret = 0; 780 781 if (!(ep = (*kp->getcrypt)(*kp->modep))) { 782 if (len == 0) 783 return; 784 kp->keylen = 0; 785 } else if (len == 0) { 786 /* 787 * Empty option, indicates a failure. 788 */ 789 if (kp->keylen == 0) 790 return; 791 kp->keylen = 0; 792 if (ep->keyid) 793 (void)(*ep->keyid)(dir, kp->keyid, &kp->keylen); 794 795 } else if ((len != kp->keylen) || 796 (memcmp(keyid, kp->keyid, len) != 0)) { 797 /* 798 * Length or contents are different 799 */ 800 kp->keylen = len; 801 memmove(kp->keyid, keyid, len); 802 if (ep->keyid) 803 (void)(*ep->keyid)(dir, kp->keyid, &kp->keylen); 804 } else { 805 if (ep->keyid) 806 ret = (*ep->keyid)(dir, kp->keyid, &kp->keylen); 807 if ((ret == 0) && (dir == DIR_ENCRYPT) && autoencrypt) 808 encrypt_start_output(*kp->modep); 809 return; 810 } 811 812 encrypt_send_keyid(dir, kp->keyid, kp->keylen, 0); 813 } 814 815 void 816 encrypt_send_keyid(dir, keyid, keylen, saveit) 817 int dir; 818 unsigned char *keyid; 819 int keylen; 820 int saveit; 821 { 822 unsigned char *strp; 823 824 str_keyid[3] = (dir == DIR_ENCRYPT) 825 ? ENCRYPT_ENC_KEYID : ENCRYPT_DEC_KEYID; 826 if (saveit) { 827 struct key_info *kp = &ki[(dir == DIR_ENCRYPT) ? 0 : 1]; 828 memmove(kp->keyid, keyid, keylen); 829 kp->keylen = keylen; 830 } 831 832 for (strp = &str_keyid[4]; keylen > 0; --keylen) { 833 if ((*strp++ = *keyid++) == IAC) 834 *strp++ = IAC; 835 } 836 *strp++ = IAC; 837 *strp++ = SE; 838 net_write(str_keyid, strp - str_keyid); 839 printsub('>', &str_keyid[2], strp - str_keyid - 2); 840 } 841 842 void 843 encrypt_auto(on) 844 int on; 845 { 846 if (on < 0) 847 autoencrypt ^= 1; 848 else 849 autoencrypt = on ? 1 : 0; 850 } 851 852 void 853 decrypt_auto(on) 854 int on; 855 { 856 if (on < 0) 857 autodecrypt ^= 1; 858 else 859 autodecrypt = on ? 1 : 0; 860 } 861 862 void 863 encrypt_start_output(type) 864 int type; 865 { 866 Encryptions *ep; 867 register unsigned char *p; 868 register int i; 869 870 if (!(ep = findencryption(type))) { 871 if (encrypt_debug_mode) { 872 printf(">>>%s: Can't encrypt with type %s (%d)\r\n", 873 Name, 874 ENCTYPE_NAME_OK(type) 875 ? ENCTYPE_NAME(type) : "(unknown)", 876 type); 877 } 878 return; 879 } 880 if (ep->start) { 881 i = (*ep->start)(DIR_ENCRYPT, Server); 882 if (encrypt_debug_mode) { 883 printf(">>>%s: Encrypt start: %s (%d) %s\r\n", 884 Name, 885 (i < 0) ? "failed" : 886 "initial negotiation in progress", 887 i, ENCTYPE_NAME(type)); 888 } 889 if (i) 890 return; 891 } 892 p = str_start + 3; 893 *p++ = ENCRYPT_START; 894 for (i = 0; i < ki[0].keylen; ++i) { 895 if ((*p++ = ki[0].keyid[i]) == IAC) 896 *p++ = IAC; 897 } 898 *p++ = IAC; 899 *p++ = SE; 900 net_write(str_start, p - str_start); 901 net_encrypt(); 902 printsub('>', &str_start[2], p - &str_start[2]); 903 /* 904 * If we are already encrypting in some mode, then 905 * encrypt the ring (which includes our request) in 906 * the old mode, mark it all as "clear text" and then 907 * switch to the new mode. 908 */ 909 encrypt_output = ep->output; 910 encrypt_mode = type; 911 if (encrypt_debug_mode) 912 printf(">>>%s: Started to encrypt output with type %s\r\n", 913 Name, ENCTYPE_NAME(type)); 914 if (encrypt_verbose) 915 printf("[ Output is now encrypted with type %s ]\r\n", 916 ENCTYPE_NAME(type)); 917 } 918 919 void 920 encrypt_send_end() 921 { 922 if (!encrypt_output) 923 return; 924 925 str_end[3] = ENCRYPT_END; 926 net_write(str_end, sizeof(str_end)); 927 net_encrypt(); 928 printsub('>', &str_end[2], sizeof(str_end) - 2); 929 /* 930 * Encrypt the output buffer now because it will not be done by 931 * netflush... 932 */ 933 encrypt_output = 0; 934 if (encrypt_debug_mode) 935 printf(">>>%s: Output is back to clear text\r\n", Name); 936 if (encrypt_verbose) 937 printf("[ Output is now clear text ]\r\n"); 938 } 939 940 void 941 encrypt_send_request_start() 942 { 943 register unsigned char *p; 944 register int i; 945 946 p = &str_start[3]; 947 *p++ = ENCRYPT_REQSTART; 948 for (i = 0; i < ki[1].keylen; ++i) { 949 if ((*p++ = ki[1].keyid[i]) == IAC) 950 *p++ = IAC; 951 } 952 *p++ = IAC; 953 *p++ = SE; 954 net_write(str_start, p - str_start); 955 printsub('>', &str_start[2], p - &str_start[2]); 956 if (encrypt_debug_mode) 957 printf(">>>%s: Request input to be encrypted\r\n", Name); 958 } 959 960 void 961 encrypt_send_request_end() 962 { 963 str_end[3] = ENCRYPT_REQEND; 964 net_write(str_end, sizeof(str_end)); 965 printsub('>', &str_end[2], sizeof(str_end) - 2); 966 967 if (encrypt_debug_mode) 968 printf(">>>%s: Request input to be clear text\r\n", Name); 969 } 970 971 void 972 encrypt_wait() 973 { 974 if (encrypt_debug_mode) 975 printf(">>>%s: in encrypt_wait\r\n", Name); 976 if (!havesessionkey || !(I_SUPPORT_ENCRYPT & remote_supports_decrypt)) 977 return; 978 while (autoencrypt && !encrypt_output) 979 if (telnet_spin()) 980 return; 981 } 982 983 void 984 encrypt_debug(mode) 985 int mode; 986 { 987 encrypt_debug_mode = mode; 988 } 989 990 void 991 encrypt_gen_printsub(data, cnt, buf, buflen) 992 unsigned char *data, *buf; 993 int cnt, buflen; 994 { 995 char tbuf[16], *cp; 996 997 cnt -= 2; 998 data += 2; 999 buf[buflen-1] = '\0'; 1000 buf[buflen-2] = '*'; 1001 buflen -= 2;; 1002 for (; cnt > 0; cnt--, data++) { 1003 sprintf(tbuf, " %d", *data); 1004 for (cp = tbuf; *cp && buflen > 0; --buflen) 1005 *buf++ = *cp++; 1006 if (buflen <= 0) 1007 return; 1008 } 1009 *buf = '\0'; 1010 } 1011 1012 void 1013 encrypt_printsub(data, cnt, buf, buflen) 1014 unsigned char *data, *buf; 1015 int cnt, buflen; 1016 { 1017 Encryptions *ep; 1018 register int type = data[1]; 1019 1020 for (ep = encryptions; ep->type && ep->type != type; ep++) 1021 ; 1022 1023 if (ep->printsub) 1024 (*ep->printsub)(data, cnt, buf, buflen); 1025 else 1026 encrypt_gen_printsub(data, cnt, buf, buflen); 1027 } 1028 #endif /* ENCRYPTION */ 1029