init_sysctl.c revision 1.66
1/*	$NetBSD: init_sysctl.c,v 1.66 2006/04/14 13:09:06 blymn Exp $ */
2
3/*-
4 * Copyright (c) 2003 The NetBSD Foundation, Inc.
5 * All rights reserved.
6 *
7 * This code is derived from software contributed to The NetBSD Foundation
8 * by Andrew Brown.
9 *
10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions
12 * are met:
13 * 1. Redistributions of source code must retain the above copyright
14 *    notice, this list of conditions and the following disclaimer.
15 * 2. Redistributions in binary form must reproduce the above copyright
16 *    notice, this list of conditions and the following disclaimer in the
17 *    documentation and/or other materials provided with the distribution.
18 * 3. All advertising materials mentioning features or use of this software
19 *    must display the following acknowledgement:
20 *      This product includes software developed by the NetBSD
21 *      Foundation, Inc. and its contributors.
22 * 4. Neither the name of The NetBSD Foundation nor the names of its
23 *    contributors may be used to endorse or promote products derived
24 *    from this software without specific prior written permission.
25 *
26 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
27 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
28 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
29 * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
30 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
31 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
32 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
33 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
34 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
35 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
36 * POSSIBILITY OF SUCH DAMAGE.
37 */
38
39#include <sys/cdefs.h>
40__KERNEL_RCSID(0, "$NetBSD: init_sysctl.c,v 1.66 2006/04/14 13:09:06 blymn Exp $");
41
42#include "opt_sysv.h"
43#include "opt_multiprocessor.h"
44#include "opt_posix.h"
45#include "opt_verified_exec.h"
46#include "pty.h"
47#include "rnd.h"
48
49#include <sys/types.h>
50#include <sys/param.h>
51#include <sys/sysctl.h>
52#include <sys/errno.h>
53#include <sys/systm.h>
54#include <sys/kernel.h>
55#include <sys/unistd.h>
56#include <sys/disklabel.h>
57#include <sys/rnd.h>
58#include <sys/vnode.h>
59#include <sys/mount.h>
60#include <sys/namei.h>
61#include <sys/msgbuf.h>
62#include <dev/cons.h>
63#include <sys/socketvar.h>
64#include <sys/file.h>
65#include <sys/filedesc.h>
66#include <sys/tty.h>
67#include <sys/malloc.h>
68#include <sys/resource.h>
69#include <sys/resourcevar.h>
70#include <sys/exec.h>
71#include <sys/conf.h>
72#include <sys/device.h>
73#ifdef VERIFIED_EXEC
74#define	VERIEXEC_NEED_NODE
75#include <sys/verified_exec.h>
76#endif /* VERIFIED_EXEC */
77#include <sys/stat.h>
78
79#if defined(SYSVMSG) || defined(SYSVSEM) || defined(SYSVSHM)
80#include <sys/ipc.h>
81#endif
82#ifdef SYSVMSG
83#include <sys/msg.h>
84#endif
85#ifdef SYSVSEM
86#include <sys/sem.h>
87#endif
88#ifdef SYSVSHM
89#include <sys/shm.h>
90#endif
91
92#include <machine/cpu.h>
93
94/* XXX this should not be here */
95int security_curtain = 0;
96int security_setidcore_dump;
97char security_setidcore_path[MAXPATHLEN] = "/var/crash/%n.core";
98uid_t security_setidcore_owner = 0;
99gid_t security_setidcore_group = 0;
100mode_t security_setidcore_mode = (S_IRUSR|S_IWUSR);
101
102/*
103 * try over estimating by 5 procs/lwps
104 */
105#define KERN_PROCSLOP	(5 * sizeof(struct kinfo_proc))
106#define KERN_LWPSLOP	(5 * sizeof(struct kinfo_lwp))
107
108#ifndef MULTIPROCESSOR
109#define	sysctl_ncpus()	(1)
110#else /* MULTIPROCESSOR */
111#ifndef CPU_INFO_FOREACH
112#define CPU_INFO_ITERATOR int
113#define CPU_INFO_FOREACH(cii, ci) cii = 0, ci = curcpu(); ci != NULL; ci = NULL
114#endif
115static int
116sysctl_ncpus(void)
117{
118	struct cpu_info *ci;
119	CPU_INFO_ITERATOR cii;
120
121	int ncpus = 0;
122	for (CPU_INFO_FOREACH(cii, ci))
123		ncpus++;
124	return (ncpus);
125}
126#endif /* MULTIPROCESSOR */
127
128#ifdef DIAGNOSTIC
129static int sysctl_kern_trigger_panic(SYSCTLFN_PROTO);
130#endif
131static int sysctl_kern_maxvnodes(SYSCTLFN_PROTO);
132static int sysctl_kern_rtc_offset(SYSCTLFN_PROTO);
133static int sysctl_kern_maxproc(SYSCTLFN_PROTO);
134static int sysctl_kern_securelevel(SYSCTLFN_PROTO);
135static int sysctl_kern_hostid(SYSCTLFN_PROTO);
136static int sysctl_setlen(SYSCTLFN_PROTO);
137static int sysctl_kern_clockrate(SYSCTLFN_PROTO);
138static int sysctl_kern_file(SYSCTLFN_PROTO);
139static int sysctl_kern_autonice(SYSCTLFN_PROTO);
140static int sysctl_msgbuf(SYSCTLFN_PROTO);
141static int sysctl_kern_defcorename(SYSCTLFN_PROTO);
142static int sysctl_kern_cptime(SYSCTLFN_PROTO);
143#if defined(SYSVMSG) || defined(SYSVSEM) || defined(SYSVSHM)
144static int sysctl_kern_sysvipc(SYSCTLFN_PROTO);
145#endif /* defined(SYSVMSG) || defined(SYSVSEM) || defined(SYSVSHM) */
146#if NPTY > 0
147static int sysctl_kern_maxptys(SYSCTLFN_PROTO);
148#endif /* NPTY > 0 */
149static int sysctl_kern_sbmax(SYSCTLFN_PROTO);
150static int sysctl_kern_urnd(SYSCTLFN_PROTO);
151static int sysctl_kern_lwp(SYSCTLFN_PROTO);
152static int sysctl_kern_forkfsleep(SYSCTLFN_PROTO);
153static int sysctl_kern_root_partition(SYSCTLFN_PROTO);
154static int sysctl_kern_drivers(SYSCTLFN_PROTO);
155static int sysctl_kern_file2(SYSCTLFN_PROTO);
156#ifdef VERIFIED_EXEC
157static int sysctl_kern_veriexec(SYSCTLFN_PROTO);
158#endif
159static int sysctl_security_setidcore(SYSCTLFN_PROTO);
160static int sysctl_security_setidcorename(SYSCTLFN_PROTO);
161static int sysctl_kern_cpid(SYSCTLFN_PROTO);
162static int sysctl_doeproc(SYSCTLFN_PROTO);
163static int sysctl_kern_proc_args(SYSCTLFN_PROTO);
164static int sysctl_hw_usermem(SYSCTLFN_PROTO);
165static int sysctl_hw_cnmagic(SYSCTLFN_PROTO);
166static int sysctl_hw_ncpu(SYSCTLFN_PROTO);
167
168static void fill_kproc2(struct proc *, struct kinfo_proc2 *);
169static void fill_lwp(struct lwp *l, struct kinfo_lwp *kl);
170static void fill_file(struct kinfo_file *, const struct file *, struct proc *,
171		      int);
172
173/*
174 * ********************************************************************
175 * section 1: setup routines
176 * ********************************************************************
177 * these functions are stuffed into a link set for sysctl setup
178 * functions.  they're never called or referenced from anywhere else.
179 * ********************************************************************
180 */
181
182/*
183 * sets up the base nodes...
184 */
185SYSCTL_SETUP(sysctl_root_setup, "sysctl base setup")
186{
187
188	sysctl_createv(clog, 0, NULL, NULL,
189		       CTLFLAG_PERMANENT,
190		       CTLTYPE_NODE, "kern",
191		       SYSCTL_DESCR("High kernel"),
192		       NULL, 0, NULL, 0,
193		       CTL_KERN, CTL_EOL);
194	sysctl_createv(clog, 0, NULL, NULL,
195		       CTLFLAG_PERMANENT,
196		       CTLTYPE_NODE, "vm",
197		       SYSCTL_DESCR("Virtual memory"),
198		       NULL, 0, NULL, 0,
199		       CTL_VM, CTL_EOL);
200	sysctl_createv(clog, 0, NULL, NULL,
201		       CTLFLAG_PERMANENT,
202		       CTLTYPE_NODE, "vfs",
203		       SYSCTL_DESCR("Filesystem"),
204		       NULL, 0, NULL, 0,
205		       CTL_VFS, CTL_EOL);
206	sysctl_createv(clog, 0, NULL, NULL,
207		       CTLFLAG_PERMANENT,
208		       CTLTYPE_NODE, "net",
209		       SYSCTL_DESCR("Networking"),
210		       NULL, 0, NULL, 0,
211		       CTL_NET, CTL_EOL);
212	sysctl_createv(clog, 0, NULL, NULL,
213		       CTLFLAG_PERMANENT,
214		       CTLTYPE_NODE, "debug",
215		       SYSCTL_DESCR("Debugging"),
216		       NULL, 0, NULL, 0,
217		       CTL_DEBUG, CTL_EOL);
218	sysctl_createv(clog, 0, NULL, NULL,
219		       CTLFLAG_PERMANENT,
220		       CTLTYPE_NODE, "hw",
221		       SYSCTL_DESCR("Generic CPU, I/O"),
222		       NULL, 0, NULL, 0,
223		       CTL_HW, CTL_EOL);
224	sysctl_createv(clog, 0, NULL, NULL,
225		       CTLFLAG_PERMANENT,
226		       CTLTYPE_NODE, "machdep",
227		       SYSCTL_DESCR("Machine dependent"),
228		       NULL, 0, NULL, 0,
229		       CTL_MACHDEP, CTL_EOL);
230	/*
231	 * this node is inserted so that the sysctl nodes in libc can
232	 * operate.
233	 */
234	sysctl_createv(clog, 0, NULL, NULL,
235		       CTLFLAG_PERMANENT,
236		       CTLTYPE_NODE, "user",
237		       SYSCTL_DESCR("User-level"),
238		       NULL, 0, NULL, 0,
239		       CTL_USER, CTL_EOL);
240	sysctl_createv(clog, 0, NULL, NULL,
241		       CTLFLAG_PERMANENT,
242		       CTLTYPE_NODE, "ddb",
243		       SYSCTL_DESCR("In-kernel debugger"),
244		       NULL, 0, NULL, 0,
245		       CTL_DDB, CTL_EOL);
246	sysctl_createv(clog, 0, NULL, NULL,
247		       CTLFLAG_PERMANENT,
248		       CTLTYPE_NODE, "proc",
249		       SYSCTL_DESCR("Per-process"),
250		       NULL, 0, NULL, 0,
251		       CTL_PROC, CTL_EOL);
252	sysctl_createv(clog, 0, NULL, NULL,
253		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
254		       CTLTYPE_NODE, "vendor",
255		       SYSCTL_DESCR("Vendor specific"),
256		       NULL, 0, NULL, 0,
257		       CTL_VENDOR, CTL_EOL);
258	sysctl_createv(clog, 0, NULL, NULL,
259		       CTLFLAG_PERMANENT,
260		       CTLTYPE_NODE, "emul",
261		       SYSCTL_DESCR("Emulation settings"),
262		       NULL, 0, NULL, 0,
263		       CTL_EMUL, CTL_EOL);
264	sysctl_createv(clog, 0, NULL, NULL,
265		       CTLFLAG_PERMANENT,
266		       CTLTYPE_NODE, "security",
267		       SYSCTL_DESCR("Security"),
268		       NULL, 0, NULL, 0,
269		       CTL_SECURITY, CTL_EOL);
270}
271
272/*
273 * this setup routine is a replacement for kern_sysctl()
274 */
275SYSCTL_SETUP(sysctl_kern_setup, "sysctl kern subtree setup")
276{
277	extern int kern_logsigexit;	/* defined in kern/kern_sig.c */
278	extern fixpt_t ccpu;		/* defined in kern/kern_synch.c */
279	extern int dumponpanic;		/* defined in kern/subr_prf.c */
280
281	sysctl_createv(clog, 0, NULL, NULL,
282		       CTLFLAG_PERMANENT,
283		       CTLTYPE_NODE, "kern", NULL,
284		       NULL, 0, NULL, 0,
285		       CTL_KERN, CTL_EOL);
286
287	sysctl_createv(clog, 0, NULL, NULL,
288		       CTLFLAG_PERMANENT,
289		       CTLTYPE_STRING, "ostype",
290		       SYSCTL_DESCR("Operating system type"),
291		       NULL, 0, &ostype, 0,
292		       CTL_KERN, KERN_OSTYPE, CTL_EOL);
293	sysctl_createv(clog, 0, NULL, NULL,
294		       CTLFLAG_PERMANENT,
295		       CTLTYPE_STRING, "osrelease",
296		       SYSCTL_DESCR("Operating system release"),
297		       NULL, 0, &osrelease, 0,
298		       CTL_KERN, KERN_OSRELEASE, CTL_EOL);
299	sysctl_createv(clog, 0, NULL, NULL,
300		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
301		       CTLTYPE_INT, "osrevision",
302		       SYSCTL_DESCR("Operating system revision"),
303		       NULL, __NetBSD_Version__, NULL, 0,
304		       CTL_KERN, KERN_OSREV, CTL_EOL);
305	sysctl_createv(clog, 0, NULL, NULL,
306		       CTLFLAG_PERMANENT,
307		       CTLTYPE_STRING, "version",
308		       SYSCTL_DESCR("Kernel version"),
309		       NULL, 0, &version, 0,
310		       CTL_KERN, KERN_VERSION, CTL_EOL);
311	sysctl_createv(clog, 0, NULL, NULL,
312		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
313		       CTLTYPE_INT, "maxvnodes",
314		       SYSCTL_DESCR("Maximum number of vnodes"),
315		       sysctl_kern_maxvnodes, 0, NULL, 0,
316		       CTL_KERN, KERN_MAXVNODES, CTL_EOL);
317	sysctl_createv(clog, 0, NULL, NULL,
318		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
319		       CTLTYPE_INT, "maxproc",
320		       SYSCTL_DESCR("Maximum number of simultaneous processes"),
321		       sysctl_kern_maxproc, 0, NULL, 0,
322		       CTL_KERN, KERN_MAXPROC, CTL_EOL);
323	sysctl_createv(clog, 0, NULL, NULL,
324		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
325		       CTLTYPE_INT, "maxfiles",
326		       SYSCTL_DESCR("Maximum number of open files"),
327		       NULL, 0, &maxfiles, 0,
328		       CTL_KERN, KERN_MAXFILES, CTL_EOL);
329	sysctl_createv(clog, 0, NULL, NULL,
330		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
331		       CTLTYPE_INT, "argmax",
332		       SYSCTL_DESCR("Maximum number of bytes of arguments to "
333				    "execve(2)"),
334		       NULL, ARG_MAX, NULL, 0,
335		       CTL_KERN, KERN_ARGMAX, CTL_EOL);
336	sysctl_createv(clog, 0, NULL, NULL,
337		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
338		       CTLTYPE_INT, "securelevel",
339		       SYSCTL_DESCR("System security level"),
340		       sysctl_kern_securelevel, 0, &securelevel, 0,
341		       CTL_KERN, KERN_SECURELVL, CTL_EOL);
342	sysctl_createv(clog, 0, NULL, NULL,
343		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
344		       CTLTYPE_STRING, "hostname",
345		       SYSCTL_DESCR("System hostname"),
346		       sysctl_setlen, 0, &hostname, MAXHOSTNAMELEN,
347		       CTL_KERN, KERN_HOSTNAME, CTL_EOL);
348	sysctl_createv(clog, 0, NULL, NULL,
349		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE|CTLFLAG_HEX,
350		       CTLTYPE_INT, "hostid",
351		       SYSCTL_DESCR("System host ID number"),
352		       sysctl_kern_hostid, 0, NULL, 0,
353		       CTL_KERN, KERN_HOSTID, CTL_EOL);
354	sysctl_createv(clog, 0, NULL, NULL,
355		       CTLFLAG_PERMANENT,
356		       CTLTYPE_STRUCT, "clockrate",
357		       SYSCTL_DESCR("Kernel clock rates"),
358		       sysctl_kern_clockrate, 0, NULL,
359		       sizeof(struct clockinfo),
360		       CTL_KERN, KERN_CLOCKRATE, CTL_EOL);
361	sysctl_createv(clog, 0, NULL, NULL,
362		       CTLFLAG_PERMANENT,
363		       CTLTYPE_INT, "hardclock_ticks",
364		       SYSCTL_DESCR("Number of hardclock ticks"),
365		       NULL, 0, &hardclock_ticks, sizeof(hardclock_ticks),
366		       CTL_KERN, KERN_HARDCLOCK_TICKS, CTL_EOL);
367	sysctl_createv(clog, 0, NULL, NULL,
368		       CTLFLAG_PERMANENT,
369		       CTLTYPE_STRUCT, "vnode",
370		       SYSCTL_DESCR("System vnode table"),
371		       sysctl_kern_vnode, 0, NULL, 0,
372		       CTL_KERN, KERN_VNODE, CTL_EOL);
373	sysctl_createv(clog, 0, NULL, NULL,
374		       CTLFLAG_PERMANENT,
375		       CTLTYPE_STRUCT, "file",
376		       SYSCTL_DESCR("System open file table"),
377		       sysctl_kern_file, 0, NULL, 0,
378		       CTL_KERN, KERN_FILE, CTL_EOL);
379#ifndef GPROF
380	sysctl_createv(clog, 0, NULL, NULL,
381		       CTLFLAG_PERMANENT,
382		       CTLTYPE_NODE, "profiling",
383		       SYSCTL_DESCR("Profiling information (not available)"),
384		       sysctl_notavail, 0, NULL, 0,
385		       CTL_KERN, KERN_PROF, CTL_EOL);
386#endif
387	sysctl_createv(clog, 0, NULL, NULL,
388		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
389		       CTLTYPE_INT, "posix1version",
390		       SYSCTL_DESCR("Version of ISO/IEC 9945 (POSIX 1003.1) "
391				    "with which the operating system attempts "
392				    "to comply"),
393		       NULL, _POSIX_VERSION, NULL, 0,
394		       CTL_KERN, KERN_POSIX1, CTL_EOL);
395	sysctl_createv(clog, 0, NULL, NULL,
396		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
397		       CTLTYPE_INT, "ngroups",
398		       SYSCTL_DESCR("Maximum number of supplemental groups"),
399		       NULL, NGROUPS_MAX, NULL, 0,
400		       CTL_KERN, KERN_NGROUPS, CTL_EOL);
401	sysctl_createv(clog, 0, NULL, NULL,
402		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
403		       CTLTYPE_INT, "job_control",
404		       SYSCTL_DESCR("Whether job control is available"),
405		       NULL, 1, NULL, 0,
406		       CTL_KERN, KERN_JOB_CONTROL, CTL_EOL);
407	sysctl_createv(clog, 0, NULL, NULL,
408		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
409		       CTLTYPE_INT, "saved_ids",
410		       SYSCTL_DESCR("Whether POSIX saved set-group/user ID is "
411				    "available"), NULL,
412#ifdef _POSIX_SAVED_IDS
413		       1,
414#else /* _POSIX_SAVED_IDS */
415		       0,
416#endif /* _POSIX_SAVED_IDS */
417		       NULL, 0, CTL_KERN, KERN_SAVED_IDS, CTL_EOL);
418	sysctl_createv(clog, 0, NULL, NULL,
419		       CTLFLAG_PERMANENT,
420		       CTLTYPE_STRUCT, "boottime",
421		       SYSCTL_DESCR("System boot time"),
422		       NULL, 0, &boottime, sizeof(boottime),
423		       CTL_KERN, KERN_BOOTTIME, CTL_EOL);
424	sysctl_createv(clog, 0, NULL, NULL,
425		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
426		       CTLTYPE_STRING, "domainname",
427		       SYSCTL_DESCR("YP domain name"),
428		       sysctl_setlen, 0, &domainname, MAXHOSTNAMELEN,
429		       CTL_KERN, KERN_DOMAINNAME, CTL_EOL);
430	sysctl_createv(clog, 0, NULL, NULL,
431		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
432		       CTLTYPE_INT, "maxpartitions",
433		       SYSCTL_DESCR("Maximum number of partitions allowed per "
434				    "disk"),
435		       NULL, MAXPARTITIONS, NULL, 0,
436		       CTL_KERN, KERN_MAXPARTITIONS, CTL_EOL);
437	sysctl_createv(clog, 0, NULL, NULL,
438		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
439		       CTLTYPE_INT, "rawpartition",
440		       SYSCTL_DESCR("Raw partition of a disk"),
441		       NULL, RAW_PART, NULL, 0,
442		       CTL_KERN, KERN_RAWPARTITION, CTL_EOL);
443	sysctl_createv(clog, 0, NULL, NULL,
444		       CTLFLAG_PERMANENT,
445		       CTLTYPE_STRUCT, "timex", NULL,
446		       sysctl_notavail, 0, NULL, 0,
447		       CTL_KERN, KERN_TIMEX, CTL_EOL);
448	sysctl_createv(clog, 0, NULL, NULL,
449		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
450		       CTLTYPE_INT, "autonicetime",
451		       SYSCTL_DESCR("CPU clock seconds before non-root "
452				    "process priority is lowered"),
453		       sysctl_kern_autonice, 0, &autonicetime, 0,
454		       CTL_KERN, KERN_AUTONICETIME, CTL_EOL);
455	sysctl_createv(clog, 0, NULL, NULL,
456		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
457		       CTLTYPE_INT, "autoniceval",
458		       SYSCTL_DESCR("Automatic reniced non-root process "
459				    "priority"),
460		       sysctl_kern_autonice, 0, &autoniceval, 0,
461		       CTL_KERN, KERN_AUTONICEVAL, CTL_EOL);
462	sysctl_createv(clog, 0, NULL, NULL,
463		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
464		       CTLTYPE_INT, "rtc_offset",
465		       SYSCTL_DESCR("Offset of real time clock from UTC in "
466				    "minutes"),
467		       sysctl_kern_rtc_offset, 0, &rtc_offset, 0,
468		       CTL_KERN, KERN_RTC_OFFSET, CTL_EOL);
469	sysctl_createv(clog, 0, NULL, NULL,
470		       CTLFLAG_PERMANENT,
471		       CTLTYPE_STRING, "root_device",
472		       SYSCTL_DESCR("Name of the root device"),
473		       sysctl_root_device, 0, NULL, 0,
474		       CTL_KERN, KERN_ROOT_DEVICE, CTL_EOL);
475	sysctl_createv(clog, 0, NULL, NULL,
476		       CTLFLAG_PERMANENT,
477		       CTLTYPE_INT, "msgbufsize",
478		       SYSCTL_DESCR("Size of the kernel message buffer"),
479		       sysctl_msgbuf, 0, NULL, 0,
480		       CTL_KERN, KERN_MSGBUFSIZE, CTL_EOL);
481	sysctl_createv(clog, 0, NULL, NULL,
482		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
483		       CTLTYPE_INT, "fsync",
484		       SYSCTL_DESCR("Whether the POSIX 1003.1b File "
485				    "Synchronization Option is available on "
486				    "this system"),
487		       NULL, 1, NULL, 0,
488		       CTL_KERN, KERN_FSYNC, CTL_EOL);
489	sysctl_createv(clog, 0, NULL, NULL,
490		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
491		       CTLTYPE_INT, "sysvmsg",
492		       SYSCTL_DESCR("System V style message support available"),
493		       NULL,
494#ifdef SYSVMSG
495		       1,
496#else /* SYSVMSG */
497		       0,
498#endif /* SYSVMSG */
499		       NULL, 0, CTL_KERN, KERN_SYSVMSG, CTL_EOL);
500	sysctl_createv(clog, 0, NULL, NULL,
501		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
502		       CTLTYPE_INT, "sysvsem",
503		       SYSCTL_DESCR("System V style semaphore support "
504				    "available"), NULL,
505#ifdef SYSVSEM
506		       1,
507#else /* SYSVSEM */
508		       0,
509#endif /* SYSVSEM */
510		       NULL, 0, CTL_KERN, KERN_SYSVSEM, CTL_EOL);
511	sysctl_createv(clog, 0, NULL, NULL,
512		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
513		       CTLTYPE_INT, "sysvshm",
514		       SYSCTL_DESCR("System V style shared memory support "
515				    "available"), NULL,
516#ifdef SYSVSHM
517		       1,
518#else /* SYSVSHM */
519		       0,
520#endif /* SYSVSHM */
521		       NULL, 0, CTL_KERN, KERN_SYSVSHM, CTL_EOL);
522	sysctl_createv(clog, 0, NULL, NULL,
523		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
524		       CTLTYPE_INT, "synchronized_io",
525		       SYSCTL_DESCR("Whether the POSIX 1003.1b Synchronized "
526				    "I/O Option is available on this system"),
527		       NULL, 1, NULL, 0,
528		       CTL_KERN, KERN_SYNCHRONIZED_IO, CTL_EOL);
529	sysctl_createv(clog, 0, NULL, NULL,
530		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
531		       CTLTYPE_INT, "iov_max",
532		       SYSCTL_DESCR("Maximum number of iovec structures per "
533				    "process"),
534		       NULL, IOV_MAX, NULL, 0,
535		       CTL_KERN, KERN_IOV_MAX, CTL_EOL);
536	sysctl_createv(clog, 0, NULL, NULL,
537		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
538		       CTLTYPE_INT, "mapped_files",
539		       SYSCTL_DESCR("Whether the POSIX 1003.1b Memory Mapped "
540				    "Files Option is available on this system"),
541		       NULL, 1, NULL, 0,
542		       CTL_KERN, KERN_MAPPED_FILES, CTL_EOL);
543	sysctl_createv(clog, 0, NULL, NULL,
544		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
545		       CTLTYPE_INT, "memlock",
546		       SYSCTL_DESCR("Whether the POSIX 1003.1b Process Memory "
547				    "Locking Option is available on this "
548				    "system"),
549		       NULL, 1, NULL, 0,
550		       CTL_KERN, KERN_MEMLOCK, CTL_EOL);
551	sysctl_createv(clog, 0, NULL, NULL,
552		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
553		       CTLTYPE_INT, "memlock_range",
554		       SYSCTL_DESCR("Whether the POSIX 1003.1b Range Memory "
555				    "Locking Option is available on this "
556				    "system"),
557		       NULL, 1, NULL, 0,
558		       CTL_KERN, KERN_MEMLOCK_RANGE, CTL_EOL);
559	sysctl_createv(clog, 0, NULL, NULL,
560		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
561		       CTLTYPE_INT, "memory_protection",
562		       SYSCTL_DESCR("Whether the POSIX 1003.1b Memory "
563				    "Protection Option is available on this "
564				    "system"),
565		       NULL, 1, NULL, 0,
566		       CTL_KERN, KERN_MEMORY_PROTECTION, CTL_EOL);
567	sysctl_createv(clog, 0, NULL, NULL,
568		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
569		       CTLTYPE_INT, "login_name_max",
570		       SYSCTL_DESCR("Maximum login name length"),
571		       NULL, LOGIN_NAME_MAX, NULL, 0,
572		       CTL_KERN, KERN_LOGIN_NAME_MAX, CTL_EOL);
573	sysctl_createv(clog, 0, NULL, NULL,
574		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
575		       CTLTYPE_STRING, "defcorename",
576		       SYSCTL_DESCR("Default core file name"),
577		       sysctl_kern_defcorename, 0, defcorename, MAXPATHLEN,
578		       CTL_KERN, KERN_DEFCORENAME, CTL_EOL);
579	sysctl_createv(clog, 0, NULL, NULL,
580		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
581		       CTLTYPE_INT, "logsigexit",
582		       SYSCTL_DESCR("Log process exit when caused by signals"),
583		       NULL, 0, &kern_logsigexit, 0,
584		       CTL_KERN, KERN_LOGSIGEXIT, CTL_EOL);
585	sysctl_createv(clog, 0, NULL, NULL,
586		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
587		       CTLTYPE_INT, "fscale",
588		       SYSCTL_DESCR("Kernel fixed-point scale factor"),
589		       NULL, FSCALE, NULL, 0,
590		       CTL_KERN, KERN_FSCALE, CTL_EOL);
591	sysctl_createv(clog, 0, NULL, NULL,
592		       CTLFLAG_PERMANENT,
593		       CTLTYPE_INT, "ccpu",
594		       SYSCTL_DESCR("Scheduler exponential decay value"),
595		       NULL, 0, &ccpu, 0,
596		       CTL_KERN, KERN_CCPU, CTL_EOL);
597	sysctl_createv(clog, 0, NULL, NULL,
598		       CTLFLAG_PERMANENT,
599		       CTLTYPE_STRUCT, "cp_time",
600		       SYSCTL_DESCR("Clock ticks spent in different CPU states"),
601		       sysctl_kern_cptime, 0, NULL, 0,
602		       CTL_KERN, KERN_CP_TIME, CTL_EOL);
603#if defined(SYSVMSG) || defined(SYSVSEM) || defined(SYSVSHM)
604	sysctl_createv(clog, 0, NULL, NULL,
605		       CTLFLAG_PERMANENT,
606		       CTLTYPE_STRUCT, "sysvipc_info",
607		       SYSCTL_DESCR("System V style IPC information"),
608		       sysctl_kern_sysvipc, 0, NULL, 0,
609		       CTL_KERN, KERN_SYSVIPC_INFO, CTL_EOL);
610#endif /* SYSVMSG || SYSVSEM || SYSVSHM */
611	sysctl_createv(clog, 0, NULL, NULL,
612		       CTLFLAG_PERMANENT,
613		       CTLTYPE_INT, "msgbuf",
614		       SYSCTL_DESCR("Kernel message buffer"),
615		       sysctl_msgbuf, 0, NULL, 0,
616		       CTL_KERN, KERN_MSGBUF, CTL_EOL);
617	sysctl_createv(clog, 0, NULL, NULL,
618		       CTLFLAG_PERMANENT,
619		       CTLTYPE_STRUCT, "consdev",
620		       SYSCTL_DESCR("Console device"),
621		       sysctl_consdev, 0, NULL, sizeof(dev_t),
622		       CTL_KERN, KERN_CONSDEV, CTL_EOL);
623#if NPTY > 0
624	sysctl_createv(clog, 0, NULL, NULL,
625		       CTLFLAG_PERMANENT,
626		       CTLTYPE_INT, "maxptys",
627		       SYSCTL_DESCR("Maximum number of pseudo-ttys"),
628		       sysctl_kern_maxptys, 0, NULL, 0,
629		       CTL_KERN, KERN_MAXPTYS, CTL_EOL);
630#endif /* NPTY > 0 */
631	sysctl_createv(clog, 0, NULL, NULL,
632		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
633		       CTLTYPE_INT, "maxphys",
634		       SYSCTL_DESCR("Maximum raw I/O transfer size"),
635		       NULL, MAXPHYS, NULL, 0,
636		       CTL_KERN, KERN_MAXPHYS, CTL_EOL);
637	sysctl_createv(clog, 0, NULL, NULL,
638		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
639		       CTLTYPE_INT, "sbmax",
640		       SYSCTL_DESCR("Maximum socket buffer size"),
641		       sysctl_kern_sbmax, 0, NULL, 0,
642		       CTL_KERN, KERN_SBMAX, CTL_EOL);
643	sysctl_createv(clog, 0, NULL, NULL,
644		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
645		       CTLTYPE_INT, "monotonic_clock",
646		       SYSCTL_DESCR("Implementation version of the POSIX "
647				    "1003.1b Monotonic Clock Option"),
648		       /* XXX _POSIX_VERSION */
649		       NULL, _POSIX_MONOTONIC_CLOCK, NULL, 0,
650		       CTL_KERN, KERN_MONOTONIC_CLOCK, CTL_EOL);
651	sysctl_createv(clog, 0, NULL, NULL,
652		       CTLFLAG_PERMANENT,
653		       CTLTYPE_INT, "urandom",
654		       SYSCTL_DESCR("Random integer value"),
655		       sysctl_kern_urnd, 0, NULL, 0,
656		       CTL_KERN, KERN_URND, CTL_EOL);
657	sysctl_createv(clog, 0, NULL, NULL,
658		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
659		       CTLTYPE_INT, "labelsector",
660		       SYSCTL_DESCR("Sector number containing the disklabel"),
661		       NULL, LABELSECTOR, NULL, 0,
662		       CTL_KERN, KERN_LABELSECTOR, CTL_EOL);
663	sysctl_createv(clog, 0, NULL, NULL,
664		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
665		       CTLTYPE_INT, "labeloffset",
666		       SYSCTL_DESCR("Offset of the disklabel within the "
667				    "sector"),
668		       NULL, LABELOFFSET, NULL, 0,
669		       CTL_KERN, KERN_LABELOFFSET, CTL_EOL);
670	sysctl_createv(clog, 0, NULL, NULL,
671		       CTLFLAG_PERMANENT,
672		       CTLTYPE_NODE, "lwp",
673		       SYSCTL_DESCR("System-wide LWP information"),
674		       sysctl_kern_lwp, 0, NULL, 0,
675		       CTL_KERN, KERN_LWP, CTL_EOL);
676	sysctl_createv(clog, 0, NULL, NULL,
677		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
678		       CTLTYPE_INT, "forkfsleep",
679		       SYSCTL_DESCR("Milliseconds to sleep on fork failure due "
680				    "to process limits"),
681		       sysctl_kern_forkfsleep, 0, NULL, 0,
682		       CTL_KERN, KERN_FORKFSLEEP, CTL_EOL);
683	sysctl_createv(clog, 0, NULL, NULL,
684		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
685		       CTLTYPE_INT, "posix_threads",
686		       SYSCTL_DESCR("Version of IEEE Std 1003.1 and its "
687				    "Threads option to which the system "
688				    "attempts to conform"),
689		       /* XXX _POSIX_VERSION */
690		       NULL, _POSIX_THREADS, NULL, 0,
691		       CTL_KERN, KERN_POSIX_THREADS, CTL_EOL);
692	sysctl_createv(clog, 0, NULL, NULL,
693		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
694		       CTLTYPE_INT, "posix_semaphores",
695		       SYSCTL_DESCR("Version of IEEE Std 1003.1 and its "
696				    "Semaphores option to which the system "
697				    "attempts to conform"), NULL,
698#ifdef P1003_1B_SEMAPHORE
699		       200112,
700#else /* P1003_1B_SEMAPHORE */
701		       0,
702#endif /* P1003_1B_SEMAPHORE */
703		       NULL, 0, CTL_KERN, KERN_POSIX_SEMAPHORES, CTL_EOL);
704	sysctl_createv(clog, 0, NULL, NULL,
705		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
706		       CTLTYPE_INT, "posix_barriers",
707		       SYSCTL_DESCR("Version of IEEE Std 1003.1 and its "
708				    "Barriers option to which the system "
709				    "attempts to conform"),
710		       /* XXX _POSIX_VERSION */
711		       NULL, _POSIX_BARRIERS, NULL, 0,
712		       CTL_KERN, KERN_POSIX_BARRIERS, CTL_EOL);
713	sysctl_createv(clog, 0, NULL, NULL,
714		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
715		       CTLTYPE_INT, "posix_timers",
716		       SYSCTL_DESCR("Version of IEEE Std 1003.1 and its "
717				    "Timers option to which the system "
718				    "attempts to conform"),
719		       /* XXX _POSIX_VERSION */
720		       NULL, _POSIX_TIMERS, NULL, 0,
721		       CTL_KERN, KERN_POSIX_TIMERS, CTL_EOL);
722	sysctl_createv(clog, 0, NULL, NULL,
723		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
724		       CTLTYPE_INT, "posix_spin_locks",
725		       SYSCTL_DESCR("Version of IEEE Std 1003.1 and its Spin "
726				    "Locks option to which the system attempts "
727				    "to conform"),
728		       /* XXX _POSIX_VERSION */
729		       NULL, _POSIX_SPIN_LOCKS, NULL, 0,
730		       CTL_KERN, KERN_POSIX_SPIN_LOCKS, CTL_EOL);
731	sysctl_createv(clog, 0, NULL, NULL,
732		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
733		       CTLTYPE_INT, "posix_reader_writer_locks",
734		       SYSCTL_DESCR("Version of IEEE Std 1003.1 and its "
735				    "Read-Write Locks option to which the "
736				    "system attempts to conform"),
737		       /* XXX _POSIX_VERSION */
738		       NULL, _POSIX_READER_WRITER_LOCKS, NULL, 0,
739		       CTL_KERN, KERN_POSIX_READER_WRITER_LOCKS, CTL_EOL);
740	sysctl_createv(clog, 0, NULL, NULL,
741		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
742		       CTLTYPE_INT, "dump_on_panic",
743		       SYSCTL_DESCR("Perform a crash dump on system panic"),
744		       NULL, 0, &dumponpanic, 0,
745		       CTL_KERN, KERN_DUMP_ON_PANIC, CTL_EOL);
746#ifdef DIAGNOSTIC
747	sysctl_createv(clog, 0, NULL, NULL,
748		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
749		       CTLTYPE_INT, "panic_now",
750		       SYSCTL_DESCR("Trigger a panic"),
751		       sysctl_kern_trigger_panic, 0, NULL, 0,
752		       CTL_KERN, CTL_CREATE, CTL_EOL);
753#endif
754	sysctl_createv(clog, 0, NULL, NULL,
755		       CTLFLAG_PERMANENT,
756		       CTLTYPE_INT, "root_partition",
757		       SYSCTL_DESCR("Root partition on the root device"),
758		       sysctl_kern_root_partition, 0, NULL, 0,
759		       CTL_KERN, KERN_ROOT_PARTITION, CTL_EOL);
760	sysctl_createv(clog, 0, NULL, NULL,
761		       CTLFLAG_PERMANENT,
762		       CTLTYPE_STRUCT, "drivers",
763		       SYSCTL_DESCR("List of all drivers with block and "
764				    "character device numbers"),
765		       sysctl_kern_drivers, 0, NULL, 0,
766		       CTL_KERN, KERN_DRIVERS, CTL_EOL);
767	sysctl_createv(clog, 0, NULL, NULL,
768		       CTLFLAG_PERMANENT,
769		       CTLTYPE_STRUCT, "file2",
770		       SYSCTL_DESCR("System open file table"),
771		       sysctl_kern_file2, 0, NULL, 0,
772		       CTL_KERN, KERN_FILE2, CTL_EOL);
773#ifdef VERIFIED_EXEC
774	sysctl_createv(clog, 0, NULL, NULL,
775		       CTLFLAG_PERMANENT,
776		       CTLTYPE_NODE, "veriexec",
777		       SYSCTL_DESCR("Verified Exec"),
778		       NULL, 0, NULL, 0,
779		       CTL_KERN, KERN_VERIEXEC, CTL_EOL);
780	sysctl_createv(clog, 0, NULL, NULL,
781		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
782		       CTLTYPE_INT, "verbose",
783		       SYSCTL_DESCR("Verified Exec verbose level"),
784		       NULL, 0, &veriexec_verbose, 0,
785		       CTL_KERN, KERN_VERIEXEC, VERIEXEC_VERBOSE,
786		       CTL_EOL);
787	sysctl_createv(clog, 0, NULL, NULL,
788		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
789		       CTLTYPE_INT, "strict",
790		       SYSCTL_DESCR("Verified Exec strict level"),
791		       sysctl_kern_veriexec, 0, NULL, 0,
792		       CTL_KERN, KERN_VERIEXEC, VERIEXEC_STRICT, CTL_EOL);
793	sysctl_createv(clog, 0, NULL, NULL,
794		       CTLFLAG_PERMANENT,
795		       CTLTYPE_STRING, "algorithms",
796		       SYSCTL_DESCR("Verified Exec supported hashing "
797				    "algorithms"),
798		       sysctl_kern_veriexec, 0, NULL, 0,
799		       CTL_KERN, KERN_VERIEXEC, VERIEXEC_ALGORITHMS, CTL_EOL);
800	sysctl_createv(clog, 0, NULL, &veriexec_count_node,
801		       CTLFLAG_PERMANENT,
802		       CTLTYPE_NODE, "count",
803		       SYSCTL_DESCR("Number of fingerprints on device(s)"),
804		       NULL, 0, NULL, 0,
805		       CTL_KERN, KERN_VERIEXEC, VERIEXEC_COUNT, CTL_EOL);
806#endif /* VERIFIED_EXEC */
807	sysctl_createv(clog, 0, NULL, NULL,
808		       CTLFLAG_PERMANENT,
809		       CTLTYPE_STRUCT, "cp_id",
810		       SYSCTL_DESCR("Mapping of CPU number to CPU id"),
811		       sysctl_kern_cpid, 0, NULL, 0,
812		       CTL_KERN, KERN_CP_ID, CTL_EOL);
813}
814
815SYSCTL_SETUP(sysctl_kern_proc_setup,
816	     "sysctl kern.proc/proc2/proc_args subtree setup")
817{
818
819	sysctl_createv(clog, 0, NULL, NULL,
820		       CTLFLAG_PERMANENT,
821		       CTLTYPE_NODE, "kern", NULL,
822		       NULL, 0, NULL, 0,
823		       CTL_KERN, CTL_EOL);
824
825	sysctl_createv(clog, 0, NULL, NULL,
826		       CTLFLAG_PERMANENT,
827		       CTLTYPE_NODE, "proc",
828		       SYSCTL_DESCR("System-wide process information"),
829		       sysctl_doeproc, 0, NULL, 0,
830		       CTL_KERN, KERN_PROC, CTL_EOL);
831	sysctl_createv(clog, 0, NULL, NULL,
832		       CTLFLAG_PERMANENT,
833		       CTLTYPE_NODE, "proc2",
834		       SYSCTL_DESCR("Machine-independent process information"),
835		       sysctl_doeproc, 0, NULL, 0,
836		       CTL_KERN, KERN_PROC2, CTL_EOL);
837	sysctl_createv(clog, 0, NULL, NULL,
838		       CTLFLAG_PERMANENT,
839		       CTLTYPE_NODE, "proc_args",
840		       SYSCTL_DESCR("Process argument information"),
841		       sysctl_kern_proc_args, 0, NULL, 0,
842		       CTL_KERN, KERN_PROC_ARGS, CTL_EOL);
843
844	/*
845	  "nodes" under these:
846
847	  KERN_PROC_ALL
848	  KERN_PROC_PID pid
849	  KERN_PROC_PGRP pgrp
850	  KERN_PROC_SESSION sess
851	  KERN_PROC_TTY tty
852	  KERN_PROC_UID uid
853	  KERN_PROC_RUID uid
854	  KERN_PROC_GID gid
855	  KERN_PROC_RGID gid
856
857	  all in all, probably not worth the effort...
858	*/
859}
860
861SYSCTL_SETUP(sysctl_hw_setup, "sysctl hw subtree setup")
862{
863	u_int u;
864	u_quad_t q;
865
866	sysctl_createv(clog, 0, NULL, NULL,
867		       CTLFLAG_PERMANENT,
868		       CTLTYPE_NODE, "hw", NULL,
869		       NULL, 0, NULL, 0,
870		       CTL_HW, CTL_EOL);
871
872	sysctl_createv(clog, 0, NULL, NULL,
873		       CTLFLAG_PERMANENT,
874		       CTLTYPE_STRING, "machine",
875		       SYSCTL_DESCR("Machine class"),
876		       NULL, 0, machine, 0,
877		       CTL_HW, HW_MACHINE, CTL_EOL);
878	sysctl_createv(clog, 0, NULL, NULL,
879		       CTLFLAG_PERMANENT,
880		       CTLTYPE_STRING, "model",
881		       SYSCTL_DESCR("Machine model"),
882		       NULL, 0, cpu_model, 0,
883		       CTL_HW, HW_MODEL, CTL_EOL);
884	sysctl_createv(clog, 0, NULL, NULL,
885		       CTLFLAG_PERMANENT,
886		       CTLTYPE_INT, "ncpu",
887		       SYSCTL_DESCR("Number of active CPUs"),
888		       sysctl_hw_ncpu, 0, NULL, 0,
889		       CTL_HW, HW_NCPU, CTL_EOL);
890	sysctl_createv(clog, 0, NULL, NULL,
891		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
892		       CTLTYPE_INT, "byteorder",
893		       SYSCTL_DESCR("System byte order"),
894		       NULL, BYTE_ORDER, NULL, 0,
895		       CTL_HW, HW_BYTEORDER, CTL_EOL);
896	u = ((u_int)physmem > (UINT_MAX / PAGE_SIZE)) ?
897		UINT_MAX : physmem * PAGE_SIZE;
898	sysctl_createv(clog, 0, NULL, NULL,
899		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
900		       CTLTYPE_INT, "physmem",
901		       SYSCTL_DESCR("Bytes of physical memory"),
902		       NULL, u, NULL, 0,
903		       CTL_HW, HW_PHYSMEM, CTL_EOL);
904	sysctl_createv(clog, 0, NULL, NULL,
905		       CTLFLAG_PERMANENT,
906		       CTLTYPE_INT, "usermem",
907		       SYSCTL_DESCR("Bytes of non-kernel memory"),
908		       sysctl_hw_usermem, 0, NULL, 0,
909		       CTL_HW, HW_USERMEM, CTL_EOL);
910	sysctl_createv(clog, 0, NULL, NULL,
911		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
912		       CTLTYPE_INT, "pagesize",
913		       SYSCTL_DESCR("Software page size"),
914		       NULL, PAGE_SIZE, NULL, 0,
915		       CTL_HW, HW_PAGESIZE, CTL_EOL);
916	sysctl_createv(clog, 0, NULL, NULL,
917		       CTLFLAG_PERMANENT,
918		       CTLTYPE_STRING, "machine_arch",
919		       SYSCTL_DESCR("Machine CPU class"),
920		       NULL, 0, machine_arch, 0,
921		       CTL_HW, HW_MACHINE_ARCH, CTL_EOL);
922	sysctl_createv(clog, 0, NULL, NULL,
923		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
924		       CTLTYPE_INT, "alignbytes",
925		       SYSCTL_DESCR("Alignment constraint for all possible "
926				    "data types"),
927		       NULL, ALIGNBYTES, NULL, 0,
928		       CTL_HW, HW_ALIGNBYTES, CTL_EOL);
929	sysctl_createv(clog, 0, NULL, NULL,
930		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE|CTLFLAG_HEX,
931		       CTLTYPE_STRING, "cnmagic",
932		       SYSCTL_DESCR("Console magic key sequence"),
933		       sysctl_hw_cnmagic, 0, NULL, CNS_LEN,
934		       CTL_HW, HW_CNMAGIC, CTL_EOL);
935	q = (u_quad_t)physmem * PAGE_SIZE;
936	sysctl_createv(clog, 0, NULL, NULL,
937		       CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE,
938		       CTLTYPE_QUAD, "physmem64",
939		       SYSCTL_DESCR("Bytes of physical memory"),
940		       NULL, q, NULL, 0,
941		       CTL_HW, HW_PHYSMEM64, CTL_EOL);
942	sysctl_createv(clog, 0, NULL, NULL,
943		       CTLFLAG_PERMANENT,
944		       CTLTYPE_QUAD, "usermem64",
945		       SYSCTL_DESCR("Bytes of non-kernel memory"),
946		       sysctl_hw_usermem, 0, NULL, 0,
947		       CTL_HW, HW_USERMEM64, CTL_EOL);
948}
949
950#ifdef DEBUG
951/*
952 * Debugging related system variables.
953 */
954struct ctldebug /* debug0, */ /* debug1, */ debug2, debug3, debug4;
955struct ctldebug debug5, debug6, debug7, debug8, debug9;
956struct ctldebug debug10, debug11, debug12, debug13, debug14;
957struct ctldebug debug15, debug16, debug17, debug18, debug19;
958static struct ctldebug *debugvars[CTL_DEBUG_MAXID] = {
959	&debug0, &debug1, &debug2, &debug3, &debug4,
960	&debug5, &debug6, &debug7, &debug8, &debug9,
961	&debug10, &debug11, &debug12, &debug13, &debug14,
962	&debug15, &debug16, &debug17, &debug18, &debug19,
963};
964
965/*
966 * this setup routine is a replacement for debug_sysctl()
967 *
968 * note that it creates several nodes per defined debug variable
969 */
970SYSCTL_SETUP(sysctl_debug_setup, "sysctl debug subtree setup")
971{
972	struct ctldebug *cdp;
973	char nodename[20];
974	int i;
975
976	/*
977	 * two ways here:
978	 *
979	 * the "old" way (debug.name -> value) which was emulated by
980	 * the sysctl(8) binary
981	 *
982	 * the new way, which the sysctl(8) binary was actually using
983
984	 node	debug
985	 node	debug.0
986	 string	debug.0.name
987	 int	debug.0.value
988	 int	debug.name
989
990	 */
991
992	sysctl_createv(clog, 0, NULL, NULL,
993		       CTLFLAG_PERMANENT,
994		       CTLTYPE_NODE, "debug", NULL,
995		       NULL, 0, NULL, 0,
996		       CTL_DEBUG, CTL_EOL);
997
998	for (i = 0; i < CTL_DEBUG_MAXID; i++) {
999		cdp = debugvars[i];
1000		if (cdp->debugname == NULL || cdp->debugvar == NULL)
1001			continue;
1002
1003		snprintf(nodename, sizeof(nodename), "debug%d", i);
1004		sysctl_createv(clog, 0, NULL, NULL,
1005			       CTLFLAG_PERMANENT|CTLFLAG_HIDDEN,
1006			       CTLTYPE_NODE, nodename, NULL,
1007			       NULL, 0, NULL, 0,
1008			       CTL_DEBUG, i, CTL_EOL);
1009		sysctl_createv(clog, 0, NULL, NULL,
1010			       CTLFLAG_PERMANENT|CTLFLAG_HIDDEN,
1011			       CTLTYPE_STRING, "name", NULL,
1012			       /*XXXUNCONST*/
1013			       NULL, 0, __UNCONST(cdp->debugname), 0,
1014			       CTL_DEBUG, i, CTL_DEBUG_NAME, CTL_EOL);
1015		sysctl_createv(clog, 0, NULL, NULL,
1016			       CTLFLAG_PERMANENT|CTLFLAG_HIDDEN,
1017			       CTLTYPE_INT, "value", NULL,
1018			       NULL, 0, cdp->debugvar, 0,
1019			       CTL_DEBUG, i, CTL_DEBUG_VALUE, CTL_EOL);
1020		sysctl_createv(clog, 0, NULL, NULL,
1021			       CTLFLAG_PERMANENT,
1022			       CTLTYPE_INT, cdp->debugname, NULL,
1023			       NULL, 0, cdp->debugvar, 0,
1024			       CTL_DEBUG, CTL_CREATE, CTL_EOL);
1025	}
1026}
1027#endif /* DEBUG */
1028
1029SYSCTL_SETUP(sysctl_security_setup, "sysctl security subtree setup")
1030{
1031	const struct sysctlnode *rnode = NULL;
1032
1033	sysctl_createv(clog, 0, NULL, &rnode,
1034		       CTLFLAG_PERMANENT,
1035		       CTLTYPE_NODE, "security", NULL,
1036		       NULL, 0, NULL, 0,
1037		       CTL_SECURITY, CTL_EOL);
1038
1039	sysctl_createv(clog, 0, &rnode, NULL,
1040		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
1041		       CTLTYPE_INT, "curtain",
1042		       SYSCTL_DESCR("Curtain information about objects"
1043				    " to users not owning them."),
1044		       NULL, 0, &security_curtain, 0,
1045		       CTL_CREATE, CTL_EOL);
1046
1047	sysctl_createv(clog, 0, &rnode, &rnode,
1048		       CTLFLAG_PERMANENT,
1049		       CTLTYPE_NODE, "setid_core",
1050		       SYSCTL_DESCR("Set-id processes' coredump settings."),
1051		       NULL, 0, NULL, 0,
1052		       CTL_CREATE, CTL_EOL);
1053	sysctl_createv(clog, 0, &rnode, NULL,
1054		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
1055		       CTLTYPE_INT, "dump",
1056		       SYSCTL_DESCR("Allow set-id processes to dump core."),
1057		       sysctl_security_setidcore, 0, &security_setidcore_dump,
1058		       sizeof(security_setidcore_dump),
1059		       CTL_CREATE, CTL_EOL);
1060	sysctl_createv(clog, 0, &rnode, NULL,
1061		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
1062		       CTLTYPE_STRING, "path",
1063		       SYSCTL_DESCR("Path pattern for set-id coredumps."),
1064		       sysctl_security_setidcorename, 0,
1065		       &security_setidcore_path,
1066		       sizeof(security_setidcore_path),
1067		       CTL_CREATE, CTL_EOL);
1068	sysctl_createv(clog, 0, &rnode, NULL,
1069		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
1070		       CTLTYPE_INT, "owner",
1071		       SYSCTL_DESCR("Owner id for set-id processes' cores."),
1072		       sysctl_security_setidcore, 0, &security_setidcore_owner,
1073		       0,
1074		       CTL_CREATE, CTL_EOL);
1075	sysctl_createv(clog, 0, &rnode, NULL,
1076		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
1077		       CTLTYPE_INT, "group",
1078		       SYSCTL_DESCR("Group id for set-id processes' cores."),
1079		       sysctl_security_setidcore, 0, &security_setidcore_group,
1080		       0,
1081		       CTL_CREATE, CTL_EOL);
1082	sysctl_createv(clog, 0, &rnode, NULL,
1083		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
1084		       CTLTYPE_INT, "mode",
1085		       SYSCTL_DESCR("Mode for set-id processes' cores."),
1086		       sysctl_security_setidcore, 0, &security_setidcore_mode,
1087		       0,
1088		       CTL_CREATE, CTL_EOL);
1089}
1090
1091/*
1092 * ********************************************************************
1093 * section 2: private node-specific helper routines.
1094 * ********************************************************************
1095 */
1096
1097#ifdef DIAGNOSTIC
1098static int
1099sysctl_kern_trigger_panic(SYSCTLFN_ARGS)
1100{
1101	int newtrig, error;
1102	struct sysctlnode node;
1103
1104	newtrig = 0;
1105	node = *rnode;
1106	node.sysctl_data = &newtrig;
1107	error = sysctl_lookup(SYSCTLFN_CALL(&node));
1108	if (error || newp == NULL)
1109		return (error);
1110
1111	if (newtrig != 0)
1112		panic("Panic triggered");
1113
1114	return (error);
1115}
1116#endif
1117
1118/*
1119 * sysctl helper routine for kern.maxvnodes.  drain vnodes if
1120 * new value is lower than desiredvnodes and then calls reinit
1121 * routines that needs to adjust to the new value.
1122 */
1123static int
1124sysctl_kern_maxvnodes(SYSCTLFN_ARGS)
1125{
1126	int error, new_vnodes, old_vnodes;
1127	struct sysctlnode node;
1128
1129	new_vnodes = desiredvnodes;
1130	node = *rnode;
1131	node.sysctl_data = &new_vnodes;
1132	error = sysctl_lookup(SYSCTLFN_CALL(&node));
1133	if (error || newp == NULL)
1134		return (error);
1135
1136	old_vnodes = desiredvnodes;
1137	desiredvnodes = new_vnodes;
1138	if (new_vnodes < old_vnodes) {
1139		error = vfs_drainvnodes(new_vnodes, l);
1140		if (error) {
1141			desiredvnodes = old_vnodes;
1142			return (error);
1143		}
1144	}
1145	vfs_reinit();
1146	nchreinit();
1147
1148	return (0);
1149}
1150
1151/*
1152 * sysctl helper routine for rtc_offset - set time after changes
1153 */
1154static int
1155sysctl_kern_rtc_offset(SYSCTLFN_ARGS)
1156{
1157	struct timespec ts, delta;
1158	int error, new_rtc_offset;
1159	struct sysctlnode node;
1160
1161	new_rtc_offset = rtc_offset;
1162	node = *rnode;
1163	node.sysctl_data = &new_rtc_offset;
1164	error = sysctl_lookup(SYSCTLFN_CALL(&node));
1165	if (error || newp == NULL)
1166		return (error);
1167
1168	if (securelevel > 0)
1169		return (EPERM);
1170	if (rtc_offset == new_rtc_offset)
1171		return (0);
1172
1173	/* if we change the offset, adjust the time */
1174	nanotime(&ts);
1175	delta.tv_sec = 60 * (new_rtc_offset - rtc_offset);
1176	delta.tv_nsec = 0;
1177	timespecadd(&ts, &delta, &ts);
1178	rtc_offset = new_rtc_offset;
1179	settime(l->l_proc, &ts);
1180
1181	return (0);
1182}
1183
1184/*
1185 * sysctl helper routine for kern.maxproc.  ensures that the new
1186 * values are not too low or too high.
1187 */
1188static int
1189sysctl_kern_maxproc(SYSCTLFN_ARGS)
1190{
1191	int error, nmaxproc;
1192	struct sysctlnode node;
1193
1194	nmaxproc = maxproc;
1195	node = *rnode;
1196	node.sysctl_data = &nmaxproc;
1197	error = sysctl_lookup(SYSCTLFN_CALL(&node));
1198	if (error || newp == NULL)
1199		return (error);
1200
1201	if (nmaxproc < 0 || nmaxproc >= PID_MAX)
1202		return (EINVAL);
1203#ifdef __HAVE_CPU_MAXPROC
1204	if (nmaxproc > cpu_maxproc())
1205		return (EINVAL);
1206#endif
1207	maxproc = nmaxproc;
1208
1209	return (0);
1210}
1211
1212/*
1213 * sysctl helper routine for kern.securelevel.  ensures that the value
1214 * only rises unless the caller has pid 1 (assumed to be init).
1215 */
1216static int
1217sysctl_kern_securelevel(SYSCTLFN_ARGS)
1218{
1219	int newsecurelevel, error;
1220	struct sysctlnode node;
1221
1222	newsecurelevel = securelevel;
1223	node = *rnode;
1224	node.sysctl_data = &newsecurelevel;
1225	error = sysctl_lookup(SYSCTLFN_CALL(&node));
1226	if (error || newp == NULL)
1227		return (error);
1228
1229	if (newsecurelevel < securelevel && l && l->l_proc->p_pid != 1)
1230		return (EPERM);
1231	securelevel = newsecurelevel;
1232
1233	return (error);
1234}
1235
1236/*
1237 * sysctl helper function for kern.hostid.  the hostid is a long, but
1238 * we export it as an int, so we need to give it a little help.
1239 */
1240static int
1241sysctl_kern_hostid(SYSCTLFN_ARGS)
1242{
1243	int error, inthostid;
1244	struct sysctlnode node;
1245
1246	inthostid = hostid;  /* XXX assumes sizeof int <= sizeof long */
1247	node = *rnode;
1248	node.sysctl_data = &inthostid;
1249	error = sysctl_lookup(SYSCTLFN_CALL(&node));
1250	if (error || newp == NULL)
1251		return (error);
1252
1253	hostid = (unsigned)inthostid;
1254
1255	return (0);
1256}
1257
1258/*
1259 * sysctl helper function for kern.hostname and kern.domainnname.
1260 * resets the relevant recorded length when the underlying name is
1261 * changed.
1262 */
1263static int
1264sysctl_setlen(SYSCTLFN_ARGS)
1265{
1266	int error;
1267
1268	error = sysctl_lookup(SYSCTLFN_CALL(rnode));
1269	if (error || newp == NULL)
1270		return (error);
1271
1272	switch (rnode->sysctl_num) {
1273	case KERN_HOSTNAME:
1274		hostnamelen = strlen((const char*)rnode->sysctl_data);
1275		break;
1276	case KERN_DOMAINNAME:
1277		domainnamelen = strlen((const char*)rnode->sysctl_data);
1278		break;
1279	}
1280
1281	return (0);
1282}
1283
1284/*
1285 * sysctl helper routine for kern.clockrate.  assembles a struct on
1286 * the fly to be returned to the caller.
1287 */
1288static int
1289sysctl_kern_clockrate(SYSCTLFN_ARGS)
1290{
1291	struct clockinfo clkinfo;
1292	struct sysctlnode node;
1293
1294	clkinfo.tick = tick;
1295	clkinfo.tickadj = tickadj;
1296	clkinfo.hz = hz;
1297	clkinfo.profhz = profhz;
1298	clkinfo.stathz = stathz ? stathz : hz;
1299
1300	node = *rnode;
1301	node.sysctl_data = &clkinfo;
1302	return (sysctl_lookup(SYSCTLFN_CALL(&node)));
1303}
1304
1305
1306/*
1307 * sysctl helper routine for kern.file pseudo-subtree.
1308 */
1309static int
1310sysctl_kern_file(SYSCTLFN_ARGS)
1311{
1312	int error;
1313	size_t buflen;
1314	struct file *fp;
1315	char *start, *where;
1316
1317	start = where = oldp;
1318	buflen = *oldlenp;
1319	if (where == NULL) {
1320		/*
1321		 * overestimate by 10 files
1322		 */
1323		*oldlenp = sizeof(filehead) + (nfiles + 10) * sizeof(struct file);
1324		return (0);
1325	}
1326
1327	/*
1328	 * first copyout filehead
1329	 */
1330	if (buflen < sizeof(filehead)) {
1331		*oldlenp = 0;
1332		return (0);
1333	}
1334	error = copyout(&filehead, where, sizeof(filehead));
1335	if (error)
1336		return (error);
1337	buflen -= sizeof(filehead);
1338	where += sizeof(filehead);
1339
1340	/*
1341	 * followed by an array of file structures
1342	 */
1343	LIST_FOREACH(fp, &filehead, f_list) {
1344		if (CURTAIN(l->l_proc->p_ucred->cr_uid, fp->f_cred->cr_uid))
1345			continue;
1346		if (buflen < sizeof(struct file)) {
1347			*oldlenp = where - start;
1348			return (ENOMEM);
1349		}
1350		error = copyout(fp, where, sizeof(struct file));
1351		if (error)
1352			return (error);
1353		buflen -= sizeof(struct file);
1354		where += sizeof(struct file);
1355	}
1356	*oldlenp = where - start;
1357	return (0);
1358}
1359
1360/*
1361 * sysctl helper routine for kern.autonicetime and kern.autoniceval.
1362 * asserts that the assigned value is in the correct range.
1363 */
1364static int
1365sysctl_kern_autonice(SYSCTLFN_ARGS)
1366{
1367	int error, t = 0;
1368	struct sysctlnode node;
1369
1370	node = *rnode;
1371	t = *(int*)node.sysctl_data;
1372	node.sysctl_data = &t;
1373	error = sysctl_lookup(SYSCTLFN_CALL(&node));
1374	if (error || newp == NULL)
1375		return (error);
1376
1377	switch (node.sysctl_num) {
1378	case KERN_AUTONICETIME:
1379		if (t >= 0)
1380			autonicetime = t;
1381		break;
1382	case KERN_AUTONICEVAL:
1383		if (t < PRIO_MIN)
1384			t = PRIO_MIN;
1385		else if (t > PRIO_MAX)
1386			t = PRIO_MAX;
1387		autoniceval = t;
1388		break;
1389	}
1390
1391	return (0);
1392}
1393
1394/*
1395 * sysctl helper routine for kern.msgbufsize and kern.msgbuf.  for the
1396 * former it merely checks the message buffer is set up.  for the latter,
1397 * it also copies out the data if necessary.
1398 */
1399static int
1400sysctl_msgbuf(SYSCTLFN_ARGS)
1401{
1402	char *where = oldp;
1403	size_t len, maxlen;
1404	long beg, end;
1405	int error;
1406
1407	if (!msgbufenabled || msgbufp->msg_magic != MSG_MAGIC) {
1408		msgbufenabled = 0;
1409		return (ENXIO);
1410	}
1411
1412	switch (rnode->sysctl_num) {
1413	case KERN_MSGBUFSIZE: {
1414		struct sysctlnode node = *rnode;
1415		int msg_bufs = (int)msgbufp->msg_bufs;
1416		node.sysctl_data = &msg_bufs;
1417		return (sysctl_lookup(SYSCTLFN_CALL(&node)));
1418	}
1419	case KERN_MSGBUF:
1420		break;
1421	default:
1422		return (EOPNOTSUPP);
1423	}
1424
1425	if (newp != NULL)
1426		return (EPERM);
1427
1428        if (oldp == NULL) {
1429		/* always return full buffer size */
1430		*oldlenp = msgbufp->msg_bufs;
1431		return (0);
1432        }
1433
1434	error = 0;
1435	maxlen = MIN(msgbufp->msg_bufs, *oldlenp);
1436
1437	/*
1438	 * First, copy from the write pointer to the end of
1439	 * message buffer.
1440	 */
1441	beg = msgbufp->msg_bufx;
1442	end = msgbufp->msg_bufs;
1443	while (maxlen > 0) {
1444		len = MIN(end - beg, maxlen);
1445		if (len == 0)
1446			break;
1447		error = copyout(&msgbufp->msg_bufc[beg], where, len);
1448		if (error)
1449			break;
1450		where += len;
1451		maxlen -= len;
1452
1453		/*
1454		 * ... then, copy from the beginning of message buffer to
1455		 * the write pointer.
1456		 */
1457		beg = 0;
1458		end = msgbufp->msg_bufx;
1459	}
1460
1461	return (error);
1462}
1463
1464/*
1465 * sysctl helper routine for kern.defcorename.  in the case of a new
1466 * string being assigned, check that it's not a zero-length string.
1467 * (XXX the check in -current doesn't work, but do we really care?)
1468 */
1469static int
1470sysctl_kern_defcorename(SYSCTLFN_ARGS)
1471{
1472	int error;
1473	char *newcorename;
1474	struct sysctlnode node;
1475
1476	newcorename = PNBUF_GET();
1477	node = *rnode;
1478	node.sysctl_data = &newcorename[0];
1479	memcpy(node.sysctl_data, rnode->sysctl_data, MAXPATHLEN);
1480	error = sysctl_lookup(SYSCTLFN_CALL(&node));
1481	if (error || newp == NULL) {
1482		goto done;
1483	}
1484
1485	/*
1486	 * when sysctl_lookup() deals with a string, it's guaranteed
1487	 * to come back nul terminated.  so there.  :)
1488	 */
1489	if (strlen(newcorename) == 0) {
1490		error = EINVAL;
1491	} else {
1492		memcpy(rnode->sysctl_data, node.sysctl_data, MAXPATHLEN);
1493		error = 0;
1494	}
1495done:
1496	PNBUF_PUT(newcorename);
1497	return error;
1498}
1499
1500/*
1501 * sysctl helper routine for kern.cp_time node.  adds up cpu time
1502 * across all cpus.
1503 */
1504static int
1505sysctl_kern_cptime(SYSCTLFN_ARGS)
1506{
1507	struct sysctlnode node = *rnode;
1508
1509#ifndef MULTIPROCESSOR
1510
1511	if (namelen == 1) {
1512		if (name[0] != 0)
1513			return (ENOENT);
1514		/*
1515		 * you're allowed to ask for the zero'th processor
1516		 */
1517		name++;
1518		namelen--;
1519	}
1520	node.sysctl_data = curcpu()->ci_schedstate.spc_cp_time;
1521	node.sysctl_size = sizeof(curcpu()->ci_schedstate.spc_cp_time);
1522	return (sysctl_lookup(SYSCTLFN_CALL(&node)));
1523
1524#else /* MULTIPROCESSOR */
1525
1526	uint64_t *cp_time = NULL;
1527	int error, n = sysctl_ncpus(), i;
1528	struct cpu_info *ci;
1529	CPU_INFO_ITERATOR cii;
1530
1531	/*
1532	 * if you specifically pass a buffer that is the size of the
1533	 * sum, or if you are probing for the size, you get the "sum"
1534	 * of cp_time (and the size thereof) across all processors.
1535	 *
1536	 * alternately, you can pass an additional mib number and get
1537	 * cp_time for that particular processor.
1538	 */
1539	switch (namelen) {
1540	case 0:
1541	    	if (*oldlenp == sizeof(uint64_t) * CPUSTATES || oldp == NULL) {
1542			node.sysctl_size = sizeof(uint64_t) * CPUSTATES;
1543			n = -1; /* SUM */
1544		}
1545		else {
1546			node.sysctl_size = n * sizeof(uint64_t) * CPUSTATES;
1547			n = -2; /* ALL */
1548		}
1549		break;
1550	case 1:
1551		if (name[0] < 0 || name[0] >= n)
1552			return (ENOENT); /* ENOSUCHPROCESSOR */
1553		node.sysctl_size = sizeof(uint64_t) * CPUSTATES;
1554		n = name[0];
1555		/*
1556		 * adjust these so that sysctl_lookup() will be happy
1557		 */
1558		name++;
1559		namelen--;
1560		break;
1561	default:
1562		return (EINVAL);
1563	}
1564
1565	cp_time = malloc(node.sysctl_size, M_TEMP, M_WAITOK|M_CANFAIL);
1566	if (cp_time == NULL)
1567		return (ENOMEM);
1568	node.sysctl_data = cp_time;
1569	memset(cp_time, 0, node.sysctl_size);
1570
1571	for (CPU_INFO_FOREACH(cii, ci)) {
1572		if (n <= 0)
1573			for (i = 0; i < CPUSTATES; i++)
1574				cp_time[i] += ci->ci_schedstate.spc_cp_time[i];
1575		/*
1576		 * if a specific processor was requested and we just
1577		 * did it, we're done here
1578		 */
1579		if (n == 0)
1580			break;
1581		/*
1582		 * if doing "all", skip to next cp_time set for next processor
1583		 */
1584		if (n == -2)
1585			cp_time += CPUSTATES;
1586		/*
1587		 * if we're doing a specific processor, we're one
1588		 * processor closer
1589		 */
1590		if (n > 0)
1591			n--;
1592	}
1593
1594	error = sysctl_lookup(SYSCTLFN_CALL(&node));
1595	free(node.sysctl_data, M_TEMP);
1596	return (error);
1597
1598#endif /* MULTIPROCESSOR */
1599}
1600
1601#if defined(SYSVMSG) || defined(SYSVSEM) || defined(SYSVSHM)
1602/*
1603 * sysctl helper routine for kern.sysvipc_info subtree.
1604 */
1605
1606#define	FILL_PERM(src, dst) do { \
1607	(dst)._key = (src)._key; \
1608	(dst).uid = (src).uid; \
1609	(dst).gid = (src).gid; \
1610	(dst).cuid = (src).cuid; \
1611	(dst).cgid = (src).cgid; \
1612	(dst).mode = (src).mode; \
1613	(dst)._seq = (src)._seq; \
1614} while (/*CONSTCOND*/ 0);
1615#define	FILL_MSG(src, dst) do { \
1616	FILL_PERM((src).msg_perm, (dst).msg_perm); \
1617	(dst).msg_qnum = (src).msg_qnum; \
1618	(dst).msg_qbytes = (src).msg_qbytes; \
1619	(dst)._msg_cbytes = (src)._msg_cbytes; \
1620	(dst).msg_lspid = (src).msg_lspid; \
1621	(dst).msg_lrpid = (src).msg_lrpid; \
1622	(dst).msg_stime = (src).msg_stime; \
1623	(dst).msg_rtime = (src).msg_rtime; \
1624	(dst).msg_ctime = (src).msg_ctime; \
1625} while (/*CONSTCOND*/ 0)
1626#define	FILL_SEM(src, dst) do { \
1627	FILL_PERM((src).sem_perm, (dst).sem_perm); \
1628	(dst).sem_nsems = (src).sem_nsems; \
1629	(dst).sem_otime = (src).sem_otime; \
1630	(dst).sem_ctime = (src).sem_ctime; \
1631} while (/*CONSTCOND*/ 0)
1632#define	FILL_SHM(src, dst) do { \
1633	FILL_PERM((src).shm_perm, (dst).shm_perm); \
1634	(dst).shm_segsz = (src).shm_segsz; \
1635	(dst).shm_lpid = (src).shm_lpid; \
1636	(dst).shm_cpid = (src).shm_cpid; \
1637	(dst).shm_atime = (src).shm_atime; \
1638	(dst).shm_dtime = (src).shm_dtime; \
1639	(dst).shm_ctime = (src).shm_ctime; \
1640	(dst).shm_nattch = (src).shm_nattch; \
1641} while (/*CONSTCOND*/ 0)
1642
1643static int
1644sysctl_kern_sysvipc(SYSCTLFN_ARGS)
1645{
1646	void *where = oldp;
1647	size_t *sizep = oldlenp;
1648#ifdef SYSVMSG
1649	struct msg_sysctl_info *msgsi = NULL;
1650#endif
1651#ifdef SYSVSEM
1652	struct sem_sysctl_info *semsi = NULL;
1653#endif
1654#ifdef SYSVSHM
1655	struct shm_sysctl_info *shmsi = NULL;
1656#endif
1657	size_t infosize, dssize, tsize, buflen;
1658	void *bf = NULL;
1659	char *start;
1660	int32_t nds;
1661	int i, error, ret;
1662
1663	if (namelen != 1)
1664		return (EINVAL);
1665
1666	start = where;
1667	buflen = *sizep;
1668
1669	switch (*name) {
1670	case KERN_SYSVIPC_MSG_INFO:
1671#ifdef SYSVMSG
1672		infosize = sizeof(msgsi->msginfo);
1673		nds = msginfo.msgmni;
1674		dssize = sizeof(msgsi->msgids[0]);
1675		break;
1676#else
1677		return (EINVAL);
1678#endif
1679	case KERN_SYSVIPC_SEM_INFO:
1680#ifdef SYSVSEM
1681		infosize = sizeof(semsi->seminfo);
1682		nds = seminfo.semmni;
1683		dssize = sizeof(semsi->semids[0]);
1684		break;
1685#else
1686		return (EINVAL);
1687#endif
1688	case KERN_SYSVIPC_SHM_INFO:
1689#ifdef SYSVSHM
1690		infosize = sizeof(shmsi->shminfo);
1691		nds = shminfo.shmmni;
1692		dssize = sizeof(shmsi->shmids[0]);
1693		break;
1694#else
1695		return (EINVAL);
1696#endif
1697	default:
1698		return (EINVAL);
1699	}
1700	/*
1701	 * Round infosize to 64 bit boundary if requesting more than just
1702	 * the info structure or getting the total data size.
1703	 */
1704	if (where == NULL || *sizep > infosize)
1705		infosize = ((infosize + 7) / 8) * 8;
1706	tsize = infosize + nds * dssize;
1707
1708	/* Return just the total size required. */
1709	if (where == NULL) {
1710		*sizep = tsize;
1711		return (0);
1712	}
1713
1714	/* Not enough room for even the info struct. */
1715	if (buflen < infosize) {
1716		*sizep = 0;
1717		return (ENOMEM);
1718	}
1719	bf = malloc(min(tsize, buflen), M_TEMP, M_WAITOK);
1720	memset(bf, 0, min(tsize, buflen));
1721
1722	switch (*name) {
1723#ifdef SYSVMSG
1724	case KERN_SYSVIPC_MSG_INFO:
1725		msgsi = (struct msg_sysctl_info *)bf;
1726		msgsi->msginfo = msginfo;
1727		break;
1728#endif
1729#ifdef SYSVSEM
1730	case KERN_SYSVIPC_SEM_INFO:
1731		semsi = (struct sem_sysctl_info *)bf;
1732		semsi->seminfo = seminfo;
1733		break;
1734#endif
1735#ifdef SYSVSHM
1736	case KERN_SYSVIPC_SHM_INFO:
1737		shmsi = (struct shm_sysctl_info *)bf;
1738		shmsi->shminfo = shminfo;
1739		break;
1740#endif
1741	}
1742	buflen -= infosize;
1743
1744	ret = 0;
1745	if (buflen > 0) {
1746		/* Fill in the IPC data structures.  */
1747		for (i = 0; i < nds; i++) {
1748			if (buflen < dssize) {
1749				ret = ENOMEM;
1750				break;
1751			}
1752			switch (*name) {
1753#ifdef SYSVMSG
1754			case KERN_SYSVIPC_MSG_INFO:
1755				FILL_MSG(msqids[i], msgsi->msgids[i]);
1756				break;
1757#endif
1758#ifdef SYSVSEM
1759			case KERN_SYSVIPC_SEM_INFO:
1760				FILL_SEM(sema[i], semsi->semids[i]);
1761				break;
1762#endif
1763#ifdef SYSVSHM
1764			case KERN_SYSVIPC_SHM_INFO:
1765				FILL_SHM(shmsegs[i], shmsi->shmids[i]);
1766				break;
1767#endif
1768			}
1769			buflen -= dssize;
1770		}
1771	}
1772	*sizep -= buflen;
1773	error = copyout(bf, start, *sizep);
1774	/* If copyout succeeded, use return code set earlier. */
1775	if (error == 0)
1776		error = ret;
1777	if (bf)
1778		free(bf, M_TEMP);
1779	return (error);
1780}
1781
1782#undef FILL_PERM
1783#undef FILL_MSG
1784#undef FILL_SEM
1785#undef FILL_SHM
1786
1787#endif /* defined(SYSVMSG) || defined(SYSVSEM) || defined(SYSVSHM) */
1788
1789#if NPTY > 0
1790/*
1791 * sysctl helper routine for kern.maxptys.  ensures that any new value
1792 * is acceptable to the pty subsystem.
1793 */
1794static int
1795sysctl_kern_maxptys(SYSCTLFN_ARGS)
1796{
1797	int pty_maxptys(int, int);		/* defined in kern/tty_pty.c */
1798	int error, xmax;
1799	struct sysctlnode node;
1800
1801	/* get current value of maxptys */
1802	xmax = pty_maxptys(0, 0);
1803
1804	node = *rnode;
1805	node.sysctl_data = &xmax;
1806	error = sysctl_lookup(SYSCTLFN_CALL(&node));
1807	if (error || newp == NULL)
1808		return (error);
1809
1810	if (xmax != pty_maxptys(xmax, 1))
1811		return (EINVAL);
1812
1813	return (0);
1814}
1815#endif /* NPTY > 0 */
1816
1817/*
1818 * sysctl helper routine for kern.sbmax.  basically just ensures that
1819 * any new value is not too small.
1820 */
1821static int
1822sysctl_kern_sbmax(SYSCTLFN_ARGS)
1823{
1824	int error, new_sbmax;
1825	struct sysctlnode node;
1826
1827	new_sbmax = sb_max;
1828	node = *rnode;
1829	node.sysctl_data = &new_sbmax;
1830	error = sysctl_lookup(SYSCTLFN_CALL(&node));
1831	if (error || newp == NULL)
1832		return (error);
1833
1834	error = sb_max_set(new_sbmax);
1835
1836	return (error);
1837}
1838
1839/*
1840 * sysctl helper routine for kern.urandom node.  picks a random number
1841 * for you.
1842 */
1843static int
1844sysctl_kern_urnd(SYSCTLFN_ARGS)
1845{
1846#if NRND > 0
1847	int v;
1848
1849	if (rnd_extract_data(&v, sizeof(v), RND_EXTRACT_ANY) == sizeof(v)) {
1850		struct sysctlnode node = *rnode;
1851		node.sysctl_data = &v;
1852		return (sysctl_lookup(SYSCTLFN_CALL(&node)));
1853	}
1854	else
1855		return (EIO);	/*XXX*/
1856#else
1857	return (EOPNOTSUPP);
1858#endif
1859}
1860
1861/*
1862 * sysctl helper routine to do kern.lwp.* work.
1863 */
1864static int
1865sysctl_kern_lwp(SYSCTLFN_ARGS)
1866{
1867	struct kinfo_lwp klwp;
1868	struct proc *p;
1869	struct lwp *l2;
1870	char *where, *dp;
1871	int pid, elem_size, elem_count;
1872	int buflen, needed, error;
1873
1874	if (namelen == 1 && name[0] == CTL_QUERY)
1875		return (sysctl_query(SYSCTLFN_CALL(rnode)));
1876
1877	dp = where = oldp;
1878	buflen = where != NULL ? *oldlenp : 0;
1879	error = needed = 0;
1880
1881	if (newp != NULL || namelen != 3)
1882		return (EINVAL);
1883	pid = name[0];
1884	elem_size = name[1];
1885	elem_count = name[2];
1886
1887	p = pfind(pid);
1888	if (p == NULL)
1889		return (ESRCH);
1890	LIST_FOREACH(l2, &p->p_lwps, l_sibling) {
1891		if (buflen >= elem_size && elem_count > 0) {
1892			fill_lwp(l2, &klwp);
1893			/*
1894			 * Copy out elem_size, but not larger than
1895			 * the size of a struct kinfo_proc2.
1896			 */
1897			error = copyout(&klwp, dp,
1898			    min(sizeof(klwp), elem_size));
1899			if (error)
1900				goto cleanup;
1901			dp += elem_size;
1902			buflen -= elem_size;
1903			elem_count--;
1904		}
1905		needed += elem_size;
1906	}
1907
1908	if (where != NULL) {
1909		*oldlenp = dp - where;
1910		if (needed > *oldlenp)
1911			return (ENOMEM);
1912	} else {
1913		needed += KERN_LWPSLOP;
1914		*oldlenp = needed;
1915	}
1916	return (0);
1917 cleanup:
1918	return (error);
1919}
1920
1921/*
1922 * sysctl helper routine for kern.forkfsleep node.  ensures that the
1923 * given value is not too large or two small, and is at least one
1924 * timer tick if not zero.
1925 */
1926static int
1927sysctl_kern_forkfsleep(SYSCTLFN_ARGS)
1928{
1929	/* userland sees value in ms, internally is in ticks */
1930	extern int forkfsleep;		/* defined in kern/kern_fork.c */
1931	int error, timo, lsleep;
1932	struct sysctlnode node;
1933
1934	lsleep = forkfsleep * 1000 / hz;
1935	node = *rnode;
1936	node.sysctl_data = &lsleep;
1937	error = sysctl_lookup(SYSCTLFN_CALL(&node));
1938	if (error || newp == NULL)
1939		return (error);
1940
1941	/* refuse negative values, and overly 'long time' */
1942	if (lsleep < 0 || lsleep > MAXSLP * 1000)
1943		return (EINVAL);
1944
1945	timo = mstohz(lsleep);
1946
1947	/* if the interval is >0 ms && <1 tick, use 1 tick */
1948	if (lsleep != 0 && timo == 0)
1949		forkfsleep = 1;
1950	else
1951		forkfsleep = timo;
1952
1953	return (0);
1954}
1955
1956/*
1957 * sysctl helper routine for kern.root_partition
1958 */
1959static int
1960sysctl_kern_root_partition(SYSCTLFN_ARGS)
1961{
1962	int rootpart = DISKPART(rootdev);
1963	struct sysctlnode node = *rnode;
1964
1965	node.sysctl_data = &rootpart;
1966	return (sysctl_lookup(SYSCTLFN_CALL(&node)));
1967}
1968
1969/*
1970 * sysctl helper function for kern.drivers
1971 */
1972static int
1973sysctl_kern_drivers(SYSCTLFN_ARGS)
1974{
1975	int error;
1976	size_t buflen;
1977	struct kinfo_drivers kd;
1978	char *start, *where;
1979	const char *dname;
1980	int i;
1981	extern struct devsw_conv *devsw_conv;
1982	extern int max_devsw_convs;
1983
1984	if (newp != NULL || namelen != 0)
1985		return (EINVAL);
1986
1987	start = where = oldp;
1988	buflen = *oldlenp;
1989	if (where == NULL) {
1990		*oldlenp = max_devsw_convs * sizeof kd;
1991		return 0;
1992	}
1993
1994	/*
1995	 * An array of kinfo_drivers structures
1996	 */
1997	error = 0;
1998	for (i = 0; i < max_devsw_convs; i++) {
1999		dname = devsw_conv[i].d_name;
2000		if (dname == NULL)
2001			continue;
2002		if (buflen < sizeof kd) {
2003			error = ENOMEM;
2004			break;
2005		}
2006		memset(&kd, 0, sizeof(kd));
2007		kd.d_bmajor = devsw_conv[i].d_bmajor;
2008		kd.d_cmajor = devsw_conv[i].d_cmajor;
2009		strlcpy(kd.d_name, dname, sizeof kd.d_name);
2010		error = copyout(&kd, where, sizeof kd);
2011		if (error != 0)
2012			break;
2013		buflen -= sizeof kd;
2014		where += sizeof kd;
2015	}
2016	*oldlenp = where - start;
2017	return error;
2018}
2019
2020/*
2021 * sysctl helper function for kern.file2
2022 */
2023static int
2024sysctl_kern_file2(SYSCTLFN_ARGS)
2025{
2026	struct proc *p;
2027	struct file *fp;
2028	struct filedesc *fd;
2029	struct kinfo_file kf;
2030	char *dp;
2031	u_int i, op;
2032	size_t len, needed, elem_size, out_size;
2033	int error, arg, elem_count;
2034
2035	if (namelen == 1 && name[0] == CTL_QUERY)
2036		return (sysctl_query(SYSCTLFN_CALL(rnode)));
2037
2038	if (namelen != 4)
2039		return (EINVAL);
2040
2041	error = 0;
2042	dp = oldp;
2043	len = (oldp != NULL) ? *oldlenp : 0;
2044	op = name[0];
2045	arg = name[1];
2046	elem_size = name[2];
2047	elem_count = name[3];
2048	out_size = MIN(sizeof(kf), elem_size);
2049	needed = 0;
2050
2051	if (elem_size < 1 || elem_count < 0)
2052		return (EINVAL);
2053
2054	switch (op) {
2055	case KERN_FILE_BYFILE:
2056		/*
2057		 * doesn't use arg so it must be zero
2058		 */
2059		if (arg != 0)
2060			return (EINVAL);
2061		LIST_FOREACH(fp, &filehead, f_list) {
2062			if (CURTAIN(l->l_proc->p_ucred->cr_uid,
2063				    fp->f_cred->cr_uid))
2064				continue;
2065			if (len >= elem_size && elem_count > 0) {
2066				fill_file(&kf, fp, NULL, 0);
2067				error = copyout(&kf, dp, out_size);
2068				if (error)
2069					break;
2070				dp += elem_size;
2071				len -= elem_size;
2072			}
2073			if (elem_count > 0) {
2074				needed += elem_size;
2075				if (elem_count != INT_MAX)
2076					elem_count--;
2077			}
2078		}
2079		break;
2080	    case KERN_FILE_BYPID:
2081		if (arg < -1)
2082			/* -1 means all processes */
2083			return (EINVAL);
2084		proclist_lock_read();
2085		PROCLIST_FOREACH(p, &allproc) {
2086			if (p->p_stat == SIDL)
2087				/* skip embryonic processes */
2088				continue;
2089			if (CURTAIN(l->l_proc->p_ucred->cr_uid,
2090				    p->p_ucred->cr_uid))
2091				continue;
2092			if (arg > 0 && p->p_pid != arg)
2093				/* pick only the one we want */
2094				/* XXX want 0 to mean "kernel files" */
2095				continue;
2096			fd = p->p_fd;
2097			for (i = 0; i < fd->fd_nfiles; i++) {
2098				fp = fd->fd_ofiles[i];
2099				if (fp == NULL || !FILE_IS_USABLE(fp))
2100					continue;
2101				if (len >= elem_size && elem_count > 0) {
2102					fill_file(&kf, fd->fd_ofiles[i],
2103						  p, i);
2104					error = copyout(&kf, dp, out_size);
2105					if (error)
2106						break;
2107					dp += elem_size;
2108					len -= elem_size;
2109				}
2110				if (elem_count > 0) {
2111					needed += elem_size;
2112					if (elem_count != INT_MAX)
2113						elem_count--;
2114				}
2115			}
2116		}
2117		proclist_unlock_read();
2118		break;
2119	default:
2120		return (EINVAL);
2121	}
2122
2123	if (oldp == NULL)
2124		needed += KERN_FILESLOP * elem_size;
2125	*oldlenp = needed;
2126
2127	return (error);
2128}
2129
2130static void
2131fill_file(struct kinfo_file *kp, const struct file *fp, struct proc *p, int i)
2132{
2133
2134	memset(kp, 0, sizeof(*kp));
2135
2136	kp->ki_fileaddr =	PTRTOUINT64(fp);
2137	kp->ki_flag =		fp->f_flag;
2138	kp->ki_iflags =		fp->f_iflags;
2139	kp->ki_ftype =		fp->f_type;
2140	kp->ki_count =		fp->f_count;
2141	kp->ki_msgcount =	fp->f_msgcount;
2142	kp->ki_usecount =	fp->f_usecount;
2143	kp->ki_fucred =		PTRTOUINT64(fp->f_cred);
2144	kp->ki_fuid =		fp->f_cred->cr_uid;
2145	kp->ki_fgid =		fp->f_cred->cr_gid;
2146	kp->ki_fops =		PTRTOUINT64(fp->f_ops);
2147	kp->ki_foffset =	fp->f_offset;
2148	kp->ki_fdata =		PTRTOUINT64(fp->f_data);
2149
2150	/* vnode information to glue this file to something */
2151	if (fp->f_type == DTYPE_VNODE) {
2152		struct vnode *vp = (struct vnode *)fp->f_data;
2153
2154		kp->ki_vun =	PTRTOUINT64(vp->v_un.vu_socket);
2155		kp->ki_vsize =	vp->v_size;
2156		kp->ki_vtype =	vp->v_type;
2157		kp->ki_vtag =	vp->v_tag;
2158		kp->ki_vdata =	PTRTOUINT64(vp->v_data);
2159	}
2160
2161        /* process information when retrieved via KERN_FILE_BYPID */
2162	if (p) {
2163		kp->ki_pid =		p->p_pid;
2164		kp->ki_fd =		i;
2165		kp->ki_ofileflags =	p->p_fd->fd_ofileflags[i];
2166	}
2167}
2168
2169static int
2170sysctl_doeproc(SYSCTLFN_ARGS)
2171{
2172	struct eproc eproc;
2173	struct kinfo_proc2 kproc2;
2174	struct kinfo_proc *dp;
2175	struct proc *p;
2176	const struct proclist_desc *pd;
2177	char *where, *dp2;
2178	int type, op, arg;
2179	u_int elem_size, elem_count;
2180	size_t buflen, needed;
2181	int error;
2182
2183	if (namelen == 1 && name[0] == CTL_QUERY)
2184		return (sysctl_query(SYSCTLFN_CALL(rnode)));
2185
2186	dp = oldp;
2187	dp2 = where = oldp;
2188	buflen = where != NULL ? *oldlenp : 0;
2189	error = 0;
2190	needed = 0;
2191	type = rnode->sysctl_num;
2192
2193	if (type == KERN_PROC) {
2194		if (namelen != 2 && !(namelen == 1 && name[0] == KERN_PROC_ALL))
2195			return (EINVAL);
2196		op = name[0];
2197		if (op != KERN_PROC_ALL)
2198			arg = name[1];
2199		else
2200			arg = 0;		/* Quell compiler warning */
2201		elem_size = elem_count = 0;	/* Ditto */
2202	} else {
2203		if (namelen != 4)
2204			return (EINVAL);
2205		op = name[0];
2206		arg = name[1];
2207		elem_size = name[2];
2208		elem_count = name[3];
2209	}
2210
2211	proclist_lock_read();
2212
2213	pd = proclists;
2214again:
2215	PROCLIST_FOREACH(p, pd->pd_list) {
2216		/*
2217		 * Skip embryonic processes.
2218		 */
2219		if (p->p_stat == SIDL)
2220			continue;
2221
2222		if (CURTAIN(l->l_proc->p_ucred->cr_uid, p->p_ucred->cr_uid))
2223			continue;
2224
2225		/*
2226		 * TODO - make more efficient (see notes below).
2227		 * do by session.
2228		 */
2229		switch (op) {
2230
2231		case KERN_PROC_PID:
2232			/* could do this with just a lookup */
2233			if (p->p_pid != (pid_t)arg)
2234				continue;
2235			break;
2236
2237		case KERN_PROC_PGRP:
2238			/* could do this by traversing pgrp */
2239			if (p->p_pgrp->pg_id != (pid_t)arg)
2240				continue;
2241			break;
2242
2243		case KERN_PROC_SESSION:
2244			if (p->p_session->s_sid != (pid_t)arg)
2245				continue;
2246			break;
2247
2248		case KERN_PROC_TTY:
2249			if (arg == (int) KERN_PROC_TTY_REVOKE) {
2250				if ((p->p_flag & P_CONTROLT) == 0 ||
2251				    p->p_session->s_ttyp == NULL ||
2252				    p->p_session->s_ttyvp != NULL)
2253					continue;
2254			} else if ((p->p_flag & P_CONTROLT) == 0 ||
2255			    p->p_session->s_ttyp == NULL) {
2256				if ((dev_t)arg != KERN_PROC_TTY_NODEV)
2257					continue;
2258			} else if (p->p_session->s_ttyp->t_dev != (dev_t)arg)
2259				continue;
2260			break;
2261
2262		case KERN_PROC_UID:
2263			if (p->p_ucred->cr_uid != (uid_t)arg)
2264				continue;
2265			break;
2266
2267		case KERN_PROC_RUID:
2268			if (p->p_cred->p_ruid != (uid_t)arg)
2269				continue;
2270			break;
2271
2272		case KERN_PROC_GID:
2273			if (p->p_ucred->cr_gid != (uid_t)arg)
2274				continue;
2275			break;
2276
2277		case KERN_PROC_RGID:
2278			if (p->p_cred->p_rgid != (uid_t)arg)
2279				continue;
2280			break;
2281
2282		case KERN_PROC_ALL:
2283			/* allow everything */
2284			break;
2285
2286		default:
2287			error = EINVAL;
2288			goto cleanup;
2289		}
2290		if (type == KERN_PROC) {
2291			if (buflen >= sizeof(struct kinfo_proc)) {
2292				fill_eproc(p, &eproc);
2293				error = copyout(p, &dp->kp_proc,
2294				    sizeof(struct proc));
2295				if (error)
2296					goto cleanup;
2297				error = copyout(&eproc, &dp->kp_eproc,
2298				    sizeof(eproc));
2299				if (error)
2300					goto cleanup;
2301				dp++;
2302				buflen -= sizeof(struct kinfo_proc);
2303			}
2304			needed += sizeof(struct kinfo_proc);
2305		} else { /* KERN_PROC2 */
2306			if (buflen >= elem_size && elem_count > 0) {
2307				fill_kproc2(p, &kproc2);
2308				/*
2309				 * Copy out elem_size, but not larger than
2310				 * the size of a struct kinfo_proc2.
2311				 */
2312				error = copyout(&kproc2, dp2,
2313				    min(sizeof(kproc2), elem_size));
2314				if (error)
2315					goto cleanup;
2316				dp2 += elem_size;
2317				buflen -= elem_size;
2318				elem_count--;
2319			}
2320			needed += elem_size;
2321		}
2322	}
2323	pd++;
2324	if (pd->pd_list != NULL)
2325		goto again;
2326	proclist_unlock_read();
2327
2328	if (where != NULL) {
2329		if (type == KERN_PROC)
2330			*oldlenp = (char *)dp - where;
2331		else
2332			*oldlenp = dp2 - where;
2333		if (needed > *oldlenp)
2334			return (ENOMEM);
2335	} else {
2336		needed += KERN_PROCSLOP;
2337		*oldlenp = needed;
2338	}
2339	return (0);
2340 cleanup:
2341	proclist_unlock_read();
2342	return (error);
2343}
2344
2345/*
2346 * sysctl helper routine for kern.proc_args pseudo-subtree.
2347 */
2348static int
2349sysctl_kern_proc_args(SYSCTLFN_ARGS)
2350{
2351	struct ps_strings pss;
2352	struct proc *p, *up = l->l_proc;
2353	size_t len, upper_bound, xlen, i;
2354	struct uio auio;
2355	struct iovec aiov;
2356	vaddr_t argv;
2357	pid_t pid;
2358	int nargv, type, error;
2359	char *arg;
2360	char *tmp;
2361	struct vmspace *vmspace;
2362	vaddr_t psstr_addr;
2363	vaddr_t offsetn;
2364	vaddr_t offsetv;
2365
2366	if (namelen == 1 && name[0] == CTL_QUERY)
2367		return (sysctl_query(SYSCTLFN_CALL(rnode)));
2368
2369	if (newp != NULL || namelen != 2)
2370		return (EINVAL);
2371	pid = name[0];
2372	type = name[1];
2373
2374	switch (type) {
2375	case KERN_PROC_ARGV:
2376	case KERN_PROC_NARGV:
2377	case KERN_PROC_ENV:
2378	case KERN_PROC_NENV:
2379		/* ok */
2380		break;
2381	default:
2382		return (EINVAL);
2383	}
2384
2385	proclist_lock_read();
2386
2387	/* check pid */
2388	if ((p = p_find(pid, PFIND_LOCKED)) == NULL) {
2389		error = EINVAL;
2390		goto out_locked;
2391	}
2392
2393	if (CURTAIN(l->l_proc->p_ucred->cr_uid, p->p_ucred->cr_uid)) {
2394		error = EPERM;
2395		goto out_locked;
2396	}
2397
2398	/* only root or same user change look at the environment */
2399	if (type == KERN_PROC_ENV || type == KERN_PROC_NENV) {
2400		if (up->p_ucred->cr_uid != 0) {
2401			if (up->p_cred->p_ruid != p->p_cred->p_ruid ||
2402			    up->p_cred->p_ruid != p->p_cred->p_svuid) {
2403				error = EPERM;
2404				goto out_locked;
2405			}
2406		}
2407	}
2408
2409	if (oldp == NULL) {
2410		if (type == KERN_PROC_NARGV || type == KERN_PROC_NENV)
2411			*oldlenp = sizeof (int);
2412		else
2413			*oldlenp = ARG_MAX;	/* XXX XXX XXX */
2414		error = 0;
2415		goto out_locked;
2416	}
2417
2418	/*
2419	 * Zombies don't have a stack, so we can't read their psstrings.
2420	 * System processes also don't have a user stack.
2421	 */
2422	if (P_ZOMBIE(p) || (p->p_flag & P_SYSTEM) != 0) {
2423		error = EINVAL;
2424		goto out_locked;
2425	}
2426
2427	/*
2428	 * Lock the process down in memory.
2429	 */
2430	/* XXXCDC: how should locking work here? */
2431	if ((p->p_flag & P_WEXIT) || (p->p_vmspace->vm_refcnt < 1)) {
2432		error = EFAULT;
2433		goto out_locked;
2434	}
2435
2436	psstr_addr = (vaddr_t)p->p_psstr;
2437	if (type == KERN_PROC_ARGV || type == KERN_PROC_NARGV) {
2438		offsetn = p->p_psnargv;
2439		offsetv = p->p_psargv;
2440	} else {
2441		offsetn = p->p_psnenv;
2442		offsetv = p->p_psenv;
2443	}
2444	vmspace = p->p_vmspace;
2445	vmspace->vm_refcnt++;	/* XXX */
2446
2447	proclist_unlock_read();
2448
2449	/*
2450	 * Allocate a temporary buffer to hold the arguments.
2451	 */
2452	arg = malloc(PAGE_SIZE, M_TEMP, M_WAITOK);
2453
2454	/*
2455	 * Read in the ps_strings structure.
2456	 */
2457	aiov.iov_base = &pss;
2458	aiov.iov_len = sizeof(pss);
2459	auio.uio_iov = &aiov;
2460	auio.uio_iovcnt = 1;
2461	auio.uio_offset = psstr_addr;
2462	auio.uio_resid = sizeof(pss);
2463	auio.uio_rw = UIO_READ;
2464	UIO_SETUP_SYSSPACE(&auio);
2465	error = uvm_io(&vmspace->vm_map, &auio);
2466	if (error)
2467		goto done;
2468
2469	memcpy(&nargv, (char *)&pss + offsetn, sizeof(nargv));
2470	if (type == KERN_PROC_NARGV || type == KERN_PROC_NENV) {
2471		error = copyout(&nargv, oldp, sizeof(nargv));
2472		*oldlenp = sizeof(nargv);
2473		goto done;
2474	}
2475	/*
2476	 * Now read the address of the argument vector.
2477	 */
2478	switch (type) {
2479	case KERN_PROC_ARGV:
2480		/* XXX compat32 stuff here */
2481		/* FALLTHROUGH */
2482	case KERN_PROC_ENV:
2483		memcpy(&tmp, (char *)&pss + offsetv, sizeof(tmp));
2484		break;
2485	default:
2486		return (EINVAL);
2487	}
2488	auio.uio_offset = (off_t)(unsigned long)tmp;
2489	aiov.iov_base = &argv;
2490	aiov.iov_len = sizeof(argv);
2491	auio.uio_iov = &aiov;
2492	auio.uio_iovcnt = 1;
2493	auio.uio_resid = sizeof(argv);
2494	auio.uio_rw = UIO_READ;
2495	UIO_SETUP_SYSSPACE(&auio);
2496	error = uvm_io(&vmspace->vm_map, &auio);
2497	if (error)
2498		goto done;
2499
2500	/*
2501	 * Now copy in the actual argument vector, one page at a time,
2502	 * since we don't know how long the vector is (though, we do
2503	 * know how many NUL-terminated strings are in the vector).
2504	 */
2505	len = 0;
2506	upper_bound = *oldlenp;
2507	for (; nargv != 0 && len < upper_bound; len += xlen) {
2508		aiov.iov_base = arg;
2509		aiov.iov_len = PAGE_SIZE;
2510		auio.uio_iov = &aiov;
2511		auio.uio_iovcnt = 1;
2512		auio.uio_offset = argv + len;
2513		xlen = PAGE_SIZE - ((argv + len) & PAGE_MASK);
2514		auio.uio_resid = xlen;
2515		auio.uio_rw = UIO_READ;
2516		UIO_SETUP_SYSSPACE(&auio);
2517		error = uvm_io(&vmspace->vm_map, &auio);
2518		if (error)
2519			goto done;
2520
2521		for (i = 0; i < xlen && nargv != 0; i++) {
2522			if (arg[i] == '\0')
2523				nargv--;	/* one full string */
2524		}
2525
2526		/*
2527		 * Make sure we don't copyout past the end of the user's
2528		 * buffer.
2529		 */
2530		if (len + i > upper_bound)
2531			i = upper_bound - len;
2532
2533		error = copyout(arg, (char *)oldp + len, i);
2534		if (error)
2535			break;
2536
2537		if (nargv == 0) {
2538			len += i;
2539			break;
2540		}
2541	}
2542	*oldlenp = len;
2543
2544done:
2545	uvmspace_free(vmspace);
2546
2547	free(arg, M_TEMP);
2548	return error;
2549
2550out_locked:
2551	proclist_unlock_read();
2552	return error;
2553}
2554
2555/*
2556 * Sysctl helper routine for Verified Exec.
2557 */
2558#ifdef VERIFIED_EXEC
2559static int
2560sysctl_kern_veriexec(SYSCTLFN_ARGS)
2561{
2562	int newval, error;
2563	int *var = NULL, raise_only = 0;
2564	struct sysctlnode node;
2565
2566	node = *rnode;
2567
2568	switch (rnode->sysctl_num) {
2569	case VERIEXEC_STRICT:
2570		raise_only = 1;
2571		var = &veriexec_strict;
2572		break;
2573	case VERIEXEC_ALGORITHMS:
2574		node.sysctl_data = veriexec_fp_names;
2575		node.sysctl_size = strlen(veriexec_fp_names) + 1;
2576		return (sysctl_lookup(SYSCTLFN_CALL(&node)));
2577	default:
2578		return (EINVAL);
2579	}
2580
2581	newval = *var;
2582
2583	node.sysctl_data = &newval;
2584	error = sysctl_lookup(SYSCTLFN_CALL(&node));
2585	if (error || newp == NULL) {
2586		return (error);
2587	}
2588
2589	if (raise_only && (newval < *var))
2590		return (EPERM);
2591
2592	*var = newval;
2593
2594	return (error);
2595}
2596#endif /* VERIFIED_EXEC */
2597
2598static int
2599sysctl_security_setidcore(SYSCTLFN_ARGS)
2600{
2601	int newsize, error;
2602	struct sysctlnode node;
2603
2604	node = *rnode;
2605	node.sysctl_data = &newsize;
2606	newsize = *(int *)rnode->sysctl_data;
2607	error = sysctl_lookup(SYSCTLFN_CALL(&node));
2608	if (error || newp == NULL)
2609		return error;
2610
2611	if (securelevel > 0)
2612		return (EPERM);
2613
2614	*(int *)rnode->sysctl_data = newsize;
2615
2616	return 0;
2617}
2618
2619static int
2620sysctl_security_setidcorename(SYSCTLFN_ARGS)
2621{
2622	int error;
2623	char newsetidcorename[MAXPATHLEN];
2624	struct sysctlnode node;
2625
2626	node = *rnode;
2627	node.sysctl_data = &newsetidcorename[0];
2628	memcpy(node.sysctl_data, rnode->sysctl_data, MAXPATHLEN);
2629	error = sysctl_lookup(SYSCTLFN_CALL(&node));
2630	if (error || newp == NULL)
2631		return (error);
2632
2633	if (securelevel > 0)
2634		return (EPERM);
2635
2636	if (strlen(newsetidcorename) == 0)
2637		return (EINVAL);
2638
2639	memcpy(rnode->sysctl_data, node.sysctl_data, MAXPATHLEN);
2640
2641	return (0);
2642}
2643
2644/*
2645 * sysctl helper routine for kern.cp_id node.  maps cpus to their
2646 * cpuids.
2647 */
2648static int
2649sysctl_kern_cpid(SYSCTLFN_ARGS)
2650{
2651	struct sysctlnode node = *rnode;
2652
2653#ifndef MULTIPROCESSOR
2654	uint64_t id;
2655
2656	if (namelen == 1) {
2657		if (name[0] != 0)
2658			return (ENOENT);
2659		/*
2660		 * you're allowed to ask for the zero'th processor
2661		 */
2662		name++;
2663		namelen--;
2664	}
2665	node.sysctl_data = &id;
2666	node.sysctl_size = sizeof(id);
2667	id = cpu_number();
2668	return (sysctl_lookup(SYSCTLFN_CALL(&node)));
2669
2670#else /* MULTIPROCESSOR */
2671	uint64_t *cp_id = NULL;
2672	int error, n = sysctl_ncpus();
2673	struct cpu_info *ci;
2674	CPU_INFO_ITERATOR cii;
2675
2676	/*
2677	 * here you may either retrieve a single cpu id or the whole
2678	 * set.  the size you get back when probing depends on what
2679	 * you ask for.
2680	 */
2681	switch (namelen) {
2682	case 0:
2683		node.sysctl_size = n * sizeof(uint64_t);
2684		n = -2; /* ALL */
2685		break;
2686	case 1:
2687		if (name[0] < 0 || name[0] >= n)
2688			return (ENOENT); /* ENOSUCHPROCESSOR */
2689		node.sysctl_size = sizeof(uint64_t);
2690		n = name[0];
2691		/*
2692		 * adjust these so that sysctl_lookup() will be happy
2693		 */
2694		name++;
2695		namelen--;
2696		break;
2697	default:
2698		return (EINVAL);
2699	}
2700
2701	cp_id = malloc(node.sysctl_size, M_TEMP, M_WAITOK|M_CANFAIL);
2702	if (cp_id == NULL)
2703		return (ENOMEM);
2704	node.sysctl_data = cp_id;
2705	memset(cp_id, 0, node.sysctl_size);
2706
2707	for (CPU_INFO_FOREACH(cii, ci)) {
2708		if (n <= 0)
2709			cp_id[0] = ci->ci_cpuid;
2710		/*
2711		 * if a specific processor was requested and we just
2712		 * did it, we're done here
2713		 */
2714		if (n == 0)
2715			break;
2716		/*
2717		 * if doing "all", skip to next cp_id slot for next processor
2718		 */
2719		if (n == -2)
2720			cp_id++;
2721		/*
2722		 * if we're doing a specific processor, we're one
2723		 * processor closer
2724		 */
2725		if (n > 0)
2726			n--;
2727	}
2728
2729	error = sysctl_lookup(SYSCTLFN_CALL(&node));
2730	free(node.sysctl_data, M_TEMP);
2731	return (error);
2732
2733#endif /* MULTIPROCESSOR */
2734}
2735
2736/*
2737 * sysctl helper routine for hw.usermem and hw.usermem64.  values are
2738 * calculate on the fly taking into account integer overflow and the
2739 * current wired count.
2740 */
2741static int
2742sysctl_hw_usermem(SYSCTLFN_ARGS)
2743{
2744	u_int ui;
2745	u_quad_t uq;
2746	struct sysctlnode node;
2747
2748	node = *rnode;
2749	switch (rnode->sysctl_num) {
2750	    case HW_USERMEM:
2751		if ((ui = physmem - uvmexp.wired) > (UINT_MAX / PAGE_SIZE))
2752			ui = UINT_MAX;
2753		else
2754			ui *= PAGE_SIZE;
2755		node.sysctl_data = &ui;
2756		break;
2757	case HW_USERMEM64:
2758		uq = (u_quad_t)(physmem - uvmexp.wired) * PAGE_SIZE;
2759		node.sysctl_data = &uq;
2760		break;
2761	default:
2762		return (EINVAL);
2763	}
2764
2765	return (sysctl_lookup(SYSCTLFN_CALL(&node)));
2766}
2767
2768/*
2769 * sysctl helper routine for kern.cnmagic node.  pulls the old value
2770 * out, encoded, and stuffs the new value in for decoding.
2771 */
2772static int
2773sysctl_hw_cnmagic(SYSCTLFN_ARGS)
2774{
2775	char magic[CNS_LEN];
2776	int error;
2777	struct sysctlnode node;
2778
2779	if (oldp)
2780		cn_get_magic(magic, CNS_LEN);
2781	node = *rnode;
2782	node.sysctl_data = &magic[0];
2783	error = sysctl_lookup(SYSCTLFN_CALL(&node));
2784	if (error || newp == NULL)
2785		return (error);
2786
2787	return (cn_set_magic(magic));
2788}
2789
2790static int
2791sysctl_hw_ncpu(SYSCTLFN_ARGS)
2792{
2793	int ncpu;
2794	struct sysctlnode node;
2795
2796	ncpu = sysctl_ncpus();
2797	node = *rnode;
2798	node.sysctl_data = &ncpu;
2799
2800	return (sysctl_lookup(SYSCTLFN_CALL(&node)));
2801}
2802
2803
2804/*
2805 * ********************************************************************
2806 * section 3: public helper routines that are used for more than one
2807 * node
2808 * ********************************************************************
2809 */
2810
2811/*
2812 * sysctl helper routine for the kern.root_device node and some ports'
2813 * machdep.root_device nodes.
2814 */
2815int
2816sysctl_root_device(SYSCTLFN_ARGS)
2817{
2818	struct sysctlnode node;
2819
2820	node = *rnode;
2821	node.sysctl_data = root_device->dv_xname;
2822	node.sysctl_size = strlen(root_device->dv_xname) + 1;
2823	return (sysctl_lookup(SYSCTLFN_CALL(&node)));
2824}
2825
2826/*
2827 * sysctl helper routine for kern.consdev, dependent on the current
2828 * state of the console.  also used for machdep.console_device on some
2829 * ports.
2830 */
2831int
2832sysctl_consdev(SYSCTLFN_ARGS)
2833{
2834	dev_t consdev;
2835	struct sysctlnode node;
2836
2837	if (cn_tab != NULL)
2838		consdev = cn_tab->cn_dev;
2839	else
2840		consdev = NODEV;
2841	node = *rnode;
2842	node.sysctl_data = &consdev;
2843	node.sysctl_size = sizeof(consdev);
2844	return (sysctl_lookup(SYSCTLFN_CALL(&node)));
2845}
2846
2847/*
2848 * ********************************************************************
2849 * section 4: support for some helpers
2850 * ********************************************************************
2851 */
2852
2853/*
2854 * Fill in a kinfo_proc2 structure for the specified process.
2855 */
2856static void
2857fill_kproc2(struct proc *p, struct kinfo_proc2 *ki)
2858{
2859	struct tty *tp;
2860	struct lwp *l;
2861	struct timeval ut, st;
2862
2863	memset(ki, 0, sizeof(*ki));
2864
2865	ki->p_paddr = PTRTOUINT64(p);
2866	ki->p_fd = PTRTOUINT64(p->p_fd);
2867	ki->p_cwdi = PTRTOUINT64(p->p_cwdi);
2868	ki->p_stats = PTRTOUINT64(p->p_stats);
2869	ki->p_limit = PTRTOUINT64(p->p_limit);
2870	ki->p_vmspace = PTRTOUINT64(p->p_vmspace);
2871	ki->p_sigacts = PTRTOUINT64(p->p_sigacts);
2872	ki->p_sess = PTRTOUINT64(p->p_session);
2873	ki->p_tsess = 0;	/* may be changed if controlling tty below */
2874	ki->p_ru = PTRTOUINT64(p->p_ru);
2875
2876	ki->p_eflag = 0;
2877	ki->p_exitsig = p->p_exitsig;
2878	ki->p_flag = p->p_flag;
2879
2880	ki->p_pid = p->p_pid;
2881	if (p->p_pptr)
2882		ki->p_ppid = p->p_pptr->p_pid;
2883	else
2884		ki->p_ppid = 0;
2885	ki->p_sid = p->p_session->s_sid;
2886	ki->p__pgid = p->p_pgrp->pg_id;
2887
2888	ki->p_tpgid = NO_PGID;	/* may be changed if controlling tty below */
2889
2890	ki->p_uid = p->p_ucred->cr_uid;
2891	ki->p_ruid = p->p_cred->p_ruid;
2892	ki->p_gid = p->p_ucred->cr_gid;
2893	ki->p_rgid = p->p_cred->p_rgid;
2894	ki->p_svuid = p->p_cred->p_svuid;
2895	ki->p_svgid = p->p_cred->p_svgid;
2896
2897	memcpy(ki->p_groups, p->p_cred->pc_ucred->cr_groups,
2898	    min(sizeof(ki->p_groups), sizeof(p->p_cred->pc_ucred->cr_groups)));
2899	ki->p_ngroups = p->p_cred->pc_ucred->cr_ngroups;
2900
2901	ki->p_jobc = p->p_pgrp->pg_jobc;
2902	if ((p->p_flag & P_CONTROLT) && (tp = p->p_session->s_ttyp)) {
2903		ki->p_tdev = tp->t_dev;
2904		ki->p_tpgid = tp->t_pgrp ? tp->t_pgrp->pg_id : NO_PGID;
2905		ki->p_tsess = PTRTOUINT64(tp->t_session);
2906	} else {
2907		ki->p_tdev = NODEV;
2908	}
2909
2910	ki->p_estcpu = p->p_estcpu;
2911	ki->p_rtime_sec = p->p_rtime.tv_sec;
2912	ki->p_rtime_usec = p->p_rtime.tv_usec;
2913	ki->p_cpticks = p->p_cpticks;
2914	ki->p_pctcpu = p->p_pctcpu;
2915
2916	ki->p_uticks = p->p_uticks;
2917	ki->p_sticks = p->p_sticks;
2918	ki->p_iticks = p->p_iticks;
2919
2920	ki->p_tracep = PTRTOUINT64(p->p_tracep);
2921	ki->p_traceflag = p->p_traceflag;
2922
2923
2924	memcpy(&ki->p_siglist, &p->p_sigctx.ps_siglist, sizeof(ki_sigset_t));
2925	memcpy(&ki->p_sigmask, &p->p_sigctx.ps_sigmask, sizeof(ki_sigset_t));
2926	memcpy(&ki->p_sigignore, &p->p_sigctx.ps_sigignore,sizeof(ki_sigset_t));
2927	memcpy(&ki->p_sigcatch, &p->p_sigctx.ps_sigcatch, sizeof(ki_sigset_t));
2928
2929	ki->p_stat = p->p_stat; /* Will likely be overridden by LWP status */
2930	ki->p_realstat = p->p_stat;
2931	ki->p_nice = p->p_nice;
2932
2933	ki->p_xstat = p->p_xstat;
2934	ki->p_acflag = p->p_acflag;
2935
2936	strncpy(ki->p_comm, p->p_comm,
2937	    min(sizeof(ki->p_comm), sizeof(p->p_comm)));
2938
2939	strncpy(ki->p_login, p->p_session->s_login,
2940	    min(sizeof ki->p_login - 1, sizeof p->p_session->s_login));
2941
2942	ki->p_nlwps = p->p_nlwps;
2943	ki->p_nrlwps = p->p_nrlwps;
2944	ki->p_realflag = p->p_flag;
2945
2946	if (p->p_stat == SIDL || P_ZOMBIE(p)) {
2947		ki->p_vm_rssize = 0;
2948		ki->p_vm_tsize = 0;
2949		ki->p_vm_dsize = 0;
2950		ki->p_vm_ssize = 0;
2951		l = NULL;
2952	} else {
2953		struct vmspace *vm = p->p_vmspace;
2954
2955		ki->p_vm_rssize = vm_resident_count(vm);
2956		ki->p_vm_tsize = vm->vm_tsize;
2957		ki->p_vm_dsize = vm->vm_dsize;
2958		ki->p_vm_ssize = vm->vm_ssize;
2959
2960		/* Pick a "representative" LWP */
2961		l = proc_representative_lwp(p);
2962		ki->p_forw = PTRTOUINT64(l->l_forw);
2963		ki->p_back = PTRTOUINT64(l->l_back);
2964		ki->p_addr = PTRTOUINT64(l->l_addr);
2965		ki->p_stat = l->l_stat;
2966		ki->p_flag |= l->l_flag & P_SHARED;
2967		ki->p_swtime = l->l_swtime;
2968		ki->p_slptime = l->l_slptime;
2969		if (l->l_stat == LSONPROC) {
2970			KDASSERT(l->l_cpu != NULL);
2971			ki->p_schedflags = l->l_cpu->ci_schedstate.spc_flags;
2972		} else
2973			ki->p_schedflags = 0;
2974		ki->p_holdcnt = l->l_holdcnt;
2975		ki->p_priority = l->l_priority;
2976		ki->p_usrpri = l->l_usrpri;
2977		if (l->l_wmesg)
2978			strncpy(ki->p_wmesg, l->l_wmesg, sizeof(ki->p_wmesg));
2979		ki->p_wchan = PTRTOUINT64(l->l_wchan);
2980
2981	}
2982
2983	if (p->p_session->s_ttyvp)
2984		ki->p_eflag |= EPROC_CTTY;
2985	if (SESS_LEADER(p))
2986		ki->p_eflag |= EPROC_SLEADER;
2987
2988	/* XXX Is this double check necessary? */
2989	if (P_ZOMBIE(p)) {
2990		ki->p_uvalid = 0;
2991	} else {
2992		ki->p_uvalid = 1;
2993
2994		ki->p_ustart_sec = p->p_stats->p_start.tv_sec;
2995		ki->p_ustart_usec = p->p_stats->p_start.tv_usec;
2996
2997		calcru(p, &ut, &st, 0);
2998		ki->p_uutime_sec = ut.tv_sec;
2999		ki->p_uutime_usec = ut.tv_usec;
3000		ki->p_ustime_sec = st.tv_sec;
3001		ki->p_ustime_usec = st.tv_usec;
3002
3003		ki->p_uru_maxrss = p->p_stats->p_ru.ru_maxrss;
3004		ki->p_uru_ixrss = p->p_stats->p_ru.ru_ixrss;
3005		ki->p_uru_idrss = p->p_stats->p_ru.ru_idrss;
3006		ki->p_uru_isrss = p->p_stats->p_ru.ru_isrss;
3007		ki->p_uru_minflt = p->p_stats->p_ru.ru_minflt;
3008		ki->p_uru_majflt = p->p_stats->p_ru.ru_majflt;
3009		ki->p_uru_nswap = p->p_stats->p_ru.ru_nswap;
3010		ki->p_uru_inblock = p->p_stats->p_ru.ru_inblock;
3011		ki->p_uru_oublock = p->p_stats->p_ru.ru_oublock;
3012		ki->p_uru_msgsnd = p->p_stats->p_ru.ru_msgsnd;
3013		ki->p_uru_msgrcv = p->p_stats->p_ru.ru_msgrcv;
3014		ki->p_uru_nsignals = p->p_stats->p_ru.ru_nsignals;
3015		ki->p_uru_nvcsw = p->p_stats->p_ru.ru_nvcsw;
3016		ki->p_uru_nivcsw = p->p_stats->p_ru.ru_nivcsw;
3017
3018		timeradd(&p->p_stats->p_cru.ru_utime,
3019			 &p->p_stats->p_cru.ru_stime, &ut);
3020		ki->p_uctime_sec = ut.tv_sec;
3021		ki->p_uctime_usec = ut.tv_usec;
3022	}
3023#ifdef MULTIPROCESSOR
3024	if (l && l->l_cpu != NULL)
3025		ki->p_cpuid = l->l_cpu->ci_cpuid;
3026	else
3027#endif
3028		ki->p_cpuid = KI_NOCPU;
3029}
3030
3031/*
3032 * Fill in a kinfo_lwp structure for the specified lwp.
3033 */
3034static void
3035fill_lwp(struct lwp *l, struct kinfo_lwp *kl)
3036{
3037
3038	kl->l_forw = PTRTOUINT64(l->l_forw);
3039	kl->l_back = PTRTOUINT64(l->l_back);
3040	kl->l_laddr = PTRTOUINT64(l);
3041	kl->l_addr = PTRTOUINT64(l->l_addr);
3042	kl->l_stat = l->l_stat;
3043	kl->l_lid = l->l_lid;
3044	kl->l_flag = l->l_flag;
3045
3046	kl->l_swtime = l->l_swtime;
3047	kl->l_slptime = l->l_slptime;
3048	if (l->l_stat == LSONPROC) {
3049		KDASSERT(l->l_cpu != NULL);
3050		kl->l_schedflags = l->l_cpu->ci_schedstate.spc_flags;
3051	} else
3052		kl->l_schedflags = 0;
3053	kl->l_holdcnt = l->l_holdcnt;
3054	kl->l_priority = l->l_priority;
3055	kl->l_usrpri = l->l_usrpri;
3056	if (l->l_wmesg)
3057		strncpy(kl->l_wmesg, l->l_wmesg, sizeof(kl->l_wmesg));
3058	kl->l_wchan = PTRTOUINT64(l->l_wchan);
3059#ifdef MULTIPROCESSOR
3060	if (l->l_cpu != NULL)
3061		kl->l_cpuid = l->l_cpu->ci_cpuid;
3062	else
3063#endif
3064		kl->l_cpuid = KI_NOCPU;
3065}
3066
3067/*
3068 * Fill in an eproc structure for the specified process.
3069 */
3070void
3071fill_eproc(struct proc *p, struct eproc *ep)
3072{
3073	struct tty *tp;
3074	struct lwp *l;
3075
3076	ep->e_paddr = p;
3077	ep->e_sess = p->p_session;
3078	ep->e_pcred = *p->p_cred;
3079	ep->e_ucred = *p->p_ucred;
3080	if (p->p_stat == SIDL || P_ZOMBIE(p)) {
3081		ep->e_vm.vm_rssize = 0;
3082		ep->e_vm.vm_tsize = 0;
3083		ep->e_vm.vm_dsize = 0;
3084		ep->e_vm.vm_ssize = 0;
3085		/* ep->e_vm.vm_pmap = XXX; */
3086	} else {
3087		struct vmspace *vm = p->p_vmspace;
3088
3089		ep->e_vm.vm_rssize = vm_resident_count(vm);
3090		ep->e_vm.vm_tsize = vm->vm_tsize;
3091		ep->e_vm.vm_dsize = vm->vm_dsize;
3092		ep->e_vm.vm_ssize = vm->vm_ssize;
3093
3094		/* Pick a "representative" LWP */
3095		l = proc_representative_lwp(p);
3096
3097		if (l->l_wmesg)
3098			strncpy(ep->e_wmesg, l->l_wmesg, WMESGLEN);
3099	}
3100	if (p->p_pptr)
3101		ep->e_ppid = p->p_pptr->p_pid;
3102	else
3103		ep->e_ppid = 0;
3104	ep->e_pgid = p->p_pgrp->pg_id;
3105	ep->e_sid = ep->e_sess->s_sid;
3106	ep->e_jobc = p->p_pgrp->pg_jobc;
3107	if ((p->p_flag & P_CONTROLT) &&
3108	    (tp = ep->e_sess->s_ttyp)) {
3109		ep->e_tdev = tp->t_dev;
3110		ep->e_tpgid = tp->t_pgrp ? tp->t_pgrp->pg_id : NO_PGID;
3111		ep->e_tsess = tp->t_session;
3112	} else
3113		ep->e_tdev = NODEV;
3114
3115	ep->e_xsize = ep->e_xrssize = 0;
3116	ep->e_xccount = ep->e_xswrss = 0;
3117	ep->e_flag = ep->e_sess->s_ttyvp ? EPROC_CTTY : 0;
3118	if (SESS_LEADER(p))
3119		ep->e_flag |= EPROC_SLEADER;
3120	strncpy(ep->e_login, ep->e_sess->s_login, MAXLOGNAME);
3121}
3122