Print this page
    
15254 %ymm registers not restored after signal handler
15367 x86 getfpregs() summons corrupting %xmm ghosts
15333 want x86 /proc xregs support (libc_db, libproc, mdb, etc.)
15336 want libc functions for extended ucontext_t
15334 want ps_lwphandle-specific reg routines
15328 FPU_CW_INIT mistreats reserved bit
15335 i86pc fpu_subr.c isn't really platform-specific
15332 setcontext(2) isn't actually noreturn
15331 need <sys/stdalign.h>
Change-Id: I7060aa86042dfb989f77fc3323c065ea2eafa9ad
Conflicts:
    usr/src/uts/common/fs/proc/prcontrol.c
    usr/src/uts/intel/os/archdep.c
    usr/src/uts/intel/sys/ucontext.h
    usr/src/uts/intel/syscall/getcontext.c
    
      
        | Split | 
	Close | 
      
      | Expand all | 
      | Collapse all | 
    
    
          --- old/usr/src/lib/libproc/common/Pgcore.c
          +++ new/usr/src/lib/libproc/common/Pgcore.c
   1    1  /*
   2    2   * CDDL HEADER START
   3    3   *
   4    4   * The contents of this file are subject to the terms of the
   5    5   * Common Development and Distribution License (the "License").
   6    6   * You may not use this file except in compliance with the License.
   7    7   *
   8    8   * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
   9    9   * or http://www.opensolaris.org/os/licensing.
  10   10   * See the License for the specific language governing permissions
  11   11   * and limitations under the License.
  12   12   *
  13   13   * When distributing Covered Code, include this CDDL HEADER in each
  14   14   * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
  15   15   * If applicable, add the following below this CDDL HEADER, with the
  16   16   * fields enclosed by brackets "[]" replaced with your own identifying
  17   17   * information: Portions Copyright [yyyy] [name of copyright owner]
  18   18   *
  19   19   * CDDL HEADER END
  20   20   */
  
    | 
      ↓ open down ↓ | 
    20 lines elided | 
    
      ↑ open up ↑ | 
  
  21   21  
  22   22  /*
  23   23   * Copyright 2009 Sun Microsystems, Inc.  All rights reserved.
  24   24   * Use is subject to license terms.
  25   25   */
  26   26  /*
  27   27   * Copyright 2012 DEY Storage Systems, Inc.  All rights reserved.
  28   28   * Copyright 2018 Joyent, Inc.
  29   29   * Copyright (c) 2013 by Delphix. All rights reserved.
  30   30   * Copyright 2020 OmniOS Community Edition (OmniOSce) Association.
  31      - * Copyright 2021 Oxide Computer Company
       31 + * Copyright 2023 Oxide Computer Company
  32   32   */
  33   33  
  34   34  #define _STRUCTURED_PROC        1
  35   35  
  36   36  #include <assert.h>
  37   37  #include <stdlib.h>
  38   38  #include <ctype.h>
  39   39  #include <string.h>
  40   40  #include <strings.h>
  41   41  #include <errno.h>
  42   42  #include <procfs.h>
  43   43  #include <priv.h>
  44   44  #include <sys/elf.h>
  45   45  #include <sys/machelf.h>
  46   46  #include <sys/sysmacros.h>
  47   47  #include <sys/systeminfo.h>
  48   48  #include <sys/proc.h>
  49   49  #include <sys/utsname.h>
  50   50  #include <core_shstrtab.h>
  51   51  
  52   52  #include <sys/old_procfs.h>
  53   53  
  54   54  #include "Pcontrol.h"
  55   55  #include "P32ton.h"
  56   56  #include "proc_fd.h"
  57   57  
  58   58  typedef struct {
  59   59          struct ps_prochandle *P;
  60   60          int             pgc_fd;
  61   61          off64_t         *pgc_poff;
  62   62          off64_t         *pgc_soff;
  63   63          off64_t         *pgc_doff;
  64   64          core_content_t  pgc_content;
  65   65          void            *pgc_chunk;
  66   66          size_t          pgc_chunksz;
  67   67  
  68   68          shstrtab_t      pgc_shstrtab;
  69   69  } pgcore_t;
  70   70  
  71   71  typedef struct {
  72   72          int             fd_fd;
  73   73          off64_t         *fd_doff;
  74   74  } fditer_t;
  75   75  
  76   76  static int
  77   77  gc_pwrite64(int fd, const void *buf, size_t len, off64_t off)
  78   78  {
  79   79          int err;
  80   80  
  81   81          err = pwrite64(fd, buf, len, off);
  82   82  
  83   83          if (err < 0)
  84   84                  return (err);
  85   85  
  86   86          /*
  87   87           * We will take a page from ZFS's book here and use the otherwise
  88   88           * unused EBADE to mean a short write.  Typically this will actually
  89   89           * result from ENOSPC or EDQUOT, but we can't be sure.
  90   90           */
  91   91          if (err < len) {
  92   92                  errno = EBADE;
  93   93                  return (-1);
  94   94          }
  95   95  
  96   96          return (0);
  97   97  }
  98   98  
  99   99  int
 100  100  Pgcore(struct ps_prochandle *P, const char *fname, core_content_t content)
 101  101  {
 102  102          int fd;
 103  103          int err;
 104  104          int saved_errno;
 105  105  
 106  106          if ((fd = creat64(fname, 0666)) < 0)
 107  107                  return (-1);
 108  108  
 109  109          if ((err = Pfgcore(P, fd, content)) != 0) {
 110  110                  saved_errno = errno;
 111  111                  (void) close(fd);
 112  112                  (void) unlink(fname);
 113  113                  errno = saved_errno;
 114  114                  return (err);
 115  115          }
 116  116  
 117  117          return (close(fd));
 118  118  }
 119  119  
 120  120  /*
 121  121   * Since we don't want to use the old-school procfs interfaces, we use the
 122  122   * new-style data structures we already have to construct the old-style
 123  123   * data structures. We include these data structures in core files for
 124  124   * backward compatability.
 125  125   */
 126  126  
 127  127  static void
 128  128  mkprstatus(struct ps_prochandle *P, const lwpstatus_t *lsp,
 129  129      const lwpsinfo_t *lip, prstatus_t *psp)
 130  130  {
 131  131          bzero(psp, sizeof (*psp));
 132  132  
 133  133          if (lsp->pr_flags & PR_STOPPED)
 134  134                  psp->pr_flags = 0x0001;
 135  135          if (lsp->pr_flags & PR_ISTOP)
 136  136                  psp->pr_flags = 0x0002;
 137  137          if (lsp->pr_flags & PR_DSTOP)
 138  138                  psp->pr_flags = 0x0004;
 139  139          if (lsp->pr_flags & PR_ASLEEP)
 140  140                  psp->pr_flags = 0x0008;
 141  141          if (lsp->pr_flags & PR_FORK)
 142  142                  psp->pr_flags = 0x0010;
 143  143          if (lsp->pr_flags & PR_RLC)
 144  144                  psp->pr_flags = 0x0020;
 145  145          /*
 146  146           * Note that PR_PTRACE (0x0040) from <sys/old_procfs.h> is never set;
 147  147           * PR_PCOMPAT corresponds to PR_PTRACE in the newer <sys/procfs.h>.
 148  148           */
 149  149          if (lsp->pr_flags & PR_PCINVAL)
 150  150                  psp->pr_flags = 0x0080;
 151  151          if (lsp->pr_flags & PR_ISSYS)
 152  152                  psp->pr_flags = 0x0100;
 153  153          if (lsp->pr_flags & PR_STEP)
 154  154                  psp->pr_flags = 0x0200;
 155  155          if (lsp->pr_flags & PR_KLC)
 156  156                  psp->pr_flags = 0x0400;
 157  157          if (lsp->pr_flags & PR_ASYNC)
 158  158                  psp->pr_flags = 0x0800;
 159  159          if (lsp->pr_flags & PR_PTRACE)
 160  160                  psp->pr_flags = 0x1000;
 161  161          if (lsp->pr_flags & PR_MSACCT)
 162  162                  psp->pr_flags = 0x2000;
 163  163          if (lsp->pr_flags & PR_BPTADJ)
 164  164                  psp->pr_flags = 0x4000;
 165  165          if (lsp->pr_flags & PR_ASLWP)
 166  166                  psp->pr_flags = 0x8000;
 167  167  
 168  168          psp->pr_why = lsp->pr_why;
 169  169          psp->pr_what = lsp->pr_what;
 170  170          psp->pr_info = lsp->pr_info;
 171  171          psp->pr_cursig = lsp->pr_cursig;
 172  172          psp->pr_nlwp = P->status.pr_nlwp;
 173  173          psp->pr_sigpend = P->status.pr_sigpend;
 174  174          psp->pr_sighold = lsp->pr_lwphold;
 175  175          psp->pr_altstack = lsp->pr_altstack;
 176  176          psp->pr_action = lsp->pr_action;
 177  177          psp->pr_pid = P->status.pr_pid;
 178  178          psp->pr_ppid = P->status.pr_ppid;
 179  179          psp->pr_pgrp = P->status.pr_pgid;
 180  180          psp->pr_sid = P->status.pr_sid;
 181  181          psp->pr_utime = P->status.pr_utime;
 182  182          psp->pr_stime = P->status.pr_stime;
 183  183          psp->pr_cutime = P->status.pr_cutime;
 184  184          psp->pr_cstime = P->status.pr_cstime;
 185  185          (void) strncpy(psp->pr_clname, lsp->pr_clname, sizeof (psp->pr_clname));
 186  186          psp->pr_syscall = lsp->pr_syscall;
 187  187          psp->pr_nsysarg = lsp->pr_nsysarg;
 188  188          bcopy(lsp->pr_sysarg, psp->pr_sysarg, sizeof (psp->pr_sysarg));
 189  189          psp->pr_who = lsp->pr_lwpid;
 190  190          psp->pr_lwppend = lsp->pr_lwppend;
 191  191          psp->pr_oldcontext = (ucontext_t *)lsp->pr_oldcontext;
 192  192          psp->pr_brkbase = (caddr_t)P->status.pr_brkbase;
 193  193          psp->pr_brksize = P->status.pr_brksize;
 194  194          psp->pr_stkbase = (caddr_t)P->status.pr_stkbase;
 195  195          psp->pr_stksize = P->status.pr_stksize;
 196  196          psp->pr_processor = (short)lip->pr_onpro;
 197  197          psp->pr_bind = (short)lip->pr_bindpro;
 198  198          psp->pr_instr = lsp->pr_instr;
 199  199          bcopy(lsp->pr_reg, psp->pr_reg, sizeof (psp->pr_sysarg));
 200  200  }
 201  201  
 202  202  static void
 203  203  mkprpsinfo(struct ps_prochandle *P, prpsinfo_t *psp)
 204  204  {
 205  205          bzero(psp, sizeof (*psp));
 206  206          psp->pr_state = P->psinfo.pr_lwp.pr_state;
 207  207          psp->pr_sname = P->psinfo.pr_lwp.pr_sname;
 208  208          psp->pr_zomb = (psp->pr_state == SZOMB);
 209  209          psp->pr_nice = P->psinfo.pr_lwp.pr_nice;
 210  210          psp->pr_flag = P->psinfo.pr_lwp.pr_flag;
 211  211          psp->pr_uid = P->psinfo.pr_uid;
 212  212          psp->pr_gid = P->psinfo.pr_gid;
 213  213          psp->pr_pid = P->psinfo.pr_pid;
 214  214          psp->pr_ppid = P->psinfo.pr_ppid;
 215  215          psp->pr_pgrp = P->psinfo.pr_pgid;
 216  216          psp->pr_sid = P->psinfo.pr_sid;
 217  217          psp->pr_addr = (caddr_t)P->psinfo.pr_addr;
 218  218          psp->pr_size = P->psinfo.pr_size;
 219  219          psp->pr_rssize = P->psinfo.pr_rssize;
 220  220          psp->pr_wchan = (caddr_t)P->psinfo.pr_lwp.pr_wchan;
 221  221          psp->pr_start = P->psinfo.pr_start;
 222  222          psp->pr_time = P->psinfo.pr_time;
 223  223          psp->pr_pri = P->psinfo.pr_lwp.pr_pri;
 224  224          psp->pr_oldpri = P->psinfo.pr_lwp.pr_oldpri;
 225  225          psp->pr_cpu = P->psinfo.pr_lwp.pr_cpu;
 226  226          psp->pr_ottydev = cmpdev(P->psinfo.pr_ttydev);
 227  227          psp->pr_lttydev = P->psinfo.pr_ttydev;
 228  228          (void) strncpy(psp->pr_clname, P->psinfo.pr_lwp.pr_clname,
 229  229              sizeof (psp->pr_clname));
 230  230          (void) strncpy(psp->pr_fname, P->psinfo.pr_fname,
 231  231              sizeof (psp->pr_fname));
 232  232          bcopy(&P->psinfo.pr_psargs, &psp->pr_psargs,
 233  233              sizeof (psp->pr_psargs));
 234  234          psp->pr_syscall = P->psinfo.pr_lwp.pr_syscall;
 235  235          psp->pr_ctime = P->psinfo.pr_ctime;
 236  236          psp->pr_bysize = psp->pr_size * PAGESIZE;
 237  237          psp->pr_byrssize = psp->pr_rssize * PAGESIZE;
 238  238          psp->pr_argc = P->psinfo.pr_argc;
 239  239          psp->pr_argv = (char **)P->psinfo.pr_argv;
 240  240          psp->pr_envp = (char **)P->psinfo.pr_envp;
 241  241          psp->pr_wstat = P->psinfo.pr_wstat;
 242  242          psp->pr_pctcpu = P->psinfo.pr_pctcpu;
 243  243          psp->pr_pctmem = P->psinfo.pr_pctmem;
 244  244          psp->pr_euid = P->psinfo.pr_euid;
 245  245          psp->pr_egid = P->psinfo.pr_egid;
 246  246          psp->pr_aslwpid = 0;
 247  247          psp->pr_dmodel = P->psinfo.pr_dmodel;
 248  248  }
 249  249  
 250  250  #ifdef _LP64
 251  251  
 252  252  static void
 253  253  mkprstatus32(struct ps_prochandle *P, const lwpstatus_t *lsp,
 254  254      const lwpsinfo_t *lip, prstatus32_t *psp)
 255  255  {
 256  256          bzero(psp, sizeof (*psp));
 257  257  
 258  258          if (lsp->pr_flags & PR_STOPPED)
 259  259                  psp->pr_flags = 0x0001;
 260  260          if (lsp->pr_flags & PR_ISTOP)
 261  261                  psp->pr_flags = 0x0002;
 262  262          if (lsp->pr_flags & PR_DSTOP)
 263  263                  psp->pr_flags = 0x0004;
 264  264          if (lsp->pr_flags & PR_ASLEEP)
 265  265                  psp->pr_flags = 0x0008;
 266  266          if (lsp->pr_flags & PR_FORK)
 267  267                  psp->pr_flags = 0x0010;
 268  268          if (lsp->pr_flags & PR_RLC)
 269  269                  psp->pr_flags = 0x0020;
 270  270          /*
 271  271           * Note that PR_PTRACE (0x0040) from <sys/old_procfs.h> is never set;
 272  272           * PR_PCOMPAT corresponds to PR_PTRACE in the newer <sys/procfs.h>.
 273  273           */
 274  274          if (lsp->pr_flags & PR_PCINVAL)
 275  275                  psp->pr_flags = 0x0080;
 276  276          if (lsp->pr_flags & PR_ISSYS)
 277  277                  psp->pr_flags = 0x0100;
 278  278          if (lsp->pr_flags & PR_STEP)
 279  279                  psp->pr_flags = 0x0200;
 280  280          if (lsp->pr_flags & PR_KLC)
 281  281                  psp->pr_flags = 0x0400;
 282  282          if (lsp->pr_flags & PR_ASYNC)
 283  283                  psp->pr_flags = 0x0800;
 284  284          if (lsp->pr_flags & PR_PTRACE)
 285  285                  psp->pr_flags = 0x1000;
 286  286          if (lsp->pr_flags & PR_MSACCT)
 287  287                  psp->pr_flags = 0x2000;
 288  288          if (lsp->pr_flags & PR_BPTADJ)
 289  289                  psp->pr_flags = 0x4000;
 290  290          if (lsp->pr_flags & PR_ASLWP)
 291  291                  psp->pr_flags = 0x8000;
 292  292  
 293  293          psp->pr_why = lsp->pr_why;
 294  294          psp->pr_what = lsp->pr_what;
 295  295          siginfo_n_to_32(&lsp->pr_info, &psp->pr_info);
 296  296          psp->pr_cursig = lsp->pr_cursig;
 297  297          psp->pr_nlwp = P->status.pr_nlwp;
 298  298          psp->pr_sigpend = P->status.pr_sigpend;
 299  299          psp->pr_sighold = lsp->pr_lwphold;
 300  300          stack_n_to_32(&lsp->pr_altstack, &psp->pr_altstack);
 301  301          sigaction_n_to_32(&lsp->pr_action, &psp->pr_action);
 302  302          psp->pr_pid = P->status.pr_pid;
 303  303          psp->pr_ppid = P->status.pr_ppid;
 304  304          psp->pr_pgrp = P->status.pr_pgid;
 305  305          psp->pr_sid = P->status.pr_sid;
 306  306          timestruc_n_to_32(&P->status.pr_utime, &psp->pr_utime);
 307  307          timestruc_n_to_32(&P->status.pr_stime, &psp->pr_stime);
 308  308          timestruc_n_to_32(&P->status.pr_cutime, &psp->pr_cutime);
 309  309          timestruc_n_to_32(&P->status.pr_cstime, &psp->pr_cstime);
 310  310          (void) strncpy(psp->pr_clname, lsp->pr_clname, sizeof (psp->pr_clname));
 311  311          psp->pr_syscall = lsp->pr_syscall;
 312  312          psp->pr_nsysarg = lsp->pr_nsysarg;
 313  313          bcopy(lsp->pr_sysarg, psp->pr_sysarg, sizeof (psp->pr_sysarg));
 314  314          psp->pr_who = lsp->pr_lwpid;
 315  315          psp->pr_lwppend = lsp->pr_lwppend;
 316  316          psp->pr_oldcontext = (caddr32_t)lsp->pr_oldcontext;
 317  317          psp->pr_brkbase = (caddr32_t)P->status.pr_brkbase;
 318  318          psp->pr_brksize = P->status.pr_brksize;
 319  319          psp->pr_stkbase = (caddr32_t)P->status.pr_stkbase;
 320  320          psp->pr_stksize = P->status.pr_stksize;
 321  321          psp->pr_processor = (short)lip->pr_onpro;
 322  322          psp->pr_bind = (short)lip->pr_bindpro;
 323  323          psp->pr_instr = lsp->pr_instr;
 324  324          bcopy(lsp->pr_reg, psp->pr_reg, sizeof (psp->pr_sysarg));
 325  325  }
 326  326  
 327  327  static void
 328  328  mkprpsinfo32(struct ps_prochandle *P, prpsinfo32_t *psp)
 329  329  {
 330  330          bzero(psp, sizeof (*psp));
 331  331          psp->pr_state = P->psinfo.pr_lwp.pr_state;
 332  332          psp->pr_sname = P->psinfo.pr_lwp.pr_sname;
 333  333          psp->pr_zomb = (psp->pr_state == SZOMB);
 334  334          psp->pr_nice = P->psinfo.pr_lwp.pr_nice;
 335  335          psp->pr_flag = P->psinfo.pr_lwp.pr_flag;
 336  336          psp->pr_uid = P->psinfo.pr_uid;
 337  337          psp->pr_gid = P->psinfo.pr_gid;
 338  338          psp->pr_pid = P->psinfo.pr_pid;
 339  339          psp->pr_ppid = P->psinfo.pr_ppid;
 340  340          psp->pr_pgrp = P->psinfo.pr_pgid;
 341  341          psp->pr_sid = P->psinfo.pr_sid;
 342  342          psp->pr_addr = (caddr32_t)P->psinfo.pr_addr;
 343  343          psp->pr_size = P->psinfo.pr_size;
 344  344          psp->pr_rssize = P->psinfo.pr_rssize;
 345  345          psp->pr_wchan = (caddr32_t)P->psinfo.pr_lwp.pr_wchan;
 346  346          timestruc_n_to_32(&P->psinfo.pr_start, &psp->pr_start);
 347  347          timestruc_n_to_32(&P->psinfo.pr_time, &psp->pr_time);
 348  348          psp->pr_pri = P->psinfo.pr_lwp.pr_pri;
 349  349          psp->pr_oldpri = P->psinfo.pr_lwp.pr_oldpri;
 350  350          psp->pr_cpu = P->psinfo.pr_lwp.pr_cpu;
 351  351          psp->pr_ottydev = cmpdev(P->psinfo.pr_ttydev);
 352  352          psp->pr_lttydev = prcmpldev(P->psinfo.pr_ttydev);
 353  353          (void) strncpy(psp->pr_clname, P->psinfo.pr_lwp.pr_clname,
 354  354              sizeof (psp->pr_clname));
 355  355          (void) strncpy(psp->pr_fname, P->psinfo.pr_fname,
 356  356              sizeof (psp->pr_fname));
 357  357          bcopy(&P->psinfo.pr_psargs, &psp->pr_psargs,
 358  358              sizeof (psp->pr_psargs));
 359  359          psp->pr_syscall = P->psinfo.pr_lwp.pr_syscall;
 360  360          timestruc_n_to_32(&P->psinfo.pr_ctime, &psp->pr_ctime);
 361  361          psp->pr_bysize = psp->pr_size * PAGESIZE;
 362  362          psp->pr_byrssize = psp->pr_rssize * PAGESIZE;
 363  363          psp->pr_argc = P->psinfo.pr_argc;
 364  364          psp->pr_argv = (caddr32_t)P->psinfo.pr_argv;
 365  365          psp->pr_envp = (caddr32_t)P->psinfo.pr_envp;
 366  366          psp->pr_wstat = P->psinfo.pr_wstat;
 367  367          psp->pr_pctcpu = P->psinfo.pr_pctcpu;
 368  368          psp->pr_pctmem = P->psinfo.pr_pctmem;
 369  369          psp->pr_euid = P->psinfo.pr_euid;
 370  370          psp->pr_egid = P->psinfo.pr_egid;
 371  371          psp->pr_aslwpid = 0;
 372  372          psp->pr_dmodel = P->psinfo.pr_dmodel;
 373  373  }
 374  374  
 375  375  #endif  /* _LP64 */
 376  376  
 377  377  static int
 378  378  write_note(int fd, uint_t type, const void *desc, size_t descsz, off64_t *offp)
 379  379  {
 380  380          /*
 381  381           * Note headers are the same regardless of the data model of the
 382  382           * ELF file; we arbitrarily use Elf64_Nhdr here.
 383  383           */
 384  384          struct {
 385  385                  Elf64_Nhdr nhdr;
 386  386                  char name[8];
 387  387          } n;
 388  388  
 389  389          bzero(&n, sizeof (n));
 390  390          bcopy("CORE", n.name, 4);
 391  391          n.nhdr.n_type = type;
 392  392          n.nhdr.n_namesz = 5;
 393  393          n.nhdr.n_descsz = roundup(descsz, 4);
 394  394  
 395  395          if (gc_pwrite64(fd, &n, sizeof (n), *offp) != 0)
 396  396                  return (-1);
 397  397  
 398  398          *offp += sizeof (n);
 399  399  
 400  400          if (gc_pwrite64(fd, desc, n.nhdr.n_descsz, *offp) != 0)
 401  401                  return (-1);
 402  402  
 403  403          *offp += n.nhdr.n_descsz;
 404  404  
 405  405          return (0);
 406  406  }
 407  407  
 408  408  static int
 409  409  old_per_lwp(void *data, const lwpstatus_t *lsp, const lwpsinfo_t *lip)
 410  410  {
 411  411          pgcore_t *pgc = data;
 412  412          struct ps_prochandle *P = pgc->P;
 413  413  
 414  414          /*
 415  415           * Legacy core files don't contain information about zombie LWPs.
 416  416           * We use Plwp_iter_all() so that we get the lwpsinfo_t structure
 417  417           * more cheaply.
 418  418           */
 419  419          if (lsp == NULL)
 420  420                  return (0);
 421  421  
 422  422          if (P->status.pr_dmodel == PR_MODEL_NATIVE) {
 423  423                  prstatus_t prstatus;
 424  424                  mkprstatus(P, lsp, lip, &prstatus);
 425  425                  if (write_note(pgc->pgc_fd, NT_PRSTATUS, &prstatus,
 426  426                      sizeof (prstatus_t), pgc->pgc_doff) != 0)
 427  427                          return (0);
 428  428                  if (write_note(pgc->pgc_fd, NT_PRFPREG, &lsp->pr_fpreg,
 429  429                      sizeof (prfpregset_t), pgc->pgc_doff) != 0)
 430  430                          return (1);
 431  431  #ifdef _LP64
 432  432          } else {
 433  433                  prstatus32_t pr32;
 434  434                  prfpregset32_t pf32;
 435  435                  mkprstatus32(P, lsp, lip, &pr32);
  
    | 
      ↓ open down ↓ | 
    394 lines elided | 
    
      ↑ open up ↑ | 
  
 436  436                  if (write_note(pgc->pgc_fd, NT_PRSTATUS, &pr32,
 437  437                      sizeof (prstatus32_t), pgc->pgc_doff) != 0)
 438  438                          return (1);
 439  439                  prfpregset_n_to_32(&lsp->pr_fpreg, &pf32);
 440  440                  if (write_note(pgc->pgc_fd, NT_PRFPREG, &pf32,
 441  441                      sizeof (prfpregset32_t), pgc->pgc_doff) != 0)
 442  442                          return (1);
 443  443  #endif  /* _LP64 */
 444  444          }
 445  445  
 446      -#ifdef sparc
 447      -        {
 448      -                prxregset_t xregs;
 449      -                if (Plwp_getxregs(P, lsp->pr_lwpid, &xregs) == 0 &&
 450      -                    write_note(pgc->pgc_fd, NT_PRXREG, &xregs,
 451      -                    sizeof (prxregset_t), pgc->pgc_doff) != 0)
 452      -                        return (1);
 453      -        }
 454      -#endif  /* sparc */
 455      -
 456  446          return (0);
 457  447  }
 458  448  
 459  449  static int
 460  450  new_per_lwp(void *data, const lwpstatus_t *lsp, const lwpsinfo_t *lip)
 461  451  {
 462  452          pgcore_t *pgc = data;
 463  453          struct ps_prochandle *P = pgc->P;
 464  454          prlwpname_t name = { 0, "" };
 465  455          psinfo_t ps;
 466  456  
 467  457          /*
 468  458           * If lsp is NULL this indicates that this is a zombie LWP in
 469  459           * which case we dump only the lwpsinfo_t structure and none of
 470  460           * the other ancillary LWP state data.
 471  461           */
 472  462          if (P->status.pr_dmodel == PR_MODEL_NATIVE) {
 473  463                  if (write_note(pgc->pgc_fd, NT_LWPSINFO, lip,
 474  464                      sizeof (lwpsinfo_t), pgc->pgc_doff) != 0)
 475  465                          return (1);
 476  466                  if (lsp == NULL)
 477  467                          return (0);
 478  468                  if (write_note(pgc->pgc_fd, NT_LWPSTATUS, lsp,
 479  469                      sizeof (lwpstatus_t), pgc->pgc_doff) != 0)
 480  470                          return (1);
 481  471  #ifdef _LP64
 482  472          } else {
 483  473                  lwpsinfo32_t li32;
 484  474                  lwpstatus32_t ls32;
 485  475                  lwpsinfo_n_to_32(lip, &li32);
 486  476                  if (write_note(pgc->pgc_fd, NT_LWPSINFO, &li32,
 487  477                      sizeof (lwpsinfo32_t), pgc->pgc_doff) != 0)
  
    | 
      ↓ open down ↓ | 
    22 lines elided | 
    
      ↑ open up ↑ | 
  
 488  478                          return (1);
 489  479                  if (lsp == NULL)
 490  480                          return (0);
 491  481                  lwpstatus_n_to_32(lsp, &ls32);
 492  482                  if (write_note(pgc->pgc_fd, NT_LWPSTATUS, &ls32,
 493  483                      sizeof (lwpstatus32_t), pgc->pgc_doff) != 0)
 494  484                          return (1);
 495  485  #endif  /* _LP64 */
 496  486          }
 497  487  
 498      -#ifdef sparc
 499  488          {
 500      -                prxregset_t xregs;
 501      -                gwindows_t gwins;
      489 +                prxregset_t *xregs;
 502  490                  size_t size;
 503  491  
 504      -                if (Plwp_getxregs(P, lsp->pr_lwpid, &xregs) == 0) {
 505      -                        if (write_note(pgc->pgc_fd, NT_PRXREG, &xregs,
 506      -                            sizeof (prxregset_t), pgc->pgc_doff) != 0)
 507      -                                return (1);
 508      -                }
 509      -
 510      -                if (Plwp_getgwindows(P, lsp->pr_lwpid, &gwins) == 0 &&
 511      -                    gwins.wbcnt > 0) {
 512      -                        size = sizeof (gwins) - sizeof (gwins.wbuf) +
 513      -                            gwins.wbcnt * sizeof (gwins.wbuf[0]);
 514      -
 515      -                        if (write_note(pgc->pgc_fd, NT_GWINDOWS, &gwins, size,
      492 +                /*
      493 +                 * While historically this function was only present on some
      494 +                 * architectures (despite the presence of the empty file
      495 +                 * elsewhere), if we call this on a platform without support
      496 +                 * it'll now fail and thus is no longer subject to
      497 +                 * platform-specific ifdefs.
      498 +                 */
      499 +                if (Plwp_getxregs(P, lsp->pr_lwpid, &xregs, &size) == 0) {
      500 +                        if (write_note(pgc->pgc_fd, NT_PRXREG, xregs, size,
 516  501                              pgc->pgc_doff) != 0)
 517  502                                  return (1);
 518      -                }
 519  503  
 520      -        }
 521      -#ifdef __sparcv9
 522      -        if (P->status.pr_dmodel == PR_MODEL_LP64) {
 523      -                asrset_t asrs;
 524      -                if (Plwp_getasrs(P, lsp->pr_lwpid, asrs) == 0) {
 525      -                        if (write_note(pgc->pgc_fd, NT_ASRS, &asrs,
 526      -                            sizeof (asrset_t), pgc->pgc_doff) != 0)
 527      -                                return (1);
      504 +                        Plwp_freexregs(P, xregs, size);
 528  505                  }
 529  506          }
 530      -#endif  /* __sparcv9 */
 531      -#endif  /* sparc */
 532  507  
 533  508          if (Plwp_getname(P, lsp->pr_lwpid, name.pr_lwpname,
 534  509              sizeof (name.pr_lwpname)) == 0) {
 535  510                  name.pr_lwpid = lsp->pr_lwpid;
 536  511                  if (write_note(pgc->pgc_fd, NT_LWPNAME, &name,
 537  512                      sizeof (name), pgc->pgc_doff) != 0)
 538  513                          return (1);
 539  514          }
 540  515  
 541  516          if (!(lsp->pr_flags & PR_AGENT))
 542  517                  return (0);
 543  518  
 544  519          if (Plwp_getspymaster(P, lsp->pr_lwpid, &ps) != 0)
 545  520                  return (0);
 546  521  
 547  522          if (P->status.pr_dmodel == PR_MODEL_NATIVE) {
 548  523                  if (write_note(pgc->pgc_fd, NT_SPYMASTER, &ps,
 549  524                      sizeof (psinfo_t), pgc->pgc_doff) != 0)
 550  525                          return (1);
 551  526  #ifdef _LP64
 552  527          } else {
 553  528                  psinfo32_t ps32;
 554  529                  psinfo_n_to_32(&ps, &ps32);
 555  530                  if (write_note(pgc->pgc_fd, NT_SPYMASTER, &ps32,
 556  531                      sizeof (psinfo32_t), pgc->pgc_doff) != 0)
 557  532                          return (1);
 558  533  #endif  /* _LP64 */
 559  534          }
 560  535  
 561  536  
 562  537          return (0);
 563  538  }
 564  539  
 565  540  static int
 566  541  iter_fd(void *data, const prfdinfo_t *fdinfo)
 567  542  {
 568  543          fditer_t *iter = data;
 569  544          prfdinfo_core_t core;
 570  545          int ret = 0;
 571  546  
 572  547          if (proc_fdinfo_to_core(fdinfo, &core) != 0)
 573  548                  return (1);
 574  549  
 575  550          ret = write_note(iter->fd_fd, NT_FDINFO, &core,
 576  551              sizeof (core), iter->fd_doff);
 577  552  
 578  553          if (ret != 0)
 579  554                  return (1);
 580  555          return (0);
 581  556  }
 582  557  
 583  558  /*
 584  559   * Look for sections that begin with the string '.debug_'. In particular, this
 585  560   * will catch all DWARF related sections and it will catch those that different
 586  561   * folks use that are not related to DWARF, but still begin with this prefix
 587  562   * (e.g. .debug_gdb_scripts). Notably though, this does not catch something like
 588  563   * stabs (though it could). This really is filtering based on the section name,
 589  564   * less so intent.
 590  565   */
 591  566  static boolean_t
 592  567  is_debug_section(file_info_t *fptr, GElf_Shdr *shdr)
 593  568  {
 594  569          if (shdr->sh_name == 0 || shdr->sh_name > fptr->file_shstrsz)
 595  570                  return (B_FALSE);
 596  571  
 597  572          if (strncmp(fptr->file_shstrs + shdr->sh_name, ".debug_",
 598  573              strlen(".debug_")) != 0) {
 599  574                  return (B_FALSE);
 600  575          }
 601  576  
 602  577          return (B_TRUE);
 603  578  }
 604  579  
 605  580  static uint_t
 606  581  count_debug(file_info_t *fptr)
 607  582  {
 608  583          uint_t count = 0;
 609  584          Elf_Scn *scn = NULL;
 610  585  
 611  586          if (fptr->file_elf == NULL || fptr->file_shstrsz <= 1) {
 612  587                  return (0);
 613  588          }
 614  589  
 615  590          while ((scn = elf_nextscn(fptr->file_elf, scn)) != NULL) {
 616  591                  GElf_Shdr shdr;
 617  592  
 618  593                  if (gelf_getshdr(scn, &shdr) == NULL)
 619  594                          continue;
 620  595  
 621  596                  if (is_debug_section(fptr, &shdr))
 622  597                          count++;
 623  598          }
 624  599  
 625  600          return (count);
 626  601  }
 627  602  
 628  603  static uint_t
 629  604  count_sections(pgcore_t *pgc)
 630  605  {
 631  606          struct ps_prochandle *P = pgc->P;
 632  607          file_info_t *fptr;
 633  608          uint_t nshdrs = 0;
 634  609  
 635  610          if (!(pgc->pgc_content & (CC_CONTENT_CTF | CC_CONTENT_SYMTAB |
 636  611              CC_CONTENT_DEBUG))) {
 637  612                  return (0);
 638  613          }
 639  614  
 640  615          for (fptr = list_head(&P->file_head); fptr != NULL;
 641  616              fptr = list_next(&P->file_head, fptr)) {
 642  617                  int hit_symtab = 0;
 643  618  
 644  619                  Pbuild_file_symtab(P, fptr);
 645  620  
 646  621                  if ((pgc->pgc_content & CC_CONTENT_CTF) &&
 647  622                      Pbuild_file_ctf(P, fptr) != NULL) {
 648  623                          sym_tbl_t *sym;
 649  624  
 650  625                          nshdrs++;
 651  626  
 652  627                          if (fptr->file_ctf_dyn) {
 653  628                                  sym = &fptr->file_dynsym;
 654  629                          } else {
 655  630                                  sym = &fptr->file_symtab;
 656  631                                  hit_symtab = 1;
 657  632                          }
 658  633  
 659  634                          if (sym->sym_data_pri != NULL && sym->sym_symn != 0 &&
 660  635                              sym->sym_strs != NULL)
 661  636                                  nshdrs += 2;
 662  637                  }
 663  638  
 664  639                  if ((pgc->pgc_content & CC_CONTENT_SYMTAB) && !hit_symtab &&
 665  640                      fptr->file_symtab.sym_data_pri != NULL &&
 666  641                      fptr->file_symtab.sym_symn != 0 &&
 667  642                      fptr->file_symtab.sym_strs != NULL) {
 668  643                          nshdrs += 2;
 669  644                  }
 670  645  
 671  646                  if ((pgc->pgc_content & CC_CONTENT_DEBUG) != 0)
 672  647                          nshdrs += count_debug(fptr);
 673  648          }
 674  649  
 675  650          return (nshdrs == 0 ? 0 : nshdrs + 2);
 676  651  }
 677  652  
 678  653  static int
 679  654  write_shdr(pgcore_t *pgc, const char *name, uint_t type, ulong_t flags,
 680  655      uintptr_t addr, ulong_t offset, size_t size, uint_t link, uint_t info,
 681  656      uintptr_t addralign, uintptr_t entsize)
 682  657  {
 683  658          if (pgc->P->status.pr_dmodel == PR_MODEL_ILP32) {
 684  659                  Elf32_Shdr shdr;
 685  660  
 686  661                  bzero(&shdr, sizeof (shdr));
 687  662                  if (!shstrtab_ndx(&pgc->pgc_shstrtab, name, &shdr.sh_name)) {
 688  663                          return (-1);
 689  664                  }
 690  665                  shdr.sh_type = type;
 691  666                  shdr.sh_flags = flags;
 692  667                  shdr.sh_addr = (Elf32_Addr)addr;
 693  668                  shdr.sh_offset = offset;
 694  669                  shdr.sh_size = size;
 695  670                  shdr.sh_link = link;
 696  671                  shdr.sh_info = info;
 697  672                  shdr.sh_addralign = addralign;
 698  673                  shdr.sh_entsize = entsize;
 699  674  
 700  675                  if (gc_pwrite64(pgc->pgc_fd, &shdr, sizeof (shdr),
 701  676                      *pgc->pgc_soff) != 0)
 702  677                          return (-1);
 703  678  
 704  679                  *pgc->pgc_soff += sizeof (shdr);
 705  680  #ifdef _LP64
 706  681          } else {
 707  682                  Elf64_Shdr shdr;
 708  683  
 709  684                  bzero(&shdr, sizeof (shdr));
 710  685                  if (!shstrtab_ndx(&pgc->pgc_shstrtab, name, &shdr.sh_name)) {
 711  686                          return (-1);
 712  687                  }
 713  688                  shdr.sh_type = type;
 714  689                  shdr.sh_flags = flags;
 715  690                  shdr.sh_addr = addr;
 716  691                  shdr.sh_offset = offset;
 717  692                  shdr.sh_size = size;
 718  693                  shdr.sh_link = link;
 719  694                  shdr.sh_info = info;
 720  695                  shdr.sh_addralign = addralign;
 721  696                  shdr.sh_entsize = entsize;
 722  697  
 723  698                  if (gc_pwrite64(pgc->pgc_fd, &shdr, sizeof (shdr),
 724  699                      *pgc->pgc_soff) != 0)
 725  700                          return (-1);
 726  701  
 727  702                  *pgc->pgc_soff += sizeof (shdr);
 728  703  #endif  /* _LP64 */
 729  704          }
 730  705  
 731  706          return (0);
 732  707  }
 733  708  
 734  709  static int
 735  710  dump_symtab(pgcore_t *pgc, file_info_t *fptr, uint_t index, int dynsym)
 736  711  {
 737  712          sym_tbl_t *sym = dynsym ? &fptr->file_dynsym : &fptr->file_symtab;
 738  713          shstrtype_t symname = dynsym ? STR_DYNSYM : STR_SYMTAB;
 739  714          shstrtype_t strname = dynsym ? STR_DYNSTR : STR_STRTAB;
 740  715          uint_t symtype = dynsym ? SHT_DYNSYM : SHT_SYMTAB;
 741  716          size_t size;
 742  717          uintptr_t addr = fptr->file_map->map_pmap.pr_vaddr;
 743  718  
 744  719          if (sym->sym_data_pri == NULL || sym->sym_symn == 0 ||
 745  720              sym->sym_strs == NULL)
 746  721                  return (0);
 747  722  
 748  723          size = sym->sym_hdr_pri.sh_size;
 749  724          if (gc_pwrite64(pgc->pgc_fd, sym->sym_data_pri->d_buf, size,
 750  725              *pgc->pgc_doff) != 0)
 751  726                  return (-1);
 752  727  
 753  728          if (write_shdr(pgc, shstrtab_data[symname], symtype, 0, addr,
 754  729              *pgc->pgc_doff, size, index + 1, sym->sym_hdr_pri.sh_info,
 755  730              sym->sym_hdr_pri.sh_addralign, sym->sym_hdr_pri.sh_entsize) != 0)
 756  731                  return (-1);
 757  732  
 758  733          *pgc->pgc_doff += roundup(size, 8);
 759  734  
 760  735          size = sym->sym_strhdr.sh_size;
 761  736          if (gc_pwrite64(pgc->pgc_fd, sym->sym_strs, size, *pgc->pgc_doff) != 0)
 762  737                  return (-1);
 763  738  
 764  739          if (write_shdr(pgc, shstrtab_data[strname], SHT_STRTAB, SHF_STRINGS,
 765  740              addr, *pgc->pgc_doff, size, 0, 0, 1, 0) != 0)
 766  741                  return (-1);
 767  742  
 768  743          *pgc->pgc_doff += roundup(size, 8);
 769  744  
 770  745          return (0);
 771  746  }
 772  747  
 773  748  static int
 774  749  dump_debug(pgcore_t *pgc, file_info_t *fptr, uint_t *indexp)
 775  750  {
 776  751          Elf_Scn *scn = NULL;
 777  752  
 778  753          if (fptr->file_elf == NULL || fptr->file_shstrsz <= 1) {
 779  754                  return (0);
 780  755          }
 781  756  
 782  757          while ((scn = elf_nextscn(fptr->file_elf, scn)) != NULL) {
 783  758                  GElf_Shdr shdr;
 784  759                  Elf_Data *data;
 785  760  
 786  761                  if (gelf_getshdr(scn, &shdr) == NULL)
 787  762                          continue;
 788  763  
 789  764                  if (!is_debug_section(fptr, &shdr))
 790  765                          continue;
 791  766  
 792  767                  if ((data = elf_getdata(scn, NULL)) == NULL) {
 793  768                          return (-1);
 794  769                  }
 795  770  
 796  771                  if (gc_pwrite64(pgc->pgc_fd, data->d_buf, data->d_size,
 797  772                      *pgc->pgc_doff) != 0)
 798  773                          return (-1);
 799  774  
 800  775                  if (write_shdr(pgc, fptr->file_shstrs + shdr.sh_name,
 801  776                      shdr.sh_type, shdr.sh_flags,
 802  777                      fptr->file_map->map_pmap.pr_vaddr, *pgc->pgc_doff,
 803  778                      data->d_size, 0, shdr.sh_info, shdr.sh_addralign,
 804  779                      shdr.sh_entsize) != 0) {
 805  780                          return (-1);
 806  781                  }
 807  782  
 808  783                  *indexp = *indexp + 1;
 809  784                  *pgc->pgc_doff += roundup(data->d_size, 8);
 810  785          }
 811  786  
 812  787          return (0);
 813  788  }
 814  789  
 815  790  static int
 816  791  dump_sections(pgcore_t *pgc)
 817  792  {
 818  793          struct ps_prochandle *P = pgc->P;
 819  794          file_info_t *fptr;
 820  795          uint_t index = 1;
 821  796  
 822  797          if (!(pgc->pgc_content & (CC_CONTENT_CTF | CC_CONTENT_SYMTAB |
 823  798              CC_CONTENT_DEBUG))) {
 824  799                  return (0);
 825  800          }
 826  801  
 827  802          for (fptr = list_head(&P->file_head); fptr != NULL;
 828  803              fptr = list_next(&P->file_head, fptr)) {
 829  804                  int hit_symtab = 0;
 830  805  
 831  806                  Pbuild_file_symtab(P, fptr);
 832  807  
 833  808                  if ((pgc->pgc_content & CC_CONTENT_CTF) &&
 834  809                      Pbuild_file_ctf(P, fptr) != NULL) {
 835  810                          sym_tbl_t *sym;
 836  811                          uint_t dynsym;
 837  812                          uint_t symindex = 0;
 838  813  
 839  814                          /*
 840  815                           * Write the symtab out first so we can correctly
 841  816                           * set the sh_link field in the CTF section header.
 842  817                           * symindex will be 0 if there is no corresponding
 843  818                           * symbol table section.
 844  819                           */
 845  820                          if (fptr->file_ctf_dyn) {
 846  821                                  sym = &fptr->file_dynsym;
 847  822                                  dynsym = 1;
 848  823                          } else {
 849  824                                  sym = &fptr->file_symtab;
 850  825                                  dynsym = 0;
 851  826                                  hit_symtab = 1;
 852  827                          }
 853  828  
 854  829                          if (sym->sym_data_pri != NULL && sym->sym_symn != 0 &&
 855  830                              sym->sym_strs != NULL) {
 856  831                                  symindex = index;
 857  832                                  if (dump_symtab(pgc, fptr, index, dynsym) != 0)
 858  833                                          return (-1);
 859  834                                  index += 2;
 860  835                          }
 861  836  
 862  837                          /*
 863  838                           * Write the CTF data that we've read out of the
 864  839                           * file itself into the core file.
 865  840                           */
 866  841                          if (gc_pwrite64(pgc->pgc_fd, fptr->file_ctf_buf,
 867  842                              fptr->file_ctf_size, *pgc->pgc_doff) != 0)
 868  843                                  return (-1);
 869  844  
 870  845                          if (write_shdr(pgc, shstrtab_data[STR_CTF],
 871  846                              SHT_PROGBITS, 0, fptr->file_map->map_pmap.pr_vaddr,
 872  847                              *pgc->pgc_doff, fptr->file_ctf_size, symindex, 0,
 873  848                              4, 0) != 0)
 874  849                                  return (-1);
 875  850  
 876  851                          index++;
 877  852                          *pgc->pgc_doff += roundup(fptr->file_ctf_size, 8);
 878  853                  }
 879  854  
 880  855                  if ((pgc->pgc_content & CC_CONTENT_SYMTAB) && !hit_symtab &&
 881  856                      fptr->file_symtab.sym_data_pri != NULL &&
 882  857                      fptr->file_symtab.sym_symn != 0 &&
 883  858                      fptr->file_symtab.sym_strs != NULL) {
 884  859                          if (dump_symtab(pgc, fptr, index, 0) != 0)
 885  860                                  return (-1);
 886  861                          index += 2;
 887  862                  }
 888  863  
 889  864                  if ((pgc->pgc_content & CC_CONTENT_DEBUG) != 0 &&
 890  865                      dump_debug(pgc, fptr, &index) != 0) {
 891  866                          return (-1);
 892  867                  }
 893  868          }
 894  869  
 895  870          return (0);
 896  871  }
 897  872  
 898  873  /*ARGSUSED*/
 899  874  static int
 900  875  dump_map(void *data, const prmap_t *pmp, const char *name)
 901  876  {
 902  877          pgcore_t *pgc = data;
 903  878          struct ps_prochandle *P = pgc->P;
 904  879  #ifdef _LP64
 905  880          Elf64_Phdr phdr;
 906  881  #else
 907  882          Elf32_Phdr phdr;
 908  883  #endif
 909  884          size_t n;
 910  885  
 911  886          bzero(&phdr, sizeof (phdr));
 912  887          phdr.p_type = PT_LOAD;
 913  888          phdr.p_vaddr = pmp->pr_vaddr;
 914  889          phdr.p_memsz = pmp->pr_size;
 915  890          if (pmp->pr_mflags & MA_READ)
 916  891                  phdr.p_flags |= PF_R;
 917  892          if (pmp->pr_mflags & MA_WRITE)
 918  893                  phdr.p_flags |= PF_W;
 919  894          if (pmp->pr_mflags & MA_EXEC)
 920  895                  phdr.p_flags |= PF_X;
 921  896  
 922  897          if (pmp->pr_vaddr + pmp->pr_size > P->status.pr_stkbase &&
 923  898              pmp->pr_vaddr < P->status.pr_stkbase + P->status.pr_stksize) {
 924  899                  if (!(pgc->pgc_content & CC_CONTENT_STACK))
 925  900                          goto exclude;
 926  901  
 927  902          } else if ((pmp->pr_mflags & MA_ANON) &&
 928  903              pmp->pr_vaddr + pmp->pr_size > P->status.pr_brkbase &&
 929  904              pmp->pr_vaddr < P->status.pr_brkbase + P->status.pr_brksize) {
 930  905                  if (!(pgc->pgc_content & CC_CONTENT_HEAP))
 931  906                          goto exclude;
 932  907  
 933  908          } else if (pmp->pr_mflags & MA_ISM) {
 934  909                  if (pmp->pr_mflags & MA_NORESERVE) {
 935  910                          if (!(pgc->pgc_content & CC_CONTENT_DISM))
 936  911                                  goto exclude;
 937  912                  } else {
 938  913                          if (!(pgc->pgc_content & CC_CONTENT_ISM))
 939  914                                  goto exclude;
 940  915                  }
 941  916  
 942  917          } else if (pmp->pr_mflags & MA_SHM) {
 943  918                  if (!(pgc->pgc_content & CC_CONTENT_SHM))
 944  919                          goto exclude;
 945  920  
 946  921          } else if (pmp->pr_mflags & MA_SHARED) {
 947  922                  if (pmp->pr_mflags & MA_ANON) {
 948  923                          if (!(pgc->pgc_content & CC_CONTENT_SHANON))
 949  924                                  goto exclude;
 950  925                  } else {
 951  926                          if (!(pgc->pgc_content & CC_CONTENT_SHFILE))
 952  927                                  goto exclude;
 953  928                  }
 954  929  
 955  930          } else if (pmp->pr_mflags & MA_ANON) {
 956  931                  if (!(pgc->pgc_content & CC_CONTENT_ANON))
 957  932                          goto exclude;
 958  933  
 959  934          } else if (phdr.p_flags == (PF_R | PF_X)) {
 960  935                  if (!(pgc->pgc_content & CC_CONTENT_TEXT))
 961  936                          goto exclude;
 962  937  
 963  938          } else if (phdr.p_flags == PF_R) {
 964  939                  if (!(pgc->pgc_content & CC_CONTENT_RODATA))
 965  940                          goto exclude;
 966  941  
 967  942          } else {
 968  943                  if (!(pgc->pgc_content & CC_CONTENT_DATA))
 969  944                          goto exclude;
 970  945          }
 971  946  
 972  947          n = 0;
 973  948          while (n < pmp->pr_size) {
 974  949                  size_t csz = MIN(pmp->pr_size - n, pgc->pgc_chunksz);
 975  950                  ssize_t ret;
 976  951  
 977  952                  /*
 978  953                   * If we happen to have a PROT_NONE mapping, don't try to read
 979  954                   * from the address space.
 980  955                   */
 981  956                  if ((pmp->pr_mflags & (MA_READ | MA_WRITE | MA_EXEC)) == 0) {
 982  957                          bzero(pgc->pgc_chunk, csz);
 983  958                          ret = csz;
 984  959                  } else {
 985  960                          ret = Pread(P, pgc->pgc_chunk, csz, pmp->pr_vaddr + n);
 986  961                  }
 987  962  
 988  963                  /*
 989  964                   * If we can't read out part of the victim's address
 990  965                   * space for some reason ignore that failure and try to
 991  966                   * emit a partial core file without that mapping's data.
 992  967                   * As in the kernel, we mark these failures with the
 993  968                   * PF_SUNW_FAILURE flag and store the errno where the
 994  969                   * mapping would have been.
 995  970                   */
 996  971                  if (ret != csz || gc_pwrite64(pgc->pgc_fd, pgc->pgc_chunk, csz,
 997  972                      *pgc->pgc_doff + n) != 0) {
 998  973                          int err = errno;
 999  974                          (void) gc_pwrite64(pgc->pgc_fd, &err, sizeof (err),
1000  975                              *pgc->pgc_doff);
1001  976                          *pgc->pgc_doff += roundup(sizeof (err), 8);
1002  977  
1003  978                          phdr.p_flags |= PF_SUNW_FAILURE;
1004  979                          (void) ftruncate64(pgc->pgc_fd, *pgc->pgc_doff);
1005  980                          goto exclude;
1006  981                  }
1007  982  
1008  983                  n += csz;
1009  984          }
1010  985  
1011  986          phdr.p_offset = *pgc->pgc_doff;
1012  987          phdr.p_filesz = pmp->pr_size;
1013  988          *pgc->pgc_doff += roundup(phdr.p_filesz, 8);
1014  989  
1015  990  exclude:
1016  991          if (P->status.pr_dmodel == PR_MODEL_NATIVE) {
1017  992                  if (gc_pwrite64(pgc->pgc_fd, &phdr, sizeof (phdr),
1018  993                      *pgc->pgc_poff) != 0)
1019  994                          return (1);
1020  995  
1021  996                  *pgc->pgc_poff += sizeof (phdr);
1022  997  #ifdef _LP64
1023  998          } else {
1024  999                  Elf32_Phdr phdr32;
1025 1000  
1026 1001                  bzero(&phdr32, sizeof (phdr32));
1027 1002                  phdr32.p_type = phdr.p_type;
1028 1003                  phdr32.p_vaddr = (Elf32_Addr)phdr.p_vaddr;
1029 1004                  phdr32.p_memsz = (Elf32_Word)phdr.p_memsz;
1030 1005                  phdr32.p_flags = phdr.p_flags;
1031 1006                  phdr32.p_offset = (Elf32_Off)phdr.p_offset;
1032 1007                  phdr32.p_filesz = (Elf32_Word)phdr.p_filesz;
1033 1008  
1034 1009                  if (gc_pwrite64(pgc->pgc_fd, &phdr32, sizeof (phdr32),
1035 1010                      *pgc->pgc_poff) != 0)
1036 1011                          return (1);
1037 1012  
1038 1013                  *pgc->pgc_poff += sizeof (phdr32);
1039 1014  #endif  /* _LP64 */
1040 1015          }
1041 1016  
1042 1017          return (0);
1043 1018  }
1044 1019  
1045 1020  int
1046 1021  write_shstrtab(struct ps_prochandle *P, pgcore_t *pgc)
1047 1022  {
1048 1023          off64_t off = *pgc->pgc_doff;
1049 1024          size_t size = 0;
1050 1025          shstrtab_t *s = &pgc->pgc_shstrtab;
1051 1026  
1052 1027          if (shstrtab_size(s) == 1)
1053 1028                  return (0);
1054 1029  
1055 1030          /*
1056 1031           * Preemptively stick the name of the shstrtab in the string table.
1057 1032           */
1058 1033          if (!shstrtab_ndx(&pgc->pgc_shstrtab,
1059 1034              shstrtab_data[STR_SHSTRTAB], NULL)) {
1060 1035                  return (1);
1061 1036          }
1062 1037          size = shstrtab_size(s);
1063 1038  
1064 1039          /*
1065 1040           * Dump all the strings that we used being sure we include the
1066 1041           * terminating null character.
1067 1042           */
1068 1043          for (shstrtab_ent_t *ent = list_head(&s->sst_names); ent != NULL;
1069 1044              ent = list_next(&s->sst_names, ent)) {
1070 1045                  if (gc_pwrite64(pgc->pgc_fd, ent->sste_name, ent->sste_len,
1071 1046                      off + ent->sste_offset) != 0) {
1072 1047                          return (1);
1073 1048                  }
1074 1049          }
1075 1050  
1076 1051          if (P->status.pr_dmodel == PR_MODEL_ILP32) {
1077 1052                  Elf32_Shdr shdr;
1078 1053  
1079 1054                  bzero(&shdr, sizeof (shdr));
1080 1055                  if (!shstrtab_ndx(&pgc->pgc_shstrtab,
1081 1056                      shstrtab_data[STR_SHSTRTAB], &shdr.sh_name)) {
1082 1057                          return (1);
1083 1058                  }
1084 1059                  shdr.sh_size = size;
1085 1060                  shdr.sh_offset = *pgc->pgc_doff;
1086 1061                  shdr.sh_addralign = 1;
1087 1062                  shdr.sh_flags = SHF_STRINGS;
1088 1063                  shdr.sh_type = SHT_STRTAB;
1089 1064  
1090 1065                  if (gc_pwrite64(pgc->pgc_fd, &shdr, sizeof (shdr),
1091 1066                      *pgc->pgc_soff) != 0)
1092 1067                          return (1);
1093 1068  
1094 1069                  *pgc->pgc_soff += sizeof (shdr);
1095 1070  #ifdef _LP64
1096 1071          } else {
1097 1072                  Elf64_Shdr shdr;
1098 1073  
1099 1074                  bzero(&shdr, sizeof (shdr));
1100 1075                  if (!shstrtab_ndx(&pgc->pgc_shstrtab,
1101 1076                      shstrtab_data[STR_SHSTRTAB], &shdr.sh_name)) {
1102 1077                          return (1);
1103 1078                  }
1104 1079                  shdr.sh_size = size;
1105 1080                  shdr.sh_offset = *pgc->pgc_doff;
1106 1081                  shdr.sh_addralign = 1;
1107 1082                  shdr.sh_flags = SHF_STRINGS;
1108 1083                  shdr.sh_type = SHT_STRTAB;
1109 1084  
1110 1085                  if (gc_pwrite64(pgc->pgc_fd, &shdr, sizeof (shdr),
1111 1086                      *pgc->pgc_soff) != 0)
1112 1087                          return (1);
1113 1088  
1114 1089                  *pgc->pgc_soff += sizeof (shdr);
1115 1090  #endif  /* _LP64 */
1116 1091          }
1117 1092  
1118 1093          *pgc->pgc_doff += roundup(size, 8);
1119 1094  
1120 1095          return (0);
1121 1096  }
1122 1097  
1123 1098  /*
1124 1099   * Don't explicity stop the process; that's up to the consumer.
1125 1100   */
1126 1101  int
1127 1102  Pfgcore(struct ps_prochandle *P, int fd, core_content_t content)
1128 1103  {
1129 1104          char plat[SYS_NMLN];
1130 1105          char zonename[ZONENAME_MAX];
1131 1106          int platlen = -1;
1132 1107          pgcore_t pgc;
1133 1108          off64_t poff, soff, doff, boff;
1134 1109          struct utsname uts;
1135 1110          uint_t nphdrs, nshdrs;
1136 1111  
1137 1112          if (ftruncate64(fd, 0) != 0)
1138 1113                  return (-1);
1139 1114  
1140 1115          if (content == CC_CONTENT_INVALID) {
1141 1116                  errno = EINVAL;
1142 1117                  return (-1);
1143 1118          }
1144 1119  
1145 1120          /*
1146 1121           * Cache the mappings and other useful data.
1147 1122           */
1148 1123          (void) Prd_agent(P);
1149 1124          (void) Ppsinfo(P);
1150 1125  
1151 1126          (void) memset(&pgc, 0, sizeof (pgc));
1152 1127          pgc.P = P;
1153 1128          pgc.pgc_fd = fd;
1154 1129          pgc.pgc_poff = &poff;
1155 1130          pgc.pgc_soff = &soff;
1156 1131          pgc.pgc_doff = &doff;
1157 1132          pgc.pgc_content = content;
1158 1133          pgc.pgc_chunksz = PAGESIZE;
1159 1134          if ((pgc.pgc_chunk = malloc(pgc.pgc_chunksz)) == NULL)
1160 1135                  return (-1);
1161 1136  
1162 1137          if (!shstrtab_init(&pgc.pgc_shstrtab)) {
1163 1138                  goto err;
1164 1139          }
1165 1140  
1166 1141          /*
1167 1142           * There are two PT_NOTE program headers for ancillary data, and
1168 1143           * one for each mapping.
1169 1144           */
1170 1145          nphdrs = 2 + P->map_count;
1171 1146          nshdrs = count_sections(&pgc);
1172 1147  
1173 1148          (void) Pplatform(P, plat, sizeof (plat));
1174 1149          platlen = strlen(plat) + 1;
1175 1150          Preadauxvec(P);
1176 1151          (void) Puname(P, &uts);
1177 1152          if (Pzonename(P, zonename, sizeof (zonename)) == NULL)
1178 1153                  zonename[0] = '\0';
1179 1154  
1180 1155          /*
1181 1156           * The core file contents may required zero section headers, but if we
1182 1157           * overflow the 16 bits allotted to the program header count in the ELF
1183 1158           * header, we'll need that program header at index zero.
1184 1159           */
1185 1160          if (nshdrs == 0 && nphdrs >= PN_XNUM)
1186 1161                  nshdrs = 1;
1187 1162  
1188 1163          /*
1189 1164           * Set up the ELF header.
1190 1165           */
1191 1166          if (P->status.pr_dmodel == PR_MODEL_ILP32) {
1192 1167                  Elf32_Ehdr ehdr;
1193 1168  
1194 1169                  bzero(&ehdr, sizeof (ehdr));
1195 1170                  ehdr.e_ident[EI_MAG0] = ELFMAG0;
1196 1171                  ehdr.e_ident[EI_MAG1] = ELFMAG1;
1197 1172                  ehdr.e_ident[EI_MAG2] = ELFMAG2;
1198 1173                  ehdr.e_ident[EI_MAG3] = ELFMAG3;
1199 1174                  ehdr.e_type = ET_CORE;
1200 1175  
1201 1176                  ehdr.e_ident[EI_CLASS] = ELFCLASS32;
1202 1177  #if defined(__sparc)
1203 1178                  ehdr.e_machine = EM_SPARC;
1204 1179                  ehdr.e_ident[EI_DATA] = ELFDATA2MSB;
1205 1180  #elif defined(__i386) || defined(__amd64)
1206 1181                  ehdr.e_machine = EM_386;
1207 1182                  ehdr.e_ident[EI_DATA] = ELFDATA2LSB;
1208 1183  #else
1209 1184  #error "unknown machine type"
1210 1185  #endif
1211 1186                  ehdr.e_ident[EI_VERSION] = EV_CURRENT;
1212 1187  
1213 1188                  ehdr.e_version = EV_CURRENT;
1214 1189                  ehdr.e_ehsize = sizeof (ehdr);
1215 1190  
1216 1191                  if (nphdrs >= PN_XNUM)
1217 1192                          ehdr.e_phnum = PN_XNUM;
1218 1193                  else
1219 1194                          ehdr.e_phnum = (unsigned short)nphdrs;
1220 1195  
1221 1196                  ehdr.e_phentsize = sizeof (Elf32_Phdr);
1222 1197                  ehdr.e_phoff = ehdr.e_ehsize;
1223 1198  
1224 1199                  if (nshdrs > 0) {
1225 1200                          if (nshdrs >= SHN_LORESERVE)
1226 1201                                  ehdr.e_shnum = 0;
1227 1202                          else
1228 1203                                  ehdr.e_shnum = (unsigned short)nshdrs;
1229 1204  
1230 1205                          if (nshdrs - 1 >= SHN_LORESERVE)
1231 1206                                  ehdr.e_shstrndx = SHN_XINDEX;
1232 1207                          else
1233 1208                                  ehdr.e_shstrndx = (unsigned short)(nshdrs - 1);
1234 1209  
1235 1210                          ehdr.e_shentsize = sizeof (Elf32_Shdr);
1236 1211                          ehdr.e_shoff = ehdr.e_phoff + ehdr.e_phentsize * nphdrs;
1237 1212                  }
1238 1213  
1239 1214                  if (gc_pwrite64(fd, &ehdr, sizeof (ehdr), 0) != 0)
1240 1215                          goto err;
1241 1216  
1242 1217                  poff = ehdr.e_phoff;
1243 1218                  soff = ehdr.e_shoff;
1244 1219                  doff = boff = ehdr.e_ehsize +
1245 1220                      ehdr.e_phentsize * nphdrs +
1246 1221                      ehdr.e_shentsize * nshdrs;
1247 1222  
1248 1223  #ifdef _LP64
1249 1224          } else {
1250 1225                  Elf64_Ehdr ehdr;
1251 1226  
1252 1227                  bzero(&ehdr, sizeof (ehdr));
1253 1228                  ehdr.e_ident[EI_MAG0] = ELFMAG0;
1254 1229                  ehdr.e_ident[EI_MAG1] = ELFMAG1;
1255 1230                  ehdr.e_ident[EI_MAG2] = ELFMAG2;
1256 1231                  ehdr.e_ident[EI_MAG3] = ELFMAG3;
1257 1232                  ehdr.e_type = ET_CORE;
1258 1233  
1259 1234                  ehdr.e_ident[EI_CLASS] = ELFCLASS64;
1260 1235  #if defined(__sparc)
1261 1236                  ehdr.e_machine = EM_SPARCV9;
1262 1237                  ehdr.e_ident[EI_DATA] = ELFDATA2MSB;
1263 1238  #elif defined(__i386) || defined(__amd64)
1264 1239                  ehdr.e_machine = EM_AMD64;
1265 1240                  ehdr.e_ident[EI_DATA] = ELFDATA2LSB;
1266 1241  #else
1267 1242  #error "unknown machine type"
1268 1243  #endif
1269 1244                  ehdr.e_ident[EI_VERSION] = EV_CURRENT;
1270 1245  
1271 1246                  ehdr.e_version = EV_CURRENT;
1272 1247                  ehdr.e_ehsize = sizeof (ehdr);
1273 1248  
1274 1249                  if (nphdrs >= PN_XNUM)
1275 1250                          ehdr.e_phnum = PN_XNUM;
1276 1251                  else
1277 1252                          ehdr.e_phnum = (unsigned short)nphdrs;
1278 1253  
1279 1254                  ehdr.e_phentsize = sizeof (Elf64_Phdr);
1280 1255                  ehdr.e_phoff = ehdr.e_ehsize;
1281 1256  
1282 1257                  if (nshdrs > 0) {
1283 1258                          if (nshdrs >= SHN_LORESERVE)
1284 1259                                  ehdr.e_shnum = 0;
1285 1260                          else
1286 1261                                  ehdr.e_shnum = (unsigned short)nshdrs;
1287 1262  
1288 1263                          if (nshdrs - 1 >= SHN_LORESERVE)
1289 1264                                  ehdr.e_shstrndx = SHN_XINDEX;
1290 1265                          else
1291 1266                                  ehdr.e_shstrndx = (unsigned short)(nshdrs - 1);
1292 1267  
1293 1268                          ehdr.e_shentsize = sizeof (Elf64_Shdr);
1294 1269                          ehdr.e_shoff = ehdr.e_phoff + ehdr.e_phentsize * nphdrs;
1295 1270                  }
1296 1271  
1297 1272                  if (gc_pwrite64(fd, &ehdr, sizeof (ehdr), 0) != 0)
1298 1273                          goto err;
1299 1274  
1300 1275                  poff = ehdr.e_phoff;
1301 1276                  soff = ehdr.e_shoff;
1302 1277                  doff = boff = ehdr.e_ehsize +
1303 1278                      ehdr.e_phentsize * nphdrs +
1304 1279                      ehdr.e_shentsize * nshdrs;
1305 1280  
1306 1281  #endif  /* _LP64 */
1307 1282          }
1308 1283  
1309 1284          /*
1310 1285           * Write the zero indexed section if it exists.
1311 1286           */
1312 1287          if (nshdrs > 0 && write_shdr(&pgc, shstrtab_data[STR_NONE], 0, 0, 0, 0,
1313 1288              nshdrs >= SHN_LORESERVE ? nshdrs : 0,
1314 1289              nshdrs - 1 >= SHN_LORESERVE ? nshdrs - 1 : 0,
1315 1290              nphdrs >= PN_XNUM ? nphdrs : 0, 0, 0) != 0)
1316 1291                  goto err;
1317 1292  
1318 1293          /*
1319 1294           * Construct the old-style note header and section.
1320 1295           */
1321 1296  
1322 1297          if (P->status.pr_dmodel == PR_MODEL_NATIVE) {
1323 1298                  prpsinfo_t prpsinfo;
1324 1299  
1325 1300                  mkprpsinfo(P, &prpsinfo);
1326 1301                  if (write_note(fd, NT_PRPSINFO, &prpsinfo, sizeof (prpsinfo_t),
1327 1302                      &doff) != 0) {
1328 1303                          goto err;
1329 1304                  }
1330 1305                  if (write_note(fd, NT_AUXV, P->auxv,
1331 1306                      P->nauxv * sizeof (P->auxv[0]), &doff) != 0) {
1332 1307                          goto err;
1333 1308                  }
1334 1309  #ifdef _LP64
1335 1310          } else {
1336 1311                  prpsinfo32_t pi32;
1337 1312                  auxv32_t *av32;
1338 1313                  size_t size = sizeof (auxv32_t) * P->nauxv;
1339 1314                  int i;
1340 1315  
1341 1316                  mkprpsinfo32(P, &pi32);
1342 1317                  if (write_note(fd, NT_PRPSINFO, &pi32, sizeof (prpsinfo32_t),
1343 1318                      &doff) != 0) {
1344 1319                          goto err;
1345 1320                  }
1346 1321  
1347 1322                  if ((av32 = malloc(size)) == NULL)
1348 1323                          goto err;
1349 1324  
1350 1325                  for (i = 0; i < P->nauxv; i++) {
1351 1326                          auxv_n_to_32(&P->auxv[i], &av32[i]);
1352 1327                  }
1353 1328  
1354 1329                  if (write_note(fd, NT_AUXV, av32, size, &doff) != 0) {
1355 1330                          free(av32);
1356 1331                          goto err;
1357 1332                  }
1358 1333  
1359 1334                  free(av32);
1360 1335  #endif  /* _LP64 */
1361 1336          }
1362 1337  
1363 1338          if (write_note(fd, NT_PLATFORM, plat, platlen, &doff) != 0)
1364 1339                  goto err;
1365 1340  
1366 1341          if (Plwp_iter_all(P, old_per_lwp, &pgc) != 0)
1367 1342                  goto err;
1368 1343  
1369 1344          if (P->status.pr_dmodel == PR_MODEL_ILP32) {
1370 1345                  Elf32_Phdr phdr;
1371 1346  
1372 1347                  bzero(&phdr, sizeof (phdr));
1373 1348                  phdr.p_type = PT_NOTE;
1374 1349                  phdr.p_flags = PF_R;
1375 1350                  phdr.p_offset = (Elf32_Off)boff;
1376 1351                  phdr.p_filesz = doff - boff;
1377 1352                  boff = doff;
1378 1353  
1379 1354                  if (gc_pwrite64(fd, &phdr, sizeof (phdr), poff) != 0)
1380 1355                          goto err;
1381 1356                  poff += sizeof (phdr);
1382 1357  #ifdef _LP64
1383 1358          } else {
1384 1359                  Elf64_Phdr phdr;
1385 1360  
1386 1361                  bzero(&phdr, sizeof (phdr));
1387 1362                  phdr.p_type = PT_NOTE;
1388 1363                  phdr.p_flags = PF_R;
1389 1364                  phdr.p_offset = boff;
1390 1365                  phdr.p_filesz = doff - boff;
1391 1366                  boff = doff;
1392 1367  
1393 1368                  if (gc_pwrite64(fd, &phdr, sizeof (phdr), poff) != 0)
1394 1369                          goto err;
1395 1370                  poff += sizeof (phdr);
1396 1371  #endif  /* _LP64 */
1397 1372          }
1398 1373  
1399 1374          /*
1400 1375           * Construct the new-style note header and section.
1401 1376           */
1402 1377  
1403 1378          if (P->status.pr_dmodel == PR_MODEL_NATIVE) {
1404 1379                  if (write_note(fd, NT_PSINFO, &P->psinfo, sizeof (psinfo_t),
1405 1380                      &doff) != 0) {
1406 1381                          goto err;
1407 1382                  }
1408 1383                  if (write_note(fd, NT_PSTATUS, &P->status, sizeof (pstatus_t),
1409 1384                      &doff) != 0) {
1410 1385                          goto err;
1411 1386                  }
1412 1387                  if (write_note(fd, NT_AUXV, P->auxv,
1413 1388                      P->nauxv * sizeof (P->auxv[0]), &doff) != 0) {
1414 1389                          goto err;
1415 1390                  }
1416 1391  #ifdef _LP64
1417 1392          } else {
1418 1393                  psinfo32_t pi32;
1419 1394                  pstatus32_t ps32;
1420 1395                  auxv32_t *av32;
1421 1396                  size_t size = sizeof (auxv32_t) * P->nauxv;
1422 1397                  int i;
1423 1398  
1424 1399                  psinfo_n_to_32(&P->psinfo, &pi32);
1425 1400                  if (write_note(fd, NT_PSINFO, &pi32, sizeof (psinfo32_t),
1426 1401                      &doff) != 0) {
1427 1402                          goto err;
1428 1403                  }
1429 1404                  pstatus_n_to_32(&P->status, &ps32);
1430 1405                  if (write_note(fd, NT_PSTATUS, &ps32, sizeof (pstatus32_t),
1431 1406                      &doff) != 0) {
1432 1407                          goto err;
1433 1408                  }
1434 1409                  if ((av32 = malloc(size)) == NULL)
1435 1410                          goto err;
1436 1411  
1437 1412                  for (i = 0; i < P->nauxv; i++) {
1438 1413                          auxv_n_to_32(&P->auxv[i], &av32[i]);
1439 1414                  }
1440 1415  
1441 1416                  if (write_note(fd, NT_AUXV, av32, size, &doff) != 0) {
1442 1417                          free(av32);
1443 1418                          goto err;
1444 1419                  }
1445 1420  
1446 1421                  free(av32);
1447 1422  #endif  /* _LP64 */
1448 1423          }
1449 1424  
1450 1425          if (write_note(fd, NT_PLATFORM, plat, platlen, &doff) != 0 ||
1451 1426              write_note(fd, NT_UTSNAME, &uts, sizeof (uts), &doff) != 0 ||
1452 1427              write_note(fd, NT_CONTENT, &content, sizeof (content), &doff) != 0)
1453 1428                  goto err;
1454 1429  
1455 1430          {
1456 1431                  prcred_t cred, *cp;
1457 1432                  size_t size = sizeof (prcred_t);
1458 1433  
1459 1434                  if (Pcred(P, &cred, 0) != 0)
1460 1435                          goto err;
1461 1436  
1462 1437                  if (cred.pr_ngroups > 0)
1463 1438                          size += sizeof (gid_t) * (cred.pr_ngroups - 1);
1464 1439                  if ((cp = malloc(size)) == NULL)
1465 1440                          goto err;
1466 1441  
1467 1442                  if (Pcred(P, cp, cred.pr_ngroups) != 0 ||
1468 1443                      write_note(fd, NT_PRCRED, cp, size, &doff) != 0) {
1469 1444                          free(cp);
1470 1445                          goto err;
1471 1446                  }
1472 1447  
1473 1448                  free(cp);
1474 1449          }
1475 1450  
1476 1451          {
1477 1452                  prpriv_t *ppriv = NULL;
1478 1453                  const priv_impl_info_t *pinfo;
1479 1454                  size_t pprivsz, pinfosz;
1480 1455  
1481 1456                  if (Ppriv(P, &ppriv) == -1)
1482 1457                          goto err;
1483 1458                  pprivsz = PRIV_PRPRIV_SIZE(ppriv);
1484 1459  
1485 1460                  if (write_note(fd, NT_PRPRIV, ppriv, pprivsz, &doff) != 0) {
1486 1461                          Ppriv_free(P, ppriv);
1487 1462                          goto err;
1488 1463                  }
1489 1464                  Ppriv_free(P, ppriv);
1490 1465  
1491 1466                  if ((pinfo = getprivimplinfo()) == NULL)
1492 1467                          goto err;
1493 1468                  pinfosz = PRIV_IMPL_INFO_SIZE(pinfo);
1494 1469  
1495 1470                  if (write_note(fd, NT_PRPRIVINFO, pinfo, pinfosz, &doff) != 0)
1496 1471                          goto err;
1497 1472          }
1498 1473  
1499 1474          if (write_note(fd, NT_ZONENAME, zonename, strlen(zonename) + 1,
1500 1475              &doff) != 0)
1501 1476                  goto err;
1502 1477  
1503 1478          {
1504 1479                  fditer_t iter;
1505 1480                  iter.fd_fd = fd;
1506 1481                  iter.fd_doff = &doff;
1507 1482  
1508 1483                  if (Pfdinfo_iter(P, iter_fd, &iter) != 0)
1509 1484                          goto err;
1510 1485          }
1511 1486  
1512 1487  
1513 1488          {
1514 1489                  prsecflags_t *psf = NULL;
1515 1490  
1516 1491                  if (Psecflags(P, &psf) != 0)
1517 1492                          goto err;
1518 1493  
1519 1494                  if (write_note(fd, NT_SECFLAGS, psf,
1520 1495                      sizeof (prsecflags_t), &doff) != 0) {
1521 1496                          Psecflags_free(psf);
1522 1497                          goto err;
1523 1498                  }
1524 1499  
1525 1500                  Psecflags_free(psf);
1526 1501          }
1527 1502  
1528 1503  #if defined(__i386) || defined(__amd64)
1529 1504          /* CSTYLED */
1530 1505          {
1531 1506                  struct ssd *ldtp;
1532 1507                  size_t size;
1533 1508                  int nldt;
1534 1509  
1535 1510                  /*
1536 1511                   * Only dump out non-zero sized LDT notes.
1537 1512                   */
1538 1513                  if ((nldt = Pldt(P, NULL, 0)) != 0) {
1539 1514                          size = sizeof (struct ssd) * nldt;
1540 1515                          if ((ldtp = malloc(size)) == NULL)
1541 1516                                  goto err;
1542 1517  
1543 1518                          if (Pldt(P, ldtp, nldt) == -1 ||
1544 1519                              write_note(fd, NT_LDT, ldtp, size, &doff) != 0) {
1545 1520                                  free(ldtp);
1546 1521                                  goto err;
1547 1522                          }
1548 1523  
1549 1524                          free(ldtp);
1550 1525                  }
1551 1526          }
1552 1527  #endif  /* __i386 || __amd64 */
1553 1528  
1554 1529          if (Plwp_iter_all(P, new_per_lwp, &pgc) != 0)
1555 1530                  goto err;
1556 1531  
1557 1532          if (P->status.pr_dmodel == PR_MODEL_ILP32) {
1558 1533                  Elf32_Phdr phdr;
1559 1534  
1560 1535                  bzero(&phdr, sizeof (phdr));
1561 1536                  phdr.p_type = PT_NOTE;
1562 1537                  phdr.p_flags = PF_R;
1563 1538                  phdr.p_offset = (Elf32_Off)boff;
1564 1539                  phdr.p_filesz = doff - boff;
1565 1540                  boff = doff;
1566 1541  
1567 1542                  if (gc_pwrite64(fd, &phdr, sizeof (phdr), poff) != 0)
1568 1543                          goto err;
1569 1544                  poff += sizeof (phdr);
1570 1545  #ifdef _LP64
1571 1546          } else {
1572 1547                  Elf64_Phdr phdr;
1573 1548  
1574 1549                  bzero(&phdr, sizeof (phdr));
1575 1550                  phdr.p_type = PT_NOTE;
1576 1551                  phdr.p_flags = PF_R;
1577 1552                  phdr.p_offset = boff;
1578 1553                  phdr.p_filesz = doff - boff;
1579 1554                  boff = doff;
1580 1555  
1581 1556                  if (gc_pwrite64(fd, &phdr, sizeof (phdr), poff) != 0)
1582 1557                          goto err;
1583 1558                  poff += sizeof (phdr);
1584 1559  #endif  /* _LP64 */
1585 1560          }
1586 1561  
1587 1562          /*
1588 1563           * Construct the headers for each mapping and write out its data
1589 1564           * if the content parameter indicates that it should be present
1590 1565           * in the core file.
1591 1566           */
1592 1567          if (Pmapping_iter(P, dump_map, &pgc) != 0)
1593 1568                  goto err;
1594 1569  
1595 1570          if (dump_sections(&pgc) != 0)
1596 1571                  goto err;
1597 1572  
1598 1573          if (write_shstrtab(P, &pgc) != 0)
1599 1574                  goto err;
1600 1575  
1601 1576          free(pgc.pgc_chunk);
1602 1577          shstrtab_fini(&pgc.pgc_shstrtab);
1603 1578  
1604 1579          return (0);
1605 1580  
1606 1581  err:
1607 1582          /*
1608 1583           * Wipe out anything we may have written if there was an error.
1609 1584           */
1610 1585          (void) ftruncate64(fd, 0);
1611 1586          free(pgc.pgc_chunk);
1612 1587          shstrtab_fini(&pgc.pgc_shstrtab);
1613 1588  
1614 1589          return (-1);
1615 1590  }
1616 1591  
1617 1592  static const char *content_str[] = {
1618 1593          "stack",        /* CC_CONTENT_STACK */
1619 1594          "heap",         /* CC_CONTENT_HEAP */
1620 1595          "shfile",       /* CC_CONTENT_SHFILE */
1621 1596          "shanon",       /* CC_CONTENT_SHANON */
1622 1597          "text",         /* CC_CONTENT_TEXT */
1623 1598          "data",         /* CC_CONTENT_DATA */
1624 1599          "rodata",       /* CC_CONTENT_RODATA */
1625 1600          "anon",         /* CC_CONTENT_ANON */
1626 1601          "shm",          /* CC_CONTENT_SHM */
1627 1602          "ism",          /* CC_CONTENT_ISM */
1628 1603          "dism",         /* CC_CONTENT_DISM */
1629 1604          "ctf",          /* CC_CONTENT_CTF */
1630 1605          "symtab",       /* CC_CONTENT_SYMTAB */
1631 1606          "debug"         /* CC_CONTENT_DEBUG */
1632 1607  };
1633 1608  
1634 1609  static uint_t ncontent_str = sizeof (content_str) / sizeof (content_str[0]);
1635 1610  
1636 1611  #define STREQ(a, b, n)  (strlen(b) == (n) && strncmp(a, b, n) == 0)
1637 1612  
1638 1613  int
1639 1614  proc_str2content(const char *str, core_content_t *cp)
1640 1615  {
1641 1616          const char *cur = str;
1642 1617          int add = 1;
1643 1618          core_content_t mask, content = 0;
1644 1619  
1645 1620          for (;;) {
1646 1621                  for (cur = str; isalpha(*cur); cur++)
1647 1622                          continue;
1648 1623  
1649 1624                  if (STREQ(str, "default", cur - str)) {
1650 1625                          mask = CC_CONTENT_DEFAULT;
1651 1626                  } else if (STREQ(str, "all", cur - str)) {
1652 1627                          mask = CC_CONTENT_ALL;
1653 1628                  } else if (STREQ(str, "none", cur - str)) {
1654 1629                          mask = 0;
1655 1630                  } else {
1656 1631                          int i = 0;
1657 1632  
1658 1633                          while (!STREQ(str, content_str[i], cur - str)) {
1659 1634                                  i++;
1660 1635  
1661 1636                                  if (i >= ncontent_str)
1662 1637                                          return (-1);
1663 1638                          }
1664 1639  
1665 1640                          mask = (core_content_t)1 << i;
1666 1641                  }
1667 1642  
1668 1643                  if (add)
1669 1644                          content |= mask;
1670 1645                  else
1671 1646                          content &= ~mask;
1672 1647  
1673 1648                  switch (*cur) {
1674 1649                  case '\0':
1675 1650                          *cp = content;
1676 1651                          return (0);
1677 1652                  case '+':
1678 1653                          add = 1;
1679 1654                          break;
1680 1655                  case '-':
1681 1656                          add = 0;
1682 1657                          break;
1683 1658                  default:
1684 1659                          return (-1);
1685 1660                  }
1686 1661  
1687 1662                  str = cur + 1;
1688 1663          }
1689 1664  }
1690 1665  
1691 1666  static int
1692 1667  popc(core_content_t x)
1693 1668  {
1694 1669          int i;
1695 1670  
1696 1671          for (i = 0; x != 0; i++)
1697 1672                  x &= x - 1;
1698 1673  
1699 1674          return (i);
1700 1675  }
1701 1676  
1702 1677  int
1703 1678  proc_content2str(core_content_t content, char *buf, size_t size)
1704 1679  {
1705 1680          int nonecnt, defcnt, allcnt;
1706 1681          core_content_t mask, bit;
1707 1682          int first;
1708 1683          uint_t index;
1709 1684          size_t n, tot = 0;
1710 1685  
1711 1686          if (content == 0)
1712 1687                  return ((int)strlcpy(buf, "none", size));
1713 1688  
1714 1689          if (content & ~CC_CONTENT_ALL)
1715 1690                  return ((int)strlcpy(buf, "<invalid>", size));
1716 1691  
1717 1692          nonecnt = popc(content);
1718 1693          defcnt = 1 + popc(content ^ CC_CONTENT_DEFAULT);
1719 1694          allcnt = 1 + popc(content ^ CC_CONTENT_ALL);
1720 1695  
1721 1696          if (defcnt <= nonecnt && defcnt <= allcnt) {
1722 1697                  mask = content ^ CC_CONTENT_DEFAULT;
1723 1698                  first = 0;
1724 1699                  tot += (n = strlcpy(buf, "default", size));
1725 1700                  if (n > size)
1726 1701                          n = size;
1727 1702                  buf += n;
1728 1703                  size -= n;
1729 1704          } else if (allcnt < nonecnt) {
1730 1705                  mask = content ^ CC_CONTENT_ALL;
1731 1706                  first = 0;
1732 1707                  tot += (n = strlcpy(buf, "all", size));
1733 1708                  if (n > size)
1734 1709                          n = size;
1735 1710                  buf += n;
1736 1711                  size -= n;
1737 1712          } else {
1738 1713                  mask = content;
1739 1714                  first = 1;
1740 1715          }
1741 1716  
1742 1717          while (mask != 0) {
1743 1718                  bit = mask ^ (mask & (mask - 1));
1744 1719  
1745 1720                  if (!first) {
1746 1721                          if (size > 1) {
1747 1722                                  *buf = (bit & content) ? '+' : '-';
1748 1723                                  buf++;
1749 1724                                  size--;
1750 1725                          }
1751 1726  
1752 1727                          tot++;
1753 1728                  }
1754 1729                  index = popc(bit - 1);
1755 1730                  tot += (n = strlcpy(buf, content_str[index], size));
1756 1731                  if (n > size)
1757 1732                          n = size;
1758 1733                  buf += n;
1759 1734                  size -= n;
1760 1735  
1761 1736                  mask ^= bit;
1762 1737                  first = 0;
1763 1738          }
1764 1739  
1765 1740          return ((int)tot);
1766 1741  }
  
    | 
      ↓ open down ↓ | 
    1225 lines elided | 
    
      ↑ open up ↑ | 
  
XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX