kvm_proc.c revision 195843
19823Sprr/*- 29823Sprr * Copyright (c) 1989, 1992, 1993 39823Sprr * The Regents of the University of California. All rights reserved. 49823Sprr * 59823Sprr * This code is derived from software developed by the Computer Systems 69823Sprr * Engineering group at Lawrence Berkeley Laboratory under DARPA contract 79823Sprr * BG 91-66 and contributed to Berkeley. 89823Sprr * 99823Sprr * Redistribution and use in source and binary forms, with or without 109823Sprr * modification, are permitted provided that the following conditions 119823Sprr * are met: 129823Sprr * 1. Redistributions of source code must retain the above copyright 139823Sprr * notice, this list of conditions and the following disclaimer. 149823Sprr * 2. Redistributions in binary form must reproduce the above copyright 159823Sprr * notice, this list of conditions and the following disclaimer in the 169823Sprr * documentation and/or other materials provided with the distribution. 179823Sprr * 4. Neither the name of the University nor the names of its contributors 189823Sprr * may be used to endorse or promote products derived from this software 199823Sprr * without specific prior written permission. 209823Sprr * 219823Sprr * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 229823Sprr * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 239823Sprr * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 249823Sprr * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 259823Sprr * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 269823Sprr * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 279823Sprr * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 289823Sprr * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 299823Sprr * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 309823Sprr * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 319823Sprr * SUCH DAMAGE. 329823Sprr */ 339823Sprr 349823Sprr#if 0 359823Sprr#if defined(LIBC_SCCS) && !defined(lint) 369823Sprrstatic char sccsid[] = "@(#)kvm_proc.c 8.3 (Berkeley) 9/23/93"; 379823Sprr#endif /* LIBC_SCCS and not lint */ 389823Sprr#endif 399823Sprr 409823Sprr#include <sys/cdefs.h> 419823Sprr__FBSDID("$FreeBSD: head/lib/libkvm/kvm_proc.c 195843 2009-07-24 15:03:10Z brooks $"); 429823Sprr 439823Sprr/* 449823Sprr * Proc traversal interface for kvm. ps and w are (probably) the exclusive 459823Sprr * users of this code, so we've factored it out into a separate module. 469823Sprr * Thus, we keep this grunge out of the other kvm applications (i.e., 479823Sprr * most other applications are interested only in open/close/read/nlist). 489823Sprr */ 499823Sprr 509823Sprr#include <sys/param.h> 519823Sprr#define _WANT_UCRED /* make ucred.h give us 'struct ucred' */ 529823Sprr#include <sys/ucred.h> 539823Sprr#include <sys/queue.h> 549823Sprr#include <sys/_lock.h> 559823Sprr#include <sys/_mutex.h> 569823Sprr#include <sys/_task.h> 579823Sprr#include <sys/cpuset.h> 589823Sprr#include <sys/user.h> 599823Sprr#include <sys/proc.h> 609823Sprr#define _WANT_PRISON /* make jail.h give us 'struct prison' */ 619823Sprr#include <sys/jail.h> 629823Sprr#include <sys/exec.h> 639823Sprr#include <sys/stat.h> 649823Sprr#include <sys/sysent.h> 659823Sprr#include <sys/ioctl.h> 669823Sprr#include <sys/tty.h> 679823Sprr#include <sys/file.h> 689823Sprr#include <sys/conf.h> 699823Sprr#include <stdio.h> 709823Sprr#include <stdlib.h> 719823Sprr#include <unistd.h> 729823Sprr#include <nlist.h> 739823Sprr#include <kvm.h> 749823Sprr 759823Sprr#include <vm/vm.h> 769823Sprr#include <vm/vm_param.h> 779823Sprr 789823Sprr#include <sys/sysctl.h> 799823Sprr 809823Sprr#include <limits.h> 819823Sprr#include <memory.h> 829823Sprr#include <paths.h> 839823Sprr 849823Sprr#include "kvm_private.h" 859823Sprr 869823Sprr#define KREAD(kd, addr, obj) \ 879823Sprr (kvm_read(kd, addr, (char *)(obj), sizeof(*obj)) != sizeof(*obj)) 889823Sprr 899823Sprrstatic int ticks; 909823Sprrstatic int hz; 919823Sprr 929823Sprr/* 939823Sprr * Read proc's from memory file into buffer bp, which has space to hold 949823Sprr * at most maxcnt procs. 959823Sprr */ 969823Sprrstatic int 979823Sprrkvm_proclist(kd, what, arg, p, bp, maxcnt) 989823Sprr kvm_t *kd; 999823Sprr int what, arg; 1009823Sprr struct proc *p; 1019823Sprr struct kinfo_proc *bp; 1029823Sprr int maxcnt; 1039823Sprr{ 1049823Sprr int cnt = 0; 1059823Sprr struct kinfo_proc kinfo_proc, *kp; 1069823Sprr struct pgrp pgrp; 1079823Sprr struct session sess; 1089823Sprr struct cdev t_cdev; 1099823Sprr struct tty tty; 1109823Sprr struct vmspace vmspace; 1119823Sprr struct sigacts sigacts; 1129823Sprr struct pstats pstats; 1139823Sprr struct ucred ucred; 1149823Sprr struct prison pr; 1159823Sprr struct thread mtd; 1169823Sprr struct proc proc; 1179823Sprr struct proc pproc; 1189823Sprr struct timeval tv; 1199823Sprr struct sysentvec sysent; 1209823Sprr char svname[KI_EMULNAMELEN]; 1219823Sprr 1229823Sprr kp = &kinfo_proc; 1239823Sprr kp->ki_structsize = sizeof(kinfo_proc); 1249823Sprr /* 1259823Sprr * Loop on the processes. this is completely broken because we need to be 1269823Sprr * able to loop on the threads and merge the ones that are the same process some how. 1279823Sprr */ 1289823Sprr for (; cnt < maxcnt && p != NULL; p = LIST_NEXT(&proc, p_list)) { 1299823Sprr memset(kp, 0, sizeof *kp); 1309823Sprr if (KREAD(kd, (u_long)p, &proc)) { 1319823Sprr _kvm_err(kd, kd->program, "can't read proc at %x", p); 1329823Sprr return (-1); 1339823Sprr } 1349823Sprr if (proc.p_state != PRS_ZOMBIE) { 1359823Sprr if (KREAD(kd, (u_long)TAILQ_FIRST(&proc.p_threads), 1369823Sprr &mtd)) { 1379823Sprr _kvm_err(kd, kd->program, 1389823Sprr "can't read thread at %x", 1399823Sprr TAILQ_FIRST(&proc.p_threads)); 1409823Sprr return (-1); 1419823Sprr } 1429823Sprr } 1439823Sprr if (KREAD(kd, (u_long)proc.p_ucred, &ucred) == 0) { 1449823Sprr kp->ki_ruid = ucred.cr_ruid; 1459823Sprr kp->ki_svuid = ucred.cr_svuid; 1469823Sprr kp->ki_rgid = ucred.cr_rgid; 1479823Sprr kp->ki_svgid = ucred.cr_svgid; 1489823Sprr kp->ki_cr_flags = ucred.cr_flags; 1499823Sprr if (ucred.cr_ngroups > KI_NGROUPS) { 1509823Sprr kp->ki_ngroups = KI_NGROUPS; 1519823Sprr kp->ki_cr_flags |= KI_CRF_GRP_OVERFLOW; 1529823Sprr } 1539823Sprr kp->ki_ngroups = ucred.cr_ngroups; 1549823Sprr bcopy(ucred.cr_groups, kp->ki_groups, 1559823Sprr kp->ki_ngroups * sizeof(gid_t)); 1569823Sprr kp->ki_uid = ucred.cr_uid; 1579823Sprr if (ucred.cr_prison != NULL) { 1589823Sprr if (KREAD(kd, (u_long)ucred.cr_prison, &pr)) { 1599823Sprr _kvm_err(kd, kd->program, 1609823Sprr "can't read prison at %x", 1619823Sprr ucred.cr_prison); 1629823Sprr return (-1); 1639823Sprr } 1649823Sprr kp->ki_jid = pr.pr_id; 1659823Sprr } 1669823Sprr } 1679823Sprr 1689823Sprr switch(what & ~KERN_PROC_INC_THREAD) { 1699823Sprr 1709823Sprr case KERN_PROC_GID: 1719823Sprr if (kp->ki_groups[0] != (gid_t)arg) 1729823Sprr continue; 1739823Sprr break; 1749823Sprr 1759823Sprr case KERN_PROC_PID: 1769823Sprr if (proc.p_pid != (pid_t)arg) 1779823Sprr continue; 1789823Sprr break; 1799823Sprr 1809823Sprr case KERN_PROC_RGID: 1819823Sprr if (kp->ki_rgid != (gid_t)arg) 1829823Sprr continue; 1839823Sprr break; 1849823Sprr 1859823Sprr case KERN_PROC_UID: 1869823Sprr if (kp->ki_uid != (uid_t)arg) 1879823Sprr continue; 1889823Sprr break; 1899823Sprr 1909823Sprr case KERN_PROC_RUID: 1919823Sprr if (kp->ki_ruid != (uid_t)arg) 1929823Sprr continue; 1939823Sprr break; 1949823Sprr } 1959823Sprr /* 1969823Sprr * We're going to add another proc to the set. If this 1979823Sprr * will overflow the buffer, assume the reason is because 1989823Sprr * nprocs (or the proc list) is corrupt and declare an error. 1999823Sprr */ 2009823Sprr if (cnt >= maxcnt) { 2019823Sprr _kvm_err(kd, kd->program, "nprocs corrupt"); 2029823Sprr return (-1); 2039823Sprr } 2049823Sprr /* 2059823Sprr * gather kinfo_proc 2069823Sprr */ 2079823Sprr kp->ki_paddr = p; 2089823Sprr kp->ki_addr = 0; /* XXX uarea */ 2099823Sprr /* kp->ki_kstack = proc.p_thread.td_kstack; XXXKSE */ 2109823Sprr kp->ki_args = proc.p_args; 2119823Sprr kp->ki_tracep = proc.p_tracevp; 2129823Sprr kp->ki_textvp = proc.p_textvp; 2139823Sprr kp->ki_fd = proc.p_fd; 2149823Sprr kp->ki_vmspace = proc.p_vmspace; 2159823Sprr if (proc.p_sigacts != NULL) { 2169823Sprr if (KREAD(kd, (u_long)proc.p_sigacts, &sigacts)) { 2179823Sprr _kvm_err(kd, kd->program, 2189823Sprr "can't read sigacts at %x", proc.p_sigacts); 2199823Sprr return (-1); 2209823Sprr } 2219823Sprr kp->ki_sigignore = sigacts.ps_sigignore; 2229823Sprr kp->ki_sigcatch = sigacts.ps_sigcatch; 2239823Sprr } 2249823Sprr#if 0 2259823Sprr if ((proc.p_flag & P_INMEM) && proc.p_stats != NULL) { 2269823Sprr if (KREAD(kd, (u_long)proc.p_stats, &pstats)) { 2279823Sprr _kvm_err(kd, kd->program, 2289823Sprr "can't read stats at %x", proc.p_stats); 2299823Sprr return (-1); 2309823Sprr } 2319823Sprr kp->ki_start = pstats.p_start; 2329823Sprr 2339823Sprr /* 2349823Sprr * XXX: The times here are probably zero and need 2359823Sprr * to be calculated from the raw data in p_rux and 2369823Sprr * p_crux. 2379823Sprr */ 2389823Sprr kp->ki_rusage = pstats.p_ru; 2399823Sprr kp->ki_childstime = pstats.p_cru.ru_stime; 2409823Sprr kp->ki_childutime = pstats.p_cru.ru_utime; 2419823Sprr /* Some callers want child-times in a single value */ 2429823Sprr timeradd(&kp->ki_childstime, &kp->ki_childutime, 2439823Sprr &kp->ki_childtime); 2449823Sprr } 2459823Sprr#endif 2469823Sprr if (proc.p_oppid) 2479823Sprr kp->ki_ppid = proc.p_oppid; 2489823Sprr else if (proc.p_pptr) { 2499823Sprr if (KREAD(kd, (u_long)proc.p_pptr, &pproc)) { 2509823Sprr _kvm_err(kd, kd->program, 2519823Sprr "can't read pproc at %x", proc.p_pptr); 2529823Sprr return (-1); 2539823Sprr } 2549823Sprr kp->ki_ppid = pproc.p_pid; 2559823Sprr } else 2569823Sprr kp->ki_ppid = 0; 2579823Sprr if (proc.p_pgrp == NULL) 2589823Sprr goto nopgrp; 2599823Sprr if (KREAD(kd, (u_long)proc.p_pgrp, &pgrp)) { 2609823Sprr _kvm_err(kd, kd->program, "can't read pgrp at %x", 2619823Sprr proc.p_pgrp); 2629823Sprr return (-1); 2639823Sprr } 2649823Sprr kp->ki_pgid = pgrp.pg_id; 2659823Sprr kp->ki_jobc = pgrp.pg_jobc; 2669823Sprr if (KREAD(kd, (u_long)pgrp.pg_session, &sess)) { 2679823Sprr _kvm_err(kd, kd->program, "can't read session at %x", 2689823Sprr pgrp.pg_session); 2699823Sprr return (-1); 2709823Sprr } 2719823Sprr kp->ki_sid = sess.s_sid; 2729823Sprr (void)memcpy(kp->ki_login, sess.s_login, 2739823Sprr sizeof(kp->ki_login)); 2749823Sprr kp->ki_kiflag = sess.s_ttyvp ? KI_CTTY : 0; 2759823Sprr if (sess.s_leader == p) 2769823Sprr kp->ki_kiflag |= KI_SLEADER; 2779823Sprr if ((proc.p_flag & P_CONTROLT) && sess.s_ttyp != NULL) { 2789823Sprr if (KREAD(kd, (u_long)sess.s_ttyp, &tty)) { 2799823Sprr _kvm_err(kd, kd->program, 2809823Sprr "can't read tty at %x", sess.s_ttyp); 2819823Sprr return (-1); 2829823Sprr } 2839823Sprr if (tty.t_dev != NULL) { 2849823Sprr if (KREAD(kd, (u_long)tty.t_dev, &t_cdev)) { 2859823Sprr _kvm_err(kd, kd->program, 2869823Sprr "can't read cdev at %x", 2879823Sprr tty.t_dev); 2889823Sprr return (-1); 2899823Sprr } 2909823Sprr#if 0 2919823Sprr kp->ki_tdev = t_cdev.si_udev; 2929823Sprr#else 2939823Sprr kp->ki_tdev = NODEV; 2949823Sprr#endif 2959823Sprr } 2969823Sprr if (tty.t_pgrp != NULL) { 2979823Sprr if (KREAD(kd, (u_long)tty.t_pgrp, &pgrp)) { 2989823Sprr _kvm_err(kd, kd->program, 2999823Sprr "can't read tpgrp at %x", 3009823Sprr tty.t_pgrp); 3019823Sprr return (-1); 3029823Sprr } 3039823Sprr kp->ki_tpgid = pgrp.pg_id; 3049823Sprr } else 3059823Sprr kp->ki_tpgid = -1; 3069823Sprr if (tty.t_session != NULL) { 3079823Sprr if (KREAD(kd, (u_long)tty.t_session, &sess)) { 3089823Sprr _kvm_err(kd, kd->program, 3099823Sprr "can't read session at %x", 3109823Sprr tty.t_session); 3119823Sprr return (-1); 3129823Sprr } 3139823Sprr kp->ki_tsid = sess.s_sid; 3149823Sprr } 3159823Sprr } else { 3169823Sprrnopgrp: 3179823Sprr kp->ki_tdev = NODEV; 3189823Sprr } 3199823Sprr if ((proc.p_state != PRS_ZOMBIE) && mtd.td_wmesg) 3209823Sprr (void)kvm_read(kd, (u_long)mtd.td_wmesg, 3219823Sprr kp->ki_wmesg, WMESGLEN); 3229823Sprr 3239823Sprr (void)kvm_read(kd, (u_long)proc.p_vmspace, 3249823Sprr (char *)&vmspace, sizeof(vmspace)); 3259823Sprr kp->ki_size = vmspace.vm_map.size; 3269823Sprr kp->ki_rssize = vmspace.vm_swrss; /* XXX */ 3279823Sprr kp->ki_swrss = vmspace.vm_swrss; 3289823Sprr kp->ki_tsize = vmspace.vm_tsize; 3299823Sprr kp->ki_dsize = vmspace.vm_dsize; 3309823Sprr kp->ki_ssize = vmspace.vm_ssize; 3319823Sprr 3329823Sprr switch (what & ~KERN_PROC_INC_THREAD) { 3339823Sprr 3349823Sprr case KERN_PROC_PGRP: 3359823Sprr if (kp->ki_pgid != (pid_t)arg) 3369823Sprr continue; 3379823Sprr break; 3389823Sprr 3399823Sprr case KERN_PROC_SESSION: 3409823Sprr if (kp->ki_sid != (pid_t)arg) 3419823Sprr continue; 3429823Sprr break; 3439823Sprr 3449823Sprr case KERN_PROC_TTY: 3459823Sprr if ((proc.p_flag & P_CONTROLT) == 0 || 3469823Sprr kp->ki_tdev != (dev_t)arg) 3479823Sprr continue; 3489823Sprr break; 3499823Sprr } 3509823Sprr if (proc.p_comm[0] != 0) 3519823Sprr strlcpy(kp->ki_comm, proc.p_comm, MAXCOMLEN); 3529823Sprr (void)kvm_read(kd, (u_long)proc.p_sysent, (char *)&sysent, 3539823Sprr sizeof(sysent)); 3549823Sprr (void)kvm_read(kd, (u_long)sysent.sv_name, (char *)&svname, 3559823Sprr sizeof(svname)); 3569823Sprr if (svname[0] != 0) 3579823Sprr strlcpy(kp->ki_emul, svname, KI_EMULNAMELEN); 3589823Sprr if ((proc.p_state != PRS_ZOMBIE) && 3599823Sprr (mtd.td_blocked != 0)) { 3609823Sprr kp->ki_kiflag |= KI_LOCKBLOCK; 3619823Sprr if (mtd.td_lockname) 3629823Sprr (void)kvm_read(kd, 3639823Sprr (u_long)mtd.td_lockname, 3649823Sprr kp->ki_lockname, LOCKNAMELEN); 3659823Sprr kp->ki_lockname[LOCKNAMELEN] = 0; 3669823Sprr } 3679823Sprr /* 3689823Sprr * XXX: This is plain wrong, rux_runtime has nothing 3699823Sprr * to do with struct bintime, rux_runtime is just a 64-bit 3709823Sprr * integer counter of cputicks. What we need here is a way 3719823Sprr * to convert cputicks to usecs. The kernel does it in 3729823Sprr * kern/kern_tc.c, but the function can't be just copied. 3739823Sprr */ 3749823Sprr bintime2timeval(&proc.p_rux.rux_runtime, &tv); 3759823Sprr kp->ki_runtime = (u_int64_t)tv.tv_sec * 1000000 + tv.tv_usec; 3769823Sprr kp->ki_pid = proc.p_pid; 3779823Sprr kp->ki_siglist = proc.p_siglist; 3789823Sprr SIGSETOR(kp->ki_siglist, mtd.td_siglist); 3799823Sprr kp->ki_sigmask = mtd.td_sigmask; 3809823Sprr kp->ki_xstat = proc.p_xstat; 3819823Sprr kp->ki_acflag = proc.p_acflag; 3829823Sprr kp->ki_lock = proc.p_lock; 3839823Sprr if (proc.p_state != PRS_ZOMBIE) { 3849823Sprr kp->ki_swtime = (ticks - proc.p_swtick) / hz; 3859823Sprr kp->ki_flag = proc.p_flag; 3869823Sprr kp->ki_sflag = 0; 3879823Sprr kp->ki_nice = proc.p_nice; 3889823Sprr kp->ki_traceflag = proc.p_traceflag; 3899823Sprr if (proc.p_state == PRS_NORMAL) { 3909823Sprr if (TD_ON_RUNQ(&mtd) || 3919823Sprr TD_CAN_RUN(&mtd) || 3929823Sprr TD_IS_RUNNING(&mtd)) { 3939823Sprr kp->ki_stat = SRUN; 3949823Sprr } else if (mtd.td_state == 3959823Sprr TDS_INHIBITED) { 3969823Sprr if (P_SHOULDSTOP(&proc)) { 3979823Sprr kp->ki_stat = SSTOP; 3989823Sprr } else if ( 3999823Sprr TD_IS_SLEEPING(&mtd)) { 4009823Sprr kp->ki_stat = SSLEEP; 4019823Sprr } else if (TD_ON_LOCK(&mtd)) { 4029823Sprr kp->ki_stat = SLOCK; 4039823Sprr } else { 4049823Sprr kp->ki_stat = SWAIT; 4059823Sprr } 4069823Sprr } 4079823Sprr } else { 4089823Sprr kp->ki_stat = SIDL; 4099823Sprr } 4109823Sprr /* Stuff from the thread */ 4119823Sprr kp->ki_pri.pri_level = mtd.td_priority; 4129823Sprr kp->ki_pri.pri_native = mtd.td_base_pri; 4139823Sprr kp->ki_lastcpu = mtd.td_lastcpu; 4149823Sprr kp->ki_wchan = mtd.td_wchan; 4159823Sprr if (mtd.td_name[0] != 0) 4169823Sprr strlcpy(kp->ki_ocomm, mtd.td_name, MAXCOMLEN); 4179823Sprr kp->ki_oncpu = mtd.td_oncpu; 4189823Sprr if (mtd.td_name[0] != '\0') 4199823Sprr strlcpy(kp->ki_ocomm, mtd.td_name, sizeof(kp->ki_ocomm)); 4209823Sprr kp->ki_pctcpu = 0; 4219823Sprr kp->ki_rqindex = 0; 4229823Sprr } else { 4239823Sprr kp->ki_stat = SZOMB; 4249823Sprr } 4259823Sprr bcopy(&kinfo_proc, bp, sizeof(kinfo_proc)); 4269823Sprr ++bp; 4279823Sprr ++cnt; 4289823Sprr } 4299823Sprr return (cnt); 4309823Sprr} 4319823Sprr 4329823Sprr/* 4339823Sprr * Build proc info array by reading in proc list from a crash dump. 4349823Sprr * Return number of procs read. maxcnt is the max we will read. 4359823Sprr */ 4369823Sprrstatic int 4379823Sprrkvm_deadprocs(kd, what, arg, a_allproc, a_zombproc, maxcnt) 4389823Sprr kvm_t *kd; 4399823Sprr int what, arg; 4409823Sprr u_long a_allproc; 4419823Sprr u_long a_zombproc; 4429823Sprr int maxcnt; 4439823Sprr{ 4449823Sprr struct kinfo_proc *bp = kd->procbase; 4459823Sprr int acnt, zcnt; 4469823Sprr struct proc *p; 4479823Sprr 4489823Sprr if (KREAD(kd, a_allproc, &p)) { 4499823Sprr _kvm_err(kd, kd->program, "cannot read allproc"); 4509823Sprr return (-1); 4519823Sprr } 4529823Sprr acnt = kvm_proclist(kd, what, arg, p, bp, maxcnt); 4539823Sprr if (acnt < 0) 4549823Sprr return (acnt); 4559823Sprr 4569823Sprr if (KREAD(kd, a_zombproc, &p)) { 4579823Sprr _kvm_err(kd, kd->program, "cannot read zombproc"); 4589823Sprr return (-1); 4599823Sprr } 4609823Sprr zcnt = kvm_proclist(kd, what, arg, p, bp + acnt, maxcnt - acnt); 461 if (zcnt < 0) 462 zcnt = 0; 463 464 return (acnt + zcnt); 465} 466 467struct kinfo_proc * 468kvm_getprocs(kd, op, arg, cnt) 469 kvm_t *kd; 470 int op, arg; 471 int *cnt; 472{ 473 int mib[4], st, nprocs; 474 size_t size; 475 int temp_op; 476 477 if (kd->procbase != 0) { 478 free((void *)kd->procbase); 479 /* 480 * Clear this pointer in case this call fails. Otherwise, 481 * kvm_close() will free it again. 482 */ 483 kd->procbase = 0; 484 } 485 if (ISALIVE(kd)) { 486 size = 0; 487 mib[0] = CTL_KERN; 488 mib[1] = KERN_PROC; 489 mib[2] = op; 490 mib[3] = arg; 491 temp_op = op & ~KERN_PROC_INC_THREAD; 492 st = sysctl(mib, 493 temp_op == KERN_PROC_ALL || temp_op == KERN_PROC_PROC ? 494 3 : 4, NULL, &size, NULL, 0); 495 if (st == -1) { 496 _kvm_syserr(kd, kd->program, "kvm_getprocs"); 497 return (0); 498 } 499 /* 500 * We can't continue with a size of 0 because we pass 501 * it to realloc() (via _kvm_realloc()), and passing 0 502 * to realloc() results in undefined behavior. 503 */ 504 if (size == 0) { 505 /* 506 * XXX: We should probably return an invalid, 507 * but non-NULL, pointer here so any client 508 * program trying to dereference it will 509 * crash. However, _kvm_freeprocs() calls 510 * free() on kd->procbase if it isn't NULL, 511 * and free()'ing a junk pointer isn't good. 512 * Then again, _kvm_freeprocs() isn't used 513 * anywhere . . . 514 */ 515 kd->procbase = _kvm_malloc(kd, 1); 516 goto liveout; 517 } 518 do { 519 size += size / 10; 520 kd->procbase = (struct kinfo_proc *) 521 _kvm_realloc(kd, kd->procbase, size); 522 if (kd->procbase == 0) 523 return (0); 524 st = sysctl(mib, temp_op == KERN_PROC_ALL || 525 temp_op == KERN_PROC_PROC ? 3 : 4, 526 kd->procbase, &size, NULL, 0); 527 } while (st == -1 && errno == ENOMEM); 528 if (st == -1) { 529 _kvm_syserr(kd, kd->program, "kvm_getprocs"); 530 return (0); 531 } 532 /* 533 * We have to check the size again because sysctl() 534 * may "round up" oldlenp if oldp is NULL; hence it 535 * might've told us that there was data to get when 536 * there really isn't any. 537 */ 538 if (size > 0 && 539 kd->procbase->ki_structsize != sizeof(struct kinfo_proc)) { 540 _kvm_err(kd, kd->program, 541 "kinfo_proc size mismatch (expected %d, got %d)", 542 sizeof(struct kinfo_proc), 543 kd->procbase->ki_structsize); 544 return (0); 545 } 546liveout: 547 nprocs = size == 0 ? 0 : size / kd->procbase->ki_structsize; 548 } else { 549 struct nlist nl[6], *p; 550 551 nl[0].n_name = "_nprocs"; 552 nl[1].n_name = "_allproc"; 553 nl[2].n_name = "_zombproc"; 554 nl[3].n_name = "_ticks"; 555 nl[4].n_name = "_hz"; 556 nl[5].n_name = 0; 557 558 if (kvm_nlist(kd, nl) != 0) { 559 for (p = nl; p->n_type != 0; ++p) 560 ; 561 _kvm_err(kd, kd->program, 562 "%s: no such symbol", p->n_name); 563 return (0); 564 } 565 if (KREAD(kd, nl[0].n_value, &nprocs)) { 566 _kvm_err(kd, kd->program, "can't read nprocs"); 567 return (0); 568 } 569 if (KREAD(kd, nl[3].n_value, &ticks)) { 570 _kvm_err(kd, kd->program, "can't read ticks"); 571 return (0); 572 } 573 if (KREAD(kd, nl[4].n_value, &hz)) { 574 _kvm_err(kd, kd->program, "can't read hz"); 575 return (0); 576 } 577 size = nprocs * sizeof(struct kinfo_proc); 578 kd->procbase = (struct kinfo_proc *)_kvm_malloc(kd, size); 579 if (kd->procbase == 0) 580 return (0); 581 582 nprocs = kvm_deadprocs(kd, op, arg, nl[1].n_value, 583 nl[2].n_value, nprocs); 584#ifdef notdef 585 size = nprocs * sizeof(struct kinfo_proc); 586 (void)realloc(kd->procbase, size); 587#endif 588 } 589 *cnt = nprocs; 590 return (kd->procbase); 591} 592 593void 594_kvm_freeprocs(kd) 595 kvm_t *kd; 596{ 597 if (kd->procbase) { 598 free(kd->procbase); 599 kd->procbase = 0; 600 } 601} 602 603void * 604_kvm_realloc(kd, p, n) 605 kvm_t *kd; 606 void *p; 607 size_t n; 608{ 609 void *np = (void *)realloc(p, n); 610 611 if (np == 0) { 612 free(p); 613 _kvm_err(kd, kd->program, "out of memory"); 614 } 615 return (np); 616} 617 618#ifndef MAX 619#define MAX(a, b) ((a) > (b) ? (a) : (b)) 620#endif 621 622/* 623 * Read in an argument vector from the user address space of process kp. 624 * addr if the user-space base address of narg null-terminated contiguous 625 * strings. This is used to read in both the command arguments and 626 * environment strings. Read at most maxcnt characters of strings. 627 */ 628static char ** 629kvm_argv(kd, kp, addr, narg, maxcnt) 630 kvm_t *kd; 631 struct kinfo_proc *kp; 632 u_long addr; 633 int narg; 634 int maxcnt; 635{ 636 char *np, *cp, *ep, *ap; 637 u_long oaddr = -1; 638 int len, cc; 639 char **argv; 640 641 /* 642 * Check that there aren't an unreasonable number of agruments, 643 * and that the address is in user space. 644 */ 645 if (narg > 512 || addr < VM_MIN_ADDRESS || addr >= VM_MAXUSER_ADDRESS) 646 return (0); 647 648 /* 649 * kd->argv : work space for fetching the strings from the target 650 * process's space, and is converted for returning to caller 651 */ 652 if (kd->argv == 0) { 653 /* 654 * Try to avoid reallocs. 655 */ 656 kd->argc = MAX(narg + 1, 32); 657 kd->argv = (char **)_kvm_malloc(kd, kd->argc * 658 sizeof(*kd->argv)); 659 if (kd->argv == 0) 660 return (0); 661 } else if (narg + 1 > kd->argc) { 662 kd->argc = MAX(2 * kd->argc, narg + 1); 663 kd->argv = (char **)_kvm_realloc(kd, kd->argv, kd->argc * 664 sizeof(*kd->argv)); 665 if (kd->argv == 0) 666 return (0); 667 } 668 /* 669 * kd->argspc : returned to user, this is where the kd->argv 670 * arrays are left pointing to the collected strings. 671 */ 672 if (kd->argspc == 0) { 673 kd->argspc = (char *)_kvm_malloc(kd, PAGE_SIZE); 674 if (kd->argspc == 0) 675 return (0); 676 kd->arglen = PAGE_SIZE; 677 } 678 /* 679 * kd->argbuf : used to pull in pages from the target process. 680 * the strings are copied out of here. 681 */ 682 if (kd->argbuf == 0) { 683 kd->argbuf = (char *)_kvm_malloc(kd, PAGE_SIZE); 684 if (kd->argbuf == 0) 685 return (0); 686 } 687 688 /* Pull in the target process'es argv vector */ 689 cc = sizeof(char *) * narg; 690 if (kvm_uread(kd, kp, addr, (char *)kd->argv, cc) != cc) 691 return (0); 692 /* 693 * ap : saved start address of string we're working on in kd->argspc 694 * np : pointer to next place to write in kd->argspc 695 * len: length of data in kd->argspc 696 * argv: pointer to the argv vector that we are hunting around the 697 * target process space for, and converting to addresses in 698 * our address space (kd->argspc). 699 */ 700 ap = np = kd->argspc; 701 argv = kd->argv; 702 len = 0; 703 /* 704 * Loop over pages, filling in the argument vector. 705 * Note that the argv strings could be pointing *anywhere* in 706 * the user address space and are no longer contiguous. 707 * Note that *argv is modified when we are going to fetch a string 708 * that crosses a page boundary. We copy the next part of the string 709 * into to "np" and eventually convert the pointer. 710 */ 711 while (argv < kd->argv + narg && *argv != 0) { 712 713 /* get the address that the current argv string is on */ 714 addr = (u_long)*argv & ~(PAGE_SIZE - 1); 715 716 /* is it the same page as the last one? */ 717 if (addr != oaddr) { 718 if (kvm_uread(kd, kp, addr, kd->argbuf, PAGE_SIZE) != 719 PAGE_SIZE) 720 return (0); 721 oaddr = addr; 722 } 723 724 /* offset within the page... kd->argbuf */ 725 addr = (u_long)*argv & (PAGE_SIZE - 1); 726 727 /* cp = start of string, cc = count of chars in this chunk */ 728 cp = kd->argbuf + addr; 729 cc = PAGE_SIZE - addr; 730 731 /* dont get more than asked for by user process */ 732 if (maxcnt > 0 && cc > maxcnt - len) 733 cc = maxcnt - len; 734 735 /* pointer to end of string if we found it in this page */ 736 ep = memchr(cp, '\0', cc); 737 if (ep != 0) 738 cc = ep - cp + 1; 739 /* 740 * at this point, cc is the count of the chars that we are 741 * going to retrieve this time. we may or may not have found 742 * the end of it. (ep points to the null if the end is known) 743 */ 744 745 /* will we exceed the malloc/realloced buffer? */ 746 if (len + cc > kd->arglen) { 747 int off; 748 char **pp; 749 char *op = kd->argspc; 750 751 kd->arglen *= 2; 752 kd->argspc = (char *)_kvm_realloc(kd, kd->argspc, 753 kd->arglen); 754 if (kd->argspc == 0) 755 return (0); 756 /* 757 * Adjust argv pointers in case realloc moved 758 * the string space. 759 */ 760 off = kd->argspc - op; 761 for (pp = kd->argv; pp < argv; pp++) 762 *pp += off; 763 ap += off; 764 np += off; 765 } 766 /* np = where to put the next part of the string in kd->argspc*/ 767 /* np is kinda redundant.. could use "kd->argspc + len" */ 768 memcpy(np, cp, cc); 769 np += cc; /* inc counters */ 770 len += cc; 771 772 /* 773 * if end of string found, set the *argv pointer to the 774 * saved beginning of string, and advance. argv points to 775 * somewhere in kd->argv.. This is initially relative 776 * to the target process, but when we close it off, we set 777 * it to point in our address space. 778 */ 779 if (ep != 0) { 780 *argv++ = ap; 781 ap = np; 782 } else { 783 /* update the address relative to the target process */ 784 *argv += cc; 785 } 786 787 if (maxcnt > 0 && len >= maxcnt) { 788 /* 789 * We're stopping prematurely. Terminate the 790 * current string. 791 */ 792 if (ep == 0) { 793 *np = '\0'; 794 *argv++ = ap; 795 } 796 break; 797 } 798 } 799 /* Make sure argv is terminated. */ 800 *argv = 0; 801 return (kd->argv); 802} 803 804static void 805ps_str_a(p, addr, n) 806 struct ps_strings *p; 807 u_long *addr; 808 int *n; 809{ 810 *addr = (u_long)p->ps_argvstr; 811 *n = p->ps_nargvstr; 812} 813 814static void 815ps_str_e(p, addr, n) 816 struct ps_strings *p; 817 u_long *addr; 818 int *n; 819{ 820 *addr = (u_long)p->ps_envstr; 821 *n = p->ps_nenvstr; 822} 823 824/* 825 * Determine if the proc indicated by p is still active. 826 * This test is not 100% foolproof in theory, but chances of 827 * being wrong are very low. 828 */ 829static int 830proc_verify(curkp) 831 struct kinfo_proc *curkp; 832{ 833 struct kinfo_proc newkp; 834 int mib[4]; 835 size_t len; 836 837 mib[0] = CTL_KERN; 838 mib[1] = KERN_PROC; 839 mib[2] = KERN_PROC_PID; 840 mib[3] = curkp->ki_pid; 841 len = sizeof(newkp); 842 if (sysctl(mib, 4, &newkp, &len, NULL, 0) == -1) 843 return (0); 844 return (curkp->ki_pid == newkp.ki_pid && 845 (newkp.ki_stat != SZOMB || curkp->ki_stat == SZOMB)); 846} 847 848static char ** 849kvm_doargv(kd, kp, nchr, info) 850 kvm_t *kd; 851 struct kinfo_proc *kp; 852 int nchr; 853 void (*info)(struct ps_strings *, u_long *, int *); 854{ 855 char **ap; 856 u_long addr; 857 int cnt; 858 static struct ps_strings arginfo; 859 static u_long ps_strings; 860 size_t len; 861 862 if (ps_strings == 0) { 863 len = sizeof(ps_strings); 864 if (sysctlbyname("kern.ps_strings", &ps_strings, &len, NULL, 865 0) == -1) 866 ps_strings = PS_STRINGS; 867 } 868 869 /* 870 * Pointers are stored at the top of the user stack. 871 */ 872 if (kp->ki_stat == SZOMB || 873 kvm_uread(kd, kp, ps_strings, (char *)&arginfo, 874 sizeof(arginfo)) != sizeof(arginfo)) 875 return (0); 876 877 (*info)(&arginfo, &addr, &cnt); 878 if (cnt == 0) 879 return (0); 880 ap = kvm_argv(kd, kp, addr, cnt, nchr); 881 /* 882 * For live kernels, make sure this process didn't go away. 883 */ 884 if (ap != 0 && ISALIVE(kd) && !proc_verify(kp)) 885 ap = 0; 886 return (ap); 887} 888 889/* 890 * Get the command args. This code is now machine independent. 891 */ 892char ** 893kvm_getargv(kd, kp, nchr) 894 kvm_t *kd; 895 const struct kinfo_proc *kp; 896 int nchr; 897{ 898 int oid[4]; 899 int i; 900 size_t bufsz; 901 static unsigned long buflen; 902 static char *buf, *p; 903 static char **bufp; 904 static int argc; 905 906 if (!ISALIVE(kd)) { 907 _kvm_err(kd, kd->program, 908 "cannot read user space from dead kernel"); 909 return (0); 910 } 911 912 if (!buflen) { 913 bufsz = sizeof(buflen); 914 i = sysctlbyname("kern.ps_arg_cache_limit", 915 &buflen, &bufsz, NULL, 0); 916 if (i == -1) { 917 buflen = 0; 918 } else { 919 buf = malloc(buflen); 920 if (buf == NULL) 921 buflen = 0; 922 argc = 32; 923 bufp = malloc(sizeof(char *) * argc); 924 } 925 } 926 if (buf != NULL) { 927 oid[0] = CTL_KERN; 928 oid[1] = KERN_PROC; 929 oid[2] = KERN_PROC_ARGS; 930 oid[3] = kp->ki_pid; 931 bufsz = buflen; 932 i = sysctl(oid, 4, buf, &bufsz, 0, 0); 933 if (i == 0 && bufsz > 0) { 934 i = 0; 935 p = buf; 936 do { 937 bufp[i++] = p; 938 p += strlen(p) + 1; 939 if (i >= argc) { 940 argc += argc; 941 bufp = realloc(bufp, 942 sizeof(char *) * argc); 943 } 944 } while (p < buf + bufsz); 945 bufp[i++] = 0; 946 return (bufp); 947 } 948 } 949 if (kp->ki_flag & P_SYSTEM) 950 return (NULL); 951 return (kvm_doargv(kd, kp, nchr, ps_str_a)); 952} 953 954char ** 955kvm_getenvv(kd, kp, nchr) 956 kvm_t *kd; 957 const struct kinfo_proc *kp; 958 int nchr; 959{ 960 return (kvm_doargv(kd, kp, nchr, ps_str_e)); 961} 962 963/* 964 * Read from user space. The user context is given by p. 965 */ 966ssize_t 967kvm_uread(kd, kp, uva, buf, len) 968 kvm_t *kd; 969 struct kinfo_proc *kp; 970 u_long uva; 971 char *buf; 972 size_t len; 973{ 974 char *cp; 975 char procfile[MAXPATHLEN]; 976 ssize_t amount; 977 int fd; 978 979 if (!ISALIVE(kd)) { 980 _kvm_err(kd, kd->program, 981 "cannot read user space from dead kernel"); 982 return (0); 983 } 984 985 sprintf(procfile, "/proc/%d/mem", kp->ki_pid); 986 fd = open(procfile, O_RDONLY, 0); 987 if (fd < 0) { 988 _kvm_err(kd, kd->program, "cannot open %s", procfile); 989 return (0); 990 } 991 992 cp = buf; 993 while (len > 0) { 994 errno = 0; 995 if (lseek(fd, (off_t)uva, 0) == -1 && errno != 0) { 996 _kvm_err(kd, kd->program, "invalid address (%x) in %s", 997 uva, procfile); 998 break; 999 } 1000 amount = read(fd, cp, len); 1001 if (amount < 0) { 1002 _kvm_syserr(kd, kd->program, "error reading %s", 1003 procfile); 1004 break; 1005 } 1006 if (amount == 0) { 1007 _kvm_err(kd, kd->program, "EOF reading %s", procfile); 1008 break; 1009 } 1010 cp += amount; 1011 uva += amount; 1012 len -= amount; 1013 } 1014 1015 close(fd); 1016 return ((ssize_t)(cp - buf)); 1017} 1018