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