OpenCores
URL https://opencores.org/ocsvn/scarts/scarts/trunk

Subversion Repositories scarts

[/] [scarts/] [trunk/] [toolchain/] [scarts-binutils/] [binutils-2.19.1/] [binutils/] [readelf.c] - Blame information for rev 6

Details | Compare with Previous | View Log

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

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.