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 * Copyright 2004 Sun Microsystems, Inc. All rights reserved. 23 * Use is subject to license terms. 24 */ 25 26 /* 27 * Copyright (c) 1983, 1984, 1985, 1986, 1987, 1988, 1989 AT&T 28 * All Rights Reserved. 29 */ 30 31 /* 32 * University Copyright- Copyright (c) 1982, 1986, 1988 33 * The Regents of the University of California. 34 * All Rights Reserved. 35 * 36 * University Acknowledgment- Portions of this document are derived from 37 * software developed by the University of California, Berkeley, and its 38 * contributors. 39 */ 40 41 #pragma ident "%Z%%M% %I% %E% SMI" 42 43 /* 44 * Telnet server. 45 */ 46 #include <sys/types.h> 47 #include <sys/param.h> 48 #include <sys/socket.h> 49 #include <sys/wait.h> 50 #include <sys/file.h> 51 #include <sys/stat.h> 52 #include <sys/filio.h> 53 #include <sys/time.h> 54 #include <sys/stropts.h> 55 #include <sys/stream.h> 56 #include <sys/tihdr.h> 57 #include <sys/utsname.h> 58 #include <unistd.h> 59 60 #include <netinet/in.h> 61 62 #define AUTHWHO_STR 63 #define AUTHTYPE_NAMES 64 #define AUTHHOW_NAMES 65 #define AUTHRSP_NAMES 66 #define ENCRYPT_NAMES 67 68 #include <arpa/telnet.h> 69 #include <arpa/inet.h> 70 #include <stdio.h> 71 #include <stdarg.h> 72 #include <signal.h> 73 #include <errno.h> 74 #include <netdb.h> 75 #include <syslog.h> 76 #include <ctype.h> 77 #include <fcntl.h> 78 #include <sac.h> /* for SC_WILDC */ 79 #include <utmpx.h> 80 #include <sys/ttold.h> 81 #include <malloc.h> 82 #include <string.h> 83 #include <security/pam_appl.h> 84 #include <sys/tihdr.h> 85 #include <sys/logindmux.h> 86 #include <sys/telioctl.h> 87 #include <deflt.h> 88 #include <stdlib.h> 89 #include <string.h> 90 #include <stropts.h> 91 #include <termios.h> 92 93 #include <com_err.h> 94 #include <krb5.h> 95 #include <krb5_repository.h> 96 #include <des/des.h> 97 #include <rpc/des_crypt.h> 98 #include <sys/cryptmod.h> 99 #include <bsm/adt.h> 100 101 #define TELNETD_OPTS "Ss:a:dEXUhR:M:" 102 #ifdef DEBUG 103 #define DEBUG_OPTS "p:e" 104 #else 105 #define DEBUG_OPTS "" 106 #endif /* DEBUG */ 107 108 #define OPT_NO 0 /* won't do this option */ 109 #define OPT_YES 1 /* will do this option */ 110 #define OPT_YES_BUT_ALWAYS_LOOK 2 111 #define OPT_NO_BUT_ALWAYS_LOOK 3 112 113 #define MAXOPTLEN 256 114 #define MAXUSERNAMELEN 256 115 116 static char remopts[MAXOPTLEN]; 117 static char myopts[MAXOPTLEN]; 118 static uchar_t doopt[] = { (uchar_t)IAC, (uchar_t)DO, '%', 'c', 0 }; 119 static uchar_t dont[] = { (uchar_t)IAC, (uchar_t)DONT, '%', 'c', 0 }; 120 static uchar_t will[] = { (uchar_t)IAC, (uchar_t)WILL, '%', 'c', 0 }; 121 static uchar_t wont[] = { (uchar_t)IAC, (uchar_t)WONT, '%', 'c', 0 }; 122 /* 123 * I/O data buffers, pointers, and counters. 124 */ 125 static char ptyobuf[BUFSIZ], *pfrontp = ptyobuf, *pbackp = ptyobuf; 126 127 static char *netibuf, *netip; 128 static int netibufsize; 129 130 #define NIACCUM(c) { *netip++ = c; \ 131 ncc++; \ 132 } 133 134 static char netobuf[BUFSIZ], *nfrontp = netobuf, *nbackp = netobuf; 135 static char *neturg = 0; /* one past last bye of urgent data */ 136 /* the remote system seems to NOT be an old 4.2 */ 137 static int not42 = 1; 138 static char defaultfile[] = "/etc/default/telnetd"; 139 static char bannervar[] = "BANNER="; 140 141 static char BANNER1[] = "\r\n\r\n"; 142 static char BANNER2[] = "\r\n\r\0\r\n\r\0"; 143 144 /* 145 * buffer for sub-options - enlarged to 4096 to handle credentials 146 * from AUTH options 147 */ 148 static char subbuffer[4096], *subpointer = subbuffer, *subend = subbuffer; 149 #define SB_CLEAR() subpointer = subbuffer; 150 #define SB_TERM() { subend = subpointer; SB_CLEAR(); } 151 #define SB_ACCUM(c) if (subpointer < (subbuffer+sizeof (subbuffer))) { \ 152 *subpointer++ = (c); \ 153 } 154 #define SB_GET() ((*subpointer++)&0xff) 155 #define SB_EOF() (subpointer >= subend) 156 #define SB_LEN() (subend - subpointer) 157 158 #define MAXCCACHENAMELEN 36 159 #define MAXERRSTRLEN 1024 160 #define MAXPRINCLEN 256 161 162 static boolean_t auth_debug = 0; 163 static boolean_t negotiate_auth_krb5 = 1; 164 static boolean_t auth_negotiated = 0; 165 static int auth_status = 0; 166 static int auth_level = 0; 167 static char *AuthenticatingUser = NULL; 168 static char *krb5_name = NULL; 169 170 static krb5_address rsaddr = { 0, 0, 0, NULL }; 171 static krb5_address rsport = { 0, 0, 0, NULL }; 172 173 static krb5_context telnet_context = 0; 174 static krb5_auth_context auth_context = 0; 175 176 /* telnetd gets session key from here */ 177 static krb5_ticket *ticket = NULL; 178 static krb5_keyblock *session_key = NULL; 179 static char *telnet_srvtab = NULL; 180 181 typedef struct { 182 uchar_t AuthName; 183 uchar_t AuthHow; 184 char *AuthString; 185 } AuthInfo; 186 187 static AuthInfo auth_list[] = { 188 {AUTHTYPE_KERBEROS_V5, AUTH_WHO_CLIENT | AUTH_HOW_MUTUAL | 189 AUTH_ENCRYPT_ON, "KRB5 MUTUAL CRYPTO"}, 190 {AUTHTYPE_KERBEROS_V5, AUTH_WHO_CLIENT | AUTH_HOW_MUTUAL, 191 "KRB5 MUTUAL" }, 192 {AUTHTYPE_KERBEROS_V5, AUTH_WHO_CLIENT | AUTH_HOW_ONE_WAY, 193 "KRB5 1-WAY" }, 194 {0, 0, "NONE"} 195 }; 196 197 static AuthInfo NoAuth = {0, 0, NULL}; 198 199 static AuthInfo *authenticated = NULL; 200 201 #define PREAMBLE_SIZE 5 /* for auth_reply_str allocation */ 202 #define POSTAMBLE_SIZE 5 203 #define STR_DATA_LEN(len) ((len) * 2 + PREAMBLE_SIZE + POSTAMBLE_SIZE) 204 205 static void auth_name(uchar_t *, int); 206 static void auth_is(uchar_t *, int); 207 208 #define NO_ENCRYPTION 0x00 209 #define SEND_ENCRYPTED 0x01 210 #define RECV_ENCRYPTED 0x02 211 #define ENCRYPT_BOTH_WAYS (SEND_ENCRYPTED | RECV_ENCRYPTED) 212 213 static telnet_enc_data_t encr_data; 214 static boolean_t negotiate_encrypt = B_TRUE; 215 static boolean_t sent_encrypt_support = B_FALSE; 216 static boolean_t sent_will_encrypt = B_FALSE; 217 static boolean_t sent_do_encrypt = B_FALSE; 218 static boolean_t enc_debug = 0; 219 220 static void encrypt_session_key(Session_Key *key, cipher_info_t *cinfo); 221 static int encrypt_send_encrypt_is(); 222 223 extern void mit_des_fixup_key_parity(Block); 224 extern int krb5_setenv(const char *, const char *, int); 225 /* need to know what FD to use to talk to the crypto module */ 226 static int cryptmod_fd = -1; 227 228 #define LOGIN_PROGRAM "/bin/login" 229 230 /* 231 * State for recv fsm 232 */ 233 #define TS_DATA 0 /* base state */ 234 #define TS_IAC 1 /* look for double IAC's */ 235 #define TS_CR 2 /* CR-LF ->'s CR */ 236 #define TS_SB 3 /* throw away begin's... */ 237 #define TS_SE 4 /* ...end's (suboption negotiation) */ 238 #define TS_WILL 5 /* will option negotiation */ 239 #define TS_WONT 6 /* wont " */ 240 #define TS_DO 7 /* do " */ 241 #define TS_DONT 8 /* dont " */ 242 243 static int ncc; 244 static int master; /* master side of pty */ 245 static int pty; /* side of pty that gets ioctls */ 246 static int net; 247 static int inter; 248 extern char **environ; 249 static char *line; 250 static int SYNCHing = 0; /* we are in TELNET SYNCH mode */ 251 static int state = TS_DATA; 252 253 static int env_ovar = -1; /* XXX.sparker */ 254 static int env_ovalue = -1; /* XXX.sparker */ 255 static char pam_svc_name[64]; 256 static boolean_t telmod_init_done = B_FALSE; 257 258 static void doit(int, struct sockaddr_storage *); 259 static void willoption(int); 260 static void wontoption(int); 261 static void dooption(int); 262 static void dontoption(int); 263 static void fatal(int, char *); 264 static void fatalperror(int, char *, int); 265 static void mode(int, int); 266 static void interrupt(void); 267 static void drainstream(int); 268 static int readstream(int, char *, int); 269 static int send_oob(int fd, char *ptr, int count); 270 static int local_setenv(const char *name, const char *value, int rewrite); 271 static void local_unsetenv(const char *name); 272 static void suboption(void); 273 static int removemod(int f, char *modname); 274 static void willoption(int option); 275 static void wontoption(int option); 276 static void dooption(int option); 277 static void dontoption(int option); 278 static void write_data(const char *, ...); 279 static void write_data_len(const char *, int); 280 static void rmut(void); 281 static void cleanup(int); 282 static void telnet(int, int); 283 static void telrcv(void); 284 static void sendbrk(void); 285 static void ptyflush(void); 286 static void netclear(void); 287 static void netflush(void); 288 static void showbanner(void); 289 static void map_banner(char *); 290 static void defbanner(void); 291 static void ttloop(void); 292 293 /* 294 * The env_list linked list is used to store the environment variables 295 * until the final exec of login. A malevolent client might try to 296 * send an environment variable intended to affect the telnet daemon's 297 * execution. Right now the BANNER expansion is the only instance. 298 * Note that it is okay to pass the environment variables to login 299 * because login protects itself against environment variables mischief. 300 */ 301 302 struct envlist { 303 struct envlist *next; 304 char *name; 305 char *value; 306 int delete; 307 }; 308 309 static struct envlist *envlist_head = NULL; 310 311 /* 312 * The following are some clocks used to decide how to interpret 313 * the relationship between various variables. 314 */ 315 316 static struct { 317 int 318 system, /* what the current time is */ 319 echotoggle, /* last time user entered echo character */ 320 modenegotiated, /* last time operating mode negotiated */ 321 didnetreceive, /* last time we read data from network */ 322 ttypeopt, /* ttype will/won't received */ 323 ttypesubopt, /* ttype subopt is received */ 324 getterminal, /* time started to get terminal information */ 325 xdisplocopt, /* xdisploc will/wont received */ 326 xdisplocsubopt, /* xdisploc suboption received */ 327 nawsopt, /* window size will/wont received */ 328 nawssubopt, /* window size received */ 329 environopt, /* environment option will/wont received */ 330 oenvironopt, /* "old" environ option will/wont received */ 331 environsubopt, /* environment option suboption received */ 332 oenvironsubopt, /* "old environ option suboption received */ 333 gotDM; /* when did we last see a data mark */ 334 335 int getauth; 336 int authopt; /* Authentication option negotiated */ 337 int authdone; 338 339 int getencr; 340 int encropt; 341 int encr_support; 342 } clocks; 343 344 static int init_neg_done = 0; 345 static boolean_t resolve_hostname = 0; 346 static boolean_t show_hostinfo = 1; 347 348 #define settimer(x) (clocks.x = ++clocks.system) 349 #define sequenceIs(x, y) (clocks.x < clocks.y) 350 351 static void send_will(int); 352 static void send_wont(int); 353 static void send_do(int); 354 static char *__findenv(const char *name, int *offset); 355 356 /* ARGSUSED */ 357 static void 358 auth_finished(AuthInfo *ap, int result) 359 { 360 if ((authenticated = ap) == NULL) { 361 authenticated = &NoAuth; 362 if (myopts[TELOPT_ENCRYPT] == OPT_YES) 363 send_wont(TELOPT_ENCRYPT); 364 myopts[TELOPT_ENCRYPT] = remopts[TELOPT_ENCRYPT] = OPT_NO; 365 encr_data.encrypt.autoflag = 0; 366 } else if (result != AUTH_REJECT && 367 myopts[TELOPT_ENCRYPT] == OPT_YES && 368 remopts[TELOPT_ENCRYPT] == OPT_YES) { 369 370 /* 371 * Authentication successful, so we have a session key, and 372 * we're willing to do ENCRYPT, so send our ENCRYPT SUPPORT. 373 * 374 * Can't have sent ENCRYPT SUPPORT yet! And if we're sending it 375 * now it's really only because we did the DO ENCRYPT/WILL 376 * ENCRYPT dance before authentication, which is ok, but not too 377 * bright since we have to do the DONT ENCRYPT/WONT ENCRYPT 378 * dance if authentication fails, though clients typically just 379 * don't care. 380 */ 381 write_data("%c%c%c%c%c%c%c", 382 (uchar_t)IAC, 383 (uchar_t)SB, 384 (uchar_t)TELOPT_ENCRYPT, 385 (uchar_t)ENCRYPT_SUPPORT, 386 (uchar_t)TELOPT_ENCTYPE_DES_CFB64, 387 (uchar_t)IAC, 388 (uchar_t)SE); 389 390 netflush(); 391 392 sent_encrypt_support = B_TRUE; 393 394 if (enc_debug) 395 (void) fprintf(stderr, 396 "SENT ENCRYPT SUPPORT\n"); 397 398 (void) encrypt_send_encrypt_is(); 399 } 400 401 auth_status = result; 402 403 settimer(authdone); 404 } 405 406 static void 407 reply_to_client(AuthInfo *ap, int type, void *data, int len) 408 { 409 uchar_t reply[BUFSIZ]; 410 uchar_t *p = reply; 411 uchar_t *cd = (uchar_t *)data; 412 413 if (len == -1 && data != NULL) 414 len = strlen((char *)data); 415 else if (len > (sizeof (reply) - 9)) { 416 syslog(LOG_ERR, 417 "krb5 auth reply length too large (%d)", len); 418 if (auth_debug) 419 (void) fprintf(stderr, 420 "krb5 auth reply length too large (%d)\n", 421 len); 422 return; 423 } else if (data == NULL) 424 len = 0; 425 426 *p++ = IAC; 427 *p++ = SB; 428 *p++ = TELOPT_AUTHENTICATION; 429 *p++ = AUTHTYPE_KERBEROS_V5; 430 *p++ = ap->AuthName; 431 *p++ = ap->AuthHow; /* MUTUAL, ONE-WAY, etc */ 432 *p++ = type; /* RESPONSE or ACCEPT */ 433 while (len-- > 0) { 434 if ((*p++ = *cd++) == IAC) 435 *p++ = IAC; 436 } 437 *p++ = IAC; 438 *p++ = SE; 439 440 /* queue the data to be sent */ 441 write_data_len((const char *)reply, p-reply); 442 443 #if defined(AUTHTYPE_NAMES) && defined(AUTHWHO_STR) &&\ 444 defined(AUTHHOW_NAMES) && defined(AUTHRSP_NAMES) 445 if (auth_debug) { 446 (void) fprintf(stderr, "SENT TELOPT_AUTHENTICATION REPLY " 447 "%s %s|%s %s\n", 448 AUTHTYPE_NAME(ap->AuthName), 449 AUTHWHO_NAME(ap->AuthHow & AUTH_WHO_MASK), 450 AUTHHOW_NAME(ap->AuthHow & AUTH_HOW_MASK), 451 AUTHRSP_NAME(type)); 452 } 453 #endif /* AUTHTYPE_NAMES && AUTHWHO_NAMES && AUTHHOW_NAMES && AUTHRSP_NAMES */ 454 455 netflush(); 456 } 457 458 /* Decode, decrypt and store the forwarded creds in the local ccache. */ 459 static krb5_error_code 460 rd_and_store_forwarded_creds(krb5_context context, 461 krb5_auth_context auth_context, 462 krb5_data *inbuf, krb5_ticket *ticket, 463 char *username) 464 { 465 krb5_creds **creds; 466 krb5_error_code retval; 467 char ccname[MAXCCACHENAMELEN]; 468 krb5_ccache ccache = NULL; 469 470 if (retval = krb5_rd_cred(context, auth_context, inbuf, &creds, NULL)) 471 return (retval); 472 473 (void) sprintf(ccname, "FILE:/tmp/krb5cc_p%ld", getpid()); 474 (void) krb5_setenv("KRB5CCNAME", ccname, 1); 475 476 if ((retval = krb5_cc_default(context, &ccache))) 477 goto cleanup; 478 479 if ((retval = krb5_cc_initialize(context, ccache, 480 ticket->enc_part2->client)) != 0) 481 goto cleanup; 482 483 if ((retval = krb5_cc_store_cred(context, ccache, *creds)) != 0) 484 goto cleanup; 485 486 if ((retval = krb5_cc_close(context, ccache)) != 0) 487 goto cleanup; 488 489 if (username != NULL) { 490 /* 491 * This verifies that the user is valid on the local system, 492 * maps the username from KerberosV5 to unix, 493 * and moves the KRB5CCNAME file to the correct place 494 * /tmp/krb5cc_[uid] with correct ownership (0600 uid gid). 495 * 496 * NOTE: the user must be in the gsscred table in order to map 497 * from KRB5 to Unix. 498 */ 499 (void) krb5_kuserok(context, ticket->enc_part2->client, 500 username); 501 } 502 if (auth_debug) 503 (void) fprintf(stderr, 504 "Successfully stored forwarded creds\n"); 505 506 cleanup: 507 krb5_free_creds(context, *creds); 508 return (retval); 509 } 510 511 static void 512 kerberos5_is(AuthInfo *ap, uchar_t *data, int cnt) 513 { 514 krb5_error_code err = 0; 515 krb5_principal server; 516 krb5_keyblock *newkey = NULL; 517 krb5_keytab keytabid = 0; 518 krb5_data outbuf; 519 krb5_data inbuf; 520 krb5_authenticator *authenticator; 521 char errbuf[MAXERRSTRLEN]; 522 char *name; 523 krb5_data auth; 524 525 Session_Key skey; 526 527 if (cnt-- < 1) 528 return; 529 switch (*data++) { 530 case KRB_AUTH: 531 auth.data = (char *)data; 532 auth.length = cnt; 533 534 if (auth_context == NULL) { 535 err = krb5_auth_con_init(telnet_context, &auth_context); 536 if (err) 537 syslog(LOG_ERR, 538 "Error getting krb5 auth " 539 "context: %s", error_message(err)); 540 } 541 if (!err) { 542 krb5_rcache rcache; 543 544 err = krb5_auth_con_getrcache(telnet_context, 545 auth_context, 546 &rcache); 547 if (!err && !rcache) { 548 err = krb5_sname_to_principal(telnet_context, 549 0, 0, 550 KRB5_NT_SRV_HST, 551 &server); 552 if (!err) { 553 err = krb5_get_server_rcache( 554 telnet_context, 555 krb5_princ_component( 556 telnet_context, 557 server, 0), 558 &rcache); 559 560 krb5_free_principal(telnet_context, 561 server); 562 } 563 } 564 if (err) 565 syslog(LOG_ERR, 566 "Error allocating krb5 replay cache: %s", 567 error_message(err)); 568 else { 569 err = krb5_auth_con_setrcache(telnet_context, 570 auth_context, 571 rcache); 572 if (err) 573 syslog(LOG_ERR, 574 "Error creating krb5 " 575 "replay cache: %s", 576 error_message(err)); 577 } 578 } 579 if (!err && telnet_srvtab != NULL) 580 err = krb5_kt_resolve(telnet_context, 581 telnet_srvtab, &keytabid); 582 if (!err) 583 err = krb5_rd_req(telnet_context, &auth_context, &auth, 584 NULL, keytabid, NULL, &ticket); 585 if (err) { 586 (void) snprintf(errbuf, sizeof (errbuf), 587 "Error reading krb5 auth information:" 588 " %s", error_message(err)); 589 goto errout; 590 } 591 592 /* 593 * Verify that the correct principal was used 594 */ 595 if (krb5_princ_component(telnet_context, 596 ticket->server, 0)->length < MAXPRINCLEN) { 597 char princ[MAXPRINCLEN]; 598 (void) strncpy(princ, 599 krb5_princ_component(telnet_context, 600 ticket->server, 0)->data, 601 krb5_princ_component(telnet_context, 602 ticket->server, 0)->length); 603 princ[krb5_princ_component(telnet_context, 604 ticket->server, 0)->length] = '\0'; 605 if (strcmp("host", princ)) { 606 if (strlen(princ) < sizeof (errbuf) - 39) { 607 (void) snprintf(errbuf, sizeof (errbuf), 608 "incorrect service " 609 "name: \"%s\" != " 610 "\"host\"", 611 princ); 612 } else { 613 (void) strncpy(errbuf, 614 "incorrect service " 615 "name: principal != " 616 "\"host\"", 617 sizeof (errbuf)); 618 } 619 goto errout; 620 } 621 } else { 622 (void) strlcpy(errbuf, "service name too long", 623 sizeof (errbuf)); 624 goto errout; 625 } 626 627 err = krb5_auth_con_getauthenticator(telnet_context, 628 auth_context, 629 &authenticator); 630 if (err) { 631 (void) snprintf(errbuf, sizeof (errbuf), 632 "Failed to get authenticator: %s", 633 error_message(err)); 634 goto errout; 635 } 636 if ((ap->AuthHow & AUTH_ENCRYPT_MASK) == AUTH_ENCRYPT_ON && 637 !authenticator->checksum) { 638 (void) strlcpy(errbuf, 639 "authenticator is missing checksum", 640 sizeof (errbuf)); 641 goto errout; 642 } 643 if (authenticator->checksum) { 644 char type_check[2]; 645 krb5_checksum *cksum = authenticator->checksum; 646 krb5_keyblock *key; 647 krb5_data input; 648 krb5_boolean valid; 649 650 type_check[0] = ap->AuthName; 651 type_check[1] = ap->AuthHow; 652 653 err = krb5_auth_con_getkey(telnet_context, 654 auth_context, &key); 655 if (err) { 656 (void) snprintf(errbuf, sizeof (errbuf), 657 "Failed to get key from " 658 "authenticator: %s", 659 error_message(err)); 660 goto errout; 661 } 662 663 input.data = type_check; 664 input.length = 2; 665 err = krb5_c_verify_checksum(telnet_context, 666 key, 0, 667 &input, 668 cksum, 669 &valid); 670 if (!err && !valid) 671 err = KRB5KRB_AP_ERR_BAD_INTEGRITY; 672 673 if (err) { 674 (void) snprintf(errbuf, sizeof (errbuf), 675 "Kerberos checksum " 676 "verification failed: " 677 "%s", 678 error_message(err)); 679 goto errout; 680 } 681 krb5_free_keyblock(telnet_context, key); 682 } 683 684 krb5_free_authenticator(telnet_context, authenticator); 685 if ((ap->AuthHow & AUTH_HOW_MASK) == AUTH_HOW_MUTUAL) { 686 /* do ap_rep stuff here */ 687 if ((err = krb5_mk_rep(telnet_context, auth_context, 688 &outbuf))) { 689 (void) snprintf(errbuf, sizeof (errbuf), 690 "Failed to make " 691 "Kerberos auth reply: " 692 "%s", 693 error_message(err)); 694 goto errout; 695 } 696 reply_to_client(ap, KRB_RESPONSE, outbuf.data, 697 outbuf.length); 698 } 699 if (krb5_unparse_name(telnet_context, 700 ticket->enc_part2->client, 701 &name)) 702 name = 0; 703 reply_to_client(ap, KRB_ACCEPT, name, name ? -1 : 0); 704 if (auth_debug) { 705 syslog(LOG_NOTICE, 706 "\tKerberos5 identifies user as ``%s''\r\n", 707 name ? name : ""); 708 } 709 if (name != NULL) { 710 krb5_name = (char *)strdup(name); 711 } 712 auth_finished(ap, AUTH_USER); 713 714 if (name != NULL) 715 free(name); 716 krb5_auth_con_getremotesubkey(telnet_context, auth_context, 717 &newkey); 718 if (session_key != NULL) { 719 krb5_free_keyblock(telnet_context, session_key); 720 session_key = 0; 721 } 722 if (newkey != NULL) { 723 krb5_copy_keyblock(telnet_context, 724 newkey, &session_key); 725 krb5_free_keyblock(telnet_context, newkey); 726 } else { 727 krb5_copy_keyblock(telnet_context, 728 ticket->enc_part2->session, 729 &session_key); 730 } 731 732 /* 733 * Initialize encryption stuff. Currently, we are only 734 * supporting 8 byte keys and blocks. Check for this later. 735 */ 736 skey.type = SK_DES; 737 skey.length = DES_BLOCKSIZE; 738 skey.data = session_key->contents; 739 encrypt_session_key(&skey, &encr_data.encrypt); 740 encrypt_session_key(&skey, &encr_data.decrypt); 741 break; 742 case KRB_FORWARD: 743 inbuf.length = cnt; 744 inbuf.data = (char *)data; 745 if (auth_debug) 746 (void) fprintf(stderr, 747 "RCVD KRB_FORWARD data (%d bytes)\n", cnt); 748 749 if (auth_context != NULL) { 750 krb5_rcache rcache; 751 752 err = krb5_auth_con_getrcache(telnet_context, 753 auth_context, &rcache); 754 if (!err && !rcache) { 755 err = krb5_sname_to_principal(telnet_context, 756 0, 0, KRB5_NT_SRV_HST, &server); 757 if (!err) { 758 err = krb5_get_server_rcache( 759 telnet_context, 760 krb5_princ_component( 761 telnet_context, 762 server, 0), 763 &rcache); 764 krb5_free_principal(telnet_context, 765 server); 766 } 767 } 768 if (err) { 769 syslog(LOG_ERR, 770 "Error allocating krb5 replay cache: %s", 771 error_message(err)); 772 } else { 773 err = krb5_auth_con_setrcache(telnet_context, 774 auth_context, rcache); 775 if (err) 776 syslog(LOG_ERR, 777 "Error creating krb5 replay cache:" 778 " %s", 779 error_message(err)); 780 } 781 } 782 /* 783 * Use the 'rsaddr' and 'rsport' (remote service addr/port) 784 * from the original connection. This data is used to 785 * verify the forwarded credentials. 786 */ 787 if (!(err = krb5_auth_con_setaddrs(telnet_context, auth_context, 788 NULL, &rsaddr))) 789 err = krb5_auth_con_setports(telnet_context, 790 auth_context, NULL, &rsport); 791 792 if (err == 0) 793 /* 794 * If all is well, store the forwarded creds in 795 * the users local credential cache. 796 */ 797 err = rd_and_store_forwarded_creds(telnet_context, 798 auth_context, &inbuf, 799 ticket, 800 AuthenticatingUser); 801 if (err) { 802 (void) snprintf(errbuf, sizeof (errbuf), 803 "Read forwarded creds failed: %s", 804 error_message(err)); 805 syslog(LOG_ERR, "%s", errbuf); 806 807 reply_to_client(ap, KRB_FORWARD_REJECT, errbuf, -1); 808 if (auth_debug) 809 (void) fprintf(stderr, 810 "\tCould not read " 811 "forwarded credentials\r\n"); 812 } else 813 reply_to_client(ap, KRB_FORWARD_ACCEPT, (void *) 0, 0); 814 815 if (rsaddr.contents != NULL) 816 free(rsaddr.contents); 817 818 if (rsport.contents != NULL) 819 free(rsport.contents); 820 821 if (auth_debug) 822 (void) fprintf(stderr, "\tForwarded " 823 "credentials obtained\r\n"); 824 break; 825 default: 826 if (auth_debug) 827 (void) fprintf(stderr, 828 "\tUnknown Kerberos option %d\r\n", 829 data[-1]); 830 reply_to_client(ap, KRB_REJECT, (void *) 0, 0); 831 break; 832 } 833 return; 834 835 errout: 836 reply_to_client(ap, KRB_REJECT, errbuf, -1); 837 838 if (auth_debug) 839 (void) fprintf(stderr, "\tKerberos V5 error: %s\r\n", errbuf); 840 841 syslog(LOG_ERR, "%s", errbuf); 842 843 if (auth_context != NULL) { 844 krb5_auth_con_free(telnet_context, auth_context); 845 auth_context = 0; 846 } 847 } 848 849 static int 850 krb5_init() 851 { 852 int code = 0; 853 854 if (telnet_context == NULL) { 855 code = krb5_init_context(&telnet_context); 856 if (code != 0 && auth_debug) 857 syslog(LOG_NOTICE, 858 "Cannot initialize Kerberos V5: %s", 859 error_message(code)); 860 } 861 862 return (code); 863 } 864 865 static void 866 auth_name(uchar_t *data, int cnt) 867 { 868 char namebuf[MAXPRINCLEN]; 869 870 if (cnt < 1) { 871 if (auth_debug) 872 (void) fprintf(stderr, 873 "\t(auth_name) Empty NAME in auth " 874 "reply\n"); 875 return; 876 } 877 if (cnt > sizeof (namebuf)-1) { 878 if (auth_debug) 879 (void) fprintf(stderr, 880 "\t(auth_name) NAME exceeds %d bytes\n", 881 sizeof (namebuf)-1); 882 return; 883 } 884 (void) memcpy((void *)namebuf, (void *)data, cnt); 885 namebuf[cnt] = 0; 886 if (auth_debug) 887 (void) fprintf(stderr, "\t(auth_name) name [%s]\n", namebuf); 888 AuthenticatingUser = (char *)strdup(namebuf); 889 } 890 891 static void 892 auth_is(uchar_t *data, int cnt) 893 { 894 AuthInfo *aptr = auth_list; 895 896 if (cnt < 2) 897 return; 898 899 /* 900 * We failed to negoiate secure authentication 901 */ 902 if (data[0] == AUTHTYPE_NULL) { 903 auth_finished(0, AUTH_REJECT); 904 return; 905 } 906 907 while (aptr->AuthName != NULL && 908 (aptr->AuthName != data[0] || aptr->AuthHow != data[1])) 909 aptr++; 910 911 if (aptr != NULL) { 912 if (auth_debug) 913 (void) fprintf(stderr, "\t(auth_is) auth type is %s " 914 "(%d bytes)\n", aptr->AuthString, cnt); 915 916 if (aptr->AuthName == AUTHTYPE_KERBEROS_V5) 917 kerberos5_is(aptr, data+2, cnt-2); 918 } 919 } 920 921 static int 922 krb5_user_status(char *name, int namelen, int level) 923 { 924 int retval = AUTH_USER; 925 926 if (auth_debug) 927 (void) fprintf(stderr, "\t(krb5_user_status) level = %d " 928 "auth_level = %d user = %s\n", 929 level, auth_level, 930 (AuthenticatingUser != NULL ? AuthenticatingUser : "")); 931 932 if (level < AUTH_USER) 933 return (level); 934 935 if (AuthenticatingUser != NULL && 936 (retval = krb5_kuserok(telnet_context, ticket->enc_part2->client, 937 AuthenticatingUser))) { 938 (void) strncpy(name, AuthenticatingUser, namelen); 939 return (AUTH_VALID); 940 } else { 941 if (!retval) 942 syslog(LOG_ERR, 943 "Krb5 principal lacks permission to " 944 "access local account for %s", 945 AuthenticatingUser); 946 return (AUTH_USER); 947 } 948 } 949 950 /* 951 * Wrapper around /dev/urandom 952 */ 953 static int 954 getrandom(char *buf, int buflen) 955 { 956 static int devrandom = -1; 957 958 if (devrandom == -1 && 959 (devrandom = open("/dev/urandom", O_RDONLY)) == -1) { 960 fatalperror(net, "Unable to open /dev/urandom: ", 961 errno); 962 return (-1); 963 } 964 965 if (read(devrandom, buf, buflen) == -1) { 966 fatalperror(net, "Unable to read from /dev/urandom: ", 967 errno); 968 return (-1); 969 } 970 971 return (0); 972 } 973 974 /* 975 * encrypt_init 976 * 977 * Initialize the encryption data structures 978 */ 979 static void 980 encrypt_init() 981 { 982 (void) memset(&encr_data.encrypt, 0, sizeof (cipher_info_t)); 983 (void) memset(&encr_data.decrypt, 0, sizeof (cipher_info_t)); 984 985 encr_data.encrypt.state = ENCR_STATE_NOT_READY; 986 encr_data.decrypt.state = ENCR_STATE_NOT_READY; 987 } 988 989 /* 990 * encrypt_send_request_start 991 * 992 * Request that the remote side automatically start sending 993 * encrypted output 994 */ 995 static void 996 encrypt_send_request_start() 997 { 998 uchar_t buf[6+TELNET_MAXKEYIDLEN], *p; 999 1000 p = buf; 1001 1002 *p++ = IAC; 1003 *p++ = SB; 1004 *p++ = TELOPT_ENCRYPT; 1005 *p++ = ENCRYPT_REQSTART; 1006 /* 1007 * We are telling the remote side which 1008 * decrypt key we will use so that it may 1009 * encrypt in the same key. 1010 */ 1011 (void) memcpy(p, encr_data.decrypt.keyid, encr_data.decrypt.keyidlen); 1012 p += encr_data.decrypt.keyidlen; 1013 1014 *p++ = IAC; 1015 *p++ = SE; 1016 1017 write_data_len((const char *)buf, p-buf); 1018 netflush(); 1019 if (enc_debug) 1020 (void) fprintf(stderr, 1021 "SENT TELOPT_ENCRYPT ENCRYPT_REQSTART\n"); 1022 } 1023 1024 /* 1025 * encrypt_is 1026 * 1027 * When we receive the TELOPT_ENCRYPT ENCRYPT_IS ... 1028 * message, the client is telling us that it will be sending 1029 * encrypted data using the indicated cipher. 1030 * We must initialize the read (decrypt) side of our connection 1031 */ 1032 static void 1033 encrypt_is(uchar_t *data, int cnt) 1034 { 1035 register int type; 1036 register int iv_status = CFB64_IV_OK; 1037 register int lstate = 0; 1038 1039 uchar_t sbbuf[] = { 1040 (uchar_t)IAC, 1041 (uchar_t)SB, 1042 (uchar_t)TELOPT_ENCRYPT, 1043 (uchar_t)ENCRYPT_REPLY, 1044 (uchar_t)0, /* placeholder: sbbuf[4] */ 1045 (uchar_t)CFB64_IV_OK, /* placeholder: sbbuf[5] */ 1046 (uchar_t)IAC, 1047 (uchar_t)SE, 1048 }; 1049 1050 if (--cnt < 0) 1051 return; 1052 1053 type = sbbuf[4] = *data++; 1054 1055 /* 1056 * Steps to take: 1057 * 1. Create the proper stream Initialization vector 1058 * - copy the correct 'seed' to IV and output blocks 1059 * - set the correct key schedule 1060 * 2. Generate reply for the other side: 1061 * IAC SB TELOPT_ENCRYPT ENCRYPT_REPLY type CFB64_IV_OK 1062 * [ data ... ] IAC SE 1063 * 3. Tell crypto module: method, direction, IV 1064 */ 1065 switch (type) { 1066 case TELOPT_ENCTYPE_DES_CFB64: 1067 encr_data.decrypt.type = type; 1068 1069 lstate = encr_data.decrypt.state; 1070 if (enc_debug) 1071 (void) fprintf(stderr, 1072 "\t(encrypt_is) initial state = %d\n", 1073 lstate); 1074 /* 1075 * Before we extract the IV bytes, make sure we got 1076 * enough data. 1077 */ 1078 if (cnt < sizeof (Block)) { 1079 iv_status = CFB64_IV_BAD; 1080 if (enc_debug) 1081 (void) fprintf(stderr, 1082 "\t(encrypt_is) Not enough " 1083 "IV bytes\n"); 1084 lstate = ENCR_STATE_NOT_READY; 1085 } else { 1086 data++; /* skip over the CFB64_IV byte */ 1087 (void) memcpy(encr_data.decrypt.ivec, data, 1088 sizeof (Block)); 1089 lstate = ENCR_STATE_IN_PROGRESS; 1090 } 1091 break; 1092 case TELOPT_ENCTYPE_NULL: 1093 encr_data.decrypt.type = type; 1094 lstate &= ~ENCR_STATE_NO_RECV_IV; 1095 lstate &= ~ENCR_STATE_NO_SEND_IV; 1096 if (enc_debug) 1097 (void) fprintf(stderr, 1098 "\t(encrypt_is) We accept NULL encr\n"); 1099 break; 1100 default: 1101 iv_status = CFB64_IV_BAD; 1102 encr_data.decrypt.type = NULL; 1103 if (enc_debug) 1104 (void) fprintf(stderr, 1105 "\t(encrypt_is) Can't find type (%d) " 1106 "for initial negotiation\r\n", 1107 type); 1108 lstate = ENCR_STATE_NOT_READY; 1109 break; 1110 } 1111 1112 sbbuf[5] = (uchar_t)iv_status; /* either CFB64_IV_OK or BAD */ 1113 1114 if (iv_status == CFB64_IV_OK) { 1115 /* 1116 * send IV to crypto module and indicate it is for 1117 * decrypt only 1118 */ 1119 lstate &= ~ENCR_STATE_NO_RECV_IV; /* we received an OK IV */ 1120 lstate &= ~ENCR_STATE_NO_SEND_IV; /* we dont send an IV */ 1121 } else { 1122 /* tell crypto module to disable crypto on "read" stream */ 1123 lstate = ENCR_STATE_NOT_READY; 1124 } 1125 1126 write_data_len((const char *)sbbuf, sizeof (sbbuf)); 1127 netflush(); 1128 #ifdef ENCRYPT_NAMES 1129 if (enc_debug) 1130 (void) fprintf(stderr, 1131 "SENT TELOPT_ENCRYPT ENCRYPT_REPLY %s %s\n", 1132 ENCTYPE_NAME(type), 1133 (iv_status == CFB64_IV_OK ? "CFB64_IV_OK" : 1134 "CFB64_IV_BAD")); 1135 #endif /* ENCRYPT_NAMES */ 1136 /* Update the state of the decryption negotiation */ 1137 encr_data.decrypt.state = lstate; 1138 1139 if (lstate == ENCR_STATE_NOT_READY) 1140 encr_data.decrypt.autoflag = 0; 1141 else { 1142 if (lstate == ENCR_STATE_OK && encr_data.decrypt.autoflag) 1143 encrypt_send_request_start(); 1144 } 1145 if (enc_debug) 1146 (void) fprintf(stderr, 1147 "\t(encrypt_is) final DECRYPT state = %d\n", 1148 encr_data.decrypt.state); 1149 } 1150 1151 /* 1152 * encrypt_send_encrypt_is 1153 * 1154 * Tell the client what encryption we will use 1155 * and what our IV will be. 1156 */ 1157 static int 1158 encrypt_send_encrypt_is() 1159 { 1160 register int lstate; 1161 krb5_error_code kret; 1162 uchar_t sbbuf[MAXOPTLEN], *p; 1163 int i; 1164 1165 lstate = encr_data.encrypt.state; 1166 1167 if (encr_data.encrypt.type == ENCTYPE_NULL) { 1168 /* 1169 * Haven't received ENCRYPT SUPPORT yet or we couldn't agree 1170 * on a cipher. 1171 */ 1172 return (lstate); 1173 } 1174 1175 /* 1176 * - Create a random DES key 1177 * 1178 * - DES ECB encrypt 1179 * encrypt the IV using itself as the key. 1180 * 1181 * - Send response 1182 * IAC SB TELOPT_ENCRYPT ENCRYPT_IS CFB64 FB64_IV [ feed block ] 1183 * IAC SE 1184 * 1185 */ 1186 if (lstate == ENCR_STATE_NOT_READY) 1187 lstate = ENCR_STATE_IN_PROGRESS; 1188 else if ((lstate & ENCR_STATE_NO_SEND_IV) == 0) { 1189 if (enc_debug) 1190 (void) fprintf(stderr, 1191 "\t(encrypt_send_is) IV already sent," 1192 " state = %d\n", lstate); 1193 return (lstate); 1194 } 1195 1196 if (!VALIDKEY(encr_data.encrypt.krbdes_key)) { 1197 /* 1198 * Invalid key, set flag so we try again later 1199 * when we get a good one 1200 */ 1201 encr_data.encrypt.need_start = 1; 1202 if (enc_debug) 1203 (void) fprintf(stderr, 1204 "\t(encrypt_send_is) No Key, cannot " 1205 "start encryption yet\n"); 1206 return (lstate); 1207 } 1208 if (enc_debug) 1209 (void) fprintf(stderr, 1210 "\t(encrypt_send_is) Creating new feed\n"); 1211 1212 /* 1213 * Create a random feed and send it over. 1214 * 1215 * Use the /dev/[u]random interface to generate 1216 * our encryption IV. 1217 */ 1218 kret = getrandom((char *)encr_data.encrypt.ivec, sizeof (Block)); 1219 1220 if (kret) { 1221 if (enc_debug) 1222 (void) fprintf(stderr, 1223 "\t(encrypt_send_is) error from " 1224 "getrandom: %d\n", kret); 1225 syslog(LOG_ERR, "Failed to create encryption key (err %d)\n"); 1226 encr_data.encrypt.type = ENCTYPE_NULL; 1227 } else { 1228 mit_des_fixup_key_parity(encr_data.encrypt.ivec); 1229 } 1230 1231 p = sbbuf; 1232 *p++ = IAC; 1233 *p++ = SB; 1234 *p++ = TELOPT_ENCRYPT; 1235 *p++ = ENCRYPT_IS; 1236 *p++ = encr_data.encrypt.type; 1237 *p++ = CFB64_IV; 1238 1239 /* 1240 * Copy the IV bytes individually so that when a 1241 * 255 (telnet IAC) is used, it can be "escaped" by 1242 * adding it twice (telnet RFC 854). 1243 */ 1244 for (i = 0; i < sizeof (Block); i++) 1245 if ((*p++ = encr_data.encrypt.ivec[i]) == IAC) 1246 *p++ = IAC; 1247 1248 *p++ = IAC; 1249 *p++ = SE; 1250 write_data_len((const char *)sbbuf, (size_t)(p-sbbuf)); 1251 netflush(); 1252 1253 if (!kret) { 1254 lstate &= ~ENCR_STATE_NO_SEND_IV; /* we sent our IV */ 1255 lstate &= ~ENCR_STATE_NO_SEND_IV; /* dont need decrypt IV */ 1256 } 1257 encr_data.encrypt.state = lstate; 1258 1259 if (enc_debug) { 1260 int i; 1261 (void) fprintf(stderr, 1262 "SENT TELOPT_ENCRYPT ENCRYPT_IS %d CFB64_IV ", 1263 encr_data.encrypt.type); 1264 for (i = 0; i < (p-sbbuf); i++) 1265 (void) fprintf(stderr, "%d ", (int)sbbuf[i]); 1266 (void) fprintf(stderr, "\n"); 1267 } 1268 1269 return (lstate); 1270 } 1271 1272 /* 1273 * stop_stream 1274 * 1275 * Utility routine to send a CRIOCSTOP ioctl to the 1276 * crypto module (cryptmod). 1277 */ 1278 static void 1279 stop_stream(int fd, int dir) 1280 { 1281 struct strioctl crioc; 1282 uint32_t stopdir = dir; 1283 1284 crioc.ic_cmd = CRYPTIOCSTOP; 1285 crioc.ic_timout = -1; 1286 crioc.ic_len = sizeof (stopdir); 1287 crioc.ic_dp = (char *)&stopdir; 1288 1289 if (ioctl(fd, I_STR, &crioc)) { 1290 syslog(LOG_ERR, "Error sending CRYPTIOCSTOP ioctl: %m"); 1291 } 1292 } 1293 1294 /* 1295 * start_stream 1296 * 1297 * Utility routine to send a CRYPTIOCSTART ioctl to the 1298 * crypto module (cryptmod). This routine may contain optional 1299 * payload data that the cryptmod will interpret as bytes that 1300 * need to be decrypted and sent back up to the application 1301 * via the data stream. 1302 */ 1303 static void 1304 start_stream(int fd, int dir, int datalen, char *data) 1305 { 1306 struct strioctl crioc; 1307 1308 crioc.ic_cmd = (dir == CRYPT_ENCRYPT ? CRYPTIOCSTARTENC : 1309 CRYPTIOCSTARTDEC); 1310 crioc.ic_timout = -1; 1311 crioc.ic_len = datalen; 1312 crioc.ic_dp = data; 1313 1314 if (ioctl(fd, I_STR, &crioc)) { 1315 syslog(LOG_ERR, "Error sending CRYPTIOCSTART ioctl: %m"); 1316 } 1317 } 1318 1319 /* 1320 * encrypt_start_output 1321 * 1322 * Tell the other side to start encrypting its data 1323 */ 1324 static void 1325 encrypt_start_output() 1326 { 1327 int lstate; 1328 uchar_t *p; 1329 uchar_t sbbuf[MAXOPTLEN]; 1330 struct strioctl crioc; 1331 struct cr_info_t cki; 1332 1333 /* 1334 * Initialize crypto and send the ENCRYPT_IS msg 1335 */ 1336 lstate = encrypt_send_encrypt_is(); 1337 1338 if (lstate != ENCR_STATE_OK) { 1339 if (enc_debug) 1340 (void) fprintf(stderr, 1341 "\t(encrypt_start_output) ENCRYPT state " 1342 "= %d\n", lstate); 1343 return; 1344 } 1345 1346 p = sbbuf; 1347 1348 *p++ = IAC; 1349 *p++ = SB; 1350 *p++ = TELOPT_ENCRYPT; 1351 *p++ = ENCRYPT_START; 1352 1353 (void) memcpy(p, encr_data.encrypt.keyid, encr_data.encrypt.keyidlen); 1354 p += encr_data.encrypt.keyidlen; 1355 1356 *p++ = IAC; 1357 *p++ = SE; 1358 1359 /* Flush this data out before we start encrypting */ 1360 write_data_len((const char *)sbbuf, (int)(p-sbbuf)); 1361 netflush(); 1362 1363 if (enc_debug) 1364 (void) fprintf(stderr, "SENT TELOPT_ENCRYPT ENCRYPT_START %d " 1365 "(lstate = %d) data waiting = %d\n", 1366 (int)encr_data.encrypt.keyid[0], 1367 lstate, nfrontp-nbackp); 1368 1369 encr_data.encrypt.state = lstate; 1370 1371 /* 1372 * tell crypto module what key to use for encrypting 1373 * Note that the ENCRYPT has not yet been enabled, but we 1374 * need to first set the crypto key to use. 1375 */ 1376 cki.direction_mask = CRYPT_ENCRYPT; 1377 1378 if (encr_data.encrypt.type == TELOPT_ENCTYPE_DES_CFB64) { 1379 cki.crypto_method = CRYPT_METHOD_DES_CFB; 1380 } else { 1381 if (enc_debug) 1382 (void) fprintf(stderr, 1383 "\t(encrypt_start_output) - unknown " 1384 "crypto_method %d\n", 1385 encr_data.encrypt.type); 1386 syslog(LOG_ERR, "unrecognized crypto encrypt method: %d", 1387 encr_data.encrypt.type); 1388 1389 return; 1390 } 1391 1392 /* 1393 * If we previously configured this crypto method, we dont want to 1394 * overwrite the key or ivec information already given to the crypto 1395 * module as it will cause the cipher data between the client and server 1396 * to become out of synch and impossible to decipher. 1397 */ 1398 if (encr_data.encrypt.setup == cki.crypto_method) { 1399 cki.keylen = 0; 1400 cki.iveclen = 0; 1401 } else { 1402 cki.keylen = DES_BLOCKSIZE; 1403 (void) memcpy(cki.key, (void *)encr_data.encrypt.krbdes_key, 1404 DES_BLOCKSIZE); 1405 1406 cki.iveclen = DES_BLOCKSIZE; 1407 (void) memcpy(cki.ivec, (void *)encr_data.encrypt.ivec, 1408 DES_BLOCKSIZE); 1409 1410 cki.ivec_usage = IVEC_ONETIME; 1411 } 1412 1413 cki.option_mask = 0; 1414 1415 /* Stop encrypt side prior to setup so we dont lose data */ 1416 stop_stream(cryptmod_fd, CRYPT_ENCRYPT); 1417 1418 crioc.ic_cmd = CRYPTIOCSETUP; 1419 crioc.ic_timout = -1; 1420 crioc.ic_len = sizeof (struct cr_info_t); 1421 crioc.ic_dp = (char *)&cki; 1422 1423 if (ioctl(cryptmod_fd, I_STR, &crioc)) { 1424 perror("ioctl(CRYPTIOCSETUP) [encrypt_start_output] error"); 1425 } else { 1426 /* Setup completed OK */ 1427 encr_data.encrypt.setup = cki.crypto_method; 1428 } 1429 1430 /* 1431 * We do not check for "stuck" data when setting up the 1432 * outbound "encrypt" channel. Any data queued prior to 1433 * this IOCTL will get processed correctly without our help. 1434 */ 1435 start_stream(cryptmod_fd, CRYPT_ENCRYPT, 0, NULL); 1436 1437 /* 1438 * tell crypto module to start encrypting 1439 */ 1440 if (enc_debug) 1441 (void) fprintf(stderr, 1442 "\t(encrypt_start_output) Encrypting output\n"); 1443 } 1444 1445 /* 1446 * encrypt_request_start 1447 * 1448 * The client requests that we start encryption immediately after 1449 * successful negotiation 1450 */ 1451 static void 1452 encrypt_request_start(void) 1453 { 1454 if (encr_data.encrypt.type == ENCTYPE_NULL) { 1455 encr_data.encrypt.autoflag = 1; 1456 if (enc_debug) 1457 (void) fprintf(stderr, "\t(encrypt_request_start) " 1458 "autoencrypt = ON\n"); 1459 } else { 1460 encrypt_start_output(); 1461 } 1462 } 1463 1464 /* 1465 * encrypt_end 1466 * 1467 * ENCRYPT END received, stop decrypting the read stream 1468 */ 1469 static void 1470 encrypt_end(int direction) 1471 { 1472 struct cr_info_t cki; 1473 struct strioctl crioc; 1474 uint32_t stopdir; 1475 1476 stopdir = (direction == TELNET_DIR_DECRYPT ? CRYPT_DECRYPT : 1477 CRYPT_ENCRYPT); 1478 1479 stop_stream(cryptmod_fd, stopdir); 1480 1481 /* 1482 * Call this function when we wish to disable crypto in 1483 * either direction (ENCRYPT or DECRYPT) 1484 */ 1485 cki.direction_mask = (direction == TELNET_DIR_DECRYPT ? CRYPT_DECRYPT : 1486 CRYPT_ENCRYPT); 1487 cki.crypto_method = CRYPT_METHOD_NONE; 1488 cki.option_mask = 0; 1489 1490 cki.keylen = 0; 1491 cki.iveclen = 0; 1492 1493 crioc.ic_cmd = CRYPTIOCSETUP; 1494 crioc.ic_timout = -1; 1495 crioc.ic_len = sizeof (cki); 1496 crioc.ic_dp = (char *)&cki; 1497 1498 if (ioctl(cryptmod_fd, I_STR, &crioc)) { 1499 perror("ioctl(CRYPTIOCSETUP) [encrypt_end] error"); 1500 } 1501 1502 start_stream(cryptmod_fd, stopdir, 0, NULL); 1503 } 1504 1505 /* 1506 * encrypt_request_end 1507 * 1508 * When we receive a REQEND from the client, it means 1509 * that we are supposed to stop encrypting 1510 */ 1511 static void 1512 encrypt_request_end() 1513 { 1514 /* 1515 * Tell the other side we are done encrypting 1516 */ 1517 1518 write_data("%c%c%c%c%c%c", 1519 (uchar_t)IAC, 1520 (uchar_t)SB, 1521 (uchar_t)TELOPT_ENCRYPT, 1522 (uchar_t)ENCRYPT_END, 1523 (uchar_t)IAC, 1524 (uchar_t)SE); 1525 netflush(); 1526 if (enc_debug) 1527 (void) fprintf(stderr, "SENT TELOPT_ENCRYPT ENCRYPT_END\n"); 1528 1529 /* 1530 * Turn off encryption of the write stream 1531 */ 1532 encrypt_end(TELNET_DIR_ENCRYPT); 1533 } 1534 1535 /* 1536 * encrypt_send_request_end 1537 * 1538 * We stop encrypting the write stream and tell the other side about it. 1539 */ 1540 static void 1541 encrypt_send_request_end() 1542 { 1543 write_data("%c%c%c%c%c%c", 1544 (uchar_t)IAC, 1545 (uchar_t)SB, 1546 (uchar_t)TELOPT_ENCRYPT, 1547 (uchar_t)ENCRYPT_REQEND, 1548 (uchar_t)IAC, 1549 (uchar_t)SE); 1550 netflush(); 1551 if (enc_debug) 1552 (void) fprintf(stderr, "SENT TELOPT_ENCRYPT ENCRYPT_REQEND\n"); 1553 } 1554 1555 /* 1556 * encrypt_start 1557 * 1558 * The client is going to start sending encrypted data 1559 * using the previously negotiated cipher (see what we set 1560 * when we did the REPLY in encrypt_is). 1561 */ 1562 static void 1563 encrypt_start(void) 1564 { 1565 struct cr_info_t cki; 1566 struct strioctl crioc; 1567 int bytes = 0; 1568 char *dataptr = NULL; 1569 1570 if (encr_data.decrypt.type == ENCTYPE_NULL) { 1571 if (enc_debug) 1572 (void) fprintf(stderr, 1573 "\t(encrypt_start) No DECRYPT method " 1574 "defined yet\n"); 1575 encrypt_send_request_end(); 1576 return; 1577 } 1578 1579 cki.direction_mask = CRYPT_DECRYPT; 1580 1581 if (encr_data.decrypt.type == TELOPT_ENCTYPE_DES_CFB64) { 1582 cki.crypto_method = CRYPT_METHOD_DES_CFB; 1583 } else { 1584 if (enc_debug) 1585 (void) fprintf(stderr, 1586 "\t(encrypt_start) - unknown " 1587 "crypto_method %d\n", encr_data.decrypt.type); 1588 1589 syslog(LOG_ERR, "unrecognized crypto decrypt method: %d", 1590 encr_data.decrypt.type); 1591 1592 return; 1593 } 1594 1595 /* 1596 * Don't overwrite previously configured key and ivec info 1597 */ 1598 if (encr_data.decrypt.setup != cki.crypto_method) { 1599 (void) memcpy(cki.key, (void *)encr_data.decrypt.krbdes_key, 1600 DES_BLOCKSIZE); 1601 (void) memcpy(cki.ivec, (void *)encr_data.decrypt.ivec, 1602 DES_BLOCKSIZE); 1603 1604 cki.keylen = DES_BLOCKSIZE; 1605 cki.iveclen = DES_BLOCKSIZE; 1606 cki.ivec_usage = IVEC_ONETIME; 1607 } else { 1608 cki.keylen = 0; 1609 cki.iveclen = 0; 1610 } 1611 cki.option_mask = 0; 1612 1613 stop_stream(cryptmod_fd, CRYPT_DECRYPT); 1614 1615 crioc.ic_cmd = CRYPTIOCSETUP; 1616 crioc.ic_timout = -1; 1617 crioc.ic_len = sizeof (struct cr_info_t); 1618 crioc.ic_dp = (char *)&cki; 1619 1620 if (ioctl(cryptmod_fd, I_STR, &crioc)) { 1621 syslog(LOG_ERR, "ioctl(CRYPTIOCSETUP) [encrypt_start] " 1622 "error: %m"); 1623 } else { 1624 encr_data.decrypt.setup = cki.crypto_method; 1625 } 1626 if (enc_debug) 1627 (void) fprintf(stderr, 1628 "\t(encrypt_start) called CRYPTIOCSETUP for " 1629 "decrypt side\n"); 1630 1631 /* 1632 * Read any data stuck between the cryptmod and the application 1633 * so we can pass it back down to be properly decrypted after 1634 * this operation finishes. 1635 */ 1636 if (ioctl(cryptmod_fd, I_NREAD, &bytes) < 0) { 1637 syslog(LOG_ERR, "I_NREAD returned error %m"); 1638 bytes = 0; 1639 } 1640 1641 /* 1642 * Any data which was read AFTER the ENCRYPT START message 1643 * must be sent back down to be decrypted properly. 1644 * 1645 * 'ncc' is the number of bytes that have been read but 1646 * not yet processed by the telnet state machine. 1647 * 1648 * 'bytes' is the number of bytes waiting to be read from 1649 * the stream. 1650 * 1651 * If either one is a positive value, then those bytes 1652 * must be pulled up and sent back down to be decrypted. 1653 */ 1654 if (ncc || bytes) { 1655 drainstream(bytes); 1656 if (enc_debug) 1657 (void) fprintf(stderr, 1658 "\t(encrypt_start) after drainstream, " 1659 "ncc=%d bytes = %d\n", ncc, bytes); 1660 bytes += ncc; 1661 dataptr = netip; 1662 } 1663 1664 start_stream(cryptmod_fd, CRYPT_DECRYPT, bytes, dataptr); 1665 1666 /* 1667 * The bytes putback into the stream are no longer 1668 * available to be read by the server, so adjust the 1669 * counter accordingly. 1670 */ 1671 ncc = 0; 1672 netip = netibuf; 1673 (void) memset(netip, 0, netibufsize); 1674 1675 #ifdef ENCRYPT_NAMES 1676 if (enc_debug) { 1677 (void) fprintf(stderr, 1678 "\t(encrypt_start) Start DECRYPT using %s\n", 1679 ENCTYPE_NAME(encr_data.decrypt.type)); 1680 } 1681 #endif /* ENCRYPT_NAMES */ 1682 } 1683 1684 /* 1685 * encrypt_support 1686 * 1687 * Called when we recieve the TELOPT_ENCRYPT SUPPORT [ encr type list ] 1688 * message from a client. 1689 * 1690 * Choose an agreeable method (DES_CFB64) and 1691 * respond with TELOPT_ENCRYPT ENCRYPT_IS [ desired crypto method ] 1692 * 1693 * from: RFC 2946 1694 */ 1695 static void 1696 encrypt_support(char *data, int cnt) 1697 { 1698 int lstate = ENCR_STATE_NOT_READY; 1699 int type, use_type = 0; 1700 1701 while (cnt-- > 0 && use_type == 0) { 1702 type = *data++; 1703 #ifdef ENCRYPT_NAMES 1704 if (enc_debug) 1705 (void) fprintf(stderr, 1706 "RCVD ENCRYPT SUPPORT %s\n", 1707 ENCTYPE_NAME(type)); 1708 #endif /* ENCRYPT_NAMES */ 1709 /* 1710 * Prefer CFB64 1711 */ 1712 if (type == TELOPT_ENCTYPE_DES_CFB64) { 1713 use_type = type; 1714 } 1715 } 1716 encr_data.encrypt.type = use_type; 1717 1718 if (use_type != TELOPT_ENCTYPE_NULL && 1719 authenticated != NULL && authenticated != &NoAuth && 1720 auth_status != AUTH_REJECT) { 1721 1722 /* Authenticated -> have session key -> send ENCRYPT IS */ 1723 lstate = encrypt_send_encrypt_is(); 1724 if (lstate == ENCR_STATE_OK) 1725 encrypt_start_output(); 1726 } else if (use_type == TELOPT_ENCTYPE_NULL) { 1727 if (enc_debug) 1728 (void) fprintf(stderr, 1729 "\t(encrypt_support) Cannot agree " 1730 "on crypto algorithm, output encryption " 1731 "disabled.\n"); 1732 1733 /* 1734 * Cannot agree on crypto algorithm 1735 * RFC 2946 sez: 1736 * send "IAC SB ENCRYPT IS NULL IAC SE" 1737 * optionally, also send IAC WONT ENCRYPT 1738 */ 1739 write_data("%c%c%c%c%c%c%c", 1740 (uchar_t)IAC, 1741 (uchar_t)SB, 1742 (uchar_t)TELOPT_ENCRYPT, 1743 (uchar_t)ENCRYPT_IS, 1744 (uchar_t)TELOPT_ENCTYPE_NULL, 1745 (uchar_t)IAC, 1746 (uchar_t)SE); 1747 send_wont(TELOPT_ENCRYPT); 1748 netflush(); 1749 if (enc_debug) 1750 (void) fprintf(stderr, 1751 "SENT TELOPT_ENCRYPT ENCRYPT_IS " 1752 "[NULL]\n"); 1753 1754 remopts[TELOPT_ENCRYPT] = OPT_NO; 1755 } 1756 settimer(encr_support); 1757 } 1758 1759 /* 1760 * encrypt_send_keyid 1761 * 1762 * Sent the key id we will use to the client 1763 */ 1764 static void 1765 encrypt_send_keyid(int dir, uchar_t *keyid, int keylen, boolean_t saveit) 1766 { 1767 uchar_t sbbuf[128], *p; 1768 1769 p = sbbuf; 1770 1771 *p++ = IAC; 1772 *p++ = SB; 1773 *p++ = TELOPT_ENCRYPT; 1774 *p++ = (dir == TELNET_DIR_ENCRYPT ? ENCRYPT_ENC_KEYID : 1775 ENCRYPT_DEC_KEYID); 1776 if (saveit) { 1777 if (enc_debug) 1778 (void) fprintf(stderr, 1779 "\t(send_keyid) store %d byte %s keyid\n", 1780 keylen, 1781 (dir == TELNET_DIR_ENCRYPT ? "ENCRYPT" : 1782 "DECRYPT")); 1783 1784 if (dir == TELNET_DIR_ENCRYPT) { 1785 (void) memcpy(encr_data.encrypt.keyid, keyid, keylen); 1786 encr_data.encrypt.keyidlen = keylen; 1787 } else { 1788 (void) memcpy(encr_data.decrypt.keyid, keyid, keylen); 1789 encr_data.decrypt.keyidlen = keylen; 1790 } 1791 } 1792 (void) memcpy(p, keyid, keylen); 1793 p += keylen; 1794 1795 *p++ = IAC; 1796 *p++ = SE; 1797 write_data_len((const char *)sbbuf, (size_t)(p-sbbuf)); 1798 netflush(); 1799 1800 if (enc_debug) 1801 (void) fprintf(stderr, "SENT TELOPT_ENCRYPT %s %d\n", 1802 (dir == TELNET_DIR_ENCRYPT ? "ENC_KEYID" : 1803 "DEC_KEYID"), keyid[0]); 1804 } 1805 1806 /* 1807 * encrypt_reply 1808 * 1809 * When we receive the TELOPT_ENCRYPT REPLY [crtype] CFB64_IV_OK IAC SE 1810 * message, process it accordingly. 1811 * If the vector is acceptable, tell client we are encrypting and 1812 * enable encryption on our write stream. 1813 * 1814 * Negotiate the KEYID next.. 1815 * RFC 2946, 2952 1816 */ 1817 static void 1818 encrypt_reply(char *data, int len) 1819 { 1820 uchar_t type = (uchar_t)(*data++); 1821 uchar_t result = (uchar_t)(*data); 1822 int lstate; 1823 1824 #ifdef ENCRYPT_NAMES 1825 if (enc_debug) 1826 (void) fprintf(stderr, 1827 "\t(encrypt_reply) ENCRYPT REPLY %s %s [len=%d]\n", 1828 ENCRYPT_NAME(type), 1829 (result == CFB64_IV_OK ? "CFB64_IV_OK" : 1830 "CFB64_IV_BAD"), len); 1831 #endif /* ENCRYPT_NAMES */ 1832 1833 lstate = encr_data.encrypt.state; 1834 if (enc_debug) 1835 (void) fprintf(stderr, 1836 "\t(encrypt_reply) initial ENCRYPT state = %d\n", 1837 lstate); 1838 switch (result) { 1839 case CFB64_IV_OK: 1840 if (lstate == ENCR_STATE_NOT_READY) 1841 lstate = ENCR_STATE_IN_PROGRESS; 1842 lstate &= ~ENCR_STATE_NO_RECV_IV; /* we got the IV */ 1843 lstate &= ~ENCR_STATE_NO_SEND_IV; /* we dont need to send IV */ 1844 1845 /* 1846 * The correct response here is to send the encryption key id 1847 * RFC 2752. 1848 * 1849 * Send keyid 0 to indicate that we will just use default 1850 * keys. 1851 */ 1852 encrypt_send_keyid(TELNET_DIR_ENCRYPT, (uchar_t *)"\0", 1, 1); 1853 1854 break; 1855 case CFB64_IV_BAD: 1856 /* 1857 * Clear the ivec 1858 */ 1859 (void) memset(encr_data.encrypt.ivec, 0, sizeof (Block)); 1860 lstate = ENCR_STATE_NOT_READY; 1861 break; 1862 default: 1863 if (enc_debug) 1864 (void) fprintf(stderr, 1865 "\t(encrypt_reply) Got unknown IV value in " 1866 "REPLY message\n"); 1867 lstate = ENCR_STATE_NOT_READY; 1868 break; 1869 } 1870 1871 encr_data.encrypt.state = lstate; 1872 if (lstate == ENCR_STATE_NOT_READY) { 1873 encr_data.encrypt.autoflag = 0; 1874 encr_data.encrypt.type = ENCTYPE_NULL; 1875 if (enc_debug) 1876 (void) fprintf(stderr, 1877 "\t(encrypt_reply) encrypt.autoflag = " 1878 "OFF\n"); 1879 } else { 1880 encr_data.encrypt.type = type; 1881 if ((lstate == ENCR_STATE_OK) && encr_data.encrypt.autoflag) 1882 encrypt_start_output(); 1883 } 1884 1885 if (enc_debug) 1886 (void) fprintf(stderr, 1887 "\t(encrypt_reply) ENCRYPT final state = %d\n", 1888 lstate); 1889 } 1890 1891 static void 1892 encrypt_set_keyid_state(uchar_t *keyid, int *keyidlen, int dir) 1893 { 1894 int lstate; 1895 1896 lstate = (dir == TELNET_DIR_ENCRYPT ? encr_data.encrypt.state : 1897 encr_data.decrypt.state); 1898 1899 if (enc_debug) 1900 (void) fprintf(stderr, 1901 "\t(set_keyid_state) %s initial state = %d\n", 1902 (dir == TELNET_DIR_ENCRYPT ? "ENCRYPT" : 1903 "DECRYPT"), lstate); 1904 1905 /* 1906 * Currently, we only support using the default keyid, 1907 * so it should be an error if the len > 1 or the keyid != 0. 1908 */ 1909 if (*keyidlen != 1 || (*keyid != '\0')) { 1910 if (enc_debug) 1911 (void) fprintf(stderr, 1912 "\t(set_keyid_state) unexpected keyid: " 1913 "len=%d value=%d\n", *keyidlen, *keyid); 1914 *keyidlen = 0; 1915 syslog(LOG_ERR, "rcvd unexpected keyid %d - only keyid of 0 " 1916 "is supported", *keyid); 1917 } else { 1918 /* 1919 * We move to the "IN_PROGRESS" state. 1920 */ 1921 if (lstate == ENCR_STATE_NOT_READY) 1922 lstate = ENCR_STATE_IN_PROGRESS; 1923 /* 1924 * Clear the NO_KEYID bit because we now have a valid keyid 1925 */ 1926 lstate &= ~ENCR_STATE_NO_KEYID; 1927 } 1928 1929 if (enc_debug) 1930 (void) fprintf(stderr, 1931 "\t(set_keyid_state) %s final state = %d\n", 1932 (dir == TELNET_DIR_ENCRYPT ? "ENCRYPT" : 1933 "DECRYPT"), lstate); 1934 1935 if (dir == TELNET_DIR_ENCRYPT) 1936 encr_data.encrypt.state = lstate; 1937 else 1938 encr_data.decrypt.state = lstate; 1939 } 1940 1941 /* 1942 * encrypt_keyid 1943 * 1944 * Set the keyid value in the key_info structure. 1945 * if necessary send a response to the sender 1946 */ 1947 static void 1948 encrypt_keyid(uchar_t *newkeyid, int *keyidlen, uchar_t *keyid, 1949 int len, int dir) 1950 { 1951 if (len > TELNET_MAXNUMKEYS) { 1952 if (enc_debug) 1953 (void) fprintf(stderr, 1954 "\t(keyid) keylen too big (%d)\n", len); 1955 return; 1956 } 1957 1958 if (enc_debug) { 1959 (void) fprintf(stderr, "\t(keyid) set KEYID for %s len = %d\n", 1960 (dir == TELNET_DIR_ENCRYPT ? "ENCRYPT" : 1961 "DECRYPT"), len); 1962 } 1963 1964 if (len == 0) { 1965 if (*keyidlen == 0) { 1966 if (enc_debug) 1967 (void) fprintf(stderr, 1968 "\t(keyid) Got 0 length keyid - " 1969 "failure\n"); 1970 return; 1971 } 1972 *keyidlen = 0; 1973 encrypt_set_keyid_state(newkeyid, keyidlen, dir); 1974 1975 } else if (len != *keyidlen || memcmp(keyid, newkeyid, len)) { 1976 if (enc_debug) 1977 (void) fprintf(stderr, 1978 "\t(keyid) Setting new key (%d bytes)\n", 1979 len); 1980 1981 *keyidlen = len; 1982 (void) memcpy(newkeyid, keyid, len); 1983 1984 encrypt_set_keyid_state(newkeyid, keyidlen, dir); 1985 } else { 1986 encrypt_set_keyid_state(newkeyid, keyidlen, dir); 1987 1988 if (enc_debug) 1989 (void) fprintf(stderr, 1990 "\t(keyid) %s Key already in place," 1991 "state = %d autoflag=%d\n", 1992 (dir == TELNET_DIR_ENCRYPT ? "ENCRYPT" : "DECRYPT"), 1993 (dir == TELNET_DIR_ENCRYPT ? encr_data.encrypt.state: 1994 encr_data.decrypt.state), 1995 (dir == TELNET_DIR_ENCRYPT ? 1996 encr_data.encrypt.autoflag: 1997 encr_data.decrypt.autoflag)); 1998 1999 /* key already in place */ 2000 if ((encr_data.encrypt.state == ENCR_STATE_OK) && 2001 dir == TELNET_DIR_ENCRYPT && encr_data.encrypt.autoflag) { 2002 encrypt_start_output(); 2003 } 2004 return; 2005 } 2006 2007 if (enc_debug) 2008 (void) fprintf(stderr, "\t(keyid) %s final state = %d\n", 2009 (dir == TELNET_DIR_ENCRYPT ? "ENCRYPT" : 2010 "DECRYPT"), 2011 (dir == TELNET_DIR_ENCRYPT ? 2012 encr_data.encrypt.state : 2013 encr_data.decrypt.state)); 2014 2015 encrypt_send_keyid(dir, newkeyid, *keyidlen, 0); 2016 } 2017 2018 /* 2019 * encrypt_enc_keyid 2020 * 2021 * We received the ENC_KEYID message from a client indicating that 2022 * the client wishes to verify that the indicated keyid maps to a 2023 * valid key. 2024 */ 2025 static void 2026 encrypt_enc_keyid(char *data, int cnt) 2027 { 2028 /* 2029 * Verify the decrypt keyid is valid 2030 */ 2031 encrypt_keyid(encr_data.decrypt.keyid, &encr_data.decrypt.keyidlen, 2032 (uchar_t *)data, cnt, TELNET_DIR_DECRYPT); 2033 } 2034 2035 /* 2036 * encrypt_dec_keyid 2037 * 2038 * We received the DEC_KEYID message from a client indicating that 2039 * the client wants to verify that the indicated keyid maps to a valid key. 2040 */ 2041 static void 2042 encrypt_dec_keyid(char *data, int cnt) 2043 { 2044 encrypt_keyid(encr_data.encrypt.keyid, &encr_data.encrypt.keyidlen, 2045 (uchar_t *)data, cnt, TELNET_DIR_ENCRYPT); 2046 } 2047 2048 /* 2049 * encrypt_session_key 2050 * 2051 * Store the session key in the encryption data record 2052 */ 2053 static void 2054 encrypt_session_key(Session_Key *key, cipher_info_t *cinfo) 2055 { 2056 if (key == NULL || key->type != SK_DES) { 2057 if (enc_debug) 2058 (void) fprintf(stderr, 2059 "\t(session_key) Cannot set krb5 " 2060 "session key (unknown type = %d)\n", 2061 key ? key->type : -1); 2062 } 2063 if (enc_debug) 2064 (void) fprintf(stderr, 2065 "\t(session_key) Settting session key " 2066 "for server\n"); 2067 2068 /* store the key in the cipher info data struct */ 2069 (void) memcpy(cinfo->krbdes_key, (void *)key->data, sizeof (Block)); 2070 2071 /* 2072 * Now look to see if we still need to send the key and start 2073 * encrypting. 2074 * 2075 * If so, go ahead an call it now that we have the key. 2076 */ 2077 if (cinfo->need_start) { 2078 if (encrypt_send_encrypt_is() == ENCR_STATE_OK) { 2079 cinfo->need_start = 0; 2080 } 2081 } 2082 } 2083 2084 /* 2085 * new_env 2086 * 2087 * Used to add an environment variable and value to the 2088 * linked list structure. 2089 */ 2090 static int 2091 new_env(const char *name, const char *value) 2092 { 2093 struct envlist *env; 2094 2095 env = malloc(sizeof (struct envlist)); 2096 if (env == NULL) 2097 return (1); 2098 if ((env->name = strdup(name)) == NULL) { 2099 free(env); 2100 return (1); 2101 } 2102 if ((env->value = strdup(value)) == NULL) { 2103 free(env->name); 2104 free(env); 2105 return (1); 2106 } 2107 env->delete = 0; 2108 env->next = envlist_head; 2109 envlist_head = env; 2110 return (0); 2111 } 2112 2113 /* 2114 * del_env 2115 * 2116 * Used to delete an environment variable from the linked list 2117 * structure. We just set a flag because we will delete the list 2118 * anyway before we exec login. 2119 */ 2120 static int 2121 del_env(const char *name) 2122 { 2123 struct envlist *env; 2124 2125 for (env = envlist_head; env; env = env->next) { 2126 if (strcmp(env->name, name) == 0) { 2127 env->delete = 1; 2128 break; 2129 } 2130 } 2131 return (0); 2132 } 2133 2134 static int 2135 issock(int fd) 2136 { 2137 struct stat stats; 2138 2139 if (fstat(fd, &stats) == -1) 2140 return (0); 2141 return (S_ISSOCK(stats.st_mode)); 2142 } 2143 2144 /* 2145 * audit_telnet_settid stores the terminal id while it is still 2146 * available. Subsequent calls to adt_load_hostname() return 2147 * the id which is stored here. 2148 */ 2149 static int 2150 audit_telnet_settid(int sock) { 2151 adt_session_data_t *ah; 2152 adt_termid_t *termid; 2153 int rc; 2154 2155 if ((rc = adt_start_session(&ah, NULL, 0)) == 0) { 2156 if ((rc = adt_load_termid(sock, &termid)) == 0) { 2157 if ((rc = adt_set_user(ah, ADT_NO_AUDIT, 2158 ADT_NO_AUDIT, 0, ADT_NO_AUDIT, 2159 termid, ADT_SETTID)) == 0) 2160 (void) adt_set_proc(ah); 2161 free(termid); 2162 } 2163 (void) adt_end_session(ah); 2164 } 2165 return (rc); 2166 } 2167 2168 /* ARGSUSED */ 2169 int 2170 main(int argc, char *argv[]) 2171 { 2172 struct sockaddr_storage from; 2173 int on = 1; 2174 socklen_t fromlen; 2175 int issocket; 2176 #if defined(DEBUG) 2177 ushort_t porttouse = 0; 2178 boolean_t standalone = 0; 2179 #endif /* defined(DEBUG) */ 2180 extern char *optarg; 2181 char c; 2182 int tos = -1; 2183 2184 while ((c = getopt(argc, argv, TELNETD_OPTS DEBUG_OPTS)) != -1) { 2185 switch (c) { 2186 #if defined(DEBUG) 2187 case 'p': 2188 /* 2189 * note: alternative port number only used in 2190 * standalone mode. 2191 */ 2192 porttouse = atoi(optarg); 2193 standalone = 1; 2194 break; 2195 case 'e': 2196 enc_debug = 1; 2197 break; 2198 #endif /* DEBUG */ 2199 case 'a': 2200 if (strcasecmp(optarg, "none") == 0) { 2201 auth_level = 0; 2202 } else if (strcasecmp(optarg, "user") == 0) { 2203 auth_level = AUTH_USER; 2204 } else if (strcasecmp(optarg, "valid") == 0) { 2205 auth_level = AUTH_VALID; 2206 } else if (strcasecmp(optarg, "off") == 0) { 2207 auth_level = -1; 2208 negotiate_auth_krb5 = 0; 2209 } else if (strcasecmp(optarg, "debug") == 0) { 2210 auth_debug = 1; 2211 } else { 2212 syslog(LOG_ERR, 2213 "unknown authentication level specified " 2214 "with \'-a\' option (%s)", optarg); 2215 auth_level = AUTH_USER; 2216 } 2217 break; 2218 case 'X': 2219 /* disable authentication negotiation */ 2220 negotiate_auth_krb5 = 0; 2221 break; 2222 case 'R': 2223 case 'M': 2224 if (optarg != NULL) { 2225 int ret = krb5_init(); 2226 if (ret) { 2227 syslog(LOG_ERR, 2228 "Unable to use Kerberos V5 as " 2229 "requested, exiting"); 2230 exit(1); 2231 } 2232 krb5_set_default_realm(telnet_context, optarg); 2233 syslog(LOG_NOTICE, 2234 "using %s as default KRB5 realm", optarg); 2235 } 2236 break; 2237 case 'S': 2238 telnet_srvtab = (char *)strdup(optarg); 2239 break; 2240 case 'E': /* disable automatic encryption */ 2241 negotiate_encrypt = B_FALSE; 2242 break; 2243 case 'U': 2244 resolve_hostname = 1; 2245 break; 2246 case 's': 2247 if (optarg == NULL || (tos = atoi(optarg)) < 0 || 2248 tos > 255) { 2249 syslog(LOG_ERR, "telnetd: illegal tos value: " 2250 "%s\n", optarg); 2251 } else { 2252 if (tos < 0) 2253 tos = 020; 2254 } 2255 break; 2256 case 'h': 2257 show_hostinfo = 0; 2258 break; 2259 default: 2260 syslog(LOG_ERR, "telnetd: illegal cmd line option %c", 2261 c); 2262 break; 2263 } 2264 } 2265 2266 netibufsize = BUFSIZ; 2267 if (!(netibuf = (char *)malloc(netibufsize))) 2268 syslog(LOG_ERR, "netibuf malloc failed\n"); 2269 (void) memset(netibuf, 0, netibufsize); 2270 netip = netibuf; 2271 2272 #if defined(DEBUG) 2273 if (standalone) { 2274 int s, ns, foo; 2275 struct servent *sp; 2276 static struct sockaddr_in6 sin6 = { AF_INET6 }; 2277 int option = 1; 2278 2279 if (porttouse) { 2280 sin6.sin6_port = htons(porttouse); 2281 } else { 2282 sp = getservbyname("telnet", "tcp"); 2283 if (sp == 0) { 2284 (void) fprintf(stderr, 2285 "telnetd: tcp/telnet: " 2286 "unknown service\n"); 2287 exit(EXIT_FAILURE); 2288 } 2289 sin6.sin6_port = sp->s_port; 2290 } 2291 2292 s = socket(AF_INET6, SOCK_STREAM, IPPROTO_TCP); 2293 if (s < 0) { 2294 perror("telnetd: socket"); 2295 exit(EXIT_FAILURE); 2296 } 2297 if (setsockopt(s, SOL_SOCKET, SO_REUSEADDR, (char *)&option, 2298 sizeof (option)) == -1) 2299 perror("setsockopt SO_REUSEADDR"); 2300 if (bind(s, (struct sockaddr *)&sin6, sizeof (sin6)) < 0) { 2301 perror("bind"); 2302 exit(EXIT_FAILURE); 2303 } 2304 if (listen(s, 32) < 0) { 2305 perror("listen"); 2306 exit(EXIT_FAILURE); 2307 } 2308 2309 /* automatically reap all child processes */ 2310 (void) signal(SIGCHLD, SIG_IGN); 2311 2312 for (;;) { 2313 pid_t pid; 2314 2315 foo = sizeof (sin6); 2316 ns = accept(s, (struct sockaddr *)&sin6, &foo); 2317 if (ns < 0) { 2318 perror("accept"); 2319 exit(EXIT_FAILURE); 2320 } 2321 pid = fork(); 2322 if (pid == -1) { 2323 perror("fork"); 2324 exit(EXIT_FAILURE); 2325 } 2326 if (pid == 0) { 2327 (void) dup2(ns, 0); 2328 (void) close(s); 2329 (void) signal(SIGCHLD, SIG_DFL); 2330 break; 2331 } 2332 (void) close(ns); 2333 } 2334 } 2335 #endif /* defined(DEBUG) */ 2336 2337 openlog("telnetd", LOG_PID | LOG_ODELAY, LOG_DAEMON); 2338 2339 issocket = issock(0); 2340 if (!issocket) 2341 fatal(0, "stdin is not a socket file descriptor"); 2342 2343 fromlen = (socklen_t)sizeof (from); 2344 (void) memset((char *)&from, 0, sizeof (from)); 2345 if (getpeername(0, (struct sockaddr *)&from, &fromlen) 2346 < 0) { 2347 (void) fprintf(stderr, "%s: ", argv[0]); 2348 perror("getpeername"); 2349 _exit(EXIT_FAILURE); 2350 } 2351 2352 if (audit_telnet_settid(0)) { /* set terminal ID */ 2353 (void) fprintf(stderr, "%s: ", argv[0]); 2354 perror("audit"); 2355 exit(EXIT_FAILURE); 2356 } 2357 2358 if (setsockopt(0, SOL_SOCKET, SO_KEEPALIVE, (const char *)&on, 2359 sizeof (on)) < 0) { 2360 syslog(LOG_WARNING, "setsockopt (SO_KEEPALIVE): %m"); 2361 } 2362 2363 /* 2364 * Set the TOS value 2365 */ 2366 if (tos != -1 && 2367 setsockopt(0, IPPROTO_IP, IP_TOS, 2368 (char *)&tos, sizeof (tos)) < 0 && 2369 errno != ENOPROTOOPT) { 2370 syslog(LOG_ERR, "setsockopt (IP_TOS %d): %m", tos); 2371 } 2372 2373 if (setsockopt(net, SOL_SOCKET, SO_OOBINLINE, (char *)&on, 2374 sizeof (on)) < 0) { 2375 syslog(LOG_WARNING, "setsockopt (SO_OOBINLINE): %m"); 2376 } 2377 2378 /* set the default PAM service name */ 2379 (void) strcpy(pam_svc_name, "telnet"); 2380 2381 doit(0, &from); 2382 /* NOTREACHED */ 2383 return (EXIT_SUCCESS); 2384 } 2385 2386 static char *terminaltype = 0; 2387 2388 /* 2389 * ttloop 2390 * 2391 * A small subroutine to flush the network output buffer, get some data 2392 * from the network, and pass it through the telnet state machine. We 2393 * also flush the pty input buffer (by dropping its data) if it becomes 2394 * too full. 2395 */ 2396 static void 2397 ttloop(void) 2398 { 2399 if (nfrontp-nbackp) { 2400 netflush(); 2401 } 2402 read_again: 2403 ncc = read(net, netibuf, netibufsize); 2404 if (ncc < 0) { 2405 if (errno == EINTR) 2406 goto read_again; 2407 syslog(LOG_INFO, "ttloop: read: %m"); 2408 exit(EXIT_FAILURE); 2409 } else if (ncc == 0) { 2410 syslog(LOG_INFO, "ttloop: peer closed connection\n"); 2411 exit(EXIT_FAILURE); 2412 } 2413 2414 netip = netibuf; 2415 telrcv(); /* state machine */ 2416 if (ncc > 0) { 2417 pfrontp = pbackp = ptyobuf; 2418 telrcv(); 2419 } 2420 } 2421 2422 static void 2423 send_do(int option) 2424 { 2425 write_data("%c%c%c", (uchar_t)IAC, (uchar_t)DO, (uchar_t)option); 2426 } 2427 2428 static void 2429 send_will(int option) 2430 { 2431 write_data("%c%c%c", (uchar_t)IAC, (uchar_t)WILL, (uchar_t)option); 2432 } 2433 2434 static void 2435 send_wont(int option) 2436 { 2437 write_data("%c%c%c", (uchar_t)IAC, (uchar_t)WONT, (uchar_t)option); 2438 } 2439 2440 2441 /* 2442 * getauthtype 2443 * 2444 * Negotiate automatic authentication, is possible. 2445 */ 2446 static int 2447 getauthtype(char *username, int *len) 2448 { 2449 int init_status = -1; 2450 2451 init_status = krb5_init(); 2452 2453 if (auth_level == -1 || init_status != 0) { 2454 remopts[TELOPT_AUTHENTICATION] = OPT_NO; 2455 myopts[TELOPT_AUTHENTICATION] = OPT_NO; 2456 negotiate_auth_krb5 = B_FALSE; 2457 negotiate_encrypt = B_FALSE; 2458 return (AUTH_REJECT); 2459 } 2460 2461 if (init_status == 0 && auth_level != -1) { 2462 if (negotiate_auth_krb5) { 2463 /* 2464 * Negotiate Authentication FIRST 2465 */ 2466 send_do(TELOPT_AUTHENTICATION); 2467 remopts[TELOPT_AUTHENTICATION] = 2468 OPT_YES_BUT_ALWAYS_LOOK; 2469 } 2470 while (sequenceIs(authopt, getauth)) 2471 ttloop(); 2472 2473 if (remopts[TELOPT_AUTHENTICATION] == OPT_YES) { 2474 /* 2475 * Request KRB5 Mutual authentication and if that fails, 2476 * KRB5 1-way client authentication 2477 */ 2478 uchar_t sbbuf[MAXOPTLEN], *p; 2479 p = sbbuf; 2480 *p++ = (uchar_t)IAC; 2481 *p++ = (uchar_t)SB; 2482 *p++ = (uchar_t)TELOPT_AUTHENTICATION; 2483 *p++ = (uchar_t)TELQUAL_SEND; 2484 if (negotiate_auth_krb5) { 2485 *p++ = (uchar_t)AUTHTYPE_KERBEROS_V5; 2486 *p++ = (uchar_t)(AUTH_WHO_CLIENT | 2487 AUTH_HOW_MUTUAL | 2488 AUTH_ENCRYPT_ON); 2489 *p++ = (uchar_t)AUTHTYPE_KERBEROS_V5; 2490 *p++ = (uchar_t)(AUTH_WHO_CLIENT | 2491 AUTH_HOW_MUTUAL); 2492 *p++ = (uchar_t)AUTHTYPE_KERBEROS_V5; 2493 *p++ = (uchar_t)(AUTH_WHO_CLIENT| 2494 AUTH_HOW_ONE_WAY); 2495 } else { 2496 *p++ = (uchar_t)AUTHTYPE_NULL; 2497 } 2498 *p++ = (uchar_t)IAC; 2499 *p++ = (uchar_t)SE; 2500 2501 write_data_len((const char *)sbbuf, 2502 (size_t)(p - sbbuf)); 2503 netflush(); 2504 if (auth_debug) 2505 (void) fprintf(stderr, 2506 "SENT TELOPT_AUTHENTICATION " 2507 "[data]\n"); 2508 2509 /* auth_wait returns the authentication level */ 2510 /* status = auth_wait(username, len); */ 2511 while (sequenceIs(authdone, getauth)) 2512 ttloop(); 2513 /* 2514 * Now check to see if the user is valid or not 2515 */ 2516 if (authenticated == NULL || authenticated == &NoAuth) 2517 auth_status = AUTH_REJECT; 2518 else { 2519 /* 2520 * We cant be VALID until the user status is 2521 * checked. 2522 */ 2523 if (auth_status == AUTH_VALID) 2524 auth_status = AUTH_USER; 2525 2526 if (authenticated->AuthName == 2527 AUTHTYPE_KERBEROS_V5) 2528 auth_status = krb5_user_status( 2529 username, *len, auth_status); 2530 } 2531 } 2532 } 2533 return (auth_status); 2534 } 2535 2536 static void 2537 getencrtype(void) 2538 { 2539 if (krb5_privacy_allowed() && negotiate_encrypt) { 2540 if (myopts[TELOPT_ENCRYPT] != OPT_YES) { 2541 if (!sent_will_encrypt) { 2542 send_will(TELOPT_ENCRYPT); 2543 sent_will_encrypt = B_TRUE; 2544 } 2545 if (enc_debug) 2546 (void) fprintf(stderr, "SENT WILL ENCRYPT\n"); 2547 } 2548 if (remopts[TELOPT_ENCRYPT] != OPT_YES) { 2549 if (!sent_do_encrypt) { 2550 send_do(TELOPT_ENCRYPT); 2551 sent_do_encrypt = B_TRUE; 2552 } 2553 if (enc_debug) 2554 (void) fprintf(stderr, "SENT DO ENCRYPT\n"); 2555 } 2556 myopts[TELOPT_ENCRYPT] = OPT_YES; 2557 2558 while (sequenceIs(encropt, getencr)) 2559 ttloop(); 2560 2561 if (auth_status != AUTH_REJECT && 2562 remopts[TELOPT_ENCRYPT] == OPT_YES && 2563 myopts[TELOPT_ENCRYPT] == OPT_YES) { 2564 2565 if (sent_encrypt_support == B_FALSE) { 2566 write_data("%c%c%c%c%c%c%c", 2567 (uchar_t)IAC, 2568 (uchar_t)SB, 2569 (uchar_t)TELOPT_ENCRYPT, 2570 (uchar_t)ENCRYPT_SUPPORT, 2571 (uchar_t)TELOPT_ENCTYPE_DES_CFB64, 2572 (uchar_t)IAC, 2573 (uchar_t)SE); 2574 2575 netflush(); 2576 } 2577 /* 2578 * Now wait for a response to these messages before 2579 * continuing... 2580 * Look for TELOPT_ENCRYPT suboptions 2581 */ 2582 while (sequenceIs(encr_support, getencr)) 2583 ttloop(); 2584 } 2585 } else { 2586 /* Dont need responses to these, so dont wait for them */ 2587 settimer(encropt); 2588 remopts[TELOPT_ENCRYPT] = OPT_NO; 2589 myopts[TELOPT_ENCRYPT] = OPT_NO; 2590 } 2591 2592 } 2593 2594 /* 2595 * getterminaltype 2596 * 2597 * Ask the other end to send along its terminal type. 2598 * Output is the variable terminaltype filled in. 2599 */ 2600 static void 2601 getterminaltype(void) 2602 { 2603 /* 2604 * The remote side may have already sent this info, so 2605 * dont ask for these options if the other side already 2606 * sent the information. 2607 */ 2608 if (sequenceIs(ttypeopt, getterminal)) { 2609 send_do(TELOPT_TTYPE); 2610 remopts[TELOPT_TTYPE] = OPT_YES_BUT_ALWAYS_LOOK; 2611 } 2612 2613 if (sequenceIs(nawsopt, getterminal)) { 2614 send_do(TELOPT_NAWS); 2615 remopts[TELOPT_NAWS] = OPT_YES_BUT_ALWAYS_LOOK; 2616 } 2617 2618 if (sequenceIs(xdisplocopt, getterminal)) { 2619 send_do(TELOPT_XDISPLOC); 2620 remopts[TELOPT_XDISPLOC] = OPT_YES_BUT_ALWAYS_LOOK; 2621 } 2622 2623 if (sequenceIs(environopt, getterminal)) { 2624 send_do(TELOPT_NEW_ENVIRON); 2625 remopts[TELOPT_NEW_ENVIRON] = OPT_YES_BUT_ALWAYS_LOOK; 2626 } 2627 2628 if (sequenceIs(oenvironopt, getterminal)) { 2629 send_do(TELOPT_OLD_ENVIRON); 2630 remopts[TELOPT_OLD_ENVIRON] = OPT_YES_BUT_ALWAYS_LOOK; 2631 } 2632 2633 /* make sure encryption is started here */ 2634 while (auth_status != AUTH_REJECT && 2635 authenticated != &NoAuth && authenticated != NULL && 2636 remopts[TELOPT_ENCRYPT] == OPT_YES && 2637 encr_data.encrypt.autoflag && 2638 encr_data.encrypt.state != ENCR_STATE_OK) { 2639 if (enc_debug) 2640 (void) fprintf(stderr, "getterminaltype() forcing encrypt\n"); 2641 ttloop(); 2642 } 2643 2644 if (enc_debug) { 2645 (void) fprintf(stderr, "getterminaltype() encryption %sstarted\n", 2646 encr_data.encrypt.state == ENCR_STATE_OK ? "" : "not "); 2647 } 2648 2649 while (sequenceIs(ttypeopt, getterminal) || 2650 sequenceIs(nawsopt, getterminal) || 2651 sequenceIs(xdisplocopt, getterminal) || 2652 sequenceIs(environopt, getterminal) || 2653 sequenceIs(oenvironopt, getterminal)) { 2654 ttloop(); 2655 } 2656 2657 2658 if (remopts[TELOPT_TTYPE] == OPT_YES) { 2659 static uchar_t sbbuf[] = { (uchar_t)IAC, (uchar_t)SB, 2660 (uchar_t)TELOPT_TTYPE, (uchar_t)TELQUAL_SEND, 2661 (uchar_t)IAC, (uchar_t)SE }; 2662 2663 write_data_len((const char *)sbbuf, sizeof (sbbuf)); 2664 } 2665 if (remopts[TELOPT_XDISPLOC] == OPT_YES) { 2666 static uchar_t sbbuf[] = { (uchar_t)IAC, (uchar_t)SB, 2667 (uchar_t)TELOPT_XDISPLOC, (uchar_t)TELQUAL_SEND, 2668 (uchar_t)IAC, (uchar_t)SE }; 2669 2670 write_data_len((const char *)sbbuf, sizeof (sbbuf)); 2671 } 2672 if (remopts[TELOPT_NEW_ENVIRON] == OPT_YES) { 2673 static uchar_t sbbuf[] = { (uchar_t)IAC, (uchar_t)SB, 2674 (uchar_t)TELOPT_NEW_ENVIRON, (uchar_t)TELQUAL_SEND, 2675 (uchar_t)IAC, (uchar_t)SE }; 2676 2677 write_data_len((const char *)sbbuf, sizeof (sbbuf)); 2678 } 2679 if (remopts[TELOPT_OLD_ENVIRON] == OPT_YES) { 2680 static uchar_t sbbuf[] = { (uchar_t)IAC, (uchar_t)SB, 2681 (uchar_t)TELOPT_OLD_ENVIRON, (uchar_t)TELQUAL_SEND, 2682 (uchar_t)IAC, (uchar_t)SE }; 2683 2684 write_data_len((const char *)sbbuf, sizeof (sbbuf)); 2685 } 2686 2687 if (remopts[TELOPT_TTYPE] == OPT_YES) { 2688 while (sequenceIs(ttypesubopt, getterminal)) { 2689 ttloop(); 2690 } 2691 } 2692 if (remopts[TELOPT_XDISPLOC] == OPT_YES) { 2693 while (sequenceIs(xdisplocsubopt, getterminal)) { 2694 ttloop(); 2695 } 2696 } 2697 if (remopts[TELOPT_NEW_ENVIRON] == OPT_YES) { 2698 while (sequenceIs(environsubopt, getterminal)) { 2699 ttloop(); 2700 } 2701 } 2702 if (remopts[TELOPT_OLD_ENVIRON] == OPT_YES) { 2703 while (sequenceIs(oenvironsubopt, getterminal)) { 2704 ttloop(); 2705 } 2706 } 2707 init_neg_done = 1; 2708 } 2709 2710 pid_t pid; 2711 2712 /* 2713 * Get a pty, scan input lines. 2714 */ 2715 static void 2716 doit(int f, struct sockaddr_storage *who) 2717 { 2718 char *host; 2719 char host_name[MAXHOSTNAMELEN]; 2720 int p, t, tt; 2721 struct sgttyb b; 2722 int ptmfd; /* fd of logindmux connected to pty */ 2723 int netfd; /* fd of logindmux connected to netf */ 2724 struct stat buf; 2725 struct protocol_arg telnetp; 2726 struct strioctl telnetmod; 2727 struct envlist *env, *next; 2728 int nsize = 0; 2729 char abuf[INET6_ADDRSTRLEN]; 2730 struct sockaddr_in *sin; 2731 struct sockaddr_in6 *sin6; 2732 socklen_t wholen; 2733 char username[MAXUSERNAMELEN]; 2734 int len; 2735 uchar_t passthru; 2736 char *slavename; 2737 2738 if ((p = open("/dev/ptmx", O_RDWR | O_NOCTTY)) == -1) { 2739 fatalperror(f, "open /dev/ptmx", errno); 2740 } 2741 if (grantpt(p) == -1) 2742 fatal(f, "could not grant slave pty"); 2743 if (unlockpt(p) == -1) 2744 fatal(f, "could not unlock slave pty"); 2745 if ((slavename = ptsname(p)) == NULL) 2746 fatal(f, "could not enable slave pty"); 2747 (void) dup2(f, 0); 2748 if ((t = open(slavename, O_RDWR | O_NOCTTY)) == -1) 2749 fatal(f, "could not open slave pty"); 2750 if (ioctl(t, I_PUSH, "ptem") == -1) 2751 fatalperror(f, "ioctl I_PUSH ptem", errno); 2752 if (ioctl(t, I_PUSH, "ldterm") == -1) 2753 fatalperror(f, "ioctl I_PUSH ldterm", errno); 2754 if (ioctl(t, I_PUSH, "ttcompat") == -1) 2755 fatalperror(f, "ioctl I_PUSH ttcompat", errno); 2756 2757 line = slavename; 2758 2759 pty = t; 2760 2761 if (ioctl(t, TIOCGETP, &b) == -1) 2762 syslog(LOG_INFO, "ioctl TIOCGETP pty t: %m\n"); 2763 b.sg_flags = O_CRMOD|O_XTABS|O_ANYP; 2764 /* XXX - ispeed and ospeed must be non-zero */ 2765 b.sg_ispeed = B38400; 2766 b.sg_ospeed = B38400; 2767 if (ioctl(t, TIOCSETN, &b) == -1) 2768 syslog(LOG_INFO, "ioctl TIOCSETN pty t: %m\n"); 2769 if (ioctl(pty, TIOCGETP, &b) == -1) 2770 syslog(LOG_INFO, "ioctl TIOCGETP pty pty: %m\n"); 2771 b.sg_flags &= ~O_ECHO; 2772 if (ioctl(pty, TIOCSETN, &b) == -1) 2773 syslog(LOG_INFO, "ioctl TIOCSETN pty pty: %m\n"); 2774 2775 if (who->ss_family == AF_INET) { 2776 char *addrbuf = NULL; 2777 char *portbuf = NULL; 2778 2779 sin = (struct sockaddr_in *)who; 2780 wholen = sizeof (struct sockaddr_in); 2781 2782 addrbuf = (char *)malloc(wholen); 2783 if (addrbuf == NULL) 2784 fatal(f, "Cannot alloc memory for address info\n"); 2785 portbuf = (char *)malloc(sizeof (sin->sin_port)); 2786 if (portbuf == NULL) { 2787 free(addrbuf); 2788 fatal(f, "Cannot alloc memory for port info\n"); 2789 } 2790 2791 (void) memcpy(addrbuf, (const void *)&sin->sin_addr, wholen); 2792 (void) memcpy(portbuf, (const void *)&sin->sin_port, 2793 sizeof (sin->sin_port)); 2794 2795 if (rsaddr.contents != NULL) 2796 free(rsaddr.contents); 2797 2798 rsaddr.contents = (krb5_octet *)addrbuf; 2799 rsaddr.length = wholen; 2800 rsaddr.addrtype = ADDRTYPE_INET; 2801 2802 if (rsport.contents != NULL) 2803 free(rsport.contents); 2804 2805 rsport.contents = (krb5_octet *)portbuf; 2806 rsport.length = sizeof (sin->sin_port); 2807 rsport.addrtype = ADDRTYPE_IPPORT; 2808 } else if (who->ss_family == AF_INET6) { 2809 struct in_addr ipv4_addr; 2810 char *addrbuf = NULL; 2811 char *portbuf = NULL; 2812 2813 sin6 = (struct sockaddr_in6 *)who; 2814 wholen = sizeof (struct sockaddr_in6); 2815 2816 IN6_V4MAPPED_TO_INADDR(&sin6->sin6_addr, 2817 &ipv4_addr); 2818 2819 addrbuf = (char *)malloc(wholen); 2820 if (addrbuf == NULL) 2821 fatal(f, "Cannot alloc memory for address info\n"); 2822 2823 portbuf = (char *)malloc(sizeof (sin6->sin6_port)); 2824 if (portbuf == NULL) { 2825 free(addrbuf); 2826 fatal(f, "Cannot alloc memory for port info\n"); 2827 } 2828 2829 (void) memcpy((void *) addrbuf, 2830 (const void *)&ipv4_addr, 2831 wholen); 2832 /* 2833 * If we already used rsaddr.contents, free the previous 2834 * buffer. 2835 */ 2836 if (rsaddr.contents != NULL) 2837 free(rsaddr.contents); 2838 2839 rsaddr.contents = (krb5_octet *)addrbuf; 2840 rsaddr.length = sizeof (ipv4_addr); 2841 rsaddr.addrtype = ADDRTYPE_INET; 2842 2843 (void) memcpy((void *) portbuf, (const void *)&sin6->sin6_port, 2844 sizeof (sin6->sin6_port)); 2845 2846 if (rsport.contents != NULL) 2847 free(rsport.contents); 2848 2849 rsport.contents = (krb5_octet *)portbuf; 2850 rsport.length = sizeof (sin6->sin6_port); 2851 rsport.addrtype = ADDRTYPE_IPPORT; 2852 } else { 2853 syslog(LOG_ERR, "unknown address family %d\n", 2854 who->ss_family); 2855 fatal(f, "getpeername: unknown address family\n"); 2856 } 2857 2858 if (getnameinfo((const struct sockaddr *) who, wholen, host_name, 2859 sizeof (host_name), NULL, 0, 0) == 0) { 2860 host = host_name; 2861 } else { 2862 /* 2863 * If the '-U' option was given on the cmd line, we must 2864 * be able to lookup the hostname 2865 */ 2866 if (resolve_hostname) { 2867 fatal(f, "Couldn't resolve your address into a " 2868 "host name.\r\nPlease contact your net " 2869 "administrator"); 2870 } 2871 2872 if (who->ss_family == AF_INET6) { 2873 if (IN6_IS_ADDR_V4MAPPED(&sin6->sin6_addr)) { 2874 struct in_addr ipv4_addr; 2875 2876 IN6_V4MAPPED_TO_INADDR(&sin6->sin6_addr, 2877 &ipv4_addr); 2878 host = (char *)inet_ntop(AF_INET, 2879 &ipv4_addr, abuf, sizeof (abuf)); 2880 } else { 2881 host = (char *)inet_ntop(AF_INET6, 2882 &sin6->sin6_addr, abuf, 2883 sizeof (abuf)); 2884 } 2885 } else if (who->ss_family == AF_INET) { 2886 host = (char *)inet_ntop(AF_INET, 2887 &sin->sin_addr, abuf, sizeof (abuf)); 2888 } 2889 } 2890 /* 2891 * Note that sockmod has to be removed since readstream assumes 2892 * a "raw" TPI endpoint (e.g. it uses getmsg). 2893 */ 2894 if (removemod(f, "sockmod") < 0) 2895 fatalperror(f, "couldn't remove sockmod", errno); 2896 2897 encrypt_init(); 2898 2899 /* 2900 * Push the crypto module on the stream before 'telmod' so it 2901 * can encrypt/decrypt without interfering with telmod functionality 2902 * We must push it now because many of the crypto options negotiated 2903 * initially must be saved in the crypto module (via IOCTL calls). 2904 */ 2905 if (ioctl(f, I_PUSH, "cryptmod") < 0) 2906 fatalperror(f, "ioctl I_PUSH cryptmod", errno); 2907 2908 cryptmod_fd = f; 2909 /* 2910 * gotta set the encryption clock now because it is often negotiated 2911 * immediately by the client, and if we wait till after we negotiate 2912 * auth, it will be out of whack with when the WILL/WONT ENCRYPT 2913 * option is received. 2914 */ 2915 settimer(getencr); 2916 2917 /* 2918 * get terminal type. 2919 */ 2920 username[0] = '\0'; 2921 len = sizeof (username); 2922 2923 settimer(getterminal); 2924 settimer(getauth); 2925 /* 2926 * Exchange TELOPT_AUTHENTICATE options per RFC 2941/2942 2927 */ 2928 auth_status = getauthtype(username, &len); 2929 /* 2930 * Exchange TELOPT_ENCRYPT options per RFC 2946 2931 */ 2932 getencrtype(); 2933 getterminaltype(); 2934 2935 if (ioctl(f, I_PUSH, "telmod") < 0) 2936 fatalperror(f, "ioctl I_PUSH telmod", errno); 2937 2938 /* 2939 * Make sure telmod will pass unrecognized IOCTLs to cryptmod 2940 */ 2941 passthru = 1; 2942 2943 telnetmod.ic_cmd = CRYPTPASSTHRU; 2944 telnetmod.ic_timout = -1; 2945 telnetmod.ic_len = sizeof (uchar_t); 2946 telnetmod.ic_dp = (char *)&passthru; 2947 2948 if (ioctl(f, I_STR, &telnetmod) < 0) 2949 fatal(f, "ioctl CRPASSTHRU failed\n"); 2950 2951 if (!ncc) 2952 netip = netibuf; 2953 2954 /* 2955 * readstream will do a getmsg till it receives M_PROTO type 2956 * T_DATA_REQ from telnetmodopen(). This signals that all data 2957 * in-flight before telmod was pushed has been received at the 2958 * stream head. 2959 */ 2960 while ((nsize = readstream(f, netibuf, ncc + netip - netibuf)) > 0) { 2961 ncc += nsize; 2962 } 2963 2964 if (nsize < 0) { 2965 fatalperror(f, "readstream failed\n", errno); 2966 } 2967 2968 /* 2969 * open logindmux drivers and link them with network and ptm 2970 * file descriptors. 2971 */ 2972 if ((ptmfd = open("/dev/logindmux", O_RDWR)) == -1) { 2973 fatalperror(f, "open /dev/logindmux", errno); 2974 } 2975 if ((netfd = open("/dev/logindmux", O_RDWR)) == -1) { 2976 fatalperror(f, "open /dev/logindmux", errno); 2977 } 2978 2979 if (ioctl(ptmfd, I_LINK, p) < 0) 2980 fatal(f, "ioctl I_LINK of /dev/ptmx failed\n"); 2981 if (ioctl(netfd, I_LINK, f) < 0) 2982 fatal(f, "ioctl I_LINK of tcp connection failed\n"); 2983 2984 /* 2985 * Figure out the device number of ptm's mux fd, and pass that 2986 * to the net's mux. 2987 */ 2988 if (fstat(ptmfd, &buf) < 0) { 2989 fatalperror(f, "fstat ptmfd failed", errno); 2990 } 2991 telnetp.dev = buf.st_rdev; 2992 telnetp.flag = 0; 2993 2994 telnetmod.ic_cmd = LOGDMX_IOC_QEXCHANGE; 2995 telnetmod.ic_timout = -1; 2996 telnetmod.ic_len = sizeof (struct protocol_arg); 2997 telnetmod.ic_dp = (char *)&telnetp; 2998 2999 if (ioctl(netfd, I_STR, &telnetmod) < 0) 3000 fatal(netfd, "ioctl LOGDMX_IOC_QEXCHANGE of netfd failed\n"); 3001 3002 /* 3003 * Figure out the device number of the net's mux fd, and pass that 3004 * to the ptm's mux. 3005 */ 3006 if (fstat(netfd, &buf) < 0) { 3007 fatalperror(f, "fstat netfd failed", errno); 3008 } 3009 telnetp.dev = buf.st_rdev; 3010 telnetp.flag = 1; 3011 3012 telnetmod.ic_cmd = LOGDMX_IOC_QEXCHANGE; 3013 telnetmod.ic_timout = -1; 3014 telnetmod.ic_len = sizeof (struct protocol_arg); 3015 telnetmod.ic_dp = (char *)&telnetp; 3016 3017 if (ioctl(ptmfd, I_STR, &telnetmod) < 0) 3018 fatal(netfd, "ioctl LOGDMX_IOC_QEXCHANGE of ptmfd failed\n"); 3019 3020 net = netfd; 3021 master = ptmfd; 3022 cryptmod_fd = netfd; 3023 3024 /* 3025 * Show banner that getty never gave, but 3026 * only if the user did not automatically authenticate. 3027 */ 3028 if (getenv("USER") == '\0' && auth_status < AUTH_USER) 3029 showbanner(); 3030 3031 /* 3032 * If the user automatically authenticated with Kerberos 3033 * we must set the service name that PAM will use. We 3034 * need to do it BEFORE the child fork so that 'cleanup' 3035 * in the parent can call the PAM cleanup stuff with the 3036 * same PAM service that /bin/login will use to authenticate 3037 * this session. 3038 */ 3039 if (auth_level >= 0 && auth_status >= AUTH_USER && 3040 (AuthenticatingUser != NULL) && strlen(AuthenticatingUser)) { 3041 (void) strcpy(pam_svc_name, "ktelnet"); 3042 } 3043 /* 3044 * Request to do suppress go ahead. 3045 * 3046 * Send this before sending the TELOPT_ECHO stuff below because 3047 * some clients (MIT KRB5 telnet) have quirky 'kludge mode' support 3048 * that has them turn off local echo mode if SGA is not received first. 3049 * This also has the odd side-effect of causing the client to enable 3050 * encryption and then immediately disable it during the ECHO option 3051 * negotiations. Its just better to to SGA first now that we support 3052 * encryption. 3053 */ 3054 if (!myopts[TELOPT_SGA]) { 3055 dooption(TELOPT_SGA); 3056 } 3057 3058 /* 3059 * Pretend we got a DO ECHO from the client if we have not 3060 * yet negotiated the ECHO. 3061 */ 3062 if (!myopts[TELOPT_ECHO]) { 3063 dooption(TELOPT_ECHO); 3064 } 3065 3066 /* 3067 * Is the client side a 4.2 (NOT 4.3) system? We need to know this 3068 * because 4.2 clients are unable to deal with TCP urgent data. 3069 * 3070 * To find out, we send out a "DO ECHO". If the remote system 3071 * answers "WILL ECHO" it is probably a 4.2 client, and we note 3072 * that fact ("WILL ECHO" ==> that the client will echo what 3073 * WE, the server, sends it; it does NOT mean that the client will 3074 * echo the terminal input). 3075 */ 3076 send_do(TELOPT_ECHO); 3077 remopts[TELOPT_ECHO] = OPT_YES_BUT_ALWAYS_LOOK; 3078 3079 if ((pid = fork()) < 0) 3080 fatalperror(netfd, "fork", errno); 3081 if (pid) 3082 telnet(net, master); 3083 /* 3084 * The child process needs to be the session leader 3085 * and have the pty as its controlling tty. Thus we need 3086 * to re-open the slave side of the pty no without 3087 * the O_NOCTTY flag that we have been careful to 3088 * use up to this point. 3089 */ 3090 (void) setsid(); 3091 3092 tt = open(line, O_RDWR); 3093 if (tt < 0) 3094 fatalperror(netfd, line, errno); 3095 (void) close(netfd); 3096 (void) close(ptmfd); 3097 (void) close(f); 3098 (void) close(p); 3099 (void) close(t); 3100 if (tt != 0) 3101 (void) dup2(tt, 0); 3102 if (tt != 1) 3103 (void) dup2(tt, 1); 3104 if (tt != 2) 3105 (void) dup2(tt, 2); 3106 if (tt > 2) 3107 (void) close(tt); 3108 3109 if (terminaltype) 3110 (void) local_setenv("TERM", terminaltype+5, 1); 3111 /* 3112 * -h : pass on name of host. 3113 * WARNING: -h is accepted by login if and only if 3114 * getuid() == 0. 3115 * -p : don't clobber the environment (so terminal type stays set). 3116 */ 3117 { 3118 /* System V login expects a utmp entry to already be there */ 3119 struct utmpx ut; 3120 (void) memset((char *)&ut, 0, sizeof (ut)); 3121 (void) strncpy(ut.ut_user, ".telnet", sizeof (ut.ut_user)); 3122 (void) strncpy(ut.ut_line, line, sizeof (ut.ut_line)); 3123 ut.ut_pid = getpid(); 3124 ut.ut_id[0] = 't'; 3125 ut.ut_id[1] = (char)SC_WILDC; 3126 ut.ut_id[2] = (char)SC_WILDC; 3127 ut.ut_id[3] = (char)SC_WILDC; 3128 ut.ut_type = LOGIN_PROCESS; 3129 ut.ut_exit.e_termination = 0; 3130 ut.ut_exit.e_exit = 0; 3131 (void) time(&ut.ut_tv.tv_sec); 3132 if (makeutx(&ut) == NULL) 3133 syslog(LOG_INFO, "in.telnetd:\tmakeutx failed"); 3134 } 3135 3136 /* 3137 * Load in the cached environment variables and either 3138 * set/unset them in the environment. 3139 */ 3140 for (next = envlist_head; next; ) { 3141 env = next; 3142 if (env->delete) 3143 (void) local_unsetenv(env->name); 3144 else 3145 (void) local_setenv(env->name, env->value, 1); 3146 free(env->name); 3147 free(env->value); 3148 next = env->next; 3149 free(env); 3150 } 3151 3152 if (!username || !username[0]) 3153 auth_status = AUTH_REJECT; /* we dont know who this is */ 3154 3155 /* If the current auth status is less than the required level, exit */ 3156 if (auth_status < auth_level) { 3157 fatal(net, "Authentication failed\n"); 3158 exit(EXIT_FAILURE); 3159 } 3160 3161 /* 3162 * If AUTH_VALID (proper authentication REQUIRED and we have 3163 * a krb5_name), exec '/bin/login', make sure it uses the 3164 * correct PAM service name (pam_svc_name). If possible, 3165 * make sure the krb5 authenticated user's name (krb5_name) 3166 * is in the PAM REPOSITORY for krb5. 3167 */ 3168 if (auth_level >= 0 && 3169 (auth_status == AUTH_VALID || auth_status == AUTH_USER) && 3170 ((krb5_name != NULL) && strlen(krb5_name)) && 3171 ((AuthenticatingUser != NULL) && strlen(AuthenticatingUser))) { 3172 (void) execl(LOGIN_PROGRAM, "login", 3173 "-p", 3174 "-d", slavename, 3175 "-h", host, 3176 "-u", krb5_name, 3177 "-s", pam_svc_name, 3178 "-R", KRB5_REPOSITORY_NAME, 3179 AuthenticatingUser, 0); 3180 } else if (auth_level >= 0 && 3181 auth_status >= AUTH_USER && 3182 (((AuthenticatingUser != NULL) && strlen(AuthenticatingUser)) || 3183 getenv("USER"))) { 3184 /* 3185 * If we only know the name but not the principal, 3186 * login will have to authenticate further. 3187 */ 3188 (void) execl(LOGIN_PROGRAM, "login", 3189 "-p", 3190 "-d", slavename, 3191 "-h", host, 3192 "-s", pam_svc_name, 3193 (AuthenticatingUser != NULL ? AuthenticatingUser : 3194 getenv("USER")), 3195 0); 3196 3197 } else /* default, no auth. info available, login does it all */ { 3198 (void) execl(LOGIN_PROGRAM, "login", 3199 "-p", "-h", host, "-d", slavename, 3200 getenv("USER"), 0); 3201 } 3202 3203 fatalperror(netfd, LOGIN_PROGRAM, errno); 3204 /*NOTREACHED*/ 3205 } 3206 3207 static void 3208 fatal(int f, char *msg) 3209 { 3210 char buf[BUFSIZ]; 3211 3212 (void) snprintf(buf, sizeof (buf), "telnetd: %s.\r\n", msg); 3213 (void) write(f, buf, strlen(buf)); 3214 exit(EXIT_FAILURE); 3215 /*NOTREACHED*/ 3216 } 3217 3218 static void 3219 fatalperror(int f, char *msg, int errnum) 3220 { 3221 char buf[BUFSIZ]; 3222 3223 (void) snprintf(buf, sizeof (buf), 3224 "%s: %s\r\n", msg, strerror(errnum)); 3225 fatal(f, buf); 3226 /*NOTREACHED*/ 3227 } 3228 3229 /* 3230 * Main loop. Select from pty and network, and 3231 * hand data to telnet receiver finite state machine 3232 * when it receives telnet protocol. Regular data 3233 * flow between pty and network takes place through 3234 * inkernel telnet streams module (telmod). 3235 */ 3236 static void 3237 telnet(int net, int master) 3238 { 3239 int on = 1; 3240 char mode; 3241 struct strioctl telnetmod; 3242 int nsize = 0; 3243 char binary_in = 0; 3244 char binary_out = 0; 3245 3246 if (ioctl(net, FIONBIO, &on) == -1) 3247 syslog(LOG_INFO, "ioctl FIONBIO net: %m\n"); 3248 if (ioctl(master, FIONBIO, &on) == -1) 3249 syslog(LOG_INFO, "ioctl FIONBIO pty p: %m\n"); 3250 (void) signal(SIGTSTP, SIG_IGN); 3251 (void) signal(SIGCHLD, (void (*)())cleanup); 3252 (void) setpgrp(); 3253 3254 /* 3255 * Call telrcv() once to pick up anything received during 3256 * terminal type negotiation. 3257 */ 3258 telrcv(); 3259 3260 netflush(); 3261 ptyflush(); 3262 3263 for (;;) { 3264 fd_set ibits, obits, xbits; 3265 int c; 3266 3267 if (ncc < 0) 3268 break; 3269 3270 FD_ZERO(&ibits); 3271 FD_ZERO(&obits); 3272 FD_ZERO(&xbits); 3273 3274 /* 3275 * If we couldn't flush all our output to the network, 3276 * keep checking for when we can. 3277 */ 3278 if (nfrontp - nbackp) 3279 FD_SET(net, &obits); 3280 /* 3281 * Never look for input if there's still 3282 * stuff in the corresponding output buffer 3283 */ 3284 if (pfrontp - pbackp) { 3285 FD_SET(master, &obits); 3286 } else { 3287 FD_SET(net, &ibits); 3288 } 3289 if (!SYNCHing) { 3290 FD_SET(net, &xbits); 3291 } 3292 3293 #define max(x, y) (((x) < (y)) ? (y) : (x)) 3294 3295 /* 3296 * make an ioctl to telnet module (net side) to send 3297 * binary mode of telnet daemon. binary_in and 3298 * binary_out are 0 if not in binary mode. 3299 */ 3300 if (binary_in != myopts[TELOPT_BINARY] || 3301 binary_out != remopts[TELOPT_BINARY]) { 3302 3303 mode = 0; 3304 if (myopts[TELOPT_BINARY] != OPT_NO) 3305 mode |= TEL_BINARY_IN; 3306 3307 if (remopts[TELOPT_BINARY] != OPT_NO) 3308 mode |= TEL_BINARY_OUT; 3309 3310 telnetmod.ic_cmd = TEL_IOC_MODE; 3311 telnetmod.ic_timout = -1; 3312 telnetmod.ic_len = 1; 3313 telnetmod.ic_dp = &mode; 3314 3315 syslog(LOG_DEBUG, "TEL_IOC_MODE binary has changed\n"); 3316 3317 if (ioctl(net, I_STR, &telnetmod) < 0) 3318 fatal(net, "ioctl TEL_IOC_MODE failed\n"); 3319 binary_in = myopts[TELOPT_BINARY]; 3320 binary_out = remopts[TELOPT_BINARY]; 3321 } 3322 if (state == TS_DATA) { 3323 if ((nfrontp == nbackp) && 3324 (pfrontp == pbackp)) { 3325 if (ioctl(net, I_NREAD, &nsize) < 0) 3326 fatalperror(net, 3327 "ioctl I_NREAD failed\n", errno); 3328 if (nsize) 3329 drainstream(nsize); 3330 3331 /* 3332 * make an ioctl to reinsert remaining data at 3333 * streamhead. After this, ioctl reenables the 3334 * telnet lower put queue. This queue was 3335 * noenabled by telnet module after sending 3336 * protocol/urgent data to telnetd. 3337 */ 3338 3339 telnetmod.ic_cmd = TEL_IOC_ENABLE; 3340 telnetmod.ic_timout = -1; 3341 if (ncc || nsize) { 3342 telnetmod.ic_len = ncc + nsize; 3343 telnetmod.ic_dp = netip; 3344 } else { 3345 telnetmod.ic_len = 0; 3346 telnetmod.ic_dp = NULL; 3347 } 3348 if (ioctl(net, I_STR, &telnetmod) < 0) 3349 fatal(net, "ioctl TEL_IOC_ENABLE \ 3350 failed\n"); 3351 3352 telmod_init_done = B_TRUE; 3353 3354 netip = netibuf; 3355 (void) memset(netibuf, 0, netibufsize); 3356 3357 ncc = 0; 3358 } 3359 } else { 3360 /* 3361 * state not changed to TS_DATA and hence, more to read 3362 * send ioctl to get one more message block. 3363 */ 3364 telnetmod.ic_cmd = TEL_IOC_GETBLK; 3365 telnetmod.ic_timout = -1; 3366 telnetmod.ic_len = 0; 3367 telnetmod.ic_dp = NULL; 3368 3369 if (ioctl(net, I_STR, &telnetmod) < 0) 3370 fatal(net, "ioctl TEL_IOC_GETBLK failed\n"); 3371 } 3372 3373 if ((c = select(max(net, master) + 1, &ibits, &obits, &xbits, 3374 (struct timeval *)0)) < 1) { 3375 if (c == -1) { 3376 if (errno == EINTR) { 3377 continue; 3378 } 3379 } 3380 (void) sleep(5); 3381 continue; 3382 } 3383 3384 /* 3385 * Any urgent data? 3386 */ 3387 if (FD_ISSET(net, &xbits)) { 3388 SYNCHing = 1; 3389 } 3390 3391 /* 3392 * Something to read from the network... 3393 */ 3394 if (FD_ISSET(net, &ibits)) { 3395 ncc = read(net, netibuf, netibufsize); 3396 if (ncc < 0 && errno == EWOULDBLOCK) 3397 ncc = 0; 3398 else { 3399 if (ncc <= 0) { 3400 break; 3401 } 3402 netip = netibuf; 3403 } 3404 } 3405 3406 if (FD_ISSET(net, &obits) && (nfrontp - nbackp) > 0) 3407 netflush(); 3408 if (ncc > 0) 3409 telrcv(); 3410 if (FD_ISSET(master, &obits) && (pfrontp - pbackp) > 0) 3411 ptyflush(); 3412 } 3413 cleanup(0); 3414 } 3415 3416 static void 3417 telrcv(void) 3418 { 3419 int c; 3420 3421 while (ncc > 0) { 3422 if ((&ptyobuf[BUFSIZ] - pfrontp) < 2) 3423 return; 3424 c = *netip & 0377; 3425 /* 3426 * Once we hit data, we want to transition back to 3427 * in-kernel processing. However, this code is shared 3428 * by getterminaltype()/ttloop() which run before the 3429 * in-kernel plumbing is available. So if we are still 3430 * processing the initial option negotiation, even TS_DATA 3431 * must be processed here. 3432 */ 3433 if (c != IAC && state == TS_DATA && init_neg_done) { 3434 break; 3435 } 3436 netip++; 3437 ncc--; 3438 switch (state) { 3439 3440 case TS_CR: 3441 state = TS_DATA; 3442 /* Strip off \n or \0 after a \r */ 3443 if ((c == 0) || (c == '\n')) { 3444 break; 3445 } 3446 /* FALLTHRU */ 3447 3448 case TS_DATA: 3449 if (c == IAC) { 3450 state = TS_IAC; 3451 break; 3452 } 3453 if (inter > 0) 3454 break; 3455 /* 3456 * We map \r\n ==> \r, since 3457 * We now map \r\n ==> \r for pragmatic reasons. 3458 * Many client implementations send \r\n when 3459 * the user hits the CarriageReturn key. 3460 * 3461 * We USED to map \r\n ==> \n, since \r\n says 3462 * that we want to be in column 1 of the next 3463 * line. 3464 */ 3465 if (c == '\r' && (myopts[TELOPT_BINARY] == OPT_NO)) { 3466 state = TS_CR; 3467 } 3468 *pfrontp++ = c; 3469 break; 3470 3471 case TS_IAC: 3472 switch (c) { 3473 3474 /* 3475 * Send the process on the pty side an 3476 * interrupt. Do this with a NULL or 3477 * interrupt char; depending on the tty mode. 3478 */ 3479 case IP: 3480 interrupt(); 3481 break; 3482 3483 case BREAK: 3484 sendbrk(); 3485 break; 3486 3487 /* 3488 * Are You There? 3489 */ 3490 case AYT: 3491 write_data_len("\r\n[Yes]\r\n", 9); 3492 break; 3493 3494 /* 3495 * Abort Output 3496 */ 3497 case AO: { 3498 struct ltchars tmpltc; 3499 3500 ptyflush(); /* half-hearted */ 3501 if (ioctl(pty, TIOCGLTC, &tmpltc) == -1) 3502 syslog(LOG_INFO, 3503 "ioctl TIOCGLTC: %m\n"); 3504 if (tmpltc.t_flushc != '\377') { 3505 *pfrontp++ = tmpltc.t_flushc; 3506 } 3507 netclear(); /* clear buffer back */ 3508 write_data("%c%c", (uchar_t)IAC, 3509 (uchar_t)DM); 3510 3511 neturg = nfrontp-1; /* off by one XXX */ 3512 netflush(); 3513 netflush(); /* XXX.sparker */ 3514 break; 3515 } 3516 3517 /* 3518 * Erase Character and 3519 * Erase Line 3520 */ 3521 case EC: 3522 case EL: { 3523 struct sgttyb b; 3524 char ch; 3525 3526 ptyflush(); /* half-hearted */ 3527 if (ioctl(pty, TIOCGETP, &b) == -1) 3528 syslog(LOG_INFO, 3529 "ioctl TIOCGETP: %m\n"); 3530 ch = (c == EC) ? 3531 b.sg_erase : b.sg_kill; 3532 if (ch != '\377') { 3533 *pfrontp++ = ch; 3534 } 3535 break; 3536 } 3537 3538 /* 3539 * Check for urgent data... 3540 */ 3541 case DM: 3542 break; 3543 3544 /* 3545 * Begin option subnegotiation... 3546 */ 3547 case SB: 3548 state = TS_SB; 3549 SB_CLEAR(); 3550 continue; 3551 3552 case WILL: 3553 state = TS_WILL; 3554 continue; 3555 3556 case WONT: 3557 state = TS_WONT; 3558 continue; 3559 3560 case DO: 3561 state = TS_DO; 3562 continue; 3563 3564 case DONT: 3565 state = TS_DONT; 3566 continue; 3567 3568 case IAC: 3569 *pfrontp++ = c; 3570 break; 3571 } 3572 state = TS_DATA; 3573 break; 3574 case TS_SB: 3575 if (c == IAC) { 3576 state = TS_SE; 3577 } else { 3578 SB_ACCUM(c); 3579 } 3580 break; 3581 case TS_SE: 3582 if (c != SE) { 3583 if (c != IAC) { 3584 SB_ACCUM((uchar_t)IAC); 3585 } 3586 SB_ACCUM(c); 3587 state = TS_SB; 3588 3589 } else { 3590 SB_TERM(); 3591 suboption(); /* handle sub-option */ 3592 state = TS_DATA; 3593 } 3594 break; 3595 3596 case TS_WILL: 3597 if (remopts[c] != OPT_YES) 3598 willoption(c); 3599 state = TS_DATA; 3600 continue; 3601 3602 case TS_WONT: 3603 if (remopts[c] != OPT_NO) 3604 wontoption(c); 3605 state = TS_DATA; 3606 continue; 3607 3608 case TS_DO: 3609 if (myopts[c] != OPT_YES) 3610 dooption(c); 3611 state = TS_DATA; 3612 continue; 3613 3614 case TS_DONT: 3615 if (myopts[c] != OPT_NO) { 3616 dontoption(c); 3617 } 3618 state = TS_DATA; 3619 continue; 3620 3621 default: 3622 syslog(LOG_ERR, "telnetd: panic state=%d\n", state); 3623 (void) printf("telnetd: panic state=%d\n", state); 3624 exit(EXIT_FAILURE); 3625 } 3626 } 3627 } 3628 3629 static void 3630 willoption(int option) 3631 { 3632 uchar_t *fmt; 3633 boolean_t send_reply = B_TRUE; 3634 3635 switch (option) { 3636 case TELOPT_BINARY: 3637 mode(O_RAW, 0); 3638 fmt = doopt; 3639 break; 3640 3641 case TELOPT_ECHO: 3642 not42 = 0; /* looks like a 4.2 system */ 3643 /* 3644 * Now, in a 4.2 system, to break them out of ECHOing 3645 * (to the terminal) mode, we need to send a "WILL ECHO". 3646 * Kludge upon kludge! 3647 */ 3648 if (myopts[TELOPT_ECHO] == OPT_YES) { 3649 dooption(TELOPT_ECHO); 3650 } 3651 fmt = dont; 3652 break; 3653 case TELOPT_TTYPE: 3654 settimer(ttypeopt); 3655 goto common; 3656 3657 case TELOPT_NAWS: 3658 settimer(nawsopt); 3659 goto common; 3660 3661 case TELOPT_XDISPLOC: 3662 settimer(xdisplocopt); 3663 goto common; 3664 3665 case TELOPT_NEW_ENVIRON: 3666 settimer(environopt); 3667 goto common; 3668 3669 case TELOPT_AUTHENTICATION: 3670 settimer(authopt); 3671 if (remopts[option] == OPT_NO || 3672 negotiate_auth_krb5 == 0) 3673 fmt = dont; 3674 else 3675 fmt = doopt; 3676 break; 3677 3678 case TELOPT_OLD_ENVIRON: 3679 settimer(oenvironopt); 3680 goto common; 3681 common: 3682 if (remopts[option] == OPT_YES_BUT_ALWAYS_LOOK) { 3683 remopts[option] = OPT_YES; 3684 return; 3685 } 3686 /*FALLTHRU*/ 3687 case TELOPT_SGA: 3688 fmt = doopt; 3689 break; 3690 3691 case TELOPT_TM: 3692 fmt = dont; 3693 break; 3694 3695 case TELOPT_ENCRYPT: 3696 settimer(encropt); /* got response to do/dont */ 3697 if (enc_debug) 3698 (void) fprintf(stderr, 3699 "RCVD IAC WILL TELOPT_ENCRYPT\n"); 3700 if (krb5_privacy_allowed()) { 3701 fmt = doopt; 3702 if (sent_do_encrypt) 3703 send_reply = B_FALSE; 3704 else 3705 sent_do_encrypt = B_TRUE; 3706 } else { 3707 fmt = dont; 3708 } 3709 break; 3710 3711 default: 3712 fmt = dont; 3713 break; 3714 } 3715 if (fmt == doopt) { 3716 remopts[option] = OPT_YES; 3717 } else { 3718 remopts[option] = OPT_NO; 3719 } 3720 if (send_reply) { 3721 write_data((const char *)fmt, option); 3722 netflush(); 3723 } 3724 } 3725 3726 static void 3727 wontoption(int option) 3728 { 3729 uchar_t *fmt; 3730 int send_reply = 1; 3731 3732 switch (option) { 3733 case TELOPT_ECHO: 3734 not42 = 1; /* doesn't seem to be a 4.2 system */ 3735 break; 3736 3737 case TELOPT_BINARY: 3738 mode(0, O_RAW); 3739 break; 3740 3741 case TELOPT_TTYPE: 3742 settimer(ttypeopt); 3743 break; 3744 3745 case TELOPT_NAWS: 3746 settimer(nawsopt); 3747 break; 3748 3749 case TELOPT_XDISPLOC: 3750 settimer(xdisplocopt); 3751 break; 3752 3753 case TELOPT_NEW_ENVIRON: 3754 settimer(environopt); 3755 break; 3756 3757 case TELOPT_OLD_ENVIRON: 3758 settimer(oenvironopt); 3759 break; 3760 3761 case TELOPT_AUTHENTICATION: 3762 settimer(authopt); 3763 auth_finished(0, AUTH_REJECT); 3764 if (auth_debug) 3765 (void) fprintf(stderr, 3766 "RCVD WONT TELOPT_AUTHENTICATE\n"); 3767 3768 remopts[option] = OPT_NO; 3769 send_reply = 0; 3770 break; 3771 3772 case TELOPT_ENCRYPT: 3773 if (enc_debug) 3774 (void) fprintf(stderr, 3775 "RCVD IAC WONT TELOPT_ENCRYPT\n"); 3776 settimer(encropt); /* got response to will/wont */ 3777 /* 3778 * Remote side cannot send encryption. No reply necessary 3779 * Treat this as if "IAC SB ENCRYPT END IAC SE" were 3780 * received (RFC 2946) and disable crypto. 3781 */ 3782 encrypt_end(TELNET_DIR_DECRYPT); 3783 send_reply = 0; 3784 break; 3785 } 3786 3787 fmt = dont; 3788 remopts[option] = OPT_NO; 3789 if (send_reply) { 3790 write_data((const char *)fmt, option); 3791 } 3792 } 3793 3794 /* 3795 * We received an "IAC DO ..." message from the client, change our state 3796 * to OPT_YES. 3797 */ 3798 static void 3799 dooption(int option) 3800 { 3801 uchar_t *fmt; 3802 boolean_t send_reply = B_TRUE; 3803 3804 switch (option) { 3805 3806 case TELOPT_TM: 3807 fmt = wont; 3808 break; 3809 3810 case TELOPT_ECHO: 3811 mode(O_ECHO|O_CRMOD, 0); 3812 fmt = will; 3813 break; 3814 3815 case TELOPT_BINARY: 3816 mode(O_RAW, 0); 3817 fmt = will; 3818 break; 3819 3820 case TELOPT_SGA: 3821 fmt = will; 3822 break; 3823 3824 case TELOPT_LOGOUT: 3825 /* 3826 * Options don't get much easier. Acknowledge the option, 3827 * and then clean up and exit. 3828 */ 3829 write_data((const char *)will, option); 3830 netflush(); 3831 cleanup(0); 3832 /*NOTREACHED*/ 3833 3834 case TELOPT_ENCRYPT: 3835 if (enc_debug) 3836 (void) fprintf(stderr, "RCVD DO TELOPT_ENCRYPT\n"); 3837 settimer(encropt); 3838 /* 3839 * We received a "DO". This indicates that the other side 3840 * wants us to encrypt our data (pending negotiatoin). 3841 * reply with "IAC WILL ENCRYPT" if we are able to send 3842 * encrypted data. 3843 */ 3844 if (krb5_privacy_allowed() && negotiate_encrypt) { 3845 fmt = will; 3846 if (sent_will_encrypt) 3847 send_reply = B_FALSE; 3848 else 3849 sent_will_encrypt = B_TRUE; 3850 /* return if we already sent "WILL ENCRYPT" */ 3851 if (myopts[option] == OPT_YES) 3852 return; 3853 } else { 3854 fmt = wont; 3855 } 3856 break; 3857 3858 case TELOPT_AUTHENTICATION: 3859 if (auth_debug) { 3860 (void) fprintf(stderr, 3861 "RCVD DO TELOPT_AUTHENTICATION\n"); 3862 } 3863 /* 3864 * RFC 2941 - only the server can send 3865 * "DO TELOPT_AUTHENTICATION". 3866 * if a server receives this, it must respond with WONT... 3867 */ 3868 fmt = wont; 3869 break; 3870 3871 default: 3872 fmt = wont; 3873 break; 3874 } 3875 if (fmt == will) { 3876 myopts[option] = OPT_YES; 3877 } else { 3878 myopts[option] = OPT_NO; 3879 } 3880 if (send_reply) { 3881 write_data((const char *)fmt, option); 3882 netflush(); 3883 } 3884 } 3885 3886 /* 3887 * We received an "IAC DONT ..." message from client. 3888 * Client does not agree with the option so act accordingly. 3889 */ 3890 static void 3891 dontoption(int option) 3892 { 3893 int send_reply = 1; 3894 switch (option) { 3895 case TELOPT_ECHO: 3896 /* 3897 * we should stop echoing, since the client side will be doing 3898 * it, but keep mapping CR since CR-LF will be mapped to it. 3899 */ 3900 mode(0, O_ECHO); 3901 break; 3902 3903 case TELOPT_ENCRYPT: 3904 if (enc_debug) 3905 (void) fprintf(stderr, "RCVD IAC DONT ENCRYPT\n"); 3906 settimer(encropt); 3907 /* 3908 * Remote side cannot receive any encrypted data, 3909 * so dont send any. No reply necessary. 3910 */ 3911 send_reply = 0; 3912 break; 3913 3914 default: 3915 break; 3916 } 3917 3918 myopts[option] = OPT_NO; 3919 3920 if (send_reply) { 3921 write_data((const char *)wont, option); 3922 } 3923 } 3924 3925 /* 3926 * suboption() 3927 * 3928 * Look at the sub-option buffer, and try to be helpful to the other 3929 * side. 3930 * 3931 */ 3932 static void 3933 suboption(void) 3934 { 3935 int subchar; 3936 3937 switch (subchar = SB_GET()) { 3938 case TELOPT_TTYPE: { /* Yaaaay! */ 3939 static char terminalname[5+41] = "TERM="; 3940 3941 settimer(ttypesubopt); 3942 3943 if (SB_GET() != TELQUAL_IS) { 3944 return; /* ??? XXX but, this is the most robust */ 3945 } 3946 3947 terminaltype = terminalname+strlen(terminalname); 3948 3949 while (terminaltype < (terminalname + sizeof (terminalname) - 3950 1) && !SB_EOF()) { 3951 int c; 3952 3953 c = SB_GET(); 3954 if (isupper(c)) { 3955 c = tolower(c); 3956 } 3957 *terminaltype++ = c; /* accumulate name */ 3958 } 3959 *terminaltype = 0; 3960 terminaltype = terminalname; 3961 break; 3962 } 3963 3964 case TELOPT_NAWS: { 3965 struct winsize ws; 3966 3967 if (SB_EOF()) { 3968 return; 3969 } 3970 ws.ws_col = SB_GET() << 8; 3971 if (SB_EOF()) { 3972 return; 3973 } 3974 ws.ws_col |= SB_GET(); 3975 if (SB_EOF()) { 3976 return; 3977 } 3978 ws.ws_row = SB_GET() << 8; 3979 if (SB_EOF()) { 3980 return; 3981 } 3982 ws.ws_row |= SB_GET(); 3983 ws.ws_xpixel = 0; ws.ws_ypixel = 0; 3984 (void) ioctl(pty, TIOCSWINSZ, &ws); 3985 settimer(nawsopt); 3986 break; 3987 } 3988 3989 case TELOPT_XDISPLOC: { 3990 if (SB_EOF() || SB_GET() != TELQUAL_IS) { 3991 return; 3992 } 3993 settimer(xdisplocsubopt); 3994 subpointer[SB_LEN()] = '\0'; 3995 if ((new_env("DISPLAY", subpointer)) == 1) 3996 perror("malloc"); 3997 break; 3998 } 3999 4000 case TELOPT_NEW_ENVIRON: 4001 case TELOPT_OLD_ENVIRON: { 4002 int c; 4003 char *cp, *varp, *valp; 4004 4005 if (SB_EOF()) 4006 return; 4007 c = SB_GET(); 4008 if (c == TELQUAL_IS) { 4009 if (subchar == TELOPT_OLD_ENVIRON) 4010 settimer(oenvironsubopt); 4011 else 4012 settimer(environsubopt); 4013 } else if (c != TELQUAL_INFO) { 4014 return; 4015 } 4016 4017 if (subchar == TELOPT_NEW_ENVIRON) { 4018 while (!SB_EOF()) { 4019 c = SB_GET(); 4020 if ((c == NEW_ENV_VAR) || (c == ENV_USERVAR)) 4021 break; 4022 } 4023 } else 4024 { 4025 while (!SB_EOF()) { 4026 c = SB_GET(); 4027 if ((c == env_ovar) || (c == ENV_USERVAR)) 4028 break; 4029 } 4030 } 4031 4032 if (SB_EOF()) 4033 return; 4034 4035 cp = varp = (char *)subpointer; 4036 valp = 0; 4037 4038 while (!SB_EOF()) { 4039 c = SB_GET(); 4040 if (subchar == TELOPT_OLD_ENVIRON) { 4041 if (c == env_ovar) 4042 c = NEW_ENV_VAR; 4043 else if (c == env_ovalue) 4044 c = NEW_ENV_VALUE; 4045 } 4046 switch (c) { 4047 4048 case NEW_ENV_VALUE: 4049 *cp = '\0'; 4050 cp = valp = (char *)subpointer; 4051 break; 4052 4053 case NEW_ENV_VAR: 4054 case ENV_USERVAR: 4055 *cp = '\0'; 4056 if (valp) { 4057 if ((new_env(varp, valp)) == 1) { 4058 perror("malloc"); 4059 } 4060 } else { 4061 (void) del_env(varp); 4062 } 4063 cp = varp = (char *)subpointer; 4064 valp = 0; 4065 break; 4066 4067 case ENV_ESC: 4068 if (SB_EOF()) 4069 break; 4070 c = SB_GET(); 4071 /* FALL THROUGH */ 4072 default: 4073 *cp++ = c; 4074 break; 4075 } 4076 } 4077 *cp = '\0'; 4078 if (valp) { 4079 if ((new_env(varp, valp)) == 1) { 4080 perror("malloc"); 4081 } 4082 } else { 4083 (void) del_env(varp); 4084 } 4085 break; 4086 } /* end of case TELOPT_NEW_ENVIRON */ 4087 4088 case TELOPT_AUTHENTICATION: 4089 if (SB_EOF()) 4090 break; 4091 switch (SB_GET()) { 4092 case TELQUAL_SEND: 4093 case TELQUAL_REPLY: 4094 /* 4095 * These are sent server only and cannot be sent by the 4096 * client. 4097 */ 4098 break; 4099 case TELQUAL_IS: 4100 if (auth_debug) 4101 (void) fprintf(stderr, 4102 "RCVD AUTHENTICATION IS " 4103 "(%d bytes)\n", 4104 SB_LEN()); 4105 if (!auth_negotiated) 4106 auth_is((uchar_t *)subpointer, SB_LEN()); 4107 break; 4108 case TELQUAL_NAME: 4109 if (auth_debug) 4110 (void) fprintf(stderr, 4111 "RCVD AUTHENTICATION NAME " 4112 "(%d bytes)\n", 4113 SB_LEN()); 4114 if (!auth_negotiated) 4115 auth_name((uchar_t *)subpointer, SB_LEN()); 4116 break; 4117 } 4118 break; 4119 4120 case TELOPT_ENCRYPT: { 4121 int c; 4122 if (SB_EOF()) 4123 break; 4124 c = SB_GET(); 4125 #ifdef ENCRYPT_NAMES 4126 if (enc_debug) 4127 (void) fprintf(stderr, "RCVD ENCRYPT %s\n", 4128 ENCRYPT_NAME(c)); 4129 #endif /* ENCRYPT_NAMES */ 4130 switch (c) { 4131 case ENCRYPT_SUPPORT: 4132 encrypt_support(subpointer, SB_LEN()); 4133 break; 4134 case ENCRYPT_IS: 4135 encrypt_is((uchar_t *)subpointer, SB_LEN()); 4136 break; 4137 case ENCRYPT_REPLY: 4138 (void) encrypt_reply(subpointer, SB_LEN()); 4139 break; 4140 case ENCRYPT_START: 4141 encrypt_start(); 4142 break; 4143 case ENCRYPT_END: 4144 encrypt_end(TELNET_DIR_DECRYPT); 4145 break; 4146 case ENCRYPT_REQSTART: 4147 encrypt_request_start(); 4148 break; 4149 case ENCRYPT_REQEND: 4150 /* 4151 * We can always send an REQEND so that we cannot 4152 * get stuck encrypting. We should only get this 4153 * if we have been able to get in the correct mode 4154 * anyhow. 4155 */ 4156 encrypt_request_end(); 4157 break; 4158 case ENCRYPT_ENC_KEYID: 4159 encrypt_enc_keyid(subpointer, SB_LEN()); 4160 break; 4161 case ENCRYPT_DEC_KEYID: 4162 encrypt_dec_keyid(subpointer, SB_LEN()); 4163 break; 4164 default: 4165 break; 4166 } 4167 } 4168 break; 4169 4170 default: 4171 break; 4172 } 4173 } 4174 4175 static void 4176 mode(int on, int off) 4177 { 4178 struct termios tios; 4179 4180 ptyflush(); 4181 if (tcgetattr(pty, &tios) < 0) 4182 syslog(LOG_INFO, "tcgetattr: %m\n"); 4183 4184 if (on & O_RAW) { 4185 tios.c_cflag |= CS8; 4186 tios.c_iflag &= ~IUCLC; 4187 tios.c_lflag &= ~(XCASE|IEXTEN); 4188 } 4189 if (off & O_RAW) { 4190 if ((tios.c_cflag & PARENB) != 0) 4191 tios.c_cflag &= ~CS8; 4192 tios.c_lflag |= IEXTEN; 4193 } 4194 4195 if (on & O_ECHO) 4196 tios.c_lflag |= ECHO; 4197 if (off & O_ECHO) 4198 tios.c_lflag &= ~ECHO; 4199 4200 if (on & O_CRMOD) { 4201 tios.c_iflag |= ICRNL; 4202 tios.c_oflag |= ONLCR; 4203 } 4204 /* 4205 * Because "O_CRMOD" will never be set in "off" we don't have to 4206 * handle this case here. 4207 */ 4208 4209 if (tcsetattr(pty, TCSANOW, &tios) < 0) 4210 syslog(LOG_INFO, "tcsetattr: %m\n"); 4211 } 4212 4213 /* 4214 * Send interrupt to process on other side of pty. 4215 * If it is in raw mode, just write NULL; 4216 * otherwise, write intr char. 4217 */ 4218 static void 4219 interrupt(void) 4220 { 4221 struct sgttyb b; 4222 struct tchars tchars; 4223 4224 ptyflush(); /* half-hearted */ 4225 if (ioctl(pty, TIOCGETP, &b) == -1) 4226 syslog(LOG_INFO, "ioctl TIOCGETP: %m\n"); 4227 if (b.sg_flags & O_RAW) { 4228 *pfrontp++ = '\0'; 4229 return; 4230 } 4231 *pfrontp++ = ioctl(pty, TIOCGETC, &tchars) < 0 ? 4232 '\177' : tchars.t_intrc; 4233 } 4234 4235 /* 4236 * Send quit to process on other side of pty. 4237 * If it is in raw mode, just write NULL; 4238 * otherwise, write quit char. 4239 */ 4240 static void 4241 sendbrk(void) 4242 { 4243 struct sgttyb b; 4244 struct tchars tchars; 4245 4246 ptyflush(); /* half-hearted */ 4247 (void) ioctl(pty, TIOCGETP, &b); 4248 if (b.sg_flags & O_RAW) { 4249 *pfrontp++ = '\0'; 4250 return; 4251 } 4252 *pfrontp++ = ioctl(pty, TIOCGETC, &tchars) < 0 ? 4253 '\034' : tchars.t_quitc; 4254 } 4255 4256 static void 4257 ptyflush(void) 4258 { 4259 int n; 4260 4261 if ((n = pfrontp - pbackp) > 0) 4262 n = write(master, pbackp, n); 4263 if (n < 0) 4264 return; 4265 pbackp += n; 4266 if (pbackp == pfrontp) 4267 pbackp = pfrontp = ptyobuf; 4268 } 4269 4270 /* 4271 * nextitem() 4272 * 4273 * Return the address of the next "item" in the TELNET data 4274 * stream. This will be the address of the next character if 4275 * the current address is a user data character, or it will 4276 * be the address of the character following the TELNET command 4277 * if the current address is a TELNET IAC ("I Am a Command") 4278 * character. 4279 */ 4280 4281 static char * 4282 nextitem(char *current) 4283 { 4284 if ((*current&0xff) != IAC) { 4285 return (current+1); 4286 } 4287 switch (*(current+1)&0xff) { 4288 case DO: 4289 case DONT: 4290 case WILL: 4291 case WONT: 4292 return (current+3); 4293 case SB: /* loop forever looking for the SE */ 4294 { 4295 char *look = current+2; 4296 4297 for (;;) { 4298 if ((*look++&0xff) == IAC) { 4299 if ((*look++&0xff) == SE) { 4300 return (look); 4301 } 4302 } 4303 } 4304 } 4305 default: 4306 return (current+2); 4307 } 4308 } 4309 4310 4311 /* 4312 * netclear() 4313 * 4314 * We are about to do a TELNET SYNCH operation. Clear 4315 * the path to the network. 4316 * 4317 * Things are a bit tricky since we may have sent the first 4318 * byte or so of a previous TELNET command into the network. 4319 * So, we have to scan the network buffer from the beginning 4320 * until we are up to where we want to be. 4321 * 4322 * A side effect of what we do, just to keep things 4323 * simple, is to clear the urgent data pointer. The principal 4324 * caller should be setting the urgent data pointer AFTER calling 4325 * us in any case. 4326 */ 4327 static void 4328 netclear(void) 4329 { 4330 char *thisitem, *next; 4331 char *good; 4332 #define wewant(p) ((nfrontp > p) && ((*p&0xff) == IAC) && \ 4333 ((*(p+1)&0xff) != EC) && ((*(p+1)&0xff) != EL)) 4334 4335 thisitem = netobuf; 4336 4337 while ((next = nextitem(thisitem)) <= nbackp) { 4338 thisitem = next; 4339 } 4340 4341 /* Now, thisitem is first before/at boundary. */ 4342 4343 good = netobuf; /* where the good bytes go */ 4344 4345 while (nfrontp > thisitem) { 4346 if (wewant(thisitem)) { 4347 int length; 4348 4349 next = thisitem; 4350 do { 4351 next = nextitem(next); 4352 } while (wewant(next) && (nfrontp > next)); 4353 length = next-thisitem; 4354 (void) memmove(good, thisitem, length); 4355 good += length; 4356 thisitem = next; 4357 } else { 4358 thisitem = nextitem(thisitem); 4359 } 4360 } 4361 4362 nbackp = netobuf; 4363 nfrontp = good; /* next byte to be sent */ 4364 neturg = 0; 4365 } 4366 4367 4368 /* 4369 * netflush 4370 * Send as much data as possible to the network, 4371 * handling requests for urgent data. 4372 */ 4373 static void 4374 netflush(void) 4375 { 4376 int n; 4377 4378 if ((n = nfrontp - nbackp) > 0) { 4379 /* 4380 * if no urgent data, or if the other side appears to be an 4381 * old 4.2 client (and thus unable to survive TCP urgent data), 4382 * write the entire buffer in non-OOB mode. 4383 */ 4384 if ((neturg == 0) || (not42 == 0)) { 4385 n = write(net, nbackp, n); /* normal write */ 4386 } else { 4387 n = neturg - nbackp; 4388 /* 4389 * In 4.2 (and 4.3) systems, there is some question 4390 * about what byte in a sendOOB operation is the "OOB" 4391 * data. To make ourselves compatible, we only send ONE 4392 * byte out of band, the one WE THINK should be OOB 4393 * (though we really have more the TCP philosophy of 4394 * urgent data rather than the Unix philosophy of OOB 4395 * data). 4396 */ 4397 if (n > 1) { 4398 /* send URGENT all by itself */ 4399 n = write(net, nbackp, n-1); 4400 } else { 4401 /* URGENT data */ 4402 n = send_oob(net, nbackp, n); 4403 } 4404 } 4405 } 4406 if (n < 0) { 4407 if (errno == EWOULDBLOCK) 4408 return; 4409 /* should blow this guy away... */ 4410 return; 4411 } 4412 4413 nbackp += n; 4414 4415 if (nbackp >= neturg) { 4416 neturg = 0; 4417 } 4418 if (nbackp == nfrontp) { 4419 nbackp = nfrontp = netobuf; 4420 } 4421 } 4422 4423 /* ARGSUSED */ 4424 static void 4425 cleanup(int signum) 4426 { 4427 /* 4428 * If the TEL_IOC_ENABLE ioctl hasn't completed, then we need to 4429 * handle closing differently. We close "net" first and then 4430 * "master" in that order. We do close(net) first because 4431 * we have no other way to disconnect forwarding between the network 4432 * and master. So by issuing the close()'s we ensure that no further 4433 * data rises from TCP. A more complex fix would be adding proper 4434 * support for throwing a "stop" switch for forwarding data between 4435 * logindmux peers. It's possible to block in the close of the tty 4436 * while the network still receives data and the telmod module is 4437 * TEL_STOPPED. A denial-of-service attack generates this case, 4438 * see 4102102. 4439 */ 4440 4441 if (!telmod_init_done) { 4442 (void) close(net); 4443 (void) close(master); 4444 } 4445 rmut(); 4446 4447 exit(EXIT_FAILURE); 4448 } 4449 4450 static void 4451 rmut(void) 4452 { 4453 pam_handle_t *pamh; 4454 struct utmpx *up; 4455 char user[sizeof (up->ut_user) + 1]; 4456 char ttyn[sizeof (up->ut_line) + 1]; 4457 char rhost[sizeof (up->ut_host) + 1]; 4458 4459 /* while cleaning up don't allow disruption */ 4460 (void) signal(SIGCHLD, SIG_IGN); 4461 4462 setutxent(); 4463 while (up = getutxent()) { 4464 if (up->ut_pid == pid) { 4465 if (up->ut_type == DEAD_PROCESS) { 4466 /* 4467 * Cleaned up elsewhere. 4468 */ 4469 break; 4470 } 4471 4472 /* 4473 * call pam_close_session if login changed 4474 * the utmpx user entry from type LOGIN_PROCESS 4475 * to type USER_PROCESS, which happens 4476 * after pam_open_session is called. 4477 */ 4478 if (up->ut_type == USER_PROCESS) { 4479 (void) strlcpy(user, up->ut_user, 4480 sizeof (user)); 4481 (void) strlcpy(ttyn, up->ut_line, 4482 sizeof (ttyn)); 4483 (void) strlcpy(rhost, up->ut_host, 4484 sizeof (rhost)); 4485 if ((pam_start("telnet", user, NULL, &pamh)) == 4486 PAM_SUCCESS) { 4487 (void) pam_set_item(pamh, PAM_TTY, 4488 ttyn); 4489 (void) pam_set_item(pamh, PAM_RHOST, 4490 rhost); 4491 (void) pam_close_session(pamh, 0); 4492 (void) pam_end(pamh, PAM_SUCCESS); 4493 } 4494 } 4495 4496 up->ut_type = DEAD_PROCESS; 4497 up->ut_exit.e_termination = WTERMSIG(0); 4498 up->ut_exit.e_exit = WEXITSTATUS(0); 4499 (void) time(&up->ut_tv.tv_sec); 4500 4501 if (modutx(up) == NULL) { 4502 /* 4503 * Since modutx failed we'll 4504 * write out the new entry 4505 * ourselves. 4506 */ 4507 (void) pututxline(up); 4508 updwtmpx("wtmpx", up); 4509 } 4510 break; 4511 } 4512 } 4513 4514 endutxent(); 4515 4516 (void) signal(SIGCHLD, (void (*)())cleanup); 4517 } 4518 4519 static int 4520 readstream(int fd, char *buf, int offset) 4521 { 4522 struct strbuf ctlbuf, datbuf; 4523 union T_primitives tpi; 4524 int ret = 0; 4525 int flags = 0; 4526 int bytes_avail, count; 4527 4528 (void) memset((char *)&ctlbuf, 0, sizeof (ctlbuf)); 4529 (void) memset((char *)&datbuf, 0, sizeof (datbuf)); 4530 4531 ctlbuf.buf = (char *)&tpi; 4532 ctlbuf.maxlen = sizeof (tpi); 4533 4534 if (ioctl(fd, I_NREAD, &bytes_avail) < 0) { 4535 syslog(LOG_ERR, "I_NREAD returned error %m"); 4536 return (-1); 4537 } 4538 if (bytes_avail > netibufsize - offset) { 4539 count = netip - netibuf; 4540 netibuf = (char *)realloc(netibuf, 4541 (unsigned)netibufsize + bytes_avail); 4542 if (netibuf == NULL) { 4543 fatal(net, "netibuf realloc failed\n"); 4544 } 4545 netibufsize += bytes_avail; 4546 netip = netibuf + count; 4547 buf = netibuf; 4548 } 4549 datbuf.buf = buf + offset; 4550 datbuf.maxlen = netibufsize; 4551 ret = getmsg(fd, &ctlbuf, &datbuf, &flags); 4552 if (ret < 0) { 4553 syslog(LOG_ERR, "getmsg returned -1, errno %d\n", 4554 errno); 4555 return (-1); 4556 } 4557 if (ctlbuf.len <= 0) { 4558 return (datbuf.len); 4559 } 4560 4561 if (tpi.type == T_DATA_REQ) { 4562 return (0); 4563 } 4564 4565 if ((tpi.type == T_ORDREL_IND) || (tpi.type == T_DISCON_IND)) 4566 cleanup(0); 4567 fatal(fd, "no data or protocol element recognized"); 4568 /*NOTREACHED*/ 4569 } 4570 4571 static void 4572 drainstream(int size) 4573 { 4574 int nbytes; 4575 int tsize; 4576 4577 tsize = netip - netibuf; 4578 4579 if ((tsize + ncc + size) > netibufsize) { 4580 if (!(netibuf = (char *)realloc(netibuf, 4581 (unsigned)tsize + ncc + size))) 4582 fatalperror(net, "netibuf realloc failed\n", errno); 4583 netibufsize = tsize + ncc + size; 4584 4585 netip = netibuf + tsize; 4586 } 4587 4588 if ((nbytes = read(net, (char *)netip + ncc, size)) != size) 4589 syslog(LOG_ERR, "read %d bytes\n", nbytes); 4590 } 4591 4592 /* 4593 * TPI style replacement for socket send() primitive, so we don't require 4594 * sockmod to be on the stream. 4595 */ 4596 static int 4597 send_oob(int fd, char *ptr, int count) 4598 { 4599 struct T_exdata_req exd_req; 4600 struct strbuf hdr, dat; 4601 int ret; 4602 4603 exd_req.PRIM_type = T_EXDATA_REQ; 4604 exd_req.MORE_flag = 0; 4605 4606 hdr.buf = (char *)&exd_req; 4607 hdr.len = sizeof (exd_req); 4608 4609 dat.buf = ptr; 4610 dat.len = count; 4611 4612 ret = putmsg(fd, &hdr, &dat, 0); 4613 if (ret == 0) { 4614 ret = count; 4615 } 4616 return (ret); 4617 } 4618 4619 4620 /* 4621 * local_setenv -- 4622 * Set the value of the environmental variable "name" to be 4623 * "value". If rewrite is set, replace any current value. 4624 */ 4625 static int 4626 local_setenv(const char *name, const char *value, int rewrite) 4627 { 4628 static int alloced; /* if allocated space before */ 4629 char *c; 4630 int l_value, offset; 4631 4632 /* 4633 * Do not allow environment variables which begin with LD_ to be 4634 * inserted into the environment. While normally the dynamic linker 4635 * protects the login program, that is based on the assumption hostile 4636 * invocation of login are from non-root users. However, since telnetd 4637 * runs as root, this cannot be utilized. So instead we simply 4638 * prevent LD_* from being inserted into the environment. 4639 * This also applies to other environment variables that 4640 * are to be ignored in setugid apps. 4641 * Note that at this point name can contain '='! 4642 * Also, do not allow TTYPROMPT to be passed along here. 4643 */ 4644 if (strncmp(name, "LD_", 3) == 0 || 4645 strncmp(name, "NLSPATH", 7) == 0 || 4646 (strncmp(name, "TTYPROMPT", 9) == 0 && 4647 (name[9] == '\0' || name[9] == '='))) { 4648 return (-1); 4649 } 4650 if (*value == '=') /* no `=' in value */ 4651 ++value; 4652 l_value = strlen(value); 4653 if ((c = __findenv(name, &offset))) { /* find if already exists */ 4654 if (!rewrite) 4655 return (0); 4656 if ((int)strlen(c) >= l_value) { /* old larger; copy over */ 4657 while (*c++ = *value++); 4658 return (0); 4659 } 4660 } else { /* create new slot */ 4661 int cnt; 4662 char **p; 4663 4664 for (p = environ, cnt = 0; *p; ++p, ++cnt); 4665 if (alloced) { /* just increase size */ 4666 environ = (char **)realloc((char *)environ, 4667 (size_t)(sizeof (char *) * (cnt + 2))); 4668 if (!environ) 4669 return (-1); 4670 } else { /* get new space */ 4671 alloced = 1; /* copy old entries into it */ 4672 p = (char **)malloc((size_t)(sizeof (char *)* 4673 (cnt + 2))); 4674 if (!p) 4675 return (-1); 4676 (void) memcpy(p, environ, cnt * sizeof (char *)); 4677 environ = p; 4678 } 4679 environ[cnt + 1] = NULL; 4680 offset = cnt; 4681 } 4682 for (c = (char *)name; *c && *c != '='; ++c); /* no `=' in name */ 4683 if (!(environ[offset] = /* name + `=' + value */ 4684 malloc((size_t)((int)(c - name) + l_value + 2)))) 4685 return (-1); 4686 for (c = environ[offset]; ((*c = *name++) != 0) && (*c != '='); ++c); 4687 for (*c++ = '='; *c++ = *value++; ); 4688 return (0); 4689 } 4690 4691 /* 4692 * local_unsetenv(name) -- 4693 * Delete environmental variable "name". 4694 */ 4695 static void 4696 local_unsetenv(const char *name) 4697 { 4698 char **p; 4699 int offset; 4700 4701 while (__findenv(name, &offset)) /* if set multiple times */ 4702 for (p = &environ[offset]; ; ++p) 4703 if ((*p = *(p + 1)) == 0) 4704 break; 4705 } 4706 4707 /* 4708 * __findenv -- 4709 * Returns pointer to value associated with name, if any, else NULL. 4710 * Sets offset to be the offset of the name/value combination in the 4711 * environmental array, for use by local_setenv() and local_unsetenv(). 4712 * Explicitly removes '=' in argument name. 4713 */ 4714 static char * 4715 __findenv(const char *name, int *offset) 4716 { 4717 extern char **environ; 4718 int len; 4719 const char *np; 4720 char **p, *c; 4721 4722 if (name == NULL || environ == NULL) 4723 return (NULL); 4724 for (np = name; *np && *np != '='; ++np) 4725 continue; 4726 len = np - name; 4727 for (p = environ; (c = *p) != NULL; ++p) 4728 if (strncmp(c, name, len) == 0 && c[len] == '=') { 4729 *offset = p - environ; 4730 return (c + len + 1); 4731 } 4732 return (NULL); 4733 } 4734 4735 static void 4736 showbanner(void) 4737 { 4738 char *cp; 4739 char evalbuf[BUFSIZ]; 4740 4741 if (defopen(defaultfile) == 0) { 4742 int flags; 4743 4744 /* ignore case */ 4745 flags = defcntl(DC_GETFLAGS, 0); 4746 TURNOFF(flags, DC_CASE); 4747 defcntl(DC_SETFLAGS, flags); 4748 if (cp = defread(bannervar)) { 4749 FILE *fp; 4750 4751 if (strlen(cp) + strlen("eval echo '") + strlen("'\n") 4752 + 1 < sizeof (evalbuf)) { 4753 (void) strlcpy(evalbuf, "eval echo '", 4754 sizeof (evalbuf)); 4755 (void) strlcat(evalbuf, cp, sizeof (evalbuf)); 4756 (void) strlcat(evalbuf, "'\n", 4757 sizeof (evalbuf)); 4758 4759 if (fp = popen(evalbuf, "r")) { 4760 char buf[BUFSIZ]; 4761 size_t size; 4762 4763 /* 4764 * Pipe I/O atomicity guarantees we 4765 * need only one read. 4766 */ 4767 if ((size = fread(buf, 1, 4768 sizeof (buf) - 1, 4769 fp)) != 0) { 4770 char *p; 4771 buf[size] = '\0'; 4772 p = strrchr(buf, '\n'); 4773 if (p != NULL) 4774 *p = '\0'; 4775 if (strlen(buf)) { 4776 map_banner(buf); 4777 netflush(); 4778 } 4779 } 4780 (void) pclose(fp); 4781 /* close default file */ 4782 (void) defopen(NULL); 4783 return; 4784 } 4785 } 4786 } 4787 (void) defopen(NULL); /* close default file */ 4788 } 4789 4790 defbanner(); 4791 netflush(); 4792 } 4793 4794 static void 4795 map_banner(char *p) 4796 { 4797 char *q; 4798 4799 /* 4800 * Map the banner: "\n" -> "\r\n" and "\r" -> "\r\0" 4801 */ 4802 for (q = nfrontp; p && *p && q < nfrontp + sizeof (netobuf) - 1; ) 4803 if (*p == '\n') { 4804 *q++ = '\r'; 4805 *q++ = '\n'; 4806 p++; 4807 } else if (*p == '\r') { 4808 *q++ = '\r'; 4809 *q++ = '\0'; 4810 p++; 4811 } else 4812 *q++ = *p++; 4813 4814 nfrontp += q - netobuf; 4815 } 4816 4817 /* 4818 * Show banner that getty never gave. By default, this is `uname -sr`. 4819 * 4820 * The banner includes some null's (for TELNET CR disambiguation), 4821 * so we have to be somewhat complicated. 4822 */ 4823 static void 4824 defbanner(void) 4825 { 4826 struct utsname u; 4827 4828 /* 4829 * Dont show this if the '-h' option was present 4830 */ 4831 if (!show_hostinfo) 4832 return; 4833 4834 if (uname(&u) == -1) 4835 return; 4836 4837 write_data_len((const char *) BANNER1, sizeof (BANNER1) - 1); 4838 write_data_len(u.sysname, strlen(u.sysname)); 4839 write_data_len(" ", 1); 4840 write_data_len(u.release, strlen(u.release)); 4841 write_data_len((const char *)BANNER2, sizeof (BANNER2) - 1); 4842 } 4843 4844 /* 4845 * Verify that the named module is at the top of the stream 4846 * and then pop it off. 4847 */ 4848 static int 4849 removemod(int f, char *modname) 4850 { 4851 char topmodname[BUFSIZ]; 4852 4853 if (ioctl(f, I_LOOK, topmodname) < 0) 4854 return (-1); 4855 if (strcmp(modname, topmodname) != 0) { 4856 errno = ENXIO; 4857 return (-1); 4858 } 4859 if (ioctl(f, I_POP, 0) < 0) 4860 return (-1); 4861 return (0); 4862 } 4863 4864 static void 4865 write_data(const char *format, ...) 4866 { 4867 va_list args; 4868 int len; 4869 char argp[BUFSIZ]; 4870 4871 va_start(args, format); 4872 4873 if ((len = vsnprintf(argp, sizeof (argp), format, args)) == -1) 4874 return; 4875 4876 write_data_len(argp, len); 4877 va_end(args); 4878 } 4879 4880 static void 4881 write_data_len(const char *buf, int len) 4882 { 4883 int remaining, copied; 4884 4885 remaining = BUFSIZ - (nfrontp - netobuf); 4886 while (len > 0) { 4887 /* 4888 * If there's not enough space in netobuf then 4889 * try to make some. 4890 */ 4891 if ((len > BUFSIZ ? BUFSIZ : len) > remaining) { 4892 netflush(); 4893 remaining = BUFSIZ - (nfrontp - netobuf); 4894 } 4895 /* Copy as much as we can */ 4896 copied = remaining > len ? len : remaining; 4897 (void) memmove(nfrontp, buf, copied); 4898 nfrontp += copied; 4899 len -= copied; 4900 remaining -= copied; 4901 buf += copied; 4902 } 4903 } 4904