init_sysctl.c revision 1.219
1/* $NetBSD: init_sysctl.c,v 1.219 2018/11/24 17:26:27 maxv 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.219 2018/11/24 17:26:27 maxv Exp $"); 34 35#include "opt_sysv.h" 36#include "opt_compat_netbsd.h" 37#include "opt_modular.h" 38#include "opt_gprof.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_impl.h> /* For vfs_drainvnodes(). */ 52#include <sys/mount.h> 53#include <sys/namei.h> 54#include <dev/cons.h> 55#include <sys/socketvar.h> 56#include <sys/file.h> 57#include <sys/filedesc.h> 58#include <sys/tty.h> 59#include <sys/kmem.h> 60#include <sys/reboot.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 70#include <sys/cpu.h> 71 72int security_setidcore_dump; 73char security_setidcore_path[MAXPATHLEN] = "/var/crash/%n.core"; 74uid_t security_setidcore_owner = 0; 75gid_t security_setidcore_group = 0; 76mode_t security_setidcore_mode = (S_IRUSR|S_IWUSR); 77 78/* 79 * Current status of SysV IPC capability. Initially, these are 80 * 0 if the capability is not built-in to the kernel, but can 81 * be updated if the appropriate kernel module is (auto)loaded. 82 */ 83 84int kern_has_sysvmsg = 0; 85int kern_has_sysvshm = 0; 86int kern_has_sysvsem = 0; 87 88int kern_expose_address = 0; 89 90static const u_int sysctl_lwpprflagmap[] = { 91 LPR_DETACHED, L_DETACHED, 92 0 93}; 94 95/* 96 * try over estimating by 5 procs/lwps 97 */ 98#define KERN_LWPSLOP (5 * sizeof(struct kinfo_lwp)) 99 100static int dcopyout(struct lwp *, const void *, void *, size_t); 101 102static int 103dcopyout(struct lwp *l, const void *kaddr, void *uaddr, size_t len) 104{ 105 int error; 106 107 error = copyout(kaddr, uaddr, len); 108 ktrmibio(-1, UIO_READ, uaddr, len, error); 109 110 return error; 111} 112 113#ifdef DIAGNOSTIC 114static int sysctl_kern_trigger_panic(SYSCTLFN_PROTO); 115#endif 116static int sysctl_kern_maxvnodes(SYSCTLFN_PROTO); 117static int sysctl_kern_messages(SYSCTLFN_PROTO); 118static int sysctl_kern_rtc_offset(SYSCTLFN_PROTO); 119static int sysctl_kern_maxproc(SYSCTLFN_PROTO); 120static int sysctl_kern_hostid(SYSCTLFN_PROTO); 121static int sysctl_kern_defcorename(SYSCTLFN_PROTO); 122static int sysctl_kern_cptime(SYSCTLFN_PROTO); 123#if NPTY > 0 124static int sysctl_kern_maxptys(SYSCTLFN_PROTO); 125#endif /* NPTY > 0 */ 126static int sysctl_kern_lwp(SYSCTLFN_PROTO); 127static int sysctl_kern_forkfsleep(SYSCTLFN_PROTO); 128static int sysctl_kern_root_partition(SYSCTLFN_PROTO); 129static int sysctl_kern_drivers(SYSCTLFN_PROTO); 130static int sysctl_security_setidcore(SYSCTLFN_PROTO); 131static int sysctl_security_setidcorename(SYSCTLFN_PROTO); 132static int sysctl_security_expose_address(SYSCTLFN_PROTO); 133static int sysctl_kern_cpid(SYSCTLFN_PROTO); 134static int sysctl_hw_usermem(SYSCTLFN_PROTO); 135static int sysctl_hw_cnmagic(SYSCTLFN_PROTO); 136 137static void fill_lwp(struct lwp *l, struct kinfo_lwp *kl); 138 139/* 140 * ******************************************************************** 141 * section 1: setup routines 142 * ******************************************************************** 143 * These functions are stuffed into a link set for sysctl setup 144 * functions. They're never called or referenced from anywhere else. 145 * ******************************************************************** 146 */ 147 148/* 149 * this setup routine is a replacement for kern_sysctl() 150 */ 151SYSCTL_SETUP(sysctl_kern_setup, "sysctl kern subtree setup") 152{ 153 extern int kern_logsigexit; /* defined in kern/kern_sig.c */ 154 extern fixpt_t ccpu; /* defined in kern/kern_synch.c */ 155 extern int dumponpanic; /* defined in kern/subr_prf.c */ 156 const struct sysctlnode *rnode; 157 158 sysctl_createv(clog, 0, NULL, NULL, 159 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 160 CTLTYPE_INT, "maxvnodes", 161 SYSCTL_DESCR("Maximum number of vnodes"), 162 sysctl_kern_maxvnodes, 0, NULL, 0, 163 CTL_KERN, KERN_MAXVNODES, CTL_EOL); 164 sysctl_createv(clog, 0, NULL, NULL, 165 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 166 CTLTYPE_INT, "maxproc", 167 SYSCTL_DESCR("Maximum number of simultaneous processes"), 168 sysctl_kern_maxproc, 0, NULL, 0, 169 CTL_KERN, KERN_MAXPROC, CTL_EOL); 170 sysctl_createv(clog, 0, NULL, NULL, 171 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 172 CTLTYPE_INT, "maxfiles", 173 SYSCTL_DESCR("Maximum number of open files"), 174 NULL, 0, &maxfiles, 0, 175 CTL_KERN, KERN_MAXFILES, CTL_EOL); 176 sysctl_createv(clog, 0, NULL, NULL, 177 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 178 CTLTYPE_INT, "argmax", 179 SYSCTL_DESCR("Maximum number of bytes of arguments to " 180 "execve(2)"), 181 NULL, ARG_MAX, NULL, 0, 182 CTL_KERN, KERN_ARGMAX, CTL_EOL); 183 sysctl_createv(clog, 0, NULL, NULL, 184 CTLFLAG_PERMANENT|CTLFLAG_READWRITE|CTLFLAG_HEX, 185 CTLTYPE_INT, "hostid", 186 SYSCTL_DESCR("System host ID number"), 187 sysctl_kern_hostid, 0, NULL, 0, 188 CTL_KERN, KERN_HOSTID, CTL_EOL); 189 sysctl_createv(clog, 0, NULL, NULL, 190 CTLFLAG_PERMANENT, 191 CTLTYPE_STRUCT, "vnode", 192 SYSCTL_DESCR("System vnode table"), 193 sysctl_kern_vnode, 0, NULL, 0, 194 CTL_KERN, KERN_VNODE, CTL_EOL); 195#ifndef GPROF 196 sysctl_createv(clog, 0, NULL, NULL, 197 CTLFLAG_PERMANENT, 198 CTLTYPE_NODE, "profiling", 199 SYSCTL_DESCR("Profiling information (not available)"), 200 sysctl_notavail, 0, NULL, 0, 201 CTL_KERN, KERN_PROF, CTL_EOL); 202#endif 203 sysctl_createv(clog, 0, NULL, NULL, 204 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 205 CTLTYPE_INT, "posix1version", 206 SYSCTL_DESCR("Version of ISO/IEC 9945 (POSIX 1003.1) " 207 "with which the operating system attempts " 208 "to comply"), 209 NULL, _POSIX_VERSION, NULL, 0, 210 CTL_KERN, KERN_POSIX1, CTL_EOL); 211 sysctl_createv(clog, 0, NULL, NULL, 212 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 213 CTLTYPE_INT, "ngroups", 214 SYSCTL_DESCR("Maximum number of supplemental groups"), 215 NULL, NGROUPS_MAX, NULL, 0, 216 CTL_KERN, KERN_NGROUPS, CTL_EOL); 217 sysctl_createv(clog, 0, NULL, NULL, 218 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 219 CTLTYPE_INT, "job_control", 220 SYSCTL_DESCR("Whether job control is available"), 221 NULL, 1, NULL, 0, 222 CTL_KERN, KERN_JOB_CONTROL, CTL_EOL); 223 sysctl_createv(clog, 0, NULL, NULL, 224 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 225 CTLTYPE_INT, "saved_ids", 226 SYSCTL_DESCR("Whether POSIX saved set-group/user ID is " 227 "available"), NULL, 228#ifdef _POSIX_SAVED_IDS 229 1, 230#else /* _POSIX_SAVED_IDS */ 231 0, 232#endif /* _POSIX_SAVED_IDS */ 233 NULL, 0, CTL_KERN, KERN_SAVED_IDS, CTL_EOL); 234 sysctl_createv(clog, 0, NULL, NULL, 235 CTLFLAG_PERMANENT|CTLFLAG_HEX, 236 CTLTYPE_INT, "boothowto", 237 SYSCTL_DESCR("Flags from boot loader"), 238 NULL, 0, &boothowto, sizeof(boothowto), 239 CTL_KERN, CTL_CREATE, CTL_EOL); 240 sysctl_createv(clog, 0, NULL, NULL, 241 CTLFLAG_PERMANENT, 242 CTLTYPE_STRUCT, "boottime", 243 SYSCTL_DESCR("System boot time"), 244 NULL, 0, &boottime, sizeof(boottime), 245 CTL_KERN, KERN_BOOTTIME, CTL_EOL); 246 sysctl_createv(clog, 0, NULL, NULL, 247 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 248 CTLTYPE_INT, "maxpartitions", 249 SYSCTL_DESCR("Maximum number of partitions allowed per " 250 "disk"), 251 NULL, MAXPARTITIONS, NULL, 0, 252 CTL_KERN, KERN_MAXPARTITIONS, CTL_EOL); 253 sysctl_createv(clog, 0, NULL, NULL, 254 CTLFLAG_PERMANENT, 255 CTLTYPE_STRUCT, "timex", NULL, 256 sysctl_notavail, 0, NULL, 0, 257 CTL_KERN, KERN_TIMEX, CTL_EOL); 258 sysctl_createv(clog, 0, NULL, NULL, 259 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 260 CTLTYPE_INT, "rtc_offset", 261 SYSCTL_DESCR("Offset of real time clock from UTC in " 262 "minutes"), 263 sysctl_kern_rtc_offset, 0, &rtc_offset, 0, 264 CTL_KERN, KERN_RTC_OFFSET, CTL_EOL); 265 sysctl_createv(clog, 0, NULL, NULL, 266 CTLFLAG_PERMANENT, 267 CTLTYPE_STRING, "root_device", 268 SYSCTL_DESCR("Name of the root device"), 269 sysctl_root_device, 0, NULL, 0, 270 CTL_KERN, KERN_ROOT_DEVICE, CTL_EOL); 271 sysctl_createv(clog, 0, NULL, NULL, 272 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 273 CTLTYPE_INT, "fsync", 274 SYSCTL_DESCR("Whether the POSIX 1003.1b File " 275 "Synchronization Option is available on " 276 "this system"), 277 NULL, 1, NULL, 0, 278 CTL_KERN, KERN_FSYNC, CTL_EOL); 279 sysctl_createv(clog, 0, NULL, NULL, 280 CTLFLAG_PERMANENT, 281 CTLTYPE_NODE, "ipc", 282 SYSCTL_DESCR("SysV IPC options"), 283 NULL, 0, NULL, 0, 284 CTL_KERN, KERN_SYSVIPC, CTL_EOL); 285 sysctl_createv(clog, 0, NULL, NULL, 286 CTLFLAG_PERMANENT|CTLFLAG_READONLY, 287 CTLTYPE_INT, "sysvmsg", 288 SYSCTL_DESCR("System V style message support available"), 289 NULL, 0, &kern_has_sysvmsg, sizeof(int), 290 CTL_KERN, KERN_SYSVIPC, KERN_SYSVIPC_MSG, CTL_EOL); 291 sysctl_createv(clog, 0, NULL, NULL, 292 CTLFLAG_PERMANENT|CTLFLAG_READONLY, 293 CTLTYPE_INT, "sysvsem", 294 SYSCTL_DESCR("System V style semaphore support " 295 "available"), 296 NULL, 0, &kern_has_sysvsem, sizeof(int), 297 CTL_KERN, KERN_SYSVIPC, KERN_SYSVIPC_SEM, CTL_EOL); 298 sysctl_createv(clog, 0, NULL, NULL, 299 CTLFLAG_PERMANENT|CTLFLAG_READONLY, 300 CTLTYPE_INT, "sysvshm", 301 SYSCTL_DESCR("System V style shared memory support " 302 "available"), 303 NULL, 0, &kern_has_sysvshm, sizeof(int), 304 CTL_KERN, KERN_SYSVIPC, KERN_SYSVIPC_SHM, CTL_EOL); 305 sysctl_createv(clog, 0, NULL, NULL, 306 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 307 CTLTYPE_INT, "synchronized_io", 308 SYSCTL_DESCR("Whether the POSIX 1003.1b Synchronized " 309 "I/O Option is available on this system"), 310 NULL, 1, NULL, 0, 311 CTL_KERN, KERN_SYNCHRONIZED_IO, CTL_EOL); 312 sysctl_createv(clog, 0, NULL, NULL, 313 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 314 CTLTYPE_INT, "iov_max", 315 SYSCTL_DESCR("Maximum number of iovec structures per " 316 "process"), 317 NULL, IOV_MAX, NULL, 0, 318 CTL_KERN, KERN_IOV_MAX, CTL_EOL); 319 sysctl_createv(clog, 0, NULL, NULL, 320 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 321 CTLTYPE_INT, "mapped_files", 322 SYSCTL_DESCR("Whether the POSIX 1003.1b Memory Mapped " 323 "Files Option is available on this system"), 324 NULL, 1, NULL, 0, 325 CTL_KERN, KERN_MAPPED_FILES, CTL_EOL); 326 sysctl_createv(clog, 0, NULL, NULL, 327 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 328 CTLTYPE_INT, "memlock", 329 SYSCTL_DESCR("Whether the POSIX 1003.1b Process Memory " 330 "Locking Option is available on this " 331 "system"), 332 NULL, 1, NULL, 0, 333 CTL_KERN, KERN_MEMLOCK, CTL_EOL); 334 sysctl_createv(clog, 0, NULL, NULL, 335 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 336 CTLTYPE_INT, "memlock_range", 337 SYSCTL_DESCR("Whether the POSIX 1003.1b Range Memory " 338 "Locking Option is available on this " 339 "system"), 340 NULL, 1, NULL, 0, 341 CTL_KERN, KERN_MEMLOCK_RANGE, CTL_EOL); 342 sysctl_createv(clog, 0, NULL, NULL, 343 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 344 CTLTYPE_INT, "memory_protection", 345 SYSCTL_DESCR("Whether the POSIX 1003.1b Memory " 346 "Protection Option is available on this " 347 "system"), 348 NULL, 1, NULL, 0, 349 CTL_KERN, KERN_MEMORY_PROTECTION, CTL_EOL); 350 sysctl_createv(clog, 0, NULL, NULL, 351 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 352 CTLTYPE_INT, "login_name_max", 353 SYSCTL_DESCR("Maximum login name length"), 354 NULL, LOGIN_NAME_MAX, NULL, 0, 355 CTL_KERN, KERN_LOGIN_NAME_MAX, CTL_EOL); 356 sysctl_createv(clog, 0, NULL, NULL, 357 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 358 CTLTYPE_STRING, "defcorename", 359 SYSCTL_DESCR("Default core file name"), 360 sysctl_kern_defcorename, 0, defcorename, MAXPATHLEN, 361 CTL_KERN, KERN_DEFCORENAME, CTL_EOL); 362 sysctl_createv(clog, 0, NULL, NULL, 363 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 364 CTLTYPE_INT, "logsigexit", 365 SYSCTL_DESCR("Log process exit when caused by signals"), 366 NULL, 0, &kern_logsigexit, 0, 367 CTL_KERN, KERN_LOGSIGEXIT, CTL_EOL); 368 sysctl_createv(clog, 0, NULL, NULL, 369 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 370 CTLTYPE_INT, "fscale", 371 SYSCTL_DESCR("Kernel fixed-point scale factor"), 372 NULL, FSCALE, NULL, 0, 373 CTL_KERN, KERN_FSCALE, CTL_EOL); 374 sysctl_createv(clog, 0, NULL, NULL, 375 CTLFLAG_PERMANENT, 376 CTLTYPE_INT, "ccpu", 377 SYSCTL_DESCR("Scheduler exponential decay value"), 378 NULL, 0, &ccpu, 0, 379 CTL_KERN, KERN_CCPU, CTL_EOL); 380 sysctl_createv(clog, 0, NULL, NULL, 381 CTLFLAG_PERMANENT, 382 CTLTYPE_STRUCT, "cp_time", 383 SYSCTL_DESCR("Clock ticks spent in different CPU states"), 384 sysctl_kern_cptime, 0, NULL, 0, 385 CTL_KERN, KERN_CP_TIME, CTL_EOL); 386 sysctl_createv(clog, 0, NULL, NULL, 387 CTLFLAG_PERMANENT, 388 CTLTYPE_STRUCT, "consdev", 389 SYSCTL_DESCR("Console device"), 390 sysctl_consdev, 0, NULL, sizeof(dev_t), 391 CTL_KERN, KERN_CONSDEV, CTL_EOL); 392#if NPTY > 0 393 sysctl_createv(clog, 0, NULL, NULL, 394 CTLFLAG_PERMANENT, 395 CTLTYPE_INT, "maxptys", 396 SYSCTL_DESCR("Maximum number of pseudo-ttys"), 397 sysctl_kern_maxptys, 0, NULL, 0, 398 CTL_KERN, KERN_MAXPTYS, CTL_EOL); 399#endif /* NPTY > 0 */ 400 sysctl_createv(clog, 0, NULL, NULL, 401 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 402 CTLTYPE_INT, "maxphys", 403 SYSCTL_DESCR("Maximum raw I/O transfer size"), 404 NULL, MAXPHYS, NULL, 0, 405 CTL_KERN, KERN_MAXPHYS, CTL_EOL); 406 sysctl_createv(clog, 0, NULL, NULL, 407 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 408 CTLTYPE_INT, "monotonic_clock", 409 SYSCTL_DESCR("Implementation version of the POSIX " 410 "1003.1b Monotonic Clock Option"), 411 /* XXX _POSIX_VERSION */ 412 NULL, _POSIX_MONOTONIC_CLOCK, NULL, 0, 413 CTL_KERN, KERN_MONOTONIC_CLOCK, CTL_EOL); 414 sysctl_createv(clog, 0, NULL, NULL, 415 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 416 CTLTYPE_INT, "labelsector", 417 SYSCTL_DESCR("Sector number containing the disklabel"), 418 NULL, LABELSECTOR, NULL, 0, 419 CTL_KERN, KERN_LABELSECTOR, CTL_EOL); 420 sysctl_createv(clog, 0, NULL, NULL, 421 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 422 CTLTYPE_INT, "labeloffset", 423 SYSCTL_DESCR("Offset of the disklabel within the " 424 "sector"), 425 NULL, LABELOFFSET, NULL, 0, 426 CTL_KERN, KERN_LABELOFFSET, CTL_EOL); 427 sysctl_createv(clog, 0, NULL, NULL, 428 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 429 CTLTYPE_INT, "labelusesmbr", 430 SYSCTL_DESCR("disklabel is inside MBR partition"), 431 NULL, LABELUSESMBR, NULL, 0, 432 CTL_KERN, CTL_CREATE, CTL_EOL); 433 sysctl_createv(clog, 0, NULL, NULL, 434 CTLFLAG_PERMANENT, 435 CTLTYPE_NODE, "lwp", 436 SYSCTL_DESCR("System-wide LWP information"), 437 sysctl_kern_lwp, 0, NULL, 0, 438 CTL_KERN, KERN_LWP, CTL_EOL); 439 sysctl_createv(clog, 0, NULL, NULL, 440 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 441 CTLTYPE_INT, "forkfsleep", 442 SYSCTL_DESCR("Milliseconds to sleep on fork failure due " 443 "to process limits"), 444 sysctl_kern_forkfsleep, 0, NULL, 0, 445 CTL_KERN, KERN_FORKFSLEEP, CTL_EOL); 446 sysctl_createv(clog, 0, NULL, NULL, 447 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 448 CTLTYPE_INT, "posix_threads", 449 SYSCTL_DESCR("Version of IEEE Std 1003.1 and its " 450 "Threads option to which the system " 451 "attempts to conform"), 452 /* XXX _POSIX_VERSION */ 453 NULL, _POSIX_THREADS, NULL, 0, 454 CTL_KERN, KERN_POSIX_THREADS, CTL_EOL); 455 sysctl_createv(clog, 0, NULL, NULL, 456 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 457 CTLTYPE_INT, "posix_semaphores", 458 SYSCTL_DESCR("Version of IEEE Std 1003.1 and its " 459 "Semaphores option to which the system " 460 "attempts to conform"), NULL, 461 200112, NULL, 0, 462 CTL_KERN, KERN_POSIX_SEMAPHORES, CTL_EOL); 463 sysctl_createv(clog, 0, NULL, NULL, 464 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 465 CTLTYPE_INT, "posix_barriers", 466 SYSCTL_DESCR("Version of IEEE Std 1003.1 and its " 467 "Barriers option to which the system " 468 "attempts to conform"), 469 /* XXX _POSIX_VERSION */ 470 NULL, _POSIX_BARRIERS, NULL, 0, 471 CTL_KERN, KERN_POSIX_BARRIERS, CTL_EOL); 472 sysctl_createv(clog, 0, NULL, NULL, 473 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 474 CTLTYPE_INT, "posix_timers", 475 SYSCTL_DESCR("Version of IEEE Std 1003.1 and its " 476 "Timers option to which the system " 477 "attempts to conform"), 478 /* XXX _POSIX_VERSION */ 479 NULL, _POSIX_TIMERS, NULL, 0, 480 CTL_KERN, KERN_POSIX_TIMERS, CTL_EOL); 481 sysctl_createv(clog, 0, NULL, NULL, 482 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 483 CTLTYPE_INT, "posix_spin_locks", 484 SYSCTL_DESCR("Version of IEEE Std 1003.1 and its Spin " 485 "Locks option to which the system attempts " 486 "to conform"), 487 /* XXX _POSIX_VERSION */ 488 NULL, _POSIX_SPIN_LOCKS, NULL, 0, 489 CTL_KERN, KERN_POSIX_SPIN_LOCKS, CTL_EOL); 490 sysctl_createv(clog, 0, NULL, NULL, 491 CTLFLAG_PERMANENT|CTLFLAG_IMMEDIATE, 492 CTLTYPE_INT, "posix_reader_writer_locks", 493 SYSCTL_DESCR("Version of IEEE Std 1003.1 and its " 494 "Read-Write Locks option to which the " 495 "system attempts to conform"), 496 /* XXX _POSIX_VERSION */ 497 NULL, _POSIX_READER_WRITER_LOCKS, NULL, 0, 498 CTL_KERN, KERN_POSIX_READER_WRITER_LOCKS, CTL_EOL); 499 sysctl_createv(clog, 0, NULL, NULL, 500 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 501 CTLTYPE_INT, "dump_on_panic", 502 SYSCTL_DESCR("Perform a crash dump on system panic"), 503 NULL, 0, &dumponpanic, 0, 504 CTL_KERN, KERN_DUMP_ON_PANIC, CTL_EOL); 505#ifdef DIAGNOSTIC 506 sysctl_createv(clog, 0, NULL, NULL, 507 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 508 CTLTYPE_INT, "panic_now", 509 SYSCTL_DESCR("Trigger a panic"), 510 sysctl_kern_trigger_panic, 0, NULL, 0, 511 CTL_KERN, CTL_CREATE, CTL_EOL); 512#endif 513 sysctl_createv(clog, 0, NULL, NULL, 514 CTLFLAG_PERMANENT, 515 CTLTYPE_INT, "root_partition", 516 SYSCTL_DESCR("Root partition on the root device"), 517 sysctl_kern_root_partition, 0, NULL, 0, 518 CTL_KERN, KERN_ROOT_PARTITION, CTL_EOL); 519 sysctl_createv(clog, 0, NULL, NULL, 520 CTLFLAG_PERMANENT, 521 CTLTYPE_STRUCT, "drivers", 522 SYSCTL_DESCR("List of all drivers with block and " 523 "character device numbers"), 524 sysctl_kern_drivers, 0, NULL, 0, 525 CTL_KERN, KERN_DRIVERS, CTL_EOL); 526 sysctl_createv(clog, 0, NULL, NULL, 527 CTLFLAG_PERMANENT, 528 CTLTYPE_STRUCT, "cp_id", 529 SYSCTL_DESCR("Mapping of CPU number to CPU id"), 530 sysctl_kern_cpid, 0, NULL, 0, 531 CTL_KERN, KERN_CP_ID, CTL_EOL); 532 sysctl_createv(clog, 0, NULL, &rnode, 533 CTLFLAG_PERMANENT, 534 CTLTYPE_NODE, "coredump", 535 SYSCTL_DESCR("Coredump settings."), 536 NULL, 0, NULL, 0, 537 CTL_KERN, CTL_CREATE, CTL_EOL); 538 sysctl_createv(clog, 0, &rnode, &rnode, 539 CTLFLAG_PERMANENT, 540 CTLTYPE_NODE, "setid", 541 SYSCTL_DESCR("Set-id processes' coredump settings."), 542 NULL, 0, NULL, 0, 543 CTL_CREATE, CTL_EOL); 544 sysctl_createv(clog, 0, &rnode, NULL, 545 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 546 CTLTYPE_INT, "dump", 547 SYSCTL_DESCR("Allow set-id processes to dump core."), 548 sysctl_security_setidcore, 0, &security_setidcore_dump, 549 sizeof(security_setidcore_dump), 550 CTL_CREATE, CTL_EOL); 551 sysctl_createv(clog, 0, &rnode, NULL, 552 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 553 CTLTYPE_STRING, "path", 554 SYSCTL_DESCR("Path pattern for set-id coredumps."), 555 sysctl_security_setidcorename, 0, 556 security_setidcore_path, 557 sizeof(security_setidcore_path), 558 CTL_CREATE, CTL_EOL); 559 sysctl_createv(clog, 0, &rnode, NULL, 560 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 561 CTLTYPE_INT, "owner", 562 SYSCTL_DESCR("Owner id for set-id processes' cores."), 563 sysctl_security_setidcore, 0, &security_setidcore_owner, 564 0, 565 CTL_CREATE, CTL_EOL); 566 sysctl_createv(clog, 0, &rnode, NULL, 567 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 568 CTLTYPE_INT, "group", 569 SYSCTL_DESCR("Group id for set-id processes' cores."), 570 sysctl_security_setidcore, 0, &security_setidcore_group, 571 0, 572 CTL_CREATE, CTL_EOL); 573 sysctl_createv(clog, 0, &rnode, NULL, 574 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 575 CTLTYPE_INT, "mode", 576 SYSCTL_DESCR("Mode for set-id processes' cores."), 577 sysctl_security_setidcore, 0, &security_setidcore_mode, 578 0, 579 CTL_CREATE, CTL_EOL); 580 sysctl_createv(clog, 0, NULL, NULL, 581 CTLFLAG_IMMEDIATE|CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 582 CTLTYPE_INT, "no_sa_support", 583 SYSCTL_DESCR("0 if the kernel supports SA, otherwise " 584 "it doesn't"), 585 NULL, 1, NULL, 0, 586 CTL_KERN, CTL_CREATE, CTL_EOL); 587 sysctl_createv(clog, 0, NULL, NULL, 588 CTLFLAG_PERMANENT, 589 CTLTYPE_STRING, "configname", 590 SYSCTL_DESCR("Name of config file"), 591 NULL, 0, __UNCONST(kernel_ident), 0, 592 CTL_KERN, CTL_CREATE, CTL_EOL); 593 sysctl_createv(clog, 0, NULL, NULL, 594 CTLFLAG_PERMANENT, 595 CTLTYPE_STRING, "buildinfo", 596 SYSCTL_DESCR("Information from build environment"), 597 NULL, 0, __UNCONST(buildinfo), 0, 598 CTL_KERN, CTL_CREATE, CTL_EOL); 599 sysctl_createv(clog, 0, NULL, NULL, 600 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 601 CTLTYPE_INT, "messages", 602 SYSCTL_DESCR("Kernel message verbosity"), 603 sysctl_kern_messages, 0, NULL, 0, 604 CTL_KERN, CTL_CREATE, CTL_EOL); 605 sysctl_createv(clog, 0, NULL, NULL, 606 CTLFLAG_PERMANENT|CTLFLAG_READWRITE, 607 CTLTYPE_INT, "expose_address", 608 SYSCTL_DESCR("Expose kernel addresses to userland"), 609 sysctl_security_expose_address, 0, &kern_expose_address, 610 0, CTL_KERN, CTL_CREATE, CTL_EOL); 611} 612 613SYSCTL_SETUP(sysctl_hw_misc_setup, "sysctl hw subtree misc setup") 614{ 615 616 sysctl_createv(clog, 0, NULL, NULL, 617 CTLFLAG_PERMANENT, 618 CTLTYPE_INT, "usermem", 619 SYSCTL_DESCR("Bytes of non-kernel memory"), 620 sysctl_hw_usermem, 0, NULL, 0, 621 CTL_HW, HW_USERMEM, CTL_EOL); 622 sysctl_createv(clog, 0, NULL, NULL, 623 CTLFLAG_PERMANENT|CTLFLAG_READWRITE|CTLFLAG_HEX, 624 CTLTYPE_STRING, "cnmagic", 625 SYSCTL_DESCR("Console magic key sequence"), 626 sysctl_hw_cnmagic, 0, NULL, CNS_LEN, 627 CTL_HW, HW_CNMAGIC, CTL_EOL); 628 sysctl_createv(clog, 0, NULL, NULL, 629 CTLFLAG_PERMANENT, 630 CTLTYPE_QUAD, "usermem64", 631 SYSCTL_DESCR("Bytes of non-kernel memory"), 632 sysctl_hw_usermem, 0, NULL, 0, 633 CTL_HW, HW_USERMEM64, CTL_EOL); 634} 635 636#ifdef DEBUG 637/* 638 * Debugging related system variables. 639 */ 640struct ctldebug /* debug0, */ /* debug1, */ debug2, debug3, debug4; 641struct ctldebug debug5, debug6, debug7, debug8, debug9; 642struct ctldebug debug10, debug11, debug12, debug13, debug14; 643struct ctldebug debug15, debug16, debug17, debug18, debug19; 644static struct ctldebug *debugvars[] = { 645 &debug0, &debug1, &debug2, &debug3, &debug4, 646 &debug5, &debug6, &debug7, &debug8, &debug9, 647 &debug10, &debug11, &debug12, &debug13, &debug14, 648 &debug15, &debug16, &debug17, &debug18, &debug19, 649}; 650 651/* 652 * this setup routine is a replacement for debug_sysctl() 653 * 654 * note that it creates several nodes per defined debug variable 655 */ 656SYSCTL_SETUP(sysctl_debug_setup, "sysctl debug subtree setup") 657{ 658 struct ctldebug *cdp; 659 char nodename[20]; 660 int i; 661 662 /* 663 * two ways here: 664 * 665 * the "old" way (debug.name -> value) which was emulated by 666 * the sysctl(8) binary 667 * 668 * the new way, which the sysctl(8) binary was actually using 669 670 node debug 671 node debug.0 672 string debug.0.name 673 int debug.0.value 674 int debug.name 675 676 */ 677 678 for (i = 0; i < __arraycount(debugvars); i++) { 679 cdp = debugvars[i]; 680 if (cdp->debugname == NULL || cdp->debugvar == NULL) 681 continue; 682 683 snprintf(nodename, sizeof(nodename), "debug%d", i); 684 sysctl_createv(clog, 0, NULL, NULL, 685 CTLFLAG_PERMANENT|CTLFLAG_HIDDEN, 686 CTLTYPE_NODE, nodename, NULL, 687 NULL, 0, NULL, 0, 688 CTL_DEBUG, i, CTL_EOL); 689 sysctl_createv(clog, 0, NULL, NULL, 690 CTLFLAG_PERMANENT|CTLFLAG_HIDDEN, 691 CTLTYPE_STRING, "name", NULL, 692 /*XXXUNCONST*/ 693 NULL, 0, __UNCONST(cdp->debugname), 0, 694 CTL_DEBUG, i, CTL_DEBUG_NAME, CTL_EOL); 695 sysctl_createv(clog, 0, NULL, NULL, 696 CTLFLAG_PERMANENT|CTLFLAG_HIDDEN, 697 CTLTYPE_INT, "value", NULL, 698 NULL, 0, cdp->debugvar, 0, 699 CTL_DEBUG, i, CTL_DEBUG_VALUE, CTL_EOL); 700 sysctl_createv(clog, 0, NULL, NULL, 701 CTLFLAG_PERMANENT, 702 CTLTYPE_INT, cdp->debugname, NULL, 703 NULL, 0, cdp->debugvar, 0, 704 CTL_DEBUG, CTL_CREATE, CTL_EOL); 705 } 706} 707#endif /* DEBUG */ 708 709/* 710 * ******************************************************************** 711 * section 2: private node-specific helper routines. 712 * ******************************************************************** 713 */ 714 715#ifdef DIAGNOSTIC 716static int 717sysctl_kern_trigger_panic(SYSCTLFN_ARGS) 718{ 719 int newtrig, error; 720 struct sysctlnode node; 721 722 newtrig = 0; 723 node = *rnode; 724 node.sysctl_data = &newtrig; 725 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 726 if (error || newp == NULL) 727 return (error); 728 729 if (newtrig != 0) 730 panic("Panic triggered"); 731 732 return (error); 733} 734#endif 735 736/* 737 * sysctl helper routine for kern.maxvnodes. Drain vnodes if 738 * new value is lower than desiredvnodes and then calls reinit 739 * routines that needs to adjust to the new value. 740 */ 741static int 742sysctl_kern_maxvnodes(SYSCTLFN_ARGS) 743{ 744 int error, new_vnodes, old_vnodes, new_max; 745 struct sysctlnode node; 746 747 new_vnodes = desiredvnodes; 748 node = *rnode; 749 node.sysctl_data = &new_vnodes; 750 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 751 if (error || newp == NULL) 752 return (error); 753 754 /* 755 * sysctl passes down unsigned values, require them 756 * to be positive 757 */ 758 if (new_vnodes <= 0) 759 return (EINVAL); 760 761 /* Limits: 75% of kmem and physical memory. */ 762 new_max = calc_cache_size(vmem_size(kmem_arena, VMEM_FREE|VMEM_ALLOC), 763 75, 75) / VNODE_COST; 764 if (new_vnodes > new_max) 765 new_vnodes = new_max; 766 767 old_vnodes = desiredvnodes; 768 desiredvnodes = new_vnodes; 769 error = vfs_drainvnodes(); 770 if (error) { 771 desiredvnodes = old_vnodes; 772 return (error); 773 } 774 vfs_reinit(); 775 nchreinit(); 776 777 return (0); 778} 779 780/* 781 * sysctl helper routine for kern.messages. 782 * Alters boothowto to display kernel messages in increasing verbosity 783 * from 0 to 4. 784 */ 785 786#define MAXMESSAGES 4 787static int 788sysctl_kern_messages(SYSCTLFN_ARGS) 789{ 790 int error, messageverbose, messagemask, newboothowto; 791 struct sysctlnode node; 792 793 messagemask = (AB_NORMAL|AB_QUIET|AB_SILENT|AB_VERBOSE|AB_DEBUG); 794 switch (boothowto & messagemask) { 795 case AB_SILENT: 796 messageverbose = 0; 797 break; 798 case AB_QUIET: 799 messageverbose = 1; 800 break; 801 case AB_VERBOSE: 802 messageverbose = 3; 803 break; 804 case AB_DEBUG: 805 messageverbose = 4; 806 break; 807 case AB_NORMAL: 808 default: 809 messageverbose = 2; 810 } 811 812 node = *rnode; 813 node.sysctl_data = &messageverbose; 814 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 815 if (error || newp == NULL) 816 return (error); 817 if (messageverbose < 0 || messageverbose > MAXMESSAGES) 818 return EINVAL; 819 820 /* Set boothowto */ 821 newboothowto = boothowto & ~messagemask; 822 823 switch (messageverbose) { 824 case 0: 825 newboothowto |= AB_SILENT; 826 break; 827 case 1: 828 newboothowto |= AB_QUIET; 829 break; 830 case 3: 831 newboothowto |= AB_VERBOSE; 832 break; 833 case 4: 834 newboothowto |= AB_DEBUG; 835 break; 836 case 2: 837 default: /* Messages default to normal. */ 838 break; 839 } 840 841 boothowto = newboothowto; 842 843 return (0); 844} 845 846/* 847 * sysctl helper routine for rtc_offset - set time after changes 848 */ 849static int 850sysctl_kern_rtc_offset(SYSCTLFN_ARGS) 851{ 852 struct timespec ts, delta; 853 int error, new_rtc_offset; 854 struct sysctlnode node; 855 856 new_rtc_offset = rtc_offset; 857 node = *rnode; 858 node.sysctl_data = &new_rtc_offset; 859 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 860 if (error || newp == NULL) 861 return (error); 862 863 if (kauth_authorize_system(l->l_cred, KAUTH_SYSTEM_TIME, 864 KAUTH_REQ_SYSTEM_TIME_RTCOFFSET, 865 KAUTH_ARG(new_rtc_offset), NULL, NULL)) 866 return (EPERM); 867 if (rtc_offset == new_rtc_offset) 868 return (0); 869 870 /* if we change the offset, adjust the time */ 871 nanotime(&ts); 872 delta.tv_sec = 60 * (new_rtc_offset - rtc_offset); 873 delta.tv_nsec = 0; 874 timespecadd(&ts, &delta, &ts); 875 rtc_offset = new_rtc_offset; 876 return (settime(l->l_proc, &ts)); 877} 878 879/* 880 * sysctl helper routine for kern.maxproc. Ensures that the new 881 * values are not too low or too high. 882 */ 883static int 884sysctl_kern_maxproc(SYSCTLFN_ARGS) 885{ 886 int error, nmaxproc; 887 struct sysctlnode node; 888 889 nmaxproc = maxproc; 890 node = *rnode; 891 node.sysctl_data = &nmaxproc; 892 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 893 if (error || newp == NULL) 894 return (error); 895 896 if (nmaxproc < 0 || nmaxproc >= PID_MAX) 897 return (EINVAL); 898#ifdef __HAVE_CPU_MAXPROC 899 if (nmaxproc > cpu_maxproc()) 900 return (EINVAL); 901#endif 902 maxproc = nmaxproc; 903 904 return (0); 905} 906 907/* 908 * sysctl helper function for kern.hostid. The hostid is a long, but 909 * we export it as an int, so we need to give it a little help. 910 */ 911static int 912sysctl_kern_hostid(SYSCTLFN_ARGS) 913{ 914 int error, inthostid; 915 struct sysctlnode node; 916 917 inthostid = hostid; /* XXX assumes sizeof int <= sizeof long */ 918 node = *rnode; 919 node.sysctl_data = &inthostid; 920 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 921 if (error || newp == NULL) 922 return (error); 923 924 hostid = (unsigned)inthostid; 925 926 return (0); 927} 928 929/* 930 * sysctl helper routine for kern.defcorename. In the case of a new 931 * string being assigned, check that it's not a zero-length string. 932 * (XXX the check in -current doesn't work, but do we really care?) 933 */ 934static int 935sysctl_kern_defcorename(SYSCTLFN_ARGS) 936{ 937 int error; 938 char *newcorename; 939 struct sysctlnode node; 940 941 newcorename = PNBUF_GET(); 942 node = *rnode; 943 node.sysctl_data = &newcorename[0]; 944 memcpy(node.sysctl_data, rnode->sysctl_data, MAXPATHLEN); 945 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 946 if (error || newp == NULL) { 947 goto done; 948 } 949 950 /* 951 * when sysctl_lookup() deals with a string, it's guaranteed 952 * to come back nul terminated. So there. :) 953 */ 954 if (strlen(newcorename) == 0) { 955 error = EINVAL; 956 } else { 957 memcpy(rnode->sysctl_data, node.sysctl_data, MAXPATHLEN); 958 error = 0; 959 } 960done: 961 PNBUF_PUT(newcorename); 962 return error; 963} 964 965/* 966 * sysctl helper routine for kern.cp_time node. Adds up cpu time 967 * across all cpus. 968 */ 969static int 970sysctl_kern_cptime(SYSCTLFN_ARGS) 971{ 972 struct sysctlnode node = *rnode; 973 uint64_t *cp_time = NULL; 974 int error, n = ncpu, i; 975 struct cpu_info *ci; 976 CPU_INFO_ITERATOR cii; 977 978 /* 979 * if you specifically pass a buffer that is the size of the 980 * sum, or if you are probing for the size, you get the "sum" 981 * of cp_time (and the size thereof) across all processors. 982 * 983 * alternately, you can pass an additional mib number and get 984 * cp_time for that particular processor. 985 */ 986 switch (namelen) { 987 case 0: 988 if (*oldlenp == sizeof(uint64_t) * CPUSTATES || oldp == NULL) { 989 node.sysctl_size = sizeof(uint64_t) * CPUSTATES; 990 n = -1; /* SUM */ 991 } 992 else { 993 node.sysctl_size = n * sizeof(uint64_t) * CPUSTATES; 994 n = -2; /* ALL */ 995 } 996 break; 997 case 1: 998 if (name[0] < 0 || name[0] >= n) 999 return (ENOENT); /* ENOSUCHPROCESSOR */ 1000 node.sysctl_size = sizeof(uint64_t) * CPUSTATES; 1001 n = name[0]; 1002 /* 1003 * adjust these so that sysctl_lookup() will be happy 1004 */ 1005 name++; 1006 namelen--; 1007 break; 1008 default: 1009 return (EINVAL); 1010 } 1011 1012 cp_time = kmem_alloc(node.sysctl_size, KM_SLEEP); 1013 node.sysctl_data = cp_time; 1014 memset(cp_time, 0, node.sysctl_size); 1015 1016 for (CPU_INFO_FOREACH(cii, ci)) { 1017 if (n <= 0) { 1018 for (i = 0; i < CPUSTATES; i++) { 1019 cp_time[i] += ci->ci_schedstate.spc_cp_time[i]; 1020 } 1021 } 1022 /* 1023 * if a specific processor was requested and we just 1024 * did it, we're done here 1025 */ 1026 if (n == 0) 1027 break; 1028 /* 1029 * if doing "all", skip to next cp_time set for next processor 1030 */ 1031 if (n == -2) 1032 cp_time += CPUSTATES; 1033 /* 1034 * if we're doing a specific processor, we're one 1035 * processor closer 1036 */ 1037 if (n > 0) 1038 n--; 1039 } 1040 1041 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 1042 kmem_free(node.sysctl_data, node.sysctl_size); 1043 return (error); 1044} 1045 1046#if NPTY > 0 1047/* 1048 * sysctl helper routine for kern.maxptys. Ensures that any new value 1049 * is acceptable to the pty subsystem. 1050 */ 1051static int 1052sysctl_kern_maxptys(SYSCTLFN_ARGS) 1053{ 1054 int pty_maxptys(int, int); /* defined in kern/tty_pty.c */ 1055 int error, xmax; 1056 struct sysctlnode node; 1057 1058 /* get current value of maxptys */ 1059 xmax = pty_maxptys(0, 0); 1060 1061 node = *rnode; 1062 node.sysctl_data = &xmax; 1063 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 1064 if (error || newp == NULL) 1065 return (error); 1066 1067 if (xmax != pty_maxptys(xmax, 1)) 1068 return (EINVAL); 1069 1070 return (0); 1071} 1072#endif /* NPTY > 0 */ 1073 1074/* 1075 * sysctl helper routine to do kern.lwp.* work. 1076 */ 1077static int 1078sysctl_kern_lwp(SYSCTLFN_ARGS) 1079{ 1080 struct kinfo_lwp klwp; 1081 struct proc *p; 1082 struct lwp *l2, *l3; 1083 char *where, *dp; 1084 int pid, elem_size, elem_count; 1085 int buflen, needed, error; 1086 bool gotit; 1087 1088 if (namelen == 1 && name[0] == CTL_QUERY) 1089 return (sysctl_query(SYSCTLFN_CALL(rnode))); 1090 1091 dp = where = oldp; 1092 buflen = where != NULL ? *oldlenp : 0; 1093 error = needed = 0; 1094 1095 if (newp != NULL || namelen != 3) 1096 return (EINVAL); 1097 pid = name[0]; 1098 elem_size = name[1]; 1099 elem_count = name[2]; 1100 1101 sysctl_unlock(); 1102 if (pid == -1) { 1103 mutex_enter(proc_lock); 1104 PROCLIST_FOREACH(p, &allproc) { 1105 /* Grab a hold on the process. */ 1106 if (!rw_tryenter(&p->p_reflock, RW_READER)) { 1107 continue; 1108 } 1109 mutex_exit(proc_lock); 1110 1111 mutex_enter(p->p_lock); 1112 LIST_FOREACH(l2, &p->p_lwps, l_sibling) { 1113 if (buflen >= elem_size && elem_count > 0) { 1114 lwp_lock(l2); 1115 fill_lwp(l2, &klwp); 1116 lwp_unlock(l2); 1117 mutex_exit(p->p_lock); 1118 1119 /* 1120 * Copy out elem_size, but not 1121 * larger than the size of a 1122 * struct kinfo_proc2. 1123 */ 1124 error = dcopyout(l, &klwp, dp, 1125 uimin(sizeof(klwp), elem_size)); 1126 if (error) { 1127 rw_exit(&p->p_reflock); 1128 goto cleanup; 1129 } 1130 mutex_enter(p->p_lock); 1131 LIST_FOREACH(l3, &p->p_lwps, 1132 l_sibling) { 1133 if (l2 == l3) 1134 break; 1135 } 1136 if (l3 == NULL) { 1137 mutex_exit(p->p_lock); 1138 rw_exit(&p->p_reflock); 1139 error = EAGAIN; 1140 goto cleanup; 1141 } 1142 dp += elem_size; 1143 buflen -= elem_size; 1144 elem_count--; 1145 } 1146 needed += elem_size; 1147 } 1148 mutex_exit(p->p_lock); 1149 1150 /* Drop reference to process. */ 1151 mutex_enter(proc_lock); 1152 rw_exit(&p->p_reflock); 1153 } 1154 mutex_exit(proc_lock); 1155 } else { 1156 mutex_enter(proc_lock); 1157 p = proc_find(pid); 1158 if (p == NULL) { 1159 error = ESRCH; 1160 mutex_exit(proc_lock); 1161 goto cleanup; 1162 } 1163 /* Grab a hold on the process. */ 1164 gotit = rw_tryenter(&p->p_reflock, RW_READER); 1165 mutex_exit(proc_lock); 1166 if (!gotit) { 1167 error = ESRCH; 1168 goto cleanup; 1169 } 1170 1171 mutex_enter(p->p_lock); 1172 LIST_FOREACH(l2, &p->p_lwps, l_sibling) { 1173 if (buflen >= elem_size && elem_count > 0) { 1174 lwp_lock(l2); 1175 fill_lwp(l2, &klwp); 1176 lwp_unlock(l2); 1177 mutex_exit(p->p_lock); 1178 /* 1179 * Copy out elem_size, but not larger than 1180 * the size of a struct kinfo_proc2. 1181 */ 1182 error = dcopyout(l, &klwp, dp, 1183 uimin(sizeof(klwp), elem_size)); 1184 if (error) { 1185 rw_exit(&p->p_reflock); 1186 goto cleanup; 1187 } 1188 mutex_enter(p->p_lock); 1189 LIST_FOREACH(l3, &p->p_lwps, l_sibling) { 1190 if (l2 == l3) 1191 break; 1192 } 1193 if (l3 == NULL) { 1194 mutex_exit(p->p_lock); 1195 rw_exit(&p->p_reflock); 1196 error = EAGAIN; 1197 goto cleanup; 1198 } 1199 dp += elem_size; 1200 buflen -= elem_size; 1201 elem_count--; 1202 } 1203 needed += elem_size; 1204 } 1205 mutex_exit(p->p_lock); 1206 1207 /* Drop reference to process. */ 1208 rw_exit(&p->p_reflock); 1209 } 1210 1211 if (where != NULL) { 1212 *oldlenp = dp - where; 1213 if (needed > *oldlenp) { 1214 sysctl_relock(); 1215 return (ENOMEM); 1216 } 1217 } else { 1218 needed += KERN_LWPSLOP; 1219 *oldlenp = needed; 1220 } 1221 error = 0; 1222 cleanup: 1223 sysctl_relock(); 1224 return (error); 1225} 1226 1227/* 1228 * sysctl helper routine for kern.forkfsleep node. Ensures that the 1229 * given value is not too large or two small, and is at least one 1230 * timer tick if not zero. 1231 */ 1232static int 1233sysctl_kern_forkfsleep(SYSCTLFN_ARGS) 1234{ 1235 /* userland sees value in ms, internally is in ticks */ 1236 extern int forkfsleep; /* defined in kern/kern_fork.c */ 1237 int error, timo, lsleep; 1238 struct sysctlnode node; 1239 1240 lsleep = forkfsleep * 1000 / hz; 1241 node = *rnode; 1242 node.sysctl_data = &lsleep; 1243 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 1244 if (error || newp == NULL) 1245 return (error); 1246 1247 /* refuse negative values, and overly 'long time' */ 1248 if (lsleep < 0 || lsleep > MAXSLP * 1000) 1249 return (EINVAL); 1250 1251 timo = mstohz(lsleep); 1252 1253 /* if the interval is >0 ms && <1 tick, use 1 tick */ 1254 if (lsleep != 0 && timo == 0) 1255 forkfsleep = 1; 1256 else 1257 forkfsleep = timo; 1258 1259 return (0); 1260} 1261 1262/* 1263 * sysctl helper routine for kern.root_partition 1264 */ 1265static int 1266sysctl_kern_root_partition(SYSCTLFN_ARGS) 1267{ 1268 int rootpart = DISKPART(rootdev); 1269 struct sysctlnode node = *rnode; 1270 1271 node.sysctl_data = &rootpart; 1272 return (sysctl_lookup(SYSCTLFN_CALL(&node))); 1273} 1274 1275/* 1276 * sysctl helper function for kern.drivers 1277 */ 1278static int 1279sysctl_kern_drivers(SYSCTLFN_ARGS) 1280{ 1281 int error; 1282 size_t buflen; 1283 struct kinfo_drivers kd; 1284 char *start, *where; 1285 const char *dname; 1286 int i; 1287 extern struct devsw_conv *devsw_conv; 1288 extern int max_devsw_convs; 1289 1290 start = where = oldp; 1291 buflen = *oldlenp; 1292 if (where == NULL) { 1293 *oldlenp = max_devsw_convs * sizeof kd; 1294 return 0; 1295 } 1296 1297 /* 1298 * An array of kinfo_drivers structures 1299 */ 1300 error = 0; 1301 sysctl_unlock(); 1302 mutex_enter(&device_lock); 1303 for (i = 0; i < max_devsw_convs; i++) { 1304 dname = devsw_conv[i].d_name; 1305 if (dname == NULL) 1306 continue; 1307 if (buflen < sizeof kd) { 1308 error = ENOMEM; 1309 break; 1310 } 1311 memset(&kd, 0, sizeof(kd)); 1312 kd.d_bmajor = devsw_conv[i].d_bmajor; 1313 kd.d_cmajor = devsw_conv[i].d_cmajor; 1314 strlcpy(kd.d_name, dname, sizeof kd.d_name); 1315 mutex_exit(&device_lock); 1316 error = dcopyout(l, &kd, where, sizeof kd); 1317 mutex_enter(&device_lock); 1318 if (error != 0) 1319 break; 1320 buflen -= sizeof kd; 1321 where += sizeof kd; 1322 } 1323 mutex_exit(&device_lock); 1324 sysctl_relock(); 1325 *oldlenp = where - start; 1326 return error; 1327} 1328 1329static int 1330sysctl_security_setidcore(SYSCTLFN_ARGS) 1331{ 1332 int newsize, error; 1333 struct sysctlnode node; 1334 1335 node = *rnode; 1336 node.sysctl_data = &newsize; 1337 newsize = *(int *)rnode->sysctl_data; 1338 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 1339 if (error || newp == NULL) 1340 return error; 1341 1342 if (kauth_authorize_system(l->l_cred, KAUTH_SYSTEM_SETIDCORE, 1343 0, NULL, NULL, NULL)) 1344 return (EPERM); 1345 1346 *(int *)rnode->sysctl_data = newsize; 1347 1348 return 0; 1349} 1350 1351static int 1352sysctl_security_expose_address(SYSCTLFN_ARGS) 1353{ 1354 int expose_address, error; 1355 struct sysctlnode node; 1356 1357 node = *rnode; 1358 node.sysctl_data = &expose_address; 1359 expose_address = *(int *)rnode->sysctl_data; 1360 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 1361 if (error || newp == NULL) 1362 return error; 1363 1364 if (kauth_authorize_system(l->l_cred, KAUTH_SYSTEM_KERNADDR, 1365 0, NULL, NULL, NULL)) 1366 return (EPERM); 1367 1368 *(int *)rnode->sysctl_data = expose_address; 1369 1370 return 0; 1371} 1372 1373bool 1374get_expose_address(struct proc *p) 1375{ 1376 /* allow only if sysctl variable is set or privileged */ 1377 return kern_expose_address || kauth_authorize_process(kauth_cred_get(), 1378 KAUTH_PROCESS_CANSEE, p, 1379 KAUTH_ARG(KAUTH_REQ_PROCESS_CANSEE_KPTR), NULL, NULL) == 0; 1380} 1381 1382static int 1383sysctl_security_setidcorename(SYSCTLFN_ARGS) 1384{ 1385 int error; 1386 char *newsetidcorename; 1387 struct sysctlnode node; 1388 1389 newsetidcorename = PNBUF_GET(); 1390 node = *rnode; 1391 node.sysctl_data = newsetidcorename; 1392 memcpy(node.sysctl_data, rnode->sysctl_data, MAXPATHLEN); 1393 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 1394 if (error || newp == NULL) { 1395 goto out; 1396 } 1397 if (kauth_authorize_system(l->l_cred, KAUTH_SYSTEM_SETIDCORE, 1398 0, NULL, NULL, NULL)) { 1399 error = EPERM; 1400 goto out; 1401 } 1402 if (strlen(newsetidcorename) == 0) { 1403 error = EINVAL; 1404 goto out; 1405 } 1406 memcpy(rnode->sysctl_data, node.sysctl_data, MAXPATHLEN); 1407out: 1408 PNBUF_PUT(newsetidcorename); 1409 return error; 1410} 1411 1412/* 1413 * sysctl helper routine for kern.cp_id node. Maps cpus to their 1414 * cpuids. 1415 */ 1416static int 1417sysctl_kern_cpid(SYSCTLFN_ARGS) 1418{ 1419 struct sysctlnode node = *rnode; 1420 uint64_t *cp_id = NULL; 1421 int error, n = ncpu; 1422 struct cpu_info *ci; 1423 CPU_INFO_ITERATOR cii; 1424 1425 /* 1426 * Here you may either retrieve a single cpu id or the whole 1427 * set. The size you get back when probing depends on what 1428 * you ask for. 1429 */ 1430 switch (namelen) { 1431 case 0: 1432 node.sysctl_size = n * sizeof(uint64_t); 1433 n = -2; /* ALL */ 1434 break; 1435 case 1: 1436 if (name[0] < 0 || name[0] >= n) 1437 return (ENOENT); /* ENOSUCHPROCESSOR */ 1438 node.sysctl_size = sizeof(uint64_t); 1439 n = name[0]; 1440 /* 1441 * adjust these so that sysctl_lookup() will be happy 1442 */ 1443 name++; 1444 namelen--; 1445 break; 1446 default: 1447 return (EINVAL); 1448 } 1449 1450 cp_id = kmem_alloc(node.sysctl_size, KM_SLEEP); 1451 node.sysctl_data = cp_id; 1452 memset(cp_id, 0, node.sysctl_size); 1453 1454 for (CPU_INFO_FOREACH(cii, ci)) { 1455 if (n <= 0) 1456 cp_id[0] = cpu_index(ci); 1457 /* 1458 * if a specific processor was requested and we just 1459 * did it, we're done here 1460 */ 1461 if (n == 0) 1462 break; 1463 /* 1464 * if doing "all", skip to next cp_id slot for next processor 1465 */ 1466 if (n == -2) 1467 cp_id++; 1468 /* 1469 * if we're doing a specific processor, we're one 1470 * processor closer 1471 */ 1472 if (n > 0) 1473 n--; 1474 } 1475 1476 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 1477 kmem_free(node.sysctl_data, node.sysctl_size); 1478 return (error); 1479} 1480 1481/* 1482 * sysctl helper routine for hw.usermem and hw.usermem64. Values are 1483 * calculate on the fly taking into account integer overflow and the 1484 * current wired count. 1485 */ 1486static int 1487sysctl_hw_usermem(SYSCTLFN_ARGS) 1488{ 1489 u_int ui; 1490 u_quad_t uq; 1491 struct sysctlnode node; 1492 1493 node = *rnode; 1494 switch (rnode->sysctl_num) { 1495 case HW_USERMEM: 1496 if ((ui = physmem - uvmexp.wired) > (UINT_MAX / PAGE_SIZE)) 1497 ui = UINT_MAX; 1498 else 1499 ui *= PAGE_SIZE; 1500 node.sysctl_data = &ui; 1501 break; 1502 case HW_USERMEM64: 1503 uq = (u_quad_t)(physmem - uvmexp.wired) * PAGE_SIZE; 1504 node.sysctl_data = &uq; 1505 break; 1506 default: 1507 return (EINVAL); 1508 } 1509 1510 return (sysctl_lookup(SYSCTLFN_CALL(&node))); 1511} 1512 1513/* 1514 * sysctl helper routine for kern.cnmagic node. Pulls the old value 1515 * out, encoded, and stuffs the new value in for decoding. 1516 */ 1517static int 1518sysctl_hw_cnmagic(SYSCTLFN_ARGS) 1519{ 1520 char magic[CNS_LEN]; 1521 int error; 1522 struct sysctlnode node; 1523 1524 if (oldp) 1525 cn_get_magic(magic, CNS_LEN); 1526 node = *rnode; 1527 node.sysctl_data = &magic[0]; 1528 error = sysctl_lookup(SYSCTLFN_CALL(&node)); 1529 if (error || newp == NULL) 1530 return (error); 1531 1532 return (cn_set_magic(magic)); 1533} 1534 1535/* 1536 * ******************************************************************** 1537 * section 3: public helper routines that are used for more than one 1538 * node 1539 * ******************************************************************** 1540 */ 1541 1542/* 1543 * sysctl helper routine for the kern.root_device node and some ports' 1544 * machdep.root_device nodes. 1545 */ 1546int 1547sysctl_root_device(SYSCTLFN_ARGS) 1548{ 1549 struct sysctlnode node; 1550 1551 node = *rnode; 1552 node.sysctl_data = __UNCONST(device_xname(root_device)); 1553 node.sysctl_size = strlen(device_xname(root_device)) + 1; 1554 return (sysctl_lookup(SYSCTLFN_CALL(&node))); 1555} 1556 1557/* 1558 * sysctl helper routine for kern.consdev, dependent on the current 1559 * state of the console. Also used for machdep.console_device on some 1560 * ports. 1561 */ 1562int 1563sysctl_consdev(SYSCTLFN_ARGS) 1564{ 1565 dev_t consdev; 1566 uint32_t oconsdev; 1567 struct sysctlnode node; 1568 1569 if (cn_tab != NULL) 1570 consdev = cn_tab->cn_dev; 1571 else 1572 consdev = NODEV; 1573 node = *rnode; 1574 switch (*oldlenp) { 1575 case sizeof(consdev): 1576 node.sysctl_data = &consdev; 1577 node.sysctl_size = sizeof(consdev); 1578 break; 1579 case sizeof(oconsdev): 1580 oconsdev = (uint32_t)consdev; 1581 node.sysctl_data = &oconsdev; 1582 node.sysctl_size = sizeof(oconsdev); 1583 break; 1584 default: 1585 return EINVAL; 1586 } 1587 return (sysctl_lookup(SYSCTLFN_CALL(&node))); 1588} 1589 1590/* 1591 * ******************************************************************** 1592 * section 4: support for some helpers 1593 * ******************************************************************** 1594 */ 1595 1596 1597/* 1598 * Fill in a kinfo_lwp structure for the specified lwp. 1599 */ 1600static void 1601fill_lwp(struct lwp *l, struct kinfo_lwp *kl) 1602{ 1603 const bool allowaddr = get_expose_address(curproc); 1604 struct proc *p = l->l_proc; 1605 struct timeval tv; 1606 1607 KASSERT(lwp_locked(l, NULL)); 1608 1609 memset(kl, 0, sizeof(*kl)); 1610 1611 kl->l_forw = 0; 1612 kl->l_back = 0; 1613 COND_SET_VALUE(kl->l_laddr, PTRTOUINT64(l), allowaddr); 1614 COND_SET_VALUE(kl->l_addr, PTRTOUINT64(l->l_addr), allowaddr); 1615 kl->l_stat = l->l_stat; 1616 kl->l_lid = l->l_lid; 1617 kl->l_flag = L_INMEM; 1618 kl->l_flag |= sysctl_map_flags(sysctl_lwpprflagmap, l->l_prflag); 1619 kl->l_flag |= sysctl_map_flags(sysctl_lwpflagmap, l->l_flag); 1620 1621 kl->l_swtime = l->l_swtime; 1622 kl->l_slptime = l->l_slptime; 1623 if (l->l_stat == LSONPROC) 1624 kl->l_schedflags = l->l_cpu->ci_schedstate.spc_flags; 1625 else 1626 kl->l_schedflags = 0; 1627 kl->l_priority = lwp_eprio(l); 1628 kl->l_usrpri = l->l_priority; 1629 if (l->l_wchan) 1630 strncpy(kl->l_wmesg, l->l_wmesg, sizeof(kl->l_wmesg)); 1631 COND_SET_VALUE(kl->l_wchan, PTRTOUINT64(l->l_wchan), allowaddr); 1632 kl->l_cpuid = cpu_index(l->l_cpu); 1633 bintime2timeval(&l->l_rtime, &tv); 1634 kl->l_rtime_sec = tv.tv_sec; 1635 kl->l_rtime_usec = tv.tv_usec; 1636 kl->l_cpticks = l->l_cpticks; 1637 kl->l_pctcpu = l->l_pctcpu; 1638 kl->l_pid = p->p_pid; 1639 if (l->l_name == NULL) 1640 kl->l_name[0] = '\0'; 1641 else 1642 strlcpy(kl->l_name, l->l_name, sizeof(kl->l_name)); 1643} 1644