Add DWARF 2.1 attributes
[external/binutils.git] / binutils / readelf.c
1 /* readelf.c -- display contents of an ELF format file
2    Copyright 1998, 1999, 2000, 2001 Free Software Foundation, Inc.
3
4    Originally developed by Eric Youngdale <eric@andante.jic.com>
5    Modifications by Nick Clifton <nickc@redhat.com>
6
7    This file is part of GNU Binutils.
8
9    This program is free software; you can redistribute it and/or modify
10    it under the terms of the GNU General Public License as published by
11    the Free Software Foundation; either version 2 of the License, or
12    (at your option) any later version.
13
14    This program is distributed in the hope that it will be useful,
15    but WITHOUT ANY WARRANTY; without even the implied warranty of
16    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17    GNU General Public License for more details.
18
19    You should have received a copy of the GNU General Public License
20    along with this program; if not, write to the Free Software
21    Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
22    02111-1307, USA.  */
23 \f
24
25 #include <assert.h>
26 #include <sys/types.h>
27 #include <sys/stat.h>
28 #include <stdio.h>
29 #include <time.h>
30
31 #if __GNUC__ >= 2
32 /* Define BFD64 here, even if our default architecture is 32 bit ELF
33    as this will allow us to read in and parse 64bit and 32bit ELF files.
34    Only do this if we belive that the compiler can support a 64 bit
35    data type.  For now we only rely on GCC being able to do this.  */
36 #define BFD64
37 #endif
38
39 #include "bfd.h"
40
41 #include "elf/common.h"
42 #include "elf/external.h"
43 #include "elf/internal.h"
44 #include "elf/dwarf2.h"
45
46 /* The following headers use the elf/reloc-macros.h file to
47    automatically generate relocation recognition functions
48    such as elf_mips_reloc_type()  */
49
50 #define RELOC_MACROS_GEN_FUNC
51
52 #include "elf/i386.h"
53 #include "elf/v850.h"
54 #include "elf/ppc.h"
55 #include "elf/mips.h"
56 #include "elf/alpha.h"
57 #include "elf/arm.h"
58 #include "elf/m68k.h"
59 #include "elf/sparc.h"
60 #include "elf/m32r.h"
61 #include "elf/d10v.h"
62 #include "elf/d30v.h"
63 #include "elf/sh.h"
64 #include "elf/mn10200.h"
65 #include "elf/mn10300.h"
66 #include "elf/hppa.h"
67 #include "elf/arc.h"
68 #include "elf/fr30.h"
69 #include "elf/mcore.h"
70 #include "elf/i960.h"
71 #include "elf/pj.h"
72 #include "elf/avr.h"
73 #include "elf/ia64.h"
74 #include "elf/cris.h"
75 #include "elf/i860.h"
76 #include "elf/x86-64.h"
77 #include "elf/s390.h"
78
79 #include "bucomm.h"
80 #include "getopt.h"
81
82 char *                  program_name = "readelf";
83 unsigned int            dynamic_addr;
84 bfd_size_type           dynamic_size;
85 unsigned int            rela_addr;
86 unsigned int            rela_size;
87 char *                  dynamic_strings;
88 char *                  string_table;
89 unsigned long           string_table_length;
90 unsigned long           num_dynamic_syms;
91 Elf_Internal_Sym *      dynamic_symbols;
92 Elf_Internal_Syminfo *  dynamic_syminfo;
93 unsigned long           dynamic_syminfo_offset;
94 unsigned int            dynamic_syminfo_nent;
95 char                    program_interpreter [64];
96 int                     dynamic_info[DT_JMPREL + 1];
97 int                     version_info[16];
98 int                     loadaddr = 0;
99 Elf_Internal_Ehdr       elf_header;
100 Elf_Internal_Shdr *     section_headers;
101 Elf_Internal_Dyn *      dynamic_segment;
102 int                     show_name;
103 int                     do_dynamic;
104 int                     do_syms;
105 int                     do_reloc;
106 int                     do_sections;
107 int                     do_segments;
108 int                     do_unwind;
109 int                     do_using_dynamic;
110 int                     do_header;
111 int                     do_dump;
112 int                     do_version;
113 int                     do_histogram;
114 int                     do_debugging;
115 int                     do_debug_info;
116 int                     do_debug_abbrevs;
117 int                     do_debug_lines;
118 int                     do_debug_pubnames;
119 int                     do_debug_aranges;
120 int                     do_debug_frames;
121 int                     do_debug_frames_interp;
122 int                     do_arch;
123 int                     do_notes;
124 int                     is_32bit_elf;
125
126 /* A dynamic array of flags indicating which sections require dumping.  */
127 char *                  dump_sects = NULL;
128 unsigned int            num_dump_sects = 0;
129
130 #define HEX_DUMP        (1 << 0)
131 #define DISASS_DUMP     (1 << 1)
132 #define DEBUG_DUMP      (1 << 2)
133
134 /* How to rpint a vma value.  */
135 typedef enum print_mode
136 {
137   HEX,
138   DEC,
139   DEC_5,
140   UNSIGNED,
141   PREFIX_HEX,
142   FULL_HEX,
143   LONG_HEX
144 }
145 print_mode;
146
147 /* Forward declarations for dumb compilers.  */
148 static void               print_vma                   PARAMS ((bfd_vma, print_mode));
149 static bfd_vma (*         byte_get)                   PARAMS ((unsigned char *, int));
150 static bfd_vma            byte_get_little_endian      PARAMS ((unsigned char *, int));
151 static bfd_vma            byte_get_big_endian         PARAMS ((unsigned char *, int));
152 static const char *       get_mips_dynamic_type       PARAMS ((unsigned long));
153 static const char *       get_sparc64_dynamic_type    PARAMS ((unsigned long));
154 static const char *       get_parisc_dynamic_type     PARAMS ((unsigned long));
155 static const char *       get_dynamic_type            PARAMS ((unsigned long));
156 static int                slurp_rela_relocs           PARAMS ((FILE *, unsigned long, unsigned long, Elf_Internal_Rela **, unsigned long *));
157 static int                slurp_rel_relocs            PARAMS ((FILE *, unsigned long, unsigned long, Elf_Internal_Rel **, unsigned long *));
158 static int                dump_relocations            PARAMS ((FILE *, unsigned long, unsigned long, Elf_Internal_Sym *, unsigned long, char *, int));
159 static char *             get_file_type               PARAMS ((unsigned));
160 static char *             get_machine_name            PARAMS ((unsigned));
161 static void               decode_ARM_machine_flags    PARAMS ((unsigned, char []));
162 static char *             get_machine_flags           PARAMS ((unsigned, unsigned));
163 static const char *       get_mips_segment_type       PARAMS ((unsigned long));
164 static const char *       get_parisc_segment_type     PARAMS ((unsigned long));
165 static const char *       get_ia64_segment_type       PARAMS ((unsigned long));
166 static const char *       get_segment_type            PARAMS ((unsigned long));
167 static const char *       get_mips_section_type_name  PARAMS ((unsigned int));
168 static const char *       get_parisc_section_type_name PARAMS ((unsigned int));
169 static const char *       get_ia64_section_type_name  PARAMS ((unsigned int));
170 static const char *       get_section_type_name       PARAMS ((unsigned int));
171 static const char *       get_symbol_binding          PARAMS ((unsigned int));
172 static const char *       get_symbol_type             PARAMS ((unsigned int));
173 static const char *       get_symbol_visibility       PARAMS ((unsigned int));
174 static const char *       get_symbol_index_type       PARAMS ((unsigned int));
175 static const char *       get_dynamic_flags           PARAMS ((bfd_vma));
176 static void               usage                       PARAMS ((void));
177 static void               parse_args                  PARAMS ((int, char **));
178 static int                process_file_header         PARAMS ((void));
179 static int                process_program_headers     PARAMS ((FILE *));
180 static int                process_section_headers     PARAMS ((FILE *));
181 static int                process_unwind              PARAMS ((FILE *));
182 static void               dynamic_segment_mips_val    PARAMS ((Elf_Internal_Dyn *));
183 static void               dynamic_segment_parisc_val  PARAMS ((Elf_Internal_Dyn *));
184 static int                process_dynamic_segment     PARAMS ((FILE *));
185 static int                process_symbol_table        PARAMS ((FILE *));
186 static int                process_section_contents    PARAMS ((FILE *));
187 static void               process_file                PARAMS ((char *));
188 static int                process_relocs              PARAMS ((FILE *));
189 static int                process_version_sections    PARAMS ((FILE *));
190 static char *             get_ver_flags               PARAMS ((unsigned int));
191 static int                get_32bit_section_headers   PARAMS ((FILE *));
192 static int                get_64bit_section_headers   PARAMS ((FILE *));
193 static int                get_32bit_program_headers   PARAMS ((FILE *, Elf_Internal_Phdr *));
194 static int                get_64bit_program_headers   PARAMS ((FILE *, Elf_Internal_Phdr *));
195 static int                get_file_header             PARAMS ((FILE *));
196 static Elf_Internal_Sym * get_32bit_elf_symbols       PARAMS ((FILE *, unsigned long, unsigned long));
197 static Elf_Internal_Sym * get_64bit_elf_symbols       PARAMS ((FILE *, unsigned long, unsigned long));
198 static const char *       get_elf_section_flags       PARAMS ((bfd_vma));
199 static int *              get_dynamic_data            PARAMS ((FILE *, unsigned int));
200 static int                get_32bit_dynamic_segment   PARAMS ((FILE *));
201 static int                get_64bit_dynamic_segment   PARAMS ((FILE *));
202 #ifdef SUPPORT_DISASSEMBLY
203 static int                disassemble_section         PARAMS ((Elf32_Internal_Shdr *, FILE *));
204 #endif
205 static int                dump_section                PARAMS ((Elf32_Internal_Shdr *, FILE *));
206 static int                display_debug_section       PARAMS ((Elf32_Internal_Shdr *, FILE *));
207 static int                display_debug_info          PARAMS ((Elf32_Internal_Shdr *, unsigned char *, FILE *));
208 static int                display_debug_not_supported PARAMS ((Elf32_Internal_Shdr *, unsigned char *, FILE *));
209 static int                display_debug_lines         PARAMS ((Elf32_Internal_Shdr *, unsigned char *, FILE *));
210 static int                display_debug_abbrev        PARAMS ((Elf32_Internal_Shdr *, unsigned char *, FILE *));
211 static int                display_debug_aranges       PARAMS ((Elf32_Internal_Shdr *, unsigned char *, FILE *));
212 static int                display_debug_frames        PARAMS ((Elf32_Internal_Shdr *, unsigned char *, FILE *));
213 static unsigned char *    process_abbrev_section      PARAMS ((unsigned char *, unsigned char *));
214 static unsigned long      read_leb128                 PARAMS ((unsigned char *, int *, int));
215 static int                process_extended_line_op    PARAMS ((unsigned char *, int, int));
216 static void               reset_state_machine         PARAMS ((int));
217 static char *             get_TAG_name                PARAMS ((unsigned long));
218 static char *             get_AT_name                 PARAMS ((unsigned long));
219 static char *             get_FORM_name               PARAMS ((unsigned long));
220 static void               free_abbrevs                PARAMS ((void));
221 static void               add_abbrev                  PARAMS ((unsigned long, unsigned long, int));
222 static void               add_abbrev_attr             PARAMS ((unsigned long, unsigned long));
223 static unsigned char *    read_and_display_attr       PARAMS ((unsigned long, unsigned long, unsigned char *, unsigned long, unsigned long));
224 static unsigned char *    display_block               PARAMS ((unsigned char *, unsigned long));
225 static void               decode_location_expression  PARAMS ((unsigned char *, unsigned int, unsigned long));
226 static void               request_dump                PARAMS ((unsigned int, char));
227 static const char *       get_elf_class               PARAMS ((unsigned char));
228 static const char *       get_data_encoding           PARAMS ((unsigned char));
229 static const char *       get_osabi_name              PARAMS ((unsigned char));
230 static int                guess_is_rela               PARAMS ((unsigned long));
231 static char *             get_note_type                  PARAMS ((unsigned int));
232 static int                process_note                   PARAMS ((Elf32_Internal_Note *));
233 static int                process_corefile_note_segment  PARAMS ((FILE *, bfd_vma, bfd_vma));
234 static int                process_corefile_note_segments PARAMS ((FILE *));
235 static int                process_corefile_contents      PARAMS ((FILE *));
236
237 typedef int Elf32_Word;
238
239 #ifndef TRUE
240 #define TRUE     1
241 #define FALSE    0
242 #endif
243 #define UNKNOWN -1
244
245 #define SECTION_NAME(X) ((X) == NULL ? "<none>" : \
246                                  ((X)->sh_name >= string_table_length \
247                                   ? "<corrupt>" : string_table + (X)->sh_name))
248
249 #define DT_VERSIONTAGIDX(tag)   (DT_VERNEEDNUM - (tag)) /* Reverse order! */
250
251 #define BYTE_GET(field) byte_get (field, sizeof (field))
252
253 /* If we can support a 64 bit data type then BFD64 should be defined
254    and sizeof (bfd_vma) == 8.  In this case when translating from an
255    external 8 byte field to an internal field, we can assume that the
256    internal field is also 8 bytes wide and so we can extract all the data.
257    If, however, BFD64 is not defined, then we must assume that the
258    internal data structure only has 4 byte wide fields that are the
259    equivalent of the 8 byte wide external counterparts, and so we must
260    truncate the data.  */
261 #ifdef  BFD64
262 #define BYTE_GET8(field)        byte_get (field, -8)
263 #else
264 #define BYTE_GET8(field)        byte_get (field, 8)
265 #endif
266
267 #define NUM_ELEM(array) (sizeof (array) / sizeof ((array)[0]))
268
269 #define GET_ELF_SYMBOLS(file, offset, size)                     \
270   (is_32bit_elf ? get_32bit_elf_symbols (file, offset, size)    \
271    : get_64bit_elf_symbols (file, offset, size))
272
273
274 #ifdef ANSI_PROTOTYPES
275 static void
276 error (const char * message, ...)
277 {
278   va_list args;
279
280   fprintf (stderr, _("%s: Error: "), program_name);
281   va_start (args, message);
282   vfprintf (stderr, message, args);
283   va_end (args);
284   return;
285 }
286
287 static void
288 warn (const char * message, ...)
289 {
290   va_list args;
291
292   fprintf (stderr, _("%s: Warning: "), program_name);
293   va_start (args, message);
294   vfprintf (stderr, message, args);
295   va_end (args);
296   return;
297 }
298 #else
299 static void
300 error (va_alist)
301      va_dcl
302 {
303   char * message;
304   va_list args;
305
306   fprintf (stderr, _("%s: Error: "), program_name);
307   va_start (args);
308   message = va_arg (args, char *);
309   vfprintf (stderr, message, args);
310   va_end (args);
311   return;
312 }
313
314 static void
315 warn (va_alist)
316      va_dcl
317 {
318   char * message;
319   va_list args;
320
321   fprintf (stderr, _("%s: Warning: "), program_name);
322   va_start (args);
323   message = va_arg (args, char *);
324   vfprintf (stderr, message, args);
325   va_end (args);
326   return;
327 }
328 #endif
329
330 static PTR get_data PARAMS ((PTR, FILE *, long, size_t, const char *));
331
332 static PTR
333 get_data (var, file, offset, size, reason)
334      PTR var;
335      FILE *file;
336      long offset;
337      size_t size;
338      const char *reason;
339 {
340   PTR mvar;
341
342   if (size == 0)
343     return NULL;
344
345   if (fseek (file, offset, SEEK_SET))
346     {
347       error (_("Unable to seek to %x for %s\n"), offset, reason);
348       return NULL;
349     }
350
351   mvar = var;
352   if (mvar == NULL)
353     {
354       mvar = (PTR) malloc (size);
355
356       if (mvar == NULL)
357         {
358           error (_("Out of memory allocating %d bytes for %s\n"),
359                  size, reason);
360           return NULL;
361         }
362     }
363
364   if (fread (mvar, size, 1, file) != 1)
365     {
366       error (_("Unable to read in %d bytes of %s\n"), size, reason);
367       if (mvar != var)
368         free (mvar);
369       return NULL;
370     }
371
372   return mvar;
373 }
374
375 static bfd_vma
376 byte_get_little_endian (field, size)
377      unsigned char * field;
378      int             size;
379 {
380   switch (size)
381     {
382     case 1:
383       return * field;
384
385     case 2:
386       return  ((unsigned int) (field [0]))
387         |    (((unsigned int) (field [1])) << 8);
388
389 #ifndef BFD64
390     case 8:
391       /* We want to extract data from an 8 byte wide field and
392          place it into a 4 byte wide field.  Since this is a little
393          endian source we can juts use the 4 byte extraction code.  */
394       /* Fall through.  */
395 #endif
396     case 4:
397       return  ((unsigned long) (field [0]))
398         |    (((unsigned long) (field [1])) << 8)
399         |    (((unsigned long) (field [2])) << 16)
400         |    (((unsigned long) (field [3])) << 24);
401
402 #ifdef BFD64
403     case 8:
404     case -8:
405       /* This is a special case, generated by the BYTE_GET8 macro.
406          It means that we are loading an 8 byte value from a field
407          in an external structure into an 8 byte value in a field
408          in an internal strcuture.  */
409       return  ((bfd_vma) (field [0]))
410         |    (((bfd_vma) (field [1])) << 8)
411         |    (((bfd_vma) (field [2])) << 16)
412         |    (((bfd_vma) (field [3])) << 24)
413         |    (((bfd_vma) (field [4])) << 32)
414         |    (((bfd_vma) (field [5])) << 40)
415         |    (((bfd_vma) (field [6])) << 48)
416         |    (((bfd_vma) (field [7])) << 56);
417 #endif
418     default:
419       error (_("Unhandled data length: %d\n"), size);
420       abort ();
421     }
422 }
423
424 /* Print a VMA value.  */
425 static void
426 print_vma (vma, mode)
427      bfd_vma vma;
428      print_mode mode;
429 {
430 #ifdef BFD64
431   if (is_32bit_elf)
432 #endif
433     {
434       switch (mode)
435         {
436         case FULL_HEX: printf ("0x"); /* drop through */
437         case LONG_HEX: printf ("%8.8lx", (unsigned long) vma); break;
438         case PREFIX_HEX: printf ("0x"); /* drop through */
439         case HEX: printf ("%lx", (unsigned long) vma); break;
440         case DEC: printf ("%ld", (unsigned long) vma); break;
441         case DEC_5: printf ("%5ld", (long) vma); break;
442         case UNSIGNED: printf ("%lu", (unsigned long) vma); break;
443         }
444     }
445 #ifdef BFD64
446   else
447     {
448       switch (mode)
449         {
450         case FULL_HEX:
451           printf ("0x");
452           /* drop through */
453
454         case LONG_HEX:
455           printf_vma (vma);
456           break;
457
458         case PREFIX_HEX:
459           printf ("0x");
460           /* drop through */
461
462         case HEX:
463 #if BFD_HOST_64BIT_LONG
464           printf ("%lx", vma);
465 #else
466           if (_bfd_int64_high (vma))
467             printf ("%lx%lx", _bfd_int64_high (vma), _bfd_int64_low (vma));
468           else
469             printf ("%lx", _bfd_int64_low (vma));
470 #endif
471           break;
472
473         case DEC:
474 #if BFD_HOST_64BIT_LONG
475           printf ("%ld", vma);
476 #else
477           if (_bfd_int64_high (vma))
478             /* ugg */
479             printf ("++%ld", _bfd_int64_low (vma));
480           else
481             printf ("%ld", _bfd_int64_low (vma));
482 #endif
483           break;
484
485         case DEC_5:
486 #if BFD_HOST_64BIT_LONG
487           printf ("%5ld", vma);
488 #else
489           if (_bfd_int64_high (vma))
490             /* ugg */
491             printf ("++%ld", _bfd_int64_low (vma));
492           else
493             printf ("%5ld", _bfd_int64_low (vma));
494 #endif
495           break;
496
497         case UNSIGNED:
498 #if BFD_HOST_64BIT_LONG
499           printf ("%lu", vma);
500 #else
501           if (_bfd_int64_high (vma))
502             /* ugg */
503             printf ("++%lu", _bfd_int64_low (vma));
504           else
505             printf ("%lu", _bfd_int64_low (vma));
506 #endif
507           break;
508         }
509     }
510 #endif
511 }
512
513 static bfd_vma
514 byte_get_big_endian (field, size)
515      unsigned char * field;
516      int             size;
517 {
518   switch (size)
519     {
520     case 1:
521       return * field;
522
523     case 2:
524       return ((unsigned int) (field [1])) | (((int) (field [0])) << 8);
525
526     case 4:
527       return ((unsigned long) (field [3]))
528         |   (((unsigned long) (field [2])) << 8)
529         |   (((unsigned long) (field [1])) << 16)
530         |   (((unsigned long) (field [0])) << 24);
531
532 #ifndef BFD64
533     case 8:
534       /* Although we are extracing data from an 8 byte wide field, we
535          are returning only 4 bytes of data.  */
536       return ((unsigned long) (field [7]))
537         |   (((unsigned long) (field [6])) << 8)
538         |   (((unsigned long) (field [5])) << 16)
539         |   (((unsigned long) (field [4])) << 24);
540 #else
541     case 8:
542     case -8:
543       /* This is a special case, generated by the BYTE_GET8 macro.
544          It means that we are loading an 8 byte value from a field
545          in an external structure into an 8 byte value in a field
546          in an internal strcuture.  */
547       return ((bfd_vma) (field [7]))
548         |   (((bfd_vma) (field [6])) << 8)
549         |   (((bfd_vma) (field [5])) << 16)
550         |   (((bfd_vma) (field [4])) << 24)
551         |   (((bfd_vma) (field [3])) << 32)
552         |   (((bfd_vma) (field [2])) << 40)
553         |   (((bfd_vma) (field [1])) << 48)
554         |   (((bfd_vma) (field [0])) << 56);
555 #endif
556
557     default:
558       error (_("Unhandled data length: %d\n"), size);
559       abort ();
560     }
561 }
562
563 /* Guess the relocation size commonly used by the specific machines.  */
564
565 static int
566 guess_is_rela (e_machine)
567      unsigned long e_machine;
568 {
569   switch (e_machine)
570     {
571       /* Targets that use REL relocations.  */
572     case EM_ARM:
573     case EM_386:
574     case EM_486:
575     case EM_960:
576     case EM_CYGNUS_M32R:
577     case EM_CYGNUS_D10V:
578     case EM_MIPS:
579     case EM_MIPS_RS3_LE:
580       return FALSE;
581
582       /* Targets that use RELA relocations.  */
583     case EM_68K:
584     case EM_SPARC32PLUS:
585     case EM_SPARCV9:
586     case EM_SPARC:
587     case EM_PPC:
588     case EM_CYGNUS_V850:
589     case EM_CYGNUS_D30V:
590     case EM_CYGNUS_MN10200:
591     case EM_CYGNUS_MN10300:
592     case EM_CYGNUS_FR30:
593     case EM_SH:
594     case EM_ALPHA:
595     case EM_MCORE:
596     case EM_IA_64:
597     case EM_AVR:
598     case EM_CRIS:
599     case EM_860:
600     case EM_X86_64:
601     case EM_S390:
602     case EM_S390_OLD:
603       return TRUE;
604
605     case EM_MMA:
606     case EM_PCP:
607     case EM_NCPU:
608     case EM_NDR1:
609     case EM_STARCORE:
610     case EM_ME16:
611     case EM_ST100:
612     case EM_TINYJ:
613     case EM_FX66:
614     case EM_ST9PLUS:
615     case EM_ST7:
616     case EM_68HC16:
617     case EM_68HC11:
618     case EM_68HC08:
619     case EM_68HC05:
620     case EM_SVX:
621     case EM_ST19:
622     case EM_VAX:
623     default:
624       warn (_("Don't know about relocations on this machine architecture\n"));
625       return FALSE;
626     }
627 }
628
629 static int
630 slurp_rela_relocs (file, rel_offset, rel_size, relasp, nrelasp)
631      FILE *file;
632      unsigned long rel_offset;
633      unsigned long rel_size;
634      Elf_Internal_Rela **relasp;
635      unsigned long *nrelasp;
636 {
637   Elf_Internal_Rela *relas;
638   unsigned long nrelas;
639   unsigned int i;
640
641   if (is_32bit_elf)
642     {
643       Elf32_External_Rela * erelas;
644
645       erelas = (Elf32_External_Rela *) get_data (NULL, file, rel_offset,
646                                                  rel_size, _("relocs"));
647       if (!erelas)
648         return 0;
649
650       nrelas = rel_size / sizeof (Elf32_External_Rela);
651
652       relas = (Elf_Internal_Rela *)
653         malloc (nrelas * sizeof (Elf_Internal_Rela));
654
655       if (relas == NULL)
656         {
657           error(_("out of memory parsing relocs"));
658           return 0;
659         }
660
661       for (i = 0; i < nrelas; i++)
662         {
663           relas[i].r_offset = BYTE_GET (erelas[i].r_offset);
664           relas[i].r_info   = BYTE_GET (erelas[i].r_info);
665           relas[i].r_addend = BYTE_GET (erelas[i].r_addend);
666         }
667
668       free (erelas);
669     }
670   else
671     {
672       Elf64_External_Rela * erelas;
673
674       erelas = (Elf64_External_Rela *) get_data (NULL, file, rel_offset,
675                                                  rel_size, _("relocs"));
676       if (!erelas)
677         return 0;
678
679       nrelas = rel_size / sizeof (Elf64_External_Rela);
680
681       relas = (Elf_Internal_Rela *)
682         malloc (nrelas * sizeof (Elf_Internal_Rela));
683
684       if (relas == NULL)
685         {
686           error(_("out of memory parsing relocs"));
687           return 0;
688         }
689
690       for (i = 0; i < nrelas; i++)
691         {
692           relas[i].r_offset = BYTE_GET8 (erelas[i].r_offset);
693           relas[i].r_info   = BYTE_GET8 (erelas[i].r_info);
694           relas[i].r_addend = BYTE_GET8 (erelas[i].r_addend);
695         }
696
697       free (erelas);
698     }
699   *relasp = relas;
700   *nrelasp = nrelas;
701   return 1;
702 }
703
704 static int
705 slurp_rel_relocs (file, rel_offset, rel_size, relsp, nrelsp)
706      FILE *file;
707      unsigned long rel_offset;
708      unsigned long rel_size;
709      Elf_Internal_Rel **relsp;
710      unsigned long *nrelsp;
711 {
712   Elf_Internal_Rel *rels;
713   unsigned long nrels;
714   unsigned int i;
715
716   if (is_32bit_elf)
717     {
718       Elf32_External_Rel * erels;
719
720       erels = (Elf32_External_Rel *) get_data (NULL, file, rel_offset,
721                                                rel_size, _("relocs"));
722       if (!erels)
723         return 0;
724
725       nrels = rel_size / sizeof (Elf32_External_Rel);
726
727       rels = (Elf_Internal_Rel *) malloc (nrels * sizeof (Elf_Internal_Rel));
728
729       if (rels == NULL)
730         {
731           error(_("out of memory parsing relocs"));
732           return 0;
733         }
734
735       for (i = 0; i < nrels; i++)
736         {
737           rels[i].r_offset = BYTE_GET (erels[i].r_offset);
738           rels[i].r_info   = BYTE_GET (erels[i].r_info);
739         }
740
741       free (erels);
742     }
743   else
744     {
745       Elf64_External_Rel * erels;
746
747       erels = (Elf64_External_Rel *) get_data (NULL, file, rel_offset,
748                                                rel_size, _("relocs"));
749       if (!erels)
750         return 0;
751
752       nrels = rel_size / sizeof (Elf64_External_Rel);
753
754       rels = (Elf_Internal_Rel *) malloc (nrels * sizeof (Elf_Internal_Rel));
755
756       if (rels == NULL)
757         {
758           error(_("out of memory parsing relocs"));
759           return 0;
760         }
761
762       for (i = 0; i < nrels; i++)
763         {
764           rels[i].r_offset = BYTE_GET8 (erels[i].r_offset);
765           rels[i].r_info   = BYTE_GET8 (erels[i].r_info);
766         }
767
768       free (erels);
769     }
770   *relsp = rels;
771   *nrelsp = nrels;
772   return 1;
773 }
774
775 /* Display the contents of the relocation data found at the specified offset.  */
776 static int
777 dump_relocations (file, rel_offset, rel_size, symtab, nsyms, strtab, is_rela)
778      FILE *             file;
779      unsigned long      rel_offset;
780      unsigned long      rel_size;
781      Elf_Internal_Sym * symtab;
782      unsigned long      nsyms;
783      char *             strtab;
784      int                is_rela;
785 {
786   unsigned int        i;
787   Elf_Internal_Rel *  rels;
788   Elf_Internal_Rela * relas;
789
790
791   if (is_rela == UNKNOWN)
792     is_rela = guess_is_rela (elf_header.e_machine);
793
794   if (is_rela)
795     {
796       if (!slurp_rela_relocs (file, rel_offset, rel_size, &relas, &rel_size))
797         return 0;
798     }
799   else
800     {
801       if (!slurp_rel_relocs (file, rel_offset, rel_size, &rels, &rel_size))
802         return 0;
803     }
804
805   if (is_rela)
806     printf
807       (_("  Offset    Info  Type            Symbol's Value  Symbol's Name          Addend\n"));
808   else
809     printf
810       (_("  Offset    Info  Type            Symbol's Value  Symbol's Name\n"));
811
812   for (i = 0; i < rel_size; i++)
813     {
814       const char * rtype;
815       bfd_vma      offset;
816       bfd_vma      info;
817       bfd_vma      symtab_index;
818       bfd_vma      type;
819
820       if (is_rela)
821         {
822           offset = relas [i].r_offset;
823           info   = relas [i].r_info;
824         }
825       else
826         {
827           offset = rels [i].r_offset;
828           info   = rels [i].r_info;
829         }
830
831       if (is_32bit_elf)
832         {
833           type         = ELF32_R_TYPE (info);
834           symtab_index = ELF32_R_SYM  (info);
835         }
836       else
837         {
838           if (elf_header.e_machine == EM_SPARCV9)
839             type       = ELF64_R_TYPE_ID (info);
840           else
841             type       = ELF64_R_TYPE (info);
842           /* The #ifdef BFD64 below is to prevent a compile time warning.
843              We know that if we do not have a 64 bit data type that we
844              will never execute this code anyway.  */
845 #ifdef BFD64
846           symtab_index = ELF64_R_SYM  (info);
847 #endif
848         }
849
850 #ifdef _bfd_int64_low
851       printf ("  %8.8lx  %5.5lx ", _bfd_int64_low (offset), _bfd_int64_low (info));
852 #else
853       printf ("  %8.8lx  %5.5lx ", offset, info);
854 #endif
855
856       switch (elf_header.e_machine)
857         {
858         default:
859           rtype = NULL;
860           break;
861
862         case EM_CYGNUS_M32R:
863           rtype = elf_m32r_reloc_type (type);
864           break;
865
866         case EM_386:
867         case EM_486:
868           rtype = elf_i386_reloc_type (type);
869           break;
870
871         case EM_68K:
872           rtype = elf_m68k_reloc_type (type);
873           break;
874
875         case EM_960:
876           rtype = elf_i960_reloc_type (type);
877           break;
878
879         case EM_AVR:
880           rtype = elf_avr_reloc_type (type);
881           break;
882
883         case EM_OLD_SPARCV9:
884         case EM_SPARC32PLUS:
885         case EM_SPARCV9:
886         case EM_SPARC:
887           rtype = elf_sparc_reloc_type (type);
888           break;
889
890         case EM_CYGNUS_V850:
891           rtype = v850_reloc_type (type);
892           break;
893
894         case EM_CYGNUS_D10V:
895           rtype = elf_d10v_reloc_type (type);
896           break;
897
898         case EM_CYGNUS_D30V:
899           rtype = elf_d30v_reloc_type (type);
900           break;
901
902         case EM_SH:
903           rtype = elf_sh_reloc_type (type);
904           break;
905
906         case EM_CYGNUS_MN10300:
907           rtype = elf_mn10300_reloc_type (type);
908           break;
909
910         case EM_CYGNUS_MN10200:
911           rtype = elf_mn10200_reloc_type (type);
912           break;
913
914         case EM_CYGNUS_FR30:
915           rtype = elf_fr30_reloc_type (type);
916           break;
917
918         case EM_MCORE:
919           rtype = elf_mcore_reloc_type (type);
920           break;
921
922         case EM_PPC:
923           rtype = elf_ppc_reloc_type (type);
924           break;
925
926         case EM_MIPS:
927         case EM_MIPS_RS3_LE:
928           rtype = elf_mips_reloc_type (type);
929           break;
930
931         case EM_ALPHA:
932           rtype = elf_alpha_reloc_type (type);
933           break;
934
935         case EM_ARM:
936           rtype = elf_arm_reloc_type (type);
937           break;
938
939         case EM_CYGNUS_ARC:
940         case EM_ARC:
941           rtype = elf_arc_reloc_type (type);
942           break;
943
944         case EM_PARISC:
945           rtype = elf_hppa_reloc_type (type);
946           break;
947
948         case EM_PJ:
949           rtype = elf_pj_reloc_type (type);
950           break;
951         case EM_IA_64:
952           rtype = elf_ia64_reloc_type (type);
953           break;
954
955         case EM_CRIS:
956           rtype = elf_cris_reloc_type (type);
957           break;
958
959         case EM_860:
960           rtype = elf_i860_reloc_type (type);
961           break;
962
963         case EM_X86_64:
964           rtype = elf_x86_64_reloc_type (type);
965           break;
966
967         case EM_S390_OLD:
968         case EM_S390:
969           rtype = elf_s390_reloc_type (type);
970           break;
971         }
972
973       if (rtype == NULL)
974 #ifdef _bfd_int64_low
975         printf (_("unrecognised: %-7lx"), _bfd_int64_low (type));
976 #else
977         printf (_("unrecognised: %-7lx"), type);
978 #endif
979       else
980         printf ("%-21.21s", rtype);
981
982       if (symtab_index)
983         {
984           if (symtab == NULL || symtab_index >= nsyms)
985             printf (" bad symbol index: %08lx", (unsigned long) symtab_index);
986           else
987             {
988               Elf_Internal_Sym * psym;
989
990               psym = symtab + symtab_index;
991
992               printf (" ");
993               print_vma (psym->st_value, LONG_HEX);
994               printf ("  ");
995
996               if (psym->st_name == 0)
997                 printf ("%-25.25s",
998                         SECTION_NAME (section_headers + psym->st_shndx));
999               else if (strtab == NULL)
1000                 printf (_("<string table index %3ld>"), psym->st_name);
1001               else
1002                 printf ("%-25.25s", strtab + psym->st_name);
1003
1004               if (is_rela)
1005                 printf (" + %lx", (unsigned long) relas [i].r_addend);
1006             }
1007         }
1008       else if (is_rela)
1009         {
1010           printf ("%*c", is_32bit_elf ? 34 : 26, ' ');
1011           print_vma (relas[i].r_addend, LONG_HEX);
1012         }
1013
1014       if (elf_header.e_machine == EM_SPARCV9
1015           && !strcmp (rtype, "R_SPARC_OLO10"))
1016         printf (" + %lx", (unsigned long) ELF64_R_TYPE_DATA (info));
1017
1018       putchar ('\n');
1019     }
1020
1021   if (is_rela)
1022     free (relas);
1023   else
1024     free (rels);
1025
1026   return 1;
1027 }
1028
1029 static const char *
1030 get_mips_dynamic_type (type)
1031      unsigned long type;
1032 {
1033   switch (type)
1034     {
1035     case DT_MIPS_RLD_VERSION: return "MIPS_RLD_VERSION";
1036     case DT_MIPS_TIME_STAMP: return "MIPS_TIME_STAMP";
1037     case DT_MIPS_ICHECKSUM: return "MIPS_ICHECKSUM";
1038     case DT_MIPS_IVERSION: return "MIPS_IVERSION";
1039     case DT_MIPS_FLAGS: return "MIPS_FLAGS";
1040     case DT_MIPS_BASE_ADDRESS: return "MIPS_BASE_ADDRESS";
1041     case DT_MIPS_MSYM: return "MIPS_MSYM";
1042     case DT_MIPS_CONFLICT: return "MIPS_CONFLICT";
1043     case DT_MIPS_LIBLIST: return "MIPS_LIBLIST";
1044     case DT_MIPS_LOCAL_GOTNO: return "MIPS_LOCAL_GOTNO";
1045     case DT_MIPS_CONFLICTNO: return "MIPS_CONFLICTNO";
1046     case DT_MIPS_LIBLISTNO: return "MIPS_LIBLISTNO";
1047     case DT_MIPS_SYMTABNO: return "MIPS_SYMTABNO";
1048     case DT_MIPS_UNREFEXTNO: return "MIPS_UNREFEXTNO";
1049     case DT_MIPS_GOTSYM: return "MIPS_GOTSYM";
1050     case DT_MIPS_HIPAGENO: return "MIPS_HIPAGENO";
1051     case DT_MIPS_RLD_MAP: return "MIPS_RLD_MAP";
1052     case DT_MIPS_DELTA_CLASS: return "MIPS_DELTA_CLASS";
1053     case DT_MIPS_DELTA_CLASS_NO: return "MIPS_DELTA_CLASS_NO";
1054     case DT_MIPS_DELTA_INSTANCE: return "MIPS_DELTA_INSTANCE";
1055     case DT_MIPS_DELTA_INSTANCE_NO: return "MIPS_DELTA_INSTANCE_NO";
1056     case DT_MIPS_DELTA_RELOC: return "MIPS_DELTA_RELOC";
1057     case DT_MIPS_DELTA_RELOC_NO: return "MIPS_DELTA_RELOC_NO";
1058     case DT_MIPS_DELTA_SYM: return "MIPS_DELTA_SYM";
1059     case DT_MIPS_DELTA_SYM_NO: return "MIPS_DELTA_SYM_NO";
1060     case DT_MIPS_DELTA_CLASSSYM: return "MIPS_DELTA_CLASSSYM";
1061     case DT_MIPS_DELTA_CLASSSYM_NO: return "MIPS_DELTA_CLASSSYM_NO";
1062     case DT_MIPS_CXX_FLAGS: return "MIPS_CXX_FLAGS";
1063     case DT_MIPS_PIXIE_INIT: return "MIPS_PIXIE_INIT";
1064     case DT_MIPS_SYMBOL_LIB: return "MIPS_SYMBOL_LIB";
1065     case DT_MIPS_LOCALPAGE_GOTIDX: return "MIPS_LOCALPAGE_GOTIDX";
1066     case DT_MIPS_LOCAL_GOTIDX: return "MIPS_LOCAL_GOTIDX";
1067     case DT_MIPS_HIDDEN_GOTIDX: return "MIPS_HIDDEN_GOTIDX";
1068     case DT_MIPS_PROTECTED_GOTIDX: return "MIPS_PROTECTED_GOTIDX";
1069     case DT_MIPS_OPTIONS: return "MIPS_OPTIONS";
1070     case DT_MIPS_INTERFACE: return "MIPS_INTERFACE";
1071     case DT_MIPS_DYNSTR_ALIGN: return "MIPS_DYNSTR_ALIGN";
1072     case DT_MIPS_INTERFACE_SIZE: return "MIPS_INTERFACE_SIZE";
1073     case DT_MIPS_RLD_TEXT_RESOLVE_ADDR: return "MIPS_RLD_TEXT_RESOLVE_ADDR";
1074     case DT_MIPS_PERF_SUFFIX: return "MIPS_PERF_SUFFIX";
1075     case DT_MIPS_COMPACT_SIZE: return "MIPS_COMPACT_SIZE";
1076     case DT_MIPS_GP_VALUE: return "MIPS_GP_VALUE";
1077     case DT_MIPS_AUX_DYNAMIC: return "MIPS_AUX_DYNAMIC";
1078     default:
1079       return NULL;
1080     }
1081 }
1082
1083 static const char *
1084 get_sparc64_dynamic_type (type)
1085      unsigned long type;
1086 {
1087   switch (type)
1088     {
1089     case DT_SPARC_REGISTER: return "SPARC_REGISTER";
1090     default:
1091       return NULL;
1092     }
1093 }
1094
1095 static const char *
1096 get_parisc_dynamic_type (type)
1097      unsigned long type;
1098 {
1099   switch (type)
1100     {
1101     case DT_HP_LOAD_MAP:        return "HP_LOAD_MAP";
1102     case DT_HP_DLD_FLAGS:       return "HP_DLD_FLAGS";
1103     case DT_HP_DLD_HOOK:        return "HP_DLD_HOOK";
1104     case DT_HP_UX10_INIT:       return "HP_UX10_INIT";
1105     case DT_HP_UX10_INITSZ:     return "HP_UX10_INITSZ";
1106     case DT_HP_PREINIT:         return "HP_PREINIT";
1107     case DT_HP_PREINITSZ:       return "HP_PREINITSZ";
1108     case DT_HP_NEEDED:          return "HP_NEEDED";
1109     case DT_HP_TIME_STAMP:      return "HP_TIME_STAMP";
1110     case DT_HP_CHECKSUM:        return "HP_CHECKSUM";
1111     case DT_HP_GST_SIZE:        return "HP_GST_SIZE";
1112     case DT_HP_GST_VERSION:     return "HP_GST_VERSION";
1113     case DT_HP_GST_HASHVAL:     return "HP_GST_HASHVAL";
1114     default:
1115       return NULL;
1116     }
1117 }
1118
1119 static const char *
1120 get_dynamic_type (type)
1121      unsigned long type;
1122 {
1123   static char buff [32];
1124
1125   switch (type)
1126     {
1127     case DT_NULL:       return "NULL";
1128     case DT_NEEDED:     return "NEEDED";
1129     case DT_PLTRELSZ:   return "PLTRELSZ";
1130     case DT_PLTGOT:     return "PLTGOT";
1131     case DT_HASH:       return "HASH";
1132     case DT_STRTAB:     return "STRTAB";
1133     case DT_SYMTAB:     return "SYMTAB";
1134     case DT_RELA:       return "RELA";
1135     case DT_RELASZ:     return "RELASZ";
1136     case DT_RELAENT:    return "RELAENT";
1137     case DT_STRSZ:      return "STRSZ";
1138     case DT_SYMENT:     return "SYMENT";
1139     case DT_INIT:       return "INIT";
1140     case DT_FINI:       return "FINI";
1141     case DT_SONAME:     return "SONAME";
1142     case DT_RPATH:      return "RPATH";
1143     case DT_SYMBOLIC:   return "SYMBOLIC";
1144     case DT_REL:        return "REL";
1145     case DT_RELSZ:      return "RELSZ";
1146     case DT_RELENT:     return "RELENT";
1147     case DT_PLTREL:     return "PLTREL";
1148     case DT_DEBUG:      return "DEBUG";
1149     case DT_TEXTREL:    return "TEXTREL";
1150     case DT_JMPREL:     return "JMPREL";
1151     case DT_BIND_NOW:   return "BIND_NOW";
1152     case DT_INIT_ARRAY: return "INIT_ARRAY";
1153     case DT_FINI_ARRAY: return "FINI_ARRAY";
1154     case DT_INIT_ARRAYSZ: return "INIT_ARRAYSZ";
1155     case DT_FINI_ARRAYSZ: return "FINI_ARRAYSZ";
1156     case DT_RUNPATH:    return "RUNPATH";
1157     case DT_FLAGS:      return "FLAGS";
1158
1159     case DT_PREINIT_ARRAY: return "PREINIT_ARRAY";
1160     case DT_PREINIT_ARRAYSZ: return "PREINIT_ARRAYSZ";
1161
1162     case DT_CHECKSUM:   return "CHECKSUM";
1163     case DT_PLTPADSZ:   return "PLTPADSZ";
1164     case DT_MOVEENT:    return "MOVEENT";
1165     case DT_MOVESZ:     return "MOVESZ";
1166     case DT_FEATURE:    return "FEATURE";
1167     case DT_POSFLAG_1:  return "POSFLAG_1";
1168     case DT_SYMINSZ:    return "SYMINSZ";
1169     case DT_SYMINENT:   return "SYMINENT"; /* aka VALRNGHI */
1170
1171     case DT_ADDRRNGLO:  return "ADDRRNGLO";
1172     case DT_CONFIG:     return "CONFIG";
1173     case DT_DEPAUDIT:   return "DEPAUDIT";
1174     case DT_AUDIT:      return "AUDIT";
1175     case DT_PLTPAD:     return "PLTPAD";
1176     case DT_MOVETAB:    return "MOVETAB";
1177     case DT_SYMINFO:    return "SYMINFO"; /* aka ADDRRNGHI */
1178
1179     case DT_VERSYM:     return "VERSYM";
1180
1181     case DT_RELACOUNT:  return "RELACOUNT";
1182     case DT_RELCOUNT:   return "RELCOUNT";
1183     case DT_FLAGS_1:    return "FLAGS_1";
1184     case DT_VERDEF:     return "VERDEF";
1185     case DT_VERDEFNUM:  return "VERDEFNUM";
1186     case DT_VERNEED:    return "VERNEED";
1187     case DT_VERNEEDNUM: return "VERNEEDNUM";
1188
1189     case DT_AUXILIARY:  return "AUXILIARY";
1190     case DT_USED:       return "USED";
1191     case DT_FILTER:     return "FILTER";
1192
1193     default:
1194       if ((type >= DT_LOPROC) && (type <= DT_HIPROC))
1195         {
1196           const char * result;
1197
1198           switch (elf_header.e_machine)
1199             {
1200             case EM_MIPS:
1201             case EM_MIPS_RS3_LE:
1202               result = get_mips_dynamic_type (type);
1203               break;
1204             case EM_SPARCV9:
1205               result = get_sparc64_dynamic_type (type);
1206               break;
1207             default:
1208               result = NULL;
1209               break;
1210             }
1211
1212           if (result != NULL)
1213             return result;
1214
1215           sprintf (buff, _("Processor Specific: %lx"), type);
1216         }
1217       else if ((type >= DT_LOOS) && (type <= DT_HIOS))
1218         {
1219           const char * result;
1220
1221           switch (elf_header.e_machine)
1222             {
1223             case EM_PARISC:
1224               result = get_parisc_dynamic_type (type);
1225               break;
1226             default:
1227               result = NULL;
1228               break;
1229             }
1230
1231           if (result != NULL)
1232             return result;
1233
1234           sprintf (buff, _("Operating System specific: %lx"), type);
1235         }
1236       else
1237         sprintf (buff, _("<unknown>: %lx"), type);
1238
1239       return buff;
1240     }
1241 }
1242
1243 static char *
1244 get_file_type (e_type)
1245      unsigned e_type;
1246 {
1247   static char buff [32];
1248
1249   switch (e_type)
1250     {
1251     case ET_NONE:       return _("NONE (None)");
1252     case ET_REL:        return _("REL (Relocatable file)");
1253     case ET_EXEC:       return _("EXEC (Executable file)");
1254     case ET_DYN:        return _("DYN (Shared object file)");
1255     case ET_CORE:       return _("CORE (Core file)");
1256
1257     default:
1258       if ((e_type >= ET_LOPROC) && (e_type <= ET_HIPROC))
1259         sprintf (buff, _("Processor Specific: (%x)"), e_type);
1260       else if ((e_type >= ET_LOOS) && (e_type <= ET_HIOS))
1261         sprintf (buff, _("OS Specific: (%x)"), e_type);
1262       else
1263         sprintf (buff, _("<unknown>: %x"), e_type);
1264       return buff;
1265     }
1266 }
1267
1268 static char *
1269 get_machine_name (e_machine)
1270      unsigned e_machine;
1271 {
1272   static char buff [64]; /* XXX */
1273
1274   switch (e_machine)
1275     {
1276     case EM_NONE:               return _("None");
1277     case EM_M32:                return "WE32100";
1278     case EM_SPARC:              return "Sparc";
1279     case EM_386:                return "Intel 80386";
1280     case EM_68K:                return "MC68000";
1281     case EM_88K:                return "MC88000";
1282     case EM_486:                return "Intel 80486";
1283     case EM_860:                return "Intel 80860";
1284     case EM_MIPS:               return "MIPS R3000";
1285     case EM_S370:               return "IBM System/370";
1286     case EM_MIPS_RS3_LE:        return "MIPS R4000 big-endian";
1287     case EM_OLD_SPARCV9:        return "Sparc v9 (old)";
1288     case EM_PARISC:             return "HPPA";
1289     case EM_PPC_OLD:            return "Power PC (old)";
1290     case EM_SPARC32PLUS:        return "Sparc v8+" ;
1291     case EM_960:                return "Intel 90860";
1292     case EM_PPC:                return "PowerPC";
1293     case EM_V800:               return "NEC V800";
1294     case EM_FR20:               return "Fujitsu FR20";
1295     case EM_RH32:               return "TRW RH32";
1296     case EM_MCORE:              return "MCORE";
1297     case EM_ARM:                return "ARM";
1298     case EM_OLD_ALPHA:          return "Digital Alpha (old)";
1299     case EM_SH:                 return "Hitachi SH";
1300     case EM_SPARCV9:            return "Sparc v9";
1301     case EM_TRICORE:            return "Siemens Tricore";
1302     case EM_ARC:                return "ARC";
1303     case EM_H8_300:             return "Hitachi H8/300";
1304     case EM_H8_300H:            return "Hitachi H8/300H";
1305     case EM_H8S:                return "Hitachi H8S";
1306     case EM_H8_500:             return "Hitachi H8/500";
1307     case EM_IA_64:              return "Intel IA-64";
1308     case EM_MIPS_X:             return "Stanford MIPS-X";
1309     case EM_COLDFIRE:           return "Motorola Coldfire";
1310     case EM_68HC12:             return "Motorola M68HC12";
1311     case EM_ALPHA:              return "Alpha";
1312     case EM_CYGNUS_D10V:        return "d10v";
1313     case EM_CYGNUS_D30V:        return "d30v";
1314     case EM_CYGNUS_ARC:         return "ARC";
1315     case EM_CYGNUS_M32R:        return "Mitsubishi M32r";
1316     case EM_CYGNUS_V850:        return "NEC v850";
1317     case EM_CYGNUS_MN10300:     return "mn10300";
1318     case EM_CYGNUS_MN10200:     return "mn10200";
1319     case EM_CYGNUS_FR30:        return "Fujitsu FR30";
1320     case EM_PJ:                 return "picoJava";
1321     case EM_MMA:                return "Fujitsu Multimedia Accelerator";
1322     case EM_PCP:                return "Siemens PCP";
1323     case EM_NCPU:               return "Sony nCPU embedded RISC processor";
1324     case EM_NDR1:               return "Denso NDR1 microprocesspr";
1325     case EM_STARCORE:           return "Motorola Star*Core processor";
1326     case EM_ME16:               return "Toyota ME16 processor";
1327     case EM_ST100:              return "STMicroelectronics ST100 processor";
1328     case EM_TINYJ:              return "Advanced Logic Corp. TinyJ embedded processor";
1329     case EM_FX66:               return "Siemens FX66 microcontroller";
1330     case EM_ST9PLUS:            return "STMicroelectronics ST9+ 8/16 bit microcontroller";
1331     case EM_ST7:                return "STMicroelectronics ST7 8-bit microcontroller";
1332     case EM_68HC16:             return "Motorola MC68HC16 Microcontroller";
1333     case EM_68HC11:             return "Motorola MC68HC11 Microcontroller";
1334     case EM_68HC08:             return "Motorola MC68HC08 Microcontroller";
1335     case EM_68HC05:             return "Motorola MC68HC05 Microcontroller";
1336     case EM_SVX:                return "Silicon Graphics SVx";
1337     case EM_ST19:               return "STMicroelectronics ST19 8-bit microcontroller";
1338     case EM_VAX:                return "Digital VAX";
1339     case EM_AVR:                return "Atmel AVR 8-bit microcontroller";
1340     case EM_CRIS:               return "Axis Communications 32-bit embedded processor";
1341     case EM_JAVELIN:            return "Infineon Technologies 32-bit embedded cpu";
1342     case EM_FIREPATH:           return "Element 14 64-bit DSP processor";
1343     case EM_ZSP:                return "LSI Logic's 16-bit DSP processor";
1344     case EM_MMIX:               return "Donald Knuth's educational 64-bit processor";
1345     case EM_HUANY:              return "Harvard Universitys's machine-independent object format";
1346     case EM_PRISM:              return "SiTera Prism";
1347     case EM_X86_64:             return "Advanced Micro Devices X86-64";
1348     case EM_S390_OLD:
1349     case EM_S390:               return "IBM S/390";
1350     default:
1351       sprintf (buff, _("<unknown>: %x"), e_machine);
1352       return buff;
1353     }
1354 }
1355
1356 static void
1357 decode_ARM_machine_flags (e_flags, buf)
1358      unsigned e_flags;
1359      char buf[];
1360 {
1361   unsigned eabi;
1362   int unknown = 0;
1363
1364   eabi = EF_ARM_EABI_VERSION (e_flags);
1365   e_flags &= ~ EF_ARM_EABIMASK;
1366
1367   /* Handle "generic" ARM flags.  */
1368   if (e_flags & EF_ARM_RELEXEC)
1369     {
1370       strcat (buf, ", relocatable executable");
1371       e_flags &= ~ EF_ARM_RELEXEC;
1372     }
1373
1374   if (e_flags & EF_ARM_HASENTRY)
1375     {
1376       strcat (buf, ", has entry point");
1377       e_flags &= ~ EF_ARM_HASENTRY;
1378     }
1379
1380   /* Now handle EABI specific flags.  */
1381   switch (eabi)
1382     {
1383     default:
1384       strcat (buf, ", <unrecognised EABI>");
1385       if (e_flags)
1386         unknown = 1;
1387       break;
1388
1389     case EF_ARM_EABI_VER1:
1390       strcat (buf, ", Version1 EABI");
1391       while (e_flags)
1392         {
1393           unsigned flag;
1394
1395           /* Process flags one bit at a time.  */
1396           flag = e_flags & - e_flags;
1397           e_flags &= ~ flag;
1398
1399           switch (flag)
1400             {
1401             case EF_ARM_SYMSARESORTED: /* Conflicts with EF_ARM_INTERWORK.  */
1402               strcat (buf, ", sorted symbol tables");
1403               break;
1404
1405             default:
1406               unknown = 1;
1407               break;
1408             }
1409         }
1410       break;
1411
1412     case EF_ARM_EABI_VER2:
1413       strcat (buf, ", Version2 EABI");
1414       while (e_flags)
1415         {
1416           unsigned flag;
1417
1418           /* Process flags one bit at a time.  */
1419           flag = e_flags & - e_flags;
1420           e_flags &= ~ flag;
1421
1422           switch (flag)
1423             {
1424             case EF_ARM_SYMSARESORTED: /* Conflicts with EF_ARM_INTERWORK.  */
1425               strcat (buf, ", sorted symbol tables");
1426               break;
1427
1428             case EF_ARM_DYNSYMSUSESEGIDX:
1429               strcat (buf, ", dynamic symbols use segment index");
1430               break;
1431
1432             case EF_ARM_MAPSYMSFIRST:
1433               strcat (buf, ", mapping symbols precede others");
1434               break;
1435
1436             default:
1437               unknown = 1;
1438               break;
1439             }
1440         }
1441       break;
1442
1443     case EF_ARM_EABI_UNKNOWN:
1444       strcat (buf, ", GNU EABI");
1445       while (e_flags)
1446         {
1447           unsigned flag;
1448
1449           /* Process flags one bit at a time.  */
1450           flag = e_flags & - e_flags;
1451           e_flags &= ~ flag;
1452
1453           switch (flag)
1454             {
1455             case EF_ARM_INTERWORK:
1456               strcat (buf, ", interworking enabled");
1457               break;
1458
1459             case EF_ARM_APCS_26:
1460               strcat (buf, ", uses APCS/26");
1461               break;
1462
1463             case EF_ARM_APCS_FLOAT:
1464               strcat (buf, ", uses APCS/float");
1465               break;
1466
1467             case EF_ARM_PIC:
1468               strcat (buf, ", position independent");
1469               break;
1470
1471             case EF_ARM_ALIGN8:
1472               strcat (buf, ", 8 bit structure alignment");
1473               break;
1474
1475             case EF_ARM_NEW_ABI:
1476               strcat (buf, ", uses new ABI");
1477               break;
1478
1479             case EF_ARM_OLD_ABI:
1480               strcat (buf, ", uses old ABI");
1481               break;
1482
1483             case EF_ARM_SOFT_FLOAT:
1484               strcat (buf, ", software FP");
1485               break;
1486
1487             default:
1488               unknown = 1;
1489               break;
1490             }
1491         }
1492     }
1493
1494   if (unknown)
1495     strcat (buf,", <unknown>");
1496 }
1497
1498 static char *
1499 get_machine_flags (e_flags, e_machine)
1500      unsigned e_flags;
1501      unsigned e_machine;
1502 {
1503   static char buf [1024];
1504
1505   buf[0] = '\0';
1506
1507   if (e_flags)
1508     {
1509       switch (e_machine)
1510         {
1511         default:
1512           break;
1513
1514         case EM_ARM:
1515           decode_ARM_machine_flags (e_flags, buf);
1516           break;
1517
1518         case EM_68K:
1519           if (e_flags & EF_CPU32)
1520             strcat (buf, ", cpu32");
1521           break;
1522
1523         case EM_PPC:
1524           if (e_flags & EF_PPC_EMB)
1525             strcat (buf, ", emb");
1526
1527           if (e_flags & EF_PPC_RELOCATABLE)
1528             strcat (buf, ", relocatable");
1529
1530           if (e_flags & EF_PPC_RELOCATABLE_LIB)
1531             strcat (buf, ", relocatable-lib");
1532           break;
1533
1534         case EM_CYGNUS_V850:
1535           switch (e_flags & EF_V850_ARCH)
1536             {
1537             case E_V850E_ARCH:
1538               strcat (buf, ", v850e");
1539               break;
1540             case E_V850EA_ARCH:
1541               strcat (buf, ", v850ea");
1542               break;
1543             case E_V850_ARCH:
1544               strcat (buf, ", v850");
1545               break;
1546             default:
1547               strcat (buf, ", unknown v850 architecture variant");
1548               break;
1549             }
1550           break;
1551
1552         case EM_CYGNUS_M32R:
1553           if ((e_flags & EF_M32R_ARCH) == E_M32R_ARCH)
1554             strcat (buf, ", m32r");
1555
1556           break;
1557
1558         case EM_MIPS:
1559         case EM_MIPS_RS3_LE:
1560           if (e_flags & EF_MIPS_NOREORDER)
1561             strcat (buf, ", noreorder");
1562
1563           if (e_flags & EF_MIPS_PIC)
1564             strcat (buf, ", pic");
1565
1566           if (e_flags & EF_MIPS_CPIC)
1567             strcat (buf, ", cpic");
1568
1569           if (e_flags & EF_MIPS_ABI2)
1570             strcat (buf, ", abi2");
1571
1572           if ((e_flags & EF_MIPS_ARCH) == E_MIPS_ARCH_1)
1573             strcat (buf, ", mips1");
1574
1575           if ((e_flags & EF_MIPS_ARCH) == E_MIPS_ARCH_2)
1576             strcat (buf, ", mips2");
1577
1578           if ((e_flags & EF_MIPS_ARCH) == E_MIPS_ARCH_3)
1579             strcat (buf, ", mips3");
1580
1581           if ((e_flags & EF_MIPS_ARCH) == E_MIPS_ARCH_4)
1582             strcat (buf, ", mips4");
1583
1584           if ((e_flags & EF_MIPS_ARCH) == E_MIPS_ARCH_5)
1585             strcat (buf, ", mips5");
1586
1587           if ((e_flags & EF_MIPS_ARCH) == E_MIPS_ARCH_32)
1588             strcat (buf, ", mips32");
1589
1590           if ((e_flags & EF_MIPS_ARCH) == E_MIPS_ARCH_64)
1591             strcat (buf, ", mips64");
1592
1593           switch ((e_flags & EF_MIPS_MACH))
1594             {
1595             case E_MIPS_MACH_3900: strcat (buf, ", 3900"); break;
1596             case E_MIPS_MACH_4010: strcat (buf, ", 4010"); break;
1597             case E_MIPS_MACH_4100: strcat (buf, ", 4100"); break;
1598             case E_MIPS_MACH_4650: strcat (buf, ", 4650"); break;
1599             case E_MIPS_MACH_4111: strcat (buf, ", 4111"); break;
1600             case E_MIPS_MACH_MIPS32_4K: strcat (buf, ", mips32-4k"); break;
1601             case E_MIPS_MACH_SB1:  strcat (buf, ", sb1");  break;
1602             default: strcat (buf, " UNKNOWN"); break;
1603             }
1604           break;
1605
1606         case EM_SPARCV9:
1607           if (e_flags & EF_SPARC_32PLUS)
1608             strcat (buf, ", v8+");
1609
1610           if (e_flags & EF_SPARC_SUN_US1)
1611             strcat (buf, ", ultrasparcI");
1612
1613           if (e_flags & EF_SPARC_SUN_US3)
1614             strcat (buf, ", ultrasparcIII");
1615
1616           if (e_flags & EF_SPARC_HAL_R1)
1617             strcat (buf, ", halr1");
1618
1619           if (e_flags & EF_SPARC_LEDATA)
1620             strcat (buf, ", ledata");
1621
1622           if ((e_flags & EF_SPARCV9_MM) == EF_SPARCV9_TSO)
1623             strcat (buf, ", tso");
1624
1625           if ((e_flags & EF_SPARCV9_MM) == EF_SPARCV9_PSO)
1626             strcat (buf, ", pso");
1627
1628           if ((e_flags & EF_SPARCV9_MM) == EF_SPARCV9_RMO)
1629             strcat (buf, ", rmo");
1630           break;
1631
1632         case EM_PARISC:
1633           switch (e_flags & EF_PARISC_ARCH)
1634             {
1635             case EFA_PARISC_1_0:
1636               strcpy (buf, ", PA-RISC 1.0");
1637               break;
1638             case EFA_PARISC_1_1:
1639               strcpy (buf, ", PA-RISC 1.1");
1640               break;
1641             case EFA_PARISC_2_0:
1642               strcpy (buf, ", PA-RISC 2.0");
1643               break;
1644             default:
1645               break;
1646             }
1647           if (e_flags & EF_PARISC_TRAPNIL)
1648             strcat (buf, ", trapnil");
1649           if (e_flags & EF_PARISC_EXT)
1650             strcat (buf, ", ext");
1651           if (e_flags & EF_PARISC_LSB)
1652             strcat (buf, ", lsb");
1653           if (e_flags & EF_PARISC_WIDE)
1654             strcat (buf, ", wide");
1655           if (e_flags & EF_PARISC_NO_KABP)
1656             strcat (buf, ", no kabp");
1657           if (e_flags & EF_PARISC_LAZYSWAP)
1658             strcat (buf, ", lazyswap");
1659           break;
1660
1661         case EM_PJ:
1662           if ((e_flags & EF_PICOJAVA_NEWCALLS) == EF_PICOJAVA_NEWCALLS)
1663             strcat (buf, ", new calling convention");
1664
1665           if ((e_flags & EF_PICOJAVA_GNUCALLS) == EF_PICOJAVA_GNUCALLS)
1666             strcat (buf, ", gnu calling convention");
1667           break;
1668
1669         case EM_IA_64:
1670           if ((e_flags & EF_IA_64_ABI64))
1671             strcat (buf, ", 64-bit");
1672           else
1673             strcat (buf, ", 32-bit");
1674           if ((e_flags & EF_IA_64_REDUCEDFP))
1675             strcat (buf, ", reduced fp model");
1676           if ((e_flags & EF_IA_64_NOFUNCDESC_CONS_GP))
1677             strcat (buf, ", no function descriptors, constant gp");
1678           else if ((e_flags & EF_IA_64_CONS_GP))
1679             strcat (buf, ", constant gp");
1680           if ((e_flags & EF_IA_64_ABSOLUTE))
1681             strcat (buf, ", absolute");
1682           break;
1683         }
1684     }
1685
1686   return buf;
1687 }
1688
1689 static const char *
1690 get_mips_segment_type (type)
1691      unsigned long type;
1692 {
1693   switch (type)
1694     {
1695     case PT_MIPS_REGINFO:
1696       return "REGINFO";
1697     case PT_MIPS_RTPROC:
1698       return "RTPROC";
1699     case PT_MIPS_OPTIONS:
1700       return "OPTIONS";
1701     default:
1702       break;
1703     }
1704
1705   return NULL;
1706 }
1707
1708 static const char *
1709 get_parisc_segment_type (type)
1710      unsigned long type;
1711 {
1712   switch (type)
1713     {
1714     case PT_HP_TLS:             return "HP_TLS";
1715     case PT_HP_CORE_NONE:       return "HP_CORE_NONE";
1716     case PT_HP_CORE_VERSION:    return "HP_CORE_VERSION";
1717     case PT_HP_CORE_KERNEL:     return "HP_CORE_KERNEL";
1718     case PT_HP_CORE_COMM:       return "HP_CORE_COMM";
1719     case PT_HP_CORE_PROC:       return "HP_CORE_PROC";
1720     case PT_HP_CORE_LOADABLE:   return "HP_CORE_LOADABLE";
1721     case PT_HP_CORE_STACK:      return "HP_CORE_STACK";
1722     case PT_HP_CORE_SHM:        return "HP_CORE_SHM";
1723     case PT_HP_CORE_MMF:        return "HP_CORE_MMF";
1724     case PT_HP_PARALLEL:        return "HP_PARALLEL";
1725     case PT_HP_FASTBIND:        return "HP_FASTBIND";
1726     case PT_PARISC_ARCHEXT:     return "PARISC_ARCHEXT";
1727     case PT_PARISC_UNWIND:      return "PARISC_UNWIND";
1728     default:
1729       break;
1730     }
1731
1732   return NULL;
1733 }
1734
1735 static const char *
1736 get_ia64_segment_type (type)
1737      unsigned long type;
1738 {
1739   switch (type)
1740     {
1741     case PT_IA_64_ARCHEXT:      return "IA_64_ARCHEXT";
1742     case PT_IA_64_UNWIND:       return "IA_64_UNWIND";
1743     default:
1744       break;
1745     }
1746
1747   return NULL;
1748 }
1749
1750 static const char *
1751 get_segment_type (p_type)
1752      unsigned long p_type;
1753 {
1754   static char buff [32];
1755
1756   switch (p_type)
1757     {
1758     case PT_NULL:       return "NULL";
1759     case PT_LOAD:       return "LOAD";
1760     case PT_DYNAMIC:    return "DYNAMIC";
1761     case PT_INTERP:     return "INTERP";
1762     case PT_NOTE:       return "NOTE";
1763     case PT_SHLIB:      return "SHLIB";
1764     case PT_PHDR:       return "PHDR";
1765
1766     default:
1767       if ((p_type >= PT_LOPROC) && (p_type <= PT_HIPROC))
1768         {
1769           const char * result;
1770
1771           switch (elf_header.e_machine)
1772             {
1773             case EM_MIPS:
1774             case EM_MIPS_RS3_LE:
1775               result = get_mips_segment_type (p_type);
1776               break;
1777             case EM_PARISC:
1778               result = get_parisc_segment_type (p_type);
1779               break;
1780             case EM_IA_64:
1781               result = get_ia64_segment_type (p_type);
1782               break;
1783             default:
1784               result = NULL;
1785               break;
1786             }
1787
1788           if (result != NULL)
1789             return result;
1790
1791           sprintf (buff, "LOPROC+%lx", p_type - PT_LOPROC);
1792         }
1793       else if ((p_type >= PT_LOOS) && (p_type <= PT_HIOS))
1794         {
1795           const char * result;
1796
1797           switch (elf_header.e_machine)
1798             {
1799             case EM_PARISC:
1800               result = get_parisc_segment_type (p_type);
1801               break;
1802             default:
1803               result = NULL;
1804               break;
1805             }
1806
1807           if (result != NULL)
1808             return result;
1809
1810           sprintf (buff, "LOOS+%lx", p_type - PT_LOOS);
1811         }
1812       else
1813         sprintf (buff, _("<unknown>: %lx"), p_type);
1814
1815       return buff;
1816     }
1817 }
1818
1819 static const char *
1820 get_mips_section_type_name (sh_type)
1821      unsigned int sh_type;
1822 {
1823   switch (sh_type)
1824     {
1825     case SHT_MIPS_LIBLIST:       return "MIPS_LIBLIST";
1826     case SHT_MIPS_MSYM:          return "MIPS_MSYM";
1827     case SHT_MIPS_CONFLICT:      return "MIPS_CONFLICT";
1828     case SHT_MIPS_GPTAB:         return "MIPS_GPTAB";
1829     case SHT_MIPS_UCODE:         return "MIPS_UCODE";
1830     case SHT_MIPS_DEBUG:         return "MIPS_DEBUG";
1831     case SHT_MIPS_REGINFO:       return "MIPS_REGINFO";
1832     case SHT_MIPS_PACKAGE:       return "MIPS_PACKAGE";
1833     case SHT_MIPS_PACKSYM:       return "MIPS_PACKSYM";
1834     case SHT_MIPS_RELD:          return "MIPS_RELD";
1835     case SHT_MIPS_IFACE:         return "MIPS_IFACE";
1836     case SHT_MIPS_CONTENT:       return "MIPS_CONTENT";
1837     case SHT_MIPS_OPTIONS:       return "MIPS_OPTIONS";
1838     case SHT_MIPS_SHDR:          return "MIPS_SHDR";
1839     case SHT_MIPS_FDESC:         return "MIPS_FDESC";
1840     case SHT_MIPS_EXTSYM:        return "MIPS_EXTSYM";
1841     case SHT_MIPS_DENSE:         return "MIPS_DENSE";
1842     case SHT_MIPS_PDESC:         return "MIPS_PDESC";
1843     case SHT_MIPS_LOCSYM:        return "MIPS_LOCSYM";
1844     case SHT_MIPS_AUXSYM:        return "MIPS_AUXSYM";
1845     case SHT_MIPS_OPTSYM:        return "MIPS_OPTSYM";
1846     case SHT_MIPS_LOCSTR:        return "MIPS_LOCSTR";
1847     case SHT_MIPS_LINE:          return "MIPS_LINE";
1848     case SHT_MIPS_RFDESC:        return "MIPS_RFDESC";
1849     case SHT_MIPS_DELTASYM:      return "MIPS_DELTASYM";
1850     case SHT_MIPS_DELTAINST:     return "MIPS_DELTAINST";
1851     case SHT_MIPS_DELTACLASS:    return "MIPS_DELTACLASS";
1852     case SHT_MIPS_DWARF:         return "MIPS_DWARF";
1853     case SHT_MIPS_DELTADECL:     return "MIPS_DELTADECL";
1854     case SHT_MIPS_SYMBOL_LIB:    return "MIPS_SYMBOL_LIB";
1855     case SHT_MIPS_EVENTS:        return "MIPS_EVENTS";
1856     case SHT_MIPS_TRANSLATE:     return "MIPS_TRANSLATE";
1857     case SHT_MIPS_PIXIE:         return "MIPS_PIXIE";
1858     case SHT_MIPS_XLATE:         return "MIPS_XLATE";
1859     case SHT_MIPS_XLATE_DEBUG:   return "MIPS_XLATE_DEBUG";
1860     case SHT_MIPS_WHIRL:         return "MIPS_WHIRL";
1861     case SHT_MIPS_EH_REGION:     return "MIPS_EH_REGION";
1862     case SHT_MIPS_XLATE_OLD:     return "MIPS_XLATE_OLD";
1863     case SHT_MIPS_PDR_EXCEPTION: return "MIPS_PDR_EXCEPTION";
1864     default:
1865       break;
1866     }
1867   return NULL;
1868 }
1869
1870 static const char *
1871 get_parisc_section_type_name (sh_type)
1872      unsigned int sh_type;
1873 {
1874   switch (sh_type)
1875     {
1876     case SHT_PARISC_EXT:        return "PARISC_EXT";
1877     case SHT_PARISC_UNWIND:     return "PARISC_UNWIND";
1878     case SHT_PARISC_DOC:        return "PARISC_DOC";
1879     default:
1880       break;
1881     }
1882   return NULL;
1883 }
1884
1885 static const char *
1886 get_ia64_section_type_name (sh_type)
1887      unsigned int sh_type;
1888 {
1889   switch (sh_type)
1890     {
1891     case SHT_IA_64_EXT:         return "IA_64_EXT";
1892     case SHT_IA_64_UNWIND:      return "IA_64_UNWIND";
1893     default:
1894       break;
1895     }
1896   return NULL;
1897 }
1898
1899 static const char *
1900 get_section_type_name (sh_type)
1901      unsigned int sh_type;
1902 {
1903   static char buff [32];
1904
1905   switch (sh_type)
1906     {
1907     case SHT_NULL:              return "NULL";
1908     case SHT_PROGBITS:          return "PROGBITS";
1909     case SHT_SYMTAB:            return "SYMTAB";
1910     case SHT_STRTAB:            return "STRTAB";
1911     case SHT_RELA:              return "RELA";
1912     case SHT_HASH:              return "HASH";
1913     case SHT_DYNAMIC:           return "DYNAMIC";
1914     case SHT_NOTE:              return "NOTE";
1915     case SHT_NOBITS:            return "NOBITS";
1916     case SHT_REL:               return "REL";
1917     case SHT_SHLIB:             return "SHLIB";
1918     case SHT_DYNSYM:            return "DYNSYM";
1919     case SHT_INIT_ARRAY:        return "INIT_ARRAY";
1920     case SHT_FINI_ARRAY:        return "FINI_ARRAY";
1921     case SHT_PREINIT_ARRAY:     return "PREINIT_ARRAY";
1922     case SHT_GROUP:             return "GROUP";
1923     case SHT_SYMTAB_SHNDX:      return "SYMTAB SECTION INDICIES";
1924     case SHT_GNU_verdef:        return "VERDEF";
1925     case SHT_GNU_verneed:       return "VERNEED";
1926     case SHT_GNU_versym:        return "VERSYM";
1927     case 0x6ffffff0:            return "VERSYM";
1928     case 0x6ffffffc:            return "VERDEF";
1929     case 0x7ffffffd:            return "AUXILIARY";
1930     case 0x7fffffff:            return "FILTER";
1931
1932     default:
1933       if ((sh_type >= SHT_LOPROC) && (sh_type <= SHT_HIPROC))
1934         {
1935           const char * result;
1936
1937           switch (elf_header.e_machine)
1938             {
1939             case EM_MIPS:
1940             case EM_MIPS_RS3_LE:
1941               result = get_mips_section_type_name (sh_type);
1942               break;
1943             case EM_PARISC:
1944               result = get_parisc_section_type_name (sh_type);
1945               break;
1946             case EM_IA_64:
1947               result = get_ia64_section_type_name (sh_type);
1948               break;
1949             default:
1950               result = NULL;
1951               break;
1952             }
1953
1954           if (result != NULL)
1955             return result;
1956
1957           sprintf (buff, "SHT_LOPROC+%x", sh_type - SHT_LOPROC);
1958         }
1959       else if ((sh_type >= SHT_LOOS) && (sh_type <= SHT_HIOS))
1960         sprintf (buff, "SHT_LOOS+%x", sh_type - SHT_LOOS);
1961       else if ((sh_type >= SHT_LOUSER) && (sh_type <= SHT_HIUSER))
1962         sprintf (buff, "SHT_LOUSER+%x", sh_type - SHT_LOUSER);
1963       else
1964         sprintf (buff, _("<unknown>: %x"), sh_type);
1965
1966       return buff;
1967     }
1968 }
1969
1970 struct option options [] =
1971 {
1972   {"all",              no_argument, 0, 'a'},
1973   {"file-header",      no_argument, 0, 'h'},
1974   {"program-headers",  no_argument, 0, 'l'},
1975   {"headers",          no_argument, 0, 'e'},
1976   {"histogram",        no_argument, 0, 'I'},
1977   {"segments",         no_argument, 0, 'l'},
1978   {"sections",         no_argument, 0, 'S'},
1979   {"section-headers",  no_argument, 0, 'S'},
1980   {"symbols",          no_argument, 0, 's'},
1981   {"syms",             no_argument, 0, 's'},
1982   {"relocs",           no_argument, 0, 'r'},
1983   {"notes",            no_argument, 0, 'n'},
1984   {"dynamic",          no_argument, 0, 'd'},
1985   {"arch-specific",    no_argument, 0, 'A'},
1986   {"version-info",     no_argument, 0, 'V'},
1987   {"use-dynamic",      no_argument, 0, 'D'},
1988   {"hex-dump",         required_argument, 0, 'x'},
1989   {"debug-dump",       optional_argument, 0, 'w'},
1990   {"unwind",           no_argument, 0, 'u'},
1991 #ifdef SUPPORT_DISASSEMBLY
1992   {"instruction-dump", required_argument, 0, 'i'},
1993 #endif
1994
1995   {"version",          no_argument, 0, 'v'},
1996   {"help",             no_argument, 0, 'H'},
1997   {0,                  no_argument, 0, 0}
1998 };
1999
2000 static void
2001 usage ()
2002 {
2003   fprintf (stdout, _("Usage: readelf {options} elf-file(s)\n"));
2004   fprintf (stdout, _("  Options are:\n"));
2005   fprintf (stdout, _("  -a or --all               Equivalent to: -h -l -S -s -r -d -V -A -I\n"));
2006   fprintf (stdout, _("  -h or --file-header       Display the ELF file header\n"));
2007   fprintf (stdout, _("  -l or --program-headers or --segments\n"));
2008   fprintf (stdout, _("                            Display the program headers\n"));
2009   fprintf (stdout, _("  -S or --section-headers or --sections\n"));
2010   fprintf (stdout, _("                            Display the sections' header\n"));
2011   fprintf (stdout, _("  -e or --headers           Equivalent to: -h -l -S\n"));
2012   fprintf (stdout, _("  -s or --syms or --symbols Display the symbol table\n"));
2013   fprintf (stdout, _("  -n or --notes             Display the core notes (if present)\n"));
2014   fprintf (stdout, _("  -r or --relocs            Display the relocations (if present)\n"));
2015   fprintf (stdout, _("  -u or --unwind            Display the unwind info (if present)\n"));
2016   fprintf (stdout, _("  -d or --dynamic           Display the dynamic segment (if present)\n"));
2017   fprintf (stdout, _("  -V or --version-info      Display the version sections (if present)\n"));
2018   fprintf (stdout, _("  -A or --arch-specific     Display architecture specific information (if any).\n"));
2019   fprintf (stdout, _("  -D or --use-dynamic       Use the dynamic section info when displaying symbols\n"));
2020   fprintf (stdout, _("  -x <number> or --hex-dump=<number>\n"));
2021   fprintf (stdout, _("                            Dump the contents of section <number>\n"));
2022   fprintf (stdout, _("  -w[liaprf] or --debug-dump[=line,=info,=abbrev,=pubnames,=ranges,=frames]\n"));
2023   fprintf (stdout, _("                            Display the contents of DWARF2 debug sections\n"));
2024 #ifdef SUPPORT_DISASSEMBLY
2025   fprintf (stdout, _("  -i <number> or --instruction-dump=<number>\n"));
2026   fprintf (stdout, _("                            Disassemble the contents of section <number>\n"));
2027 #endif
2028   fprintf (stdout, _("  -I or --histogram         Display histogram of bucket list lengths\n"));
2029   fprintf (stdout, _("  -v or --version           Display the version number of readelf\n"));
2030   fprintf (stdout, _("  -H or --help              Display this information\n"));
2031   fprintf (stdout, _("Report bugs to %s\n"), REPORT_BUGS_TO);
2032
2033   exit (0);
2034 }
2035
2036 static void
2037 request_dump (section, type)
2038      unsigned int section;
2039      char         type;
2040 {
2041   if (section >= num_dump_sects)
2042     {
2043       char * new_dump_sects;
2044
2045       new_dump_sects = (char *) calloc (section + 1, 1);
2046
2047       if (new_dump_sects == NULL)
2048         error (_("Out of memory allocating dump request table."));
2049       else
2050         {
2051           /* Copy current flag settings.  */
2052           memcpy (new_dump_sects, dump_sects, num_dump_sects);
2053
2054           free (dump_sects);
2055
2056           dump_sects = new_dump_sects;
2057           num_dump_sects = section + 1;
2058         }
2059     }
2060
2061   if (dump_sects)
2062     dump_sects [section] |= type;
2063
2064   return;
2065 }
2066
2067 static void
2068 parse_args (argc, argv)
2069      int argc;
2070      char ** argv;
2071 {
2072   int c;
2073
2074   if (argc < 2)
2075     usage ();
2076
2077   while ((c = getopt_long
2078           (argc, argv, "ersuahnldSDAIw::x:i:vV", options, NULL)) != EOF)
2079     {
2080       char *    cp;
2081       int       section;
2082
2083       switch (c)
2084         {
2085         case 0:
2086           /* Long options.  */
2087           break;
2088         case 'H':
2089           usage ();
2090           break;
2091
2092         case 'a':
2093           do_syms ++;
2094           do_reloc ++;
2095           do_unwind ++;
2096           do_dynamic ++;
2097           do_header ++;
2098           do_sections ++;
2099           do_segments ++;
2100           do_version ++;
2101           do_histogram ++;
2102           do_arch ++;
2103           do_notes ++;
2104           break;
2105         case 'e':
2106           do_header ++;
2107           do_sections ++;
2108           do_segments ++;
2109           break;
2110         case 'A':
2111           do_arch ++;
2112           break;
2113         case 'D':
2114           do_using_dynamic ++;
2115           break;
2116         case 'r':
2117           do_reloc ++;
2118           break;
2119         case 'u':
2120           do_unwind ++;
2121           break;
2122         case 'h':
2123           do_header ++;
2124           break;
2125         case 'l':
2126           do_segments ++;
2127           break;
2128         case 's':
2129           do_syms ++;
2130           break;
2131         case 'S':
2132           do_sections ++;
2133           break;
2134         case 'd':
2135           do_dynamic ++;
2136           break;
2137         case 'I':
2138           do_histogram ++;
2139           break;
2140         case 'n':
2141           do_notes ++;
2142           break;
2143         case 'x':
2144           do_dump ++;
2145           section = strtoul (optarg, & cp, 0);
2146           if (! * cp && section >= 0)
2147             {
2148               request_dump (section, HEX_DUMP);
2149               break;
2150             }
2151           goto oops;
2152         case 'w':
2153           do_dump ++;
2154           if (optarg == 0)
2155             do_debugging = 1;
2156           else
2157             {
2158               do_debugging = 0;
2159               switch (optarg[0])
2160                 {
2161                 case 'i':
2162                 case 'I':
2163                   do_debug_info = 1;
2164                   break;
2165
2166                 case 'a':
2167                 case 'A':
2168                   do_debug_abbrevs = 1;
2169                   break;
2170
2171                 case 'l':
2172                 case 'L':
2173                   do_debug_lines = 1;
2174                   break;
2175
2176                 case 'p':
2177                 case 'P':
2178                   do_debug_pubnames = 1;
2179                   break;
2180
2181                 case 'r':
2182                 case 'R':
2183                   do_debug_aranges = 1;
2184                   break;
2185
2186                 case 'F':
2187                   do_debug_frames_interp = 1;
2188                 case 'f':
2189                   do_debug_frames = 1;
2190                   break;
2191
2192                 default:
2193                   warn (_("Unrecognised debug option '%s'\n"), optarg);
2194                   break;
2195                 }
2196             }
2197           break;
2198 #ifdef SUPPORT_DISASSEMBLY
2199         case 'i':
2200           do_dump ++;
2201           section = strtoul (optarg, & cp, 0);
2202           if (! * cp && section >= 0)
2203             {
2204               request_dump (section, DISASS_DUMP);
2205               break;
2206             }
2207           goto oops;
2208 #endif
2209         case 'v':
2210           print_version (program_name);
2211           break;
2212         case 'V':
2213           do_version ++;
2214           break;
2215         default:
2216         oops:
2217           /* xgettext:c-format */
2218           error (_("Invalid option '-%c'\n"), c);
2219           /* Drop through.  */
2220         case '?':
2221           usage ();
2222         }
2223     }
2224
2225   if (!do_dynamic && !do_syms && !do_reloc && !do_unwind && !do_sections
2226       && !do_segments && !do_header && !do_dump && !do_version
2227       && !do_histogram && !do_debugging && !do_arch && !do_notes)
2228     usage ();
2229   else if (argc < 3)
2230     {
2231       warn (_("Nothing to do.\n"));
2232       usage();
2233     }
2234 }
2235
2236 static const char *
2237 get_elf_class (elf_class)
2238      unsigned char elf_class;
2239 {
2240   static char buff [32];
2241
2242   switch (elf_class)
2243     {
2244     case ELFCLASSNONE: return _("none");
2245     case ELFCLASS32:   return _("ELF32");
2246     case ELFCLASS64:   return _("ELF64");
2247     default:
2248       sprintf (buff, _("<unknown: %x>"), elf_class);
2249       return buff;
2250     }
2251 }
2252
2253 static const char *
2254 get_data_encoding (encoding)
2255      unsigned char encoding;
2256 {
2257   static char buff [32];
2258
2259   switch (encoding)
2260     {
2261     case ELFDATANONE: return _("none");
2262     case ELFDATA2LSB: return _("2's complement, little endian");
2263     case ELFDATA2MSB: return _("2's complement, big endian");
2264     default:
2265       sprintf (buff, _("<unknown: %x>"), encoding);
2266       return buff;
2267     }
2268 }
2269
2270 static const char *
2271 get_osabi_name (osabi)
2272      unsigned char osabi;
2273 {
2274   static char buff [32];
2275
2276   switch (osabi)
2277     {
2278     case ELFOSABI_NONE:       return _("UNIX - System V");
2279     case ELFOSABI_HPUX:       return _("UNIX - HP-UX");
2280     case ELFOSABI_NETBSD:     return _("UNIX - NetBSD");
2281     case ELFOSABI_LINUX:      return _("UNIX - Linux");
2282     case ELFOSABI_HURD:       return _("GNU/Hurd");
2283     case ELFOSABI_SOLARIS:    return _("UNIX - Solaris");
2284     case ELFOSABI_AIX:        return _("UNIX - AIX");
2285     case ELFOSABI_IRIX:       return _("UNIX - IRIX");
2286     case ELFOSABI_FREEBSD:    return _("UNIX - FreeBSD");
2287     case ELFOSABI_TRU64:      return _("UNIX - TRU64");
2288     case ELFOSABI_MODESTO:    return _("Novell - Modesto");
2289     case ELFOSABI_OPENBSD:    return _("UNIX - OpenBSD");
2290     case ELFOSABI_STANDALONE: return _("Standalone App");
2291     case ELFOSABI_ARM:        return _("ARM");
2292     default:
2293       sprintf (buff, _("<unknown: %x>"), osabi);
2294       return buff;
2295     }
2296 }
2297
2298 /* Decode the data held in 'elf_header'.  */
2299 static int
2300 process_file_header ()
2301 {
2302   if (   elf_header.e_ident [EI_MAG0] != ELFMAG0
2303       || elf_header.e_ident [EI_MAG1] != ELFMAG1
2304       || elf_header.e_ident [EI_MAG2] != ELFMAG2
2305       || elf_header.e_ident [EI_MAG3] != ELFMAG3)
2306     {
2307       error
2308         (_("Not an ELF file - it has the wrong magic bytes at the start\n"));
2309       return 0;
2310     }
2311
2312   if (do_header)
2313     {
2314       int i;
2315
2316       printf (_("ELF Header:\n"));
2317       printf (_("  Magic:   "));
2318       for (i = 0; i < EI_NIDENT; i ++)
2319         printf ("%2.2x ", elf_header.e_ident [i]);
2320       printf ("\n");
2321       printf (_("  Class:                             %s\n"),
2322               get_elf_class (elf_header.e_ident [EI_CLASS]));
2323       printf (_("  Data:                              %s\n"),
2324               get_data_encoding (elf_header.e_ident [EI_DATA]));
2325       printf (_("  Version:                           %d %s\n"),
2326               elf_header.e_ident [EI_VERSION],
2327               (elf_header.e_ident [EI_VERSION] == EV_CURRENT
2328                ? "(current)"
2329                : (elf_header.e_ident [EI_VERSION] != EV_NONE
2330                   ? "<unknown: %lx>"
2331                   : "")));
2332       printf (_("  OS/ABI:                            %s\n"),
2333               get_osabi_name (elf_header.e_ident [EI_OSABI]));
2334       printf (_("  ABI Version:                       %d\n"),
2335               elf_header.e_ident [EI_ABIVERSION]);
2336       printf (_("  Type:                              %s\n"),
2337               get_file_type (elf_header.e_type));
2338       printf (_("  Machine:                           %s\n"),
2339               get_machine_name (elf_header.e_machine));
2340       printf (_("  Version:                           0x%lx\n"),
2341               (unsigned long) elf_header.e_version);
2342
2343       printf (_("  Entry point address:               "));
2344       print_vma ((bfd_vma) elf_header.e_entry, PREFIX_HEX);
2345       printf (_("\n  Start of program headers:          "));
2346       print_vma ((bfd_vma) elf_header.e_phoff, DEC);
2347       printf (_(" (bytes into file)\n  Start of section headers:          "));
2348       print_vma ((bfd_vma) elf_header.e_shoff, DEC);
2349       printf (_(" (bytes into file)\n"));
2350
2351       printf (_("  Flags:                             0x%lx%s\n"),
2352               (unsigned long) elf_header.e_flags,
2353               get_machine_flags (elf_header.e_flags, elf_header.e_machine));
2354       printf (_("  Size of this header:               %ld (bytes)\n"),
2355               (long) elf_header.e_ehsize);
2356       printf (_("  Size of program headers:           %ld (bytes)\n"),
2357               (long) elf_header.e_phentsize);
2358       printf (_("  Number of program headers:         %ld\n"),
2359               (long) elf_header.e_phnum);
2360       printf (_("  Size of section headers:           %ld (bytes)\n"),
2361               (long) elf_header.e_shentsize);
2362       printf (_("  Number of section headers:         %ld\n"),
2363               (long) elf_header.e_shnum);
2364       printf (_("  Section header string table index: %ld\n"),
2365               (long) elf_header.e_shstrndx);
2366     }
2367
2368   return 1;
2369 }
2370
2371
2372 static int
2373 get_32bit_program_headers (file, program_headers)
2374      FILE * file;
2375      Elf_Internal_Phdr * program_headers;
2376 {
2377   Elf32_External_Phdr * phdrs;
2378   Elf32_External_Phdr * external;
2379   Elf32_Internal_Phdr * internal;
2380   unsigned int          i;
2381
2382   phdrs = ((Elf32_External_Phdr *)
2383            get_data (NULL, file, elf_header.e_phoff,
2384                      elf_header.e_phentsize * elf_header.e_phnum,
2385                      _("program headers")));
2386   if (!phdrs)
2387     return 0;
2388
2389   for (i = 0, internal = program_headers, external = phdrs;
2390        i < elf_header.e_phnum;
2391        i ++, internal ++, external ++)
2392     {
2393       internal->p_type   = BYTE_GET (external->p_type);
2394       internal->p_offset = BYTE_GET (external->p_offset);
2395       internal->p_vaddr  = BYTE_GET (external->p_vaddr);
2396       internal->p_paddr  = BYTE_GET (external->p_paddr);
2397       internal->p_filesz = BYTE_GET (external->p_filesz);
2398       internal->p_memsz  = BYTE_GET (external->p_memsz);
2399       internal->p_flags  = BYTE_GET (external->p_flags);
2400       internal->p_align  = BYTE_GET (external->p_align);
2401     }
2402
2403   free (phdrs);
2404
2405   return 1;
2406 }
2407
2408 static int
2409 get_64bit_program_headers (file, program_headers)
2410      FILE * file;
2411      Elf_Internal_Phdr * program_headers;
2412 {
2413   Elf64_External_Phdr * phdrs;
2414   Elf64_External_Phdr * external;
2415   Elf64_Internal_Phdr * internal;
2416   unsigned int          i;
2417
2418   phdrs = ((Elf64_External_Phdr *)
2419            get_data (NULL, file, elf_header.e_phoff,
2420                      elf_header.e_phentsize * elf_header.e_phnum,
2421                      _("program headers")));
2422   if (!phdrs)
2423     return 0;
2424
2425   for (i = 0, internal = program_headers, external = phdrs;
2426        i < elf_header.e_phnum;
2427        i ++, internal ++, external ++)
2428     {
2429       internal->p_type   = BYTE_GET (external->p_type);
2430       internal->p_flags  = BYTE_GET (external->p_flags);
2431       internal->p_offset = BYTE_GET8 (external->p_offset);
2432       internal->p_vaddr  = BYTE_GET8 (external->p_vaddr);
2433       internal->p_paddr  = BYTE_GET8 (external->p_paddr);
2434       internal->p_filesz = BYTE_GET8 (external->p_filesz);
2435       internal->p_memsz  = BYTE_GET8 (external->p_memsz);
2436       internal->p_align  = BYTE_GET8 (external->p_align);
2437     }
2438
2439   free (phdrs);
2440
2441   return 1;
2442 }
2443
2444 static int
2445 process_program_headers (file)
2446      FILE * file;
2447 {
2448   Elf_Internal_Phdr * program_headers;
2449   Elf_Internal_Phdr * segment;
2450   unsigned int        i;
2451
2452   if (elf_header.e_phnum == 0)
2453     {
2454       if (do_segments)
2455         printf (_("\nThere are no program headers in this file.\n"));
2456       return 1;
2457     }
2458
2459   if (do_segments && !do_header)
2460     {
2461       printf (_("\nElf file type is %s\n"), get_file_type (elf_header.e_type));
2462       printf (_("Entry point "));
2463       print_vma ((bfd_vma) elf_header.e_entry, PREFIX_HEX);
2464       printf (_("\nThere are %d program headers, starting at offset "),
2465               elf_header.e_phnum);
2466       print_vma ((bfd_vma) elf_header.e_phoff, DEC);
2467       printf ("\n");
2468     }
2469
2470   program_headers = (Elf_Internal_Phdr *) malloc
2471     (elf_header.e_phnum * sizeof (Elf_Internal_Phdr));
2472
2473   if (program_headers == NULL)
2474     {
2475       error (_("Out of memory\n"));
2476       return 0;
2477     }
2478
2479   if (is_32bit_elf)
2480     i = get_32bit_program_headers (file, program_headers);
2481   else
2482     i = get_64bit_program_headers (file, program_headers);
2483
2484   if (i == 0)
2485     {
2486       free (program_headers);
2487       return 0;
2488     }
2489
2490   if (do_segments)
2491     {
2492       printf
2493         (_("\nProgram Header%s:\n"), elf_header.e_phnum > 1 ? "s" : "");
2494
2495       if (is_32bit_elf)
2496         printf
2497           (_("  Type           Offset   VirtAddr   PhysAddr   FileSiz MemSiz  Flg Align\n"));
2498       else
2499         {
2500           printf
2501             (_("  Type           Offset             VirtAddr           PhysAddr\n"));
2502           printf
2503             (_("                 FileSiz            MemSiz              Flags  Align\n"));
2504         }
2505     }
2506
2507   loadaddr = -1;
2508   dynamic_addr = 0;
2509   dynamic_size = 0;
2510
2511   for (i = 0, segment = program_headers;
2512        i < elf_header.e_phnum;
2513        i ++, segment ++)
2514     {
2515       if (do_segments)
2516         {
2517           printf ("  %-14.14s ", get_segment_type (segment->p_type));
2518
2519           if (is_32bit_elf)
2520             {
2521               printf ("0x%6.6lx ", (unsigned long) segment->p_offset);
2522               printf ("0x%8.8lx ", (unsigned long) segment->p_vaddr);
2523               printf ("0x%8.8lx ", (unsigned long) segment->p_paddr);
2524               printf ("0x%5.5lx ", (unsigned long) segment->p_filesz);
2525               printf ("0x%5.5lx ", (unsigned long) segment->p_memsz);
2526               printf ("%c%c%c ",
2527                       (segment->p_flags & PF_R ? 'R' : ' '),
2528                       (segment->p_flags & PF_W ? 'W' : ' '),
2529                       (segment->p_flags & PF_X ? 'E' : ' '));
2530               printf ("%#lx", (unsigned long) segment->p_align);
2531             }
2532           else
2533             {
2534               print_vma (segment->p_offset, FULL_HEX);
2535               putchar (' ');
2536               print_vma (segment->p_vaddr, FULL_HEX);
2537               putchar (' ');
2538               print_vma (segment->p_paddr, FULL_HEX);
2539               printf ("\n                 ");
2540               print_vma (segment->p_filesz, FULL_HEX);
2541               putchar (' ');
2542               print_vma (segment->p_memsz, FULL_HEX);
2543               printf ("  %c%c%c    ",
2544                       (segment->p_flags & PF_R ? 'R' : ' '),
2545                       (segment->p_flags & PF_W ? 'W' : ' '),
2546                       (segment->p_flags & PF_X ? 'E' : ' '));
2547               print_vma (segment->p_align, HEX);
2548             }
2549         }
2550
2551       switch (segment->p_type)
2552         {
2553         case PT_LOAD:
2554           if (loadaddr == -1)
2555             loadaddr = (segment->p_vaddr & 0xfffff000)
2556               - (segment->p_offset & 0xfffff000);
2557           break;
2558
2559         case PT_DYNAMIC:
2560           if (dynamic_addr)
2561             error (_("more than one dynamic segment\n"));
2562
2563           dynamic_addr = segment->p_offset;
2564           dynamic_size = segment->p_filesz;
2565           break;
2566
2567         case PT_INTERP:
2568           if (fseek (file, (long) segment->p_offset, SEEK_SET))
2569             error (_("Unable to find program interpreter name\n"));
2570           else
2571             {
2572               program_interpreter[0] = 0;
2573               fscanf (file, "%63s", program_interpreter);
2574
2575               if (do_segments)
2576                 printf (_("\n      [Requesting program interpreter: %s]"),
2577                     program_interpreter);
2578             }
2579           break;
2580         }
2581
2582       if (do_segments)
2583         putc ('\n', stdout);
2584     }
2585
2586   if (loadaddr == -1)
2587     {
2588       /* Very strange. */
2589       loadaddr = 0;
2590     }
2591
2592   if (do_segments && section_headers != NULL)
2593     {
2594       printf (_("\n Section to Segment mapping:\n"));
2595       printf (_("  Segment Sections...\n"));
2596
2597       assert (string_table != NULL);
2598
2599       for (i = 0; i < elf_header.e_phnum; i++)
2600         {
2601           int                 j;
2602           Elf_Internal_Shdr * section;
2603
2604           segment = program_headers + i;
2605           section = section_headers;
2606
2607           printf ("   %2.2d     ", i);
2608
2609           for (j = 0; j < elf_header.e_shnum; j++, section ++)
2610             {
2611               if (section->sh_size > 0
2612                   /* Compare allocated sections by VMA, unallocated
2613                      sections by file offset.  */
2614                   && (section->sh_flags & SHF_ALLOC
2615                       ? (section->sh_addr >= segment->p_vaddr
2616                          && section->sh_addr + section->sh_size
2617                          <= segment->p_vaddr + segment->p_memsz)
2618                       : ((bfd_vma) section->sh_offset >= segment->p_offset
2619                          && (section->sh_offset + section->sh_size
2620                              <= segment->p_offset + segment->p_filesz))))
2621                 printf ("%s ", SECTION_NAME (section));
2622             }
2623
2624           putc ('\n',stdout);
2625         }
2626     }
2627
2628   free (program_headers);
2629
2630   return 1;
2631 }
2632
2633
2634 static int
2635 get_32bit_section_headers (file)
2636      FILE * file;
2637 {
2638   Elf32_External_Shdr * shdrs;
2639   Elf32_Internal_Shdr * internal;
2640   unsigned int          i;
2641
2642   shdrs = ((Elf32_External_Shdr *)
2643            get_data (NULL, file, elf_header.e_shoff,
2644                      elf_header.e_shentsize * elf_header.e_shnum,
2645                      _("section headers")));
2646   if (!shdrs)
2647     return 0;
2648
2649   section_headers = (Elf_Internal_Shdr *) malloc
2650     (elf_header.e_shnum * sizeof (Elf_Internal_Shdr));
2651
2652   if (section_headers == NULL)
2653     {
2654       error (_("Out of memory\n"));
2655       return 0;
2656     }
2657
2658   for (i = 0, internal = section_headers;
2659        i < elf_header.e_shnum;
2660        i ++, internal ++)
2661     {
2662       internal->sh_name      = BYTE_GET (shdrs[i].sh_name);
2663       internal->sh_type      = BYTE_GET (shdrs[i].sh_type);
2664       internal->sh_flags     = BYTE_GET (shdrs[i].sh_flags);
2665       internal->sh_addr      = BYTE_GET (shdrs[i].sh_addr);
2666       internal->sh_offset    = BYTE_GET (shdrs[i].sh_offset);
2667       internal->sh_size      = BYTE_GET (shdrs[i].sh_size);
2668       internal->sh_link      = BYTE_GET (shdrs[i].sh_link);
2669       internal->sh_info      = BYTE_GET (shdrs[i].sh_info);
2670       internal->sh_addralign = BYTE_GET (shdrs[i].sh_addralign);
2671       internal->sh_entsize   = BYTE_GET (shdrs[i].sh_entsize);
2672     }
2673
2674   free (shdrs);
2675
2676   return 1;
2677 }
2678
2679 static int
2680 get_64bit_section_headers (file)
2681      FILE * file;
2682 {
2683   Elf64_External_Shdr * shdrs;
2684   Elf64_Internal_Shdr * internal;
2685   unsigned int          i;
2686
2687   shdrs = ((Elf64_External_Shdr *)
2688            get_data (NULL, file, elf_header.e_shoff,
2689                      elf_header.e_shentsize * elf_header.e_shnum,
2690                      _("section headers")));
2691   if (!shdrs)
2692     return 0;
2693
2694   section_headers = (Elf_Internal_Shdr *) malloc
2695     (elf_header.e_shnum * sizeof (Elf_Internal_Shdr));
2696
2697   if (section_headers == NULL)
2698     {
2699       error (_("Out of memory\n"));
2700       return 0;
2701     }
2702
2703   for (i = 0, internal = section_headers;
2704        i < elf_header.e_shnum;
2705        i ++, internal ++)
2706     {
2707       internal->sh_name      = BYTE_GET (shdrs[i].sh_name);
2708       internal->sh_type      = BYTE_GET (shdrs[i].sh_type);
2709       internal->sh_flags     = BYTE_GET8 (shdrs[i].sh_flags);
2710       internal->sh_addr      = BYTE_GET8 (shdrs[i].sh_addr);
2711       internal->sh_size      = BYTE_GET8 (shdrs[i].sh_size);
2712       internal->sh_entsize   = BYTE_GET8 (shdrs[i].sh_entsize);
2713       internal->sh_link      = BYTE_GET (shdrs[i].sh_link);
2714       internal->sh_info      = BYTE_GET (shdrs[i].sh_info);
2715       internal->sh_offset    = BYTE_GET (shdrs[i].sh_offset);
2716       internal->sh_addralign = BYTE_GET (shdrs[i].sh_addralign);
2717     }
2718
2719   free (shdrs);
2720
2721   return 1;
2722 }
2723
2724 static Elf_Internal_Sym *
2725 get_32bit_elf_symbols (file, offset, number)
2726      FILE * file;
2727      unsigned long offset;
2728      unsigned long number;
2729 {
2730   Elf32_External_Sym * esyms;
2731   Elf_Internal_Sym *   isyms;
2732   Elf_Internal_Sym *   psym;
2733   unsigned int         j;
2734
2735   esyms = ((Elf32_External_Sym *)
2736            get_data (NULL, file, offset,
2737                      number * sizeof (Elf32_External_Sym), _("symbols")));
2738   if (!esyms)
2739     return NULL;
2740
2741   isyms = (Elf_Internal_Sym *) malloc (number * sizeof (Elf_Internal_Sym));
2742
2743   if (isyms == NULL)
2744     {
2745       error (_("Out of memory\n"));
2746       free (esyms);
2747
2748       return NULL;
2749     }
2750
2751   for (j = 0, psym = isyms;
2752        j < number;
2753        j ++, psym ++)
2754     {
2755       psym->st_name  = BYTE_GET (esyms[j].st_name);
2756       psym->st_value = BYTE_GET (esyms[j].st_value);
2757       psym->st_size  = BYTE_GET (esyms[j].st_size);
2758       psym->st_shndx = BYTE_GET (esyms[j].st_shndx);
2759       psym->st_info  = BYTE_GET (esyms[j].st_info);
2760       psym->st_other = BYTE_GET (esyms[j].st_other);
2761     }
2762
2763   free (esyms);
2764
2765   return isyms;
2766 }
2767
2768 static Elf_Internal_Sym *
2769 get_64bit_elf_symbols (file, offset, number)
2770      FILE * file;
2771      unsigned long offset;
2772      unsigned long number;
2773 {
2774   Elf64_External_Sym * esyms;
2775   Elf_Internal_Sym *   isyms;
2776   Elf_Internal_Sym *   psym;
2777   unsigned int         j;
2778
2779   esyms = ((Elf64_External_Sym *)
2780            get_data (NULL, file, offset,
2781                      number * sizeof (Elf64_External_Sym), _("symbols")));
2782   if (!esyms)
2783     return NULL;
2784
2785   isyms = (Elf_Internal_Sym *) malloc (number * sizeof (Elf_Internal_Sym));
2786
2787   if (isyms == NULL)
2788     {
2789       error (_("Out of memory\n"));
2790       free (esyms);
2791
2792       return NULL;
2793     }
2794
2795   for (j = 0, psym = isyms;
2796        j < number;
2797        j ++, psym ++)
2798     {
2799       psym->st_name  = BYTE_GET (esyms[j].st_name);
2800       psym->st_info  = BYTE_GET (esyms[j].st_info);
2801       psym->st_other = BYTE_GET (esyms[j].st_other);
2802       psym->st_shndx = BYTE_GET (esyms[j].st_shndx);
2803       psym->st_value = BYTE_GET8 (esyms[j].st_value);
2804       psym->st_size  = BYTE_GET8 (esyms[j].st_size);
2805     }
2806
2807   free (esyms);
2808
2809   return isyms;
2810 }
2811
2812 static const char *
2813 get_elf_section_flags (sh_flags)
2814      bfd_vma sh_flags;
2815 {
2816   static char buff [32];
2817
2818   * buff = 0;
2819
2820   while (sh_flags)
2821     {
2822       bfd_vma flag;
2823
2824       flag = sh_flags & - sh_flags;
2825       sh_flags &= ~ flag;
2826
2827       switch (flag)
2828         {
2829         case SHF_WRITE:            strcat (buff, "W"); break;
2830         case SHF_ALLOC:            strcat (buff, "A"); break;
2831         case SHF_EXECINSTR:        strcat (buff, "X"); break;
2832         case SHF_MERGE:            strcat (buff, "M"); break;
2833         case SHF_STRINGS:          strcat (buff, "S"); break;
2834         case SHF_INFO_LINK:        strcat (buff, "I"); break;
2835         case SHF_LINK_ORDER:       strcat (buff, "L"); break;
2836         case SHF_OS_NONCONFORMING: strcat (buff, "O"); break;
2837         case SHF_GROUP:            strcat (buff, "G"); break;
2838
2839         default:
2840           if (flag & SHF_MASKOS)
2841             {
2842               strcat (buff, "o");
2843               sh_flags &= ~ SHF_MASKOS;
2844             }
2845           else if (flag & SHF_MASKPROC)
2846             {
2847               strcat (buff, "p");
2848               sh_flags &= ~ SHF_MASKPROC;
2849             }
2850           else
2851             strcat (buff, "x");
2852           break;
2853         }
2854     }
2855
2856   return buff;
2857 }
2858
2859 static int
2860 process_section_headers (file)
2861      FILE * file;
2862 {
2863   Elf_Internal_Shdr * section;
2864   int                 i;
2865
2866   section_headers = NULL;
2867
2868   if (elf_header.e_shnum == 0)
2869     {
2870       if (do_sections)
2871         printf (_("\nThere are no sections in this file.\n"));
2872
2873       return 1;
2874     }
2875
2876   if (do_sections && !do_header)
2877     printf (_("There are %d section headers, starting at offset 0x%lx:\n"),
2878             elf_header.e_shnum, (unsigned long) elf_header.e_shoff);
2879
2880   if (is_32bit_elf)
2881     {
2882       if (! get_32bit_section_headers (file))
2883         return 0;
2884     }
2885   else if (! get_64bit_section_headers (file))
2886     return 0;
2887
2888   /* Read in the string table, so that we have names to display.  */
2889   section = section_headers + elf_header.e_shstrndx;
2890
2891   if (section->sh_size != 0)
2892     {
2893       string_table = (char *) get_data (NULL, file, section->sh_offset,
2894                                         section->sh_size, _("string table"));
2895
2896       string_table_length = section->sh_size;
2897     }
2898
2899   /* Scan the sections for the dynamic symbol table
2900      and dynamic string table and debug sections. */
2901   dynamic_symbols = NULL;
2902   dynamic_strings = NULL;
2903   dynamic_syminfo = NULL;
2904
2905   for (i = 0, section = section_headers;
2906        i < elf_header.e_shnum;
2907        i ++, section ++)
2908     {
2909       char * name = SECTION_NAME (section);
2910
2911       if (section->sh_type == SHT_DYNSYM)
2912         {
2913           if (dynamic_symbols != NULL)
2914             {
2915               error (_("File contains multiple dynamic symbol tables\n"));
2916               continue;
2917             }
2918
2919           num_dynamic_syms = section->sh_size / section->sh_entsize;
2920           dynamic_symbols =
2921             GET_ELF_SYMBOLS (file, section->sh_offset, num_dynamic_syms);
2922         }
2923       else if (section->sh_type == SHT_STRTAB
2924                && strcmp (name, ".dynstr") == 0)
2925         {
2926           if (dynamic_strings != NULL)
2927             {
2928               error (_("File contains multiple dynamic string tables\n"));
2929               continue;
2930             }
2931
2932           dynamic_strings = (char *) get_data (NULL, file, section->sh_offset,
2933                                                section->sh_size,
2934                                                _("dynamic strings"));
2935         }
2936       else if ((do_debugging || do_debug_info || do_debug_abbrevs
2937                 || do_debug_lines || do_debug_pubnames || do_debug_aranges
2938                 || do_debug_frames)
2939                && strncmp (name, ".debug_", 7) == 0)
2940         {
2941           name += 7;
2942
2943           if (do_debugging
2944               || (do_debug_info     && (strcmp (name, "info") == 0))
2945               || (do_debug_abbrevs  && (strcmp (name, "abbrev") == 0))
2946               || (do_debug_lines    && (strcmp (name, "line") == 0))
2947               || (do_debug_pubnames && (strcmp (name, "pubnames") == 0))
2948               || (do_debug_aranges  && (strcmp (name, "aranges") == 0))
2949               || (do_debug_frames   && (strcmp (name, "frame") == 0))
2950               )
2951             request_dump (i, DEBUG_DUMP);
2952         }
2953       /* linkonce section to be combined with .debug_info at link time.  */
2954       else if ((do_debugging || do_debug_info)
2955                && strncmp (name, ".gnu.linkonce.wi.", 17) == 0)
2956         request_dump (i, DEBUG_DUMP);
2957       else if (do_debug_frames && strcmp (name, ".eh_frame") == 0)
2958         request_dump (i, DEBUG_DUMP);
2959     }
2960
2961   if (! do_sections)
2962     return 1;
2963
2964   printf (_("\nSection Header%s:\n"), elf_header.e_shnum > 1 ? "s" : "");
2965
2966   if (is_32bit_elf)
2967     printf
2968       (_("  [Nr] Name              Type            Addr     Off    Size   ES Flg Lk Inf Al\n"));
2969   else
2970     {
2971       printf (_("  [Nr] Name              Type             Address           Offset\n"));
2972       printf (_("       Size              EntSize          Flags  Link  Info  Align\n"));
2973     }
2974
2975   for (i = 0, section = section_headers;
2976        i < elf_header.e_shnum;
2977        i ++, section ++)
2978     {
2979       printf ("  [%2d] %-17.17s %-15.15s ",
2980               i,
2981               SECTION_NAME (section),
2982               get_section_type_name (section->sh_type));
2983
2984       if (is_32bit_elf)
2985         {
2986           print_vma (section->sh_addr, LONG_HEX);
2987
2988           printf ( " %6.6lx %6.6lx %2.2lx",
2989                    (unsigned long) section->sh_offset,
2990                    (unsigned long) section->sh_size,
2991                    (unsigned long) section->sh_entsize);
2992
2993           printf (" %3s ", get_elf_section_flags (section->sh_flags));
2994
2995           printf ("%2ld %3lx %2ld\n",
2996                   (unsigned long) section->sh_link,
2997                   (unsigned long) section->sh_info,
2998                   (unsigned long) section->sh_addralign);
2999         }
3000       else
3001         {
3002           putchar (' ');
3003           print_vma (section->sh_addr, LONG_HEX);
3004           printf ("  %8.8lx", section->sh_offset);
3005           printf ("\n       ");
3006           print_vma (section->sh_size, LONG_HEX);
3007           printf ("  ");
3008           print_vma (section->sh_entsize, LONG_HEX);
3009
3010           printf (" %3s ", get_elf_section_flags (section->sh_flags));
3011
3012           printf ("     %2ld   %3lx     %ld\n",
3013                   (unsigned long) section->sh_link,
3014                   (unsigned long) section->sh_info,
3015                   (unsigned long) section->sh_addralign);
3016         }
3017     }
3018
3019   printf (_("Key to Flags:\n"));
3020   printf (_("  W (write), A (alloc), X (execute), M (merge), S (strings)\n"));
3021   printf (_("  I (info), L (link order), G (group), x (unknown)\n"));
3022   printf (_("  O (extra OS processing required) o (OS specific), p (processor specific)\n"));
3023
3024   return 1;
3025 }
3026
3027 /* Process the reloc section.  */
3028 static int
3029 process_relocs (file)
3030      FILE * file;
3031 {
3032   unsigned long    rel_size;
3033   unsigned long    rel_offset;
3034
3035
3036   if (!do_reloc)
3037     return 1;
3038
3039   if (do_using_dynamic)
3040     {
3041       int is_rela = FALSE;
3042
3043       rel_size   = 0;
3044       rel_offset = 0;
3045
3046       if (dynamic_info[DT_REL])
3047         {
3048           rel_offset = dynamic_info[DT_REL];
3049           rel_size   = dynamic_info[DT_RELSZ];
3050           is_rela    = FALSE;
3051         }
3052       else if (dynamic_info [DT_RELA])
3053         {
3054           rel_offset = dynamic_info[DT_RELA];
3055           rel_size   = dynamic_info[DT_RELASZ];
3056           is_rela    = TRUE;
3057         }
3058       else if (dynamic_info[DT_JMPREL])
3059         {
3060           rel_offset = dynamic_info[DT_JMPREL];
3061           rel_size   = dynamic_info[DT_PLTRELSZ];
3062
3063           switch (dynamic_info[DT_PLTREL])
3064             {
3065             case DT_REL:
3066               is_rela = FALSE;
3067               break;
3068             case DT_RELA:
3069               is_rela = TRUE;
3070               break;
3071             default:
3072               is_rela = UNKNOWN;
3073               break;
3074             }
3075         }
3076
3077       if (rel_size)
3078         {
3079           printf
3080             (_("\nRelocation section at offset 0x%lx contains %ld bytes:\n"),
3081              rel_offset, rel_size);
3082
3083           dump_relocations (file, rel_offset - loadaddr, rel_size,
3084                             dynamic_symbols, num_dynamic_syms, dynamic_strings, is_rela);
3085         }
3086       else
3087         printf (_("\nThere are no dynamic relocations in this file.\n"));
3088     }
3089   else
3090     {
3091       Elf32_Internal_Shdr *     section;
3092       unsigned long             i;
3093       int               found = 0;
3094
3095       for (i = 0, section = section_headers;
3096            i < elf_header.e_shnum;
3097            i++, section ++)
3098         {
3099           if (   section->sh_type != SHT_RELA
3100               && section->sh_type != SHT_REL)
3101             continue;
3102
3103           rel_offset = section->sh_offset;
3104           rel_size   = section->sh_size;
3105
3106           if (rel_size)
3107             {
3108               Elf32_Internal_Shdr * strsec;
3109               Elf_Internal_Sym *    symtab;
3110               char *                strtab;
3111               int                   is_rela;
3112               unsigned long         nsyms;
3113
3114               printf (_("\nRelocation section "));
3115
3116               if (string_table == NULL)
3117                 printf ("%d", section->sh_name);
3118               else
3119                 printf ("'%s'", SECTION_NAME (section));
3120
3121               printf (_(" at offset 0x%lx contains %lu entries:\n"),
3122                  rel_offset, (unsigned long) (rel_size / section->sh_entsize));
3123
3124               symtab = NULL;
3125               strtab = NULL;
3126               nsyms = 0;
3127               if (section->sh_link)
3128                 {
3129                   Elf32_Internal_Shdr * symsec;
3130
3131                   symsec = section_headers + section->sh_link;
3132                   nsyms = symsec->sh_size / symsec->sh_entsize;
3133                   symtab = GET_ELF_SYMBOLS (file, symsec->sh_offset, nsyms);
3134
3135                   if (symtab == NULL)
3136                     continue;
3137
3138                   strsec = section_headers + symsec->sh_link;
3139
3140                   strtab = (char *) get_data (NULL, file, strsec->sh_offset,
3141                                               strsec->sh_size,
3142                                               _("string table"));
3143                 }
3144               is_rela = section->sh_type == SHT_RELA;
3145
3146               dump_relocations (file, rel_offset, rel_size,
3147                                 symtab, nsyms, strtab, is_rela);
3148
3149               if (strtab)
3150                 free (strtab);
3151               if (symtab)
3152                 free (symtab);
3153
3154               found = 1;
3155             }
3156         }
3157
3158       if (! found)
3159         printf (_("\nThere are no relocations in this file.\n"));
3160     }
3161
3162   return 1;
3163 }
3164
3165 #include "unwind-ia64.h"
3166
3167 /* An absolute address consists of a section and an offset.  If the
3168    section is NULL, the offset itself is the address, otherwise, the
3169    address equals to LOAD_ADDRESS(section) + offset.  */
3170
3171 struct absaddr
3172   {
3173     unsigned short section;
3174     bfd_vma offset;
3175   };
3176
3177 struct unw_aux_info
3178   {
3179     struct unw_table_entry
3180       {
3181         struct absaddr    start;
3182         struct absaddr    end;
3183         struct absaddr    info;
3184       }
3185     *table;                             /* Unwind table.  */
3186     unsigned long         table_len;    /* Length of unwind table.  */
3187     unsigned char *       info;         /* Unwind info.  */
3188     unsigned long         info_size;    /* Size of unwind info.  */
3189     bfd_vma               info_addr;    /* starting address of unwind info.  */
3190     bfd_vma               seg_base;     /* Starting address of segment.  */
3191     Elf_Internal_Sym *    symtab;       /* The symbol table.  */
3192     unsigned              long nsyms;   /* Number of symbols.  */
3193     char *                strtab;       /* The string table.  */
3194     unsigned long         strtab_size;  /* Size of string table.  */
3195   };
3196
3197 static void find_symbol_for_address PARAMS ((struct unw_aux_info *,
3198                                              struct absaddr, const char **,
3199                                              bfd_vma *));
3200 static void dump_ia64_unwind PARAMS ((struct unw_aux_info *));
3201 static int  slurp_ia64_unwind_table PARAMS ((FILE *, struct unw_aux_info *,
3202                                             Elf32_Internal_Shdr *));
3203
3204 static void
3205 find_symbol_for_address (aux, addr, symname, offset)
3206      struct unw_aux_info *aux;
3207      struct absaddr addr;
3208      const char **symname;
3209      bfd_vma *offset;
3210 {
3211   bfd_vma dist = (bfd_vma) 0x100000;
3212   Elf_Internal_Sym *sym, *best = NULL;
3213   unsigned long i;
3214
3215   for (i = 0, sym = aux->symtab; i < aux->nsyms; ++i, ++sym)
3216     {
3217       if (ELF_ST_TYPE (sym->st_info) == STT_FUNC
3218           && sym->st_name != 0
3219           && (addr.section == SHN_UNDEF || addr.section == sym->st_shndx)
3220           && addr.offset >= sym->st_value
3221           && addr.offset - sym->st_value < dist)
3222         {
3223           best = sym;
3224           dist = addr.offset - sym->st_value;
3225           if (!dist)
3226             break;
3227         }
3228     }
3229   if (best)
3230     {
3231       *symname = (best->st_name >= aux->strtab_size
3232                   ? "<corrupt>" : aux->strtab + best->st_name);
3233       *offset = dist;
3234       return;
3235     }
3236   *symname = NULL;
3237   *offset = addr.offset;
3238 }
3239
3240 static void
3241 dump_ia64_unwind (aux)
3242      struct unw_aux_info *aux;
3243 {
3244   bfd_vma addr_size;
3245   struct unw_table_entry * tp;
3246   int in_body;
3247
3248   addr_size = is_32bit_elf ? 4 : 8;
3249
3250   for (tp = aux->table; tp < aux->table + aux->table_len; ++tp)
3251     {
3252       bfd_vma stamp;
3253       bfd_vma offset;
3254       const unsigned char * dp;
3255       const unsigned char * head;
3256       const char * procname;
3257
3258       find_symbol_for_address (aux, tp->start, &procname, &offset);
3259
3260       fputs ("\n<", stdout);
3261
3262       if (procname)
3263         {
3264           fputs (procname, stdout);
3265
3266           if (offset)
3267             printf ("+%lx", (unsigned long) offset);
3268         }
3269
3270       fputs (">: [", stdout);
3271       print_vma (tp->start.offset, PREFIX_HEX);
3272       fputc ('-', stdout);
3273       print_vma (tp->end.offset, PREFIX_HEX);
3274       printf ("), info at +0x%lx\n",
3275               (unsigned long) (tp->info.offset - aux->seg_base));
3276
3277       head = aux->info + (tp->info.offset - aux->info_addr);
3278       stamp = BYTE_GET8 ((unsigned char *) head);
3279
3280       printf ("  v%u, flags=0x%lx (%s%s ), len=%lu bytes\n",
3281               (unsigned) UNW_VER (stamp),
3282               (unsigned long) ((stamp & UNW_FLAG_MASK) >> 32),
3283               UNW_FLAG_EHANDLER (stamp) ? " ehandler" : "",
3284               UNW_FLAG_UHANDLER (stamp) ? " uhandler" : "",
3285               (unsigned long) (addr_size * UNW_LENGTH (stamp)));
3286
3287       if (UNW_VER (stamp) != 1)
3288         {
3289           printf ("\tUnknown version.\n");
3290           continue;
3291         }
3292
3293       in_body = 0;
3294       for (dp = head + 8; dp < head + 8 + addr_size * UNW_LENGTH (stamp);)
3295         dp = unw_decode (dp, in_body, & in_body);
3296     }
3297 }
3298
3299 static int
3300 slurp_ia64_unwind_table (file, aux, sec)
3301      FILE *file;
3302      struct unw_aux_info *aux;
3303      Elf32_Internal_Shdr *sec;
3304 {
3305   unsigned long size, addr_size, nrelas, i;
3306   Elf_Internal_Phdr *prog_hdrs, *seg;
3307   struct unw_table_entry *tep;
3308   Elf32_Internal_Shdr *relsec;
3309   Elf_Internal_Rela *rela, *rp;
3310   unsigned char *table, *tp;
3311   Elf_Internal_Sym *sym;
3312   const char *relname;
3313   int result;
3314
3315   addr_size = is_32bit_elf ? 4 : 8;
3316
3317   /* First, find the starting address of the segment that includes
3318      this section: */
3319
3320   if (elf_header.e_phnum)
3321     {
3322       prog_hdrs = (Elf_Internal_Phdr *)
3323         xmalloc (elf_header.e_phnum * sizeof (Elf_Internal_Phdr));
3324
3325       if (is_32bit_elf)
3326         result = get_32bit_program_headers (file, prog_hdrs);
3327       else
3328         result = get_64bit_program_headers (file, prog_hdrs);
3329
3330       if (!result)
3331         {
3332           free (prog_hdrs);
3333           return 0;
3334         }
3335
3336       for (seg = prog_hdrs; seg < prog_hdrs + elf_header.e_phnum; ++seg)
3337         {
3338           if (seg->p_type != PT_LOAD)
3339             continue;
3340
3341           if (sec->sh_addr >= seg->p_vaddr
3342               && (sec->sh_addr + sec->sh_size <= seg->p_vaddr + seg->p_memsz))
3343             {
3344               aux->seg_base = seg->p_vaddr;
3345               break;
3346             }
3347         }
3348
3349       free (prog_hdrs);
3350     }
3351
3352   /* Second, build the unwind table from the contents of the unwind section:  */
3353   size = sec->sh_size;
3354   table = (char *) get_data (NULL, file, sec->sh_offset,
3355                              size, _("unwind table"));
3356   if (!table)
3357     return 0;
3358
3359   tep = aux->table = xmalloc (size / (3 * addr_size) * sizeof (aux->table[0]));
3360   for (tp = table; tp < table + size; tp += 3 * addr_size, ++ tep)
3361     {
3362       tep->start.section = SHN_UNDEF;
3363       tep->end.section   = SHN_UNDEF;
3364       tep->info.section  = SHN_UNDEF;
3365       if (is_32bit_elf)
3366         {
3367           tep->start.offset = byte_get ((unsigned char *) tp + 0, 4);
3368           tep->end.offset   = byte_get ((unsigned char *) tp + 4, 4);
3369           tep->info.offset  = byte_get ((unsigned char *) tp + 8, 4);
3370         }
3371       else
3372         {
3373           tep->start.offset = BYTE_GET8 ((unsigned char *) tp +  0);
3374           tep->end.offset   = BYTE_GET8 ((unsigned char *) tp +  8);
3375           tep->info.offset  = BYTE_GET8 ((unsigned char *) tp + 16);
3376         }
3377       tep->start.offset += aux->seg_base;
3378       tep->end.offset   += aux->seg_base;
3379       tep->info.offset  += aux->seg_base;
3380     }
3381   free (table);
3382
3383   /* Third, apply any relocations to the unwind table: */
3384
3385   for (relsec = section_headers;
3386        relsec < section_headers + elf_header.e_shnum;
3387        ++relsec)
3388     {
3389       if (relsec->sh_type != SHT_RELA
3390           || section_headers + relsec->sh_info != sec)
3391         continue;
3392
3393       if (!slurp_rela_relocs (file, relsec->sh_offset, relsec->sh_size,
3394                               & rela, & nrelas))
3395         return 0;
3396
3397       for (rp = rela; rp < rela + nrelas; ++rp)
3398         {
3399           if (is_32bit_elf)
3400             {
3401               relname = elf_ia64_reloc_type (ELF32_R_TYPE (rp->r_info));
3402               sym = aux->symtab + ELF32_R_SYM (rp->r_info);
3403
3404               if (ELF32_ST_TYPE (sym->st_info) != STT_SECTION)
3405                 {
3406                   warn (_("Skipping unexpected symbol type %u"),
3407                         ELF32_ST_TYPE (sym->st_info));
3408                   continue;
3409                 }
3410             }
3411           else
3412             {
3413               relname = elf_ia64_reloc_type (ELF64_R_TYPE (rp->r_info));
3414               sym = aux->symtab + ELF64_R_SYM (rp->r_info);
3415
3416               if (ELF64_ST_TYPE (sym->st_info) != STT_SECTION)
3417                 {
3418                   warn (_("Skipping unexpected symbol type %u"),
3419                         ELF64_ST_TYPE (sym->st_info));
3420                   continue;
3421                 }
3422             }
3423
3424           if (strncmp (relname, "R_IA64_SEGREL", 13) != 0)
3425             {
3426               warn (_("Skipping unexpected relocation type %s"), relname);
3427               continue;
3428             }
3429
3430           i = rp->r_offset / (3 * addr_size);
3431
3432           switch (rp->r_offset/addr_size % 3)
3433             {
3434             case 0:
3435               aux->table[i].start.section = sym->st_shndx;
3436               aux->table[i].start.offset += rp->r_addend;
3437               break;
3438             case 1:
3439               aux->table[i].end.section   = sym->st_shndx;
3440               aux->table[i].end.offset   += rp->r_addend;
3441               break;
3442             case 2:
3443               aux->table[i].info.section  = sym->st_shndx;
3444               aux->table[i].info.offset  += rp->r_addend;
3445               break;
3446             default:
3447               break;
3448             }
3449         }
3450
3451       free (rela);
3452     }
3453
3454   aux->table_len = size / (3 * addr_size);
3455   return 1;
3456 }
3457
3458 static int
3459 process_unwind (file)
3460      FILE * file;
3461 {
3462   Elf32_Internal_Shdr *sec, *unwsec = NULL, *strsec;
3463   unsigned long i, addr_size, unwcount = 0, unwstart = 0;
3464   struct unw_aux_info aux;
3465
3466   if (!do_unwind)
3467     return 1;
3468
3469   if (elf_header.e_machine != EM_IA_64)
3470     {
3471       printf (_("\nThere are no unwind sections in this file.\n"));
3472       return 1;
3473     }
3474
3475   memset (& aux, 0, sizeof (aux));
3476
3477   addr_size = is_32bit_elf ? 4 : 8;
3478
3479   for (i = 0, sec = section_headers; i < elf_header.e_shnum; ++i, ++sec)
3480     {
3481       if (sec->sh_type == SHT_SYMTAB)
3482         {
3483           aux.nsyms = sec->sh_size / sec->sh_entsize;
3484           aux.symtab = GET_ELF_SYMBOLS (file, sec->sh_offset, aux.nsyms);
3485
3486           strsec = section_headers + sec->sh_link;
3487           aux.strtab_size = strsec->sh_size;
3488           aux.strtab = (char *) get_data (NULL, file, strsec->sh_offset,
3489                                           aux.strtab_size, _("string table"));
3490         }
3491       else if (sec->sh_type == SHT_IA_64_UNWIND)
3492         unwcount++;
3493     }
3494
3495   if (!unwcount)
3496     printf (_("\nThere are no unwind sections in this file.\n"));
3497
3498   while (unwcount-- > 0)
3499     {
3500       char *suffix;
3501       size_t len, len2;
3502
3503       for (i = unwstart, sec = section_headers + unwstart;
3504            i < elf_header.e_shnum; ++i, ++sec)
3505         if (sec->sh_type == SHT_IA_64_UNWIND)
3506           {
3507             unwsec = sec;
3508             break;
3509           }
3510
3511       unwstart = i + 1;
3512       len = sizeof (ELF_STRING_ia64_unwind_once) - 1;
3513
3514       if (strncmp (SECTION_NAME (unwsec), ELF_STRING_ia64_unwind_once,
3515                    len) == 0)
3516         {
3517           /* .gnu.linkonce.ia64unw.FOO -> .gnu.linkonce.ia64unwi.FOO */
3518           len2 = sizeof (ELF_STRING_ia64_unwind_info_once) - 1;
3519           suffix = SECTION_NAME (unwsec) + len;
3520           for (i = 0, sec = section_headers; i < elf_header.e_shnum;
3521                ++i, ++sec)
3522             if (strncmp (SECTION_NAME (sec),
3523                          ELF_STRING_ia64_unwind_info_once, len2) == 0
3524                 && strcmp (SECTION_NAME (sec) + len2, suffix) == 0)
3525               break;
3526         }
3527       else
3528         {
3529           /* .IA_64.unwindFOO -> .IA_64.unwind_infoFOO
3530              .IA_64.unwind or BAR -> .IA_64.unwind_info */
3531           len = sizeof (ELF_STRING_ia64_unwind) - 1;
3532           len2 = sizeof (ELF_STRING_ia64_unwind_info) - 1;
3533           suffix = "";
3534           if (strncmp (SECTION_NAME (unwsec), ELF_STRING_ia64_unwind,
3535                        len) == 0)
3536             suffix = SECTION_NAME (unwsec) + len;
3537           for (i = 0, sec = section_headers; i < elf_header.e_shnum;
3538                ++i, ++sec)
3539             if (strncmp (SECTION_NAME (sec),
3540                          ELF_STRING_ia64_unwind_info, len2) == 0
3541                 && strcmp (SECTION_NAME (sec) + len2, suffix) == 0)
3542               break;
3543         }
3544
3545       if (i == elf_header.e_shnum)
3546         {
3547           printf (_("\nCould not find unwind info section for "));
3548
3549           if (string_table == NULL)
3550             printf ("%d", unwsec->sh_name);
3551           else
3552             printf ("'%s'", SECTION_NAME (unwsec));
3553         }
3554       else
3555         {
3556           aux.info_size = sec->sh_size;
3557           aux.info_addr = sec->sh_addr;
3558           aux.info = (char *) get_data (NULL, file, sec->sh_offset,
3559                                         aux.info_size, _("unwind info"));
3560
3561           printf (_("\nUnwind section "));
3562
3563           if (string_table == NULL)
3564             printf ("%d", unwsec->sh_name);
3565           else
3566             printf ("'%s'", SECTION_NAME (unwsec));
3567
3568           printf (_(" at offset 0x%lx contains %lu entries:\n"),
3569                   unwsec->sh_offset,
3570                   (unsigned long) (unwsec->sh_size / (3 * addr_size)));
3571
3572           (void) slurp_ia64_unwind_table (file, & aux, unwsec);
3573
3574           if (aux.table_len > 0)
3575             dump_ia64_unwind (& aux);
3576
3577           if (aux.table)
3578             free ((char *) aux.table);
3579           if (aux.info)
3580             free ((char *) aux.info);
3581           aux.table = NULL;
3582           aux.info = NULL;
3583         }
3584     }
3585
3586   if (aux.symtab)
3587     free (aux.symtab);
3588   if (aux.strtab)
3589     free ((char *) aux.strtab);
3590
3591   return 1;
3592 }
3593
3594 static void
3595 dynamic_segment_mips_val (entry)
3596      Elf_Internal_Dyn * entry;
3597 {
3598   switch (entry->d_tag)
3599     {
3600     case DT_MIPS_FLAGS:
3601       if (entry->d_un.d_val == 0)
3602         printf ("NONE\n");
3603       else
3604         {
3605           static const char * opts[] =
3606           {
3607             "QUICKSTART", "NOTPOT", "NO_LIBRARY_REPLACEMENT",
3608             "NO_MOVE", "SGI_ONLY", "GUARANTEE_INIT", "DELTA_C_PLUS_PLUS",
3609             "GUARANTEE_START_INIT", "PIXIE", "DEFAULT_DELAY_LOAD",
3610             "REQUICKSTART", "REQUICKSTARTED", "CORD", "NO_UNRES_UNDEF",
3611             "RLD_ORDER_SAFE"
3612           };
3613           unsigned int cnt;
3614           int first = 1;
3615           for (cnt = 0; cnt < NUM_ELEM (opts); ++ cnt)
3616             if (entry->d_un.d_val & (1 << cnt))
3617               {
3618                 printf ("%s%s", first ? "" : " ", opts[cnt]);
3619                 first = 0;
3620               }
3621           puts ("");
3622         }
3623       break;
3624
3625     case DT_MIPS_IVERSION:
3626       if (dynamic_strings != NULL)
3627         printf ("Interface Version: %s\n",
3628                 dynamic_strings + entry->d_un.d_val);
3629       else
3630         printf ("%ld\n", (long) entry->d_un.d_ptr);
3631       break;
3632
3633     case DT_MIPS_TIME_STAMP:
3634       {
3635         char timebuf[20];
3636         struct tm * tmp;
3637
3638         time_t time = entry->d_un.d_val;
3639         tmp = gmtime (&time);
3640         sprintf (timebuf, "%04u-%02u-%02uT%02u:%02u:%02u",
3641                  tmp->tm_year + 1900, tmp->tm_mon + 1, tmp->tm_mday,
3642                  tmp->tm_hour, tmp->tm_min, tmp->tm_sec);
3643         printf ("Time Stamp: %s\n", timebuf);
3644       }
3645       break;
3646
3647     case DT_MIPS_RLD_VERSION:
3648     case DT_MIPS_LOCAL_GOTNO:
3649     case DT_MIPS_CONFLICTNO:
3650     case DT_MIPS_LIBLISTNO:
3651     case DT_MIPS_SYMTABNO:
3652     case DT_MIPS_UNREFEXTNO:
3653     case DT_MIPS_HIPAGENO:
3654     case DT_MIPS_DELTA_CLASS_NO:
3655     case DT_MIPS_DELTA_INSTANCE_NO:
3656     case DT_MIPS_DELTA_RELOC_NO:
3657     case DT_MIPS_DELTA_SYM_NO:
3658     case DT_MIPS_DELTA_CLASSSYM_NO:
3659     case DT_MIPS_COMPACT_SIZE:
3660       printf ("%ld\n", (long) entry->d_un.d_ptr);
3661       break;
3662
3663     default:
3664       printf ("%#lx\n", (long) entry->d_un.d_ptr);
3665     }
3666 }
3667
3668
3669 static void
3670 dynamic_segment_parisc_val (entry)
3671      Elf_Internal_Dyn * entry;
3672 {
3673   switch (entry->d_tag)
3674     {
3675     case DT_HP_DLD_FLAGS:
3676       {
3677         static struct
3678         {
3679           long int bit;
3680           const char * str;
3681         }
3682         flags[] =
3683         {
3684           { DT_HP_DEBUG_PRIVATE, "HP_DEBUG_PRIVATE" },
3685           { DT_HP_DEBUG_CALLBACK, "HP_DEBUG_CALLBACK" },
3686           { DT_HP_DEBUG_CALLBACK_BOR, "HP_DEBUG_CALLBACK_BOR" },
3687           { DT_HP_NO_ENVVAR, "HP_NO_ENVVAR" },
3688           { DT_HP_BIND_NOW, "HP_BIND_NOW" },
3689           { DT_HP_BIND_NONFATAL, "HP_BIND_NONFATAL" },
3690           { DT_HP_BIND_VERBOSE, "HP_BIND_VERBOSE" },
3691           { DT_HP_BIND_RESTRICTED, "HP_BIND_RESTRICTED" },
3692           { DT_HP_BIND_SYMBOLIC, "HP_BIND_SYMBOLIC" },
3693           { DT_HP_RPATH_FIRST, "HP_RPATH_FIRST" },
3694           { DT_HP_BIND_DEPTH_FIRST, "HP_BIND_DEPTH_FIRST" }
3695         };
3696         int first = 1;
3697         size_t cnt;
3698         bfd_vma val = entry->d_un.d_val;
3699
3700         for (cnt = 0; cnt < sizeof (flags) / sizeof (flags[0]); ++cnt)
3701           if (val & flags[cnt].bit)
3702             {
3703               if (! first)
3704                 putchar (' ');
3705               fputs (flags[cnt].str, stdout);
3706               first = 0;
3707               val ^= flags[cnt].bit;
3708             }
3709
3710         if (val != 0 || first)
3711           {
3712             if (! first)
3713               putchar (' ');
3714             print_vma (val, HEX);
3715           }
3716       }
3717       break;
3718
3719     default:
3720       print_vma (entry->d_un.d_ptr, PREFIX_HEX);
3721       break;
3722     }
3723 }
3724
3725 static int
3726 get_32bit_dynamic_segment (file)
3727      FILE * file;
3728 {
3729   Elf32_External_Dyn * edyn;
3730   Elf_Internal_Dyn *   entry;
3731   bfd_size_type        i;
3732
3733   edyn = (Elf32_External_Dyn *) get_data (NULL, file, dynamic_addr,
3734                                           dynamic_size, _("dynamic segment"));
3735   if (!edyn)
3736     return 0;
3737
3738   /* SGI's ELF has more than one section in the DYNAMIC segment.  Determine
3739      how large this .dynamic is now.  We can do this even before the byte
3740      swapping since the DT_NULL tag is recognizable.  */
3741   dynamic_size = 0;
3742   while (*(Elf32_Word *) edyn [dynamic_size++].d_tag != DT_NULL)
3743     ;
3744
3745   dynamic_segment = (Elf_Internal_Dyn *)
3746     malloc (dynamic_size * sizeof (Elf_Internal_Dyn));
3747
3748   if (dynamic_segment == NULL)
3749     {
3750       error (_("Out of memory\n"));
3751       free (edyn);
3752       return 0;
3753     }
3754
3755   for (i = 0, entry = dynamic_segment;
3756        i < dynamic_size;
3757        i ++, entry ++)
3758     {
3759       entry->d_tag      = BYTE_GET (edyn [i].d_tag);
3760       entry->d_un.d_val = BYTE_GET (edyn [i].d_un.d_val);
3761     }
3762
3763   free (edyn);
3764
3765   return 1;
3766 }
3767
3768 static int
3769 get_64bit_dynamic_segment (file)
3770      FILE * file;
3771 {
3772   Elf64_External_Dyn * edyn;
3773   Elf_Internal_Dyn *   entry;
3774   bfd_size_type        i;
3775
3776   edyn = (Elf64_External_Dyn *) get_data (NULL, file, dynamic_addr,
3777                                           dynamic_size, _("dynamic segment"));
3778   if (!edyn)
3779     return 0;
3780
3781   /* SGI's ELF has more than one section in the DYNAMIC segment.  Determine
3782      how large this .dynamic is now.  We can do this even before the byte
3783      swapping since the DT_NULL tag is recognizable.  */
3784   dynamic_size = 0;
3785   while (*(bfd_vma *) edyn [dynamic_size ++].d_tag != DT_NULL)
3786     ;
3787
3788   dynamic_segment = (Elf_Internal_Dyn *)
3789     malloc (dynamic_size * sizeof (Elf_Internal_Dyn));
3790
3791   if (dynamic_segment == NULL)
3792     {
3793       error (_("Out of memory\n"));
3794       free (edyn);
3795       return 0;
3796     }
3797
3798   for (i = 0, entry = dynamic_segment;
3799        i < dynamic_size;
3800        i ++, entry ++)
3801     {
3802       entry->d_tag      = BYTE_GET8 (edyn [i].d_tag);
3803       entry->d_un.d_val = BYTE_GET8 (edyn [i].d_un.d_val);
3804     }
3805
3806   free (edyn);
3807
3808   return 1;
3809 }
3810
3811 static const char *
3812 get_dynamic_flags (flags)
3813      bfd_vma flags;
3814 {
3815   static char buff [64];
3816   while (flags)
3817     {
3818       bfd_vma flag;
3819
3820       flag = flags & - flags;
3821       flags &= ~ flag;
3822
3823       switch (flag)
3824         {
3825         case DF_ORIGIN:   strcat (buff, "ORIGIN "); break;
3826         case DF_SYMBOLIC: strcat (buff, "SYMBOLIC "); break;
3827         case DF_TEXTREL:  strcat (buff, "TEXTREL "); break;
3828         case DF_BIND_NOW: strcat (buff, "BIND_NOW "); break;
3829         default:          strcat (buff, "unknown "); break;
3830         }
3831     }
3832   return buff;
3833 }
3834
3835 /* Parse and display the contents of the dynamic segment.  */
3836 static int
3837 process_dynamic_segment (file)
3838      FILE * file;
3839 {
3840   Elf_Internal_Dyn * entry;
3841   bfd_size_type      i;
3842
3843   if (dynamic_size == 0)
3844     {
3845       if (do_dynamic)
3846         printf (_("\nThere is no dynamic segment in this file.\n"));
3847
3848       return 1;
3849     }
3850
3851   if (is_32bit_elf)
3852     {
3853       if (! get_32bit_dynamic_segment (file))
3854         return 0;
3855     }
3856   else if (! get_64bit_dynamic_segment (file))
3857     return 0;
3858
3859   /* Find the appropriate symbol table.  */
3860   if (dynamic_symbols == NULL)
3861     {
3862       for (i = 0, entry = dynamic_segment;
3863            i < dynamic_size;
3864            ++i, ++ entry)
3865         {
3866           unsigned long        offset;
3867
3868           if (entry->d_tag != DT_SYMTAB)
3869             continue;
3870
3871           dynamic_info[DT_SYMTAB] = entry->d_un.d_val;
3872
3873           /* Since we do not know how big the symbol table is,
3874              we default to reading in the entire file (!) and
3875              processing that.  This is overkill, I know, but it
3876              should work. */
3877           offset = entry->d_un.d_val - loadaddr;
3878
3879           if (fseek (file, 0, SEEK_END))
3880             error (_("Unable to seek to end of file!"));
3881
3882           if (is_32bit_elf)
3883             num_dynamic_syms = (ftell (file) - offset) / sizeof (Elf32_External_Sym);
3884           else
3885             num_dynamic_syms = (ftell (file) - offset) / sizeof (Elf64_External_Sym);
3886
3887           if (num_dynamic_syms < 1)
3888             {
3889               error (_("Unable to determine the number of symbols to load\n"));
3890               continue;
3891             }
3892
3893           dynamic_symbols = GET_ELF_SYMBOLS (file, offset, num_dynamic_syms);
3894         }
3895     }
3896
3897   /* Similarly find a string table.  */
3898   if (dynamic_strings == NULL)
3899     {
3900       for (i = 0, entry = dynamic_segment;
3901            i < dynamic_size;
3902            ++i, ++ entry)
3903         {
3904           unsigned long offset;
3905           long          str_tab_len;
3906
3907           if (entry->d_tag != DT_STRTAB)
3908             continue;
3909
3910           dynamic_info[DT_STRTAB] = entry->d_un.d_val;
3911
3912           /* Since we do not know how big the string table is,
3913              we default to reading in the entire file (!) and
3914              processing that.  This is overkill, I know, but it
3915              should work. */
3916
3917           offset = entry->d_un.d_val - loadaddr;
3918           if (fseek (file, 0, SEEK_END))
3919             error (_("Unable to seek to end of file\n"));
3920           str_tab_len = ftell (file) - offset;
3921
3922           if (str_tab_len < 1)
3923             {
3924               error
3925                 (_("Unable to determine the length of the dynamic string table\n"));
3926               continue;
3927             }
3928
3929           dynamic_strings = (char *) get_data (NULL, file, offset, str_tab_len,
3930                                                _("dynamic string table"));
3931
3932           break;
3933         }
3934     }
3935
3936   /* And find the syminfo section if available.  */
3937   if (dynamic_syminfo == NULL)
3938     {
3939       unsigned int syminsz = 0;
3940
3941       for (i = 0, entry = dynamic_segment;
3942            i < dynamic_size;
3943            ++i, ++ entry)
3944         {
3945           if (entry->d_tag == DT_SYMINENT)
3946             {
3947               /* Note: these braces are necessary to avoid a syntax
3948                  error from the SunOS4 C compiler.  */
3949               assert (sizeof (Elf_External_Syminfo) == entry->d_un.d_val);
3950             }
3951           else if (entry->d_tag == DT_SYMINSZ)
3952             syminsz = entry->d_un.d_val;
3953           else if (entry->d_tag == DT_SYMINFO)
3954             dynamic_syminfo_offset = entry->d_un.d_val - loadaddr;
3955         }
3956
3957       if (dynamic_syminfo_offset != 0 && syminsz != 0)
3958         {
3959           Elf_External_Syminfo * extsyminfo;
3960           Elf_Internal_Syminfo * syminfo;
3961
3962           /* There is a syminfo section.  Read the data.  */
3963           extsyminfo = ((Elf_External_Syminfo *)
3964                         get_data (NULL, file, dynamic_syminfo_offset,
3965                                   syminsz, _("symbol information")));
3966           if (!extsyminfo)
3967             return 0;
3968
3969           dynamic_syminfo = (Elf_Internal_Syminfo *) malloc (syminsz);
3970           if (dynamic_syminfo == NULL)
3971             {
3972               error (_("Out of memory\n"));
3973               return 0;
3974             }
3975
3976           dynamic_syminfo_nent = syminsz / sizeof (Elf_External_Syminfo);
3977           for (i = 0, syminfo = dynamic_syminfo; i < dynamic_syminfo_nent;
3978                ++i, ++syminfo)
3979             {
3980               syminfo->si_boundto = BYTE_GET (extsyminfo[i].si_boundto);
3981               syminfo->si_flags = BYTE_GET (extsyminfo[i].si_flags);
3982             }
3983
3984           free (extsyminfo);
3985         }
3986     }
3987
3988   if (do_dynamic && dynamic_addr)
3989     printf (_("\nDynamic segment at offset 0x%x contains %ld entries:\n"),
3990             dynamic_addr, (long) dynamic_size);
3991   if (do_dynamic)
3992     printf (_("  Tag        Type                         Name/Value\n"));
3993
3994   for (i = 0, entry = dynamic_segment;
3995        i < dynamic_size;
3996        i++, entry ++)
3997     {
3998       if (do_dynamic)
3999         {
4000           const char * dtype;
4001
4002           putchar (' ');
4003           print_vma (entry->d_tag, FULL_HEX);
4004           dtype = get_dynamic_type (entry->d_tag);
4005           printf (" (%s)%*s", dtype,
4006                   ((is_32bit_elf ? 27 : 19)
4007                    - (int) strlen (dtype)),
4008                   " ");
4009         }
4010
4011       switch (entry->d_tag)
4012         {
4013         case DT_FLAGS:
4014           if (do_dynamic)
4015             printf ("%s", get_dynamic_flags (entry->d_un.d_val));
4016           break;
4017
4018         case DT_AUXILIARY:
4019         case DT_FILTER:
4020         case DT_CONFIG:
4021         case DT_DEPAUDIT:
4022         case DT_AUDIT:
4023           if (do_dynamic)
4024             {
4025               switch (entry->d_tag)
4026                 {
4027                 case DT_AUXILIARY:
4028                   printf (_("Auxiliary library"));
4029                   break;
4030
4031                 case DT_FILTER:
4032                   printf (_("Filter library"));
4033                   break;
4034
4035                 case DT_CONFIG:
4036                   printf (_("Configuration file"));
4037                   break;
4038
4039                 case DT_DEPAUDIT:
4040                   printf (_("Dependency audit library"));
4041                   break;
4042
4043                 case DT_AUDIT:
4044                   printf (_("Audit library"));
4045                   break;
4046                 }
4047
4048               if (dynamic_strings)
4049                 printf (": [%s]\n", dynamic_strings + entry->d_un.d_val);
4050               else
4051                 {
4052                   printf (": ");
4053                   print_vma (entry->d_un.d_val, PREFIX_HEX);
4054                   putchar ('\n');
4055                 }
4056             }
4057           break;
4058
4059         case DT_FEATURE:
4060           if (do_dynamic)
4061             {
4062               printf (_("Flags:"));
4063               if (entry->d_un.d_val == 0)
4064                 printf (_(" None\n"));
4065               else
4066                 {
4067                   unsigned long int val = entry->d_un.d_val;
4068                   if (val & DTF_1_PARINIT)
4069                     {
4070                       printf (" PARINIT");
4071                       val ^= DTF_1_PARINIT;
4072                     }
4073                   if (val & DTF_1_CONFEXP)
4074                     {
4075                       printf (" CONFEXP");
4076                       val ^= DTF_1_CONFEXP;
4077                     }
4078                   if (val != 0)
4079                     printf (" %lx", val);
4080                   puts ("");
4081                 }
4082             }
4083           break;
4084
4085         case DT_POSFLAG_1:
4086           if (do_dynamic)
4087             {
4088               printf (_("Flags:"));
4089               if (entry->d_un.d_val == 0)
4090                 printf (_(" None\n"));
4091               else
4092                 {
4093                   unsigned long int val = entry->d_un.d_val;
4094                   if (val & DF_P1_LAZYLOAD)
4095                     {
4096                       printf (" LAZYLOAD");
4097                       val ^= DF_P1_LAZYLOAD;
4098                     }
4099                   if (val & DF_P1_GROUPPERM)
4100                     {
4101                       printf (" GROUPPERM");
4102                       val ^= DF_P1_GROUPPERM;
4103                     }
4104                   if (val != 0)
4105                     printf (" %lx", val);
4106                   puts ("");
4107                 }
4108             }
4109           break;
4110
4111         case DT_FLAGS_1:
4112           if (do_dynamic)
4113             {
4114               printf (_("Flags:"));
4115               if (entry->d_un.d_val == 0)
4116                 printf (_(" None\n"));
4117               else
4118                 {
4119                   unsigned long int val = entry->d_un.d_val;
4120                   if (val & DF_1_NOW)
4121                     {
4122                       printf (" NOW");
4123                       val ^= DF_1_NOW;
4124                     }
4125                   if (val & DF_1_GLOBAL)
4126                     {
4127                       printf (" GLOBAL");
4128                       val ^= DF_1_GLOBAL;
4129                     }
4130                   if (val & DF_1_GROUP)
4131                     {
4132                       printf (" GROUP");
4133                       val ^= DF_1_GROUP;
4134                     }
4135                   if (val & DF_1_NODELETE)
4136                     {
4137                       printf (" NODELETE");
4138                       val ^= DF_1_NODELETE;
4139                     }
4140                   if (val & DF_1_LOADFLTR)
4141                     {
4142                       printf (" LOADFLTR");
4143                       val ^= DF_1_LOADFLTR;
4144                     }
4145                   if (val & DF_1_INITFIRST)
4146                     {
4147                       printf (" INITFIRST");
4148                       val ^= DF_1_INITFIRST;
4149                     }
4150                   if (val & DF_1_NOOPEN)
4151                     {
4152                       printf (" NOOPEN");
4153                       val ^= DF_1_NOOPEN;
4154                     }
4155                   if (val & DF_1_ORIGIN)
4156                     {
4157                       printf (" ORIGIN");
4158                       val ^= DF_1_ORIGIN;
4159                     }
4160                   if (val & DF_1_DIRECT)
4161                     {
4162                       printf (" DIRECT");
4163                       val ^= DF_1_DIRECT;
4164                     }
4165                   if (val & DF_1_TRANS)
4166                     {
4167                       printf (" TRANS");
4168                       val ^= DF_1_TRANS;
4169                     }
4170                   if (val & DF_1_INTERPOSE)
4171                     {
4172                       printf (" INTERPOSE");
4173                       val ^= DF_1_INTERPOSE;
4174                     }
4175                   if (val & DF_1_NODEFLIB)
4176                     {
4177                       printf (" NODEFLIB");
4178                       val ^= DF_1_NODEFLIB;
4179                     }
4180                   if (val & DF_1_NODUMP)
4181                     {
4182                       printf (" NODUMP");
4183                       val ^= DF_1_NODUMP;
4184                     }
4185                   if (val & DF_1_CONLFAT)
4186                     {
4187                       printf (" CONLFAT");
4188                       val ^= DF_1_CONLFAT;
4189                     }
4190                   if (val != 0)
4191                     printf (" %lx", val);
4192                   puts ("");
4193                 }
4194             }
4195           break;
4196
4197         case DT_PLTREL:
4198           if (do_dynamic)
4199             puts (get_dynamic_type (entry->d_un.d_val));
4200           break;
4201
4202         case DT_NULL    :
4203         case DT_NEEDED  :
4204         case DT_PLTGOT  :
4205         case DT_HASH    :
4206         case DT_STRTAB  :
4207         case DT_SYMTAB  :
4208         case DT_RELA    :
4209         case DT_INIT    :
4210         case DT_FINI    :
4211         case DT_SONAME  :
4212         case DT_RPATH   :
4213         case DT_SYMBOLIC:
4214         case DT_REL     :
4215         case DT_DEBUG   :
4216         case DT_TEXTREL :
4217         case DT_JMPREL  :
4218         case DT_RUNPATH :
4219           dynamic_info[entry->d_tag] = entry->d_un.d_val;
4220
4221           if (do_dynamic)
4222             {
4223               char * name;
4224
4225               if (dynamic_strings == NULL)
4226                 name = NULL;
4227               else
4228                 name = dynamic_strings + entry->d_un.d_val;
4229
4230               if (name)
4231                 {
4232                   switch (entry->d_tag)
4233                     {
4234                     case DT_NEEDED:
4235                       printf (_("Shared library: [%s]"), name);
4236
4237                       if (strcmp (name, program_interpreter) == 0)
4238                         printf (_(" program interpreter"));
4239                       break;
4240
4241                     case DT_SONAME:
4242                       printf (_("Library soname: [%s]"), name);
4243                       break;
4244
4245                     case DT_RPATH:
4246                       printf (_("Library rpath: [%s]"), name);
4247                       break;
4248
4249                     case DT_RUNPATH:
4250                       printf (_("Library runpath: [%s]"), name);
4251                       break;
4252
4253                     default:
4254                       print_vma (entry->d_un.d_val, PREFIX_HEX);
4255                       break;
4256                     }
4257                 }
4258               else
4259                 print_vma (entry->d_un.d_val, PREFIX_HEX);
4260
4261               putchar ('\n');
4262             }
4263           break;
4264
4265         case DT_PLTRELSZ:
4266         case DT_RELASZ  :
4267         case DT_STRSZ   :
4268         case DT_RELSZ   :
4269         case DT_RELAENT :
4270         case DT_SYMENT  :
4271         case DT_RELENT  :
4272         case DT_PLTPADSZ:
4273         case DT_MOVEENT :
4274         case DT_MOVESZ  :
4275         case DT_INIT_ARRAYSZ:
4276         case DT_FINI_ARRAYSZ:
4277           if (do_dynamic)
4278             {
4279               print_vma (entry->d_un.d_val, UNSIGNED);
4280               printf (" (bytes)\n");
4281             }
4282           break;
4283
4284         case DT_VERDEFNUM:
4285         case DT_VERNEEDNUM:
4286         case DT_RELACOUNT:
4287         case DT_RELCOUNT:
4288           if (do_dynamic)
4289             {
4290               print_vma (entry->d_un.d_val, UNSIGNED);
4291               putchar ('\n');
4292             }
4293           break;
4294
4295         case DT_SYMINSZ:
4296         case DT_SYMINENT:
4297         case DT_SYMINFO:
4298         case DT_USED:
4299         case DT_INIT_ARRAY:
4300         case DT_FINI_ARRAY:
4301           if (do_dynamic)
4302             {
4303               if (dynamic_strings != NULL && entry->d_tag == DT_USED)
4304                 {
4305                   char * name;
4306
4307                   name = dynamic_strings + entry->d_un.d_val;
4308
4309                   if (* name)
4310                     {
4311                       printf (_("Not needed object: [%s]\n"), name);
4312                       break;
4313                     }
4314                 }
4315
4316               print_vma (entry->d_un.d_val, PREFIX_HEX);
4317               putchar ('\n');
4318             }
4319           break;
4320
4321         case DT_BIND_NOW:
4322           /* The value of this entry is ignored.  */
4323           break;
4324
4325         default:
4326           if ((entry->d_tag >= DT_VERSYM) && (entry->d_tag <= DT_VERNEEDNUM))
4327             version_info [DT_VERSIONTAGIDX (entry->d_tag)] =
4328               entry->d_un.d_val;
4329
4330           if (do_dynamic)
4331             {
4332               switch (elf_header.e_machine)
4333                 {
4334                 case EM_MIPS:
4335                 case EM_MIPS_RS3_LE:
4336                   dynamic_segment_mips_val (entry);
4337                   break;
4338                 case EM_PARISC:
4339                   dynamic_segment_parisc_val (entry);
4340                   break;
4341                 default:
4342                   print_vma (entry->d_un.d_val, PREFIX_HEX);
4343                   putchar ('\n');
4344                 }
4345             }
4346           break;
4347         }
4348     }
4349
4350   return 1;
4351 }
4352
4353 static char *
4354 get_ver_flags (flags)
4355      unsigned int flags;
4356 {
4357   static char buff [32];
4358
4359   buff[0] = 0;
4360
4361   if (flags == 0)
4362     return _("none");
4363
4364   if (flags & VER_FLG_BASE)
4365     strcat (buff, "BASE ");
4366
4367   if (flags & VER_FLG_WEAK)
4368     {
4369       if (flags & VER_FLG_BASE)
4370         strcat (buff, "| ");
4371
4372       strcat (buff, "WEAK ");
4373     }
4374
4375   if (flags & ~(VER_FLG_BASE | VER_FLG_WEAK))
4376     strcat (buff, "| <unknown>");
4377
4378   return buff;
4379 }
4380
4381 /* Display the contents of the version sections.  */
4382 static int
4383 process_version_sections (file)
4384      FILE * file;
4385 {
4386   Elf32_Internal_Shdr * section;
4387   unsigned   i;
4388   int        found = 0;
4389
4390   if (! do_version)
4391     return 1;
4392
4393   for (i = 0, section = section_headers;
4394        i < elf_header.e_shnum;
4395        i++, section ++)
4396     {
4397       switch (section->sh_type)
4398         {
4399         case SHT_GNU_verdef:
4400           {
4401             Elf_External_Verdef * edefs;
4402             unsigned int          idx;
4403             unsigned int          cnt;
4404
4405             found = 1;
4406
4407             printf
4408               (_("\nVersion definition section '%s' contains %ld entries:\n"),
4409                SECTION_NAME (section), section->sh_info);
4410
4411             printf (_("  Addr: 0x"));
4412             printf_vma (section->sh_addr);
4413             printf (_("  Offset: %#08lx  Link: %lx (%s)\n"),
4414                     (unsigned long) section->sh_offset, section->sh_link,
4415                     SECTION_NAME (section_headers + section->sh_link));
4416
4417             edefs = ((Elf_External_Verdef *)
4418                      get_data (NULL, file, section->sh_offset,
4419                                section->sh_size,
4420                                _("version definition section")));
4421             if (!edefs)
4422               break;
4423
4424             for (idx = cnt = 0; cnt < section->sh_info; ++ cnt)
4425               {
4426                 char *                 vstart;
4427                 Elf_External_Verdef *  edef;
4428                 Elf_Internal_Verdef    ent;
4429                 Elf_External_Verdaux * eaux;
4430                 Elf_Internal_Verdaux   aux;
4431                 int                    j;
4432                 int                    isum;
4433
4434                 vstart = ((char *) edefs) + idx;
4435
4436                 edef = (Elf_External_Verdef *) vstart;
4437
4438                 ent.vd_version = BYTE_GET (edef->vd_version);
4439                 ent.vd_flags   = BYTE_GET (edef->vd_flags);
4440                 ent.vd_ndx     = BYTE_GET (edef->vd_ndx);
4441                 ent.vd_cnt     = BYTE_GET (edef->vd_cnt);
4442                 ent.vd_hash    = BYTE_GET (edef->vd_hash);
4443                 ent.vd_aux     = BYTE_GET (edef->vd_aux);
4444                 ent.vd_next    = BYTE_GET (edef->vd_next);
4445
4446                 printf (_("  %#06x: Rev: %d  Flags: %s"),
4447                         idx, ent.vd_version, get_ver_flags (ent.vd_flags));
4448
4449                 printf (_("  Index: %d  Cnt: %d  "),
4450                         ent.vd_ndx, ent.vd_cnt);
4451
4452                 vstart += ent.vd_aux;
4453
4454                 eaux = (Elf_External_Verdaux *) vstart;
4455
4456                 aux.vda_name = BYTE_GET (eaux->vda_name);
4457                 aux.vda_next = BYTE_GET (eaux->vda_next);
4458
4459                 if (dynamic_strings)
4460                   printf (_("Name: %s\n"), dynamic_strings + aux.vda_name);
4461                 else
4462                   printf (_("Name index: %ld\n"), aux.vda_name);
4463
4464                 isum = idx + ent.vd_aux;
4465
4466                 for (j = 1; j < ent.vd_cnt; j ++)
4467                   {
4468                     isum   += aux.vda_next;
4469                     vstart += aux.vda_next;
4470
4471                     eaux = (Elf_External_Verdaux *) vstart;
4472
4473                     aux.vda_name = BYTE_GET (eaux->vda_name);
4474                     aux.vda_next = BYTE_GET (eaux->vda_next);
4475
4476                     if (dynamic_strings)
4477                       printf (_("  %#06x: Parent %d: %s\n"),
4478                               isum, j, dynamic_strings + aux.vda_name);
4479                     else
4480                       printf (_("  %#06x: Parent %d, name index: %ld\n"),
4481                               isum, j, aux.vda_name);
4482                   }
4483
4484                 idx += ent.vd_next;
4485               }
4486
4487             free (edefs);
4488           }
4489           break;
4490
4491         case SHT_GNU_verneed:
4492           {
4493             Elf_External_Verneed *  eneed;
4494             unsigned int            idx;
4495             unsigned int            cnt;
4496
4497             found = 1;
4498
4499             printf (_("\nVersion needs section '%s' contains %ld entries:\n"),
4500                     SECTION_NAME (section), section->sh_info);
4501
4502             printf (_(" Addr: 0x"));
4503             printf_vma (section->sh_addr);
4504             printf (_("  Offset: %#08lx  Link to section: %ld (%s)\n"),
4505                     (unsigned long) section->sh_offset, section->sh_link,
4506                     SECTION_NAME (section_headers + section->sh_link));
4507
4508             eneed = ((Elf_External_Verneed *)
4509                      get_data (NULL, file, section->sh_offset,
4510                                section->sh_size, _("version need section")));
4511             if (!eneed)
4512               break;
4513
4514             for (idx = cnt = 0; cnt < section->sh_info; ++cnt)
4515               {
4516                 Elf_External_Verneed * entry;
4517                 Elf_Internal_Verneed     ent;
4518                 int                      j;
4519                 int                      isum;
4520                 char *                   vstart;
4521
4522                 vstart = ((char *) eneed) + idx;
4523
4524                 entry = (Elf_External_Verneed *) vstart;
4525
4526                 ent.vn_version = BYTE_GET (entry->vn_version);
4527                 ent.vn_cnt     = BYTE_GET (entry->vn_cnt);
4528                 ent.vn_file    = BYTE_GET (entry->vn_file);
4529                 ent.vn_aux     = BYTE_GET (entry->vn_aux);
4530                 ent.vn_next    = BYTE_GET (entry->vn_next);
4531
4532                 printf (_("  %#06x: Version: %d"), idx, ent.vn_version);
4533
4534                 if (dynamic_strings)
4535                   printf (_("  File: %s"), dynamic_strings + ent.vn_file);
4536                 else
4537                   printf (_("  File: %lx"), ent.vn_file);
4538
4539                 printf (_("  Cnt: %d\n"), ent.vn_cnt);
4540
4541                 vstart += ent.vn_aux;
4542
4543                 for (j = 0, isum = idx + ent.vn_aux; j < ent.vn_cnt; ++j)
4544                   {
4545                     Elf_External_Vernaux * eaux;
4546                     Elf_Internal_Vernaux   aux;
4547
4548                     eaux = (Elf_External_Vernaux *) vstart;
4549
4550                     aux.vna_hash  = BYTE_GET (eaux->vna_hash);
4551                     aux.vna_flags = BYTE_GET (eaux->vna_flags);
4552                     aux.vna_other = BYTE_GET (eaux->vna_other);
4553                     aux.vna_name  = BYTE_GET (eaux->vna_name);
4554                     aux.vna_next  = BYTE_GET (eaux->vna_next);
4555
4556                     if (dynamic_strings)
4557                       printf (_("  %#06x: Name: %s"),
4558                               isum, dynamic_strings + aux.vna_name);
4559                     else
4560                       printf (_("  %#06x: Name index: %lx"),
4561                               isum, aux.vna_name);
4562
4563                     printf (_("  Flags: %s  Version: %d\n"),
4564                             get_ver_flags (aux.vna_flags), aux.vna_other);
4565
4566                     isum   += aux.vna_next;
4567                     vstart += aux.vna_next;
4568                   }
4569
4570                 idx += ent.vn_next;
4571               }
4572
4573             free (eneed);
4574           }
4575           break;
4576
4577         case SHT_GNU_versym:
4578           {
4579             Elf32_Internal_Shdr *       link_section;
4580             int         total;
4581             int         cnt;
4582             unsigned char *             edata;
4583             unsigned short *            data;
4584             char *              strtab;
4585             Elf_Internal_Sym *          symbols;
4586             Elf32_Internal_Shdr *       string_sec;
4587
4588             link_section = section_headers + section->sh_link;
4589             total = section->sh_size / section->sh_entsize;
4590
4591             found = 1;
4592
4593             symbols = GET_ELF_SYMBOLS (file, link_section->sh_offset,
4594                                        link_section->sh_size / link_section->sh_entsize);
4595
4596             string_sec = section_headers + link_section->sh_link;
4597
4598             strtab = (char *) get_data (NULL, file, string_sec->sh_offset,
4599                                         string_sec->sh_size,
4600                                         _("version string table"));
4601             if (!strtab)
4602               break;
4603
4604             printf (_("\nVersion symbols section '%s' contains %d entries:\n"),
4605                     SECTION_NAME (section), total);
4606
4607             printf (_(" Addr: "));
4608             printf_vma (section->sh_addr);
4609             printf (_("  Offset: %#08lx  Link: %lx (%s)\n"),
4610                     (unsigned long) section->sh_offset, section->sh_link,
4611                     SECTION_NAME (link_section));
4612
4613             edata =
4614               ((unsigned char *)
4615                get_data (NULL, file,
4616                          version_info[DT_VERSIONTAGIDX (DT_VERSYM)] - loadaddr,
4617                          total * sizeof (short), _("version symbol data")));
4618             if (!edata)
4619               {
4620                 free (strtab);
4621                 break;
4622               }
4623
4624             data = (unsigned short *) malloc (total * sizeof (short));
4625
4626             for (cnt = total; cnt --;)
4627               data [cnt] = byte_get (edata + cnt * sizeof (short),
4628                                      sizeof (short));
4629
4630             free (edata);
4631
4632             for (cnt = 0; cnt < total; cnt += 4)
4633               {
4634                 int j, nn;
4635                 int check_def, check_need;
4636                 char * name;
4637
4638                 printf ("  %03x:", cnt);
4639
4640                 for (j = 0; (j < 4) && (cnt + j) < total; ++j)
4641                   switch (data [cnt + j])
4642                     {
4643                     case 0:
4644                       fputs (_("   0 (*local*)    "), stdout);
4645                       break;
4646
4647                     case 1:
4648                       fputs (_("   1 (*global*)   "), stdout);
4649                       break;
4650
4651                     default:
4652                       nn = printf ("%4x%c", data [cnt + j] & 0x7fff,
4653                                    data [cnt + j] & 0x8000 ? 'h' : ' ');
4654
4655                       check_def = 1;
4656                       check_need = 1;
4657                       if (symbols [cnt + j].st_shndx >= SHN_LORESERVE
4658                           || section_headers[symbols [cnt + j].st_shndx].sh_type
4659                           != SHT_NOBITS)
4660                         {
4661                           if (symbols [cnt + j].st_shndx == SHN_UNDEF)
4662                             check_def = 0;
4663                           else
4664                             check_need = 0;
4665                         }
4666
4667                       if (check_need
4668                           && version_info [DT_VERSIONTAGIDX (DT_VERNEED)])
4669                         {
4670                           Elf_Internal_Verneed     ivn;
4671                           unsigned long            offset;
4672
4673                           offset = version_info [DT_VERSIONTAGIDX (DT_VERNEED)]
4674                             - loadaddr;
4675
4676                           do
4677                             {
4678                               Elf_Internal_Vernaux   ivna;
4679                               Elf_External_Verneed   evn;
4680                               Elf_External_Vernaux   evna;
4681                               unsigned long          a_off;
4682
4683                               get_data (&evn, file, offset, sizeof (evn),
4684                                         _("version need"));
4685
4686                               ivn.vn_aux  = BYTE_GET (evn.vn_aux);
4687                               ivn.vn_next = BYTE_GET (evn.vn_next);
4688
4689                               a_off = offset + ivn.vn_aux;
4690
4691                               do
4692                                 {
4693                                   get_data (&evna, file, a_off, sizeof (evna),
4694                                             _("version need aux (2)"));
4695
4696                                   ivna.vna_next  = BYTE_GET (evna.vna_next);
4697                                   ivna.vna_other = BYTE_GET (evna.vna_other);
4698
4699                                   a_off += ivna.vna_next;
4700                                 }
4701                               while (ivna.vna_other != data [cnt + j]
4702                                      && ivna.vna_next != 0);
4703
4704                               if (ivna.vna_other == data [cnt + j])
4705                                 {
4706                                   ivna.vna_name = BYTE_GET (evna.vna_name);
4707
4708                                   name = strtab + ivna.vna_name;
4709                                   nn += printf ("(%s%-*s",
4710                                                 name,
4711                                                 12 - (int) strlen (name),
4712                                                 ")");
4713                                   check_def = 0;
4714                                   break;
4715                                 }
4716
4717                               offset += ivn.vn_next;
4718                             }
4719                           while (ivn.vn_next);
4720                         }
4721
4722                       if (check_def && data [cnt + j] != 0x8001
4723                           && version_info [DT_VERSIONTAGIDX (DT_VERDEF)])
4724                         {
4725                           Elf_Internal_Verdef  ivd;
4726                           Elf_External_Verdef  evd;
4727                           unsigned long        offset;
4728
4729                           offset = version_info
4730                             [DT_VERSIONTAGIDX (DT_VERDEF)] - loadaddr;
4731
4732                           do
4733                             {
4734                               get_data (&evd, file, offset, sizeof (evd),
4735                                         _("version def"));
4736
4737                               ivd.vd_next = BYTE_GET (evd.vd_next);
4738                               ivd.vd_ndx  = BYTE_GET (evd.vd_ndx);
4739
4740                               offset += ivd.vd_next;
4741                             }
4742                           while (ivd.vd_ndx != (data [cnt + j] & 0x7fff)
4743                                  && ivd.vd_next != 0);
4744
4745                           if (ivd.vd_ndx == (data [cnt + j] & 0x7fff))
4746                             {
4747                               Elf_External_Verdaux  evda;
4748                               Elf_Internal_Verdaux  ivda;
4749
4750                               ivd.vd_aux = BYTE_GET (evd.vd_aux);
4751
4752                               get_data (&evda, file,
4753                                         offset - ivd.vd_next + ivd.vd_aux,
4754                                         sizeof (evda), _("version def aux"));
4755
4756                               ivda.vda_name = BYTE_GET (evda.vda_name);
4757
4758                               name = strtab + ivda.vda_name;
4759                               nn += printf ("(%s%-*s",
4760                                             name,
4761                                             12 - (int) strlen (name),
4762                                             ")");
4763                             }
4764                         }
4765
4766                       if (nn < 18)
4767                         printf ("%*c", 18 - nn, ' ');
4768                     }
4769
4770                 putchar ('\n');
4771               }
4772
4773             free (data);
4774             free (strtab);
4775             free (symbols);
4776           }
4777           break;
4778
4779         default:
4780           break;
4781         }
4782     }
4783
4784   if (! found)
4785     printf (_("\nNo version information found in this file.\n"));
4786
4787   return 1;
4788 }
4789
4790 static const char *
4791 get_symbol_binding (binding)
4792      unsigned int binding;
4793 {
4794   static char buff [32];
4795
4796   switch (binding)
4797     {
4798     case STB_LOCAL:  return "LOCAL";
4799     case STB_GLOBAL: return "GLOBAL";
4800     case STB_WEAK:   return "WEAK";
4801     default:
4802       if (binding >= STB_LOPROC && binding <= STB_HIPROC)
4803         sprintf (buff, _("<processor specific>: %d"), binding);
4804       else if (binding >= STB_LOOS && binding <= STB_HIOS)
4805         sprintf (buff, _("<OS specific>: %d"), binding);
4806       else
4807         sprintf (buff, _("<unknown>: %d"), binding);
4808       return buff;
4809     }
4810 }
4811
4812 static const char *
4813 get_symbol_type (type)
4814      unsigned int type;
4815 {
4816   static char buff [32];
4817
4818   switch (type)
4819     {
4820     case STT_NOTYPE:   return "NOTYPE";
4821     case STT_OBJECT:   return "OBJECT";
4822     case STT_FUNC:     return "FUNC";
4823     case STT_SECTION:  return "SECTION";
4824     case STT_FILE:     return "FILE";
4825     case STT_COMMON:   return "COMMON";
4826     default:
4827       if (type >= STT_LOPROC && type <= STT_HIPROC)
4828         {
4829           if (elf_header.e_machine == EM_ARM && type == STT_ARM_TFUNC)
4830             return "THUMB_FUNC";
4831
4832           if (elf_header.e_machine == EM_SPARCV9 && type == STT_REGISTER)
4833             return "REGISTER";
4834
4835           if (elf_header.e_machine == EM_PARISC && type == STT_PARISC_MILLI)
4836             return "PARISC_MILLI";
4837
4838           sprintf (buff, _("<processor specific>: %d"), type);
4839         }
4840       else if (type >= STT_LOOS && type <= STT_HIOS)
4841         {
4842           if (elf_header.e_machine == EM_PARISC)
4843             {
4844               if (type == STT_HP_OPAQUE)
4845                 return "HP_OPAQUE";
4846               if (type == STT_HP_STUB)
4847                 return "HP_STUB";
4848             }
4849
4850           sprintf (buff, _("<OS specific>: %d"), type);
4851         }
4852       else
4853         sprintf (buff, _("<unknown>: %d"), type);
4854       return buff;
4855     }
4856 }
4857
4858 static const char *
4859 get_symbol_visibility (visibility)
4860      unsigned int visibility;
4861 {
4862   switch (visibility)
4863     {
4864     case STV_DEFAULT:   return "DEFAULT";
4865     case STV_INTERNAL:  return "INTERNAL";
4866     case STV_HIDDEN:    return "HIDDEN";
4867     case STV_PROTECTED: return "PROTECTED";
4868     default: abort ();
4869     }
4870 }
4871
4872 static const char *
4873 get_symbol_index_type (type)
4874      unsigned int type;
4875 {
4876   switch (type)
4877     {
4878     case SHN_UNDEF:  return "UND";
4879     case SHN_ABS:    return "ABS";
4880     case SHN_COMMON: return "COM";
4881     default:
4882       if (type >= SHN_LOPROC && type <= SHN_HIPROC)
4883         return "PRC";
4884       else if (type >= SHN_LORESERVE && type <= SHN_HIRESERVE)
4885         return "RSV";
4886       else if (type >= SHN_LOOS && type <= SHN_HIOS)
4887         return "OS ";
4888       else
4889         {
4890           static char buff [32];
4891
4892           sprintf (buff, "%3d", type);
4893           return buff;
4894         }
4895     }
4896 }
4897
4898 static int *
4899 get_dynamic_data (file, number)
4900      FILE *       file;
4901      unsigned int number;
4902 {
4903   unsigned char * e_data;
4904   int *  i_data;
4905
4906   e_data = (unsigned char *) malloc (number * 4);
4907
4908   if (e_data == NULL)
4909     {
4910       error (_("Out of memory\n"));
4911       return NULL;
4912     }
4913
4914   if (fread (e_data, 4, number, file) != number)
4915     {
4916       error (_("Unable to read in dynamic data\n"));
4917       return NULL;
4918     }
4919
4920   i_data = (int *) malloc (number * sizeof (* i_data));
4921
4922   if (i_data == NULL)
4923     {
4924       error (_("Out of memory\n"));
4925       free (e_data);
4926       return NULL;
4927     }
4928
4929   while (number--)
4930     i_data [number] = byte_get (e_data + number * 4, 4);
4931
4932   free (e_data);
4933
4934   return i_data;
4935 }
4936
4937 /* Dump the symbol table */
4938 static int
4939 process_symbol_table (file)
4940      FILE * file;
4941 {
4942   Elf32_Internal_Shdr *   section;
4943   unsigned char   nb [4];
4944   unsigned char   nc [4];
4945   int    nbuckets = 0;
4946   int    nchains = 0;
4947   int *  buckets = NULL;
4948   int *  chains = NULL;
4949
4950   if (! do_syms && !do_histogram)
4951     return 1;
4952
4953   if (dynamic_info[DT_HASH] && ((do_using_dynamic && dynamic_strings != NULL)
4954                                 || do_histogram))
4955     {
4956       if (fseek (file, dynamic_info[DT_HASH] - loadaddr, SEEK_SET))
4957         {
4958           error (_("Unable to seek to start of dynamic information"));
4959           return 0;
4960         }
4961
4962       if (fread (nb, sizeof (nb), 1, file) != 1)
4963         {
4964           error (_("Failed to read in number of buckets\n"));
4965           return 0;
4966         }
4967
4968       if (fread (nc, sizeof (nc), 1, file) != 1)
4969         {
4970           error (_("Failed to read in number of chains\n"));
4971           return 0;
4972         }
4973
4974       nbuckets = byte_get (nb, 4);
4975       nchains  = byte_get (nc, 4);
4976
4977       buckets = get_dynamic_data (file, nbuckets);
4978       chains  = get_dynamic_data (file, nchains);
4979
4980       if (buckets == NULL || chains == NULL)
4981         return 0;
4982     }
4983
4984   if (do_syms
4985       && dynamic_info[DT_HASH] && do_using_dynamic && dynamic_strings != NULL)
4986     {
4987       int    hn;
4988       int    si;
4989
4990       printf (_("\nSymbol table for image:\n"));
4991       if (is_32bit_elf)
4992         printf (_("  Num Buc:    Value  Size   Type   Bind Vis      Ndx Name\n"));
4993       else
4994         printf (_("  Num Buc:    Value          Size   Type   Bind Vis      Ndx Name\n"));
4995
4996       for (hn = 0; hn < nbuckets; hn++)
4997         {
4998           if (! buckets [hn])
4999             continue;
5000
5001           for (si = buckets [hn]; si < nchains && si > 0; si = chains [si])
5002             {
5003               Elf_Internal_Sym * psym;
5004
5005               psym = dynamic_symbols + si;
5006
5007               printf ("  %3d %3d: ", si, hn);
5008               print_vma (psym->st_value, LONG_HEX);
5009               putchar (' ' );
5010               print_vma (psym->st_size, DEC_5);
5011
5012               printf ("  %6s", get_symbol_type (ELF_ST_TYPE (psym->st_info)));
5013               printf (" %6s",  get_symbol_binding (ELF_ST_BIND (psym->st_info)));
5014               printf (" %3s",  get_symbol_visibility (ELF_ST_VISIBILITY (psym->st_other)));
5015               printf (" %3.3s", get_symbol_index_type (psym->st_shndx));
5016               printf (" %s\n", dynamic_strings + psym->st_name);
5017             }
5018         }
5019     }
5020   else if (do_syms && !do_using_dynamic)
5021     {
5022       unsigned int     i;
5023
5024       for (i = 0, section = section_headers;
5025            i < elf_header.e_shnum;
5026            i++, section++)
5027         {
5028           unsigned int          si;
5029           char *                strtab;
5030           Elf_Internal_Sym *    symtab;
5031           Elf_Internal_Sym *    psym;
5032
5033
5034           if (   section->sh_type != SHT_SYMTAB
5035               && section->sh_type != SHT_DYNSYM)
5036             continue;
5037
5038           printf (_("\nSymbol table '%s' contains %lu entries:\n"),
5039                   SECTION_NAME (section),
5040                   (unsigned long) (section->sh_size / section->sh_entsize));
5041           if (is_32bit_elf)
5042             printf (_("   Num:    Value  Size Type    Bind   Vis      Ndx Name\n"));
5043           else
5044             printf (_("   Num:    Value          Size Type    Bind   Vis      Ndx Name\n"));
5045
5046           symtab = GET_ELF_SYMBOLS (file, section->sh_offset,
5047                                     section->sh_size / section->sh_entsize);
5048           if (symtab == NULL)
5049             continue;
5050
5051           if (section->sh_link == elf_header.e_shstrndx)
5052             strtab = string_table;
5053           else
5054             {
5055               Elf32_Internal_Shdr * string_sec;
5056
5057               string_sec = section_headers + section->sh_link;
5058
5059               strtab = (char *) get_data (NULL, file, string_sec->sh_offset,
5060                                           string_sec->sh_size,
5061                                           _("string table"));
5062             }
5063
5064           for (si = 0, psym = symtab;
5065                si < section->sh_size / section->sh_entsize;
5066                si ++, psym ++)
5067             {
5068               printf ("%6d: ", si);
5069               print_vma (psym->st_value, LONG_HEX);
5070               putchar (' ');
5071               print_vma (psym->st_size, DEC_5);
5072               printf (" %-7s", get_symbol_type (ELF_ST_TYPE (psym->st_info)));
5073               printf (" %-6s", get_symbol_binding (ELF_ST_BIND (psym->st_info)));
5074               printf (" %-3s", get_symbol_visibility (ELF_ST_VISIBILITY (psym->st_other)));
5075               printf (" %4s", get_symbol_index_type (psym->st_shndx));
5076               printf (" %s", strtab + psym->st_name);
5077
5078               if (section->sh_type == SHT_DYNSYM &&
5079                   version_info [DT_VERSIONTAGIDX (DT_VERSYM)] != 0)
5080                 {
5081                   unsigned char   data[2];
5082                   unsigned short  vers_data;
5083                   unsigned long   offset;
5084                   int             is_nobits;
5085                   int             check_def;
5086
5087                   offset = version_info [DT_VERSIONTAGIDX (DT_VERSYM)]
5088                     - loadaddr;
5089
5090                   get_data (&data, file, offset + si * sizeof (vers_data),
5091                             sizeof (data), _("version data"));
5092
5093                   vers_data = byte_get (data, 2);
5094
5095                   is_nobits = psym->st_shndx < SHN_LORESERVE ?
5096                     (section_headers [psym->st_shndx].sh_type == SHT_NOBITS)
5097                     : 0;
5098
5099                   check_def = (psym->st_shndx != SHN_UNDEF);
5100
5101                   if ((vers_data & 0x8000) || vers_data > 1)
5102                     {
5103                       if (version_info [DT_VERSIONTAGIDX (DT_VERNEED)]
5104                           && (is_nobits || ! check_def))
5105                         {
5106                           Elf_External_Verneed  evn;
5107                           Elf_Internal_Verneed  ivn;
5108                           Elf_Internal_Vernaux  ivna;
5109
5110                           /* We must test both.  */
5111                           offset = version_info
5112                             [DT_VERSIONTAGIDX (DT_VERNEED)] - loadaddr;
5113
5114                           do
5115                             {
5116                               unsigned long  vna_off;
5117
5118                               get_data (&evn, file, offset, sizeof (evn),
5119                                         _("version need"));
5120
5121                               ivn.vn_aux  = BYTE_GET (evn.vn_aux);
5122                               ivn.vn_next = BYTE_GET (evn.vn_next);
5123
5124                               vna_off = offset + ivn.vn_aux;
5125
5126                               do
5127                                 {
5128                                   Elf_External_Vernaux  evna;
5129
5130                                   get_data (&evna, file, vna_off,
5131                                             sizeof (evna),
5132                                             _("version need aux (3)"));
5133
5134                                   ivna.vna_other = BYTE_GET (evna.vna_other);
5135                                   ivna.vna_next  = BYTE_GET (evna.vna_next);
5136                                   ivna.vna_name  = BYTE_GET (evna.vna_name);
5137
5138                                   vna_off += ivna.vna_next;
5139                                 }
5140                               while (ivna.vna_other != vers_data
5141                                      && ivna.vna_next != 0);
5142
5143                               if (ivna.vna_other == vers_data)
5144                                 break;
5145
5146                               offset += ivn.vn_next;
5147                             }
5148                           while (ivn.vn_next != 0);
5149
5150                           if (ivna.vna_other == vers_data)
5151                             {
5152                               printf ("@%s (%d)",
5153                                       strtab + ivna.vna_name, ivna.vna_other);
5154                               check_def = 0;
5155                             }
5156                           else if (! is_nobits)
5157                             error (_("bad dynamic symbol"));
5158                           else
5159                             check_def = 1;
5160                         }
5161
5162                       if (check_def)
5163                         {
5164                           if (vers_data != 0x8001
5165                               && version_info [DT_VERSIONTAGIDX (DT_VERDEF)])
5166                             {
5167                               Elf_Internal_Verdef     ivd;
5168                               Elf_Internal_Verdaux    ivda;
5169                               Elf_External_Verdaux  evda;
5170                               unsigned long           offset;
5171
5172                               offset =
5173                                 version_info [DT_VERSIONTAGIDX (DT_VERDEF)]
5174                                 - loadaddr;
5175
5176                               do
5177                                 {
5178                                   Elf_External_Verdef   evd;
5179
5180                                   get_data (&evd, file, offset, sizeof (evd),
5181                                             _("version def"));
5182
5183                                   ivd.vd_ndx  = BYTE_GET (evd.vd_ndx);
5184                                   ivd.vd_aux  = BYTE_GET (evd.vd_aux);
5185                                   ivd.vd_next = BYTE_GET (evd.vd_next);
5186
5187                                   offset += ivd.vd_next;
5188                                 }
5189                               while (ivd.vd_ndx != (vers_data & 0x7fff)
5190                                      && ivd.vd_next != 0);
5191
5192                               offset -= ivd.vd_next;
5193                               offset += ivd.vd_aux;
5194
5195                               get_data (&evda, file, offset, sizeof (evda),
5196                                         _("version def aux"));
5197
5198                               ivda.vda_name = BYTE_GET (evda.vda_name);
5199
5200                               if (psym->st_name != ivda.vda_name)
5201                                 printf ((vers_data & 0x8000)
5202                                         ? "@%s" : "@@%s",
5203                                         strtab + ivda.vda_name);
5204                             }
5205                         }
5206                     }
5207                 }
5208
5209               putchar ('\n');
5210             }
5211
5212           free (symtab);
5213           if (strtab != string_table)
5214             free (strtab);
5215         }
5216     }
5217   else if (do_syms)
5218     printf
5219       (_("\nDynamic symbol information is not available for displaying symbols.\n"));
5220
5221   if (do_histogram && buckets != NULL)
5222     {
5223       int * lengths;
5224       int * counts;
5225       int   hn;
5226       int   si;
5227       int   maxlength = 0;
5228       int   nzero_counts = 0;
5229       int   nsyms = 0;
5230
5231       printf (_("\nHistogram for bucket list length (total of %d buckets):\n"),
5232               nbuckets);
5233       printf (_(" Length  Number     %% of total  Coverage\n"));
5234
5235       lengths = (int *) calloc (nbuckets, sizeof (int));
5236       if (lengths == NULL)
5237         {
5238           error (_("Out of memory"));
5239           return 0;
5240         }
5241       for (hn = 0; hn < nbuckets; ++hn)
5242         {
5243           if (! buckets [hn])
5244             continue;
5245
5246           for (si = buckets[hn]; si > 0 && si < nchains; si = chains[si])
5247             {
5248               ++ nsyms;
5249               if (maxlength < ++lengths[hn])
5250                 ++ maxlength;
5251             }
5252         }
5253
5254       counts = (int *) calloc (maxlength + 1, sizeof (int));
5255       if (counts == NULL)
5256         {
5257           error (_("Out of memory"));
5258           return 0;
5259         }
5260
5261       for (hn = 0; hn < nbuckets; ++hn)
5262         ++ counts [lengths [hn]];
5263
5264       if (nbuckets > 0)
5265         {
5266           printf ("      0  %-10d (%5.1f%%)\n",
5267                   counts[0], (counts[0] * 100.0) / nbuckets);
5268           for (si = 1; si <= maxlength; ++si)
5269             {
5270               nzero_counts += counts[si] * si;
5271               printf ("%7d  %-10d (%5.1f%%)    %5.1f%%\n",
5272                       si, counts[si], (counts[si] * 100.0) / nbuckets,
5273                       (nzero_counts * 100.0) / nsyms);
5274             }
5275         }
5276
5277       free (counts);
5278       free (lengths);
5279     }
5280
5281   if (buckets != NULL)
5282     {
5283       free (buckets);
5284       free (chains);
5285     }
5286
5287   return 1;
5288 }
5289
5290 static int
5291 process_syminfo (file)
5292      FILE * file ATTRIBUTE_UNUSED;
5293 {
5294   unsigned int i;
5295
5296   if (dynamic_syminfo == NULL
5297       || !do_dynamic)
5298     /* No syminfo, this is ok.  */
5299     return 1;
5300
5301   /* There better should be a dynamic symbol section.  */
5302   if (dynamic_symbols == NULL || dynamic_strings == NULL)
5303     return 0;
5304
5305   if (dynamic_addr)
5306     printf (_("\nDynamic info segment at offset 0x%lx contains %d entries:\n"),
5307             dynamic_syminfo_offset, dynamic_syminfo_nent);
5308
5309   printf (_(" Num: Name                           BoundTo     Flags\n"));
5310   for (i = 0; i < dynamic_syminfo_nent; ++i)
5311     {
5312       unsigned short int flags = dynamic_syminfo[i].si_flags;
5313
5314       printf ("%4d: %-30s ", i,
5315               dynamic_strings + dynamic_symbols[i].st_name);
5316
5317       switch (dynamic_syminfo[i].si_boundto)
5318         {
5319         case SYMINFO_BT_SELF:
5320           fputs ("SELF       ", stdout);
5321           break;
5322         case SYMINFO_BT_PARENT:
5323           fputs ("PARENT     ", stdout);
5324           break;
5325         default:
5326           if (dynamic_syminfo[i].si_boundto > 0
5327               && dynamic_syminfo[i].si_boundto < dynamic_size)
5328             printf ("%-10s ",
5329                     dynamic_strings
5330                     + dynamic_segment[dynamic_syminfo[i].si_boundto].d_un.d_val);
5331           else
5332             printf ("%-10d ", dynamic_syminfo[i].si_boundto);
5333           break;
5334         }
5335
5336       if (flags & SYMINFO_FLG_DIRECT)
5337         printf (" DIRECT");
5338       if (flags & SYMINFO_FLG_PASSTHRU)
5339         printf (" PASSTHRU");
5340       if (flags & SYMINFO_FLG_COPY)
5341         printf (" COPY");
5342       if (flags & SYMINFO_FLG_LAZYLOAD)
5343         printf (" LAZYLOAD");
5344
5345       puts ("");
5346     }
5347
5348   return 1;
5349 }
5350
5351 #ifdef SUPPORT_DISASSEMBLY
5352 static void
5353 disassemble_section (section, file)
5354      Elf32_Internal_Shdr * section;
5355      FILE * file;
5356 {
5357   printf (_("\nAssembly dump of section %s\n"),
5358           SECTION_NAME (section));
5359
5360   /* XXX -- to be done --- XXX */
5361
5362   return 1;
5363 }
5364 #endif
5365
5366 static int
5367 dump_section (section, file)
5368      Elf32_Internal_Shdr * section;
5369      FILE * file;
5370 {
5371   bfd_size_type   bytes;
5372   bfd_vma         addr;
5373   unsigned char * data;
5374   unsigned char * start;
5375
5376   bytes = section->sh_size;
5377
5378   if (bytes == 0)
5379     {
5380       printf (_("\nSection '%s' has no data to dump.\n"),
5381               SECTION_NAME (section));
5382       return 0;
5383     }
5384   else
5385     printf (_("\nHex dump of section '%s':\n"), SECTION_NAME (section));
5386
5387   addr = section->sh_addr;
5388
5389   start = (unsigned char *) get_data (NULL, file, section->sh_offset, bytes,
5390                                       _("section data"));
5391   if (!start)
5392     return 0;
5393
5394   data = start;
5395
5396   while (bytes)
5397     {
5398       int j;
5399       int k;
5400       int lbytes;
5401
5402       lbytes = (bytes > 16 ? 16 : bytes);
5403
5404       printf ("  0x%8.8lx ", (unsigned long) addr);
5405
5406       switch (elf_header.e_ident [EI_DATA])
5407         {
5408         default:
5409         case ELFDATA2LSB:
5410           for (j = 15; j >= 0; j --)
5411             {
5412               if (j < lbytes)
5413                 printf ("%2.2x", data [j]);
5414               else
5415                 printf ("  ");
5416
5417               if (!(j & 0x3))
5418                 printf (" ");
5419             }
5420           break;
5421
5422         case ELFDATA2MSB:
5423           for (j = 0; j < 16; j++)
5424             {
5425               if (j < lbytes)
5426                 printf ("%2.2x", data [j]);
5427               else
5428                 printf ("  ");
5429
5430               if ((j & 3) == 3)
5431                 printf (" ");
5432             }
5433           break;
5434         }
5435
5436       for (j = 0; j < lbytes; j++)
5437         {
5438           k = data [j];
5439           if (k >= ' ' && k < 0x80)
5440             printf ("%c", k);
5441           else
5442             printf (".");
5443         }
5444
5445       putchar ('\n');
5446
5447       data  += lbytes;
5448       addr  += lbytes;
5449       bytes -= lbytes;
5450     }
5451
5452   free (start);
5453
5454   return 1;
5455 }
5456
5457
5458 static unsigned long int
5459 read_leb128 (data, length_return, sign)
5460      unsigned char * data;
5461      int *           length_return;
5462      int             sign;
5463 {
5464   unsigned long int result = 0;
5465   unsigned int      num_read = 0;
5466   int               shift = 0;
5467   unsigned char     byte;
5468
5469   do
5470     {
5471       byte = * data ++;
5472       num_read ++;
5473
5474       result |= (byte & 0x7f) << shift;
5475
5476       shift += 7;
5477
5478     }
5479   while (byte & 0x80);
5480
5481   if (length_return != NULL)
5482     * length_return = num_read;
5483
5484   if (sign && (shift < 32) && (byte & 0x40))
5485     result |= -1 << shift;
5486
5487   return result;
5488 }
5489
5490 typedef struct State_Machine_Registers
5491 {
5492   unsigned long address;
5493   unsigned int  file;
5494   unsigned int  line;
5495   unsigned int  column;
5496   int           is_stmt;
5497   int           basic_block;
5498   int           end_sequence;
5499 /* This variable hold the number of the last entry seen
5500    in the File Table.  */
5501   unsigned int  last_file_entry;
5502 } SMR;
5503
5504 static SMR state_machine_regs;
5505
5506 static void
5507 reset_state_machine (is_stmt)
5508      int is_stmt;
5509 {
5510   state_machine_regs.address = 0;
5511   state_machine_regs.file = 1;
5512   state_machine_regs.line = 1;
5513   state_machine_regs.column = 0;
5514   state_machine_regs.is_stmt = is_stmt;
5515   state_machine_regs.basic_block = 0;
5516   state_machine_regs.end_sequence = 0;
5517   state_machine_regs.last_file_entry = 0;
5518 }
5519
5520 /* Handled an extend line op.  Returns true if this is the end
5521    of sequence.  */
5522 static int
5523 process_extended_line_op (data, is_stmt, pointer_size)
5524      unsigned char * data;
5525      int is_stmt;
5526      int pointer_size;
5527 {
5528   unsigned char   op_code;
5529   int             bytes_read;
5530   unsigned int    len;
5531   unsigned char * name;
5532   unsigned long   adr;
5533
5534   len = read_leb128 (data, & bytes_read, 0);
5535   data += bytes_read;
5536
5537   if (len == 0)
5538     {
5539       warn (_("badly formed extended line op encountered!"));
5540       return bytes_read;
5541     }
5542
5543   len += bytes_read;
5544   op_code = * data ++;
5545
5546   printf (_("  Extended opcode %d: "), op_code);
5547
5548   switch (op_code)
5549     {
5550     case DW_LNE_end_sequence:
5551       printf (_("End of Sequence\n\n"));
5552       reset_state_machine (is_stmt);
5553       break;
5554
5555     case DW_LNE_set_address:
5556       adr = byte_get (data, pointer_size);
5557       printf (_("set Address to 0x%lx\n"), adr);
5558       state_machine_regs.address = adr;
5559       break;
5560
5561     case DW_LNE_define_file:
5562       printf (_("  define new File Table entry\n"));
5563       printf (_("  Entry\tDir\tTime\tSize\tName\n"));
5564
5565       printf (_("   %d\t"), ++ state_machine_regs.last_file_entry);
5566       name = data;
5567       data += strlen ((char *) data) + 1;
5568       printf (_("%lu\t"), read_leb128 (data, & bytes_read, 0));
5569       data += bytes_read;
5570       printf (_("%lu\t"), read_leb128 (data, & bytes_read, 0));
5571       data += bytes_read;
5572       printf (_("%lu\t"), read_leb128 (data, & bytes_read, 0));
5573       printf (_("%s\n\n"), name);
5574       break;
5575
5576     default:
5577       printf (_("UNKNOWN: length %d\n"), len - bytes_read);
5578       break;
5579     }
5580
5581   return len;
5582 }
5583
5584 /* Size of pointers in the .debug_line section.  This information is not
5585    really present in that section.  It's obtained before dumping the debug
5586    sections by doing some pre-scan of the .debug_info section.  */
5587 static int debug_line_pointer_size = 4;
5588
5589 static int
5590 display_debug_lines (section, start, file)
5591      Elf32_Internal_Shdr * section;
5592      unsigned char *       start;
5593      FILE *                file ATTRIBUTE_UNUSED;
5594 {
5595   DWARF2_External_LineInfo * external;
5596   DWARF2_Internal_LineInfo   info;
5597   unsigned char *            standard_opcodes;
5598   unsigned char *            data = start;
5599   unsigned char *            end  = start + section->sh_size;
5600   unsigned char *            end_of_sequence;
5601   int                        i;
5602
5603   printf (_("\nDump of debug contents of section %s:\n\n"),
5604           SECTION_NAME (section));
5605
5606   while (data < end)
5607     {
5608       external = (DWARF2_External_LineInfo *) data;
5609
5610       /* Check the length of the block.  */
5611       info.li_length = BYTE_GET (external->li_length);
5612       if (info.li_length + sizeof (external->li_length) > section->sh_size)
5613         {
5614           warn
5615             (_("The line info appears to be corrupt - the section is too small\n"));
5616           return 0;
5617         }
5618
5619       /* Check its version number.  */
5620       info.li_version = BYTE_GET (external->li_version);
5621       if (info.li_version != 2)
5622         {
5623           warn (_("Only DWARF version 2 line info is currently supported.\n"));
5624           return 0;
5625         }
5626
5627       info.li_prologue_length = BYTE_GET (external->li_prologue_length);
5628       info.li_min_insn_length = BYTE_GET (external->li_min_insn_length);
5629       info.li_default_is_stmt = BYTE_GET (external->li_default_is_stmt);
5630       info.li_line_base       = BYTE_GET (external->li_line_base);
5631       info.li_line_range      = BYTE_GET (external->li_line_range);
5632       info.li_opcode_base     = BYTE_GET (external->li_opcode_base);
5633
5634       /* Sign extend the line base field.  */
5635       info.li_line_base <<= 24;
5636       info.li_line_base >>= 24;
5637
5638       printf (_("  Length:                      %ld\n"), info.li_length);
5639       printf (_("  DWARF Version:               %d\n"), info.li_version);
5640       printf (_("  Prologue Length:             %d\n"), info.li_prologue_length);
5641       printf (_("  Minimum Instruction Length:  %d\n"), info.li_min_insn_length);
5642       printf (_("  Initial value of 'is_stmt':  %d\n"), info.li_default_is_stmt);
5643       printf (_("  Line Base:                   %d\n"), info.li_line_base);
5644       printf (_("  Line Range:                  %d\n"), info.li_line_range);
5645       printf (_("  Opcode Base:                 %d\n"), info.li_opcode_base);
5646
5647       end_of_sequence = data + info.li_length + sizeof (external->li_length);
5648
5649       reset_state_machine (info.li_default_is_stmt);
5650
5651       /* Display the contents of the Opcodes table.  */
5652       standard_opcodes = data + sizeof (* external);
5653
5654       printf (_("\n Opcodes:\n"));
5655
5656       for (i = 1; i < info.li_opcode_base; i++)
5657         printf (_("  Opcode %d has %d args\n"), i, standard_opcodes[i - 1]);
5658
5659       /* Display the contents of the Directory table.  */
5660       data = standard_opcodes + info.li_opcode_base - 1;
5661
5662       if (* data == 0)
5663         printf (_("\n The Directory Table is empty.\n"));
5664       else
5665         {
5666           printf (_("\n The Directory Table:\n"));
5667
5668           while (* data != 0)
5669             {
5670               printf (_("  %s\n"), data);
5671
5672               data += strlen ((char *) data) + 1;
5673             }
5674         }
5675
5676       /* Skip the NUL at the end of the table.  */
5677       data ++;
5678
5679       /* Display the contents of the File Name table.  */
5680       if (* data == 0)
5681         printf (_("\n The File Name Table is empty.\n"));
5682       else
5683         {
5684           printf (_("\n The File Name Table:\n"));
5685           printf (_("  Entry\tDir\tTime\tSize\tName\n"));
5686
5687           while (* data != 0)
5688             {
5689               unsigned char * name;
5690               int bytes_read;
5691
5692               printf (_("  %d\t"), ++ state_machine_regs.last_file_entry);
5693               name = data;
5694
5695               data += strlen ((char *) data) + 1;
5696
5697               printf (_("%lu\t"), read_leb128 (data, & bytes_read, 0));
5698               data += bytes_read;
5699               printf (_("%lu\t"), read_leb128 (data, & bytes_read, 0));
5700               data += bytes_read;
5701               printf (_("%lu\t"), read_leb128 (data, & bytes_read, 0));
5702               data += bytes_read;
5703               printf (_("%s\n"), name);
5704             }
5705         }
5706
5707       /* Skip the NUL at the end of the table.  */
5708       data ++;
5709
5710       /* Now display the statements.  */
5711       printf (_("\n Line Number Statements:\n"));
5712
5713
5714       while (data < end_of_sequence)
5715         {
5716           unsigned char op_code;
5717           int           adv;
5718           int           bytes_read;
5719
5720           op_code = * data ++;
5721
5722           switch (op_code)
5723             {
5724             case DW_LNS_extended_op:
5725               data += process_extended_line_op (data, info.li_default_is_stmt,
5726                                                 debug_line_pointer_size);
5727               break;
5728
5729             case DW_LNS_copy:
5730               printf (_("  Copy\n"));
5731               break;
5732
5733             case DW_LNS_advance_pc:
5734               adv = info.li_min_insn_length * read_leb128 (data, & bytes_read, 0);
5735               data += bytes_read;
5736               state_machine_regs.address += adv;
5737               printf (_("  Advance PC by %d to %lx\n"), adv,
5738                       state_machine_regs.address);
5739               break;
5740
5741             case DW_LNS_advance_line:
5742               adv = read_leb128 (data, & bytes_read, 1);
5743               data += bytes_read;
5744               state_machine_regs.line += adv;
5745               printf (_("  Advance Line by %d to %d\n"), adv,
5746                       state_machine_regs.line);
5747               break;
5748
5749             case DW_LNS_set_file:
5750               adv = read_leb128 (data, & bytes_read, 0);
5751               data += bytes_read;
5752               printf (_("  Set File Name to entry %d in the File Name Table\n"),
5753                       adv);
5754               state_machine_regs.file = adv;
5755               break;
5756
5757             case DW_LNS_set_column:
5758               adv = read_leb128 (data, & bytes_read, 0);
5759               data += bytes_read;
5760               printf (_("  Set column to %d\n"), adv);
5761               state_machine_regs.column = adv;
5762               break;
5763
5764             case DW_LNS_negate_stmt:
5765               adv = state_machine_regs.is_stmt;
5766               adv = ! adv;
5767               printf (_("  Set is_stmt to %d\n"), adv);
5768               state_machine_regs.is_stmt = adv;
5769               break;
5770
5771             case DW_LNS_set_basic_block:
5772               printf (_("  Set basic block\n"));
5773               state_machine_regs.basic_block = 1;
5774               break;
5775
5776             case DW_LNS_const_add_pc:
5777               adv = (((255 - info.li_opcode_base) / info.li_line_range)
5778                      * info.li_min_insn_length);
5779               state_machine_regs.address += adv;
5780               printf (_("  Advance PC by constant %d to 0x%lx\n"), adv,
5781                       state_machine_regs.address);
5782               break;
5783
5784             case DW_LNS_fixed_advance_pc:
5785               adv = byte_get (data, 2);
5786               data += 2;
5787               state_machine_regs.address += adv;
5788               printf (_("  Advance PC by fixed size amount %d to 0x%lx\n"),
5789                       adv, state_machine_regs.address);
5790               break;
5791
5792             default:
5793               op_code -= info.li_opcode_base;
5794               adv      = (op_code / info.li_line_range) * info.li_min_insn_length;
5795               state_machine_regs.address += adv;
5796               printf (_("  Special opcode %d: advance Address by %d to 0x%lx"),
5797                       op_code, adv, state_machine_regs.address);
5798               adv = (op_code % info.li_line_range) + info.li_line_base;
5799               state_machine_regs.line += adv;
5800               printf (_(" and Line by %d to %d\n"),
5801                       adv, state_machine_regs.line);
5802               break;
5803             }
5804         }
5805       printf ("\n");
5806     }
5807
5808   return 1;
5809 }
5810
5811 static int
5812 display_debug_pubnames (section, start, file)
5813      Elf32_Internal_Shdr * section;
5814      unsigned char *       start;
5815      FILE *                file ATTRIBUTE_UNUSED;
5816 {
5817   DWARF2_External_PubNames * external;
5818   DWARF2_Internal_PubNames   pubnames;
5819   unsigned char *            end;
5820
5821   end = start + section->sh_size;
5822
5823   printf (_("Contents of the %s section:\n\n"), SECTION_NAME (section));
5824
5825   while (start < end)
5826     {
5827       unsigned char * data;
5828       unsigned long   offset;
5829
5830       external = (DWARF2_External_PubNames *) start;
5831
5832       pubnames.pn_length  = BYTE_GET (external->pn_length);
5833       pubnames.pn_version = BYTE_GET (external->pn_version);
5834       pubnames.pn_offset  = BYTE_GET (external->pn_offset);
5835       pubnames.pn_size    = BYTE_GET (external->pn_size);
5836
5837       data   = start + sizeof (* external);
5838       start += pubnames.pn_length + sizeof (external->pn_length);
5839
5840       if (pubnames.pn_version != 2)
5841         {
5842           static int warned = 0;
5843
5844           if (! warned)
5845             {
5846               warn (_("Only DWARF 2 pubnames are currently supported\n"));
5847               warned = 1;
5848             }
5849
5850           continue;
5851         }
5852
5853       printf (_("  Length:                              %ld\n"),
5854               pubnames.pn_length);
5855       printf (_("  Version:                             %d\n"),
5856               pubnames.pn_version);
5857       printf (_("  Offset into .debug_info section:     %ld\n"),
5858               pubnames.pn_offset);
5859       printf (_("  Size of area in .debug_info section: %ld\n"),
5860               pubnames.pn_size);
5861
5862       printf (_("\n    Offset\tName\n"));
5863
5864       do
5865         {
5866           offset = byte_get (data, 4);
5867
5868           if (offset != 0)
5869             {
5870               data += 4;
5871               printf ("    %ld\t\t%s\n", offset, data);
5872               data += strlen ((char *) data) + 1;
5873             }
5874         }
5875       while (offset != 0);
5876     }
5877
5878   printf ("\n");
5879   return 1;
5880 }
5881
5882 static char *
5883 get_TAG_name (tag)
5884      unsigned long tag;
5885 {
5886   switch (tag)
5887     {
5888     case DW_TAG_padding: return "DW_TAG_padding";
5889     case DW_TAG_array_type: return "DW_TAG_array_type";
5890     case DW_TAG_class_type: return "DW_TAG_class_type";
5891     case DW_TAG_entry_point: return "DW_TAG_entry_point";
5892     case DW_TAG_enumeration_type: return "DW_TAG_enumeration_type";
5893     case DW_TAG_formal_parameter: return "DW_TAG_formal_parameter";
5894     case DW_TAG_imported_declaration: return "DW_TAG_imported_declaration";
5895     case DW_TAG_label: return "DW_TAG_label";
5896     case DW_TAG_lexical_block: return "DW_TAG_lexical_block";
5897     case DW_TAG_member: return "DW_TAG_member";
5898     case DW_TAG_pointer_type: return "DW_TAG_pointer_type";
5899     case DW_TAG_reference_type: return "DW_TAG_reference_type";
5900     case DW_TAG_compile_unit: return "DW_TAG_compile_unit";
5901     case DW_TAG_string_type: return "DW_TAG_string_type";
5902     case DW_TAG_structure_type: return "DW_TAG_structure_type";
5903     case DW_TAG_subroutine_type: return "DW_TAG_subroutine_type";
5904     case DW_TAG_typedef: return "DW_TAG_typedef";
5905     case DW_TAG_union_type: return "DW_TAG_union_type";
5906     case DW_TAG_unspecified_parameters: return "DW_TAG_unspecified_parameters";
5907     case DW_TAG_variant: return "DW_TAG_variant";
5908     case DW_TAG_common_block: return "DW_TAG_common_block";
5909     case DW_TAG_common_inclusion: return "DW_TAG_common_inclusion";
5910     case DW_TAG_inheritance: return "DW_TAG_inheritance";
5911     case DW_TAG_inlined_subroutine: return "DW_TAG_inlined_subroutine";
5912     case DW_TAG_module: return "DW_TAG_module";
5913     case DW_TAG_ptr_to_member_type: return "DW_TAG_ptr_to_member_type";
5914     case DW_TAG_set_type: return "DW_TAG_set_type";
5915     case DW_TAG_subrange_type: return "DW_TAG_subrange_type";
5916     case DW_TAG_with_stmt: return "DW_TAG_with_stmt";
5917     case DW_TAG_access_declaration: return "DW_TAG_access_declaration";
5918     case DW_TAG_base_type: return "DW_TAG_base_type";
5919     case DW_TAG_catch_block: return "DW_TAG_catch_block";
5920     case DW_TAG_const_type: return "DW_TAG_const_type";
5921     case DW_TAG_constant: return "DW_TAG_constant";
5922     case DW_TAG_enumerator: return "DW_TAG_enumerator";
5923     case DW_TAG_file_type: return "DW_TAG_file_type";
5924     case DW_TAG_friend: return "DW_TAG_friend";
5925     case DW_TAG_namelist: return "DW_TAG_namelist";
5926     case DW_TAG_namelist_item: return "DW_TAG_namelist_item";
5927     case DW_TAG_packed_type: return "DW_TAG_packed_type";
5928     case DW_TAG_subprogram: return "DW_TAG_subprogram";
5929     case DW_TAG_template_type_param: return "DW_TAG_template_type_param";
5930     case DW_TAG_template_value_param: return "DW_TAG_template_value_param";
5931     case DW_TAG_thrown_type: return "DW_TAG_thrown_type";
5932     case DW_TAG_try_block: return "DW_TAG_try_block";
5933     case DW_TAG_variant_part: return "DW_TAG_variant_part";
5934     case DW_TAG_variable: return "DW_TAG_variable";
5935     case DW_TAG_volatile_type: return "DW_TAG_volatile_type";
5936     case DW_TAG_MIPS_loop: return "DW_TAG_MIPS_loop";
5937     case DW_TAG_format_label: return "DW_TAG_format_label";
5938     case DW_TAG_function_template: return "DW_TAG_function_template";
5939     case DW_TAG_class_template: return "DW_TAG_class_template";
5940     default:
5941       {
5942         static char buffer [100];
5943
5944         sprintf (buffer, _("Unknown TAG value: %lx"), tag);
5945         return buffer;
5946       }
5947     }
5948 }
5949
5950 static char *
5951 get_AT_name (attribute)
5952      unsigned long attribute;
5953 {
5954   switch (attribute)
5955     {
5956     case DW_AT_sibling: return "DW_AT_sibling";
5957     case DW_AT_location: return "DW_AT_location";
5958     case DW_AT_name: return "DW_AT_name";
5959     case DW_AT_ordering: return "DW_AT_ordering";
5960     case DW_AT_subscr_data: return "DW_AT_subscr_data";
5961     case DW_AT_byte_size: return "DW_AT_byte_size";
5962     case DW_AT_bit_offset: return "DW_AT_bit_offset";
5963     case DW_AT_bit_size: return "DW_AT_bit_size";
5964     case DW_AT_element_list: return "DW_AT_element_list";
5965     case DW_AT_stmt_list: return "DW_AT_stmt_list";
5966     case DW_AT_low_pc: return "DW_AT_low_pc";
5967     case DW_AT_high_pc: return "DW_AT_high_pc";
5968     case DW_AT_language: return "DW_AT_language";
5969     case DW_AT_member: return "DW_AT_member";
5970     case DW_AT_discr: return "DW_AT_discr";
5971     case DW_AT_discr_value: return "DW_AT_discr_value";
5972     case DW_AT_visibility: return "DW_AT_visibility";
5973     case DW_AT_import: return "DW_AT_import";
5974     case DW_AT_string_length: return "DW_AT_string_length";
5975     case DW_AT_common_reference: return "DW_AT_common_reference";
5976     case DW_AT_comp_dir: return "DW_AT_comp_dir";
5977     case DW_AT_const_value: return "DW_AT_const_value";
5978     case DW_AT_containing_type: return "DW_AT_containing_type";
5979     case DW_AT_default_value: return "DW_AT_default_value";
5980     case DW_AT_inline: return "DW_AT_inline";
5981     case DW_AT_is_optional: return "DW_AT_is_optional";
5982     case DW_AT_lower_bound: return "DW_AT_lower_bound";
5983     case DW_AT_producer: return "DW_AT_producer";
5984     case DW_AT_prototyped: return "DW_AT_prototyped";
5985     case DW_AT_return_addr: return "DW_AT_return_addr";
5986     case DW_AT_start_scope: return "DW_AT_start_scope";
5987     case DW_AT_stride_size: return "DW_AT_stride_size";
5988     case DW_AT_upper_bound: return "DW_AT_upper_bound";
5989     case DW_AT_abstract_origin: return "DW_AT_abstract_origin";
5990     case DW_AT_accessibility: return "DW_AT_accessibility";
5991     case DW_AT_address_class: return "DW_AT_address_class";
5992     case DW_AT_artificial: return "DW_AT_artificial";
5993     case DW_AT_base_types: return "DW_AT_base_types";
5994     case DW_AT_calling_convention: return "DW_AT_calling_convention";
5995     case DW_AT_count: return "DW_AT_count";
5996     case DW_AT_data_member_location: return "DW_AT_data_member_location";
5997     case DW_AT_decl_column: return "DW_AT_decl_column";
5998     case DW_AT_decl_file: return "DW_AT_decl_file";
5999     case DW_AT_decl_line: return "DW_AT_decl_line";
6000     case DW_AT_declaration: return "DW_AT_declaration";
6001     case DW_AT_discr_list: return "DW_AT_discr_list";
6002     case DW_AT_encoding: return "DW_AT_encoding";
6003     case DW_AT_external: return "DW_AT_external";
6004     case DW_AT_frame_base: return "DW_AT_frame_base";
6005     case DW_AT_friend: return "DW_AT_friend";
6006     case DW_AT_identifier_case: return "DW_AT_identifier_case";
6007     case DW_AT_macro_info: return "DW_AT_macro_info";
6008     case DW_AT_namelist_items: return "DW_AT_namelist_items";
6009     case DW_AT_priority: return "DW_AT_priority";
6010     case DW_AT_segment: return "DW_AT_segment";
6011     case DW_AT_specification: return "DW_AT_specification";
6012     case DW_AT_static_link: return "DW_AT_static_link";
6013     case DW_AT_type: return "DW_AT_type";
6014     case DW_AT_use_location: return "DW_AT_use_location";
6015     case DW_AT_variable_parameter: return "DW_AT_variable_parameter";
6016     case DW_AT_virtuality: return "DW_AT_virtuality";
6017     case DW_AT_vtable_elem_location: return "DW_AT_vtable_elem_location";
6018       /* DWARF 2.1 values.  */
6019     case DW_AT_allocated: return "DW_AT_allocated";
6020     case DW_AT_associated: return "DW_AT_associated";
6021     case DW_AT_data_location: return "DW_AT_data_location";
6022     case DW_AT_stride: return "DW_AT_stride";
6023     case DW_AT_entry_pc: return "DW_AT_entry_pc";
6024     case DW_AT_use_UTF8: return "DW_AT_use_UTF8";
6025     case DW_AT_extension: return "DW_AT_extension";
6026     case DW_AT_ranges: return "DW_AT_ranges";
6027     case DW_AT_trampoline: return "DW_AT_trampoline";
6028     case DW_AT_call_column: return "DW_AT_call_column";
6029     case DW_AT_call_file: return "DW_AT_call_file";
6030     case DW_AT_call_line: return "DW_AT_call_line";
6031       /* SGI/MIPS extensions.  */
6032     case DW_AT_MIPS_fde: return "DW_AT_MIPS_fde";
6033     case DW_AT_MIPS_loop_begin: return "DW_AT_MIPS_loop_begin";
6034     case DW_AT_MIPS_tail_loop_begin: return "DW_AT_MIPS_tail_loop_begin";
6035     case DW_AT_MIPS_epilog_begin: return "DW_AT_MIPS_epilog_begin";
6036     case DW_AT_MIPS_loop_unroll_factor: return "DW_AT_MIPS_loop_unroll_factor";
6037     case DW_AT_MIPS_software_pipeline_depth: return "DW_AT_MIPS_software_pipeline_depth";
6038     case DW_AT_MIPS_linkage_name: return "DW_AT_MIPS_linkage_name";
6039     case DW_AT_MIPS_stride: return "DW_AT_MIPS_stride";
6040     case DW_AT_MIPS_abstract_name: return "DW_AT_MIPS_abstract_name";
6041     case DW_AT_MIPS_clone_origin: return "DW_AT_MIPS_clone_origin";
6042     case DW_AT_MIPS_has_inlines: return "DW_AT_MIPS_has_inlines";
6043       /* GNU extensions.  */
6044     case DW_AT_sf_names: return "DW_AT_sf_names";
6045     case DW_AT_src_info: return "DW_AT_src_info";
6046     case DW_AT_mac_info: return "DW_AT_mac_info";
6047     case DW_AT_src_coords: return "DW_AT_src_coords";
6048     case DW_AT_body_begin: return "DW_AT_body_begin";
6049     case DW_AT_body_end: return "DW_AT_body_end";
6050     default:
6051       {
6052         static char buffer [100];
6053
6054         sprintf (buffer, _("Unknown AT value: %lx"), attribute);
6055         return buffer;
6056       }
6057     }
6058 }
6059
6060 static char *
6061 get_FORM_name (form)
6062      unsigned long form;
6063 {
6064   switch (form)
6065     {
6066     case DW_FORM_addr: return "DW_FORM_addr";
6067     case DW_FORM_block2: return "DW_FORM_block2";
6068     case DW_FORM_block4: return "DW_FORM_block4";
6069     case DW_FORM_data2: return "DW_FORM_data2";
6070     case DW_FORM_data4: return "DW_FORM_data4";
6071     case DW_FORM_data8: return "DW_FORM_data8";
6072     case DW_FORM_string: return "DW_FORM_string";
6073     case DW_FORM_block: return "DW_FORM_block";
6074     case DW_FORM_block1: return "DW_FORM_block1";
6075     case DW_FORM_data1: return "DW_FORM_data1";
6076     case DW_FORM_flag: return "DW_FORM_flag";
6077     case DW_FORM_sdata: return "DW_FORM_sdata";
6078     case DW_FORM_strp: return "DW_FORM_strp";
6079     case DW_FORM_udata: return "DW_FORM_udata";
6080     case DW_FORM_ref_addr: return "DW_FORM_ref_addr";
6081     case DW_FORM_ref1: return "DW_FORM_ref1";
6082     case DW_FORM_ref2: return "DW_FORM_ref2";
6083     case DW_FORM_ref4: return "DW_FORM_ref4";
6084     case DW_FORM_ref8: return "DW_FORM_ref8";
6085     case DW_FORM_ref_udata: return "DW_FORM_ref_udata";
6086     case DW_FORM_indirect: return "DW_FORM_indirect";
6087     default:
6088       {
6089         static char buffer [100];
6090
6091         sprintf (buffer, _("Unknown FORM value: %lx"), form);
6092         return buffer;
6093       }
6094     }
6095 }
6096
6097 /* FIXME:  There are better and more effiecint ways to handle
6098    these structures.  For now though, I just want something that
6099    is simple to implement.  */
6100 typedef struct abbrev_attr
6101 {
6102   unsigned long        attribute;
6103   unsigned long        form;
6104   struct abbrev_attr * next;
6105 }
6106 abbrev_attr;
6107
6108 typedef struct abbrev_entry
6109 {
6110   unsigned long          entry;
6111   unsigned long          tag;
6112   int                    children;
6113   struct abbrev_attr *   first_attr;
6114   struct abbrev_attr *   last_attr;
6115   struct abbrev_entry *  next;
6116 }
6117 abbrev_entry;
6118
6119 static abbrev_entry * first_abbrev = NULL;
6120 static abbrev_entry * last_abbrev = NULL;
6121
6122 static void
6123 free_abbrevs PARAMS ((void))
6124 {
6125   abbrev_entry * abbrev;
6126
6127   for (abbrev = first_abbrev; abbrev;)
6128     {
6129       abbrev_entry * next = abbrev->next;
6130       abbrev_attr  * attr;
6131
6132       for (attr = abbrev->first_attr; attr;)
6133         {
6134           abbrev_attr * next = attr->next;
6135
6136           free (attr);
6137           attr = next;
6138         }
6139
6140       free (abbrev);
6141       abbrev = next;
6142     }
6143
6144   last_abbrev = first_abbrev = NULL;
6145 }
6146
6147 static void
6148 add_abbrev (number, tag, children)
6149      unsigned long number;
6150      unsigned long tag;
6151      int           children;
6152 {
6153   abbrev_entry * entry;
6154
6155   entry = (abbrev_entry *) malloc (sizeof (* entry));
6156
6157   if (entry == NULL)
6158     /* ugg */
6159     return;
6160
6161   entry->entry      = number;
6162   entry->tag        = tag;
6163   entry->children   = children;
6164   entry->first_attr = NULL;
6165   entry->last_attr  = NULL;
6166   entry->next       = NULL;
6167
6168   if (first_abbrev == NULL)
6169     first_abbrev = entry;
6170   else
6171     last_abbrev->next = entry;
6172
6173   last_abbrev = entry;
6174 }
6175
6176 static void
6177 add_abbrev_attr (attribute, form)
6178      unsigned long attribute;
6179      unsigned long form;
6180 {
6181   abbrev_attr * attr;
6182
6183   attr = (abbrev_attr *) malloc (sizeof (* attr));
6184
6185   if (attr == NULL)
6186     /* ugg */
6187     return;
6188
6189   attr->attribute = attribute;
6190   attr->form      = form;
6191   attr->next      = NULL;
6192
6193   if (last_abbrev->first_attr == NULL)
6194     last_abbrev->first_attr = attr;
6195   else
6196     last_abbrev->last_attr->next = attr;
6197
6198   last_abbrev->last_attr = attr;
6199 }
6200
6201 /* Processes the (partial) contents of a .debug_abbrev section.
6202    Returns NULL if the end of the section was encountered.
6203    Returns the address after the last byte read if the end of
6204    an abbreviation set was found.  */
6205
6206 static unsigned char *
6207 process_abbrev_section (start, end)
6208      unsigned char * start;
6209      unsigned char * end;
6210 {
6211   if (first_abbrev != NULL)
6212     return NULL;
6213
6214   while (start < end)
6215     {
6216       int           bytes_read;
6217       unsigned long entry;
6218       unsigned long tag;
6219       unsigned long attribute;
6220       int           children;
6221
6222       entry = read_leb128 (start, & bytes_read, 0);
6223       start += bytes_read;
6224
6225       /* A single zero is supposed to end the section according
6226          to the standard.  If there's more, then signal that to
6227          the caller.  */
6228       if (entry == 0)
6229         return start == end ? NULL : start;
6230
6231       tag = read_leb128 (start, & bytes_read, 0);
6232       start += bytes_read;
6233
6234       children = * start ++;
6235
6236       add_abbrev (entry, tag, children);
6237
6238       do
6239         {
6240           unsigned long form;
6241
6242           attribute = read_leb128 (start, & bytes_read, 0);
6243           start += bytes_read;
6244
6245           form = read_leb128 (start, & bytes_read, 0);
6246           start += bytes_read;
6247
6248           if (attribute != 0)
6249             add_abbrev_attr (attribute, form);
6250         }
6251       while (attribute != 0);
6252     }
6253
6254   return NULL;
6255 }
6256
6257
6258 static int
6259 display_debug_abbrev (section, start, file)
6260      Elf32_Internal_Shdr * section;
6261      unsigned char *       start;
6262      FILE *                file ATTRIBUTE_UNUSED;
6263 {
6264   abbrev_entry *  entry;
6265   unsigned char * end = start + section->sh_size;
6266
6267   printf (_("Contents of the %s section:\n\n"), SECTION_NAME (section));
6268
6269   do
6270     {
6271       start = process_abbrev_section (start, end);
6272
6273       printf (_("  Number TAG\n"));
6274
6275       for (entry = first_abbrev; entry; entry = entry->next)
6276         {
6277           abbrev_attr * attr;
6278
6279           printf (_("   %ld      %s    [%s]\n"),
6280                   entry->entry,
6281                   get_TAG_name (entry->tag),
6282                   entry->children ? _("has children") : _("no children"));
6283
6284           for (attr = entry->first_attr; attr; attr = attr->next)
6285             {
6286               printf (_("    %-18s %s\n"),
6287                       get_AT_name (attr->attribute),
6288                       get_FORM_name (attr->form));
6289             }
6290         }
6291     }
6292   while (start);
6293
6294   printf ("\n");
6295
6296   return 1;
6297 }
6298
6299
6300 static unsigned char *
6301 display_block (data, length)
6302      unsigned char * data;
6303      unsigned long   length;
6304 {
6305   printf (_(" %lu byte block: "), length);
6306
6307   while (length --)
6308     printf ("%lx ", (unsigned long) byte_get (data ++, 1));
6309
6310   return data;
6311 }
6312
6313 static void
6314 decode_location_expression (data, pointer_size, length)
6315      unsigned char * data;
6316      unsigned int    pointer_size;
6317      unsigned long   length;
6318 {
6319   unsigned        op;
6320   int             bytes_read;
6321   unsigned long   uvalue;
6322   unsigned char * end = data + length;
6323
6324   while (data < end)
6325     {
6326       op = * data ++;
6327
6328       switch (op)
6329         {
6330         case DW_OP_addr:
6331           printf ("DW_OP_addr: %lx",
6332                   (unsigned long) byte_get (data, pointer_size));
6333           data += pointer_size;
6334           break;
6335         case DW_OP_deref:
6336           printf ("DW_OP_deref");
6337           break;
6338         case DW_OP_const1u:
6339           printf ("DW_OP_const1u: %lu", (unsigned long) byte_get (data++, 1));
6340           break;
6341         case DW_OP_const1s:
6342           printf ("DW_OP_const1s: %ld", (long) byte_get (data++, 1));
6343           break;
6344         case DW_OP_const2u:
6345           printf ("DW_OP_const2u: %lu", (unsigned long) byte_get (data, 2));
6346           data += 2;
6347           break;
6348         case DW_OP_const2s:
6349           printf ("DW_OP_const2s: %ld", (long) byte_get (data, 2));
6350           data += 2;
6351           break;
6352         case DW_OP_const4u:
6353           printf ("DW_OP_const4u: %lu", (unsigned long) byte_get (data, 4));
6354           data += 4;
6355           break;
6356         case DW_OP_const4s:
6357           printf ("DW_OP_const4s: %ld", (long) byte_get (data, 4));
6358           data += 4;
6359           break;
6360         case DW_OP_const8u:
6361           printf ("DW_OP_const8u: %lu %lu", (unsigned long) byte_get (data, 4),
6362                   (unsigned long) byte_get (data + 4, 4));
6363           data += 8;
6364           break;
6365         case DW_OP_const8s:
6366           printf ("DW_OP_const8s: %ld %ld", (long) byte_get (data, 4),
6367                   (long) byte_get (data + 4, 4));
6368           data += 8;
6369           break;
6370         case DW_OP_constu:
6371           printf ("DW_OP_constu: %lu", read_leb128 (data, &bytes_read, 0));
6372           data += bytes_read;
6373           break;
6374         case DW_OP_consts:
6375           printf ("DW_OP_consts: %ld", read_leb128 (data, &bytes_read, 1));
6376           data += bytes_read;
6377           break;
6378         case DW_OP_dup:
6379           printf ("DW_OP_dup");
6380           break;
6381         case DW_OP_drop:
6382           printf ("DW_OP_drop");
6383           break;
6384         case DW_OP_over:
6385           printf ("DW_OP_over");
6386           break;
6387         case DW_OP_pick:
6388           printf ("DW_OP_pick: %ld", (unsigned long) byte_get (data++, 1));
6389           break;
6390         case DW_OP_swap:
6391           printf ("DW_OP_swap");
6392           break;
6393         case DW_OP_rot:
6394           printf ("DW_OP_rot");
6395           break;
6396         case DW_OP_xderef:
6397           printf ("DW_OP_xderef");
6398           break;
6399         case DW_OP_abs:
6400           printf ("DW_OP_abs");
6401           break;
6402         case DW_OP_and:
6403           printf ("DW_OP_and");
6404           break;
6405         case DW_OP_div:
6406           printf ("DW_OP_div");
6407           break;
6408         case DW_OP_minus:
6409           printf ("DW_OP_minus");
6410           break;
6411         case DW_OP_mod:
6412           printf ("DW_OP_mod");
6413           break;
6414         case DW_OP_mul:
6415           printf ("DW_OP_mul");
6416           break;
6417         case DW_OP_neg:
6418           printf ("DW_OP_neg");
6419           break;
6420         case DW_OP_not:
6421           printf ("DW_OP_not");
6422           break;
6423         case DW_OP_or:
6424           printf ("DW_OP_or");
6425           break;
6426         case DW_OP_plus:
6427           printf ("DW_OP_plus");
6428           break;
6429         case DW_OP_plus_uconst:
6430           printf ("DW_OP_plus_uconst: %lu",
6431                   read_leb128 (data, &bytes_read, 0));
6432           data += bytes_read;
6433           break;
6434         case DW_OP_shl:
6435           printf ("DW_OP_shl");
6436           break;
6437         case DW_OP_shr:
6438           printf ("DW_OP_shr");
6439           break;
6440         case DW_OP_shra:
6441           printf ("DW_OP_shra");
6442           break;
6443         case DW_OP_xor:
6444           printf ("DW_OP_xor");
6445           break;
6446         case DW_OP_bra:
6447           printf ("DW_OP_bra: %ld", (long) byte_get (data, 2));
6448           data += 2;
6449           break;
6450         case DW_OP_eq:
6451           printf ("DW_OP_eq");
6452           break;
6453         case DW_OP_ge:
6454           printf ("DW_OP_ge");
6455           break;
6456         case DW_OP_gt:
6457           printf ("DW_OP_gt");
6458           break;
6459         case DW_OP_le:
6460           printf ("DW_OP_le");
6461           break;
6462         case DW_OP_lt:
6463           printf ("DW_OP_lt");
6464           break;
6465         case DW_OP_ne:
6466           printf ("DW_OP_ne");
6467           break;
6468         case DW_OP_skip:
6469           printf ("DW_OP_skip: %ld", (long) byte_get (data, 2));
6470           data += 2;
6471           break;
6472
6473         case DW_OP_lit0:
6474         case DW_OP_lit1:
6475         case DW_OP_lit2:
6476         case DW_OP_lit3:
6477         case DW_OP_lit4:
6478         case DW_OP_lit5:
6479         case DW_OP_lit6:
6480         case DW_OP_lit7:
6481         case DW_OP_lit8:
6482         case DW_OP_lit9:
6483         case DW_OP_lit10:
6484         case DW_OP_lit11:
6485         case DW_OP_lit12:
6486         case DW_OP_lit13:
6487         case DW_OP_lit14:
6488         case DW_OP_lit15:
6489         case DW_OP_lit16:
6490         case DW_OP_lit17:
6491         case DW_OP_lit18:
6492         case DW_OP_lit19:
6493         case DW_OP_lit20:
6494         case DW_OP_lit21:
6495         case DW_OP_lit22:
6496         case DW_OP_lit23:
6497         case DW_OP_lit24:
6498         case DW_OP_lit25:
6499         case DW_OP_lit26:
6500         case DW_OP_lit27:
6501         case DW_OP_lit28:
6502         case DW_OP_lit29:
6503         case DW_OP_lit30:
6504         case DW_OP_lit31:
6505           printf ("DW_OP_lit%d", op - DW_OP_lit0);
6506           break;
6507
6508         case DW_OP_reg0:
6509         case DW_OP_reg1:
6510         case DW_OP_reg2:
6511         case DW_OP_reg3:
6512         case DW_OP_reg4:
6513         case DW_OP_reg5:
6514         case DW_OP_reg6:
6515         case DW_OP_reg7:
6516         case DW_OP_reg8:
6517         case DW_OP_reg9:
6518         case DW_OP_reg10:
6519         case DW_OP_reg11:
6520         case DW_OP_reg12:
6521         case DW_OP_reg13:
6522         case DW_OP_reg14:
6523         case DW_OP_reg15:
6524         case DW_OP_reg16:
6525         case DW_OP_reg17:
6526         case DW_OP_reg18:
6527         case DW_OP_reg19:
6528         case DW_OP_reg20:
6529         case DW_OP_reg21:
6530         case DW_OP_reg22:
6531         case DW_OP_reg23:
6532         case DW_OP_reg24:
6533         case DW_OP_reg25:
6534         case DW_OP_reg26:
6535         case DW_OP_reg27:
6536         case DW_OP_reg28:
6537         case DW_OP_reg29:
6538         case DW_OP_reg30:
6539         case DW_OP_reg31:
6540           printf ("DW_OP_reg%d", op - DW_OP_reg0);
6541           break;
6542
6543         case DW_OP_breg0:
6544         case DW_OP_breg1:
6545         case DW_OP_breg2:
6546         case DW_OP_breg3:
6547         case DW_OP_breg4:
6548         case DW_OP_breg5:
6549         case DW_OP_breg6:
6550         case DW_OP_breg7:
6551         case DW_OP_breg8:
6552         case DW_OP_breg9:
6553         case DW_OP_breg10:
6554         case DW_OP_breg11:
6555         case DW_OP_breg12:
6556         case DW_OP_breg13:
6557         case DW_OP_breg14:
6558         case DW_OP_breg15:
6559         case DW_OP_breg16:
6560         case DW_OP_breg17:
6561         case DW_OP_breg18:
6562         case DW_OP_breg19:
6563         case DW_OP_breg20:
6564         case DW_OP_breg21:
6565         case DW_OP_breg22:
6566         case DW_OP_breg23:
6567         case DW_OP_breg24:
6568         case DW_OP_breg25:
6569         case DW_OP_breg26:
6570         case DW_OP_breg27:
6571         case DW_OP_breg28:
6572         case DW_OP_breg29:
6573         case DW_OP_breg30:
6574         case DW_OP_breg31:
6575           printf ("DW_OP_breg%d: %ld", op - DW_OP_breg0,
6576                   read_leb128 (data, &bytes_read, 1));
6577           data += bytes_read;
6578           break;
6579
6580         case DW_OP_regx:
6581           printf ("DW_OP_regx: %lu", read_leb128 (data, &bytes_read, 0));
6582           data += bytes_read;
6583           break;
6584         case DW_OP_fbreg:
6585           printf ("DW_OP_fbreg: %ld", read_leb128 (data, &bytes_read, 1));
6586           data += bytes_read;
6587           break;
6588         case DW_OP_bregx:
6589           uvalue = read_leb128 (data, &bytes_read, 0);
6590           data += bytes_read;
6591           printf ("DW_OP_bregx: %lu %ld", uvalue,
6592                   read_leb128 (data, &bytes_read, 1));
6593           data += bytes_read;
6594           break;
6595         case DW_OP_piece:
6596           printf ("DW_OP_piece: %lu", read_leb128 (data, &bytes_read, 0));
6597           data += bytes_read;
6598           break;
6599         case DW_OP_deref_size:
6600           printf ("DW_OP_deref_size: %ld", (long) byte_get (data++, 1));
6601           break;
6602         case DW_OP_xderef_size:
6603           printf ("DW_OP_xderef_size: %ld", (long) byte_get (data++, 1));
6604           break;
6605         case DW_OP_nop:
6606           printf ("DW_OP_nop");
6607           break;
6608
6609           /* DWARF 2.1 extensions.  */
6610         case DW_OP_push_object_address:
6611           printf ("DW_OP_push_object_address");
6612           break;
6613         case DW_OP_call2:
6614           printf ("DW_OP_call2: <%lx>", (long) byte_get (data, 2));
6615           data += 2;
6616           break;
6617         case DW_OP_call4:
6618           printf ("DW_OP_call4: <%lx>", (long) byte_get (data, 4));
6619           data += 4;
6620           break;
6621         case DW_OP_calli:
6622           printf ("DW_OP_calli");
6623           break;
6624
6625         default:
6626           if (op >= DW_OP_lo_user
6627               && op <= DW_OP_hi_user)
6628             printf (_("(User defined location op)"));
6629           else
6630             printf (_("(Unknown location op)"));
6631           /* No way to tell where the next op is, so just bail.  */
6632           return;
6633         }
6634
6635       /* Separate the ops.  */
6636       printf ("; ");
6637     }
6638 }
6639
6640
6641 static unsigned char *
6642 read_and_display_attr (attribute, form, data, cu_offset, pointer_size)
6643      unsigned long   attribute;
6644      unsigned long   form;
6645      unsigned char * data;
6646      unsigned long   cu_offset;
6647      unsigned long   pointer_size;
6648 {
6649   unsigned long   uvalue = 0;
6650   unsigned char * block_start = NULL;
6651   int             bytes_read;
6652
6653   printf ("     %-18s:", get_AT_name (attribute));
6654
6655   switch (form)
6656     {
6657     default:
6658       break;
6659
6660     case DW_FORM_ref_addr:
6661     case DW_FORM_addr:
6662       uvalue = byte_get (data, pointer_size);
6663       data += pointer_size;
6664       break;
6665
6666     case DW_FORM_ref1:
6667     case DW_FORM_flag:
6668     case DW_FORM_data1:
6669       uvalue = byte_get (data ++, 1);
6670       break;
6671
6672     case DW_FORM_ref2:
6673     case DW_FORM_data2:
6674       uvalue = byte_get (data, 2);
6675       data += 2;
6676       break;
6677
6678     case DW_FORM_ref4:
6679     case DW_FORM_data4:
6680       uvalue = byte_get (data, 4);
6681       data += 4;
6682       break;
6683
6684     case DW_FORM_sdata:
6685       uvalue = read_leb128 (data, & bytes_read, 1);
6686       data += bytes_read;
6687       break;
6688
6689     case DW_FORM_ref_udata:
6690     case DW_FORM_udata:
6691       uvalue = read_leb128 (data, & bytes_read, 0);
6692       data += bytes_read;
6693       break;
6694     }
6695
6696   switch (form)
6697     {
6698     case DW_FORM_ref_addr:
6699       printf (" <#%lx>", uvalue);
6700       break;
6701
6702     case DW_FORM_ref1:
6703     case DW_FORM_ref2:
6704     case DW_FORM_ref4:
6705     case DW_FORM_ref_udata:
6706       printf (" <%lx>", uvalue + cu_offset);
6707       break;
6708
6709     case DW_FORM_addr:
6710       printf (" %#lx", uvalue);
6711
6712     case DW_FORM_flag:
6713     case DW_FORM_data1:
6714     case DW_FORM_data2:
6715     case DW_FORM_data4:
6716     case DW_FORM_sdata:
6717     case DW_FORM_udata:
6718       printf (" %ld", uvalue);
6719       break;
6720
6721     case DW_FORM_ref8:
6722     case DW_FORM_data8:
6723       uvalue = byte_get (data, 4);
6724       printf (" %lx", uvalue);
6725       printf (" %lx", (unsigned long) byte_get (data + 4, 4));
6726       data += 8;
6727       break;
6728
6729     case DW_FORM_string:
6730       printf (" %s", data);
6731       data += strlen ((char *) data) + 1;
6732       break;
6733
6734     case DW_FORM_block:
6735       uvalue = read_leb128 (data, & bytes_read, 0);
6736       block_start = data + bytes_read;
6737       data = display_block (block_start, uvalue);
6738       break;
6739
6740     case DW_FORM_block1:
6741       uvalue = byte_get (data, 1);
6742       block_start = data + 1;
6743       data = display_block (block_start, uvalue);
6744       break;
6745
6746     case DW_FORM_block2:
6747       uvalue = byte_get (data, 2);
6748       block_start = data + 2;
6749       data = display_block (block_start, uvalue);
6750       break;
6751
6752     case DW_FORM_block4:
6753       uvalue = byte_get (data, 4);
6754       block_start = data + 4;
6755       data = display_block (block_start, uvalue);
6756       break;
6757
6758     case DW_FORM_strp:
6759     case DW_FORM_indirect:
6760       warn (_("Unable to handle FORM: %d"), form);
6761       break;
6762
6763     default:
6764       warn (_("Unrecognised form: %d"), form);
6765       break;
6766     }
6767
6768   /* For some attributes we can display futher information.  */
6769
6770   printf ("\t");
6771
6772   switch (attribute)
6773     {
6774     case DW_AT_inline:
6775       switch (uvalue)
6776         {
6777         case DW_INL_not_inlined:          printf (_("(not inlined)")); break;
6778         case DW_INL_inlined:              printf (_("(inlined)")); break;
6779         case DW_INL_declared_not_inlined: printf (_("(declared as inline but ignored)")); break;
6780         case DW_INL_declared_inlined:     printf (_("(declared as inline and inlined)")); break;
6781         default: printf (_("  (Unknown inline attribute value: %lx)"), uvalue); break;
6782         }
6783       break;
6784
6785     case DW_AT_language:
6786       switch (uvalue)
6787         {
6788         case DW_LANG_C:              printf ("(non-ANSI C)"); break;
6789         case DW_LANG_C89:            printf ("(ANSI C)"); break;
6790         case DW_LANG_C_plus_plus:    printf ("(C++)"); break;
6791         case DW_LANG_Fortran77:      printf ("(FORTRAN 77)"); break;
6792         case DW_LANG_Fortran90:      printf ("(Fortran 90)"); break;
6793         case DW_LANG_Modula2:        printf ("(Modula 2)"); break;
6794         case DW_LANG_Pascal83:       printf ("(ANSI Pascal)"); break;
6795         case DW_LANG_Ada83:          printf ("(Ada)"); break;
6796         case DW_LANG_Cobol74:        printf ("(Cobol 74)"); break;
6797         case DW_LANG_Cobol85:        printf ("(Cobol 85)"); break;
6798         case DW_LANG_Mips_Assembler: printf ("(MIPS assembler)"); break;
6799         default:                     printf ("(Unknown: %lx)", uvalue); break;
6800         }
6801       break;
6802
6803     case DW_AT_encoding:
6804       switch (uvalue)
6805         {
6806         case DW_ATE_void:            printf ("(void)"); break;
6807         case DW_ATE_address:         printf ("(machine address)"); break;
6808         case DW_ATE_boolean:         printf ("(boolean)"); break;
6809         case DW_ATE_complex_float:   printf ("(complex float)"); break;
6810         case DW_ATE_float:           printf ("(float)"); break;
6811         case DW_ATE_signed:          printf ("(signed)"); break;
6812         case DW_ATE_signed_char:     printf ("(signed char)"); break;
6813         case DW_ATE_unsigned:        printf ("(unsigned)"); break;
6814         case DW_ATE_unsigned_char:   printf ("(unsigned char)"); break;
6815         default:
6816           if (uvalue >= DW_ATE_lo_user
6817               && uvalue <= DW_ATE_hi_user)
6818             printf ("(user defined type)");
6819           else
6820             printf ("(unknown type)");
6821           break;
6822         }
6823       break;
6824
6825     case DW_AT_accessibility:
6826       switch (uvalue)
6827         {
6828         case DW_ACCESS_public:          printf ("(public)"); break;
6829         case DW_ACCESS_protected:       printf ("(protected)"); break;
6830         case DW_ACCESS_private:         printf ("(private)"); break;
6831         default:                        printf ("(unknown accessibility)"); break;
6832         }
6833       break;
6834
6835     case DW_AT_visibility:
6836       switch (uvalue)
6837         {
6838         case DW_VIS_local:      printf ("(local)"); break;
6839         case DW_VIS_exported:   printf ("(exported)"); break;
6840         case DW_VIS_qualified:  printf ("(qualified)"); break;
6841         default:                printf ("(unknown visibility)"); break;
6842         }
6843       break;
6844
6845     case DW_AT_virtuality:
6846       switch (uvalue)
6847         {
6848         case DW_VIRTUALITY_none:        printf ("(none)"); break;
6849         case DW_VIRTUALITY_virtual:     printf ("(virtual)"); break;
6850         case DW_VIRTUALITY_pure_virtual:printf ("(pure_virtual)"); break;
6851         default:                        printf ("(unknown virtuality)"); break;
6852         }
6853       break;
6854
6855     case DW_AT_identifier_case:
6856       switch (uvalue)
6857         {
6858         case DW_ID_case_sensitive:      printf ("(case_sensitive)"); break;
6859         case DW_ID_up_case:             printf ("(up_case)"); break;
6860         case DW_ID_down_case:           printf ("(down_case)"); break;
6861         case DW_ID_case_insensitive:    printf ("(case_insensitive)"); break;
6862         default:                        printf ("(unknown case)"); break;
6863         }
6864       break;
6865
6866     case DW_AT_calling_convention:
6867       switch (uvalue)
6868         {
6869         case DW_CC_normal:      printf ("(normal)"); break;
6870         case DW_CC_program:     printf ("(program)"); break;
6871         case DW_CC_nocall:      printf ("(nocall)"); break;
6872         default:
6873           if (uvalue >= DW_CC_lo_user
6874               && uvalue <= DW_CC_hi_user)
6875             printf ("(user defined)");
6876           else
6877             printf ("(unknown convention)");
6878         }
6879       break;
6880
6881     case DW_AT_ordering:
6882       switch (uvalue)
6883         {
6884         case -1: printf ("(undefined)"); break;
6885         case 0:  printf ("(row major)"); break;
6886         case 1:  printf ("(column major)"); break;
6887         }
6888       break;
6889
6890     case DW_AT_frame_base:
6891     case DW_AT_location:
6892     case DW_AT_data_member_location:
6893     case DW_AT_vtable_elem_location:
6894     case DW_AT_allocated:
6895     case DW_AT_associated:
6896     case DW_AT_data_location:
6897     case DW_AT_stride:
6898     case DW_AT_upper_bound:
6899     case DW_AT_lower_bound:
6900       if (block_start)
6901         {
6902           printf ("(");
6903           decode_location_expression (block_start, pointer_size, uvalue);
6904           printf (")");
6905         }
6906       break;
6907
6908     default:
6909       break;
6910     }
6911
6912   printf ("\n");
6913   return data;
6914 }
6915
6916 static int
6917 display_debug_info (section, start, file)
6918      Elf32_Internal_Shdr * section;
6919      unsigned char *       start;
6920      FILE *                file;
6921 {
6922   unsigned char * end = start + section->sh_size;
6923   unsigned char * section_begin = start;
6924
6925   printf (_("The section %s contains:\n\n"), SECTION_NAME (section));
6926
6927   while (start < end)
6928     {
6929       DWARF2_External_CompUnit * external;
6930       DWARF2_Internal_CompUnit   compunit;
6931       unsigned char *            tags;
6932       int                        i;
6933       int                        level;
6934       unsigned long              cu_offset;
6935
6936       external = (DWARF2_External_CompUnit *) start;
6937
6938       compunit.cu_length        = BYTE_GET (external->cu_length);
6939       compunit.cu_version       = BYTE_GET (external->cu_version);
6940       compunit.cu_abbrev_offset = BYTE_GET (external->cu_abbrev_offset);
6941       compunit.cu_pointer_size  = BYTE_GET (external->cu_pointer_size);
6942
6943       tags = start + sizeof (* external);
6944       cu_offset = start - section_begin;
6945       start += compunit.cu_length + sizeof (external->cu_length);
6946
6947       printf (_("  Compilation Unit @ %lx:\n"), cu_offset);
6948       printf (_("   Length:        %ld\n"), compunit.cu_length);
6949       printf (_("   Version:       %d\n"), compunit.cu_version);
6950       printf (_("   Abbrev Offset: %ld\n"), compunit.cu_abbrev_offset);
6951       printf (_("   Pointer Size:  %d\n"), compunit.cu_pointer_size);
6952
6953       if (compunit.cu_version != 2)
6954         {
6955           warn (_("Only version 2 DWARF debug information is currently supported.\n"));
6956           continue;
6957         }
6958
6959       if (first_abbrev != NULL)
6960         free_abbrevs ();
6961
6962       /* Read in the abbrevs used by this compilation unit.  */
6963
6964       {
6965         Elf32_Internal_Shdr * sec;
6966         unsigned char *       begin;
6967
6968         /* Locate the .debug_abbrev section and process it.  */
6969         for (i = 0, sec = section_headers;
6970              i < elf_header.e_shnum;
6971              i ++, sec ++)
6972           if (strcmp (SECTION_NAME (sec), ".debug_abbrev") == 0)
6973             break;
6974
6975         if (i == -1 || sec->sh_size == 0)
6976           {
6977             warn (_("Unable to locate .debug_abbrev section!\n"));
6978             return 0;
6979           }
6980
6981         begin = ((unsigned char *)
6982                  get_data (NULL, file, sec->sh_offset, sec->sh_size, 
6983                            _("debug_abbrev section data")));
6984         if (!begin)
6985           return 0;
6986
6987         process_abbrev_section (begin + compunit.cu_abbrev_offset,
6988                                 begin + sec->sh_size);
6989
6990         free (begin);
6991       }
6992
6993       level = 0;
6994       while (tags < start)
6995         {
6996           int            bytes_read;
6997           unsigned long  abbrev_number;
6998           abbrev_entry * entry;
6999           abbrev_attr  * attr;
7000
7001           abbrev_number = read_leb128 (tags, & bytes_read, 0);
7002           tags += bytes_read;
7003
7004           /* A null DIE marks the end of a list of children.  */
7005           if (abbrev_number == 0)
7006             {
7007               --level;
7008               continue;
7009             }
7010
7011           /* Scan through the abbreviation list until we reach the
7012              correct entry.  */
7013           for (entry = first_abbrev;
7014                entry && entry->entry != abbrev_number;
7015                entry = entry->next)
7016             continue;
7017
7018           if (entry == NULL)
7019             {
7020               warn (_("Unable to locate entry %lu in the abbreviation table\n"),
7021                     abbrev_number);
7022               return 0;
7023             }
7024
7025           printf (_(" <%d><%x>: Abbrev Number: %lu (%s)\n"),
7026                   level, tags - section_begin - bytes_read,
7027                   abbrev_number,
7028                   get_TAG_name (entry->tag));
7029
7030           for (attr = entry->first_attr; attr; attr = attr->next)
7031             tags = read_and_display_attr (attr->attribute,
7032                                           attr->form,
7033                                           tags, cu_offset,
7034                                           compunit.cu_pointer_size);
7035
7036           if (entry->children)
7037             ++level;
7038         }
7039     }
7040
7041   printf ("\n");
7042
7043   return 1;
7044 }
7045
7046 static int
7047 display_debug_aranges (section, start, file)
7048      Elf32_Internal_Shdr * section;
7049      unsigned char *       start;
7050      FILE *                file ATTRIBUTE_UNUSED;
7051 {
7052   unsigned char * end = start + section->sh_size;
7053
7054   printf (_("The section %s contains:\n\n"), SECTION_NAME (section));
7055
7056   while (start < end)
7057     {
7058       DWARF2_External_ARange * external;
7059       DWARF2_Internal_ARange   arange;
7060       unsigned char *          ranges;
7061       unsigned long            length;
7062       unsigned long            address;
7063       int                      excess;
7064
7065       external = (DWARF2_External_ARange *) start;
7066
7067       arange.ar_length       = BYTE_GET (external->ar_length);
7068       arange.ar_version      = BYTE_GET (external->ar_version);
7069       arange.ar_info_offset  = BYTE_GET (external->ar_info_offset);
7070       arange.ar_pointer_size = BYTE_GET (external->ar_pointer_size);
7071       arange.ar_segment_size = BYTE_GET (external->ar_segment_size);
7072
7073       if (arange.ar_version != 2)
7074         {
7075           warn (_("Only DWARF 2 aranges are currently supported.\n"));
7076           break;
7077         }
7078
7079       printf (_("  Length:                   %ld\n"), arange.ar_length);
7080       printf (_("  Version:                  %d\n"), arange.ar_version);
7081       printf (_("  Offset into .debug_info:  %lx\n"), arange.ar_info_offset);
7082       printf (_("  Pointer Size:             %d\n"), arange.ar_pointer_size);
7083       printf (_("  Segment Size:             %d\n"), arange.ar_segment_size);
7084
7085       printf (_("\n    Address  Length\n"));
7086
7087       ranges = start + sizeof (* external);
7088
7089       /* Must pad to an alignment boundary that is twice the pointer size.  */
7090       excess = sizeof (* external) % (2 * arange.ar_pointer_size);
7091       if (excess)
7092         ranges += (2 * arange.ar_pointer_size) - excess;
7093
7094       for (;;)
7095         {
7096           address = byte_get (ranges, arange.ar_pointer_size);
7097
7098           ranges += arange.ar_pointer_size;
7099
7100           length  = byte_get (ranges, arange.ar_pointer_size);
7101
7102           ranges += arange.ar_pointer_size;
7103
7104           /* A pair of zeros marks the end of the list.  */
7105           if (address == 0 && length == 0)
7106             break;
7107
7108           printf ("    %8.8lx %lu\n", address, length);
7109         }
7110
7111       start += arange.ar_length + sizeof (external->ar_length);
7112     }
7113
7114   printf ("\n");
7115
7116   return 1;
7117 }
7118
7119 typedef struct Frame_Chunk
7120 {
7121   struct Frame_Chunk * next;
7122   unsigned char *      chunk_start;
7123   int                  ncols;
7124   /* DW_CFA_{undefined,same_value,offset,register,unreferenced}  */
7125   short int *          col_type;
7126   int *                col_offset;
7127   char *               augmentation;
7128   unsigned int         code_factor;
7129   int                  data_factor;
7130   unsigned long        pc_begin;
7131   unsigned long        pc_range;
7132   int                  cfa_reg;
7133   int                  cfa_offset;
7134   int                  ra;
7135   unsigned char        fde_encoding;
7136 }
7137 Frame_Chunk;
7138
7139 /* A marker for a col_type that means this column was never referenced
7140    in the frame info.  */
7141 #define DW_CFA_unreferenced (-1)
7142
7143 static void
7144 frame_need_space (fc, reg)
7145      Frame_Chunk * fc;
7146      int reg;
7147 {
7148   int prev = fc->ncols;
7149
7150   if (reg < fc->ncols)
7151     return;
7152
7153   fc->ncols = reg + 1;
7154   fc->col_type = (short int *) xrealloc (fc->col_type,
7155                                          fc->ncols * sizeof (short int));
7156   fc->col_offset = (int *) xrealloc (fc->col_offset,
7157                                      fc->ncols * sizeof (int));
7158
7159   while (prev < fc->ncols)
7160     {
7161       fc->col_type[prev] = DW_CFA_unreferenced;
7162       fc->col_offset[prev] = 0;
7163       prev++;
7164     }
7165 }
7166
7167 static void
7168 frame_display_row (fc, need_col_headers, max_regs)
7169      Frame_Chunk * fc;
7170      int *         need_col_headers;
7171      int *         max_regs;
7172 {
7173   int r;
7174   char tmp[100];
7175
7176   if (* max_regs < fc->ncols)
7177     * max_regs = fc->ncols;
7178
7179   if (* need_col_headers)
7180     {
7181       * need_col_headers = 0;
7182
7183       printf ("   LOC   CFA      ");
7184
7185       for (r = 0; r < * max_regs; r++)
7186         if (fc->col_type[r] != DW_CFA_unreferenced)
7187           {
7188             if (r == fc->ra)
7189               printf ("ra   ");
7190             else
7191               printf ("r%-4d", r);
7192           }
7193
7194       printf ("\n");
7195     }
7196
7197   printf ("%08lx ", fc->pc_begin);
7198   sprintf (tmp, "r%d%+d", fc->cfa_reg, fc->cfa_offset);
7199   printf ("%-8s ", tmp);
7200
7201   for (r = 0; r < fc->ncols; r++)
7202     {
7203       if (fc->col_type[r] != DW_CFA_unreferenced)
7204         {
7205           switch (fc->col_type[r])
7206             {
7207             case DW_CFA_undefined:
7208               strcpy (tmp, "u");
7209               break;
7210             case DW_CFA_same_value:
7211               strcpy (tmp, "s");
7212               break;
7213             case DW_CFA_offset:
7214               sprintf (tmp, "c%+d", fc->col_offset[r]);
7215               break;
7216             case DW_CFA_register:
7217               sprintf (tmp, "r%d", fc->col_offset[r]);
7218               break;
7219             default:
7220               strcpy (tmp, "n/a");
7221               break;
7222             }
7223           printf ("%-5s", tmp);
7224         }
7225     }
7226   printf ("\n");
7227 }
7228
7229 static int
7230 size_of_encoded_value (encoding)
7231      int encoding;
7232 {
7233   switch (encoding & 0x7)
7234     {
7235     default:    /* ??? */
7236     case 0:     return is_32bit_elf ? 4 : 8;
7237     case 2:     return 2;
7238     case 3:     return 4;
7239     case 4:     return 8;
7240     }
7241 }
7242
7243 #define GET(N)  byte_get (start, N); start += N
7244 #define LEB()   read_leb128 (start, & length_return, 0); start += length_return
7245 #define SLEB()  read_leb128 (start, & length_return, 1); start += length_return
7246
7247 static int
7248 display_debug_frames (section, start, file)
7249      Elf32_Internal_Shdr * section;
7250      unsigned char *       start;
7251      FILE *                file ATTRIBUTE_UNUSED;
7252 {
7253   unsigned char * end = start + section->sh_size;
7254   unsigned char * section_start = start;
7255   Frame_Chunk *   chunks = 0;
7256   Frame_Chunk *   remembered_state = 0;
7257   Frame_Chunk *   rs;
7258   int             is_eh = (strcmp (SECTION_NAME (section), ".eh_frame") == 0);
7259   int             length_return;
7260   int             max_regs = 0;
7261   int             addr_size = is_32bit_elf ? 4 : 8;
7262
7263   printf (_("The section %s contains:\n"), SECTION_NAME (section));
7264
7265   while (start < end)
7266     {
7267       unsigned char * saved_start;
7268       unsigned char * block_end;
7269       unsigned long   length;
7270       unsigned long   cie_id;
7271       Frame_Chunk *   fc;
7272       Frame_Chunk *   cie;
7273       int             need_col_headers = 1;
7274       unsigned char * augmentation_data = NULL;
7275       unsigned long   augmentation_data_len = 0;
7276       int             encoded_ptr_size = addr_size;
7277
7278       saved_start = start;
7279       length = byte_get (start, 4); start += 4;
7280
7281       if (length == 0)
7282         return 1;
7283
7284       block_end = saved_start + length + 4;
7285       cie_id = byte_get (start, 4); start += 4;
7286
7287       if (is_eh ? (cie_id == 0) : (cie_id == DW_CIE_ID))
7288         {
7289           int version;
7290
7291           fc = (Frame_Chunk *) xmalloc (sizeof (Frame_Chunk));
7292           memset (fc, 0, sizeof (Frame_Chunk));
7293
7294           fc->next = chunks;
7295           chunks = fc;
7296           fc->chunk_start = saved_start;
7297           fc->ncols = 0;
7298           fc->col_type = (short int *) xmalloc (sizeof (short int));
7299           fc->col_offset = (int *) xmalloc (sizeof (int));
7300           frame_need_space (fc, max_regs-1);
7301
7302           version = *start++;
7303
7304           fc->augmentation = start;
7305           start = strchr (start, '\0') + 1;
7306
7307           if (fc->augmentation[0] == 'z')
7308             {
7309               fc->code_factor = LEB ();
7310               fc->data_factor = SLEB ();
7311               fc->ra = byte_get (start, 1); start += 1;
7312               augmentation_data_len = LEB ();
7313               augmentation_data = start;
7314               start += augmentation_data_len;
7315             }
7316           else if (strcmp (fc->augmentation, "eh") == 0)
7317             {
7318               start += addr_size;
7319               fc->code_factor = LEB ();
7320               fc->data_factor = SLEB ();
7321               fc->ra = byte_get (start, 1); start += 1;
7322             }
7323           else
7324             {
7325               fc->code_factor = LEB ();
7326               fc->data_factor = SLEB ();
7327               fc->ra = byte_get (start, 1); start += 1;
7328             }
7329           cie = fc;
7330
7331           if (do_debug_frames_interp)
7332             printf ("\n%08lx %08lx %08lx CIE \"%s\" cf=%d df=%d ra=%d\n",
7333                     (unsigned long)(saved_start - section_start), length, cie_id,
7334                     fc->augmentation, fc->code_factor, fc->data_factor,
7335                     fc->ra);
7336           else
7337             {
7338               printf ("\n%08lx %08lx %08lx CIE\n",
7339                       (unsigned long)(saved_start - section_start), length, cie_id);
7340               printf ("  Version:               %d\n", version);
7341               printf ("  Augmentation:          \"%s\"\n", fc->augmentation);
7342               printf ("  Code alignment factor: %u\n", fc->code_factor);
7343               printf ("  Data alignment factor: %d\n", fc->data_factor);
7344               printf ("  Return address column: %d\n", fc->ra);
7345
7346               if (augmentation_data_len)
7347                 {
7348                   unsigned long i;
7349                   printf ("  Augmentation data:    ");
7350                   for (i = 0; i < augmentation_data_len; ++i)
7351                     printf (" %02x", augmentation_data[i]);
7352                   putchar ('\n');
7353                 }
7354               putchar ('\n');
7355             }
7356
7357           if (augmentation_data_len)
7358             {
7359               unsigned char *p, *q;
7360               p = fc->augmentation + 1;
7361               q = augmentation_data;
7362
7363               while (1)
7364                 {
7365                   if (*p == 'L')
7366                     q++;
7367                   else if (*p == 'P')
7368                     q += 1 + size_of_encoded_value (*q);
7369                   else if (*p == 'R')
7370                     fc->fde_encoding = *q++;
7371                   else
7372                     break;
7373                   p++;
7374                 }
7375
7376               if (fc->fde_encoding)
7377                 encoded_ptr_size = size_of_encoded_value (fc->fde_encoding);
7378             }
7379
7380           frame_need_space (fc, fc->ra);
7381         }
7382       else
7383         {
7384           unsigned char *    look_for;
7385           static Frame_Chunk fde_fc;
7386
7387           fc = & fde_fc;
7388           memset (fc, 0, sizeof (Frame_Chunk));
7389
7390           look_for = is_eh ? start - 4 - cie_id : section_start + cie_id;
7391
7392           for (cie=chunks; cie ; cie = cie->next)
7393             if (cie->chunk_start == look_for)
7394               break;
7395
7396           if (!cie)
7397             {
7398               warn ("Invalid CIE pointer %08lx in FDE at %08lx\n",
7399                     cie_id, saved_start);
7400               start = block_end;
7401               fc->ncols = 0;
7402               fc->col_type = (short int *) xmalloc (sizeof (short int));
7403               fc->col_offset = (int *) xmalloc (sizeof (int));
7404               frame_need_space (fc, max_regs - 1);
7405               cie = fc;
7406               fc->augmentation = "";
7407               fc->fde_encoding = 0;
7408             }
7409           else
7410             {
7411               fc->ncols = cie->ncols;
7412               fc->col_type = (short int *) xmalloc (fc->ncols * sizeof (short int));
7413               fc->col_offset = (int *) xmalloc (fc->ncols * sizeof (int));
7414               memcpy (fc->col_type, cie->col_type, fc->ncols * sizeof (short int));
7415               memcpy (fc->col_offset, cie->col_offset, fc->ncols * sizeof (int));
7416               fc->augmentation = cie->augmentation;
7417               fc->code_factor = cie->code_factor;
7418               fc->data_factor = cie->data_factor;
7419               fc->cfa_reg = cie->cfa_reg;
7420               fc->cfa_offset = cie->cfa_offset;
7421               fc->ra = cie->ra;
7422               frame_need_space (fc, max_regs-1);
7423               fc->fde_encoding = cie->fde_encoding;
7424             }
7425
7426           if (fc->fde_encoding)
7427             encoded_ptr_size = size_of_encoded_value (fc->fde_encoding);
7428
7429           fc->pc_begin = byte_get (start, encoded_ptr_size);
7430           start += encoded_ptr_size;
7431           fc->pc_range = byte_get (start, encoded_ptr_size);
7432           start += encoded_ptr_size;
7433
7434           if (cie->augmentation[0] == 'z')
7435             {
7436               augmentation_data_len = LEB ();
7437               augmentation_data = start;
7438               start += augmentation_data_len;
7439             }
7440
7441           printf ("\n%08lx %08lx %08lx FDE cie=%08x pc=%08lx..%08lx\n",
7442                   (unsigned long)(saved_start - section_start), length, cie_id,
7443                   cie->chunk_start - section_start, fc->pc_begin,
7444                   fc->pc_begin + fc->pc_range);
7445           if (! do_debug_frames_interp && augmentation_data_len)
7446             {
7447               unsigned long i;
7448               printf ("  Augmentation data:    ");
7449               for (i = 0; i < augmentation_data_len; ++i)
7450                 printf (" %02x", augmentation_data[i]);
7451               putchar ('\n');
7452               putchar ('\n');
7453             }
7454         }
7455
7456       /* At this point, fc is the current chunk, cie (if any) is set, and we're
7457          about to interpret instructions for the chunk.  */
7458
7459       if (do_debug_frames_interp)
7460       {
7461         /* Start by making a pass over the chunk, allocating storage
7462            and taking note of what registers are used.  */
7463         unsigned char * tmp = start;
7464
7465         while (start < block_end)
7466           {
7467             unsigned op, opa;
7468             unsigned long reg;
7469
7470             op = * start ++;
7471             opa = op & 0x3f;
7472             if (op & 0xc0)
7473               op &= 0xc0;
7474
7475             /* Warning: if you add any more cases to this switch, be
7476                sure to add them to the corresponding switch below.  */
7477             switch (op)
7478               {
7479               case DW_CFA_advance_loc:
7480                 break;
7481               case DW_CFA_offset:
7482                 LEB ();
7483                 frame_need_space (fc, opa);
7484                 fc->col_type[opa] = DW_CFA_undefined;
7485                 break;
7486               case DW_CFA_restore:
7487                 frame_need_space (fc, opa);
7488                 fc->col_type[opa] = DW_CFA_undefined;
7489                 break;
7490               case DW_CFA_set_loc:
7491                 start += encoded_ptr_size;
7492                 break;
7493               case DW_CFA_advance_loc1:
7494                 start += 1;
7495                 break;
7496               case DW_CFA_advance_loc2:
7497                 start += 2;
7498                 break;
7499               case DW_CFA_advance_loc4:
7500                 start += 4;
7501                 break;
7502               case DW_CFA_offset_extended:
7503                 reg = LEB (); LEB ();
7504                 frame_need_space (fc, reg);
7505                 fc->col_type[reg] = DW_CFA_undefined;
7506                 break;
7507               case DW_CFA_restore_extended:
7508                 reg = LEB ();
7509                 frame_need_space (fc, reg);
7510                 fc->col_type[reg] = DW_CFA_undefined;
7511                 break;
7512               case DW_CFA_undefined:
7513                 reg = LEB ();
7514                 frame_need_space (fc, reg);
7515                 fc->col_type[reg] = DW_CFA_undefined;
7516                 break;
7517               case DW_CFA_same_value:
7518                 reg = LEB ();
7519                 frame_need_space (fc, reg);
7520                 fc->col_type[reg] = DW_CFA_undefined;
7521                 break;
7522               case DW_CFA_register:
7523                 reg = LEB (); LEB ();
7524                 frame_need_space (fc, reg);
7525                 fc->col_type[reg] = DW_CFA_undefined;
7526                 break;
7527               case DW_CFA_def_cfa:
7528                 LEB (); LEB ();
7529                 break;
7530               case DW_CFA_def_cfa_register:
7531                 LEB ();
7532                 break;
7533               case DW_CFA_def_cfa_offset:
7534                 LEB ();
7535                 break;
7536 #ifndef DW_CFA_GNU_args_size
7537 #define DW_CFA_GNU_args_size 0x2e
7538 #endif
7539               case DW_CFA_GNU_args_size:
7540                 LEB ();
7541                 break;
7542 #ifndef DW_CFA_GNU_negative_offset_extended
7543 #define DW_CFA_GNU_negative_offset_extended 0x2f
7544 #endif
7545               case DW_CFA_GNU_negative_offset_extended:
7546                 reg = LEB (); LEB ();
7547                 frame_need_space (fc, reg);
7548                 fc->col_type[reg] = DW_CFA_undefined;
7549
7550               default:
7551                 break;
7552               }
7553           }
7554         start = tmp;
7555       }
7556
7557       /* Now we know what registers are used, make a second pass over
7558          the chunk, this time actually printing out the info.  */
7559
7560       while (start < block_end)
7561         {
7562           unsigned op, opa;
7563           unsigned long ul, reg, roffs;
7564           long l, ofs;
7565           bfd_vma vma;
7566
7567           op = * start ++;
7568           opa = op & 0x3f;
7569           if (op & 0xc0)
7570             op &= 0xc0;
7571
7572             /* Warning: if you add any more cases to this switch, be
7573                sure to add them to the corresponding switch above.  */
7574           switch (op)
7575             {
7576             case DW_CFA_advance_loc:
7577               if (do_debug_frames_interp)
7578                 frame_display_row (fc, &need_col_headers, &max_regs);
7579               else
7580                 printf ("  DW_CFA_advance_loc: %d to %08lx\n",
7581                         opa * fc->code_factor,
7582                         fc->pc_begin + opa * fc->code_factor);
7583               fc->pc_begin += opa * fc->code_factor;
7584               break;
7585
7586             case DW_CFA_offset:
7587               roffs = LEB ();
7588               if (! do_debug_frames_interp)
7589                 printf ("  DW_CFA_offset: r%d at cfa%+ld\n",
7590                         opa, roffs * fc->data_factor);
7591               fc->col_type[opa] = DW_CFA_offset;
7592               fc->col_offset[opa] = roffs * fc->data_factor;
7593               break;
7594
7595             case DW_CFA_restore:
7596               if (! do_debug_frames_interp)
7597                 printf ("  DW_CFA_restore: r%d\n", opa);
7598               fc->col_type[opa] = cie->col_type[opa];
7599               fc->col_offset[opa] = cie->col_offset[opa];
7600               break;
7601
7602             case DW_CFA_set_loc:
7603               vma = byte_get (start, encoded_ptr_size);
7604               start += encoded_ptr_size;
7605               if (do_debug_frames_interp)
7606                 frame_display_row (fc, &need_col_headers, &max_regs);
7607               else
7608                 printf ("  DW_CFA_set_loc: %08lx\n", (unsigned long)vma);
7609               fc->pc_begin = vma;
7610               break;
7611
7612             case DW_CFA_advance_loc1:
7613               ofs = byte_get (start, 1); start += 1;
7614               if (do_debug_frames_interp)
7615                 frame_display_row (fc, &need_col_headers, &max_regs);
7616               else
7617                 printf ("  DW_CFA_advance_loc1: %ld to %08lx\n",
7618                         ofs * fc->code_factor,
7619                         fc->pc_begin + ofs * fc->code_factor);
7620               fc->pc_begin += ofs * fc->code_factor;
7621               break;
7622
7623             case DW_CFA_advance_loc2:
7624               ofs = byte_get (start, 2); start += 2;
7625               if (do_debug_frames_interp)
7626                 frame_display_row (fc, &need_col_headers, &max_regs);
7627               else
7628                 printf ("  DW_CFA_advance_loc2: %ld to %08lx\n",
7629                         ofs * fc->code_factor,
7630                         fc->pc_begin + ofs * fc->code_factor);
7631               fc->pc_begin += ofs * fc->code_factor;
7632               break;
7633
7634             case DW_CFA_advance_loc4:
7635               ofs = byte_get (start, 4); start += 4;
7636               if (do_debug_frames_interp)
7637                 frame_display_row (fc, &need_col_headers, &max_regs);
7638               else
7639                 printf ("  DW_CFA_advance_loc4: %ld to %08lx\n",
7640                         ofs * fc->code_factor,
7641                         fc->pc_begin + ofs * fc->code_factor);
7642               fc->pc_begin += ofs * fc->code_factor;
7643               break;
7644
7645             case DW_CFA_offset_extended:
7646               reg = LEB ();
7647               roffs = LEB ();
7648               if (! do_debug_frames_interp)
7649                 printf ("  DW_CFA_offset_extended: r%ld at cfa%+ld\n",
7650                         reg, roffs * fc->data_factor);
7651               fc->col_type[reg] = DW_CFA_offset;
7652               fc->col_offset[reg] = roffs * fc->data_factor;
7653               break;
7654
7655             case DW_CFA_restore_extended:
7656               reg = LEB ();
7657               if (! do_debug_frames_interp)
7658                 printf ("  DW_CFA_restore_extended: r%ld\n", reg);
7659               fc->col_type[reg] = cie->col_type[reg];
7660               fc->col_offset[reg] = cie->col_offset[reg];
7661               break;
7662
7663             case DW_CFA_undefined:
7664               reg = LEB ();
7665               if (! do_debug_frames_interp)
7666                 printf ("  DW_CFA_undefined: r%ld\n", reg);
7667               fc->col_type[reg] = DW_CFA_undefined;
7668               fc->col_offset[reg] = 0;
7669               break;
7670
7671             case DW_CFA_same_value:
7672               reg = LEB ();
7673               if (! do_debug_frames_interp)
7674                 printf ("  DW_CFA_same_value: r%ld\n", reg);
7675               fc->col_type[reg] = DW_CFA_same_value;
7676               fc->col_offset[reg] = 0;
7677               break;
7678
7679             case DW_CFA_register:
7680               reg = LEB ();
7681               roffs = LEB ();
7682               if (! do_debug_frames_interp)
7683                 printf ("  DW_CFA_register: r%ld\n", reg);
7684               fc->col_type[reg] = DW_CFA_register;
7685               fc->col_offset[reg] = roffs;
7686               break;
7687
7688             case DW_CFA_remember_state:
7689               if (! do_debug_frames_interp)
7690                 printf ("  DW_CFA_remember_state\n");
7691               rs = (Frame_Chunk *) xmalloc (sizeof (Frame_Chunk));
7692               rs->ncols = fc->ncols;
7693               rs->col_type = (short int *) xmalloc (rs->ncols * sizeof (short int));
7694               rs->col_offset = (int *) xmalloc (rs->ncols * sizeof (int));
7695               memcpy (rs->col_type, fc->col_type, rs->ncols);
7696               memcpy (rs->col_offset, fc->col_offset, rs->ncols * sizeof (int));
7697               rs->next = remembered_state;
7698               remembered_state = rs;
7699               break;
7700
7701             case DW_CFA_restore_state:
7702               if (! do_debug_frames_interp)
7703                 printf ("  DW_CFA_restore_state\n");
7704               rs = remembered_state;
7705               remembered_state = rs->next;
7706               frame_need_space (fc, rs->ncols-1);
7707               memcpy (fc->col_type, rs->col_type, rs->ncols);
7708               memcpy (fc->col_offset, rs->col_offset, rs->ncols * sizeof (int));
7709               free (rs->col_type);
7710               free (rs->col_offset);
7711               free (rs);
7712               break;
7713
7714             case DW_CFA_def_cfa:
7715               fc->cfa_reg = LEB ();
7716               fc->cfa_offset = LEB ();
7717               if (! do_debug_frames_interp)
7718                 printf ("  DW_CFA_def_cfa: r%d ofs %d\n",
7719                         fc->cfa_reg, fc->cfa_offset);
7720               break;
7721
7722             case DW_CFA_def_cfa_register:
7723               fc->cfa_reg = LEB ();
7724               if (! do_debug_frames_interp)
7725                 printf ("  DW_CFA_def_cfa_reg: r%d\n", fc->cfa_reg);
7726               break;
7727
7728             case DW_CFA_def_cfa_offset:
7729               fc->cfa_offset = LEB ();
7730               if (! do_debug_frames_interp)
7731                 printf ("  DW_CFA_def_cfa_offset: %d\n", fc->cfa_offset);
7732               break;
7733
7734             case DW_CFA_nop:
7735               if (! do_debug_frames_interp)
7736                 printf ("  DW_CFA_nop\n");
7737               break;
7738
7739 #ifndef DW_CFA_GNU_window_save
7740 #define DW_CFA_GNU_window_save 0x2d
7741 #endif
7742             case DW_CFA_GNU_window_save:
7743               if (! do_debug_frames_interp)
7744                 printf ("  DW_CFA_GNU_window_save\n");
7745               break;
7746
7747             case DW_CFA_GNU_args_size:
7748               ul = LEB ();
7749               if (! do_debug_frames_interp)
7750                 printf ("  DW_CFA_GNU_args_size: %ld\n", ul);
7751               break;
7752
7753             case DW_CFA_GNU_negative_offset_extended:
7754               reg = LEB ();
7755               l = - LEB ();
7756               frame_need_space (fc, reg);
7757               if (! do_debug_frames_interp)
7758                 printf ("  DW_CFA_GNU_negative_offset_extended: r%ld at cfa%+ld\n",
7759                         reg, l * fc->data_factor);
7760               fc->col_type[reg] = DW_CFA_offset;
7761               fc->col_offset[reg] = l * fc->data_factor;
7762               break;
7763
7764             default:
7765               fprintf (stderr, "unsupported or unknown DW_CFA_%d\n", op);
7766               start = block_end;
7767             }
7768         }
7769
7770       if (do_debug_frames_interp)
7771         frame_display_row (fc, &need_col_headers, &max_regs);
7772
7773       start = block_end;
7774     }
7775
7776   printf ("\n");
7777
7778   return 1;
7779 }
7780
7781 #undef GET
7782 #undef LEB
7783 #undef SLEB
7784
7785 static int
7786 display_debug_not_supported (section, start, file)
7787      Elf32_Internal_Shdr * section;
7788      unsigned char *       start ATTRIBUTE_UNUSED;
7789      FILE *                file ATTRIBUTE_UNUSED;
7790 {
7791   printf (_("Displaying the debug contents of section %s is not yet supported.\n"),
7792             SECTION_NAME (section));
7793
7794   return 1;
7795 }
7796
7797 /* Pre-scan the .debug_info section to record the size of address.
7798    When dumping the .debug_line, we use that size information, assuming
7799    that all compilation units have the same address size.  */
7800 static int
7801 prescan_debug_info (section, start, file)
7802      Elf32_Internal_Shdr * section ATTRIBUTE_UNUSED;
7803      unsigned char *       start;
7804      FILE *                file ATTRIBUTE_UNUSED;
7805 {
7806   DWARF2_External_CompUnit * external;
7807
7808   external = (DWARF2_External_CompUnit *) start;
7809
7810   debug_line_pointer_size = BYTE_GET (external->cu_pointer_size);
7811   return 0;
7812 }
7813
7814   /* A structure containing the name of a debug section and a pointer
7815      to a function that can decode it.  The third field is a prescan
7816      function to be run over the section before displaying any of the
7817      sections.  */
7818 struct
7819 {
7820   char * name;
7821   int (* display) PARAMS ((Elf32_Internal_Shdr *, unsigned char *, FILE *));
7822   int (* prescan) PARAMS ((Elf32_Internal_Shdr *, unsigned char *, FILE *));
7823 }
7824 debug_displays[] =
7825 {
7826   { ".debug_info",        display_debug_info, prescan_debug_info },
7827   { ".debug_abbrev",      display_debug_abbrev, NULL },
7828   { ".debug_line",        display_debug_lines, NULL },
7829   { ".debug_aranges",     display_debug_aranges, NULL },
7830   { ".debug_pubnames",    display_debug_pubnames, NULL },
7831   { ".debug_frame",       display_debug_frames, NULL },
7832   { ".eh_frame",          display_debug_frames, NULL },
7833   { ".debug_macinfo",     display_debug_not_supported, NULL },
7834   { ".debug_str",         display_debug_not_supported, NULL },
7835   { ".debug_static_func", display_debug_not_supported, NULL },
7836   { ".debug_static_vars", display_debug_not_supported, NULL },
7837   { ".debug_types",       display_debug_not_supported, NULL },
7838   { ".debug_weaknames",   display_debug_not_supported, NULL }
7839 };
7840
7841 static int
7842 display_debug_section (section, file)
7843      Elf32_Internal_Shdr * section;
7844      FILE * file;
7845 {
7846   char *          name = SECTION_NAME (section);
7847   bfd_size_type   length;
7848   unsigned char * start;
7849   int             i;
7850
7851   length = section->sh_size;
7852   if (length == 0)
7853     {
7854       printf (_("\nSection '%s' has no debugging data.\n"), name);
7855       return 0;
7856     }
7857
7858   start = (unsigned char *) get_data (NULL, file, section->sh_offset, length, 
7859                                       _("debug section data"));
7860   if (!start)
7861     return 0;
7862
7863   /* See if we know how to display the contents of this section.  */
7864   if (strncmp (name, ".gnu.linkonce.wi.", 17) == 0)
7865     name = ".debug_info";
7866
7867   for (i = NUM_ELEM (debug_displays); i--;)
7868     if (strcmp (debug_displays[i].name, name) == 0)
7869       {
7870         debug_displays[i].display (section, start, file);
7871         break;
7872       }
7873
7874   if (i == -1)
7875     printf (_("Unrecognised debug section: %s\n"), name);
7876
7877   free (start);
7878
7879   /* If we loaded in the abbrev section at some point,
7880      we must release it here.  */
7881   if (first_abbrev != NULL)
7882     free_abbrevs ();
7883
7884   return 1;
7885 }
7886
7887 static int
7888 process_section_contents (file)
7889      FILE * file;
7890 {
7891   Elf32_Internal_Shdr * section;
7892   unsigned int  i;
7893
7894   if (! do_dump)
7895     return 1;
7896
7897   /* Pre-scan the debug sections to find some debug information not
7898      present in some of them.  For the .debug_line, we must find out the
7899      size of address (specified in .debug_info and .debug_aranges).  */
7900   for (i = 0, section = section_headers;
7901        i < elf_header.e_shnum && i < num_dump_sects;
7902        i ++, section ++)
7903     {
7904       char *    name = SECTION_NAME (section);
7905       int       j;
7906
7907       if (section->sh_size == 0)
7908         continue;
7909
7910       /* See if there is some pre-scan operation for this section.  */
7911       for (j = NUM_ELEM (debug_displays); j--;)
7912         if (strcmp (debug_displays[j].name, name) == 0)
7913           {
7914             if (debug_displays[j].prescan != NULL)
7915               {
7916                 bfd_size_type   length;
7917                 unsigned char * start;
7918
7919                 length = section->sh_size;
7920                 start = ((unsigned char *)
7921                          get_data (NULL, file, section->sh_offset, length, 
7922                                    _("debug section data")));
7923                 if (!start)
7924                   return 0;
7925
7926                 debug_displays[j].prescan (section, start, file);
7927                 free (start);
7928               }
7929
7930             break;
7931           }
7932     }
7933
7934   for (i = 0, section = section_headers;
7935        i < elf_header.e_shnum && i < num_dump_sects;
7936        i ++, section ++)
7937     {
7938 #ifdef SUPPORT_DISASSEMBLY
7939       if (dump_sects[i] & DISASS_DUMP)
7940         disassemble_section (section, file);
7941 #endif
7942       if (dump_sects[i] & HEX_DUMP)
7943         dump_section (section, file);
7944
7945       if (dump_sects[i] & DEBUG_DUMP)
7946         display_debug_section (section, file);
7947     }
7948
7949   if (i < num_dump_sects)
7950     warn (_("Some sections were not dumped because they do not exist!\n"));
7951
7952   return 1;
7953 }
7954
7955 static void
7956 process_mips_fpe_exception (mask)
7957      int mask;
7958 {
7959   if (mask)
7960     {
7961       int first = 1;
7962       if (mask & OEX_FPU_INEX)
7963         fputs ("INEX", stdout), first = 0;
7964       if (mask & OEX_FPU_UFLO)
7965         printf ("%sUFLO", first ? "" : "|"), first = 0;
7966       if (mask & OEX_FPU_OFLO)
7967         printf ("%sOFLO", first ? "" : "|"), first = 0;
7968       if (mask & OEX_FPU_DIV0)
7969         printf ("%sDIV0", first ? "" : "|"), first = 0;
7970       if (mask & OEX_FPU_INVAL)
7971         printf ("%sINVAL", first ? "" : "|");
7972     }
7973   else
7974     fputs ("0", stdout);
7975 }
7976
7977 static int
7978 process_mips_specific (file)
7979      FILE * file;
7980 {
7981   Elf_Internal_Dyn * entry;
7982   size_t liblist_offset = 0;
7983   size_t liblistno = 0;
7984   size_t conflictsno = 0;
7985   size_t options_offset = 0;
7986   size_t conflicts_offset = 0;
7987
7988   /* We have a lot of special sections.  Thanks SGI!  */
7989   if (dynamic_segment == NULL)
7990     /* No information available.  */
7991     return 0;
7992
7993   for (entry = dynamic_segment; entry->d_tag != DT_NULL; ++entry)
7994     switch (entry->d_tag)
7995       {
7996       case DT_MIPS_LIBLIST:
7997         liblist_offset = entry->d_un.d_val - loadaddr;
7998         break;
7999       case DT_MIPS_LIBLISTNO:
8000         liblistno = entry->d_un.d_val;
8001         break;
8002       case DT_MIPS_OPTIONS:
8003         options_offset = entry->d_un.d_val - loadaddr;
8004         break;
8005       case DT_MIPS_CONFLICT:
8006         conflicts_offset = entry->d_un.d_val - loadaddr;
8007         break;
8008       case DT_MIPS_CONFLICTNO:
8009         conflictsno = entry->d_un.d_val;
8010         break;
8011       default:
8012         break;
8013       }
8014
8015   if (liblist_offset != 0 && liblistno != 0 && do_dynamic)
8016     {
8017       Elf32_External_Lib * elib;
8018       size_t cnt;
8019
8020       elib = ((Elf32_External_Lib *)
8021               get_data (NULL, file, liblist_offset,
8022                         liblistno * sizeof (Elf32_External_Lib),
8023                         _("liblist")));
8024       if (elib)
8025         {
8026           printf ("\nSection '.liblist' contains %lu entries:\n",
8027                   (unsigned long) liblistno);
8028           fputs ("     Library              Time Stamp          Checksum   Version Flags\n",
8029                  stdout);
8030
8031           for (cnt = 0; cnt < liblistno; ++cnt)
8032             {
8033               Elf32_Lib liblist;
8034               time_t time;
8035               char timebuf[20];
8036               struct tm * tmp;
8037
8038               liblist.l_name = BYTE_GET (elib[cnt].l_name);
8039               time = BYTE_GET (elib[cnt].l_time_stamp);
8040               liblist.l_checksum = BYTE_GET (elib[cnt].l_checksum);
8041               liblist.l_version = BYTE_GET (elib[cnt].l_version);
8042               liblist.l_flags = BYTE_GET (elib[cnt].l_flags);
8043
8044               tmp = gmtime (&time);
8045               sprintf (timebuf, "%04u-%02u-%02uT%02u:%02u:%02u",
8046                        tmp->tm_year + 1900, tmp->tm_mon + 1, tmp->tm_mday,
8047                        tmp->tm_hour, tmp->tm_min, tmp->tm_sec);
8048
8049               printf ("%3lu: %-20s %s %#10lx %-7ld", (unsigned long) cnt,
8050                       dynamic_strings + liblist.l_name, timebuf,
8051                       liblist.l_checksum, liblist.l_version);
8052
8053               if (liblist.l_flags == 0)
8054                 puts (" NONE");
8055               else
8056                 {
8057                   static const struct
8058                   {
8059                     const char * name;
8060                     int bit;
8061                   }
8062                   l_flags_vals[] =
8063                   {
8064                     { " EXACT_MATCH", LL_EXACT_MATCH },
8065                     { " IGNORE_INT_VER", LL_IGNORE_INT_VER },
8066                     { " REQUIRE_MINOR", LL_REQUIRE_MINOR },
8067                     { " EXPORTS", LL_EXPORTS },
8068                     { " DELAY_LOAD", LL_DELAY_LOAD },
8069                     { " DELTA", LL_DELTA }
8070                   };
8071                   int flags = liblist.l_flags;
8072                   size_t fcnt;
8073
8074                   for (fcnt = 0;
8075                        fcnt < sizeof (l_flags_vals) / sizeof (l_flags_vals[0]);
8076                        ++fcnt)
8077                     if ((flags & l_flags_vals[fcnt].bit) != 0)
8078                       {
8079                         fputs (l_flags_vals[fcnt].name, stdout);
8080                         flags ^= l_flags_vals[fcnt].bit;
8081                       }
8082                   if (flags != 0)
8083                     printf (" %#x", (unsigned int) flags);
8084
8085                   puts ("");
8086                 }
8087             }
8088
8089           free (elib);
8090         }
8091     }
8092
8093   if (options_offset != 0)
8094     {
8095       Elf_External_Options * eopt;
8096       Elf_Internal_Shdr *    sect = section_headers;
8097       Elf_Internal_Options * iopt;
8098       Elf_Internal_Options * option;
8099       size_t offset;
8100       int cnt;
8101
8102       /* Find the section header so that we get the size.  */
8103       while (sect->sh_type != SHT_MIPS_OPTIONS)
8104         ++ sect;
8105
8106       eopt = (Elf_External_Options *) get_data (NULL, file, options_offset,
8107                                                 sect->sh_size, _("options"));
8108       if (eopt)
8109         {
8110           iopt = ((Elf_Internal_Options *)
8111                   malloc ((sect->sh_size / sizeof (eopt)) * sizeof (* iopt)));
8112           if (iopt == NULL)
8113             {
8114               error (_("Out of memory"));
8115               return 0;
8116             }
8117
8118           offset = cnt = 0;
8119           option = iopt;
8120
8121           while (offset < sect->sh_size)
8122             {
8123               Elf_External_Options * eoption;
8124
8125               eoption = (Elf_External_Options *) ((char *) eopt + offset);
8126
8127               option->kind = BYTE_GET (eoption->kind);
8128               option->size = BYTE_GET (eoption->size);
8129               option->section = BYTE_GET (eoption->section);
8130               option->info = BYTE_GET (eoption->info);
8131
8132               offset += option->size;
8133
8134               ++option;
8135               ++cnt;
8136             }
8137
8138           printf (_("\nSection '%s' contains %d entries:\n"),
8139                   SECTION_NAME (sect), cnt);
8140
8141           option = iopt;
8142
8143           while (cnt-- > 0)
8144             {
8145               size_t len;
8146
8147               switch (option->kind)
8148                 {
8149                 case ODK_NULL:
8150                   /* This shouldn't happen.  */
8151                   printf (" NULL       %d %lx", option->section, option->info);
8152                   break;
8153                 case ODK_REGINFO:
8154                   printf (" REGINFO    ");
8155                   if (elf_header.e_machine == EM_MIPS)
8156                     {
8157                       /* 32bit form.  */
8158                       Elf32_External_RegInfo * ereg;
8159                       Elf32_RegInfo            reginfo;
8160
8161                       ereg = (Elf32_External_RegInfo *) (option + 1);
8162                       reginfo.ri_gprmask = BYTE_GET (ereg->ri_gprmask);
8163                       reginfo.ri_cprmask[0] = BYTE_GET (ereg->ri_cprmask[0]);
8164                       reginfo.ri_cprmask[1] = BYTE_GET (ereg->ri_cprmask[1]);
8165                       reginfo.ri_cprmask[2] = BYTE_GET (ereg->ri_cprmask[2]);
8166                       reginfo.ri_cprmask[3] = BYTE_GET (ereg->ri_cprmask[3]);
8167                       reginfo.ri_gp_value = BYTE_GET (ereg->ri_gp_value);
8168
8169                       printf ("GPR %08lx  GP 0x%lx\n",
8170                               reginfo.ri_gprmask,
8171                               (unsigned long) reginfo.ri_gp_value);
8172                       printf ("            CPR0 %08lx  CPR1 %08lx  CPR2 %08lx  CPR3 %08lx\n",
8173                               reginfo.ri_cprmask[0], reginfo.ri_cprmask[1],
8174                               reginfo.ri_cprmask[2], reginfo.ri_cprmask[3]);
8175                     }
8176                   else
8177                     {
8178                       /* 64 bit form.  */
8179                       Elf64_External_RegInfo * ereg;
8180                       Elf64_Internal_RegInfo reginfo;
8181
8182                       ereg = (Elf64_External_RegInfo *) (option + 1);
8183                       reginfo.ri_gprmask    = BYTE_GET (ereg->ri_gprmask);
8184                       reginfo.ri_cprmask[0] = BYTE_GET (ereg->ri_cprmask[0]);
8185                       reginfo.ri_cprmask[1] = BYTE_GET (ereg->ri_cprmask[1]);
8186                       reginfo.ri_cprmask[2] = BYTE_GET (ereg->ri_cprmask[2]);
8187                       reginfo.ri_cprmask[3] = BYTE_GET (ereg->ri_cprmask[3]);
8188                       reginfo.ri_gp_value   = BYTE_GET8 (ereg->ri_gp_value);
8189
8190                       printf ("GPR %08lx  GP 0x",
8191                               reginfo.ri_gprmask);
8192                       printf_vma (reginfo.ri_gp_value);
8193                       printf ("\n");
8194
8195                       printf ("            CPR0 %08lx  CPR1 %08lx  CPR2 %08lx  CPR3 %08lx\n",
8196                               reginfo.ri_cprmask[0], reginfo.ri_cprmask[1],
8197                               reginfo.ri_cprmask[2], reginfo.ri_cprmask[3]);
8198                     }
8199                   ++option;
8200                   continue;
8201                 case ODK_EXCEPTIONS:
8202                   fputs (" EXCEPTIONS fpe_min(", stdout);
8203                   process_mips_fpe_exception (option->info & OEX_FPU_MIN);
8204                   fputs (") fpe_max(", stdout);
8205                   process_mips_fpe_exception ((option->info & OEX_FPU_MAX) >> 8);
8206                   fputs (")", stdout);
8207
8208                   if (option->info & OEX_PAGE0)
8209                     fputs (" PAGE0", stdout);
8210                   if (option->info & OEX_SMM)
8211                     fputs (" SMM", stdout);
8212                   if (option->info & OEX_FPDBUG)
8213                     fputs (" FPDBUG", stdout);
8214                   if (option->info & OEX_DISMISS)
8215                     fputs (" DISMISS", stdout);
8216                   break;
8217                 case ODK_PAD:
8218                   fputs (" PAD       ", stdout);
8219                   if (option->info & OPAD_PREFIX)
8220                     fputs (" PREFIX", stdout);
8221                   if (option->info & OPAD_POSTFIX)
8222                     fputs (" POSTFIX", stdout);
8223                   if (option->info & OPAD_SYMBOL)
8224                     fputs (" SYMBOL", stdout);
8225                   break;
8226                 case ODK_HWPATCH:
8227                   fputs (" HWPATCH   ", stdout);
8228                   if (option->info & OHW_R4KEOP)
8229                     fputs (" R4KEOP", stdout);
8230                   if (option->info & OHW_R8KPFETCH)
8231                     fputs (" R8KPFETCH", stdout);
8232                   if (option->info & OHW_R5KEOP)
8233                     fputs (" R5KEOP", stdout);
8234                   if (option->info & OHW_R5KCVTL)
8235                     fputs (" R5KCVTL", stdout);
8236                   break;
8237                 case ODK_FILL:
8238                   fputs (" FILL       ", stdout);
8239                   /* XXX Print content of info word?  */
8240                   break;
8241                 case ODK_TAGS:
8242                   fputs (" TAGS       ", stdout);
8243                   /* XXX Print content of info word?  */
8244                   break;
8245                 case ODK_HWAND:
8246                   fputs (" HWAND     ", stdout);
8247                   if (option->info & OHWA0_R4KEOP_CHECKED)
8248                     fputs (" R4KEOP_CHECKED", stdout);
8249                   if (option->info & OHWA0_R4KEOP_CLEAN)
8250                     fputs (" R4KEOP_CLEAN", stdout);
8251                   break;
8252                 case ODK_HWOR:
8253                   fputs (" HWOR      ", stdout);
8254                   if (option->info & OHWA0_R4KEOP_CHECKED)
8255                     fputs (" R4KEOP_CHECKED", stdout);
8256                   if (option->info & OHWA0_R4KEOP_CLEAN)
8257                     fputs (" R4KEOP_CLEAN", stdout);
8258                   break;
8259                 case ODK_GP_GROUP:
8260                   printf (" GP_GROUP  %#06lx  self-contained %#06lx",
8261                           option->info & OGP_GROUP,
8262                           (option->info & OGP_SELF) >> 16);
8263                   break;
8264                 case ODK_IDENT:
8265                   printf (" IDENT     %#06lx  self-contained %#06lx",
8266                           option->info & OGP_GROUP,
8267                           (option->info & OGP_SELF) >> 16);
8268                   break;
8269                 default:
8270                   /* This shouldn't happen.  */
8271                   printf (" %3d ???     %d %lx",
8272                           option->kind, option->section, option->info);
8273                   break;
8274                 }
8275
8276               len = sizeof (* eopt);
8277               while (len < option->size)
8278                 if (((char *) option)[len] >= ' '
8279                     && ((char *) option)[len] < 0x7f)
8280                   printf ("%c", ((char *) option)[len++]);
8281                 else
8282                   printf ("\\%03o", ((char *) option)[len++]);
8283
8284               fputs ("\n", stdout);
8285               ++option;
8286             }
8287
8288           free (eopt);
8289         }
8290     }
8291
8292   if (conflicts_offset != 0 && conflictsno != 0)
8293     {
8294       Elf32_Conflict * iconf;
8295       size_t cnt;
8296
8297       if (dynamic_symbols == NULL)
8298         {
8299           error (_("conflict list with without table"));
8300           return 0;
8301         }
8302
8303       iconf = (Elf32_Conflict *) malloc (conflictsno * sizeof (* iconf));
8304       if (iconf == NULL)
8305         {
8306           error (_("Out of memory"));
8307           return 0;
8308         }
8309
8310       if (is_32bit_elf)
8311         {
8312           Elf32_External_Conflict * econf32;
8313
8314           econf32 = ((Elf32_External_Conflict *)
8315                      get_data (NULL, file, conflicts_offset,
8316                                conflictsno * sizeof (* econf32),
8317                                _("conflict")));
8318           if (!econf32)
8319             return 0;
8320
8321           for (cnt = 0; cnt < conflictsno; ++cnt)
8322             iconf[cnt] = BYTE_GET (econf32[cnt]);
8323
8324           free (econf32);
8325         }
8326       else
8327         {
8328           Elf64_External_Conflict * econf64;
8329
8330           econf64 = ((Elf64_External_Conflict *)
8331                      get_data (NULL, file, conflicts_offset,
8332                                conflictsno * sizeof (* econf64),
8333                                _("conflict")));
8334           if (!econf64)
8335             return 0;
8336
8337           for (cnt = 0; cnt < conflictsno; ++cnt)
8338             iconf[cnt] = BYTE_GET (econf64[cnt]);
8339
8340           free (econf64);
8341         }
8342
8343       printf (_("\nSection '.conflict' contains %d entries:\n"), conflictsno);
8344       puts (_("  Num:    Index       Value  Name"));
8345
8346       for (cnt = 0; cnt < conflictsno; ++cnt)
8347         {
8348           Elf_Internal_Sym * psym = &dynamic_symbols[iconf[cnt]];
8349
8350           printf ("%5lu: %8lu  ", (unsigned long) cnt, iconf[cnt]);
8351           print_vma (psym->st_value, FULL_HEX);
8352           printf ("  %s\n", dynamic_strings + psym->st_name);
8353         }
8354
8355       free (iconf);
8356     }
8357
8358   return 1;
8359 }
8360
8361 static char *
8362 get_note_type (e_type)
8363      unsigned e_type;
8364 {
8365   static char buff[64];
8366
8367   switch (e_type)
8368     {
8369     case NT_PRSTATUS:   return _("NT_PRSTATUS (prstatus structure)");
8370     case NT_FPREGSET:   return _("NT_FPREGSET (floating point registers)");
8371     case NT_PRPSINFO:   return _("NT_PRPSINFO (prpsinfo structure)");
8372     case NT_TASKSTRUCT: return _("NT_TASKSTRUCT (task structure)");
8373     case NT_PRXFPREG:   return _("NT_PRXFPREG (user_xfpregs structure)");
8374     case NT_PSTATUS:    return _("NT_PSTATUS (pstatus structure)");
8375     case NT_FPREGS:     return _("NT_FPREGS (floating point registers)");
8376     case NT_PSINFO:     return _("NT_PSINFO (psinfo structure)");
8377     case NT_LWPSTATUS:  return _("NT_LWPSTATUS (lwpstatus_t structure)");
8378     case NT_LWPSINFO:   return _("NT_LWPSINFO (lwpsinfo_t structure)");
8379     case NT_WIN32PSTATUS: return _("NT_WIN32PSTATUS (win32_pstatus strcuture)");
8380     default:
8381       sprintf (buff, _("Unknown note type: (0x%08x)"), e_type);
8382       return buff;
8383     }
8384 }
8385
8386 /* Note that by the ELF standard, the name field is already null byte
8387    terminated, and namesz includes the terminating null byte.
8388    I.E. the value of namesz for the name "FSF" is 4.
8389
8390    If the value of namesz is zero, there is no name present. */
8391 static int
8392 process_note (pnote)
8393   Elf32_Internal_Note * pnote;
8394 {
8395   printf ("  %s\t\t0x%08lx\t%s\n",
8396           pnote->namesz ? pnote->namedata : "(NONE)",
8397           pnote->descsz, get_note_type (pnote->type));
8398   return 1;
8399 }
8400
8401
8402 static int
8403 process_corefile_note_segment (file, offset, length)
8404      FILE * file;
8405      bfd_vma offset;
8406      bfd_vma length;
8407 {
8408   Elf_External_Note *  pnotes;
8409   Elf_External_Note *  external;
8410   int                  res = 1;
8411
8412   if (length <= 0)
8413     return 0;
8414
8415   pnotes = (Elf_External_Note *) get_data (NULL, file, offset, length,
8416                                            _("notes"));
8417   if (!pnotes)
8418     return 0;
8419
8420   external = pnotes;
8421
8422   printf (_("\nNotes at offset 0x%08lx with length 0x%08lx:\n"),
8423           (unsigned long) offset, (unsigned long) length);
8424   printf (_("  Owner\t\tData size\tDescription\n"));
8425
8426   while (external < (Elf_External_Note *)((char *) pnotes + length))
8427     {
8428       Elf32_Internal_Note inote;
8429       char * temp = NULL;
8430
8431       inote.type     = BYTE_GET (external->type);
8432       inote.namesz   = BYTE_GET (external->namesz);
8433       inote.namedata = external->name;
8434       inote.descsz   = BYTE_GET (external->descsz);
8435       inote.descdata = inote.namedata + align_power (inote.namesz, 2);
8436       inote.descpos  = offset + (inote.descdata - (char *) pnotes);
8437
8438       external = (Elf_External_Note *)(inote.descdata + align_power (inote.descsz, 2));
8439
8440       /* Verify that name is null terminated.  It appears that at least
8441          one version of Linux (RedHat 6.0) generates corefiles that don't
8442          comply with the ELF spec by failing to include the null byte in
8443          namesz.  */
8444       if (inote.namedata[inote.namesz] != '\0')
8445         {
8446           temp = malloc (inote.namesz + 1);
8447
8448           if (temp == NULL)
8449             {
8450               error (_("Out of memory\n"));
8451               res = 0;
8452               break;
8453             }
8454
8455           strncpy (temp, inote.namedata, inote.namesz);
8456           temp[inote.namesz] = 0;
8457
8458           /* warn (_("'%s' NOTE name not properly null terminated\n"), temp);  */
8459           inote.namedata = temp;
8460         }
8461
8462       res &= process_note (& inote);
8463
8464       if (temp != NULL)
8465         {
8466           free (temp);
8467           temp = NULL;
8468         }
8469     }
8470
8471   free (pnotes);
8472
8473   return res;
8474 }
8475
8476 static int
8477 process_corefile_note_segments (file)
8478      FILE * file;
8479 {
8480   Elf_Internal_Phdr * program_headers;
8481   Elf_Internal_Phdr * segment;
8482   unsigned int        i;
8483   int                 res = 1;
8484
8485   program_headers = (Elf_Internal_Phdr *) malloc
8486     (elf_header.e_phnum * sizeof (Elf_Internal_Phdr));
8487
8488   if (program_headers == NULL)
8489     {
8490       error (_("Out of memory\n"));
8491       return 0;
8492     }
8493
8494   if (is_32bit_elf)
8495     i = get_32bit_program_headers (file, program_headers);
8496   else
8497     i = get_64bit_program_headers (file, program_headers);
8498
8499   if (i == 0)
8500     {
8501       free (program_headers);
8502       return 0;
8503     }
8504
8505   for (i = 0, segment = program_headers;
8506        i < elf_header.e_phnum;
8507        i ++, segment ++)
8508     {
8509       if (segment->p_type == PT_NOTE)
8510         res &= process_corefile_note_segment (file,
8511                                               (bfd_vma) segment->p_offset,
8512                                               (bfd_vma) segment->p_filesz);
8513     }
8514
8515   free (program_headers);
8516
8517   return res;
8518 }
8519
8520 static int
8521 process_corefile_contents (file)
8522      FILE * file;
8523 {
8524   /* If we have not been asked to display the notes then do nothing.  */
8525   if (! do_notes)
8526     return 1;
8527
8528   /* If file is not a core file then exit.  */
8529   if (elf_header.e_type != ET_CORE)
8530     return 1;
8531
8532   /* No program headers means no NOTE segment.  */
8533   if (elf_header.e_phnum == 0)
8534     {
8535       printf (_("No note segments present in the core file.\n"));
8536       return 1;
8537    }
8538
8539   return process_corefile_note_segments (file);
8540 }
8541
8542 static int
8543 process_arch_specific (file)
8544      FILE * file;
8545 {
8546   if (! do_arch)
8547     return 1;
8548
8549   switch (elf_header.e_machine)
8550     {
8551     case EM_MIPS:
8552     case EM_MIPS_RS3_LE:
8553       return process_mips_specific (file);
8554       break;
8555     default:
8556       break;
8557     }
8558   return 1;
8559 }
8560
8561 static int
8562 get_file_header (file)
8563      FILE * file;
8564 {
8565   /* Read in the identity array.  */
8566   if (fread (elf_header.e_ident, EI_NIDENT, 1, file) != 1)
8567     return 0;
8568
8569   /* Determine how to read the rest of the header.  */
8570   switch (elf_header.e_ident [EI_DATA])
8571     {
8572     default: /* fall through */
8573     case ELFDATANONE: /* fall through */
8574     case ELFDATA2LSB: byte_get = byte_get_little_endian; break;
8575     case ELFDATA2MSB: byte_get = byte_get_big_endian; break;
8576     }
8577
8578   /* For now we only support 32 bit and 64 bit ELF files.  */
8579   is_32bit_elf = (elf_header.e_ident [EI_CLASS] != ELFCLASS64);
8580
8581   /* Read in the rest of the header.  */
8582   if (is_32bit_elf)
8583     {
8584       Elf32_External_Ehdr ehdr32;
8585
8586       if (fread (ehdr32.e_type, sizeof (ehdr32) - EI_NIDENT, 1, file) != 1)
8587         return 0;
8588
8589       elf_header.e_type      = BYTE_GET (ehdr32.e_type);
8590       elf_header.e_machine   = BYTE_GET (ehdr32.e_machine);
8591       elf_header.e_version   = BYTE_GET (ehdr32.e_version);
8592       elf_header.e_entry     = BYTE_GET (ehdr32.e_entry);
8593       elf_header.e_phoff     = BYTE_GET (ehdr32.e_phoff);
8594       elf_header.e_shoff     = BYTE_GET (ehdr32.e_shoff);
8595       elf_header.e_flags     = BYTE_GET (ehdr32.e_flags);
8596       elf_header.e_ehsize    = BYTE_GET (ehdr32.e_ehsize);
8597       elf_header.e_phentsize = BYTE_GET (ehdr32.e_phentsize);
8598       elf_header.e_phnum     = BYTE_GET (ehdr32.e_phnum);
8599       elf_header.e_shentsize = BYTE_GET (ehdr32.e_shentsize);
8600       elf_header.e_shnum     = BYTE_GET (ehdr32.e_shnum);
8601       elf_header.e_shstrndx  = BYTE_GET (ehdr32.e_shstrndx);
8602     }
8603   else
8604     {
8605       Elf64_External_Ehdr ehdr64;
8606
8607       /* If we have been compiled with sizeof (bfd_vma) == 4, then
8608          we will not be able to cope with the 64bit data found in
8609          64 ELF files.  Detect this now and abort before we start
8610          overwritting things.  */
8611       if (sizeof (bfd_vma) < 8)
8612         {
8613           error (_("This instance of readelf has been built without support for a\n"));
8614           error (_("64 bit data type and so it cannot read 64 bit ELF files.\n"));
8615           return 0;
8616         }
8617
8618       if (fread (ehdr64.e_type, sizeof (ehdr64) - EI_NIDENT, 1, file) != 1)
8619         return 0;
8620
8621       elf_header.e_type      = BYTE_GET (ehdr64.e_type);
8622       elf_header.e_machine   = BYTE_GET (ehdr64.e_machine);
8623       elf_header.e_version   = BYTE_GET (ehdr64.e_version);
8624       elf_header.e_entry     = BYTE_GET8 (ehdr64.e_entry);
8625       elf_header.e_phoff     = BYTE_GET8 (ehdr64.e_phoff);
8626       elf_header.e_shoff     = BYTE_GET8 (ehdr64.e_shoff);
8627       elf_header.e_flags     = BYTE_GET (ehdr64.e_flags);
8628       elf_header.e_ehsize    = BYTE_GET (ehdr64.e_ehsize);
8629       elf_header.e_phentsize = BYTE_GET (ehdr64.e_phentsize);
8630       elf_header.e_phnum     = BYTE_GET (ehdr64.e_phnum);
8631       elf_header.e_shentsize = BYTE_GET (ehdr64.e_shentsize);
8632       elf_header.e_shnum     = BYTE_GET (ehdr64.e_shnum);
8633       elf_header.e_shstrndx  = BYTE_GET (ehdr64.e_shstrndx);
8634     }
8635
8636   return 1;
8637 }
8638
8639 static void
8640 process_file (file_name)
8641      char * file_name;
8642 {
8643   FILE *       file;
8644   struct stat  statbuf;
8645   unsigned int i;
8646
8647   if (stat (file_name, & statbuf) < 0)
8648     {
8649       error (_("Cannot stat input file %s.\n"), file_name);
8650       return;
8651     }
8652
8653   file = fopen (file_name, "rb");
8654   if (file == NULL)
8655     {
8656       error (_("Input file %s not found.\n"), file_name);
8657       return;
8658     }
8659
8660   if (! get_file_header (file))
8661     {
8662       error (_("%s: Failed to read file header\n"), file_name);
8663       fclose (file);
8664       return;
8665     }
8666
8667   /* Initialise per file variables.  */
8668   for (i = NUM_ELEM (version_info); i--;)
8669     version_info[i] = 0;
8670
8671   for (i = NUM_ELEM (dynamic_info); i--;)
8672     dynamic_info[i] = 0;
8673
8674   /* Process the file.  */
8675   if (show_name)
8676     printf (_("\nFile: %s\n"), file_name);
8677
8678   if (! process_file_header ())
8679     {
8680       fclose (file);
8681       return;
8682     }
8683
8684   process_section_headers (file);
8685
8686   process_program_headers (file);
8687
8688   process_dynamic_segment (file);
8689
8690   process_relocs (file);
8691
8692   process_unwind (file);
8693
8694   process_symbol_table (file);
8695
8696   process_syminfo (file);
8697
8698   process_version_sections (file);
8699
8700   process_section_contents (file);
8701
8702   process_corefile_contents (file);
8703
8704   process_arch_specific (file);
8705
8706   fclose (file);
8707
8708   if (section_headers)
8709     {
8710       free (section_headers);
8711       section_headers = NULL;
8712     }
8713
8714   if (string_table)
8715     {
8716       free (string_table);
8717       string_table = NULL;
8718       string_table_length = 0;
8719     }
8720
8721   if (dynamic_strings)
8722     {
8723       free (dynamic_strings);
8724       dynamic_strings = NULL;
8725     }
8726
8727   if (dynamic_symbols)
8728     {
8729       free (dynamic_symbols);
8730       dynamic_symbols = NULL;
8731       num_dynamic_syms = 0;
8732     }
8733
8734   if (dynamic_syminfo)
8735     {
8736       free (dynamic_syminfo);
8737       dynamic_syminfo = NULL;
8738     }
8739 }
8740
8741 #ifdef SUPPORT_DISASSEMBLY
8742 /* Needed by the i386 disassembler.  For extra credit, someone could
8743    fix this so that we insert symbolic addresses here, esp for GOT/PLT
8744    symbols */
8745
8746 void
8747 print_address (unsigned int addr, FILE * outfile)
8748 {
8749   fprintf (outfile,"0x%8.8x", addr);
8750 }
8751
8752 /* Needed by the i386 disassembler. */
8753 void
8754 db_task_printsym (unsigned int addr)
8755 {
8756   print_address (addr, stderr);
8757 }
8758 #endif
8759
8760 int
8761 main (argc, argv)
8762      int     argc;
8763      char ** argv;
8764 {
8765 #if defined (HAVE_SETLOCALE) && defined (HAVE_LC_MESSAGES)
8766   setlocale (LC_MESSAGES, "");
8767 #endif
8768   bindtextdomain (PACKAGE, LOCALEDIR);
8769   textdomain (PACKAGE);
8770
8771   parse_args (argc, argv);
8772
8773   if (optind < (argc - 1))
8774     show_name = 1;
8775
8776   while (optind < argc)
8777     process_file (argv [optind ++]);
8778
8779   if (dump_sects != NULL)
8780     free (dump_sects);
8781
8782   return 0;
8783 }