Annotation of src/usr.bin/vmstat/vmstat.c, Revision 1.98
1.11 deraadt 1: /* $NetBSD: vmstat.c,v 1.29.4.1 1996/06/05 00:21:05 cgd Exp $ */
1.98 ! mickey 2: /* $OpenBSD: vmstat.c,v 1.97 2005/09/28 00:54:05 pedro Exp $ */
1.1 deraadt 3:
4: /*
5: * Copyright (c) 1980, 1986, 1991, 1993
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.
1.77 millert 16: * 3. Neither the name of the University nor the names of its contributors
1.1 deraadt 17: * may be used to endorse or promote products derived from this software
18: * without specific prior written permission.
19: *
20: * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
21: * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
22: * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
23: * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
24: * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
25: * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
26: * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
27: * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
28: * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
29: * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
30: * SUCH DAMAGE.
31: */
32:
33: #ifndef lint
34: static char copyright[] =
35: "@(#) Copyright (c) 1980, 1986, 1991, 1993\n\
36: The Regents of the University of California. All rights reserved.\n";
37: #endif /* not lint */
38:
39: #ifndef lint
40: #if 0
41: static char sccsid[] = "@(#)vmstat.c 8.1 (Berkeley) 6/6/93";
42: #else
1.98 ! mickey 43: static const char rcsid[] = "$OpenBSD: vmstat.c,v 1.97 2005/09/28 00:54:05 pedro Exp $";
1.1 deraadt 44: #endif
45: #endif /* not lint */
1.48 art 46:
1.1 deraadt 47: #include <sys/param.h>
48: #include <sys/time.h>
49: #include <sys/proc.h>
50: #include <sys/user.h>
51: #include <sys/dkstat.h>
52: #include <sys/buf.h>
53: #include <sys/namei.h>
54: #include <sys/malloc.h>
55: #include <sys/fcntl.h>
56: #include <sys/ioctl.h>
57: #include <sys/sysctl.h>
58: #include <sys/device.h>
1.48 art 59: #include <sys/pool.h>
1.1 deraadt 60: #include <time.h>
61: #include <nlist.h>
62: #include <kvm.h>
1.21 millert 63: #include <err.h>
1.1 deraadt 64: #include <errno.h>
65: #include <unistd.h>
66: #include <signal.h>
67: #include <stdio.h>
68: #include <ctype.h>
69: #include <stdlib.h>
70: #include <string.h>
71: #include <paths.h>
72: #include <limits.h>
1.6 tholo 73: #include "dkstats.h"
1.1 deraadt 74:
1.56 angelos 75: #include <uvm/uvm_object.h>
1.29 art 76: #include <uvm/uvm_extern.h>
77:
1.1 deraadt 78: struct nlist namelist[] = {
1.70 deraadt 79: #define X_UVMEXP 0 /* sysctl */
1.29 art 80: { "_uvmexp" },
1.70 deraadt 81: #define X_BOOTTIME 1 /* sysctl */
1.1 deraadt 82: { "_boottime" },
1.70 deraadt 83: #define X_NCHSTATS 2 /* sysctl */
1.1 deraadt 84: { "_nchstats" },
1.70 deraadt 85: #define X_KMEMSTAT 3 /* sysctl */
86: { "_kmemstats" },
87: #define X_KMEMBUCKETS 4 /* sysctl */
88: { "_bucket" },
89: #define X_FORKSTAT 5 /* sysctl */
90: { "_forkstat" },
91: #define X_NSELCOLL 6 /* sysctl */
92: { "_nselcoll" },
93: #define X_POOLHEAD 7 /* sysctl */
94: { "_pool_head" },
1.98 ! mickey 95: };
! 96:
! 97: struct nlist namelist2[] = {
! 98: { "_uvm_km_pages_free" },
1.1 deraadt 99: { "" },
100: };
101:
1.6 tholo 102: /* Objects defined in dkstats.c */
1.73 tdeval 103: extern struct _disk cur, last;
1.10 deraadt 104: extern char **dr_name;
105: extern int *dk_select, dk_ndrive;
1.1 deraadt 106:
1.29 art 107: struct uvmexp uvmexp, ouvmexp;
1.6 tholo 108: int ndrives;
1.1 deraadt 109:
110: int winlines = 20;
111:
112: kvm_t *kd;
113:
114: #define FORKSTAT 0x01
115: #define INTRSTAT 0x02
116: #define MEMSTAT 0x04
117: #define SUMSTAT 0x08
118: #define TIMESTAT 0x10
119: #define VMSTAT 0x20
120:
1.66 millert 121: void cpustats(void);
122: void dkstats(void);
123: void dointr(void);
124: void domem(void);
125: void dopool(void);
126: void dosum(void);
127: void dovmstat(u_int, int);
128: void kread(int, void *, size_t);
1.98 ! mickey 129: int kreado(struct nlist *, void *, size_t);
1.66 millert 130: void usage(void);
131: void dotimes(void);
132: void doforkst(void);
133: void printhdr(void);
1.1 deraadt 134:
1.66 millert 135: char **choosedrives(char **);
1.10 deraadt 136:
137: /* Namelist and memory file names. */
138: char *nlistf, *memf;
1.6 tholo 139:
1.50 art 140: extern char *__progname;
141:
1.65 art 142: int verbose = 0;
1.87 aaron 143: int zflag = 0;
1.65 art 144:
1.84 deraadt 145: int ncpu;
146:
1.21 millert 147: int
1.72 deraadt 148: main(int argc, char *argv[])
1.1 deraadt 149: {
150: extern int optind;
151: extern char *optarg;
1.84 deraadt 152: int mib[2];
153: size_t size;
1.62 mpech 154: int c, todo;
1.1 deraadt 155: u_int interval;
156: int reps;
1.25 deraadt 157: char errbuf[_POSIX2_LINE_MAX];
1.96 djm 158: gid_t gid;
1.1 deraadt 159:
160: interval = reps = todo = 0;
1.87 aaron 161: while ((c = getopt(argc, argv, "c:fiM:mN:stw:vz")) != -1) {
1.1 deraadt 162: switch (c) {
163: case 'c':
164: reps = atoi(optarg);
165: break;
166: case 'f':
167: todo |= FORKSTAT;
168: break;
169: case 'i':
170: todo |= INTRSTAT;
171: break;
172: case 'M':
173: memf = optarg;
174: break;
175: case 'm':
176: todo |= MEMSTAT;
177: break;
178: case 'N':
179: nlistf = optarg;
180: break;
181: case 's':
182: todo |= SUMSTAT;
183: break;
184: case 't':
185: todo |= TIMESTAT;
186: break;
187: case 'w':
188: interval = atoi(optarg);
189: break;
1.65 art 190: case 'v':
191: verbose = 1;
192: break;
1.87 aaron 193: case 'z':
194: zflag = 1;
195: break;
1.1 deraadt 196: case '?':
197: default:
198: usage();
199: }
200: }
201: argc -= optind;
202: argv += optind;
203:
204: if (todo == 0)
205: todo = VMSTAT;
206:
1.96 djm 207: gid = getgid();
1.56 angelos 208: if (nlistf != NULL || memf != NULL) {
1.96 djm 209: if (setresgid(gid, gid, gid) == -1)
210: err(1, "setresgid");
1.56 angelos 211: }
212:
1.1 deraadt 213: /*
214: * Discard setgid privileges if not the running kernel so that bad
215: * guys can't print interesting stuff from kernel memory.
216: */
1.56 angelos 217: #if notyet
1.15 tholo 218: if (nlistf != NULL || memf != NULL) {
1.56 angelos 219: #endif
220: kd = kvm_openfiles(nlistf, memf, NULL, O_RDONLY, errbuf);
221: if (kd == 0)
222: errx(1, "kvm_openfiles: %s", errbuf);
223:
1.96 djm 224: if (nlistf == NULL && memf == NULL)
225: if (setresgid(gid, gid, gid) == -1)
226: err(1, "setresgid");
227:
1.56 angelos 228: if ((c = kvm_nlist(kd, namelist)) != 0) {
229:
230: if (c > 0) {
231: (void)fprintf(stderr,
232: "%s: undefined symbols:", __progname);
233: for (c = 0;
234: c < sizeof(namelist)/sizeof(namelist[0]);
235: c++)
236: if (namelist[c].n_type == 0)
237: fprintf(stderr, " %s",
238: namelist[c].n_name);
239: (void)fputc('\n', stderr);
240: exit(1);
241: } else
242: errx(1, "kvm_nlist: %s", kvm_geterr(kd));
243: }
244: #ifdef notyet
1.96 djm 245: } else if (setresgid(gid, gid, gid) == -1)
246: err(1, "setresgid");
1.59 heko 247: #endif /* notyet */
1.1 deraadt 248:
1.84 deraadt 249: mib[0] = CTL_HW;
250: mib[1] = HW_NCPU;
251: size = sizeof(ncpu);
252: (void) sysctl(mib, 2, &ncpu, &size, NULL, 0);
253:
1.1 deraadt 254: if (todo & VMSTAT) {
255: struct winsize winsize;
256:
1.6 tholo 257: dkinit(0); /* Initialize disk stats, no disks selected. */
258: argv = choosedrives(argv); /* Select disks. */
1.1 deraadt 259: winsize.ws_row = 0;
260: (void) ioctl(STDOUT_FILENO, TIOCGWINSZ, (char *)&winsize);
261: if (winsize.ws_row > 0)
262: winlines = winsize.ws_row;
263:
264: }
1.25 deraadt 265:
1.1 deraadt 266: #define BACKWARD_COMPATIBILITY
267: #ifdef BACKWARD_COMPATIBILITY
268: if (*argv) {
269: interval = atoi(*argv);
270: if (*++argv)
271: reps = atoi(*argv);
272: }
273: #endif
274:
275: if (interval) {
276: if (!reps)
277: reps = -1;
278: } else if (reps)
279: interval = 1;
280:
281: if (todo & FORKSTAT)
282: doforkst();
1.48 art 283: if (todo & MEMSTAT) {
1.1 deraadt 284: domem();
1.48 art 285: dopool();
286: }
1.1 deraadt 287: if (todo & SUMSTAT)
288: dosum();
289: if (todo & TIMESTAT)
290: dotimes();
291: if (todo & INTRSTAT)
292: dointr();
293: if (todo & VMSTAT)
294: dovmstat(interval, reps);
295: exit(0);
296: }
297:
298: char **
1.72 deraadt 299: choosedrives(char **argv)
1.1 deraadt 300: {
1.62 mpech 301: int i;
1.1 deraadt 302:
303: /*
304: * Choose drives to be displayed. Priority goes to (in order) drives
305: * supplied as arguments, default drives. If everything isn't filled
306: * in and there are drives not taken care of, display the first few
307: * that fit.
308: */
309: #define BACKWARD_COMPATIBILITY
310: for (ndrives = 0; *argv; ++argv) {
311: #ifdef BACKWARD_COMPATIBILITY
312: if (isdigit(**argv))
313: break;
314: #endif
315: for (i = 0; i < dk_ndrive; i++) {
316: if (strcmp(dr_name[i], *argv))
317: continue;
1.6 tholo 318: dk_select[i] = 1;
1.1 deraadt 319: ++ndrives;
320: break;
321: }
322: }
1.64 deraadt 323: for (i = 0; i < dk_ndrive && ndrives < 2; i++) {
1.6 tholo 324: if (dk_select[i])
1.1 deraadt 325: continue;
1.6 tholo 326: dk_select[i] = 1;
1.1 deraadt 327: ++ndrives;
328: }
329: return(argv);
330: }
331:
1.19 deraadt 332: time_t
1.72 deraadt 333: getuptime(void)
1.1 deraadt 334: {
1.11 deraadt 335: static time_t now;
336: static struct timeval boottime;
1.1 deraadt 337: time_t uptime;
1.50 art 338: int mib[2];
339: size_t size;
1.1 deraadt 340:
1.50 art 341: if (boottime.tv_sec == 0) {
1.56 angelos 342: if (nlistf == NULL && memf == NULL) {
1.50 art 343: size = sizeof(boottime);
344: mib[0] = CTL_KERN;
345: mib[1] = KERN_BOOTTIME;
346: if (sysctl(mib, 2, &boottime, &size, NULL, 0) < 0) {
1.56 angelos 347: warn("could not get kern.boottime");
1.50 art 348: bzero(&boottime, sizeof(boottime));
349: }
1.56 angelos 350: } else {
351: kread(X_BOOTTIME, &boottime, sizeof(boottime));
1.50 art 352: }
353: }
1.1 deraadt 354: (void)time(&now);
1.11 deraadt 355: uptime = now - boottime.tv_sec;
1.50 art 356: if (uptime <= 0 || uptime > 60*60*24*365*10)
357: errx(1, "time makes no sense; namelist must be wrong");
358:
1.1 deraadt 359: return(uptime);
360: }
361:
362: int hz, hdrcnt;
363:
364: void
1.72 deraadt 365: dovmstat(u_int interval, int reps)
1.1 deraadt 366: {
367: struct vmtotal total;
368: time_t uptime, halfuptime;
1.78 deraadt 369: void needhdr(int);
1.1 deraadt 370: int mib[2];
1.50 art 371: struct clockinfo clkinfo;
1.1 deraadt 372: size_t size;
373:
374: uptime = getuptime();
375: halfuptime = uptime / 2;
376: (void)signal(SIGCONT, needhdr);
377:
1.50 art 378: mib[0] = CTL_KERN;
379: mib[1] = KERN_CLOCKRATE;
380: size = sizeof(clkinfo);
381: if (sysctl(mib, 2, &clkinfo, &size, NULL, 0) < 0) {
1.56 angelos 382: warn("could not read kern.clockrate");
1.50 art 383: return;
384: }
385: hz = clkinfo.stathz;
1.1 deraadt 386:
387: for (hdrcnt = 1;;) {
1.6 tholo 388: /* Read new disk statistics */
389: dkreadstats();
1.73 tdeval 390: if (!--hdrcnt || last.dk_ndrive != cur.dk_ndrive)
391: printhdr();
1.56 angelos 392: if (nlistf == NULL && memf == NULL) {
393: size = sizeof(struct uvmexp);
1.52 angelos 394: mib[0] = CTL_VM;
395: mib[1] = VM_UVMEXP;
396: if (sysctl(mib, 2, &uvmexp, &size, NULL, 0) < 0) {
1.56 angelos 397: warn("could not get vm.uvmexp");
398: bzero(&uvmexp, sizeof(struct uvmexp));
1.52 angelos 399: }
1.56 angelos 400: } else {
401: kread(X_UVMEXP, &uvmexp, sizeof(struct uvmexp));
1.52 angelos 402: }
1.1 deraadt 403: size = sizeof(total);
404: mib[0] = CTL_VM;
405: mib[1] = VM_METER;
406: if (sysctl(mib, 2, &total, &size, NULL, 0) < 0) {
1.56 angelos 407: warn("could not read vm.vmmeter");
1.1 deraadt 408: bzero(&total, sizeof(total));
409: }
1.22 millert 410: (void)printf("%2u%2u%2u",
1.1 deraadt 411: total.t_rq - 1, total.t_dw + total.t_pw, total.t_sw);
1.29 art 412: #define rate(x) (((x) + halfuptime) / uptime) /* round */
413: #define pgtok(a) ((a) * ((int)uvmexp.pagesize >> 10))
1.35 hugh 414: (void)printf("%7u%7u ",
1.1 deraadt 415: pgtok(total.t_avm), pgtok(total.t_free));
1.64 deraadt 416: (void)printf("%5u ", rate(uvmexp.faults - ouvmexp.faults));
1.29 art 417: (void)printf("%3u ", rate(uvmexp.pdreact - ouvmexp.pdreact));
418: (void)printf("%3u ", rate(uvmexp.pageins - ouvmexp.pageins));
419: (void)printf("%3u %3u ",
420: rate(uvmexp.pdpageouts - ouvmexp.pdpageouts), 0);
421: (void)printf("%3u ", rate(uvmexp.pdscans - ouvmexp.pdscans));
422: dkstats();
1.64 deraadt 423: (void)printf("%4u %5u %4u ",
1.29 art 424: rate(uvmexp.intrs - ouvmexp.intrs),
425: rate(uvmexp.syscalls - ouvmexp.syscalls),
426: rate(uvmexp.swtch - ouvmexp.swtch));
1.1 deraadt 427: cpustats();
428: (void)printf("\n");
429: (void)fflush(stdout);
430: if (reps >= 0 && --reps <= 0)
431: break;
1.29 art 432: ouvmexp = uvmexp;
1.1 deraadt 433: uptime = interval;
434: /*
435: * We round upward to avoid losing low-frequency events
436: * (i.e., >= 1 per interval but < 1 per second).
437: */
1.14 deraadt 438: halfuptime = uptime == 1 ? 0 : (uptime + 1) / 2;
1.1 deraadt 439: (void)sleep(interval);
440: }
441: }
442:
1.21 millert 443: void
1.72 deraadt 444: printhdr(void)
1.1 deraadt 445: {
1.62 mpech 446: int i;
1.1 deraadt 447:
1.67 ho 448: (void)printf(" procs memory page%*s", 20, "");
1.6 tholo 449: if (ndrives > 0)
1.79 tedu 450: (void)printf("%s %*straps cpu\n",
1.6 tholo 451: ((ndrives > 1) ? "disks" : "disk"),
1.64 deraadt 452: ((ndrives > 1) ? ndrives * 4 - 4 : 0), "");
1.1 deraadt 453: else
1.79 tedu 454: (void)printf("%*s traps cpu\n",
1.6 tholo 455: ndrives * 3, "");
456:
1.64 deraadt 457: (void)printf(" r b w avm fre flt re pi po fr sr ");
1.1 deraadt 458: for (i = 0; i < dk_ndrive; i++)
1.6 tholo 459: if (dk_select[i])
1.67 ho 460: (void)printf("%c%c%c ", dr_name[i][0],
1.64 deraadt 461: dr_name[i][1],
1.1 deraadt 462: dr_name[i][strlen(dr_name[i]) - 1]);
1.79 tedu 463: (void)printf(" int sys cs us sy id\n");
1.1 deraadt 464: hdrcnt = winlines - 2;
465: }
466:
467: /*
468: * Force a header to be prepended to the next output.
469: */
1.90 deraadt 470: /* ARGSUSED */
1.1 deraadt 471: void
1.78 deraadt 472: needhdr(int signo)
1.1 deraadt 473: {
474:
475: hdrcnt = 1;
476: }
477:
478: void
1.72 deraadt 479: dotimes(void)
1.1 deraadt 480: {
481: u_int pgintime, rectime;
1.52 angelos 482: int mib[2];
483: size_t size;
1.1 deraadt 484:
1.56 angelos 485: /* XXX Why are these set to 0 ? This doesn't look right. */
1.12 tholo 486: pgintime = 0;
487: rectime = 0;
1.56 angelos 488:
489: if (nlistf == NULL && memf == NULL) {
490: size = sizeof(struct uvmexp);
1.52 angelos 491: mib[0] = CTL_VM;
492: mib[1] = VM_UVMEXP;
493: if (sysctl(mib, 2, &uvmexp, &size, NULL, 0) < 0) {
1.56 angelos 494: warn("could not read vm.uvmexp");
495: bzero(&uvmexp, sizeof(struct uvmexp));
1.52 angelos 496: }
1.56 angelos 497: } else {
498: kread(X_UVMEXP, &uvmexp, sizeof(struct uvmexp));
1.52 angelos 499: }
500:
1.29 art 501: (void)printf("%u reactivates, %u total time (usec)\n",
502: uvmexp.pdreact, rectime);
1.89 miod 503: if (uvmexp.pdreact != 0)
504: (void)printf("average: %u usec / reclaim\n",
505: rectime / uvmexp.pdreact);
1.29 art 506: (void)printf("\n");
507: (void)printf("%u page ins, %u total time (msec)\n",
508: uvmexp.pageins, pgintime / 10);
1.89 miod 509: if (uvmexp.pageins != 0)
510: (void)printf("average: %8.1f msec / page in\n",
511: pgintime / (uvmexp.pageins * 10.0));
1.1 deraadt 512: }
513:
1.21 millert 514: int
1.72 deraadt 515: pct(long top, long bot)
1.1 deraadt 516: {
517: long ans;
518:
519: if (bot == 0)
520: return(0);
521: ans = (quad_t)top * 100 / bot;
522: return (ans);
523: }
524:
525: #define PCT(top, bot) pct((long)(top), (long)(bot))
526:
527: void
1.72 deraadt 528: dosum(void)
1.1 deraadt 529: {
530: struct nchstats nchstats;
531: long nchtotal;
1.52 angelos 532: size_t size;
533: int mib[2], nselcoll;
1.1 deraadt 534:
1.56 angelos 535: if (nlistf == NULL && memf == NULL) {
536: size = sizeof(struct uvmexp);
1.52 angelos 537: mib[0] = CTL_VM;
538: mib[1] = VM_UVMEXP;
539: if (sysctl(mib, 2, &uvmexp, &size, NULL, 0) < 0) {
1.56 angelos 540: warn("could not read vm.uvmexp");
541: bzero(&uvmexp, sizeof(struct uvmexp));
1.52 angelos 542: }
1.56 angelos 543: } else {
544: kread(X_UVMEXP, &uvmexp, sizeof(struct uvmexp));
1.52 angelos 545: }
546:
1.32 art 547: /* vm_page constants */
1.35 hugh 548: (void)printf("%11u bytes per page\n", uvmexp.pagesize);
1.32 art 549:
550: /* vm_page counters */
1.35 hugh 551: (void)printf("%11u pages managed\n", uvmexp.npages);
552: (void)printf("%11u pages free\n", uvmexp.free);
553: (void)printf("%11u pages active\n", uvmexp.active);
554: (void)printf("%11u pages inactive\n", uvmexp.inactive);
555: (void)printf("%11u pages being paged out\n", uvmexp.paging);
556: (void)printf("%11u pages wired\n", uvmexp.wired);
1.71 art 557: (void)printf("%11u pages zeroed\n", uvmexp.zeropages);
1.35 hugh 558: (void)printf("%11u pages reserved for pagedaemon\n",
1.48 art 559: uvmexp.reserve_pagedaemon);
1.35 hugh 560: (void)printf("%11u pages reserved for kernel\n",
1.48 art 561: uvmexp.reserve_kernel);
1.32 art 562:
563: /* swap */
1.35 hugh 564: (void)printf("%11u swap pages\n", uvmexp.swpages);
565: (void)printf("%11u swap pages in use\n", uvmexp.swpginuse);
566: (void)printf("%11u total anon's in system\n", uvmexp.nanon);
567: (void)printf("%11u free anon's\n", uvmexp.nfreeanon);
1.32 art 568:
569: /* stat counters */
1.35 hugh 570: (void)printf("%11u page faults\n", uvmexp.faults);
571: (void)printf("%11u traps\n", uvmexp.traps);
572: (void)printf("%11u interrupts\n", uvmexp.intrs);
573: (void)printf("%11u cpu context switches\n", uvmexp.swtch);
1.95 mickey 574: (void)printf("%11u fpu context switches\n", uvmexp.fpswtch);
1.35 hugh 575: (void)printf("%11u software interrupts\n", uvmexp.softs);
576: (void)printf("%11u syscalls\n", uvmexp.syscalls);
577: (void)printf("%11u pagein operations\n", uvmexp.pageins);
578: (void)printf("%11u swap ins\n", uvmexp.swapins);
579: (void)printf("%11u swap outs\n", uvmexp.swapouts);
580: (void)printf("%11u forks\n", uvmexp.forks);
581: (void)printf("%11u forks where vmspace is shared\n",
1.48 art 582: uvmexp.forks_sharevm);
1.97 pedro 583: (void)printf("%11u kernel map entries\n", uvmexp.kmapent);
1.32 art 584:
585: /* daemon counters */
1.64 deraadt 586: (void)printf("%11u number of times the pagedaemon woke up\n",
1.48 art 587: uvmexp.pdwoke);
1.35 hugh 588: (void)printf("%11u revolutions of the clock hand\n", uvmexp.pdrevs);
589: (void)printf("%11u pages freed by pagedaemon\n", uvmexp.pdfreed);
590: (void)printf("%11u pages scanned by pagedaemon\n", uvmexp.pdscans);
591: (void)printf("%11u pages reactivated by pagedaemon\n", uvmexp.pdreact);
592: (void)printf("%11u busy pages found by pagedaemon\n", uvmexp.pdbusy);
1.29 art 593:
1.56 angelos 594: if (nlistf == NULL && memf == NULL) {
1.52 angelos 595: size = sizeof(nchstats);
596: mib[0] = CTL_KERN;
597: mib[1] = KERN_NCHSTATS;
598: if (sysctl(mib, 2, &nchstats, &size, NULL, 0) < 0) {
1.56 angelos 599: warn("could not read kern.nchstats");
1.52 angelos 600: bzero(&nchstats, sizeof(nchstats));
601: }
1.56 angelos 602: } else {
603: kread(X_NCHSTATS, &nchstats, sizeof(nchstats));
1.52 angelos 604: }
605:
1.1 deraadt 606: nchtotal = nchstats.ncs_goodhits + nchstats.ncs_neghits +
607: nchstats.ncs_badhits + nchstats.ncs_falsehits +
608: nchstats.ncs_miss + nchstats.ncs_long;
1.35 hugh 609: (void)printf("%11ld total name lookups\n", nchtotal);
1.52 angelos 610: (void)printf("%11s cache hits (%d%% pos + %d%% neg) system %d%% "
611: "per-directory\n",
1.1 deraadt 612: "", PCT(nchstats.ncs_goodhits, nchtotal),
613: PCT(nchstats.ncs_neghits, nchtotal),
614: PCT(nchstats.ncs_pass2, nchtotal));
1.35 hugh 615: (void)printf("%11s deletions %d%%, falsehits %d%%, toolong %d%%\n", "",
1.1 deraadt 616: PCT(nchstats.ncs_badhits, nchtotal),
617: PCT(nchstats.ncs_falsehits, nchtotal),
618: PCT(nchstats.ncs_long, nchtotal));
1.52 angelos 619:
1.56 angelos 620: if (nlistf == NULL && memf == NULL) {
1.52 angelos 621: size = sizeof(nselcoll);
622: mib[0] = CTL_KERN;
623: mib[1] = KERN_NSELCOLL;
624: if (sysctl(mib, 2, &nselcoll, &size, NULL, 0) < 0) {
1.56 angelos 625: warn("could not read kern.nselcoll");
1.52 angelos 626: nselcoll = 0;
627: }
1.56 angelos 628: } else {
629: kread(X_NSELCOLL, &nselcoll, sizeof(nselcoll));
1.52 angelos 630: }
1.50 art 631: (void)printf("%11d select collisions\n", nselcoll);
1.1 deraadt 632: }
633:
634: void
1.72 deraadt 635: doforkst(void)
1.1 deraadt 636: {
637: struct forkstat fks;
1.52 angelos 638: size_t size;
639: int mib[2];
640:
1.56 angelos 641: if (nlistf == NULL && memf == NULL) {
1.52 angelos 642: size = sizeof(struct forkstat);
643: mib[0] = CTL_KERN;
644: mib[1] = KERN_FORKSTAT;
645: if (sysctl(mib, 2, &fks, &size, NULL, 0) < 0) {
1.56 angelos 646: warn("could not read kern.forkstat");
1.52 angelos 647: bzero(&fks, sizeof(struct forkstat));
648: }
1.56 angelos 649: } else {
650: kread(X_FORKSTAT, &fks, sizeof(struct forkstat));
1.52 angelos 651: }
1.1 deraadt 652:
653: (void)printf("%d forks, %d pages, average %.2f\n",
654: fks.cntfork, fks.sizfork, (double)fks.sizfork / fks.cntfork);
655: (void)printf("%d vforks, %d pages, average %.2f\n",
1.72 deraadt 656: fks.cntvfork, fks.sizvfork,
657: (double)fks.sizvfork / (fks.cntvfork ? fks.cntvfork : 1));
1.12 tholo 658: (void)printf("%d rforks, %d pages, average %.2f\n",
1.72 deraadt 659: fks.cntrfork, fks.sizrfork,
660: (double)fks.sizrfork / (fks.cntrfork ? fks.cntrfork : 1));
1.36 niklas 661: (void)printf("%d kthread creations, %d pages, average %.2f\n",
1.72 deraadt 662: fks.cntkthread, fks.sizkthread,
663: (double)fks.sizkthread / (fks.cntkthread ? fks.cntkthread : 1));
1.1 deraadt 664: }
665:
666: void
1.72 deraadt 667: dkstats(void)
1.1 deraadt 668: {
1.62 mpech 669: int dn, state;
1.1 deraadt 670: double etime;
671:
1.6 tholo 672: /* Calculate disk stat deltas. */
673: dkswap();
1.1 deraadt 674: etime = 0;
675: for (state = 0; state < CPUSTATES; ++state) {
1.6 tholo 676: etime += cur.cp_time[state];
1.1 deraadt 677: }
678: if (etime == 0)
679: etime = 1;
680: etime /= hz;
1.84 deraadt 681: etime /= ncpu;
1.1 deraadt 682: for (dn = 0; dn < dk_ndrive; ++dn) {
1.6 tholo 683: if (!dk_select[dn])
1.1 deraadt 684: continue;
1.82 tedu 685: (void)printf("%3.0f ",
686: (cur.dk_rxfer[dn] + cur.dk_rxfer[dn]) / etime);
1.1 deraadt 687: }
688: }
689:
690: void
1.72 deraadt 691: cpustats(void)
1.1 deraadt 692: {
1.62 mpech 693: int state;
1.1 deraadt 694: double pct, total;
695:
696: total = 0;
697: for (state = 0; state < CPUSTATES; ++state)
1.6 tholo 698: total += cur.cp_time[state];
1.1 deraadt 699: if (total)
700: pct = 100 / total;
701: else
702: pct = 0;
1.6 tholo 703: (void)printf("%2.0f ", (cur.cp_time[CP_USER] + cur.cp_time[CP_NICE]) * pct);
704: (void)printf("%2.0f ", (cur.cp_time[CP_SYS] + cur.cp_time[CP_INTR]) * pct);
705: (void)printf("%2.0f", cur.cp_time[CP_IDLE] * pct);
1.1 deraadt 706: }
707:
708: void
1.72 deraadt 709: dointr(void)
1.74 art 710: {
711: struct device dev;
712:
713: time_t uptime;
1.90 deraadt 714: u_int64_t inttotal;
1.74 art 715: int nintr;
716: char intrname[128];
717: int mib[4];
718: size_t siz;
719: int i;
720:
1.93 miod 721: if (nlistf != NULL || memf != NULL) {
722: errx(1,
723: "interrupt statistics are only available on live kernels");
724: }
725:
1.74 art 726: uptime = getuptime();
727:
728: mib[0] = CTL_KERN;
729: mib[1] = KERN_INTRCNT;
730: mib[2] = KERN_INTRCNT_NUM;
731: siz = sizeof(nintr);
732: if (sysctl(mib, 3, &nintr, &siz, NULL, 0) < 0) {
733: warnx("could not read kern.intrcnt.nintrcnt");
734: return;
735: }
736:
1.91 deraadt 737: (void)printf("%-16s %20s %8s\n", "interrupt", "total", "rate");
1.87 aaron 738:
1.74 art 739: inttotal = 0;
740: for (i = 0; i < nintr; i++) {
1.87 aaron 741: char name[128];
1.90 deraadt 742: u_quad_t cnt;
1.87 aaron 743: int vector;
1.74 art 744:
745: mib[0] = CTL_KERN;
746: mib[1] = KERN_INTRCNT;
747: mib[2] = KERN_INTRCNT_NAME;
748: mib[3] = i;
1.87 aaron 749: siz = sizeof(name);
750: if (sysctl(mib, 4, name, &siz, NULL, 0) < 0) {
1.74 art 751: warnx("could not read kern.intrcnt.name.%d", i);
1.87 aaron 752: return;
753: }
754:
755: mib[0] = CTL_KERN;
756: mib[1] = KERN_INTRCNT;
757: mib[2] = KERN_INTRCNT_VECTOR;
758: mib[3] = i;
759: siz = sizeof(vector);
760: if (sysctl(mib, 4, &vector, &siz, NULL, 0) < 0) {
761: strlcpy(intrname, name, sizeof(intrname));
762: } else {
763: snprintf(intrname, sizeof(intrname), "irq%d/%s",
764: vector, name);
1.74 art 765: }
766:
767: mib[0] = CTL_KERN;
768: mib[1] = KERN_INTRCNT;
769: mib[2] = KERN_INTRCNT_CNT;
770: mib[3] = i;
771: siz = sizeof(cnt);
772: if (sysctl(mib, 4, &cnt, &siz, NULL, 0) < 0) {
1.75 grange 773: warnx("could not read kern.intrcnt.cnt.%d", i);
1.90 deraadt 774: return;
1.74 art 775: }
1.90 deraadt 776:
1.87 aaron 777: if (cnt || zflag)
1.91 deraadt 778: (void)printf("%-16.16s %20llu %8llu\n", intrname,
1.90 deraadt 779: cnt, cnt / uptime);
1.74 art 780: inttotal += cnt;
781: }
782:
1.91 deraadt 783: (void)printf("%-16s %20llu %8llu\n", "Total", inttotal,
1.90 deraadt 784: inttotal / uptime);
1.1 deraadt 785: }
786:
787: /*
788: * These names are defined in <sys/malloc.h>.
789: */
790: char *kmemnames[] = INITKMEMNAMES;
791:
792: void
1.72 deraadt 793: domem(void)
1.1 deraadt 794: {
1.62 mpech 795: struct kmembuckets *kp;
796: struct kmemstats *ks;
797: int i, j;
1.1 deraadt 798: int len, size, first;
1.50 art 799: u_long totuse = 0, totfree = 0;
800: quad_t totreq = 0;
1.1 deraadt 801: char *name;
802: struct kmemstats kmemstats[M_LAST];
803: struct kmembuckets buckets[MINBUCKET + 16];
1.50 art 804: int mib[4];
805: size_t siz;
806: char buf[BUFSIZ], *bufp, *ap;
807:
808: if (memf == NULL && nlistf == NULL) {
1.53 deraadt 809: mib[0] = CTL_KERN;
1.50 art 810: mib[1] = KERN_MALLOCSTATS;
811: mib[2] = KERN_MALLOC_BUCKETS;
812: siz = sizeof(buf);
813: if (sysctl(mib, 3, buf, &siz, NULL, 0) < 0) {
1.56 angelos 814: warnx("could not read kern.malloc.buckets");
1.50 art 815: return;
816: }
817:
818: bufp = buf;
819: mib[2] = KERN_MALLOC_BUCKET;
820: siz = sizeof(struct kmembuckets);
821: i = 0;
822: while ((ap = strsep(&bufp, ",")) != NULL) {
1.53 deraadt 823: mib[3] = atoi(ap);
1.50 art 824:
825: if (sysctl(mib, 4, &buckets[MINBUCKET + i], &siz,
1.53 deraadt 826: NULL, 0) < 0) {
1.56 angelos 827: warn("could not read kern.malloc.bucket.%d", mib[3]);
1.50 art 828: return;
829: }
830: i++;
831: }
832: } else {
1.53 deraadt 833: kread(X_KMEMBUCKETS, buckets, sizeof(buckets));
1.50 art 834: }
1.1 deraadt 835:
1.18 kstailey 836: for (first = 1, i = MINBUCKET, kp = &buckets[i]; i < MINBUCKET + 16;
837: i++, kp++) {
1.65 art 838: if (kp->kb_calls == 0 && !verbose)
1.1 deraadt 839: continue;
1.18 kstailey 840: if (first) {
841: (void)printf("Memory statistics by bucket size\n");
842: (void)printf(
1.50 art 843: " Size In Use Free Requests HighWater Couldfree\n");
1.18 kstailey 844: first = 0;
845: }
1.1 deraadt 846: size = 1 << i;
1.60 art 847: (void)printf("%8d %8llu %6llu %18llu %7llu %10llu\n", size,
848: (unsigned long long)(kp->kb_total - kp->kb_totalfree),
849: (unsigned long long)kp->kb_totalfree,
850: (unsigned long long)kp->kb_calls,
851: (unsigned long long)kp->kb_highwat,
852: (unsigned long long)kp->kb_couldfree);
1.1 deraadt 853: totfree += size * kp->kb_totalfree;
1.18 kstailey 854: }
855:
856: /*
857: * If kmem statistics are not being gathered by the kernel,
858: * first will still be 1.
859: */
860: if (first) {
861: printf(
862: "Kmem statistics are not being gathered by the kernel.\n");
863: return;
1.1 deraadt 864: }
865:
1.52 angelos 866: if (memf == NULL && nlistf == NULL) {
867: bzero(kmemstats, sizeof(kmemstats));
868: for (i = 0; i < M_LAST; i++) {
1.53 deraadt 869: mib[0] = CTL_KERN;
1.52 angelos 870: mib[1] = KERN_MALLOCSTATS;
871: mib[2] = KERN_MALLOC_KMEMSTATS;
872: mib[3] = i;
873: siz = sizeof(struct kmemstats);
874:
875: /*
876: * Skip errors -- these are presumed to be unallocated
877: * entries.
878: */
879: if (sysctl(mib, 4, &kmemstats[i], &siz, NULL, 0) < 0)
880: continue;
881: }
882: } else {
883: kread(X_KMEMSTAT, kmemstats, sizeof(kmemstats));
884: }
885:
1.1 deraadt 886: (void)printf("\nMemory usage type by bucket size\n");
887: (void)printf(" Size Type(s)\n");
888: kp = &buckets[MINBUCKET];
889: for (j = 1 << MINBUCKET; j < 1 << (MINBUCKET + 16); j <<= 1, kp++) {
890: if (kp->kb_calls == 0)
891: continue;
892: first = 1;
893: len = 8;
894: for (i = 0, ks = &kmemstats[0]; i < M_LAST; i++, ks++) {
895: if (ks->ks_calls == 0)
896: continue;
897: if ((ks->ks_size & j) == 0)
898: continue;
899: name = kmemnames[i] ? kmemnames[i] : "undefined";
900: len += 2 + strlen(name);
901: if (first)
902: printf("%8d %s", j, name);
903: else
904: printf(",");
905: if (len >= 80) {
906: printf("\n\t ");
907: len = 10 + strlen(name);
908: }
909: if (!first)
910: printf(" %s", name);
911: first = 0;
912: }
913: printf("\n");
914: }
915:
916: (void)printf(
1.26 deraadt 917: "\nMemory statistics by type Type Kern\n");
1.1 deraadt 918: (void)printf(
1.26 deraadt 919: " Type InUse MemUse HighUse Limit Requests Limit Limit Size(s)\n");
1.1 deraadt 920: for (i = 0, ks = &kmemstats[0]; i < M_LAST; i++, ks++) {
921: if (ks->ks_calls == 0)
922: continue;
1.24 mickey 923: (void)printf("%14s%6ld%6ldK%7ldK%6ldK%9ld%5u%6u",
1.1 deraadt 924: kmemnames[i] ? kmemnames[i] : "undefined",
925: ks->ks_inuse, (ks->ks_memuse + 1023) / 1024,
926: (ks->ks_maxused + 1023) / 1024,
927: (ks->ks_limit + 1023) / 1024, ks->ks_calls,
928: ks->ks_limblocks, ks->ks_mapblocks);
929: first = 1;
930: for (j = 1 << MINBUCKET; j < 1 << (MINBUCKET + 16); j <<= 1) {
931: if ((ks->ks_size & j) == 0)
932: continue;
933: if (first)
934: printf(" %d", j);
935: else
936: printf(",%d", j);
937: first = 0;
938: }
939: printf("\n");
940: totuse += ks->ks_memuse;
941: totreq += ks->ks_calls;
942: }
943: (void)printf("\nMemory Totals: In Use Free Requests\n");
1.50 art 944: (void)printf(" %7luK %6luK %8qu\n",
1.1 deraadt 945: (totuse + 1023) / 1024, (totfree + 1023) / 1024, totreq);
946: }
947:
1.54 art 948: static void
949: print_pool(struct pool *pp, char *name)
950: {
951: static int first = 1;
952: int ovflw;
953: char maxp[32];
954:
955: if (first) {
956: (void)printf("Memory resource pool statistics\n");
957: (void)printf(
958: "%-11s%5s%9s%5s%9s%6s%6s%6s%6s%6s%6s%5s\n",
959: "Name",
960: "Size",
961: "Requests",
962: "Fail",
963: "Releases",
964: "Pgreq",
965: "Pgrel",
966: "Npage",
967: "Hiwat",
968: "Minpg",
969: "Maxpg",
970: "Idle");
971: first = 0;
972: }
1.65 art 973:
974: /* Skip unused pools unless verbose output. */
975: if (pp->pr_nget == 0 && !verbose)
976: return;
977:
1.54 art 978: if (pp->pr_maxpages == UINT_MAX)
1.69 deraadt 979: snprintf(maxp, sizeof maxp, "inf");
1.54 art 980: else
1.69 deraadt 981: snprintf(maxp, sizeof maxp, "%u", pp->pr_maxpages);
1.54 art 982: /*
983: * Print single word. `ovflow' is number of characters didn't fit
984: * on the last word. `fmt' is a format string to print this word.
985: * It must contain asterisk for field width. `width' is a width
986: * occupied by this word. `fixed' is a number of constant chars in
987: * `fmt'. `val' is a value to be printed using format string `fmt'.
988: */
989: #define PRWORD(ovflw, fmt, width, fixed, val) do { \
990: (ovflw) += printf((fmt), \
991: (width) - (fixed) - (ovflw) > 0 ? \
992: (width) - (fixed) - (ovflw) : 0, \
993: (val)) - (width); \
994: if ((ovflw) < 0) \
995: (ovflw) = 0; \
996: } while (/* CONSTCOND */0)
997:
998: ovflw = 0;
999: PRWORD(ovflw, "%-*s", 11, 0, name);
1000: PRWORD(ovflw, " %*u", 5, 1, pp->pr_size);
1001: PRWORD(ovflw, " %*lu", 9, 1, pp->pr_nget);
1002: PRWORD(ovflw, " %*lu", 5, 1, pp->pr_nfail);
1003: PRWORD(ovflw, " %*lu", 9, 1, pp->pr_nput);
1004: PRWORD(ovflw, " %*lu", 6, 1, pp->pr_npagealloc);
1005: PRWORD(ovflw, " %*lu", 6, 1, pp->pr_npagefree);
1006: PRWORD(ovflw, " %*d", 6, 1, pp->pr_npages);
1007: PRWORD(ovflw, " %*d", 6, 1, pp->pr_hiwat);
1008: PRWORD(ovflw, " %*d", 6, 1, pp->pr_minpages);
1009: PRWORD(ovflw, " %*s", 6, 1, maxp);
1010: PRWORD(ovflw, " %*lu\n", 5, 1, pp->pr_nidle);
1011: }
1012:
1.55 art 1013: static void dopool_kvm(void);
1014: static void dopool_sysctl(void);
1015:
1.48 art 1016: void
1017: dopool(void)
1018: {
1.55 art 1019: if (nlistf == NULL && memf == NULL)
1020: dopool_sysctl();
1021: else
1022: dopool_kvm();
1023: }
1024:
1025: void
1026: dopool_sysctl(void)
1027: {
1.63 art 1028: long total = 0, inuse = 0;
1.55 art 1029: struct pool pool;
1030: size_t size;
1031: int mib[4];
1.98 ! mickey 1032: int npools, i, kmfp;
1.55 art 1033:
1034: mib[0] = CTL_KERN;
1035: mib[1] = KERN_POOL;
1036: mib[2] = KERN_POOL_NPOOLS;
1037: size = sizeof(npools);
1038: if (sysctl(mib, 3, &npools, &size, NULL, 0) < 0) {
1.92 pedro 1039: warn("can't figure out number of pools in kernel");
1.55 art 1040: return;
1041: }
1042:
1043: for (i = 1; npools; i++) {
1044: char name[32];
1045:
1046: mib[0] = CTL_KERN;
1047: mib[1] = KERN_POOL;
1048: mib[2] = KERN_POOL_POOL;
1049: mib[3] = i;
1050: size = sizeof(struct pool);
1051: if (sysctl(mib, 4, &pool, &size, NULL, 0) < 0) {
1052: if (errno == ENOENT)
1053: continue;
1.92 pedro 1054: warn("error getting pool");
1.55 art 1055: return;
1056: }
1057: npools--;
1058: mib[2] = KERN_POOL_NAME;
1059: size = sizeof(name);
1060: if (sysctl(mib, 4, &name, &size, NULL, 0) < 0) {
1.92 pedro 1061: warn("error getting pool name");
1.55 art 1062: return;
1063: }
1064: print_pool(&pool, name);
1.63 art 1065:
1066: inuse += (pool.pr_nget - pool.pr_nput) * pool.pr_size;
1067: total += pool.pr_npages * getpagesize(); /* XXX */
1.55 art 1068: }
1.63 art 1069:
1070: inuse /= 1024;
1071: total /= 1024;
1.98 ! mickey 1072: if (!kreado(namelist2, &kmfp, sizeof(kmfp)))
! 1073: total += kmfp * (getpagesize() / 1024);
1.63 art 1074: printf("\nIn use %ldK, total allocated %ldK; utilization %.1f%%\n",
1075: inuse, total, (double)(100 * inuse) / total);
1.55 art 1076: }
1077:
1078: void
1079: dopool_kvm(void)
1080: {
1.48 art 1081: long addr;
1082: long total = 0, inuse = 0;
1083: TAILQ_HEAD(,pool) pool_head;
1084: struct pool pool, *pp = &pool;
1.98 ! mickey 1085: int kmfp;
1.48 art 1086:
1087: kread(X_POOLHEAD, &pool_head, sizeof(pool_head));
1088: addr = (long)TAILQ_FIRST(&pool_head);
1089:
1.55 art 1090: while (addr != 0) {
1.54 art 1091: char name[32];
1.56 angelos 1092:
1.48 art 1093: if (kvm_read(kd, addr, (void *)pp, sizeof *pp) != sizeof *pp) {
1094: (void)fprintf(stderr,
1095: "vmstat: pool chain trashed: %s\n",
1096: kvm_geterr(kd));
1097: exit(1);
1098: }
1099: if (kvm_read(kd, (long)pp->pr_wchan, name, sizeof name) < 0) {
1100: (void)fprintf(stderr,
1101: "vmstat: pool name trashed: %s\n",
1102: kvm_geterr(kd));
1103: exit(1);
1104: }
1.56 angelos 1105:
1.48 art 1106: name[31] = '\0';
1107:
1.54 art 1108: print_pool(pp, name);
1.48 art 1109:
1110: inuse += (pp->pr_nget - pp->pr_nput) * pp->pr_size;
1.63 art 1111: total += pp->pr_npages * getpagesize(); /* XXX */
1.56 angelos 1112:
1.48 art 1113: addr = (long)TAILQ_NEXT(pp, pr_poollist);
1114: }
1115:
1116: inuse /= 1024;
1117: total /= 1024;
1.98 ! mickey 1118: if (!kreado(namelist2, &kmfp, sizeof(kmfp)))
! 1119: total += kmfp * (getpagesize() / 1024);
1.48 art 1120: printf("\nIn use %ldK, total allocated %ldK; utilization %.1f%%\n",
1121: inuse, total, (double)(100 * inuse) / total);
1122: }
1123:
1.1 deraadt 1124: /*
1125: * kread reads something from the kernel, given its nlist index.
1126: */
1127: void
1.72 deraadt 1128: kread(int nlx, void *addr, size_t size)
1.1 deraadt 1129: {
1130: char *sym;
1131:
1132: if (namelist[nlx].n_type == 0 || namelist[nlx].n_value == 0) {
1133: sym = namelist[nlx].n_name;
1134: if (*sym == '_')
1135: ++sym;
1.50 art 1136: errx(1, "symbol %s not defined", sym);
1.1 deraadt 1137: }
1138: if (kvm_read(kd, namelist[nlx].n_value, addr, size) != size) {
1139: sym = namelist[nlx].n_name;
1140: if (*sym == '_')
1141: ++sym;
1.50 art 1142: errx(1, "%s: %s", sym, kvm_geterr(kd));
1.1 deraadt 1143: }
1.98 ! mickey 1144: }
! 1145:
! 1146: /*
! 1147: * kread reads something from the kernel, given its nlist index.
! 1148: */
! 1149: int
! 1150: kreado(struct nlist *nl, void *addr, size_t size)
! 1151: {
! 1152: char *sym;
! 1153: int c;
! 1154:
! 1155: if ((c = kvm_nlist(kd, nl)) != 0)
! 1156: return (c);
! 1157:
! 1158: if (nl->n_type == 0 || nl->n_value == 0)
! 1159: return (-1);
! 1160:
! 1161: if (kvm_read(kd, nl->n_value, addr, size) != size)
! 1162: return (-1);
! 1163:
! 1164: return (0);
1.1 deraadt 1165: }
1166:
1167: void
1.72 deraadt 1168: usage(void)
1.1 deraadt 1169: {
1.88 jmc 1170: (void)fprintf(stderr, "usage: %s [-fimstvz] [-c count] [-M core] "
1.50 art 1171: "[-N system] [-w wait] [disks]\n", __progname);
1.1 deraadt 1172: exit(1);
1173: }