1 /*
   2  * CDDL HEADER START
   3  *
   4  * The contents of this file are subject to the terms of the
   5  * Common Development and Distribution License (the "License").
   6  * You may not use this file except in compliance with the License.
   7  *
   8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
   9  * or http://www.opensolaris.org/os/licensing.
  10  * See the License for the specific language governing permissions
  11  * and limitations under the License.
  12  *
  13  * When distributing Covered Code, include this CDDL HEADER in each
  14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
  15  * If applicable, add the following below this CDDL HEADER, with the
  16  * fields enclosed by brackets "[]" replaced with your own identifying
  17  * information: Portions Copyright [yyyy] [name of copyright owner]
  18  *
  19  * CDDL HEADER END
  20  */
  21 /*
  22  * Copyright 2014 Garrett D'Amore <garrett@damore.org>
  23  *
  24  * Copyright 2008 Sun Microsystems, Inc.  All rights reserved.
  25  * Use is subject to license terms.
  26  */
  27 
  28 #ifndef _RTLD_DB_H
  29 #define _RTLD_DB_H
  30 
  31 #ifdef  __cplusplus
  32 extern "C" {
  33 #endif
  34 
  35 #include <sys/types.h>
  36 #include <sys/lwp.h>
  37 #include <sys/elf.h>
  38 #include <link.h>
  39 #include <proc_service.h>
  40 
  41 
  42 /*
  43  * librtld_db interface versions
  44  */
  45 #define RD_VERSION1     1
  46 #define RD_VERSION2     2
  47 #define RD_VERSION3     3
  48 #define RD_VERSION4     4
  49 #define RD_VERSION      RD_VERSION4
  50 
  51 typedef enum {
  52         RD_ERR,         /* generic */
  53         RD_OK,          /* generic "call" succeeded */
  54         RD_NOCAPAB,     /* capability not available */
  55         RD_DBERR,       /* import service failed */
  56         RD_NOBASE,      /* 5.x: aux tag AT_BASE not found */
  57         RD_NODYNAM,     /* symbol 'DYNAMIC' not found */
  58         RD_NOMAPS       /* link-maps are not yet available */
  59 } rd_err_e;
  60 
  61 
  62 /*
  63  * ways that the event notification can take place:
  64  */
  65 typedef enum {
  66         RD_NOTIFY_BPT,          /* set break-point at address */
  67         RD_NOTIFY_AUTOBPT,      /* 4.x compat. not used in 5.x */
  68         RD_NOTIFY_SYSCALL       /* watch for syscall */
  69 } rd_notify_e;
  70 
  71 /*
  72  * information on ways that the event notification can take place:
  73  */
  74 typedef struct rd_notify {
  75         rd_notify_e     type;
  76         union {
  77                 psaddr_t        bptaddr;        /* break point address */
  78                 long            syscallno;      /* system call id */
  79         } u;
  80 } rd_notify_t;
  81 
  82 /*
  83  * information about event instance:
  84  */
  85 typedef enum {
  86         RD_NOSTATE = 0,         /* no state information */
  87         RD_CONSISTENT,          /* link-maps are stable */
  88         RD_ADD,                 /* currently adding object to link-maps */
  89         RD_DELETE               /* currently deleteing object from link-maps */
  90 } rd_state_e;
  91 
  92 typedef struct rd_event_msg {
  93         rd_event_e      type;
  94         union {
  95                 rd_state_e      state;  /* for DLACTIVITY */
  96         } u;
  97 } rd_event_msg_t;
  98 
  99 
 100 /*
 101  * iteration over load objects
 102  */
 103 typedef struct rd_loadobj {
 104         psaddr_t        rl_nameaddr;    /* address of the name in user space */
 105         unsigned        rl_flags;
 106         psaddr_t        rl_base;        /* base of address of code */
 107         psaddr_t        rl_data_base;   /* base of address of data */
 108         Lmid_t          rl_lmident;     /* ident of link map */
 109         psaddr_t        rl_refnameaddr; /* reference name of filter in user */
 110                                         /* space.  If non null object is a */
 111                                         /* filter. */
 112         psaddr_t        rl_plt_base;    /* These fields are present for 4.x */
 113         unsigned        rl_plt_size;    /* compatibility and are not */
 114                                         /* currently used  in SunOS5.x */
 115         psaddr_t        rl_bend;        /* end of image (text+data+bss) */
 116         psaddr_t        rl_padstart;    /* start of padding */
 117         psaddr_t        rl_padend;      /* end of image after padding */
 118         psaddr_t        rl_dynamic;     /* points to the DYNAMIC section */
 119                                         /* in the target process */
 120         unsigned long   rl_tlsmodid;    /* module ID for TLS references */
 121 } rd_loadobj_t;
 122 
 123 /*
 124  * Values for rl_flags
 125  */
 126 #define RD_FLG_MEM_OBJECT       0x0001  /* Identifies this object as */
 127                                         /* originating from a relocatable */
 128                                         /* module which was dynamically */
 129                                         /* loaded */
 130 
 131 /*
 132  * Commands for rd_ctl()
 133  */
 134 #define RD_CTL_SET_HELPPATH     0x01    /* Set the path used to find helpers */
 135 
 136 typedef struct rd_agent rd_agent_t;
 137 typedef int rl_iter_f(const rd_loadobj_t *, void *);
 138 
 139 
 140 /*
 141  * PLT skipping
 142  */
 143 typedef enum {
 144     RD_RESOLVE_NONE,            /* don't do anything special */
 145     RD_RESOLVE_STEP,            /* step 'pi_nstep' instructions */
 146     RD_RESOLVE_TARGET,          /* resolved target is in 'pi_target' */
 147     RD_RESOLVE_TARGET_STEP      /* put a bpt on target, then step nstep times */
 148 } rd_skip_e;
 149 
 150 
 151 typedef struct rd_plt_info {
 152         rd_skip_e       pi_skip_method;
 153         long            pi_nstep;
 154         psaddr_t        pi_target;
 155         psaddr_t        pi_baddr;
 156         unsigned int    pi_flags;
 157 } rd_plt_info_t;
 158 
 159 
 160 /*
 161  * Values for pi_flags
 162  */
 163 #define RD_FLG_PI_PLTBOUND      0x0001  /* Indicates that the PLT */
 164                                         /* has been bound - and that */
 165                                         /* pi_baddr will contain its */
 166                                         /* destination address */
 167 
 168 struct  ps_prochandle;
 169 
 170 /*
 171  * librtld_db.so entry points
 172  */
 173 extern void             rd_delete(rd_agent_t *);
 174 extern char             *rd_errstr(rd_err_e rderr);
 175 extern rd_err_e         rd_event_addr(rd_agent_t *, rd_event_e, rd_notify_t *);
 176 extern rd_err_e         rd_event_enable(rd_agent_t *, int);
 177 extern rd_err_e         rd_event_getmsg(rd_agent_t *, rd_event_msg_t *);
 178 extern rd_err_e         rd_init(int);
 179 extern rd_err_e         rd_ctl(int, void *);
 180 extern rd_err_e         rd_loadobj_iter(rd_agent_t *, rl_iter_f *,
 181                                 void *);
 182 extern void             rd_log(const int);
 183 extern rd_agent_t       *rd_new(struct ps_prochandle *);
 184 extern rd_err_e         rd_objpad_enable(struct rd_agent *, size_t);
 185 extern rd_err_e         rd_plt_resolution(rd_agent_t *, psaddr_t, lwpid_t,
 186                                 psaddr_t, rd_plt_info_t *);
 187 extern rd_err_e         rd_get_dyns(rd_agent_t *, psaddr_t, void **, size_t *);
 188 extern rd_err_e         rd_reset(struct rd_agent *);
 189 
 190 #ifdef  __cplusplus
 191 }
 192 #endif
 193 
 194 #endif  /* _RTLD_DB_H */