1 | /* $Header: /afs/dev.mit.edu/source/repository/third/tcsh/sh.time.c,v 1.1.1.2 1998-10-03 21:10:08 danw Exp $ */ |
---|
2 | /* |
---|
3 | * sh.time.c: Shell time keeping and printing. |
---|
4 | */ |
---|
5 | /*- |
---|
6 | * Copyright (c) 1980, 1991 The Regents of the University of California. |
---|
7 | * All rights reserved. |
---|
8 | * |
---|
9 | * Redistribution and use in source and binary forms, with or without |
---|
10 | * modification, are permitted provided that the following conditions |
---|
11 | * are met: |
---|
12 | * 1. Redistributions of source code must retain the above copyright |
---|
13 | * notice, this list of conditions and the following disclaimer. |
---|
14 | * 2. Redistributions in binary form must reproduce the above copyright |
---|
15 | * notice, this list of conditions and the following disclaimer in the |
---|
16 | * documentation and/or other materials provided with the distribution. |
---|
17 | * 3. All advertising materials mentioning features or use of this software |
---|
18 | * must display the following acknowledgement: |
---|
19 | * This product includes software developed by the University of |
---|
20 | * California, Berkeley and its contributors. |
---|
21 | * 4. Neither the name of the University nor the names of its contributors |
---|
22 | * may be used to endorse or promote products derived from this software |
---|
23 | * without specific prior written permission. |
---|
24 | * |
---|
25 | * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND |
---|
26 | * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE |
---|
27 | * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE |
---|
28 | * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE |
---|
29 | * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL |
---|
30 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS |
---|
31 | * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) |
---|
32 | * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT |
---|
33 | * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY |
---|
34 | * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF |
---|
35 | * SUCH DAMAGE. |
---|
36 | */ |
---|
37 | #include "sh.h" |
---|
38 | |
---|
39 | RCSID("$Id: sh.time.c,v 1.1.1.2 1998-10-03 21:10:08 danw Exp $") |
---|
40 | |
---|
41 | #ifdef SUNOS4 |
---|
42 | # include <machine/param.h> |
---|
43 | #endif /* SUNOS4 */ |
---|
44 | |
---|
45 | /* |
---|
46 | * C Shell - routines handling process timing and niceing |
---|
47 | */ |
---|
48 | #ifdef BSDTIMES |
---|
49 | # ifndef RUSAGE_SELF |
---|
50 | # define RUSAGE_SELF 0 |
---|
51 | # define RUSAGE_CHILDREN -1 |
---|
52 | # endif /* RUSAGE_SELF */ |
---|
53 | #else /* BSDTIMES */ |
---|
54 | struct tms times0; |
---|
55 | #endif /* BSDTIMES */ |
---|
56 | |
---|
57 | #if !defined(BSDTIMES) && !defined(_SEQUENT_) |
---|
58 | # ifdef POSIX |
---|
59 | static void pdtimet __P((clock_t, clock_t)); |
---|
60 | # else /* ! POSIX */ |
---|
61 | static void pdtimet __P((time_t, time_t)); |
---|
62 | # endif /* ! POSIX */ |
---|
63 | #else /* BSDTIMES || _SEQUENT_ */ |
---|
64 | static void tvadd __P((timeval_t *, timeval_t *)); |
---|
65 | static void pdeltat __P((timeval_t *, timeval_t *)); |
---|
66 | #endif /* BSDTIMES || _SEQUENT_ */ |
---|
67 | |
---|
68 | void |
---|
69 | settimes() |
---|
70 | { |
---|
71 | #ifdef BSDTIMES |
---|
72 | struct sysrusage ruch; |
---|
73 | #ifdef convex |
---|
74 | memset(ru0, 0, sizeof(ru0)); |
---|
75 | memset(ruch, 0, sizeof(ruch)); |
---|
76 | #endif /* convex */ |
---|
77 | |
---|
78 | (void) gettimeofday(&time0, NULL); |
---|
79 | (void) getrusage(RUSAGE_SELF, (struct rusage *) &ru0); |
---|
80 | (void) getrusage(RUSAGE_CHILDREN, (struct rusage *) &ruch); |
---|
81 | ruadd(&ru0, &ruch); |
---|
82 | #else |
---|
83 | # ifdef _SEQUENT_ |
---|
84 | struct process_stats ruch; |
---|
85 | |
---|
86 | (void) get_process_stats(&time0, PS_SELF, &ru0, &ruch); |
---|
87 | ruadd(&ru0, &ruch); |
---|
88 | # else /* _SEQUENT_ */ |
---|
89 | # ifndef COHERENT |
---|
90 | time0 = times(×0); |
---|
91 | # else /* !COHERENT */ |
---|
92 | time0 = HZ * time(NULL); |
---|
93 | times(×0); |
---|
94 | # endif /* !COHERENT */ |
---|
95 | times0.tms_stime += times0.tms_cstime; |
---|
96 | times0.tms_utime += times0.tms_cutime; |
---|
97 | times0.tms_cstime = 0; |
---|
98 | times0.tms_cutime = 0; |
---|
99 | # endif /* _SEQUENT_ */ |
---|
100 | #endif /* BSDTIMES */ |
---|
101 | } |
---|
102 | |
---|
103 | /* |
---|
104 | * dotime is only called if it is truly a builtin function and not a |
---|
105 | * prefix to another command |
---|
106 | */ |
---|
107 | /*ARGSUSED*/ |
---|
108 | void |
---|
109 | dotime(v, c) |
---|
110 | Char **v; |
---|
111 | struct command *c; |
---|
112 | { |
---|
113 | #ifdef BSDTIMES |
---|
114 | timeval_t timedol; |
---|
115 | struct sysrusage ru1, ruch; |
---|
116 | #ifdef convex |
---|
117 | memset(ru1, 0, sizeof(ru1)); |
---|
118 | memset(ruch, 0, sizeof(ruch)); |
---|
119 | #endif /* convex */ |
---|
120 | |
---|
121 | (void) getrusage(RUSAGE_SELF, (struct rusage *) &ru1); |
---|
122 | (void) getrusage(RUSAGE_CHILDREN, (struct rusage *) &ruch); |
---|
123 | ruadd(&ru1, &ruch); |
---|
124 | (void) gettimeofday(&timedol, NULL); |
---|
125 | prusage(&ru0, &ru1, &timedol, &time0); |
---|
126 | #else |
---|
127 | # ifdef _SEQUENT_ |
---|
128 | timeval_t timedol; |
---|
129 | struct process_stats ru1, ruch; |
---|
130 | |
---|
131 | (void) get_process_stats(&timedol, PS_SELF, &ru1, &ruch); |
---|
132 | ruadd(&ru1, &ruch); |
---|
133 | prusage(&ru0, &ru1, &timedol, &time0); |
---|
134 | # else /* _SEQUENT_ */ |
---|
135 | # ifndef POSIX |
---|
136 | time_t timedol; |
---|
137 | # else /* POSIX */ |
---|
138 | clock_t timedol; |
---|
139 | # endif /* POSIX */ |
---|
140 | |
---|
141 | struct tms times_dol; |
---|
142 | |
---|
143 | #ifndef COHERENT |
---|
144 | timedol = times(×_dol); |
---|
145 | #else |
---|
146 | timedol = HZ * time(NULL); |
---|
147 | times(×_dol); |
---|
148 | #endif |
---|
149 | times_dol.tms_stime += times_dol.tms_cstime; |
---|
150 | times_dol.tms_utime += times_dol.tms_cutime; |
---|
151 | times_dol.tms_cstime = 0; |
---|
152 | times_dol.tms_cutime = 0; |
---|
153 | prusage(×0, ×_dol, timedol, time0); |
---|
154 | # endif /* _SEQUENT_ */ |
---|
155 | #endif /* BSDTIMES */ |
---|
156 | USE(c); |
---|
157 | USE(v); |
---|
158 | } |
---|
159 | |
---|
160 | /* |
---|
161 | * donice is only called when it on the line by itself or with a +- value |
---|
162 | */ |
---|
163 | /*ARGSUSED*/ |
---|
164 | void |
---|
165 | donice(v, c) |
---|
166 | register Char **v; |
---|
167 | struct command *c; |
---|
168 | { |
---|
169 | register Char *cp; |
---|
170 | int nval = 0; |
---|
171 | |
---|
172 | USE(c); |
---|
173 | v++, cp = *v++; |
---|
174 | if (cp == 0) |
---|
175 | nval = 4; |
---|
176 | else if (*v == 0 && any("+-", cp[0])) |
---|
177 | nval = getn(cp); |
---|
178 | #ifdef BSDNICE |
---|
179 | (void) setpriority(PRIO_PROCESS, 0, nval); |
---|
180 | #else /* BSDNICE */ |
---|
181 | (void) nice(nval); |
---|
182 | #endif /* BSDNICE */ |
---|
183 | } |
---|
184 | |
---|
185 | #ifdef BSDTIMES |
---|
186 | void |
---|
187 | ruadd(ru, ru2) |
---|
188 | register struct sysrusage *ru, *ru2; |
---|
189 | { |
---|
190 | tvadd(&ru->ru_utime, &ru2->ru_utime); |
---|
191 | tvadd(&ru->ru_stime, &ru2->ru_stime); |
---|
192 | if (ru2->ru_maxrss > ru->ru_maxrss) |
---|
193 | ru->ru_maxrss = ru2->ru_maxrss; |
---|
194 | |
---|
195 | ru->ru_ixrss += ru2->ru_ixrss; |
---|
196 | ru->ru_idrss += ru2->ru_idrss; |
---|
197 | ru->ru_isrss += ru2->ru_isrss; |
---|
198 | ru->ru_minflt += ru2->ru_minflt; |
---|
199 | ru->ru_majflt += ru2->ru_majflt; |
---|
200 | ru->ru_nswap += ru2->ru_nswap; |
---|
201 | ru->ru_inblock += ru2->ru_inblock; |
---|
202 | ru->ru_oublock += ru2->ru_oublock; |
---|
203 | ru->ru_msgsnd += ru2->ru_msgsnd; |
---|
204 | ru->ru_msgrcv += ru2->ru_msgrcv; |
---|
205 | ru->ru_nsignals += ru2->ru_nsignals; |
---|
206 | ru->ru_nvcsw += ru2->ru_nvcsw; |
---|
207 | ru->ru_nivcsw += ru2->ru_nivcsw; |
---|
208 | |
---|
209 | # ifdef convex |
---|
210 | tvadd(&ru->ru_exutime, &ru2->ru_exutime); |
---|
211 | ru->ru_utotal += ru2->ru_utotal; |
---|
212 | ru->ru_usamples += ru2->ru_usamples; |
---|
213 | ru->ru_stotal += ru2->ru_stotal; |
---|
214 | ru->ru_ssamples += ru2->ru_ssamples; |
---|
215 | # endif /* convex */ |
---|
216 | } |
---|
217 | |
---|
218 | #else /* BSDTIMES */ |
---|
219 | # ifdef _SEQUENT_ |
---|
220 | void |
---|
221 | ruadd(ru, ru2) |
---|
222 | register struct process_stats *ru, *ru2; |
---|
223 | { |
---|
224 | tvadd(&ru->ps_utime, &ru2->ps_utime); |
---|
225 | tvadd(&ru->ps_stime, &ru2->ps_stime); |
---|
226 | if (ru2->ps_maxrss > ru->ps_maxrss) |
---|
227 | ru->ps_maxrss = ru2->ps_maxrss; |
---|
228 | |
---|
229 | ru->ps_pagein += ru2->ps_pagein; |
---|
230 | ru->ps_reclaim += ru2->ps_reclaim; |
---|
231 | ru->ps_zerofill += ru2->ps_zerofill; |
---|
232 | ru->ps_pffincr += ru2->ps_pffincr; |
---|
233 | ru->ps_pffdecr += ru2->ps_pffdecr; |
---|
234 | ru->ps_swap += ru2->ps_swap; |
---|
235 | ru->ps_syscall += ru2->ps_syscall; |
---|
236 | ru->ps_volcsw += ru2->ps_volcsw; |
---|
237 | ru->ps_involcsw += ru2->ps_involcsw; |
---|
238 | ru->ps_signal += ru2->ps_signal; |
---|
239 | ru->ps_lread += ru2->ps_lread; |
---|
240 | ru->ps_lwrite += ru2->ps_lwrite; |
---|
241 | ru->ps_bread += ru2->ps_bread; |
---|
242 | ru->ps_bwrite += ru2->ps_bwrite; |
---|
243 | ru->ps_phread += ru2->ps_phread; |
---|
244 | ru->ps_phwrite += ru2->ps_phwrite; |
---|
245 | } |
---|
246 | |
---|
247 | # endif /* _SEQUENT_ */ |
---|
248 | #endif /* BSDTIMES */ |
---|
249 | |
---|
250 | #ifdef BSDTIMES |
---|
251 | |
---|
252 | /* |
---|
253 | * PWP: the LOG1024 and pagetok stuff taken from the top command, |
---|
254 | * written by William LeFebvre |
---|
255 | */ |
---|
256 | /* Log base 2 of 1024 is 10 (2^10 == 1024) */ |
---|
257 | #define LOG1024 10 |
---|
258 | |
---|
259 | /* Convert clicks (kernel pages) to kbytes ... */ |
---|
260 | /* If there is no PGSHIFT defined, assume it is 11 */ |
---|
261 | /* Is this needed for compatability with some old flavor of 4.2 or 4.1? */ |
---|
262 | #ifdef SUNOS4 |
---|
263 | # ifndef PGSHIFT |
---|
264 | # define pagetok(size) ((size) << 1) |
---|
265 | # else |
---|
266 | # if PGSHIFT>10 |
---|
267 | # define pagetok(size) ((size) << (PGSHIFT - LOG1024)) |
---|
268 | # else |
---|
269 | # define pagetok(size) ((size) >> (LOG1024 - PGSHIFT)) |
---|
270 | # endif |
---|
271 | # endif |
---|
272 | #endif |
---|
273 | |
---|
274 | /* |
---|
275 | * if any other machines return wierd values in the ru_i* stuff, put |
---|
276 | * the adjusting macro here: |
---|
277 | */ |
---|
278 | #ifdef SUNOS4 |
---|
279 | # define IADJUST(i) (pagetok(i)/2) |
---|
280 | #else /* SUNOS4 */ |
---|
281 | # ifdef convex |
---|
282 | /* |
---|
283 | * convex has megabytes * CLK_TCK |
---|
284 | * multiply by 100 since we use time in 100ths of a second in prusage |
---|
285 | */ |
---|
286 | # define IADJUST(i) (((i) << 10) / CLK_TCK * 100) |
---|
287 | # else /* convex */ |
---|
288 | # define IADJUST(i) (i) |
---|
289 | # endif /* convex */ |
---|
290 | #endif /* SUNOS4 */ |
---|
291 | |
---|
292 | void |
---|
293 | prusage(r0, r1, e, b) |
---|
294 | register struct sysrusage *r0, *r1; |
---|
295 | timeval_t *e, *b; |
---|
296 | |
---|
297 | #else /* BSDTIMES */ |
---|
298 | # ifdef _SEQUENT_ |
---|
299 | void |
---|
300 | prusage(r0, r1, e, b) |
---|
301 | register struct process_stats *r0, *r1; |
---|
302 | timeval_t *e, *b; |
---|
303 | |
---|
304 | # else /* _SEQUENT_ */ |
---|
305 | void |
---|
306 | prusage(bs, es, e, b) |
---|
307 | struct tms *bs, *es; |
---|
308 | |
---|
309 | # ifndef POSIX |
---|
310 | time_t e, b; |
---|
311 | |
---|
312 | # else /* POSIX */ |
---|
313 | clock_t e, b; |
---|
314 | |
---|
315 | # endif /* POSIX */ |
---|
316 | # endif /* _SEQUENT_ */ |
---|
317 | #endif /* BSDTIMES */ |
---|
318 | { |
---|
319 | #ifdef BSDTIMES |
---|
320 | register time_t t = |
---|
321 | (r1->ru_utime.tv_sec - r0->ru_utime.tv_sec) * 100 + |
---|
322 | (r1->ru_utime.tv_usec - r0->ru_utime.tv_usec) / 10000 + |
---|
323 | (r1->ru_stime.tv_sec - r0->ru_stime.tv_sec) * 100 + |
---|
324 | (r1->ru_stime.tv_usec - r0->ru_stime.tv_usec) / 10000; |
---|
325 | |
---|
326 | #else |
---|
327 | # ifdef _SEQUENT_ |
---|
328 | register time_t t = |
---|
329 | (r1->ps_utime.tv_sec - r0->ps_utime.tv_sec) * 100 + |
---|
330 | (r1->ps_utime.tv_usec - r0->ps_utime.tv_usec) / 10000 + |
---|
331 | (r1->ps_stime.tv_sec - r0->ps_stime.tv_sec) * 100 + |
---|
332 | (r1->ps_stime.tv_usec - r0->ps_stime.tv_usec) / 10000; |
---|
333 | |
---|
334 | # else /* _SEQUENT_ */ |
---|
335 | # ifndef POSIX |
---|
336 | register time_t t = (es->tms_utime - bs->tms_utime + |
---|
337 | es->tms_stime - bs->tms_stime) * 100 / HZ; |
---|
338 | |
---|
339 | # else /* POSIX */ |
---|
340 | register clock_t t = (es->tms_utime - bs->tms_utime + |
---|
341 | es->tms_stime - bs->tms_stime) * 100 / clk_tck; |
---|
342 | |
---|
343 | # endif /* POSIX */ |
---|
344 | # endif /* _SEQUENT_ */ |
---|
345 | #endif /* BSDTIMES */ |
---|
346 | |
---|
347 | register char *cp; |
---|
348 | register long i; |
---|
349 | register struct varent *vp = adrof(STRtime); |
---|
350 | |
---|
351 | #ifdef BSDTIMES |
---|
352 | # ifdef convex |
---|
353 | static struct system_information sysinfo; |
---|
354 | long long memtmp; /* let memory calculations exceede 2Gb */ |
---|
355 | # endif /* convex */ |
---|
356 | int ms = (int) |
---|
357 | ((e->tv_sec - b->tv_sec) * 100 + (e->tv_usec - b->tv_usec) / 10000); |
---|
358 | |
---|
359 | cp = "%Uu %Ss %E %P %X+%Dk %I+%Oio %Fpf+%Ww"; |
---|
360 | #else /* !BSDTIMES */ |
---|
361 | # ifdef _SEQUENT_ |
---|
362 | int ms = (int) |
---|
363 | ((e->tv_sec - b->tv_sec) * 100 + (e->tv_usec - b->tv_usec) / 10000); |
---|
364 | |
---|
365 | cp = "%Uu %Ss %E %P %I+%Oio %Fpf+%Ww"; |
---|
366 | # else /* !_SEQUENT_ */ |
---|
367 | # ifndef POSIX |
---|
368 | time_t ms = ((time_t)((e - b) / HZ) * 100) + |
---|
369 | (time_t)(((e - b) % HZ) * 100) / HZ; |
---|
370 | # else /* POSIX */ |
---|
371 | clock_t ms = ((clock_t)((e - b) / clk_tck) * 100) + |
---|
372 | (clock_t)(((e - b) % clk_tck) * 100) / clk_tck; |
---|
373 | # endif /* POSIX */ |
---|
374 | |
---|
375 | cp = "%Uu %Ss %E %P"; |
---|
376 | |
---|
377 | /* |
---|
378 | * the tms stuff is not very precise, so we fudge it. |
---|
379 | * granularity fix: can't be more than 100% |
---|
380 | * this breaks in multi-processor systems... |
---|
381 | * maybe I should take it out and let people see more then 100% |
---|
382 | * utilizations. |
---|
383 | */ |
---|
384 | # if 0 |
---|
385 | if (ms < t && ms != 0) |
---|
386 | ms = t; |
---|
387 | # endif |
---|
388 | # endif /*! _SEQUENT_ */ |
---|
389 | #endif /* !BSDTIMES */ |
---|
390 | #ifdef TDEBUG |
---|
391 | xprintf("es->tms_utime %lu bs->tms_utime %lu\n", |
---|
392 | es->tms_utime, bs->tms_utime); |
---|
393 | xprintf("es->tms_stime %lu bs->tms_stime %lu\n", |
---|
394 | es->tms_stime, bs->tms_stime); |
---|
395 | xprintf("ms %lu e %lu b %lu\n", ms, e, b); |
---|
396 | xprintf("t %lu\n", t); |
---|
397 | #endif /* TDEBUG */ |
---|
398 | |
---|
399 | if (vp && vp->vec[0] && vp->vec[1]) |
---|
400 | cp = short2str(vp->vec[1]); |
---|
401 | for (; *cp; cp++) |
---|
402 | if (*cp != '%') |
---|
403 | xputchar(*cp); |
---|
404 | else if (cp[1]) |
---|
405 | switch (*++cp) { |
---|
406 | |
---|
407 | case 'U': /* user CPU time used */ |
---|
408 | #ifdef BSDTIMES |
---|
409 | pdeltat(&r1->ru_utime, &r0->ru_utime); |
---|
410 | #else |
---|
411 | # ifdef _SEQUENT_ |
---|
412 | pdeltat(&r1->ps_utime, &r0->ps_utime); |
---|
413 | # else /* _SEQUENT_ */ |
---|
414 | # ifndef POSIX |
---|
415 | pdtimet(es->tms_utime, bs->tms_utime); |
---|
416 | # else /* POSIX */ |
---|
417 | pdtimet(es->tms_utime, bs->tms_utime); |
---|
418 | # endif /* POSIX */ |
---|
419 | # endif /* _SEQUENT_ */ |
---|
420 | #endif /* BSDTIMES */ |
---|
421 | break; |
---|
422 | |
---|
423 | case 'S': /* system CPU time used */ |
---|
424 | #ifdef BSDTIMES |
---|
425 | pdeltat(&r1->ru_stime, &r0->ru_stime); |
---|
426 | #else |
---|
427 | # ifdef _SEQUENT_ |
---|
428 | pdeltat(&r1->ps_stime, &r0->ps_stime); |
---|
429 | # else /* _SEQUENT_ */ |
---|
430 | # ifndef POSIX |
---|
431 | pdtimet(es->tms_stime, bs->tms_stime); |
---|
432 | # else /* POSIX */ |
---|
433 | pdtimet(es->tms_stime, bs->tms_stime); |
---|
434 | # endif /* POSIX */ |
---|
435 | # endif /* _SEQUENT_ */ |
---|
436 | #endif /* BSDTIMES */ |
---|
437 | break; |
---|
438 | |
---|
439 | case 'E': /* elapsed (wall-clock) time */ |
---|
440 | #ifdef BSDTIMES |
---|
441 | pcsecs((long) ms); |
---|
442 | #else /* BSDTIMES */ |
---|
443 | pcsecs(ms); |
---|
444 | #endif /* BSDTIMES */ |
---|
445 | break; |
---|
446 | |
---|
447 | case 'P': /* percent time spent running */ |
---|
448 | /* check if the process did not run */ |
---|
449 | #ifdef convex |
---|
450 | /* |
---|
451 | * scale the cpu %- ages by the number of processors |
---|
452 | * available on this machine |
---|
453 | */ |
---|
454 | if ((sysinfo.cpu_count == 0) && |
---|
455 | (getsysinfo(SYSINFO_SIZE, &sysinfo) < 0)) |
---|
456 | sysinfo.cpu_count = 1; |
---|
457 | i = (ms == 0) ? 0 : (t * 1000 / (ms * sysinfo.cpu_count)); |
---|
458 | #else /* convex */ |
---|
459 | i = (ms == 0) ? 0 : (t * 1000 / ms); |
---|
460 | #endif /* convex */ |
---|
461 | xprintf("%ld.%01ld%%", i / 10, i % 10); /* nn.n% */ |
---|
462 | break; |
---|
463 | |
---|
464 | #ifdef BSDTIMES |
---|
465 | case 'W': /* number of swaps */ |
---|
466 | i = r1->ru_nswap - r0->ru_nswap; |
---|
467 | xprintf("%ld", i); |
---|
468 | break; |
---|
469 | |
---|
470 | #ifdef convex |
---|
471 | case 'X': /* (average) shared text size */ |
---|
472 | memtmp = (t == 0 ? 0LL : IADJUST((long long)r1->ru_ixrss - |
---|
473 | (long long)r0->ru_ixrss) / |
---|
474 | (long long)t); |
---|
475 | xprintf("%lu", (unsigned long)memtmp); |
---|
476 | |
---|
477 | break; |
---|
478 | |
---|
479 | case 'D': /* (average) unshared data size */ |
---|
480 | memtmp = (t == 0 ? 0LL : IADJUST((long long)r1->ru_idrss + |
---|
481 | (long long)r1->ru_isrss - |
---|
482 | ((long long)r0->ru_idrss + |
---|
483 | (long long)r0->ru_isrss)) / |
---|
484 | (long long)t); |
---|
485 | xprintf("%lu", (unsigned long)memtmp); |
---|
486 | break; |
---|
487 | |
---|
488 | case 'K': /* (average) total data memory used */ |
---|
489 | memtmp = (t == 0 ? 0LL : IADJUST(((long long)r1->ru_ixrss + |
---|
490 | (long long)r1->ru_isrss + |
---|
491 | (long long)r1->ru_idrss) - |
---|
492 | ((long long)r0->ru_ixrss + |
---|
493 | (long long)r0->ru_idrss + |
---|
494 | (long long)r0->ru_isrss)) / |
---|
495 | (long long)t); |
---|
496 | xprintf("%lu", (unsigned long)memtmp); |
---|
497 | break; |
---|
498 | #else /* !convex */ |
---|
499 | case 'X': /* (average) shared text size */ |
---|
500 | xprintf("%ld", t == 0 ? 0L : |
---|
501 | IADJUST(r1->ru_ixrss - r0->ru_ixrss) / t); |
---|
502 | break; |
---|
503 | |
---|
504 | case 'D': /* (average) unshared data size */ |
---|
505 | xprintf("%ld", t == 0 ? 0L : |
---|
506 | IADJUST(r1->ru_idrss + r1->ru_isrss - |
---|
507 | (r0->ru_idrss + r0->ru_isrss)) / t); |
---|
508 | break; |
---|
509 | |
---|
510 | case 'K': /* (average) total data memory used */ |
---|
511 | xprintf("%ld", t == 0 ? 0L : |
---|
512 | IADJUST((r1->ru_ixrss + r1->ru_isrss + r1->ru_idrss) - |
---|
513 | (r0->ru_ixrss + r0->ru_idrss + r0->ru_isrss)) / t); |
---|
514 | break; |
---|
515 | #endif /* convex */ |
---|
516 | case 'M': /* max. Resident Set Size */ |
---|
517 | #ifdef SUNOS4 |
---|
518 | xprintf("%ld", pagetok(r1->ru_maxrss)); |
---|
519 | #else |
---|
520 | # ifdef convex |
---|
521 | xprintf("%ld", r1->ru_maxrss * 4L); |
---|
522 | # else /* !convex */ |
---|
523 | xprintf("%ld", r1->ru_maxrss / 2L); |
---|
524 | # endif /* convex */ |
---|
525 | #endif /* SUNOS4 */ |
---|
526 | break; |
---|
527 | |
---|
528 | case 'F': /* page faults */ |
---|
529 | xprintf("%ld", r1->ru_majflt - r0->ru_majflt); |
---|
530 | break; |
---|
531 | |
---|
532 | case 'R': /* page reclaims */ |
---|
533 | xprintf("%ld", r1->ru_minflt - r0->ru_minflt); |
---|
534 | break; |
---|
535 | |
---|
536 | case 'I': /* FS blocks in */ |
---|
537 | xprintf("%ld", r1->ru_inblock - r0->ru_inblock); |
---|
538 | break; |
---|
539 | |
---|
540 | case 'O': /* FS blocks out */ |
---|
541 | xprintf("%ld", r1->ru_oublock - r0->ru_oublock); |
---|
542 | break; |
---|
543 | |
---|
544 | # ifdef convex |
---|
545 | case 'C': /* CPU parallelization factor */ |
---|
546 | if (r1->ru_usamples != 0LL) { |
---|
547 | long long parr = ((r1->ru_utotal * 100LL) / |
---|
548 | r1->ru_usamples); |
---|
549 | xprintf("%d.%02d", (int)(parr/100), (int)(parr%100)); |
---|
550 | } else |
---|
551 | xprintf("?"); |
---|
552 | break; |
---|
553 | # endif /* convex */ |
---|
554 | case 'r': /* PWP: socket messages recieved */ |
---|
555 | xprintf("%ld", r1->ru_msgrcv - r0->ru_msgrcv); |
---|
556 | break; |
---|
557 | |
---|
558 | case 's': /* PWP: socket messages sent */ |
---|
559 | xprintf("%ld", r1->ru_msgsnd - r0->ru_msgsnd); |
---|
560 | break; |
---|
561 | |
---|
562 | case 'k': /* PWP: signals received */ |
---|
563 | xprintf("%ld", r1->ru_nsignals - r0->ru_nsignals); |
---|
564 | break; |
---|
565 | |
---|
566 | case 'w': /* PWP: voluntary context switches (waits) */ |
---|
567 | xprintf("%ld", r1->ru_nvcsw - r0->ru_nvcsw); |
---|
568 | break; |
---|
569 | |
---|
570 | case 'c': /* PWP: involuntary context switches */ |
---|
571 | xprintf("%ld", r1->ru_nivcsw - r0->ru_nivcsw); |
---|
572 | break; |
---|
573 | #else /* BSDTIMES */ |
---|
574 | # ifdef _SEQUENT_ |
---|
575 | case 'W': /* number of swaps */ |
---|
576 | i = r1->ps_swap - r0->ps_swap; |
---|
577 | xprintf("%ld", i); |
---|
578 | break; |
---|
579 | |
---|
580 | case 'M': |
---|
581 | xprintf("%ld", r1->ps_maxrss / 2); |
---|
582 | break; |
---|
583 | |
---|
584 | case 'F': |
---|
585 | xprintf("%ld", r1->ps_pagein - r0->ps_pagein); |
---|
586 | break; |
---|
587 | |
---|
588 | case 'R': |
---|
589 | xprintf("%ld", r1->ps_reclaim - r0->ps_reclaim); |
---|
590 | break; |
---|
591 | |
---|
592 | case 'I': |
---|
593 | xprintf("%ld", r1->ps_bread - r0->ps_bread); |
---|
594 | break; |
---|
595 | |
---|
596 | case 'O': |
---|
597 | xprintf("%ld", r1->ps_bwrite - r0->ps_bwrite); |
---|
598 | break; |
---|
599 | |
---|
600 | case 'k': |
---|
601 | xprintf("%ld", r1->ps_signal - r0->ps_signal); |
---|
602 | break; |
---|
603 | |
---|
604 | case 'w': |
---|
605 | xprintf("%ld", r1->ps_volcsw - r0->ps_volcsw); |
---|
606 | break; |
---|
607 | |
---|
608 | case 'c': |
---|
609 | xprintf("%ld", r1->ps_involcsw - r0->ps_involcsw); |
---|
610 | break; |
---|
611 | |
---|
612 | case 'Z': |
---|
613 | xprintf("%ld", r1->ps_zerofill - r0->ps_zerofill); |
---|
614 | break; |
---|
615 | |
---|
616 | case 'i': |
---|
617 | xprintf("%ld", r1->ps_pffincr - r0->ps_pffincr); |
---|
618 | break; |
---|
619 | |
---|
620 | case 'd': |
---|
621 | xprintf("%ld", r1->ps_pffdecr - r0->ps_pffdecr); |
---|
622 | break; |
---|
623 | |
---|
624 | case 'Y': |
---|
625 | xprintf("%ld", r1->ps_syscall - r0->ps_syscall); |
---|
626 | break; |
---|
627 | |
---|
628 | case 'l': |
---|
629 | xprintf("%ld", r1->ps_lread - r0->ps_lread); |
---|
630 | break; |
---|
631 | |
---|
632 | case 'm': |
---|
633 | xprintf("%ld", r1->ps_lwrite - r0->ps_lwrite); |
---|
634 | break; |
---|
635 | |
---|
636 | case 'p': |
---|
637 | xprintf("%ld", r1->ps_phread - r0->ps_phread); |
---|
638 | break; |
---|
639 | |
---|
640 | case 'q': |
---|
641 | xprintf("%ld", r1->ps_phwrite - r0->ps_phwrite); |
---|
642 | break; |
---|
643 | # endif /* _SEQUENT_ */ |
---|
644 | #endif /* BSDTIMES */ |
---|
645 | default: |
---|
646 | break; |
---|
647 | } |
---|
648 | xputchar('\n'); |
---|
649 | } |
---|
650 | |
---|
651 | #if defined(BSDTIMES) || defined(_SEQUENT_) |
---|
652 | static void |
---|
653 | pdeltat(t1, t0) |
---|
654 | timeval_t *t1, *t0; |
---|
655 | { |
---|
656 | timeval_t td; |
---|
657 | |
---|
658 | tvsub(&td, t1, t0); |
---|
659 | xprintf("%ld.%03ld", td.tv_sec, td.tv_usec / 1000L); |
---|
660 | } |
---|
661 | |
---|
662 | static void |
---|
663 | tvadd(tsum, t0) |
---|
664 | timeval_t *tsum, *t0; |
---|
665 | { |
---|
666 | |
---|
667 | tsum->tv_sec += t0->tv_sec; |
---|
668 | tsum->tv_usec += t0->tv_usec; |
---|
669 | if (tsum->tv_usec >= 1000000) |
---|
670 | tsum->tv_sec++, tsum->tv_usec -= 1000000; |
---|
671 | } |
---|
672 | |
---|
673 | void |
---|
674 | tvsub(tdiff, t1, t0) |
---|
675 | timeval_t *tdiff, *t1, *t0; |
---|
676 | { |
---|
677 | |
---|
678 | tdiff->tv_sec = t1->tv_sec - t0->tv_sec; |
---|
679 | tdiff->tv_usec = t1->tv_usec - t0->tv_usec; |
---|
680 | if (tdiff->tv_usec < 0) |
---|
681 | tdiff->tv_sec--, tdiff->tv_usec += 1000000; |
---|
682 | } |
---|
683 | |
---|
684 | #else /* !BSDTIMES && !_SEQUENT_ */ |
---|
685 | static void |
---|
686 | pdtimet(eval, bval) |
---|
687 | #ifndef POSIX |
---|
688 | time_t eval, bval; |
---|
689 | |
---|
690 | #else /* POSIX */ |
---|
691 | clock_t eval, bval; |
---|
692 | |
---|
693 | #endif /* POSIX */ |
---|
694 | { |
---|
695 | #ifndef POSIX |
---|
696 | time_t val; |
---|
697 | |
---|
698 | #else /* POSIX */ |
---|
699 | clock_t val; |
---|
700 | |
---|
701 | #endif /* POSIX */ |
---|
702 | |
---|
703 | #ifndef POSIX |
---|
704 | val = (eval - bval) * 100 / HZ; |
---|
705 | #else /* POSIX */ |
---|
706 | val = (eval - bval) * 100 / clk_tck; |
---|
707 | #endif /* POSIX */ |
---|
708 | |
---|
709 | xprintf("%ld.%02ld", val / 100, val - (val / 100 * 100)); |
---|
710 | } |
---|
711 | #endif /* BSDTIMES || _SEQUENT_ */ |
---|