1*7c478bd9Sstevel@tonic-gate /* 2*7c478bd9Sstevel@tonic-gate * Copyright 2001 Sun Microsystems, Inc. All rights reserved. 3*7c478bd9Sstevel@tonic-gate * Use is subject to license terms. 4*7c478bd9Sstevel@tonic-gate */ 5*7c478bd9Sstevel@tonic-gate 6*7c478bd9Sstevel@tonic-gate /* Copyright (c) 1983, 1984, 1985, 1986, 1987, 1988, 1989 AT&T */ 7*7c478bd9Sstevel@tonic-gate /* All Rights Reserved */ 8*7c478bd9Sstevel@tonic-gate 9*7c478bd9Sstevel@tonic-gate /* 10*7c478bd9Sstevel@tonic-gate * Copyright (c) 1980 Regents of the University of California. 11*7c478bd9Sstevel@tonic-gate * All rights reserved. The Berkeley software License Agreement 12*7c478bd9Sstevel@tonic-gate * specifies the terms and conditions for redistribution. 13*7c478bd9Sstevel@tonic-gate */ 14*7c478bd9Sstevel@tonic-gate 15*7c478bd9Sstevel@tonic-gate #pragma ident "%Z%%M% %I% %E% SMI" 16*7c478bd9Sstevel@tonic-gate 17*7c478bd9Sstevel@tonic-gate /*LINTLIBRARY*/ 18*7c478bd9Sstevel@tonic-gate 19*7c478bd9Sstevel@tonic-gate #ifndef lint 20*7c478bd9Sstevel@tonic-gate static char 21*7c478bd9Sstevel@tonic-gate sccsid[] = "@(#)cr_tty.c 1.7 88/02/08 SMI"; /* from UCB 5.2 85/11/08 */ 22*7c478bd9Sstevel@tonic-gate #endif /* not lint */ 23*7c478bd9Sstevel@tonic-gate 24*7c478bd9Sstevel@tonic-gate /* 25*7c478bd9Sstevel@tonic-gate * Terminal initialization routines. 26*7c478bd9Sstevel@tonic-gate */ 27*7c478bd9Sstevel@tonic-gate 28*7c478bd9Sstevel@tonic-gate #include <unistd.h> 29*7c478bd9Sstevel@tonic-gate #include <string.h> 30*7c478bd9Sstevel@tonic-gate #include <sgtty.h> 31*7c478bd9Sstevel@tonic-gate #include "curses.ext" 32*7c478bd9Sstevel@tonic-gate #include <term.h> 33*7c478bd9Sstevel@tonic-gate 34*7c478bd9Sstevel@tonic-gate /* forward declaration */ 35*7c478bd9Sstevel@tonic-gate void zap(void); 36*7c478bd9Sstevel@tonic-gate 37*7c478bd9Sstevel@tonic-gate static bool *sflags[] = { 38*7c478bd9Sstevel@tonic-gate &AM, &BS, &DA, &DB, &EO, &HC, &HZ, &IN, &MI, 39*7c478bd9Sstevel@tonic-gate &MS, &NC, &NS, &OS, &UL, &XB, &XN, &XT, &XS, 40*7c478bd9Sstevel@tonic-gate &XX 41*7c478bd9Sstevel@tonic-gate }; 42*7c478bd9Sstevel@tonic-gate 43*7c478bd9Sstevel@tonic-gate static char *_PC, 44*7c478bd9Sstevel@tonic-gate **sstrs[] = { 45*7c478bd9Sstevel@tonic-gate &AL, &BC, &BT, &CD, &CE, &CL, &CM, &CR, &CS, 46*7c478bd9Sstevel@tonic-gate &DC, &DL, &DM, &DO, &ED, &EI, &K0, &K1, &K2, 47*7c478bd9Sstevel@tonic-gate &K3, &K4, &K5, &K6, &K7, &K8, &K9, &HO, &IC, 48*7c478bd9Sstevel@tonic-gate &IM, &IP, &KD, &KE, &KH, &KL, &KR, &KS, &KU, 49*7c478bd9Sstevel@tonic-gate &LL, &MA, &ND, &NL, &_PC, &RC, &SC, &SE, &SF, 50*7c478bd9Sstevel@tonic-gate &SO, &SR, &TA, &TE, &TI, &UC, &UE, &UP, &US, 51*7c478bd9Sstevel@tonic-gate &VB, &VS, &VE, &AL_PARM, &DL_PARM, &UP_PARM, 52*7c478bd9Sstevel@tonic-gate &DOWN_PARM, &LEFT_PARM, &RIGHT_PARM, 53*7c478bd9Sstevel@tonic-gate }; 54*7c478bd9Sstevel@tonic-gate 55*7c478bd9Sstevel@tonic-gate char _tspace[2048]; /* Space for capability strings */ 56*7c478bd9Sstevel@tonic-gate 57*7c478bd9Sstevel@tonic-gate static char *aoftspace; /* Address of _tspace for relocation */ 58*7c478bd9Sstevel@tonic-gate 59*7c478bd9Sstevel@tonic-gate static int destcol, destline; 60*7c478bd9Sstevel@tonic-gate 61*7c478bd9Sstevel@tonic-gate /* 62*7c478bd9Sstevel@tonic-gate * This routine does terminal type initialization routines, and 63*7c478bd9Sstevel@tonic-gate * calculation of flags at entry. It is almost entirely stolen from 64*7c478bd9Sstevel@tonic-gate * Bill Joy's ex version 2.6. 65*7c478bd9Sstevel@tonic-gate */ 66*7c478bd9Sstevel@tonic-gate short ospeed = -1; 67*7c478bd9Sstevel@tonic-gate 68*7c478bd9Sstevel@tonic-gate int 69*7c478bd9Sstevel@tonic-gate gettmode(void) 70*7c478bd9Sstevel@tonic-gate { 71*7c478bd9Sstevel@tonic-gate if (gtty(_tty_ch, &_tty) < 0) 72*7c478bd9Sstevel@tonic-gate return (ERR); 73*7c478bd9Sstevel@tonic-gate savetty(); 74*7c478bd9Sstevel@tonic-gate if (stty(_tty_ch, &_tty) < 0) 75*7c478bd9Sstevel@tonic-gate _tty.sg_flags = _res_flg; 76*7c478bd9Sstevel@tonic-gate ospeed = _tty.sg_ospeed; 77*7c478bd9Sstevel@tonic-gate _res_flg = _tty.sg_flags; 78*7c478bd9Sstevel@tonic-gate UPPERCASE = (_tty.sg_flags & LCASE) != 0; 79*7c478bd9Sstevel@tonic-gate GT = ((_tty.sg_flags & XTABS) == 0); 80*7c478bd9Sstevel@tonic-gate NONL = ((_tty.sg_flags & CRMOD) == 0); 81*7c478bd9Sstevel@tonic-gate _tty.sg_flags &= ~XTABS; 82*7c478bd9Sstevel@tonic-gate (void) stty(_tty_ch, &_tty); 83*7c478bd9Sstevel@tonic-gate #ifdef DEBUG 84*7c478bd9Sstevel@tonic-gate fprintf(outf, "GETTMODE: UPPERCASE = %s\n", UPPERCASE ? "TRUE":"FALSE"); 85*7c478bd9Sstevel@tonic-gate fprintf(outf, "GETTMODE: GT = %s\n", GT ? "TRUE" : "FALSE"); 86*7c478bd9Sstevel@tonic-gate fprintf(outf, "GETTMODE: NONL = %s\n", NONL ? "TRUE" : "FALSE"); 87*7c478bd9Sstevel@tonic-gate fprintf(outf, "GETTMODE: ospeed = %d\n", ospeed); 88*7c478bd9Sstevel@tonic-gate #endif 89*7c478bd9Sstevel@tonic-gate return (OK); 90*7c478bd9Sstevel@tonic-gate } 91*7c478bd9Sstevel@tonic-gate 92*7c478bd9Sstevel@tonic-gate int 93*7c478bd9Sstevel@tonic-gate setterm(char *type) 94*7c478bd9Sstevel@tonic-gate { 95*7c478bd9Sstevel@tonic-gate int unknown; 96*7c478bd9Sstevel@tonic-gate static char genbuf[1024]; 97*7c478bd9Sstevel@tonic-gate #ifdef TIOCGWINSZ 98*7c478bd9Sstevel@tonic-gate struct winsize win; 99*7c478bd9Sstevel@tonic-gate #endif 100*7c478bd9Sstevel@tonic-gate 101*7c478bd9Sstevel@tonic-gate #ifdef DEBUG 102*7c478bd9Sstevel@tonic-gate fprintf(outf, "SETTERM(\"%s\")\n", type); 103*7c478bd9Sstevel@tonic-gate fprintf(outf, "SETTERM: LINES = %d, COLS = %d\n", LINES, COLS); 104*7c478bd9Sstevel@tonic-gate #endif 105*7c478bd9Sstevel@tonic-gate if (type[0] == '\0') 106*7c478bd9Sstevel@tonic-gate type = "xx"; 107*7c478bd9Sstevel@tonic-gate unknown = FALSE; 108*7c478bd9Sstevel@tonic-gate if (tgetent(genbuf, type) != 1) { 109*7c478bd9Sstevel@tonic-gate unknown++; 110*7c478bd9Sstevel@tonic-gate (void) strcpy(genbuf, "xx|dumb:"); 111*7c478bd9Sstevel@tonic-gate } 112*7c478bd9Sstevel@tonic-gate #ifdef DEBUG 113*7c478bd9Sstevel@tonic-gate fprintf(outf, "SETTERM: tty = %s\n", type); 114*7c478bd9Sstevel@tonic-gate #endif 115*7c478bd9Sstevel@tonic-gate #ifdef TIOCGWINSZ 116*7c478bd9Sstevel@tonic-gate if (ioctl(_tty_ch, TIOCGWINSZ, &win) >= 0) { 117*7c478bd9Sstevel@tonic-gate if (LINES == 0) 118*7c478bd9Sstevel@tonic-gate LINES = win.ws_row; 119*7c478bd9Sstevel@tonic-gate if (COLS == 0) 120*7c478bd9Sstevel@tonic-gate COLS = win.ws_col; 121*7c478bd9Sstevel@tonic-gate } 122*7c478bd9Sstevel@tonic-gate #endif 123*7c478bd9Sstevel@tonic-gate 124*7c478bd9Sstevel@tonic-gate if (LINES == 0) 125*7c478bd9Sstevel@tonic-gate LINES = tgetnum("li"); 126*7c478bd9Sstevel@tonic-gate if (LINES <= 5) 127*7c478bd9Sstevel@tonic-gate LINES = 24; 128*7c478bd9Sstevel@tonic-gate 129*7c478bd9Sstevel@tonic-gate if (COLS == 0) 130*7c478bd9Sstevel@tonic-gate COLS = tgetnum("co"); 131*7c478bd9Sstevel@tonic-gate if (COLS <= 4) 132*7c478bd9Sstevel@tonic-gate COLS = 80; 133*7c478bd9Sstevel@tonic-gate 134*7c478bd9Sstevel@tonic-gate #ifdef DEBUG 135*7c478bd9Sstevel@tonic-gate fprintf(outf, "SETTERM: LINES = %d, COLS = %d\n", LINES, COLS); 136*7c478bd9Sstevel@tonic-gate #endif 137*7c478bd9Sstevel@tonic-gate aoftspace = _tspace; 138*7c478bd9Sstevel@tonic-gate zap(); /* get terminal description */ 139*7c478bd9Sstevel@tonic-gate 140*7c478bd9Sstevel@tonic-gate /* 141*7c478bd9Sstevel@tonic-gate * Handle funny termcap capabilities 142*7c478bd9Sstevel@tonic-gate */ 143*7c478bd9Sstevel@tonic-gate if (CS && SC && RC) AL = DL = ""; 144*7c478bd9Sstevel@tonic-gate if (AL_PARM && AL == NULL) AL = ""; 145*7c478bd9Sstevel@tonic-gate if (DL_PARM && DL == NULL) DL = ""; 146*7c478bd9Sstevel@tonic-gate if (IC && IM == NULL) IM = ""; 147*7c478bd9Sstevel@tonic-gate if (IC && EI == NULL) EI = ""; 148*7c478bd9Sstevel@tonic-gate if (!GT) BT = NULL; /* If we can't tab, we can't backtab either */ 149*7c478bd9Sstevel@tonic-gate 150*7c478bd9Sstevel@tonic-gate if (tgoto(CM, destcol, destline)[0] == 'O') 151*7c478bd9Sstevel@tonic-gate CA = FALSE, CM = 0; 152*7c478bd9Sstevel@tonic-gate else 153*7c478bd9Sstevel@tonic-gate CA = TRUE; 154*7c478bd9Sstevel@tonic-gate 155*7c478bd9Sstevel@tonic-gate PC = _PC ? _PC[0] : FALSE; 156*7c478bd9Sstevel@tonic-gate aoftspace = _tspace; 157*7c478bd9Sstevel@tonic-gate (void) strncpy(ttytype, longname(genbuf, type), sizeof (ttytype) - 1); 158*7c478bd9Sstevel@tonic-gate ttytype[sizeof (ttytype) - 1] = '\0'; 159*7c478bd9Sstevel@tonic-gate if (unknown) 160*7c478bd9Sstevel@tonic-gate return (ERR); 161*7c478bd9Sstevel@tonic-gate return (OK); 162*7c478bd9Sstevel@tonic-gate } 163*7c478bd9Sstevel@tonic-gate 164*7c478bd9Sstevel@tonic-gate /* 165*7c478bd9Sstevel@tonic-gate * This routine gets all the terminal flags from the termcap database 166*7c478bd9Sstevel@tonic-gate */ 167*7c478bd9Sstevel@tonic-gate 168*7c478bd9Sstevel@tonic-gate void 169*7c478bd9Sstevel@tonic-gate zap(void) 170*7c478bd9Sstevel@tonic-gate { 171*7c478bd9Sstevel@tonic-gate char *namp; 172*7c478bd9Sstevel@tonic-gate bool **fp; 173*7c478bd9Sstevel@tonic-gate char ***sp; 174*7c478bd9Sstevel@tonic-gate #ifdef DEBUG 175*7c478bd9Sstevel@tonic-gate char *cp; 176*7c478bd9Sstevel@tonic-gate #endif 177*7c478bd9Sstevel@tonic-gate 178*7c478bd9Sstevel@tonic-gate namp = "ambsdadbeohchzinmimsncnsosulxbxnxtxsxx"; 179*7c478bd9Sstevel@tonic-gate fp = sflags; 180*7c478bd9Sstevel@tonic-gate do { 181*7c478bd9Sstevel@tonic-gate *(*fp++) = tgetflag(namp); 182*7c478bd9Sstevel@tonic-gate #ifdef DEBUG 183*7c478bd9Sstevel@tonic-gate fprintf(outf, "%2.2s = %s\n", namp, *fp[-1] ? "TRUE" : "FALSE"); 184*7c478bd9Sstevel@tonic-gate #endif 185*7c478bd9Sstevel@tonic-gate namp += 2; 186*7c478bd9Sstevel@tonic-gate } while (*namp); 187*7c478bd9Sstevel@tonic-gate namp = "albcbtcdceclcmcrcsdcdldmdoedeik0k1k2k3k4k5k6k7k8k9" 188*7c478bd9Sstevel@tonic-gate "hoicimipkdkekhklkrkskullmandnlpcrcscsesfsosrtatet" 189*7c478bd9Sstevel@tonic-gate "iucueupusvbvsveALDLUPDOLERI"; 190*7c478bd9Sstevel@tonic-gate sp = sstrs; 191*7c478bd9Sstevel@tonic-gate do { 192*7c478bd9Sstevel@tonic-gate *(*sp++) = tgetstr(namp, &aoftspace); 193*7c478bd9Sstevel@tonic-gate #ifdef DEBUG 194*7c478bd9Sstevel@tonic-gate fprintf(outf, "%2.2s = %s", 195*7c478bd9Sstevel@tonic-gate namp, *sp[-1] == NULL ? "NULL\n" : "\""); 196*7c478bd9Sstevel@tonic-gate if (*sp[-1] != NULL) { 197*7c478bd9Sstevel@tonic-gate for (cp = *sp[-1]; *cp; cp++) 198*7c478bd9Sstevel@tonic-gate fprintf(outf, "%s", unctrl(*cp)); 199*7c478bd9Sstevel@tonic-gate fprintf(outf, "\"\n"); 200*7c478bd9Sstevel@tonic-gate } 201*7c478bd9Sstevel@tonic-gate #endif 202*7c478bd9Sstevel@tonic-gate namp += 2; 203*7c478bd9Sstevel@tonic-gate } while (*namp); 204*7c478bd9Sstevel@tonic-gate if (XS) 205*7c478bd9Sstevel@tonic-gate SO = SE = NULL; 206*7c478bd9Sstevel@tonic-gate else { 207*7c478bd9Sstevel@tonic-gate if (tgetnum("sg") > 0) 208*7c478bd9Sstevel@tonic-gate SO = NULL; 209*7c478bd9Sstevel@tonic-gate if (tgetnum("ug") > 0) 210*7c478bd9Sstevel@tonic-gate US = NULL; 211*7c478bd9Sstevel@tonic-gate if (!SO && US) { 212*7c478bd9Sstevel@tonic-gate SO = US; 213*7c478bd9Sstevel@tonic-gate SE = UE; 214*7c478bd9Sstevel@tonic-gate } 215*7c478bd9Sstevel@tonic-gate } 216*7c478bd9Sstevel@tonic-gate } 217*7c478bd9Sstevel@tonic-gate 218*7c478bd9Sstevel@tonic-gate /* 219*7c478bd9Sstevel@tonic-gate * return a capability from termcap 220*7c478bd9Sstevel@tonic-gate */ 221*7c478bd9Sstevel@tonic-gate 222*7c478bd9Sstevel@tonic-gate char * 223*7c478bd9Sstevel@tonic-gate getcap(char *name) 224*7c478bd9Sstevel@tonic-gate { 225*7c478bd9Sstevel@tonic-gate return (tgetstr(name, &aoftspace)); 226*7c478bd9Sstevel@tonic-gate } 227