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