init_sysctl.c revision 1.187
1/* $NetBSD: init_sysctl.c,v 1.187 2012/02/19 21:06:49 rmind Exp $ */ 2 3/*- 4 * Copyright (c) 2003, 2007, 2008, 2009 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, and by Andrew Doran. 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 * 19 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 20 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 21 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 22 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 23 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 26 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 27 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 28 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 29 * POSSIBILITY OF SUCH DAMAGE. 30 */ 31 32#include <sys/cdefs.h> 33__KERNEL_RCSID(0, "$NetBSD: init_sysctl.c,v 1.187 2012/02/19 21:06:49 rmind Exp $"); 34 35#include "opt_sysv.h" 36#include "opt_compat_netbsd.h" 37#include "opt_modular.h" 38#include "opt_posix.h" 39#include "pty.h" 40 41#include <sys/types.h> 42#include <sys/param.h> 43#include <sys/sysctl.h> 44#include <sys/cpu.h> 45#include <sys/errno.h> 46#include <sys/systm.h> 47#include <sys/kernel.h> 48#include <sys/unistd.h> 49#include <sys/disklabel.h> 50#include <sys/cprng.h> 51#include <sys/vnode.h> 52#include <sys/mount.h> 53#include <sys/namei.h> 54#include <sys/msgbuf.h> 55#include <dev/cons.h> 56#include <sys/socketvar.h> 57#include <sys/file.h> 58#include <sys/filedesc.h> 59#include <sys/tty.h> 60#include <sys/kmem.h> 61#include <sys/resource.h> 62#include <sys/resourcevar.h> 63#include <sys/exec.h> 64#include <sys/conf.h> 65#include <sys/device.h> 66#include <sys/stat.h> 67#include <sys/kauth.h> 68#include <sys/ktrace.h> 69#include <sys/ksem.h> 70 71#ifdef COMPAT_50 72#include <compat/sys/time.h> 73#endif 74 75#include <sys/cpu.h> 76 77#if defined(MODULAR) || defined(P1003_1B_SEMAPHORE) 78int posix_semaphores = 200112; 79#else 80int posix_semaphores; 81#endif 82 83int security_setidcore_dump; 84char security_setidcore_path[MAXPATHLEN] = "/var/crash/%n.core"; 85uid_t security_setidcore_owner = 0; 86gid_t security_setidcore_group = 0; 87mode_t security_setidcore_mode = (S_IRUSR|S_IWUSR); 88 89static const u_int sysctl_flagmap[] = { 90 PK_ADVLOCK, P_ADVLOCK, 91 PK_EXEC, P_EXEC, 92 PK_NOCLDWAIT, P_NOCLDWAIT, 93 PK_32, P_32, 94 PK_CLDSIGIGN, P_CLDSIGIGN, 95 PK_SUGID, P_SUGID, 96 0 97}; 98 99static const u_int sysctl_sflagmap[] = { 100 PS_NOCLDSTOP, P_NOCLDSTOP, 101 PS_WEXIT, P_WEXIT, 102 PS_STOPFORK, P_STOPFORK, 103 PS_STOPEXEC, P_STOPEXEC, 104 PS_STOPEXIT, P_STOPEXIT, 105 0 106}; 107 108static const u_int sysctl_slflagmap[] = { 109 PSL_TRACED, P_TRACED, 110 PSL_FSTRACE, P_FSTRACE, 111 PSL_CHTRACED, P_CHTRACED, 112 PSL_SYSCALL, P_SYSCALL, 113 0 114}; 115 116static const u_int sysctl_lflagmap[] = { 117 PL_CONTROLT, P_CONTROLT, 118 PL_PPWAIT, P_PPWAIT, 119 0 120}; 121 122static const u_int sysctl_stflagmap[] = { 123 PST_PROFIL, P_PROFIL, 124 0 125 126}; 127 128static const u_int sysctl_lwpprflagmap[] = { 129 LPR_DETACHED, L_DETACHED, 130 0 131}; 132 133/* 134 * try over estimating by 5 procs/lwps 135 */ 136#define KERN_LWPSLOP (5 * sizeof(struct kinfo_lwp)) 137 138static int dcopyout(struct lwp *, const void *, void *, size_t); 139 140static int 141dcopyout(struct lwp *l, const void *kaddr, void *uaddr, size_t len) 142{ 143 int error; 144 145 error = copyout(kaddr, uaddr, len); 146 ktrmibio(-1, UIO_READ, uaddr, len, error); 147 148 return error; 149} 150 151#ifdef DIAGNOSTIC 152static int sysctl_kern_trigger_panic(SYSCTLFN_PROTO); 153#endif 154static int sysctl_kern_maxvnodes(SYSCTLFN_PROTO); 155static int sysctl_kern_rtc_offset(SYSCTLFN_PROTO); 156static int sysctl_kern_maxproc(SYSCTLFN_PROTO); 157static int sysctl_kern_hostid(SYSCTLFN_PROTO); 158static int sysctl_setlen(SYSCTLFN_PROTO); 159static int sysctl_kern_clockrate(SYSCTLFN_PROTO); 160static int sysctl_msgbuf(SYSCTLFN_PROTO); 161static int sysctl_kern_defcorename(SYSCTLFN_PROTO); 162static int sysctl_kern_cptime(SYSCTLFN_PROTO); 163#if NPTY > 0 164static int sysctl_kern_maxptys(SYSCTLFN_PROTO); 165#endif /* NPTY > 0 */ 166static int sysctl_kern_sbmax(SYSCTLFN_PROTO); 167static int sysctl_kern_urnd(SYSCTLFN_PROTO); 168static int sysctl_kern_arnd(SYSCTLFN_PROTO); 169static int sysctl_kern_lwp(SYSCTLFN_PROTO); 170static int sysctl_kern_forkfsleep(SYSCTLFN_PROTO); 171static int sysctl_kern_root_partition(SYSCTLFN_PROTO); 172static int sysctl_kern_drivers(SYSCTLFN_PROTO); 173static int sysctl_security_setidcore(SYSCTLFN_PROTO); 174static int sysctl_security_setidcorename(SYSCTLFN_PROTO); 175static int sysctl_kern_cpid(SYSCTLFN_PROTO); 176static int sysctl_hw_usermem(SYSCTLFN_PROTO); 177static int sysctl_hw_cnmagic(SYSCTLFN_PROTO); 178 179static void fill_lwp(struct lwp *l, struct kinfo_lwp *kl); 180 181/* 182 * ******************************************************************** 183 * section 1: setup routines 184 * ******************************************************************** 185 * These functions are stuffed into a link set for sysctl setup 186 * functions. They're never called or referenced from anywhere else. 187 * ******************************************************************** 188 */ 189 190/* 191 * this setup routine is a replacement for kern_sysctl() 192 */ 193SYSCTL_SETUP(sysctl_kern_setup, "sysctl kern subtree setup") 194{ 195 extern int kern_logsigexit; /* defined in kern/kern_sig.c */ 196 extern fixpt_t ccpu; /* defined in kern/kern_synch.c */ 197 extern int dumponpanic; /* defined in kern/subr_prf.c */ 198 const struct sysctlnode *rnode; 199 200 sysctl_createv(clog, 0, NULL, NULL, 201 CTLFLAG_PERMANENT, 202 CTLTYPE_NODE, "kern", NULL, 203 NULL, 0, NULL, 0, 204 CTL_KERN, CTL_EOL); 205 206 sysctl_createv(clog, 0, NULL, NULL, 207 CTLFLAG_PERMANENT, 208 CTLTYPE_STRING, "ostype", 209 SYSCTL_DESCR("Operating system type"), 210 NULL, 0, __UNCONST(&ostype), 0, 211 CTL_KERN, KERN_OSTYPE, CTL_EOL); 212 sysctl_createv(clog, 0, NULL, NULL, 213 CTLFLAG_PERMANENT, 214 CTLTYPE_STRING, "osrelease", 215 SYSCTL_DESCR("Operating system release"), 216 NULL, 0, __UNCONST(&osrelease), 0, 217 CTL_KERN, KERN_OSRELEASE, CTL_EOL); 218 sysctl_createv(clog, 0, NULL, NULL, 219 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 220 CTLTYPE_INT, "osrevision", 221 SYSCTL_DESCR("Operating system revision"), 222 NULL, __NetBSD_Version__, NULL, 0, 223 CTL_KERN, KERN_OSREV, CTL_EOL); 224 sysctl_createv(clog, 0, NULL, NULL, 225 CTLFLAG_PERMANENT, 226 CTLTYPE_STRING, "version", 227 SYSCTL_DESCR("Kernel version"), 228 NULL, 0, __UNCONST(&version), 0, 229 CTL_KERN, KERN_VERSION, CTL_EOL); 230 sysctl_createv(clog, 0, NULL, NULL, 231 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 232 CTLTYPE_INT, "maxvnodes", 233 SYSCTL_DESCR("Maximum number of vnodes"), 234 sysctl_kern_maxvnodes, 0, NULL, 0, 235 CTL_KERN, KERN_MAXVNODES, CTL_EOL); 236 sysctl_createv(clog, 0, NULL, NULL, 237 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 238 CTLTYPE_INT, "maxproc", 239 SYSCTL_DESCR("Maximum number of simultaneous processes"), 240 sysctl_kern_maxproc, 0, NULL, 0, 241 CTL_KERN, KERN_MAXPROC, CTL_EOL); 242 sysctl_createv(clog, 0, NULL, NULL, 243 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 244 CTLTYPE_INT, "maxfiles", 245 SYSCTL_DESCR("Maximum number of open files"), 246 NULL, 0, &maxfiles, 0, 247 CTL_KERN, KERN_MAXFILES, CTL_EOL); 248 sysctl_createv(clog, 0, NULL, NULL, 249 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 250 CTLTYPE_INT, "argmax", 251 SYSCTL_DESCR("Maximum number of bytes of arguments to " 252 "execve(2)"), 253 NULL, ARG_MAX, NULL, 0, 254 CTL_KERN, KERN_ARGMAX, CTL_EOL); 255 sysctl_createv(clog, 0, NULL, NULL, 256 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 257 CTLTYPE_STRING, "hostname", 258 SYSCTL_DESCR("System hostname"), 259 sysctl_setlen, 0, &hostname, MAXHOSTNAMELEN, 260 CTL_KERN, KERN_HOSTNAME, CTL_EOL); 261 sysctl_createv(clog, 0, NULL, NULL, 262 CTLFLAG_PERMANENT|CTLFLAG_READWRITE|CTLFLAG_HEX, 263 CTLTYPE_INT, "hostid", 264 SYSCTL_DESCR("System host ID number"), 265 sysctl_kern_hostid, 0, NULL, 0, 266 CTL_KERN, KERN_HOSTID, CTL_EOL); 267 sysctl_createv(clog, 0, NULL, NULL, 268 CTLFLAG_PERMANENT, 269 CTLTYPE_STRUCT, "clockrate", 270 SYSCTL_DESCR("Kernel clock rates"), 271 sysctl_kern_clockrate, 0, NULL, 272 sizeof(struct clockinfo), 273 CTL_KERN, KERN_CLOCKRATE, CTL_EOL); 274 sysctl_createv(clog, 0, NULL, NULL, 275 CTLFLAG_PERMANENT, 276 CTLTYPE_INT, "hardclock_ticks", 277 SYSCTL_DESCR("Number of hardclock ticks"), 278 NULL, 0, &hardclock_ticks, sizeof(hardclock_ticks), 279 CTL_KERN, KERN_HARDCLOCK_TICKS, CTL_EOL); 280 sysctl_createv(clog, 0, NULL, NULL, 281 CTLFLAG_PERMANENT, 282 CTLTYPE_STRUCT, "vnode", 283 SYSCTL_DESCR("System vnode table"), 284 sysctl_kern_vnode, 0, NULL, 0, 285 CTL_KERN, KERN_VNODE, CTL_EOL); 286#ifndef GPROF 287 sysctl_createv(clog, 0, NULL, NULL, 288 CTLFLAG_PERMANENT, 289 CTLTYPE_NODE, "profiling", 290 SYSCTL_DESCR("Profiling information (not available)"), 291 sysctl_notavail, 0, NULL, 0, 292 CTL_KERN, KERN_PROF, CTL_EOL); 293#endif 294 sysctl_createv(clog, 0, NULL, NULL, 295 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 296 CTLTYPE_INT, "posix1version", 297 SYSCTL_DESCR("Version of ISO/IEC 9945 (POSIX 1003.1) " 298 "with which the operating system attempts " 299 "to comply"), 300 NULL, _POSIX_VERSION, NULL, 0, 301 CTL_KERN, KERN_POSIX1, CTL_EOL); 302 sysctl_createv(clog, 0, NULL, NULL, 303 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 304 CTLTYPE_INT, "ngroups", 305 SYSCTL_DESCR("Maximum number of supplemental groups"), 306 NULL, NGROUPS_MAX, NULL, 0, 307 CTL_KERN, KERN_NGROUPS, CTL_EOL); 308 sysctl_createv(clog, 0, NULL, NULL, 309 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 310 CTLTYPE_INT, "job_control", 311 SYSCTL_DESCR("Whether job control is available"), 312 NULL, 1, NULL, 0, 313 CTL_KERN, KERN_JOB_CONTROL, CTL_EOL); 314 sysctl_createv(clog, 0, NULL, NULL, 315 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 316 CTLTYPE_INT, "saved_ids", 317 SYSCTL_DESCR("Whether POSIX saved set-group/user ID is " 318 "available"), NULL, 319#ifdef _POSIX_SAVED_IDS 320 1, 321#else /* _POSIX_SAVED_IDS */ 322 0, 323#endif /* _POSIX_SAVED_IDS */ 324 NULL, 0, CTL_KERN, KERN_SAVED_IDS, CTL_EOL); 325 sysctl_createv(clog, 0, NULL, NULL, 326 CTLFLAG_PERMANENT|CTLFLAG_HEX, 327 CTLTYPE_INT, "boothowto", 328 SYSCTL_DESCR("Flags from boot loader"), 329 NULL, 0, &boothowto, sizeof(boothowto), 330 CTL_KERN, CTL_CREATE, CTL_EOL); 331 sysctl_createv(clog, 0, NULL, NULL, 332 CTLFLAG_PERMANENT, 333 CTLTYPE_STRUCT, "boottime", 334 SYSCTL_DESCR("System boot time"), 335 NULL, 0, &boottime, sizeof(boottime), 336 CTL_KERN, KERN_BOOTTIME, CTL_EOL); 337#ifdef COMPAT_50 338 { 339 extern struct timeval50 boottime50; 340 sysctl_createv(clog, 0, NULL, NULL, 341 CTLFLAG_PERMANENT, 342 CTLTYPE_STRUCT, "oboottime", 343 SYSCTL_DESCR("System boot time"), 344 NULL, 0, &boottime50, sizeof(boottime50), 345 CTL_KERN, KERN_OBOOTTIME, CTL_EOL); 346 } 347#endif 348 sysctl_createv(clog, 0, NULL, NULL, 349 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 350 CTLTYPE_STRING, "domainname", 351 SYSCTL_DESCR("YP domain name"), 352 sysctl_setlen, 0, &domainname, MAXHOSTNAMELEN, 353 CTL_KERN, KERN_DOMAINNAME, CTL_EOL); 354 sysctl_createv(clog, 0, NULL, NULL, 355 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 356 CTLTYPE_INT, "maxpartitions", 357 SYSCTL_DESCR("Maximum number of partitions allowed per " 358 "disk"), 359 NULL, MAXPARTITIONS, NULL, 0, 360 CTL_KERN, KERN_MAXPARTITIONS, CTL_EOL); 361 sysctl_createv(clog, 0, NULL, NULL, 362 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 363 CTLTYPE_INT, "rawpartition", 364 SYSCTL_DESCR("Raw partition of a disk"), 365 NULL, RAW_PART, NULL, 0, 366 CTL_KERN, KERN_RAWPARTITION, CTL_EOL); 367 sysctl_createv(clog, 0, NULL, NULL, 368 CTLFLAG_PERMANENT, 369 CTLTYPE_STRUCT, "timex", NULL, 370 sysctl_notavail, 0, NULL, 0, 371 CTL_KERN, KERN_TIMEX, CTL_EOL); 372 sysctl_createv(clog, 0, NULL, NULL, 373 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 374 CTLTYPE_INT, "rtc_offset", 375 SYSCTL_DESCR("Offset of real time clock from UTC in " 376 "minutes"), 377 sysctl_kern_rtc_offset, 0, &rtc_offset, 0, 378 CTL_KERN, KERN_RTC_OFFSET, CTL_EOL); 379 sysctl_createv(clog, 0, NULL, NULL, 380 CTLFLAG_PERMANENT, 381 CTLTYPE_STRING, "root_device", 382 SYSCTL_DESCR("Name of the root device"), 383 sysctl_root_device, 0, NULL, 0, 384 CTL_KERN, KERN_ROOT_DEVICE, CTL_EOL); 385 sysctl_createv(clog, 0, NULL, NULL, 386 CTLFLAG_PERMANENT, 387 CTLTYPE_INT, "msgbufsize", 388 SYSCTL_DESCR("Size of the kernel message buffer"), 389 sysctl_msgbuf, 0, NULL, 0, 390 CTL_KERN, KERN_MSGBUFSIZE, CTL_EOL); 391 sysctl_createv(clog, 0, NULL, NULL, 392 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 393 CTLTYPE_INT, "fsync", 394 SYSCTL_DESCR("Whether the POSIX 1003.1b File " 395 "Synchronization Option is available on " 396 "this system"), 397 NULL, 1, NULL, 0, 398 CTL_KERN, KERN_FSYNC, CTL_EOL); 399 sysctl_createv(clog, 0, NULL, NULL, 400 CTLFLAG_PERMANENT, 401 CTLTYPE_NODE, "ipc", 402 SYSCTL_DESCR("SysV IPC options"), 403 NULL, 0, NULL, 0, 404 CTL_KERN, KERN_SYSVIPC, CTL_EOL); 405 sysctl_createv(clog, 0, NULL, NULL, 406 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 407 CTLTYPE_INT, "sysvmsg", 408 SYSCTL_DESCR("System V style message support available"), 409 NULL, 410#ifdef SYSVMSG 411 1, 412#else /* SYSVMSG */ 413 0, 414#endif /* SYSVMSG */ 415 NULL, 0, CTL_KERN, KERN_SYSVIPC, KERN_SYSVIPC_MSG, CTL_EOL); 416 sysctl_createv(clog, 0, NULL, NULL, 417 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 418 CTLTYPE_INT, "sysvsem", 419 SYSCTL_DESCR("System V style semaphore support " 420 "available"), NULL, 421#ifdef SYSVSEM 422 1, 423#else /* SYSVSEM */ 424 0, 425#endif /* SYSVSEM */ 426 NULL, 0, CTL_KERN, KERN_SYSVIPC, KERN_SYSVIPC_SEM, CTL_EOL); 427 sysctl_createv(clog, 0, NULL, NULL, 428 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 429 CTLTYPE_INT, "sysvshm", 430 SYSCTL_DESCR("System V style shared memory support " 431 "available"), NULL, 432#ifdef SYSVSHM 433 1, 434#else /* SYSVSHM */ 435 0, 436#endif /* SYSVSHM */ 437 NULL, 0, CTL_KERN, KERN_SYSVIPC, KERN_SYSVIPC_SHM, CTL_EOL); 438 sysctl_createv(clog, 0, NULL, NULL, 439 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 440 CTLTYPE_INT, "synchronized_io", 441 SYSCTL_DESCR("Whether the POSIX 1003.1b Synchronized " 442 "I/O Option is available on this system"), 443 NULL, 1, NULL, 0, 444 CTL_KERN, KERN_SYNCHRONIZED_IO, CTL_EOL); 445 sysctl_createv(clog, 0, NULL, NULL, 446 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 447 CTLTYPE_INT, "iov_max", 448 SYSCTL_DESCR("Maximum number of iovec structures per " 449 "process"), 450 NULL, IOV_MAX, NULL, 0, 451 CTL_KERN, KERN_IOV_MAX, CTL_EOL); 452 sysctl_createv(clog, 0, NULL, NULL, 453 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 454 CTLTYPE_INT, "mapped_files", 455 SYSCTL_DESCR("Whether the POSIX 1003.1b Memory Mapped " 456 "Files Option is available on this system"), 457 NULL, 1, NULL, 0, 458 CTL_KERN, KERN_MAPPED_FILES, CTL_EOL); 459 sysctl_createv(clog, 0, NULL, NULL, 460 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 461 CTLTYPE_INT, "memlock", 462 SYSCTL_DESCR("Whether the POSIX 1003.1b Process Memory " 463 "Locking Option is available on this " 464 "system"), 465 NULL, 1, NULL, 0, 466 CTL_KERN, KERN_MEMLOCK, CTL_EOL); 467 sysctl_createv(clog, 0, NULL, NULL, 468 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 469 CTLTYPE_INT, "memlock_range", 470 SYSCTL_DESCR("Whether the POSIX 1003.1b Range Memory " 471 "Locking Option is available on this " 472 "system"), 473 NULL, 1, NULL, 0, 474 CTL_KERN, KERN_MEMLOCK_RANGE, CTL_EOL); 475 sysctl_createv(clog, 0, NULL, NULL, 476 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 477 CTLTYPE_INT, "memory_protection", 478 SYSCTL_DESCR("Whether the POSIX 1003.1b Memory " 479 "Protection Option is available on this " 480 "system"), 481 NULL, 1, NULL, 0, 482 CTL_KERN, KERN_MEMORY_PROTECTION, CTL_EOL); 483 sysctl_createv(clog, 0, NULL, NULL, 484 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 485 CTLTYPE_INT, "login_name_max", 486 SYSCTL_DESCR("Maximum login name length"), 487 NULL, LOGIN_NAME_MAX, NULL, 0, 488 CTL_KERN, KERN_LOGIN_NAME_MAX, CTL_EOL); 489 sysctl_createv(clog, 0, NULL, NULL, 490 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 491 CTLTYPE_STRING, "defcorename", 492 SYSCTL_DESCR("Default core file name"), 493 sysctl_kern_defcorename, 0, defcorename, MAXPATHLEN, 494 CTL_KERN, KERN_DEFCORENAME, CTL_EOL); 495 sysctl_createv(clog, 0, NULL, NULL, 496 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 497 CTLTYPE_INT, "logsigexit", 498 SYSCTL_DESCR("Log process exit when caused by signals"), 499 NULL, 0, &kern_logsigexit, 0, 500 CTL_KERN, KERN_LOGSIGEXIT, CTL_EOL); 501 sysctl_createv(clog, 0, NULL, NULL, 502 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 503 CTLTYPE_INT, "fscale", 504 SYSCTL_DESCR("Kernel fixed-point scale factor"), 505 NULL, FSCALE, NULL, 0, 506 CTL_KERN, KERN_FSCALE, CTL_EOL); 507 sysctl_createv(clog, 0, NULL, NULL, 508 CTLFLAG_PERMANENT, 509 CTLTYPE_INT, "ccpu", 510 SYSCTL_DESCR("Scheduler exponential decay value"), 511 NULL, 0, &ccpu, 0, 512 CTL_KERN, KERN_CCPU, CTL_EOL); 513 sysctl_createv(clog, 0, NULL, NULL, 514 CTLFLAG_PERMANENT, 515 CTLTYPE_STRUCT, "cp_time", 516 SYSCTL_DESCR("Clock ticks spent in different CPU states"), 517 sysctl_kern_cptime, 0, NULL, 0, 518 CTL_KERN, KERN_CP_TIME, CTL_EOL); 519 sysctl_createv(clog, 0, NULL, NULL, 520 CTLFLAG_PERMANENT, 521 CTLTYPE_INT, "msgbuf", 522 SYSCTL_DESCR("Kernel message buffer"), 523 sysctl_msgbuf, 0, NULL, 0, 524 CTL_KERN, KERN_MSGBUF, CTL_EOL); 525 sysctl_createv(clog, 0, NULL, NULL, 526 CTLFLAG_PERMANENT, 527 CTLTYPE_STRUCT, "consdev", 528 SYSCTL_DESCR("Console device"), 529 sysctl_consdev, 0, NULL, sizeof(dev_t), 530 CTL_KERN, KERN_CONSDEV, CTL_EOL); 531#if NPTY > 0 532 sysctl_createv(clog, 0, NULL, NULL, 533 CTLFLAG_PERMANENT, 534 CTLTYPE_INT, "maxptys", 535 SYSCTL_DESCR("Maximum number of pseudo-ttys"), 536 sysctl_kern_maxptys, 0, NULL, 0, 537 CTL_KERN, KERN_MAXPTYS, CTL_EOL); 538#endif /* NPTY > 0 */ 539 sysctl_createv(clog, 0, NULL, NULL, 540 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 541 CTLTYPE_INT, "maxphys", 542 SYSCTL_DESCR("Maximum raw I/O transfer size"), 543 NULL, MAXPHYS, NULL, 0, 544 CTL_KERN, KERN_MAXPHYS, CTL_EOL); 545 sysctl_createv(clog, 0, NULL, NULL, 546 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 547 CTLTYPE_INT, "sbmax", 548 SYSCTL_DESCR("Maximum socket buffer size"), 549 sysctl_kern_sbmax, 0, NULL, 0, 550 CTL_KERN, KERN_SBMAX, CTL_EOL); 551 sysctl_createv(clog, 0, NULL, NULL, 552 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 553 CTLTYPE_INT, "monotonic_clock", 554 SYSCTL_DESCR("Implementation version of the POSIX " 555 "1003.1b Monotonic Clock Option"), 556 /* XXX _POSIX_VERSION */ 557 NULL, _POSIX_MONOTONIC_CLOCK, NULL, 0, 558 CTL_KERN, KERN_MONOTONIC_CLOCK, CTL_EOL); 559 sysctl_createv(clog, 0, NULL, NULL, 560 CTLFLAG_PERMANENT, 561 CTLTYPE_INT, "urandom", 562 SYSCTL_DESCR("Random integer value"), 563 sysctl_kern_urnd, 0, NULL, 0, 564 CTL_KERN, KERN_URND, CTL_EOL); 565 sysctl_createv(clog, 0, NULL, NULL, 566 CTLFLAG_PERMANENT, 567 CTLTYPE_INT, "arandom", 568 SYSCTL_DESCR("n bytes of random data"), 569 sysctl_kern_arnd, 0, NULL, 0, 570 CTL_KERN, KERN_ARND, CTL_EOL); 571 sysctl_createv(clog, 0, NULL, NULL, 572 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 573 CTLTYPE_INT, "labelsector", 574 SYSCTL_DESCR("Sector number containing the disklabel"), 575 NULL, LABELSECTOR, NULL, 0, 576 CTL_KERN, KERN_LABELSECTOR, CTL_EOL); 577 sysctl_createv(clog, 0, NULL, NULL, 578 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 579 CTLTYPE_INT, "labeloffset", 580 SYSCTL_DESCR("Offset of the disklabel within the " 581 "sector"), 582 NULL, LABELOFFSET, NULL, 0, 583 CTL_KERN, KERN_LABELOFFSET, CTL_EOL); 584 sysctl_createv(clog, 0, NULL, NULL, 585 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 586 CTLTYPE_INT, "labelusesmbr", 587 SYSCTL_DESCR("disklabel is inside MBR partition"), 588 NULL, LABELUSESMBR, NULL, 0, 589 CTL_KERN, CTL_CREATE, CTL_EOL); 590 sysctl_createv(clog, 0, NULL, NULL, 591 CTLFLAG_PERMANENT, 592 CTLTYPE_NODE, "lwp", 593 SYSCTL_DESCR("System-wide LWP information"), 594 sysctl_kern_lwp, 0, NULL, 0, 595 CTL_KERN, KERN_LWP, CTL_EOL); 596 sysctl_createv(clog, 0, NULL, NULL, 597 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 598 CTLTYPE_INT, "forkfsleep", 599 SYSCTL_DESCR("Milliseconds to sleep on fork failure due " 600 "to process limits"), 601 sysctl_kern_forkfsleep, 0, NULL, 0, 602 CTL_KERN, KERN_FORKFSLEEP, CTL_EOL); 603 sysctl_createv(clog, 0, NULL, NULL, 604 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 605 CTLTYPE_INT, "posix_threads", 606 SYSCTL_DESCR("Version of IEEE Std 1003.1 and its " 607 "Threads option to which the system " 608 "attempts to conform"), 609 /* XXX _POSIX_VERSION */ 610 NULL, _POSIX_THREADS, NULL, 0, 611 CTL_KERN, KERN_POSIX_THREADS, CTL_EOL); 612 sysctl_createv(clog, 0, NULL, NULL, 613 CTLFLAG_PERMANENT, 614 CTLTYPE_INT, "posix_semaphores", 615 SYSCTL_DESCR("Version of IEEE Std 1003.1 and its " 616 "Semaphores option to which the system " 617 "attempts to conform"), NULL, 618 0, &posix_semaphores, 619 0, CTL_KERN, KERN_POSIX_SEMAPHORES, CTL_EOL); 620 sysctl_createv(clog, 0, NULL, NULL, 621 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 622 CTLTYPE_INT, "posix_barriers", 623 SYSCTL_DESCR("Version of IEEE Std 1003.1 and its " 624 "Barriers option to which the system " 625 "attempts to conform"), 626 /* XXX _POSIX_VERSION */ 627 NULL, _POSIX_BARRIERS, NULL, 0, 628 CTL_KERN, KERN_POSIX_BARRIERS, CTL_EOL); 629 sysctl_createv(clog, 0, NULL, NULL, 630 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 631 CTLTYPE_INT, "posix_timers", 632 SYSCTL_DESCR("Version of IEEE Std 1003.1 and its " 633 "Timers option to which the system " 634 "attempts to conform"), 635 /* XXX _POSIX_VERSION */ 636 NULL, _POSIX_TIMERS, NULL, 0, 637 CTL_KERN, KERN_POSIX_TIMERS, CTL_EOL); 638 sysctl_createv(clog, 0, NULL, NULL, 639 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 640 CTLTYPE_INT, "posix_spin_locks", 641 SYSCTL_DESCR("Version of IEEE Std 1003.1 and its Spin " 642 "Locks option to which the system attempts " 643 "to conform"), 644 /* XXX _POSIX_VERSION */ 645 NULL, _POSIX_SPIN_LOCKS, NULL, 0, 646 CTL_KERN, KERN_POSIX_SPIN_LOCKS, CTL_EOL); 647 sysctl_createv(clog, 0, NULL, NULL, 648 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 649 CTLTYPE_INT, "posix_reader_writer_locks", 650 SYSCTL_DESCR("Version of IEEE Std 1003.1 and its " 651 "Read-Write Locks option to which the " 652 "system attempts to conform"), 653 /* XXX _POSIX_VERSION */ 654 NULL, _POSIX_READER_WRITER_LOCKS, NULL, 0, 655 CTL_KERN, KERN_POSIX_READER_WRITER_LOCKS, CTL_EOL); 656 sysctl_createv(clog, 0, NULL, NULL, 657 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 658 CTLTYPE_INT, "dump_on_panic", 659 SYSCTL_DESCR("Perform a crash dump on system panic"), 660 NULL, 0, &dumponpanic, 0, 661 CTL_KERN, KERN_DUMP_ON_PANIC, CTL_EOL); 662#ifdef DIAGNOSTIC 663 sysctl_createv(clog, 0, NULL, NULL, 664 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 665 CTLTYPE_INT, "panic_now", 666 SYSCTL_DESCR("Trigger a panic"), 667 sysctl_kern_trigger_panic, 0, NULL, 0, 668 CTL_KERN, CTL_CREATE, CTL_EOL); 669#endif 670 sysctl_createv(clog, 0, NULL, NULL, 671 CTLFLAG_PERMANENT, 672 CTLTYPE_INT, "root_partition", 673 SYSCTL_DESCR("Root partition on the root device"), 674 sysctl_kern_root_partition, 0, NULL, 0, 675 CTL_KERN, KERN_ROOT_PARTITION, CTL_EOL); 676 sysctl_createv(clog, 0, NULL, NULL, 677 CTLFLAG_PERMANENT, 678 CTLTYPE_STRUCT, "drivers", 679 SYSCTL_DESCR("List of all drivers with block and " 680 "character device numbers"), 681 sysctl_kern_drivers, 0, NULL, 0, 682 CTL_KERN, KERN_DRIVERS, CTL_EOL); 683 sysctl_createv(clog, 0, NULL, NULL, 684 CTLFLAG_PERMANENT, 685 CTLTYPE_STRUCT, "cp_id", 686 SYSCTL_DESCR("Mapping of CPU number to CPU id"), 687 sysctl_kern_cpid, 0, NULL, 0, 688 CTL_KERN, KERN_CP_ID, CTL_EOL); 689 sysctl_createv(clog, 0, NULL, &rnode, 690 CTLFLAG_PERMANENT, 691 CTLTYPE_NODE, "coredump", 692 SYSCTL_DESCR("Coredump settings."), 693 NULL, 0, NULL, 0, 694 CTL_KERN, CTL_CREATE, CTL_EOL); 695 sysctl_createv(clog, 0, &rnode, &rnode, 696 CTLFLAG_PERMANENT, 697 CTLTYPE_NODE, "setid", 698 SYSCTL_DESCR("Set-id processes' coredump settings."), 699 NULL, 0, NULL, 0, 700 CTL_CREATE, CTL_EOL); 701 sysctl_createv(clog, 0, &rnode, NULL, 702 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 703 CTLTYPE_INT, "dump", 704 SYSCTL_DESCR("Allow set-id processes to dump core."), 705 sysctl_security_setidcore, 0, &security_setidcore_dump, 706 sizeof(security_setidcore_dump), 707 CTL_CREATE, CTL_EOL); 708 sysctl_createv(clog, 0, &rnode, NULL, 709 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 710 CTLTYPE_STRING, "path", 711 SYSCTL_DESCR("Path pattern for set-id coredumps."), 712 sysctl_security_setidcorename, 0, 713 &security_setidcore_path, 714 sizeof(security_setidcore_path), 715 CTL_CREATE, CTL_EOL); 716 sysctl_createv(clog, 0, &rnode, NULL, 717 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 718 CTLTYPE_INT, "owner", 719 SYSCTL_DESCR("Owner id for set-id processes' cores."), 720 sysctl_security_setidcore, 0, &security_setidcore_owner, 721 0, 722 CTL_CREATE, CTL_EOL); 723 sysctl_createv(clog, 0, &rnode, NULL, 724 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 725 CTLTYPE_INT, "group", 726 SYSCTL_DESCR("Group id for set-id processes' cores."), 727 sysctl_security_setidcore, 0, &security_setidcore_group, 728 0, 729 CTL_CREATE, CTL_EOL); 730 sysctl_createv(clog, 0, &rnode, NULL, 731 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 732 CTLTYPE_INT, "mode", 733 SYSCTL_DESCR("Mode for set-id processes' cores."), 734 sysctl_security_setidcore, 0, &security_setidcore_mode, 735 0, 736 CTL_CREATE, CTL_EOL); 737 sysctl_createv(clog, 0, NULL, NULL, 738 CTLFLAG_IMMEDIATE|CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 739 CTLTYPE_INT, "no_sa_support", 740 SYSCTL_DESCR("0 if the kernel supports SA, otherwise " 741 "it doesn't"), 742 NULL, 1, NULL, 0, 743 CTL_KERN, CTL_CREATE, CTL_EOL); 744 /* kern.posix. */ 745 sysctl_createv(clog, 0, NULL, &rnode, 746 CTLFLAG_PERMANENT, 747 CTLTYPE_NODE, "posix", 748 SYSCTL_DESCR("POSIX options"), 749 NULL, 0, NULL, 0, 750 CTL_KERN, CTL_CREATE, CTL_EOL); 751 sysctl_createv(clog, 0, &rnode, NULL, 752 CTLFLAG_PERMANENT | CTLFLAG_READWRITE, 753 CTLTYPE_INT, "semmax", 754 SYSCTL_DESCR("Maximal number of semaphores"), 755 NULL, 0, &ksem_max, 0, 756 CTL_CREATE, CTL_EOL); 757} 758 759SYSCTL_SETUP(sysctl_hw_setup, "sysctl hw subtree setup") 760{ 761 u_int u; 762 u_quad_t q; 763 764 sysctl_createv(clog, 0, NULL, NULL, 765 CTLFLAG_PERMANENT, 766 CTLTYPE_NODE, "hw", NULL, 767 NULL, 0, NULL, 0, 768 CTL_HW, CTL_EOL); 769 770 sysctl_createv(clog, 0, NULL, NULL, 771 CTLFLAG_PERMANENT, 772 CTLTYPE_STRING, "machine", 773 SYSCTL_DESCR("Machine class"), 774 NULL, 0, machine, 0, 775 CTL_HW, HW_MACHINE, CTL_EOL); 776 sysctl_createv(clog, 0, NULL, NULL, 777 CTLFLAG_PERMANENT, 778 CTLTYPE_STRING, "model", 779 SYSCTL_DESCR("Machine model"), 780 NULL, 0, cpu_model, 0, 781 CTL_HW, HW_MODEL, CTL_EOL); 782 sysctl_createv(clog, 0, NULL, NULL, 783 CTLFLAG_PERMANENT, 784 CTLTYPE_INT, "ncpu", 785 SYSCTL_DESCR("Number of CPUs configured"), 786 NULL, 0, &ncpu, 0, 787 CTL_HW, HW_NCPU, CTL_EOL); 788 sysctl_createv(clog, 0, NULL, NULL, 789 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 790 CTLTYPE_INT, "byteorder", 791 SYSCTL_DESCR("System byte order"), 792 NULL, BYTE_ORDER, NULL, 0, 793 CTL_HW, HW_BYTEORDER, CTL_EOL); 794 u = ((u_int)physmem > (UINT_MAX / PAGE_SIZE)) ? 795 UINT_MAX : physmem * PAGE_SIZE; 796 sysctl_createv(clog, 0, NULL, NULL, 797 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 798 CTLTYPE_INT, "physmem", 799 SYSCTL_DESCR("Bytes of physical memory"), 800 NULL, u, NULL, 0, 801 CTL_HW, HW_PHYSMEM, CTL_EOL); 802 sysctl_createv(clog, 0, NULL, NULL, 803 CTLFLAG_PERMANENT, 804 CTLTYPE_INT, "usermem", 805 SYSCTL_DESCR("Bytes of non-kernel memory"), 806 sysctl_hw_usermem, 0, NULL, 0, 807 CTL_HW, HW_USERMEM, CTL_EOL); 808 sysctl_createv(clog, 0, NULL, NULL, 809 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 810 CTLTYPE_INT, "pagesize", 811 SYSCTL_DESCR("Software page size"), 812 NULL, PAGE_SIZE, NULL, 0, 813 CTL_HW, HW_PAGESIZE, CTL_EOL); 814 sysctl_createv(clog, 0, NULL, NULL, 815 CTLFLAG_PERMANENT, 816 CTLTYPE_STRING, "machine_arch", 817 SYSCTL_DESCR("Machine CPU class"), 818 NULL, 0, machine_arch, 0, 819 CTL_HW, HW_MACHINE_ARCH, CTL_EOL); 820 sysctl_createv(clog, 0, NULL, NULL, 821 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 822 CTLTYPE_INT, "alignbytes", 823 SYSCTL_DESCR("Alignment constraint for all possible " 824 "data types"), 825 NULL, ALIGNBYTES, NULL, 0, 826 CTL_HW, HW_ALIGNBYTES, CTL_EOL); 827 sysctl_createv(clog, 0, NULL, NULL, 828 CTLFLAG_PERMANENT|CTLFLAG_READWRITE|CTLFLAG_HEX, 829 CTLTYPE_STRING, "cnmagic", 830 SYSCTL_DESCR("Console magic key sequence"), 831 sysctl_hw_cnmagic, 0, NULL, CNS_LEN, 832 CTL_HW, HW_CNMAGIC, CTL_EOL); 833 q = (u_quad_t)physmem * PAGE_SIZE; 834 sysctl_createv(clog, 0, NULL, NULL, 835 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 836 CTLTYPE_QUAD, "physmem64", 837 SYSCTL_DESCR("Bytes of physical memory"), 838 NULL, q, NULL, 0, 839 CTL_HW, HW_PHYSMEM64, CTL_EOL); 840 sysctl_createv(clog, 0, NULL, NULL, 841 CTLFLAG_PERMANENT, 842 CTLTYPE_QUAD, "usermem64", 843 SYSCTL_DESCR("Bytes of non-kernel memory"), 844 sysctl_hw_usermem, 0, NULL, 0, 845 CTL_HW, HW_USERMEM64, CTL_EOL); 846 sysctl_createv(clog, 0, NULL, NULL, 847 CTLFLAG_PERMANENT, 848 CTLTYPE_INT, "ncpuonline", 849 SYSCTL_DESCR("Number of CPUs online"), 850 NULL, 0, &ncpuonline, 0, 851 CTL_HW, HW_NCPUONLINE, CTL_EOL); 852} 853 854#ifdef DEBUG 855/* 856 * Debugging related system variables. 857 */ 858struct ctldebug /* debug0, */ /* debug1, */ debug2, debug3, debug4; 859struct ctldebug debug5, debug6, debug7, debug8, debug9; 860struct ctldebug debug10, debug11, debug12, debug13, debug14; 861struct ctldebug debug15, debug16, debug17, debug18, debug19; 862static struct ctldebug *debugvars[CTL_DEBUG_MAXID] = { 863 &debug0, &debug1, &debug2, &debug3, &debug4, 864 &debug5, &debug6, &debug7, &debug8, &debug9, 865 &debug10, &debug11, &debug12, &debug13, &debug14, 866 &debug15, &debug16, &debug17, &debug18, &debug19, 867}; 868 869/* 870 * this setup routine is a replacement for debug_sysctl() 871 * 872 * note that it creates several nodes per defined debug variable 873 */ 874SYSCTL_SETUP(sysctl_debug_setup, "sysctl debug subtree setup") 875{ 876 struct ctldebug *cdp; 877 char nodename[20]; 878 int i; 879 880 /* 881 * two ways here: 882 * 883 * the "old" way (debug.name -> value) which was emulated by 884 * the sysctl(8) binary 885 * 886 * the new way, which the sysctl(8) binary was actually using 887 888 node debug 889 node debug.0 890 string debug.0.name 891 int debug.0.value 892 int debug.name 893 894 */ 895 896 sysctl_createv(clog, 0, NULL, NULL, 897 CTLFLAG_PERMANENT, 898 CTLTYPE_NODE, "debug", NULL, 899 NULL, 0, NULL, 0, 900 CTL_DEBUG, CTL_EOL); 901 902 for (i = 0; i < CTL_DEBUG_MAXID; i++) { 903 cdp = debugvars[i]; 904 if (cdp->debugname == NULL || cdp->debugvar == NULL) 905 continue; 906 907 snprintf(nodename, sizeof(nodename), "debug%d", i); 908 sysctl_createv(clog, 0, NULL, NULL, 909 CTLFLAG_PERMANENT|CTLFLAG_HIDDEN, 910 CTLTYPE_NODE, nodename, NULL, 911 NULL, 0, NULL, 0, 912 CTL_DEBUG, i, CTL_EOL); 913 sysctl_createv(clog, 0, NULL, NULL, 914 CTLFLAG_PERMANENT|CTLFLAG_HIDDEN, 915 CTLTYPE_STRING, "name", NULL, 916 /*XXXUNCONST*/ 917 NULL, 0, __UNCONST(cdp->debugname), 0, 918 CTL_DEBUG, i, CTL_DEBUG_NAME, CTL_EOL); 919 sysctl_createv(clog, 0, NULL, NULL, 920 CTLFLAG_PERMANENT|CTLFLAG_HIDDEN, 921 CTLTYPE_INT, "value", NULL, 922 NULL, 0, cdp->debugvar, 0, 923 CTL_DEBUG, i, CTL_DEBUG_VALUE, CTL_EOL); 924 sysctl_createv(clog, 0, NULL, NULL, 925 CTLFLAG_PERMANENT, 926 CTLTYPE_INT, cdp->debugname, NULL, 927 NULL, 0, cdp->debugvar, 0, 928 CTL_DEBUG, CTL_CREATE, CTL_EOL); 929 } 930} 931#endif /* DEBUG */ 932 933/* 934 * ******************************************************************** 935 * section 2: private node-specific helper routines. 936 * ******************************************************************** 937 */ 938 939#ifdef DIAGNOSTIC 940static int 941sysctl_kern_trigger_panic(SYSCTLFN_ARGS) 942{ 943 int newtrig, error; 944 struct sysctlnode node; 945 946 newtrig = 0; 947 node = *rnode; 948 node.sysctl_data = &newtrig; 949 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 950 if (error || newp == NULL) 951 return (error); 952 953 if (newtrig != 0) 954 panic("Panic triggered"); 955 956 return (error); 957} 958#endif 959 960/* 961 * sysctl helper routine for kern.maxvnodes. Drain vnodes if 962 * new value is lower than desiredvnodes and then calls reinit 963 * routines that needs to adjust to the new value. 964 */ 965static int 966sysctl_kern_maxvnodes(SYSCTLFN_ARGS) 967{ 968 int error, new_vnodes, old_vnodes, new_max; 969 struct sysctlnode node; 970 971 new_vnodes = desiredvnodes; 972 node = *rnode; 973 node.sysctl_data = &new_vnodes; 974 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 975 if (error || newp == NULL) 976 return (error); 977 978 /* Limits: 75% of KVA and physical memory. */ 979 new_max = calc_cache_size(kernel_map, 75, 75) / VNODE_COST; 980 if (new_vnodes > new_max) 981 new_vnodes = new_max; 982 983 old_vnodes = desiredvnodes; 984 desiredvnodes = new_vnodes; 985 if (new_vnodes < old_vnodes) { 986 error = vfs_drainvnodes(new_vnodes); 987 if (error) { 988 desiredvnodes = old_vnodes; 989 return (error); 990 } 991 } 992 vfs_reinit(); 993 nchreinit(); 994 995 return (0); 996} 997 998/* 999 * sysctl helper routine for rtc_offset - set time after changes 1000 */ 1001static int 1002sysctl_kern_rtc_offset(SYSCTLFN_ARGS) 1003{ 1004 struct timespec ts, delta; 1005 int error, new_rtc_offset; 1006 struct sysctlnode node; 1007 1008 new_rtc_offset = rtc_offset; 1009 node = *rnode; 1010 node.sysctl_data = &new_rtc_offset; 1011 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 1012 if (error || newp == NULL) 1013 return (error); 1014 1015 if (kauth_authorize_system(l->l_cred, KAUTH_SYSTEM_TIME, 1016 KAUTH_REQ_SYSTEM_TIME_RTCOFFSET, 1017 KAUTH_ARG(new_rtc_offset), NULL, NULL)) 1018 return (EPERM); 1019 if (rtc_offset == new_rtc_offset) 1020 return (0); 1021 1022 /* if we change the offset, adjust the time */ 1023 nanotime(&ts); 1024 delta.tv_sec = 60 * (new_rtc_offset - rtc_offset); 1025 delta.tv_nsec = 0; 1026 timespecadd(&ts, &delta, &ts); 1027 rtc_offset = new_rtc_offset; 1028 return (settime(l->l_proc, &ts)); 1029} 1030 1031/* 1032 * sysctl helper routine for kern.maxproc. Ensures that the new 1033 * values are not too low or too high. 1034 */ 1035static int 1036sysctl_kern_maxproc(SYSCTLFN_ARGS) 1037{ 1038 int error, nmaxproc; 1039 struct sysctlnode node; 1040 1041 nmaxproc = maxproc; 1042 node = *rnode; 1043 node.sysctl_data = &nmaxproc; 1044 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 1045 if (error || newp == NULL) 1046 return (error); 1047 1048 if (nmaxproc < 0 || nmaxproc >= PID_MAX) 1049 return (EINVAL); 1050#ifdef __HAVE_CPU_MAXPROC 1051 if (nmaxproc > cpu_maxproc()) 1052 return (EINVAL); 1053#endif 1054 maxproc = nmaxproc; 1055 1056 return (0); 1057} 1058 1059/* 1060 * sysctl helper function for kern.hostid. The hostid is a long, but 1061 * we export it as an int, so we need to give it a little help. 1062 */ 1063static int 1064sysctl_kern_hostid(SYSCTLFN_ARGS) 1065{ 1066 int error, inthostid; 1067 struct sysctlnode node; 1068 1069 inthostid = hostid; /* XXX assumes sizeof int <= sizeof long */ 1070 node = *rnode; 1071 node.sysctl_data = &inthostid; 1072 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 1073 if (error || newp == NULL) 1074 return (error); 1075 1076 hostid = (unsigned)inthostid; 1077 1078 return (0); 1079} 1080 1081/* 1082 * sysctl helper function for kern.hostname and kern.domainnname. 1083 * resets the relevant recorded length when the underlying name is 1084 * changed. 1085 */ 1086static int 1087sysctl_setlen(SYSCTLFN_ARGS) 1088{ 1089 int error; 1090 1091 error = sysctl_lookup(SYSCTLFN_CALL(rnode)); 1092 if (error || newp == NULL) 1093 return (error); 1094 1095 switch (rnode->sysctl_num) { 1096 case KERN_HOSTNAME: 1097 hostnamelen = strlen((const char*)rnode->sysctl_data); 1098 break; 1099 case KERN_DOMAINNAME: 1100 domainnamelen = strlen((const char*)rnode->sysctl_data); 1101 break; 1102 } 1103 1104 return (0); 1105} 1106 1107/* 1108 * sysctl helper routine for kern.clockrate. Assembles a struct on 1109 * the fly to be returned to the caller. 1110 */ 1111static int 1112sysctl_kern_clockrate(SYSCTLFN_ARGS) 1113{ 1114 struct clockinfo clkinfo; 1115 struct sysctlnode node; 1116 1117 clkinfo.tick = tick; 1118 clkinfo.tickadj = tickadj; 1119 clkinfo.hz = hz; 1120 clkinfo.profhz = profhz; 1121 clkinfo.stathz = stathz ? stathz : hz; 1122 1123 node = *rnode; 1124 node.sysctl_data = &clkinfo; 1125 return (sysctl_lookup(SYSCTLFN_CALL(&node))); 1126} 1127 1128/* 1129 * sysctl helper routine for kern.msgbufsize and kern.msgbuf. For the 1130 * former it merely checks the message buffer is set up. For the latter, 1131 * it also copies out the data if necessary. 1132 */ 1133static int 1134sysctl_msgbuf(SYSCTLFN_ARGS) 1135{ 1136 char *where = oldp; 1137 size_t len, maxlen; 1138 long beg, end; 1139 extern kmutex_t log_lock; 1140 int error; 1141 1142 if (!msgbufenabled || msgbufp->msg_magic != MSG_MAGIC) { 1143 msgbufenabled = 0; 1144 return (ENXIO); 1145 } 1146 1147 switch (rnode->sysctl_num) { 1148 case KERN_MSGBUFSIZE: { 1149 struct sysctlnode node = *rnode; 1150 int msg_bufs = (int)msgbufp->msg_bufs; 1151 node.sysctl_data = &msg_bufs; 1152 return (sysctl_lookup(SYSCTLFN_CALL(&node))); 1153 } 1154 case KERN_MSGBUF: 1155 break; 1156 default: 1157 return (EOPNOTSUPP); 1158 } 1159 1160 if (newp != NULL) 1161 return (EPERM); 1162 1163 if (oldp == NULL) { 1164 /* always return full buffer size */ 1165 *oldlenp = msgbufp->msg_bufs; 1166 return (0); 1167 } 1168 1169 sysctl_unlock(); 1170 1171 /* 1172 * First, copy from the write pointer to the end of 1173 * message buffer. 1174 */ 1175 error = 0; 1176 mutex_spin_enter(&log_lock); 1177 maxlen = MIN(msgbufp->msg_bufs, *oldlenp); 1178 beg = msgbufp->msg_bufx; 1179 end = msgbufp->msg_bufs; 1180 mutex_spin_exit(&log_lock); 1181 1182 while (maxlen > 0) { 1183 len = MIN(end - beg, maxlen); 1184 if (len == 0) 1185 break; 1186 /* XXX unlocked, but hardly matters. */ 1187 error = dcopyout(l, &msgbufp->msg_bufc[beg], where, len); 1188 if (error) 1189 break; 1190 where += len; 1191 maxlen -= len; 1192 1193 /* 1194 * ... then, copy from the beginning of message buffer to 1195 * the write pointer. 1196 */ 1197 beg = 0; 1198 end = msgbufp->msg_bufx; 1199 } 1200 1201 sysctl_relock(); 1202 return (error); 1203} 1204 1205/* 1206 * sysctl helper routine for kern.defcorename. In the case of a new 1207 * string being assigned, check that it's not a zero-length string. 1208 * (XXX the check in -current doesn't work, but do we really care?) 1209 */ 1210static int 1211sysctl_kern_defcorename(SYSCTLFN_ARGS) 1212{ 1213 int error; 1214 char *newcorename; 1215 struct sysctlnode node; 1216 1217 newcorename = PNBUF_GET(); 1218 node = *rnode; 1219 node.sysctl_data = &newcorename[0]; 1220 memcpy(node.sysctl_data, rnode->sysctl_data, MAXPATHLEN); 1221 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 1222 if (error || newp == NULL) { 1223 goto done; 1224 } 1225 1226 /* 1227 * when sysctl_lookup() deals with a string, it's guaranteed 1228 * to come back nul terminated. So there. :) 1229 */ 1230 if (strlen(newcorename) == 0) { 1231 error = EINVAL; 1232 } else { 1233 memcpy(rnode->sysctl_data, node.sysctl_data, MAXPATHLEN); 1234 error = 0; 1235 } 1236done: 1237 PNBUF_PUT(newcorename); 1238 return error; 1239} 1240 1241/* 1242 * sysctl helper routine for kern.cp_time node. Adds up cpu time 1243 * across all cpus. 1244 */ 1245static int 1246sysctl_kern_cptime(SYSCTLFN_ARGS) 1247{ 1248 struct sysctlnode node = *rnode; 1249 uint64_t *cp_time = NULL; 1250 int error, n = ncpu, i; 1251 struct cpu_info *ci; 1252 CPU_INFO_ITERATOR cii; 1253 1254 /* 1255 * if you specifically pass a buffer that is the size of the 1256 * sum, or if you are probing for the size, you get the "sum" 1257 * of cp_time (and the size thereof) across all processors. 1258 * 1259 * alternately, you can pass an additional mib number and get 1260 * cp_time for that particular processor. 1261 */ 1262 switch (namelen) { 1263 case 0: 1264 if (*oldlenp == sizeof(uint64_t) * CPUSTATES || oldp == NULL) { 1265 node.sysctl_size = sizeof(uint64_t) * CPUSTATES; 1266 n = -1; /* SUM */ 1267 } 1268 else { 1269 node.sysctl_size = n * sizeof(uint64_t) * CPUSTATES; 1270 n = -2; /* ALL */ 1271 } 1272 break; 1273 case 1: 1274 if (name[0] < 0 || name[0] >= n) 1275 return (ENOENT); /* ENOSUCHPROCESSOR */ 1276 node.sysctl_size = sizeof(uint64_t) * CPUSTATES; 1277 n = name[0]; 1278 /* 1279 * adjust these so that sysctl_lookup() will be happy 1280 */ 1281 name++; 1282 namelen--; 1283 break; 1284 default: 1285 return (EINVAL); 1286 } 1287 1288 cp_time = kmem_alloc(node.sysctl_size, KM_SLEEP); 1289 if (cp_time == NULL) 1290 return (ENOMEM); 1291 node.sysctl_data = cp_time; 1292 memset(cp_time, 0, node.sysctl_size); 1293 1294 for (CPU_INFO_FOREACH(cii, ci)) { 1295 if (n <= 0) { 1296 for (i = 0; i < CPUSTATES; i++) { 1297 cp_time[i] += ci->ci_schedstate.spc_cp_time[i]; 1298 } 1299 } 1300 /* 1301 * if a specific processor was requested and we just 1302 * did it, we're done here 1303 */ 1304 if (n == 0) 1305 break; 1306 /* 1307 * if doing "all", skip to next cp_time set for next processor 1308 */ 1309 if (n == -2) 1310 cp_time += CPUSTATES; 1311 /* 1312 * if we're doing a specific processor, we're one 1313 * processor closer 1314 */ 1315 if (n > 0) 1316 n--; 1317 } 1318 1319 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 1320 kmem_free(node.sysctl_data, node.sysctl_size); 1321 return (error); 1322} 1323 1324#if NPTY > 0 1325/* 1326 * sysctl helper routine for kern.maxptys. Ensures that any new value 1327 * is acceptable to the pty subsystem. 1328 */ 1329static int 1330sysctl_kern_maxptys(SYSCTLFN_ARGS) 1331{ 1332 int pty_maxptys(int, int); /* defined in kern/tty_pty.c */ 1333 int error, xmax; 1334 struct sysctlnode node; 1335 1336 /* get current value of maxptys */ 1337 xmax = pty_maxptys(0, 0); 1338 1339 node = *rnode; 1340 node.sysctl_data = &xmax; 1341 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 1342 if (error || newp == NULL) 1343 return (error); 1344 1345 if (xmax != pty_maxptys(xmax, 1)) 1346 return (EINVAL); 1347 1348 return (0); 1349} 1350#endif /* NPTY > 0 */ 1351 1352/* 1353 * sysctl helper routine for kern.sbmax. Basically just ensures that 1354 * any new value is not too small. 1355 */ 1356static int 1357sysctl_kern_sbmax(SYSCTLFN_ARGS) 1358{ 1359 int error, new_sbmax; 1360 struct sysctlnode node; 1361 1362 new_sbmax = sb_max; 1363 node = *rnode; 1364 node.sysctl_data = &new_sbmax; 1365 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 1366 if (error || newp == NULL) 1367 return (error); 1368 1369 KERNEL_LOCK(1, NULL); 1370 error = sb_max_set(new_sbmax); 1371 KERNEL_UNLOCK_ONE(NULL); 1372 1373 return (error); 1374} 1375 1376/* 1377 * sysctl helper routine for kern.urandom node. Picks a random number 1378 * for you. 1379 */ 1380static int 1381sysctl_kern_urnd(SYSCTLFN_ARGS) 1382{ 1383 int v, rv; 1384 1385 rv = cprng_strong(sysctl_prng, &v, sizeof(v), 0); 1386 if (rv == sizeof(v)) { 1387 struct sysctlnode node = *rnode; 1388 node.sysctl_data = &v; 1389 return (sysctl_lookup(SYSCTLFN_CALL(&node))); 1390 } 1391 else 1392 return (EIO); /*XXX*/ 1393} 1394 1395/* 1396 * sysctl helper routine for kern.arandom node. Picks a random number 1397 * for you. 1398 */ 1399static int 1400sysctl_kern_arnd(SYSCTLFN_ARGS) 1401{ 1402 int error; 1403 void *v; 1404 struct sysctlnode node = *rnode; 1405 1406 if (*oldlenp == 0) 1407 return 0; 1408 /* 1409 * This code used to allow sucking 8192 bytes at a time out 1410 * of the kernel arc4random generator. Evidently there is some 1411 * very old OpenBSD application code that may try to do this. 1412 * 1413 * Note that this node is documented as type "INT" -- 4 or 8 1414 * bytes, not 8192. 1415 * 1416 * We continue to support this abuse of the "len" pointer here 1417 * but only 256 bytes at a time, as, anecdotally, the actual 1418 * application use here was to generate RC4 keys in userspace. 1419 * 1420 * Support for such large requests will probably be removed 1421 * entirely in the future. 1422 */ 1423 if (*oldlenp > 256) 1424 return E2BIG; 1425 1426 v = kmem_alloc(*oldlenp, KM_SLEEP); 1427 cprng_fast(v, *oldlenp); 1428 node.sysctl_data = v; 1429 node.sysctl_size = *oldlenp; 1430 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 1431 kmem_free(v, *oldlenp); 1432 return error; 1433} 1434/* 1435 * sysctl helper routine to do kern.lwp.* work. 1436 */ 1437static int 1438sysctl_kern_lwp(SYSCTLFN_ARGS) 1439{ 1440 struct kinfo_lwp klwp; 1441 struct proc *p; 1442 struct lwp *l2, *l3; 1443 char *where, *dp; 1444 int pid, elem_size, elem_count; 1445 int buflen, needed, error; 1446 bool gotit; 1447 1448 if (namelen == 1 && name[0] == CTL_QUERY) 1449 return (sysctl_query(SYSCTLFN_CALL(rnode))); 1450 1451 dp = where = oldp; 1452 buflen = where != NULL ? *oldlenp : 0; 1453 error = needed = 0; 1454 1455 if (newp != NULL || namelen != 3) 1456 return (EINVAL); 1457 pid = name[0]; 1458 elem_size = name[1]; 1459 elem_count = name[2]; 1460 1461 sysctl_unlock(); 1462 if (pid == -1) { 1463 mutex_enter(proc_lock); 1464 PROCLIST_FOREACH(p, &allproc) { 1465 /* Grab a hold on the process. */ 1466 if (!rw_tryenter(&p->p_reflock, RW_READER)) { 1467 continue; 1468 } 1469 mutex_exit(proc_lock); 1470 1471 mutex_enter(p->p_lock); 1472 LIST_FOREACH(l2, &p->p_lwps, l_sibling) { 1473 if (buflen >= elem_size && elem_count > 0) { 1474 lwp_lock(l2); 1475 fill_lwp(l2, &klwp); 1476 lwp_unlock(l2); 1477 mutex_exit(p->p_lock); 1478 1479 /* 1480 * Copy out elem_size, but not 1481 * larger than the size of a 1482 * struct kinfo_proc2. 1483 */ 1484 error = dcopyout(l, &klwp, dp, 1485 min(sizeof(klwp), elem_size)); 1486 if (error) { 1487 rw_exit(&p->p_reflock); 1488 goto cleanup; 1489 } 1490 mutex_enter(p->p_lock); 1491 LIST_FOREACH(l3, &p->p_lwps, 1492 l_sibling) { 1493 if (l2 == l3) 1494 break; 1495 } 1496 if (l3 == NULL) { 1497 mutex_exit(p->p_lock); 1498 rw_exit(&p->p_reflock); 1499 error = EAGAIN; 1500 goto cleanup; 1501 } 1502 dp += elem_size; 1503 buflen -= elem_size; 1504 elem_count--; 1505 } 1506 needed += elem_size; 1507 } 1508 mutex_exit(p->p_lock); 1509 1510 /* Drop reference to process. */ 1511 mutex_enter(proc_lock); 1512 rw_exit(&p->p_reflock); 1513 } 1514 mutex_exit(proc_lock); 1515 } else { 1516 mutex_enter(proc_lock); 1517 p = proc_find(pid); 1518 if (p == NULL) { 1519 error = ESRCH; 1520 mutex_exit(proc_lock); 1521 goto cleanup; 1522 } 1523 /* Grab a hold on the process. */ 1524 gotit = rw_tryenter(&p->p_reflock, RW_READER); 1525 mutex_exit(proc_lock); 1526 if (!gotit) { 1527 error = ESRCH; 1528 goto cleanup; 1529 } 1530 1531 mutex_enter(p->p_lock); 1532 LIST_FOREACH(l2, &p->p_lwps, l_sibling) { 1533 if (buflen >= elem_size && elem_count > 0) { 1534 lwp_lock(l2); 1535 fill_lwp(l2, &klwp); 1536 lwp_unlock(l2); 1537 mutex_exit(p->p_lock); 1538 /* 1539 * Copy out elem_size, but not larger than 1540 * the size of a struct kinfo_proc2. 1541 */ 1542 error = dcopyout(l, &klwp, dp, 1543 min(sizeof(klwp), elem_size)); 1544 if (error) { 1545 rw_exit(&p->p_reflock); 1546 goto cleanup; 1547 } 1548 mutex_enter(p->p_lock); 1549 LIST_FOREACH(l3, &p->p_lwps, l_sibling) { 1550 if (l2 == l3) 1551 break; 1552 } 1553 if (l3 == NULL) { 1554 mutex_exit(p->p_lock); 1555 rw_exit(&p->p_reflock); 1556 error = EAGAIN; 1557 goto cleanup; 1558 } 1559 dp += elem_size; 1560 buflen -= elem_size; 1561 elem_count--; 1562 } 1563 needed += elem_size; 1564 } 1565 mutex_exit(p->p_lock); 1566 1567 /* Drop reference to process. */ 1568 rw_exit(&p->p_reflock); 1569 } 1570 1571 if (where != NULL) { 1572 *oldlenp = dp - where; 1573 if (needed > *oldlenp) { 1574 sysctl_relock(); 1575 return (ENOMEM); 1576 } 1577 } else { 1578 needed += KERN_LWPSLOP; 1579 *oldlenp = needed; 1580 } 1581 error = 0; 1582 cleanup: 1583 sysctl_relock(); 1584 return (error); 1585} 1586 1587/* 1588 * sysctl helper routine for kern.forkfsleep node. Ensures that the 1589 * given value is not too large or two small, and is at least one 1590 * timer tick if not zero. 1591 */ 1592static int 1593sysctl_kern_forkfsleep(SYSCTLFN_ARGS) 1594{ 1595 /* userland sees value in ms, internally is in ticks */ 1596 extern int forkfsleep; /* defined in kern/kern_fork.c */ 1597 int error, timo, lsleep; 1598 struct sysctlnode node; 1599 1600 lsleep = forkfsleep * 1000 / hz; 1601 node = *rnode; 1602 node.sysctl_data = &lsleep; 1603 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 1604 if (error || newp == NULL) 1605 return (error); 1606 1607 /* refuse negative values, and overly 'long time' */ 1608 if (lsleep < 0 || lsleep > MAXSLP * 1000) 1609 return (EINVAL); 1610 1611 timo = mstohz(lsleep); 1612 1613 /* if the interval is >0 ms && <1 tick, use 1 tick */ 1614 if (lsleep != 0 && timo == 0) 1615 forkfsleep = 1; 1616 else 1617 forkfsleep = timo; 1618 1619 return (0); 1620} 1621 1622/* 1623 * sysctl helper routine for kern.root_partition 1624 */ 1625static int 1626sysctl_kern_root_partition(SYSCTLFN_ARGS) 1627{ 1628 int rootpart = DISKPART(rootdev); 1629 struct sysctlnode node = *rnode; 1630 1631 node.sysctl_data = &rootpart; 1632 return (sysctl_lookup(SYSCTLFN_CALL(&node))); 1633} 1634 1635/* 1636 * sysctl helper function for kern.drivers 1637 */ 1638static int 1639sysctl_kern_drivers(SYSCTLFN_ARGS) 1640{ 1641 int error; 1642 size_t buflen; 1643 struct kinfo_drivers kd; 1644 char *start, *where; 1645 const char *dname; 1646 int i; 1647 extern struct devsw_conv *devsw_conv; 1648 extern int max_devsw_convs; 1649 1650 if (newp != NULL || namelen != 0) 1651 return (EINVAL); 1652 1653 start = where = oldp; 1654 buflen = *oldlenp; 1655 if (where == NULL) { 1656 *oldlenp = max_devsw_convs * sizeof kd; 1657 return 0; 1658 } 1659 1660 /* 1661 * An array of kinfo_drivers structures 1662 */ 1663 error = 0; 1664 sysctl_unlock(); 1665 mutex_enter(&device_lock); 1666 for (i = 0; i < max_devsw_convs; i++) { 1667 dname = devsw_conv[i].d_name; 1668 if (dname == NULL) 1669 continue; 1670 if (buflen < sizeof kd) { 1671 error = ENOMEM; 1672 break; 1673 } 1674 memset(&kd, 0, sizeof(kd)); 1675 kd.d_bmajor = devsw_conv[i].d_bmajor; 1676 kd.d_cmajor = devsw_conv[i].d_cmajor; 1677 strlcpy(kd.d_name, dname, sizeof kd.d_name); 1678 mutex_exit(&device_lock); 1679 error = dcopyout(l, &kd, where, sizeof kd); 1680 mutex_enter(&device_lock); 1681 if (error != 0) 1682 break; 1683 buflen -= sizeof kd; 1684 where += sizeof kd; 1685 } 1686 mutex_exit(&device_lock); 1687 sysctl_relock(); 1688 *oldlenp = where - start; 1689 return error; 1690} 1691 1692static int 1693sysctl_security_setidcore(SYSCTLFN_ARGS) 1694{ 1695 int newsize, error; 1696 struct sysctlnode node; 1697 1698 node = *rnode; 1699 node.sysctl_data = &newsize; 1700 newsize = *(int *)rnode->sysctl_data; 1701 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 1702 if (error || newp == NULL) 1703 return error; 1704 1705 if (kauth_authorize_system(l->l_cred, KAUTH_SYSTEM_SETIDCORE, 1706 0, NULL, NULL, NULL)) 1707 return (EPERM); 1708 1709 *(int *)rnode->sysctl_data = newsize; 1710 1711 return 0; 1712} 1713 1714static int 1715sysctl_security_setidcorename(SYSCTLFN_ARGS) 1716{ 1717 int error; 1718 char *newsetidcorename; 1719 struct sysctlnode node; 1720 1721 newsetidcorename = PNBUF_GET(); 1722 node = *rnode; 1723 node.sysctl_data = newsetidcorename; 1724 memcpy(node.sysctl_data, rnode->sysctl_data, MAXPATHLEN); 1725 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 1726 if (error || newp == NULL) { 1727 goto out; 1728 } 1729 if (kauth_authorize_system(l->l_cred, KAUTH_SYSTEM_SETIDCORE, 1730 0, NULL, NULL, NULL)) { 1731 error = EPERM; 1732 goto out; 1733 } 1734 if (strlen(newsetidcorename) == 0) { 1735 error = EINVAL; 1736 goto out; 1737 } 1738 memcpy(rnode->sysctl_data, node.sysctl_data, MAXPATHLEN); 1739out: 1740 PNBUF_PUT(newsetidcorename); 1741 return error; 1742} 1743 1744/* 1745 * sysctl helper routine for kern.cp_id node. Maps cpus to their 1746 * cpuids. 1747 */ 1748static int 1749sysctl_kern_cpid(SYSCTLFN_ARGS) 1750{ 1751 struct sysctlnode node = *rnode; 1752 uint64_t *cp_id = NULL; 1753 int error, n = ncpu; 1754 struct cpu_info *ci; 1755 CPU_INFO_ITERATOR cii; 1756 1757 /* 1758 * Here you may either retrieve a single cpu id or the whole 1759 * set. The size you get back when probing depends on what 1760 * you ask for. 1761 */ 1762 switch (namelen) { 1763 case 0: 1764 node.sysctl_size = n * sizeof(uint64_t); 1765 n = -2; /* ALL */ 1766 break; 1767 case 1: 1768 if (name[0] < 0 || name[0] >= n) 1769 return (ENOENT); /* ENOSUCHPROCESSOR */ 1770 node.sysctl_size = sizeof(uint64_t); 1771 n = name[0]; 1772 /* 1773 * adjust these so that sysctl_lookup() will be happy 1774 */ 1775 name++; 1776 namelen--; 1777 break; 1778 default: 1779 return (EINVAL); 1780 } 1781 1782 cp_id = kmem_alloc(node.sysctl_size, KM_SLEEP); 1783 if (cp_id == NULL) 1784 return (ENOMEM); 1785 node.sysctl_data = cp_id; 1786 memset(cp_id, 0, node.sysctl_size); 1787 1788 for (CPU_INFO_FOREACH(cii, ci)) { 1789 if (n <= 0) 1790 cp_id[0] = cpu_index(ci); 1791 /* 1792 * if a specific processor was requested and we just 1793 * did it, we're done here 1794 */ 1795 if (n == 0) 1796 break; 1797 /* 1798 * if doing "all", skip to next cp_id slot for next processor 1799 */ 1800 if (n == -2) 1801 cp_id++; 1802 /* 1803 * if we're doing a specific processor, we're one 1804 * processor closer 1805 */ 1806 if (n > 0) 1807 n--; 1808 } 1809 1810 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 1811 kmem_free(node.sysctl_data, node.sysctl_size); 1812 return (error); 1813} 1814 1815/* 1816 * sysctl helper routine for hw.usermem and hw.usermem64. Values are 1817 * calculate on the fly taking into account integer overflow and the 1818 * current wired count. 1819 */ 1820static int 1821sysctl_hw_usermem(SYSCTLFN_ARGS) 1822{ 1823 u_int ui; 1824 u_quad_t uq; 1825 struct sysctlnode node; 1826 1827 node = *rnode; 1828 switch (rnode->sysctl_num) { 1829 case HW_USERMEM: 1830 if ((ui = physmem - uvmexp.wired) > (UINT_MAX / PAGE_SIZE)) 1831 ui = UINT_MAX; 1832 else 1833 ui *= PAGE_SIZE; 1834 node.sysctl_data = &ui; 1835 break; 1836 case HW_USERMEM64: 1837 uq = (u_quad_t)(physmem - uvmexp.wired) * PAGE_SIZE; 1838 node.sysctl_data = &uq; 1839 break; 1840 default: 1841 return (EINVAL); 1842 } 1843 1844 return (sysctl_lookup(SYSCTLFN_CALL(&node))); 1845} 1846 1847/* 1848 * sysctl helper routine for kern.cnmagic node. Pulls the old value 1849 * out, encoded, and stuffs the new value in for decoding. 1850 */ 1851static int 1852sysctl_hw_cnmagic(SYSCTLFN_ARGS) 1853{ 1854 char magic[CNS_LEN]; 1855 int error; 1856 struct sysctlnode node; 1857 1858 if (oldp) 1859 cn_get_magic(magic, CNS_LEN); 1860 node = *rnode; 1861 node.sysctl_data = &magic[0]; 1862 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 1863 if (error || newp == NULL) 1864 return (error); 1865 1866 return (cn_set_magic(magic)); 1867} 1868 1869/* 1870 * ******************************************************************** 1871 * section 3: public helper routines that are used for more than one 1872 * node 1873 * ******************************************************************** 1874 */ 1875 1876/* 1877 * sysctl helper routine for the kern.root_device node and some ports' 1878 * machdep.root_device nodes. 1879 */ 1880int 1881sysctl_root_device(SYSCTLFN_ARGS) 1882{ 1883 struct sysctlnode node; 1884 1885 node = *rnode; 1886 node.sysctl_data = root_device->dv_xname; 1887 node.sysctl_size = strlen(device_xname(root_device)) + 1; 1888 return (sysctl_lookup(SYSCTLFN_CALL(&node))); 1889} 1890 1891/* 1892 * sysctl helper routine for kern.consdev, dependent on the current 1893 * state of the console. Also used for machdep.console_device on some 1894 * ports. 1895 */ 1896int 1897sysctl_consdev(SYSCTLFN_ARGS) 1898{ 1899 dev_t consdev; 1900 uint32_t oconsdev; 1901 struct sysctlnode node; 1902 1903 if (cn_tab != NULL) 1904 consdev = cn_tab->cn_dev; 1905 else 1906 consdev = NODEV; 1907 node = *rnode; 1908 switch (*oldlenp) { 1909 case sizeof(consdev): 1910 node.sysctl_data = &consdev; 1911 node.sysctl_size = sizeof(consdev); 1912 break; 1913 case sizeof(oconsdev): 1914 oconsdev = (uint32_t)consdev; 1915 node.sysctl_data = &oconsdev; 1916 node.sysctl_size = sizeof(oconsdev); 1917 break; 1918 default: 1919 return EINVAL; 1920 } 1921 return (sysctl_lookup(SYSCTLFN_CALL(&node))); 1922} 1923 1924/* 1925 * ******************************************************************** 1926 * section 4: support for some helpers 1927 * ******************************************************************** 1928 */ 1929 1930 1931/* 1932 * Fill in a kinfo_lwp structure for the specified lwp. 1933 */ 1934static void 1935fill_lwp(struct lwp *l, struct kinfo_lwp *kl) 1936{ 1937 struct proc *p = l->l_proc; 1938 struct timeval tv; 1939 1940 KASSERT(lwp_locked(l, NULL)); 1941 1942 memset(kl, 0, sizeof(*kl)); 1943 1944 kl->l_forw = 0; 1945 kl->l_back = 0; 1946 kl->l_laddr = PTRTOUINT64(l); 1947 kl->l_addr = PTRTOUINT64(l->l_addr); 1948 kl->l_stat = l->l_stat; 1949 kl->l_lid = l->l_lid; 1950 kl->l_flag = L_INMEM; 1951 kl->l_flag |= sysctl_map_flags(sysctl_lwpprflagmap, l->l_prflag); 1952 kl->l_flag |= sysctl_map_flags(sysctl_lwpflagmap, l->l_flag); 1953 1954 kl->l_swtime = l->l_swtime; 1955 kl->l_slptime = l->l_slptime; 1956 if (l->l_stat == LSONPROC) 1957 kl->l_schedflags = l->l_cpu->ci_schedstate.spc_flags; 1958 else 1959 kl->l_schedflags = 0; 1960 kl->l_priority = lwp_eprio(l); 1961 kl->l_usrpri = l->l_priority; 1962 if (l->l_wchan) 1963 strncpy(kl->l_wmesg, l->l_wmesg, sizeof(kl->l_wmesg)); 1964 kl->l_wchan = PTRTOUINT64(l->l_wchan); 1965 kl->l_cpuid = cpu_index(l->l_cpu); 1966 bintime2timeval(&l->l_rtime, &tv); 1967 kl->l_rtime_sec = tv.tv_sec; 1968 kl->l_rtime_usec = tv.tv_usec; 1969 kl->l_cpticks = l->l_cpticks; 1970 kl->l_pctcpu = l->l_pctcpu; 1971 kl->l_pid = p->p_pid; 1972 if (l->l_name == NULL) 1973 kl->l_name[0] = '\0'; 1974 else 1975 strlcpy(kl->l_name, l->l_name, sizeof(kl->l_name)); 1976} 1977