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[] = "@(#)lcmd2.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 "var.h"
19 #include "lcmd.h"
20 #include "alias.h"
21 #include <sys/types.h>
22 #include <sys/resource.h>
23
24 /*ARGSUSED*/
25 l_iostat(v, a)
26 struct value *v, *a;
27 {
28 register struct ww *w;
29
30 if ((w = openiwin(16, "IO Statistics")) == 0) {
31 error("Can't open statistics window: %s.", wwerror());
32 return;
33 }
34 wwprintf(w, "ttflush\twrite\terror\tzero\tchar\n");
35 wwprintf(w, "%d\t%d\t%d\t%d\t%d\n",
36 wwnflush, wwnwr, wwnwre, wwnwrz, wwnwrc);
37 wwprintf(w, "token\tuse\tbad\tsaving\ttotal\tbaud\n");
38 wwprintf(w, "%d\t%d\t%d\t%d\t%d\t%d/%d (%.1f/%.1f)\n",
39 wwntokdef, wwntokuse, wwntokbad, wwntoksave, wwntokc,
40 wwntokc - wwntoksave ?
41 (int) ((float) wwbaud * wwntokc /
42 (wwntokc - wwntoksave)) :
43 wwbaud,
44 wwnwrc ? (int) ((float) wwbaud * (wwnwrc + wwntoksave) /
45 wwnwrc) :
46 wwbaud,
47 wwntokc - wwntoksave ?
48 (float) wwntokc / (wwntokc - wwntoksave) : 1.0,
49 wwnwrc ? (float) (wwnwrc + wwntoksave) / wwnwrc : 1.0);
50 wwprintf(w, "wwwrite\tattempt\tchar\n");
51 wwprintf(w, "%d\t%d\t%d\n",
52 wwnwwr, wwnwwra, wwnwwrc);
53 wwprintf(w, "wwupdat\tline\tmiss\tscan\tclreol\tclreos\tmiss\tline\n");
54 wwprintf(w, "%d\t%d\t%d\t%d\t%d\t%d\t%d\t%d\n",
55 wwnupdate, wwnupdline, wwnupdmiss, wwnupdscan, wwnupdclreol,
56 wwnupdclreos, wwnupdclreosmiss, wwnupdclreosline);
57 wwprintf(w, "select\terror\tzero\n");
58 wwprintf(w, "%d\t%d\t%d\n",
59 wwnselect, wwnselecte, wwnselectz);
60 wwprintf(w, "read\terror\tzero\tchar\tack\tnack\tstat\terrorc\n");
61 wwprintf(w, "%d\t%d\t%d\t%d\t%d\t%d\t%d\t%d\n",
62 wwnread, wwnreade, wwnreadz, wwnreadc, wwnreadack, wwnreadnack,
63 wwnreadstat, wwnreadec);
64 wwprintf(w, "ptyread\terror\tzero\tcontrol\tdata\tchar\n");
65 wwprintf(w, "%d\t%d\t%d\t%d\t%d\t%d\n",
66 wwnwread, wwnwreade, wwnwreadz,
67 wwnwreadp, wwnwreadd, wwnwreadc);
68 waitnl(w);
69 closeiwin(w);
70 }
71
72 struct lcmd_arg arg_time[] = {
73 { "who", 1, ARG_STR },
74 0
75 };
76
77 /*ARGSUSED*/
78 l_time(v, a)
79 struct value *v;
80 register struct value *a;
81 {
82 register struct ww *w;
83 struct rusage rusage;
84 struct timeval timeval;
85 char *strtime();
86
87 if ((w = openiwin(8, "Timing and Resource Usage")) == 0) {
88 error("Can't open time window: %s.", wwerror());
89 return;
90 }
91
92 (void) gettimeofday(&timeval, (struct timezone *)0);
93 timeval.tv_sec -= starttime.tv_sec;
94 if ((timeval.tv_usec -= starttime.tv_usec) < 0) {
95 timeval.tv_sec--;
96 timeval.tv_usec += 1000000;
97 }
98 (void) getrusage(a->v_type == V_STR
99 && str_match(a->v_str, "children", 1)
100 ? RUSAGE_CHILDREN : RUSAGE_SELF, &rusage);
101
102 wwprintf(w, "%-15s %-15s %-15s\n",
103 "time", "utime", "stime");
104 wwprintf(w, "%-15s ", strtime(&timeval));
105 wwprintf(w, "%-15s ", strtime(&rusage.ru_utime));
106 wwprintf(w, "%-15s\n", strtime(&rusage.ru_stime));
107 wwprintf(w, "%-15s %-15s %-15s %-15s\n",
108 "maxrss", "ixrss", "idrss", "isrss");
109 wwprintf(w, "%-15ld %-15ld %-15ld %-15ld\n",
110 rusage.ru_maxrss, rusage.ru_ixrss,
111 rusage.ru_idrss, rusage.ru_isrss);
112 wwprintf(w, "%-7s %-7s %-7s %-7s %-7s %-7s %-7s %-7s %-7s %-7s\n",
113 "minflt", "majflt", "nswap", "inblk", "oublk",
114 "msgsnd", "msgrcv", "nsigs", "nvcsw", "nivcsw");
115 wwprintf(w, "%-7ld %-7ld %-7ld %-7ld %-7ld %-7ld %-7ld %-7ld %-7ld %-7ld\n",
116 rusage.ru_minflt, rusage.ru_majflt, rusage.ru_nswap,
117 rusage.ru_inblock, rusage.ru_oublock,
118 rusage.ru_msgsnd, rusage.ru_msgrcv, rusage.ru_nsignals,
119 rusage.ru_nvcsw, rusage.ru_nivcsw);
120
121 waitnl(w);
122 closeiwin(w);
123 }
124
125 char *
strtime(t)126 strtime(t)
127 register struct timeval *t;
128 {
129 char fill = 0;
130 static char buf[20];
131 register char *p = buf;
132
133 if (t->tv_sec > 60*60) {
134 (void) sprintf(p, "%ld:", t->tv_sec / (60*60));
135 while (*p++)
136 ;
137 p--;
138 t->tv_sec %= 60*60;
139 fill++;
140 }
141 if (t->tv_sec > 60) {
142 (void) sprintf(p, fill ? "%02ld:" : "%ld:", t->tv_sec / 60);
143 while (*p++)
144 ;
145 p--;
146 t->tv_sec %= 60;
147 fill++;
148 }
149 (void) sprintf(p, fill ? "%02ld.%02d" : "%ld.%02ld",
150 t->tv_sec, t->tv_usec / 10000);
151 return buf;
152 }
153
154 /*ARGSUSED*/
155 l_list(v, a)
156 struct value *v, *a;
157 {
158 register struct ww *w, *wp;
159 register i;
160 int n;
161
162 for (n = 0, i = 0; i < NWINDOW; i++)
163 if (window[i] != 0)
164 n++;
165 if (n == 0) {
166 error("No windows.");
167 return;
168 }
169 if ((w = openiwin(n + 2, "Windows")) == 0) {
170 error("Can't open listing window: %s.", wwerror());
171 return;
172 }
173 for (i = 0; i < NWINDOW; i++) {
174 if ((wp = window[i]) == 0)
175 continue;
176 wwprintf(w, "%c %c %-13s %-.*s\n",
177 wp == selwin ? '+' : (wp == lastselwin ? '-' : ' '),
178 i + '1',
179 wp->ww_state == WWS_HASPROC ? "" : "(No process)",
180 wwncol - 20,
181 wp->ww_label ? wp->ww_label : "(No label)");
182 }
183 waitnl(w);
184 closeiwin(w);
185 }
186
187 /*ARGSUSED*/
188 l_variable(v, a)
189 struct value *v, *a;
190 {
191 register struct ww *w;
192 int printvar();
193
194 if ((w = openiwin(wwnrow - 3, "Variables")) == 0) {
195 error("Can't open variable window: %s.", wwerror());
196 return;
197 }
198 if (var_walk(printvar, (int)w) >= 0)
199 waitnl(w);
200 closeiwin(w);
201 }
202
printvar(w,r)203 printvar(w, r)
204 register struct ww *w;
205 register struct var *r;
206 {
207 if (more(w, 0) == 2)
208 return -1;
209 wwprintf(w, "%16s ", r->r_name);
210 switch (r->r_val.v_type) {
211 case V_STR:
212 wwprintf(w, "%s\n", r->r_val.v_str);
213 break;
214 case V_NUM:
215 wwprintf(w, "%d\n", r->r_val.v_num);
216 break;
217 case V_ERR:
218 wwprintf(w, "ERROR\n");
219 break;
220 }
221 return 0;
222 }
223
224 struct lcmd_arg arg_def_shell[] = {
225 { "", 0, ARG_ANY|ARG_LIST },
226 0
227 };
228
229 l_def_shell(v, a)
230 struct value *v, *a;
231 {
232 register char **pp;
233 register struct value *vp;
234
235 if (a->v_type == V_ERR) {
236 if ((v->v_str = str_cpy(default_shellfile)) != 0)
237 v->v_type = V_STR;
238 return;
239 }
240 if (v->v_str = default_shellfile) {
241 v->v_type = V_STR;
242 for (pp = default_shell + 1; *pp; pp++) {
243 str_free(*pp);
244 *pp = 0;
245 }
246 }
247 for (pp = default_shell, vp = a;
248 vp->v_type != V_ERR &&
249 pp < &default_shell[sizeof default_shell/sizeof *default_shell-1];
250 pp++, vp++)
251 if ((*pp = vp->v_type == V_STR ?
252 str_cpy(vp->v_str) : str_itoa(vp->v_num)) == 0) {
253 /* just leave default_shell[] the way it is */
254 p_memerror();
255 break;
256 }
257 if (default_shellfile = *default_shell)
258 if (*default_shell = rindex(default_shellfile, '/'))
259 (*default_shell)++;
260 else
261 *default_shell = default_shellfile;
262 }
263
264 struct lcmd_arg arg_alias[] = {
265 { "", 0, ARG_STR },
266 { "", 0, ARG_STR|ARG_LIST },
267 0
268 };
269
270 l_alias(v, a)
271 struct value *v, *a;
272 {
273 if (a->v_type == V_ERR) {
274 register struct ww *w;
275 int printalias();
276
277 if ((w = openiwin(wwnrow - 3, "Aliases")) == 0) {
278 error("Can't open alias window: %s.", wwerror());
279 return;
280 }
281 if (alias_walk(printalias, (int)w) >= 0)
282 waitnl(w);
283 closeiwin(w);
284 } else {
285 register struct alias *ap = 0;
286
287 if (ap = alias_lookup(a->v_str)) {
288 if ((v->v_str = str_cpy(ap->a_buf)) == 0) {
289 p_memerror();
290 return;
291 }
292 v->v_type = V_STR;
293 }
294 if (a[1].v_type == V_STR) {
295 register struct value *vp;
296 register char *p, *q;
297 char *str;
298 register n;
299
300 for (n = 0, vp = a + 1; vp->v_type != V_ERR; vp++, n++)
301 for (p = vp->v_str; *p; p++, n++)
302 ;
303 if ((str = str_alloc(n)) == 0) {
304 p_memerror();
305 return;
306 }
307 for (q = str, vp = a + 1; vp->v_type != V_ERR;
308 vp++, q[-1] = ' ')
309 for (p = vp->v_str; *q++ = *p++;)
310 ;
311 q[-1] = 0;
312 if ((ap = alias_set(a[0].v_str, (char *)0)) == 0) {
313 p_memerror();
314 str_free(str);
315 return;
316 }
317 ap->a_buf = str;
318 }
319 }
320 }
321
printalias(w,a)322 printalias(w, a)
323 register struct ww *w;
324 register struct alias *a;
325 {
326 if (more(w, 0) == 2)
327 return -1;
328 wwprintf(w, "%16s %s\n", a->a_name, a->a_buf);
329 return 0;
330 }
331
332 struct lcmd_arg arg_unalias[] = {
333 { "alias", 1, ARG_STR },
334 0
335 };
336
337 l_unalias(v, a)
338 struct value *v, *a;
339 {
340 if (a->v_type == ARG_STR)
341 v->v_num = alias_unset(a->v_str);
342 v->v_type = V_NUM;
343 }
344
345 struct lcmd_arg arg_echo[] = {
346 { "window", 1, ARG_NUM },
347 { "", 0, ARG_ANY|ARG_LIST },
348 0
349 };
350
351 /*ARGSUSED*/
352 l_echo(v, a)
353 struct value *v;
354 register struct value *a;
355 {
356 char buf[20];
357 struct ww *w;
358
359 if ((w = vtowin(a++, selwin)) == 0)
360 return;
361 while (a->v_type != V_ERR) {
362 if (a->v_type == V_NUM) {
363 (void) sprintf(buf, "%d", a->v_num);
364 (void) wwwrite(w, buf, strlen(buf));
365 } else
366 (void) wwwrite(w, a->v_str, strlen(a->v_str));
367 if ((++a)->v_type != V_ERR)
368 (void) wwwrite(w, " ", 1);
369 }
370 (void) wwwrite(w, "\r\n", 2);
371 }
372