1 /*
2 Copyright (C) 2000-2006 Silicon Graphics, Inc. All Rights Reserved.
3 Portions Copyright (C) 2007-2019 David Anderson. All Rights Reserved.
4 Portions Copyright 2012 SN Systems Ltd. All rights reserved.
5
6 This program is free software; you can redistribute it
7 and/or modify it under the terms of version 2.1 of the
8 GNU Lesser General Public License as published by the Free
9 Software Foundation.
10
11 This program is distributed in the hope that it would be
12 useful, but WITHOUT ANY WARRANTY; without even the implied
13 warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
14 PURPOSE.
15
16 Further, this software is distributed without any warranty
17 that it is free of the rightful claim of any third person
18 regarding infringement or the like. Any license provided
19 herein, whether implied or otherwise, applies only to this
20 software file. Patent licenses, if any, provided herein
21 do not apply to combinations of this program with other
22 software, or any other product whatsoever.
23
24 You should have received a copy of the GNU Lesser General
25 Public License along with this program; if not, write the
26 Free Software Foundation, Inc., 51 Franklin Street - Fifth
27 Floor, Boston MA 02110-1301, USA.
28
29 */
30
31 #include "config.h"
32 #include <stdio.h>
33 #ifdef HAVE_STDLIB_H
34 #include <stdlib.h>
35 #endif /* HAVE_STDLIB_H */
36 #ifdef HAVE_STDINT_H
37 #include <stdint.h> /* For uintptr_t */
38 #endif /* HAVE_STDINT_H */
39 #include "dwarf_incl.h"
40 #include "dwarf_alloc.h"
41 #include "dwarf_error.h"
42 #include "dwarf_util.h"
43 #include "dwarf_frame.h"
44 #include "dwarf_arange.h" /* Using Arange as a way to build a list */
45
46 #define FDE_NULL_CHECKS_AND_SET_DBG(fde,dbg ) \
47 do { \
48 if ((fde) == NULL) { \
49 _dwarf_error(NULL, error, DW_DLE_FDE_NULL);\
50 return (DW_DLV_ERROR); \
51 } \
52 (dbg)= (fde)->fd_dbg; \
53 if ((dbg) == NULL) { \
54 _dwarf_error(NULL, error, DW_DLE_FDE_DBG_NULL);\
55 return (DW_DLV_ERROR); \
56 } } while (0)
57
58
59 #define MIN(a,b) (((a) < (b))? a:b)
60
61 #if 0
62 static void
63 dump_bytes(const char *msg,Dwarf_Small * start, long len)
64 {
65 Dwarf_Small *end = start + len;
66 Dwarf_Small *cur = start;
67 printf("%s (0x%lx) ",msg,(unsigned long)start);
68 for (; cur < end; cur++) {
69 printf("%02x", *cur);
70 }
71 printf("\n");
72 }
73 #endif /* 0 */
74
75
76 static int dwarf_initialize_fde_table(Dwarf_Debug dbg,
77 struct Dwarf_Frame_s *fde_table,
78 unsigned table_real_data_size,
79 Dwarf_Error * error);
80 static void dwarf_free_fde_table(struct Dwarf_Frame_s *fde_table);
81 static void dwarf_init_reg_rules_ru(struct Dwarf_Reg_Rule_s *base,
82 unsigned first, unsigned last,int initial_value);
83 static void dwarf_init_reg_rules_dw(struct Dwarf_Regtable_Entry_s *base,
84 unsigned first, unsigned last,int initial_value);
85 static void dwarf_init_reg_rules_dw3(struct Dwarf_Regtable_Entry3_s *base,
86 unsigned first, unsigned last,int initial_value);
87
88
89 #if 0 /* FOR DEBUGGING */
90 /* Only used for debugging libdwarf. */
91 static void dump_frame_rule(char *msg,
92 struct Dwarf_Reg_Rule_s *reg_rule);
93 #endif
94
95
96 int
dwarf_get_frame_section_name(Dwarf_Debug dbg,const char ** sec_name,Dwarf_Error * error)97 dwarf_get_frame_section_name(Dwarf_Debug dbg,
98 const char **sec_name,
99 Dwarf_Error *error)
100 {
101 struct Dwarf_Section_s *sec = 0;
102 if (error != NULL) {
103 *error = NULL;
104 }
105 sec = &dbg->de_debug_frame;
106 if (sec->dss_size == 0) {
107 /* We don't have such a section at all. */
108 return DW_DLV_NO_ENTRY;
109 }
110 *sec_name = sec->dss_name;
111 return DW_DLV_OK;
112 }
113
114 int
dwarf_get_frame_section_name_eh_gnu(Dwarf_Debug dbg,const char ** sec_name,Dwarf_Error * error)115 dwarf_get_frame_section_name_eh_gnu(Dwarf_Debug dbg,
116 const char **sec_name,
117 Dwarf_Error *error)
118 {
119 struct Dwarf_Section_s *sec = 0;
120 if (error != NULL) {
121 *error = NULL;
122 }
123 sec = &dbg->de_debug_frame_eh_gnu;
124 if (sec->dss_size == 0) {
125 /* We don't have such a section at all. */
126 return DW_DLV_NO_ENTRY;
127 }
128 *sec_name = sec->dss_name;
129 return DW_DLV_OK;
130 }
131
132 /*
133 This function is the heart of the debug_frame stuff. Don't even
134 think of reading this without reading both the Libdwarf and
135 consumer API carefully first. This function basically executes
136 frame instructions contained in a Cie or an Fde, but does in a
137 number of different ways depending on the information sought.
138 Start_instr_ptr points to the first byte of the frame instruction
139 stream, and final_instr_ptr to the to the first byte after the
140 last.
141
142 The offsets returned in the frame instructions are factored. That
143 is they need to be multiplied by either the code_alignment_factor
144 or the data_alignment_factor, as appropriate to obtain the actual
145 offset. This makes it possible to expand an instruction stream
146 without the corresponding Cie. However, when an Fde frame instr
147 sequence is being expanded there must be a valid Cie with a pointer
148 to an initial table row.
149
150
151 If successful, returns DW_DLV_OK
152 And sets returned_count thru the pointer
153 if make_instr is true.
154 If make_instr is false returned_count
155 should NOT be used by the caller (returned_count
156 is set to 0 thru the pointer by this routine...)
157 If unsuccessful, returns DW_DLV_ERROR
158 and sets returned_error to the error code
159
160 It does not do a whole lot of input validation being a private
161 function. Please make sure inputs are valid.
162
163 (1) If make_instr is true, it makes a list of pointers to
164 Dwarf_Frame_Op structures containing the frame instructions
165 executed. A pointer to this list is returned in ret_frame_instr.
166 Make_instr is true only when a list of frame instructions is to be
167 returned. In this case since we are not interested in the contents
168 of the table, the input Cie can be NULL. This is the only case
169 where the inpute Cie can be NULL.
170
171 (2) If search_pc is true, frame instructions are executed till
172 either a location is reached that is greater than the search_pc_val
173 provided, or all instructions are executed. At this point the
174 last row of the table generated is returned in a structure.
175 A pointer to this structure is supplied in table.
176
177 (3) This function is also used to create the initial table row
178 defined by a Cie. In this case, the Dwarf_Cie pointer cie, is
179 NULL. For an FDE, however, cie points to the associated Cie.
180
181 (4) If search_pc is true and (has_more_rows and subsequent_pc
182 are non-null) then:
183 has_more_rows is set true if there are instruction
184 bytes following the detection of search_over.
185 If all the instruction bytes have been seen
186 then *has_more_rows is set false.
187
188 If *has_more_rows is true then *subsequent_pc
189 is set to the pc value that is the following
190 row in the table.
191
192 make_instr - make list of frame instr? 0/1
193 ret_frame_instr - Ptr to list of ptrs to frame instrs
194 search_pc - Search for a pc value? 0/1
195 search_pc_val - Search for this pc value
196 initial_loc - Initial code location value.
197 start_instr_ptr - Ptr to start of frame instrs.
198 final_instr_ptr - Ptr just past frame instrs.
199 table - Ptr to struct with last row.
200 cie - Ptr to Cie used by the Fde.
201
202 Different cies may have distinct address-sizes, so the cie
203 is used, not de_pointer_size.
204
205 */
206
207 int
_dwarf_exec_frame_instr(Dwarf_Bool make_instr,Dwarf_Frame_Op ** ret_frame_instr,Dwarf_Bool search_pc,Dwarf_Addr search_pc_val,Dwarf_Addr initial_loc,Dwarf_Small * start_instr_ptr,Dwarf_Small * final_instr_ptr,Dwarf_Frame table,Dwarf_Cie cie,Dwarf_Debug dbg,Dwarf_Half reg_num_of_cfa,Dwarf_Signed * returned_count,Dwarf_Bool * has_more_rows,Dwarf_Addr * subsequent_pc,Dwarf_Error * error)208 _dwarf_exec_frame_instr(Dwarf_Bool make_instr,
209 Dwarf_Frame_Op ** ret_frame_instr,
210 Dwarf_Bool search_pc,
211 Dwarf_Addr search_pc_val,
212 Dwarf_Addr initial_loc,
213 Dwarf_Small * start_instr_ptr,
214 Dwarf_Small * final_instr_ptr,
215 Dwarf_Frame table,
216 Dwarf_Cie cie,
217 Dwarf_Debug dbg,
218 Dwarf_Half reg_num_of_cfa,
219 Dwarf_Signed * returned_count,
220 Dwarf_Bool * has_more_rows,
221 Dwarf_Addr * subsequent_pc,
222 Dwarf_Error *error)
223 {
224 /* The following macro depends on macreg and
225 machigh_reg both being unsigned to avoid
226 unintended behavior and to avoid compiler warnings when
227 high warning levels are turned on. */
228 #define ERROR_IF_REG_NUM_TOO_HIGH(macreg,machigh_reg) \
229 do { \
230 if ((macreg) >= (machigh_reg)) { \
231 SIMPLE_ERROR_RETURN(DW_DLE_DF_REG_NUM_TOO_HIGH); \
232 } \
233 } /*CONSTCOND */ while (0)
234 #define SIMPLE_ERROR_RETURN(code) \
235 free(localregtab); \
236 _dwarf_error(dbg,error,code); \
237 return DW_DLV_ERROR
238
239 /* Sweeps the frame instructions. */
240 Dwarf_Small *instr_ptr = 0;
241
242 /* Register numbers not limited to just 255, thus not using
243 Dwarf_Small. */
244 typedef unsigned reg_num_type;
245
246 Dwarf_Unsigned factored_N_value = 0;
247 Dwarf_Signed signed_factored_N_value = 0;
248 Dwarf_Addr current_loc = initial_loc; /* code location/
249 pc-value corresponding to the frame instructions.
250 Starts at zero when the caller has no value to pass in. */
251
252 /* Must be min de_pointer_size bytes and must be at least 4 */
253 Dwarf_Unsigned adv_loc = 0;
254
255 unsigned reg_count = dbg->de_frame_reg_rules_entry_count;
256 struct Dwarf_Reg_Rule_s *localregtab = calloc(reg_count,
257 sizeof(struct Dwarf_Reg_Rule_s));
258
259 struct Dwarf_Reg_Rule_s cfa_reg;
260
261 /* This is used to end executing frame instructions. */
262 /* Becomes true when search_pc is true and current_loc */
263 /* is greater than search_pc_val. */
264 Dwarf_Bool search_over = false;
265
266 Dwarf_Addr possible_subsequent_pc = 0;
267
268 /* Used by the DW_FRAME_advance_loc instr */
269 /* to hold the increment in pc value. */
270 Dwarf_Addr adv_pc = 0;
271
272 Dwarf_Half address_size = (cie)? cie->ci_address_size:
273 dbg->de_pointer_size;
274
275 /* Counts the number of frame instructions executed. */
276 Dwarf_Unsigned instr_count = 0;
277
278 /* These contain the current fields of the current frame
279 instruction. */
280 Dwarf_Small fp_base_op = 0;
281 Dwarf_Small fp_extended_op = 0;
282 reg_num_type fp_register = 0;
283
284 /* The value in fp_offset may be signed, though we call it
285 unsigned. This works ok for 2-s complement arithmetic. */
286 Dwarf_Unsigned fp_offset = 0;
287 Dwarf_Off fp_instr_offset = 0;
288
289 /* Stack_table points to the row (Dwarf_Frame ie) being pushed or
290 popped by a remember or restore instruction. Top_stack points to
291 the top of the stack of rows. */
292 Dwarf_Frame stack_table = NULL;
293 Dwarf_Frame top_stack = NULL;
294
295 /* These are used only when make_instr is true. Curr_instr is a
296 pointer to the current frame instruction executed.
297 Curr_instr_ptr, head_instr_list, and curr_instr_list are used to
298 form a chain of Dwarf_Frame_Op structs. Dealloc_instr_ptr is
299 used to deallocate the structs used to form the chain.
300 Head_instr_block points to a contiguous list of pointers to the
301 Dwarf_Frame_Op structs executed. */
302 Dwarf_Frame_Op *curr_instr = 0;
303 Dwarf_Chain curr_instr_item = 0;
304 Dwarf_Chain head_instr_chain = NULL;
305 Dwarf_Chain tail_instr_chain = NULL;
306 Dwarf_Frame_Op *head_instr_block = 0;
307
308 /* These are the alignment_factors taken from the Cie provided.
309 When no input Cie is provided they are set to 1, because only
310 factored offsets are required. */
311 Dwarf_Signed code_alignment_factor = 1;
312 Dwarf_Signed data_alignment_factor = 1;
313
314 /* This flag indicates when an actual alignment factor is needed.
315 So if a frame instruction that computes an offset using an
316 alignment factor is encountered when this flag is set, an error
317 is returned because the Cie did not have a valid augmentation. */
318 Dwarf_Bool need_augmentation = false;
319
320 Dwarf_Unsigned i = 0;
321
322 /* Initialize first row from associated Cie. Using temp regs
323 explicity */
324
325 if (localregtab == 0) {
326 SIMPLE_ERROR_RETURN(DW_DLE_ALLOC_FAIL);
327 }
328 {
329 struct Dwarf_Reg_Rule_s *t1reg = localregtab;
330 if (cie != NULL && cie->ci_initial_table != NULL) {
331 unsigned minregcount = 0;
332 unsigned curreg = 0;
333 struct Dwarf_Reg_Rule_s *t2reg = cie->ci_initial_table->fr_reg;
334
335 if (reg_count != cie->ci_initial_table->fr_reg_count) {
336 /* Should never happen, it makes no sense to have the
337 table sizes change. There is no real allowance for
338 the set of registers to change dynamically in a
339 single Dwarf_Debug (except the size can be set near
340 initial Dwarf_Debug creation time). */
341 SIMPLE_ERROR_RETURN
342 (DW_DLE_FRAME_REGISTER_COUNT_MISMATCH);
343 }
344 minregcount = MIN(reg_count,cie->ci_initial_table->fr_reg_count);
345 for (; curreg < minregcount ;curreg++, t1reg++, t2reg++) {
346 *t1reg = *t2reg;
347 }
348 cfa_reg = cie->ci_initial_table->fr_cfa_rule;
349 } else {
350 dwarf_init_reg_rules_ru(localregtab,0,reg_count,
351 dbg->de_frame_rule_initial_value);
352 dwarf_init_reg_rules_ru(&cfa_reg,0, 1,
353 dbg->de_frame_rule_initial_value);
354 }
355 }
356
357 /* The idea here is that the code_alignment_factor and
358 data_alignment_factor which are needed for certain instructions
359 are valid only when the Cie has a proper augmentation string. So
360 if the augmentation is not right, only Frame instruction can be
361 read. */
362 if (cie != NULL && cie->ci_augmentation != NULL) {
363 code_alignment_factor = cie->ci_code_alignment_factor;
364 data_alignment_factor = cie->ci_data_alignment_factor;
365 } else {
366 need_augmentation = !make_instr;
367 }
368 instr_ptr = start_instr_ptr;
369 while ((instr_ptr < final_instr_ptr) && (!search_over)) {
370 Dwarf_Small instr = 0;
371 Dwarf_Small opcode = 0;
372 reg_num_type reg_no = 0;
373
374 fp_instr_offset = instr_ptr - start_instr_ptr;
375 instr = *(Dwarf_Small *) instr_ptr;
376 instr_ptr += sizeof(Dwarf_Small);
377
378 fp_base_op = (instr & 0xc0) >> 6;
379 if ((instr & 0xc0) == 0x00) {
380 opcode = instr; /* is really extended op */
381 fp_extended_op = (instr & (~(0xc0))) & 0xff;
382 } else {
383 opcode = instr & 0xc0; /* is base op */
384 fp_extended_op = 0;
385 }
386
387 fp_register = 0;
388 fp_offset = 0;
389 switch (opcode) {
390 case DW_CFA_advance_loc:
391 {
392 /* base op */
393 fp_offset = adv_pc = instr & DW_FRAME_INSTR_OFFSET_MASK;
394
395 if (need_augmentation) {
396 SIMPLE_ERROR_RETURN(DW_DLE_DF_NO_CIE_AUGMENTATION);
397 }
398 adv_pc = adv_pc * code_alignment_factor;
399 possible_subsequent_pc = current_loc + adv_pc;
400 search_over = search_pc &&
401 (possible_subsequent_pc > search_pc_val);
402 /* If gone past pc needed, retain old pc. */
403 if (!search_over) {
404 current_loc = possible_subsequent_pc;
405 }
406 break;
407 }
408
409 case DW_CFA_offset:
410 { /* base op */
411 reg_no =
412 (reg_num_type) (instr & DW_FRAME_INSTR_OFFSET_MASK);
413 ERROR_IF_REG_NUM_TOO_HIGH(reg_no, reg_count);
414
415 DECODE_LEB128_UWORD_CK(instr_ptr, factored_N_value,
416 dbg,error,final_instr_ptr);
417
418 fp_register = reg_no;
419 fp_offset = factored_N_value;
420
421 if (need_augmentation) {
422 SIMPLE_ERROR_RETURN(DW_DLE_DF_NO_CIE_AUGMENTATION);
423 }
424
425 localregtab[reg_no].ru_is_off = 1;
426 localregtab[reg_no].ru_value_type = DW_EXPR_OFFSET;
427 localregtab[reg_no].ru_register = reg_num_of_cfa;
428 localregtab[reg_no].ru_offset_or_block_len =
429 factored_N_value * data_alignment_factor;
430
431 break;
432 }
433
434 case DW_CFA_restore:
435 { /* base op */
436 reg_no = (instr & DW_FRAME_INSTR_OFFSET_MASK);
437 ERROR_IF_REG_NUM_TOO_HIGH(reg_no, reg_count);
438
439 fp_register = reg_no;
440
441 if (cie != NULL && cie->ci_initial_table != NULL)
442 localregtab[reg_no] =
443 cie->ci_initial_table->fr_reg[reg_no];
444 else if (!make_instr) {
445 SIMPLE_ERROR_RETURN(DW_DLE_DF_MAKE_INSTR_NO_INIT);
446 }
447
448 break;
449 }
450 case DW_CFA_set_loc:
451 {
452 Dwarf_Addr new_loc = 0;
453
454 READ_UNALIGNED_CK(dbg, new_loc, Dwarf_Addr,
455 instr_ptr, address_size,
456 error,final_instr_ptr);
457 instr_ptr += address_size;
458 if (new_loc != 0 && current_loc != 0) {
459 /* Pre-relocation or before current_loc is set the
460 test comparing new_loc and current_loc makes no
461 sense. Testing for non-zero (above) is a way
462 (fallible) to check that current_loc, new_loc
463 are already relocated. */
464 if (new_loc <= current_loc) {
465 /* Within a frame, address must increase.
466 Seemingly it has not.
467 Seems to be an error. */
468 SIMPLE_ERROR_RETURN
469 (DW_DLE_DF_NEW_LOC_LESS_OLD_LOC);
470 }
471 }
472
473 search_over = search_pc && (new_loc > search_pc_val);
474
475 /* If gone past pc needed, retain old pc. */
476 possible_subsequent_pc = new_loc;
477 if (!search_over) {
478 current_loc = possible_subsequent_pc;
479 }
480 fp_offset = new_loc;
481 break;
482 }
483
484 case DW_CFA_advance_loc1:
485 {
486 READ_UNALIGNED_CK(dbg, adv_loc, Dwarf_Unsigned,
487 instr_ptr, sizeof(Dwarf_Small),
488 error,final_instr_ptr);
489 instr_ptr += sizeof(Dwarf_Small);
490 fp_offset = adv_loc;
491
492 if (need_augmentation) {
493 SIMPLE_ERROR_RETURN(DW_DLE_DF_NO_CIE_AUGMENTATION);
494 }
495 adv_loc *= code_alignment_factor;
496
497 possible_subsequent_pc = current_loc + adv_loc;
498 search_over = search_pc &&
499 (possible_subsequent_pc > search_pc_val);
500
501 /* If gone past pc needed, retain old pc. */
502 if (!search_over) {
503 current_loc = possible_subsequent_pc;
504 }
505 break;
506 }
507
508 case DW_CFA_advance_loc2:
509 {
510 READ_UNALIGNED_CK(dbg, adv_loc, Dwarf_Unsigned,
511 instr_ptr, DWARF_HALF_SIZE,
512 error,final_instr_ptr);
513 instr_ptr += DWARF_HALF_SIZE;
514 fp_offset = adv_loc;
515
516 if (need_augmentation) {
517 SIMPLE_ERROR_RETURN(DW_DLE_DF_NO_CIE_AUGMENTATION);
518 }
519 adv_loc *= code_alignment_factor;
520
521 possible_subsequent_pc = current_loc + adv_loc;
522 search_over = search_pc &&
523 (possible_subsequent_pc > search_pc_val);
524 /* If gone past pc needed, retain old pc. */
525 if (!search_over) {
526 current_loc = possible_subsequent_pc;
527 }
528 break;
529 }
530
531 case DW_CFA_advance_loc4:
532 {
533 READ_UNALIGNED_CK(dbg, adv_loc, Dwarf_Unsigned,
534 instr_ptr, DWARF_32BIT_SIZE,
535 error,final_instr_ptr);
536 instr_ptr += DWARF_32BIT_SIZE;
537 fp_offset = adv_loc;
538
539 if (need_augmentation) {
540 SIMPLE_ERROR_RETURN(DW_DLE_DF_NO_CIE_AUGMENTATION);
541 }
542 adv_loc *= code_alignment_factor;
543
544 possible_subsequent_pc = current_loc + adv_loc;
545 search_over = search_pc &&
546 (possible_subsequent_pc > search_pc_val);
547 /* If gone past pc needed, retain old pc. */
548 if (!search_over) {
549 current_loc = possible_subsequent_pc;
550 }
551 break;
552 }
553 case DW_CFA_MIPS_advance_loc8:
554 {
555 READ_UNALIGNED_CK(dbg, adv_loc, Dwarf_Unsigned,
556 instr_ptr, DWARF_64BIT_SIZE,
557 error,final_instr_ptr);
558 instr_ptr += DWARF_64BIT_SIZE;
559 fp_offset = adv_loc;
560
561 if (need_augmentation) {
562 SIMPLE_ERROR_RETURN(DW_DLE_DF_NO_CIE_AUGMENTATION);
563 }
564 adv_loc *= code_alignment_factor;
565
566 possible_subsequent_pc = current_loc + adv_loc;
567 search_over = search_pc &&
568 (possible_subsequent_pc > search_pc_val);
569 /* If gone past pc needed, retain old pc. */
570 if (!search_over) {
571 current_loc = possible_subsequent_pc;
572 }
573 break;
574 }
575
576 case DW_CFA_offset_extended:
577 {
578 Dwarf_Unsigned lreg = 0;
579
580 DECODE_LEB128_UWORD_CK(instr_ptr, lreg,
581 dbg,error,final_instr_ptr);
582 reg_no = (reg_num_type) lreg;
583 ERROR_IF_REG_NUM_TOO_HIGH(reg_no, reg_count);
584
585 DECODE_LEB128_UWORD_CK(instr_ptr, factored_N_value,
586 dbg,error,final_instr_ptr);
587
588 if (need_augmentation) {
589 SIMPLE_ERROR_RETURN(DW_DLE_DF_NO_CIE_AUGMENTATION);
590 }
591 localregtab[reg_no].ru_is_off = 1;
592 localregtab[reg_no].ru_value_type = DW_EXPR_OFFSET;
593 localregtab[reg_no].ru_register = reg_num_of_cfa;
594 localregtab[reg_no].ru_offset_or_block_len = factored_N_value *
595 data_alignment_factor;
596
597 fp_register = reg_no;
598 fp_offset = factored_N_value;
599 break;
600 }
601
602 case DW_CFA_restore_extended:
603 {
604 Dwarf_Unsigned lreg = 0;
605
606 DECODE_LEB128_UWORD_CK(instr_ptr, lreg,
607 dbg,error,final_instr_ptr);
608 reg_no = (reg_num_type) lreg;
609
610 ERROR_IF_REG_NUM_TOO_HIGH(reg_no, reg_count);
611
612 if (cie != NULL && cie->ci_initial_table != NULL) {
613 localregtab[reg_no] = cie->ci_initial_table->fr_reg[reg_no];
614 } else {
615 if (!make_instr) {
616 SIMPLE_ERROR_RETURN
617 (DW_DLE_DF_MAKE_INSTR_NO_INIT);
618 }
619 }
620
621 fp_register = reg_no;
622 break;
623 }
624
625 case DW_CFA_undefined:
626 {
627 Dwarf_Unsigned lreg = 0;
628
629 DECODE_LEB128_UWORD_CK(instr_ptr, lreg,
630 dbg,error,final_instr_ptr);
631 reg_no = (reg_num_type) lreg;
632 ERROR_IF_REG_NUM_TOO_HIGH(reg_no, reg_count);
633
634 localregtab[reg_no].ru_is_off = 0;
635 localregtab[reg_no].ru_value_type = DW_EXPR_OFFSET;
636 localregtab[reg_no].ru_register =
637 dbg->de_frame_undefined_value_number;
638 localregtab[reg_no].ru_offset_or_block_len = 0;
639
640 fp_register = reg_no;
641 break;
642 }
643
644 case DW_CFA_same_value:
645 {
646 Dwarf_Unsigned lreg = 0;
647
648 DECODE_LEB128_UWORD_CK(instr_ptr, lreg,
649 dbg,error,final_instr_ptr);
650 reg_no = (reg_num_type) lreg;
651 ERROR_IF_REG_NUM_TOO_HIGH(reg_no, reg_count);
652
653 localregtab[reg_no].ru_is_off = 0;
654 localregtab[reg_no].ru_value_type = DW_EXPR_OFFSET;
655 localregtab[reg_no].ru_register =
656 dbg->de_frame_same_value_number;
657 localregtab[reg_no].ru_offset_or_block_len = 0;
658 fp_register = reg_no;
659 break;
660 }
661
662 case DW_CFA_register:
663 {
664 Dwarf_Unsigned lreg;
665 reg_num_type reg_noA = 0;
666 reg_num_type reg_noB = 0;
667
668 DECODE_LEB128_UWORD_CK(instr_ptr, lreg,
669 dbg,error,final_instr_ptr);
670 reg_noA = (reg_num_type) lreg;
671
672 ERROR_IF_REG_NUM_TOO_HIGH(reg_noA, reg_count);
673
674 DECODE_LEB128_UWORD_CK(instr_ptr, lreg,
675 dbg,error,final_instr_ptr);
676 reg_noB = (reg_num_type) lreg;
677
678 if (reg_noB > reg_count) {
679 SIMPLE_ERROR_RETURN(DW_DLE_DF_REG_NUM_TOO_HIGH);
680 }
681
682
683 localregtab[reg_noA].ru_is_off = 0;
684 localregtab[reg_noA].ru_value_type = DW_EXPR_OFFSET;
685 localregtab[reg_noA].ru_register = reg_noB;
686 localregtab[reg_noA].ru_offset_or_block_len = 0;
687
688 fp_register = reg_noA;
689 fp_offset = reg_noB;
690 break;
691 }
692
693 case DW_CFA_remember_state:
694 {
695 stack_table = (Dwarf_Frame)
696 _dwarf_get_alloc(dbg, DW_DLA_FRAME, 1);
697 if (stack_table == NULL) {
698 SIMPLE_ERROR_RETURN(DW_DLE_DF_ALLOC_FAIL);
699 }
700
701 for (i = 0; i < reg_count; i++)
702 stack_table->fr_reg[i] = localregtab[i];
703 stack_table->fr_cfa_rule = cfa_reg;
704
705 if (top_stack != NULL)
706 stack_table->fr_next = top_stack;
707 top_stack = stack_table;
708
709 break;
710 }
711
712 case DW_CFA_restore_state:
713 {
714 if (top_stack == NULL) {
715 SIMPLE_ERROR_RETURN(DW_DLE_DF_POP_EMPTY_STACK);
716 }
717 stack_table = top_stack;
718 top_stack = stack_table->fr_next;
719
720 for (i = 0; i < reg_count; i++)
721 localregtab[i] = stack_table->fr_reg[i];
722 cfa_reg = stack_table->fr_cfa_rule;
723
724 dwarf_dealloc(dbg, stack_table, DW_DLA_FRAME);
725 break;
726 }
727
728 case DW_CFA_def_cfa:
729 {
730 Dwarf_Unsigned lreg = 0;
731
732 DECODE_LEB128_UWORD_CK(instr_ptr, lreg,
733 dbg,error,final_instr_ptr);
734 reg_no = (reg_num_type) lreg;
735
736 ERROR_IF_REG_NUM_TOO_HIGH(reg_no, reg_count);
737
738 DECODE_LEB128_UWORD_CK(instr_ptr, factored_N_value,
739 dbg,error,final_instr_ptr);
740
741 if (need_augmentation) {
742 SIMPLE_ERROR_RETURN(DW_DLE_DF_NO_CIE_AUGMENTATION);
743 }
744 cfa_reg.ru_is_off = 1;
745 cfa_reg.ru_value_type = DW_EXPR_OFFSET;
746 cfa_reg.ru_register = reg_no;
747 cfa_reg.ru_offset_or_block_len = factored_N_value;
748
749 fp_register = reg_no;
750 fp_offset = factored_N_value;
751 break;
752 }
753
754 case DW_CFA_def_cfa_register:
755 {
756 Dwarf_Unsigned lreg = 0;
757
758 DECODE_LEB128_UWORD_CK(instr_ptr, lreg,
759 dbg,error,final_instr_ptr);
760 reg_no = (reg_num_type) lreg;
761 ERROR_IF_REG_NUM_TOO_HIGH(reg_no, reg_count);
762
763 cfa_reg.ru_register = reg_no;
764 /* Do NOT set ru_offset_or_block_len or ru_is_off here.
765 See dwarf2/3 spec. */
766 fp_register = reg_no;
767 break;
768 }
769
770 case DW_CFA_def_cfa_offset:
771 {
772 DECODE_LEB128_UWORD_CK(instr_ptr, factored_N_value,
773 dbg,error,final_instr_ptr);
774
775 if (need_augmentation) {
776 SIMPLE_ERROR_RETURN(DW_DLE_DF_NO_CIE_AUGMENTATION);
777 }
778 /* Do set ru_is_off here, as here factored_N_value
779 counts. */
780 cfa_reg.ru_is_off = 1;
781 cfa_reg.ru_value_type = DW_EXPR_OFFSET;
782 cfa_reg.ru_offset_or_block_len = factored_N_value;
783
784 fp_offset = factored_N_value;
785 break;
786 }
787 /* This is for Metaware with augmentation string HC
788 We do not really know what to do with it. */
789 case DW_CFA_METAWARE_info:
790 {
791 DECODE_LEB128_UWORD_CK(instr_ptr, factored_N_value,
792 dbg,error,final_instr_ptr);
793
794 /* Not really known what the value means or is. */
795 cfa_reg.ru_is_off = 1;
796 cfa_reg.ru_value_type = DW_EXPR_OFFSET;
797 cfa_reg.ru_offset_or_block_len = factored_N_value;
798
799 break;
800 }
801 case DW_CFA_nop:
802 {
803 break;
804 }
805 /* DWARF3 ops begin here. */
806 case DW_CFA_def_cfa_expression:
807 {
808 /* A single DW_FORM_block representing a dwarf
809 expression. The form block establishes the way to
810 compute the CFA. */
811 Dwarf_Unsigned block_len = 0;
812
813 DECODE_LEB128_UWORD_CK(instr_ptr, block_len,
814 dbg,error,final_instr_ptr);
815 cfa_reg.ru_is_off = 0; /* arbitrary */
816 cfa_reg.ru_value_type = DW_EXPR_EXPRESSION;
817 cfa_reg.ru_offset_or_block_len = block_len;
818 cfa_reg.ru_block = instr_ptr;
819 fp_offset = (Dwarf_Unsigned)(uintptr_t)instr_ptr;
820 instr_ptr += block_len;
821 }
822 break;
823 case DW_CFA_expression:
824 {
825 /* An unsigned leb128 value is the first operand (a
826 register number). The second operand is single
827 DW_FORM_block representing a dwarf expression. The
828 evaluator pushes the CFA on the evaluation stack
829 then evaluates the expression to compute the value
830 of the register contents. */
831 Dwarf_Unsigned lreg = 0;
832 Dwarf_Unsigned block_len = 0;
833
834 DECODE_LEB128_UWORD_CK(instr_ptr, lreg,
835 dbg,error,final_instr_ptr);
836 reg_no = (reg_num_type) lreg;
837 ERROR_IF_REG_NUM_TOO_HIGH(reg_no, reg_count);
838 DECODE_LEB128_UWORD_CK(instr_ptr, block_len,
839 dbg,error,final_instr_ptr);
840 localregtab[lreg].ru_is_off = 0; /* arbitrary */
841 localregtab[lreg].ru_value_type = DW_EXPR_EXPRESSION;
842 localregtab[lreg].ru_offset_or_block_len = block_len;
843 localregtab[lreg].ru_block = instr_ptr;
844 fp_offset = (Dwarf_Unsigned)(uintptr_t)instr_ptr;
845 fp_register = reg_no;
846 instr_ptr += block_len;
847 }
848 break;
849 case DW_CFA_offset_extended_sf:
850 {
851 /* The first operand is an unsigned leb128 register
852 number. The second is a signed factored offset.
853 Identical to DW_CFA_offset_extended except the
854 second operand is signed */
855 Dwarf_Unsigned lreg = 0;
856
857 DECODE_LEB128_UWORD_CK(instr_ptr, lreg,
858 dbg,error,final_instr_ptr);
859 reg_no = (reg_num_type) lreg;
860 ERROR_IF_REG_NUM_TOO_HIGH(reg_no, reg_count);
861
862 DECODE_LEB128_SWORD_CK(instr_ptr, signed_factored_N_value,
863 dbg,error,final_instr_ptr);
864
865 if (need_augmentation) {
866 SIMPLE_ERROR_RETURN(DW_DLE_DF_NO_CIE_AUGMENTATION);
867 }
868 localregtab[reg_no].ru_is_off = 1;
869 localregtab[reg_no].ru_value_type = DW_EXPR_OFFSET;
870 localregtab[reg_no].ru_register = reg_num_of_cfa;
871 localregtab[reg_no].ru_offset_or_block_len =
872 signed_factored_N_value * data_alignment_factor;
873
874 fp_register = reg_no;
875 fp_offset = signed_factored_N_value;
876 }
877 break;
878 case DW_CFA_def_cfa_sf:
879 {
880 /* The first operand is an unsigned leb128 register
881 number. The second is a signed leb128 factored
882 offset. Identical to DW_CFA_def_cfa except that the
883 second operand is signed and factored. */
884 Dwarf_Unsigned lreg;
885
886 DECODE_LEB128_UWORD_CK(instr_ptr, lreg,
887 dbg,error,final_instr_ptr);
888 reg_no = (reg_num_type) lreg;
889 ERROR_IF_REG_NUM_TOO_HIGH(reg_no, reg_count);
890
891 DECODE_LEB128_SWORD_CK(instr_ptr, signed_factored_N_value,
892 dbg,error,final_instr_ptr);
893
894 if (need_augmentation) {
895 SIMPLE_ERROR_RETURN(DW_DLE_DF_NO_CIE_AUGMENTATION);
896 }
897 cfa_reg.ru_is_off = 1;
898 cfa_reg.ru_value_type = DW_EXPR_OFFSET;
899 cfa_reg.ru_register = reg_no;
900 cfa_reg.ru_offset_or_block_len =
901 signed_factored_N_value * data_alignment_factor;
902
903 fp_register = reg_no;
904 fp_offset = signed_factored_N_value;
905 }
906 break;
907 case DW_CFA_def_cfa_offset_sf:
908 {
909 /* The operand is a signed leb128 operand representing
910 a factored offset. Identical to
911 DW_CFA_def_cfa_offset excep the operand is signed
912 and factored. */
913
914 DECODE_LEB128_SWORD_CK(instr_ptr, signed_factored_N_value,
915 dbg,error,final_instr_ptr);
916 if (need_augmentation) {
917 SIMPLE_ERROR_RETURN(DW_DLE_DF_NO_CIE_AUGMENTATION);
918 }
919 /* Do set ru_is_off here, as here factored_N_value
920 counts. */
921 cfa_reg.ru_is_off = 1;
922 cfa_reg.ru_value_type = DW_EXPR_OFFSET;
923 cfa_reg.ru_offset_or_block_len =
924 signed_factored_N_value * data_alignment_factor;
925
926 fp_offset = signed_factored_N_value;
927 }
928 break;
929 case DW_CFA_val_offset:
930 {
931 /* The first operand is an unsigned leb128 register
932 number. The second is a factored unsigned offset.
933 Makes the register be a val_offset(N) rule with N =
934 factored_offset*data_alignment_factor. */
935
936 Dwarf_Unsigned lreg = 0;
937
938 DECODE_LEB128_UWORD_CK(instr_ptr, lreg,
939 dbg,error,final_instr_ptr);
940 reg_no = (reg_num_type) lreg;
941
942 ERROR_IF_REG_NUM_TOO_HIGH(reg_no, reg_count);
943
944 DECODE_LEB128_UWORD_CK(instr_ptr, factored_N_value,
945 dbg,error,final_instr_ptr);
946
947 if (need_augmentation) {
948 SIMPLE_ERROR_RETURN(DW_DLE_DF_NO_CIE_AUGMENTATION);
949 }
950 /* Do set ru_is_off here, as here factored_N_value
951 counts. */
952 localregtab[reg_no].ru_is_off = 1;
953 localregtab[reg_no].ru_register = reg_num_of_cfa;
954 localregtab[reg_no].ru_value_type = DW_EXPR_VAL_OFFSET;
955 localregtab[reg_no].ru_offset_or_block_len =
956 factored_N_value * data_alignment_factor;
957
958 fp_offset = factored_N_value;
959 break;
960 }
961 case DW_CFA_val_offset_sf:
962 {
963 /* The first operand is an unsigned leb128 register
964 number. The second is a factored signed offset.
965 Makes the register be a val_offset(N) rule with N =
966 factored_offset*data_alignment_factor. */
967 Dwarf_Unsigned lreg = 0;
968
969 DECODE_LEB128_UWORD_CK(instr_ptr, lreg,
970 dbg,error,final_instr_ptr);
971 reg_no = (reg_num_type) lreg;
972
973 ERROR_IF_REG_NUM_TOO_HIGH(reg_no, reg_count);
974 DECODE_LEB128_SWORD_CK(instr_ptr, signed_factored_N_value,
975 dbg,error,final_instr_ptr);
976 if (need_augmentation) {
977 SIMPLE_ERROR_RETURN(DW_DLE_DF_NO_CIE_AUGMENTATION);
978 }
979 /* Do set ru_is_off here, as here factored_N_value
980 counts. */
981 localregtab[reg_no].ru_is_off = 1;
982 localregtab[reg_no].ru_value_type = DW_EXPR_VAL_OFFSET;
983 localregtab[reg_no].ru_offset_or_block_len =
984 signed_factored_N_value * data_alignment_factor;
985
986 fp_offset = signed_factored_N_value;
987
988 }
989 break;
990 case DW_CFA_val_expression:
991 {
992 /* The first operand is an unsigned leb128 register
993 number. The second is a DW_FORM_block representing a
994 DWARF expression. The rule for the register number
995 becomes a val_expression(E) rule. */
996 Dwarf_Unsigned lreg = 0;
997 Dwarf_Unsigned block_len = 0;
998
999 DECODE_LEB128_UWORD_CK(instr_ptr, lreg,
1000 dbg,error,final_instr_ptr);
1001 reg_no = (reg_num_type) lreg;
1002 ERROR_IF_REG_NUM_TOO_HIGH(reg_no, reg_count);
1003 DECODE_LEB128_UWORD_CK(instr_ptr, block_len,
1004 dbg,error,final_instr_ptr);
1005 localregtab[lreg].ru_is_off = 0; /* arbitrary */
1006 localregtab[lreg].ru_value_type = DW_EXPR_VAL_EXPRESSION;
1007 localregtab[lreg].ru_offset_or_block_len = block_len;
1008 localregtab[lreg].ru_block = instr_ptr;
1009 fp_offset = (Dwarf_Unsigned)(uintptr_t)instr_ptr;
1010
1011 instr_ptr += block_len;
1012 fp_register = reg_no;
1013
1014 }
1015 break;
1016
1017 /* END DWARF3 new ops. */
1018
1019
1020 #ifdef DW_CFA_GNU_window_save
1021 case DW_CFA_GNU_window_save:
1022 {
1023 /* No information: this just tells unwinder to restore
1024 the window registers from the previous frame's
1025 window save area */
1026 break;
1027 }
1028 #endif
1029 #ifdef DW_CFA_GNU_args_size
1030 /* Single uleb128 is the current arg area size in bytes. No
1031 register exists yet to save this in */
1032 case DW_CFA_GNU_args_size:
1033 {
1034 UNUSEDARG Dwarf_Unsigned lreg = 0;
1035
1036 DECODE_LEB128_UWORD_CK(instr_ptr, lreg,
1037 dbg,error,final_instr_ptr);
1038 /* We have nowhere to store lreg.
1039 FIXME
1040 This is the total size of arguments pushed on
1041 the stack.
1042 https://refspecs.linuxfoundation.org/LSB_3.0.0/LSB-PDA/LSB-PDA.junk/dwarfext.html
1043 */
1044
1045 break;
1046 }
1047 #endif
1048 default:
1049 /* ERROR, we have an opcode we know nothing about. Memory
1050 leak here, but an error like this is not supposed to
1051 happen so we ignore the leak. These used to be ignored,
1052 now we notice and report. */
1053 SIMPLE_ERROR_RETURN(DW_DLE_DF_FRAME_DECODING_ERROR);
1054
1055 }
1056
1057 if (make_instr) {
1058 instr_count++;
1059
1060 curr_instr = (Dwarf_Frame_Op *)
1061 _dwarf_get_alloc(dbg, DW_DLA_FRAME_OP, 1);
1062 if (curr_instr == NULL) {
1063 SIMPLE_ERROR_RETURN(DW_DLE_DF_ALLOC_FAIL);
1064 }
1065
1066 curr_instr->fp_base_op = fp_base_op;
1067 curr_instr->fp_extended_op = fp_extended_op;
1068 curr_instr->fp_register = fp_register;
1069 curr_instr->fp_offset = fp_offset;
1070 curr_instr->fp_instr_offset = fp_instr_offset;
1071
1072 curr_instr_item = (Dwarf_Chain)
1073 _dwarf_get_alloc(dbg, DW_DLA_CHAIN, 1);
1074 if (curr_instr_item == NULL) {
1075 SIMPLE_ERROR_RETURN(DW_DLE_DF_ALLOC_FAIL);
1076 }
1077
1078 curr_instr_item->ch_item = curr_instr;
1079 curr_instr_item->ch_itemtype = DW_DLA_FRAME_OP;
1080 if (head_instr_chain == NULL)
1081 head_instr_chain = tail_instr_chain = curr_instr_item;
1082 else {
1083 tail_instr_chain->ch_next = curr_instr_item;
1084 tail_instr_chain = curr_instr_item;
1085 }
1086 }
1087 }
1088
1089 /* If frame instruction decoding was right we would stop exactly at
1090 final_instr_ptr. */
1091 if (instr_ptr > final_instr_ptr) {
1092 SIMPLE_ERROR_RETURN(DW_DLE_DF_FRAME_DECODING_ERROR);
1093 }
1094 /* If search_over is set the last instr was an advance_loc
1095 so we are not done with rows. */
1096 if ((instr_ptr == final_instr_ptr) && !search_over) {
1097 if (has_more_rows) {
1098 *has_more_rows = false;
1099 }
1100 if (subsequent_pc) {
1101 *subsequent_pc = 0;
1102 }
1103 } else {
1104 if (has_more_rows) {
1105 *has_more_rows = true;
1106 }
1107 if (subsequent_pc) {
1108 *subsequent_pc = possible_subsequent_pc;
1109 }
1110 }
1111
1112 /* Fill in the actual output table, the space the caller passed in. */
1113 if (table != NULL) {
1114
1115 struct Dwarf_Reg_Rule_s *t2reg = table->fr_reg;
1116 struct Dwarf_Reg_Rule_s *t3reg = localregtab;
1117 unsigned minregcount = MIN(table->fr_reg_count,reg_count);
1118 unsigned curreg = 0;
1119
1120 table->fr_loc = current_loc;
1121 for (; curreg < minregcount ; curreg++, t3reg++, t2reg++) {
1122 *t2reg = *t3reg;
1123 }
1124
1125 /* CONSTCOND */
1126 /* Do not update the main table with the cfa_reg.
1127 Just leave cfa_reg as cfa_reg. */
1128 table->fr_cfa_rule = cfa_reg;
1129 }
1130
1131 /* Dealloc anything remaining on stack. */
1132 for (; top_stack != NULL;) {
1133 stack_table = top_stack;
1134 top_stack = top_stack->fr_next;
1135 dwarf_dealloc(dbg, stack_table, DW_DLA_FRAME);
1136 }
1137
1138 if (make_instr) {
1139 /* Allocate array of Dwarf_Frame_Op structs. */
1140 head_instr_block = (Dwarf_Frame_Op *)
1141 _dwarf_get_alloc(dbg, DW_DLA_FRAME_BLOCK, instr_count);
1142 if (head_instr_block == NULL) {
1143 SIMPLE_ERROR_RETURN(DW_DLE_DF_ALLOC_FAIL);
1144 }
1145
1146 /* Store Dwarf_Frame_Op instances in this array and
1147 deallocate the structs that chain the Dwarf_Frame_Op's. */
1148 curr_instr_item = head_instr_chain;
1149 for (i = 0; i < instr_count; i++) {
1150 void *item = curr_instr_item->ch_item;
1151 int itemtype = curr_instr_item->ch_itemtype;
1152 Dwarf_Chain prev_instr = 0;
1153
1154 /* This copies the structs, not pointers */
1155 *(head_instr_block + i) = *(Dwarf_Frame_Op *)item;
1156 prev_instr = curr_instr_item;
1157 curr_instr_item = curr_instr_item->ch_next;
1158 /* Now the pointed-to are space to dealloc */
1159 dwarf_dealloc(dbg, item, itemtype);
1160 dwarf_dealloc(dbg, prev_instr, DW_DLA_CHAIN);
1161 }
1162 *ret_frame_instr = head_instr_block;
1163 *returned_count = (Dwarf_Signed) instr_count;
1164 } else {
1165 *returned_count = 0;
1166 }
1167 free(localregtab);
1168 return DW_DLV_OK;
1169 #undef ERROR_IF_REG_NUM_TOO_HIGH
1170 #undef SIMPLE_ERROR_RETURN
1171 }
1172
1173 /* Depending on version, either read the return address register
1174 as a ubyte or as an leb number.
1175 The form of this value changed for DWARF3.
1176 */
1177 int
_dwarf_get_return_address_reg(Dwarf_Small * frame_ptr,int version,Dwarf_Debug dbg,Dwarf_Byte_Ptr section_end,unsigned long * size,Dwarf_Unsigned * return_address_register,Dwarf_Error * error)1178 _dwarf_get_return_address_reg(Dwarf_Small *frame_ptr,
1179 int version,
1180 Dwarf_Debug dbg,
1181 Dwarf_Byte_Ptr section_end,
1182 unsigned long *size,
1183 Dwarf_Unsigned *return_address_register,
1184 Dwarf_Error *error)
1185 {
1186 Dwarf_Unsigned uvalue = 0;
1187 Dwarf_Unsigned leb128_length = 0;
1188
1189 if (version == 1) {
1190 if (frame_ptr >= section_end) {
1191 _dwarf_error(NULL, error, DW_DLE_DF_FRAME_DECODING_ERROR);
1192 return DW_DLV_ERROR;
1193 }
1194 *size = 1;
1195 uvalue = *(unsigned char *) frame_ptr;
1196 *return_address_register = uvalue;
1197 return DW_DLV_OK;
1198 }
1199 DECODE_LEB128_UWORD_LEN_CK(frame_ptr,uvalue,leb128_length,
1200 dbg,error,section_end);
1201 *size = leb128_length;
1202 *return_address_register = uvalue;
1203 return DW_DLV_OK;
1204 }
1205
1206
1207 /* Trivial consumer function.
1208 */
1209 int
dwarf_get_cie_of_fde(Dwarf_Fde fde,Dwarf_Cie * cie_returned,Dwarf_Error * error)1210 dwarf_get_cie_of_fde(Dwarf_Fde fde,
1211 Dwarf_Cie * cie_returned, Dwarf_Error * error)
1212 {
1213 if (fde == NULL) {
1214 _dwarf_error(NULL, error, DW_DLE_FDE_NULL);
1215 return (DW_DLV_ERROR);
1216 }
1217
1218 *cie_returned = fde->fd_cie;
1219 return DW_DLV_OK;
1220
1221 }
1222
dwarf_get_cie_index(Dwarf_Cie cie,Dwarf_Signed * indx,Dwarf_Error * error)1223 int dwarf_get_cie_index(
1224 Dwarf_Cie cie,
1225 Dwarf_Signed* indx,
1226 Dwarf_Error* error )
1227 {
1228 if (cie == NULL)
1229 {
1230 _dwarf_error(NULL, error, DW_DLE_CIE_NULL);
1231 return (DW_DLV_ERROR);
1232 }
1233
1234 *indx = cie->ci_index;
1235 return (DW_DLV_OK);
1236 }
1237
1238 /* For g++ .eh_frame fde and cie.
1239 the cie id is different as the
1240 definition of the cie_id in an fde
1241 is the distance back from the address of the
1242 value to the cie.
1243 Or 0 if this is a true cie.
1244 Non standard dwarf, designed this way to be
1245 convenient at run time for an allocated
1246 (mapped into memory as part of the running image) section.
1247 */
1248 int
dwarf_get_fde_list_eh(Dwarf_Debug dbg,Dwarf_Cie ** cie_data,Dwarf_Signed * cie_element_count,Dwarf_Fde ** fde_data,Dwarf_Signed * fde_element_count,Dwarf_Error * error)1249 dwarf_get_fde_list_eh(Dwarf_Debug dbg,
1250 Dwarf_Cie ** cie_data,
1251 Dwarf_Signed * cie_element_count,
1252 Dwarf_Fde ** fde_data,
1253 Dwarf_Signed * fde_element_count,
1254 Dwarf_Error * error)
1255 {
1256 int res = _dwarf_load_section(dbg, &dbg->de_debug_frame_eh_gnu,error);
1257 if (res != DW_DLV_OK) {
1258 return res;
1259 }
1260
1261 res = _dwarf_get_fde_list_internal(dbg,
1262 cie_data,
1263 cie_element_count,
1264 fde_data,
1265 fde_element_count,
1266 dbg->de_debug_frame_eh_gnu.dss_data,
1267 dbg->de_debug_frame_eh_gnu.dss_index,
1268 dbg->de_debug_frame_eh_gnu.dss_size,
1269 /* cie_id_value */ 0,
1270 /* use_gnu_cie_calc= */ 1,
1271 error);
1272 return res;
1273 }
1274
1275
1276
1277 /* For standard dwarf .debug_frame
1278 cie_id is -1 in a cie, and
1279 is the section offset in the .debug_frame section
1280 of the cie otherwise. Standard dwarf
1281 */
1282 int
dwarf_get_fde_list(Dwarf_Debug dbg,Dwarf_Cie ** cie_data,Dwarf_Signed * cie_element_count,Dwarf_Fde ** fde_data,Dwarf_Signed * fde_element_count,Dwarf_Error * error)1283 dwarf_get_fde_list(Dwarf_Debug dbg,
1284 Dwarf_Cie ** cie_data,
1285 Dwarf_Signed * cie_element_count,
1286 Dwarf_Fde ** fde_data,
1287 Dwarf_Signed * fde_element_count,
1288 Dwarf_Error * error)
1289 {
1290 int res = _dwarf_load_section(dbg, &dbg->de_debug_frame,error);
1291 if (res != DW_DLV_OK) {
1292 return res;
1293 }
1294
1295 res = _dwarf_get_fde_list_internal(dbg, cie_data,
1296 cie_element_count,
1297 fde_data,
1298 fde_element_count,
1299 dbg->de_debug_frame.dss_data,
1300 dbg->de_debug_frame.dss_index,
1301 dbg->de_debug_frame.dss_size,
1302 DW_CIE_ID,
1303 /* use_gnu_cie_calc= */ 0,
1304 error);
1305 return res;
1306 }
1307
1308
1309 /* Only works on dwarf sections, not eh_frame
1310 because based on DW_AT_MIPS_fde.
1311 Given a Dwarf_Die, see if it has a
1312 DW_AT_MIPS_fde attribute and if so use that
1313 to get an fde offset.
1314 Then create a Dwarf_Fde to return thru the ret_fde pointer.
1315 Also creates a cie (pointed at from the Dwarf_Fde). */
1316 int
dwarf_get_fde_for_die(Dwarf_Debug dbg,Dwarf_Die die,Dwarf_Fde * ret_fde,Dwarf_Error * error)1317 dwarf_get_fde_for_die(Dwarf_Debug dbg,
1318 Dwarf_Die die,
1319 Dwarf_Fde * ret_fde, Dwarf_Error * error)
1320 {
1321 Dwarf_Attribute attr;
1322 Dwarf_Unsigned fde_offset = 0;
1323 Dwarf_Signed signdval = 0;
1324 Dwarf_Fde new_fde = 0;
1325 unsigned char *fde_ptr = 0;
1326 unsigned char *fde_start_ptr = 0;
1327 unsigned char *fde_end_ptr = 0;
1328 unsigned char *cie_ptr = 0;
1329 Dwarf_Unsigned cie_id = 0;
1330
1331 /* Fields for the current Cie being read. */
1332 int res = 0;
1333 int resattr = 0;
1334 int sdatares = 0;
1335
1336 struct cie_fde_prefix_s prefix;
1337 struct cie_fde_prefix_s prefix_c;
1338
1339 if (die == NULL) {
1340 _dwarf_error(NULL, error, DW_DLE_DIE_NULL);
1341 return (DW_DLV_ERROR);
1342 }
1343
1344 resattr = dwarf_attr(die, DW_AT_MIPS_fde, &attr, error);
1345 if (resattr != DW_DLV_OK) {
1346 return resattr;
1347 }
1348
1349 /* why is this formsdata? FIX */
1350 sdatares = dwarf_formsdata(attr, &signdval, error);
1351 if (sdatares != DW_DLV_OK) {
1352 return sdatares;
1353 }
1354
1355 res = _dwarf_load_section(dbg, &dbg->de_debug_frame,error);
1356 if (res != DW_DLV_OK) {
1357 return res;
1358 }
1359
1360 fde_offset = signdval;
1361 fde_start_ptr = dbg->de_debug_frame.dss_data;
1362 fde_ptr = fde_start_ptr + fde_offset;
1363 fde_end_ptr = fde_start_ptr + dbg->de_debug_frame.dss_size;
1364
1365
1366 /* First read in the 'common prefix' to figure out what * we are to
1367 do with this entry. */
1368 memset(&prefix_c, 0, sizeof(prefix_c));
1369 memset(&prefix, 0, sizeof(prefix));
1370 res = dwarf_read_cie_fde_prefix(dbg, fde_ptr,
1371 dbg->de_debug_frame.dss_data,
1372 dbg->de_debug_frame.dss_index,
1373 dbg->de_debug_frame.dss_size,
1374 &prefix,
1375 error);
1376 if (res == DW_DLV_ERROR) {
1377 return res;
1378 }
1379 if (res == DW_DLV_NO_ENTRY) {
1380 return res;
1381 }
1382 fde_ptr = prefix.cf_addr_after_prefix;
1383 cie_id = prefix.cf_cie_id;
1384 /* Pass NULL, not section pointer, for 3rd argument.
1385 de_debug_frame.dss_data has no eh_frame relevance. */
1386 res = dwarf_create_fde_from_after_start(dbg, &prefix,
1387 fde_start_ptr,
1388 fde_ptr,
1389 fde_end_ptr,
1390 /* use_gnu_cie_calc= */ 0,
1391 /* Dwarf_Cie = */ 0,
1392 &new_fde, error);
1393 if (res == DW_DLV_ERROR) {
1394 return res;
1395 } else if (res == DW_DLV_NO_ENTRY) {
1396 return res;
1397 }
1398 /* DW_DLV_OK */
1399
1400 /* now read the cie corresponding to the fde */
1401 cie_ptr = new_fde->fd_section_ptr + cie_id;
1402 res = dwarf_read_cie_fde_prefix(dbg, cie_ptr,
1403 dbg->de_debug_frame.dss_data,
1404 dbg->de_debug_frame.dss_index,
1405 dbg->de_debug_frame.dss_size,
1406 &prefix_c, error);
1407 if (res == DW_DLV_ERROR) {
1408 return res;
1409 }
1410 if (res == DW_DLV_NO_ENTRY)
1411 return res;
1412
1413 cie_ptr = prefix_c.cf_addr_after_prefix;
1414 cie_id = prefix_c.cf_cie_id;
1415
1416 if (cie_id == (Dwarf_Unsigned)DW_CIE_ID) {
1417 int res2 = 0;
1418 Dwarf_Cie new_cie = 0;
1419
1420 /* Pass NULL, not section pointer, for 3rd argument.
1421 de_debug_frame.dss_data has no eh_frame relevance. */
1422 res2 = dwarf_create_cie_from_after_start(dbg,
1423 &prefix_c,
1424 fde_start_ptr,
1425 cie_ptr,
1426 fde_end_ptr,
1427 /* cie_count= */ 0,
1428 /* use_gnu_cie_calc= */
1429 0, &new_cie, error);
1430 if (res2 == DW_DLV_ERROR) {
1431 dwarf_dealloc(dbg, new_fde, DW_DLA_FDE);
1432 return res;
1433 } else if (res2 == DW_DLV_NO_ENTRY) {
1434 dwarf_dealloc(dbg, new_fde, DW_DLA_FDE);
1435 return res;
1436 }
1437 new_fde->fd_cie = new_cie;
1438 } else {
1439 _dwarf_error(dbg, error, DW_DLE_NO_CIE_FOR_FDE);
1440 return (DW_DLV_ERROR);
1441 }
1442
1443 *ret_fde = new_fde;
1444 return DW_DLV_OK;
1445 }
1446
1447 /* A dwarf consumer operation, see the consumer library documentation.
1448 */
1449 int
dwarf_get_fde_range(Dwarf_Fde fde,Dwarf_Addr * low_pc,Dwarf_Unsigned * func_length,Dwarf_Ptr * fde_bytes,Dwarf_Unsigned * fde_byte_length,Dwarf_Off * cie_offset,Dwarf_Signed * cie_index,Dwarf_Off * fde_offset,Dwarf_Error * error)1450 dwarf_get_fde_range(Dwarf_Fde fde,
1451 Dwarf_Addr * low_pc,
1452 Dwarf_Unsigned * func_length,
1453 Dwarf_Ptr * fde_bytes,
1454 Dwarf_Unsigned * fde_byte_length,
1455 Dwarf_Off * cie_offset,
1456 Dwarf_Signed * cie_index,
1457 Dwarf_Off * fde_offset, Dwarf_Error * error)
1458 {
1459 Dwarf_Debug dbg;
1460
1461 if (fde == NULL) {
1462 _dwarf_error(NULL, error, DW_DLE_FDE_NULL);
1463 return (DW_DLV_ERROR);
1464 }
1465
1466 dbg = fde->fd_dbg;
1467 if (dbg == NULL) {
1468 _dwarf_error(NULL, error, DW_DLE_FDE_DBG_NULL);
1469 return (DW_DLV_ERROR);
1470 }
1471
1472
1473 /* We have always already done the section load here, so no need to
1474 load the section. We did the section load in order to create the
1475 Dwarf_Fde pointer passed in here. */
1476
1477
1478 if (low_pc != NULL)
1479 *low_pc = fde->fd_initial_location;
1480 if (func_length != NULL)
1481 *func_length = fde->fd_address_range;
1482 if (fde_bytes != NULL)
1483 *fde_bytes = fde->fd_fde_start;
1484 if (fde_byte_length != NULL)
1485 *fde_byte_length = fde->fd_length;
1486 if (cie_offset != NULL)
1487 *cie_offset = fde->fd_cie_offset;
1488 if (cie_index != NULL)
1489 *cie_index = fde->fd_cie_index;
1490 if (fde_offset != NULL)
1491 *fde_offset = fde->fd_fde_start - fde->fd_section_ptr;
1492
1493 return DW_DLV_OK;
1494 }
1495
1496 /* IRIX specific function. The exception tables
1497 have C++ destructor information and are
1498 at present undocumented. */
1499 int
dwarf_get_fde_exception_info(Dwarf_Fde fde,Dwarf_Signed * offset_into_exception_tables,Dwarf_Error * error)1500 dwarf_get_fde_exception_info(Dwarf_Fde fde,
1501 Dwarf_Signed *
1502 offset_into_exception_tables,
1503 Dwarf_Error * error)
1504 {
1505 Dwarf_Debug dbg;
1506
1507 dbg = fde->fd_dbg;
1508 if (dbg == NULL) {
1509 _dwarf_error(NULL, error, DW_DLE_FDE_DBG_NULL);
1510 return (DW_DLV_ERROR);
1511 }
1512 *offset_into_exception_tables =
1513 fde->fd_offset_into_exception_tables;
1514 return DW_DLV_OK;
1515 }
1516
1517
1518
1519 /* A consumer code function.
1520 Given a CIE pointer, return the normal CIE data thru
1521 pointers.
1522 Special augmentation data is not returned here.
1523 */
1524 int
dwarf_get_cie_info(Dwarf_Cie cie,Dwarf_Unsigned * bytes_in_cie,Dwarf_Small * ptr_to_version,char ** augmenter,Dwarf_Unsigned * code_alignment_factor,Dwarf_Signed * data_alignment_factor,Dwarf_Half * return_address_register,Dwarf_Ptr * initial_instructions,Dwarf_Unsigned * initial_instructions_length,Dwarf_Error * error)1525 dwarf_get_cie_info(Dwarf_Cie cie,
1526 Dwarf_Unsigned * bytes_in_cie,
1527 Dwarf_Small * ptr_to_version,
1528 char **augmenter,
1529 Dwarf_Unsigned * code_alignment_factor,
1530 Dwarf_Signed * data_alignment_factor,
1531 Dwarf_Half * return_address_register,
1532 Dwarf_Ptr * initial_instructions,
1533 Dwarf_Unsigned * initial_instructions_length,
1534 Dwarf_Error * error)
1535 {
1536 Dwarf_Half offset_size = 0;
1537 return dwarf_get_cie_info_b(cie,
1538 bytes_in_cie,
1539 ptr_to_version,
1540 augmenter,
1541 code_alignment_factor,
1542 data_alignment_factor,
1543 return_address_register,
1544 initial_instructions,
1545 initial_instructions_length,
1546 &offset_size,
1547 error);
1548 }
1549 int
dwarf_get_cie_info_b(Dwarf_Cie cie,Dwarf_Unsigned * bytes_in_cie,Dwarf_Small * ptr_to_version,char ** augmenter,Dwarf_Unsigned * code_alignment_factor,Dwarf_Signed * data_alignment_factor,Dwarf_Half * return_address_register,Dwarf_Ptr * initial_instructions,Dwarf_Unsigned * initial_instructions_length,Dwarf_Half * offset_size,Dwarf_Error * error)1550 dwarf_get_cie_info_b(Dwarf_Cie cie,
1551 Dwarf_Unsigned * bytes_in_cie,
1552 Dwarf_Small * ptr_to_version,
1553 char **augmenter,
1554 Dwarf_Unsigned * code_alignment_factor,
1555 Dwarf_Signed * data_alignment_factor,
1556 Dwarf_Half * return_address_register,
1557 Dwarf_Ptr * initial_instructions,
1558 Dwarf_Unsigned * initial_instructions_length,
1559 Dwarf_Half * offset_size,
1560 Dwarf_Error * error)
1561 {
1562 Dwarf_Debug dbg = 0;
1563
1564 if (cie == NULL) {
1565 _dwarf_error(NULL, error, DW_DLE_CIE_NULL);
1566 return (DW_DLV_ERROR);
1567 }
1568
1569 dbg = cie->ci_dbg;
1570 if (dbg == NULL) {
1571 _dwarf_error(NULL, error, DW_DLE_CIE_DBG_NULL);
1572 return (DW_DLV_ERROR);
1573 }
1574
1575 if (ptr_to_version != NULL)
1576 *ptr_to_version = cie->ci_cie_version_number;
1577 if (augmenter != NULL)
1578 *augmenter = cie->ci_augmentation;
1579 if (code_alignment_factor != NULL)
1580 *code_alignment_factor = cie->ci_code_alignment_factor;
1581 if (data_alignment_factor != NULL)
1582 *data_alignment_factor = cie->ci_data_alignment_factor;
1583 if (return_address_register != NULL)
1584 *return_address_register = cie->ci_return_address_register;
1585 if (initial_instructions != NULL)
1586 *initial_instructions = cie->ci_cie_instr_start;
1587 if (initial_instructions_length != NULL) {
1588 *initial_instructions_length = cie->ci_length +
1589 cie->ci_length_size +
1590 cie->ci_extension_size -
1591 (cie->ci_cie_instr_start - cie->ci_cie_start);
1592 }
1593 if (offset_size) {
1594 *offset_size = cie->ci_length_size;
1595 }
1596 *bytes_in_cie = (cie->ci_length);
1597 return (DW_DLV_OK);
1598 }
1599
1600 /* Return the register rules for all registers at a given pc.
1601 */
1602 static int
_dwarf_get_fde_info_for_a_pc_row(Dwarf_Fde fde,Dwarf_Addr pc_requested,Dwarf_Frame table,Dwarf_Half cfa_reg_col_num,Dwarf_Bool * has_more_rows,Dwarf_Addr * subsequent_pc,Dwarf_Error * error)1603 _dwarf_get_fde_info_for_a_pc_row(Dwarf_Fde fde,
1604 Dwarf_Addr pc_requested,
1605 Dwarf_Frame table,
1606 Dwarf_Half cfa_reg_col_num,
1607 Dwarf_Bool * has_more_rows,
1608 Dwarf_Addr * subsequent_pc,
1609 Dwarf_Error * error)
1610 {
1611 Dwarf_Debug dbg = 0;
1612 Dwarf_Cie cie = 0;
1613 Dwarf_Signed icount = 0;
1614 int res = 0;
1615
1616 if (fde == NULL) {
1617 _dwarf_error(NULL, error, DW_DLE_FDE_NULL);
1618 return DW_DLV_ERROR;
1619 }
1620
1621 dbg = fde->fd_dbg;
1622 if (dbg == NULL) {
1623 _dwarf_error(NULL, error, DW_DLE_FDE_DBG_NULL);
1624 return DW_DLV_ERROR;
1625 }
1626
1627 if (pc_requested < fde->fd_initial_location ||
1628 pc_requested >=
1629 fde->fd_initial_location + fde->fd_address_range) {
1630 _dwarf_error(dbg, error, DW_DLE_PC_NOT_IN_FDE_RANGE);
1631 return DW_DLV_ERROR;
1632 }
1633
1634 cie = fde->fd_cie;
1635 if (cie->ci_initial_table == NULL) {
1636 Dwarf_Small *instrstart = cie->ci_cie_instr_start;
1637 Dwarf_Small *instrend = instrstart +cie->ci_length +
1638 cie->ci_length_size +
1639 cie->ci_extension_size -
1640 (cie->ci_cie_instr_start -
1641 cie->ci_cie_start);
1642
1643 if (instrend > cie->ci_cie_end) {
1644 _dwarf_error(dbg, error,DW_DLE_CIE_INSTR_PTR_ERROR);
1645 return DW_DLV_ERROR;
1646 }
1647 cie->ci_initial_table = (Dwarf_Frame)_dwarf_get_alloc(dbg, DW_DLA_FRAME, 1);
1648
1649 if (cie->ci_initial_table == NULL) {
1650 _dwarf_error(dbg, error, DW_DLE_ALLOC_FAIL);
1651 return DW_DLV_ERROR;
1652 }
1653 dwarf_init_reg_rules_ru(cie->ci_initial_table->fr_reg,
1654 0, cie->ci_initial_table->fr_reg_count,
1655 dbg->de_frame_rule_initial_value);
1656 dwarf_init_reg_rules_ru(&cie->ci_initial_table->fr_cfa_rule,
1657 0,1,dbg->de_frame_rule_initial_value);
1658 res = _dwarf_exec_frame_instr( /* make_instr= */ false,
1659 /* ret_frame_instr= */ NULL,
1660 /* search_pc */ false,
1661 /* search_pc_val */ 0,
1662 /* location */ 0,
1663 instrstart,
1664 instrend,
1665 cie->ci_initial_table, cie, dbg,
1666 cfa_reg_col_num, &icount,
1667 NULL,NULL,
1668 error);
1669 if (res != DW_DLV_OK) {
1670 return res;
1671 }
1672 }
1673
1674 {
1675 Dwarf_Small *instr_end = fde->fd_fde_instr_start +
1676 fde->fd_length +
1677 fde->fd_length_size +
1678 fde->fd_extension_size - (fde->fd_fde_instr_start -
1679 fde->fd_fde_start);
1680 if (instr_end > fde->fd_fde_end) {
1681 _dwarf_error(dbg, error,DW_DLE_FDE_INSTR_PTR_ERROR);
1682 return DW_DLV_ERROR;
1683 }
1684
1685 res = _dwarf_exec_frame_instr( /* make_instr= */ false,
1686 /* ret_frame_instr= */ NULL,
1687 /* search_pc */ true,
1688 /* search_pc_val */ pc_requested,
1689 fde->fd_initial_location,
1690 fde->fd_fde_instr_start,
1691 instr_end,
1692 table,
1693 cie, dbg,
1694 cfa_reg_col_num, &icount,
1695 has_more_rows,
1696 subsequent_pc,
1697 error);
1698 }
1699 if (res != DW_DLV_OK) {
1700 return res;
1701 }
1702
1703 return DW_DLV_OK;
1704 }
1705
1706 /* A consumer call for efficiently getting the register info
1707 for all registers in one call.
1708
1709 The output table rules array is size DW_REG_TABLE_SIZE.
1710 The frame info rules array in fde_table is of size
1711 DW_REG_TABLE_SIZE too.
1712
1713 This interface really only works well with MIPS/IRIX
1714 where DW_FRAME_CFA_COL is zero (in that case it's safe).
1715
1716 It is also restricted to the case where
1717 DW_REG_TABLE_SIZE == DW_FRAME_LAST_REG_NUM ==
1718 dbg->de_frame_reg_rules_entry_count (true for MIPS/IRIX).
1719 If this condition is not met calling this routine can result in
1720 incorrect output or in memory corruption.
1721
1722 It is much better to use dwarf_get_fde_info_for_all_regs3()
1723 instead of this interface.
1724 */
1725 int
dwarf_get_fde_info_for_all_regs(Dwarf_Fde fde,Dwarf_Addr pc_requested,Dwarf_Regtable * reg_table,Dwarf_Addr * row_pc,Dwarf_Error * error)1726 dwarf_get_fde_info_for_all_regs(Dwarf_Fde fde,
1727 Dwarf_Addr pc_requested,
1728 Dwarf_Regtable * reg_table,
1729 Dwarf_Addr * row_pc,
1730 Dwarf_Error * error)
1731 {
1732
1733 /* Table size: DW_REG_TABLE_SIZE */
1734 struct Dwarf_Frame_s fde_table;
1735 Dwarf_Signed i = 0;
1736 struct Dwarf_Reg_Rule_s *rule = NULL;
1737 struct Dwarf_Regtable_Entry_s *out_rule = NULL;
1738 int res = 0;
1739 Dwarf_Debug dbg = 0;
1740
1741 /* For this interface the size is fixed at compile time. */
1742 int output_table_real_data_size = DW_REG_TABLE_SIZE;
1743
1744 FDE_NULL_CHECKS_AND_SET_DBG(fde, dbg);
1745
1746 res = dwarf_initialize_fde_table(dbg, &fde_table,
1747 output_table_real_data_size,
1748 error);
1749 if (res != DW_DLV_OK)
1750 return res;
1751
1752 /* _dwarf_get_fde_info_for_a_pc_row will perform more sanity checks
1753 */
1754 res = _dwarf_get_fde_info_for_a_pc_row(fde, pc_requested,
1755 &fde_table, dbg->de_frame_cfa_col_number,NULL,NULL, error);
1756 if (res != DW_DLV_OK) {
1757 dwarf_free_fde_table(&fde_table);
1758 return res;
1759 }
1760
1761 out_rule = ®_table->rules[0];
1762 rule = &fde_table.fr_reg[0];
1763 for (i = 0; i < output_table_real_data_size;
1764 i++, ++out_rule, ++rule) {
1765 out_rule->dw_offset_relevant = rule->ru_is_off;
1766 out_rule->dw_value_type = rule->ru_value_type;
1767 out_rule->dw_regnum = rule->ru_register;
1768 out_rule->dw_offset = rule->ru_offset_or_block_len;
1769 }
1770 dwarf_init_reg_rules_dw(®_table->rules[0],i,DW_REG_TABLE_SIZE,
1771 dbg->de_frame_undefined_value_number);
1772
1773 /* The test is just in case it's not inside the table. For non-MIPS
1774 it could be outside the table and that is just fine, it was
1775 really a mistake to put it in the table in 1993. */
1776 /* CONSTCOND */
1777 if (dbg->de_frame_cfa_col_number < DW_REG_TABLE_SIZE) {
1778 out_rule = ®_table->rules[dbg->de_frame_cfa_col_number];
1779 out_rule->dw_offset_relevant = fde_table.fr_cfa_rule.ru_is_off;
1780 out_rule->dw_value_type = fde_table.fr_cfa_rule.ru_value_type;
1781 out_rule->dw_regnum = fde_table.fr_cfa_rule.ru_register;
1782 out_rule->dw_offset =
1783 fde_table.fr_cfa_rule.ru_offset_or_block_len;
1784 }
1785
1786 if (row_pc != NULL)
1787 *row_pc = fde_table.fr_loc;
1788 dwarf_free_fde_table(&fde_table);
1789 return DW_DLV_OK;
1790 }
1791
1792 /* A consumer call for efficiently getting the register info
1793 for all registers in one call.
1794
1795 The output table rules array is size output_table_real_data_size.
1796 (normally DW_REG_TABLE_SIZE).
1797 The frame info rules array in fde_table is normally of size
1798 DW_FRAME_LAST_REG_NUM. */
1799 int
dwarf_get_fde_info_for_all_regs3(Dwarf_Fde fde,Dwarf_Addr pc_requested,Dwarf_Regtable3 * reg_table,Dwarf_Addr * row_pc,Dwarf_Error * error)1800 dwarf_get_fde_info_for_all_regs3(Dwarf_Fde fde,
1801 Dwarf_Addr pc_requested,
1802 Dwarf_Regtable3 * reg_table,
1803 Dwarf_Addr * row_pc,
1804 Dwarf_Error * error)
1805 {
1806
1807 struct Dwarf_Frame_s fde_table;
1808 Dwarf_Signed i = 0;
1809 int res = 0;
1810 struct Dwarf_Reg_Rule_s *rule = NULL;
1811 struct Dwarf_Regtable_Entry3_s *out_rule = NULL;
1812 Dwarf_Debug dbg = 0;
1813 int output_table_real_data_size = reg_table->rt3_reg_table_size;
1814
1815 FDE_NULL_CHECKS_AND_SET_DBG(fde, dbg);
1816
1817 output_table_real_data_size =
1818 MIN(output_table_real_data_size,
1819 dbg->de_frame_reg_rules_entry_count);
1820
1821 res = dwarf_initialize_fde_table(dbg, &fde_table,
1822 output_table_real_data_size,
1823 error);
1824 if (res != DW_DLV_OK) {
1825 return res;
1826 }
1827
1828 /* _dwarf_get_fde_info_for_a_pc_row will perform more sanity checks
1829 */
1830 res = _dwarf_get_fde_info_for_a_pc_row(fde, pc_requested,
1831 &fde_table,
1832 dbg->de_frame_cfa_col_number,
1833 NULL,NULL,
1834 error);
1835 if (res != DW_DLV_OK) {
1836 dwarf_free_fde_table(&fde_table);
1837 return res;
1838 }
1839
1840 out_rule = ®_table->rt3_rules[0];
1841 rule = &fde_table.fr_reg[0];
1842 for (i = 0; i < output_table_real_data_size;
1843 i++, ++out_rule, ++rule) {
1844 out_rule->dw_offset_relevant = rule->ru_is_off;
1845 out_rule->dw_value_type = rule->ru_value_type;
1846 out_rule->dw_regnum = rule->ru_register;
1847 out_rule->dw_offset_or_block_len = rule->ru_offset_or_block_len;
1848 out_rule->dw_block_ptr = rule->ru_block;
1849 }
1850 dwarf_init_reg_rules_dw3(®_table->rt3_rules[0],i,reg_table->rt3_reg_table_size,
1851 dbg->de_frame_undefined_value_number);
1852
1853 reg_table->rt3_cfa_rule.dw_offset_relevant =
1854 fde_table.fr_cfa_rule.ru_is_off;
1855 reg_table->rt3_cfa_rule.dw_value_type =
1856 fde_table.fr_cfa_rule.ru_value_type;
1857 reg_table->rt3_cfa_rule.dw_regnum =
1858 fde_table.fr_cfa_rule.ru_register;
1859 reg_table->rt3_cfa_rule.dw_offset_or_block_len =
1860 fde_table.fr_cfa_rule.ru_offset_or_block_len;
1861 reg_table->rt3_cfa_rule.dw_block_ptr =
1862 fde_table.fr_cfa_rule.ru_block;
1863
1864 if (row_pc != NULL)
1865 *row_pc = fde_table.fr_loc;
1866
1867 dwarf_free_fde_table(&fde_table);
1868 return DW_DLV_OK;
1869 }
1870
1871 /* Obsolete as of 2006.
1872 Gets the register info for a single register at a given PC value
1873 for the FDE specified.
1874
1875 This is the old MIPS interface and should no longer be used.
1876 Use dwarf_get_fde_info_for_reg3() instead.
1877 It can not handle DWARF3 or later properly as it
1878 assumes the CFA is representable as a table column. */
1879 int
dwarf_get_fde_info_for_reg(Dwarf_Fde fde,Dwarf_Half table_column,Dwarf_Addr pc_requested,Dwarf_Signed * offset_relevant,Dwarf_Signed * register_num,Dwarf_Signed * offset,Dwarf_Addr * row_pc,Dwarf_Error * error)1880 dwarf_get_fde_info_for_reg(Dwarf_Fde fde,
1881 Dwarf_Half table_column,
1882 Dwarf_Addr pc_requested,
1883 Dwarf_Signed * offset_relevant,
1884 Dwarf_Signed * register_num,
1885 Dwarf_Signed * offset,
1886 Dwarf_Addr * row_pc, Dwarf_Error * error)
1887 {
1888 struct Dwarf_Frame_s fde_table;
1889 int res = DW_DLV_ERROR;
1890 Dwarf_Debug dbg = 0;
1891 int output_table_real_data_size = 0;
1892
1893 FDE_NULL_CHECKS_AND_SET_DBG(fde, dbg);
1894 output_table_real_data_size = dbg->de_frame_reg_rules_entry_count;
1895
1896 res = dwarf_initialize_fde_table(dbg, &fde_table,
1897 output_table_real_data_size,
1898 error);
1899 if (res != DW_DLV_OK)
1900 return res;
1901
1902 if (table_column >= output_table_real_data_size) {
1903 dwarf_free_fde_table(&fde_table);
1904 _dwarf_error(dbg, error, DW_DLE_FRAME_TABLE_COL_BAD);
1905 return (DW_DLV_ERROR);
1906 }
1907
1908 /* _dwarf_get_fde_info_for_a_pc_row will perform more sanity checks
1909 */
1910 res =
1911 _dwarf_get_fde_info_for_a_pc_row(fde, pc_requested, &fde_table,
1912 dbg->de_frame_cfa_col_number,
1913 NULL,NULL,error);
1914 if (res != DW_DLV_OK) {
1915 dwarf_free_fde_table(&fde_table);
1916 return res;
1917 }
1918
1919 if (fde_table.fr_reg[table_column].ru_value_type != DW_EXPR_OFFSET) {
1920 /* The problem here is that this interface cannot deal with
1921 other sorts of (newer) dwarf frame values. Code must
1922 use dwarf_get_fde_info_for_reg3() to get these
1923 values correctly. We error rather than return
1924 misleading incomplete data. */
1925 dwarf_free_fde_table(&fde_table);
1926 _dwarf_error(NULL, error,
1927 DW_DLE_FRAME_REGISTER_UNREPRESENTABLE);
1928 return (DW_DLV_ERROR);
1929 }
1930 if (table_column == dbg->de_frame_cfa_col_number) {
1931 if (register_num != NULL)
1932 *register_num = fde_table.fr_cfa_rule.ru_register;
1933 if (offset != NULL)
1934 *offset = fde_table.fr_cfa_rule.ru_offset_or_block_len;
1935 if (row_pc != NULL)
1936 *row_pc = fde_table.fr_loc;
1937 *offset_relevant = fde_table.fr_cfa_rule.ru_is_off;
1938
1939 } else {
1940 if (register_num != NULL)
1941 *register_num = fde_table.fr_reg[table_column].ru_register;
1942 if (offset != NULL)
1943 *offset = fde_table.fr_reg[table_column].ru_offset_or_block_len;
1944 if (row_pc != NULL)
1945 *row_pc = fde_table.fr_loc;
1946
1947 *offset_relevant = fde_table.fr_reg[table_column].ru_is_off;
1948 }
1949 dwarf_free_fde_table(&fde_table);
1950 return DW_DLV_OK;
1951 }
1952
1953 /* In this interface, table_column of DW_FRAME_CFA_COL
1954 is not meaningful.
1955 Use dwarf_get_fde_info_for_cfa_reg3() to get the CFA.
1956 Call dwarf_set_frame_cfa_value() to set the correct column
1957 after calling dwarf_init()
1958 (DW_FRAME_CFA_COL3 is a sensible column to use).
1959 */
1960 int
dwarf_get_fde_info_for_reg3(Dwarf_Fde fde,Dwarf_Half table_column,Dwarf_Addr pc_requested,Dwarf_Small * value_type,Dwarf_Signed * offset_relevant,Dwarf_Signed * register_num,Dwarf_Signed * offset_or_block_len,Dwarf_Ptr * block_ptr,Dwarf_Addr * row_pc_out,Dwarf_Error * error)1961 dwarf_get_fde_info_for_reg3(Dwarf_Fde fde,
1962 Dwarf_Half table_column,
1963 Dwarf_Addr pc_requested,
1964 Dwarf_Small * value_type,
1965 Dwarf_Signed * offset_relevant,
1966 Dwarf_Signed * register_num,
1967 Dwarf_Signed * offset_or_block_len,
1968 Dwarf_Ptr * block_ptr,
1969 Dwarf_Addr * row_pc_out,
1970 Dwarf_Error * error)
1971 {
1972 int res = dwarf_get_fde_info_for_reg3_b(fde,
1973 table_column, pc_requested, value_type,
1974 offset_relevant, register_num,
1975 offset_or_block_len,
1976 block_ptr,
1977 row_pc_out,
1978 /* Not looking for the has_more_rows flag
1979 nor for the next pc in the frame data. */
1980 NULL,NULL,
1981 error);
1982 return res;
1983 }
1984
1985
1986 /* New May 2018.
1987 If one is tracking the value of a single table
1988 column through a function, this lets us
1989 skip to the next pc value easily.
1990
1991 if pc_requested is a change from the last
1992 pc_requested on this pc, this function
1993 returns *has_more_rows and *subsequent_pc
1994 (null pointers passed are acceptable, the
1995 assignment through the pointer is skipped
1996 if the pointer is null).
1997 Otherwise *has_more_rows and *subsequent_pc
1998 are not set.
1999 */
2000 int
dwarf_get_fde_info_for_reg3_b(Dwarf_Fde fde,Dwarf_Half table_column,Dwarf_Addr pc_requested,Dwarf_Small * value_type,Dwarf_Signed * offset_relevant,Dwarf_Signed * register_num,Dwarf_Signed * offset_or_block_len,Dwarf_Ptr * block_ptr,Dwarf_Addr * row_pc_out,Dwarf_Bool * has_more_rows,Dwarf_Addr * subsequent_pc,Dwarf_Error * error)2001 dwarf_get_fde_info_for_reg3_b(Dwarf_Fde fde,
2002 Dwarf_Half table_column,
2003 Dwarf_Addr pc_requested,
2004 Dwarf_Small * value_type,
2005 Dwarf_Signed * offset_relevant,
2006 Dwarf_Signed * register_num,
2007 Dwarf_Signed * offset_or_block_len,
2008 Dwarf_Ptr * block_ptr,
2009 Dwarf_Addr * row_pc_out,
2010 Dwarf_Bool * has_more_rows,
2011 Dwarf_Addr * subsequent_pc,
2012 Dwarf_Error * error)
2013 {
2014 struct Dwarf_Frame_s * fde_table = &(fde->fd_fde_table);
2015 int res = DW_DLV_ERROR;
2016
2017 Dwarf_Debug dbg = 0;
2018 int table_real_data_size = 0;
2019
2020 FDE_NULL_CHECKS_AND_SET_DBG(fde, dbg);
2021
2022 if (!fde->fd_have_fde_tab ||
2023 /* The test is just in case it's not inside the table. For non-MIPS
2024 it could be outside the table and that is just fine, it was
2025 really a mistake to put it in the table in 1993. */
2026 fde->fd_fde_pc_requested != pc_requested) {
2027 if (fde->fd_have_fde_tab) {
2028 dwarf_free_fde_table(fde_table);
2029 fde->fd_have_fde_tab = false;
2030 }
2031 table_real_data_size = dbg->de_frame_reg_rules_entry_count;
2032 res = dwarf_initialize_fde_table(dbg, fde_table,
2033 table_real_data_size, error);
2034 if (res != DW_DLV_OK) {
2035 return res;
2036 }
2037 if (table_column >= table_real_data_size) {
2038 dwarf_free_fde_table(fde_table);
2039 fde->fd_have_fde_tab = false;
2040 _dwarf_error(dbg, error, DW_DLE_FRAME_TABLE_COL_BAD);
2041 return (DW_DLV_ERROR);
2042 }
2043
2044 /* _dwarf_get_fde_info_for_a_pc_row will perform more sanity checks
2045 */
2046 res = _dwarf_get_fde_info_for_a_pc_row(fde, pc_requested, fde_table,
2047 dbg->de_frame_cfa_col_number,
2048 has_more_rows,subsequent_pc,
2049 error);
2050 if (res != DW_DLV_OK) {
2051 dwarf_free_fde_table(fde_table);
2052 fde->fd_have_fde_tab = false;
2053 return res;
2054 }
2055 }
2056
2057 if (register_num != NULL) {
2058 *register_num = fde_table->fr_reg[table_column].ru_register;
2059 }
2060 if (offset_or_block_len != NULL) {
2061 *offset_or_block_len =
2062 fde_table->fr_reg[table_column].ru_offset_or_block_len;
2063 }
2064 if (row_pc_out != NULL) {
2065 *row_pc_out = fde_table->fr_loc;
2066 }
2067 if (block_ptr) {
2068 *block_ptr = fde_table->fr_reg[table_column].ru_block;
2069 }
2070
2071 /* Without value_type the data cannot be understood, so we insist
2072 on it being present, we don't test it. */
2073 *value_type = fde_table->fr_reg[table_column].ru_value_type;
2074 *offset_relevant = (fde_table->fr_reg[table_column].ru_is_off);
2075 fde->fd_have_fde_tab = true;
2076 fde->fd_fde_pc_requested = pc_requested;
2077 return DW_DLV_OK;
2078
2079 }
2080
2081 /* New 2006.
2082 For current DWARF, this is a preferred interface.
2083
2084 Compared to dwarf_get_fde_info_for_reg()
2085 it more correctly deals with the CFA by not
2086 making the CFA a column number, which means
2087 DW_FRAME_CFA_COL3 becomes, like DW_CFA_SAME_VALUE,
2088 a special value, not something one uses as an index.
2089
2090 See also dwarf_get_fde_info_for_cfa_reg3_b(), which
2091 is slightly preferred.
2092 */
2093 int
dwarf_get_fde_info_for_cfa_reg3(Dwarf_Fde fde,Dwarf_Addr pc_requested,Dwarf_Small * value_type,Dwarf_Signed * offset_relevant,Dwarf_Signed * register_num,Dwarf_Signed * offset_or_block_len,Dwarf_Ptr * block_ptr,Dwarf_Addr * row_pc_out,Dwarf_Error * error)2094 dwarf_get_fde_info_for_cfa_reg3(Dwarf_Fde fde,
2095 Dwarf_Addr pc_requested,
2096 Dwarf_Small * value_type,
2097 Dwarf_Signed * offset_relevant,
2098 Dwarf_Signed * register_num,
2099 Dwarf_Signed * offset_or_block_len,
2100 Dwarf_Ptr * block_ptr,
2101 Dwarf_Addr * row_pc_out,
2102 Dwarf_Error * error)
2103 {
2104 Dwarf_Bool has_more_rows = 0;
2105 Dwarf_Addr next_pc = 0;
2106 int res = 0;
2107 res = dwarf_get_fde_info_for_cfa_reg3_b(fde,
2108 pc_requested,
2109 value_type,
2110 offset_relevant,
2111 register_num,
2112 offset_or_block_len,
2113 block_ptr,
2114 row_pc_out,
2115 &has_more_rows,
2116 &next_pc,
2117 error);
2118 return res;
2119 }
2120
2121 /* New June 11,2016.
2122 For current DWARF, this is a preferred interface.
2123
2124 Has extra arguments has_more_rows and next_pc
2125 (compared to dwarf_get_fde_info_for_cfa_reg3())
2126 which can be used to more efficiently traverse
2127 frame data (primarily for dwarfdump and like
2128 programs).
2129
2130 Like dwarf_get_fde_info_for_cfa_reg3() it
2131 deals with the CFA by not
2132 making the CFA a column number, which means
2133 DW_FRAME_CFA_COL3 becomes, like DW_CFA_SAME_VALUE,
2134 a special value, not something one uses as an index.
2135
2136 Call dwarf_set_frame_cfa_value() to set the correct column
2137 after calling dwarf_init()
2138 (DW_FRAME_CFA_COL3 is a sensible column to use, and
2139 is the default unless '--enable-oldframecol'
2140 is used to configure libdwarf). */
2141 int
dwarf_get_fde_info_for_cfa_reg3_b(Dwarf_Fde fde,Dwarf_Addr pc_requested,Dwarf_Small * value_type,Dwarf_Signed * offset_relevant,Dwarf_Signed * register_num,Dwarf_Signed * offset_or_block_len,Dwarf_Ptr * block_ptr,Dwarf_Addr * row_pc_out,Dwarf_Bool * has_more_rows,Dwarf_Addr * subsequent_pc,Dwarf_Error * error)2142 dwarf_get_fde_info_for_cfa_reg3_b(Dwarf_Fde fde,
2143 Dwarf_Addr pc_requested,
2144 Dwarf_Small * value_type,
2145 Dwarf_Signed * offset_relevant,
2146 Dwarf_Signed * register_num,
2147 Dwarf_Signed * offset_or_block_len,
2148 Dwarf_Ptr * block_ptr,
2149 Dwarf_Addr * row_pc_out,
2150 Dwarf_Bool * has_more_rows,
2151 Dwarf_Addr * subsequent_pc,
2152 Dwarf_Error * error)
2153 {
2154 struct Dwarf_Frame_s fde_table;
2155 int res = DW_DLV_ERROR;
2156 Dwarf_Debug dbg = 0;
2157
2158 int table_real_data_size = 0;
2159
2160 FDE_NULL_CHECKS_AND_SET_DBG(fde, dbg);
2161
2162 table_real_data_size = dbg->de_frame_reg_rules_entry_count;
2163 res = dwarf_initialize_fde_table(dbg, &fde_table,
2164 table_real_data_size, error);
2165 if (res != DW_DLV_OK)
2166 return res;
2167 res = _dwarf_get_fde_info_for_a_pc_row(fde, pc_requested,
2168 &fde_table,
2169 dbg->de_frame_cfa_col_number,has_more_rows,
2170 subsequent_pc,error);
2171 if (res != DW_DLV_OK) {
2172 dwarf_free_fde_table(&fde_table);
2173 return res;
2174 }
2175
2176 if (register_num != NULL)
2177 *register_num = fde_table.fr_cfa_rule.ru_register;
2178 if (offset_or_block_len != NULL)
2179 *offset_or_block_len =
2180 fde_table.fr_cfa_rule.ru_offset_or_block_len;
2181 if (row_pc_out != NULL) {
2182 *row_pc_out = fde_table.fr_loc;
2183 }
2184 if (block_ptr) {
2185 *block_ptr = fde_table.fr_cfa_rule.ru_block;
2186 }
2187
2188 /* Without value_type the data cannot be understood, so we insist
2189 on it being present, we don't test it. */
2190 *value_type = fde_table.fr_cfa_rule.ru_value_type;
2191 *offset_relevant = fde_table.fr_cfa_rule.ru_is_off;
2192 dwarf_free_fde_table(&fde_table);
2193 return DW_DLV_OK;
2194 }
2195
2196
2197
2198 /* Return pointer to the instructions in the dwarf fde. */
2199 int
dwarf_get_fde_instr_bytes(Dwarf_Fde inFde,Dwarf_Ptr * outinstraddr,Dwarf_Unsigned * outaddrlen,Dwarf_Error * error)2200 dwarf_get_fde_instr_bytes(Dwarf_Fde inFde, Dwarf_Ptr * outinstraddr,
2201 Dwarf_Unsigned * outaddrlen,
2202 Dwarf_Error * error)
2203 {
2204 Dwarf_Unsigned len = 0;
2205 unsigned char *instrs = 0;
2206 Dwarf_Debug dbg = 0;
2207
2208 if (inFde == NULL) {
2209 _dwarf_error(dbg, error, DW_DLE_FDE_NULL);
2210 return (DW_DLV_ERROR);
2211 }
2212
2213 dbg = inFde->fd_dbg;
2214 if (dbg == NULL) {
2215 _dwarf_error(dbg, error, DW_DLE_FDE_DBG_NULL);
2216 return (DW_DLV_ERROR);
2217 }
2218
2219 instrs = inFde->fd_fde_instr_start;
2220
2221 len = (inFde->fd_fde_start + inFde->fd_length +
2222 inFde->fd_length_size + inFde->fd_extension_size) - instrs;
2223
2224 *outinstraddr = instrs;
2225 *outaddrlen = len;
2226 return DW_DLV_OK;
2227 }
2228
2229 /* Allows getting an fde from its table via an index.
2230 With more error checking than simply indexing oneself. */
2231 int
dwarf_get_fde_n(Dwarf_Fde * fde_data,Dwarf_Unsigned fde_index,Dwarf_Fde * returned_fde,Dwarf_Error * error)2232 dwarf_get_fde_n(Dwarf_Fde * fde_data,
2233 Dwarf_Unsigned fde_index,
2234 Dwarf_Fde * returned_fde, Dwarf_Error * error)
2235 {
2236 Dwarf_Debug dbg = 0;
2237 Dwarf_Unsigned fdecount = 0;
2238
2239 if (fde_data == NULL) {
2240 _dwarf_error(dbg, error, DW_DLE_FDE_PTR_NULL);
2241 return (DW_DLV_ERROR);
2242 }
2243
2244 FDE_NULL_CHECKS_AND_SET_DBG(*fde_data, dbg);
2245 /* Assumes fde_data table has at least one entry. */
2246 fdecount = fde_data[0]->fd_is_eh?
2247 dbg->de_fde_count_eh:dbg->de_fde_count;
2248 if (fde_index >= fdecount) {
2249 return (DW_DLV_NO_ENTRY);
2250 }
2251 *returned_fde = (*(fde_data + fde_index));
2252 return DW_DLV_OK;
2253 }
2254
2255
2256 /* Lopc and hipc are extensions to the interface to
2257 return the range of addresses that are described
2258 by the returned fde. */
2259 int
dwarf_get_fde_at_pc(Dwarf_Fde * fde_data,Dwarf_Addr pc_of_interest,Dwarf_Fde * returned_fde,Dwarf_Addr * lopc,Dwarf_Addr * hipc,Dwarf_Error * error)2260 dwarf_get_fde_at_pc(Dwarf_Fde * fde_data,
2261 Dwarf_Addr pc_of_interest,
2262 Dwarf_Fde * returned_fde,
2263 Dwarf_Addr * lopc,
2264 Dwarf_Addr * hipc, Dwarf_Error * error)
2265 {
2266 Dwarf_Debug dbg = NULL;
2267 Dwarf_Fde fde = NULL;
2268 Dwarf_Fde entryfde = NULL;
2269 Dwarf_Signed fdecount = 0;
2270
2271 if (fde_data == NULL) {
2272 _dwarf_error(NULL, error, DW_DLE_FDE_PTR_NULL);
2273 return (DW_DLV_ERROR);
2274 }
2275
2276 /* Assumes fde_data table has at least one entry. */
2277 entryfde = *fde_data;
2278 FDE_NULL_CHECKS_AND_SET_DBG(entryfde, dbg);
2279 fdecount = entryfde->fd_is_eh?
2280 dbg->de_fde_count_eh:dbg->de_fde_count;
2281 {
2282 /* The fdes are sorted by their addresses. Binary search to
2283 find correct fde. */
2284 Dwarf_Signed low = 0;
2285 Dwarf_Signed high = fdecount - 1L;
2286 Dwarf_Signed middle = 0;
2287 Dwarf_Fde cur_fde;
2288
2289 while (low <= high) {
2290 middle = (low + high) / 2;
2291 cur_fde = fde_data[middle];
2292 if (pc_of_interest < cur_fde->fd_initial_location) {
2293 high = middle - 1;
2294 } else if (pc_of_interest >=
2295 (cur_fde->fd_initial_location +
2296 cur_fde->fd_address_range)) {
2297 low = middle + 1;
2298 } else {
2299 fde = fde_data[middle];
2300 break;
2301 }
2302 }
2303 }
2304
2305 if (fde) {
2306 if (lopc != NULL)
2307 *lopc = fde->fd_initial_location;
2308 if (hipc != NULL)
2309 *hipc =
2310 fde->fd_initial_location + fde->fd_address_range - 1;
2311 *returned_fde = fde;
2312 return (DW_DLV_OK);
2313 }
2314
2315 return (DW_DLV_NO_ENTRY);
2316 }
2317
2318
2319 /* Expands a single frame instruction block
2320 from a specific cie
2321 into a n array of Dwarf_Frame_Op-s.
2322 This depends on having the cfa column set sensibly.
2323
2324 Call dwarf_set_frame_cfa_value() to set the correct column
2325 after calling dwarf_init() unless you are using
2326 the old MIPS frame interfaces (in which case the default
2327 will be ok). (DW_FRAME_CFA_COL3 is a sensible column to use ).
2328 */
2329 int
dwarf_expand_frame_instructions(Dwarf_Cie cie,Dwarf_Ptr instruction,Dwarf_Unsigned i_length,Dwarf_Frame_Op ** returned_op_list,Dwarf_Signed * returned_op_count,Dwarf_Error * error)2330 dwarf_expand_frame_instructions(Dwarf_Cie cie,
2331 Dwarf_Ptr instruction,
2332 Dwarf_Unsigned i_length,
2333 Dwarf_Frame_Op ** returned_op_list,
2334 Dwarf_Signed * returned_op_count,
2335 Dwarf_Error * error)
2336 {
2337 Dwarf_Signed instr_count;
2338 int res = DW_DLV_ERROR;
2339 Dwarf_Debug dbg = 0;
2340 Dwarf_Small * instr_start = instruction;
2341 Dwarf_Small * instr_end = (Dwarf_Small *)instruction + i_length;;
2342
2343 if (cie == 0) {
2344 _dwarf_error(NULL, error, DW_DLE_DBG_NULL);
2345 return (DW_DLV_ERROR);
2346 }
2347 dbg = cie->ci_dbg;
2348
2349 if (returned_op_list == 0 || returned_op_count == 0) {
2350 _dwarf_error(dbg, error, DW_DLE_RET_OP_LIST_NULL);
2351 return (DW_DLV_ERROR);
2352 }
2353 if ( instr_end < instr_start) {
2354 /* Impossible unless there was wraparond somewhere and
2355 we missed it. */
2356 _dwarf_error(dbg, error,DW_DLE_FDE_INSTR_PTR_ERROR);
2357 return DW_DLV_ERROR;
2358 }
2359
2360 res = _dwarf_exec_frame_instr( /* make_instr= */ true,
2361 returned_op_list,
2362 /* search_pc */ false,
2363 /* search_pc_val */ 0,
2364 /* location */ 0,
2365 instr_start,
2366 instr_end,
2367 /* Dwarf_Frame */ NULL,
2368 cie,
2369 dbg,
2370 dbg->de_frame_cfa_col_number, &instr_count,
2371 NULL,NULL,
2372 error);
2373 if (res != DW_DLV_OK) {
2374 return (res);
2375 }
2376 *returned_op_count = instr_count;
2377 return DW_DLV_OK;
2378 }
2379
2380
2381 /* Used by dwarfdump -v to print offsets, for debugging
2382 dwarf info.
2383 The dwarf_ version is preferred over the obsolete _dwarf version.
2384 _dwarf version kept for compatibility.
2385 */
2386 /* ARGSUSED 4 */
2387 int
_dwarf_fde_section_offset(Dwarf_Debug dbg,Dwarf_Fde in_fde,Dwarf_Off * fde_off,Dwarf_Off * cie_off,Dwarf_Error * err)2388 _dwarf_fde_section_offset(Dwarf_Debug dbg, Dwarf_Fde in_fde,
2389 Dwarf_Off * fde_off, Dwarf_Off * cie_off,
2390 Dwarf_Error * err)
2391 {
2392 return dwarf_fde_section_offset(dbg,in_fde,fde_off,
2393 cie_off,err);
2394 }
2395 /* ARGSUSED 4 */
2396 int
dwarf_fde_section_offset(Dwarf_Debug dbg,Dwarf_Fde in_fde,Dwarf_Off * fde_off,Dwarf_Off * cie_off,Dwarf_Error * err)2397 dwarf_fde_section_offset(Dwarf_Debug dbg, Dwarf_Fde in_fde,
2398 Dwarf_Off * fde_off, Dwarf_Off * cie_off,
2399 Dwarf_Error * err)
2400 {
2401 char *start = 0;
2402 char *loc = 0;
2403
2404 if(!in_fde) {
2405 _dwarf_error(dbg, err, DW_DLE_FDE_NULL);
2406 return DW_DLV_ERROR;
2407 }
2408 start = (char *) in_fde->fd_section_ptr;
2409 loc = (char *) in_fde->fd_fde_start;
2410
2411 *fde_off = (loc - start);
2412 *cie_off = in_fde->fd_cie_offset;
2413 return DW_DLV_OK;
2414 }
2415
2416 /* Used by dwarfdump -v to print offsets, for debugging
2417 dwarf info.
2418 The dwarf_ version is preferred over the obsolete _dwarf version.
2419 _dwarf version kept for compatibility.
2420 */
2421 /* ARGSUSED 4 */
2422 int
_dwarf_cie_section_offset(Dwarf_Debug dbg,Dwarf_Cie in_cie,Dwarf_Off * cie_off,Dwarf_Error * err)2423 _dwarf_cie_section_offset(Dwarf_Debug dbg, Dwarf_Cie in_cie,
2424 Dwarf_Off * cie_off, Dwarf_Error * err)
2425 {
2426 return dwarf_cie_section_offset(dbg,in_cie,cie_off,err);
2427 }
2428 /* ARGSUSED 4 */
2429 int
dwarf_cie_section_offset(Dwarf_Debug dbg,Dwarf_Cie in_cie,Dwarf_Off * cie_off,Dwarf_Error * err)2430 dwarf_cie_section_offset(Dwarf_Debug dbg, Dwarf_Cie in_cie,
2431 Dwarf_Off * cie_off, Dwarf_Error * err)
2432 {
2433 char *start = 0;
2434 char *loc = 0;
2435
2436 if(!in_cie) {
2437 _dwarf_error(dbg, err, DW_DLE_CIE_NULL);
2438 return DW_DLV_ERROR;
2439 }
2440 start = (char *) in_cie->ci_section_ptr;
2441 loc = (char *) in_cie->ci_cie_start;
2442
2443 *cie_off = (loc - start);
2444 return DW_DLV_OK;
2445 }
2446
2447 /* Returns a pointer to target-specific augmentation data thru augdata
2448 and returns the length of the data thru augdata_len.
2449
2450 It's up to the consumer code to know how to interpret the bytes
2451 of target-specific data (endian issues apply too, these
2452 are just raw bytes pointed to).
2453 See Linux Standard Base Core Specification version 3.0 for
2454 the details on .eh_frame info.
2455
2456 Returns DW_DLV_ERROR if fde is NULL or some other serious
2457 error.
2458 Returns DW_DLV_NO_ENTRY if there is no target-specific
2459 augmentation data.
2460
2461 The bytes pointed to are in the Dwarf_Cie, and as long as that
2462 is valid the bytes are there. No 'dealloc' call is needed
2463 for the bytes. */
2464 int
dwarf_get_cie_augmentation_data(Dwarf_Cie cie,Dwarf_Small ** augdata,Dwarf_Unsigned * augdata_len,Dwarf_Error * error)2465 dwarf_get_cie_augmentation_data(Dwarf_Cie cie,
2466 Dwarf_Small ** augdata,
2467 Dwarf_Unsigned * augdata_len,
2468 Dwarf_Error * error)
2469 {
2470 if (cie == NULL) {
2471 _dwarf_error(NULL, error, DW_DLE_CIE_NULL);
2472 return (DW_DLV_ERROR);
2473 }
2474 if (cie->ci_gnu_eh_augmentation_len == 0) {
2475 return DW_DLV_NO_ENTRY;
2476 }
2477 *augdata = (Dwarf_Small *) (cie->ci_gnu_eh_augmentation_bytes);
2478 *augdata_len = cie->ci_gnu_eh_augmentation_len;
2479 return DW_DLV_OK;
2480 }
2481
2482
2483 /* Returns a pointer to target-specific augmentation data thru augdata
2484 and returns the length of the data thru augdata_len.
2485
2486 It's up to the consumer code to know how to interpret the bytes
2487 of target-specific data (endian issues apply too, these
2488 are just raw bytes pointed to).
2489 See Linux Standard Base Core Specification version 3.0 for
2490 the details on .eh_frame info.
2491
2492 Returns DW_DLV_ERROR if fde is NULL or some other serious
2493 error.
2494 Returns DW_DLV_NO_ENTRY if there is no target-specific
2495 augmentation data.
2496
2497 The bytes pointed to are in the Dwarf_Fde, and as long as that
2498 is valid the bytes are there. No 'dealloc' call is needed
2499 for the bytes. */
2500 int
dwarf_get_fde_augmentation_data(Dwarf_Fde fde,Dwarf_Small ** augdata,Dwarf_Unsigned * augdata_len,Dwarf_Error * error)2501 dwarf_get_fde_augmentation_data(Dwarf_Fde fde,
2502 Dwarf_Small * *augdata,
2503 Dwarf_Unsigned * augdata_len,
2504 Dwarf_Error * error)
2505 {
2506 Dwarf_Cie cie = 0;
2507
2508 if (fde == NULL) {
2509 _dwarf_error(NULL, error, DW_DLE_FDE_NULL);
2510 return (DW_DLV_ERROR);
2511 }
2512 if(!fde->fd_gnu_eh_aug_present) {
2513 return DW_DLV_NO_ENTRY;
2514 }
2515 cie = fde->fd_cie;
2516 if (cie == NULL) {
2517 _dwarf_error(NULL, error, DW_DLE_CIE_NULL);
2518 return (DW_DLV_ERROR);
2519 }
2520 *augdata = (Dwarf_Small *) fde->fd_gnu_eh_augmentation_bytes;
2521 *augdata_len = fde->fd_gnu_eh_augmentation_len;
2522 return DW_DLV_OK;
2523 }
2524
2525
2526 #if 0 /* FOR DEBUGGING */
2527 /* Used solely for debugging libdwarf. */
2528 static void
2529 dump_frame_rule(char *msg, struct Dwarf_Reg_Rule_s *reg_rule)
2530 {
2531 printf
2532 ("%s type %s (0x%" DW_PR_XZEROS DW_PR_DUx
2533 "), is_off %" DW_PR_DUu
2534 " reg %" DW_PR_DUu " offset 0x%" DW_PR_XZEROS DW_PR_DUx
2535 " blockp 0x%" DW_PR_XZEROS DW_PR_DUx "\n",
2536 msg,
2537 (reg_rule->ru_value_type == DW_EXPR_OFFSET) ?
2538 "DW_EXPR_OFFSET" :
2539 (reg_rule->ru_value_type == DW_EXPR_VAL_OFFSET) ?
2540 "DW_EXPR_VAL_OFFSET" :
2541 (reg_rule->ru_value_type == DW_EXPR_VAL_EXPRESSION) ?
2542 "DW_EXPR_VAL_EXPRESSION" :
2543 (reg_rule->ru_value_type == DW_EXPR_EXPRESSION) ?
2544 "DW_EXPR_EXPRESSION" : "Unknown",
2545 (Dwarf_Unsigned) reg_rule->ru_value_type,
2546 (Dwarf_Unsigned) reg_rule->ru_is_off,
2547 (Dwarf_Unsigned) reg_rule->ru_register,
2548 (Dwarf_Unsigned) reg_rule->ru_offset_or_block_len,
2549 (Dwarf_Unsigned) reg_rule->ru_block);
2550 return;
2551 }
2552 #endif
2553
2554 /* This allows consumers to set the 'initial value' so that
2555 an ISA/ABI specific default can be used, dynamically,
2556 at run time. Useful for dwarfdump and non-MIPS architectures..
2557 The value defaults to one of
2558 DW_FRAME_SAME_VALUE or DW_FRAME_UNKNOWN_VALUE
2559 but dwarfdump can dump multiple ISA/ABI objects so
2560 we may want to get this set to what the ABI says is correct.
2561
2562 Returns the value that was present before we changed it here. */
2563 Dwarf_Half
dwarf_set_frame_rule_initial_value(Dwarf_Debug dbg,Dwarf_Half value)2564 dwarf_set_frame_rule_initial_value(Dwarf_Debug dbg, Dwarf_Half value)
2565 {
2566 Dwarf_Half orig = dbg->de_frame_rule_initial_value;
2567 dbg->de_frame_rule_initial_value = value;
2568 return orig;
2569 }
2570
2571 /* The following spelling for backwards compatibility. */
2572 Dwarf_Half
dwarf_set_frame_rule_inital_value(Dwarf_Debug dbg,Dwarf_Half value)2573 dwarf_set_frame_rule_inital_value(Dwarf_Debug dbg, Dwarf_Half value)
2574 {
2575 return dwarf_set_frame_rule_initial_value(dbg,value);
2576 }
2577
2578 /* This allows consumers to set the array size of the reg rules
2579 table so that
2580 an ISA/ABI specific value can be used, dynamically,
2581 at run time. Useful for non-MIPS archtectures.
2582 The value defaults to DW_FRAME_LAST_REG_NUM.
2583 but dwarfdump can dump multiple ISA/ABI objects so
2584 consumers want to get this set to what the ABI says is correct.
2585
2586 Returns the value that was present before we changed it here.
2587 */
2588
2589 Dwarf_Half
dwarf_set_frame_rule_table_size(Dwarf_Debug dbg,Dwarf_Half value)2590 dwarf_set_frame_rule_table_size(Dwarf_Debug dbg, Dwarf_Half value)
2591 {
2592 Dwarf_Half orig = dbg->de_frame_reg_rules_entry_count;
2593 dbg->de_frame_reg_rules_entry_count = value;
2594
2595 /* Take the caller-specified value, but do not
2596 let the value be too small. Keep it at least to
2597 DW_FRAME_LAST_REG_NUM.
2598 This helps prevent libdwarf (mistakenly) indexing outside
2599 of of a register array when the ABI reg count is really small. */
2600 if (value < DW_FRAME_LAST_REG_NUM) {
2601 dbg->de_frame_reg_rules_entry_count = DW_FRAME_LAST_REG_NUM;
2602 }
2603 return orig;
2604 }
2605 /* This allows consumers to set the CFA register value
2606 so that an ISA/ABI specific value can be used, dynamically,
2607 at run time. Useful for non-MIPS archtectures.
2608 The value defaults to DW_FRAME_CFA_COL3 and should be
2609 higher than any real register in the ABI.
2610 Dwarfdump can dump multiple ISA/ABI objects so
2611 consumers want to get this set to what the ABI says is correct.
2612
2613 Returns the value that was present before we changed it here. */
2614
2615 Dwarf_Half
dwarf_set_frame_cfa_value(Dwarf_Debug dbg,Dwarf_Half value)2616 dwarf_set_frame_cfa_value(Dwarf_Debug dbg, Dwarf_Half value)
2617 {
2618 Dwarf_Half orig = dbg->de_frame_cfa_col_number;
2619 dbg->de_frame_cfa_col_number = value;
2620 return orig;
2621 }
2622 /* Similar to above, but for the other crucial fields for frames. */
2623 Dwarf_Half
dwarf_set_frame_same_value(Dwarf_Debug dbg,Dwarf_Half value)2624 dwarf_set_frame_same_value(Dwarf_Debug dbg, Dwarf_Half value)
2625 {
2626 Dwarf_Half orig = dbg->de_frame_same_value_number;
2627 dbg->de_frame_same_value_number = value;
2628 return orig;
2629 }
2630 Dwarf_Half
dwarf_set_frame_undefined_value(Dwarf_Debug dbg,Dwarf_Half value)2631 dwarf_set_frame_undefined_value(Dwarf_Debug dbg, Dwarf_Half value)
2632 {
2633 Dwarf_Half orig = dbg->de_frame_same_value_number;
2634 dbg->de_frame_undefined_value_number = value;
2635 return orig;
2636 }
2637
2638 /* Does something only if value passed in is greater than 0 and
2639 a size than we can handle (in number of bytes). */
dwarf_set_default_address_size(Dwarf_Debug dbg,Dwarf_Small value)2640 Dwarf_Small dwarf_set_default_address_size(Dwarf_Debug dbg,
2641 Dwarf_Small value )
2642 {
2643 Dwarf_Small orig = dbg->de_pointer_size;
2644 if (value > 0 && value <= sizeof(Dwarf_Addr)) {
2645 dbg->de_pointer_size = value;
2646 }
2647 return orig;
2648 }
2649
2650 static int
init_reg_rules_alloc(Dwarf_Debug dbg,struct Dwarf_Frame_s * f,unsigned count,Dwarf_Error * error)2651 init_reg_rules_alloc(Dwarf_Debug dbg,struct Dwarf_Frame_s *f,
2652 unsigned count, Dwarf_Error * error)
2653 {
2654 f->fr_reg_count = count;
2655 f->fr_reg = (struct Dwarf_Reg_Rule_s *)
2656 calloc(sizeof(struct Dwarf_Reg_Rule_s), count);
2657 if (f->fr_reg == 0) {
2658 if (error) {
2659 _dwarf_error(dbg, error, DW_DLE_DF_ALLOC_FAIL);
2660 }
2661 return (DW_DLV_ERROR);
2662 }
2663 dwarf_init_reg_rules_ru(f->fr_reg,0, count,
2664 dbg->de_frame_rule_initial_value);
2665 return DW_DLV_OK;
2666 }
2667 static int
dwarf_initialize_fde_table(Dwarf_Debug dbg,struct Dwarf_Frame_s * fde_table,unsigned table_real_data_size,Dwarf_Error * error)2668 dwarf_initialize_fde_table(Dwarf_Debug dbg,
2669 struct Dwarf_Frame_s *fde_table,
2670 unsigned table_real_data_size,
2671 Dwarf_Error * error)
2672 {
2673 unsigned entry_size = sizeof(struct Dwarf_Frame_s);
2674 memset(fde_table,0,entry_size);
2675 fde_table->fr_loc = 0;
2676 fde_table->fr_next = 0;
2677
2678 return init_reg_rules_alloc(dbg,fde_table,table_real_data_size,error);
2679 }
2680 static void
dwarf_free_fde_table(struct Dwarf_Frame_s * fde_table)2681 dwarf_free_fde_table(struct Dwarf_Frame_s *fde_table)
2682 {
2683 free(fde_table->fr_reg);
2684 fde_table->fr_reg_count = 0;
2685 fde_table->fr_reg = 0;
2686 }
2687
2688
2689 /* Return DW_DLV_OK if we succeed. else return DW_DLV_ERROR.
2690 */
2691 int
_dwarf_frame_constructor(Dwarf_Debug dbg,void * frame)2692 _dwarf_frame_constructor(Dwarf_Debug dbg, void *frame)
2693 {
2694 struct Dwarf_Frame_s *fp = frame;
2695
2696 if (!dbg) {
2697 return DW_DLV_ERROR;
2698 }
2699 return init_reg_rules_alloc(dbg,fp,dbg->de_frame_reg_rules_entry_count, 0);
2700 }
2701
2702 void
_dwarf_frame_destructor(void * frame)2703 _dwarf_frame_destructor(void *frame)
2704 {
2705 struct Dwarf_Frame_s *fp = frame;
2706 dwarf_free_fde_table(fp);
2707 }
2708 void
_dwarf_fde_destructor(void * f)2709 _dwarf_fde_destructor(void *f)
2710 {
2711 struct Dwarf_Fde_s *fde = f;
2712 if (fde->fd_have_fde_tab) {
2713 dwarf_free_fde_table(&fde->fd_fde_table);
2714 fde->fd_have_fde_tab = false;
2715 }
2716 }
2717
2718 static void
dwarf_init_reg_rules_ru(struct Dwarf_Reg_Rule_s * base,unsigned first,unsigned last,int initial_value)2719 dwarf_init_reg_rules_ru(struct Dwarf_Reg_Rule_s *base,
2720 unsigned first, unsigned last,int initial_value)
2721 {
2722 struct Dwarf_Reg_Rule_s *r = base+first;
2723 unsigned i = first;
2724 for (; i < last; ++i,++r) {
2725 r->ru_is_off = 0;
2726 r->ru_value_type = DW_EXPR_OFFSET;
2727 r->ru_register = initial_value;
2728 r->ru_offset_or_block_len = 0;
2729 r->ru_block = 0;
2730 }
2731 }
2732 static void
dwarf_init_reg_rules_dw(struct Dwarf_Regtable_Entry_s * base,unsigned first,unsigned last,int initial_value)2733 dwarf_init_reg_rules_dw(struct Dwarf_Regtable_Entry_s *base,
2734 unsigned first, unsigned last,int initial_value)
2735 {
2736 struct Dwarf_Regtable_Entry_s *r = base+first;
2737 unsigned i = first;
2738 for (; i < last; ++i,++r) {
2739 r->dw_offset_relevant = 0;
2740 r->dw_value_type = DW_EXPR_OFFSET;
2741 r->dw_regnum = initial_value;
2742 r->dw_offset = 0;
2743 }
2744 }
2745 static void
dwarf_init_reg_rules_dw3(struct Dwarf_Regtable_Entry3_s * base,unsigned first,unsigned last,int initial_value)2746 dwarf_init_reg_rules_dw3(struct Dwarf_Regtable_Entry3_s *base,
2747 unsigned first, unsigned last,int initial_value)
2748 {
2749 struct Dwarf_Regtable_Entry3_s *r = base+first;
2750 unsigned i = first;
2751 for (; i < last; ++i,++r) {
2752 r->dw_offset_relevant = 0;
2753 r->dw_value_type = DW_EXPR_OFFSET;
2754 r->dw_regnum = initial_value;
2755 r->dw_offset_or_block_len = 0;
2756 r->dw_block_ptr = 0;
2757 }
2758 }
2759