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