1 /* 2 * Copyright (c) 1981 Regents of the University of California. 3 * All rights reserved. 4 * 5 * %sccs.include.redist.c% 6 */ 7 8 #ifndef lint 9 static char sccsid[] = "@(#)setterm.c 5.11 (Berkeley) 09/21/92"; 10 #endif /* not lint */ 11 12 #include <sys/ioctl.h> 13 14 #include <curses.h> 15 #include <stdlib.h> 16 #include <string.h> 17 #include <unistd.h> 18 19 static void zap __P((void)); 20 21 static char *sflags[] = { 22 &AM, &BS, &DA, &EO, &HC, &HZ, &IN, &MI, &MS, 23 &NC, &NS, &OS, &UL, &XB, &XN, &XT, &XS, &XX 24 }; 25 26 static char *_PC, 27 **sstrs[] = { 28 &AL, &BC, &BT, &CD, &CE, &CL, &CM, &CR, &CS, 29 &DC, &DL, &DM, &DO, &ED, &EI, &K0, &K1, &K2, 30 &K3, &K4, &K5, &K6, &K7, &K8, &K9, &HO, &IC, 31 &IM, &IP, &KD, &KE, &KH, &KL, &KR, &KS, &KU, 32 &LL, &MA, &ND, &NL, &_PC, &RC, &SC, &SE, &SF, 33 &SO, &SR, &TA, &TE, &TI, &UC, &UE, &UP, &US, 34 &VB, &VS, &VE, &al, &dl, &sf, &sr, &AL_PARM, 35 &DL_PARM, &UP_PARM, &DOWN_PARM, &LEFT_PARM, 36 &RIGHT_PARM, 37 }; 38 39 static char *aoftspace; /* Address of _tspace for relocation */ 40 static char tspace[2048]; /* Space for capability strings */ 41 42 static int destcol, destline; 43 44 char *ttytype; 45 46 int 47 setterm(type) 48 register char *type; 49 { 50 static char genbuf[1024]; 51 static char __ttytype[1024]; 52 register int unknown; 53 struct winsize win; 54 char *p; 55 56 #ifdef DEBUG 57 __TRACE("setterm: (\"%s\")\nLINES = %d, COLS = %d\n", 58 type, LINES, COLS); 59 #endif 60 if (type[0] == '\0') 61 type = "xx"; 62 unknown = 0; 63 if (tgetent(genbuf, type) != 1) { 64 unknown++; 65 strcpy(genbuf, "xx|dumb:"); 66 } 67 #ifdef DEBUG 68 __TRACE("setterm: tty = %s\n", type); 69 #endif 70 71 /* Try TIOCGWINSZ, and, if it fails, the termcap entry. */ 72 if (ioctl(STDERR_FILENO, TIOCGWINSZ, &win) != -1 && 73 win.ws_row != 0 && win.ws_col != 0) { 74 LINES = win.ws_row; 75 COLS = win.ws_col; 76 } else { 77 LINES = tgetnum("li"); 78 COLS = tgetnum("co"); 79 } 80 81 /* POSIX 1003.2 requires that the environment override. */ 82 if ((p = getenv("ROWS")) != NULL) 83 LINES = strtol(p, NULL, 10); 84 if ((p = getenv("COLUMNS")) != NULL) 85 COLS = strtol(p, NULL, 10); 86 87 /* 88 * XXX 89 * Historically, curses fails if rows <= 5, cols <= 4. 90 */ 91 if (LINES <= 5 || COLS <= 4) 92 return (ERR); 93 94 #ifdef DEBUG 95 __TRACE("setterm: LINES = %d, COLS = %d\n", LINES, COLS); 96 #endif 97 aoftspace = tspace; 98 zap(); /* Get terminal description. */ 99 100 /* Handle funny termcap capabilities. */ 101 if (CS && SC && RC) 102 AL = DL = ""; 103 if (AL_PARM && AL == NULL) 104 AL = ""; 105 if (DL_PARM && DL == NULL) 106 DL = ""; 107 if (IC) { 108 if (IM == NULL) 109 IM = ""; 110 if (EI == NULL) 111 EI = ""; 112 } 113 if (!GT) /* If we can't tab, we can't backtab either. */ 114 BT = NULL; 115 116 if (tgoto(CM, destcol, destline)[0] == 'O') { 117 CA = 0; 118 CM = 0; 119 } else 120 CA = 1; 121 122 PC = _PC ? _PC[0] : 0; 123 aoftspace = tspace; 124 ttytype = longname(genbuf, __ttytype); 125 126 if ((!AL && !al) || (!DL && !dl)) 127 __noqch = 1; 128 129 return (unknown ? ERR : OK); 130 } 131 132 /* 133 * zap -- 134 * Gets all the terminal flags from the termcap database. 135 */ 136 static void 137 zap() 138 { 139 register char *namp, ***sp; 140 register char **fp; 141 char tmp[3]; 142 #ifdef DEBUG 143 register char *cp; 144 #endif 145 tmp[2] = '\0'; 146 147 namp = "ambsdadbeohchzinmimsncnsosulxbxnxtxsxx"; 148 fp = sflags; 149 do { 150 *tmp = *namp; 151 *(tmp + 1) = *(namp + 1); 152 *(*fp++) = tgetflag(tmp); 153 #ifdef DEBUG 154 __TRACE("2.2s = %s\n", namp, *fp[-1] ? "TRUE" : "FALSE"); 155 #endif 156 namp += 2; 157 158 } while (*namp); 159 namp = "ALbcbtcdceclcmcrcsdcDLdmdoedeik0k1k2k3k4k5k6k7k8k9hoicimipkdkekhklkrkskullmandnlpcrcscseSFsoSRtatetiucueupusvbvsvealdlsfsrALDLUPDOLERI"; 160 sp = sstrs; 161 do { 162 *tmp = *namp; 163 *(tmp + 1) = *(namp + 1); 164 *(*sp++) = tgetstr(tmp, &aoftspace); 165 #ifdef DEBUG 166 __TRACE("2.2s = %s", namp, *sp[-1] == NULL ? "NULL\n" : "\""); 167 if (*sp[-1] != NULL) { 168 for (cp = *sp[-1]; *cp; cp++) 169 __TRACE("%s", unctrl(*cp)); 170 __TRACE("\"\n"); 171 } 172 #endif 173 namp += 2; 174 } while (*namp); 175 if (XS) 176 SO = SE = NULL; 177 else { 178 if (tgetnum("sg") > 0) 179 SO = NULL; 180 if (tgetnum("ug") > 0) 181 US = NULL; 182 if (!SO && US) { 183 SO = US; 184 SE = UE; 185 } 186 } 187 } 188 189 /* 190 * getcap -- 191 * Return a capability from termcap. 192 */ 193 char * 194 getcap(name) 195 char *name; 196 { 197 return (tgetstr(name, &aoftspace)); 198 } 199