summaryrefslogtreecommitdiff
path: root/usr/src/head/rtld_db.h
blob: 0bfe30057ef3223c5c5ff822e3d0272186f8a1fd (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
/*
 * CDDL HEADER START
 *
 * The contents of this file are subject to the terms of the
 * Common Development and Distribution License (the "License").
 * You may not use this file except in compliance with the License.
 *
 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
 * or http://www.opensolaris.org/os/licensing.
 * See the License for the specific language governing permissions
 * and limitations under the License.
 *
 * When distributing Covered Code, include this CDDL HEADER in each
 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
 * If applicable, add the following below this CDDL HEADER, with the
 * fields enclosed by brackets "[]" replaced with your own identifying
 * information: Portions Copyright [yyyy] [name of copyright owner]
 *
 * CDDL HEADER END
 */
/*
 * Copyright 2014 Garrett D'Amore <garrett@damore.org>
 *
 * Copyright 2008 Sun Microsystems, Inc.  All rights reserved.
 * Use is subject to license terms.
 */

#ifndef	_RTLD_DB_H
#define	_RTLD_DB_H

#ifdef	__cplusplus
extern "C" {
#endif

#include <sys/types.h>
#include <sys/lwp.h>
#include <sys/elf.h>
#include <link.h>
#include <proc_service.h>


/*
 * librtld_db interface versions
 */
#define	RD_VERSION1	1
#define	RD_VERSION2	2
#define	RD_VERSION3	3
#define	RD_VERSION4	4
#define	RD_VERSION	RD_VERSION4

typedef enum {
	RD_ERR,		/* generic */
	RD_OK,		/* generic "call" succeeded */
	RD_NOCAPAB,	/* capability not available */
	RD_DBERR,	/* import service failed */
	RD_NOBASE,	/* 5.x: aux tag AT_BASE not found */
	RD_NODYNAM,	/* symbol 'DYNAMIC' not found */
	RD_NOMAPS	/* link-maps are not yet available */
} rd_err_e;


/*
 * ways that the event notification can take place:
 */
typedef enum {
	RD_NOTIFY_BPT,		/* set break-point at address */
	RD_NOTIFY_AUTOBPT,	/* 4.x compat. not used in 5.x */
	RD_NOTIFY_SYSCALL	/* watch for syscall */
} rd_notify_e;

/*
 * information on ways that the event notification can take place:
 */
typedef struct rd_notify {
	rd_notify_e	type;
	union {
		psaddr_t	bptaddr;	/* break point address */
		long		syscallno;	/* system call id */
	} u;
} rd_notify_t;

/*
 * information about event instance:
 */
typedef enum {
	RD_NOSTATE = 0,		/* no state information */
	RD_CONSISTENT,		/* link-maps are stable */
	RD_ADD,			/* currently adding object to link-maps */
	RD_DELETE		/* currently deleteing object from link-maps */
} rd_state_e;

typedef struct rd_event_msg {
	rd_event_e	type;
	union {
		rd_state_e	state;	/* for DLACTIVITY */
	} u;
} rd_event_msg_t;


/*
 * iteration over load objects
 */
typedef struct rd_loadobj {
	psaddr_t	rl_nameaddr;	/* address of the name in user space */
	unsigned	rl_flags;
	psaddr_t	rl_base;	/* base of address of code */
	psaddr_t	rl_data_base;	/* base of address of data */
	Lmid_t		rl_lmident;	/* ident of link map */
	psaddr_t	rl_refnameaddr;	/* reference name of filter in user */
					/* space.  If non null object is a */
					/* filter. */
	psaddr_t	rl_plt_base;	/* These fields are present for 4.x */
	unsigned	rl_plt_size;	/* compatibility and are not */
					/* currently used  in SunOS5.x */
	psaddr_t	rl_bend;	/* end of image (text+data+bss) */
	psaddr_t	rl_padstart;	/* start of padding */
	psaddr_t	rl_padend;	/* end of image after padding */
	psaddr_t	rl_dynamic;	/* points to the DYNAMIC section */
					/* in the target process */
	unsigned long	rl_tlsmodid;	/* module ID for TLS references */
} rd_loadobj_t;

/*
 * Values for rl_flags
 */
#define	RD_FLG_MEM_OBJECT	0x0001	/* Identifies this object as */
					/* originating from a relocatable */
					/* module which was dynamically */
					/* loaded */

/*
 * Commands for rd_ctl()
 */
#define	RD_CTL_SET_HELPPATH	0x01	/* Set the path used to find helpers */

typedef struct rd_agent rd_agent_t;
typedef int rl_iter_f(const rd_loadobj_t *, void *);


/*
 * PLT skipping
 */
typedef enum {
    RD_RESOLVE_NONE,		/* don't do anything special */
    RD_RESOLVE_STEP,		/* step 'pi_nstep' instructions */
    RD_RESOLVE_TARGET,		/* resolved target is in 'pi_target' */
    RD_RESOLVE_TARGET_STEP	/* put a bpt on target, then step nstep times */
} rd_skip_e;


typedef struct rd_plt_info {
	rd_skip_e	pi_skip_method;
	long		pi_nstep;
	psaddr_t	pi_target;
	psaddr_t	pi_baddr;
	unsigned int	pi_flags;
} rd_plt_info_t;


/*
 * Values for pi_flags
 */
#define	RD_FLG_PI_PLTBOUND	0x0001	/* Indicates that the PLT */
					/* has been bound - and that */
					/* pi_baddr will contain its */
					/* destination address */

struct	ps_prochandle;

/*
 * librtld_db.so entry points
 */
extern void		rd_delete(rd_agent_t *);
extern char		*rd_errstr(rd_err_e rderr);
extern rd_err_e		rd_event_addr(rd_agent_t *, rd_event_e, rd_notify_t *);
extern rd_err_e		rd_event_enable(rd_agent_t *, int);
extern rd_err_e		rd_event_getmsg(rd_agent_t *, rd_event_msg_t *);
extern rd_err_e		rd_init(int);
extern rd_err_e		rd_ctl(int, void *);
extern rd_err_e		rd_loadobj_iter(rd_agent_t *, rl_iter_f *,
				void *);
extern void		rd_log(const int);
extern rd_agent_t	*rd_new(struct ps_prochandle *);
extern rd_err_e		rd_objpad_enable(struct rd_agent *, size_t);
extern rd_err_e		rd_plt_resolution(rd_agent_t *, psaddr_t, lwpid_t,
				psaddr_t, rd_plt_info_t *);
extern rd_err_e		rd_get_dyns(rd_agent_t *, psaddr_t, void **, size_t *);
extern rd_err_e		rd_reset(struct rd_agent *);

#ifdef	__cplusplus
}
#endif

#endif	/* _RTLD_DB_H */