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