xref: /openbsd/bin/ps/print.c (revision 78b63d65)
1 /*	$OpenBSD: print.c,v 1.22 2001/12/05 02:23:59 art Exp $	*/
2 /*	$NetBSD: print.c,v 1.27 1995/09/29 21:58:12 cgd Exp $	*/
3 
4 /*-
5  * Copyright (c) 1990, 1993, 1994
6  *	The Regents of the University of California.  All rights reserved.
7  *
8  * Redistribution and use in source and binary forms, with or without
9  * modification, are permitted provided that the following conditions
10  * are met:
11  * 1. Redistributions of source code must retain the above copyright
12  *    notice, this list of conditions and the following disclaimer.
13  * 2. Redistributions in binary form must reproduce the above copyright
14  *    notice, this list of conditions and the following disclaimer in the
15  *    documentation and/or other materials provided with the distribution.
16  * 3. All advertising materials mentioning features or use of this software
17  *    must display the following acknowledgement:
18  *	This product includes software developed by the University of
19  *	California, Berkeley and its contributors.
20  * 4. Neither the name of the University nor the names of its contributors
21  *    may be used to endorse or promote products derived from this software
22  *    without specific prior written permission.
23  *
24  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
25  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
26  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
27  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
28  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
29  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
30  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
31  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
32  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
33  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
34  * SUCH DAMAGE.
35  */
36 
37 #ifndef lint
38 #if 0
39 static char sccsid[] = "@(#)print.c	8.6 (Berkeley) 4/16/94";
40 #else
41 static char rcsid[] = "$OpenBSD: print.c,v 1.22 2001/12/05 02:23:59 art Exp $";
42 #endif
43 #endif /* not lint */
44 
45 #include <sys/param.h>
46 #include <sys/time.h>
47 #include <sys/resource.h>
48 #include <sys/proc.h>
49 #include <sys/stat.h>
50 
51 #include <sys/ucred.h>
52 #include <sys/sysctl.h>
53 #include <uvm/uvm_extern.h>
54 
55 #include <err.h>
56 #include <grp.h>
57 #include <kvm.h>
58 #include <math.h>
59 #include <nlist.h>
60 #include <stddef.h>
61 #include <stdio.h>
62 #include <stdlib.h>
63 #include <string.h>
64 #include <tzfile.h>
65 #include <unistd.h>
66 #include <pwd.h>
67 
68 #include "ps.h"
69 
70 extern kvm_t *kd;
71 extern int needenv, needcomm, commandonly;
72 
73 static char *cmdpart __P((char *));
74 
75 #define	min(a,b)	((a) < (b) ? (a) : (b))
76 
77 static char *
78 cmdpart(arg0)
79 	char *arg0;
80 {
81 	char *cp;
82 
83 	return ((cp = strrchr(arg0, '/')) != NULL ? cp + 1 : arg0);
84 }
85 
86 void
87 printheader()
88 {
89 	VAR *v;
90 	struct varent *vent;
91 
92 	for (vent = vhead; vent; vent = vent->next) {
93 		v = vent->var;
94 		if (v->flag & LJUST) {
95 			if (vent->next == NULL)	/* last one */
96 				(void)printf("%s", v->header);
97 			else
98 				(void)printf("%-*s", v->width, v->header);
99 		} else
100 			(void)printf("%*s", v->width, v->header);
101 		if (vent->next != NULL)
102 			(void)putchar(' ');
103 	}
104 	(void)putchar('\n');
105 }
106 
107 void
108 command(ki, ve)
109 	KINFO *ki;
110 	VARENT *ve;
111 {
112 	VAR *v;
113 	int left;
114 	char **argv, **p;
115 
116 	v = ve->var;
117 	if (ve->next != NULL || termwidth != UNLIMITED) {
118 		if (ve->next == NULL) {
119 			left = termwidth - (totwidth - v->width);
120 			if (left < 1) /* already wrapped, just use std width */
121 				left = v->width;
122 		} else
123 			left = v->width;
124 	} else
125 		left = -1;
126 	if (needenv) {
127 		argv = kvm_getenvv(kd, ki->ki_p, termwidth);
128 		if ((p = argv) != NULL) {
129 			while (*p) {
130 				fmt_puts(*p, &left);
131 				p++;
132 				fmt_putc(' ', &left);
133 			}
134 		}
135 	}
136 	if (needcomm) {
137 		if (!commandonly) {
138 			argv = kvm_getargv(kd, ki->ki_p, termwidth);
139 			if ((p = argv) != NULL) {
140 				while (*p) {
141 					fmt_puts(*p, &left);
142 					p++;
143 					fmt_putc(' ', &left);
144 				}
145 			}
146 			if (argv == 0 || argv[0] == 0 ||
147 			    strcmp(cmdpart(argv[0]), KI_PROC(ki)->p_comm)) {
148 				fmt_putc('(', &left);
149 				fmt_puts(KI_PROC(ki)->p_comm, &left);
150 				fmt_putc(')', &left);
151 			}
152 		} else {
153 			fmt_puts(KI_PROC(ki)->p_comm, &left);
154 		}
155 	}
156 	if (ve->next && left > 0)
157 		printf("%*s", left, "");
158 }
159 
160 void
161 ucomm(k, ve)
162 	KINFO *k;
163 	VARENT *ve;
164 {
165 	VAR *v;
166 
167 	v = ve->var;
168 	(void)printf("%-*s", v->width, KI_PROC(k)->p_comm);
169 }
170 
171 void
172 logname(k, ve)
173 	KINFO *k;
174 	VARENT *ve;
175 {
176 	VAR *v;
177 
178 	v = ve->var;
179 	if (KI_EPROC(k)->e_login[0]) {
180 		int n = min(v->width, MAXLOGNAME);
181 		(void)printf("%-*.*s", n, n, KI_EPROC(k)->e_login);
182 		if (v->width > n)
183 			(void)printf("%*s", v->width - n, "");
184 	} else
185 		(void)printf("%-*s", v->width, "-");
186 }
187 
188 #define pgtok(a)	(((a)*getpagesize())/1024)
189 
190 void
191 state(k, ve)
192 	KINFO *k;
193 	VARENT *ve;
194 {
195 	struct proc *p;
196 	int flag;
197 	char *cp;
198 	VAR *v;
199 	char buf[16];
200 
201 	v = ve->var;
202 	p = KI_PROC(k);
203 	flag = p->p_flag;
204 	cp = buf;
205 
206 	switch (p->p_stat) {
207 
208 	case SSTOP:
209 		*cp = 'T';
210 		break;
211 
212 	case SSLEEP:
213 		if (flag & P_SINTR)	/* interruptible (long) */
214 			*cp = p->p_slptime >= maxslp ? 'I' : 'S';
215 		else
216 			*cp = 'D';
217 		break;
218 
219 	case SRUN:
220 	case SIDL:
221 		*cp = 'R';
222 		break;
223 
224 	case SZOMB:
225 		*cp = 'Z';
226 		break;
227 
228 	default:
229 		*cp = '?';
230 	}
231 	cp++;
232 	if (flag & P_INMEM) {
233 	} else
234 		*cp++ = 'W';
235 	if (p->p_nice < NZERO)
236 		*cp++ = '<';
237 	else if (p->p_nice > NZERO)
238 		*cp++ = 'N';
239 	if (flag & P_TRACED)
240 		*cp++ = 'X';
241 	if (flag & P_WEXIT && p->p_stat != SZOMB)
242 		*cp++ = 'E';
243 	if (flag & P_PPWAIT)
244 		*cp++ = 'V';
245 	if (flag & P_SYSTEM)
246 		*cp++ = 'K';
247 	/* XXX Since P_SYSTEM now shows a K, should L just be for holdcnt? */
248 	if ((flag & P_SYSTEM) || p->p_holdcnt)
249 		*cp++ = 'L';
250 	if ((flag & P_SYSTEM) == 0 &&
251 	    KI_EPROC(k)->e_maxrss / 1024 < pgtok(KI_EPROC(k)->e_vm.vm_rssize))
252 		*cp++ = '>';
253 	if (KI_EPROC(k)->e_flag & EPROC_SLEADER)
254 		*cp++ = 's';
255 	if ((flag & P_CONTROLT) && KI_EPROC(k)->e_pgid == KI_EPROC(k)->e_tpgid)
256 		*cp++ = '+';
257 	*cp = '\0';
258 	(void)printf("%-*s", v->width, buf);
259 }
260 
261 void
262 pri(k, ve)
263 	KINFO *k;
264 	VARENT *ve;
265 {
266 	VAR *v;
267 
268 	v = ve->var;
269 	(void)printf("%*d", v->width, KI_PROC(k)->p_priority - PZERO);
270 }
271 
272 void
273 uname(k, ve)
274 	KINFO *k;
275 	VARENT *ve;
276 {
277 	VAR *v;
278 
279 	v = ve->var;
280 	(void)printf("%-*s",
281 	    (int)v->width, user_from_uid(KI_EPROC(k)->e_ucred.cr_uid, 0));
282 }
283 
284 void
285 runame(k, ve)
286 	KINFO *k;
287 	VARENT *ve;
288 {
289 	VAR *v;
290 
291 	v = ve->var;
292 	(void)printf("%-*s",
293 	    (int)v->width, user_from_uid(KI_EPROC(k)->e_pcred.p_ruid, 0));
294 }
295 
296 void
297 gname(k, ve)
298 	KINFO *k;
299 	VARENT *ve;
300 {
301 	VAR *v;
302 
303 	v = ve->var;
304 	(void)printf("%-*s",
305 	    (int)v->width, group_from_gid(KI_EPROC(k)->e_ucred.cr_gid, 0));
306 }
307 
308 void
309 rgname(k, ve)
310 	KINFO *k;
311 	VARENT *ve;
312 {
313 	VAR *v;
314 
315 	v = ve->var;
316 	(void)printf("%-*s",
317 	    (int)v->width, group_from_gid(KI_EPROC(k)->e_pcred.p_rgid, 0));
318 }
319 
320 void
321 tdev(k, ve)
322 	KINFO *k;
323 	VARENT *ve;
324 {
325 	VAR *v;
326 	dev_t dev;
327 	char buff[16];
328 
329 	v = ve->var;
330 	dev = KI_EPROC(k)->e_tdev;
331 	if (dev == NODEV)
332 		(void)printf("%*s", v->width, "??");
333 	else {
334 		(void)snprintf(buff, sizeof(buff),
335 		    "%d/%d", major(dev), minor(dev));
336 		(void)printf("%*s", v->width, buff);
337 	}
338 }
339 
340 void
341 tname(k, ve)
342 	KINFO *k;
343 	VARENT *ve;
344 {
345 	VAR *v;
346 	dev_t dev;
347 	char *ttname;
348 
349 	v = ve->var;
350 	dev = KI_EPROC(k)->e_tdev;
351 	if (dev == NODEV || (ttname = devname(dev, S_IFCHR)) == NULL)
352 		(void)printf("%-*s", v->width, "??");
353 	else {
354 		if (strncmp(ttname, "tty", 3) == 0)
355 			ttname += 3;
356 		(void)printf("%*.*s%c", v->width-1, v->width-1, ttname,
357 			KI_EPROC(k)->e_flag & EPROC_CTTY ? ' ' : '-');
358 	}
359 }
360 
361 void
362 longtname(k, ve)
363 	KINFO *k;
364 	VARENT *ve;
365 {
366 	VAR *v;
367 	dev_t dev;
368 	char *ttname;
369 
370 	v = ve->var;
371 	dev = KI_EPROC(k)->e_tdev;
372 	if (dev == NODEV || (ttname = devname(dev, S_IFCHR)) == NULL)
373 		(void)printf("%-*s", v->width, "??");
374 	else
375 		(void)printf("%-*s", v->width, ttname);
376 }
377 
378 void
379 started(k, ve)
380 	KINFO *k;
381 	VARENT *ve;
382 {
383 	VAR *v;
384 	static time_t now;
385 	time_t startt;
386 	struct tm *tp;
387 	char buf[100];
388 
389 	v = ve->var;
390 	if (!k->ki_u.u_valid) {
391 		(void)printf("%-*s", v->width, "-");
392 		return;
393 	}
394 
395 	startt = k->ki_u.u_start.tv_sec;
396 	tp = localtime(&startt);
397 	if (!now)
398 		(void)time(&now);
399 	if (now - k->ki_u.u_start.tv_sec < 24 * SECSPERHOUR) {
400 		/* I *hate* SCCS... */
401 		static char fmt[] = __CONCAT("%l:%", "M%p");
402 		(void)strftime(buf, sizeof(buf) - 1, fmt, tp);
403 	} else if (now - k->ki_u.u_start.tv_sec < 7 * SECSPERDAY) {
404 		/* I *hate* SCCS... */
405 		static char fmt[] = __CONCAT("%a%", "I%p");
406 		(void)strftime(buf, sizeof(buf) - 1, fmt, tp);
407 	} else
408 		(void)strftime(buf, sizeof(buf) - 1, "%e%b%y", tp);
409 	(void)printf("%-*s", v->width, buf);
410 }
411 
412 void
413 lstarted(k, ve)
414 	KINFO *k;
415 	VARENT *ve;
416 {
417 	VAR *v;
418 	time_t startt;
419 	char buf[100];
420 
421 	v = ve->var;
422 	if (!k->ki_u.u_valid) {
423 		(void)printf("%-*s", v->width, "-");
424 		return;
425 	}
426 	startt = k->ki_u.u_start.tv_sec;
427 	(void)strftime(buf, sizeof(buf) -1, "%c",
428 	    localtime(&startt));
429 	(void)printf("%-*s", v->width, buf);
430 }
431 
432 void
433 wchan(k, ve)
434 	KINFO *k;
435 	VARENT *ve;
436 {
437 	VAR *v;
438 
439 	v = ve->var;
440 	if (KI_PROC(k)->p_wchan) {
441 		int n;
442 
443 		if (KI_PROC(k)->p_wmesg) {
444 			n = min(v->width, WMESGLEN);
445 			(void)printf("%-*.*s", n, n, KI_EPROC(k)->e_wmesg);
446 			if (v->width > n)
447 				(void)printf("%*s", v->width - n, "");
448 		} else
449 			(void)printf("%-*lx", v->width,
450 			    (long)KI_PROC(k)->p_wchan &~ KERNBASE);
451 	} else
452 		(void)printf("%-*s", v->width, "-");
453 }
454 
455 void
456 vsize(k, ve)
457 	KINFO *k;
458 	VARENT *ve;
459 {
460 	VAR *v;
461 
462 	v = ve->var;
463 	(void)printf("%*d", v->width,
464 	    pgtok(KI_EPROC(k)->e_vm.vm_dsize + KI_EPROC(k)->e_vm.vm_ssize +
465 		KI_EPROC(k)->e_vm.vm_tsize));
466 }
467 
468 void
469 rssize(k, ve)
470 	KINFO *k;
471 	VARENT *ve;
472 {
473 	VAR *v;
474 
475 	v = ve->var;
476 	/* XXX don't have info about shared */
477 	(void)printf("%*d", v->width, (KI_PROC(k)->p_flag & P_SYSTEM) ? 0 :
478 	    pgtok(KI_EPROC(k)->e_vm.vm_rssize));
479 }
480 
481 void
482 p_rssize(k, ve)		/* doesn't account for text */
483 	KINFO *k;
484 	VARENT *ve;
485 {
486 	VAR *v;
487 
488 	v = ve->var;
489 	(void)printf("%*d", v->width, (KI_PROC(k)->p_flag & P_SYSTEM) ? 0 :
490 	    pgtok(KI_EPROC(k)->e_vm.vm_rssize));
491 }
492 
493 void
494 cputime(k, ve)
495 	KINFO *k;
496 	VARENT *ve;
497 {
498 	VAR *v;
499 	long secs;
500 	long psecs;	/* "parts" of a second. first micro, then centi */
501 	char obuff[128];
502 
503 	v = ve->var;
504 	if (KI_PROC(k)->p_stat == SZOMB || !k->ki_u.u_valid) {
505 		secs = 0;
506 		psecs = 0;
507 	} else {
508 		/*
509 		 * This counts time spent handling interrupts.  We could
510 		 * fix this, but it is not 100% trivial (and interrupt
511 		 * time fractions only work on the sparc anyway).	XXX
512 		 */
513 		secs = KI_PROC(k)->p_rtime.tv_sec;
514 		psecs = KI_PROC(k)->p_rtime.tv_usec;
515 		if (sumrusage) {
516 			secs += k->ki_u.u_cru.ru_utime.tv_sec +
517 				k->ki_u.u_cru.ru_stime.tv_sec;
518 			psecs += k->ki_u.u_cru.ru_utime.tv_usec +
519 				k->ki_u.u_cru.ru_stime.tv_usec;
520 		}
521 		/*
522 		 * round and scale to 100's
523 		 */
524 		psecs = (psecs + 5000) / 10000;
525 		secs += psecs / 100;
526 		psecs = psecs % 100;
527 	}
528 	(void)snprintf(obuff, sizeof(obuff),
529 	    "%3ld:%02ld.%02ld", secs/60, secs%60, psecs);
530 	(void)printf("%*s", v->width, obuff);
531 }
532 
533 double
534 getpcpu(k)
535 	KINFO *k;
536 {
537 	struct proc *p;
538 	static int failure;
539 	double d;
540 
541 	if (!nlistread)
542 		failure = donlist();
543 	if (failure)
544 		return (0.0);
545 
546 	p = KI_PROC(k);
547 #define	fxtofl(fixpt)	((double)(fixpt) / fscale)
548 
549 	/* XXX - I don't like this */
550 	if (p->p_swtime == 0 || (p->p_flag & P_INMEM) == 0)
551 		return (0.0);
552 	if (rawcpu)
553 		return (100.0 * fxtofl(p->p_pctcpu));
554 
555 	d = p->p_swtime * log(fxtofl(ccpu));
556 	if (d < -700.0)
557 		d = 0.0;		/* avoid IEEE underflow */
558 	else
559 		d = exp(d);
560 	return (100.0 * fxtofl(p->p_pctcpu) /
561 		(1.0 - d));
562 }
563 
564 void
565 pcpu(k, ve)
566 	KINFO *k;
567 	VARENT *ve;
568 {
569 	VAR *v;
570 
571 	v = ve->var;
572 	(void)printf("%*.1f", v->width, getpcpu(k));
573 }
574 
575 double
576 getpmem(k)
577 	KINFO *k;
578 {
579 	static int failure;
580 	struct proc *p;
581 	struct eproc *e;
582 	double fracmem;
583 	int szptudot;
584 
585 	if (!nlistread)
586 		failure = donlist();
587 	if (failure)
588 		return (0.0);
589 
590 	p = KI_PROC(k);
591 	e = KI_EPROC(k);
592 	if ((p->p_flag & P_INMEM) == 0 || (p->p_flag & P_SYSTEM))
593 		return (0.0);
594 	/* XXX want pmap ptpages, segtab, etc. (per architecture) */
595 	szptudot = USPACE/getpagesize();
596 	/* XXX don't have info about shared */
597 	fracmem = ((float)e->e_vm.vm_rssize + szptudot)/mempages;
598 	return (100.0 * fracmem);
599 }
600 
601 void
602 pmem(k, ve)
603 	KINFO *k;
604 	VARENT *ve;
605 {
606 	VAR *v;
607 
608 	v = ve->var;
609 	(void)printf("%*.1f", v->width, getpmem(k));
610 }
611 
612 void
613 pagein(k, ve)
614 	KINFO *k;
615 	VARENT *ve;
616 {
617 	VAR *v;
618 
619 	v = ve->var;
620 	(void)printf("%*ld", v->width,
621 	    k->ki_u.u_valid ? k->ki_u.u_ru.ru_majflt : 0);
622 }
623 
624 void
625 maxrss(k, ve)
626 	KINFO *k;
627 	VARENT *ve;
628 {
629 	VAR *v;
630 
631 	v = ve->var;
632 	(void)printf("%*lld", v->width, KI_EPROC(k)->e_maxrss / 1024);
633 }
634 
635 void
636 tsize(k, ve)
637 	KINFO *k;
638 	VARENT *ve;
639 {
640 	VAR *v;
641 
642 	v = ve->var;
643 	(void)printf("%*d", v->width, pgtok(KI_EPROC(k)->e_vm.vm_tsize));
644 }
645 
646 /*
647  * Generic output routines.  Print fields from various prototype
648  * structures.
649  */
650 static void
651 printval(bp, v)
652 	char *bp;
653 	VAR *v;
654 {
655 	static char ofmt[32] = "%";
656 	char *fcp, *cp;
657 	enum type type;
658 
659 	cp = ofmt + 1;
660 	fcp = v->fmt;
661 	if (v->flag & LJUST)
662 		*cp++ = '-';
663 	*cp++ = '*';
664 	while ((*cp++ = *fcp++));
665 
666 	/*
667 	 * Note that the "INF127" check is nonsensical for types
668 	 * that are or can be signed.
669 	 */
670 #define	GET(type)		(*(type *)bp)
671 #define	CHK_INF127(n)		(((n) > 127) && (v->flag & INF127) ? 127 : (n))
672 
673 	switch (v->type) {
674 	case INT32:
675 		if (sizeof(int32_t) == sizeof(int))
676 			type = INT;
677 		else if (sizeof(int32_t) == sizeof(long))
678 			type = LONG;
679 		else
680 			errx(1, "unknown conversion for type %d", v->type);
681 		break;
682 	case UINT32:
683 		if (sizeof(u_int32_t) == sizeof(u_int))
684 			type = UINT;
685 		else if (sizeof(u_int32_t) == sizeof(u_long))
686 			type = ULONG;
687 		else
688 			errx(1, "unknown conversion for type %d", v->type);
689 		break;
690 	default:
691 		type = v->type;
692 		break;
693 	}
694 
695 	switch (type) {
696 	case CHAR:
697 		(void)printf(ofmt, v->width, GET(char));
698 		break;
699 	case UCHAR:
700 		(void)printf(ofmt, v->width, CHK_INF127(GET(u_char)));
701 		break;
702 	case SHORT:
703 		(void)printf(ofmt, v->width, GET(short));
704 		break;
705 	case USHORT:
706 		(void)printf(ofmt, v->width, CHK_INF127(GET(u_short)));
707 		break;
708 	case INT:
709 		(void)printf(ofmt, v->width, GET(int));
710 		break;
711 	case UINT:
712 		(void)printf(ofmt, v->width, CHK_INF127(GET(u_int)));
713 		break;
714 	case LONG:
715 		(void)printf(ofmt, v->width, GET(long));
716 		break;
717 	case ULONG:
718 		(void)printf(ofmt, v->width, CHK_INF127(GET(u_long)));
719 		break;
720 	case KPTR:
721 		(void)printf(ofmt, v->width, GET(u_long) &~ KERNBASE);
722 		break;
723 	default:
724 		errx(1, "unknown type %d", v->type);
725 	}
726 #undef GET
727 #undef CHK_INF127
728 }
729 
730 void
731 pvar(k, ve)
732 	KINFO *k;
733 	VARENT *ve;
734 {
735 	VAR *v;
736 
737 	v = ve->var;
738 	printval((char *)((char *)KI_PROC(k) + v->off), v);
739 }
740 
741 void
742 evar(k, ve)
743 	KINFO *k;
744 	VARENT *ve;
745 {
746 	VAR *v;
747 
748 	v = ve->var;
749 	printval((char *)((char *)KI_EPROC(k) + v->off), v);
750 }
751 
752 void
753 uvar(k, ve)
754 	KINFO *k;
755 	VARENT *ve;
756 {
757 	VAR *v;
758 
759 	v = ve->var;
760 	if (k->ki_u.u_valid)
761 		printval((char *)((char *)&k->ki_u + v->off), v);
762 	else
763 		(void)printf("%*s", v->width, "-");
764 }
765 
766 void
767 rvar(k, ve)
768 	KINFO *k;
769 	VARENT *ve;
770 {
771 	VAR *v;
772 
773 	v = ve->var;
774 	if (k->ki_u.u_valid)
775 		printval((char *)((char *)(&k->ki_u.u_ru) + v->off), v);
776 	else
777 		(void)printf("%*s", v->width, "-");
778 }
779 
780 void
781 emulname(k, ve)
782 	KINFO *k;
783 	VARENT *ve;
784 {
785 	VAR *v;
786 
787 	v = ve->var;
788 
789 	(void)printf("%-*s",
790 	    (int)v->width, KI_EPROC(k)->e_emul);
791 }
792