Print this page
27908 ::gcore breaks sparc build


   4  * You may only use this file in accordance with the terms of version
   5  * 1.0 of the CDDL.
   6  *
   7  * A full copy of the text of the CDDL should have accompanied this
   8  * source.  A copy of the CDDL is also available via the Internet at
   9  * http://www.illumos.org/license/CDDL.
  10  */
  11 /*
  12  * Copyright (c) 2013 by Delphix. All rights reserved.
  13  */
  14 
  15 /*
  16  * This file implements the mdb ::gcore command.  The command relies on the
  17  * libproc Pgcore function to actually generate the core file but we provide
  18  * our own ops vector to populate data required by Pgcore.  The ops vector
  19  * function implementations simulate the functionality implemented by procfs.
  20  * The data provided by some of the ops vector functions is not complete
  21  * (missing data is documented in function headers) but there is enough
  22  * information to generate a core file that can be loaded into mdb.
  23  *
  24  * Currently only x86 is supported!

  25  */
  26 
  27 #ifndef _KMDB
  28 
  29 /*
  30  * The kernel has its own definition of exit which has a different signature
  31  * than the user space definition.  This seems to be the standard way to deal
  32  * with this.
  33  */
  34 #define exit kern_exit
  35 
  36 #include <mdb/mdb_modapi.h>
  37 #include <mdb/mdb_param.h>
  38 #include <mdb/mdb_ks.h>
  39 #include <mdb/mdb_ctf.h>
  40 #include <mdb/mdb_debug.h>

  41 
  42 #include <sys/class.h>
  43 #include <sys/cpuvar.h>
  44 #include <sys/proc.h>
  45 #include <sys/cred_impl.h>
  46 #include <sys/lgrp.h>
  47 #include <sys/pool.h>
  48 #include <sys/project.h>
  49 #include <sys/regset.h>
  50 #include <sys/schedctl.h>
  51 #include <sys/session.h>
  52 #include <sys/syscall.h>
  53 #include <sys/task.h>
  54 #include <sys/var.h>
  55 #include <sys/privregs.h>
  56 #include <sys/psw.h>
  57 #include <sys/fault.h>
  58 #include <sys/procfs.h>
  59 #include <sys/sysmacros.h>
  60 #include <sys/wait.h>
  61 #include <vm/seg.h>
  62 #include <vm/vpage.h>
  63 #include <fs/proc/prdata.h>
  64 
  65 #undef exit
  66 
  67 #include <stdio.h>
  68 #include <stdbool.h>
  69 #include <string.h>
  70 #include <libproc.h>
  71 
  72 #include "avl.h"
  73 
  74 #ifdef _LP64
  75 #define LSPAN(type)     (P2ROUNDUP(sizeof (type), 16))
  76 #else
  77 #define LSPAN(type)     (P2ROUNDUP(sizeof (type), 8))
  78 #endif


  84 #define GSOP_FINI(_gs)          (_gs)->gs_ops->gsop_fini((_gs))
  85 #define GSOP_INCORE(_gs, _addr, _eaddr) \
  86         (_gs)->gs_ops->gsop_incore((_gs), (_addr), (_eaddr))
  87 #define GSOP_GETPROT(_gs, _addr)        \
  88         (_gs)->gs_ops->gsop_getprot((_gs), (_addr))
  89 #define GSOP_GETOFFSET(_gs, _addr)      \
  90         (_gs)->gs_ops->gsop_getoffset((_gs), (_addr))
  91 #define GSOP_GETTYPE(_gs, _addr)        \
  92         (_gs)->gs_ops->gsop_gettype((_gs), (_addr))
  93 #define GSOP_NAME(_gs, _name, _size)    \
  94         (_gs)->gs_ops->gsop_name((_gs), (_name), (_size))
  95 #define GSOP_NORESERVE(_gs)             \
  96         (_gs)->gs_ops->gsop_noreserve((_gs))
  97 
  98 #ifdef GCORE_DEBUG
  99 #define dprintf(...)    mdb_printf(__VA_ARGS__)
 100 #else
 101 #define dprintf(...)
 102 #endif
 103 
 104 /* mdb versions of kernel structures used for ctf read calls */
 105 typedef struct mdb_proc {
 106         uintptr_t       p_as;
 107         uintptr_t       p_brkbase;
 108         size_t          p_brksize;
 109         uintptr_t       p_usrstack;
 110         size_t          p_stksize;
 111         user_t          p_user;
 112         uintptr_t       p_agenttp;
 113         uintptr_t       p_tlist;
 114         uintptr_t       p_zone;
 115         uintptr_t       p_ldt;
 116         kcondvar_t      p_holdlwps;
 117         int             p_lwpcnt;
 118         uintptr_t       p_lwpdir;
 119         uint_t          p_lwpdir_sz;
 120         uintptr_t       p_cred;
 121         uint_t          p_flag;
 122         int             p_zombcnt;
 123         uintptr_t       p_pidp;
 124         pid_t           p_ppid;
 125         uintptr_t       p_pgidp;
 126         uintptr_t       p_sessp;
 127         uintptr_t       p_task;
 128         uintptr_t       p_pool;
 129         model_t         p_model;
 130         char            p_wcode;
 131         ushort_t        p_ldtlimit;
 132         uintptr_t       p_exec;
 133         uint_t          p_proc_flag;
 134         ushort_t        p_pidflag;
 135         k_sigset_t      p_ignore;
 136         k_sigset_t      p_siginfo;
 137         k_sigset_t      p_sig;
 138         k_sigset_t      p_sigmask;
 139         k_fltset_t      p_fltmask;
 140         int             p_wdata;
 141 } mdb_proc_t;
 142 
 143 typedef struct mdb_kthread {
 144         ushort_t        t_proc_flag;
 145         uint_t          t_state;
 146         lwpchan_t       t_lwpchan;
 147         ushort_t        t_whystop;
 148         uint8_t         t_dtrace_stop;
 149         uintptr_t       t_forw;
 150         uintptr_t       t_lwp;
 151         id_t            t_tid;
 152         short           t_sysnum;
 153         pri_t           t_pri;
 154         time_t          t_start;
 155         id_t            t_cid;
 156         uintptr_t       t_cpu;
 157         int             t_bind_pset;
 158         short           t_bind_cpu;
 159         uintptr_t       t_lpl;
 160         ushort_t        t_schedflag;
 161         ushort_t        t_whatstop;
 162         k_sigset_t      t_sig;
 163         uintptr_t       t_schedctl;
 164         k_sigset_t      t_hold;
 165         hrtime_t        t_stoptime;
 166 } mdb_kthread_t;
 167 
 168 typedef struct mdb_seg {
 169         uintptr_t       s_base;
 170         size_t          s_size;
 171         uintptr_t       s_ops;
 172         uintptr_t       s_data;
 173         uintptr_t       s_as;
 174 } mdb_seg_t;
 175 
 176 typedef struct mdb_as {
 177         uintptr_t       a_proc;
 178 } mdb_as_t;
 179 
 180 typedef struct mdb_segvn_data {
 181         uintptr_t       vp;
 182         uint64_t        offset;
 183         uint16_t        flags;
 184         uint8_t         pageprot;
 185         uint8_t         prot;
 186         uintptr_t       amp;
 187         struct vpage    *vpage;
 188         uint64_t        anon_index;
 189         uint8_t         type;
 190 } mdb_segvn_data_t;
 191 
 192 typedef struct mdb_vnode {
 193         enum vtype      v_type;
 194         uintptr_t       v_data;
 195         uintptr_t       v_op;
 196         uintptr_t       v_path;
 197 } mdb_vnode_t;
 198 
 199 typedef struct mdb_znode {
 200         uint64_t        z_size;
 201 } mdb_znode_t;
 202 
 203 typedef struct mdb_tmpnode {
 204         vattr_t         tn_attr;
 205 } mdb_tmpnode_t;
 206 
 207 typedef struct mdb_vnodeops {
 208         uintptr_t       vnop_name;
 209 } mdb_vnodeops_t;
 210 
 211 typedef struct mdb_shm_data {
 212         uintptr_t       shm_sptseg;
 213 } mdb_shm_data_t;
 214 
 215 typedef struct mdb_watched_page {
 216         uintptr_t       wp_vaddr;
 217         uint8_t         wp_oprot;
 218 } mdb_watched_page_t;
 219 
 220 typedef struct mdb_pid {
 221         pid_t           pid_id;
 222 } mdb_pid_t;
 223 
 224 typedef struct mdb_sess {
 225         uintptr_t       s_sidp;
 226 } mdb_sess_t;
 227 
 228 typedef struct mdb_task {
 229         taskid_t        tk_tkid;
 230         uintptr_t       tk_proj;
 231 } mdb_task_t;
 232 
 233 typedef struct mdb_kproject {
 234         projid_t        kpj_id;
 235 } mdb_kproject_t;
 236 
 237 typedef struct mdb_zone {
 238         zoneid_t        zone_id;
 239         uintptr_t       zone_name;
 240 } mdb_zone_t;
 241 
 242 typedef struct mdb_sc_shared {
 243         char            sc_sigblock;
 244 } mdb_sc_shared_t;
 245 
 246 typedef struct mdb_klwp {
 247         uintptr_t       lwp_regs;
 248         struct pcb      lwp_pcb;
 249         uchar_t         lwp_asleep;
 250         uchar_t         lwp_cursig;
 251         uintptr_t       lwp_curinfo;
 252         k_siginfo_t     lwp_siginfo;
 253         stack_t         lwp_sigaltstack;
 254         uintptr_t       lwp_oldcontext;
 255         short           lwp_badpriv;
 256         uintptr_t       lwp_ustack;
 257         char            lwp_eosys;
 258 } mdb_klwp_t;
 259 
 260 typedef struct mdb_cpu {
 261         processorid_t   cpu_id;
 262 } mdb_cpu_t;
 263 
 264 typedef struct mdb_lpl {
 265         lgrp_id_t       lpl_lgrpid;
 266 } mdb_lpl_t;
 267 
 268 typedef struct mdb_sigqueue {
 269         k_siginfo_t     sq_info;
 270 } mdb_sigqueue_t;
 271 
 272 typedef struct mdb_pool {
 273         poolid_t        pool_id;
 274 } mdb_pool_t;
 275 
 276 typedef struct mdb_amp {
 277         uintptr_t       ahp;
 278 } mdb_amp_t;
 279 
 280 typedef struct mdb_anon_hdr {
 281         pgcnt_t         size;
 282         uintptr_t       array_chunk;
 283         int             flags;
 284 } mdb_anon_hdr_t;
 285 
 286 typedef struct mdb_anon {
 287         uintptr_t       an_vp;
 288         anoff_t         an_off;
 289 } mdb_anon_t;
 290 
 291 /* Used to construct a linked list of prmap_ts */
 292 typedef struct prmap_node {
 293         struct prmap_node *next;
 294         prmap_t         m;
 295 } prmap_node_t;
 296 
 297 /* Fields common to psinfo_t and pstatus_t */
 298 typedef struct pcommon {
 299         int             pc_nlwp;
 300         int             pc_nzomb;
 301         pid_t           pc_pid;
 302         pid_t           pc_ppid;
 303         pid_t           pc_pgid;
 304         pid_t           pc_sid;
 305         taskid_t        pc_taskid;
 306         projid_t        pc_projid;
 307         zoneid_t        pc_zoneid;
 308         char            pc_dmodel;
 309 } pcommon_t;
 310 
 311 /* AVL walk callback structures */
 312 typedef struct read_maps_cbarg {
 313         mdb_proc_t      *p;
 314         uintptr_t       brkseg;
 315         uintptr_t       stkseg;
 316         prmap_node_t    *map_head;
 317         prmap_node_t    *map_tail;
 318         int             map_len;
 319 } read_maps_cbarg_t;
 320 
 321 typedef struct as_segat_cbarg {
 322         uintptr_t       addr;
 323         uintptr_t       res;
 324 } as_segat_cbarg_t;
 325 
 326 typedef struct getwatchprot_cbarg {
 327         uintptr_t       wp_vaddr;
 328         mdb_watched_page_t wp;
 329         boolean_t       found;
 330 } getwatchprot_cbarg_t;
 331 
 332 struct gcore_segops;
 333 typedef struct gcore_seg {
 334         mdb_seg_t       *gs_seg;
 335         void            *gs_data;
 336         struct gcore_segops *gs_ops;
 337 } gcore_seg_t;
 338 
 339 /* Callback function type for processing lwp entries */
 340 typedef int (*lwp_callback_t)(mdb_proc_t *, lwpent_t *, void *);
 341 
 342 /* Private data */
 343 static uintptr_t gcore_segvn_ops;
 344 static priv_impl_info_t prinfo;
 345 static sclass_t *gcore_sclass;
 346 static uintptr_t gcore_kas;
 347 static boolean_t gcore_initialized = B_FALSE;
 348 
 349 typedef int (*gsop_init_t)(gcore_seg_t *);
 350 typedef void (*gsop_fini_t)(gcore_seg_t *);
 351 typedef u_offset_t (*gsop_incore_t)(gcore_seg_t *, u_offset_t, u_offset_t);
 352 typedef uint_t (*gsop_getprot_t)(gcore_seg_t *, u_offset_t);
 353 typedef int (*gsop_getoffset_t)(gcore_seg_t *, u_offset_t);
 354 typedef void (*gsop_name_t)(gcore_seg_t *, char *name, size_t size);
 355 typedef int (*gsop_gettype_t)(gcore_seg_t *, u_offset_t);
 356 typedef boolean_t (*gsop_noreserve_t)(gcore_seg_t *);
 357 
 358 typedef struct gcore_segops {


 707         as_segat_arg.res = 0;
 708 
 709         segtree_addr = as_addr + mdb_ctf_offsetof_by_name("struct as",
 710             "a_segtree");
 711         (void) avl_walk_mdb(segtree_addr, as_segat_cb, &as_segat_arg);
 712 
 713         return (as_segat_arg.res);
 714 }
 715 
 716 static uintptr_t
 717 gcore_break_seg(mdb_proc_t *p)
 718 {
 719         uintptr_t addr = p->p_brkbase;
 720 
 721         if (p->p_brkbase != 0)
 722                 addr += p->p_brksize - 1;
 723 
 724         return (gcore_as_segat(p->p_as, addr));
 725 }
 726 
 727 /* ISA dependent function. */
 728 static uintptr_t
 729 gcore_prgetstackbase(mdb_proc_t *p)
 730 {
 731         return (p->p_usrstack - p->p_stksize);
 732 }
 733 
 734 static u_offset_t
 735 gcore_vnode_size(uintptr_t vnode_addr)
 736 {
 737         mdb_vnode_t     vnode;
 738         mdb_vnodeops_t  vnodeops;
 739         char            vops_name[128];
 740 
 741         if (mdb_ctf_vread(&vnode, "vnode_t", "mdb_vnode_t", vnode_addr, 0) ==
 742             -1) {
 743                 return (-1);
 744         }
 745 
 746         if (mdb_ctf_vread(&vnodeops, "vnodeops_t", "mdb_vnodeops_t",
 747             vnode.v_op, 0) == -1) {
 748                 return (-1);
 749         }
 750 
 751         if (mdb_readstr(vops_name, sizeof (vops_name), vnodeops.vnop_name) ==
 752             -1) {
 753                 mdb_warn("Failed to read vnop_name from %p\n",


1368                 prassignset(&sp->sa_mask, &up->u_sigmask[sig-1]);
1369                 if (sigismember(&up->u_sigonstack, sig))
1370                         sp->sa_flags |= SA_ONSTACK;
1371                 if (sigismember(&up->u_sigresethand, sig))
1372                         sp->sa_flags |= SA_RESETHAND;
1373                 if (sigismember(&up->u_sigrestart, sig))
1374                         sp->sa_flags |= SA_RESTART;
1375                 if (sigismember(&p->p_siginfo, sig))
1376                         sp->sa_flags |= SA_SIGINFO;
1377                 if (sigismember(&up->u_signodefer, sig))
1378                         sp->sa_flags |= SA_NODEFER;
1379                 if (sig == SIGCLD) {
1380                         if (p->p_flag & SNOWAIT)
1381                                 sp->sa_flags |= SA_NOCLDWAIT;
1382                         if ((p->p_flag & SJCTL) == 0)
1383                                 sp->sa_flags |= SA_NOCLDSTOP;
1384                 }
1385         }
1386 }
1387 
1388 /* ISA dependent function. */
1389 static int
1390 gcore_prfetchinstr(mdb_klwp_t *lwp, ulong_t *ip)
1391 {
1392         *ip = (ulong_t)(instr_t)lwp->lwp_pcb.pcb_instr;
1393         return (lwp->lwp_pcb.pcb_flags & INSTR_VALID);
1394 }
1395 
1396 /* ISA dependent function. */
1397 static int
1398 gcore_prisstep(mdb_klwp_t *lwp)
1399 {
1400         return ((lwp->lwp_pcb.pcb_flags &
1401             (NORMAL_STEP|WATCH_STEP|DEBUG_PENDING)) != 0);
1402 }
1403 
1404 /* ISA dependent function. */
1405 static void
1406 gcore_getgregs(mdb_klwp_t *lwp, gregset_t grp)
1407 {
1408         struct regs rgs;
1409         struct regs *rp;
1410 
1411         if (mdb_vread(&rgs, sizeof (rgs), lwp->lwp_regs) != sizeof (rgs)) {
1412                 mdb_warn("Failed to read regs from %p\n", lwp->lwp_regs);
1413                 return;
1414         }
1415         rp = &rgs;
1416 
1417 #if defined(__amd64)
1418         struct pcb *pcb = &lwp->lwp_pcb;
1419 
1420         grp[REG_RDI] = rp->r_rdi;
1421         grp[REG_RSI] = rp->r_rsi;
1422         grp[REG_RDX] = rp->r_rdx;
1423         grp[REG_RCX] = rp->r_rcx;
1424         grp[REG_R8] = rp->r_r8;
1425         grp[REG_R9] = rp->r_r9;
1426         grp[REG_RAX] = rp->r_rax;
1427         grp[REG_RBX] = rp->r_rbx;
1428         grp[REG_RBP] = rp->r_rbp;
1429         grp[REG_R10] = rp->r_r10;
1430         grp[REG_R11] = rp->r_r11;
1431         grp[REG_R12] = rp->r_r12;
1432         grp[REG_R13] = rp->r_r13;
1433         grp[REG_R14] = rp->r_r14;
1434         grp[REG_R15] = rp->r_r15;
1435         grp[REG_FSBASE] = pcb->pcb_fsbase;
1436         grp[REG_GSBASE] = pcb->pcb_gsbase;
1437         if (pcb->pcb_rupdate == 1) {
1438                 grp[REG_DS] = pcb->pcb_ds;
1439                 grp[REG_ES] = pcb->pcb_es;
1440                 grp[REG_FS] = pcb->pcb_fs;
1441                 grp[REG_GS] = pcb->pcb_gs;
1442         } else {
1443                 grp[REG_DS] = rp->r_ds;
1444                 grp[REG_ES] = rp->r_es;
1445                 grp[REG_FS] = rp->r_fs;
1446                 grp[REG_GS] = rp->r_gs;
1447         }
1448         grp[REG_TRAPNO] = rp->r_trapno;
1449         grp[REG_ERR] = rp->r_err;
1450         grp[REG_RIP] = rp->r_rip;
1451         grp[REG_CS] = rp->r_cs;
1452         grp[REG_SS] = rp->r_ss;
1453         grp[REG_RFL] = rp->r_rfl;
1454         grp[REG_RSP] = rp->r_rsp;
1455 #else
1456         bcopy(&rp->r_gs, grp, sizeof (gregset_t));
1457 #endif
1458 }
1459 
1460 /* ISA dependent functions. */
1461 static int
1462 gcore_prgetrvals(mdb_klwp_t *lwp, long *rval1, long *rval2)
1463 {
1464         struct regs *r = lwptoregs(lwp);
1465 
1466         if (r->r_ps & PS_C)
1467                 return (r->r_r0);
1468         if (lwp->lwp_eosys == JUSTRETURN) {
1469                 *rval1 = 0;
1470                 *rval2 = 0;
1471         } else {
1472                 *rval1 = r->r_r0;
1473                 *rval2 = r->r_r1;
1474         }
1475         return (0);
1476 }
1477 
1478 static void
1479 gcore_prgetprregs(mdb_klwp_t *lwp, prgregset_t prp)
1480 {
1481         gcore_getgregs(lwp, prp);
1482 }
1483 
1484 /*
1485  * Field not populated:
1486  *   - pr_tstamp
1487  *   - pr_utime
1488  *   - pr_stime
1489  *   - pr_syscall
1490  *   - pr_syarg
1491  *   - pr_nsysarg
1492  *   - pr_fpreg
1493  */
1494 /*ARGSUSED*/
1495 static int
1496 gcore_prgetlwpstatus(mdb_proc_t *p, uintptr_t t_addr, mdb_kthread_t *t,
1497     lwpstatus_t *sp, zone_t *zp)




   4  * You may only use this file in accordance with the terms of version
   5  * 1.0 of the CDDL.
   6  *
   7  * A full copy of the text of the CDDL should have accompanied this
   8  * source.  A copy of the CDDL is also available via the Internet at
   9  * http://www.illumos.org/license/CDDL.
  10  */
  11 /*
  12  * Copyright (c) 2013 by Delphix. All rights reserved.
  13  */
  14 
  15 /*
  16  * This file implements the mdb ::gcore command.  The command relies on the
  17  * libproc Pgcore function to actually generate the core file but we provide
  18  * our own ops vector to populate data required by Pgcore.  The ops vector
  19  * function implementations simulate the functionality implemented by procfs.
  20  * The data provided by some of the ops vector functions is not complete
  21  * (missing data is documented in function headers) but there is enough
  22  * information to generate a core file that can be loaded into mdb.
  23  *
  24  * Currently only x86 is supported. ISA-dependent functions are implemented
  25  * in gcore_isadep.c.
  26  */
  27 
  28 #ifndef _KMDB
  29 
  30 /*
  31  * The kernel has its own definition of exit which has a different signature
  32  * than the user space definition.  This seems to be the standard way to deal
  33  * with this.
  34  */
  35 #define exit kern_exit
  36 
  37 #include <mdb/mdb_modapi.h>
  38 #include <mdb/mdb_param.h>
  39 #include <mdb/mdb_ks.h>
  40 #include <mdb/mdb_ctf.h>
  41 #include <mdb/mdb_debug.h>
  42 #include <mdb/mdb_gcore.h>
  43 
  44 #include <sys/class.h>
  45 #include <sys/cpuvar.h>
  46 #include <sys/proc.h>

  47 #include <sys/lgrp.h>
  48 #include <sys/pool.h>
  49 #include <sys/project.h>
  50 #include <sys/regset.h>
  51 #include <sys/schedctl.h>
  52 #include <sys/session.h>
  53 #include <sys/syscall.h>
  54 #include <sys/task.h>
  55 #include <sys/var.h>
  56 #include <sys/privregs.h>

  57 #include <sys/fault.h>

  58 #include <sys/sysmacros.h>
  59 #include <sys/wait.h>
  60 #include <vm/seg.h>
  61 #include <vm/vpage.h>
  62 #include <fs/proc/prdata.h>
  63 
  64 #undef exit
  65 
  66 #include <stdio.h>
  67 #include <stdbool.h>
  68 #include <string.h>
  69 #include <libproc.h>
  70 
  71 #include "avl.h"
  72 
  73 #ifdef _LP64
  74 #define LSPAN(type)     (P2ROUNDUP(sizeof (type), 16))
  75 #else
  76 #define LSPAN(type)     (P2ROUNDUP(sizeof (type), 8))
  77 #endif


  83 #define GSOP_FINI(_gs)          (_gs)->gs_ops->gsop_fini((_gs))
  84 #define GSOP_INCORE(_gs, _addr, _eaddr) \
  85         (_gs)->gs_ops->gsop_incore((_gs), (_addr), (_eaddr))
  86 #define GSOP_GETPROT(_gs, _addr)        \
  87         (_gs)->gs_ops->gsop_getprot((_gs), (_addr))
  88 #define GSOP_GETOFFSET(_gs, _addr)      \
  89         (_gs)->gs_ops->gsop_getoffset((_gs), (_addr))
  90 #define GSOP_GETTYPE(_gs, _addr)        \
  91         (_gs)->gs_ops->gsop_gettype((_gs), (_addr))
  92 #define GSOP_NAME(_gs, _name, _size)    \
  93         (_gs)->gs_ops->gsop_name((_gs), (_name), (_size))
  94 #define GSOP_NORESERVE(_gs)             \
  95         (_gs)->gs_ops->gsop_noreserve((_gs))
  96 
  97 #ifdef GCORE_DEBUG
  98 #define dprintf(...)    mdb_printf(__VA_ARGS__)
  99 #else
 100 #define dprintf(...)
 101 #endif
 102 











































































































































































































































 103 /* Callback function type for processing lwp entries */
 104 typedef int (*lwp_callback_t)(mdb_proc_t *, lwpent_t *, void *);
 105 
 106 /* Private data */
 107 static uintptr_t gcore_segvn_ops;
 108 static priv_impl_info_t prinfo;
 109 static sclass_t *gcore_sclass;
 110 static uintptr_t gcore_kas;
 111 static boolean_t gcore_initialized = B_FALSE;
 112 
 113 typedef int (*gsop_init_t)(gcore_seg_t *);
 114 typedef void (*gsop_fini_t)(gcore_seg_t *);
 115 typedef u_offset_t (*gsop_incore_t)(gcore_seg_t *, u_offset_t, u_offset_t);
 116 typedef uint_t (*gsop_getprot_t)(gcore_seg_t *, u_offset_t);
 117 typedef int (*gsop_getoffset_t)(gcore_seg_t *, u_offset_t);
 118 typedef void (*gsop_name_t)(gcore_seg_t *, char *name, size_t size);
 119 typedef int (*gsop_gettype_t)(gcore_seg_t *, u_offset_t);
 120 typedef boolean_t (*gsop_noreserve_t)(gcore_seg_t *);
 121 
 122 typedef struct gcore_segops {


 471         as_segat_arg.res = 0;
 472 
 473         segtree_addr = as_addr + mdb_ctf_offsetof_by_name("struct as",
 474             "a_segtree");
 475         (void) avl_walk_mdb(segtree_addr, as_segat_cb, &as_segat_arg);
 476 
 477         return (as_segat_arg.res);
 478 }
 479 
 480 static uintptr_t
 481 gcore_break_seg(mdb_proc_t *p)
 482 {
 483         uintptr_t addr = p->p_brkbase;
 484 
 485         if (p->p_brkbase != 0)
 486                 addr += p->p_brksize - 1;
 487 
 488         return (gcore_as_segat(p->p_as, addr));
 489 }
 490 







 491 static u_offset_t
 492 gcore_vnode_size(uintptr_t vnode_addr)
 493 {
 494         mdb_vnode_t     vnode;
 495         mdb_vnodeops_t  vnodeops;
 496         char            vops_name[128];
 497 
 498         if (mdb_ctf_vread(&vnode, "vnode_t", "mdb_vnode_t", vnode_addr, 0) ==
 499             -1) {
 500                 return (-1);
 501         }
 502 
 503         if (mdb_ctf_vread(&vnodeops, "vnodeops_t", "mdb_vnodeops_t",
 504             vnode.v_op, 0) == -1) {
 505                 return (-1);
 506         }
 507 
 508         if (mdb_readstr(vops_name, sizeof (vops_name), vnodeops.vnop_name) ==
 509             -1) {
 510                 mdb_warn("Failed to read vnop_name from %p\n",


1125                 prassignset(&sp->sa_mask, &up->u_sigmask[sig-1]);
1126                 if (sigismember(&up->u_sigonstack, sig))
1127                         sp->sa_flags |= SA_ONSTACK;
1128                 if (sigismember(&up->u_sigresethand, sig))
1129                         sp->sa_flags |= SA_RESETHAND;
1130                 if (sigismember(&up->u_sigrestart, sig))
1131                         sp->sa_flags |= SA_RESTART;
1132                 if (sigismember(&p->p_siginfo, sig))
1133                         sp->sa_flags |= SA_SIGINFO;
1134                 if (sigismember(&up->u_signodefer, sig))
1135                         sp->sa_flags |= SA_NODEFER;
1136                 if (sig == SIGCLD) {
1137                         if (p->p_flag & SNOWAIT)
1138                                 sp->sa_flags |= SA_NOCLDWAIT;
1139                         if ((p->p_flag & SJCTL) == 0)
1140                                 sp->sa_flags |= SA_NOCLDSTOP;
1141                 }
1142         }
1143 }
1144 


























































































1145 static void
1146 gcore_prgetprregs(mdb_klwp_t *lwp, prgregset_t prp)
1147 {
1148         gcore_getgregs(lwp, prp);
1149 }
1150 
1151 /*
1152  * Field not populated:
1153  *   - pr_tstamp
1154  *   - pr_utime
1155  *   - pr_stime
1156  *   - pr_syscall
1157  *   - pr_syarg
1158  *   - pr_nsysarg
1159  *   - pr_fpreg
1160  */
1161 /*ARGSUSED*/
1162 static int
1163 gcore_prgetlwpstatus(mdb_proc_t *p, uintptr_t t_addr, mdb_kthread_t *t,
1164     lwpstatus_t *sp, zone_t *zp)