xref: /csrg-svn/lib/libkvm/kvm_getloadavg.c (revision 59367)
1*59367Sbostic /*-
2*59367Sbostic  * Copyright (c) 1993 The Regents of the University of California.
3*59367Sbostic  * All rights reserved.
4*59367Sbostic  *
5*59367Sbostic  * %sccs.include.redist.c%
6*59367Sbostic  */
7*59367Sbostic 
8*59367Sbostic #if defined(LIBC_SCCS) && !defined(lint)
9*59367Sbostic static char sccsid[] = "@(#)kvm_getloadavg.c	5.1 (Berkeley) 04/27/93";
10*59367Sbostic #endif /* LIBC_SCCS and not lint */
11*59367Sbostic 
12*59367Sbostic #include <sys/param.h>
13*59367Sbostic #include <sys/time.h>
14*59367Sbostic #include <sys/resource.h>
15*59367Sbostic #include <sys/proc.h>
16*59367Sbostic #include <sys/sysctl.h>
17*59367Sbostic #include <vm/vm_param.h>
18*59367Sbostic 
19*59367Sbostic #include <db.h>
20*59367Sbostic #include <fcntl.h>
21*59367Sbostic #include <limits.h>
22*59367Sbostic #include <nlist.h>
23*59367Sbostic #include <kvm.h>
24*59367Sbostic 
25*59367Sbostic #include "kvm_private.h"
26*59367Sbostic 
27*59367Sbostic static struct nlist nl[] = {
28*59367Sbostic 	{ "_averunnable" },
29*59367Sbostic #define	X_AVERUNNABLE	0
30*59367Sbostic 	{ "_fscale" },
31*59367Sbostic #define	X_FSCALE	1
32*59367Sbostic 	{ "" },
33*59367Sbostic };
34*59367Sbostic 
35*59367Sbostic /*
36*59367Sbostic  * kvm_getloadavg() -- Get system load averages, from live or dead kernels.
37*59367Sbostic  *
38*59367Sbostic  * Put `nelem' samples into `loadavg' array.
39*59367Sbostic  * Return number of samples retrieved, or -1 on error.
40*59367Sbostic  */
41*59367Sbostic int
42*59367Sbostic kvm_getloadavg(kd, loadavg, nelem)
43*59367Sbostic 	kvm_t *kd;
44*59367Sbostic 	double loadavg[];
45*59367Sbostic 	int nelem;
46*59367Sbostic {
47*59367Sbostic 	struct loadavg loadinfo;
48*59367Sbostic 	struct nlist *p;
49*59367Sbostic 	int fscale, i;
50*59367Sbostic 
51*59367Sbostic 	if (ISALIVE(kd))
52*59367Sbostic 		return (getloadavg(loadavg, nelem));
53*59367Sbostic 
54*59367Sbostic 	if (kvm_nlist(kd, nl) != 0) {
55*59367Sbostic 		for (p = nl; p->n_type != 0; ++p);
56*59367Sbostic 		_kvm_err(kd, kd->program,
57*59367Sbostic 		    "%s: no such symbol", p->n_name);
58*59367Sbostic 		return (-1);
59*59367Sbostic 	}
60*59367Sbostic 
61*59367Sbostic #define KREAD(kd, addr, obj) \
62*59367Sbostic 	(kvm_read(kd, addr, (char *)(obj), sizeof(*obj)) != sizeof(*obj))
63*59367Sbostic 	if (KREAD(kd, nl[X_AVERUNNABLE].n_value, &loadinfo)) {
64*59367Sbostic 		_kvm_err(kd, kd->program, "can't read averunnable");
65*59367Sbostic 		return (-1);
66*59367Sbostic 	}
67*59367Sbostic 
68*59367Sbostic 	/*
69*59367Sbostic 	 * Old kernels have fscale separately; if not found assume
70*59367Sbostic 	 * running new format.
71*59367Sbostic 	 */
72*59367Sbostic 	if (!KREAD(kd, nl[X_FSCALE].n_value, &fscale))
73*59367Sbostic 		loadinfo.fscale = fscale;
74*59367Sbostic 
75*59367Sbostic 	nelem = MIN(nelem, sizeof(loadinfo.ldavg) / sizeof(fixpt_t));
76*59367Sbostic 	for (i = 0; i < nelem; i++)
77*59367Sbostic 		loadavg[i] = (double) loadinfo.ldavg[i] / loadinfo.fscale;
78*59367Sbostic 	return (nelem);
79*59367Sbostic }
80