1 /* 2 * CDDL HEADER START 3 * 4 * The contents of this file are subject to the terms of the 5 * Common Development and Distribution License (the "License"). 6 * You may not use this file except in compliance with the License. 7 * 8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 9 * or http://www.opensolaris.org/os/licensing. 10 * See the License for the specific language governing permissions 11 * and limitations under the License. 12 * 13 * When distributing Covered Code, include this CDDL HEADER in each 14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15 * If applicable, add the following below this CDDL HEADER, with the 16 * fields enclosed by brackets "[]" replaced with your own identifying 17 * information: Portions Copyright [yyyy] [name of copyright owner] 18 * 19 * CDDL HEADER END 20 */ 21 22 /* 23 * Copyright (c) 1989, 2010, Oracle and/or its affiliates. All rights reserved. 24 * Copyright (c) 2018, Joyent, Inc. 25 * Copyright (c) 2017 by Delphix. All rights reserved. 26 * Copyright 2020 OmniOS Community Edition (OmniOSce) Association. 27 * Copyright 2022 MNX Cloud, Inc. 28 * Copyright 2023 Oxide Computer Company 29 */ 30 31 /* Copyright (c) 1984, 1986, 1987, 1988, 1989 AT&T */ 32 /* All Rights Reserved */ 33 34 #include <sys/types.h> 35 #include <sys/param.h> 36 #include <sys/time.h> 37 #include <sys/cred.h> 38 #include <sys/policy.h> 39 #include <sys/debug.h> 40 #include <sys/dirent.h> 41 #include <sys/errno.h> 42 #include <sys/file.h> 43 #include <sys/inline.h> 44 #include <sys/kmem.h> 45 #include <sys/pathname.h> 46 #include <sys/proc.h> 47 #include <sys/brand.h> 48 #include <sys/signal.h> 49 #include <sys/stat.h> 50 #include <sys/sysmacros.h> 51 #include <sys/systm.h> 52 #include <sys/zone.h> 53 #include <sys/uio.h> 54 #include <sys/var.h> 55 #include <sys/mode.h> 56 #include <sys/poll.h> 57 #include <sys/user.h> 58 #include <sys/vfs.h> 59 #include <sys/vfs_opreg.h> 60 #include <sys/gfs.h> 61 #include <sys/vnode.h> 62 #include <sys/fault.h> 63 #include <sys/syscall.h> 64 #include <sys/procfs.h> 65 #include <sys/atomic.h> 66 #include <sys/cmn_err.h> 67 #include <sys/contract_impl.h> 68 #include <sys/ctfs.h> 69 #include <sys/avl.h> 70 #include <sys/ctype.h> 71 #include <fs/fs_subr.h> 72 #include <vm/rm.h> 73 #include <vm/as.h> 74 #include <vm/seg.h> 75 #include <vm/seg_vn.h> 76 #include <vm/hat.h> 77 #include <fs/proc/prdata.h> 78 #if defined(__sparc) 79 #include <sys/regset.h> 80 #endif 81 #if defined(__x86) 82 #include <sys/sysi86.h> 83 #endif 84 85 /* 86 * Created by prinit. 87 */ 88 vnodeops_t *prvnodeops; 89 90 /* 91 * Directory characteristics (patterned after the s5 file system). 92 */ 93 #define PRROOTINO 2 94 95 #define PRDIRSIZE 14 96 struct prdirect { 97 ushort_t d_ino; 98 char d_name[PRDIRSIZE]; 99 }; 100 101 #define PRSDSIZE (sizeof (struct prdirect)) 102 103 /* 104 * Directory characteristics. 105 */ 106 typedef struct prdirent { 107 ino64_t d_ino; /* "inode number" of entry */ 108 off64_t d_off; /* offset of disk directory entry */ 109 unsigned short d_reclen; /* length of this record */ 110 char d_name[14]; /* name of file */ 111 } prdirent_t; 112 113 /* 114 * Contents of a /proc/<pid> directory. 115 * Reuse d_ino field for the /proc file type. 116 */ 117 static prdirent_t piddir[] = { 118 { PR_PIDDIR, 1 * sizeof (prdirent_t), sizeof (prdirent_t), 119 "." }, 120 { PR_PROCDIR, 2 * sizeof (prdirent_t), sizeof (prdirent_t), 121 ".." }, 122 { PR_AS, 3 * sizeof (prdirent_t), sizeof (prdirent_t), 123 "as" }, 124 { PR_CTL, 4 * sizeof (prdirent_t), sizeof (prdirent_t), 125 "ctl" }, 126 { PR_STATUS, 5 * sizeof (prdirent_t), sizeof (prdirent_t), 127 "status" }, 128 { PR_LSTATUS, 6 * sizeof (prdirent_t), sizeof (prdirent_t), 129 "lstatus" }, 130 { PR_PSINFO, 7 * sizeof (prdirent_t), sizeof (prdirent_t), 131 "psinfo" }, 132 { PR_LPSINFO, 8 * sizeof (prdirent_t), sizeof (prdirent_t), 133 "lpsinfo" }, 134 { PR_MAP, 9 * sizeof (prdirent_t), sizeof (prdirent_t), 135 "map" }, 136 { PR_RMAP, 10 * sizeof (prdirent_t), sizeof (prdirent_t), 137 "rmap" }, 138 { PR_XMAP, 11 * sizeof (prdirent_t), sizeof (prdirent_t), 139 "xmap" }, 140 { PR_CRED, 12 * sizeof (prdirent_t), sizeof (prdirent_t), 141 "cred" }, 142 { PR_SIGACT, 13 * sizeof (prdirent_t), sizeof (prdirent_t), 143 "sigact" }, 144 { PR_AUXV, 14 * sizeof (prdirent_t), sizeof (prdirent_t), 145 "auxv" }, 146 { PR_USAGE, 15 * sizeof (prdirent_t), sizeof (prdirent_t), 147 "usage" }, 148 { PR_LUSAGE, 16 * sizeof (prdirent_t), sizeof (prdirent_t), 149 "lusage" }, 150 { PR_PAGEDATA, 17 * sizeof (prdirent_t), sizeof (prdirent_t), 151 "pagedata" }, 152 { PR_WATCH, 18 * sizeof (prdirent_t), sizeof (prdirent_t), 153 "watch" }, 154 { PR_CURDIR, 19 * sizeof (prdirent_t), sizeof (prdirent_t), 155 "cwd" }, 156 { PR_ROOTDIR, 20 * sizeof (prdirent_t), sizeof (prdirent_t), 157 "root" }, 158 { PR_FDDIR, 21 * sizeof (prdirent_t), sizeof (prdirent_t), 159 "fd" }, 160 { PR_FDINFODIR, 22 * sizeof (prdirent_t), sizeof (prdirent_t), 161 "fdinfo" }, 162 { PR_OBJECTDIR, 23 * sizeof (prdirent_t), sizeof (prdirent_t), 163 "object" }, 164 { PR_LWPDIR, 24 * sizeof (prdirent_t), sizeof (prdirent_t), 165 "lwp" }, 166 { PR_PRIV, 25 * sizeof (prdirent_t), sizeof (prdirent_t), 167 "priv" }, 168 { PR_PATHDIR, 26 * sizeof (prdirent_t), sizeof (prdirent_t), 169 "path" }, 170 { PR_CTDIR, 27 * sizeof (prdirent_t), sizeof (prdirent_t), 171 "contracts" }, 172 { PR_SECFLAGS, 28 * sizeof (prdirent_t), sizeof (prdirent_t), 173 "secflags" }, 174 #if defined(__x86) 175 { PR_LDT, 29 * sizeof (prdirent_t), sizeof (prdirent_t), 176 "ldt" }, 177 #endif 178 }; 179 180 #define NPIDDIRFILES (sizeof (piddir) / sizeof (piddir[0]) - 2) 181 182 /* 183 * Contents of a /proc/<pid>/lwp/<lwpid> directory. 184 */ 185 static prdirent_t lwpiddir[] = { 186 { PR_LWPIDDIR, 1 * sizeof (prdirent_t), sizeof (prdirent_t), 187 "." }, 188 { PR_LWPDIR, 2 * sizeof (prdirent_t), sizeof (prdirent_t), 189 ".." }, 190 { PR_LWPCTL, 3 * sizeof (prdirent_t), sizeof (prdirent_t), 191 "lwpctl" }, 192 { PR_LWPNAME, 4 * sizeof (prdirent_t), sizeof (prdirent_t), 193 "lwpname" }, 194 { PR_LWPSTATUS, 5 * sizeof (prdirent_t), sizeof (prdirent_t), 195 "lwpstatus" }, 196 { PR_LWPSINFO, 6 * sizeof (prdirent_t), sizeof (prdirent_t), 197 "lwpsinfo" }, 198 { PR_LWPUSAGE, 7 * sizeof (prdirent_t), sizeof (prdirent_t), 199 "lwpusage" }, 200 { PR_XREGS, 8 * sizeof (prdirent_t), sizeof (prdirent_t), 201 "xregs" }, 202 { PR_TMPLDIR, 9 * sizeof (prdirent_t), sizeof (prdirent_t), 203 "templates" }, 204 { PR_SPYMASTER, 10 * sizeof (prdirent_t), sizeof (prdirent_t), 205 "spymaster" }, 206 #if defined(__sparc) 207 { PR_GWINDOWS, 11 * sizeof (prdirent_t), sizeof (prdirent_t), 208 "gwindows" }, 209 { PR_ASRS, 12 * sizeof (prdirent_t), sizeof (prdirent_t), 210 "asrs" }, 211 #endif 212 }; 213 214 #define NLWPIDDIRFILES (sizeof (lwpiddir) / sizeof (lwpiddir[0]) - 2) 215 216 /* 217 * Span of entries in the array files (lstatus, lpsinfo, lusage). 218 * We make the span larger than the size of the structure on purpose, 219 * to make sure that programs cannot use the structure size by mistake. 220 * Align _ILP32 structures at 8 bytes, _LP64 structures at 16 bytes. 221 */ 222 #ifdef _LP64 223 #define LSPAN(type) (round16(sizeof (type)) + 16) 224 #define LSPAN32(type) (round8(sizeof (type)) + 8) 225 #else 226 #define LSPAN(type) (round8(sizeof (type)) + 8) 227 #endif 228 229 static void rebuild_objdir(struct as *); 230 static void prfreecommon(prcommon_t *); 231 static int praccess(vnode_t *, int, int, cred_t *, caller_context_t *); 232 233 static int 234 propen(vnode_t **vpp, int flag, cred_t *cr, caller_context_t *ct) 235 { 236 vnode_t *vp = *vpp; 237 prnode_t *pnp = VTOP(vp); 238 prcommon_t *pcp = pnp->pr_pcommon; 239 prnodetype_t type = pnp->pr_type; 240 vnode_t *rvp; 241 vtype_t vtype; 242 proc_t *p; 243 int error = 0; 244 prnode_t *npnp = NULL; 245 246 /* 247 * Nothing to do for the /proc directory itself. 248 */ 249 if (type == PR_PROCDIR) 250 return (0); 251 252 /* 253 * If we are opening an underlying mapped object, reject opens 254 * for writing regardless of the objects's access modes. 255 * If we are opening a file in the /proc/pid/fd directory, 256 * reject the open for any but a regular file or directory. 257 * Just do it if we are opening the current or root directory. 258 */ 259 switch (type) { 260 case PR_OBJECT: 261 case PR_FD: 262 case PR_CURDIR: 263 case PR_ROOTDIR: 264 rvp = pnp->pr_realvp; 265 vtype = rvp->v_type; 266 if ((type == PR_OBJECT && (flag & FWRITE)) || 267 (type == PR_FD && vtype != VREG && vtype != VDIR)) 268 error = EACCES; 269 else { 270 /* 271 * Need to hold rvp since VOP_OPEN() may release it. 272 */ 273 VN_HOLD(rvp); 274 error = VOP_OPEN(&rvp, flag, cr, ct); 275 if (error) { 276 VN_RELE(rvp); 277 } else { 278 *vpp = rvp; 279 VN_RELE(vp); 280 } 281 } 282 return (error); 283 default: 284 break; 285 } 286 287 /* 288 * If we are opening the pagedata file, allocate a prnode now 289 * to avoid calling kmem_alloc() while holding p->p_lock. 290 */ 291 if (type == PR_PAGEDATA || type == PR_OPAGEDATA) 292 npnp = prgetnode(vp, type); 293 294 /* 295 * If the process exists, lock it now. 296 * Otherwise we have a race condition with prclose(). 297 */ 298 p = pr_p_lock(pnp); 299 mutex_exit(&pr_pidlock); 300 if (p == NULL) { 301 if (npnp != NULL) 302 prfreenode(npnp); 303 return (ENOENT); 304 } 305 ASSERT(p == pcp->prc_proc); 306 ASSERT(p->p_proc_flag & P_PR_LOCK); 307 308 /* 309 * Maintain a count of opens for write. Allow exactly one 310 * O_WRITE|O_EXCL request and fail subsequent ones. 311 * Don't fail opens of old (bletch!) /proc lwp files. 312 * Special case for open by the process itself: 313 * Always allow the open by self and discount this 314 * open for other opens for writing. 315 */ 316 if (flag & FWRITE) { 317 if (p == curproc) { 318 pcp->prc_selfopens++; 319 pnp->pr_flags |= PR_ISSELF; 320 } else if (type == PR_LWPIDFILE) { 321 /* EMPTY */; 322 } else if (flag & FEXCL) { 323 if (pcp->prc_writers > pcp->prc_selfopens) { 324 error = EBUSY; 325 goto out; 326 } 327 /* semantic for old /proc interface */ 328 if (type == PR_PIDDIR) 329 pcp->prc_flags |= PRC_EXCL; 330 } else if (pcp->prc_flags & PRC_EXCL) { 331 ASSERT(pcp->prc_writers > pcp->prc_selfopens); 332 error = secpolicy_proc_excl_open(cr); 333 if (error) 334 goto out; 335 } 336 pcp->prc_writers++; 337 /* 338 * The vnode may have become invalid between the 339 * VOP_LOOKUP() of the /proc vnode and the VOP_OPEN(). 340 * If so, do now what prinvalidate() should have done. 341 */ 342 if ((pnp->pr_flags & PR_INVAL) || 343 (type == PR_PIDDIR && 344 (VTOP(pnp->pr_pidfile)->pr_flags & PR_INVAL))) { 345 if (p != curproc) 346 pcp->prc_selfopens++; 347 ASSERT(pcp->prc_selfopens <= pcp->prc_writers); 348 if (pcp->prc_selfopens == pcp->prc_writers) 349 pcp->prc_flags &= ~PRC_EXCL; 350 } 351 } 352 353 /* 354 * If this is a large file open, indicate that in our flags -- some 355 * procfs structures are not off_t-neutral (e.g., priovec_t), and 356 * the open will need to be differentiated where 32-bit processes 357 * pass these structures across the user/kernel boundary. 358 */ 359 if (flag & FOFFMAX) 360 pnp->pr_flags |= PR_OFFMAX; 361 362 /* 363 * Do file-specific things. 364 */ 365 switch (type) { 366 default: 367 break; 368 case PR_PAGEDATA: 369 case PR_OPAGEDATA: 370 /* 371 * Enable data collection for page data file; 372 * get unique id from the hat layer. 373 */ 374 { 375 int id; 376 377 /* 378 * Drop p->p_lock to call hat_startstat() 379 */ 380 mutex_exit(&p->p_lock); 381 if ((p->p_flag & SSYS) || p->p_as == &kas || 382 (id = hat_startstat(p->p_as)) == -1) { 383 mutex_enter(&p->p_lock); 384 error = ENOMEM; 385 } else if (pnp->pr_hatid == 0) { 386 mutex_enter(&p->p_lock); 387 pnp->pr_hatid = (uint_t)id; 388 } else { 389 mutex_enter(&p->p_lock); 390 /* 391 * Use our newly allocated prnode. 392 */ 393 npnp->pr_hatid = (uint_t)id; 394 /* 395 * prgetnode() initialized most of the prnode. 396 * Duplicate the remainder. 397 */ 398 npnp->pr_ino = pnp->pr_ino; 399 npnp->pr_common = pnp->pr_common; 400 npnp->pr_pcommon = pnp->pr_pcommon; 401 npnp->pr_parent = pnp->pr_parent; 402 VN_HOLD(npnp->pr_parent); 403 npnp->pr_index = pnp->pr_index; 404 405 npnp->pr_next = p->p_plist; 406 p->p_plist = PTOV(npnp); 407 408 VN_RELE(PTOV(pnp)); 409 pnp = npnp; 410 npnp = NULL; 411 *vpp = PTOV(pnp); 412 } 413 } 414 break; 415 } 416 417 out: 418 prunlock(pnp); 419 420 if (npnp != NULL) 421 prfreenode(npnp); 422 return (error); 423 } 424 425 /* ARGSUSED */ 426 static int 427 prclose(vnode_t *vp, int flag, int count, offset_t offset, cred_t *cr, 428 caller_context_t *ct) 429 { 430 prnode_t *pnp = VTOP(vp); 431 prcommon_t *pcp = pnp->pr_pcommon; 432 prnodetype_t type = pnp->pr_type; 433 proc_t *p; 434 kthread_t *t; 435 user_t *up; 436 437 /* 438 * Nothing to do for the /proc directory itself. 439 */ 440 if (type == PR_PROCDIR) 441 return (0); 442 443 ASSERT(type != PR_OBJECT && type != PR_FD && 444 type != PR_CURDIR && type != PR_ROOTDIR); 445 446 /* 447 * If the process exists, lock it now. 448 * Otherwise we have a race condition with propen(). 449 * Hold pr_pidlock across the reference to prc_selfopens, 450 * and prc_writers in case there is no process anymore, 451 * to cover the case of concurrent calls to prclose() 452 * after the process has been reaped by freeproc(). 453 */ 454 p = pr_p_lock(pnp); 455 456 /* 457 * There is nothing more to do until the last close of 458 * the file table entry except to clear the pr_owner 459 * field of the prnode and notify any waiters 460 * (their file descriptor may have just been closed). 461 */ 462 if (count > 1) { 463 mutex_exit(&pr_pidlock); 464 if (pnp->pr_owner == curproc && !fisopen(vp)) 465 pnp->pr_owner = NULL; 466 if (p != NULL) { 467 prnotify(vp); 468 prunlock(pnp); 469 } 470 return (0); 471 } 472 473 /* 474 * Decrement the count of self-opens for writing. 475 * Decrement the total count of opens for writing. 476 * Cancel exclusive opens when only self-opens remain. 477 */ 478 if (flag & FWRITE) { 479 /* 480 * prc_selfopens also contains the count of 481 * invalid writers. See prinvalidate(). 482 */ 483 if ((pnp->pr_flags & (PR_ISSELF|PR_INVAL)) || 484 (type == PR_PIDDIR && 485 (VTOP(pnp->pr_pidfile)->pr_flags & PR_INVAL))) { 486 ASSERT(pcp->prc_selfopens != 0); 487 --pcp->prc_selfopens; 488 } 489 ASSERT(pcp->prc_writers != 0); 490 if (--pcp->prc_writers == pcp->prc_selfopens) 491 pcp->prc_flags &= ~PRC_EXCL; 492 } 493 ASSERT(pcp->prc_writers >= pcp->prc_selfopens); 494 mutex_exit(&pr_pidlock); 495 if (pnp->pr_owner == curproc && !fisopen(vp)) 496 pnp->pr_owner = NULL; 497 498 /* 499 * If there is no process, there is nothing more to do. 500 */ 501 if (p == NULL) 502 return (0); 503 504 ASSERT(p == pcp->prc_proc); 505 prnotify(vp); /* notify waiters */ 506 507 /* 508 * Do file-specific things. 509 */ 510 switch (type) { 511 default: 512 break; 513 case PR_PAGEDATA: 514 case PR_OPAGEDATA: 515 /* 516 * This is a page data file. 517 * Free the hat level statistics. 518 * Drop p->p_lock before calling hat_freestat(). 519 */ 520 mutex_exit(&p->p_lock); 521 if (p->p_as != &kas && pnp->pr_hatid != 0) 522 hat_freestat(p->p_as, pnp->pr_hatid); 523 mutex_enter(&p->p_lock); 524 pnp->pr_hatid = 0; 525 break; 526 } 527 528 /* 529 * On last close of all writable file descriptors, 530 * perform run-on-last-close and/or kill-on-last-close logic. 531 * Can't do this is the /proc agent lwp still exists. 532 */ 533 if (pcp->prc_writers == 0 && 534 p->p_agenttp == NULL && 535 !(pcp->prc_flags & PRC_DESTROY) && 536 p->p_stat != SZOMB && 537 (p->p_proc_flag & (P_PR_RUNLCL|P_PR_KILLCL))) { 538 int killproc; 539 540 /* 541 * Cancel any watchpoints currently in effect. 542 * The process might disappear during this operation. 543 */ 544 if (pr_cancel_watch(pnp) == NULL) 545 return (0); 546 /* 547 * If any tracing flags are set, clear them. 548 */ 549 if (p->p_proc_flag & P_PR_TRACE) { 550 up = PTOU(p); 551 premptyset(&up->u_entrymask); 552 premptyset(&up->u_exitmask); 553 up->u_systrap = 0; 554 } 555 premptyset(&p->p_sigmask); 556 premptyset(&p->p_fltmask); 557 killproc = (p->p_proc_flag & P_PR_KILLCL); 558 p->p_proc_flag &= ~(P_PR_RUNLCL|P_PR_KILLCL|P_PR_TRACE); 559 /* 560 * Cancel any outstanding single-step requests. 561 */ 562 if ((t = p->p_tlist) != NULL) { 563 /* 564 * Drop p_lock because prnostep() touches the stack. 565 * The loop is safe because the process is P_PR_LOCK'd. 566 */ 567 mutex_exit(&p->p_lock); 568 do { 569 prnostep(ttolwp(t)); 570 } while ((t = t->t_forw) != p->p_tlist); 571 mutex_enter(&p->p_lock); 572 } 573 /* 574 * Set runnable all lwps stopped by /proc. 575 */ 576 if (killproc) 577 sigtoproc(p, NULL, SIGKILL); 578 else 579 allsetrun(p); 580 } 581 582 prunlock(pnp); 583 return (0); 584 } 585 586 /* 587 * Array of read functions, indexed by /proc file type. 588 */ 589 static int pr_read_inval(), pr_read_as(), pr_read_status(), 590 pr_read_lstatus(), pr_read_psinfo(), pr_read_lpsinfo(), 591 pr_read_map(), pr_read_rmap(), pr_read_xmap(), 592 pr_read_cred(), pr_read_sigact(), pr_read_auxv(), 593 #if defined(__x86) 594 pr_read_ldt(), 595 #endif 596 pr_read_usage(), pr_read_lusage(), pr_read_pagedata(), 597 pr_read_watch(), pr_read_lwpstatus(), pr_read_lwpsinfo(), 598 pr_read_lwpusage(), pr_read_lwpname(), 599 pr_read_xregs(), pr_read_priv(), 600 pr_read_spymaster(), pr_read_secflags(), 601 #if defined(__sparc) 602 pr_read_gwindows(), pr_read_asrs(), 603 #endif 604 pr_read_piddir(), pr_read_pidfile(), pr_read_opagedata(), 605 pr_read_fdinfo(); 606 607 static int (*pr_read_function[PR_NFILES])() = { 608 pr_read_inval, /* /proc */ 609 pr_read_inval, /* /proc/self */ 610 pr_read_piddir, /* /proc/<pid> (old /proc read()) */ 611 pr_read_as, /* /proc/<pid>/as */ 612 pr_read_inval, /* /proc/<pid>/ctl */ 613 pr_read_status, /* /proc/<pid>/status */ 614 pr_read_lstatus, /* /proc/<pid>/lstatus */ 615 pr_read_psinfo, /* /proc/<pid>/psinfo */ 616 pr_read_lpsinfo, /* /proc/<pid>/lpsinfo */ 617 pr_read_map, /* /proc/<pid>/map */ 618 pr_read_rmap, /* /proc/<pid>/rmap */ 619 pr_read_xmap, /* /proc/<pid>/xmap */ 620 pr_read_cred, /* /proc/<pid>/cred */ 621 pr_read_sigact, /* /proc/<pid>/sigact */ 622 pr_read_auxv, /* /proc/<pid>/auxv */ 623 #if defined(__x86) 624 pr_read_ldt, /* /proc/<pid>/ldt */ 625 #endif 626 pr_read_usage, /* /proc/<pid>/usage */ 627 pr_read_lusage, /* /proc/<pid>/lusage */ 628 pr_read_pagedata, /* /proc/<pid>/pagedata */ 629 pr_read_watch, /* /proc/<pid>/watch */ 630 pr_read_inval, /* /proc/<pid>/cwd */ 631 pr_read_inval, /* /proc/<pid>/root */ 632 pr_read_inval, /* /proc/<pid>/fd */ 633 pr_read_inval, /* /proc/<pid>/fd/nn */ 634 pr_read_inval, /* /proc/<pid>/fdinfo */ 635 pr_read_fdinfo, /* /proc/<pid>/fdinfo/nn */ 636 pr_read_inval, /* /proc/<pid>/object */ 637 pr_read_inval, /* /proc/<pid>/object/xxx */ 638 pr_read_inval, /* /proc/<pid>/lwp */ 639 pr_read_inval, /* /proc/<pid>/lwp/<lwpid> */ 640 pr_read_inval, /* /proc/<pid>/lwp/<lwpid>/lwpctl */ 641 pr_read_lwpname, /* /proc/<pid>/lwp/<lwpid>/lwpname */ 642 pr_read_lwpstatus, /* /proc/<pid>/lwp/<lwpid>/lwpstatus */ 643 pr_read_lwpsinfo, /* /proc/<pid>/lwp/<lwpid>/lwpsinfo */ 644 pr_read_lwpusage, /* /proc/<pid>/lwp/<lwpid>/lwpusage */ 645 pr_read_xregs, /* /proc/<pid>/lwp/<lwpid>/xregs */ 646 pr_read_inval, /* /proc/<pid>/lwp/<lwpid>/templates */ 647 pr_read_inval, /* /proc/<pid>/lwp/<lwpid>/templates/<id> */ 648 pr_read_spymaster, /* /proc/<pid>/lwp/<lwpid>/spymaster */ 649 #if defined(__sparc) 650 pr_read_gwindows, /* /proc/<pid>/lwp/<lwpid>/gwindows */ 651 pr_read_asrs, /* /proc/<pid>/lwp/<lwpid>/asrs */ 652 #endif 653 pr_read_priv, /* /proc/<pid>/priv */ 654 pr_read_inval, /* /proc/<pid>/path */ 655 pr_read_inval, /* /proc/<pid>/path/xxx */ 656 pr_read_inval, /* /proc/<pid>/contracts */ 657 pr_read_inval, /* /proc/<pid>/contracts/<ctid> */ 658 pr_read_secflags, /* /proc/<pid>/secflags */ 659 pr_read_pidfile, /* old process file */ 660 pr_read_pidfile, /* old lwp file */ 661 pr_read_opagedata, /* old pagedata file */ 662 }; 663 664 /* ARGSUSED */ 665 static int 666 pr_read_inval(prnode_t *pnp, uio_t *uiop, cred_t *cr) 667 { 668 /* 669 * No read() on any /proc directory, use getdents(2) instead. 670 * Cannot read a control file either. 671 * An underlying mapped object file cannot get here. 672 */ 673 return (EINVAL); 674 } 675 676 static int 677 pr_uioread(void *base, long count, uio_t *uiop) 678 { 679 int error = 0; 680 681 ASSERT(count >= 0); 682 count -= uiop->uio_offset; 683 if (count > 0 && uiop->uio_offset >= 0) { 684 error = uiomove((char *)base + uiop->uio_offset, 685 count, UIO_READ, uiop); 686 } 687 688 return (error); 689 } 690 691 static int 692 pr_read_as(prnode_t *pnp, uio_t *uiop) 693 { 694 int error; 695 696 ASSERT(pnp->pr_type == PR_AS); 697 698 if ((error = prlock(pnp, ZNO)) == 0) { 699 proc_t *p = pnp->pr_common->prc_proc; 700 struct as *as = p->p_as; 701 702 /* 703 * /proc I/O cannot be done to a system process. 704 * A 32-bit process cannot read a 64-bit process. 705 */ 706 if ((p->p_flag & SSYS) || as == &kas) { 707 error = 0; 708 #ifdef _SYSCALL32_IMPL 709 } else if (curproc->p_model == DATAMODEL_ILP32 && 710 PROCESS_NOT_32BIT(p)) { 711 error = EOVERFLOW; 712 #endif 713 } else { 714 /* 715 * We don't hold p_lock over an i/o operation because 716 * that could lead to deadlock with the clock thread. 717 */ 718 mutex_exit(&p->p_lock); 719 error = prusrio(p, UIO_READ, uiop, 0); 720 mutex_enter(&p->p_lock); 721 } 722 prunlock(pnp); 723 } 724 725 return (error); 726 } 727 728 static int 729 pr_read_status(prnode_t *pnp, uio_t *uiop, cred_t *cr) 730 { 731 pstatus_t *sp; 732 int error; 733 734 ASSERT(pnp->pr_type == PR_STATUS); 735 736 /* 737 * We kmem_alloc() the pstatus structure because 738 * it is so big it might blow the kernel stack. 739 */ 740 sp = kmem_alloc(sizeof (*sp), KM_SLEEP); 741 if ((error = prlock(pnp, ZNO)) == 0) { 742 prgetstatus(pnp->pr_common->prc_proc, sp, VTOZONE(PTOV(pnp))); 743 prunlock(pnp); 744 error = pr_uioread(sp, sizeof (*sp), uiop); 745 } 746 kmem_free(sp, sizeof (*sp)); 747 return (error); 748 } 749 750 static int 751 pr_read_lstatus(prnode_t *pnp, uio_t *uiop, cred_t *cr) 752 { 753 proc_t *p; 754 kthread_t *t; 755 lwpdir_t *ldp; 756 size_t size; 757 prheader_t *php; 758 lwpstatus_t *sp; 759 int error; 760 int nlwp; 761 int i; 762 763 ASSERT(pnp->pr_type == PR_LSTATUS); 764 765 if ((error = prlock(pnp, ZNO)) != 0) 766 return (error); 767 p = pnp->pr_common->prc_proc; 768 nlwp = p->p_lwpcnt; 769 size = sizeof (prheader_t) + nlwp * LSPAN(lwpstatus_t); 770 771 /* drop p->p_lock to do kmem_alloc(KM_SLEEP) */ 772 mutex_exit(&p->p_lock); 773 php = kmem_zalloc(size, KM_SLEEP); 774 mutex_enter(&p->p_lock); 775 /* p->p_lwpcnt can't change while process is locked */ 776 ASSERT(nlwp == p->p_lwpcnt); 777 778 php->pr_nent = nlwp; 779 php->pr_entsize = LSPAN(lwpstatus_t); 780 781 sp = (lwpstatus_t *)(php + 1); 782 for (ldp = p->p_lwpdir, i = 0; i < p->p_lwpdir_sz; i++, ldp++) { 783 if (ldp->ld_entry == NULL || 784 (t = ldp->ld_entry->le_thread) == NULL) 785 continue; 786 prgetlwpstatus(t, sp, VTOZONE(PTOV(pnp))); 787 sp = (lwpstatus_t *)((caddr_t)sp + LSPAN(lwpstatus_t)); 788 } 789 prunlock(pnp); 790 791 error = pr_uioread(php, size, uiop); 792 kmem_free(php, size); 793 return (error); 794 } 795 796 static int 797 pr_read_psinfo(prnode_t *pnp, uio_t *uiop, cred_t *cr) 798 { 799 psinfo_t psinfo; 800 proc_t *p; 801 int error = 0; 802 803 ASSERT(pnp->pr_type == PR_PSINFO); 804 805 /* 806 * We don't want the full treatment of prlock(pnp) here. 807 * This file is world-readable and never goes invalid. 808 * It doesn't matter if we are in the middle of an exec(). 809 */ 810 p = pr_p_lock(pnp); 811 mutex_exit(&pr_pidlock); 812 if (p == NULL) 813 error = ENOENT; 814 else { 815 ASSERT(p == pnp->pr_common->prc_proc); 816 prgetpsinfo(p, &psinfo); 817 prunlock(pnp); 818 error = pr_uioread(&psinfo, sizeof (psinfo), uiop); 819 } 820 return (error); 821 } 822 823 static int 824 pr_read_fdinfo(prnode_t *pnp, uio_t *uiop, cred_t *cr) 825 { 826 prfdinfo_t *fdinfo; 827 list_t data; 828 proc_t *p; 829 uint_t fd; 830 file_t *fp; 831 short ufp_flag; 832 int error = 0; 833 834 ASSERT(pnp->pr_type == PR_FDINFO); 835 836 /* 837 * This is a guess at the size of the structure that needs to 838 * be returned. It's a balance between not allocating too much more 839 * space than is required and not requiring too many subsequent 840 * reallocations. Allocate it before acquiring the process lock. 841 */ 842 pr_iol_initlist(&data, sizeof (prfdinfo_t) + MAXPATHLEN + 2, 1); 843 844 if ((error = prlock(pnp, ZNO)) != 0) { 845 pr_iol_freelist(&data); 846 return (error); 847 } 848 849 p = pnp->pr_common->prc_proc; 850 851 if ((p->p_flag & SSYS) || p->p_as == &kas) { 852 prunlock(pnp); 853 pr_iol_freelist(&data); 854 return (0); 855 } 856 857 fd = pnp->pr_index; 858 859 /* Fetch and lock the file_t for this descriptor */ 860 fp = pr_getf(p, fd, &ufp_flag); 861 862 if (fp == NULL) { 863 error = ENOENT; 864 prunlock(pnp); 865 goto out; 866 } 867 868 /* 869 * For fdinfo, we don't want to include the placeholder pr_misc at the 870 * end of the struct. We'll terminate the data with an empty pr_misc 871 * header before returning. 872 */ 873 874 fdinfo = pr_iol_newbuf(&data, offsetof(prfdinfo_t, pr_misc)); 875 fdinfo->pr_fd = fd; 876 fdinfo->pr_fdflags = ufp_flag; 877 fdinfo->pr_fileflags = fp->f_flag2 << 16 | fp->f_flag; 878 if ((fdinfo->pr_fileflags & (FSEARCH | FEXEC)) == 0) 879 fdinfo->pr_fileflags += FOPEN; 880 fdinfo->pr_offset = fp->f_offset; 881 /* 882 * Information from the vnode (rather than the file_t) is retrieved 883 * later, in prgetfdinfo() - for example sock_getfasync() 884 */ 885 886 prunlock(pnp); 887 888 error = prgetfdinfo(p, fp->f_vnode, fdinfo, cr, fp->f_cred, &data); 889 890 pr_releasef(fp); 891 892 out: 893 if (error == 0) 894 error = pr_iol_uiomove_and_free(&data, uiop, error); 895 else 896 pr_iol_freelist(&data); 897 898 return (error); 899 } 900 901 static int 902 pr_read_lpsinfo(prnode_t *pnp, uio_t *uiop, cred_t *cr) 903 { 904 proc_t *p; 905 kthread_t *t; 906 lwpdir_t *ldp; 907 lwpent_t *lep; 908 size_t size; 909 prheader_t *php; 910 lwpsinfo_t *sp; 911 int error; 912 int nlwp; 913 int i; 914 915 ASSERT(pnp->pr_type == PR_LPSINFO); 916 917 /* 918 * We don't want the full treatment of prlock(pnp) here. 919 * This file is world-readable and never goes invalid. 920 * It doesn't matter if we are in the middle of an exec(). 921 */ 922 p = pr_p_lock(pnp); 923 mutex_exit(&pr_pidlock); 924 if (p == NULL) 925 return (ENOENT); 926 ASSERT(p == pnp->pr_common->prc_proc); 927 if ((nlwp = p->p_lwpcnt + p->p_zombcnt) == 0) { 928 prunlock(pnp); 929 return (ENOENT); 930 } 931 size = sizeof (prheader_t) + nlwp * LSPAN(lwpsinfo_t); 932 933 /* drop p->p_lock to do kmem_alloc(KM_SLEEP) */ 934 mutex_exit(&p->p_lock); 935 php = kmem_zalloc(size, KM_SLEEP); 936 mutex_enter(&p->p_lock); 937 /* p->p_lwpcnt can't change while process is locked */ 938 ASSERT(nlwp == p->p_lwpcnt + p->p_zombcnt); 939 940 php->pr_nent = nlwp; 941 php->pr_entsize = LSPAN(lwpsinfo_t); 942 943 sp = (lwpsinfo_t *)(php + 1); 944 for (ldp = p->p_lwpdir, i = 0; i < p->p_lwpdir_sz; i++, ldp++) { 945 if ((lep = ldp->ld_entry) == NULL) 946 continue; 947 if ((t = lep->le_thread) != NULL) 948 prgetlwpsinfo(t, sp); 949 else { 950 bzero(sp, sizeof (*sp)); 951 sp->pr_lwpid = lep->le_lwpid; 952 sp->pr_state = SZOMB; 953 sp->pr_sname = 'Z'; 954 sp->pr_start.tv_sec = lep->le_start; 955 sp->pr_bindpro = PBIND_NONE; 956 sp->pr_bindpset = PS_NONE; 957 } 958 sp = (lwpsinfo_t *)((caddr_t)sp + LSPAN(lwpsinfo_t)); 959 } 960 prunlock(pnp); 961 962 error = pr_uioread(php, size, uiop); 963 kmem_free(php, size); 964 return (error); 965 } 966 967 static int 968 pr_read_map_common(prnode_t *pnp, uio_t *uiop, prnodetype_t type) 969 { 970 proc_t *p; 971 struct as *as; 972 list_t iolhead; 973 int error; 974 975 readmap_common: 976 if ((error = prlock(pnp, ZNO)) != 0) 977 return (error); 978 979 p = pnp->pr_common->prc_proc; 980 as = p->p_as; 981 982 if ((p->p_flag & SSYS) || as == &kas) { 983 prunlock(pnp); 984 return (0); 985 } 986 987 if (!AS_LOCK_TRYENTER(as, RW_WRITER)) { 988 prunlock(pnp); 989 delay(1); 990 goto readmap_common; 991 } 992 mutex_exit(&p->p_lock); 993 994 switch (type) { 995 case PR_XMAP: 996 error = prgetxmap(p, &iolhead); 997 break; 998 case PR_RMAP: 999 error = prgetmap(p, 1, &iolhead); 1000 break; 1001 case PR_MAP: 1002 error = prgetmap(p, 0, &iolhead); 1003 break; 1004 } 1005 1006 AS_LOCK_EXIT(as); 1007 mutex_enter(&p->p_lock); 1008 prunlock(pnp); 1009 1010 error = pr_iol_uiomove_and_free(&iolhead, uiop, error); 1011 1012 return (error); 1013 } 1014 1015 static int 1016 pr_read_map(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1017 { 1018 ASSERT(pnp->pr_type == PR_MAP); 1019 return (pr_read_map_common(pnp, uiop, pnp->pr_type)); 1020 } 1021 1022 static int 1023 pr_read_rmap(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1024 { 1025 ASSERT(pnp->pr_type == PR_RMAP); 1026 return (pr_read_map_common(pnp, uiop, pnp->pr_type)); 1027 } 1028 1029 static int 1030 pr_read_xmap(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1031 { 1032 ASSERT(pnp->pr_type == PR_XMAP); 1033 return (pr_read_map_common(pnp, uiop, pnp->pr_type)); 1034 } 1035 1036 static int 1037 pr_read_cred(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1038 { 1039 proc_t *p; 1040 prcred_t *pcrp; 1041 int error; 1042 size_t count; 1043 1044 ASSERT(pnp->pr_type == PR_CRED); 1045 1046 /* 1047 * We kmem_alloc() the prcred_t structure because 1048 * the number of supplementary groups is variable. 1049 */ 1050 pcrp = 1051 kmem_alloc(sizeof (prcred_t) + sizeof (gid_t) * (ngroups_max - 1), 1052 KM_SLEEP); 1053 1054 if ((error = prlock(pnp, ZNO)) != 0) 1055 goto out; 1056 p = pnp->pr_common->prc_proc; 1057 ASSERT(p != NULL); 1058 1059 prgetcred(p, pcrp); 1060 prunlock(pnp); 1061 1062 count = sizeof (prcred_t); 1063 if (pcrp->pr_ngroups > 1) 1064 count += sizeof (gid_t) * (pcrp->pr_ngroups - 1); 1065 error = pr_uioread(pcrp, count, uiop); 1066 out: 1067 kmem_free(pcrp, sizeof (prcred_t) + sizeof (gid_t) * (ngroups_max - 1)); 1068 return (error); 1069 } 1070 1071 static int 1072 pr_read_priv(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1073 { 1074 proc_t *p; 1075 size_t psize = prgetprivsize(); 1076 prpriv_t *ppriv = kmem_alloc(psize, KM_SLEEP); 1077 int error; 1078 1079 ASSERT(pnp->pr_type == PR_PRIV); 1080 1081 if ((error = prlock(pnp, ZNO)) != 0) 1082 goto out; 1083 p = pnp->pr_common->prc_proc; 1084 ASSERT(p != NULL); 1085 1086 prgetpriv(p, ppriv); 1087 prunlock(pnp); 1088 1089 error = pr_uioread(ppriv, psize, uiop); 1090 out: 1091 kmem_free(ppriv, psize); 1092 return (error); 1093 } 1094 1095 static int 1096 pr_read_sigact(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1097 { 1098 int nsig = PROC_IS_BRANDED(curproc)? BROP(curproc)->b_nsig : NSIG; 1099 proc_t *p; 1100 struct sigaction *sap; 1101 int sig; 1102 int error; 1103 user_t *up; 1104 1105 ASSERT(pnp->pr_type == PR_SIGACT); 1106 1107 /* 1108 * We kmem_alloc() the sigaction array because 1109 * it is so big it might blow the kernel stack. 1110 */ 1111 sap = kmem_alloc((nsig-1) * sizeof (struct sigaction), KM_SLEEP); 1112 1113 if ((error = prlock(pnp, ZNO)) != 0) 1114 goto out; 1115 p = pnp->pr_common->prc_proc; 1116 ASSERT(p != NULL); 1117 1118 if (uiop->uio_offset >= (nsig-1)*sizeof (struct sigaction)) { 1119 prunlock(pnp); 1120 goto out; 1121 } 1122 1123 up = PTOU(p); 1124 for (sig = 1; sig < nsig; sig++) 1125 prgetaction(p, up, sig, &sap[sig-1]); 1126 prunlock(pnp); 1127 1128 error = pr_uioread(sap, (nsig - 1) * sizeof (struct sigaction), uiop); 1129 out: 1130 kmem_free(sap, (nsig-1) * sizeof (struct sigaction)); 1131 return (error); 1132 } 1133 1134 static int 1135 pr_read_auxv(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1136 { 1137 auxv_t auxv[__KERN_NAUXV_IMPL]; 1138 proc_t *p; 1139 user_t *up; 1140 int error; 1141 1142 ASSERT(pnp->pr_type == PR_AUXV); 1143 1144 if ((error = prlock(pnp, ZNO)) != 0) 1145 return (error); 1146 1147 if (uiop->uio_offset >= sizeof (auxv)) { 1148 prunlock(pnp); 1149 return (0); 1150 } 1151 1152 p = pnp->pr_common->prc_proc; 1153 up = PTOU(p); 1154 bcopy(up->u_auxv, auxv, sizeof (auxv)); 1155 prunlock(pnp); 1156 1157 return (pr_uioread(auxv, sizeof (auxv), uiop)); 1158 } 1159 1160 #if defined(__x86) 1161 /* 1162 * XX64 1163 * This is almost certainly broken for the amd64 kernel, because 1164 * we have two kinds of LDT structures to export -- one for compatibility 1165 * mode, and one for long mode, sigh. 1166 * 1167 * For now let's just have a ldt of size 0 for 64-bit processes. 1168 */ 1169 static int 1170 pr_read_ldt(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1171 { 1172 proc_t *p; 1173 struct ssd *ssd; 1174 size_t size; 1175 int error; 1176 1177 ASSERT(pnp->pr_type == PR_LDT); 1178 1179 if ((error = prlock(pnp, ZNO)) != 0) 1180 return (error); 1181 p = pnp->pr_common->prc_proc; 1182 1183 mutex_exit(&p->p_lock); 1184 mutex_enter(&p->p_ldtlock); 1185 size = prnldt(p) * sizeof (struct ssd); 1186 if (uiop->uio_offset >= size) { 1187 mutex_exit(&p->p_ldtlock); 1188 mutex_enter(&p->p_lock); 1189 prunlock(pnp); 1190 return (0); 1191 } 1192 1193 ssd = kmem_alloc(size, KM_SLEEP); 1194 prgetldt(p, ssd); 1195 mutex_exit(&p->p_ldtlock); 1196 mutex_enter(&p->p_lock); 1197 prunlock(pnp); 1198 1199 error = pr_uioread(ssd, size, uiop); 1200 kmem_free(ssd, size); 1201 return (error); 1202 } 1203 #endif /* __x86 */ 1204 1205 static int 1206 pr_read_usage(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1207 { 1208 prhusage_t *pup; 1209 prusage_t *upup; 1210 proc_t *p; 1211 kthread_t *t; 1212 int error; 1213 1214 ASSERT(pnp->pr_type == PR_USAGE); 1215 1216 /* allocate now, before locking the process */ 1217 pup = kmem_zalloc(sizeof (*pup), KM_SLEEP); 1218 upup = kmem_alloc(sizeof (*upup), KM_SLEEP); 1219 1220 /* 1221 * We don't want the full treatment of prlock(pnp) here. 1222 * This file is world-readable and never goes invalid. 1223 * It doesn't matter if we are in the middle of an exec(). 1224 */ 1225 p = pr_p_lock(pnp); 1226 mutex_exit(&pr_pidlock); 1227 if (p == NULL) { 1228 error = ENOENT; 1229 goto out; 1230 } 1231 ASSERT(p == pnp->pr_common->prc_proc); 1232 1233 if (uiop->uio_offset >= sizeof (prusage_t)) { 1234 prunlock(pnp); 1235 error = 0; 1236 goto out; 1237 } 1238 1239 pup->pr_tstamp = gethrtime(); 1240 1241 pup->pr_count = p->p_defunct; 1242 pup->pr_create = p->p_mstart; 1243 pup->pr_term = p->p_mterm; 1244 1245 pup->pr_rtime = p->p_mlreal; 1246 pup->pr_utime = p->p_acct[LMS_USER]; 1247 pup->pr_stime = p->p_acct[LMS_SYSTEM]; 1248 pup->pr_ttime = p->p_acct[LMS_TRAP]; 1249 pup->pr_tftime = p->p_acct[LMS_TFAULT]; 1250 pup->pr_dftime = p->p_acct[LMS_DFAULT]; 1251 pup->pr_kftime = p->p_acct[LMS_KFAULT]; 1252 pup->pr_ltime = p->p_acct[LMS_USER_LOCK]; 1253 pup->pr_slptime = p->p_acct[LMS_SLEEP]; 1254 pup->pr_wtime = p->p_acct[LMS_WAIT_CPU]; 1255 pup->pr_stoptime = p->p_acct[LMS_STOPPED]; 1256 1257 pup->pr_minf = p->p_ru.minflt; 1258 pup->pr_majf = p->p_ru.majflt; 1259 pup->pr_nswap = p->p_ru.nswap; 1260 pup->pr_inblk = p->p_ru.inblock; 1261 pup->pr_oublk = p->p_ru.oublock; 1262 pup->pr_msnd = p->p_ru.msgsnd; 1263 pup->pr_mrcv = p->p_ru.msgrcv; 1264 pup->pr_sigs = p->p_ru.nsignals; 1265 pup->pr_vctx = p->p_ru.nvcsw; 1266 pup->pr_ictx = p->p_ru.nivcsw; 1267 pup->pr_sysc = p->p_ru.sysc; 1268 pup->pr_ioch = p->p_ru.ioch; 1269 1270 /* 1271 * Add the usage information for each active lwp. 1272 */ 1273 if ((t = p->p_tlist) != NULL && 1274 !(pnp->pr_pcommon->prc_flags & PRC_DESTROY)) { 1275 do { 1276 if (t->t_proc_flag & TP_LWPEXIT) 1277 continue; 1278 pup->pr_count++; 1279 praddusage(t, pup); 1280 } while ((t = t->t_forw) != p->p_tlist); 1281 } 1282 1283 prunlock(pnp); 1284 1285 prcvtusage(pup, upup); 1286 1287 error = pr_uioread(upup, sizeof (prusage_t), uiop); 1288 out: 1289 kmem_free(pup, sizeof (*pup)); 1290 kmem_free(upup, sizeof (*upup)); 1291 return (error); 1292 } 1293 1294 static int 1295 pr_read_lusage(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1296 { 1297 int nlwp; 1298 prhusage_t *pup; 1299 prheader_t *php; 1300 prusage_t *upup; 1301 size_t size; 1302 hrtime_t curtime; 1303 proc_t *p; 1304 kthread_t *t; 1305 lwpdir_t *ldp; 1306 int error; 1307 int i; 1308 1309 ASSERT(pnp->pr_type == PR_LUSAGE); 1310 1311 /* 1312 * We don't want the full treatment of prlock(pnp) here. 1313 * This file is world-readable and never goes invalid. 1314 * It doesn't matter if we are in the middle of an exec(). 1315 */ 1316 p = pr_p_lock(pnp); 1317 mutex_exit(&pr_pidlock); 1318 if (p == NULL) 1319 return (ENOENT); 1320 ASSERT(p == pnp->pr_common->prc_proc); 1321 if ((nlwp = p->p_lwpcnt) == 0) { 1322 prunlock(pnp); 1323 return (ENOENT); 1324 } 1325 1326 size = sizeof (prheader_t) + (nlwp + 1) * LSPAN(prusage_t); 1327 if (uiop->uio_offset >= size) { 1328 prunlock(pnp); 1329 return (0); 1330 } 1331 1332 /* drop p->p_lock to do kmem_alloc(KM_SLEEP) */ 1333 mutex_exit(&p->p_lock); 1334 pup = kmem_zalloc(size + sizeof (prhusage_t), KM_SLEEP); 1335 mutex_enter(&p->p_lock); 1336 /* p->p_lwpcnt can't change while process is locked */ 1337 ASSERT(nlwp == p->p_lwpcnt); 1338 1339 php = (prheader_t *)(pup + 1); 1340 upup = (prusage_t *)(php + 1); 1341 1342 php->pr_nent = nlwp + 1; 1343 php->pr_entsize = LSPAN(prusage_t); 1344 1345 curtime = gethrtime(); 1346 1347 /* 1348 * First the summation over defunct lwps. 1349 */ 1350 pup->pr_count = p->p_defunct; 1351 pup->pr_tstamp = curtime; 1352 pup->pr_create = p->p_mstart; 1353 pup->pr_term = p->p_mterm; 1354 1355 pup->pr_rtime = p->p_mlreal; 1356 pup->pr_utime = p->p_acct[LMS_USER]; 1357 pup->pr_stime = p->p_acct[LMS_SYSTEM]; 1358 pup->pr_ttime = p->p_acct[LMS_TRAP]; 1359 pup->pr_tftime = p->p_acct[LMS_TFAULT]; 1360 pup->pr_dftime = p->p_acct[LMS_DFAULT]; 1361 pup->pr_kftime = p->p_acct[LMS_KFAULT]; 1362 pup->pr_ltime = p->p_acct[LMS_USER_LOCK]; 1363 pup->pr_slptime = p->p_acct[LMS_SLEEP]; 1364 pup->pr_wtime = p->p_acct[LMS_WAIT_CPU]; 1365 pup->pr_stoptime = p->p_acct[LMS_STOPPED]; 1366 1367 pup->pr_minf = p->p_ru.minflt; 1368 pup->pr_majf = p->p_ru.majflt; 1369 pup->pr_nswap = p->p_ru.nswap; 1370 pup->pr_inblk = p->p_ru.inblock; 1371 pup->pr_oublk = p->p_ru.oublock; 1372 pup->pr_msnd = p->p_ru.msgsnd; 1373 pup->pr_mrcv = p->p_ru.msgrcv; 1374 pup->pr_sigs = p->p_ru.nsignals; 1375 pup->pr_vctx = p->p_ru.nvcsw; 1376 pup->pr_ictx = p->p_ru.nivcsw; 1377 pup->pr_sysc = p->p_ru.sysc; 1378 pup->pr_ioch = p->p_ru.ioch; 1379 1380 prcvtusage(pup, upup); 1381 1382 /* 1383 * Fill one prusage struct for each active lwp. 1384 */ 1385 for (ldp = p->p_lwpdir, i = 0; i < p->p_lwpdir_sz; i++, ldp++) { 1386 if (ldp->ld_entry == NULL || 1387 (t = ldp->ld_entry->le_thread) == NULL) 1388 continue; 1389 ASSERT(!(t->t_proc_flag & TP_LWPEXIT)); 1390 ASSERT(nlwp > 0); 1391 --nlwp; 1392 upup = (prusage_t *)((caddr_t)upup + LSPAN(prusage_t)); 1393 prgetusage(t, pup); 1394 prcvtusage(pup, upup); 1395 } 1396 ASSERT(nlwp == 0); 1397 1398 prunlock(pnp); 1399 1400 error = pr_uioread(php, size, uiop); 1401 kmem_free(pup, size + sizeof (prhusage_t)); 1402 return (error); 1403 } 1404 1405 static int 1406 pr_read_pagedata(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1407 { 1408 proc_t *p; 1409 int error; 1410 1411 ASSERT(pnp->pr_type == PR_PAGEDATA); 1412 1413 if ((error = prlock(pnp, ZNO)) != 0) 1414 return (error); 1415 1416 p = pnp->pr_common->prc_proc; 1417 if ((p->p_flag & SSYS) || p->p_as == &kas) { 1418 prunlock(pnp); 1419 return (0); 1420 } 1421 1422 mutex_exit(&p->p_lock); 1423 error = prpdread(p, pnp->pr_hatid, uiop); 1424 mutex_enter(&p->p_lock); 1425 1426 prunlock(pnp); 1427 return (error); 1428 } 1429 1430 static int 1431 pr_read_opagedata(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1432 { 1433 proc_t *p; 1434 struct as *as; 1435 int error; 1436 1437 ASSERT(pnp->pr_type == PR_OPAGEDATA); 1438 1439 if ((error = prlock(pnp, ZNO)) != 0) 1440 return (error); 1441 1442 p = pnp->pr_common->prc_proc; 1443 as = p->p_as; 1444 if ((p->p_flag & SSYS) || as == &kas) { 1445 prunlock(pnp); 1446 return (0); 1447 } 1448 1449 mutex_exit(&p->p_lock); 1450 error = oprpdread(as, pnp->pr_hatid, uiop); 1451 mutex_enter(&p->p_lock); 1452 1453 prunlock(pnp); 1454 return (error); 1455 } 1456 1457 static int 1458 pr_read_watch(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1459 { 1460 proc_t *p; 1461 int error; 1462 prwatch_t *Bpwp; 1463 size_t size; 1464 prwatch_t *pwp; 1465 int nwarea; 1466 struct watched_area *pwarea; 1467 1468 ASSERT(pnp->pr_type == PR_WATCH); 1469 1470 if ((error = prlock(pnp, ZNO)) != 0) 1471 return (error); 1472 1473 p = pnp->pr_common->prc_proc; 1474 nwarea = avl_numnodes(&p->p_warea); 1475 size = nwarea * sizeof (prwatch_t); 1476 if (uiop->uio_offset >= size) { 1477 prunlock(pnp); 1478 return (0); 1479 } 1480 1481 /* drop p->p_lock to do kmem_alloc(KM_SLEEP) */ 1482 mutex_exit(&p->p_lock); 1483 Bpwp = pwp = kmem_zalloc(size, KM_SLEEP); 1484 mutex_enter(&p->p_lock); 1485 /* p->p_nwarea can't change while process is locked */ 1486 ASSERT(nwarea == avl_numnodes(&p->p_warea)); 1487 1488 /* gather the watched areas */ 1489 for (pwarea = avl_first(&p->p_warea); pwarea != NULL; 1490 pwarea = AVL_NEXT(&p->p_warea, pwarea), pwp++) { 1491 pwp->pr_vaddr = (uintptr_t)pwarea->wa_vaddr; 1492 pwp->pr_size = pwarea->wa_eaddr - pwarea->wa_vaddr; 1493 pwp->pr_wflags = (int)pwarea->wa_flags; 1494 } 1495 1496 prunlock(pnp); 1497 1498 error = pr_uioread(Bpwp, size, uiop); 1499 kmem_free(Bpwp, size); 1500 return (error); 1501 } 1502 1503 static int 1504 pr_read_lwpstatus(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1505 { 1506 lwpstatus_t *sp; 1507 int error; 1508 1509 ASSERT(pnp->pr_type == PR_LWPSTATUS); 1510 1511 /* 1512 * We kmem_alloc() the lwpstatus structure because 1513 * it is so big it might blow the kernel stack. 1514 */ 1515 sp = kmem_alloc(sizeof (*sp), KM_SLEEP); 1516 1517 if ((error = prlock(pnp, ZNO)) != 0) 1518 goto out; 1519 1520 if (uiop->uio_offset >= sizeof (*sp)) { 1521 prunlock(pnp); 1522 goto out; 1523 } 1524 1525 prgetlwpstatus(pnp->pr_common->prc_thread, sp, VTOZONE(PTOV(pnp))); 1526 prunlock(pnp); 1527 1528 error = pr_uioread(sp, sizeof (*sp), uiop); 1529 out: 1530 kmem_free(sp, sizeof (*sp)); 1531 return (error); 1532 } 1533 1534 static int 1535 pr_read_lwpsinfo(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1536 { 1537 lwpsinfo_t lwpsinfo; 1538 proc_t *p; 1539 kthread_t *t; 1540 lwpent_t *lep; 1541 1542 ASSERT(pnp->pr_type == PR_LWPSINFO); 1543 1544 /* 1545 * We don't want the full treatment of prlock(pnp) here. 1546 * This file is world-readable and never goes invalid. 1547 * It doesn't matter if we are in the middle of an exec(). 1548 */ 1549 p = pr_p_lock(pnp); 1550 mutex_exit(&pr_pidlock); 1551 if (p == NULL) 1552 return (ENOENT); 1553 ASSERT(p == pnp->pr_common->prc_proc); 1554 if (pnp->pr_common->prc_tslot == -1) { 1555 prunlock(pnp); 1556 return (ENOENT); 1557 } 1558 1559 if (uiop->uio_offset >= sizeof (lwpsinfo)) { 1560 prunlock(pnp); 1561 return (0); 1562 } 1563 1564 if ((t = pnp->pr_common->prc_thread) != NULL) 1565 prgetlwpsinfo(t, &lwpsinfo); 1566 else { 1567 lep = p->p_lwpdir[pnp->pr_common->prc_tslot].ld_entry; 1568 bzero(&lwpsinfo, sizeof (lwpsinfo)); 1569 lwpsinfo.pr_lwpid = lep->le_lwpid; 1570 lwpsinfo.pr_state = SZOMB; 1571 lwpsinfo.pr_sname = 'Z'; 1572 lwpsinfo.pr_start.tv_sec = lep->le_start; 1573 lwpsinfo.pr_bindpro = PBIND_NONE; 1574 lwpsinfo.pr_bindpset = PS_NONE; 1575 } 1576 prunlock(pnp); 1577 1578 return (pr_uioread(&lwpsinfo, sizeof (lwpsinfo), uiop)); 1579 } 1580 1581 static int 1582 pr_read_lwpusage(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1583 { 1584 prhusage_t *pup; 1585 prusage_t *upup; 1586 proc_t *p; 1587 int error; 1588 1589 ASSERT(pnp->pr_type == PR_LWPUSAGE); 1590 1591 /* allocate now, before locking the process */ 1592 pup = kmem_zalloc(sizeof (*pup), KM_SLEEP); 1593 upup = kmem_alloc(sizeof (*upup), KM_SLEEP); 1594 1595 /* 1596 * We don't want the full treatment of prlock(pnp) here. 1597 * This file is world-readable and never goes invalid. 1598 * It doesn't matter if we are in the middle of an exec(). 1599 */ 1600 p = pr_p_lock(pnp); 1601 mutex_exit(&pr_pidlock); 1602 if (p == NULL) { 1603 error = ENOENT; 1604 goto out; 1605 } 1606 ASSERT(p == pnp->pr_common->prc_proc); 1607 if (pnp->pr_common->prc_thread == NULL) { 1608 prunlock(pnp); 1609 error = ENOENT; 1610 goto out; 1611 } 1612 if (uiop->uio_offset >= sizeof (prusage_t)) { 1613 prunlock(pnp); 1614 error = 0; 1615 goto out; 1616 } 1617 1618 pup->pr_tstamp = gethrtime(); 1619 prgetusage(pnp->pr_common->prc_thread, pup); 1620 1621 prunlock(pnp); 1622 1623 prcvtusage(pup, upup); 1624 1625 error = pr_uioread(upup, sizeof (prusage_t), uiop); 1626 out: 1627 kmem_free(pup, sizeof (*pup)); 1628 kmem_free(upup, sizeof (*upup)); 1629 return (error); 1630 } 1631 1632 static int 1633 pr_read_lwpname(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1634 { 1635 char lwpname[THREAD_NAME_MAX]; 1636 kthread_t *t; 1637 int error; 1638 1639 ASSERT(pnp->pr_type == PR_LWPNAME); 1640 1641 if (uiop->uio_offset >= THREAD_NAME_MAX) 1642 return (0); 1643 1644 if ((error = prlock(pnp, ZNO)) != 0) 1645 return (error); 1646 1647 bzero(lwpname, sizeof (lwpname)); 1648 1649 t = pnp->pr_common->prc_thread; 1650 1651 if (t->t_name != NULL) 1652 (void) strlcpy(lwpname, t->t_name, sizeof (lwpname)); 1653 1654 prunlock(pnp); 1655 1656 return (pr_uioread(lwpname, sizeof (lwpname), uiop)); 1657 } 1658 1659 /* ARGSUSED */ 1660 static int 1661 pr_read_xregs(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1662 { 1663 proc_t *p; 1664 kthread_t *t; 1665 int error; 1666 void *xreg; 1667 size_t size; 1668 1669 ASSERT(pnp->pr_type == PR_XREGS); 1670 1671 if ((error = prlock(pnp, ZNO)) != 0) 1672 return (error); 1673 1674 p = pnp->pr_common->prc_proc; 1675 t = pnp->pr_common->prc_thread; 1676 1677 /* 1678 * While we would prefer to do the allocation without holding the 1679 * process under a prlock(), we can only determine this size while 1680 * holding the process as the hold guarantees us: 1681 * 1682 * o That the process in question actualy exists. 1683 * o That the process in question cannot change the set of FPU features 1684 * it has enabled. 1685 * 1686 * We will drop p_lock across the allocation call itself. This should be 1687 * safe as the enabled feature set should not change while the process 1688 * is locked (e.g. enabling extending FPU state like AMX on x86 should 1689 * require the process to be locked). 1690 */ 1691 size = prhasx(p) ? prgetprxregsize(p) : 0; 1692 if (size == 0) { 1693 prunlock(pnp); 1694 return (0); 1695 } 1696 mutex_exit(&p->p_lock); 1697 xreg = kmem_zalloc(size, KM_SLEEP); 1698 mutex_enter(&p->p_lock); 1699 ASSERT3U(size, ==, prgetprxregsize(p)); 1700 1701 if (uiop->uio_offset >= size) { 1702 prunlock(pnp); 1703 goto out; 1704 } 1705 1706 /* drop p->p_lock while (possibly) touching the stack */ 1707 mutex_exit(&p->p_lock); 1708 prgetprxregs(ttolwp(t), xreg); 1709 mutex_enter(&p->p_lock); 1710 prunlock(pnp); 1711 1712 error = pr_uioread(xreg, size, uiop); 1713 out: 1714 kmem_free(xreg, size); 1715 return (error); 1716 } 1717 1718 static int 1719 pr_read_spymaster(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1720 { 1721 psinfo_t psinfo; 1722 int error; 1723 klwp_t *lwp; 1724 1725 ASSERT(pnp->pr_type == PR_SPYMASTER); 1726 1727 if ((error = prlock(pnp, ZNO)) != 0) 1728 return (error); 1729 1730 if (pnp->pr_common->prc_thread == NULL) { 1731 prunlock(pnp); 1732 return (0); 1733 } 1734 1735 lwp = pnp->pr_common->prc_thread->t_lwp; 1736 1737 if (lwp->lwp_spymaster == NULL) { 1738 prunlock(pnp); 1739 return (0); 1740 } 1741 1742 bcopy(lwp->lwp_spymaster, &psinfo, sizeof (psinfo_t)); 1743 prunlock(pnp); 1744 1745 return (pr_uioread(&psinfo, sizeof (psinfo), uiop)); 1746 } 1747 1748 static int 1749 pr_read_secflags(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1750 { 1751 prsecflags_t ret; 1752 int error; 1753 proc_t *p; 1754 1755 ASSERT(pnp->pr_type == PR_SECFLAGS); 1756 1757 if ((error = prlock(pnp, ZNO)) != 0) 1758 return (error); 1759 1760 p = pnp->pr_common->prc_proc; 1761 prgetsecflags(p, &ret); 1762 prunlock(pnp); 1763 1764 return (pr_uioread(&ret, sizeof (ret), uiop)); 1765 } 1766 1767 #if defined(__sparc) 1768 1769 static int 1770 pr_read_gwindows(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1771 { 1772 proc_t *p; 1773 kthread_t *t; 1774 gwindows_t *gwp; 1775 int error; 1776 size_t size; 1777 1778 ASSERT(pnp->pr_type == PR_GWINDOWS); 1779 1780 gwp = kmem_zalloc(sizeof (gwindows_t), KM_SLEEP); 1781 1782 if ((error = prlock(pnp, ZNO)) != 0) 1783 goto out; 1784 1785 p = pnp->pr_common->prc_proc; 1786 t = pnp->pr_common->prc_thread; 1787 1788 /* 1789 * Drop p->p_lock while touching the stack. 1790 * The P_PR_LOCK flag prevents the lwp from 1791 * disappearing while we do this. 1792 */ 1793 mutex_exit(&p->p_lock); 1794 if ((size = prnwindows(ttolwp(t))) != 0) 1795 size = sizeof (gwindows_t) - 1796 (SPARC_MAXREGWINDOW - size) * sizeof (struct rwindow); 1797 if (uiop->uio_offset >= size) { 1798 mutex_enter(&p->p_lock); 1799 prunlock(pnp); 1800 goto out; 1801 } 1802 prgetwindows(ttolwp(t), gwp); 1803 mutex_enter(&p->p_lock); 1804 prunlock(pnp); 1805 1806 error = pr_uioread(gwp, size, uiop); 1807 out: 1808 kmem_free(gwp, sizeof (gwindows_t)); 1809 return (error); 1810 } 1811 1812 /* ARGSUSED */ 1813 static int 1814 pr_read_asrs(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1815 { 1816 int error; 1817 1818 ASSERT(pnp->pr_type == PR_ASRS); 1819 1820 /* the asrs file exists only for sparc v9 _LP64 processes */ 1821 if ((error = prlock(pnp, ZNO)) == 0) { 1822 proc_t *p = pnp->pr_common->prc_proc; 1823 kthread_t *t = pnp->pr_common->prc_thread; 1824 asrset_t asrset; 1825 1826 if (p->p_model != DATAMODEL_LP64 || 1827 uiop->uio_offset >= sizeof (asrset_t)) { 1828 prunlock(pnp); 1829 return (0); 1830 } 1831 1832 /* 1833 * Drop p->p_lock while touching the stack. 1834 * The P_PR_LOCK flag prevents the lwp from 1835 * disappearing while we do this. 1836 */ 1837 mutex_exit(&p->p_lock); 1838 prgetasregs(ttolwp(t), asrset); 1839 mutex_enter(&p->p_lock); 1840 prunlock(pnp); 1841 1842 error = pr_uioread(&asrset[0], sizeof (asrset_t), uiop); 1843 } 1844 1845 return (error); 1846 } 1847 1848 #endif /* __sparc */ 1849 1850 static int 1851 pr_read_piddir(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1852 { 1853 ASSERT(pnp->pr_type == PR_PIDDIR); 1854 ASSERT(pnp->pr_pidfile != NULL); 1855 1856 /* use the underlying PR_PIDFILE to read the process */ 1857 pnp = VTOP(pnp->pr_pidfile); 1858 ASSERT(pnp->pr_type == PR_PIDFILE); 1859 1860 return (pr_read_pidfile(pnp, uiop)); 1861 } 1862 1863 static int 1864 pr_read_pidfile(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1865 { 1866 int error; 1867 1868 ASSERT(pnp->pr_type == PR_PIDFILE || pnp->pr_type == PR_LWPIDFILE); 1869 1870 if ((error = prlock(pnp, ZNO)) == 0) { 1871 proc_t *p = pnp->pr_common->prc_proc; 1872 struct as *as = p->p_as; 1873 1874 if ((p->p_flag & SSYS) || as == &kas) { 1875 /* 1876 * /proc I/O cannot be done to a system process. 1877 */ 1878 error = EIO; /* old /proc semantics */ 1879 } else { 1880 /* 1881 * We drop p_lock because we don't want to hold 1882 * it over an I/O operation because that could 1883 * lead to deadlock with the clock thread. 1884 * The process will not disappear and its address 1885 * space will not change because it is marked P_PR_LOCK. 1886 */ 1887 mutex_exit(&p->p_lock); 1888 error = prusrio(p, UIO_READ, uiop, 1); 1889 mutex_enter(&p->p_lock); 1890 } 1891 prunlock(pnp); 1892 } 1893 1894 return (error); 1895 } 1896 1897 #ifdef _SYSCALL32_IMPL 1898 1899 /* 1900 * Array of ILP32 read functions, indexed by /proc file type. 1901 */ 1902 static int pr_read_status_32(), 1903 pr_read_lstatus_32(), pr_read_psinfo_32(), pr_read_lpsinfo_32(), 1904 pr_read_map_32(), pr_read_rmap_32(), pr_read_xmap_32(), 1905 pr_read_sigact_32(), pr_read_auxv_32(), 1906 pr_read_usage_32(), pr_read_lusage_32(), pr_read_pagedata_32(), 1907 pr_read_watch_32(), pr_read_lwpstatus_32(), pr_read_lwpsinfo_32(), 1908 pr_read_lwpusage_32(), pr_read_spymaster_32(), 1909 #if defined(__sparc) 1910 pr_read_gwindows_32(), 1911 #endif 1912 pr_read_opagedata_32(); 1913 1914 static int (*pr_read_function_32[PR_NFILES])() = { 1915 pr_read_inval, /* /proc */ 1916 pr_read_inval, /* /proc/self */ 1917 pr_read_piddir, /* /proc/<pid> (old /proc read()) */ 1918 pr_read_as, /* /proc/<pid>/as */ 1919 pr_read_inval, /* /proc/<pid>/ctl */ 1920 pr_read_status_32, /* /proc/<pid>/status */ 1921 pr_read_lstatus_32, /* /proc/<pid>/lstatus */ 1922 pr_read_psinfo_32, /* /proc/<pid>/psinfo */ 1923 pr_read_lpsinfo_32, /* /proc/<pid>/lpsinfo */ 1924 pr_read_map_32, /* /proc/<pid>/map */ 1925 pr_read_rmap_32, /* /proc/<pid>/rmap */ 1926 pr_read_xmap_32, /* /proc/<pid>/xmap */ 1927 pr_read_cred, /* /proc/<pid>/cred */ 1928 pr_read_sigact_32, /* /proc/<pid>/sigact */ 1929 pr_read_auxv_32, /* /proc/<pid>/auxv */ 1930 #if defined(__x86) 1931 pr_read_ldt, /* /proc/<pid>/ldt */ 1932 #endif 1933 pr_read_usage_32, /* /proc/<pid>/usage */ 1934 pr_read_lusage_32, /* /proc/<pid>/lusage */ 1935 pr_read_pagedata_32, /* /proc/<pid>/pagedata */ 1936 pr_read_watch_32, /* /proc/<pid>/watch */ 1937 pr_read_inval, /* /proc/<pid>/cwd */ 1938 pr_read_inval, /* /proc/<pid>/root */ 1939 pr_read_inval, /* /proc/<pid>/fd */ 1940 pr_read_inval, /* /proc/<pid>/fd/nn */ 1941 pr_read_inval, /* /proc/<pid>/fdinfo */ 1942 pr_read_fdinfo, /* /proc/<pid>/fdinfo/nn */ 1943 pr_read_inval, /* /proc/<pid>/object */ 1944 pr_read_inval, /* /proc/<pid>/object/xxx */ 1945 pr_read_inval, /* /proc/<pid>/lwp */ 1946 pr_read_inval, /* /proc/<pid>/lwp/<lwpid> */ 1947 pr_read_inval, /* /proc/<pid>/lwp/<lwpid>/lwpctl */ 1948 pr_read_lwpname, /* /proc/<pid>/lwp/<lwpid>/lwpname */ 1949 pr_read_lwpstatus_32, /* /proc/<pid>/lwp/<lwpid>/lwpstatus */ 1950 pr_read_lwpsinfo_32, /* /proc/<pid>/lwp/<lwpid>/lwpsinfo */ 1951 pr_read_lwpusage_32, /* /proc/<pid>/lwp/<lwpid>/lwpusage */ 1952 pr_read_xregs, /* /proc/<pid>/lwp/<lwpid>/xregs */ 1953 pr_read_inval, /* /proc/<pid>/lwp/<lwpid>/templates */ 1954 pr_read_inval, /* /proc/<pid>/lwp/<lwpid>/templates/<id> */ 1955 pr_read_spymaster_32, /* /proc/<pid>/lwp/<lwpid>/spymaster */ 1956 #if defined(__sparc) 1957 pr_read_gwindows_32, /* /proc/<pid>/lwp/<lwpid>/gwindows */ 1958 pr_read_asrs, /* /proc/<pid>/lwp/<lwpid>/asrs */ 1959 #endif 1960 pr_read_priv, /* /proc/<pid>/priv */ 1961 pr_read_inval, /* /proc/<pid>/path */ 1962 pr_read_inval, /* /proc/<pid>/path/xxx */ 1963 pr_read_inval, /* /proc/<pid>/contracts */ 1964 pr_read_inval, /* /proc/<pid>/contracts/<ctid> */ 1965 pr_read_secflags, /* /proc/<pid>/secflags */ 1966 pr_read_pidfile, /* old process file */ 1967 pr_read_pidfile, /* old lwp file */ 1968 pr_read_opagedata_32, /* old pagedata file */ 1969 }; 1970 1971 static int 1972 pr_read_status_32(prnode_t *pnp, uio_t *uiop, cred_t *cr) 1973 { 1974 pstatus32_t *sp; 1975 proc_t *p; 1976 int error; 1977 1978 ASSERT(pnp->pr_type == PR_STATUS); 1979 1980 /* 1981 * We kmem_alloc() the pstatus structure because 1982 * it is so big it might blow the kernel stack. 1983 */ 1984 sp = kmem_alloc(sizeof (*sp), KM_SLEEP); 1985 if ((error = prlock(pnp, ZNO)) == 0) { 1986 /* 1987 * A 32-bit process cannot get the status of a 64-bit process. 1988 * The fields for the 64-bit quantities are not large enough. 1989 */ 1990 p = pnp->pr_common->prc_proc; 1991 if (PROCESS_NOT_32BIT(p)) { 1992 prunlock(pnp); 1993 error = EOVERFLOW; 1994 } else { 1995 prgetstatus32(pnp->pr_common->prc_proc, sp, 1996 VTOZONE(PTOV(pnp))); 1997 prunlock(pnp); 1998 error = pr_uioread(sp, sizeof (*sp), uiop); 1999 } 2000 } 2001 kmem_free((caddr_t)sp, sizeof (*sp)); 2002 return (error); 2003 } 2004 2005 static int 2006 pr_read_lstatus_32(prnode_t *pnp, uio_t *uiop, cred_t *cr) 2007 { 2008 proc_t *p; 2009 kthread_t *t; 2010 lwpdir_t *ldp; 2011 size_t size; 2012 prheader32_t *php; 2013 lwpstatus32_t *sp; 2014 int error; 2015 int nlwp; 2016 int i; 2017 2018 ASSERT(pnp->pr_type == PR_LSTATUS); 2019 2020 if ((error = prlock(pnp, ZNO)) != 0) 2021 return (error); 2022 p = pnp->pr_common->prc_proc; 2023 /* 2024 * A 32-bit process cannot get the status of a 64-bit process. 2025 * The fields for the 64-bit quantities are not large enough. 2026 */ 2027 if (PROCESS_NOT_32BIT(p)) { 2028 prunlock(pnp); 2029 return (EOVERFLOW); 2030 } 2031 nlwp = p->p_lwpcnt; 2032 size = sizeof (prheader32_t) + nlwp * LSPAN32(lwpstatus32_t); 2033 2034 /* drop p->p_lock to do kmem_alloc(KM_SLEEP) */ 2035 mutex_exit(&p->p_lock); 2036 php = kmem_zalloc(size, KM_SLEEP); 2037 mutex_enter(&p->p_lock); 2038 /* p->p_lwpcnt can't change while process is locked */ 2039 ASSERT(nlwp == p->p_lwpcnt); 2040 2041 php->pr_nent = nlwp; 2042 php->pr_entsize = LSPAN32(lwpstatus32_t); 2043 2044 sp = (lwpstatus32_t *)(php + 1); 2045 for (ldp = p->p_lwpdir, i = 0; i < p->p_lwpdir_sz; i++, ldp++) { 2046 if (ldp->ld_entry == NULL || 2047 (t = ldp->ld_entry->le_thread) == NULL) 2048 continue; 2049 prgetlwpstatus32(t, sp, VTOZONE(PTOV(pnp))); 2050 sp = (lwpstatus32_t *)((caddr_t)sp + LSPAN32(lwpstatus32_t)); 2051 } 2052 prunlock(pnp); 2053 2054 error = pr_uioread(php, size, uiop); 2055 kmem_free(php, size); 2056 return (error); 2057 } 2058 2059 static int 2060 pr_read_psinfo_32(prnode_t *pnp, uio_t *uiop, cred_t *cr) 2061 { 2062 psinfo32_t psinfo; 2063 proc_t *p; 2064 int error = 0; 2065 2066 ASSERT(pnp->pr_type == PR_PSINFO); 2067 2068 /* 2069 * We don't want the full treatment of prlock(pnp) here. 2070 * This file is world-readable and never goes invalid. 2071 * It doesn't matter if we are in the middle of an exec(). 2072 */ 2073 p = pr_p_lock(pnp); 2074 mutex_exit(&pr_pidlock); 2075 if (p == NULL) 2076 error = ENOENT; 2077 else { 2078 ASSERT(p == pnp->pr_common->prc_proc); 2079 prgetpsinfo32(p, &psinfo); 2080 prunlock(pnp); 2081 error = pr_uioread(&psinfo, sizeof (psinfo), uiop); 2082 } 2083 return (error); 2084 } 2085 2086 static int 2087 pr_read_lpsinfo_32(prnode_t *pnp, uio_t *uiop, cred_t *cr) 2088 { 2089 proc_t *p; 2090 kthread_t *t; 2091 lwpdir_t *ldp; 2092 lwpent_t *lep; 2093 size_t size; 2094 prheader32_t *php; 2095 lwpsinfo32_t *sp; 2096 int error; 2097 int nlwp; 2098 int i; 2099 2100 ASSERT(pnp->pr_type == PR_LPSINFO); 2101 2102 /* 2103 * We don't want the full treatment of prlock(pnp) here. 2104 * This file is world-readable and never goes invalid. 2105 * It doesn't matter if we are in the middle of an exec(). 2106 */ 2107 p = pr_p_lock(pnp); 2108 mutex_exit(&pr_pidlock); 2109 if (p == NULL) 2110 return (ENOENT); 2111 ASSERT(p == pnp->pr_common->prc_proc); 2112 if ((nlwp = p->p_lwpcnt + p->p_zombcnt) == 0) { 2113 prunlock(pnp); 2114 return (ENOENT); 2115 } 2116 size = sizeof (prheader32_t) + nlwp * LSPAN32(lwpsinfo32_t); 2117 2118 /* drop p->p_lock to do kmem_alloc(KM_SLEEP) */ 2119 mutex_exit(&p->p_lock); 2120 php = kmem_zalloc(size, KM_SLEEP); 2121 mutex_enter(&p->p_lock); 2122 /* p->p_lwpcnt can't change while process is locked */ 2123 ASSERT(nlwp == p->p_lwpcnt + p->p_zombcnt); 2124 2125 php->pr_nent = nlwp; 2126 php->pr_entsize = LSPAN32(lwpsinfo32_t); 2127 2128 sp = (lwpsinfo32_t *)(php + 1); 2129 for (ldp = p->p_lwpdir, i = 0; i < p->p_lwpdir_sz; i++, ldp++) { 2130 if ((lep = ldp->ld_entry) == NULL) 2131 continue; 2132 if ((t = lep->le_thread) != NULL) 2133 prgetlwpsinfo32(t, sp); 2134 else { 2135 bzero(sp, sizeof (*sp)); 2136 sp->pr_lwpid = lep->le_lwpid; 2137 sp->pr_state = SZOMB; 2138 sp->pr_sname = 'Z'; 2139 sp->pr_start.tv_sec = (time32_t)lep->le_start; 2140 } 2141 sp = (lwpsinfo32_t *)((caddr_t)sp + LSPAN32(lwpsinfo32_t)); 2142 } 2143 prunlock(pnp); 2144 2145 error = pr_uioread(php, size, uiop); 2146 kmem_free(php, size); 2147 return (error); 2148 } 2149 2150 static int 2151 pr_read_map_common_32(prnode_t *pnp, uio_t *uiop, prnodetype_t type) 2152 { 2153 proc_t *p; 2154 struct as *as; 2155 list_t iolhead; 2156 int error; 2157 2158 readmap32_common: 2159 if ((error = prlock(pnp, ZNO)) != 0) 2160 return (error); 2161 2162 p = pnp->pr_common->prc_proc; 2163 as = p->p_as; 2164 2165 if ((p->p_flag & SSYS) || as == &kas) { 2166 prunlock(pnp); 2167 return (0); 2168 } 2169 2170 if (PROCESS_NOT_32BIT(p)) { 2171 prunlock(pnp); 2172 return (EOVERFLOW); 2173 } 2174 2175 if (!AS_LOCK_TRYENTER(as, RW_WRITER)) { 2176 prunlock(pnp); 2177 delay(1); 2178 goto readmap32_common; 2179 } 2180 mutex_exit(&p->p_lock); 2181 2182 switch (type) { 2183 case PR_XMAP: 2184 error = prgetxmap32(p, &iolhead); 2185 break; 2186 case PR_RMAP: 2187 error = prgetmap32(p, 1, &iolhead); 2188 break; 2189 case PR_MAP: 2190 error = prgetmap32(p, 0, &iolhead); 2191 break; 2192 } 2193 AS_LOCK_EXIT(as); 2194 mutex_enter(&p->p_lock); 2195 prunlock(pnp); 2196 2197 error = pr_iol_uiomove_and_free(&iolhead, uiop, error); 2198 2199 return (error); 2200 } 2201 2202 static int 2203 pr_read_map_32(prnode_t *pnp, uio_t *uiop, cred_t *cr) 2204 { 2205 ASSERT(pnp->pr_type == PR_MAP); 2206 return (pr_read_map_common_32(pnp, uiop, pnp->pr_type)); 2207 } 2208 2209 static int 2210 pr_read_rmap_32(prnode_t *pnp, uio_t *uiop, cred_t *cr) 2211 { 2212 ASSERT(pnp->pr_type == PR_RMAP); 2213 return (pr_read_map_common_32(pnp, uiop, pnp->pr_type)); 2214 } 2215 2216 static int 2217 pr_read_xmap_32(prnode_t *pnp, uio_t *uiop, cred_t *cr) 2218 { 2219 ASSERT(pnp->pr_type == PR_XMAP); 2220 return (pr_read_map_common_32(pnp, uiop, pnp->pr_type)); 2221 } 2222 2223 static int 2224 pr_read_sigact_32(prnode_t *pnp, uio_t *uiop, cred_t *cr) 2225 { 2226 int nsig = PROC_IS_BRANDED(curproc)? BROP(curproc)->b_nsig : NSIG; 2227 proc_t *p; 2228 struct sigaction32 *sap; 2229 int sig; 2230 int error; 2231 user_t *up; 2232 2233 ASSERT(pnp->pr_type == PR_SIGACT); 2234 2235 /* 2236 * We kmem_alloc() the sigaction32 array because 2237 * it is so big it might blow the kernel stack. 2238 */ 2239 sap = kmem_alloc((nsig-1) * sizeof (struct sigaction32), KM_SLEEP); 2240 2241 if ((error = prlock(pnp, ZNO)) != 0) 2242 goto out; 2243 p = pnp->pr_common->prc_proc; 2244 2245 if (PROCESS_NOT_32BIT(p)) { 2246 prunlock(pnp); 2247 error = EOVERFLOW; 2248 goto out; 2249 } 2250 2251 if (uiop->uio_offset >= (nsig-1) * sizeof (struct sigaction32)) { 2252 prunlock(pnp); 2253 goto out; 2254 } 2255 2256 up = PTOU(p); 2257 for (sig = 1; sig < nsig; sig++) 2258 prgetaction32(p, up, sig, &sap[sig-1]); 2259 prunlock(pnp); 2260 2261 error = pr_uioread(sap, (nsig - 1) * sizeof (struct sigaction32), uiop); 2262 out: 2263 kmem_free(sap, (nsig-1) * sizeof (struct sigaction32)); 2264 return (error); 2265 } 2266 2267 static int 2268 pr_read_auxv_32(prnode_t *pnp, uio_t *uiop, cred_t *cr) 2269 { 2270 auxv32_t auxv[__KERN_NAUXV_IMPL]; 2271 proc_t *p; 2272 user_t *up; 2273 int error; 2274 int i; 2275 2276 ASSERT(pnp->pr_type == PR_AUXV); 2277 2278 if ((error = prlock(pnp, ZNO)) != 0) 2279 return (error); 2280 p = pnp->pr_common->prc_proc; 2281 2282 if (PROCESS_NOT_32BIT(p)) { 2283 prunlock(pnp); 2284 return (EOVERFLOW); 2285 } 2286 2287 if (uiop->uio_offset >= sizeof (auxv)) { 2288 prunlock(pnp); 2289 return (0); 2290 } 2291 2292 up = PTOU(p); 2293 for (i = 0; i < __KERN_NAUXV_IMPL; i++) { 2294 auxv[i].a_type = (int32_t)up->u_auxv[i].a_type; 2295 auxv[i].a_un.a_val = (int32_t)up->u_auxv[i].a_un.a_val; 2296 } 2297 prunlock(pnp); 2298 2299 return (pr_uioread(auxv, sizeof (auxv), uiop)); 2300 } 2301 2302 static int 2303 pr_read_usage_32(prnode_t *pnp, uio_t *uiop, cred_t *cr) 2304 { 2305 prhusage_t *pup; 2306 prusage32_t *upup; 2307 proc_t *p; 2308 kthread_t *t; 2309 int error; 2310 2311 ASSERT(pnp->pr_type == PR_USAGE); 2312 2313 /* allocate now, before locking the process */ 2314 pup = kmem_zalloc(sizeof (*pup), KM_SLEEP); 2315 upup = kmem_alloc(sizeof (*upup), KM_SLEEP); 2316 2317 /* 2318 * We don't want the full treatment of prlock(pnp) here. 2319 * This file is world-readable and never goes invalid. 2320 * It doesn't matter if we are in the middle of an exec(). 2321 */ 2322 p = pr_p_lock(pnp); 2323 mutex_exit(&pr_pidlock); 2324 if (p == NULL) { 2325 error = ENOENT; 2326 goto out; 2327 } 2328 ASSERT(p == pnp->pr_common->prc_proc); 2329 2330 if (uiop->uio_offset >= sizeof (prusage32_t)) { 2331 prunlock(pnp); 2332 error = 0; 2333 goto out; 2334 } 2335 2336 pup->pr_tstamp = gethrtime(); 2337 2338 pup->pr_count = p->p_defunct; 2339 pup->pr_create = p->p_mstart; 2340 pup->pr_term = p->p_mterm; 2341 2342 pup->pr_rtime = p->p_mlreal; 2343 pup->pr_utime = p->p_acct[LMS_USER]; 2344 pup->pr_stime = p->p_acct[LMS_SYSTEM]; 2345 pup->pr_ttime = p->p_acct[LMS_TRAP]; 2346 pup->pr_tftime = p->p_acct[LMS_TFAULT]; 2347 pup->pr_dftime = p->p_acct[LMS_DFAULT]; 2348 pup->pr_kftime = p->p_acct[LMS_KFAULT]; 2349 pup->pr_ltime = p->p_acct[LMS_USER_LOCK]; 2350 pup->pr_slptime = p->p_acct[LMS_SLEEP]; 2351 pup->pr_wtime = p->p_acct[LMS_WAIT_CPU]; 2352 pup->pr_stoptime = p->p_acct[LMS_STOPPED]; 2353 2354 pup->pr_minf = p->p_ru.minflt; 2355 pup->pr_majf = p->p_ru.majflt; 2356 pup->pr_nswap = p->p_ru.nswap; 2357 pup->pr_inblk = p->p_ru.inblock; 2358 pup->pr_oublk = p->p_ru.oublock; 2359 pup->pr_msnd = p->p_ru.msgsnd; 2360 pup->pr_mrcv = p->p_ru.msgrcv; 2361 pup->pr_sigs = p->p_ru.nsignals; 2362 pup->pr_vctx = p->p_ru.nvcsw; 2363 pup->pr_ictx = p->p_ru.nivcsw; 2364 pup->pr_sysc = p->p_ru.sysc; 2365 pup->pr_ioch = p->p_ru.ioch; 2366 2367 /* 2368 * Add the usage information for each active lwp. 2369 */ 2370 if ((t = p->p_tlist) != NULL && 2371 !(pnp->pr_pcommon->prc_flags & PRC_DESTROY)) { 2372 do { 2373 if (t->t_proc_flag & TP_LWPEXIT) 2374 continue; 2375 pup->pr_count++; 2376 praddusage(t, pup); 2377 } while ((t = t->t_forw) != p->p_tlist); 2378 } 2379 2380 prunlock(pnp); 2381 2382 prcvtusage32(pup, upup); 2383 2384 error = pr_uioread(upup, sizeof (prusage32_t), uiop); 2385 out: 2386 kmem_free(pup, sizeof (*pup)); 2387 kmem_free(upup, sizeof (*upup)); 2388 return (error); 2389 } 2390 2391 static int 2392 pr_read_lusage_32(prnode_t *pnp, uio_t *uiop, cred_t *cr) 2393 { 2394 int nlwp; 2395 prhusage_t *pup; 2396 prheader32_t *php; 2397 prusage32_t *upup; 2398 size_t size; 2399 hrtime_t curtime; 2400 proc_t *p; 2401 kthread_t *t; 2402 lwpdir_t *ldp; 2403 int error; 2404 int i; 2405 2406 ASSERT(pnp->pr_type == PR_LUSAGE); 2407 2408 /* 2409 * We don't want the full treatment of prlock(pnp) here. 2410 * This file is world-readable and never goes invalid. 2411 * It doesn't matter if we are in the middle of an exec(). 2412 */ 2413 p = pr_p_lock(pnp); 2414 mutex_exit(&pr_pidlock); 2415 if (p == NULL) 2416 return (ENOENT); 2417 ASSERT(p == pnp->pr_common->prc_proc); 2418 if ((nlwp = p->p_lwpcnt) == 0) { 2419 prunlock(pnp); 2420 return (ENOENT); 2421 } 2422 2423 size = sizeof (prheader32_t) + (nlwp + 1) * LSPAN32(prusage32_t); 2424 if (uiop->uio_offset >= size) { 2425 prunlock(pnp); 2426 return (0); 2427 } 2428 2429 /* drop p->p_lock to do kmem_alloc(KM_SLEEP) */ 2430 mutex_exit(&p->p_lock); 2431 pup = kmem_zalloc(size + sizeof (prhusage_t), KM_SLEEP); 2432 mutex_enter(&p->p_lock); 2433 /* p->p_lwpcnt can't change while process is locked */ 2434 ASSERT(nlwp == p->p_lwpcnt); 2435 2436 php = (prheader32_t *)(pup + 1); 2437 upup = (prusage32_t *)(php + 1); 2438 2439 php->pr_nent = nlwp + 1; 2440 php->pr_entsize = LSPAN32(prusage32_t); 2441 2442 curtime = gethrtime(); 2443 2444 /* 2445 * First the summation over defunct lwps. 2446 */ 2447 pup->pr_count = p->p_defunct; 2448 pup->pr_tstamp = curtime; 2449 pup->pr_create = p->p_mstart; 2450 pup->pr_term = p->p_mterm; 2451 2452 pup->pr_rtime = p->p_mlreal; 2453 pup->pr_utime = p->p_acct[LMS_USER]; 2454 pup->pr_stime = p->p_acct[LMS_SYSTEM]; 2455 pup->pr_ttime = p->p_acct[LMS_TRAP]; 2456 pup->pr_tftime = p->p_acct[LMS_TFAULT]; 2457 pup->pr_dftime = p->p_acct[LMS_DFAULT]; 2458 pup->pr_kftime = p->p_acct[LMS_KFAULT]; 2459 pup->pr_ltime = p->p_acct[LMS_USER_LOCK]; 2460 pup->pr_slptime = p->p_acct[LMS_SLEEP]; 2461 pup->pr_wtime = p->p_acct[LMS_WAIT_CPU]; 2462 pup->pr_stoptime = p->p_acct[LMS_STOPPED]; 2463 2464 pup->pr_minf = p->p_ru.minflt; 2465 pup->pr_majf = p->p_ru.majflt; 2466 pup->pr_nswap = p->p_ru.nswap; 2467 pup->pr_inblk = p->p_ru.inblock; 2468 pup->pr_oublk = p->p_ru.oublock; 2469 pup->pr_msnd = p->p_ru.msgsnd; 2470 pup->pr_mrcv = p->p_ru.msgrcv; 2471 pup->pr_sigs = p->p_ru.nsignals; 2472 pup->pr_vctx = p->p_ru.nvcsw; 2473 pup->pr_ictx = p->p_ru.nivcsw; 2474 pup->pr_sysc = p->p_ru.sysc; 2475 pup->pr_ioch = p->p_ru.ioch; 2476 2477 prcvtusage32(pup, upup); 2478 2479 /* 2480 * Fill one prusage struct for each active lwp. 2481 */ 2482 for (ldp = p->p_lwpdir, i = 0; i < p->p_lwpdir_sz; i++, ldp++) { 2483 if (ldp->ld_entry == NULL || 2484 (t = ldp->ld_entry->le_thread) == NULL) 2485 continue; 2486 ASSERT(!(t->t_proc_flag & TP_LWPEXIT)); 2487 ASSERT(nlwp > 0); 2488 --nlwp; 2489 upup = (prusage32_t *) 2490 ((caddr_t)upup + LSPAN32(prusage32_t)); 2491 prgetusage(t, pup); 2492 prcvtusage32(pup, upup); 2493 } 2494 ASSERT(nlwp == 0); 2495 2496 prunlock(pnp); 2497 2498 error = pr_uioread(php, size, uiop); 2499 kmem_free(pup, size + sizeof (prhusage_t)); 2500 return (error); 2501 } 2502 2503 static int 2504 pr_read_pagedata_32(prnode_t *pnp, uio_t *uiop, cred_t *cr) 2505 { 2506 proc_t *p; 2507 int error; 2508 2509 ASSERT(pnp->pr_type == PR_PAGEDATA); 2510 2511 if ((error = prlock(pnp, ZNO)) != 0) 2512 return (error); 2513 2514 p = pnp->pr_common->prc_proc; 2515 if ((p->p_flag & SSYS) || p->p_as == &kas) { 2516 prunlock(pnp); 2517 return (0); 2518 } 2519 2520 if (PROCESS_NOT_32BIT(p)) { 2521 prunlock(pnp); 2522 return (EOVERFLOW); 2523 } 2524 2525 mutex_exit(&p->p_lock); 2526 error = prpdread32(p, pnp->pr_hatid, uiop); 2527 mutex_enter(&p->p_lock); 2528 2529 prunlock(pnp); 2530 return (error); 2531 } 2532 2533 static int 2534 pr_read_opagedata_32(prnode_t *pnp, uio_t *uiop, cred_t *cr) 2535 { 2536 proc_t *p; 2537 struct as *as; 2538 int error; 2539 2540 ASSERT(pnp->pr_type == PR_OPAGEDATA); 2541 2542 if ((error = prlock(pnp, ZNO)) != 0) 2543 return (error); 2544 2545 p = pnp->pr_common->prc_proc; 2546 as = p->p_as; 2547 2548 if ((p->p_flag & SSYS) || as == &kas) { 2549 prunlock(pnp); 2550 return (0); 2551 } 2552 2553 if (PROCESS_NOT_32BIT(p)) { 2554 prunlock(pnp); 2555 return (EOVERFLOW); 2556 } 2557 2558 mutex_exit(&p->p_lock); 2559 error = oprpdread32(as, pnp->pr_hatid, uiop); 2560 mutex_enter(&p->p_lock); 2561 2562 prunlock(pnp); 2563 return (error); 2564 } 2565 2566 static int 2567 pr_read_watch_32(prnode_t *pnp, uio_t *uiop, cred_t *cr) 2568 { 2569 proc_t *p; 2570 int error; 2571 prwatch32_t *Bpwp; 2572 size_t size; 2573 prwatch32_t *pwp; 2574 int nwarea; 2575 struct watched_area *pwarea; 2576 2577 ASSERT(pnp->pr_type == PR_WATCH); 2578 2579 if ((error = prlock(pnp, ZNO)) != 0) 2580 return (error); 2581 2582 p = pnp->pr_common->prc_proc; 2583 if (PROCESS_NOT_32BIT(p)) { 2584 prunlock(pnp); 2585 return (EOVERFLOW); 2586 } 2587 nwarea = avl_numnodes(&p->p_warea); 2588 size = nwarea * sizeof (prwatch32_t); 2589 if (uiop->uio_offset >= size) { 2590 prunlock(pnp); 2591 return (0); 2592 } 2593 2594 /* drop p->p_lock to do kmem_alloc(KM_SLEEP) */ 2595 mutex_exit(&p->p_lock); 2596 Bpwp = pwp = kmem_zalloc(size, KM_SLEEP); 2597 mutex_enter(&p->p_lock); 2598 /* p->p_nwarea can't change while process is locked */ 2599 ASSERT(nwarea == avl_numnodes(&p->p_warea)); 2600 2601 /* gather the watched areas */ 2602 for (pwarea = avl_first(&p->p_warea); pwarea != NULL; 2603 pwarea = AVL_NEXT(&p->p_warea, pwarea), pwp++) { 2604 pwp->pr_vaddr = (caddr32_t)(uintptr_t)pwarea->wa_vaddr; 2605 pwp->pr_size = (size32_t)(pwarea->wa_eaddr - pwarea->wa_vaddr); 2606 pwp->pr_wflags = (int)pwarea->wa_flags; 2607 } 2608 2609 prunlock(pnp); 2610 2611 error = pr_uioread(Bpwp, size, uiop); 2612 kmem_free(Bpwp, size); 2613 return (error); 2614 } 2615 2616 static int 2617 pr_read_lwpstatus_32(prnode_t *pnp, uio_t *uiop, cred_t *cr) 2618 { 2619 lwpstatus32_t *sp; 2620 proc_t *p; 2621 int error; 2622 2623 ASSERT(pnp->pr_type == PR_LWPSTATUS); 2624 2625 /* 2626 * We kmem_alloc() the lwpstatus structure because 2627 * it is so big it might blow the kernel stack. 2628 */ 2629 sp = kmem_alloc(sizeof (*sp), KM_SLEEP); 2630 2631 if ((error = prlock(pnp, ZNO)) != 0) 2632 goto out; 2633 2634 /* 2635 * A 32-bit process cannot get the status of a 64-bit process. 2636 * The fields for the 64-bit quantities are not large enough. 2637 */ 2638 p = pnp->pr_common->prc_proc; 2639 if (PROCESS_NOT_32BIT(p)) { 2640 prunlock(pnp); 2641 error = EOVERFLOW; 2642 goto out; 2643 } 2644 2645 if (uiop->uio_offset >= sizeof (*sp)) { 2646 prunlock(pnp); 2647 goto out; 2648 } 2649 2650 prgetlwpstatus32(pnp->pr_common->prc_thread, sp, VTOZONE(PTOV(pnp))); 2651 prunlock(pnp); 2652 2653 error = pr_uioread(sp, sizeof (*sp), uiop); 2654 out: 2655 kmem_free(sp, sizeof (*sp)); 2656 return (error); 2657 } 2658 2659 static int 2660 pr_read_lwpsinfo_32(prnode_t *pnp, uio_t *uiop, cred_t *cr) 2661 { 2662 lwpsinfo32_t lwpsinfo; 2663 proc_t *p; 2664 kthread_t *t; 2665 lwpent_t *lep; 2666 2667 ASSERT(pnp->pr_type == PR_LWPSINFO); 2668 2669 /* 2670 * We don't want the full treatment of prlock(pnp) here. 2671 * This file is world-readable and never goes invalid. 2672 * It doesn't matter if we are in the middle of an exec(). 2673 */ 2674 p = pr_p_lock(pnp); 2675 mutex_exit(&pr_pidlock); 2676 if (p == NULL) 2677 return (ENOENT); 2678 ASSERT(p == pnp->pr_common->prc_proc); 2679 if (pnp->pr_common->prc_tslot == -1) { 2680 prunlock(pnp); 2681 return (ENOENT); 2682 } 2683 2684 if (uiop->uio_offset >= sizeof (lwpsinfo)) { 2685 prunlock(pnp); 2686 return (0); 2687 } 2688 2689 if ((t = pnp->pr_common->prc_thread) != NULL) 2690 prgetlwpsinfo32(t, &lwpsinfo); 2691 else { 2692 lep = p->p_lwpdir[pnp->pr_common->prc_tslot].ld_entry; 2693 bzero(&lwpsinfo, sizeof (lwpsinfo)); 2694 lwpsinfo.pr_lwpid = lep->le_lwpid; 2695 lwpsinfo.pr_state = SZOMB; 2696 lwpsinfo.pr_sname = 'Z'; 2697 lwpsinfo.pr_start.tv_sec = (time32_t)lep->le_start; 2698 } 2699 prunlock(pnp); 2700 2701 return (pr_uioread(&lwpsinfo, sizeof (lwpsinfo), uiop)); 2702 } 2703 2704 static int 2705 pr_read_lwpusage_32(prnode_t *pnp, uio_t *uiop, cred_t *cr) 2706 { 2707 prhusage_t *pup; 2708 prusage32_t *upup; 2709 proc_t *p; 2710 int error; 2711 2712 ASSERT(pnp->pr_type == PR_LWPUSAGE); 2713 2714 /* allocate now, before locking the process */ 2715 pup = kmem_zalloc(sizeof (*pup), KM_SLEEP); 2716 upup = kmem_alloc(sizeof (*upup), KM_SLEEP); 2717 2718 /* 2719 * We don't want the full treatment of prlock(pnp) here. 2720 * This file is world-readable and never goes invalid. 2721 * It doesn't matter if we are in the middle of an exec(). 2722 */ 2723 p = pr_p_lock(pnp); 2724 mutex_exit(&pr_pidlock); 2725 if (p == NULL) { 2726 error = ENOENT; 2727 goto out; 2728 } 2729 ASSERT(p == pnp->pr_common->prc_proc); 2730 if (pnp->pr_common->prc_thread == NULL) { 2731 prunlock(pnp); 2732 error = ENOENT; 2733 goto out; 2734 } 2735 if (uiop->uio_offset >= sizeof (prusage32_t)) { 2736 prunlock(pnp); 2737 error = 0; 2738 goto out; 2739 } 2740 2741 pup->pr_tstamp = gethrtime(); 2742 prgetusage(pnp->pr_common->prc_thread, pup); 2743 2744 prunlock(pnp); 2745 2746 prcvtusage32(pup, upup); 2747 2748 error = pr_uioread(upup, sizeof (prusage32_t), uiop); 2749 out: 2750 kmem_free(pup, sizeof (*pup)); 2751 kmem_free(upup, sizeof (*upup)); 2752 return (error); 2753 } 2754 2755 static int 2756 pr_read_spymaster_32(prnode_t *pnp, uio_t *uiop, cred_t *cr) 2757 { 2758 psinfo32_t psinfo; 2759 int error; 2760 klwp_t *lwp; 2761 2762 ASSERT(pnp->pr_type == PR_SPYMASTER); 2763 2764 if ((error = prlock(pnp, ZNO)) != 0) 2765 return (error); 2766 2767 if (pnp->pr_common->prc_thread == NULL) { 2768 prunlock(pnp); 2769 return (0); 2770 } 2771 2772 lwp = pnp->pr_common->prc_thread->t_lwp; 2773 2774 if (lwp->lwp_spymaster == NULL) { 2775 prunlock(pnp); 2776 return (0); 2777 } 2778 2779 psinfo_kto32(lwp->lwp_spymaster, &psinfo); 2780 prunlock(pnp); 2781 2782 return (pr_uioread(&psinfo, sizeof (psinfo), uiop)); 2783 } 2784 2785 #if defined(__sparc) 2786 static int 2787 pr_read_gwindows_32(prnode_t *pnp, uio_t *uiop, cred_t *cr) 2788 { 2789 proc_t *p; 2790 kthread_t *t; 2791 gwindows32_t *gwp; 2792 int error; 2793 size_t size; 2794 2795 ASSERT(pnp->pr_type == PR_GWINDOWS); 2796 2797 gwp = kmem_zalloc(sizeof (gwindows32_t), KM_SLEEP); 2798 2799 if ((error = prlock(pnp, ZNO)) != 0) 2800 goto out; 2801 2802 p = pnp->pr_common->prc_proc; 2803 t = pnp->pr_common->prc_thread; 2804 2805 if (PROCESS_NOT_32BIT(p)) { 2806 prunlock(pnp); 2807 error = EOVERFLOW; 2808 goto out; 2809 } 2810 2811 /* 2812 * Drop p->p_lock while touching the stack. 2813 * The P_PR_LOCK flag prevents the lwp from 2814 * disappearing while we do this. 2815 */ 2816 mutex_exit(&p->p_lock); 2817 if ((size = prnwindows(ttolwp(t))) != 0) 2818 size = sizeof (gwindows32_t) - 2819 (SPARC_MAXREGWINDOW - size) * sizeof (struct rwindow32); 2820 if (uiop->uio_offset >= size) { 2821 mutex_enter(&p->p_lock); 2822 prunlock(pnp); 2823 goto out; 2824 } 2825 prgetwindows32(ttolwp(t), gwp); 2826 mutex_enter(&p->p_lock); 2827 prunlock(pnp); 2828 2829 error = pr_uioread(gwp, size, uiop); 2830 out: 2831 kmem_free(gwp, sizeof (gwindows32_t)); 2832 return (error); 2833 } 2834 #endif /* __sparc */ 2835 2836 #endif /* _SYSCALL32_IMPL */ 2837 2838 /* ARGSUSED */ 2839 static int 2840 prread(vnode_t *vp, uio_t *uiop, int ioflag, cred_t *cr, caller_context_t *ct) 2841 { 2842 prnode_t *pnp = VTOP(vp); 2843 2844 ASSERT(pnp->pr_type < PR_NFILES); 2845 2846 #ifdef _SYSCALL32_IMPL 2847 /* 2848 * What is read from the /proc files depends on the data 2849 * model of the caller. An LP64 process will see LP64 2850 * data. An ILP32 process will see ILP32 data. 2851 */ 2852 if (curproc->p_model == DATAMODEL_LP64) 2853 return (pr_read_function[pnp->pr_type](pnp, uiop, cr)); 2854 else 2855 return (pr_read_function_32[pnp->pr_type](pnp, uiop, cr)); 2856 #else 2857 return (pr_read_function[pnp->pr_type](pnp, uiop, cr)); 2858 #endif 2859 } 2860 2861 /* Note we intentionally don't handle partial writes/updates. */ 2862 static int 2863 pr_write_lwpname(prnode_t *pnp, uio_t *uiop) 2864 { 2865 kthread_t *t = NULL; 2866 char *lwpname; 2867 int error; 2868 2869 lwpname = kmem_zalloc(THREAD_NAME_MAX, KM_SLEEP); 2870 2871 if ((error = uiomove(lwpname, THREAD_NAME_MAX, UIO_WRITE, uiop)) != 0) { 2872 kmem_free(lwpname, THREAD_NAME_MAX); 2873 return (error); 2874 } 2875 2876 /* Somebody tried to write too long a thread name... */ 2877 if (lwpname[THREAD_NAME_MAX - 1] != '\0' || uiop->uio_resid > 0) { 2878 kmem_free(lwpname, THREAD_NAME_MAX); 2879 return (EIO); 2880 } 2881 2882 VERIFY3U(lwpname[THREAD_NAME_MAX - 1], ==, '\0'); 2883 2884 for (size_t i = 0; lwpname[i] != '\0'; i++) { 2885 if (!ISPRINT(lwpname[i])) { 2886 kmem_free(lwpname, THREAD_NAME_MAX); 2887 return (EINVAL); 2888 } 2889 } 2890 2891 /* Equivalent of thread_setname(), but with the ZNO magic. */ 2892 if ((error = prlock(pnp, ZNO)) != 0) { 2893 kmem_free(lwpname, THREAD_NAME_MAX); 2894 return (error); 2895 } 2896 2897 t = pnp->pr_common->prc_thread; 2898 if (t->t_name == NULL) { 2899 t->t_name = lwpname; 2900 } else { 2901 (void) strlcpy(t->t_name, lwpname, THREAD_NAME_MAX); 2902 kmem_free(lwpname, THREAD_NAME_MAX); 2903 } 2904 2905 prunlock(pnp); 2906 return (0); 2907 } 2908 2909 /* ARGSUSED */ 2910 static int 2911 prwrite(vnode_t *vp, uio_t *uiop, int ioflag, cred_t *cr, caller_context_t *ct) 2912 { 2913 prnode_t *pnp = VTOP(vp); 2914 int old = 0; 2915 int error; 2916 ssize_t resid; 2917 2918 ASSERT(pnp->pr_type < PR_NFILES); 2919 2920 /* 2921 * Only a handful of /proc files are writable, enumerate them here. 2922 */ 2923 switch (pnp->pr_type) { 2924 case PR_PIDDIR: /* directory write()s: visceral revulsion. */ 2925 ASSERT(pnp->pr_pidfile != NULL); 2926 /* use the underlying PR_PIDFILE to write the process */ 2927 vp = pnp->pr_pidfile; 2928 pnp = VTOP(vp); 2929 ASSERT(pnp->pr_type == PR_PIDFILE); 2930 /* FALLTHROUGH */ 2931 case PR_PIDFILE: 2932 case PR_LWPIDFILE: 2933 old = 1; 2934 /* FALLTHROUGH */ 2935 case PR_AS: 2936 if ((error = prlock(pnp, ZNO)) == 0) { 2937 proc_t *p = pnp->pr_common->prc_proc; 2938 struct as *as = p->p_as; 2939 2940 if ((p->p_flag & SSYS) || as == &kas) { 2941 /* 2942 * /proc I/O cannot be done to a system process. 2943 */ 2944 error = EIO; 2945 #ifdef _SYSCALL32_IMPL 2946 } else if (curproc->p_model == DATAMODEL_ILP32 && 2947 PROCESS_NOT_32BIT(p)) { 2948 error = EOVERFLOW; 2949 #endif 2950 } else { 2951 /* 2952 * See comments above (pr_read_pidfile) 2953 * about this locking dance. 2954 */ 2955 mutex_exit(&p->p_lock); 2956 error = prusrio(p, UIO_WRITE, uiop, old); 2957 mutex_enter(&p->p_lock); 2958 } 2959 prunlock(pnp); 2960 } 2961 return (error); 2962 2963 case PR_CTL: 2964 case PR_LWPCTL: 2965 resid = uiop->uio_resid; 2966 /* 2967 * Perform the action on the control file 2968 * by passing curthreads credentials 2969 * and not target process's credentials. 2970 */ 2971 #ifdef _SYSCALL32_IMPL 2972 if (curproc->p_model == DATAMODEL_ILP32) 2973 error = prwritectl32(vp, uiop, CRED()); 2974 else 2975 error = prwritectl(vp, uiop, CRED()); 2976 #else 2977 error = prwritectl(vp, uiop, CRED()); 2978 #endif 2979 /* 2980 * This hack makes sure that the EINTR is passed 2981 * all the way back to the caller's write() call. 2982 */ 2983 if (error == EINTR) 2984 uiop->uio_resid = resid; 2985 return (error); 2986 2987 case PR_LWPNAME: 2988 return (pr_write_lwpname(pnp, uiop)); 2989 2990 default: 2991 return ((vp->v_type == VDIR)? EISDIR : EBADF); 2992 } 2993 /* NOTREACHED */ 2994 } 2995 2996 static int 2997 prgetattr(vnode_t *vp, vattr_t *vap, int flags, cred_t *cr, 2998 caller_context_t *ct) 2999 { 3000 prnode_t *pnp = VTOP(vp); 3001 prnodetype_t type = pnp->pr_type; 3002 prcommon_t *pcp; 3003 proc_t *p; 3004 struct as *as; 3005 int error; 3006 vnode_t *rvp; 3007 timestruc_t now; 3008 extern uint_t nproc; 3009 int ngroups; 3010 int nsig; 3011 3012 /* 3013 * This ugly bit of code allows us to keep both versions of this 3014 * function from the same source. 3015 */ 3016 #ifdef _LP64 3017 int iam32bit = (curproc->p_model == DATAMODEL_ILP32); 3018 #define PR_OBJSIZE(obj32, obj64) \ 3019 (iam32bit ? sizeof (obj32) : sizeof (obj64)) 3020 #define PR_OBJSPAN(obj32, obj64) \ 3021 (iam32bit ? LSPAN32(obj32) : LSPAN(obj64)) 3022 #else 3023 #define PR_OBJSIZE(obj32, obj64) \ 3024 (sizeof (obj64)) 3025 #define PR_OBJSPAN(obj32, obj64) \ 3026 (LSPAN(obj64)) 3027 #endif 3028 3029 /* 3030 * Return all the attributes. Should be refined 3031 * so that it returns only those asked for. 3032 * Most of this is complete fakery anyway. 3033 */ 3034 3035 /* 3036 * For files in the /proc/<pid>/object directory, 3037 * return the attributes of the underlying object. 3038 * For files in the /proc/<pid>/fd directory, 3039 * return the attributes of the underlying file, but 3040 * make it look inaccessible if it is not a regular file. 3041 * Make directories look like symlinks. 3042 */ 3043 switch (type) { 3044 case PR_CURDIR: 3045 case PR_ROOTDIR: 3046 if (!(flags & ATTR_REAL)) 3047 break; 3048 /* restrict full knowledge of the attributes to owner or root */ 3049 if ((error = praccess(vp, 0, 0, cr, ct)) != 0) 3050 return (error); 3051 /* FALLTHROUGH */ 3052 case PR_OBJECT: 3053 case PR_FD: 3054 rvp = pnp->pr_realvp; 3055 error = VOP_GETATTR(rvp, vap, flags, cr, ct); 3056 if (error) 3057 return (error); 3058 if (type == PR_FD) { 3059 if (rvp->v_type != VREG && rvp->v_type != VDIR) 3060 vap->va_mode = 0; 3061 else 3062 vap->va_mode &= pnp->pr_mode; 3063 } 3064 if (type == PR_OBJECT) 3065 vap->va_mode &= 07555; 3066 if (rvp->v_type == VDIR && !(flags & ATTR_REAL)) { 3067 vap->va_type = VLNK; 3068 vap->va_size = 0; 3069 vap->va_nlink = 1; 3070 } 3071 return (0); 3072 default: 3073 break; 3074 } 3075 3076 bzero(vap, sizeof (*vap)); 3077 /* 3078 * Large Files: Internally proc now uses VPROC to indicate 3079 * a proc file. Since we have been returning VREG through 3080 * VOP_GETATTR() until now, we continue to do this so as 3081 * not to break apps depending on this return value. 3082 */ 3083 vap->va_type = (vp->v_type == VPROC) ? VREG : vp->v_type; 3084 vap->va_mode = pnp->pr_mode; 3085 vap->va_fsid = vp->v_vfsp->vfs_dev; 3086 vap->va_blksize = DEV_BSIZE; 3087 vap->va_rdev = 0; 3088 vap->va_seq = 0; 3089 3090 if (type == PR_PROCDIR) { 3091 vap->va_uid = 0; 3092 vap->va_gid = 0; 3093 vap->va_nlink = nproc + 2; 3094 vap->va_nodeid = (ino64_t)PRROOTINO; 3095 gethrestime(&now); 3096 vap->va_atime = vap->va_mtime = vap->va_ctime = now; 3097 vap->va_size = (v.v_proc + 2) * PRSDSIZE; 3098 vap->va_nblocks = btod(vap->va_size); 3099 return (0); 3100 } 3101 3102 /* 3103 * /proc/<pid>/self is a symbolic link, and has no prcommon member 3104 */ 3105 if (type == PR_SELF) { 3106 vap->va_uid = crgetruid(CRED()); 3107 vap->va_gid = crgetrgid(CRED()); 3108 vap->va_nodeid = (ino64_t)PR_SELF; 3109 gethrestime(&now); 3110 vap->va_atime = vap->va_mtime = vap->va_ctime = now; 3111 vap->va_nlink = 1; 3112 vap->va_type = VLNK; 3113 vap->va_size = 0; 3114 return (0); 3115 } 3116 3117 /* A subset of prlock(pnp...) */ 3118 p = pr_p_lock(pnp); 3119 mutex_exit(&pr_pidlock); 3120 if (p == NULL) 3121 return (ENOENT); 3122 pcp = pnp->pr_common; 3123 3124 /* 3125 * Because we're performing a subset of prlock() inline here, we must 3126 * follow prlock's semantics when encountering a zombie process 3127 * (PRC_DESTROY flag is set) or an exiting process (SEXITING flag is 3128 * set). Those semantics indicate acting as if the process is no 3129 * longer there (return ENOENT). 3130 * 3131 * If we chose to proceed here regardless, we may encounter issues 3132 * when we drop the p_lock (see PR_OBJECTDIR, PR_PATHDIR, PR_*MAP, 3133 * PR_LDT, and PR_*PAGEDATA below). A process-cleanup which was 3134 * blocked on p_lock may ignore the P_PR_LOCK flag we set above, since 3135 * it set one of PRC_DESTROY or SEXITING. If the process then gets 3136 * destroyed our "p" will be useless, as will its p_lock. 3137 * 3138 * It may be desirable to move this check to only places further down 3139 * prior to actual droppages of p->p_lock, but for now, we're playing 3140 * it safe and checking here immediately, like prlock() does.. 3141 */ 3142 if (((pcp->prc_flags & PRC_DESTROY) || (p->p_flag & SEXITING))) { 3143 prunlock(pnp); 3144 return (ENOENT); 3145 } 3146 3147 mutex_enter(&p->p_crlock); 3148 vap->va_uid = crgetruid(p->p_cred); 3149 vap->va_gid = crgetrgid(p->p_cred); 3150 mutex_exit(&p->p_crlock); 3151 3152 vap->va_nlink = 1; 3153 vap->va_nodeid = pnp->pr_ino? pnp->pr_ino : 3154 pmkino(pcp->prc_tslot, pcp->prc_slot, pnp->pr_type); 3155 if ((pcp->prc_flags & PRC_LWP) && pcp->prc_tslot != -1) { 3156 vap->va_atime.tv_sec = vap->va_mtime.tv_sec = 3157 vap->va_ctime.tv_sec = 3158 p->p_lwpdir[pcp->prc_tslot].ld_entry->le_start; 3159 vap->va_atime.tv_nsec = vap->va_mtime.tv_nsec = 3160 vap->va_ctime.tv_nsec = 0; 3161 } else { 3162 user_t *up = PTOU(p); 3163 vap->va_atime.tv_sec = vap->va_mtime.tv_sec = 3164 vap->va_ctime.tv_sec = up->u_start.tv_sec; 3165 vap->va_atime.tv_nsec = vap->va_mtime.tv_nsec = 3166 vap->va_ctime.tv_nsec = up->u_start.tv_nsec; 3167 } 3168 3169 switch (type) { 3170 case PR_PIDDIR: 3171 /* va_nlink: count 'lwp', 'object' and 'fd' directory links */ 3172 vap->va_nlink = 5; 3173 vap->va_size = sizeof (piddir); 3174 break; 3175 case PR_OBJECTDIR: 3176 if ((p->p_flag & SSYS) || (as = p->p_as) == &kas) 3177 vap->va_size = 2 * PRSDSIZE; 3178 else { 3179 mutex_exit(&p->p_lock); 3180 AS_LOCK_ENTER(as, RW_WRITER); 3181 if (as->a_updatedir) 3182 rebuild_objdir(as); 3183 vap->va_size = (as->a_sizedir + 2) * PRSDSIZE; 3184 AS_LOCK_EXIT(as); 3185 mutex_enter(&p->p_lock); 3186 } 3187 vap->va_nlink = 2; 3188 break; 3189 case PR_PATHDIR: 3190 if ((p->p_flag & SSYS) || (as = p->p_as) == &kas) 3191 vap->va_size = (P_FINFO(p)->fi_nfiles + 4) * PRSDSIZE; 3192 else { 3193 mutex_exit(&p->p_lock); 3194 AS_LOCK_ENTER(as, RW_WRITER); 3195 if (as->a_updatedir) 3196 rebuild_objdir(as); 3197 vap->va_size = (as->a_sizedir + 4 + 3198 P_FINFO(p)->fi_nfiles) * PRSDSIZE; 3199 AS_LOCK_EXIT(as); 3200 mutex_enter(&p->p_lock); 3201 } 3202 vap->va_nlink = 2; 3203 break; 3204 case PR_PATH: 3205 case PR_CURDIR: 3206 case PR_ROOTDIR: 3207 case PR_CT: 3208 vap->va_type = VLNK; 3209 vap->va_size = 0; 3210 break; 3211 case PR_FDDIR: 3212 case PR_FDINFODIR: 3213 vap->va_nlink = 2; 3214 vap->va_size = (P_FINFO(p)->fi_nfiles + 2) * PRSDSIZE; 3215 break; 3216 case PR_FDINFO: { 3217 file_t *fp; 3218 int fd = pnp->pr_index; 3219 3220 fp = pr_getf(p, fd, NULL); 3221 if (fp == NULL) { 3222 prunlock(pnp); 3223 return (ENOENT); 3224 } 3225 prunlock(pnp); 3226 vap->va_size = prgetfdinfosize(p, fp->f_vnode, cr); 3227 vap->va_nblocks = (fsblkcnt64_t)btod(vap->va_size); 3228 pr_releasef(fp); 3229 return (0); 3230 } 3231 case PR_LWPDIR: 3232 /* 3233 * va_nlink: count each lwp as a directory link. 3234 * va_size: size of p_lwpdir + 2 3235 */ 3236 vap->va_nlink = p->p_lwpcnt + p->p_zombcnt + 2; 3237 vap->va_size = (p->p_lwpdir_sz + 2) * PRSDSIZE; 3238 break; 3239 case PR_LWPIDDIR: 3240 vap->va_nlink = 2; 3241 vap->va_size = sizeof (lwpiddir); 3242 break; 3243 case PR_CTDIR: 3244 vap->va_nlink = 2; 3245 vap->va_size = (avl_numnodes(&p->p_ct_held) + 2) * PRSDSIZE; 3246 break; 3247 case PR_TMPLDIR: 3248 vap->va_nlink = 2; 3249 vap->va_size = (ct_ntypes + 2) * PRSDSIZE; 3250 break; 3251 case PR_AS: 3252 case PR_PIDFILE: 3253 case PR_LWPIDFILE: 3254 if ((p->p_flag & SSYS) || (as = p->p_as) == &kas) 3255 vap->va_size = 0; 3256 else 3257 vap->va_size = as->a_resvsize; 3258 break; 3259 case PR_STATUS: 3260 vap->va_size = PR_OBJSIZE(pstatus32_t, pstatus_t); 3261 break; 3262 case PR_LSTATUS: 3263 vap->va_size = PR_OBJSIZE(prheader32_t, prheader_t) + 3264 p->p_lwpcnt * PR_OBJSPAN(lwpstatus32_t, lwpstatus_t); 3265 break; 3266 case PR_PSINFO: 3267 vap->va_size = PR_OBJSIZE(psinfo32_t, psinfo_t); 3268 break; 3269 case PR_LPSINFO: 3270 vap->va_size = PR_OBJSIZE(prheader32_t, prheader_t) + 3271 (p->p_lwpcnt + p->p_zombcnt) * 3272 PR_OBJSPAN(lwpsinfo32_t, lwpsinfo_t); 3273 break; 3274 case PR_MAP: 3275 case PR_RMAP: 3276 case PR_XMAP: 3277 if ((p->p_flag & SSYS) || (as = p->p_as) == &kas) 3278 vap->va_size = 0; 3279 else { 3280 mutex_exit(&p->p_lock); 3281 AS_LOCK_ENTER(as, RW_WRITER); 3282 if (type == PR_MAP) 3283 vap->va_mtime = as->a_updatetime; 3284 if (type == PR_XMAP) 3285 vap->va_size = prnsegs(as, 0) * 3286 PR_OBJSIZE(prxmap32_t, prxmap_t); 3287 else 3288 vap->va_size = prnsegs(as, type == PR_RMAP) * 3289 PR_OBJSIZE(prmap32_t, prmap_t); 3290 AS_LOCK_EXIT(as); 3291 mutex_enter(&p->p_lock); 3292 } 3293 break; 3294 case PR_CRED: 3295 mutex_enter(&p->p_crlock); 3296 vap->va_size = sizeof (prcred_t); 3297 ngroups = crgetngroups(p->p_cred); 3298 if (ngroups > 1) 3299 vap->va_size += (ngroups - 1) * sizeof (gid_t); 3300 mutex_exit(&p->p_crlock); 3301 break; 3302 case PR_PRIV: 3303 vap->va_size = prgetprivsize(); 3304 break; 3305 case PR_SECFLAGS: 3306 vap->va_size = sizeof (prsecflags_t); 3307 break; 3308 case PR_SIGACT: 3309 nsig = PROC_IS_BRANDED(curproc)? BROP(curproc)->b_nsig : NSIG; 3310 vap->va_size = (nsig-1) * 3311 PR_OBJSIZE(struct sigaction32, struct sigaction); 3312 break; 3313 case PR_AUXV: 3314 vap->va_size = __KERN_NAUXV_IMPL * PR_OBJSIZE(auxv32_t, auxv_t); 3315 break; 3316 #if defined(__x86) 3317 case PR_LDT: 3318 mutex_exit(&p->p_lock); 3319 mutex_enter(&p->p_ldtlock); 3320 vap->va_size = prnldt(p) * sizeof (struct ssd); 3321 mutex_exit(&p->p_ldtlock); 3322 mutex_enter(&p->p_lock); 3323 break; 3324 #endif 3325 case PR_USAGE: 3326 vap->va_size = PR_OBJSIZE(prusage32_t, prusage_t); 3327 break; 3328 case PR_LUSAGE: 3329 vap->va_size = PR_OBJSIZE(prheader32_t, prheader_t) + 3330 (p->p_lwpcnt + 1) * PR_OBJSPAN(prusage32_t, prusage_t); 3331 break; 3332 case PR_PAGEDATA: 3333 if ((p->p_flag & SSYS) || (as = p->p_as) == &kas) 3334 vap->va_size = 0; 3335 else { 3336 /* 3337 * We can drop p->p_lock before grabbing the 3338 * address space lock because p->p_as will not 3339 * change while the process is marked P_PR_LOCK. 3340 */ 3341 mutex_exit(&p->p_lock); 3342 AS_LOCK_ENTER(as, RW_WRITER); 3343 #ifdef _LP64 3344 vap->va_size = iam32bit? 3345 prpdsize32(as) : prpdsize(as); 3346 #else 3347 vap->va_size = prpdsize(as); 3348 #endif 3349 AS_LOCK_EXIT(as); 3350 mutex_enter(&p->p_lock); 3351 } 3352 break; 3353 case PR_OPAGEDATA: 3354 if ((p->p_flag & SSYS) || (as = p->p_as) == &kas) 3355 vap->va_size = 0; 3356 else { 3357 mutex_exit(&p->p_lock); 3358 AS_LOCK_ENTER(as, RW_WRITER); 3359 #ifdef _LP64 3360 vap->va_size = iam32bit? 3361 oprpdsize32(as) : oprpdsize(as); 3362 #else 3363 vap->va_size = oprpdsize(as); 3364 #endif 3365 AS_LOCK_EXIT(as); 3366 mutex_enter(&p->p_lock); 3367 } 3368 break; 3369 case PR_WATCH: 3370 vap->va_size = avl_numnodes(&p->p_warea) * 3371 PR_OBJSIZE(prwatch32_t, prwatch_t); 3372 break; 3373 case PR_LWPSTATUS: 3374 vap->va_size = PR_OBJSIZE(lwpstatus32_t, lwpstatus_t); 3375 break; 3376 case PR_LWPSINFO: 3377 vap->va_size = PR_OBJSIZE(lwpsinfo32_t, lwpsinfo_t); 3378 break; 3379 case PR_LWPUSAGE: 3380 vap->va_size = PR_OBJSIZE(prusage32_t, prusage_t); 3381 break; 3382 case PR_XREGS: 3383 if (prhasx(p)) 3384 vap->va_size = prgetprxregsize(p); 3385 else 3386 vap->va_size = 0; 3387 break; 3388 case PR_SPYMASTER: 3389 if (pnp->pr_common->prc_thread != NULL && 3390 pnp->pr_common->prc_thread->t_lwp->lwp_spymaster != NULL) { 3391 vap->va_size = PR_OBJSIZE(psinfo32_t, psinfo_t); 3392 } else { 3393 vap->va_size = 0; 3394 } 3395 break; 3396 #if defined(__sparc) 3397 case PR_GWINDOWS: 3398 { 3399 kthread_t *t; 3400 int n; 3401 3402 /* 3403 * If there is no lwp then just make the size zero. 3404 * This can happen if the lwp exits between the VOP_LOOKUP() 3405 * of the /proc/<pid>/lwp/<lwpid>/gwindows file and the 3406 * VOP_GETATTR() of the resulting vnode. 3407 */ 3408 if ((t = pcp->prc_thread) == NULL) { 3409 vap->va_size = 0; 3410 break; 3411 } 3412 /* 3413 * Drop p->p_lock while touching the stack. 3414 * The P_PR_LOCK flag prevents the lwp from 3415 * disappearing while we do this. 3416 */ 3417 mutex_exit(&p->p_lock); 3418 if ((n = prnwindows(ttolwp(t))) == 0) 3419 vap->va_size = 0; 3420 else 3421 vap->va_size = PR_OBJSIZE(gwindows32_t, gwindows_t) - 3422 (SPARC_MAXREGWINDOW - n) * 3423 PR_OBJSIZE(struct rwindow32, struct rwindow); 3424 mutex_enter(&p->p_lock); 3425 break; 3426 } 3427 case PR_ASRS: 3428 #ifdef _LP64 3429 if (p->p_model == DATAMODEL_LP64) 3430 vap->va_size = sizeof (asrset_t); 3431 else 3432 #endif 3433 vap->va_size = 0; 3434 break; 3435 #endif 3436 case PR_CTL: 3437 case PR_LWPCTL: 3438 default: 3439 vap->va_size = 0; 3440 break; 3441 } 3442 3443 prunlock(pnp); 3444 vap->va_nblocks = (fsblkcnt64_t)btod(vap->va_size); 3445 return (0); 3446 } 3447 3448 static int 3449 praccess(vnode_t *vp, int mode, int flags, cred_t *cr, caller_context_t *ct) 3450 { 3451 prnode_t *pnp = VTOP(vp); 3452 prnodetype_t type = pnp->pr_type; 3453 int vmode; 3454 vtype_t vtype; 3455 proc_t *p; 3456 int error = 0; 3457 vnode_t *rvp; 3458 vnode_t *xvp; 3459 3460 if ((mode & VWRITE) && vn_is_readonly(vp)) 3461 return (EROFS); 3462 3463 switch (type) { 3464 case PR_PROCDIR: 3465 break; 3466 3467 case PR_OBJECT: 3468 case PR_FD: 3469 /* 3470 * Disallow write access to the underlying objects. 3471 * Disallow access to underlying non-regular-file fds. 3472 * Disallow access to fds with other than existing open modes. 3473 */ 3474 rvp = pnp->pr_realvp; 3475 vtype = rvp->v_type; 3476 vmode = pnp->pr_mode; 3477 if ((type == PR_OBJECT && (mode & VWRITE)) || 3478 (type == PR_FD && vtype != VREG && vtype != VDIR) || 3479 (type == PR_FD && (vmode & mode) != mode && 3480 secpolicy_proc_access(cr) != 0)) 3481 return (EACCES); 3482 return (VOP_ACCESS(rvp, mode, flags, cr, ct)); 3483 3484 case PR_PSINFO: /* these files can be read by anyone */ 3485 case PR_LPSINFO: 3486 case PR_LWPSINFO: 3487 case PR_LWPDIR: 3488 case PR_LWPIDDIR: 3489 case PR_USAGE: 3490 case PR_LUSAGE: 3491 case PR_LWPUSAGE: 3492 p = pr_p_lock(pnp); 3493 mutex_exit(&pr_pidlock); 3494 if (p == NULL) 3495 return (ENOENT); 3496 prunlock(pnp); 3497 break; 3498 3499 default: 3500 /* 3501 * Except for the world-readable files above, 3502 * only /proc/pid exists if the process is a zombie. 3503 */ 3504 if ((error = prlock(pnp, 3505 (type == PR_PIDDIR)? ZYES : ZNO)) != 0) 3506 return (error); 3507 p = pnp->pr_common->prc_proc; 3508 if (p != curproc) 3509 error = priv_proc_cred_perm(cr, p, NULL, mode); 3510 3511 if (error != 0 || p == curproc || (p->p_flag & SSYS) || 3512 p->p_as == &kas || (xvp = p->p_exec) == NULL) { 3513 prunlock(pnp); 3514 } else { 3515 /* 3516 * Determine if the process's executable is readable. 3517 * We have to drop p->p_lock before the secpolicy 3518 * and VOP operation. 3519 */ 3520 VN_HOLD(xvp); 3521 prunlock(pnp); 3522 if (secpolicy_proc_access(cr) != 0) 3523 error = VOP_ACCESS(xvp, VREAD, 0, cr, ct); 3524 VN_RELE(xvp); 3525 } 3526 if (error) 3527 return (error); 3528 break; 3529 } 3530 3531 if (type == PR_CURDIR || type == PR_ROOTDIR) { 3532 /* 3533 * Final access check on the underlying directory vnode. 3534 */ 3535 return (VOP_ACCESS(pnp->pr_realvp, mode, flags, cr, ct)); 3536 } 3537 3538 /* 3539 * Visceral revulsion: For compatibility with old /proc, 3540 * allow the /proc/<pid> directory to be opened for writing. 3541 */ 3542 vmode = pnp->pr_mode; 3543 if (type == PR_PIDDIR) 3544 vmode |= VWRITE; 3545 if ((vmode & mode) != mode) 3546 error = secpolicy_proc_access(cr); 3547 return (error); 3548 } 3549 3550 /* 3551 * Array of lookup functions, indexed by /proc file type. 3552 */ 3553 static vnode_t *pr_lookup_notdir(), *pr_lookup_procdir(), *pr_lookup_piddir(), 3554 *pr_lookup_objectdir(), *pr_lookup_lwpdir(), *pr_lookup_lwpiddir(), 3555 *pr_lookup_fddir(), *pr_lookup_fdinfodir(), *pr_lookup_pathdir(), 3556 *pr_lookup_tmpldir(), *pr_lookup_ctdir(); 3557 3558 static vnode_t *(*pr_lookup_function[PR_NFILES])() = { 3559 pr_lookup_procdir, /* /proc */ 3560 pr_lookup_notdir, /* /proc/self */ 3561 pr_lookup_piddir, /* /proc/<pid> */ 3562 pr_lookup_notdir, /* /proc/<pid>/as */ 3563 pr_lookup_notdir, /* /proc/<pid>/ctl */ 3564 pr_lookup_notdir, /* /proc/<pid>/status */ 3565 pr_lookup_notdir, /* /proc/<pid>/lstatus */ 3566 pr_lookup_notdir, /* /proc/<pid>/psinfo */ 3567 pr_lookup_notdir, /* /proc/<pid>/lpsinfo */ 3568 pr_lookup_notdir, /* /proc/<pid>/map */ 3569 pr_lookup_notdir, /* /proc/<pid>/rmap */ 3570 pr_lookup_notdir, /* /proc/<pid>/xmap */ 3571 pr_lookup_notdir, /* /proc/<pid>/cred */ 3572 pr_lookup_notdir, /* /proc/<pid>/sigact */ 3573 pr_lookup_notdir, /* /proc/<pid>/auxv */ 3574 #if defined(__x86) 3575 pr_lookup_notdir, /* /proc/<pid>/ldt */ 3576 #endif 3577 pr_lookup_notdir, /* /proc/<pid>/usage */ 3578 pr_lookup_notdir, /* /proc/<pid>/lusage */ 3579 pr_lookup_notdir, /* /proc/<pid>/pagedata */ 3580 pr_lookup_notdir, /* /proc/<pid>/watch */ 3581 pr_lookup_notdir, /* /proc/<pid>/cwd */ 3582 pr_lookup_notdir, /* /proc/<pid>/root */ 3583 pr_lookup_fddir, /* /proc/<pid>/fd */ 3584 pr_lookup_notdir, /* /proc/<pid>/fd/nn */ 3585 pr_lookup_fdinfodir, /* /proc/<pid>/fdinfo */ 3586 pr_lookup_notdir, /* /proc/<pid>/fdinfo/nn */ 3587 pr_lookup_objectdir, /* /proc/<pid>/object */ 3588 pr_lookup_notdir, /* /proc/<pid>/object/xxx */ 3589 pr_lookup_lwpdir, /* /proc/<pid>/lwp */ 3590 pr_lookup_lwpiddir, /* /proc/<pid>/lwp/<lwpid> */ 3591 pr_lookup_notdir, /* /proc/<pid>/lwp/<lwpid>/lwpctl */ 3592 pr_lookup_notdir, /* /proc/<pid>/lwp/<lwpid>/lwpname */ 3593 pr_lookup_notdir, /* /proc/<pid>/lwp/<lwpid>/lwpstatus */ 3594 pr_lookup_notdir, /* /proc/<pid>/lwp/<lwpid>/lwpsinfo */ 3595 pr_lookup_notdir, /* /proc/<pid>/lwp/<lwpid>/lwpusage */ 3596 pr_lookup_notdir, /* /proc/<pid>/lwp/<lwpid>/xregs */ 3597 pr_lookup_tmpldir, /* /proc/<pid>/lwp/<lwpid>/templates */ 3598 pr_lookup_notdir, /* /proc/<pid>/lwp/<lwpid>/templates/<id> */ 3599 pr_lookup_notdir, /* /proc/<pid>/lwp/<lwpid>/spymaster */ 3600 #if defined(__sparc) 3601 pr_lookup_notdir, /* /proc/<pid>/lwp/<lwpid>/gwindows */ 3602 pr_lookup_notdir, /* /proc/<pid>/lwp/<lwpid>/asrs */ 3603 #endif 3604 pr_lookup_notdir, /* /proc/<pid>/priv */ 3605 pr_lookup_pathdir, /* /proc/<pid>/path */ 3606 pr_lookup_notdir, /* /proc/<pid>/path/xxx */ 3607 pr_lookup_ctdir, /* /proc/<pid>/contracts */ 3608 pr_lookup_notdir, /* /proc/<pid>/contracts/<ctid> */ 3609 pr_lookup_notdir, /* /proc/<pid>/secflags */ 3610 pr_lookup_notdir, /* old process file */ 3611 pr_lookup_notdir, /* old lwp file */ 3612 pr_lookup_notdir, /* old pagedata file */ 3613 }; 3614 3615 static int 3616 prlookup(vnode_t *dp, char *comp, vnode_t **vpp, pathname_t *pathp, 3617 int flags, vnode_t *rdir, cred_t *cr, caller_context_t *ct, 3618 int *direntflags, pathname_t *realpnp) 3619 { 3620 prnode_t *pnp = VTOP(dp); 3621 prnodetype_t type = pnp->pr_type; 3622 int error; 3623 3624 ASSERT(dp->v_type == VDIR); 3625 ASSERT(type < PR_NFILES); 3626 3627 if (type != PR_PROCDIR && strcmp(comp, "..") == 0) { 3628 VN_HOLD(pnp->pr_parent); 3629 *vpp = pnp->pr_parent; 3630 return (0); 3631 } 3632 3633 if (*comp == '\0' || 3634 strcmp(comp, ".") == 0 || strcmp(comp, "..") == 0) { 3635 VN_HOLD(dp); 3636 *vpp = dp; 3637 return (0); 3638 } 3639 3640 switch (type) { 3641 case PR_CURDIR: 3642 case PR_ROOTDIR: 3643 /* restrict lookup permission to owner or root */ 3644 if ((error = praccess(dp, VEXEC, 0, cr, ct)) != 0) 3645 return (error); 3646 /* FALLTHROUGH */ 3647 case PR_FD: 3648 /* 3649 * Performing a VOP_LOOKUP on the underlying vnode and emitting 3650 * the resulting vnode, without encapsulation, as our own is a 3651 * very special case when it comes to the assumptions built 3652 * into VFS. 3653 * 3654 * Since the resulting vnode is highly likely to be at some 3655 * abitrary position in another filesystem, we insist that the 3656 * VTRAVERSE flag is set on the parent. This prevents things 3657 * such as the v_path freshness logic from mistaking the 3658 * resulting vnode as a "real" child of the parent, rather than 3659 * a consequence of this "procfs wormhole". 3660 * 3661 * Failure to establish such protections can lead to 3662 * incorrectly calculated v_paths being set on nodes reached 3663 * through these lookups. 3664 */ 3665 ASSERT((dp->v_flag & VTRAVERSE) != 0); 3666 3667 dp = pnp->pr_realvp; 3668 return (VOP_LOOKUP(dp, comp, vpp, pathp, flags, rdir, cr, ct, 3669 direntflags, realpnp)); 3670 default: 3671 break; 3672 } 3673 3674 if ((type == PR_OBJECTDIR || type == PR_FDDIR || 3675 type == PR_FDINFODIR || type == PR_PATHDIR) && 3676 (error = praccess(dp, VEXEC, 0, cr, ct)) != 0) 3677 return (error); 3678 3679 /* XXX - Do we need to pass ct, direntflags, or realpnp? */ 3680 *vpp = (pr_lookup_function[type](dp, comp)); 3681 3682 return ((*vpp == NULL) ? ENOENT : 0); 3683 } 3684 3685 /* ARGSUSED */ 3686 static int 3687 prcreate(vnode_t *dp, char *comp, vattr_t *vap, vcexcl_t excl, 3688 int mode, vnode_t **vpp, cred_t *cr, int flag, caller_context_t *ct, 3689 vsecattr_t *vsecp) 3690 { 3691 int error; 3692 3693 if ((error = prlookup(dp, comp, vpp, NULL, 0, NULL, cr, 3694 ct, NULL, NULL)) != 0) { 3695 if (error == ENOENT) { 3696 /* One can't O_CREAT nonexistent files in /proc. */ 3697 error = EACCES; 3698 } 3699 return (error); 3700 } 3701 3702 if (excl == EXCL) { 3703 /* Disallow the O_EXCL case */ 3704 error = EEXIST; 3705 } else if ((error = praccess(*vpp, mode, 0, cr, ct)) == 0) { 3706 /* Before proceeding, handle O_TRUNC if necessary. */ 3707 if (vap->va_mask & AT_SIZE) { 3708 vnode_t *vp = *vpp; 3709 3710 if (vp->v_type == VDIR) { 3711 /* Only allow O_TRUNC on files */ 3712 error = EISDIR; 3713 } else if (vp->v_type != VPROC || 3714 VTOP(vp)->pr_type != PR_FD) { 3715 /* 3716 * Disallow for files outside of the 3717 * /proc/<pid>/fd/<n> entries 3718 */ 3719 error = EACCES; 3720 } else { 3721 uint_t mask; 3722 3723 vp = VTOP(vp)->pr_realvp; 3724 mask = vap->va_mask; 3725 vap->va_mask = AT_SIZE; 3726 error = VOP_SETATTR(vp, vap, 0, cr, ct); 3727 vap->va_mask = mask; 3728 } 3729 } 3730 } 3731 3732 if (error) { 3733 VN_RELE(*vpp); 3734 *vpp = NULL; 3735 } 3736 return (error); 3737 } 3738 3739 /* ARGSUSED */ 3740 static vnode_t * 3741 pr_lookup_notdir(vnode_t *dp, char *comp) 3742 { 3743 return (NULL); 3744 } 3745 3746 /* 3747 * Find or construct a process vnode for the given pid. 3748 */ 3749 static vnode_t * 3750 pr_lookup_procdir(vnode_t *dp, char *comp) 3751 { 3752 pid_t pid; 3753 prnode_t *pnp; 3754 prcommon_t *pcp; 3755 vnode_t *vp; 3756 proc_t *p; 3757 int c; 3758 3759 ASSERT(VTOP(dp)->pr_type == PR_PROCDIR); 3760 3761 if (strcmp(comp, "self") == 0) { 3762 pnp = prgetnode(dp, PR_SELF); 3763 return (PTOV(pnp)); 3764 } else { 3765 pid = 0; 3766 while ((c = *comp++) != '\0') { 3767 if (c < '0' || c > '9') 3768 return (NULL); 3769 pid = 10*pid + c - '0'; 3770 if (pid > maxpid) 3771 return (NULL); 3772 } 3773 } 3774 3775 pnp = prgetnode(dp, PR_PIDDIR); 3776 3777 mutex_enter(&pidlock); 3778 if ((p = prfind(pid)) == NULL || p->p_stat == SIDL) { 3779 mutex_exit(&pidlock); 3780 prfreenode(pnp); 3781 return (NULL); 3782 } 3783 ASSERT(p->p_stat != 0); 3784 3785 /* NOTE: we're holding pidlock across the policy call. */ 3786 if (secpolicy_basic_procinfo(CRED(), p, curproc) != 0) { 3787 mutex_exit(&pidlock); 3788 prfreenode(pnp); 3789 return (NULL); 3790 } 3791 3792 mutex_enter(&p->p_lock); 3793 mutex_exit(&pidlock); 3794 3795 /* 3796 * If a process vnode already exists and it is not invalid 3797 * and it was created by the current process and it belongs 3798 * to the same /proc mount point as our parent vnode, then 3799 * just use it and discard the newly-allocated prnode. 3800 */ 3801 for (vp = p->p_trace; vp != NULL; vp = VTOP(vp)->pr_next) { 3802 if (!(VTOP(VTOP(vp)->pr_pidfile)->pr_flags & PR_INVAL) && 3803 VTOP(vp)->pr_owner == curproc && 3804 vp->v_vfsp == dp->v_vfsp) { 3805 ASSERT(!(VTOP(vp)->pr_flags & PR_INVAL)); 3806 VN_HOLD(vp); 3807 prfreenode(pnp); 3808 mutex_exit(&p->p_lock); 3809 return (vp); 3810 } 3811 } 3812 pnp->pr_owner = curproc; 3813 3814 /* 3815 * prgetnode() initialized most of the prnode. 3816 * Finish the job. 3817 */ 3818 pcp = pnp->pr_common; /* the newly-allocated prcommon struct */ 3819 if ((vp = p->p_trace) != NULL) { 3820 /* discard the new prcommon and use the existing prcommon */ 3821 prfreecommon(pcp); 3822 pcp = VTOP(vp)->pr_common; 3823 mutex_enter(&pcp->prc_mutex); 3824 ASSERT(pcp->prc_refcnt > 0); 3825 pcp->prc_refcnt++; 3826 mutex_exit(&pcp->prc_mutex); 3827 pnp->pr_common = pcp; 3828 } else { 3829 /* initialize the new prcommon struct */ 3830 if ((p->p_flag & SSYS) || p->p_as == &kas) 3831 pcp->prc_flags |= PRC_SYS; 3832 if (p->p_stat == SZOMB || (p->p_flag & SEXITING) != 0) 3833 pcp->prc_flags |= PRC_DESTROY; 3834 pcp->prc_proc = p; 3835 pcp->prc_datamodel = p->p_model; 3836 pcp->prc_pid = p->p_pid; 3837 pcp->prc_slot = p->p_slot; 3838 } 3839 pnp->pr_pcommon = pcp; 3840 pnp->pr_parent = dp; 3841 VN_HOLD(dp); 3842 /* 3843 * Link in the old, invalid directory vnode so we 3844 * can later determine the last close of the file. 3845 */ 3846 pnp->pr_next = p->p_trace; 3847 p->p_trace = dp = PTOV(pnp); 3848 3849 /* 3850 * Kludge for old /proc: initialize the PR_PIDFILE as well. 3851 */ 3852 vp = pnp->pr_pidfile; 3853 pnp = VTOP(vp); 3854 pnp->pr_ino = ptoi(pcp->prc_pid); 3855 pnp->pr_common = pcp; 3856 pnp->pr_pcommon = pcp; 3857 pnp->pr_parent = dp; 3858 pnp->pr_next = p->p_plist; 3859 p->p_plist = vp; 3860 3861 mutex_exit(&p->p_lock); 3862 return (dp); 3863 } 3864 3865 static vnode_t * 3866 pr_lookup_piddir(vnode_t *dp, char *comp) 3867 { 3868 prnode_t *dpnp = VTOP(dp); 3869 vnode_t *vp; 3870 prnode_t *pnp; 3871 proc_t *p; 3872 user_t *up; 3873 prdirent_t *dirp; 3874 int i; 3875 enum prnodetype type; 3876 3877 ASSERT(dpnp->pr_type == PR_PIDDIR); 3878 3879 for (i = 0; i < NPIDDIRFILES; i++) { 3880 /* Skip "." and ".." */ 3881 dirp = &piddir[i+2]; 3882 if (strcmp(comp, dirp->d_name) == 0) 3883 break; 3884 } 3885 3886 if (i >= NPIDDIRFILES) 3887 return (NULL); 3888 3889 type = (int)dirp->d_ino; 3890 pnp = prgetnode(dp, type); 3891 3892 p = pr_p_lock(dpnp); 3893 mutex_exit(&pr_pidlock); 3894 if (p == NULL) { 3895 prfreenode(pnp); 3896 return (NULL); 3897 } 3898 if (dpnp->pr_pcommon->prc_flags & PRC_DESTROY) { 3899 switch (type) { 3900 case PR_PSINFO: 3901 case PR_USAGE: 3902 break; 3903 default: 3904 prunlock(dpnp); 3905 prfreenode(pnp); 3906 return (NULL); 3907 } 3908 } 3909 3910 switch (type) { 3911 case PR_CURDIR: 3912 case PR_ROOTDIR: 3913 up = PTOU(p); 3914 vp = (type == PR_CURDIR)? up->u_cdir : 3915 (up->u_rdir? up->u_rdir : rootdir); 3916 3917 if (vp == NULL) { 3918 /* can't happen(?) */ 3919 prunlock(dpnp); 3920 prfreenode(pnp); 3921 return (NULL); 3922 } 3923 /* 3924 * Fill in the prnode so future references will 3925 * be able to find the underlying object's vnode. 3926 */ 3927 VN_HOLD(vp); 3928 pnp->pr_realvp = vp; 3929 PTOV(pnp)->v_flag |= VTRAVERSE; 3930 break; 3931 default: 3932 break; 3933 } 3934 3935 mutex_enter(&dpnp->pr_mutex); 3936 3937 if ((vp = dpnp->pr_files[i]) != NULL && 3938 !(VTOP(vp)->pr_flags & PR_INVAL)) { 3939 VN_HOLD(vp); 3940 mutex_exit(&dpnp->pr_mutex); 3941 prunlock(dpnp); 3942 prfreenode(pnp); 3943 return (vp); 3944 } 3945 3946 /* 3947 * prgetnode() initialized most of the prnode. 3948 * Finish the job. 3949 */ 3950 pnp->pr_common = dpnp->pr_common; 3951 pnp->pr_pcommon = dpnp->pr_pcommon; 3952 pnp->pr_parent = dp; 3953 VN_HOLD(dp); 3954 pnp->pr_index = i; 3955 3956 dpnp->pr_files[i] = vp = PTOV(pnp); 3957 3958 /* 3959 * Link new vnode into list of all /proc vnodes for the process. 3960 */ 3961 if (vp->v_type == VPROC) { 3962 pnp->pr_next = p->p_plist; 3963 p->p_plist = vp; 3964 } 3965 mutex_exit(&dpnp->pr_mutex); 3966 prunlock(dpnp); 3967 return (vp); 3968 } 3969 3970 static vnode_t * 3971 pr_lookup_objectdir(vnode_t *dp, char *comp) 3972 { 3973 prnode_t *dpnp = VTOP(dp); 3974 prnode_t *pnp; 3975 proc_t *p; 3976 struct seg *seg; 3977 struct as *as; 3978 vnode_t *vp; 3979 vattr_t vattr; 3980 3981 ASSERT(dpnp->pr_type == PR_OBJECTDIR); 3982 3983 pnp = prgetnode(dp, PR_OBJECT); 3984 3985 if (prlock(dpnp, ZNO) != 0) { 3986 prfreenode(pnp); 3987 return (NULL); 3988 } 3989 p = dpnp->pr_common->prc_proc; 3990 if ((p->p_flag & SSYS) || (as = p->p_as) == &kas) { 3991 prunlock(dpnp); 3992 prfreenode(pnp); 3993 return (NULL); 3994 } 3995 3996 /* 3997 * We drop p_lock before grabbing the address space lock 3998 * in order to avoid a deadlock with the clock thread. 3999 * The process will not disappear and its address space 4000 * will not change because it is marked P_PR_LOCK. 4001 */ 4002 mutex_exit(&p->p_lock); 4003 AS_LOCK_ENTER(as, RW_READER); 4004 if ((seg = AS_SEGFIRST(as)) == NULL) { 4005 vp = NULL; 4006 goto out; 4007 } 4008 if (strcmp(comp, "a.out") == 0) { 4009 vp = p->p_exec; 4010 goto out; 4011 } 4012 do { 4013 /* 4014 * Manufacture a filename for the "object" directory. 4015 */ 4016 vattr.va_mask = AT_FSID|AT_NODEID; 4017 if (seg->s_ops == &segvn_ops && 4018 SEGOP_GETVP(seg, seg->s_base, &vp) == 0 && 4019 vp != NULL && vp->v_type == VREG && 4020 VOP_GETATTR(vp, &vattr, 0, CRED(), NULL) == 0) { 4021 char name[64]; 4022 4023 if (vp == p->p_exec) /* "a.out" */ 4024 continue; 4025 pr_object_name(name, vp, &vattr); 4026 if (strcmp(name, comp) == 0) 4027 goto out; 4028 } 4029 } while ((seg = AS_SEGNEXT(as, seg)) != NULL); 4030 4031 vp = NULL; 4032 out: 4033 if (vp != NULL) { 4034 VN_HOLD(vp); 4035 } 4036 AS_LOCK_EXIT(as); 4037 mutex_enter(&p->p_lock); 4038 prunlock(dpnp); 4039 4040 if (vp == NULL) 4041 prfreenode(pnp); 4042 else { 4043 /* 4044 * Fill in the prnode so future references will 4045 * be able to find the underlying object's vnode. 4046 * Don't link this prnode into the list of all 4047 * prnodes for the process; this is a one-use node. 4048 * Its use is entirely to catch and fail opens for writing. 4049 */ 4050 pnp->pr_realvp = vp; 4051 vp = PTOV(pnp); 4052 } 4053 4054 return (vp); 4055 } 4056 4057 /* 4058 * Find or construct an lwp vnode for the given lwpid. 4059 */ 4060 static vnode_t * 4061 pr_lookup_lwpdir(vnode_t *dp, char *comp) 4062 { 4063 id_t tid; /* same type as t->t_tid */ 4064 int want_agent; 4065 prnode_t *dpnp = VTOP(dp); 4066 prnode_t *pnp; 4067 prcommon_t *pcp; 4068 vnode_t *vp; 4069 proc_t *p; 4070 kthread_t *t; 4071 lwpdir_t *ldp; 4072 lwpent_t *lep; 4073 int tslot; 4074 int c; 4075 4076 ASSERT(dpnp->pr_type == PR_LWPDIR); 4077 4078 tid = 0; 4079 if (strcmp(comp, "agent") == 0) 4080 want_agent = 1; 4081 else { 4082 want_agent = 0; 4083 while ((c = *comp++) != '\0') { 4084 id_t otid; 4085 4086 if (c < '0' || c > '9') 4087 return (NULL); 4088 otid = tid; 4089 tid = 10*tid + c - '0'; 4090 if (tid/10 != otid) /* integer overflow */ 4091 return (NULL); 4092 } 4093 } 4094 4095 pnp = prgetnode(dp, PR_LWPIDDIR); 4096 4097 p = pr_p_lock(dpnp); 4098 mutex_exit(&pr_pidlock); 4099 if (p == NULL) { 4100 prfreenode(pnp); 4101 return (NULL); 4102 } 4103 4104 if (want_agent) { 4105 if ((t = p->p_agenttp) == NULL) 4106 lep = NULL; 4107 else { 4108 tid = t->t_tid; 4109 tslot = t->t_dslot; 4110 lep = p->p_lwpdir[tslot].ld_entry; 4111 } 4112 } else { 4113 if ((ldp = lwp_hash_lookup(p, tid)) == NULL) 4114 lep = NULL; 4115 else { 4116 tslot = (int)(ldp - p->p_lwpdir); 4117 lep = ldp->ld_entry; 4118 } 4119 } 4120 4121 if (lep == NULL) { 4122 prunlock(dpnp); 4123 prfreenode(pnp); 4124 return (NULL); 4125 } 4126 4127 /* 4128 * If an lwp vnode already exists and it is not invalid 4129 * and it was created by the current process and it belongs 4130 * to the same /proc mount point as our parent vnode, then 4131 * just use it and discard the newly-allocated prnode. 4132 */ 4133 for (vp = lep->le_trace; vp != NULL; vp = VTOP(vp)->pr_next) { 4134 if (!(VTOP(vp)->pr_flags & PR_INVAL) && 4135 VTOP(vp)->pr_owner == curproc && 4136 vp->v_vfsp == dp->v_vfsp) { 4137 VN_HOLD(vp); 4138 prunlock(dpnp); 4139 prfreenode(pnp); 4140 return (vp); 4141 } 4142 } 4143 pnp->pr_owner = curproc; 4144 4145 /* 4146 * prgetnode() initialized most of the prnode. 4147 * Finish the job. 4148 */ 4149 pcp = pnp->pr_common; /* the newly-allocated prcommon struct */ 4150 if ((vp = lep->le_trace) != NULL) { 4151 /* discard the new prcommon and use the existing prcommon */ 4152 prfreecommon(pcp); 4153 pcp = VTOP(vp)->pr_common; 4154 mutex_enter(&pcp->prc_mutex); 4155 ASSERT(pcp->prc_refcnt > 0); 4156 pcp->prc_refcnt++; 4157 mutex_exit(&pcp->prc_mutex); 4158 pnp->pr_common = pcp; 4159 } else { 4160 /* initialize the new prcommon struct */ 4161 pcp->prc_flags |= PRC_LWP; 4162 if ((p->p_flag & SSYS) || p->p_as == &kas) 4163 pcp->prc_flags |= PRC_SYS; 4164 if ((t = lep->le_thread) == NULL) 4165 pcp->prc_flags |= PRC_DESTROY; 4166 pcp->prc_proc = p; 4167 pcp->prc_datamodel = dpnp->pr_pcommon->prc_datamodel; 4168 pcp->prc_pid = p->p_pid; 4169 pcp->prc_slot = p->p_slot; 4170 pcp->prc_thread = t; 4171 pcp->prc_tid = tid; 4172 pcp->prc_tslot = tslot; 4173 } 4174 pnp->pr_pcommon = dpnp->pr_pcommon; 4175 pnp->pr_parent = dp; 4176 VN_HOLD(dp); 4177 /* 4178 * Link in the old, invalid directory vnode so we 4179 * can later determine the last close of the file. 4180 */ 4181 pnp->pr_next = lep->le_trace; 4182 lep->le_trace = vp = PTOV(pnp); 4183 prunlock(dpnp); 4184 return (vp); 4185 } 4186 4187 static vnode_t * 4188 pr_lookup_lwpiddir(vnode_t *dp, char *comp) 4189 { 4190 prnode_t *dpnp = VTOP(dp); 4191 vnode_t *vp; 4192 prnode_t *pnp; 4193 proc_t *p; 4194 prdirent_t *dirp; 4195 int i; 4196 enum prnodetype type; 4197 4198 ASSERT(dpnp->pr_type == PR_LWPIDDIR); 4199 4200 for (i = 0; i < NLWPIDDIRFILES; i++) { 4201 /* Skip "." and ".." */ 4202 dirp = &lwpiddir[i+2]; 4203 if (strcmp(comp, dirp->d_name) == 0) 4204 break; 4205 } 4206 4207 if (i >= NLWPIDDIRFILES) 4208 return (NULL); 4209 4210 type = (int)dirp->d_ino; 4211 pnp = prgetnode(dp, type); 4212 4213 p = pr_p_lock(dpnp); 4214 mutex_exit(&pr_pidlock); 4215 if (p == NULL) { 4216 prfreenode(pnp); 4217 return (NULL); 4218 } 4219 if (dpnp->pr_common->prc_flags & PRC_DESTROY) { 4220 /* 4221 * Only the lwpsinfo file is present for zombie lwps. 4222 * Nothing is present if the lwp has been reaped. 4223 */ 4224 if (dpnp->pr_common->prc_tslot == -1 || 4225 type != PR_LWPSINFO) { 4226 prunlock(dpnp); 4227 prfreenode(pnp); 4228 return (NULL); 4229 } 4230 } 4231 4232 #if defined(__sparc) 4233 /* the asrs file exists only for sparc v9 _LP64 processes */ 4234 if (type == PR_ASRS && p->p_model != DATAMODEL_LP64) { 4235 prunlock(dpnp); 4236 prfreenode(pnp); 4237 return (NULL); 4238 } 4239 #endif 4240 4241 mutex_enter(&dpnp->pr_mutex); 4242 4243 if ((vp = dpnp->pr_files[i]) != NULL && 4244 !(VTOP(vp)->pr_flags & PR_INVAL)) { 4245 VN_HOLD(vp); 4246 mutex_exit(&dpnp->pr_mutex); 4247 prunlock(dpnp); 4248 prfreenode(pnp); 4249 return (vp); 4250 } 4251 4252 /* 4253 * prgetnode() initialized most of the prnode. 4254 * Finish the job. 4255 */ 4256 pnp->pr_common = dpnp->pr_common; 4257 pnp->pr_pcommon = dpnp->pr_pcommon; 4258 pnp->pr_parent = dp; 4259 VN_HOLD(dp); 4260 pnp->pr_index = i; 4261 4262 dpnp->pr_files[i] = vp = PTOV(pnp); 4263 4264 /* 4265 * Link new vnode into list of all /proc vnodes for the process. 4266 */ 4267 if (vp->v_type == VPROC) { 4268 pnp->pr_next = p->p_plist; 4269 p->p_plist = vp; 4270 } 4271 mutex_exit(&dpnp->pr_mutex); 4272 prunlock(dpnp); 4273 return (vp); 4274 } 4275 4276 /* 4277 * Lookup one of the process's file vnodes. 4278 */ 4279 static vnode_t * 4280 pr_lookup_fddir(vnode_t *dp, char *comp) 4281 { 4282 prnode_t *dpnp = VTOP(dp); 4283 prnode_t *pnp; 4284 vnode_t *vp = NULL; 4285 proc_t *p; 4286 file_t *fp; 4287 uint_t fd; 4288 int c; 4289 4290 ASSERT(dpnp->pr_type == PR_FDDIR); 4291 4292 fd = 0; 4293 while ((c = *comp++) != '\0') { 4294 int ofd; 4295 if (c < '0' || c > '9') 4296 return (NULL); 4297 ofd = fd; 4298 fd = 10 * fd + c - '0'; 4299 if (fd / 10 != ofd) /* integer overflow */ 4300 return (NULL); 4301 } 4302 4303 pnp = prgetnode(dp, PR_FD); 4304 4305 if (prlock(dpnp, ZNO) != 0) { 4306 prfreenode(pnp); 4307 return (NULL); 4308 } 4309 p = dpnp->pr_common->prc_proc; 4310 if ((p->p_flag & SSYS) || p->p_as == &kas) { 4311 prunlock(dpnp); 4312 prfreenode(pnp); 4313 return (NULL); 4314 } 4315 4316 if ((fp = pr_getf(p, fd, NULL)) != NULL) { 4317 pnp->pr_mode = 07111; 4318 if (fp->f_flag & FREAD) 4319 pnp->pr_mode |= 0444; 4320 if (fp->f_flag & FWRITE) 4321 pnp->pr_mode |= 0222; 4322 vp = fp->f_vnode; 4323 VN_HOLD(vp); 4324 } 4325 4326 prunlock(dpnp); 4327 if (fp != NULL) { 4328 pr_releasef(fp); 4329 } 4330 4331 if (vp == NULL) { 4332 prfreenode(pnp); 4333 return (NULL); 4334 } 4335 4336 /* 4337 * Fill in the prnode so future references will 4338 * be able to find the underlying object's vnode. 4339 * Don't link this prnode into the list of all 4340 * prnodes for the process; this is a one-use node. 4341 */ 4342 pnp->pr_realvp = vp; 4343 pnp->pr_parent = dp; /* needed for prlookup */ 4344 VN_HOLD(dp); 4345 vp = PTOV(pnp); 4346 if (pnp->pr_realvp->v_type == VDIR) { 4347 vp->v_type = VDIR; 4348 vp->v_flag |= VTRAVERSE; 4349 } 4350 4351 return (vp); 4352 } 4353 4354 static vnode_t * 4355 pr_lookup_fdinfodir(vnode_t *dp, char *comp) 4356 { 4357 prnode_t *dpnp = VTOP(dp); 4358 prnode_t *pnp; 4359 vnode_t *vp = NULL; 4360 proc_t *p; 4361 uint_t fd; 4362 int c; 4363 4364 ASSERT(dpnp->pr_type == PR_FDINFODIR); 4365 4366 fd = 0; 4367 while ((c = *comp++) != '\0') { 4368 int ofd; 4369 if (c < '0' || c > '9') 4370 return (NULL); 4371 ofd = fd; 4372 fd = 10 * fd + c - '0'; 4373 if (fd / 10 != ofd) /* integer overflow */ 4374 return (NULL); 4375 } 4376 4377 pnp = prgetnode(dp, PR_FDINFO); 4378 4379 if (prlock(dpnp, ZNO) != 0) { 4380 prfreenode(pnp); 4381 return (NULL); 4382 } 4383 p = dpnp->pr_common->prc_proc; 4384 if ((p->p_flag & SSYS) || p->p_as == &kas) { 4385 prunlock(dpnp); 4386 prfreenode(pnp); 4387 return (NULL); 4388 } 4389 4390 /* 4391 * Don't link this prnode into the list of all 4392 * prnodes for the process; this is a one-use node. 4393 * Unlike the FDDIR case, the underlying vnode is not stored in 4394 * pnp->pr_realvp. Instead, the fd number is stored in pnp->pr_index 4395 * and used by pr_read_fdinfo() to return information for the right 4396 * file descriptor. 4397 */ 4398 pnp->pr_common = dpnp->pr_common; 4399 pnp->pr_pcommon = dpnp->pr_pcommon; 4400 pnp->pr_parent = dp; 4401 pnp->pr_index = fd; 4402 VN_HOLD(dp); 4403 prunlock(dpnp); 4404 vp = PTOV(pnp); 4405 4406 return (vp); 4407 } 4408 4409 static vnode_t * 4410 pr_lookup_pathdir(vnode_t *dp, char *comp) 4411 { 4412 prnode_t *dpnp = VTOP(dp); 4413 prnode_t *pnp; 4414 vnode_t *vp = NULL; 4415 proc_t *p; 4416 uint_t fd, flags = 0; 4417 int c; 4418 uf_entry_t *ufp; 4419 uf_info_t *fip; 4420 enum { NAME_FD, NAME_OBJECT, NAME_ROOT, NAME_CWD, NAME_UNKNOWN } type; 4421 char *tmp; 4422 int idx; 4423 struct seg *seg; 4424 struct as *as = NULL; 4425 vattr_t vattr; 4426 4427 ASSERT(dpnp->pr_type == PR_PATHDIR); 4428 4429 /* 4430 * First, check if this is a numeric entry, in which case we have a 4431 * file descriptor. 4432 */ 4433 fd = 0; 4434 type = NAME_FD; 4435 tmp = comp; 4436 while ((c = *tmp++) != '\0') { 4437 int ofd; 4438 if (c < '0' || c > '9') { 4439 type = NAME_UNKNOWN; 4440 break; 4441 } 4442 ofd = fd; 4443 fd = 10*fd + c - '0'; 4444 if (fd/10 != ofd) { /* integer overflow */ 4445 type = NAME_UNKNOWN; 4446 break; 4447 } 4448 } 4449 4450 /* 4451 * Next, see if it is one of the special values {root, cwd}. 4452 */ 4453 if (type == NAME_UNKNOWN) { 4454 if (strcmp(comp, "root") == 0) 4455 type = NAME_ROOT; 4456 else if (strcmp(comp, "cwd") == 0) 4457 type = NAME_CWD; 4458 } 4459 4460 /* 4461 * Grab the necessary data from the process 4462 */ 4463 if (prlock(dpnp, ZNO) != 0) 4464 return (NULL); 4465 p = dpnp->pr_common->prc_proc; 4466 4467 fip = P_FINFO(p); 4468 4469 switch (type) { 4470 case NAME_ROOT: 4471 if ((vp = PTOU(p)->u_rdir) == NULL) 4472 vp = p->p_zone->zone_rootvp; 4473 VN_HOLD(vp); 4474 break; 4475 case NAME_CWD: 4476 vp = PTOU(p)->u_cdir; 4477 VN_HOLD(vp); 4478 break; 4479 default: 4480 if ((p->p_flag & SSYS) || (as = p->p_as) == &kas) { 4481 prunlock(dpnp); 4482 return (NULL); 4483 } 4484 } 4485 mutex_exit(&p->p_lock); 4486 4487 /* 4488 * Determine if this is an object entry 4489 */ 4490 if (type == NAME_UNKNOWN) { 4491 /* 4492 * Start with the inode index immediately after the number of 4493 * files. 4494 */ 4495 mutex_enter(&fip->fi_lock); 4496 idx = fip->fi_nfiles + 4; 4497 mutex_exit(&fip->fi_lock); 4498 4499 if (strcmp(comp, "a.out") == 0) { 4500 if (p->p_execdir != NULL) { 4501 vp = p->p_execdir; 4502 VN_HOLD(vp); 4503 type = NAME_OBJECT; 4504 flags |= PR_AOUT; 4505 } else { 4506 vp = p->p_exec; 4507 VN_HOLD(vp); 4508 type = NAME_OBJECT; 4509 } 4510 } else { 4511 AS_LOCK_ENTER(as, RW_READER); 4512 if ((seg = AS_SEGFIRST(as)) != NULL) { 4513 do { 4514 /* 4515 * Manufacture a filename for the 4516 * "object" directory. 4517 */ 4518 vattr.va_mask = AT_FSID|AT_NODEID; 4519 if (seg->s_ops == &segvn_ops && 4520 SEGOP_GETVP(seg, seg->s_base, &vp) 4521 == 0 && 4522 vp != NULL && vp->v_type == VREG && 4523 VOP_GETATTR(vp, &vattr, 0, CRED(), 4524 NULL) == 0) { 4525 char name[64]; 4526 4527 if (vp == p->p_exec) 4528 continue; 4529 idx++; 4530 pr_object_name(name, vp, 4531 &vattr); 4532 if (strcmp(name, comp) == 0) 4533 break; 4534 } 4535 } while ((seg = AS_SEGNEXT(as, seg)) != NULL); 4536 } 4537 4538 if (seg == NULL) { 4539 vp = NULL; 4540 } else { 4541 VN_HOLD(vp); 4542 type = NAME_OBJECT; 4543 } 4544 4545 AS_LOCK_EXIT(as); 4546 } 4547 } 4548 4549 4550 switch (type) { 4551 case NAME_FD: 4552 mutex_enter(&fip->fi_lock); 4553 if (fd < fip->fi_nfiles) { 4554 UF_ENTER(ufp, fip, fd); 4555 if (ufp->uf_file != NULL) { 4556 vp = ufp->uf_file->f_vnode; 4557 VN_HOLD(vp); 4558 } 4559 UF_EXIT(ufp); 4560 } 4561 mutex_exit(&fip->fi_lock); 4562 idx = fd + 4; 4563 break; 4564 case NAME_ROOT: 4565 idx = 2; 4566 break; 4567 case NAME_CWD: 4568 idx = 3; 4569 break; 4570 case NAME_OBJECT: 4571 case NAME_UNKNOWN: 4572 /* Nothing to do */ 4573 break; 4574 } 4575 4576 mutex_enter(&p->p_lock); 4577 prunlock(dpnp); 4578 4579 if (vp != NULL) { 4580 pnp = prgetnode(dp, PR_PATH); 4581 4582 pnp->pr_flags |= flags; 4583 pnp->pr_common = dpnp->pr_common; 4584 pnp->pr_pcommon = dpnp->pr_pcommon; 4585 pnp->pr_realvp = vp; 4586 pnp->pr_parent = dp; /* needed for prlookup */ 4587 pnp->pr_ino = pmkino(idx, dpnp->pr_common->prc_slot, PR_PATH); 4588 VN_HOLD(dp); 4589 vp = PTOV(pnp); 4590 vp->v_type = VLNK; 4591 } 4592 4593 return (vp); 4594 } 4595 4596 /* 4597 * Look up one of the process's active templates. 4598 */ 4599 static vnode_t * 4600 pr_lookup_tmpldir(vnode_t *dp, char *comp) 4601 { 4602 prnode_t *dpnp = VTOP(dp); 4603 prnode_t *pnp; 4604 vnode_t *vp = NULL; 4605 proc_t *p; 4606 int i; 4607 4608 ASSERT(dpnp->pr_type == PR_TMPLDIR); 4609 4610 for (i = 0; i < ct_ntypes; i++) 4611 if (strcmp(comp, ct_types[i]->ct_type_name) == 0) 4612 break; 4613 if (i == ct_ntypes) 4614 return (NULL); 4615 4616 pnp = prgetnode(dp, PR_TMPL); 4617 4618 if (prlock(dpnp, ZNO) != 0) { 4619 prfreenode(pnp); 4620 return (NULL); 4621 } 4622 p = dpnp->pr_common->prc_proc; 4623 if ((p->p_flag & SSYS) || p->p_as == &kas || 4624 (dpnp->pr_common->prc_flags & (PRC_DESTROY | PRC_LWP)) != PRC_LWP) { 4625 prunlock(dpnp); 4626 prfreenode(pnp); 4627 return (NULL); 4628 } 4629 if (ttolwp(dpnp->pr_common->prc_thread)->lwp_ct_active[i] != NULL) { 4630 pnp->pr_common = dpnp->pr_common; 4631 pnp->pr_pcommon = dpnp->pr_pcommon; 4632 pnp->pr_parent = dp; 4633 pnp->pr_cttype = i; 4634 VN_HOLD(dp); 4635 vp = PTOV(pnp); 4636 } else { 4637 prfreenode(pnp); 4638 } 4639 prunlock(dpnp); 4640 4641 return (vp); 4642 } 4643 4644 /* 4645 * Look up one of the contracts owned by the process. 4646 */ 4647 static vnode_t * 4648 pr_lookup_ctdir(vnode_t *dp, char *comp) 4649 { 4650 prnode_t *dpnp = VTOP(dp); 4651 prnode_t *pnp; 4652 vnode_t *vp = NULL; 4653 proc_t *p; 4654 id_t id = 0; 4655 contract_t *ct; 4656 int c; 4657 4658 ASSERT(dpnp->pr_type == PR_CTDIR); 4659 4660 while ((c = *comp++) != '\0') { 4661 id_t oid; 4662 if (c < '0' || c > '9') 4663 return (NULL); 4664 oid = id; 4665 id = 10 * id + c - '0'; 4666 if (id / 10 != oid) /* integer overflow */ 4667 return (NULL); 4668 } 4669 4670 /* 4671 * Search all contracts; we'll filter below. 4672 */ 4673 ct = contract_ptr(id, GLOBAL_ZONEUNIQID); 4674 if (ct == NULL) 4675 return (NULL); 4676 4677 pnp = prgetnode(dp, PR_CT); 4678 4679 if (prlock(dpnp, ZNO) != 0) { 4680 prfreenode(pnp); 4681 contract_rele(ct); 4682 return (NULL); 4683 } 4684 p = dpnp->pr_common->prc_proc; 4685 /* 4686 * We only allow lookups of contracts owned by this process, or, 4687 * if we are zsched and this is a zone's procfs, contracts on 4688 * stuff in the zone which are held by processes or contracts 4689 * outside the zone. (see logic in contract_status_common) 4690 */ 4691 if ((ct->ct_owner != p) && 4692 !(p == VTOZONE(dp)->zone_zsched && ct->ct_state < CTS_ORPHAN && 4693 VTOZONE(dp)->zone_uniqid == contract_getzuniqid(ct) && 4694 VTOZONE(dp)->zone_uniqid != GLOBAL_ZONEUNIQID && 4695 ct->ct_czuniqid == GLOBAL_ZONEUNIQID)) { 4696 prunlock(dpnp); 4697 prfreenode(pnp); 4698 contract_rele(ct); 4699 return (NULL); 4700 } 4701 pnp->pr_common = dpnp->pr_common; 4702 pnp->pr_pcommon = dpnp->pr_pcommon; 4703 pnp->pr_contract = ct; 4704 pnp->pr_parent = dp; 4705 pnp->pr_ino = pmkino(id, pnp->pr_common->prc_slot, PR_CT); 4706 VN_HOLD(dp); 4707 prunlock(dpnp); 4708 vp = PTOV(pnp); 4709 4710 return (vp); 4711 } 4712 4713 /* 4714 * Construct an lwp vnode for the old /proc interface. 4715 * We stand on our head to make the /proc plumbing correct. 4716 */ 4717 vnode_t * 4718 prlwpnode(prnode_t *pnp, uint_t tid) 4719 { 4720 char comp[12]; 4721 vnode_t *dp; 4722 vnode_t *vp; 4723 prcommon_t *pcp; 4724 proc_t *p; 4725 4726 /* 4727 * Lookup the /proc/<pid>/lwp/<lwpid> directory vnode. 4728 */ 4729 if (pnp->pr_type == PR_PIDFILE) { 4730 dp = pnp->pr_parent; /* /proc/<pid> */ 4731 VN_HOLD(dp); 4732 vp = pr_lookup_piddir(dp, "lwp"); 4733 VN_RELE(dp); 4734 if ((dp = vp) == NULL) /* /proc/<pid>/lwp */ 4735 return (NULL); 4736 } else if (pnp->pr_type == PR_LWPIDFILE) { 4737 dp = pnp->pr_parent; /* /proc/<pid>/lwp/<lwpid> */ 4738 dp = VTOP(dp)->pr_parent; /* /proc/<pid>/lwp */ 4739 VN_HOLD(dp); 4740 } else { 4741 return (NULL); 4742 } 4743 4744 (void) pr_u32tos(tid, comp, sizeof (comp)); 4745 vp = pr_lookup_lwpdir(dp, comp); 4746 VN_RELE(dp); 4747 if ((dp = vp) == NULL) 4748 return (NULL); 4749 4750 pnp = prgetnode(dp, PR_LWPIDFILE); 4751 vp = PTOV(pnp); 4752 4753 /* 4754 * prgetnode() initialized most of the prnode. 4755 * Finish the job. 4756 */ 4757 pcp = VTOP(dp)->pr_common; 4758 pnp->pr_ino = ptoi(pcp->prc_pid); 4759 pnp->pr_common = pcp; 4760 pnp->pr_pcommon = VTOP(dp)->pr_pcommon; 4761 pnp->pr_parent = dp; 4762 /* 4763 * Link new vnode into list of all /proc vnodes for the process. 4764 */ 4765 p = pr_p_lock(pnp); 4766 mutex_exit(&pr_pidlock); 4767 if (p == NULL) { 4768 VN_RELE(dp); 4769 prfreenode(pnp); 4770 vp = NULL; 4771 } else if (pcp->prc_thread == NULL) { 4772 prunlock(pnp); 4773 VN_RELE(dp); 4774 prfreenode(pnp); 4775 vp = NULL; 4776 } else { 4777 pnp->pr_next = p->p_plist; 4778 p->p_plist = vp; 4779 prunlock(pnp); 4780 } 4781 4782 return (vp); 4783 } 4784 4785 #if defined(DEBUG) 4786 4787 static uint32_t nprnode; 4788 static uint32_t nprcommon; 4789 4790 #define INCREMENT(x) atomic_inc_32(&x); 4791 #define DECREMENT(x) atomic_dec_32(&x); 4792 4793 #else 4794 4795 #define INCREMENT(x) 4796 #define DECREMENT(x) 4797 4798 #endif /* DEBUG */ 4799 4800 /* 4801 * New /proc vnode required; allocate it and fill in most of the fields. 4802 */ 4803 prnode_t * 4804 prgetnode(vnode_t *dp, prnodetype_t type) 4805 { 4806 prnode_t *pnp; 4807 prcommon_t *pcp; 4808 vnode_t *vp; 4809 ulong_t nfiles; 4810 4811 INCREMENT(nprnode); 4812 pnp = kmem_zalloc(sizeof (prnode_t), KM_SLEEP); 4813 4814 mutex_init(&pnp->pr_mutex, NULL, MUTEX_DEFAULT, NULL); 4815 pnp->pr_type = type; 4816 4817 pnp->pr_vnode = vn_alloc(KM_SLEEP); 4818 4819 vp = PTOV(pnp); 4820 vp->v_flag = VNOCACHE|VNOMAP|VNOSWAP|VNOMOUNT; 4821 vn_setops(vp, prvnodeops); 4822 vp->v_vfsp = dp->v_vfsp; 4823 vp->v_type = VPROC; 4824 vp->v_data = (caddr_t)pnp; 4825 4826 switch (type) { 4827 case PR_PIDDIR: 4828 case PR_LWPIDDIR: 4829 /* 4830 * We need a prcommon and a files array for each of these. 4831 */ 4832 INCREMENT(nprcommon); 4833 4834 pcp = kmem_zalloc(sizeof (prcommon_t), KM_SLEEP); 4835 pcp->prc_refcnt = 1; 4836 pnp->pr_common = pcp; 4837 mutex_init(&pcp->prc_mutex, NULL, MUTEX_DEFAULT, NULL); 4838 cv_init(&pcp->prc_wait, NULL, CV_DEFAULT, NULL); 4839 4840 nfiles = (type == PR_PIDDIR)? NPIDDIRFILES : NLWPIDDIRFILES; 4841 pnp->pr_files = 4842 kmem_zalloc(nfiles * sizeof (vnode_t *), KM_SLEEP); 4843 4844 vp->v_type = VDIR; 4845 /* 4846 * Mode should be read-search by all, but we cannot so long 4847 * as we must support compatibility mode with old /proc. 4848 * Make /proc/<pid> be read by owner only, search by all. 4849 * Make /proc/<pid>/lwp/<lwpid> read-search by all. Also, 4850 * set VDIROPEN on /proc/<pid> so it can be opened for writing. 4851 */ 4852 if (type == PR_PIDDIR) { 4853 /* kludge for old /proc interface */ 4854 prnode_t *xpnp = prgetnode(dp, PR_PIDFILE); 4855 pnp->pr_pidfile = PTOV(xpnp); 4856 pnp->pr_mode = 0511; 4857 vp->v_flag |= VDIROPEN; 4858 } else { 4859 pnp->pr_mode = 0555; 4860 } 4861 4862 break; 4863 4864 case PR_CURDIR: 4865 case PR_ROOTDIR: 4866 case PR_FDDIR: 4867 case PR_FDINFODIR: 4868 case PR_OBJECTDIR: 4869 case PR_PATHDIR: 4870 case PR_CTDIR: 4871 case PR_TMPLDIR: 4872 vp->v_type = VDIR; 4873 pnp->pr_mode = 0500; /* read-search by owner only */ 4874 break; 4875 4876 case PR_CT: 4877 vp->v_type = VLNK; 4878 pnp->pr_mode = 0500; /* read-search by owner only */ 4879 break; 4880 4881 case PR_PATH: 4882 case PR_SELF: 4883 vp->v_type = VLNK; 4884 pnp->pr_mode = 0777; 4885 break; 4886 4887 case PR_LWPDIR: 4888 vp->v_type = VDIR; 4889 pnp->pr_mode = 0555; /* read-search by all */ 4890 break; 4891 4892 case PR_AS: 4893 case PR_TMPL: 4894 pnp->pr_mode = 0600; /* read-write by owner only */ 4895 break; 4896 4897 case PR_CTL: 4898 case PR_LWPCTL: 4899 pnp->pr_mode = 0200; /* write-only by owner only */ 4900 break; 4901 4902 case PR_PIDFILE: 4903 case PR_LWPIDFILE: 4904 pnp->pr_mode = 0600; /* read-write by owner only */ 4905 break; 4906 4907 case PR_LWPNAME: 4908 pnp->pr_mode = 0644; /* readable by all + owner can write */ 4909 break; 4910 4911 case PR_PSINFO: 4912 case PR_LPSINFO: 4913 case PR_LWPSINFO: 4914 case PR_USAGE: 4915 case PR_LUSAGE: 4916 case PR_LWPUSAGE: 4917 pnp->pr_mode = 0444; /* read-only by all */ 4918 break; 4919 4920 default: 4921 pnp->pr_mode = 0400; /* read-only by owner only */ 4922 break; 4923 } 4924 vn_exists(vp); 4925 return (pnp); 4926 } 4927 4928 /* 4929 * Free the storage obtained from prgetnode(). 4930 */ 4931 void 4932 prfreenode(prnode_t *pnp) 4933 { 4934 vnode_t *vp; 4935 ulong_t nfiles; 4936 4937 vn_invalid(PTOV(pnp)); 4938 vn_free(PTOV(pnp)); 4939 mutex_destroy(&pnp->pr_mutex); 4940 4941 switch (pnp->pr_type) { 4942 case PR_PIDDIR: 4943 /* kludge for old /proc interface */ 4944 if (pnp->pr_pidfile != NULL) { 4945 prfreenode(VTOP(pnp->pr_pidfile)); 4946 pnp->pr_pidfile = NULL; 4947 } 4948 /* FALLTHROUGH */ 4949 case PR_LWPIDDIR: 4950 /* 4951 * We allocated a prcommon and a files array for each of these. 4952 */ 4953 prfreecommon(pnp->pr_common); 4954 nfiles = (pnp->pr_type == PR_PIDDIR)? 4955 NPIDDIRFILES : NLWPIDDIRFILES; 4956 kmem_free(pnp->pr_files, nfiles * sizeof (vnode_t *)); 4957 break; 4958 default: 4959 break; 4960 } 4961 /* 4962 * If there is an underlying vnode, be sure 4963 * to release it after freeing the prnode. 4964 */ 4965 vp = pnp->pr_realvp; 4966 kmem_free(pnp, sizeof (*pnp)); 4967 DECREMENT(nprnode); 4968 if (vp != NULL) { 4969 VN_RELE(vp); 4970 } 4971 } 4972 4973 /* 4974 * Free a prcommon structure, if the reference count reaches zero. 4975 */ 4976 static void 4977 prfreecommon(prcommon_t *pcp) 4978 { 4979 mutex_enter(&pcp->prc_mutex); 4980 ASSERT(pcp->prc_refcnt > 0); 4981 if (--pcp->prc_refcnt != 0) 4982 mutex_exit(&pcp->prc_mutex); 4983 else { 4984 mutex_exit(&pcp->prc_mutex); 4985 4986 ASSERT(pcp->prc_refcnt == 0); 4987 ASSERT(pcp->prc_selfopens == 0 && pcp->prc_writers == 0); 4988 4989 pollhead_clean(&pcp->prc_pollhead); 4990 mutex_destroy(&pcp->prc_mutex); 4991 cv_destroy(&pcp->prc_wait); 4992 kmem_free(pcp, sizeof (prcommon_t)); 4993 DECREMENT(nprcommon); 4994 } 4995 } 4996 4997 /* 4998 * Array of readdir functions, indexed by /proc file type. 4999 */ 5000 static int pr_readdir_notdir(), pr_readdir_procdir(), pr_readdir_piddir(), 5001 pr_readdir_objectdir(), pr_readdir_lwpdir(), pr_readdir_lwpiddir(), 5002 pr_readdir_fddir(), pr_readdir_fdinfodir(), pr_readdir_pathdir(), 5003 pr_readdir_tmpldir(), pr_readdir_ctdir(); 5004 5005 static int (*pr_readdir_function[PR_NFILES])() = { 5006 pr_readdir_procdir, /* /proc */ 5007 pr_readdir_notdir, /* /proc/self */ 5008 pr_readdir_piddir, /* /proc/<pid> */ 5009 pr_readdir_notdir, /* /proc/<pid>/as */ 5010 pr_readdir_notdir, /* /proc/<pid>/ctl */ 5011 pr_readdir_notdir, /* /proc/<pid>/status */ 5012 pr_readdir_notdir, /* /proc/<pid>/lstatus */ 5013 pr_readdir_notdir, /* /proc/<pid>/psinfo */ 5014 pr_readdir_notdir, /* /proc/<pid>/lpsinfo */ 5015 pr_readdir_notdir, /* /proc/<pid>/map */ 5016 pr_readdir_notdir, /* /proc/<pid>/rmap */ 5017 pr_readdir_notdir, /* /proc/<pid>/xmap */ 5018 pr_readdir_notdir, /* /proc/<pid>/cred */ 5019 pr_readdir_notdir, /* /proc/<pid>/sigact */ 5020 pr_readdir_notdir, /* /proc/<pid>/auxv */ 5021 #if defined(__x86) 5022 pr_readdir_notdir, /* /proc/<pid>/ldt */ 5023 #endif 5024 pr_readdir_notdir, /* /proc/<pid>/usage */ 5025 pr_readdir_notdir, /* /proc/<pid>/lusage */ 5026 pr_readdir_notdir, /* /proc/<pid>/pagedata */ 5027 pr_readdir_notdir, /* /proc/<pid>/watch */ 5028 pr_readdir_notdir, /* /proc/<pid>/cwd */ 5029 pr_readdir_notdir, /* /proc/<pid>/root */ 5030 pr_readdir_fddir, /* /proc/<pid>/fd */ 5031 pr_readdir_notdir, /* /proc/<pid>/fd/nn */ 5032 pr_readdir_fdinfodir, /* /proc/<pid>/fdinfo */ 5033 pr_readdir_notdir, /* /proc/<pid>/fdinfo/nn */ 5034 pr_readdir_objectdir, /* /proc/<pid>/object */ 5035 pr_readdir_notdir, /* /proc/<pid>/object/xxx */ 5036 pr_readdir_lwpdir, /* /proc/<pid>/lwp */ 5037 pr_readdir_lwpiddir, /* /proc/<pid>/lwp/<lwpid> */ 5038 pr_readdir_notdir, /* /proc/<pid>/lwp/<lwpid>/lwpctl */ 5039 pr_readdir_notdir, /* /proc/<pid>/lwp/<lwpid>/lwpname */ 5040 pr_readdir_notdir, /* /proc/<pid>/lwp/<lwpid>/lwpstatus */ 5041 pr_readdir_notdir, /* /proc/<pid>/lwp/<lwpid>/lwpsinfo */ 5042 pr_readdir_notdir, /* /proc/<pid>/lwp/<lwpid>/lwpusage */ 5043 pr_readdir_notdir, /* /proc/<pid>/lwp/<lwpid>/xregs */ 5044 pr_readdir_tmpldir, /* /proc/<pid>/lwp/<lwpid>/templates */ 5045 pr_readdir_notdir, /* /proc/<pid>/lwp/<lwpid>/templates/<id> */ 5046 pr_readdir_notdir, /* /proc/<pid>/lwp/<lwpid>/spymaster */ 5047 #if defined(__sparc) 5048 pr_readdir_notdir, /* /proc/<pid>/lwp/<lwpid>/gwindows */ 5049 pr_readdir_notdir, /* /proc/<pid>/lwp/<lwpid>/asrs */ 5050 #endif 5051 pr_readdir_notdir, /* /proc/<pid>/priv */ 5052 pr_readdir_pathdir, /* /proc/<pid>/path */ 5053 pr_readdir_notdir, /* /proc/<pid>/path/xxx */ 5054 pr_readdir_ctdir, /* /proc/<pid>/contracts */ 5055 pr_readdir_notdir, /* /proc/<pid>/contracts/<ctid> */ 5056 pr_readdir_notdir, /* /proc/<pid>/secflags */ 5057 pr_readdir_notdir, /* old process file */ 5058 pr_readdir_notdir, /* old lwp file */ 5059 pr_readdir_notdir, /* old pagedata file */ 5060 }; 5061 5062 /* ARGSUSED */ 5063 static int 5064 prreaddir(vnode_t *vp, uio_t *uiop, cred_t *cr, int *eofp, 5065 caller_context_t *ct, int flags) 5066 { 5067 prnode_t *pnp = VTOP(vp); 5068 5069 ASSERT(pnp->pr_type < PR_NFILES); 5070 5071 /* XXX - Do we need to pass ct and flags? */ 5072 return (pr_readdir_function[pnp->pr_type](pnp, uiop, eofp)); 5073 } 5074 5075 /* ARGSUSED */ 5076 static int 5077 pr_readdir_notdir(prnode_t *pnp, uio_t *uiop, int *eofp) 5078 { 5079 return (ENOTDIR); 5080 } 5081 5082 /* ARGSUSED */ 5083 static int 5084 pr_readdir_procdir(prnode_t *pnp, uio_t *uiop, int *eofp) 5085 { 5086 zoneid_t zoneid; 5087 gfs_readdir_state_t gstate; 5088 int error, eof = 0; 5089 offset_t n; 5090 5091 ASSERT(pnp->pr_type == PR_PROCDIR); 5092 5093 zoneid = VTOZONE(PTOV(pnp))->zone_id; 5094 5095 if ((error = gfs_readdir_init(&gstate, PNSIZ, PRSDSIZE, uiop, 5096 PRROOTINO, PRROOTINO, 0)) != 0) 5097 return (error); 5098 5099 /* 5100 * Loop until user's request is satisfied or until all processes 5101 * have been examined. 5102 */ 5103 while ((error = gfs_readdir_pred(&gstate, uiop, &n)) == 0) { 5104 uint_t pid; 5105 int pslot; 5106 proc_t *p; 5107 5108 /* 5109 * Find next entry. Skip processes not visible where 5110 * this /proc was mounted. 5111 */ 5112 mutex_enter(&pidlock); 5113 while (n < v.v_proc && 5114 ((p = pid_entry(n)) == NULL || p->p_stat == SIDL || 5115 (zoneid != GLOBAL_ZONEID && p->p_zone->zone_id != zoneid) || 5116 secpolicy_basic_procinfo(CRED(), p, curproc) != 0)) 5117 n++; 5118 5119 /* 5120 * Stop when entire proc table has been examined. 5121 */ 5122 if (n >= v.v_proc) { 5123 mutex_exit(&pidlock); 5124 eof = 1; 5125 break; 5126 } 5127 5128 ASSERT(p->p_stat != 0); 5129 pid = p->p_pid; 5130 pslot = p->p_slot; 5131 mutex_exit(&pidlock); 5132 error = gfs_readdir_emitn(&gstate, uiop, n, 5133 pmkino(0, pslot, PR_PIDDIR), pid); 5134 if (error) 5135 break; 5136 } 5137 5138 return (gfs_readdir_fini(&gstate, error, eofp, eof)); 5139 } 5140 5141 /* ARGSUSED */ 5142 static int 5143 pr_readdir_piddir(prnode_t *pnp, uio_t *uiop, int *eofp) 5144 { 5145 int zombie = ((pnp->pr_pcommon->prc_flags & PRC_DESTROY) != 0); 5146 prdirent_t dirent; 5147 prdirent_t *dirp; 5148 offset_t off; 5149 int error; 5150 5151 ASSERT(pnp->pr_type == PR_PIDDIR); 5152 5153 if (uiop->uio_offset < 0 || 5154 uiop->uio_offset % sizeof (prdirent_t) != 0 || 5155 uiop->uio_resid < sizeof (prdirent_t)) 5156 return (EINVAL); 5157 if (pnp->pr_pcommon->prc_proc == NULL) 5158 return (ENOENT); 5159 if (uiop->uio_offset >= sizeof (piddir)) 5160 goto out; 5161 5162 /* 5163 * Loop until user's request is satisfied, omitting some 5164 * files along the way if the process is a zombie. 5165 */ 5166 for (dirp = &piddir[uiop->uio_offset / sizeof (prdirent_t)]; 5167 uiop->uio_resid >= sizeof (prdirent_t) && 5168 dirp < &piddir[NPIDDIRFILES+2]; 5169 uiop->uio_offset = off + sizeof (prdirent_t), dirp++) { 5170 off = uiop->uio_offset; 5171 if (zombie) { 5172 switch (dirp->d_ino) { 5173 case PR_PIDDIR: 5174 case PR_PROCDIR: 5175 case PR_PSINFO: 5176 case PR_USAGE: 5177 break; 5178 default: 5179 continue; 5180 } 5181 } 5182 bcopy(dirp, &dirent, sizeof (prdirent_t)); 5183 if (dirent.d_ino == PR_PROCDIR) 5184 dirent.d_ino = PRROOTINO; 5185 else 5186 dirent.d_ino = pmkino(0, pnp->pr_pcommon->prc_slot, 5187 dirent.d_ino); 5188 if ((error = uiomove((caddr_t)&dirent, sizeof (prdirent_t), 5189 UIO_READ, uiop)) != 0) 5190 return (error); 5191 } 5192 out: 5193 if (eofp) 5194 *eofp = (uiop->uio_offset >= sizeof (piddir)); 5195 return (0); 5196 } 5197 5198 static void 5199 rebuild_objdir(struct as *as) 5200 { 5201 struct seg *seg; 5202 vnode_t *vp; 5203 vattr_t vattr; 5204 vnode_t **dir; 5205 ulong_t nalloc; 5206 ulong_t nentries; 5207 int i, j; 5208 ulong_t nold, nnew; 5209 5210 ASSERT(AS_WRITE_HELD(as)); 5211 5212 if (as->a_updatedir == 0 && as->a_objectdir != NULL) 5213 return; 5214 as->a_updatedir = 0; 5215 5216 if ((nalloc = avl_numnodes(&as->a_segtree)) == 0 || 5217 (seg = AS_SEGFIRST(as)) == NULL) /* can't happen? */ 5218 return; 5219 5220 /* 5221 * Allocate space for the new object directory. 5222 * (This is usually about two times too many entries.) 5223 */ 5224 nalloc = (nalloc + 0xf) & ~0xf; /* multiple of 16 */ 5225 dir = kmem_zalloc(nalloc * sizeof (vnode_t *), KM_SLEEP); 5226 5227 /* fill in the new directory with desired entries */ 5228 nentries = 0; 5229 do { 5230 vattr.va_mask = AT_FSID|AT_NODEID; 5231 if (seg->s_ops == &segvn_ops && 5232 SEGOP_GETVP(seg, seg->s_base, &vp) == 0 && 5233 vp != NULL && vp->v_type == VREG && 5234 VOP_GETATTR(vp, &vattr, 0, CRED(), NULL) == 0) { 5235 for (i = 0; i < nentries; i++) 5236 if (vp == dir[i]) 5237 break; 5238 if (i == nentries) { 5239 ASSERT(nentries < nalloc); 5240 dir[nentries++] = vp; 5241 } 5242 } 5243 } while ((seg = AS_SEGNEXT(as, seg)) != NULL); 5244 5245 if (as->a_objectdir == NULL) { /* first time */ 5246 as->a_objectdir = dir; 5247 as->a_sizedir = nalloc; 5248 return; 5249 } 5250 5251 /* 5252 * Null out all of the defunct entries in the old directory. 5253 */ 5254 nold = 0; 5255 nnew = nentries; 5256 for (i = 0; i < as->a_sizedir; i++) { 5257 if ((vp = as->a_objectdir[i]) != NULL) { 5258 for (j = 0; j < nentries; j++) { 5259 if (vp == dir[j]) { 5260 dir[j] = NULL; 5261 nnew--; 5262 break; 5263 } 5264 } 5265 if (j == nentries) 5266 as->a_objectdir[i] = NULL; 5267 else 5268 nold++; 5269 } 5270 } 5271 5272 if (nold + nnew > as->a_sizedir) { 5273 /* 5274 * Reallocate the old directory to have enough 5275 * space for the old and new entries combined. 5276 * Round up to the next multiple of 16. 5277 */ 5278 ulong_t newsize = (nold + nnew + 0xf) & ~0xf; 5279 vnode_t **newdir = kmem_zalloc(newsize * sizeof (vnode_t *), 5280 KM_SLEEP); 5281 bcopy(as->a_objectdir, newdir, 5282 as->a_sizedir * sizeof (vnode_t *)); 5283 kmem_free(as->a_objectdir, as->a_sizedir * sizeof (vnode_t *)); 5284 as->a_objectdir = newdir; 5285 as->a_sizedir = newsize; 5286 } 5287 5288 /* 5289 * Move all new entries to the old directory and 5290 * deallocate the space used by the new directory. 5291 */ 5292 if (nnew) { 5293 for (i = 0, j = 0; i < nentries; i++) { 5294 if ((vp = dir[i]) == NULL) 5295 continue; 5296 for (; j < as->a_sizedir; j++) { 5297 if (as->a_objectdir[j] != NULL) 5298 continue; 5299 as->a_objectdir[j++] = vp; 5300 break; 5301 } 5302 } 5303 } 5304 kmem_free(dir, nalloc * sizeof (vnode_t *)); 5305 } 5306 5307 /* 5308 * Return the vnode from a slot in the process's object directory. 5309 * The caller must have locked the process's address space. 5310 * The only caller is below, in pr_readdir_objectdir(). 5311 */ 5312 static vnode_t * 5313 obj_entry(struct as *as, int slot) 5314 { 5315 ASSERT(AS_LOCK_HELD(as)); 5316 if (as->a_objectdir == NULL) 5317 return (NULL); 5318 ASSERT(slot < as->a_sizedir); 5319 return (as->a_objectdir[slot]); 5320 } 5321 5322 /* ARGSUSED */ 5323 static int 5324 pr_readdir_objectdir(prnode_t *pnp, uio_t *uiop, int *eofp) 5325 { 5326 gfs_readdir_state_t gstate; 5327 int error, eof = 0; 5328 offset_t n; 5329 int pslot; 5330 size_t objdirsize; 5331 proc_t *p; 5332 struct as *as; 5333 vnode_t *vp; 5334 5335 ASSERT(pnp->pr_type == PR_OBJECTDIR); 5336 5337 if ((error = prlock(pnp, ZNO)) != 0) 5338 return (error); 5339 p = pnp->pr_common->prc_proc; 5340 pslot = p->p_slot; 5341 5342 /* 5343 * We drop p_lock before grabbing the address space lock 5344 * in order to avoid a deadlock with the clock thread. 5345 * The process will not disappear and its address space 5346 * will not change because it is marked P_PR_LOCK. 5347 */ 5348 mutex_exit(&p->p_lock); 5349 5350 if ((error = gfs_readdir_init(&gstate, 64, PRSDSIZE, uiop, 5351 pmkino(0, pslot, PR_PIDDIR), 5352 pmkino(0, pslot, PR_OBJECTDIR), 0)) != 0) { 5353 mutex_enter(&p->p_lock); 5354 prunlock(pnp); 5355 return (error); 5356 } 5357 5358 if ((p->p_flag & SSYS) || (as = p->p_as) == &kas) { 5359 as = NULL; 5360 objdirsize = 0; 5361 } 5362 5363 /* 5364 * Loop until user's request is satisfied or until 5365 * all mapped objects have been examined. Cannot hold 5366 * the address space lock for the following call as 5367 * gfs_readdir_pred() utimately causes a call to uiomove(). 5368 */ 5369 while ((error = gfs_readdir_pred(&gstate, uiop, &n)) == 0) { 5370 vattr_t vattr; 5371 char str[64]; 5372 5373 /* 5374 * Set the correct size of the directory just 5375 * in case the process has changed it's address 5376 * space via mmap/munmap calls. 5377 */ 5378 if (as != NULL) { 5379 AS_LOCK_ENTER(as, RW_WRITER); 5380 if (as->a_updatedir) 5381 rebuild_objdir(as); 5382 objdirsize = as->a_sizedir; 5383 } 5384 5385 /* 5386 * Find next object. 5387 */ 5388 vattr.va_mask = AT_FSID | AT_NODEID; 5389 while (n < objdirsize && (((vp = obj_entry(as, n)) == NULL) || 5390 (VOP_GETATTR(vp, &vattr, 0, CRED(), NULL) 5391 != 0))) { 5392 vattr.va_mask = AT_FSID | AT_NODEID; 5393 n++; 5394 } 5395 5396 if (as != NULL) 5397 AS_LOCK_EXIT(as); 5398 5399 /* 5400 * Stop when all objects have been reported. 5401 */ 5402 if (n >= objdirsize) { 5403 eof = 1; 5404 break; 5405 } 5406 5407 if (vp == p->p_exec) 5408 (void) strcpy(str, "a.out"); 5409 else 5410 pr_object_name(str, vp, &vattr); 5411 5412 error = gfs_readdir_emit(&gstate, uiop, n, vattr.va_nodeid, 5413 str, 0); 5414 5415 if (error) 5416 break; 5417 } 5418 5419 mutex_enter(&p->p_lock); 5420 prunlock(pnp); 5421 5422 return (gfs_readdir_fini(&gstate, error, eofp, eof)); 5423 } 5424 5425 /* ARGSUSED */ 5426 static int 5427 pr_readdir_lwpdir(prnode_t *pnp, uio_t *uiop, int *eofp) 5428 { 5429 gfs_readdir_state_t gstate; 5430 int error, eof = 0; 5431 offset_t tslot; 5432 proc_t *p; 5433 int pslot; 5434 lwpdir_t *lwpdir; 5435 int lwpdirsize; 5436 5437 ASSERT(pnp->pr_type == PR_LWPDIR); 5438 5439 p = pr_p_lock(pnp); 5440 mutex_exit(&pr_pidlock); 5441 if (p == NULL) 5442 return (ENOENT); 5443 ASSERT(p == pnp->pr_common->prc_proc); 5444 pslot = p->p_slot; 5445 lwpdir = p->p_lwpdir; 5446 lwpdirsize = p->p_lwpdir_sz; 5447 5448 /* 5449 * Drop p->p_lock so we can safely do uiomove(). 5450 * The lwp directory will not change because 5451 * we have the process locked with P_PR_LOCK. 5452 */ 5453 mutex_exit(&p->p_lock); 5454 5455 5456 if ((error = gfs_readdir_init(&gstate, PLNSIZ, PRSDSIZE, uiop, 5457 pmkino(0, pslot, PR_PIDDIR), 5458 pmkino(0, pslot, PR_LWPDIR), 0)) != 0) { 5459 mutex_enter(&p->p_lock); 5460 prunlock(pnp); 5461 return (error); 5462 } 5463 5464 /* 5465 * Loop until user's request is satisfied or until all lwps 5466 * have been examined. 5467 */ 5468 while ((error = gfs_readdir_pred(&gstate, uiop, &tslot)) == 0) { 5469 lwpent_t *lep; 5470 uint_t tid; 5471 5472 /* 5473 * Find next LWP. 5474 */ 5475 while (tslot < lwpdirsize && 5476 ((lep = lwpdir[tslot].ld_entry) == NULL)) 5477 tslot++; 5478 /* 5479 * Stop when all lwps have been reported. 5480 */ 5481 if (tslot >= lwpdirsize) { 5482 eof = 1; 5483 break; 5484 } 5485 5486 tid = lep->le_lwpid; 5487 error = gfs_readdir_emitn(&gstate, uiop, tslot, 5488 pmkino(tslot, pslot, PR_LWPIDDIR), tid); 5489 if (error) 5490 break; 5491 } 5492 5493 mutex_enter(&p->p_lock); 5494 prunlock(pnp); 5495 5496 return (gfs_readdir_fini(&gstate, error, eofp, eof)); 5497 } 5498 5499 /* ARGSUSED */ 5500 static int 5501 pr_readdir_lwpiddir(prnode_t *pnp, uio_t *uiop, int *eofp) 5502 { 5503 prcommon_t *pcp = pnp->pr_common; 5504 int zombie = ((pcp->prc_flags & PRC_DESTROY) != 0); 5505 prdirent_t dirent; 5506 prdirent_t *dirp; 5507 offset_t off; 5508 int error; 5509 int pslot; 5510 int tslot; 5511 5512 ASSERT(pnp->pr_type == PR_LWPIDDIR); 5513 5514 if (uiop->uio_offset < 0 || 5515 uiop->uio_offset % sizeof (prdirent_t) != 0 || 5516 uiop->uio_resid < sizeof (prdirent_t)) 5517 return (EINVAL); 5518 if (pcp->prc_proc == NULL || pcp->prc_tslot == -1) 5519 return (ENOENT); 5520 if (uiop->uio_offset >= sizeof (lwpiddir)) 5521 goto out; 5522 5523 /* 5524 * Loop until user's request is satisfied, omitting some files 5525 * along the way if the lwp is a zombie and also depending 5526 * on the data model of the process. 5527 */ 5528 pslot = pcp->prc_slot; 5529 tslot = pcp->prc_tslot; 5530 for (dirp = &lwpiddir[uiop->uio_offset / sizeof (prdirent_t)]; 5531 uiop->uio_resid >= sizeof (prdirent_t) && 5532 dirp < &lwpiddir[NLWPIDDIRFILES+2]; 5533 uiop->uio_offset = off + sizeof (prdirent_t), dirp++) { 5534 off = uiop->uio_offset; 5535 if (zombie) { 5536 switch (dirp->d_ino) { 5537 case PR_LWPIDDIR: 5538 case PR_LWPDIR: 5539 case PR_LWPSINFO: 5540 break; 5541 default: 5542 continue; 5543 } 5544 } 5545 #if defined(__sparc) 5546 /* the asrs file exists only for sparc v9 _LP64 processes */ 5547 if (dirp->d_ino == PR_ASRS && 5548 pcp->prc_datamodel != DATAMODEL_LP64) 5549 continue; 5550 #endif 5551 bcopy(dirp, &dirent, sizeof (prdirent_t)); 5552 if (dirent.d_ino == PR_LWPDIR) 5553 dirent.d_ino = pmkino(0, pslot, dirp->d_ino); 5554 else 5555 dirent.d_ino = pmkino(tslot, pslot, dirp->d_ino); 5556 if ((error = uiomove((caddr_t)&dirent, sizeof (prdirent_t), 5557 UIO_READ, uiop)) != 0) 5558 return (error); 5559 } 5560 out: 5561 if (eofp) 5562 *eofp = (uiop->uio_offset >= sizeof (lwpiddir)); 5563 return (0); 5564 } 5565 5566 /* 5567 * Helper function for reading a directory which lists open file desciptors 5568 */ 5569 static int 5570 pr_readdir_fdlist(prnode_t *pnp, uio_t *uiop, int *eofp, 5571 prnodetype_t dirtype, prnodetype_t entrytype) 5572 { 5573 gfs_readdir_state_t gstate; 5574 int error, eof = 0; 5575 offset_t n; 5576 proc_t *p; 5577 int pslot; 5578 int fddirsize; 5579 uf_info_t *fip; 5580 5581 if ((error = prlock(pnp, ZNO)) != 0) 5582 return (error); 5583 p = pnp->pr_common->prc_proc; 5584 pslot = p->p_slot; 5585 fip = P_FINFO(p); 5586 mutex_exit(&p->p_lock); 5587 5588 if ((error = gfs_readdir_init(&gstate, PLNSIZ, PRSDSIZE, uiop, 5589 pmkino(0, pslot, PR_PIDDIR), pmkino(0, pslot, dirtype), 0)) != 0) { 5590 mutex_enter(&p->p_lock); 5591 prunlock(pnp); 5592 return (error); 5593 } 5594 5595 mutex_enter(&fip->fi_lock); 5596 if ((p->p_flag & SSYS) || p->p_as == &kas) 5597 fddirsize = 0; 5598 else 5599 fddirsize = fip->fi_nfiles; 5600 5601 /* 5602 * Loop until user's request is satisfied or until 5603 * all file descriptors have been examined. 5604 */ 5605 while ((error = gfs_readdir_pred(&gstate, uiop, &n)) == 0) { 5606 /* 5607 * Find next fd. 5608 */ 5609 while (n < fddirsize && fip->fi_list[n].uf_file == NULL) 5610 n++; 5611 /* 5612 * Stop when all fds have been reported. 5613 */ 5614 if (n >= fddirsize) { 5615 eof = 1; 5616 break; 5617 } 5618 5619 error = gfs_readdir_emitn(&gstate, uiop, n, 5620 pmkino(n, pslot, entrytype), n); 5621 if (error) 5622 break; 5623 } 5624 5625 mutex_exit(&fip->fi_lock); 5626 mutex_enter(&p->p_lock); 5627 prunlock(pnp); 5628 5629 return (gfs_readdir_fini(&gstate, error, eofp, eof)); 5630 } 5631 5632 static int 5633 pr_readdir_fddir(prnode_t *pnp, uio_t *uiop, int *eofp) 5634 { 5635 5636 ASSERT(pnp->pr_type == PR_FDDIR); 5637 5638 return (pr_readdir_fdlist(pnp, uiop, eofp, pnp->pr_type, PR_FD)); 5639 } 5640 5641 static int 5642 pr_readdir_fdinfodir(prnode_t *pnp, uio_t *uiop, int *eofp) 5643 { 5644 5645 ASSERT(pnp->pr_type == PR_FDINFODIR); 5646 5647 return (pr_readdir_fdlist(pnp, uiop, eofp, pnp->pr_type, PR_FDINFO)); 5648 } 5649 5650 /* ARGSUSED */ 5651 static int 5652 pr_readdir_pathdir(prnode_t *pnp, uio_t *uiop, int *eofp) 5653 { 5654 longlong_t bp[DIRENT64_RECLEN(64) / sizeof (longlong_t)]; 5655 dirent64_t *dirent = (dirent64_t *)bp; 5656 int reclen; 5657 ssize_t oresid; 5658 offset_t off, idx; 5659 int error = 0; 5660 proc_t *p; 5661 int fd, obj; 5662 int pslot; 5663 int fddirsize; 5664 uf_info_t *fip; 5665 struct as *as = NULL; 5666 size_t objdirsize; 5667 vattr_t vattr; 5668 vnode_t *vp; 5669 5670 ASSERT(pnp->pr_type == PR_PATHDIR); 5671 5672 if (uiop->uio_offset < 0 || 5673 uiop->uio_resid <= 0 || 5674 (uiop->uio_offset % PRSDSIZE) != 0) 5675 return (EINVAL); 5676 oresid = uiop->uio_resid; 5677 bzero(bp, sizeof (bp)); 5678 5679 if ((error = prlock(pnp, ZNO)) != 0) 5680 return (error); 5681 p = pnp->pr_common->prc_proc; 5682 fip = P_FINFO(p); 5683 pslot = p->p_slot; 5684 mutex_exit(&p->p_lock); 5685 5686 if ((p->p_flag & SSYS) || (as = p->p_as) == &kas) { 5687 as = NULL; 5688 objdirsize = 0; 5689 } else { 5690 AS_LOCK_ENTER(as, RW_WRITER); 5691 if (as->a_updatedir) 5692 rebuild_objdir(as); 5693 objdirsize = as->a_sizedir; 5694 AS_LOCK_EXIT(as); 5695 as = NULL; 5696 } 5697 5698 mutex_enter(&fip->fi_lock); 5699 if ((p->p_flag & SSYS) || p->p_as == &kas) 5700 fddirsize = 0; 5701 else 5702 fddirsize = fip->fi_nfiles; 5703 5704 for (; uiop->uio_resid > 0; uiop->uio_offset = off + PRSDSIZE) { 5705 /* 5706 * There are 4 special files in the path directory: ".", "..", 5707 * "root", and "cwd". We handle those specially here. 5708 */ 5709 off = uiop->uio_offset; 5710 idx = off / PRSDSIZE; 5711 if (off == 0) { /* "." */ 5712 dirent->d_ino = pmkino(0, pslot, PR_PATHDIR); 5713 dirent->d_name[0] = '.'; 5714 dirent->d_name[1] = '\0'; 5715 reclen = DIRENT64_RECLEN(1); 5716 } else if (idx == 1) { /* ".." */ 5717 dirent->d_ino = pmkino(0, pslot, PR_PIDDIR); 5718 dirent->d_name[0] = '.'; 5719 dirent->d_name[1] = '.'; 5720 dirent->d_name[2] = '\0'; 5721 reclen = DIRENT64_RECLEN(2); 5722 } else if (idx == 2) { /* "root" */ 5723 dirent->d_ino = pmkino(idx, pslot, PR_PATH); 5724 (void) strcpy(dirent->d_name, "root"); 5725 reclen = DIRENT64_RECLEN(4); 5726 } else if (idx == 3) { /* "cwd" */ 5727 dirent->d_ino = pmkino(idx, pslot, PR_PATH); 5728 (void) strcpy(dirent->d_name, "cwd"); 5729 reclen = DIRENT64_RECLEN(3); 5730 } else if (idx < 4 + fddirsize) { 5731 /* 5732 * In this case, we have one of the file descriptors. 5733 */ 5734 fd = idx - 4; 5735 if (fip->fi_list[fd].uf_file == NULL) 5736 continue; 5737 dirent->d_ino = pmkino(idx, pslot, PR_PATH); 5738 (void) pr_u32tos(fd, dirent->d_name, PLNSIZ+1); 5739 reclen = DIRENT64_RECLEN(PLNSIZ); 5740 } else if (idx < 4 + fddirsize + objdirsize) { 5741 if (fip != NULL) { 5742 mutex_exit(&fip->fi_lock); 5743 fip = NULL; 5744 } 5745 5746 /* 5747 * We drop p_lock before grabbing the address space lock 5748 * in order to avoid a deadlock with the clock thread. 5749 * The process will not disappear and its address space 5750 * will not change because it is marked P_PR_LOCK. 5751 */ 5752 if (as == NULL) { 5753 as = p->p_as; 5754 AS_LOCK_ENTER(as, RW_WRITER); 5755 } 5756 5757 if (as->a_updatedir) { 5758 rebuild_objdir(as); 5759 objdirsize = as->a_sizedir; 5760 } 5761 5762 obj = idx - 4 - fddirsize; 5763 if ((vp = obj_entry(as, obj)) == NULL) 5764 continue; 5765 vattr.va_mask = AT_FSID|AT_NODEID; 5766 if (VOP_GETATTR(vp, &vattr, 0, CRED(), NULL) != 0) 5767 continue; 5768 if (vp == p->p_exec) 5769 (void) strcpy(dirent->d_name, "a.out"); 5770 else 5771 pr_object_name(dirent->d_name, vp, &vattr); 5772 dirent->d_ino = pmkino(idx, pslot, PR_PATH); 5773 reclen = DIRENT64_RECLEN(strlen(dirent->d_name)); 5774 } else { 5775 break; 5776 } 5777 5778 dirent->d_off = uiop->uio_offset + PRSDSIZE; 5779 dirent->d_reclen = (ushort_t)reclen; 5780 if (reclen > uiop->uio_resid) { 5781 /* 5782 * Error if no entries have been returned yet. 5783 */ 5784 if (uiop->uio_resid == oresid) 5785 error = EINVAL; 5786 break; 5787 } 5788 /* 5789 * Drop the address space lock to do the uiomove(). 5790 */ 5791 if (as != NULL) 5792 AS_LOCK_EXIT(as); 5793 5794 error = uiomove((caddr_t)dirent, reclen, UIO_READ, uiop); 5795 if (as != NULL) 5796 AS_LOCK_ENTER(as, RW_WRITER); 5797 5798 if (error) 5799 break; 5800 } 5801 5802 if (error == 0 && eofp) 5803 *eofp = (uiop->uio_offset >= (fddirsize + 2) * PRSDSIZE); 5804 5805 if (fip != NULL) 5806 mutex_exit(&fip->fi_lock); 5807 if (as != NULL) 5808 AS_LOCK_EXIT(as); 5809 mutex_enter(&p->p_lock); 5810 prunlock(pnp); 5811 return (error); 5812 } 5813 5814 static int 5815 pr_readdir_tmpldir(prnode_t *pnp, uio_t *uiop, int *eofp) 5816 { 5817 proc_t *p; 5818 int pslot, tslot; 5819 gfs_readdir_state_t gstate; 5820 int error, eof = 0; 5821 offset_t n; 5822 5823 ASSERT(pnp->pr_type == PR_TMPLDIR); 5824 5825 if ((error = prlock(pnp, ZNO)) != 0) 5826 return (error); 5827 p = pnp->pr_common->prc_proc; 5828 pslot = pnp->pr_common->prc_slot; 5829 tslot = pnp->pr_common->prc_tslot; 5830 mutex_exit(&p->p_lock); 5831 5832 if ((error = gfs_readdir_init(&gstate, PRDIRSIZE, PRSDSIZE, uiop, 5833 pmkino(tslot, pslot, PR_LWPDIR), 5834 pmkino(tslot, pslot, PR_TMPLDIR), 0)) != 0) { 5835 mutex_enter(&p->p_lock); 5836 prunlock(pnp); 5837 return (error); 5838 } 5839 5840 while ((error = gfs_readdir_pred(&gstate, uiop, &n)) == 0) { 5841 /* 5842 * Check for an active template. Reading a directory's 5843 * contents is already racy, so we don't bother taking 5844 * any locks. 5845 */ 5846 while (n < ct_ntypes && 5847 pnp->pr_common->prc_thread->t_lwp->lwp_ct_active[n] == NULL) 5848 n++; 5849 /* 5850 * Stop when all types have been reported. 5851 */ 5852 if (n >= ct_ntypes) { 5853 eof = 1; 5854 break; 5855 } 5856 /* 5857 * The pmkino invocation below will need to be updated 5858 * when we create our fifth contract type. 5859 */ 5860 ASSERT(ct_ntypes <= 4); 5861 error = gfs_readdir_emit(&gstate, uiop, n, 5862 pmkino((tslot << 2) | n, pslot, PR_TMPL), 5863 ct_types[n]->ct_type_name, 0); 5864 if (error) 5865 break; 5866 } 5867 5868 mutex_enter(&p->p_lock); 5869 prunlock(pnp); 5870 5871 return (gfs_readdir_fini(&gstate, error, eofp, eof)); 5872 } 5873 5874 static int 5875 pr_readdir_ctdir(prnode_t *pnp, uio_t *uiop, int *eofp) 5876 { 5877 proc_t *p; 5878 int pslot; 5879 gfs_readdir_state_t gstate; 5880 int error, eof = 0; 5881 offset_t n; 5882 uint64_t zid; 5883 5884 ASSERT(pnp->pr_type == PR_CTDIR); 5885 5886 if ((error = prlock(pnp, ZNO)) != 0) 5887 return (error); 5888 p = pnp->pr_common->prc_proc; 5889 pslot = p->p_slot; 5890 mutex_exit(&p->p_lock); 5891 5892 if ((error = gfs_readdir_init(&gstate, PRDIRSIZE, PRSDSIZE, uiop, 5893 pmkino(0, pslot, PR_PIDDIR), pmkino(0, pslot, PR_CTDIR), 0)) != 0) { 5894 mutex_enter(&p->p_lock); 5895 prunlock(pnp); 5896 return (error); 5897 } 5898 5899 zid = VTOZONE(pnp->pr_vnode)->zone_uniqid; 5900 while ((error = gfs_readdir_pred(&gstate, uiop, &n)) == 0) { 5901 id_t next = contract_plookup(p, n, zid); 5902 if (next == -1) { 5903 eof = 1; 5904 break; 5905 } 5906 error = gfs_readdir_emitn(&gstate, uiop, next, 5907 pmkino(next, pslot, PR_CT), next); 5908 if (error) 5909 break; 5910 } 5911 5912 mutex_enter(&p->p_lock); 5913 prunlock(pnp); 5914 5915 return (gfs_readdir_fini(&gstate, error, eofp, eof)); 5916 } 5917 5918 /* ARGSUSED */ 5919 static int 5920 prfsync(vnode_t *vp, int syncflag, cred_t *cr, caller_context_t *ct) 5921 { 5922 return (0); 5923 } 5924 5925 /* 5926 * Utility: remove a /proc vnode from a linked list, threaded through pr_next. 5927 */ 5928 static void 5929 pr_list_unlink(vnode_t *pvp, vnode_t **listp) 5930 { 5931 vnode_t *vp; 5932 prnode_t *pnp; 5933 5934 while ((vp = *listp) != NULL) { 5935 pnp = VTOP(vp); 5936 if (vp == pvp) { 5937 *listp = pnp->pr_next; 5938 pnp->pr_next = NULL; 5939 break; 5940 } 5941 listp = &pnp->pr_next; 5942 } 5943 } 5944 5945 /* ARGSUSED */ 5946 static void 5947 prinactive(vnode_t *vp, cred_t *cr, caller_context_t *ct) 5948 { 5949 prnode_t *pnp = VTOP(vp); 5950 prnodetype_t type = pnp->pr_type; 5951 proc_t *p; 5952 vnode_t *dp; 5953 vnode_t *ovp = NULL; 5954 prnode_t *opnp = NULL; 5955 5956 switch (type) { 5957 case PR_OBJECT: 5958 case PR_FD: 5959 case PR_FDINFO: 5960 case PR_SELF: 5961 case PR_PATH: 5962 /* These are not linked into the usual lists */ 5963 ASSERT(vp->v_count == 1); 5964 if ((dp = pnp->pr_parent) != NULL) 5965 VN_RELE(dp); 5966 prfreenode(pnp); 5967 return; 5968 default: 5969 break; 5970 } 5971 5972 mutex_enter(&pr_pidlock); 5973 if (pnp->pr_pcommon == NULL) 5974 p = NULL; 5975 else if ((p = pnp->pr_pcommon->prc_proc) != NULL) 5976 mutex_enter(&p->p_lock); 5977 mutex_enter(&vp->v_lock); 5978 5979 if (type == PR_PROCDIR || vp->v_count > 1) { 5980 VN_RELE_LOCKED(vp); 5981 mutex_exit(&vp->v_lock); 5982 if (p != NULL) 5983 mutex_exit(&p->p_lock); 5984 mutex_exit(&pr_pidlock); 5985 return; 5986 } 5987 5988 if ((dp = pnp->pr_parent) != NULL) { 5989 prnode_t *dpnp; 5990 5991 switch (type) { 5992 case PR_PIDFILE: 5993 case PR_LWPIDFILE: 5994 case PR_OPAGEDATA: 5995 break; 5996 default: 5997 dpnp = VTOP(dp); 5998 mutex_enter(&dpnp->pr_mutex); 5999 if (dpnp->pr_files != NULL && 6000 dpnp->pr_files[pnp->pr_index] == vp) 6001 dpnp->pr_files[pnp->pr_index] = NULL; 6002 mutex_exit(&dpnp->pr_mutex); 6003 break; 6004 } 6005 pnp->pr_parent = NULL; 6006 } 6007 6008 ASSERT(vp->v_count == 1); 6009 6010 /* 6011 * If we allocated an old /proc/pid node, free it too. 6012 */ 6013 if (pnp->pr_pidfile != NULL) { 6014 ASSERT(type == PR_PIDDIR); 6015 ovp = pnp->pr_pidfile; 6016 opnp = VTOP(ovp); 6017 ASSERT(opnp->pr_type == PR_PIDFILE); 6018 pnp->pr_pidfile = NULL; 6019 } 6020 6021 mutex_exit(&pr_pidlock); 6022 6023 if (p != NULL) { 6024 /* 6025 * Remove the vnodes from the lists of 6026 * /proc vnodes for the process. 6027 */ 6028 int slot; 6029 6030 switch (type) { 6031 case PR_PIDDIR: 6032 pr_list_unlink(vp, &p->p_trace); 6033 break; 6034 case PR_LWPIDDIR: 6035 if ((slot = pnp->pr_common->prc_tslot) != -1) { 6036 lwpent_t *lep = p->p_lwpdir[slot].ld_entry; 6037 pr_list_unlink(vp, &lep->le_trace); 6038 } 6039 break; 6040 default: 6041 pr_list_unlink(vp, &p->p_plist); 6042 break; 6043 } 6044 if (ovp != NULL) 6045 pr_list_unlink(ovp, &p->p_plist); 6046 mutex_exit(&p->p_lock); 6047 } 6048 6049 mutex_exit(&vp->v_lock); 6050 6051 if (type == PR_CT && pnp->pr_contract != NULL) { 6052 contract_rele(pnp->pr_contract); 6053 pnp->pr_contract = NULL; 6054 } 6055 6056 if (opnp != NULL) 6057 prfreenode(opnp); 6058 prfreenode(pnp); 6059 if (dp != NULL) { 6060 VN_RELE(dp); 6061 } 6062 } 6063 6064 /* ARGSUSED */ 6065 static int 6066 prseek(vnode_t *vp, offset_t ooff, offset_t *noffp, caller_context_t *ct) 6067 { 6068 return (0); 6069 } 6070 6071 /* 6072 * We use the p_execdir member of proc_t to expand the %d token in core file 6073 * paths (the directory path for the executable that dumped core; see 6074 * coreadm(8) for details). We'd like gcore(1) to be able to expand %d in 6075 * the same way as core dumping from the kernel, but there's no convenient 6076 * and comprehensible way to export the path name for p_execdir. To solve 6077 * this, we try to find the actual path to the executable that was used. In 6078 * pr_lookup_pathdir(), we mark the a.out path name vnode with the PR_AOUT 6079 * flag, and use that here to indicate that more work is needed beyond the 6080 * call to vnodetopath(). 6081 */ 6082 static int 6083 prreadlink_lookup(prnode_t *pnp, char *buf, size_t size, cred_t *cr) 6084 { 6085 proc_t *p; 6086 vnode_t *vp, *execvp, *vrootp; 6087 int ret; 6088 size_t len; 6089 dirent64_t *dp; 6090 size_t dlen = DIRENT64_RECLEN(MAXPATHLEN); 6091 char *dbuf; 6092 6093 p = curproc; 6094 mutex_enter(&p->p_lock); 6095 if ((vrootp = PTOU(p)->u_rdir) == NULL) 6096 vrootp = rootdir; 6097 VN_HOLD(vrootp); 6098 mutex_exit(&p->p_lock); 6099 6100 ret = vnodetopath(vrootp, pnp->pr_realvp, buf, size, cr); 6101 6102 /* 6103 * If PR_AOUT isn't set, then we looked up the path for the vnode; 6104 * otherwise, we looked up the path for (what we believe to be) the 6105 * containing directory. 6106 */ 6107 if ((pnp->pr_flags & PR_AOUT) == 0) { 6108 VN_RELE(vrootp); 6109 return (ret); 6110 } 6111 6112 /* 6113 * Fail if there's a problem locking the process. This will only 6114 * occur if the process is changing so the information we would 6115 * report would already be invalid. 6116 */ 6117 if (prlock(pnp, ZNO) != 0) { 6118 VN_RELE(vrootp); 6119 return (EIO); 6120 } 6121 6122 p = pnp->pr_common->prc_proc; 6123 mutex_exit(&p->p_lock); 6124 6125 execvp = p->p_exec; 6126 VN_HOLD(execvp); 6127 6128 /* 6129 * If our initial lookup of the directory failed, fall back to 6130 * the path name information for p_exec. 6131 */ 6132 if (ret != 0) { 6133 mutex_enter(&p->p_lock); 6134 prunlock(pnp); 6135 ret = vnodetopath(vrootp, execvp, buf, size, cr); 6136 VN_RELE(execvp); 6137 VN_RELE(vrootp); 6138 return (ret); 6139 } 6140 6141 len = strlen(buf); 6142 6143 /* 6144 * We use u_comm as a guess for the last component of the full 6145 * executable path name. If there isn't going to be enough space 6146 * we fall back to using the p_exec so that we can have _an_ 6147 * answer even if it's not perfect. 6148 */ 6149 if (strlen(PTOU(p)->u_comm) + len + 1 < size) { 6150 buf[len] = '/'; 6151 (void) strcpy(buf + len + 1, PTOU(p)->u_comm); 6152 mutex_enter(&p->p_lock); 6153 prunlock(pnp); 6154 6155 /* 6156 * Do a forward lookup of our u_comm guess. 6157 */ 6158 if (lookupnameat(buf + len + 1, UIO_SYSSPACE, FOLLOW, NULLVPP, 6159 &vp, pnp->pr_realvp) == 0) { 6160 if (vn_compare(vp, execvp)) { 6161 VN_RELE(vp); 6162 VN_RELE(execvp); 6163 VN_RELE(vrootp); 6164 return (0); 6165 } 6166 6167 VN_RELE(vp); 6168 } 6169 } else { 6170 mutex_enter(&p->p_lock); 6171 prunlock(pnp); 6172 } 6173 6174 dbuf = kmem_alloc(dlen, KM_SLEEP); 6175 6176 /* 6177 * Try to find a matching vnode by iterating through the directory's 6178 * entries. If that fails, fall back to the path information for 6179 * p_exec. 6180 */ 6181 if ((ret = dirfindvp(vrootp, pnp->pr_realvp, execvp, cr, dbuf, 6182 dlen, &dp)) == 0 && strlen(dp->d_name) + len + 1 < size) { 6183 buf[len] = '/'; 6184 (void) strcpy(buf + len + 1, dp->d_name); 6185 } else { 6186 ret = vnodetopath(vrootp, execvp, buf, size, cr); 6187 } 6188 6189 kmem_free(dbuf, dlen); 6190 VN_RELE(execvp); 6191 VN_RELE(vrootp); 6192 6193 return (ret); 6194 } 6195 6196 /* ARGSUSED */ 6197 static int 6198 prreadlink(vnode_t *vp, uio_t *uiop, cred_t *cr, caller_context_t *ctp) 6199 { 6200 prnode_t *pnp = VTOP(vp); 6201 char *buf; 6202 int ret = EINVAL; 6203 char idbuf[16]; 6204 int length, rlength; 6205 contract_t *ct; 6206 6207 switch (pnp->pr_type) { 6208 case PR_SELF: 6209 (void) snprintf(idbuf, sizeof (idbuf), "%d", curproc->p_pid); 6210 ret = uiomove(idbuf, strlen(idbuf), UIO_READ, uiop); 6211 break; 6212 case PR_OBJECT: 6213 case PR_FD: 6214 case PR_CURDIR: 6215 case PR_ROOTDIR: 6216 if (pnp->pr_realvp->v_type == VDIR) 6217 ret = 0; 6218 break; 6219 case PR_PATH: 6220 buf = kmem_alloc(MAXPATHLEN, KM_SLEEP); 6221 6222 if ((ret = prreadlink_lookup(pnp, buf, MAXPATHLEN, cr)) == 0) 6223 ret = uiomove(buf, strlen(buf), UIO_READ, uiop); 6224 6225 kmem_free(buf, MAXPATHLEN); 6226 break; 6227 case PR_CT: 6228 ASSERT(pnp->pr_contract != NULL); 6229 ct = pnp->pr_contract; 6230 length = sizeof (CTFS_ROOT "//") + sizeof (idbuf) + 6231 strlen(ct->ct_type->ct_type_name); 6232 buf = kmem_alloc(length, KM_SLEEP); 6233 rlength = snprintf(buf, length, CTFS_ROOT "/%s/%d", 6234 ct->ct_type->ct_type_name, ct->ct_id); 6235 ASSERT(rlength < length); 6236 ret = uiomove(buf, rlength, UIO_READ, uiop); 6237 kmem_free(buf, length); 6238 break; 6239 default: 6240 break; 6241 } 6242 6243 return (ret); 6244 } 6245 6246 /*ARGSUSED2*/ 6247 static int 6248 prcmp(vnode_t *vp1, vnode_t *vp2, caller_context_t *ct) 6249 { 6250 prnode_t *pp1, *pp2; 6251 6252 if (vp1 == vp2) 6253 return (1); 6254 6255 if (!vn_matchops(vp1, prvnodeops) || !vn_matchops(vp2, prvnodeops)) 6256 return (0); 6257 6258 pp1 = VTOP(vp1); 6259 pp2 = VTOP(vp2); 6260 6261 if (pp1->pr_type != pp2->pr_type) 6262 return (0); 6263 if (pp1->pr_type == PR_PROCDIR) 6264 return (1); 6265 if (pp1->pr_ino || pp2->pr_ino) 6266 return (pp2->pr_ino == pp1->pr_ino); 6267 6268 if (pp1->pr_common == NULL || pp2->pr_common == NULL) 6269 return (0); 6270 6271 return (pp1->pr_common->prc_slot == pp2->pr_common->prc_slot && 6272 pp1->pr_common->prc_tslot == pp2->pr_common->prc_tslot); 6273 } 6274 6275 static int 6276 prrealvp(vnode_t *vp, vnode_t **vpp, caller_context_t *ct) 6277 { 6278 vnode_t *rvp; 6279 6280 if ((rvp = VTOP(vp)->pr_realvp) != NULL) { 6281 vp = rvp; 6282 if (VOP_REALVP(vp, &rvp, ct) == 0) 6283 vp = rvp; 6284 } 6285 6286 *vpp = vp; 6287 return (0); 6288 } 6289 6290 /* 6291 * Return the answer requested to poll(). 6292 * POLLIN, POLLRDNORM, and POLLOUT are recognized as in fs_poll(). 6293 * In addition, these have special meaning for /proc files: 6294 * POLLPRI process or lwp stopped on an event of interest 6295 * POLLERR /proc file descriptor is invalid 6296 * POLLHUP process or lwp has terminated 6297 */ 6298 /*ARGSUSED5*/ 6299 static int 6300 prpoll(vnode_t *vp, short events, int anyyet, short *reventsp, 6301 pollhead_t **phpp, caller_context_t *ct) 6302 { 6303 prnode_t *pnp = VTOP(vp); 6304 prcommon_t *pcp = pnp->pr_common; 6305 pollhead_t *php = &pcp->prc_pollhead; 6306 proc_t *p; 6307 short revents; 6308 int error; 6309 int lockstate; 6310 6311 ASSERT(pnp->pr_type < PR_NFILES); 6312 6313 /* 6314 * Support for old /proc interface. 6315 */ 6316 if (pnp->pr_pidfile != NULL) { 6317 vp = pnp->pr_pidfile; 6318 pnp = VTOP(vp); 6319 ASSERT(pnp->pr_type == PR_PIDFILE); 6320 ASSERT(pnp->pr_common == pcp); 6321 } 6322 6323 *reventsp = revents = 0; 6324 *phpp = (pollhead_t *)NULL; 6325 6326 if (vp->v_type == VDIR) { 6327 *reventsp |= POLLNVAL; 6328 return (0); 6329 } 6330 6331 /* avoid deadlock with prnotify() */ 6332 if (pollunlock(&lockstate) != 0) { 6333 *reventsp = POLLNVAL; 6334 return (0); 6335 } 6336 6337 if ((error = prlock(pnp, ZNO)) != 0) { 6338 pollrelock(lockstate); 6339 switch (error) { 6340 case ENOENT: /* process or lwp died */ 6341 *reventsp = POLLHUP; 6342 error = 0; 6343 break; 6344 case EAGAIN: /* invalidated */ 6345 *reventsp = POLLERR; 6346 error = 0; 6347 break; 6348 } 6349 return (error); 6350 } 6351 6352 /* 6353 * We have the process marked locked (P_PR_LOCK) and we are holding 6354 * its p->p_lock. We want to unmark the process but retain 6355 * exclusive control w.r.t. other /proc controlling processes 6356 * before reacquiring the polling locks. 6357 * 6358 * prunmark() does this for us. It unmarks the process 6359 * but retains p->p_lock so we still have exclusive control. 6360 * We will drop p->p_lock at the end to relinquish control. 6361 * 6362 * We cannot call prunlock() at the end to relinquish control 6363 * because prunlock(), like prunmark(), may drop and reacquire 6364 * p->p_lock and that would lead to a lock order violation 6365 * w.r.t. the polling locks we are about to reacquire. 6366 */ 6367 p = pcp->prc_proc; 6368 ASSERT(p != NULL); 6369 prunmark(p); 6370 6371 pollrelock(lockstate); /* reacquire dropped poll locks */ 6372 6373 if ((p->p_flag & SSYS) || p->p_as == &kas) 6374 revents = POLLNVAL; 6375 else { 6376 short ev; 6377 6378 if ((ev = (events & (POLLIN|POLLRDNORM))) != 0) 6379 revents |= ev; 6380 /* 6381 * POLLWRNORM (same as POLLOUT) really should not be 6382 * used to indicate that the process or lwp stopped. 6383 * However, USL chose to use POLLWRNORM rather than 6384 * POLLPRI to indicate this, so we just accept either 6385 * requested event to indicate stopped. (grr...) 6386 */ 6387 if ((ev = (events & (POLLPRI|POLLOUT|POLLWRNORM))) != 0) { 6388 kthread_t *t; 6389 6390 if (pcp->prc_flags & PRC_LWP) { 6391 t = pcp->prc_thread; 6392 ASSERT(t != NULL); 6393 thread_lock(t); 6394 } else { 6395 t = prchoose(p); /* returns locked t */ 6396 ASSERT(t != NULL); 6397 } 6398 6399 if (ISTOPPED(t) || VSTOPPED(t)) 6400 revents |= ev; 6401 thread_unlock(t); 6402 } 6403 } 6404 6405 *reventsp = revents; 6406 if ((!anyyet && revents == 0) || (events & POLLET)) { 6407 /* 6408 * Arrange to wake up the polling lwp when 6409 * the target process/lwp stops or terminates 6410 * or when the file descriptor becomes invalid. 6411 */ 6412 pcp->prc_flags |= PRC_POLL; 6413 *phpp = php; 6414 } 6415 mutex_exit(&p->p_lock); 6416 return (0); 6417 } 6418 6419 /* in prioctl.c */ 6420 extern int prioctl(vnode_t *, int, intptr_t, int, cred_t *, int *, 6421 caller_context_t *); 6422 6423 /* 6424 * /proc vnode operations vector 6425 */ 6426 const fs_operation_def_t pr_vnodeops_template[] = { 6427 VOPNAME_OPEN, { .vop_open = propen }, 6428 VOPNAME_CLOSE, { .vop_close = prclose }, 6429 VOPNAME_READ, { .vop_read = prread }, 6430 VOPNAME_WRITE, { .vop_write = prwrite }, 6431 VOPNAME_IOCTL, { .vop_ioctl = prioctl }, 6432 VOPNAME_GETATTR, { .vop_getattr = prgetattr }, 6433 VOPNAME_ACCESS, { .vop_access = praccess }, 6434 VOPNAME_LOOKUP, { .vop_lookup = prlookup }, 6435 VOPNAME_CREATE, { .vop_create = prcreate }, 6436 VOPNAME_READDIR, { .vop_readdir = prreaddir }, 6437 VOPNAME_READLINK, { .vop_readlink = prreadlink }, 6438 VOPNAME_FSYNC, { .vop_fsync = prfsync }, 6439 VOPNAME_INACTIVE, { .vop_inactive = prinactive }, 6440 VOPNAME_SEEK, { .vop_seek = prseek }, 6441 VOPNAME_CMP, { .vop_cmp = prcmp }, 6442 VOPNAME_FRLOCK, { .error = fs_error }, 6443 VOPNAME_REALVP, { .vop_realvp = prrealvp }, 6444 VOPNAME_POLL, { .vop_poll = prpoll }, 6445 VOPNAME_DISPOSE, { .error = fs_error }, 6446 VOPNAME_SHRLOCK, { .error = fs_error }, 6447 NULL, NULL 6448 }; 6449