• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /* Internal definitions for libdw.
2    Copyright (C) 2002-2011, 2013-2018 Red Hat, Inc.
3    This file is part of elfutils.
4 
5    This file is free software; you can redistribute it and/or modify
6    it under the terms of either
7 
8      * the GNU Lesser General Public License as published by the Free
9        Software Foundation; either version 3 of the License, or (at
10        your option) any later version
11 
12    or
13 
14      * the GNU General Public License as published by the Free
15        Software Foundation; either version 2 of the License, or (at
16        your option) any later version
17 
18    or both in parallel, as here.
19 
20    elfutils is distributed in the hope that it will be useful, but
21    WITHOUT ANY WARRANTY; without even the implied warranty of
22    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
23    General Public License for more details.
24 
25    You should have received copies of the GNU General Public License and
26    the GNU Lesser General Public License along with this program.  If
27    not, see <http://www.gnu.org/licenses/>.  */
28 
29 #ifndef _LIBDWP_H
30 #define _LIBDWP_H 1
31 
32 #include <libintl.h>
33 #include <stdbool.h>
34 #include <pthread.h>
35 
36 #include <libdw.h>
37 #include <dwarf.h>
38 #include "atomics.h"
39 
40 
41 /* gettext helper macros.  */
42 #define _(Str) dgettext ("elfutils", Str)
43 
44 
45 /* Known location expressions already decoded.  */
46 struct loc_s
47 {
48   void *addr;
49   Dwarf_Op *loc;
50   size_t nloc;
51 };
52 
53 /* Known DW_OP_implicit_value blocks already decoded.
54    This overlaps struct loc_s exactly, but only the
55    first member really has to match.  */
56 struct loc_block_s
57 {
58   void *addr;
59   unsigned char *data;
60   size_t length;
61 };
62 
63 /* Already decoded .debug_line units.  */
64 struct files_lines_s
65 {
66   Dwarf_Off debug_line_offset;
67   Dwarf_Files *files;
68   Dwarf_Lines *lines;
69 };
70 
71 /* Valid indeces for the section data.  */
72 enum
73   {
74     IDX_debug_info = 0,
75     IDX_debug_types,
76     IDX_debug_abbrev,
77     IDX_debug_aranges,
78     IDX_debug_addr,
79     IDX_debug_line,
80     IDX_debug_line_str,
81     IDX_debug_frame,
82     IDX_debug_loc,
83     IDX_debug_loclists,
84     IDX_debug_pubnames,
85     IDX_debug_str,
86     IDX_debug_str_offsets,
87     IDX_debug_macinfo,
88     IDX_debug_macro,
89     IDX_debug_ranges,
90     IDX_debug_rnglists,
91     IDX_gnu_debugaltlink,
92     IDX_last
93   };
94 
95 
96 /* Error values.  */
97 enum
98 {
99   DWARF_E_NOERROR = 0,
100   DWARF_E_UNKNOWN_ERROR,
101   DWARF_E_INVALID_ACCESS,
102   DWARF_E_NO_REGFILE,
103   DWARF_E_IO_ERROR,
104   DWARF_E_INVALID_ELF,
105   DWARF_E_NO_DWARF,
106   DWARF_E_COMPRESSED_ERROR,
107   DWARF_E_NOELF,
108   DWARF_E_GETEHDR_ERROR,
109   DWARF_E_NOMEM,
110   DWARF_E_UNIMPL,
111   DWARF_E_INVALID_CMD,
112   DWARF_E_INVALID_VERSION,
113   DWARF_E_INVALID_FILE,
114   DWARF_E_NO_ENTRY,
115   DWARF_E_INVALID_DWARF,
116   DWARF_E_NO_STRING,
117   DWARF_E_NO_DEBUG_STR,
118   DWARF_E_NO_DEBUG_LINE_STR,
119   DWARF_E_NO_STR_OFFSETS,
120   DWARF_E_NO_ADDR,
121   DWARF_E_NO_CONSTANT,
122   DWARF_E_NO_REFERENCE,
123   DWARF_E_INVALID_REFERENCE,
124   DWARF_E_NO_DEBUG_LINE,
125   DWARF_E_INVALID_DEBUG_LINE,
126   DWARF_E_TOO_BIG,
127   DWARF_E_VERSION,
128   DWARF_E_INVALID_DIR_IDX,
129   DWARF_E_ADDR_OUTOFRANGE,
130   DWARF_E_NO_DEBUG_LOC,
131   DWARF_E_NO_DEBUG_LOCLISTS,
132   DWARF_E_NO_LOC_VALUE,
133   DWARF_E_NO_BLOCK,
134   DWARF_E_INVALID_LINE_IDX,
135   DWARF_E_INVALID_ARANGE_IDX,
136   DWARF_E_NO_MATCH,
137   DWARF_E_NO_FLAG,
138   DWARF_E_INVALID_OFFSET,
139   DWARF_E_NO_DEBUG_RANGES,
140   DWARF_E_NO_DEBUG_RNGLISTS,
141   DWARF_E_INVALID_CFI,
142   DWARF_E_NO_ALT_DEBUGLINK,
143   DWARF_E_INVALID_OPCODE,
144   DWARF_E_NOT_CUDIE,
145   DWARF_E_UNKNOWN_LANGUAGE,
146   DWARF_E_NO_DEBUG_ADDR,
147 };
148 
149 
150 #include "dwarf_sig8_hash.h"
151 
152 /* This is the structure representing the debugging state.  */
153 struct Dwarf
154 {
155   /* The underlying ELF file.  */
156   Elf *elf;
157 
158   /* The (absolute) path to the ELF dir, if known.  To help locating
159      alt and dwo files.  */
160   char *debugdir;
161 
162   /* dwz alternate DWARF file.  */
163   Dwarf *alt_dwarf;
164 
165   /* The section data.  */
166   Elf_Data *sectiondata[IDX_last];
167 
168   /* True if the file has a byte order different from the host.  */
169   bool other_byte_order;
170 
171   /* If true, we allocated the ELF descriptor ourselves.  */
172   bool free_elf;
173 
174   /* If >= 0, we allocated the alt_dwarf ourselves and must end it and
175      close this file descriptor.  */
176   int alt_fd;
177 
178   /* Information for traversing the .debug_pubnames section.  This is
179      an array and separately allocated with malloc.  */
180   struct pubnames_s
181   {
182     Dwarf_Off cu_offset;
183     Dwarf_Off set_start;
184     unsigned int cu_header_size;
185     int address_len;
186   } *pubnames_sets;
187   size_t pubnames_nsets;
188 
189   /* Search tree for the CUs.  */
190   void *cu_tree;
191   Dwarf_Off next_cu_offset;
192 
193   /* Search tree and sig8 hash table for .debug_types type units.  */
194   void *tu_tree;
195   Dwarf_Off next_tu_offset;
196   Dwarf_Sig8_Hash sig8_hash;
197 
198   /* Search tree for split Dwarf associated with CUs in this debug.  */
199   void *split_tree;
200 
201   /* Search tree for .debug_macro operator tables.  */
202   void *macro_ops;
203 
204   /* Search tree for decoded .debug_line units.  */
205   void *files_lines;
206 
207   /* Address ranges.  */
208   Dwarf_Aranges *aranges;
209 
210   /* Cached info from the CFI section.  */
211   struct Dwarf_CFI_s *cfi;
212 
213   /* Fake loc CU.  Used when synthesizing attributes for Dwarf_Ops that
214      came from a location list entry in dwarf_getlocation_attr.
215      Depending on version this is the .debug_loc or .debug_loclists
216      section (could be both if mixing CUs with different DWARF versions).  */
217   struct Dwarf_CU *fake_loc_cu;
218   struct Dwarf_CU *fake_loclists_cu;
219 
220   /* Similar for addrx/constx, which will come from .debug_addr section.  */
221   struct Dwarf_CU *fake_addr_cu;
222 
223   /* Supporting lock for internal memory handling.  Ensures threads that have
224      an entry in the mem_tails array are not disturbed by new threads doing
225      allocations for this Dwarf.  */
226   pthread_rwlock_t mem_rwl;
227 
228   /* Internal memory handling.  This is basically a simplified thread-local
229      reimplementation of obstacks.  Unfortunately the standard obstack
230      implementation is not usable in libraries.  */
231   size_t mem_stacks;
232   struct libdw_memblock
233   {
234     size_t size;
235     size_t remaining;
236     struct libdw_memblock *prev;
237     char mem[0];
238   } **mem_tails;
239 
240   /* Default size of allocated memory blocks.  */
241   size_t mem_default_size;
242 
243   /* Registered OOM handler.  */
244   Dwarf_OOM oom_handler;
245 };
246 
247 
248 /* Abbreviation representation.  */
249 struct Dwarf_Abbrev
250 {
251   Dwarf_Off offset;	  /* Offset to start of abbrev into .debug_abbrev.  */
252   unsigned char *attrp;   /* Pointer to start of attribute name/form pairs. */
253   bool has_children : 1;  /* Whether or not the DIE has children. */
254   unsigned int code : 31; /* The (unique) abbrev code.  */
255   unsigned int tag;	  /* The tag of the DIE. */
256 } attribute_packed;
257 
258 #include "dwarf_abbrev_hash.h"
259 
260 
261 /* Files in line information records.  */
262 struct Dwarf_Files_s
263   {
264     unsigned int ndirs;
265     unsigned int nfiles;
266     struct Dwarf_Fileinfo_s
267     {
268       char *name;
269       Dwarf_Word mtime;
270       Dwarf_Word length;
271     } info[0];
272     /* nfiles of those, followed by char *[ndirs].  */
273   };
274 typedef struct Dwarf_Fileinfo_s Dwarf_Fileinfo;
275 
276 
277 /* Representation of a row in the line table.  */
278 
279 struct Dwarf_Line_s
280 {
281   Dwarf_Files *files;
282 
283   Dwarf_Addr addr;
284   unsigned int file;
285   int line;
286   unsigned short int column;
287   unsigned int is_stmt:1;
288   unsigned int basic_block:1;
289   unsigned int end_sequence:1;
290   unsigned int prologue_end:1;
291   unsigned int epilogue_begin:1;
292   /* The remaining bit fields are not flags, but hold values presumed to be
293      small.  All the flags and other bit fields should add up to 48 bits
294      to give the whole struct a nice round size.  */
295   unsigned int op_index:8;
296   unsigned int isa:8;
297   unsigned int discriminator:24;
298 };
299 
300 struct Dwarf_Lines_s
301 {
302   size_t nlines;
303   struct Dwarf_Line_s info[0];
304 };
305 
306 /* Representation of address ranges.  */
307 struct Dwarf_Aranges_s
308 {
309   Dwarf *dbg;
310   size_t naranges;
311 
312   struct Dwarf_Arange_s
313   {
314     Dwarf_Addr addr;
315     Dwarf_Word length;
316     Dwarf_Off offset;
317   } info[0];
318 };
319 
320 
321 /* CU representation.  */
322 struct Dwarf_CU
323 {
324   Dwarf *dbg;
325   Dwarf_Off start;
326   Dwarf_Off end;
327   uint8_t address_size;
328   uint8_t offset_size;
329   uint16_t version;
330 
331   size_t sec_idx; /* Normally .debug_info, could be .debug_type or "fake". */
332 
333   /* The unit type if version >= 5.  Otherwise 0 for normal CUs (from
334      .debug_info) or 1 for v4 type units (from .debug_types).  */
335   uint8_t unit_type;
336 
337   /* Zero if the unit type doesn't support a die/type offset and/or id/sig.
338      Nonzero if it is a v4 type unit or for DWARFv5 units depending on
339      unit_type.  */
340   size_t subdie_offset;
341   uint64_t unit_id8;
342 
343   /* If this is a skeleton unit this points to the split compile unit.
344      Or the other way around if this is a split compile unit.  Set to -1
345      if not yet searched.  Always use __libdw_find_split_unit to access
346      this field.  */
347   struct Dwarf_CU *split;
348 
349   /* Hash table for the abbreviations.  */
350   Dwarf_Abbrev_Hash abbrev_hash;
351   /* Offset of the first abbreviation.  */
352   size_t orig_abbrev_offset;
353   /* Offset past last read abbreviation.  */
354   size_t last_abbrev_offset;
355 
356   /* The srcline information.  */
357   Dwarf_Lines *lines;
358 
359   /* The source file information.  */
360   Dwarf_Files *files;
361 
362   /* Known location lists.  */
363   void *locs;
364 
365   /* Base address for use with ranges and locs.
366      Don't access directly, call __libdw_cu_base_address.  */
367   Dwarf_Addr base_address;
368 
369   /* The offset into the .debug_addr section where index zero begins.
370      Don't access directly, call __libdw_cu_addr_base.  */
371   Dwarf_Off addr_base;
372 
373   /* The offset into the .debug_str_offsets section where index zero begins.
374      Don't access directly, call __libdw_cu_str_off_base.  */
375   Dwarf_Off str_off_base;
376 
377   /* The offset into the .debug_ranges section to use for GNU
378      DebugFission split units.  Don't access directly, call
379      __libdw_cu_ranges_base.  */
380   Dwarf_Off ranges_base;
381 
382   /* The start of the offset table in .debug_loclists.
383      Don't access directly, call __libdw_cu_locs_base.  */
384   Dwarf_Off locs_base;
385 
386   /* Memory boundaries of this CU.  */
387   void *startp;
388   void *endp;
389 };
390 
391 #define ISV4TU(cu) ((cu)->version == 4 && (cu)->sec_idx == IDX_debug_types)
392 
393 /* Compute the offset of a CU's first DIE from the CU offset.
394    CU must be a valid/known version/unit_type.  */
395 static inline Dwarf_Off
__libdw_first_die_from_cu_start(Dwarf_Off cu_start,uint8_t offset_size,uint16_t version,uint8_t unit_type)396 __libdw_first_die_from_cu_start (Dwarf_Off cu_start,
397 				 uint8_t offset_size,
398 				 uint16_t version,
399 				 uint8_t unit_type)
400 {
401 /*
402   assert (offset_size == 4 || offset_size == 8);
403   assert (version >= 2 && version <= 5);
404   assert (unit_type == DW_UT_compile
405 	  || unit_type == DW_UT_partial
406 	  || unit_type == DW_UT_skeleton
407 	  || unit_type == DW_UT_split_compile
408 	  || unit_type == DW_UT_type
409 	  || unit_type == DW_UT_split_type);
410 */
411 
412   Dwarf_Off off = cu_start;
413   if (version < 5)
414     {
415    /*
416         LEN       VER     OFFSET    ADDR
417       4-bytes + 2-bytes + 4-bytes + 1-byte  for 32-bit dwarf
418      12-bytes + 2-bytes + 8-bytes + 1-byte  for 64-bit dwarf
419    or in .debug_types, 			     SIGNATURE TYPE-OFFSET
420       4-bytes + 2-bytes + 4-bytes + 1-byte + 8-bytes + 4-bytes  for 32-bit
421      12-bytes + 2-bytes + 8-bytes + 1-byte + 8-bytes + 8-bytes  for 64-bit
422 
423    Note the trick in the computation.  If the offset_size is 4
424    the '- 4' term changes the '3 *' (or '4 *') into a '2 *' (or '3 *).
425    If the offset_size is 8 it accounts for the 4-byte escape value
426    used at the start of the length.  */
427       if (unit_type != DW_UT_type)
428 	off += 3 * offset_size - 4 + 3;
429       else
430 	off += 4 * offset_size - 4 + 3 + 8;
431     }
432   else
433     {
434      /*
435         LEN       VER      TYPE     ADDR     OFFSET   SIGNATURE  TYPE-OFFSET
436       4-bytes + 2-bytes + 1-byte + 1-byte + 4-bytes + 8-bytes + 4-bytes 32-bit
437      12-bytes + 2-bytes + 1-byte + 1-byte + 8-bytes + 8-bytes + 8-bytes 64-bit
438         Both signature and type offset are optional.
439 
440         Note same 4/8 offset size trick as above.
441         We explicitly ignore unknow unit types (see asserts above).  */
442       off += 3 * offset_size - 4 + 4;
443       if (unit_type == DW_UT_skeleton || unit_type == DW_UT_split_compile
444 	  || unit_type == DW_UT_type || unit_type == DW_UT_split_type)
445 	{
446 	  off += 8;
447 	  if (unit_type == DW_UT_type || unit_type == DW_UT_split_type)
448 	    off += offset_size;
449 	}
450     }
451 
452   return off;
453 }
454 
455 static inline Dwarf_Off
__libdw_first_die_off_from_cu(struct Dwarf_CU * cu)456 __libdw_first_die_off_from_cu (struct Dwarf_CU *cu)
457 {
458   return __libdw_first_die_from_cu_start (cu->start,
459 					  cu->offset_size,
460 					  cu->version,
461 					  cu->unit_type);
462 }
463 
464 #define CUDIE(fromcu)							      \
465   ((Dwarf_Die)								      \
466    {									      \
467      .cu = (fromcu),							      \
468      .addr = ((char *) (fromcu)->dbg->sectiondata[cu_sec_idx (fromcu)]->d_buf \
469 	      + __libdw_first_die_off_from_cu (fromcu))			      \
470    })
471 
472 #define SUBDIE(fromcu)							      \
473   ((Dwarf_Die)								      \
474    {									      \
475      .cu = (fromcu),							      \
476      .addr = ((char *) (fromcu)->dbg->sectiondata[cu_sec_idx (fromcu)]->d_buf \
477 	      + (fromcu)->start + (fromcu)->subdie_offset)		      \
478    })
479 
480 
481 /* Prototype of a single .debug_macro operator.  */
482 typedef struct
483 {
484   Dwarf_Word nforms;
485   unsigned char const *forms;
486 } Dwarf_Macro_Op_Proto;
487 
488 /* Prototype table.  */
489 typedef struct
490 {
491   /* Offset of .debug_macro section.  */
492   Dwarf_Off offset;
493 
494   /* Offset of associated .debug_line section.  */
495   Dwarf_Off line_offset;
496 
497   /* The source file information.  */
498   Dwarf_Files *files;
499 
500   /* If this macro unit was opened through dwarf_getmacros or
501      dwarf_getmacros_die, this caches value of DW_AT_comp_dir, if
502      present.  */
503   const char *comp_dir;
504 
505   /* Header length.  */
506   Dwarf_Half header_len;
507 
508   uint16_t version;
509   bool is_64bit;
510   uint8_t sec_index;	/* IDX_debug_macro or IDX_debug_macinfo.  */
511 
512   /* Shows where in TABLE each opcode is defined.  Since opcode 0 is
513      never used, it stores index of opcode X in X-1'th element.  The
514      value of 0xff means not stored at all.  */
515   unsigned char opcodes[255];
516 
517   /* Individual opcode prototypes.  */
518   Dwarf_Macro_Op_Proto table[];
519 } Dwarf_Macro_Op_Table;
520 
521 struct Dwarf_Macro_s
522 {
523   Dwarf_Macro_Op_Table *table;
524   Dwarf_Attribute *attributes;
525   uint8_t opcode;
526 };
527 
528 static inline Dwarf_Word
libdw_macro_nforms(Dwarf_Macro * macro)529 libdw_macro_nforms (Dwarf_Macro *macro)
530 {
531   return macro->table->table[macro->table->opcodes[macro->opcode - 1]].nforms;
532 }
533 
534 /* Returns true for any allowed FORM in the opcode_operands_table as
535    mentioned in the DWARF5 spec (6.3.1 Macro Information Header).
536    Or those mentioned in DWARF5 spec (6.2.4.2 Vendor-defined Content
537    Descriptions) for the directory/file table (plus DW_FORM_strp_sup).  */
538 static inline bool
libdw_valid_user_form(int form)539 libdw_valid_user_form (int form)
540 {
541   switch (form)
542     {
543       case DW_FORM_block:
544       case DW_FORM_block1:
545       case DW_FORM_block2:
546       case DW_FORM_block4:
547       case DW_FORM_data1:
548       case DW_FORM_data2:
549       case DW_FORM_data4:
550       case DW_FORM_data8:
551       case DW_FORM_data16:
552       case DW_FORM_flag:
553       case DW_FORM_line_strp:
554       case DW_FORM_sdata:
555       case DW_FORM_sec_offset:
556       case DW_FORM_string:
557       case DW_FORM_strp:
558       case DW_FORM_strp_sup:
559       case DW_FORM_strx:
560       case DW_FORM_strx1:
561       case DW_FORM_strx2:
562       case DW_FORM_strx3:
563       case DW_FORM_strx4:
564       case DW_FORM_udata:
565 	return true;
566       default:
567 	return false;
568     }
569 }
570 
571 
572 /* We have to include the file at this point because the inline
573    functions access internals of the Dwarf structure.  */
574 #include "memory-access.h"
575 
576 
577 /* Set error value.  */
578 extern void __libdw_seterrno (int value) internal_function;
579 
580 
581 /* Memory handling, the easy parts.  */
582 #define libdw_alloc(dbg, type, tsize, cnt) \
583   ({ struct libdw_memblock *_tail = __libdw_alloc_tail(dbg);		      \
584      size_t _required = (tsize) * (cnt);				      \
585      type *_result = (type *) (_tail->mem + (_tail->size - _tail->remaining));\
586      size_t _padding = ((__alignof (type)				      \
587 			 - ((uintptr_t) _result & (__alignof (type) - 1)))    \
588 			& (__alignof (type) - 1));			      \
589      if (unlikely (_tail->remaining < _required + _padding))		      \
590        _result = (type *) __libdw_allocate (dbg, _required, __alignof (type));\
591      else								      \
592        {								      \
593 	 _required += _padding;						      \
594 	 _result = (type *) ((char *) _result + _padding);		      \
595 	 _tail->remaining -= _required;					      \
596        }								      \
597      _result; })
598 
599 #define libdw_typed_alloc(dbg, type) \
600   libdw_alloc (dbg, type, sizeof (type), 1)
601 
602 /* Can only be used to undo the last libdw_alloc.  */
603 #define libdw_unalloc(dbg, type, tsize, cnt) \
604   ({ struct libdw_memblock *_tail = __libdw_thread_tail (dbg);		      \
605      size_t _required = (tsize) * (cnt);				      \
606      /* We cannot know the padding, it is lost.  */			      \
607      _tail->remaining += _required; })					      \
608 
609 #define libdw_typed_unalloc(dbg, type) \
610   libdw_unalloc (dbg, type, sizeof (type), 1)
611 
612 /* Callback to choose a thread-local memory allocation stack.  */
613 extern struct libdw_memblock *__libdw_alloc_tail (Dwarf* dbg)
614      __nonnull_attribute__ (1);
615 
616 extern struct libdw_memblock *__libdw_thread_tail (Dwarf* dbg)
617      __nonnull_attribute__ (1);
618 
619 /* Callback to allocate more.  */
620 extern void *__libdw_allocate (Dwarf *dbg, size_t minsize, size_t align)
621      __attribute__ ((__malloc__)) __nonnull_attribute__ (1);
622 
623 /* Default OOM handler.  */
624 extern void __libdw_oom (void) __attribute ((noreturn)) attribute_hidden;
625 
626 /* Read next unit (or v4 debug type) and return next offset.  Doesn't
627    create an actual Dwarf_CU just provides necessary header fields.  */
628 extern int
629 internal_function
630 __libdw_next_unit (Dwarf *dbg, bool v4_debug_types, Dwarf_Off off,
631 		   Dwarf_Off *next_off, size_t *header_sizep,
632 		   Dwarf_Half *versionp, uint8_t *unit_typep,
633 		   Dwarf_Off *abbrev_offsetp, uint8_t *address_sizep,
634 		   uint8_t *offset_sizep, uint64_t *unit_id8p,
635 		   Dwarf_Off *subdie_offsetp)
636      __nonnull_attribute__ (4) internal_function;
637 
638 /* Allocate the internal data for a unit not seen before.  */
639 extern struct Dwarf_CU *__libdw_intern_next_unit (Dwarf *dbg, bool debug_types)
640      __nonnull_attribute__ (1) internal_function;
641 
642 /* Find CU for given offset.  */
643 extern struct Dwarf_CU *__libdw_findcu (Dwarf *dbg, Dwarf_Off offset, bool tu)
644      __nonnull_attribute__ (1) internal_function;
645 
646 /* Find CU for given DIE address.  */
647 extern struct Dwarf_CU *__libdw_findcu_addr (Dwarf *dbg, void *addr)
648      __nonnull_attribute__ (1) internal_function;
649 
650 /* Find split Dwarf for given DIE address.  */
651 extern struct Dwarf *__libdw_find_split_dbg_addr (Dwarf *dbg, void *addr)
652      __nonnull_attribute__ (1) internal_function;
653 
654 /* Find the split (or skeleton) unit.  */
655 extern struct Dwarf_CU *__libdw_find_split_unit (Dwarf_CU *cu)
656      internal_function;
657 
658 /* Get abbreviation with given code.  */
659 extern Dwarf_Abbrev *__libdw_findabbrev (struct Dwarf_CU *cu,
660 					 unsigned int code)
661      __nonnull_attribute__ (1) internal_function;
662 
663 /* Get abbreviation at given offset.  */
664 extern Dwarf_Abbrev *__libdw_getabbrev (Dwarf *dbg, struct Dwarf_CU *cu,
665 					Dwarf_Off offset, size_t *lengthp,
666 					Dwarf_Abbrev *result)
667      __nonnull_attribute__ (1) internal_function;
668 
669 /* Get abbreviation of given DIE, and optionally set *READP to the DIE memory
670    just past the abbreviation code.  */
671 static inline Dwarf_Abbrev *
672 __nonnull_attribute__ (1)
__libdw_dieabbrev(Dwarf_Die * die,const unsigned char ** readp)673 __libdw_dieabbrev (Dwarf_Die *die, const unsigned char **readp)
674 {
675   /* Do we need to get the abbreviation, or need to read after the code?  */
676   if (die->abbrev == NULL || readp != NULL)
677     {
678       /* Get the abbreviation code.  */
679       unsigned int code;
680       const unsigned char *addr = die->addr;
681       if (unlikely (die->cu == NULL
682 		    || addr >= (const unsigned char *) die->cu->endp))
683 	return die->abbrev = DWARF_END_ABBREV;
684       get_uleb128 (code, addr, die->cu->endp);
685       if (readp != NULL)
686 	*readp = addr;
687 
688       /* Find the abbreviation.  */
689       if (die->abbrev == NULL)
690 	die->abbrev = __libdw_findabbrev (die->cu, code);
691     }
692   return die->abbrev;
693 }
694 
695 /* Helper functions for form handling.  */
696 extern size_t __libdw_form_val_compute_len (struct Dwarf_CU *cu,
697 					    unsigned int form,
698 					    const unsigned char *valp)
699      __nonnull_attribute__ (1, 3) internal_function;
700 
701 /* Find the length of a form attribute in DIE/info data.  */
702 static inline size_t
703 __nonnull_attribute__ (1, 3)
__libdw_form_val_len(struct Dwarf_CU * cu,unsigned int form,const unsigned char * valp)704 __libdw_form_val_len (struct Dwarf_CU *cu, unsigned int form,
705 		      const unsigned char *valp)
706 {
707   /* Small lookup table of forms with fixed lengths.  Absent indexes are
708      initialized 0, so any truly desired 0 is set to 0x80 and masked.  */
709   static const uint8_t form_lengths[] =
710     {
711       [DW_FORM_flag_present] = 0x80,
712       [DW_FORM_implicit_const] = 0x80, /* Value is in abbrev, not in info.  */
713 
714       [DW_FORM_flag] = 1,
715       [DW_FORM_data1] = 1, [DW_FORM_ref1] = 1,
716       [DW_FORM_addrx1] = 1, [DW_FORM_strx1] = 1,
717 
718       [DW_FORM_data2] = 2, [DW_FORM_ref2] = 2,
719       [DW_FORM_addrx2] = 2, [DW_FORM_strx2] = 2,
720 
721       [DW_FORM_addrx3] = 3, [DW_FORM_strx3] = 3,
722 
723       [DW_FORM_data4] = 4, [DW_FORM_ref4] = 4, [DW_FORM_ref_sup4] = 4,
724       [DW_FORM_addrx4] = 4, [DW_FORM_strx4] = 4,
725 
726       [DW_FORM_ref_sig8] = 8,
727       [DW_FORM_data8] = 8, [DW_FORM_ref8] = 8, [DW_FORM_ref_sup8] = 8,
728 
729       [DW_FORM_data16] = 16,
730     };
731 
732   /* Return immediately for forms with fixed lengths.  */
733   if (form < sizeof form_lengths / sizeof form_lengths[0])
734     {
735       uint8_t len = form_lengths[form];
736       if (len != 0)
737 	{
738 	  const unsigned char *endp = cu->endp;
739 	  len &= 0x7f; /* Mask to allow 0x80 -> 0.  */
740 	  if (unlikely (len > (size_t) (endp - valp)))
741 	    {
742 	      __libdw_seterrno (DWARF_E_INVALID_DWARF);
743 	      return -1;
744 	    }
745 	  return len;
746 	}
747     }
748 
749   /* Other forms require some computation.  */
750   return __libdw_form_val_compute_len (cu, form, valp);
751 }
752 
753 /* Helper function for DW_FORM_ref* handling.  */
754 extern int __libdw_formref (Dwarf_Attribute *attr, Dwarf_Off *return_offset)
755      __nonnull_attribute__ (1, 2) internal_function;
756 
757 
758 /* Helper function to locate attribute.  */
759 extern unsigned char *__libdw_find_attr (Dwarf_Die *die,
760 					 unsigned int search_name,
761 					 unsigned int *codep,
762 					 unsigned int *formp)
763      __nonnull_attribute__ (1) internal_function;
764 
765 /* Helper function to access integer attribute.  */
766 extern int __libdw_attr_intval (Dwarf_Die *die, int *valp, int attval)
767      __nonnull_attribute__ (1, 2) internal_function;
768 
769 /* Helper function to walk scopes.  */
770 struct Dwarf_Die_Chain
771 {
772   Dwarf_Die die;
773   struct Dwarf_Die_Chain *parent;
774   bool prune;			/* The PREVISIT function can set this.  */
775 };
776 extern int __libdw_visit_scopes (unsigned int depth,
777 				 struct Dwarf_Die_Chain *root,
778 				 struct Dwarf_Die_Chain *imports,
779 				 int (*previsit) (unsigned int depth,
780 						  struct Dwarf_Die_Chain *,
781 						  void *arg),
782 				 int (*postvisit) (unsigned int depth,
783 						   struct Dwarf_Die_Chain *,
784 						   void *arg),
785 				 void *arg)
786   __nonnull_attribute__ (2, 4) internal_function;
787 
788 /* Parse a DWARF Dwarf_Block into an array of Dwarf_Op's,
789    and cache the result (via tsearch).  */
790 extern int __libdw_intern_expression (Dwarf *dbg,
791 				      bool other_byte_order,
792 				      unsigned int address_size,
793 				      unsigned int ref_size,
794 				      void **cache, const Dwarf_Block *block,
795 				      bool cfap, bool valuep,
796 				      Dwarf_Op **llbuf, size_t *listlen,
797 				      int sec_index)
798   __nonnull_attribute__ (5, 6, 9, 10) internal_function;
799 
800 extern Dwarf_Die *__libdw_offdie (Dwarf *dbg, Dwarf_Off offset,
801 				  Dwarf_Die *result, bool debug_types)
802   internal_function;
803 
804 
805 /* Return error code of last failing function call.  This value is kept
806    separately for each thread.  */
807 extern int __dwarf_errno_internal (void);
808 
809 
810 /* Reader hooks.  */
811 
812 /* Relocation hooks return -1 on error (in that case the error code
813    must already have been set), 0 if there is no relocation and 1 if a
814    relocation was present.*/
815 
816 static inline int
__libdw_relocate_address(Dwarf * dbg,int sec_index,const void * addr,int width,Dwarf_Addr * val)817 __libdw_relocate_address (Dwarf *dbg __attribute__ ((unused)),
818 			  int sec_index __attribute__ ((unused)),
819 			  const void *addr __attribute__ ((unused)),
820 			  int width __attribute__ ((unused)),
821 			  Dwarf_Addr *val __attribute__ ((unused)))
822 {
823   return 0;
824 }
825 
826 static inline int
__libdw_relocate_offset(Dwarf * dbg,int sec_index,const void * addr,int width,Dwarf_Off * val)827 __libdw_relocate_offset (Dwarf *dbg __attribute__ ((unused)),
828 			 int sec_index __attribute__ ((unused)),
829 			 const void *addr __attribute__ ((unused)),
830 			 int width __attribute__ ((unused)),
831 			 Dwarf_Off *val __attribute__ ((unused)))
832 {
833   return 0;
834 }
835 
836 static inline Elf_Data *
__libdw_checked_get_data(Dwarf * dbg,int sec_index)837 __libdw_checked_get_data (Dwarf *dbg, int sec_index)
838 {
839   Elf_Data *data = dbg->sectiondata[sec_index];
840   if (unlikely (data == NULL)
841       || unlikely (data->d_buf == NULL))
842     {
843       __libdw_seterrno (DWARF_E_INVALID_DWARF);
844       return NULL;
845     }
846   return data;
847 }
848 
849 static inline int
__libdw_offset_in_section(Dwarf * dbg,int sec_index,Dwarf_Off offset,size_t size)850 __libdw_offset_in_section (Dwarf *dbg, int sec_index,
851 			   Dwarf_Off offset, size_t size)
852 {
853   Elf_Data *data = __libdw_checked_get_data (dbg, sec_index);
854   if (data == NULL)
855     return -1;
856   if (unlikely (offset > data->d_size)
857       || unlikely (data->d_size < size)
858       || unlikely (offset > data->d_size - size))
859     {
860       __libdw_seterrno (DWARF_E_INVALID_OFFSET);
861       return -1;
862     }
863 
864   return 0;
865 }
866 
867 static inline bool
__libdw_in_section(Dwarf * dbg,int sec_index,const void * addr,size_t size)868 __libdw_in_section (Dwarf *dbg, int sec_index,
869 		    const void *addr, size_t size)
870 {
871   Elf_Data *data = __libdw_checked_get_data (dbg, sec_index);
872   if (data == NULL)
873     return false;
874   if (unlikely (addr < data->d_buf)
875       || unlikely (data->d_size < size)
876       || unlikely ((size_t)(addr - data->d_buf) > data->d_size - size))
877     {
878       __libdw_seterrno (DWARF_E_INVALID_OFFSET);
879       return false;
880     }
881 
882   return true;
883 }
884 
885 #define READ_AND_RELOCATE(RELOC_HOOK, VAL)				\
886   ({									\
887     if (!__libdw_in_section (dbg, sec_index, addr, width))		\
888       return -1;							\
889 									\
890     const unsigned char *orig_addr = addr;				\
891     if (width == 4)							\
892       VAL = read_4ubyte_unaligned_inc (dbg, addr);			\
893     else								\
894       VAL = read_8ubyte_unaligned_inc (dbg, addr);			\
895 									\
896     int status = RELOC_HOOK (dbg, sec_index, orig_addr, width, &VAL);	\
897     if (status < 0)							\
898       return status;							\
899     status > 0;								\
900    })
901 
902 static inline int
__libdw_read_address_inc(Dwarf * dbg,int sec_index,const unsigned char ** addrp,int width,Dwarf_Addr * ret)903 __libdw_read_address_inc (Dwarf *dbg,
904 			  int sec_index, const unsigned char **addrp,
905 			  int width, Dwarf_Addr *ret)
906 {
907   const unsigned char *addr = *addrp;
908   READ_AND_RELOCATE (__libdw_relocate_address, (*ret));
909   *addrp = addr;
910   return 0;
911 }
912 
913 static inline int
__libdw_read_address(Dwarf * dbg,int sec_index,const unsigned char * addr,int width,Dwarf_Addr * ret)914 __libdw_read_address (Dwarf *dbg,
915 		      int sec_index, const unsigned char *addr,
916 		      int width, Dwarf_Addr *ret)
917 {
918   READ_AND_RELOCATE (__libdw_relocate_address, (*ret));
919   return 0;
920 }
921 
922 static inline int
__libdw_read_offset_inc(Dwarf * dbg,int sec_index,const unsigned char ** addrp,int width,Dwarf_Off * ret,int sec_ret,size_t size)923 __libdw_read_offset_inc (Dwarf *dbg,
924 			 int sec_index, const unsigned char **addrp,
925 			 int width, Dwarf_Off *ret, int sec_ret,
926 			 size_t size)
927 {
928   const unsigned char *addr = *addrp;
929   READ_AND_RELOCATE (__libdw_relocate_offset, (*ret));
930   *addrp = addr;
931   return __libdw_offset_in_section (dbg, sec_ret, *ret, size);
932 }
933 
934 static inline int
__libdw_read_offset(Dwarf * dbg,Dwarf * dbg_ret,int sec_index,const unsigned char * addr,int width,Dwarf_Off * ret,int sec_ret,size_t size)935 __libdw_read_offset (Dwarf *dbg, Dwarf *dbg_ret,
936 		     int sec_index, const unsigned char *addr,
937 		     int width, Dwarf_Off *ret, int sec_ret,
938 		     size_t size)
939 {
940   READ_AND_RELOCATE (__libdw_relocate_offset, (*ret));
941   return __libdw_offset_in_section (dbg_ret, sec_ret, *ret, size);
942 }
943 
944 static inline size_t
cu_sec_idx(struct Dwarf_CU * cu)945 cu_sec_idx (struct Dwarf_CU *cu)
946 {
947   return cu->sec_idx;
948 }
949 
950 static inline bool
is_cudie(Dwarf_Die * cudie)951 is_cudie (Dwarf_Die *cudie)
952 {
953   return cudie->cu != NULL && CUDIE (cudie->cu).addr == cudie->addr;
954 }
955 
956 /* Read up begin/end pair and increment read pointer.
957     - If it's normal range record, set up *BEGINP and *ENDP and return 0.
958     - If it's base address selection record, set up *BASEP and return 1.
959     - If it's end of rangelist, don't set anything and return 2
960     - If an error occurs, don't set anything and return <0.  */
961 int __libdw_read_begin_end_pair_inc (Dwarf_CU *cu, int sec_index,
962 				     const unsigned char **readp,
963 				     const unsigned char *readend,
964 				     int width,
965 				     Dwarf_Addr *beginp, Dwarf_Addr *endp,
966 				     Dwarf_Addr *basep)
967   internal_function;
968 
969 const unsigned char * __libdw_formptr (Dwarf_Attribute *attr, int sec_index,
970 				       int err_nodata,
971 				       const unsigned char **endpp,
972 				       Dwarf_Off *offsetp)
973   internal_function;
974 
975 /* Fills in the given attribute to point at an empty location expression.  */
976 void __libdw_empty_loc_attr (Dwarf_Attribute *attr)
977   internal_function;
978 
979 /* Load .debug_line unit at DEBUG_LINE_OFFSET.  COMP_DIR is a value of
980    DW_AT_comp_dir or NULL if that attribute is not available.  Caches
981    the loaded unit and optionally set *LINESP and/or *FILESP (if not
982    NULL) with loaded information.  Returns 0 for success or a negative
983    value for failure.  */
984 int __libdw_getsrclines (Dwarf *dbg, Dwarf_Off debug_line_offset,
985 			 const char *comp_dir, unsigned address_size,
986 			 Dwarf_Lines **linesp, Dwarf_Files **filesp)
987   internal_function
988   __nonnull_attribute__ (1);
989 
990 /* Load and return value of DW_AT_comp_dir from CUDIE.  */
991 const char *__libdw_getcompdir (Dwarf_Die *cudie);
992 
993 /* Get the base address for the CU, fetches it when not yet set.
994    This is used as initial base address for ranges and loclists.  */
995 Dwarf_Addr __libdw_cu_base_address (Dwarf_CU *cu);
996 
997 /* Get the address base for the CU, fetches it when not yet set.  */
998 static inline Dwarf_Off
__libdw_cu_addr_base(Dwarf_CU * cu)999 __libdw_cu_addr_base (Dwarf_CU *cu)
1000 {
1001   if (cu->addr_base == (Dwarf_Off) -1)
1002     {
1003       Dwarf_Die cu_die = CUDIE(cu);
1004       Dwarf_Attribute attr;
1005       Dwarf_Off offset = 0;
1006       if (dwarf_attr (&cu_die, DW_AT_GNU_addr_base, &attr) != NULL
1007 	  || dwarf_attr (&cu_die, DW_AT_addr_base, &attr) != NULL)
1008 	{
1009 	  Dwarf_Word off;
1010 	  if (dwarf_formudata (&attr, &off) == 0)
1011 	    offset = off;
1012 	}
1013       cu->addr_base = offset;
1014     }
1015 
1016   return cu->addr_base;
1017 }
1018 
1019 /* Gets the .debug_str_offsets base offset to use.  static inline to
1020    be shared between libdw and eu-readelf.  */
1021 static inline Dwarf_Off
str_offsets_base_off(Dwarf * dbg,Dwarf_CU * cu)1022 str_offsets_base_off (Dwarf *dbg, Dwarf_CU *cu)
1023 {
1024   /* If we don't have a CU, then find and use the first one in the
1025      debug file (when we support .dwp files, we must actually find the
1026      one matching our "caller" - aka macro or line).  If we (now) have
1027      a cu and str_offsets_base attribute, just use that.  Otherwise
1028      use the first offset.  But we might have to parse the header
1029      first, but only if this is version 5.  Assume if all else fails,
1030      this is version 4, without header.  */
1031 
1032   if (cu == NULL && dbg != NULL)
1033     {
1034       Dwarf_CU *first_cu;
1035       if (dwarf_get_units (dbg, NULL, &first_cu,
1036 			   NULL, NULL, NULL, NULL) == 0)
1037 	cu = first_cu;
1038     }
1039 
1040   if (cu != NULL)
1041     {
1042       if (cu->str_off_base == (Dwarf_Off) -1)
1043 	{
1044 	  Dwarf_Die cu_die = CUDIE(cu);
1045 	  Dwarf_Attribute attr;
1046 	  if (dwarf_attr (&cu_die, DW_AT_str_offsets_base, &attr) != NULL)
1047 	    {
1048 	      Dwarf_Word off;
1049 	      if (dwarf_formudata (&attr, &off) == 0)
1050 		{
1051 		  cu->str_off_base = off;
1052 		  return cu->str_off_base;
1053 		}
1054 	    }
1055 	  /* For older DWARF simply assume zero (no header).  */
1056 	  if (cu->version < 5)
1057 	    {
1058 	      cu->str_off_base = 0;
1059 	      return cu->str_off_base;
1060 	    }
1061 
1062 	  if (dbg == NULL)
1063 	    dbg = cu->dbg;
1064 	}
1065       else
1066 	return cu->str_off_base;
1067     }
1068 
1069   /* No str_offsets_base attribute, we have to assume "zero".
1070      But there could be a header first.  */
1071   Dwarf_Off off = 0;
1072   if (dbg == NULL)
1073     goto no_header;
1074 
1075   Elf_Data *data =  dbg->sectiondata[IDX_debug_str_offsets];
1076   if (data == NULL)
1077     goto no_header;
1078 
1079   const unsigned char *start;
1080   const unsigned char *readp;
1081   const unsigned char *readendp;
1082   start = readp = (const unsigned char *) data->d_buf;
1083   readendp = (const unsigned char *) data->d_buf + data->d_size;
1084 
1085   uint64_t unit_length;
1086   uint16_t version;
1087 
1088   unit_length = read_4ubyte_unaligned_inc (dbg, readp);
1089   if (unlikely (unit_length == 0xffffffff))
1090     {
1091       if (unlikely (readendp - readp < 8))
1092 	goto no_header;
1093       unit_length = read_8ubyte_unaligned_inc (dbg, readp);
1094       /* In theory the offset size could be different
1095 	 between CU and str_offsets unit.  But we just
1096 	 ignore that here. */
1097     }
1098 
1099   /* We need at least 2-bytes (version) + 2-bytes (padding) =
1100      4 bytes to complete the header.  And this unit cannot go
1101      beyond the section data.  */
1102   if (readendp - readp < 4
1103       || unit_length < 4
1104       || (uint64_t) (readendp - readp) < unit_length)
1105     goto no_header;
1106 
1107   version = read_2ubyte_unaligned_inc (dbg, readp);
1108   if (version != 5)
1109     goto no_header;
1110   /* padding */
1111   read_2ubyte_unaligned_inc (dbg, readp);
1112 
1113   off = (Dwarf_Off) (readp - start);
1114 
1115  no_header:
1116   if (cu != NULL)
1117     cu->str_off_base = off;
1118 
1119   return off;
1120 }
1121 
1122 
1123 /* Get the string offsets base for the CU, fetches it when not yet set.  */
__libdw_cu_str_off_base(Dwarf_CU * cu)1124 static inline Dwarf_Off __libdw_cu_str_off_base (Dwarf_CU *cu)
1125 {
1126   return str_offsets_base_off (NULL, cu);
1127 }
1128 
1129 
1130 /* Either a direct offset into .debug_ranges for version < 5, or the
1131    start of the offset table in .debug_rnglists for version > 5.  */
1132 static inline Dwarf_Off
__libdw_cu_ranges_base(Dwarf_CU * cu)1133 __libdw_cu_ranges_base (Dwarf_CU *cu)
1134 {
1135   if (cu->ranges_base == (Dwarf_Off) -1)
1136     {
1137       Dwarf_Off offset = 0;
1138       Dwarf_Die cu_die = CUDIE(cu);
1139       Dwarf_Attribute attr;
1140       if (cu->version < 5)
1141 	{
1142 	  if (dwarf_attr (&cu_die, DW_AT_GNU_ranges_base, &attr) != NULL)
1143 	    {
1144 	      Dwarf_Word off;
1145 	      if (dwarf_formudata (&attr, &off) == 0)
1146 		offset = off;
1147 	    }
1148 	}
1149       else
1150 	{
1151 	  if (dwarf_attr (&cu_die, DW_AT_rnglists_base, &attr) != NULL)
1152 	    {
1153 	      Dwarf_Word off;
1154 	      if (dwarf_formudata (&attr, &off) == 0)
1155 		offset = off;
1156 	    }
1157 
1158 	  /* There wasn't an rnglists_base, if the Dwarf does have a
1159 	     .debug_rnglists section, then it might be we need the
1160 	     base after the first header. */
1161 	  Elf_Data *data = cu->dbg->sectiondata[IDX_debug_rnglists];
1162 	  if (offset == 0 && data != NULL)
1163 	    {
1164 	      Dwarf *dbg = cu->dbg;
1165 	      const unsigned char *readp = data->d_buf;
1166 	      const unsigned char *const dataend
1167 		= (unsigned char *) data->d_buf + data->d_size;
1168 
1169 	      uint64_t unit_length = read_4ubyte_unaligned_inc (dbg, readp);
1170 	      unsigned int offset_size = 4;
1171 	      if (unlikely (unit_length == 0xffffffff))
1172 		{
1173 		  if (unlikely (readp > dataend - 8))
1174 		    goto no_header;
1175 
1176 		  unit_length = read_8ubyte_unaligned_inc (dbg, readp);
1177 		  offset_size = 8;
1178 		}
1179 
1180 	      if (readp > dataend - 8
1181 		  || unit_length < 8
1182 		  || unit_length > (uint64_t) (dataend - readp))
1183 		goto no_header;
1184 
1185 	      uint16_t version = read_2ubyte_unaligned_inc (dbg, readp);
1186 	      if (version != 5)
1187 		goto no_header;
1188 
1189 	      uint8_t address_size = *readp++;
1190 	      if (address_size != 4 && address_size != 8)
1191 		goto no_header;
1192 
1193 	      uint8_t segment_size = *readp++;
1194 	      if (segment_size != 0)
1195 		goto no_header;
1196 
1197 	      uint32_t offset_entry_count;
1198 	      offset_entry_count = read_4ubyte_unaligned_inc (dbg, readp);
1199 
1200 	      const unsigned char *offset_array_start = readp;
1201 	      if (offset_entry_count <= 0)
1202 		goto no_header;
1203 
1204 	      uint64_t needed = offset_entry_count * offset_size;
1205 	      if (unit_length - 8 < needed)
1206 		goto no_header;
1207 
1208 	      offset = (Dwarf_Off) (offset_array_start
1209 				    - (unsigned char *) data->d_buf);
1210 	    }
1211 	}
1212     no_header:
1213       cu->ranges_base = offset;
1214     }
1215 
1216   return cu->ranges_base;
1217 }
1218 
1219 
1220 /* The start of the offset table in .debug_loclists for DWARF5.  */
1221 static inline Dwarf_Off
__libdw_cu_locs_base(Dwarf_CU * cu)1222 __libdw_cu_locs_base (Dwarf_CU *cu)
1223 {
1224   if (cu->locs_base == (Dwarf_Off) -1)
1225     {
1226       Dwarf_Off offset = 0;
1227       Dwarf_Die cu_die = CUDIE(cu);
1228       Dwarf_Attribute attr;
1229       if (dwarf_attr (&cu_die, DW_AT_loclists_base, &attr) != NULL)
1230 	{
1231 	  Dwarf_Word off;
1232 	  if (dwarf_formudata (&attr, &off) == 0)
1233 	    offset = off;
1234 	}
1235 
1236       /* There wasn't an loclists_base, if the Dwarf does have a
1237 	 .debug_loclists section, then it might be we need the
1238 	 base after the first header. */
1239       Elf_Data *data = cu->dbg->sectiondata[IDX_debug_loclists];
1240       if (offset == 0 && data != NULL)
1241 	{
1242 	  Dwarf *dbg = cu->dbg;
1243 	  const unsigned char *readp = data->d_buf;
1244 	  const unsigned char *const dataend
1245 	    = (unsigned char *) data->d_buf + data->d_size;
1246 
1247 	  uint64_t unit_length = read_4ubyte_unaligned_inc (dbg, readp);
1248 	  unsigned int offset_size = 4;
1249 	  if (unlikely (unit_length == 0xffffffff))
1250 	    {
1251 	      if (unlikely (readp > dataend - 8))
1252 		goto no_header;
1253 
1254 	      unit_length = read_8ubyte_unaligned_inc (dbg, readp);
1255 	      offset_size = 8;
1256 	    }
1257 
1258 	  if (readp > dataend - 8
1259 	      || unit_length < 8
1260 	      || unit_length > (uint64_t) (dataend - readp))
1261 	    goto no_header;
1262 
1263 	  uint16_t version = read_2ubyte_unaligned_inc (dbg, readp);
1264 	  if (version != 5)
1265 	    goto no_header;
1266 
1267 	  uint8_t address_size = *readp++;
1268 	  if (address_size != 4 && address_size != 8)
1269 	    goto no_header;
1270 
1271 	  uint8_t segment_size = *readp++;
1272 	  if (segment_size != 0)
1273 	    goto no_header;
1274 
1275 	  uint32_t offset_entry_count;
1276 	  offset_entry_count = read_4ubyte_unaligned_inc (dbg, readp);
1277 
1278 	  const unsigned char *offset_array_start = readp;
1279 	  if (offset_entry_count <= 0)
1280 	    goto no_header;
1281 
1282 	  uint64_t needed = offset_entry_count * offset_size;
1283 	  if (unit_length - 8 < needed)
1284 	    goto no_header;
1285 
1286 	  offset = (Dwarf_Off) (offset_array_start
1287 				- (unsigned char *) data->d_buf);
1288 	}
1289 
1290     no_header:
1291       cu->locs_base = offset;
1292     }
1293 
1294   return cu->locs_base;
1295 }
1296 
1297 /* Helper function for tsearch/tfind split_tree Dwarf.  */
1298 int __libdw_finddbg_cb (const void *arg1, const void *arg2);
1299 
1300 /* Link skeleton and split compile units.  */
1301 static inline void
__libdw_link_skel_split(Dwarf_CU * skel,Dwarf_CU * split)1302 __libdw_link_skel_split (Dwarf_CU *skel, Dwarf_CU *split)
1303 {
1304   skel->split = split;
1305   split->split = skel;
1306 
1307   /* Get .debug_addr and addr_base greedy.
1308      We also need it for the fake addr cu.
1309      There is only one per split debug.  */
1310   Dwarf *dbg = skel->dbg;
1311   Dwarf *sdbg = split->dbg;
1312   if (sdbg->sectiondata[IDX_debug_addr] == NULL
1313       && dbg->sectiondata[IDX_debug_addr] != NULL)
1314     {
1315       sdbg->sectiondata[IDX_debug_addr]
1316 	= dbg->sectiondata[IDX_debug_addr];
1317       split->addr_base = __libdw_cu_addr_base (skel);
1318       sdbg->fake_addr_cu = dbg->fake_addr_cu;
1319     }
1320 }
1321 
1322 
1323 /* Given an address index for a CU return the address.
1324    Returns -1 and sets libdw_errno if an error occurs.  */
1325 int __libdw_addrx (Dwarf_CU *cu, Dwarf_Word idx, Dwarf_Addr *addr);
1326 
1327 
1328 /* Helper function to set debugdir field in Dwarf, used from dwarf_begin_elf
1329    and libdwfl process_file.  */
1330 char * __libdw_debugdir (int fd);
1331 
1332 
1333 /* Given the directory of a debug file, an absolute or relative dir
1334    to look in, and file returns a full path.
1335 
1336    If the file is absolute (starts with a /) a copy of file is returned.
1337    the file isn't absolute, but dir is absolute, then a path that is
1338    the concatenation of dir and file is returned.  If neither file,
1339    nor dir is absolute, the path will be constructed using dir (if not
1340    NULL) and file relative to the debugdir (if valid).
1341 
1342    The debugdir and the dir may be NULL (in which case they aren't used).
1343    If file is NULL, or no full path can be constructed NULL is returned.
1344 
1345    The caller is responsible for freeing the result if not NULL.  */
1346 char * __libdw_filepath (const char *debugdir, const char *dir,
1347 			 const char *file)
1348   internal_function;
1349 
1350 
1351 /* Aliases to avoid PLTs.  */
1352 INTDECL (dwarf_aggregate_size)
1353 INTDECL (dwarf_attr)
1354 INTDECL (dwarf_attr_integrate)
1355 INTDECL (dwarf_begin)
1356 INTDECL (dwarf_begin_elf)
1357 INTDECL (dwarf_child)
1358 INTDECL (dwarf_default_lower_bound)
1359 INTDECL (dwarf_dieoffset)
1360 INTDECL (dwarf_diename)
1361 INTDECL (dwarf_end)
1362 INTDECL (dwarf_entrypc)
1363 INTDECL (dwarf_errmsg)
1364 INTDECL (dwarf_formaddr)
1365 INTDECL (dwarf_formblock)
1366 INTDECL (dwarf_formref_die)
1367 INTDECL (dwarf_formsdata)
1368 INTDECL (dwarf_formstring)
1369 INTDECL (dwarf_formudata)
1370 INTDECL (dwarf_getabbrevattr_data)
1371 INTDECL (dwarf_getalt)
1372 INTDECL (dwarf_getarange_addr)
1373 INTDECL (dwarf_getarangeinfo)
1374 INTDECL (dwarf_getaranges)
1375 INTDECL (dwarf_getlocation_die)
1376 INTDECL (dwarf_getsrcfiles)
1377 INTDECL (dwarf_getsrclines)
1378 INTDECL (dwarf_hasattr)
1379 INTDECL (dwarf_haschildren)
1380 INTDECL (dwarf_haspc)
1381 INTDECL (dwarf_highpc)
1382 INTDECL (dwarf_lowpc)
1383 INTDECL (dwarf_nextcu)
1384 INTDECL (dwarf_next_unit)
1385 INTDECL (dwarf_offdie)
1386 INTDECL (dwarf_peel_type)
1387 INTDECL (dwarf_ranges)
1388 INTDECL (dwarf_setalt)
1389 INTDECL (dwarf_siblingof)
1390 INTDECL (dwarf_srclang)
1391 INTDECL (dwarf_tag)
1392 
1393 #endif	/* libdwP.h */
1394