1 /* Internal definitions for libdwarf. 2 Copyright (C) 2002-2011, 2013, 2014 Red Hat, Inc. 3 This file is part of elfutils. 4 Written by Ulrich Drepper <drepper (at) redhat.com>, 2002. 5 6 This file is free software; you can redistribute it and/or modify 7 it under the terms of either 8 9 * the GNU Lesser General Public License as published by the Free 10 Software Foundation; either version 3 of the License, or (at 11 your option) any later version 12 13 or 14 15 * the GNU General Public License as published by the Free 16 Software Foundation; either version 2 of the License, or (at 17 your option) any later version 18 19 or both in parallel, as here. 20 21 elfutils is distributed in the hope that it will be useful, but 22 WITHOUT ANY WARRANTY; without even the implied warranty of 23 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 24 General Public License for more details. 25 26 You should have received copies of the GNU General Public License and 27 the GNU Lesser General Public License along with this program. If 28 not, see <http://www.gnu.org/licenses/>. */ 29 30 #ifndef _LIBDWP_H 31 #define _LIBDWP_H 1 32 33 #include <libintl.h> 34 #include <stdbool.h> 35 36 #include <libdw.h> 37 #include <dwarf.h> 38 39 40 /* gettext helper macros. */ 41 #define _(Str) dgettext ("elfutils", Str) 42 43 44 /* Known location expressions already decoded. */ 45 struct loc_s 46 { 47 void *addr; 48 Dwarf_Op *loc; 49 size_t nloc; 50 }; 51 52 /* Known DW_OP_implicit_value blocks already decoded. 53 This overlaps struct loc_s exactly, but only the 54 first member really has to match. */ 55 struct loc_block_s 56 { 57 void *addr; 58 unsigned char *data; 59 size_t length; 60 }; 61 62 /* Already decoded .debug_line units. */ 63 struct files_lines_s 64 { 65 Dwarf_Off debug_line_offset; 66 Dwarf_Files *files; 67 Dwarf_Lines *lines; 68 }; 69 70 /* Valid indeces for the section data. */ 71 enum 72 { 73 IDX_debug_info = 0, 74 IDX_debug_types, 75 IDX_debug_abbrev, 76 IDX_debug_aranges, 77 IDX_debug_line, 78 IDX_debug_frame, 79 IDX_debug_loc, 80 IDX_debug_pubnames, 81 IDX_debug_str, 82 IDX_debug_macinfo, 83 IDX_debug_macro, 84 IDX_debug_ranges, 85 IDX_gnu_debugaltlink, 86 IDX_last 87 }; 88 89 90 /* Error values. */ 91 enum 92 { 93 DWARF_E_NOERROR = 0, 94 DWARF_E_UNKNOWN_ERROR, 95 DWARF_E_INVALID_ACCESS, 96 DWARF_E_NO_REGFILE, 97 DWARF_E_IO_ERROR, 98 DWARF_E_INVALID_ELF, 99 DWARF_E_NO_DWARF, 100 DWARF_E_NOELF, 101 DWARF_E_GETEHDR_ERROR, 102 DWARF_E_NOMEM, 103 DWARF_E_UNIMPL, 104 DWARF_E_INVALID_CMD, 105 DWARF_E_INVALID_VERSION, 106 DWARF_E_INVALID_FILE, 107 DWARF_E_NO_ENTRY, 108 DWARF_E_INVALID_DWARF, 109 DWARF_E_NO_STRING, 110 DWARF_E_NO_ADDR, 111 DWARF_E_NO_CONSTANT, 112 DWARF_E_NO_REFERENCE, 113 DWARF_E_INVALID_REFERENCE, 114 DWARF_E_NO_DEBUG_LINE, 115 DWARF_E_INVALID_DEBUG_LINE, 116 DWARF_E_TOO_BIG, 117 DWARF_E_VERSION, 118 DWARF_E_INVALID_DIR_IDX, 119 DWARF_E_ADDR_OUTOFRANGE, 120 DWARF_E_NO_LOCLIST, 121 DWARF_E_NO_BLOCK, 122 DWARF_E_INVALID_LINE_IDX, 123 DWARF_E_INVALID_ARANGE_IDX, 124 DWARF_E_NO_MATCH, 125 DWARF_E_NO_FLAG, 126 DWARF_E_INVALID_OFFSET, 127 DWARF_E_NO_DEBUG_RANGES, 128 DWARF_E_INVALID_CFI, 129 DWARF_E_NO_ALT_DEBUGLINK, 130 DWARF_E_INVALID_OPCODE, 131 }; 132 133 134 #include "dwarf_sig8_hash.h" 135 136 /* This is the structure representing the debugging state. */ 137 struct Dwarf 138 { 139 /* The underlying ELF file. */ 140 Elf *elf; 141 142 /* dwz alternate DWARF file. */ 143 Dwarf *alt_dwarf; 144 145 /* The section data. */ 146 Elf_Data *sectiondata[IDX_last]; 147 148 #if USE_ZLIB 149 /* The 1 << N bit is set if sectiondata[N] is malloc'd decompressed data. */ 150 unsigned int sectiondata_gzip_mask:IDX_last; 151 #endif 152 153 /* True if the file has a byte order different from the host. */ 154 bool other_byte_order; 155 156 /* If true, we allocated the ELF descriptor ourselves. */ 157 bool free_elf; 158 159 /* Information for traversing the .debug_pubnames section. This is 160 an array and separately allocated with malloc. */ 161 struct pubnames_s 162 { 163 Dwarf_Off cu_offset; 164 Dwarf_Off set_start; 165 unsigned int cu_header_size; 166 int address_len; 167 } *pubnames_sets; 168 size_t pubnames_nsets; 169 170 /* Search tree for the CUs. */ 171 void *cu_tree; 172 Dwarf_Off next_cu_offset; 173 174 /* Search tree and sig8 hash table for .debug_types type units. */ 175 void *tu_tree; 176 Dwarf_Off next_tu_offset; 177 Dwarf_Sig8_Hash sig8_hash; 178 179 /* Search tree for .debug_macro operator tables. */ 180 void *macro_ops; 181 182 /* Search tree for decoded .debug_line units. */ 183 void *files_lines; 184 185 /* Address ranges. */ 186 Dwarf_Aranges *aranges; 187 188 /* Cached info from the CFI section. */ 189 struct Dwarf_CFI_s *cfi; 190 191 /* Fake loc CU. Used when synthesizing attributes for Dwarf_Ops that 192 came from a location list entry in dwarf_getlocation_attr. */ 193 struct Dwarf_CU *fake_loc_cu; 194 195 /* Internal memory handling. This is basically a simplified 196 reimplementation of obstacks. Unfortunately the standard obstack 197 implementation is not usable in libraries. */ 198 struct libdw_memblock 199 { 200 size_t size; 201 size_t remaining; 202 struct libdw_memblock *prev; 203 char mem[0]; 204 } *mem_tail; 205 206 /* Default size of allocated memory blocks. */ 207 size_t mem_default_size; 208 209 /* Registered OOM handler. */ 210 Dwarf_OOM oom_handler; 211 }; 212 213 214 /* Abbreviation representation. */ 215 struct Dwarf_Abbrev 216 { 217 Dwarf_Off offset; 218 unsigned char *attrp; 219 unsigned int attrcnt; 220 unsigned int code; 221 unsigned int tag; 222 bool has_children; 223 }; 224 225 #include "dwarf_abbrev_hash.h" 226 227 228 /* Files in line information records. */ 229 struct Dwarf_Files_s 230 { 231 unsigned int ndirs; 232 unsigned int nfiles; 233 struct Dwarf_Fileinfo_s 234 { 235 char *name; 236 Dwarf_Word mtime; 237 Dwarf_Word length; 238 } info[0]; 239 /* nfiles of those, followed by char *[ndirs]. */ 240 }; 241 typedef struct Dwarf_Fileinfo_s Dwarf_Fileinfo; 242 243 244 /* Representation of a row in the line table. */ 245 246 struct Dwarf_Line_s 247 { 248 Dwarf_Files *files; 249 250 Dwarf_Addr addr; 251 unsigned int file; 252 int line; 253 unsigned short int column; 254 unsigned int is_stmt:1; 255 unsigned int basic_block:1; 256 unsigned int end_sequence:1; 257 unsigned int prologue_end:1; 258 unsigned int epilogue_begin:1; 259 /* The remaining bit fields are not flags, but hold values presumed to be 260 small. All the flags and other bit fields should add up to 48 bits 261 to give the whole struct a nice round size. */ 262 unsigned int op_index:8; 263 unsigned int isa:8; 264 unsigned int discriminator:24; 265 }; 266 267 struct Dwarf_Lines_s 268 { 269 size_t nlines; 270 struct Dwarf_Line_s info[0]; 271 }; 272 273 /* Representation of address ranges. */ 274 struct Dwarf_Aranges_s 275 { 276 Dwarf *dbg; 277 size_t naranges; 278 279 struct Dwarf_Arange_s 280 { 281 Dwarf_Addr addr; 282 Dwarf_Word length; 283 Dwarf_Off offset; 284 } info[0]; 285 }; 286 287 288 /* CU representation. */ 289 struct Dwarf_CU 290 { 291 Dwarf *dbg; 292 Dwarf_Off start; 293 Dwarf_Off end; 294 uint8_t address_size; 295 uint8_t offset_size; 296 uint16_t version; 297 298 /* Zero if this is a normal CU. Nonzero if it is a type unit. */ 299 size_t type_offset; 300 uint64_t type_sig8; 301 302 /* Hash table for the abbreviations. */ 303 Dwarf_Abbrev_Hash abbrev_hash; 304 /* Offset of the first abbreviation. */ 305 size_t orig_abbrev_offset; 306 /* Offset past last read abbreviation. */ 307 size_t last_abbrev_offset; 308 309 /* The srcline information. */ 310 Dwarf_Lines *lines; 311 312 /* The source file information. */ 313 Dwarf_Files *files; 314 315 /* Known location lists. */ 316 void *locs; 317 318 /* Memory boundaries of this CU. */ 319 void *startp; 320 void *endp; 321 }; 322 323 /* Compute the offset of a CU's first DIE from its offset. This 324 is either: 325 LEN VER OFFSET ADDR 326 4-bytes + 2-bytes + 4-bytes + 1-byte for 32-bit dwarf 327 12-bytes + 2-bytes + 8-bytes + 1-byte for 64-bit dwarf 328 or in .debug_types, SIGNATURE TYPE-OFFSET 329 4-bytes + 2-bytes + 4-bytes + 1-byte + 8-bytes + 4-bytes for 32-bit 330 12-bytes + 2-bytes + 8-bytes + 1-byte + 8-bytes + 8-bytes for 64-bit 331 332 Note the trick in the computation. If the offset_size is 4 333 the '- 4' term changes the '3 *' into a '2 *'. If the 334 offset_size is 8 it accounts for the 4-byte escape value 335 used at the start of the length. */ 336 #define DIE_OFFSET_FROM_CU_OFFSET(cu_offset, offset_size, type_unit) \ 337 ((type_unit) ? ((cu_offset) + 4 * (offset_size) - 4 + 3 + 8) \ 338 : ((cu_offset) + 3 * (offset_size) - 4 + 3)) 339 340 #define CUDIE(fromcu) \ 341 ((Dwarf_Die) \ 342 { \ 343 .cu = (fromcu), \ 344 .addr = ((char *) fromcu->dbg->sectiondata[cu_sec_idx (fromcu)]->d_buf \ 345 + DIE_OFFSET_FROM_CU_OFFSET ((fromcu)->start, \ 346 (fromcu)->offset_size, \ 347 (fromcu)->type_offset != 0)) \ 348 }) \ 349 350 351 /* Prototype of a single .debug_macro operator. */ 352 typedef struct 353 { 354 Dwarf_Word nforms; 355 unsigned char const *forms; 356 } Dwarf_Macro_Op_Proto; 357 358 /* Prototype table. */ 359 typedef struct 360 { 361 /* Offset of .debug_macro section. */ 362 Dwarf_Off offset; 363 364 /* Offset of associated .debug_line section. */ 365 Dwarf_Off line_offset; 366 367 /* The source file information. */ 368 Dwarf_Files *files; 369 370 /* If this macro unit was opened through dwarf_getmacros or 371 dwarf_getmacros_die, this caches value of DW_AT_comp_dir, if 372 present. */ 373 const char *comp_dir; 374 375 /* Header length. */ 376 Dwarf_Half header_len; 377 378 uint16_t version; 379 bool is_64bit; 380 uint8_t sec_index; /* IDX_debug_macro or IDX_debug_macinfo. */ 381 382 /* Shows where in TABLE each opcode is defined. Since opcode 0 is 383 never used, it stores index of opcode X in X-1'th element. The 384 value of 0xff means not stored at all. */ 385 unsigned char opcodes[255]; 386 387 /* Individual opcode prototypes. */ 388 Dwarf_Macro_Op_Proto table[]; 389 } Dwarf_Macro_Op_Table; 390 391 struct Dwarf_Macro_s 392 { 393 Dwarf_Macro_Op_Table *table; 394 Dwarf_Attribute *attributes; 395 uint8_t opcode; 396 }; 397 398 static inline Dwarf_Word 399 libdw_macro_nforms (Dwarf_Macro *macro) 400 { 401 return macro->table->table[macro->table->opcodes[macro->opcode - 1]].nforms; 402 } 403 404 /* We have to include the file at this point because the inline 405 functions access internals of the Dwarf structure. */ 406 #include "memory-access.h" 407 408 409 /* Set error value. */ 410 extern void __libdw_seterrno (int value) internal_function; 411 412 413 /* Memory handling, the easy parts. This macro does not do any locking. */ 414 #define libdw_alloc(dbg, type, tsize, cnt) \ 415 ({ struct libdw_memblock *_tail = (dbg)->mem_tail; \ 416 size_t _required = (tsize) * (cnt); \ 417 type *_result = (type *) (_tail->mem + (_tail->size - _tail->remaining));\ 418 size_t _padding = ((__alignof (type) \ 419 - ((uintptr_t) _result & (__alignof (type) - 1))) \ 420 & (__alignof (type) - 1)); \ 421 if (unlikely (_tail->remaining < _required + _padding)) \ 422 _result = (type *) __libdw_allocate (dbg, _required, __alignof (type));\ 423 else \ 424 { \ 425 _required += _padding; \ 426 _result = (type *) ((char *) _result + _padding); \ 427 _tail->remaining -= _required; \ 428 } \ 429 _result; }) 430 431 #define libdw_typed_alloc(dbg, type) \ 432 libdw_alloc (dbg, type, sizeof (type), 1) 433 434 /* Callback to allocate more. */ 435 extern void *__libdw_allocate (Dwarf *dbg, size_t minsize, size_t align) 436 __attribute__ ((__malloc__)) __nonnull_attribute__ (1); 437 438 /* Default OOM handler. */ 439 extern void __libdw_oom (void) __attribute ((noreturn, visibility ("hidden"))); 440 441 #if USE_ZLIB 442 extern void __libdw_free_zdata (Dwarf *dwarf) internal_function; 443 #else 444 # define __libdw_free_zdata(dwarf) ((void) (dwarf)) 445 #endif 446 447 /* Allocate the internal data for a unit not seen before. */ 448 extern struct Dwarf_CU *__libdw_intern_next_unit (Dwarf *dbg, bool debug_types) 449 __nonnull_attribute__ (1) internal_function; 450 451 /* Find CU for given offset. */ 452 extern struct Dwarf_CU *__libdw_findcu (Dwarf *dbg, Dwarf_Off offset, bool tu) 453 __nonnull_attribute__ (1) internal_function; 454 455 /* Get abbreviation with given code. */ 456 extern Dwarf_Abbrev *__libdw_findabbrev (struct Dwarf_CU *cu, 457 unsigned int code) 458 __nonnull_attribute__ (1) internal_function; 459 460 /* Get abbreviation at given offset. */ 461 extern Dwarf_Abbrev *__libdw_getabbrev (Dwarf *dbg, struct Dwarf_CU *cu, 462 Dwarf_Off offset, size_t *lengthp, 463 Dwarf_Abbrev *result) 464 __nonnull_attribute__ (1) internal_function; 465 466 /* Get abbreviation of given DIE, and optionally set *READP to the DIE memory 467 just past the abbreviation code. */ 468 static inline Dwarf_Abbrev * 469 __nonnull_attribute__ (1) 470 __libdw_dieabbrev (Dwarf_Die *die, const unsigned char **readp) 471 { 472 /* Do we need to get the abbreviation, or need to read after the code? */ 473 if (die->abbrev == NULL || readp != NULL) 474 { 475 /* Get the abbreviation code. */ 476 unsigned int code; 477 const unsigned char *addr = die->addr; 478 get_uleb128 (code, addr, die->cu->endp); 479 if (readp != NULL) 480 *readp = addr; 481 482 /* Find the abbreviation. */ 483 if (die->abbrev == NULL) 484 die->abbrev = __libdw_findabbrev (die->cu, code); 485 } 486 return die->abbrev; 487 } 488 489 /* Helper functions for form handling. */ 490 extern size_t __libdw_form_val_compute_len (struct Dwarf_CU *cu, 491 unsigned int form, 492 const unsigned char *valp) 493 __nonnull_attribute__ (1, 3) internal_function; 494 495 /* Find the length of a form attribute. */ 496 static inline size_t 497 __nonnull_attribute__ (1, 3) 498 __libdw_form_val_len (struct Dwarf_CU *cu, unsigned int form, 499 const unsigned char *valp) 500 { 501 /* Small lookup table of forms with fixed lengths. Absent indexes are 502 initialized 0, so any truly desired 0 is set to 0x80 and masked. */ 503 static const uint8_t form_lengths[] = 504 { 505 [DW_FORM_flag_present] = 0x80, 506 [DW_FORM_data1] = 1, [DW_FORM_ref1] = 1, [DW_FORM_flag] = 1, 507 [DW_FORM_data2] = 2, [DW_FORM_ref2] = 2, 508 [DW_FORM_data4] = 4, [DW_FORM_ref4] = 4, 509 [DW_FORM_data8] = 8, [DW_FORM_ref8] = 8, [DW_FORM_ref_sig8] = 8, 510 }; 511 512 /* Return immediately for forms with fixed lengths. */ 513 if (form < sizeof form_lengths / sizeof form_lengths[0]) 514 { 515 uint8_t len = form_lengths[form]; 516 if (len != 0) 517 { 518 const unsigned char *endp = cu->endp; 519 len &= 0x7f; /* Mask to allow 0x80 -> 0. */ 520 if (unlikely (len > (size_t) (endp - valp))) 521 { 522 __libdw_seterrno (DWARF_E_INVALID_DWARF); 523 return -1; 524 } 525 return len; 526 } 527 } 528 529 /* Other forms require some computation. */ 530 return __libdw_form_val_compute_len (cu, form, valp); 531 } 532 533 /* Helper function for DW_FORM_ref* handling. */ 534 extern int __libdw_formref (Dwarf_Attribute *attr, Dwarf_Off *return_offset) 535 __nonnull_attribute__ (1, 2) internal_function; 536 537 538 /* Helper function to locate attribute. */ 539 extern unsigned char *__libdw_find_attr (Dwarf_Die *die, 540 unsigned int search_name, 541 unsigned int *codep, 542 unsigned int *formp) 543 __nonnull_attribute__ (1) internal_function; 544 545 /* Helper function to access integer attribute. */ 546 extern int __libdw_attr_intval (Dwarf_Die *die, int *valp, int attval) 547 __nonnull_attribute__ (1, 2) internal_function; 548 549 /* Helper function to walk scopes. */ 550 struct Dwarf_Die_Chain 551 { 552 Dwarf_Die die; 553 struct Dwarf_Die_Chain *parent; 554 bool prune; /* The PREVISIT function can set this. */ 555 }; 556 extern int __libdw_visit_scopes (unsigned int depth, 557 struct Dwarf_Die_Chain *root, 558 int (*previsit) (unsigned int depth, 559 struct Dwarf_Die_Chain *, 560 void *arg), 561 int (*postvisit) (unsigned int depth, 562 struct Dwarf_Die_Chain *, 563 void *arg), 564 void *arg) 565 __nonnull_attribute__ (2, 3) internal_function; 566 567 /* Parse a DWARF Dwarf_Block into an array of Dwarf_Op's, 568 and cache the result (via tsearch). */ 569 extern int __libdw_intern_expression (Dwarf *dbg, 570 bool other_byte_order, 571 unsigned int address_size, 572 unsigned int ref_size, 573 void **cache, const Dwarf_Block *block, 574 bool cfap, bool valuep, 575 Dwarf_Op **llbuf, size_t *listlen, 576 int sec_index) 577 __nonnull_attribute__ (5, 6, 9, 10) internal_function; 578 579 extern Dwarf_Die *__libdw_offdie (Dwarf *dbg, Dwarf_Off offset, 580 Dwarf_Die *result, bool debug_types) 581 internal_function; 582 583 584 /* Return error code of last failing function call. This value is kept 585 separately for each thread. */ 586 extern int __dwarf_errno_internal (void); 587 588 589 /* Reader hooks. */ 590 591 /* Relocation hooks return -1 on error (in that case the error code 592 must already have been set), 0 if there is no relocation and 1 if a 593 relocation was present.*/ 594 595 static inline int 596 __libdw_relocate_address (Dwarf *dbg __attribute__ ((unused)), 597 int sec_index __attribute__ ((unused)), 598 const void *addr __attribute__ ((unused)), 599 int width __attribute__ ((unused)), 600 Dwarf_Addr *val __attribute__ ((unused))) 601 { 602 return 0; 603 } 604 605 static inline int 606 __libdw_relocate_offset (Dwarf *dbg __attribute__ ((unused)), 607 int sec_index __attribute__ ((unused)), 608 const void *addr __attribute__ ((unused)), 609 int width __attribute__ ((unused)), 610 Dwarf_Off *val __attribute__ ((unused))) 611 { 612 return 0; 613 } 614 615 static inline Elf_Data * 616 __libdw_checked_get_data (Dwarf *dbg, int sec_index) 617 { 618 Elf_Data *data = dbg->sectiondata[sec_index]; 619 if (unlikely (data == NULL) 620 || unlikely (data->d_buf == NULL)) 621 { 622 __libdw_seterrno (DWARF_E_INVALID_DWARF); 623 return NULL; 624 } 625 return data; 626 } 627 628 static inline int 629 __libdw_offset_in_section (Dwarf *dbg, int sec_index, 630 Dwarf_Off offset, size_t size) 631 { 632 Elf_Data *data = __libdw_checked_get_data (dbg, sec_index); 633 if (data == NULL) 634 return -1; 635 if (unlikely (offset > data->d_size) 636 || unlikely (data->d_size - offset < size)) 637 { 638 __libdw_seterrno (DWARF_E_INVALID_OFFSET); 639 return -1; 640 } 641 642 return 0; 643 } 644 645 static inline bool 646 __libdw_in_section (Dwarf *dbg, int sec_index, 647 const void *addr, size_t size) 648 { 649 Elf_Data *data = __libdw_checked_get_data (dbg, sec_index); 650 if (data == NULL) 651 return false; 652 if (unlikely (addr < data->d_buf) 653 || unlikely (data->d_size - (addr - data->d_buf) < size)) 654 { 655 __libdw_seterrno (DWARF_E_INVALID_OFFSET); 656 return false; 657 } 658 659 return true; 660 } 661 662 #define READ_AND_RELOCATE(RELOC_HOOK, VAL) \ 663 ({ \ 664 if (!__libdw_in_section (dbg, sec_index, addr, width)) \ 665 return -1; \ 666 \ 667 const unsigned char *orig_addr = addr; \ 668 if (width == 4) \ 669 VAL = read_4ubyte_unaligned_inc (dbg, addr); \ 670 else \ 671 VAL = read_8ubyte_unaligned_inc (dbg, addr); \ 672 \ 673 int status = RELOC_HOOK (dbg, sec_index, orig_addr, width, &VAL); \ 674 if (status < 0) \ 675 return status; \ 676 status > 0; \ 677 }) 678 679 static inline int 680 __libdw_read_address_inc (Dwarf *dbg, 681 int sec_index, const unsigned char **addrp, 682 int width, Dwarf_Addr *ret) 683 { 684 const unsigned char *addr = *addrp; 685 READ_AND_RELOCATE (__libdw_relocate_address, (*ret)); 686 *addrp = addr; 687 return 0; 688 } 689 690 static inline int 691 __libdw_read_address (Dwarf *dbg, 692 int sec_index, const unsigned char *addr, 693 int width, Dwarf_Addr *ret) 694 { 695 READ_AND_RELOCATE (__libdw_relocate_address, (*ret)); 696 return 0; 697 } 698 699 static inline int 700 __libdw_read_offset_inc (Dwarf *dbg, 701 int sec_index, const unsigned char **addrp, 702 int width, Dwarf_Off *ret, int sec_ret, 703 size_t size) 704 { 705 const unsigned char *addr = *addrp; 706 READ_AND_RELOCATE (__libdw_relocate_offset, (*ret)); 707 *addrp = addr; 708 return __libdw_offset_in_section (dbg, sec_ret, *ret, size); 709 } 710 711 static inline int 712 __libdw_read_offset (Dwarf *dbg, Dwarf *dbg_ret, 713 int sec_index, const unsigned char *addr, 714 int width, Dwarf_Off *ret, int sec_ret, 715 size_t size) 716 { 717 READ_AND_RELOCATE (__libdw_relocate_offset, (*ret)); 718 return __libdw_offset_in_section (dbg_ret, sec_ret, *ret, size); 719 } 720 721 static inline size_t 722 cu_sec_idx (struct Dwarf_CU *cu) 723 { 724 return cu->type_offset == 0 ? IDX_debug_info : IDX_debug_types; 725 } 726 727 /* Read up begin/end pair and increment read pointer. 728 - If it's normal range record, set up *BEGINP and *ENDP and return 0. 729 - If it's base address selection record, set up *BASEP and return 1. 730 - If it's end of rangelist, don't set anything and return 2 731 - If an error occurs, don't set anything and return <0. */ 732 int __libdw_read_begin_end_pair_inc (Dwarf *dbg, int sec_index, 733 unsigned char **addr, int width, 734 Dwarf_Addr *beginp, Dwarf_Addr *endp, 735 Dwarf_Addr *basep) 736 internal_function; 737 738 unsigned char * __libdw_formptr (Dwarf_Attribute *attr, int sec_index, 739 int err_nodata, unsigned char **endpp, 740 Dwarf_Off *offsetp) 741 internal_function; 742 743 /* Fills in the given attribute to point at an empty location expression. */ 744 void __libdw_empty_loc_attr (Dwarf_Attribute *attr) 745 internal_function; 746 747 /* Load .debug_line unit at DEBUG_LINE_OFFSET. COMP_DIR is a value of 748 DW_AT_comp_dir or NULL if that attribute is not available. Caches 749 the loaded unit and optionally set *LINESP and/or *FILESP (if not 750 NULL) with loaded information. Returns 0 for success or a negative 751 value for failure. */ 752 int __libdw_getsrclines (Dwarf *dbg, Dwarf_Off debug_line_offset, 753 const char *comp_dir, unsigned address_size, 754 Dwarf_Lines **linesp, Dwarf_Files **filesp) 755 internal_function 756 __nonnull_attribute__ (1); 757 758 /* Load and return value of DW_AT_comp_dir from CUDIE. */ 759 const char *__libdw_getcompdir (Dwarf_Die *cudie); 760 761 762 /* Aliases to avoid PLTs. */ 763 INTDECL (dwarf_aggregate_size) 764 INTDECL (dwarf_attr) 765 INTDECL (dwarf_attr_integrate) 766 INTDECL (dwarf_begin) 767 INTDECL (dwarf_begin_elf) 768 INTDECL (dwarf_child) 769 INTDECL (dwarf_dieoffset) 770 INTDECL (dwarf_diename) 771 INTDECL (dwarf_end) 772 INTDECL (dwarf_entrypc) 773 INTDECL (dwarf_errmsg) 774 INTDECL (dwarf_formaddr) 775 INTDECL (dwarf_formblock) 776 INTDECL (dwarf_formref_die) 777 INTDECL (dwarf_formsdata) 778 INTDECL (dwarf_formstring) 779 INTDECL (dwarf_formudata) 780 INTDECL (dwarf_getalt) 781 INTDECL (dwarf_getarange_addr) 782 INTDECL (dwarf_getarangeinfo) 783 INTDECL (dwarf_getaranges) 784 INTDECL (dwarf_getlocation_die) 785 INTDECL (dwarf_getsrcfiles) 786 INTDECL (dwarf_getsrclines) 787 INTDECL (dwarf_hasattr) 788 INTDECL (dwarf_haschildren) 789 INTDECL (dwarf_haspc) 790 INTDECL (dwarf_highpc) 791 INTDECL (dwarf_lowpc) 792 INTDECL (dwarf_nextcu) 793 INTDECL (dwarf_next_unit) 794 INTDECL (dwarf_offdie) 795 INTDECL (dwarf_peel_type) 796 INTDECL (dwarf_ranges) 797 INTDECL (dwarf_setalt) 798 INTDECL (dwarf_siblingof) 799 INTDECL (dwarf_srclang) 800 INTDECL (dwarf_tag) 801 802 #endif /* libdwP.h */ 803