|
1 /* |
|
2 Copyright (C) 2000,2004,2005 Silicon Graphics, Inc. All Rights Reserved. |
|
3 Portions Copyright (C) 2007 David Anderson. All Rights Reserved. |
|
4 |
|
5 This program is free software; you can redistribute it and/or modify it |
|
6 under the terms of version 2.1 of the GNU Lesser General Public License |
|
7 as published by the Free Software Foundation. |
|
8 |
|
9 This program is distributed in the hope that it would be useful, but |
|
10 WITHOUT ANY WARRANTY; without even the implied warranty of |
|
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. |
|
12 |
|
13 Further, this software is distributed without any warranty that it is |
|
14 free of the rightful claim of any third person regarding infringement |
|
15 or the like. Any license provided herein, whether implied or |
|
16 otherwise, applies only to this software file. Patent licenses, if |
|
17 any, provided herein do not apply to combinations of this program with |
|
18 other software, or any other product whatsoever. |
|
19 |
|
20 You should have received a copy of the GNU Lesser General Public |
|
21 License along with this program; if not, write the Free Software |
|
22 Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston MA 02110-1301, |
|
23 USA. |
|
24 |
|
25 Contact information: Silicon Graphics, Inc., 1500 Crittenden Lane, |
|
26 Mountain View, CA 94043, or: |
|
27 |
|
28 http://www.sgi.com |
|
29 |
|
30 For further information regarding this notice, see: |
|
31 |
|
32 http://oss.sgi.com/projects/GenInfo/NoticeExplan |
|
33 |
|
34 */ |
|
35 /* The address of the Free Software Foundation is |
|
36 Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, |
|
37 Boston, MA 02110-1301, USA. |
|
38 SGI has moved from the Crittenden Lane address. |
|
39 */ |
|
40 |
|
41 |
|
42 |
|
43 |
|
44 |
|
45 #include "config.h" |
|
46 #include "dwarf_incl.h" |
|
47 #include <stdio.h> |
|
48 #include "dwarf_die_deliv.h" |
|
49 |
|
50 |
|
51 |
|
52 /* |
|
53 Given a form, and a pointer to the bytes encoding |
|
54 a value of that form, val_ptr, this function returns |
|
55 the length, in bytes, of a value of that form. |
|
56 When using this function, check for a return of 0 |
|
57 a recursive DW_FORM_INDIRECT value. |
|
58 */ |
|
59 Dwarf_Unsigned |
|
60 _dwarf_get_size_of_val(Dwarf_Debug dbg, |
|
61 Dwarf_Unsigned form, |
|
62 Dwarf_Small * val_ptr, int v_length_size) |
|
63 { |
|
64 Dwarf_Unsigned length = 0; |
|
65 Dwarf_Word leb128_length = 0; |
|
66 Dwarf_Unsigned form_indirect = 0; |
|
67 Dwarf_Unsigned ret_value = 0; |
|
68 |
|
69 switch (form) { |
|
70 |
|
71 default: /* Handles form = 0. */ |
|
72 return (form); |
|
73 |
|
74 case DW_FORM_addr: |
|
75 return (dbg->de_pointer_size); |
|
76 |
|
77 case DW_FORM_ref_addr: |
|
78 return (v_length_size); |
|
79 |
|
80 case DW_FORM_block1: |
|
81 return (*(Dwarf_Small *) val_ptr + 1); |
|
82 |
|
83 case DW_FORM_block2: |
|
84 READ_UNALIGNED(dbg, ret_value, Dwarf_Unsigned, |
|
85 val_ptr, sizeof(Dwarf_Half)); |
|
86 return (ret_value + sizeof(Dwarf_Half)); |
|
87 |
|
88 case DW_FORM_block4: |
|
89 READ_UNALIGNED(dbg, ret_value, Dwarf_Unsigned, |
|
90 val_ptr, sizeof(Dwarf_ufixed)); |
|
91 return (ret_value + sizeof(Dwarf_ufixed)); |
|
92 |
|
93 |
|
94 case DW_FORM_data1: |
|
95 return (1); |
|
96 |
|
97 case DW_FORM_data2: |
|
98 return (2); |
|
99 |
|
100 case DW_FORM_data4: |
|
101 return (4); |
|
102 |
|
103 case DW_FORM_data8: |
|
104 return (8); |
|
105 |
|
106 case DW_FORM_string: |
|
107 return (strlen((char *) val_ptr) + 1); |
|
108 |
|
109 case DW_FORM_block: |
|
110 length = _dwarf_decode_u_leb128(val_ptr, &leb128_length); |
|
111 return (length + leb128_length); |
|
112 |
|
113 case DW_FORM_flag: |
|
114 return (1); |
|
115 |
|
116 case DW_FORM_ref_udata: |
|
117 _dwarf_decode_u_leb128(val_ptr, &leb128_length); |
|
118 return (leb128_length); |
|
119 |
|
120 case DW_FORM_indirect: |
|
121 { |
|
122 Dwarf_Word indir_len = 0; |
|
123 |
|
124 form_indirect = _dwarf_decode_u_leb128(val_ptr, &indir_len); |
|
125 if (form_indirect == DW_FORM_indirect) { |
|
126 return (0); /* We are in big trouble: The true form |
|
127 of DW_FORM_indirect is |
|
128 DW_FORM_indirect? Nonsense. Should |
|
129 never happen. */ |
|
130 } |
|
131 return (indir_len + _dwarf_get_size_of_val(dbg, |
|
132 form_indirect, |
|
133 val_ptr + |
|
134 indir_len, |
|
135 v_length_size)); |
|
136 } |
|
137 |
|
138 case DW_FORM_ref1: |
|
139 return (1); |
|
140 |
|
141 case DW_FORM_ref2: |
|
142 return (2); |
|
143 |
|
144 case DW_FORM_ref4: |
|
145 return (4); |
|
146 |
|
147 case DW_FORM_ref8: |
|
148 return (8); |
|
149 |
|
150 case DW_FORM_sdata: |
|
151 _dwarf_decode_s_leb128(val_ptr, &leb128_length); |
|
152 return (leb128_length); |
|
153 |
|
154 case DW_FORM_strp: |
|
155 return (v_length_size); |
|
156 |
|
157 case DW_FORM_udata: |
|
158 _dwarf_decode_u_leb128(val_ptr, &leb128_length); |
|
159 return (leb128_length); |
|
160 } |
|
161 } |
|
162 |
|
163 |
|
164 /* |
|
165 This function returns a pointer to a Dwarf_Abbrev_List_s |
|
166 struct for the abbrev with the given code. It puts the |
|
167 struct on the appropriate hash table. It also adds all |
|
168 the abbrev between the last abbrev added and this one to |
|
169 the hash table. In other words, the .debug_abbrev section |
|
170 is scanned sequentially from the top for an abbrev with |
|
171 the given code. All intervening abbrevs are also put |
|
172 into the hash table. |
|
173 |
|
174 This function hashes the given code, and checks the chain |
|
175 at that hash table entry to see if a Dwarf_Abbrev_List_s |
|
176 with the given code exists. If yes, it returns a pointer |
|
177 to that struct. Otherwise, it scans the .debug_abbrev |
|
178 section from the last byte scanned for that CU till either |
|
179 an abbrev with the given code is found, or an abbrev code |
|
180 of 0 is read. It puts Dwarf_Abbrev_List_s entries for all |
|
181 abbrev's read till that point into the hash table. The |
|
182 hash table contains both a head pointer and a tail pointer |
|
183 for each entry. |
|
184 |
|
185 Returns NULL on error. |
|
186 */ |
|
187 Dwarf_Abbrev_List |
|
188 _dwarf_get_abbrev_for_code(Dwarf_CU_Context cu_context, Dwarf_Word code) |
|
189 { |
|
190 Dwarf_Debug dbg = cu_context->cc_dbg; |
|
191 Dwarf_Hash_Table hash_table = cu_context->cc_abbrev_hash_table; |
|
192 Dwarf_Word hash_num; |
|
193 Dwarf_Abbrev_List hash_abbrev_list; |
|
194 Dwarf_Abbrev_List abbrev_list; |
|
195 Dwarf_Byte_Ptr abbrev_ptr; |
|
196 Dwarf_Half abbrev_code, abbrev_tag; |
|
197 Dwarf_Half attr_name, attr_form; |
|
198 |
|
199 hash_num = code % ABBREV_HASH_TABLE_SIZE; |
|
200 for (hash_abbrev_list = hash_table[hash_num].at_head; |
|
201 hash_abbrev_list != NULL && hash_abbrev_list->ab_code != code; |
|
202 hash_abbrev_list = hash_abbrev_list->ab_next); |
|
203 if (hash_abbrev_list != NULL) |
|
204 return (hash_abbrev_list); |
|
205 |
|
206 abbrev_ptr = cu_context->cc_last_abbrev_ptr != NULL ? |
|
207 cu_context->cc_last_abbrev_ptr : |
|
208 dbg->de_debug_abbrev + cu_context->cc_abbrev_offset; |
|
209 |
|
210 /* End of abbrev's for this cu, since abbrev code is 0. */ |
|
211 if (*abbrev_ptr == 0) { |
|
212 return (NULL); |
|
213 } |
|
214 |
|
215 do { |
|
216 Dwarf_Unsigned utmp; |
|
217 |
|
218 DECODE_LEB128_UWORD(abbrev_ptr, utmp); |
|
219 abbrev_code = (Dwarf_Half) utmp; |
|
220 DECODE_LEB128_UWORD(abbrev_ptr, utmp); |
|
221 abbrev_tag = (Dwarf_Half) utmp; |
|
222 |
|
223 abbrev_list = (Dwarf_Abbrev_List) |
|
224 _dwarf_get_alloc(cu_context->cc_dbg, DW_DLA_ABBREV_LIST, 1); |
|
225 if (abbrev_list == NULL) |
|
226 return (NULL); |
|
227 |
|
228 hash_num = abbrev_code % ABBREV_HASH_TABLE_SIZE; |
|
229 if (hash_table[hash_num].at_head == NULL) { |
|
230 hash_table[hash_num].at_head = |
|
231 hash_table[hash_num].at_tail = abbrev_list; |
|
232 } else { |
|
233 hash_table[hash_num].at_tail->ab_next = abbrev_list; |
|
234 hash_table[hash_num].at_tail = abbrev_list; |
|
235 } |
|
236 |
|
237 abbrev_list->ab_code = abbrev_code; |
|
238 abbrev_list->ab_tag = abbrev_tag; |
|
239 |
|
240 abbrev_list->ab_has_child = *(abbrev_ptr++); |
|
241 abbrev_list->ab_abbrev_ptr = abbrev_ptr; |
|
242 |
|
243 /* Cycle thru the abbrev content, ignoring the content except |
|
244 to find the end of the content. */ |
|
245 do { |
|
246 Dwarf_Unsigned utmp3; |
|
247 |
|
248 DECODE_LEB128_UWORD(abbrev_ptr, utmp3); |
|
249 attr_name = (Dwarf_Half) utmp3; |
|
250 DECODE_LEB128_UWORD(abbrev_ptr, utmp3); |
|
251 attr_form = (Dwarf_Half) utmp3; |
|
252 } while (attr_name != 0 && attr_form != 0); |
|
253 |
|
254 } while (*abbrev_ptr != 0 && abbrev_code != code); |
|
255 |
|
256 cu_context->cc_last_abbrev_ptr = abbrev_ptr; |
|
257 return (abbrev_code == code ? abbrev_list : NULL); |
|
258 } |
|
259 |
|
260 |
|
261 /* return 1 if string ends before 'endptr' else |
|
262 ** return 0 meaning string is not properly terminated. |
|
263 ** Presumption is the 'endptr' pts to end of some dwarf section data. |
|
264 */ |
|
265 int |
|
266 _dwarf_string_valid(void *startptr, void *endptr) |
|
267 { |
|
268 |
|
269 char *start = startptr; |
|
270 char *end = endptr; |
|
271 |
|
272 while (start < end) { |
|
273 if (*start == 0) { |
|
274 return 1; /* OK! */ |
|
275 } |
|
276 ++start; |
|
277 ++end; |
|
278 } |
|
279 return 0; /* FAIL! bad string! */ |
|
280 } |
|
281 |
|
282 /* |
|
283 A byte-swapping version of memcpy |
|
284 for cross-endian use. |
|
285 Only 2,4,8 should be lengths passed in. |
|
286 */ |
|
287 void * |
|
288 _dwarf_memcpy_swap_bytes(void *s1, const void *s2, size_t len) |
|
289 { |
|
290 void *orig_s1 = s1; |
|
291 unsigned char *targ = (unsigned char *) s1; |
|
292 unsigned char *src = (unsigned char *) s2; |
|
293 |
|
294 if (len == 4) { |
|
295 targ[3] = src[0]; |
|
296 targ[2] = src[1]; |
|
297 targ[1] = src[2]; |
|
298 targ[0] = src[3]; |
|
299 } else if (len == 8) { |
|
300 targ[7] = src[0]; |
|
301 targ[6] = src[1]; |
|
302 targ[5] = src[2]; |
|
303 targ[4] = src[3]; |
|
304 targ[3] = src[4]; |
|
305 targ[2] = src[5]; |
|
306 targ[1] = src[6]; |
|
307 targ[0] = src[7]; |
|
308 } else if (len == 2) { |
|
309 targ[1] = src[0]; |
|
310 targ[0] = src[1]; |
|
311 } |
|
312 /* should NOT get below here: is not the intended use */ |
|
313 else if (len == 1) { |
|
314 targ[0] = src[0]; |
|
315 } else { |
|
316 memcpy(s1, s2, len); |
|
317 } |
|
318 |
|
319 return orig_s1; |
|
320 } |
|
321 |
|
322 |
|
323 /* |
|
324 This calculation used to be sprinkled all over. |
|
325 Now brought to one place. |
|
326 |
|
327 We try to accurately compute the size of a cu header |
|
328 given a known cu header location ( an offset in .debug_info). |
|
329 |
|
330 */ |
|
331 /* ARGSUSED */ |
|
332 Dwarf_Unsigned |
|
333 _dwarf_length_of_cu_header(Dwarf_Debug dbg, Dwarf_Unsigned offset) |
|
334 { |
|
335 int local_length_size = 0; |
|
336 int local_extension_size = 0; |
|
337 Dwarf_Unsigned length = 0; |
|
338 Dwarf_Small *cuptr = dbg->de_debug_info + offset; |
|
339 |
|
340 READ_AREA_LENGTH(dbg, length, Dwarf_Unsigned, |
|
341 cuptr, local_length_size, local_extension_size); |
|
342 |
|
343 return local_extension_size + /* initial extesion, if present |
|
344 */ |
|
345 local_length_size + /* Size of cu length field. */ |
|
346 sizeof(Dwarf_Half) + /* Size of version stamp field. */ |
|
347 local_length_size + /* Size of abbrev offset field. */ |
|
348 sizeof(Dwarf_Small); /* Size of address size field. */ |
|
349 |
|
350 } |
|
351 |
|
352 /* |
|
353 Pretend we know nothing about the CU |
|
354 and just roughly compute the result. |
|
355 */ |
|
356 Dwarf_Unsigned |
|
357 _dwarf_length_of_cu_header_simple(Dwarf_Debug dbg) |
|
358 { |
|
359 return dbg->de_length_size + /* Size of cu length field. */ |
|
360 sizeof(Dwarf_Half) + /* Size of version stamp field. */ |
|
361 dbg->de_length_size + /* Size of abbrev offset field. */ |
|
362 sizeof(Dwarf_Small); /* Size of address size field. */ |
|
363 } |
|
364 |
|
365 /* Now that we delay loading .debug_info, we need to do the |
|
366 load in more places. So putting the load |
|
367 code in one place now instead of replicating it in multiple |
|
368 places. |
|
369 |
|
370 */ |
|
371 int |
|
372 _dwarf_load_debug_info(Dwarf_Debug dbg, Dwarf_Error * error) |
|
373 { |
|
374 int res; |
|
375 |
|
376 /* Testing de_debug_info allows us to avoid testing |
|
377 de_debug_abbrev. One test instead of 2. .debug_info is useless |
|
378 without .debug_abbrev. */ |
|
379 if (dbg->de_debug_info) { |
|
380 return DW_DLV_OK; |
|
381 } |
|
382 |
|
383 res = _dwarf_load_section(dbg, dbg->de_debug_abbrev_index, |
|
384 &dbg->de_debug_abbrev, error); |
|
385 if (res != DW_DLV_OK) { |
|
386 return res; |
|
387 } |
|
388 res = _dwarf_load_section(dbg, dbg->de_debug_info_index, |
|
389 &dbg->de_debug_info, error); |
|
390 return res; |
|
391 |
|
392 } |