1 /* 2 * Copyright (c) 1983, 1993 3 * The Regents of the University of California. All rights reserved. 4 * 5 * This code is derived from software contributed to Berkeley by 6 * Edward Wang at The University of California, Berkeley. 7 * 8 * %sccs.include.redist.c% 9 */ 10 11 #ifndef lint 12 static char sccsid[] = "@(#)lcmd1.c 8.1 (Berkeley) 06/06/93"; 13 #endif /* not lint */ 14 15 #include "defs.h" 16 #include "string.h" 17 #include "value.h" 18 #include "lcmd.h" 19 #include "var.h" 20 21 struct lcmd_arg arg_window[] = { 22 { "row", 1, ARG_NUM }, 23 { "column", 1, ARG_NUM }, 24 { "nrows", 2, ARG_NUM }, 25 { "ncols", 2, ARG_NUM }, 26 { "nlines", 2, ARG_NUM }, 27 { "label", 1, ARG_STR }, 28 { "pty", 1, ARG_ANY }, 29 { "frame", 1, ARG_ANY }, 30 { "mapnl", 1, ARG_ANY }, 31 { "keepopen", 1, ARG_ANY }, 32 { "smooth", 1, ARG_ANY }, 33 { "shell", 1, ARG_STR|ARG_LIST }, 34 0 35 }; 36 37 l_window(v, a) 38 struct value *v; 39 register struct value *a; 40 { 41 struct ww *w; 42 int col, row, ncol, nrow, id, nline; 43 char *label; 44 char haspty, hasframe, mapnl, keepopen, smooth; 45 char *shf, **sh; 46 char *argv[sizeof default_shell / sizeof *default_shell]; 47 register char **pp; 48 49 if ((id = findid()) < 0) 50 return; 51 row = a->v_type == V_ERR ? 1 : a->v_num; 52 a++; 53 col = a->v_type == V_ERR ? 0 : a->v_num; 54 a++; 55 nrow = a->v_type == V_ERR ? wwnrow - row : a->v_num; 56 a++; 57 ncol = a->v_type == V_ERR ? wwncol - col : a->v_num; 58 a++; 59 nline = a->v_type == V_ERR ? default_nline : a->v_num; 60 a++; 61 label = a->v_type == V_ERR ? 0 : a->v_str; 62 if ((haspty = vtobool(++a, 1, -1)) < 0) 63 return; 64 if ((hasframe = vtobool(++a, 1, -1)) < 0) 65 return; 66 if ((mapnl = vtobool(++a, !haspty, -1)) < 0) 67 return; 68 if ((keepopen = vtobool(++a, 0, -1)) < 0) 69 return; 70 if ((smooth = vtobool(++a, default_smooth, -1)) < 0) 71 return; 72 if ((++a)->v_type != V_ERR) { 73 for (pp = argv; a->v_type != V_ERR && 74 pp < &argv[sizeof argv/sizeof *argv-1]; pp++, a++) 75 *pp = a->v_str; 76 *pp = 0; 77 shf = *(sh = argv); 78 if (*sh = rindex(shf, '/')) 79 (*sh)++; 80 else 81 *sh = shf; 82 } else { 83 sh = default_shell; 84 shf = default_shellfile; 85 } 86 if ((w = openwin(id, row, col, nrow, ncol, nline, label, haspty, 87 hasframe, shf, sh)) == 0) 88 return; 89 w->ww_mapnl = mapnl; 90 w->ww_keepopen = keepopen; 91 w->ww_noupdate = !smooth; 92 v->v_type = V_NUM; 93 v->v_num = id + 1; 94 } 95 96 struct lcmd_arg arg_def_nline[] = { 97 { "nlines", 1, ARG_NUM }, 98 0 99 }; 100 101 l_def_nline(v, a) 102 register struct value *v, *a; 103 { 104 v->v_num = default_nline; 105 v->v_type = V_NUM; 106 if (a->v_type != V_ERR) 107 default_nline = a->v_num; 108 } 109 110 struct lcmd_arg arg_smooth[] = { 111 { "window", 1, ARG_NUM }, 112 { "flag", 1, ARG_ANY }, 113 0 114 }; 115 116 l_smooth(v, a) 117 register struct value *v, *a; 118 { 119 struct ww *w; 120 121 v->v_type = V_NUM; 122 v->v_num = 0; 123 if ((w = vtowin(a++, selwin)) == 0) 124 return; 125 v->v_num = !w->ww_noupdate; 126 w->ww_noupdate = !vtobool(a, v->v_num, v->v_num); 127 } 128 129 struct lcmd_arg arg_def_smooth[] = { 130 { "flag", 1, ARG_ANY }, 131 0 132 }; 133 134 l_def_smooth(v, a) 135 register struct value *v, *a; 136 { 137 v->v_type = V_NUM; 138 v->v_num = default_smooth; 139 default_smooth = vtobool(a, v->v_num, v->v_num); 140 } 141 142 struct lcmd_arg arg_select[] = { 143 { "window", 1, ARG_NUM }, 144 0 145 }; 146 147 l_select(v, a) 148 register struct value *v, *a; 149 { 150 struct ww *w; 151 152 v->v_type = V_NUM; 153 v->v_num = selwin ? selwin->ww_id + 1 : -1; 154 if (a->v_type == V_ERR) 155 return; 156 if ((w = vtowin(a, (struct ww *)0)) == 0) 157 return; 158 setselwin(w); 159 } 160 161 struct lcmd_arg arg_debug[] = { 162 { "flag", 1, ARG_ANY }, 163 0 164 }; 165 166 l_debug(v, a) 167 register struct value *v, *a; 168 { 169 v->v_type = V_NUM; 170 v->v_num = debug; 171 debug = vtobool(a, debug, debug); 172 } 173 174 struct lcmd_arg arg_escape[] = { 175 { "escapec", 1, ARG_STR }, 176 0 177 }; 178 179 l_escape(v, a) 180 register struct value *v, *a; 181 { 182 char buf[2]; 183 184 buf[0] = escapec; 185 buf[1] = 0; 186 if ((v->v_str = str_cpy(buf)) == 0) { 187 error("Out of memory."); 188 return; 189 } 190 v->v_type = V_STR; 191 if (a->v_type != V_ERR) 192 setescape(a->v_str); 193 } 194 195 struct lcmd_arg arg_label[] = { 196 { "window", 1, ARG_NUM }, 197 { "label", 1, ARG_STR }, 198 0 199 }; 200 201 /*ARGSUSED*/ 202 l_label(v, a) 203 struct value *v; 204 register struct value *a; 205 { 206 struct ww *w; 207 208 if ((w = vtowin(a, selwin)) == 0) 209 return; 210 if ((++a)->v_type != V_ERR && setlabel(w, a->v_str) < 0) 211 error("Out of memory."); 212 reframe(); 213 } 214 215 struct lcmd_arg arg_foreground[] = { 216 { "window", 1, ARG_NUM }, 217 { "flag", 1, ARG_ANY }, 218 0 219 }; 220 221 l_foreground(v, a) 222 register struct value *v, *a; 223 { 224 struct ww *w; 225 char flag; 226 227 if ((w = vtowin(a, selwin)) == 0) 228 return; 229 v->v_type = V_NUM; 230 v->v_num = isfg(w); 231 flag = vtobool(++a, v->v_num, v->v_num); 232 if (flag == v->v_num) 233 return; 234 deletewin(w); 235 addwin(w, flag); 236 reframe(); 237 } 238 239 struct lcmd_arg arg_terse[] = { 240 { "flag", 1, ARG_ANY }, 241 0 242 }; 243 244 l_terse(v, a) 245 register struct value *v, *a; 246 { 247 v->v_type = V_NUM; 248 v->v_num = terse; 249 setterse(vtobool(a, terse, terse)); 250 } 251 252 struct lcmd_arg arg_source[] = { 253 { "filename", 1, ARG_STR }, 254 0 255 }; 256 257 l_source(v, a) 258 register struct value *v, *a; 259 { 260 v->v_type = V_NUM; 261 if (a->v_type != V_ERR && dosource(a->v_str) < 0) { 262 error("Can't open %s.", a->v_str); 263 v->v_num = -1; 264 } else 265 v->v_num = 0; 266 } 267 268 struct lcmd_arg arg_write[] = { 269 { "window", 1, ARG_NUM }, 270 { "", 0, ARG_ANY|ARG_LIST }, 271 0 272 }; 273 274 /*ARGSUSED*/ 275 l_write(v, a) 276 struct value *v; 277 register struct value *a; 278 { 279 char buf[20]; 280 struct ww *w; 281 282 if ((w = vtowin(a++, selwin)) == 0) 283 return; 284 while (a->v_type != V_ERR) { 285 if (a->v_type == V_NUM) { 286 (void) sprintf(buf, "%d", a->v_num); 287 (void) write(w->ww_pty, buf, strlen(buf)); 288 } else 289 (void) write(w->ww_pty, a->v_str, strlen(a->v_str)); 290 if ((++a)->v_type != V_ERR) 291 (void) write(w->ww_pty, " ", 1); 292 } 293 } 294 295 struct lcmd_arg arg_close[] = { 296 { "window", 1, ARG_ANY|ARG_LIST }, 297 0 298 }; 299 300 /*ARGSUSED*/ 301 l_close(v, a) 302 struct value *v; 303 register struct value *a; 304 { 305 struct ww *w; 306 307 if (a->v_type == V_STR && str_match(a->v_str, "all", 3)) 308 closewin((struct ww *)0); 309 else 310 for (; a->v_type != V_ERR; a++) 311 if ((w = vtowin(a, (struct ww *)0)) != 0) 312 closewin(w); 313 } 314 315 struct lcmd_arg arg_cursormodes[] = { 316 { "modes", 1, ARG_NUM }, 317 0 318 }; 319 320 l_cursormodes(v, a) 321 register struct value *v, *a; 322 { 323 324 v->v_type = V_NUM; 325 v->v_num = wwcursormodes; 326 if (a->v_type != V_ERR) 327 wwsetcursormodes(a->v_num); 328 } 329 330 struct lcmd_arg arg_unset[] = { 331 { "variable", 1, ARG_ANY }, 332 0 333 }; 334 335 l_unset(v, a) 336 register struct value *v, *a; 337 { 338 v->v_type = V_NUM; 339 switch (a->v_type) { 340 case V_ERR: 341 v->v_num = -1; 342 return; 343 case V_NUM: 344 if ((a->v_str = str_itoa(a->v_num)) == 0) { 345 error("Out of memory."); 346 v->v_num = -1; 347 return; 348 } 349 a->v_type = V_STR; 350 break; 351 } 352 v->v_num = var_unset(a->v_str); 353 } 354 355 struct ww * 356 vtowin(v, w) 357 register struct value *v; 358 struct ww *w; 359 { 360 switch (v->v_type) { 361 case V_ERR: 362 if (w != 0) 363 return w; 364 error("No window specified."); 365 return 0; 366 case V_STR: 367 error("%s: No such window.", v->v_str); 368 return 0; 369 } 370 if (v->v_num < 1 || v->v_num > NWINDOW 371 || (w = window[v->v_num - 1]) == 0) { 372 error("%d: No such window.", v->v_num); 373 return 0; 374 } 375 return w; 376 } 377 378 vtobool(v, def, err) 379 register struct value *v; 380 char def, err; 381 { 382 switch (v->v_type) { 383 case V_NUM: 384 return v->v_num != 0; 385 case V_STR: 386 if (str_match(v->v_str, "true", 1) 387 || str_match(v->v_str, "on", 2) 388 || str_match(v->v_str, "yes", 1)) 389 return 1; 390 else if (str_match(v->v_str, "false", 1) 391 || str_match(v->v_str, "off", 2) 392 || str_match(v->v_str, "no", 1)) 393 return 0; 394 else { 395 error("%s: Illegal boolean value.", v->v_str); 396 return err; 397 } 398 /*NOTREACHED*/ 399 case V_ERR: 400 return def; 401 } 402 /*NOTREACHED*/ 403 } 404