1*0Sstevel@tonic-gate /* 2*0Sstevel@tonic-gate * Copyright 2002 Sun Microsystems, Inc. All rights reserved. 3*0Sstevel@tonic-gate * Use is subject to license terms. 4*0Sstevel@tonic-gate */ 5*0Sstevel@tonic-gate 6*0Sstevel@tonic-gate #pragma ident "%Z%%M% %I% %E% SMI" 7*0Sstevel@tonic-gate 8*0Sstevel@tonic-gate /* 9*0Sstevel@tonic-gate * Copyright (c) 1988, 1990 Regents of the University of California. 10*0Sstevel@tonic-gate * All rights reserved. 11*0Sstevel@tonic-gate * 12*0Sstevel@tonic-gate * Redistribution and use in source and binary forms, with or without 13*0Sstevel@tonic-gate * modification, are permitted provided that the following conditions 14*0Sstevel@tonic-gate * are met: 15*0Sstevel@tonic-gate * 1. Redistributions of source code must retain the above copyright 16*0Sstevel@tonic-gate * notice, this list of conditions and the following disclaimer. 17*0Sstevel@tonic-gate * 2. Redistributions in binary form must reproduce the above copyright 18*0Sstevel@tonic-gate * notice, this list of conditions and the following disclaimer in the 19*0Sstevel@tonic-gate * documentation and/or other materials provided with the distribution. 20*0Sstevel@tonic-gate * 3. All advertising materials mentioning features or use of this software 21*0Sstevel@tonic-gate * must display the following acknowledgement: 22*0Sstevel@tonic-gate * This product includes software developed by the University of 23*0Sstevel@tonic-gate * California, Berkeley and its contributors. 24*0Sstevel@tonic-gate * 4. Neither the name of the University nor the names of its contributors 25*0Sstevel@tonic-gate * may be used to endorse or promote products derived from this software 26*0Sstevel@tonic-gate * without specific prior written permission. 27*0Sstevel@tonic-gate * 28*0Sstevel@tonic-gate * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 29*0Sstevel@tonic-gate * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 30*0Sstevel@tonic-gate * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 31*0Sstevel@tonic-gate * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 32*0Sstevel@tonic-gate * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 33*0Sstevel@tonic-gate * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 34*0Sstevel@tonic-gate * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 35*0Sstevel@tonic-gate * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 36*0Sstevel@tonic-gate * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 37*0Sstevel@tonic-gate * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 38*0Sstevel@tonic-gate * SUCH DAMAGE. 39*0Sstevel@tonic-gate */ 40*0Sstevel@tonic-gate 41*0Sstevel@tonic-gate #ifndef lint 42*0Sstevel@tonic-gate char copyright[] = 43*0Sstevel@tonic-gate "@(#) Copyright (c) 1988, 1990 Regents of the University of California.\n" 44*0Sstevel@tonic-gate " All rights reserved.\n"; 45*0Sstevel@tonic-gate #endif /* not lint */ 46*0Sstevel@tonic-gate 47*0Sstevel@tonic-gate #ifndef lint 48*0Sstevel@tonic-gate static char sccsid[] = "@(#)main.c 5.5 (Berkeley) 12/18/92"; 49*0Sstevel@tonic-gate #endif /* not lint */ 50*0Sstevel@tonic-gate 51*0Sstevel@tonic-gate #include <string.h> 52*0Sstevel@tonic-gate #include <sys/types.h> 53*0Sstevel@tonic-gate 54*0Sstevel@tonic-gate #include "ring.h" 55*0Sstevel@tonic-gate #include "externs.h" 56*0Sstevel@tonic-gate #include "defines.h" 57*0Sstevel@tonic-gate 58*0Sstevel@tonic-gate /* These values need to be the same as defined in libtelnet/kerberos5.c */ 59*0Sstevel@tonic-gate /* Either define them in both places, or put in some common header file. */ 60*0Sstevel@tonic-gate #define OPTS_FORWARD_CREDS 0x00000002 61*0Sstevel@tonic-gate #define OPTS_FORWARDABLE_CREDS 0x00000001 62*0Sstevel@tonic-gate 63*0Sstevel@tonic-gate /* 64*0Sstevel@tonic-gate * This flag is incremented, if any of the 65*0Sstevel@tonic-gate * Kerberos command line options are used. 66*0Sstevel@tonic-gate */ 67*0Sstevel@tonic-gate int krb5auth_flag = 0; 68*0Sstevel@tonic-gate 69*0Sstevel@tonic-gate /* 70*0Sstevel@tonic-gate * Initialize variables. 71*0Sstevel@tonic-gate */ 72*0Sstevel@tonic-gate int 73*0Sstevel@tonic-gate tninit() 74*0Sstevel@tonic-gate { 75*0Sstevel@tonic-gate init_terminal(); 76*0Sstevel@tonic-gate 77*0Sstevel@tonic-gate init_network(); 78*0Sstevel@tonic-gate 79*0Sstevel@tonic-gate if (init_telnet() == 0) 80*0Sstevel@tonic-gate return (0); 81*0Sstevel@tonic-gate 82*0Sstevel@tonic-gate init_sys(); 83*0Sstevel@tonic-gate 84*0Sstevel@tonic-gate return (1); 85*0Sstevel@tonic-gate } 86*0Sstevel@tonic-gate 87*0Sstevel@tonic-gate #if defined(USE_TOS) 88*0Sstevel@tonic-gate #define TELNET_OPTIONS "8EKLS:X:acde:fFk:l:n:rt:x" 89*0Sstevel@tonic-gate #else 90*0Sstevel@tonic-gate #define TELNET_OPTIONS "8EKLX:acde:fFk:l:n:rt:x" 91*0Sstevel@tonic-gate #endif /* USE_TOS */ 92*0Sstevel@tonic-gate 93*0Sstevel@tonic-gate static void 94*0Sstevel@tonic-gate usage() 95*0Sstevel@tonic-gate { 96*0Sstevel@tonic-gate (void) fprintf(stderr, "Usage: %s %s\n", 97*0Sstevel@tonic-gate prompt, 98*0Sstevel@tonic-gate " [-8] [-E] [-K] [-L] [-a] [-c] [-d] [-f/-F] [-r] [-x]" 99*0Sstevel@tonic-gate "\n\t[-e char] [-k realm] [-l user] [-n tracefile] [-X atype]" 100*0Sstevel@tonic-gate "\n\t[host-name [port]]"); 101*0Sstevel@tonic-gate exit(1); 102*0Sstevel@tonic-gate } 103*0Sstevel@tonic-gate 104*0Sstevel@tonic-gate /* 105*0Sstevel@tonic-gate * main. Parse arguments, invoke the protocol or command parser. 106*0Sstevel@tonic-gate */ 107*0Sstevel@tonic-gate 108*0Sstevel@tonic-gate 109*0Sstevel@tonic-gate int 110*0Sstevel@tonic-gate main(int argc, char *argv[]) 111*0Sstevel@tonic-gate { 112*0Sstevel@tonic-gate int ch; 113*0Sstevel@tonic-gate char *user; 114*0Sstevel@tonic-gate extern boolean_t auth_enable_encrypt; 115*0Sstevel@tonic-gate extern int forward_flags; 116*0Sstevel@tonic-gate 117*0Sstevel@tonic-gate /* Clear out things */ 118*0Sstevel@tonic-gate if (tninit() == 0) 119*0Sstevel@tonic-gate return (EXIT_FAILURE); 120*0Sstevel@tonic-gate 121*0Sstevel@tonic-gate if (!isatty(fileno(stdin))) { 122*0Sstevel@tonic-gate setbuf(stdin, NULL); 123*0Sstevel@tonic-gate } 124*0Sstevel@tonic-gate if (!isatty(fileno(stdout))) { 125*0Sstevel@tonic-gate setbuf(stdout, NULL); 126*0Sstevel@tonic-gate } 127*0Sstevel@tonic-gate 128*0Sstevel@tonic-gate TerminalSaveState(); 129*0Sstevel@tonic-gate 130*0Sstevel@tonic-gate if (prompt = strrchr(argv[0], '/')) 131*0Sstevel@tonic-gate ++prompt; 132*0Sstevel@tonic-gate else 133*0Sstevel@tonic-gate prompt = argv[0]; 134*0Sstevel@tonic-gate 135*0Sstevel@tonic-gate user = NULL; 136*0Sstevel@tonic-gate 137*0Sstevel@tonic-gate rlogin = (strncmp(prompt, "rlog", 4) == 0) ? '~' : _POSIX_VDISABLE; 138*0Sstevel@tonic-gate autologin = -1; 139*0Sstevel@tonic-gate 140*0Sstevel@tonic-gate while ((ch = getopt(argc, argv, TELNET_OPTIONS)) != EOF) { 141*0Sstevel@tonic-gate switch (ch) { 142*0Sstevel@tonic-gate case 'K': 143*0Sstevel@tonic-gate autologin_set = 1; 144*0Sstevel@tonic-gate autologin = 0; 145*0Sstevel@tonic-gate krb5auth_flag++; 146*0Sstevel@tonic-gate break; 147*0Sstevel@tonic-gate case 'X': 148*0Sstevel@tonic-gate auth_disable_name(optarg); 149*0Sstevel@tonic-gate krb5auth_flag++; 150*0Sstevel@tonic-gate break; 151*0Sstevel@tonic-gate case 'a': 152*0Sstevel@tonic-gate autologin_set = 1; 153*0Sstevel@tonic-gate autologin = 1; 154*0Sstevel@tonic-gate krb5auth_flag++; 155*0Sstevel@tonic-gate break; 156*0Sstevel@tonic-gate case 'f': 157*0Sstevel@tonic-gate if (forward_flags & OPTS_FORWARD_CREDS) { 158*0Sstevel@tonic-gate (void) fprintf(stderr, gettext( 159*0Sstevel@tonic-gate "%s: Only one of -f " 160*0Sstevel@tonic-gate "and -F allowed.\n"), prompt); 161*0Sstevel@tonic-gate usage(); 162*0Sstevel@tonic-gate } 163*0Sstevel@tonic-gate forward_flags |= OPTS_FORWARD_CREDS; 164*0Sstevel@tonic-gate forward_flag_set = 1; 165*0Sstevel@tonic-gate krb5auth_flag++; 166*0Sstevel@tonic-gate break; 167*0Sstevel@tonic-gate case 'F': 168*0Sstevel@tonic-gate if (forward_flags & OPTS_FORWARD_CREDS) { 169*0Sstevel@tonic-gate (void) fprintf(stderr, gettext( 170*0Sstevel@tonic-gate "%s: Only one of -f " 171*0Sstevel@tonic-gate "and -F allowed.\n"), prompt); 172*0Sstevel@tonic-gate usage(); 173*0Sstevel@tonic-gate } 174*0Sstevel@tonic-gate forward_flags |= OPTS_FORWARD_CREDS; 175*0Sstevel@tonic-gate forward_flags |= OPTS_FORWARDABLE_CREDS; 176*0Sstevel@tonic-gate forwardable_flag_set = 1; 177*0Sstevel@tonic-gate forward_flag = 1; 178*0Sstevel@tonic-gate krb5auth_flag++; 179*0Sstevel@tonic-gate break; 180*0Sstevel@tonic-gate case 'k': 181*0Sstevel@tonic-gate set_krb5_realm(optarg); 182*0Sstevel@tonic-gate krb5auth_flag++; 183*0Sstevel@tonic-gate break; 184*0Sstevel@tonic-gate case 'x': 185*0Sstevel@tonic-gate if (krb5_privacy_allowed()) { 186*0Sstevel@tonic-gate encrypt_auto(1); 187*0Sstevel@tonic-gate decrypt_auto(1); 188*0Sstevel@tonic-gate wantencryption = B_TRUE; 189*0Sstevel@tonic-gate autologin = 1; 190*0Sstevel@tonic-gate autologin_set = 1; 191*0Sstevel@tonic-gate auth_enable_encrypt = B_TRUE; 192*0Sstevel@tonic-gate encrypt_flag_set = 1; 193*0Sstevel@tonic-gate krb5auth_flag++; 194*0Sstevel@tonic-gate } else { 195*0Sstevel@tonic-gate (void) fprintf(stderr, gettext( 196*0Sstevel@tonic-gate "%s: Encryption not supported.\n"), 197*0Sstevel@tonic-gate prompt); 198*0Sstevel@tonic-gate exit(1); 199*0Sstevel@tonic-gate } 200*0Sstevel@tonic-gate break; 201*0Sstevel@tonic-gate 202*0Sstevel@tonic-gate /* begin common options */ 203*0Sstevel@tonic-gate case '8': 204*0Sstevel@tonic-gate eight = 3; /* binary output and input */ 205*0Sstevel@tonic-gate break; 206*0Sstevel@tonic-gate case 'E': 207*0Sstevel@tonic-gate escape_valid = B_FALSE; 208*0Sstevel@tonic-gate rlogin = escape = _POSIX_VDISABLE; 209*0Sstevel@tonic-gate break; 210*0Sstevel@tonic-gate case 'L': 211*0Sstevel@tonic-gate eight |= 2; /* binary output only */ 212*0Sstevel@tonic-gate break; 213*0Sstevel@tonic-gate #if USE_TOS 214*0Sstevel@tonic-gate case 'S': 215*0Sstevel@tonic-gate (void) fprintf(stderr, 216*0Sstevel@tonic-gate "%s: Warning: -S ignored, no parsetos() support.\n", 217*0Sstevel@tonic-gate prompt); 218*0Sstevel@tonic-gate break; 219*0Sstevel@tonic-gate #endif /* USE_TOS */ 220*0Sstevel@tonic-gate case 'c': 221*0Sstevel@tonic-gate skiprc = 1; 222*0Sstevel@tonic-gate break; 223*0Sstevel@tonic-gate case 'd': 224*0Sstevel@tonic-gate debug = 1; 225*0Sstevel@tonic-gate break; 226*0Sstevel@tonic-gate case 'e': 227*0Sstevel@tonic-gate escape_valid = B_TRUE; 228*0Sstevel@tonic-gate set_escape_char(optarg); 229*0Sstevel@tonic-gate break; 230*0Sstevel@tonic-gate case 'l': 231*0Sstevel@tonic-gate autologin_set = 1; 232*0Sstevel@tonic-gate autologin = 1; 233*0Sstevel@tonic-gate user = optarg; 234*0Sstevel@tonic-gate break; 235*0Sstevel@tonic-gate case 'n': 236*0Sstevel@tonic-gate SetNetTrace(optarg); 237*0Sstevel@tonic-gate break; 238*0Sstevel@tonic-gate case 'r': 239*0Sstevel@tonic-gate rlogin = '~'; 240*0Sstevel@tonic-gate break; 241*0Sstevel@tonic-gate case 't': 242*0Sstevel@tonic-gate (void) fprintf(stderr, 243*0Sstevel@tonic-gate "%s: Warning: -t ignored, no TN3270 support.\n", 244*0Sstevel@tonic-gate prompt); 245*0Sstevel@tonic-gate break; 246*0Sstevel@tonic-gate default: 247*0Sstevel@tonic-gate usage(); 248*0Sstevel@tonic-gate /* NOTREACHED */ 249*0Sstevel@tonic-gate } 250*0Sstevel@tonic-gate } 251*0Sstevel@tonic-gate if (autologin == -1) 252*0Sstevel@tonic-gate autologin = (rlogin == _POSIX_VDISABLE) ? 0 : 1; 253*0Sstevel@tonic-gate 254*0Sstevel@tonic-gate argc -= optind; 255*0Sstevel@tonic-gate argv += optind; 256*0Sstevel@tonic-gate 257*0Sstevel@tonic-gate if (argc) { 258*0Sstevel@tonic-gate char *args[7], **argp = args; 259*0Sstevel@tonic-gate 260*0Sstevel@tonic-gate if (argc > 2) 261*0Sstevel@tonic-gate usage(); 262*0Sstevel@tonic-gate *argp++ = prompt; 263*0Sstevel@tonic-gate if (user) { 264*0Sstevel@tonic-gate *argp++ = "-l"; 265*0Sstevel@tonic-gate *argp++ = user; 266*0Sstevel@tonic-gate } 267*0Sstevel@tonic-gate *argp++ = argv[0]; /* host */ 268*0Sstevel@tonic-gate if (argc > 1) 269*0Sstevel@tonic-gate *argp++ = argv[1]; /* port */ 270*0Sstevel@tonic-gate *argp = 0; 271*0Sstevel@tonic-gate 272*0Sstevel@tonic-gate if (setjmp(toplevel) != 0) 273*0Sstevel@tonic-gate Exit(EXIT_SUCCESS); 274*0Sstevel@tonic-gate if (tn(argp - args, args) == 1) 275*0Sstevel@tonic-gate return (EXIT_SUCCESS); 276*0Sstevel@tonic-gate else 277*0Sstevel@tonic-gate return (EXIT_FAILURE); 278*0Sstevel@tonic-gate } 279*0Sstevel@tonic-gate (void) setjmp(toplevel); 280*0Sstevel@tonic-gate for (;;) { 281*0Sstevel@tonic-gate command(1, 0, 0); 282*0Sstevel@tonic-gate } 283*0Sstevel@tonic-gate } 284