81d10944deac0c747ab85a5395f420ab56d34c15
[platform/upstream/elfutils.git] / src / readelf.c
1 /* Print information from ELF file in human-readable form.
2    Copyright (C) 1999-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 the GNU General Public License as published by
7    the Free Software Foundation; either version 3 of the License, or
8    (at your option) any later version.
9
10    elfutils is distributed in the hope that it will be useful, but
11    WITHOUT ANY WARRANTY; without even the implied warranty of
12    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13    GNU General Public License for more details.
14
15    You should have received a copy of the GNU General Public License
16    along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
17
18 #ifdef HAVE_CONFIG_H
19 # include <config.h>
20 #endif
21
22 #include <argp.h>
23 #include <assert.h>
24 #include <ctype.h>
25 #include <dwarf.h>
26 #include <errno.h>
27 #include <error.h>
28 #include <fcntl.h>
29 #include <gelf.h>
30 #include <inttypes.h>
31 #include <langinfo.h>
32 #include <libdw.h>
33 #include <libdwfl.h>
34 #include <libintl.h>
35 #include <locale.h>
36 #include <stdarg.h>
37 #include <stdbool.h>
38 #include <stdio.h>
39 #include <stdio_ext.h>
40 #include <stdlib.h>
41 #include <string.h>
42 #include <strings.h>
43 #include <time.h>
44 #include <unistd.h>
45 #include <sys/stat.h>
46 #include <signal.h>
47
48 #include <libeu.h>
49 #include <system.h>
50 #include <printversion.h>
51 #include "../libelf/libelfP.h"
52 #include "../libelf/common.h"
53 #include "../libebl/libeblP.h"
54 #include "../libdwelf/libdwelf.h"
55 #include "../libdw/libdwP.h"
56 #include "../libdwfl/libdwflP.h"
57 #include "../libdw/memory-access.h"
58
59 #include "../libdw/known-dwarf.h"
60
61 #ifdef __linux__
62 #define CORE_SIGILL  SIGILL
63 #define CORE_SIGBUS  SIGBUS
64 #define CORE_SIGFPE  SIGFPE
65 #define CORE_SIGSEGV SIGSEGV
66 #define CORE_SI_USER SI_USER
67 #else
68 /* We want the linux version of those as that is what shows up in the core files. */
69 #define CORE_SIGILL  4  /* Illegal instruction (ANSI).  */
70 #define CORE_SIGBUS  7  /* BUS error (4.2 BSD).  */
71 #define CORE_SIGFPE  8  /* Floating-point exception (ANSI).  */
72 #define CORE_SIGSEGV 11 /* Segmentation violation (ANSI).  */
73 #define CORE_SI_USER 0  /* Sent by kill, sigsend.  */
74 #endif
75
76 /* Name and version of program.  */
77 ARGP_PROGRAM_VERSION_HOOK_DEF = print_version;
78
79 /* Bug report address.  */
80 ARGP_PROGRAM_BUG_ADDRESS_DEF = PACKAGE_BUGREPORT;
81
82 /* argp key value for --elf-section, non-ascii.  */
83 #define ELF_INPUT_SECTION 256
84
85 /* argp key value for --dwarf-skeleton, non-ascii.  */
86 #define DWARF_SKELETON 257
87
88 /* Terrible hack for hooking unrelated skeleton/split compile units,
89    see __libdw_link_skel_split in print_debug.  */
90 static bool do_not_close_dwfl = false;
91
92 /* Definitions of arguments for argp functions.  */
93 static const struct argp_option options[] =
94 {
95   { NULL, 0, NULL, 0, N_("ELF input selection:"), 0 },
96   { "elf-section", ELF_INPUT_SECTION, "SECTION", OPTION_ARG_OPTIONAL,
97     N_("Use the named SECTION (default .gnu_debugdata) as (compressed) ELF "
98        "input data"), 0 },
99   { "dwarf-skeleton", DWARF_SKELETON, "FILE", 0,
100     N_("Used with -w to find the skeleton Compile Units in FILE associated "
101        "with the Split Compile units in a .dwo input file"), 0 },
102   { NULL, 0, NULL, 0, N_("ELF output selection:"), 0 },
103   { "all", 'a', NULL, 0,
104     N_("All these plus -p .strtab -p .dynstr -p .comment"), 0 },
105   { "dynamic", 'd', NULL, 0, N_("Display the dynamic segment"), 0 },
106   { "file-header", 'h', NULL, 0, N_("Display the ELF file header"), 0 },
107   { "histogram", 'I', NULL, 0,
108     N_("Display histogram of bucket list lengths"), 0 },
109   { "program-headers", 'l', NULL, 0, N_("Display the program headers"), 0 },
110   { "segments", 'l', NULL, OPTION_ALIAS | OPTION_HIDDEN, NULL, 0 },
111   { "relocs", 'r', NULL, 0, N_("Display relocations"), 0 },
112   { "section-groups", 'g', NULL, 0, N_("Display the section groups"), 0 },
113   { "section-headers", 'S', NULL, 0, N_("Display the sections' headers"), 0 },
114   { "sections", 'S', NULL, OPTION_ALIAS | OPTION_HIDDEN, NULL, 0 },
115   { "symbols", 's', "SECTION", OPTION_ARG_OPTIONAL,
116     N_("Display the symbol table sections"), 0 },
117   { "version-info", 'V', NULL, 0, N_("Display versioning information"), 0 },
118   { "notes", 'n', NULL, 0, N_("Display the ELF notes"), 0 },
119   { "arch-specific", 'A', NULL, 0,
120     N_("Display architecture specific information, if any"), 0 },
121   { "exception", 'e', NULL, 0,
122     N_("Display sections for exception handling"), 0 },
123
124   { NULL, 0, NULL, 0, N_("Additional output selection:"), 0 },
125   { "debug-dump", 'w', "SECTION", OPTION_ARG_OPTIONAL,
126     N_("Display DWARF section content.  SECTION can be one of abbrev, addr, "
127        "aranges, decodedaranges, frame, gdb_index, info, info+, loc, line, "
128        "decodedline, ranges, pubnames, str, macinfo, macro or exception"), 0 },
129   { "hex-dump", 'x', "SECTION", 0,
130     N_("Dump the uninterpreted contents of SECTION, by number or name"), 0 },
131   { "strings", 'p', "SECTION", OPTION_ARG_OPTIONAL,
132     N_("Print string contents of sections"), 0 },
133   { "string-dump", 'p', NULL, OPTION_ALIAS | OPTION_HIDDEN, NULL, 0 },
134   { "archive-index", 'c', NULL, 0,
135     N_("Display the symbol index of an archive"), 0 },
136
137   { NULL, 0, NULL, 0, N_("Output control:"), 0 },
138   { "numeric-addresses", 'N', NULL, 0,
139     N_("Do not find symbol names for addresses in DWARF data"), 0 },
140   { "unresolved-address-offsets", 'U', NULL, 0,
141     N_("Display just offsets instead of resolving values to addresses in DWARF data"), 0 },
142   { "wide", 'W', NULL, 0,
143     N_("Ignored for compatibility (lines always wide)"), 0 },
144   { "decompress", 'z', NULL, 0,
145     N_("Show compression information for compressed sections (when used with -S); decompress section before dumping data (when used with -p or -x)"), 0 },
146   { NULL, 0, NULL, 0, NULL, 0 }
147 };
148
149 /* Short description of program.  */
150 static const char doc[] = N_("\
151 Print information from ELF file in human-readable form.");
152
153 /* Strings for arguments in help texts.  */
154 static const char args_doc[] = N_("FILE...");
155
156 /* Prototype for option handler.  */
157 static error_t parse_opt (int key, char *arg, struct argp_state *state);
158
159 /* Data structure to communicate with argp functions.  */
160 static struct argp argp =
161 {
162   options, parse_opt, args_doc, doc, NULL, NULL, NULL
163 };
164
165 /* If non-null, the section from which we should read to (compressed) ELF.  */
166 static const char *elf_input_section = NULL;
167
168 /* If non-null, the file that contains the skeleton CUs.  */
169 static const char *dwarf_skeleton = NULL;
170
171 /* Flags set by the option controlling the output.  */
172
173 /* True if dynamic segment should be printed.  */
174 static bool print_dynamic_table;
175
176 /* True if the file header should be printed.  */
177 static bool print_file_header;
178
179 /* True if the program headers should be printed.  */
180 static bool print_program_header;
181
182 /* True if relocations should be printed.  */
183 static bool print_relocations;
184
185 /* True if the section headers should be printed.  */
186 static bool print_section_header;
187
188 /* True if the symbol table should be printed.  */
189 static bool print_symbol_table;
190
191 /* A specific section name, or NULL to print all symbol tables.  */
192 static char *symbol_table_section;
193
194 /* True if the version information should be printed.  */
195 static bool print_version_info;
196
197 /* True if section groups should be printed.  */
198 static bool print_section_groups;
199
200 /* True if bucket list length histogram should be printed.  */
201 static bool print_histogram;
202
203 /* True if the architecture specific data should be printed.  */
204 static bool print_arch;
205
206 /* True if note section content should be printed.  */
207 static bool print_notes;
208
209 /* True if SHF_STRINGS section content should be printed.  */
210 static bool print_string_sections;
211
212 /* True if archive index should be printed.  */
213 static bool print_archive_index;
214
215 /* True if any of the control options except print_archive_index is set.  */
216 static bool any_control_option;
217
218 /* True if we should print addresses from DWARF in symbolic form.  */
219 static bool print_address_names = true;
220
221 /* True if we should print raw values instead of relativized addresses.  */
222 static bool print_unresolved_addresses = false;
223
224 /* True if we should print the .debug_aranges section using libdw.  */
225 static bool decodedaranges = false;
226
227 /* True if we should print the .debug_aranges section using libdw.  */
228 static bool decodedline = false;
229
230 /* True if we want to show more information about compressed sections.  */
231 static bool print_decompress = false;
232
233 /* True if we want to show split compile units for debug_info skeletons.  */
234 static bool show_split_units = false;
235
236 /* Select printing of debugging sections.  */
237 static enum section_e
238 {
239   section_abbrev = 1,           /* .debug_abbrev  */
240   section_aranges = 2,          /* .debug_aranges  */
241   section_frame = 4,            /* .debug_frame or .eh_frame & al.  */
242   section_info = 8,             /* .debug_info, (implies .debug_types)  */
243   section_line = 16,            /* .debug_line  */
244   section_loc = 32,             /* .debug_loc  */
245   section_pubnames = 64,        /* .debug_pubnames  */
246   section_str = 128,            /* .debug_str  */
247   section_macinfo = 256,        /* .debug_macinfo  */
248   section_ranges = 512,         /* .debug_ranges  */
249   section_exception = 1024,     /* .eh_frame & al.  */
250   section_gdb_index = 2048,     /* .gdb_index  */
251   section_macro = 4096,         /* .debug_macro  */
252   section_addr = 8192,          /* .debug_addr  */
253   section_types = 16384,        /* .debug_types (implied by .debug_info)  */
254   section_all = (section_abbrev | section_aranges | section_frame
255                  | section_info | section_line | section_loc
256                  | section_pubnames | section_str | section_macinfo
257                  | section_ranges | section_exception | section_gdb_index
258                  | section_macro | section_addr | section_types)
259 } print_debug_sections, implicit_debug_sections;
260
261 /* Select hex dumping of sections.  */
262 static struct section_argument *dump_data_sections;
263 static struct section_argument **dump_data_sections_tail = &dump_data_sections;
264
265 /* Select string dumping of sections.  */
266 static struct section_argument *string_sections;
267 static struct section_argument **string_sections_tail = &string_sections;
268
269 struct section_argument
270 {
271   struct section_argument *next;
272   const char *arg;
273   bool implicit;
274 };
275
276 /* Numbers of sections and program headers in the file.  */
277 static size_t shnum;
278 static size_t phnum;
279
280
281 /* Declarations of local functions.  */
282 static void process_file (int fd, const char *fname, bool only_one);
283 static void process_elf_file (Dwfl_Module *dwflmod, int fd);
284 static void print_ehdr (Ebl *ebl, GElf_Ehdr *ehdr);
285 static void print_shdr (Ebl *ebl, GElf_Ehdr *ehdr);
286 static void print_phdr (Ebl *ebl, GElf_Ehdr *ehdr);
287 static void print_scngrp (Ebl *ebl);
288 static void print_dynamic (Ebl *ebl);
289 static void print_relocs (Ebl *ebl, GElf_Ehdr *ehdr);
290 static void handle_relocs_rel (Ebl *ebl, GElf_Ehdr *ehdr, Elf_Scn *scn,
291                                GElf_Shdr *shdr);
292 static void handle_relocs_rela (Ebl *ebl, GElf_Ehdr *ehdr, Elf_Scn *scn,
293                                 GElf_Shdr *shdr);
294 static void print_symtab (Ebl *ebl, int type);
295 static void handle_symtab (Ebl *ebl, Elf_Scn *scn, GElf_Shdr *shdr);
296 static void print_verinfo (Ebl *ebl);
297 static void handle_verneed (Ebl *ebl, Elf_Scn *scn, GElf_Shdr *shdr);
298 static void handle_verdef (Ebl *ebl, Elf_Scn *scn, GElf_Shdr *shdr);
299 static void handle_versym (Ebl *ebl, Elf_Scn *scn,
300                            GElf_Shdr *shdr);
301 static void print_debug (Dwfl_Module *dwflmod, Ebl *ebl, GElf_Ehdr *ehdr);
302 static void handle_hash (Ebl *ebl);
303 static void handle_notes (Ebl *ebl, GElf_Ehdr *ehdr);
304 static void print_liblist (Ebl *ebl);
305 static void print_attributes (Ebl *ebl, const GElf_Ehdr *ehdr);
306 static void dump_data (Ebl *ebl);
307 static void dump_strings (Ebl *ebl);
308 static void print_strings (Ebl *ebl);
309 static void dump_archive_index (Elf *, const char *);
310
311
312 /* Looked up once with gettext in main.  */
313 static char *yes_str;
314 static char *no_str;
315
316 int
317 main (int argc, char *argv[])
318 {
319   /* We use no threads here which can interfere with handling a stream.  */
320   (void) __fsetlocking (stdout, FSETLOCKING_BYCALLER);
321
322   /* Set locale.  */
323   setlocale (LC_ALL, "");
324
325   /* Initialize the message catalog.  */
326   textdomain (PACKAGE_TARNAME);
327
328   /* Look up once.  */
329   yes_str = gettext ("yes");
330   no_str = gettext ("yes");
331
332   /* Parse and process arguments.  */
333   int remaining;
334   argp_parse (&argp, argc, argv, 0, &remaining, NULL);
335
336   /* Before we start tell the ELF library which version we are using.  */
337   elf_version (EV_CURRENT);
338
339   /* Now process all the files given at the command line.  */
340   bool only_one = remaining + 1 == argc;
341   do
342     {
343       /* Open the file.  */
344       int fd = open (argv[remaining], O_RDONLY);
345       if (fd == -1)
346         {
347           error (0, errno, gettext ("cannot open input file"));
348           continue;
349         }
350
351       process_file (fd, argv[remaining], only_one);
352
353       close (fd);
354     }
355   while (++remaining < argc);
356
357   return error_message_count != 0;
358 }
359
360
361 /* Handle program arguments.  */
362 static error_t
363 parse_opt (int key, char *arg,
364            struct argp_state *state __attribute__ ((unused)))
365 {
366   void add_dump_section (const char *name, bool implicit)
367   {
368     struct section_argument *a = xmalloc (sizeof *a);
369     a->arg = name;
370     a->next = NULL;
371     a->implicit = implicit;
372     struct section_argument ***tailp
373       = key == 'x' ? &dump_data_sections_tail : &string_sections_tail;
374     **tailp = a;
375     *tailp = &a->next;
376   }
377
378   switch (key)
379     {
380     case 'a':
381       print_file_header = true;
382       print_program_header = true;
383       print_relocations = true;
384       print_section_header = true;
385       print_symbol_table = true;
386       print_version_info = true;
387       print_dynamic_table = true;
388       print_section_groups = true;
389       print_histogram = true;
390       print_arch = true;
391       print_notes = true;
392       implicit_debug_sections |= section_exception;
393       add_dump_section (".strtab", true);
394       add_dump_section (".dynstr", true);
395       add_dump_section (".comment", true);
396       any_control_option = true;
397       break;
398     case 'A':
399       print_arch = true;
400       any_control_option = true;
401       break;
402     case 'd':
403       print_dynamic_table = true;
404       any_control_option = true;
405       break;
406     case 'e':
407       print_debug_sections |= section_exception;
408       any_control_option = true;
409       break;
410     case 'g':
411       print_section_groups = true;
412       any_control_option = true;
413       break;
414     case 'h':
415       print_file_header = true;
416       any_control_option = true;
417       break;
418     case 'I':
419       print_histogram = true;
420       any_control_option = true;
421       break;
422     case 'l':
423       print_program_header = true;
424       any_control_option = true;
425       break;
426     case 'n':
427       print_notes = true;
428       any_control_option = true;
429       break;
430     case 'r':
431       print_relocations = true;
432       any_control_option = true;
433      break;
434     case 'S':
435       print_section_header = true;
436       any_control_option = true;
437       break;
438     case 's':
439       print_symbol_table = true;
440       any_control_option = true;
441       symbol_table_section = arg;
442       break;
443     case 'V':
444       print_version_info = true;
445       any_control_option = true;
446       break;
447     case 'c':
448       print_archive_index = true;
449       break;
450     case 'w':
451       if (arg == NULL)
452         {
453           print_debug_sections = section_all;
454           implicit_debug_sections = section_info;
455           show_split_units = true;
456         }
457       else if (strcmp (arg, "abbrev") == 0)
458         print_debug_sections |= section_abbrev;
459       else if (strcmp (arg, "addr") == 0)
460         {
461           print_debug_sections |= section_addr;
462           implicit_debug_sections |= section_info;
463         }
464       else if (strcmp (arg, "aranges") == 0)
465         print_debug_sections |= section_aranges;
466       else if (strcmp (arg, "decodedaranges") == 0)
467         {
468           print_debug_sections |= section_aranges;
469           decodedaranges = true;
470         }
471       else if (strcmp (arg, "ranges") == 0)
472         {
473           print_debug_sections |= section_ranges;
474           implicit_debug_sections |= section_info;
475         }
476       else if (strcmp (arg, "frame") == 0 || strcmp (arg, "frames") == 0)
477         print_debug_sections |= section_frame;
478       else if (strcmp (arg, "info") == 0)
479         {
480           print_debug_sections |= section_info;
481           print_debug_sections |= section_types;
482         }
483       else if (strcmp (arg, "info+") == 0)
484         {
485           print_debug_sections |= section_info;
486           print_debug_sections |= section_types;
487           show_split_units = true;
488         }
489       else if (strcmp (arg, "loc") == 0)
490         {
491           print_debug_sections |= section_loc;
492           implicit_debug_sections |= section_info;
493         }
494       else if (strcmp (arg, "line") == 0)
495         print_debug_sections |= section_line;
496       else if (strcmp (arg, "decodedline") == 0)
497         {
498           print_debug_sections |= section_line;
499           decodedline = true;
500         }
501       else if (strcmp (arg, "pubnames") == 0)
502         print_debug_sections |= section_pubnames;
503       else if (strcmp (arg, "str") == 0)
504         {
505           print_debug_sections |= section_str;
506           /* For mapping string offset tables to CUs.  */
507           implicit_debug_sections |= section_info;
508         }
509       else if (strcmp (arg, "macinfo") == 0)
510         print_debug_sections |= section_macinfo;
511       else if (strcmp (arg, "macro") == 0)
512         print_debug_sections |= section_macro;
513       else if (strcmp (arg, "exception") == 0)
514         print_debug_sections |= section_exception;
515       else if (strcmp (arg, "gdb_index") == 0)
516         print_debug_sections |= section_gdb_index;
517       else
518         {
519           fprintf (stderr, gettext ("Unknown DWARF debug section `%s'.\n"),
520                    arg);
521           argp_help (&argp, stderr, ARGP_HELP_SEE,
522                      program_invocation_short_name);
523           exit (1);
524         }
525       any_control_option = true;
526       break;
527     case 'p':
528       any_control_option = true;
529       if (arg == NULL)
530         {
531           print_string_sections = true;
532           break;
533         }
534       FALLTHROUGH;
535     case 'x':
536       add_dump_section (arg, false);
537       any_control_option = true;
538       break;
539     case 'N':
540       print_address_names = false;
541       break;
542     case 'U':
543       print_unresolved_addresses = true;
544       break;
545     case ARGP_KEY_NO_ARGS:
546       fputs (gettext ("Missing file name.\n"), stderr);
547       goto do_argp_help;
548     case ARGP_KEY_FINI:
549       if (! any_control_option && ! print_archive_index)
550         {
551           fputs (gettext ("No operation specified.\n"), stderr);
552         do_argp_help:
553           argp_help (&argp, stderr, ARGP_HELP_SEE,
554                      program_invocation_short_name);
555           exit (EXIT_FAILURE);
556         }
557       break;
558     case 'W':                   /* Ignored.  */
559       break;
560     case 'z':
561       print_decompress = true;
562       break;
563     case ELF_INPUT_SECTION:
564       if (arg == NULL)
565         elf_input_section = ".gnu_debugdata";
566       else
567         elf_input_section = arg;
568       break;
569     case DWARF_SKELETON:
570       dwarf_skeleton = arg;
571       break;
572     default:
573       return ARGP_ERR_UNKNOWN;
574     }
575   return 0;
576 }
577
578
579 /* Create a file descriptor to read the data from the
580    elf_input_section given a file descriptor to an ELF file.  */
581 static int
582 open_input_section (int fd)
583 {
584   size_t shnums;
585   size_t cnt;
586   size_t shstrndx;
587   Elf *elf = elf_begin (fd, ELF_C_READ_MMAP, NULL);
588   if (elf == NULL)
589     {
590       error (0, 0, gettext ("cannot generate Elf descriptor: %s"),
591              elf_errmsg (-1));
592       return -1;
593     }
594
595   if (elf_getshdrnum (elf, &shnums) < 0)
596     {
597       error (0, 0, gettext ("cannot determine number of sections: %s"),
598              elf_errmsg (-1));
599     open_error:
600       elf_end (elf);
601       return -1;
602     }
603
604   if (elf_getshdrstrndx (elf, &shstrndx) < 0)
605     {
606       error (0, 0, gettext ("cannot get section header string table index"));
607       goto open_error;
608     }
609
610   for (cnt = 0; cnt < shnums; ++cnt)
611     {
612       Elf_Scn *scn = elf_getscn (elf, cnt);
613       if (scn == NULL)
614         {
615           error (0, 0, gettext ("cannot get section: %s"),
616                  elf_errmsg (-1));
617           goto open_error;
618         }
619
620       GElf_Shdr shdr_mem;
621       GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem);
622       if (unlikely (shdr == NULL))
623         {
624           error (0, 0, gettext ("cannot get section header: %s"),
625                  elf_errmsg (-1));
626           goto open_error;
627         }
628
629       const char *sname = elf_strptr (elf, shstrndx, shdr->sh_name);
630       if (sname == NULL)
631         {
632           error (0, 0, gettext ("cannot get section name"));
633           goto open_error;
634         }
635
636       if (strcmp (sname, elf_input_section) == 0)
637         {
638           Elf_Data *data = elf_rawdata (scn, NULL);
639           if (data == NULL)
640             {
641               error (0, 0, gettext ("cannot get %s content: %s"),
642                      sname, elf_errmsg (-1));
643               goto open_error;
644             }
645
646           /* Create (and immediately unlink) a temporary file to store
647              section data in to create a file descriptor for it.  */
648           const char *tmpdir = getenv ("TMPDIR") ?: P_tmpdir;
649           static const char suffix[] = "/readelfXXXXXX";
650           int tmplen = strlen (tmpdir) + sizeof (suffix);
651           char *tempname = alloca (tmplen);
652           sprintf (tempname, "%s%s", tmpdir, suffix);
653
654           int sfd = mkstemp (tempname);
655           if (sfd == -1)
656             {
657               error (0, 0, gettext ("cannot create temp file '%s'"),
658                      tempname);
659               goto open_error;
660             }
661           unlink (tempname);
662
663           ssize_t size = data->d_size;
664           if (write_retry (sfd, data->d_buf, size) != size)
665             {
666               error (0, 0, gettext ("cannot write section data"));
667               goto open_error;
668             }
669
670           if (elf_end (elf) != 0)
671             {
672               error (0, 0, gettext ("error while closing Elf descriptor: %s"),
673                      elf_errmsg (-1));
674               return -1;
675             }
676
677           if (lseek (sfd, 0, SEEK_SET) == -1)
678             {
679               error (0, 0, gettext ("error while rewinding file descriptor"));
680               return -1;
681             }
682
683           return sfd;
684         }
685     }
686
687   /* Named section not found.  */
688   if (elf_end (elf) != 0)
689     error (0, 0, gettext ("error while closing Elf descriptor: %s"),
690            elf_errmsg (-1));
691   return -1;
692 }
693
694 /* Check if the file is an archive, and if so dump its index.  */
695 static void
696 check_archive_index (int fd, const char *fname, bool only_one)
697 {
698   /* Create an `Elf' descriptor.  */
699   Elf *elf = elf_begin (fd, ELF_C_READ_MMAP, NULL);
700   if (elf == NULL)
701     error (0, 0, gettext ("cannot generate Elf descriptor: %s"),
702            elf_errmsg (-1));
703   else
704     {
705       if (elf_kind (elf) == ELF_K_AR)
706         {
707           if (!only_one)
708             printf ("\n%s:\n\n", fname);
709           dump_archive_index (elf, fname);
710         }
711       else
712         error (0, 0,
713                gettext ("'%s' is not an archive, cannot print archive index"),
714                fname);
715
716       /* Now we can close the descriptor.  */
717       if (elf_end (elf) != 0)
718         error (0, 0, gettext ("error while closing Elf descriptor: %s"),
719                elf_errmsg (-1));
720     }
721 }
722
723 /* Trivial callback used for checking if we opened an archive.  */
724 static int
725 count_dwflmod (Dwfl_Module *dwflmod __attribute__ ((unused)),
726                void **userdata __attribute__ ((unused)),
727                const char *name __attribute__ ((unused)),
728                Dwarf_Addr base __attribute__ ((unused)),
729                void *arg)
730 {
731   if (*(bool *) arg)
732     return DWARF_CB_ABORT;
733   *(bool *) arg = true;
734   return DWARF_CB_OK;
735 }
736
737 struct process_dwflmod_args
738 {
739   int fd;
740   bool only_one;
741 };
742
743 static int
744 process_dwflmod (Dwfl_Module *dwflmod,
745                  void **userdata __attribute__ ((unused)),
746                  const char *name __attribute__ ((unused)),
747                  Dwarf_Addr base __attribute__ ((unused)),
748                  void *arg)
749 {
750   const struct process_dwflmod_args *a = arg;
751
752   /* Print the file name.  */
753   if (!a->only_one)
754     {
755       const char *fname;
756       dwfl_module_info (dwflmod, NULL, NULL, NULL, NULL, NULL, &fname, NULL);
757
758       printf ("\n%s:\n\n", fname);
759     }
760
761   process_elf_file (dwflmod, a->fd);
762
763   return DWARF_CB_OK;
764 }
765
766 /* Stub libdwfl callback, only the ELF handle already open is ever used.
767    Only used for finding the alternate debug file if the Dwarf comes from
768    the main file.  We are not interested in separate debuginfo.  */
769 static int
770 find_no_debuginfo (Dwfl_Module *mod,
771                    void **userdata,
772                    const char *modname,
773                    Dwarf_Addr base,
774                    const char *file_name,
775                    const char *debuglink_file,
776                    GElf_Word debuglink_crc,
777                    char **debuginfo_file_name)
778 {
779   Dwarf_Addr dwbias;
780   dwfl_module_info (mod, NULL, NULL, NULL, &dwbias, NULL, NULL, NULL);
781
782   /* We are only interested if the Dwarf has been setup on the main
783      elf file but is only missing the alternate debug link.  If dwbias
784      hasn't even been setup, this is searching for separate debuginfo
785      for the main elf.  We don't care in that case.  */
786   if (dwbias == (Dwarf_Addr) -1)
787     return -1;
788
789   return dwfl_standard_find_debuginfo (mod, userdata, modname, base,
790                                        file_name, debuglink_file,
791                                        debuglink_crc, debuginfo_file_name);
792 }
793
794 static Dwfl *
795 create_dwfl (int fd, const char *fname)
796 {
797   /* Duplicate an fd for dwfl_report_offline to swallow.  */
798   int dwfl_fd = dup (fd);
799   if (unlikely (dwfl_fd < 0))
800     error (EXIT_FAILURE, errno, "dup");
801
802   /* Use libdwfl in a trivial way to open the libdw handle for us.
803      This takes care of applying relocations to DWARF data in ET_REL files.  */
804   static const Dwfl_Callbacks callbacks =
805     {
806       .section_address = dwfl_offline_section_address,
807       .find_debuginfo = find_no_debuginfo
808     };
809   Dwfl *dwfl = dwfl_begin (&callbacks);
810   if (likely (dwfl != NULL))
811     /* Let 0 be the logical address of the file (or first in archive).  */
812     dwfl->offline_next_address = 0;
813   if (dwfl_report_offline (dwfl, fname, fname, dwfl_fd) == NULL)
814     {
815       struct stat st;
816       if (fstat (dwfl_fd, &st) != 0)
817         error (0, errno, gettext ("cannot stat input file"));
818       else if (unlikely (st.st_size == 0))
819         error (0, 0, gettext ("input file is empty"));
820       else
821         error (0, 0, gettext ("failed reading '%s': %s"),
822                fname, dwfl_errmsg (-1));
823       close (dwfl_fd);          /* Consumed on success, not on failure.  */
824       dwfl = NULL;
825     }
826   else
827     dwfl_report_end (dwfl, NULL, NULL);
828
829   return dwfl;
830 }
831
832 /* Process one input file.  */
833 static void
834 process_file (int fd, const char *fname, bool only_one)
835 {
836   if (print_archive_index)
837     check_archive_index (fd, fname, only_one);
838
839   if (!any_control_option)
840     return;
841
842   if (elf_input_section != NULL)
843     {
844       /* Replace fname and fd with section content. */
845       char *fnname = alloca (strlen (fname) + strlen (elf_input_section) + 2);
846       sprintf (fnname, "%s:%s", fname, elf_input_section);
847       fd = open_input_section (fd);
848       if (fd == -1)
849         {
850           error (0, 0, gettext ("No such section '%s' in '%s'"),
851                  elf_input_section, fname);
852           return;
853         }
854       fname = fnname;
855     }
856
857   Dwfl *dwfl = create_dwfl (fd, fname);
858   if (dwfl != NULL)
859     {
860       if (only_one)
861         {
862           /* Clear ONLY_ONE if we have multiple modules, from an archive.  */
863           bool seen = false;
864           only_one = dwfl_getmodules (dwfl, &count_dwflmod, &seen, 0) == 0;
865         }
866
867       /* Process the one or more modules gleaned from this file.  */
868       struct process_dwflmod_args a = { .fd = fd, .only_one = only_one };
869       dwfl_getmodules (dwfl, &process_dwflmod, &a, 0);
870     }
871   /* Terrible hack for hooking unrelated skeleton/split compile units,
872      see __libdw_link_skel_split in print_debug.  */
873   if (! do_not_close_dwfl)
874     dwfl_end (dwfl);
875
876   /* Need to close the replaced fd if we created it.  Caller takes
877      care of original.  */
878   if (elf_input_section != NULL)
879     close (fd);
880 }
881
882 /* Check whether there are any compressed sections in the ELF file.  */
883 static bool
884 elf_contains_chdrs (Elf *elf)
885 {
886   Elf_Scn *scn = NULL;
887   while ((scn = elf_nextscn (elf, scn)) != NULL)
888     {
889       GElf_Shdr shdr_mem;
890       GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem);
891       if (shdr != NULL && (shdr->sh_flags & SHF_COMPRESSED) != 0)
892         return true;
893     }
894   return false;
895 }
896
897 /* Process one ELF file.  */
898 static void
899 process_elf_file (Dwfl_Module *dwflmod, int fd)
900 {
901   GElf_Addr dwflbias;
902   Elf *elf = dwfl_module_getelf (dwflmod, &dwflbias);
903
904   GElf_Ehdr ehdr_mem;
905   GElf_Ehdr *ehdr = gelf_getehdr (elf, &ehdr_mem);
906
907   if (ehdr == NULL)
908     {
909     elf_error:
910       error (0, 0, gettext ("cannot read ELF header: %s"), elf_errmsg (-1));
911       return;
912     }
913
914   Ebl *ebl = ebl_openbackend (elf);
915   if (unlikely (ebl == NULL))
916     {
917     ebl_error:
918       error (0, errno, gettext ("cannot create EBL handle"));
919       return;
920     }
921
922   /* Determine the number of sections.  */
923   if (unlikely (elf_getshdrnum (ebl->elf, &shnum) < 0))
924     error (EXIT_FAILURE, 0,
925            gettext ("cannot determine number of sections: %s"),
926            elf_errmsg (-1));
927
928   /* Determine the number of phdrs.  */
929   if (unlikely (elf_getphdrnum (ebl->elf, &phnum) < 0))
930     error (EXIT_FAILURE, 0,
931            gettext ("cannot determine number of program headers: %s"),
932            elf_errmsg (-1));
933
934   /* For an ET_REL file, libdwfl has adjusted the in-core shdrs and
935      may have applied relocation to some sections.  If there are any
936      compressed sections, any pass (or libdw/libdwfl) might have
937      uncompressed them.  So we need to get a fresh Elf handle on the
938      file to display those.  */
939   bool print_unchanged = ((print_section_header
940                            || print_relocations
941                            || dump_data_sections != NULL
942                            || print_notes)
943                           && (ehdr->e_type == ET_REL
944                               || elf_contains_chdrs (ebl->elf)));
945
946   Elf *pure_elf = NULL;
947   Ebl *pure_ebl = ebl;
948   if (print_unchanged)
949     {
950       /* Read the file afresh.  */
951       off_t aroff = elf_getaroff (elf);
952       pure_elf = elf_begin (fd, ELF_C_READ_MMAP, NULL);
953       if (aroff > 0)
954         {
955           /* Archive member.  */
956           (void) elf_rand (pure_elf, aroff);
957           Elf *armem = elf_begin (-1, ELF_C_READ_MMAP, pure_elf);
958           elf_end (pure_elf);
959           pure_elf = armem;
960         }
961       if (pure_elf == NULL)
962         goto elf_error;
963       pure_ebl = ebl_openbackend (pure_elf);
964       if (pure_ebl == NULL)
965         goto ebl_error;
966     }
967
968   if (print_file_header)
969     print_ehdr (ebl, ehdr);
970   if (print_section_header)
971     print_shdr (pure_ebl, ehdr);
972   if (print_program_header)
973     print_phdr (ebl, ehdr);
974   if (print_section_groups)
975     print_scngrp (ebl);
976   if (print_dynamic_table)
977     print_dynamic (ebl);
978   if (print_relocations)
979     print_relocs (pure_ebl, ehdr);
980   if (print_histogram)
981     handle_hash (ebl);
982   if (print_symbol_table)
983     print_symtab (ebl, SHT_DYNSYM);
984   if (print_version_info)
985     print_verinfo (ebl);
986   if (print_symbol_table)
987     print_symtab (ebl, SHT_SYMTAB);
988   if (print_arch)
989     print_liblist (ebl);
990   if (print_arch)
991     print_attributes (ebl, ehdr);
992   if (dump_data_sections != NULL)
993     dump_data (pure_ebl);
994   if (string_sections != NULL)
995     dump_strings (ebl);
996   if ((print_debug_sections | implicit_debug_sections) != 0)
997     print_debug (dwflmod, ebl, ehdr);
998   if (print_notes)
999     handle_notes (pure_ebl, ehdr);
1000   if (print_string_sections)
1001     print_strings (ebl);
1002
1003   ebl_closebackend (ebl);
1004
1005   if (pure_ebl != ebl)
1006     {
1007       ebl_closebackend (pure_ebl);
1008       elf_end (pure_elf);
1009     }
1010 }
1011
1012
1013 /* Print file type.  */
1014 static void
1015 print_file_type (unsigned short int e_type)
1016 {
1017   if (likely (e_type <= ET_CORE))
1018     {
1019       static const char *const knowntypes[] =
1020       {
1021         N_("NONE (None)"),
1022         N_("REL (Relocatable file)"),
1023         N_("EXEC (Executable file)"),
1024         N_("DYN (Shared object file)"),
1025         N_("CORE (Core file)")
1026       };
1027       puts (gettext (knowntypes[e_type]));
1028     }
1029   else if (e_type >= ET_LOOS && e_type <= ET_HIOS)
1030     printf (gettext ("OS Specific: (%x)\n"),  e_type);
1031   else if (e_type >= ET_LOPROC /* && e_type <= ET_HIPROC always true */)
1032     printf (gettext ("Processor Specific: (%x)\n"),  e_type);
1033   else
1034     puts ("???");
1035 }
1036
1037
1038 /* Print ELF header.  */
1039 static void
1040 print_ehdr (Ebl *ebl, GElf_Ehdr *ehdr)
1041 {
1042   fputs_unlocked (gettext ("ELF Header:\n  Magic:  "), stdout);
1043   for (size_t cnt = 0; cnt < EI_NIDENT; ++cnt)
1044     printf (" %02hhx", ehdr->e_ident[cnt]);
1045
1046   printf (gettext ("\n  Class:                             %s\n"),
1047           ehdr->e_ident[EI_CLASS] == ELFCLASS32 ? "ELF32"
1048           : ehdr->e_ident[EI_CLASS] == ELFCLASS64 ? "ELF64"
1049           : "\?\?\?");
1050
1051   printf (gettext ("  Data:                              %s\n"),
1052           ehdr->e_ident[EI_DATA] == ELFDATA2LSB
1053           ? "2's complement, little endian"
1054           : ehdr->e_ident[EI_DATA] == ELFDATA2MSB
1055           ? "2's complement, big endian" : "\?\?\?");
1056
1057   printf (gettext ("  Ident Version:                     %hhd %s\n"),
1058           ehdr->e_ident[EI_VERSION],
1059           ehdr->e_ident[EI_VERSION] == EV_CURRENT ? gettext ("(current)")
1060           : "(\?\?\?)");
1061
1062   char buf[512];
1063   printf (gettext ("  OS/ABI:                            %s\n"),
1064           ebl_osabi_name (ebl, ehdr->e_ident[EI_OSABI], buf, sizeof (buf)));
1065
1066   printf (gettext ("  ABI Version:                       %hhd\n"),
1067           ehdr->e_ident[EI_ABIVERSION]);
1068
1069   fputs_unlocked (gettext ("  Type:                              "), stdout);
1070   print_file_type (ehdr->e_type);
1071
1072   printf (gettext ("  Machine:                           %s\n"), ebl->name);
1073
1074   printf (gettext ("  Version:                           %d %s\n"),
1075           ehdr->e_version,
1076           ehdr->e_version  == EV_CURRENT ? gettext ("(current)") : "(\?\?\?)");
1077
1078   printf (gettext ("  Entry point address:               %#" PRIx64 "\n"),
1079           ehdr->e_entry);
1080
1081   printf (gettext ("  Start of program headers:          %" PRId64 " %s\n"),
1082           ehdr->e_phoff, gettext ("(bytes into file)"));
1083
1084   printf (gettext ("  Start of section headers:          %" PRId64 " %s\n"),
1085           ehdr->e_shoff, gettext ("(bytes into file)"));
1086
1087   printf (gettext ("  Flags:                             %s\n"),
1088           ebl_machine_flag_name (ebl, ehdr->e_flags, buf, sizeof (buf)));
1089
1090   printf (gettext ("  Size of this header:               %" PRId16 " %s\n"),
1091           ehdr->e_ehsize, gettext ("(bytes)"));
1092
1093   printf (gettext ("  Size of program header entries:    %" PRId16 " %s\n"),
1094           ehdr->e_phentsize, gettext ("(bytes)"));
1095
1096   printf (gettext ("  Number of program headers entries: %" PRId16),
1097           ehdr->e_phnum);
1098   if (ehdr->e_phnum == PN_XNUM)
1099     {
1100       GElf_Shdr shdr_mem;
1101       GElf_Shdr *shdr = gelf_getshdr (elf_getscn (ebl->elf, 0), &shdr_mem);
1102       if (shdr != NULL)
1103         printf (gettext (" (%" PRIu32 " in [0].sh_info)"),
1104                 (uint32_t) shdr->sh_info);
1105       else
1106         fputs_unlocked (gettext (" ([0] not available)"), stdout);
1107     }
1108   fputc_unlocked ('\n', stdout);
1109
1110   printf (gettext ("  Size of section header entries:    %" PRId16 " %s\n"),
1111           ehdr->e_shentsize, gettext ("(bytes)"));
1112
1113   printf (gettext ("  Number of section headers entries: %" PRId16),
1114           ehdr->e_shnum);
1115   if (ehdr->e_shnum == 0)
1116     {
1117       GElf_Shdr shdr_mem;
1118       GElf_Shdr *shdr = gelf_getshdr (elf_getscn (ebl->elf, 0), &shdr_mem);
1119       if (shdr != NULL)
1120         printf (gettext (" (%" PRIu32 " in [0].sh_size)"),
1121                 (uint32_t) shdr->sh_size);
1122       else
1123         fputs_unlocked (gettext (" ([0] not available)"), stdout);
1124     }
1125   fputc_unlocked ('\n', stdout);
1126
1127   if (unlikely (ehdr->e_shstrndx == SHN_XINDEX))
1128     {
1129       GElf_Shdr shdr_mem;
1130       GElf_Shdr *shdr = gelf_getshdr (elf_getscn (ebl->elf, 0), &shdr_mem);
1131       if (shdr != NULL)
1132         /* We managed to get the zeroth section.  */
1133         snprintf (buf, sizeof (buf), gettext (" (%" PRIu32 " in [0].sh_link)"),
1134                   (uint32_t) shdr->sh_link);
1135       else
1136         {
1137           strncpy (buf, gettext (" ([0] not available)"), sizeof (buf));
1138           buf[sizeof (buf) - 1] = '\0';
1139         }
1140
1141       printf (gettext ("  Section header string table index: XINDEX%s\n\n"),
1142               buf);
1143     }
1144   else
1145     printf (gettext ("  Section header string table index: %" PRId16 "\n\n"),
1146             ehdr->e_shstrndx);
1147 }
1148
1149
1150 static const char *
1151 get_visibility_type (int value)
1152 {
1153   switch (value)
1154     {
1155     case STV_DEFAULT:
1156       return "DEFAULT";
1157     case STV_INTERNAL:
1158       return "INTERNAL";
1159     case STV_HIDDEN:
1160       return "HIDDEN";
1161     case STV_PROTECTED:
1162       return "PROTECTED";
1163     default:
1164       return "???";
1165     }
1166 }
1167
1168 static const char *
1169 elf_ch_type_name (unsigned int code)
1170 {
1171   if (code == 0)
1172     return "NONE";
1173
1174   if (code == ELFCOMPRESS_ZLIB)
1175     return "ZLIB";
1176
1177   return "UNKNOWN";
1178 }
1179
1180 /* Print the section headers.  */
1181 static void
1182 print_shdr (Ebl *ebl, GElf_Ehdr *ehdr)
1183 {
1184   size_t cnt;
1185   size_t shstrndx;
1186
1187   if (! print_file_header)
1188     printf (gettext ("\
1189 There are %d section headers, starting at offset %#" PRIx64 ":\n\
1190 \n"),
1191             ehdr->e_shnum, ehdr->e_shoff);
1192
1193   /* Get the section header string table index.  */
1194   if (unlikely (elf_getshdrstrndx (ebl->elf, &shstrndx) < 0))
1195     error (EXIT_FAILURE, 0,
1196            gettext ("cannot get section header string table index"));
1197
1198   puts (gettext ("Section Headers:"));
1199
1200   if (ehdr->e_ident[EI_CLASS] == ELFCLASS32)
1201     puts (gettext ("[Nr] Name                 Type         Addr     Off    Size   ES Flags Lk Inf Al"));
1202   else
1203     puts (gettext ("[Nr] Name                 Type         Addr             Off      Size     ES Flags Lk Inf Al"));
1204
1205   if (print_decompress)
1206     {
1207       if (ehdr->e_ident[EI_CLASS] == ELFCLASS32)
1208         puts (gettext ("     [Compression  Size   Al]"));
1209       else
1210         puts (gettext ("     [Compression  Size     Al]"));
1211     }
1212
1213   for (cnt = 0; cnt < shnum; ++cnt)
1214     {
1215       Elf_Scn *scn = elf_getscn (ebl->elf, cnt);
1216
1217       if (unlikely (scn == NULL))
1218         error (EXIT_FAILURE, 0, gettext ("cannot get section: %s"),
1219                elf_errmsg (-1));
1220
1221       /* Get the section header.  */
1222       GElf_Shdr shdr_mem;
1223       GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem);
1224       if (unlikely (shdr == NULL))
1225         error (EXIT_FAILURE, 0, gettext ("cannot get section header: %s"),
1226                elf_errmsg (-1));
1227
1228       char flagbuf[20];
1229       char *cp = flagbuf;
1230       if (shdr->sh_flags & SHF_WRITE)
1231         *cp++ = 'W';
1232       if (shdr->sh_flags & SHF_ALLOC)
1233         *cp++ = 'A';
1234       if (shdr->sh_flags & SHF_EXECINSTR)
1235         *cp++ = 'X';
1236       if (shdr->sh_flags & SHF_MERGE)
1237         *cp++ = 'M';
1238       if (shdr->sh_flags & SHF_STRINGS)
1239         *cp++ = 'S';
1240       if (shdr->sh_flags & SHF_INFO_LINK)
1241         *cp++ = 'I';
1242       if (shdr->sh_flags & SHF_LINK_ORDER)
1243         *cp++ = 'L';
1244       if (shdr->sh_flags & SHF_OS_NONCONFORMING)
1245         *cp++ = 'N';
1246       if (shdr->sh_flags & SHF_GROUP)
1247         *cp++ = 'G';
1248       if (shdr->sh_flags & SHF_TLS)
1249         *cp++ = 'T';
1250       if (shdr->sh_flags & SHF_COMPRESSED)
1251         *cp++ = 'C';
1252       if (shdr->sh_flags & SHF_ORDERED)
1253         *cp++ = 'O';
1254       if (shdr->sh_flags & SHF_EXCLUDE)
1255         *cp++ = 'E';
1256       *cp = '\0';
1257
1258       const char *sname;
1259       char buf[128];
1260       sname = elf_strptr (ebl->elf, shstrndx, shdr->sh_name) ?: "<corrupt>";
1261       printf ("[%2zu] %-20s %-12s %0*" PRIx64 " %0*" PRIx64 " %0*" PRIx64
1262               " %2" PRId64 " %-5s %2" PRId32 " %3" PRId32
1263               " %2" PRId64 "\n",
1264               cnt, sname,
1265               ebl_section_type_name (ebl, shdr->sh_type, buf, sizeof (buf)),
1266               ehdr->e_ident[EI_CLASS] == ELFCLASS32 ? 8 : 16, shdr->sh_addr,
1267               ehdr->e_ident[EI_CLASS] == ELFCLASS32 ? 6 : 8, shdr->sh_offset,
1268               ehdr->e_ident[EI_CLASS] == ELFCLASS32 ? 6 : 8, shdr->sh_size,
1269               shdr->sh_entsize, flagbuf, shdr->sh_link, shdr->sh_info,
1270               shdr->sh_addralign);
1271
1272       if (print_decompress)
1273         {
1274           if ((shdr->sh_flags & SHF_COMPRESSED) != 0)
1275             {
1276               GElf_Chdr chdr;
1277               if (gelf_getchdr (scn, &chdr) != NULL)
1278                 printf ("     [ELF %s (%" PRId32 ") %0*" PRIx64
1279                         " %2" PRId64 "]\n",
1280                         elf_ch_type_name (chdr.ch_type),
1281                         chdr.ch_type,
1282                         ehdr->e_ident[EI_CLASS] == ELFCLASS32 ? 6 : 8,
1283                         chdr.ch_size, chdr.ch_addralign);
1284               else
1285                 error (0, 0,
1286                        gettext ("bad compression header for section %zd: %s"),
1287                        elf_ndxscn (scn), elf_errmsg (-1));
1288             }
1289           else if (strncmp(".zdebug", sname, strlen (".zdebug")) == 0)
1290             {
1291               ssize_t size;
1292               if ((size = dwelf_scn_gnu_compressed_size (scn)) >= 0)
1293                 printf ("     [GNU ZLIB     %0*zx   ]\n",
1294                         ehdr->e_ident[EI_CLASS] == ELFCLASS32 ? 6 : 8, size);
1295               else
1296                 error (0, 0,
1297                        gettext ("bad gnu compressed size for section %zd: %s"),
1298                        elf_ndxscn (scn), elf_errmsg (-1));
1299             }
1300         }
1301     }
1302
1303   fputc_unlocked ('\n', stdout);
1304 }
1305
1306
1307 /* Print the program header.  */
1308 static void
1309 print_phdr (Ebl *ebl, GElf_Ehdr *ehdr)
1310 {
1311   if (phnum == 0)
1312     /* No program header, this is OK in relocatable objects.  */
1313     return;
1314
1315   puts (gettext ("Program Headers:"));
1316   if (ehdr->e_ident[EI_CLASS] == ELFCLASS32)
1317     puts (gettext ("\
1318   Type           Offset   VirtAddr   PhysAddr   FileSiz  MemSiz   Flg Align"));
1319   else
1320     puts (gettext ("\
1321   Type           Offset   VirtAddr           PhysAddr           FileSiz  MemSiz   Flg Align"));
1322
1323   /* Process all program headers.  */
1324   bool has_relro = false;
1325   GElf_Addr relro_from = 0;
1326   GElf_Addr relro_to = 0;
1327   for (size_t cnt = 0; cnt < phnum; ++cnt)
1328     {
1329       char buf[128];
1330       GElf_Phdr mem;
1331       GElf_Phdr *phdr = gelf_getphdr (ebl->elf, cnt, &mem);
1332
1333       /* If for some reason the header cannot be returned show this.  */
1334       if (unlikely (phdr == NULL))
1335         {
1336           puts ("  ???");
1337           continue;
1338         }
1339
1340       printf ("  %-14s 0x%06" PRIx64 " 0x%0*" PRIx64 " 0x%0*" PRIx64
1341               " 0x%06" PRIx64 " 0x%06" PRIx64 " %c%c%c 0x%" PRIx64 "\n",
1342               ebl_segment_type_name (ebl, phdr->p_type, buf, sizeof (buf)),
1343               phdr->p_offset,
1344               ehdr->e_ident[EI_CLASS] == ELFCLASS32 ? 8 : 16, phdr->p_vaddr,
1345               ehdr->e_ident[EI_CLASS] == ELFCLASS32 ? 8 : 16, phdr->p_paddr,
1346               phdr->p_filesz,
1347               phdr->p_memsz,
1348               phdr->p_flags & PF_R ? 'R' : ' ',
1349               phdr->p_flags & PF_W ? 'W' : ' ',
1350               phdr->p_flags & PF_X ? 'E' : ' ',
1351               phdr->p_align);
1352
1353       if (phdr->p_type == PT_INTERP)
1354         {
1355           /* If we are sure the file offset is valid then we can show
1356              the user the name of the interpreter.  We check whether
1357              there is a section at the file offset.  Normally there
1358              would be a section called ".interp".  But in separate
1359              .debug files it is a NOBITS section (and so doesn't match
1360              with gelf_offscn).  Which probably means the offset is
1361              not valid another reason could be because the ELF file
1362              just doesn't contain any section headers, in that case
1363              just play it safe and don't display anything.  */
1364
1365           Elf_Scn *scn = gelf_offscn (ebl->elf, phdr->p_offset);
1366           GElf_Shdr shdr_mem;
1367           GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem);
1368
1369           size_t maxsize;
1370           char *filedata = elf_rawfile (ebl->elf, &maxsize);
1371
1372           if (shdr != NULL && shdr->sh_type == SHT_PROGBITS
1373               && filedata != NULL && phdr->p_offset < maxsize
1374               && phdr->p_filesz <= maxsize - phdr->p_offset
1375               && memchr (filedata + phdr->p_offset, '\0',
1376                          phdr->p_filesz) != NULL)
1377             printf (gettext ("\t[Requesting program interpreter: %s]\n"),
1378                     filedata + phdr->p_offset);
1379         }
1380       else if (phdr->p_type == PT_GNU_RELRO)
1381         {
1382           has_relro = true;
1383           relro_from = phdr->p_vaddr;
1384           relro_to = relro_from + phdr->p_memsz;
1385         }
1386     }
1387
1388   if (ehdr->e_shnum == 0)
1389     /* No sections in the file.  Punt.  */
1390     return;
1391
1392   /* Get the section header string table index.  */
1393   size_t shstrndx;
1394   if (unlikely (elf_getshdrstrndx (ebl->elf, &shstrndx) < 0))
1395     error (EXIT_FAILURE, 0,
1396            gettext ("cannot get section header string table index"));
1397
1398   puts (gettext ("\n Section to Segment mapping:\n  Segment Sections..."));
1399
1400   for (size_t cnt = 0; cnt < phnum; ++cnt)
1401     {
1402       /* Print the segment number.  */
1403       printf ("   %2.2zu     ", cnt);
1404
1405       GElf_Phdr phdr_mem;
1406       GElf_Phdr *phdr = gelf_getphdr (ebl->elf, cnt, &phdr_mem);
1407       /* This must not happen.  */
1408       if (unlikely (phdr == NULL))
1409         error (EXIT_FAILURE, 0, gettext ("cannot get program header: %s"),
1410                elf_errmsg (-1));
1411
1412       /* Iterate over the sections.  */
1413       bool in_relro = false;
1414       bool in_ro = false;
1415       for (size_t inner = 1; inner < shnum; ++inner)
1416         {
1417           Elf_Scn *scn = elf_getscn (ebl->elf, inner);
1418           /* This should not happen.  */
1419           if (unlikely (scn == NULL))
1420             error (EXIT_FAILURE, 0, gettext ("cannot get section: %s"),
1421                    elf_errmsg (-1));
1422
1423           /* Get the section header.  */
1424           GElf_Shdr shdr_mem;
1425           GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem);
1426           if (unlikely (shdr == NULL))
1427             error (EXIT_FAILURE, 0,
1428                    gettext ("cannot get section header: %s"),
1429                    elf_errmsg (-1));
1430
1431           if (shdr->sh_size > 0
1432               /* Compare allocated sections by VMA, unallocated
1433                  sections by file offset.  */
1434               && (shdr->sh_flags & SHF_ALLOC
1435                   ? (shdr->sh_addr >= phdr->p_vaddr
1436                      && (shdr->sh_addr + shdr->sh_size
1437                          <= phdr->p_vaddr + phdr->p_memsz))
1438                   : (shdr->sh_offset >= phdr->p_offset
1439                      && (shdr->sh_offset + shdr->sh_size
1440                          <= phdr->p_offset + phdr->p_filesz))))
1441             {
1442               if (has_relro && !in_relro
1443                   && shdr->sh_addr >= relro_from
1444                   && shdr->sh_addr + shdr->sh_size <= relro_to)
1445                 {
1446                   fputs_unlocked (" [RELRO:", stdout);
1447                   in_relro = true;
1448                 }
1449               else if (has_relro && in_relro && shdr->sh_addr >= relro_to)
1450                 {
1451                   fputs_unlocked ("]", stdout);
1452                   in_relro =  false;
1453                 }
1454               else if (has_relro && in_relro
1455                        && shdr->sh_addr + shdr->sh_size > relro_to)
1456                 fputs_unlocked ("] <RELRO:", stdout);
1457               else if (phdr->p_type == PT_LOAD && (phdr->p_flags & PF_W) == 0)
1458                 {
1459                   if (!in_ro)
1460                     {
1461                       fputs_unlocked (" [RO:", stdout);
1462                       in_ro = true;
1463                     }
1464                 }
1465               else
1466                 {
1467                   /* Determine the segment this section is part of.  */
1468                   size_t cnt2;
1469                   GElf_Phdr phdr2_mem;
1470                   GElf_Phdr *phdr2 = NULL;
1471                   for (cnt2 = 0; cnt2 < phnum; ++cnt2)
1472                     {
1473                       phdr2 = gelf_getphdr (ebl->elf, cnt2, &phdr2_mem);
1474
1475                       if (phdr2 != NULL && phdr2->p_type == PT_LOAD
1476                           && shdr->sh_addr >= phdr2->p_vaddr
1477                           && (shdr->sh_addr + shdr->sh_size
1478                               <= phdr2->p_vaddr + phdr2->p_memsz))
1479                         break;
1480                     }
1481
1482                   if (cnt2 < phnum)
1483                     {
1484                       if ((phdr2->p_flags & PF_W) == 0 && !in_ro)
1485                         {
1486                           fputs_unlocked (" [RO:", stdout);
1487                           in_ro = true;
1488                         }
1489                       else if ((phdr2->p_flags & PF_W) != 0 && in_ro)
1490                         {
1491                           fputs_unlocked ("]", stdout);
1492                           in_ro = false;
1493                         }
1494                     }
1495                 }
1496
1497               printf (" %s",
1498                       elf_strptr (ebl->elf, shstrndx, shdr->sh_name));
1499
1500               /* Signal that this sectin is only partially covered.  */
1501               if (has_relro && in_relro
1502                        && shdr->sh_addr + shdr->sh_size > relro_to)
1503                 {
1504                   fputs_unlocked (">", stdout);
1505                   in_relro =  false;
1506                 }
1507             }
1508         }
1509       if (in_relro || in_ro)
1510         fputs_unlocked ("]", stdout);
1511
1512       /* Finish the line.  */
1513       fputc_unlocked ('\n', stdout);
1514     }
1515 }
1516
1517
1518 static const char *
1519 section_name (Ebl *ebl, GElf_Ehdr *ehdr, GElf_Shdr *shdr)
1520 {
1521   return elf_strptr (ebl->elf, ehdr->e_shstrndx, shdr->sh_name) ?: "???";
1522 }
1523
1524
1525 static void
1526 handle_scngrp (Ebl *ebl, Elf_Scn *scn, GElf_Shdr *shdr)
1527 {
1528   /* Get the data of the section.  */
1529   Elf_Data *data = elf_getdata (scn, NULL);
1530
1531   Elf_Scn *symscn = elf_getscn (ebl->elf, shdr->sh_link);
1532   GElf_Shdr symshdr_mem;
1533   GElf_Shdr *symshdr = gelf_getshdr (symscn, &symshdr_mem);
1534   Elf_Data *symdata = elf_getdata (symscn, NULL);
1535
1536   if (data == NULL || data->d_size < sizeof (Elf32_Word) || symshdr == NULL
1537       || symdata == NULL)
1538     return;
1539
1540   /* Get the section header string table index.  */
1541   size_t shstrndx;
1542   if (unlikely (elf_getshdrstrndx (ebl->elf, &shstrndx) < 0))
1543     error (EXIT_FAILURE, 0,
1544            gettext ("cannot get section header string table index"));
1545
1546   Elf32_Word *grpref = (Elf32_Word *) data->d_buf;
1547
1548   GElf_Sym sym_mem;
1549   GElf_Sym *sym = gelf_getsym (symdata, shdr->sh_info, &sym_mem);
1550
1551   printf ((grpref[0] & GRP_COMDAT)
1552           ? ngettext ("\
1553 \nCOMDAT section group [%2zu] '%s' with signature '%s' contains %zu entry:\n",
1554                       "\
1555 \nCOMDAT section group [%2zu] '%s' with signature '%s' contains %zu entries:\n",
1556                       data->d_size / sizeof (Elf32_Word) - 1)
1557           : ngettext ("\
1558 \nSection group [%2zu] '%s' with signature '%s' contains %zu entry:\n", "\
1559 \nSection group [%2zu] '%s' with signature '%s' contains %zu entries:\n",
1560                       data->d_size / sizeof (Elf32_Word) - 1),
1561           elf_ndxscn (scn),
1562           elf_strptr (ebl->elf, shstrndx, shdr->sh_name),
1563           (sym == NULL ? NULL
1564            : elf_strptr (ebl->elf, symshdr->sh_link, sym->st_name))
1565           ?: gettext ("<INVALID SYMBOL>"),
1566           data->d_size / sizeof (Elf32_Word) - 1);
1567
1568   for (size_t cnt = 1; cnt < data->d_size / sizeof (Elf32_Word); ++cnt)
1569     {
1570       GElf_Shdr grpshdr_mem;
1571       GElf_Shdr *grpshdr = gelf_getshdr (elf_getscn (ebl->elf, grpref[cnt]),
1572                                          &grpshdr_mem);
1573
1574       const char *str;
1575       printf ("  [%2u] %s\n",
1576               grpref[cnt],
1577               grpshdr != NULL
1578               && (str = elf_strptr (ebl->elf, shstrndx, grpshdr->sh_name))
1579               ? str : gettext ("<INVALID SECTION>"));
1580     }
1581 }
1582
1583
1584 static void
1585 print_scngrp (Ebl *ebl)
1586 {
1587   /* Find all relocation sections and handle them.  */
1588   Elf_Scn *scn = NULL;
1589
1590   while ((scn = elf_nextscn (ebl->elf, scn)) != NULL)
1591     {
1592        /* Handle the section if it is a symbol table.  */
1593       GElf_Shdr shdr_mem;
1594       GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem);
1595
1596       if (shdr != NULL && shdr->sh_type == SHT_GROUP)
1597         {
1598           if ((shdr->sh_flags & SHF_COMPRESSED) != 0)
1599             {
1600               if (elf_compress (scn, 0, 0) < 0)
1601                 printf ("WARNING: %s [%zd]\n",
1602                         gettext ("Couldn't uncompress section"),
1603                         elf_ndxscn (scn));
1604               shdr = gelf_getshdr (scn, &shdr_mem);
1605               if (unlikely (shdr == NULL))
1606                 error (EXIT_FAILURE, 0,
1607                        gettext ("cannot get section [%zd] header: %s"),
1608                        elf_ndxscn (scn),
1609                        elf_errmsg (-1));
1610             }
1611           handle_scngrp (ebl, scn, shdr);
1612         }
1613     }
1614 }
1615
1616
1617 static const struct flags
1618 {
1619   int mask;
1620   const char *str;
1621 } dt_flags[] =
1622   {
1623     { DF_ORIGIN, "ORIGIN" },
1624     { DF_SYMBOLIC, "SYMBOLIC" },
1625     { DF_TEXTREL, "TEXTREL" },
1626     { DF_BIND_NOW, "BIND_NOW" },
1627     { DF_STATIC_TLS, "STATIC_TLS" }
1628   };
1629 static const int ndt_flags = sizeof (dt_flags) / sizeof (dt_flags[0]);
1630
1631 static const struct flags dt_flags_1[] =
1632   {
1633     { DF_1_NOW, "NOW" },
1634     { DF_1_GLOBAL, "GLOBAL" },
1635     { DF_1_GROUP, "GROUP" },
1636     { DF_1_NODELETE, "NODELETE" },
1637     { DF_1_LOADFLTR, "LOADFLTR" },
1638     { DF_1_INITFIRST, "INITFIRST" },
1639     { DF_1_NOOPEN, "NOOPEN" },
1640     { DF_1_ORIGIN, "ORIGIN" },
1641     { DF_1_DIRECT, "DIRECT" },
1642     { DF_1_TRANS, "TRANS" },
1643     { DF_1_INTERPOSE, "INTERPOSE" },
1644     { DF_1_NODEFLIB, "NODEFLIB" },
1645     { DF_1_NODUMP, "NODUMP" },
1646     { DF_1_CONFALT, "CONFALT" },
1647     { DF_1_ENDFILTEE, "ENDFILTEE" },
1648     { DF_1_DISPRELDNE, "DISPRELDNE" },
1649     { DF_1_DISPRELPND, "DISPRELPND" },
1650   };
1651 static const int ndt_flags_1 = sizeof (dt_flags_1) / sizeof (dt_flags_1[0]);
1652
1653 static const struct flags dt_feature_1[] =
1654   {
1655     { DTF_1_PARINIT, "PARINIT" },
1656     { DTF_1_CONFEXP, "CONFEXP" }
1657   };
1658 static const int ndt_feature_1 = (sizeof (dt_feature_1)
1659                                   / sizeof (dt_feature_1[0]));
1660
1661 static const struct flags dt_posflag_1[] =
1662   {
1663     { DF_P1_LAZYLOAD, "LAZYLOAD" },
1664     { DF_P1_GROUPPERM, "GROUPPERM" }
1665   };
1666 static const int ndt_posflag_1 = (sizeof (dt_posflag_1)
1667                                   / sizeof (dt_posflag_1[0]));
1668
1669
1670 static void
1671 print_flags (int class, GElf_Xword d_val, const struct flags *flags,
1672                 int nflags)
1673 {
1674   bool first = true;
1675   int cnt;
1676
1677   for (cnt = 0; cnt < nflags; ++cnt)
1678     if (d_val & flags[cnt].mask)
1679       {
1680         if (!first)
1681           putchar_unlocked (' ');
1682         fputs_unlocked (flags[cnt].str, stdout);
1683         d_val &= ~flags[cnt].mask;
1684         first = false;
1685       }
1686
1687   if (d_val != 0)
1688     {
1689       if (!first)
1690         putchar_unlocked (' ');
1691       printf ("%#0*" PRIx64, class == ELFCLASS32 ? 10 : 18, d_val);
1692     }
1693
1694   putchar_unlocked ('\n');
1695 }
1696
1697
1698 static void
1699 print_dt_flags (int class, GElf_Xword d_val)
1700 {
1701   print_flags (class, d_val, dt_flags, ndt_flags);
1702 }
1703
1704
1705 static void
1706 print_dt_flags_1 (int class, GElf_Xword d_val)
1707 {
1708   print_flags (class, d_val, dt_flags_1, ndt_flags_1);
1709 }
1710
1711
1712 static void
1713 print_dt_feature_1 (int class, GElf_Xword d_val)
1714 {
1715   print_flags (class, d_val, dt_feature_1, ndt_feature_1);
1716 }
1717
1718
1719 static void
1720 print_dt_posflag_1 (int class, GElf_Xword d_val)
1721 {
1722   print_flags (class, d_val, dt_posflag_1, ndt_posflag_1);
1723 }
1724
1725
1726 static void
1727 handle_dynamic (Ebl *ebl, Elf_Scn *scn, GElf_Shdr *shdr)
1728 {
1729   int class = gelf_getclass (ebl->elf);
1730   GElf_Shdr glink_mem;
1731   GElf_Shdr *glink;
1732   Elf_Data *data;
1733   size_t cnt;
1734   size_t shstrndx;
1735   size_t sh_entsize;
1736
1737   /* Get the data of the section.  */
1738   data = elf_getdata (scn, NULL);
1739   if (data == NULL)
1740     return;
1741
1742   /* Get the section header string table index.  */
1743   if (unlikely (elf_getshdrstrndx (ebl->elf, &shstrndx) < 0))
1744     error (EXIT_FAILURE, 0,
1745            gettext ("cannot get section header string table index"));
1746
1747   sh_entsize = gelf_fsize (ebl->elf, ELF_T_DYN, 1, EV_CURRENT);
1748
1749   glink = gelf_getshdr (elf_getscn (ebl->elf, shdr->sh_link), &glink_mem);
1750   if (glink == NULL)
1751     error (EXIT_FAILURE, 0, gettext ("invalid sh_link value in section %zu"),
1752            elf_ndxscn (scn));
1753
1754   printf (ngettext ("\
1755 \nDynamic segment contains %lu entry:\n Addr: %#0*" PRIx64 "  Offset: %#08" PRIx64 "  Link to section: [%2u] '%s'\n",
1756                     "\
1757 \nDynamic segment contains %lu entries:\n Addr: %#0*" PRIx64 "  Offset: %#08" PRIx64 "  Link to section: [%2u] '%s'\n",
1758                     shdr->sh_size / sh_entsize),
1759           (unsigned long int) (shdr->sh_size / sh_entsize),
1760           class == ELFCLASS32 ? 10 : 18, shdr->sh_addr,
1761           shdr->sh_offset,
1762           (int) shdr->sh_link,
1763           elf_strptr (ebl->elf, shstrndx, glink->sh_name));
1764   fputs_unlocked (gettext ("  Type              Value\n"), stdout);
1765
1766   for (cnt = 0; cnt < shdr->sh_size / sh_entsize; ++cnt)
1767     {
1768       GElf_Dyn dynmem;
1769       GElf_Dyn *dyn = gelf_getdyn (data, cnt, &dynmem);
1770       if (dyn == NULL)
1771         break;
1772
1773       char buf[64];
1774       printf ("  %-17s ",
1775               ebl_dynamic_tag_name (ebl, dyn->d_tag, buf, sizeof (buf)));
1776
1777       switch (dyn->d_tag)
1778         {
1779         case DT_NULL:
1780         case DT_DEBUG:
1781         case DT_BIND_NOW:
1782         case DT_TEXTREL:
1783           /* No further output.  */
1784           fputc_unlocked ('\n', stdout);
1785           break;
1786
1787         case DT_NEEDED:
1788           printf (gettext ("Shared library: [%s]\n"),
1789                   elf_strptr (ebl->elf, shdr->sh_link, dyn->d_un.d_val));
1790           break;
1791
1792         case DT_SONAME:
1793           printf (gettext ("Library soname: [%s]\n"),
1794                   elf_strptr (ebl->elf, shdr->sh_link, dyn->d_un.d_val));
1795           break;
1796
1797         case DT_RPATH:
1798           printf (gettext ("Library rpath: [%s]\n"),
1799                   elf_strptr (ebl->elf, shdr->sh_link, dyn->d_un.d_val));
1800           break;
1801
1802         case DT_RUNPATH:
1803           printf (gettext ("Library runpath: [%s]\n"),
1804                   elf_strptr (ebl->elf, shdr->sh_link, dyn->d_un.d_val));
1805           break;
1806
1807         case DT_PLTRELSZ:
1808         case DT_RELASZ:
1809         case DT_STRSZ:
1810         case DT_RELSZ:
1811         case DT_RELAENT:
1812         case DT_SYMENT:
1813         case DT_RELENT:
1814         case DT_PLTPADSZ:
1815         case DT_MOVEENT:
1816         case DT_MOVESZ:
1817         case DT_INIT_ARRAYSZ:
1818         case DT_FINI_ARRAYSZ:
1819         case DT_SYMINSZ:
1820         case DT_SYMINENT:
1821         case DT_GNU_CONFLICTSZ:
1822         case DT_GNU_LIBLISTSZ:
1823           printf (gettext ("%" PRId64 " (bytes)\n"), dyn->d_un.d_val);
1824           break;
1825
1826         case DT_VERDEFNUM:
1827         case DT_VERNEEDNUM:
1828         case DT_RELACOUNT:
1829         case DT_RELCOUNT:
1830           printf ("%" PRId64 "\n", dyn->d_un.d_val);
1831           break;
1832
1833         case DT_PLTREL:;
1834           const char *tagname = ebl_dynamic_tag_name (ebl, dyn->d_un.d_val,
1835                                                       NULL, 0);
1836           puts (tagname ?: "???");
1837           break;
1838
1839         case DT_FLAGS:
1840           print_dt_flags (class, dyn->d_un.d_val);
1841           break;
1842
1843         case DT_FLAGS_1:
1844           print_dt_flags_1 (class, dyn->d_un.d_val);
1845           break;
1846
1847         case DT_FEATURE_1:
1848           print_dt_feature_1 (class, dyn->d_un.d_val);
1849           break;
1850
1851         case DT_POSFLAG_1:
1852           print_dt_posflag_1 (class, dyn->d_un.d_val);
1853           break;
1854
1855         default:
1856           printf ("%#0*" PRIx64 "\n",
1857                   class == ELFCLASS32 ? 10 : 18, dyn->d_un.d_val);
1858           break;
1859         }
1860     }
1861 }
1862
1863
1864 /* Print the dynamic segment.  */
1865 static void
1866 print_dynamic (Ebl *ebl)
1867 {
1868   for (size_t i = 0; i < phnum; ++i)
1869     {
1870       GElf_Phdr phdr_mem;
1871       GElf_Phdr *phdr = gelf_getphdr (ebl->elf, i, &phdr_mem);
1872
1873       if (phdr != NULL && phdr->p_type == PT_DYNAMIC)
1874         {
1875           Elf_Scn *scn = gelf_offscn (ebl->elf, phdr->p_offset);
1876           GElf_Shdr shdr_mem;
1877           GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem);
1878           if (shdr != NULL && shdr->sh_type == SHT_DYNAMIC)
1879             handle_dynamic (ebl, scn, shdr);
1880           break;
1881         }
1882     }
1883 }
1884
1885
1886 /* Print relocations.  */
1887 static void
1888 print_relocs (Ebl *ebl, GElf_Ehdr *ehdr)
1889 {
1890   /* Find all relocation sections and handle them.  */
1891   Elf_Scn *scn = NULL;
1892
1893   while ((scn = elf_nextscn (ebl->elf, scn)) != NULL)
1894     {
1895        /* Handle the section if it is a symbol table.  */
1896       GElf_Shdr shdr_mem;
1897       GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem);
1898
1899       if (likely (shdr != NULL))
1900         {
1901           if (shdr->sh_type == SHT_REL)
1902             handle_relocs_rel (ebl, ehdr, scn, shdr);
1903           else if (shdr->sh_type == SHT_RELA)
1904             handle_relocs_rela (ebl, ehdr, scn, shdr);
1905         }
1906     }
1907 }
1908
1909
1910 /* Handle a relocation section.  */
1911 static void
1912 handle_relocs_rel (Ebl *ebl, GElf_Ehdr *ehdr, Elf_Scn *scn, GElf_Shdr *shdr)
1913 {
1914   int class = gelf_getclass (ebl->elf);
1915   size_t sh_entsize = gelf_fsize (ebl->elf, ELF_T_REL, 1, EV_CURRENT);
1916   int nentries = shdr->sh_size / sh_entsize;
1917
1918   /* Get the data of the section.  */
1919   Elf_Data *data = elf_getdata (scn, NULL);
1920   if (data == NULL)
1921     return;
1922
1923   /* Get the symbol table information.  */
1924   Elf_Scn *symscn = elf_getscn (ebl->elf, shdr->sh_link);
1925   GElf_Shdr symshdr_mem;
1926   GElf_Shdr *symshdr = gelf_getshdr (symscn, &symshdr_mem);
1927   Elf_Data *symdata = elf_getdata (symscn, NULL);
1928
1929   /* Get the section header of the section the relocations are for.  */
1930   GElf_Shdr destshdr_mem;
1931   GElf_Shdr *destshdr = gelf_getshdr (elf_getscn (ebl->elf, shdr->sh_info),
1932                                       &destshdr_mem);
1933
1934   if (unlikely (symshdr == NULL || symdata == NULL || destshdr == NULL))
1935     {
1936       printf (gettext ("\nInvalid symbol table at offset %#0" PRIx64 "\n"),
1937               shdr->sh_offset);
1938       return;
1939     }
1940
1941   /* Search for the optional extended section index table.  */
1942   Elf_Data *xndxdata = NULL;
1943   int xndxscnidx = elf_scnshndx (scn);
1944   if (unlikely (xndxscnidx > 0))
1945     xndxdata = elf_getdata (elf_getscn (ebl->elf, xndxscnidx), NULL);
1946
1947   /* Get the section header string table index.  */
1948   size_t shstrndx;
1949   if (unlikely (elf_getshdrstrndx (ebl->elf, &shstrndx) < 0))
1950     error (EXIT_FAILURE, 0,
1951            gettext ("cannot get section header string table index"));
1952
1953   if (shdr->sh_info != 0)
1954     printf (ngettext ("\
1955 \nRelocation section [%2zu] '%s' for section [%2u] '%s' at offset %#0" PRIx64 " contains %d entry:\n",
1956                     "\
1957 \nRelocation section [%2zu] '%s' for section [%2u] '%s' at offset %#0" PRIx64 " contains %d entries:\n",
1958                       nentries),
1959             elf_ndxscn (scn),
1960             elf_strptr (ebl->elf, shstrndx, shdr->sh_name),
1961             (unsigned int) shdr->sh_info,
1962             elf_strptr (ebl->elf, shstrndx, destshdr->sh_name),
1963             shdr->sh_offset,
1964             nentries);
1965   else
1966     /* The .rel.dyn section does not refer to a specific section but
1967        instead of section index zero.  Do not try to print a section
1968        name.  */
1969     printf (ngettext ("\
1970 \nRelocation section [%2u] '%s' at offset %#0" PRIx64 " contains %d entry:\n",
1971                     "\
1972 \nRelocation section [%2u] '%s' at offset %#0" PRIx64 " contains %d entries:\n",
1973                       nentries),
1974             (unsigned int) elf_ndxscn (scn),
1975             elf_strptr (ebl->elf, shstrndx, shdr->sh_name),
1976             shdr->sh_offset,
1977             nentries);
1978   fputs_unlocked (class == ELFCLASS32
1979                   ? gettext ("\
1980   Offset      Type                 Value       Name\n")
1981                   : gettext ("\
1982   Offset              Type                 Value               Name\n"),
1983          stdout);
1984
1985   int is_statically_linked = 0;
1986   for (int cnt = 0; cnt < nentries; ++cnt)
1987     {
1988       GElf_Rel relmem;
1989       GElf_Rel *rel = gelf_getrel (data, cnt, &relmem);
1990       if (likely (rel != NULL))
1991         {
1992           char buf[128];
1993           GElf_Sym symmem;
1994           Elf32_Word xndx;
1995           GElf_Sym *sym = gelf_getsymshndx (symdata, xndxdata,
1996                                             GELF_R_SYM (rel->r_info),
1997                                             &symmem, &xndx);
1998           if (unlikely (sym == NULL))
1999             {
2000               /* As a special case we have to handle relocations in static
2001                  executables.  This only happens for IRELATIVE relocations
2002                  (so far).  There is no symbol table.  */
2003               if (is_statically_linked == 0)
2004                 {
2005                   /* Find the program header and look for a PT_INTERP entry. */
2006                   is_statically_linked = -1;
2007                   if (ehdr->e_type == ET_EXEC)
2008                     {
2009                       is_statically_linked = 1;
2010
2011                       for (size_t inner = 0; inner < phnum; ++inner)
2012                         {
2013                           GElf_Phdr phdr_mem;
2014                           GElf_Phdr *phdr = gelf_getphdr (ebl->elf, inner,
2015                                                           &phdr_mem);
2016                           if (phdr != NULL && phdr->p_type == PT_INTERP)
2017                             {
2018                               is_statically_linked = -1;
2019                               break;
2020                             }
2021                         }
2022                     }
2023                 }
2024
2025               if (is_statically_linked > 0 && shdr->sh_link == 0)
2026                 printf ("\
2027   %#0*" PRIx64 "  %-20s %*s  %s\n",
2028                         class == ELFCLASS32 ? 10 : 18, rel->r_offset,
2029                         ebl_reloc_type_check (ebl, GELF_R_TYPE (rel->r_info))
2030                         /* Avoid the leading R_ which isn't carrying any
2031                            information.  */
2032                         ? ebl_reloc_type_name (ebl, GELF_R_TYPE (rel->r_info),
2033                                                buf, sizeof (buf)) + 2
2034                         : gettext ("<INVALID RELOC>"),
2035                         class == ELFCLASS32 ? 10 : 18, "",
2036                         elf_strptr (ebl->elf, shstrndx, destshdr->sh_name));
2037               else
2038                 printf ("  %#0*" PRIx64 "  %-20s <%s %ld>\n",
2039                         class == ELFCLASS32 ? 10 : 18, rel->r_offset,
2040                         ebl_reloc_type_check (ebl, GELF_R_TYPE (rel->r_info))
2041                         /* Avoid the leading R_ which isn't carrying any
2042                            information.  */
2043                         ? ebl_reloc_type_name (ebl, GELF_R_TYPE (rel->r_info),
2044                                                buf, sizeof (buf)) + 2
2045                         : gettext ("<INVALID RELOC>"),
2046                         gettext ("INVALID SYMBOL"),
2047                         (long int) GELF_R_SYM (rel->r_info));
2048             }
2049           else if (GELF_ST_TYPE (sym->st_info) != STT_SECTION)
2050             printf ("  %#0*" PRIx64 "  %-20s %#0*" PRIx64 "  %s\n",
2051                     class == ELFCLASS32 ? 10 : 18, rel->r_offset,
2052                     likely (ebl_reloc_type_check (ebl,
2053                                                   GELF_R_TYPE (rel->r_info)))
2054                     /* Avoid the leading R_ which isn't carrying any
2055                        information.  */
2056                     ? ebl_reloc_type_name (ebl, GELF_R_TYPE (rel->r_info),
2057                                            buf, sizeof (buf)) + 2
2058                     : gettext ("<INVALID RELOC>"),
2059                     class == ELFCLASS32 ? 10 : 18, sym->st_value,
2060                     elf_strptr (ebl->elf, symshdr->sh_link, sym->st_name));
2061           else
2062             {
2063               /* This is a relocation against a STT_SECTION symbol.  */
2064               GElf_Shdr secshdr_mem;
2065               GElf_Shdr *secshdr;
2066               secshdr = gelf_getshdr (elf_getscn (ebl->elf,
2067                                                   sym->st_shndx == SHN_XINDEX
2068                                                   ? xndx : sym->st_shndx),
2069                                       &secshdr_mem);
2070
2071               if (unlikely (secshdr == NULL))
2072                 printf ("  %#0*" PRIx64 "  %-20s <%s %ld>\n",
2073                         class == ELFCLASS32 ? 10 : 18, rel->r_offset,
2074                         ebl_reloc_type_check (ebl, GELF_R_TYPE (rel->r_info))
2075                         /* Avoid the leading R_ which isn't carrying any
2076                            information.  */
2077                         ? ebl_reloc_type_name (ebl, GELF_R_TYPE (rel->r_info),
2078                                                buf, sizeof (buf)) + 2
2079                         : gettext ("<INVALID RELOC>"),
2080                         gettext ("INVALID SECTION"),
2081                         (long int) (sym->st_shndx == SHN_XINDEX
2082                                     ? xndx : sym->st_shndx));
2083               else
2084                 printf ("  %#0*" PRIx64 "  %-20s %#0*" PRIx64 "  %s\n",
2085                         class == ELFCLASS32 ? 10 : 18, rel->r_offset,
2086                         ebl_reloc_type_check (ebl, GELF_R_TYPE (rel->r_info))
2087                         /* Avoid the leading R_ which isn't carrying any
2088                            information.  */
2089                         ? ebl_reloc_type_name (ebl, GELF_R_TYPE (rel->r_info),
2090                                                buf, sizeof (buf)) + 2
2091                         : gettext ("<INVALID RELOC>"),
2092                         class == ELFCLASS32 ? 10 : 18, sym->st_value,
2093                         elf_strptr (ebl->elf, shstrndx, secshdr->sh_name));
2094             }
2095         }
2096     }
2097 }
2098
2099
2100 /* Handle a relocation section.  */
2101 static void
2102 handle_relocs_rela (Ebl *ebl, GElf_Ehdr *ehdr, Elf_Scn *scn, GElf_Shdr *shdr)
2103 {
2104   int class = gelf_getclass (ebl->elf);
2105   size_t sh_entsize = gelf_fsize (ebl->elf, ELF_T_RELA, 1, EV_CURRENT);
2106   int nentries = shdr->sh_size / sh_entsize;
2107
2108   /* Get the data of the section.  */
2109   Elf_Data *data = elf_getdata (scn, NULL);
2110   if (data == NULL)
2111     return;
2112
2113   /* Get the symbol table information.  */
2114   Elf_Scn *symscn = elf_getscn (ebl->elf, shdr->sh_link);
2115   GElf_Shdr symshdr_mem;
2116   GElf_Shdr *symshdr = gelf_getshdr (symscn, &symshdr_mem);
2117   Elf_Data *symdata = elf_getdata (symscn, NULL);
2118
2119   /* Get the section header of the section the relocations are for.  */
2120   GElf_Shdr destshdr_mem;
2121   GElf_Shdr *destshdr = gelf_getshdr (elf_getscn (ebl->elf, shdr->sh_info),
2122                                       &destshdr_mem);
2123
2124   if (unlikely (symshdr == NULL || symdata == NULL || destshdr == NULL))
2125     {
2126       printf (gettext ("\nInvalid symbol table at offset %#0" PRIx64 "\n"),
2127               shdr->sh_offset);
2128       return;
2129     }
2130
2131   /* Search for the optional extended section index table.  */
2132   Elf_Data *xndxdata = NULL;
2133   int xndxscnidx = elf_scnshndx (scn);
2134   if (unlikely (xndxscnidx > 0))
2135     xndxdata = elf_getdata (elf_getscn (ebl->elf, xndxscnidx), NULL);
2136
2137   /* Get the section header string table index.  */
2138   size_t shstrndx;
2139   if (unlikely (elf_getshdrstrndx (ebl->elf, &shstrndx) < 0))
2140     error (EXIT_FAILURE, 0,
2141            gettext ("cannot get section header string table index"));
2142
2143   if (shdr->sh_info != 0)
2144     printf (ngettext ("\
2145 \nRelocation section [%2zu] '%s' for section [%2u] '%s' at offset %#0" PRIx64 " contains %d entry:\n",
2146                     "\
2147 \nRelocation section [%2zu] '%s' for section [%2u] '%s' at offset %#0" PRIx64 " contains %d entries:\n",
2148                     nentries),
2149           elf_ndxscn (scn),
2150           elf_strptr (ebl->elf, shstrndx, shdr->sh_name),
2151           (unsigned int) shdr->sh_info,
2152           elf_strptr (ebl->elf, shstrndx, destshdr->sh_name),
2153           shdr->sh_offset,
2154           nentries);
2155   else
2156     /* The .rela.dyn section does not refer to a specific section but
2157        instead of section index zero.  Do not try to print a section
2158        name.  */
2159     printf (ngettext ("\
2160 \nRelocation section [%2u] '%s' at offset %#0" PRIx64 " contains %d entry:\n",
2161                     "\
2162 \nRelocation section [%2u] '%s' at offset %#0" PRIx64 " contains %d entries:\n",
2163                       nentries),
2164             (unsigned int) elf_ndxscn (scn),
2165             elf_strptr (ebl->elf, shstrndx, shdr->sh_name),
2166             shdr->sh_offset,
2167             nentries);
2168   fputs_unlocked (class == ELFCLASS32
2169                   ? gettext ("\
2170   Offset      Type            Value       Addend Name\n")
2171                   : gettext ("\
2172   Offset              Type            Value               Addend Name\n"),
2173                   stdout);
2174
2175   int is_statically_linked = 0;
2176   for (int cnt = 0; cnt < nentries; ++cnt)
2177     {
2178       GElf_Rela relmem;
2179       GElf_Rela *rel = gelf_getrela (data, cnt, &relmem);
2180       if (likely (rel != NULL))
2181         {
2182           char buf[64];
2183           GElf_Sym symmem;
2184           Elf32_Word xndx;
2185           GElf_Sym *sym = gelf_getsymshndx (symdata, xndxdata,
2186                                             GELF_R_SYM (rel->r_info),
2187                                             &symmem, &xndx);
2188
2189           if (unlikely (sym == NULL))
2190             {
2191               /* As a special case we have to handle relocations in static
2192                  executables.  This only happens for IRELATIVE relocations
2193                  (so far).  There is no symbol table.  */
2194               if (is_statically_linked == 0)
2195                 {
2196                   /* Find the program header and look for a PT_INTERP entry. */
2197                   is_statically_linked = -1;
2198                   if (ehdr->e_type == ET_EXEC)
2199                     {
2200                       is_statically_linked = 1;
2201
2202                       for (size_t inner = 0; inner < phnum; ++inner)
2203                         {
2204                           GElf_Phdr phdr_mem;
2205                           GElf_Phdr *phdr = gelf_getphdr (ebl->elf, inner,
2206                                                           &phdr_mem);
2207                           if (phdr != NULL && phdr->p_type == PT_INTERP)
2208                             {
2209                               is_statically_linked = -1;
2210                               break;
2211                             }
2212                         }
2213                     }
2214                 }
2215
2216               if (is_statically_linked > 0 && shdr->sh_link == 0)
2217                 printf ("\
2218   %#0*" PRIx64 "  %-15s %*s  %#6" PRIx64 " %s\n",
2219                         class == ELFCLASS32 ? 10 : 18, rel->r_offset,
2220                         ebl_reloc_type_check (ebl, GELF_R_TYPE (rel->r_info))
2221                         /* Avoid the leading R_ which isn't carrying any
2222                            information.  */
2223                         ? ebl_reloc_type_name (ebl, GELF_R_TYPE (rel->r_info),
2224                                                buf, sizeof (buf)) + 2
2225                         : gettext ("<INVALID RELOC>"),
2226                         class == ELFCLASS32 ? 10 : 18, "",
2227                         rel->r_addend,
2228                         elf_strptr (ebl->elf, shstrndx, destshdr->sh_name));
2229               else
2230                 printf ("  %#0*" PRIx64 "  %-15s <%s %ld>\n",
2231                         class == ELFCLASS32 ? 10 : 18, rel->r_offset,
2232                         ebl_reloc_type_check (ebl, GELF_R_TYPE (rel->r_info))
2233                         /* Avoid the leading R_ which isn't carrying any
2234                            information.  */
2235                         ? ebl_reloc_type_name (ebl, GELF_R_TYPE (rel->r_info),
2236                                                buf, sizeof (buf)) + 2
2237                         : gettext ("<INVALID RELOC>"),
2238                         gettext ("INVALID SYMBOL"),
2239                         (long int) GELF_R_SYM (rel->r_info));
2240             }
2241           else if (GELF_ST_TYPE (sym->st_info) != STT_SECTION)
2242             printf ("\
2243   %#0*" PRIx64 "  %-15s %#0*" PRIx64 "  %+6" PRId64 " %s\n",
2244                     class == ELFCLASS32 ? 10 : 18, rel->r_offset,
2245                     likely (ebl_reloc_type_check (ebl,
2246                                                   GELF_R_TYPE (rel->r_info)))
2247                     /* Avoid the leading R_ which isn't carrying any
2248                        information.  */
2249                     ? ebl_reloc_type_name (ebl, GELF_R_TYPE (rel->r_info),
2250                                            buf, sizeof (buf)) + 2
2251                     : gettext ("<INVALID RELOC>"),
2252                     class == ELFCLASS32 ? 10 : 18, sym->st_value,
2253                     rel->r_addend,
2254                     elf_strptr (ebl->elf, symshdr->sh_link, sym->st_name));
2255           else
2256             {
2257               /* This is a relocation against a STT_SECTION symbol.  */
2258               GElf_Shdr secshdr_mem;
2259               GElf_Shdr *secshdr;
2260               secshdr = gelf_getshdr (elf_getscn (ebl->elf,
2261                                                   sym->st_shndx == SHN_XINDEX
2262                                                   ? xndx : sym->st_shndx),
2263                                       &secshdr_mem);
2264
2265               if (unlikely (secshdr == NULL))
2266                 printf ("  %#0*" PRIx64 "  %-15s <%s %ld>\n",
2267                         class == ELFCLASS32 ? 10 : 18, rel->r_offset,
2268                         ebl_reloc_type_check (ebl, GELF_R_TYPE (rel->r_info))
2269                         /* Avoid the leading R_ which isn't carrying any
2270                            information.  */
2271                         ? ebl_reloc_type_name (ebl, GELF_R_TYPE (rel->r_info),
2272                                                buf, sizeof (buf)) + 2
2273                         : gettext ("<INVALID RELOC>"),
2274                         gettext ("INVALID SECTION"),
2275                         (long int) (sym->st_shndx == SHN_XINDEX
2276                                     ? xndx : sym->st_shndx));
2277               else
2278                 printf ("\
2279   %#0*" PRIx64 "  %-15s %#0*" PRIx64 "  %+6" PRId64 " %s\n",
2280                         class == ELFCLASS32 ? 10 : 18, rel->r_offset,
2281                         ebl_reloc_type_check (ebl, GELF_R_TYPE (rel->r_info))
2282                         /* Avoid the leading R_ which isn't carrying any
2283                            information.  */
2284                         ? ebl_reloc_type_name (ebl, GELF_R_TYPE (rel->r_info),
2285                                                buf, sizeof (buf)) + 2
2286                         : gettext ("<INVALID RELOC>"),
2287                         class == ELFCLASS32 ? 10 : 18, sym->st_value,
2288                         rel->r_addend,
2289                         elf_strptr (ebl->elf, shstrndx, secshdr->sh_name));
2290             }
2291         }
2292     }
2293 }
2294
2295
2296 /* Print the program header.  */
2297 static void
2298 print_symtab (Ebl *ebl, int type)
2299 {
2300   /* Find the symbol table(s).  For this we have to search through the
2301      section table.  */
2302   Elf_Scn *scn = NULL;
2303
2304   while ((scn = elf_nextscn (ebl->elf, scn)) != NULL)
2305     {
2306       /* Handle the section if it is a symbol table.  */
2307       GElf_Shdr shdr_mem;
2308       GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem);
2309
2310       if (shdr != NULL && shdr->sh_type == (GElf_Word) type)
2311         {
2312           if (symbol_table_section != NULL)
2313             {
2314               /* Get the section header string table index.  */
2315               size_t shstrndx;
2316               const char *sname;
2317               if (unlikely (elf_getshdrstrndx (ebl->elf, &shstrndx) < 0))
2318                 error (EXIT_FAILURE, 0,
2319                        gettext ("cannot get section header string table index"));
2320               sname = elf_strptr (ebl->elf, shstrndx, shdr->sh_name);
2321               if (sname == NULL || strcmp (sname, symbol_table_section) != 0)
2322                 continue;
2323             }
2324
2325           if ((shdr->sh_flags & SHF_COMPRESSED) != 0)
2326             {
2327               if (elf_compress (scn, 0, 0) < 0)
2328                 printf ("WARNING: %s [%zd]\n",
2329                         gettext ("Couldn't uncompress section"),
2330                         elf_ndxscn (scn));
2331               shdr = gelf_getshdr (scn, &shdr_mem);
2332               if (unlikely (shdr == NULL))
2333                 error (EXIT_FAILURE, 0,
2334                        gettext ("cannot get section [%zd] header: %s"),
2335                        elf_ndxscn (scn), elf_errmsg (-1));
2336             }
2337           handle_symtab (ebl, scn, shdr);
2338         }
2339     }
2340 }
2341
2342
2343 static void
2344 handle_symtab (Ebl *ebl, Elf_Scn *scn, GElf_Shdr *shdr)
2345 {
2346   Elf_Data *versym_data = NULL;
2347   Elf_Data *verneed_data = NULL;
2348   Elf_Data *verdef_data = NULL;
2349   Elf_Data *xndx_data = NULL;
2350   int class = gelf_getclass (ebl->elf);
2351   Elf32_Word verneed_stridx = 0;
2352   Elf32_Word verdef_stridx = 0;
2353
2354   /* Get the data of the section.  */
2355   Elf_Data *data = elf_getdata (scn, NULL);
2356   if (data == NULL)
2357     return;
2358
2359   /* Find out whether we have other sections we might need.  */
2360   Elf_Scn *runscn = NULL;
2361   while ((runscn = elf_nextscn (ebl->elf, runscn)) != NULL)
2362     {
2363       GElf_Shdr runshdr_mem;
2364       GElf_Shdr *runshdr = gelf_getshdr (runscn, &runshdr_mem);
2365
2366       if (likely (runshdr != NULL))
2367         {
2368           if (runshdr->sh_type == SHT_GNU_versym
2369               && runshdr->sh_link == elf_ndxscn (scn))
2370             /* Bingo, found the version information.  Now get the data.  */
2371             versym_data = elf_getdata (runscn, NULL);
2372           else if (runshdr->sh_type == SHT_GNU_verneed)
2373             {
2374               /* This is the information about the needed versions.  */
2375               verneed_data = elf_getdata (runscn, NULL);
2376               verneed_stridx = runshdr->sh_link;
2377             }
2378           else if (runshdr->sh_type == SHT_GNU_verdef)
2379             {
2380               /* This is the information about the defined versions.  */
2381               verdef_data = elf_getdata (runscn, NULL);
2382               verdef_stridx = runshdr->sh_link;
2383             }
2384           else if (runshdr->sh_type == SHT_SYMTAB_SHNDX
2385               && runshdr->sh_link == elf_ndxscn (scn))
2386             /* Extended section index.  */
2387             xndx_data = elf_getdata (runscn, NULL);
2388         }
2389     }
2390
2391   /* Get the section header string table index.  */
2392   size_t shstrndx;
2393   if (unlikely (elf_getshdrstrndx (ebl->elf, &shstrndx) < 0))
2394     error (EXIT_FAILURE, 0,
2395            gettext ("cannot get section header string table index"));
2396
2397   GElf_Shdr glink_mem;
2398   GElf_Shdr *glink = gelf_getshdr (elf_getscn (ebl->elf, shdr->sh_link),
2399                                    &glink_mem);
2400   if (glink == NULL)
2401     error (EXIT_FAILURE, 0, gettext ("invalid sh_link value in section %zu"),
2402            elf_ndxscn (scn));
2403
2404   /* Now we can compute the number of entries in the section.  */
2405   unsigned int nsyms = data->d_size / (class == ELFCLASS32
2406                                        ? sizeof (Elf32_Sym)
2407                                        : sizeof (Elf64_Sym));
2408
2409   printf (ngettext ("\nSymbol table [%2u] '%s' contains %u entry:\n",
2410                     "\nSymbol table [%2u] '%s' contains %u entries:\n",
2411                     nsyms),
2412           (unsigned int) elf_ndxscn (scn),
2413           elf_strptr (ebl->elf, shstrndx, shdr->sh_name), nsyms);
2414   printf (ngettext (" %lu local symbol  String table: [%2u] '%s'\n",
2415                     " %lu local symbols  String table: [%2u] '%s'\n",
2416                     shdr->sh_info),
2417           (unsigned long int) shdr->sh_info,
2418           (unsigned int) shdr->sh_link,
2419           elf_strptr (ebl->elf, shstrndx, glink->sh_name));
2420
2421   fputs_unlocked (class == ELFCLASS32
2422                   ? gettext ("\
2423   Num:    Value   Size Type    Bind   Vis          Ndx Name\n")
2424                   : gettext ("\
2425   Num:            Value   Size Type    Bind   Vis          Ndx Name\n"),
2426                   stdout);
2427
2428   for (unsigned int cnt = 0; cnt < nsyms; ++cnt)
2429     {
2430       char typebuf[64];
2431       char bindbuf[64];
2432       char scnbuf[64];
2433       Elf32_Word xndx;
2434       GElf_Sym sym_mem;
2435       GElf_Sym *sym = gelf_getsymshndx (data, xndx_data, cnt, &sym_mem, &xndx);
2436
2437       if (unlikely (sym == NULL))
2438         continue;
2439
2440       /* Determine the real section index.  */
2441       if (likely (sym->st_shndx != SHN_XINDEX))
2442         xndx = sym->st_shndx;
2443
2444       printf (gettext ("\
2445 %5u: %0*" PRIx64 " %6" PRId64 " %-7s %-6s %-9s %6s %s"),
2446               cnt,
2447               class == ELFCLASS32 ? 8 : 16,
2448               sym->st_value,
2449               sym->st_size,
2450               ebl_symbol_type_name (ebl, GELF_ST_TYPE (sym->st_info),
2451                                     typebuf, sizeof (typebuf)),
2452               ebl_symbol_binding_name (ebl, GELF_ST_BIND (sym->st_info),
2453                                        bindbuf, sizeof (bindbuf)),
2454               get_visibility_type (GELF_ST_VISIBILITY (sym->st_other)),
2455               ebl_section_name (ebl, sym->st_shndx, xndx, scnbuf,
2456                                 sizeof (scnbuf), NULL, shnum),
2457               elf_strptr (ebl->elf, shdr->sh_link, sym->st_name));
2458
2459       if (versym_data != NULL)
2460         {
2461           /* Get the version information.  */
2462           GElf_Versym versym_mem;
2463           GElf_Versym *versym = gelf_getversym (versym_data, cnt, &versym_mem);
2464
2465           if (versym != NULL && ((*versym & 0x8000) != 0 || *versym > 1))
2466             {
2467               bool is_nobits = false;
2468               bool check_def = xndx != SHN_UNDEF;
2469
2470               if (xndx < SHN_LORESERVE || sym->st_shndx == SHN_XINDEX)
2471                 {
2472                   GElf_Shdr symshdr_mem;
2473                   GElf_Shdr *symshdr =
2474                     gelf_getshdr (elf_getscn (ebl->elf, xndx), &symshdr_mem);
2475
2476                   is_nobits = (symshdr != NULL
2477                                && symshdr->sh_type == SHT_NOBITS);
2478                 }
2479
2480               if (is_nobits || ! check_def)
2481                 {
2482                   /* We must test both.  */
2483                   GElf_Vernaux vernaux_mem;
2484                   GElf_Vernaux *vernaux = NULL;
2485                   size_t vn_offset = 0;
2486
2487                   GElf_Verneed verneed_mem;
2488                   GElf_Verneed *verneed = gelf_getverneed (verneed_data, 0,
2489                                                            &verneed_mem);
2490                   while (verneed != NULL)
2491                     {
2492                       size_t vna_offset = vn_offset;
2493
2494                       vernaux = gelf_getvernaux (verneed_data,
2495                                                  vna_offset += verneed->vn_aux,
2496                                                  &vernaux_mem);
2497                       while (vernaux != NULL
2498                              && vernaux->vna_other != *versym
2499                              && vernaux->vna_next != 0)
2500                         {
2501                           /* Update the offset.  */
2502                           vna_offset += vernaux->vna_next;
2503
2504                           vernaux = (vernaux->vna_next == 0
2505                                      ? NULL
2506                                      : gelf_getvernaux (verneed_data,
2507                                                         vna_offset,
2508                                                         &vernaux_mem));
2509                         }
2510
2511                       /* Check whether we found the version.  */
2512                       if (vernaux != NULL && vernaux->vna_other == *versym)
2513                         /* Found it.  */
2514                         break;
2515
2516                       vn_offset += verneed->vn_next;
2517                       verneed = (verneed->vn_next == 0
2518                                  ? NULL
2519                                  : gelf_getverneed (verneed_data, vn_offset,
2520                                                     &verneed_mem));
2521                     }
2522
2523                   if (vernaux != NULL && vernaux->vna_other == *versym)
2524                     {
2525                       printf ("@%s (%u)",
2526                               elf_strptr (ebl->elf, verneed_stridx,
2527                                           vernaux->vna_name),
2528                               (unsigned int) vernaux->vna_other);
2529                       check_def = 0;
2530                     }
2531                   else if (unlikely (! is_nobits))
2532                     error (0, 0, gettext ("bad dynamic symbol"));
2533                   else
2534                     check_def = 1;
2535                 }
2536
2537               if (check_def && *versym != 0x8001)
2538                 {
2539                   /* We must test both.  */
2540                   size_t vd_offset = 0;
2541
2542                   GElf_Verdef verdef_mem;
2543                   GElf_Verdef *verdef = gelf_getverdef (verdef_data, 0,
2544                                                         &verdef_mem);
2545                   while (verdef != NULL)
2546                     {
2547                       if (verdef->vd_ndx == (*versym & 0x7fff))
2548                         /* Found the definition.  */
2549                         break;
2550
2551                       vd_offset += verdef->vd_next;
2552                       verdef = (verdef->vd_next == 0
2553                                 ? NULL
2554                                 : gelf_getverdef (verdef_data, vd_offset,
2555                                                   &verdef_mem));
2556                     }
2557
2558                   if (verdef != NULL)
2559                     {
2560                       GElf_Verdaux verdaux_mem;
2561                       GElf_Verdaux *verdaux
2562                         = gelf_getverdaux (verdef_data,
2563                                            vd_offset + verdef->vd_aux,
2564                                            &verdaux_mem);
2565
2566                       if (verdaux != NULL)
2567                         printf ((*versym & 0x8000) ? "@%s" : "@@%s",
2568                                 elf_strptr (ebl->elf, verdef_stridx,
2569                                             verdaux->vda_name));
2570                     }
2571                 }
2572             }
2573         }
2574
2575       putchar_unlocked ('\n');
2576     }
2577 }
2578
2579
2580 /* Print version information.  */
2581 static void
2582 print_verinfo (Ebl *ebl)
2583 {
2584   /* Find the version information sections.  For this we have to
2585      search through the section table.  */
2586   Elf_Scn *scn = NULL;
2587
2588   while ((scn = elf_nextscn (ebl->elf, scn)) != NULL)
2589     {
2590       /* Handle the section if it is part of the versioning handling.  */
2591       GElf_Shdr shdr_mem;
2592       GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem);
2593
2594       if (likely (shdr != NULL))
2595         {
2596           if (shdr->sh_type == SHT_GNU_verneed)
2597             handle_verneed (ebl, scn, shdr);
2598           else if (shdr->sh_type == SHT_GNU_verdef)
2599             handle_verdef (ebl, scn, shdr);
2600           else if (shdr->sh_type == SHT_GNU_versym)
2601             handle_versym (ebl, scn, shdr);
2602         }
2603     }
2604 }
2605
2606
2607 static const char *
2608 get_ver_flags (unsigned int flags)
2609 {
2610   static char buf[32];
2611   char *endp;
2612
2613   if (flags == 0)
2614     return gettext ("none");
2615
2616   if (flags & VER_FLG_BASE)
2617     endp = stpcpy (buf, "BASE ");
2618   else
2619     endp = buf;
2620
2621   if (flags & VER_FLG_WEAK)
2622     {
2623       if (endp != buf)
2624         endp = stpcpy (endp, "| ");
2625
2626       endp = stpcpy (endp, "WEAK ");
2627     }
2628
2629   if (unlikely (flags & ~(VER_FLG_BASE | VER_FLG_WEAK)))
2630     {
2631       strncpy (endp, gettext ("| <unknown>"), buf + sizeof (buf) - endp);
2632       buf[sizeof (buf) - 1] = '\0';
2633     }
2634
2635   return buf;
2636 }
2637
2638
2639 static void
2640 handle_verneed (Ebl *ebl, Elf_Scn *scn, GElf_Shdr *shdr)
2641 {
2642   int class = gelf_getclass (ebl->elf);
2643
2644   /* Get the data of the section.  */
2645   Elf_Data *data = elf_getdata (scn, NULL);
2646   if (data == NULL)
2647     return;
2648
2649   /* Get the section header string table index.  */
2650   size_t shstrndx;
2651   if (unlikely (elf_getshdrstrndx (ebl->elf, &shstrndx) < 0))
2652     error (EXIT_FAILURE, 0,
2653            gettext ("cannot get section header string table index"));
2654
2655   GElf_Shdr glink_mem;
2656   GElf_Shdr *glink = gelf_getshdr (elf_getscn (ebl->elf, shdr->sh_link),
2657                                    &glink_mem);
2658   if (glink == NULL)
2659     error (EXIT_FAILURE, 0, gettext ("invalid sh_link value in section %zu"),
2660            elf_ndxscn (scn));
2661
2662   printf (ngettext ("\
2663 \nVersion needs section [%2u] '%s' contains %d entry:\n Addr: %#0*" PRIx64 "  Offset: %#08" PRIx64 "  Link to section: [%2u] '%s'\n",
2664                     "\
2665 \nVersion needs section [%2u] '%s' contains %d entries:\n Addr: %#0*" PRIx64 "  Offset: %#08" PRIx64 "  Link to section: [%2u] '%s'\n",
2666                     shdr->sh_info),
2667           (unsigned int) elf_ndxscn (scn),
2668           elf_strptr (ebl->elf, shstrndx, shdr->sh_name), shdr->sh_info,
2669           class == ELFCLASS32 ? 10 : 18, shdr->sh_addr,
2670           shdr->sh_offset,
2671           (unsigned int) shdr->sh_link,
2672           elf_strptr (ebl->elf, shstrndx, glink->sh_name));
2673
2674   unsigned int offset = 0;
2675   for (int cnt = shdr->sh_info; --cnt >= 0; )
2676     {
2677       /* Get the data at the next offset.  */
2678       GElf_Verneed needmem;
2679       GElf_Verneed *need = gelf_getverneed (data, offset, &needmem);
2680       if (unlikely (need == NULL))
2681         break;
2682
2683       printf (gettext ("  %#06x: Version: %hu  File: %s  Cnt: %hu\n"),
2684               offset, (unsigned short int) need->vn_version,
2685               elf_strptr (ebl->elf, shdr->sh_link, need->vn_file),
2686               (unsigned short int) need->vn_cnt);
2687
2688       unsigned int auxoffset = offset + need->vn_aux;
2689       for (int cnt2 = need->vn_cnt; --cnt2 >= 0; )
2690         {
2691           GElf_Vernaux auxmem;
2692           GElf_Vernaux *aux = gelf_getvernaux (data, auxoffset, &auxmem);
2693           if (unlikely (aux == NULL))
2694             break;
2695
2696           printf (gettext ("  %#06x: Name: %s  Flags: %s  Version: %hu\n"),
2697                   auxoffset,
2698                   elf_strptr (ebl->elf, shdr->sh_link, aux->vna_name),
2699                   get_ver_flags (aux->vna_flags),
2700                   (unsigned short int) aux->vna_other);
2701
2702           if (aux->vna_next == 0)
2703             break;
2704
2705           auxoffset += aux->vna_next;
2706         }
2707
2708       /* Find the next offset.  */
2709       if (need->vn_next == 0)
2710         break;
2711
2712       offset += need->vn_next;
2713     }
2714 }
2715
2716
2717 static void
2718 handle_verdef (Ebl *ebl, Elf_Scn *scn, GElf_Shdr *shdr)
2719 {
2720   /* Get the data of the section.  */
2721   Elf_Data *data = elf_getdata (scn, NULL);
2722   if (data == NULL)
2723     return;
2724
2725   /* Get the section header string table index.  */
2726   size_t shstrndx;
2727   if (unlikely (elf_getshdrstrndx (ebl->elf, &shstrndx) < 0))
2728     error (EXIT_FAILURE, 0,
2729            gettext ("cannot get section header string table index"));
2730
2731   GElf_Shdr glink_mem;
2732   GElf_Shdr *glink = gelf_getshdr (elf_getscn (ebl->elf, shdr->sh_link),
2733                                    &glink_mem);
2734   if (glink == NULL)
2735     error (EXIT_FAILURE, 0, gettext ("invalid sh_link value in section %zu"),
2736            elf_ndxscn (scn));
2737
2738   int class = gelf_getclass (ebl->elf);
2739   printf (ngettext ("\
2740 \nVersion definition section [%2u] '%s' contains %d entry:\n Addr: %#0*" PRIx64 "  Offset: %#08" PRIx64 "  Link to section: [%2u] '%s'\n",
2741                     "\
2742 \nVersion definition section [%2u] '%s' contains %d entries:\n Addr: %#0*" PRIx64 "  Offset: %#08" PRIx64 "  Link to section: [%2u] '%s'\n",
2743                     shdr->sh_info),
2744           (unsigned int) elf_ndxscn (scn),
2745           elf_strptr (ebl->elf, shstrndx, shdr->sh_name),
2746           shdr->sh_info,
2747           class == ELFCLASS32 ? 10 : 18, shdr->sh_addr,
2748           shdr->sh_offset,
2749           (unsigned int) shdr->sh_link,
2750           elf_strptr (ebl->elf, shstrndx, glink->sh_name));
2751
2752   unsigned int offset = 0;
2753   for (int cnt = shdr->sh_info; --cnt >= 0; )
2754     {
2755       /* Get the data at the next offset.  */
2756       GElf_Verdef defmem;
2757       GElf_Verdef *def = gelf_getverdef (data, offset, &defmem);
2758       if (unlikely (def == NULL))
2759         break;
2760
2761       unsigned int auxoffset = offset + def->vd_aux;
2762       GElf_Verdaux auxmem;
2763       GElf_Verdaux *aux = gelf_getverdaux (data, auxoffset, &auxmem);
2764       if (unlikely (aux == NULL))
2765         break;
2766
2767       printf (gettext ("\
2768   %#06x: Version: %hd  Flags: %s  Index: %hd  Cnt: %hd  Name: %s\n"),
2769               offset, def->vd_version,
2770               get_ver_flags (def->vd_flags),
2771               def->vd_ndx,
2772               def->vd_cnt,
2773               elf_strptr (ebl->elf, shdr->sh_link, aux->vda_name));
2774
2775       auxoffset += aux->vda_next;
2776       for (int cnt2 = 1; cnt2 < def->vd_cnt; ++cnt2)
2777         {
2778           aux = gelf_getverdaux (data, auxoffset, &auxmem);
2779           if (unlikely (aux == NULL))
2780             break;
2781
2782           printf (gettext ("  %#06x: Parent %d: %s\n"),
2783                   auxoffset, cnt2,
2784                   elf_strptr (ebl->elf, shdr->sh_link, aux->vda_name));
2785
2786           if (aux->vda_next == 0)
2787             break;
2788
2789           auxoffset += aux->vda_next;
2790         }
2791
2792       /* Find the next offset.  */
2793       if (def->vd_next == 0)
2794         break;
2795       offset += def->vd_next;
2796     }
2797 }
2798
2799
2800 static void
2801 handle_versym (Ebl *ebl, Elf_Scn *scn, GElf_Shdr *shdr)
2802 {
2803   int class = gelf_getclass (ebl->elf);
2804   const char **vername;
2805   const char **filename;
2806
2807   /* Get the data of the section.  */
2808   Elf_Data *data = elf_getdata (scn, NULL);
2809   if (data == NULL)
2810     return;
2811
2812   /* Get the section header string table index.  */
2813   size_t shstrndx;
2814   if (unlikely (elf_getshdrstrndx (ebl->elf, &shstrndx) < 0))
2815     error (EXIT_FAILURE, 0,
2816            gettext ("cannot get section header string table index"));
2817
2818   /* We have to find the version definition section and extract the
2819      version names.  */
2820   Elf_Scn *defscn = NULL;
2821   Elf_Scn *needscn = NULL;
2822
2823   Elf_Scn *verscn = NULL;
2824   while ((verscn = elf_nextscn (ebl->elf, verscn)) != NULL)
2825     {
2826       GElf_Shdr vershdr_mem;
2827       GElf_Shdr *vershdr = gelf_getshdr (verscn, &vershdr_mem);
2828
2829       if (likely (vershdr != NULL))
2830         {
2831           if (vershdr->sh_type == SHT_GNU_verdef)
2832             defscn = verscn;
2833           else if (vershdr->sh_type == SHT_GNU_verneed)
2834             needscn = verscn;
2835         }
2836     }
2837
2838   size_t nvername;
2839   if (defscn != NULL || needscn != NULL)
2840     {
2841       /* We have a version information (better should have).  Now get
2842          the version names.  First find the maximum version number.  */
2843       nvername = 0;
2844       if (defscn != NULL)
2845         {
2846           /* Run through the version definitions and find the highest
2847              index.  */
2848           unsigned int offset = 0;
2849           Elf_Data *defdata;
2850           GElf_Shdr defshdrmem;
2851           GElf_Shdr *defshdr;
2852
2853           defdata = elf_getdata (defscn, NULL);
2854           if (unlikely (defdata == NULL))
2855             return;
2856
2857           defshdr = gelf_getshdr (defscn, &defshdrmem);
2858           if (unlikely (defshdr == NULL))
2859             return;
2860
2861           for (unsigned int cnt = 0; cnt < defshdr->sh_info; ++cnt)
2862             {
2863               GElf_Verdef defmem;
2864               GElf_Verdef *def;
2865
2866               /* Get the data at the next offset.  */
2867               def = gelf_getverdef (defdata, offset, &defmem);
2868               if (unlikely (def == NULL))
2869                 break;
2870
2871               nvername = MAX (nvername, (size_t) (def->vd_ndx & 0x7fff));
2872
2873               if (def->vd_next == 0)
2874                 break;
2875               offset += def->vd_next;
2876             }
2877         }
2878       if (needscn != NULL)
2879         {
2880           unsigned int offset = 0;
2881           Elf_Data *needdata;
2882           GElf_Shdr needshdrmem;
2883           GElf_Shdr *needshdr;
2884
2885           needdata = elf_getdata (needscn, NULL);
2886           if (unlikely (needdata == NULL))
2887             return;
2888
2889           needshdr = gelf_getshdr (needscn, &needshdrmem);
2890           if (unlikely (needshdr == NULL))
2891             return;
2892
2893           for (unsigned int cnt = 0; cnt < needshdr->sh_info; ++cnt)
2894             {
2895               GElf_Verneed needmem;
2896               GElf_Verneed *need;
2897               unsigned int auxoffset;
2898               int cnt2;
2899
2900               /* Get the data at the next offset.  */
2901               need = gelf_getverneed (needdata, offset, &needmem);
2902               if (unlikely (need == NULL))
2903                 break;
2904
2905               /* Run through the auxiliary entries.  */
2906               auxoffset = offset + need->vn_aux;
2907               for (cnt2 = need->vn_cnt; --cnt2 >= 0; )
2908                 {
2909                   GElf_Vernaux auxmem;
2910                   GElf_Vernaux *aux;
2911
2912                   aux = gelf_getvernaux (needdata, auxoffset, &auxmem);
2913                   if (unlikely (aux == NULL))
2914                     break;
2915
2916                   nvername = MAX (nvername,
2917                                   (size_t) (aux->vna_other & 0x7fff));
2918
2919                   if (aux->vna_next == 0)
2920                     break;
2921                   auxoffset += aux->vna_next;
2922                 }
2923
2924               if (need->vn_next == 0)
2925                 break;
2926               offset += need->vn_next;
2927             }
2928         }
2929
2930       /* This is the number of versions we know about.  */
2931       ++nvername;
2932
2933       /* Allocate the array.  */
2934       vername = (const char **) alloca (nvername * sizeof (const char *));
2935       memset(vername, 0, nvername * sizeof (const char *));
2936       filename = (const char **) alloca (nvername * sizeof (const char *));
2937       memset(filename, 0, nvername * sizeof (const char *));
2938
2939       /* Run through the data structures again and collect the strings.  */
2940       if (defscn != NULL)
2941         {
2942           /* Run through the version definitions and find the highest
2943              index.  */
2944           unsigned int offset = 0;
2945           Elf_Data *defdata;
2946           GElf_Shdr defshdrmem;
2947           GElf_Shdr *defshdr;
2948
2949           defdata = elf_getdata (defscn, NULL);
2950           if (unlikely (defdata == NULL))
2951             return;
2952
2953           defshdr = gelf_getshdr (defscn, &defshdrmem);
2954           if (unlikely (defshdr == NULL))
2955             return;
2956
2957           for (unsigned int cnt = 0; cnt < defshdr->sh_info; ++cnt)
2958             {
2959
2960               /* Get the data at the next offset.  */
2961               GElf_Verdef defmem;
2962               GElf_Verdef *def = gelf_getverdef (defdata, offset, &defmem);
2963               if (unlikely (def == NULL))
2964                 break;
2965
2966               GElf_Verdaux auxmem;
2967               GElf_Verdaux *aux = gelf_getverdaux (defdata,
2968                                                    offset + def->vd_aux,
2969                                                    &auxmem);
2970               if (unlikely (aux == NULL))
2971                 break;
2972
2973               vername[def->vd_ndx & 0x7fff]
2974                 = elf_strptr (ebl->elf, defshdr->sh_link, aux->vda_name);
2975               filename[def->vd_ndx & 0x7fff] = NULL;
2976
2977               if (def->vd_next == 0)
2978                 break;
2979               offset += def->vd_next;
2980             }
2981         }
2982       if (needscn != NULL)
2983         {
2984           unsigned int offset = 0;
2985
2986           Elf_Data *needdata = elf_getdata (needscn, NULL);
2987           GElf_Shdr needshdrmem;
2988           GElf_Shdr *needshdr = gelf_getshdr (needscn, &needshdrmem);
2989           if (unlikely (needdata == NULL || needshdr == NULL))
2990             return;
2991
2992           for (unsigned int cnt = 0; cnt < needshdr->sh_info; ++cnt)
2993             {
2994               /* Get the data at the next offset.  */
2995               GElf_Verneed needmem;
2996               GElf_Verneed *need = gelf_getverneed (needdata, offset,
2997                                                     &needmem);
2998               if (unlikely (need == NULL))
2999                 break;
3000
3001               /* Run through the auxiliary entries.  */
3002               unsigned int auxoffset = offset + need->vn_aux;
3003               for (int cnt2 = need->vn_cnt; --cnt2 >= 0; )
3004                 {
3005                   GElf_Vernaux auxmem;
3006                   GElf_Vernaux *aux = gelf_getvernaux (needdata, auxoffset,
3007                                                        &auxmem);
3008                   if (unlikely (aux == NULL))
3009                     break;
3010
3011                   vername[aux->vna_other & 0x7fff]
3012                     = elf_strptr (ebl->elf, needshdr->sh_link, aux->vna_name);
3013                   filename[aux->vna_other & 0x7fff]
3014                     = elf_strptr (ebl->elf, needshdr->sh_link, need->vn_file);
3015
3016                   if (aux->vna_next == 0)
3017                     break;
3018                   auxoffset += aux->vna_next;
3019                 }
3020
3021               if (need->vn_next == 0)
3022                 break;
3023               offset += need->vn_next;
3024             }
3025         }
3026     }
3027   else
3028     {
3029       vername = NULL;
3030       nvername = 1;
3031       filename = NULL;
3032     }
3033
3034   GElf_Shdr glink_mem;
3035   GElf_Shdr *glink = gelf_getshdr (elf_getscn (ebl->elf, shdr->sh_link),
3036                                    &glink_mem);
3037   size_t sh_entsize = gelf_fsize (ebl->elf, ELF_T_HALF, 1, EV_CURRENT);
3038   if (glink == NULL)
3039     error (EXIT_FAILURE, 0, gettext ("invalid sh_link value in section %zu"),
3040            elf_ndxscn (scn));
3041
3042   /* Print the header.  */
3043   printf (ngettext ("\
3044 \nVersion symbols section [%2u] '%s' contains %d entry:\n Addr: %#0*" PRIx64 "  Offset: %#08" PRIx64 "  Link to section: [%2u] '%s'",
3045                     "\
3046 \nVersion symbols section [%2u] '%s' contains %d entries:\n Addr: %#0*" PRIx64 "  Offset: %#08" PRIx64 "  Link to section: [%2u] '%s'",
3047                     shdr->sh_size / sh_entsize),
3048           (unsigned int) elf_ndxscn (scn),
3049           elf_strptr (ebl->elf, shstrndx, shdr->sh_name),
3050           (int) (shdr->sh_size / sh_entsize),
3051           class == ELFCLASS32 ? 10 : 18, shdr->sh_addr,
3052           shdr->sh_offset,
3053           (unsigned int) shdr->sh_link,
3054           elf_strptr (ebl->elf, shstrndx, glink->sh_name));
3055
3056   /* Now we can finally look at the actual contents of this section.  */
3057   for (unsigned int cnt = 0; cnt < shdr->sh_size / sh_entsize; ++cnt)
3058     {
3059       if (cnt % 2 == 0)
3060         printf ("\n %4d:", cnt);
3061
3062       GElf_Versym symmem;
3063       GElf_Versym *sym = gelf_getversym (data, cnt, &symmem);
3064       if (sym == NULL)
3065         break;
3066
3067       switch (*sym)
3068         {
3069           ssize_t n;
3070         case 0:
3071           fputs_unlocked (gettext ("   0 *local*                     "),
3072                           stdout);
3073           break;
3074
3075         case 1:
3076           fputs_unlocked (gettext ("   1 *global*                    "),
3077                           stdout);
3078           break;
3079
3080         default:
3081           n = printf ("%4d%c%s",
3082                       *sym & 0x7fff, *sym & 0x8000 ? 'h' : ' ',
3083                       (vername != NULL
3084                        && (unsigned int) (*sym & 0x7fff) < nvername)
3085                       ? vername[*sym & 0x7fff] : "???");
3086           if ((unsigned int) (*sym & 0x7fff) < nvername
3087               && filename != NULL && filename[*sym & 0x7fff] != NULL)
3088             n += printf ("(%s)", filename[*sym & 0x7fff]);
3089           printf ("%*s", MAX (0, 33 - (int) n), " ");
3090           break;
3091         }
3092     }
3093   putchar_unlocked ('\n');
3094 }
3095
3096
3097 static void
3098 print_hash_info (Ebl *ebl, Elf_Scn *scn, GElf_Shdr *shdr, size_t shstrndx,
3099                  uint_fast32_t maxlength, Elf32_Word nbucket,
3100                  uint_fast32_t nsyms, uint32_t *lengths, const char *extrastr)
3101 {
3102   uint32_t *counts = (uint32_t *) xcalloc (maxlength + 1, sizeof (uint32_t));
3103
3104   for (Elf32_Word cnt = 0; cnt < nbucket; ++cnt)
3105     ++counts[lengths[cnt]];
3106
3107   GElf_Shdr glink_mem;
3108   GElf_Shdr *glink = gelf_getshdr (elf_getscn (ebl->elf,
3109                                                shdr->sh_link),
3110                                    &glink_mem);
3111   if (glink == NULL)
3112     {
3113       error (0, 0, gettext ("invalid sh_link value in section %zu"),
3114              elf_ndxscn (scn));
3115       return;
3116     }
3117
3118   printf (ngettext ("\
3119 \nHistogram for bucket list length in section [%2u] '%s' (total of %d bucket):\n Addr: %#0*" PRIx64 "  Offset: %#08" PRIx64 "  Link to section: [%2u] '%s'\n",
3120                     "\
3121 \nHistogram for bucket list length in section [%2u] '%s' (total of %d buckets):\n Addr: %#0*" PRIx64 "  Offset: %#08" PRIx64 "  Link to section: [%2u] '%s'\n",
3122                     nbucket),
3123           (unsigned int) elf_ndxscn (scn),
3124           elf_strptr (ebl->elf, shstrndx, shdr->sh_name),
3125           (int) nbucket,
3126           gelf_getclass (ebl->elf) == ELFCLASS32 ? 10 : 18,
3127           shdr->sh_addr,
3128           shdr->sh_offset,
3129           (unsigned int) shdr->sh_link,
3130           elf_strptr (ebl->elf, shstrndx, glink->sh_name));
3131
3132   if (extrastr != NULL)
3133     fputs (extrastr, stdout);
3134
3135   if (likely (nbucket > 0))
3136     {
3137       uint64_t success = 0;
3138
3139       /* xgettext:no-c-format */
3140       fputs_unlocked (gettext ("\
3141  Length  Number  % of total  Coverage\n"), stdout);
3142       printf (gettext ("      0  %6" PRIu32 "      %5.1f%%\n"),
3143               counts[0], (counts[0] * 100.0) / nbucket);
3144
3145       uint64_t nzero_counts = 0;
3146       for (Elf32_Word cnt = 1; cnt <= maxlength; ++cnt)
3147         {
3148           nzero_counts += counts[cnt] * cnt;
3149           printf (gettext ("\
3150 %7d  %6" PRIu32 "      %5.1f%%    %5.1f%%\n"),
3151                   (int) cnt, counts[cnt], (counts[cnt] * 100.0) / nbucket,
3152                   (nzero_counts * 100.0) / nsyms);
3153         }
3154
3155       Elf32_Word acc = 0;
3156       for (Elf32_Word cnt = 1; cnt <= maxlength; ++cnt)
3157         {
3158           acc += cnt;
3159           success += counts[cnt] * acc;
3160         }
3161
3162       printf (gettext ("\
3163  Average number of tests:   successful lookup: %f\n\
3164                           unsuccessful lookup: %f\n"),
3165               (double) success / (double) nzero_counts,
3166               (double) nzero_counts / (double) nbucket);
3167     }
3168
3169   free (counts);
3170 }
3171
3172
3173 /* This function handles the traditional System V-style hash table format.  */
3174 static void
3175 handle_sysv_hash (Ebl *ebl, Elf_Scn *scn, GElf_Shdr *shdr, size_t shstrndx)
3176 {
3177   Elf_Data *data = elf_getdata (scn, NULL);
3178   if (unlikely (data == NULL))
3179     {
3180       error (0, 0, gettext ("cannot get data for section %d: %s"),
3181              (int) elf_ndxscn (scn), elf_errmsg (-1));
3182       return;
3183     }
3184
3185   if (unlikely (data->d_size < 2 * sizeof (Elf32_Word)))
3186     {
3187     invalid_data:
3188       error (0, 0, gettext ("invalid data in sysv.hash section %d"),
3189              (int) elf_ndxscn (scn));
3190       return;
3191     }
3192
3193   Elf32_Word nbucket = ((Elf32_Word *) data->d_buf)[0];
3194   Elf32_Word nchain = ((Elf32_Word *) data->d_buf)[1];
3195
3196   uint64_t used_buf = (2ULL + nchain + nbucket) * sizeof (Elf32_Word);
3197   if (used_buf > data->d_size)
3198     goto invalid_data;
3199
3200   Elf32_Word *bucket = &((Elf32_Word *) data->d_buf)[2];
3201   Elf32_Word *chain = &((Elf32_Word *) data->d_buf)[2 + nbucket];
3202
3203   uint32_t *lengths = (uint32_t *) xcalloc (nbucket, sizeof (uint32_t));
3204
3205   uint_fast32_t maxlength = 0;
3206   uint_fast32_t nsyms = 0;
3207   for (Elf32_Word cnt = 0; cnt < nbucket; ++cnt)
3208     {
3209       Elf32_Word inner = bucket[cnt];
3210       Elf32_Word chain_len = 0;
3211       while (inner > 0 && inner < nchain)
3212         {
3213           ++nsyms;
3214           ++chain_len;
3215           if (chain_len > nchain)
3216             goto invalid_data;
3217           if (maxlength < ++lengths[cnt])
3218             ++maxlength;
3219
3220           inner = chain[inner];
3221         }
3222     }
3223
3224   print_hash_info (ebl, scn, shdr, shstrndx, maxlength, nbucket, nsyms,
3225                    lengths, NULL);
3226
3227   free (lengths);
3228 }
3229
3230
3231 /* This function handles the incorrect, System V-style hash table
3232    format some 64-bit architectures use.  */
3233 static void
3234 handle_sysv_hash64 (Ebl *ebl, Elf_Scn *scn, GElf_Shdr *shdr, size_t shstrndx)
3235 {
3236   Elf_Data *data = elf_getdata (scn, NULL);
3237   if (unlikely (data == NULL))
3238     {
3239       error (0, 0, gettext ("cannot get data for section %d: %s"),
3240              (int) elf_ndxscn (scn), elf_errmsg (-1));
3241       return;
3242     }
3243
3244   if (unlikely (data->d_size < 2 * sizeof (Elf64_Xword)))
3245     {
3246     invalid_data:
3247       error (0, 0, gettext ("invalid data in sysv.hash64 section %d"),
3248              (int) elf_ndxscn (scn));
3249       return;
3250     }
3251
3252   Elf64_Xword nbucket = ((Elf64_Xword *) data->d_buf)[0];
3253   Elf64_Xword nchain = ((Elf64_Xword *) data->d_buf)[1];
3254
3255   uint64_t maxwords = data->d_size / sizeof (Elf64_Xword);
3256   if (maxwords < 2
3257       || maxwords - 2 < nbucket
3258       || maxwords - 2 - nbucket < nchain)
3259     goto invalid_data;
3260
3261   Elf64_Xword *bucket = &((Elf64_Xword *) data->d_buf)[2];
3262   Elf64_Xword *chain = &((Elf64_Xword *) data->d_buf)[2 + nbucket];
3263
3264   uint32_t *lengths = (uint32_t *) xcalloc (nbucket, sizeof (uint32_t));
3265
3266   uint_fast32_t maxlength = 0;
3267   uint_fast32_t nsyms = 0;
3268   for (Elf64_Xword cnt = 0; cnt < nbucket; ++cnt)
3269     {
3270       Elf64_Xword inner = bucket[cnt];
3271       Elf64_Xword chain_len = 0;
3272       while (inner > 0 && inner < nchain)
3273         {
3274           ++nsyms;
3275           ++chain_len;
3276           if (chain_len > nchain)
3277             goto invalid_data;
3278           if (maxlength < ++lengths[cnt])
3279             ++maxlength;
3280
3281           inner = chain[inner];
3282         }
3283     }
3284
3285   print_hash_info (ebl, scn, shdr, shstrndx, maxlength, nbucket, nsyms,
3286                    lengths, NULL);
3287
3288   free (lengths);
3289 }
3290
3291
3292 /* This function handles the GNU-style hash table format.  */
3293 static void
3294 handle_gnu_hash (Ebl *ebl, Elf_Scn *scn, GElf_Shdr *shdr, size_t shstrndx)
3295 {
3296   uint32_t *lengths = NULL;
3297   Elf_Data *data = elf_getdata (scn, NULL);
3298   if (unlikely (data == NULL))
3299     {
3300       error (0, 0, gettext ("cannot get data for section %d: %s"),
3301              (int) elf_ndxscn (scn), elf_errmsg (-1));
3302       return;
3303     }
3304
3305   if (unlikely (data->d_size < 4 * sizeof (Elf32_Word)))
3306     {
3307     invalid_data:
3308       free (lengths);
3309       error (0, 0, gettext ("invalid data in gnu.hash section %d"),
3310              (int) elf_ndxscn (scn));
3311       return;
3312     }
3313
3314   Elf32_Word nbucket = ((Elf32_Word *) data->d_buf)[0];
3315   Elf32_Word symbias = ((Elf32_Word *) data->d_buf)[1];
3316
3317   /* Next comes the size of the bitmap.  It's measured in words for
3318      the architecture.  It's 32 bits for 32 bit archs, and 64 bits for
3319      64 bit archs.  There is always a bloom filter present, so zero is
3320      an invalid value.  */
3321   Elf32_Word bitmask_words = ((Elf32_Word *) data->d_buf)[2];
3322   if (gelf_getclass (ebl->elf) == ELFCLASS64)
3323     bitmask_words *= 2;
3324
3325   if (bitmask_words == 0)
3326     goto invalid_data;
3327
3328   Elf32_Word shift = ((Elf32_Word *) data->d_buf)[3];
3329
3330   /* Is there still room for the sym chain?
3331      Use uint64_t calculation to prevent 32bit overlow.  */
3332   uint64_t used_buf = (4ULL + bitmask_words + nbucket) * sizeof (Elf32_Word);
3333   uint32_t max_nsyms = (data->d_size - used_buf) / sizeof (Elf32_Word);
3334   if (used_buf > data->d_size)
3335     goto invalid_data;
3336
3337   lengths = (uint32_t *) xcalloc (nbucket, sizeof (uint32_t));
3338
3339   Elf32_Word *bitmask = &((Elf32_Word *) data->d_buf)[4];
3340   Elf32_Word *bucket = &((Elf32_Word *) data->d_buf)[4 + bitmask_words];
3341   Elf32_Word *chain = &((Elf32_Word *) data->d_buf)[4 + bitmask_words
3342                                                     + nbucket];
3343
3344   /* Compute distribution of chain lengths.  */
3345   uint_fast32_t maxlength = 0;
3346   uint_fast32_t nsyms = 0;
3347   for (Elf32_Word cnt = 0; cnt < nbucket; ++cnt)
3348     if (bucket[cnt] != 0)
3349       {
3350         Elf32_Word inner = bucket[cnt] - symbias;
3351         do
3352           {
3353             ++nsyms;
3354             if (maxlength < ++lengths[cnt])
3355               ++maxlength;
3356             if (inner >= max_nsyms)
3357               goto invalid_data;
3358           }
3359         while ((chain[inner++] & 1) == 0);
3360       }
3361
3362   /* Count bits in bitmask.  */
3363   uint_fast32_t nbits = 0;
3364   for (Elf32_Word cnt = 0; cnt < bitmask_words; ++cnt)
3365     {
3366       uint_fast32_t word = bitmask[cnt];
3367
3368       word = (word & 0x55555555) + ((word >> 1) & 0x55555555);
3369       word = (word & 0x33333333) + ((word >> 2) & 0x33333333);
3370       word = (word & 0x0f0f0f0f) + ((word >> 4) & 0x0f0f0f0f);
3371       word = (word & 0x00ff00ff) + ((word >> 8) & 0x00ff00ff);
3372       nbits += (word & 0x0000ffff) + ((word >> 16) & 0x0000ffff);
3373     }
3374
3375   char *str;
3376   if (unlikely (asprintf (&str, gettext ("\
3377  Symbol Bias: %u\n\
3378  Bitmask Size: %zu bytes  %" PRIuFAST32 "%% bits set  2nd hash shift: %u\n"),
3379                           (unsigned int) symbias,
3380                           bitmask_words * sizeof (Elf32_Word),
3381                           ((nbits * 100 + 50)
3382                            / (uint_fast32_t) (bitmask_words
3383                                               * sizeof (Elf32_Word) * 8)),
3384                           (unsigned int) shift) == -1))
3385     error (EXIT_FAILURE, 0, gettext ("memory exhausted"));
3386
3387   print_hash_info (ebl, scn, shdr, shstrndx, maxlength, nbucket, nsyms,
3388                    lengths, str);
3389
3390   free (str);
3391   free (lengths);
3392 }
3393
3394
3395 /* Find the symbol table(s).  For this we have to search through the
3396    section table.  */
3397 static void
3398 handle_hash (Ebl *ebl)
3399 {
3400   /* Get the section header string table index.  */
3401   size_t shstrndx;
3402   if (unlikely (elf_getshdrstrndx (ebl->elf, &shstrndx) < 0))
3403     error (EXIT_FAILURE, 0,
3404            gettext ("cannot get section header string table index"));
3405
3406   Elf_Scn *scn = NULL;
3407   while ((scn = elf_nextscn (ebl->elf, scn)) != NULL)
3408     {
3409       /* Handle the section if it is a symbol table.  */
3410       GElf_Shdr shdr_mem;
3411       GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem);
3412
3413       if (likely (shdr != NULL))
3414         {
3415           if ((shdr->sh_type == SHT_HASH || shdr->sh_type == SHT_GNU_HASH)
3416               && (shdr->sh_flags & SHF_COMPRESSED) != 0)
3417             {
3418               if (elf_compress (scn, 0, 0) < 0)
3419                 printf ("WARNING: %s [%zd]\n",
3420                         gettext ("Couldn't uncompress section"),
3421                         elf_ndxscn (scn));
3422               shdr = gelf_getshdr (scn, &shdr_mem);
3423               if (unlikely (shdr == NULL))
3424                 error (EXIT_FAILURE, 0,
3425                        gettext ("cannot get section [%zd] header: %s"),
3426                        elf_ndxscn (scn), elf_errmsg (-1));
3427             }
3428
3429           if (shdr->sh_type == SHT_HASH)
3430             {
3431               if (ebl_sysvhash_entrysize (ebl) == sizeof (Elf64_Xword))
3432                 handle_sysv_hash64 (ebl, scn, shdr, shstrndx);
3433               else
3434                 handle_sysv_hash (ebl, scn, shdr, shstrndx);
3435             }
3436           else if (shdr->sh_type == SHT_GNU_HASH)
3437             handle_gnu_hash (ebl, scn, shdr, shstrndx);
3438         }
3439     }
3440 }
3441
3442
3443 static void
3444 print_liblist (Ebl *ebl)
3445 {
3446   /* Find the library list sections.  For this we have to search
3447      through the section table.  */
3448   Elf_Scn *scn = NULL;
3449
3450   /* Get the section header string table index.  */
3451   size_t shstrndx;
3452   if (unlikely (elf_getshdrstrndx (ebl->elf, &shstrndx) < 0))
3453     error (EXIT_FAILURE, 0,
3454            gettext ("cannot get section header string table index"));
3455
3456   while ((scn = elf_nextscn (ebl->elf, scn)) != NULL)
3457     {
3458       GElf_Shdr shdr_mem;
3459       GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem);
3460
3461       if (shdr != NULL && shdr->sh_type == SHT_GNU_LIBLIST)
3462         {
3463           size_t sh_entsize = gelf_fsize (ebl->elf, ELF_T_LIB, 1, EV_CURRENT);
3464           int nentries = shdr->sh_size / sh_entsize;
3465           printf (ngettext ("\
3466 \nLibrary list section [%2zu] '%s' at offset %#0" PRIx64 " contains %d entry:\n",
3467                             "\
3468 \nLibrary list section [%2zu] '%s' at offset %#0" PRIx64 " contains %d entries:\n",
3469                             nentries),
3470                   elf_ndxscn (scn),
3471                   elf_strptr (ebl->elf, shstrndx, shdr->sh_name),
3472                   shdr->sh_offset,
3473                   nentries);
3474
3475           Elf_Data *data = elf_getdata (scn, NULL);
3476           if (data == NULL)
3477             return;
3478
3479           puts (gettext ("\
3480        Library                       Time Stamp          Checksum Version Flags"));
3481
3482           for (int cnt = 0; cnt < nentries; ++cnt)
3483             {
3484               GElf_Lib lib_mem;
3485               GElf_Lib *lib = gelf_getlib (data, cnt, &lib_mem);
3486               if (unlikely (lib == NULL))
3487                 continue;
3488
3489               time_t t = (time_t) lib->l_time_stamp;
3490               struct tm *tm = gmtime (&t);
3491               if (unlikely (tm == NULL))
3492                 continue;
3493
3494               printf ("  [%2d] %-29s %04u-%02u-%02uT%02u:%02u:%02u %08x %-7u %u\n",
3495                       cnt, elf_strptr (ebl->elf, shdr->sh_link, lib->l_name),
3496                       tm->tm_year + 1900, tm->tm_mon + 1, tm->tm_mday,
3497                       tm->tm_hour, tm->tm_min, tm->tm_sec,
3498                       (unsigned int) lib->l_checksum,
3499                       (unsigned int) lib->l_version,
3500                       (unsigned int) lib->l_flags);
3501             }
3502         }
3503     }
3504 }
3505
3506 static void
3507 print_attributes (Ebl *ebl, const GElf_Ehdr *ehdr)
3508 {
3509   /* Find the object attributes sections.  For this we have to search
3510      through the section table.  */
3511   Elf_Scn *scn = NULL;
3512
3513   /* Get the section header string table index.  */
3514   size_t shstrndx;
3515   if (unlikely (elf_getshdrstrndx (ebl->elf, &shstrndx) < 0))
3516     error (EXIT_FAILURE, 0,
3517            gettext ("cannot get section header string table index"));
3518
3519   while ((scn = elf_nextscn (ebl->elf, scn)) != NULL)
3520     {
3521       GElf_Shdr shdr_mem;
3522       GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem);
3523
3524       if (shdr == NULL || (shdr->sh_type != SHT_GNU_ATTRIBUTES
3525                            && (shdr->sh_type != SHT_ARM_ATTRIBUTES
3526                                || ehdr->e_machine != EM_ARM)))
3527         continue;
3528
3529       printf (gettext ("\
3530 \nObject attributes section [%2zu] '%s' of %" PRIu64
3531                        " bytes at offset %#0" PRIx64 ":\n"),
3532               elf_ndxscn (scn),
3533               elf_strptr (ebl->elf, shstrndx, shdr->sh_name),
3534               shdr->sh_size, shdr->sh_offset);
3535
3536       Elf_Data *data = elf_rawdata (scn, NULL);
3537       if (unlikely (data == NULL || data->d_size == 0))
3538         return;
3539
3540       const unsigned char *p = data->d_buf;
3541
3542       /* There is only one 'version', A.  */
3543       if (unlikely (*p++ != 'A'))
3544         return;
3545
3546       fputs_unlocked (gettext ("  Owner          Size\n"), stdout);
3547
3548       inline size_t left (void)
3549       {
3550         return (const unsigned char *) data->d_buf + data->d_size - p;
3551       }
3552
3553       /* Loop over the sections.  */
3554       while (left () >= 4)
3555         {
3556           /* Section length.  */
3557           uint32_t len;
3558           memcpy (&len, p, sizeof len);
3559
3560           if (MY_ELFDATA != ehdr->e_ident[EI_DATA])
3561             CONVERT (len);
3562
3563           if (unlikely (len > left ()))
3564             break;
3565
3566           /* Section vendor name.  */
3567           const unsigned char *name = p + sizeof len;
3568           p += len;
3569
3570           unsigned const char *q = memchr (name, '\0', len);
3571           if (unlikely (q == NULL))
3572             break;
3573           ++q;
3574
3575           printf (gettext ("  %-13s  %4" PRIu32 "\n"), name, len);
3576
3577           bool gnu_vendor = (q - name == sizeof "gnu"
3578                              && !memcmp (name, "gnu", sizeof "gnu"));
3579
3580           /* Loop over subsections.  */
3581           if (shdr->sh_type != SHT_GNU_ATTRIBUTES
3582               || gnu_vendor)
3583             while (q < p)
3584               {
3585                 const unsigned char *const sub = q;
3586
3587                 unsigned int subsection_tag;
3588                 get_uleb128 (subsection_tag, q, p);
3589                 if (unlikely (q >= p))
3590                   break;
3591
3592                 uint32_t subsection_len;
3593                 if (unlikely (p - sub < (ptrdiff_t) sizeof subsection_len))
3594                   break;
3595
3596                 memcpy (&subsection_len, q, sizeof subsection_len);
3597
3598                 if (MY_ELFDATA != ehdr->e_ident[EI_DATA])
3599                   CONVERT (subsection_len);
3600
3601                 /* Don't overflow, ptrdiff_t might be 32bits, but signed.  */
3602                 if (unlikely (subsection_len == 0
3603                               || subsection_len >= (uint32_t) PTRDIFF_MAX
3604                               || p - sub < (ptrdiff_t) subsection_len))
3605                   break;
3606
3607                 const unsigned char *r = q + sizeof subsection_len;
3608                 q = sub + subsection_len;
3609
3610                 switch (subsection_tag)
3611                   {
3612                   default:
3613                     /* Unknown subsection, print and skip.  */
3614                     printf (gettext ("    %-4u %12" PRIu32 "\n"),
3615                             subsection_tag, subsection_len);
3616                     break;
3617
3618                   case 1:       /* Tag_File */
3619                     printf (gettext ("    File: %11" PRIu32 "\n"),
3620                             subsection_len);
3621
3622                     while (r < q)
3623                       {
3624                         unsigned int tag;
3625                         get_uleb128 (tag, r, q);
3626                         if (unlikely (r >= q))
3627                           break;
3628
3629                         /* GNU style tags have either a uleb128 value,
3630                            when lowest bit is not set, or a string
3631                            when the lowest bit is set.
3632                            "compatibility" (32) is special.  It has
3633                            both a string and a uleb128 value.  For
3634                            non-gnu we assume 6 till 31 only take ints.
3635                            XXX see arm backend, do we need a separate
3636                            hook?  */
3637                         uint64_t value = 0;
3638                         const char *string = NULL;
3639                         if (tag == 32 || (tag & 1) == 0
3640                             || (! gnu_vendor && (tag > 5 && tag < 32)))
3641                           {
3642                             get_uleb128 (value, r, q);
3643                             if (r > q)
3644                               break;
3645                           }
3646                         if (tag == 32
3647                             || ((tag & 1) != 0
3648                                 && (gnu_vendor
3649                                     || (! gnu_vendor && tag > 32)))
3650                             || (! gnu_vendor && tag > 3 && tag < 6))
3651                           {
3652                             string = (const char *) r;
3653                             r = memchr (r, '\0', q - r);
3654                             if (r == NULL)
3655                               break;
3656                             ++r;
3657                           }
3658
3659                         const char *tag_name = NULL;
3660                         const char *value_name = NULL;
3661                         ebl_check_object_attribute (ebl, (const char *) name,
3662                                                     tag, value,
3663                                                     &tag_name, &value_name);
3664
3665                         if (tag_name != NULL)
3666                           {
3667                             if (tag == 32)
3668                               printf (gettext ("      %s: %" PRId64 ", %s\n"),
3669                                       tag_name, value, string);
3670                             else if (string == NULL && value_name == NULL)
3671                               printf (gettext ("      %s: %" PRId64 "\n"),
3672                                       tag_name, value);
3673                             else
3674                               printf (gettext ("      %s: %s\n"),
3675                                       tag_name, string ?: value_name);
3676                           }
3677                         else
3678                           {
3679                             /* For "gnu" vendor 32 "compatibility" has
3680                                already been handled above.  */
3681                             assert (tag != 32
3682                                     || strcmp ((const char *) name, "gnu"));
3683                             if (string == NULL)
3684                               printf (gettext ("      %u: %" PRId64 "\n"),
3685                                       tag, value);
3686                             else
3687                               printf (gettext ("      %u: %s\n"),
3688                                       tag, string);
3689                           }
3690                       }
3691                   }
3692               }
3693         }
3694     }
3695 }
3696
3697
3698 static char *
3699 format_dwarf_addr (Dwfl_Module *dwflmod,
3700                    int address_size, Dwarf_Addr address, Dwarf_Addr raw)
3701 {
3702   /* See if there is a name we can give for this address.  */
3703   GElf_Sym sym;
3704   GElf_Off off = 0;
3705   const char *name = (print_address_names && ! print_unresolved_addresses)
3706     ? dwfl_module_addrinfo (dwflmod, address, &off, &sym, NULL, NULL, NULL)
3707     : NULL;
3708
3709   const char *scn;
3710   if (print_unresolved_addresses)
3711     {
3712       address = raw;
3713       scn = NULL;
3714     }
3715   else
3716     {
3717       /* Relativize the address.  */
3718       int n = dwfl_module_relocations (dwflmod);
3719       int i = n < 1 ? -1 : dwfl_module_relocate_address (dwflmod, &address);
3720
3721       /* In an ET_REL file there is a section name to refer to.  */
3722       scn = (i < 0 ? NULL
3723              : dwfl_module_relocation_info (dwflmod, i, NULL));
3724     }
3725
3726   char *result;
3727   if ((name != NULL
3728        ? (off != 0
3729           ? (scn != NULL
3730              ? (address_size == 0
3731                 ? asprintf (&result,
3732                             gettext ("%s+%#" PRIx64 " <%s+%#" PRIx64 ">"),
3733                             scn, address, name, off)
3734                 : asprintf (&result,
3735                             gettext ("%s+%#0*" PRIx64 " <%s+%#" PRIx64 ">"),
3736                             scn, 2 + address_size * 2, address,
3737                             name, off))
3738              : (address_size == 0
3739                 ? asprintf (&result,
3740                             gettext ("%#" PRIx64 " <%s+%#" PRIx64 ">"),
3741                             address, name, off)
3742                 : asprintf (&result,
3743                             gettext ("%#0*" PRIx64 " <%s+%#" PRIx64 ">"),
3744                             2 + address_size * 2, address,
3745                             name, off)))
3746           : (scn != NULL
3747              ? (address_size == 0
3748                 ? asprintf (&result,
3749                             gettext ("%s+%#" PRIx64 " <%s>"),
3750                             scn, address, name)
3751                 : asprintf (&result,
3752                             gettext ("%s+%#0*" PRIx64 " <%s>"),
3753                             scn, 2 + address_size * 2, address, name))
3754              : (address_size == 0
3755                 ? asprintf (&result,
3756                             gettext ("%#" PRIx64 " <%s>"),
3757                             address, name)
3758                 : asprintf (&result,
3759                             gettext ("%#0*" PRIx64 " <%s>"),
3760                             2 + address_size * 2, address, name))))
3761        : (scn != NULL
3762           ? (address_size == 0
3763              ? asprintf (&result,
3764                          gettext ("%s+%#" PRIx64),
3765                          scn, address)
3766              : asprintf (&result,
3767                          gettext ("%s+%#0*" PRIx64),
3768                          scn, 2 + address_size * 2, address))
3769           : (address_size == 0
3770              ? asprintf (&result,
3771                          "%#" PRIx64,
3772                          address)
3773              : asprintf (&result,
3774                          "%#0*" PRIx64,
3775                          2 + address_size * 2, address)))) < 0)
3776     error (EXIT_FAILURE, 0, _("memory exhausted"));
3777
3778   return result;
3779 }
3780
3781 static const char *
3782 dwarf_tag_string (unsigned int tag)
3783 {
3784   switch (tag)
3785     {
3786 #define DWARF_ONE_KNOWN_DW_TAG(NAME, CODE) case CODE: return #NAME;
3787       DWARF_ALL_KNOWN_DW_TAG
3788 #undef DWARF_ONE_KNOWN_DW_TAG
3789     default:
3790       return NULL;
3791     }
3792 }
3793
3794
3795 static const char *
3796 dwarf_attr_string (unsigned int attrnum)
3797 {
3798   switch (attrnum)
3799     {
3800 #define DWARF_ONE_KNOWN_DW_AT(NAME, CODE) case CODE: return #NAME;
3801       DWARF_ALL_KNOWN_DW_AT
3802 #undef DWARF_ONE_KNOWN_DW_AT
3803     default:
3804       return NULL;
3805     }
3806 }
3807
3808
3809 static const char *
3810 dwarf_form_string (unsigned int form)
3811 {
3812   switch (form)
3813     {
3814 #define DWARF_ONE_KNOWN_DW_FORM(NAME, CODE) case CODE: return #NAME;
3815       DWARF_ALL_KNOWN_DW_FORM
3816 #undef DWARF_ONE_KNOWN_DW_FORM
3817     default:
3818       return NULL;
3819     }
3820 }
3821
3822
3823 static const char *
3824 dwarf_lang_string (unsigned int lang)
3825 {
3826   switch (lang)
3827     {
3828 #define DWARF_ONE_KNOWN_DW_LANG(NAME, CODE) case CODE: return #NAME;
3829       DWARF_ALL_KNOWN_DW_LANG
3830 #undef DWARF_ONE_KNOWN_DW_LANG
3831     default:
3832       return NULL;
3833     }
3834 }
3835
3836
3837 static const char *
3838 dwarf_inline_string (unsigned int code)
3839 {
3840   static const char *const known[] =
3841     {
3842 #define DWARF_ONE_KNOWN_DW_INL(NAME, CODE) [CODE] = #NAME,
3843       DWARF_ALL_KNOWN_DW_INL
3844 #undef DWARF_ONE_KNOWN_DW_INL
3845     };
3846
3847   if (likely (code < sizeof (known) / sizeof (known[0])))
3848     return known[code];
3849
3850   return NULL;
3851 }
3852
3853
3854 static const char *
3855 dwarf_encoding_string (unsigned int code)
3856 {
3857   static const char *const known[] =
3858     {
3859 #define DWARF_ONE_KNOWN_DW_ATE(NAME, CODE) [CODE] = #NAME,
3860       DWARF_ALL_KNOWN_DW_ATE
3861 #undef DWARF_ONE_KNOWN_DW_ATE
3862     };
3863
3864   if (likely (code < sizeof (known) / sizeof (known[0])))
3865     return known[code];
3866
3867   return NULL;
3868 }
3869
3870
3871 static const char *
3872 dwarf_access_string (unsigned int code)
3873 {
3874   static const char *const known[] =
3875     {
3876 #define DWARF_ONE_KNOWN_DW_ACCESS(NAME, CODE) [CODE] = #NAME,
3877       DWARF_ALL_KNOWN_DW_ACCESS
3878 #undef DWARF_ONE_KNOWN_DW_ACCESS
3879     };
3880
3881   if (likely (code < sizeof (known) / sizeof (known[0])))
3882     return known[code];
3883
3884   return NULL;
3885 }
3886
3887
3888 static const char *
3889 dwarf_defaulted_string (unsigned int code)
3890 {
3891   static const char *const known[] =
3892     {
3893 #define DWARF_ONE_KNOWN_DW_DEFAULTED(NAME, CODE) [CODE] = #NAME,
3894       DWARF_ALL_KNOWN_DW_DEFAULTED
3895 #undef DWARF_ONE_KNOWN_DW_DEFAULTED
3896     };
3897
3898   if (likely (code < sizeof (known) / sizeof (known[0])))
3899     return known[code];
3900
3901   return NULL;
3902 }
3903
3904
3905 static const char *
3906 dwarf_visibility_string (unsigned int code)
3907 {
3908   static const char *const known[] =
3909     {
3910 #define DWARF_ONE_KNOWN_DW_VIS(NAME, CODE) [CODE] = #NAME,
3911       DWARF_ALL_KNOWN_DW_VIS
3912 #undef DWARF_ONE_KNOWN_DW_VIS
3913     };
3914
3915   if (likely (code < sizeof (known) / sizeof (known[0])))
3916     return known[code];
3917
3918   return NULL;
3919 }
3920
3921
3922 static const char *
3923 dwarf_virtuality_string (unsigned int code)
3924 {
3925   static const char *const known[] =
3926     {
3927 #define DWARF_ONE_KNOWN_DW_VIRTUALITY(NAME, CODE) [CODE] = #NAME,
3928       DWARF_ALL_KNOWN_DW_VIRTUALITY
3929 #undef DWARF_ONE_KNOWN_DW_VIRTUALITY
3930     };
3931
3932   if (likely (code < sizeof (known) / sizeof (known[0])))
3933     return known[code];
3934
3935   return NULL;
3936 }
3937
3938
3939 static const char *
3940 dwarf_identifier_case_string (unsigned int code)
3941 {
3942   static const char *const known[] =
3943     {
3944 #define DWARF_ONE_KNOWN_DW_ID(NAME, CODE) [CODE] = #NAME,
3945       DWARF_ALL_KNOWN_DW_ID
3946 #undef DWARF_ONE_KNOWN_DW_ID
3947     };
3948
3949   if (likely (code < sizeof (known) / sizeof (known[0])))
3950     return known[code];
3951
3952   return NULL;
3953 }
3954
3955
3956 static const char *
3957 dwarf_calling_convention_string (unsigned int code)
3958 {
3959   static const char *const known[] =
3960     {
3961 #define DWARF_ONE_KNOWN_DW_CC(NAME, CODE) [CODE] = #NAME,
3962       DWARF_ALL_KNOWN_DW_CC
3963 #undef DWARF_ONE_KNOWN_DW_CC
3964     };
3965
3966   if (likely (code < sizeof (known) / sizeof (known[0])))
3967     return known[code];
3968
3969   return NULL;
3970 }
3971
3972
3973 static const char *
3974 dwarf_ordering_string (unsigned int code)
3975 {
3976   static const char *const known[] =
3977     {
3978 #define DWARF_ONE_KNOWN_DW_ORD(NAME, CODE) [CODE] = #NAME,
3979       DWARF_ALL_KNOWN_DW_ORD
3980 #undef DWARF_ONE_KNOWN_DW_ORD
3981     };
3982
3983   if (likely (code < sizeof (known) / sizeof (known[0])))
3984     return known[code];
3985
3986   return NULL;
3987 }
3988
3989
3990 static const char *
3991 dwarf_discr_list_string (unsigned int code)
3992 {
3993   static const char *const known[] =
3994     {
3995 #define DWARF_ONE_KNOWN_DW_DSC(NAME, CODE) [CODE] = #NAME,
3996       DWARF_ALL_KNOWN_DW_DSC
3997 #undef DWARF_ONE_KNOWN_DW_DSC
3998     };
3999
4000   if (likely (code < sizeof (known) / sizeof (known[0])))
4001     return known[code];
4002
4003   return NULL;
4004 }
4005
4006
4007 static const char *
4008 dwarf_locexpr_opcode_string (unsigned int code)
4009 {
4010   static const char *const known[] =
4011     {
4012       /* Normally we can't affort building huge table of 64K entries,
4013          most of them zero, just because there are a couple defined
4014          values at the far end.  In case of opcodes, it's OK.  */
4015 #define DWARF_ONE_KNOWN_DW_OP(NAME, CODE) [CODE] = #NAME,
4016       DWARF_ALL_KNOWN_DW_OP
4017 #undef DWARF_ONE_KNOWN_DW_OP
4018     };
4019
4020   if (likely (code < sizeof (known) / sizeof (known[0])))
4021     return known[code];
4022
4023   return NULL;
4024 }
4025
4026
4027 static const char *
4028 dwarf_unit_string (unsigned int type)
4029 {
4030   switch (type)
4031     {
4032 #define DWARF_ONE_KNOWN_DW_UT(NAME, CODE) case CODE: return #NAME;
4033       DWARF_ALL_KNOWN_DW_UT
4034 #undef DWARF_ONE_KNOWN_DW_UT
4035     default:
4036       return NULL;
4037     }
4038 }
4039
4040
4041 static const char *
4042 dwarf_range_list_encoding_string (unsigned int kind)
4043 {
4044   switch (kind)
4045     {
4046 #define DWARF_ONE_KNOWN_DW_RLE(NAME, CODE) case CODE: return #NAME;
4047       DWARF_ALL_KNOWN_DW_RLE
4048 #undef DWARF_ONE_KNOWN_DW_RLE
4049     default:
4050       return NULL;
4051     }
4052 }
4053
4054
4055 static const char *
4056 dwarf_loc_list_encoding_string (unsigned int kind)
4057 {
4058   switch (kind)
4059     {
4060 #define DWARF_ONE_KNOWN_DW_LLE(NAME, CODE) case CODE: return #NAME;
4061       DWARF_ALL_KNOWN_DW_LLE
4062 #undef DWARF_ONE_KNOWN_DW_LLE
4063     default:
4064       return NULL;
4065     }
4066 }
4067
4068
4069 static const char *
4070 dwarf_line_content_description_string (unsigned int kind)
4071 {
4072   switch (kind)
4073     {
4074 #define DWARF_ONE_KNOWN_DW_LNCT(NAME, CODE) case CODE: return #NAME;
4075       DWARF_ALL_KNOWN_DW_LNCT
4076 #undef DWARF_ONE_KNOWN_DW_LNCT
4077     default:
4078       return NULL;
4079     }
4080 }
4081
4082
4083 /* Used by all dwarf_foo_name functions.  */
4084 static const char *
4085 string_or_unknown (const char *known, unsigned int code,
4086                    unsigned int lo_user, unsigned int hi_user,
4087                    bool print_unknown_num)
4088 {
4089   static char unknown_buf[20];
4090
4091   if (likely (known != NULL))
4092     return known;
4093
4094   if (lo_user != 0 && code >= lo_user && code <= hi_user)
4095     {
4096       snprintf (unknown_buf, sizeof unknown_buf, "lo_user+%#x",
4097                 code - lo_user);
4098       return unknown_buf;
4099     }
4100
4101   if (print_unknown_num)
4102     {
4103       snprintf (unknown_buf, sizeof unknown_buf, "??? (%#x)", code);
4104       return unknown_buf;
4105     }
4106
4107   return "???";
4108 }
4109
4110
4111 static const char *
4112 dwarf_tag_name (unsigned int tag)
4113 {
4114   const char *ret = dwarf_tag_string (tag);
4115   return string_or_unknown (ret, tag, DW_TAG_lo_user, DW_TAG_hi_user, true);
4116 }
4117
4118 static const char *
4119 dwarf_attr_name (unsigned int attr)
4120 {
4121   const char *ret = dwarf_attr_string (attr);
4122   return string_or_unknown (ret, attr, DW_AT_lo_user, DW_AT_hi_user, true);
4123 }
4124
4125
4126 static const char *
4127 dwarf_form_name (unsigned int form)
4128 {
4129   const char *ret = dwarf_form_string (form);
4130   return string_or_unknown (ret, form, 0, 0, true);
4131 }
4132
4133
4134 static const char *
4135 dwarf_lang_name (unsigned int lang)
4136 {
4137   const char *ret = dwarf_lang_string (lang);
4138   return string_or_unknown (ret, lang, DW_LANG_lo_user, DW_LANG_hi_user, false);
4139 }
4140
4141
4142 static const char *
4143 dwarf_inline_name (unsigned int code)
4144 {
4145   const char *ret = dwarf_inline_string (code);
4146   return string_or_unknown (ret, code, 0, 0, false);
4147 }
4148
4149
4150 static const char *
4151 dwarf_encoding_name (unsigned int code)
4152 {
4153   const char *ret = dwarf_encoding_string (code);
4154   return string_or_unknown (ret, code, DW_ATE_lo_user, DW_ATE_hi_user, false);
4155 }
4156
4157
4158 static const char *
4159 dwarf_access_name (unsigned int code)
4160 {
4161   const char *ret = dwarf_access_string (code);
4162   return string_or_unknown (ret, code, 0, 0, false);
4163 }
4164
4165
4166 static const char *
4167 dwarf_defaulted_name (unsigned int code)
4168 {
4169   const char *ret = dwarf_defaulted_string (code);
4170   return string_or_unknown (ret, code, 0, 0, false);
4171 }
4172
4173
4174 static const char *
4175 dwarf_visibility_name (unsigned int code)
4176 {
4177   const char *ret = dwarf_visibility_string (code);
4178   return string_or_unknown (ret, code, 0, 0, false);
4179 }
4180
4181
4182 static const char *
4183 dwarf_virtuality_name (unsigned int code)
4184 {
4185   const char *ret = dwarf_virtuality_string (code);
4186   return string_or_unknown (ret, code, 0, 0, false);
4187 }
4188
4189
4190 static const char *
4191 dwarf_identifier_case_name (unsigned int code)
4192 {
4193   const char *ret = dwarf_identifier_case_string (code);
4194   return string_or_unknown (ret, code, 0, 0, false);
4195 }
4196
4197
4198 static const char *
4199 dwarf_calling_convention_name (unsigned int code)
4200 {
4201   const char *ret = dwarf_calling_convention_string (code);
4202   return string_or_unknown (ret, code, DW_CC_lo_user, DW_CC_hi_user, false);
4203 }
4204
4205
4206 static const char *
4207 dwarf_ordering_name (unsigned int code)
4208 {
4209   const char *ret = dwarf_ordering_string (code);
4210   return string_or_unknown (ret, code, 0, 0, false);
4211 }
4212
4213
4214 static const char *
4215 dwarf_discr_list_name (unsigned int code)
4216 {
4217   const char *ret = dwarf_discr_list_string (code);
4218   return string_or_unknown (ret, code, 0, 0, false);
4219 }
4220
4221
4222 static const char *
4223 dwarf_unit_name (unsigned int type)
4224 {
4225   const char *ret = dwarf_unit_string (type);
4226   return string_or_unknown (ret, type, DW_UT_lo_user, DW_UT_hi_user, true);
4227 }
4228
4229
4230 static const char *
4231 dwarf_range_list_encoding_name (unsigned int kind)
4232 {
4233   const char *ret = dwarf_range_list_encoding_string (kind);
4234   return string_or_unknown (ret, kind, 0, 0, false);
4235 }
4236
4237
4238 static const char *
4239 dwarf_loc_list_encoding_name (unsigned int kind)
4240 {
4241   const char *ret = dwarf_loc_list_encoding_string (kind);
4242   return string_or_unknown (ret, kind, 0, 0, false);
4243 }
4244
4245
4246 static const char *
4247 dwarf_line_content_description_name (unsigned int kind)
4248 {
4249   const char *ret = dwarf_line_content_description_string (kind);
4250   return string_or_unknown (ret, kind, DW_LNCT_lo_user, DW_LNCT_hi_user,
4251                             false);
4252 }
4253
4254
4255 static void
4256 print_block (size_t n, const void *block)
4257 {
4258   if (n == 0)
4259     puts (_("empty block"));
4260   else
4261     {
4262       printf (_("%zu byte block:"), n);
4263       const unsigned char *data = block;
4264       do
4265         printf (" %02x", *data++);
4266       while (--n > 0);
4267       putchar ('\n');
4268     }
4269 }
4270
4271 static void
4272 print_bytes (size_t n, const unsigned char *bytes)
4273 {
4274   while (n-- > 0)
4275     {
4276       printf ("%02x", *bytes++);
4277       if (n > 0)
4278         printf (" ");
4279     }
4280 }
4281
4282 static int
4283 get_indexed_addr (Dwarf_CU *cu, Dwarf_Word idx, Dwarf_Addr *addr)
4284 {
4285   if (cu == NULL)
4286     return -1;
4287
4288   Elf_Data *debug_addr = cu->dbg->sectiondata[IDX_debug_addr];
4289   if (debug_addr == NULL)
4290     return -1;
4291
4292   Dwarf_Off base = __libdw_cu_addr_base (cu);
4293   Dwarf_Word off = idx * cu->address_size;
4294   if (base > debug_addr->d_size
4295       || off > debug_addr->d_size - base
4296       || cu->address_size > debug_addr->d_size - base - off)
4297     return -1;
4298
4299   const unsigned char *addrp = debug_addr->d_buf + base + off;
4300   if (cu->address_size == 4)
4301     *addr = read_4ubyte_unaligned (cu->dbg, addrp);
4302   else
4303     *addr = read_8ubyte_unaligned (cu->dbg, addrp);
4304
4305   return 0;
4306 }
4307
4308 static void
4309 print_ops (Dwfl_Module *dwflmod, Dwarf *dbg, int indent, int indentrest,
4310            unsigned int vers, unsigned int addrsize, unsigned int offset_size,
4311            struct Dwarf_CU *cu, Dwarf_Word len, const unsigned char *data)
4312 {
4313   const unsigned int ref_size = vers < 3 ? addrsize : offset_size;
4314
4315   if (len == 0)
4316     {
4317       printf ("%*s(empty)\n", indent, "");
4318       return;
4319     }
4320
4321 #define NEED(n)         if (len < (Dwarf_Word) (n)) goto invalid
4322 #define CONSUME(n)      NEED (n); else len -= (n)
4323
4324   Dwarf_Word offset = 0;
4325   while (len-- > 0)
4326     {
4327       uint_fast8_t op = *data++;
4328
4329       const char *op_name = dwarf_locexpr_opcode_string (op);
4330       if (unlikely (op_name == NULL))
4331         {
4332           static char buf[20];
4333           if (op >= DW_OP_lo_user)
4334             snprintf (buf, sizeof buf, "lo_user+%#x", op - DW_OP_lo_user);
4335           else
4336             snprintf (buf, sizeof buf, "??? (%#x)", op);
4337           op_name = buf;
4338         }
4339
4340       switch (op)
4341         {
4342         case DW_OP_addr:;
4343           /* Address operand.  */
4344           Dwarf_Word addr;
4345           NEED (addrsize);
4346           if (addrsize == 4)
4347             addr = read_4ubyte_unaligned (dbg, data);
4348           else if (addrsize == 8)
4349             addr = read_8ubyte_unaligned (dbg, data);
4350           else
4351             goto invalid;
4352           data += addrsize;
4353           CONSUME (addrsize);
4354
4355           char *a = format_dwarf_addr (dwflmod, 0, addr, addr);
4356           printf ("%*s[%2" PRIuMAX "] %s %s\n",
4357                   indent, "", (uintmax_t) offset, op_name, a);
4358           free (a);
4359
4360           offset += 1 + addrsize;
4361           break;
4362
4363         case DW_OP_call_ref:
4364         case DW_OP_GNU_variable_value:
4365           /* Offset operand.  */
4366           if (ref_size != 4 && ref_size != 8)
4367             goto invalid; /* Cannot be used in CFA.  */
4368           NEED (ref_size);
4369           if (ref_size == 4)
4370             addr = read_4ubyte_unaligned (dbg, data);
4371           else
4372             addr = read_8ubyte_unaligned (dbg, data);
4373           data += ref_size;
4374           CONSUME (ref_size);
4375           /* addr is a DIE offset, so format it as one.  */
4376           printf ("%*s[%2" PRIuMAX "] %s [%6" PRIxMAX "]\n",
4377                   indent, "", (uintmax_t) offset,
4378                   op_name, (uintmax_t) addr);
4379           offset += 1 + ref_size;
4380           break;
4381
4382         case DW_OP_deref_size:
4383         case DW_OP_xderef_size:
4384         case DW_OP_pick:
4385         case DW_OP_const1u:
4386           // XXX value might be modified by relocation
4387           NEED (1);
4388           printf ("%*s[%2" PRIuMAX "] %s %" PRIu8 "\n",
4389                   indent, "", (uintmax_t) offset,
4390                   op_name, *((uint8_t *) data));
4391           ++data;
4392           --len;
4393           offset += 2;
4394           break;
4395
4396         case DW_OP_const2u:
4397           NEED (2);
4398           // XXX value might be modified by relocation
4399           printf ("%*s[%2" PRIuMAX "] %s %" PRIu16 "\n",
4400                   indent, "", (uintmax_t) offset,
4401                   op_name, read_2ubyte_unaligned (dbg, data));
4402           CONSUME (2);
4403           data += 2;
4404           offset += 3;
4405           break;
4406
4407         case DW_OP_const4u:
4408           NEED (4);
4409           // XXX value might be modified by relocation
4410           printf ("%*s[%2" PRIuMAX "] %s %" PRIu32 "\n",
4411                   indent, "", (uintmax_t) offset,
4412                   op_name, read_4ubyte_unaligned (dbg, data));
4413           CONSUME (4);
4414           data += 4;
4415           offset += 5;
4416           break;
4417
4418         case DW_OP_const8u:
4419           NEED (8);
4420           // XXX value might be modified by relocation
4421           printf ("%*s[%2" PRIuMAX "] %s %" PRIu64 "\n",
4422                   indent, "", (uintmax_t) offset,
4423                   op_name, (uint64_t) read_8ubyte_unaligned (dbg, data));
4424           CONSUME (8);
4425           data += 8;
4426           offset += 9;
4427           break;
4428
4429         case DW_OP_const1s:
4430           NEED (1);
4431           // XXX value might be modified by relocation
4432           printf ("%*s[%2" PRIuMAX "] %s %" PRId8 "\n",
4433                   indent, "", (uintmax_t) offset,
4434                   op_name, *((int8_t *) data));
4435           ++data;
4436           --len;
4437           offset += 2;
4438           break;
4439
4440         case DW_OP_const2s:
4441           NEED (2);
4442           // XXX value might be modified by relocation
4443           printf ("%*s[%2" PRIuMAX "] %s %" PRId16 "\n",
4444                   indent, "", (uintmax_t) offset,
4445                   op_name, read_2sbyte_unaligned (dbg, data));
4446           CONSUME (2);
4447           data += 2;
4448           offset += 3;
4449           break;
4450
4451         case DW_OP_const4s:
4452           NEED (4);
4453           // XXX value might be modified by relocation
4454           printf ("%*s[%2" PRIuMAX "] %s %" PRId32 "\n",
4455                   indent, "", (uintmax_t) offset,
4456                   op_name, read_4sbyte_unaligned (dbg, data));
4457           CONSUME (4);
4458           data += 4;
4459           offset += 5;
4460           break;
4461
4462         case DW_OP_const8s:
4463           NEED (8);
4464           // XXX value might be modified by relocation
4465           printf ("%*s[%2" PRIuMAX "] %s %" PRId64 "\n",
4466                   indent, "", (uintmax_t) offset,
4467                   op_name, read_8sbyte_unaligned (dbg, data));
4468           CONSUME (8);
4469           data += 8;
4470           offset += 9;
4471           break;
4472
4473         case DW_OP_piece:
4474         case DW_OP_regx:
4475         case DW_OP_plus_uconst:
4476         case DW_OP_constu:;
4477           const unsigned char *start = data;
4478           uint64_t uleb;
4479           NEED (1);
4480           get_uleb128 (uleb, data, data + len);
4481           printf ("%*s[%2" PRIuMAX "] %s %" PRIu64 "\n",
4482                   indent, "", (uintmax_t) offset, op_name, uleb);
4483           CONSUME (data - start);
4484           offset += 1 + (data - start);
4485           break;
4486
4487         case DW_OP_addrx:
4488         case DW_OP_GNU_addr_index:
4489         case DW_OP_constx:
4490         case DW_OP_GNU_const_index:;
4491           start = data;
4492           NEED (1);
4493           get_uleb128 (uleb, data, data + len);
4494           printf ("%*s[%2" PRIuMAX "] %s [%" PRIu64 "] ",
4495                   indent, "", (uintmax_t) offset, op_name, uleb);
4496           CONSUME (data - start);
4497           offset += 1 + (data - start);
4498           if (get_indexed_addr (cu, uleb, &addr) != 0)
4499             printf ("???\n");
4500           else
4501             {
4502               a = format_dwarf_addr (dwflmod, 0, addr, addr);
4503               printf ("%s\n", a);
4504               free (a);
4505             }
4506           break;
4507
4508         case DW_OP_bit_piece:
4509           start = data;
4510           uint64_t uleb2;
4511           NEED (1);
4512           get_uleb128 (uleb, data, data + len);
4513           NEED (1);
4514           get_uleb128 (uleb2, data, data + len);
4515           printf ("%*s[%2" PRIuMAX "] %s %" PRIu64 ", %" PRIu64 "\n",
4516                   indent, "", (uintmax_t) offset, op_name, uleb, uleb2);
4517           CONSUME (data - start);
4518           offset += 1 + (data - start);
4519           break;
4520
4521         case DW_OP_fbreg:
4522         case DW_OP_breg0 ... DW_OP_breg31:
4523         case DW_OP_consts:
4524           start = data;
4525           int64_t sleb;
4526           NEED (1);
4527           get_sleb128 (sleb, data, data + len);
4528           printf ("%*s[%2" PRIuMAX "] %s %" PRId64 "\n",
4529                   indent, "", (uintmax_t) offset, op_name, sleb);
4530           CONSUME (data - start);
4531           offset += 1 + (data - start);
4532           break;
4533
4534         case DW_OP_bregx:
4535           start = data;
4536           NEED (1);
4537           get_uleb128 (uleb, data, data + len);
4538           NEED (1);
4539           get_sleb128 (sleb, data, data + len);
4540           printf ("%*s[%2" PRIuMAX "] %s %" PRIu64 " %" PRId64 "\n",
4541                   indent, "", (uintmax_t) offset, op_name, uleb, sleb);
4542           CONSUME (data - start);
4543           offset += 1 + (data - start);
4544           break;
4545
4546         case DW_OP_call2:
4547           NEED (2);
4548           printf ("%*s[%2" PRIuMAX "] %s [%6" PRIx16 "]\n",
4549                   indent, "", (uintmax_t) offset, op_name,
4550                   read_2ubyte_unaligned (dbg, data));
4551           CONSUME (2);
4552           data += 2;
4553           offset += 3;
4554           break;
4555
4556         case DW_OP_call4:
4557           NEED (4);
4558           printf ("%*s[%2" PRIuMAX "] %s [%6" PRIx32 "]\n",
4559                   indent, "", (uintmax_t) offset, op_name,
4560                   read_4ubyte_unaligned (dbg, data));
4561           CONSUME (4);
4562           data += 4;
4563           offset += 5;
4564           break;
4565
4566         case DW_OP_skip:
4567         case DW_OP_bra:
4568           NEED (2);
4569           printf ("%*s[%2" PRIuMAX "] %s %" PRIuMAX "\n",
4570                   indent, "", (uintmax_t) offset, op_name,
4571                   (uintmax_t) (offset + read_2sbyte_unaligned (dbg, data) + 3));
4572           CONSUME (2);
4573           data += 2;
4574           offset += 3;
4575           break;
4576
4577         case DW_OP_implicit_value:
4578           start = data;
4579           NEED (1);
4580           get_uleb128 (uleb, data, data + len);
4581           printf ("%*s[%2" PRIuMAX "] %s: ",
4582                   indent, "", (uintmax_t) offset, op_name);
4583           NEED (uleb);
4584           print_block (uleb, data);
4585           data += uleb;
4586           CONSUME (data - start);
4587           offset += 1 + (data - start);
4588           break;
4589
4590         case DW_OP_implicit_pointer:
4591         case DW_OP_GNU_implicit_pointer:
4592           /* DIE offset operand.  */
4593           start = data;
4594           NEED (ref_size);
4595           if (ref_size != 4 && ref_size != 8)
4596             goto invalid; /* Cannot be used in CFA.  */
4597           if (ref_size == 4)
4598             addr = read_4ubyte_unaligned (dbg, data);
4599           else
4600             addr = read_8ubyte_unaligned (dbg, data);
4601           data += ref_size;
4602           /* Byte offset operand.  */
4603           NEED (1);
4604           get_sleb128 (sleb, data, data + len);
4605
4606           printf ("%*s[%2" PRIuMAX "] %s [%6" PRIxMAX "] %+" PRId64 "\n",
4607                   indent, "", (intmax_t) offset,
4608                   op_name, (uintmax_t) addr, sleb);
4609           CONSUME (data - start);
4610           offset += 1 + (data - start);
4611           break;
4612
4613         case DW_OP_entry_value:
4614         case DW_OP_GNU_entry_value:
4615           /* Size plus expression block.  */
4616           start = data;
4617           NEED (1);
4618           get_uleb128 (uleb, data, data + len);
4619           printf ("%*s[%2" PRIuMAX "] %s:\n",
4620                   indent, "", (uintmax_t) offset, op_name);
4621           NEED (uleb);
4622           print_ops (dwflmod, dbg, indent + 5, indent + 5, vers,
4623                      addrsize, offset_size, cu, uleb, data);
4624           data += uleb;
4625           CONSUME (data - start);
4626           offset += 1 + (data - start);
4627           break;
4628
4629         case DW_OP_const_type:
4630         case DW_OP_GNU_const_type:
4631           /* uleb128 CU relative DW_TAG_base_type DIE offset, 1-byte
4632              unsigned size plus block.  */
4633           start = data;
4634           NEED (1);
4635           get_uleb128 (uleb, data, data + len);
4636           if (! print_unresolved_addresses && cu != NULL)
4637             uleb += cu->start;
4638           NEED (1);
4639           uint8_t usize = *(uint8_t *) data++;
4640           NEED (usize);
4641           printf ("%*s[%2" PRIuMAX "] %s [%6" PRIxMAX "] ",
4642                   indent, "", (uintmax_t) offset, op_name, uleb);
4643           print_block (usize, data);
4644           data += usize;
4645           CONSUME (data - start);
4646           offset += 1 + (data - start);
4647           break;
4648
4649         case DW_OP_regval_type:
4650         case DW_OP_GNU_regval_type:
4651           /* uleb128 register number, uleb128 CU relative
4652              DW_TAG_base_type DIE offset.  */
4653           start = data;
4654           NEED (1);
4655           get_uleb128 (uleb, data, data + len);
4656           NEED (1);
4657           get_uleb128 (uleb2, data, data + len);
4658           if (! print_unresolved_addresses && cu != NULL)
4659             uleb2 += cu->start;
4660           printf ("%*s[%2" PRIuMAX "] %s %" PRIu64 " [%6" PRIx64 "]\n",
4661                   indent, "", (uintmax_t) offset, op_name, uleb, uleb2);
4662           CONSUME (data - start);
4663           offset += 1 + (data - start);
4664           break;
4665
4666         case DW_OP_deref_type:
4667         case DW_OP_GNU_deref_type:
4668           /* 1-byte unsigned size of value, uleb128 CU relative
4669              DW_TAG_base_type DIE offset.  */
4670           start = data;
4671           NEED (1);
4672           usize = *(uint8_t *) data++;
4673           NEED (1);
4674           get_uleb128 (uleb, data, data + len);
4675           if (! print_unresolved_addresses && cu != NULL)
4676             uleb += cu->start;
4677           printf ("%*s[%2" PRIuMAX "] %s %" PRIu8 " [%6" PRIxMAX "]\n",
4678                   indent, "", (uintmax_t) offset,
4679                   op_name, usize, uleb);
4680           CONSUME (data - start);
4681           offset += 1 + (data - start);
4682           break;
4683
4684         case DW_OP_xderef_type:
4685           /* 1-byte unsigned size of value, uleb128 base_type DIE offset.  */
4686           start = data;
4687           NEED (1);
4688           usize = *(uint8_t *) data++;
4689           NEED (1);
4690           get_uleb128 (uleb, data, data + len);
4691           printf ("%*s[%4" PRIuMAX "] %s %" PRIu8 " [%6" PRIxMAX "]\n",
4692                   indent, "", (uintmax_t) offset,
4693                   op_name, usize, uleb);
4694           CONSUME (data - start);
4695           offset += 1 + (data - start);
4696           break;
4697
4698         case DW_OP_convert:
4699         case DW_OP_GNU_convert:
4700         case DW_OP_reinterpret:
4701         case DW_OP_GNU_reinterpret:
4702           /* uleb128 CU relative offset to DW_TAG_base_type, or zero
4703              for conversion to untyped.  */
4704           start = data;
4705           NEED (1);
4706           get_uleb128 (uleb, data, data + len);
4707           if (uleb != 0 && ! print_unresolved_addresses && cu != NULL)
4708             uleb += cu->start;
4709           printf ("%*s[%2" PRIuMAX "] %s [%6" PRIxMAX "]\n",
4710                   indent, "", (uintmax_t) offset, op_name, uleb);
4711           CONSUME (data - start);
4712           offset += 1 + (data - start);
4713           break;
4714
4715         case DW_OP_GNU_parameter_ref:
4716           /* 4 byte CU relative reference to the abstract optimized away
4717              DW_TAG_formal_parameter.  */
4718           NEED (4);
4719           uintmax_t param_off = (uintmax_t) read_4ubyte_unaligned (dbg, data);
4720           if (! print_unresolved_addresses && cu != NULL)
4721             param_off += cu->start;
4722           printf ("%*s[%2" PRIuMAX "] %s [%6" PRIxMAX "]\n",
4723                   indent, "", (uintmax_t) offset, op_name, param_off);
4724           CONSUME (4);
4725           data += 4;
4726           offset += 5;
4727           break;
4728
4729         default:
4730           /* No Operand.  */
4731           printf ("%*s[%2" PRIuMAX "] %s\n",
4732                   indent, "", (uintmax_t) offset, op_name);
4733           ++offset;
4734           break;
4735         }
4736
4737       indent = indentrest;
4738       continue;
4739
4740     invalid:
4741       printf (gettext ("%*s[%2" PRIuMAX "] %s  <TRUNCATED>\n"),
4742               indent, "", (uintmax_t) offset, op_name);
4743       break;
4744     }
4745 }
4746
4747
4748 struct listptr
4749 {
4750   Dwarf_Off offset:(64 - 3);
4751   bool addr64:1;
4752   bool dwarf64:1;
4753   bool warned:1;
4754   struct Dwarf_CU *cu;
4755   unsigned int attr;
4756 };
4757
4758 #define listptr_offset_size(p)  ((p)->dwarf64 ? 8 : 4)
4759 #define listptr_address_size(p) ((p)->addr64 ? 8 : 4)
4760
4761 static Dwarf_Addr
4762 cudie_base (Dwarf_Die *cudie)
4763 {
4764   Dwarf_Addr base;
4765   /* Find the base address of the compilation unit.  It will normally
4766      be specified by DW_AT_low_pc.  In DWARF-3 draft 4, the base
4767      address could be overridden by DW_AT_entry_pc.  It's been
4768      removed, but GCC emits DW_AT_entry_pc and not DW_AT_lowpc for
4769      compilation units with discontinuous ranges.  */
4770   if (unlikely (dwarf_lowpc (cudie, &base) != 0))
4771     {
4772       Dwarf_Attribute attr_mem;
4773       if (dwarf_formaddr (dwarf_attr (cudie, DW_AT_entry_pc, &attr_mem),
4774                           &base) != 0)
4775         base = 0;
4776     }
4777   return base;
4778 }
4779
4780 static Dwarf_Addr
4781 listptr_base (struct listptr *p)
4782 {
4783   Dwarf_Die cu = CUDIE (p->cu);
4784   return cudie_base (&cu);
4785 }
4786
4787 static int
4788 compare_listptr (const void *a, const void *b, void *arg)
4789 {
4790   const char *name = arg;
4791   struct listptr *p1 = (void *) a;
4792   struct listptr *p2 = (void *) b;
4793
4794   if (p1->offset < p2->offset)
4795     return -1;
4796   if (p1->offset > p2->offset)
4797     return 1;
4798
4799   if (!p1->warned && !p2->warned)
4800     {
4801       if (p1->addr64 != p2->addr64)
4802         {
4803           p1->warned = p2->warned = true;
4804           error (0, 0,
4805                  gettext ("%s %#" PRIx64 " used with different address sizes"),
4806                  name, (uint64_t) p1->offset);
4807         }
4808       if (p1->dwarf64 != p2->dwarf64)
4809         {
4810           p1->warned = p2->warned = true;
4811           error (0, 0,
4812                  gettext ("%s %#" PRIx64 " used with different offset sizes"),
4813                  name, (uint64_t) p1->offset);
4814         }
4815       if (listptr_base (p1) != listptr_base (p2))
4816         {
4817           p1->warned = p2->warned = true;
4818           error (0, 0,
4819                  gettext ("%s %#" PRIx64 " used with different base addresses"),
4820                  name, (uint64_t) p1->offset);
4821         }
4822       if (p1->attr != p2 ->attr)
4823         {
4824           p1->warned = p2->warned = true;
4825           error (0, 0,
4826                  gettext ("%s %#" PRIx64
4827                           " used with different attribute %s and %s"),
4828                  name, (uint64_t) p1->offset, dwarf_attr_name (p2->attr),
4829                  dwarf_attr_name (p2->attr));
4830         }
4831     }
4832
4833   return 0;
4834 }
4835
4836 struct listptr_table
4837 {
4838   size_t n;
4839   size_t alloc;
4840   struct listptr *table;
4841 };
4842
4843 static struct listptr_table known_locsptr;
4844 static struct listptr_table known_loclistsptr;
4845 static struct listptr_table known_rangelistptr;
4846 static struct listptr_table known_rnglistptr;
4847 static struct listptr_table known_addrbases;
4848 static struct listptr_table known_stroffbases;
4849
4850 static void
4851 reset_listptr (struct listptr_table *table)
4852 {
4853   free (table->table);
4854   table->table = NULL;
4855   table->n = table->alloc = 0;
4856 }
4857
4858 /* Returns false if offset doesn't fit.  See struct listptr.  */
4859 static bool
4860 notice_listptr (enum section_e section, struct listptr_table *table,
4861                 uint_fast8_t address_size, uint_fast8_t offset_size,
4862                 struct Dwarf_CU *cu, Dwarf_Off offset, unsigned int attr)
4863 {
4864   if (print_debug_sections & section)
4865     {
4866       if (table->n == table->alloc)
4867         {
4868           if (table->alloc == 0)
4869             table->alloc = 128;
4870           else
4871             table->alloc *= 2;
4872           table->table = xrealloc (table->table,
4873                                    table->alloc * sizeof table->table[0]);
4874         }
4875
4876       struct listptr *p = &table->table[table->n++];
4877
4878       *p = (struct listptr)
4879         {
4880           .addr64 = address_size == 8,
4881           .dwarf64 = offset_size == 8,
4882           .offset = offset,
4883           .cu = cu,
4884           .attr = attr
4885         };
4886
4887       if (p->offset != offset)
4888         {
4889           table->n--;
4890           return false;
4891         }
4892     }
4893   return true;
4894 }
4895
4896 static void
4897 sort_listptr (struct listptr_table *table, const char *name)
4898 {
4899   if (table->n > 0)
4900     qsort_r (table->table, table->n, sizeof table->table[0],
4901              &compare_listptr, (void *) name);
4902 }
4903
4904 static bool
4905 skip_listptr_hole (struct listptr_table *table, size_t *idxp,
4906                    uint_fast8_t *address_sizep, uint_fast8_t *offset_sizep,
4907                    Dwarf_Addr *base, struct Dwarf_CU **cu, ptrdiff_t offset,
4908                    unsigned char **readp, unsigned char *endp,
4909                    unsigned int *attr)
4910 {
4911   if (table->n == 0)
4912     return false;
4913
4914   while (*idxp < table->n && table->table[*idxp].offset < (Dwarf_Off) offset)
4915     ++*idxp;
4916
4917   struct listptr *p = &table->table[*idxp];
4918
4919   if (*idxp == table->n
4920       || p->offset >= (Dwarf_Off) (endp - *readp + offset))
4921     {
4922       *readp = endp;
4923       printf (gettext (" [%6tx]  <UNUSED GARBAGE IN REST OF SECTION>\n"),
4924               offset);
4925       return true;
4926     }
4927
4928   if (p->offset != (Dwarf_Off) offset)
4929     {
4930       *readp += p->offset - offset;
4931       printf (gettext (" [%6tx]  <UNUSED GARBAGE> ... %" PRIu64 " bytes ...\n"),
4932               offset, (Dwarf_Off) p->offset - offset);
4933       return true;
4934     }
4935
4936   if (address_sizep != NULL)
4937     *address_sizep = listptr_address_size (p);
4938   if (offset_sizep != NULL)
4939     *offset_sizep = listptr_offset_size (p);
4940   if (base != NULL)
4941     *base = listptr_base (p);
4942   if (cu != NULL)
4943     *cu = p->cu;
4944   if (attr != NULL)
4945     *attr = p->attr;
4946
4947   return false;
4948 }
4949
4950 static Dwarf_Off
4951 next_listptr_offset (struct listptr_table *table, size_t idx)
4952 {
4953   /* Note that multiple attributes could in theory point to the same loclist
4954      offset, so make sure we pick one that is bigger than the current one.
4955      The table is sorted on offset.  */
4956   Dwarf_Off offset = table->table[idx].offset;
4957   while (++idx < table->n)
4958     {
4959       Dwarf_Off next = table->table[idx].offset;
4960       if (next > offset)
4961         return next;
4962     }
4963   return 0;
4964 }
4965
4966 /* Returns the listptr associated with the given index, or NULL.  */
4967 static struct listptr *
4968 get_listptr (struct listptr_table *table, size_t idx)
4969 {
4970   if (idx >= table->n)
4971     return NULL;
4972   return &table->table[idx];
4973 }
4974
4975 /* Returns the next index, base address and CU associated with the
4976    list unit offsets.  If there is none false is returned, otherwise
4977    true.  Assumes the table has been sorted.  */
4978 static bool
4979 listptr_cu (struct listptr_table *table, size_t *idxp,
4980             Dwarf_Off start, Dwarf_Off end,
4981             Dwarf_Addr *base, struct Dwarf_CU **cu)
4982 {
4983   while (*idxp < table->n
4984          && table->table[*idxp].offset < start)
4985     ++*idxp;
4986
4987   if (*idxp < table->n
4988       && table->table[*idxp].offset >= start
4989       && table->table[*idxp].offset < end)
4990     {
4991       struct listptr *p = &table->table[*idxp];
4992       *base = listptr_base (p);
4993       *cu = p->cu;
4994       ++*idxp;
4995       return true;
4996     }
4997
4998   return false;
4999 }
5000
5001 static void
5002 print_debug_abbrev_section (Dwfl_Module *dwflmod __attribute__ ((unused)),
5003                             Ebl *ebl, GElf_Ehdr *ehdr,
5004                             Elf_Scn *scn, GElf_Shdr *shdr, Dwarf *dbg)
5005 {
5006   const size_t sh_size = (dbg->sectiondata[IDX_debug_abbrev] ?
5007                           dbg->sectiondata[IDX_debug_abbrev]->d_size : 0);
5008
5009   printf (gettext ("\nDWARF section [%2zu] '%s' at offset %#" PRIx64 ":\n"
5010                    " [ Code]\n"),
5011           elf_ndxscn (scn), section_name (ebl, ehdr, shdr),
5012           (uint64_t) shdr->sh_offset);
5013
5014   Dwarf_Off offset = 0;
5015   while (offset < sh_size)
5016     {
5017       printf (gettext ("\nAbbreviation section at offset %" PRIu64 ":\n"),
5018               offset);
5019
5020       while (1)
5021         {
5022           size_t length;
5023           Dwarf_Abbrev abbrev;
5024
5025           int res = dwarf_offabbrev (dbg, offset, &length, &abbrev);
5026           if (res != 0)
5027             {
5028               if (unlikely (res < 0))
5029                 {
5030                   printf (gettext ("\
5031  *** error while reading abbreviation: %s\n"),
5032                           dwarf_errmsg (-1));
5033                   return;
5034                 }
5035
5036               /* This is the NUL byte at the end of the section.  */
5037               ++offset;
5038               break;
5039             }
5040
5041           /* We know these calls can never fail.  */
5042           unsigned int code = dwarf_getabbrevcode (&abbrev);
5043           unsigned int tag = dwarf_getabbrevtag (&abbrev);
5044           int has_children = dwarf_abbrevhaschildren (&abbrev);
5045
5046           printf (gettext (" [%5u] offset: %" PRId64
5047                            ", children: %s, tag: %s\n"),
5048                   code, (int64_t) offset,
5049                   has_children ? gettext ("yes") : gettext ("no"),
5050                   dwarf_tag_name (tag));
5051
5052           size_t cnt = 0;
5053           unsigned int name;
5054           unsigned int form;
5055           Dwarf_Sword data;
5056           Dwarf_Off enoffset;
5057           while (dwarf_getabbrevattr_data (&abbrev, cnt, &name, &form,
5058                                            &data, &enoffset) == 0)
5059             {
5060               printf ("          attr: %s, form: %s",
5061                       dwarf_attr_name (name), dwarf_form_name (form));
5062               if (form == DW_FORM_implicit_const)
5063                 printf (" (%" PRId64 ")", data);
5064               printf (", offset: %#" PRIx64 "\n", (uint64_t) enoffset);
5065               ++cnt;
5066             }
5067
5068           offset += length;
5069         }
5070     }
5071 }
5072
5073
5074 static void
5075 print_debug_addr_section (Dwfl_Module *dwflmod __attribute__ ((unused)),
5076                           Ebl *ebl, GElf_Ehdr *ehdr,
5077                           Elf_Scn *scn, GElf_Shdr *shdr, Dwarf *dbg)
5078 {
5079   printf (gettext ("\
5080 \nDWARF section [%2zu] '%s' at offset %#" PRIx64 ":\n"),
5081           elf_ndxscn (scn), section_name (ebl, ehdr, shdr),
5082           (uint64_t) shdr->sh_offset);
5083
5084   if (shdr->sh_size == 0)
5085     return;
5086
5087   /* We like to get the section from libdw to make sure they are relocated.  */
5088   Elf_Data *data = (dbg->sectiondata[IDX_debug_addr]
5089                     ?: elf_rawdata (scn, NULL));
5090   if (unlikely (data == NULL))
5091     {
5092       error (0, 0, gettext ("cannot get .debug_addr section data: %s"),
5093              elf_errmsg (-1));
5094       return;
5095     }
5096
5097   size_t idx = 0;
5098   sort_listptr (&known_addrbases, "addr_base");
5099
5100   const unsigned char *start = (const unsigned char *) data->d_buf;
5101   const unsigned char *readp = start;
5102   const unsigned char *readendp = ((const unsigned char *) data->d_buf
5103                                    + data->d_size);
5104
5105   while (readp < readendp)
5106     {
5107       /* We cannot really know whether or not there is an header.  The
5108          DebugFission extension to DWARF4 doesn't add one.  The DWARF5
5109          .debug_addr variant does.  Whether or not we have an header,
5110          DW_AT_[GNU_]addr_base points at "index 0".  So if the current
5111          offset equals the CU addr_base then we can just start
5112          printing addresses.  If there is no CU with an exact match
5113          then we'll try to parse the header first.  */
5114       Dwarf_Off off = (Dwarf_Off) (readp
5115                                    - (const unsigned char *) data->d_buf);
5116
5117       printf ("Table at offset %" PRIx64 " ", off);
5118
5119       struct listptr *listptr = get_listptr (&known_addrbases, idx++);
5120       const unsigned char *next_unitp;
5121
5122       uint64_t unit_length;
5123       uint16_t version;
5124       uint8_t address_size;
5125       uint8_t segment_size;
5126       if (listptr == NULL)
5127         {
5128           error (0, 0, "Warning: No CU references .debug_addr after %" PRIx64,
5129                  off);
5130
5131           /* We will have to assume it is just addresses to the end... */
5132           address_size = ehdr->e_ident[EI_CLASS] == ELFCLASS32 ? 4 : 8;
5133           next_unitp = readendp;
5134           printf ("Unknown CU:\n");
5135         }
5136       else
5137         {
5138           Dwarf_Die cudie;
5139           if (dwarf_cu_die (listptr->cu, &cudie,
5140                             NULL, NULL, NULL, NULL,
5141                             NULL, NULL) == NULL)
5142             printf ("Unknown CU (%s):\n", dwarf_errmsg (-1));
5143           else
5144             printf ("for CU [%6" PRIx64 "]:\n", dwarf_dieoffset (&cudie));
5145
5146           if (listptr->offset == off)
5147             {
5148               address_size = listptr_address_size (listptr);
5149               segment_size = 0;
5150               version = 4;
5151
5152               /* The addresses start here, but where do they end?  */
5153               listptr = get_listptr (&known_addrbases, idx);
5154               if (listptr == NULL)
5155                 {
5156                   next_unitp = readendp;
5157                   unit_length = (uint64_t) (next_unitp - readp);
5158                 }
5159               else if (listptr->cu->version < 5)
5160                 {
5161                   next_unitp = start + listptr->offset;
5162                   if (listptr->offset < off || listptr->offset > data->d_size)
5163                     {
5164                       error (0, 0,
5165                              "Warning: Bad address base for next unit at %"
5166                              PRIx64, off);
5167                       next_unitp = readendp;
5168                     }
5169                   unit_length = (uint64_t) (next_unitp - readp);
5170                 }
5171               else
5172                 {
5173                   /* Tricky, we don't have a header for this unit, but
5174                      there is one for the next.  We will have to
5175                      "guess" how big it is and subtract it from the
5176                      offset (because that points after the header).  */
5177                   unsigned int offset_size = listptr_offset_size (listptr);
5178                   Dwarf_Off next_off = (listptr->offset
5179                                         - (offset_size == 4 ? 4 : 12) /* len */
5180                                         - 2 /* version */
5181                                         - 1 /* address size */
5182                                         - 1); /* segment selector size */
5183                   next_unitp = start + next_off;
5184                   if (next_off < off || next_off > data->d_size)
5185                     {
5186                       error (0, 0,
5187                              "Warning: Couldn't calculate .debug_addr "
5188                              " unit lenght at %" PRIx64, off);
5189                       next_unitp = readendp;
5190                     }
5191                 }
5192
5193               /* Pretend we have a header.  */
5194               printf ("\n");
5195               printf (gettext (" Length:         %8" PRIu64 "\n"),
5196                       unit_length);
5197               printf (gettext (" DWARF version:  %8" PRIu16 "\n"), version);
5198               printf (gettext (" Address size:   %8" PRIu64 "\n"),
5199                       (uint64_t) address_size);
5200               printf (gettext (" Segment size:   %8" PRIu64 "\n"),
5201                       (uint64_t) segment_size);
5202               printf ("\n");
5203             }
5204           else
5205             {
5206               /* OK, we have to parse an header first.  */
5207               unit_length = read_4ubyte_unaligned_inc (dbg, readp);
5208               if (unlikely (unit_length == 0xffffffff))
5209                 {
5210                   if (unlikely (readp > readendp - 8))
5211                     {
5212                     invalid_data:
5213                       error (0, 0, "Invalid data");
5214                       return;
5215                     }
5216                   unit_length = read_8ubyte_unaligned_inc (dbg, readp);
5217                 }
5218               printf ("\n");
5219               printf (gettext (" Length:         %8" PRIu64 "\n"),
5220                       unit_length);
5221
5222               /* We need at least 2-bytes (version) + 1-byte
5223                  (addr_size) + 1-byte (segment_size) = 4 bytes to
5224                  complete the header.  And this unit cannot go beyond
5225                  the section data.  */
5226               if (readp > readendp - 4
5227                   || unit_length < 4
5228                   || unit_length > (uint64_t) (readendp - readp))
5229                 goto invalid_data;
5230
5231               next_unitp = readp + unit_length;
5232
5233               version = read_2ubyte_unaligned_inc (dbg, readp);
5234               printf (gettext (" DWARF version:  %8" PRIu16 "\n"), version);
5235
5236               if (version != 5)
5237                 {
5238                   error (0, 0, gettext ("Unknown version"));
5239                   goto next_unit;
5240                 }
5241
5242               address_size = *readp++;
5243               printf (gettext (" Address size:   %8" PRIu64 "\n"),
5244                       (uint64_t) address_size);
5245
5246               if (address_size != 4 && address_size != 8)
5247                 {
5248                   error (0, 0, gettext ("unsupported address size"));
5249                   goto next_unit;
5250                 }
5251
5252               segment_size = *readp++;
5253               printf (gettext (" Segment size:   %8" PRIu64 "\n"),
5254                       (uint64_t) segment_size);
5255               printf ("\n");
5256
5257               if (segment_size != 0)
5258                 {
5259                   error (0, 0, gettext ("unsupported segment size"));
5260                   goto next_unit;
5261                 }
5262
5263               if (listptr->offset != (Dwarf_Off) (readp - start))
5264                 {
5265                   error (0, 0, "Address index doesn't start after header");
5266                   goto next_unit;
5267                 }
5268             }
5269         }
5270
5271       int digits = 1;
5272       size_t addresses = (next_unitp - readp) / address_size;
5273       while (addresses >= 10)
5274         {
5275           ++digits;
5276           addresses /= 10;
5277         }
5278
5279       unsigned int index = 0;
5280       size_t index_offset =  readp - (const unsigned char *) data->d_buf;
5281       printf (" Addresses start at offset 0x%zx:\n", index_offset);
5282       while (readp <= next_unitp - address_size)
5283         {
5284           Dwarf_Addr addr = read_addr_unaligned_inc (address_size, dbg,
5285                                                      readp);
5286           printf (" [%*u] ", digits, index++);
5287           char *a = format_dwarf_addr (dwflmod, address_size,
5288                                        addr, addr);
5289           printf ("%s\n", a);
5290           free (a);
5291         }
5292       printf ("\n");
5293
5294       if (readp != next_unitp)
5295         error (0, 0, "extra %zd bytes at end of unit",
5296                (size_t) (next_unitp - readp));
5297
5298     next_unit:
5299       readp = next_unitp;
5300     }
5301 }
5302
5303 /* Print content of DWARF .debug_aranges section.  We fortunately do
5304    not have to know a bit about the structure of the section, libdwarf
5305    takes care of it.  */
5306 static void
5307 print_decoded_aranges_section (Ebl *ebl, GElf_Ehdr *ehdr, Elf_Scn *scn,
5308                                GElf_Shdr *shdr, Dwarf *dbg)
5309 {
5310   Dwarf_Aranges *aranges;
5311   size_t cnt;
5312   if (unlikely (dwarf_getaranges (dbg, &aranges, &cnt) != 0))
5313     {
5314       error (0, 0, gettext ("cannot get .debug_aranges content: %s"),
5315              dwarf_errmsg (-1));
5316       return;
5317     }
5318
5319   GElf_Shdr glink_mem;
5320   GElf_Shdr *glink;
5321   glink = gelf_getshdr (elf_getscn (ebl->elf, shdr->sh_link), &glink_mem);
5322   if (glink == NULL)
5323     {
5324       error (0, 0, gettext ("invalid sh_link value in section %zu"),
5325              elf_ndxscn (scn));
5326       return;
5327     }
5328
5329   printf (ngettext ("\
5330 \nDWARF section [%2zu] '%s' at offset %#" PRIx64 " contains %zu entry:\n",
5331                     "\
5332 \nDWARF section [%2zu] '%s' at offset %#" PRIx64 " contains %zu entries:\n",
5333                     cnt),
5334           elf_ndxscn (scn), section_name (ebl, ehdr, shdr),
5335           (uint64_t) shdr->sh_offset, cnt);
5336
5337   /* Compute floor(log16(cnt)).  */
5338   size_t tmp = cnt;
5339   int digits = 1;
5340   while (tmp >= 16)
5341     {
5342       ++digits;
5343       tmp >>= 4;
5344     }
5345
5346   for (size_t n = 0; n < cnt; ++n)
5347     {
5348       Dwarf_Arange *runp = dwarf_onearange (aranges, n);
5349       if (unlikely (runp == NULL))
5350         {
5351           printf ("cannot get arange %zu: %s\n", n, dwarf_errmsg (-1));
5352           return;
5353         }
5354
5355       Dwarf_Addr start;
5356       Dwarf_Word length;
5357       Dwarf_Off offset;
5358
5359       if (unlikely (dwarf_getarangeinfo (runp, &start, &length, &offset) != 0))
5360         printf (gettext (" [%*zu] ???\n"), digits, n);
5361       else
5362         printf (gettext (" [%*zu] start: %0#*" PRIx64
5363                          ", length: %5" PRIu64 ", CU DIE offset: %6"
5364                          PRId64 "\n"),
5365                 digits, n, ehdr->e_ident[EI_CLASS] == ELFCLASS32 ? 10 : 18,
5366                 (uint64_t) start, (uint64_t) length, (int64_t) offset);
5367     }
5368 }
5369
5370
5371 /* Print content of DWARF .debug_aranges section.  */
5372 static void
5373 print_debug_aranges_section (Dwfl_Module *dwflmod __attribute__ ((unused)),
5374                              Ebl *ebl, GElf_Ehdr *ehdr, Elf_Scn *scn,
5375                              GElf_Shdr *shdr, Dwarf *dbg)
5376 {
5377   if (decodedaranges)
5378     {
5379       print_decoded_aranges_section (ebl, ehdr, scn, shdr, dbg);
5380       return;
5381     }
5382
5383   Elf_Data *data = (dbg->sectiondata[IDX_debug_aranges]
5384                     ?: elf_rawdata (scn, NULL));
5385
5386   if (unlikely (data == NULL))
5387     {
5388       error (0, 0, gettext ("cannot get .debug_aranges content: %s"),
5389              elf_errmsg (-1));
5390       return;
5391     }
5392
5393   printf (gettext ("\
5394 \nDWARF section [%2zu] '%s' at offset %#" PRIx64 ":\n"),
5395           elf_ndxscn (scn), section_name (ebl, ehdr, shdr),
5396           (uint64_t) shdr->sh_offset);
5397
5398   const unsigned char *readp = data->d_buf;
5399   const unsigned char *readendp = readp + data->d_size;
5400
5401   while (readp < readendp)
5402     {
5403       const unsigned char *hdrstart = readp;
5404       size_t start_offset = hdrstart - (const unsigned char *) data->d_buf;
5405
5406       printf (gettext ("\nTable at offset %zu:\n"), start_offset);
5407       if (readp + 4 > readendp)
5408         {
5409         invalid_data:
5410           error (0, 0, gettext ("invalid data in section [%zu] '%s'"),
5411                  elf_ndxscn (scn), section_name (ebl, ehdr, shdr));
5412           return;
5413         }
5414
5415       Dwarf_Word length = read_4ubyte_unaligned_inc (dbg, readp);
5416       unsigned int length_bytes = 4;
5417       if (length == DWARF3_LENGTH_64_BIT)
5418         {
5419           if (readp + 8 > readendp)
5420             goto invalid_data;
5421           length = read_8ubyte_unaligned_inc (dbg, readp);
5422           length_bytes = 8;
5423         }
5424
5425       const unsigned char *nexthdr = readp + length;
5426       printf (gettext ("\n Length:        %6" PRIu64 "\n"),
5427               (uint64_t) length);
5428
5429       if (unlikely (length > (size_t) (readendp - readp)))
5430         goto invalid_data;
5431
5432       if (length == 0)
5433         continue;
5434
5435       if (readp + 2 > readendp)
5436         goto invalid_data;
5437       uint_fast16_t version = read_2ubyte_unaligned_inc (dbg, readp);
5438       printf (gettext (" DWARF version: %6" PRIuFAST16 "\n"),
5439               version);
5440       if (version != 2)
5441         {
5442           error (0, 0, gettext ("unsupported aranges version"));
5443           goto next_table;
5444         }
5445
5446       Dwarf_Word offset;
5447       if (readp + length_bytes > readendp)
5448         goto invalid_data;
5449       if (length_bytes == 8)
5450         offset = read_8ubyte_unaligned_inc (dbg, readp);
5451       else
5452         offset = read_4ubyte_unaligned_inc (dbg, readp);
5453       printf (gettext (" CU offset:     %6" PRIx64 "\n"),
5454               (uint64_t) offset);
5455
5456       if (readp + 1 > readendp)
5457         goto invalid_data;
5458       unsigned int address_size = *readp++;
5459       printf (gettext (" Address size:  %6" PRIu64 "\n"),
5460               (uint64_t) address_size);
5461       if (address_size != 4 && address_size != 8)
5462         {
5463           error (0, 0, gettext ("unsupported address size"));
5464           goto next_table;
5465         }
5466
5467       unsigned int segment_size = *readp++;
5468       printf (gettext (" Segment size:  %6" PRIu64 "\n\n"),
5469               (uint64_t) segment_size);
5470       if (segment_size != 0 && segment_size != 4 && segment_size != 8)
5471         {
5472           error (0, 0, gettext ("unsupported segment size"));
5473           goto next_table;
5474         }
5475
5476       /* Round the address to the next multiple of 2*address_size.  */
5477       readp += ((2 * address_size - ((readp - hdrstart) % (2 * address_size)))
5478                 % (2 * address_size));
5479
5480       while (readp < nexthdr)
5481         {
5482           Dwarf_Word range_address;
5483           Dwarf_Word range_length;
5484           Dwarf_Word segment = 0;
5485           if (readp + 2 * address_size + segment_size > readendp)
5486             goto invalid_data;
5487           if (address_size == 4)
5488             {
5489               range_address = read_4ubyte_unaligned_inc (dbg, readp);
5490               range_length = read_4ubyte_unaligned_inc (dbg, readp);
5491             }
5492           else
5493             {
5494               range_address = read_8ubyte_unaligned_inc (dbg, readp);
5495               range_length = read_8ubyte_unaligned_inc (dbg, readp);
5496             }
5497
5498           if (segment_size == 4)
5499             segment = read_4ubyte_unaligned_inc (dbg, readp);
5500           else if (segment_size == 8)
5501             segment = read_8ubyte_unaligned_inc (dbg, readp);
5502
5503           if (range_address == 0 && range_length == 0 && segment == 0)
5504             break;
5505
5506           char *b = format_dwarf_addr (dwflmod, address_size, range_address,
5507                                        range_address);
5508           char *e = format_dwarf_addr (dwflmod, address_size,
5509                                        range_address + range_length - 1,
5510                                        range_length);
5511           if (segment_size != 0)
5512             printf (gettext ("   %s..%s (%" PRIx64 ")\n"), b, e,
5513                     (uint64_t) segment);
5514           else
5515             printf (gettext ("   %s..%s\n"), b, e);
5516           free (b);
5517           free (e);
5518         }
5519
5520     next_table:
5521       if (readp != nexthdr)
5522         {
5523           size_t padding = nexthdr - readp;
5524           printf (gettext ("   %zu padding bytes\n"), padding);
5525           readp = nexthdr;
5526         }
5527     }
5528 }
5529
5530
5531 static bool is_split_dwarf (Dwarf *dbg, uint64_t *id, Dwarf_CU **split_cu);
5532
5533 /* Returns true and sets cu and cu_base if the given Dwarf is a split
5534    DWARF (.dwo) file.  */
5535 static bool
5536 split_dwarf_cu_base (Dwarf *dbg, Dwarf_CU **cu, Dwarf_Addr *cu_base)
5537 {
5538   uint64_t id;
5539   if (is_split_dwarf (dbg, &id, cu))
5540     {
5541       Dwarf_Die cudie;
5542       if (dwarf_cu_info (*cu, NULL, NULL, &cudie, NULL, NULL, NULL, NULL) == 0)
5543         {
5544           *cu_base = cudie_base (&cudie);
5545           return true;
5546         }
5547     }
5548   return false;
5549 }
5550
5551 /* Print content of DWARF .debug_rnglists section.  */
5552 static void
5553 print_debug_rnglists_section (Dwfl_Module *dwflmod,
5554                               Ebl *ebl, GElf_Ehdr *ehdr,
5555                               Elf_Scn *scn, GElf_Shdr *shdr,
5556                               Dwarf *dbg __attribute__((unused)))
5557 {
5558   printf (gettext ("\
5559 \nDWARF section [%2zu] '%s' at offset %#" PRIx64 ":\n"),
5560           elf_ndxscn (scn), section_name (ebl, ehdr, shdr),
5561           (uint64_t) shdr->sh_offset);
5562
5563   Elf_Data *data =(dbg->sectiondata[IDX_debug_rnglists]
5564                    ?: elf_rawdata (scn, NULL));
5565   if (unlikely (data == NULL))
5566     {
5567       error (0, 0, gettext ("cannot get .debug_rnglists content: %s"),
5568              elf_errmsg (-1));
5569       return;
5570     }
5571
5572   /* For the listptr to get the base address/CU.  */
5573   sort_listptr (&known_rnglistptr, "rnglistptr");
5574   size_t listptr_idx = 0;
5575
5576   const unsigned char *readp = data->d_buf;
5577   const unsigned char *const dataend = ((unsigned char *) data->d_buf
5578                                         + data->d_size);
5579   while (readp < dataend)
5580     {
5581       if (unlikely (readp > dataend - 4))
5582         {
5583         invalid_data:
5584           error (0, 0, gettext ("invalid data in section [%zu] '%s'"),
5585                  elf_ndxscn (scn), section_name (ebl, ehdr, shdr));
5586           return;
5587         }
5588
5589       ptrdiff_t offset = readp - (unsigned char *) data->d_buf;
5590       printf (gettext ("Table at Offset 0x%" PRIx64 ":\n\n"),
5591               (uint64_t) offset);
5592
5593       uint64_t unit_length = read_4ubyte_unaligned_inc (dbg, readp);
5594       unsigned int offset_size = 4;
5595       if (unlikely (unit_length == 0xffffffff))
5596         {
5597           if (unlikely (readp > dataend - 8))
5598             goto invalid_data;
5599
5600           unit_length = read_8ubyte_unaligned_inc (dbg, readp);
5601           offset_size = 8;
5602         }
5603       printf (gettext (" Length:         %8" PRIu64 "\n"), unit_length);
5604
5605       /* We need at least 2-bytes + 1-byte + 1-byte + 4-bytes = 8
5606          bytes to complete the header.  And this unit cannot go beyond
5607          the section data.  */
5608       if (readp > dataend - 8
5609           || unit_length < 8
5610           || unit_length > (uint64_t) (dataend - readp))
5611         goto invalid_data;
5612
5613       const unsigned char *nexthdr = readp + unit_length;
5614
5615       uint16_t version = read_2ubyte_unaligned_inc (dbg, readp);
5616       printf (gettext (" DWARF version:  %8" PRIu16 "\n"), version);
5617
5618       if (version != 5)
5619         {
5620           error (0, 0, gettext ("Unknown version"));
5621           goto next_table;
5622         }
5623
5624       uint8_t address_size = *readp++;
5625       printf (gettext (" Address size:   %8" PRIu64 "\n"),
5626               (uint64_t) address_size);
5627
5628       if (address_size != 4 && address_size != 8)
5629         {
5630           error (0, 0, gettext ("unsupported address size"));
5631           goto next_table;
5632         }
5633
5634       uint8_t segment_size = *readp++;
5635       printf (gettext (" Segment size:   %8" PRIu64 "\n"),
5636               (uint64_t) segment_size);
5637
5638       if (segment_size != 0 && segment_size != 4 && segment_size != 8)
5639         {
5640           error (0, 0, gettext ("unsupported segment size"));
5641           goto next_table;
5642         }
5643
5644       uint32_t offset_entry_count = read_4ubyte_unaligned_inc (dbg, readp);
5645       printf (gettext (" Offset entries: %8" PRIu64 "\n"),
5646               (uint64_t) offset_entry_count);
5647
5648       /* We need the CU that uses this unit to get the initial base address. */
5649       Dwarf_Addr cu_base = 0;
5650       struct Dwarf_CU *cu = NULL;
5651       if (listptr_cu (&known_rnglistptr, &listptr_idx,
5652                       (Dwarf_Off) offset,
5653                       (Dwarf_Off) (nexthdr - (unsigned char *) data->d_buf),
5654                       &cu_base, &cu)
5655           || split_dwarf_cu_base (dbg, &cu, &cu_base))
5656         {
5657           char *basestr = format_dwarf_addr (dwflmod, address_size,
5658                                              cu_base, cu_base);
5659           Dwarf_Die cudie;
5660           if (dwarf_cu_die (cu, &cudie,
5661                             NULL, NULL, NULL, NULL,
5662                             NULL, NULL) == NULL)
5663             printf (gettext (" Unknown CU base: %s\n"), basestr);
5664           else
5665             printf (gettext (" CU [%6" PRIx64 "] base: %s\n"),
5666                     dwarf_dieoffset (&cudie), basestr);
5667           free (basestr);
5668         }
5669       else
5670         printf (gettext (" Not associated with a CU.\n"));
5671
5672       printf ("\n");
5673
5674       const unsigned char *offset_array_start = readp;
5675       if (offset_entry_count > 0)
5676         {
5677           uint64_t needed = offset_entry_count * offset_size;
5678           if (unit_length - 8 < needed)
5679             {
5680               error (0, 0,
5681                      gettext ("too many offset entries for unit length"));
5682               goto next_table;
5683             }
5684
5685           printf (gettext ("  Offsets starting at 0x%" PRIx64 ":\n"),
5686                   (uint64_t) (offset_array_start
5687                               - (unsigned char *) data->d_buf));
5688           for (uint32_t idx = 0; idx < offset_entry_count; idx++)
5689             {
5690               printf ("   [%6" PRIu32 "] ", idx);
5691               if (offset_size == 4)
5692                 {
5693                   uint32_t off = read_4ubyte_unaligned_inc (dbg, readp);
5694                   printf ("0x%" PRIx32 "\n", off);
5695                 }
5696               else
5697                 {
5698                   uint64_t off = read_8ubyte_unaligned_inc (dbg, readp);
5699                   printf ("0x%" PRIx64 "\n", off);
5700                 }
5701             }
5702           printf ("\n");
5703         }
5704
5705       Dwarf_Addr base = cu_base;
5706       bool start_of_list = true;
5707       while (readp < nexthdr)
5708         {
5709           uint8_t kind = *readp++;
5710           uint64_t op1, op2;
5711           char *a1, *a2;
5712
5713           /* Skip padding.  */
5714           if (start_of_list && kind == DW_RLE_end_of_list)
5715             continue;
5716
5717           if (start_of_list)
5718             {
5719               base = cu_base;
5720               printf ("  Offset: %" PRIx64 ", Index: %" PRIx64 "\n",
5721                       (uint64_t) (readp - (unsigned char *) data->d_buf - 1),
5722                       (uint64_t) (readp - offset_array_start - 1));
5723               start_of_list = false;
5724             }
5725
5726           printf ("    %s", dwarf_range_list_encoding_name (kind));
5727           switch (kind)
5728             {
5729             case DW_RLE_end_of_list:
5730               start_of_list = true;
5731               printf ("\n\n");
5732               break;
5733
5734             case DW_RLE_base_addressx:
5735               if ((uint64_t) (nexthdr - readp) < 1)
5736                 {
5737                 invalid_range:
5738                   error (0, 0, gettext ("invalid range list data"));
5739                   goto next_table;
5740                 }
5741               get_uleb128 (op1, readp, nexthdr);
5742               printf (" %" PRIx64 "\n", op1);
5743               if (! print_unresolved_addresses)
5744                 {
5745                   Dwarf_Addr addr;
5746                   if (get_indexed_addr (cu, op1, &addr) != 0)
5747                     printf ("      ???\n");
5748                   else
5749                     {
5750                       a1 = format_dwarf_addr (dwflmod, address_size,
5751                                               addr, addr);
5752                       printf ("      %s\n", a1);
5753                       free (a1);
5754                     }
5755                 }
5756               break;
5757
5758             case DW_RLE_startx_endx:
5759               if ((uint64_t) (nexthdr - readp) < 1)
5760                 goto invalid_range;
5761               get_uleb128 (op1, readp, nexthdr);
5762               if ((uint64_t) (nexthdr - readp) < 1)
5763                 goto invalid_range;
5764               get_uleb128 (op2, readp, nexthdr);
5765               printf (" %" PRIx64 ", %" PRIx64 "\n", op1, op2);
5766               if (! print_unresolved_addresses)
5767                 {
5768                   Dwarf_Addr addr1;
5769                   Dwarf_Addr addr2;
5770                   if (get_indexed_addr (cu, op1, &addr1) != 0
5771                       || get_indexed_addr (cu, op2, &addr2) != 0)
5772                     {
5773                       printf ("      ???..\n");
5774                       printf ("      ???\n");
5775                     }
5776                   else
5777                     {
5778                       a1 = format_dwarf_addr (dwflmod, address_size,
5779                                               addr1, addr1);
5780                       a2 = format_dwarf_addr (dwflmod, address_size,
5781                                               addr2 - 1, addr2);
5782                       printf ("      %s..\n", a1);
5783                       printf ("      %s\n", a2);
5784                       free (a1);
5785                       free (a2);
5786                     }
5787                 }
5788               break;
5789
5790             case DW_RLE_startx_length:
5791               if ((uint64_t) (nexthdr - readp) < 1)
5792                 goto invalid_range;
5793               get_uleb128 (op1, readp, nexthdr);
5794               if ((uint64_t) (nexthdr - readp) < 1)
5795                 goto invalid_range;
5796               get_uleb128 (op2, readp, nexthdr);
5797               printf (" %" PRIx64 ", %" PRIx64 "\n", op1, op2);
5798               if (! print_unresolved_addresses)
5799                 {
5800                   Dwarf_Addr addr1;
5801                   Dwarf_Addr addr2;
5802                   if (get_indexed_addr (cu, op1, &addr1) != 0)
5803                     {
5804                       printf ("      ???..\n");
5805                       printf ("      ???\n");
5806                     }
5807                   else
5808                     {
5809                       addr2 = addr1 + op2;
5810                       a1 = format_dwarf_addr (dwflmod, address_size,
5811                                               addr1, addr1);
5812                       a2 = format_dwarf_addr (dwflmod, address_size,
5813                                               addr2 - 1, addr2);
5814                       printf ("      %s..\n", a1);
5815                       printf ("      %s..\n", a2);
5816                       free (a1);
5817                       free (a2);
5818                     }
5819                 }
5820               break;
5821
5822             case DW_RLE_offset_pair:
5823               if ((uint64_t) (nexthdr - readp) < 1)
5824                 goto invalid_range;
5825               get_uleb128 (op1, readp, nexthdr);
5826               if ((uint64_t) (nexthdr - readp) < 1)
5827                 goto invalid_range;
5828               get_uleb128 (op2, readp, nexthdr);
5829               printf (" %" PRIx64 ", %" PRIx64 "\n", op1, op2);
5830               if (! print_unresolved_addresses)
5831                 {
5832                   op1 += base;
5833                   op2 += base;
5834                   a1 = format_dwarf_addr (dwflmod, address_size, op1, op1);
5835                   a2 = format_dwarf_addr (dwflmod, address_size,
5836                                           op2 - 1, op2);
5837                   printf ("      %s..\n", a1);
5838                   printf ("      %s\n", a2);
5839                   free (a1);
5840                   free (a2);
5841                 }
5842               break;
5843
5844             case DW_RLE_base_address:
5845               if (address_size == 4)
5846                 {
5847                   if ((uint64_t) (nexthdr - readp) < 4)
5848                     goto invalid_range;
5849                   op1 = read_4ubyte_unaligned_inc (dbg, readp);
5850                 }
5851               else
5852                 {
5853                   if ((uint64_t) (nexthdr - readp) < 8)
5854                     goto invalid_range;
5855                   op1 = read_8ubyte_unaligned_inc (dbg, readp);
5856                 }
5857               base = op1;
5858               printf (" 0x%" PRIx64 "\n", base);
5859               if (! print_unresolved_addresses)
5860                 {
5861                   a1 = format_dwarf_addr (dwflmod, address_size, base, base);
5862                   printf ("      %s\n", a1);
5863                   free (a1);
5864                 }
5865               break;
5866
5867             case DW_RLE_start_end:
5868               if (address_size == 4)
5869                 {
5870                   if ((uint64_t) (nexthdr - readp) < 8)
5871                     goto invalid_range;
5872                   op1 = read_4ubyte_unaligned_inc (dbg, readp);
5873                   op2 = read_4ubyte_unaligned_inc (dbg, readp);
5874                 }
5875               else
5876                 {
5877                   if ((uint64_t) (nexthdr - readp) < 16)
5878                     goto invalid_range;
5879                   op1 = read_8ubyte_unaligned_inc (dbg, readp);
5880                   op2 = read_8ubyte_unaligned_inc (dbg, readp);
5881                 }
5882               printf (" 0x%" PRIx64 "..0x%" PRIx64 "\n", op1, op2);
5883               if (! print_unresolved_addresses)
5884                 {
5885                   a1 = format_dwarf_addr (dwflmod, address_size, op1, op1);
5886                   a2 = format_dwarf_addr (dwflmod, address_size,
5887                                           op2 - 1, op2);
5888                   printf ("      %s..\n", a1);
5889                   printf ("      %s\n", a2);
5890                   free (a1);
5891                   free (a2);
5892                 }
5893               break;
5894
5895             case DW_RLE_start_length:
5896               if (address_size == 4)
5897                 {
5898                   if ((uint64_t) (nexthdr - readp) < 4)
5899                     goto invalid_range;
5900                   op1 = read_4ubyte_unaligned_inc (dbg, readp);
5901                 }
5902               else
5903                 {
5904                   if ((uint64_t) (nexthdr - readp) < 8)
5905                     goto invalid_range;
5906                   op1 = read_8ubyte_unaligned_inc (dbg, readp);
5907                 }
5908               if ((uint64_t) (nexthdr - readp) < 1)
5909                 goto invalid_range;
5910               get_uleb128 (op2, readp, nexthdr);
5911               printf (" 0x%" PRIx64 ", %" PRIx64 "\n", op1, op2);
5912               if (! print_unresolved_addresses)
5913                 {
5914                   a1 = format_dwarf_addr (dwflmod, address_size, op1, op1);
5915                   op2 = op1 + op2;
5916                   a2 = format_dwarf_addr (dwflmod, address_size,
5917                                           op2 - 1, op2);
5918                   printf ("      %s..\n", a1);
5919                   printf ("      %s\n", a2);
5920                   free (a1);
5921                   free (a2);
5922                 }
5923               break;
5924
5925             default:
5926               goto invalid_range;
5927             }
5928         }
5929
5930     next_table:
5931       if (readp != nexthdr)
5932         {
5933           size_t padding = nexthdr - readp;
5934           printf (gettext ("   %zu padding bytes\n\n"), padding);
5935           readp = nexthdr;
5936         }
5937     }
5938 }
5939
5940 /* Print content of DWARF .debug_ranges section.  */
5941 static void
5942 print_debug_ranges_section (Dwfl_Module *dwflmod,
5943                             Ebl *ebl, GElf_Ehdr *ehdr,
5944                             Elf_Scn *scn, GElf_Shdr *shdr,
5945                             Dwarf *dbg)
5946 {
5947   Elf_Data *data = (dbg->sectiondata[IDX_debug_ranges]
5948                     ?: elf_rawdata (scn, NULL));
5949   if (unlikely (data == NULL))
5950     {
5951       error (0, 0, gettext ("cannot get .debug_ranges content: %s"),
5952              elf_errmsg (-1));
5953       return;
5954     }
5955
5956   printf (gettext ("\
5957 \nDWARF section [%2zu] '%s' at offset %#" PRIx64 ":\n"),
5958           elf_ndxscn (scn), section_name (ebl, ehdr, shdr),
5959           (uint64_t) shdr->sh_offset);
5960
5961   sort_listptr (&known_rangelistptr, "rangelistptr");
5962   size_t listptr_idx = 0;
5963
5964   uint_fast8_t address_size = ehdr->e_ident[EI_CLASS] == ELFCLASS32 ? 4 : 8;
5965
5966   bool first = true;
5967   Dwarf_Addr base = 0;
5968   unsigned char *const endp = (unsigned char *) data->d_buf + data->d_size;
5969   unsigned char *readp = data->d_buf;
5970   Dwarf_CU *last_cu = NULL;
5971   while (readp < endp)
5972     {
5973       ptrdiff_t offset = readp - (unsigned char *) data->d_buf;
5974       Dwarf_CU *cu = last_cu;
5975
5976       if (first && skip_listptr_hole (&known_rangelistptr, &listptr_idx,
5977                                       &address_size, NULL, &base, &cu,
5978                                       offset, &readp, endp, NULL))
5979         continue;
5980
5981       if (last_cu != cu)
5982         {
5983           char *basestr = format_dwarf_addr (dwflmod, address_size,
5984                                              base, base);
5985           Dwarf_Die cudie;
5986           if (dwarf_cu_die (cu, &cudie,
5987                             NULL, NULL, NULL, NULL,
5988                             NULL, NULL) == NULL)
5989             printf (gettext ("\n Unknown CU base: %s\n"), basestr);
5990           else
5991             printf (gettext ("\n CU [%6" PRIx64 "] base: %s\n"),
5992                     dwarf_dieoffset (&cudie), basestr);
5993           free (basestr);
5994         }
5995       last_cu = cu;
5996
5997       if (unlikely (data->d_size - offset < (size_t) address_size * 2))
5998         {
5999           printf (gettext (" [%6tx]  <INVALID DATA>\n"), offset);
6000           break;
6001         }
6002
6003       Dwarf_Addr begin;
6004       Dwarf_Addr end;
6005       if (address_size == 8)
6006         {
6007           begin = read_8ubyte_unaligned_inc (dbg, readp);
6008           end = read_8ubyte_unaligned_inc (dbg, readp);
6009         }
6010       else
6011         {
6012           begin = read_4ubyte_unaligned_inc (dbg, readp);
6013           end = read_4ubyte_unaligned_inc (dbg, readp);
6014           if (begin == (Dwarf_Addr) (uint32_t) -1)
6015             begin = (Dwarf_Addr) -1l;
6016         }
6017
6018       if (begin == (Dwarf_Addr) -1l) /* Base address entry.  */
6019         {
6020           char *b = format_dwarf_addr (dwflmod, address_size, end, end);
6021           printf (gettext (" [%6tx] base address\n          %s\n"), offset, b);
6022           free (b);
6023           base = end;
6024         }
6025       else if (begin == 0 && end == 0) /* End of list entry.  */
6026         {
6027           if (first)
6028             printf (gettext (" [%6tx] empty list\n"), offset);
6029           first = true;
6030         }
6031       else
6032         {
6033           /* We have an address range entry.  */
6034           if (first)            /* First address range entry in a list.  */
6035             printf (" [%6tx] ", offset);
6036           else
6037             printf ("          ");
6038
6039           printf ("range %" PRIx64 ", %" PRIx64 "\n", begin, end);
6040           if (! print_unresolved_addresses)
6041             {
6042               char *b = format_dwarf_addr (dwflmod, address_size, base + begin,
6043                                            base + begin);
6044               char *e = format_dwarf_addr (dwflmod, address_size,
6045                                            base + end - 1, base + end);
6046               printf ("          %s..\n", b);
6047               printf ("          %s\n", e);
6048               free (b);
6049               free (e);
6050             }
6051
6052           first = false;
6053         }
6054     }
6055 }
6056
6057 #define REGNAMESZ 16
6058 static const char *
6059 register_info (Ebl *ebl, unsigned int regno, const Ebl_Register_Location *loc,
6060                char name[REGNAMESZ], int *bits, int *type)
6061 {
6062   const char *set;
6063   const char *pfx;
6064   int ignore;
6065   ssize_t n = ebl_register_info (ebl, regno, name, REGNAMESZ, &pfx, &set,
6066                                  bits ?: &ignore, type ?: &ignore);
6067   if (n <= 0)
6068     {
6069       if (loc != NULL)
6070         snprintf (name, REGNAMESZ, "reg%u", loc->regno);
6071       else
6072         snprintf (name, REGNAMESZ, "??? 0x%x", regno);
6073       if (bits != NULL)
6074         *bits = loc != NULL ? loc->bits : 0;
6075       if (type != NULL)
6076         *type = DW_ATE_unsigned;
6077       set = "??? unrecognized";
6078     }
6079   else
6080     {
6081       if (bits != NULL && *bits <= 0)
6082         *bits = loc != NULL ? loc->bits : 0;
6083       if (type != NULL && *type == DW_ATE_void)
6084         *type = DW_ATE_unsigned;
6085
6086     }
6087   return set;
6088 }
6089
6090 static const unsigned char *
6091 read_encoded (unsigned int encoding, const unsigned char *readp,
6092               const unsigned char *const endp, uint64_t *res, Dwarf *dbg)
6093 {
6094   if ((encoding & 0xf) == DW_EH_PE_absptr)
6095     encoding = gelf_getclass (dbg->elf) == ELFCLASS32
6096       ? DW_EH_PE_udata4 : DW_EH_PE_udata8;
6097
6098   switch (encoding & 0xf)
6099     {
6100     case DW_EH_PE_uleb128:
6101       get_uleb128 (*res, readp, endp);
6102       break;
6103     case DW_EH_PE_sleb128:
6104       get_sleb128 (*res, readp, endp);
6105       break;
6106     case DW_EH_PE_udata2:
6107       if (readp + 2 > endp)
6108         goto invalid;
6109       *res = read_2ubyte_unaligned_inc (dbg, readp);
6110       break;
6111     case DW_EH_PE_udata4:
6112       if (readp + 4 > endp)
6113         goto invalid;
6114       *res = read_4ubyte_unaligned_inc (dbg, readp);
6115       break;
6116     case DW_EH_PE_udata8:
6117       if (readp + 8 > endp)
6118         goto invalid;
6119       *res = read_8ubyte_unaligned_inc (dbg, readp);
6120       break;
6121     case DW_EH_PE_sdata2:
6122       if (readp + 2 > endp)
6123         goto invalid;
6124       *res = read_2sbyte_unaligned_inc (dbg, readp);
6125       break;
6126     case DW_EH_PE_sdata4:
6127       if (readp + 4 > endp)
6128         goto invalid;
6129       *res = read_4sbyte_unaligned_inc (dbg, readp);
6130       break;
6131     case DW_EH_PE_sdata8:
6132       if (readp + 8 > endp)
6133         goto invalid;
6134       *res = read_8sbyte_unaligned_inc (dbg, readp);
6135       break;
6136     default:
6137     invalid:
6138       error (1, 0,
6139              gettext ("invalid encoding"));
6140     }
6141
6142   return readp;
6143 }
6144
6145
6146 static void
6147 print_cfa_program (const unsigned char *readp, const unsigned char *const endp,
6148                    Dwarf_Word vma_base, unsigned int code_align,
6149                    int data_align,
6150                    unsigned int version, unsigned int ptr_size,
6151                    unsigned int encoding,
6152                    Dwfl_Module *dwflmod, Ebl *ebl, Dwarf *dbg)
6153 {
6154   char regnamebuf[REGNAMESZ];
6155   const char *regname (unsigned int regno)
6156   {
6157     register_info (ebl, regno, NULL, regnamebuf, NULL, NULL);
6158     return regnamebuf;
6159   }
6160
6161   puts ("\n   Program:");
6162   Dwarf_Word pc = vma_base;
6163   while (readp < endp)
6164     {
6165       unsigned int opcode = *readp++;
6166
6167       if (opcode < DW_CFA_advance_loc)
6168         /* Extended opcode.  */
6169         switch (opcode)
6170           {
6171             uint64_t op1;
6172             int64_t sop1;
6173             uint64_t op2;
6174             int64_t sop2;
6175
6176           case DW_CFA_nop:
6177             puts ("     nop");
6178             break;
6179           case DW_CFA_set_loc:
6180             if ((uint64_t) (endp - readp) < 1)
6181               goto invalid;
6182             readp = read_encoded (encoding, readp, endp, &op1, dbg);
6183             printf ("     set_loc %#" PRIx64 " to %#" PRIx64 "\n",
6184                     op1, pc = vma_base + op1);
6185             break;
6186           case DW_CFA_advance_loc1:
6187             if ((uint64_t) (endp - readp) < 1)
6188               goto invalid;
6189             printf ("     advance_loc1 %u to %#" PRIx64 "\n",
6190                     *readp, pc += *readp * code_align);
6191             ++readp;
6192             break;
6193           case DW_CFA_advance_loc2:
6194             if ((uint64_t) (endp - readp) < 2)
6195               goto invalid;
6196             op1 = read_2ubyte_unaligned_inc (dbg, readp);
6197             printf ("     advance_loc2 %" PRIu64 " to %#" PRIx64 "\n",
6198                     op1, pc += op1 * code_align);
6199             break;
6200           case DW_CFA_advance_loc4:
6201             if ((uint64_t) (endp - readp) < 4)
6202               goto invalid;
6203             op1 = read_4ubyte_unaligned_inc (dbg, readp);
6204             printf ("     advance_loc4 %" PRIu64 " to %#" PRIx64 "\n",
6205                     op1, pc += op1 * code_align);
6206             break;
6207           case DW_CFA_offset_extended:
6208             if ((uint64_t) (endp - readp) < 1)
6209               goto invalid;
6210             get_uleb128 (op1, readp, endp);
6211             if ((uint64_t) (endp - readp) < 1)
6212               goto invalid;
6213             get_uleb128 (op2, readp, endp);
6214             printf ("     offset_extended r%" PRIu64 " (%s) at cfa%+" PRId64
6215                     "\n",
6216                     op1, regname (op1), op2 * data_align);
6217             break;
6218           case DW_CFA_restore_extended:
6219             if ((uint64_t) (endp - readp) < 1)
6220               goto invalid;
6221             get_uleb128 (op1, readp, endp);
6222             printf ("     restore_extended r%" PRIu64 " (%s)\n",
6223                     op1, regname (op1));
6224             break;
6225           case DW_CFA_undefined:
6226             if ((uint64_t) (endp - readp) < 1)
6227               goto invalid;
6228             get_uleb128 (op1, readp, endp);
6229             printf ("     undefined r%" PRIu64 " (%s)\n", op1, regname (op1));
6230             break;
6231           case DW_CFA_same_value:
6232             if ((uint64_t) (endp - readp) < 1)
6233               goto invalid;
6234             get_uleb128 (op1, readp, endp);
6235             printf ("     same_value r%" PRIu64 " (%s)\n", op1, regname (op1));
6236             break;
6237           case DW_CFA_register:
6238             if ((uint64_t) (endp - readp) < 1)
6239               goto invalid;
6240             get_uleb128 (op1, readp, endp);
6241             if ((uint64_t) (endp - readp) < 1)
6242               goto invalid;
6243             get_uleb128 (op2, readp, endp);
6244             printf ("     register r%" PRIu64 " (%s) in r%" PRIu64 " (%s)\n",
6245                     op1, regname (op1), op2, regname (op2));
6246             break;
6247           case DW_CFA_remember_state:
6248             puts ("     remember_state");
6249             break;
6250           case DW_CFA_restore_state:
6251             puts ("     restore_state");
6252             break;
6253           case DW_CFA_def_cfa:
6254             if ((uint64_t) (endp - readp) < 1)
6255               goto invalid;
6256             get_uleb128 (op1, readp, endp);
6257             if ((uint64_t) (endp - readp) < 1)
6258               goto invalid;
6259             get_uleb128 (op2, readp, endp);
6260             printf ("     def_cfa r%" PRIu64 " (%s) at offset %" PRIu64 "\n",
6261                     op1, regname (op1), op2);
6262             break;
6263           case DW_CFA_def_cfa_register:
6264             if ((uint64_t) (endp - readp) < 1)
6265               goto invalid;
6266             get_uleb128 (op1, readp, endp);
6267             printf ("     def_cfa_register r%" PRIu64 " (%s)\n",
6268                     op1, regname (op1));
6269             break;
6270           case DW_CFA_def_cfa_offset:
6271             if ((uint64_t) (endp - readp) < 1)
6272               goto invalid;
6273             get_uleb128 (op1, readp, endp);
6274             printf ("     def_cfa_offset %" PRIu64 "\n", op1);
6275             break;
6276           case DW_CFA_def_cfa_expression:
6277             if ((uint64_t) (endp - readp) < 1)
6278               goto invalid;
6279             get_uleb128 (op1, readp, endp);     /* Length of DW_FORM_block.  */
6280             printf ("     def_cfa_expression %" PRIu64 "\n", op1);
6281             if ((uint64_t) (endp - readp) < op1)
6282               {
6283             invalid:
6284                 fputs (gettext ("         <INVALID DATA>\n"), stdout);
6285                 return;
6286               }
6287             print_ops (dwflmod, dbg, 10, 10, version, ptr_size, 0, NULL,
6288                        op1, readp);
6289             readp += op1;
6290             break;
6291           case DW_CFA_expression:
6292             if ((uint64_t) (endp - readp) < 1)
6293               goto invalid;
6294             get_uleb128 (op1, readp, endp);
6295             if ((uint64_t) (endp - readp) < 1)
6296               goto invalid;
6297             get_uleb128 (op2, readp, endp);     /* Length of DW_FORM_block.  */
6298             printf ("     expression r%" PRIu64 " (%s) \n",
6299                     op1, regname (op1));
6300             if ((uint64_t) (endp - readp) < op2)
6301               goto invalid;
6302             print_ops (dwflmod, dbg, 10, 10, version, ptr_size, 0, NULL,
6303                        op2, readp);
6304             readp += op2;
6305             break;
6306           case DW_CFA_offset_extended_sf:
6307             if ((uint64_t) (endp - readp) < 1)
6308               goto invalid;
6309             get_uleb128 (op1, readp, endp);
6310             if ((uint64_t) (endp - readp) < 1)
6311               goto invalid;
6312             get_sleb128 (sop2, readp, endp);
6313             printf ("     offset_extended_sf r%" PRIu64 " (%s) at cfa%+"
6314                     PRId64 "\n",
6315                     op1, regname (op1), sop2 * data_align);
6316             break;
6317           case DW_CFA_def_cfa_sf:
6318             if ((uint64_t) (endp - readp) < 1)
6319               goto invalid;
6320             get_uleb128 (op1, readp, endp);
6321             if ((uint64_t) (endp - readp) < 1)
6322               goto invalid;
6323             get_sleb128 (sop2, readp, endp);
6324             printf ("     def_cfa_sf r%" PRIu64 " (%s) at offset %" PRId64 "\n",
6325                     op1, regname (op1), sop2 * data_align);
6326             break;
6327           case DW_CFA_def_cfa_offset_sf:
6328             if ((uint64_t) (endp - readp) < 1)
6329               goto invalid;
6330             get_sleb128 (sop1, readp, endp);
6331             printf ("     def_cfa_offset_sf %" PRId64 "\n", sop1 * data_align);
6332             break;
6333           case DW_CFA_val_offset:
6334             if ((uint64_t) (endp - readp) < 1)
6335               goto invalid;
6336             get_uleb128 (op1, readp, endp);
6337             if ((uint64_t) (endp - readp) < 1)
6338               goto invalid;
6339             get_uleb128 (op2, readp, endp);
6340             printf ("     val_offset %" PRIu64 " at offset %" PRIu64 "\n",
6341                     op1, op2 * data_align);
6342             break;
6343           case DW_CFA_val_offset_sf:
6344             if ((uint64_t) (endp - readp) < 1)
6345               goto invalid;
6346             get_uleb128 (op1, readp, endp);
6347             if ((uint64_t) (endp - readp) < 1)
6348               goto invalid;
6349             get_sleb128 (sop2, readp, endp);
6350             printf ("     val_offset_sf %" PRIu64 " at offset %" PRId64 "\n",
6351                     op1, sop2 * data_align);
6352             break;
6353           case DW_CFA_val_expression:
6354             if ((uint64_t) (endp - readp) < 1)
6355               goto invalid;
6356             get_uleb128 (op1, readp, endp);
6357             if ((uint64_t) (endp - readp) < 1)
6358               goto invalid;
6359             get_uleb128 (op2, readp, endp);     /* Length of DW_FORM_block.  */
6360             printf ("     val_expression r%" PRIu64 " (%s)\n",
6361                     op1, regname (op1));
6362             if ((uint64_t) (endp - readp) < op2)
6363               goto invalid;
6364             print_ops (dwflmod, dbg, 10, 10, version, ptr_size, 0,
6365                        NULL, op2, readp);
6366             readp += op2;
6367             break;
6368           case DW_CFA_MIPS_advance_loc8:
6369             if ((uint64_t) (endp - readp) < 8)
6370               goto invalid;
6371             op1 = read_8ubyte_unaligned_inc (dbg, readp);
6372             printf ("     MIPS_advance_loc8 %" PRIu64 " to %#" PRIx64 "\n",
6373                     op1, pc += op1 * code_align);
6374             break;
6375           case DW_CFA_GNU_window_save:
6376             puts ("     GNU_window_save");
6377             break;
6378           case DW_CFA_GNU_args_size:
6379             if ((uint64_t) (endp - readp) < 1)
6380               goto invalid;
6381             get_uleb128 (op1, readp, endp);
6382             printf ("     args_size %" PRIu64 "\n", op1);
6383             break;
6384           default:
6385             printf ("     ??? (%u)\n", opcode);
6386             break;
6387           }
6388       else if (opcode < DW_CFA_offset)
6389         printf ("     advance_loc %u to %#" PRIx64 "\n",
6390                 opcode & 0x3f, pc += (opcode & 0x3f) * code_align);
6391       else if (opcode < DW_CFA_restore)
6392         {
6393           uint64_t offset;
6394           if ((uint64_t) (endp - readp) < 1)
6395             goto invalid;
6396           get_uleb128 (offset, readp, endp);
6397           printf ("     offset r%u (%s) at cfa%+" PRId64 "\n",
6398                   opcode & 0x3f, regname (opcode & 0x3f), offset * data_align);
6399         }
6400       else
6401         printf ("     restore r%u (%s)\n",
6402                 opcode & 0x3f, regname (opcode & 0x3f));
6403     }
6404 }
6405
6406
6407 static unsigned int
6408 encoded_ptr_size (int encoding, unsigned int ptr_size)
6409 {
6410   switch (encoding & 7)
6411     {
6412     case DW_EH_PE_udata4:
6413       return 4;
6414     case DW_EH_PE_udata8:
6415       return 8;
6416     case 0:
6417       return ptr_size;
6418     }
6419
6420   fprintf (stderr, "Unsupported pointer encoding: %#x, "
6421            "assuming pointer size of %d.\n", encoding, ptr_size);
6422   return ptr_size;
6423 }
6424
6425
6426 static unsigned int
6427 print_encoding (unsigned int val)
6428 {
6429   switch (val & 0xf)
6430     {
6431     case DW_EH_PE_absptr:
6432       fputs ("absptr", stdout);
6433       break;
6434     case DW_EH_PE_uleb128:
6435       fputs ("uleb128", stdout);
6436       break;
6437     case DW_EH_PE_udata2:
6438       fputs ("udata2", stdout);
6439       break;
6440     case DW_EH_PE_udata4:
6441       fputs ("udata4", stdout);
6442       break;
6443     case DW_EH_PE_udata8:
6444       fputs ("udata8", stdout);
6445       break;
6446     case DW_EH_PE_sleb128:
6447       fputs ("sleb128", stdout);
6448       break;
6449     case DW_EH_PE_sdata2:
6450       fputs ("sdata2", stdout);
6451       break;
6452     case DW_EH_PE_sdata4:
6453       fputs ("sdata4", stdout);
6454       break;
6455     case DW_EH_PE_sdata8:
6456       fputs ("sdata8", stdout);
6457       break;
6458     default:
6459       /* We did not use any of the bits after all.  */
6460       return val;
6461     }
6462
6463   return val & ~0xf;
6464 }
6465
6466
6467 static unsigned int
6468 print_relinfo (unsigned int val)
6469 {
6470   switch (val & 0x70)
6471     {
6472     case DW_EH_PE_pcrel:
6473       fputs ("pcrel", stdout);
6474       break;
6475     case DW_EH_PE_textrel:
6476       fputs ("textrel", stdout);
6477       break;
6478     case DW_EH_PE_datarel:
6479       fputs ("datarel", stdout);
6480       break;
6481     case DW_EH_PE_funcrel:
6482       fputs ("funcrel", stdout);
6483       break;
6484     case DW_EH_PE_aligned:
6485       fputs ("aligned", stdout);
6486       break;
6487     default:
6488       return val;
6489     }
6490
6491   return val & ~0x70;
6492 }
6493
6494
6495 static void
6496 print_encoding_base (const char *pfx, unsigned int fde_encoding)
6497 {
6498   printf ("(%s", pfx);
6499
6500   if (fde_encoding == DW_EH_PE_omit)
6501     puts ("omit)");
6502   else
6503     {
6504       unsigned int w = fde_encoding;
6505
6506       w = print_encoding (w);
6507
6508       if (w & 0x70)
6509         {
6510           if (w != fde_encoding)
6511             fputc_unlocked (' ', stdout);
6512
6513           w = print_relinfo (w);
6514         }
6515
6516       if (w != 0)
6517         printf ("%s%x", w != fde_encoding ? " " : "", w);
6518
6519       puts (")");
6520     }
6521 }
6522
6523
6524 static void
6525 print_debug_frame_section (Dwfl_Module *dwflmod, Ebl *ebl, GElf_Ehdr *ehdr,
6526                            Elf_Scn *scn, GElf_Shdr *shdr, Dwarf *dbg)
6527 {
6528   size_t shstrndx;
6529   /* We know this call will succeed since it did in the caller.  */
6530   (void) elf_getshdrstrndx (ebl->elf, &shstrndx);
6531   const char *scnname = elf_strptr (ebl->elf, shstrndx, shdr->sh_name);
6532
6533   /* Needed if we find PC-relative addresses.  */
6534   GElf_Addr bias;
6535   if (dwfl_module_getelf (dwflmod, &bias) == NULL)
6536     {
6537       error (0, 0, gettext ("cannot get ELF: %s"), dwfl_errmsg (-1));
6538       return;
6539     }
6540
6541   bool is_eh_frame = strcmp (scnname, ".eh_frame") == 0;
6542   Elf_Data *data = (is_eh_frame
6543                     ? elf_rawdata (scn, NULL)
6544                     : (dbg->sectiondata[IDX_debug_frame]
6545                        ?: elf_rawdata (scn, NULL)));
6546
6547   if (unlikely (data == NULL))
6548     {
6549       error (0, 0, gettext ("cannot get %s content: %s"),
6550              scnname, elf_errmsg (-1));
6551       return;
6552     }
6553
6554   if (is_eh_frame)
6555     printf (gettext ("\
6556 \nCall frame information section [%2zu] '%s' at offset %#" PRIx64 ":\n"),
6557             elf_ndxscn (scn), scnname, (uint64_t) shdr->sh_offset);
6558   else
6559     printf (gettext ("\
6560 \nDWARF section [%2zu] '%s' at offset %#" PRIx64 ":\n"),
6561             elf_ndxscn (scn), scnname, (uint64_t) shdr->sh_offset);
6562
6563   struct cieinfo
6564   {
6565     ptrdiff_t cie_offset;
6566     const char *augmentation;
6567     unsigned int code_alignment_factor;
6568     unsigned int data_alignment_factor;
6569     uint8_t address_size;
6570     uint8_t fde_encoding;
6571     uint8_t lsda_encoding;
6572     struct cieinfo *next;
6573   } *cies = NULL;
6574
6575   const unsigned char *readp = data->d_buf;
6576   const unsigned char *const dataend = ((unsigned char *) data->d_buf
6577                                         + data->d_size);
6578   while (readp < dataend)
6579     {
6580       if (unlikely (readp + 4 > dataend))
6581         {
6582         invalid_data:
6583           error (0, 0, gettext ("invalid data in section [%zu] '%s'"),
6584                      elf_ndxscn (scn), scnname);
6585               return;
6586         }
6587
6588       /* At the beginning there must be a CIE.  There can be multiple,
6589          hence we test tis in a loop.  */
6590       ptrdiff_t offset = readp - (unsigned char *) data->d_buf;
6591
6592       Dwarf_Word unit_length = read_4ubyte_unaligned_inc (dbg, readp);
6593       unsigned int length = 4;
6594       if (unlikely (unit_length == 0xffffffff))
6595         {
6596           if (unlikely (readp + 8 > dataend))
6597             goto invalid_data;
6598
6599           unit_length = read_8ubyte_unaligned_inc (dbg, readp);
6600           length = 8;
6601         }
6602
6603       if (unlikely (unit_length == 0))
6604         {
6605           printf (gettext ("\n [%6tx] Zero terminator\n"), offset);
6606           continue;
6607         }
6608
6609       Dwarf_Word maxsize = dataend - readp;
6610       if (unlikely (unit_length > maxsize))
6611         goto invalid_data;
6612
6613       unsigned int ptr_size = ehdr->e_ident[EI_CLASS] == ELFCLASS32 ? 4 : 8;
6614
6615       ptrdiff_t start = readp - (unsigned char *) data->d_buf;
6616       const unsigned char *const cieend = readp + unit_length;
6617       if (unlikely (cieend > dataend || readp + 8 > dataend))
6618         goto invalid_data;
6619
6620       Dwarf_Off cie_id;
6621       if (length == 4)
6622         {
6623           cie_id = read_4ubyte_unaligned_inc (dbg, readp);
6624           if (!is_eh_frame && cie_id == DW_CIE_ID_32)
6625             cie_id = DW_CIE_ID_64;
6626         }
6627       else
6628         cie_id = read_8ubyte_unaligned_inc (dbg, readp);
6629
6630       uint_fast8_t version = 2;
6631       unsigned int code_alignment_factor;
6632       int data_alignment_factor;
6633       unsigned int fde_encoding = 0;
6634       unsigned int lsda_encoding = 0;
6635       Dwarf_Word initial_location = 0;
6636       Dwarf_Word vma_base = 0;
6637
6638       if (cie_id == (is_eh_frame ? 0 : DW_CIE_ID_64))
6639         {
6640           version = *readp++;
6641           const char *const augmentation = (const char *) readp;
6642           readp = memchr (readp, '\0', cieend - readp);
6643           if (unlikely (readp == NULL))
6644             goto invalid_data;
6645           ++readp;
6646
6647           uint_fast8_t segment_size = 0;
6648           if (version >= 4)
6649             {
6650               if (cieend - readp < 5)
6651                 goto invalid_data;
6652               ptr_size = *readp++;
6653               segment_size = *readp++;
6654             }
6655
6656           if (cieend - readp < 1)
6657             goto invalid_data;
6658           get_uleb128 (code_alignment_factor, readp, cieend);
6659           if (cieend - readp < 1)
6660             goto invalid_data;
6661           get_sleb128 (data_alignment_factor, readp, cieend);
6662
6663           /* In some variant for unwind data there is another field.  */
6664           if (strcmp (augmentation, "eh") == 0)
6665             readp += ehdr->e_ident[EI_CLASS] == ELFCLASS32 ? 4 : 8;
6666
6667           unsigned int return_address_register;
6668           if (cieend - readp < 1)
6669             goto invalid_data;
6670           if (unlikely (version == 1))
6671             return_address_register = *readp++;
6672           else
6673             get_uleb128 (return_address_register, readp, cieend);
6674
6675           printf ("\n [%6tx] CIE length=%" PRIu64 "\n"
6676                   "   CIE_id:                   %" PRIu64 "\n"
6677                   "   version:                  %u\n"
6678                   "   augmentation:             \"%s\"\n",
6679                   offset, (uint64_t) unit_length, (uint64_t) cie_id,
6680                   version, augmentation);
6681           if (version >= 4)
6682             printf ("   address_size:             %u\n"
6683                     "   segment_size:             %u\n",
6684                     ptr_size, segment_size);
6685           printf ("   code_alignment_factor:    %u\n"
6686                   "   data_alignment_factor:    %d\n"
6687                   "   return_address_register:  %u\n",
6688                   code_alignment_factor,
6689                   data_alignment_factor, return_address_register);
6690
6691           if (augmentation[0] == 'z')
6692             {
6693               unsigned int augmentationlen;
6694               get_uleb128 (augmentationlen, readp, cieend);
6695
6696               if (augmentationlen > (size_t) (cieend - readp))
6697                 {
6698                   error (0, 0, gettext ("invalid augmentation length"));
6699                   readp = cieend;
6700                   continue;
6701                 }
6702
6703               const char *hdr = "Augmentation data:";
6704               const char *cp = augmentation + 1;
6705               while (*cp != '\0' && cp < augmentation + augmentationlen + 1)
6706                 {
6707                   printf ("   %-26s%#x ", hdr, *readp);
6708                   hdr = "";
6709
6710                   if (*cp == 'R')
6711                     {
6712                       fde_encoding = *readp++;
6713                       print_encoding_base (gettext ("FDE address encoding: "),
6714                                            fde_encoding);
6715                     }
6716                   else if (*cp == 'L')
6717                     {
6718                       lsda_encoding = *readp++;
6719                       print_encoding_base (gettext ("LSDA pointer encoding: "),
6720                                            lsda_encoding);
6721                     }
6722                   else if (*cp == 'P')
6723                     {
6724                       /* Personality.  This field usually has a relocation
6725                          attached pointing to __gcc_personality_v0.  */
6726                       const unsigned char *startp = readp;
6727                       unsigned int encoding = *readp++;
6728                       uint64_t val = 0;
6729                       readp = read_encoded (encoding, readp,
6730                                             readp - 1 + augmentationlen,
6731                                             &val, dbg);
6732
6733                       while (++startp < readp)
6734                         printf ("%#x ", *startp);
6735
6736                       putchar ('(');
6737                       print_encoding (encoding);
6738                       putchar (' ');
6739                       switch (encoding & 0xf)
6740                         {
6741                         case DW_EH_PE_sleb128:
6742                         case DW_EH_PE_sdata2:
6743                         case DW_EH_PE_sdata4:
6744                           printf ("%" PRId64 ")\n", val);
6745                           break;
6746                         default:
6747                           printf ("%#" PRIx64 ")\n", val);
6748                           break;
6749                         }
6750                     }
6751                   else
6752                     printf ("(%x)\n", *readp++);
6753
6754                   ++cp;
6755                 }
6756             }
6757
6758           if (likely (ptr_size == 4 || ptr_size == 8))
6759             {
6760               struct cieinfo *newp = alloca (sizeof (*newp));
6761               newp->cie_offset = offset;
6762               newp->augmentation = augmentation;
6763               newp->fde_encoding = fde_encoding;
6764               newp->lsda_encoding = lsda_encoding;
6765               newp->address_size = ptr_size;
6766               newp->code_alignment_factor = code_alignment_factor;
6767               newp->data_alignment_factor = data_alignment_factor;
6768               newp->next = cies;
6769               cies = newp;
6770             }
6771         }
6772       else
6773         {
6774           struct cieinfo *cie = cies;
6775           while (cie != NULL)
6776             if (is_eh_frame
6777                 ? ((Dwarf_Off) start - cie_id) == (Dwarf_Off) cie->cie_offset
6778                 : cie_id == (Dwarf_Off) cie->cie_offset)
6779               break;
6780             else
6781               cie = cie->next;
6782           if (unlikely (cie == NULL))
6783             {
6784               puts ("invalid CIE reference in FDE");
6785               return;
6786             }
6787
6788           /* Initialize from CIE data.  */
6789           fde_encoding = cie->fde_encoding;
6790           lsda_encoding = cie->lsda_encoding;
6791           ptr_size = encoded_ptr_size (fde_encoding, cie->address_size);
6792           code_alignment_factor = cie->code_alignment_factor;
6793           data_alignment_factor = cie->data_alignment_factor;
6794
6795           const unsigned char *base = readp;
6796           // XXX There are sometimes relocations for this value
6797           initial_location = read_addr_unaligned_inc (ptr_size, dbg, readp);
6798           Dwarf_Word address_range
6799             = read_addr_unaligned_inc (ptr_size, dbg, readp);
6800
6801           /* pcrel for an FDE address is relative to the runtime
6802              address of the start_address field itself.  Sign extend
6803              if necessary to make sure the calculation is done on the
6804              full 64 bit address even when initial_location only holds
6805              the lower 32 bits.  */
6806           Dwarf_Addr pc_start = initial_location;
6807           if (ptr_size == 4)
6808             pc_start = (uint64_t) (int32_t) pc_start;
6809           if ((fde_encoding & 0x70) == DW_EH_PE_pcrel)
6810             pc_start += ((uint64_t) shdr->sh_addr
6811                          + (base - (const unsigned char *) data->d_buf)
6812                          - bias);
6813
6814           char *a = format_dwarf_addr (dwflmod, cie->address_size,
6815                                        pc_start, initial_location);
6816           printf ("\n [%6tx] FDE length=%" PRIu64 " cie=[%6tx]\n"
6817                   "   CIE_pointer:              %" PRIu64 "\n"
6818                   "   initial_location:         %s",
6819                   offset, (uint64_t) unit_length,
6820                   cie->cie_offset, (uint64_t) cie_id, a);
6821           free (a);
6822           if ((fde_encoding & 0x70) == DW_EH_PE_pcrel)
6823             {
6824               vma_base = (((uint64_t) shdr->sh_offset
6825                            + (base - (const unsigned char *) data->d_buf)
6826                            + (uint64_t) initial_location)
6827                           & (ptr_size == 4
6828                              ? UINT64_C (0xffffffff)
6829                              : UINT64_C (0xffffffffffffffff)));
6830               printf (gettext (" (offset: %#" PRIx64 ")"),
6831                       (uint64_t) vma_base);
6832             }
6833
6834           printf ("\n   address_range:            %#" PRIx64,
6835                   (uint64_t) address_range);
6836           if ((fde_encoding & 0x70) == DW_EH_PE_pcrel)
6837             printf (gettext (" (end offset: %#" PRIx64 ")"),
6838                     ((uint64_t) vma_base + (uint64_t) address_range)
6839                     & (ptr_size == 4
6840                        ? UINT64_C (0xffffffff)
6841                        : UINT64_C (0xffffffffffffffff)));
6842           putchar ('\n');
6843
6844           if (cie->augmentation[0] == 'z')
6845             {
6846               unsigned int augmentationlen;
6847               if (cieend - readp < 1)
6848                 goto invalid_data;
6849               get_uleb128 (augmentationlen, readp, cieend);
6850
6851               if (augmentationlen > (size_t) (cieend - readp))
6852                 {
6853                   error (0, 0, gettext ("invalid augmentation length"));
6854                   readp = cieend;
6855                   continue;
6856                 }
6857
6858               if (augmentationlen > 0)
6859                 {
6860                   const char *hdr = "Augmentation data:";
6861                   const char *cp = cie->augmentation + 1;
6862                   unsigned int u = 0;
6863                   while (*cp != '\0'
6864                          && cp < cie->augmentation + augmentationlen + 1)
6865                     {
6866                       if (*cp == 'L')
6867                         {
6868                           uint64_t lsda_pointer;
6869                           const unsigned char *p
6870                             = read_encoded (lsda_encoding, &readp[u],
6871                                             &readp[augmentationlen],
6872                                             &lsda_pointer, dbg);
6873                           u = p - readp;
6874                           printf (gettext ("\
6875    %-26sLSDA pointer: %#" PRIx64 "\n"),
6876                                   hdr, lsda_pointer);
6877                           hdr = "";
6878                         }
6879                       ++cp;
6880                     }
6881
6882                   while (u < augmentationlen)
6883                     {
6884                       printf ("   %-26s%#x\n", hdr, readp[u++]);
6885                       hdr = "";
6886                     }
6887                 }
6888
6889               readp += augmentationlen;
6890             }
6891         }
6892
6893       /* Handle the initialization instructions.  */
6894       if (ptr_size != 4 && ptr_size !=8)
6895         printf ("invalid CIE pointer size (%u), must be 4 or 8.\n", ptr_size);
6896       else
6897         print_cfa_program (readp, cieend, vma_base, code_alignment_factor,
6898                            data_alignment_factor, version, ptr_size,
6899                            fde_encoding, dwflmod, ebl, dbg);
6900       readp = cieend;
6901     }
6902 }
6903
6904
6905 struct attrcb_args
6906 {
6907   Dwfl_Module *dwflmod;
6908   Dwarf *dbg;
6909   Dwarf_Die *die;
6910   int level;
6911   bool silent;
6912   bool is_split;
6913   unsigned int version;
6914   unsigned int addrsize;
6915   unsigned int offset_size;
6916   struct Dwarf_CU *cu;
6917 };
6918
6919
6920 static int
6921 attr_callback (Dwarf_Attribute *attrp, void *arg)
6922 {
6923   struct attrcb_args *cbargs = (struct attrcb_args *) arg;
6924   const int level = cbargs->level;
6925   Dwarf_Die *die = cbargs->die;
6926   bool is_split = cbargs->is_split;
6927
6928   unsigned int attr = dwarf_whatattr (attrp);
6929   if (unlikely (attr == 0))
6930     {
6931       if (!cbargs->silent)
6932         error (0, 0, gettext ("DIE [%" PRIx64 "] "
6933                               "cannot get attribute code: %s"),
6934                dwarf_dieoffset (die), dwarf_errmsg (-1));
6935       return DWARF_CB_ABORT;
6936     }
6937
6938   unsigned int form = dwarf_whatform (attrp);
6939   if (unlikely (form == 0))
6940     {
6941       if (!cbargs->silent)
6942         error (0, 0, gettext ("DIE [%" PRIx64 "] "
6943                               "cannot get attribute form: %s"),
6944                dwarf_dieoffset (die), dwarf_errmsg (-1));
6945       return DWARF_CB_ABORT;
6946     }
6947
6948   switch (form)
6949     {
6950     case DW_FORM_addr:
6951     case DW_FORM_addrx:
6952     case DW_FORM_addrx1:
6953     case DW_FORM_addrx2:
6954     case DW_FORM_addrx3:
6955     case DW_FORM_addrx4:
6956     case DW_FORM_GNU_addr_index:
6957       if (!cbargs->silent)
6958         {
6959           Dwarf_Addr addr;
6960           if (unlikely (dwarf_formaddr (attrp, &addr) != 0))
6961             {
6962             attrval_out:
6963               if (!cbargs->silent)
6964                 error (0, 0, gettext ("DIE [%" PRIx64 "] "
6965                                       "cannot get attribute '%s' (%s) value: "
6966                                       "%s"),
6967                        dwarf_dieoffset (die),
6968                        dwarf_attr_name (attr),
6969                        dwarf_form_name (form),
6970                        dwarf_errmsg (-1));
6971               /* Don't ABORT, it might be other attributes can be resolved.  */
6972               return DWARF_CB_OK;
6973             }
6974           char *a = format_dwarf_addr (cbargs->dwflmod, cbargs->addrsize,
6975                                        addr, addr);
6976           if (form != DW_FORM_addr )
6977             {
6978               Dwarf_Word index;
6979               if (dwarf_formudata (attrp, &index) != 0)
6980                 goto attrval_out;
6981               printf ("           %*s%-20s (%s) [%" PRIx64 "] %s\n",
6982                       (int) (level * 2), "", dwarf_attr_name (attr),
6983                       dwarf_form_name (form), index, a);
6984             }
6985           else
6986             printf ("           %*s%-20s (%s) %s\n",
6987                     (int) (level * 2), "", dwarf_attr_name (attr),
6988                     dwarf_form_name (form), a);
6989           free (a);
6990         }
6991       break;
6992
6993     case DW_FORM_indirect:
6994     case DW_FORM_strp:
6995     case DW_FORM_line_strp:
6996     case DW_FORM_strx:
6997     case DW_FORM_strx1:
6998     case DW_FORM_strx2:
6999     case DW_FORM_strx3:
7000     case DW_FORM_strx4:
7001     case DW_FORM_string:
7002     case DW_FORM_GNU_strp_alt:
7003     case DW_FORM_GNU_str_index:
7004       if (cbargs->silent)
7005         break;
7006       const char *str = dwarf_formstring (attrp);
7007       if (unlikely (str == NULL))
7008         goto attrval_out;
7009       printf ("           %*s%-20s (%s) \"%s\"\n",
7010               (int) (level * 2), "", dwarf_attr_name (attr),
7011               dwarf_form_name (form), str);
7012       break;
7013
7014     case DW_FORM_ref_addr:
7015     case DW_FORM_ref_udata:
7016     case DW_FORM_ref8:
7017     case DW_FORM_ref4:
7018     case DW_FORM_ref2:
7019     case DW_FORM_ref1:
7020     case DW_FORM_GNU_ref_alt:
7021     case DW_FORM_ref_sup4:
7022     case DW_FORM_ref_sup8:
7023       if (cbargs->silent)
7024         break;
7025       Dwarf_Die ref;
7026       if (unlikely (dwarf_formref_die (attrp, &ref) == NULL))
7027         goto attrval_out;
7028
7029       printf ("           %*s%-20s (%s) ",
7030               (int) (level * 2), "", dwarf_attr_name (attr),
7031               dwarf_form_name (form));
7032       if (is_split)
7033         printf ("{%6" PRIxMAX "}\n", (uintmax_t) dwarf_dieoffset (&ref));
7034       else
7035         printf ("[%6" PRIxMAX "]\n", (uintmax_t) dwarf_dieoffset (&ref));
7036       break;
7037
7038     case DW_FORM_ref_sig8:
7039       if (cbargs->silent)
7040         break;
7041       printf ("           %*s%-20s (%s) {%6" PRIx64 "}\n",
7042               (int) (level * 2), "", dwarf_attr_name (attr),
7043               dwarf_form_name (form),
7044               (uint64_t) read_8ubyte_unaligned (attrp->cu->dbg, attrp->valp));
7045       break;
7046
7047     case DW_FORM_sec_offset:
7048     case DW_FORM_rnglistx:
7049     case DW_FORM_loclistx:
7050     case DW_FORM_implicit_const:
7051     case DW_FORM_udata:
7052     case DW_FORM_sdata:
7053     case DW_FORM_data8: /* Note no data16 here, we see that as block. */
7054     case DW_FORM_data4:
7055     case DW_FORM_data2:
7056     case DW_FORM_data1:;
7057       Dwarf_Word num;
7058       if (unlikely (dwarf_formudata (attrp, &num) != 0))
7059         goto attrval_out;
7060
7061       const char *valuestr = NULL;
7062       bool as_hex_id = false;
7063       switch (attr)
7064         {
7065           /* This case can take either a constant or a loclistptr.  */
7066         case DW_AT_data_member_location:
7067           if (form != DW_FORM_sec_offset
7068               && (cbargs->version >= 4
7069                   || (form != DW_FORM_data4 && form != DW_FORM_data8)))
7070             {
7071               if (!cbargs->silent)
7072                 printf ("           %*s%-20s (%s) %" PRIxMAX "\n",
7073                         (int) (level * 2), "", dwarf_attr_name (attr),
7074                         dwarf_form_name (form), (uintmax_t) num);
7075               return DWARF_CB_OK;
7076             }
7077           FALLTHROUGH;
7078
7079         /* These cases always take a loclist[ptr] and no constant. */
7080         case DW_AT_location:
7081         case DW_AT_data_location:
7082         case DW_AT_vtable_elem_location:
7083         case DW_AT_string_length:
7084         case DW_AT_use_location:
7085         case DW_AT_frame_base:
7086         case DW_AT_return_addr:
7087         case DW_AT_static_link:
7088         case DW_AT_segment:
7089         case DW_AT_GNU_call_site_value:
7090         case DW_AT_GNU_call_site_data_value:
7091         case DW_AT_GNU_call_site_target:
7092         case DW_AT_GNU_call_site_target_clobbered:
7093         case DW_AT_GNU_locviews:
7094           {
7095             bool nlpt;
7096             if (cbargs->cu->version < 5)
7097               {
7098                 if (! cbargs->is_split)
7099                   {
7100                     nlpt = notice_listptr (section_loc, &known_locsptr,
7101                                            cbargs->addrsize,
7102                                            cbargs->offset_size,
7103                                            cbargs->cu, num, attr);
7104                   }
7105                 else
7106                   nlpt = true;
7107               }
7108             else
7109               {
7110                 /* Only register for a real section offset.  Otherwise
7111                    it is a DW_FORM_loclistx which is just an index
7112                    number and we should already have registered the
7113                    section offset for the index when we saw the
7114                    DW_AT_loclists_base CU attribute.  */
7115                 if (form == DW_FORM_sec_offset)
7116                   nlpt = notice_listptr (section_loc, &known_loclistsptr,
7117                                          cbargs->addrsize, cbargs->offset_size,
7118                                          cbargs->cu, num, attr);
7119                 else
7120                   nlpt = true;
7121
7122               }
7123
7124             if (!cbargs->silent)
7125               {
7126                 if (cbargs->cu->version < 5 || form == DW_FORM_sec_offset)
7127                   printf ("           %*s%-20s (%s) location list [%6"
7128                           PRIxMAX "]%s\n",
7129                           (int) (level * 2), "", dwarf_attr_name (attr),
7130                           dwarf_form_name (form), (uintmax_t) num,
7131                           nlpt ? "" : " <WARNING offset too big>");
7132                 else
7133                   printf ("           %*s%-20s (%s) location index [%6"
7134                           PRIxMAX "]\n",
7135                           (int) (level * 2), "", dwarf_attr_name (attr),
7136                           dwarf_form_name (form), (uintmax_t) num);
7137               }
7138           }
7139           return DWARF_CB_OK;
7140
7141         case DW_AT_loclists_base:
7142           {
7143             bool nlpt = notice_listptr (section_loc, &known_loclistsptr,
7144                                         cbargs->addrsize, cbargs->offset_size,
7145                                         cbargs->cu, num, attr);
7146
7147             if (!cbargs->silent)
7148               printf ("           %*s%-20s (%s) location list [%6" PRIxMAX "]%s\n",
7149                       (int) (level * 2), "", dwarf_attr_name (attr),
7150                       dwarf_form_name (form), (uintmax_t) num,
7151                       nlpt ? "" : " <WARNING offset too big>");
7152           }
7153           return DWARF_CB_OK;
7154
7155         case DW_AT_ranges:
7156         case DW_AT_start_scope:
7157           {
7158             bool nlpt;
7159             if (cbargs->cu->version < 5)
7160               nlpt = notice_listptr (section_ranges, &known_rangelistptr,
7161                                      cbargs->addrsize, cbargs->offset_size,
7162                                      cbargs->cu, num, attr);
7163             else
7164               {
7165                 /* Only register for a real section offset.  Otherwise
7166                    it is a DW_FORM_rangelistx which is just an index
7167                    number and we should already have registered the
7168                    section offset for the index when we saw the
7169                    DW_AT_rnglists_base CU attribute.  */
7170                 if (form == DW_FORM_sec_offset)
7171                   nlpt = notice_listptr (section_ranges, &known_rnglistptr,
7172                                          cbargs->addrsize, cbargs->offset_size,
7173                                          cbargs->cu, num, attr);
7174                 else
7175                   nlpt = true;
7176               }
7177
7178             if (!cbargs->silent)
7179               {
7180                 if (cbargs->cu->version < 5 || form == DW_FORM_sec_offset)
7181                   printf ("           %*s%-20s (%s) range list [%6"
7182                           PRIxMAX "]%s\n",
7183                           (int) (level * 2), "", dwarf_attr_name (attr),
7184                           dwarf_form_name (form), (uintmax_t) num,
7185                           nlpt ? "" : " <WARNING offset too big>");
7186                 else
7187                   printf ("           %*s%-20s (%s) range index [%6"
7188                           PRIxMAX "]\n",
7189                           (int) (level * 2), "", dwarf_attr_name (attr),
7190                           dwarf_form_name (form), (uintmax_t) num);
7191               }
7192           }
7193           return DWARF_CB_OK;
7194
7195         case DW_AT_rnglists_base:
7196           {
7197             bool nlpt = notice_listptr (section_ranges, &known_rnglistptr,
7198                                         cbargs->addrsize, cbargs->offset_size,
7199                                         cbargs->cu, num, attr);
7200             if (!cbargs->silent)
7201               printf ("           %*s%-20s (%s) range list [%6"
7202                       PRIxMAX "]%s\n",
7203                       (int) (level * 2), "", dwarf_attr_name (attr),
7204                       dwarf_form_name (form), (uintmax_t) num,
7205                       nlpt ? "" : " <WARNING offset too big>");
7206           }
7207           return DWARF_CB_OK;
7208
7209         case DW_AT_addr_base:
7210         case DW_AT_GNU_addr_base:
7211           {
7212             bool addrbase = notice_listptr (section_addr, &known_addrbases,
7213                                             cbargs->addrsize,
7214                                             cbargs->offset_size,
7215                                             cbargs->cu, num, attr);
7216             if (!cbargs->silent)
7217               printf ("           %*s%-20s (%s) address base [%6"
7218                       PRIxMAX "]%s\n",
7219                       (int) (level * 2), "", dwarf_attr_name (attr),
7220                       dwarf_form_name (form), (uintmax_t) num,
7221                       addrbase ? "" : " <WARNING offset too big>");
7222           }
7223           return DWARF_CB_OK;
7224
7225         case DW_AT_str_offsets_base:
7226           {
7227             bool stroffbase = notice_listptr (section_str, &known_stroffbases,
7228                                               cbargs->addrsize,
7229                                               cbargs->offset_size,
7230                                               cbargs->cu, num, attr);
7231             if (!cbargs->silent)
7232               printf ("           %*s%-20s (%s) str offsets base [%6"
7233                       PRIxMAX "]%s\n",
7234                       (int) (level * 2), "", dwarf_attr_name (attr),
7235                       dwarf_form_name (form), (uintmax_t) num,
7236                       stroffbase ? "" : " <WARNING offset too big>");
7237           }
7238           return DWARF_CB_OK;
7239
7240         case DW_AT_language:
7241           valuestr = dwarf_lang_name (num);
7242           break;
7243         case DW_AT_encoding:
7244           valuestr = dwarf_encoding_name (num);
7245           break;
7246         case DW_AT_accessibility:
7247           valuestr = dwarf_access_name (num);
7248           break;
7249         case DW_AT_defaulted:
7250           valuestr = dwarf_defaulted_name (num);
7251           break;
7252         case DW_AT_visibility:
7253           valuestr = dwarf_visibility_name (num);
7254           break;
7255         case DW_AT_virtuality:
7256           valuestr = dwarf_virtuality_name (num);
7257           break;
7258         case DW_AT_identifier_case:
7259           valuestr = dwarf_identifier_case_name (num);
7260           break;
7261         case DW_AT_calling_convention:
7262           valuestr = dwarf_calling_convention_name (num);
7263           break;
7264         case DW_AT_inline:
7265           valuestr = dwarf_inline_name (num);
7266           break;
7267         case DW_AT_ordering:
7268           valuestr = dwarf_ordering_name (num);
7269           break;
7270         case DW_AT_discr_list:
7271           valuestr = dwarf_discr_list_name (num);
7272           break;
7273         case DW_AT_decl_file:
7274         case DW_AT_call_file:
7275           {
7276             if (cbargs->silent)
7277               break;
7278
7279             /* Try to get the actual file, the current interface only
7280                gives us full paths, but we only want to show the file
7281                name for now.  */
7282             Dwarf_Die cudie;
7283             if (dwarf_cu_die (cbargs->cu, &cudie,
7284                               NULL, NULL, NULL, NULL, NULL, NULL) != NULL)
7285               {
7286                 Dwarf_Files *files;
7287                 size_t nfiles;
7288                 if (dwarf_getsrcfiles (&cudie, &files, &nfiles) == 0)
7289                   {
7290                     valuestr = dwarf_filesrc (files, num, NULL, NULL);
7291                     if (valuestr != NULL)
7292                       {
7293                         char *filename = strrchr (valuestr, '/');
7294                         if (filename != NULL)
7295                           valuestr = filename + 1;
7296                       }
7297                     else
7298                       error (0, 0, gettext ("invalid file (%" PRId64 "): %s"),
7299                              num, dwarf_errmsg (-1));
7300                   }
7301                 else
7302                   error (0, 0, gettext ("no srcfiles for CU [%" PRIx64 "]"),
7303                          dwarf_dieoffset (&cudie));
7304               }
7305             else
7306              error (0, 0, gettext ("couldn't get DWARF CU: %s"),
7307                     dwarf_errmsg (-1));
7308             if (valuestr == NULL)
7309               valuestr = "???";
7310           }
7311           break;
7312         case DW_AT_GNU_dwo_id:
7313           as_hex_id = true;
7314           break;
7315
7316         default:
7317           /* Nothing.  */
7318           break;
7319         }
7320
7321       if (cbargs->silent)
7322         break;
7323
7324       /* When highpc is in constant form it is relative to lowpc.
7325          In that case also show the address.  */
7326       Dwarf_Addr highpc;
7327       if (attr == DW_AT_high_pc && dwarf_highpc (cbargs->die, &highpc) == 0)
7328         {
7329           char *a = format_dwarf_addr (cbargs->dwflmod, cbargs->addrsize,
7330                                        highpc, highpc);
7331           printf ("           %*s%-20s (%s) %" PRIuMAX " (%s)\n",
7332                   (int) (level * 2), "", dwarf_attr_name (attr),
7333                   dwarf_form_name (form), (uintmax_t) num, a);
7334           free (a);
7335         }
7336       else
7337         {
7338           Dwarf_Sword snum = 0;
7339           if (form == DW_FORM_sdata)
7340             if (unlikely (dwarf_formsdata (attrp, &snum) != 0))
7341               goto attrval_out;
7342
7343           if (as_hex_id)
7344             {
7345               printf ("           %*s%-20s (%s) 0x%.16" PRIx64 "\n",
7346                       (int) (level * 2), "", dwarf_attr_name (attr),
7347                       dwarf_form_name (form), num);
7348             }
7349           else if (valuestr == NULL)
7350             {
7351               printf ("           %*s%-20s (%s)",
7352                       (int) (level * 2), "", dwarf_attr_name (attr),
7353                       dwarf_form_name (form));
7354               if (form == DW_FORM_sdata)
7355                 printf (" %" PRIdMAX "\n", (intmax_t) snum);
7356               else
7357                 printf (" %" PRIuMAX "\n", (uintmax_t) num);
7358             }
7359           else
7360             {
7361               printf ("           %*s%-20s (%s) %s",
7362                       (int) (level * 2), "", dwarf_attr_name (attr),
7363                       dwarf_form_name (form), valuestr);
7364               if (form == DW_FORM_sdata)
7365                 printf (" (%" PRIdMAX ")\n", (intmax_t) snum);
7366               else
7367                 printf (" (%" PRIuMAX ")\n", (uintmax_t) num);
7368             }
7369         }
7370       break;
7371
7372     case DW_FORM_flag:
7373       if (cbargs->silent)
7374         break;
7375       bool flag;
7376       if (unlikely (dwarf_formflag (attrp, &flag) != 0))
7377         goto attrval_out;
7378
7379       printf ("           %*s%-20s (%s) %s\n",
7380               (int) (level * 2), "", dwarf_attr_name (attr),
7381               dwarf_form_name (form), flag ? yes_str : no_str);
7382       break;
7383
7384     case DW_FORM_flag_present:
7385       if (cbargs->silent)
7386         break;
7387       printf ("           %*s%-20s (%s) %s\n",
7388               (int) (level * 2), "", dwarf_attr_name (attr),
7389               dwarf_form_name (form), yes_str);
7390       break;
7391
7392     case DW_FORM_exprloc:
7393     case DW_FORM_block4:
7394     case DW_FORM_block2:
7395     case DW_FORM_block1:
7396     case DW_FORM_block:
7397     case DW_FORM_data16: /* DWARF5 calls this a constant class.  */
7398       if (cbargs->silent)
7399         break;
7400       Dwarf_Block block;
7401       if (unlikely (dwarf_formblock (attrp, &block) != 0))
7402         goto attrval_out;
7403
7404       printf ("           %*s%-20s (%s) ",
7405               (int) (level * 2), "", dwarf_attr_name (attr),
7406               dwarf_form_name (form));
7407
7408       switch (attr)
7409         {
7410         default:
7411           if (form != DW_FORM_exprloc)
7412             {
7413               print_block (block.length, block.data);
7414               break;
7415             }
7416           FALLTHROUGH;
7417
7418         case DW_AT_location:
7419         case DW_AT_data_location:
7420         case DW_AT_data_member_location:
7421         case DW_AT_vtable_elem_location:
7422         case DW_AT_string_length:
7423         case DW_AT_use_location:
7424         case DW_AT_frame_base:
7425         case DW_AT_return_addr:
7426         case DW_AT_static_link:
7427         case DW_AT_allocated:
7428         case DW_AT_associated:
7429         case DW_AT_bit_size:
7430         case DW_AT_bit_offset:
7431         case DW_AT_bit_stride:
7432         case DW_AT_byte_size:
7433         case DW_AT_byte_stride:
7434         case DW_AT_count:
7435         case DW_AT_lower_bound:
7436         case DW_AT_upper_bound:
7437         case DW_AT_GNU_call_site_value:
7438         case DW_AT_GNU_call_site_data_value:
7439         case DW_AT_GNU_call_site_target:
7440         case DW_AT_GNU_call_site_target_clobbered:
7441           putchar ('\n');
7442           print_ops (cbargs->dwflmod, cbargs->dbg,
7443                      12 + level * 2, 12 + level * 2,
7444                      cbargs->version, cbargs->addrsize, cbargs->offset_size,
7445                      attrp->cu, block.length, block.data);
7446           break;
7447         }
7448       break;
7449
7450     default:
7451       if (cbargs->silent)
7452         break;
7453       printf ("           %*s%-20s (%s) ???\n",
7454               (int) (level * 2), "", dwarf_attr_name (attr),
7455               dwarf_form_name (form));
7456       break;
7457     }
7458
7459   return DWARF_CB_OK;
7460 }
7461
7462 static void
7463 print_debug_units (Dwfl_Module *dwflmod,
7464                    Ebl *ebl, GElf_Ehdr *ehdr,
7465                    Elf_Scn *scn, GElf_Shdr *shdr,
7466                    Dwarf *dbg, bool debug_types)
7467 {
7468   const bool silent = !(print_debug_sections & section_info) && !debug_types;
7469   const char *secname = section_name (ebl, ehdr, shdr);
7470
7471   if (!silent)
7472     printf (gettext ("\
7473 \nDWARF section [%2zu] '%s' at offset %#" PRIx64 ":\n [Offset]\n"),
7474             elf_ndxscn (scn), secname, (uint64_t) shdr->sh_offset);
7475
7476   /* If the section is empty we don't have to do anything.  */
7477   if (!silent && shdr->sh_size == 0)
7478     return;
7479
7480   int maxdies = 20;
7481   Dwarf_Die *dies = (Dwarf_Die *) xmalloc (maxdies * sizeof (Dwarf_Die));
7482
7483   /* New compilation unit.  */
7484   Dwarf_Half version;
7485
7486   Dwarf_Die result;
7487   Dwarf_Off abbroffset;
7488   uint8_t addrsize;
7489   uint8_t offsize;
7490   uint64_t unit_id;
7491   Dwarf_Off subdie_off;
7492
7493   int unit_res;
7494   Dwarf_CU *cu;
7495   Dwarf_CU cu_mem;
7496   uint8_t unit_type;
7497   Dwarf_Die cudie;
7498
7499   /* We cheat a little because we want to see only the CUs from .debug_info
7500      or .debug_types.  We know the Dwarf_CU struct layout.  Set it up at
7501      the end of .debug_info if we want .debug_types only.  Check the returned
7502      Dwarf_CU is still in the expected section.  */
7503   if (debug_types)
7504     {
7505       cu_mem.dbg = dbg;
7506       cu_mem.end = dbg->sectiondata[IDX_debug_info]->d_size;
7507       cu_mem.sec_idx = IDX_debug_info;
7508       cu = &cu_mem;
7509     }
7510   else
7511     cu = NULL;
7512
7513  next_cu:
7514   unit_res = dwarf_get_units (dbg, cu, &cu, &version, &unit_type,
7515                               &cudie, NULL);
7516   if (unit_res == 1)
7517     goto do_return;
7518
7519   if (unit_res == -1)
7520     {
7521       if (!silent)
7522         error (0, 0, gettext ("cannot get next unit: %s"), dwarf_errmsg (-1));
7523       goto do_return;
7524     }
7525
7526   if (cu->sec_idx != (size_t) (debug_types ? IDX_debug_types : IDX_debug_info))
7527     goto do_return;
7528
7529   dwarf_cu_die (cu, &result, NULL, &abbroffset, &addrsize, &offsize,
7530                 &unit_id, &subdie_off);
7531
7532   if (!silent)
7533     {
7534       Dwarf_Off offset = cu->start;
7535       if (debug_types && version < 5)
7536         {
7537           Dwarf_Die typedie;
7538           Dwarf_Off dieoffset;
7539           dieoffset = dwarf_dieoffset (dwarf_offdie_types (dbg, subdie_off,
7540                                                            &typedie));
7541           printf (gettext (" Type unit at offset %" PRIu64 ":\n"
7542                            " Version: %" PRIu16
7543                            ", Abbreviation section offset: %" PRIu64
7544                            ", Address size: %" PRIu8
7545                            ", Offset size: %" PRIu8
7546                            "\n Type signature: %#" PRIx64
7547                            ", Type offset: %#" PRIx64 " [%" PRIx64 "]\n"),
7548                   (uint64_t) offset, version, abbroffset, addrsize, offsize,
7549                   unit_id, (uint64_t) subdie_off, dieoffset);
7550         }
7551       else
7552         {
7553           printf (gettext (" Compilation unit at offset %" PRIu64 ":\n"
7554                            " Version: %" PRIu16
7555                            ", Abbreviation section offset: %" PRIu64
7556                            ", Address size: %" PRIu8
7557                            ", Offset size: %" PRIu8 "\n"),
7558                   (uint64_t) offset, version, abbroffset, addrsize, offsize);
7559
7560           if (version >= 5 || (unit_type != DW_UT_compile
7561                                && unit_type != DW_UT_partial))
7562             {
7563               printf (gettext (" Unit type: %s (%" PRIu8 ")"),
7564                                dwarf_unit_name (unit_type), unit_type);
7565               if (unit_type == DW_UT_type
7566                   || unit_type == DW_UT_skeleton
7567                   || unit_type == DW_UT_split_compile
7568                   || unit_type == DW_UT_split_type)
7569                 printf (", Unit id: 0x%.16" PRIx64 "", unit_id);
7570               if (unit_type == DW_UT_type
7571                   || unit_type == DW_UT_split_type)
7572                 {
7573                   Dwarf_Die typedie;
7574                   Dwarf_Off dieoffset;
7575                   dwarf_cu_info (cu, NULL, NULL, NULL, &typedie,
7576                                  NULL, NULL, NULL);
7577                   dieoffset = dwarf_dieoffset (&typedie);
7578                   printf (", Unit DIE off: %#" PRIx64 " [%" PRIx64 "]",
7579                           subdie_off, dieoffset);
7580                 }
7581               printf ("\n");
7582             }
7583         }
7584     }
7585
7586   if (version < 2 || version > 5
7587       || unit_type < DW_UT_compile || unit_type > DW_UT_split_type)
7588     {
7589       if (!silent)
7590         error (0, 0, gettext ("unknown version (%d) or unit type (%d)"),
7591                version, unit_type);
7592       goto next_cu;
7593     }
7594
7595   struct attrcb_args args =
7596     {
7597       .dwflmod = dwflmod,
7598       .silent = silent,
7599       .version = version,
7600       .addrsize = addrsize,
7601       .offset_size = offsize
7602     };
7603
7604   bool is_split = false;
7605   int level = 0;
7606   dies[0] = cudie;
7607   args.cu = dies[0].cu;
7608   args.dbg = dbg;
7609   args.is_split = is_split;
7610
7611   /* We might return here again for the split CU subdie.  */
7612   do_cu:
7613   do
7614     {
7615       Dwarf_Off offset = dwarf_dieoffset (&dies[level]);
7616       if (unlikely (offset == (Dwarf_Off) -1))
7617         {
7618           if (!silent)
7619             error (0, 0, gettext ("cannot get DIE offset: %s"),
7620                    dwarf_errmsg (-1));
7621           goto do_return;
7622         }
7623
7624       int tag = dwarf_tag (&dies[level]);
7625       if (unlikely (tag == DW_TAG_invalid))
7626         {
7627           if (!silent)
7628             error (0, 0, gettext ("cannot get tag of DIE at offset [%" PRIx64
7629                                   "] in section '%s': %s"),
7630                    (uint64_t) offset, secname, dwarf_errmsg (-1));
7631           goto do_return;
7632         }
7633
7634       if (!silent)
7635         {
7636           unsigned int code = dwarf_getabbrevcode (dies[level].abbrev);
7637           if (is_split)
7638             printf (" {%6" PRIx64 "}  ", (uint64_t) offset);
7639           else
7640             printf (" [%6" PRIx64 "]  ", (uint64_t) offset);
7641           printf ("%*s%-20s abbrev: %u\n", (int) (level * 2), "",
7642                   dwarf_tag_name (tag), code);
7643         }
7644
7645       /* Print the attribute values.  */
7646       args.level = level;
7647       args.die = &dies[level];
7648       (void) dwarf_getattrs (&dies[level], attr_callback, &args, 0);
7649
7650       /* Make room for the next level's DIE.  */
7651       if (level + 1 == maxdies)
7652         dies = (Dwarf_Die *) xrealloc (dies,
7653                                        (maxdies += 10)
7654                                        * sizeof (Dwarf_Die));
7655
7656       int res = dwarf_child (&dies[level], &dies[level + 1]);
7657       if (res > 0)
7658         {
7659           while ((res = dwarf_siblingof (&dies[level], &dies[level])) == 1)
7660             if (level-- == 0)
7661               break;
7662
7663           if (unlikely (res == -1))
7664             {
7665               if (!silent)
7666                 error (0, 0, gettext ("cannot get next DIE: %s\n"),
7667                        dwarf_errmsg (-1));
7668               goto do_return;
7669             }
7670         }
7671       else if (unlikely (res < 0))
7672         {
7673           if (!silent)
7674             error (0, 0, gettext ("cannot get next DIE: %s"),
7675                    dwarf_errmsg (-1));
7676           goto do_return;
7677         }
7678       else
7679         ++level;
7680     }
7681   while (level >= 0);
7682
7683   /* We might want to show the split compile unit if this was a skeleton.
7684      We need to scan it if we are requesting printing .debug_ranges for
7685      DWARF4 since GNU DebugFission uses "offsets" into the main ranges
7686      section.  */
7687   if (unit_type == DW_UT_skeleton
7688       && ((!silent && show_split_units)
7689           || (version < 5 && (print_debug_sections & section_ranges) != 0)))
7690     {
7691       Dwarf_Die subdie;
7692       if (dwarf_cu_info (cu, NULL, NULL, NULL, &subdie, NULL, NULL, NULL) != 0
7693           || dwarf_tag (&subdie) == DW_TAG_invalid)
7694         {
7695           if (!silent)
7696             {
7697               Dwarf_Attribute dwo_at;
7698               const char *dwo_name =
7699                 (dwarf_formstring (dwarf_attr (&cudie, DW_AT_dwo_name,
7700                                                &dwo_at))
7701                  ?: (dwarf_formstring (dwarf_attr (&cudie, DW_AT_GNU_dwo_name,
7702                                                    &dwo_at))
7703                      ?: "<unknown>"));
7704               fprintf (stderr,
7705                        "Could not find split unit '%s', id: %" PRIx64 "\n",
7706                        dwo_name, unit_id);
7707             }
7708         }
7709       else
7710         {
7711           Dwarf_CU *split_cu = subdie.cu;
7712           dwarf_cu_die (split_cu, &result, NULL, &abbroffset,
7713                         &addrsize, &offsize, &unit_id, &subdie_off);
7714           Dwarf_Off offset = cu->start;
7715
7716           if (!silent)
7717             {
7718               printf (gettext (" Split compilation unit at offset %"
7719                                PRIu64 ":\n"
7720                                " Version: %" PRIu16
7721                                ", Abbreviation section offset: %" PRIu64
7722                                ", Address size: %" PRIu8
7723                                ", Offset size: %" PRIu8 "\n"),
7724                       (uint64_t) offset, version, abbroffset,
7725                       addrsize, offsize);
7726               printf (gettext (" Unit type: %s (%" PRIu8 ")"),
7727                       dwarf_unit_name (unit_type), unit_type);
7728               printf (", Unit id: 0x%.16" PRIx64 "", unit_id);
7729               printf ("\n");
7730             }
7731
7732           unit_type = DW_UT_split_compile;
7733           is_split = true;
7734           level = 0;
7735           dies[0] = subdie;
7736           args.cu = dies[0].cu;
7737           args.dbg = split_cu->dbg;
7738           args.is_split = is_split;
7739           goto do_cu;
7740         }
7741     }
7742
7743   /* And again... */
7744   goto next_cu;
7745
7746  do_return:
7747   free (dies);
7748 }
7749
7750 static void
7751 print_debug_info_section (Dwfl_Module *dwflmod, Ebl *ebl, GElf_Ehdr *ehdr,
7752                           Elf_Scn *scn, GElf_Shdr *shdr, Dwarf *dbg)
7753 {
7754   print_debug_units (dwflmod, ebl, ehdr, scn, shdr, dbg, false);
7755 }
7756
7757 static void
7758 print_debug_types_section (Dwfl_Module *dwflmod, Ebl *ebl, GElf_Ehdr *ehdr,
7759                            Elf_Scn *scn, GElf_Shdr *shdr, Dwarf *dbg)
7760 {
7761   print_debug_units (dwflmod, ebl, ehdr, scn, shdr, dbg, true);
7762 }
7763
7764
7765 static void
7766 print_decoded_line_section (Dwfl_Module *dwflmod, Ebl *ebl, GElf_Ehdr *ehdr,
7767                             Elf_Scn *scn, GElf_Shdr *shdr, Dwarf *dbg)
7768 {
7769   printf (gettext ("\
7770 \nDWARF section [%2zu] '%s' at offset %#" PRIx64 ":\n\n"),
7771           elf_ndxscn (scn), section_name (ebl, ehdr, shdr),
7772           (uint64_t) shdr->sh_offset);
7773
7774   size_t address_size
7775     = elf_getident (ebl->elf, NULL)[EI_CLASS] == ELFCLASS32 ? 4 : 8;
7776
7777   Dwarf_Off cuoffset;
7778   Dwarf_Off ncuoffset = 0;
7779   size_t hsize;
7780   while (dwarf_nextcu (dbg, cuoffset = ncuoffset, &ncuoffset, &hsize,
7781                        NULL, NULL, NULL) == 0)
7782     {
7783       Dwarf_Die cudie;
7784       if (dwarf_offdie (dbg, cuoffset + hsize, &cudie) == NULL)
7785         continue;
7786
7787       size_t nlines;
7788       Dwarf_Lines *lines;
7789       if (dwarf_getsrclines (&cudie, &lines, &nlines) != 0)
7790         continue;
7791
7792       printf (" CU [%" PRIx64 "] %s\n",
7793               dwarf_dieoffset (&cudie), dwarf_diename (&cudie));
7794       printf ("  line:col SBPE* disc isa op address"
7795               " (Statement Block Prologue Epilogue *End)\n");
7796       const char *last_file = "";
7797       for (size_t n = 0; n < nlines; n++)
7798         {
7799           Dwarf_Line *line = dwarf_onesrcline (lines, n);
7800           if (line == NULL)
7801             {
7802               printf ("  dwarf_onesrcline: %s\n", dwarf_errmsg (-1));
7803               continue;
7804             }
7805           Dwarf_Word mtime, length;
7806           const char *file = dwarf_linesrc (line, &mtime, &length);
7807           if (file == NULL)
7808             {
7809               printf ("  <%s> (mtime: ?, length: ?)\n", dwarf_errmsg (-1));
7810               last_file = "";
7811             }
7812           else if (strcmp (last_file, file) != 0)
7813             {
7814               printf ("  %s (mtime: %" PRIu64 ", length: %" PRIu64 ")\n",
7815                       file, mtime, length);
7816               last_file = file;
7817             }
7818
7819           int lineno, colno;
7820           bool statement, endseq, block, prologue_end, epilogue_begin;
7821           unsigned int lineop, isa, disc;
7822           Dwarf_Addr address;
7823           dwarf_lineaddr (line, &address);
7824           dwarf_lineno (line, &lineno);
7825           dwarf_linecol (line, &colno);
7826           dwarf_lineop_index (line, &lineop);
7827           dwarf_linebeginstatement (line, &statement);
7828           dwarf_lineendsequence (line, &endseq);
7829           dwarf_lineblock (line, &block);
7830           dwarf_lineprologueend (line, &prologue_end);
7831           dwarf_lineepiloguebegin (line, &epilogue_begin);
7832           dwarf_lineisa (line, &isa);
7833           dwarf_linediscriminator (line, &disc);
7834
7835           /* End sequence is special, it is one byte past.  */
7836           char *a = format_dwarf_addr (dwflmod, address_size,
7837                                        address - (endseq ? 1 : 0), address);
7838           printf ("  %4d:%-3d %c%c%c%c%c %4d %3d %2d %s\n",
7839                   lineno, colno,
7840                   (statement ? 'S' : ' '),
7841                   (block ? 'B' : ' '),
7842                   (prologue_end ? 'P' : ' '),
7843                   (epilogue_begin ? 'E' : ' '),
7844                   (endseq ? '*' : ' '),
7845                   disc, isa, lineop, a);
7846           free (a);
7847
7848           if (endseq)
7849             printf("\n");
7850         }
7851     }
7852 }
7853
7854
7855 /* Print the value of a form.
7856    Returns new value of readp, or readendp on failure.  */
7857 static const unsigned char *
7858 print_form_data (Dwarf *dbg, int form, const unsigned char *readp,
7859                  const unsigned char *readendp, unsigned int offset_len,
7860                  Dwarf_Off str_offsets_base)
7861 {
7862   Dwarf_Word val;
7863   unsigned char *endp;
7864   Elf_Data *data;
7865   char *str;
7866   switch (form)
7867     {
7868     case DW_FORM_data1:
7869       if (readendp - readp < 1)
7870         {
7871         invalid_data:
7872           error (0, 0, "invalid data");
7873           return readendp;
7874         }
7875       val = *readp++;
7876       printf (" %" PRIx8, (unsigned int) val);
7877       break;
7878
7879     case DW_FORM_data2:
7880       if (readendp - readp < 2)
7881         goto invalid_data;
7882       val = read_2ubyte_unaligned_inc (dbg, readp);
7883       printf(" %" PRIx16, (unsigned int) val);
7884       break;
7885
7886     case DW_FORM_data4:
7887       if (readendp - readp < 4)
7888         goto invalid_data;
7889       val = read_4ubyte_unaligned_inc (dbg, readp);
7890       printf (" %" PRIx32, (unsigned int) val);
7891       break;
7892
7893     case DW_FORM_data8:
7894       if (readendp - readp < 8)
7895         goto invalid_data;
7896       val = read_8ubyte_unaligned_inc (dbg, readp);
7897       printf (" %" PRIx64, val);
7898       break;
7899
7900     case DW_FORM_sdata:
7901       if (readendp - readp < 1)
7902         goto invalid_data;
7903       get_sleb128 (val, readp, readendp);
7904       printf (" %" PRIx64, val);
7905       break;
7906
7907     case DW_FORM_udata:
7908       if (readendp - readp < 1)
7909         goto invalid_data;
7910       get_uleb128 (val, readp, readendp);
7911       printf (" %" PRIx64, val);
7912       break;
7913
7914     case DW_FORM_block:
7915       if (readendp - readp < 1)
7916         goto invalid_data;
7917       get_uleb128 (val, readp, readendp);
7918       if (readendp - readp < (ptrdiff_t) val)
7919         goto invalid_data;
7920       print_bytes (val, readp);
7921       readp += val;
7922       break;
7923
7924     case DW_FORM_block1:
7925       if (readendp - readp < 1)
7926         goto invalid_data;
7927       val = *readp++;
7928       if (readendp - readp < (ptrdiff_t) val)
7929         goto invalid_data;
7930       print_bytes (val, readp);
7931       readp += val;
7932       break;
7933
7934     case DW_FORM_block2:
7935       if (readendp - readp < 2)
7936         goto invalid_data;
7937       val = read_2ubyte_unaligned_inc (dbg, readp);
7938       if (readendp - readp < (ptrdiff_t) val)
7939         goto invalid_data;
7940       print_bytes (val, readp);
7941       readp += val;
7942       break;
7943
7944     case DW_FORM_block4:
7945       if (readendp - readp < 2)
7946         goto invalid_data;
7947       val = read_4ubyte_unaligned_inc (dbg, readp);
7948       if (readendp - readp < (ptrdiff_t) val)
7949         goto invalid_data;
7950       print_bytes (val, readp);
7951       readp += val;
7952       break;
7953
7954     case DW_FORM_data16:
7955       if (readendp - readp < 16)
7956         goto invalid_data;
7957       print_bytes (16, readp);
7958       readp += 16;
7959       break;
7960
7961     case DW_FORM_flag:
7962       if (readendp - readp < 1)
7963         goto invalid_data;
7964       val = *readp++;
7965       printf ("%s", val != 0 ? gettext ("yes") : gettext ("no"));
7966       break;
7967
7968     case DW_FORM_string:
7969       endp = memchr (readp, '\0', readendp - readp);
7970       if (endp == NULL)
7971         goto invalid_data;
7972       printf ("%s", readp);
7973       readp = endp + 1;
7974       break;
7975
7976     case DW_FORM_strp:
7977     case DW_FORM_line_strp:
7978     case DW_FORM_strp_sup:
7979       if (readendp - readp < (ptrdiff_t) offset_len)
7980         goto invalid_data;
7981       if (offset_len == 8)
7982         val = read_8ubyte_unaligned_inc (dbg, readp);
7983       else
7984         val = read_4ubyte_unaligned_inc (dbg, readp);
7985       if (form == DW_FORM_strp)
7986         data = dbg->sectiondata[IDX_debug_str];
7987       else if (form == DW_FORM_line_strp)
7988         data = dbg->sectiondata[IDX_debug_line_str];
7989       else /* form == DW_FORM_strp_sup */
7990         {
7991           Dwarf *alt = dwarf_getalt (dbg);
7992           data = alt != NULL ? alt->sectiondata[IDX_debug_str] : NULL;
7993         }
7994       if (data == NULL || val >= data->d_size
7995           || memchr (data->d_buf + val, '\0', data->d_size - val) == NULL)
7996         str = "???";
7997       else
7998         str = (char *) data->d_buf + val;
7999       printf ("%s (%" PRIu64 ")", str, val);
8000       break;
8001
8002     case DW_FORM_sec_offset:
8003       if (readendp - readp < (ptrdiff_t) offset_len)
8004         goto invalid_data;
8005       if (offset_len == 8)
8006         val = read_8ubyte_unaligned_inc (dbg, readp);
8007       else
8008         val = read_4ubyte_unaligned_inc (dbg, readp);
8009       printf ("[%" PRIx64 "]", val);
8010       break;
8011
8012     case DW_FORM_strx:
8013     case DW_FORM_GNU_str_index:
8014       if (readendp - readp < 1)
8015         goto invalid_data;
8016       get_uleb128 (val, readp, readendp);
8017     strx_val:
8018       data = dbg->sectiondata[IDX_debug_str_offsets];
8019       if (data == NULL
8020           || data->d_size - str_offsets_base < val)
8021         str = "???";
8022       else
8023         {
8024           readp = data->d_buf + str_offsets_base + val;
8025           readendp = data->d_buf + data->d_size;
8026           if (readendp - readp < (ptrdiff_t) offset_len)
8027             str = "???";
8028           else
8029             {
8030               Dwarf_Off idx;
8031               if (offset_len == 8)
8032                 idx = read_8ubyte_unaligned_inc (dbg, readp);
8033               else
8034                 idx = read_4ubyte_unaligned_inc (dbg, readp);
8035
8036               data = dbg->sectiondata[IDX_debug_str];
8037               if (data == NULL || idx >= data->d_size
8038                   || memchr (data->d_buf + idx, '\0',
8039                              data->d_size - idx) == NULL)
8040                 str = "???";
8041               else
8042                 str = (char *) data->d_buf + idx;
8043             }
8044         }
8045       printf ("%s (%" PRIu64 ")", str, val);
8046       break;
8047
8048     case DW_FORM_strx1:
8049       if (readendp - readp < 1)
8050         goto invalid_data;
8051       val = *readp;
8052       goto strx_val;
8053
8054     case DW_FORM_strx2:
8055       if (readendp - readp < 2)
8056         goto invalid_data;
8057       val = read_2ubyte_unaligned (dbg, readp);
8058       goto strx_val;
8059
8060     case DW_FORM_strx3:
8061       if (readendp - readp < 3)
8062         goto invalid_data;
8063       val = read_3ubyte_unaligned (dbg, readp);
8064       goto strx_val;
8065
8066     case DW_FORM_strx4:
8067       if (readendp - readp < 4)
8068         goto invalid_data;
8069       val = read_4ubyte_unaligned (dbg, readp);
8070       goto strx_val;
8071
8072     default:
8073       error (0, 0, gettext ("unknown form: %s"), dwarf_form_name (form));
8074       return readendp;
8075     }
8076
8077   return readp;
8078 }
8079
8080 static void
8081 print_debug_line_section (Dwfl_Module *dwflmod, Ebl *ebl, GElf_Ehdr *ehdr,
8082                           Elf_Scn *scn, GElf_Shdr *shdr, Dwarf *dbg)
8083 {
8084   if (decodedline)
8085     {
8086       print_decoded_line_section (dwflmod, ebl, ehdr, scn, shdr, dbg);
8087       return;
8088     }
8089
8090   printf (gettext ("\
8091 \nDWARF section [%2zu] '%s' at offset %#" PRIx64 ":\n"),
8092           elf_ndxscn (scn), section_name (ebl, ehdr, shdr),
8093           (uint64_t) shdr->sh_offset);
8094
8095   if (shdr->sh_size == 0)
8096     return;
8097
8098   /* There is no functionality in libdw to read the information in the
8099      way it is represented here.  Hardcode the decoder.  */
8100   Elf_Data *data = (dbg->sectiondata[IDX_debug_line]
8101                     ?: elf_rawdata (scn, NULL));
8102   if (unlikely (data == NULL))
8103     {
8104       error (0, 0, gettext ("cannot get line data section data: %s"),
8105              elf_errmsg (-1));
8106       return;
8107     }
8108
8109   const unsigned char *linep = (const unsigned char *) data->d_buf;
8110   const unsigned char *lineendp;
8111
8112   while (linep
8113          < (lineendp = (const unsigned char *) data->d_buf + data->d_size))
8114     {
8115       size_t start_offset = linep - (const unsigned char *) data->d_buf;
8116
8117       printf (gettext ("\nTable at offset %zu:\n"), start_offset);
8118
8119       if (unlikely (linep + 4 > lineendp))
8120         goto invalid_data;
8121       Dwarf_Word unit_length = read_4ubyte_unaligned_inc (dbg, linep);
8122       unsigned int length = 4;
8123       if (unlikely (unit_length == 0xffffffff))
8124         {
8125           if (unlikely (linep + 8 > lineendp))
8126             {
8127             invalid_data:
8128               error (0, 0, gettext ("invalid data in section [%zu] '%s'"),
8129                      elf_ndxscn (scn), section_name (ebl, ehdr, shdr));
8130               return;
8131             }
8132           unit_length = read_8ubyte_unaligned_inc (dbg, linep);
8133           length = 8;
8134         }
8135
8136       /* Check whether we have enough room in the section.  */
8137       if (unlikely (unit_length > (size_t) (lineendp - linep)))
8138         goto invalid_data;
8139       lineendp = linep + unit_length;
8140
8141       /* The next element of the header is the version identifier.  */
8142       if ((size_t) (lineendp - linep) < 2)
8143         goto invalid_data;
8144       uint_fast16_t version = read_2ubyte_unaligned_inc (dbg, linep);
8145
8146       size_t address_size
8147         = elf_getident (ebl->elf, NULL)[EI_CLASS] == ELFCLASS32 ? 4 : 8;
8148       unsigned char segment_selector_size = 0;
8149       if (version > 4)
8150         {
8151           if ((size_t) (lineendp - linep) < 2)
8152             goto invalid_data;
8153           address_size = *linep++;
8154           segment_selector_size = *linep++;
8155         }
8156
8157       /* Next comes the header length.  */
8158       Dwarf_Word header_length;
8159       if (length == 4)
8160         {
8161           if ((size_t) (lineendp - linep) < 4)
8162             goto invalid_data;
8163           header_length = read_4ubyte_unaligned_inc (dbg, linep);
8164         }
8165       else
8166         {
8167           if ((size_t) (lineendp - linep) < 8)
8168             goto invalid_data;
8169           header_length = read_8ubyte_unaligned_inc (dbg, linep);
8170         }
8171
8172       /* Next the minimum instruction length.  */
8173       if ((size_t) (lineendp - linep) < 1)
8174         goto invalid_data;
8175       uint_fast8_t minimum_instr_len = *linep++;
8176
8177       /* Next the maximum operations per instruction, in version 4 format.  */
8178       uint_fast8_t max_ops_per_instr;
8179       if (version < 4)
8180         max_ops_per_instr = 1;
8181       else
8182         {
8183           if ((size_t) (lineendp - linep) < 1)
8184             goto invalid_data;
8185           max_ops_per_instr = *linep++;
8186         }
8187
8188       /* We need at least 4 more bytes.  */
8189       if ((size_t) (lineendp - linep) < 4)
8190         goto invalid_data;
8191
8192       /* Then the flag determining the default value of the is_stmt
8193          register.  */
8194       uint_fast8_t default_is_stmt = *linep++;
8195
8196       /* Now the line base.  */
8197       int_fast8_t line_base = *linep++;
8198
8199       /* And the line range.  */
8200       uint_fast8_t line_range = *linep++;
8201
8202       /* The opcode base.  */
8203       uint_fast8_t opcode_base = *linep++;
8204
8205       /* Print what we got so far.  */
8206       printf (gettext ("\n"
8207                        " Length:                         %" PRIu64 "\n"
8208                        " DWARF version:                  %" PRIuFAST16 "\n"
8209                        " Prologue length:                %" PRIu64 "\n"
8210                        " Address size:                   %zd\n"
8211                        " Segment selector size:          %zd\n"
8212                        " Min instruction length:         %" PRIuFAST8 "\n"
8213                        " Max operations per instruction: %" PRIuFAST8 "\n"
8214                        " Initial value if 'is_stmt':     %" PRIuFAST8 "\n"
8215                        " Line base:                      %" PRIdFAST8 "\n"
8216                        " Line range:                     %" PRIuFAST8 "\n"
8217                        " Opcode base:                    %" PRIuFAST8 "\n"
8218                        "\n"
8219                        "Opcodes:\n"),
8220               (uint64_t) unit_length, version, (uint64_t) header_length,
8221               address_size, (size_t) segment_selector_size,
8222               minimum_instr_len, max_ops_per_instr,
8223               default_is_stmt, line_base,
8224               line_range, opcode_base);
8225
8226       if (version < 2 || version > 5)
8227         {
8228           error (0, 0, gettext ("cannot handle .debug_line version: %u\n"),
8229                  (unsigned int) version);
8230           linep = lineendp;
8231           continue;
8232         }
8233
8234       if (address_size != 4 && address_size != 8)
8235         {
8236           error (0, 0, gettext ("cannot handle address size: %u\n"),
8237                  (unsigned int) address_size);
8238           linep = lineendp;
8239           continue;
8240         }
8241
8242       if (segment_selector_size != 0)
8243         {
8244           error (0, 0, gettext ("cannot handle segment selector size: %u\n"),
8245                  (unsigned int) segment_selector_size);
8246           linep = lineendp;
8247           continue;
8248         }
8249
8250       if (unlikely (linep + opcode_base - 1 >= lineendp))
8251         {
8252         invalid_unit:
8253           error (0, 0,
8254                  gettext ("invalid data at offset %tu in section [%zu] '%s'"),
8255                  linep - (const unsigned char *) data->d_buf,
8256                  elf_ndxscn (scn), section_name (ebl, ehdr, shdr));
8257           linep = lineendp;
8258           continue;
8259         }
8260       int opcode_base_l10 = 1;
8261       unsigned int tmp = opcode_base;
8262       while (tmp > 10)
8263         {
8264           tmp /= 10;
8265           ++opcode_base_l10;
8266         }
8267       const uint8_t *standard_opcode_lengths = linep - 1;
8268       for (uint_fast8_t cnt = 1; cnt < opcode_base; ++cnt)
8269         printf (ngettext ("  [%*" PRIuFAST8 "]  %hhu argument\n",
8270                           "  [%*" PRIuFAST8 "]  %hhu arguments\n",
8271                           (int) linep[cnt - 1]),
8272                 opcode_base_l10, cnt, linep[cnt - 1]);
8273       linep += opcode_base - 1;
8274
8275       if (unlikely (linep >= lineendp))
8276         goto invalid_unit;
8277
8278       Dwarf_Off str_offsets_base = str_offsets_base_off (dbg, NULL);
8279
8280       puts (gettext ("\nDirectory table:"));
8281       if (version > 4)
8282         {
8283           struct encpair { uint16_t desc; uint16_t form; };
8284           struct encpair enc[256];
8285
8286           printf (gettext ("      ["));
8287           if ((size_t) (lineendp - linep) < 1)
8288             goto invalid_data;
8289           unsigned char directory_entry_format_count = *linep++;
8290           for (int i = 0; i < directory_entry_format_count; i++)
8291             {
8292               uint16_t desc, form;
8293               if ((size_t) (lineendp - linep) < 1)
8294                 goto invalid_data;
8295               get_uleb128 (desc, linep, lineendp);
8296               if ((size_t) (lineendp - linep) < 1)
8297                 goto invalid_data;
8298               get_uleb128 (form, linep, lineendp);
8299
8300               enc[i].desc = desc;
8301               enc[i].form = form;
8302
8303               printf ("%s(%s)",
8304                       dwarf_line_content_description_name (desc),
8305                       dwarf_form_name (form));
8306               if (i + 1 < directory_entry_format_count)
8307                 printf (", ");
8308             }
8309           printf ("]\n");
8310
8311           uint64_t directories_count;
8312           if ((size_t) (lineendp - linep) < 1)
8313             goto invalid_data;
8314           get_uleb128 (directories_count, linep, lineendp);
8315
8316           if (directory_entry_format_count == 0
8317               && directories_count != 0)
8318             goto invalid_data;
8319
8320           for (uint64_t i = 0; i < directories_count; i++)
8321             {
8322               printf (" %-5" PRIu64 " ", i);
8323               for (int j = 0; j < directory_entry_format_count; j++)
8324                 {
8325                   linep = print_form_data (dbg, enc[j].form,
8326                                            linep, lineendp, length,
8327                                            str_offsets_base);
8328                   if (j + 1 < directory_entry_format_count)
8329                     printf (", ");
8330                 }
8331               printf ("\n");
8332             }
8333         }
8334       else
8335         {
8336           while (*linep != 0)
8337             {
8338               unsigned char *endp = memchr (linep, '\0', lineendp - linep);
8339               if (unlikely (endp == NULL))
8340                 goto invalid_unit;
8341
8342               printf (" %s\n", (char *) linep);
8343
8344               linep = endp + 1;
8345             }
8346           /* Skip the final NUL byte.  */
8347           ++linep;
8348         }
8349
8350       if (unlikely (linep >= lineendp))
8351         goto invalid_unit;
8352
8353       puts (gettext ("\nFile name table:"));
8354       if (version > 4)
8355         {
8356           struct encpair { uint16_t desc; uint16_t form; };
8357           struct encpair enc[256];
8358
8359           printf (gettext ("      ["));
8360           if ((size_t) (lineendp - linep) < 1)
8361             goto invalid_data;
8362           unsigned char file_name_format_count = *linep++;
8363           for (int i = 0; i < file_name_format_count; i++)
8364             {
8365               uint64_t desc, form;
8366               if ((size_t) (lineendp - linep) < 1)
8367                 goto invalid_data;
8368               get_uleb128 (desc, linep, lineendp);
8369               if ((size_t) (lineendp - linep) < 1)
8370                 goto invalid_data;
8371               get_uleb128 (form, linep, lineendp);
8372
8373               if (! libdw_valid_user_form (form))
8374                 goto invalid_data;
8375
8376               enc[i].desc = desc;
8377               enc[i].form = form;
8378
8379               printf ("%s(%s)",
8380                       dwarf_line_content_description_name (desc),
8381                       dwarf_form_name (form));
8382               if (i + 1 < file_name_format_count)
8383                 printf (", ");
8384             }
8385           printf ("]\n");
8386
8387           uint64_t file_name_count;
8388           if ((size_t) (lineendp - linep) < 1)
8389             goto invalid_data;
8390           get_uleb128 (file_name_count, linep, lineendp);
8391
8392           if (file_name_format_count == 0
8393               && file_name_count != 0)
8394             goto invalid_data;
8395
8396           for (uint64_t i = 0; i < file_name_count; i++)
8397             {
8398               printf (" %-5" PRIu64 " ", i);
8399               for (int j = 0; j < file_name_format_count; j++)
8400                 {
8401                   linep = print_form_data (dbg, enc[j].form,
8402                                            linep, lineendp, length,
8403                                            str_offsets_base);
8404                   if (j + 1 < file_name_format_count)
8405                     printf (", ");
8406                 }
8407               printf ("\n");
8408             }
8409         }
8410       else
8411         {
8412           puts (gettext (" Entry Dir   Time      Size      Name"));
8413           for (unsigned int cnt = 1; *linep != 0; ++cnt)
8414             {
8415               /* First comes the file name.  */
8416               char *fname = (char *) linep;
8417               unsigned char *endp = memchr (fname, '\0', lineendp - linep);
8418               if (unlikely (endp == NULL))
8419                 goto invalid_unit;
8420               linep = endp + 1;
8421
8422               /* Then the index.  */
8423               unsigned int diridx;
8424               if (lineendp - linep < 1)
8425                 goto invalid_unit;
8426               get_uleb128 (diridx, linep, lineendp);
8427
8428               /* Next comes the modification time.  */
8429               unsigned int mtime;
8430               if (lineendp - linep < 1)
8431                 goto invalid_unit;
8432               get_uleb128 (mtime, linep, lineendp);
8433
8434               /* Finally the length of the file.  */
8435               unsigned int fsize;
8436               if (lineendp - linep < 1)
8437                 goto invalid_unit;
8438               get_uleb128 (fsize, linep, lineendp);
8439
8440               printf (" %-5u %-5u %-9u %-9u %s\n",
8441                       cnt, diridx, mtime, fsize, fname);
8442             }
8443           /* Skip the final NUL byte.  */
8444           ++linep;
8445         }
8446
8447       puts (gettext ("\nLine number statements:"));
8448       Dwarf_Word address = 0;
8449       unsigned int op_index = 0;
8450       size_t line = 1;
8451       uint_fast8_t is_stmt = default_is_stmt;
8452
8453       /* Determine the CU this block is for.  */
8454       Dwarf_Off cuoffset;
8455       Dwarf_Off ncuoffset = 0;
8456       size_t hsize;
8457       while (dwarf_nextcu (dbg, cuoffset = ncuoffset, &ncuoffset, &hsize,
8458                            NULL, NULL, NULL) == 0)
8459         {
8460           Dwarf_Die cudie;
8461           if (dwarf_offdie (dbg, cuoffset + hsize, &cudie) == NULL)
8462             continue;
8463           Dwarf_Attribute stmt_list;
8464           if (dwarf_attr (&cudie, DW_AT_stmt_list, &stmt_list) == NULL)
8465             continue;
8466           Dwarf_Word lineoff;
8467           if (dwarf_formudata (&stmt_list, &lineoff) != 0)
8468             continue;
8469           if (lineoff == start_offset)
8470             {
8471               /* Found the CU.  */
8472               address_size = cudie.cu->address_size;
8473               break;
8474             }
8475         }
8476
8477       /* Apply the "operation advance" from a special opcode
8478          or DW_LNS_advance_pc (as per DWARF4 6.2.5.1).  */
8479       unsigned int op_addr_advance;
8480       bool show_op_index;
8481       inline void advance_pc (unsigned int op_advance)
8482       {
8483         op_addr_advance = minimum_instr_len * ((op_index + op_advance)
8484                                                / max_ops_per_instr);
8485         address += op_addr_advance;
8486         show_op_index = (op_index > 0 ||
8487                          (op_index + op_advance) % max_ops_per_instr > 0);
8488         op_index = (op_index + op_advance) % max_ops_per_instr;
8489       }
8490
8491       if (max_ops_per_instr == 0)
8492         {
8493           error (0, 0,
8494                  gettext ("invalid maximum operations per instruction is zero"));
8495           linep = lineendp;
8496           continue;
8497         }
8498
8499       while (linep < lineendp)
8500         {
8501           size_t offset = linep - (const unsigned char *) data->d_buf;
8502           unsigned int u128;
8503           int s128;
8504
8505           /* Read the opcode.  */
8506           unsigned int opcode = *linep++;
8507
8508           printf (" [%6" PRIx64 "]", (uint64_t)offset);
8509           /* Is this a special opcode?  */
8510           if (likely (opcode >= opcode_base))
8511             {
8512               if (unlikely (line_range == 0))
8513                 goto invalid_unit;
8514
8515               /* Yes.  Handling this is quite easy since the opcode value
8516                  is computed with
8517
8518                  opcode = (desired line increment - line_base)
8519                            + (line_range * address advance) + opcode_base
8520               */
8521               int line_increment = (line_base
8522                                     + (opcode - opcode_base) % line_range);
8523
8524               /* Perform the increments.  */
8525               line += line_increment;
8526               advance_pc ((opcode - opcode_base) / line_range);
8527
8528               char *a = format_dwarf_addr (dwflmod, 0, address, address);
8529               if (show_op_index)
8530                 printf (gettext ("\
8531  special opcode %u: address+%u = %s, op_index = %u, line%+d = %zu\n"),
8532                         opcode, op_addr_advance, a, op_index,
8533                         line_increment, line);
8534               else
8535                 printf (gettext ("\
8536  special opcode %u: address+%u = %s, line%+d = %zu\n"),
8537                         opcode, op_addr_advance, a, line_increment, line);
8538               free (a);
8539             }
8540           else if (opcode == 0)
8541             {
8542               /* This an extended opcode.  */
8543               if (unlikely (linep + 2 > lineendp))
8544                 goto invalid_unit;
8545
8546               /* The length.  */
8547               unsigned int len = *linep++;
8548
8549               if (unlikely (linep + len > lineendp))
8550                 goto invalid_unit;
8551
8552               /* The sub-opcode.  */
8553               opcode = *linep++;
8554
8555               printf (gettext (" extended opcode %u: "), opcode);
8556
8557               switch (opcode)
8558                 {
8559                 case DW_LNE_end_sequence:
8560                   puts (gettext (" end of sequence"));
8561
8562                   /* Reset the registers we care about.  */
8563                   address = 0;
8564                   op_index = 0;
8565                   line = 1;
8566                   is_stmt = default_is_stmt;
8567                   break;
8568
8569                 case DW_LNE_set_address:
8570                   op_index = 0;
8571                   if (unlikely ((size_t) (lineendp - linep) < address_size))
8572                     goto invalid_unit;
8573                   if (address_size == 4)
8574                     address = read_4ubyte_unaligned_inc (dbg, linep);
8575                   else
8576                     address = read_8ubyte_unaligned_inc (dbg, linep);
8577                   {
8578                     char *a = format_dwarf_addr (dwflmod, 0, address, address);
8579                     printf (gettext (" set address to %s\n"), a);
8580                     free (a);
8581                   }
8582                   break;
8583
8584                 case DW_LNE_define_file:
8585                   {
8586                     char *fname = (char *) linep;
8587                     unsigned char *endp = memchr (linep, '\0',
8588                                                   lineendp - linep);
8589                     if (unlikely (endp == NULL))
8590                       goto invalid_unit;
8591                     linep = endp + 1;
8592
8593                     unsigned int diridx;
8594                     if (lineendp - linep < 1)
8595                       goto invalid_unit;
8596                     get_uleb128 (diridx, linep, lineendp);
8597                     Dwarf_Word mtime;
8598                     if (lineendp - linep < 1)
8599                       goto invalid_unit;
8600                     get_uleb128 (mtime, linep, lineendp);
8601                     Dwarf_Word filelength;
8602                     if (lineendp - linep < 1)
8603                       goto invalid_unit;
8604                     get_uleb128 (filelength, linep, lineendp);
8605
8606                     printf (gettext ("\
8607  define new file: dir=%u, mtime=%" PRIu64 ", length=%" PRIu64 ", name=%s\n"),
8608                             diridx, (uint64_t) mtime, (uint64_t) filelength,
8609                             fname);
8610                   }
8611                   break;
8612
8613                 case DW_LNE_set_discriminator:
8614                   /* Takes one ULEB128 parameter, the discriminator.  */
8615                   if (unlikely (standard_opcode_lengths[opcode] != 1))
8616                     goto invalid_unit;
8617
8618                   get_uleb128 (u128, linep, lineendp);
8619                   printf (gettext (" set discriminator to %u\n"), u128);
8620                   break;
8621
8622                 default:
8623                   /* Unknown, ignore it.  */
8624                   puts (gettext (" unknown opcode"));
8625                   linep += len - 1;
8626                   break;
8627                 }
8628             }
8629           else if (opcode <= DW_LNS_set_isa)
8630             {
8631               /* This is a known standard opcode.  */
8632               switch (opcode)
8633                 {
8634                 case DW_LNS_copy:
8635                   /* Takes no argument.  */
8636                   puts (gettext (" copy"));
8637                   break;
8638
8639                 case DW_LNS_advance_pc:
8640                   /* Takes one uleb128 parameter which is added to the
8641                      address.  */
8642                   get_uleb128 (u128, linep, lineendp);
8643                   advance_pc (u128);
8644                   {
8645                     char *a = format_dwarf_addr (dwflmod, 0, address, address);
8646                     if (show_op_index)
8647                       printf (gettext ("\
8648  advance address by %u to %s, op_index to %u\n"),
8649                               op_addr_advance, a, op_index);
8650                     else
8651                       printf (gettext (" advance address by %u to %s\n"),
8652                               op_addr_advance, a);
8653                     free (a);
8654                   }
8655                   break;
8656
8657                 case DW_LNS_advance_line:
8658                   /* Takes one sleb128 parameter which is added to the
8659                      line.  */
8660                   get_sleb128 (s128, linep, lineendp);
8661                   line += s128;
8662                   printf (gettext ("\
8663  advance line by constant %d to %" PRId64 "\n"),
8664                           s128, (int64_t) line);
8665                   break;
8666
8667                 case DW_LNS_set_file:
8668                   /* Takes one uleb128 parameter which is stored in file.  */
8669                   get_uleb128 (u128, linep, lineendp);
8670                   printf (gettext (" set file to %" PRIu64 "\n"),
8671                           (uint64_t) u128);
8672                   break;
8673
8674                 case DW_LNS_set_column:
8675                   /* Takes one uleb128 parameter which is stored in column.  */
8676                   if (unlikely (standard_opcode_lengths[opcode] != 1))
8677                     goto invalid_unit;
8678
8679                   get_uleb128 (u128, linep, lineendp);
8680                   printf (gettext (" set column to %" PRIu64 "\n"),
8681                           (uint64_t) u128);
8682                   break;
8683
8684                 case DW_LNS_negate_stmt:
8685                   /* Takes no argument.  */
8686                   is_stmt = 1 - is_stmt;
8687                   printf (gettext (" set '%s' to %" PRIuFAST8 "\n"),
8688                           "is_stmt", is_stmt);
8689                   break;
8690
8691                 case DW_LNS_set_basic_block:
8692                   /* Takes no argument.  */
8693                   puts (gettext (" set basic block flag"));
8694                   break;
8695
8696                 case DW_LNS_const_add_pc:
8697                   /* Takes no argument.  */
8698
8699                   if (unlikely (line_range == 0))
8700                     goto invalid_unit;
8701
8702                   advance_pc ((255 - opcode_base) / line_range);
8703                   {
8704                     char *a = format_dwarf_addr (dwflmod, 0, address, address);
8705                     if (show_op_index)
8706                       printf (gettext ("\
8707  advance address by constant %u to %s, op_index to %u\n"),
8708                               op_addr_advance, a, op_index);
8709                     else
8710                       printf (gettext ("\
8711  advance address by constant %u to %s\n"),
8712                               op_addr_advance, a);
8713                     free (a);
8714                   }
8715                   break;
8716
8717                 case DW_LNS_fixed_advance_pc:
8718                   /* Takes one 16 bit parameter which is added to the
8719                      address.  */
8720                   if (unlikely (standard_opcode_lengths[opcode] != 1))
8721                     goto invalid_unit;
8722
8723                   u128 = read_2ubyte_unaligned_inc (dbg, linep);
8724                   address += u128;
8725                   op_index = 0;
8726                   {
8727                     char *a = format_dwarf_addr (dwflmod, 0, address, address);
8728                     printf (gettext ("\
8729  advance address by fixed value %u to %s\n"),
8730                             u128, a);
8731                     free (a);
8732                   }
8733                   break;
8734
8735                 case DW_LNS_set_prologue_end:
8736                   /* Takes no argument.  */
8737                   puts (gettext (" set prologue end flag"));
8738                   break;
8739
8740                 case DW_LNS_set_epilogue_begin:
8741                   /* Takes no argument.  */
8742                   puts (gettext (" set epilogue begin flag"));
8743                   break;
8744
8745                 case DW_LNS_set_isa:
8746                   /* Takes one uleb128 parameter which is stored in isa.  */
8747                   if (unlikely (standard_opcode_lengths[opcode] != 1))
8748                     goto invalid_unit;
8749
8750                   get_uleb128 (u128, linep, lineendp);
8751                   printf (gettext (" set isa to %u\n"), u128);
8752                   break;
8753                 }
8754             }
8755           else
8756             {
8757               /* This is a new opcode the generator but not we know about.
8758                  Read the parameters associated with it but then discard
8759                  everything.  Read all the parameters for this opcode.  */
8760               printf (ngettext (" unknown opcode with %" PRIu8 " parameter:",
8761                                 " unknown opcode with %" PRIu8 " parameters:",
8762                                 standard_opcode_lengths[opcode]),
8763                       standard_opcode_lengths[opcode]);
8764               for (int n = standard_opcode_lengths[opcode]; n > 0; --n)
8765                 {
8766                   get_uleb128 (u128, linep, lineendp);
8767                   if (n != standard_opcode_lengths[opcode])
8768                     putc_unlocked (',', stdout);
8769                   printf (" %u", u128);
8770                 }
8771
8772               /* Next round, ignore this opcode.  */
8773               continue;
8774             }
8775         }
8776     }
8777
8778   /* There must only be one data block.  */
8779   assert (elf_getdata (scn, data) == NULL);
8780 }
8781
8782
8783 static void
8784 print_debug_loclists_section (Dwfl_Module *dwflmod,
8785                               Ebl *ebl, GElf_Ehdr *ehdr,
8786                               Elf_Scn *scn, GElf_Shdr *shdr,
8787                               Dwarf *dbg)
8788 {
8789   printf (gettext ("\
8790 \nDWARF section [%2zu] '%s' at offset %#" PRIx64 ":\n"),
8791           elf_ndxscn (scn), section_name (ebl, ehdr, shdr),
8792           (uint64_t) shdr->sh_offset);
8793
8794   Elf_Data *data = (dbg->sectiondata[IDX_debug_loclists]
8795                     ?: elf_rawdata (scn, NULL));
8796   if (unlikely (data == NULL))
8797     {
8798       error (0, 0, gettext ("cannot get .debug_loclists content: %s"),
8799              elf_errmsg (-1));
8800       return;
8801     }
8802
8803   /* For the listptr to get the base address/CU.  */
8804   sort_listptr (&known_loclistsptr, "loclistsptr");
8805   size_t listptr_idx = 0;
8806
8807   const unsigned char *readp = data->d_buf;
8808   const unsigned char *const dataend = ((unsigned char *) data->d_buf
8809                                         + data->d_size);
8810   while (readp < dataend)
8811     {
8812       if (unlikely (readp > dataend - 4))
8813         {
8814         invalid_data:
8815           error (0, 0, gettext ("invalid data in section [%zu] '%s'"),
8816                  elf_ndxscn (scn), section_name (ebl, ehdr, shdr));
8817           return;
8818         }
8819
8820       ptrdiff_t offset = readp - (unsigned char *) data->d_buf;
8821       printf (gettext ("Table at Offset 0x%" PRIx64 ":\n\n"),
8822               (uint64_t) offset);
8823
8824       uint64_t unit_length = read_4ubyte_unaligned_inc (dbg, readp);
8825       unsigned int offset_size = 4;
8826       if (unlikely (unit_length == 0xffffffff))
8827         {
8828           if (unlikely (readp > dataend - 8))
8829             goto invalid_data;
8830
8831           unit_length = read_8ubyte_unaligned_inc (dbg, readp);
8832           offset_size = 8;
8833         }
8834       printf (gettext (" Length:         %8" PRIu64 "\n"), unit_length);
8835
8836       /* We need at least 2-bytes + 1-byte + 1-byte + 4-bytes = 8
8837          bytes to complete the header.  And this unit cannot go beyond
8838          the section data.  */
8839       if (readp > dataend - 8
8840           || unit_length < 8
8841           || unit_length > (uint64_t) (dataend - readp))
8842         goto invalid_data;
8843
8844       const unsigned char *nexthdr = readp + unit_length;
8845
8846       uint16_t version = read_2ubyte_unaligned_inc (dbg, readp);
8847       printf (gettext (" DWARF version:  %8" PRIu16 "\n"), version);
8848
8849       if (version != 5)
8850         {
8851           error (0, 0, gettext ("Unknown version"));
8852           goto next_table;
8853         }
8854
8855       uint8_t address_size = *readp++;
8856       printf (gettext (" Address size:   %8" PRIu64 "\n"),
8857               (uint64_t) address_size);
8858
8859       if (address_size != 4 && address_size != 8)
8860         {
8861           error (0, 0, gettext ("unsupported address size"));
8862           goto next_table;
8863         }
8864
8865       uint8_t segment_size = *readp++;
8866       printf (gettext (" Segment size:   %8" PRIu64 "\n"),
8867               (uint64_t) segment_size);
8868
8869       if (segment_size != 0)
8870         {
8871           error (0, 0, gettext ("unsupported segment size"));
8872           goto next_table;
8873         }
8874
8875       uint32_t offset_entry_count = read_4ubyte_unaligned_inc (dbg, readp);
8876       printf (gettext (" Offset entries: %8" PRIu64 "\n"),
8877               (uint64_t) offset_entry_count);
8878
8879       /* We need the CU that uses this unit to get the initial base address. */
8880       Dwarf_Addr cu_base = 0;
8881       struct Dwarf_CU *cu = NULL;
8882       if (listptr_cu (&known_loclistsptr, &listptr_idx,
8883                       (Dwarf_Off) offset,
8884                       (Dwarf_Off) (nexthdr - (unsigned char *) data->d_buf),
8885                       &cu_base, &cu)
8886           || split_dwarf_cu_base (dbg, &cu, &cu_base))
8887         {
8888           char *basestr = format_dwarf_addr (dwflmod, address_size,
8889                                              cu_base, cu_base);
8890           Dwarf_Die cudie;
8891           if (dwarf_cu_die (cu, &cudie,
8892                             NULL, NULL, NULL, NULL,
8893                             NULL, NULL) == NULL)
8894             printf (gettext (" Unknown CU base: %s\n"), basestr);
8895           else
8896             printf (gettext (" CU [%6" PRIx64 "] base: %s\n"),
8897                     dwarf_dieoffset (&cudie), basestr);
8898           free (basestr);
8899         }
8900       else
8901         printf (gettext (" Not associated with a CU.\n"));
8902
8903       printf ("\n");
8904
8905       const unsigned char *offset_array_start = readp;
8906       if (offset_entry_count > 0)
8907         {
8908           uint64_t needed = offset_entry_count * offset_size;
8909           if (unit_length - 8 < needed)
8910             {
8911               error (0, 0,
8912                      gettext ("too many offset entries for unit length"));
8913               goto next_table;
8914             }
8915
8916           printf (gettext ("  Offsets starting at 0x%" PRIx64 ":\n"),
8917                   (uint64_t) (offset_array_start
8918                               - (unsigned char *) data->d_buf));
8919           for (uint32_t idx = 0; idx < offset_entry_count; idx++)
8920             {
8921               printf ("   [%6" PRIu32 "] ", idx);
8922               if (offset_size == 4)
8923                 {
8924                   uint32_t off = read_4ubyte_unaligned_inc (dbg, readp);
8925                   printf ("0x%" PRIx32 "\n", off);
8926                 }
8927               else
8928                 {
8929                   uint64_t off = read_8ubyte_unaligned_inc (dbg, readp);
8930                   printf ("0x%" PRIx64 "\n", off);
8931                 }
8932             }
8933           printf ("\n");
8934         }
8935
8936       Dwarf_Addr base = cu_base;
8937       bool start_of_list = true;
8938       while (readp < nexthdr)
8939         {
8940           uint8_t kind = *readp++;
8941           uint64_t op1, op2, len;
8942           char *a1, *a2;
8943
8944           /* Skip padding.  */
8945           if (start_of_list && kind == DW_LLE_end_of_list)
8946             continue;
8947
8948           if (start_of_list)
8949             {
8950               base = cu_base;
8951               printf ("  Offset: %" PRIx64 ", Index: %" PRIx64 "\n",
8952                       (uint64_t) (readp - (unsigned char *) data->d_buf - 1),
8953                       (uint64_t) (readp - offset_array_start - 1));
8954               start_of_list = false;
8955             }
8956
8957           printf ("    %s", dwarf_loc_list_encoding_name (kind));
8958           switch (kind)
8959             {
8960             case DW_LLE_end_of_list:
8961               start_of_list = true;
8962               printf ("\n\n");
8963               break;
8964
8965             case DW_LLE_base_addressx:
8966               if ((uint64_t) (nexthdr - readp) < 1)
8967                 {
8968                 invalid_entry:
8969                   error (0, 0, gettext ("invalid loclists data"));
8970                   goto next_table;
8971                 }
8972               get_uleb128 (op1, readp, nexthdr);
8973               printf (" %" PRIx64 "\n", op1);
8974               if (! print_unresolved_addresses)
8975                 {
8976                   Dwarf_Addr addr;
8977                   if (get_indexed_addr (cu, op1, &addr) != 0)
8978                     printf ("      ???\n");
8979                   else
8980                     {
8981                       a1 = format_dwarf_addr (dwflmod, address_size,
8982                                               addr, addr);
8983                       printf ("      %s\n", a1);
8984                       free (a1);
8985                     }
8986                 }
8987               break;
8988
8989             case DW_LLE_startx_endx:
8990               if ((uint64_t) (nexthdr - readp) < 1)
8991                 goto invalid_entry;
8992               get_uleb128 (op1, readp, nexthdr);
8993               if ((uint64_t) (nexthdr - readp) < 1)
8994                 goto invalid_entry;
8995               get_uleb128 (op2, readp, nexthdr);
8996               printf (" %" PRIx64 ", %" PRIx64 "\n", op1, op2);
8997               if (! print_unresolved_addresses)
8998                 {
8999                   Dwarf_Addr addr1;
9000                   Dwarf_Addr addr2;
9001                   if (get_indexed_addr (cu, op1, &addr1) != 0
9002                       || get_indexed_addr (cu, op2, &addr2) != 0)
9003                     {
9004                       printf ("      ???..\n");
9005                       printf ("      ???\n");
9006                     }
9007                   else
9008                     {
9009                       a1 = format_dwarf_addr (dwflmod, address_size,
9010                                               addr1, addr1);
9011                       a2 = format_dwarf_addr (dwflmod, address_size,
9012                                               addr2 - 1, addr2);
9013                       printf ("      %s..\n", a1);
9014                       printf ("      %s\n", a2);
9015                       free (a1);
9016                       free (a2);
9017                     }
9018                 }
9019               if ((uint64_t) (nexthdr - readp) < 1)
9020                 goto invalid_entry;
9021               get_uleb128 (len, readp, nexthdr);
9022               if ((uint64_t) (nexthdr - readp) < len)
9023                 goto invalid_entry;
9024               print_ops (dwflmod, dbg, 8, 8, version,
9025                          address_size, offset_size, cu, len, readp);
9026               readp += len;
9027               break;
9028
9029             case DW_LLE_startx_length:
9030               if ((uint64_t) (nexthdr - readp) < 1)
9031                 goto invalid_entry;
9032               get_uleb128 (op1, readp, nexthdr);
9033               if ((uint64_t) (nexthdr - readp) < 1)
9034                 goto invalid_entry;
9035               get_uleb128 (op2, readp, nexthdr);
9036               printf (" %" PRIx64 ", %" PRIx64 "\n", op1, op2);
9037               if (! print_unresolved_addresses)
9038                 {
9039                   Dwarf_Addr addr1;
9040                   Dwarf_Addr addr2;
9041                   if (get_indexed_addr (cu, op1, &addr1) != 0)
9042                     {
9043                       printf ("      ???..\n");
9044                       printf ("      ???\n");
9045                     }
9046                   else
9047                     {
9048                       addr2 = addr1 + op2;
9049                       a1 = format_dwarf_addr (dwflmod, address_size,
9050                                               addr1, addr1);
9051                       a2 = format_dwarf_addr (dwflmod, address_size,
9052                                               addr2 - 1, addr2);
9053                       printf ("      %s..\n", a1);
9054                       printf ("      %s..\n", a2);
9055                       free (a1);
9056                       free (a2);
9057                     }
9058                 }
9059               if ((uint64_t) (nexthdr - readp) < 1)
9060                 goto invalid_entry;
9061               get_uleb128 (len, readp, nexthdr);
9062               if ((uint64_t) (nexthdr - readp) < len)
9063                 goto invalid_entry;
9064               print_ops (dwflmod, dbg, 8, 8, version,
9065                          address_size, offset_size, cu, len, readp);
9066               readp += len;
9067               break;
9068
9069             case DW_LLE_offset_pair:
9070               if ((uint64_t) (nexthdr - readp) < 1)
9071                 goto invalid_entry;
9072               get_uleb128 (op1, readp, nexthdr);
9073               if ((uint64_t) (nexthdr - readp) < 1)
9074                 goto invalid_entry;
9075               get_uleb128 (op2, readp, nexthdr);
9076               printf (" %" PRIx64 ", %" PRIx64 "\n", op1, op2);
9077               if (! print_unresolved_addresses)
9078                 {
9079                   op1 += base;
9080                   op2 += base;
9081                   a1 = format_dwarf_addr (dwflmod, address_size, op1, op1);
9082                   a2 = format_dwarf_addr (dwflmod, address_size,
9083                                           op2 - 1, op2);
9084                   printf ("      %s..\n", a1);
9085                   printf ("      %s\n", a2);
9086                   free (a1);
9087                   free (a2);
9088                 }
9089               if ((uint64_t) (nexthdr - readp) < 1)
9090                 goto invalid_entry;
9091               get_uleb128 (len, readp, nexthdr);
9092               if ((uint64_t) (nexthdr - readp) < len)
9093                 goto invalid_entry;
9094               print_ops (dwflmod, dbg, 8, 8, version,
9095                          address_size, offset_size, cu, len, readp);
9096               readp += len;
9097               break;
9098
9099             case DW_LLE_default_location:
9100               if ((uint64_t) (nexthdr - readp) < 1)
9101                 goto invalid_entry;
9102               get_uleb128 (len, readp, nexthdr);
9103               if ((uint64_t) (nexthdr - readp) < len)
9104                 goto invalid_entry;
9105               print_ops (dwflmod, dbg, 8, 8, version,
9106                          address_size, offset_size, cu, len, readp);
9107               readp += len;
9108               break;
9109
9110             case DW_LLE_base_address:
9111               if (address_size == 4)
9112                 {
9113                   if ((uint64_t) (nexthdr - readp) < 4)
9114                     goto invalid_entry;
9115                   op1 = read_4ubyte_unaligned_inc (dbg, readp);
9116                 }
9117               else
9118                 {
9119                   if ((uint64_t) (nexthdr - readp) < 8)
9120                     goto invalid_entry;
9121                   op1 = read_8ubyte_unaligned_inc (dbg, readp);
9122                 }
9123               base = op1;
9124               printf (" 0x%" PRIx64 "\n", base);
9125               if (! print_unresolved_addresses)
9126                 {
9127                   a1 = format_dwarf_addr (dwflmod, address_size, base, base);
9128                   printf ("      %s\n", a1);
9129                   free (a1);
9130                 }
9131               break;
9132
9133             case DW_LLE_start_end:
9134               if (address_size == 4)
9135                 {
9136                   if ((uint64_t) (nexthdr - readp) < 8)
9137                     goto invalid_entry;
9138                   op1 = read_4ubyte_unaligned_inc (dbg, readp);
9139                   op2 = read_4ubyte_unaligned_inc (dbg, readp);
9140                 }
9141               else
9142                 {
9143                   if ((uint64_t) (nexthdr - readp) < 16)
9144                     goto invalid_entry;
9145                   op1 = read_8ubyte_unaligned_inc (dbg, readp);
9146                   op2 = read_8ubyte_unaligned_inc (dbg, readp);
9147                 }
9148               printf (" 0x%" PRIx64 "..0x%" PRIx64 "\n", op1, op2);
9149               if (! print_unresolved_addresses)
9150                 {
9151                   a1 = format_dwarf_addr (dwflmod, address_size, op1, op1);
9152                   a2 = format_dwarf_addr (dwflmod, address_size,
9153                                           op2 - 1, op2);
9154                   printf ("      %s..\n", a1);
9155                   printf ("      %s\n", a2);
9156                   free (a1);
9157                   free (a2);
9158                 }
9159               if ((uint64_t) (nexthdr - readp) < 1)
9160                 goto invalid_entry;
9161               get_uleb128 (len, readp, nexthdr);
9162               if ((uint64_t) (nexthdr - readp) < len)
9163                 goto invalid_entry;
9164               print_ops (dwflmod, dbg, 8, 8, version,
9165                          address_size, offset_size, cu, len, readp);
9166               readp += len;
9167               break;
9168
9169             case DW_LLE_start_length:
9170               if (address_size == 4)
9171                 {
9172                   if ((uint64_t) (nexthdr - readp) < 4)
9173                     goto invalid_entry;
9174                   op1 = read_4ubyte_unaligned_inc (dbg, readp);
9175                 }
9176               else
9177                 {
9178                   if ((uint64_t) (nexthdr - readp) < 8)
9179                     goto invalid_entry;
9180                   op1 = read_8ubyte_unaligned_inc (dbg, readp);
9181                 }
9182               if ((uint64_t) (nexthdr - readp) < 1)
9183                 goto invalid_entry;
9184               get_uleb128 (op2, readp, nexthdr);
9185               printf (" 0x%" PRIx64 ", %" PRIx64 "\n", op1, op2);
9186               if (! print_unresolved_addresses)
9187                 {
9188                   a1 = format_dwarf_addr (dwflmod, address_size, op1, op1);
9189                   op2 = op1 + op2;
9190                   a2 = format_dwarf_addr (dwflmod, address_size,
9191                                           op2 - 1, op2);
9192                   printf ("      %s..\n", a1);
9193                   printf ("      %s\n", a2);
9194                   free (a1);
9195                   free (a2);
9196                 }
9197               if ((uint64_t) (nexthdr - readp) < 1)
9198                 goto invalid_entry;
9199               get_uleb128 (len, readp, nexthdr);
9200               if ((uint64_t) (nexthdr - readp) < len)
9201                 goto invalid_entry;
9202               print_ops (dwflmod, dbg, 8, 8, version,
9203                          address_size, offset_size, cu, len, readp);
9204               readp += len;
9205               break;
9206
9207             default:
9208               goto invalid_entry;
9209             }
9210         }
9211
9212     next_table:
9213       if (readp != nexthdr)
9214         {
9215           size_t padding = nexthdr - readp;
9216           printf (gettext ("   %zu padding bytes\n\n"), padding);
9217           readp = nexthdr;
9218         }
9219     }
9220 }
9221
9222
9223 static void
9224 print_debug_loc_section (Dwfl_Module *dwflmod,
9225                          Ebl *ebl, GElf_Ehdr *ehdr,
9226                          Elf_Scn *scn, GElf_Shdr *shdr, Dwarf *dbg)
9227 {
9228   Elf_Data *data = (dbg->sectiondata[IDX_debug_loc]
9229                     ?: elf_rawdata (scn, NULL));
9230
9231   if (unlikely (data == NULL))
9232     {
9233       error (0, 0, gettext ("cannot get .debug_loc content: %s"),
9234              elf_errmsg (-1));
9235       return;
9236     }
9237
9238   printf (gettext ("\
9239 \nDWARF section [%2zu] '%s' at offset %#" PRIx64 ":\n"),
9240           elf_ndxscn (scn), section_name (ebl, ehdr, shdr),
9241           (uint64_t) shdr->sh_offset);
9242
9243   sort_listptr (&known_locsptr, "loclistptr");
9244   size_t listptr_idx = 0;
9245
9246   uint_fast8_t address_size = ehdr->e_ident[EI_CLASS] == ELFCLASS32 ? 4 : 8;
9247   uint_fast8_t offset_size = 4;
9248
9249   bool first = true;
9250   Dwarf_Addr base = 0;
9251   unsigned char *readp = data->d_buf;
9252   unsigned char *const endp = (unsigned char *) data->d_buf + data->d_size;
9253   Dwarf_CU *last_cu = NULL;
9254   while (readp < endp)
9255     {
9256       ptrdiff_t offset = readp - (unsigned char *) data->d_buf;
9257       Dwarf_CU *cu = last_cu;
9258       unsigned int attr = 0;
9259
9260       if (first && skip_listptr_hole (&known_locsptr, &listptr_idx,
9261                                       &address_size, &offset_size, &base,
9262                                       &cu, offset, &readp, endp, &attr))
9263         continue;
9264
9265       if (last_cu != cu)
9266        {
9267         char *basestr = format_dwarf_addr (dwflmod, address_size,
9268                                            base, base);
9269         Dwarf_Die cudie;
9270         if (dwarf_cu_die (cu, &cudie,
9271                           NULL, NULL, NULL, NULL,
9272                           NULL, NULL) == NULL)
9273           printf (gettext ("\n Unknown CU base: %s\n"), basestr);
9274         else
9275           printf (gettext ("\n CU [%6" PRIx64 "] base: %s\n"),
9276                   dwarf_dieoffset (&cudie), basestr);
9277         free (basestr);
9278        }
9279       last_cu = cu;
9280
9281       if (attr == DW_AT_GNU_locviews)
9282         {
9283           Dwarf_Off next_off = next_listptr_offset (&known_locsptr,
9284                                                     listptr_idx);
9285           const unsigned char *locp = readp;
9286           const unsigned char *locendp;
9287           if (next_off == 0)
9288             locendp = endp;
9289           else
9290             locendp = (const unsigned char *) data->d_buf + next_off;
9291
9292           while (locp < locendp)
9293             {
9294               uint64_t v1, v2;
9295               get_uleb128 (v1, locp, locendp);
9296               if (locp >= locendp)
9297                 {
9298                   printf (gettext (" [%6tx]  <INVALID DATA>\n"), offset);
9299                   break;
9300                 }
9301               get_uleb128 (v2, locp, locendp);
9302               if (first)                /* First view pair in a list.  */
9303                 printf (" [%6tx] ", offset);
9304               else
9305                 printf ("          ");
9306               printf ("view pair %" PRId64 ", %" PRId64 "\n", v1, v2);
9307               first = false;
9308             }
9309
9310           first = true;
9311           readp = (unsigned char *) locendp;
9312           continue;
9313         }
9314
9315       /* GNU DebugFission encoded addresses as addrx.  */
9316       bool is_debugfission = ((cu != NULL
9317                                || split_dwarf_cu_base (dbg, &cu, &base))
9318                               && (cu->version < 5
9319                                   && cu->unit_type == DW_UT_split_compile));
9320       if (!is_debugfission
9321           && unlikely (data->d_size - offset < (size_t) address_size * 2))
9322         {
9323         invalid_data:
9324           printf (gettext (" [%6tx]  <INVALID DATA>\n"), offset);
9325           break;
9326         }
9327
9328       Dwarf_Addr begin;
9329       Dwarf_Addr end;
9330       bool use_base = true;
9331       if (is_debugfission)
9332         {
9333           const unsigned char *locp = readp;
9334           const unsigned char *locendp = readp + data->d_size;
9335           if (locp >= locendp)
9336             goto invalid_data;
9337
9338           Dwarf_Word idx;
9339           unsigned char code = *locp++;
9340           switch (code)
9341             {
9342             case DW_LLE_GNU_end_of_list_entry:
9343               begin = 0;
9344               end = 0;
9345               break;
9346
9347             case DW_LLE_GNU_base_address_selection_entry:
9348               if (locp >= locendp)
9349                 goto invalid_data;
9350               begin = (Dwarf_Addr) -1;
9351               get_uleb128 (idx, locp, locendp);
9352               if (get_indexed_addr (cu, idx, &end) != 0)
9353                 end = idx; /* ... */
9354               break;
9355
9356             case DW_LLE_GNU_start_end_entry:
9357               if (locp >= locendp)
9358                 goto invalid_data;
9359               get_uleb128 (idx, locp, locendp);
9360               if (get_indexed_addr (cu, idx, &begin) != 0)
9361                 end = idx; /* ... */
9362               if (locp >= locendp)
9363                 goto invalid_data;
9364               get_uleb128 (idx, locp, locendp);
9365               if (get_indexed_addr (cu, idx, &end) != 0)
9366                 end = idx; /* ... */
9367               use_base = false;
9368               break;
9369
9370             case DW_LLE_GNU_start_length_entry:
9371               if (locp >= locendp)
9372                 goto invalid_data;
9373               get_uleb128 (idx, locp, locendp);
9374               if (get_indexed_addr (cu, idx, &begin) != 0)
9375                 begin = idx; /* ... */
9376               if (locendp - locp < 4)
9377                 goto invalid_data;
9378               end = read_4ubyte_unaligned_inc (dbg, locp);
9379               end += begin;
9380               use_base = false;
9381               break;
9382
9383             default:
9384                 goto invalid_data;
9385             }
9386
9387           readp = (unsigned char *) locp;
9388         }
9389       else if (address_size == 8)
9390         {
9391           begin = read_8ubyte_unaligned_inc (dbg, readp);
9392           end = read_8ubyte_unaligned_inc (dbg, readp);
9393         }
9394       else
9395         {
9396           begin = read_4ubyte_unaligned_inc (dbg, readp);
9397           end = read_4ubyte_unaligned_inc (dbg, readp);
9398           if (begin == (Dwarf_Addr) (uint32_t) -1)
9399             begin = (Dwarf_Addr) -1l;
9400         }
9401
9402       if (begin == (Dwarf_Addr) -1l) /* Base address entry.  */
9403         {
9404           char *b = format_dwarf_addr (dwflmod, address_size, end, end);
9405           printf (gettext (" [%6tx] base address\n          %s\n"), offset, b);
9406           free (b);
9407           base = end;
9408         }
9409       else if (begin == 0 && end == 0) /* End of list entry.  */
9410         {
9411           if (first)
9412             printf (gettext (" [%6tx] empty list\n"), offset);
9413           first = true;
9414         }
9415       else
9416         {
9417           /* We have a location expression entry.  */
9418           uint_fast16_t len = read_2ubyte_unaligned_inc (dbg, readp);
9419
9420           if (first)            /* First entry in a list.  */
9421             printf (" [%6tx] ", offset);
9422           else
9423             printf ("          ");
9424
9425           printf ("range %" PRIx64 ", %" PRIx64 "\n", begin, end);
9426           if (! print_unresolved_addresses)
9427             {
9428               Dwarf_Addr dab = use_base ? base + begin : begin;
9429               Dwarf_Addr dae = use_base ? base + end : end;
9430               char *b = format_dwarf_addr (dwflmod, address_size,
9431                                            dab, dab);
9432               char *e = format_dwarf_addr (dwflmod, address_size,
9433                                            dae - 1, dae);
9434               printf ("          %s..\n", b);
9435               printf ("          %s\n", e);
9436               free (b);
9437               free (e);
9438             }
9439
9440           if (endp - readp <= (ptrdiff_t) len)
9441             {
9442               fputs (gettext ("   <INVALID DATA>\n"), stdout);
9443               break;
9444             }
9445
9446           print_ops (dwflmod, dbg, 11, 11,
9447                      cu != NULL ? cu->version : 3,
9448                      address_size, offset_size, cu, len, readp);
9449
9450           first = false;
9451           readp += len;
9452         }
9453     }
9454 }
9455
9456 struct mac_culist
9457 {
9458   Dwarf_Die die;
9459   Dwarf_Off offset;
9460   Dwarf_Files *files;
9461   struct mac_culist *next;
9462 };
9463
9464
9465 static int
9466 mac_compare (const void *p1, const void *p2)
9467 {
9468   struct mac_culist *m1 = (struct mac_culist *) p1;
9469   struct mac_culist *m2 = (struct mac_culist *) p2;
9470
9471   if (m1->offset < m2->offset)
9472     return -1;
9473   if (m1->offset > m2->offset)
9474     return 1;
9475   return 0;
9476 }
9477
9478
9479 static void
9480 print_debug_macinfo_section (Dwfl_Module *dwflmod __attribute__ ((unused)),
9481                              Ebl *ebl, GElf_Ehdr *ehdr,
9482                              Elf_Scn *scn, GElf_Shdr *shdr, Dwarf *dbg)
9483 {
9484   printf (gettext ("\
9485 \nDWARF section [%2zu] '%s' at offset %#" PRIx64 ":\n"),
9486           elf_ndxscn (scn), section_name (ebl, ehdr, shdr),
9487           (uint64_t) shdr->sh_offset);
9488   putc_unlocked ('\n', stdout);
9489
9490   /* There is no function in libdw to iterate over the raw content of
9491      the section but it is easy enough to do.  */
9492   Elf_Data *data = (dbg->sectiondata[IDX_debug_macinfo]
9493                     ?: elf_rawdata (scn, NULL));
9494   if (unlikely (data == NULL))
9495     {
9496       error (0, 0, gettext ("cannot get macro information section data: %s"),
9497              elf_errmsg (-1));
9498       return;
9499     }
9500
9501   /* Get the source file information for all CUs.  */
9502   Dwarf_Off offset;
9503   Dwarf_Off ncu = 0;
9504   size_t hsize;
9505   struct mac_culist *culist = NULL;
9506   size_t nculist = 0;
9507   while (dwarf_nextcu (dbg, offset = ncu, &ncu, &hsize, NULL, NULL, NULL) == 0)
9508     {
9509       Dwarf_Die cudie;
9510       if (dwarf_offdie (dbg, offset + hsize, &cudie) == NULL)
9511         continue;
9512
9513       Dwarf_Attribute attr;
9514       if (dwarf_attr (&cudie, DW_AT_macro_info, &attr) == NULL)
9515         continue;
9516
9517       Dwarf_Word macoff;
9518       if (dwarf_formudata (&attr, &macoff) != 0)
9519         continue;
9520
9521       struct mac_culist *newp = (struct mac_culist *) alloca (sizeof (*newp));
9522       newp->die = cudie;
9523       newp->offset = macoff;
9524       newp->files = NULL;
9525       newp->next = culist;
9526       culist = newp;
9527       ++nculist;
9528     }
9529
9530   /* Convert the list into an array for easier consumption.  */
9531   struct mac_culist *cus = (struct mac_culist *) alloca ((nculist + 1)
9532                                                          * sizeof (*cus));
9533   /* Add sentinel.  */
9534   cus[nculist].offset = data->d_size;
9535   cus[nculist].files = (Dwarf_Files *) -1l;
9536   if (nculist > 0)
9537     {
9538       for (size_t cnt = nculist - 1; culist != NULL; --cnt)
9539         {
9540           assert (cnt < nculist);
9541           cus[cnt] = *culist;
9542           culist = culist->next;
9543         }
9544
9545       /* Sort the array according to the offset in the .debug_macinfo
9546          section.  Note we keep the sentinel at the end.  */
9547       qsort (cus, nculist, sizeof (*cus), mac_compare);
9548     }
9549
9550   const unsigned char *readp = (const unsigned char *) data->d_buf;
9551   const unsigned char *readendp = readp + data->d_size;
9552   int level = 1;
9553
9554   while (readp < readendp)
9555     {
9556       unsigned int opcode = *readp++;
9557       unsigned int u128;
9558       unsigned int u128_2;
9559       const unsigned char *endp;
9560
9561       switch (opcode)
9562         {
9563         case DW_MACINFO_define:
9564         case DW_MACINFO_undef:
9565         case DW_MACINFO_vendor_ext:
9566           /*  For the first two opcodes the parameters are
9567                 line, string
9568               For the latter
9569                 number, string.
9570               We can treat these cases together.  */
9571           get_uleb128 (u128, readp, readendp);
9572
9573           endp = memchr (readp, '\0', readendp - readp);
9574           if (unlikely (endp == NULL))
9575             {
9576               printf (gettext ("\
9577 %*s*** non-terminated string at end of section"),
9578                       level, "");
9579               return;
9580             }
9581
9582           if (opcode == DW_MACINFO_define)
9583             printf ("%*s#define %s, line %u\n",
9584                     level, "", (char *) readp, u128);
9585           else if (opcode == DW_MACINFO_undef)
9586             printf ("%*s#undef %s, line %u\n",
9587                     level, "", (char *) readp, u128);
9588           else
9589             printf (" #vendor-ext %s, number %u\n", (char *) readp, u128);
9590
9591           readp = endp + 1;
9592           break;
9593
9594         case DW_MACINFO_start_file:
9595           /* The two parameters are line and file index, in this order.  */
9596           get_uleb128 (u128, readp, readendp);
9597           if (readendp - readp < 1)
9598             {
9599               printf (gettext ("\
9600 %*s*** missing DW_MACINFO_start_file argument at end of section"),
9601                       level, "");
9602               return;
9603             }
9604           get_uleb128 (u128_2, readp, readendp);
9605
9606           /* Find the CU DIE for this file.  */
9607           size_t macoff = readp - (const unsigned char *) data->d_buf;
9608           const char *fname = "???";
9609           if (macoff >= cus[0].offset)
9610             {
9611               while (macoff >= cus[1].offset && cus[1].offset != data->d_size)
9612                 ++cus;
9613
9614               if (cus[0].files == NULL
9615                 && dwarf_getsrcfiles (&cus[0].die, &cus[0].files, NULL) != 0)
9616                 cus[0].files = (Dwarf_Files *) -1l;
9617
9618               if (cus[0].files != (Dwarf_Files *) -1l)
9619                 fname = (dwarf_filesrc (cus[0].files, u128_2, NULL, NULL)
9620                          ?: "???");
9621             }
9622
9623           printf ("%*sstart_file %u, [%u] %s\n",
9624                   level, "", u128, u128_2, fname);
9625           ++level;
9626           break;
9627
9628         case DW_MACINFO_end_file:
9629           --level;
9630           printf ("%*send_file\n", level, "");
9631           /* Nothing more to do.  */
9632           break;
9633
9634         default:
9635           // XXX gcc seems to generate files with a trailing zero.
9636           if (unlikely (opcode != 0 || readp != readendp))
9637             printf ("%*s*** invalid opcode %u\n", level, "", opcode);
9638           break;
9639         }
9640     }
9641 }
9642
9643
9644 static void
9645 print_debug_macro_section (Dwfl_Module *dwflmod __attribute__ ((unused)),
9646                            Ebl *ebl, GElf_Ehdr *ehdr,
9647                            Elf_Scn *scn, GElf_Shdr *shdr, Dwarf *dbg)
9648 {
9649   printf (gettext ("\
9650 \nDWARF section [%2zu] '%s' at offset %#" PRIx64 ":\n"),
9651           elf_ndxscn (scn), section_name (ebl, ehdr, shdr),
9652           (uint64_t) shdr->sh_offset);
9653   putc_unlocked ('\n', stdout);
9654
9655   Elf_Data *data = (dbg->sectiondata[IDX_debug_macro]
9656                     ?: elf_rawdata (scn, NULL));
9657   if (unlikely (data == NULL))
9658     {
9659       error (0, 0, gettext ("cannot get macro information section data: %s"),
9660              elf_errmsg (-1));
9661       return;
9662     }
9663
9664   /* Get the source file information for all CUs.  Uses same
9665      datastructure as macinfo.  But uses offset field to directly
9666      match .debug_line offset.  And just stored in a list.  */
9667   Dwarf_Off offset;
9668   Dwarf_Off ncu = 0;
9669   size_t hsize;
9670   struct mac_culist *culist = NULL;
9671   size_t nculist = 0;
9672   while (dwarf_nextcu (dbg, offset = ncu, &ncu, &hsize, NULL, NULL, NULL) == 0)
9673     {
9674       Dwarf_Die cudie;
9675       if (dwarf_offdie (dbg, offset + hsize, &cudie) == NULL)
9676         continue;
9677
9678       Dwarf_Attribute attr;
9679       if (dwarf_attr (&cudie, DW_AT_stmt_list, &attr) == NULL)
9680         continue;
9681
9682       Dwarf_Word lineoff;
9683       if (dwarf_formudata (&attr, &lineoff) != 0)
9684         continue;
9685
9686       struct mac_culist *newp = (struct mac_culist *) alloca (sizeof (*newp));
9687       newp->die = cudie;
9688       newp->offset = lineoff;
9689       newp->files = NULL;
9690       newp->next = culist;
9691       culist = newp;
9692       ++nculist;
9693     }
9694
9695   const unsigned char *readp = (const unsigned char *) data->d_buf;
9696   const unsigned char *readendp = readp + data->d_size;
9697
9698   while (readp < readendp)
9699     {
9700       printf (gettext (" Offset:             0x%" PRIx64 "\n"),
9701               (uint64_t) (readp - (const unsigned char *) data->d_buf));
9702
9703       // Header, 2 byte version, 1 byte flag, optional .debug_line offset,
9704       // optional vendor extension macro entry table.
9705       if (readp + 2 > readendp)
9706         {
9707         invalid_data:
9708           error (0, 0, gettext ("invalid data"));
9709           return;
9710         }
9711       const uint16_t vers = read_2ubyte_unaligned_inc (dbg, readp);
9712       printf (gettext (" Version:            %" PRIu16 "\n"), vers);
9713
9714       // Version 4 is the GNU extension for DWARF4.  DWARF5 will use version
9715       // 5 when it gets standardized.
9716       if (vers != 4 && vers != 5)
9717         {
9718           printf (gettext ("  unknown version, cannot parse section\n"));
9719           return;
9720         }
9721
9722       if (readp + 1 > readendp)
9723         goto invalid_data;
9724       const unsigned char flag = *readp++;
9725       printf (gettext (" Flag:               0x%" PRIx8 "\n"), flag);
9726
9727       unsigned int offset_len = (flag & 0x01) ? 8 : 4;
9728       printf (gettext (" Offset length:      %" PRIu8 "\n"), offset_len);
9729       Dwarf_Off line_offset = -1;
9730       if (flag & 0x02)
9731         {
9732           if (offset_len == 8)
9733             line_offset = read_8ubyte_unaligned_inc (dbg, readp);
9734           else
9735             line_offset = read_4ubyte_unaligned_inc (dbg, readp);
9736           printf (gettext (" .debug_line offset: 0x%" PRIx64 "\n"),
9737                   line_offset);
9738         }
9739
9740       struct mac_culist *cu = NULL;
9741       if (line_offset != (Dwarf_Off) -1)
9742         {
9743           cu = culist;
9744           while (cu != NULL && line_offset != cu->offset)
9745             cu = cu->next;
9746         }
9747
9748       Dwarf_Off str_offsets_base = str_offsets_base_off (dbg, (cu != NULL
9749                                                                ? cu->die.cu
9750                                                                : NULL));
9751
9752       const unsigned char *vendor[DW_MACRO_hi_user - DW_MACRO_lo_user];
9753       memset (vendor, 0, sizeof vendor);
9754       if (flag & 0x04)
9755         {
9756           // 1 byte length, for each item, 1 byte opcode, uleb128 number
9757           // of arguments, for each argument 1 byte form code.
9758           if (readp + 1 > readendp)
9759             goto invalid_data;
9760           unsigned int tlen = *readp++;
9761           printf (gettext ("  extension opcode table, %" PRIu8 " items:\n"),
9762                   tlen);
9763           for (unsigned int i = 0; i < tlen; i++)
9764             {
9765               if (readp + 1 > readendp)
9766                 goto invalid_data;
9767               unsigned int opcode = *readp++;
9768               printf (gettext ("    [%" PRIx8 "]"), opcode);
9769               if (opcode < DW_MACRO_lo_user
9770                   || opcode > DW_MACRO_hi_user)
9771                 goto invalid_data;
9772               // Record the start of description for this vendor opcode.
9773               // uleb128 nr args, 1 byte per arg form.
9774               vendor[opcode - DW_MACRO_lo_user] = readp;
9775               if (readp + 1 > readendp)
9776                 goto invalid_data;
9777               unsigned int args = *readp++;
9778               if (args > 0)
9779                 {
9780                   printf (gettext (" %" PRIu8 " arguments:"), args);
9781                   while (args > 0)
9782                     {
9783                       if (readp + 1 > readendp)
9784                         goto invalid_data;
9785                       unsigned int form = *readp++;
9786                       printf (" %s", dwarf_form_name (form));
9787                       if (! libdw_valid_user_form (form))
9788                         goto invalid_data;
9789                       args--;
9790                       if (args > 0)
9791                         putchar_unlocked (',');
9792                     }
9793                 }
9794               else
9795                 printf (gettext (" no arguments."));
9796               putchar_unlocked ('\n');
9797             }
9798         }
9799       putchar_unlocked ('\n');
9800
9801       int level = 1;
9802       if (readp + 1 > readendp)
9803         goto invalid_data;
9804       unsigned int opcode = *readp++;
9805       while (opcode != 0)
9806         {
9807           unsigned int u128;
9808           unsigned int u128_2;
9809           const unsigned char *endp;
9810           uint64_t off;
9811
9812           switch (opcode)
9813             {
9814             case DW_MACRO_start_file:
9815               get_uleb128 (u128, readp, readendp);
9816               if (readp >= readendp)
9817                 goto invalid_data;
9818               get_uleb128 (u128_2, readp, readendp);
9819
9820               /* Find the CU DIE that matches this line offset.  */
9821               const char *fname = "???";
9822               if (cu != NULL)
9823                 {
9824                   if (cu->files == NULL
9825                       && dwarf_getsrcfiles (&cu->die, &cu->files,
9826                                             NULL) != 0)
9827                     cu->files = (Dwarf_Files *) -1l;
9828
9829                   if (cu->files != (Dwarf_Files *) -1l)
9830                     fname = (dwarf_filesrc (cu->files, u128_2,
9831                                             NULL, NULL) ?: "???");
9832                 }
9833               printf ("%*sstart_file %u, [%u] %s\n",
9834                       level, "", u128, u128_2, fname);
9835               ++level;
9836               break;
9837
9838             case DW_MACRO_end_file:
9839               --level;
9840               printf ("%*send_file\n", level, "");
9841               break;
9842
9843             case DW_MACRO_define:
9844               get_uleb128 (u128, readp, readendp);
9845               endp = memchr (readp, '\0', readendp - readp);
9846               if (endp == NULL)
9847                 goto invalid_data;
9848               printf ("%*s#define %s, line %u\n",
9849                       level, "", readp, u128);
9850               readp = endp + 1;
9851               break;
9852
9853             case DW_MACRO_undef:
9854               get_uleb128 (u128, readp, readendp);
9855               endp = memchr (readp, '\0', readendp - readp);
9856               if (endp == NULL)
9857                 goto invalid_data;
9858               printf ("%*s#undef %s, line %u\n",
9859                       level, "", readp, u128);
9860               readp = endp + 1;
9861               break;
9862
9863             case DW_MACRO_define_strp:
9864               get_uleb128 (u128, readp, readendp);
9865               if (readp + offset_len > readendp)
9866                 goto invalid_data;
9867               if (offset_len == 8)
9868                 off = read_8ubyte_unaligned_inc (dbg, readp);
9869               else
9870                 off = read_4ubyte_unaligned_inc (dbg, readp);
9871               printf ("%*s#define %s, line %u (indirect)\n",
9872                       level, "", dwarf_getstring (dbg, off, NULL), u128);
9873               break;
9874
9875             case DW_MACRO_undef_strp:
9876               get_uleb128 (u128, readp, readendp);
9877               if (readp + offset_len > readendp)
9878                 goto invalid_data;
9879               if (offset_len == 8)
9880                 off = read_8ubyte_unaligned_inc (dbg, readp);
9881               else
9882                 off = read_4ubyte_unaligned_inc (dbg, readp);
9883               printf ("%*s#undef %s, line %u (indirect)\n",
9884                       level, "", dwarf_getstring (dbg, off, NULL), u128);
9885               break;
9886
9887             case DW_MACRO_import:
9888               if (readp + offset_len > readendp)
9889                 goto invalid_data;
9890               if (offset_len == 8)
9891                 off = read_8ubyte_unaligned_inc (dbg, readp);
9892               else
9893                 off = read_4ubyte_unaligned_inc (dbg, readp);
9894               printf ("%*s#include offset 0x%" PRIx64 "\n",
9895                       level, "", off);
9896               break;
9897
9898             case DW_MACRO_define_sup:
9899               get_uleb128 (u128, readp, readendp);
9900               if (readp + offset_len > readendp)
9901                 goto invalid_data;
9902               printf ("%*s#define ", level, "");
9903               readp =  print_form_data (dbg, DW_FORM_strp_sup,
9904                                         readp, readendp, offset_len,
9905                                         str_offsets_base);
9906               printf (", line %u (sup)\n", u128);
9907               break;
9908
9909             case DW_MACRO_undef_sup:
9910               get_uleb128 (u128, readp, readendp);
9911               if (readp + offset_len > readendp)
9912                 goto invalid_data;
9913               printf ("%*s#undef ", level, "");
9914               readp =  print_form_data (dbg, DW_FORM_strp_sup,
9915                                         readp, readendp, offset_len,
9916                                         str_offsets_base);
9917               printf (", line %u (sup)\n", u128);
9918               break;
9919
9920             case DW_MACRO_import_sup:
9921               if (readp + offset_len > readendp)
9922                 goto invalid_data;
9923               if (offset_len == 8)
9924                 off = read_8ubyte_unaligned_inc (dbg, readp);
9925               else
9926                 off = read_4ubyte_unaligned_inc (dbg, readp);
9927               // XXX Needs support for reading from supplementary object file.
9928               printf ("%*s#include offset 0x%" PRIx64 " (sup)\n",
9929                       level, "", off);
9930               break;
9931
9932             case DW_MACRO_define_strx:
9933               get_uleb128 (u128, readp, readendp);
9934               if (readp + offset_len > readendp)
9935                 goto invalid_data;
9936               printf ("%*s#define ", level, "");
9937               readp =  print_form_data (dbg, DW_FORM_strx,
9938                                         readp, readendp, offset_len,
9939                                         str_offsets_base);
9940               printf (", line %u (strx)\n", u128);
9941               break;
9942
9943             case DW_MACRO_undef_strx:
9944               get_uleb128 (u128, readp, readendp);
9945               if (readp + offset_len > readendp)
9946                 goto invalid_data;
9947               printf ("%*s#undef ", level, "");
9948               readp =  print_form_data (dbg, DW_FORM_strx,
9949                                         readp, readendp, offset_len,
9950                                         str_offsets_base);
9951               printf (", line %u (strx)\n", u128);
9952               break;
9953
9954             default:
9955               printf ("%*svendor opcode 0x%" PRIx8, level, "", opcode);
9956               if (opcode < DW_MACRO_lo_user
9957                   || opcode > DW_MACRO_lo_user
9958                   || vendor[opcode - DW_MACRO_lo_user] == NULL)
9959                 goto invalid_data;
9960
9961               const unsigned char *op_desc;
9962               op_desc = vendor[opcode - DW_MACRO_lo_user];
9963
9964               // Just skip the arguments, we cannot really interpret them,
9965               // but print as much as we can.
9966               unsigned int args = *op_desc++;
9967               while (args > 0 && readp < readendp)
9968                 {
9969                   unsigned int form = *op_desc++;
9970                   readp = print_form_data (dbg, form, readp, readendp,
9971                                            offset_len, str_offsets_base);
9972                   args--;
9973                   if (args > 0)
9974                     printf (", ");
9975                 }
9976               putchar_unlocked ('\n');
9977             }
9978
9979           if (readp + 1 > readendp)
9980             goto invalid_data;
9981           opcode = *readp++;
9982           if (opcode == 0)
9983             putchar_unlocked ('\n');
9984         }
9985     }
9986 }
9987
9988
9989 /* Callback for printing global names.  */
9990 static int
9991 print_pubnames (Dwarf *dbg __attribute__ ((unused)), Dwarf_Global *global,
9992                 void *arg)
9993 {
9994   int *np = (int *) arg;
9995
9996   printf (gettext (" [%5d] DIE offset: %6" PRId64
9997                    ", CU DIE offset: %6" PRId64 ", name: %s\n"),
9998           (*np)++, global->die_offset, global->cu_offset, global->name);
9999
10000   return 0;
10001 }
10002
10003
10004 /* Print the known exported symbols in the DWARF section '.debug_pubnames'.  */
10005 static void
10006 print_debug_pubnames_section (Dwfl_Module *dwflmod __attribute__ ((unused)),
10007                               Ebl *ebl, GElf_Ehdr *ehdr,
10008                               Elf_Scn *scn, GElf_Shdr *shdr, Dwarf *dbg)
10009 {
10010   printf (gettext ("\nDWARF section [%2zu] '%s' at offset %#" PRIx64 ":\n"),
10011           elf_ndxscn (scn), section_name (ebl, ehdr, shdr),
10012           (uint64_t) shdr->sh_offset);
10013
10014   int n = 0;
10015   (void) dwarf_getpubnames (dbg, print_pubnames, &n, 0);
10016 }
10017
10018 /* Print the content of the DWARF string section '.debug_str'.  */
10019 static void
10020 print_debug_str_section (Dwfl_Module *dwflmod __attribute__ ((unused)),
10021                          Ebl *ebl, GElf_Ehdr *ehdr,
10022                          Elf_Scn *scn, GElf_Shdr *shdr,
10023                          Dwarf *dbg __attribute__ ((unused)))
10024 {
10025   Elf_Data *data = elf_rawdata (scn, NULL);
10026   const size_t sh_size = data ? data->d_size : 0;
10027
10028   /* Compute floor(log16(shdr->sh_size)).  */
10029   GElf_Addr tmp = sh_size;
10030   int digits = 1;
10031   while (tmp >= 16)
10032     {
10033       ++digits;
10034       tmp >>= 4;
10035     }
10036   digits = MAX (4, digits);
10037
10038   printf (gettext ("\nDWARF section [%2zu] '%s' at offset %#" PRIx64 ":\n"
10039                    " %*s  String\n"),
10040           elf_ndxscn (scn),
10041           section_name (ebl, ehdr, shdr), (uint64_t) shdr->sh_offset,
10042           /* TRANS: the debugstr| prefix makes the string unique.  */
10043           digits + 2, sgettext ("debugstr|Offset"));
10044
10045   Dwarf_Off offset = 0;
10046   while (offset < sh_size)
10047     {
10048       size_t len;
10049       const char *str = (const char *) data->d_buf + offset;
10050       const char *endp = memchr (str, '\0', sh_size - offset);
10051       if (unlikely (endp == NULL))
10052         {
10053           printf (gettext (" *** error, missing string terminator\n"));
10054           break;
10055         }
10056
10057       printf (" [%*" PRIx64 "]  \"%s\"\n", digits, (uint64_t) offset, str);
10058       len = endp - str;
10059       offset += len + 1;
10060     }
10061 }
10062
10063 static void
10064 print_debug_str_offsets_section (Dwfl_Module *dwflmod __attribute__ ((unused)),
10065                                  Ebl *ebl, GElf_Ehdr *ehdr,
10066                                  Elf_Scn *scn, GElf_Shdr *shdr, Dwarf *dbg)
10067 {
10068   printf (gettext ("\
10069 \nDWARF section [%2zu] '%s' at offset %#" PRIx64 ":\n"),
10070           elf_ndxscn (scn), section_name (ebl, ehdr, shdr),
10071           (uint64_t) shdr->sh_offset);
10072
10073   if (shdr->sh_size == 0)
10074     return;
10075
10076   /* We like to get the section from libdw to make sure they are relocated.  */
10077   Elf_Data *data = (dbg->sectiondata[IDX_debug_str_offsets]
10078                     ?: elf_rawdata (scn, NULL));
10079   if (unlikely (data == NULL))
10080     {
10081       error (0, 0, gettext ("cannot get .debug_str_offsets section data: %s"),
10082              elf_errmsg (-1));
10083       return;
10084     }
10085
10086   size_t idx = 0;
10087   sort_listptr (&known_stroffbases, "str_offsets");
10088
10089   const unsigned char *start = (const unsigned char *) data->d_buf;
10090   const unsigned char *readp = start;
10091   const unsigned char *readendp = ((const unsigned char *) data->d_buf
10092                                    + data->d_size);
10093
10094   while (readp < readendp)
10095     {
10096       /* Most string offset tables will have a header.  For split
10097          dwarf unit GNU DebugFission didn't add one.  But they were
10098          also only defined for split units (main or skeleton units
10099          didn't have indirect strings).  So if we don't have a
10100          DW_AT_str_offsets_base at all and this is offset zero, then
10101          just start printing offsets immediately, if this is a .dwo
10102          section.  */
10103       Dwarf_Off off = (Dwarf_Off) (readp
10104                                    - (const unsigned char *) data->d_buf);
10105
10106       printf ("Table at offset %" PRIx64 " ", off);
10107
10108       struct listptr *listptr = get_listptr (&known_stroffbases, idx++);
10109       const unsigned char *next_unitp = readendp;
10110       uint8_t offset_size;
10111       bool has_header;
10112       if (listptr == NULL)
10113         {
10114           /* This can happen for .dwo files.  There is only an header
10115              in the case this is a version 5 split DWARF file.  */
10116           Dwarf_CU *cu;
10117           uint8_t unit_type;
10118           if (dwarf_get_units (dbg, NULL, &cu, NULL, &unit_type,
10119                                NULL, NULL) != 0)
10120             {
10121               error (0, 0, "Warning: Cannot find any DWARF unit.");
10122               /* Just guess some values.  */
10123               has_header = false;
10124               offset_size = 4;
10125             }
10126           else if (off == 0
10127                    && (unit_type == DW_UT_split_type
10128                        || unit_type == DW_UT_split_compile))
10129             {
10130               has_header = cu->version > 4;
10131               offset_size = cu->offset_size;
10132             }
10133           else
10134             {
10135               error (0, 0,
10136                      "Warning: No CU references .debug_str_offsets after %"
10137                      PRIx64, off);
10138               has_header = cu->version > 4;
10139               offset_size = cu->offset_size;
10140             }
10141           printf ("\n");
10142         }
10143       else
10144         {
10145           /* This must be DWARF5, since GNU DebugFission didn't define
10146              DW_AT_str_offsets_base.  */
10147           has_header = true;
10148
10149           Dwarf_Die cudie;
10150           if (dwarf_cu_die (listptr->cu, &cudie,
10151                             NULL, NULL, NULL, NULL,
10152                             NULL, NULL) == NULL)
10153             printf ("Unknown CU (%s):\n", dwarf_errmsg (-1));
10154           else
10155             printf ("for CU [%6" PRIx64 "]:\n", dwarf_dieoffset (&cudie));
10156         }
10157
10158       if (has_header)
10159         {
10160           uint64_t unit_length;
10161           uint16_t version;
10162           uint16_t padding;
10163
10164           unit_length = read_4ubyte_unaligned_inc (dbg, readp);
10165           if (unlikely (unit_length == 0xffffffff))
10166             {
10167               if (unlikely (readp > readendp - 8))
10168                 {
10169                 invalid_data:
10170                   error (0, 0, "Invalid data");
10171                   return;
10172                 }
10173               unit_length = read_8ubyte_unaligned_inc (dbg, readp);
10174               offset_size = 8;
10175             }
10176           else
10177             offset_size = 4;
10178
10179           printf ("\n");
10180           printf (gettext (" Length:        %8" PRIu64 "\n"),
10181                   unit_length);
10182           printf (gettext (" Offset size:   %8" PRIu8 "\n"),
10183                   offset_size);
10184
10185           /* We need at least 2-bytes (version) + 2-bytes (padding) =
10186              4 bytes to complete the header.  And this unit cannot go
10187              beyond the section data.  */
10188           if (readp > readendp - 4
10189               || unit_length < 4
10190               || unit_length > (uint64_t) (readendp - readp))
10191             goto invalid_data;
10192
10193           next_unitp = readp + unit_length;
10194
10195           version = read_2ubyte_unaligned_inc (dbg, readp);
10196           printf (gettext (" DWARF version: %8" PRIu16 "\n"), version);
10197
10198           if (version != 5)
10199             {
10200               error (0, 0, gettext ("Unknown version"));
10201               goto next_unit;
10202             }
10203
10204           padding = read_2ubyte_unaligned_inc (dbg, readp);
10205           printf (gettext (" Padding:       %8" PRIx16 "\n"), padding);
10206
10207           if (listptr != NULL
10208               && listptr->offset != (Dwarf_Off) (readp - start))
10209             {
10210               error (0, 0, "String offsets index doesn't start after header");
10211               goto next_unit;
10212             }
10213
10214           printf ("\n");
10215         }
10216
10217       int digits = 1;
10218       size_t offsets = (next_unitp - readp) / offset_size;
10219       while (offsets >= 10)
10220         {
10221           ++digits;
10222           offsets /= 10;
10223         }
10224
10225       unsigned int index = 0;
10226       size_t index_offset =  readp - (const unsigned char *) data->d_buf;
10227       printf (" Offsets start at 0x%zx:\n", index_offset);
10228       while (readp <= next_unitp - offset_size)
10229         {
10230           Dwarf_Word offset;
10231           if (offset_size == 4)
10232             offset = read_4ubyte_unaligned_inc (dbg, readp);
10233           else
10234             offset = read_8ubyte_unaligned_inc (dbg, readp);
10235           const char *str = dwarf_getstring (dbg, offset, NULL);
10236           printf (" [%*u] [%*" PRIx64 "]  \"%s\"\n",
10237                   digits, index++, (int) offset_size * 2, offset, str ?: "???");
10238         }
10239       printf ("\n");
10240
10241       if (readp != next_unitp)
10242         error (0, 0, "extra %zd bytes at end of unit",
10243                (size_t) (next_unitp - readp));
10244
10245     next_unit:
10246       readp = next_unitp;
10247     }
10248 }
10249
10250
10251 /* Print the content of the call frame search table section
10252    '.eh_frame_hdr'.  */
10253 static void
10254 print_debug_frame_hdr_section (Dwfl_Module *dwflmod __attribute__ ((unused)),
10255                                Ebl *ebl __attribute__ ((unused)),
10256                                GElf_Ehdr *ehdr __attribute__ ((unused)),
10257                                Elf_Scn *scn, GElf_Shdr *shdr, Dwarf *dbg)
10258 {
10259   printf (gettext ("\
10260 \nCall frame search table section [%2zu] '.eh_frame_hdr':\n"),
10261           elf_ndxscn (scn));
10262
10263   Elf_Data *data = elf_rawdata (scn, NULL);
10264
10265   if (unlikely (data == NULL))
10266     {
10267       error (0, 0, gettext ("cannot get %s content: %s"),
10268              ".eh_frame_hdr", elf_errmsg (-1));
10269       return;
10270     }
10271
10272   const unsigned char *readp = data->d_buf;
10273   const unsigned char *const dataend = ((unsigned char *) data->d_buf
10274                                         + data->d_size);
10275
10276   if (unlikely (readp + 4 > dataend))
10277     {
10278     invalid_data:
10279       error (0, 0, gettext ("invalid data"));
10280       return;
10281     }
10282
10283   unsigned int version = *readp++;
10284   unsigned int eh_frame_ptr_enc = *readp++;
10285   unsigned int fde_count_enc = *readp++;
10286   unsigned int table_enc = *readp++;
10287
10288   printf (" version:          %u\n"
10289           " eh_frame_ptr_enc: %#x ",
10290           version, eh_frame_ptr_enc);
10291   print_encoding_base ("", eh_frame_ptr_enc);
10292   printf (" fde_count_enc:    %#x ", fde_count_enc);
10293   print_encoding_base ("", fde_count_enc);
10294   printf (" table_enc:        %#x ", table_enc);
10295   print_encoding_base ("", table_enc);
10296
10297   uint64_t eh_frame_ptr = 0;
10298   if (eh_frame_ptr_enc != DW_EH_PE_omit)
10299     {
10300       readp = read_encoded (eh_frame_ptr_enc, readp, dataend, &eh_frame_ptr,
10301                             dbg);
10302       if (unlikely (readp == NULL))
10303         goto invalid_data;
10304
10305       printf (" eh_frame_ptr:     %#" PRIx64, eh_frame_ptr);
10306       if ((eh_frame_ptr_enc & 0x70) == DW_EH_PE_pcrel)
10307         printf (" (offset: %#" PRIx64 ")",
10308                 /* +4 because of the 4 byte header of the section.  */
10309                 (uint64_t) shdr->sh_offset + 4 + eh_frame_ptr);
10310
10311       putchar_unlocked ('\n');
10312     }
10313
10314   uint64_t fde_count = 0;
10315   if (fde_count_enc != DW_EH_PE_omit)
10316     {
10317       readp = read_encoded (fde_count_enc, readp, dataend, &fde_count, dbg);
10318       if (unlikely (readp == NULL))
10319         goto invalid_data;
10320
10321       printf (" fde_count:        %" PRIu64 "\n", fde_count);
10322     }
10323
10324   if (fde_count == 0 || table_enc == DW_EH_PE_omit)
10325     return;
10326
10327   puts (" Table:");
10328
10329   /* Optimize for the most common case.  */
10330   if (table_enc == (DW_EH_PE_datarel | DW_EH_PE_sdata4))
10331     while (fde_count > 0 && readp + 8 <= dataend)
10332       {
10333         int32_t initial_location = read_4sbyte_unaligned_inc (dbg, readp);
10334         uint64_t initial_offset = ((uint64_t) shdr->sh_offset
10335                                    + (int64_t) initial_location);
10336         int32_t address = read_4sbyte_unaligned_inc (dbg, readp);
10337         // XXX Possibly print symbol name or section offset for initial_offset
10338         printf ("  %#" PRIx32 " (offset: %#6" PRIx64 ") -> %#" PRIx32
10339                 " fde=[%6" PRIx64 "]\n",
10340                 initial_location, initial_offset,
10341                 address, address - (eh_frame_ptr + 4));
10342       }
10343   else
10344     while (0 && readp < dataend)
10345       {
10346
10347       }
10348 }
10349
10350
10351 /* Print the content of the exception handling table section
10352    '.eh_frame_hdr'.  */
10353 static void
10354 print_debug_exception_table (Dwfl_Module *dwflmod __attribute__ ((unused)),
10355                              Ebl *ebl __attribute__ ((unused)),
10356                              GElf_Ehdr *ehdr __attribute__ ((unused)),
10357                              Elf_Scn *scn,
10358                              GElf_Shdr *shdr __attribute__ ((unused)),
10359                              Dwarf *dbg __attribute__ ((unused)))
10360 {
10361   printf (gettext ("\
10362 \nException handling table section [%2zu] '.gcc_except_table':\n"),
10363           elf_ndxscn (scn));
10364
10365   Elf_Data *data = elf_rawdata (scn, NULL);
10366
10367   if (unlikely (data == NULL))
10368     {
10369       error (0, 0, gettext ("cannot get %s content: %s"),
10370              ".gcc_except_table", elf_errmsg (-1));
10371       return;
10372     }
10373
10374   const unsigned char *readp = data->d_buf;
10375   const unsigned char *const dataend = readp + data->d_size;
10376
10377   if (unlikely (readp + 1 > dataend))
10378     {
10379     invalid_data:
10380       error (0, 0, gettext ("invalid data"));
10381       return;
10382     }
10383   unsigned int lpstart_encoding = *readp++;
10384   printf (gettext (" LPStart encoding:    %#x "), lpstart_encoding);
10385   print_encoding_base ("", lpstart_encoding);
10386   if (lpstart_encoding != DW_EH_PE_omit)
10387     {
10388       uint64_t lpstart;
10389       readp = read_encoded (lpstart_encoding, readp, dataend, &lpstart, dbg);
10390       printf (" LPStart:             %#" PRIx64 "\n", lpstart);
10391     }
10392
10393   if (unlikely (readp + 1 > dataend))
10394     goto invalid_data;
10395   unsigned int ttype_encoding = *readp++;
10396   printf (gettext (" TType encoding:      %#x "), ttype_encoding);
10397   print_encoding_base ("", ttype_encoding);
10398   const unsigned char *ttype_base = NULL;
10399   if (ttype_encoding != DW_EH_PE_omit)
10400     {
10401       unsigned int ttype_base_offset;
10402       get_uleb128 (ttype_base_offset, readp, dataend);
10403       printf (" TType base offset:   %#x\n", ttype_base_offset);
10404       if ((size_t) (dataend - readp) > ttype_base_offset)
10405         ttype_base = readp + ttype_base_offset;
10406     }
10407
10408   if (unlikely (readp + 1 > dataend))
10409     goto invalid_data;
10410   unsigned int call_site_encoding = *readp++;
10411   printf (gettext (" Call site encoding:  %#x "), call_site_encoding);
10412   print_encoding_base ("", call_site_encoding);
10413   unsigned int call_site_table_len;
10414   get_uleb128 (call_site_table_len, readp, dataend);
10415
10416   const unsigned char *const action_table = readp + call_site_table_len;
10417   if (unlikely (action_table > dataend))
10418     goto invalid_data;
10419   unsigned int u = 0;
10420   unsigned int max_action = 0;
10421   while (readp < action_table)
10422     {
10423       if (u == 0)
10424         puts (gettext ("\n Call site table:"));
10425
10426       uint64_t call_site_start;
10427       readp = read_encoded (call_site_encoding, readp, dataend,
10428                             &call_site_start, dbg);
10429       uint64_t call_site_length;
10430       readp = read_encoded (call_site_encoding, readp, dataend,
10431                             &call_site_length, dbg);
10432       uint64_t landing_pad;
10433       readp = read_encoded (call_site_encoding, readp, dataend,
10434                             &landing_pad, dbg);
10435       unsigned int action;
10436       get_uleb128 (action, readp, dataend);
10437       max_action = MAX (action, max_action);
10438       printf (gettext (" [%4u] Call site start:   %#" PRIx64 "\n"
10439                        "        Call site length:  %" PRIu64 "\n"
10440                        "        Landing pad:       %#" PRIx64 "\n"
10441                        "        Action:            %u\n"),
10442               u++, call_site_start, call_site_length, landing_pad, action);
10443     }
10444   if (readp != action_table)
10445     goto invalid_data;
10446
10447   unsigned int max_ar_filter = 0;
10448   if (max_action > 0)
10449     {
10450       puts ("\n Action table:");
10451
10452       size_t maxdata = (size_t) (dataend - action_table);
10453       if (max_action > maxdata || maxdata - max_action < 1)
10454         {
10455         invalid_action_table:
10456           fputs (gettext ("   <INVALID DATA>\n"), stdout);
10457           return;
10458         }
10459
10460       const unsigned char *const action_table_end
10461         = action_table + max_action + 1;
10462
10463       u = 0;
10464       do
10465         {
10466           int ar_filter;
10467           get_sleb128 (ar_filter, readp, action_table_end);
10468           if (ar_filter > 0 && (unsigned int) ar_filter > max_ar_filter)
10469             max_ar_filter = ar_filter;
10470           int ar_disp;
10471           if (readp >= action_table_end)
10472             goto invalid_action_table;
10473           get_sleb128 (ar_disp, readp, action_table_end);
10474
10475           printf (" [%4u] ar_filter:  % d\n"
10476                   "        ar_disp:    % -5d",
10477                   u, ar_filter, ar_disp);
10478           if (abs (ar_disp) & 1)
10479             printf (" -> [%4u]\n", u + (ar_disp + 1) / 2);
10480           else if (ar_disp != 0)
10481             puts (" -> ???");
10482           else
10483             putchar_unlocked ('\n');
10484           ++u;
10485         }
10486       while (readp < action_table_end);
10487     }
10488
10489   if (max_ar_filter > 0 && ttype_base != NULL)
10490     {
10491       unsigned char dsize;
10492       puts ("\n TType table:");
10493
10494       // XXX Not *4, size of encoding;
10495       switch (ttype_encoding & 7)
10496         {
10497         case DW_EH_PE_udata2:
10498         case DW_EH_PE_sdata2:
10499           dsize = 2;
10500           break;
10501         case DW_EH_PE_udata4:
10502         case DW_EH_PE_sdata4:
10503           dsize = 4;
10504           break;
10505         case DW_EH_PE_udata8:
10506         case DW_EH_PE_sdata8:
10507           dsize = 8;
10508           break;
10509         default:
10510           dsize = 0;
10511           error (1, 0, gettext ("invalid TType encoding"));
10512         }
10513
10514       if (max_ar_filter
10515           > (size_t) (ttype_base - (const unsigned char *) data->d_buf) / dsize)
10516         goto invalid_data;
10517
10518       readp = ttype_base - max_ar_filter * dsize;
10519       do
10520         {
10521           uint64_t ttype;
10522           readp = read_encoded (ttype_encoding, readp, ttype_base, &ttype,
10523                                 dbg);
10524           printf (" [%4u] %#" PRIx64 "\n", max_ar_filter--, ttype);
10525         }
10526       while (readp < ttype_base);
10527     }
10528 }
10529
10530 /* Print the content of the '.gdb_index' section.
10531    http://sourceware.org/gdb/current/onlinedocs/gdb/Index-Section-Format.html
10532 */
10533 static void
10534 print_gdb_index_section (Dwfl_Module *dwflmod, Ebl *ebl, GElf_Ehdr *ehdr,
10535                          Elf_Scn *scn, GElf_Shdr *shdr, Dwarf *dbg)
10536 {
10537   printf (gettext ("\nGDB section [%2zu] '%s' at offset %#" PRIx64
10538                    " contains %" PRId64 " bytes :\n"),
10539           elf_ndxscn (scn), section_name (ebl, ehdr, shdr),
10540           (uint64_t) shdr->sh_offset, (uint64_t) shdr->sh_size);
10541
10542   Elf_Data *data = elf_rawdata (scn, NULL);
10543
10544   if (unlikely (data == NULL))
10545     {
10546       error (0, 0, gettext ("cannot get %s content: %s"),
10547              ".gdb_index", elf_errmsg (-1));
10548       return;
10549     }
10550
10551   // .gdb_index is always in little endian.
10552   Dwarf dummy_dbg = { .other_byte_order = MY_ELFDATA != ELFDATA2LSB };
10553   dbg = &dummy_dbg;
10554
10555   const unsigned char *readp = data->d_buf;
10556   const unsigned char *const dataend = readp + data->d_size;
10557
10558   if (unlikely (readp + 4 > dataend))
10559     {
10560     invalid_data:
10561       error (0, 0, gettext ("invalid data"));
10562       return;
10563     }
10564
10565   int32_t vers = read_4ubyte_unaligned (dbg, readp);
10566   printf (gettext (" Version:         %" PRId32 "\n"), vers);
10567
10568   // The only difference between version 4 and version 5 is the
10569   // hash used for generating the table.  Version 6 contains symbols
10570   // for inlined functions, older versions didn't.  Version 7 adds
10571   // symbol kinds.  Version 8 just indicates that it correctly includes
10572   // TUs for symbols.
10573   if (vers < 4 || vers > 8)
10574     {
10575       printf (gettext ("  unknown version, cannot parse section\n"));
10576       return;
10577     }
10578
10579   readp += 4;
10580   if (unlikely (readp + 4 > dataend))
10581     goto invalid_data;
10582
10583   uint32_t cu_off = read_4ubyte_unaligned (dbg, readp);
10584   printf (gettext (" CU offset:       %#" PRIx32 "\n"), cu_off);
10585
10586   readp += 4;
10587   if (unlikely (readp + 4 > dataend))
10588     goto invalid_data;
10589
10590   uint32_t tu_off = read_4ubyte_unaligned (dbg, readp);
10591   printf (gettext (" TU offset:       %#" PRIx32 "\n"), tu_off);
10592
10593   readp += 4;
10594   if (unlikely (readp + 4 > dataend))
10595     goto invalid_data;
10596
10597   uint32_t addr_off = read_4ubyte_unaligned (dbg, readp);
10598   printf (gettext (" address offset:  %#" PRIx32 "\n"), addr_off);
10599
10600   readp += 4;
10601   if (unlikely (readp + 4 > dataend))
10602     goto invalid_data;
10603
10604   uint32_t sym_off = read_4ubyte_unaligned (dbg, readp);
10605   printf (gettext (" symbol offset:   %#" PRIx32 "\n"), sym_off);
10606
10607   readp += 4;
10608   if (unlikely (readp + 4 > dataend))
10609     goto invalid_data;
10610
10611   uint32_t const_off = read_4ubyte_unaligned (dbg, readp);
10612   printf (gettext (" constant offset: %#" PRIx32 "\n"), const_off);
10613
10614   if (unlikely ((size_t) (dataend - (const unsigned char *) data->d_buf)
10615                 < const_off))
10616     goto invalid_data;
10617
10618   readp = data->d_buf + cu_off;
10619
10620   const unsigned char *nextp = data->d_buf + tu_off;
10621   if (tu_off >= data->d_size)
10622     goto invalid_data;
10623
10624   size_t cu_nr = (nextp - readp) / 16;
10625
10626   printf (gettext ("\n CU list at offset %#" PRIx32
10627                    " contains %zu entries:\n"),
10628           cu_off, cu_nr);
10629
10630   size_t n = 0;
10631   while (dataend - readp >= 16 && n < cu_nr)
10632     {
10633       uint64_t off = read_8ubyte_unaligned (dbg, readp);
10634       readp += 8;
10635
10636       uint64_t len = read_8ubyte_unaligned (dbg, readp);
10637       readp += 8;
10638
10639       printf (" [%4zu] start: %0#8" PRIx64
10640               ", length: %5" PRIu64 "\n", n, off, len);
10641       n++;
10642     }
10643
10644   readp = data->d_buf + tu_off;
10645   nextp = data->d_buf + addr_off;
10646   if (addr_off >= data->d_size)
10647     goto invalid_data;
10648
10649   size_t tu_nr = (nextp - readp) / 24;
10650
10651   printf (gettext ("\n TU list at offset %#" PRIx32
10652                    " contains %zu entries:\n"),
10653           tu_off, tu_nr);
10654
10655   n = 0;
10656   while (dataend - readp >= 24 && n < tu_nr)
10657     {
10658       uint64_t off = read_8ubyte_unaligned (dbg, readp);
10659       readp += 8;
10660
10661       uint64_t type = read_8ubyte_unaligned (dbg, readp);
10662       readp += 8;
10663
10664       uint64_t sig = read_8ubyte_unaligned (dbg, readp);
10665       readp += 8;
10666
10667       printf (" [%4zu] CU offset: %5" PRId64
10668               ", type offset: %5" PRId64
10669               ", signature: %0#8" PRIx64 "\n", n, off, type, sig);
10670       n++;
10671     }
10672
10673   readp = data->d_buf + addr_off;
10674   nextp = data->d_buf + sym_off;
10675   if (sym_off >= data->d_size)
10676     goto invalid_data;
10677
10678   size_t addr_nr = (nextp - readp) / 20;
10679
10680   printf (gettext ("\n Address list at offset %#" PRIx32
10681                    " contains %zu entries:\n"),
10682           addr_off, addr_nr);
10683
10684   n = 0;
10685   while (dataend - readp >= 20 && n < addr_nr)
10686     {
10687       uint64_t low = read_8ubyte_unaligned (dbg, readp);
10688       readp += 8;
10689
10690       uint64_t high = read_8ubyte_unaligned (dbg, readp);
10691       readp += 8;
10692
10693       uint32_t idx = read_4ubyte_unaligned (dbg, readp);
10694       readp += 4;
10695
10696       char *l = format_dwarf_addr (dwflmod, 8, low, low);
10697       char *h = format_dwarf_addr (dwflmod, 8, high - 1, high);
10698       printf (" [%4zu] %s..%s, CU index: %5" PRId32 "\n",
10699               n, l, h, idx);
10700       free (l);
10701       free (h);
10702       n++;
10703     }
10704
10705   const unsigned char *const_start = data->d_buf + const_off;
10706   if (const_off >= data->d_size)
10707     goto invalid_data;
10708
10709   readp = data->d_buf + sym_off;
10710   nextp = const_start;
10711   size_t sym_nr = (nextp - readp) / 8;
10712
10713   printf (gettext ("\n Symbol table at offset %#" PRIx32
10714                    " contains %zu slots:\n"),
10715           addr_off, sym_nr);
10716
10717   n = 0;
10718   while (dataend - readp >= 8 && n < sym_nr)
10719     {
10720       uint32_t name = read_4ubyte_unaligned (dbg, readp);
10721       readp += 4;
10722
10723       uint32_t vector = read_4ubyte_unaligned (dbg, readp);
10724       readp += 4;
10725
10726       if (name != 0 || vector != 0)
10727         {
10728           const unsigned char *sym = const_start + name;
10729           if (unlikely ((size_t) (dataend - const_start) < name
10730                         || memchr (sym, '\0', dataend - sym) == NULL))
10731             goto invalid_data;
10732
10733           printf (" [%4zu] symbol: %s, CUs: ", n, sym);
10734
10735           const unsigned char *readcus = const_start + vector;
10736           if (unlikely ((size_t) (dataend - const_start) < vector))
10737             goto invalid_data;
10738           uint32_t cus = read_4ubyte_unaligned (dbg, readcus);
10739           while (cus--)
10740             {
10741               uint32_t cu_kind, cu, kind;
10742               bool is_static;
10743               readcus += 4;
10744               if (unlikely (readcus + 4 > dataend))
10745                 goto invalid_data;
10746               cu_kind = read_4ubyte_unaligned (dbg, readcus);
10747               cu = cu_kind & ((1 << 24) - 1);
10748               kind = (cu_kind >> 28) & 7;
10749               is_static = cu_kind & (1U << 31);
10750               if (cu > cu_nr - 1)
10751                 printf ("%" PRId32 "T", cu - (uint32_t) cu_nr);
10752               else
10753                 printf ("%" PRId32, cu);
10754               if (kind != 0)
10755                 {
10756                   printf (" (");
10757                   switch (kind)
10758                     {
10759                     case 1:
10760                       printf ("type");
10761                       break;
10762                     case 2:
10763                       printf ("var");
10764                       break;
10765                     case 3:
10766                       printf ("func");
10767                       break;
10768                     case 4:
10769                       printf ("other");
10770                       break;
10771                     default:
10772                       printf ("unknown-0x%" PRIx32, kind);
10773                       break;
10774                     }
10775                   printf (":%c)", (is_static ? 'S' : 'G'));
10776                 }
10777               if (cus > 0)
10778                 printf (", ");
10779             }
10780           printf ("\n");
10781         }
10782       n++;
10783     }
10784 }
10785
10786 /* Returns true and sets split DWARF CU id if there is a split compile
10787    unit in the given Dwarf, and no non-split units are found (before it).  */
10788 static bool
10789 is_split_dwarf (Dwarf *dbg, uint64_t *id, Dwarf_CU **split_cu)
10790 {
10791   Dwarf_CU *cu = NULL;
10792   while (dwarf_get_units (dbg, cu, &cu, NULL, NULL, NULL, NULL) == 0)
10793     {
10794       uint8_t unit_type;
10795       if (dwarf_cu_info (cu, NULL, &unit_type, NULL, NULL,
10796                          id, NULL, NULL) != 0)
10797         return false;
10798
10799       if (unit_type != DW_UT_split_compile && unit_type != DW_UT_split_type)
10800         return false;
10801
10802       /* We really only care about the split compile unit, the types
10803          should be fine and self sufficient.  Also they don't have an
10804          id that we can match with a skeleton unit.  */
10805       if (unit_type == DW_UT_split_compile)
10806         {
10807           *split_cu = cu;
10808           return true;
10809         }
10810     }
10811
10812   return false;
10813 }
10814
10815 /* Check that there is one and only one Dwfl_Module, return in arg.  */
10816 static int
10817 getone_dwflmod (Dwfl_Module *dwflmod,
10818                void **userdata __attribute__ ((unused)),
10819                const char *name __attribute__ ((unused)),
10820                Dwarf_Addr base __attribute__ ((unused)),
10821                void *arg)
10822 {
10823   Dwfl_Module **m = (Dwfl_Module **) arg;
10824   if (*m != NULL)
10825     return DWARF_CB_ABORT;
10826   *m = dwflmod;
10827   return DWARF_CB_OK;
10828 }
10829
10830 static void
10831 print_debug (Dwfl_Module *dwflmod, Ebl *ebl, GElf_Ehdr *ehdr)
10832 {
10833   /* Used for skeleton file, if necessary for split DWARF.  */
10834   Dwfl *skel_dwfl = NULL;
10835   Dwfl_Module *skel_mod = NULL;
10836   char *skel_name = NULL;
10837   Dwarf *split_dbg = NULL;
10838   Dwarf_CU *split_cu = NULL;
10839
10840   /* Before we start the real work get a debug context descriptor.  */
10841   Dwarf_Addr dwbias;
10842   Dwarf *dbg = dwfl_module_getdwarf (dwflmod, &dwbias);
10843   Dwarf dummy_dbg =
10844     {
10845       .elf = ebl->elf,
10846       .other_byte_order = MY_ELFDATA != ehdr->e_ident[EI_DATA]
10847     };
10848   if (dbg == NULL)
10849     {
10850       if ((print_debug_sections & ~section_exception) != 0)
10851         error (0, 0, gettext ("cannot get debug context descriptor: %s"),
10852                dwfl_errmsg (-1));
10853       dbg = &dummy_dbg;
10854     }
10855   else
10856     {
10857       /* If we are asked about a split dwarf (.dwo) file, use the user
10858          provided, or find the corresponding skeleton file. If we got
10859          a skeleton file, replace the given dwflmod and dbg, with one
10860          derived from the skeleton file to provide enough context.  */
10861       uint64_t split_id;
10862       if (is_split_dwarf (dbg, &split_id, &split_cu))
10863         {
10864           if (dwarf_skeleton != NULL)
10865             skel_name = strdup (dwarf_skeleton);
10866           else
10867             {
10868               /* Replace file.dwo with file.o and see if that matches. */
10869               const char *fname;
10870               dwfl_module_info (dwflmod, NULL, NULL, NULL, NULL, NULL,
10871                                 &fname, NULL);
10872               if (fname != NULL)
10873                 {
10874                   size_t flen = strlen (fname);
10875                   if (flen > 4 && strcmp (".dwo", fname + flen - 4) == 0)
10876                     {
10877                       skel_name = strdup (fname);
10878                       if (skel_name != NULL)
10879                         {
10880                           skel_name[flen - 3] = 'o';
10881                           skel_name[flen - 2] = '\0';
10882                         }
10883                     }
10884                 }
10885             }
10886
10887           if (skel_name != NULL)
10888             {
10889               int skel_fd = open (skel_name, O_RDONLY);
10890               if (skel_fd == -1)
10891                 fprintf (stderr, "Warning: Couldn't open DWARF skeleton file"
10892                          " '%s'\n", skel_name);
10893               else
10894                 skel_dwfl = create_dwfl (skel_fd, skel_name);
10895
10896               if (skel_dwfl != NULL)
10897                 {
10898                   if (dwfl_getmodules (skel_dwfl, &getone_dwflmod,
10899                                        &skel_mod, 0) != 0)
10900                     {
10901                       fprintf (stderr, "Warning: Bad DWARF skeleton,"
10902                                " multiple modules '%s'\n", skel_name);
10903                       dwfl_end (skel_dwfl);
10904                       skel_mod = NULL;
10905                     }
10906                 }
10907               else if (skel_fd != -1)
10908                 fprintf (stderr, "Warning: Couldn't create skeleton dwfl for"
10909                          " '%s': %s\n", skel_name, dwfl_errmsg (-1));
10910
10911               if (skel_mod != NULL)
10912                 {
10913                   Dwarf *skel_dbg = dwfl_module_getdwarf (skel_mod, &dwbias);
10914                   if (skel_dbg != NULL)
10915                     {
10916                       /* First check the skeleton CU DIE, only fetch
10917                          the split DIE if we know the id matches to
10918                          not unnecessary search for any split DIEs we
10919                          don't need. */
10920                       Dwarf_CU *cu = NULL;
10921                       while (dwarf_get_units (skel_dbg, cu, &cu,
10922                                               NULL, NULL, NULL, NULL) == 0)
10923                         {
10924                           uint8_t unit_type;
10925                           uint64_t skel_id;
10926                           if (dwarf_cu_info (cu, NULL, &unit_type, NULL, NULL,
10927                                              &skel_id, NULL, NULL) == 0
10928                               && unit_type == DW_UT_skeleton
10929                               && split_id == skel_id)
10930                             {
10931                               Dwarf_Die subdie;
10932                               if (dwarf_cu_info (cu, NULL, NULL, NULL,
10933                                                  &subdie,
10934                                                  NULL, NULL, NULL) == 0
10935                                   && dwarf_tag (&subdie) != DW_TAG_invalid)
10936                                 {
10937                                   split_dbg = dwarf_cu_getdwarf (subdie.cu);
10938                                   if (split_dbg == NULL)
10939                                     fprintf (stderr,
10940                                              "Warning: Couldn't get split_dbg:"
10941                                              " %s\n", dwarf_errmsg (-1));
10942                                   break;
10943                                 }
10944                               else
10945                                 {
10946                                   /* Everything matches up, but not
10947                                      according to libdw. Which means
10948                                      the user knew better.  So...
10949                                      Terrible hack... We can never
10950                                      destroy the underlying dwfl
10951                                      because it would free the wrong
10952                                      Dwarfs... So we leak memory...*/
10953                                   if (cu->split == NULL
10954                                       && dwarf_skeleton != NULL)
10955                                     {
10956                                       do_not_close_dwfl = true;
10957                                       __libdw_link_skel_split (cu, split_cu);
10958                                       split_dbg = dwarf_cu_getdwarf (split_cu);
10959                                       break;
10960                                     }
10961                                   else
10962                                     fprintf (stderr, "Warning: Couldn't get"
10963                                              " skeleton subdie: %s\n",
10964                                              dwarf_errmsg (-1));
10965                                 }
10966                             }
10967                         }
10968                       if (split_dbg == NULL)
10969                         fprintf (stderr, "Warning: '%s' didn't contain a skeleton for split id %" PRIx64 "\n", skel_name, split_id);
10970                     }
10971                   else
10972                     fprintf (stderr, "Warning: Couldn't get skeleton DWARF:"
10973                              " %s\n", dwfl_errmsg (-1));
10974                 }
10975             }
10976
10977           if (split_dbg != NULL)
10978             {
10979               dbg = split_dbg;
10980               dwflmod = skel_mod;
10981             }
10982           else if (skel_name == NULL)
10983             fprintf (stderr,
10984                      "Warning: split DWARF file, but no skeleton found.\n");
10985         }
10986       else if (dwarf_skeleton != NULL)
10987         fprintf (stderr, "Warning: DWARF skeleton given,"
10988                  " but not a split DWARF file\n");
10989     }
10990
10991   /* Get the section header string table index.  */
10992   size_t shstrndx;
10993   if (unlikely (elf_getshdrstrndx (ebl->elf, &shstrndx) < 0))
10994     error (EXIT_FAILURE, 0,
10995            gettext ("cannot get section header string table index"));
10996
10997   /* If the .debug_info section is listed as implicitly required then
10998      we must make sure to handle it before handling any other debug
10999      section.  Various other sections depend on the CU DIEs being
11000      scanned (silently) first.  */
11001   bool implicit_info = (implicit_debug_sections & section_info) != 0;
11002   bool explicit_info = (print_debug_sections & section_info) != 0;
11003   if (implicit_info)
11004     {
11005       Elf_Scn *scn = NULL;
11006       while ((scn = elf_nextscn (ebl->elf, scn)) != NULL)
11007         {
11008           GElf_Shdr shdr_mem;
11009           GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem);
11010
11011           if (shdr != NULL && shdr->sh_type == SHT_PROGBITS)
11012             {
11013               const char *name = elf_strptr (ebl->elf, shstrndx,
11014                                              shdr->sh_name);
11015               if (name == NULL)
11016                 continue;
11017
11018               if (strcmp (name, ".debug_info") == 0
11019                   || strcmp (name, ".debug_info.dwo") == 0
11020                   || strcmp (name, ".zdebug_info") == 0
11021                   || strcmp (name, ".zdebug_info.dwo") == 0)
11022                 {
11023                   print_debug_info_section (dwflmod, ebl, ehdr,
11024                                             scn, shdr, dbg);
11025                   break;
11026                 }
11027             }
11028         }
11029       print_debug_sections &= ~section_info;
11030       implicit_debug_sections &= ~section_info;
11031     }
11032
11033   /* Look through all the sections for the debugging sections to print.  */
11034   Elf_Scn *scn = NULL;
11035   while ((scn = elf_nextscn (ebl->elf, scn)) != NULL)
11036     {
11037       GElf_Shdr shdr_mem;
11038       GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem);
11039
11040       if (shdr != NULL && shdr->sh_type == SHT_PROGBITS)
11041         {
11042           static const struct
11043           {
11044             const char *name;
11045             enum section_e bitmask;
11046             void (*fp) (Dwfl_Module *, Ebl *,
11047                         GElf_Ehdr *, Elf_Scn *, GElf_Shdr *, Dwarf *);
11048           } debug_sections[] =
11049             {
11050 #define NEW_SECTION(name) \
11051               { ".debug_" #name, section_##name, print_debug_##name##_section }
11052               NEW_SECTION (abbrev),
11053               NEW_SECTION (addr),
11054               NEW_SECTION (aranges),
11055               NEW_SECTION (frame),
11056               NEW_SECTION (info),
11057               NEW_SECTION (types),
11058               NEW_SECTION (line),
11059               NEW_SECTION (loc),
11060               /* loclists is loc for DWARF5.  */
11061               { ".debug_loclists", section_loc,
11062                 print_debug_loclists_section },
11063               NEW_SECTION (pubnames),
11064               NEW_SECTION (str),
11065               /* A DWARF5 specialised debug string section.  */
11066               { ".debug_line_str", section_str,
11067                 print_debug_str_section },
11068               /* DWARF5 string offsets table.  */
11069               { ".debug_str_offsets", section_str,
11070                 print_debug_str_offsets_section },
11071               NEW_SECTION (macinfo),
11072               NEW_SECTION (macro),
11073               NEW_SECTION (ranges),
11074               /* rnglists is ranges for DWARF5.  */
11075               { ".debug_rnglists", section_ranges,
11076                 print_debug_rnglists_section },
11077               { ".eh_frame", section_frame | section_exception,
11078                 print_debug_frame_section },
11079               { ".eh_frame_hdr", section_frame | section_exception,
11080                 print_debug_frame_hdr_section },
11081               { ".gcc_except_table", section_frame | section_exception,
11082                 print_debug_exception_table },
11083               { ".gdb_index", section_gdb_index, print_gdb_index_section }
11084             };
11085           const int ndebug_sections = (sizeof (debug_sections)
11086                                        / sizeof (debug_sections[0]));
11087           const char *name = elf_strptr (ebl->elf, shstrndx,
11088                                          shdr->sh_name);
11089           if (name == NULL)
11090             continue;
11091
11092           int n;
11093           for (n = 0; n < ndebug_sections; ++n)
11094             {
11095               size_t dbglen = strlen (debug_sections[n].name);
11096               size_t scnlen = strlen (name);
11097               if ((strncmp (name, debug_sections[n].name, dbglen) == 0
11098                    && (dbglen == scnlen
11099                        || (scnlen == dbglen + 4
11100                            && strstr (name, ".dwo") == name + dbglen)))
11101                   || (name[0] == '.' && name[1] == 'z'
11102                       && debug_sections[n].name[1] == 'd'
11103                       && strncmp (&name[2], &debug_sections[n].name[1],
11104                                   dbglen - 1) == 0
11105                       && (scnlen == dbglen + 1
11106                           || (scnlen == dbglen + 5
11107                               && strstr (name, ".dwo") == name + dbglen + 1))))
11108                 {
11109                   if ((print_debug_sections | implicit_debug_sections)
11110                       & debug_sections[n].bitmask)
11111                     debug_sections[n].fp (dwflmod, ebl, ehdr, scn, shdr, dbg);
11112                   break;
11113                 }
11114             }
11115         }
11116     }
11117
11118   dwfl_end (skel_dwfl);
11119   free (skel_name);
11120
11121   /* Turn implicit and/or explicit back on in case we go over another file.  */
11122   if (implicit_info)
11123     implicit_debug_sections |= section_info;
11124   if (explicit_info)
11125     print_debug_sections |= section_info;
11126
11127   reset_listptr (&known_locsptr);
11128   reset_listptr (&known_loclistsptr);
11129   reset_listptr (&known_rangelistptr);
11130   reset_listptr (&known_rnglistptr);
11131   reset_listptr (&known_addrbases);
11132   reset_listptr (&known_stroffbases);
11133 }
11134
11135
11136 #define ITEM_INDENT             4
11137 #define WRAP_COLUMN             75
11138
11139 /* Print "NAME: FORMAT", wrapping when output text would make the line
11140    exceed WRAP_COLUMN.  Unpadded numbers look better for the core items
11141    but this function is also used for registers which should be printed
11142    aligned.  Fortunately registers output uses fixed fields width (such
11143    as %11d) for the alignment.
11144
11145    Line breaks should not depend on the particular values although that
11146    may happen in some cases of the core items.  */
11147
11148 static unsigned int
11149 __attribute__ ((format (printf, 6, 7)))
11150 print_core_item (unsigned int colno, char sep, unsigned int wrap,
11151                  size_t name_width, const char *name, const char *format, ...)
11152 {
11153   size_t len = strlen (name);
11154   if (name_width < len)
11155     name_width = len;
11156
11157   char *out;
11158   va_list ap;
11159   va_start (ap, format);
11160   int out_len = vasprintf (&out, format, ap);
11161   va_end (ap);
11162   if (out_len == -1)
11163     error (EXIT_FAILURE, 0, _("memory exhausted"));
11164
11165   size_t n = name_width + sizeof ": " - 1 + out_len;
11166
11167   if (colno == 0)
11168     {
11169       printf ("%*s", ITEM_INDENT, "");
11170       colno = ITEM_INDENT + n;
11171     }
11172   else if (colno + 2 + n < wrap)
11173     {
11174       printf ("%c ", sep);
11175       colno += 2 + n;
11176     }
11177   else
11178     {
11179       printf ("\n%*s", ITEM_INDENT, "");
11180       colno = ITEM_INDENT + n;
11181     }
11182
11183   printf ("%s: %*s%s", name, (int) (name_width - len), "", out);
11184
11185   free (out);
11186
11187   return colno;
11188 }
11189
11190 static const void *
11191 convert (Elf *core, Elf_Type type, uint_fast16_t count,
11192          void *value, const void *data, size_t size)
11193 {
11194   Elf_Data valuedata =
11195     {
11196       .d_type = type,
11197       .d_buf = value,
11198       .d_size = size ?: gelf_fsize (core, type, count, EV_CURRENT),
11199       .d_version = EV_CURRENT,
11200     };
11201   Elf_Data indata =
11202     {
11203       .d_type = type,
11204       .d_buf = (void *) data,
11205       .d_size = valuedata.d_size,
11206       .d_version = EV_CURRENT,
11207     };
11208
11209   Elf_Data *d = (gelf_getclass (core) == ELFCLASS32
11210                  ? elf32_xlatetom : elf64_xlatetom)
11211     (&valuedata, &indata, elf_getident (core, NULL)[EI_DATA]);
11212   if (d == NULL)
11213     error (EXIT_FAILURE, 0,
11214            gettext ("cannot convert core note data: %s"), elf_errmsg (-1));
11215
11216   return data + indata.d_size;
11217 }
11218
11219 typedef uint8_t GElf_Byte;
11220
11221 static unsigned int
11222 handle_core_item (Elf *core, const Ebl_Core_Item *item, const void *desc,
11223                   unsigned int colno, size_t *repeated_size)
11224 {
11225   uint_fast16_t count = item->count ?: 1;
11226   /* Ebl_Core_Item count is always a small number.
11227      Make sure the backend didn't put in some large bogus value.  */
11228   assert (count < 128);
11229
11230 #define TYPES                                                                 \
11231   DO_TYPE (BYTE, Byte, "0x%.2" PRIx8, "%" PRId8);                             \
11232   DO_TYPE (HALF, Half, "0x%.4" PRIx16, "%" PRId16);                           \
11233   DO_TYPE (WORD, Word, "0x%.8" PRIx32, "%" PRId32);                           \
11234   DO_TYPE (SWORD, Sword, "%" PRId32, "%" PRId32);                             \
11235   DO_TYPE (XWORD, Xword, "0x%.16" PRIx64, "%" PRId64);                        \
11236   DO_TYPE (SXWORD, Sxword, "%" PRId64, "%" PRId64)
11237
11238 #define DO_TYPE(NAME, Name, hex, dec) GElf_##Name Name
11239   typedef union { TYPES; } value_t;
11240   void *data = alloca (count * sizeof (value_t));
11241 #undef DO_TYPE
11242
11243 #define DO_TYPE(NAME, Name, hex, dec) \
11244     GElf_##Name *value_##Name __attribute__((unused)) = data
11245   TYPES;
11246 #undef DO_TYPE
11247
11248   size_t size = gelf_fsize (core, item->type, count, EV_CURRENT);
11249   size_t convsize = size;
11250   if (repeated_size != NULL)
11251     {
11252       if (*repeated_size > size && (item->format == 'b' || item->format == 'B'))
11253         {
11254           data = alloca (*repeated_size);
11255           count *= *repeated_size / size;
11256           convsize = count * size;
11257           *repeated_size -= convsize;
11258         }
11259       else if (item->count != 0 || item->format != '\n')
11260         *repeated_size -= size;
11261     }
11262
11263   convert (core, item->type, count, data, desc + item->offset, convsize);
11264
11265   Elf_Type type = item->type;
11266   if (type == ELF_T_ADDR)
11267     type = gelf_getclass (core) == ELFCLASS32 ? ELF_T_WORD : ELF_T_XWORD;
11268
11269   switch (item->format)
11270     {
11271     case 'd':
11272       assert (count == 1);
11273       switch (type)
11274         {
11275 #define DO_TYPE(NAME, Name, hex, dec)                                         \
11276           case ELF_T_##NAME:                                                  \
11277             colno = print_core_item (colno, ',', WRAP_COLUMN,                 \
11278                                      0, item->name, dec, value_##Name[0]); \
11279             break
11280           TYPES;
11281 #undef DO_TYPE
11282         default:
11283           abort ();
11284         }
11285       break;
11286
11287     case 'x':
11288       assert (count == 1);
11289       switch (type)
11290         {
11291 #define DO_TYPE(NAME, Name, hex, dec)                                         \
11292           case ELF_T_##NAME:                                                  \
11293             colno = print_core_item (colno, ',', WRAP_COLUMN,                 \
11294                                      0, item->name, hex, value_##Name[0]);      \
11295             break
11296           TYPES;
11297 #undef DO_TYPE
11298         default:
11299           abort ();
11300         }
11301       break;
11302
11303     case 'b':
11304     case 'B':
11305       assert (size % sizeof (unsigned int) == 0);
11306       unsigned int nbits = count * size * 8;
11307       unsigned int pop = 0;
11308       for (const unsigned int *i = data; (void *) i < data + count * size; ++i)
11309         pop += __builtin_popcount (*i);
11310       bool negate = pop > nbits / 2;
11311       const unsigned int bias = item->format == 'b';
11312
11313       {
11314         char printed[(negate ? nbits - pop : pop) * 16 + 1];
11315         char *p = printed;
11316         *p = '\0';
11317
11318         if (BYTE_ORDER != LITTLE_ENDIAN && size > sizeof (unsigned int))
11319           {
11320             assert (size == sizeof (unsigned int) * 2);
11321             for (unsigned int *i = data;
11322                  (void *) i < data + count * size; i += 2)
11323               {
11324                 unsigned int w = i[1];
11325                 i[1] = i[0];
11326                 i[0] = w;
11327               }
11328           }
11329
11330         unsigned int lastbit = 0;
11331         unsigned int run = 0;
11332         for (const unsigned int *i = data;
11333              (void *) i < data + count * size; ++i)
11334           {
11335             unsigned int bit = ((void *) i - data) * 8;
11336             unsigned int w = negate ? ~*i : *i;
11337             while (w != 0)
11338               {
11339                 /* Note that a right shift equal to (or greater than)
11340                    the number of bits of w is undefined behaviour.  In
11341                    particular when the least significant bit is bit 32
11342                    (w = 0x8000000) then w >>= n is undefined.  So
11343                    explicitly handle that case separately.  */
11344                 unsigned int n = ffs (w);
11345                 if (n < sizeof (w) * 8)
11346                   w >>= n;
11347                 else
11348                   w = 0;
11349                 bit += n;
11350
11351                 if (lastbit != 0 && lastbit + 1 == bit)
11352                   ++run;
11353                 else
11354                   {
11355                     if (lastbit == 0)
11356                       p += sprintf (p, "%u", bit - bias);
11357                     else if (run == 0)
11358                       p += sprintf (p, ",%u", bit - bias);
11359                     else
11360                       p += sprintf (p, "-%u,%u", lastbit - bias, bit - bias);
11361                     run = 0;
11362                   }
11363
11364                 lastbit = bit;
11365               }
11366           }
11367         if (lastbit > 0 && run > 0 && lastbit + 1 != nbits)
11368           p += sprintf (p, "-%u", lastbit - bias);
11369
11370         colno = print_core_item (colno, ',', WRAP_COLUMN, 0, item->name,
11371                                  negate ? "~<%s>" : "<%s>", printed);
11372       }
11373       break;
11374
11375     case 'T':
11376     case (char) ('T'|0x80):
11377       assert (count == 2);
11378       Dwarf_Word sec;
11379       Dwarf_Word usec;
11380       switch (type)
11381         {
11382 #define DO_TYPE(NAME, Name, hex, dec)                                         \
11383           case ELF_T_##NAME:                                                  \
11384             sec = value_##Name[0];                                            \
11385             usec = value_##Name[1];                                           \
11386             break
11387           TYPES;
11388 #undef DO_TYPE
11389         default:
11390           abort ();
11391         }
11392       if (unlikely (item->format == (char) ('T'|0x80)))
11393         {
11394           /* This is a hack for an ill-considered 64-bit ABI where
11395              tv_usec is actually a 32-bit field with 32 bits of padding
11396              rounding out struct timeval.  We've already converted it as
11397              a 64-bit field.  For little-endian, this just means the
11398              high half is the padding; it's presumably zero, but should
11399              be ignored anyway.  For big-endian, it means the 32-bit
11400              field went into the high half of USEC.  */
11401           GElf_Ehdr ehdr_mem;
11402           GElf_Ehdr *ehdr = gelf_getehdr (core, &ehdr_mem);
11403           if (likely (ehdr->e_ident[EI_DATA] == ELFDATA2MSB))
11404             usec >>= 32;
11405           else
11406             usec &= UINT32_MAX;
11407         }
11408       colno = print_core_item (colno, ',', WRAP_COLUMN, 0, item->name,
11409                                "%" PRIu64 ".%.6" PRIu64, sec, usec);
11410       break;
11411
11412     case 'c':
11413       assert (count == 1);
11414       colno = print_core_item (colno, ',', WRAP_COLUMN, 0, item->name,
11415                                "%c", value_Byte[0]);
11416       break;
11417
11418     case 's':
11419       colno = print_core_item (colno, ',', WRAP_COLUMN, 0, item->name,
11420                                "%.*s", (int) count, value_Byte);
11421       break;
11422
11423     case '\n':
11424       /* This is a list of strings separated by '\n'.  */
11425       assert (item->count == 0);
11426       assert (repeated_size != NULL);
11427       assert (item->name == NULL);
11428       if (unlikely (item->offset >= *repeated_size))
11429         break;
11430
11431       const char *s = desc + item->offset;
11432       size = *repeated_size - item->offset;
11433       *repeated_size = 0;
11434       while (size > 0)
11435         {
11436           const char *eol = memchr (s, '\n', size);
11437           int len = size;
11438           if (eol != NULL)
11439             len = eol - s;
11440           printf ("%*s%.*s\n", ITEM_INDENT, "", len, s);
11441           if (eol == NULL)
11442             break;
11443           size -= eol + 1 - s;
11444           s = eol + 1;
11445         }
11446
11447       colno = WRAP_COLUMN;
11448       break;
11449
11450     case 'h':
11451       break;
11452
11453     default:
11454       error (0, 0, "XXX not handling format '%c' for %s",
11455              item->format, item->name);
11456       break;
11457     }
11458
11459 #undef TYPES
11460
11461   return colno;
11462 }
11463
11464
11465 /* Sort items by group, and by layout offset within each group.  */
11466 static int
11467 compare_core_items (const void *a, const void *b)
11468 {
11469   const Ebl_Core_Item *const *p1 = a;
11470   const Ebl_Core_Item *const *p2 = b;
11471   const Ebl_Core_Item *item1 = *p1;
11472   const Ebl_Core_Item *item2 = *p2;
11473
11474   return ((item1->group == item2->group ? 0
11475            : strcmp (item1->group, item2->group))
11476           ?: (int) item1->offset - (int) item2->offset);
11477 }
11478
11479 /* Sort item groups by layout offset of the first item in the group.  */
11480 static int
11481 compare_core_item_groups (const void *a, const void *b)
11482 {
11483   const Ebl_Core_Item *const *const *p1 = a;
11484   const Ebl_Core_Item *const *const *p2 = b;
11485   const Ebl_Core_Item *const *group1 = *p1;
11486   const Ebl_Core_Item *const *group2 = *p2;
11487   const Ebl_Core_Item *item1 = *group1;
11488   const Ebl_Core_Item *item2 = *group2;
11489
11490   return (int) item1->offset - (int) item2->offset;
11491 }
11492
11493 static unsigned int
11494 handle_core_items (Elf *core, const void *desc, size_t descsz,
11495                    const Ebl_Core_Item *items, size_t nitems)
11496 {
11497   if (nitems == 0)
11498     return 0;
11499   unsigned int colno = 0;
11500
11501   /* FORMAT '\n' makes sense to be present only as a single item as it
11502      processes all the data of a note.  FORMATs 'b' and 'B' have a special case
11503      if present as a single item but they can be also processed with other
11504      items below.  */
11505   if (nitems == 1 && (items[0].format == '\n' || items[0].format == 'b'
11506                       || items[0].format == 'B'))
11507     {
11508       assert (items[0].offset == 0);
11509       size_t size = descsz;
11510       colno = handle_core_item (core, items, desc, colno, &size);
11511       /* If SIZE is not zero here there is some remaining data.  But we do not
11512          know how to process it anyway.  */
11513       return colno;
11514     }
11515   for (size_t i = 0; i < nitems; ++i)
11516     assert (items[i].format != '\n');
11517
11518   /* Sort to collect the groups together.  */
11519   const Ebl_Core_Item *sorted_items[nitems];
11520   for (size_t i = 0; i < nitems; ++i)
11521     sorted_items[i] = &items[i];
11522   qsort (sorted_items, nitems, sizeof sorted_items[0], &compare_core_items);
11523
11524   /* Collect the unique groups and sort them.  */
11525   const Ebl_Core_Item **groups[nitems];
11526   groups[0] = &sorted_items[0];
11527   size_t ngroups = 1;
11528   for (size_t i = 1; i < nitems; ++i)
11529     if (sorted_items[i]->group != sorted_items[i - 1]->group
11530         && strcmp (sorted_items[i]->group, sorted_items[i - 1]->group))
11531       groups[ngroups++] = &sorted_items[i];
11532   qsort (groups, ngroups, sizeof groups[0], &compare_core_item_groups);
11533
11534   /* Write out all the groups.  */
11535   const void *last = desc;
11536   do
11537     {
11538       for (size_t i = 0; i < ngroups; ++i)
11539         {
11540           for (const Ebl_Core_Item **item = groups[i];
11541                (item < &sorted_items[nitems]
11542                 && ((*item)->group == groups[i][0]->group
11543                     || !strcmp ((*item)->group, groups[i][0]->group)));
11544                ++item)
11545             colno = handle_core_item (core, *item, desc, colno, NULL);
11546
11547           /* Force a line break at the end of the group.  */
11548           colno = WRAP_COLUMN;
11549         }
11550
11551       if (descsz == 0)
11552         break;
11553
11554       /* This set of items consumed a certain amount of the note's data.
11555          If there is more data there, we have another unit of the same size.
11556          Loop to print that out too.  */
11557       const Ebl_Core_Item *item = &items[nitems - 1];
11558       size_t eltsz = item->offset + gelf_fsize (core, item->type,
11559                                                 item->count ?: 1, EV_CURRENT);
11560
11561       int reps = -1;
11562       do
11563         {
11564           ++reps;
11565           desc += eltsz;
11566           descsz -= eltsz;
11567         }
11568       while (descsz >= eltsz && !memcmp (desc, last, eltsz));
11569
11570       if (reps == 1)
11571         {
11572           /* For just one repeat, print it unabridged twice.  */
11573           desc -= eltsz;
11574           descsz += eltsz;
11575         }
11576       else if (reps > 1)
11577         printf (gettext ("\n%*s... <repeats %u more times> ..."),
11578                 ITEM_INDENT, "", reps);
11579
11580       last = desc;
11581     }
11582   while (descsz > 0);
11583
11584   return colno;
11585 }
11586
11587 static unsigned int
11588 handle_bit_registers (const Ebl_Register_Location *regloc, const void *desc,
11589                       unsigned int colno)
11590 {
11591   desc += regloc->offset;
11592
11593   abort ();                     /* XXX */
11594   return colno;
11595 }
11596
11597
11598 static unsigned int
11599 handle_core_register (Ebl *ebl, Elf *core, int maxregname,
11600                       const Ebl_Register_Location *regloc, const void *desc,
11601                       unsigned int colno)
11602 {
11603   if (regloc->bits % 8 != 0)
11604     return handle_bit_registers (regloc, desc, colno);
11605
11606   desc += regloc->offset;
11607
11608   for (int reg = regloc->regno; reg < regloc->regno + regloc->count; ++reg)
11609     {
11610       char name[REGNAMESZ];
11611       int bits;
11612       int type;
11613       register_info (ebl, reg, regloc, name, &bits, &type);
11614
11615 #define TYPES                                                                 \
11616       BITS (8, BYTE, "%4" PRId8, "0x%.2" PRIx8);                              \
11617       BITS (16, HALF, "%6" PRId16, "0x%.4" PRIx16);                           \
11618       BITS (32, WORD, "%11" PRId32, " 0x%.8" PRIx32);                         \
11619       BITS (64, XWORD, "%20" PRId64, "  0x%.16" PRIx64)
11620
11621 #define BITS(bits, xtype, sfmt, ufmt)                           \
11622       uint##bits##_t b##bits; int##bits##_t b##bits##s
11623       union { TYPES; uint64_t b128[2]; } value;
11624 #undef  BITS
11625
11626       switch (type)
11627         {
11628         case DW_ATE_unsigned:
11629         case DW_ATE_signed:
11630         case DW_ATE_address:
11631           switch (bits)
11632             {
11633 #define BITS(bits, xtype, sfmt, ufmt)                                         \
11634             case bits:                                                        \
11635               desc = convert (core, ELF_T_##xtype, 1, &value, desc, 0);       \
11636               if (type == DW_ATE_signed)                                      \
11637                 colno = print_core_item (colno, ' ', WRAP_COLUMN,             \
11638                                          maxregname, name,                    \
11639                                          sfmt, value.b##bits##s);             \
11640               else                                                            \
11641                 colno = print_core_item (colno, ' ', WRAP_COLUMN,             \
11642                                          maxregname, name,                    \
11643                                          ufmt, value.b##bits);                \
11644               break
11645
11646             TYPES;
11647
11648             case 128:
11649               assert (type == DW_ATE_unsigned);
11650               desc = convert (core, ELF_T_XWORD, 2, &value, desc, 0);
11651               int be = elf_getident (core, NULL)[EI_DATA] == ELFDATA2MSB;
11652               colno = print_core_item (colno, ' ', WRAP_COLUMN,
11653                                        maxregname, name,
11654                                        "0x%.16" PRIx64 "%.16" PRIx64,
11655                                        value.b128[!be], value.b128[be]);
11656               break;
11657
11658             default:
11659               abort ();
11660 #undef  BITS
11661             }
11662           break;
11663
11664         default:
11665           /* Print each byte in hex, the whole thing in native byte order.  */
11666           assert (bits % 8 == 0);
11667           const uint8_t *bytes = desc;
11668           desc += bits / 8;
11669           char hex[bits / 4 + 1];
11670           hex[bits / 4] = '\0';
11671           int incr = 1;
11672           if (elf_getident (core, NULL)[EI_DATA] == ELFDATA2LSB)
11673             {
11674               bytes += bits / 8 - 1;
11675               incr = -1;
11676             }
11677           size_t idx = 0;
11678           for (char *h = hex; bits > 0; bits -= 8, idx += incr)
11679             {
11680               *h++ = "0123456789abcdef"[bytes[idx] >> 4];
11681               *h++ = "0123456789abcdef"[bytes[idx] & 0xf];
11682             }
11683           colno = print_core_item (colno, ' ', WRAP_COLUMN,
11684                                    maxregname, name, "0x%s", hex);
11685           break;
11686         }
11687       desc += regloc->pad;
11688
11689 #undef TYPES
11690     }
11691
11692   return colno;
11693 }
11694
11695
11696 struct register_info
11697 {
11698   const Ebl_Register_Location *regloc;
11699   const char *set;
11700   char name[REGNAMESZ];
11701   int regno;
11702   int bits;
11703   int type;
11704 };
11705
11706 static int
11707 register_bitpos (const struct register_info *r)
11708 {
11709   return (r->regloc->offset * 8
11710           + ((r->regno - r->regloc->regno)
11711              * (r->regloc->bits + r->regloc->pad * 8)));
11712 }
11713
11714 static int
11715 compare_sets_by_info (const struct register_info *r1,
11716                       const struct register_info *r2)
11717 {
11718   return ((int) r2->bits - (int) r1->bits
11719           ?: register_bitpos (r1) - register_bitpos (r2));
11720 }
11721
11722 /* Sort registers by set, and by size and layout offset within each set.  */
11723 static int
11724 compare_registers (const void *a, const void *b)
11725 {
11726   const struct register_info *r1 = a;
11727   const struct register_info *r2 = b;
11728
11729   /* Unused elements sort last.  */
11730   if (r1->regloc == NULL)
11731     return r2->regloc == NULL ? 0 : 1;
11732   if (r2->regloc == NULL)
11733     return -1;
11734
11735   return ((r1->set == r2->set ? 0 : strcmp (r1->set, r2->set))
11736           ?: compare_sets_by_info (r1, r2));
11737 }
11738
11739 /* Sort register sets by layout offset of the first register in the set.  */
11740 static int
11741 compare_register_sets (const void *a, const void *b)
11742 {
11743   const struct register_info *const *p1 = a;
11744   const struct register_info *const *p2 = b;
11745   return compare_sets_by_info (*p1, *p2);
11746 }
11747
11748 static unsigned int
11749 handle_core_registers (Ebl *ebl, Elf *core, const void *desc,
11750                        const Ebl_Register_Location *reglocs, size_t nregloc)
11751 {
11752   if (nregloc == 0)
11753     return 0;
11754
11755   ssize_t maxnreg = ebl_register_info (ebl, 0, NULL, 0, NULL, NULL, NULL, NULL);
11756   if (maxnreg <= 0)
11757     {
11758       for (size_t i = 0; i < nregloc; ++i)
11759         if (maxnreg < reglocs[i].regno + reglocs[i].count)
11760           maxnreg = reglocs[i].regno + reglocs[i].count;
11761       assert (maxnreg > 0);
11762     }
11763
11764   struct register_info regs[maxnreg];
11765   memset (regs, 0, sizeof regs);
11766
11767   /* Sort to collect the sets together.  */
11768   int maxreg = 0;
11769   for (size_t i = 0; i < nregloc; ++i)
11770     for (int reg = reglocs[i].regno;
11771          reg < reglocs[i].regno + reglocs[i].count;
11772          ++reg)
11773       {
11774         assert (reg < maxnreg);
11775         if (reg > maxreg)
11776           maxreg = reg;
11777         struct register_info *info = &regs[reg];
11778         info->regloc = &reglocs[i];
11779         info->regno = reg;
11780         info->set = register_info (ebl, reg, &reglocs[i],
11781                                    info->name, &info->bits, &info->type);
11782       }
11783   qsort (regs, maxreg + 1, sizeof regs[0], &compare_registers);
11784
11785   /* Collect the unique sets and sort them.  */
11786   inline bool same_set (const struct register_info *a,
11787                         const struct register_info *b)
11788   {
11789     return (a < &regs[maxnreg] && a->regloc != NULL
11790             && b < &regs[maxnreg] && b->regloc != NULL
11791             && a->bits == b->bits
11792             && (a->set == b->set || !strcmp (a->set, b->set)));
11793   }
11794   struct register_info *sets[maxreg + 1];
11795   sets[0] = &regs[0];
11796   size_t nsets = 1;
11797   for (int i = 1; i <= maxreg; ++i)
11798     if (regs[i].regloc != NULL && !same_set (&regs[i], &regs[i - 1]))
11799       sets[nsets++] = &regs[i];
11800   qsort (sets, nsets, sizeof sets[0], &compare_register_sets);
11801
11802   /* Write out all the sets.  */
11803   unsigned int colno = 0;
11804   for (size_t i = 0; i < nsets; ++i)
11805     {
11806       /* Find the longest name of a register in this set.  */
11807       size_t maxname = 0;
11808       const struct register_info *end;
11809       for (end = sets[i]; same_set (sets[i], end); ++end)
11810         {
11811           size_t len = strlen (end->name);
11812           if (len > maxname)
11813             maxname = len;
11814         }
11815
11816       for (const struct register_info *reg = sets[i];
11817            reg < end;
11818            reg += reg->regloc->count ?: 1)
11819         colno = handle_core_register (ebl, core, maxname,
11820                                       reg->regloc, desc, colno);
11821
11822       /* Force a line break at the end of the group.  */
11823       colno = WRAP_COLUMN;
11824     }
11825
11826   return colno;
11827 }
11828
11829 static void
11830 handle_auxv_note (Ebl *ebl, Elf *core, GElf_Word descsz, GElf_Off desc_pos)
11831 {
11832   Elf_Data *data = elf_getdata_rawchunk (core, desc_pos, descsz, ELF_T_AUXV);
11833   if (data == NULL)
11834   elf_error:
11835     error (EXIT_FAILURE, 0,
11836            gettext ("cannot convert core note data: %s"), elf_errmsg (-1));
11837
11838   const size_t nauxv = descsz / gelf_fsize (core, ELF_T_AUXV, 1, EV_CURRENT);
11839   for (size_t i = 0; i < nauxv; ++i)
11840     {
11841       GElf_auxv_t av_mem;
11842       GElf_auxv_t *av = gelf_getauxv (data, i, &av_mem);
11843       if (av == NULL)
11844         goto elf_error;
11845
11846       const char *name;
11847       const char *fmt;
11848       if (ebl_auxv_info (ebl, av->a_type, &name, &fmt) == 0)
11849         {
11850           /* Unknown type.  */
11851           if (av->a_un.a_val == 0)
11852             printf ("    %" PRIu64 "\n", av->a_type);
11853           else
11854             printf ("    %" PRIu64 ": %#" PRIx64 "\n",
11855                     av->a_type, av->a_un.a_val);
11856         }
11857       else
11858         switch (fmt[0])
11859           {
11860           case '\0':            /* Normally zero.  */
11861             if (av->a_un.a_val == 0)
11862               {
11863                 printf ("    %s\n", name);
11864                 break;
11865               }
11866             FALLTHROUGH;
11867           case 'x':             /* hex */
11868           case 'p':             /* address */
11869           case 's':             /* address of string */
11870             printf ("    %s: %#" PRIx64 "\n", name, av->a_un.a_val);
11871             break;
11872           case 'u':
11873             printf ("    %s: %" PRIu64 "\n", name, av->a_un.a_val);
11874             break;
11875           case 'd':
11876             printf ("    %s: %" PRId64 "\n", name, av->a_un.a_val);
11877             break;
11878
11879           case 'b':
11880             printf ("    %s: %#" PRIx64 "  ", name, av->a_un.a_val);
11881             GElf_Xword bit = 1;
11882             const char *pfx = "<";
11883             for (const char *p = fmt + 1; *p != 0; p = strchr (p, '\0') + 1)
11884               {
11885                 if (av->a_un.a_val & bit)
11886                   {
11887                     printf ("%s%s", pfx, p);
11888                     pfx = " ";
11889                   }
11890                 bit <<= 1;
11891               }
11892             printf (">\n");
11893             break;
11894
11895           default:
11896             abort ();
11897           }
11898     }
11899 }
11900
11901 static bool
11902 buf_has_data (unsigned char const *ptr, unsigned char const *end, size_t sz)
11903 {
11904   return ptr < end && (size_t) (end - ptr) >= sz;
11905 }
11906
11907 static bool
11908 buf_read_int (Elf *core, unsigned char const **ptrp, unsigned char const *end,
11909               int *retp)
11910 {
11911   if (! buf_has_data (*ptrp, end, 4))
11912     return false;
11913
11914   *ptrp = convert (core, ELF_T_WORD, 1, retp, *ptrp, 4);
11915   return true;
11916 }
11917
11918 static bool
11919 buf_read_ulong (Elf *core, unsigned char const **ptrp, unsigned char const *end,
11920                 uint64_t *retp)
11921 {
11922   size_t sz = gelf_fsize (core, ELF_T_ADDR, 1, EV_CURRENT);
11923   if (! buf_has_data (*ptrp, end, sz))
11924     return false;
11925
11926   union
11927   {
11928     uint64_t u64;
11929     uint32_t u32;
11930   } u;
11931
11932   *ptrp = convert (core, ELF_T_ADDR, 1, &u, *ptrp, sz);
11933
11934   if (sz == 4)
11935     *retp = u.u32;
11936   else
11937     *retp = u.u64;
11938   return true;
11939 }
11940
11941 static void
11942 handle_siginfo_note (Elf *core, GElf_Word descsz, GElf_Off desc_pos)
11943 {
11944   Elf_Data *data = elf_getdata_rawchunk (core, desc_pos, descsz, ELF_T_BYTE);
11945   if (data == NULL)
11946     error (EXIT_FAILURE, 0,
11947            gettext ("cannot convert core note data: %s"), elf_errmsg (-1));
11948
11949   unsigned char const *ptr = data->d_buf;
11950   unsigned char const *const end = data->d_buf + data->d_size;
11951
11952   /* Siginfo head is three ints: signal number, error number, origin
11953      code.  */
11954   int si_signo, si_errno, si_code;
11955   if (! buf_read_int (core, &ptr, end, &si_signo)
11956       || ! buf_read_int (core, &ptr, end, &si_errno)
11957       || ! buf_read_int (core, &ptr, end, &si_code))
11958     {
11959     fail:
11960       printf ("    Not enough data in NT_SIGINFO note.\n");
11961       return;
11962     }
11963
11964   /* Next is a pointer-aligned union of structures.  On 64-bit
11965      machines, that implies a word of padding.  */
11966   if (gelf_getclass (core) == ELFCLASS64)
11967     ptr += 4;
11968
11969   printf ("    si_signo: %d, si_errno: %d, si_code: %d\n",
11970           si_signo, si_errno, si_code);
11971
11972   if (si_code > 0)
11973     switch (si_signo)
11974       {
11975       case CORE_SIGILL:
11976       case CORE_SIGFPE:
11977       case CORE_SIGSEGV:
11978       case CORE_SIGBUS:
11979         {
11980           uint64_t addr;
11981           if (! buf_read_ulong (core, &ptr, end, &addr))
11982             goto fail;
11983           printf ("    fault address: %#" PRIx64 "\n", addr);
11984           break;
11985         }
11986       default:
11987         ;
11988       }
11989   else if (si_code == CORE_SI_USER)
11990     {
11991       int pid, uid;
11992       if (! buf_read_int (core, &ptr, end, &pid)
11993           || ! buf_read_int (core, &ptr, end, &uid))
11994         goto fail;
11995       printf ("    sender PID: %d, sender UID: %d\n", pid, uid);
11996     }
11997 }
11998
11999 static void
12000 handle_file_note (Elf *core, GElf_Word descsz, GElf_Off desc_pos)
12001 {
12002   Elf_Data *data = elf_getdata_rawchunk (core, desc_pos, descsz, ELF_T_BYTE);
12003   if (data == NULL)
12004     error (EXIT_FAILURE, 0,
12005            gettext ("cannot convert core note data: %s"), elf_errmsg (-1));
12006
12007   unsigned char const *ptr = data->d_buf;
12008   unsigned char const *const end = data->d_buf + data->d_size;
12009
12010   uint64_t count, page_size;
12011   if (! buf_read_ulong (core, &ptr, end, &count)
12012       || ! buf_read_ulong (core, &ptr, end, &page_size))
12013     {
12014     fail:
12015       printf ("    Not enough data in NT_FILE note.\n");
12016       return;
12017     }
12018
12019   size_t addrsize = gelf_fsize (core, ELF_T_ADDR, 1, EV_CURRENT);
12020   uint64_t maxcount = (size_t) (end - ptr) / (3 * addrsize);
12021   if (count > maxcount)
12022     goto fail;
12023
12024   /* Where file names are stored.  */
12025   unsigned char const *const fstart = ptr + 3 * count * addrsize;
12026   char const *fptr = (char *) fstart;
12027
12028   printf ("    %" PRId64 " files:\n", count);
12029   for (uint64_t i = 0; i < count; ++i)
12030     {
12031       uint64_t mstart, mend, moffset;
12032       if (! buf_read_ulong (core, &ptr, fstart, &mstart)
12033           || ! buf_read_ulong (core, &ptr, fstart, &mend)
12034           || ! buf_read_ulong (core, &ptr, fstart, &moffset))
12035         goto fail;
12036
12037       const char *fnext = memchr (fptr, '\0', (char *) end - fptr);
12038       if (fnext == NULL)
12039         goto fail;
12040
12041       int ct = printf ("      %08" PRIx64 "-%08" PRIx64
12042                        " %08" PRIx64 " %" PRId64,
12043                        mstart, mend, moffset * page_size, mend - mstart);
12044       printf ("%*s%s\n", ct > 50 ? 3 : 53 - ct, "", fptr);
12045
12046       fptr = fnext + 1;
12047     }
12048 }
12049
12050 static void
12051 handle_core_note (Ebl *ebl, const GElf_Nhdr *nhdr,
12052                   const char *name, const void *desc)
12053 {
12054   GElf_Word regs_offset;
12055   size_t nregloc;
12056   const Ebl_Register_Location *reglocs;
12057   size_t nitems;
12058   const Ebl_Core_Item *items;
12059
12060   if (! ebl_core_note (ebl, nhdr, name,
12061                        &regs_offset, &nregloc, &reglocs, &nitems, &items))
12062     return;
12063
12064   /* Pass 0 for DESCSZ when there are registers in the note,
12065      so that the ITEMS array does not describe the whole thing.
12066      For non-register notes, the actual descsz might be a multiple
12067      of the unit size, not just exactly the unit size.  */
12068   unsigned int colno = handle_core_items (ebl->elf, desc,
12069                                           nregloc == 0 ? nhdr->n_descsz : 0,
12070                                           items, nitems);
12071   if (colno != 0)
12072     putchar_unlocked ('\n');
12073
12074   colno = handle_core_registers (ebl, ebl->elf, desc + regs_offset,
12075                                  reglocs, nregloc);
12076   if (colno != 0)
12077     putchar_unlocked ('\n');
12078 }
12079
12080 static void
12081 handle_notes_data (Ebl *ebl, const GElf_Ehdr *ehdr,
12082                    GElf_Off start, Elf_Data *data)
12083 {
12084   fputs_unlocked (gettext ("  Owner          Data size  Type\n"), stdout);
12085
12086   if (data == NULL)
12087     goto bad_note;
12088
12089   size_t offset = 0;
12090   GElf_Nhdr nhdr;
12091   size_t name_offset;
12092   size_t desc_offset;
12093   while (offset < data->d_size
12094          && (offset = gelf_getnote (data, offset,
12095                                     &nhdr, &name_offset, &desc_offset)) > 0)
12096     {
12097       const char *name = nhdr.n_namesz == 0 ? "" : data->d_buf + name_offset;
12098       const char *desc = data->d_buf + desc_offset;
12099
12100       char buf[100];
12101       char buf2[100];
12102       printf (gettext ("  %-13.*s  %9" PRId32 "  %s\n"),
12103               (int) nhdr.n_namesz, name, nhdr.n_descsz,
12104               ehdr->e_type == ET_CORE
12105               ? ebl_core_note_type_name (ebl, nhdr.n_type,
12106                                          buf, sizeof (buf))
12107               : ebl_object_note_type_name (ebl, name, nhdr.n_type,
12108                                            buf2, sizeof (buf2)));
12109
12110       /* Filter out invalid entries.  */
12111       if (memchr (name, '\0', nhdr.n_namesz) != NULL
12112           /* XXX For now help broken Linux kernels.  */
12113           || 1)
12114         {
12115           if (ehdr->e_type == ET_CORE)
12116             {
12117               if (nhdr.n_type == NT_AUXV
12118                   && (nhdr.n_namesz == 4 /* Broken old Linux kernels.  */
12119                       || (nhdr.n_namesz == 5 && name[4] == '\0'))
12120                   && !memcmp (name, "CORE", 4))
12121                 handle_auxv_note (ebl, ebl->elf, nhdr.n_descsz,
12122                                   start + desc_offset);
12123               else if (nhdr.n_namesz == 5 && strcmp (name, "CORE") == 0)
12124                 switch (nhdr.n_type)
12125                   {
12126                   case NT_SIGINFO:
12127                     handle_siginfo_note (ebl->elf, nhdr.n_descsz,
12128                                          start + desc_offset);
12129                     break;
12130
12131                   case NT_FILE:
12132                     handle_file_note (ebl->elf, nhdr.n_descsz,
12133                                       start + desc_offset);
12134                     break;
12135
12136                   default:
12137                     handle_core_note (ebl, &nhdr, name, desc);
12138                   }
12139               else
12140                 handle_core_note (ebl, &nhdr, name, desc);
12141             }
12142           else
12143             ebl_object_note (ebl, name, nhdr.n_type, nhdr.n_descsz, desc);
12144         }
12145     }
12146
12147   if (offset == data->d_size)
12148     return;
12149
12150  bad_note:
12151   error (0, 0,
12152          gettext ("cannot get content of note: %s"),
12153          data != NULL ? "garbage data" : elf_errmsg (-1));
12154 }
12155
12156 static void
12157 handle_notes (Ebl *ebl, GElf_Ehdr *ehdr)
12158 {
12159   /* If we have section headers, just look for SHT_NOTE sections.
12160      In a debuginfo file, the program headers are not reliable.  */
12161   if (shnum != 0)
12162     {
12163       /* Get the section header string table index.  */
12164       size_t shstrndx;
12165       if (elf_getshdrstrndx (ebl->elf, &shstrndx) < 0)
12166         error (EXIT_FAILURE, 0,
12167                gettext ("cannot get section header string table index"));
12168
12169       Elf_Scn *scn = NULL;
12170       while ((scn = elf_nextscn (ebl->elf, scn)) != NULL)
12171         {
12172           GElf_Shdr shdr_mem;
12173           GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem);
12174
12175           if (shdr == NULL || shdr->sh_type != SHT_NOTE)
12176             /* Not what we are looking for.  */
12177             continue;
12178
12179           printf (gettext ("\
12180 \nNote section [%2zu] '%s' of %" PRIu64 " bytes at offset %#0" PRIx64 ":\n"),
12181                   elf_ndxscn (scn),
12182                   elf_strptr (ebl->elf, shstrndx, shdr->sh_name),
12183                   shdr->sh_size, shdr->sh_offset);
12184
12185           handle_notes_data (ebl, ehdr, shdr->sh_offset,
12186                              elf_getdata (scn, NULL));
12187         }
12188       return;
12189     }
12190
12191   /* We have to look through the program header to find the note
12192      sections.  There can be more than one.  */
12193   for (size_t cnt = 0; cnt < phnum; ++cnt)
12194     {
12195       GElf_Phdr mem;
12196       GElf_Phdr *phdr = gelf_getphdr (ebl->elf, cnt, &mem);
12197
12198       if (phdr == NULL || phdr->p_type != PT_NOTE)
12199         /* Not what we are looking for.  */
12200         continue;
12201
12202       printf (gettext ("\
12203 \nNote segment of %" PRIu64 " bytes at offset %#0" PRIx64 ":\n"),
12204               phdr->p_filesz, phdr->p_offset);
12205
12206       handle_notes_data (ebl, ehdr, phdr->p_offset,
12207                          elf_getdata_rawchunk (ebl->elf,
12208                                                phdr->p_offset, phdr->p_filesz,
12209                                                ELF_T_NHDR));
12210     }
12211 }
12212
12213
12214 static void
12215 hex_dump (const uint8_t *data, size_t len)
12216 {
12217   size_t pos = 0;
12218   while (pos < len)
12219     {
12220       printf ("  0x%08zx ", pos);
12221
12222       const size_t chunk = MIN (len - pos, 16);
12223
12224       for (size_t i = 0; i < chunk; ++i)
12225         if (i % 4 == 3)
12226           printf ("%02x ", data[pos + i]);
12227         else
12228           printf ("%02x", data[pos + i]);
12229
12230       if (chunk < 16)
12231         printf ("%*s", (int) ((16 - chunk) * 2 + (16 - chunk + 3) / 4), "");
12232
12233       for (size_t i = 0; i < chunk; ++i)
12234         {
12235           unsigned char b = data[pos + i];
12236           printf ("%c", isprint (b) ? b : '.');
12237         }
12238
12239       putchar ('\n');
12240       pos += chunk;
12241     }
12242 }
12243
12244 static void
12245 dump_data_section (Elf_Scn *scn, const GElf_Shdr *shdr, const char *name)
12246 {
12247   if (shdr->sh_size == 0 || shdr->sh_type == SHT_NOBITS)
12248     printf (gettext ("\nSection [%zu] '%s' has no data to dump.\n"),
12249             elf_ndxscn (scn), name);
12250   else
12251     {
12252       if (print_decompress)
12253         {
12254           /* We try to decompress the section, but keep the old shdr around
12255              so we can show both the original shdr size and the uncompressed
12256              data size.   */
12257           if ((shdr->sh_flags & SHF_COMPRESSED) != 0)
12258             {
12259               if (elf_compress (scn, 0, 0) < 0)
12260                 printf ("WARNING: %s [%zd]\n",
12261                         gettext ("Couldn't uncompress section"),
12262                         elf_ndxscn (scn));
12263             }
12264           else if (strncmp (name, ".zdebug", strlen (".zdebug")) == 0)
12265             {
12266               if (elf_compress_gnu (scn, 0, 0) < 0)
12267                 printf ("WARNING: %s [%zd]\n",
12268                         gettext ("Couldn't uncompress section"),
12269                         elf_ndxscn (scn));
12270             }
12271         }
12272
12273       Elf_Data *data = elf_rawdata (scn, NULL);
12274       if (data == NULL)
12275         error (0, 0, gettext ("cannot get data for section [%zu] '%s': %s"),
12276                elf_ndxscn (scn), name, elf_errmsg (-1));
12277       else
12278         {
12279           if (data->d_size == shdr->sh_size)
12280             printf (gettext ("\nHex dump of section [%zu] '%s', %" PRIu64
12281                              " bytes at offset %#0" PRIx64 ":\n"),
12282                     elf_ndxscn (scn), name,
12283                     shdr->sh_size, shdr->sh_offset);
12284           else
12285             printf (gettext ("\nHex dump of section [%zu] '%s', %" PRIu64
12286                              " bytes (%zd uncompressed) at offset %#0"
12287                              PRIx64 ":\n"),
12288                     elf_ndxscn (scn), name,
12289                     shdr->sh_size, data->d_size, shdr->sh_offset);
12290           hex_dump (data->d_buf, data->d_size);
12291         }
12292     }
12293 }
12294
12295 static void
12296 print_string_section (Elf_Scn *scn, const GElf_Shdr *shdr, const char *name)
12297 {
12298   if (shdr->sh_size == 0 || shdr->sh_type == SHT_NOBITS)
12299     printf (gettext ("\nSection [%zu] '%s' has no strings to dump.\n"),
12300             elf_ndxscn (scn), name);
12301   else
12302     {
12303       if (print_decompress)
12304         {
12305           /* We try to decompress the section, but keep the old shdr around
12306              so we can show both the original shdr size and the uncompressed
12307              data size.  */
12308           if ((shdr->sh_flags & SHF_COMPRESSED) != 0)
12309             {
12310               if (elf_compress (scn, 0, 0) < 0)
12311                 printf ("WARNING: %s [%zd]\n",
12312                         gettext ("Couldn't uncompress section"),
12313                         elf_ndxscn (scn));
12314             }
12315           else if (strncmp (name, ".zdebug", strlen (".zdebug")) == 0)
12316             {
12317               if (elf_compress_gnu (scn, 0, 0) < 0)
12318                 printf ("WARNING: %s [%zd]\n",
12319                         gettext ("Couldn't uncompress section"),
12320                         elf_ndxscn (scn));
12321             }
12322         }
12323
12324       Elf_Data *data = elf_rawdata (scn, NULL);
12325       if (data == NULL)
12326         error (0, 0, gettext ("cannot get data for section [%zu] '%s': %s"),
12327                elf_ndxscn (scn), name, elf_errmsg (-1));
12328       else
12329         {
12330           if (data->d_size == shdr->sh_size)
12331             printf (gettext ("\nString section [%zu] '%s' contains %" PRIu64
12332                              " bytes at offset %#0" PRIx64 ":\n"),
12333                     elf_ndxscn (scn), name,
12334                     shdr->sh_size, shdr->sh_offset);
12335           else
12336             printf (gettext ("\nString section [%zu] '%s' contains %" PRIu64
12337                              " bytes (%zd uncompressed) at offset %#0"
12338                              PRIx64 ":\n"),
12339                     elf_ndxscn (scn), name,
12340                     shdr->sh_size, data->d_size, shdr->sh_offset);
12341
12342           const char *start = data->d_buf;
12343           const char *const limit = start + data->d_size;
12344           do
12345             {
12346               const char *end = memchr (start, '\0', limit - start);
12347               const size_t pos = start - (const char *) data->d_buf;
12348               if (unlikely (end == NULL))
12349                 {
12350                   printf ("  [%6zx]- %.*s\n",
12351                           pos, (int) (limit - start), start);
12352                   break;
12353                 }
12354               printf ("  [%6zx]  %s\n", pos, start);
12355               start = end + 1;
12356             } while (start < limit);
12357         }
12358     }
12359 }
12360
12361 static void
12362 for_each_section_argument (Elf *elf, const struct section_argument *list,
12363                            void (*dump) (Elf_Scn *scn, const GElf_Shdr *shdr,
12364                                          const char *name))
12365 {
12366   /* Get the section header string table index.  */
12367   size_t shstrndx;
12368   if (elf_getshdrstrndx (elf, &shstrndx) < 0)
12369     error (EXIT_FAILURE, 0,
12370            gettext ("cannot get section header string table index"));
12371
12372   for (const struct section_argument *a = list; a != NULL; a = a->next)
12373     {
12374       Elf_Scn *scn;
12375       GElf_Shdr shdr_mem;
12376       const char *name = NULL;
12377
12378       char *endp = NULL;
12379       unsigned long int shndx = strtoul (a->arg, &endp, 0);
12380       if (endp != a->arg && *endp == '\0')
12381         {
12382           scn = elf_getscn (elf, shndx);
12383           if (scn == NULL)
12384             {
12385               error (0, 0, gettext ("\nsection [%lu] does not exist"), shndx);
12386               continue;
12387             }
12388
12389           if (gelf_getshdr (scn, &shdr_mem) == NULL)
12390             error (EXIT_FAILURE, 0, gettext ("cannot get section header: %s"),
12391                    elf_errmsg (-1));
12392           name = elf_strptr (elf, shstrndx, shdr_mem.sh_name);
12393         }
12394       else
12395         {
12396           /* Need to look up the section by name.  */
12397           scn = NULL;
12398           bool found = false;
12399           while ((scn = elf_nextscn (elf, scn)) != NULL)
12400             {
12401               if (gelf_getshdr (scn, &shdr_mem) == NULL)
12402                 continue;
12403               name = elf_strptr (elf, shstrndx, shdr_mem.sh_name);
12404               if (name == NULL)
12405                 continue;
12406               if (!strcmp (name, a->arg))
12407                 {
12408                   found = true;
12409                   (*dump) (scn, &shdr_mem, name);
12410                 }
12411             }
12412
12413           if (unlikely (!found) && !a->implicit)
12414             error (0, 0, gettext ("\nsection '%s' does not exist"), a->arg);
12415         }
12416     }
12417 }
12418
12419 static void
12420 dump_data (Ebl *ebl)
12421 {
12422   for_each_section_argument (ebl->elf, dump_data_sections, &dump_data_section);
12423 }
12424
12425 static void
12426 dump_strings (Ebl *ebl)
12427 {
12428   for_each_section_argument (ebl->elf, string_sections, &print_string_section);
12429 }
12430
12431 static void
12432 print_strings (Ebl *ebl)
12433 {
12434   /* Get the section header string table index.  */
12435   size_t shstrndx;
12436   if (unlikely (elf_getshdrstrndx (ebl->elf, &shstrndx) < 0))
12437     error (EXIT_FAILURE, 0,
12438            gettext ("cannot get section header string table index"));
12439
12440   Elf_Scn *scn;
12441   GElf_Shdr shdr_mem;
12442   const char *name;
12443   scn = NULL;
12444   while ((scn = elf_nextscn (ebl->elf, scn)) != NULL)
12445     {
12446       if (gelf_getshdr (scn, &shdr_mem) == NULL)
12447         continue;
12448
12449       if (shdr_mem.sh_type != SHT_PROGBITS
12450           || !(shdr_mem.sh_flags & SHF_STRINGS))
12451         continue;
12452
12453       name = elf_strptr (ebl->elf, shstrndx, shdr_mem.sh_name);
12454       if (name == NULL)
12455         continue;
12456
12457       print_string_section (scn, &shdr_mem, name);
12458     }
12459 }
12460
12461 static void
12462 dump_archive_index (Elf *elf, const char *fname)
12463 {
12464   size_t narsym;
12465   const Elf_Arsym *arsym = elf_getarsym (elf, &narsym);
12466   if (arsym == NULL)
12467     {
12468       int result = elf_errno ();
12469       if (unlikely (result != ELF_E_NO_INDEX))
12470         error (EXIT_FAILURE, 0,
12471                gettext ("cannot get symbol index of archive '%s': %s"),
12472                fname, elf_errmsg (result));
12473       else
12474         printf (gettext ("\nArchive '%s' has no symbol index\n"), fname);
12475       return;
12476     }
12477
12478   printf (gettext ("\nIndex of archive '%s' has %zu entries:\n"),
12479           fname, narsym);
12480
12481   size_t as_off = 0;
12482   for (const Elf_Arsym *s = arsym; s < &arsym[narsym - 1]; ++s)
12483     {
12484       if (s->as_off != as_off)
12485         {
12486           as_off = s->as_off;
12487
12488           Elf *subelf = NULL;
12489           if (unlikely (elf_rand (elf, as_off) == 0)
12490               || unlikely ((subelf = elf_begin (-1, ELF_C_READ_MMAP, elf))
12491                            == NULL))
12492 #if __GLIBC__ < 2 || (__GLIBC__ == 2 && __GLIBC_MINOR__ < 7)
12493             while (1)
12494 #endif
12495               error (EXIT_FAILURE, 0,
12496                      gettext ("cannot extract member at offset %zu in '%s': %s"),
12497                      as_off, fname, elf_errmsg (-1));
12498
12499           const Elf_Arhdr *h = elf_getarhdr (subelf);
12500
12501           printf (gettext ("Archive member '%s' contains:\n"), h->ar_name);
12502
12503           elf_end (subelf);
12504         }
12505
12506       printf ("\t%s\n", s->as_name);
12507     }
12508 }
12509
12510 #include "debugpred.h"