blob: e1d47be5d9088892a64fe9995fbc8efd5543f802 [file] [log] [blame]
hp.com!davidm76166fb2002-04-05 23:37:55 +00001/* libunwind - a platform-independent unwind library
mostang.com!davidm53b6d612004-01-21 01:05:07 +00002 Copyright (C) 2001-2004 Hewlett-Packard Co
hp.com!davidm76166fb2002-04-05 23:37:55 +00003 Contributed by David Mosberger-Tang <davidm@hpl.hp.com>
4
5This file is part of libunwind.
6
mostang.com!davidmaca38432002-11-16 03:25:36 +00007Permission is hereby granted, free of charge, to any person obtaining
8a copy of this software and associated documentation files (the
9"Software"), to deal in the Software without restriction, including
10without limitation the rights to use, copy, modify, merge, publish,
11distribute, sublicense, and/or sell copies of the Software, and to
12permit persons to whom the Software is furnished to do so, subject to
13the following conditions:
hp.com!davidm76166fb2002-04-05 23:37:55 +000014
mostang.com!davidmaca38432002-11-16 03:25:36 +000015The above copyright notice and this permission notice shall be
16included in all copies or substantial portions of the Software.
hp.com!davidm76166fb2002-04-05 23:37:55 +000017
mostang.com!davidmaca38432002-11-16 03:25:36 +000018THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
19EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
20MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
21NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
22LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
23OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
24WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */
hp.com!davidm76166fb2002-04-05 23:37:55 +000025
26#define UNW_PASTE2(x,y) x##y
27#define UNW_PASTE(x,y) UNW_PASTE2(x,y)
28#define UNW_OBJ(fn) UNW_PASTE(UNW_PREFIX, fn)
mostang.com!davidm50d7a152002-12-03 08:19:58 +000029#define UNW_ARCH_OBJ(fn) UNW_PASTE(UNW_PASTE(UNW_PASTE(_U,UNW_TARGET),_), fn)
hp.com!davidm76166fb2002-04-05 23:37:55 +000030
31#ifdef UNW_LOCAL_ONLY
32# define UNW_PREFIX UNW_PASTE(UNW_PASTE(_UL,UNW_TARGET),_)
33#else /* !UNW_LOCAL_ONLY */
34# define UNW_PREFIX UNW_PASTE(UNW_PASTE(_U,UNW_TARGET),_)
35#endif /* !UNW_LOCAL_ONLY */
36
hp.com!davidm76166fb2002-04-05 23:37:55 +000037/* Error codes. The unwind routines return the *negated* values of
38 these error codes on error and a non-negative value on success. */
39typedef enum
40 {
41 UNW_ESUCCESS = 0, /* no error */
42 UNW_EUNSPEC, /* unspecified (general) error */
43 UNW_ENOMEM, /* out of memory */
44 UNW_EBADREG, /* bad register number */
45 UNW_EREADONLYREG, /* attempt to write read-only register */
46 UNW_ESTOPUNWIND, /* stop unwinding */
47 UNW_EINVALIDIP, /* invalid IP */
48 UNW_EBADFRAME, /* bad frame */
mostang.com!davidm50d7a152002-12-03 08:19:58 +000049 UNW_EINVAL, /* unsupported operation or bad value */
hp.com!davidm76166fb2002-04-05 23:37:55 +000050 UNW_EBADVERSION, /* unwind info has unsupported version */
51 UNW_ENOINFO /* no unwind info found */
52 }
53unw_error_t;
54
55/* The following enum defines the indices for a couple of
56 (pseudo-)registers which have the same meaning across all
57 platforms. (RO) means read-only. (RW) means read-write. General
58 registers (aka "integer registers") are expected to start with
59 index 0. The number of such registers is architecture-dependent.
60 The remaining indices can be used as an architecture sees fit. The
61 last valid register index is given by UNW_REG_LAST. */
62typedef enum
63 {
64 UNW_REG_IP = UNW_TDEP_IP, /* (rw) instruction pointer (pc) */
65 UNW_REG_SP = UNW_TDEP_SP, /* (ro) stack pointer */
mostang.com!davidmc670abb2003-03-06 06:14:36 +000066 UNW_REG_EH = UNW_TDEP_EH, /* (rw) exception-handling reg base */
hp.com!davidm76166fb2002-04-05 23:37:55 +000067 UNW_REG_LAST = UNW_TDEP_LAST_REG
68 }
69unw_frame_regnum_t;
70
mostang.com!davidmc670abb2003-03-06 06:14:36 +000071/* Number of exception-handler argument registers: */
72#define UNW_NUM_EH_REGS UNW_TDEP_NUM_EH_REGS
73
mostang.com!davidm16f21892002-11-09 07:59:02 +000074typedef enum
75 {
76 UNW_CACHE_NONE, /* no caching */
77 UNW_CACHE_GLOBAL, /* shared global cache */
78 UNW_CACHE_PER_THREAD /* per-thread caching */
79 }
80unw_caching_policy_t;
81
hp.com!davidm76166fb2002-04-05 23:37:55 +000082typedef int unw_regnum_t;
83
84/* The unwind cursor starts at the youngest (most deeply nested) frame
85 and is used to track the frame state as the unwinder steps from
86 frame to frame. It is safe to make (shallow) copies of variables
87 of this type. */
88typedef struct unw_cursor
89 {
mostang.com!davidma4bea2c2003-01-21 08:08:32 +000090 unw_word_t opaque[UNW_TDEP_CURSOR_LEN];
hp.com!davidm76166fb2002-04-05 23:37:55 +000091 }
92unw_cursor_t;
93
94/* This type encapsulates the entire (preserved) machine-state. */
95typedef unw_tdep_context_t unw_context_t;
96
97/* unw_getcontext() fills the unw_context_t pointed to by UC with the
98 machine state as it exists at the call-site. For implementation
99 reasons, this needs to be a target-dependent macro. It's easiest
100 to think of unw_getcontext() as being identical to getcontext(). */
mostang.com!davidm53b6d612004-01-21 01:05:07 +0000101#define unw_getcontext(uc) unw_tdep_getcontext(uc)
102
103/* Return 1 if register number R is a floating-point register, zero
104 otherwise.
105 This routine is signal-safe. */
106#define unw_is_fpreg(r) unw_tdep_is_fpreg(r)
hp.com!davidm76166fb2002-04-05 23:37:55 +0000107
mostang.com!davidm981c8cc2003-02-08 10:10:59 +0000108typedef unw_tdep_fpreg_t unw_fpreg_t;
hp.com!davidm76166fb2002-04-05 23:37:55 +0000109
mostang.com!davidm87bc2e32002-11-16 06:50:04 +0000110typedef struct unw_addr_space *unw_addr_space_t;
111
mostang.com!davidmd5db6012003-12-21 05:53:57 +0000112/* Each target may define it's own set of flags, but bits 0-15 are
113 reserved for general libunwind-use. */
mostang.com!davidma4bea2c2003-01-21 08:08:32 +0000114#define UNW_PI_FLAG_FIRST_TDEP_BIT 16
115
mostang.com!davidm50d7a152002-12-03 08:19:58 +0000116typedef struct unw_proc_info
117 {
118 unw_word_t start_ip; /* first IP covered by this procedure */
119 unw_word_t end_ip; /* first IP NOT covered by this procedure */
120 unw_word_t lsda; /* address of lang.-spec. data area (if any) */
121 unw_word_t handler; /* optional personality routine */
122 unw_word_t gp; /* global-pointer value for this procedure */
123 unw_word_t flags; /* misc. flags */
mostang.com!davidm50d7a152002-12-03 08:19:58 +0000124
125 int format; /* unwind-info format (arch-specific) */
hp.com!davidmfbe40e52003-12-20 11:20:42 +0000126 int unwind_info_size; /* size of the information (if applicable) */
mostang.com!davidm50d7a152002-12-03 08:19:58 +0000127 void *unwind_info; /* unwind-info (arch-specific) */
hp.com!davidmfbe40e52003-12-20 11:20:42 +0000128 unw_tdep_proc_info_t extra; /* target-dependent auxiliary proc-info */
mostang.com!davidm50d7a152002-12-03 08:19:58 +0000129 }
130unw_proc_info_t;
131
hp.com!davidm76166fb2002-04-05 23:37:55 +0000132/* These are backend callback routines that provide access to the
133 state of a "remote" process. This can be used, for example, to
134 unwind another process through the ptrace() interface. */
135typedef struct unw_accessors
136 {
mostang.com!davidm50d7a152002-12-03 08:19:58 +0000137 /* Look up the unwind info associated with instruction-pointer IP.
138 On success, the routine fills in the PROC_INFO structure. */
mostang.com!davidm53b6d612004-01-21 01:05:07 +0000139 int (*find_proc_info) (unw_addr_space_t, unw_word_t, unw_proc_info_t *,
140 int, void *);
hp.com!davidm76166fb2002-04-05 23:37:55 +0000141
mostang.com!davidmb6251b02002-12-12 09:17:41 +0000142 /* Release any resources (e.g., memory) that were allocated for
143 the unwind info returned in by a previous call to
144 find_proc_info() with NEED_UNWIND_INFO set to 1. */
mostang.com!davidm53b6d612004-01-21 01:05:07 +0000145 void (*put_unwind_info) (unw_addr_space_t, unw_proc_info_t *, void *);
mostang.com!davidmb6251b02002-12-12 09:17:41 +0000146
147 /* Return the list-head of the dynamically registered unwind
148 info. */
mostang.com!davidm53b6d612004-01-21 01:05:07 +0000149 int (*get_dyn_info_list_addr) (unw_addr_space_t, unw_word_t *, void *);
mostang.com!davidmb6251b02002-12-12 09:17:41 +0000150
151 /* Access aligned word at address ADDR. The value is returned
152 according to the endianness of the host (e.g., if the host is
153 little-endian and the target is big-endian, access_mem() needs
154 to byte-swap the value before returning it). */
mostang.com!davidm53b6d612004-01-21 01:05:07 +0000155 int (*access_mem) (unw_addr_space_t, unw_word_t, unw_word_t *, int,
156 void *);
hp.com!davidm76166fb2002-04-05 23:37:55 +0000157
158 /* Access register number REG at address ADDR. */
mostang.com!davidm53b6d612004-01-21 01:05:07 +0000159 int (*access_reg) (unw_addr_space_t, unw_regnum_t, unw_word_t *, int,
160 void *);
hp.com!davidm76166fb2002-04-05 23:37:55 +0000161
162 /* Access register number REG at address ADDR. */
mostang.com!davidm53b6d612004-01-21 01:05:07 +0000163 int (*access_fpreg) (unw_addr_space_t, unw_regnum_t,
164 unw_fpreg_t *, int, void *);
hp.com!davidm76166fb2002-04-05 23:37:55 +0000165
mostang.com!davidm53b6d612004-01-21 01:05:07 +0000166 int (*resume) (unw_addr_space_t, unw_cursor_t *, void *);
mostang.com!davidm73438412003-02-27 09:58:57 +0000167
168 /* Optional call back to obtain the name of a (static) procedure.
169 Dynamically generated procedures are handled automatically by
170 libunwind. This callback is optional and may be set to
171 NULL. */
mostang.com!davidm53b6d612004-01-21 01:05:07 +0000172 int (*get_proc_name) (unw_addr_space_t, unw_word_t, char *, size_t,
173 unw_word_t *, void *);
hp.com!davidm76166fb2002-04-05 23:37:55 +0000174 }
175unw_accessors_t;
176
177typedef enum unw_save_loc_type
178 {
179 UNW_SLT_NONE, /* register is not saved ("not an l-value") */
180 UNW_SLT_MEMORY, /* register has been saved in memory */
181 UNW_SLT_REG /* register has been saved in (another) register */
182 }
183unw_save_loc_type_t;
184
185typedef struct unw_save_loc
186 {
187 unw_save_loc_type_t type;
188 union
189 {
190 unw_word_t addr; /* valid if type==UNW_SLT_MEMORY */
191 unw_regnum_t regnum; /* valid if type==UNW_SLT_REG */
192 }
193 u;
194 unw_tdep_save_loc_t extra; /* target-dependent additional information */
195 }
196unw_save_loc_t;
197
198/* These routines work both for local and remote unwinding. */
199
mostang.com!davidm53b6d612004-01-21 01:05:07 +0000200#define unw_local_addr_space UNW_OBJ(local_addr_space)
201#define unw_create_addr_space UNW_OBJ(create_addr_space)
202#define unw_destroy_addr_space UNW_OBJ(destroy_addr_space)
203#define unw_get_accessors UNW_ARCH_OBJ(get_accessors)
204#define unw_init_local UNW_OBJ(init_local)
205#define unw_init_remote UNW_OBJ(init_remote)
206#define unw_step UNW_OBJ(step)
207#define unw_resume UNW_OBJ(resume)
208#define unw_get_proc_info UNW_OBJ(get_proc_info)
209#define unw_get_proc_info_by_ip UNW_OBJ(get_proc_info_by_ip)
210#define unw_get_reg UNW_OBJ(get_reg)
211#define unw_set_reg UNW_OBJ(set_reg)
212#define unw_get_fpreg UNW_OBJ(get_fpreg)
213#define unw_set_fpreg UNW_OBJ(set_fpreg)
214#define unw_get_save_loc UNW_OBJ(get_save_loc)
215#define unw_is_signal_frame UNW_OBJ(is_signal_frame)
216#define unw_get_proc_name UNW_OBJ(get_proc_name)
hp.com!davidm6ea8ff62004-01-24 07:22:30 +0000217#define unw_set_caching_policy UNW_OBJ(set_caching_policy)
mostang.com!davidm53b6d612004-01-21 01:05:07 +0000218#define unw_regname UNW_ARCH_OBJ(regname)
mostang.com!davidm53b6d612004-01-21 01:05:07 +0000219#define unw_flush_cache UNW_ARCH_OBJ(flush_cache)
mostang.com!davidm87bc2e32002-11-16 06:50:04 +0000220
mostang.com!davidm53b6d612004-01-21 01:05:07 +0000221extern unw_addr_space_t unw_create_addr_space (unw_accessors_t *, int);
222extern void unw_destroy_addr_space (unw_addr_space_t);
223extern unw_accessors_t *unw_get_accessors (unw_addr_space_t);
224extern void unw_flush_cache (unw_addr_space_t, unw_word_t, unw_word_t);
225extern int unw_set_caching_policy (unw_addr_space_t, unw_caching_policy_t);
226extern const char *unw_regname (unw_regnum_t);
mostang.com!davidm20a6c1a2002-12-19 07:16:50 +0000227
mostang.com!davidm53b6d612004-01-21 01:05:07 +0000228extern int unw_init_local (unw_cursor_t *, unw_context_t *);
229extern int unw_init_remote (unw_cursor_t *, unw_addr_space_t, void *);
230extern int unw_step (unw_cursor_t *);
231extern int unw_resume (unw_cursor_t *);
232extern int unw_get_proc_info (unw_cursor_t *, unw_proc_info_t *);
233extern int unw_get_proc_info_by_ip (unw_addr_space_t, unw_word_t,
234 unw_proc_info_t *, void *);
235extern int unw_get_reg (unw_cursor_t *, int, unw_word_t *);
236extern int unw_set_reg (unw_cursor_t *, int, unw_word_t);
237extern int unw_get_fpreg (unw_cursor_t *, int, unw_fpreg_t *);
238extern int unw_set_fpreg (unw_cursor_t *, int, unw_fpreg_t);
239extern int unw_get_save_loc (unw_cursor_t *, int, unw_save_loc_t *);
240extern int unw_is_signal_frame (unw_cursor_t *);
241extern int unw_get_proc_name (unw_cursor_t *, char *, size_t, unw_word_t *);
hp.com!davidm76166fb2002-04-05 23:37:55 +0000242
mostang.com!davidm53b6d612004-01-21 01:05:07 +0000243extern unw_addr_space_t unw_local_addr_space;