Add Visium support to bfd
[deliverable/binutils-gdb.git] / binutils / readelf.c
CommitLineData
252b5132 1/* readelf.c -- display contents of an ELF format file
4b95cf5c 2 Copyright (C) 1998-2014 Free Software Foundation, Inc.
252b5132
RH
3
4 Originally developed by Eric Youngdale <eric@andante.jic.com>
12ab83a9 5 Modifications by Nick Clifton <nickc@redhat.com>
252b5132
RH
6
7 This file is part of GNU Binutils.
8
9 This program is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
32866df7 11 the Free Software Foundation; either version 3 of the License, or
252b5132
RH
12 (at your option) any later version.
13
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
18
19 You should have received a copy of the GNU General Public License
20 along with this program; if not, write to the Free Software
b43b5d5f
NC
21 Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA
22 02110-1301, USA. */
252b5132 23\f
9eb20dd8 24/* The difference between readelf and objdump:
252b5132 25
74013231 26 Both programs are capable of displaying the contents of ELF format files,
9eb20dd8 27 so why does the binutils project have two file dumpers ?
0de14b54 28
9eb20dd8
NC
29 The reason is that objdump sees an ELF file through a BFD filter of the
30 world; if BFD has a bug where, say, it disagrees about a machine constant
31 in e_flags, then the odds are good that it will remain internally
32 consistent. The linker sees it the BFD way, objdump sees it the BFD way,
33 GAS sees it the BFD way. There was need for a tool to go find out what
34 the file actually says.
35
36 This is why the readelf program does not link against the BFD library - it
37 exists as an independent program to help verify the correct working of BFD.
38
39 There is also the case that readelf can provide more information about an
40 ELF file than is provided by objdump. In particular it can display DWARF
41 debugging information which (at the moment) objdump cannot. */
42\f
3db64b00 43#include "sysdep.h"
252b5132 44#include <assert.h>
252b5132 45#include <time.h>
1b315056
CS
46#ifdef HAVE_ZLIB_H
47#include <zlib.h>
48#endif
3bfcb652 49#ifdef HAVE_WCHAR_H
7bfd842d 50#include <wchar.h>
3bfcb652 51#endif
252b5132 52
a952a375 53#if __GNUC__ >= 2
19936277 54/* Define BFD64 here, even if our default architecture is 32 bit ELF
a952a375 55 as this will allow us to read in and parse 64bit and 32bit ELF files.
b34976b6 56 Only do this if we believe that the compiler can support a 64 bit
a952a375 57 data type. For now we only rely on GCC being able to do this. */
19936277 58#define BFD64
a952a375
NC
59#endif
60
3db64b00
AM
61#include "bfd.h"
62#include "bucomm.h"
3284fe0c 63#include "elfcomm.h"
19e6b90e 64#include "dwarf.h"
252b5132
RH
65
66#include "elf/common.h"
67#include "elf/external.h"
68#include "elf/internal.h"
252b5132 69
4b78141a
NC
70
71/* Included here, before RELOC_MACROS_GEN_FUNC is defined, so that
72 we can obtain the H8 reloc numbers. We need these for the
73 get_reloc_size() function. We include h8.h again after defining
74 RELOC_MACROS_GEN_FUNC so that we get the naming function as well. */
75
76#include "elf/h8.h"
77#undef _ELF_H8_H
78
79/* Undo the effects of #including reloc-macros.h. */
80
81#undef START_RELOC_NUMBERS
82#undef RELOC_NUMBER
83#undef FAKE_RELOC
84#undef EMPTY_RELOC
85#undef END_RELOC_NUMBERS
86#undef _RELOC_MACROS_H
87
252b5132
RH
88/* The following headers use the elf/reloc-macros.h file to
89 automatically generate relocation recognition functions
90 such as elf_mips_reloc_type() */
91
92#define RELOC_MACROS_GEN_FUNC
93
a06ea964 94#include "elf/aarch64.h"
252b5132 95#include "elf/alpha.h"
3b16e843 96#include "elf/arc.h"
252b5132 97#include "elf/arm.h"
3b16e843 98#include "elf/avr.h"
1d65ded4 99#include "elf/bfin.h"
60bca95a 100#include "elf/cr16.h"
3b16e843 101#include "elf/cris.h"
1c0d3aa6 102#include "elf/crx.h"
252b5132
RH
103#include "elf/d10v.h"
104#include "elf/d30v.h"
d172d4ba 105#include "elf/dlx.h"
cfb8c092 106#include "elf/epiphany.h"
252b5132 107#include "elf/fr30.h"
5c70f934 108#include "elf/frv.h"
3b16e843
NC
109#include "elf/h8.h"
110#include "elf/hppa.h"
111#include "elf/i386.h"
35b1837e 112#include "elf/i370.h"
3b16e843
NC
113#include "elf/i860.h"
114#include "elf/i960.h"
115#include "elf/ia64.h"
1e4cf259 116#include "elf/ip2k.h"
84e94c90 117#include "elf/lm32.h"
1c0d3aa6 118#include "elf/iq2000.h"
49f58d10 119#include "elf/m32c.h"
3b16e843
NC
120#include "elf/m32r.h"
121#include "elf/m68k.h"
75751cd9 122#include "elf/m68hc11.h"
252b5132 123#include "elf/mcore.h"
15ab5209 124#include "elf/mep.h"
a3c62988 125#include "elf/metag.h"
7ba29e2a 126#include "elf/microblaze.h"
3b16e843 127#include "elf/mips.h"
3c3bdf30 128#include "elf/mmix.h"
3b16e843
NC
129#include "elf/mn10200.h"
130#include "elf/mn10300.h"
5506d11a 131#include "elf/moxie.h"
4970f871 132#include "elf/mt.h"
2469cfa2 133#include "elf/msp430.h"
35c08157 134#include "elf/nds32.h"
13761a11 135#include "elf/nios2.h"
73589c9d 136#include "elf/or1k.h"
7d466069 137#include "elf/pj.h"
3b16e843 138#include "elf/ppc.h"
c833c019 139#include "elf/ppc64.h"
99c513f6 140#include "elf/rl78.h"
c7927a3c 141#include "elf/rx.h"
a85d7ed0 142#include "elf/s390.h"
1c0d3aa6 143#include "elf/score.h"
3b16e843
NC
144#include "elf/sh.h"
145#include "elf/sparc.h"
e9f53129 146#include "elf/spu.h"
40b36596 147#include "elf/tic6x.h"
aa137e4d
NC
148#include "elf/tilegx.h"
149#include "elf/tilepro.h"
3b16e843 150#include "elf/v850.h"
179d3252 151#include "elf/vax.h"
3b16e843 152#include "elf/x86-64.h"
c29aca4a 153#include "elf/xc16x.h"
f6c1a2d5 154#include "elf/xgate.h"
93fbbb04 155#include "elf/xstormy16.h"
88da6820 156#include "elf/xtensa.h"
252b5132 157
252b5132 158#include "getopt.h"
566b0d53 159#include "libiberty.h"
09c11c86 160#include "safe-ctype.h"
2cf0635d 161#include "filenames.h"
252b5132 162
15b42fb0
AM
163#ifndef offsetof
164#define offsetof(TYPE, MEMBER) ((size_t) &(((TYPE *) 0)->MEMBER))
165#endif
166
2cf0635d 167char * program_name = "readelf";
c9c1d674 168static unsigned long archive_file_offset;
85b1c36d 169static unsigned long archive_file_size;
f54498b4 170static bfd_size_type current_file_size;
85b1c36d
BE
171static unsigned long dynamic_addr;
172static bfd_size_type dynamic_size;
8b73c356 173static size_t dynamic_nent;
2cf0635d 174static char * dynamic_strings;
85b1c36d 175static unsigned long dynamic_strings_length;
2cf0635d 176static char * string_table;
85b1c36d
BE
177static unsigned long string_table_length;
178static unsigned long num_dynamic_syms;
2cf0635d
NC
179static Elf_Internal_Sym * dynamic_symbols;
180static Elf_Internal_Syminfo * dynamic_syminfo;
85b1c36d
BE
181static unsigned long dynamic_syminfo_offset;
182static unsigned int dynamic_syminfo_nent;
f8eae8b2 183static char program_interpreter[PATH_MAX];
bb8a0291 184static bfd_vma dynamic_info[DT_ENCODING];
fdc90cb4 185static bfd_vma dynamic_info_DT_GNU_HASH;
85b1c36d
BE
186static bfd_vma version_info[16];
187static Elf_Internal_Ehdr elf_header;
2cf0635d
NC
188static Elf_Internal_Shdr * section_headers;
189static Elf_Internal_Phdr * program_headers;
190static Elf_Internal_Dyn * dynamic_section;
191static Elf_Internal_Shdr * symtab_shndx_hdr;
85b1c36d
BE
192static int show_name;
193static int do_dynamic;
194static int do_syms;
2c610e4b 195static int do_dyn_syms;
85b1c36d
BE
196static int do_reloc;
197static int do_sections;
198static int do_section_groups;
5477e8a0 199static int do_section_details;
85b1c36d
BE
200static int do_segments;
201static int do_unwind;
202static int do_using_dynamic;
203static int do_header;
204static int do_dump;
205static int do_version;
85b1c36d
BE
206static int do_histogram;
207static int do_debugging;
85b1c36d
BE
208static int do_arch;
209static int do_notes;
4145f1d5 210static int do_archive_index;
85b1c36d 211static int is_32bit_elf;
252b5132 212
e4b17d5c
L
213struct group_list
214{
2cf0635d 215 struct group_list * next;
e4b17d5c
L
216 unsigned int section_index;
217};
218
219struct group
220{
2cf0635d 221 struct group_list * root;
e4b17d5c
L
222 unsigned int group_index;
223};
224
85b1c36d 225static size_t group_count;
2cf0635d
NC
226static struct group * section_groups;
227static struct group ** section_headers_groups;
e4b17d5c 228
09c11c86
NC
229
230/* Flag bits indicating particular types of dump. */
231#define HEX_DUMP (1 << 0) /* The -x command line switch. */
232#define DISASS_DUMP (1 << 1) /* The -i command line switch. */
233#define DEBUG_DUMP (1 << 2) /* The -w command line switch. */
234#define STRING_DUMP (1 << 3) /* The -p command line switch. */
cf13d699 235#define RELOC_DUMP (1 << 4) /* The -R command line switch. */
09c11c86
NC
236
237typedef unsigned char dump_type;
238
239/* A linked list of the section names for which dumps were requested. */
aef1f6d0
DJ
240struct dump_list_entry
241{
2cf0635d 242 char * name;
09c11c86 243 dump_type type;
2cf0635d 244 struct dump_list_entry * next;
aef1f6d0 245};
2cf0635d 246static struct dump_list_entry * dump_sects_byname;
aef1f6d0 247
09c11c86
NC
248/* A dynamic array of flags indicating for which sections a dump
249 has been requested via command line switches. */
250static dump_type * cmdline_dump_sects = NULL;
251static unsigned int num_cmdline_dump_sects = 0;
18bd398b
NC
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
aef1f6d0
DJ
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. */
09c11c86
NC
258static dump_type * dump_sects = NULL;
259static unsigned int num_dump_sects = 0;
252b5132 260
252b5132 261
c256ffe7 262/* How to print a vma value. */
843dd992
NC
263typedef enum print_mode
264{
265 HEX,
266 DEC,
267 DEC_5,
268 UNSIGNED,
269 PREFIX_HEX,
270 FULL_HEX,
271 LONG_HEX
272}
273print_mode;
274
bb4d2ac2
L
275/* Versioned symbol info. */
276enum versioned_symbol_info
277{
278 symbol_undefined,
279 symbol_hidden,
280 symbol_public
281};
282
283static const char *get_symbol_version_string
284 (FILE *file, int is_dynsym, const char *strtab,
285 unsigned long int strtab_size, unsigned int si,
286 Elf_Internal_Sym *psym, enum versioned_symbol_info *sym_info,
287 unsigned short *vna_other);
288
9c19a809
NC
289#define UNKNOWN -1
290
2b692964
NC
291#define SECTION_NAME(X) \
292 ((X) == NULL ? _("<none>") \
293 : string_table == NULL ? _("<no-name>") \
294 : ((X)->sh_name >= string_table_length ? _("<corrupt>") \
0b49d371 295 : string_table + (X)->sh_name))
252b5132 296
ee42cf8c 297#define DT_VERSIONTAGIDX(tag) (DT_VERNEEDNUM - (tag)) /* Reverse order! */
252b5132 298
ba5cdace
NC
299#define GET_ELF_SYMBOLS(file, section, sym_count) \
300 (is_32bit_elf ? get_32bit_elf_symbols (file, section, sym_count) \
301 : get_64bit_elf_symbols (file, section, sym_count))
9ea033b2 302
d79b3d50
NC
303#define VALID_DYNAMIC_NAME(offset) ((dynamic_strings != NULL) && (offset < dynamic_strings_length))
304/* GET_DYNAMIC_NAME asssumes that VALID_DYNAMIC_NAME has
305 already been called and verified that the string exists. */
306#define GET_DYNAMIC_NAME(offset) (dynamic_strings + offset)
18bd398b 307
61865e30
NC
308#define REMOVE_ARCH_BITS(ADDR) \
309 do \
310 { \
311 if (elf_header.e_machine == EM_ARM) \
312 (ADDR) &= ~1; \
313 } \
314 while (0)
d79b3d50 315\f
c9c1d674
EG
316/* Retrieve NMEMB structures, each SIZE bytes long from FILE starting at OFFSET +
317 the offset of the current archive member, if we are examining an archive.
59245841
NC
318 Put the retrieved data into VAR, if it is not NULL. Otherwise allocate a buffer
319 using malloc and fill that. In either case return the pointer to the start of
320 the retrieved data or NULL if something went wrong. If something does go wrong
c9c1d674
EG
321 and REASON is not NULL then emit an error message using REASON as part of the
322 context. */
59245841 323
c256ffe7 324static void *
c9c1d674 325get_data (void * var, FILE * file, unsigned long offset, size_t size, size_t nmemb,
2cf0635d 326 const char * reason)
a6e9f9df 327{
2cf0635d 328 void * mvar;
c9c1d674 329 size_t amt = size * nmemb;
a6e9f9df 330
c256ffe7 331 if (size == 0 || nmemb == 0)
a6e9f9df
AM
332 return NULL;
333
c9c1d674
EG
334 /* Be kind to memory chekers (eg valgrind, address sanitizer) by not
335 attempting to allocate memory when the read is bound to fail. */
336 if (amt > current_file_size
337 || offset + archive_file_offset + amt > current_file_size)
a6e9f9df 338 {
049b0c3a 339 if (reason)
c9c1d674
EG
340 error (_("Reading 0x%lx bytes extends past end of file for %s\n"),
341 (unsigned long) amt, reason);
a6e9f9df
AM
342 return NULL;
343 }
344
c9c1d674 345 if (fseek (file, archive_file_offset + offset, SEEK_SET))
071436c6
NC
346 {
347 if (reason)
c9c1d674
EG
348 error (_("Unable to seek to 0x%lx for %s\n"),
349 (unsigned long) archive_file_offset + offset, reason);
071436c6
NC
350 return NULL;
351 }
352
a6e9f9df
AM
353 mvar = var;
354 if (mvar == NULL)
355 {
c256ffe7
JJ
356 /* Check for overflow. */
357 if (nmemb < (~(size_t) 0 - 1) / size)
358 /* + 1 so that we can '\0' terminate invalid string table sections. */
359 mvar = malloc (size * nmemb + 1);
a6e9f9df
AM
360
361 if (mvar == NULL)
362 {
049b0c3a
NC
363 if (reason)
364 error (_("Out of memory allocating 0x%lx bytes for %s\n"),
365 (unsigned long)(size * nmemb), reason);
a6e9f9df
AM
366 return NULL;
367 }
c256ffe7 368
c9c1d674 369 ((char *) mvar)[amt] = '\0';
a6e9f9df
AM
370 }
371
c256ffe7 372 if (fread (mvar, size, nmemb, file) != nmemb)
a6e9f9df 373 {
049b0c3a
NC
374 if (reason)
375 error (_("Unable to read in 0x%lx bytes of %s\n"),
c9c1d674 376 (unsigned long) amt, reason);
a6e9f9df
AM
377 if (mvar != var)
378 free (mvar);
379 return NULL;
380 }
381
382 return mvar;
383}
384
14a91970 385/* Print a VMA value. */
cb8f3167 386
66543521 387static int
14a91970 388print_vma (bfd_vma vma, print_mode mode)
66543521 389{
66543521
AM
390 int nc = 0;
391
14a91970 392 switch (mode)
66543521 393 {
14a91970
AM
394 case FULL_HEX:
395 nc = printf ("0x");
396 /* Drop through. */
66543521 397
14a91970 398 case LONG_HEX:
f7a99963 399#ifdef BFD64
14a91970 400 if (is_32bit_elf)
437c2fb7 401 return nc + printf ("%8.8" BFD_VMA_FMT "x", vma);
f7a99963 402#endif
14a91970
AM
403 printf_vma (vma);
404 return nc + 16;
b19aac67 405
14a91970
AM
406 case DEC_5:
407 if (vma <= 99999)
408 return printf ("%5" BFD_VMA_FMT "d", vma);
409 /* Drop through. */
66543521 410
14a91970
AM
411 case PREFIX_HEX:
412 nc = printf ("0x");
413 /* Drop through. */
66543521 414
14a91970
AM
415 case HEX:
416 return nc + printf ("%" BFD_VMA_FMT "x", vma);
b19aac67 417
14a91970
AM
418 case DEC:
419 return printf ("%" BFD_VMA_FMT "d", vma);
b19aac67 420
14a91970
AM
421 case UNSIGNED:
422 return printf ("%" BFD_VMA_FMT "u", vma);
f7a99963 423 }
66543521 424 return 0;
f7a99963
NC
425}
426
7bfd842d 427/* Display a symbol on stdout. Handles the display of control characters and
3bfcb652 428 multibye characters (assuming the host environment supports them).
31104126 429
7bfd842d
NC
430 Display at most abs(WIDTH) characters, truncating as necessary, unless do_wide is true.
431
432 If WIDTH is negative then ensure that the output is at least (- WIDTH) characters,
433 padding as necessary.
171191ba
NC
434
435 Returns the number of emitted characters. */
436
437static unsigned int
7a88bc9c 438print_symbol (int width, const char *symbol)
31104126 439{
171191ba 440 bfd_boolean extra_padding = FALSE;
7bfd842d 441 int num_printed = 0;
3bfcb652 442#ifdef HAVE_MBSTATE_T
7bfd842d 443 mbstate_t state;
3bfcb652 444#endif
7bfd842d 445 int width_remaining;
961c521f 446
7bfd842d 447 if (width < 0)
961c521f 448 {
961c521f
NC
449 /* Keep the width positive. This also helps. */
450 width = - width;
171191ba 451 extra_padding = TRUE;
0b4362b0 452 }
74e1a04b 453 assert (width != 0);
961c521f 454
7bfd842d
NC
455 if (do_wide)
456 /* Set the remaining width to a very large value.
457 This simplifies the code below. */
458 width_remaining = INT_MAX;
459 else
460 width_remaining = width;
cb8f3167 461
3bfcb652 462#ifdef HAVE_MBSTATE_T
7bfd842d
NC
463 /* Initialise the multibyte conversion state. */
464 memset (& state, 0, sizeof (state));
3bfcb652 465#endif
961c521f 466
7bfd842d
NC
467 while (width_remaining)
468 {
469 size_t n;
7bfd842d 470 const char c = *symbol++;
961c521f 471
7bfd842d 472 if (c == 0)
961c521f
NC
473 break;
474
7bfd842d
NC
475 /* Do not print control characters directly as they can affect terminal
476 settings. Such characters usually appear in the names generated
477 by the assembler for local labels. */
478 if (ISCNTRL (c))
961c521f 479 {
7bfd842d 480 if (width_remaining < 2)
961c521f
NC
481 break;
482
7bfd842d
NC
483 printf ("^%c", c + 0x40);
484 width_remaining -= 2;
171191ba 485 num_printed += 2;
961c521f 486 }
7bfd842d
NC
487 else if (ISPRINT (c))
488 {
489 putchar (c);
490 width_remaining --;
491 num_printed ++;
492 }
961c521f
NC
493 else
494 {
3bfcb652
NC
495#ifdef HAVE_MBSTATE_T
496 wchar_t w;
497#endif
7bfd842d
NC
498 /* Let printf do the hard work of displaying multibyte characters. */
499 printf ("%.1s", symbol - 1);
500 width_remaining --;
501 num_printed ++;
502
3bfcb652 503#ifdef HAVE_MBSTATE_T
7bfd842d
NC
504 /* Try to find out how many bytes made up the character that was
505 just printed. Advance the symbol pointer past the bytes that
506 were displayed. */
507 n = mbrtowc (& w, symbol - 1, MB_CUR_MAX, & state);
3bfcb652
NC
508#else
509 n = 1;
510#endif
7bfd842d
NC
511 if (n != (size_t) -1 && n != (size_t) -2 && n > 0)
512 symbol += (n - 1);
961c521f 513 }
961c521f 514 }
171191ba 515
7bfd842d 516 if (extra_padding && num_printed < width)
171191ba
NC
517 {
518 /* Fill in the remaining spaces. */
7bfd842d
NC
519 printf ("%-*s", width - num_printed, " ");
520 num_printed = width;
171191ba
NC
521 }
522
523 return num_printed;
31104126
NC
524}
525
74e1a04b
NC
526/* Returns a pointer to a static buffer containing a printable version of
527 the given section's name. Like print_symbol, except that it does not try
528 to print multibyte characters, it just interprets them as hex values. */
529
530static const char *
531printable_section_name (Elf_Internal_Shdr * sec)
532{
533#define MAX_PRINT_SEC_NAME_LEN 128
534 static char sec_name_buf [MAX_PRINT_SEC_NAME_LEN + 1];
535 const char * name = SECTION_NAME (sec);
536 char * buf = sec_name_buf;
537 char c;
538 unsigned int remaining = MAX_PRINT_SEC_NAME_LEN;
539
540 while ((c = * name ++) != 0)
541 {
542 if (ISCNTRL (c))
543 {
544 if (remaining < 2)
545 break;
546
547 * buf ++ = '^';
548 * buf ++ = c + 0x40;
549 remaining -= 2;
550 }
551 else if (ISPRINT (c))
552 {
553 * buf ++ = c;
554 remaining -= 1;
555 }
556 else
557 {
558 static char hex[17] = "0123456789ABCDEF";
559
560 if (remaining < 4)
561 break;
562 * buf ++ = '<';
563 * buf ++ = hex[(c & 0xf0) >> 4];
564 * buf ++ = hex[c & 0x0f];
565 * buf ++ = '>';
566 remaining -= 4;
567 }
568
569 if (remaining == 0)
570 break;
571 }
572
573 * buf = 0;
574 return sec_name_buf;
575}
576
577static const char *
578printable_section_name_from_index (unsigned long ndx)
579{
580 if (ndx >= elf_header.e_shnum)
581 return _("<corrupt>");
582
583 return printable_section_name (section_headers + ndx);
584}
585
89fac5e3
RS
586/* Return a pointer to section NAME, or NULL if no such section exists. */
587
588static Elf_Internal_Shdr *
2cf0635d 589find_section (const char * name)
89fac5e3
RS
590{
591 unsigned int i;
592
593 for (i = 0; i < elf_header.e_shnum; i++)
594 if (streq (SECTION_NAME (section_headers + i), name))
595 return section_headers + i;
596
597 return NULL;
598}
599
0b6ae522
DJ
600/* Return a pointer to a section containing ADDR, or NULL if no such
601 section exists. */
602
603static Elf_Internal_Shdr *
604find_section_by_address (bfd_vma addr)
605{
606 unsigned int i;
607
608 for (i = 0; i < elf_header.e_shnum; i++)
609 {
610 Elf_Internal_Shdr *sec = section_headers + i;
611 if (addr >= sec->sh_addr && addr < sec->sh_addr + sec->sh_size)
612 return sec;
613 }
614
615 return NULL;
616}
617
071436c6
NC
618static Elf_Internal_Shdr *
619find_section_by_type (unsigned int type)
620{
621 unsigned int i;
622
623 for (i = 0; i < elf_header.e_shnum; i++)
624 {
625 Elf_Internal_Shdr *sec = section_headers + i;
626 if (sec->sh_type == type)
627 return sec;
628 }
629
630 return NULL;
631}
632
657d0d47
CC
633/* Return a pointer to section NAME, or NULL if no such section exists,
634 restricted to the list of sections given in SET. */
635
636static Elf_Internal_Shdr *
637find_section_in_set (const char * name, unsigned int * set)
638{
639 unsigned int i;
640
641 if (set != NULL)
642 {
643 while ((i = *set++) > 0)
644 if (streq (SECTION_NAME (section_headers + i), name))
645 return section_headers + i;
646 }
647
648 return find_section (name);
649}
650
0b6ae522
DJ
651/* Read an unsigned LEB128 encoded value from p. Set *PLEN to the number of
652 bytes read. */
653
f6f0e17b
NC
654static inline unsigned long
655read_uleb128 (unsigned char *data,
656 unsigned int *length_return,
657 const unsigned char * const end)
0b6ae522 658{
f6f0e17b 659 return read_leb128 (data, length_return, FALSE, end);
0b6ae522
DJ
660}
661
28f997cf
TG
662/* Return true if the current file is for IA-64 machine and OpenVMS ABI.
663 This OS has so many departures from the ELF standard that we test it at
664 many places. */
665
666static inline int
667is_ia64_vms (void)
668{
669 return elf_header.e_machine == EM_IA_64
670 && elf_header.e_ident[EI_OSABI] == ELFOSABI_OPENVMS;
671}
672
bcedfee6 673/* Guess the relocation size commonly used by the specific machines. */
252b5132 674
252b5132 675static int
2dc4cec1 676guess_is_rela (unsigned int e_machine)
252b5132 677{
9c19a809 678 switch (e_machine)
252b5132
RH
679 {
680 /* Targets that use REL relocations. */
252b5132
RH
681 case EM_386:
682 case EM_486:
63fcb9e9 683 case EM_960:
e9f53129 684 case EM_ARM:
2b0337b0 685 case EM_D10V:
252b5132 686 case EM_CYGNUS_D10V:
e9f53129 687 case EM_DLX:
252b5132 688 case EM_MIPS:
4fe85591 689 case EM_MIPS_RS3_LE:
e9f53129 690 case EM_CYGNUS_M32R:
1c0d3aa6 691 case EM_SCORE:
f6c1a2d5 692 case EM_XGATE:
9c19a809 693 return FALSE;
103f02d3 694
252b5132
RH
695 /* Targets that use RELA relocations. */
696 case EM_68K:
e9f53129 697 case EM_860:
a06ea964 698 case EM_AARCH64:
cfb8c092 699 case EM_ADAPTEVA_EPIPHANY:
e9f53129
AM
700 case EM_ALPHA:
701 case EM_ALTERA_NIOS2:
702 case EM_AVR:
703 case EM_AVR_OLD:
704 case EM_BLACKFIN:
60bca95a 705 case EM_CR16:
e9f53129
AM
706 case EM_CRIS:
707 case EM_CRX:
2b0337b0 708 case EM_D30V:
252b5132 709 case EM_CYGNUS_D30V:
2b0337b0 710 case EM_FR30:
252b5132 711 case EM_CYGNUS_FR30:
5c70f934 712 case EM_CYGNUS_FRV:
e9f53129
AM
713 case EM_H8S:
714 case EM_H8_300:
715 case EM_H8_300H:
800eeca4 716 case EM_IA_64:
1e4cf259
NC
717 case EM_IP2K:
718 case EM_IP2K_OLD:
3b36097d 719 case EM_IQ2000:
84e94c90 720 case EM_LATTICEMICO32:
ff7eeb89 721 case EM_M32C_OLD:
49f58d10 722 case EM_M32C:
e9f53129
AM
723 case EM_M32R:
724 case EM_MCORE:
15ab5209 725 case EM_CYGNUS_MEP:
a3c62988 726 case EM_METAG:
e9f53129
AM
727 case EM_MMIX:
728 case EM_MN10200:
729 case EM_CYGNUS_MN10200:
730 case EM_MN10300:
731 case EM_CYGNUS_MN10300:
5506d11a 732 case EM_MOXIE:
e9f53129
AM
733 case EM_MSP430:
734 case EM_MSP430_OLD:
d031aafb 735 case EM_MT:
35c08157 736 case EM_NDS32:
64fd6348 737 case EM_NIOS32:
73589c9d 738 case EM_OR1K:
e9f53129
AM
739 case EM_PPC64:
740 case EM_PPC:
99c513f6 741 case EM_RL78:
c7927a3c 742 case EM_RX:
e9f53129
AM
743 case EM_S390:
744 case EM_S390_OLD:
745 case EM_SH:
746 case EM_SPARC:
747 case EM_SPARC32PLUS:
748 case EM_SPARCV9:
749 case EM_SPU:
40b36596 750 case EM_TI_C6000:
aa137e4d
NC
751 case EM_TILEGX:
752 case EM_TILEPRO:
708e2187 753 case EM_V800:
e9f53129
AM
754 case EM_V850:
755 case EM_CYGNUS_V850:
756 case EM_VAX:
757 case EM_X86_64:
8a9036a4 758 case EM_L1OM:
7a9068fe 759 case EM_K1OM:
e9f53129
AM
760 case EM_XSTORMY16:
761 case EM_XTENSA:
762 case EM_XTENSA_OLD:
7ba29e2a
NC
763 case EM_MICROBLAZE:
764 case EM_MICROBLAZE_OLD:
9c19a809 765 return TRUE;
103f02d3 766
e9f53129
AM
767 case EM_68HC05:
768 case EM_68HC08:
769 case EM_68HC11:
770 case EM_68HC16:
771 case EM_FX66:
772 case EM_ME16:
d1133906 773 case EM_MMA:
d1133906
NC
774 case EM_NCPU:
775 case EM_NDR1:
e9f53129 776 case EM_PCP:
d1133906 777 case EM_ST100:
e9f53129 778 case EM_ST19:
d1133906 779 case EM_ST7:
e9f53129
AM
780 case EM_ST9PLUS:
781 case EM_STARCORE:
d1133906 782 case EM_SVX:
e9f53129 783 case EM_TINYJ:
9c19a809
NC
784 default:
785 warn (_("Don't know about relocations on this machine architecture\n"));
786 return FALSE;
787 }
788}
252b5132 789
9c19a809 790static int
2cf0635d 791slurp_rela_relocs (FILE * file,
d3ba0551
AM
792 unsigned long rel_offset,
793 unsigned long rel_size,
2cf0635d
NC
794 Elf_Internal_Rela ** relasp,
795 unsigned long * nrelasp)
9c19a809 796{
2cf0635d 797 Elf_Internal_Rela * relas;
8b73c356 798 size_t nrelas;
4d6ed7c8 799 unsigned int i;
252b5132 800
4d6ed7c8
NC
801 if (is_32bit_elf)
802 {
2cf0635d 803 Elf32_External_Rela * erelas;
103f02d3 804
3f5e193b 805 erelas = (Elf32_External_Rela *) get_data (NULL, file, rel_offset, 1,
9cf03b7e 806 rel_size, _("32-bit relocation data"));
a6e9f9df
AM
807 if (!erelas)
808 return 0;
252b5132 809
4d6ed7c8 810 nrelas = rel_size / sizeof (Elf32_External_Rela);
103f02d3 811
3f5e193b
NC
812 relas = (Elf_Internal_Rela *) cmalloc (nrelas,
813 sizeof (Elf_Internal_Rela));
103f02d3 814
4d6ed7c8
NC
815 if (relas == NULL)
816 {
c256ffe7 817 free (erelas);
591a748a 818 error (_("out of memory parsing relocs\n"));
4d6ed7c8
NC
819 return 0;
820 }
103f02d3 821
4d6ed7c8
NC
822 for (i = 0; i < nrelas; i++)
823 {
824 relas[i].r_offset = BYTE_GET (erelas[i].r_offset);
825 relas[i].r_info = BYTE_GET (erelas[i].r_info);
598aaa76 826 relas[i].r_addend = BYTE_GET_SIGNED (erelas[i].r_addend);
4d6ed7c8 827 }
103f02d3 828
4d6ed7c8
NC
829 free (erelas);
830 }
831 else
832 {
2cf0635d 833 Elf64_External_Rela * erelas;
103f02d3 834
3f5e193b 835 erelas = (Elf64_External_Rela *) get_data (NULL, file, rel_offset, 1,
9cf03b7e 836 rel_size, _("64-bit relocation data"));
a6e9f9df
AM
837 if (!erelas)
838 return 0;
4d6ed7c8
NC
839
840 nrelas = rel_size / sizeof (Elf64_External_Rela);
103f02d3 841
3f5e193b
NC
842 relas = (Elf_Internal_Rela *) cmalloc (nrelas,
843 sizeof (Elf_Internal_Rela));
103f02d3 844
4d6ed7c8
NC
845 if (relas == NULL)
846 {
c256ffe7 847 free (erelas);
591a748a 848 error (_("out of memory parsing relocs\n"));
4d6ed7c8 849 return 0;
9c19a809 850 }
4d6ed7c8
NC
851
852 for (i = 0; i < nrelas; i++)
9c19a809 853 {
66543521
AM
854 relas[i].r_offset = BYTE_GET (erelas[i].r_offset);
855 relas[i].r_info = BYTE_GET (erelas[i].r_info);
598aaa76 856 relas[i].r_addend = BYTE_GET_SIGNED (erelas[i].r_addend);
861fb55a
DJ
857
858 /* The #ifdef BFD64 below is to prevent a compile time
859 warning. We know that if we do not have a 64 bit data
860 type that we will never execute this code anyway. */
861#ifdef BFD64
862 if (elf_header.e_machine == EM_MIPS
863 && elf_header.e_ident[EI_DATA] != ELFDATA2MSB)
864 {
865 /* In little-endian objects, r_info isn't really a
866 64-bit little-endian value: it has a 32-bit
867 little-endian symbol index followed by four
868 individual byte fields. Reorder INFO
869 accordingly. */
91d6fa6a
NC
870 bfd_vma inf = relas[i].r_info;
871 inf = (((inf & 0xffffffff) << 32)
872 | ((inf >> 56) & 0xff)
873 | ((inf >> 40) & 0xff00)
874 | ((inf >> 24) & 0xff0000)
875 | ((inf >> 8) & 0xff000000));
876 relas[i].r_info = inf;
861fb55a
DJ
877 }
878#endif /* BFD64 */
4d6ed7c8 879 }
103f02d3 880
4d6ed7c8
NC
881 free (erelas);
882 }
883 *relasp = relas;
884 *nrelasp = nrelas;
885 return 1;
886}
103f02d3 887
4d6ed7c8 888static int
2cf0635d 889slurp_rel_relocs (FILE * file,
d3ba0551
AM
890 unsigned long rel_offset,
891 unsigned long rel_size,
2cf0635d
NC
892 Elf_Internal_Rela ** relsp,
893 unsigned long * nrelsp)
4d6ed7c8 894{
2cf0635d 895 Elf_Internal_Rela * rels;
8b73c356 896 size_t nrels;
4d6ed7c8 897 unsigned int i;
103f02d3 898
4d6ed7c8
NC
899 if (is_32bit_elf)
900 {
2cf0635d 901 Elf32_External_Rel * erels;
103f02d3 902
3f5e193b 903 erels = (Elf32_External_Rel *) get_data (NULL, file, rel_offset, 1,
9cf03b7e 904 rel_size, _("32-bit relocation data"));
a6e9f9df
AM
905 if (!erels)
906 return 0;
103f02d3 907
4d6ed7c8 908 nrels = rel_size / sizeof (Elf32_External_Rel);
103f02d3 909
3f5e193b 910 rels = (Elf_Internal_Rela *) cmalloc (nrels, sizeof (Elf_Internal_Rela));
103f02d3 911
4d6ed7c8
NC
912 if (rels == NULL)
913 {
c256ffe7 914 free (erels);
591a748a 915 error (_("out of memory parsing relocs\n"));
4d6ed7c8
NC
916 return 0;
917 }
918
919 for (i = 0; i < nrels; i++)
920 {
921 rels[i].r_offset = BYTE_GET (erels[i].r_offset);
922 rels[i].r_info = BYTE_GET (erels[i].r_info);
c8286bd1 923 rels[i].r_addend = 0;
9ea033b2 924 }
4d6ed7c8
NC
925
926 free (erels);
9c19a809
NC
927 }
928 else
929 {
2cf0635d 930 Elf64_External_Rel * erels;
9ea033b2 931
3f5e193b 932 erels = (Elf64_External_Rel *) get_data (NULL, file, rel_offset, 1,
9cf03b7e 933 rel_size, _("64-bit relocation data"));
a6e9f9df
AM
934 if (!erels)
935 return 0;
103f02d3 936
4d6ed7c8 937 nrels = rel_size / sizeof (Elf64_External_Rel);
103f02d3 938
3f5e193b 939 rels = (Elf_Internal_Rela *) cmalloc (nrels, sizeof (Elf_Internal_Rela));
103f02d3 940
4d6ed7c8 941 if (rels == NULL)
9c19a809 942 {
c256ffe7 943 free (erels);
591a748a 944 error (_("out of memory parsing relocs\n"));
4d6ed7c8
NC
945 return 0;
946 }
103f02d3 947
4d6ed7c8
NC
948 for (i = 0; i < nrels; i++)
949 {
66543521
AM
950 rels[i].r_offset = BYTE_GET (erels[i].r_offset);
951 rels[i].r_info = BYTE_GET (erels[i].r_info);
c8286bd1 952 rels[i].r_addend = 0;
861fb55a
DJ
953
954 /* The #ifdef BFD64 below is to prevent a compile time
955 warning. We know that if we do not have a 64 bit data
956 type that we will never execute this code anyway. */
957#ifdef BFD64
958 if (elf_header.e_machine == EM_MIPS
959 && elf_header.e_ident[EI_DATA] != ELFDATA2MSB)
960 {
961 /* In little-endian objects, r_info isn't really a
962 64-bit little-endian value: it has a 32-bit
963 little-endian symbol index followed by four
964 individual byte fields. Reorder INFO
965 accordingly. */
91d6fa6a
NC
966 bfd_vma inf = rels[i].r_info;
967 inf = (((inf & 0xffffffff) << 32)
968 | ((inf >> 56) & 0xff)
969 | ((inf >> 40) & 0xff00)
970 | ((inf >> 24) & 0xff0000)
971 | ((inf >> 8) & 0xff000000));
972 rels[i].r_info = inf;
861fb55a
DJ
973 }
974#endif /* BFD64 */
4d6ed7c8 975 }
103f02d3 976
4d6ed7c8
NC
977 free (erels);
978 }
979 *relsp = rels;
980 *nrelsp = nrels;
981 return 1;
982}
103f02d3 983
aca88567
NC
984/* Returns the reloc type extracted from the reloc info field. */
985
986static unsigned int
987get_reloc_type (bfd_vma reloc_info)
988{
989 if (is_32bit_elf)
990 return ELF32_R_TYPE (reloc_info);
991
992 switch (elf_header.e_machine)
993 {
994 case EM_MIPS:
995 /* Note: We assume that reloc_info has already been adjusted for us. */
996 return ELF64_MIPS_R_TYPE (reloc_info);
997
998 case EM_SPARCV9:
999 return ELF64_R_TYPE_ID (reloc_info);
1000
1001 default:
1002 return ELF64_R_TYPE (reloc_info);
1003 }
1004}
1005
1006/* Return the symbol index extracted from the reloc info field. */
1007
1008static bfd_vma
1009get_reloc_symindex (bfd_vma reloc_info)
1010{
1011 return is_32bit_elf ? ELF32_R_SYM (reloc_info) : ELF64_R_SYM (reloc_info);
1012}
1013
13761a11
NC
1014static inline bfd_boolean
1015uses_msp430x_relocs (void)
1016{
1017 return
1018 elf_header.e_machine == EM_MSP430 /* Paranoia. */
1019 /* GCC uses osabi == ELFOSBI_STANDALONE. */
1020 && (((elf_header.e_flags & EF_MSP430_MACH) == E_MSP430_MACH_MSP430X)
1021 /* TI compiler uses ELFOSABI_NONE. */
1022 || (elf_header.e_ident[EI_OSABI] == ELFOSABI_NONE));
1023}
1024
d3ba0551
AM
1025/* Display the contents of the relocation data found at the specified
1026 offset. */
ee42cf8c 1027
41e92641 1028static void
2cf0635d 1029dump_relocations (FILE * file,
d3ba0551
AM
1030 unsigned long rel_offset,
1031 unsigned long rel_size,
2cf0635d 1032 Elf_Internal_Sym * symtab,
d3ba0551 1033 unsigned long nsyms,
2cf0635d 1034 char * strtab,
d79b3d50 1035 unsigned long strtablen,
bb4d2ac2
L
1036 int is_rela,
1037 int is_dynsym)
4d6ed7c8 1038{
b34976b6 1039 unsigned int i;
2cf0635d 1040 Elf_Internal_Rela * rels;
103f02d3 1041
4d6ed7c8
NC
1042 if (is_rela == UNKNOWN)
1043 is_rela = guess_is_rela (elf_header.e_machine);
103f02d3 1044
4d6ed7c8
NC
1045 if (is_rela)
1046 {
c8286bd1 1047 if (!slurp_rela_relocs (file, rel_offset, rel_size, &rels, &rel_size))
41e92641 1048 return;
4d6ed7c8
NC
1049 }
1050 else
1051 {
1052 if (!slurp_rel_relocs (file, rel_offset, rel_size, &rels, &rel_size))
41e92641 1053 return;
252b5132
RH
1054 }
1055
410f7a12
L
1056 if (is_32bit_elf)
1057 {
1058 if (is_rela)
2c71103e
NC
1059 {
1060 if (do_wide)
1061 printf (_(" Offset Info Type Sym. Value Symbol's Name + Addend\n"));
1062 else
1063 printf (_(" Offset Info Type Sym.Value Sym. Name + Addend\n"));
1064 }
410f7a12 1065 else
2c71103e
NC
1066 {
1067 if (do_wide)
1068 printf (_(" Offset Info Type Sym. Value Symbol's Name\n"));
1069 else
1070 printf (_(" Offset Info Type Sym.Value Sym. Name\n"));
1071 }
410f7a12 1072 }
252b5132 1073 else
410f7a12
L
1074 {
1075 if (is_rela)
2c71103e
NC
1076 {
1077 if (do_wide)
8beeaeb7 1078 printf (_(" Offset Info Type Symbol's Value Symbol's Name + Addend\n"));
2c71103e
NC
1079 else
1080 printf (_(" Offset Info Type Sym. Value Sym. Name + Addend\n"));
1081 }
410f7a12 1082 else
2c71103e
NC
1083 {
1084 if (do_wide)
8beeaeb7 1085 printf (_(" Offset Info Type Symbol's Value Symbol's Name\n"));
2c71103e
NC
1086 else
1087 printf (_(" Offset Info Type Sym. Value Sym. Name\n"));
1088 }
410f7a12 1089 }
252b5132
RH
1090
1091 for (i = 0; i < rel_size; i++)
1092 {
2cf0635d 1093 const char * rtype;
b34976b6 1094 bfd_vma offset;
91d6fa6a 1095 bfd_vma inf;
b34976b6
AM
1096 bfd_vma symtab_index;
1097 bfd_vma type;
103f02d3 1098
b34976b6 1099 offset = rels[i].r_offset;
91d6fa6a 1100 inf = rels[i].r_info;
103f02d3 1101
91d6fa6a
NC
1102 type = get_reloc_type (inf);
1103 symtab_index = get_reloc_symindex (inf);
252b5132 1104
410f7a12
L
1105 if (is_32bit_elf)
1106 {
39dbeff8
AM
1107 printf ("%8.8lx %8.8lx ",
1108 (unsigned long) offset & 0xffffffff,
91d6fa6a 1109 (unsigned long) inf & 0xffffffff);
410f7a12
L
1110 }
1111 else
1112 {
39dbeff8
AM
1113#if BFD_HOST_64BIT_LONG
1114 printf (do_wide
1115 ? "%16.16lx %16.16lx "
1116 : "%12.12lx %12.12lx ",
91d6fa6a 1117 offset, inf);
39dbeff8 1118#elif BFD_HOST_64BIT_LONG_LONG
6e3d6dc1 1119#ifndef __MSVCRT__
39dbeff8
AM
1120 printf (do_wide
1121 ? "%16.16llx %16.16llx "
1122 : "%12.12llx %12.12llx ",
91d6fa6a 1123 offset, inf);
6e3d6dc1
NC
1124#else
1125 printf (do_wide
1126 ? "%16.16I64x %16.16I64x "
1127 : "%12.12I64x %12.12I64x ",
91d6fa6a 1128 offset, inf);
6e3d6dc1 1129#endif
39dbeff8 1130#else
2c71103e
NC
1131 printf (do_wide
1132 ? "%8.8lx%8.8lx %8.8lx%8.8lx "
1133 : "%4.4lx%8.8lx %4.4lx%8.8lx ",
410f7a12
L
1134 _bfd_int64_high (offset),
1135 _bfd_int64_low (offset),
91d6fa6a
NC
1136 _bfd_int64_high (inf),
1137 _bfd_int64_low (inf));
9ea033b2 1138#endif
410f7a12 1139 }
103f02d3 1140
252b5132
RH
1141 switch (elf_header.e_machine)
1142 {
1143 default:
1144 rtype = NULL;
1145 break;
1146
a06ea964
NC
1147 case EM_AARCH64:
1148 rtype = elf_aarch64_reloc_type (type);
1149 break;
1150
2b0337b0 1151 case EM_M32R:
252b5132 1152 case EM_CYGNUS_M32R:
9ea033b2 1153 rtype = elf_m32r_reloc_type (type);
252b5132
RH
1154 break;
1155
1156 case EM_386:
1157 case EM_486:
9ea033b2 1158 rtype = elf_i386_reloc_type (type);
252b5132
RH
1159 break;
1160
ba2685cc
AM
1161 case EM_68HC11:
1162 case EM_68HC12:
1163 rtype = elf_m68hc11_reloc_type (type);
1164 break;
75751cd9 1165
252b5132 1166 case EM_68K:
9ea033b2 1167 rtype = elf_m68k_reloc_type (type);
252b5132
RH
1168 break;
1169
63fcb9e9 1170 case EM_960:
9ea033b2 1171 rtype = elf_i960_reloc_type (type);
63fcb9e9
ILT
1172 break;
1173
adde6300 1174 case EM_AVR:
2b0337b0 1175 case EM_AVR_OLD:
adde6300
AM
1176 rtype = elf_avr_reloc_type (type);
1177 break;
1178
9ea033b2
NC
1179 case EM_OLD_SPARCV9:
1180 case EM_SPARC32PLUS:
1181 case EM_SPARCV9:
252b5132 1182 case EM_SPARC:
9ea033b2 1183 rtype = elf_sparc_reloc_type (type);
252b5132
RH
1184 break;
1185
e9f53129
AM
1186 case EM_SPU:
1187 rtype = elf_spu_reloc_type (type);
1188 break;
1189
708e2187
NC
1190 case EM_V800:
1191 rtype = v800_reloc_type (type);
1192 break;
2b0337b0 1193 case EM_V850:
252b5132 1194 case EM_CYGNUS_V850:
9ea033b2 1195 rtype = v850_reloc_type (type);
252b5132
RH
1196 break;
1197
2b0337b0 1198 case EM_D10V:
252b5132 1199 case EM_CYGNUS_D10V:
9ea033b2 1200 rtype = elf_d10v_reloc_type (type);
252b5132
RH
1201 break;
1202
2b0337b0 1203 case EM_D30V:
252b5132 1204 case EM_CYGNUS_D30V:
9ea033b2 1205 rtype = elf_d30v_reloc_type (type);
252b5132
RH
1206 break;
1207
d172d4ba
NC
1208 case EM_DLX:
1209 rtype = elf_dlx_reloc_type (type);
1210 break;
1211
252b5132 1212 case EM_SH:
9ea033b2 1213 rtype = elf_sh_reloc_type (type);
252b5132
RH
1214 break;
1215
2b0337b0 1216 case EM_MN10300:
252b5132 1217 case EM_CYGNUS_MN10300:
9ea033b2 1218 rtype = elf_mn10300_reloc_type (type);
252b5132
RH
1219 break;
1220
2b0337b0 1221 case EM_MN10200:
252b5132 1222 case EM_CYGNUS_MN10200:
9ea033b2 1223 rtype = elf_mn10200_reloc_type (type);
252b5132
RH
1224 break;
1225
2b0337b0 1226 case EM_FR30:
252b5132 1227 case EM_CYGNUS_FR30:
9ea033b2 1228 rtype = elf_fr30_reloc_type (type);
252b5132
RH
1229 break;
1230
ba2685cc
AM
1231 case EM_CYGNUS_FRV:
1232 rtype = elf_frv_reloc_type (type);
1233 break;
5c70f934 1234
252b5132 1235 case EM_MCORE:
9ea033b2 1236 rtype = elf_mcore_reloc_type (type);
252b5132
RH
1237 break;
1238
3c3bdf30
NC
1239 case EM_MMIX:
1240 rtype = elf_mmix_reloc_type (type);
1241 break;
1242
5506d11a
AM
1243 case EM_MOXIE:
1244 rtype = elf_moxie_reloc_type (type);
1245 break;
1246
2469cfa2 1247 case EM_MSP430:
13761a11
NC
1248 if (uses_msp430x_relocs ())
1249 {
1250 rtype = elf_msp430x_reloc_type (type);
1251 break;
1252 }
2469cfa2
NC
1253 case EM_MSP430_OLD:
1254 rtype = elf_msp430_reloc_type (type);
1255 break;
1256
35c08157
KLC
1257 case EM_NDS32:
1258 rtype = elf_nds32_reloc_type (type);
1259 break;
1260
252b5132 1261 case EM_PPC:
9ea033b2 1262 rtype = elf_ppc_reloc_type (type);
252b5132
RH
1263 break;
1264
c833c019
AM
1265 case EM_PPC64:
1266 rtype = elf_ppc64_reloc_type (type);
1267 break;
1268
252b5132 1269 case EM_MIPS:
4fe85591 1270 case EM_MIPS_RS3_LE:
9ea033b2 1271 rtype = elf_mips_reloc_type (type);
252b5132
RH
1272 break;
1273
1274 case EM_ALPHA:
9ea033b2 1275 rtype = elf_alpha_reloc_type (type);
252b5132
RH
1276 break;
1277
1278 case EM_ARM:
9ea033b2 1279 rtype = elf_arm_reloc_type (type);
252b5132
RH
1280 break;
1281
584da044 1282 case EM_ARC:
9ea033b2 1283 rtype = elf_arc_reloc_type (type);
252b5132
RH
1284 break;
1285
1286 case EM_PARISC:
69e617ca 1287 rtype = elf_hppa_reloc_type (type);
252b5132 1288 break;
7d466069 1289
b8720f9d
JL
1290 case EM_H8_300:
1291 case EM_H8_300H:
1292 case EM_H8S:
1293 rtype = elf_h8_reloc_type (type);
1294 break;
1295
73589c9d
CS
1296 case EM_OR1K:
1297 rtype = elf_or1k_reloc_type (type);
3b16e843
NC
1298 break;
1299
7d466069 1300 case EM_PJ:
2b0337b0 1301 case EM_PJ_OLD:
7d466069
ILT
1302 rtype = elf_pj_reloc_type (type);
1303 break;
800eeca4
JW
1304 case EM_IA_64:
1305 rtype = elf_ia64_reloc_type (type);
1306 break;
1b61cf92
HPN
1307
1308 case EM_CRIS:
1309 rtype = elf_cris_reloc_type (type);
1310 break;
535c37ff
JE
1311
1312 case EM_860:
1313 rtype = elf_i860_reloc_type (type);
1314 break;
bcedfee6
NC
1315
1316 case EM_X86_64:
8a9036a4 1317 case EM_L1OM:
7a9068fe 1318 case EM_K1OM:
bcedfee6
NC
1319 rtype = elf_x86_64_reloc_type (type);
1320 break;
a85d7ed0 1321
35b1837e
AM
1322 case EM_S370:
1323 rtype = i370_reloc_type (type);
1324 break;
1325
53c7db4b
KH
1326 case EM_S390_OLD:
1327 case EM_S390:
1328 rtype = elf_s390_reloc_type (type);
1329 break;
93fbbb04 1330
1c0d3aa6
NC
1331 case EM_SCORE:
1332 rtype = elf_score_reloc_type (type);
1333 break;
1334
93fbbb04
GK
1335 case EM_XSTORMY16:
1336 rtype = elf_xstormy16_reloc_type (type);
1337 break;
179d3252 1338
1fe1f39c
NC
1339 case EM_CRX:
1340 rtype = elf_crx_reloc_type (type);
1341 break;
1342
179d3252
JT
1343 case EM_VAX:
1344 rtype = elf_vax_reloc_type (type);
1345 break;
1e4cf259 1346
cfb8c092
NC
1347 case EM_ADAPTEVA_EPIPHANY:
1348 rtype = elf_epiphany_reloc_type (type);
1349 break;
1350
1e4cf259
NC
1351 case EM_IP2K:
1352 case EM_IP2K_OLD:
1353 rtype = elf_ip2k_reloc_type (type);
1354 break;
3b36097d
SC
1355
1356 case EM_IQ2000:
1357 rtype = elf_iq2000_reloc_type (type);
1358 break;
88da6820
NC
1359
1360 case EM_XTENSA_OLD:
1361 case EM_XTENSA:
1362 rtype = elf_xtensa_reloc_type (type);
1363 break;
a34e3ecb 1364
84e94c90
NC
1365 case EM_LATTICEMICO32:
1366 rtype = elf_lm32_reloc_type (type);
1367 break;
1368
ff7eeb89 1369 case EM_M32C_OLD:
49f58d10
JB
1370 case EM_M32C:
1371 rtype = elf_m32c_reloc_type (type);
1372 break;
1373
d031aafb
NS
1374 case EM_MT:
1375 rtype = elf_mt_reloc_type (type);
a34e3ecb 1376 break;
1d65ded4
CM
1377
1378 case EM_BLACKFIN:
1379 rtype = elf_bfin_reloc_type (type);
1380 break;
15ab5209
DB
1381
1382 case EM_CYGNUS_MEP:
1383 rtype = elf_mep_reloc_type (type);
1384 break;
60bca95a
NC
1385
1386 case EM_CR16:
1387 rtype = elf_cr16_reloc_type (type);
1388 break;
dd24e3da 1389
7ba29e2a
NC
1390 case EM_MICROBLAZE:
1391 case EM_MICROBLAZE_OLD:
1392 rtype = elf_microblaze_reloc_type (type);
1393 break;
c7927a3c 1394
99c513f6
DD
1395 case EM_RL78:
1396 rtype = elf_rl78_reloc_type (type);
1397 break;
1398
c7927a3c
NC
1399 case EM_RX:
1400 rtype = elf_rx_reloc_type (type);
1401 break;
c29aca4a 1402
a3c62988
NC
1403 case EM_METAG:
1404 rtype = elf_metag_reloc_type (type);
1405 break;
1406
c29aca4a
NC
1407 case EM_XC16X:
1408 case EM_C166:
1409 rtype = elf_xc16x_reloc_type (type);
1410 break;
40b36596
JM
1411
1412 case EM_TI_C6000:
1413 rtype = elf_tic6x_reloc_type (type);
1414 break;
aa137e4d
NC
1415
1416 case EM_TILEGX:
1417 rtype = elf_tilegx_reloc_type (type);
1418 break;
1419
1420 case EM_TILEPRO:
1421 rtype = elf_tilepro_reloc_type (type);
1422 break;
f6c1a2d5
NC
1423
1424 case EM_XGATE:
1425 rtype = elf_xgate_reloc_type (type);
1426 break;
36591ba1
SL
1427
1428 case EM_ALTERA_NIOS2:
1429 rtype = elf_nios2_reloc_type (type);
1430 break;
252b5132
RH
1431 }
1432
1433 if (rtype == NULL)
39dbeff8 1434 printf (_("unrecognized: %-7lx"), (unsigned long) type & 0xffffffff);
252b5132 1435 else
8beeaeb7 1436 printf (do_wide ? "%-22.22s" : "%-17.17s", rtype);
252b5132 1437
7ace3541 1438 if (elf_header.e_machine == EM_ALPHA
157c2599 1439 && rtype != NULL
7ace3541
RH
1440 && streq (rtype, "R_ALPHA_LITUSE")
1441 && is_rela)
1442 {
1443 switch (rels[i].r_addend)
1444 {
1445 case LITUSE_ALPHA_ADDR: rtype = "ADDR"; break;
1446 case LITUSE_ALPHA_BASE: rtype = "BASE"; break;
1447 case LITUSE_ALPHA_BYTOFF: rtype = "BYTOFF"; break;
1448 case LITUSE_ALPHA_JSR: rtype = "JSR"; break;
1449 case LITUSE_ALPHA_TLSGD: rtype = "TLSGD"; break;
1450 case LITUSE_ALPHA_TLSLDM: rtype = "TLSLDM"; break;
1451 case LITUSE_ALPHA_JSRDIRECT: rtype = "JSRDIRECT"; break;
1452 default: rtype = NULL;
1453 }
1454 if (rtype)
1455 printf (" (%s)", rtype);
1456 else
1457 {
1458 putchar (' ');
1459 printf (_("<unknown addend: %lx>"),
1460 (unsigned long) rels[i].r_addend);
1461 }
1462 }
1463 else if (symtab_index)
252b5132 1464 {
af3fc3bc 1465 if (symtab == NULL || symtab_index >= nsyms)
2b692964 1466 printf (_(" bad symbol index: %08lx"), (unsigned long) symtab_index);
af3fc3bc 1467 else
19936277 1468 {
2cf0635d 1469 Elf_Internal_Sym * psym;
bb4d2ac2
L
1470 const char * version_string;
1471 enum versioned_symbol_info sym_info;
1472 unsigned short vna_other;
19936277 1473
af3fc3bc 1474 psym = symtab + symtab_index;
103f02d3 1475
bb4d2ac2
L
1476 version_string
1477 = get_symbol_version_string (file, is_dynsym,
1478 strtab, strtablen,
1479 symtab_index,
1480 psym,
1481 &sym_info,
1482 &vna_other);
1483
af3fc3bc 1484 printf (" ");
171191ba 1485
d8045f23
NC
1486 if (ELF_ST_TYPE (psym->st_info) == STT_GNU_IFUNC)
1487 {
1488 const char * name;
1489 unsigned int len;
1490 unsigned int width = is_32bit_elf ? 8 : 14;
1491
1492 /* Relocations against GNU_IFUNC symbols do not use the value
1493 of the symbol as the address to relocate against. Instead
1494 they invoke the function named by the symbol and use its
1495 result as the address for relocation.
1496
1497 To indicate this to the user, do not display the value of
1498 the symbol in the "Symbols's Value" field. Instead show
1499 its name followed by () as a hint that the symbol is
1500 invoked. */
1501
1502 if (strtab == NULL
1503 || psym->st_name == 0
1504 || psym->st_name >= strtablen)
1505 name = "??";
1506 else
1507 name = strtab + psym->st_name;
1508
1509 len = print_symbol (width, name);
bb4d2ac2
L
1510 if (version_string)
1511 printf (sym_info == symbol_public ? "@@%s" : "@%s",
1512 version_string);
d8045f23
NC
1513 printf ("()%-*s", len <= width ? (width + 1) - len : 1, " ");
1514 }
1515 else
1516 {
1517 print_vma (psym->st_value, LONG_HEX);
171191ba 1518
d8045f23
NC
1519 printf (is_32bit_elf ? " " : " ");
1520 }
103f02d3 1521
af3fc3bc 1522 if (psym->st_name == 0)
f1ef08cb 1523 {
2cf0635d 1524 const char * sec_name = "<null>";
f1ef08cb
AM
1525 char name_buf[40];
1526
1527 if (ELF_ST_TYPE (psym->st_info) == STT_SECTION)
1528 {
4fbb74a6 1529 if (psym->st_shndx < elf_header.e_shnum)
74e1a04b 1530 sec_name = SECTION_NAME (section_headers + psym->st_shndx);
f1ef08cb
AM
1531 else if (psym->st_shndx == SHN_ABS)
1532 sec_name = "ABS";
1533 else if (psym->st_shndx == SHN_COMMON)
1534 sec_name = "COMMON";
ac145307
BS
1535 else if ((elf_header.e_machine == EM_MIPS
1536 && psym->st_shndx == SHN_MIPS_SCOMMON)
1537 || (elf_header.e_machine == EM_TI_C6000
1538 && psym->st_shndx == SHN_TIC6X_SCOMMON))
172553c7
TS
1539 sec_name = "SCOMMON";
1540 else if (elf_header.e_machine == EM_MIPS
1541 && psym->st_shndx == SHN_MIPS_SUNDEFINED)
1542 sec_name = "SUNDEF";
8a9036a4 1543 else if ((elf_header.e_machine == EM_X86_64
7a9068fe
L
1544 || elf_header.e_machine == EM_L1OM
1545 || elf_header.e_machine == EM_K1OM)
3b22753a
L
1546 && psym->st_shndx == SHN_X86_64_LCOMMON)
1547 sec_name = "LARGE_COMMON";
9ce701e2
L
1548 else if (elf_header.e_machine == EM_IA_64
1549 && elf_header.e_ident[EI_OSABI] == ELFOSABI_HPUX
1550 && psym->st_shndx == SHN_IA_64_ANSI_COMMON)
1551 sec_name = "ANSI_COM";
28f997cf 1552 else if (is_ia64_vms ()
148b93f2
NC
1553 && psym->st_shndx == SHN_IA_64_VMS_SYMVEC)
1554 sec_name = "VMS_SYMVEC";
f1ef08cb
AM
1555 else
1556 {
1557 sprintf (name_buf, "<section 0x%x>",
1558 (unsigned int) psym->st_shndx);
1559 sec_name = name_buf;
1560 }
1561 }
1562 print_symbol (22, sec_name);
1563 }
af3fc3bc 1564 else if (strtab == NULL)
d79b3d50 1565 printf (_("<string table index: %3ld>"), psym->st_name);
c256ffe7 1566 else if (psym->st_name >= strtablen)
d79b3d50 1567 printf (_("<corrupt string table index: %3ld>"), psym->st_name);
af3fc3bc 1568 else
bb4d2ac2
L
1569 {
1570 print_symbol (22, strtab + psym->st_name);
1571 if (version_string)
1572 printf (sym_info == symbol_public ? "@@%s" : "@%s",
1573 version_string);
1574 }
103f02d3 1575
af3fc3bc 1576 if (is_rela)
171191ba 1577 {
598aaa76 1578 bfd_signed_vma off = rels[i].r_addend;
171191ba 1579
91d6fa6a 1580 if (off < 0)
598aaa76 1581 printf (" - %" BFD_VMA_FMT "x", - off);
171191ba 1582 else
598aaa76 1583 printf (" + %" BFD_VMA_FMT "x", off);
171191ba 1584 }
19936277 1585 }
252b5132 1586 }
1b228002 1587 else if (is_rela)
f7a99963 1588 {
e04d7088
L
1589 bfd_signed_vma off = rels[i].r_addend;
1590
1591 printf ("%*c", is_32bit_elf ? 12 : 20, ' ');
1592 if (off < 0)
1593 printf ("-%" BFD_VMA_FMT "x", - off);
1594 else
1595 printf ("%" BFD_VMA_FMT "x", off);
f7a99963 1596 }
252b5132 1597
157c2599
NC
1598 if (elf_header.e_machine == EM_SPARCV9
1599 && rtype != NULL
1600 && streq (rtype, "R_SPARC_OLO10"))
91d6fa6a 1601 printf (" + %lx", (unsigned long) ELF64_R_TYPE_DATA (inf));
351b4b40 1602
252b5132 1603 putchar ('\n');
2c71103e 1604
aca88567 1605#ifdef BFD64
53c7db4b 1606 if (! is_32bit_elf && elf_header.e_machine == EM_MIPS)
2c71103e 1607 {
91d6fa6a
NC
1608 bfd_vma type2 = ELF64_MIPS_R_TYPE2 (inf);
1609 bfd_vma type3 = ELF64_MIPS_R_TYPE3 (inf);
2cf0635d
NC
1610 const char * rtype2 = elf_mips_reloc_type (type2);
1611 const char * rtype3 = elf_mips_reloc_type (type3);
aca88567 1612
2c71103e
NC
1613 printf (" Type2: ");
1614
1615 if (rtype2 == NULL)
39dbeff8
AM
1616 printf (_("unrecognized: %-7lx"),
1617 (unsigned long) type2 & 0xffffffff);
2c71103e
NC
1618 else
1619 printf ("%-17.17s", rtype2);
1620
18bd398b 1621 printf ("\n Type3: ");
2c71103e
NC
1622
1623 if (rtype3 == NULL)
39dbeff8
AM
1624 printf (_("unrecognized: %-7lx"),
1625 (unsigned long) type3 & 0xffffffff);
2c71103e
NC
1626 else
1627 printf ("%-17.17s", rtype3);
1628
53c7db4b 1629 putchar ('\n');
2c71103e 1630 }
aca88567 1631#endif /* BFD64 */
252b5132
RH
1632 }
1633
c8286bd1 1634 free (rels);
252b5132
RH
1635}
1636
1637static const char *
d3ba0551 1638get_mips_dynamic_type (unsigned long type)
252b5132
RH
1639{
1640 switch (type)
1641 {
1642 case DT_MIPS_RLD_VERSION: return "MIPS_RLD_VERSION";
1643 case DT_MIPS_TIME_STAMP: return "MIPS_TIME_STAMP";
1644 case DT_MIPS_ICHECKSUM: return "MIPS_ICHECKSUM";
1645 case DT_MIPS_IVERSION: return "MIPS_IVERSION";
1646 case DT_MIPS_FLAGS: return "MIPS_FLAGS";
1647 case DT_MIPS_BASE_ADDRESS: return "MIPS_BASE_ADDRESS";
1648 case DT_MIPS_MSYM: return "MIPS_MSYM";
1649 case DT_MIPS_CONFLICT: return "MIPS_CONFLICT";
1650 case DT_MIPS_LIBLIST: return "MIPS_LIBLIST";
1651 case DT_MIPS_LOCAL_GOTNO: return "MIPS_LOCAL_GOTNO";
1652 case DT_MIPS_CONFLICTNO: return "MIPS_CONFLICTNO";
1653 case DT_MIPS_LIBLISTNO: return "MIPS_LIBLISTNO";
1654 case DT_MIPS_SYMTABNO: return "MIPS_SYMTABNO";
1655 case DT_MIPS_UNREFEXTNO: return "MIPS_UNREFEXTNO";
1656 case DT_MIPS_GOTSYM: return "MIPS_GOTSYM";
1657 case DT_MIPS_HIPAGENO: return "MIPS_HIPAGENO";
1658 case DT_MIPS_RLD_MAP: return "MIPS_RLD_MAP";
1659 case DT_MIPS_DELTA_CLASS: return "MIPS_DELTA_CLASS";
1660 case DT_MIPS_DELTA_CLASS_NO: return "MIPS_DELTA_CLASS_NO";
1661 case DT_MIPS_DELTA_INSTANCE: return "MIPS_DELTA_INSTANCE";
1662 case DT_MIPS_DELTA_INSTANCE_NO: return "MIPS_DELTA_INSTANCE_NO";
1663 case DT_MIPS_DELTA_RELOC: return "MIPS_DELTA_RELOC";
1664 case DT_MIPS_DELTA_RELOC_NO: return "MIPS_DELTA_RELOC_NO";
1665 case DT_MIPS_DELTA_SYM: return "MIPS_DELTA_SYM";
1666 case DT_MIPS_DELTA_SYM_NO: return "MIPS_DELTA_SYM_NO";
1667 case DT_MIPS_DELTA_CLASSSYM: return "MIPS_DELTA_CLASSSYM";
1668 case DT_MIPS_DELTA_CLASSSYM_NO: return "MIPS_DELTA_CLASSSYM_NO";
1669 case DT_MIPS_CXX_FLAGS: return "MIPS_CXX_FLAGS";
1670 case DT_MIPS_PIXIE_INIT: return "MIPS_PIXIE_INIT";
1671 case DT_MIPS_SYMBOL_LIB: return "MIPS_SYMBOL_LIB";
1672 case DT_MIPS_LOCALPAGE_GOTIDX: return "MIPS_LOCALPAGE_GOTIDX";
1673 case DT_MIPS_LOCAL_GOTIDX: return "MIPS_LOCAL_GOTIDX";
1674 case DT_MIPS_HIDDEN_GOTIDX: return "MIPS_HIDDEN_GOTIDX";
1675 case DT_MIPS_PROTECTED_GOTIDX: return "MIPS_PROTECTED_GOTIDX";
1676 case DT_MIPS_OPTIONS: return "MIPS_OPTIONS";
1677 case DT_MIPS_INTERFACE: return "MIPS_INTERFACE";
1678 case DT_MIPS_DYNSTR_ALIGN: return "MIPS_DYNSTR_ALIGN";
1679 case DT_MIPS_INTERFACE_SIZE: return "MIPS_INTERFACE_SIZE";
1680 case DT_MIPS_RLD_TEXT_RESOLVE_ADDR: return "MIPS_RLD_TEXT_RESOLVE_ADDR";
1681 case DT_MIPS_PERF_SUFFIX: return "MIPS_PERF_SUFFIX";
1682 case DT_MIPS_COMPACT_SIZE: return "MIPS_COMPACT_SIZE";
1683 case DT_MIPS_GP_VALUE: return "MIPS_GP_VALUE";
1684 case DT_MIPS_AUX_DYNAMIC: return "MIPS_AUX_DYNAMIC";
861fb55a
DJ
1685 case DT_MIPS_PLTGOT: return "MIPS_PLTGOT";
1686 case DT_MIPS_RWPLT: return "MIPS_RWPLT";
252b5132
RH
1687 default:
1688 return NULL;
1689 }
1690}
1691
9a097730 1692static const char *
d3ba0551 1693get_sparc64_dynamic_type (unsigned long type)
9a097730
RH
1694{
1695 switch (type)
1696 {
1697 case DT_SPARC_REGISTER: return "SPARC_REGISTER";
1698 default:
1699 return NULL;
1700 }
103f02d3
UD
1701}
1702
7490d522
AM
1703static const char *
1704get_ppc_dynamic_type (unsigned long type)
1705{
1706 switch (type)
1707 {
a7f2871e 1708 case DT_PPC_GOT: return "PPC_GOT";
e8910a83 1709 case DT_PPC_OPT: return "PPC_OPT";
7490d522
AM
1710 default:
1711 return NULL;
1712 }
1713}
1714
f1cb7e17 1715static const char *
d3ba0551 1716get_ppc64_dynamic_type (unsigned long type)
f1cb7e17
AM
1717{
1718 switch (type)
1719 {
a7f2871e
AM
1720 case DT_PPC64_GLINK: return "PPC64_GLINK";
1721 case DT_PPC64_OPD: return "PPC64_OPD";
1722 case DT_PPC64_OPDSZ: return "PPC64_OPDSZ";
e8910a83 1723 case DT_PPC64_OPT: return "PPC64_OPT";
f1cb7e17
AM
1724 default:
1725 return NULL;
1726 }
1727}
1728
103f02d3 1729static const char *
d3ba0551 1730get_parisc_dynamic_type (unsigned long type)
103f02d3
UD
1731{
1732 switch (type)
1733 {
1734 case DT_HP_LOAD_MAP: return "HP_LOAD_MAP";
1735 case DT_HP_DLD_FLAGS: return "HP_DLD_FLAGS";
1736 case DT_HP_DLD_HOOK: return "HP_DLD_HOOK";
1737 case DT_HP_UX10_INIT: return "HP_UX10_INIT";
1738 case DT_HP_UX10_INITSZ: return "HP_UX10_INITSZ";
1739 case DT_HP_PREINIT: return "HP_PREINIT";
1740 case DT_HP_PREINITSZ: return "HP_PREINITSZ";
1741 case DT_HP_NEEDED: return "HP_NEEDED";
1742 case DT_HP_TIME_STAMP: return "HP_TIME_STAMP";
1743 case DT_HP_CHECKSUM: return "HP_CHECKSUM";
1744 case DT_HP_GST_SIZE: return "HP_GST_SIZE";
1745 case DT_HP_GST_VERSION: return "HP_GST_VERSION";
1746 case DT_HP_GST_HASHVAL: return "HP_GST_HASHVAL";
eec8f817
DA
1747 case DT_HP_EPLTREL: return "HP_GST_EPLTREL";
1748 case DT_HP_EPLTRELSZ: return "HP_GST_EPLTRELSZ";
1749 case DT_HP_FILTERED: return "HP_FILTERED";
1750 case DT_HP_FILTER_TLS: return "HP_FILTER_TLS";
1751 case DT_HP_COMPAT_FILTERED: return "HP_COMPAT_FILTERED";
1752 case DT_HP_LAZYLOAD: return "HP_LAZYLOAD";
1753 case DT_HP_BIND_NOW_COUNT: return "HP_BIND_NOW_COUNT";
1754 case DT_PLT: return "PLT";
1755 case DT_PLT_SIZE: return "PLT_SIZE";
1756 case DT_DLT: return "DLT";
1757 case DT_DLT_SIZE: return "DLT_SIZE";
103f02d3
UD
1758 default:
1759 return NULL;
1760 }
1761}
9a097730 1762
ecc51f48 1763static const char *
d3ba0551 1764get_ia64_dynamic_type (unsigned long type)
ecc51f48
NC
1765{
1766 switch (type)
1767 {
148b93f2
NC
1768 case DT_IA_64_PLT_RESERVE: return "IA_64_PLT_RESERVE";
1769 case DT_IA_64_VMS_SUBTYPE: return "VMS_SUBTYPE";
1770 case DT_IA_64_VMS_IMGIOCNT: return "VMS_IMGIOCNT";
1771 case DT_IA_64_VMS_LNKFLAGS: return "VMS_LNKFLAGS";
1772 case DT_IA_64_VMS_VIR_MEM_BLK_SIZ: return "VMS_VIR_MEM_BLK_SIZ";
1773 case DT_IA_64_VMS_IDENT: return "VMS_IDENT";
1774 case DT_IA_64_VMS_NEEDED_IDENT: return "VMS_NEEDED_IDENT";
1775 case DT_IA_64_VMS_IMG_RELA_CNT: return "VMS_IMG_RELA_CNT";
1776 case DT_IA_64_VMS_SEG_RELA_CNT: return "VMS_SEG_RELA_CNT";
1777 case DT_IA_64_VMS_FIXUP_RELA_CNT: return "VMS_FIXUP_RELA_CNT";
1778 case DT_IA_64_VMS_FIXUP_NEEDED: return "VMS_FIXUP_NEEDED";
1779 case DT_IA_64_VMS_SYMVEC_CNT: return "VMS_SYMVEC_CNT";
1780 case DT_IA_64_VMS_XLATED: return "VMS_XLATED";
1781 case DT_IA_64_VMS_STACKSIZE: return "VMS_STACKSIZE";
1782 case DT_IA_64_VMS_UNWINDSZ: return "VMS_UNWINDSZ";
1783 case DT_IA_64_VMS_UNWIND_CODSEG: return "VMS_UNWIND_CODSEG";
1784 case DT_IA_64_VMS_UNWIND_INFOSEG: return "VMS_UNWIND_INFOSEG";
1785 case DT_IA_64_VMS_LINKTIME: return "VMS_LINKTIME";
1786 case DT_IA_64_VMS_SEG_NO: return "VMS_SEG_NO";
1787 case DT_IA_64_VMS_SYMVEC_OFFSET: return "VMS_SYMVEC_OFFSET";
1788 case DT_IA_64_VMS_SYMVEC_SEG: return "VMS_SYMVEC_SEG";
1789 case DT_IA_64_VMS_UNWIND_OFFSET: return "VMS_UNWIND_OFFSET";
1790 case DT_IA_64_VMS_UNWIND_SEG: return "VMS_UNWIND_SEG";
1791 case DT_IA_64_VMS_STRTAB_OFFSET: return "VMS_STRTAB_OFFSET";
1792 case DT_IA_64_VMS_SYSVER_OFFSET: return "VMS_SYSVER_OFFSET";
1793 case DT_IA_64_VMS_IMG_RELA_OFF: return "VMS_IMG_RELA_OFF";
1794 case DT_IA_64_VMS_SEG_RELA_OFF: return "VMS_SEG_RELA_OFF";
1795 case DT_IA_64_VMS_FIXUP_RELA_OFF: return "VMS_FIXUP_RELA_OFF";
1796 case DT_IA_64_VMS_PLTGOT_OFFSET: return "VMS_PLTGOT_OFFSET";
1797 case DT_IA_64_VMS_PLTGOT_SEG: return "VMS_PLTGOT_SEG";
1798 case DT_IA_64_VMS_FPMODE: return "VMS_FPMODE";
ecc51f48
NC
1799 default:
1800 return NULL;
1801 }
1802}
1803
fabcb361
RH
1804static const char *
1805get_alpha_dynamic_type (unsigned long type)
1806{
1807 switch (type)
1808 {
1809 case DT_ALPHA_PLTRO: return "ALPHA_PLTRO";
1810 default:
1811 return NULL;
1812 }
1813}
1814
1c0d3aa6
NC
1815static const char *
1816get_score_dynamic_type (unsigned long type)
1817{
1818 switch (type)
1819 {
1820 case DT_SCORE_BASE_ADDRESS: return "SCORE_BASE_ADDRESS";
1821 case DT_SCORE_LOCAL_GOTNO: return "SCORE_LOCAL_GOTNO";
1822 case DT_SCORE_SYMTABNO: return "SCORE_SYMTABNO";
1823 case DT_SCORE_GOTSYM: return "SCORE_GOTSYM";
1824 case DT_SCORE_UNREFEXTNO: return "SCORE_UNREFEXTNO";
1825 case DT_SCORE_HIPAGENO: return "SCORE_HIPAGENO";
1826 default:
1827 return NULL;
1828 }
1829}
1830
40b36596
JM
1831static const char *
1832get_tic6x_dynamic_type (unsigned long type)
1833{
1834 switch (type)
1835 {
1836 case DT_C6000_GSYM_OFFSET: return "C6000_GSYM_OFFSET";
1837 case DT_C6000_GSTR_OFFSET: return "C6000_GSTR_OFFSET";
1838 case DT_C6000_DSBT_BASE: return "C6000_DSBT_BASE";
1839 case DT_C6000_DSBT_SIZE: return "C6000_DSBT_SIZE";
1840 case DT_C6000_PREEMPTMAP: return "C6000_PREEMPTMAP";
1841 case DT_C6000_DSBT_INDEX: return "C6000_DSBT_INDEX";
1842 default:
1843 return NULL;
1844 }
1845}
1c0d3aa6 1846
36591ba1
SL
1847static const char *
1848get_nios2_dynamic_type (unsigned long type)
1849{
1850 switch (type)
1851 {
1852 case DT_NIOS2_GP: return "NIOS2_GP";
1853 default:
1854 return NULL;
1855 }
1856}
1857
252b5132 1858static const char *
d3ba0551 1859get_dynamic_type (unsigned long type)
252b5132 1860{
e9e44622 1861 static char buff[64];
252b5132
RH
1862
1863 switch (type)
1864 {
1865 case DT_NULL: return "NULL";
1866 case DT_NEEDED: return "NEEDED";
1867 case DT_PLTRELSZ: return "PLTRELSZ";
1868 case DT_PLTGOT: return "PLTGOT";
1869 case DT_HASH: return "HASH";
1870 case DT_STRTAB: return "STRTAB";
1871 case DT_SYMTAB: return "SYMTAB";
1872 case DT_RELA: return "RELA";
1873 case DT_RELASZ: return "RELASZ";
1874 case DT_RELAENT: return "RELAENT";
1875 case DT_STRSZ: return "STRSZ";
1876 case DT_SYMENT: return "SYMENT";
1877 case DT_INIT: return "INIT";
1878 case DT_FINI: return "FINI";
1879 case DT_SONAME: return "SONAME";
1880 case DT_RPATH: return "RPATH";
1881 case DT_SYMBOLIC: return "SYMBOLIC";
1882 case DT_REL: return "REL";
1883 case DT_RELSZ: return "RELSZ";
1884 case DT_RELENT: return "RELENT";
1885 case DT_PLTREL: return "PLTREL";
1886 case DT_DEBUG: return "DEBUG";
1887 case DT_TEXTREL: return "TEXTREL";
1888 case DT_JMPREL: return "JMPREL";
1889 case DT_BIND_NOW: return "BIND_NOW";
1890 case DT_INIT_ARRAY: return "INIT_ARRAY";
1891 case DT_FINI_ARRAY: return "FINI_ARRAY";
1892 case DT_INIT_ARRAYSZ: return "INIT_ARRAYSZ";
1893 case DT_FINI_ARRAYSZ: return "FINI_ARRAYSZ";
d1133906
NC
1894 case DT_RUNPATH: return "RUNPATH";
1895 case DT_FLAGS: return "FLAGS";
2d0e6f43 1896
d1133906
NC
1897 case DT_PREINIT_ARRAY: return "PREINIT_ARRAY";
1898 case DT_PREINIT_ARRAYSZ: return "PREINIT_ARRAYSZ";
103f02d3 1899
05107a46 1900 case DT_CHECKSUM: return "CHECKSUM";
252b5132
RH
1901 case DT_PLTPADSZ: return "PLTPADSZ";
1902 case DT_MOVEENT: return "MOVEENT";
1903 case DT_MOVESZ: return "MOVESZ";
dcefbbbd 1904 case DT_FEATURE: return "FEATURE";
252b5132
RH
1905 case DT_POSFLAG_1: return "POSFLAG_1";
1906 case DT_SYMINSZ: return "SYMINSZ";
1907 case DT_SYMINENT: return "SYMINENT"; /* aka VALRNGHI */
103f02d3 1908
252b5132 1909 case DT_ADDRRNGLO: return "ADDRRNGLO";
dcefbbbd
L
1910 case DT_CONFIG: return "CONFIG";
1911 case DT_DEPAUDIT: return "DEPAUDIT";
1912 case DT_AUDIT: return "AUDIT";
1913 case DT_PLTPAD: return "PLTPAD";
1914 case DT_MOVETAB: return "MOVETAB";
252b5132 1915 case DT_SYMINFO: return "SYMINFO"; /* aka ADDRRNGHI */
103f02d3 1916
252b5132 1917 case DT_VERSYM: return "VERSYM";
103f02d3 1918
67a4f2b7
AO
1919 case DT_TLSDESC_GOT: return "TLSDESC_GOT";
1920 case DT_TLSDESC_PLT: return "TLSDESC_PLT";
252b5132
RH
1921 case DT_RELACOUNT: return "RELACOUNT";
1922 case DT_RELCOUNT: return "RELCOUNT";
1923 case DT_FLAGS_1: return "FLAGS_1";
1924 case DT_VERDEF: return "VERDEF";
1925 case DT_VERDEFNUM: return "VERDEFNUM";
1926 case DT_VERNEED: return "VERNEED";
1927 case DT_VERNEEDNUM: return "VERNEEDNUM";
103f02d3 1928
019148e4 1929 case DT_AUXILIARY: return "AUXILIARY";
252b5132
RH
1930 case DT_USED: return "USED";
1931 case DT_FILTER: return "FILTER";
103f02d3 1932
047b2264
JJ
1933 case DT_GNU_PRELINKED: return "GNU_PRELINKED";
1934 case DT_GNU_CONFLICT: return "GNU_CONFLICT";
1935 case DT_GNU_CONFLICTSZ: return "GNU_CONFLICTSZ";
1936 case DT_GNU_LIBLIST: return "GNU_LIBLIST";
1937 case DT_GNU_LIBLISTSZ: return "GNU_LIBLISTSZ";
fdc90cb4 1938 case DT_GNU_HASH: return "GNU_HASH";
047b2264 1939
252b5132
RH
1940 default:
1941 if ((type >= DT_LOPROC) && (type <= DT_HIPROC))
1942 {
2cf0635d 1943 const char * result;
103f02d3 1944
252b5132
RH
1945 switch (elf_header.e_machine)
1946 {
1947 case EM_MIPS:
4fe85591 1948 case EM_MIPS_RS3_LE:
252b5132
RH
1949 result = get_mips_dynamic_type (type);
1950 break;
9a097730
RH
1951 case EM_SPARCV9:
1952 result = get_sparc64_dynamic_type (type);
1953 break;
7490d522
AM
1954 case EM_PPC:
1955 result = get_ppc_dynamic_type (type);
1956 break;
f1cb7e17
AM
1957 case EM_PPC64:
1958 result = get_ppc64_dynamic_type (type);
1959 break;
ecc51f48
NC
1960 case EM_IA_64:
1961 result = get_ia64_dynamic_type (type);
1962 break;
fabcb361
RH
1963 case EM_ALPHA:
1964 result = get_alpha_dynamic_type (type);
1965 break;
1c0d3aa6
NC
1966 case EM_SCORE:
1967 result = get_score_dynamic_type (type);
1968 break;
40b36596
JM
1969 case EM_TI_C6000:
1970 result = get_tic6x_dynamic_type (type);
1971 break;
36591ba1
SL
1972 case EM_ALTERA_NIOS2:
1973 result = get_nios2_dynamic_type (type);
1974 break;
252b5132
RH
1975 default:
1976 result = NULL;
1977 break;
1978 }
1979
1980 if (result != NULL)
1981 return result;
1982
e9e44622 1983 snprintf (buff, sizeof (buff), _("Processor Specific: %lx"), type);
252b5132 1984 }
eec8f817
DA
1985 else if (((type >= DT_LOOS) && (type <= DT_HIOS))
1986 || (elf_header.e_machine == EM_PARISC
1987 && (type >= OLD_DT_LOOS) && (type <= OLD_DT_HIOS)))
103f02d3 1988 {
2cf0635d 1989 const char * result;
103f02d3
UD
1990
1991 switch (elf_header.e_machine)
1992 {
1993 case EM_PARISC:
1994 result = get_parisc_dynamic_type (type);
1995 break;
148b93f2
NC
1996 case EM_IA_64:
1997 result = get_ia64_dynamic_type (type);
1998 break;
103f02d3
UD
1999 default:
2000 result = NULL;
2001 break;
2002 }
2003
2004 if (result != NULL)
2005 return result;
2006
e9e44622
JJ
2007 snprintf (buff, sizeof (buff), _("Operating System specific: %lx"),
2008 type);
103f02d3 2009 }
252b5132 2010 else
e9e44622 2011 snprintf (buff, sizeof (buff), _("<unknown>: %lx"), type);
103f02d3 2012
252b5132
RH
2013 return buff;
2014 }
2015}
2016
2017static char *
d3ba0551 2018get_file_type (unsigned e_type)
252b5132 2019{
b34976b6 2020 static char buff[32];
252b5132
RH
2021
2022 switch (e_type)
2023 {
2024 case ET_NONE: return _("NONE (None)");
2025 case ET_REL: return _("REL (Relocatable file)");
ba2685cc
AM
2026 case ET_EXEC: return _("EXEC (Executable file)");
2027 case ET_DYN: return _("DYN (Shared object file)");
2028 case ET_CORE: return _("CORE (Core file)");
252b5132
RH
2029
2030 default:
2031 if ((e_type >= ET_LOPROC) && (e_type <= ET_HIPROC))
e9e44622 2032 snprintf (buff, sizeof (buff), _("Processor Specific: (%x)"), e_type);
252b5132 2033 else if ((e_type >= ET_LOOS) && (e_type <= ET_HIOS))
e9e44622 2034 snprintf (buff, sizeof (buff), _("OS Specific: (%x)"), e_type);
252b5132 2035 else
e9e44622 2036 snprintf (buff, sizeof (buff), _("<unknown>: %x"), e_type);
252b5132
RH
2037 return buff;
2038 }
2039}
2040
2041static char *
d3ba0551 2042get_machine_name (unsigned e_machine)
252b5132 2043{
b34976b6 2044 static char buff[64]; /* XXX */
252b5132
RH
2045
2046 switch (e_machine)
2047 {
c45021f2 2048 case EM_NONE: return _("None");
a06ea964 2049 case EM_AARCH64: return "AArch64";
c45021f2
NC
2050 case EM_M32: return "WE32100";
2051 case EM_SPARC: return "Sparc";
e9f53129 2052 case EM_SPU: return "SPU";
c45021f2
NC
2053 case EM_386: return "Intel 80386";
2054 case EM_68K: return "MC68000";
2055 case EM_88K: return "MC88000";
2056 case EM_486: return "Intel 80486";
2057 case EM_860: return "Intel 80860";
2058 case EM_MIPS: return "MIPS R3000";
2059 case EM_S370: return "IBM System/370";
7036c0e1 2060 case EM_MIPS_RS3_LE: return "MIPS R4000 big-endian";
252b5132 2061 case EM_OLD_SPARCV9: return "Sparc v9 (old)";
c45021f2 2062 case EM_PARISC: return "HPPA";
252b5132 2063 case EM_PPC_OLD: return "Power PC (old)";
7036c0e1 2064 case EM_SPARC32PLUS: return "Sparc v8+" ;
c45021f2
NC
2065 case EM_960: return "Intel 90860";
2066 case EM_PPC: return "PowerPC";
285d1771 2067 case EM_PPC64: return "PowerPC64";
c45021f2
NC
2068 case EM_FR20: return "Fujitsu FR20";
2069 case EM_RH32: return "TRW RH32";
b34976b6 2070 case EM_MCORE: return "MCORE";
7036c0e1
AJ
2071 case EM_ARM: return "ARM";
2072 case EM_OLD_ALPHA: return "Digital Alpha (old)";
ef230218 2073 case EM_SH: return "Renesas / SuperH SH";
c45021f2
NC
2074 case EM_SPARCV9: return "Sparc v9";
2075 case EM_TRICORE: return "Siemens Tricore";
584da044 2076 case EM_ARC: return "ARC";
c2dcd04e
NC
2077 case EM_H8_300: return "Renesas H8/300";
2078 case EM_H8_300H: return "Renesas H8/300H";
2079 case EM_H8S: return "Renesas H8S";
2080 case EM_H8_500: return "Renesas H8/500";
30800947 2081 case EM_IA_64: return "Intel IA-64";
252b5132
RH
2082 case EM_MIPS_X: return "Stanford MIPS-X";
2083 case EM_COLDFIRE: return "Motorola Coldfire";
c45021f2 2084 case EM_ALPHA: return "Alpha";
2b0337b0
AO
2085 case EM_CYGNUS_D10V:
2086 case EM_D10V: return "d10v";
2087 case EM_CYGNUS_D30V:
b34976b6 2088 case EM_D30V: return "d30v";
2b0337b0 2089 case EM_CYGNUS_M32R:
26597c86 2090 case EM_M32R: return "Renesas M32R (formerly Mitsubishi M32r)";
2b0337b0 2091 case EM_CYGNUS_V850:
708e2187 2092 case EM_V800: return "Renesas V850 (using RH850 ABI)";
f6c1a2d5 2093 case EM_V850: return "Renesas V850";
2b0337b0
AO
2094 case EM_CYGNUS_MN10300:
2095 case EM_MN10300: return "mn10300";
2096 case EM_CYGNUS_MN10200:
2097 case EM_MN10200: return "mn10200";
5506d11a 2098 case EM_MOXIE: return "Moxie";
2b0337b0
AO
2099 case EM_CYGNUS_FR30:
2100 case EM_FR30: return "Fujitsu FR30";
b34976b6 2101 case EM_CYGNUS_FRV: return "Fujitsu FR-V";
2b0337b0 2102 case EM_PJ_OLD:
b34976b6 2103 case EM_PJ: return "picoJava";
7036c0e1
AJ
2104 case EM_MMA: return "Fujitsu Multimedia Accelerator";
2105 case EM_PCP: return "Siemens PCP";
2106 case EM_NCPU: return "Sony nCPU embedded RISC processor";
2107 case EM_NDR1: return "Denso NDR1 microprocesspr";
2108 case EM_STARCORE: return "Motorola Star*Core processor";
2109 case EM_ME16: return "Toyota ME16 processor";
2110 case EM_ST100: return "STMicroelectronics ST100 processor";
2111 case EM_TINYJ: return "Advanced Logic Corp. TinyJ embedded processor";
11636f9e
JM
2112 case EM_PDSP: return "Sony DSP processor";
2113 case EM_PDP10: return "Digital Equipment Corp. PDP-10";
2114 case EM_PDP11: return "Digital Equipment Corp. PDP-11";
7036c0e1
AJ
2115 case EM_FX66: return "Siemens FX66 microcontroller";
2116 case EM_ST9PLUS: return "STMicroelectronics ST9+ 8/16 bit microcontroller";
2117 case EM_ST7: return "STMicroelectronics ST7 8-bit microcontroller";
2118 case EM_68HC16: return "Motorola MC68HC16 Microcontroller";
6927f982 2119 case EM_68HC12: return "Motorola MC68HC12 Microcontroller";
7036c0e1
AJ
2120 case EM_68HC11: return "Motorola MC68HC11 Microcontroller";
2121 case EM_68HC08: return "Motorola MC68HC08 Microcontroller";
2122 case EM_68HC05: return "Motorola MC68HC05 Microcontroller";
2123 case EM_SVX: return "Silicon Graphics SVx";
2124 case EM_ST19: return "STMicroelectronics ST19 8-bit microcontroller";
2125 case EM_VAX: return "Digital VAX";
2b0337b0 2126 case EM_AVR_OLD:
b34976b6 2127 case EM_AVR: return "Atmel AVR 8-bit microcontroller";
1b61cf92 2128 case EM_CRIS: return "Axis Communications 32-bit embedded processor";
c45021f2
NC
2129 case EM_JAVELIN: return "Infineon Technologies 32-bit embedded cpu";
2130 case EM_FIREPATH: return "Element 14 64-bit DSP processor";
2131 case EM_ZSP: return "LSI Logic's 16-bit DSP processor";
b34976b6 2132 case EM_MMIX: return "Donald Knuth's educational 64-bit processor";
c45021f2 2133 case EM_HUANY: return "Harvard Universitys's machine-independent object format";
3b36097d 2134 case EM_PRISM: return "Vitesse Prism";
bcedfee6 2135 case EM_X86_64: return "Advanced Micro Devices X86-64";
8a9036a4 2136 case EM_L1OM: return "Intel L1OM";
7a9068fe 2137 case EM_K1OM: return "Intel K1OM";
b7498e0e 2138 case EM_S390_OLD:
b34976b6 2139 case EM_S390: return "IBM S/390";
1c0d3aa6 2140 case EM_SCORE: return "SUNPLUS S+Core";
61865e30 2141 case EM_XSTORMY16: return "Sanyo XStormy16 CPU core";
73589c9d 2142 case EM_OR1K: return "OpenRISC 1000";
11636f9e 2143 case EM_ARC_A5: return "ARC International ARCompact processor";
1fe1f39c 2144 case EM_CRX: return "National Semiconductor CRX microprocessor";
cfb8c092 2145 case EM_ADAPTEVA_EPIPHANY: return "Adapteva EPIPHANY";
d172d4ba 2146 case EM_DLX: return "OpenDLX";
1e4cf259 2147 case EM_IP2K_OLD:
b34976b6 2148 case EM_IP2K: return "Ubicom IP2xxx 8-bit microcontrollers";
3b36097d 2149 case EM_IQ2000: return "Vitesse IQ2000";
88da6820
NC
2150 case EM_XTENSA_OLD:
2151 case EM_XTENSA: return "Tensilica Xtensa Processor";
11636f9e
JM
2152 case EM_VIDEOCORE: return "Alphamosaic VideoCore processor";
2153 case EM_TMM_GPP: return "Thompson Multimedia General Purpose Processor";
2154 case EM_NS32K: return "National Semiconductor 32000 series";
2155 case EM_TPC: return "Tenor Network TPC processor";
2156 case EM_ST200: return "STMicroelectronics ST200 microcontroller";
2157 case EM_MAX: return "MAX Processor";
2158 case EM_CR: return "National Semiconductor CompactRISC";
2159 case EM_F2MC16: return "Fujitsu F2MC16";
2160 case EM_MSP430: return "Texas Instruments msp430 microcontroller";
84e94c90 2161 case EM_LATTICEMICO32: return "Lattice Mico32";
ff7eeb89 2162 case EM_M32C_OLD:
49f58d10 2163 case EM_M32C: return "Renesas M32c";
d031aafb 2164 case EM_MT: return "Morpho Techologies MT processor";
7bbe5bc5 2165 case EM_BLACKFIN: return "Analog Devices Blackfin";
11636f9e
JM
2166 case EM_SE_C33: return "S1C33 Family of Seiko Epson processors";
2167 case EM_SEP: return "Sharp embedded microprocessor";
2168 case EM_ARCA: return "Arca RISC microprocessor";
2169 case EM_UNICORE: return "Unicore";
2170 case EM_EXCESS: return "eXcess 16/32/64-bit configurable embedded CPU";
2171 case EM_DXP: return "Icera Semiconductor Inc. Deep Execution Processor";
64fd6348
NC
2172 case EM_NIOS32: return "Altera Nios";
2173 case EM_ALTERA_NIOS2: return "Altera Nios II";
c29aca4a 2174 case EM_C166:
d70c5fc7 2175 case EM_XC16X: return "Infineon Technologies xc16x";
11636f9e
JM
2176 case EM_M16C: return "Renesas M16C series microprocessors";
2177 case EM_DSPIC30F: return "Microchip Technology dsPIC30F Digital Signal Controller";
2178 case EM_CE: return "Freescale Communication Engine RISC core";
2179 case EM_TSK3000: return "Altium TSK3000 core";
2180 case EM_RS08: return "Freescale RS08 embedded processor";
2181 case EM_ECOG2: return "Cyan Technology eCOG2 microprocessor";
2182 case EM_DSP24: return "New Japan Radio (NJR) 24-bit DSP Processor";
2183 case EM_VIDEOCORE3: return "Broadcom VideoCore III processor";
2184 case EM_SE_C17: return "Seiko Epson C17 family";
2185 case EM_TI_C6000: return "Texas Instruments TMS320C6000 DSP family";
2186 case EM_TI_C2000: return "Texas Instruments TMS320C2000 DSP family";
2187 case EM_TI_C5500: return "Texas Instruments TMS320C55x DSP family";
2188 case EM_MMDSP_PLUS: return "STMicroelectronics 64bit VLIW Data Signal Processor";
2189 case EM_CYPRESS_M8C: return "Cypress M8C microprocessor";
2190 case EM_R32C: return "Renesas R32C series microprocessors";
2191 case EM_TRIMEDIA: return "NXP Semiconductors TriMedia architecture family";
2192 case EM_QDSP6: return "QUALCOMM DSP6 Processor";
2193 case EM_8051: return "Intel 8051 and variants";
2194 case EM_STXP7X: return "STMicroelectronics STxP7x family";
2195 case EM_NDS32: return "Andes Technology compact code size embedded RISC processor family";
2196 case EM_ECOG1X: return "Cyan Technology eCOG1X family";
2197 case EM_MAXQ30: return "Dallas Semiconductor MAXQ30 Core microcontrollers";
2198 case EM_XIMO16: return "New Japan Radio (NJR) 16-bit DSP Processor";
2199 case EM_MANIK: return "M2000 Reconfigurable RISC Microprocessor";
2200 case EM_CRAYNV2: return "Cray Inc. NV2 vector architecture";
15ab5209 2201 case EM_CYGNUS_MEP: return "Toshiba MeP Media Engine";
cb8f3167 2202 case EM_CR16:
f6c1a2d5 2203 case EM_MICROBLAZE:
7ba29e2a 2204 case EM_MICROBLAZE_OLD: return "Xilinx MicroBlaze";
99c513f6 2205 case EM_RL78: return "Renesas RL78";
c7927a3c 2206 case EM_RX: return "Renesas RX";
a3c62988 2207 case EM_METAG: return "Imagination Technologies Meta processor architecture";
11636f9e
JM
2208 case EM_MCST_ELBRUS: return "MCST Elbrus general purpose hardware architecture";
2209 case EM_ECOG16: return "Cyan Technology eCOG16 family";
2210 case EM_ETPU: return "Freescale Extended Time Processing Unit";
2211 case EM_SLE9X: return "Infineon Technologies SLE9X core";
2212 case EM_AVR32: return "Atmel Corporation 32-bit microprocessor family";
2213 case EM_STM8: return "STMicroeletronics STM8 8-bit microcontroller";
2214 case EM_TILE64: return "Tilera TILE64 multicore architecture family";
2215 case EM_TILEPRO: return "Tilera TILEPro multicore architecture family";
aa137e4d 2216 case EM_TILEGX: return "Tilera TILE-Gx multicore architecture family";
11636f9e 2217 case EM_CUDA: return "NVIDIA CUDA architecture";
f6c1a2d5 2218 case EM_XGATE: return "Motorola XGATE embedded processor";
252b5132 2219 default:
35d9dd2f 2220 snprintf (buff, sizeof (buff), _("<unknown>: 0x%x"), e_machine);
252b5132
RH
2221 return buff;
2222 }
2223}
2224
f3485b74 2225static void
d3ba0551 2226decode_ARM_machine_flags (unsigned e_flags, char buf[])
f3485b74
NC
2227{
2228 unsigned eabi;
2229 int unknown = 0;
2230
2231 eabi = EF_ARM_EABI_VERSION (e_flags);
2232 e_flags &= ~ EF_ARM_EABIMASK;
2233
2234 /* Handle "generic" ARM flags. */
2235 if (e_flags & EF_ARM_RELEXEC)
2236 {
2237 strcat (buf, ", relocatable executable");
2238 e_flags &= ~ EF_ARM_RELEXEC;
2239 }
76da6bbe 2240
f3485b74
NC
2241 if (e_flags & EF_ARM_HASENTRY)
2242 {
2243 strcat (buf, ", has entry point");
2244 e_flags &= ~ EF_ARM_HASENTRY;
2245 }
76da6bbe 2246
f3485b74
NC
2247 /* Now handle EABI specific flags. */
2248 switch (eabi)
2249 {
2250 default:
2c71103e 2251 strcat (buf, ", <unrecognized EABI>");
f3485b74
NC
2252 if (e_flags)
2253 unknown = 1;
2254 break;
2255
2256 case EF_ARM_EABI_VER1:
a5bcd848 2257 strcat (buf, ", Version1 EABI");
f3485b74
NC
2258 while (e_flags)
2259 {
2260 unsigned flag;
76da6bbe 2261
f3485b74
NC
2262 /* Process flags one bit at a time. */
2263 flag = e_flags & - e_flags;
2264 e_flags &= ~ flag;
76da6bbe 2265
f3485b74
NC
2266 switch (flag)
2267 {
a5bcd848 2268 case EF_ARM_SYMSARESORTED: /* Conflicts with EF_ARM_INTERWORK. */
f3485b74
NC
2269 strcat (buf, ", sorted symbol tables");
2270 break;
76da6bbe 2271
f3485b74
NC
2272 default:
2273 unknown = 1;
2274 break;
2275 }
2276 }
2277 break;
76da6bbe 2278
a5bcd848
PB
2279 case EF_ARM_EABI_VER2:
2280 strcat (buf, ", Version2 EABI");
2281 while (e_flags)
2282 {
2283 unsigned flag;
2284
2285 /* Process flags one bit at a time. */
2286 flag = e_flags & - e_flags;
2287 e_flags &= ~ flag;
2288
2289 switch (flag)
2290 {
2291 case EF_ARM_SYMSARESORTED: /* Conflicts with EF_ARM_INTERWORK. */
2292 strcat (buf, ", sorted symbol tables");
2293 break;
2294
2295 case EF_ARM_DYNSYMSUSESEGIDX:
2296 strcat (buf, ", dynamic symbols use segment index");
2297 break;
2298
2299 case EF_ARM_MAPSYMSFIRST:
2300 strcat (buf, ", mapping symbols precede others");
2301 break;
2302
2303 default:
2304 unknown = 1;
2305 break;
2306 }
2307 }
2308 break;
2309
d507cf36
PB
2310 case EF_ARM_EABI_VER3:
2311 strcat (buf, ", Version3 EABI");
8cb51566
PB
2312 break;
2313
2314 case EF_ARM_EABI_VER4:
2315 strcat (buf, ", Version4 EABI");
3bfcb652
NC
2316 while (e_flags)
2317 {
2318 unsigned flag;
2319
2320 /* Process flags one bit at a time. */
2321 flag = e_flags & - e_flags;
2322 e_flags &= ~ flag;
2323
2324 switch (flag)
2325 {
2326 case EF_ARM_BE8:
2327 strcat (buf, ", BE8");
2328 break;
2329
2330 case EF_ARM_LE8:
2331 strcat (buf, ", LE8");
2332 break;
2333
2334 default:
2335 unknown = 1;
2336 break;
2337 }
2338 break;
2339 }
2340 break;
3a4a14e9
PB
2341
2342 case EF_ARM_EABI_VER5:
2343 strcat (buf, ", Version5 EABI");
d507cf36
PB
2344 while (e_flags)
2345 {
2346 unsigned flag;
2347
2348 /* Process flags one bit at a time. */
2349 flag = e_flags & - e_flags;
2350 e_flags &= ~ flag;
2351
2352 switch (flag)
2353 {
2354 case EF_ARM_BE8:
2355 strcat (buf, ", BE8");
2356 break;
2357
2358 case EF_ARM_LE8:
2359 strcat (buf, ", LE8");
2360 break;
2361
3bfcb652
NC
2362 case EF_ARM_ABI_FLOAT_SOFT: /* Conflicts with EF_ARM_SOFT_FLOAT. */
2363 strcat (buf, ", soft-float ABI");
2364 break;
2365
2366 case EF_ARM_ABI_FLOAT_HARD: /* Conflicts with EF_ARM_VFP_FLOAT. */
2367 strcat (buf, ", hard-float ABI");
2368 break;
2369
d507cf36
PB
2370 default:
2371 unknown = 1;
2372 break;
2373 }
2374 }
2375 break;
2376
f3485b74 2377 case EF_ARM_EABI_UNKNOWN:
a5bcd848 2378 strcat (buf, ", GNU EABI");
f3485b74
NC
2379 while (e_flags)
2380 {
2381 unsigned flag;
76da6bbe 2382
f3485b74
NC
2383 /* Process flags one bit at a time. */
2384 flag = e_flags & - e_flags;
2385 e_flags &= ~ flag;
76da6bbe 2386
f3485b74
NC
2387 switch (flag)
2388 {
a5bcd848 2389 case EF_ARM_INTERWORK:
f3485b74
NC
2390 strcat (buf, ", interworking enabled");
2391 break;
76da6bbe 2392
a5bcd848 2393 case EF_ARM_APCS_26:
f3485b74
NC
2394 strcat (buf, ", uses APCS/26");
2395 break;
76da6bbe 2396
a5bcd848 2397 case EF_ARM_APCS_FLOAT:
f3485b74
NC
2398 strcat (buf, ", uses APCS/float");
2399 break;
76da6bbe 2400
a5bcd848 2401 case EF_ARM_PIC:
f3485b74
NC
2402 strcat (buf, ", position independent");
2403 break;
76da6bbe 2404
a5bcd848 2405 case EF_ARM_ALIGN8:
f3485b74
NC
2406 strcat (buf, ", 8 bit structure alignment");
2407 break;
76da6bbe 2408
a5bcd848 2409 case EF_ARM_NEW_ABI:
f3485b74
NC
2410 strcat (buf, ", uses new ABI");
2411 break;
76da6bbe 2412
a5bcd848 2413 case EF_ARM_OLD_ABI:
f3485b74
NC
2414 strcat (buf, ", uses old ABI");
2415 break;
76da6bbe 2416
a5bcd848 2417 case EF_ARM_SOFT_FLOAT:
f3485b74
NC
2418 strcat (buf, ", software FP");
2419 break;
76da6bbe 2420
90e01f86
ILT
2421 case EF_ARM_VFP_FLOAT:
2422 strcat (buf, ", VFP");
2423 break;
2424
fde78edd
NC
2425 case EF_ARM_MAVERICK_FLOAT:
2426 strcat (buf, ", Maverick FP");
2427 break;
2428
f3485b74
NC
2429 default:
2430 unknown = 1;
2431 break;
2432 }
2433 }
2434 }
f3485b74
NC
2435
2436 if (unknown)
2b692964 2437 strcat (buf,_(", <unknown>"));
f3485b74
NC
2438}
2439
343433df
AB
2440static void
2441decode_AVR_machine_flags (unsigned e_flags, char buf[], size_t size)
2442{
2443 --size; /* Leave space for null terminator. */
2444
2445 switch (e_flags & EF_AVR_MACH)
2446 {
2447 case E_AVR_MACH_AVR1:
2448 strncat (buf, ", avr:1", size);
2449 break;
2450 case E_AVR_MACH_AVR2:
2451 strncat (buf, ", avr:2", size);
2452 break;
2453 case E_AVR_MACH_AVR25:
2454 strncat (buf, ", avr:25", size);
2455 break;
2456 case E_AVR_MACH_AVR3:
2457 strncat (buf, ", avr:3", size);
2458 break;
2459 case E_AVR_MACH_AVR31:
2460 strncat (buf, ", avr:31", size);
2461 break;
2462 case E_AVR_MACH_AVR35:
2463 strncat (buf, ", avr:35", size);
2464 break;
2465 case E_AVR_MACH_AVR4:
2466 strncat (buf, ", avr:4", size);
2467 break;
2468 case E_AVR_MACH_AVR5:
2469 strncat (buf, ", avr:5", size);
2470 break;
2471 case E_AVR_MACH_AVR51:
2472 strncat (buf, ", avr:51", size);
2473 break;
2474 case E_AVR_MACH_AVR6:
2475 strncat (buf, ", avr:6", size);
2476 break;
2477 case E_AVR_MACH_AVRTINY:
2478 strncat (buf, ", avr:100", size);
2479 break;
2480 case E_AVR_MACH_XMEGA1:
2481 strncat (buf, ", avr:101", size);
2482 break;
2483 case E_AVR_MACH_XMEGA2:
2484 strncat (buf, ", avr:102", size);
2485 break;
2486 case E_AVR_MACH_XMEGA3:
2487 strncat (buf, ", avr:103", size);
2488 break;
2489 case E_AVR_MACH_XMEGA4:
2490 strncat (buf, ", avr:104", size);
2491 break;
2492 case E_AVR_MACH_XMEGA5:
2493 strncat (buf, ", avr:105", size);
2494 break;
2495 case E_AVR_MACH_XMEGA6:
2496 strncat (buf, ", avr:106", size);
2497 break;
2498 case E_AVR_MACH_XMEGA7:
2499 strncat (buf, ", avr:107", size);
2500 break;
2501 default:
2502 strncat (buf, ", avr:<unknown>", size);
2503 break;
2504 }
2505
2506 size -= strlen (buf);
2507 if (e_flags & EF_AVR_LINKRELAX_PREPARED)
2508 strncat (buf, ", link-relax", size);
2509}
2510
35c08157
KLC
2511static void
2512decode_NDS32_machine_flags (unsigned e_flags, char buf[], size_t size)
2513{
2514 unsigned abi;
2515 unsigned arch;
2516 unsigned config;
2517 unsigned version;
2518 int has_fpu = 0;
2519 int r = 0;
2520
2521 static const char *ABI_STRINGS[] =
2522 {
2523 "ABI v0", /* use r5 as return register; only used in N1213HC */
2524 "ABI v1", /* use r0 as return register */
2525 "ABI v2", /* use r0 as return register and don't reserve 24 bytes for arguments */
2526 "ABI v2fp", /* for FPU */
40c7a7cb
KLC
2527 "AABI",
2528 "ABI2 FP+"
35c08157
KLC
2529 };
2530 static const char *VER_STRINGS[] =
2531 {
2532 "Andes ELF V1.3 or older",
2533 "Andes ELF V1.3.1",
2534 "Andes ELF V1.4"
2535 };
2536 static const char *ARCH_STRINGS[] =
2537 {
2538 "",
2539 "Andes Star v1.0",
2540 "Andes Star v2.0",
2541 "Andes Star v3.0",
2542 "Andes Star v3.0m"
2543 };
2544
2545 abi = EF_NDS_ABI & e_flags;
2546 arch = EF_NDS_ARCH & e_flags;
2547 config = EF_NDS_INST & e_flags;
2548 version = EF_NDS32_ELF_VERSION & e_flags;
2549
2550 memset (buf, 0, size);
2551
2552 switch (abi)
2553 {
2554 case E_NDS_ABI_V0:
2555 case E_NDS_ABI_V1:
2556 case E_NDS_ABI_V2:
2557 case E_NDS_ABI_V2FP:
2558 case E_NDS_ABI_AABI:
40c7a7cb 2559 case E_NDS_ABI_V2FP_PLUS:
35c08157
KLC
2560 /* In case there are holes in the array. */
2561 r += snprintf (buf + r, size - r, ", %s", ABI_STRINGS[abi >> EF_NDS_ABI_SHIFT]);
2562 break;
2563
2564 default:
2565 r += snprintf (buf + r, size - r, ", <unrecognized ABI>");
2566 break;
2567 }
2568
2569 switch (version)
2570 {
2571 case E_NDS32_ELF_VER_1_2:
2572 case E_NDS32_ELF_VER_1_3:
2573 case E_NDS32_ELF_VER_1_4:
2574 r += snprintf (buf + r, size - r, ", %s", VER_STRINGS[version >> EF_NDS32_ELF_VERSION_SHIFT]);
2575 break;
2576
2577 default:
2578 r += snprintf (buf + r, size - r, ", <unrecognized ELF version number>");
2579 break;
2580 }
2581
2582 if (E_NDS_ABI_V0 == abi)
2583 {
2584 /* OLD ABI; only used in N1213HC, has performance extension 1. */
2585 r += snprintf (buf + r, size - r, ", Andes Star v1.0, N1213HC, MAC, PERF1");
2586 if (arch == E_NDS_ARCH_STAR_V1_0)
2587 r += snprintf (buf + r, size -r, ", 16b"); /* has 16-bit instructions */
2588 return;
2589 }
2590
2591 switch (arch)
2592 {
2593 case E_NDS_ARCH_STAR_V1_0:
2594 case E_NDS_ARCH_STAR_V2_0:
2595 case E_NDS_ARCH_STAR_V3_0:
2596 case E_NDS_ARCH_STAR_V3_M:
2597 r += snprintf (buf + r, size - r, ", %s", ARCH_STRINGS[arch >> EF_NDS_ARCH_SHIFT]);
2598 break;
2599
2600 default:
2601 r += snprintf (buf + r, size - r, ", <unrecognized architecture>");
2602 /* ARCH version determines how the e_flags are interpreted.
2603 If it is unknown, we cannot proceed. */
2604 return;
2605 }
2606
2607 /* Newer ABI; Now handle architecture specific flags. */
2608 if (arch == E_NDS_ARCH_STAR_V1_0)
2609 {
2610 if (config & E_NDS32_HAS_MFUSR_PC_INST)
2611 r += snprintf (buf + r, size -r, ", MFUSR_PC");
2612
2613 if (!(config & E_NDS32_HAS_NO_MAC_INST))
2614 r += snprintf (buf + r, size -r, ", MAC");
2615
2616 if (config & E_NDS32_HAS_DIV_INST)
2617 r += snprintf (buf + r, size -r, ", DIV");
2618
2619 if (config & E_NDS32_HAS_16BIT_INST)
2620 r += snprintf (buf + r, size -r, ", 16b");
2621 }
2622 else
2623 {
2624 if (config & E_NDS32_HAS_MFUSR_PC_INST)
2625 {
2626 if (version <= E_NDS32_ELF_VER_1_3)
2627 r += snprintf (buf + r, size -r, ", [B8]");
2628 else
2629 r += snprintf (buf + r, size -r, ", EX9");
2630 }
2631
2632 if (config & E_NDS32_HAS_MAC_DX_INST)
2633 r += snprintf (buf + r, size -r, ", MAC_DX");
2634
2635 if (config & E_NDS32_HAS_DIV_DX_INST)
2636 r += snprintf (buf + r, size -r, ", DIV_DX");
2637
2638 if (config & E_NDS32_HAS_16BIT_INST)
2639 {
2640 if (version <= E_NDS32_ELF_VER_1_3)
2641 r += snprintf (buf + r, size -r, ", 16b");
2642 else
2643 r += snprintf (buf + r, size -r, ", IFC");
2644 }
2645 }
2646
2647 if (config & E_NDS32_HAS_EXT_INST)
2648 r += snprintf (buf + r, size -r, ", PERF1");
2649
2650 if (config & E_NDS32_HAS_EXT2_INST)
2651 r += snprintf (buf + r, size -r, ", PERF2");
2652
2653 if (config & E_NDS32_HAS_FPU_INST)
2654 {
2655 has_fpu = 1;
2656 r += snprintf (buf + r, size -r, ", FPU_SP");
2657 }
2658
2659 if (config & E_NDS32_HAS_FPU_DP_INST)
2660 {
2661 has_fpu = 1;
2662 r += snprintf (buf + r, size -r, ", FPU_DP");
2663 }
2664
2665 if (config & E_NDS32_HAS_FPU_MAC_INST)
2666 {
2667 has_fpu = 1;
2668 r += snprintf (buf + r, size -r, ", FPU_MAC");
2669 }
2670
2671 if (has_fpu)
2672 {
2673 switch ((config & E_NDS32_FPU_REG_CONF) >> E_NDS32_FPU_REG_CONF_SHIFT)
2674 {
2675 case E_NDS32_FPU_REG_8SP_4DP:
2676 r += snprintf (buf + r, size -r, ", FPU_REG:8/4");
2677 break;
2678 case E_NDS32_FPU_REG_16SP_8DP:
2679 r += snprintf (buf + r, size -r, ", FPU_REG:16/8");
2680 break;
2681 case E_NDS32_FPU_REG_32SP_16DP:
2682 r += snprintf (buf + r, size -r, ", FPU_REG:32/16");
2683 break;
2684 case E_NDS32_FPU_REG_32SP_32DP:
2685 r += snprintf (buf + r, size -r, ", FPU_REG:32/32");
2686 break;
2687 }
2688 }
2689
2690 if (config & E_NDS32_HAS_AUDIO_INST)
2691 r += snprintf (buf + r, size -r, ", AUDIO");
2692
2693 if (config & E_NDS32_HAS_STRING_INST)
2694 r += snprintf (buf + r, size -r, ", STR");
2695
2696 if (config & E_NDS32_HAS_REDUCED_REGS)
2697 r += snprintf (buf + r, size -r, ", 16REG");
2698
2699 if (config & E_NDS32_HAS_VIDEO_INST)
2700 {
2701 if (version <= E_NDS32_ELF_VER_1_3)
2702 r += snprintf (buf + r, size -r, ", VIDEO");
2703 else
2704 r += snprintf (buf + r, size -r, ", SATURATION");
2705 }
2706
2707 if (config & E_NDS32_HAS_ENCRIPT_INST)
2708 r += snprintf (buf + r, size -r, ", ENCRP");
2709
2710 if (config & E_NDS32_HAS_L2C_INST)
2711 r += snprintf (buf + r, size -r, ", L2C");
2712}
2713
252b5132 2714static char *
d3ba0551 2715get_machine_flags (unsigned e_flags, unsigned e_machine)
252b5132 2716{
b34976b6 2717 static char buf[1024];
252b5132
RH
2718
2719 buf[0] = '\0';
76da6bbe 2720
252b5132
RH
2721 if (e_flags)
2722 {
2723 switch (e_machine)
2724 {
2725 default:
2726 break;
2727
f3485b74
NC
2728 case EM_ARM:
2729 decode_ARM_machine_flags (e_flags, buf);
2730 break;
76da6bbe 2731
343433df
AB
2732 case EM_AVR:
2733 decode_AVR_machine_flags (e_flags, buf, sizeof buf);
2734 break;
2735
781303ce
MF
2736 case EM_BLACKFIN:
2737 if (e_flags & EF_BFIN_PIC)
2738 strcat (buf, ", PIC");
2739
2740 if (e_flags & EF_BFIN_FDPIC)
2741 strcat (buf, ", FDPIC");
2742
2743 if (e_flags & EF_BFIN_CODE_IN_L1)
2744 strcat (buf, ", code in L1");
2745
2746 if (e_flags & EF_BFIN_DATA_IN_L1)
2747 strcat (buf, ", data in L1");
2748
2749 break;
2750
ec2dfb42
AO
2751 case EM_CYGNUS_FRV:
2752 switch (e_flags & EF_FRV_CPU_MASK)
2753 {
2754 case EF_FRV_CPU_GENERIC:
2755 break;
2756
2757 default:
2758 strcat (buf, ", fr???");
2759 break;
57346661 2760
ec2dfb42
AO
2761 case EF_FRV_CPU_FR300:
2762 strcat (buf, ", fr300");
2763 break;
2764
2765 case EF_FRV_CPU_FR400:
2766 strcat (buf, ", fr400");
2767 break;
2768 case EF_FRV_CPU_FR405:
2769 strcat (buf, ", fr405");
2770 break;
2771
2772 case EF_FRV_CPU_FR450:
2773 strcat (buf, ", fr450");
2774 break;
2775
2776 case EF_FRV_CPU_FR500:
2777 strcat (buf, ", fr500");
2778 break;
2779 case EF_FRV_CPU_FR550:
2780 strcat (buf, ", fr550");
2781 break;
2782
2783 case EF_FRV_CPU_SIMPLE:
2784 strcat (buf, ", simple");
2785 break;
2786 case EF_FRV_CPU_TOMCAT:
2787 strcat (buf, ", tomcat");
2788 break;
2789 }
1c877e87 2790 break;
ec2dfb42 2791
53c7db4b 2792 case EM_68K:
425c6cb0 2793 if ((e_flags & EF_M68K_ARCH_MASK) == EF_M68K_M68000)
76f57f3a 2794 strcat (buf, ", m68000");
425c6cb0 2795 else if ((e_flags & EF_M68K_ARCH_MASK) == EF_M68K_CPU32)
3bdcfdf4
KH
2796 strcat (buf, ", cpu32");
2797 else if ((e_flags & EF_M68K_ARCH_MASK) == EF_M68K_FIDO)
2798 strcat (buf, ", fido_a");
425c6cb0 2799 else
266abb8f 2800 {
2cf0635d
NC
2801 char const * isa = _("unknown");
2802 char const * mac = _("unknown mac");
2803 char const * additional = NULL;
0112cd26 2804
c694fd50 2805 switch (e_flags & EF_M68K_CF_ISA_MASK)
266abb8f 2806 {
c694fd50 2807 case EF_M68K_CF_ISA_A_NODIV:
0b2e31dc
NS
2808 isa = "A";
2809 additional = ", nodiv";
2810 break;
c694fd50 2811 case EF_M68K_CF_ISA_A:
266abb8f
NS
2812 isa = "A";
2813 break;
c694fd50 2814 case EF_M68K_CF_ISA_A_PLUS:
266abb8f
NS
2815 isa = "A+";
2816 break;
c694fd50 2817 case EF_M68K_CF_ISA_B_NOUSP:
0b2e31dc
NS
2818 isa = "B";
2819 additional = ", nousp";
2820 break;
c694fd50 2821 case EF_M68K_CF_ISA_B:
266abb8f
NS
2822 isa = "B";
2823 break;
f608cd77
NS
2824 case EF_M68K_CF_ISA_C:
2825 isa = "C";
2826 break;
2827 case EF_M68K_CF_ISA_C_NODIV:
2828 isa = "C";
2829 additional = ", nodiv";
2830 break;
266abb8f
NS
2831 }
2832 strcat (buf, ", cf, isa ");
2833 strcat (buf, isa);
0b2e31dc
NS
2834 if (additional)
2835 strcat (buf, additional);
c694fd50 2836 if (e_flags & EF_M68K_CF_FLOAT)
0b2e31dc 2837 strcat (buf, ", float");
c694fd50 2838 switch (e_flags & EF_M68K_CF_MAC_MASK)
266abb8f
NS
2839 {
2840 case 0:
2841 mac = NULL;
2842 break;
c694fd50 2843 case EF_M68K_CF_MAC:
266abb8f
NS
2844 mac = "mac";
2845 break;
c694fd50 2846 case EF_M68K_CF_EMAC:
266abb8f
NS
2847 mac = "emac";
2848 break;
f608cd77
NS
2849 case EF_M68K_CF_EMAC_B:
2850 mac = "emac_b";
2851 break;
266abb8f
NS
2852 }
2853 if (mac)
2854 {
2855 strcat (buf, ", ");
2856 strcat (buf, mac);
2857 }
266abb8f 2858 }
53c7db4b 2859 break;
33c63f9d 2860
252b5132
RH
2861 case EM_PPC:
2862 if (e_flags & EF_PPC_EMB)
2863 strcat (buf, ", emb");
2864
2865 if (e_flags & EF_PPC_RELOCATABLE)
2b692964 2866 strcat (buf, _(", relocatable"));
252b5132
RH
2867
2868 if (e_flags & EF_PPC_RELOCATABLE_LIB)
2b692964 2869 strcat (buf, _(", relocatable-lib"));
252b5132
RH
2870 break;
2871
ee67d69a
AM
2872 case EM_PPC64:
2873 if (e_flags & EF_PPC64_ABI)
2874 {
2875 char abi[] = ", abiv0";
2876
2877 abi[6] += e_flags & EF_PPC64_ABI;
2878 strcat (buf, abi);
2879 }
2880 break;
2881
708e2187
NC
2882 case EM_V800:
2883 if ((e_flags & EF_RH850_ABI) == EF_RH850_ABI)
2884 strcat (buf, ", RH850 ABI");
0b4362b0 2885
708e2187
NC
2886 if (e_flags & EF_V800_850E3)
2887 strcat (buf, ", V3 architecture");
2888
2889 if ((e_flags & (EF_RH850_FPU_DOUBLE | EF_RH850_FPU_SINGLE)) == 0)
2890 strcat (buf, ", FPU not used");
2891
2892 if ((e_flags & (EF_RH850_REGMODE22 | EF_RH850_REGMODE32)) == 0)
2893 strcat (buf, ", regmode: COMMON");
2894
2895 if ((e_flags & (EF_RH850_GP_FIX | EF_RH850_GP_NOFIX)) == 0)
2896 strcat (buf, ", r4 not used");
2897
2898 if ((e_flags & (EF_RH850_EP_FIX | EF_RH850_EP_NOFIX)) == 0)
2899 strcat (buf, ", r30 not used");
2900
2901 if ((e_flags & (EF_RH850_TP_FIX | EF_RH850_TP_NOFIX)) == 0)
2902 strcat (buf, ", r5 not used");
2903
2904 if ((e_flags & (EF_RH850_REG2_RESERVE | EF_RH850_REG2_NORESERVE)) == 0)
2905 strcat (buf, ", r2 not used");
2906
2907 for (e_flags &= 0xFFFF; e_flags; e_flags &= ~ (e_flags & - e_flags))
2908 {
2909 switch (e_flags & - e_flags)
2910 {
2911 case EF_RH850_FPU_DOUBLE: strcat (buf, ", double precision FPU"); break;
2912 case EF_RH850_FPU_SINGLE: strcat (buf, ", single precision FPU"); break;
2913 case EF_RH850_SIMD: strcat (buf, ", SIMD"); break;
2914 case EF_RH850_CACHE: strcat (buf, ", CACHE"); break;
2915 case EF_RH850_MMU: strcat (buf, ", MMU"); break;
2916 case EF_RH850_REGMODE22: strcat (buf, ", regmode:22"); break;
2917 case EF_RH850_REGMODE32: strcat (buf, ", regmode:23"); break;
2918 case EF_RH850_DATA_ALIGN8: strcat (buf, ", 8-byte alignment"); break;
2919 case EF_RH850_GP_FIX: strcat (buf, ", r4 fixed"); break;
2920 case EF_RH850_GP_NOFIX: strcat (buf, ", r4 free"); break;
2921 case EF_RH850_EP_FIX: strcat (buf, ", r30 fixed"); break;
2922 case EF_RH850_EP_NOFIX: strcat (buf, ", r30 free"); break;
2923 case EF_RH850_TP_FIX: strcat (buf, ", r5 fixed"); break;
2924 case EF_RH850_TP_NOFIX: strcat (buf, ", r5 free"); break;
2925 case EF_RH850_REG2_RESERVE: strcat (buf, ", r2 fixed"); break;
2926 case EF_RH850_REG2_NORESERVE: strcat (buf, ", r2 free"); break;
2927 default: break;
2928 }
2929 }
2930 break;
2931
2b0337b0 2932 case EM_V850:
252b5132
RH
2933 case EM_CYGNUS_V850:
2934 switch (e_flags & EF_V850_ARCH)
2935 {
78c8d46c
NC
2936 case E_V850E3V5_ARCH:
2937 strcat (buf, ", v850e3v5");
2938 break;
1cd986c5
NC
2939 case E_V850E2V3_ARCH:
2940 strcat (buf, ", v850e2v3");
2941 break;
2942 case E_V850E2_ARCH:
2943 strcat (buf, ", v850e2");
2944 break;
2945 case E_V850E1_ARCH:
2946 strcat (buf, ", v850e1");
8ad30312 2947 break;
252b5132
RH
2948 case E_V850E_ARCH:
2949 strcat (buf, ", v850e");
2950 break;
252b5132
RH
2951 case E_V850_ARCH:
2952 strcat (buf, ", v850");
2953 break;
2954 default:
2b692964 2955 strcat (buf, _(", unknown v850 architecture variant"));
252b5132
RH
2956 break;
2957 }
2958 break;
2959
2b0337b0 2960 case EM_M32R:
252b5132
RH
2961 case EM_CYGNUS_M32R:
2962 if ((e_flags & EF_M32R_ARCH) == E_M32R_ARCH)
2963 strcat (buf, ", m32r");
252b5132
RH
2964 break;
2965
2966 case EM_MIPS:
4fe85591 2967 case EM_MIPS_RS3_LE:
252b5132
RH
2968 if (e_flags & EF_MIPS_NOREORDER)
2969 strcat (buf, ", noreorder");
2970
2971 if (e_flags & EF_MIPS_PIC)
2972 strcat (buf, ", pic");
2973
2974 if (e_flags & EF_MIPS_CPIC)
2975 strcat (buf, ", cpic");
2976
d1bdd336
TS
2977 if (e_flags & EF_MIPS_UCODE)
2978 strcat (buf, ", ugen_reserved");
2979
252b5132
RH
2980 if (e_flags & EF_MIPS_ABI2)
2981 strcat (buf, ", abi2");
2982
43521d43
TS
2983 if (e_flags & EF_MIPS_OPTIONS_FIRST)
2984 strcat (buf, ", odk first");
2985
a5d22d2a
TS
2986 if (e_flags & EF_MIPS_32BITMODE)
2987 strcat (buf, ", 32bitmode");
2988
ba92f887
MR
2989 if (e_flags & EF_MIPS_NAN2008)
2990 strcat (buf, ", nan2008");
2991
fef1b0b3
SE
2992 if (e_flags & EF_MIPS_FP64)
2993 strcat (buf, ", fp64");
2994
156c2f8b
NC
2995 switch ((e_flags & EF_MIPS_MACH))
2996 {
2997 case E_MIPS_MACH_3900: strcat (buf, ", 3900"); break;
2998 case E_MIPS_MACH_4010: strcat (buf, ", 4010"); break;
2999 case E_MIPS_MACH_4100: strcat (buf, ", 4100"); break;
156c2f8b 3000 case E_MIPS_MACH_4111: strcat (buf, ", 4111"); break;
810dfa6e
L
3001 case E_MIPS_MACH_4120: strcat (buf, ", 4120"); break;
3002 case E_MIPS_MACH_4650: strcat (buf, ", 4650"); break;
3003 case E_MIPS_MACH_5400: strcat (buf, ", 5400"); break;
3004 case E_MIPS_MACH_5500: strcat (buf, ", 5500"); break;
c6c98b38 3005 case E_MIPS_MACH_SB1: strcat (buf, ", sb1"); break;
ebcb91b7 3006 case E_MIPS_MACH_9000: strcat (buf, ", 9000"); break;
350cc38d
MS
3007 case E_MIPS_MACH_LS2E: strcat (buf, ", loongson-2e"); break;
3008 case E_MIPS_MACH_LS2F: strcat (buf, ", loongson-2f"); break;
fd503541 3009 case E_MIPS_MACH_LS3A: strcat (buf, ", loongson-3a"); break;
05c6f050 3010 case E_MIPS_MACH_OCTEON: strcat (buf, ", octeon"); break;
67c2a3e8 3011 case E_MIPS_MACH_OCTEON2: strcat (buf, ", octeon2"); break;
d32e5c54 3012 case E_MIPS_MACH_OCTEON3: strcat (buf, ", octeon3"); break;
52b6b6b9 3013 case E_MIPS_MACH_XLR: strcat (buf, ", xlr"); break;
43521d43
TS
3014 case 0:
3015 /* We simply ignore the field in this case to avoid confusion:
3016 MIPS ELF does not specify EF_MIPS_MACH, it is a GNU
3017 extension. */
3018 break;
2b692964 3019 default: strcat (buf, _(", unknown CPU")); break;
156c2f8b 3020 }
43521d43
TS
3021
3022 switch ((e_flags & EF_MIPS_ABI))
3023 {
3024 case E_MIPS_ABI_O32: strcat (buf, ", o32"); break;
3025 case E_MIPS_ABI_O64: strcat (buf, ", o64"); break;
3026 case E_MIPS_ABI_EABI32: strcat (buf, ", eabi32"); break;
3027 case E_MIPS_ABI_EABI64: strcat (buf, ", eabi64"); break;
3028 case 0:
3029 /* We simply ignore the field in this case to avoid confusion:
3030 MIPS ELF does not specify EF_MIPS_ABI, it is a GNU extension.
3031 This means it is likely to be an o32 file, but not for
3032 sure. */
3033 break;
2b692964 3034 default: strcat (buf, _(", unknown ABI")); break;
43521d43
TS
3035 }
3036
3037 if (e_flags & EF_MIPS_ARCH_ASE_MDMX)
3038 strcat (buf, ", mdmx");
3039
3040 if (e_flags & EF_MIPS_ARCH_ASE_M16)
3041 strcat (buf, ", mips16");
3042
df58fc94
RS
3043 if (e_flags & EF_MIPS_ARCH_ASE_MICROMIPS)
3044 strcat (buf, ", micromips");
3045
43521d43
TS
3046 switch ((e_flags & EF_MIPS_ARCH))
3047 {
3048 case E_MIPS_ARCH_1: strcat (buf, ", mips1"); break;
3049 case E_MIPS_ARCH_2: strcat (buf, ", mips2"); break;
3050 case E_MIPS_ARCH_3: strcat (buf, ", mips3"); break;
3051 case E_MIPS_ARCH_4: strcat (buf, ", mips4"); break;
3052 case E_MIPS_ARCH_5: strcat (buf, ", mips5"); break;
3053 case E_MIPS_ARCH_32: strcat (buf, ", mips32"); break;
cb44e358 3054 case E_MIPS_ARCH_32R2: strcat (buf, ", mips32r2"); break;
7361da2c 3055 case E_MIPS_ARCH_32R6: strcat (buf, ", mips32r6"); break;
43521d43 3056 case E_MIPS_ARCH_64: strcat (buf, ", mips64"); break;
5f74bc13 3057 case E_MIPS_ARCH_64R2: strcat (buf, ", mips64r2"); break;
7361da2c 3058 case E_MIPS_ARCH_64R6: strcat (buf, ", mips64r6"); break;
2b692964 3059 default: strcat (buf, _(", unknown ISA")); break;
43521d43 3060 }
252b5132 3061 break;
351b4b40 3062
35c08157
KLC
3063 case EM_NDS32:
3064 decode_NDS32_machine_flags (e_flags, buf, sizeof buf);
3065 break;
3066
ccde1100
AO
3067 case EM_SH:
3068 switch ((e_flags & EF_SH_MACH_MASK))
3069 {
3070 case EF_SH1: strcat (buf, ", sh1"); break;
3071 case EF_SH2: strcat (buf, ", sh2"); break;
3072 case EF_SH3: strcat (buf, ", sh3"); break;
3073 case EF_SH_DSP: strcat (buf, ", sh-dsp"); break;
3074 case EF_SH3_DSP: strcat (buf, ", sh3-dsp"); break;
3075 case EF_SH4AL_DSP: strcat (buf, ", sh4al-dsp"); break;
3076 case EF_SH3E: strcat (buf, ", sh3e"); break;
3077 case EF_SH4: strcat (buf, ", sh4"); break;
3078 case EF_SH5: strcat (buf, ", sh5"); break;
3079 case EF_SH2E: strcat (buf, ", sh2e"); break;
3080 case EF_SH4A: strcat (buf, ", sh4a"); break;
1d70c7fb 3081 case EF_SH2A: strcat (buf, ", sh2a"); break;
ccde1100
AO
3082 case EF_SH4_NOFPU: strcat (buf, ", sh4-nofpu"); break;
3083 case EF_SH4A_NOFPU: strcat (buf, ", sh4a-nofpu"); break;
1d70c7fb 3084 case EF_SH2A_NOFPU: strcat (buf, ", sh2a-nofpu"); break;
0b92ab21
NH
3085 case EF_SH3_NOMMU: strcat (buf, ", sh3-nommu"); break;
3086 case EF_SH4_NOMMU_NOFPU: strcat (buf, ", sh4-nommu-nofpu"); break;
3087 case EF_SH2A_SH4_NOFPU: strcat (buf, ", sh2a-nofpu-or-sh4-nommu-nofpu"); break;
3088 case EF_SH2A_SH3_NOFPU: strcat (buf, ", sh2a-nofpu-or-sh3-nommu"); break;
3089 case EF_SH2A_SH4: strcat (buf, ", sh2a-or-sh4"); break;
3090 case EF_SH2A_SH3E: strcat (buf, ", sh2a-or-sh3e"); break;
2b692964 3091 default: strcat (buf, _(", unknown ISA")); break;
ccde1100
AO
3092 }
3093
cec6a5b8
MR
3094 if (e_flags & EF_SH_PIC)
3095 strcat (buf, ", pic");
3096
3097 if (e_flags & EF_SH_FDPIC)
3098 strcat (buf, ", fdpic");
ccde1100 3099 break;
73589c9d
CS
3100
3101 case EM_OR1K:
3102 if (e_flags & EF_OR1K_NODELAY)
3103 strcat (buf, ", no delay");
3104 break;
57346661 3105
351b4b40
RH
3106 case EM_SPARCV9:
3107 if (e_flags & EF_SPARC_32PLUS)
3108 strcat (buf, ", v8+");
3109
3110 if (e_flags & EF_SPARC_SUN_US1)
d07faca2
RH
3111 strcat (buf, ", ultrasparcI");
3112
3113 if (e_flags & EF_SPARC_SUN_US3)
3114 strcat (buf, ", ultrasparcIII");
351b4b40
RH
3115
3116 if (e_flags & EF_SPARC_HAL_R1)
3117 strcat (buf, ", halr1");
3118
3119 if (e_flags & EF_SPARC_LEDATA)
3120 strcat (buf, ", ledata");
3121
3122 if ((e_flags & EF_SPARCV9_MM) == EF_SPARCV9_TSO)
3123 strcat (buf, ", tso");
3124
3125 if ((e_flags & EF_SPARCV9_MM) == EF_SPARCV9_PSO)
3126 strcat (buf, ", pso");
3127
3128 if ((e_flags & EF_SPARCV9_MM) == EF_SPARCV9_RMO)
3129 strcat (buf, ", rmo");
3130 break;
7d466069 3131
103f02d3
UD
3132 case EM_PARISC:
3133 switch (e_flags & EF_PARISC_ARCH)
3134 {
3135 case EFA_PARISC_1_0:
3136 strcpy (buf, ", PA-RISC 1.0");
3137 break;
3138 case EFA_PARISC_1_1:
3139 strcpy (buf, ", PA-RISC 1.1");
3140 break;
3141 case EFA_PARISC_2_0:
3142 strcpy (buf, ", PA-RISC 2.0");
3143 break;
3144 default:
3145 break;
3146 }
3147 if (e_flags & EF_PARISC_TRAPNIL)
3148 strcat (buf, ", trapnil");
3149 if (e_flags & EF_PARISC_EXT)
3150 strcat (buf, ", ext");
3151 if (e_flags & EF_PARISC_LSB)
3152 strcat (buf, ", lsb");
3153 if (e_flags & EF_PARISC_WIDE)
3154 strcat (buf, ", wide");
3155 if (e_flags & EF_PARISC_NO_KABP)
3156 strcat (buf, ", no kabp");
3157 if (e_flags & EF_PARISC_LAZYSWAP)
3158 strcat (buf, ", lazyswap");
30800947 3159 break;
76da6bbe 3160
7d466069 3161 case EM_PJ:
2b0337b0 3162 case EM_PJ_OLD:
7d466069
ILT
3163 if ((e_flags & EF_PICOJAVA_NEWCALLS) == EF_PICOJAVA_NEWCALLS)
3164 strcat (buf, ", new calling convention");
3165
3166 if ((e_flags & EF_PICOJAVA_GNUCALLS) == EF_PICOJAVA_GNUCALLS)
3167 strcat (buf, ", gnu calling convention");
3168 break;
4d6ed7c8
NC
3169
3170 case EM_IA_64:
3171 if ((e_flags & EF_IA_64_ABI64))
3172 strcat (buf, ", 64-bit");
3173 else
3174 strcat (buf, ", 32-bit");
3175 if ((e_flags & EF_IA_64_REDUCEDFP))
3176 strcat (buf, ", reduced fp model");
3177 if ((e_flags & EF_IA_64_NOFUNCDESC_CONS_GP))
3178 strcat (buf, ", no function descriptors, constant gp");
3179 else if ((e_flags & EF_IA_64_CONS_GP))
3180 strcat (buf, ", constant gp");
3181 if ((e_flags & EF_IA_64_ABSOLUTE))
3182 strcat (buf, ", absolute");
28f997cf
TG
3183 if (elf_header.e_ident[EI_OSABI] == ELFOSABI_OPENVMS)
3184 {
3185 if ((e_flags & EF_IA_64_VMS_LINKAGES))
3186 strcat (buf, ", vms_linkages");
3187 switch ((e_flags & EF_IA_64_VMS_COMCOD))
3188 {
3189 case EF_IA_64_VMS_COMCOD_SUCCESS:
3190 break;
3191 case EF_IA_64_VMS_COMCOD_WARNING:
3192 strcat (buf, ", warning");
3193 break;
3194 case EF_IA_64_VMS_COMCOD_ERROR:
3195 strcat (buf, ", error");
3196 break;
3197 case EF_IA_64_VMS_COMCOD_ABORT:
3198 strcat (buf, ", abort");
3199 break;
3200 default:
bee0ee85
NC
3201 warn (_("Unrecognised IA64 VMS Command Code: %x\n"),
3202 e_flags & EF_IA_64_VMS_COMCOD);
3203 strcat (buf, ", <unknown>");
28f997cf
TG
3204 }
3205 }
4d6ed7c8 3206 break;
179d3252
JT
3207
3208 case EM_VAX:
3209 if ((e_flags & EF_VAX_NONPIC))
3210 strcat (buf, ", non-PIC");
3211 if ((e_flags & EF_VAX_DFLOAT))
3212 strcat (buf, ", D-Float");
3213 if ((e_flags & EF_VAX_GFLOAT))
3214 strcat (buf, ", G-Float");
3215 break;
c7927a3c 3216
4046d87a
NC
3217 case EM_RL78:
3218 if (e_flags & E_FLAG_RL78_G10)
3219 strcat (buf, ", G10");
856ea05c
KP
3220 if (e_flags & E_FLAG_RL78_64BIT_DOUBLES)
3221 strcat (buf, ", 64-bit doubles");
4046d87a 3222 break;
0b4362b0 3223
c7927a3c
NC
3224 case EM_RX:
3225 if (e_flags & E_FLAG_RX_64BIT_DOUBLES)
3226 strcat (buf, ", 64-bit doubles");
3227 if (e_flags & E_FLAG_RX_DSP)
dd24e3da 3228 strcat (buf, ", dsp");
d4cb0ea0 3229 if (e_flags & E_FLAG_RX_PID)
0b4362b0 3230 strcat (buf, ", pid");
708e2187
NC
3231 if (e_flags & E_FLAG_RX_ABI)
3232 strcat (buf, ", RX ABI");
d4cb0ea0 3233 break;
55786da2
AK
3234
3235 case EM_S390:
3236 if (e_flags & EF_S390_HIGH_GPRS)
3237 strcat (buf, ", highgprs");
d4cb0ea0 3238 break;
40b36596
JM
3239
3240 case EM_TI_C6000:
3241 if ((e_flags & EF_C6000_REL))
3242 strcat (buf, ", relocatable module");
d4cb0ea0 3243 break;
13761a11
NC
3244
3245 case EM_MSP430:
3246 strcat (buf, _(": architecture variant: "));
3247 switch (e_flags & EF_MSP430_MACH)
3248 {
3249 case E_MSP430_MACH_MSP430x11: strcat (buf, "MSP430x11"); break;
3250 case E_MSP430_MACH_MSP430x11x1 : strcat (buf, "MSP430x11x1 "); break;
3251 case E_MSP430_MACH_MSP430x12: strcat (buf, "MSP430x12"); break;
3252 case E_MSP430_MACH_MSP430x13: strcat (buf, "MSP430x13"); break;
3253 case E_MSP430_MACH_MSP430x14: strcat (buf, "MSP430x14"); break;
3254 case E_MSP430_MACH_MSP430x15: strcat (buf, "MSP430x15"); break;
3255 case E_MSP430_MACH_MSP430x16: strcat (buf, "MSP430x16"); break;
3256 case E_MSP430_MACH_MSP430x31: strcat (buf, "MSP430x31"); break;
3257 case E_MSP430_MACH_MSP430x32: strcat (buf, "MSP430x32"); break;
3258 case E_MSP430_MACH_MSP430x33: strcat (buf, "MSP430x33"); break;
3259 case E_MSP430_MACH_MSP430x41: strcat (buf, "MSP430x41"); break;
3260 case E_MSP430_MACH_MSP430x42: strcat (buf, "MSP430x42"); break;
3261 case E_MSP430_MACH_MSP430x43: strcat (buf, "MSP430x43"); break;
3262 case E_MSP430_MACH_MSP430x44: strcat (buf, "MSP430x44"); break;
3263 case E_MSP430_MACH_MSP430X : strcat (buf, "MSP430X"); break;
3264 default:
3265 strcat (buf, _(": unknown")); break;
3266 }
3267
3268 if (e_flags & ~ EF_MSP430_MACH)
3269 strcat (buf, _(": unknown extra flag bits also present"));
252b5132
RH
3270 }
3271 }
3272
3273 return buf;
3274}
3275
252b5132 3276static const char *
d3ba0551
AM
3277get_osabi_name (unsigned int osabi)
3278{
3279 static char buff[32];
3280
3281 switch (osabi)
3282 {
3283 case ELFOSABI_NONE: return "UNIX - System V";
3284 case ELFOSABI_HPUX: return "UNIX - HP-UX";
3285 case ELFOSABI_NETBSD: return "UNIX - NetBSD";
9c55345c 3286 case ELFOSABI_GNU: return "UNIX - GNU";
d3ba0551
AM
3287 case ELFOSABI_SOLARIS: return "UNIX - Solaris";
3288 case ELFOSABI_AIX: return "UNIX - AIX";
3289 case ELFOSABI_IRIX: return "UNIX - IRIX";
3290 case ELFOSABI_FREEBSD: return "UNIX - FreeBSD";
3291 case ELFOSABI_TRU64: return "UNIX - TRU64";
3292 case ELFOSABI_MODESTO: return "Novell - Modesto";
3293 case ELFOSABI_OPENBSD: return "UNIX - OpenBSD";
3294 case ELFOSABI_OPENVMS: return "VMS - OpenVMS";
3295 case ELFOSABI_NSK: return "HP - Non-Stop Kernel";
3b26c801 3296 case ELFOSABI_AROS: return "AROS";
11636f9e 3297 case ELFOSABI_FENIXOS: return "FenixOS";
d3ba0551 3298 default:
40b36596
JM
3299 if (osabi >= 64)
3300 switch (elf_header.e_machine)
3301 {
3302 case EM_ARM:
3303 switch (osabi)
3304 {
3305 case ELFOSABI_ARM: return "ARM";
3306 default:
3307 break;
3308 }
3309 break;
3310
3311 case EM_MSP430:
3312 case EM_MSP430_OLD:
3313 switch (osabi)
3314 {
3315 case ELFOSABI_STANDALONE: return _("Standalone App");
3316 default:
3317 break;
3318 }
3319 break;
3320
3321 case EM_TI_C6000:
3322 switch (osabi)
3323 {
3324 case ELFOSABI_C6000_ELFABI: return _("Bare-metal C6000");
3325 case ELFOSABI_C6000_LINUX: return "Linux C6000";
3326 default:
3327 break;
3328 }
3329 break;
3330
3331 default:
3332 break;
3333 }
e9e44622 3334 snprintf (buff, sizeof (buff), _("<unknown: %x>"), osabi);
d3ba0551
AM
3335 return buff;
3336 }
3337}
3338
a06ea964
NC
3339static const char *
3340get_aarch64_segment_type (unsigned long type)
3341{
3342 switch (type)
3343 {
3344 case PT_AARCH64_ARCHEXT:
3345 return "AARCH64_ARCHEXT";
3346 default:
3347 break;
3348 }
3349
3350 return NULL;
3351}
3352
b294bdf8
MM
3353static const char *
3354get_arm_segment_type (unsigned long type)
3355{
3356 switch (type)
3357 {
3358 case PT_ARM_EXIDX:
3359 return "EXIDX";
3360 default:
3361 break;
3362 }
3363
3364 return NULL;
3365}
3366
d3ba0551
AM
3367static const char *
3368get_mips_segment_type (unsigned long type)
252b5132
RH
3369{
3370 switch (type)
3371 {
3372 case PT_MIPS_REGINFO:
3373 return "REGINFO";
3374 case PT_MIPS_RTPROC:
3375 return "RTPROC";
3376 case PT_MIPS_OPTIONS:
3377 return "OPTIONS";
351cdf24
MF
3378 case PT_MIPS_ABIFLAGS:
3379 return "ABIFLAGS";
252b5132
RH
3380 default:
3381 break;
3382 }
3383
3384 return NULL;
3385}
3386
103f02d3 3387static const char *
d3ba0551 3388get_parisc_segment_type (unsigned long type)
103f02d3
UD
3389{
3390 switch (type)
3391 {
3392 case PT_HP_TLS: return "HP_TLS";
3393 case PT_HP_CORE_NONE: return "HP_CORE_NONE";
3394 case PT_HP_CORE_VERSION: return "HP_CORE_VERSION";
3395 case PT_HP_CORE_KERNEL: return "HP_CORE_KERNEL";
3396 case PT_HP_CORE_COMM: return "HP_CORE_COMM";
3397 case PT_HP_CORE_PROC: return "HP_CORE_PROC";
3398 case PT_HP_CORE_LOADABLE: return "HP_CORE_LOADABLE";
3399 case PT_HP_CORE_STACK: return "HP_CORE_STACK";
3400 case PT_HP_CORE_SHM: return "HP_CORE_SHM";
3401 case PT_HP_CORE_MMF: return "HP_CORE_MMF";
3402 case PT_HP_PARALLEL: return "HP_PARALLEL";
3403 case PT_HP_FASTBIND: return "HP_FASTBIND";
eec8f817
DA
3404 case PT_HP_OPT_ANNOT: return "HP_OPT_ANNOT";
3405 case PT_HP_HSL_ANNOT: return "HP_HSL_ANNOT";
3406 case PT_HP_STACK: return "HP_STACK";
3407 case PT_HP_CORE_UTSNAME: return "HP_CORE_UTSNAME";
103f02d3
UD
3408 case PT_PARISC_ARCHEXT: return "PARISC_ARCHEXT";
3409 case PT_PARISC_UNWIND: return "PARISC_UNWIND";
61472819 3410 case PT_PARISC_WEAKORDER: return "PARISC_WEAKORDER";
103f02d3
UD
3411 default:
3412 break;
3413 }
3414
3415 return NULL;
3416}
3417
4d6ed7c8 3418static const char *
d3ba0551 3419get_ia64_segment_type (unsigned long type)
4d6ed7c8
NC
3420{
3421 switch (type)
3422 {
3423 case PT_IA_64_ARCHEXT: return "IA_64_ARCHEXT";
3424 case PT_IA_64_UNWIND: return "IA_64_UNWIND";
00428cca
AM
3425 case PT_HP_TLS: return "HP_TLS";
3426 case PT_IA_64_HP_OPT_ANOT: return "HP_OPT_ANNOT";
3427 case PT_IA_64_HP_HSL_ANOT: return "HP_HSL_ANNOT";
3428 case PT_IA_64_HP_STACK: return "HP_STACK";
4d6ed7c8
NC
3429 default:
3430 break;
3431 }
3432
3433 return NULL;
3434}
3435
40b36596
JM
3436static const char *
3437get_tic6x_segment_type (unsigned long type)
3438{
3439 switch (type)
3440 {
3441 case PT_C6000_PHATTR: return "C6000_PHATTR";
3442 default:
3443 break;
3444 }
3445
3446 return NULL;
3447}
3448
252b5132 3449static const char *
d3ba0551 3450get_segment_type (unsigned long p_type)
252b5132 3451{
b34976b6 3452 static char buff[32];
252b5132
RH
3453
3454 switch (p_type)
3455 {
b34976b6
AM
3456 case PT_NULL: return "NULL";
3457 case PT_LOAD: return "LOAD";
252b5132 3458 case PT_DYNAMIC: return "DYNAMIC";
b34976b6
AM
3459 case PT_INTERP: return "INTERP";
3460 case PT_NOTE: return "NOTE";
3461 case PT_SHLIB: return "SHLIB";
3462 case PT_PHDR: return "PHDR";
13ae64f3 3463 case PT_TLS: return "TLS";
252b5132 3464
65765700
JJ
3465 case PT_GNU_EH_FRAME:
3466 return "GNU_EH_FRAME";
2b05f1b7 3467 case PT_GNU_STACK: return "GNU_STACK";
8c37241b 3468 case PT_GNU_RELRO: return "GNU_RELRO";
65765700 3469
252b5132
RH
3470 default:
3471 if ((p_type >= PT_LOPROC) && (p_type <= PT_HIPROC))
3472 {
2cf0635d 3473 const char * result;
103f02d3 3474
252b5132
RH
3475 switch (elf_header.e_machine)
3476 {
a06ea964
NC
3477 case EM_AARCH64:
3478 result = get_aarch64_segment_type (p_type);
3479 break;
b294bdf8
MM
3480 case EM_ARM:
3481 result = get_arm_segment_type (p_type);
3482 break;
252b5132 3483 case EM_MIPS:
4fe85591 3484 case EM_MIPS_RS3_LE:
252b5132
RH
3485 result = get_mips_segment_type (p_type);
3486 break;
103f02d3
UD
3487 case EM_PARISC:
3488 result = get_parisc_segment_type (p_type);
3489 break;
4d6ed7c8
NC
3490 case EM_IA_64:
3491 result = get_ia64_segment_type (p_type);
3492 break;
40b36596
JM
3493 case EM_TI_C6000:
3494 result = get_tic6x_segment_type (p_type);
3495 break;
252b5132
RH
3496 default:
3497 result = NULL;
3498 break;
3499 }
103f02d3 3500
252b5132
RH
3501 if (result != NULL)
3502 return result;
103f02d3 3503
252b5132
RH
3504 sprintf (buff, "LOPROC+%lx", p_type - PT_LOPROC);
3505 }
3506 else if ((p_type >= PT_LOOS) && (p_type <= PT_HIOS))
103f02d3 3507 {
2cf0635d 3508 const char * result;
103f02d3
UD
3509
3510 switch (elf_header.e_machine)
3511 {
3512 case EM_PARISC:
3513 result = get_parisc_segment_type (p_type);
3514 break;
00428cca
AM
3515 case EM_IA_64:
3516 result = get_ia64_segment_type (p_type);
3517 break;
103f02d3
UD
3518 default:
3519 result = NULL;
3520 break;
3521 }
3522
3523 if (result != NULL)
3524 return result;
3525
3526 sprintf (buff, "LOOS+%lx", p_type - PT_LOOS);
3527 }
252b5132 3528 else
e9e44622 3529 snprintf (buff, sizeof (buff), _("<unknown>: %lx"), p_type);
252b5132
RH
3530
3531 return buff;
3532 }
3533}
3534
3535static const char *
d3ba0551 3536get_mips_section_type_name (unsigned int sh_type)
252b5132
RH
3537{
3538 switch (sh_type)
3539 {
b34976b6
AM
3540 case SHT_MIPS_LIBLIST: return "MIPS_LIBLIST";
3541 case SHT_MIPS_MSYM: return "MIPS_MSYM";
3542 case SHT_MIPS_CONFLICT: return "MIPS_CONFLICT";
3543 case SHT_MIPS_GPTAB: return "MIPS_GPTAB";
3544 case SHT_MIPS_UCODE: return "MIPS_UCODE";
3545 case SHT_MIPS_DEBUG: return "MIPS_DEBUG";
3546 case SHT_MIPS_REGINFO: return "MIPS_REGINFO";
3547 case SHT_MIPS_PACKAGE: return "MIPS_PACKAGE";
3548 case SHT_MIPS_PACKSYM: return "MIPS_PACKSYM";
3549 case SHT_MIPS_RELD: return "MIPS_RELD";
3550 case SHT_MIPS_IFACE: return "MIPS_IFACE";
3551 case SHT_MIPS_CONTENT: return "MIPS_CONTENT";
3552 case SHT_MIPS_OPTIONS: return "MIPS_OPTIONS";
3553 case SHT_MIPS_SHDR: return "MIPS_SHDR";
3554 case SHT_MIPS_FDESC: return "MIPS_FDESC";
3555 case SHT_MIPS_EXTSYM: return "MIPS_EXTSYM";
3556 case SHT_MIPS_DENSE: return "MIPS_DENSE";
3557 case SHT_MIPS_PDESC: return "MIPS_PDESC";
3558 case SHT_MIPS_LOCSYM: return "MIPS_LOCSYM";
3559 case SHT_MIPS_AUXSYM: return "MIPS_AUXSYM";
3560 case SHT_MIPS_OPTSYM: return "MIPS_OPTSYM";
3561 case SHT_MIPS_LOCSTR: return "MIPS_LOCSTR";
3562 case SHT_MIPS_LINE: return "MIPS_LINE";
3563 case SHT_MIPS_RFDESC: return "MIPS_RFDESC";
3564 case SHT_MIPS_DELTASYM: return "MIPS_DELTASYM";
3565 case SHT_MIPS_DELTAINST: return "MIPS_DELTAINST";
3566 case SHT_MIPS_DELTACLASS: return "MIPS_DELTACLASS";
3567 case SHT_MIPS_DWARF: return "MIPS_DWARF";
3568 case SHT_MIPS_DELTADECL: return "MIPS_DELTADECL";
3569 case SHT_MIPS_SYMBOL_LIB: return "MIPS_SYMBOL_LIB";
3570 case SHT_MIPS_EVENTS: return "MIPS_EVENTS";
3571 case SHT_MIPS_TRANSLATE: return "MIPS_TRANSLATE";
3572 case SHT_MIPS_PIXIE: return "MIPS_PIXIE";
3573 case SHT_MIPS_XLATE: return "MIPS_XLATE";
3574 case SHT_MIPS_XLATE_DEBUG: return "MIPS_XLATE_DEBUG";
3575 case SHT_MIPS_WHIRL: return "MIPS_WHIRL";
3576 case SHT_MIPS_EH_REGION: return "MIPS_EH_REGION";
3577 case SHT_MIPS_XLATE_OLD: return "MIPS_XLATE_OLD";
252b5132 3578 case SHT_MIPS_PDR_EXCEPTION: return "MIPS_PDR_EXCEPTION";
351cdf24 3579 case SHT_MIPS_ABIFLAGS: return "MIPS_ABIFLAGS";
252b5132
RH
3580 default:
3581 break;
3582 }
3583 return NULL;
3584}
3585
103f02d3 3586static const char *
d3ba0551 3587get_parisc_section_type_name (unsigned int sh_type)
103f02d3
UD
3588{
3589 switch (sh_type)
3590 {
3591 case SHT_PARISC_EXT: return "PARISC_EXT";
3592 case SHT_PARISC_UNWIND: return "PARISC_UNWIND";
3593 case SHT_PARISC_DOC: return "PARISC_DOC";
eec8f817
DA
3594 case SHT_PARISC_ANNOT: return "PARISC_ANNOT";
3595 case SHT_PARISC_SYMEXTN: return "PARISC_SYMEXTN";
3596 case SHT_PARISC_STUBS: return "PARISC_STUBS";
61472819 3597 case SHT_PARISC_DLKM: return "PARISC_DLKM";
103f02d3
UD
3598 default:
3599 break;
3600 }
3601 return NULL;
3602}
3603
4d6ed7c8 3604static const char *
d3ba0551 3605get_ia64_section_type_name (unsigned int sh_type)
4d6ed7c8 3606{
18bd398b 3607 /* If the top 8 bits are 0x78 the next 8 are the os/abi ID. */
ecc51f48
NC
3608 if ((sh_type & 0xFF000000) == SHT_IA_64_LOPSREG)
3609 return get_osabi_name ((sh_type & 0x00FF0000) >> 16);
0de14b54 3610
4d6ed7c8
NC
3611 switch (sh_type)
3612 {
148b93f2
NC
3613 case SHT_IA_64_EXT: return "IA_64_EXT";
3614 case SHT_IA_64_UNWIND: return "IA_64_UNWIND";
3615 case SHT_IA_64_PRIORITY_INIT: return "IA_64_PRIORITY_INIT";
3616 case SHT_IA_64_VMS_TRACE: return "VMS_TRACE";
3617 case SHT_IA_64_VMS_TIE_SIGNATURES: return "VMS_TIE_SIGNATURES";
3618 case SHT_IA_64_VMS_DEBUG: return "VMS_DEBUG";
3619 case SHT_IA_64_VMS_DEBUG_STR: return "VMS_DEBUG_STR";
3620 case SHT_IA_64_VMS_LINKAGES: return "VMS_LINKAGES";
3621 case SHT_IA_64_VMS_SYMBOL_VECTOR: return "VMS_SYMBOL_VECTOR";
3622 case SHT_IA_64_VMS_FIXUP: return "VMS_FIXUP";
4d6ed7c8
NC
3623 default:
3624 break;
3625 }
3626 return NULL;
3627}
3628
d2b2c203
DJ
3629static const char *
3630get_x86_64_section_type_name (unsigned int sh_type)
3631{
3632 switch (sh_type)
3633 {
3634 case SHT_X86_64_UNWIND: return "X86_64_UNWIND";
3635 default:
3636 break;
3637 }
3638 return NULL;
3639}
3640
a06ea964
NC
3641static const char *
3642get_aarch64_section_type_name (unsigned int sh_type)
3643{
3644 switch (sh_type)
3645 {
3646 case SHT_AARCH64_ATTRIBUTES:
3647 return "AARCH64_ATTRIBUTES";
3648 default:
3649 break;
3650 }
3651 return NULL;
3652}
3653
40a18ebd
NC
3654static const char *
3655get_arm_section_type_name (unsigned int sh_type)
3656{
3657 switch (sh_type)
3658 {
7f6fed87
NC
3659 case SHT_ARM_EXIDX: return "ARM_EXIDX";
3660 case SHT_ARM_PREEMPTMAP: return "ARM_PREEMPTMAP";
3661 case SHT_ARM_ATTRIBUTES: return "ARM_ATTRIBUTES";
3662 case SHT_ARM_DEBUGOVERLAY: return "ARM_DEBUGOVERLAY";
3663 case SHT_ARM_OVERLAYSECTION: return "ARM_OVERLAYSECTION";
40a18ebd
NC
3664 default:
3665 break;
3666 }
3667 return NULL;
3668}
3669
40b36596
JM
3670static const char *
3671get_tic6x_section_type_name (unsigned int sh_type)
3672{
3673 switch (sh_type)
3674 {
3675 case SHT_C6000_UNWIND:
3676 return "C6000_UNWIND";
3677 case SHT_C6000_PREEMPTMAP:
3678 return "C6000_PREEMPTMAP";
3679 case SHT_C6000_ATTRIBUTES:
3680 return "C6000_ATTRIBUTES";
3681 case SHT_TI_ICODE:
3682 return "TI_ICODE";
3683 case SHT_TI_XREF:
3684 return "TI_XREF";
3685 case SHT_TI_HANDLER:
3686 return "TI_HANDLER";
3687 case SHT_TI_INITINFO:
3688 return "TI_INITINFO";
3689 case SHT_TI_PHATTRS:
3690 return "TI_PHATTRS";
3691 default:
3692 break;
3693 }
3694 return NULL;
3695}
3696
13761a11
NC
3697static const char *
3698get_msp430x_section_type_name (unsigned int sh_type)
3699{
3700 switch (sh_type)
3701 {
3702 case SHT_MSP430_SEC_FLAGS: return "MSP430_SEC_FLAGS";
3703 case SHT_MSP430_SYM_ALIASES: return "MSP430_SYM_ALIASES";
3704 case SHT_MSP430_ATTRIBUTES: return "MSP430_ATTRIBUTES";
3705 default: return NULL;
3706 }
3707}
3708
252b5132 3709static const char *
d3ba0551 3710get_section_type_name (unsigned int sh_type)
252b5132 3711{
b34976b6 3712 static char buff[32];
252b5132
RH
3713
3714 switch (sh_type)
3715 {
3716 case SHT_NULL: return "NULL";
3717 case SHT_PROGBITS: return "PROGBITS";
3718 case SHT_SYMTAB: return "SYMTAB";
3719 case SHT_STRTAB: return "STRTAB";
3720 case SHT_RELA: return "RELA";
3721 case SHT_HASH: return "HASH";
3722 case SHT_DYNAMIC: return "DYNAMIC";
3723 case SHT_NOTE: return "NOTE";
3724 case SHT_NOBITS: return "NOBITS";
3725 case SHT_REL: return "REL";
3726 case SHT_SHLIB: return "SHLIB";
3727 case SHT_DYNSYM: return "DYNSYM";
d1133906
NC
3728 case SHT_INIT_ARRAY: return "INIT_ARRAY";
3729 case SHT_FINI_ARRAY: return "FINI_ARRAY";
3730 case SHT_PREINIT_ARRAY: return "PREINIT_ARRAY";
fdc90cb4 3731 case SHT_GNU_HASH: return "GNU_HASH";
93ebe586
NC
3732 case SHT_GROUP: return "GROUP";
3733 case SHT_SYMTAB_SHNDX: return "SYMTAB SECTION INDICIES";
252b5132
RH
3734 case SHT_GNU_verdef: return "VERDEF";
3735 case SHT_GNU_verneed: return "VERNEED";
3736 case SHT_GNU_versym: return "VERSYM";
b34976b6
AM
3737 case 0x6ffffff0: return "VERSYM";
3738 case 0x6ffffffc: return "VERDEF";
252b5132
RH
3739 case 0x7ffffffd: return "AUXILIARY";
3740 case 0x7fffffff: return "FILTER";
047b2264 3741 case SHT_GNU_LIBLIST: return "GNU_LIBLIST";
252b5132
RH
3742
3743 default:
3744 if ((sh_type >= SHT_LOPROC) && (sh_type <= SHT_HIPROC))
3745 {
2cf0635d 3746 const char * result;
252b5132
RH
3747
3748 switch (elf_header.e_machine)
3749 {
3750 case EM_MIPS:
4fe85591 3751 case EM_MIPS_RS3_LE:
252b5132
RH
3752 result = get_mips_section_type_name (sh_type);
3753 break;
103f02d3
UD
3754 case EM_PARISC:
3755 result = get_parisc_section_type_name (sh_type);
3756 break;
4d6ed7c8
NC
3757 case EM_IA_64:
3758 result = get_ia64_section_type_name (sh_type);
3759 break;
d2b2c203 3760 case EM_X86_64:
8a9036a4 3761 case EM_L1OM:
7a9068fe 3762 case EM_K1OM:
d2b2c203
DJ
3763 result = get_x86_64_section_type_name (sh_type);
3764 break;
a06ea964
NC
3765 case EM_AARCH64:
3766 result = get_aarch64_section_type_name (sh_type);
3767 break;
40a18ebd
NC
3768 case EM_ARM:
3769 result = get_arm_section_type_name (sh_type);
3770 break;
40b36596
JM
3771 case EM_TI_C6000:
3772 result = get_tic6x_section_type_name (sh_type);
3773 break;
13761a11
NC
3774 case EM_MSP430:
3775 result = get_msp430x_section_type_name (sh_type);
3776 break;
252b5132
RH
3777 default:
3778 result = NULL;
3779 break;
3780 }
3781
3782 if (result != NULL)
3783 return result;
3784
c91d0dfb 3785 sprintf (buff, "LOPROC+%x", sh_type - SHT_LOPROC);
252b5132
RH
3786 }
3787 else if ((sh_type >= SHT_LOOS) && (sh_type <= SHT_HIOS))
148b93f2 3788 {
2cf0635d 3789 const char * result;
148b93f2
NC
3790
3791 switch (elf_header.e_machine)
3792 {
3793 case EM_IA_64:
3794 result = get_ia64_section_type_name (sh_type);
3795 break;
3796 default:
3797 result = NULL;
3798 break;
3799 }
3800
3801 if (result != NULL)
3802 return result;
3803
3804 sprintf (buff, "LOOS+%x", sh_type - SHT_LOOS);
3805 }
252b5132 3806 else if ((sh_type >= SHT_LOUSER) && (sh_type <= SHT_HIUSER))
c91d0dfb 3807 sprintf (buff, "LOUSER+%x", sh_type - SHT_LOUSER);
252b5132 3808 else
a7dbfd1c
NC
3809 /* This message is probably going to be displayed in a 15
3810 character wide field, so put the hex value first. */
3811 snprintf (buff, sizeof (buff), _("%08x: <unknown>"), sh_type);
103f02d3 3812
252b5132
RH
3813 return buff;
3814 }
3815}
3816
2979dc34 3817#define OPTION_DEBUG_DUMP 512
2c610e4b 3818#define OPTION_DYN_SYMS 513
fd2f0033
TT
3819#define OPTION_DWARF_DEPTH 514
3820#define OPTION_DWARF_START 515
4723351a 3821#define OPTION_DWARF_CHECK 516
2979dc34 3822
85b1c36d 3823static struct option options[] =
252b5132 3824{
b34976b6 3825 {"all", no_argument, 0, 'a'},
252b5132
RH
3826 {"file-header", no_argument, 0, 'h'},
3827 {"program-headers", no_argument, 0, 'l'},
b34976b6
AM
3828 {"headers", no_argument, 0, 'e'},
3829 {"histogram", no_argument, 0, 'I'},
3830 {"segments", no_argument, 0, 'l'},
3831 {"sections", no_argument, 0, 'S'},
252b5132 3832 {"section-headers", no_argument, 0, 'S'},
f5842774 3833 {"section-groups", no_argument, 0, 'g'},
5477e8a0 3834 {"section-details", no_argument, 0, 't'},
595cf52e 3835 {"full-section-name",no_argument, 0, 'N'},
b34976b6
AM
3836 {"symbols", no_argument, 0, 's'},
3837 {"syms", no_argument, 0, 's'},
2c610e4b 3838 {"dyn-syms", no_argument, 0, OPTION_DYN_SYMS},
b34976b6
AM
3839 {"relocs", no_argument, 0, 'r'},
3840 {"notes", no_argument, 0, 'n'},
3841 {"dynamic", no_argument, 0, 'd'},
a952a375 3842 {"arch-specific", no_argument, 0, 'A'},
252b5132
RH
3843 {"version-info", no_argument, 0, 'V'},
3844 {"use-dynamic", no_argument, 0, 'D'},
09c11c86 3845 {"unwind", no_argument, 0, 'u'},
4145f1d5 3846 {"archive-index", no_argument, 0, 'c'},
b34976b6 3847 {"hex-dump", required_argument, 0, 'x'},
cf13d699 3848 {"relocated-dump", required_argument, 0, 'R'},
09c11c86 3849 {"string-dump", required_argument, 0, 'p'},
252b5132
RH
3850#ifdef SUPPORT_DISASSEMBLY
3851 {"instruction-dump", required_argument, 0, 'i'},
3852#endif
cf13d699 3853 {"debug-dump", optional_argument, 0, OPTION_DEBUG_DUMP},
252b5132 3854
fd2f0033
TT
3855 {"dwarf-depth", required_argument, 0, OPTION_DWARF_DEPTH},
3856 {"dwarf-start", required_argument, 0, OPTION_DWARF_START},
4723351a 3857 {"dwarf-check", no_argument, 0, OPTION_DWARF_CHECK},
fd2f0033 3858
b34976b6
AM
3859 {"version", no_argument, 0, 'v'},
3860 {"wide", no_argument, 0, 'W'},
3861 {"help", no_argument, 0, 'H'},
3862 {0, no_argument, 0, 0}
252b5132
RH
3863};
3864
3865static void
2cf0635d 3866usage (FILE * stream)
252b5132 3867{
92f01d61
JM
3868 fprintf (stream, _("Usage: readelf <option(s)> elf-file(s)\n"));
3869 fprintf (stream, _(" Display information about the contents of ELF format files\n"));
3870 fprintf (stream, _(" Options are:\n\
8b53311e
NC
3871 -a --all Equivalent to: -h -l -S -s -r -d -V -A -I\n\
3872 -h --file-header Display the ELF file header\n\
3873 -l --program-headers Display the program headers\n\
3874 --segments An alias for --program-headers\n\
3875 -S --section-headers Display the sections' header\n\
3876 --sections An alias for --section-headers\n\
f5842774 3877 -g --section-groups Display the section groups\n\
5477e8a0 3878 -t --section-details Display the section details\n\
8b53311e
NC
3879 -e --headers Equivalent to: -h -l -S\n\
3880 -s --syms Display the symbol table\n\
3f08eb35 3881 --symbols An alias for --syms\n\
2c610e4b 3882 --dyn-syms Display the dynamic symbol table\n\
8b53311e
NC
3883 -n --notes Display the core notes (if present)\n\
3884 -r --relocs Display the relocations (if present)\n\
3885 -u --unwind Display the unwind info (if present)\n\
b2d38a17 3886 -d --dynamic Display the dynamic section (if present)\n\
8b53311e 3887 -V --version-info Display the version sections (if present)\n\
1b31d05e 3888 -A --arch-specific Display architecture specific information (if any)\n\
4145f1d5 3889 -c --archive-index Display the symbol/file index in an archive\n\
8b53311e 3890 -D --use-dynamic Use the dynamic section info when displaying symbols\n\
09c11c86
NC
3891 -x --hex-dump=<number|name>\n\
3892 Dump the contents of section <number|name> as bytes\n\
3893 -p --string-dump=<number|name>\n\
3894 Dump the contents of section <number|name> as strings\n\
cf13d699
NC
3895 -R --relocated-dump=<number|name>\n\
3896 Dump the contents of section <number|name> as relocated bytes\n\
f9f0e732 3897 -w[lLiaprmfFsoRt] or\n\
1ed06042 3898 --debug-dump[=rawline,=decodedline,=info,=abbrev,=pubnames,=aranges,=macro,=frames,\n\
6f875884 3899 =frames-interp,=str,=loc,=Ranges,=pubtypes,\n\
657d0d47
CC
3900 =gdb_index,=trace_info,=trace_abbrev,=trace_aranges,\n\
3901 =addr,=cu_index]\n\
8b53311e 3902 Display the contents of DWARF2 debug sections\n"));
fd2f0033
TT
3903 fprintf (stream, _("\
3904 --dwarf-depth=N Do not display DIEs at depth N or greater\n\
3905 --dwarf-start=N Display DIEs starting with N, at the same depth\n\
3906 or deeper\n"));
252b5132 3907#ifdef SUPPORT_DISASSEMBLY
92f01d61 3908 fprintf (stream, _("\
09c11c86
NC
3909 -i --instruction-dump=<number|name>\n\
3910 Disassemble the contents of section <number|name>\n"));
252b5132 3911#endif
92f01d61 3912 fprintf (stream, _("\
8b53311e
NC
3913 -I --histogram Display histogram of bucket list lengths\n\
3914 -W --wide Allow output width to exceed 80 characters\n\
07012eee 3915 @<file> Read options from <file>\n\
8b53311e
NC
3916 -H --help Display this information\n\
3917 -v --version Display the version number of readelf\n"));
1118d252 3918
92f01d61
JM
3919 if (REPORT_BUGS_TO[0] && stream == stdout)
3920 fprintf (stdout, _("Report bugs to %s\n"), REPORT_BUGS_TO);
252b5132 3921
92f01d61 3922 exit (stream == stdout ? 0 : 1);
252b5132
RH
3923}
3924
18bd398b
NC
3925/* Record the fact that the user wants the contents of section number
3926 SECTION to be displayed using the method(s) encoded as flags bits
3927 in TYPE. Note, TYPE can be zero if we are creating the array for
3928 the first time. */
3929
252b5132 3930static void
09c11c86 3931request_dump_bynumber (unsigned int section, dump_type type)
252b5132
RH
3932{
3933 if (section >= num_dump_sects)
3934 {
2cf0635d 3935 dump_type * new_dump_sects;
252b5132 3936
3f5e193b
NC
3937 new_dump_sects = (dump_type *) calloc (section + 1,
3938 sizeof (* dump_sects));
252b5132
RH
3939
3940 if (new_dump_sects == NULL)
591a748a 3941 error (_("Out of memory allocating dump request table.\n"));
252b5132
RH
3942 else
3943 {
3944 /* Copy current flag settings. */
09c11c86 3945 memcpy (new_dump_sects, dump_sects, num_dump_sects * sizeof (* dump_sects));
252b5132
RH
3946
3947 free (dump_sects);
3948
3949 dump_sects = new_dump_sects;
3950 num_dump_sects = section + 1;
3951 }
3952 }
3953
3954 if (dump_sects)
b34976b6 3955 dump_sects[section] |= type;
252b5132
RH
3956
3957 return;
3958}
3959
aef1f6d0
DJ
3960/* Request a dump by section name. */
3961
3962static void
2cf0635d 3963request_dump_byname (const char * section, dump_type type)
aef1f6d0 3964{
2cf0635d 3965 struct dump_list_entry * new_request;
aef1f6d0 3966
3f5e193b
NC
3967 new_request = (struct dump_list_entry *)
3968 malloc (sizeof (struct dump_list_entry));
aef1f6d0 3969 if (!new_request)
591a748a 3970 error (_("Out of memory allocating dump request table.\n"));
aef1f6d0
DJ
3971
3972 new_request->name = strdup (section);
3973 if (!new_request->name)
591a748a 3974 error (_("Out of memory allocating dump request table.\n"));
aef1f6d0
DJ
3975
3976 new_request->type = type;
3977
3978 new_request->next = dump_sects_byname;
3979 dump_sects_byname = new_request;
3980}
3981
cf13d699
NC
3982static inline void
3983request_dump (dump_type type)
3984{
3985 int section;
3986 char * cp;
3987
3988 do_dump++;
3989 section = strtoul (optarg, & cp, 0);
3990
3991 if (! *cp && section >= 0)
3992 request_dump_bynumber (section, type);
3993 else
3994 request_dump_byname (optarg, type);
3995}
3996
3997
252b5132 3998static void
2cf0635d 3999parse_args (int argc, char ** argv)
252b5132
RH
4000{
4001 int c;
4002
4003 if (argc < 2)
92f01d61 4004 usage (stderr);
252b5132
RH
4005
4006 while ((c = getopt_long
cf13d699 4007 (argc, argv, "ADHINR:SVWacdeghi:lnp:rstuvw::x:", options, NULL)) != EOF)
252b5132 4008 {
252b5132
RH
4009 switch (c)
4010 {
4011 case 0:
4012 /* Long options. */
4013 break;
4014 case 'H':
92f01d61 4015 usage (stdout);
252b5132
RH
4016 break;
4017
4018 case 'a':
b34976b6
AM
4019 do_syms++;
4020 do_reloc++;
4021 do_unwind++;
4022 do_dynamic++;
4023 do_header++;
4024 do_sections++;
f5842774 4025 do_section_groups++;
b34976b6
AM
4026 do_segments++;
4027 do_version++;
4028 do_histogram++;
4029 do_arch++;
4030 do_notes++;
252b5132 4031 break;
f5842774
L
4032 case 'g':
4033 do_section_groups++;
4034 break;
5477e8a0 4035 case 't':
595cf52e 4036 case 'N':
5477e8a0
L
4037 do_sections++;
4038 do_section_details++;
595cf52e 4039 break;
252b5132 4040 case 'e':
b34976b6
AM
4041 do_header++;
4042 do_sections++;
4043 do_segments++;
252b5132 4044 break;
a952a375 4045 case 'A':
b34976b6 4046 do_arch++;
a952a375 4047 break;
252b5132 4048 case 'D':
b34976b6 4049 do_using_dynamic++;
252b5132
RH
4050 break;
4051 case 'r':
b34976b6 4052 do_reloc++;
252b5132 4053 break;
4d6ed7c8 4054 case 'u':
b34976b6 4055 do_unwind++;
4d6ed7c8 4056 break;
252b5132 4057 case 'h':
b34976b6 4058 do_header++;
252b5132
RH
4059 break;
4060 case 'l':
b34976b6 4061 do_segments++;
252b5132
RH
4062 break;
4063 case 's':
b34976b6 4064 do_syms++;
252b5132
RH
4065 break;
4066 case 'S':
b34976b6 4067 do_sections++;
252b5132
RH
4068 break;
4069 case 'd':
b34976b6 4070 do_dynamic++;
252b5132 4071 break;
a952a375 4072 case 'I':
b34976b6 4073 do_histogram++;
a952a375 4074 break;
779fe533 4075 case 'n':
b34976b6 4076 do_notes++;
779fe533 4077 break;
4145f1d5
NC
4078 case 'c':
4079 do_archive_index++;
4080 break;
252b5132 4081 case 'x':
cf13d699 4082 request_dump (HEX_DUMP);
aef1f6d0 4083 break;
09c11c86 4084 case 'p':
cf13d699
NC
4085 request_dump (STRING_DUMP);
4086 break;
4087 case 'R':
4088 request_dump (RELOC_DUMP);
09c11c86 4089 break;
252b5132 4090 case 'w':
b34976b6 4091 do_dump++;
252b5132 4092 if (optarg == 0)
613ff48b
CC
4093 {
4094 do_debugging = 1;
4095 dwarf_select_sections_all ();
4096 }
252b5132
RH
4097 else
4098 {
4099 do_debugging = 0;
4cb93e3b 4100 dwarf_select_sections_by_letters (optarg);
252b5132
RH
4101 }
4102 break;
2979dc34 4103 case OPTION_DEBUG_DUMP:
b34976b6 4104 do_dump++;
2979dc34
JJ
4105 if (optarg == 0)
4106 do_debugging = 1;
4107 else
4108 {
2979dc34 4109 do_debugging = 0;
4cb93e3b 4110 dwarf_select_sections_by_names (optarg);
2979dc34
JJ
4111 }
4112 break;
fd2f0033
TT
4113 case OPTION_DWARF_DEPTH:
4114 {
4115 char *cp;
4116
4117 dwarf_cutoff_level = strtoul (optarg, & cp, 0);
4118 }
4119 break;
4120 case OPTION_DWARF_START:
4121 {
4122 char *cp;
4123
4124 dwarf_start_die = strtoul (optarg, & cp, 0);
4125 }
4126 break;
4723351a
CC
4127 case OPTION_DWARF_CHECK:
4128 dwarf_check = 1;
4129 break;
2c610e4b
L
4130 case OPTION_DYN_SYMS:
4131 do_dyn_syms++;
4132 break;
252b5132
RH
4133#ifdef SUPPORT_DISASSEMBLY
4134 case 'i':
cf13d699
NC
4135 request_dump (DISASS_DUMP);
4136 break;
252b5132
RH
4137#endif
4138 case 'v':
4139 print_version (program_name);
4140 break;
4141 case 'V':
b34976b6 4142 do_version++;
252b5132 4143 break;
d974e256 4144 case 'W':
b34976b6 4145 do_wide++;
d974e256 4146 break;
252b5132 4147 default:
252b5132
RH
4148 /* xgettext:c-format */
4149 error (_("Invalid option '-%c'\n"), c);
4150 /* Drop through. */
4151 case '?':
92f01d61 4152 usage (stderr);
252b5132
RH
4153 }
4154 }
4155
4d6ed7c8 4156 if (!do_dynamic && !do_syms && !do_reloc && !do_unwind && !do_sections
252b5132 4157 && !do_segments && !do_header && !do_dump && !do_version
f5842774 4158 && !do_histogram && !do_debugging && !do_arch && !do_notes
2c610e4b
L
4159 && !do_section_groups && !do_archive_index
4160 && !do_dyn_syms)
92f01d61 4161 usage (stderr);
252b5132
RH
4162 else if (argc < 3)
4163 {
4164 warn (_("Nothing to do.\n"));
92f01d61 4165 usage (stderr);
252b5132
RH
4166 }
4167}
4168
4169static const char *
d3ba0551 4170get_elf_class (unsigned int elf_class)
252b5132 4171{
b34976b6 4172 static char buff[32];
103f02d3 4173
252b5132
RH
4174 switch (elf_class)
4175 {
4176 case ELFCLASSNONE: return _("none");
e3c8793a
NC
4177 case ELFCLASS32: return "ELF32";
4178 case ELFCLASS64: return "ELF64";
ab5e7794 4179 default:
e9e44622 4180 snprintf (buff, sizeof (buff), _("<unknown: %x>"), elf_class);
ab5e7794 4181 return buff;
252b5132
RH
4182 }
4183}
4184
4185static const char *
d3ba0551 4186get_data_encoding (unsigned int encoding)
252b5132 4187{
b34976b6 4188 static char buff[32];
103f02d3 4189
252b5132
RH
4190 switch (encoding)
4191 {
4192 case ELFDATANONE: return _("none");
33c63f9d
CM
4193 case ELFDATA2LSB: return _("2's complement, little endian");
4194 case ELFDATA2MSB: return _("2's complement, big endian");
103f02d3 4195 default:
e9e44622 4196 snprintf (buff, sizeof (buff), _("<unknown: %x>"), encoding);
ab5e7794 4197 return buff;
252b5132
RH
4198 }
4199}
4200
252b5132 4201/* Decode the data held in 'elf_header'. */
ee42cf8c 4202
252b5132 4203static int
d3ba0551 4204process_file_header (void)
252b5132 4205{
b34976b6
AM
4206 if ( elf_header.e_ident[EI_MAG0] != ELFMAG0
4207 || elf_header.e_ident[EI_MAG1] != ELFMAG1
4208 || elf_header.e_ident[EI_MAG2] != ELFMAG2
4209 || elf_header.e_ident[EI_MAG3] != ELFMAG3)
252b5132
RH
4210 {
4211 error
4212 (_("Not an ELF file - it has the wrong magic bytes at the start\n"));
4213 return 0;
4214 }
4215
2dc4cec1
L
4216 init_dwarf_regnames (elf_header.e_machine);
4217
252b5132
RH
4218 if (do_header)
4219 {
4220 int i;
4221
4222 printf (_("ELF Header:\n"));
4223 printf (_(" Magic: "));
b34976b6
AM
4224 for (i = 0; i < EI_NIDENT; i++)
4225 printf ("%2.2x ", elf_header.e_ident[i]);
252b5132
RH
4226 printf ("\n");
4227 printf (_(" Class: %s\n"),
b34976b6 4228 get_elf_class (elf_header.e_ident[EI_CLASS]));
252b5132 4229 printf (_(" Data: %s\n"),
b34976b6 4230 get_data_encoding (elf_header.e_ident[EI_DATA]));
252b5132 4231 printf (_(" Version: %d %s\n"),
b34976b6
AM
4232 elf_header.e_ident[EI_VERSION],
4233 (elf_header.e_ident[EI_VERSION] == EV_CURRENT
789be9f7 4234 ? "(current)"
b34976b6 4235 : (elf_header.e_ident[EI_VERSION] != EV_NONE
2b692964 4236 ? _("<unknown: %lx>")
789be9f7 4237 : "")));
252b5132 4238 printf (_(" OS/ABI: %s\n"),
b34976b6 4239 get_osabi_name (elf_header.e_ident[EI_OSABI]));
252b5132 4240 printf (_(" ABI Version: %d\n"),
b34976b6 4241 elf_header.e_ident[EI_ABIVERSION]);
252b5132
RH
4242 printf (_(" Type: %s\n"),
4243 get_file_type (elf_header.e_type));
4244 printf (_(" Machine: %s\n"),
4245 get_machine_name (elf_header.e_machine));
4246 printf (_(" Version: 0x%lx\n"),
4247 (unsigned long) elf_header.e_version);
76da6bbe 4248
f7a99963
NC
4249 printf (_(" Entry point address: "));
4250 print_vma ((bfd_vma) elf_header.e_entry, PREFIX_HEX);
4251 printf (_("\n Start of program headers: "));
4252 print_vma ((bfd_vma) elf_header.e_phoff, DEC);
4253 printf (_(" (bytes into file)\n Start of section headers: "));
4254 print_vma ((bfd_vma) elf_header.e_shoff, DEC);
4255 printf (_(" (bytes into file)\n"));
76da6bbe 4256
252b5132
RH
4257 printf (_(" Flags: 0x%lx%s\n"),
4258 (unsigned long) elf_header.e_flags,
4259 get_machine_flags (elf_header.e_flags, elf_header.e_machine));
4260 printf (_(" Size of this header: %ld (bytes)\n"),
4261 (long) elf_header.e_ehsize);
4262 printf (_(" Size of program headers: %ld (bytes)\n"),
4263 (long) elf_header.e_phentsize);
2046a35d 4264 printf (_(" Number of program headers: %ld"),
252b5132 4265 (long) elf_header.e_phnum);
2046a35d
AM
4266 if (section_headers != NULL
4267 && elf_header.e_phnum == PN_XNUM
4268 && section_headers[0].sh_info != 0)
cc5914eb 4269 printf (" (%ld)", (long) section_headers[0].sh_info);
2046a35d 4270 putc ('\n', stdout);
252b5132
RH
4271 printf (_(" Size of section headers: %ld (bytes)\n"),
4272 (long) elf_header.e_shentsize);
560f3c1c 4273 printf (_(" Number of section headers: %ld"),
252b5132 4274 (long) elf_header.e_shnum);
4fbb74a6 4275 if (section_headers != NULL && elf_header.e_shnum == SHN_UNDEF)
560f3c1c
AM
4276 printf (" (%ld)", (long) section_headers[0].sh_size);
4277 putc ('\n', stdout);
4278 printf (_(" Section header string table index: %ld"),
252b5132 4279 (long) elf_header.e_shstrndx);
4fbb74a6
AM
4280 if (section_headers != NULL
4281 && elf_header.e_shstrndx == (SHN_XINDEX & 0xffff))
72de5009 4282 printf (" (%u)", section_headers[0].sh_link);
15ba6505
AM
4283 else if (elf_header.e_shstrndx != SHN_UNDEF
4284 && elf_header.e_shstrndx >= elf_header.e_shnum)
2b692964 4285 printf (_(" <corrupt: out of range>"));
560f3c1c
AM
4286 putc ('\n', stdout);
4287 }
4288
4289 if (section_headers != NULL)
4290 {
2046a35d
AM
4291 if (elf_header.e_phnum == PN_XNUM
4292 && section_headers[0].sh_info != 0)
4293 elf_header.e_phnum = section_headers[0].sh_info;
4fbb74a6 4294 if (elf_header.e_shnum == SHN_UNDEF)
560f3c1c 4295 elf_header.e_shnum = section_headers[0].sh_size;
4fbb74a6 4296 if (elf_header.e_shstrndx == (SHN_XINDEX & 0xffff))
560f3c1c 4297 elf_header.e_shstrndx = section_headers[0].sh_link;
4fbb74a6 4298 else if (elf_header.e_shstrndx >= elf_header.e_shnum)
0b49d371 4299 elf_header.e_shstrndx = SHN_UNDEF;
560f3c1c
AM
4300 free (section_headers);
4301 section_headers = NULL;
252b5132 4302 }
103f02d3 4303
9ea033b2
NC
4304 return 1;
4305}
4306
e0a31db1 4307static bfd_boolean
91d6fa6a 4308get_32bit_program_headers (FILE * file, Elf_Internal_Phdr * pheaders)
9ea033b2 4309{
2cf0635d
NC
4310 Elf32_External_Phdr * phdrs;
4311 Elf32_External_Phdr * external;
4312 Elf_Internal_Phdr * internal;
b34976b6 4313 unsigned int i;
e0a31db1
NC
4314 unsigned int size = elf_header.e_phentsize;
4315 unsigned int num = elf_header.e_phnum;
4316
4317 /* PR binutils/17531: Cope with unexpected section header sizes. */
4318 if (size == 0 || num == 0)
4319 return FALSE;
4320 if (size < sizeof * phdrs)
4321 {
4322 error (_("The e_phentsize field in the ELF header is less than the size of an ELF program header\n"));
4323 return FALSE;
4324 }
4325 if (size > sizeof * phdrs)
4326 warn (_("The e_phentsize field in the ELF header is larger than the size of an ELF program header\n"));
103f02d3 4327
3f5e193b 4328 phdrs = (Elf32_External_Phdr *) get_data (NULL, file, elf_header.e_phoff,
e0a31db1
NC
4329 size, num, _("program headers"));
4330 if (phdrs == NULL)
4331 return FALSE;
9ea033b2 4332
91d6fa6a 4333 for (i = 0, internal = pheaders, external = phdrs;
9ea033b2 4334 i < elf_header.e_phnum;
b34976b6 4335 i++, internal++, external++)
252b5132 4336 {
9ea033b2
NC
4337 internal->p_type = BYTE_GET (external->p_type);
4338 internal->p_offset = BYTE_GET (external->p_offset);
4339 internal->p_vaddr = BYTE_GET (external->p_vaddr);
4340 internal->p_paddr = BYTE_GET (external->p_paddr);
4341 internal->p_filesz = BYTE_GET (external->p_filesz);
4342 internal->p_memsz = BYTE_GET (external->p_memsz);
4343 internal->p_flags = BYTE_GET (external->p_flags);
4344 internal->p_align = BYTE_GET (external->p_align);
252b5132
RH
4345 }
4346
9ea033b2 4347 free (phdrs);
e0a31db1 4348 return TRUE;
252b5132
RH
4349}
4350
e0a31db1 4351static bfd_boolean
91d6fa6a 4352get_64bit_program_headers (FILE * file, Elf_Internal_Phdr * pheaders)
9ea033b2 4353{
2cf0635d
NC
4354 Elf64_External_Phdr * phdrs;
4355 Elf64_External_Phdr * external;
4356 Elf_Internal_Phdr * internal;
b34976b6 4357 unsigned int i;
e0a31db1
NC
4358 unsigned int size = elf_header.e_phentsize;
4359 unsigned int num = elf_header.e_phnum;
4360
4361 /* PR binutils/17531: Cope with unexpected section header sizes. */
4362 if (size == 0 || num == 0)
4363 return FALSE;
4364 if (size < sizeof * phdrs)
4365 {
4366 error (_("The e_phentsize field in the ELF header is less than the size of an ELF program header\n"));
4367 return FALSE;
4368 }
4369 if (size > sizeof * phdrs)
4370 warn (_("The e_phentsize field in the ELF header is larger than the size of an ELF program header\n"));
103f02d3 4371
3f5e193b 4372 phdrs = (Elf64_External_Phdr *) get_data (NULL, file, elf_header.e_phoff,
e0a31db1 4373 size, num, _("program headers"));
a6e9f9df 4374 if (!phdrs)
e0a31db1 4375 return FALSE;
9ea033b2 4376
91d6fa6a 4377 for (i = 0, internal = pheaders, external = phdrs;
9ea033b2 4378 i < elf_header.e_phnum;
b34976b6 4379 i++, internal++, external++)
9ea033b2
NC
4380 {
4381 internal->p_type = BYTE_GET (external->p_type);
4382 internal->p_flags = BYTE_GET (external->p_flags);
66543521
AM
4383 internal->p_offset = BYTE_GET (external->p_offset);
4384 internal->p_vaddr = BYTE_GET (external->p_vaddr);
4385 internal->p_paddr = BYTE_GET (external->p_paddr);
4386 internal->p_filesz = BYTE_GET (external->p_filesz);
4387 internal->p_memsz = BYTE_GET (external->p_memsz);
4388 internal->p_align = BYTE_GET (external->p_align);
9ea033b2
NC
4389 }
4390
4391 free (phdrs);
e0a31db1 4392 return TRUE;
9ea033b2 4393}
252b5132 4394
d93f0186
NC
4395/* Returns 1 if the program headers were read into `program_headers'. */
4396
4397static int
2cf0635d 4398get_program_headers (FILE * file)
d93f0186 4399{
2cf0635d 4400 Elf_Internal_Phdr * phdrs;
d93f0186
NC
4401
4402 /* Check cache of prior read. */
4403 if (program_headers != NULL)
4404 return 1;
4405
3f5e193b
NC
4406 phdrs = (Elf_Internal_Phdr *) cmalloc (elf_header.e_phnum,
4407 sizeof (Elf_Internal_Phdr));
d93f0186
NC
4408
4409 if (phdrs == NULL)
4410 {
8b73c356
NC
4411 error (_("Out of memory reading %u program headers\n"),
4412 elf_header.e_phnum);
d93f0186
NC
4413 return 0;
4414 }
4415
4416 if (is_32bit_elf
4417 ? get_32bit_program_headers (file, phdrs)
4418 : get_64bit_program_headers (file, phdrs))
4419 {
4420 program_headers = phdrs;
4421 return 1;
4422 }
4423
4424 free (phdrs);
4425 return 0;
4426}
4427
2f62977e
NC
4428/* Returns 1 if the program headers were loaded. */
4429
252b5132 4430static int
2cf0635d 4431process_program_headers (FILE * file)
252b5132 4432{
2cf0635d 4433 Elf_Internal_Phdr * segment;
b34976b6 4434 unsigned int i;
252b5132
RH
4435
4436 if (elf_header.e_phnum == 0)
4437 {
82f2dbf7
NC
4438 /* PR binutils/12467. */
4439 if (elf_header.e_phoff != 0)
4440 warn (_("possibly corrupt ELF header - it has a non-zero program"
4441 " header offset, but no program headers"));
4442 else if (do_segments)
252b5132 4443 printf (_("\nThere are no program headers in this file.\n"));
2f62977e 4444 return 0;
252b5132
RH
4445 }
4446
4447 if (do_segments && !do_header)
4448 {
f7a99963
NC
4449 printf (_("\nElf file type is %s\n"), get_file_type (elf_header.e_type));
4450 printf (_("Entry point "));
4451 print_vma ((bfd_vma) elf_header.e_entry, PREFIX_HEX);
4452 printf (_("\nThere are %d program headers, starting at offset "),
4453 elf_header.e_phnum);
4454 print_vma ((bfd_vma) elf_header.e_phoff, DEC);
4455 printf ("\n");
252b5132
RH
4456 }
4457
d93f0186 4458 if (! get_program_headers (file))
252b5132 4459 return 0;
103f02d3 4460
252b5132
RH
4461 if (do_segments)
4462 {
3a1a2036
NC
4463 if (elf_header.e_phnum > 1)
4464 printf (_("\nProgram Headers:\n"));
4465 else
4466 printf (_("\nProgram Headers:\n"));
76da6bbe 4467
f7a99963
NC
4468 if (is_32bit_elf)
4469 printf
4470 (_(" Type Offset VirtAddr PhysAddr FileSiz MemSiz Flg Align\n"));
d974e256
JJ
4471 else if (do_wide)
4472 printf
4473 (_(" Type Offset VirtAddr PhysAddr FileSiz MemSiz Flg Align\n"));
f7a99963
NC
4474 else
4475 {
4476 printf
4477 (_(" Type Offset VirtAddr PhysAddr\n"));
4478 printf
4479 (_(" FileSiz MemSiz Flags Align\n"));
4480 }
252b5132
RH
4481 }
4482
252b5132 4483 dynamic_addr = 0;
1b228002 4484 dynamic_size = 0;
252b5132
RH
4485
4486 for (i = 0, segment = program_headers;
4487 i < elf_header.e_phnum;
b34976b6 4488 i++, segment++)
252b5132
RH
4489 {
4490 if (do_segments)
4491 {
103f02d3 4492 printf (" %-14.14s ", get_segment_type (segment->p_type));
f7a99963
NC
4493
4494 if (is_32bit_elf)
4495 {
4496 printf ("0x%6.6lx ", (unsigned long) segment->p_offset);
4497 printf ("0x%8.8lx ", (unsigned long) segment->p_vaddr);
4498 printf ("0x%8.8lx ", (unsigned long) segment->p_paddr);
4499 printf ("0x%5.5lx ", (unsigned long) segment->p_filesz);
4500 printf ("0x%5.5lx ", (unsigned long) segment->p_memsz);
4501 printf ("%c%c%c ",
4502 (segment->p_flags & PF_R ? 'R' : ' '),
4503 (segment->p_flags & PF_W ? 'W' : ' '),
4504 (segment->p_flags & PF_X ? 'E' : ' '));
4505 printf ("%#lx", (unsigned long) segment->p_align);
4506 }
d974e256
JJ
4507 else if (do_wide)
4508 {
4509 if ((unsigned long) segment->p_offset == segment->p_offset)
4510 printf ("0x%6.6lx ", (unsigned long) segment->p_offset);
4511 else
4512 {
4513 print_vma (segment->p_offset, FULL_HEX);
4514 putchar (' ');
4515 }
4516
4517 print_vma (segment->p_vaddr, FULL_HEX);
4518 putchar (' ');
4519 print_vma (segment->p_paddr, FULL_HEX);
4520 putchar (' ');
4521
4522 if ((unsigned long) segment->p_filesz == segment->p_filesz)
4523 printf ("0x%6.6lx ", (unsigned long) segment->p_filesz);
4524 else
4525 {
4526 print_vma (segment->p_filesz, FULL_HEX);
4527 putchar (' ');
4528 }
4529
4530 if ((unsigned long) segment->p_memsz == segment->p_memsz)
4531 printf ("0x%6.6lx", (unsigned long) segment->p_memsz);
4532 else
4533 {
f48e6c45 4534 print_vma (segment->p_memsz, FULL_HEX);
d974e256
JJ
4535 }
4536
4537 printf (" %c%c%c ",
4538 (segment->p_flags & PF_R ? 'R' : ' '),
4539 (segment->p_flags & PF_W ? 'W' : ' '),
4540 (segment->p_flags & PF_X ? 'E' : ' '));
4541
4542 if ((unsigned long) segment->p_align == segment->p_align)
4543 printf ("%#lx", (unsigned long) segment->p_align);
4544 else
4545 {
4546 print_vma (segment->p_align, PREFIX_HEX);
4547 }
4548 }
f7a99963
NC
4549 else
4550 {
4551 print_vma (segment->p_offset, FULL_HEX);
4552 putchar (' ');
4553 print_vma (segment->p_vaddr, FULL_HEX);
4554 putchar (' ');
4555 print_vma (segment->p_paddr, FULL_HEX);
4556 printf ("\n ");
4557 print_vma (segment->p_filesz, FULL_HEX);
4558 putchar (' ');
4559 print_vma (segment->p_memsz, FULL_HEX);
4560 printf (" %c%c%c ",
4561 (segment->p_flags & PF_R ? 'R' : ' '),
4562 (segment->p_flags & PF_W ? 'W' : ' '),
4563 (segment->p_flags & PF_X ? 'E' : ' '));
4564 print_vma (segment->p_align, HEX);
4565 }
252b5132
RH
4566 }
4567
f54498b4
NC
4568 if (do_segments)
4569 putc ('\n', stdout);
4570
252b5132
RH
4571 switch (segment->p_type)
4572 {
252b5132
RH
4573 case PT_DYNAMIC:
4574 if (dynamic_addr)
4575 error (_("more than one dynamic segment\n"));
4576
20737c13
AM
4577 /* By default, assume that the .dynamic section is the first
4578 section in the DYNAMIC segment. */
4579 dynamic_addr = segment->p_offset;
4580 dynamic_size = segment->p_filesz;
f54498b4
NC
4581 /* PR binutils/17512: Avoid corrupt dynamic section info in the segment. */
4582 if (dynamic_addr + dynamic_size >= current_file_size)
4583 {
4584 error (_("the dynamic segment offset + size exceeds the size of the file\n"));
4585 dynamic_addr = dynamic_size = 0;
4586 }
20737c13 4587
b2d38a17
NC
4588 /* Try to locate the .dynamic section. If there is
4589 a section header table, we can easily locate it. */
4590 if (section_headers != NULL)
4591 {
2cf0635d 4592 Elf_Internal_Shdr * sec;
b2d38a17 4593
89fac5e3
RS
4594 sec = find_section (".dynamic");
4595 if (sec == NULL || sec->sh_size == 0)
b2d38a17 4596 {
28f997cf
TG
4597 /* A corresponding .dynamic section is expected, but on
4598 IA-64/OpenVMS it is OK for it to be missing. */
4599 if (!is_ia64_vms ())
4600 error (_("no .dynamic section in the dynamic segment\n"));
b2d38a17
NC
4601 break;
4602 }
4603
42bb2e33 4604 if (sec->sh_type == SHT_NOBITS)
20737c13
AM
4605 {
4606 dynamic_size = 0;
4607 break;
4608 }
42bb2e33 4609
b2d38a17
NC
4610 dynamic_addr = sec->sh_offset;
4611 dynamic_size = sec->sh_size;
4612
4613 if (dynamic_addr < segment->p_offset
4614 || dynamic_addr > segment->p_offset + segment->p_filesz)
20737c13
AM
4615 warn (_("the .dynamic section is not contained"
4616 " within the dynamic segment\n"));
b2d38a17 4617 else if (dynamic_addr > segment->p_offset)
20737c13
AM
4618 warn (_("the .dynamic section is not the first section"
4619 " in the dynamic segment.\n"));
b2d38a17 4620 }
252b5132
RH
4621 break;
4622
4623 case PT_INTERP:
fb52b2f4
NC
4624 if (fseek (file, archive_file_offset + (long) segment->p_offset,
4625 SEEK_SET))
252b5132
RH
4626 error (_("Unable to find program interpreter name\n"));
4627 else
4628 {
f8eae8b2 4629 char fmt [32];
9495b2e6 4630 int ret = snprintf (fmt, sizeof (fmt), "%%%ds", PATH_MAX - 1);
f8eae8b2
L
4631
4632 if (ret >= (int) sizeof (fmt) || ret < 0)
591a748a 4633 error (_("Internal error: failed to create format string to display program interpreter\n"));
f8eae8b2 4634
252b5132 4635 program_interpreter[0] = 0;
7bd7b3ef
AM
4636 if (fscanf (file, fmt, program_interpreter) <= 0)
4637 error (_("Unable to read program interpreter name\n"));
252b5132
RH
4638
4639 if (do_segments)
f54498b4 4640 printf (_(" [Requesting program interpreter: %s]\n"),
252b5132
RH
4641 program_interpreter);
4642 }
4643 break;
4644 }
252b5132
RH
4645 }
4646
c256ffe7 4647 if (do_segments && section_headers != NULL && string_table != NULL)
252b5132
RH
4648 {
4649 printf (_("\n Section to Segment mapping:\n"));
4650 printf (_(" Segment Sections...\n"));
4651
252b5132
RH
4652 for (i = 0; i < elf_header.e_phnum; i++)
4653 {
9ad5cbcf 4654 unsigned int j;
2cf0635d 4655 Elf_Internal_Shdr * section;
252b5132
RH
4656
4657 segment = program_headers + i;
b391a3e3 4658 section = section_headers + 1;
252b5132
RH
4659
4660 printf (" %2.2d ", i);
4661
b34976b6 4662 for (j = 1; j < elf_header.e_shnum; j++, section++)
252b5132 4663 {
f4638467
AM
4664 if (!ELF_TBSS_SPECIAL (section, segment)
4665 && ELF_SECTION_IN_SEGMENT_STRICT (section, segment))
74e1a04b 4666 printf ("%s ", printable_section_name (section));
252b5132
RH
4667 }
4668
4669 putc ('\n',stdout);
4670 }
4671 }
4672
252b5132
RH
4673 return 1;
4674}
4675
4676
d93f0186
NC
4677/* Find the file offset corresponding to VMA by using the program headers. */
4678
4679static long
2cf0635d 4680offset_from_vma (FILE * file, bfd_vma vma, bfd_size_type size)
d93f0186 4681{
2cf0635d 4682 Elf_Internal_Phdr * seg;
d93f0186
NC
4683
4684 if (! get_program_headers (file))
4685 {
4686 warn (_("Cannot interpret virtual addresses without program headers.\n"));
4687 return (long) vma;
4688 }
4689
4690 for (seg = program_headers;
4691 seg < program_headers + elf_header.e_phnum;
4692 ++seg)
4693 {
4694 if (seg->p_type != PT_LOAD)
4695 continue;
4696
4697 if (vma >= (seg->p_vaddr & -seg->p_align)
4698 && vma + size <= seg->p_vaddr + seg->p_filesz)
4699 return vma - seg->p_vaddr + seg->p_offset;
4700 }
4701
4702 warn (_("Virtual address 0x%lx not located in any PT_LOAD segment.\n"),
0af1713e 4703 (unsigned long) vma);
d93f0186
NC
4704 return (long) vma;
4705}
4706
4707
049b0c3a
NC
4708/* Allocate memory and load the sections headers into the global pointer
4709 SECTION_HEADERS. If PROBE is true, this is just a probe and we do not
4710 generate any error messages if the load fails. */
4711
4712static bfd_boolean
4713get_32bit_section_headers (FILE * file, bfd_boolean probe)
252b5132 4714{
2cf0635d
NC
4715 Elf32_External_Shdr * shdrs;
4716 Elf_Internal_Shdr * internal;
b34976b6 4717 unsigned int i;
049b0c3a
NC
4718 unsigned int size = elf_header.e_shentsize;
4719 unsigned int num = probe ? 1 : elf_header.e_shnum;
4720
4721 /* PR binutils/17531: Cope with unexpected section header sizes. */
4722 if (size == 0 || num == 0)
4723 return FALSE;
4724 if (size < sizeof * shdrs)
4725 {
4726 if (! probe)
4727 error (_("The e_shentsize field in the ELF header is less than the size of an ELF section header\n"));
4728 return FALSE;
4729 }
4730 if (!probe && size > sizeof * shdrs)
4731 warn (_("The e_shentsize field in the ELF header is larger than the size of an ELF section header\n"));
252b5132 4732
3f5e193b 4733 shdrs = (Elf32_External_Shdr *) get_data (NULL, file, elf_header.e_shoff,
049b0c3a
NC
4734 size, num,
4735 probe ? NULL : _("section headers"));
4736 if (shdrs == NULL)
4737 return FALSE;
252b5132 4738
049b0c3a
NC
4739 if (section_headers != NULL)
4740 free (section_headers);
3f5e193b
NC
4741 section_headers = (Elf_Internal_Shdr *) cmalloc (num,
4742 sizeof (Elf_Internal_Shdr));
252b5132
RH
4743 if (section_headers == NULL)
4744 {
049b0c3a 4745 if (!probe)
8b73c356 4746 error (_("Out of memory reading %u section headers\n"), num);
049b0c3a 4747 return FALSE;
252b5132
RH
4748 }
4749
4750 for (i = 0, internal = section_headers;
560f3c1c 4751 i < num;
b34976b6 4752 i++, internal++)
252b5132
RH
4753 {
4754 internal->sh_name = BYTE_GET (shdrs[i].sh_name);
4755 internal->sh_type = BYTE_GET (shdrs[i].sh_type);
4756 internal->sh_flags = BYTE_GET (shdrs[i].sh_flags);
4757 internal->sh_addr = BYTE_GET (shdrs[i].sh_addr);
4758 internal->sh_offset = BYTE_GET (shdrs[i].sh_offset);
4759 internal->sh_size = BYTE_GET (shdrs[i].sh_size);
4760 internal->sh_link = BYTE_GET (shdrs[i].sh_link);
4761 internal->sh_info = BYTE_GET (shdrs[i].sh_info);
4762 internal->sh_addralign = BYTE_GET (shdrs[i].sh_addralign);
4763 internal->sh_entsize = BYTE_GET (shdrs[i].sh_entsize);
4764 }
4765
4766 free (shdrs);
049b0c3a 4767 return TRUE;
252b5132
RH
4768}
4769
049b0c3a
NC
4770static bfd_boolean
4771get_64bit_section_headers (FILE * file, bfd_boolean probe)
9ea033b2 4772{
2cf0635d
NC
4773 Elf64_External_Shdr * shdrs;
4774 Elf_Internal_Shdr * internal;
b34976b6 4775 unsigned int i;
049b0c3a
NC
4776 unsigned int size = elf_header.e_shentsize;
4777 unsigned int num = probe ? 1 : elf_header.e_shnum;
4778
4779 /* PR binutils/17531: Cope with unexpected section header sizes. */
4780 if (size == 0 || num == 0)
4781 return FALSE;
4782 if (size < sizeof * shdrs)
4783 {
4784 if (! probe)
4785 error (_("The e_shentsize field in the ELF header is less than the size of an ELF section header\n"));
4786 return FALSE;
4787 }
4788 if (! probe && size > sizeof * shdrs)
4789 warn (_("The e_shentsize field in the ELF header is larger than the size of an ELF section header\n"));
9ea033b2 4790
3f5e193b 4791 shdrs = (Elf64_External_Shdr *) get_data (NULL, file, elf_header.e_shoff,
049b0c3a
NC
4792 size, num,
4793 probe ? NULL : _("section headers"));
4794 if (shdrs == NULL)
4795 return FALSE;
9ea033b2 4796
049b0c3a
NC
4797 if (section_headers != NULL)
4798 free (section_headers);
3f5e193b
NC
4799 section_headers = (Elf_Internal_Shdr *) cmalloc (num,
4800 sizeof (Elf_Internal_Shdr));
9ea033b2
NC
4801 if (section_headers == NULL)
4802 {
049b0c3a 4803 if (! probe)
8b73c356 4804 error (_("Out of memory reading %u section headers\n"), num);
049b0c3a 4805 return FALSE;
9ea033b2
NC
4806 }
4807
4808 for (i = 0, internal = section_headers;
560f3c1c 4809 i < num;
b34976b6 4810 i++, internal++)
9ea033b2
NC
4811 {
4812 internal->sh_name = BYTE_GET (shdrs[i].sh_name);
4813 internal->sh_type = BYTE_GET (shdrs[i].sh_type);
66543521
AM
4814 internal->sh_flags = BYTE_GET (shdrs[i].sh_flags);
4815 internal->sh_addr = BYTE_GET (shdrs[i].sh_addr);
4816 internal->sh_size = BYTE_GET (shdrs[i].sh_size);
4817 internal->sh_entsize = BYTE_GET (shdrs[i].sh_entsize);
9ea033b2
NC
4818 internal->sh_link = BYTE_GET (shdrs[i].sh_link);
4819 internal->sh_info = BYTE_GET (shdrs[i].sh_info);
4820 internal->sh_offset = BYTE_GET (shdrs[i].sh_offset);
4821 internal->sh_addralign = BYTE_GET (shdrs[i].sh_addralign);
4822 }
4823
4824 free (shdrs);
049b0c3a 4825 return TRUE;
9ea033b2
NC
4826}
4827
252b5132 4828static Elf_Internal_Sym *
ba5cdace
NC
4829get_32bit_elf_symbols (FILE * file,
4830 Elf_Internal_Shdr * section,
4831 unsigned long * num_syms_return)
252b5132 4832{
ba5cdace 4833 unsigned long number = 0;
dd24e3da 4834 Elf32_External_Sym * esyms = NULL;
ba5cdace 4835 Elf_External_Sym_Shndx * shndx = NULL;
dd24e3da 4836 Elf_Internal_Sym * isyms = NULL;
2cf0635d 4837 Elf_Internal_Sym * psym;
b34976b6 4838 unsigned int j;
252b5132 4839
c9c1d674
EG
4840 if (section->sh_size == 0)
4841 {
4842 if (num_syms_return != NULL)
4843 * num_syms_return = 0;
4844 return NULL;
4845 }
4846
dd24e3da 4847 /* Run some sanity checks first. */
c9c1d674 4848 if (section->sh_entsize == 0 || section->sh_entsize > section->sh_size)
dd24e3da 4849 {
c9c1d674
EG
4850 error (_("Section %s has an invalid sh_entsize of 0x%lx\n"),
4851 printable_section_name (section), (unsigned long) section->sh_entsize);
ba5cdace 4852 goto exit_point;
dd24e3da
NC
4853 }
4854
f54498b4
NC
4855 if (section->sh_size > current_file_size)
4856 {
4857 error (_("Section %s has an invalid sh_size of 0x%lx\n"),
74e1a04b 4858 printable_section_name (section), (unsigned long) section->sh_size);
f54498b4
NC
4859 goto exit_point;
4860 }
4861
dd24e3da
NC
4862 number = section->sh_size / section->sh_entsize;
4863
4864 if (number * sizeof (Elf32_External_Sym) > section->sh_size + 1)
4865 {
c9c1d674 4866 error (_("Size (0x%lx) of section %s is not a multiple of its sh_entsize (0x%lx)\n"),
8066deb1
AM
4867 (unsigned long) section->sh_size,
4868 printable_section_name (section),
4869 (unsigned long) section->sh_entsize);
ba5cdace 4870 goto exit_point;
dd24e3da
NC
4871 }
4872
3f5e193b
NC
4873 esyms = (Elf32_External_Sym *) get_data (NULL, file, section->sh_offset, 1,
4874 section->sh_size, _("symbols"));
dd24e3da 4875 if (esyms == NULL)
ba5cdace 4876 goto exit_point;
252b5132 4877
9ad5cbcf
AM
4878 shndx = NULL;
4879 if (symtab_shndx_hdr != NULL
4880 && (symtab_shndx_hdr->sh_link
4fbb74a6 4881 == (unsigned long) (section - section_headers)))
9ad5cbcf 4882 {
3f5e193b
NC
4883 shndx = (Elf_External_Sym_Shndx *) get_data (NULL, file,
4884 symtab_shndx_hdr->sh_offset,
4885 1, symtab_shndx_hdr->sh_size,
9cf03b7e 4886 _("symbol table section indicies"));
dd24e3da
NC
4887 if (shndx == NULL)
4888 goto exit_point;
c9c1d674
EG
4889 /* PR17531: file: heap-buffer-overflow */
4890 else if (symtab_shndx_hdr->sh_size / sizeof (Elf_External_Sym_Shndx) < number)
4891 {
4892 error (_("Index section %s has an sh_size of 0x%lx - expected 0x%lx\n"),
4893 printable_section_name (symtab_shndx_hdr),
4894 (unsigned long) symtab_shndx_hdr->sh_size,
4895 (unsigned long) section->sh_size);
4896 goto exit_point;
4897 }
9ad5cbcf
AM
4898 }
4899
3f5e193b 4900 isyms = (Elf_Internal_Sym *) cmalloc (number, sizeof (Elf_Internal_Sym));
252b5132
RH
4901
4902 if (isyms == NULL)
4903 {
8b73c356
NC
4904 error (_("Out of memory reading %lu symbols\n"),
4905 (unsigned long) number);
dd24e3da 4906 goto exit_point;
252b5132
RH
4907 }
4908
dd24e3da 4909 for (j = 0, psym = isyms; j < number; j++, psym++)
252b5132
RH
4910 {
4911 psym->st_name = BYTE_GET (esyms[j].st_name);
4912 psym->st_value = BYTE_GET (esyms[j].st_value);
4913 psym->st_size = BYTE_GET (esyms[j].st_size);
4914 psym->st_shndx = BYTE_GET (esyms[j].st_shndx);
4fbb74a6 4915 if (psym->st_shndx == (SHN_XINDEX & 0xffff) && shndx != NULL)
9ad5cbcf
AM
4916 psym->st_shndx
4917 = byte_get ((unsigned char *) &shndx[j], sizeof (shndx[j]));
4fbb74a6
AM
4918 else if (psym->st_shndx >= (SHN_LORESERVE & 0xffff))
4919 psym->st_shndx += SHN_LORESERVE - (SHN_LORESERVE & 0xffff);
252b5132
RH
4920 psym->st_info = BYTE_GET (esyms[j].st_info);
4921 psym->st_other = BYTE_GET (esyms[j].st_other);
4922 }
4923
dd24e3da 4924 exit_point:
ba5cdace 4925 if (shndx != NULL)
9ad5cbcf 4926 free (shndx);
ba5cdace 4927 if (esyms != NULL)
dd24e3da 4928 free (esyms);
252b5132 4929
ba5cdace
NC
4930 if (num_syms_return != NULL)
4931 * num_syms_return = isyms == NULL ? 0 : number;
4932
252b5132
RH
4933 return isyms;
4934}
4935
9ea033b2 4936static Elf_Internal_Sym *
ba5cdace
NC
4937get_64bit_elf_symbols (FILE * file,
4938 Elf_Internal_Shdr * section,
4939 unsigned long * num_syms_return)
9ea033b2 4940{
ba5cdace
NC
4941 unsigned long number = 0;
4942 Elf64_External_Sym * esyms = NULL;
4943 Elf_External_Sym_Shndx * shndx = NULL;
4944 Elf_Internal_Sym * isyms = NULL;
2cf0635d 4945 Elf_Internal_Sym * psym;
b34976b6 4946 unsigned int j;
9ea033b2 4947
c9c1d674
EG
4948 if (section->sh_size == 0)
4949 {
4950 if (num_syms_return != NULL)
4951 * num_syms_return = 0;
4952 return NULL;
4953 }
4954
dd24e3da 4955 /* Run some sanity checks first. */
c9c1d674 4956 if (section->sh_entsize == 0 || section->sh_entsize > section->sh_size)
dd24e3da 4957 {
c9c1d674 4958 error (_("Section %s has an invalid sh_entsize of 0x%lx\n"),
8066deb1
AM
4959 printable_section_name (section),
4960 (unsigned long) section->sh_entsize);
ba5cdace 4961 goto exit_point;
dd24e3da
NC
4962 }
4963
f54498b4
NC
4964 if (section->sh_size > current_file_size)
4965 {
4966 error (_("Section %s has an invalid sh_size of 0x%lx\n"),
8066deb1
AM
4967 printable_section_name (section),
4968 (unsigned long) section->sh_size);
f54498b4
NC
4969 goto exit_point;
4970 }
4971
dd24e3da
NC
4972 number = section->sh_size / section->sh_entsize;
4973
4974 if (number * sizeof (Elf64_External_Sym) > section->sh_size + 1)
4975 {
c9c1d674 4976 error (_("Size (0x%lx) of section %s is not a multiple of its sh_entsize (0x%lx)\n"),
8066deb1
AM
4977 (unsigned long) section->sh_size,
4978 printable_section_name (section),
4979 (unsigned long) section->sh_entsize);
ba5cdace 4980 goto exit_point;
dd24e3da
NC
4981 }
4982
3f5e193b
NC
4983 esyms = (Elf64_External_Sym *) get_data (NULL, file, section->sh_offset, 1,
4984 section->sh_size, _("symbols"));
a6e9f9df 4985 if (!esyms)
ba5cdace 4986 goto exit_point;
9ea033b2 4987
9ad5cbcf
AM
4988 if (symtab_shndx_hdr != NULL
4989 && (symtab_shndx_hdr->sh_link
4fbb74a6 4990 == (unsigned long) (section - section_headers)))
9ad5cbcf 4991 {
3f5e193b
NC
4992 shndx = (Elf_External_Sym_Shndx *) get_data (NULL, file,
4993 symtab_shndx_hdr->sh_offset,
4994 1, symtab_shndx_hdr->sh_size,
9cf03b7e 4995 _("symbol table section indicies"));
ba5cdace
NC
4996 if (shndx == NULL)
4997 goto exit_point;
c9c1d674
EG
4998 else if (symtab_shndx_hdr->sh_size / sizeof (Elf_External_Sym_Shndx) < number)
4999 {
5000 error (_("Index section %s has an sh_size of 0x%lx - expected 0x%lx\n"),
5001 printable_section_name (symtab_shndx_hdr),
5002 (unsigned long) symtab_shndx_hdr->sh_size,
5003 (unsigned long) section->sh_size);
5004 goto exit_point;
5005 }
9ad5cbcf
AM
5006 }
5007
3f5e193b 5008 isyms = (Elf_Internal_Sym *) cmalloc (number, sizeof (Elf_Internal_Sym));
9ea033b2
NC
5009
5010 if (isyms == NULL)
5011 {
8b73c356
NC
5012 error (_("Out of memory reading %lu symbols\n"),
5013 (unsigned long) number);
ba5cdace 5014 goto exit_point;
9ea033b2
NC
5015 }
5016
ba5cdace 5017 for (j = 0, psym = isyms; j < number; j++, psym++)
9ea033b2
NC
5018 {
5019 psym->st_name = BYTE_GET (esyms[j].st_name);
5020 psym->st_info = BYTE_GET (esyms[j].st_info);
5021 psym->st_other = BYTE_GET (esyms[j].st_other);
5022 psym->st_shndx = BYTE_GET (esyms[j].st_shndx);
ba5cdace 5023
4fbb74a6 5024 if (psym->st_shndx == (SHN_XINDEX & 0xffff) && shndx != NULL)
9ad5cbcf
AM
5025 psym->st_shndx
5026 = byte_get ((unsigned char *) &shndx[j], sizeof (shndx[j]));
4fbb74a6
AM
5027 else if (psym->st_shndx >= (SHN_LORESERVE & 0xffff))
5028 psym->st_shndx += SHN_LORESERVE - (SHN_LORESERVE & 0xffff);
ba5cdace 5029
66543521
AM
5030 psym->st_value = BYTE_GET (esyms[j].st_value);
5031 psym->st_size = BYTE_GET (esyms[j].st_size);
9ea033b2
NC
5032 }
5033
ba5cdace
NC
5034 exit_point:
5035 if (shndx != NULL)
9ad5cbcf 5036 free (shndx);
ba5cdace
NC
5037 if (esyms != NULL)
5038 free (esyms);
5039
5040 if (num_syms_return != NULL)
5041 * num_syms_return = isyms == NULL ? 0 : number;
9ea033b2
NC
5042
5043 return isyms;
5044}
5045
d1133906 5046static const char *
d3ba0551 5047get_elf_section_flags (bfd_vma sh_flags)
d1133906 5048{
5477e8a0 5049 static char buff[1024];
2cf0635d 5050 char * p = buff;
8d5ff12c 5051 int field_size = is_32bit_elf ? 8 : 16;
91d6fa6a
NC
5052 int sindex;
5053 int size = sizeof (buff) - (field_size + 4 + 1);
8d5ff12c
L
5054 bfd_vma os_flags = 0;
5055 bfd_vma proc_flags = 0;
5056 bfd_vma unknown_flags = 0;
148b93f2 5057 static const struct
5477e8a0 5058 {
2cf0635d 5059 const char * str;
5477e8a0
L
5060 int len;
5061 }
5062 flags [] =
5063 {
cfcac11d
NC
5064 /* 0 */ { STRING_COMMA_LEN ("WRITE") },
5065 /* 1 */ { STRING_COMMA_LEN ("ALLOC") },
5066 /* 2 */ { STRING_COMMA_LEN ("EXEC") },
5067 /* 3 */ { STRING_COMMA_LEN ("MERGE") },
5068 /* 4 */ { STRING_COMMA_LEN ("STRINGS") },
5069 /* 5 */ { STRING_COMMA_LEN ("INFO LINK") },
5070 /* 6 */ { STRING_COMMA_LEN ("LINK ORDER") },
5071 /* 7 */ { STRING_COMMA_LEN ("OS NONCONF") },
5072 /* 8 */ { STRING_COMMA_LEN ("GROUP") },
5073 /* 9 */ { STRING_COMMA_LEN ("TLS") },
5074 /* IA-64 specific. */
5075 /* 10 */ { STRING_COMMA_LEN ("SHORT") },
5076 /* 11 */ { STRING_COMMA_LEN ("NORECOV") },
5077 /* IA-64 OpenVMS specific. */
5078 /* 12 */ { STRING_COMMA_LEN ("VMS_GLOBAL") },
5079 /* 13 */ { STRING_COMMA_LEN ("VMS_OVERLAID") },
5080 /* 14 */ { STRING_COMMA_LEN ("VMS_SHARED") },
5081 /* 15 */ { STRING_COMMA_LEN ("VMS_VECTOR") },
5082 /* 16 */ { STRING_COMMA_LEN ("VMS_ALLOC_64BIT") },
5083 /* 17 */ { STRING_COMMA_LEN ("VMS_PROTECTED") },
18ae9cc1 5084 /* Generic. */
cfcac11d 5085 /* 18 */ { STRING_COMMA_LEN ("EXCLUDE") },
18ae9cc1 5086 /* SPARC specific. */
cfcac11d 5087 /* 19 */ { STRING_COMMA_LEN ("ORDERED") }
5477e8a0
L
5088 };
5089
5090 if (do_section_details)
5091 {
8d5ff12c
L
5092 sprintf (buff, "[%*.*lx]: ",
5093 field_size, field_size, (unsigned long) sh_flags);
5094 p += field_size + 4;
5477e8a0 5095 }
76da6bbe 5096
d1133906
NC
5097 while (sh_flags)
5098 {
5099 bfd_vma flag;
5100
5101 flag = sh_flags & - sh_flags;
5102 sh_flags &= ~ flag;
76da6bbe 5103
5477e8a0 5104 if (do_section_details)
d1133906 5105 {
5477e8a0
L
5106 switch (flag)
5107 {
91d6fa6a
NC
5108 case SHF_WRITE: sindex = 0; break;
5109 case SHF_ALLOC: sindex = 1; break;
5110 case SHF_EXECINSTR: sindex = 2; break;
5111 case SHF_MERGE: sindex = 3; break;
5112 case SHF_STRINGS: sindex = 4; break;
5113 case SHF_INFO_LINK: sindex = 5; break;
5114 case SHF_LINK_ORDER: sindex = 6; break;
5115 case SHF_OS_NONCONFORMING: sindex = 7; break;
5116 case SHF_GROUP: sindex = 8; break;
5117 case SHF_TLS: sindex = 9; break;
18ae9cc1 5118 case SHF_EXCLUDE: sindex = 18; break;
76da6bbe 5119
5477e8a0 5120 default:
91d6fa6a 5121 sindex = -1;
cfcac11d 5122 switch (elf_header.e_machine)
148b93f2 5123 {
cfcac11d 5124 case EM_IA_64:
148b93f2 5125 if (flag == SHF_IA_64_SHORT)
91d6fa6a 5126 sindex = 10;
148b93f2 5127 else if (flag == SHF_IA_64_NORECOV)
91d6fa6a 5128 sindex = 11;
148b93f2
NC
5129#ifdef BFD64
5130 else if (elf_header.e_ident[EI_OSABI] == ELFOSABI_OPENVMS)
5131 switch (flag)
5132 {
91d6fa6a
NC
5133 case SHF_IA_64_VMS_GLOBAL: sindex = 12; break;
5134 case SHF_IA_64_VMS_OVERLAID: sindex = 13; break;
5135 case SHF_IA_64_VMS_SHARED: sindex = 14; break;
5136 case SHF_IA_64_VMS_VECTOR: sindex = 15; break;
5137 case SHF_IA_64_VMS_ALLOC_64BIT: sindex = 16; break;
5138 case SHF_IA_64_VMS_PROTECTED: sindex = 17; break;
148b93f2
NC
5139 default: break;
5140 }
5141#endif
cfcac11d
NC
5142 break;
5143
caa83f8b
NC
5144 case EM_386:
5145 case EM_486:
5146 case EM_X86_64:
7f502d6c 5147 case EM_L1OM:
7a9068fe 5148 case EM_K1OM:
cfcac11d
NC
5149 case EM_OLD_SPARCV9:
5150 case EM_SPARC32PLUS:
5151 case EM_SPARCV9:
5152 case EM_SPARC:
18ae9cc1 5153 if (flag == SHF_ORDERED)
91d6fa6a 5154 sindex = 19;
cfcac11d
NC
5155 break;
5156 default:
5157 break;
148b93f2 5158 }
5477e8a0
L
5159 }
5160
91d6fa6a 5161 if (sindex != -1)
5477e8a0 5162 {
8d5ff12c
L
5163 if (p != buff + field_size + 4)
5164 {
5165 if (size < (10 + 2))
bee0ee85
NC
5166 {
5167 warn (_("Internal error: not enough buffer room for section flag info"));
5168 return _("<unknown>");
5169 }
8d5ff12c
L
5170 size -= 2;
5171 *p++ = ',';
5172 *p++ = ' ';
5173 }
5174
91d6fa6a
NC
5175 size -= flags [sindex].len;
5176 p = stpcpy (p, flags [sindex].str);
5477e8a0 5177 }
3b22753a 5178 else if (flag & SHF_MASKOS)
8d5ff12c 5179 os_flags |= flag;
d1133906 5180 else if (flag & SHF_MASKPROC)
8d5ff12c 5181 proc_flags |= flag;
d1133906 5182 else
8d5ff12c 5183 unknown_flags |= flag;
5477e8a0
L
5184 }
5185 else
5186 {
5187 switch (flag)
5188 {
5189 case SHF_WRITE: *p = 'W'; break;
5190 case SHF_ALLOC: *p = 'A'; break;
5191 case SHF_EXECINSTR: *p = 'X'; break;
5192 case SHF_MERGE: *p = 'M'; break;
5193 case SHF_STRINGS: *p = 'S'; break;
5194 case SHF_INFO_LINK: *p = 'I'; break;
5195 case SHF_LINK_ORDER: *p = 'L'; break;
5196 case SHF_OS_NONCONFORMING: *p = 'O'; break;
5197 case SHF_GROUP: *p = 'G'; break;
5198 case SHF_TLS: *p = 'T'; break;
18ae9cc1 5199 case SHF_EXCLUDE: *p = 'E'; break;
5477e8a0
L
5200
5201 default:
8a9036a4 5202 if ((elf_header.e_machine == EM_X86_64
7a9068fe
L
5203 || elf_header.e_machine == EM_L1OM
5204 || elf_header.e_machine == EM_K1OM)
5477e8a0
L
5205 && flag == SHF_X86_64_LARGE)
5206 *p = 'l';
5207 else if (flag & SHF_MASKOS)
5208 {
5209 *p = 'o';
5210 sh_flags &= ~ SHF_MASKOS;
5211 }
5212 else if (flag & SHF_MASKPROC)
5213 {
5214 *p = 'p';
5215 sh_flags &= ~ SHF_MASKPROC;
5216 }
5217 else
5218 *p = 'x';
5219 break;
5220 }
5221 p++;
d1133906
NC
5222 }
5223 }
76da6bbe 5224
8d5ff12c
L
5225 if (do_section_details)
5226 {
5227 if (os_flags)
5228 {
5229 size -= 5 + field_size;
5230 if (p != buff + field_size + 4)
5231 {
5232 if (size < (2 + 1))
bee0ee85
NC
5233 {
5234 warn (_("Internal error: not enough buffer room for section flag info"));
5235 return _("<unknown>");
5236 }
8d5ff12c
L
5237 size -= 2;
5238 *p++ = ',';
5239 *p++ = ' ';
5240 }
5241 sprintf (p, "OS (%*.*lx)", field_size, field_size,
5242 (unsigned long) os_flags);
5243 p += 5 + field_size;
5244 }
5245 if (proc_flags)
5246 {
5247 size -= 7 + field_size;
5248 if (p != buff + field_size + 4)
5249 {
5250 if (size < (2 + 1))
bee0ee85
NC
5251 {
5252 warn (_("Internal error: not enough buffer room for section flag info"));
5253 return _("<unknown>");
5254 }
8d5ff12c
L
5255 size -= 2;
5256 *p++ = ',';
5257 *p++ = ' ';
5258 }
5259 sprintf (p, "PROC (%*.*lx)", field_size, field_size,
5260 (unsigned long) proc_flags);
5261 p += 7 + field_size;
5262 }
5263 if (unknown_flags)
5264 {
5265 size -= 10 + field_size;
5266 if (p != buff + field_size + 4)
5267 {
5268 if (size < (2 + 1))
bee0ee85
NC
5269 {
5270 warn (_("Internal error: not enough buffer room for section flag info"));
5271 return _("<unknown>");
5272 }
8d5ff12c
L
5273 size -= 2;
5274 *p++ = ',';
5275 *p++ = ' ';
5276 }
2b692964 5277 sprintf (p, _("UNKNOWN (%*.*lx)"), field_size, field_size,
8d5ff12c
L
5278 (unsigned long) unknown_flags);
5279 p += 10 + field_size;
5280 }
5281 }
5282
e9e44622 5283 *p = '\0';
d1133906
NC
5284 return buff;
5285}
5286
252b5132 5287static int
2cf0635d 5288process_section_headers (FILE * file)
252b5132 5289{
2cf0635d 5290 Elf_Internal_Shdr * section;
b34976b6 5291 unsigned int i;
252b5132
RH
5292
5293 section_headers = NULL;
5294
5295 if (elf_header.e_shnum == 0)
5296 {
82f2dbf7
NC
5297 /* PR binutils/12467. */
5298 if (elf_header.e_shoff != 0)
5299 warn (_("possibly corrupt ELF file header - it has a non-zero"
5300 " section header offset, but no section headers\n"));
5301 else if (do_sections)
252b5132
RH
5302 printf (_("\nThere are no sections in this file.\n"));
5303
5304 return 1;
5305 }
5306
5307 if (do_sections && !do_header)
9ea033b2 5308 printf (_("There are %d section headers, starting at offset 0x%lx:\n"),
252b5132
RH
5309 elf_header.e_shnum, (unsigned long) elf_header.e_shoff);
5310
9ea033b2
NC
5311 if (is_32bit_elf)
5312 {
049b0c3a 5313 if (! get_32bit_section_headers (file, FALSE))
9ea033b2
NC
5314 return 0;
5315 }
049b0c3a 5316 else if (! get_64bit_section_headers (file, FALSE))
252b5132
RH
5317 return 0;
5318
5319 /* Read in the string table, so that we have names to display. */
0b49d371 5320 if (elf_header.e_shstrndx != SHN_UNDEF
4fbb74a6 5321 && elf_header.e_shstrndx < elf_header.e_shnum)
252b5132 5322 {
4fbb74a6 5323 section = section_headers + elf_header.e_shstrndx;
d40ac9bd 5324
c256ffe7
JJ
5325 if (section->sh_size != 0)
5326 {
3f5e193b
NC
5327 string_table = (char *) get_data (NULL, file, section->sh_offset,
5328 1, section->sh_size,
5329 _("string table"));
0de14b54 5330
c256ffe7
JJ
5331 string_table_length = string_table != NULL ? section->sh_size : 0;
5332 }
252b5132
RH
5333 }
5334
5335 /* Scan the sections for the dynamic symbol table
e3c8793a 5336 and dynamic string table and debug sections. */
252b5132
RH
5337 dynamic_symbols = NULL;
5338 dynamic_strings = NULL;
5339 dynamic_syminfo = NULL;
f1ef08cb 5340 symtab_shndx_hdr = NULL;
103f02d3 5341
89fac5e3
RS
5342 eh_addr_size = is_32bit_elf ? 4 : 8;
5343 switch (elf_header.e_machine)
5344 {
5345 case EM_MIPS:
5346 case EM_MIPS_RS3_LE:
5347 /* The 64-bit MIPS EABI uses a combination of 32-bit ELF and 64-bit
5348 FDE addresses. However, the ABI also has a semi-official ILP32
5349 variant for which the normal FDE address size rules apply.
5350
5351 GCC 4.0 marks EABI64 objects with a dummy .gcc_compiled_longXX
5352 section, where XX is the size of longs in bits. Unfortunately,
5353 earlier compilers provided no way of distinguishing ILP32 objects
5354 from LP64 objects, so if there's any doubt, we should assume that
5355 the official LP64 form is being used. */
5356 if ((elf_header.e_flags & EF_MIPS_ABI) == E_MIPS_ABI_EABI64
5357 && find_section (".gcc_compiled_long32") == NULL)
5358 eh_addr_size = 8;
5359 break;
0f56a26a
DD
5360
5361 case EM_H8_300:
5362 case EM_H8_300H:
5363 switch (elf_header.e_flags & EF_H8_MACH)
5364 {
5365 case E_H8_MACH_H8300:
5366 case E_H8_MACH_H8300HN:
5367 case E_H8_MACH_H8300SN:
5368 case E_H8_MACH_H8300SXN:
5369 eh_addr_size = 2;
5370 break;
5371 case E_H8_MACH_H8300H:
5372 case E_H8_MACH_H8300S:
5373 case E_H8_MACH_H8300SX:
5374 eh_addr_size = 4;
5375 break;
5376 }
f4236fe4
DD
5377 break;
5378
ff7eeb89 5379 case EM_M32C_OLD:
f4236fe4
DD
5380 case EM_M32C:
5381 switch (elf_header.e_flags & EF_M32C_CPU_MASK)
5382 {
5383 case EF_M32C_CPU_M16C:
5384 eh_addr_size = 2;
5385 break;
5386 }
5387 break;
89fac5e3
RS
5388 }
5389
76ca31c0
NC
5390#define CHECK_ENTSIZE_VALUES(section, i, size32, size64) \
5391 do \
5392 { \
5393 bfd_size_type expected_entsize = is_32bit_elf ? size32 : size64; \
5394 if (section->sh_entsize != expected_entsize) \
9dd3a467 5395 { \
76ca31c0
NC
5396 char buf[40]; \
5397 sprintf_vma (buf, section->sh_entsize); \
5398 /* Note: coded this way so that there is a single string for \
5399 translation. */ \
5400 error (_("Section %d has invalid sh_entsize of %s\n"), i, buf); \
5401 error (_("(Using the expected size of %u for the rest of this dump)\n"), \
5402 (unsigned) expected_entsize); \
9dd3a467 5403 section->sh_entsize = expected_entsize; \
76ca31c0
NC
5404 } \
5405 } \
08d8fa11 5406 while (0)
9dd3a467
NC
5407
5408#define CHECK_ENTSIZE(section, i, type) \
08d8fa11
JJ
5409 CHECK_ENTSIZE_VALUES (section, i, sizeof (Elf32_External_##type), \
5410 sizeof (Elf64_External_##type))
5411
252b5132
RH
5412 for (i = 0, section = section_headers;
5413 i < elf_header.e_shnum;
b34976b6 5414 i++, section++)
252b5132 5415 {
2cf0635d 5416 char * name = SECTION_NAME (section);
252b5132
RH
5417
5418 if (section->sh_type == SHT_DYNSYM)
5419 {
5420 if (dynamic_symbols != NULL)
5421 {
5422 error (_("File contains multiple dynamic symbol tables\n"));
5423 continue;
5424 }
5425
08d8fa11 5426 CHECK_ENTSIZE (section, i, Sym);
ba5cdace 5427 dynamic_symbols = GET_ELF_SYMBOLS (file, section, & num_dynamic_syms);
252b5132
RH
5428 }
5429 else if (section->sh_type == SHT_STRTAB
18bd398b 5430 && streq (name, ".dynstr"))
252b5132
RH
5431 {
5432 if (dynamic_strings != NULL)
5433 {
5434 error (_("File contains multiple dynamic string tables\n"));
5435 continue;
5436 }
5437
3f5e193b
NC
5438 dynamic_strings = (char *) get_data (NULL, file, section->sh_offset,
5439 1, section->sh_size,
5440 _("dynamic strings"));
59245841 5441 dynamic_strings_length = dynamic_strings == NULL ? 0 : section->sh_size;
252b5132 5442 }
9ad5cbcf
AM
5443 else if (section->sh_type == SHT_SYMTAB_SHNDX)
5444 {
5445 if (symtab_shndx_hdr != NULL)
5446 {
5447 error (_("File contains multiple symtab shndx tables\n"));
5448 continue;
5449 }
5450 symtab_shndx_hdr = section;
5451 }
08d8fa11
JJ
5452 else if (section->sh_type == SHT_SYMTAB)
5453 CHECK_ENTSIZE (section, i, Sym);
5454 else if (section->sh_type == SHT_GROUP)
5455 CHECK_ENTSIZE_VALUES (section, i, GRP_ENTRY_SIZE, GRP_ENTRY_SIZE);
5456 else if (section->sh_type == SHT_REL)
5457 CHECK_ENTSIZE (section, i, Rel);
5458 else if (section->sh_type == SHT_RELA)
5459 CHECK_ENTSIZE (section, i, Rela);
252b5132 5460 else if ((do_debugging || do_debug_info || do_debug_abbrevs
f9f0e732 5461 || do_debug_lines || do_debug_pubnames || do_debug_pubtypes
cb8f3167 5462 || do_debug_aranges || do_debug_frames || do_debug_macinfo
657d0d47
CC
5463 || do_debug_str || do_debug_loc || do_debug_ranges
5464 || do_debug_addr || do_debug_cu_index)
1b315056
CS
5465 && (const_strneq (name, ".debug_")
5466 || const_strneq (name, ".zdebug_")))
252b5132 5467 {
1b315056
CS
5468 if (name[1] == 'z')
5469 name += sizeof (".zdebug_") - 1;
5470 else
5471 name += sizeof (".debug_") - 1;
252b5132
RH
5472
5473 if (do_debugging
4723351a
CC
5474 || (do_debug_info && const_strneq (name, "info"))
5475 || (do_debug_info && const_strneq (name, "types"))
5476 || (do_debug_abbrevs && const_strneq (name, "abbrev"))
b40bf0a2
NC
5477 || (do_debug_lines && strcmp (name, "line") == 0)
5478 || (do_debug_lines && const_strneq (name, "line."))
4723351a
CC
5479 || (do_debug_pubnames && const_strneq (name, "pubnames"))
5480 || (do_debug_pubtypes && const_strneq (name, "pubtypes"))
459d52c8
DE
5481 || (do_debug_pubnames && const_strneq (name, "gnu_pubnames"))
5482 || (do_debug_pubtypes && const_strneq (name, "gnu_pubtypes"))
4723351a
CC
5483 || (do_debug_aranges && const_strneq (name, "aranges"))
5484 || (do_debug_ranges && const_strneq (name, "ranges"))
5485 || (do_debug_frames && const_strneq (name, "frame"))
5486 || (do_debug_macinfo && const_strneq (name, "macinfo"))
5487 || (do_debug_macinfo && const_strneq (name, "macro"))
5488 || (do_debug_str && const_strneq (name, "str"))
5489 || (do_debug_loc && const_strneq (name, "loc"))
657d0d47
CC
5490 || (do_debug_addr && const_strneq (name, "addr"))
5491 || (do_debug_cu_index && const_strneq (name, "cu_index"))
5492 || (do_debug_cu_index && const_strneq (name, "tu_index"))
252b5132 5493 )
09c11c86 5494 request_dump_bynumber (i, DEBUG_DUMP);
252b5132 5495 }
a262ae96 5496 /* Linkonce section to be combined with .debug_info at link time. */
09fd7e38 5497 else if ((do_debugging || do_debug_info)
0112cd26 5498 && const_strneq (name, ".gnu.linkonce.wi."))
09c11c86 5499 request_dump_bynumber (i, DEBUG_DUMP);
18bd398b 5500 else if (do_debug_frames && streq (name, ".eh_frame"))
09c11c86 5501 request_dump_bynumber (i, DEBUG_DUMP);
5bbdf3d5
DE
5502 else if (do_gdb_index && streq (name, ".gdb_index"))
5503 request_dump_bynumber (i, DEBUG_DUMP);
6f875884
TG
5504 /* Trace sections for Itanium VMS. */
5505 else if ((do_debugging || do_trace_info || do_trace_abbrevs
5506 || do_trace_aranges)
5507 && const_strneq (name, ".trace_"))
5508 {
5509 name += sizeof (".trace_") - 1;
5510
5511 if (do_debugging
5512 || (do_trace_info && streq (name, "info"))
5513 || (do_trace_abbrevs && streq (name, "abbrev"))
5514 || (do_trace_aranges && streq (name, "aranges"))
5515 )
5516 request_dump_bynumber (i, DEBUG_DUMP);
5517 }
252b5132
RH
5518 }
5519
5520 if (! do_sections)
5521 return 1;
5522
3a1a2036
NC
5523 if (elf_header.e_shnum > 1)
5524 printf (_("\nSection Headers:\n"));
5525 else
5526 printf (_("\nSection Header:\n"));
76da6bbe 5527
f7a99963 5528 if (is_32bit_elf)
595cf52e 5529 {
5477e8a0 5530 if (do_section_details)
595cf52e
L
5531 {
5532 printf (_(" [Nr] Name\n"));
5477e8a0 5533 printf (_(" Type Addr Off Size ES Lk Inf Al\n"));
595cf52e
L
5534 }
5535 else
5536 printf
5537 (_(" [Nr] Name Type Addr Off Size ES Flg Lk Inf Al\n"));
5538 }
d974e256 5539 else if (do_wide)
595cf52e 5540 {
5477e8a0 5541 if (do_section_details)
595cf52e
L
5542 {
5543 printf (_(" [Nr] Name\n"));
5477e8a0 5544 printf (_(" Type Address Off Size ES Lk Inf Al\n"));
595cf52e
L
5545 }
5546 else
5547 printf
5548 (_(" [Nr] Name Type Address Off Size ES Flg Lk Inf Al\n"));
5549 }
f7a99963
NC
5550 else
5551 {
5477e8a0 5552 if (do_section_details)
595cf52e
L
5553 {
5554 printf (_(" [Nr] Name\n"));
5477e8a0
L
5555 printf (_(" Type Address Offset Link\n"));
5556 printf (_(" Size EntSize Info Align\n"));
595cf52e
L
5557 }
5558 else
5559 {
5560 printf (_(" [Nr] Name Type Address Offset\n"));
5561 printf (_(" Size EntSize Flags Link Info Align\n"));
5562 }
f7a99963 5563 }
252b5132 5564
5477e8a0
L
5565 if (do_section_details)
5566 printf (_(" Flags\n"));
5567
252b5132
RH
5568 for (i = 0, section = section_headers;
5569 i < elf_header.e_shnum;
b34976b6 5570 i++, section++)
252b5132 5571 {
7bfd842d 5572 printf (" [%2u] ", i);
5477e8a0 5573 if (do_section_details)
74e1a04b 5574 printf ("%s\n ", printable_section_name (section));
595cf52e 5575 else
74e1a04b 5576 print_symbol (-17, SECTION_NAME (section));
0b4362b0 5577
ea52a088
NC
5578 printf (do_wide ? " %-15s " : " %-15.15s ",
5579 get_section_type_name (section->sh_type));
0b4362b0 5580
f7a99963
NC
5581 if (is_32bit_elf)
5582 {
cfcac11d
NC
5583 const char * link_too_big = NULL;
5584
f7a99963 5585 print_vma (section->sh_addr, LONG_HEX);
76da6bbe 5586
f7a99963
NC
5587 printf ( " %6.6lx %6.6lx %2.2lx",
5588 (unsigned long) section->sh_offset,
5589 (unsigned long) section->sh_size,
5590 (unsigned long) section->sh_entsize);
d1133906 5591
5477e8a0
L
5592 if (do_section_details)
5593 fputs (" ", stdout);
5594 else
5595 printf (" %3s ", get_elf_section_flags (section->sh_flags));
76da6bbe 5596
cfcac11d
NC
5597 if (section->sh_link >= elf_header.e_shnum)
5598 {
5599 link_too_big = "";
5600 /* The sh_link value is out of range. Normally this indicates
caa83f8b 5601 an error but it can have special values in Solaris binaries. */
cfcac11d
NC
5602 switch (elf_header.e_machine)
5603 {
caa83f8b
NC
5604 case EM_386:
5605 case EM_486:
5606 case EM_X86_64:
7f502d6c 5607 case EM_L1OM:
7a9068fe 5608 case EM_K1OM:
cfcac11d
NC
5609 case EM_OLD_SPARCV9:
5610 case EM_SPARC32PLUS:
5611 case EM_SPARCV9:
5612 case EM_SPARC:
5613 if (section->sh_link == (SHN_BEFORE & 0xffff))
5614 link_too_big = "BEFORE";
5615 else if (section->sh_link == (SHN_AFTER & 0xffff))
5616 link_too_big = "AFTER";
5617 break;
5618 default:
5619 break;
5620 }
5621 }
5622
5623 if (do_section_details)
5624 {
5625 if (link_too_big != NULL && * link_too_big)
5626 printf ("<%s> ", link_too_big);
5627 else
5628 printf ("%2u ", section->sh_link);
5629 printf ("%3u %2lu\n", section->sh_info,
5630 (unsigned long) section->sh_addralign);
5631 }
5632 else
5633 printf ("%2u %3u %2lu\n",
5634 section->sh_link,
5635 section->sh_info,
5636 (unsigned long) section->sh_addralign);
5637
5638 if (link_too_big && ! * link_too_big)
5639 warn (_("section %u: sh_link value of %u is larger than the number of sections\n"),
5640 i, section->sh_link);
f7a99963 5641 }
d974e256
JJ
5642 else if (do_wide)
5643 {
5644 print_vma (section->sh_addr, LONG_HEX);
5645
5646 if ((long) section->sh_offset == section->sh_offset)
5647 printf (" %6.6lx", (unsigned long) section->sh_offset);
5648 else
5649 {
5650 putchar (' ');
5651 print_vma (section->sh_offset, LONG_HEX);
5652 }
5653
5654 if ((unsigned long) section->sh_size == section->sh_size)
5655 printf (" %6.6lx", (unsigned long) section->sh_size);
5656 else
5657 {
5658 putchar (' ');
5659 print_vma (section->sh_size, LONG_HEX);
5660 }
5661
5662 if ((unsigned long) section->sh_entsize == section->sh_entsize)
5663 printf (" %2.2lx", (unsigned long) section->sh_entsize);
5664 else
5665 {
5666 putchar (' ');
5667 print_vma (section->sh_entsize, LONG_HEX);
5668 }
5669
5477e8a0
L
5670 if (do_section_details)
5671 fputs (" ", stdout);
5672 else
5673 printf (" %3s ", get_elf_section_flags (section->sh_flags));
d974e256 5674
72de5009 5675 printf ("%2u %3u ", section->sh_link, section->sh_info);
d974e256
JJ
5676
5677 if ((unsigned long) section->sh_addralign == section->sh_addralign)
72de5009 5678 printf ("%2lu\n", (unsigned long) section->sh_addralign);
d974e256
JJ
5679 else
5680 {
5681 print_vma (section->sh_addralign, DEC);
5682 putchar ('\n');
5683 }
5684 }
5477e8a0 5685 else if (do_section_details)
595cf52e 5686 {
5477e8a0 5687 printf (" %-15.15s ",
595cf52e 5688 get_section_type_name (section->sh_type));
595cf52e
L
5689 print_vma (section->sh_addr, LONG_HEX);
5690 if ((long) section->sh_offset == section->sh_offset)
5477e8a0 5691 printf (" %16.16lx", (unsigned long) section->sh_offset);
595cf52e
L
5692 else
5693 {
5694 printf (" ");
5695 print_vma (section->sh_offset, LONG_HEX);
5696 }
72de5009 5697 printf (" %u\n ", section->sh_link);
595cf52e 5698 print_vma (section->sh_size, LONG_HEX);
5477e8a0 5699 putchar (' ');
595cf52e
L
5700 print_vma (section->sh_entsize, LONG_HEX);
5701
72de5009
AM
5702 printf (" %-16u %lu\n",
5703 section->sh_info,
595cf52e
L
5704 (unsigned long) section->sh_addralign);
5705 }
f7a99963
NC
5706 else
5707 {
5708 putchar (' ');
5709 print_vma (section->sh_addr, LONG_HEX);
53c7db4b
KH
5710 if ((long) section->sh_offset == section->sh_offset)
5711 printf (" %8.8lx", (unsigned long) section->sh_offset);
5712 else
5713 {
5714 printf (" ");
5715 print_vma (section->sh_offset, LONG_HEX);
5716 }
f7a99963
NC
5717 printf ("\n ");
5718 print_vma (section->sh_size, LONG_HEX);
5719 printf (" ");
5720 print_vma (section->sh_entsize, LONG_HEX);
76da6bbe 5721
d1133906 5722 printf (" %3s ", get_elf_section_flags (section->sh_flags));
76da6bbe 5723
72de5009
AM
5724 printf (" %2u %3u %lu\n",
5725 section->sh_link,
5726 section->sh_info,
f7a99963
NC
5727 (unsigned long) section->sh_addralign);
5728 }
5477e8a0
L
5729
5730 if (do_section_details)
5731 printf (" %s\n", get_elf_section_flags (section->sh_flags));
252b5132
RH
5732 }
5733
5477e8a0 5734 if (!do_section_details)
3dbcc61d
NC
5735 {
5736 if (elf_header.e_machine == EM_X86_64
7a9068fe
L
5737 || elf_header.e_machine == EM_L1OM
5738 || elf_header.e_machine == EM_K1OM)
3dbcc61d
NC
5739 printf (_("Key to Flags:\n\
5740 W (write), A (alloc), X (execute), M (merge), S (strings), l (large)\n\
5741 I (info), L (link order), G (group), T (TLS), E (exclude), x (unknown)\n\
5742 O (extra OS processing required) o (OS specific), p (processor specific)\n"));
5743 else
5744 printf (_("Key to Flags:\n\
e3c8793a 5745 W (write), A (alloc), X (execute), M (merge), S (strings)\n\
1d0055ea 5746 I (info), L (link order), G (group), T (TLS), E (exclude), x (unknown)\n\
e3c8793a 5747 O (extra OS processing required) o (OS specific), p (processor specific)\n"));
0b4362b0 5748 }
d1133906 5749
252b5132
RH
5750 return 1;
5751}
5752
f5842774
L
5753static const char *
5754get_group_flags (unsigned int flags)
5755{
5756 static char buff[32];
5757 switch (flags)
5758 {
220453ec
AM
5759 case 0:
5760 return "";
5761
f5842774 5762 case GRP_COMDAT:
220453ec 5763 return "COMDAT ";
f5842774
L
5764
5765 default:
220453ec 5766 snprintf (buff, sizeof (buff), _("[<unknown>: 0x%x] "), flags);
f5842774
L
5767 break;
5768 }
5769 return buff;
5770}
5771
5772static int
2cf0635d 5773process_section_groups (FILE * file)
f5842774 5774{
2cf0635d 5775 Elf_Internal_Shdr * section;
f5842774 5776 unsigned int i;
2cf0635d
NC
5777 struct group * group;
5778 Elf_Internal_Shdr * symtab_sec;
5779 Elf_Internal_Shdr * strtab_sec;
5780 Elf_Internal_Sym * symtab;
ba5cdace 5781 unsigned long num_syms;
2cf0635d 5782 char * strtab;
c256ffe7 5783 size_t strtab_size;
d1f5c6e3
L
5784
5785 /* Don't process section groups unless needed. */
5786 if (!do_unwind && !do_section_groups)
5787 return 1;
f5842774
L
5788
5789 if (elf_header.e_shnum == 0)
5790 {
5791 if (do_section_groups)
82f2dbf7 5792 printf (_("\nThere are no sections to group in this file.\n"));
f5842774
L
5793
5794 return 1;
5795 }
5796
5797 if (section_headers == NULL)
5798 {
5799 error (_("Section headers are not available!\n"));
fa1908fd
NC
5800 /* PR 13622: This can happen with a corrupt ELF header. */
5801 return 0;
f5842774
L
5802 }
5803
3f5e193b
NC
5804 section_headers_groups = (struct group **) calloc (elf_header.e_shnum,
5805 sizeof (struct group *));
e4b17d5c
L
5806
5807 if (section_headers_groups == NULL)
5808 {
8b73c356
NC
5809 error (_("Out of memory reading %u section group headers\n"),
5810 elf_header.e_shnum);
e4b17d5c
L
5811 return 0;
5812 }
5813
f5842774 5814 /* Scan the sections for the group section. */
d1f5c6e3 5815 group_count = 0;
f5842774
L
5816 for (i = 0, section = section_headers;
5817 i < elf_header.e_shnum;
5818 i++, section++)
e4b17d5c
L
5819 if (section->sh_type == SHT_GROUP)
5820 group_count++;
5821
d1f5c6e3
L
5822 if (group_count == 0)
5823 {
5824 if (do_section_groups)
5825 printf (_("\nThere are no section groups in this file.\n"));
5826
5827 return 1;
5828 }
5829
3f5e193b 5830 section_groups = (struct group *) calloc (group_count, sizeof (struct group));
e4b17d5c
L
5831
5832 if (section_groups == NULL)
5833 {
8b73c356
NC
5834 error (_("Out of memory reading %lu groups\n"),
5835 (unsigned long) group_count);
e4b17d5c
L
5836 return 0;
5837 }
5838
d1f5c6e3
L
5839 symtab_sec = NULL;
5840 strtab_sec = NULL;
5841 symtab = NULL;
ba5cdace 5842 num_syms = 0;
d1f5c6e3 5843 strtab = NULL;
c256ffe7 5844 strtab_size = 0;
e4b17d5c
L
5845 for (i = 0, section = section_headers, group = section_groups;
5846 i < elf_header.e_shnum;
5847 i++, section++)
f5842774
L
5848 {
5849 if (section->sh_type == SHT_GROUP)
5850 {
74e1a04b
NC
5851 const char * name = printable_section_name (section);
5852 const char * group_name;
2cf0635d
NC
5853 unsigned char * start;
5854 unsigned char * indices;
f5842774 5855 unsigned int entry, j, size;
2cf0635d
NC
5856 Elf_Internal_Shdr * sec;
5857 Elf_Internal_Sym * sym;
f5842774
L
5858
5859 /* Get the symbol table. */
4fbb74a6
AM
5860 if (section->sh_link >= elf_header.e_shnum
5861 || ((sec = section_headers + section->sh_link)->sh_type
c256ffe7 5862 != SHT_SYMTAB))
f5842774
L
5863 {
5864 error (_("Bad sh_link in group section `%s'\n"), name);
5865 continue;
5866 }
d1f5c6e3
L
5867
5868 if (symtab_sec != sec)
5869 {
5870 symtab_sec = sec;
5871 if (symtab)
5872 free (symtab);
ba5cdace 5873 symtab = GET_ELF_SYMBOLS (file, symtab_sec, & num_syms);
d1f5c6e3 5874 }
f5842774 5875
dd24e3da
NC
5876 if (symtab == NULL)
5877 {
5878 error (_("Corrupt header in group section `%s'\n"), name);
5879 continue;
5880 }
5881
ba5cdace
NC
5882 if (section->sh_info >= num_syms)
5883 {
5884 error (_("Bad sh_info in group section `%s'\n"), name);
5885 continue;
5886 }
5887
f5842774
L
5888 sym = symtab + section->sh_info;
5889
5890 if (ELF_ST_TYPE (sym->st_info) == STT_SECTION)
5891 {
4fbb74a6
AM
5892 if (sym->st_shndx == 0
5893 || sym->st_shndx >= elf_header.e_shnum)
f5842774
L
5894 {
5895 error (_("Bad sh_info in group section `%s'\n"), name);
5896 continue;
5897 }
ba2685cc 5898
4fbb74a6 5899 group_name = SECTION_NAME (section_headers + sym->st_shndx);
c256ffe7
JJ
5900 strtab_sec = NULL;
5901 if (strtab)
5902 free (strtab);
f5842774 5903 strtab = NULL;
c256ffe7 5904 strtab_size = 0;
f5842774
L
5905 }
5906 else
5907 {
5908 /* Get the string table. */
4fbb74a6 5909 if (symtab_sec->sh_link >= elf_header.e_shnum)
c256ffe7
JJ
5910 {
5911 strtab_sec = NULL;
5912 if (strtab)
5913 free (strtab);
5914 strtab = NULL;
5915 strtab_size = 0;
5916 }
5917 else if (strtab_sec
4fbb74a6 5918 != (sec = section_headers + symtab_sec->sh_link))
d1f5c6e3
L
5919 {
5920 strtab_sec = sec;
5921 if (strtab)
5922 free (strtab);
071436c6 5923
3f5e193b 5924 strtab = (char *) get_data (NULL, file, strtab_sec->sh_offset,
071436c6
NC
5925 1, strtab_sec->sh_size,
5926 _("string table"));
c256ffe7 5927 strtab_size = strtab != NULL ? strtab_sec->sh_size : 0;
d1f5c6e3 5928 }
c256ffe7 5929 group_name = sym->st_name < strtab_size
2b692964 5930 ? strtab + sym->st_name : _("<corrupt>");
f5842774
L
5931 }
5932
c9c1d674
EG
5933 /* PR 17531: file: loop. */
5934 if (section->sh_entsize > section->sh_size)
5935 {
5936 error (_("Section %s has sh_entsize (0x%lx) which is larger than its size (0x%lx)\n"),
5937 printable_section_name (section),
8066deb1
AM
5938 (unsigned long) section->sh_entsize,
5939 (unsigned long) section->sh_size);
c9c1d674
EG
5940 break;
5941 }
5942
3f5e193b
NC
5943 start = (unsigned char *) get_data (NULL, file, section->sh_offset,
5944 1, section->sh_size,
5945 _("section data"));
59245841
NC
5946 if (start == NULL)
5947 continue;
f5842774
L
5948
5949 indices = start;
5950 size = (section->sh_size / section->sh_entsize) - 1;
5951 entry = byte_get (indices, 4);
5952 indices += 4;
e4b17d5c
L
5953
5954 if (do_section_groups)
5955 {
2b692964 5956 printf (_("\n%sgroup section [%5u] `%s' [%s] contains %u sections:\n"),
391cb864 5957 get_group_flags (entry), i, name, group_name, size);
ba2685cc 5958
e4b17d5c
L
5959 printf (_(" [Index] Name\n"));
5960 }
5961
5962 group->group_index = i;
5963
f5842774
L
5964 for (j = 0; j < size; j++)
5965 {
2cf0635d 5966 struct group_list * g;
e4b17d5c 5967
f5842774
L
5968 entry = byte_get (indices, 4);
5969 indices += 4;
5970
4fbb74a6 5971 if (entry >= elf_header.e_shnum)
391cb864
L
5972 {
5973 error (_("section [%5u] in group section [%5u] > maximum section [%5u]\n"),
5974 entry, i, elf_header.e_shnum - 1);
5975 continue;
5976 }
391cb864 5977
4fbb74a6 5978 if (section_headers_groups [entry] != NULL)
e4b17d5c 5979 {
d1f5c6e3
L
5980 if (entry)
5981 {
391cb864
L
5982 error (_("section [%5u] in group section [%5u] already in group section [%5u]\n"),
5983 entry, i,
4fbb74a6 5984 section_headers_groups [entry]->group_index);
d1f5c6e3
L
5985 continue;
5986 }
5987 else
5988 {
5989 /* Intel C/C++ compiler may put section 0 in a
5990 section group. We just warn it the first time
5991 and ignore it afterwards. */
5992 static int warned = 0;
5993 if (!warned)
5994 {
5995 error (_("section 0 in group section [%5u]\n"),
4fbb74a6 5996 section_headers_groups [entry]->group_index);
d1f5c6e3
L
5997 warned++;
5998 }
5999 }
e4b17d5c
L
6000 }
6001
4fbb74a6 6002 section_headers_groups [entry] = group;
e4b17d5c
L
6003
6004 if (do_section_groups)
6005 {
4fbb74a6 6006 sec = section_headers + entry;
74e1a04b 6007 printf (" [%5u] %s\n", entry, printable_section_name (sec));
ba2685cc
AM
6008 }
6009
3f5e193b 6010 g = (struct group_list *) xmalloc (sizeof (struct group_list));
e4b17d5c
L
6011 g->section_index = entry;
6012 g->next = group->root;
6013 group->root = g;
f5842774
L
6014 }
6015
f5842774
L
6016 if (start)
6017 free (start);
e4b17d5c
L
6018
6019 group++;
f5842774
L
6020 }
6021 }
6022
d1f5c6e3
L
6023 if (symtab)
6024 free (symtab);
6025 if (strtab)
6026 free (strtab);
f5842774
L
6027 return 1;
6028}
6029
28f997cf
TG
6030/* Data used to display dynamic fixups. */
6031
6032struct ia64_vms_dynfixup
6033{
6034 bfd_vma needed_ident; /* Library ident number. */
6035 bfd_vma needed; /* Index in the dstrtab of the library name. */
6036 bfd_vma fixup_needed; /* Index of the library. */
6037 bfd_vma fixup_rela_cnt; /* Number of fixups. */
6038 bfd_vma fixup_rela_off; /* Fixups offset in the dynamic segment. */
6039};
6040
6041/* Data used to display dynamic relocations. */
6042
6043struct ia64_vms_dynimgrela
6044{
6045 bfd_vma img_rela_cnt; /* Number of relocations. */
6046 bfd_vma img_rela_off; /* Reloc offset in the dynamic segment. */
6047};
6048
6049/* Display IA-64 OpenVMS dynamic fixups (used to dynamically link a shared
6050 library). */
6051
6052static void
6053dump_ia64_vms_dynamic_fixups (FILE *file, struct ia64_vms_dynfixup *fixup,
6054 const char *strtab, unsigned int strtab_sz)
6055{
6056 Elf64_External_VMS_IMAGE_FIXUP *imfs;
6057 long i;
6058 const char *lib_name;
6059
6060 imfs = get_data (NULL, file, dynamic_addr + fixup->fixup_rela_off,
6061 1, fixup->fixup_rela_cnt * sizeof (*imfs),
6062 _("dynamic section image fixups"));
6063 if (!imfs)
6064 return;
6065
6066 if (fixup->needed < strtab_sz)
6067 lib_name = strtab + fixup->needed;
6068 else
6069 {
6070 warn ("corrupt library name index of 0x%lx found in dynamic entry",
7f01b0c6 6071 (unsigned long) fixup->needed);
28f997cf
TG
6072 lib_name = "???";
6073 }
6074 printf (_("\nImage fixups for needed library #%d: %s - ident: %lx\n"),
6075 (int) fixup->fixup_needed, lib_name, (long) fixup->needed_ident);
6076 printf
6077 (_("Seg Offset Type SymVec DataType\n"));
6078
6079 for (i = 0; i < (long) fixup->fixup_rela_cnt; i++)
6080 {
6081 unsigned int type;
6082 const char *rtype;
6083
6084 printf ("%3u ", (unsigned) BYTE_GET (imfs [i].fixup_seg));
6085 printf_vma ((bfd_vma) BYTE_GET (imfs [i].fixup_offset));
6086 type = BYTE_GET (imfs [i].type);
6087 rtype = elf_ia64_reloc_type (type);
6088 if (rtype == NULL)
6089 printf (" 0x%08x ", type);
6090 else
6091 printf (" %-32s ", rtype);
6092 printf ("%6u ", (unsigned) BYTE_GET (imfs [i].symvec_index));
6093 printf ("0x%08x\n", (unsigned) BYTE_GET (imfs [i].data_type));
6094 }
6095
6096 free (imfs);
6097}
6098
6099/* Display IA-64 OpenVMS dynamic relocations (used to relocate an image). */
6100
6101static void
6102dump_ia64_vms_dynamic_relocs (FILE *file, struct ia64_vms_dynimgrela *imgrela)
6103{
6104 Elf64_External_VMS_IMAGE_RELA *imrs;
6105 long i;
6106
6107 imrs = get_data (NULL, file, dynamic_addr + imgrela->img_rela_off,
6108 1, imgrela->img_rela_cnt * sizeof (*imrs),
9cf03b7e 6109 _("dynamic section image relocations"));
28f997cf
TG
6110 if (!imrs)
6111 return;
6112
6113 printf (_("\nImage relocs\n"));
6114 printf
6115 (_("Seg Offset Type Addend Seg Sym Off\n"));
6116
6117 for (i = 0; i < (long) imgrela->img_rela_cnt; i++)
6118 {
6119 unsigned int type;
6120 const char *rtype;
6121
6122 printf ("%3u ", (unsigned) BYTE_GET (imrs [i].rela_seg));
6123 printf ("%08" BFD_VMA_FMT "x ",
6124 (bfd_vma) BYTE_GET (imrs [i].rela_offset));
6125 type = BYTE_GET (imrs [i].type);
6126 rtype = elf_ia64_reloc_type (type);
6127 if (rtype == NULL)
6128 printf ("0x%08x ", type);
6129 else
6130 printf ("%-31s ", rtype);
6131 print_vma (BYTE_GET (imrs [i].addend), FULL_HEX);
6132 printf ("%3u ", (unsigned) BYTE_GET (imrs [i].sym_seg));
6133 printf ("%08" BFD_VMA_FMT "x\n",
6134 (bfd_vma) BYTE_GET (imrs [i].sym_offset));
6135 }
6136
6137 free (imrs);
6138}
6139
6140/* Display IA-64 OpenVMS dynamic relocations and fixups. */
6141
6142static int
6143process_ia64_vms_dynamic_relocs (FILE *file)
6144{
6145 struct ia64_vms_dynfixup fixup;
6146 struct ia64_vms_dynimgrela imgrela;
6147 Elf_Internal_Dyn *entry;
6148 int res = 0;
6149 bfd_vma strtab_off = 0;
6150 bfd_vma strtab_sz = 0;
6151 char *strtab = NULL;
6152
6153 memset (&fixup, 0, sizeof (fixup));
6154 memset (&imgrela, 0, sizeof (imgrela));
6155
6156 /* Note: the order of the entries is specified by the OpenVMS specs. */
6157 for (entry = dynamic_section;
6158 entry < dynamic_section + dynamic_nent;
6159 entry++)
6160 {
6161 switch (entry->d_tag)
6162 {
6163 case DT_IA_64_VMS_STRTAB_OFFSET:
6164 strtab_off = entry->d_un.d_val;
6165 break;
6166 case DT_STRSZ:
6167 strtab_sz = entry->d_un.d_val;
6168 if (strtab == NULL)
6169 strtab = get_data (NULL, file, dynamic_addr + strtab_off,
6170 1, strtab_sz, _("dynamic string section"));
6171 break;
6172
6173 case DT_IA_64_VMS_NEEDED_IDENT:
6174 fixup.needed_ident = entry->d_un.d_val;
6175 break;
6176 case DT_NEEDED:
6177 fixup.needed = entry->d_un.d_val;
6178 break;
6179 case DT_IA_64_VMS_FIXUP_NEEDED:
6180 fixup.fixup_needed = entry->d_un.d_val;
6181 break;
6182 case DT_IA_64_VMS_FIXUP_RELA_CNT:
6183 fixup.fixup_rela_cnt = entry->d_un.d_val;
6184 break;
6185 case DT_IA_64_VMS_FIXUP_RELA_OFF:
6186 fixup.fixup_rela_off = entry->d_un.d_val;
6187 res++;
6188 dump_ia64_vms_dynamic_fixups (file, &fixup, strtab, strtab_sz);
6189 break;
6190
6191 case DT_IA_64_VMS_IMG_RELA_CNT:
6192 imgrela.img_rela_cnt = entry->d_un.d_val;
6193 break;
6194 case DT_IA_64_VMS_IMG_RELA_OFF:
6195 imgrela.img_rela_off = entry->d_un.d_val;
6196 res++;
6197 dump_ia64_vms_dynamic_relocs (file, &imgrela);
6198 break;
6199
6200 default:
6201 break;
6202 }
6203 }
6204
6205 if (strtab != NULL)
6206 free (strtab);
6207
6208 return res;
6209}
6210
85b1c36d 6211static struct
566b0d53 6212{
2cf0635d 6213 const char * name;
566b0d53
L
6214 int reloc;
6215 int size;
6216 int rela;
6217} dynamic_relocations [] =
6218{
6219 { "REL", DT_REL, DT_RELSZ, FALSE },
6220 { "RELA", DT_RELA, DT_RELASZ, TRUE },
6221 { "PLT", DT_JMPREL, DT_PLTRELSZ, UNKNOWN }
6222};
6223
252b5132 6224/* Process the reloc section. */
18bd398b 6225
252b5132 6226static int
2cf0635d 6227process_relocs (FILE * file)
252b5132 6228{
b34976b6
AM
6229 unsigned long rel_size;
6230 unsigned long rel_offset;
252b5132
RH
6231
6232
6233 if (!do_reloc)
6234 return 1;
6235
6236 if (do_using_dynamic)
6237 {
566b0d53 6238 int is_rela;
2cf0635d 6239 const char * name;
566b0d53
L
6240 int has_dynamic_reloc;
6241 unsigned int i;
0de14b54 6242
566b0d53 6243 has_dynamic_reloc = 0;
252b5132 6244
566b0d53 6245 for (i = 0; i < ARRAY_SIZE (dynamic_relocations); i++)
252b5132 6246 {
566b0d53
L
6247 is_rela = dynamic_relocations [i].rela;
6248 name = dynamic_relocations [i].name;
6249 rel_size = dynamic_info [dynamic_relocations [i].size];
6250 rel_offset = dynamic_info [dynamic_relocations [i].reloc];
103f02d3 6251
566b0d53
L
6252 has_dynamic_reloc |= rel_size;
6253
6254 if (is_rela == UNKNOWN)
aa903cfb 6255 {
566b0d53
L
6256 if (dynamic_relocations [i].reloc == DT_JMPREL)
6257 switch (dynamic_info[DT_PLTREL])
6258 {
6259 case DT_REL:
6260 is_rela = FALSE;
6261 break;
6262 case DT_RELA:
6263 is_rela = TRUE;
6264 break;
6265 }
aa903cfb 6266 }
252b5132 6267
566b0d53
L
6268 if (rel_size)
6269 {
6270 printf
6271 (_("\n'%s' relocation section at offset 0x%lx contains %ld bytes:\n"),
6272 name, rel_offset, rel_size);
252b5132 6273
d93f0186
NC
6274 dump_relocations (file,
6275 offset_from_vma (file, rel_offset, rel_size),
6276 rel_size,
566b0d53 6277 dynamic_symbols, num_dynamic_syms,
bb4d2ac2
L
6278 dynamic_strings, dynamic_strings_length,
6279 is_rela, 1);
566b0d53 6280 }
252b5132 6281 }
566b0d53 6282
28f997cf
TG
6283 if (is_ia64_vms ())
6284 has_dynamic_reloc |= process_ia64_vms_dynamic_relocs (file);
6285
566b0d53 6286 if (! has_dynamic_reloc)
252b5132
RH
6287 printf (_("\nThere are no dynamic relocations in this file.\n"));
6288 }
6289 else
6290 {
2cf0635d 6291 Elf_Internal_Shdr * section;
b34976b6
AM
6292 unsigned long i;
6293 int found = 0;
252b5132
RH
6294
6295 for (i = 0, section = section_headers;
6296 i < elf_header.e_shnum;
b34976b6 6297 i++, section++)
252b5132
RH
6298 {
6299 if ( section->sh_type != SHT_RELA
6300 && section->sh_type != SHT_REL)
6301 continue;
6302
6303 rel_offset = section->sh_offset;
6304 rel_size = section->sh_size;
6305
6306 if (rel_size)
6307 {
2cf0635d 6308 Elf_Internal_Shdr * strsec;
b34976b6 6309 int is_rela;
103f02d3 6310
252b5132
RH
6311 printf (_("\nRelocation section "));
6312
6313 if (string_table == NULL)
19936277 6314 printf ("%d", section->sh_name);
252b5132 6315 else
74e1a04b 6316 printf ("'%s'", printable_section_name (section));
252b5132
RH
6317
6318 printf (_(" at offset 0x%lx contains %lu entries:\n"),
6319 rel_offset, (unsigned long) (rel_size / section->sh_entsize));
6320
d79b3d50
NC
6321 is_rela = section->sh_type == SHT_RELA;
6322
4fbb74a6
AM
6323 if (section->sh_link != 0
6324 && section->sh_link < elf_header.e_shnum)
af3fc3bc 6325 {
2cf0635d
NC
6326 Elf_Internal_Shdr * symsec;
6327 Elf_Internal_Sym * symtab;
d79b3d50 6328 unsigned long nsyms;
c256ffe7 6329 unsigned long strtablen = 0;
2cf0635d 6330 char * strtab = NULL;
57346661 6331
4fbb74a6 6332 symsec = section_headers + section->sh_link;
08d8fa11
JJ
6333 if (symsec->sh_type != SHT_SYMTAB
6334 && symsec->sh_type != SHT_DYNSYM)
6335 continue;
6336
ba5cdace 6337 symtab = GET_ELF_SYMBOLS (file, symsec, & nsyms);
252b5132 6338
af3fc3bc
AM
6339 if (symtab == NULL)
6340 continue;
252b5132 6341
4fbb74a6
AM
6342 if (symsec->sh_link != 0
6343 && symsec->sh_link < elf_header.e_shnum)
c256ffe7 6344 {
4fbb74a6 6345 strsec = section_headers + symsec->sh_link;
103f02d3 6346
3f5e193b 6347 strtab = (char *) get_data (NULL, file, strsec->sh_offset,
071436c6
NC
6348 1, strsec->sh_size,
6349 _("string table"));
c256ffe7
JJ
6350 strtablen = strtab == NULL ? 0 : strsec->sh_size;
6351 }
252b5132 6352
d79b3d50 6353 dump_relocations (file, rel_offset, rel_size,
bb4d2ac2
L
6354 symtab, nsyms, strtab, strtablen,
6355 is_rela,
6356 symsec->sh_type == SHT_DYNSYM);
d79b3d50
NC
6357 if (strtab)
6358 free (strtab);
6359 free (symtab);
6360 }
6361 else
6362 dump_relocations (file, rel_offset, rel_size,
bb4d2ac2 6363 NULL, 0, NULL, 0, is_rela, 0);
252b5132
RH
6364
6365 found = 1;
6366 }
6367 }
6368
6369 if (! found)
6370 printf (_("\nThere are no relocations in this file.\n"));
6371 }
6372
6373 return 1;
6374}
6375
57346661
AM
6376/* Process the unwind section. */
6377
4d6ed7c8
NC
6378#include "unwind-ia64.h"
6379
6380/* An absolute address consists of a section and an offset. If the
6381 section is NULL, the offset itself is the address, otherwise, the
6382 address equals to LOAD_ADDRESS(section) + offset. */
6383
6384struct absaddr
6385 {
6386 unsigned short section;
6387 bfd_vma offset;
6388 };
6389
1949de15
L
6390#define ABSADDR(a) \
6391 ((a).section \
6392 ? section_headers [(a).section].sh_addr + (a).offset \
6393 : (a).offset)
6394
3f5e193b
NC
6395struct ia64_unw_table_entry
6396 {
6397 struct absaddr start;
6398 struct absaddr end;
6399 struct absaddr info;
6400 };
6401
57346661 6402struct ia64_unw_aux_info
4d6ed7c8 6403 {
3f5e193b
NC
6404
6405 struct ia64_unw_table_entry *table; /* Unwind table. */
b34976b6 6406 unsigned long table_len; /* Length of unwind table. */
2cf0635d 6407 unsigned char * info; /* Unwind info. */
b34976b6
AM
6408 unsigned long info_size; /* Size of unwind info. */
6409 bfd_vma info_addr; /* starting address of unwind info. */
6410 bfd_vma seg_base; /* Starting address of segment. */
2cf0635d 6411 Elf_Internal_Sym * symtab; /* The symbol table. */
b34976b6 6412 unsigned long nsyms; /* Number of symbols. */
2cf0635d 6413 char * strtab; /* The string table. */
b34976b6 6414 unsigned long strtab_size; /* Size of string table. */
4d6ed7c8
NC
6415 };
6416
4d6ed7c8 6417static void
2cf0635d 6418find_symbol_for_address (Elf_Internal_Sym * symtab,
57346661 6419 unsigned long nsyms,
2cf0635d 6420 const char * strtab,
57346661 6421 unsigned long strtab_size,
d3ba0551 6422 struct absaddr addr,
2cf0635d
NC
6423 const char ** symname,
6424 bfd_vma * offset)
4d6ed7c8 6425{
d3ba0551 6426 bfd_vma dist = 0x100000;
2cf0635d
NC
6427 Elf_Internal_Sym * sym;
6428 Elf_Internal_Sym * best = NULL;
4d6ed7c8
NC
6429 unsigned long i;
6430
0b6ae522
DJ
6431 REMOVE_ARCH_BITS (addr.offset);
6432
57346661 6433 for (i = 0, sym = symtab; i < nsyms; ++i, ++sym)
4d6ed7c8 6434 {
0b6ae522
DJ
6435 bfd_vma value = sym->st_value;
6436
6437 REMOVE_ARCH_BITS (value);
6438
4d6ed7c8
NC
6439 if (ELF_ST_TYPE (sym->st_info) == STT_FUNC
6440 && sym->st_name != 0
6441 && (addr.section == SHN_UNDEF || addr.section == sym->st_shndx)
0b6ae522
DJ
6442 && addr.offset >= value
6443 && addr.offset - value < dist)
4d6ed7c8
NC
6444 {
6445 best = sym;
0b6ae522 6446 dist = addr.offset - value;
4d6ed7c8
NC
6447 if (!dist)
6448 break;
6449 }
6450 }
1b31d05e 6451
4d6ed7c8
NC
6452 if (best)
6453 {
57346661 6454 *symname = (best->st_name >= strtab_size
2b692964 6455 ? _("<corrupt>") : strtab + best->st_name);
4d6ed7c8
NC
6456 *offset = dist;
6457 return;
6458 }
1b31d05e 6459
4d6ed7c8
NC
6460 *symname = NULL;
6461 *offset = addr.offset;
6462}
6463
6464static void
2cf0635d 6465dump_ia64_unwind (struct ia64_unw_aux_info * aux)
4d6ed7c8 6466{
2cf0635d 6467 struct ia64_unw_table_entry * tp;
4d6ed7c8 6468 int in_body;
7036c0e1 6469
4d6ed7c8
NC
6470 for (tp = aux->table; tp < aux->table + aux->table_len; ++tp)
6471 {
6472 bfd_vma stamp;
6473 bfd_vma offset;
2cf0635d
NC
6474 const unsigned char * dp;
6475 const unsigned char * head;
6476 const char * procname;
4d6ed7c8 6477
57346661
AM
6478 find_symbol_for_address (aux->symtab, aux->nsyms, aux->strtab,
6479 aux->strtab_size, tp->start, &procname, &offset);
4d6ed7c8
NC
6480
6481 fputs ("\n<", stdout);
6482
6483 if (procname)
6484 {
6485 fputs (procname, stdout);
6486
6487 if (offset)
6488 printf ("+%lx", (unsigned long) offset);
6489 }
6490
6491 fputs (">: [", stdout);
6492 print_vma (tp->start.offset, PREFIX_HEX);
6493 fputc ('-', stdout);
6494 print_vma (tp->end.offset, PREFIX_HEX);
86f55779 6495 printf ("], info at +0x%lx\n",
4d6ed7c8
NC
6496 (unsigned long) (tp->info.offset - aux->seg_base));
6497
1949de15 6498 head = aux->info + (ABSADDR (tp->info) - aux->info_addr);
a4a00738 6499 stamp = byte_get ((unsigned char *) head, sizeof (stamp));
4d6ed7c8 6500
86f55779 6501 printf (" v%u, flags=0x%lx (%s%s), len=%lu bytes\n",
4d6ed7c8
NC
6502 (unsigned) UNW_VER (stamp),
6503 (unsigned long) ((stamp & UNW_FLAG_MASK) >> 32),
6504 UNW_FLAG_EHANDLER (stamp) ? " ehandler" : "",
6505 UNW_FLAG_UHANDLER (stamp) ? " uhandler" : "",
89fac5e3 6506 (unsigned long) (eh_addr_size * UNW_LENGTH (stamp)));
4d6ed7c8
NC
6507
6508 if (UNW_VER (stamp) != 1)
6509 {
2b692964 6510 printf (_("\tUnknown version.\n"));
4d6ed7c8
NC
6511 continue;
6512 }
6513
6514 in_body = 0;
89fac5e3 6515 for (dp = head + 8; dp < head + 8 + eh_addr_size * UNW_LENGTH (stamp);)
4d6ed7c8
NC
6516 dp = unw_decode (dp, in_body, & in_body);
6517 }
6518}
6519
6520static int
2cf0635d
NC
6521slurp_ia64_unwind_table (FILE * file,
6522 struct ia64_unw_aux_info * aux,
6523 Elf_Internal_Shdr * sec)
4d6ed7c8 6524{
89fac5e3 6525 unsigned long size, nrelas, i;
2cf0635d
NC
6526 Elf_Internal_Phdr * seg;
6527 struct ia64_unw_table_entry * tep;
6528 Elf_Internal_Shdr * relsec;
6529 Elf_Internal_Rela * rela;
6530 Elf_Internal_Rela * rp;
6531 unsigned char * table;
6532 unsigned char * tp;
6533 Elf_Internal_Sym * sym;
6534 const char * relname;
4d6ed7c8 6535
4d6ed7c8
NC
6536 /* First, find the starting address of the segment that includes
6537 this section: */
6538
6539 if (elf_header.e_phnum)
6540 {
d93f0186 6541 if (! get_program_headers (file))
4d6ed7c8 6542 return 0;
4d6ed7c8 6543
d93f0186
NC
6544 for (seg = program_headers;
6545 seg < program_headers + elf_header.e_phnum;
6546 ++seg)
4d6ed7c8
NC
6547 {
6548 if (seg->p_type != PT_LOAD)
6549 continue;
6550
6551 if (sec->sh_addr >= seg->p_vaddr
6552 && (sec->sh_addr + sec->sh_size <= seg->p_vaddr + seg->p_memsz))
6553 {
6554 aux->seg_base = seg->p_vaddr;
6555 break;
6556 }
6557 }
4d6ed7c8
NC
6558 }
6559
6560 /* Second, build the unwind table from the contents of the unwind section: */
6561 size = sec->sh_size;
3f5e193b
NC
6562 table = (unsigned char *) get_data (NULL, file, sec->sh_offset, 1, size,
6563 _("unwind table"));
a6e9f9df
AM
6564 if (!table)
6565 return 0;
4d6ed7c8 6566
3f5e193b
NC
6567 aux->table = (struct ia64_unw_table_entry *)
6568 xcmalloc (size / (3 * eh_addr_size), sizeof (aux->table[0]));
89fac5e3 6569 tep = aux->table;
c6a0c689 6570 for (tp = table; tp < table + size; ++tep)
4d6ed7c8
NC
6571 {
6572 tep->start.section = SHN_UNDEF;
6573 tep->end.section = SHN_UNDEF;
6574 tep->info.section = SHN_UNDEF;
c6a0c689
AM
6575 tep->start.offset = byte_get (tp, eh_addr_size); tp += eh_addr_size;
6576 tep->end.offset = byte_get (tp, eh_addr_size); tp += eh_addr_size;
6577 tep->info.offset = byte_get (tp, eh_addr_size); tp += eh_addr_size;
4d6ed7c8
NC
6578 tep->start.offset += aux->seg_base;
6579 tep->end.offset += aux->seg_base;
6580 tep->info.offset += aux->seg_base;
6581 }
6582 free (table);
6583
41e92641 6584 /* Third, apply any relocations to the unwind table: */
4d6ed7c8
NC
6585 for (relsec = section_headers;
6586 relsec < section_headers + elf_header.e_shnum;
6587 ++relsec)
6588 {
6589 if (relsec->sh_type != SHT_RELA
4fbb74a6
AM
6590 || relsec->sh_info >= elf_header.e_shnum
6591 || section_headers + relsec->sh_info != sec)
4d6ed7c8
NC
6592 continue;
6593
6594 if (!slurp_rela_relocs (file, relsec->sh_offset, relsec->sh_size,
6595 & rela, & nrelas))
6596 return 0;
6597
6598 for (rp = rela; rp < rela + nrelas; ++rp)
6599 {
aca88567
NC
6600 relname = elf_ia64_reloc_type (get_reloc_type (rp->r_info));
6601 sym = aux->symtab + get_reloc_symindex (rp->r_info);
4d6ed7c8 6602
0112cd26 6603 if (! const_strneq (relname, "R_IA64_SEGREL"))
4d6ed7c8 6604 {
e5fb9629 6605 warn (_("Skipping unexpected relocation type %s\n"), relname);
4d6ed7c8
NC
6606 continue;
6607 }
6608
89fac5e3 6609 i = rp->r_offset / (3 * eh_addr_size);
4d6ed7c8 6610
89fac5e3 6611 switch (rp->r_offset/eh_addr_size % 3)
4d6ed7c8
NC
6612 {
6613 case 0:
6614 aux->table[i].start.section = sym->st_shndx;
e466bc6e 6615 aux->table[i].start.offset = rp->r_addend + sym->st_value;
4d6ed7c8
NC
6616 break;
6617 case 1:
6618 aux->table[i].end.section = sym->st_shndx;
e466bc6e 6619 aux->table[i].end.offset = rp->r_addend + sym->st_value;
4d6ed7c8
NC
6620 break;
6621 case 2:
6622 aux->table[i].info.section = sym->st_shndx;
e466bc6e 6623 aux->table[i].info.offset = rp->r_addend + sym->st_value;
4d6ed7c8
NC
6624 break;
6625 default:
6626 break;
6627 }
6628 }
6629
6630 free (rela);
6631 }
6632
89fac5e3 6633 aux->table_len = size / (3 * eh_addr_size);
4d6ed7c8
NC
6634 return 1;
6635}
6636
1b31d05e 6637static void
2cf0635d 6638ia64_process_unwind (FILE * file)
4d6ed7c8 6639{
2cf0635d
NC
6640 Elf_Internal_Shdr * sec;
6641 Elf_Internal_Shdr * unwsec = NULL;
6642 Elf_Internal_Shdr * strsec;
89fac5e3 6643 unsigned long i, unwcount = 0, unwstart = 0;
57346661 6644 struct ia64_unw_aux_info aux;
f1467e33 6645
4d6ed7c8
NC
6646 memset (& aux, 0, sizeof (aux));
6647
4d6ed7c8
NC
6648 for (i = 0, sec = section_headers; i < elf_header.e_shnum; ++i, ++sec)
6649 {
c256ffe7 6650 if (sec->sh_type == SHT_SYMTAB
4fbb74a6 6651 && sec->sh_link < elf_header.e_shnum)
4d6ed7c8 6652 {
ba5cdace 6653 aux.symtab = GET_ELF_SYMBOLS (file, sec, & aux.nsyms);
4d6ed7c8 6654
4fbb74a6 6655 strsec = section_headers + sec->sh_link;
4082ef84
NC
6656 if (aux.strtab != NULL)
6657 {
6658 error (_("Multiple auxillary string tables encountered\n"));
6659 free (aux.strtab);
6660 }
3f5e193b
NC
6661 aux.strtab = (char *) get_data (NULL, file, strsec->sh_offset,
6662 1, strsec->sh_size,
6663 _("string table"));
c256ffe7 6664 aux.strtab_size = aux.strtab != NULL ? strsec->sh_size : 0;
4d6ed7c8
NC
6665 }
6666 else if (sec->sh_type == SHT_IA_64_UNWIND)
579f31ac
JJ
6667 unwcount++;
6668 }
6669
6670 if (!unwcount)
6671 printf (_("\nThere are no unwind sections in this file.\n"));
6672
6673 while (unwcount-- > 0)
6674 {
2cf0635d 6675 char * suffix;
579f31ac
JJ
6676 size_t len, len2;
6677
4082ef84 6678 for (i = unwstart, sec = section_headers + unwstart, unwsec = NULL;
579f31ac
JJ
6679 i < elf_header.e_shnum; ++i, ++sec)
6680 if (sec->sh_type == SHT_IA_64_UNWIND)
6681 {
6682 unwsec = sec;
6683 break;
6684 }
4082ef84
NC
6685 /* We have already counted the number of SHT_IA64_UNWIND
6686 sections so the loop above should never fail. */
6687 assert (unwsec != NULL);
579f31ac
JJ
6688
6689 unwstart = i + 1;
6690 len = sizeof (ELF_STRING_ia64_unwind_once) - 1;
6691
e4b17d5c
L
6692 if ((unwsec->sh_flags & SHF_GROUP) != 0)
6693 {
6694 /* We need to find which section group it is in. */
4082ef84 6695 struct group_list * g;
e4b17d5c 6696
4082ef84
NC
6697 if (section_headers_groups == NULL
6698 || section_headers_groups [i] == NULL)
6699 i = elf_header.e_shnum;
6700 else
e4b17d5c 6701 {
4082ef84 6702 g = section_headers_groups [i]->root;
18bd398b 6703
4082ef84
NC
6704 for (; g != NULL; g = g->next)
6705 {
6706 sec = section_headers + g->section_index;
e4b17d5c 6707
4082ef84
NC
6708 if (streq (SECTION_NAME (sec), ELF_STRING_ia64_unwind_info))
6709 break;
6710 }
6711
6712 if (g == NULL)
6713 i = elf_header.e_shnum;
6714 }
e4b17d5c 6715 }
18bd398b 6716 else if (strneq (SECTION_NAME (unwsec), ELF_STRING_ia64_unwind_once, len))
579f31ac 6717 {
18bd398b 6718 /* .gnu.linkonce.ia64unw.FOO -> .gnu.linkonce.ia64unwi.FOO. */
579f31ac
JJ
6719 len2 = sizeof (ELF_STRING_ia64_unwind_info_once) - 1;
6720 suffix = SECTION_NAME (unwsec) + len;
6721 for (i = 0, sec = section_headers; i < elf_header.e_shnum;
6722 ++i, ++sec)
18bd398b
NC
6723 if (strneq (SECTION_NAME (sec), ELF_STRING_ia64_unwind_info_once, len2)
6724 && streq (SECTION_NAME (sec) + len2, suffix))
579f31ac
JJ
6725 break;
6726 }
6727 else
6728 {
6729 /* .IA_64.unwindFOO -> .IA_64.unwind_infoFOO
18bd398b 6730 .IA_64.unwind or BAR -> .IA_64.unwind_info. */
579f31ac
JJ
6731 len = sizeof (ELF_STRING_ia64_unwind) - 1;
6732 len2 = sizeof (ELF_STRING_ia64_unwind_info) - 1;
6733 suffix = "";
18bd398b 6734 if (strneq (SECTION_NAME (unwsec), ELF_STRING_ia64_unwind, len))
579f31ac
JJ
6735 suffix = SECTION_NAME (unwsec) + len;
6736 for (i = 0, sec = section_headers; i < elf_header.e_shnum;
6737 ++i, ++sec)
18bd398b
NC
6738 if (strneq (SECTION_NAME (sec), ELF_STRING_ia64_unwind_info, len2)
6739 && streq (SECTION_NAME (sec) + len2, suffix))
579f31ac
JJ
6740 break;
6741 }
6742
6743 if (i == elf_header.e_shnum)
6744 {
6745 printf (_("\nCould not find unwind info section for "));
6746
6747 if (string_table == NULL)
6748 printf ("%d", unwsec->sh_name);
6749 else
74e1a04b 6750 printf ("'%s'", printable_section_name (unwsec));
579f31ac
JJ
6751 }
6752 else
4d6ed7c8 6753 {
4d6ed7c8 6754 aux.info_addr = sec->sh_addr;
3f5e193b 6755 aux.info = (unsigned char *) get_data (NULL, file, sec->sh_offset, 1,
4082ef84
NC
6756 sec->sh_size,
6757 _("unwind info"));
59245841 6758 aux.info_size = aux.info == NULL ? 0 : sec->sh_size;
4d6ed7c8 6759
579f31ac 6760 printf (_("\nUnwind section "));
4d6ed7c8 6761
579f31ac
JJ
6762 if (string_table == NULL)
6763 printf ("%d", unwsec->sh_name);
6764 else
74e1a04b 6765 printf ("'%s'", printable_section_name (unwsec));
4d6ed7c8 6766
579f31ac 6767 printf (_(" at offset 0x%lx contains %lu entries:\n"),
e59b4dfb 6768 (unsigned long) unwsec->sh_offset,
89fac5e3 6769 (unsigned long) (unwsec->sh_size / (3 * eh_addr_size)));
4d6ed7c8 6770
579f31ac 6771 (void) slurp_ia64_unwind_table (file, & aux, unwsec);
4d6ed7c8 6772
579f31ac
JJ
6773 if (aux.table_len > 0)
6774 dump_ia64_unwind (& aux);
6775
6776 if (aux.table)
6777 free ((char *) aux.table);
6778 if (aux.info)
6779 free ((char *) aux.info);
6780 aux.table = NULL;
6781 aux.info = NULL;
6782 }
4d6ed7c8 6783 }
4d6ed7c8 6784
4d6ed7c8
NC
6785 if (aux.symtab)
6786 free (aux.symtab);
6787 if (aux.strtab)
6788 free ((char *) aux.strtab);
4d6ed7c8
NC
6789}
6790
3f5e193b
NC
6791struct hppa_unw_table_entry
6792 {
6793 struct absaddr start;
6794 struct absaddr end;
6795 unsigned int Cannot_unwind:1; /* 0 */
6796 unsigned int Millicode:1; /* 1 */
6797 unsigned int Millicode_save_sr0:1; /* 2 */
6798 unsigned int Region_description:2; /* 3..4 */
6799 unsigned int reserved1:1; /* 5 */
6800 unsigned int Entry_SR:1; /* 6 */
6801 unsigned int Entry_FR:4; /* number saved */ /* 7..10 */
6802 unsigned int Entry_GR:5; /* number saved */ /* 11..15 */
6803 unsigned int Args_stored:1; /* 16 */
6804 unsigned int Variable_Frame:1; /* 17 */
6805 unsigned int Separate_Package_Body:1; /* 18 */
6806 unsigned int Frame_Extension_Millicode:1; /* 19 */
6807 unsigned int Stack_Overflow_Check:1; /* 20 */
6808 unsigned int Two_Instruction_SP_Increment:1; /* 21 */
6809 unsigned int Ada_Region:1; /* 22 */
6810 unsigned int cxx_info:1; /* 23 */
6811 unsigned int cxx_try_catch:1; /* 24 */
6812 unsigned int sched_entry_seq:1; /* 25 */
6813 unsigned int reserved2:1; /* 26 */
6814 unsigned int Save_SP:1; /* 27 */
6815 unsigned int Save_RP:1; /* 28 */
6816 unsigned int Save_MRP_in_frame:1; /* 29 */
6817 unsigned int extn_ptr_defined:1; /* 30 */
6818 unsigned int Cleanup_defined:1; /* 31 */
6819
6820 unsigned int MPE_XL_interrupt_marker:1; /* 0 */
6821 unsigned int HP_UX_interrupt_marker:1; /* 1 */
6822 unsigned int Large_frame:1; /* 2 */
6823 unsigned int Pseudo_SP_Set:1; /* 3 */
6824 unsigned int reserved4:1; /* 4 */
6825 unsigned int Total_frame_size:27; /* 5..31 */
6826 };
6827
57346661
AM
6828struct hppa_unw_aux_info
6829 {
3f5e193b 6830 struct hppa_unw_table_entry *table; /* Unwind table. */
57346661
AM
6831 unsigned long table_len; /* Length of unwind table. */
6832 bfd_vma seg_base; /* Starting address of segment. */
2cf0635d 6833 Elf_Internal_Sym * symtab; /* The symbol table. */
57346661 6834 unsigned long nsyms; /* Number of symbols. */
2cf0635d 6835 char * strtab; /* The string table. */
57346661
AM
6836 unsigned long strtab_size; /* Size of string table. */
6837 };
6838
6839static void
2cf0635d 6840dump_hppa_unwind (struct hppa_unw_aux_info * aux)
57346661 6841{
2cf0635d 6842 struct hppa_unw_table_entry * tp;
57346661 6843
57346661
AM
6844 for (tp = aux->table; tp < aux->table + aux->table_len; ++tp)
6845 {
6846 bfd_vma offset;
2cf0635d 6847 const char * procname;
57346661
AM
6848
6849 find_symbol_for_address (aux->symtab, aux->nsyms, aux->strtab,
6850 aux->strtab_size, tp->start, &procname,
6851 &offset);
6852
6853 fputs ("\n<", stdout);
6854
6855 if (procname)
6856 {
6857 fputs (procname, stdout);
6858
6859 if (offset)
6860 printf ("+%lx", (unsigned long) offset);
6861 }
6862
6863 fputs (">: [", stdout);
6864 print_vma (tp->start.offset, PREFIX_HEX);
6865 fputc ('-', stdout);
6866 print_vma (tp->end.offset, PREFIX_HEX);
6867 printf ("]\n\t");
6868
18bd398b
NC
6869#define PF(_m) if (tp->_m) printf (#_m " ");
6870#define PV(_m) if (tp->_m) printf (#_m "=%d ", tp->_m);
57346661
AM
6871 PF(Cannot_unwind);
6872 PF(Millicode);
6873 PF(Millicode_save_sr0);
18bd398b 6874 /* PV(Region_description); */
57346661
AM
6875 PF(Entry_SR);
6876 PV(Entry_FR);
6877 PV(Entry_GR);
6878 PF(Args_stored);
6879 PF(Variable_Frame);
6880 PF(Separate_Package_Body);
6881 PF(Frame_Extension_Millicode);
6882 PF(Stack_Overflow_Check);
6883 PF(Two_Instruction_SP_Increment);
6884 PF(Ada_Region);
6885 PF(cxx_info);
6886 PF(cxx_try_catch);
6887 PF(sched_entry_seq);
6888 PF(Save_SP);
6889 PF(Save_RP);
6890 PF(Save_MRP_in_frame);
6891 PF(extn_ptr_defined);
6892 PF(Cleanup_defined);
6893 PF(MPE_XL_interrupt_marker);
6894 PF(HP_UX_interrupt_marker);
6895 PF(Large_frame);
6896 PF(Pseudo_SP_Set);
6897 PV(Total_frame_size);
6898#undef PF
6899#undef PV
6900 }
6901
18bd398b 6902 printf ("\n");
57346661
AM
6903}
6904
6905static int
2cf0635d
NC
6906slurp_hppa_unwind_table (FILE * file,
6907 struct hppa_unw_aux_info * aux,
6908 Elf_Internal_Shdr * sec)
57346661 6909{
1c0751b2 6910 unsigned long size, unw_ent_size, nentries, nrelas, i;
2cf0635d
NC
6911 Elf_Internal_Phdr * seg;
6912 struct hppa_unw_table_entry * tep;
6913 Elf_Internal_Shdr * relsec;
6914 Elf_Internal_Rela * rela;
6915 Elf_Internal_Rela * rp;
6916 unsigned char * table;
6917 unsigned char * tp;
6918 Elf_Internal_Sym * sym;
6919 const char * relname;
57346661 6920
57346661
AM
6921 /* First, find the starting address of the segment that includes
6922 this section. */
6923
6924 if (elf_header.e_phnum)
6925 {
6926 if (! get_program_headers (file))
6927 return 0;
6928
6929 for (seg = program_headers;
6930 seg < program_headers + elf_header.e_phnum;
6931 ++seg)
6932 {
6933 if (seg->p_type != PT_LOAD)
6934 continue;
6935
6936 if (sec->sh_addr >= seg->p_vaddr
6937 && (sec->sh_addr + sec->sh_size <= seg->p_vaddr + seg->p_memsz))
6938 {
6939 aux->seg_base = seg->p_vaddr;
6940 break;
6941 }
6942 }
6943 }
6944
6945 /* Second, build the unwind table from the contents of the unwind
6946 section. */
6947 size = sec->sh_size;
3f5e193b
NC
6948 table = (unsigned char *) get_data (NULL, file, sec->sh_offset, 1, size,
6949 _("unwind table"));
57346661
AM
6950 if (!table)
6951 return 0;
6952
1c0751b2
DA
6953 unw_ent_size = 16;
6954 nentries = size / unw_ent_size;
6955 size = unw_ent_size * nentries;
57346661 6956
3f5e193b
NC
6957 tep = aux->table = (struct hppa_unw_table_entry *)
6958 xcmalloc (nentries, sizeof (aux->table[0]));
57346661 6959
1c0751b2 6960 for (tp = table; tp < table + size; tp += unw_ent_size, ++tep)
57346661
AM
6961 {
6962 unsigned int tmp1, tmp2;
6963
6964 tep->start.section = SHN_UNDEF;
6965 tep->end.section = SHN_UNDEF;
6966
1c0751b2
DA
6967 tep->start.offset = byte_get ((unsigned char *) tp + 0, 4);
6968 tep->end.offset = byte_get ((unsigned char *) tp + 4, 4);
6969 tmp1 = byte_get ((unsigned char *) tp + 8, 4);
6970 tmp2 = byte_get ((unsigned char *) tp + 12, 4);
6971
6972 tep->start.offset += aux->seg_base;
6973 tep->end.offset += aux->seg_base;
57346661
AM
6974
6975 tep->Cannot_unwind = (tmp1 >> 31) & 0x1;
6976 tep->Millicode = (tmp1 >> 30) & 0x1;
6977 tep->Millicode_save_sr0 = (tmp1 >> 29) & 0x1;
6978 tep->Region_description = (tmp1 >> 27) & 0x3;
6979 tep->reserved1 = (tmp1 >> 26) & 0x1;
6980 tep->Entry_SR = (tmp1 >> 25) & 0x1;
6981 tep->Entry_FR = (tmp1 >> 21) & 0xf;
6982 tep->Entry_GR = (tmp1 >> 16) & 0x1f;
6983 tep->Args_stored = (tmp1 >> 15) & 0x1;
6984 tep->Variable_Frame = (tmp1 >> 14) & 0x1;
6985 tep->Separate_Package_Body = (tmp1 >> 13) & 0x1;
6986 tep->Frame_Extension_Millicode = (tmp1 >> 12) & 0x1;
6987 tep->Stack_Overflow_Check = (tmp1 >> 11) & 0x1;
6988 tep->Two_Instruction_SP_Increment = (tmp1 >> 10) & 0x1;
6989 tep->Ada_Region = (tmp1 >> 9) & 0x1;
6990 tep->cxx_info = (tmp1 >> 8) & 0x1;
6991 tep->cxx_try_catch = (tmp1 >> 7) & 0x1;
6992 tep->sched_entry_seq = (tmp1 >> 6) & 0x1;
6993 tep->reserved2 = (tmp1 >> 5) & 0x1;
6994 tep->Save_SP = (tmp1 >> 4) & 0x1;
6995 tep->Save_RP = (tmp1 >> 3) & 0x1;
6996 tep->Save_MRP_in_frame = (tmp1 >> 2) & 0x1;
6997 tep->extn_ptr_defined = (tmp1 >> 1) & 0x1;
6998 tep->Cleanup_defined = tmp1 & 0x1;
6999
7000 tep->MPE_XL_interrupt_marker = (tmp2 >> 31) & 0x1;
7001 tep->HP_UX_interrupt_marker = (tmp2 >> 30) & 0x1;
7002 tep->Large_frame = (tmp2 >> 29) & 0x1;
7003 tep->Pseudo_SP_Set = (tmp2 >> 28) & 0x1;
7004 tep->reserved4 = (tmp2 >> 27) & 0x1;
7005 tep->Total_frame_size = tmp2 & 0x7ffffff;
57346661
AM
7006 }
7007 free (table);
7008
7009 /* Third, apply any relocations to the unwind table. */
57346661
AM
7010 for (relsec = section_headers;
7011 relsec < section_headers + elf_header.e_shnum;
7012 ++relsec)
7013 {
7014 if (relsec->sh_type != SHT_RELA
4fbb74a6
AM
7015 || relsec->sh_info >= elf_header.e_shnum
7016 || section_headers + relsec->sh_info != sec)
57346661
AM
7017 continue;
7018
7019 if (!slurp_rela_relocs (file, relsec->sh_offset, relsec->sh_size,
7020 & rela, & nrelas))
7021 return 0;
7022
7023 for (rp = rela; rp < rela + nrelas; ++rp)
7024 {
aca88567
NC
7025 relname = elf_hppa_reloc_type (get_reloc_type (rp->r_info));
7026 sym = aux->symtab + get_reloc_symindex (rp->r_info);
57346661
AM
7027
7028 /* R_PARISC_SEGREL32 or R_PARISC_SEGREL64. */
0112cd26 7029 if (! const_strneq (relname, "R_PARISC_SEGREL"))
57346661
AM
7030 {
7031 warn (_("Skipping unexpected relocation type %s\n"), relname);
7032 continue;
7033 }
7034
7035 i = rp->r_offset / unw_ent_size;
7036
89fac5e3 7037 switch ((rp->r_offset % unw_ent_size) / eh_addr_size)
57346661
AM
7038 {
7039 case 0:
7040 aux->table[i].start.section = sym->st_shndx;
1e456d54 7041 aux->table[i].start.offset = sym->st_value + rp->r_addend;
57346661
AM
7042 break;
7043 case 1:
7044 aux->table[i].end.section = sym->st_shndx;
1e456d54 7045 aux->table[i].end.offset = sym->st_value + rp->r_addend;
57346661
AM
7046 break;
7047 default:
7048 break;
7049 }
7050 }
7051
7052 free (rela);
7053 }
7054
1c0751b2 7055 aux->table_len = nentries;
57346661
AM
7056
7057 return 1;
7058}
7059
1b31d05e 7060static void
2cf0635d 7061hppa_process_unwind (FILE * file)
57346661 7062{
57346661 7063 struct hppa_unw_aux_info aux;
2cf0635d
NC
7064 Elf_Internal_Shdr * unwsec = NULL;
7065 Elf_Internal_Shdr * strsec;
7066 Elf_Internal_Shdr * sec;
18bd398b 7067 unsigned long i;
57346661 7068
c256ffe7 7069 if (string_table == NULL)
1b31d05e
NC
7070 return;
7071
7072 memset (& aux, 0, sizeof (aux));
57346661
AM
7073
7074 for (i = 0, sec = section_headers; i < elf_header.e_shnum; ++i, ++sec)
7075 {
c256ffe7 7076 if (sec->sh_type == SHT_SYMTAB
4fbb74a6 7077 && sec->sh_link < elf_header.e_shnum)
57346661 7078 {
ba5cdace 7079 aux.symtab = GET_ELF_SYMBOLS (file, sec, & aux.nsyms);
57346661 7080
4fbb74a6 7081 strsec = section_headers + sec->sh_link;
4082ef84
NC
7082 if (aux.strtab != NULL)
7083 {
7084 error (_("Multiple auxillary string tables encountered\n"));
7085 free (aux.strtab);
7086 }
3f5e193b
NC
7087 aux.strtab = (char *) get_data (NULL, file, strsec->sh_offset,
7088 1, strsec->sh_size,
7089 _("string table"));
c256ffe7 7090 aux.strtab_size = aux.strtab != NULL ? strsec->sh_size : 0;
57346661 7091 }
18bd398b 7092 else if (streq (SECTION_NAME (sec), ".PARISC.unwind"))
57346661
AM
7093 unwsec = sec;
7094 }
7095
7096 if (!unwsec)
7097 printf (_("\nThere are no unwind sections in this file.\n"));
7098
7099 for (i = 0, sec = section_headers; i < elf_header.e_shnum; ++i, ++sec)
7100 {
18bd398b 7101 if (streq (SECTION_NAME (sec), ".PARISC.unwind"))
57346661 7102 {
74e1a04b
NC
7103 printf (_("\nUnwind section '%s' at offset 0x%lx contains %lu entries:\n"),
7104 printable_section_name (sec),
57346661 7105 (unsigned long) sec->sh_offset,
89fac5e3 7106 (unsigned long) (sec->sh_size / (2 * eh_addr_size + 8)));
57346661
AM
7107
7108 slurp_hppa_unwind_table (file, &aux, sec);
7109 if (aux.table_len > 0)
7110 dump_hppa_unwind (&aux);
7111
7112 if (aux.table)
7113 free ((char *) aux.table);
7114 aux.table = NULL;
7115 }
7116 }
7117
7118 if (aux.symtab)
7119 free (aux.symtab);
7120 if (aux.strtab)
7121 free ((char *) aux.strtab);
57346661
AM
7122}
7123
0b6ae522
DJ
7124struct arm_section
7125{
a734115a
NC
7126 unsigned char * data; /* The unwind data. */
7127 Elf_Internal_Shdr * sec; /* The cached unwind section header. */
7128 Elf_Internal_Rela * rela; /* The cached relocations for this section. */
7129 unsigned long nrelas; /* The number of relocations. */
7130 unsigned int rel_type; /* REL or RELA ? */
7131 Elf_Internal_Rela * next_rela; /* Cyclic pointer to the next reloc to process. */
0b6ae522
DJ
7132};
7133
7134struct arm_unw_aux_info
7135{
a734115a
NC
7136 FILE * file; /* The file containing the unwind sections. */
7137 Elf_Internal_Sym * symtab; /* The file's symbol table. */
7138 unsigned long nsyms; /* Number of symbols. */
7139 char * strtab; /* The file's string table. */
7140 unsigned long strtab_size; /* Size of string table. */
0b6ae522
DJ
7141};
7142
7143static const char *
7144arm_print_vma_and_name (struct arm_unw_aux_info *aux,
7145 bfd_vma fn, struct absaddr addr)
7146{
7147 const char *procname;
7148 bfd_vma sym_offset;
7149
7150 if (addr.section == SHN_UNDEF)
7151 addr.offset = fn;
7152
7153 find_symbol_for_address (aux->symtab, aux->nsyms, aux->strtab,
7154 aux->strtab_size, addr, &procname,
7155 &sym_offset);
7156
7157 print_vma (fn, PREFIX_HEX);
7158
7159 if (procname)
7160 {
7161 fputs (" <", stdout);
7162 fputs (procname, stdout);
7163
7164 if (sym_offset)
7165 printf ("+0x%lx", (unsigned long) sym_offset);
7166 fputc ('>', stdout);
7167 }
7168
7169 return procname;
7170}
7171
7172static void
7173arm_free_section (struct arm_section *arm_sec)
7174{
7175 if (arm_sec->data != NULL)
7176 free (arm_sec->data);
7177
7178 if (arm_sec->rela != NULL)
7179 free (arm_sec->rela);
7180}
7181
a734115a
NC
7182/* 1) If SEC does not match the one cached in ARM_SEC, then free the current
7183 cached section and install SEC instead.
7184 2) Locate the 32-bit word at WORD_OFFSET in unwind section SEC
7185 and return its valued in * WORDP, relocating if necessary.
1b31d05e 7186 3) Update the NEXT_RELA field in ARM_SEC and store the section index and
a734115a 7187 relocation's offset in ADDR.
1b31d05e
NC
7188 4) If SYM_NAME is non-NULL and a relocation was applied, record the offset
7189 into the string table of the symbol associated with the reloc. If no
7190 reloc was applied store -1 there.
7191 5) Return TRUE upon success, FALSE otherwise. */
a734115a
NC
7192
7193static bfd_boolean
1b31d05e
NC
7194get_unwind_section_word (struct arm_unw_aux_info * aux,
7195 struct arm_section * arm_sec,
7196 Elf_Internal_Shdr * sec,
7197 bfd_vma word_offset,
7198 unsigned int * wordp,
7199 struct absaddr * addr,
7200 bfd_vma * sym_name)
0b6ae522
DJ
7201{
7202 Elf_Internal_Rela *rp;
7203 Elf_Internal_Sym *sym;
7204 const char * relname;
7205 unsigned int word;
7206 bfd_boolean wrapped;
7207
e0a31db1
NC
7208 if (sec == NULL || arm_sec == NULL)
7209 return FALSE;
7210
0b6ae522
DJ
7211 addr->section = SHN_UNDEF;
7212 addr->offset = 0;
7213
1b31d05e
NC
7214 if (sym_name != NULL)
7215 *sym_name = (bfd_vma) -1;
7216
a734115a 7217 /* If necessary, update the section cache. */
0b6ae522
DJ
7218 if (sec != arm_sec->sec)
7219 {
7220 Elf_Internal_Shdr *relsec;
7221
7222 arm_free_section (arm_sec);
7223
7224 arm_sec->sec = sec;
7225 arm_sec->data = get_data (NULL, aux->file, sec->sh_offset, 1,
7226 sec->sh_size, _("unwind data"));
0b6ae522
DJ
7227 arm_sec->rela = NULL;
7228 arm_sec->nrelas = 0;
7229
7230 for (relsec = section_headers;
7231 relsec < section_headers + elf_header.e_shnum;
7232 ++relsec)
7233 {
7234 if (relsec->sh_info >= elf_header.e_shnum
1ae40aa4
NC
7235 || section_headers + relsec->sh_info != sec
7236 /* PR 15745: Check the section type as well. */
7237 || (relsec->sh_type != SHT_REL
7238 && relsec->sh_type != SHT_RELA))
0b6ae522
DJ
7239 continue;
7240
a734115a 7241 arm_sec->rel_type = relsec->sh_type;
0b6ae522
DJ
7242 if (relsec->sh_type == SHT_REL)
7243 {
7244 if (!slurp_rel_relocs (aux->file, relsec->sh_offset,
7245 relsec->sh_size,
7246 & arm_sec->rela, & arm_sec->nrelas))
a734115a 7247 return FALSE;
0b6ae522 7248 }
1ae40aa4 7249 else /* relsec->sh_type == SHT_RELA */
0b6ae522
DJ
7250 {
7251 if (!slurp_rela_relocs (aux->file, relsec->sh_offset,
7252 relsec->sh_size,
7253 & arm_sec->rela, & arm_sec->nrelas))
a734115a 7254 return FALSE;
0b6ae522 7255 }
1ae40aa4 7256 break;
0b6ae522
DJ
7257 }
7258
7259 arm_sec->next_rela = arm_sec->rela;
7260 }
7261
a734115a 7262 /* If there is no unwind data we can do nothing. */
0b6ae522 7263 if (arm_sec->data == NULL)
a734115a 7264 return FALSE;
0b6ae522 7265
e0a31db1
NC
7266 /* If the offset is invalid then fail. */
7267 if (word_offset > sec->sh_size - 4)
7268 return FALSE;
7269
a734115a 7270 /* Get the word at the required offset. */
0b6ae522
DJ
7271 word = byte_get (arm_sec->data + word_offset, 4);
7272
0eff7165
NC
7273 /* PR 17531: file: id:000001,src:001266+003044,op:splice,rep:128. */
7274 if (arm_sec->rela == NULL)
7275 {
7276 * wordp = word;
7277 return TRUE;
7278 }
7279
a734115a 7280 /* Look through the relocs to find the one that applies to the provided offset. */
0b6ae522
DJ
7281 wrapped = FALSE;
7282 for (rp = arm_sec->next_rela; rp != arm_sec->rela + arm_sec->nrelas; rp++)
7283 {
7284 bfd_vma prelval, offset;
7285
7286 if (rp->r_offset > word_offset && !wrapped)
7287 {
7288 rp = arm_sec->rela;
7289 wrapped = TRUE;
7290 }
7291 if (rp->r_offset > word_offset)
7292 break;
7293
7294 if (rp->r_offset & 3)
7295 {
7296 warn (_("Skipping unexpected relocation at offset 0x%lx\n"),
7297 (unsigned long) rp->r_offset);
7298 continue;
7299 }
7300
7301 if (rp->r_offset < word_offset)
7302 continue;
7303
74e1a04b
NC
7304 /* PR 17531: file: 027-161405-0.004 */
7305 if (aux->symtab == NULL)
7306 continue;
7307
0b6ae522
DJ
7308 if (arm_sec->rel_type == SHT_REL)
7309 {
7310 offset = word & 0x7fffffff;
7311 if (offset & 0x40000000)
7312 offset |= ~ (bfd_vma) 0x7fffffff;
7313 }
a734115a 7314 else if (arm_sec->rel_type == SHT_RELA)
0b6ae522 7315 offset = rp->r_addend;
a734115a 7316 else
74e1a04b
NC
7317 {
7318 error (_("Unknown section relocation type %d encountered\n"),
7319 arm_sec->rel_type);
7320 break;
7321 }
0b6ae522 7322
071436c6
NC
7323 /* PR 17531 file: 027-1241568-0.004. */
7324 if (ELF32_R_SYM (rp->r_info) >= aux->nsyms)
7325 {
7326 error (_("Bad symbol index in unwind relocation (%lu > %lu)\n"),
7327 (unsigned long) ELF32_R_SYM (rp->r_info), aux->nsyms);
7328 break;
7329 }
7330
7331 sym = aux->symtab + ELF32_R_SYM (rp->r_info);
0b6ae522
DJ
7332 offset += sym->st_value;
7333 prelval = offset - (arm_sec->sec->sh_addr + rp->r_offset);
7334
a734115a
NC
7335 /* Check that we are processing the expected reloc type. */
7336 if (elf_header.e_machine == EM_ARM)
7337 {
7338 relname = elf_arm_reloc_type (ELF32_R_TYPE (rp->r_info));
071436c6
NC
7339 if (relname == NULL)
7340 {
7341 warn (_("Skipping unknown ARM relocation type: %d\n"),
7342 (int) ELF32_R_TYPE (rp->r_info));
7343 continue;
7344 }
a734115a
NC
7345
7346 if (streq (relname, "R_ARM_NONE"))
7347 continue;
0b4362b0 7348
a734115a
NC
7349 if (! streq (relname, "R_ARM_PREL31"))
7350 {
071436c6 7351 warn (_("Skipping unexpected ARM relocation type %s\n"), relname);
a734115a
NC
7352 continue;
7353 }
7354 }
7355 else if (elf_header.e_machine == EM_TI_C6000)
7356 {
7357 relname = elf_tic6x_reloc_type (ELF32_R_TYPE (rp->r_info));
071436c6
NC
7358 if (relname == NULL)
7359 {
7360 warn (_("Skipping unknown C6000 relocation type: %d\n"),
7361 (int) ELF32_R_TYPE (rp->r_info));
7362 continue;
7363 }
0b4362b0 7364
a734115a
NC
7365 if (streq (relname, "R_C6000_NONE"))
7366 continue;
7367
7368 if (! streq (relname, "R_C6000_PREL31"))
7369 {
071436c6 7370 warn (_("Skipping unexpected C6000 relocation type %s\n"), relname);
a734115a
NC
7371 continue;
7372 }
7373
7374 prelval >>= 1;
7375 }
7376 else
74e1a04b
NC
7377 {
7378 /* This function currently only supports ARM and TI unwinders. */
7379 warn (_("Only TI and ARM unwinders are currently supported\n"));
7380 break;
7381 }
fa197c1c 7382
0b6ae522
DJ
7383 word = (word & ~ (bfd_vma) 0x7fffffff) | (prelval & 0x7fffffff);
7384 addr->section = sym->st_shndx;
7385 addr->offset = offset;
74e1a04b 7386
1b31d05e
NC
7387 if (sym_name)
7388 * sym_name = sym->st_name;
0b6ae522
DJ
7389 break;
7390 }
7391
7392 *wordp = word;
7393 arm_sec->next_rela = rp;
7394
a734115a 7395 return TRUE;
0b6ae522
DJ
7396}
7397
a734115a
NC
7398static const char *tic6x_unwind_regnames[16] =
7399{
0b4362b0
RM
7400 "A15", "B15", "B14", "B13", "B12", "B11", "B10", "B3",
7401 "A14", "A13", "A12", "A11", "A10",
a734115a
NC
7402 "[invalid reg 13]", "[invalid reg 14]", "[invalid reg 15]"
7403};
fa197c1c 7404
0b6ae522 7405static void
fa197c1c 7406decode_tic6x_unwind_regmask (unsigned int mask)
0b6ae522 7407{
fa197c1c
PB
7408 int i;
7409
7410 for (i = 12; mask; mask >>= 1, i--)
7411 {
7412 if (mask & 1)
7413 {
7414 fputs (tic6x_unwind_regnames[i], stdout);
7415 if (mask > 1)
7416 fputs (", ", stdout);
7417 }
7418 }
7419}
0b6ae522
DJ
7420
7421#define ADVANCE \
7422 if (remaining == 0 && more_words) \
7423 { \
7424 data_offset += 4; \
1b31d05e
NC
7425 if (! get_unwind_section_word (aux, data_arm_sec, data_sec, \
7426 data_offset, & word, & addr, NULL)) \
0b6ae522
DJ
7427 return; \
7428 remaining = 4; \
7429 more_words--; \
7430 } \
7431
7432#define GET_OP(OP) \
7433 ADVANCE; \
7434 if (remaining) \
7435 { \
7436 remaining--; \
7437 (OP) = word >> 24; \
7438 word <<= 8; \
7439 } \
7440 else \
7441 { \
2b692964 7442 printf (_("[Truncated opcode]\n")); \
0b6ae522
DJ
7443 return; \
7444 } \
cc5914eb 7445 printf ("0x%02x ", OP)
0b6ae522 7446
fa197c1c
PB
7447static void
7448decode_arm_unwind_bytecode (struct arm_unw_aux_info *aux,
7449 unsigned int word, unsigned int remaining,
7450 unsigned int more_words,
7451 bfd_vma data_offset, Elf_Internal_Shdr *data_sec,
7452 struct arm_section *data_arm_sec)
7453{
7454 struct absaddr addr;
0b6ae522
DJ
7455
7456 /* Decode the unwinding instructions. */
7457 while (1)
7458 {
7459 unsigned int op, op2;
7460
7461 ADVANCE;
7462 if (remaining == 0)
7463 break;
7464 remaining--;
7465 op = word >> 24;
7466 word <<= 8;
7467
cc5914eb 7468 printf (" 0x%02x ", op);
0b6ae522
DJ
7469
7470 if ((op & 0xc0) == 0x00)
7471 {
7472 int offset = ((op & 0x3f) << 2) + 4;
61865e30 7473
cc5914eb 7474 printf (" vsp = vsp + %d", offset);
0b6ae522
DJ
7475 }
7476 else if ((op & 0xc0) == 0x40)
7477 {
7478 int offset = ((op & 0x3f) << 2) + 4;
61865e30 7479
cc5914eb 7480 printf (" vsp = vsp - %d", offset);
0b6ae522
DJ
7481 }
7482 else if ((op & 0xf0) == 0x80)
7483 {
7484 GET_OP (op2);
7485 if (op == 0x80 && op2 == 0)
7486 printf (_("Refuse to unwind"));
7487 else
7488 {
7489 unsigned int mask = ((op & 0x0f) << 8) | op2;
7490 int first = 1;
7491 int i;
2b692964 7492
0b6ae522
DJ
7493 printf ("pop {");
7494 for (i = 0; i < 12; i++)
7495 if (mask & (1 << i))
7496 {
7497 if (first)
7498 first = 0;
7499 else
7500 printf (", ");
7501 printf ("r%d", 4 + i);
7502 }
7503 printf ("}");
7504 }
7505 }
7506 else if ((op & 0xf0) == 0x90)
7507 {
7508 if (op == 0x9d || op == 0x9f)
7509 printf (_(" [Reserved]"));
7510 else
cc5914eb 7511 printf (" vsp = r%d", op & 0x0f);
0b6ae522
DJ
7512 }
7513 else if ((op & 0xf0) == 0xa0)
7514 {
7515 int end = 4 + (op & 0x07);
7516 int first = 1;
7517 int i;
61865e30 7518
0b6ae522
DJ
7519 printf (" pop {");
7520 for (i = 4; i <= end; i++)
7521 {
7522 if (first)
7523 first = 0;
7524 else
7525 printf (", ");
7526 printf ("r%d", i);
7527 }
7528 if (op & 0x08)
7529 {
1b31d05e 7530 if (!first)
0b6ae522
DJ
7531 printf (", ");
7532 printf ("r14");
7533 }
7534 printf ("}");
7535 }
7536 else if (op == 0xb0)
7537 printf (_(" finish"));
7538 else if (op == 0xb1)
7539 {
7540 GET_OP (op2);
7541 if (op2 == 0 || (op2 & 0xf0) != 0)
7542 printf (_("[Spare]"));
7543 else
7544 {
7545 unsigned int mask = op2 & 0x0f;
7546 int first = 1;
7547 int i;
61865e30 7548
0b6ae522
DJ
7549 printf ("pop {");
7550 for (i = 0; i < 12; i++)
7551 if (mask & (1 << i))
7552 {
7553 if (first)
7554 first = 0;
7555 else
7556 printf (", ");
7557 printf ("r%d", i);
7558 }
7559 printf ("}");
7560 }
7561 }
7562 else if (op == 0xb2)
7563 {
b115cf96 7564 unsigned char buf[9];
0b6ae522
DJ
7565 unsigned int i, len;
7566 unsigned long offset;
61865e30 7567
b115cf96 7568 for (i = 0; i < sizeof (buf); i++)
0b6ae522
DJ
7569 {
7570 GET_OP (buf[i]);
7571 if ((buf[i] & 0x80) == 0)
7572 break;
7573 }
4082ef84
NC
7574 if (i == sizeof (buf))
7575 printf (_("corrupt change to vsp"));
7576 else
7577 {
7578 offset = read_uleb128 (buf, &len, buf + i + 1);
7579 assert (len == i + 1);
7580 offset = offset * 4 + 0x204;
7581 printf ("vsp = vsp + %ld", offset);
7582 }
0b6ae522 7583 }
61865e30 7584 else if (op == 0xb3 || op == 0xc8 || op == 0xc9)
0b6ae522 7585 {
61865e30
NC
7586 unsigned int first, last;
7587
7588 GET_OP (op2);
7589 first = op2 >> 4;
7590 last = op2 & 0x0f;
7591 if (op == 0xc8)
7592 first = first + 16;
7593 printf ("pop {D%d", first);
7594 if (last)
7595 printf ("-D%d", first + last);
7596 printf ("}");
7597 }
7598 else if ((op & 0xf8) == 0xb8 || (op & 0xf8) == 0xd0)
7599 {
7600 unsigned int count = op & 0x07;
7601
7602 printf ("pop {D8");
7603 if (count)
7604 printf ("-D%d", 8 + count);
7605 printf ("}");
7606 }
7607 else if (op >= 0xc0 && op <= 0xc5)
7608 {
7609 unsigned int count = op & 0x07;
7610
7611 printf (" pop {wR10");
7612 if (count)
7613 printf ("-wR%d", 10 + count);
7614 printf ("}");
7615 }
7616 else if (op == 0xc6)
7617 {
7618 unsigned int first, last;
7619
7620 GET_OP (op2);
7621 first = op2 >> 4;
7622 last = op2 & 0x0f;
7623 printf ("pop {wR%d", first);
7624 if (last)
7625 printf ("-wR%d", first + last);
7626 printf ("}");
7627 }
7628 else if (op == 0xc7)
7629 {
7630 GET_OP (op2);
7631 if (op2 == 0 || (op2 & 0xf0) != 0)
7632 printf (_("[Spare]"));
0b6ae522
DJ
7633 else
7634 {
61865e30
NC
7635 unsigned int mask = op2 & 0x0f;
7636 int first = 1;
7637 int i;
7638
7639 printf ("pop {");
7640 for (i = 0; i < 4; i++)
7641 if (mask & (1 << i))
7642 {
7643 if (first)
7644 first = 0;
7645 else
7646 printf (", ");
7647 printf ("wCGR%d", i);
7648 }
7649 printf ("}");
0b6ae522
DJ
7650 }
7651 }
61865e30
NC
7652 else
7653 printf (_(" [unsupported opcode]"));
0b6ae522
DJ
7654 printf ("\n");
7655 }
fa197c1c
PB
7656}
7657
7658static void
7659decode_tic6x_unwind_bytecode (struct arm_unw_aux_info *aux,
7660 unsigned int word, unsigned int remaining,
7661 unsigned int more_words,
7662 bfd_vma data_offset, Elf_Internal_Shdr *data_sec,
7663 struct arm_section *data_arm_sec)
7664{
7665 struct absaddr addr;
7666
7667 /* Decode the unwinding instructions. */
7668 while (1)
7669 {
7670 unsigned int op, op2;
7671
7672 ADVANCE;
7673 if (remaining == 0)
7674 break;
7675 remaining--;
7676 op = word >> 24;
7677 word <<= 8;
7678
9cf03b7e 7679 printf (" 0x%02x ", op);
fa197c1c
PB
7680
7681 if ((op & 0xc0) == 0x00)
7682 {
7683 int offset = ((op & 0x3f) << 3) + 8;
9cf03b7e 7684 printf (" sp = sp + %d", offset);
fa197c1c
PB
7685 }
7686 else if ((op & 0xc0) == 0x80)
7687 {
7688 GET_OP (op2);
7689 if (op == 0x80 && op2 == 0)
7690 printf (_("Refuse to unwind"));
7691 else
7692 {
7693 unsigned int mask = ((op & 0x1f) << 8) | op2;
7694 if (op & 0x20)
7695 printf ("pop compact {");
7696 else
7697 printf ("pop {");
7698
7699 decode_tic6x_unwind_regmask (mask);
7700 printf("}");
7701 }
7702 }
7703 else if ((op & 0xf0) == 0xc0)
7704 {
7705 unsigned int reg;
7706 unsigned int nregs;
7707 unsigned int i;
7708 const char *name;
a734115a
NC
7709 struct
7710 {
fa197c1c
PB
7711 unsigned int offset;
7712 unsigned int reg;
7713 } regpos[16];
7714
7715 /* Scan entire instruction first so that GET_OP output is not
7716 interleaved with disassembly. */
7717 nregs = 0;
7718 for (i = 0; nregs < (op & 0xf); i++)
7719 {
7720 GET_OP (op2);
7721 reg = op2 >> 4;
7722 if (reg != 0xf)
7723 {
7724 regpos[nregs].offset = i * 2;
7725 regpos[nregs].reg = reg;
7726 nregs++;
7727 }
7728
7729 reg = op2 & 0xf;
7730 if (reg != 0xf)
7731 {
7732 regpos[nregs].offset = i * 2 + 1;
7733 regpos[nregs].reg = reg;
7734 nregs++;
7735 }
7736 }
7737
7738 printf (_("pop frame {"));
7739 reg = nregs - 1;
7740 for (i = i * 2; i > 0; i--)
7741 {
7742 if (regpos[reg].offset == i - 1)
7743 {
7744 name = tic6x_unwind_regnames[regpos[reg].reg];
7745 if (reg > 0)
7746 reg--;
7747 }
7748 else
7749 name = _("[pad]");
7750
7751 fputs (name, stdout);
7752 if (i > 1)
7753 printf (", ");
7754 }
7755
7756 printf ("}");
7757 }
7758 else if (op == 0xd0)
7759 printf (" MOV FP, SP");
7760 else if (op == 0xd1)
7761 printf (" __c6xabi_pop_rts");
7762 else if (op == 0xd2)
7763 {
7764 unsigned char buf[9];
7765 unsigned int i, len;
7766 unsigned long offset;
a734115a 7767
fa197c1c
PB
7768 for (i = 0; i < sizeof (buf); i++)
7769 {
7770 GET_OP (buf[i]);
7771 if ((buf[i] & 0x80) == 0)
7772 break;
7773 }
0eff7165
NC
7774 /* PR 17531: file: id:000001,src:001906+004739,op:splice,rep:2. */
7775 if (i == sizeof (buf))
7776 {
7777 printf ("<corrupt sp adjust>\n");
7778 warn (_("Corrupt stack pointer adjustment detected\n"));
7779 return;
7780 }
7781
f6f0e17b 7782 offset = read_uleb128 (buf, &len, buf + i + 1);
fa197c1c
PB
7783 assert (len == i + 1);
7784 offset = offset * 8 + 0x408;
7785 printf (_("sp = sp + %ld"), offset);
7786 }
7787 else if ((op & 0xf0) == 0xe0)
7788 {
7789 if ((op & 0x0f) == 7)
7790 printf (" RETURN");
7791 else
7792 printf (" MV %s, B3", tic6x_unwind_regnames[op & 0x0f]);
7793 }
7794 else
7795 {
7796 printf (_(" [unsupported opcode]"));
7797 }
7798 putchar ('\n');
7799 }
7800}
7801
7802static bfd_vma
a734115a 7803arm_expand_prel31 (bfd_vma word, bfd_vma where)
fa197c1c
PB
7804{
7805 bfd_vma offset;
7806
7807 offset = word & 0x7fffffff;
7808 if (offset & 0x40000000)
7809 offset |= ~ (bfd_vma) 0x7fffffff;
7810
7811 if (elf_header.e_machine == EM_TI_C6000)
7812 offset <<= 1;
7813
7814 return offset + where;
7815}
7816
7817static void
1b31d05e
NC
7818decode_arm_unwind (struct arm_unw_aux_info * aux,
7819 unsigned int word,
7820 unsigned int remaining,
7821 bfd_vma data_offset,
7822 Elf_Internal_Shdr * data_sec,
7823 struct arm_section * data_arm_sec)
fa197c1c
PB
7824{
7825 int per_index;
7826 unsigned int more_words = 0;
37e14bc3 7827 struct absaddr addr;
1b31d05e 7828 bfd_vma sym_name = (bfd_vma) -1;
fa197c1c
PB
7829
7830 if (remaining == 0)
7831 {
1b31d05e
NC
7832 /* Fetch the first word.
7833 Note - when decoding an object file the address extracted
7834 here will always be 0. So we also pass in the sym_name
7835 parameter so that we can find the symbol associated with
7836 the personality routine. */
7837 if (! get_unwind_section_word (aux, data_arm_sec, data_sec, data_offset,
7838 & word, & addr, & sym_name))
fa197c1c 7839 return;
1b31d05e 7840
fa197c1c
PB
7841 remaining = 4;
7842 }
7843
7844 if ((word & 0x80000000) == 0)
7845 {
7846 /* Expand prel31 for personality routine. */
7847 bfd_vma fn;
7848 const char *procname;
7849
a734115a 7850 fn = arm_expand_prel31 (word, data_sec->sh_addr + data_offset);
fa197c1c 7851 printf (_(" Personality routine: "));
1b31d05e
NC
7852 if (fn == 0
7853 && addr.section == SHN_UNDEF && addr.offset == 0
7854 && sym_name != (bfd_vma) -1 && sym_name < aux->strtab_size)
7855 {
7856 procname = aux->strtab + sym_name;
7857 print_vma (fn, PREFIX_HEX);
7858 if (procname)
7859 {
7860 fputs (" <", stdout);
7861 fputs (procname, stdout);
7862 fputc ('>', stdout);
7863 }
7864 }
7865 else
7866 procname = arm_print_vma_and_name (aux, fn, addr);
fa197c1c
PB
7867 fputc ('\n', stdout);
7868
7869 /* The GCC personality routines use the standard compact
7870 encoding, starting with one byte giving the number of
7871 words. */
7872 if (procname != NULL
7873 && (const_strneq (procname, "__gcc_personality_v0")
7874 || const_strneq (procname, "__gxx_personality_v0")
7875 || const_strneq (procname, "__gcj_personality_v0")
7876 || const_strneq (procname, "__gnu_objc_personality_v0")))
7877 {
7878 remaining = 0;
7879 more_words = 1;
7880 ADVANCE;
7881 if (!remaining)
7882 {
7883 printf (_(" [Truncated data]\n"));
7884 return;
7885 }
7886 more_words = word >> 24;
7887 word <<= 8;
7888 remaining--;
7889 per_index = -1;
7890 }
7891 else
7892 return;
7893 }
7894 else
7895 {
1b31d05e 7896 /* ARM EHABI Section 6.3:
0b4362b0 7897
1b31d05e 7898 An exception-handling table entry for the compact model looks like:
0b4362b0 7899
1b31d05e
NC
7900 31 30-28 27-24 23-0
7901 -- ----- ----- ----
7902 1 0 index Data for personalityRoutine[index] */
7903
7904 if (elf_header.e_machine == EM_ARM
7905 && (word & 0x70000000))
83c257ca 7906 warn (_("Corrupt ARM compact model table entry: %x \n"), word);
1b31d05e 7907
fa197c1c 7908 per_index = (word >> 24) & 0x7f;
1b31d05e 7909 printf (_(" Compact model index: %d\n"), per_index);
fa197c1c
PB
7910 if (per_index == 0)
7911 {
7912 more_words = 0;
7913 word <<= 8;
7914 remaining--;
7915 }
7916 else if (per_index < 3)
7917 {
7918 more_words = (word >> 16) & 0xff;
7919 word <<= 16;
7920 remaining -= 2;
7921 }
7922 }
7923
7924 switch (elf_header.e_machine)
7925 {
7926 case EM_ARM:
7927 if (per_index < 3)
7928 {
7929 decode_arm_unwind_bytecode (aux, word, remaining, more_words,
7930 data_offset, data_sec, data_arm_sec);
7931 }
7932 else
1b31d05e
NC
7933 {
7934 warn (_("Unknown ARM compact model index encountered\n"));
7935 printf (_(" [reserved]\n"));
7936 }
fa197c1c
PB
7937 break;
7938
7939 case EM_TI_C6000:
7940 if (per_index < 3)
7941 {
7942 decode_tic6x_unwind_bytecode (aux, word, remaining, more_words,
1b31d05e 7943 data_offset, data_sec, data_arm_sec);
fa197c1c
PB
7944 }
7945 else if (per_index < 5)
7946 {
7947 if (((word >> 17) & 0x7f) == 0x7f)
7948 printf (_(" Restore stack from frame pointer\n"));
7949 else
7950 printf (_(" Stack increment %d\n"), (word >> 14) & 0x1fc);
7951 printf (_(" Registers restored: "));
7952 if (per_index == 4)
7953 printf (" (compact) ");
7954 decode_tic6x_unwind_regmask ((word >> 4) & 0x1fff);
7955 putchar ('\n');
7956 printf (_(" Return register: %s\n"),
7957 tic6x_unwind_regnames[word & 0xf]);
7958 }
7959 else
1b31d05e 7960 printf (_(" [reserved (%d)]\n"), per_index);
fa197c1c
PB
7961 break;
7962
7963 default:
74e1a04b 7964 error (_("Unsupported architecture type %d encountered when decoding unwind table\n"),
1b31d05e 7965 elf_header.e_machine);
fa197c1c 7966 }
0b6ae522
DJ
7967
7968 /* Decode the descriptors. Not implemented. */
7969}
7970
7971static void
7972dump_arm_unwind (struct arm_unw_aux_info *aux, Elf_Internal_Shdr *exidx_sec)
7973{
7974 struct arm_section exidx_arm_sec, extab_arm_sec;
7975 unsigned int i, exidx_len;
7976
7977 memset (&exidx_arm_sec, 0, sizeof (exidx_arm_sec));
7978 memset (&extab_arm_sec, 0, sizeof (extab_arm_sec));
7979 exidx_len = exidx_sec->sh_size / 8;
7980
7981 for (i = 0; i < exidx_len; i++)
7982 {
7983 unsigned int exidx_fn, exidx_entry;
7984 struct absaddr fn_addr, entry_addr;
7985 bfd_vma fn;
7986
7987 fputc ('\n', stdout);
7988
1b31d05e
NC
7989 if (! get_unwind_section_word (aux, & exidx_arm_sec, exidx_sec,
7990 8 * i, & exidx_fn, & fn_addr, NULL)
7991 || ! get_unwind_section_word (aux, & exidx_arm_sec, exidx_sec,
7992 8 * i + 4, & exidx_entry, & entry_addr, NULL))
0b6ae522 7993 {
1b31d05e
NC
7994 arm_free_section (& exidx_arm_sec);
7995 arm_free_section (& extab_arm_sec);
0b6ae522
DJ
7996 return;
7997 }
7998
83c257ca
NC
7999 /* ARM EHABI, Section 5:
8000 An index table entry consists of 2 words.
8001 The first word contains a prel31 offset to the start of a function, with bit 31 clear. */
8002 if (exidx_fn & 0x80000000)
8003 warn (_("corrupt index table entry: %x\n"), exidx_fn);
8004
a734115a 8005 fn = arm_expand_prel31 (exidx_fn, exidx_sec->sh_addr + 8 * i);
0b6ae522 8006
a734115a 8007 arm_print_vma_and_name (aux, fn, fn_addr);
0b6ae522
DJ
8008 fputs (": ", stdout);
8009
8010 if (exidx_entry == 1)
8011 {
8012 print_vma (exidx_entry, PREFIX_HEX);
8013 fputs (" [cantunwind]\n", stdout);
8014 }
8015 else if (exidx_entry & 0x80000000)
8016 {
8017 print_vma (exidx_entry, PREFIX_HEX);
8018 fputc ('\n', stdout);
8019 decode_arm_unwind (aux, exidx_entry, 4, 0, NULL, NULL);
8020 }
8021 else
8022 {
8f73510c 8023 bfd_vma table, table_offset = 0;
0b6ae522
DJ
8024 Elf_Internal_Shdr *table_sec;
8025
8026 fputs ("@", stdout);
a734115a 8027 table = arm_expand_prel31 (exidx_entry, exidx_sec->sh_addr + 8 * i + 4);
0b6ae522
DJ
8028 print_vma (table, PREFIX_HEX);
8029 printf ("\n");
8030
8031 /* Locate the matching .ARM.extab. */
8032 if (entry_addr.section != SHN_UNDEF
8033 && entry_addr.section < elf_header.e_shnum)
8034 {
8035 table_sec = section_headers + entry_addr.section;
8036 table_offset = entry_addr.offset;
8037 }
8038 else
8039 {
8040 table_sec = find_section_by_address (table);
8041 if (table_sec != NULL)
8042 table_offset = table - table_sec->sh_addr;
8043 }
8044 if (table_sec == NULL)
8045 {
8046 warn (_("Could not locate .ARM.extab section containing 0x%lx.\n"),
8047 (unsigned long) table);
8048 continue;
8049 }
8050 decode_arm_unwind (aux, 0, 0, table_offset, table_sec,
8051 &extab_arm_sec);
8052 }
8053 }
8054
8055 printf ("\n");
8056
8057 arm_free_section (&exidx_arm_sec);
8058 arm_free_section (&extab_arm_sec);
8059}
8060
fa197c1c 8061/* Used for both ARM and C6X unwinding tables. */
1b31d05e
NC
8062
8063static void
0b6ae522
DJ
8064arm_process_unwind (FILE *file)
8065{
8066 struct arm_unw_aux_info aux;
8067 Elf_Internal_Shdr *unwsec = NULL;
8068 Elf_Internal_Shdr *strsec;
8069 Elf_Internal_Shdr *sec;
8070 unsigned long i;
fa197c1c 8071 unsigned int sec_type;
0b6ae522 8072
fa197c1c
PB
8073 switch (elf_header.e_machine)
8074 {
8075 case EM_ARM:
8076 sec_type = SHT_ARM_EXIDX;
8077 break;
8078
8079 case EM_TI_C6000:
8080 sec_type = SHT_C6000_UNWIND;
8081 break;
8082
0b4362b0 8083 default:
74e1a04b 8084 error (_("Unsupported architecture type %d encountered when processing unwind table\n"),
1b31d05e
NC
8085 elf_header.e_machine);
8086 return;
fa197c1c
PB
8087 }
8088
0b6ae522 8089 if (string_table == NULL)
1b31d05e
NC
8090 return;
8091
8092 memset (& aux, 0, sizeof (aux));
8093 aux.file = file;
0b6ae522
DJ
8094
8095 for (i = 0, sec = section_headers; i < elf_header.e_shnum; ++i, ++sec)
8096 {
8097 if (sec->sh_type == SHT_SYMTAB && sec->sh_link < elf_header.e_shnum)
8098 {
ba5cdace 8099 aux.symtab = GET_ELF_SYMBOLS (file, sec, & aux.nsyms);
0b6ae522
DJ
8100
8101 strsec = section_headers + sec->sh_link;
74e1a04b
NC
8102
8103 /* PR binutils/17531 file: 011-12666-0.004. */
8104 if (aux.strtab != NULL)
8105 {
4082ef84 8106 error (_("Multiple string tables found in file.\n"));
74e1a04b
NC
8107 free (aux.strtab);
8108 }
0b6ae522
DJ
8109 aux.strtab = get_data (NULL, file, strsec->sh_offset,
8110 1, strsec->sh_size, _("string table"));
8111 aux.strtab_size = aux.strtab != NULL ? strsec->sh_size : 0;
8112 }
fa197c1c 8113 else if (sec->sh_type == sec_type)
0b6ae522
DJ
8114 unwsec = sec;
8115 }
8116
1b31d05e 8117 if (unwsec == NULL)
0b6ae522 8118 printf (_("\nThere are no unwind sections in this file.\n"));
1b31d05e
NC
8119 else
8120 for (i = 0, sec = section_headers; i < elf_header.e_shnum; ++i, ++sec)
8121 {
8122 if (sec->sh_type == sec_type)
8123 {
8124 printf (_("\nUnwind table index '%s' at offset 0x%lx contains %lu entries:\n"),
74e1a04b 8125 printable_section_name (sec),
1b31d05e
NC
8126 (unsigned long) sec->sh_offset,
8127 (unsigned long) (sec->sh_size / (2 * eh_addr_size)));
0b6ae522 8128
1b31d05e
NC
8129 dump_arm_unwind (&aux, sec);
8130 }
8131 }
0b6ae522
DJ
8132
8133 if (aux.symtab)
8134 free (aux.symtab);
8135 if (aux.strtab)
8136 free ((char *) aux.strtab);
0b6ae522
DJ
8137}
8138
1b31d05e 8139static void
2cf0635d 8140process_unwind (FILE * file)
57346661 8141{
2cf0635d
NC
8142 struct unwind_handler
8143 {
57346661 8144 int machtype;
1b31d05e 8145 void (* handler)(FILE *);
2cf0635d
NC
8146 } handlers[] =
8147 {
0b6ae522 8148 { EM_ARM, arm_process_unwind },
57346661
AM
8149 { EM_IA_64, ia64_process_unwind },
8150 { EM_PARISC, hppa_process_unwind },
fa197c1c 8151 { EM_TI_C6000, arm_process_unwind },
57346661
AM
8152 { 0, 0 }
8153 };
8154 int i;
8155
8156 if (!do_unwind)
1b31d05e 8157 return;
57346661
AM
8158
8159 for (i = 0; handlers[i].handler != NULL; i++)
8160 if (elf_header.e_machine == handlers[i].machtype)
9f758fdc
NC
8161 {
8162 handlers[i].handler (file);
8163 return;
8164 }
57346661 8165
1b31d05e
NC
8166 printf (_("\nThe decoding of unwind sections for machine type %s is not currently supported.\n"),
8167 get_machine_name (elf_header.e_machine));
57346661
AM
8168}
8169
252b5132 8170static void
2cf0635d 8171dynamic_section_mips_val (Elf_Internal_Dyn * entry)
252b5132
RH
8172{
8173 switch (entry->d_tag)
8174 {
8175 case DT_MIPS_FLAGS:
8176 if (entry->d_un.d_val == 0)
4b68bca3 8177 printf (_("NONE"));
252b5132
RH
8178 else
8179 {
8180 static const char * opts[] =
8181 {
8182 "QUICKSTART", "NOTPOT", "NO_LIBRARY_REPLACEMENT",
8183 "NO_MOVE", "SGI_ONLY", "GUARANTEE_INIT", "DELTA_C_PLUS_PLUS",
8184 "GUARANTEE_START_INIT", "PIXIE", "DEFAULT_DELAY_LOAD",
8185 "REQUICKSTART", "REQUICKSTARTED", "CORD", "NO_UNRES_UNDEF",
8186 "RLD_ORDER_SAFE"
8187 };
8188 unsigned int cnt;
8189 int first = 1;
2b692964 8190
60bca95a 8191 for (cnt = 0; cnt < ARRAY_SIZE (opts); ++cnt)
252b5132
RH
8192 if (entry->d_un.d_val & (1 << cnt))
8193 {
8194 printf ("%s%s", first ? "" : " ", opts[cnt]);
8195 first = 0;
8196 }
252b5132
RH
8197 }
8198 break;
103f02d3 8199
252b5132 8200 case DT_MIPS_IVERSION:
d79b3d50 8201 if (VALID_DYNAMIC_NAME (entry->d_un.d_val))
4b68bca3 8202 printf (_("Interface Version: %s"), GET_DYNAMIC_NAME (entry->d_un.d_val));
252b5132 8203 else
76ca31c0
NC
8204 {
8205 char buf[40];
8206 sprintf_vma (buf, entry->d_un.d_ptr);
8207 /* Note: coded this way so that there is a single string for translation. */
8208 printf (_("<corrupt: %s>"), buf);
8209 }
252b5132 8210 break;
103f02d3 8211
252b5132
RH
8212 case DT_MIPS_TIME_STAMP:
8213 {
8214 char timebuf[20];
2cf0635d 8215 struct tm * tmp;
50da7a9c 8216
91d6fa6a
NC
8217 time_t atime = entry->d_un.d_val;
8218 tmp = gmtime (&atime);
e9e44622
JJ
8219 snprintf (timebuf, sizeof (timebuf), "%04u-%02u-%02uT%02u:%02u:%02u",
8220 tmp->tm_year + 1900, tmp->tm_mon + 1, tmp->tm_mday,
8221 tmp->tm_hour, tmp->tm_min, tmp->tm_sec);
4b68bca3 8222 printf (_("Time Stamp: %s"), timebuf);
252b5132
RH
8223 }
8224 break;
103f02d3 8225
252b5132
RH
8226 case DT_MIPS_RLD_VERSION:
8227 case DT_MIPS_LOCAL_GOTNO:
8228 case DT_MIPS_CONFLICTNO:
8229 case DT_MIPS_LIBLISTNO:
8230 case DT_MIPS_SYMTABNO:
8231 case DT_MIPS_UNREFEXTNO:
8232 case DT_MIPS_HIPAGENO:
8233 case DT_MIPS_DELTA_CLASS_NO:
8234 case DT_MIPS_DELTA_INSTANCE_NO:
8235 case DT_MIPS_DELTA_RELOC_NO:
8236 case DT_MIPS_DELTA_SYM_NO:
8237 case DT_MIPS_DELTA_CLASSSYM_NO:
8238 case DT_MIPS_COMPACT_SIZE:
4b68bca3 8239 print_vma (entry->d_un.d_ptr, DEC);
252b5132 8240 break;
103f02d3
UD
8241
8242 default:
4b68bca3 8243 print_vma (entry->d_un.d_ptr, PREFIX_HEX);
103f02d3 8244 }
4b68bca3 8245 putchar ('\n');
103f02d3
UD
8246}
8247
103f02d3 8248static void
2cf0635d 8249dynamic_section_parisc_val (Elf_Internal_Dyn * entry)
103f02d3
UD
8250{
8251 switch (entry->d_tag)
8252 {
8253 case DT_HP_DLD_FLAGS:
8254 {
8255 static struct
8256 {
8257 long int bit;
2cf0635d 8258 const char * str;
5e220199
NC
8259 }
8260 flags[] =
8261 {
8262 { DT_HP_DEBUG_PRIVATE, "HP_DEBUG_PRIVATE" },
8263 { DT_HP_DEBUG_CALLBACK, "HP_DEBUG_CALLBACK" },
8264 { DT_HP_DEBUG_CALLBACK_BOR, "HP_DEBUG_CALLBACK_BOR" },
8265 { DT_HP_NO_ENVVAR, "HP_NO_ENVVAR" },
8266 { DT_HP_BIND_NOW, "HP_BIND_NOW" },
8267 { DT_HP_BIND_NONFATAL, "HP_BIND_NONFATAL" },
8268 { DT_HP_BIND_VERBOSE, "HP_BIND_VERBOSE" },
8269 { DT_HP_BIND_RESTRICTED, "HP_BIND_RESTRICTED" },
8270 { DT_HP_BIND_SYMBOLIC, "HP_BIND_SYMBOLIC" },
8271 { DT_HP_RPATH_FIRST, "HP_RPATH_FIRST" },
eec8f817
DA
8272 { DT_HP_BIND_DEPTH_FIRST, "HP_BIND_DEPTH_FIRST" },
8273 { DT_HP_GST, "HP_GST" },
8274 { DT_HP_SHLIB_FIXED, "HP_SHLIB_FIXED" },
8275 { DT_HP_MERGE_SHLIB_SEG, "HP_MERGE_SHLIB_SEG" },
8276 { DT_HP_NODELETE, "HP_NODELETE" },
8277 { DT_HP_GROUP, "HP_GROUP" },
8278 { DT_HP_PROTECT_LINKAGE_TABLE, "HP_PROTECT_LINKAGE_TABLE" }
5e220199 8279 };
103f02d3 8280 int first = 1;
5e220199 8281 size_t cnt;
f7a99963 8282 bfd_vma val = entry->d_un.d_val;
103f02d3 8283
60bca95a 8284 for (cnt = 0; cnt < ARRAY_SIZE (flags); ++cnt)
103f02d3 8285 if (val & flags[cnt].bit)
30800947
NC
8286 {
8287 if (! first)
8288 putchar (' ');
8289 fputs (flags[cnt].str, stdout);
8290 first = 0;
8291 val ^= flags[cnt].bit;
8292 }
76da6bbe 8293
103f02d3 8294 if (val != 0 || first)
f7a99963
NC
8295 {
8296 if (! first)
8297 putchar (' ');
8298 print_vma (val, HEX);
8299 }
103f02d3
UD
8300 }
8301 break;
76da6bbe 8302
252b5132 8303 default:
f7a99963
NC
8304 print_vma (entry->d_un.d_ptr, PREFIX_HEX);
8305 break;
252b5132 8306 }
35b1837e 8307 putchar ('\n');
252b5132
RH
8308}
8309
28f997cf
TG
8310#ifdef BFD64
8311
8312/* VMS vs Unix time offset and factor. */
8313
8314#define VMS_EPOCH_OFFSET 35067168000000000LL
8315#define VMS_GRANULARITY_FACTOR 10000000
8316
8317/* Display a VMS time in a human readable format. */
8318
8319static void
8320print_vms_time (bfd_int64_t vmstime)
8321{
8322 struct tm *tm;
8323 time_t unxtime;
8324
8325 unxtime = (vmstime - VMS_EPOCH_OFFSET) / VMS_GRANULARITY_FACTOR;
8326 tm = gmtime (&unxtime);
8327 printf ("%04u-%02u-%02uT%02u:%02u:%02u",
8328 tm->tm_year + 1900, tm->tm_mon + 1, tm->tm_mday,
8329 tm->tm_hour, tm->tm_min, tm->tm_sec);
8330}
8331#endif /* BFD64 */
8332
ecc51f48 8333static void
2cf0635d 8334dynamic_section_ia64_val (Elf_Internal_Dyn * entry)
ecc51f48
NC
8335{
8336 switch (entry->d_tag)
8337 {
0de14b54 8338 case DT_IA_64_PLT_RESERVE:
bdf4d63a 8339 /* First 3 slots reserved. */
ecc51f48
NC
8340 print_vma (entry->d_un.d_ptr, PREFIX_HEX);
8341 printf (" -- ");
8342 print_vma (entry->d_un.d_ptr + (3 * 8), PREFIX_HEX);
bdf4d63a
JJ
8343 break;
8344
28f997cf
TG
8345 case DT_IA_64_VMS_LINKTIME:
8346#ifdef BFD64
8347 print_vms_time (entry->d_un.d_val);
8348#endif
8349 break;
8350
8351 case DT_IA_64_VMS_LNKFLAGS:
8352 print_vma (entry->d_un.d_ptr, PREFIX_HEX);
8353 if (entry->d_un.d_val & VMS_LF_CALL_DEBUG)
8354 printf (" CALL_DEBUG");
8355 if (entry->d_un.d_val & VMS_LF_NOP0BUFS)
8356 printf (" NOP0BUFS");
8357 if (entry->d_un.d_val & VMS_LF_P0IMAGE)
8358 printf (" P0IMAGE");
8359 if (entry->d_un.d_val & VMS_LF_MKTHREADS)
8360 printf (" MKTHREADS");
8361 if (entry->d_un.d_val & VMS_LF_UPCALLS)
8362 printf (" UPCALLS");
8363 if (entry->d_un.d_val & VMS_LF_IMGSTA)
8364 printf (" IMGSTA");
8365 if (entry->d_un.d_val & VMS_LF_INITIALIZE)
8366 printf (" INITIALIZE");
8367 if (entry->d_un.d_val & VMS_LF_MAIN)
8368 printf (" MAIN");
8369 if (entry->d_un.d_val & VMS_LF_EXE_INIT)
8370 printf (" EXE_INIT");
8371 if (entry->d_un.d_val & VMS_LF_TBK_IN_IMG)
8372 printf (" TBK_IN_IMG");
8373 if (entry->d_un.d_val & VMS_LF_DBG_IN_IMG)
8374 printf (" DBG_IN_IMG");
8375 if (entry->d_un.d_val & VMS_LF_TBK_IN_DSF)
8376 printf (" TBK_IN_DSF");
8377 if (entry->d_un.d_val & VMS_LF_DBG_IN_DSF)
8378 printf (" DBG_IN_DSF");
8379 if (entry->d_un.d_val & VMS_LF_SIGNATURES)
8380 printf (" SIGNATURES");
8381 if (entry->d_un.d_val & VMS_LF_REL_SEG_OFF)
8382 printf (" REL_SEG_OFF");
8383 break;
8384
bdf4d63a
JJ
8385 default:
8386 print_vma (entry->d_un.d_ptr, PREFIX_HEX);
8387 break;
ecc51f48 8388 }
bdf4d63a 8389 putchar ('\n');
ecc51f48
NC
8390}
8391
252b5132 8392static int
2cf0635d 8393get_32bit_dynamic_section (FILE * file)
252b5132 8394{
2cf0635d
NC
8395 Elf32_External_Dyn * edyn;
8396 Elf32_External_Dyn * ext;
8397 Elf_Internal_Dyn * entry;
103f02d3 8398
3f5e193b
NC
8399 edyn = (Elf32_External_Dyn *) get_data (NULL, file, dynamic_addr, 1,
8400 dynamic_size, _("dynamic section"));
a6e9f9df
AM
8401 if (!edyn)
8402 return 0;
103f02d3 8403
071436c6
NC
8404 /* SGI's ELF has more than one section in the DYNAMIC segment, and we
8405 might not have the luxury of section headers. Look for the DT_NULL
8406 terminator to determine the number of entries. */
ba2685cc 8407 for (ext = edyn, dynamic_nent = 0;
071436c6 8408 (char *) ext < (char *) edyn + dynamic_size - sizeof (* entry);
ba2685cc
AM
8409 ext++)
8410 {
8411 dynamic_nent++;
8412 if (BYTE_GET (ext->d_tag) == DT_NULL)
8413 break;
8414 }
252b5132 8415
3f5e193b
NC
8416 dynamic_section = (Elf_Internal_Dyn *) cmalloc (dynamic_nent,
8417 sizeof (* entry));
b2d38a17 8418 if (dynamic_section == NULL)
252b5132 8419 {
8b73c356
NC
8420 error (_("Out of memory allocating space for %lu dynamic entries\n"),
8421 (unsigned long) dynamic_nent);
9ea033b2
NC
8422 free (edyn);
8423 return 0;
8424 }
252b5132 8425
fb514b26 8426 for (ext = edyn, entry = dynamic_section;
ba2685cc 8427 entry < dynamic_section + dynamic_nent;
fb514b26 8428 ext++, entry++)
9ea033b2 8429 {
fb514b26
AM
8430 entry->d_tag = BYTE_GET (ext->d_tag);
8431 entry->d_un.d_val = BYTE_GET (ext->d_un.d_val);
252b5132
RH
8432 }
8433
9ea033b2
NC
8434 free (edyn);
8435
8436 return 1;
8437}
8438
8439static int
2cf0635d 8440get_64bit_dynamic_section (FILE * file)
9ea033b2 8441{
2cf0635d
NC
8442 Elf64_External_Dyn * edyn;
8443 Elf64_External_Dyn * ext;
8444 Elf_Internal_Dyn * entry;
103f02d3 8445
071436c6 8446 /* Read in the data. */
3f5e193b
NC
8447 edyn = (Elf64_External_Dyn *) get_data (NULL, file, dynamic_addr, 1,
8448 dynamic_size, _("dynamic section"));
a6e9f9df
AM
8449 if (!edyn)
8450 return 0;
103f02d3 8451
071436c6
NC
8452 /* SGI's ELF has more than one section in the DYNAMIC segment, and we
8453 might not have the luxury of section headers. Look for the DT_NULL
8454 terminator to determine the number of entries. */
ba2685cc 8455 for (ext = edyn, dynamic_nent = 0;
071436c6
NC
8456 /* PR 17533 file: 033-67080-0.004 - do not read off the end of the buffer. */
8457 (char *) ext < ((char *) edyn) + dynamic_size - sizeof (* ext);
ba2685cc
AM
8458 ext++)
8459 {
8460 dynamic_nent++;
66543521 8461 if (BYTE_GET (ext->d_tag) == DT_NULL)
ba2685cc
AM
8462 break;
8463 }
252b5132 8464
3f5e193b
NC
8465 dynamic_section = (Elf_Internal_Dyn *) cmalloc (dynamic_nent,
8466 sizeof (* entry));
b2d38a17 8467 if (dynamic_section == NULL)
252b5132 8468 {
8b73c356
NC
8469 error (_("Out of memory allocating space for %lu dynamic entries\n"),
8470 (unsigned long) dynamic_nent);
252b5132
RH
8471 free (edyn);
8472 return 0;
8473 }
8474
071436c6 8475 /* Convert from external to internal formats. */
fb514b26 8476 for (ext = edyn, entry = dynamic_section;
ba2685cc 8477 entry < dynamic_section + dynamic_nent;
fb514b26 8478 ext++, entry++)
252b5132 8479 {
66543521
AM
8480 entry->d_tag = BYTE_GET (ext->d_tag);
8481 entry->d_un.d_val = BYTE_GET (ext->d_un.d_val);
252b5132
RH
8482 }
8483
8484 free (edyn);
8485
9ea033b2
NC
8486 return 1;
8487}
8488
e9e44622
JJ
8489static void
8490print_dynamic_flags (bfd_vma flags)
d1133906 8491{
e9e44622 8492 int first = 1;
13ae64f3 8493
d1133906
NC
8494 while (flags)
8495 {
8496 bfd_vma flag;
8497
8498 flag = flags & - flags;
8499 flags &= ~ flag;
8500
e9e44622
JJ
8501 if (first)
8502 first = 0;
8503 else
8504 putc (' ', stdout);
13ae64f3 8505
d1133906
NC
8506 switch (flag)
8507 {
e9e44622
JJ
8508 case DF_ORIGIN: fputs ("ORIGIN", stdout); break;
8509 case DF_SYMBOLIC: fputs ("SYMBOLIC", stdout); break;
8510 case DF_TEXTREL: fputs ("TEXTREL", stdout); break;
8511 case DF_BIND_NOW: fputs ("BIND_NOW", stdout); break;
8512 case DF_STATIC_TLS: fputs ("STATIC_TLS", stdout); break;
2b692964 8513 default: fputs (_("unknown"), stdout); break;
d1133906
NC
8514 }
8515 }
e9e44622 8516 puts ("");
d1133906
NC
8517}
8518
b2d38a17
NC
8519/* Parse and display the contents of the dynamic section. */
8520
9ea033b2 8521static int
2cf0635d 8522process_dynamic_section (FILE * file)
9ea033b2 8523{
2cf0635d 8524 Elf_Internal_Dyn * entry;
9ea033b2
NC
8525
8526 if (dynamic_size == 0)
8527 {
8528 if (do_dynamic)
b2d38a17 8529 printf (_("\nThere is no dynamic section in this file.\n"));
9ea033b2
NC
8530
8531 return 1;
8532 }
8533
8534 if (is_32bit_elf)
8535 {
b2d38a17 8536 if (! get_32bit_dynamic_section (file))
9ea033b2
NC
8537 return 0;
8538 }
b2d38a17 8539 else if (! get_64bit_dynamic_section (file))
9ea033b2
NC
8540 return 0;
8541
252b5132
RH
8542 /* Find the appropriate symbol table. */
8543 if (dynamic_symbols == NULL)
8544 {
86dba8ee
AM
8545 for (entry = dynamic_section;
8546 entry < dynamic_section + dynamic_nent;
8547 ++entry)
252b5132 8548 {
c8286bd1 8549 Elf_Internal_Shdr section;
252b5132
RH
8550
8551 if (entry->d_tag != DT_SYMTAB)
8552 continue;
8553
8554 dynamic_info[DT_SYMTAB] = entry->d_un.d_val;
8555
8556 /* Since we do not know how big the symbol table is,
8557 we default to reading in the entire file (!) and
8558 processing that. This is overkill, I know, but it
e3c8793a 8559 should work. */
d93f0186 8560 section.sh_offset = offset_from_vma (file, entry->d_un.d_val, 0);
252b5132 8561
fb52b2f4
NC
8562 if (archive_file_offset != 0)
8563 section.sh_size = archive_file_size - section.sh_offset;
8564 else
8565 {
8566 if (fseek (file, 0, SEEK_END))
591a748a 8567 error (_("Unable to seek to end of file!\n"));
fb52b2f4
NC
8568
8569 section.sh_size = ftell (file) - section.sh_offset;
8570 }
252b5132 8571
9ea033b2 8572 if (is_32bit_elf)
9ad5cbcf 8573 section.sh_entsize = sizeof (Elf32_External_Sym);
9ea033b2 8574 else
9ad5cbcf 8575 section.sh_entsize = sizeof (Elf64_External_Sym);
071436c6 8576 section.sh_name = string_table_length;
252b5132 8577
ba5cdace 8578 dynamic_symbols = GET_ELF_SYMBOLS (file, &section, & num_dynamic_syms);
19936277 8579 if (num_dynamic_syms < 1)
252b5132
RH
8580 {
8581 error (_("Unable to determine the number of symbols to load\n"));
8582 continue;
8583 }
252b5132
RH
8584 }
8585 }
8586
8587 /* Similarly find a string table. */
8588 if (dynamic_strings == NULL)
8589 {
86dba8ee
AM
8590 for (entry = dynamic_section;
8591 entry < dynamic_section + dynamic_nent;
8592 ++entry)
252b5132
RH
8593 {
8594 unsigned long offset;
b34976b6 8595 long str_tab_len;
252b5132
RH
8596
8597 if (entry->d_tag != DT_STRTAB)
8598 continue;
8599
8600 dynamic_info[DT_STRTAB] = entry->d_un.d_val;
8601
8602 /* Since we do not know how big the string table is,
8603 we default to reading in the entire file (!) and
8604 processing that. This is overkill, I know, but it
e3c8793a 8605 should work. */
252b5132 8606
d93f0186 8607 offset = offset_from_vma (file, entry->d_un.d_val, 0);
fb52b2f4
NC
8608
8609 if (archive_file_offset != 0)
8610 str_tab_len = archive_file_size - offset;
8611 else
8612 {
8613 if (fseek (file, 0, SEEK_END))
8614 error (_("Unable to seek to end of file\n"));
8615 str_tab_len = ftell (file) - offset;
8616 }
252b5132
RH
8617
8618 if (str_tab_len < 1)
8619 {
8620 error
8621 (_("Unable to determine the length of the dynamic string table\n"));
8622 continue;
8623 }
8624
3f5e193b
NC
8625 dynamic_strings = (char *) get_data (NULL, file, offset, 1,
8626 str_tab_len,
8627 _("dynamic string table"));
59245841 8628 dynamic_strings_length = dynamic_strings == NULL ? 0 : str_tab_len;
252b5132
RH
8629 break;
8630 }
8631 }
8632
8633 /* And find the syminfo section if available. */
8634 if (dynamic_syminfo == NULL)
8635 {
3e8bba36 8636 unsigned long syminsz = 0;
252b5132 8637
86dba8ee
AM
8638 for (entry = dynamic_section;
8639 entry < dynamic_section + dynamic_nent;
8640 ++entry)
252b5132
RH
8641 {
8642 if (entry->d_tag == DT_SYMINENT)
8643 {
8644 /* Note: these braces are necessary to avoid a syntax
8645 error from the SunOS4 C compiler. */
049b0c3a
NC
8646 /* PR binutils/17531: A corrupt file can trigger this test.
8647 So do not use an assert, instead generate an error message. */
8648 if (sizeof (Elf_External_Syminfo) != entry->d_un.d_val)
071436c6 8649 error (_("Bad value (%d) for SYMINENT entry\n"),
049b0c3a 8650 (int) entry->d_un.d_val);
252b5132
RH
8651 }
8652 else if (entry->d_tag == DT_SYMINSZ)
8653 syminsz = entry->d_un.d_val;
8654 else if (entry->d_tag == DT_SYMINFO)
d93f0186
NC
8655 dynamic_syminfo_offset = offset_from_vma (file, entry->d_un.d_val,
8656 syminsz);
252b5132
RH
8657 }
8658
8659 if (dynamic_syminfo_offset != 0 && syminsz != 0)
8660 {
2cf0635d
NC
8661 Elf_External_Syminfo * extsyminfo;
8662 Elf_External_Syminfo * extsym;
8663 Elf_Internal_Syminfo * syminfo;
252b5132
RH
8664
8665 /* There is a syminfo section. Read the data. */
3f5e193b
NC
8666 extsyminfo = (Elf_External_Syminfo *)
8667 get_data (NULL, file, dynamic_syminfo_offset, 1, syminsz,
8668 _("symbol information"));
a6e9f9df
AM
8669 if (!extsyminfo)
8670 return 0;
252b5132 8671
3f5e193b 8672 dynamic_syminfo = (Elf_Internal_Syminfo *) malloc (syminsz);
252b5132
RH
8673 if (dynamic_syminfo == NULL)
8674 {
8b73c356
NC
8675 error (_("Out of memory allocating %lu byte for dynamic symbol info\n"),
8676 (unsigned long) syminsz);
252b5132
RH
8677 return 0;
8678 }
8679
8680 dynamic_syminfo_nent = syminsz / sizeof (Elf_External_Syminfo);
86dba8ee
AM
8681 for (syminfo = dynamic_syminfo, extsym = extsyminfo;
8682 syminfo < dynamic_syminfo + dynamic_syminfo_nent;
8683 ++syminfo, ++extsym)
252b5132 8684 {
86dba8ee
AM
8685 syminfo->si_boundto = BYTE_GET (extsym->si_boundto);
8686 syminfo->si_flags = BYTE_GET (extsym->si_flags);
252b5132
RH
8687 }
8688
8689 free (extsyminfo);
8690 }
8691 }
8692
8693 if (do_dynamic && dynamic_addr)
8b73c356
NC
8694 printf (_("\nDynamic section at offset 0x%lx contains %lu entries:\n"),
8695 dynamic_addr, (unsigned long) dynamic_nent);
252b5132
RH
8696 if (do_dynamic)
8697 printf (_(" Tag Type Name/Value\n"));
8698
86dba8ee
AM
8699 for (entry = dynamic_section;
8700 entry < dynamic_section + dynamic_nent;
8701 entry++)
252b5132
RH
8702 {
8703 if (do_dynamic)
f7a99963 8704 {
2cf0635d 8705 const char * dtype;
e699b9ff 8706
f7a99963
NC
8707 putchar (' ');
8708 print_vma (entry->d_tag, FULL_HEX);
e699b9ff
ILT
8709 dtype = get_dynamic_type (entry->d_tag);
8710 printf (" (%s)%*s", dtype,
8711 ((is_32bit_elf ? 27 : 19)
8712 - (int) strlen (dtype)),
f7a99963
NC
8713 " ");
8714 }
252b5132
RH
8715
8716 switch (entry->d_tag)
8717 {
d1133906
NC
8718 case DT_FLAGS:
8719 if (do_dynamic)
e9e44622 8720 print_dynamic_flags (entry->d_un.d_val);
d1133906 8721 break;
76da6bbe 8722
252b5132
RH
8723 case DT_AUXILIARY:
8724 case DT_FILTER:
019148e4
L
8725 case DT_CONFIG:
8726 case DT_DEPAUDIT:
8727 case DT_AUDIT:
252b5132
RH
8728 if (do_dynamic)
8729 {
019148e4 8730 switch (entry->d_tag)
b34976b6 8731 {
019148e4
L
8732 case DT_AUXILIARY:
8733 printf (_("Auxiliary library"));
8734 break;
8735
8736 case DT_FILTER:
8737 printf (_("Filter library"));
8738 break;
8739
b34976b6 8740 case DT_CONFIG:
019148e4
L
8741 printf (_("Configuration file"));
8742 break;
8743
8744 case DT_DEPAUDIT:
8745 printf (_("Dependency audit library"));
8746 break;
8747
8748 case DT_AUDIT:
8749 printf (_("Audit library"));
8750 break;
8751 }
252b5132 8752
d79b3d50
NC
8753 if (VALID_DYNAMIC_NAME (entry->d_un.d_val))
8754 printf (": [%s]\n", GET_DYNAMIC_NAME (entry->d_un.d_val));
252b5132 8755 else
f7a99963
NC
8756 {
8757 printf (": ");
8758 print_vma (entry->d_un.d_val, PREFIX_HEX);
8759 putchar ('\n');
8760 }
252b5132
RH
8761 }
8762 break;
8763
dcefbbbd 8764 case DT_FEATURE:
252b5132
RH
8765 if (do_dynamic)
8766 {
8767 printf (_("Flags:"));
86f55779 8768
252b5132
RH
8769 if (entry->d_un.d_val == 0)
8770 printf (_(" None\n"));
8771 else
8772 {
8773 unsigned long int val = entry->d_un.d_val;
86f55779 8774
252b5132
RH
8775 if (val & DTF_1_PARINIT)
8776 {
8777 printf (" PARINIT");
8778 val ^= DTF_1_PARINIT;
8779 }
dcefbbbd
L
8780 if (val & DTF_1_CONFEXP)
8781 {
8782 printf (" CONFEXP");
8783 val ^= DTF_1_CONFEXP;
8784 }
252b5132
RH
8785 if (val != 0)
8786 printf (" %lx", val);
8787 puts ("");
8788 }
8789 }
8790 break;
8791
8792 case DT_POSFLAG_1:
8793 if (do_dynamic)
8794 {
8795 printf (_("Flags:"));
86f55779 8796
252b5132
RH
8797 if (entry->d_un.d_val == 0)
8798 printf (_(" None\n"));
8799 else
8800 {
8801 unsigned long int val = entry->d_un.d_val;
86f55779 8802
252b5132
RH
8803 if (val & DF_P1_LAZYLOAD)
8804 {
8805 printf (" LAZYLOAD");
8806 val ^= DF_P1_LAZYLOAD;
8807 }
8808 if (val & DF_P1_GROUPPERM)
8809 {
8810 printf (" GROUPPERM");
8811 val ^= DF_P1_GROUPPERM;
8812 }
8813 if (val != 0)
8814 printf (" %lx", val);
8815 puts ("");
8816 }
8817 }
8818 break;
8819
8820 case DT_FLAGS_1:
8821 if (do_dynamic)
8822 {
8823 printf (_("Flags:"));
8824 if (entry->d_un.d_val == 0)
8825 printf (_(" None\n"));
8826 else
8827 {
8828 unsigned long int val = entry->d_un.d_val;
86f55779 8829
252b5132
RH
8830 if (val & DF_1_NOW)
8831 {
8832 printf (" NOW");
8833 val ^= DF_1_NOW;
8834 }
8835 if (val & DF_1_GLOBAL)
8836 {
8837 printf (" GLOBAL");
8838 val ^= DF_1_GLOBAL;
8839 }
8840 if (val & DF_1_GROUP)
8841 {
8842 printf (" GROUP");
8843 val ^= DF_1_GROUP;
8844 }
8845 if (val & DF_1_NODELETE)
8846 {
8847 printf (" NODELETE");
8848 val ^= DF_1_NODELETE;
8849 }
8850 if (val & DF_1_LOADFLTR)
8851 {
8852 printf (" LOADFLTR");
8853 val ^= DF_1_LOADFLTR;
8854 }
8855 if (val & DF_1_INITFIRST)
8856 {
8857 printf (" INITFIRST");
8858 val ^= DF_1_INITFIRST;
8859 }
8860 if (val & DF_1_NOOPEN)
8861 {
8862 printf (" NOOPEN");
8863 val ^= DF_1_NOOPEN;
8864 }
8865 if (val & DF_1_ORIGIN)
8866 {
8867 printf (" ORIGIN");
8868 val ^= DF_1_ORIGIN;
8869 }
8870 if (val & DF_1_DIRECT)
8871 {
8872 printf (" DIRECT");
8873 val ^= DF_1_DIRECT;
8874 }
8875 if (val & DF_1_TRANS)
8876 {
8877 printf (" TRANS");
8878 val ^= DF_1_TRANS;
8879 }
8880 if (val & DF_1_INTERPOSE)
8881 {
8882 printf (" INTERPOSE");
8883 val ^= DF_1_INTERPOSE;
8884 }
f7db6139 8885 if (val & DF_1_NODEFLIB)
dcefbbbd 8886 {
f7db6139
L
8887 printf (" NODEFLIB");
8888 val ^= DF_1_NODEFLIB;
dcefbbbd
L
8889 }
8890 if (val & DF_1_NODUMP)
8891 {
8892 printf (" NODUMP");
8893 val ^= DF_1_NODUMP;
8894 }
34b60028 8895 if (val & DF_1_CONFALT)
dcefbbbd 8896 {
34b60028
L
8897 printf (" CONFALT");
8898 val ^= DF_1_CONFALT;
8899 }
8900 if (val & DF_1_ENDFILTEE)
8901 {
8902 printf (" ENDFILTEE");
8903 val ^= DF_1_ENDFILTEE;
8904 }
8905 if (val & DF_1_DISPRELDNE)
8906 {
8907 printf (" DISPRELDNE");
8908 val ^= DF_1_DISPRELDNE;
8909 }
8910 if (val & DF_1_DISPRELPND)
8911 {
8912 printf (" DISPRELPND");
8913 val ^= DF_1_DISPRELPND;
8914 }
8915 if (val & DF_1_NODIRECT)
8916 {
8917 printf (" NODIRECT");
8918 val ^= DF_1_NODIRECT;
8919 }
8920 if (val & DF_1_IGNMULDEF)
8921 {
8922 printf (" IGNMULDEF");
8923 val ^= DF_1_IGNMULDEF;
8924 }
8925 if (val & DF_1_NOKSYMS)
8926 {
8927 printf (" NOKSYMS");
8928 val ^= DF_1_NOKSYMS;
8929 }
8930 if (val & DF_1_NOHDR)
8931 {
8932 printf (" NOHDR");
8933 val ^= DF_1_NOHDR;
8934 }
8935 if (val & DF_1_EDITED)
8936 {
8937 printf (" EDITED");
8938 val ^= DF_1_EDITED;
8939 }
8940 if (val & DF_1_NORELOC)
8941 {
8942 printf (" NORELOC");
8943 val ^= DF_1_NORELOC;
8944 }
8945 if (val & DF_1_SYMINTPOSE)
8946 {
8947 printf (" SYMINTPOSE");
8948 val ^= DF_1_SYMINTPOSE;
8949 }
8950 if (val & DF_1_GLOBAUDIT)
8951 {
8952 printf (" GLOBAUDIT");
8953 val ^= DF_1_GLOBAUDIT;
8954 }
8955 if (val & DF_1_SINGLETON)
8956 {
8957 printf (" SINGLETON");
8958 val ^= DF_1_SINGLETON;
dcefbbbd 8959 }
252b5132
RH
8960 if (val != 0)
8961 printf (" %lx", val);
8962 puts ("");
8963 }
8964 }
8965 break;
8966
8967 case DT_PLTREL:
566b0d53 8968 dynamic_info[entry->d_tag] = entry->d_un.d_val;
252b5132
RH
8969 if (do_dynamic)
8970 puts (get_dynamic_type (entry->d_un.d_val));
8971 break;
8972
8973 case DT_NULL :
8974 case DT_NEEDED :
8975 case DT_PLTGOT :
8976 case DT_HASH :
8977 case DT_STRTAB :
8978 case DT_SYMTAB :
8979 case DT_RELA :
8980 case DT_INIT :
8981 case DT_FINI :
8982 case DT_SONAME :
8983 case DT_RPATH :
8984 case DT_SYMBOLIC:
8985 case DT_REL :
8986 case DT_DEBUG :
8987 case DT_TEXTREL :
8988 case DT_JMPREL :
019148e4 8989 case DT_RUNPATH :
252b5132
RH
8990 dynamic_info[entry->d_tag] = entry->d_un.d_val;
8991
8992 if (do_dynamic)
8993 {
2cf0635d 8994 char * name;
252b5132 8995
d79b3d50
NC
8996 if (VALID_DYNAMIC_NAME (entry->d_un.d_val))
8997 name = GET_DYNAMIC_NAME (entry->d_un.d_val);
252b5132 8998 else
d79b3d50 8999 name = NULL;
252b5132
RH
9000
9001 if (name)
9002 {
9003 switch (entry->d_tag)
9004 {
9005 case DT_NEEDED:
9006 printf (_("Shared library: [%s]"), name);
9007
18bd398b 9008 if (streq (name, program_interpreter))
f7a99963 9009 printf (_(" program interpreter"));
252b5132
RH
9010 break;
9011
9012 case DT_SONAME:
f7a99963 9013 printf (_("Library soname: [%s]"), name);
252b5132
RH
9014 break;
9015
9016 case DT_RPATH:
f7a99963 9017 printf (_("Library rpath: [%s]"), name);
252b5132
RH
9018 break;
9019
019148e4
L
9020 case DT_RUNPATH:
9021 printf (_("Library runpath: [%s]"), name);
9022 break;
9023
252b5132 9024 default:
f7a99963
NC
9025 print_vma (entry->d_un.d_val, PREFIX_HEX);
9026 break;
252b5132
RH
9027 }
9028 }
9029 else
f7a99963
NC
9030 print_vma (entry->d_un.d_val, PREFIX_HEX);
9031
9032 putchar ('\n');
252b5132
RH
9033 }
9034 break;
9035
9036 case DT_PLTRELSZ:
9037 case DT_RELASZ :
9038 case DT_STRSZ :
9039 case DT_RELSZ :
9040 case DT_RELAENT :
9041 case DT_SYMENT :
9042 case DT_RELENT :
566b0d53 9043 dynamic_info[entry->d_tag] = entry->d_un.d_val;
252b5132
RH
9044 case DT_PLTPADSZ:
9045 case DT_MOVEENT :
9046 case DT_MOVESZ :
9047 case DT_INIT_ARRAYSZ:
9048 case DT_FINI_ARRAYSZ:
047b2264
JJ
9049 case DT_GNU_CONFLICTSZ:
9050 case DT_GNU_LIBLISTSZ:
252b5132 9051 if (do_dynamic)
f7a99963
NC
9052 {
9053 print_vma (entry->d_un.d_val, UNSIGNED);
2b692964 9054 printf (_(" (bytes)\n"));
f7a99963 9055 }
252b5132
RH
9056 break;
9057
9058 case DT_VERDEFNUM:
9059 case DT_VERNEEDNUM:
9060 case DT_RELACOUNT:
9061 case DT_RELCOUNT:
9062 if (do_dynamic)
f7a99963
NC
9063 {
9064 print_vma (entry->d_un.d_val, UNSIGNED);
9065 putchar ('\n');
9066 }
252b5132
RH
9067 break;
9068
9069 case DT_SYMINSZ:
9070 case DT_SYMINENT:
9071 case DT_SYMINFO:
9072 case DT_USED:
9073 case DT_INIT_ARRAY:
9074 case DT_FINI_ARRAY:
9075 if (do_dynamic)
9076 {
d79b3d50
NC
9077 if (entry->d_tag == DT_USED
9078 && VALID_DYNAMIC_NAME (entry->d_un.d_val))
252b5132 9079 {
2cf0635d 9080 char * name = GET_DYNAMIC_NAME (entry->d_un.d_val);
252b5132 9081
b34976b6 9082 if (*name)
252b5132
RH
9083 {
9084 printf (_("Not needed object: [%s]\n"), name);
9085 break;
9086 }
9087 }
103f02d3 9088
f7a99963
NC
9089 print_vma (entry->d_un.d_val, PREFIX_HEX);
9090 putchar ('\n');
252b5132
RH
9091 }
9092 break;
9093
9094 case DT_BIND_NOW:
9095 /* The value of this entry is ignored. */
35b1837e
AM
9096 if (do_dynamic)
9097 putchar ('\n');
252b5132 9098 break;
103f02d3 9099
047b2264
JJ
9100 case DT_GNU_PRELINKED:
9101 if (do_dynamic)
9102 {
2cf0635d 9103 struct tm * tmp;
91d6fa6a 9104 time_t atime = entry->d_un.d_val;
047b2264 9105
91d6fa6a 9106 tmp = gmtime (&atime);
071436c6
NC
9107 /* PR 17533 file: 041-1244816-0.004. */
9108 if (tmp == NULL)
5a2cbcf4
L
9109 printf (_("<corrupt time val: %lx"),
9110 (unsigned long) atime);
071436c6
NC
9111 else
9112 printf ("%04u-%02u-%02uT%02u:%02u:%02u\n",
9113 tmp->tm_year + 1900, tmp->tm_mon + 1, tmp->tm_mday,
9114 tmp->tm_hour, tmp->tm_min, tmp->tm_sec);
047b2264
JJ
9115
9116 }
9117 break;
9118
fdc90cb4
JJ
9119 case DT_GNU_HASH:
9120 dynamic_info_DT_GNU_HASH = entry->d_un.d_val;
9121 if (do_dynamic)
9122 {
9123 print_vma (entry->d_un.d_val, PREFIX_HEX);
9124 putchar ('\n');
9125 }
9126 break;
9127
252b5132
RH
9128 default:
9129 if ((entry->d_tag >= DT_VERSYM) && (entry->d_tag <= DT_VERNEEDNUM))
b34976b6 9130 version_info[DT_VERSIONTAGIDX (entry->d_tag)] =
252b5132
RH
9131 entry->d_un.d_val;
9132
9133 if (do_dynamic)
9134 {
9135 switch (elf_header.e_machine)
9136 {
9137 case EM_MIPS:
4fe85591 9138 case EM_MIPS_RS3_LE:
b2d38a17 9139 dynamic_section_mips_val (entry);
252b5132 9140 break;
103f02d3 9141 case EM_PARISC:
b2d38a17 9142 dynamic_section_parisc_val (entry);
103f02d3 9143 break;
ecc51f48 9144 case EM_IA_64:
b2d38a17 9145 dynamic_section_ia64_val (entry);
ecc51f48 9146 break;
252b5132 9147 default:
f7a99963
NC
9148 print_vma (entry->d_un.d_val, PREFIX_HEX);
9149 putchar ('\n');
252b5132
RH
9150 }
9151 }
9152 break;
9153 }
9154 }
9155
9156 return 1;
9157}
9158
9159static char *
d3ba0551 9160get_ver_flags (unsigned int flags)
252b5132 9161{
b34976b6 9162 static char buff[32];
252b5132
RH
9163
9164 buff[0] = 0;
9165
9166 if (flags == 0)
9167 return _("none");
9168
9169 if (flags & VER_FLG_BASE)
9170 strcat (buff, "BASE ");
9171
9172 if (flags & VER_FLG_WEAK)
9173 {
9174 if (flags & VER_FLG_BASE)
9175 strcat (buff, "| ");
9176
9177 strcat (buff, "WEAK ");
9178 }
9179
44ec90b9
RO
9180 if (flags & VER_FLG_INFO)
9181 {
9182 if (flags & (VER_FLG_BASE|VER_FLG_WEAK))
9183 strcat (buff, "| ");
9184
9185 strcat (buff, "INFO ");
9186 }
9187
9188 if (flags & ~(VER_FLG_BASE | VER_FLG_WEAK | VER_FLG_INFO))
2b692964 9189 strcat (buff, _("| <unknown>"));
252b5132
RH
9190
9191 return buff;
9192}
9193
9194/* Display the contents of the version sections. */
98fb390a 9195
252b5132 9196static int
2cf0635d 9197process_version_sections (FILE * file)
252b5132 9198{
2cf0635d 9199 Elf_Internal_Shdr * section;
b34976b6
AM
9200 unsigned i;
9201 int found = 0;
252b5132
RH
9202
9203 if (! do_version)
9204 return 1;
9205
9206 for (i = 0, section = section_headers;
9207 i < elf_header.e_shnum;
b34976b6 9208 i++, section++)
252b5132
RH
9209 {
9210 switch (section->sh_type)
9211 {
9212 case SHT_GNU_verdef:
9213 {
2cf0635d 9214 Elf_External_Verdef * edefs;
b34976b6
AM
9215 unsigned int idx;
9216 unsigned int cnt;
2cf0635d 9217 char * endbuf;
252b5132
RH
9218
9219 found = 1;
9220
74e1a04b
NC
9221 printf (_("\nVersion definition section '%s' contains %u entries:\n"),
9222 printable_section_name (section),
9223 section->sh_info);
252b5132
RH
9224
9225 printf (_(" Addr: 0x"));
9226 printf_vma (section->sh_addr);
74e1a04b 9227 printf (_(" Offset: %#08lx Link: %u (%s)"),
1b228002 9228 (unsigned long) section->sh_offset, section->sh_link,
74e1a04b 9229 printable_section_name_from_index (section->sh_link));
252b5132 9230
3f5e193b
NC
9231 edefs = (Elf_External_Verdef *)
9232 get_data (NULL, file, section->sh_offset, 1,section->sh_size,
9233 _("version definition section"));
a6e9f9df
AM
9234 if (!edefs)
9235 break;
59245841 9236 endbuf = (char *) edefs + section->sh_size;
252b5132 9237
b34976b6 9238 for (idx = cnt = 0; cnt < section->sh_info; ++cnt)
252b5132 9239 {
2cf0635d
NC
9240 char * vstart;
9241 Elf_External_Verdef * edef;
b34976b6 9242 Elf_Internal_Verdef ent;
2cf0635d 9243 Elf_External_Verdaux * eaux;
b34976b6
AM
9244 Elf_Internal_Verdaux aux;
9245 int j;
9246 int isum;
103f02d3 9247
7e26601c
NC
9248 /* Check for very large indicies. */
9249 if (idx > (size_t) (endbuf - (char *) edefs))
dd24e3da
NC
9250 break;
9251
252b5132 9252 vstart = ((char *) edefs) + idx;
54806181
AM
9253 if (vstart + sizeof (*edef) > endbuf)
9254 break;
252b5132
RH
9255
9256 edef = (Elf_External_Verdef *) vstart;
9257
9258 ent.vd_version = BYTE_GET (edef->vd_version);
9259 ent.vd_flags = BYTE_GET (edef->vd_flags);
9260 ent.vd_ndx = BYTE_GET (edef->vd_ndx);
9261 ent.vd_cnt = BYTE_GET (edef->vd_cnt);
9262 ent.vd_hash = BYTE_GET (edef->vd_hash);
9263 ent.vd_aux = BYTE_GET (edef->vd_aux);
9264 ent.vd_next = BYTE_GET (edef->vd_next);
9265
9266 printf (_(" %#06x: Rev: %d Flags: %s"),
9267 idx, ent.vd_version, get_ver_flags (ent.vd_flags));
9268
9269 printf (_(" Index: %d Cnt: %d "),
9270 ent.vd_ndx, ent.vd_cnt);
9271
dd24e3da 9272 /* Check for overflow. */
7e26601c 9273 if (ent.vd_aux > (size_t) (endbuf - vstart))
dd24e3da
NC
9274 break;
9275
252b5132
RH
9276 vstart += ent.vd_aux;
9277
9278 eaux = (Elf_External_Verdaux *) vstart;
9279
9280 aux.vda_name = BYTE_GET (eaux->vda_name);
9281 aux.vda_next = BYTE_GET (eaux->vda_next);
9282
d79b3d50
NC
9283 if (VALID_DYNAMIC_NAME (aux.vda_name))
9284 printf (_("Name: %s\n"), GET_DYNAMIC_NAME (aux.vda_name));
252b5132
RH
9285 else
9286 printf (_("Name index: %ld\n"), aux.vda_name);
9287
9288 isum = idx + ent.vd_aux;
9289
b34976b6 9290 for (j = 1; j < ent.vd_cnt; j++)
252b5132 9291 {
dd24e3da 9292 /* Check for overflow. */
7e26601c 9293 if (aux.vda_next > (size_t) (endbuf - vstart))
dd24e3da
NC
9294 break;
9295
252b5132
RH
9296 isum += aux.vda_next;
9297 vstart += aux.vda_next;
9298
9299 eaux = (Elf_External_Verdaux *) vstart;
54806181
AM
9300 if (vstart + sizeof (*eaux) > endbuf)
9301 break;
252b5132
RH
9302
9303 aux.vda_name = BYTE_GET (eaux->vda_name);
9304 aux.vda_next = BYTE_GET (eaux->vda_next);
9305
d79b3d50 9306 if (VALID_DYNAMIC_NAME (aux.vda_name))
252b5132 9307 printf (_(" %#06x: Parent %d: %s\n"),
d79b3d50 9308 isum, j, GET_DYNAMIC_NAME (aux.vda_name));
252b5132
RH
9309 else
9310 printf (_(" %#06x: Parent %d, name index: %ld\n"),
9311 isum, j, aux.vda_name);
9312 }
dd24e3da 9313
54806181
AM
9314 if (j < ent.vd_cnt)
9315 printf (_(" Version def aux past end of section\n"));
252b5132 9316
5d921cbd
NC
9317 /* PR 17531: file: id:000001,src:000172+005151,op:splice,rep:2. */
9318 if (idx + ent.vd_next <= idx)
9319 break;
9320
252b5132
RH
9321 idx += ent.vd_next;
9322 }
dd24e3da 9323
54806181
AM
9324 if (cnt < section->sh_info)
9325 printf (_(" Version definition past end of section\n"));
252b5132
RH
9326
9327 free (edefs);
9328 }
9329 break;
103f02d3 9330
252b5132
RH
9331 case SHT_GNU_verneed:
9332 {
2cf0635d 9333 Elf_External_Verneed * eneed;
b34976b6
AM
9334 unsigned int idx;
9335 unsigned int cnt;
2cf0635d 9336 char * endbuf;
252b5132
RH
9337
9338 found = 1;
9339
72de5009 9340 printf (_("\nVersion needs section '%s' contains %u entries:\n"),
74e1a04b 9341 printable_section_name (section), section->sh_info);
252b5132
RH
9342
9343 printf (_(" Addr: 0x"));
9344 printf_vma (section->sh_addr);
72de5009 9345 printf (_(" Offset: %#08lx Link: %u (%s)\n"),
1b228002 9346 (unsigned long) section->sh_offset, section->sh_link,
74e1a04b 9347 printable_section_name_from_index (section->sh_link));
252b5132 9348
3f5e193b
NC
9349 eneed = (Elf_External_Verneed *) get_data (NULL, file,
9350 section->sh_offset, 1,
9351 section->sh_size,
9cf03b7e 9352 _("Version Needs section"));
a6e9f9df
AM
9353 if (!eneed)
9354 break;
59245841 9355 endbuf = (char *) eneed + section->sh_size;
252b5132
RH
9356
9357 for (idx = cnt = 0; cnt < section->sh_info; ++cnt)
9358 {
2cf0635d 9359 Elf_External_Verneed * entry;
b34976b6
AM
9360 Elf_Internal_Verneed ent;
9361 int j;
9362 int isum;
2cf0635d 9363 char * vstart;
252b5132 9364
7e26601c 9365 if (idx > (size_t) (endbuf - (char *) eneed))
dd24e3da
NC
9366 break;
9367
252b5132 9368 vstart = ((char *) eneed) + idx;
54806181
AM
9369 if (vstart + sizeof (*entry) > endbuf)
9370 break;
252b5132
RH
9371
9372 entry = (Elf_External_Verneed *) vstart;
9373
9374 ent.vn_version = BYTE_GET (entry->vn_version);
9375 ent.vn_cnt = BYTE_GET (entry->vn_cnt);
9376 ent.vn_file = BYTE_GET (entry->vn_file);
9377 ent.vn_aux = BYTE_GET (entry->vn_aux);
9378 ent.vn_next = BYTE_GET (entry->vn_next);
9379
9380 printf (_(" %#06x: Version: %d"), idx, ent.vn_version);
9381
d79b3d50
NC
9382 if (VALID_DYNAMIC_NAME (ent.vn_file))
9383 printf (_(" File: %s"), GET_DYNAMIC_NAME (ent.vn_file));
252b5132
RH
9384 else
9385 printf (_(" File: %lx"), ent.vn_file);
9386
9387 printf (_(" Cnt: %d\n"), ent.vn_cnt);
9388
dd24e3da 9389 /* Check for overflow. */
7e26601c 9390 if (ent.vn_aux > (size_t) (endbuf - vstart))
dd24e3da
NC
9391 break;
9392
252b5132
RH
9393 vstart += ent.vn_aux;
9394
9395 for (j = 0, isum = idx + ent.vn_aux; j < ent.vn_cnt; ++j)
9396 {
2cf0635d 9397 Elf_External_Vernaux * eaux;
b34976b6 9398 Elf_Internal_Vernaux aux;
252b5132 9399
54806181
AM
9400 if (vstart + sizeof (*eaux) > endbuf)
9401 break;
252b5132
RH
9402 eaux = (Elf_External_Vernaux *) vstart;
9403
9404 aux.vna_hash = BYTE_GET (eaux->vna_hash);
9405 aux.vna_flags = BYTE_GET (eaux->vna_flags);
9406 aux.vna_other = BYTE_GET (eaux->vna_other);
9407 aux.vna_name = BYTE_GET (eaux->vna_name);
9408 aux.vna_next = BYTE_GET (eaux->vna_next);
9409
d79b3d50 9410 if (VALID_DYNAMIC_NAME (aux.vna_name))
ecc2063b 9411 printf (_(" %#06x: Name: %s"),
d79b3d50 9412 isum, GET_DYNAMIC_NAME (aux.vna_name));
252b5132 9413 else
ecc2063b 9414 printf (_(" %#06x: Name index: %lx"),
252b5132
RH
9415 isum, aux.vna_name);
9416
9417 printf (_(" Flags: %s Version: %d\n"),
9418 get_ver_flags (aux.vna_flags), aux.vna_other);
9419
dd24e3da 9420 /* Check for overflow. */
7e26601c 9421 if (aux.vna_next > (size_t) (endbuf - vstart))
dd24e3da
NC
9422 break;
9423
252b5132
RH
9424 isum += aux.vna_next;
9425 vstart += aux.vna_next;
9426 }
9cf03b7e 9427
54806181 9428 if (j < ent.vn_cnt)
9cf03b7e 9429 warn (_("Missing Version Needs auxillary information\n"));
252b5132 9430
bcf83b2a 9431 if (ent.vn_next == 0 && cnt < section->sh_info - 1)
c24cf8b6
NC
9432 {
9433 warn (_("Corrupt Version Needs structure - offset to next structure is zero with entries still left to be processed\n"));
9434 cnt = section->sh_info;
9435 break;
9436 }
252b5132
RH
9437 idx += ent.vn_next;
9438 }
9cf03b7e 9439
54806181 9440 if (cnt < section->sh_info)
9cf03b7e 9441 warn (_("Missing Version Needs information\n"));
103f02d3 9442
252b5132
RH
9443 free (eneed);
9444 }
9445 break;
9446
9447 case SHT_GNU_versym:
9448 {
2cf0635d 9449 Elf_Internal_Shdr * link_section;
8b73c356
NC
9450 size_t total;
9451 unsigned int cnt;
2cf0635d
NC
9452 unsigned char * edata;
9453 unsigned short * data;
9454 char * strtab;
9455 Elf_Internal_Sym * symbols;
9456 Elf_Internal_Shdr * string_sec;
ba5cdace 9457 unsigned long num_syms;
d3ba0551 9458 long off;
252b5132 9459
4fbb74a6 9460 if (section->sh_link >= elf_header.e_shnum)
c256ffe7
JJ
9461 break;
9462
4fbb74a6 9463 link_section = section_headers + section->sh_link;
08d8fa11 9464 total = section->sh_size / sizeof (Elf_External_Versym);
252b5132 9465
4fbb74a6 9466 if (link_section->sh_link >= elf_header.e_shnum)
c256ffe7
JJ
9467 break;
9468
252b5132
RH
9469 found = 1;
9470
ba5cdace 9471 symbols = GET_ELF_SYMBOLS (file, link_section, & num_syms);
dd24e3da
NC
9472 if (symbols == NULL)
9473 break;
252b5132 9474
4fbb74a6 9475 string_sec = section_headers + link_section->sh_link;
252b5132 9476
3f5e193b
NC
9477 strtab = (char *) get_data (NULL, file, string_sec->sh_offset, 1,
9478 string_sec->sh_size,
9479 _("version string table"));
a6e9f9df 9480 if (!strtab)
0429c154
MS
9481 {
9482 free (symbols);
9483 break;
9484 }
252b5132 9485
8b73c356
NC
9486 printf (_("\nVersion symbols section '%s' contains %lu entries:\n"),
9487 printable_section_name (section), (unsigned long) total);
252b5132
RH
9488
9489 printf (_(" Addr: "));
9490 printf_vma (section->sh_addr);
72de5009 9491 printf (_(" Offset: %#08lx Link: %u (%s)\n"),
1b228002 9492 (unsigned long) section->sh_offset, section->sh_link,
74e1a04b 9493 printable_section_name (link_section));
252b5132 9494
d3ba0551
AM
9495 off = offset_from_vma (file,
9496 version_info[DT_VERSIONTAGIDX (DT_VERSYM)],
9497 total * sizeof (short));
3f5e193b
NC
9498 edata = (unsigned char *) get_data (NULL, file, off, total,
9499 sizeof (short),
9500 _("version symbol data"));
a6e9f9df
AM
9501 if (!edata)
9502 {
9503 free (strtab);
0429c154 9504 free (symbols);
a6e9f9df
AM
9505 break;
9506 }
252b5132 9507
3f5e193b 9508 data = (short unsigned int *) cmalloc (total, sizeof (short));
252b5132
RH
9509
9510 for (cnt = total; cnt --;)
b34976b6
AM
9511 data[cnt] = byte_get (edata + cnt * sizeof (short),
9512 sizeof (short));
252b5132
RH
9513
9514 free (edata);
9515
9516 for (cnt = 0; cnt < total; cnt += 4)
9517 {
9518 int j, nn;
00d93f34 9519 int check_def, check_need;
2cf0635d 9520 char * name;
252b5132
RH
9521
9522 printf (" %03x:", cnt);
9523
9524 for (j = 0; (j < 4) && (cnt + j) < total; ++j)
b34976b6 9525 switch (data[cnt + j])
252b5132
RH
9526 {
9527 case 0:
9528 fputs (_(" 0 (*local*) "), stdout);
9529 break;
9530
9531 case 1:
9532 fputs (_(" 1 (*global*) "), stdout);
9533 break;
9534
9535 default:
c244d050
NC
9536 nn = printf ("%4x%c", data[cnt + j] & VERSYM_VERSION,
9537 data[cnt + j] & VERSYM_HIDDEN ? 'h' : ' ');
252b5132 9538
dd24e3da 9539 /* If this index value is greater than the size of the symbols
ba5cdace
NC
9540 array, break to avoid an out-of-bounds read. */
9541 if ((unsigned long)(cnt + j) >= num_syms)
dd24e3da
NC
9542 {
9543 warn (_("invalid index into symbol array\n"));
9544 break;
9545 }
9546
00d93f34
JJ
9547 check_def = 1;
9548 check_need = 1;
4fbb74a6
AM
9549 if (symbols[cnt + j].st_shndx >= elf_header.e_shnum
9550 || section_headers[symbols[cnt + j].st_shndx].sh_type
c256ffe7 9551 != SHT_NOBITS)
252b5132 9552 {
b34976b6 9553 if (symbols[cnt + j].st_shndx == SHN_UNDEF)
00d93f34
JJ
9554 check_def = 0;
9555 else
9556 check_need = 0;
252b5132 9557 }
00d93f34
JJ
9558
9559 if (check_need
b34976b6 9560 && version_info[DT_VERSIONTAGIDX (DT_VERNEED)])
252b5132 9561 {
b34976b6
AM
9562 Elf_Internal_Verneed ivn;
9563 unsigned long offset;
252b5132 9564
d93f0186
NC
9565 offset = offset_from_vma
9566 (file, version_info[DT_VERSIONTAGIDX (DT_VERNEED)],
9567 sizeof (Elf_External_Verneed));
252b5132 9568
b34976b6 9569 do
252b5132 9570 {
b34976b6
AM
9571 Elf_Internal_Vernaux ivna;
9572 Elf_External_Verneed evn;
9573 Elf_External_Vernaux evna;
9574 unsigned long a_off;
252b5132 9575
59245841
NC
9576 if (get_data (&evn, file, offset, sizeof (evn), 1,
9577 _("version need")) == NULL)
9578 break;
0b4362b0 9579
252b5132
RH
9580 ivn.vn_aux = BYTE_GET (evn.vn_aux);
9581 ivn.vn_next = BYTE_GET (evn.vn_next);
9582
9583 a_off = offset + ivn.vn_aux;
9584
9585 do
9586 {
59245841
NC
9587 if (get_data (&evna, file, a_off, sizeof (evna),
9588 1, _("version need aux (2)")) == NULL)
9589 {
9590 ivna.vna_next = 0;
9591 ivna.vna_other = 0;
9592 }
9593 else
9594 {
9595 ivna.vna_next = BYTE_GET (evna.vna_next);
9596 ivna.vna_other = BYTE_GET (evna.vna_other);
9597 }
252b5132
RH
9598
9599 a_off += ivna.vna_next;
9600 }
b34976b6 9601 while (ivna.vna_other != data[cnt + j]
252b5132
RH
9602 && ivna.vna_next != 0);
9603
b34976b6 9604 if (ivna.vna_other == data[cnt + j])
252b5132
RH
9605 {
9606 ivna.vna_name = BYTE_GET (evna.vna_name);
9607
54806181
AM
9608 if (ivna.vna_name >= string_sec->sh_size)
9609 name = _("*invalid*");
9610 else
9611 name = strtab + ivna.vna_name;
252b5132 9612 nn += printf ("(%s%-*s",
16062207
ILT
9613 name,
9614 12 - (int) strlen (name),
252b5132 9615 ")");
00d93f34 9616 check_def = 0;
252b5132
RH
9617 break;
9618 }
9619
9620 offset += ivn.vn_next;
9621 }
9622 while (ivn.vn_next);
9623 }
00d93f34 9624
b34976b6
AM
9625 if (check_def && data[cnt + j] != 0x8001
9626 && version_info[DT_VERSIONTAGIDX (DT_VERDEF)])
252b5132 9627 {
b34976b6
AM
9628 Elf_Internal_Verdef ivd;
9629 Elf_External_Verdef evd;
9630 unsigned long offset;
252b5132 9631
d93f0186
NC
9632 offset = offset_from_vma
9633 (file, version_info[DT_VERSIONTAGIDX (DT_VERDEF)],
9634 sizeof evd);
252b5132
RH
9635
9636 do
9637 {
59245841
NC
9638 if (get_data (&evd, file, offset, sizeof (evd), 1,
9639 _("version def")) == NULL)
9640 {
9641 ivd.vd_next = 0;
3102e897
NC
9642 /* PR 17531: file: 046-1082287-0.004. */
9643 ivd.vd_ndx = (data[cnt + j] & VERSYM_VERSION) + 1;
9644 break;
59245841
NC
9645 }
9646 else
9647 {
9648 ivd.vd_next = BYTE_GET (evd.vd_next);
9649 ivd.vd_ndx = BYTE_GET (evd.vd_ndx);
9650 }
252b5132
RH
9651
9652 offset += ivd.vd_next;
9653 }
c244d050 9654 while (ivd.vd_ndx != (data[cnt + j] & VERSYM_VERSION)
252b5132
RH
9655 && ivd.vd_next != 0);
9656
c244d050 9657 if (ivd.vd_ndx == (data[cnt + j] & VERSYM_VERSION))
252b5132 9658 {
b34976b6
AM
9659 Elf_External_Verdaux evda;
9660 Elf_Internal_Verdaux ivda;
252b5132
RH
9661
9662 ivd.vd_aux = BYTE_GET (evd.vd_aux);
9663
59245841
NC
9664 if (get_data (&evda, file,
9665 offset - ivd.vd_next + ivd.vd_aux,
9666 sizeof (evda), 1,
9667 _("version def aux")) == NULL)
9668 break;
252b5132
RH
9669
9670 ivda.vda_name = BYTE_GET (evda.vda_name);
9671
54806181
AM
9672 if (ivda.vda_name >= string_sec->sh_size)
9673 name = _("*invalid*");
9674 else
9675 name = strtab + ivda.vda_name;
252b5132 9676 nn += printf ("(%s%-*s",
16062207
ILT
9677 name,
9678 12 - (int) strlen (name),
252b5132
RH
9679 ")");
9680 }
9681 }
9682
9683 if (nn < 18)
9684 printf ("%*c", 18 - nn, ' ');
9685 }
9686
9687 putchar ('\n');
9688 }
9689
9690 free (data);
9691 free (strtab);
9692 free (symbols);
9693 }
9694 break;
103f02d3 9695
252b5132
RH
9696 default:
9697 break;
9698 }
9699 }
9700
9701 if (! found)
9702 printf (_("\nNo version information found in this file.\n"));
9703
9704 return 1;
9705}
9706
d1133906 9707static const char *
d3ba0551 9708get_symbol_binding (unsigned int binding)
252b5132 9709{
b34976b6 9710 static char buff[32];
252b5132
RH
9711
9712 switch (binding)
9713 {
b34976b6
AM
9714 case STB_LOCAL: return "LOCAL";
9715 case STB_GLOBAL: return "GLOBAL";
9716 case STB_WEAK: return "WEAK";
252b5132
RH
9717 default:
9718 if (binding >= STB_LOPROC && binding <= STB_HIPROC)
e9e44622
JJ
9719 snprintf (buff, sizeof (buff), _("<processor specific>: %d"),
9720 binding);
252b5132 9721 else if (binding >= STB_LOOS && binding <= STB_HIOS)
3e7a7d11
NC
9722 {
9723 if (binding == STB_GNU_UNIQUE
9c55345c
TS
9724 && (elf_header.e_ident[EI_OSABI] == ELFOSABI_GNU
9725 /* GNU is still using the default value 0. */
3e7a7d11
NC
9726 || elf_header.e_ident[EI_OSABI] == ELFOSABI_NONE))
9727 return "UNIQUE";
9728 snprintf (buff, sizeof (buff), _("<OS specific>: %d"), binding);
9729 }
252b5132 9730 else
e9e44622 9731 snprintf (buff, sizeof (buff), _("<unknown>: %d"), binding);
252b5132
RH
9732 return buff;
9733 }
9734}
9735
d1133906 9736static const char *
d3ba0551 9737get_symbol_type (unsigned int type)
252b5132 9738{
b34976b6 9739 static char buff[32];
252b5132
RH
9740
9741 switch (type)
9742 {
b34976b6
AM
9743 case STT_NOTYPE: return "NOTYPE";
9744 case STT_OBJECT: return "OBJECT";
9745 case STT_FUNC: return "FUNC";
9746 case STT_SECTION: return "SECTION";
9747 case STT_FILE: return "FILE";
9748 case STT_COMMON: return "COMMON";
9749 case STT_TLS: return "TLS";
15ab5209
DB
9750 case STT_RELC: return "RELC";
9751 case STT_SRELC: return "SRELC";
252b5132
RH
9752 default:
9753 if (type >= STT_LOPROC && type <= STT_HIPROC)
df75f1af 9754 {
3510a7b8
NC
9755 if (elf_header.e_machine == EM_ARM && type == STT_ARM_TFUNC)
9756 return "THUMB_FUNC";
103f02d3 9757
351b4b40 9758 if (elf_header.e_machine == EM_SPARCV9 && type == STT_REGISTER)
103f02d3
UD
9759 return "REGISTER";
9760
9761 if (elf_header.e_machine == EM_PARISC && type == STT_PARISC_MILLI)
9762 return "PARISC_MILLI";
9763
e9e44622 9764 snprintf (buff, sizeof (buff), _("<processor specific>: %d"), type);
df75f1af 9765 }
252b5132 9766 else if (type >= STT_LOOS && type <= STT_HIOS)
103f02d3
UD
9767 {
9768 if (elf_header.e_machine == EM_PARISC)
9769 {
9770 if (type == STT_HP_OPAQUE)
9771 return "HP_OPAQUE";
9772 if (type == STT_HP_STUB)
9773 return "HP_STUB";
9774 }
9775
d8045f23 9776 if (type == STT_GNU_IFUNC
9c55345c 9777 && (elf_header.e_ident[EI_OSABI] == ELFOSABI_GNU
83c257ca 9778 || elf_header.e_ident[EI_OSABI] == ELFOSABI_FREEBSD
9c55345c 9779 /* GNU is still using the default value 0. */
d8045f23
NC
9780 || elf_header.e_ident[EI_OSABI] == ELFOSABI_NONE))
9781 return "IFUNC";
9782
e9e44622 9783 snprintf (buff, sizeof (buff), _("<OS specific>: %d"), type);
103f02d3 9784 }
252b5132 9785 else
e9e44622 9786 snprintf (buff, sizeof (buff), _("<unknown>: %d"), type);
252b5132
RH
9787 return buff;
9788 }
9789}
9790
d1133906 9791static const char *
d3ba0551 9792get_symbol_visibility (unsigned int visibility)
d1133906
NC
9793{
9794 switch (visibility)
9795 {
b34976b6
AM
9796 case STV_DEFAULT: return "DEFAULT";
9797 case STV_INTERNAL: return "INTERNAL";
9798 case STV_HIDDEN: return "HIDDEN";
d1133906 9799 case STV_PROTECTED: return "PROTECTED";
bee0ee85
NC
9800 default:
9801 error (_("Unrecognized visibility value: %u"), visibility);
9802 return _("<unknown>");
d1133906
NC
9803 }
9804}
9805
5e2b0d47
NC
9806static const char *
9807get_mips_symbol_other (unsigned int other)
9808{
9809 switch (other)
9810 {
df58fc94
RS
9811 case STO_OPTIONAL:
9812 return "OPTIONAL";
9813 case STO_MIPS_PLT:
9814 return "MIPS PLT";
9815 case STO_MIPS_PIC:
9816 return "MIPS PIC";
9817 case STO_MICROMIPS:
9818 return "MICROMIPS";
9819 case STO_MICROMIPS | STO_MIPS_PIC:
9820 return "MICROMIPS, MIPS PIC";
9821 case STO_MIPS16:
9822 return "MIPS16";
9823 default:
9824 return NULL;
5e2b0d47
NC
9825 }
9826}
9827
28f997cf
TG
9828static const char *
9829get_ia64_symbol_other (unsigned int other)
9830{
9831 if (is_ia64_vms ())
9832 {
9833 static char res[32];
9834
9835 res[0] = 0;
9836
9837 /* Function types is for images and .STB files only. */
9838 switch (elf_header.e_type)
9839 {
9840 case ET_DYN:
9841 case ET_EXEC:
9842 switch (VMS_ST_FUNC_TYPE (other))
9843 {
9844 case VMS_SFT_CODE_ADDR:
9845 strcat (res, " CA");
9846 break;
9847 case VMS_SFT_SYMV_IDX:
9848 strcat (res, " VEC");
9849 break;
9850 case VMS_SFT_FD:
9851 strcat (res, " FD");
9852 break;
9853 case VMS_SFT_RESERVE:
9854 strcat (res, " RSV");
9855 break;
9856 default:
bee0ee85
NC
9857 warn (_("Unrecognized IA64 VMS ST Function type: %d\n"),
9858 VMS_ST_FUNC_TYPE (other));
9859 strcat (res, " <unknown>");
9860 break;
28f997cf
TG
9861 }
9862 break;
9863 default:
9864 break;
9865 }
9866 switch (VMS_ST_LINKAGE (other))
9867 {
9868 case VMS_STL_IGNORE:
9869 strcat (res, " IGN");
9870 break;
9871 case VMS_STL_RESERVE:
9872 strcat (res, " RSV");
9873 break;
9874 case VMS_STL_STD:
9875 strcat (res, " STD");
9876 break;
9877 case VMS_STL_LNK:
9878 strcat (res, " LNK");
9879 break;
9880 default:
bee0ee85
NC
9881 warn (_("Unrecognized IA64 VMS ST Linkage: %d\n"),
9882 VMS_ST_LINKAGE (other));
9883 strcat (res, " <unknown>");
9884 break;
28f997cf
TG
9885 }
9886
9887 if (res[0] != 0)
9888 return res + 1;
9889 else
9890 return res;
9891 }
9892 return NULL;
9893}
9894
6911b7dc
AM
9895static const char *
9896get_ppc64_symbol_other (unsigned int other)
9897{
9898 if (PPC64_LOCAL_ENTRY_OFFSET (other) != 0)
9899 {
9900 static char buf[32];
9901 snprintf (buf, sizeof buf, _("<localentry>: %d"),
9902 PPC64_LOCAL_ENTRY_OFFSET (other));
9903 return buf;
9904 }
9905 return NULL;
9906}
9907
5e2b0d47
NC
9908static const char *
9909get_symbol_other (unsigned int other)
9910{
9911 const char * result = NULL;
9912 static char buff [32];
9913
9914 if (other == 0)
9915 return "";
9916
9917 switch (elf_header.e_machine)
9918 {
9919 case EM_MIPS:
9920 result = get_mips_symbol_other (other);
28f997cf
TG
9921 break;
9922 case EM_IA_64:
9923 result = get_ia64_symbol_other (other);
9924 break;
6911b7dc
AM
9925 case EM_PPC64:
9926 result = get_ppc64_symbol_other (other);
9927 break;
5e2b0d47
NC
9928 default:
9929 break;
9930 }
9931
9932 if (result)
9933 return result;
9934
9935 snprintf (buff, sizeof buff, _("<other>: %x"), other);
9936 return buff;
9937}
9938
d1133906 9939static const char *
d3ba0551 9940get_symbol_index_type (unsigned int type)
252b5132 9941{
b34976b6 9942 static char buff[32];
5cf1065c 9943
252b5132
RH
9944 switch (type)
9945 {
b34976b6
AM
9946 case SHN_UNDEF: return "UND";
9947 case SHN_ABS: return "ABS";
9948 case SHN_COMMON: return "COM";
252b5132 9949 default:
9ce701e2
L
9950 if (type == SHN_IA_64_ANSI_COMMON
9951 && elf_header.e_machine == EM_IA_64
9952 && elf_header.e_ident[EI_OSABI] == ELFOSABI_HPUX)
9953 return "ANSI_COM";
8a9036a4 9954 else if ((elf_header.e_machine == EM_X86_64
7a9068fe
L
9955 || elf_header.e_machine == EM_L1OM
9956 || elf_header.e_machine == EM_K1OM)
3b22753a
L
9957 && type == SHN_X86_64_LCOMMON)
9958 return "LARGE_COM";
ac145307
BS
9959 else if ((type == SHN_MIPS_SCOMMON
9960 && elf_header.e_machine == EM_MIPS)
9961 || (type == SHN_TIC6X_SCOMMON
9962 && elf_header.e_machine == EM_TI_C6000))
172553c7
TS
9963 return "SCOM";
9964 else if (type == SHN_MIPS_SUNDEFINED
9965 && elf_header.e_machine == EM_MIPS)
9966 return "SUND";
9ce701e2 9967 else if (type >= SHN_LOPROC && type <= SHN_HIPROC)
4fbb74a6 9968 sprintf (buff, "PRC[0x%04x]", type & 0xffff);
252b5132 9969 else if (type >= SHN_LOOS && type <= SHN_HIOS)
4fbb74a6
AM
9970 sprintf (buff, "OS [0x%04x]", type & 0xffff);
9971 else if (type >= SHN_LORESERVE)
9972 sprintf (buff, "RSV[0x%04x]", type & 0xffff);
c6d8cab4 9973 else if (type >= elf_header.e_shnum)
e0a31db1 9974 sprintf (buff, _("bad section index[%3d]"), type);
252b5132 9975 else
232e7cb8 9976 sprintf (buff, "%3d", type);
5cf1065c 9977 break;
252b5132 9978 }
5cf1065c
NC
9979
9980 return buff;
252b5132
RH
9981}
9982
66543521 9983static bfd_vma *
8b73c356 9984get_dynamic_data (FILE * file, size_t number, unsigned int ent_size)
252b5132 9985{
2cf0635d
NC
9986 unsigned char * e_data;
9987 bfd_vma * i_data;
252b5132 9988
3102e897
NC
9989 /* Be kind to memory chekers (eg valgrind, address sanitizer) by not
9990 attempting to allocate memory when the read is bound to fail. */
9991 if (ent_size * number > current_file_size)
9992 {
9993 error (_("Invalid number of dynamic entries: %lu\n"),
9994 (unsigned long) number);
9995 return NULL;
9996 }
9997
3f5e193b 9998 e_data = (unsigned char *) cmalloc (number, ent_size);
252b5132
RH
9999 if (e_data == NULL)
10000 {
8b73c356
NC
10001 error (_("Out of memory reading %lu dynamic entries\n"),
10002 (unsigned long) number);
252b5132
RH
10003 return NULL;
10004 }
10005
66543521 10006 if (fread (e_data, ent_size, number, file) != number)
252b5132 10007 {
3102e897
NC
10008 error (_("Unable to read in %lu bytes of dynamic data\n"),
10009 (unsigned long) (number * ent_size));
10010 free (e_data);
252b5132
RH
10011 return NULL;
10012 }
10013
3f5e193b 10014 i_data = (bfd_vma *) cmalloc (number, sizeof (*i_data));
252b5132
RH
10015 if (i_data == NULL)
10016 {
8b73c356
NC
10017 error (_("Out of memory allocating space for %lu dynamic entries\n"),
10018 (unsigned long) number);
252b5132
RH
10019 free (e_data);
10020 return NULL;
10021 }
10022
10023 while (number--)
66543521 10024 i_data[number] = byte_get (e_data + number * ent_size, ent_size);
252b5132
RH
10025
10026 free (e_data);
10027
10028 return i_data;
10029}
10030
6bd1a22c
L
10031static void
10032print_dynamic_symbol (bfd_vma si, unsigned long hn)
10033{
2cf0635d 10034 Elf_Internal_Sym * psym;
6bd1a22c
L
10035 int n;
10036
6bd1a22c
L
10037 n = print_vma (si, DEC_5);
10038 if (n < 5)
0b4362b0 10039 fputs (&" "[n], stdout);
6bd1a22c 10040 printf (" %3lu: ", hn);
e0a31db1
NC
10041
10042 if (dynamic_symbols == NULL || si >= num_dynamic_syms)
10043 {
3102e897
NC
10044 printf (_("<No info available for dynamic symbol number %lu>\n"),
10045 (unsigned long) si);
e0a31db1
NC
10046 return;
10047 }
10048
10049 psym = dynamic_symbols + si;
6bd1a22c
L
10050 print_vma (psym->st_value, LONG_HEX);
10051 putchar (' ');
10052 print_vma (psym->st_size, DEC_5);
10053
f4be36b3
AM
10054 printf (" %-7s", get_symbol_type (ELF_ST_TYPE (psym->st_info)));
10055 printf (" %-6s", get_symbol_binding (ELF_ST_BIND (psym->st_info)));
10056 printf (" %-7s", get_symbol_visibility (ELF_ST_VISIBILITY (psym->st_other)));
6bd1a22c
L
10057 /* Check to see if any other bits in the st_other field are set.
10058 Note - displaying this information disrupts the layout of the
10059 table being generated, but for the moment this case is very
10060 rare. */
10061 if (psym->st_other ^ ELF_ST_VISIBILITY (psym->st_other))
10062 printf (" [%s] ", get_symbol_other (psym->st_other ^ ELF_ST_VISIBILITY (psym->st_other)));
10063 printf (" %3.3s ", get_symbol_index_type (psym->st_shndx));
10064 if (VALID_DYNAMIC_NAME (psym->st_name))
10065 print_symbol (25, GET_DYNAMIC_NAME (psym->st_name));
10066 else
2b692964 10067 printf (_(" <corrupt: %14ld>"), psym->st_name);
6bd1a22c
L
10068 putchar ('\n');
10069}
10070
bb4d2ac2
L
10071static const char *
10072get_symbol_version_string (FILE *file, int is_dynsym,
10073 const char *strtab,
10074 unsigned long int strtab_size,
10075 unsigned int si, Elf_Internal_Sym *psym,
10076 enum versioned_symbol_info *sym_info,
10077 unsigned short *vna_other)
10078{
10079 const char *version_string = NULL;
10080
10081 if (is_dynsym
10082 && version_info[DT_VERSIONTAGIDX (DT_VERSYM)] != 0)
10083 {
10084 unsigned char data[2];
10085 unsigned short vers_data;
10086 unsigned long offset;
10087 int is_nobits;
10088 int check_def;
10089
10090 offset = offset_from_vma
10091 (file, version_info[DT_VERSIONTAGIDX (DT_VERSYM)],
10092 sizeof data + si * sizeof (vers_data));
10093
10094 if (get_data (&data, file, offset + si * sizeof (vers_data),
10095 sizeof (data), 1, _("version data")) == NULL)
10096 return NULL;
10097
10098 vers_data = byte_get (data, 2);
10099
10100 is_nobits = (psym->st_shndx < elf_header.e_shnum
10101 && section_headers[psym->st_shndx].sh_type
10102 == SHT_NOBITS);
10103
10104 check_def = (psym->st_shndx != SHN_UNDEF);
10105
10106 if ((vers_data & VERSYM_HIDDEN) || vers_data > 1)
10107 {
10108 if (version_info[DT_VERSIONTAGIDX (DT_VERNEED)]
10109 && (is_nobits || ! check_def))
10110 {
10111 Elf_External_Verneed evn;
10112 Elf_Internal_Verneed ivn;
10113 Elf_Internal_Vernaux ivna;
10114
10115 /* We must test both. */
10116 offset = offset_from_vma
10117 (file, version_info[DT_VERSIONTAGIDX (DT_VERNEED)],
10118 sizeof evn);
10119
10120 do
10121 {
10122 unsigned long vna_off;
10123
10124 if (get_data (&evn, file, offset, sizeof (evn), 1,
10125 _("version need")) == NULL)
10126 {
10127 ivna.vna_next = 0;
10128 ivna.vna_other = 0;
10129 ivna.vna_name = 0;
10130 break;
10131 }
10132
10133 ivn.vn_aux = BYTE_GET (evn.vn_aux);
10134 ivn.vn_next = BYTE_GET (evn.vn_next);
10135
10136 vna_off = offset + ivn.vn_aux;
10137
10138 do
10139 {
10140 Elf_External_Vernaux evna;
10141
10142 if (get_data (&evna, file, vna_off,
10143 sizeof (evna), 1,
10144 _("version need aux (3)")) == NULL)
10145 {
10146 ivna.vna_next = 0;
10147 ivna.vna_other = 0;
10148 ivna.vna_name = 0;
10149 }
10150 else
10151 {
10152 ivna.vna_other = BYTE_GET (evna.vna_other);
10153 ivna.vna_next = BYTE_GET (evna.vna_next);
10154 ivna.vna_name = BYTE_GET (evna.vna_name);
10155 }
10156
10157 vna_off += ivna.vna_next;
10158 }
10159 while (ivna.vna_other != vers_data
10160 && ivna.vna_next != 0);
10161
10162 if (ivna.vna_other == vers_data)
10163 break;
10164
10165 offset += ivn.vn_next;
10166 }
10167 while (ivn.vn_next != 0);
10168
10169 if (ivna.vna_other == vers_data)
10170 {
10171 *sym_info = symbol_undefined;
10172 *vna_other = ivna.vna_other;
10173 version_string = (ivna.vna_name < strtab_size
10174 ? strtab + ivna.vna_name
10175 : _("<corrupt>"));
10176 check_def = 0;
10177 }
10178 else if (! is_nobits)
10179 error (_("bad dynamic symbol\n"));
10180 else
10181 check_def = 1;
10182 }
10183
10184 if (check_def)
10185 {
10186 if (vers_data != 0x8001
10187 && version_info[DT_VERSIONTAGIDX (DT_VERDEF)])
10188 {
10189 Elf_Internal_Verdef ivd;
10190 Elf_Internal_Verdaux ivda;
10191 Elf_External_Verdaux evda;
10192 unsigned long off;
10193
10194 off = offset_from_vma
10195 (file,
10196 version_info[DT_VERSIONTAGIDX (DT_VERDEF)],
10197 sizeof (Elf_External_Verdef));
10198
10199 do
10200 {
10201 Elf_External_Verdef evd;
10202
10203 if (get_data (&evd, file, off, sizeof (evd),
10204 1, _("version def")) == NULL)
10205 {
10206 ivd.vd_ndx = 0;
10207 ivd.vd_aux = 0;
10208 ivd.vd_next = 0;
10209 }
10210 else
10211 {
10212 ivd.vd_ndx = BYTE_GET (evd.vd_ndx);
10213 ivd.vd_aux = BYTE_GET (evd.vd_aux);
10214 ivd.vd_next = BYTE_GET (evd.vd_next);
10215 }
10216
10217 off += ivd.vd_next;
10218 }
10219 while (ivd.vd_ndx != (vers_data & VERSYM_VERSION)
10220 && ivd.vd_next != 0);
10221
10222 off -= ivd.vd_next;
10223 off += ivd.vd_aux;
10224
10225 if (get_data (&evda, file, off, sizeof (evda),
10226 1, _("version def aux")) == NULL)
10227 return version_string;
10228
10229 ivda.vda_name = BYTE_GET (evda.vda_name);
10230
10231 if (psym->st_name != ivda.vda_name)
10232 {
10233 *sym_info = ((vers_data & VERSYM_HIDDEN) != 0
10234 ? symbol_hidden : symbol_public);
10235 version_string = (ivda.vda_name < strtab_size
10236 ? strtab + ivda.vda_name
10237 : _("<corrupt>"));
10238 }
10239 }
10240 }
10241 }
10242 }
10243 return version_string;
10244}
10245
e3c8793a 10246/* Dump the symbol table. */
252b5132 10247static int
2cf0635d 10248process_symbol_table (FILE * file)
252b5132 10249{
2cf0635d 10250 Elf_Internal_Shdr * section;
8b73c356
NC
10251 bfd_size_type nbuckets = 0;
10252 bfd_size_type nchains = 0;
2cf0635d
NC
10253 bfd_vma * buckets = NULL;
10254 bfd_vma * chains = NULL;
fdc90cb4 10255 bfd_vma ngnubuckets = 0;
2cf0635d
NC
10256 bfd_vma * gnubuckets = NULL;
10257 bfd_vma * gnuchains = NULL;
6bd1a22c 10258 bfd_vma gnusymidx = 0;
071436c6 10259 bfd_size_type ngnuchains = 0;
252b5132 10260
2c610e4b 10261 if (!do_syms && !do_dyn_syms && !do_histogram)
252b5132
RH
10262 return 1;
10263
6bd1a22c
L
10264 if (dynamic_info[DT_HASH]
10265 && (do_histogram
2c610e4b
L
10266 || (do_using_dynamic
10267 && !do_dyn_syms
10268 && dynamic_strings != NULL)))
252b5132 10269 {
66543521
AM
10270 unsigned char nb[8];
10271 unsigned char nc[8];
8b73c356 10272 unsigned int hash_ent_size = 4;
66543521
AM
10273
10274 if ((elf_header.e_machine == EM_ALPHA
10275 || elf_header.e_machine == EM_S390
10276 || elf_header.e_machine == EM_S390_OLD)
10277 && elf_header.e_ident[EI_CLASS] == ELFCLASS64)
10278 hash_ent_size = 8;
10279
fb52b2f4
NC
10280 if (fseek (file,
10281 (archive_file_offset
10282 + offset_from_vma (file, dynamic_info[DT_HASH],
10283 sizeof nb + sizeof nc)),
d93f0186 10284 SEEK_SET))
252b5132 10285 {
591a748a 10286 error (_("Unable to seek to start of dynamic information\n"));
d3a44ec6 10287 goto no_hash;
252b5132
RH
10288 }
10289
66543521 10290 if (fread (nb, hash_ent_size, 1, file) != 1)
252b5132
RH
10291 {
10292 error (_("Failed to read in number of buckets\n"));
d3a44ec6 10293 goto no_hash;
252b5132
RH
10294 }
10295
66543521 10296 if (fread (nc, hash_ent_size, 1, file) != 1)
252b5132
RH
10297 {
10298 error (_("Failed to read in number of chains\n"));
d3a44ec6 10299 goto no_hash;
252b5132
RH
10300 }
10301
66543521
AM
10302 nbuckets = byte_get (nb, hash_ent_size);
10303 nchains = byte_get (nc, hash_ent_size);
252b5132 10304
66543521
AM
10305 buckets = get_dynamic_data (file, nbuckets, hash_ent_size);
10306 chains = get_dynamic_data (file, nchains, hash_ent_size);
252b5132 10307
d3a44ec6 10308 no_hash:
252b5132 10309 if (buckets == NULL || chains == NULL)
d3a44ec6
JJ
10310 {
10311 if (do_using_dynamic)
10312 return 0;
10313 free (buckets);
10314 free (chains);
10315 buckets = NULL;
10316 chains = NULL;
10317 nbuckets = 0;
10318 nchains = 0;
10319 }
252b5132
RH
10320 }
10321
6bd1a22c
L
10322 if (dynamic_info_DT_GNU_HASH
10323 && (do_histogram
2c610e4b
L
10324 || (do_using_dynamic
10325 && !do_dyn_syms
10326 && dynamic_strings != NULL)))
252b5132 10327 {
6bd1a22c
L
10328 unsigned char nb[16];
10329 bfd_vma i, maxchain = 0xffffffff, bitmaskwords;
10330 bfd_vma buckets_vma;
10331
10332 if (fseek (file,
10333 (archive_file_offset
10334 + offset_from_vma (file, dynamic_info_DT_GNU_HASH,
10335 sizeof nb)),
10336 SEEK_SET))
10337 {
10338 error (_("Unable to seek to start of dynamic information\n"));
d3a44ec6 10339 goto no_gnu_hash;
6bd1a22c 10340 }
252b5132 10341
6bd1a22c
L
10342 if (fread (nb, 16, 1, file) != 1)
10343 {
10344 error (_("Failed to read in number of buckets\n"));
d3a44ec6 10345 goto no_gnu_hash;
6bd1a22c
L
10346 }
10347
10348 ngnubuckets = byte_get (nb, 4);
10349 gnusymidx = byte_get (nb + 4, 4);
10350 bitmaskwords = byte_get (nb + 8, 4);
10351 buckets_vma = dynamic_info_DT_GNU_HASH + 16;
f7a99963 10352 if (is_32bit_elf)
6bd1a22c 10353 buckets_vma += bitmaskwords * 4;
f7a99963 10354 else
6bd1a22c 10355 buckets_vma += bitmaskwords * 8;
252b5132 10356
6bd1a22c
L
10357 if (fseek (file,
10358 (archive_file_offset
10359 + offset_from_vma (file, buckets_vma, 4)),
10360 SEEK_SET))
252b5132 10361 {
6bd1a22c 10362 error (_("Unable to seek to start of dynamic information\n"));
d3a44ec6 10363 goto no_gnu_hash;
6bd1a22c
L
10364 }
10365
10366 gnubuckets = get_dynamic_data (file, ngnubuckets, 4);
252b5132 10367
6bd1a22c 10368 if (gnubuckets == NULL)
d3a44ec6 10369 goto no_gnu_hash;
6bd1a22c
L
10370
10371 for (i = 0; i < ngnubuckets; i++)
10372 if (gnubuckets[i] != 0)
10373 {
10374 if (gnubuckets[i] < gnusymidx)
10375 return 0;
10376
10377 if (maxchain == 0xffffffff || gnubuckets[i] > maxchain)
10378 maxchain = gnubuckets[i];
10379 }
10380
10381 if (maxchain == 0xffffffff)
d3a44ec6 10382 goto no_gnu_hash;
6bd1a22c
L
10383
10384 maxchain -= gnusymidx;
10385
10386 if (fseek (file,
10387 (archive_file_offset
10388 + offset_from_vma (file, buckets_vma
10389 + 4 * (ngnubuckets + maxchain), 4)),
10390 SEEK_SET))
10391 {
10392 error (_("Unable to seek to start of dynamic information\n"));
d3a44ec6 10393 goto no_gnu_hash;
6bd1a22c
L
10394 }
10395
10396 do
10397 {
10398 if (fread (nb, 4, 1, file) != 1)
252b5132 10399 {
6bd1a22c 10400 error (_("Failed to determine last chain length\n"));
d3a44ec6 10401 goto no_gnu_hash;
6bd1a22c 10402 }
252b5132 10403
6bd1a22c 10404 if (maxchain + 1 == 0)
d3a44ec6 10405 goto no_gnu_hash;
252b5132 10406
6bd1a22c
L
10407 ++maxchain;
10408 }
10409 while ((byte_get (nb, 4) & 1) == 0);
76da6bbe 10410
6bd1a22c
L
10411 if (fseek (file,
10412 (archive_file_offset
10413 + offset_from_vma (file, buckets_vma + 4 * ngnubuckets, 4)),
10414 SEEK_SET))
10415 {
10416 error (_("Unable to seek to start of dynamic information\n"));
d3a44ec6 10417 goto no_gnu_hash;
6bd1a22c
L
10418 }
10419
10420 gnuchains = get_dynamic_data (file, maxchain, 4);
071436c6 10421 ngnuchains = maxchain;
6bd1a22c 10422
d3a44ec6 10423 no_gnu_hash:
6bd1a22c 10424 if (gnuchains == NULL)
d3a44ec6
JJ
10425 {
10426 free (gnubuckets);
d3a44ec6
JJ
10427 gnubuckets = NULL;
10428 ngnubuckets = 0;
f64fddf1
NC
10429 if (do_using_dynamic)
10430 return 0;
d3a44ec6 10431 }
6bd1a22c
L
10432 }
10433
10434 if ((dynamic_info[DT_HASH] || dynamic_info_DT_GNU_HASH)
10435 && do_syms
10436 && do_using_dynamic
3102e897
NC
10437 && dynamic_strings != NULL
10438 && dynamic_symbols != NULL)
6bd1a22c
L
10439 {
10440 unsigned long hn;
10441
10442 if (dynamic_info[DT_HASH])
10443 {
10444 bfd_vma si;
10445
10446 printf (_("\nSymbol table for image:\n"));
10447 if (is_32bit_elf)
10448 printf (_(" Num Buc: Value Size Type Bind Vis Ndx Name\n"));
10449 else
10450 printf (_(" Num Buc: Value Size Type Bind Vis Ndx Name\n"));
10451
10452 for (hn = 0; hn < nbuckets; hn++)
10453 {
10454 if (! buckets[hn])
10455 continue;
10456
10457 for (si = buckets[hn]; si < nchains && si > 0; si = chains[si])
10458 print_dynamic_symbol (si, hn);
252b5132
RH
10459 }
10460 }
6bd1a22c
L
10461
10462 if (dynamic_info_DT_GNU_HASH)
10463 {
10464 printf (_("\nSymbol table of `.gnu.hash' for image:\n"));
10465 if (is_32bit_elf)
10466 printf (_(" Num Buc: Value Size Type Bind Vis Ndx Name\n"));
10467 else
10468 printf (_(" Num Buc: Value Size Type Bind Vis Ndx Name\n"));
10469
10470 for (hn = 0; hn < ngnubuckets; ++hn)
10471 if (gnubuckets[hn] != 0)
10472 {
10473 bfd_vma si = gnubuckets[hn];
10474 bfd_vma off = si - gnusymidx;
10475
10476 do
10477 {
10478 print_dynamic_symbol (si, hn);
10479 si++;
10480 }
071436c6 10481 while (off < ngnuchains && (gnuchains[off++] & 1) == 0);
6bd1a22c
L
10482 }
10483 }
252b5132 10484 }
8b73c356
NC
10485 else if ((do_dyn_syms || (do_syms && !do_using_dynamic))
10486 && section_headers != NULL)
252b5132 10487 {
b34976b6 10488 unsigned int i;
252b5132
RH
10489
10490 for (i = 0, section = section_headers;
10491 i < elf_header.e_shnum;
10492 i++, section++)
10493 {
b34976b6 10494 unsigned int si;
2cf0635d 10495 char * strtab = NULL;
c256ffe7 10496 unsigned long int strtab_size = 0;
2cf0635d
NC
10497 Elf_Internal_Sym * symtab;
10498 Elf_Internal_Sym * psym;
ba5cdace 10499 unsigned long num_syms;
252b5132 10500
2c610e4b
L
10501 if ((section->sh_type != SHT_SYMTAB
10502 && section->sh_type != SHT_DYNSYM)
10503 || (!do_syms
10504 && section->sh_type == SHT_SYMTAB))
252b5132
RH
10505 continue;
10506
dd24e3da
NC
10507 if (section->sh_entsize == 0)
10508 {
10509 printf (_("\nSymbol table '%s' has a sh_entsize of zero!\n"),
74e1a04b 10510 printable_section_name (section));
dd24e3da
NC
10511 continue;
10512 }
10513
252b5132 10514 printf (_("\nSymbol table '%s' contains %lu entries:\n"),
74e1a04b 10515 printable_section_name (section),
252b5132 10516 (unsigned long) (section->sh_size / section->sh_entsize));
dd24e3da 10517
f7a99963 10518 if (is_32bit_elf)
ca47b30c 10519 printf (_(" Num: Value Size Type Bind Vis Ndx Name\n"));
f7a99963 10520 else
ca47b30c 10521 printf (_(" Num: Value Size Type Bind Vis Ndx Name\n"));
252b5132 10522
ba5cdace 10523 symtab = GET_ELF_SYMBOLS (file, section, & num_syms);
252b5132
RH
10524 if (symtab == NULL)
10525 continue;
10526
10527 if (section->sh_link == elf_header.e_shstrndx)
c256ffe7
JJ
10528 {
10529 strtab = string_table;
10530 strtab_size = string_table_length;
10531 }
4fbb74a6 10532 else if (section->sh_link < elf_header.e_shnum)
252b5132 10533 {
2cf0635d 10534 Elf_Internal_Shdr * string_sec;
252b5132 10535
4fbb74a6 10536 string_sec = section_headers + section->sh_link;
252b5132 10537
3f5e193b
NC
10538 strtab = (char *) get_data (NULL, file, string_sec->sh_offset,
10539 1, string_sec->sh_size,
10540 _("string table"));
c256ffe7 10541 strtab_size = strtab != NULL ? string_sec->sh_size : 0;
252b5132
RH
10542 }
10543
ba5cdace 10544 for (si = 0, psym = symtab; si < num_syms; si++, psym++)
252b5132 10545 {
bb4d2ac2
L
10546 const char *version_string;
10547 enum versioned_symbol_info sym_info;
10548 unsigned short vna_other;
10549
5e220199 10550 printf ("%6d: ", si);
f7a99963
NC
10551 print_vma (psym->st_value, LONG_HEX);
10552 putchar (' ');
10553 print_vma (psym->st_size, DEC_5);
d1133906
NC
10554 printf (" %-7s", get_symbol_type (ELF_ST_TYPE (psym->st_info)));
10555 printf (" %-6s", get_symbol_binding (ELF_ST_BIND (psym->st_info)));
f4be36b3 10556 printf (" %-7s", get_symbol_visibility (ELF_ST_VISIBILITY (psym->st_other)));
5e2b0d47
NC
10557 /* Check to see if any other bits in the st_other field are set.
10558 Note - displaying this information disrupts the layout of the
10559 table being generated, but for the moment this case is very rare. */
10560 if (psym->st_other ^ ELF_ST_VISIBILITY (psym->st_other))
10561 printf (" [%s] ", get_symbol_other (psym->st_other ^ ELF_ST_VISIBILITY (psym->st_other)));
31104126 10562 printf (" %4s ", get_symbol_index_type (psym->st_shndx));
c256ffe7 10563 print_symbol (25, psym->st_name < strtab_size
2b692964 10564 ? strtab + psym->st_name : _("<corrupt>"));
252b5132 10565
bb4d2ac2
L
10566 version_string
10567 = get_symbol_version_string (file,
10568 section->sh_type == SHT_DYNSYM,
10569 strtab, strtab_size, si,
10570 psym, &sym_info, &vna_other);
10571 if (version_string)
252b5132 10572 {
bb4d2ac2
L
10573 if (sym_info == symbol_undefined)
10574 printf ("@%s (%d)", version_string, vna_other);
10575 else
10576 printf (sym_info == symbol_hidden ? "@%s" : "@@%s",
10577 version_string);
252b5132
RH
10578 }
10579
10580 putchar ('\n');
10581 }
10582
10583 free (symtab);
10584 if (strtab != string_table)
10585 free (strtab);
10586 }
10587 }
10588 else if (do_syms)
10589 printf
10590 (_("\nDynamic symbol information is not available for displaying symbols.\n"));
10591
10592 if (do_histogram && buckets != NULL)
10593 {
2cf0635d
NC
10594 unsigned long * lengths;
10595 unsigned long * counts;
66543521
AM
10596 unsigned long hn;
10597 bfd_vma si;
10598 unsigned long maxlength = 0;
10599 unsigned long nzero_counts = 0;
10600 unsigned long nsyms = 0;
252b5132 10601
66543521
AM
10602 printf (_("\nHistogram for bucket list length (total of %lu buckets):\n"),
10603 (unsigned long) nbuckets);
252b5132 10604
3f5e193b 10605 lengths = (unsigned long *) calloc (nbuckets, sizeof (*lengths));
252b5132
RH
10606 if (lengths == NULL)
10607 {
8b73c356 10608 error (_("Out of memory allocating space for histogram buckets\n"));
252b5132
RH
10609 return 0;
10610 }
8b73c356
NC
10611
10612 printf (_(" Length Number %% of total Coverage\n"));
252b5132
RH
10613 for (hn = 0; hn < nbuckets; ++hn)
10614 {
f7a99963 10615 for (si = buckets[hn]; si > 0 && si < nchains; si = chains[si])
252b5132 10616 {
b34976b6 10617 ++nsyms;
252b5132 10618 if (maxlength < ++lengths[hn])
b34976b6 10619 ++maxlength;
049b0c3a
NC
10620
10621 /* PR binutils/17531: A corrupt binary could contain broken
10622 histogram data. Do not go into an infinite loop trying
10623 to process it. */
10624 if (chains[si] == si)
10625 {
10626 error (_("histogram chain links to itself\n"));
10627 break;
10628 }
252b5132
RH
10629 }
10630 }
10631
3f5e193b 10632 counts = (unsigned long *) calloc (maxlength + 1, sizeof (*counts));
252b5132
RH
10633 if (counts == NULL)
10634 {
b2e951ec 10635 free (lengths);
8b73c356 10636 error (_("Out of memory allocating space for histogram counts\n"));
252b5132
RH
10637 return 0;
10638 }
10639
10640 for (hn = 0; hn < nbuckets; ++hn)
b34976b6 10641 ++counts[lengths[hn]];
252b5132 10642
103f02d3 10643 if (nbuckets > 0)
252b5132 10644 {
66543521
AM
10645 unsigned long i;
10646 printf (" 0 %-10lu (%5.1f%%)\n",
103f02d3 10647 counts[0], (counts[0] * 100.0) / nbuckets);
66543521 10648 for (i = 1; i <= maxlength; ++i)
103f02d3 10649 {
66543521
AM
10650 nzero_counts += counts[i] * i;
10651 printf ("%7lu %-10lu (%5.1f%%) %5.1f%%\n",
10652 i, counts[i], (counts[i] * 100.0) / nbuckets,
103f02d3
UD
10653 (nzero_counts * 100.0) / nsyms);
10654 }
252b5132
RH
10655 }
10656
10657 free (counts);
10658 free (lengths);
10659 }
10660
10661 if (buckets != NULL)
10662 {
10663 free (buckets);
10664 free (chains);
10665 }
10666
d3a44ec6 10667 if (do_histogram && gnubuckets != NULL)
fdc90cb4 10668 {
2cf0635d
NC
10669 unsigned long * lengths;
10670 unsigned long * counts;
fdc90cb4
JJ
10671 unsigned long hn;
10672 unsigned long maxlength = 0;
10673 unsigned long nzero_counts = 0;
10674 unsigned long nsyms = 0;
fdc90cb4 10675
8b73c356
NC
10676 printf (_("\nHistogram for `.gnu.hash' bucket list length (total of %lu buckets):\n"),
10677 (unsigned long) ngnubuckets);
10678
3f5e193b 10679 lengths = (unsigned long *) calloc (ngnubuckets, sizeof (*lengths));
fdc90cb4
JJ
10680 if (lengths == NULL)
10681 {
8b73c356 10682 error (_("Out of memory allocating space for gnu histogram buckets\n"));
fdc90cb4
JJ
10683 return 0;
10684 }
10685
fdc90cb4
JJ
10686 printf (_(" Length Number %% of total Coverage\n"));
10687
10688 for (hn = 0; hn < ngnubuckets; ++hn)
10689 if (gnubuckets[hn] != 0)
10690 {
10691 bfd_vma off, length = 1;
10692
6bd1a22c 10693 for (off = gnubuckets[hn] - gnusymidx;
071436c6
NC
10694 /* PR 17531 file: 010-77222-0.004. */
10695 off < ngnuchains && (gnuchains[off] & 1) == 0;
10696 ++off)
fdc90cb4
JJ
10697 ++length;
10698 lengths[hn] = length;
10699 if (length > maxlength)
10700 maxlength = length;
10701 nsyms += length;
10702 }
10703
3f5e193b 10704 counts = (unsigned long *) calloc (maxlength + 1, sizeof (*counts));
fdc90cb4
JJ
10705 if (counts == NULL)
10706 {
b2e951ec 10707 free (lengths);
8b73c356 10708 error (_("Out of memory allocating space for gnu histogram counts\n"));
fdc90cb4
JJ
10709 return 0;
10710 }
10711
10712 for (hn = 0; hn < ngnubuckets; ++hn)
10713 ++counts[lengths[hn]];
10714
10715 if (ngnubuckets > 0)
10716 {
10717 unsigned long j;
10718 printf (" 0 %-10lu (%5.1f%%)\n",
10719 counts[0], (counts[0] * 100.0) / ngnubuckets);
10720 for (j = 1; j <= maxlength; ++j)
10721 {
10722 nzero_counts += counts[j] * j;
10723 printf ("%7lu %-10lu (%5.1f%%) %5.1f%%\n",
10724 j, counts[j], (counts[j] * 100.0) / ngnubuckets,
10725 (nzero_counts * 100.0) / nsyms);
10726 }
10727 }
10728
10729 free (counts);
10730 free (lengths);
10731 free (gnubuckets);
10732 free (gnuchains);
10733 }
10734
252b5132
RH
10735 return 1;
10736}
10737
10738static int
2cf0635d 10739process_syminfo (FILE * file ATTRIBUTE_UNUSED)
252b5132 10740{
b4c96d0d 10741 unsigned int i;
252b5132
RH
10742
10743 if (dynamic_syminfo == NULL
10744 || !do_dynamic)
10745 /* No syminfo, this is ok. */
10746 return 1;
10747
10748 /* There better should be a dynamic symbol section. */
10749 if (dynamic_symbols == NULL || dynamic_strings == NULL)
10750 return 0;
10751
10752 if (dynamic_addr)
10753 printf (_("\nDynamic info segment at offset 0x%lx contains %d entries:\n"),
10754 dynamic_syminfo_offset, dynamic_syminfo_nent);
10755
10756 printf (_(" Num: Name BoundTo Flags\n"));
10757 for (i = 0; i < dynamic_syminfo_nent; ++i)
10758 {
10759 unsigned short int flags = dynamic_syminfo[i].si_flags;
10760
31104126 10761 printf ("%4d: ", i);
4082ef84
NC
10762 if (i >= num_dynamic_syms)
10763 printf (_("<corrupt index>"));
10764 else if (VALID_DYNAMIC_NAME (dynamic_symbols[i].st_name))
d79b3d50
NC
10765 print_symbol (30, GET_DYNAMIC_NAME (dynamic_symbols[i].st_name));
10766 else
2b692964 10767 printf (_("<corrupt: %19ld>"), dynamic_symbols[i].st_name);
31104126 10768 putchar (' ');
252b5132
RH
10769
10770 switch (dynamic_syminfo[i].si_boundto)
10771 {
10772 case SYMINFO_BT_SELF:
10773 fputs ("SELF ", stdout);
10774 break;
10775 case SYMINFO_BT_PARENT:
10776 fputs ("PARENT ", stdout);
10777 break;
10778 default:
10779 if (dynamic_syminfo[i].si_boundto > 0
d79b3d50
NC
10780 && dynamic_syminfo[i].si_boundto < dynamic_nent
10781 && VALID_DYNAMIC_NAME (dynamic_section[dynamic_syminfo[i].si_boundto].d_un.d_val))
31104126 10782 {
d79b3d50 10783 print_symbol (10, GET_DYNAMIC_NAME (dynamic_section[dynamic_syminfo[i].si_boundto].d_un.d_val));
31104126
NC
10784 putchar (' ' );
10785 }
252b5132
RH
10786 else
10787 printf ("%-10d ", dynamic_syminfo[i].si_boundto);
10788 break;
10789 }
10790
10791 if (flags & SYMINFO_FLG_DIRECT)
10792 printf (" DIRECT");
10793 if (flags & SYMINFO_FLG_PASSTHRU)
10794 printf (" PASSTHRU");
10795 if (flags & SYMINFO_FLG_COPY)
10796 printf (" COPY");
10797 if (flags & SYMINFO_FLG_LAZYLOAD)
10798 printf (" LAZYLOAD");
10799
10800 puts ("");
10801 }
10802
10803 return 1;
10804}
10805
cf13d699
NC
10806/* Check to see if the given reloc needs to be handled in a target specific
10807 manner. If so then process the reloc and return TRUE otherwise return
10808 FALSE. */
09c11c86 10809
cf13d699
NC
10810static bfd_boolean
10811target_specific_reloc_handling (Elf_Internal_Rela * reloc,
10812 unsigned char * start,
10813 Elf_Internal_Sym * symtab)
252b5132 10814{
cf13d699 10815 unsigned int reloc_type = get_reloc_type (reloc->r_info);
252b5132 10816
cf13d699 10817 switch (elf_header.e_machine)
252b5132 10818 {
13761a11
NC
10819 case EM_MSP430:
10820 case EM_MSP430_OLD:
10821 {
10822 static Elf_Internal_Sym * saved_sym = NULL;
10823
10824 switch (reloc_type)
10825 {
10826 case 10: /* R_MSP430_SYM_DIFF */
10827 if (uses_msp430x_relocs ())
10828 break;
10829 case 21: /* R_MSP430X_SYM_DIFF */
10830 saved_sym = symtab + get_reloc_symindex (reloc->r_info);
10831 return TRUE;
10832
10833 case 1: /* R_MSP430_32 or R_MSP430_ABS32 */
10834 case 3: /* R_MSP430_16 or R_MSP430_ABS8 */
10835 goto handle_sym_diff;
0b4362b0 10836
13761a11
NC
10837 case 5: /* R_MSP430_16_BYTE */
10838 case 9: /* R_MSP430_8 */
10839 if (uses_msp430x_relocs ())
10840 break;
10841 goto handle_sym_diff;
10842
10843 case 2: /* R_MSP430_ABS16 */
10844 case 15: /* R_MSP430X_ABS16 */
10845 if (! uses_msp430x_relocs ())
10846 break;
10847 goto handle_sym_diff;
0b4362b0 10848
13761a11
NC
10849 handle_sym_diff:
10850 if (saved_sym != NULL)
10851 {
10852 bfd_vma value;
10853
10854 value = reloc->r_addend
10855 + (symtab[get_reloc_symindex (reloc->r_info)].st_value
10856 - saved_sym->st_value);
10857
10858 byte_put (start + reloc->r_offset, value, reloc_type == 1 ? 4 : 2);
10859
10860 saved_sym = NULL;
10861 return TRUE;
10862 }
10863 break;
10864
10865 default:
10866 if (saved_sym != NULL)
071436c6 10867 error (_("Unhandled MSP430 reloc type found after SYM_DIFF reloc\n"));
13761a11
NC
10868 break;
10869 }
10870 break;
10871 }
10872
cf13d699
NC
10873 case EM_MN10300:
10874 case EM_CYGNUS_MN10300:
10875 {
10876 static Elf_Internal_Sym * saved_sym = NULL;
252b5132 10877
cf13d699
NC
10878 switch (reloc_type)
10879 {
10880 case 34: /* R_MN10300_ALIGN */
10881 return TRUE;
10882 case 33: /* R_MN10300_SYM_DIFF */
10883 saved_sym = symtab + get_reloc_symindex (reloc->r_info);
10884 return TRUE;
10885 case 1: /* R_MN10300_32 */
10886 case 2: /* R_MN10300_16 */
10887 if (saved_sym != NULL)
10888 {
10889 bfd_vma value;
252b5132 10890
cf13d699
NC
10891 value = reloc->r_addend
10892 + (symtab[get_reloc_symindex (reloc->r_info)].st_value
10893 - saved_sym->st_value);
252b5132 10894
cf13d699 10895 byte_put (start + reloc->r_offset, value, reloc_type == 1 ? 4 : 2);
252b5132 10896
cf13d699
NC
10897 saved_sym = NULL;
10898 return TRUE;
10899 }
10900 break;
10901 default:
10902 if (saved_sym != NULL)
071436c6 10903 error (_("Unhandled MN10300 reloc type found after SYM_DIFF reloc\n"));
cf13d699
NC
10904 break;
10905 }
10906 break;
10907 }
252b5132
RH
10908 }
10909
cf13d699 10910 return FALSE;
252b5132
RH
10911}
10912
aca88567
NC
10913/* Returns TRUE iff RELOC_TYPE is a 32-bit absolute RELA relocation used in
10914 DWARF debug sections. This is a target specific test. Note - we do not
10915 go through the whole including-target-headers-multiple-times route, (as
10916 we have already done with <elf/h8.h>) because this would become very
10917 messy and even then this function would have to contain target specific
10918 information (the names of the relocs instead of their numeric values).
10919 FIXME: This is not the correct way to solve this problem. The proper way
10920 is to have target specific reloc sizing and typing functions created by
10921 the reloc-macros.h header, in the same way that it already creates the
10922 reloc naming functions. */
10923
10924static bfd_boolean
10925is_32bit_abs_reloc (unsigned int reloc_type)
10926{
10927 switch (elf_header.e_machine)
10928 {
41e92641
NC
10929 case EM_386:
10930 case EM_486:
10931 return reloc_type == 1; /* R_386_32. */
aca88567
NC
10932 case EM_68K:
10933 return reloc_type == 1; /* R_68K_32. */
10934 case EM_860:
10935 return reloc_type == 1; /* R_860_32. */
137b6b5f
AM
10936 case EM_960:
10937 return reloc_type == 2; /* R_960_32. */
a06ea964
NC
10938 case EM_AARCH64:
10939 return reloc_type == 258; /* R_AARCH64_ABS32 */
aca88567 10940 case EM_ALPHA:
137b6b5f 10941 return reloc_type == 1; /* R_ALPHA_REFLONG. */
41e92641
NC
10942 case EM_ARC:
10943 return reloc_type == 1; /* R_ARC_32. */
10944 case EM_ARM:
10945 return reloc_type == 2; /* R_ARM_ABS32 */
cb8f3167 10946 case EM_AVR_OLD:
aca88567
NC
10947 case EM_AVR:
10948 return reloc_type == 1;
cfb8c092
NC
10949 case EM_ADAPTEVA_EPIPHANY:
10950 return reloc_type == 3;
aca88567
NC
10951 case EM_BLACKFIN:
10952 return reloc_type == 0x12; /* R_byte4_data. */
10953 case EM_CRIS:
10954 return reloc_type == 3; /* R_CRIS_32. */
10955 case EM_CR16:
10956 return reloc_type == 3; /* R_CR16_NUM32. */
10957 case EM_CRX:
10958 return reloc_type == 15; /* R_CRX_NUM32. */
10959 case EM_CYGNUS_FRV:
10960 return reloc_type == 1;
41e92641
NC
10961 case EM_CYGNUS_D10V:
10962 case EM_D10V:
10963 return reloc_type == 6; /* R_D10V_32. */
aca88567
NC
10964 case EM_CYGNUS_D30V:
10965 case EM_D30V:
10966 return reloc_type == 12; /* R_D30V_32_NORMAL. */
41e92641
NC
10967 case EM_DLX:
10968 return reloc_type == 3; /* R_DLX_RELOC_32. */
aca88567
NC
10969 case EM_CYGNUS_FR30:
10970 case EM_FR30:
10971 return reloc_type == 3; /* R_FR30_32. */
10972 case EM_H8S:
10973 case EM_H8_300:
10974 case EM_H8_300H:
10975 return reloc_type == 1; /* R_H8_DIR32. */
3730236a
NC
10976 case EM_IA_64:
10977 return reloc_type == 0x65; /* R_IA64_SECREL32LSB. */
aca88567
NC
10978 case EM_IP2K_OLD:
10979 case EM_IP2K:
10980 return reloc_type == 2; /* R_IP2K_32. */
10981 case EM_IQ2000:
10982 return reloc_type == 2; /* R_IQ2000_32. */
84e94c90
NC
10983 case EM_LATTICEMICO32:
10984 return reloc_type == 3; /* R_LM32_32. */
ff7eeb89 10985 case EM_M32C_OLD:
aca88567
NC
10986 case EM_M32C:
10987 return reloc_type == 3; /* R_M32C_32. */
10988 case EM_M32R:
10989 return reloc_type == 34; /* R_M32R_32_RELA. */
10990 case EM_MCORE:
10991 return reloc_type == 1; /* R_MCORE_ADDR32. */
10992 case EM_CYGNUS_MEP:
10993 return reloc_type == 4; /* R_MEP_32. */
a3c62988
NC
10994 case EM_METAG:
10995 return reloc_type == 2; /* R_METAG_ADDR32. */
137b6b5f
AM
10996 case EM_MICROBLAZE:
10997 return reloc_type == 1; /* R_MICROBLAZE_32. */
aca88567
NC
10998 case EM_MIPS:
10999 return reloc_type == 2; /* R_MIPS_32. */
11000 case EM_MMIX:
11001 return reloc_type == 4; /* R_MMIX_32. */
11002 case EM_CYGNUS_MN10200:
11003 case EM_MN10200:
11004 return reloc_type == 1; /* R_MN10200_32. */
11005 case EM_CYGNUS_MN10300:
11006 case EM_MN10300:
11007 return reloc_type == 1; /* R_MN10300_32. */
5506d11a
AM
11008 case EM_MOXIE:
11009 return reloc_type == 1; /* R_MOXIE_32. */
aca88567
NC
11010 case EM_MSP430_OLD:
11011 case EM_MSP430:
13761a11 11012 return reloc_type == 1; /* R_MSP430_32 or R_MSP320_ABS32. */
aca88567
NC
11013 case EM_MT:
11014 return reloc_type == 2; /* R_MT_32. */
35c08157
KLC
11015 case EM_NDS32:
11016 return reloc_type == 20; /* R_NDS32_RELA. */
3e0873ac 11017 case EM_ALTERA_NIOS2:
36591ba1 11018 return reloc_type == 12; /* R_NIOS2_BFD_RELOC_32. */
3e0873ac
NC
11019 case EM_NIOS32:
11020 return reloc_type == 1; /* R_NIOS_32. */
73589c9d
CS
11021 case EM_OR1K:
11022 return reloc_type == 1; /* R_OR1K_32. */
aca88567 11023 case EM_PARISC:
5fda8eca
NC
11024 return (reloc_type == 1 /* R_PARISC_DIR32. */
11025 || reloc_type == 41); /* R_PARISC_SECREL32. */
aca88567
NC
11026 case EM_PJ:
11027 case EM_PJ_OLD:
11028 return reloc_type == 1; /* R_PJ_DATA_DIR32. */
11029 case EM_PPC64:
11030 return reloc_type == 1; /* R_PPC64_ADDR32. */
11031 case EM_PPC:
11032 return reloc_type == 1; /* R_PPC_ADDR32. */
99c513f6
DD
11033 case EM_RL78:
11034 return reloc_type == 1; /* R_RL78_DIR32. */
c7927a3c
NC
11035 case EM_RX:
11036 return reloc_type == 1; /* R_RX_DIR32. */
aca88567
NC
11037 case EM_S370:
11038 return reloc_type == 1; /* R_I370_ADDR31. */
11039 case EM_S390_OLD:
11040 case EM_S390:
11041 return reloc_type == 4; /* R_S390_32. */
41e92641
NC
11042 case EM_SCORE:
11043 return reloc_type == 8; /* R_SCORE_ABS32. */
aca88567
NC
11044 case EM_SH:
11045 return reloc_type == 1; /* R_SH_DIR32. */
11046 case EM_SPARC32PLUS:
11047 case EM_SPARCV9:
11048 case EM_SPARC:
11049 return reloc_type == 3 /* R_SPARC_32. */
11050 || reloc_type == 23; /* R_SPARC_UA32. */
a7dd7d05
AM
11051 case EM_SPU:
11052 return reloc_type == 6; /* R_SPU_ADDR32 */
40b36596
JM
11053 case EM_TI_C6000:
11054 return reloc_type == 1; /* R_C6000_ABS32. */
aa137e4d
NC
11055 case EM_TILEGX:
11056 return reloc_type == 2; /* R_TILEGX_32. */
11057 case EM_TILEPRO:
11058 return reloc_type == 1; /* R_TILEPRO_32. */
aca88567
NC
11059 case EM_CYGNUS_V850:
11060 case EM_V850:
11061 return reloc_type == 6; /* R_V850_ABS32. */
708e2187
NC
11062 case EM_V800:
11063 return reloc_type == 0x33; /* R_V810_WORD. */
aca88567
NC
11064 case EM_VAX:
11065 return reloc_type == 1; /* R_VAX_32. */
11066 case EM_X86_64:
8a9036a4 11067 case EM_L1OM:
7a9068fe 11068 case EM_K1OM:
aca88567 11069 return reloc_type == 10; /* R_X86_64_32. */
c29aca4a
NC
11070 case EM_XC16X:
11071 case EM_C166:
11072 return reloc_type == 3; /* R_XC16C_ABS_32. */
f6c1a2d5
NC
11073 case EM_XGATE:
11074 return reloc_type == 4; /* R_XGATE_32. */
aca88567
NC
11075 case EM_XSTORMY16:
11076 return reloc_type == 1; /* R_XSTROMY16_32. */
11077 case EM_XTENSA_OLD:
11078 case EM_XTENSA:
11079 return reloc_type == 1; /* R_XTENSA_32. */
aca88567 11080 default:
bee0ee85
NC
11081 {
11082 static unsigned int prev_warn = 0;
11083
11084 /* Avoid repeating the same warning multiple times. */
11085 if (prev_warn != elf_header.e_machine)
11086 error (_("Missing knowledge of 32-bit reloc types used in DWARF sections of machine number %d\n"),
11087 elf_header.e_machine);
11088 prev_warn = elf_header.e_machine;
11089 return FALSE;
11090 }
aca88567
NC
11091 }
11092}
11093
11094/* Like is_32bit_abs_reloc except that it returns TRUE iff RELOC_TYPE is
11095 a 32-bit pc-relative RELA relocation used in DWARF debug sections. */
11096
11097static bfd_boolean
11098is_32bit_pcrel_reloc (unsigned int reloc_type)
11099{
11100 switch (elf_header.e_machine)
11101 {
41e92641
NC
11102 case EM_386:
11103 case EM_486:
3e0873ac 11104 return reloc_type == 2; /* R_386_PC32. */
aca88567 11105 case EM_68K:
3e0873ac 11106 return reloc_type == 4; /* R_68K_PC32. */
a06ea964
NC
11107 case EM_AARCH64:
11108 return reloc_type == 261; /* R_AARCH64_PREL32 */
cfb8c092
NC
11109 case EM_ADAPTEVA_EPIPHANY:
11110 return reloc_type == 6;
aca88567
NC
11111 case EM_ALPHA:
11112 return reloc_type == 10; /* R_ALPHA_SREL32. */
41e92641 11113 case EM_ARM:
3e0873ac 11114 return reloc_type == 3; /* R_ARM_REL32 */
137b6b5f
AM
11115 case EM_MICROBLAZE:
11116 return reloc_type == 2; /* R_MICROBLAZE_32_PCREL. */
73589c9d
CS
11117 case EM_OR1K:
11118 return reloc_type == 9; /* R_OR1K_32_PCREL. */
aca88567 11119 case EM_PARISC:
85acf597 11120 return reloc_type == 9; /* R_PARISC_PCREL32. */
aca88567
NC
11121 case EM_PPC:
11122 return reloc_type == 26; /* R_PPC_REL32. */
11123 case EM_PPC64:
3e0873ac 11124 return reloc_type == 26; /* R_PPC64_REL32. */
aca88567
NC
11125 case EM_S390_OLD:
11126 case EM_S390:
3e0873ac 11127 return reloc_type == 5; /* R_390_PC32. */
aca88567 11128 case EM_SH:
3e0873ac 11129 return reloc_type == 2; /* R_SH_REL32. */
aca88567
NC
11130 case EM_SPARC32PLUS:
11131 case EM_SPARCV9:
11132 case EM_SPARC:
3e0873ac 11133 return reloc_type == 6; /* R_SPARC_DISP32. */
a7dd7d05
AM
11134 case EM_SPU:
11135 return reloc_type == 13; /* R_SPU_REL32. */
aa137e4d
NC
11136 case EM_TILEGX:
11137 return reloc_type == 6; /* R_TILEGX_32_PCREL. */
11138 case EM_TILEPRO:
11139 return reloc_type == 4; /* R_TILEPRO_32_PCREL. */
aca88567 11140 case EM_X86_64:
8a9036a4 11141 case EM_L1OM:
7a9068fe 11142 case EM_K1OM:
3e0873ac 11143 return reloc_type == 2; /* R_X86_64_PC32. */
2fcb9706
BW
11144 case EM_XTENSA_OLD:
11145 case EM_XTENSA:
11146 return reloc_type == 14; /* R_XTENSA_32_PCREL. */
aca88567
NC
11147 default:
11148 /* Do not abort or issue an error message here. Not all targets use
11149 pc-relative 32-bit relocs in their DWARF debug information and we
11150 have already tested for target coverage in is_32bit_abs_reloc. A
cf13d699
NC
11151 more helpful warning message will be generated by apply_relocations
11152 anyway, so just return. */
aca88567
NC
11153 return FALSE;
11154 }
11155}
11156
11157/* Like is_32bit_abs_reloc except that it returns TRUE iff RELOC_TYPE is
11158 a 64-bit absolute RELA relocation used in DWARF debug sections. */
11159
11160static bfd_boolean
11161is_64bit_abs_reloc (unsigned int reloc_type)
11162{
11163 switch (elf_header.e_machine)
11164 {
a06ea964
NC
11165 case EM_AARCH64:
11166 return reloc_type == 257; /* R_AARCH64_ABS64. */
aca88567
NC
11167 case EM_ALPHA:
11168 return reloc_type == 2; /* R_ALPHA_REFQUAD. */
3730236a
NC
11169 case EM_IA_64:
11170 return reloc_type == 0x27; /* R_IA64_DIR64LSB. */
3e0873ac
NC
11171 case EM_PARISC:
11172 return reloc_type == 80; /* R_PARISC_DIR64. */
aca88567
NC
11173 case EM_PPC64:
11174 return reloc_type == 38; /* R_PPC64_ADDR64. */
11175 case EM_SPARC32PLUS:
11176 case EM_SPARCV9:
11177 case EM_SPARC:
11178 return reloc_type == 54; /* R_SPARC_UA64. */
11179 case EM_X86_64:
8a9036a4 11180 case EM_L1OM:
7a9068fe 11181 case EM_K1OM:
aca88567 11182 return reloc_type == 1; /* R_X86_64_64. */
e819ade1
AS
11183 case EM_S390_OLD:
11184 case EM_S390:
aa137e4d
NC
11185 return reloc_type == 22; /* R_S390_64. */
11186 case EM_TILEGX:
11187 return reloc_type == 1; /* R_TILEGX_64. */
85a82265 11188 case EM_MIPS:
aa137e4d 11189 return reloc_type == 18; /* R_MIPS_64. */
aca88567
NC
11190 default:
11191 return FALSE;
11192 }
11193}
11194
85acf597
RH
11195/* Like is_32bit_pcrel_reloc except that it returns TRUE iff RELOC_TYPE is
11196 a 64-bit pc-relative RELA relocation used in DWARF debug sections. */
11197
11198static bfd_boolean
11199is_64bit_pcrel_reloc (unsigned int reloc_type)
11200{
11201 switch (elf_header.e_machine)
11202 {
a06ea964
NC
11203 case EM_AARCH64:
11204 return reloc_type == 260; /* R_AARCH64_PREL64. */
85acf597 11205 case EM_ALPHA:
aa137e4d 11206 return reloc_type == 11; /* R_ALPHA_SREL64. */
85acf597 11207 case EM_IA_64:
aa137e4d 11208 return reloc_type == 0x4f; /* R_IA64_PCREL64LSB. */
85acf597 11209 case EM_PARISC:
aa137e4d 11210 return reloc_type == 72; /* R_PARISC_PCREL64. */
85acf597 11211 case EM_PPC64:
aa137e4d 11212 return reloc_type == 44; /* R_PPC64_REL64. */
85acf597
RH
11213 case EM_SPARC32PLUS:
11214 case EM_SPARCV9:
11215 case EM_SPARC:
aa137e4d 11216 return reloc_type == 46; /* R_SPARC_DISP64. */
85acf597 11217 case EM_X86_64:
8a9036a4 11218 case EM_L1OM:
7a9068fe 11219 case EM_K1OM:
aa137e4d 11220 return reloc_type == 24; /* R_X86_64_PC64. */
85acf597
RH
11221 case EM_S390_OLD:
11222 case EM_S390:
aa137e4d
NC
11223 return reloc_type == 23; /* R_S390_PC64. */
11224 case EM_TILEGX:
11225 return reloc_type == 5; /* R_TILEGX_64_PCREL. */
85acf597
RH
11226 default:
11227 return FALSE;
11228 }
11229}
11230
4dc3c23d
AM
11231/* Like is_32bit_abs_reloc except that it returns TRUE iff RELOC_TYPE is
11232 a 24-bit absolute RELA relocation used in DWARF debug sections. */
11233
11234static bfd_boolean
11235is_24bit_abs_reloc (unsigned int reloc_type)
11236{
11237 switch (elf_header.e_machine)
11238 {
11239 case EM_CYGNUS_MN10200:
11240 case EM_MN10200:
11241 return reloc_type == 4; /* R_MN10200_24. */
11242 default:
11243 return FALSE;
11244 }
11245}
11246
aca88567
NC
11247/* Like is_32bit_abs_reloc except that it returns TRUE iff RELOC_TYPE is
11248 a 16-bit absolute RELA relocation used in DWARF debug sections. */
11249
11250static bfd_boolean
11251is_16bit_abs_reloc (unsigned int reloc_type)
4b78141a
NC
11252{
11253 switch (elf_header.e_machine)
11254 {
aca88567
NC
11255 case EM_AVR_OLD:
11256 case EM_AVR:
11257 return reloc_type == 4; /* R_AVR_16. */
cfb8c092
NC
11258 case EM_ADAPTEVA_EPIPHANY:
11259 return reloc_type == 5;
41e92641
NC
11260 case EM_CYGNUS_D10V:
11261 case EM_D10V:
11262 return reloc_type == 3; /* R_D10V_16. */
4b78141a
NC
11263 case EM_H8S:
11264 case EM_H8_300:
11265 case EM_H8_300H:
aca88567
NC
11266 return reloc_type == R_H8_DIR16;
11267 case EM_IP2K_OLD:
11268 case EM_IP2K:
11269 return reloc_type == 1; /* R_IP2K_16. */
ff7eeb89 11270 case EM_M32C_OLD:
f4236fe4
DD
11271 case EM_M32C:
11272 return reloc_type == 1; /* R_M32C_16 */
aca88567 11273 case EM_MSP430:
13761a11
NC
11274 if (uses_msp430x_relocs ())
11275 return reloc_type == 2; /* R_MSP430_ABS16. */
78c8d46c 11276 case EM_MSP430_OLD:
aca88567 11277 return reloc_type == 5; /* R_MSP430_16_BYTE. */
35c08157
KLC
11278 case EM_NDS32:
11279 return reloc_type == 19; /* R_NDS32_RELA. */
3e0873ac 11280 case EM_ALTERA_NIOS2:
36591ba1 11281 return reloc_type == 13; /* R_NIOS2_BFD_RELOC_16. */
3e0873ac
NC
11282 case EM_NIOS32:
11283 return reloc_type == 9; /* R_NIOS_16. */
73589c9d
CS
11284 case EM_OR1K:
11285 return reloc_type == 2; /* R_OR1K_16. */
40b36596
JM
11286 case EM_TI_C6000:
11287 return reloc_type == 2; /* R_C6000_ABS16. */
c29aca4a
NC
11288 case EM_XC16X:
11289 case EM_C166:
11290 return reloc_type == 2; /* R_XC16C_ABS_16. */
e63734a3
AM
11291 case EM_CYGNUS_MN10200:
11292 case EM_MN10200:
11293 return reloc_type == 2; /* R_MN10200_16. */
0a22ae8e
NC
11294 case EM_CYGNUS_MN10300:
11295 case EM_MN10300:
11296 return reloc_type == 2; /* R_MN10300_16. */
f6c1a2d5
NC
11297 case EM_XGATE:
11298 return reloc_type == 3; /* R_XGATE_16. */
4b78141a 11299 default:
aca88567 11300 return FALSE;
4b78141a
NC
11301 }
11302}
11303
2a7b2e88
JK
11304/* Returns TRUE iff RELOC_TYPE is a NONE relocation used for discarded
11305 relocation entries (possibly formerly used for SHT_GROUP sections). */
11306
11307static bfd_boolean
11308is_none_reloc (unsigned int reloc_type)
11309{
11310 switch (elf_header.e_machine)
11311 {
cb8f3167
NC
11312 case EM_68K: /* R_68K_NONE. */
11313 case EM_386: /* R_386_NONE. */
2a7b2e88
JK
11314 case EM_SPARC32PLUS:
11315 case EM_SPARCV9:
cb8f3167
NC
11316 case EM_SPARC: /* R_SPARC_NONE. */
11317 case EM_MIPS: /* R_MIPS_NONE. */
11318 case EM_PARISC: /* R_PARISC_NONE. */
11319 case EM_ALPHA: /* R_ALPHA_NONE. */
cfb8c092 11320 case EM_ADAPTEVA_EPIPHANY:
cb8f3167
NC
11321 case EM_PPC: /* R_PPC_NONE. */
11322 case EM_PPC64: /* R_PPC64_NONE. */
11323 case EM_ARM: /* R_ARM_NONE. */
11324 case EM_IA_64: /* R_IA64_NONE. */
11325 case EM_SH: /* R_SH_NONE. */
2a7b2e88 11326 case EM_S390_OLD:
cb8f3167
NC
11327 case EM_S390: /* R_390_NONE. */
11328 case EM_CRIS: /* R_CRIS_NONE. */
11329 case EM_X86_64: /* R_X86_64_NONE. */
8a9036a4 11330 case EM_L1OM: /* R_X86_64_NONE. */
7a9068fe 11331 case EM_K1OM: /* R_X86_64_NONE. */
cb8f3167 11332 case EM_MN10300: /* R_MN10300_NONE. */
5506d11a 11333 case EM_MOXIE: /* R_MOXIE_NONE. */
cb8f3167 11334 case EM_M32R: /* R_M32R_NONE. */
40b36596 11335 case EM_TI_C6000:/* R_C6000_NONE. */
aa137e4d
NC
11336 case EM_TILEGX: /* R_TILEGX_NONE. */
11337 case EM_TILEPRO: /* R_TILEPRO_NONE. */
c29aca4a
NC
11338 case EM_XC16X:
11339 case EM_C166: /* R_XC16X_NONE. */
36591ba1
SL
11340 case EM_ALTERA_NIOS2: /* R_NIOS2_NONE. */
11341 case EM_NIOS32: /* R_NIOS_NONE. */
73589c9d 11342 case EM_OR1K: /* R_OR1K_NONE. */
cb8f3167 11343 return reloc_type == 0;
a06ea964
NC
11344 case EM_AARCH64:
11345 return reloc_type == 0 || reloc_type == 256;
35c08157
KLC
11346 case EM_NDS32:
11347 return (reloc_type == 0 /* R_XTENSA_NONE. */
11348 || reloc_type == 204 /* R_NDS32_DIFF8. */
11349 || reloc_type == 205 /* R_NDS32_DIFF16. */
11350 || reloc_type == 206 /* R_NDS32_DIFF32. */
11351 || reloc_type == 207 /* R_NDS32_ULEB128. */);
58332dda
JK
11352 case EM_XTENSA_OLD:
11353 case EM_XTENSA:
4dc3c23d
AM
11354 return (reloc_type == 0 /* R_XTENSA_NONE. */
11355 || reloc_type == 17 /* R_XTENSA_DIFF8. */
11356 || reloc_type == 18 /* R_XTENSA_DIFF16. */
11357 || reloc_type == 19 /* R_XTENSA_DIFF32. */);
a3c62988
NC
11358 case EM_METAG:
11359 return reloc_type == 3; /* R_METAG_NONE. */
2a7b2e88
JK
11360 }
11361 return FALSE;
11362}
11363
cf13d699
NC
11364/* Apply relocations to a section.
11365 Note: So far support has been added only for those relocations
11366 which can be found in debug sections.
11367 FIXME: Add support for more relocations ? */
1b315056 11368
cf13d699
NC
11369static void
11370apply_relocations (void * file,
11371 Elf_Internal_Shdr * section,
11372 unsigned char * start)
1b315056 11373{
cf13d699
NC
11374 Elf_Internal_Shdr * relsec;
11375 unsigned char * end = start + section->sh_size;
cb8f3167 11376
cf13d699
NC
11377 if (elf_header.e_type != ET_REL)
11378 return;
1b315056 11379
cf13d699 11380 /* Find the reloc section associated with the section. */
5b18a4bc
NC
11381 for (relsec = section_headers;
11382 relsec < section_headers + elf_header.e_shnum;
11383 ++relsec)
252b5132 11384 {
41e92641
NC
11385 bfd_boolean is_rela;
11386 unsigned long num_relocs;
2cf0635d
NC
11387 Elf_Internal_Rela * relocs;
11388 Elf_Internal_Rela * rp;
11389 Elf_Internal_Shdr * symsec;
11390 Elf_Internal_Sym * symtab;
ba5cdace 11391 unsigned long num_syms;
2cf0635d 11392 Elf_Internal_Sym * sym;
252b5132 11393
41e92641 11394 if ((relsec->sh_type != SHT_RELA && relsec->sh_type != SHT_REL)
4fbb74a6
AM
11395 || relsec->sh_info >= elf_header.e_shnum
11396 || section_headers + relsec->sh_info != section
c256ffe7 11397 || relsec->sh_size == 0
4fbb74a6 11398 || relsec->sh_link >= elf_header.e_shnum)
5b18a4bc 11399 continue;
428409d5 11400
41e92641
NC
11401 is_rela = relsec->sh_type == SHT_RELA;
11402
11403 if (is_rela)
11404 {
3f5e193b
NC
11405 if (!slurp_rela_relocs ((FILE *) file, relsec->sh_offset,
11406 relsec->sh_size, & relocs, & num_relocs))
41e92641
NC
11407 return;
11408 }
11409 else
11410 {
3f5e193b
NC
11411 if (!slurp_rel_relocs ((FILE *) file, relsec->sh_offset,
11412 relsec->sh_size, & relocs, & num_relocs))
41e92641
NC
11413 return;
11414 }
11415
11416 /* SH uses RELA but uses in place value instead of the addend field. */
11417 if (elf_header.e_machine == EM_SH)
11418 is_rela = FALSE;
428409d5 11419
4fbb74a6 11420 symsec = section_headers + relsec->sh_link;
ba5cdace 11421 symtab = GET_ELF_SYMBOLS ((FILE *) file, symsec, & num_syms);
103f02d3 11422
41e92641 11423 for (rp = relocs; rp < relocs + num_relocs; ++rp)
252b5132 11424 {
41e92641
NC
11425 bfd_vma addend;
11426 unsigned int reloc_type;
11427 unsigned int reloc_size;
91d6fa6a 11428 unsigned char * rloc;
ba5cdace 11429 unsigned long sym_index;
4b78141a 11430
aca88567 11431 reloc_type = get_reloc_type (rp->r_info);
41e92641 11432
98fb390a 11433 if (target_specific_reloc_handling (rp, start, symtab))
2a7b2e88 11434 continue;
98fb390a
NC
11435 else if (is_none_reloc (reloc_type))
11436 continue;
11437 else if (is_32bit_abs_reloc (reloc_type)
11438 || is_32bit_pcrel_reloc (reloc_type))
aca88567 11439 reloc_size = 4;
85acf597
RH
11440 else if (is_64bit_abs_reloc (reloc_type)
11441 || is_64bit_pcrel_reloc (reloc_type))
aca88567 11442 reloc_size = 8;
4dc3c23d
AM
11443 else if (is_24bit_abs_reloc (reloc_type))
11444 reloc_size = 3;
aca88567
NC
11445 else if (is_16bit_abs_reloc (reloc_type))
11446 reloc_size = 2;
11447 else
4b78141a 11448 {
bee0ee85
NC
11449 static unsigned int prev_reloc = 0;
11450 if (reloc_type != prev_reloc)
11451 warn (_("unable to apply unsupported reloc type %d to section %s\n"),
11452 reloc_type, printable_section_name (section));
11453 prev_reloc = reloc_type;
4b78141a
NC
11454 continue;
11455 }
103f02d3 11456
91d6fa6a 11457 rloc = start + rp->r_offset;
c8da6823 11458 if ((rloc + reloc_size) > end || (rloc < start))
700dd8b7
L
11459 {
11460 warn (_("skipping invalid relocation offset 0x%lx in section %s\n"),
11461 (unsigned long) rp->r_offset,
74e1a04b 11462 printable_section_name (section));
700dd8b7
L
11463 continue;
11464 }
103f02d3 11465
ba5cdace
NC
11466 sym_index = (unsigned long) get_reloc_symindex (rp->r_info);
11467 if (sym_index >= num_syms)
11468 {
11469 warn (_("skipping invalid relocation symbol index 0x%lx in section %s\n"),
74e1a04b 11470 sym_index, printable_section_name (section));
ba5cdace
NC
11471 continue;
11472 }
11473 sym = symtab + sym_index;
41e92641
NC
11474
11475 /* If the reloc has a symbol associated with it,
55f25fc3
L
11476 make sure that it is of an appropriate type.
11477
11478 Relocations against symbols without type can happen.
11479 Gcc -feliminate-dwarf2-dups may generate symbols
11480 without type for debug info.
11481
11482 Icc generates relocations against function symbols
11483 instead of local labels.
11484
11485 Relocations against object symbols can happen, eg when
11486 referencing a global array. For an example of this see
11487 the _clz.o binary in libgcc.a. */
aca88567 11488 if (sym != symtab
55f25fc3 11489 && ELF_ST_TYPE (sym->st_info) > STT_SECTION)
5b18a4bc 11490 {
41e92641 11491 warn (_("skipping unexpected symbol type %s in %ld'th relocation in section %s\n"),
aca88567 11492 get_symbol_type (ELF_ST_TYPE (sym->st_info)),
99dcb0b9 11493 (long int)(rp - relocs),
74e1a04b 11494 printable_section_name (relsec));
aca88567 11495 continue;
5b18a4bc 11496 }
252b5132 11497
4dc3c23d
AM
11498 addend = 0;
11499 if (is_rela)
11500 addend += rp->r_addend;
c47320c3
AM
11501 /* R_XTENSA_32, R_PJ_DATA_DIR32 and R_D30V_32_NORMAL are
11502 partial_inplace. */
4dc3c23d
AM
11503 if (!is_rela
11504 || (elf_header.e_machine == EM_XTENSA
11505 && reloc_type == 1)
11506 || ((elf_header.e_machine == EM_PJ
11507 || elf_header.e_machine == EM_PJ_OLD)
c47320c3
AM
11508 && reloc_type == 1)
11509 || ((elf_header.e_machine == EM_D30V
11510 || elf_header.e_machine == EM_CYGNUS_D30V)
11511 && reloc_type == 12))
91d6fa6a 11512 addend += byte_get (rloc, reloc_size);
cb8f3167 11513
85acf597
RH
11514 if (is_32bit_pcrel_reloc (reloc_type)
11515 || is_64bit_pcrel_reloc (reloc_type))
11516 {
11517 /* On HPPA, all pc-relative relocations are biased by 8. */
11518 if (elf_header.e_machine == EM_PARISC)
11519 addend -= 8;
91d6fa6a 11520 byte_put (rloc, (addend + sym->st_value) - rp->r_offset,
85acf597
RH
11521 reloc_size);
11522 }
41e92641 11523 else
91d6fa6a 11524 byte_put (rloc, addend + sym->st_value, reloc_size);
5b18a4bc 11525 }
252b5132 11526
5b18a4bc 11527 free (symtab);
41e92641 11528 free (relocs);
5b18a4bc
NC
11529 break;
11530 }
5b18a4bc 11531}
103f02d3 11532
cf13d699
NC
11533#ifdef SUPPORT_DISASSEMBLY
11534static int
11535disassemble_section (Elf_Internal_Shdr * section, FILE * file)
11536{
74e1a04b 11537 printf (_("\nAssembly dump of section %s\n"), printable_section_name (section));
cf13d699 11538
74e1a04b 11539 /* FIXME: XXX -- to be done --- XXX */
cf13d699
NC
11540
11541 return 1;
11542}
11543#endif
11544
11545/* Reads in the contents of SECTION from FILE, returning a pointer
11546 to a malloc'ed buffer or NULL if something went wrong. */
11547
11548static char *
11549get_section_contents (Elf_Internal_Shdr * section, FILE * file)
11550{
11551 bfd_size_type num_bytes;
11552
11553 num_bytes = section->sh_size;
11554
11555 if (num_bytes == 0 || section->sh_type == SHT_NOBITS)
11556 {
11557 printf (_("\nSection '%s' has no data to dump.\n"),
74e1a04b 11558 printable_section_name (section));
cf13d699
NC
11559 return NULL;
11560 }
11561
3f5e193b
NC
11562 return (char *) get_data (NULL, file, section->sh_offset, 1, num_bytes,
11563 _("section contents"));
cf13d699
NC
11564}
11565
dd24e3da 11566
cf13d699
NC
11567static void
11568dump_section_as_strings (Elf_Internal_Shdr * section, FILE * file)
11569{
11570 Elf_Internal_Shdr * relsec;
11571 bfd_size_type num_bytes;
cf13d699
NC
11572 char * data;
11573 char * end;
11574 char * start;
cf13d699
NC
11575 bfd_boolean some_strings_shown;
11576
11577 start = get_section_contents (section, file);
11578 if (start == NULL)
11579 return;
11580
74e1a04b 11581 printf (_("\nString dump of section '%s':\n"), printable_section_name (section));
cf13d699
NC
11582
11583 /* If the section being dumped has relocations against it the user might
11584 be expecting these relocations to have been applied. Check for this
11585 case and issue a warning message in order to avoid confusion.
11586 FIXME: Maybe we ought to have an option that dumps a section with
11587 relocs applied ? */
11588 for (relsec = section_headers;
11589 relsec < section_headers + elf_header.e_shnum;
11590 ++relsec)
11591 {
11592 if ((relsec->sh_type != SHT_RELA && relsec->sh_type != SHT_REL)
11593 || relsec->sh_info >= elf_header.e_shnum
11594 || section_headers + relsec->sh_info != section
11595 || relsec->sh_size == 0
11596 || relsec->sh_link >= elf_header.e_shnum)
11597 continue;
11598
11599 printf (_(" Note: This section has relocations against it, but these have NOT been applied to this dump.\n"));
11600 break;
11601 }
11602
11603 num_bytes = section->sh_size;
cf13d699
NC
11604 data = start;
11605 end = start + num_bytes;
11606 some_strings_shown = FALSE;
11607
11608 while (data < end)
11609 {
11610 while (!ISPRINT (* data))
11611 if (++ data >= end)
11612 break;
11613
11614 if (data < end)
11615 {
071436c6
NC
11616 size_t maxlen = end - data;
11617
cf13d699 11618#ifndef __MSVCRT__
c975cc98
NC
11619 /* PR 11128: Use two separate invocations in order to work
11620 around bugs in the Solaris 8 implementation of printf. */
11621 printf (" [%6tx] ", data - start);
cf13d699 11622#else
071436c6 11623 printf (" [%6Ix] ", (size_t) (data - start));
cf13d699 11624#endif
4082ef84
NC
11625 if (maxlen > 0)
11626 {
11627 print_symbol ((int) maxlen, data);
11628 putchar ('\n');
11629 data += strnlen (data, maxlen);
11630 }
11631 else
11632 {
11633 printf (_("<corrupt>\n"));
11634 data = end;
11635 }
cf13d699
NC
11636 some_strings_shown = TRUE;
11637 }
11638 }
11639
11640 if (! some_strings_shown)
11641 printf (_(" No strings found in this section."));
11642
11643 free (start);
11644
11645 putchar ('\n');
11646}
11647
11648static void
11649dump_section_as_bytes (Elf_Internal_Shdr * section,
11650 FILE * file,
11651 bfd_boolean relocate)
11652{
11653 Elf_Internal_Shdr * relsec;
11654 bfd_size_type bytes;
11655 bfd_vma addr;
11656 unsigned char * data;
11657 unsigned char * start;
11658
11659 start = (unsigned char *) get_section_contents (section, file);
11660 if (start == NULL)
11661 return;
11662
74e1a04b 11663 printf (_("\nHex dump of section '%s':\n"), printable_section_name (section));
cf13d699
NC
11664
11665 if (relocate)
11666 {
11667 apply_relocations (file, section, start);
11668 }
11669 else
11670 {
11671 /* If the section being dumped has relocations against it the user might
11672 be expecting these relocations to have been applied. Check for this
11673 case and issue a warning message in order to avoid confusion.
11674 FIXME: Maybe we ought to have an option that dumps a section with
11675 relocs applied ? */
11676 for (relsec = section_headers;
11677 relsec < section_headers + elf_header.e_shnum;
11678 ++relsec)
11679 {
11680 if ((relsec->sh_type != SHT_RELA && relsec->sh_type != SHT_REL)
11681 || relsec->sh_info >= elf_header.e_shnum
11682 || section_headers + relsec->sh_info != section
11683 || relsec->sh_size == 0
11684 || relsec->sh_link >= elf_header.e_shnum)
11685 continue;
11686
11687 printf (_(" NOTE: This section has relocations against it, but these have NOT been applied to this dump.\n"));
11688 break;
11689 }
11690 }
11691
11692 addr = section->sh_addr;
11693 bytes = section->sh_size;
11694 data = start;
11695
11696 while (bytes)
11697 {
11698 int j;
11699 int k;
11700 int lbytes;
11701
11702 lbytes = (bytes > 16 ? 16 : bytes);
11703
11704 printf (" 0x%8.8lx ", (unsigned long) addr);
11705
11706 for (j = 0; j < 16; j++)
11707 {
11708 if (j < lbytes)
11709 printf ("%2.2x", data[j]);
11710 else
11711 printf (" ");
11712
11713 if ((j & 3) == 3)
11714 printf (" ");
11715 }
11716
11717 for (j = 0; j < lbytes; j++)
11718 {
11719 k = data[j];
11720 if (k >= ' ' && k < 0x7f)
11721 printf ("%c", k);
11722 else
11723 printf (".");
11724 }
11725
11726 putchar ('\n');
11727
11728 data += lbytes;
11729 addr += lbytes;
11730 bytes -= lbytes;
11731 }
11732
11733 free (start);
11734
11735 putchar ('\n');
11736}
11737
4a114e3e 11738/* Uncompresses a section that was compressed using zlib, in place. */
cf13d699
NC
11739
11740static int
d3dbc530
AM
11741uncompress_section_contents (unsigned char **buffer ATTRIBUTE_UNUSED,
11742 dwarf_size_type *size ATTRIBUTE_UNUSED)
cf13d699
NC
11743{
11744#ifndef HAVE_ZLIB_H
cf13d699
NC
11745 return FALSE;
11746#else
11747 dwarf_size_type compressed_size = *size;
11748 unsigned char * compressed_buffer = *buffer;
11749 dwarf_size_type uncompressed_size;
11750 unsigned char * uncompressed_buffer;
11751 z_stream strm;
11752 int rc;
11753 dwarf_size_type header_size = 12;
11754
11755 /* Read the zlib header. In this case, it should be "ZLIB" followed
11756 by the uncompressed section size, 8 bytes in big-endian order. */
11757 if (compressed_size < header_size
11758 || ! streq ((char *) compressed_buffer, "ZLIB"))
11759 return 0;
11760
11761 uncompressed_size = compressed_buffer[4]; uncompressed_size <<= 8;
11762 uncompressed_size += compressed_buffer[5]; uncompressed_size <<= 8;
11763 uncompressed_size += compressed_buffer[6]; uncompressed_size <<= 8;
11764 uncompressed_size += compressed_buffer[7]; uncompressed_size <<= 8;
11765 uncompressed_size += compressed_buffer[8]; uncompressed_size <<= 8;
11766 uncompressed_size += compressed_buffer[9]; uncompressed_size <<= 8;
11767 uncompressed_size += compressed_buffer[10]; uncompressed_size <<= 8;
11768 uncompressed_size += compressed_buffer[11];
11769
11770 /* It is possible the section consists of several compressed
11771 buffers concatenated together, so we uncompress in a loop. */
11772 strm.zalloc = NULL;
11773 strm.zfree = NULL;
11774 strm.opaque = NULL;
11775 strm.avail_in = compressed_size - header_size;
11776 strm.next_in = (Bytef *) compressed_buffer + header_size;
11777 strm.avail_out = uncompressed_size;
3f5e193b 11778 uncompressed_buffer = (unsigned char *) xmalloc (uncompressed_size);
cf13d699
NC
11779
11780 rc = inflateInit (& strm);
11781 while (strm.avail_in > 0)
11782 {
11783 if (rc != Z_OK)
11784 goto fail;
11785 strm.next_out = ((Bytef *) uncompressed_buffer
11786 + (uncompressed_size - strm.avail_out));
11787 rc = inflate (&strm, Z_FINISH);
11788 if (rc != Z_STREAM_END)
11789 goto fail;
11790 rc = inflateReset (& strm);
11791 }
11792 rc = inflateEnd (& strm);
11793 if (rc != Z_OK
11794 || strm.avail_out != 0)
11795 goto fail;
11796
11797 free (compressed_buffer);
11798 *buffer = uncompressed_buffer;
11799 *size = uncompressed_size;
11800 return 1;
11801
11802 fail:
11803 free (uncompressed_buffer);
4a114e3e
L
11804 /* Indicate decompression failure. */
11805 *buffer = NULL;
cf13d699
NC
11806 return 0;
11807#endif /* HAVE_ZLIB_H */
11808}
11809
d966045b
DJ
11810static int
11811load_specific_debug_section (enum dwarf_section_display_enum debug,
2cf0635d 11812 Elf_Internal_Shdr * sec, void * file)
1007acb3 11813{
2cf0635d 11814 struct dwarf_section * section = &debug_displays [debug].section;
19e6b90e 11815 char buf [64];
1007acb3 11816
19e6b90e
L
11817 /* If it is already loaded, do nothing. */
11818 if (section->start != NULL)
11819 return 1;
1007acb3 11820
19e6b90e
L
11821 snprintf (buf, sizeof (buf), _("%s section data"), section->name);
11822 section->address = sec->sh_addr;
06614111 11823 section->user_data = NULL;
3f5e193b
NC
11824 section->start = (unsigned char *) get_data (NULL, (FILE *) file,
11825 sec->sh_offset, 1,
11826 sec->sh_size, buf);
59245841
NC
11827 if (section->start == NULL)
11828 section->size = 0;
11829 else
11830 {
11831 section->size = sec->sh_size;
11832 if (uncompress_section_contents (&section->start, &section->size))
11833 sec->sh_size = section->size;
11834 }
4a114e3e 11835
1b315056
CS
11836 if (section->start == NULL)
11837 return 0;
11838
19e6b90e 11839 if (debug_displays [debug].relocate)
3f5e193b 11840 apply_relocations ((FILE *) file, sec, section->start);
1007acb3 11841
1b315056 11842 return 1;
1007acb3
L
11843}
11844
657d0d47
CC
11845/* If this is not NULL, load_debug_section will only look for sections
11846 within the list of sections given here. */
11847unsigned int *section_subset = NULL;
11848
d966045b 11849int
2cf0635d 11850load_debug_section (enum dwarf_section_display_enum debug, void * file)
d966045b 11851{
2cf0635d
NC
11852 struct dwarf_section * section = &debug_displays [debug].section;
11853 Elf_Internal_Shdr * sec;
d966045b
DJ
11854
11855 /* Locate the debug section. */
657d0d47 11856 sec = find_section_in_set (section->uncompressed_name, section_subset);
d966045b
DJ
11857 if (sec != NULL)
11858 section->name = section->uncompressed_name;
11859 else
11860 {
657d0d47 11861 sec = find_section_in_set (section->compressed_name, section_subset);
d966045b
DJ
11862 if (sec != NULL)
11863 section->name = section->compressed_name;
11864 }
11865 if (sec == NULL)
11866 return 0;
11867
657d0d47
CC
11868 /* If we're loading from a subset of sections, and we've loaded
11869 a section matching this name before, it's likely that it's a
11870 different one. */
11871 if (section_subset != NULL)
11872 free_debug_section (debug);
11873
3f5e193b 11874 return load_specific_debug_section (debug, sec, (FILE *) file);
d966045b
DJ
11875}
11876
19e6b90e
L
11877void
11878free_debug_section (enum dwarf_section_display_enum debug)
1007acb3 11879{
2cf0635d 11880 struct dwarf_section * section = &debug_displays [debug].section;
1007acb3 11881
19e6b90e
L
11882 if (section->start == NULL)
11883 return;
1007acb3 11884
19e6b90e
L
11885 free ((char *) section->start);
11886 section->start = NULL;
11887 section->address = 0;
11888 section->size = 0;
1007acb3
L
11889}
11890
1007acb3 11891static int
657d0d47 11892display_debug_section (int shndx, Elf_Internal_Shdr * section, FILE * file)
1007acb3 11893{
2cf0635d 11894 char * name = SECTION_NAME (section);
74e1a04b 11895 const char * print_name = printable_section_name (section);
19e6b90e
L
11896 bfd_size_type length;
11897 int result = 1;
3f5e193b 11898 int i;
1007acb3 11899
19e6b90e
L
11900 length = section->sh_size;
11901 if (length == 0)
1007acb3 11902 {
74e1a04b 11903 printf (_("\nSection '%s' has no debugging data.\n"), print_name);
19e6b90e 11904 return 0;
1007acb3 11905 }
5dff79d8
NC
11906 if (section->sh_type == SHT_NOBITS)
11907 {
11908 /* There is no point in dumping the contents of a debugging section
11909 which has the NOBITS type - the bits in the file will be random.
11910 This can happen when a file containing a .eh_frame section is
11911 stripped with the --only-keep-debug command line option. */
74e1a04b
NC
11912 printf (_("section '%s' has the NOBITS type - its contents are unreliable.\n"),
11913 print_name);
5dff79d8
NC
11914 return 0;
11915 }
1007acb3 11916
0112cd26 11917 if (const_strneq (name, ".gnu.linkonce.wi."))
19e6b90e 11918 name = ".debug_info";
1007acb3 11919
19e6b90e
L
11920 /* See if we know how to display the contents of this section. */
11921 for (i = 0; i < max; i++)
1b315056 11922 if (streq (debug_displays[i].section.uncompressed_name, name)
b40bf0a2 11923 || (i == line && const_strneq (name, ".debug_line."))
1b315056 11924 || streq (debug_displays[i].section.compressed_name, name))
19e6b90e 11925 {
2cf0635d 11926 struct dwarf_section * sec = &debug_displays [i].section;
d966045b
DJ
11927 int secondary = (section != find_section (name));
11928
11929 if (secondary)
3f5e193b 11930 free_debug_section ((enum dwarf_section_display_enum) i);
1007acb3 11931
b40bf0a2
NC
11932 if (i == line && const_strneq (name, ".debug_line."))
11933 sec->name = name;
11934 else if (streq (sec->uncompressed_name, name))
d966045b
DJ
11935 sec->name = sec->uncompressed_name;
11936 else
11937 sec->name = sec->compressed_name;
3f5e193b
NC
11938 if (load_specific_debug_section ((enum dwarf_section_display_enum) i,
11939 section, file))
19e6b90e 11940 {
657d0d47
CC
11941 /* If this debug section is part of a CU/TU set in a .dwp file,
11942 restrict load_debug_section to the sections in that set. */
11943 section_subset = find_cu_tu_set (file, shndx);
11944
19e6b90e 11945 result &= debug_displays[i].display (sec, file);
1007acb3 11946
657d0d47
CC
11947 section_subset = NULL;
11948
d966045b 11949 if (secondary || (i != info && i != abbrev))
3f5e193b 11950 free_debug_section ((enum dwarf_section_display_enum) i);
19e6b90e 11951 }
1007acb3 11952
19e6b90e
L
11953 break;
11954 }
1007acb3 11955
19e6b90e 11956 if (i == max)
1007acb3 11957 {
74e1a04b 11958 printf (_("Unrecognized debug section: %s\n"), print_name);
19e6b90e 11959 result = 0;
1007acb3
L
11960 }
11961
19e6b90e 11962 return result;
5b18a4bc 11963}
103f02d3 11964
aef1f6d0
DJ
11965/* Set DUMP_SECTS for all sections where dumps were requested
11966 based on section name. */
11967
11968static void
11969initialise_dumps_byname (void)
11970{
2cf0635d 11971 struct dump_list_entry * cur;
aef1f6d0
DJ
11972
11973 for (cur = dump_sects_byname; cur; cur = cur->next)
11974 {
11975 unsigned int i;
11976 int any;
11977
11978 for (i = 0, any = 0; i < elf_header.e_shnum; i++)
11979 if (streq (SECTION_NAME (section_headers + i), cur->name))
11980 {
09c11c86 11981 request_dump_bynumber (i, cur->type);
aef1f6d0
DJ
11982 any = 1;
11983 }
11984
11985 if (!any)
11986 warn (_("Section '%s' was not dumped because it does not exist!\n"),
11987 cur->name);
11988 }
11989}
11990
5b18a4bc 11991static void
2cf0635d 11992process_section_contents (FILE * file)
5b18a4bc 11993{
2cf0635d 11994 Elf_Internal_Shdr * section;
19e6b90e 11995 unsigned int i;
103f02d3 11996
19e6b90e
L
11997 if (! do_dump)
11998 return;
103f02d3 11999
aef1f6d0
DJ
12000 initialise_dumps_byname ();
12001
19e6b90e
L
12002 for (i = 0, section = section_headers;
12003 i < elf_header.e_shnum && i < num_dump_sects;
12004 i++, section++)
12005 {
12006#ifdef SUPPORT_DISASSEMBLY
12007 if (dump_sects[i] & DISASS_DUMP)
12008 disassemble_section (section, file);
12009#endif
12010 if (dump_sects[i] & HEX_DUMP)
cf13d699 12011 dump_section_as_bytes (section, file, FALSE);
103f02d3 12012
cf13d699
NC
12013 if (dump_sects[i] & RELOC_DUMP)
12014 dump_section_as_bytes (section, file, TRUE);
09c11c86
NC
12015
12016 if (dump_sects[i] & STRING_DUMP)
12017 dump_section_as_strings (section, file);
cf13d699
NC
12018
12019 if (dump_sects[i] & DEBUG_DUMP)
657d0d47 12020 display_debug_section (i, section, file);
5b18a4bc 12021 }
103f02d3 12022
19e6b90e
L
12023 /* Check to see if the user requested a
12024 dump of a section that does not exist. */
12025 while (i++ < num_dump_sects)
12026 if (dump_sects[i])
12027 warn (_("Section %d was not dumped because it does not exist!\n"), i);
5b18a4bc 12028}
103f02d3 12029
5b18a4bc 12030static void
19e6b90e 12031process_mips_fpe_exception (int mask)
5b18a4bc 12032{
19e6b90e
L
12033 if (mask)
12034 {
12035 int first = 1;
12036 if (mask & OEX_FPU_INEX)
12037 fputs ("INEX", stdout), first = 0;
12038 if (mask & OEX_FPU_UFLO)
12039 printf ("%sUFLO", first ? "" : "|"), first = 0;
12040 if (mask & OEX_FPU_OFLO)
12041 printf ("%sOFLO", first ? "" : "|"), first = 0;
12042 if (mask & OEX_FPU_DIV0)
12043 printf ("%sDIV0", first ? "" : "|"), first = 0;
12044 if (mask & OEX_FPU_INVAL)
12045 printf ("%sINVAL", first ? "" : "|");
12046 }
5b18a4bc 12047 else
19e6b90e 12048 fputs ("0", stdout);
5b18a4bc 12049}
103f02d3 12050
f6f0e17b
NC
12051/* Display's the value of TAG at location P. If TAG is
12052 greater than 0 it is assumed to be an unknown tag, and
12053 a message is printed to this effect. Otherwise it is
12054 assumed that a message has already been printed.
12055
12056 If the bottom bit of TAG is set it assumed to have a
12057 string value, otherwise it is assumed to have an integer
12058 value.
12059
12060 Returns an updated P pointing to the first unread byte
12061 beyond the end of TAG's value.
12062
12063 Reads at or beyond END will not be made. */
12064
12065static unsigned char *
12066display_tag_value (int tag,
12067 unsigned char * p,
12068 const unsigned char * const end)
12069{
12070 unsigned long val;
12071
12072 if (tag > 0)
12073 printf (" Tag_unknown_%d: ", tag);
12074
12075 if (p >= end)
12076 {
4082ef84 12077 warn (_("<corrupt tag>\n"));
f6f0e17b
NC
12078 }
12079 else if (tag & 1)
12080 {
071436c6
NC
12081 /* PR 17531 file: 027-19978-0.004. */
12082 size_t maxlen = (end - p) - 1;
12083
12084 putchar ('"');
4082ef84
NC
12085 if (maxlen > 0)
12086 {
12087 print_symbol ((int) maxlen, (const char *) p);
12088 p += strnlen ((char *) p, maxlen) + 1;
12089 }
12090 else
12091 {
12092 printf (_("<corrupt string tag>"));
12093 p = (unsigned char *) end;
12094 }
071436c6 12095 printf ("\"\n");
f6f0e17b
NC
12096 }
12097 else
12098 {
12099 unsigned int len;
12100
12101 val = read_uleb128 (p, &len, end);
12102 p += len;
12103 printf ("%ld (0x%lx)\n", val, val);
12104 }
12105
4082ef84 12106 assert (p <= end);
f6f0e17b
NC
12107 return p;
12108}
12109
11c1ff18
PB
12110/* ARM EABI attributes section. */
12111typedef struct
12112{
70e99720 12113 unsigned int tag;
2cf0635d 12114 const char * name;
11c1ff18 12115 /* 0 = special, 1 = string, 2 = uleb123, > 0x80 == table lookup. */
70e99720 12116 unsigned int type;
2cf0635d 12117 const char ** table;
11c1ff18
PB
12118} arm_attr_public_tag;
12119
2cf0635d 12120static const char * arm_attr_tag_CPU_arch[] =
11c1ff18 12121 {"Pre-v4", "v4", "v4T", "v5T", "v5TE", "v5TEJ", "v6", "v6KZ", "v6T2",
bca38921 12122 "v6K", "v7", "v6-M", "v6S-M", "v7E-M", "v8"};
2cf0635d
NC
12123static const char * arm_attr_tag_ARM_ISA_use[] = {"No", "Yes"};
12124static const char * arm_attr_tag_THUMB_ISA_use[] =
11c1ff18 12125 {"No", "Thumb-1", "Thumb-2"};
75375b3e 12126static const char * arm_attr_tag_FP_arch[] =
bca38921 12127 {"No", "VFPv1", "VFPv2", "VFPv3", "VFPv3-D16", "VFPv4", "VFPv4-D16",
a715796b 12128 "FP for ARMv8", "FPv5/FP-D16 for ARMv8"};
2cf0635d 12129static const char * arm_attr_tag_WMMX_arch[] = {"No", "WMMXv1", "WMMXv2"};
dd24e3da 12130static const char * arm_attr_tag_Advanced_SIMD_arch[] =
bca38921 12131 {"No", "NEONv1", "NEONv1 with Fused-MAC", "NEON for ARMv8"};
2cf0635d 12132static const char * arm_attr_tag_PCS_config[] =
11c1ff18
PB
12133 {"None", "Bare platform", "Linux application", "Linux DSO", "PalmOS 2004",
12134 "PalmOS (reserved)", "SymbianOS 2004", "SymbianOS (reserved)"};
2cf0635d 12135static const char * arm_attr_tag_ABI_PCS_R9_use[] =
11c1ff18 12136 {"V6", "SB", "TLS", "Unused"};
2cf0635d 12137static const char * arm_attr_tag_ABI_PCS_RW_data[] =
11c1ff18 12138 {"Absolute", "PC-relative", "SB-relative", "None"};
2cf0635d 12139static const char * arm_attr_tag_ABI_PCS_RO_data[] =
11c1ff18 12140 {"Absolute", "PC-relative", "None"};
2cf0635d 12141static const char * arm_attr_tag_ABI_PCS_GOT_use[] =
11c1ff18 12142 {"None", "direct", "GOT-indirect"};
2cf0635d 12143static const char * arm_attr_tag_ABI_PCS_wchar_t[] =
11c1ff18 12144 {"None", "??? 1", "2", "??? 3", "4"};
2cf0635d
NC
12145static const char * arm_attr_tag_ABI_FP_rounding[] = {"Unused", "Needed"};
12146static const char * arm_attr_tag_ABI_FP_denormal[] =
f5f53991 12147 {"Unused", "Needed", "Sign only"};
2cf0635d
NC
12148static const char * arm_attr_tag_ABI_FP_exceptions[] = {"Unused", "Needed"};
12149static const char * arm_attr_tag_ABI_FP_user_exceptions[] = {"Unused", "Needed"};
12150static const char * arm_attr_tag_ABI_FP_number_model[] =
11c1ff18 12151 {"Unused", "Finite", "RTABI", "IEEE 754"};
2cf0635d 12152static const char * arm_attr_tag_ABI_enum_size[] =
11c1ff18 12153 {"Unused", "small", "int", "forced to int"};
2cf0635d 12154static const char * arm_attr_tag_ABI_HardFP_use[] =
75375b3e 12155 {"As Tag_FP_arch", "SP only", "DP only", "SP and DP"};
2cf0635d 12156static const char * arm_attr_tag_ABI_VFP_args[] =
11c1ff18 12157 {"AAPCS", "VFP registers", "custom"};
2cf0635d 12158static const char * arm_attr_tag_ABI_WMMX_args[] =
11c1ff18 12159 {"AAPCS", "WMMX registers", "custom"};
2cf0635d 12160static const char * arm_attr_tag_ABI_optimization_goals[] =
11c1ff18
PB
12161 {"None", "Prefer Speed", "Aggressive Speed", "Prefer Size",
12162 "Aggressive Size", "Prefer Debug", "Aggressive Debug"};
2cf0635d 12163static const char * arm_attr_tag_ABI_FP_optimization_goals[] =
11c1ff18
PB
12164 {"None", "Prefer Speed", "Aggressive Speed", "Prefer Size",
12165 "Aggressive Size", "Prefer Accuracy", "Aggressive Accuracy"};
2cf0635d 12166static const char * arm_attr_tag_CPU_unaligned_access[] = {"None", "v6"};
75375b3e 12167static const char * arm_attr_tag_FP_HP_extension[] =
8e79c3df 12168 {"Not Allowed", "Allowed"};
2cf0635d 12169static const char * arm_attr_tag_ABI_FP_16bit_format[] =
8e79c3df 12170 {"None", "IEEE 754", "Alternative Format"};
dd24e3da 12171static const char * arm_attr_tag_MPextension_use[] =
cd21e546
MGD
12172 {"Not Allowed", "Allowed"};
12173static const char * arm_attr_tag_DIV_use[] =
dd24e3da 12174 {"Allowed in Thumb-ISA, v7-R or v7-M", "Not allowed",
cd21e546 12175 "Allowed in v7-A with integer division extension"};
2cf0635d
NC
12176static const char * arm_attr_tag_T2EE_use[] = {"Not Allowed", "Allowed"};
12177static const char * arm_attr_tag_Virtualization_use[] =
dd24e3da 12178 {"Not Allowed", "TrustZone", "Virtualization Extensions",
cd21e546 12179 "TrustZone and Virtualization Extensions"};
dd24e3da 12180static const char * arm_attr_tag_MPextension_use_legacy[] =
f5f53991 12181 {"Not Allowed", "Allowed"};
11c1ff18
PB
12182
12183#define LOOKUP(id, name) \
12184 {id, #name, 0x80 | ARRAY_SIZE(arm_attr_tag_##name), arm_attr_tag_##name}
d70c5fc7 12185static arm_attr_public_tag arm_attr_public_tags[] =
11c1ff18
PB
12186{
12187 {4, "CPU_raw_name", 1, NULL},
12188 {5, "CPU_name", 1, NULL},
12189 LOOKUP(6, CPU_arch),
12190 {7, "CPU_arch_profile", 0, NULL},
12191 LOOKUP(8, ARM_ISA_use),
12192 LOOKUP(9, THUMB_ISA_use),
75375b3e 12193 LOOKUP(10, FP_arch),
11c1ff18 12194 LOOKUP(11, WMMX_arch),
f5f53991
AS
12195 LOOKUP(12, Advanced_SIMD_arch),
12196 LOOKUP(13, PCS_config),
11c1ff18
PB
12197 LOOKUP(14, ABI_PCS_R9_use),
12198 LOOKUP(15, ABI_PCS_RW_data),
f5f53991 12199 LOOKUP(16, ABI_PCS_RO_data),
11c1ff18
PB
12200 LOOKUP(17, ABI_PCS_GOT_use),
12201 LOOKUP(18, ABI_PCS_wchar_t),
12202 LOOKUP(19, ABI_FP_rounding),
12203 LOOKUP(20, ABI_FP_denormal),
12204 LOOKUP(21, ABI_FP_exceptions),
12205 LOOKUP(22, ABI_FP_user_exceptions),
12206 LOOKUP(23, ABI_FP_number_model),
75375b3e
MGD
12207 {24, "ABI_align_needed", 0, NULL},
12208 {25, "ABI_align_preserved", 0, NULL},
11c1ff18
PB
12209 LOOKUP(26, ABI_enum_size),
12210 LOOKUP(27, ABI_HardFP_use),
12211 LOOKUP(28, ABI_VFP_args),
12212 LOOKUP(29, ABI_WMMX_args),
12213 LOOKUP(30, ABI_optimization_goals),
12214 LOOKUP(31, ABI_FP_optimization_goals),
8e79c3df 12215 {32, "compatibility", 0, NULL},
f5f53991 12216 LOOKUP(34, CPU_unaligned_access),
75375b3e 12217 LOOKUP(36, FP_HP_extension),
8e79c3df 12218 LOOKUP(38, ABI_FP_16bit_format),
cd21e546
MGD
12219 LOOKUP(42, MPextension_use),
12220 LOOKUP(44, DIV_use),
f5f53991
AS
12221 {64, "nodefaults", 0, NULL},
12222 {65, "also_compatible_with", 0, NULL},
12223 LOOKUP(66, T2EE_use),
12224 {67, "conformance", 1, NULL},
12225 LOOKUP(68, Virtualization_use),
cd21e546 12226 LOOKUP(70, MPextension_use_legacy)
11c1ff18
PB
12227};
12228#undef LOOKUP
12229
11c1ff18 12230static unsigned char *
f6f0e17b
NC
12231display_arm_attribute (unsigned char * p,
12232 const unsigned char * const end)
11c1ff18 12233{
70e99720 12234 unsigned int tag;
11c1ff18 12235 unsigned int len;
70e99720 12236 unsigned int val;
2cf0635d 12237 arm_attr_public_tag * attr;
11c1ff18 12238 unsigned i;
70e99720 12239 unsigned int type;
11c1ff18 12240
f6f0e17b 12241 tag = read_uleb128 (p, &len, end);
11c1ff18
PB
12242 p += len;
12243 attr = NULL;
2cf0635d 12244 for (i = 0; i < ARRAY_SIZE (arm_attr_public_tags); i++)
11c1ff18
PB
12245 {
12246 if (arm_attr_public_tags[i].tag == tag)
12247 {
12248 attr = &arm_attr_public_tags[i];
12249 break;
12250 }
12251 }
12252
12253 if (attr)
12254 {
12255 printf (" Tag_%s: ", attr->name);
12256 switch (attr->type)
12257 {
12258 case 0:
12259 switch (tag)
12260 {
12261 case 7: /* Tag_CPU_arch_profile. */
f6f0e17b 12262 val = read_uleb128 (p, &len, end);
11c1ff18
PB
12263 p += len;
12264 switch (val)
12265 {
2b692964
NC
12266 case 0: printf (_("None\n")); break;
12267 case 'A': printf (_("Application\n")); break;
12268 case 'R': printf (_("Realtime\n")); break;
12269 case 'M': printf (_("Microcontroller\n")); break;
12270 case 'S': printf (_("Application or Realtime\n")); break;
11c1ff18
PB
12271 default: printf ("??? (%d)\n", val); break;
12272 }
12273 break;
12274
75375b3e 12275 case 24: /* Tag_align_needed. */
f6f0e17b 12276 val = read_uleb128 (p, &len, end);
75375b3e
MGD
12277 p += len;
12278 switch (val)
12279 {
2b692964
NC
12280 case 0: printf (_("None\n")); break;
12281 case 1: printf (_("8-byte\n")); break;
12282 case 2: printf (_("4-byte\n")); break;
75375b3e
MGD
12283 case 3: printf ("??? 3\n"); break;
12284 default:
12285 if (val <= 12)
dd24e3da 12286 printf (_("8-byte and up to %d-byte extended\n"),
75375b3e
MGD
12287 1 << val);
12288 else
12289 printf ("??? (%d)\n", val);
12290 break;
12291 }
12292 break;
12293
12294 case 25: /* Tag_align_preserved. */
f6f0e17b 12295 val = read_uleb128 (p, &len, end);
75375b3e
MGD
12296 p += len;
12297 switch (val)
12298 {
2b692964
NC
12299 case 0: printf (_("None\n")); break;
12300 case 1: printf (_("8-byte, except leaf SP\n")); break;
12301 case 2: printf (_("8-byte\n")); break;
75375b3e
MGD
12302 case 3: printf ("??? 3\n"); break;
12303 default:
12304 if (val <= 12)
dd24e3da 12305 printf (_("8-byte and up to %d-byte extended\n"),
75375b3e
MGD
12306 1 << val);
12307 else
12308 printf ("??? (%d)\n", val);
12309 break;
12310 }
12311 break;
12312
11c1ff18 12313 case 32: /* Tag_compatibility. */
071436c6 12314 {
071436c6
NC
12315 val = read_uleb128 (p, &len, end);
12316 p += len;
071436c6 12317 printf (_("flag = %d, vendor = "), val);
4082ef84
NC
12318 if (p < end - 1)
12319 {
12320 size_t maxlen = (end - p) - 1;
12321
12322 print_symbol ((int) maxlen, (const char *) p);
12323 p += strnlen ((char *) p, maxlen) + 1;
12324 }
12325 else
12326 {
12327 printf (_("<corrupt>"));
12328 p = (unsigned char *) end;
12329 }
071436c6 12330 putchar ('\n');
071436c6 12331 }
11c1ff18
PB
12332 break;
12333
f5f53991 12334 case 64: /* Tag_nodefaults. */
541a3cbd
NC
12335 /* PR 17531: file: 001-505008-0.01. */
12336 if (p < end)
12337 p++;
2b692964 12338 printf (_("True\n"));
f5f53991
AS
12339 break;
12340
12341 case 65: /* Tag_also_compatible_with. */
f6f0e17b 12342 val = read_uleb128 (p, &len, end);
f5f53991
AS
12343 p += len;
12344 if (val == 6 /* Tag_CPU_arch. */)
12345 {
f6f0e17b 12346 val = read_uleb128 (p, &len, end);
f5f53991 12347 p += len;
071436c6 12348 if ((unsigned int) val >= ARRAY_SIZE (arm_attr_tag_CPU_arch))
f5f53991
AS
12349 printf ("??? (%d)\n", val);
12350 else
12351 printf ("%s\n", arm_attr_tag_CPU_arch[val]);
12352 }
12353 else
12354 printf ("???\n");
071436c6
NC
12355 while (p < end && *(p++) != '\0' /* NUL terminator. */)
12356 ;
f5f53991
AS
12357 break;
12358
11c1ff18 12359 default:
bee0ee85
NC
12360 printf (_("<unknown: %d>\n"), tag);
12361 break;
11c1ff18
PB
12362 }
12363 return p;
12364
12365 case 1:
f6f0e17b 12366 return display_tag_value (-1, p, end);
11c1ff18 12367 case 2:
f6f0e17b 12368 return display_tag_value (0, p, end);
11c1ff18
PB
12369
12370 default:
12371 assert (attr->type & 0x80);
f6f0e17b 12372 val = read_uleb128 (p, &len, end);
11c1ff18
PB
12373 p += len;
12374 type = attr->type & 0x7f;
12375 if (val >= type)
12376 printf ("??? (%d)\n", val);
12377 else
12378 printf ("%s\n", attr->table[val]);
12379 return p;
12380 }
12381 }
11c1ff18 12382
f6f0e17b 12383 return display_tag_value (tag, p, end);
11c1ff18
PB
12384}
12385
104d59d1 12386static unsigned char *
60bca95a 12387display_gnu_attribute (unsigned char * p,
f6f0e17b
NC
12388 unsigned char * (* display_proc_gnu_attribute) (unsigned char *, int, const unsigned char * const),
12389 const unsigned char * const end)
104d59d1
JM
12390{
12391 int tag;
12392 unsigned int len;
12393 int val;
104d59d1 12394
f6f0e17b 12395 tag = read_uleb128 (p, &len, end);
104d59d1
JM
12396 p += len;
12397
12398 /* Tag_compatibility is the only generic GNU attribute defined at
12399 present. */
12400 if (tag == 32)
12401 {
f6f0e17b 12402 val = read_uleb128 (p, &len, end);
104d59d1 12403 p += len;
071436c6
NC
12404
12405 printf (_("flag = %d, vendor = "), val);
f6f0e17b
NC
12406 if (p == end)
12407 {
071436c6 12408 printf (_("<corrupt>\n"));
f6f0e17b
NC
12409 warn (_("corrupt vendor attribute\n"));
12410 }
12411 else
12412 {
4082ef84
NC
12413 if (p < end - 1)
12414 {
12415 size_t maxlen = (end - p) - 1;
071436c6 12416
4082ef84
NC
12417 print_symbol ((int) maxlen, (const char *) p);
12418 p += strnlen ((char *) p, maxlen) + 1;
12419 }
12420 else
12421 {
12422 printf (_("<corrupt>"));
12423 p = (unsigned char *) end;
12424 }
071436c6 12425 putchar ('\n');
f6f0e17b 12426 }
104d59d1
JM
12427 return p;
12428 }
12429
12430 if ((tag & 2) == 0 && display_proc_gnu_attribute)
f6f0e17b 12431 return display_proc_gnu_attribute (p, tag, end);
104d59d1 12432
f6f0e17b 12433 return display_tag_value (tag, p, end);
104d59d1
JM
12434}
12435
34c8bcba 12436static unsigned char *
f6f0e17b
NC
12437display_power_gnu_attribute (unsigned char * p,
12438 int tag,
12439 const unsigned char * const end)
34c8bcba 12440{
34c8bcba
JM
12441 unsigned int len;
12442 int val;
12443
12444 if (tag == Tag_GNU_Power_ABI_FP)
12445 {
f6f0e17b 12446 val = read_uleb128 (p, &len, end);
34c8bcba
JM
12447 p += len;
12448 printf (" Tag_GNU_Power_ABI_FP: ");
60bca95a 12449
34c8bcba
JM
12450 switch (val)
12451 {
12452 case 0:
2b692964 12453 printf (_("Hard or soft float\n"));
34c8bcba
JM
12454 break;
12455 case 1:
2b692964 12456 printf (_("Hard float\n"));
34c8bcba
JM
12457 break;
12458 case 2:
2b692964 12459 printf (_("Soft float\n"));
34c8bcba 12460 break;
3c7b9897 12461 case 3:
2b692964 12462 printf (_("Single-precision hard float\n"));
3c7b9897 12463 break;
34c8bcba
JM
12464 default:
12465 printf ("??? (%d)\n", val);
12466 break;
12467 }
12468 return p;
12469 }
12470
c6e65352
DJ
12471 if (tag == Tag_GNU_Power_ABI_Vector)
12472 {
f6f0e17b 12473 val = read_uleb128 (p, &len, end);
c6e65352
DJ
12474 p += len;
12475 printf (" Tag_GNU_Power_ABI_Vector: ");
12476 switch (val)
12477 {
12478 case 0:
2b692964 12479 printf (_("Any\n"));
c6e65352
DJ
12480 break;
12481 case 1:
2b692964 12482 printf (_("Generic\n"));
c6e65352
DJ
12483 break;
12484 case 2:
12485 printf ("AltiVec\n");
12486 break;
12487 case 3:
12488 printf ("SPE\n");
12489 break;
12490 default:
12491 printf ("??? (%d)\n", val);
12492 break;
12493 }
12494 return p;
12495 }
12496
f82e0623
NF
12497 if (tag == Tag_GNU_Power_ABI_Struct_Return)
12498 {
f6f0e17b
NC
12499 if (p == end)
12500 {
071436c6 12501 warn (_("corrupt Tag_GNU_Power_ABI_Struct_Return\n"));
f6f0e17b
NC
12502 return p;
12503 }
0b4362b0 12504
f6f0e17b 12505 val = read_uleb128 (p, &len, end);
f82e0623
NF
12506 p += len;
12507 printf (" Tag_GNU_Power_ABI_Struct_Return: ");
12508 switch (val)
12509 {
12510 case 0:
2b692964 12511 printf (_("Any\n"));
f82e0623
NF
12512 break;
12513 case 1:
12514 printf ("r3/r4\n");
12515 break;
12516 case 2:
2b692964 12517 printf (_("Memory\n"));
f82e0623
NF
12518 break;
12519 default:
12520 printf ("??? (%d)\n", val);
12521 break;
12522 }
12523 return p;
12524 }
12525
f6f0e17b 12526 return display_tag_value (tag & 1, p, end);
34c8bcba
JM
12527}
12528
9e8c70f9
DM
12529static void
12530display_sparc_hwcaps (int mask)
12531{
12532 if (mask)
12533 {
12534 int first = 1;
071436c6 12535
9e8c70f9
DM
12536 if (mask & ELF_SPARC_HWCAP_MUL32)
12537 fputs ("mul32", stdout), first = 0;
12538 if (mask & ELF_SPARC_HWCAP_DIV32)
12539 printf ("%sdiv32", first ? "" : "|"), first = 0;
12540 if (mask & ELF_SPARC_HWCAP_FSMULD)
12541 printf ("%sfsmuld", first ? "" : "|"), first = 0;
12542 if (mask & ELF_SPARC_HWCAP_V8PLUS)
12543 printf ("%sv8plus", first ? "" : "|"), first = 0;
12544 if (mask & ELF_SPARC_HWCAP_POPC)
12545 printf ("%spopc", first ? "" : "|"), first = 0;
12546 if (mask & ELF_SPARC_HWCAP_VIS)
12547 printf ("%svis", first ? "" : "|"), first = 0;
12548 if (mask & ELF_SPARC_HWCAP_VIS2)
12549 printf ("%svis2", first ? "" : "|"), first = 0;
12550 if (mask & ELF_SPARC_HWCAP_ASI_BLK_INIT)
12551 printf ("%sASIBlkInit", first ? "" : "|"), first = 0;
12552 if (mask & ELF_SPARC_HWCAP_FMAF)
12553 printf ("%sfmaf", first ? "" : "|"), first = 0;
12554 if (mask & ELF_SPARC_HWCAP_VIS3)
12555 printf ("%svis3", first ? "" : "|"), first = 0;
12556 if (mask & ELF_SPARC_HWCAP_HPC)
12557 printf ("%shpc", first ? "" : "|"), first = 0;
12558 if (mask & ELF_SPARC_HWCAP_RANDOM)
12559 printf ("%srandom", first ? "" : "|"), first = 0;
12560 if (mask & ELF_SPARC_HWCAP_TRANS)
12561 printf ("%strans", first ? "" : "|"), first = 0;
12562 if (mask & ELF_SPARC_HWCAP_FJFMAU)
12563 printf ("%sfjfmau", first ? "" : "|"), first = 0;
12564 if (mask & ELF_SPARC_HWCAP_IMA)
12565 printf ("%sima", first ? "" : "|"), first = 0;
12566 if (mask & ELF_SPARC_HWCAP_ASI_CACHE_SPARING)
12567 printf ("%scspare", first ? "" : "|"), first = 0;
12568 }
12569 else
071436c6
NC
12570 fputc ('0', stdout);
12571 fputc ('\n', stdout);
9e8c70f9
DM
12572}
12573
3d68f91c
JM
12574static void
12575display_sparc_hwcaps2 (int mask)
12576{
12577 if (mask)
12578 {
12579 int first = 1;
071436c6 12580
3d68f91c
JM
12581 if (mask & ELF_SPARC_HWCAP2_FJATHPLUS)
12582 fputs ("fjathplus", stdout), first = 0;
12583 if (mask & ELF_SPARC_HWCAP2_VIS3B)
12584 printf ("%svis3b", first ? "" : "|"), first = 0;
12585 if (mask & ELF_SPARC_HWCAP2_ADP)
12586 printf ("%sadp", first ? "" : "|"), first = 0;
12587 if (mask & ELF_SPARC_HWCAP2_SPARC5)
12588 printf ("%ssparc5", first ? "" : "|"), first = 0;
12589 if (mask & ELF_SPARC_HWCAP2_MWAIT)
12590 printf ("%smwait", first ? "" : "|"), first = 0;
12591 if (mask & ELF_SPARC_HWCAP2_XMPMUL)
12592 printf ("%sxmpmul", first ? "" : "|"), first = 0;
12593 if (mask & ELF_SPARC_HWCAP2_XMONT)
12594 printf ("%sxmont2", first ? "" : "|"), first = 0;
12595 if (mask & ELF_SPARC_HWCAP2_NSEC)
12596 printf ("%snsec", first ? "" : "|"), first = 0;
12597 if (mask & ELF_SPARC_HWCAP2_FJATHHPC)
12598 printf ("%sfjathhpc", first ? "" : "|"), first = 0;
12599 if (mask & ELF_SPARC_HWCAP2_FJDES)
12600 printf ("%sfjdes", first ? "" : "|"), first = 0;
12601 if (mask & ELF_SPARC_HWCAP2_FJAES)
12602 printf ("%sfjaes", first ? "" : "|"), first = 0;
12603 }
12604 else
071436c6
NC
12605 fputc ('0', stdout);
12606 fputc ('\n', stdout);
3d68f91c
JM
12607}
12608
9e8c70f9 12609static unsigned char *
f6f0e17b
NC
12610display_sparc_gnu_attribute (unsigned char * p,
12611 int tag,
12612 const unsigned char * const end)
9e8c70f9 12613{
3d68f91c
JM
12614 unsigned int len;
12615 int val;
12616
9e8c70f9
DM
12617 if (tag == Tag_GNU_Sparc_HWCAPS)
12618 {
f6f0e17b 12619 val = read_uleb128 (p, &len, end);
9e8c70f9
DM
12620 p += len;
12621 printf (" Tag_GNU_Sparc_HWCAPS: ");
9e8c70f9
DM
12622 display_sparc_hwcaps (val);
12623 return p;
3d68f91c
JM
12624 }
12625 if (tag == Tag_GNU_Sparc_HWCAPS2)
12626 {
12627 val = read_uleb128 (p, &len, end);
12628 p += len;
12629 printf (" Tag_GNU_Sparc_HWCAPS2: ");
12630 display_sparc_hwcaps2 (val);
12631 return p;
12632 }
9e8c70f9 12633
f6f0e17b 12634 return display_tag_value (tag, p, end);
9e8c70f9
DM
12635}
12636
351cdf24
MF
12637static void
12638print_mips_fp_abi_value (int val)
12639{
12640 switch (val)
12641 {
12642 case Val_GNU_MIPS_ABI_FP_ANY:
12643 printf (_("Hard or soft float\n"));
12644 break;
12645 case Val_GNU_MIPS_ABI_FP_DOUBLE:
12646 printf (_("Hard float (double precision)\n"));
12647 break;
12648 case Val_GNU_MIPS_ABI_FP_SINGLE:
12649 printf (_("Hard float (single precision)\n"));
12650 break;
12651 case Val_GNU_MIPS_ABI_FP_SOFT:
12652 printf (_("Soft float\n"));
12653 break;
12654 case Val_GNU_MIPS_ABI_FP_OLD_64:
12655 printf (_("Hard float (MIPS32r2 64-bit FPU 12 callee-saved)\n"));
12656 break;
12657 case Val_GNU_MIPS_ABI_FP_XX:
12658 printf (_("Hard float (32-bit CPU, Any FPU)\n"));
12659 break;
12660 case Val_GNU_MIPS_ABI_FP_64:
12661 printf (_("Hard float (32-bit CPU, 64-bit FPU)\n"));
12662 break;
12663 case Val_GNU_MIPS_ABI_FP_64A:
12664 printf (_("Hard float compat (32-bit CPU, 64-bit FPU)\n"));
12665 break;
12666 default:
12667 printf ("??? (%d)\n", val);
12668 break;
12669 }
12670}
12671
2cf19d5c 12672static unsigned char *
f6f0e17b
NC
12673display_mips_gnu_attribute (unsigned char * p,
12674 int tag,
12675 const unsigned char * const end)
2cf19d5c 12676{
2cf19d5c
JM
12677 if (tag == Tag_GNU_MIPS_ABI_FP)
12678 {
f6f0e17b
NC
12679 unsigned int len;
12680 int val;
12681
12682 val = read_uleb128 (p, &len, end);
2cf19d5c
JM
12683 p += len;
12684 printf (" Tag_GNU_MIPS_ABI_FP: ");
60bca95a 12685
351cdf24
MF
12686 print_mips_fp_abi_value (val);
12687
2cf19d5c
JM
12688 return p;
12689 }
12690
a9f58168
CF
12691 if (tag == Tag_GNU_MIPS_ABI_MSA)
12692 {
12693 unsigned int len;
12694 int val;
12695
12696 val = read_uleb128 (p, &len, end);
12697 p += len;
12698 printf (" Tag_GNU_MIPS_ABI_MSA: ");
12699
12700 switch (val)
12701 {
12702 case Val_GNU_MIPS_ABI_MSA_ANY:
12703 printf (_("Any MSA or not\n"));
12704 break;
12705 case Val_GNU_MIPS_ABI_MSA_128:
12706 printf (_("128-bit MSA\n"));
12707 break;
12708 default:
12709 printf ("??? (%d)\n", val);
12710 break;
12711 }
12712 return p;
12713 }
12714
f6f0e17b 12715 return display_tag_value (tag & 1, p, end);
2cf19d5c
JM
12716}
12717
59e6276b 12718static unsigned char *
f6f0e17b
NC
12719display_tic6x_attribute (unsigned char * p,
12720 const unsigned char * const end)
59e6276b
JM
12721{
12722 int tag;
12723 unsigned int len;
12724 int val;
12725
f6f0e17b 12726 tag = read_uleb128 (p, &len, end);
59e6276b
JM
12727 p += len;
12728
12729 switch (tag)
12730 {
75fa6dc1 12731 case Tag_ISA:
f6f0e17b 12732 val = read_uleb128 (p, &len, end);
59e6276b 12733 p += len;
75fa6dc1 12734 printf (" Tag_ISA: ");
59e6276b
JM
12735
12736 switch (val)
12737 {
75fa6dc1 12738 case C6XABI_Tag_ISA_none:
59e6276b
JM
12739 printf (_("None\n"));
12740 break;
75fa6dc1 12741 case C6XABI_Tag_ISA_C62X:
59e6276b
JM
12742 printf ("C62x\n");
12743 break;
75fa6dc1 12744 case C6XABI_Tag_ISA_C67X:
59e6276b
JM
12745 printf ("C67x\n");
12746 break;
75fa6dc1 12747 case C6XABI_Tag_ISA_C67XP:
59e6276b
JM
12748 printf ("C67x+\n");
12749 break;
75fa6dc1 12750 case C6XABI_Tag_ISA_C64X:
59e6276b
JM
12751 printf ("C64x\n");
12752 break;
75fa6dc1 12753 case C6XABI_Tag_ISA_C64XP:
59e6276b
JM
12754 printf ("C64x+\n");
12755 break;
75fa6dc1 12756 case C6XABI_Tag_ISA_C674X:
59e6276b
JM
12757 printf ("C674x\n");
12758 break;
12759 default:
12760 printf ("??? (%d)\n", val);
12761 break;
12762 }
12763 return p;
12764
87779176 12765 case Tag_ABI_wchar_t:
f6f0e17b 12766 val = read_uleb128 (p, &len, end);
87779176
JM
12767 p += len;
12768 printf (" Tag_ABI_wchar_t: ");
12769 switch (val)
12770 {
12771 case 0:
12772 printf (_("Not used\n"));
12773 break;
12774 case 1:
12775 printf (_("2 bytes\n"));
12776 break;
12777 case 2:
12778 printf (_("4 bytes\n"));
12779 break;
12780 default:
12781 printf ("??? (%d)\n", val);
12782 break;
12783 }
12784 return p;
12785
12786 case Tag_ABI_stack_align_needed:
f6f0e17b 12787 val = read_uleb128 (p, &len, end);
87779176
JM
12788 p += len;
12789 printf (" Tag_ABI_stack_align_needed: ");
12790 switch (val)
12791 {
12792 case 0:
12793 printf (_("8-byte\n"));
12794 break;
12795 case 1:
12796 printf (_("16-byte\n"));
12797 break;
12798 default:
12799 printf ("??? (%d)\n", val);
12800 break;
12801 }
12802 return p;
12803
12804 case Tag_ABI_stack_align_preserved:
f6f0e17b 12805 val = read_uleb128 (p, &len, end);
87779176
JM
12806 p += len;
12807 printf (" Tag_ABI_stack_align_preserved: ");
12808 switch (val)
12809 {
12810 case 0:
12811 printf (_("8-byte\n"));
12812 break;
12813 case 1:
12814 printf (_("16-byte\n"));
12815 break;
12816 default:
12817 printf ("??? (%d)\n", val);
12818 break;
12819 }
12820 return p;
12821
b5593623 12822 case Tag_ABI_DSBT:
f6f0e17b 12823 val = read_uleb128 (p, &len, end);
b5593623
JM
12824 p += len;
12825 printf (" Tag_ABI_DSBT: ");
12826 switch (val)
12827 {
12828 case 0:
12829 printf (_("DSBT addressing not used\n"));
12830 break;
12831 case 1:
12832 printf (_("DSBT addressing used\n"));
12833 break;
12834 default:
12835 printf ("??? (%d)\n", val);
12836 break;
12837 }
12838 return p;
12839
87779176 12840 case Tag_ABI_PID:
f6f0e17b 12841 val = read_uleb128 (p, &len, end);
87779176
JM
12842 p += len;
12843 printf (" Tag_ABI_PID: ");
12844 switch (val)
12845 {
12846 case 0:
12847 printf (_("Data addressing position-dependent\n"));
12848 break;
12849 case 1:
12850 printf (_("Data addressing position-independent, GOT near DP\n"));
12851 break;
12852 case 2:
12853 printf (_("Data addressing position-independent, GOT far from DP\n"));
12854 break;
12855 default:
12856 printf ("??? (%d)\n", val);
12857 break;
12858 }
12859 return p;
12860
12861 case Tag_ABI_PIC:
f6f0e17b 12862 val = read_uleb128 (p, &len, end);
87779176
JM
12863 p += len;
12864 printf (" Tag_ABI_PIC: ");
12865 switch (val)
12866 {
12867 case 0:
12868 printf (_("Code addressing position-dependent\n"));
12869 break;
12870 case 1:
12871 printf (_("Code addressing position-independent\n"));
12872 break;
12873 default:
12874 printf ("??? (%d)\n", val);
12875 break;
12876 }
12877 return p;
12878
12879 case Tag_ABI_array_object_alignment:
f6f0e17b 12880 val = read_uleb128 (p, &len, end);
87779176
JM
12881 p += len;
12882 printf (" Tag_ABI_array_object_alignment: ");
12883 switch (val)
12884 {
12885 case 0:
12886 printf (_("8-byte\n"));
12887 break;
12888 case 1:
12889 printf (_("4-byte\n"));
12890 break;
12891 case 2:
12892 printf (_("16-byte\n"));
12893 break;
12894 default:
12895 printf ("??? (%d)\n", val);
12896 break;
12897 }
12898 return p;
12899
12900 case Tag_ABI_array_object_align_expected:
f6f0e17b 12901 val = read_uleb128 (p, &len, end);
87779176
JM
12902 p += len;
12903 printf (" Tag_ABI_array_object_align_expected: ");
12904 switch (val)
12905 {
12906 case 0:
12907 printf (_("8-byte\n"));
12908 break;
12909 case 1:
12910 printf (_("4-byte\n"));
12911 break;
12912 case 2:
12913 printf (_("16-byte\n"));
12914 break;
12915 default:
12916 printf ("??? (%d)\n", val);
12917 break;
12918 }
12919 return p;
12920
3cbd1c06 12921 case Tag_ABI_compatibility:
071436c6 12922 {
071436c6
NC
12923 val = read_uleb128 (p, &len, end);
12924 p += len;
12925 printf (" Tag_ABI_compatibility: ");
071436c6 12926 printf (_("flag = %d, vendor = "), val);
4082ef84
NC
12927 if (p < end - 1)
12928 {
12929 size_t maxlen = (end - p) - 1;
12930
12931 print_symbol ((int) maxlen, (const char *) p);
12932 p += strnlen ((char *) p, maxlen) + 1;
12933 }
12934 else
12935 {
12936 printf (_("<corrupt>"));
12937 p = (unsigned char *) end;
12938 }
071436c6 12939 putchar ('\n');
071436c6
NC
12940 return p;
12941 }
87779176
JM
12942
12943 case Tag_ABI_conformance:
071436c6 12944 {
4082ef84
NC
12945 printf (" Tag_ABI_conformance: \"");
12946 if (p < end - 1)
12947 {
12948 size_t maxlen = (end - p) - 1;
071436c6 12949
4082ef84
NC
12950 print_symbol ((int) maxlen, (const char *) p);
12951 p += strnlen ((char *) p, maxlen) + 1;
12952 }
12953 else
12954 {
12955 printf (_("<corrupt>"));
12956 p = (unsigned char *) end;
12957 }
071436c6 12958 printf ("\"\n");
071436c6
NC
12959 return p;
12960 }
59e6276b
JM
12961 }
12962
f6f0e17b
NC
12963 return display_tag_value (tag, p, end);
12964}
59e6276b 12965
f6f0e17b
NC
12966static void
12967display_raw_attribute (unsigned char * p, unsigned char * end)
12968{
12969 unsigned long addr = 0;
12970 size_t bytes = end - p;
12971
e0a31db1 12972 assert (end > p);
f6f0e17b 12973 while (bytes)
87779176 12974 {
f6f0e17b
NC
12975 int j;
12976 int k;
12977 int lbytes = (bytes > 16 ? 16 : bytes);
12978
12979 printf (" 0x%8.8lx ", addr);
12980
12981 for (j = 0; j < 16; j++)
12982 {
12983 if (j < lbytes)
12984 printf ("%2.2x", p[j]);
12985 else
12986 printf (" ");
12987
12988 if ((j & 3) == 3)
12989 printf (" ");
12990 }
12991
12992 for (j = 0; j < lbytes; j++)
12993 {
12994 k = p[j];
12995 if (k >= ' ' && k < 0x7f)
12996 printf ("%c", k);
12997 else
12998 printf (".");
12999 }
13000
13001 putchar ('\n');
13002
13003 p += lbytes;
13004 bytes -= lbytes;
13005 addr += lbytes;
87779176 13006 }
59e6276b 13007
f6f0e17b 13008 putchar ('\n');
59e6276b
JM
13009}
13010
13761a11
NC
13011static unsigned char *
13012display_msp430x_attribute (unsigned char * p,
13013 const unsigned char * const end)
13014{
13015 unsigned int len;
13016 int val;
13017 int tag;
13018
13019 tag = read_uleb128 (p, & len, end);
13020 p += len;
0b4362b0 13021
13761a11
NC
13022 switch (tag)
13023 {
13024 case OFBA_MSPABI_Tag_ISA:
13025 val = read_uleb128 (p, &len, end);
13026 p += len;
13027 printf (" Tag_ISA: ");
13028 switch (val)
13029 {
13030 case 0: printf (_("None\n")); break;
13031 case 1: printf (_("MSP430\n")); break;
13032 case 2: printf (_("MSP430X\n")); break;
13033 default: printf ("??? (%d)\n", val); break;
13034 }
13035 break;
13036
13037 case OFBA_MSPABI_Tag_Code_Model:
13038 val = read_uleb128 (p, &len, end);
13039 p += len;
13040 printf (" Tag_Code_Model: ");
13041 switch (val)
13042 {
13043 case 0: printf (_("None\n")); break;
13044 case 1: printf (_("Small\n")); break;
13045 case 2: printf (_("Large\n")); break;
13046 default: printf ("??? (%d)\n", val); break;
13047 }
13048 break;
13049
13050 case OFBA_MSPABI_Tag_Data_Model:
13051 val = read_uleb128 (p, &len, end);
13052 p += len;
13053 printf (" Tag_Data_Model: ");
13054 switch (val)
13055 {
13056 case 0: printf (_("None\n")); break;
13057 case 1: printf (_("Small\n")); break;
13058 case 2: printf (_("Large\n")); break;
13059 case 3: printf (_("Restricted Large\n")); break;
13060 default: printf ("??? (%d)\n", val); break;
13061 }
13062 break;
13063
13064 default:
13065 printf (_(" <unknown tag %d>: "), tag);
13066
13067 if (tag & 1)
13068 {
071436c6 13069 putchar ('"');
4082ef84
NC
13070 if (p < end - 1)
13071 {
13072 size_t maxlen = (end - p) - 1;
13073
13074 print_symbol ((int) maxlen, (const char *) p);
13075 p += strnlen ((char *) p, maxlen) + 1;
13076 }
13077 else
13078 {
13079 printf (_("<corrupt>"));
13080 p = (unsigned char *) end;
13081 }
071436c6 13082 printf ("\"\n");
13761a11
NC
13083 }
13084 else
13085 {
13086 val = read_uleb128 (p, &len, end);
13087 p += len;
13088 printf ("%d (0x%x)\n", val, val);
13089 }
13090 break;
13091 }
13092
4082ef84 13093 assert (p <= end);
13761a11
NC
13094 return p;
13095}
13096
11c1ff18 13097static int
60bca95a
NC
13098process_attributes (FILE * file,
13099 const char * public_name,
104d59d1 13100 unsigned int proc_type,
f6f0e17b
NC
13101 unsigned char * (* display_pub_attribute) (unsigned char *, const unsigned char * const),
13102 unsigned char * (* display_proc_gnu_attribute) (unsigned char *, int, const unsigned char * const))
11c1ff18 13103{
2cf0635d 13104 Elf_Internal_Shdr * sect;
11c1ff18
PB
13105 unsigned i;
13106
13107 /* Find the section header so that we get the size. */
13108 for (i = 0, sect = section_headers;
13109 i < elf_header.e_shnum;
13110 i++, sect++)
13111 {
071436c6
NC
13112 unsigned char * contents;
13113 unsigned char * p;
13114
104d59d1 13115 if (sect->sh_type != proc_type && sect->sh_type != SHT_GNU_ATTRIBUTES)
11c1ff18
PB
13116 continue;
13117
3f5e193b
NC
13118 contents = (unsigned char *) get_data (NULL, file, sect->sh_offset, 1,
13119 sect->sh_size, _("attributes"));
60bca95a 13120 if (contents == NULL)
11c1ff18 13121 continue;
60bca95a 13122
11c1ff18
PB
13123 p = contents;
13124 if (*p == 'A')
13125 {
071436c6
NC
13126 bfd_vma section_len;
13127
13128 section_len = sect->sh_size - 1;
11c1ff18 13129 p++;
60bca95a 13130
071436c6 13131 while (section_len > 0)
11c1ff18 13132 {
071436c6 13133 bfd_vma attr_len;
e9847026 13134 unsigned int namelen;
11c1ff18 13135 bfd_boolean public_section;
104d59d1 13136 bfd_boolean gnu_section;
11c1ff18 13137
071436c6 13138 if (section_len <= 4)
e0a31db1
NC
13139 {
13140 error (_("Tag section ends prematurely\n"));
13141 break;
13142 }
071436c6 13143 attr_len = byte_get (p, 4);
11c1ff18 13144 p += 4;
60bca95a 13145
071436c6 13146 if (attr_len > section_len)
11c1ff18 13147 {
071436c6
NC
13148 error (_("Bad attribute length (%u > %u)\n"),
13149 (unsigned) attr_len, (unsigned) section_len);
13150 attr_len = section_len;
11c1ff18 13151 }
74e1a04b 13152 /* PR 17531: file: 001-101425-0.004 */
071436c6 13153 else if (attr_len < 5)
74e1a04b 13154 {
071436c6 13155 error (_("Attribute length of %u is too small\n"), (unsigned) attr_len);
74e1a04b
NC
13156 break;
13157 }
e9847026 13158
071436c6
NC
13159 section_len -= attr_len;
13160 attr_len -= 4;
13161
13162 namelen = strnlen ((char *) p, attr_len) + 1;
13163 if (namelen == 0 || namelen >= attr_len)
e9847026
NC
13164 {
13165 error (_("Corrupt attribute section name\n"));
13166 break;
13167 }
13168
071436c6
NC
13169 printf (_("Attribute Section: "));
13170 print_symbol (INT_MAX, (const char *) p);
13171 putchar ('\n');
60bca95a
NC
13172
13173 if (public_name && streq ((char *) p, public_name))
11c1ff18
PB
13174 public_section = TRUE;
13175 else
13176 public_section = FALSE;
60bca95a
NC
13177
13178 if (streq ((char *) p, "gnu"))
104d59d1
JM
13179 gnu_section = TRUE;
13180 else
13181 gnu_section = FALSE;
60bca95a 13182
11c1ff18 13183 p += namelen;
071436c6 13184 attr_len -= namelen;
e0a31db1 13185
071436c6 13186 while (attr_len > 0 && p < contents + sect->sh_size)
11c1ff18 13187 {
e0a31db1 13188 int tag;
11c1ff18
PB
13189 int val;
13190 bfd_vma size;
071436c6 13191 unsigned char * end;
60bca95a 13192
e0a31db1 13193 /* PR binutils/17531: Safe handling of corrupt files. */
071436c6 13194 if (attr_len < 6)
e0a31db1
NC
13195 {
13196 error (_("Unused bytes at end of section\n"));
13197 section_len = 0;
13198 break;
13199 }
13200
13201 tag = *(p++);
11c1ff18 13202 size = byte_get (p, 4);
071436c6 13203 if (size > attr_len)
11c1ff18 13204 {
e9847026 13205 error (_("Bad subsection length (%u > %u)\n"),
071436c6
NC
13206 (unsigned) size, (unsigned) attr_len);
13207 size = attr_len;
11c1ff18 13208 }
e0a31db1
NC
13209 /* PR binutils/17531: Safe handling of corrupt files. */
13210 if (size < 6)
13211 {
13212 error (_("Bad subsection length (%u < 6)\n"),
13213 (unsigned) size);
13214 section_len = 0;
13215 break;
13216 }
60bca95a 13217
071436c6 13218 attr_len -= size;
11c1ff18 13219 end = p + size - 1;
071436c6 13220 assert (end <= contents + sect->sh_size);
11c1ff18 13221 p += 4;
60bca95a 13222
11c1ff18
PB
13223 switch (tag)
13224 {
13225 case 1:
2b692964 13226 printf (_("File Attributes\n"));
11c1ff18
PB
13227 break;
13228 case 2:
2b692964 13229 printf (_("Section Attributes:"));
11c1ff18
PB
13230 goto do_numlist;
13231 case 3:
2b692964 13232 printf (_("Symbol Attributes:"));
11c1ff18
PB
13233 do_numlist:
13234 for (;;)
13235 {
91d6fa6a 13236 unsigned int j;
60bca95a 13237
f6f0e17b 13238 val = read_uleb128 (p, &j, end);
91d6fa6a 13239 p += j;
11c1ff18
PB
13240 if (val == 0)
13241 break;
13242 printf (" %d", val);
13243 }
13244 printf ("\n");
13245 break;
13246 default:
2b692964 13247 printf (_("Unknown tag: %d\n"), tag);
11c1ff18
PB
13248 public_section = FALSE;
13249 break;
13250 }
60bca95a 13251
071436c6 13252 if (public_section && display_pub_attribute != NULL)
11c1ff18
PB
13253 {
13254 while (p < end)
f6f0e17b 13255 p = display_pub_attribute (p, end);
071436c6 13256 assert (p <= end);
104d59d1 13257 }
071436c6 13258 else if (gnu_section && display_proc_gnu_attribute != NULL)
104d59d1
JM
13259 {
13260 while (p < end)
13261 p = display_gnu_attribute (p,
f6f0e17b
NC
13262 display_proc_gnu_attribute,
13263 end);
071436c6 13264 assert (p <= end);
11c1ff18 13265 }
071436c6 13266 else if (p < end)
11c1ff18 13267 {
071436c6 13268 printf (_(" Unknown attribute:\n"));
f6f0e17b 13269 display_raw_attribute (p, end);
11c1ff18
PB
13270 p = end;
13271 }
071436c6
NC
13272 else
13273 attr_len = 0;
11c1ff18
PB
13274 }
13275 }
13276 }
13277 else
e9847026 13278 printf (_("Unknown format '%c' (%d)\n"), *p, *p);
d70c5fc7 13279
60bca95a 13280 free (contents);
11c1ff18
PB
13281 }
13282 return 1;
13283}
13284
104d59d1 13285static int
2cf0635d 13286process_arm_specific (FILE * file)
104d59d1
JM
13287{
13288 return process_attributes (file, "aeabi", SHT_ARM_ATTRIBUTES,
13289 display_arm_attribute, NULL);
13290}
13291
34c8bcba 13292static int
2cf0635d 13293process_power_specific (FILE * file)
34c8bcba
JM
13294{
13295 return process_attributes (file, NULL, SHT_GNU_ATTRIBUTES, NULL,
13296 display_power_gnu_attribute);
13297}
13298
9e8c70f9
DM
13299static int
13300process_sparc_specific (FILE * file)
13301{
13302 return process_attributes (file, NULL, SHT_GNU_ATTRIBUTES, NULL,
13303 display_sparc_gnu_attribute);
13304}
13305
59e6276b
JM
13306static int
13307process_tic6x_specific (FILE * file)
13308{
13309 return process_attributes (file, "c6xabi", SHT_C6000_ATTRIBUTES,
13310 display_tic6x_attribute, NULL);
13311}
13312
13761a11
NC
13313static int
13314process_msp430x_specific (FILE * file)
13315{
13316 return process_attributes (file, "mspabi", SHT_MSP430_ATTRIBUTES,
13317 display_msp430x_attribute, NULL);
13318}
13319
ccb4c951
RS
13320/* DATA points to the contents of a MIPS GOT that starts at VMA PLTGOT.
13321 Print the Address, Access and Initial fields of an entry at VMA ADDR
13322 and return the VMA of the next entry. */
13323
13324static bfd_vma
2cf0635d 13325print_mips_got_entry (unsigned char * data, bfd_vma pltgot, bfd_vma addr)
ccb4c951
RS
13326{
13327 printf (" ");
13328 print_vma (addr, LONG_HEX);
13329 printf (" ");
13330 if (addr < pltgot + 0xfff0)
13331 printf ("%6d(gp)", (int) (addr - pltgot - 0x7ff0));
13332 else
13333 printf ("%10s", "");
13334 printf (" ");
13335 if (data == NULL)
2b692964 13336 printf ("%*s", is_32bit_elf ? 8 : 16, _("<unknown>"));
ccb4c951
RS
13337 else
13338 {
13339 bfd_vma entry;
13340
13341 entry = byte_get (data + addr - pltgot, is_32bit_elf ? 4 : 8);
13342 print_vma (entry, LONG_HEX);
13343 }
13344 return addr + (is_32bit_elf ? 4 : 8);
13345}
13346
861fb55a
DJ
13347/* DATA points to the contents of a MIPS PLT GOT that starts at VMA
13348 PLTGOT. Print the Address and Initial fields of an entry at VMA
13349 ADDR and return the VMA of the next entry. */
13350
13351static bfd_vma
2cf0635d 13352print_mips_pltgot_entry (unsigned char * data, bfd_vma pltgot, bfd_vma addr)
861fb55a
DJ
13353{
13354 printf (" ");
13355 print_vma (addr, LONG_HEX);
13356 printf (" ");
13357 if (data == NULL)
2b692964 13358 printf ("%*s", is_32bit_elf ? 8 : 16, _("<unknown>"));
861fb55a
DJ
13359 else
13360 {
13361 bfd_vma entry;
13362
13363 entry = byte_get (data + addr - pltgot, is_32bit_elf ? 4 : 8);
13364 print_vma (entry, LONG_HEX);
13365 }
13366 return addr + (is_32bit_elf ? 4 : 8);
13367}
13368
351cdf24
MF
13369static void
13370print_mips_ases (unsigned int mask)
13371{
13372 if (mask & AFL_ASE_DSP)
13373 fputs ("\n\tDSP ASE", stdout);
13374 if (mask & AFL_ASE_DSPR2)
13375 fputs ("\n\tDSP R2 ASE", stdout);
13376 if (mask & AFL_ASE_EVA)
13377 fputs ("\n\tEnhanced VA Scheme", stdout);
13378 if (mask & AFL_ASE_MCU)
13379 fputs ("\n\tMCU (MicroController) ASE", stdout);
13380 if (mask & AFL_ASE_MDMX)
13381 fputs ("\n\tMDMX ASE", stdout);
13382 if (mask & AFL_ASE_MIPS3D)
13383 fputs ("\n\tMIPS-3D ASE", stdout);
13384 if (mask & AFL_ASE_MT)
13385 fputs ("\n\tMT ASE", stdout);
13386 if (mask & AFL_ASE_SMARTMIPS)
13387 fputs ("\n\tSmartMIPS ASE", stdout);
13388 if (mask & AFL_ASE_VIRT)
13389 fputs ("\n\tVZ ASE", stdout);
13390 if (mask & AFL_ASE_MSA)
13391 fputs ("\n\tMSA ASE", stdout);
13392 if (mask & AFL_ASE_MIPS16)
13393 fputs ("\n\tMIPS16 ASE", stdout);
13394 if (mask & AFL_ASE_MICROMIPS)
13395 fputs ("\n\tMICROMIPS ASE", stdout);
13396 if (mask & AFL_ASE_XPA)
13397 fputs ("\n\tXPA ASE", stdout);
13398 if (mask == 0)
13399 fprintf (stdout, "\n\t%s", _("None"));
00ac7aa0
MF
13400 else if ((mask & ~AFL_ASE_MASK) != 0)
13401 fprintf (stdout, "\n\t%s (%x)", _("Unknown"), mask & ~AFL_ASE_MASK);
351cdf24
MF
13402}
13403
13404static void
13405print_mips_isa_ext (unsigned int isa_ext)
13406{
13407 switch (isa_ext)
13408 {
13409 case 0:
13410 fputs (_("None"), stdout);
13411 break;
13412 case AFL_EXT_XLR:
13413 fputs ("RMI XLR", stdout);
13414 break;
2c629856
N
13415 case AFL_EXT_OCTEON3:
13416 fputs ("Cavium Networks Octeon3", stdout);
13417 break;
351cdf24
MF
13418 case AFL_EXT_OCTEON2:
13419 fputs ("Cavium Networks Octeon2", stdout);
13420 break;
13421 case AFL_EXT_OCTEONP:
13422 fputs ("Cavium Networks OcteonP", stdout);
13423 break;
13424 case AFL_EXT_LOONGSON_3A:
13425 fputs ("Loongson 3A", stdout);
13426 break;
13427 case AFL_EXT_OCTEON:
13428 fputs ("Cavium Networks Octeon", stdout);
13429 break;
13430 case AFL_EXT_5900:
13431 fputs ("Toshiba R5900", stdout);
13432 break;
13433 case AFL_EXT_4650:
13434 fputs ("MIPS R4650", stdout);
13435 break;
13436 case AFL_EXT_4010:
13437 fputs ("LSI R4010", stdout);
13438 break;
13439 case AFL_EXT_4100:
13440 fputs ("NEC VR4100", stdout);
13441 break;
13442 case AFL_EXT_3900:
13443 fputs ("Toshiba R3900", stdout);
13444 break;
13445 case AFL_EXT_10000:
13446 fputs ("MIPS R10000", stdout);
13447 break;
13448 case AFL_EXT_SB1:
13449 fputs ("Broadcom SB-1", stdout);
13450 break;
13451 case AFL_EXT_4111:
13452 fputs ("NEC VR4111/VR4181", stdout);
13453 break;
13454 case AFL_EXT_4120:
13455 fputs ("NEC VR4120", stdout);
13456 break;
13457 case AFL_EXT_5400:
13458 fputs ("NEC VR5400", stdout);
13459 break;
13460 case AFL_EXT_5500:
13461 fputs ("NEC VR5500", stdout);
13462 break;
13463 case AFL_EXT_LOONGSON_2E:
13464 fputs ("ST Microelectronics Loongson 2E", stdout);
13465 break;
13466 case AFL_EXT_LOONGSON_2F:
13467 fputs ("ST Microelectronics Loongson 2F", stdout);
13468 break;
13469 default:
00ac7aa0 13470 fprintf (stdout, "%s (%d)", _("Unknown"), isa_ext);
351cdf24
MF
13471 }
13472}
13473
13474static int
13475get_mips_reg_size (int reg_size)
13476{
13477 return (reg_size == AFL_REG_NONE) ? 0
13478 : (reg_size == AFL_REG_32) ? 32
13479 : (reg_size == AFL_REG_64) ? 64
13480 : (reg_size == AFL_REG_128) ? 128
13481 : -1;
13482}
13483
19e6b90e 13484static int
2cf0635d 13485process_mips_specific (FILE * file)
5b18a4bc 13486{
2cf0635d 13487 Elf_Internal_Dyn * entry;
351cdf24 13488 Elf_Internal_Shdr *sect = NULL;
19e6b90e
L
13489 size_t liblist_offset = 0;
13490 size_t liblistno = 0;
13491 size_t conflictsno = 0;
13492 size_t options_offset = 0;
13493 size_t conflicts_offset = 0;
861fb55a
DJ
13494 size_t pltrelsz = 0;
13495 size_t pltrel = 0;
ccb4c951 13496 bfd_vma pltgot = 0;
861fb55a
DJ
13497 bfd_vma mips_pltgot = 0;
13498 bfd_vma jmprel = 0;
ccb4c951
RS
13499 bfd_vma local_gotno = 0;
13500 bfd_vma gotsym = 0;
13501 bfd_vma symtabno = 0;
103f02d3 13502
2cf19d5c
JM
13503 process_attributes (file, NULL, SHT_GNU_ATTRIBUTES, NULL,
13504 display_mips_gnu_attribute);
13505
351cdf24
MF
13506 sect = find_section (".MIPS.abiflags");
13507
13508 if (sect != NULL)
13509 {
13510 Elf_External_ABIFlags_v0 *abiflags_ext;
13511 Elf_Internal_ABIFlags_v0 abiflags_in;
13512
13513 if (sizeof (Elf_External_ABIFlags_v0) != sect->sh_size)
13514 fputs ("\nCorrupt ABI Flags section.\n", stdout);
13515 else
13516 {
13517 abiflags_ext = get_data (NULL, file, sect->sh_offset, 1,
13518 sect->sh_size, _("MIPS ABI Flags section"));
13519 if (abiflags_ext)
13520 {
13521 abiflags_in.version = BYTE_GET (abiflags_ext->version);
13522 abiflags_in.isa_level = BYTE_GET (abiflags_ext->isa_level);
13523 abiflags_in.isa_rev = BYTE_GET (abiflags_ext->isa_rev);
13524 abiflags_in.gpr_size = BYTE_GET (abiflags_ext->gpr_size);
13525 abiflags_in.cpr1_size = BYTE_GET (abiflags_ext->cpr1_size);
13526 abiflags_in.cpr2_size = BYTE_GET (abiflags_ext->cpr2_size);
13527 abiflags_in.fp_abi = BYTE_GET (abiflags_ext->fp_abi);
13528 abiflags_in.isa_ext = BYTE_GET (abiflags_ext->isa_ext);
13529 abiflags_in.ases = BYTE_GET (abiflags_ext->ases);
13530 abiflags_in.flags1 = BYTE_GET (abiflags_ext->flags1);
13531 abiflags_in.flags2 = BYTE_GET (abiflags_ext->flags2);
13532
13533 printf ("\nMIPS ABI Flags Version: %d\n", abiflags_in.version);
13534 printf ("\nISA: MIPS%d", abiflags_in.isa_level);
13535 if (abiflags_in.isa_rev > 1)
13536 printf ("r%d", abiflags_in.isa_rev);
13537 printf ("\nGPR size: %d",
13538 get_mips_reg_size (abiflags_in.gpr_size));
13539 printf ("\nCPR1 size: %d",
13540 get_mips_reg_size (abiflags_in.cpr1_size));
13541 printf ("\nCPR2 size: %d",
13542 get_mips_reg_size (abiflags_in.cpr2_size));
13543 fputs ("\nFP ABI: ", stdout);
13544 print_mips_fp_abi_value (abiflags_in.fp_abi);
13545 fputs ("ISA Extension: ", stdout);
13546 print_mips_isa_ext (abiflags_in.isa_ext);
13547 fputs ("\nASEs:", stdout);
13548 print_mips_ases (abiflags_in.ases);
13549 printf ("\nFLAGS 1: %8.8lx", abiflags_in.flags1);
13550 printf ("\nFLAGS 2: %8.8lx", abiflags_in.flags2);
13551 fputc ('\n', stdout);
13552 free (abiflags_ext);
13553 }
13554 }
13555 }
13556
19e6b90e
L
13557 /* We have a lot of special sections. Thanks SGI! */
13558 if (dynamic_section == NULL)
13559 /* No information available. */
13560 return 0;
252b5132 13561
071436c6
NC
13562 for (entry = dynamic_section;
13563 /* PR 17531 file: 012-50589-0.004. */
13564 entry < dynamic_section + dynamic_nent && entry->d_tag != DT_NULL;
13565 ++entry)
252b5132
RH
13566 switch (entry->d_tag)
13567 {
13568 case DT_MIPS_LIBLIST:
d93f0186
NC
13569 liblist_offset
13570 = offset_from_vma (file, entry->d_un.d_val,
13571 liblistno * sizeof (Elf32_External_Lib));
252b5132
RH
13572 break;
13573 case DT_MIPS_LIBLISTNO:
13574 liblistno = entry->d_un.d_val;
13575 break;
13576 case DT_MIPS_OPTIONS:
d93f0186 13577 options_offset = offset_from_vma (file, entry->d_un.d_val, 0);
252b5132
RH
13578 break;
13579 case DT_MIPS_CONFLICT:
d93f0186
NC
13580 conflicts_offset
13581 = offset_from_vma (file, entry->d_un.d_val,
13582 conflictsno * sizeof (Elf32_External_Conflict));
252b5132
RH
13583 break;
13584 case DT_MIPS_CONFLICTNO:
13585 conflictsno = entry->d_un.d_val;
13586 break;
ccb4c951 13587 case DT_PLTGOT:
861fb55a
DJ
13588 pltgot = entry->d_un.d_ptr;
13589 break;
ccb4c951
RS
13590 case DT_MIPS_LOCAL_GOTNO:
13591 local_gotno = entry->d_un.d_val;
13592 break;
13593 case DT_MIPS_GOTSYM:
13594 gotsym = entry->d_un.d_val;
13595 break;
13596 case DT_MIPS_SYMTABNO:
13597 symtabno = entry->d_un.d_val;
13598 break;
861fb55a
DJ
13599 case DT_MIPS_PLTGOT:
13600 mips_pltgot = entry->d_un.d_ptr;
13601 break;
13602 case DT_PLTREL:
13603 pltrel = entry->d_un.d_val;
13604 break;
13605 case DT_PLTRELSZ:
13606 pltrelsz = entry->d_un.d_val;
13607 break;
13608 case DT_JMPREL:
13609 jmprel = entry->d_un.d_ptr;
13610 break;
252b5132
RH
13611 default:
13612 break;
13613 }
13614
13615 if (liblist_offset != 0 && liblistno != 0 && do_dynamic)
13616 {
2cf0635d 13617 Elf32_External_Lib * elib;
252b5132
RH
13618 size_t cnt;
13619
3f5e193b
NC
13620 elib = (Elf32_External_Lib *) get_data (NULL, file, liblist_offset,
13621 liblistno,
13622 sizeof (Elf32_External_Lib),
9cf03b7e 13623 _("liblist section data"));
a6e9f9df 13624 if (elib)
252b5132 13625 {
2b692964 13626 printf (_("\nSection '.liblist' contains %lu entries:\n"),
a6e9f9df 13627 (unsigned long) liblistno);
2b692964 13628 fputs (_(" Library Time Stamp Checksum Version Flags\n"),
a6e9f9df
AM
13629 stdout);
13630
13631 for (cnt = 0; cnt < liblistno; ++cnt)
252b5132 13632 {
a6e9f9df 13633 Elf32_Lib liblist;
91d6fa6a 13634 time_t atime;
a6e9f9df 13635 char timebuf[20];
2cf0635d 13636 struct tm * tmp;
a6e9f9df
AM
13637
13638 liblist.l_name = BYTE_GET (elib[cnt].l_name);
91d6fa6a 13639 atime = BYTE_GET (elib[cnt].l_time_stamp);
a6e9f9df
AM
13640 liblist.l_checksum = BYTE_GET (elib[cnt].l_checksum);
13641 liblist.l_version = BYTE_GET (elib[cnt].l_version);
13642 liblist.l_flags = BYTE_GET (elib[cnt].l_flags);
13643
91d6fa6a 13644 tmp = gmtime (&atime);
e9e44622
JJ
13645 snprintf (timebuf, sizeof (timebuf),
13646 "%04u-%02u-%02uT%02u:%02u:%02u",
13647 tmp->tm_year + 1900, tmp->tm_mon + 1, tmp->tm_mday,
13648 tmp->tm_hour, tmp->tm_min, tmp->tm_sec);
a6e9f9df 13649
31104126 13650 printf ("%3lu: ", (unsigned long) cnt);
d79b3d50
NC
13651 if (VALID_DYNAMIC_NAME (liblist.l_name))
13652 print_symbol (20, GET_DYNAMIC_NAME (liblist.l_name));
13653 else
2b692964 13654 printf (_("<corrupt: %9ld>"), liblist.l_name);
31104126
NC
13655 printf (" %s %#10lx %-7ld", timebuf, liblist.l_checksum,
13656 liblist.l_version);
a6e9f9df
AM
13657
13658 if (liblist.l_flags == 0)
2b692964 13659 puts (_(" NONE"));
a6e9f9df
AM
13660 else
13661 {
13662 static const struct
252b5132 13663 {
2cf0635d 13664 const char * name;
a6e9f9df 13665 int bit;
252b5132 13666 }
a6e9f9df
AM
13667 l_flags_vals[] =
13668 {
13669 { " EXACT_MATCH", LL_EXACT_MATCH },
13670 { " IGNORE_INT_VER", LL_IGNORE_INT_VER },
13671 { " REQUIRE_MINOR", LL_REQUIRE_MINOR },
13672 { " EXPORTS", LL_EXPORTS },
13673 { " DELAY_LOAD", LL_DELAY_LOAD },
13674 { " DELTA", LL_DELTA }
13675 };
13676 int flags = liblist.l_flags;
13677 size_t fcnt;
13678
60bca95a 13679 for (fcnt = 0; fcnt < ARRAY_SIZE (l_flags_vals); ++fcnt)
a6e9f9df
AM
13680 if ((flags & l_flags_vals[fcnt].bit) != 0)
13681 {
13682 fputs (l_flags_vals[fcnt].name, stdout);
13683 flags ^= l_flags_vals[fcnt].bit;
13684 }
13685 if (flags != 0)
13686 printf (" %#x", (unsigned int) flags);
252b5132 13687
a6e9f9df
AM
13688 puts ("");
13689 }
252b5132 13690 }
252b5132 13691
a6e9f9df
AM
13692 free (elib);
13693 }
252b5132
RH
13694 }
13695
13696 if (options_offset != 0)
13697 {
2cf0635d 13698 Elf_External_Options * eopt;
2cf0635d
NC
13699 Elf_Internal_Options * iopt;
13700 Elf_Internal_Options * option;
252b5132
RH
13701 size_t offset;
13702 int cnt;
351cdf24 13703 sect = section_headers;
252b5132
RH
13704
13705 /* Find the section header so that we get the size. */
071436c6
NC
13706 sect = find_section_by_type (SHT_MIPS_OPTIONS);
13707 /* PR 17533 file: 012-277276-0.004. */
13708 if (sect == NULL)
13709 {
13710 error (_("No MIPS_OPTIONS header found\n"));
13711 return 0;
13712 }
252b5132 13713
3f5e193b
NC
13714 eopt = (Elf_External_Options *) get_data (NULL, file, options_offset, 1,
13715 sect->sh_size, _("options"));
a6e9f9df 13716 if (eopt)
252b5132 13717 {
3f5e193b
NC
13718 iopt = (Elf_Internal_Options *)
13719 cmalloc ((sect->sh_size / sizeof (eopt)), sizeof (* iopt));
a6e9f9df
AM
13720 if (iopt == NULL)
13721 {
8b73c356 13722 error (_("Out of memory allocatinf space for MIPS options\n"));
a6e9f9df
AM
13723 return 0;
13724 }
76da6bbe 13725
a6e9f9df
AM
13726 offset = cnt = 0;
13727 option = iopt;
252b5132 13728
a6e9f9df
AM
13729 while (offset < sect->sh_size)
13730 {
2cf0635d 13731 Elf_External_Options * eoption;
252b5132 13732
a6e9f9df 13733 eoption = (Elf_External_Options *) ((char *) eopt + offset);
252b5132 13734
a6e9f9df
AM
13735 option->kind = BYTE_GET (eoption->kind);
13736 option->size = BYTE_GET (eoption->size);
13737 option->section = BYTE_GET (eoption->section);
13738 option->info = BYTE_GET (eoption->info);
76da6bbe 13739
a6e9f9df 13740 offset += option->size;
252b5132 13741
a6e9f9df
AM
13742 ++option;
13743 ++cnt;
13744 }
252b5132 13745
a6e9f9df 13746 printf (_("\nSection '%s' contains %d entries:\n"),
74e1a04b 13747 printable_section_name (sect), cnt);
76da6bbe 13748
a6e9f9df 13749 option = iopt;
252b5132 13750
a6e9f9df 13751 while (cnt-- > 0)
252b5132 13752 {
a6e9f9df
AM
13753 size_t len;
13754
13755 switch (option->kind)
252b5132 13756 {
a6e9f9df
AM
13757 case ODK_NULL:
13758 /* This shouldn't happen. */
13759 printf (" NULL %d %lx", option->section, option->info);
13760 break;
13761 case ODK_REGINFO:
13762 printf (" REGINFO ");
13763 if (elf_header.e_machine == EM_MIPS)
13764 {
13765 /* 32bit form. */
2cf0635d 13766 Elf32_External_RegInfo * ereg;
b34976b6 13767 Elf32_RegInfo reginfo;
a6e9f9df
AM
13768
13769 ereg = (Elf32_External_RegInfo *) (option + 1);
13770 reginfo.ri_gprmask = BYTE_GET (ereg->ri_gprmask);
13771 reginfo.ri_cprmask[0] = BYTE_GET (ereg->ri_cprmask[0]);
13772 reginfo.ri_cprmask[1] = BYTE_GET (ereg->ri_cprmask[1]);
13773 reginfo.ri_cprmask[2] = BYTE_GET (ereg->ri_cprmask[2]);
13774 reginfo.ri_cprmask[3] = BYTE_GET (ereg->ri_cprmask[3]);
13775 reginfo.ri_gp_value = BYTE_GET (ereg->ri_gp_value);
13776
13777 printf ("GPR %08lx GP 0x%lx\n",
13778 reginfo.ri_gprmask,
13779 (unsigned long) reginfo.ri_gp_value);
13780 printf (" CPR0 %08lx CPR1 %08lx CPR2 %08lx CPR3 %08lx\n",
13781 reginfo.ri_cprmask[0], reginfo.ri_cprmask[1],
13782 reginfo.ri_cprmask[2], reginfo.ri_cprmask[3]);
13783 }
13784 else
13785 {
13786 /* 64 bit form. */
2cf0635d 13787 Elf64_External_RegInfo * ereg;
a6e9f9df
AM
13788 Elf64_Internal_RegInfo reginfo;
13789
13790 ereg = (Elf64_External_RegInfo *) (option + 1);
13791 reginfo.ri_gprmask = BYTE_GET (ereg->ri_gprmask);
13792 reginfo.ri_cprmask[0] = BYTE_GET (ereg->ri_cprmask[0]);
13793 reginfo.ri_cprmask[1] = BYTE_GET (ereg->ri_cprmask[1]);
13794 reginfo.ri_cprmask[2] = BYTE_GET (ereg->ri_cprmask[2]);
13795 reginfo.ri_cprmask[3] = BYTE_GET (ereg->ri_cprmask[3]);
66543521 13796 reginfo.ri_gp_value = BYTE_GET (ereg->ri_gp_value);
a6e9f9df
AM
13797
13798 printf ("GPR %08lx GP 0x",
13799 reginfo.ri_gprmask);
13800 printf_vma (reginfo.ri_gp_value);
13801 printf ("\n");
13802
13803 printf (" CPR0 %08lx CPR1 %08lx CPR2 %08lx CPR3 %08lx\n",
13804 reginfo.ri_cprmask[0], reginfo.ri_cprmask[1],
13805 reginfo.ri_cprmask[2], reginfo.ri_cprmask[3]);
13806 }
13807 ++option;
13808 continue;
13809 case ODK_EXCEPTIONS:
13810 fputs (" EXCEPTIONS fpe_min(", stdout);
13811 process_mips_fpe_exception (option->info & OEX_FPU_MIN);
13812 fputs (") fpe_max(", stdout);
13813 process_mips_fpe_exception ((option->info & OEX_FPU_MAX) >> 8);
13814 fputs (")", stdout);
13815
13816 if (option->info & OEX_PAGE0)
13817 fputs (" PAGE0", stdout);
13818 if (option->info & OEX_SMM)
13819 fputs (" SMM", stdout);
13820 if (option->info & OEX_FPDBUG)
13821 fputs (" FPDBUG", stdout);
13822 if (option->info & OEX_DISMISS)
13823 fputs (" DISMISS", stdout);
13824 break;
13825 case ODK_PAD:
13826 fputs (" PAD ", stdout);
13827 if (option->info & OPAD_PREFIX)
13828 fputs (" PREFIX", stdout);
13829 if (option->info & OPAD_POSTFIX)
13830 fputs (" POSTFIX", stdout);
13831 if (option->info & OPAD_SYMBOL)
13832 fputs (" SYMBOL", stdout);
13833 break;
13834 case ODK_HWPATCH:
13835 fputs (" HWPATCH ", stdout);
13836 if (option->info & OHW_R4KEOP)
13837 fputs (" R4KEOP", stdout);
13838 if (option->info & OHW_R8KPFETCH)
13839 fputs (" R8KPFETCH", stdout);
13840 if (option->info & OHW_R5KEOP)
13841 fputs (" R5KEOP", stdout);
13842 if (option->info & OHW_R5KCVTL)
13843 fputs (" R5KCVTL", stdout);
13844 break;
13845 case ODK_FILL:
13846 fputs (" FILL ", stdout);
13847 /* XXX Print content of info word? */
13848 break;
13849 case ODK_TAGS:
13850 fputs (" TAGS ", stdout);
13851 /* XXX Print content of info word? */
13852 break;
13853 case ODK_HWAND:
13854 fputs (" HWAND ", stdout);
13855 if (option->info & OHWA0_R4KEOP_CHECKED)
13856 fputs (" R4KEOP_CHECKED", stdout);
13857 if (option->info & OHWA0_R4KEOP_CLEAN)
13858 fputs (" R4KEOP_CLEAN", stdout);
13859 break;
13860 case ODK_HWOR:
13861 fputs (" HWOR ", stdout);
13862 if (option->info & OHWA0_R4KEOP_CHECKED)
13863 fputs (" R4KEOP_CHECKED", stdout);
13864 if (option->info & OHWA0_R4KEOP_CLEAN)
13865 fputs (" R4KEOP_CLEAN", stdout);
13866 break;
13867 case ODK_GP_GROUP:
13868 printf (" GP_GROUP %#06lx self-contained %#06lx",
13869 option->info & OGP_GROUP,
13870 (option->info & OGP_SELF) >> 16);
13871 break;
13872 case ODK_IDENT:
13873 printf (" IDENT %#06lx self-contained %#06lx",
13874 option->info & OGP_GROUP,
13875 (option->info & OGP_SELF) >> 16);
13876 break;
13877 default:
13878 /* This shouldn't happen. */
13879 printf (" %3d ??? %d %lx",
13880 option->kind, option->section, option->info);
13881 break;
252b5132 13882 }
a6e9f9df 13883
2cf0635d 13884 len = sizeof (* eopt);
a6e9f9df
AM
13885 while (len < option->size)
13886 if (((char *) option)[len] >= ' '
13887 && ((char *) option)[len] < 0x7f)
13888 printf ("%c", ((char *) option)[len++]);
13889 else
13890 printf ("\\%03o", ((char *) option)[len++]);
13891
13892 fputs ("\n", stdout);
252b5132 13893 ++option;
252b5132
RH
13894 }
13895
a6e9f9df 13896 free (eopt);
252b5132 13897 }
252b5132
RH
13898 }
13899
13900 if (conflicts_offset != 0 && conflictsno != 0)
13901 {
2cf0635d 13902 Elf32_Conflict * iconf;
252b5132
RH
13903 size_t cnt;
13904
13905 if (dynamic_symbols == NULL)
13906 {
591a748a 13907 error (_("conflict list found without a dynamic symbol table\n"));
252b5132
RH
13908 return 0;
13909 }
13910
3f5e193b 13911 iconf = (Elf32_Conflict *) cmalloc (conflictsno, sizeof (* iconf));
252b5132
RH
13912 if (iconf == NULL)
13913 {
8b73c356 13914 error (_("Out of memory allocating space for dynamic conflicts\n"));
252b5132
RH
13915 return 0;
13916 }
13917
9ea033b2 13918 if (is_32bit_elf)
252b5132 13919 {
2cf0635d 13920 Elf32_External_Conflict * econf32;
a6e9f9df 13921
3f5e193b
NC
13922 econf32 = (Elf32_External_Conflict *)
13923 get_data (NULL, file, conflicts_offset, conflictsno,
13924 sizeof (* econf32), _("conflict"));
a6e9f9df
AM
13925 if (!econf32)
13926 return 0;
252b5132
RH
13927
13928 for (cnt = 0; cnt < conflictsno; ++cnt)
13929 iconf[cnt] = BYTE_GET (econf32[cnt]);
a6e9f9df
AM
13930
13931 free (econf32);
252b5132
RH
13932 }
13933 else
13934 {
2cf0635d 13935 Elf64_External_Conflict * econf64;
a6e9f9df 13936
3f5e193b
NC
13937 econf64 = (Elf64_External_Conflict *)
13938 get_data (NULL, file, conflicts_offset, conflictsno,
13939 sizeof (* econf64), _("conflict"));
a6e9f9df
AM
13940 if (!econf64)
13941 return 0;
252b5132
RH
13942
13943 for (cnt = 0; cnt < conflictsno; ++cnt)
13944 iconf[cnt] = BYTE_GET (econf64[cnt]);
a6e9f9df
AM
13945
13946 free (econf64);
252b5132
RH
13947 }
13948
c7e7ca54
NC
13949 printf (_("\nSection '.conflict' contains %lu entries:\n"),
13950 (unsigned long) conflictsno);
252b5132
RH
13951 puts (_(" Num: Index Value Name"));
13952
13953 for (cnt = 0; cnt < conflictsno; ++cnt)
13954 {
b34976b6 13955 printf ("%5lu: %8lu ", (unsigned long) cnt, iconf[cnt]);
e0a31db1
NC
13956
13957 if (iconf[cnt] >= num_dynamic_syms)
13958 printf (_("<corrupt symbol index>"));
d79b3d50 13959 else
e0a31db1
NC
13960 {
13961 Elf_Internal_Sym * psym;
13962
13963 psym = & dynamic_symbols[iconf[cnt]];
13964 print_vma (psym->st_value, FULL_HEX);
13965 putchar (' ');
13966 if (VALID_DYNAMIC_NAME (psym->st_name))
13967 print_symbol (25, GET_DYNAMIC_NAME (psym->st_name));
13968 else
13969 printf (_("<corrupt: %14ld>"), psym->st_name);
13970 }
31104126 13971 putchar ('\n');
252b5132
RH
13972 }
13973
252b5132
RH
13974 free (iconf);
13975 }
13976
ccb4c951
RS
13977 if (pltgot != 0 && local_gotno != 0)
13978 {
91d6fa6a 13979 bfd_vma ent, local_end, global_end;
bbeee7ea 13980 size_t i, offset;
2cf0635d 13981 unsigned char * data;
bbeee7ea 13982 int addr_size;
ccb4c951 13983
91d6fa6a 13984 ent = pltgot;
ccb4c951
RS
13985 addr_size = (is_32bit_elf ? 4 : 8);
13986 local_end = pltgot + local_gotno * addr_size;
ccb4c951 13987
74e1a04b
NC
13988 /* PR binutils/17533 file: 012-111227-0.004 */
13989 if (symtabno < gotsym)
13990 {
13991 error (_("The GOT symbol offset (%lu) is greater than the symbol table size (%lu)\n"),
13992 (long) gotsym, (long) symtabno);
13993 return 0;
13994 }
13995
13996 global_end = local_end + (symtabno - gotsym) * addr_size;
13997 assert (global_end >= local_end);
ccb4c951 13998 offset = offset_from_vma (file, pltgot, global_end - pltgot);
3f5e193b 13999 data = (unsigned char *) get_data (NULL, file, offset,
9cf03b7e
NC
14000 global_end - pltgot, 1,
14001 _("Global Offset Table data"));
59245841
NC
14002 if (data == NULL)
14003 return 0;
14004
ccb4c951
RS
14005 printf (_("\nPrimary GOT:\n"));
14006 printf (_(" Canonical gp value: "));
14007 print_vma (pltgot + 0x7ff0, LONG_HEX);
14008 printf ("\n\n");
14009
14010 printf (_(" Reserved entries:\n"));
14011 printf (_(" %*s %10s %*s Purpose\n"),
2b692964
NC
14012 addr_size * 2, _("Address"), _("Access"),
14013 addr_size * 2, _("Initial"));
91d6fa6a 14014 ent = print_mips_got_entry (data, pltgot, ent);
2b692964 14015 printf (_(" Lazy resolver\n"));
ccb4c951 14016 if (data
91d6fa6a 14017 && (byte_get (data + ent - pltgot, addr_size)
ccb4c951
RS
14018 >> (addr_size * 8 - 1)) != 0)
14019 {
91d6fa6a 14020 ent = print_mips_got_entry (data, pltgot, ent);
2b692964 14021 printf (_(" Module pointer (GNU extension)\n"));
ccb4c951
RS
14022 }
14023 printf ("\n");
14024
91d6fa6a 14025 if (ent < local_end)
ccb4c951
RS
14026 {
14027 printf (_(" Local entries:\n"));
cc5914eb 14028 printf (" %*s %10s %*s\n",
2b692964
NC
14029 addr_size * 2, _("Address"), _("Access"),
14030 addr_size * 2, _("Initial"));
91d6fa6a 14031 while (ent < local_end)
ccb4c951 14032 {
91d6fa6a 14033 ent = print_mips_got_entry (data, pltgot, ent);
ccb4c951
RS
14034 printf ("\n");
14035 }
14036 printf ("\n");
14037 }
14038
14039 if (gotsym < symtabno)
14040 {
14041 int sym_width;
14042
14043 printf (_(" Global entries:\n"));
cc5914eb 14044 printf (" %*s %10s %*s %*s %-7s %3s %s\n",
9cf03b7e
NC
14045 addr_size * 2, _("Address"),
14046 _("Access"),
2b692964 14047 addr_size * 2, _("Initial"),
9cf03b7e
NC
14048 addr_size * 2, _("Sym.Val."),
14049 _("Type"),
14050 /* Note for translators: "Ndx" = abbreviated form of "Index". */
14051 _("Ndx"), _("Name"));
0b4362b0 14052
ccb4c951 14053 sym_width = (is_32bit_elf ? 80 : 160) - 28 - addr_size * 6 - 1;
e0a31db1 14054
ccb4c951
RS
14055 for (i = gotsym; i < symtabno; i++)
14056 {
91d6fa6a 14057 ent = print_mips_got_entry (data, pltgot, ent);
ccb4c951 14058 printf (" ");
e0a31db1
NC
14059
14060 if (dynamic_symbols == NULL)
14061 printf (_("<no dynamic symbols>"));
14062 else if (i < num_dynamic_syms)
14063 {
14064 Elf_Internal_Sym * psym = dynamic_symbols + i;
14065
14066 print_vma (psym->st_value, LONG_HEX);
14067 printf (" %-7s %3s ",
14068 get_symbol_type (ELF_ST_TYPE (psym->st_info)),
14069 get_symbol_index_type (psym->st_shndx));
14070
14071 if (VALID_DYNAMIC_NAME (psym->st_name))
14072 print_symbol (sym_width, GET_DYNAMIC_NAME (psym->st_name));
14073 else
14074 printf (_("<corrupt: %14ld>"), psym->st_name);
14075 }
ccb4c951 14076 else
7fc5ac57
JBG
14077 printf (_("<symbol index %lu exceeds number of dynamic symbols>"),
14078 (unsigned long) i);
e0a31db1 14079
ccb4c951
RS
14080 printf ("\n");
14081 }
14082 printf ("\n");
14083 }
14084
14085 if (data)
14086 free (data);
14087 }
14088
861fb55a
DJ
14089 if (mips_pltgot != 0 && jmprel != 0 && pltrel != 0 && pltrelsz != 0)
14090 {
91d6fa6a 14091 bfd_vma ent, end;
861fb55a
DJ
14092 size_t offset, rel_offset;
14093 unsigned long count, i;
2cf0635d 14094 unsigned char * data;
861fb55a 14095 int addr_size, sym_width;
2cf0635d 14096 Elf_Internal_Rela * rels;
861fb55a
DJ
14097
14098 rel_offset = offset_from_vma (file, jmprel, pltrelsz);
14099 if (pltrel == DT_RELA)
14100 {
14101 if (!slurp_rela_relocs (file, rel_offset, pltrelsz, &rels, &count))
14102 return 0;
14103 }
14104 else
14105 {
14106 if (!slurp_rel_relocs (file, rel_offset, pltrelsz, &rels, &count))
14107 return 0;
14108 }
14109
91d6fa6a 14110 ent = mips_pltgot;
861fb55a
DJ
14111 addr_size = (is_32bit_elf ? 4 : 8);
14112 end = mips_pltgot + (2 + count) * addr_size;
14113
14114 offset = offset_from_vma (file, mips_pltgot, end - mips_pltgot);
3f5e193b 14115 data = (unsigned char *) get_data (NULL, file, offset, end - mips_pltgot,
9cf03b7e 14116 1, _("Procedure Linkage Table data"));
59245841
NC
14117 if (data == NULL)
14118 return 0;
14119
9cf03b7e 14120 printf ("\nPLT GOT:\n\n");
861fb55a
DJ
14121 printf (_(" Reserved entries:\n"));
14122 printf (_(" %*s %*s Purpose\n"),
2b692964 14123 addr_size * 2, _("Address"), addr_size * 2, _("Initial"));
91d6fa6a 14124 ent = print_mips_pltgot_entry (data, mips_pltgot, ent);
2b692964 14125 printf (_(" PLT lazy resolver\n"));
91d6fa6a 14126 ent = print_mips_pltgot_entry (data, mips_pltgot, ent);
2b692964 14127 printf (_(" Module pointer\n"));
861fb55a
DJ
14128 printf ("\n");
14129
14130 printf (_(" Entries:\n"));
cc5914eb 14131 printf (" %*s %*s %*s %-7s %3s %s\n",
2b692964
NC
14132 addr_size * 2, _("Address"),
14133 addr_size * 2, _("Initial"),
14134 addr_size * 2, _("Sym.Val."), _("Type"), _("Ndx"), _("Name"));
861fb55a
DJ
14135 sym_width = (is_32bit_elf ? 80 : 160) - 17 - addr_size * 6 - 1;
14136 for (i = 0; i < count; i++)
14137 {
df97ab2a 14138 unsigned long idx = get_reloc_symindex (rels[i].r_info);
861fb55a 14139
91d6fa6a 14140 ent = print_mips_pltgot_entry (data, mips_pltgot, ent);
861fb55a 14141 printf (" ");
e0a31db1 14142
df97ab2a
MF
14143 if (idx >= num_dynamic_syms)
14144 printf (_("<corrupt symbol index: %lu>"), idx);
861fb55a 14145 else
e0a31db1 14146 {
df97ab2a 14147 Elf_Internal_Sym * psym = dynamic_symbols + idx;
e0a31db1
NC
14148
14149 print_vma (psym->st_value, LONG_HEX);
14150 printf (" %-7s %3s ",
14151 get_symbol_type (ELF_ST_TYPE (psym->st_info)),
14152 get_symbol_index_type (psym->st_shndx));
14153 if (VALID_DYNAMIC_NAME (psym->st_name))
14154 print_symbol (sym_width, GET_DYNAMIC_NAME (psym->st_name));
14155 else
14156 printf (_("<corrupt: %14ld>"), psym->st_name);
14157 }
861fb55a
DJ
14158 printf ("\n");
14159 }
14160 printf ("\n");
14161
14162 if (data)
14163 free (data);
14164 free (rels);
14165 }
14166
252b5132
RH
14167 return 1;
14168}
14169
35c08157
KLC
14170static int
14171process_nds32_specific (FILE * file)
14172{
14173 Elf_Internal_Shdr *sect = NULL;
14174
14175 sect = find_section (".nds32_e_flags");
14176 if (sect != NULL)
14177 {
14178 unsigned int *flag;
14179
14180 printf ("\nNDS32 elf flags section:\n");
14181 flag = get_data (NULL, file, sect->sh_offset, 1,
14182 sect->sh_size, _("NDS32 elf flags section"));
14183
14184 switch ((*flag) & 0x3)
14185 {
14186 case 0:
14187 printf ("(VEC_SIZE):\tNo entry.\n");
14188 break;
14189 case 1:
14190 printf ("(VEC_SIZE):\t4 bytes\n");
14191 break;
14192 case 2:
14193 printf ("(VEC_SIZE):\t16 bytes\n");
14194 break;
14195 case 3:
14196 printf ("(VEC_SIZE):\treserved\n");
14197 break;
14198 }
14199 }
14200
14201 return TRUE;
14202}
14203
047b2264 14204static int
2cf0635d 14205process_gnu_liblist (FILE * file)
047b2264 14206{
2cf0635d
NC
14207 Elf_Internal_Shdr * section;
14208 Elf_Internal_Shdr * string_sec;
14209 Elf32_External_Lib * elib;
14210 char * strtab;
c256ffe7 14211 size_t strtab_size;
047b2264
JJ
14212 size_t cnt;
14213 unsigned i;
14214
14215 if (! do_arch)
14216 return 0;
14217
14218 for (i = 0, section = section_headers;
14219 i < elf_header.e_shnum;
b34976b6 14220 i++, section++)
047b2264
JJ
14221 {
14222 switch (section->sh_type)
14223 {
14224 case SHT_GNU_LIBLIST:
4fbb74a6 14225 if (section->sh_link >= elf_header.e_shnum)
c256ffe7
JJ
14226 break;
14227
3f5e193b
NC
14228 elib = (Elf32_External_Lib *)
14229 get_data (NULL, file, section->sh_offset, 1, section->sh_size,
9cf03b7e 14230 _("liblist section data"));
047b2264
JJ
14231
14232 if (elib == NULL)
14233 break;
4fbb74a6 14234 string_sec = section_headers + section->sh_link;
047b2264 14235
3f5e193b
NC
14236 strtab = (char *) get_data (NULL, file, string_sec->sh_offset, 1,
14237 string_sec->sh_size,
14238 _("liblist string table"));
047b2264
JJ
14239 if (strtab == NULL
14240 || section->sh_entsize != sizeof (Elf32_External_Lib))
14241 {
14242 free (elib);
2842702f 14243 free (strtab);
047b2264
JJ
14244 break;
14245 }
59245841 14246 strtab_size = string_sec->sh_size;
047b2264
JJ
14247
14248 printf (_("\nLibrary list section '%s' contains %lu entries:\n"),
74e1a04b 14249 printable_section_name (section),
0af1713e 14250 (unsigned long) (section->sh_size / sizeof (Elf32_External_Lib)));
047b2264 14251
2b692964 14252 puts (_(" Library Time Stamp Checksum Version Flags"));
047b2264
JJ
14253
14254 for (cnt = 0; cnt < section->sh_size / sizeof (Elf32_External_Lib);
14255 ++cnt)
14256 {
14257 Elf32_Lib liblist;
91d6fa6a 14258 time_t atime;
047b2264 14259 char timebuf[20];
2cf0635d 14260 struct tm * tmp;
047b2264
JJ
14261
14262 liblist.l_name = BYTE_GET (elib[cnt].l_name);
91d6fa6a 14263 atime = BYTE_GET (elib[cnt].l_time_stamp);
047b2264
JJ
14264 liblist.l_checksum = BYTE_GET (elib[cnt].l_checksum);
14265 liblist.l_version = BYTE_GET (elib[cnt].l_version);
14266 liblist.l_flags = BYTE_GET (elib[cnt].l_flags);
14267
91d6fa6a 14268 tmp = gmtime (&atime);
e9e44622
JJ
14269 snprintf (timebuf, sizeof (timebuf),
14270 "%04u-%02u-%02uT%02u:%02u:%02u",
14271 tmp->tm_year + 1900, tmp->tm_mon + 1, tmp->tm_mday,
14272 tmp->tm_hour, tmp->tm_min, tmp->tm_sec);
047b2264
JJ
14273
14274 printf ("%3lu: ", (unsigned long) cnt);
14275 if (do_wide)
c256ffe7 14276 printf ("%-20s", liblist.l_name < strtab_size
2b692964 14277 ? strtab + liblist.l_name : _("<corrupt>"));
047b2264 14278 else
c256ffe7 14279 printf ("%-20.20s", liblist.l_name < strtab_size
2b692964 14280 ? strtab + liblist.l_name : _("<corrupt>"));
047b2264
JJ
14281 printf (" %s %#010lx %-7ld %-7ld\n", timebuf, liblist.l_checksum,
14282 liblist.l_version, liblist.l_flags);
14283 }
14284
14285 free (elib);
2842702f 14286 free (strtab);
047b2264
JJ
14287 }
14288 }
14289
14290 return 1;
14291}
14292
9437c45b 14293static const char *
d3ba0551 14294get_note_type (unsigned e_type)
779fe533
NC
14295{
14296 static char buff[64];
103f02d3 14297
1ec5cd37
NC
14298 if (elf_header.e_type == ET_CORE)
14299 switch (e_type)
14300 {
57346661 14301 case NT_AUXV:
1ec5cd37 14302 return _("NT_AUXV (auxiliary vector)");
57346661 14303 case NT_PRSTATUS:
1ec5cd37 14304 return _("NT_PRSTATUS (prstatus structure)");
57346661 14305 case NT_FPREGSET:
1ec5cd37 14306 return _("NT_FPREGSET (floating point registers)");
57346661 14307 case NT_PRPSINFO:
1ec5cd37 14308 return _("NT_PRPSINFO (prpsinfo structure)");
57346661 14309 case NT_TASKSTRUCT:
1ec5cd37 14310 return _("NT_TASKSTRUCT (task structure)");
57346661 14311 case NT_PRXFPREG:
1ec5cd37 14312 return _("NT_PRXFPREG (user_xfpregs structure)");
e1e95dec
AM
14313 case NT_PPC_VMX:
14314 return _("NT_PPC_VMX (ppc Altivec registers)");
89eeb0bc
LM
14315 case NT_PPC_VSX:
14316 return _("NT_PPC_VSX (ppc VSX registers)");
ff826ef3
TT
14317 case NT_386_TLS:
14318 return _("NT_386_TLS (x86 TLS information)");
14319 case NT_386_IOPERM:
14320 return _("NT_386_IOPERM (x86 I/O permissions)");
4339cae0
L
14321 case NT_X86_XSTATE:
14322 return _("NT_X86_XSTATE (x86 XSAVE extended state)");
0675e188
UW
14323 case NT_S390_HIGH_GPRS:
14324 return _("NT_S390_HIGH_GPRS (s390 upper register halves)");
d7eeb400
MS
14325 case NT_S390_TIMER:
14326 return _("NT_S390_TIMER (s390 timer register)");
14327 case NT_S390_TODCMP:
14328 return _("NT_S390_TODCMP (s390 TOD comparator register)");
14329 case NT_S390_TODPREG:
14330 return _("NT_S390_TODPREG (s390 TOD programmable register)");
14331 case NT_S390_CTRS:
14332 return _("NT_S390_CTRS (s390 control registers)");
14333 case NT_S390_PREFIX:
14334 return _("NT_S390_PREFIX (s390 prefix register)");
a367d729
AK
14335 case NT_S390_LAST_BREAK:
14336 return _("NT_S390_LAST_BREAK (s390 last breaking event address)");
14337 case NT_S390_SYSTEM_CALL:
14338 return _("NT_S390_SYSTEM_CALL (s390 system call restart data)");
abb3f6cc
NC
14339 case NT_S390_TDB:
14340 return _("NT_S390_TDB (s390 transaction diagnostic block)");
faa9a424
UW
14341 case NT_ARM_VFP:
14342 return _("NT_ARM_VFP (arm VFP registers)");
652451f8
YZ
14343 case NT_ARM_TLS:
14344 return _("NT_ARM_TLS (AArch TLS registers)");
14345 case NT_ARM_HW_BREAK:
14346 return _("NT_ARM_HW_BREAK (AArch hardware breakpoint registers)");
14347 case NT_ARM_HW_WATCH:
14348 return _("NT_ARM_HW_WATCH (AArch hardware watchpoint registers)");
57346661 14349 case NT_PSTATUS:
1ec5cd37 14350 return _("NT_PSTATUS (pstatus structure)");
57346661 14351 case NT_FPREGS:
1ec5cd37 14352 return _("NT_FPREGS (floating point registers)");
57346661 14353 case NT_PSINFO:
1ec5cd37 14354 return _("NT_PSINFO (psinfo structure)");
57346661 14355 case NT_LWPSTATUS:
1ec5cd37 14356 return _("NT_LWPSTATUS (lwpstatus_t structure)");
57346661 14357 case NT_LWPSINFO:
1ec5cd37 14358 return _("NT_LWPSINFO (lwpsinfo_t structure)");
57346661 14359 case NT_WIN32PSTATUS:
1ec5cd37 14360 return _("NT_WIN32PSTATUS (win32_pstatus structure)");
9ece1fa9
TT
14361 case NT_SIGINFO:
14362 return _("NT_SIGINFO (siginfo_t data)");
14363 case NT_FILE:
14364 return _("NT_FILE (mapped files)");
1ec5cd37
NC
14365 default:
14366 break;
14367 }
14368 else
14369 switch (e_type)
14370 {
14371 case NT_VERSION:
14372 return _("NT_VERSION (version)");
14373 case NT_ARCH:
14374 return _("NT_ARCH (architecture)");
14375 default:
14376 break;
14377 }
14378
e9e44622 14379 snprintf (buff, sizeof (buff), _("Unknown note type: (0x%08x)"), e_type);
1ec5cd37 14380 return buff;
779fe533
NC
14381}
14382
9ece1fa9
TT
14383static int
14384print_core_note (Elf_Internal_Note *pnote)
14385{
14386 unsigned int addr_size = is_32bit_elf ? 4 : 8;
14387 bfd_vma count, page_size;
14388 unsigned char *descdata, *filenames, *descend;
14389
14390 if (pnote->type != NT_FILE)
14391 return 1;
14392
14393#ifndef BFD64
14394 if (!is_32bit_elf)
14395 {
14396 printf (_(" Cannot decode 64-bit note in 32-bit build\n"));
14397 /* Still "successful". */
14398 return 1;
14399 }
14400#endif
14401
14402 if (pnote->descsz < 2 * addr_size)
14403 {
14404 printf (_(" Malformed note - too short for header\n"));
14405 return 0;
14406 }
14407
14408 descdata = (unsigned char *) pnote->descdata;
14409 descend = descdata + pnote->descsz;
14410
14411 if (descdata[pnote->descsz - 1] != '\0')
14412 {
14413 printf (_(" Malformed note - does not end with \\0\n"));
14414 return 0;
14415 }
14416
14417 count = byte_get (descdata, addr_size);
14418 descdata += addr_size;
14419
14420 page_size = byte_get (descdata, addr_size);
14421 descdata += addr_size;
14422
14423 if (pnote->descsz < 2 * addr_size + count * 3 * addr_size)
14424 {
14425 printf (_(" Malformed note - too short for supplied file count\n"));
14426 return 0;
14427 }
14428
14429 printf (_(" Page size: "));
14430 print_vma (page_size, DEC);
14431 printf ("\n");
14432
14433 printf (_(" %*s%*s%*s\n"),
14434 (int) (2 + 2 * addr_size), _("Start"),
14435 (int) (4 + 2 * addr_size), _("End"),
14436 (int) (4 + 2 * addr_size), _("Page Offset"));
14437 filenames = descdata + count * 3 * addr_size;
14438 while (--count > 0)
14439 {
14440 bfd_vma start, end, file_ofs;
14441
14442 if (filenames == descend)
14443 {
14444 printf (_(" Malformed note - filenames end too early\n"));
14445 return 0;
14446 }
14447
14448 start = byte_get (descdata, addr_size);
14449 descdata += addr_size;
14450 end = byte_get (descdata, addr_size);
14451 descdata += addr_size;
14452 file_ofs = byte_get (descdata, addr_size);
14453 descdata += addr_size;
14454
14455 printf (" ");
14456 print_vma (start, FULL_HEX);
14457 printf (" ");
14458 print_vma (end, FULL_HEX);
14459 printf (" ");
14460 print_vma (file_ofs, FULL_HEX);
14461 printf ("\n %s\n", filenames);
14462
14463 filenames += 1 + strlen ((char *) filenames);
14464 }
14465
14466 return 1;
14467}
14468
1118d252
RM
14469static const char *
14470get_gnu_elf_note_type (unsigned e_type)
14471{
14472 static char buff[64];
14473
14474 switch (e_type)
14475 {
14476 case NT_GNU_ABI_TAG:
14477 return _("NT_GNU_ABI_TAG (ABI version tag)");
14478 case NT_GNU_HWCAP:
14479 return _("NT_GNU_HWCAP (DSO-supplied software HWCAP info)");
14480 case NT_GNU_BUILD_ID:
14481 return _("NT_GNU_BUILD_ID (unique build ID bitstring)");
0297aed6
DM
14482 case NT_GNU_GOLD_VERSION:
14483 return _("NT_GNU_GOLD_VERSION (gold version)");
1118d252
RM
14484 default:
14485 break;
14486 }
14487
14488 snprintf (buff, sizeof (buff), _("Unknown note type: (0x%08x)"), e_type);
14489 return buff;
14490}
14491
664f90a3
TT
14492static int
14493print_gnu_note (Elf_Internal_Note *pnote)
14494{
14495 switch (pnote->type)
14496 {
14497 case NT_GNU_BUILD_ID:
14498 {
14499 unsigned long i;
14500
14501 printf (_(" Build ID: "));
14502 for (i = 0; i < pnote->descsz; ++i)
14503 printf ("%02x", pnote->descdata[i] & 0xff);
9cf03b7e 14504 printf ("\n");
664f90a3
TT
14505 }
14506 break;
14507
14508 case NT_GNU_ABI_TAG:
14509 {
14510 unsigned long os, major, minor, subminor;
14511 const char *osname;
14512
3102e897
NC
14513 /* PR 17531: file: 030-599401-0.004. */
14514 if (pnote->descsz < 16)
14515 {
14516 printf (_(" <corrupt GNU_ABI_TAG>\n"));
14517 break;
14518 }
14519
664f90a3
TT
14520 os = byte_get ((unsigned char *) pnote->descdata, 4);
14521 major = byte_get ((unsigned char *) pnote->descdata + 4, 4);
14522 minor = byte_get ((unsigned char *) pnote->descdata + 8, 4);
14523 subminor = byte_get ((unsigned char *) pnote->descdata + 12, 4);
14524
14525 switch (os)
14526 {
14527 case GNU_ABI_TAG_LINUX:
14528 osname = "Linux";
14529 break;
14530 case GNU_ABI_TAG_HURD:
14531 osname = "Hurd";
14532 break;
14533 case GNU_ABI_TAG_SOLARIS:
14534 osname = "Solaris";
14535 break;
14536 case GNU_ABI_TAG_FREEBSD:
14537 osname = "FreeBSD";
14538 break;
14539 case GNU_ABI_TAG_NETBSD:
14540 osname = "NetBSD";
14541 break;
14542 default:
14543 osname = "Unknown";
14544 break;
14545 }
14546
14547 printf (_(" OS: %s, ABI: %ld.%ld.%ld\n"), osname,
14548 major, minor, subminor);
14549 }
14550 break;
926c5385
CC
14551
14552 case NT_GNU_GOLD_VERSION:
14553 {
14554 unsigned long i;
14555
14556 printf (_(" Version: "));
14557 for (i = 0; i < pnote->descsz && pnote->descdata[i] != '\0'; ++i)
14558 printf ("%c", pnote->descdata[i]);
14559 printf ("\n");
14560 }
14561 break;
664f90a3
TT
14562 }
14563
14564 return 1;
14565}
14566
9437c45b 14567static const char *
d3ba0551 14568get_netbsd_elfcore_note_type (unsigned e_type)
9437c45b
JT
14569{
14570 static char buff[64];
14571
b4db1224 14572 if (e_type == NT_NETBSDCORE_PROCINFO)
9437c45b
JT
14573 {
14574 /* NetBSD core "procinfo" structure. */
14575 return _("NetBSD procinfo structure");
14576 }
14577
14578 /* As of Jan 2002 there are no other machine-independent notes
14579 defined for NetBSD core files. If the note type is less
14580 than the start of the machine-dependent note types, we don't
14581 understand it. */
14582
b4db1224 14583 if (e_type < NT_NETBSDCORE_FIRSTMACH)
9437c45b 14584 {
e9e44622 14585 snprintf (buff, sizeof (buff), _("Unknown note type: (0x%08x)"), e_type);
9437c45b
JT
14586 return buff;
14587 }
14588
14589 switch (elf_header.e_machine)
14590 {
14591 /* On the Alpha, SPARC (32-bit and 64-bit), PT_GETREGS == mach+0
14592 and PT_GETFPREGS == mach+2. */
14593
14594 case EM_OLD_ALPHA:
14595 case EM_ALPHA:
14596 case EM_SPARC:
14597 case EM_SPARC32PLUS:
14598 case EM_SPARCV9:
14599 switch (e_type)
14600 {
2b692964 14601 case NT_NETBSDCORE_FIRSTMACH + 0:
b4db1224 14602 return _("PT_GETREGS (reg structure)");
2b692964 14603 case NT_NETBSDCORE_FIRSTMACH + 2:
b4db1224 14604 return _("PT_GETFPREGS (fpreg structure)");
9437c45b
JT
14605 default:
14606 break;
14607 }
14608 break;
14609
14610 /* On all other arch's, PT_GETREGS == mach+1 and
14611 PT_GETFPREGS == mach+3. */
14612 default:
14613 switch (e_type)
14614 {
2b692964 14615 case NT_NETBSDCORE_FIRSTMACH + 1:
b4db1224 14616 return _("PT_GETREGS (reg structure)");
2b692964 14617 case NT_NETBSDCORE_FIRSTMACH + 3:
b4db1224 14618 return _("PT_GETFPREGS (fpreg structure)");
9437c45b
JT
14619 default:
14620 break;
14621 }
14622 }
14623
9cf03b7e 14624 snprintf (buff, sizeof (buff), "PT_FIRSTMACH+%d",
e9e44622 14625 e_type - NT_NETBSDCORE_FIRSTMACH);
9437c45b
JT
14626 return buff;
14627}
14628
70616151
TT
14629static const char *
14630get_stapsdt_note_type (unsigned e_type)
14631{
14632 static char buff[64];
14633
14634 switch (e_type)
14635 {
14636 case NT_STAPSDT:
14637 return _("NT_STAPSDT (SystemTap probe descriptors)");
14638
14639 default:
14640 break;
14641 }
14642
14643 snprintf (buff, sizeof (buff), _("Unknown note type: (0x%08x)"), e_type);
14644 return buff;
14645}
14646
c6a9fc58
TT
14647static int
14648print_stapsdt_note (Elf_Internal_Note *pnote)
14649{
14650 int addr_size = is_32bit_elf ? 4 : 8;
14651 char *data = pnote->descdata;
14652 char *data_end = pnote->descdata + pnote->descsz;
14653 bfd_vma pc, base_addr, semaphore;
14654 char *provider, *probe, *arg_fmt;
14655
14656 pc = byte_get ((unsigned char *) data, addr_size);
14657 data += addr_size;
14658 base_addr = byte_get ((unsigned char *) data, addr_size);
14659 data += addr_size;
14660 semaphore = byte_get ((unsigned char *) data, addr_size);
14661 data += addr_size;
14662
14663 provider = data;
14664 data += strlen (data) + 1;
14665 probe = data;
14666 data += strlen (data) + 1;
14667 arg_fmt = data;
14668 data += strlen (data) + 1;
14669
14670 printf (_(" Provider: %s\n"), provider);
14671 printf (_(" Name: %s\n"), probe);
14672 printf (_(" Location: "));
14673 print_vma (pc, FULL_HEX);
14674 printf (_(", Base: "));
14675 print_vma (base_addr, FULL_HEX);
14676 printf (_(", Semaphore: "));
14677 print_vma (semaphore, FULL_HEX);
9cf03b7e 14678 printf ("\n");
c6a9fc58
TT
14679 printf (_(" Arguments: %s\n"), arg_fmt);
14680
14681 return data == data_end;
14682}
14683
00e98fc7
TG
14684static const char *
14685get_ia64_vms_note_type (unsigned e_type)
14686{
14687 static char buff[64];
14688
14689 switch (e_type)
14690 {
14691 case NT_VMS_MHD:
14692 return _("NT_VMS_MHD (module header)");
14693 case NT_VMS_LNM:
14694 return _("NT_VMS_LNM (language name)");
14695 case NT_VMS_SRC:
14696 return _("NT_VMS_SRC (source files)");
14697 case NT_VMS_TITLE:
9cf03b7e 14698 return "NT_VMS_TITLE";
00e98fc7
TG
14699 case NT_VMS_EIDC:
14700 return _("NT_VMS_EIDC (consistency check)");
14701 case NT_VMS_FPMODE:
14702 return _("NT_VMS_FPMODE (FP mode)");
14703 case NT_VMS_LINKTIME:
9cf03b7e 14704 return "NT_VMS_LINKTIME";
00e98fc7
TG
14705 case NT_VMS_IMGNAM:
14706 return _("NT_VMS_IMGNAM (image name)");
14707 case NT_VMS_IMGID:
14708 return _("NT_VMS_IMGID (image id)");
14709 case NT_VMS_LINKID:
14710 return _("NT_VMS_LINKID (link id)");
14711 case NT_VMS_IMGBID:
14712 return _("NT_VMS_IMGBID (build id)");
14713 case NT_VMS_GSTNAM:
14714 return _("NT_VMS_GSTNAM (sym table name)");
14715 case NT_VMS_ORIG_DYN:
9cf03b7e 14716 return "NT_VMS_ORIG_DYN";
00e98fc7 14717 case NT_VMS_PATCHTIME:
9cf03b7e 14718 return "NT_VMS_PATCHTIME";
00e98fc7
TG
14719 default:
14720 snprintf (buff, sizeof (buff), _("Unknown note type: (0x%08x)"), e_type);
14721 return buff;
14722 }
14723}
14724
14725static int
14726print_ia64_vms_note (Elf_Internal_Note * pnote)
14727{
14728 switch (pnote->type)
14729 {
14730 case NT_VMS_MHD:
14731 if (pnote->descsz > 36)
14732 {
14733 size_t l = strlen (pnote->descdata + 34);
14734 printf (_(" Creation date : %.17s\n"), pnote->descdata);
14735 printf (_(" Last patch date: %.17s\n"), pnote->descdata + 17);
14736 printf (_(" Module name : %s\n"), pnote->descdata + 34);
14737 printf (_(" Module version : %s\n"), pnote->descdata + 34 + l + 1);
14738 }
14739 else
14740 printf (_(" Invalid size\n"));
14741 break;
14742 case NT_VMS_LNM:
14743 printf (_(" Language: %s\n"), pnote->descdata);
14744 break;
14745#ifdef BFD64
14746 case NT_VMS_FPMODE:
9cf03b7e 14747 printf (_(" Floating Point mode: "));
4a5cb34f 14748 printf ("0x%016" BFD_VMA_FMT "x\n",
00e98fc7
TG
14749 (bfd_vma)byte_get ((unsigned char *)pnote->descdata, 8));
14750 break;
14751 case NT_VMS_LINKTIME:
14752 printf (_(" Link time: "));
14753 print_vms_time
14754 ((bfd_int64_t) byte_get ((unsigned char *)pnote->descdata, 8));
14755 printf ("\n");
14756 break;
14757 case NT_VMS_PATCHTIME:
14758 printf (_(" Patch time: "));
14759 print_vms_time
14760 ((bfd_int64_t) byte_get ((unsigned char *)pnote->descdata, 8));
14761 printf ("\n");
14762 break;
14763 case NT_VMS_ORIG_DYN:
14764 printf (_(" Major id: %u, minor id: %u\n"),
14765 (unsigned) byte_get ((unsigned char *)pnote->descdata, 4),
14766 (unsigned) byte_get ((unsigned char *)pnote->descdata + 4, 4));
9cf03b7e 14767 printf (_(" Last modified : "));
00e98fc7
TG
14768 print_vms_time
14769 ((bfd_int64_t) byte_get ((unsigned char *)pnote->descdata + 8, 8));
9cf03b7e 14770 printf (_("\n Link flags : "));
4a5cb34f 14771 printf ("0x%016" BFD_VMA_FMT "x\n",
00e98fc7
TG
14772 (bfd_vma)byte_get ((unsigned char *)pnote->descdata + 16, 8));
14773 printf (_(" Header flags: 0x%08x\n"),
14774 (unsigned)byte_get ((unsigned char *)pnote->descdata + 24, 4));
14775 printf (_(" Image id : %s\n"), pnote->descdata + 32);
14776 break;
14777#endif
14778 case NT_VMS_IMGNAM:
14779 printf (_(" Image name: %s\n"), pnote->descdata);
14780 break;
14781 case NT_VMS_GSTNAM:
14782 printf (_(" Global symbol table name: %s\n"), pnote->descdata);
14783 break;
14784 case NT_VMS_IMGID:
14785 printf (_(" Image id: %s\n"), pnote->descdata);
14786 break;
14787 case NT_VMS_LINKID:
14788 printf (_(" Linker id: %s\n"), pnote->descdata);
14789 break;
14790 default:
14791 break;
14792 }
14793 return 1;
14794}
14795
6d118b09
NC
14796/* Note that by the ELF standard, the name field is already null byte
14797 terminated, and namesz includes the terminating null byte.
14798 I.E. the value of namesz for the name "FSF" is 4.
14799
e3c8793a 14800 If the value of namesz is zero, there is no name present. */
779fe533 14801static int
2cf0635d 14802process_note (Elf_Internal_Note * pnote)
779fe533 14803{
2cf0635d
NC
14804 const char * name = pnote->namesz ? pnote->namedata : "(NONE)";
14805 const char * nt;
9437c45b
JT
14806
14807 if (pnote->namesz == 0)
1ec5cd37
NC
14808 /* If there is no note name, then use the default set of
14809 note type strings. */
14810 nt = get_note_type (pnote->type);
14811
1118d252
RM
14812 else if (const_strneq (pnote->namedata, "GNU"))
14813 /* GNU-specific object file notes. */
14814 nt = get_gnu_elf_note_type (pnote->type);
14815
0112cd26 14816 else if (const_strneq (pnote->namedata, "NetBSD-CORE"))
1ec5cd37
NC
14817 /* NetBSD-specific core file notes. */
14818 nt = get_netbsd_elfcore_note_type (pnote->type);
14819
b15fa79e
AM
14820 else if (strneq (pnote->namedata, "SPU/", 4))
14821 {
14822 /* SPU-specific core file notes. */
14823 nt = pnote->namedata + 4;
14824 name = "SPU";
14825 }
14826
00e98fc7
TG
14827 else if (const_strneq (pnote->namedata, "IPF/VMS"))
14828 /* VMS/ia64-specific file notes. */
14829 nt = get_ia64_vms_note_type (pnote->type);
14830
70616151
TT
14831 else if (const_strneq (pnote->namedata, "stapsdt"))
14832 nt = get_stapsdt_note_type (pnote->type);
14833
9437c45b 14834 else
1ec5cd37
NC
14835 /* Don't recognize this note name; just use the default set of
14836 note type strings. */
00e98fc7 14837 nt = get_note_type (pnote->type);
9437c45b 14838
2aee03ae 14839 printf (" %-20s 0x%08lx\t%s\n", name, pnote->descsz, nt);
00e98fc7
TG
14840
14841 if (const_strneq (pnote->namedata, "IPF/VMS"))
14842 return print_ia64_vms_note (pnote);
664f90a3
TT
14843 else if (const_strneq (pnote->namedata, "GNU"))
14844 return print_gnu_note (pnote);
c6a9fc58
TT
14845 else if (const_strneq (pnote->namedata, "stapsdt"))
14846 return print_stapsdt_note (pnote);
9ece1fa9
TT
14847 else if (const_strneq (pnote->namedata, "CORE"))
14848 return print_core_note (pnote);
00e98fc7
TG
14849 else
14850 return 1;
779fe533
NC
14851}
14852
6d118b09 14853
779fe533 14854static int
2cf0635d 14855process_corefile_note_segment (FILE * file, bfd_vma offset, bfd_vma length)
779fe533 14856{
2cf0635d
NC
14857 Elf_External_Note * pnotes;
14858 Elf_External_Note * external;
b34976b6 14859 int res = 1;
103f02d3 14860
779fe533
NC
14861 if (length <= 0)
14862 return 0;
103f02d3 14863
3f5e193b 14864 pnotes = (Elf_External_Note *) get_data (NULL, file, offset, 1, length,
15b42fb0 14865 _("notes"));
dd24e3da 14866 if (pnotes == NULL)
a6e9f9df 14867 return 0;
779fe533 14868
103f02d3 14869 external = pnotes;
103f02d3 14870
9dd3a467 14871 printf (_("\nDisplaying notes found at file offset 0x%08lx with length 0x%08lx:\n"),
f3485b74 14872 (unsigned long) offset, (unsigned long) length);
2aee03ae 14873 printf (_(" %-20s %10s\tDescription\n"), _("Owner"), _("Data size"));
103f02d3 14874
15b42fb0 14875 while ((char *) external < (char *) pnotes + length)
779fe533 14876 {
b34976b6 14877 Elf_Internal_Note inote;
15b42fb0
AM
14878 size_t min_notesz;
14879 char *next;
2cf0635d 14880 char * temp = NULL;
15b42fb0 14881 size_t data_remaining = ((char *) pnotes + length) - (char *) external;
6d118b09 14882
00e98fc7 14883 if (!is_ia64_vms ())
15b42fb0 14884 {
9dd3a467
NC
14885 /* PR binutils/15191
14886 Make sure that there is enough data to read. */
15b42fb0
AM
14887 min_notesz = offsetof (Elf_External_Note, name);
14888 if (data_remaining < min_notesz)
9dd3a467
NC
14889 {
14890 warn (_("Corrupt note: only %d bytes remain, not enough for a full note\n"),
14891 (int) data_remaining);
14892 break;
14893 }
15b42fb0
AM
14894 inote.type = BYTE_GET (external->type);
14895 inote.namesz = BYTE_GET (external->namesz);
14896 inote.namedata = external->name;
14897 inote.descsz = BYTE_GET (external->descsz);
14898 inote.descdata = inote.namedata + align_power (inote.namesz, 2);
14899 inote.descpos = offset + (inote.descdata - (char *) pnotes);
14900 next = inote.descdata + align_power (inote.descsz, 2);
14901 }
00e98fc7 14902 else
15b42fb0
AM
14903 {
14904 Elf64_External_VMS_Note *vms_external;
00e98fc7 14905
9dd3a467
NC
14906 /* PR binutils/15191
14907 Make sure that there is enough data to read. */
15b42fb0
AM
14908 min_notesz = offsetof (Elf64_External_VMS_Note, name);
14909 if (data_remaining < min_notesz)
9dd3a467
NC
14910 {
14911 warn (_("Corrupt note: only %d bytes remain, not enough for a full note\n"),
14912 (int) data_remaining);
14913 break;
14914 }
3e55a963 14915
15b42fb0
AM
14916 vms_external = (Elf64_External_VMS_Note *) external;
14917 inote.type = BYTE_GET (vms_external->type);
14918 inote.namesz = BYTE_GET (vms_external->namesz);
14919 inote.namedata = vms_external->name;
14920 inote.descsz = BYTE_GET (vms_external->descsz);
14921 inote.descdata = inote.namedata + align_power (inote.namesz, 3);
14922 inote.descpos = offset + (inote.descdata - (char *) pnotes);
14923 next = inote.descdata + align_power (inote.descsz, 3);
14924 }
14925
14926 if (inote.descdata < (char *) external + min_notesz
14927 || next < (char *) external + min_notesz
5d921cbd
NC
14928 /* PR binutils/17531: file: id:000000,sig:11,src:006986,op:havoc,rep:4. */
14929 || inote.namedata + inote.namesz < inote.namedata
14930 || inote.descdata + inote.descsz < inote.descdata
15b42fb0 14931 || data_remaining < (size_t)(next - (char *) external))
3e55a963 14932 {
15b42fb0 14933 warn (_("note with invalid namesz and/or descsz found at offset 0x%lx\n"),
0af1713e 14934 (unsigned long) ((char *) external - (char *) pnotes));
9dd3a467 14935 warn (_(" type: 0x%lx, namesize: 0x%08lx, descsize: 0x%08lx\n"),
3e55a963
NC
14936 inote.type, inote.namesz, inote.descsz);
14937 break;
14938 }
14939
15b42fb0 14940 external = (Elf_External_Note *) next;
dd24e3da 14941
6d118b09
NC
14942 /* Verify that name is null terminated. It appears that at least
14943 one version of Linux (RedHat 6.0) generates corefiles that don't
14944 comply with the ELF spec by failing to include the null byte in
14945 namesz. */
8b971f9f 14946 if (inote.namedata[inote.namesz - 1] != '\0')
6d118b09 14947 {
3f5e193b 14948 temp = (char *) malloc (inote.namesz + 1);
6d118b09
NC
14949 if (temp == NULL)
14950 {
8b73c356 14951 error (_("Out of memory allocating space for inote name\n"));
6d118b09
NC
14952 res = 0;
14953 break;
14954 }
76da6bbe 14955
6d118b09
NC
14956 strncpy (temp, inote.namedata, inote.namesz);
14957 temp[inote.namesz] = 0;
76da6bbe 14958
6d118b09
NC
14959 /* warn (_("'%s' NOTE name not properly null terminated\n"), temp); */
14960 inote.namedata = temp;
14961 }
14962
14963 res &= process_note (& inote);
103f02d3 14964
6d118b09
NC
14965 if (temp != NULL)
14966 {
14967 free (temp);
14968 temp = NULL;
14969 }
779fe533
NC
14970 }
14971
14972 free (pnotes);
103f02d3 14973
779fe533
NC
14974 return res;
14975}
14976
14977static int
2cf0635d 14978process_corefile_note_segments (FILE * file)
779fe533 14979{
2cf0635d 14980 Elf_Internal_Phdr * segment;
b34976b6
AM
14981 unsigned int i;
14982 int res = 1;
103f02d3 14983
d93f0186 14984 if (! get_program_headers (file))
779fe533 14985 return 0;
103f02d3 14986
779fe533
NC
14987 for (i = 0, segment = program_headers;
14988 i < elf_header.e_phnum;
b34976b6 14989 i++, segment++)
779fe533
NC
14990 {
14991 if (segment->p_type == PT_NOTE)
103f02d3 14992 res &= process_corefile_note_segment (file,
30800947
NC
14993 (bfd_vma) segment->p_offset,
14994 (bfd_vma) segment->p_filesz);
779fe533 14995 }
103f02d3 14996
779fe533
NC
14997 return res;
14998}
14999
15000static int
2cf0635d 15001process_note_sections (FILE * file)
1ec5cd37 15002{
2cf0635d 15003 Elf_Internal_Shdr * section;
1ec5cd37 15004 unsigned long i;
df565f32 15005 int n = 0;
1ec5cd37
NC
15006 int res = 1;
15007
15008 for (i = 0, section = section_headers;
fa1908fd 15009 i < elf_header.e_shnum && section != NULL;
1ec5cd37
NC
15010 i++, section++)
15011 if (section->sh_type == SHT_NOTE)
df565f32
NC
15012 {
15013 res &= process_corefile_note_segment (file,
15014 (bfd_vma) section->sh_offset,
15015 (bfd_vma) section->sh_size);
15016 n++;
15017 }
15018
15019 if (n == 0)
15020 /* Try processing NOTE segments instead. */
15021 return process_corefile_note_segments (file);
1ec5cd37
NC
15022
15023 return res;
15024}
15025
15026static int
2cf0635d 15027process_notes (FILE * file)
779fe533
NC
15028{
15029 /* If we have not been asked to display the notes then do nothing. */
15030 if (! do_notes)
15031 return 1;
103f02d3 15032
779fe533 15033 if (elf_header.e_type != ET_CORE)
1ec5cd37 15034 return process_note_sections (file);
103f02d3 15035
779fe533 15036 /* No program headers means no NOTE segment. */
1ec5cd37
NC
15037 if (elf_header.e_phnum > 0)
15038 return process_corefile_note_segments (file);
779fe533 15039
1ec5cd37
NC
15040 printf (_("No note segments present in the core file.\n"));
15041 return 1;
779fe533
NC
15042}
15043
252b5132 15044static int
2cf0635d 15045process_arch_specific (FILE * file)
252b5132 15046{
a952a375
NC
15047 if (! do_arch)
15048 return 1;
15049
252b5132
RH
15050 switch (elf_header.e_machine)
15051 {
11c1ff18
PB
15052 case EM_ARM:
15053 return process_arm_specific (file);
252b5132 15054 case EM_MIPS:
4fe85591 15055 case EM_MIPS_RS3_LE:
252b5132
RH
15056 return process_mips_specific (file);
15057 break;
35c08157
KLC
15058 case EM_NDS32:
15059 return process_nds32_specific (file);
15060 break;
34c8bcba
JM
15061 case EM_PPC:
15062 return process_power_specific (file);
15063 break;
9e8c70f9
DM
15064 case EM_SPARC:
15065 case EM_SPARC32PLUS:
15066 case EM_SPARCV9:
15067 return process_sparc_specific (file);
15068 break;
59e6276b
JM
15069 case EM_TI_C6000:
15070 return process_tic6x_specific (file);
15071 break;
13761a11
NC
15072 case EM_MSP430:
15073 return process_msp430x_specific (file);
252b5132
RH
15074 default:
15075 break;
15076 }
15077 return 1;
15078}
15079
15080static int
2cf0635d 15081get_file_header (FILE * file)
252b5132 15082{
9ea033b2
NC
15083 /* Read in the identity array. */
15084 if (fread (elf_header.e_ident, EI_NIDENT, 1, file) != 1)
252b5132
RH
15085 return 0;
15086
9ea033b2 15087 /* Determine how to read the rest of the header. */
b34976b6 15088 switch (elf_header.e_ident[EI_DATA])
9ea033b2
NC
15089 {
15090 default: /* fall through */
15091 case ELFDATANONE: /* fall through */
adab8cdc
AO
15092 case ELFDATA2LSB:
15093 byte_get = byte_get_little_endian;
15094 byte_put = byte_put_little_endian;
15095 break;
15096 case ELFDATA2MSB:
15097 byte_get = byte_get_big_endian;
15098 byte_put = byte_put_big_endian;
15099 break;
9ea033b2
NC
15100 }
15101
15102 /* For now we only support 32 bit and 64 bit ELF files. */
b34976b6 15103 is_32bit_elf = (elf_header.e_ident[EI_CLASS] != ELFCLASS64);
9ea033b2
NC
15104
15105 /* Read in the rest of the header. */
15106 if (is_32bit_elf)
15107 {
15108 Elf32_External_Ehdr ehdr32;
252b5132 15109
9ea033b2
NC
15110 if (fread (ehdr32.e_type, sizeof (ehdr32) - EI_NIDENT, 1, file) != 1)
15111 return 0;
103f02d3 15112
9ea033b2
NC
15113 elf_header.e_type = BYTE_GET (ehdr32.e_type);
15114 elf_header.e_machine = BYTE_GET (ehdr32.e_machine);
15115 elf_header.e_version = BYTE_GET (ehdr32.e_version);
15116 elf_header.e_entry = BYTE_GET (ehdr32.e_entry);
15117 elf_header.e_phoff = BYTE_GET (ehdr32.e_phoff);
15118 elf_header.e_shoff = BYTE_GET (ehdr32.e_shoff);
15119 elf_header.e_flags = BYTE_GET (ehdr32.e_flags);
15120 elf_header.e_ehsize = BYTE_GET (ehdr32.e_ehsize);
15121 elf_header.e_phentsize = BYTE_GET (ehdr32.e_phentsize);
15122 elf_header.e_phnum = BYTE_GET (ehdr32.e_phnum);
15123 elf_header.e_shentsize = BYTE_GET (ehdr32.e_shentsize);
15124 elf_header.e_shnum = BYTE_GET (ehdr32.e_shnum);
15125 elf_header.e_shstrndx = BYTE_GET (ehdr32.e_shstrndx);
15126 }
252b5132 15127 else
9ea033b2
NC
15128 {
15129 Elf64_External_Ehdr ehdr64;
a952a375
NC
15130
15131 /* If we have been compiled with sizeof (bfd_vma) == 4, then
15132 we will not be able to cope with the 64bit data found in
15133 64 ELF files. Detect this now and abort before we start
50c2245b 15134 overwriting things. */
a952a375
NC
15135 if (sizeof (bfd_vma) < 8)
15136 {
e3c8793a
NC
15137 error (_("This instance of readelf has been built without support for a\n\
1513864 bit data type and so it cannot read 64 bit ELF files.\n"));
a952a375
NC
15139 return 0;
15140 }
103f02d3 15141
9ea033b2
NC
15142 if (fread (ehdr64.e_type, sizeof (ehdr64) - EI_NIDENT, 1, file) != 1)
15143 return 0;
103f02d3 15144
9ea033b2
NC
15145 elf_header.e_type = BYTE_GET (ehdr64.e_type);
15146 elf_header.e_machine = BYTE_GET (ehdr64.e_machine);
15147 elf_header.e_version = BYTE_GET (ehdr64.e_version);
66543521
AM
15148 elf_header.e_entry = BYTE_GET (ehdr64.e_entry);
15149 elf_header.e_phoff = BYTE_GET (ehdr64.e_phoff);
15150 elf_header.e_shoff = BYTE_GET (ehdr64.e_shoff);
9ea033b2
NC
15151 elf_header.e_flags = BYTE_GET (ehdr64.e_flags);
15152 elf_header.e_ehsize = BYTE_GET (ehdr64.e_ehsize);
15153 elf_header.e_phentsize = BYTE_GET (ehdr64.e_phentsize);
15154 elf_header.e_phnum = BYTE_GET (ehdr64.e_phnum);
15155 elf_header.e_shentsize = BYTE_GET (ehdr64.e_shentsize);
15156 elf_header.e_shnum = BYTE_GET (ehdr64.e_shnum);
15157 elf_header.e_shstrndx = BYTE_GET (ehdr64.e_shstrndx);
15158 }
252b5132 15159
7ece0d85
JJ
15160 if (elf_header.e_shoff)
15161 {
15162 /* There may be some extensions in the first section header. Don't
15163 bomb if we can't read it. */
15164 if (is_32bit_elf)
049b0c3a 15165 get_32bit_section_headers (file, TRUE);
7ece0d85 15166 else
049b0c3a 15167 get_64bit_section_headers (file, TRUE);
7ece0d85 15168 }
560f3c1c 15169
252b5132
RH
15170 return 1;
15171}
15172
fb52b2f4
NC
15173/* Process one ELF object file according to the command line options.
15174 This file may actually be stored in an archive. The file is
15175 positioned at the start of the ELF object. */
15176
ff78d6d6 15177static int
2cf0635d 15178process_object (char * file_name, FILE * file)
252b5132 15179{
252b5132
RH
15180 unsigned int i;
15181
252b5132
RH
15182 if (! get_file_header (file))
15183 {
15184 error (_("%s: Failed to read file header\n"), file_name);
ff78d6d6 15185 return 1;
252b5132
RH
15186 }
15187
15188 /* Initialise per file variables. */
60bca95a 15189 for (i = ARRAY_SIZE (version_info); i--;)
252b5132
RH
15190 version_info[i] = 0;
15191
60bca95a 15192 for (i = ARRAY_SIZE (dynamic_info); i--;)
252b5132 15193 dynamic_info[i] = 0;
5115b233 15194 dynamic_info_DT_GNU_HASH = 0;
252b5132
RH
15195
15196 /* Process the file. */
15197 if (show_name)
15198 printf (_("\nFile: %s\n"), file_name);
15199
18bd398b
NC
15200 /* Initialise the dump_sects array from the cmdline_dump_sects array.
15201 Note we do this even if cmdline_dump_sects is empty because we
15202 must make sure that the dump_sets array is zeroed out before each
15203 object file is processed. */
15204 if (num_dump_sects > num_cmdline_dump_sects)
09c11c86 15205 memset (dump_sects, 0, num_dump_sects * sizeof (* dump_sects));
18bd398b
NC
15206
15207 if (num_cmdline_dump_sects > 0)
15208 {
15209 if (num_dump_sects == 0)
15210 /* A sneaky way of allocating the dump_sects array. */
09c11c86 15211 request_dump_bynumber (num_cmdline_dump_sects, 0);
18bd398b
NC
15212
15213 assert (num_dump_sects >= num_cmdline_dump_sects);
09c11c86
NC
15214 memcpy (dump_sects, cmdline_dump_sects,
15215 num_cmdline_dump_sects * sizeof (* dump_sects));
18bd398b 15216 }
d70c5fc7 15217
252b5132 15218 if (! process_file_header ())
fb52b2f4 15219 return 1;
252b5132 15220
d1f5c6e3 15221 if (! process_section_headers (file))
2f62977e 15222 {
d1f5c6e3
L
15223 /* Without loaded section headers we cannot process lots of
15224 things. */
2f62977e 15225 do_unwind = do_version = do_dump = do_arch = 0;
252b5132 15226
2f62977e 15227 if (! do_using_dynamic)
2c610e4b 15228 do_syms = do_dyn_syms = do_reloc = 0;
2f62977e 15229 }
252b5132 15230
d1f5c6e3
L
15231 if (! process_section_groups (file))
15232 {
15233 /* Without loaded section groups we cannot process unwind. */
15234 do_unwind = 0;
15235 }
15236
2f62977e 15237 if (process_program_headers (file))
b2d38a17 15238 process_dynamic_section (file);
252b5132
RH
15239
15240 process_relocs (file);
15241
4d6ed7c8
NC
15242 process_unwind (file);
15243
252b5132
RH
15244 process_symbol_table (file);
15245
15246 process_syminfo (file);
15247
15248 process_version_sections (file);
15249
15250 process_section_contents (file);
f5842774 15251
1ec5cd37 15252 process_notes (file);
103f02d3 15253
047b2264
JJ
15254 process_gnu_liblist (file);
15255
252b5132
RH
15256 process_arch_specific (file);
15257
d93f0186
NC
15258 if (program_headers)
15259 {
15260 free (program_headers);
15261 program_headers = NULL;
15262 }
15263
252b5132
RH
15264 if (section_headers)
15265 {
15266 free (section_headers);
15267 section_headers = NULL;
15268 }
15269
15270 if (string_table)
15271 {
15272 free (string_table);
15273 string_table = NULL;
d40ac9bd 15274 string_table_length = 0;
252b5132
RH
15275 }
15276
15277 if (dynamic_strings)
15278 {
15279 free (dynamic_strings);
15280 dynamic_strings = NULL;
d79b3d50 15281 dynamic_strings_length = 0;
252b5132
RH
15282 }
15283
15284 if (dynamic_symbols)
15285 {
15286 free (dynamic_symbols);
15287 dynamic_symbols = NULL;
19936277 15288 num_dynamic_syms = 0;
252b5132
RH
15289 }
15290
15291 if (dynamic_syminfo)
15292 {
15293 free (dynamic_syminfo);
15294 dynamic_syminfo = NULL;
15295 }
ff78d6d6 15296
293c573e
MR
15297 if (dynamic_section)
15298 {
15299 free (dynamic_section);
15300 dynamic_section = NULL;
15301 }
15302
e4b17d5c
L
15303 if (section_headers_groups)
15304 {
15305 free (section_headers_groups);
15306 section_headers_groups = NULL;
15307 }
15308
15309 if (section_groups)
15310 {
2cf0635d
NC
15311 struct group_list * g;
15312 struct group_list * next;
e4b17d5c
L
15313
15314 for (i = 0; i < group_count; i++)
15315 {
15316 for (g = section_groups [i].root; g != NULL; g = next)
15317 {
15318 next = g->next;
15319 free (g);
15320 }
15321 }
15322
15323 free (section_groups);
15324 section_groups = NULL;
15325 }
15326
19e6b90e 15327 free_debug_memory ();
18bd398b 15328
ff78d6d6 15329 return 0;
252b5132
RH
15330}
15331
2cf0635d
NC
15332/* Process an ELF archive.
15333 On entry the file is positioned just after the ARMAG string. */
15334
15335static int
15336process_archive (char * file_name, FILE * file, bfd_boolean is_thin_archive)
15337{
15338 struct archive_info arch;
15339 struct archive_info nested_arch;
15340 size_t got;
2cf0635d
NC
15341 int ret;
15342
15343 show_name = 1;
15344
15345 /* The ARCH structure is used to hold information about this archive. */
15346 arch.file_name = NULL;
15347 arch.file = NULL;
15348 arch.index_array = NULL;
15349 arch.sym_table = NULL;
15350 arch.longnames = NULL;
15351
15352 /* The NESTED_ARCH structure is used as a single-item cache of information
15353 about a nested archive (when members of a thin archive reside within
15354 another regular archive file). */
15355 nested_arch.file_name = NULL;
15356 nested_arch.file = NULL;
15357 nested_arch.index_array = NULL;
15358 nested_arch.sym_table = NULL;
15359 nested_arch.longnames = NULL;
15360
15361 if (setup_archive (&arch, file_name, file, is_thin_archive, do_archive_index) != 0)
15362 {
15363 ret = 1;
15364 goto out;
4145f1d5 15365 }
fb52b2f4 15366
4145f1d5
NC
15367 if (do_archive_index)
15368 {
2cf0635d 15369 if (arch.sym_table == NULL)
4145f1d5
NC
15370 error (_("%s: unable to dump the index as none was found\n"), file_name);
15371 else
15372 {
591f7597 15373 unsigned long i, l;
4145f1d5
NC
15374 unsigned long current_pos;
15375
591f7597
NC
15376 printf (_("Index of archive %s: (%lu entries, 0x%lx bytes in the symbol table)\n"),
15377 file_name, (unsigned long) arch.index_num, arch.sym_size);
4145f1d5
NC
15378 current_pos = ftell (file);
15379
2cf0635d 15380 for (i = l = 0; i < arch.index_num; i++)
4145f1d5 15381 {
2cf0635d
NC
15382 if ((i == 0) || ((i > 0) && (arch.index_array[i] != arch.index_array[i - 1])))
15383 {
15384 char * member_name;
4145f1d5 15385
2cf0635d
NC
15386 member_name = get_archive_member_name_at (&arch, arch.index_array[i], &nested_arch);
15387
15388 if (member_name != NULL)
15389 {
15390 char * qualified_name = make_qualified_name (&arch, &nested_arch, member_name);
15391
15392 if (qualified_name != NULL)
15393 {
c2a7d3f5
NC
15394 printf (_("Contents of binary %s at offset "), qualified_name);
15395 (void) print_vma (arch.index_array[i], PREFIX_HEX);
15396 putchar ('\n');
2cf0635d
NC
15397 free (qualified_name);
15398 }
4145f1d5
NC
15399 }
15400 }
2cf0635d
NC
15401
15402 if (l >= arch.sym_size)
4145f1d5
NC
15403 {
15404 error (_("%s: end of the symbol table reached before the end of the index\n"),
15405 file_name);
cb8f3167 15406 break;
4145f1d5 15407 }
591f7597
NC
15408 /* PR 17531: file: 0b6630b2. */
15409 printf ("\t%.*s\n", (int) (arch.sym_size - l), arch.sym_table + l);
15410 l += strnlen (arch.sym_table + l, arch.sym_size - l) + 1;
4145f1d5
NC
15411 }
15412
c2a7d3f5
NC
15413 if (arch.uses_64bit_indicies)
15414 l = (l + 7) & ~ 7;
15415 else
15416 l += l & 1;
15417
2cf0635d 15418 if (l < arch.sym_size)
c2a7d3f5
NC
15419 error (_("%s: %ld bytes remain in the symbol table, but without corresponding entries in the index table\n"),
15420 file_name, arch.sym_size - l);
4145f1d5 15421
4145f1d5
NC
15422 if (fseek (file, current_pos, SEEK_SET) != 0)
15423 {
15424 error (_("%s: failed to seek back to start of object files in the archive\n"), file_name);
2cf0635d
NC
15425 ret = 1;
15426 goto out;
4145f1d5 15427 }
fb52b2f4 15428 }
4145f1d5
NC
15429
15430 if (!do_dynamic && !do_syms && !do_reloc && !do_unwind && !do_sections
15431 && !do_segments && !do_header && !do_dump && !do_version
15432 && !do_histogram && !do_debugging && !do_arch && !do_notes
2c610e4b 15433 && !do_section_groups && !do_dyn_syms)
2cf0635d
NC
15434 {
15435 ret = 0; /* Archive index only. */
15436 goto out;
15437 }
fb52b2f4
NC
15438 }
15439
d989285c 15440 ret = 0;
fb52b2f4
NC
15441
15442 while (1)
15443 {
2cf0635d
NC
15444 char * name;
15445 size_t namelen;
15446 char * qualified_name;
15447
15448 /* Read the next archive header. */
15449 if (fseek (file, arch.next_arhdr_offset, SEEK_SET) != 0)
15450 {
15451 error (_("%s: failed to seek to next archive header\n"), file_name);
15452 return 1;
15453 }
15454 got = fread (&arch.arhdr, 1, sizeof arch.arhdr, file);
15455 if (got != sizeof arch.arhdr)
15456 {
15457 if (got == 0)
15458 break;
15459 error (_("%s: failed to read archive header\n"), file_name);
15460 ret = 1;
15461 break;
15462 }
15463 if (memcmp (arch.arhdr.ar_fmag, ARFMAG, 2) != 0)
15464 {
15465 error (_("%s: did not find a valid archive header\n"), arch.file_name);
15466 ret = 1;
15467 break;
15468 }
15469
15470 arch.next_arhdr_offset += sizeof arch.arhdr;
15471
15472 archive_file_size = strtoul (arch.arhdr.ar_size, NULL, 10);
15473 if (archive_file_size & 01)
15474 ++archive_file_size;
15475
15476 name = get_archive_member_name (&arch, &nested_arch);
15477 if (name == NULL)
fb52b2f4 15478 {
0fd3a477 15479 error (_("%s: bad archive file name\n"), file_name);
d989285c
ILT
15480 ret = 1;
15481 break;
fb52b2f4 15482 }
2cf0635d 15483 namelen = strlen (name);
fb52b2f4 15484
2cf0635d
NC
15485 qualified_name = make_qualified_name (&arch, &nested_arch, name);
15486 if (qualified_name == NULL)
fb52b2f4 15487 {
2cf0635d 15488 error (_("%s: bad archive file name\n"), file_name);
d989285c
ILT
15489 ret = 1;
15490 break;
fb52b2f4
NC
15491 }
15492
2cf0635d
NC
15493 if (is_thin_archive && arch.nested_member_origin == 0)
15494 {
15495 /* This is a proxy for an external member of a thin archive. */
15496 FILE * member_file;
15497 char * member_file_name = adjust_relative_path (file_name, name, namelen);
15498 if (member_file_name == NULL)
15499 {
15500 ret = 1;
15501 break;
15502 }
15503
15504 member_file = fopen (member_file_name, "rb");
15505 if (member_file == NULL)
15506 {
15507 error (_("Input file '%s' is not readable.\n"), member_file_name);
15508 free (member_file_name);
15509 ret = 1;
15510 break;
15511 }
15512
15513 archive_file_offset = arch.nested_member_origin;
15514
15515 ret |= process_object (qualified_name, member_file);
15516
15517 fclose (member_file);
15518 free (member_file_name);
15519 }
15520 else if (is_thin_archive)
15521 {
a043396b
NC
15522 /* PR 15140: Allow for corrupt thin archives. */
15523 if (nested_arch.file == NULL)
15524 {
15525 error (_("%s: contains corrupt thin archive: %s\n"),
15526 file_name, name);
15527 ret = 1;
15528 break;
15529 }
15530
2cf0635d
NC
15531 /* This is a proxy for a member of a nested archive. */
15532 archive_file_offset = arch.nested_member_origin + sizeof arch.arhdr;
15533
15534 /* The nested archive file will have been opened and setup by
15535 get_archive_member_name. */
15536 if (fseek (nested_arch.file, archive_file_offset, SEEK_SET) != 0)
15537 {
15538 error (_("%s: failed to seek to archive member.\n"), nested_arch.file_name);
15539 ret = 1;
15540 break;
15541 }
15542
15543 ret |= process_object (qualified_name, nested_arch.file);
15544 }
15545 else
15546 {
15547 archive_file_offset = arch.next_arhdr_offset;
15548 arch.next_arhdr_offset += archive_file_size;
fb52b2f4 15549
2cf0635d
NC
15550 ret |= process_object (qualified_name, file);
15551 }
fb52b2f4 15552
2b52916e
L
15553 if (dump_sects != NULL)
15554 {
15555 free (dump_sects);
15556 dump_sects = NULL;
15557 num_dump_sects = 0;
15558 }
15559
2cf0635d 15560 free (qualified_name);
fb52b2f4
NC
15561 }
15562
4145f1d5 15563 out:
2cf0635d
NC
15564 if (nested_arch.file != NULL)
15565 fclose (nested_arch.file);
15566 release_archive (&nested_arch);
15567 release_archive (&arch);
fb52b2f4 15568
d989285c 15569 return ret;
fb52b2f4
NC
15570}
15571
15572static int
2cf0635d 15573process_file (char * file_name)
fb52b2f4 15574{
2cf0635d 15575 FILE * file;
fb52b2f4
NC
15576 struct stat statbuf;
15577 char armag[SARMAG];
15578 int ret;
15579
15580 if (stat (file_name, &statbuf) < 0)
15581 {
f24ddbdd
NC
15582 if (errno == ENOENT)
15583 error (_("'%s': No such file\n"), file_name);
15584 else
15585 error (_("Could not locate '%s'. System error message: %s\n"),
15586 file_name, strerror (errno));
15587 return 1;
15588 }
15589
15590 if (! S_ISREG (statbuf.st_mode))
15591 {
15592 error (_("'%s' is not an ordinary file\n"), file_name);
fb52b2f4
NC
15593 return 1;
15594 }
15595
15596 file = fopen (file_name, "rb");
15597 if (file == NULL)
15598 {
f24ddbdd 15599 error (_("Input file '%s' is not readable.\n"), file_name);
fb52b2f4
NC
15600 return 1;
15601 }
15602
15603 if (fread (armag, SARMAG, 1, file) != 1)
15604 {
4145f1d5 15605 error (_("%s: Failed to read file's magic number\n"), file_name);
fb52b2f4
NC
15606 fclose (file);
15607 return 1;
15608 }
15609
f54498b4
NC
15610 current_file_size = (bfd_size_type) statbuf.st_size;
15611
fb52b2f4 15612 if (memcmp (armag, ARMAG, SARMAG) == 0)
2cf0635d
NC
15613 ret = process_archive (file_name, file, FALSE);
15614 else if (memcmp (armag, ARMAGT, SARMAG) == 0)
15615 ret = process_archive (file_name, file, TRUE);
fb52b2f4
NC
15616 else
15617 {
4145f1d5
NC
15618 if (do_archive_index)
15619 error (_("File %s is not an archive so its index cannot be displayed.\n"),
15620 file_name);
15621
fb52b2f4
NC
15622 rewind (file);
15623 archive_file_size = archive_file_offset = 0;
15624 ret = process_object (file_name, file);
15625 }
15626
15627 fclose (file);
15628
f54498b4 15629 current_file_size = 0;
fb52b2f4
NC
15630 return ret;
15631}
15632
252b5132
RH
15633#ifdef SUPPORT_DISASSEMBLY
15634/* Needed by the i386 disassembler. For extra credit, someone could
9ea033b2 15635 fix this so that we insert symbolic addresses here, esp for GOT/PLT
e3c8793a 15636 symbols. */
252b5132
RH
15637
15638void
2cf0635d 15639print_address (unsigned int addr, FILE * outfile)
252b5132
RH
15640{
15641 fprintf (outfile,"0x%8.8x", addr);
15642}
15643
e3c8793a 15644/* Needed by the i386 disassembler. */
252b5132
RH
15645void
15646db_task_printsym (unsigned int addr)
15647{
15648 print_address (addr, stderr);
15649}
15650#endif
15651
15652int
2cf0635d 15653main (int argc, char ** argv)
252b5132 15654{
ff78d6d6
L
15655 int err;
15656
252b5132
RH
15657#if defined (HAVE_SETLOCALE) && defined (HAVE_LC_MESSAGES)
15658 setlocale (LC_MESSAGES, "");
3882b010
L
15659#endif
15660#if defined (HAVE_SETLOCALE)
15661 setlocale (LC_CTYPE, "");
252b5132
RH
15662#endif
15663 bindtextdomain (PACKAGE, LOCALEDIR);
15664 textdomain (PACKAGE);
15665
869b9d07
MM
15666 expandargv (&argc, &argv);
15667
252b5132
RH
15668 parse_args (argc, argv);
15669
18bd398b 15670 if (num_dump_sects > 0)
59f14fc0 15671 {
18bd398b 15672 /* Make a copy of the dump_sects array. */
3f5e193b
NC
15673 cmdline_dump_sects = (dump_type *)
15674 malloc (num_dump_sects * sizeof (* dump_sects));
59f14fc0 15675 if (cmdline_dump_sects == NULL)
591a748a 15676 error (_("Out of memory allocating dump request table.\n"));
59f14fc0
AS
15677 else
15678 {
09c11c86
NC
15679 memcpy (cmdline_dump_sects, dump_sects,
15680 num_dump_sects * sizeof (* dump_sects));
59f14fc0
AS
15681 num_cmdline_dump_sects = num_dump_sects;
15682 }
15683 }
15684
18bd398b
NC
15685 if (optind < (argc - 1))
15686 show_name = 1;
15687
ff78d6d6 15688 err = 0;
252b5132 15689 while (optind < argc)
18bd398b 15690 err |= process_file (argv[optind++]);
252b5132
RH
15691
15692 if (dump_sects != NULL)
15693 free (dump_sects);
59f14fc0
AS
15694 if (cmdline_dump_sects != NULL)
15695 free (cmdline_dump_sects);
252b5132 15696
ff78d6d6 15697 return err;
252b5132 15698}
This page took 2.649009 seconds and 4 git commands to generate.