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