2004-06-01 Paolo Bonzini <bonzini@gnu.org>
[binutils.git] / binutils / readelf.c
blobdcf50e8c4fa55f09a9fb2deeca9d79b63e6b88f8
1 /* readelf.c -- display contents of an ELF format file
2 Copyright 1998, 1999, 2000, 2001, 2002, 2003, 2004 Free Software Foundation, Inc.
4 Originally developed by Eric Youngdale <eric@andante.jic.com>
5 Modifications by Nick Clifton <nickc@redhat.com>
7 This file is part of GNU Binutils.
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.
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.
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. */
24 /* The difference between readelf and objdump:
26 Both programs are capabale of displaying the contents of ELF format files,
27 so why does the binutils project have two file dumpers ?
29 The reason is that objdump sees an ELF file through a BFD filter of the
30 world; if BFD has a bug where, say, it disagrees about a machine constant
31 in e_flags, then the odds are good that it will remain internally
32 consistent. The linker sees it the BFD way, objdump sees it the BFD way,
33 GAS sees it the BFD way. There was need for a tool to go find out what
34 the file actually says.
36 This is why the readelf program does not link against the BFD library - it
37 exists as an independent program to help verify the correct working of BFD.
39 There is also the case that readelf can provide more information about an
40 ELF file than is provided by objdump. In particular it can display DWARF
41 debugging information which (at the moment) objdump cannot. */
43 #include <assert.h>
44 #include <sys/types.h>
45 #include <sys/stat.h>
46 #include <stdio.h>
47 #include <time.h>
49 #if __GNUC__ >= 2
50 /* Define BFD64 here, even if our default architecture is 32 bit ELF
51 as this will allow us to read in and parse 64bit and 32bit ELF files.
52 Only do this if we believe that the compiler can support a 64 bit
53 data type. For now we only rely on GCC being able to do this. */
54 #define BFD64
55 #endif
57 #include "bfd.h"
59 #include "elf/common.h"
60 #include "elf/external.h"
61 #include "elf/internal.h"
62 #include "elf/dwarf2.h"
64 /* The following headers use the elf/reloc-macros.h file to
65 automatically generate relocation recognition functions
66 such as elf_mips_reloc_type() */
68 #define RELOC_MACROS_GEN_FUNC
70 #include "elf/alpha.h"
71 #include "elf/arc.h"
72 #include "elf/arm.h"
73 #include "elf/avr.h"
74 #include "elf/cris.h"
75 #include "elf/d10v.h"
76 #include "elf/d30v.h"
77 #include "elf/dlx.h"
78 #include "elf/fr30.h"
79 #include "elf/frv.h"
80 #include "elf/h8.h"
81 #include "elf/hppa.h"
82 #include "elf/i386.h"
83 #include "elf/i370.h"
84 #include "elf/i860.h"
85 #include "elf/i960.h"
86 #include "elf/ia64.h"
87 #include "elf/ip2k.h"
88 #include "elf/m32r.h"
89 #include "elf/m68k.h"
90 #include "elf/m68hc11.h"
91 #include "elf/mcore.h"
92 #include "elf/mips.h"
93 #include "elf/mmix.h"
94 #include "elf/mn10200.h"
95 #include "elf/mn10300.h"
96 #include "elf/msp430.h"
97 #include "elf/or32.h"
98 #include "elf/pj.h"
99 #include "elf/ppc.h"
100 #include "elf/ppc64.h"
101 #include "elf/s390.h"
102 #include "elf/sh.h"
103 #include "elf/sparc.h"
104 #include "elf/v850.h"
105 #include "elf/vax.h"
106 #include "elf/x86-64.h"
107 #include "elf/xstormy16.h"
108 #include "elf/iq2000.h"
109 #include "elf/xtensa.h"
111 #include "aout/ar.h"
113 #include "bucomm.h"
114 #include "getopt.h"
115 #include "libiberty.h"
117 char *program_name = "readelf";
118 long archive_file_offset;
119 unsigned long archive_file_size;
120 unsigned long dynamic_addr;
121 bfd_size_type dynamic_size;
122 char *dynamic_strings;
123 char *string_table;
124 unsigned long string_table_length;
125 unsigned long num_dynamic_syms;
126 Elf_Internal_Sym *dynamic_symbols;
127 Elf_Internal_Syminfo *dynamic_syminfo;
128 unsigned long dynamic_syminfo_offset;
129 unsigned int dynamic_syminfo_nent;
130 char program_interpreter[64];
131 bfd_vma dynamic_info[DT_JMPREL + 1];
132 bfd_vma version_info[16];
133 Elf_Internal_Ehdr elf_header;
134 Elf_Internal_Shdr *section_headers;
135 Elf_Internal_Phdr *program_headers;
136 Elf_Internal_Dyn *dynamic_segment;
137 Elf_Internal_Shdr *symtab_shndx_hdr;
138 int show_name;
139 int do_dynamic;
140 int do_syms;
141 int do_reloc;
142 int do_sections;
143 int do_section_groups;
144 int do_segments;
145 int do_unwind;
146 int do_using_dynamic;
147 int do_header;
148 int do_dump;
149 int do_version;
150 int do_wide;
151 int do_histogram;
152 int do_debugging;
153 int do_debug_info;
154 int do_debug_abbrevs;
155 int do_debug_lines;
156 int do_debug_pubnames;
157 int do_debug_aranges;
158 int do_debug_frames;
159 int do_debug_frames_interp;
160 int do_debug_macinfo;
161 int do_debug_str;
162 int do_debug_loc;
163 int do_arch;
164 int do_notes;
165 int is_32bit_elf;
167 struct group_list
169 struct group_list *next;
170 unsigned int section_index;
173 struct group
175 struct group_list *root;
176 unsigned int group_index;
179 struct group *section_groups;
180 size_t group_count = 0;
182 struct group **section_headers_groups;
184 /* A dynamic array of flags indicating which sections require dumping. */
185 char *dump_sects = NULL;
186 unsigned int num_dump_sects = 0;
188 #define HEX_DUMP (1 << 0)
189 #define DISASS_DUMP (1 << 1)
190 #define DEBUG_DUMP (1 << 2)
192 /* How to rpint a vma value. */
193 typedef enum print_mode
195 HEX,
196 DEC,
197 DEC_5,
198 UNSIGNED,
199 PREFIX_HEX,
200 FULL_HEX,
201 LONG_HEX
203 print_mode;
205 static bfd_vma (*byte_get) (unsigned char *, int);
206 static void (*byte_put) (unsigned char *, bfd_vma, int);
208 typedef int Elf32_Word;
210 #define UNKNOWN -1
212 #define SECTION_NAME(X) ((X) == NULL ? "<none>" : \
213 ((X)->sh_name >= string_table_length \
214 ? "<corrupt>" : string_table + (X)->sh_name))
216 /* Given st_shndx I, map to section_headers index. */
217 #define SECTION_HEADER_INDEX(I) \
218 ((I) < SHN_LORESERVE \
219 ? (I) \
220 : ((I) <= SHN_HIRESERVE \
221 ? 0 \
222 : (I) - (SHN_HIRESERVE + 1 - SHN_LORESERVE)))
224 /* Reverse of the above. */
225 #define SECTION_HEADER_NUM(N) \
226 ((N) < SHN_LORESERVE \
227 ? (N) \
228 : (N) + (SHN_HIRESERVE + 1 - SHN_LORESERVE))
230 #define SECTION_HEADER(I) (section_headers + SECTION_HEADER_INDEX (I))
232 #define DT_VERSIONTAGIDX(tag) (DT_VERNEEDNUM - (tag)) /* Reverse order! */
234 #define BYTE_GET(field) byte_get (field, sizeof (field))
236 /* If we can support a 64 bit data type then BFD64 should be defined
237 and sizeof (bfd_vma) == 8. In this case when translating from an
238 external 8 byte field to an internal field, we can assume that the
239 internal field is also 8 bytes wide and so we can extract all the data.
240 If, however, BFD64 is not defined, then we must assume that the
241 internal data structure only has 4 byte wide fields that are the
242 equivalent of the 8 byte wide external counterparts, and so we must
243 truncate the data. */
244 #ifdef BFD64
245 #define BYTE_GET8(field) byte_get (field, -8)
246 #else
247 #define BYTE_GET8(field) byte_get (field, 8)
248 #endif
250 #define NUM_ELEM(array) (sizeof (array) / sizeof ((array)[0]))
252 #define GET_ELF_SYMBOLS(file, section) \
253 (is_32bit_elf ? get_32bit_elf_symbols (file, section) \
254 : get_64bit_elf_symbols (file, section))
257 static void
258 error (const char *message, ...)
260 va_list args;
262 va_start (args, message);
263 fprintf (stderr, _("%s: Error: "), program_name);
264 vfprintf (stderr, message, args);
265 va_end (args);
268 static void
269 warn (const char *message, ...)
271 va_list args;
273 va_start (args, message);
274 fprintf (stderr, _("%s: Warning: "), program_name);
275 vfprintf (stderr, message, args);
276 va_end (args);
279 static void *
280 get_data (void *var, FILE *file, long offset, size_t size, const char *reason)
282 void *mvar;
284 if (size == 0)
285 return NULL;
287 if (fseek (file, archive_file_offset + offset, SEEK_SET))
289 error (_("Unable to seek to 0x%x for %s\n"),
290 archive_file_offset + offset, reason);
291 return NULL;
294 mvar = var;
295 if (mvar == NULL)
297 mvar = malloc (size);
299 if (mvar == NULL)
301 error (_("Out of memory allocating 0x%x bytes for %s\n"),
302 size, reason);
303 return NULL;
307 if (fread (mvar, size, 1, file) != 1)
309 error (_("Unable to read in 0x%x bytes of %s\n"), size, reason);
310 if (mvar != var)
311 free (mvar);
312 return NULL;
315 return mvar;
318 static bfd_vma
319 byte_get_little_endian (unsigned char *field, int size)
321 switch (size)
323 case 1:
324 return *field;
326 case 2:
327 return ((unsigned int) (field[0]))
328 | (((unsigned int) (field[1])) << 8);
330 #ifndef BFD64
331 case 8:
332 /* We want to extract data from an 8 byte wide field and
333 place it into a 4 byte wide field. Since this is a little
334 endian source we can just use the 4 byte extraction code. */
335 /* Fall through. */
336 #endif
337 case 4:
338 return ((unsigned long) (field[0]))
339 | (((unsigned long) (field[1])) << 8)
340 | (((unsigned long) (field[2])) << 16)
341 | (((unsigned long) (field[3])) << 24);
343 #ifdef BFD64
344 case 8:
345 case -8:
346 /* This is a special case, generated by the BYTE_GET8 macro.
347 It means that we are loading an 8 byte value from a field
348 in an external structure into an 8 byte value in a field
349 in an internal structure. */
350 return ((bfd_vma) (field[0]))
351 | (((bfd_vma) (field[1])) << 8)
352 | (((bfd_vma) (field[2])) << 16)
353 | (((bfd_vma) (field[3])) << 24)
354 | (((bfd_vma) (field[4])) << 32)
355 | (((bfd_vma) (field[5])) << 40)
356 | (((bfd_vma) (field[6])) << 48)
357 | (((bfd_vma) (field[7])) << 56);
358 #endif
359 default:
360 error (_("Unhandled data length: %d\n"), size);
361 abort ();
365 static bfd_vma
366 byte_get_signed (unsigned char *field, int size)
368 bfd_vma x = byte_get (field, size);
370 switch (size)
372 case 1:
373 return (x ^ 0x80) - 0x80;
374 case 2:
375 return (x ^ 0x8000) - 0x8000;
376 case 4:
377 return (x ^ 0x80000000) - 0x80000000;
378 case 8:
379 case -8:
380 return x;
381 default:
382 abort ();
386 static void
387 byte_put_little_endian (unsigned char *field, bfd_vma value, int size)
389 switch (size)
391 case 8:
392 field[7] = (((value >> 24) >> 24) >> 8) & 0xff;
393 field[6] = ((value >> 24) >> 24) & 0xff;
394 field[5] = ((value >> 24) >> 16) & 0xff;
395 field[4] = ((value >> 24) >> 8) & 0xff;
396 /* Fall through. */
397 case 4:
398 field[3] = (value >> 24) & 0xff;
399 field[2] = (value >> 16) & 0xff;
400 /* Fall through. */
401 case 2:
402 field[1] = (value >> 8) & 0xff;
403 /* Fall through. */
404 case 1:
405 field[0] = value & 0xff;
406 break;
408 default:
409 error (_("Unhandled data length: %d\n"), size);
410 abort ();
414 /* Print a VMA value. */
415 static void
416 print_vma (bfd_vma vma, print_mode mode)
418 #ifdef BFD64
419 if (is_32bit_elf)
420 #endif
422 switch (mode)
424 case FULL_HEX:
425 printf ("0x");
426 /* Drop through. */
427 case LONG_HEX:
428 printf ("%8.8lx", (unsigned long) vma);
429 break;
431 case DEC_5:
432 if (vma <= 99999)
434 printf ("%5ld", (long) vma);
435 break;
437 /* Drop through. */
438 case PREFIX_HEX:
439 printf ("0x");
440 /* Drop through. */
441 case HEX:
442 printf ("%lx", (unsigned long) vma);
443 break;
445 case DEC:
446 printf ("%ld", (unsigned long) vma);
447 break;
449 case UNSIGNED:
450 printf ("%lu", (unsigned long) vma);
451 break;
454 #ifdef BFD64
455 else
457 switch (mode)
459 case FULL_HEX:
460 printf ("0x");
461 /* Drop through. */
463 case LONG_HEX:
464 printf_vma (vma);
465 break;
467 case PREFIX_HEX:
468 printf ("0x");
469 /* Drop through. */
471 case HEX:
472 #if BFD_HOST_64BIT_LONG
473 printf ("%lx", vma);
474 #else
475 if (_bfd_int64_high (vma))
476 printf ("%lx%8.8lx", _bfd_int64_high (vma), _bfd_int64_low (vma));
477 else
478 printf ("%lx", _bfd_int64_low (vma));
479 #endif
480 break;
482 case DEC:
483 #if BFD_HOST_64BIT_LONG
484 printf ("%ld", vma);
485 #else
486 if (_bfd_int64_high (vma))
487 /* ugg */
488 printf ("++%ld", _bfd_int64_low (vma));
489 else
490 printf ("%ld", _bfd_int64_low (vma));
491 #endif
492 break;
494 case DEC_5:
495 #if BFD_HOST_64BIT_LONG
496 if (vma <= 99999)
497 printf ("%5ld", vma);
498 else
499 printf ("%#lx", vma);
500 #else
501 if (_bfd_int64_high (vma))
502 /* ugg */
503 printf ("++%ld", _bfd_int64_low (vma));
504 else if (vma <= 99999)
505 printf ("%5ld", _bfd_int64_low (vma));
506 else
507 printf ("%#lx", _bfd_int64_low (vma));
508 #endif
509 break;
511 case UNSIGNED:
512 #if BFD_HOST_64BIT_LONG
513 printf ("%lu", vma);
514 #else
515 if (_bfd_int64_high (vma))
516 /* ugg */
517 printf ("++%lu", _bfd_int64_low (vma));
518 else
519 printf ("%lu", _bfd_int64_low (vma));
520 #endif
521 break;
524 #endif
527 /* Display a symbol on stdout. If do_wide is not true then
528 format the symbol to be at most WIDTH characters,
529 truncating as necessary. If WIDTH is negative then
530 format the string to be exactly - WIDTH characters,
531 truncating or padding as necessary. */
533 static void
534 print_symbol (int width, const char *symbol)
536 if (do_wide)
537 printf ("%s", symbol);
538 else if (width < 0)
539 printf ("%-*.*s", width, width, symbol);
540 else
541 printf ("%-.*s", width, symbol);
544 static bfd_vma
545 byte_get_big_endian (unsigned char *field, int size)
547 switch (size)
549 case 1:
550 return *field;
552 case 2:
553 return ((unsigned int) (field[1])) | (((int) (field[0])) << 8);
555 case 4:
556 return ((unsigned long) (field[3]))
557 | (((unsigned long) (field[2])) << 8)
558 | (((unsigned long) (field[1])) << 16)
559 | (((unsigned long) (field[0])) << 24);
561 #ifndef BFD64
562 case 8:
563 /* Although we are extracing data from an 8 byte wide field, we
564 are returning only 4 bytes of data. */
565 return ((unsigned long) (field[7]))
566 | (((unsigned long) (field[6])) << 8)
567 | (((unsigned long) (field[5])) << 16)
568 | (((unsigned long) (field[4])) << 24);
569 #else
570 case 8:
571 case -8:
572 /* This is a special case, generated by the BYTE_GET8 macro.
573 It means that we are loading an 8 byte value from a field
574 in an external structure into an 8 byte value in a field
575 in an internal structure. */
576 return ((bfd_vma) (field[7]))
577 | (((bfd_vma) (field[6])) << 8)
578 | (((bfd_vma) (field[5])) << 16)
579 | (((bfd_vma) (field[4])) << 24)
580 | (((bfd_vma) (field[3])) << 32)
581 | (((bfd_vma) (field[2])) << 40)
582 | (((bfd_vma) (field[1])) << 48)
583 | (((bfd_vma) (field[0])) << 56);
584 #endif
586 default:
587 error (_("Unhandled data length: %d\n"), size);
588 abort ();
592 static void
593 byte_put_big_endian (unsigned char *field, bfd_vma value, int size)
595 switch (size)
597 case 8:
598 field[7] = value & 0xff;
599 field[6] = (value >> 8) & 0xff;
600 field[5] = (value >> 16) & 0xff;
601 field[4] = (value >> 24) & 0xff;
602 value >>= 16;
603 value >>= 16;
604 /* Fall through. */
605 case 4:
606 field[3] = value & 0xff;
607 field[2] = (value >> 8) & 0xff;
608 value >>= 16;
609 /* Fall through. */
610 case 2:
611 field[1] = value & 0xff;
612 value >>= 8;
613 /* Fall through. */
614 case 1:
615 field[0] = value & 0xff;
616 break;
618 default:
619 error (_("Unhandled data length: %d\n"), size);
620 abort ();
624 /* Guess the relocation size commonly used by the specific machines. */
626 static int
627 guess_is_rela (unsigned long e_machine)
629 switch (e_machine)
631 /* Targets that use REL relocations. */
632 case EM_ARM:
633 case EM_386:
634 case EM_486:
635 case EM_960:
636 case EM_DLX:
637 case EM_OPENRISC:
638 case EM_OR32:
639 case EM_CYGNUS_M32R:
640 case EM_D10V:
641 case EM_CYGNUS_D10V:
642 case EM_MIPS:
643 case EM_MIPS_RS3_LE:
644 return FALSE;
646 /* Targets that use RELA relocations. */
647 case EM_68K:
648 case EM_H8_300:
649 case EM_H8_300H:
650 case EM_H8S:
651 case EM_SPARC32PLUS:
652 case EM_SPARCV9:
653 case EM_SPARC:
654 case EM_PPC:
655 case EM_PPC64:
656 case EM_V850:
657 case EM_CYGNUS_V850:
658 case EM_D30V:
659 case EM_CYGNUS_D30V:
660 case EM_MN10200:
661 case EM_CYGNUS_MN10200:
662 case EM_MN10300:
663 case EM_CYGNUS_MN10300:
664 case EM_FR30:
665 case EM_CYGNUS_FR30:
666 case EM_CYGNUS_FRV:
667 case EM_SH:
668 case EM_ALPHA:
669 case EM_MCORE:
670 case EM_IA_64:
671 case EM_AVR:
672 case EM_AVR_OLD:
673 case EM_CRIS:
674 case EM_860:
675 case EM_X86_64:
676 case EM_S390:
677 case EM_S390_OLD:
678 case EM_MMIX:
679 case EM_MSP430:
680 case EM_MSP430_OLD:
681 case EM_XSTORMY16:
682 case EM_VAX:
683 case EM_IP2K:
684 case EM_IP2K_OLD:
685 case EM_IQ2000:
686 case EM_XTENSA:
687 case EM_XTENSA_OLD:
688 case EM_M32R:
689 return TRUE;
691 case EM_MMA:
692 case EM_PCP:
693 case EM_NCPU:
694 case EM_NDR1:
695 case EM_STARCORE:
696 case EM_ME16:
697 case EM_ST100:
698 case EM_TINYJ:
699 case EM_FX66:
700 case EM_ST9PLUS:
701 case EM_ST7:
702 case EM_68HC16:
703 case EM_68HC11:
704 case EM_68HC08:
705 case EM_68HC05:
706 case EM_SVX:
707 case EM_ST19:
708 default:
709 warn (_("Don't know about relocations on this machine architecture\n"));
710 return FALSE;
714 static int
715 slurp_rela_relocs (FILE *file,
716 unsigned long rel_offset,
717 unsigned long rel_size,
718 Elf_Internal_Rela **relasp,
719 unsigned long *nrelasp)
721 Elf_Internal_Rela *relas;
722 unsigned long nrelas;
723 unsigned int i;
725 if (is_32bit_elf)
727 Elf32_External_Rela *erelas;
729 erelas = get_data (NULL, file, rel_offset, rel_size, _("relocs"));
730 if (!erelas)
731 return 0;
733 nrelas = rel_size / sizeof (Elf32_External_Rela);
735 relas = malloc (nrelas * sizeof (Elf_Internal_Rela));
737 if (relas == NULL)
739 error(_("out of memory parsing relocs"));
740 return 0;
743 for (i = 0; i < nrelas; i++)
745 relas[i].r_offset = BYTE_GET (erelas[i].r_offset);
746 relas[i].r_info = BYTE_GET (erelas[i].r_info);
747 relas[i].r_addend = BYTE_GET (erelas[i].r_addend);
750 free (erelas);
752 else
754 Elf64_External_Rela *erelas;
756 erelas = get_data (NULL, file, rel_offset, rel_size, _("relocs"));
757 if (!erelas)
758 return 0;
760 nrelas = rel_size / sizeof (Elf64_External_Rela);
762 relas = malloc (nrelas * sizeof (Elf_Internal_Rela));
764 if (relas == NULL)
766 error(_("out of memory parsing relocs"));
767 return 0;
770 for (i = 0; i < nrelas; i++)
772 relas[i].r_offset = BYTE_GET8 (erelas[i].r_offset);
773 relas[i].r_info = BYTE_GET8 (erelas[i].r_info);
774 relas[i].r_addend = BYTE_GET8 (erelas[i].r_addend);
777 free (erelas);
779 *relasp = relas;
780 *nrelasp = nrelas;
781 return 1;
784 static int
785 slurp_rel_relocs (FILE *file,
786 unsigned long rel_offset,
787 unsigned long rel_size,
788 Elf_Internal_Rela **relsp,
789 unsigned long *nrelsp)
791 Elf_Internal_Rela *rels;
792 unsigned long nrels;
793 unsigned int i;
795 if (is_32bit_elf)
797 Elf32_External_Rel *erels;
799 erels = get_data (NULL, file, rel_offset, rel_size, _("relocs"));
800 if (!erels)
801 return 0;
803 nrels = rel_size / sizeof (Elf32_External_Rel);
805 rels = malloc (nrels * sizeof (Elf_Internal_Rela));
807 if (rels == NULL)
809 error(_("out of memory parsing relocs"));
810 return 0;
813 for (i = 0; i < nrels; i++)
815 rels[i].r_offset = BYTE_GET (erels[i].r_offset);
816 rels[i].r_info = BYTE_GET (erels[i].r_info);
817 rels[i].r_addend = 0;
820 free (erels);
822 else
824 Elf64_External_Rel *erels;
826 erels = get_data (NULL, file, rel_offset, rel_size, _("relocs"));
827 if (!erels)
828 return 0;
830 nrels = rel_size / sizeof (Elf64_External_Rel);
832 rels = malloc (nrels * sizeof (Elf_Internal_Rela));
834 if (rels == NULL)
836 error(_("out of memory parsing relocs"));
837 return 0;
840 for (i = 0; i < nrels; i++)
842 rels[i].r_offset = BYTE_GET8 (erels[i].r_offset);
843 rels[i].r_info = BYTE_GET8 (erels[i].r_info);
844 rels[i].r_addend = 0;
847 free (erels);
849 *relsp = rels;
850 *nrelsp = nrels;
851 return 1;
854 /* Display the contents of the relocation data found at the specified
855 offset. */
857 static int
858 dump_relocations (FILE *file,
859 unsigned long rel_offset,
860 unsigned long rel_size,
861 Elf_Internal_Sym *symtab,
862 unsigned long nsyms,
863 char *strtab,
864 int is_rela)
866 unsigned int i;
867 Elf_Internal_Rela *rels;
870 if (is_rela == UNKNOWN)
871 is_rela = guess_is_rela (elf_header.e_machine);
873 if (is_rela)
875 if (!slurp_rela_relocs (file, rel_offset, rel_size, &rels, &rel_size))
876 return 0;
878 else
880 if (!slurp_rel_relocs (file, rel_offset, rel_size, &rels, &rel_size))
881 return 0;
884 if (is_32bit_elf)
886 if (is_rela)
888 if (do_wide)
889 printf (_(" Offset Info Type Sym. Value Symbol's Name + Addend\n"));
890 else
891 printf (_(" Offset Info Type Sym.Value Sym. Name + Addend\n"));
893 else
895 if (do_wide)
896 printf (_(" Offset Info Type Sym. Value Symbol's Name\n"));
897 else
898 printf (_(" Offset Info Type Sym.Value Sym. Name\n"));
901 else
903 if (is_rela)
905 if (do_wide)
906 printf (_(" Offset Info Type Symbol's Value Symbol's Name + Addend\n"));
907 else
908 printf (_(" Offset Info Type Sym. Value Sym. Name + Addend\n"));
910 else
912 if (do_wide)
913 printf (_(" Offset Info Type Symbol's Value Symbol's Name\n"));
914 else
915 printf (_(" Offset Info Type Sym. Value Sym. Name\n"));
919 for (i = 0; i < rel_size; i++)
921 const char *rtype;
922 const char *rtype2 = NULL;
923 const char *rtype3 = NULL;
924 bfd_vma offset;
925 bfd_vma info;
926 bfd_vma symtab_index;
927 bfd_vma type;
928 bfd_vma type2 = 0;
929 bfd_vma type3 = 0;
931 offset = rels[i].r_offset;
932 info = rels[i].r_info;
934 if (is_32bit_elf)
936 type = ELF32_R_TYPE (info);
937 symtab_index = ELF32_R_SYM (info);
939 else
941 /* The #ifdef BFD64 below is to prevent a compile time warning.
942 We know that if we do not have a 64 bit data type that we
943 will never execute this code anyway. */
944 #ifdef BFD64
945 if (elf_header.e_machine == EM_MIPS)
947 /* In little-endian objects, r_info isn't really a 64-bit
948 little-endian value: it has a 32-bit little-endian
949 symbol index followed by four individual byte fields.
950 Reorder INFO accordingly. */
951 if (elf_header.e_ident[EI_DATA] != ELFDATA2MSB)
952 info = (((info & 0xffffffff) << 32)
953 | ((info >> 56) & 0xff)
954 | ((info >> 40) & 0xff00)
955 | ((info >> 24) & 0xff0000)
956 | ((info >> 8) & 0xff000000));
957 type = ELF64_MIPS_R_TYPE (info);
958 type2 = ELF64_MIPS_R_TYPE2 (info);
959 type3 = ELF64_MIPS_R_TYPE3 (info);
961 else if (elf_header.e_machine == EM_SPARCV9)
962 type = ELF64_R_TYPE_ID (info);
963 else
964 type = ELF64_R_TYPE (info);
966 symtab_index = ELF64_R_SYM (info);
967 #endif
970 if (is_32bit_elf)
972 #ifdef _bfd_int64_low
973 printf ("%8.8lx %8.8lx ", _bfd_int64_low (offset), _bfd_int64_low (info));
974 #else
975 printf ("%8.8lx %8.8lx ", offset, info);
976 #endif
978 else
980 #ifdef _bfd_int64_low
981 printf (do_wide
982 ? "%8.8lx%8.8lx %8.8lx%8.8lx "
983 : "%4.4lx%8.8lx %4.4lx%8.8lx ",
984 _bfd_int64_high (offset),
985 _bfd_int64_low (offset),
986 _bfd_int64_high (info),
987 _bfd_int64_low (info));
988 #else
989 printf (do_wide
990 ? "%16.16lx %16.16lx "
991 : "%12.12lx %12.12lx ",
992 offset, info);
993 #endif
996 switch (elf_header.e_machine)
998 default:
999 rtype = NULL;
1000 break;
1002 case EM_M32R:
1003 case EM_CYGNUS_M32R:
1004 rtype = elf_m32r_reloc_type (type);
1005 break;
1007 case EM_386:
1008 case EM_486:
1009 rtype = elf_i386_reloc_type (type);
1010 break;
1012 case EM_68HC11:
1013 case EM_68HC12:
1014 rtype = elf_m68hc11_reloc_type (type);
1015 break;
1017 case EM_68K:
1018 rtype = elf_m68k_reloc_type (type);
1019 break;
1021 case EM_960:
1022 rtype = elf_i960_reloc_type (type);
1023 break;
1025 case EM_AVR:
1026 case EM_AVR_OLD:
1027 rtype = elf_avr_reloc_type (type);
1028 break;
1030 case EM_OLD_SPARCV9:
1031 case EM_SPARC32PLUS:
1032 case EM_SPARCV9:
1033 case EM_SPARC:
1034 rtype = elf_sparc_reloc_type (type);
1035 break;
1037 case EM_V850:
1038 case EM_CYGNUS_V850:
1039 rtype = v850_reloc_type (type);
1040 break;
1042 case EM_D10V:
1043 case EM_CYGNUS_D10V:
1044 rtype = elf_d10v_reloc_type (type);
1045 break;
1047 case EM_D30V:
1048 case EM_CYGNUS_D30V:
1049 rtype = elf_d30v_reloc_type (type);
1050 break;
1052 case EM_DLX:
1053 rtype = elf_dlx_reloc_type (type);
1054 break;
1056 case EM_SH:
1057 rtype = elf_sh_reloc_type (type);
1058 break;
1060 case EM_MN10300:
1061 case EM_CYGNUS_MN10300:
1062 rtype = elf_mn10300_reloc_type (type);
1063 break;
1065 case EM_MN10200:
1066 case EM_CYGNUS_MN10200:
1067 rtype = elf_mn10200_reloc_type (type);
1068 break;
1070 case EM_FR30:
1071 case EM_CYGNUS_FR30:
1072 rtype = elf_fr30_reloc_type (type);
1073 break;
1075 case EM_CYGNUS_FRV:
1076 rtype = elf_frv_reloc_type (type);
1077 break;
1079 case EM_MCORE:
1080 rtype = elf_mcore_reloc_type (type);
1081 break;
1083 case EM_MMIX:
1084 rtype = elf_mmix_reloc_type (type);
1085 break;
1087 case EM_MSP430:
1088 case EM_MSP430_OLD:
1089 rtype = elf_msp430_reloc_type (type);
1090 break;
1092 case EM_PPC:
1093 rtype = elf_ppc_reloc_type (type);
1094 break;
1096 case EM_PPC64:
1097 rtype = elf_ppc64_reloc_type (type);
1098 break;
1100 case EM_MIPS:
1101 case EM_MIPS_RS3_LE:
1102 rtype = elf_mips_reloc_type (type);
1103 if (!is_32bit_elf)
1105 rtype2 = elf_mips_reloc_type (type2);
1106 rtype3 = elf_mips_reloc_type (type3);
1108 break;
1110 case EM_ALPHA:
1111 rtype = elf_alpha_reloc_type (type);
1112 break;
1114 case EM_ARM:
1115 rtype = elf_arm_reloc_type (type);
1116 break;
1118 case EM_ARC:
1119 rtype = elf_arc_reloc_type (type);
1120 break;
1122 case EM_PARISC:
1123 rtype = elf_hppa_reloc_type (type);
1124 break;
1126 case EM_H8_300:
1127 case EM_H8_300H:
1128 case EM_H8S:
1129 rtype = elf_h8_reloc_type (type);
1130 break;
1132 case EM_OPENRISC:
1133 case EM_OR32:
1134 rtype = elf_or32_reloc_type (type);
1135 break;
1137 case EM_PJ:
1138 case EM_PJ_OLD:
1139 rtype = elf_pj_reloc_type (type);
1140 break;
1141 case EM_IA_64:
1142 rtype = elf_ia64_reloc_type (type);
1143 break;
1145 case EM_CRIS:
1146 rtype = elf_cris_reloc_type (type);
1147 break;
1149 case EM_860:
1150 rtype = elf_i860_reloc_type (type);
1151 break;
1153 case EM_X86_64:
1154 rtype = elf_x86_64_reloc_type (type);
1155 break;
1157 case EM_S370:
1158 rtype = i370_reloc_type (type);
1159 break;
1161 case EM_S390_OLD:
1162 case EM_S390:
1163 rtype = elf_s390_reloc_type (type);
1164 break;
1166 case EM_XSTORMY16:
1167 rtype = elf_xstormy16_reloc_type (type);
1168 break;
1170 case EM_VAX:
1171 rtype = elf_vax_reloc_type (type);
1172 break;
1174 case EM_IP2K:
1175 case EM_IP2K_OLD:
1176 rtype = elf_ip2k_reloc_type (type);
1177 break;
1179 case EM_IQ2000:
1180 rtype = elf_iq2000_reloc_type (type);
1181 break;
1183 case EM_XTENSA_OLD:
1184 case EM_XTENSA:
1185 rtype = elf_xtensa_reloc_type (type);
1186 break;
1189 if (rtype == NULL)
1190 #ifdef _bfd_int64_low
1191 printf (_("unrecognized: %-7lx"), _bfd_int64_low (type));
1192 #else
1193 printf (_("unrecognized: %-7lx"), type);
1194 #endif
1195 else
1196 printf (do_wide ? "%-22.22s" : "%-17.17s", rtype);
1198 if (symtab_index)
1200 if (symtab == NULL || symtab_index >= nsyms)
1201 printf (" bad symbol index: %08lx", (unsigned long) symtab_index);
1202 else
1204 Elf_Internal_Sym *psym;
1206 psym = symtab + symtab_index;
1208 printf (" ");
1209 print_vma (psym->st_value, LONG_HEX);
1210 printf (is_32bit_elf ? " " : " ");
1212 if (psym->st_name == 0)
1214 const char *sec_name = "<null>";
1215 char name_buf[40];
1217 if (ELF_ST_TYPE (psym->st_info) == STT_SECTION)
1219 bfd_vma sec_index = (bfd_vma) -1;
1221 if (psym->st_shndx < SHN_LORESERVE)
1222 sec_index = psym->st_shndx;
1223 else if (psym->st_shndx > SHN_LORESERVE)
1224 sec_index = psym->st_shndx - (SHN_HIRESERVE + 1
1225 - SHN_LORESERVE);
1227 if (sec_index != (bfd_vma) -1)
1228 sec_name = SECTION_NAME (section_headers + sec_index);
1229 else if (psym->st_shndx == SHN_ABS)
1230 sec_name = "ABS";
1231 else if (psym->st_shndx == SHN_COMMON)
1232 sec_name = "COMMON";
1233 else if (elf_header.e_machine == EM_IA_64
1234 && elf_header.e_ident[EI_OSABI] == ELFOSABI_HPUX
1235 && psym->st_shndx == SHN_IA_64_ANSI_COMMON)
1236 sec_name = "ANSI_COM";
1237 else
1239 sprintf (name_buf, "<section 0x%x>",
1240 (unsigned int) psym->st_shndx);
1241 sec_name = name_buf;
1244 print_symbol (22, sec_name);
1246 else if (strtab == NULL)
1247 printf (_("<string table index %3ld>"), psym->st_name);
1248 else
1249 print_symbol (22, strtab + psym->st_name);
1251 if (is_rela)
1252 printf (" + %lx", (unsigned long) rels[i].r_addend);
1255 else if (is_rela)
1257 printf ("%*c", is_32bit_elf ? (do_wide ? 34 : 28) : (do_wide ? 26 : 20), ' ');
1258 print_vma (rels[i].r_addend, LONG_HEX);
1261 if (elf_header.e_machine == EM_SPARCV9
1262 && !strcmp (rtype, "R_SPARC_OLO10"))
1263 printf (" + %lx", (unsigned long) ELF64_R_TYPE_DATA (info));
1265 putchar ('\n');
1267 if (! is_32bit_elf && elf_header.e_machine == EM_MIPS)
1269 printf (" Type2: ");
1271 if (rtype2 == NULL)
1272 #ifdef _bfd_int64_low
1273 printf (_("unrecognized: %-7lx"), _bfd_int64_low (type2));
1274 #else
1275 printf (_("unrecognized: %-7lx"), type2);
1276 #endif
1277 else
1278 printf ("%-17.17s", rtype2);
1280 printf("\n Type3: ");
1282 if (rtype3 == NULL)
1283 #ifdef _bfd_int64_low
1284 printf (_("unrecognized: %-7lx"), _bfd_int64_low (type3));
1285 #else
1286 printf (_("unrecognized: %-7lx"), type3);
1287 #endif
1288 else
1289 printf ("%-17.17s", rtype3);
1291 putchar ('\n');
1295 free (rels);
1297 return 1;
1300 static const char *
1301 get_mips_dynamic_type (unsigned long type)
1303 switch (type)
1305 case DT_MIPS_RLD_VERSION: return "MIPS_RLD_VERSION";
1306 case DT_MIPS_TIME_STAMP: return "MIPS_TIME_STAMP";
1307 case DT_MIPS_ICHECKSUM: return "MIPS_ICHECKSUM";
1308 case DT_MIPS_IVERSION: return "MIPS_IVERSION";
1309 case DT_MIPS_FLAGS: return "MIPS_FLAGS";
1310 case DT_MIPS_BASE_ADDRESS: return "MIPS_BASE_ADDRESS";
1311 case DT_MIPS_MSYM: return "MIPS_MSYM";
1312 case DT_MIPS_CONFLICT: return "MIPS_CONFLICT";
1313 case DT_MIPS_LIBLIST: return "MIPS_LIBLIST";
1314 case DT_MIPS_LOCAL_GOTNO: return "MIPS_LOCAL_GOTNO";
1315 case DT_MIPS_CONFLICTNO: return "MIPS_CONFLICTNO";
1316 case DT_MIPS_LIBLISTNO: return "MIPS_LIBLISTNO";
1317 case DT_MIPS_SYMTABNO: return "MIPS_SYMTABNO";
1318 case DT_MIPS_UNREFEXTNO: return "MIPS_UNREFEXTNO";
1319 case DT_MIPS_GOTSYM: return "MIPS_GOTSYM";
1320 case DT_MIPS_HIPAGENO: return "MIPS_HIPAGENO";
1321 case DT_MIPS_RLD_MAP: return "MIPS_RLD_MAP";
1322 case DT_MIPS_DELTA_CLASS: return "MIPS_DELTA_CLASS";
1323 case DT_MIPS_DELTA_CLASS_NO: return "MIPS_DELTA_CLASS_NO";
1324 case DT_MIPS_DELTA_INSTANCE: return "MIPS_DELTA_INSTANCE";
1325 case DT_MIPS_DELTA_INSTANCE_NO: return "MIPS_DELTA_INSTANCE_NO";
1326 case DT_MIPS_DELTA_RELOC: return "MIPS_DELTA_RELOC";
1327 case DT_MIPS_DELTA_RELOC_NO: return "MIPS_DELTA_RELOC_NO";
1328 case DT_MIPS_DELTA_SYM: return "MIPS_DELTA_SYM";
1329 case DT_MIPS_DELTA_SYM_NO: return "MIPS_DELTA_SYM_NO";
1330 case DT_MIPS_DELTA_CLASSSYM: return "MIPS_DELTA_CLASSSYM";
1331 case DT_MIPS_DELTA_CLASSSYM_NO: return "MIPS_DELTA_CLASSSYM_NO";
1332 case DT_MIPS_CXX_FLAGS: return "MIPS_CXX_FLAGS";
1333 case DT_MIPS_PIXIE_INIT: return "MIPS_PIXIE_INIT";
1334 case DT_MIPS_SYMBOL_LIB: return "MIPS_SYMBOL_LIB";
1335 case DT_MIPS_LOCALPAGE_GOTIDX: return "MIPS_LOCALPAGE_GOTIDX";
1336 case DT_MIPS_LOCAL_GOTIDX: return "MIPS_LOCAL_GOTIDX";
1337 case DT_MIPS_HIDDEN_GOTIDX: return "MIPS_HIDDEN_GOTIDX";
1338 case DT_MIPS_PROTECTED_GOTIDX: return "MIPS_PROTECTED_GOTIDX";
1339 case DT_MIPS_OPTIONS: return "MIPS_OPTIONS";
1340 case DT_MIPS_INTERFACE: return "MIPS_INTERFACE";
1341 case DT_MIPS_DYNSTR_ALIGN: return "MIPS_DYNSTR_ALIGN";
1342 case DT_MIPS_INTERFACE_SIZE: return "MIPS_INTERFACE_SIZE";
1343 case DT_MIPS_RLD_TEXT_RESOLVE_ADDR: return "MIPS_RLD_TEXT_RESOLVE_ADDR";
1344 case DT_MIPS_PERF_SUFFIX: return "MIPS_PERF_SUFFIX";
1345 case DT_MIPS_COMPACT_SIZE: return "MIPS_COMPACT_SIZE";
1346 case DT_MIPS_GP_VALUE: return "MIPS_GP_VALUE";
1347 case DT_MIPS_AUX_DYNAMIC: return "MIPS_AUX_DYNAMIC";
1348 default:
1349 return NULL;
1353 static const char *
1354 get_sparc64_dynamic_type (unsigned long type)
1356 switch (type)
1358 case DT_SPARC_REGISTER: return "SPARC_REGISTER";
1359 default:
1360 return NULL;
1364 static const char *
1365 get_ppc64_dynamic_type (unsigned long type)
1367 switch (type)
1369 case DT_PPC64_GLINK: return "PPC64_GLINK";
1370 case DT_PPC64_OPD: return "PPC64_OPD";
1371 case DT_PPC64_OPDSZ: return "PPC64_OPDSZ";
1372 default:
1373 return NULL;
1377 static const char *
1378 get_parisc_dynamic_type (unsigned long type)
1380 switch (type)
1382 case DT_HP_LOAD_MAP: return "HP_LOAD_MAP";
1383 case DT_HP_DLD_FLAGS: return "HP_DLD_FLAGS";
1384 case DT_HP_DLD_HOOK: return "HP_DLD_HOOK";
1385 case DT_HP_UX10_INIT: return "HP_UX10_INIT";
1386 case DT_HP_UX10_INITSZ: return "HP_UX10_INITSZ";
1387 case DT_HP_PREINIT: return "HP_PREINIT";
1388 case DT_HP_PREINITSZ: return "HP_PREINITSZ";
1389 case DT_HP_NEEDED: return "HP_NEEDED";
1390 case DT_HP_TIME_STAMP: return "HP_TIME_STAMP";
1391 case DT_HP_CHECKSUM: return "HP_CHECKSUM";
1392 case DT_HP_GST_SIZE: return "HP_GST_SIZE";
1393 case DT_HP_GST_VERSION: return "HP_GST_VERSION";
1394 case DT_HP_GST_HASHVAL: return "HP_GST_HASHVAL";
1395 default:
1396 return NULL;
1400 static const char *
1401 get_ia64_dynamic_type (unsigned long type)
1403 switch (type)
1405 case DT_IA_64_PLT_RESERVE: return "IA_64_PLT_RESERVE";
1406 default:
1407 return NULL;
1411 static const char *
1412 get_dynamic_type (unsigned long type)
1414 static char buff[32];
1416 switch (type)
1418 case DT_NULL: return "NULL";
1419 case DT_NEEDED: return "NEEDED";
1420 case DT_PLTRELSZ: return "PLTRELSZ";
1421 case DT_PLTGOT: return "PLTGOT";
1422 case DT_HASH: return "HASH";
1423 case DT_STRTAB: return "STRTAB";
1424 case DT_SYMTAB: return "SYMTAB";
1425 case DT_RELA: return "RELA";
1426 case DT_RELASZ: return "RELASZ";
1427 case DT_RELAENT: return "RELAENT";
1428 case DT_STRSZ: return "STRSZ";
1429 case DT_SYMENT: return "SYMENT";
1430 case DT_INIT: return "INIT";
1431 case DT_FINI: return "FINI";
1432 case DT_SONAME: return "SONAME";
1433 case DT_RPATH: return "RPATH";
1434 case DT_SYMBOLIC: return "SYMBOLIC";
1435 case DT_REL: return "REL";
1436 case DT_RELSZ: return "RELSZ";
1437 case DT_RELENT: return "RELENT";
1438 case DT_PLTREL: return "PLTREL";
1439 case DT_DEBUG: return "DEBUG";
1440 case DT_TEXTREL: return "TEXTREL";
1441 case DT_JMPREL: return "JMPREL";
1442 case DT_BIND_NOW: return "BIND_NOW";
1443 case DT_INIT_ARRAY: return "INIT_ARRAY";
1444 case DT_FINI_ARRAY: return "FINI_ARRAY";
1445 case DT_INIT_ARRAYSZ: return "INIT_ARRAYSZ";
1446 case DT_FINI_ARRAYSZ: return "FINI_ARRAYSZ";
1447 case DT_RUNPATH: return "RUNPATH";
1448 case DT_FLAGS: return "FLAGS";
1450 case DT_PREINIT_ARRAY: return "PREINIT_ARRAY";
1451 case DT_PREINIT_ARRAYSZ: return "PREINIT_ARRAYSZ";
1453 case DT_CHECKSUM: return "CHECKSUM";
1454 case DT_PLTPADSZ: return "PLTPADSZ";
1455 case DT_MOVEENT: return "MOVEENT";
1456 case DT_MOVESZ: return "MOVESZ";
1457 case DT_FEATURE: return "FEATURE";
1458 case DT_POSFLAG_1: return "POSFLAG_1";
1459 case DT_SYMINSZ: return "SYMINSZ";
1460 case DT_SYMINENT: return "SYMINENT"; /* aka VALRNGHI */
1462 case DT_ADDRRNGLO: return "ADDRRNGLO";
1463 case DT_CONFIG: return "CONFIG";
1464 case DT_DEPAUDIT: return "DEPAUDIT";
1465 case DT_AUDIT: return "AUDIT";
1466 case DT_PLTPAD: return "PLTPAD";
1467 case DT_MOVETAB: return "MOVETAB";
1468 case DT_SYMINFO: return "SYMINFO"; /* aka ADDRRNGHI */
1470 case DT_VERSYM: return "VERSYM";
1472 case DT_RELACOUNT: return "RELACOUNT";
1473 case DT_RELCOUNT: return "RELCOUNT";
1474 case DT_FLAGS_1: return "FLAGS_1";
1475 case DT_VERDEF: return "VERDEF";
1476 case DT_VERDEFNUM: return "VERDEFNUM";
1477 case DT_VERNEED: return "VERNEED";
1478 case DT_VERNEEDNUM: return "VERNEEDNUM";
1480 case DT_AUXILIARY: return "AUXILIARY";
1481 case DT_USED: return "USED";
1482 case DT_FILTER: return "FILTER";
1484 case DT_GNU_PRELINKED: return "GNU_PRELINKED";
1485 case DT_GNU_CONFLICT: return "GNU_CONFLICT";
1486 case DT_GNU_CONFLICTSZ: return "GNU_CONFLICTSZ";
1487 case DT_GNU_LIBLIST: return "GNU_LIBLIST";
1488 case DT_GNU_LIBLISTSZ: return "GNU_LIBLISTSZ";
1490 default:
1491 if ((type >= DT_LOPROC) && (type <= DT_HIPROC))
1493 const char *result;
1495 switch (elf_header.e_machine)
1497 case EM_MIPS:
1498 case EM_MIPS_RS3_LE:
1499 result = get_mips_dynamic_type (type);
1500 break;
1501 case EM_SPARCV9:
1502 result = get_sparc64_dynamic_type (type);
1503 break;
1504 case EM_PPC64:
1505 result = get_ppc64_dynamic_type (type);
1506 break;
1507 case EM_IA_64:
1508 result = get_ia64_dynamic_type (type);
1509 break;
1510 default:
1511 result = NULL;
1512 break;
1515 if (result != NULL)
1516 return result;
1518 sprintf (buff, _("Processor Specific: %lx"), type);
1520 else if ((type >= DT_LOOS) && (type <= DT_HIOS))
1522 const char *result;
1524 switch (elf_header.e_machine)
1526 case EM_PARISC:
1527 result = get_parisc_dynamic_type (type);
1528 break;
1529 default:
1530 result = NULL;
1531 break;
1534 if (result != NULL)
1535 return result;
1537 sprintf (buff, _("Operating System specific: %lx"), type);
1539 else
1540 sprintf (buff, _("<unknown>: %lx"), type);
1542 return buff;
1546 static char *
1547 get_file_type (unsigned e_type)
1549 static char buff[32];
1551 switch (e_type)
1553 case ET_NONE: return _("NONE (None)");
1554 case ET_REL: return _("REL (Relocatable file)");
1555 case ET_EXEC: return _("EXEC (Executable file)");
1556 case ET_DYN: return _("DYN (Shared object file)");
1557 case ET_CORE: return _("CORE (Core file)");
1559 default:
1560 if ((e_type >= ET_LOPROC) && (e_type <= ET_HIPROC))
1561 sprintf (buff, _("Processor Specific: (%x)"), e_type);
1562 else if ((e_type >= ET_LOOS) && (e_type <= ET_HIOS))
1563 sprintf (buff, _("OS Specific: (%x)"), e_type);
1564 else
1565 sprintf (buff, _("<unknown>: %x"), e_type);
1566 return buff;
1570 static char *
1571 get_machine_name (unsigned e_machine)
1573 static char buff[64]; /* XXX */
1575 switch (e_machine)
1577 case EM_NONE: return _("None");
1578 case EM_M32: return "WE32100";
1579 case EM_SPARC: return "Sparc";
1580 case EM_386: return "Intel 80386";
1581 case EM_68K: return "MC68000";
1582 case EM_88K: return "MC88000";
1583 case EM_486: return "Intel 80486";
1584 case EM_860: return "Intel 80860";
1585 case EM_MIPS: return "MIPS R3000";
1586 case EM_S370: return "IBM System/370";
1587 case EM_MIPS_RS3_LE: return "MIPS R4000 big-endian";
1588 case EM_OLD_SPARCV9: return "Sparc v9 (old)";
1589 case EM_PARISC: return "HPPA";
1590 case EM_PPC_OLD: return "Power PC (old)";
1591 case EM_SPARC32PLUS: return "Sparc v8+" ;
1592 case EM_960: return "Intel 90860";
1593 case EM_PPC: return "PowerPC";
1594 case EM_PPC64: return "PowerPC64";
1595 case EM_V800: return "NEC V800";
1596 case EM_FR20: return "Fujitsu FR20";
1597 case EM_RH32: return "TRW RH32";
1598 case EM_MCORE: return "MCORE";
1599 case EM_ARM: return "ARM";
1600 case EM_OLD_ALPHA: return "Digital Alpha (old)";
1601 case EM_SH: return "Renesas / SuperH SH";
1602 case EM_SPARCV9: return "Sparc v9";
1603 case EM_TRICORE: return "Siemens Tricore";
1604 case EM_ARC: return "ARC";
1605 case EM_H8_300: return "Renesas H8/300";
1606 case EM_H8_300H: return "Renesas H8/300H";
1607 case EM_H8S: return "Renesas H8S";
1608 case EM_H8_500: return "Renesas H8/500";
1609 case EM_IA_64: return "Intel IA-64";
1610 case EM_MIPS_X: return "Stanford MIPS-X";
1611 case EM_COLDFIRE: return "Motorola Coldfire";
1612 case EM_68HC12: return "Motorola M68HC12";
1613 case EM_ALPHA: return "Alpha";
1614 case EM_CYGNUS_D10V:
1615 case EM_D10V: return "d10v";
1616 case EM_CYGNUS_D30V:
1617 case EM_D30V: return "d30v";
1618 case EM_CYGNUS_M32R:
1619 case EM_M32R: return "Renesas M32R (formerly Mitsubishi M32r)";
1620 case EM_CYGNUS_V850:
1621 case EM_V850: return "NEC v850";
1622 case EM_CYGNUS_MN10300:
1623 case EM_MN10300: return "mn10300";
1624 case EM_CYGNUS_MN10200:
1625 case EM_MN10200: return "mn10200";
1626 case EM_CYGNUS_FR30:
1627 case EM_FR30: return "Fujitsu FR30";
1628 case EM_CYGNUS_FRV: return "Fujitsu FR-V";
1629 case EM_PJ_OLD:
1630 case EM_PJ: return "picoJava";
1631 case EM_MMA: return "Fujitsu Multimedia Accelerator";
1632 case EM_PCP: return "Siemens PCP";
1633 case EM_NCPU: return "Sony nCPU embedded RISC processor";
1634 case EM_NDR1: return "Denso NDR1 microprocesspr";
1635 case EM_STARCORE: return "Motorola Star*Core processor";
1636 case EM_ME16: return "Toyota ME16 processor";
1637 case EM_ST100: return "STMicroelectronics ST100 processor";
1638 case EM_TINYJ: return "Advanced Logic Corp. TinyJ embedded processor";
1639 case EM_FX66: return "Siemens FX66 microcontroller";
1640 case EM_ST9PLUS: return "STMicroelectronics ST9+ 8/16 bit microcontroller";
1641 case EM_ST7: return "STMicroelectronics ST7 8-bit microcontroller";
1642 case EM_68HC16: return "Motorola MC68HC16 Microcontroller";
1643 case EM_68HC11: return "Motorola MC68HC11 Microcontroller";
1644 case EM_68HC08: return "Motorola MC68HC08 Microcontroller";
1645 case EM_68HC05: return "Motorola MC68HC05 Microcontroller";
1646 case EM_SVX: return "Silicon Graphics SVx";
1647 case EM_ST19: return "STMicroelectronics ST19 8-bit microcontroller";
1648 case EM_VAX: return "Digital VAX";
1649 case EM_AVR_OLD:
1650 case EM_AVR: return "Atmel AVR 8-bit microcontroller";
1651 case EM_CRIS: return "Axis Communications 32-bit embedded processor";
1652 case EM_JAVELIN: return "Infineon Technologies 32-bit embedded cpu";
1653 case EM_FIREPATH: return "Element 14 64-bit DSP processor";
1654 case EM_ZSP: return "LSI Logic's 16-bit DSP processor";
1655 case EM_MMIX: return "Donald Knuth's educational 64-bit processor";
1656 case EM_HUANY: return "Harvard Universitys's machine-independent object format";
1657 case EM_PRISM: return "Vitesse Prism";
1658 case EM_X86_64: return "Advanced Micro Devices X86-64";
1659 case EM_S390_OLD:
1660 case EM_S390: return "IBM S/390";
1661 case EM_XSTORMY16: return "Sanyo Xstormy16 CPU core";
1662 case EM_OPENRISC:
1663 case EM_OR32: return "OpenRISC";
1664 case EM_DLX: return "OpenDLX";
1665 case EM_IP2K_OLD:
1666 case EM_IP2K: return "Ubicom IP2xxx 8-bit microcontrollers";
1667 case EM_IQ2000: return "Vitesse IQ2000";
1668 case EM_XTENSA_OLD:
1669 case EM_XTENSA: return "Tensilica Xtensa Processor";
1670 default:
1671 sprintf (buff, _("<unknown>: %x"), e_machine);
1672 return buff;
1676 static void
1677 decode_ARM_machine_flags (unsigned e_flags, char buf[])
1679 unsigned eabi;
1680 int unknown = 0;
1682 eabi = EF_ARM_EABI_VERSION (e_flags);
1683 e_flags &= ~ EF_ARM_EABIMASK;
1685 /* Handle "generic" ARM flags. */
1686 if (e_flags & EF_ARM_RELEXEC)
1688 strcat (buf, ", relocatable executable");
1689 e_flags &= ~ EF_ARM_RELEXEC;
1692 if (e_flags & EF_ARM_HASENTRY)
1694 strcat (buf, ", has entry point");
1695 e_flags &= ~ EF_ARM_HASENTRY;
1698 /* Now handle EABI specific flags. */
1699 switch (eabi)
1701 default:
1702 strcat (buf, ", <unrecognized EABI>");
1703 if (e_flags)
1704 unknown = 1;
1705 break;
1707 case EF_ARM_EABI_VER1:
1708 strcat (buf, ", Version1 EABI");
1709 while (e_flags)
1711 unsigned flag;
1713 /* Process flags one bit at a time. */
1714 flag = e_flags & - e_flags;
1715 e_flags &= ~ flag;
1717 switch (flag)
1719 case EF_ARM_SYMSARESORTED: /* Conflicts with EF_ARM_INTERWORK. */
1720 strcat (buf, ", sorted symbol tables");
1721 break;
1723 default:
1724 unknown = 1;
1725 break;
1728 break;
1730 case EF_ARM_EABI_VER2:
1731 strcat (buf, ", Version2 EABI");
1732 while (e_flags)
1734 unsigned flag;
1736 /* Process flags one bit at a time. */
1737 flag = e_flags & - e_flags;
1738 e_flags &= ~ flag;
1740 switch (flag)
1742 case EF_ARM_SYMSARESORTED: /* Conflicts with EF_ARM_INTERWORK. */
1743 strcat (buf, ", sorted symbol tables");
1744 break;
1746 case EF_ARM_DYNSYMSUSESEGIDX:
1747 strcat (buf, ", dynamic symbols use segment index");
1748 break;
1750 case EF_ARM_MAPSYMSFIRST:
1751 strcat (buf, ", mapping symbols precede others");
1752 break;
1754 default:
1755 unknown = 1;
1756 break;
1759 break;
1761 case EF_ARM_EABI_VER3:
1762 strcat (buf, ", Version3 EABI");
1763 while (e_flags)
1765 unsigned flag;
1767 /* Process flags one bit at a time. */
1768 flag = e_flags & - e_flags;
1769 e_flags &= ~ flag;
1771 switch (flag)
1773 case EF_ARM_BE8:
1774 strcat (buf, ", BE8");
1775 break;
1777 case EF_ARM_LE8:
1778 strcat (buf, ", LE8");
1779 break;
1781 default:
1782 unknown = 1;
1783 break;
1786 break;
1788 case EF_ARM_EABI_UNKNOWN:
1789 strcat (buf, ", GNU EABI");
1790 while (e_flags)
1792 unsigned flag;
1794 /* Process flags one bit at a time. */
1795 flag = e_flags & - e_flags;
1796 e_flags &= ~ flag;
1798 switch (flag)
1800 case EF_ARM_INTERWORK:
1801 strcat (buf, ", interworking enabled");
1802 break;
1804 case EF_ARM_APCS_26:
1805 strcat (buf, ", uses APCS/26");
1806 break;
1808 case EF_ARM_APCS_FLOAT:
1809 strcat (buf, ", uses APCS/float");
1810 break;
1812 case EF_ARM_PIC:
1813 strcat (buf, ", position independent");
1814 break;
1816 case EF_ARM_ALIGN8:
1817 strcat (buf, ", 8 bit structure alignment");
1818 break;
1820 case EF_ARM_NEW_ABI:
1821 strcat (buf, ", uses new ABI");
1822 break;
1824 case EF_ARM_OLD_ABI:
1825 strcat (buf, ", uses old ABI");
1826 break;
1828 case EF_ARM_SOFT_FLOAT:
1829 strcat (buf, ", software FP");
1830 break;
1832 case EF_ARM_VFP_FLOAT:
1833 strcat (buf, ", VFP");
1834 break;
1836 case EF_ARM_MAVERICK_FLOAT:
1837 strcat (buf, ", Maverick FP");
1838 break;
1840 default:
1841 unknown = 1;
1842 break;
1847 if (unknown)
1848 strcat (buf,", <unknown>");
1851 static char *
1852 get_machine_flags (unsigned e_flags, unsigned e_machine)
1854 static char buf[1024];
1856 buf[0] = '\0';
1858 if (e_flags)
1860 switch (e_machine)
1862 default:
1863 break;
1865 case EM_ARM:
1866 decode_ARM_machine_flags (e_flags, buf);
1867 break;
1869 case EM_68K:
1870 if (e_flags & EF_CPU32)
1871 strcat (buf, ", cpu32");
1872 if (e_flags & EF_M68000)
1873 strcat (buf, ", m68000");
1874 break;
1876 case EM_PPC:
1877 if (e_flags & EF_PPC_EMB)
1878 strcat (buf, ", emb");
1880 if (e_flags & EF_PPC_RELOCATABLE)
1881 strcat (buf, ", relocatable");
1883 if (e_flags & EF_PPC_RELOCATABLE_LIB)
1884 strcat (buf, ", relocatable-lib");
1885 break;
1887 case EM_V850:
1888 case EM_CYGNUS_V850:
1889 switch (e_flags & EF_V850_ARCH)
1891 case E_V850E1_ARCH:
1892 strcat (buf, ", v850e1");
1893 break;
1894 case E_V850E_ARCH:
1895 strcat (buf, ", v850e");
1896 break;
1897 case E_V850_ARCH:
1898 strcat (buf, ", v850");
1899 break;
1900 default:
1901 strcat (buf, ", unknown v850 architecture variant");
1902 break;
1904 break;
1906 case EM_M32R:
1907 case EM_CYGNUS_M32R:
1908 if ((e_flags & EF_M32R_ARCH) == E_M32R_ARCH)
1909 strcat (buf, ", m32r");
1911 break;
1913 case EM_MIPS:
1914 case EM_MIPS_RS3_LE:
1915 if (e_flags & EF_MIPS_NOREORDER)
1916 strcat (buf, ", noreorder");
1918 if (e_flags & EF_MIPS_PIC)
1919 strcat (buf, ", pic");
1921 if (e_flags & EF_MIPS_CPIC)
1922 strcat (buf, ", cpic");
1924 if (e_flags & EF_MIPS_UCODE)
1925 strcat (buf, ", ugen_reserved");
1927 if (e_flags & EF_MIPS_ABI2)
1928 strcat (buf, ", abi2");
1930 if (e_flags & EF_MIPS_OPTIONS_FIRST)
1931 strcat (buf, ", odk first");
1933 if (e_flags & EF_MIPS_32BITMODE)
1934 strcat (buf, ", 32bitmode");
1936 switch ((e_flags & EF_MIPS_MACH))
1938 case E_MIPS_MACH_3900: strcat (buf, ", 3900"); break;
1939 case E_MIPS_MACH_4010: strcat (buf, ", 4010"); break;
1940 case E_MIPS_MACH_4100: strcat (buf, ", 4100"); break;
1941 case E_MIPS_MACH_4111: strcat (buf, ", 4111"); break;
1942 case E_MIPS_MACH_4120: strcat (buf, ", 4120"); break;
1943 case E_MIPS_MACH_4650: strcat (buf, ", 4650"); break;
1944 case E_MIPS_MACH_5400: strcat (buf, ", 5400"); break;
1945 case E_MIPS_MACH_5500: strcat (buf, ", 5500"); break;
1946 case E_MIPS_MACH_SB1: strcat (buf, ", sb1"); break;
1947 case 0:
1948 /* We simply ignore the field in this case to avoid confusion:
1949 MIPS ELF does not specify EF_MIPS_MACH, it is a GNU
1950 extension. */
1951 break;
1952 default: strcat (buf, ", unknown CPU"); break;
1955 switch ((e_flags & EF_MIPS_ABI))
1957 case E_MIPS_ABI_O32: strcat (buf, ", o32"); break;
1958 case E_MIPS_ABI_O64: strcat (buf, ", o64"); break;
1959 case E_MIPS_ABI_EABI32: strcat (buf, ", eabi32"); break;
1960 case E_MIPS_ABI_EABI64: strcat (buf, ", eabi64"); break;
1961 case 0:
1962 /* We simply ignore the field in this case to avoid confusion:
1963 MIPS ELF does not specify EF_MIPS_ABI, it is a GNU extension.
1964 This means it is likely to be an o32 file, but not for
1965 sure. */
1966 break;
1967 default: strcat (buf, ", unknown ABI"); break;
1970 if (e_flags & EF_MIPS_ARCH_ASE_MDMX)
1971 strcat (buf, ", mdmx");
1973 if (e_flags & EF_MIPS_ARCH_ASE_M16)
1974 strcat (buf, ", mips16");
1976 switch ((e_flags & EF_MIPS_ARCH))
1978 case E_MIPS_ARCH_1: strcat (buf, ", mips1"); break;
1979 case E_MIPS_ARCH_2: strcat (buf, ", mips2"); break;
1980 case E_MIPS_ARCH_3: strcat (buf, ", mips3"); break;
1981 case E_MIPS_ARCH_4: strcat (buf, ", mips4"); break;
1982 case E_MIPS_ARCH_5: strcat (buf, ", mips5"); break;
1983 case E_MIPS_ARCH_32: strcat (buf, ", mips32"); break;
1984 case E_MIPS_ARCH_32R2: strcat (buf, ", mips32r2"); break;
1985 case E_MIPS_ARCH_64: strcat (buf, ", mips64"); break;
1986 case E_MIPS_ARCH_64R2: strcat (buf, ", mips64r2"); break;
1987 default: strcat (buf, ", unknown ISA"); break;
1990 break;
1992 case EM_SPARCV9:
1993 if (e_flags & EF_SPARC_32PLUS)
1994 strcat (buf, ", v8+");
1996 if (e_flags & EF_SPARC_SUN_US1)
1997 strcat (buf, ", ultrasparcI");
1999 if (e_flags & EF_SPARC_SUN_US3)
2000 strcat (buf, ", ultrasparcIII");
2002 if (e_flags & EF_SPARC_HAL_R1)
2003 strcat (buf, ", halr1");
2005 if (e_flags & EF_SPARC_LEDATA)
2006 strcat (buf, ", ledata");
2008 if ((e_flags & EF_SPARCV9_MM) == EF_SPARCV9_TSO)
2009 strcat (buf, ", tso");
2011 if ((e_flags & EF_SPARCV9_MM) == EF_SPARCV9_PSO)
2012 strcat (buf, ", pso");
2014 if ((e_flags & EF_SPARCV9_MM) == EF_SPARCV9_RMO)
2015 strcat (buf, ", rmo");
2016 break;
2018 case EM_PARISC:
2019 switch (e_flags & EF_PARISC_ARCH)
2021 case EFA_PARISC_1_0:
2022 strcpy (buf, ", PA-RISC 1.0");
2023 break;
2024 case EFA_PARISC_1_1:
2025 strcpy (buf, ", PA-RISC 1.1");
2026 break;
2027 case EFA_PARISC_2_0:
2028 strcpy (buf, ", PA-RISC 2.0");
2029 break;
2030 default:
2031 break;
2033 if (e_flags & EF_PARISC_TRAPNIL)
2034 strcat (buf, ", trapnil");
2035 if (e_flags & EF_PARISC_EXT)
2036 strcat (buf, ", ext");
2037 if (e_flags & EF_PARISC_LSB)
2038 strcat (buf, ", lsb");
2039 if (e_flags & EF_PARISC_WIDE)
2040 strcat (buf, ", wide");
2041 if (e_flags & EF_PARISC_NO_KABP)
2042 strcat (buf, ", no kabp");
2043 if (e_flags & EF_PARISC_LAZYSWAP)
2044 strcat (buf, ", lazyswap");
2045 break;
2047 case EM_PJ:
2048 case EM_PJ_OLD:
2049 if ((e_flags & EF_PICOJAVA_NEWCALLS) == EF_PICOJAVA_NEWCALLS)
2050 strcat (buf, ", new calling convention");
2052 if ((e_flags & EF_PICOJAVA_GNUCALLS) == EF_PICOJAVA_GNUCALLS)
2053 strcat (buf, ", gnu calling convention");
2054 break;
2056 case EM_IA_64:
2057 if ((e_flags & EF_IA_64_ABI64))
2058 strcat (buf, ", 64-bit");
2059 else
2060 strcat (buf, ", 32-bit");
2061 if ((e_flags & EF_IA_64_REDUCEDFP))
2062 strcat (buf, ", reduced fp model");
2063 if ((e_flags & EF_IA_64_NOFUNCDESC_CONS_GP))
2064 strcat (buf, ", no function descriptors, constant gp");
2065 else if ((e_flags & EF_IA_64_CONS_GP))
2066 strcat (buf, ", constant gp");
2067 if ((e_flags & EF_IA_64_ABSOLUTE))
2068 strcat (buf, ", absolute");
2069 break;
2071 case EM_VAX:
2072 if ((e_flags & EF_VAX_NONPIC))
2073 strcat (buf, ", non-PIC");
2074 if ((e_flags & EF_VAX_DFLOAT))
2075 strcat (buf, ", D-Float");
2076 if ((e_flags & EF_VAX_GFLOAT))
2077 strcat (buf, ", G-Float");
2078 break;
2082 return buf;
2085 static const char *
2086 get_osabi_name (unsigned int osabi)
2088 static char buff[32];
2090 switch (osabi)
2092 case ELFOSABI_NONE: return "UNIX - System V";
2093 case ELFOSABI_HPUX: return "UNIX - HP-UX";
2094 case ELFOSABI_NETBSD: return "UNIX - NetBSD";
2095 case ELFOSABI_LINUX: return "UNIX - Linux";
2096 case ELFOSABI_HURD: return "GNU/Hurd";
2097 case ELFOSABI_SOLARIS: return "UNIX - Solaris";
2098 case ELFOSABI_AIX: return "UNIX - AIX";
2099 case ELFOSABI_IRIX: return "UNIX - IRIX";
2100 case ELFOSABI_FREEBSD: return "UNIX - FreeBSD";
2101 case ELFOSABI_TRU64: return "UNIX - TRU64";
2102 case ELFOSABI_MODESTO: return "Novell - Modesto";
2103 case ELFOSABI_OPENBSD: return "UNIX - OpenBSD";
2104 case ELFOSABI_OPENVMS: return "VMS - OpenVMS";
2105 case ELFOSABI_NSK: return "HP - Non-Stop Kernel";
2106 case ELFOSABI_AROS: return "Amiga Research OS";
2107 case ELFOSABI_STANDALONE: return _("Standalone App");
2108 case ELFOSABI_ARM: return "ARM";
2109 default:
2110 sprintf (buff, _("<unknown: %x>"), osabi);
2111 return buff;
2115 static const char *
2116 get_mips_segment_type (unsigned long type)
2118 switch (type)
2120 case PT_MIPS_REGINFO:
2121 return "REGINFO";
2122 case PT_MIPS_RTPROC:
2123 return "RTPROC";
2124 case PT_MIPS_OPTIONS:
2125 return "OPTIONS";
2126 default:
2127 break;
2130 return NULL;
2133 static const char *
2134 get_parisc_segment_type (unsigned long type)
2136 switch (type)
2138 case PT_HP_TLS: return "HP_TLS";
2139 case PT_HP_CORE_NONE: return "HP_CORE_NONE";
2140 case PT_HP_CORE_VERSION: return "HP_CORE_VERSION";
2141 case PT_HP_CORE_KERNEL: return "HP_CORE_KERNEL";
2142 case PT_HP_CORE_COMM: return "HP_CORE_COMM";
2143 case PT_HP_CORE_PROC: return "HP_CORE_PROC";
2144 case PT_HP_CORE_LOADABLE: return "HP_CORE_LOADABLE";
2145 case PT_HP_CORE_STACK: return "HP_CORE_STACK";
2146 case PT_HP_CORE_SHM: return "HP_CORE_SHM";
2147 case PT_HP_CORE_MMF: return "HP_CORE_MMF";
2148 case PT_HP_PARALLEL: return "HP_PARALLEL";
2149 case PT_HP_FASTBIND: return "HP_FASTBIND";
2150 case PT_PARISC_ARCHEXT: return "PARISC_ARCHEXT";
2151 case PT_PARISC_UNWIND: return "PARISC_UNWIND";
2152 default:
2153 break;
2156 return NULL;
2159 static const char *
2160 get_ia64_segment_type (unsigned long type)
2162 switch (type)
2164 case PT_IA_64_ARCHEXT: return "IA_64_ARCHEXT";
2165 case PT_IA_64_UNWIND: return "IA_64_UNWIND";
2166 case PT_HP_TLS: return "HP_TLS";
2167 case PT_IA_64_HP_OPT_ANOT: return "HP_OPT_ANNOT";
2168 case PT_IA_64_HP_HSL_ANOT: return "HP_HSL_ANNOT";
2169 case PT_IA_64_HP_STACK: return "HP_STACK";
2170 default:
2171 break;
2174 return NULL;
2177 static const char *
2178 get_segment_type (unsigned long p_type)
2180 static char buff[32];
2182 switch (p_type)
2184 case PT_NULL: return "NULL";
2185 case PT_LOAD: return "LOAD";
2186 case PT_DYNAMIC: return "DYNAMIC";
2187 case PT_INTERP: return "INTERP";
2188 case PT_NOTE: return "NOTE";
2189 case PT_SHLIB: return "SHLIB";
2190 case PT_PHDR: return "PHDR";
2191 case PT_TLS: return "TLS";
2193 case PT_GNU_EH_FRAME:
2194 return "GNU_EH_FRAME";
2195 case PT_GNU_STACK: return "STACK";
2196 case PT_GNU_RELRO: return "GNU_RELRO";
2198 default:
2199 if ((p_type >= PT_LOPROC) && (p_type <= PT_HIPROC))
2201 const char *result;
2203 switch (elf_header.e_machine)
2205 case EM_MIPS:
2206 case EM_MIPS_RS3_LE:
2207 result = get_mips_segment_type (p_type);
2208 break;
2209 case EM_PARISC:
2210 result = get_parisc_segment_type (p_type);
2211 break;
2212 case EM_IA_64:
2213 result = get_ia64_segment_type (p_type);
2214 break;
2215 default:
2216 result = NULL;
2217 break;
2220 if (result != NULL)
2221 return result;
2223 sprintf (buff, "LOPROC+%lx", p_type - PT_LOPROC);
2225 else if ((p_type >= PT_LOOS) && (p_type <= PT_HIOS))
2227 const char *result;
2229 switch (elf_header.e_machine)
2231 case EM_PARISC:
2232 result = get_parisc_segment_type (p_type);
2233 break;
2234 case EM_IA_64:
2235 result = get_ia64_segment_type (p_type);
2236 break;
2237 default:
2238 result = NULL;
2239 break;
2242 if (result != NULL)
2243 return result;
2245 sprintf (buff, "LOOS+%lx", p_type - PT_LOOS);
2247 else
2248 sprintf (buff, _("<unknown>: %lx"), p_type);
2250 return buff;
2254 static const char *
2255 get_mips_section_type_name (unsigned int sh_type)
2257 switch (sh_type)
2259 case SHT_MIPS_LIBLIST: return "MIPS_LIBLIST";
2260 case SHT_MIPS_MSYM: return "MIPS_MSYM";
2261 case SHT_MIPS_CONFLICT: return "MIPS_CONFLICT";
2262 case SHT_MIPS_GPTAB: return "MIPS_GPTAB";
2263 case SHT_MIPS_UCODE: return "MIPS_UCODE";
2264 case SHT_MIPS_DEBUG: return "MIPS_DEBUG";
2265 case SHT_MIPS_REGINFO: return "MIPS_REGINFO";
2266 case SHT_MIPS_PACKAGE: return "MIPS_PACKAGE";
2267 case SHT_MIPS_PACKSYM: return "MIPS_PACKSYM";
2268 case SHT_MIPS_RELD: return "MIPS_RELD";
2269 case SHT_MIPS_IFACE: return "MIPS_IFACE";
2270 case SHT_MIPS_CONTENT: return "MIPS_CONTENT";
2271 case SHT_MIPS_OPTIONS: return "MIPS_OPTIONS";
2272 case SHT_MIPS_SHDR: return "MIPS_SHDR";
2273 case SHT_MIPS_FDESC: return "MIPS_FDESC";
2274 case SHT_MIPS_EXTSYM: return "MIPS_EXTSYM";
2275 case SHT_MIPS_DENSE: return "MIPS_DENSE";
2276 case SHT_MIPS_PDESC: return "MIPS_PDESC";
2277 case SHT_MIPS_LOCSYM: return "MIPS_LOCSYM";
2278 case SHT_MIPS_AUXSYM: return "MIPS_AUXSYM";
2279 case SHT_MIPS_OPTSYM: return "MIPS_OPTSYM";
2280 case SHT_MIPS_LOCSTR: return "MIPS_LOCSTR";
2281 case SHT_MIPS_LINE: return "MIPS_LINE";
2282 case SHT_MIPS_RFDESC: return "MIPS_RFDESC";
2283 case SHT_MIPS_DELTASYM: return "MIPS_DELTASYM";
2284 case SHT_MIPS_DELTAINST: return "MIPS_DELTAINST";
2285 case SHT_MIPS_DELTACLASS: return "MIPS_DELTACLASS";
2286 case SHT_MIPS_DWARF: return "MIPS_DWARF";
2287 case SHT_MIPS_DELTADECL: return "MIPS_DELTADECL";
2288 case SHT_MIPS_SYMBOL_LIB: return "MIPS_SYMBOL_LIB";
2289 case SHT_MIPS_EVENTS: return "MIPS_EVENTS";
2290 case SHT_MIPS_TRANSLATE: return "MIPS_TRANSLATE";
2291 case SHT_MIPS_PIXIE: return "MIPS_PIXIE";
2292 case SHT_MIPS_XLATE: return "MIPS_XLATE";
2293 case SHT_MIPS_XLATE_DEBUG: return "MIPS_XLATE_DEBUG";
2294 case SHT_MIPS_WHIRL: return "MIPS_WHIRL";
2295 case SHT_MIPS_EH_REGION: return "MIPS_EH_REGION";
2296 case SHT_MIPS_XLATE_OLD: return "MIPS_XLATE_OLD";
2297 case SHT_MIPS_PDR_EXCEPTION: return "MIPS_PDR_EXCEPTION";
2298 default:
2299 break;
2301 return NULL;
2304 static const char *
2305 get_parisc_section_type_name (unsigned int sh_type)
2307 switch (sh_type)
2309 case SHT_PARISC_EXT: return "PARISC_EXT";
2310 case SHT_PARISC_UNWIND: return "PARISC_UNWIND";
2311 case SHT_PARISC_DOC: return "PARISC_DOC";
2312 default:
2313 break;
2315 return NULL;
2318 static const char *
2319 get_ia64_section_type_name (unsigned int sh_type)
2321 /* If the top 8 bits are 0x78 the next 8 are the os/abi ID. */
2322 if ((sh_type & 0xFF000000) == SHT_IA_64_LOPSREG)
2323 return get_osabi_name ((sh_type & 0x00FF0000) >> 16);
2325 switch (sh_type)
2327 case SHT_IA_64_EXT: return "IA_64_EXT";
2328 case SHT_IA_64_UNWIND: return "IA_64_UNWIND";
2329 case SHT_IA_64_PRIORITY_INIT: return "IA_64_PRIORITY_INIT";
2330 default:
2331 break;
2333 return NULL;
2336 static const char *
2337 get_section_type_name (unsigned int sh_type)
2339 static char buff[32];
2341 switch (sh_type)
2343 case SHT_NULL: return "NULL";
2344 case SHT_PROGBITS: return "PROGBITS";
2345 case SHT_SYMTAB: return "SYMTAB";
2346 case SHT_STRTAB: return "STRTAB";
2347 case SHT_RELA: return "RELA";
2348 case SHT_HASH: return "HASH";
2349 case SHT_DYNAMIC: return "DYNAMIC";
2350 case SHT_NOTE: return "NOTE";
2351 case SHT_NOBITS: return "NOBITS";
2352 case SHT_REL: return "REL";
2353 case SHT_SHLIB: return "SHLIB";
2354 case SHT_DYNSYM: return "DYNSYM";
2355 case SHT_INIT_ARRAY: return "INIT_ARRAY";
2356 case SHT_FINI_ARRAY: return "FINI_ARRAY";
2357 case SHT_PREINIT_ARRAY: return "PREINIT_ARRAY";
2358 case SHT_GROUP: return "GROUP";
2359 case SHT_SYMTAB_SHNDX: return "SYMTAB SECTION INDICIES";
2360 case SHT_GNU_verdef: return "VERDEF";
2361 case SHT_GNU_verneed: return "VERNEED";
2362 case SHT_GNU_versym: return "VERSYM";
2363 case 0x6ffffff0: return "VERSYM";
2364 case 0x6ffffffc: return "VERDEF";
2365 case 0x7ffffffd: return "AUXILIARY";
2366 case 0x7fffffff: return "FILTER";
2367 case SHT_GNU_LIBLIST: return "GNU_LIBLIST";
2369 default:
2370 if ((sh_type >= SHT_LOPROC) && (sh_type <= SHT_HIPROC))
2372 const char *result;
2374 switch (elf_header.e_machine)
2376 case EM_MIPS:
2377 case EM_MIPS_RS3_LE:
2378 result = get_mips_section_type_name (sh_type);
2379 break;
2380 case EM_PARISC:
2381 result = get_parisc_section_type_name (sh_type);
2382 break;
2383 case EM_IA_64:
2384 result = get_ia64_section_type_name (sh_type);
2385 break;
2386 default:
2387 result = NULL;
2388 break;
2391 if (result != NULL)
2392 return result;
2394 sprintf (buff, "LOPROC+%x", sh_type - SHT_LOPROC);
2396 else if ((sh_type >= SHT_LOOS) && (sh_type <= SHT_HIOS))
2397 sprintf (buff, "LOOS+%x", sh_type - SHT_LOOS);
2398 else if ((sh_type >= SHT_LOUSER) && (sh_type <= SHT_HIUSER))
2399 sprintf (buff, "LOUSER+%x", sh_type - SHT_LOUSER);
2400 else
2401 sprintf (buff, _("<unknown>: %x"), sh_type);
2403 return buff;
2407 #define OPTION_DEBUG_DUMP 512
2409 struct option options[] =
2411 {"all", no_argument, 0, 'a'},
2412 {"file-header", no_argument, 0, 'h'},
2413 {"program-headers", no_argument, 0, 'l'},
2414 {"headers", no_argument, 0, 'e'},
2415 {"histogram", no_argument, 0, 'I'},
2416 {"segments", no_argument, 0, 'l'},
2417 {"sections", no_argument, 0, 'S'},
2418 {"section-headers", no_argument, 0, 'S'},
2419 {"section-groups", no_argument, 0, 'g'},
2420 {"symbols", no_argument, 0, 's'},
2421 {"syms", no_argument, 0, 's'},
2422 {"relocs", no_argument, 0, 'r'},
2423 {"notes", no_argument, 0, 'n'},
2424 {"dynamic", no_argument, 0, 'd'},
2425 {"arch-specific", no_argument, 0, 'A'},
2426 {"version-info", no_argument, 0, 'V'},
2427 {"use-dynamic", no_argument, 0, 'D'},
2428 {"hex-dump", required_argument, 0, 'x'},
2429 {"debug-dump", optional_argument, 0, OPTION_DEBUG_DUMP},
2430 {"unwind", no_argument, 0, 'u'},
2431 #ifdef SUPPORT_DISASSEMBLY
2432 {"instruction-dump", required_argument, 0, 'i'},
2433 #endif
2435 {"version", no_argument, 0, 'v'},
2436 {"wide", no_argument, 0, 'W'},
2437 {"help", no_argument, 0, 'H'},
2438 {0, no_argument, 0, 0}
2441 static void
2442 usage (void)
2444 fprintf (stdout, _("Usage: readelf <option(s)> elf-file(s)\n"));
2445 fprintf (stdout, _(" Display information about the contents of ELF format files\n"));
2446 fprintf (stdout, _(" Options are:\n\
2447 -a --all Equivalent to: -h -l -S -s -r -d -V -A -I\n\
2448 -h --file-header Display the ELF file header\n\
2449 -l --program-headers Display the program headers\n\
2450 --segments An alias for --program-headers\n\
2451 -S --section-headers Display the sections' header\n\
2452 --sections An alias for --section-headers\n\
2453 -g --section-groups Display the section groups\n\
2454 -e --headers Equivalent to: -h -l -S\n\
2455 -s --syms Display the symbol table\n\
2456 --symbols An alias for --syms\n\
2457 -n --notes Display the core notes (if present)\n\
2458 -r --relocs Display the relocations (if present)\n\
2459 -u --unwind Display the unwind info (if present)\n\
2460 -d --dynamic Display the dynamic segment (if present)\n\
2461 -V --version-info Display the version sections (if present)\n\
2462 -A --arch-specific Display architecture specific information (if any).\n\
2463 -D --use-dynamic Use the dynamic section info when displaying symbols\n\
2464 -x --hex-dump=<number> Dump the contents of section <number>\n\
2465 -w[liaprmfFso] or\n\
2466 --debug-dump[=line,=info,=abbrev,=pubnames,=ranges,=macro,=frames,=str,=loc]\n\
2467 Display the contents of DWARF2 debug sections\n"));
2468 #ifdef SUPPORT_DISASSEMBLY
2469 fprintf (stdout, _("\
2470 -i --instruction-dump=<number>\n\
2471 Disassemble the contents of section <number>\n"));
2472 #endif
2473 fprintf (stdout, _("\
2474 -I --histogram Display histogram of bucket list lengths\n\
2475 -W --wide Allow output width to exceed 80 characters\n\
2476 -H --help Display this information\n\
2477 -v --version Display the version number of readelf\n"));
2478 fprintf (stdout, _("Report bugs to %s\n"), REPORT_BUGS_TO);
2480 exit (0);
2483 static void
2484 request_dump (unsigned int section, int type)
2486 if (section >= num_dump_sects)
2488 char *new_dump_sects;
2490 new_dump_sects = calloc (section + 1, 1);
2492 if (new_dump_sects == NULL)
2493 error (_("Out of memory allocating dump request table."));
2494 else
2496 /* Copy current flag settings. */
2497 memcpy (new_dump_sects, dump_sects, num_dump_sects);
2499 free (dump_sects);
2501 dump_sects = new_dump_sects;
2502 num_dump_sects = section + 1;
2506 if (dump_sects)
2507 dump_sects[section] |= type;
2509 return;
2512 static void
2513 parse_args (int argc, char **argv)
2515 int c;
2517 if (argc < 2)
2518 usage ();
2520 while ((c = getopt_long
2521 (argc, argv, "ersuahnldSDAIgw::x:i:vVWH", options, NULL)) != EOF)
2523 char *cp;
2524 int section;
2526 switch (c)
2528 case 0:
2529 /* Long options. */
2530 break;
2531 case 'H':
2532 usage ();
2533 break;
2535 case 'a':
2536 do_syms++;
2537 do_reloc++;
2538 do_unwind++;
2539 do_dynamic++;
2540 do_header++;
2541 do_sections++;
2542 do_section_groups++;
2543 do_segments++;
2544 do_version++;
2545 do_histogram++;
2546 do_arch++;
2547 do_notes++;
2548 break;
2549 case 'g':
2550 do_section_groups++;
2551 break;
2552 case 'e':
2553 do_header++;
2554 do_sections++;
2555 do_segments++;
2556 break;
2557 case 'A':
2558 do_arch++;
2559 break;
2560 case 'D':
2561 do_using_dynamic++;
2562 break;
2563 case 'r':
2564 do_reloc++;
2565 break;
2566 case 'u':
2567 do_unwind++;
2568 break;
2569 case 'h':
2570 do_header++;
2571 break;
2572 case 'l':
2573 do_segments++;
2574 break;
2575 case 's':
2576 do_syms++;
2577 break;
2578 case 'S':
2579 do_sections++;
2580 break;
2581 case 'd':
2582 do_dynamic++;
2583 break;
2584 case 'I':
2585 do_histogram++;
2586 break;
2587 case 'n':
2588 do_notes++;
2589 break;
2590 case 'x':
2591 do_dump++;
2592 section = strtoul (optarg, & cp, 0);
2593 if (! *cp && section >= 0)
2595 request_dump (section, HEX_DUMP);
2596 break;
2598 goto oops;
2599 case 'w':
2600 do_dump++;
2601 if (optarg == 0)
2602 do_debugging = 1;
2603 else
2605 unsigned int index = 0;
2607 do_debugging = 0;
2609 while (optarg[index])
2610 switch (optarg[index++])
2612 case 'i':
2613 case 'I':
2614 do_debug_info = 1;
2615 break;
2617 case 'a':
2618 case 'A':
2619 do_debug_abbrevs = 1;
2620 break;
2622 case 'l':
2623 case 'L':
2624 do_debug_lines = 1;
2625 break;
2627 case 'p':
2628 case 'P':
2629 do_debug_pubnames = 1;
2630 break;
2632 case 'r':
2633 case 'R':
2634 do_debug_aranges = 1;
2635 break;
2637 case 'F':
2638 do_debug_frames_interp = 1;
2639 case 'f':
2640 do_debug_frames = 1;
2641 break;
2643 case 'm':
2644 case 'M':
2645 do_debug_macinfo = 1;
2646 break;
2648 case 's':
2649 case 'S':
2650 do_debug_str = 1;
2651 break;
2653 case 'o':
2654 case 'O':
2655 do_debug_loc = 1;
2656 break;
2658 default:
2659 warn (_("Unrecognized debug option '%s'\n"), optarg);
2660 break;
2663 break;
2664 case OPTION_DEBUG_DUMP:
2665 do_dump++;
2666 if (optarg == 0)
2667 do_debugging = 1;
2668 else
2670 static const char *debug_dump_opt[]
2671 = { "line", "info", "abbrev", "pubnames", "ranges",
2672 "macro", "frames", "frames-interp", "str", "loc", NULL };
2673 unsigned int index;
2674 const char *p;
2676 do_debugging = 0;
2678 p = optarg;
2679 while (*p)
2681 for (index = 0; debug_dump_opt[index]; index++)
2683 size_t len = strlen (debug_dump_opt[index]);
2685 if (strncmp (p, debug_dump_opt[index], len) == 0
2686 && (p[len] == ',' || p[len] == '\0'))
2688 switch (p[0])
2690 case 'i':
2691 do_debug_info = 1;
2692 break;
2694 case 'a':
2695 do_debug_abbrevs = 1;
2696 break;
2698 case 'l':
2699 if (p[1] == 'i')
2700 do_debug_lines = 1;
2701 else
2702 do_debug_loc = 1;
2703 break;
2705 case 'p':
2706 do_debug_pubnames = 1;
2707 break;
2709 case 'r':
2710 do_debug_aranges = 1;
2711 break;
2713 case 'f':
2714 if (len > 6)
2715 do_debug_frames_interp = 1;
2716 do_debug_frames = 1;
2717 break;
2719 case 'm':
2720 do_debug_macinfo = 1;
2721 break;
2723 case 's':
2724 do_debug_str = 1;
2725 break;
2728 p += len;
2729 break;
2733 if (debug_dump_opt[index] == NULL)
2735 warn (_("Unrecognized debug option '%s'\n"), p);
2736 p = strchr (p, ',');
2737 if (p == NULL)
2738 break;
2741 if (*p == ',')
2742 p++;
2745 break;
2746 #ifdef SUPPORT_DISASSEMBLY
2747 case 'i':
2748 do_dump++;
2749 section = strtoul (optarg, & cp, 0);
2750 if (! *cp && section >= 0)
2752 request_dump (section, DISASS_DUMP);
2753 break;
2755 goto oops;
2756 #endif
2757 case 'v':
2758 print_version (program_name);
2759 break;
2760 case 'V':
2761 do_version++;
2762 break;
2763 case 'W':
2764 do_wide++;
2765 break;
2766 default:
2767 oops:
2768 /* xgettext:c-format */
2769 error (_("Invalid option '-%c'\n"), c);
2770 /* Drop through. */
2771 case '?':
2772 usage ();
2776 if (!do_dynamic && !do_syms && !do_reloc && !do_unwind && !do_sections
2777 && !do_segments && !do_header && !do_dump && !do_version
2778 && !do_histogram && !do_debugging && !do_arch && !do_notes
2779 && !do_section_groups)
2780 usage ();
2781 else if (argc < 3)
2783 warn (_("Nothing to do.\n"));
2784 usage();
2788 static const char *
2789 get_elf_class (unsigned int elf_class)
2791 static char buff[32];
2793 switch (elf_class)
2795 case ELFCLASSNONE: return _("none");
2796 case ELFCLASS32: return "ELF32";
2797 case ELFCLASS64: return "ELF64";
2798 default:
2799 sprintf (buff, _("<unknown: %x>"), elf_class);
2800 return buff;
2804 static const char *
2805 get_data_encoding (unsigned int encoding)
2807 static char buff[32];
2809 switch (encoding)
2811 case ELFDATANONE: return _("none");
2812 case ELFDATA2LSB: return _("2's complement, little endian");
2813 case ELFDATA2MSB: return _("2's complement, big endian");
2814 default:
2815 sprintf (buff, _("<unknown: %x>"), encoding);
2816 return buff;
2820 /* Decode the data held in 'elf_header'. */
2822 static int
2823 process_file_header (void)
2825 if ( elf_header.e_ident[EI_MAG0] != ELFMAG0
2826 || elf_header.e_ident[EI_MAG1] != ELFMAG1
2827 || elf_header.e_ident[EI_MAG2] != ELFMAG2
2828 || elf_header.e_ident[EI_MAG3] != ELFMAG3)
2830 error
2831 (_("Not an ELF file - it has the wrong magic bytes at the start\n"));
2832 return 0;
2835 if (do_header)
2837 int i;
2839 printf (_("ELF Header:\n"));
2840 printf (_(" Magic: "));
2841 for (i = 0; i < EI_NIDENT; i++)
2842 printf ("%2.2x ", elf_header.e_ident[i]);
2843 printf ("\n");
2844 printf (_(" Class: %s\n"),
2845 get_elf_class (elf_header.e_ident[EI_CLASS]));
2846 printf (_(" Data: %s\n"),
2847 get_data_encoding (elf_header.e_ident[EI_DATA]));
2848 printf (_(" Version: %d %s\n"),
2849 elf_header.e_ident[EI_VERSION],
2850 (elf_header.e_ident[EI_VERSION] == EV_CURRENT
2851 ? "(current)"
2852 : (elf_header.e_ident[EI_VERSION] != EV_NONE
2853 ? "<unknown: %lx>"
2854 : "")));
2855 printf (_(" OS/ABI: %s\n"),
2856 get_osabi_name (elf_header.e_ident[EI_OSABI]));
2857 printf (_(" ABI Version: %d\n"),
2858 elf_header.e_ident[EI_ABIVERSION]);
2859 printf (_(" Type: %s\n"),
2860 get_file_type (elf_header.e_type));
2861 printf (_(" Machine: %s\n"),
2862 get_machine_name (elf_header.e_machine));
2863 printf (_(" Version: 0x%lx\n"),
2864 (unsigned long) elf_header.e_version);
2866 printf (_(" Entry point address: "));
2867 print_vma ((bfd_vma) elf_header.e_entry, PREFIX_HEX);
2868 printf (_("\n Start of program headers: "));
2869 print_vma ((bfd_vma) elf_header.e_phoff, DEC);
2870 printf (_(" (bytes into file)\n Start of section headers: "));
2871 print_vma ((bfd_vma) elf_header.e_shoff, DEC);
2872 printf (_(" (bytes into file)\n"));
2874 printf (_(" Flags: 0x%lx%s\n"),
2875 (unsigned long) elf_header.e_flags,
2876 get_machine_flags (elf_header.e_flags, elf_header.e_machine));
2877 printf (_(" Size of this header: %ld (bytes)\n"),
2878 (long) elf_header.e_ehsize);
2879 printf (_(" Size of program headers: %ld (bytes)\n"),
2880 (long) elf_header.e_phentsize);
2881 printf (_(" Number of program headers: %ld\n"),
2882 (long) elf_header.e_phnum);
2883 printf (_(" Size of section headers: %ld (bytes)\n"),
2884 (long) elf_header.e_shentsize);
2885 printf (_(" Number of section headers: %ld"),
2886 (long) elf_header.e_shnum);
2887 if (section_headers != NULL && elf_header.e_shnum == 0)
2888 printf (" (%ld)", (long) section_headers[0].sh_size);
2889 putc ('\n', stdout);
2890 printf (_(" Section header string table index: %ld"),
2891 (long) elf_header.e_shstrndx);
2892 if (section_headers != NULL && elf_header.e_shstrndx == SHN_XINDEX)
2893 printf (" (%ld)", (long) section_headers[0].sh_link);
2894 putc ('\n', stdout);
2897 if (section_headers != NULL)
2899 if (elf_header.e_shnum == 0)
2900 elf_header.e_shnum = section_headers[0].sh_size;
2901 if (elf_header.e_shstrndx == SHN_XINDEX)
2902 elf_header.e_shstrndx = section_headers[0].sh_link;
2903 free (section_headers);
2904 section_headers = NULL;
2907 return 1;
2911 static int
2912 get_32bit_program_headers (FILE *file, Elf_Internal_Phdr *program_headers)
2914 Elf32_External_Phdr *phdrs;
2915 Elf32_External_Phdr *external;
2916 Elf_Internal_Phdr *internal;
2917 unsigned int i;
2919 phdrs = get_data (NULL, file, elf_header.e_phoff,
2920 elf_header.e_phentsize * elf_header.e_phnum,
2921 _("program headers"));
2922 if (!phdrs)
2923 return 0;
2925 for (i = 0, internal = program_headers, external = phdrs;
2926 i < elf_header.e_phnum;
2927 i++, internal++, external++)
2929 internal->p_type = BYTE_GET (external->p_type);
2930 internal->p_offset = BYTE_GET (external->p_offset);
2931 internal->p_vaddr = BYTE_GET (external->p_vaddr);
2932 internal->p_paddr = BYTE_GET (external->p_paddr);
2933 internal->p_filesz = BYTE_GET (external->p_filesz);
2934 internal->p_memsz = BYTE_GET (external->p_memsz);
2935 internal->p_flags = BYTE_GET (external->p_flags);
2936 internal->p_align = BYTE_GET (external->p_align);
2939 free (phdrs);
2941 return 1;
2944 static int
2945 get_64bit_program_headers (FILE *file, Elf_Internal_Phdr *program_headers)
2947 Elf64_External_Phdr *phdrs;
2948 Elf64_External_Phdr *external;
2949 Elf_Internal_Phdr *internal;
2950 unsigned int i;
2952 phdrs = get_data (NULL, file, elf_header.e_phoff,
2953 elf_header.e_phentsize * elf_header.e_phnum,
2954 _("program headers"));
2955 if (!phdrs)
2956 return 0;
2958 for (i = 0, internal = program_headers, external = phdrs;
2959 i < elf_header.e_phnum;
2960 i++, internal++, external++)
2962 internal->p_type = BYTE_GET (external->p_type);
2963 internal->p_flags = BYTE_GET (external->p_flags);
2964 internal->p_offset = BYTE_GET8 (external->p_offset);
2965 internal->p_vaddr = BYTE_GET8 (external->p_vaddr);
2966 internal->p_paddr = BYTE_GET8 (external->p_paddr);
2967 internal->p_filesz = BYTE_GET8 (external->p_filesz);
2968 internal->p_memsz = BYTE_GET8 (external->p_memsz);
2969 internal->p_align = BYTE_GET8 (external->p_align);
2972 free (phdrs);
2974 return 1;
2977 /* Returns 1 if the program headers were read into `program_headers'. */
2979 static int
2980 get_program_headers (FILE *file)
2982 Elf_Internal_Phdr *phdrs;
2984 /* Check cache of prior read. */
2985 if (program_headers != NULL)
2986 return 1;
2988 phdrs = malloc (elf_header.e_phnum * sizeof (Elf_Internal_Phdr));
2990 if (phdrs == NULL)
2992 error (_("Out of memory\n"));
2993 return 0;
2996 if (is_32bit_elf
2997 ? get_32bit_program_headers (file, phdrs)
2998 : get_64bit_program_headers (file, phdrs))
3000 program_headers = phdrs;
3001 return 1;
3004 free (phdrs);
3005 return 0;
3008 /* Returns 1 if the program headers were loaded. */
3010 static int
3011 process_program_headers (FILE *file)
3013 Elf_Internal_Phdr *segment;
3014 unsigned int i;
3016 if (elf_header.e_phnum == 0)
3018 if (do_segments)
3019 printf (_("\nThere are no program headers in this file.\n"));
3020 return 0;
3023 if (do_segments && !do_header)
3025 printf (_("\nElf file type is %s\n"), get_file_type (elf_header.e_type));
3026 printf (_("Entry point "));
3027 print_vma ((bfd_vma) elf_header.e_entry, PREFIX_HEX);
3028 printf (_("\nThere are %d program headers, starting at offset "),
3029 elf_header.e_phnum);
3030 print_vma ((bfd_vma) elf_header.e_phoff, DEC);
3031 printf ("\n");
3034 if (! get_program_headers (file))
3035 return 0;
3037 if (do_segments)
3039 if (elf_header.e_phnum > 1)
3040 printf (_("\nProgram Headers:\n"));
3041 else
3042 printf (_("\nProgram Headers:\n"));
3044 if (is_32bit_elf)
3045 printf
3046 (_(" Type Offset VirtAddr PhysAddr FileSiz MemSiz Flg Align\n"));
3047 else if (do_wide)
3048 printf
3049 (_(" Type Offset VirtAddr PhysAddr FileSiz MemSiz Flg Align\n"));
3050 else
3052 printf
3053 (_(" Type Offset VirtAddr PhysAddr\n"));
3054 printf
3055 (_(" FileSiz MemSiz Flags Align\n"));
3059 dynamic_addr = 0;
3060 dynamic_size = 0;
3062 for (i = 0, segment = program_headers;
3063 i < elf_header.e_phnum;
3064 i++, segment++)
3066 if (do_segments)
3068 printf (" %-14.14s ", get_segment_type (segment->p_type));
3070 if (is_32bit_elf)
3072 printf ("0x%6.6lx ", (unsigned long) segment->p_offset);
3073 printf ("0x%8.8lx ", (unsigned long) segment->p_vaddr);
3074 printf ("0x%8.8lx ", (unsigned long) segment->p_paddr);
3075 printf ("0x%5.5lx ", (unsigned long) segment->p_filesz);
3076 printf ("0x%5.5lx ", (unsigned long) segment->p_memsz);
3077 printf ("%c%c%c ",
3078 (segment->p_flags & PF_R ? 'R' : ' '),
3079 (segment->p_flags & PF_W ? 'W' : ' '),
3080 (segment->p_flags & PF_X ? 'E' : ' '));
3081 printf ("%#lx", (unsigned long) segment->p_align);
3083 else if (do_wide)
3085 if ((unsigned long) segment->p_offset == segment->p_offset)
3086 printf ("0x%6.6lx ", (unsigned long) segment->p_offset);
3087 else
3089 print_vma (segment->p_offset, FULL_HEX);
3090 putchar (' ');
3093 print_vma (segment->p_vaddr, FULL_HEX);
3094 putchar (' ');
3095 print_vma (segment->p_paddr, FULL_HEX);
3096 putchar (' ');
3098 if ((unsigned long) segment->p_filesz == segment->p_filesz)
3099 printf ("0x%6.6lx ", (unsigned long) segment->p_filesz);
3100 else
3102 print_vma (segment->p_filesz, FULL_HEX);
3103 putchar (' ');
3106 if ((unsigned long) segment->p_memsz == segment->p_memsz)
3107 printf ("0x%6.6lx", (unsigned long) segment->p_memsz);
3108 else
3110 print_vma (segment->p_offset, FULL_HEX);
3113 printf (" %c%c%c ",
3114 (segment->p_flags & PF_R ? 'R' : ' '),
3115 (segment->p_flags & PF_W ? 'W' : ' '),
3116 (segment->p_flags & PF_X ? 'E' : ' '));
3118 if ((unsigned long) segment->p_align == segment->p_align)
3119 printf ("%#lx", (unsigned long) segment->p_align);
3120 else
3122 print_vma (segment->p_align, PREFIX_HEX);
3125 else
3127 print_vma (segment->p_offset, FULL_HEX);
3128 putchar (' ');
3129 print_vma (segment->p_vaddr, FULL_HEX);
3130 putchar (' ');
3131 print_vma (segment->p_paddr, FULL_HEX);
3132 printf ("\n ");
3133 print_vma (segment->p_filesz, FULL_HEX);
3134 putchar (' ');
3135 print_vma (segment->p_memsz, FULL_HEX);
3136 printf (" %c%c%c ",
3137 (segment->p_flags & PF_R ? 'R' : ' '),
3138 (segment->p_flags & PF_W ? 'W' : ' '),
3139 (segment->p_flags & PF_X ? 'E' : ' '));
3140 print_vma (segment->p_align, HEX);
3144 switch (segment->p_type)
3146 case PT_DYNAMIC:
3147 if (dynamic_addr)
3148 error (_("more than one dynamic segment\n"));
3150 dynamic_addr = segment->p_offset;
3151 dynamic_size = segment->p_filesz;
3152 break;
3154 case PT_INTERP:
3155 if (fseek (file, archive_file_offset + (long) segment->p_offset,
3156 SEEK_SET))
3157 error (_("Unable to find program interpreter name\n"));
3158 else
3160 program_interpreter[0] = 0;
3161 fscanf (file, "%63s", program_interpreter);
3163 if (do_segments)
3164 printf (_("\n [Requesting program interpreter: %s]"),
3165 program_interpreter);
3167 break;
3170 if (do_segments)
3171 putc ('\n', stdout);
3174 if (do_segments && section_headers != NULL)
3176 printf (_("\n Section to Segment mapping:\n"));
3177 printf (_(" Segment Sections...\n"));
3179 assert (string_table != NULL);
3181 for (i = 0; i < elf_header.e_phnum; i++)
3183 unsigned int j;
3184 Elf_Internal_Shdr *section;
3186 segment = program_headers + i;
3187 section = section_headers;
3189 printf (" %2.2d ", i);
3191 for (j = 1; j < elf_header.e_shnum; j++, section++)
3193 if (section->sh_size > 0
3194 /* Compare allocated sections by VMA, unallocated
3195 sections by file offset. */
3196 && (section->sh_flags & SHF_ALLOC
3197 ? (section->sh_addr >= segment->p_vaddr
3198 && section->sh_addr + section->sh_size
3199 <= segment->p_vaddr + segment->p_memsz)
3200 : ((bfd_vma) section->sh_offset >= segment->p_offset
3201 && (section->sh_offset + section->sh_size
3202 <= segment->p_offset + segment->p_filesz))))
3203 printf ("%s ", SECTION_NAME (section));
3206 putc ('\n',stdout);
3210 return 1;
3214 /* Find the file offset corresponding to VMA by using the program headers. */
3216 static long
3217 offset_from_vma (FILE *file, bfd_vma vma, bfd_size_type size)
3219 Elf_Internal_Phdr *seg;
3221 if (! get_program_headers (file))
3223 warn (_("Cannot interpret virtual addresses without program headers.\n"));
3224 return (long) vma;
3227 for (seg = program_headers;
3228 seg < program_headers + elf_header.e_phnum;
3229 ++seg)
3231 if (seg->p_type != PT_LOAD)
3232 continue;
3234 if (vma >= (seg->p_vaddr & -seg->p_align)
3235 && vma + size <= seg->p_vaddr + seg->p_filesz)
3236 return vma - seg->p_vaddr + seg->p_offset;
3239 warn (_("Virtual address 0x%lx not located in any PT_LOAD segment.\n"),
3240 (long) vma);
3241 return (long) vma;
3245 static int
3246 get_32bit_section_headers (FILE *file, unsigned int num)
3248 Elf32_External_Shdr *shdrs;
3249 Elf_Internal_Shdr *internal;
3250 unsigned int i;
3252 shdrs = get_data (NULL, file, elf_header.e_shoff,
3253 elf_header.e_shentsize * num, _("section headers"));
3254 if (!shdrs)
3255 return 0;
3257 section_headers = malloc (num * sizeof (Elf_Internal_Shdr));
3259 if (section_headers == NULL)
3261 error (_("Out of memory\n"));
3262 return 0;
3265 for (i = 0, internal = section_headers;
3266 i < num;
3267 i++, internal++)
3269 internal->sh_name = BYTE_GET (shdrs[i].sh_name);
3270 internal->sh_type = BYTE_GET (shdrs[i].sh_type);
3271 internal->sh_flags = BYTE_GET (shdrs[i].sh_flags);
3272 internal->sh_addr = BYTE_GET (shdrs[i].sh_addr);
3273 internal->sh_offset = BYTE_GET (shdrs[i].sh_offset);
3274 internal->sh_size = BYTE_GET (shdrs[i].sh_size);
3275 internal->sh_link = BYTE_GET (shdrs[i].sh_link);
3276 internal->sh_info = BYTE_GET (shdrs[i].sh_info);
3277 internal->sh_addralign = BYTE_GET (shdrs[i].sh_addralign);
3278 internal->sh_entsize = BYTE_GET (shdrs[i].sh_entsize);
3281 free (shdrs);
3283 return 1;
3286 static int
3287 get_64bit_section_headers (FILE *file, unsigned int num)
3289 Elf64_External_Shdr *shdrs;
3290 Elf_Internal_Shdr *internal;
3291 unsigned int i;
3293 shdrs = get_data (NULL, file, elf_header.e_shoff,
3294 elf_header.e_shentsize * num, _("section headers"));
3295 if (!shdrs)
3296 return 0;
3298 section_headers = malloc (num * sizeof (Elf_Internal_Shdr));
3300 if (section_headers == NULL)
3302 error (_("Out of memory\n"));
3303 return 0;
3306 for (i = 0, internal = section_headers;
3307 i < num;
3308 i++, internal++)
3310 internal->sh_name = BYTE_GET (shdrs[i].sh_name);
3311 internal->sh_type = BYTE_GET (shdrs[i].sh_type);
3312 internal->sh_flags = BYTE_GET8 (shdrs[i].sh_flags);
3313 internal->sh_addr = BYTE_GET8 (shdrs[i].sh_addr);
3314 internal->sh_size = BYTE_GET8 (shdrs[i].sh_size);
3315 internal->sh_entsize = BYTE_GET8 (shdrs[i].sh_entsize);
3316 internal->sh_link = BYTE_GET (shdrs[i].sh_link);
3317 internal->sh_info = BYTE_GET (shdrs[i].sh_info);
3318 internal->sh_offset = BYTE_GET (shdrs[i].sh_offset);
3319 internal->sh_addralign = BYTE_GET (shdrs[i].sh_addralign);
3322 free (shdrs);
3324 return 1;
3327 static Elf_Internal_Sym *
3328 get_32bit_elf_symbols (FILE *file, Elf_Internal_Shdr *section)
3330 unsigned long number;
3331 Elf32_External_Sym *esyms;
3332 Elf_External_Sym_Shndx *shndx;
3333 Elf_Internal_Sym *isyms;
3334 Elf_Internal_Sym *psym;
3335 unsigned int j;
3337 esyms = get_data (NULL, file, section->sh_offset, section->sh_size,
3338 _("symbols"));
3339 if (!esyms)
3340 return NULL;
3342 shndx = NULL;
3343 if (symtab_shndx_hdr != NULL
3344 && (symtab_shndx_hdr->sh_link
3345 == (unsigned long) SECTION_HEADER_NUM (section - section_headers)))
3347 shndx = get_data (NULL, file, symtab_shndx_hdr->sh_offset,
3348 symtab_shndx_hdr->sh_size, _("symtab shndx"));
3349 if (!shndx)
3351 free (esyms);
3352 return NULL;
3356 number = section->sh_size / section->sh_entsize;
3357 isyms = malloc (number * sizeof (Elf_Internal_Sym));
3359 if (isyms == NULL)
3361 error (_("Out of memory\n"));
3362 if (shndx)
3363 free (shndx);
3364 free (esyms);
3365 return NULL;
3368 for (j = 0, psym = isyms;
3369 j < number;
3370 j++, psym++)
3372 psym->st_name = BYTE_GET (esyms[j].st_name);
3373 psym->st_value = BYTE_GET (esyms[j].st_value);
3374 psym->st_size = BYTE_GET (esyms[j].st_size);
3375 psym->st_shndx = BYTE_GET (esyms[j].st_shndx);
3376 if (psym->st_shndx == SHN_XINDEX && shndx != NULL)
3377 psym->st_shndx
3378 = byte_get ((unsigned char *) &shndx[j], sizeof (shndx[j]));
3379 psym->st_info = BYTE_GET (esyms[j].st_info);
3380 psym->st_other = BYTE_GET (esyms[j].st_other);
3383 if (shndx)
3384 free (shndx);
3385 free (esyms);
3387 return isyms;
3390 static Elf_Internal_Sym *
3391 get_64bit_elf_symbols (FILE *file, Elf_Internal_Shdr *section)
3393 unsigned long number;
3394 Elf64_External_Sym *esyms;
3395 Elf_External_Sym_Shndx *shndx;
3396 Elf_Internal_Sym *isyms;
3397 Elf_Internal_Sym *psym;
3398 unsigned int j;
3400 esyms = get_data (NULL, file, section->sh_offset, section->sh_size,
3401 _("symbols"));
3402 if (!esyms)
3403 return NULL;
3405 shndx = NULL;
3406 if (symtab_shndx_hdr != NULL
3407 && (symtab_shndx_hdr->sh_link
3408 == (unsigned long) SECTION_HEADER_NUM (section - section_headers)))
3410 shndx = get_data (NULL, file, symtab_shndx_hdr->sh_offset,
3411 symtab_shndx_hdr->sh_size, _("symtab shndx"));
3412 if (!shndx)
3414 free (esyms);
3415 return NULL;
3419 number = section->sh_size / section->sh_entsize;
3420 isyms = malloc (number * sizeof (Elf_Internal_Sym));
3422 if (isyms == NULL)
3424 error (_("Out of memory\n"));
3425 if (shndx)
3426 free (shndx);
3427 free (esyms);
3428 return NULL;
3431 for (j = 0, psym = isyms;
3432 j < number;
3433 j++, psym++)
3435 psym->st_name = BYTE_GET (esyms[j].st_name);
3436 psym->st_info = BYTE_GET (esyms[j].st_info);
3437 psym->st_other = BYTE_GET (esyms[j].st_other);
3438 psym->st_shndx = BYTE_GET (esyms[j].st_shndx);
3439 if (psym->st_shndx == SHN_XINDEX && shndx != NULL)
3440 psym->st_shndx
3441 = byte_get ((unsigned char *) &shndx[j], sizeof (shndx[j]));
3442 psym->st_value = BYTE_GET8 (esyms[j].st_value);
3443 psym->st_size = BYTE_GET8 (esyms[j].st_size);
3446 if (shndx)
3447 free (shndx);
3448 free (esyms);
3450 return isyms;
3453 static const char *
3454 get_elf_section_flags (bfd_vma sh_flags)
3456 static char buff[32];
3458 *buff = 0;
3460 while (sh_flags)
3462 bfd_vma flag;
3464 flag = sh_flags & - sh_flags;
3465 sh_flags &= ~ flag;
3467 switch (flag)
3469 case SHF_WRITE: strcat (buff, "W"); break;
3470 case SHF_ALLOC: strcat (buff, "A"); break;
3471 case SHF_EXECINSTR: strcat (buff, "X"); break;
3472 case SHF_MERGE: strcat (buff, "M"); break;
3473 case SHF_STRINGS: strcat (buff, "S"); break;
3474 case SHF_INFO_LINK: strcat (buff, "I"); break;
3475 case SHF_LINK_ORDER: strcat (buff, "L"); break;
3476 case SHF_OS_NONCONFORMING: strcat (buff, "O"); break;
3477 case SHF_GROUP: strcat (buff, "G"); break;
3478 case SHF_TLS: strcat (buff, "T"); break;
3480 default:
3481 if (flag & SHF_MASKOS)
3483 strcat (buff, "o");
3484 sh_flags &= ~ SHF_MASKOS;
3486 else if (flag & SHF_MASKPROC)
3488 strcat (buff, "p");
3489 sh_flags &= ~ SHF_MASKPROC;
3491 else
3492 strcat (buff, "x");
3493 break;
3497 return buff;
3500 static int
3501 process_section_headers (FILE *file)
3503 Elf_Internal_Shdr *section;
3504 unsigned int i;
3506 section_headers = NULL;
3508 if (elf_header.e_shnum == 0)
3510 if (do_sections)
3511 printf (_("\nThere are no sections in this file.\n"));
3513 return 1;
3516 if (do_sections && !do_header)
3517 printf (_("There are %d section headers, starting at offset 0x%lx:\n"),
3518 elf_header.e_shnum, (unsigned long) elf_header.e_shoff);
3520 if (is_32bit_elf)
3522 if (! get_32bit_section_headers (file, elf_header.e_shnum))
3523 return 0;
3525 else if (! get_64bit_section_headers (file, elf_header.e_shnum))
3526 return 0;
3528 /* Read in the string table, so that we have names to display. */
3529 section = SECTION_HEADER (elf_header.e_shstrndx);
3531 if (section->sh_size != 0)
3533 string_table = get_data (NULL, file, section->sh_offset,
3534 section->sh_size, _("string table"));
3536 if (string_table == NULL)
3537 return 0;
3539 string_table_length = section->sh_size;
3542 /* Scan the sections for the dynamic symbol table
3543 and dynamic string table and debug sections. */
3544 dynamic_symbols = NULL;
3545 dynamic_strings = NULL;
3546 dynamic_syminfo = NULL;
3547 symtab_shndx_hdr = NULL;
3549 for (i = 0, section = section_headers;
3550 i < elf_header.e_shnum;
3551 i++, section++)
3553 char *name = SECTION_NAME (section);
3555 if (section->sh_type == SHT_DYNSYM)
3557 if (dynamic_symbols != NULL)
3559 error (_("File contains multiple dynamic symbol tables\n"));
3560 continue;
3563 num_dynamic_syms = section->sh_size / section->sh_entsize;
3564 dynamic_symbols = GET_ELF_SYMBOLS (file, section);
3566 else if (section->sh_type == SHT_STRTAB
3567 && strcmp (name, ".dynstr") == 0)
3569 if (dynamic_strings != NULL)
3571 error (_("File contains multiple dynamic string tables\n"));
3572 continue;
3575 dynamic_strings = get_data (NULL, file, section->sh_offset,
3576 section->sh_size, _("dynamic strings"));
3578 else if (section->sh_type == SHT_SYMTAB_SHNDX)
3580 if (symtab_shndx_hdr != NULL)
3582 error (_("File contains multiple symtab shndx tables\n"));
3583 continue;
3585 symtab_shndx_hdr = section;
3587 else if ((do_debugging || do_debug_info || do_debug_abbrevs
3588 || do_debug_lines || do_debug_pubnames || do_debug_aranges
3589 || do_debug_frames || do_debug_macinfo || do_debug_str
3590 || do_debug_loc)
3591 && strncmp (name, ".debug_", 7) == 0)
3593 name += 7;
3595 if (do_debugging
3596 || (do_debug_info && (strcmp (name, "info") == 0))
3597 || (do_debug_abbrevs && (strcmp (name, "abbrev") == 0))
3598 || (do_debug_lines && (strcmp (name, "line") == 0))
3599 || (do_debug_pubnames && (strcmp (name, "pubnames") == 0))
3600 || (do_debug_aranges && (strcmp (name, "aranges") == 0))
3601 || (do_debug_frames && (strcmp (name, "frame") == 0))
3602 || (do_debug_macinfo && (strcmp (name, "macinfo") == 0))
3603 || (do_debug_str && (strcmp (name, "str") == 0))
3604 || (do_debug_loc && (strcmp (name, "loc") == 0))
3606 request_dump (i, DEBUG_DUMP);
3608 /* linkonce section to be combined with .debug_info at link time. */
3609 else if ((do_debugging || do_debug_info)
3610 && strncmp (name, ".gnu.linkonce.wi.", 17) == 0)
3611 request_dump (i, DEBUG_DUMP);
3612 else if (do_debug_frames && strcmp (name, ".eh_frame") == 0)
3613 request_dump (i, DEBUG_DUMP);
3616 if (! do_sections)
3617 return 1;
3619 if (elf_header.e_shnum > 1)
3620 printf (_("\nSection Headers:\n"));
3621 else
3622 printf (_("\nSection Header:\n"));
3624 if (is_32bit_elf)
3625 printf
3626 (_(" [Nr] Name Type Addr Off Size ES Flg Lk Inf Al\n"));
3627 else if (do_wide)
3628 printf
3629 (_(" [Nr] Name Type Address Off Size ES Flg Lk Inf Al\n"));
3630 else
3632 printf (_(" [Nr] Name Type Address Offset\n"));
3633 printf (_(" Size EntSize Flags Link Info Align\n"));
3636 for (i = 0, section = section_headers;
3637 i < elf_header.e_shnum;
3638 i++, section++)
3640 printf (" [%2u] %-17.17s %-15.15s ",
3641 SECTION_HEADER_NUM (i),
3642 SECTION_NAME (section),
3643 get_section_type_name (section->sh_type));
3645 if (is_32bit_elf)
3647 print_vma (section->sh_addr, LONG_HEX);
3649 printf ( " %6.6lx %6.6lx %2.2lx",
3650 (unsigned long) section->sh_offset,
3651 (unsigned long) section->sh_size,
3652 (unsigned long) section->sh_entsize);
3654 printf (" %3s ", get_elf_section_flags (section->sh_flags));
3656 printf ("%2ld %3lu %2ld\n",
3657 (unsigned long) section->sh_link,
3658 (unsigned long) section->sh_info,
3659 (unsigned long) section->sh_addralign);
3661 else if (do_wide)
3663 print_vma (section->sh_addr, LONG_HEX);
3665 if ((long) section->sh_offset == section->sh_offset)
3666 printf (" %6.6lx", (unsigned long) section->sh_offset);
3667 else
3669 putchar (' ');
3670 print_vma (section->sh_offset, LONG_HEX);
3673 if ((unsigned long) section->sh_size == section->sh_size)
3674 printf (" %6.6lx", (unsigned long) section->sh_size);
3675 else
3677 putchar (' ');
3678 print_vma (section->sh_size, LONG_HEX);
3681 if ((unsigned long) section->sh_entsize == section->sh_entsize)
3682 printf (" %2.2lx", (unsigned long) section->sh_entsize);
3683 else
3685 putchar (' ');
3686 print_vma (section->sh_entsize, LONG_HEX);
3689 printf (" %3s ", get_elf_section_flags (section->sh_flags));
3691 printf ("%2ld %3lu ",
3692 (unsigned long) section->sh_link,
3693 (unsigned long) section->sh_info);
3695 if ((unsigned long) section->sh_addralign == section->sh_addralign)
3696 printf ("%2ld\n", (unsigned long) section->sh_addralign);
3697 else
3699 print_vma (section->sh_addralign, DEC);
3700 putchar ('\n');
3703 else
3705 putchar (' ');
3706 print_vma (section->sh_addr, LONG_HEX);
3707 if ((long) section->sh_offset == section->sh_offset)
3708 printf (" %8.8lx", (unsigned long) section->sh_offset);
3709 else
3711 printf (" ");
3712 print_vma (section->sh_offset, LONG_HEX);
3714 printf ("\n ");
3715 print_vma (section->sh_size, LONG_HEX);
3716 printf (" ");
3717 print_vma (section->sh_entsize, LONG_HEX);
3719 printf (" %3s ", get_elf_section_flags (section->sh_flags));
3721 printf (" %2ld %3lu %ld\n",
3722 (unsigned long) section->sh_link,
3723 (unsigned long) section->sh_info,
3724 (unsigned long) section->sh_addralign);
3728 printf (_("Key to Flags:\n\
3729 W (write), A (alloc), X (execute), M (merge), S (strings)\n\
3730 I (info), L (link order), G (group), x (unknown)\n\
3731 O (extra OS processing required) o (OS specific), p (processor specific)\n"));
3733 return 1;
3736 static const char *
3737 get_group_flags (unsigned int flags)
3739 static char buff[32];
3740 switch (flags)
3742 case GRP_COMDAT:
3743 return "COMDAT";
3745 default:
3746 sprintf (buff, _("[<unknown>: 0x%x]"), flags);
3747 break;
3749 return buff;
3752 static int
3753 process_section_groups (FILE *file)
3755 Elf_Internal_Shdr *section;
3756 unsigned int i;
3757 struct group *group;
3759 if (elf_header.e_shnum == 0)
3761 if (do_section_groups)
3762 printf (_("\nThere are no section groups in this file.\n"));
3764 return 1;
3767 if (section_headers == NULL)
3769 error (_("Section headers are not available!\n"));
3770 abort ();
3773 section_headers_groups = calloc (elf_header.e_shnum,
3774 sizeof (struct group *));
3776 if (section_headers_groups == NULL)
3778 error (_("Out of memory\n"));
3779 return 0;
3782 /* Scan the sections for the group section. */
3783 for (i = 0, section = section_headers;
3784 i < elf_header.e_shnum;
3785 i++, section++)
3786 if (section->sh_type == SHT_GROUP)
3787 group_count++;
3789 section_groups = calloc (group_count, sizeof (struct group));
3791 if (section_groups == NULL)
3793 error (_("Out of memory\n"));
3794 return 0;
3797 for (i = 0, section = section_headers, group = section_groups;
3798 i < elf_header.e_shnum;
3799 i++, section++)
3801 if (section->sh_type == SHT_GROUP)
3803 char *name = SECTION_NAME (section);
3804 char *group_name, *strtab, *start, *indices;
3805 unsigned int entry, j, size;
3806 Elf_Internal_Sym *sym;
3807 Elf_Internal_Shdr *symtab_sec, *strtab_sec, *sec;
3808 Elf_Internal_Sym *symtab;
3810 /* Get the symbol table. */
3811 symtab_sec = SECTION_HEADER (section->sh_link);
3812 if (symtab_sec->sh_type != SHT_SYMTAB)
3814 error (_("Bad sh_link in group section `%s'\n"), name);
3815 continue;
3817 symtab = GET_ELF_SYMBOLS (file, symtab_sec);
3819 sym = symtab + section->sh_info;
3821 if (ELF_ST_TYPE (sym->st_info) == STT_SECTION)
3823 bfd_vma sec_index = SECTION_HEADER_INDEX (sym->st_shndx);
3824 if (sec_index == 0)
3826 error (_("Bad sh_info in group section `%s'\n"), name);
3827 continue;
3830 group_name = SECTION_NAME (section_headers + sec_index);
3831 strtab = NULL;
3833 else
3835 /* Get the string table. */
3836 strtab_sec = SECTION_HEADER (symtab_sec->sh_link);
3837 strtab = get_data (NULL, file, strtab_sec->sh_offset,
3838 strtab_sec->sh_size,
3839 _("string table"));
3841 group_name = strtab + sym->st_name;
3844 start = get_data (NULL, file, section->sh_offset,
3845 section->sh_size, _("section data"));
3847 indices = start;
3848 size = (section->sh_size / section->sh_entsize) - 1;
3849 entry = byte_get (indices, 4);
3850 indices += 4;
3852 if (do_section_groups)
3854 printf ("\n%s group section `%s' [%s] contains %u sections:\n",
3855 get_group_flags (entry), name, group_name, size);
3857 printf (_(" [Index] Name\n"));
3860 group->group_index = i;
3862 for (j = 0; j < size; j++)
3864 struct group_list *g;
3866 entry = byte_get (indices, 4);
3867 indices += 4;
3869 if (section_headers_groups [SECTION_HEADER_INDEX (entry)]
3870 != NULL)
3872 error (_("section [%5u] already in group section [%5u]\n"),
3873 entry, section_headers_groups [SECTION_HEADER_INDEX (entry)]->group_index);
3874 continue;
3877 section_headers_groups [SECTION_HEADER_INDEX (entry)]
3878 = group;
3880 if (do_section_groups)
3882 sec = SECTION_HEADER (entry);
3883 printf (" [%5u] %s\n",
3884 entry, SECTION_NAME (sec));
3887 g = xmalloc (sizeof (struct group_list));
3888 g->section_index = entry;
3889 g->next = group->root;
3890 group->root = g;
3893 if (strtab)
3894 free (strtab);
3895 if (start)
3896 free (start);
3898 group++;
3902 return 1;
3905 struct
3907 const char *name;
3908 int reloc;
3909 int size;
3910 int rela;
3911 } dynamic_relocations [] =
3913 { "REL", DT_REL, DT_RELSZ, FALSE },
3914 { "RELA", DT_RELA, DT_RELASZ, TRUE },
3915 { "PLT", DT_JMPREL, DT_PLTRELSZ, UNKNOWN }
3918 /* Process the reloc section. */
3919 static int
3920 process_relocs (FILE *file)
3922 unsigned long rel_size;
3923 unsigned long rel_offset;
3926 if (!do_reloc)
3927 return 1;
3929 if (do_using_dynamic)
3931 int is_rela;
3932 const char *name;
3933 int has_dynamic_reloc;
3934 unsigned int i;
3936 has_dynamic_reloc = 0;
3938 for (i = 0; i < ARRAY_SIZE (dynamic_relocations); i++)
3940 is_rela = dynamic_relocations [i].rela;
3941 name = dynamic_relocations [i].name;
3942 rel_size = dynamic_info [dynamic_relocations [i].size];
3943 rel_offset = dynamic_info [dynamic_relocations [i].reloc];
3945 has_dynamic_reloc |= rel_size;
3947 if (is_rela == UNKNOWN)
3949 if (dynamic_relocations [i].reloc == DT_JMPREL)
3950 switch (dynamic_info[DT_PLTREL])
3952 case DT_REL:
3953 is_rela = FALSE;
3954 break;
3955 case DT_RELA:
3956 is_rela = TRUE;
3957 break;
3961 if (rel_size)
3963 printf
3964 (_("\n'%s' relocation section at offset 0x%lx contains %ld bytes:\n"),
3965 name, rel_offset, rel_size);
3967 dump_relocations (file,
3968 offset_from_vma (file, rel_offset, rel_size),
3969 rel_size,
3970 dynamic_symbols, num_dynamic_syms,
3971 dynamic_strings, is_rela);
3975 if (! has_dynamic_reloc)
3976 printf (_("\nThere are no dynamic relocations in this file.\n"));
3978 else
3980 Elf_Internal_Shdr *section;
3981 unsigned long i;
3982 int found = 0;
3984 for (i = 0, section = section_headers;
3985 i < elf_header.e_shnum;
3986 i++, section++)
3988 if ( section->sh_type != SHT_RELA
3989 && section->sh_type != SHT_REL)
3990 continue;
3992 rel_offset = section->sh_offset;
3993 rel_size = section->sh_size;
3995 if (rel_size)
3997 Elf_Internal_Shdr *strsec;
3998 Elf_Internal_Sym *symtab;
3999 char *strtab;
4000 int is_rela;
4001 unsigned long nsyms;
4003 printf (_("\nRelocation section "));
4005 if (string_table == NULL)
4006 printf ("%d", section->sh_name);
4007 else
4008 printf (_("'%s'"), SECTION_NAME (section));
4010 printf (_(" at offset 0x%lx contains %lu entries:\n"),
4011 rel_offset, (unsigned long) (rel_size / section->sh_entsize));
4013 symtab = NULL;
4014 strtab = NULL;
4015 nsyms = 0;
4016 if (section->sh_link)
4018 Elf_Internal_Shdr *symsec;
4020 symsec = SECTION_HEADER (section->sh_link);
4021 nsyms = symsec->sh_size / symsec->sh_entsize;
4022 symtab = GET_ELF_SYMBOLS (file, symsec);
4024 if (symtab == NULL)
4025 continue;
4027 strsec = SECTION_HEADER (symsec->sh_link);
4029 strtab = get_data (NULL, file, strsec->sh_offset,
4030 strsec->sh_size, _("string table"));
4032 is_rela = section->sh_type == SHT_RELA;
4034 dump_relocations (file, rel_offset, rel_size,
4035 symtab, nsyms, strtab, is_rela);
4037 if (strtab)
4038 free (strtab);
4039 if (symtab)
4040 free (symtab);
4042 found = 1;
4046 if (! found)
4047 printf (_("\nThere are no relocations in this file.\n"));
4050 return 1;
4053 #include "unwind-ia64.h"
4055 /* An absolute address consists of a section and an offset. If the
4056 section is NULL, the offset itself is the address, otherwise, the
4057 address equals to LOAD_ADDRESS(section) + offset. */
4059 struct absaddr
4061 unsigned short section;
4062 bfd_vma offset;
4065 struct unw_aux_info
4067 struct unw_table_entry
4069 struct absaddr start;
4070 struct absaddr end;
4071 struct absaddr info;
4073 *table; /* Unwind table. */
4074 unsigned long table_len; /* Length of unwind table. */
4075 unsigned char *info; /* Unwind info. */
4076 unsigned long info_size; /* Size of unwind info. */
4077 bfd_vma info_addr; /* starting address of unwind info. */
4078 bfd_vma seg_base; /* Starting address of segment. */
4079 Elf_Internal_Sym *symtab; /* The symbol table. */
4080 unsigned long nsyms; /* Number of symbols. */
4081 char *strtab; /* The string table. */
4082 unsigned long strtab_size; /* Size of string table. */
4085 static void
4086 find_symbol_for_address (struct unw_aux_info *aux,
4087 struct absaddr addr,
4088 const char **symname,
4089 bfd_vma *offset)
4091 bfd_vma dist = 0x100000;
4092 Elf_Internal_Sym *sym, *best = NULL;
4093 unsigned long i;
4095 for (i = 0, sym = aux->symtab; i < aux->nsyms; ++i, ++sym)
4097 if (ELF_ST_TYPE (sym->st_info) == STT_FUNC
4098 && sym->st_name != 0
4099 && (addr.section == SHN_UNDEF || addr.section == sym->st_shndx)
4100 && addr.offset >= sym->st_value
4101 && addr.offset - sym->st_value < dist)
4103 best = sym;
4104 dist = addr.offset - sym->st_value;
4105 if (!dist)
4106 break;
4109 if (best)
4111 *symname = (best->st_name >= aux->strtab_size
4112 ? "<corrupt>" : aux->strtab + best->st_name);
4113 *offset = dist;
4114 return;
4116 *symname = NULL;
4117 *offset = addr.offset;
4120 static void
4121 dump_ia64_unwind (struct unw_aux_info *aux)
4123 bfd_vma addr_size;
4124 struct unw_table_entry *tp;
4125 int in_body;
4127 addr_size = is_32bit_elf ? 4 : 8;
4129 for (tp = aux->table; tp < aux->table + aux->table_len; ++tp)
4131 bfd_vma stamp;
4132 bfd_vma offset;
4133 const unsigned char *dp;
4134 const unsigned char *head;
4135 const char *procname;
4137 find_symbol_for_address (aux, tp->start, &procname, &offset);
4139 fputs ("\n<", stdout);
4141 if (procname)
4143 fputs (procname, stdout);
4145 if (offset)
4146 printf ("+%lx", (unsigned long) offset);
4149 fputs (">: [", stdout);
4150 print_vma (tp->start.offset, PREFIX_HEX);
4151 fputc ('-', stdout);
4152 print_vma (tp->end.offset, PREFIX_HEX);
4153 printf ("], info at +0x%lx\n",
4154 (unsigned long) (tp->info.offset - aux->seg_base));
4156 head = aux->info + (tp->info.offset - aux->info_addr);
4157 stamp = BYTE_GET8 ((unsigned char *) head);
4159 printf (" v%u, flags=0x%lx (%s%s), len=%lu bytes\n",
4160 (unsigned) UNW_VER (stamp),
4161 (unsigned long) ((stamp & UNW_FLAG_MASK) >> 32),
4162 UNW_FLAG_EHANDLER (stamp) ? " ehandler" : "",
4163 UNW_FLAG_UHANDLER (stamp) ? " uhandler" : "",
4164 (unsigned long) (addr_size * UNW_LENGTH (stamp)));
4166 if (UNW_VER (stamp) != 1)
4168 printf ("\tUnknown version.\n");
4169 continue;
4172 in_body = 0;
4173 for (dp = head + 8; dp < head + 8 + addr_size * UNW_LENGTH (stamp);)
4174 dp = unw_decode (dp, in_body, & in_body);
4178 static int
4179 slurp_ia64_unwind_table (FILE *file,
4180 struct unw_aux_info *aux,
4181 Elf_Internal_Shdr *sec)
4183 unsigned long size, addr_size, nrelas, i;
4184 Elf_Internal_Phdr *seg;
4185 struct unw_table_entry *tep;
4186 Elf_Internal_Shdr *relsec;
4187 Elf_Internal_Rela *rela, *rp;
4188 unsigned char *table, *tp;
4189 Elf_Internal_Sym *sym;
4190 const char *relname;
4192 addr_size = is_32bit_elf ? 4 : 8;
4194 /* First, find the starting address of the segment that includes
4195 this section: */
4197 if (elf_header.e_phnum)
4199 if (! get_program_headers (file))
4200 return 0;
4202 for (seg = program_headers;
4203 seg < program_headers + elf_header.e_phnum;
4204 ++seg)
4206 if (seg->p_type != PT_LOAD)
4207 continue;
4209 if (sec->sh_addr >= seg->p_vaddr
4210 && (sec->sh_addr + sec->sh_size <= seg->p_vaddr + seg->p_memsz))
4212 aux->seg_base = seg->p_vaddr;
4213 break;
4218 /* Second, build the unwind table from the contents of the unwind section: */
4219 size = sec->sh_size;
4220 table = get_data (NULL, file, sec->sh_offset, size, _("unwind table"));
4221 if (!table)
4222 return 0;
4224 tep = aux->table = xmalloc (size / (3 * addr_size) * sizeof (aux->table[0]));
4225 for (tp = table; tp < table + size; tp += 3 * addr_size, ++tep)
4227 tep->start.section = SHN_UNDEF;
4228 tep->end.section = SHN_UNDEF;
4229 tep->info.section = SHN_UNDEF;
4230 if (is_32bit_elf)
4232 tep->start.offset = byte_get ((unsigned char *) tp + 0, 4);
4233 tep->end.offset = byte_get ((unsigned char *) tp + 4, 4);
4234 tep->info.offset = byte_get ((unsigned char *) tp + 8, 4);
4236 else
4238 tep->start.offset = BYTE_GET8 ((unsigned char *) tp + 0);
4239 tep->end.offset = BYTE_GET8 ((unsigned char *) tp + 8);
4240 tep->info.offset = BYTE_GET8 ((unsigned char *) tp + 16);
4242 tep->start.offset += aux->seg_base;
4243 tep->end.offset += aux->seg_base;
4244 tep->info.offset += aux->seg_base;
4246 free (table);
4248 /* Third, apply any relocations to the unwind table: */
4250 for (relsec = section_headers;
4251 relsec < section_headers + elf_header.e_shnum;
4252 ++relsec)
4254 if (relsec->sh_type != SHT_RELA
4255 || SECTION_HEADER (relsec->sh_info) != sec)
4256 continue;
4258 if (!slurp_rela_relocs (file, relsec->sh_offset, relsec->sh_size,
4259 & rela, & nrelas))
4260 return 0;
4262 for (rp = rela; rp < rela + nrelas; ++rp)
4264 if (is_32bit_elf)
4266 relname = elf_ia64_reloc_type (ELF32_R_TYPE (rp->r_info));
4267 sym = aux->symtab + ELF32_R_SYM (rp->r_info);
4269 if (ELF32_ST_TYPE (sym->st_info) != STT_SECTION)
4271 warn (_("Skipping unexpected symbol type %u\n"),
4272 ELF32_ST_TYPE (sym->st_info));
4273 continue;
4276 else
4278 relname = elf_ia64_reloc_type (ELF64_R_TYPE (rp->r_info));
4279 sym = aux->symtab + ELF64_R_SYM (rp->r_info);
4281 if (ELF64_ST_TYPE (sym->st_info) != STT_SECTION)
4283 warn (_("Skipping unexpected symbol type %u\n"),
4284 ELF64_ST_TYPE (sym->st_info));
4285 continue;
4289 if (strncmp (relname, "R_IA64_SEGREL", 13) != 0)
4291 warn (_("Skipping unexpected relocation type %s\n"), relname);
4292 continue;
4295 i = rp->r_offset / (3 * addr_size);
4297 switch (rp->r_offset/addr_size % 3)
4299 case 0:
4300 aux->table[i].start.section = sym->st_shndx;
4301 aux->table[i].start.offset += rp->r_addend;
4302 break;
4303 case 1:
4304 aux->table[i].end.section = sym->st_shndx;
4305 aux->table[i].end.offset += rp->r_addend;
4306 break;
4307 case 2:
4308 aux->table[i].info.section = sym->st_shndx;
4309 aux->table[i].info.offset += rp->r_addend;
4310 break;
4311 default:
4312 break;
4316 free (rela);
4319 aux->table_len = size / (3 * addr_size);
4320 return 1;
4323 static int
4324 process_unwind (FILE *file)
4326 Elf_Internal_Shdr *sec, *unwsec = NULL, *strsec;
4327 unsigned long i, addr_size, unwcount = 0, unwstart = 0;
4328 struct unw_aux_info aux;
4330 if (!do_unwind)
4331 return 1;
4333 if (elf_header.e_machine != EM_IA_64)
4335 printf (_("\nThere are no unwind sections in this file.\n"));
4336 return 1;
4339 memset (& aux, 0, sizeof (aux));
4341 addr_size = is_32bit_elf ? 4 : 8;
4343 for (i = 0, sec = section_headers; i < elf_header.e_shnum; ++i, ++sec)
4345 if (sec->sh_type == SHT_SYMTAB)
4347 aux.nsyms = sec->sh_size / sec->sh_entsize;
4348 aux.symtab = GET_ELF_SYMBOLS (file, sec);
4350 strsec = SECTION_HEADER (sec->sh_link);
4351 aux.strtab_size = strsec->sh_size;
4352 aux.strtab = get_data (NULL, file, strsec->sh_offset,
4353 aux.strtab_size, _("string table"));
4355 else if (sec->sh_type == SHT_IA_64_UNWIND)
4356 unwcount++;
4359 if (!unwcount)
4360 printf (_("\nThere are no unwind sections in this file.\n"));
4362 while (unwcount-- > 0)
4364 char *suffix;
4365 size_t len, len2;
4367 for (i = unwstart, sec = section_headers + unwstart;
4368 i < elf_header.e_shnum; ++i, ++sec)
4369 if (sec->sh_type == SHT_IA_64_UNWIND)
4371 unwsec = sec;
4372 break;
4375 unwstart = i + 1;
4376 len = sizeof (ELF_STRING_ia64_unwind_once) - 1;
4378 if ((unwsec->sh_flags & SHF_GROUP) != 0)
4380 /* We need to find which section group it is in. */
4381 struct group_list *g = section_headers_groups [i]->root;
4383 for (; g != NULL; g = g->next)
4385 sec = SECTION_HEADER (g->section_index);
4386 if (strcmp (SECTION_NAME (sec),
4387 ELF_STRING_ia64_unwind_info) == 0)
4388 break;
4391 if (g == NULL)
4392 i = elf_header.e_shnum;
4394 else if (strncmp (SECTION_NAME (unwsec),
4395 ELF_STRING_ia64_unwind_once, len) == 0)
4397 /* .gnu.linkonce.ia64unw.FOO -> .gnu.linkonce.ia64unwi.FOO */
4398 len2 = sizeof (ELF_STRING_ia64_unwind_info_once) - 1;
4399 suffix = SECTION_NAME (unwsec) + len;
4400 for (i = 0, sec = section_headers; i < elf_header.e_shnum;
4401 ++i, ++sec)
4402 if (strncmp (SECTION_NAME (sec),
4403 ELF_STRING_ia64_unwind_info_once, len2) == 0
4404 && strcmp (SECTION_NAME (sec) + len2, suffix) == 0)
4405 break;
4407 else
4409 /* .IA_64.unwindFOO -> .IA_64.unwind_infoFOO
4410 .IA_64.unwind or BAR -> .IA_64.unwind_info */
4411 len = sizeof (ELF_STRING_ia64_unwind) - 1;
4412 len2 = sizeof (ELF_STRING_ia64_unwind_info) - 1;
4413 suffix = "";
4414 if (strncmp (SECTION_NAME (unwsec), ELF_STRING_ia64_unwind,
4415 len) == 0)
4416 suffix = SECTION_NAME (unwsec) + len;
4417 for (i = 0, sec = section_headers; i < elf_header.e_shnum;
4418 ++i, ++sec)
4419 if (strncmp (SECTION_NAME (sec),
4420 ELF_STRING_ia64_unwind_info, len2) == 0
4421 && strcmp (SECTION_NAME (sec) + len2, suffix) == 0)
4422 break;
4425 if (i == elf_header.e_shnum)
4427 printf (_("\nCould not find unwind info section for "));
4429 if (string_table == NULL)
4430 printf ("%d", unwsec->sh_name);
4431 else
4432 printf (_("'%s'"), SECTION_NAME (unwsec));
4434 else
4436 aux.info_size = sec->sh_size;
4437 aux.info_addr = sec->sh_addr;
4438 aux.info = get_data (NULL, file, sec->sh_offset, aux.info_size,
4439 _("unwind info"));
4441 printf (_("\nUnwind section "));
4443 if (string_table == NULL)
4444 printf ("%d", unwsec->sh_name);
4445 else
4446 printf (_("'%s'"), SECTION_NAME (unwsec));
4448 printf (_(" at offset 0x%lx contains %lu entries:\n"),
4449 (unsigned long) unwsec->sh_offset,
4450 (unsigned long) (unwsec->sh_size / (3 * addr_size)));
4452 (void) slurp_ia64_unwind_table (file, & aux, unwsec);
4454 if (aux.table_len > 0)
4455 dump_ia64_unwind (& aux);
4457 if (aux.table)
4458 free ((char *) aux.table);
4459 if (aux.info)
4460 free ((char *) aux.info);
4461 aux.table = NULL;
4462 aux.info = NULL;
4466 if (aux.symtab)
4467 free (aux.symtab);
4468 if (aux.strtab)
4469 free ((char *) aux.strtab);
4471 return 1;
4474 static void
4475 dynamic_segment_mips_val (Elf_Internal_Dyn *entry)
4477 switch (entry->d_tag)
4479 case DT_MIPS_FLAGS:
4480 if (entry->d_un.d_val == 0)
4481 printf ("NONE\n");
4482 else
4484 static const char * opts[] =
4486 "QUICKSTART", "NOTPOT", "NO_LIBRARY_REPLACEMENT",
4487 "NO_MOVE", "SGI_ONLY", "GUARANTEE_INIT", "DELTA_C_PLUS_PLUS",
4488 "GUARANTEE_START_INIT", "PIXIE", "DEFAULT_DELAY_LOAD",
4489 "REQUICKSTART", "REQUICKSTARTED", "CORD", "NO_UNRES_UNDEF",
4490 "RLD_ORDER_SAFE"
4492 unsigned int cnt;
4493 int first = 1;
4494 for (cnt = 0; cnt < NUM_ELEM (opts); ++cnt)
4495 if (entry->d_un.d_val & (1 << cnt))
4497 printf ("%s%s", first ? "" : " ", opts[cnt]);
4498 first = 0;
4500 puts ("");
4502 break;
4504 case DT_MIPS_IVERSION:
4505 if (dynamic_strings != NULL)
4506 printf ("Interface Version: %s\n",
4507 dynamic_strings + entry->d_un.d_val);
4508 else
4509 printf ("%ld\n", (long) entry->d_un.d_ptr);
4510 break;
4512 case DT_MIPS_TIME_STAMP:
4514 char timebuf[20];
4515 struct tm *tmp;
4517 time_t time = entry->d_un.d_val;
4518 tmp = gmtime (&time);
4519 sprintf (timebuf, "%04u-%02u-%02uT%02u:%02u:%02u",
4520 tmp->tm_year + 1900, tmp->tm_mon + 1, tmp->tm_mday,
4521 tmp->tm_hour, tmp->tm_min, tmp->tm_sec);
4522 printf ("Time Stamp: %s\n", timebuf);
4524 break;
4526 case DT_MIPS_RLD_VERSION:
4527 case DT_MIPS_LOCAL_GOTNO:
4528 case DT_MIPS_CONFLICTNO:
4529 case DT_MIPS_LIBLISTNO:
4530 case DT_MIPS_SYMTABNO:
4531 case DT_MIPS_UNREFEXTNO:
4532 case DT_MIPS_HIPAGENO:
4533 case DT_MIPS_DELTA_CLASS_NO:
4534 case DT_MIPS_DELTA_INSTANCE_NO:
4535 case DT_MIPS_DELTA_RELOC_NO:
4536 case DT_MIPS_DELTA_SYM_NO:
4537 case DT_MIPS_DELTA_CLASSSYM_NO:
4538 case DT_MIPS_COMPACT_SIZE:
4539 printf ("%ld\n", (long) entry->d_un.d_ptr);
4540 break;
4542 default:
4543 printf ("%#lx\n", (long) entry->d_un.d_ptr);
4548 static void
4549 dynamic_segment_parisc_val (Elf_Internal_Dyn *entry)
4551 switch (entry->d_tag)
4553 case DT_HP_DLD_FLAGS:
4555 static struct
4557 long int bit;
4558 const char *str;
4560 flags[] =
4562 { DT_HP_DEBUG_PRIVATE, "HP_DEBUG_PRIVATE" },
4563 { DT_HP_DEBUG_CALLBACK, "HP_DEBUG_CALLBACK" },
4564 { DT_HP_DEBUG_CALLBACK_BOR, "HP_DEBUG_CALLBACK_BOR" },
4565 { DT_HP_NO_ENVVAR, "HP_NO_ENVVAR" },
4566 { DT_HP_BIND_NOW, "HP_BIND_NOW" },
4567 { DT_HP_BIND_NONFATAL, "HP_BIND_NONFATAL" },
4568 { DT_HP_BIND_VERBOSE, "HP_BIND_VERBOSE" },
4569 { DT_HP_BIND_RESTRICTED, "HP_BIND_RESTRICTED" },
4570 { DT_HP_BIND_SYMBOLIC, "HP_BIND_SYMBOLIC" },
4571 { DT_HP_RPATH_FIRST, "HP_RPATH_FIRST" },
4572 { DT_HP_BIND_DEPTH_FIRST, "HP_BIND_DEPTH_FIRST" }
4574 int first = 1;
4575 size_t cnt;
4576 bfd_vma val = entry->d_un.d_val;
4578 for (cnt = 0; cnt < sizeof (flags) / sizeof (flags[0]); ++cnt)
4579 if (val & flags[cnt].bit)
4581 if (! first)
4582 putchar (' ');
4583 fputs (flags[cnt].str, stdout);
4584 first = 0;
4585 val ^= flags[cnt].bit;
4588 if (val != 0 || first)
4590 if (! first)
4591 putchar (' ');
4592 print_vma (val, HEX);
4595 break;
4597 default:
4598 print_vma (entry->d_un.d_ptr, PREFIX_HEX);
4599 break;
4601 putchar ('\n');
4604 static void
4605 dynamic_segment_ia64_val (Elf_Internal_Dyn *entry)
4607 switch (entry->d_tag)
4609 case DT_IA_64_PLT_RESERVE:
4610 /* First 3 slots reserved. */
4611 print_vma (entry->d_un.d_ptr, PREFIX_HEX);
4612 printf (" -- ");
4613 print_vma (entry->d_un.d_ptr + (3 * 8), PREFIX_HEX);
4614 break;
4616 default:
4617 print_vma (entry->d_un.d_ptr, PREFIX_HEX);
4618 break;
4620 putchar ('\n');
4623 static int
4624 get_32bit_dynamic_segment (FILE *file)
4626 Elf32_External_Dyn *edyn;
4627 Elf_Internal_Dyn *entry;
4628 bfd_size_type i;
4630 edyn = get_data (NULL, file, dynamic_addr, dynamic_size,
4631 _("dynamic segment"));
4632 if (!edyn)
4633 return 0;
4635 /* SGI's ELF has more than one section in the DYNAMIC segment. Determine
4636 how large this .dynamic is now. We can do this even before the byte
4637 swapping since the DT_NULL tag is recognizable. */
4638 dynamic_size = 0;
4639 while (*(Elf32_Word *) edyn[dynamic_size++].d_tag != DT_NULL)
4642 dynamic_segment = malloc (dynamic_size * sizeof (Elf_Internal_Dyn));
4644 if (dynamic_segment == NULL)
4646 error (_("Out of memory\n"));
4647 free (edyn);
4648 return 0;
4651 for (i = 0, entry = dynamic_segment;
4652 i < dynamic_size;
4653 i++, entry++)
4655 entry->d_tag = BYTE_GET (edyn[i].d_tag);
4656 entry->d_un.d_val = BYTE_GET (edyn[i].d_un.d_val);
4659 free (edyn);
4661 return 1;
4664 static int
4665 get_64bit_dynamic_segment (FILE *file)
4667 Elf64_External_Dyn *edyn;
4668 Elf_Internal_Dyn *entry;
4669 bfd_size_type i;
4671 edyn = get_data (NULL, file, dynamic_addr, dynamic_size,
4672 _("dynamic segment"));
4673 if (!edyn)
4674 return 0;
4676 /* SGI's ELF has more than one section in the DYNAMIC segment. Determine
4677 how large this .dynamic is now. We can do this even before the byte
4678 swapping since the DT_NULL tag is recognizable. */
4679 dynamic_size = 0;
4680 while (*(bfd_vma *) edyn[dynamic_size++].d_tag != DT_NULL)
4683 dynamic_segment = malloc (dynamic_size * sizeof (Elf_Internal_Dyn));
4685 if (dynamic_segment == NULL)
4687 error (_("Out of memory\n"));
4688 free (edyn);
4689 return 0;
4692 for (i = 0, entry = dynamic_segment;
4693 i < dynamic_size;
4694 i++, entry++)
4696 entry->d_tag = BYTE_GET8 (edyn[i].d_tag);
4697 entry->d_un.d_val = BYTE_GET8 (edyn[i].d_un.d_val);
4700 free (edyn);
4702 return 1;
4705 static const char *
4706 get_dynamic_flags (bfd_vma flags)
4708 static char buff[128];
4709 char *p = buff;
4711 *p = '\0';
4712 while (flags)
4714 bfd_vma flag;
4716 flag = flags & - flags;
4717 flags &= ~ flag;
4719 if (p != buff)
4720 *p++ = ' ';
4722 switch (flag)
4724 case DF_ORIGIN: strcpy (p, "ORIGIN"); break;
4725 case DF_SYMBOLIC: strcpy (p, "SYMBOLIC"); break;
4726 case DF_TEXTREL: strcpy (p, "TEXTREL"); break;
4727 case DF_BIND_NOW: strcpy (p, "BIND_NOW"); break;
4728 case DF_STATIC_TLS: strcpy (p, "STATIC_TLS"); break;
4729 default: strcpy (p, "unknown"); break;
4732 p = strchr (p, '\0');
4734 return buff;
4737 /* Parse and display the contents of the dynamic segment. */
4738 static int
4739 process_dynamic_segment (FILE *file)
4741 Elf_Internal_Dyn *entry;
4742 bfd_size_type i;
4744 if (dynamic_size == 0)
4746 if (do_dynamic)
4747 printf (_("\nThere is no dynamic segment in this file.\n"));
4749 return 1;
4752 if (is_32bit_elf)
4754 if (! get_32bit_dynamic_segment (file))
4755 return 0;
4757 else if (! get_64bit_dynamic_segment (file))
4758 return 0;
4760 /* Find the appropriate symbol table. */
4761 if (dynamic_symbols == NULL)
4763 for (i = 0, entry = dynamic_segment;
4764 i < dynamic_size;
4765 ++i, ++entry)
4767 Elf_Internal_Shdr section;
4769 if (entry->d_tag != DT_SYMTAB)
4770 continue;
4772 dynamic_info[DT_SYMTAB] = entry->d_un.d_val;
4774 /* Since we do not know how big the symbol table is,
4775 we default to reading in the entire file (!) and
4776 processing that. This is overkill, I know, but it
4777 should work. */
4778 section.sh_offset = offset_from_vma (file, entry->d_un.d_val, 0);
4780 if (archive_file_offset != 0)
4781 section.sh_size = archive_file_size - section.sh_offset;
4782 else
4784 if (fseek (file, 0, SEEK_END))
4785 error (_("Unable to seek to end of file!"));
4787 section.sh_size = ftell (file) - section.sh_offset;
4790 if (is_32bit_elf)
4791 section.sh_entsize = sizeof (Elf32_External_Sym);
4792 else
4793 section.sh_entsize = sizeof (Elf64_External_Sym);
4795 num_dynamic_syms = section.sh_size / section.sh_entsize;
4796 if (num_dynamic_syms < 1)
4798 error (_("Unable to determine the number of symbols to load\n"));
4799 continue;
4802 dynamic_symbols = GET_ELF_SYMBOLS (file, &section);
4806 /* Similarly find a string table. */
4807 if (dynamic_strings == NULL)
4809 for (i = 0, entry = dynamic_segment;
4810 i < dynamic_size;
4811 ++i, ++entry)
4813 unsigned long offset;
4814 long str_tab_len;
4816 if (entry->d_tag != DT_STRTAB)
4817 continue;
4819 dynamic_info[DT_STRTAB] = entry->d_un.d_val;
4821 /* Since we do not know how big the string table is,
4822 we default to reading in the entire file (!) and
4823 processing that. This is overkill, I know, but it
4824 should work. */
4826 offset = offset_from_vma (file, entry->d_un.d_val, 0);
4828 if (archive_file_offset != 0)
4829 str_tab_len = archive_file_size - offset;
4830 else
4832 if (fseek (file, 0, SEEK_END))
4833 error (_("Unable to seek to end of file\n"));
4834 str_tab_len = ftell (file) - offset;
4837 if (str_tab_len < 1)
4839 error
4840 (_("Unable to determine the length of the dynamic string table\n"));
4841 continue;
4844 dynamic_strings = get_data (NULL, file, offset, str_tab_len,
4845 _("dynamic string table"));
4846 break;
4850 /* And find the syminfo section if available. */
4851 if (dynamic_syminfo == NULL)
4853 unsigned long syminsz = 0;
4855 for (i = 0, entry = dynamic_segment;
4856 i < dynamic_size;
4857 ++i, ++entry)
4859 if (entry->d_tag == DT_SYMINENT)
4861 /* Note: these braces are necessary to avoid a syntax
4862 error from the SunOS4 C compiler. */
4863 assert (sizeof (Elf_External_Syminfo) == entry->d_un.d_val);
4865 else if (entry->d_tag == DT_SYMINSZ)
4866 syminsz = entry->d_un.d_val;
4867 else if (entry->d_tag == DT_SYMINFO)
4868 dynamic_syminfo_offset = offset_from_vma (file, entry->d_un.d_val,
4869 syminsz);
4872 if (dynamic_syminfo_offset != 0 && syminsz != 0)
4874 Elf_External_Syminfo *extsyminfo;
4875 Elf_Internal_Syminfo *syminfo;
4877 /* There is a syminfo section. Read the data. */
4878 extsyminfo = get_data (NULL, file, dynamic_syminfo_offset, syminsz,
4879 _("symbol information"));
4880 if (!extsyminfo)
4881 return 0;
4883 dynamic_syminfo = malloc (syminsz);
4884 if (dynamic_syminfo == NULL)
4886 error (_("Out of memory\n"));
4887 return 0;
4890 dynamic_syminfo_nent = syminsz / sizeof (Elf_External_Syminfo);
4891 for (i = 0, syminfo = dynamic_syminfo; i < dynamic_syminfo_nent;
4892 ++i, ++syminfo)
4894 syminfo->si_boundto = BYTE_GET (extsyminfo[i].si_boundto);
4895 syminfo->si_flags = BYTE_GET (extsyminfo[i].si_flags);
4898 free (extsyminfo);
4902 if (do_dynamic && dynamic_addr)
4903 printf (_("\nDynamic segment at offset 0x%lx contains %ld entries:\n"),
4904 dynamic_addr, (long) dynamic_size);
4905 if (do_dynamic)
4906 printf (_(" Tag Type Name/Value\n"));
4908 for (i = 0, entry = dynamic_segment;
4909 i < dynamic_size;
4910 i++, entry++)
4912 if (do_dynamic)
4914 const char *dtype;
4916 putchar (' ');
4917 print_vma (entry->d_tag, FULL_HEX);
4918 dtype = get_dynamic_type (entry->d_tag);
4919 printf (" (%s)%*s", dtype,
4920 ((is_32bit_elf ? 27 : 19)
4921 - (int) strlen (dtype)),
4922 " ");
4925 switch (entry->d_tag)
4927 case DT_FLAGS:
4928 if (do_dynamic)
4929 puts (get_dynamic_flags (entry->d_un.d_val));
4930 break;
4932 case DT_AUXILIARY:
4933 case DT_FILTER:
4934 case DT_CONFIG:
4935 case DT_DEPAUDIT:
4936 case DT_AUDIT:
4937 if (do_dynamic)
4939 switch (entry->d_tag)
4941 case DT_AUXILIARY:
4942 printf (_("Auxiliary library"));
4943 break;
4945 case DT_FILTER:
4946 printf (_("Filter library"));
4947 break;
4949 case DT_CONFIG:
4950 printf (_("Configuration file"));
4951 break;
4953 case DT_DEPAUDIT:
4954 printf (_("Dependency audit library"));
4955 break;
4957 case DT_AUDIT:
4958 printf (_("Audit library"));
4959 break;
4962 if (dynamic_strings)
4963 printf (": [%s]\n", dynamic_strings + entry->d_un.d_val);
4964 else
4966 printf (": ");
4967 print_vma (entry->d_un.d_val, PREFIX_HEX);
4968 putchar ('\n');
4971 break;
4973 case DT_FEATURE:
4974 if (do_dynamic)
4976 printf (_("Flags:"));
4978 if (entry->d_un.d_val == 0)
4979 printf (_(" None\n"));
4980 else
4982 unsigned long int val = entry->d_un.d_val;
4984 if (val & DTF_1_PARINIT)
4986 printf (" PARINIT");
4987 val ^= DTF_1_PARINIT;
4989 if (val & DTF_1_CONFEXP)
4991 printf (" CONFEXP");
4992 val ^= DTF_1_CONFEXP;
4994 if (val != 0)
4995 printf (" %lx", val);
4996 puts ("");
4999 break;
5001 case DT_POSFLAG_1:
5002 if (do_dynamic)
5004 printf (_("Flags:"));
5006 if (entry->d_un.d_val == 0)
5007 printf (_(" None\n"));
5008 else
5010 unsigned long int val = entry->d_un.d_val;
5012 if (val & DF_P1_LAZYLOAD)
5014 printf (" LAZYLOAD");
5015 val ^= DF_P1_LAZYLOAD;
5017 if (val & DF_P1_GROUPPERM)
5019 printf (" GROUPPERM");
5020 val ^= DF_P1_GROUPPERM;
5022 if (val != 0)
5023 printf (" %lx", val);
5024 puts ("");
5027 break;
5029 case DT_FLAGS_1:
5030 if (do_dynamic)
5032 printf (_("Flags:"));
5033 if (entry->d_un.d_val == 0)
5034 printf (_(" None\n"));
5035 else
5037 unsigned long int val = entry->d_un.d_val;
5039 if (val & DF_1_NOW)
5041 printf (" NOW");
5042 val ^= DF_1_NOW;
5044 if (val & DF_1_GLOBAL)
5046 printf (" GLOBAL");
5047 val ^= DF_1_GLOBAL;
5049 if (val & DF_1_GROUP)
5051 printf (" GROUP");
5052 val ^= DF_1_GROUP;
5054 if (val & DF_1_NODELETE)
5056 printf (" NODELETE");
5057 val ^= DF_1_NODELETE;
5059 if (val & DF_1_LOADFLTR)
5061 printf (" LOADFLTR");
5062 val ^= DF_1_LOADFLTR;
5064 if (val & DF_1_INITFIRST)
5066 printf (" INITFIRST");
5067 val ^= DF_1_INITFIRST;
5069 if (val & DF_1_NOOPEN)
5071 printf (" NOOPEN");
5072 val ^= DF_1_NOOPEN;
5074 if (val & DF_1_ORIGIN)
5076 printf (" ORIGIN");
5077 val ^= DF_1_ORIGIN;
5079 if (val & DF_1_DIRECT)
5081 printf (" DIRECT");
5082 val ^= DF_1_DIRECT;
5084 if (val & DF_1_TRANS)
5086 printf (" TRANS");
5087 val ^= DF_1_TRANS;
5089 if (val & DF_1_INTERPOSE)
5091 printf (" INTERPOSE");
5092 val ^= DF_1_INTERPOSE;
5094 if (val & DF_1_NODEFLIB)
5096 printf (" NODEFLIB");
5097 val ^= DF_1_NODEFLIB;
5099 if (val & DF_1_NODUMP)
5101 printf (" NODUMP");
5102 val ^= DF_1_NODUMP;
5104 if (val & DF_1_CONLFAT)
5106 printf (" CONLFAT");
5107 val ^= DF_1_CONLFAT;
5109 if (val != 0)
5110 printf (" %lx", val);
5111 puts ("");
5114 break;
5116 case DT_PLTREL:
5117 dynamic_info[entry->d_tag] = entry->d_un.d_val;
5118 if (do_dynamic)
5119 puts (get_dynamic_type (entry->d_un.d_val));
5120 break;
5122 case DT_NULL :
5123 case DT_NEEDED :
5124 case DT_PLTGOT :
5125 case DT_HASH :
5126 case DT_STRTAB :
5127 case DT_SYMTAB :
5128 case DT_RELA :
5129 case DT_INIT :
5130 case DT_FINI :
5131 case DT_SONAME :
5132 case DT_RPATH :
5133 case DT_SYMBOLIC:
5134 case DT_REL :
5135 case DT_DEBUG :
5136 case DT_TEXTREL :
5137 case DT_JMPREL :
5138 case DT_RUNPATH :
5139 dynamic_info[entry->d_tag] = entry->d_un.d_val;
5141 if (do_dynamic)
5143 char *name;
5145 if (dynamic_strings == NULL)
5146 name = NULL;
5147 else
5148 name = dynamic_strings + entry->d_un.d_val;
5150 if (name)
5152 switch (entry->d_tag)
5154 case DT_NEEDED:
5155 printf (_("Shared library: [%s]"), name);
5157 if (strcmp (name, program_interpreter) == 0)
5158 printf (_(" program interpreter"));
5159 break;
5161 case DT_SONAME:
5162 printf (_("Library soname: [%s]"), name);
5163 break;
5165 case DT_RPATH:
5166 printf (_("Library rpath: [%s]"), name);
5167 break;
5169 case DT_RUNPATH:
5170 printf (_("Library runpath: [%s]"), name);
5171 break;
5173 default:
5174 print_vma (entry->d_un.d_val, PREFIX_HEX);
5175 break;
5178 else
5179 print_vma (entry->d_un.d_val, PREFIX_HEX);
5181 putchar ('\n');
5183 break;
5185 case DT_PLTRELSZ:
5186 case DT_RELASZ :
5187 case DT_STRSZ :
5188 case DT_RELSZ :
5189 case DT_RELAENT :
5190 case DT_SYMENT :
5191 case DT_RELENT :
5192 dynamic_info[entry->d_tag] = entry->d_un.d_val;
5193 case DT_PLTPADSZ:
5194 case DT_MOVEENT :
5195 case DT_MOVESZ :
5196 case DT_INIT_ARRAYSZ:
5197 case DT_FINI_ARRAYSZ:
5198 case DT_GNU_CONFLICTSZ:
5199 case DT_GNU_LIBLISTSZ:
5200 if (do_dynamic)
5202 print_vma (entry->d_un.d_val, UNSIGNED);
5203 printf (" (bytes)\n");
5205 break;
5207 case DT_VERDEFNUM:
5208 case DT_VERNEEDNUM:
5209 case DT_RELACOUNT:
5210 case DT_RELCOUNT:
5211 if (do_dynamic)
5213 print_vma (entry->d_un.d_val, UNSIGNED);
5214 putchar ('\n');
5216 break;
5218 case DT_SYMINSZ:
5219 case DT_SYMINENT:
5220 case DT_SYMINFO:
5221 case DT_USED:
5222 case DT_INIT_ARRAY:
5223 case DT_FINI_ARRAY:
5224 if (do_dynamic)
5226 if (dynamic_strings != NULL && entry->d_tag == DT_USED)
5228 char *name;
5230 name = dynamic_strings + entry->d_un.d_val;
5232 if (*name)
5234 printf (_("Not needed object: [%s]\n"), name);
5235 break;
5239 print_vma (entry->d_un.d_val, PREFIX_HEX);
5240 putchar ('\n');
5242 break;
5244 case DT_BIND_NOW:
5245 /* The value of this entry is ignored. */
5246 if (do_dynamic)
5247 putchar ('\n');
5248 break;
5250 case DT_GNU_PRELINKED:
5251 if (do_dynamic)
5253 struct tm *tmp;
5254 time_t time = entry->d_un.d_val;
5256 tmp = gmtime (&time);
5257 printf ("%04u-%02u-%02uT%02u:%02u:%02u\n",
5258 tmp->tm_year + 1900, tmp->tm_mon + 1, tmp->tm_mday,
5259 tmp->tm_hour, tmp->tm_min, tmp->tm_sec);
5262 break;
5264 default:
5265 if ((entry->d_tag >= DT_VERSYM) && (entry->d_tag <= DT_VERNEEDNUM))
5266 version_info[DT_VERSIONTAGIDX (entry->d_tag)] =
5267 entry->d_un.d_val;
5269 if (do_dynamic)
5271 switch (elf_header.e_machine)
5273 case EM_MIPS:
5274 case EM_MIPS_RS3_LE:
5275 dynamic_segment_mips_val (entry);
5276 break;
5277 case EM_PARISC:
5278 dynamic_segment_parisc_val (entry);
5279 break;
5280 case EM_IA_64:
5281 dynamic_segment_ia64_val (entry);
5282 break;
5283 default:
5284 print_vma (entry->d_un.d_val, PREFIX_HEX);
5285 putchar ('\n');
5288 break;
5292 return 1;
5295 static char *
5296 get_ver_flags (unsigned int flags)
5298 static char buff[32];
5300 buff[0] = 0;
5302 if (flags == 0)
5303 return _("none");
5305 if (flags & VER_FLG_BASE)
5306 strcat (buff, "BASE ");
5308 if (flags & VER_FLG_WEAK)
5310 if (flags & VER_FLG_BASE)
5311 strcat (buff, "| ");
5313 strcat (buff, "WEAK ");
5316 if (flags & ~(VER_FLG_BASE | VER_FLG_WEAK))
5317 strcat (buff, "| <unknown>");
5319 return buff;
5322 /* Display the contents of the version sections. */
5323 static int
5324 process_version_sections (FILE *file)
5326 Elf_Internal_Shdr *section;
5327 unsigned i;
5328 int found = 0;
5330 if (! do_version)
5331 return 1;
5333 for (i = 0, section = section_headers;
5334 i < elf_header.e_shnum;
5335 i++, section++)
5337 switch (section->sh_type)
5339 case SHT_GNU_verdef:
5341 Elf_External_Verdef *edefs;
5342 unsigned int idx;
5343 unsigned int cnt;
5345 found = 1;
5347 printf
5348 (_("\nVersion definition section '%s' contains %ld entries:\n"),
5349 SECTION_NAME (section), section->sh_info);
5351 printf (_(" Addr: 0x"));
5352 printf_vma (section->sh_addr);
5353 printf (_(" Offset: %#08lx Link: %lx (%s)\n"),
5354 (unsigned long) section->sh_offset, section->sh_link,
5355 SECTION_NAME (SECTION_HEADER (section->sh_link)));
5357 edefs = get_data (NULL, file, section->sh_offset, section->sh_size,
5358 _("version definition section"));
5359 if (!edefs)
5360 break;
5362 for (idx = cnt = 0; cnt < section->sh_info; ++cnt)
5364 char *vstart;
5365 Elf_External_Verdef *edef;
5366 Elf_Internal_Verdef ent;
5367 Elf_External_Verdaux *eaux;
5368 Elf_Internal_Verdaux aux;
5369 int j;
5370 int isum;
5372 vstart = ((char *) edefs) + idx;
5374 edef = (Elf_External_Verdef *) vstart;
5376 ent.vd_version = BYTE_GET (edef->vd_version);
5377 ent.vd_flags = BYTE_GET (edef->vd_flags);
5378 ent.vd_ndx = BYTE_GET (edef->vd_ndx);
5379 ent.vd_cnt = BYTE_GET (edef->vd_cnt);
5380 ent.vd_hash = BYTE_GET (edef->vd_hash);
5381 ent.vd_aux = BYTE_GET (edef->vd_aux);
5382 ent.vd_next = BYTE_GET (edef->vd_next);
5384 printf (_(" %#06x: Rev: %d Flags: %s"),
5385 idx, ent.vd_version, get_ver_flags (ent.vd_flags));
5387 printf (_(" Index: %d Cnt: %d "),
5388 ent.vd_ndx, ent.vd_cnt);
5390 vstart += ent.vd_aux;
5392 eaux = (Elf_External_Verdaux *) vstart;
5394 aux.vda_name = BYTE_GET (eaux->vda_name);
5395 aux.vda_next = BYTE_GET (eaux->vda_next);
5397 if (dynamic_strings)
5398 printf (_("Name: %s\n"), dynamic_strings + aux.vda_name);
5399 else
5400 printf (_("Name index: %ld\n"), aux.vda_name);
5402 isum = idx + ent.vd_aux;
5404 for (j = 1; j < ent.vd_cnt; j++)
5406 isum += aux.vda_next;
5407 vstart += aux.vda_next;
5409 eaux = (Elf_External_Verdaux *) vstart;
5411 aux.vda_name = BYTE_GET (eaux->vda_name);
5412 aux.vda_next = BYTE_GET (eaux->vda_next);
5414 if (dynamic_strings)
5415 printf (_(" %#06x: Parent %d: %s\n"),
5416 isum, j, dynamic_strings + aux.vda_name);
5417 else
5418 printf (_(" %#06x: Parent %d, name index: %ld\n"),
5419 isum, j, aux.vda_name);
5422 idx += ent.vd_next;
5425 free (edefs);
5427 break;
5429 case SHT_GNU_verneed:
5431 Elf_External_Verneed *eneed;
5432 unsigned int idx;
5433 unsigned int cnt;
5435 found = 1;
5437 printf (_("\nVersion needs section '%s' contains %ld entries:\n"),
5438 SECTION_NAME (section), section->sh_info);
5440 printf (_(" Addr: 0x"));
5441 printf_vma (section->sh_addr);
5442 printf (_(" Offset: %#08lx Link to section: %ld (%s)\n"),
5443 (unsigned long) section->sh_offset, section->sh_link,
5444 SECTION_NAME (SECTION_HEADER (section->sh_link)));
5446 eneed = get_data (NULL, file, section->sh_offset, section->sh_size,
5447 _("version need section"));
5448 if (!eneed)
5449 break;
5451 for (idx = cnt = 0; cnt < section->sh_info; ++cnt)
5453 Elf_External_Verneed *entry;
5454 Elf_Internal_Verneed ent;
5455 int j;
5456 int isum;
5457 char *vstart;
5459 vstart = ((char *) eneed) + idx;
5461 entry = (Elf_External_Verneed *) vstart;
5463 ent.vn_version = BYTE_GET (entry->vn_version);
5464 ent.vn_cnt = BYTE_GET (entry->vn_cnt);
5465 ent.vn_file = BYTE_GET (entry->vn_file);
5466 ent.vn_aux = BYTE_GET (entry->vn_aux);
5467 ent.vn_next = BYTE_GET (entry->vn_next);
5469 printf (_(" %#06x: Version: %d"), idx, ent.vn_version);
5471 if (dynamic_strings)
5472 printf (_(" File: %s"), dynamic_strings + ent.vn_file);
5473 else
5474 printf (_(" File: %lx"), ent.vn_file);
5476 printf (_(" Cnt: %d\n"), ent.vn_cnt);
5478 vstart += ent.vn_aux;
5480 for (j = 0, isum = idx + ent.vn_aux; j < ent.vn_cnt; ++j)
5482 Elf_External_Vernaux *eaux;
5483 Elf_Internal_Vernaux aux;
5485 eaux = (Elf_External_Vernaux *) vstart;
5487 aux.vna_hash = BYTE_GET (eaux->vna_hash);
5488 aux.vna_flags = BYTE_GET (eaux->vna_flags);
5489 aux.vna_other = BYTE_GET (eaux->vna_other);
5490 aux.vna_name = BYTE_GET (eaux->vna_name);
5491 aux.vna_next = BYTE_GET (eaux->vna_next);
5493 if (dynamic_strings)
5494 printf (_(" %#06x: Name: %s"),
5495 isum, dynamic_strings + aux.vna_name);
5496 else
5497 printf (_(" %#06x: Name index: %lx"),
5498 isum, aux.vna_name);
5500 printf (_(" Flags: %s Version: %d\n"),
5501 get_ver_flags (aux.vna_flags), aux.vna_other);
5503 isum += aux.vna_next;
5504 vstart += aux.vna_next;
5507 idx += ent.vn_next;
5510 free (eneed);
5512 break;
5514 case SHT_GNU_versym:
5516 Elf_Internal_Shdr *link_section;
5517 int total;
5518 int cnt;
5519 unsigned char *edata;
5520 unsigned short *data;
5521 char *strtab;
5522 Elf_Internal_Sym *symbols;
5523 Elf_Internal_Shdr *string_sec;
5524 long off;
5526 link_section = SECTION_HEADER (section->sh_link);
5527 total = section->sh_size / section->sh_entsize;
5529 found = 1;
5531 symbols = GET_ELF_SYMBOLS (file, link_section);
5533 string_sec = SECTION_HEADER (link_section->sh_link);
5535 strtab = get_data (NULL, file, string_sec->sh_offset,
5536 string_sec->sh_size, _("version string table"));
5537 if (!strtab)
5538 break;
5540 printf (_("\nVersion symbols section '%s' contains %d entries:\n"),
5541 SECTION_NAME (section), total);
5543 printf (_(" Addr: "));
5544 printf_vma (section->sh_addr);
5545 printf (_(" Offset: %#08lx Link: %lx (%s)\n"),
5546 (unsigned long) section->sh_offset, section->sh_link,
5547 SECTION_NAME (link_section));
5549 off = offset_from_vma (file,
5550 version_info[DT_VERSIONTAGIDX (DT_VERSYM)],
5551 total * sizeof (short));
5552 edata = get_data (NULL, file, off, total * sizeof (short),
5553 _("version symbol data"));
5554 if (!edata)
5556 free (strtab);
5557 break;
5560 data = malloc (total * sizeof (short));
5562 for (cnt = total; cnt --;)
5563 data[cnt] = byte_get (edata + cnt * sizeof (short),
5564 sizeof (short));
5566 free (edata);
5568 for (cnt = 0; cnt < total; cnt += 4)
5570 int j, nn;
5571 int check_def, check_need;
5572 char *name;
5574 printf (" %03x:", cnt);
5576 for (j = 0; (j < 4) && (cnt + j) < total; ++j)
5577 switch (data[cnt + j])
5579 case 0:
5580 fputs (_(" 0 (*local*) "), stdout);
5581 break;
5583 case 1:
5584 fputs (_(" 1 (*global*) "), stdout);
5585 break;
5587 default:
5588 nn = printf ("%4x%c", data[cnt + j] & 0x7fff,
5589 data[cnt + j] & 0x8000 ? 'h' : ' ');
5591 check_def = 1;
5592 check_need = 1;
5593 if (SECTION_HEADER (symbols[cnt + j].st_shndx)->sh_type
5594 != SHT_NOBITS)
5596 if (symbols[cnt + j].st_shndx == SHN_UNDEF)
5597 check_def = 0;
5598 else
5599 check_need = 0;
5602 if (check_need
5603 && version_info[DT_VERSIONTAGIDX (DT_VERNEED)])
5605 Elf_Internal_Verneed ivn;
5606 unsigned long offset;
5608 offset = offset_from_vma
5609 (file, version_info[DT_VERSIONTAGIDX (DT_VERNEED)],
5610 sizeof (Elf_External_Verneed));
5614 Elf_Internal_Vernaux ivna;
5615 Elf_External_Verneed evn;
5616 Elf_External_Vernaux evna;
5617 unsigned long a_off;
5619 get_data (&evn, file, offset, sizeof (evn),
5620 _("version need"));
5622 ivn.vn_aux = BYTE_GET (evn.vn_aux);
5623 ivn.vn_next = BYTE_GET (evn.vn_next);
5625 a_off = offset + ivn.vn_aux;
5629 get_data (&evna, file, a_off, sizeof (evna),
5630 _("version need aux (2)"));
5632 ivna.vna_next = BYTE_GET (evna.vna_next);
5633 ivna.vna_other = BYTE_GET (evna.vna_other);
5635 a_off += ivna.vna_next;
5637 while (ivna.vna_other != data[cnt + j]
5638 && ivna.vna_next != 0);
5640 if (ivna.vna_other == data[cnt + j])
5642 ivna.vna_name = BYTE_GET (evna.vna_name);
5644 name = strtab + ivna.vna_name;
5645 nn += printf ("(%s%-*s",
5646 name,
5647 12 - (int) strlen (name),
5648 ")");
5649 check_def = 0;
5650 break;
5653 offset += ivn.vn_next;
5655 while (ivn.vn_next);
5658 if (check_def && data[cnt + j] != 0x8001
5659 && version_info[DT_VERSIONTAGIDX (DT_VERDEF)])
5661 Elf_Internal_Verdef ivd;
5662 Elf_External_Verdef evd;
5663 unsigned long offset;
5665 offset = offset_from_vma
5666 (file, version_info[DT_VERSIONTAGIDX (DT_VERDEF)],
5667 sizeof evd);
5671 get_data (&evd, file, offset, sizeof (evd),
5672 _("version def"));
5674 ivd.vd_next = BYTE_GET (evd.vd_next);
5675 ivd.vd_ndx = BYTE_GET (evd.vd_ndx);
5677 offset += ivd.vd_next;
5679 while (ivd.vd_ndx != (data[cnt + j] & 0x7fff)
5680 && ivd.vd_next != 0);
5682 if (ivd.vd_ndx == (data[cnt + j] & 0x7fff))
5684 Elf_External_Verdaux evda;
5685 Elf_Internal_Verdaux ivda;
5687 ivd.vd_aux = BYTE_GET (evd.vd_aux);
5689 get_data (&evda, file,
5690 offset - ivd.vd_next + ivd.vd_aux,
5691 sizeof (evda), _("version def aux"));
5693 ivda.vda_name = BYTE_GET (evda.vda_name);
5695 name = strtab + ivda.vda_name;
5696 nn += printf ("(%s%-*s",
5697 name,
5698 12 - (int) strlen (name),
5699 ")");
5703 if (nn < 18)
5704 printf ("%*c", 18 - nn, ' ');
5707 putchar ('\n');
5710 free (data);
5711 free (strtab);
5712 free (symbols);
5714 break;
5716 default:
5717 break;
5721 if (! found)
5722 printf (_("\nNo version information found in this file.\n"));
5724 return 1;
5727 static const char *
5728 get_symbol_binding (unsigned int binding)
5730 static char buff[32];
5732 switch (binding)
5734 case STB_LOCAL: return "LOCAL";
5735 case STB_GLOBAL: return "GLOBAL";
5736 case STB_WEAK: return "WEAK";
5737 default:
5738 if (binding >= STB_LOPROC && binding <= STB_HIPROC)
5739 sprintf (buff, _("<processor specific>: %d"), binding);
5740 else if (binding >= STB_LOOS && binding <= STB_HIOS)
5741 sprintf (buff, _("<OS specific>: %d"), binding);
5742 else
5743 sprintf (buff, _("<unknown>: %d"), binding);
5744 return buff;
5748 static const char *
5749 get_symbol_type (unsigned int type)
5751 static char buff[32];
5753 switch (type)
5755 case STT_NOTYPE: return "NOTYPE";
5756 case STT_OBJECT: return "OBJECT";
5757 case STT_FUNC: return "FUNC";
5758 case STT_SECTION: return "SECTION";
5759 case STT_FILE: return "FILE";
5760 case STT_COMMON: return "COMMON";
5761 case STT_TLS: return "TLS";
5762 default:
5763 if (type >= STT_LOPROC && type <= STT_HIPROC)
5765 if (elf_header.e_machine == EM_ARM && type == STT_ARM_TFUNC)
5766 return "THUMB_FUNC";
5768 if (elf_header.e_machine == EM_SPARCV9 && type == STT_REGISTER)
5769 return "REGISTER";
5771 if (elf_header.e_machine == EM_PARISC && type == STT_PARISC_MILLI)
5772 return "PARISC_MILLI";
5774 sprintf (buff, _("<processor specific>: %d"), type);
5776 else if (type >= STT_LOOS && type <= STT_HIOS)
5778 if (elf_header.e_machine == EM_PARISC)
5780 if (type == STT_HP_OPAQUE)
5781 return "HP_OPAQUE";
5782 if (type == STT_HP_STUB)
5783 return "HP_STUB";
5786 sprintf (buff, _("<OS specific>: %d"), type);
5788 else
5789 sprintf (buff, _("<unknown>: %d"), type);
5790 return buff;
5794 static const char *
5795 get_symbol_visibility (unsigned int visibility)
5797 switch (visibility)
5799 case STV_DEFAULT: return "DEFAULT";
5800 case STV_INTERNAL: return "INTERNAL";
5801 case STV_HIDDEN: return "HIDDEN";
5802 case STV_PROTECTED: return "PROTECTED";
5803 default: abort ();
5807 static const char *
5808 get_symbol_index_type (unsigned int type)
5810 static char buff[32];
5812 switch (type)
5814 case SHN_UNDEF: return "UND";
5815 case SHN_ABS: return "ABS";
5816 case SHN_COMMON: return "COM";
5817 default:
5818 if (type == SHN_IA_64_ANSI_COMMON
5819 && elf_header.e_machine == EM_IA_64
5820 && elf_header.e_ident[EI_OSABI] == ELFOSABI_HPUX)
5821 return "ANSI_COM";
5822 else if (type >= SHN_LOPROC && type <= SHN_HIPROC)
5823 sprintf (buff, "PRC[0x%04x]", type);
5824 else if (type >= SHN_LOOS && type <= SHN_HIOS)
5825 sprintf (buff, "OS [0x%04x]", type);
5826 else if (type >= SHN_LORESERVE && type <= SHN_HIRESERVE)
5827 sprintf (buff, "RSV[0x%04x]", type);
5828 else
5829 sprintf (buff, "%3d", type);
5830 break;
5833 return buff;
5836 static int *
5837 get_dynamic_data (FILE *file, unsigned int number)
5839 unsigned char *e_data;
5840 int *i_data;
5842 e_data = malloc (number * 4);
5844 if (e_data == NULL)
5846 error (_("Out of memory\n"));
5847 return NULL;
5850 if (fread (e_data, 4, number, file) != number)
5852 error (_("Unable to read in dynamic data\n"));
5853 return NULL;
5856 i_data = malloc (number * sizeof (*i_data));
5858 if (i_data == NULL)
5860 error (_("Out of memory\n"));
5861 free (e_data);
5862 return NULL;
5865 while (number--)
5866 i_data[number] = byte_get (e_data + number * 4, 4);
5868 free (e_data);
5870 return i_data;
5873 /* Dump the symbol table. */
5874 static int
5875 process_symbol_table (FILE *file)
5877 Elf_Internal_Shdr *section;
5878 unsigned char nb[4];
5879 unsigned char nc[4];
5880 int nbuckets = 0;
5881 int nchains = 0;
5882 int *buckets = NULL;
5883 int *chains = NULL;
5885 if (! do_syms && !do_histogram)
5886 return 1;
5888 if (dynamic_info[DT_HASH] && ((do_using_dynamic && dynamic_strings != NULL)
5889 || do_histogram))
5891 if (fseek (file,
5892 (archive_file_offset
5893 + offset_from_vma (file, dynamic_info[DT_HASH],
5894 sizeof nb + sizeof nc)),
5895 SEEK_SET))
5897 error (_("Unable to seek to start of dynamic information"));
5898 return 0;
5901 if (fread (nb, sizeof (nb), 1, file) != 1)
5903 error (_("Failed to read in number of buckets\n"));
5904 return 0;
5907 if (fread (nc, sizeof (nc), 1, file) != 1)
5909 error (_("Failed to read in number of chains\n"));
5910 return 0;
5913 nbuckets = byte_get (nb, 4);
5914 nchains = byte_get (nc, 4);
5916 buckets = get_dynamic_data (file, nbuckets);
5917 chains = get_dynamic_data (file, nchains);
5919 if (buckets == NULL || chains == NULL)
5920 return 0;
5923 if (do_syms
5924 && dynamic_info[DT_HASH] && do_using_dynamic && dynamic_strings != NULL)
5926 int hn;
5927 int si;
5929 printf (_("\nSymbol table for image:\n"));
5930 if (is_32bit_elf)
5931 printf (_(" Num Buc: Value Size Type Bind Vis Ndx Name\n"));
5932 else
5933 printf (_(" Num Buc: Value Size Type Bind Vis Ndx Name\n"));
5935 for (hn = 0; hn < nbuckets; hn++)
5937 if (! buckets[hn])
5938 continue;
5940 for (si = buckets[hn]; si < nchains && si > 0; si = chains[si])
5942 Elf_Internal_Sym *psym;
5944 psym = dynamic_symbols + si;
5946 printf (" %3d %3d: ", si, hn);
5947 print_vma (psym->st_value, LONG_HEX);
5948 putchar (' ' );
5949 print_vma (psym->st_size, DEC_5);
5951 printf (" %6s", get_symbol_type (ELF_ST_TYPE (psym->st_info)));
5952 printf (" %6s", get_symbol_binding (ELF_ST_BIND (psym->st_info)));
5953 printf (" %3s", get_symbol_visibility (ELF_ST_VISIBILITY (psym->st_other)));
5954 printf (" %3.3s ", get_symbol_index_type (psym->st_shndx));
5955 print_symbol (25, dynamic_strings + psym->st_name);
5956 putchar ('\n');
5960 else if (do_syms && !do_using_dynamic)
5962 unsigned int i;
5964 for (i = 0, section = section_headers;
5965 i < elf_header.e_shnum;
5966 i++, section++)
5968 unsigned int si;
5969 char *strtab;
5970 Elf_Internal_Sym *symtab;
5971 Elf_Internal_Sym *psym;
5974 if ( section->sh_type != SHT_SYMTAB
5975 && section->sh_type != SHT_DYNSYM)
5976 continue;
5978 printf (_("\nSymbol table '%s' contains %lu entries:\n"),
5979 SECTION_NAME (section),
5980 (unsigned long) (section->sh_size / section->sh_entsize));
5981 if (is_32bit_elf)
5982 printf (_(" Num: Value Size Type Bind Vis Ndx Name\n"));
5983 else
5984 printf (_(" Num: Value Size Type Bind Vis Ndx Name\n"));
5986 symtab = GET_ELF_SYMBOLS (file, section);
5987 if (symtab == NULL)
5988 continue;
5990 if (section->sh_link == elf_header.e_shstrndx)
5991 strtab = string_table;
5992 else
5994 Elf_Internal_Shdr *string_sec;
5996 string_sec = SECTION_HEADER (section->sh_link);
5998 strtab = get_data (NULL, file, string_sec->sh_offset,
5999 string_sec->sh_size, _("string table"));
6002 for (si = 0, psym = symtab;
6003 si < section->sh_size / section->sh_entsize;
6004 si++, psym++)
6006 printf ("%6d: ", si);
6007 print_vma (psym->st_value, LONG_HEX);
6008 putchar (' ');
6009 print_vma (psym->st_size, DEC_5);
6010 printf (" %-7s", get_symbol_type (ELF_ST_TYPE (psym->st_info)));
6011 printf (" %-6s", get_symbol_binding (ELF_ST_BIND (psym->st_info)));
6012 printf (" %-3s", get_symbol_visibility (ELF_ST_VISIBILITY (psym->st_other)));
6013 printf (" %4s ", get_symbol_index_type (psym->st_shndx));
6014 print_symbol (25, strtab + psym->st_name);
6016 if (section->sh_type == SHT_DYNSYM &&
6017 version_info[DT_VERSIONTAGIDX (DT_VERSYM)] != 0)
6019 unsigned char data[2];
6020 unsigned short vers_data;
6021 unsigned long offset;
6022 int is_nobits;
6023 int check_def;
6025 offset = offset_from_vma
6026 (file, version_info[DT_VERSIONTAGIDX (DT_VERSYM)],
6027 sizeof data + si * sizeof (vers_data));
6029 get_data (&data, file, offset + si * sizeof (vers_data),
6030 sizeof (data), _("version data"));
6032 vers_data = byte_get (data, 2);
6034 is_nobits = (SECTION_HEADER (psym->st_shndx)->sh_type
6035 == SHT_NOBITS);
6037 check_def = (psym->st_shndx != SHN_UNDEF);
6039 if ((vers_data & 0x8000) || vers_data > 1)
6041 if (version_info[DT_VERSIONTAGIDX (DT_VERNEED)]
6042 && (is_nobits || ! check_def))
6044 Elf_External_Verneed evn;
6045 Elf_Internal_Verneed ivn;
6046 Elf_Internal_Vernaux ivna;
6048 /* We must test both. */
6049 offset = offset_from_vma
6050 (file, version_info[DT_VERSIONTAGIDX (DT_VERNEED)],
6051 sizeof evn);
6055 unsigned long vna_off;
6057 get_data (&evn, file, offset, sizeof (evn),
6058 _("version need"));
6060 ivn.vn_aux = BYTE_GET (evn.vn_aux);
6061 ivn.vn_next = BYTE_GET (evn.vn_next);
6063 vna_off = offset + ivn.vn_aux;
6067 Elf_External_Vernaux evna;
6069 get_data (&evna, file, vna_off,
6070 sizeof (evna),
6071 _("version need aux (3)"));
6073 ivna.vna_other = BYTE_GET (evna.vna_other);
6074 ivna.vna_next = BYTE_GET (evna.vna_next);
6075 ivna.vna_name = BYTE_GET (evna.vna_name);
6077 vna_off += ivna.vna_next;
6079 while (ivna.vna_other != vers_data
6080 && ivna.vna_next != 0);
6082 if (ivna.vna_other == vers_data)
6083 break;
6085 offset += ivn.vn_next;
6087 while (ivn.vn_next != 0);
6089 if (ivna.vna_other == vers_data)
6091 printf ("@%s (%d)",
6092 strtab + ivna.vna_name, ivna.vna_other);
6093 check_def = 0;
6095 else if (! is_nobits)
6096 error (_("bad dynamic symbol"));
6097 else
6098 check_def = 1;
6101 if (check_def)
6103 if (vers_data != 0x8001
6104 && version_info[DT_VERSIONTAGIDX (DT_VERDEF)])
6106 Elf_Internal_Verdef ivd;
6107 Elf_Internal_Verdaux ivda;
6108 Elf_External_Verdaux evda;
6109 unsigned long offset;
6111 offset = offset_from_vma
6112 (file,
6113 version_info[DT_VERSIONTAGIDX (DT_VERDEF)],
6114 sizeof (Elf_External_Verdef));
6118 Elf_External_Verdef evd;
6120 get_data (&evd, file, offset, sizeof (evd),
6121 _("version def"));
6123 ivd.vd_ndx = BYTE_GET (evd.vd_ndx);
6124 ivd.vd_aux = BYTE_GET (evd.vd_aux);
6125 ivd.vd_next = BYTE_GET (evd.vd_next);
6127 offset += ivd.vd_next;
6129 while (ivd.vd_ndx != (vers_data & 0x7fff)
6130 && ivd.vd_next != 0);
6132 offset -= ivd.vd_next;
6133 offset += ivd.vd_aux;
6135 get_data (&evda, file, offset, sizeof (evda),
6136 _("version def aux"));
6138 ivda.vda_name = BYTE_GET (evda.vda_name);
6140 if (psym->st_name != ivda.vda_name)
6141 printf ((vers_data & 0x8000)
6142 ? "@%s" : "@@%s",
6143 strtab + ivda.vda_name);
6149 putchar ('\n');
6152 free (symtab);
6153 if (strtab != string_table)
6154 free (strtab);
6157 else if (do_syms)
6158 printf
6159 (_("\nDynamic symbol information is not available for displaying symbols.\n"));
6161 if (do_histogram && buckets != NULL)
6163 int *lengths;
6164 int *counts;
6165 int hn;
6166 int si;
6167 int maxlength = 0;
6168 int nzero_counts = 0;
6169 int nsyms = 0;
6171 printf (_("\nHistogram for bucket list length (total of %d buckets):\n"),
6172 nbuckets);
6173 printf (_(" Length Number %% of total Coverage\n"));
6175 lengths = calloc (nbuckets, sizeof (int));
6176 if (lengths == NULL)
6178 error (_("Out of memory"));
6179 return 0;
6181 for (hn = 0; hn < nbuckets; ++hn)
6183 if (! buckets[hn])
6184 continue;
6186 for (si = buckets[hn]; si > 0 && si < nchains; si = chains[si])
6188 ++nsyms;
6189 if (maxlength < ++lengths[hn])
6190 ++maxlength;
6194 counts = calloc (maxlength + 1, sizeof (int));
6195 if (counts == NULL)
6197 error (_("Out of memory"));
6198 return 0;
6201 for (hn = 0; hn < nbuckets; ++hn)
6202 ++counts[lengths[hn]];
6204 if (nbuckets > 0)
6206 printf (" 0 %-10d (%5.1f%%)\n",
6207 counts[0], (counts[0] * 100.0) / nbuckets);
6208 for (si = 1; si <= maxlength; ++si)
6210 nzero_counts += counts[si] * si;
6211 printf ("%7d %-10d (%5.1f%%) %5.1f%%\n",
6212 si, counts[si], (counts[si] * 100.0) / nbuckets,
6213 (nzero_counts * 100.0) / nsyms);
6217 free (counts);
6218 free (lengths);
6221 if (buckets != NULL)
6223 free (buckets);
6224 free (chains);
6227 return 1;
6230 static int
6231 process_syminfo (FILE *file ATTRIBUTE_UNUSED)
6233 unsigned int i;
6235 if (dynamic_syminfo == NULL
6236 || !do_dynamic)
6237 /* No syminfo, this is ok. */
6238 return 1;
6240 /* There better should be a dynamic symbol section. */
6241 if (dynamic_symbols == NULL || dynamic_strings == NULL)
6242 return 0;
6244 if (dynamic_addr)
6245 printf (_("\nDynamic info segment at offset 0x%lx contains %d entries:\n"),
6246 dynamic_syminfo_offset, dynamic_syminfo_nent);
6248 printf (_(" Num: Name BoundTo Flags\n"));
6249 for (i = 0; i < dynamic_syminfo_nent; ++i)
6251 unsigned short int flags = dynamic_syminfo[i].si_flags;
6253 printf ("%4d: ", i);
6254 print_symbol (30, dynamic_strings + dynamic_symbols[i].st_name);
6255 putchar (' ');
6257 switch (dynamic_syminfo[i].si_boundto)
6259 case SYMINFO_BT_SELF:
6260 fputs ("SELF ", stdout);
6261 break;
6262 case SYMINFO_BT_PARENT:
6263 fputs ("PARENT ", stdout);
6264 break;
6265 default:
6266 if (dynamic_syminfo[i].si_boundto > 0
6267 && dynamic_syminfo[i].si_boundto < dynamic_size)
6269 print_symbol (10,
6270 dynamic_strings
6271 + (dynamic_segment
6272 [dynamic_syminfo[i].si_boundto].d_un.d_val));
6273 putchar (' ' );
6275 else
6276 printf ("%-10d ", dynamic_syminfo[i].si_boundto);
6277 break;
6280 if (flags & SYMINFO_FLG_DIRECT)
6281 printf (" DIRECT");
6282 if (flags & SYMINFO_FLG_PASSTHRU)
6283 printf (" PASSTHRU");
6284 if (flags & SYMINFO_FLG_COPY)
6285 printf (" COPY");
6286 if (flags & SYMINFO_FLG_LAZYLOAD)
6287 printf (" LAZYLOAD");
6289 puts ("");
6292 return 1;
6295 #ifdef SUPPORT_DISASSEMBLY
6296 static void
6297 disassemble_section (Elf_Internal_Shdr *section, FILE *file)
6299 printf (_("\nAssembly dump of section %s\n"),
6300 SECTION_NAME (section));
6302 /* XXX -- to be done --- XXX */
6304 return 1;
6306 #endif
6308 static int
6309 dump_section (Elf_Internal_Shdr *section, FILE *file)
6311 bfd_size_type bytes;
6312 bfd_vma addr;
6313 unsigned char *data;
6314 unsigned char *start;
6316 bytes = section->sh_size;
6318 if (bytes == 0 || section->sh_type == SHT_NOBITS)
6320 printf (_("\nSection '%s' has no data to dump.\n"),
6321 SECTION_NAME (section));
6322 return 0;
6324 else
6325 printf (_("\nHex dump of section '%s':\n"), SECTION_NAME (section));
6327 addr = section->sh_addr;
6329 start = get_data (NULL, file, section->sh_offset, bytes, _("section data"));
6330 if (!start)
6331 return 0;
6333 data = start;
6335 while (bytes)
6337 int j;
6338 int k;
6339 int lbytes;
6341 lbytes = (bytes > 16 ? 16 : bytes);
6343 printf (" 0x%8.8lx ", (unsigned long) addr);
6345 switch (elf_header.e_ident[EI_DATA])
6347 default:
6348 case ELFDATA2LSB:
6349 for (j = 15; j >= 0; j --)
6351 if (j < lbytes)
6352 printf ("%2.2x", data[j]);
6353 else
6354 printf (" ");
6356 if (!(j & 0x3))
6357 printf (" ");
6359 break;
6361 case ELFDATA2MSB:
6362 for (j = 0; j < 16; j++)
6364 if (j < lbytes)
6365 printf ("%2.2x", data[j]);
6366 else
6367 printf (" ");
6369 if ((j & 3) == 3)
6370 printf (" ");
6372 break;
6375 for (j = 0; j < lbytes; j++)
6377 k = data[j];
6378 if (k >= ' ' && k < 0x7f)
6379 printf ("%c", k);
6380 else
6381 printf (".");
6384 putchar ('\n');
6386 data += lbytes;
6387 addr += lbytes;
6388 bytes -= lbytes;
6391 free (start);
6393 return 1;
6397 static unsigned long int
6398 read_leb128 (unsigned char *data, int *length_return, int sign)
6400 unsigned long int result = 0;
6401 unsigned int num_read = 0;
6402 int shift = 0;
6403 unsigned char byte;
6407 byte = *data++;
6408 num_read++;
6410 result |= (byte & 0x7f) << shift;
6412 shift += 7;
6415 while (byte & 0x80);
6417 if (length_return != NULL)
6418 *length_return = num_read;
6420 if (sign && (shift < 32) && (byte & 0x40))
6421 result |= -1 << shift;
6423 return result;
6426 typedef struct State_Machine_Registers
6428 unsigned long address;
6429 unsigned int file;
6430 unsigned int line;
6431 unsigned int column;
6432 int is_stmt;
6433 int basic_block;
6434 int end_sequence;
6435 /* This variable hold the number of the last entry seen
6436 in the File Table. */
6437 unsigned int last_file_entry;
6438 } SMR;
6440 static SMR state_machine_regs;
6442 static void
6443 reset_state_machine (int is_stmt)
6445 state_machine_regs.address = 0;
6446 state_machine_regs.file = 1;
6447 state_machine_regs.line = 1;
6448 state_machine_regs.column = 0;
6449 state_machine_regs.is_stmt = is_stmt;
6450 state_machine_regs.basic_block = 0;
6451 state_machine_regs.end_sequence = 0;
6452 state_machine_regs.last_file_entry = 0;
6455 /* Handled an extend line op. Returns true if this is the end
6456 of sequence. */
6457 static int
6458 process_extended_line_op (unsigned char *data, int is_stmt, int pointer_size)
6460 unsigned char op_code;
6461 int bytes_read;
6462 unsigned int len;
6463 unsigned char *name;
6464 unsigned long adr;
6466 len = read_leb128 (data, & bytes_read, 0);
6467 data += bytes_read;
6469 if (len == 0)
6471 warn (_("badly formed extended line op encountered!\n"));
6472 return bytes_read;
6475 len += bytes_read;
6476 op_code = *data++;
6478 printf (_(" Extended opcode %d: "), op_code);
6480 switch (op_code)
6482 case DW_LNE_end_sequence:
6483 printf (_("End of Sequence\n\n"));
6484 reset_state_machine (is_stmt);
6485 break;
6487 case DW_LNE_set_address:
6488 adr = byte_get (data, pointer_size);
6489 printf (_("set Address to 0x%lx\n"), adr);
6490 state_machine_regs.address = adr;
6491 break;
6493 case DW_LNE_define_file:
6494 printf (_(" define new File Table entry\n"));
6495 printf (_(" Entry\tDir\tTime\tSize\tName\n"));
6497 printf (_(" %d\t"), ++state_machine_regs.last_file_entry);
6498 name = data;
6499 data += strlen ((char *) data) + 1;
6500 printf (_("%lu\t"), read_leb128 (data, & bytes_read, 0));
6501 data += bytes_read;
6502 printf (_("%lu\t"), read_leb128 (data, & bytes_read, 0));
6503 data += bytes_read;
6504 printf (_("%lu\t"), read_leb128 (data, & bytes_read, 0));
6505 printf (_("%s\n\n"), name);
6506 break;
6508 default:
6509 printf (_("UNKNOWN: length %d\n"), len - bytes_read);
6510 break;
6513 return len;
6516 /* Finds section NAME inside FILE and returns a
6517 pointer to it, or NULL upon failure. */
6519 static Elf_Internal_Shdr *
6520 find_section (const char * name)
6522 Elf_Internal_Shdr *sec;
6523 unsigned int i;
6525 for (i = elf_header.e_shnum, sec = section_headers + i - 1;
6526 i; --i, --sec)
6527 if (strcmp (SECTION_NAME (sec), name) == 0)
6528 break;
6530 if (i && sec && sec->sh_size != 0)
6531 return sec;
6533 return NULL;
6536 /* Size of pointers in the .debug_line section. This information is not
6537 really present in that section. It's obtained before dumping the debug
6538 sections by doing some pre-scan of the .debug_info section. */
6539 static unsigned int * debug_line_pointer_sizes = NULL;
6540 static unsigned int num_debug_line_pointer_sizes = 0;
6542 /* Locate and scan the .debug_info section in the file and record the pointer
6543 sizes for the compilation units in it. Usually an executable will have
6544 just one pointer size, but this is not guaranteed, and so we try not to
6545 make any assumptions. Returns zero upon failure, or the number of
6546 compilation units upon success. */
6548 static unsigned int
6549 get_debug_line_pointer_sizes (FILE * file)
6551 Elf_Internal_Shdr * section;
6552 unsigned char * start;
6553 unsigned char * end;
6554 unsigned char * begin;
6555 unsigned long length;
6556 unsigned int num_units;
6557 unsigned int unit;
6559 section = find_section (".debug_info");
6560 if (section == NULL)
6561 return 0;
6563 length = section->sh_size;
6564 start = get_data (NULL, file, section->sh_offset, section->sh_size,
6565 _("extracting pointer sizes from .debug_info section"));
6566 if (start == NULL)
6567 return 0;
6569 end = start + section->sh_size;
6570 /* First scan the section to get the number of comp units. */
6571 for (begin = start, num_units = 0; begin < end; num_units++)
6573 /* Read the first 4 bytes. For a 32-bit DWARF section, this will
6574 be the length. For a 64-bit DWARF section, it'll be the escape
6575 code 0xffffffff followed by an 8 byte length. */
6576 length = byte_get (begin, 4);
6578 if (length == 0xffffffff)
6580 length = byte_get (begin + 4, 8);
6581 begin += length + 12;
6583 else
6584 begin += length + 4;
6587 if (num_units == 0)
6589 error (_("No comp units in .debug_info section ?"));
6590 free (start);
6591 return 0;
6594 /* Then allocate an array to hold the pointer sizes. */
6595 debug_line_pointer_sizes = malloc (num_units * sizeof * debug_line_pointer_sizes);
6596 if (debug_line_pointer_sizes == NULL)
6598 error (_("Not enough memory for a pointer size array of %u entries"),
6599 num_units);
6600 free (start);
6601 return 0;
6604 /* Populate the array. */
6605 for (begin = start, unit = 0; begin < end; unit++)
6607 length = byte_get (begin, 4);
6608 if (length == 0xffffffff)
6610 /* For 64-bit DWARF, the 1-byte address_size field is 22 bytes
6611 from the start of the section. This is computed as follows:
6613 unit_length: 12 bytes
6614 version: 2 bytes
6615 debug_abbrev_offset: 8 bytes
6616 -----------------------------
6617 Total: 22 bytes */
6619 debug_line_pointer_sizes [unit] = byte_get (begin + 22, 1);
6620 length = byte_get (begin + 4, 8);
6621 begin += length + 12;
6623 else
6625 /* For 32-bit DWARF, the 1-byte address_size field is 10 bytes from
6626 the start of the section:
6628 unit_length: 4 bytes
6629 version: 2 bytes
6630 debug_abbrev_offset: 4 bytes
6631 -----------------------------
6632 Total: 10 bytes */
6634 debug_line_pointer_sizes [unit] = byte_get (begin + 10, 1);
6635 begin += length + 4;
6639 free (start);
6640 num_debug_line_pointer_sizes = num_units;
6641 return num_units;
6644 static int
6645 display_debug_lines (Elf_Internal_Shdr *section,
6646 unsigned char *start, FILE *file)
6648 unsigned char *hdrptr;
6649 DWARF2_Internal_LineInfo info;
6650 unsigned char *standard_opcodes;
6651 unsigned char *data = start;
6652 unsigned char *end = start + section->sh_size;
6653 unsigned char *end_of_sequence;
6654 int i;
6655 int offset_size;
6656 int initial_length_size;
6657 unsigned int comp_unit = 0;
6659 printf (_("\nDump of debug contents of section %s:\n\n"),
6660 SECTION_NAME (section));
6662 if (num_debug_line_pointer_sizes == 0)
6663 get_debug_line_pointer_sizes (file);
6665 while (data < end)
6667 unsigned int pointer_size;
6669 hdrptr = data;
6671 /* Check the length of the block. */
6672 info.li_length = byte_get (hdrptr, 4);
6673 hdrptr += 4;
6675 if (info.li_length == 0xffffffff)
6677 /* This section is 64-bit DWARF 3. */
6678 info.li_length = byte_get (hdrptr, 8);
6679 hdrptr += 8;
6680 offset_size = 8;
6681 initial_length_size = 12;
6683 else
6685 offset_size = 4;
6686 initial_length_size = 4;
6689 if (info.li_length + initial_length_size > section->sh_size)
6691 warn
6692 (_("The line info appears to be corrupt - the section is too small\n"));
6693 return 0;
6696 /* Check its version number. */
6697 info.li_version = byte_get (hdrptr, 2);
6698 hdrptr += 2;
6699 if (info.li_version != 2 && info.li_version != 3)
6701 warn (_("Only DWARF version 2 and 3 line info is currently supported.\n"));
6702 return 0;
6705 info.li_prologue_length = byte_get (hdrptr, offset_size);
6706 hdrptr += offset_size;
6707 info.li_min_insn_length = byte_get (hdrptr, 1);
6708 hdrptr++;
6709 info.li_default_is_stmt = byte_get (hdrptr, 1);
6710 hdrptr++;
6711 info.li_line_base = byte_get (hdrptr, 1);
6712 hdrptr++;
6713 info.li_line_range = byte_get (hdrptr, 1);
6714 hdrptr++;
6715 info.li_opcode_base = byte_get (hdrptr, 1);
6716 hdrptr++;
6718 /* Sign extend the line base field. */
6719 info.li_line_base <<= 24;
6720 info.li_line_base >>= 24;
6722 /* Get the pointer size from the comp unit associated
6723 with this block of line number information. */
6724 if (comp_unit >= num_debug_line_pointer_sizes)
6726 error (_("Not enough comp units for .debug_lines section\n"));
6727 return 0;
6729 else
6731 pointer_size = debug_line_pointer_sizes [comp_unit];
6732 comp_unit ++;
6735 printf (_(" Length: %ld\n"), info.li_length);
6736 printf (_(" DWARF Version: %d\n"), info.li_version);
6737 printf (_(" Prologue Length: %d\n"), info.li_prologue_length);
6738 printf (_(" Minimum Instruction Length: %d\n"), info.li_min_insn_length);
6739 printf (_(" Initial value of 'is_stmt': %d\n"), info.li_default_is_stmt);
6740 printf (_(" Line Base: %d\n"), info.li_line_base);
6741 printf (_(" Line Range: %d\n"), info.li_line_range);
6742 printf (_(" Opcode Base: %d\n"), info.li_opcode_base);
6743 printf (_(" (Pointer size: %u)\n"), pointer_size);
6745 end_of_sequence = data + info.li_length + initial_length_size;
6747 reset_state_machine (info.li_default_is_stmt);
6749 /* Display the contents of the Opcodes table. */
6750 standard_opcodes = hdrptr;
6752 printf (_("\n Opcodes:\n"));
6754 for (i = 1; i < info.li_opcode_base; i++)
6755 printf (_(" Opcode %d has %d args\n"), i, standard_opcodes[i - 1]);
6757 /* Display the contents of the Directory table. */
6758 data = standard_opcodes + info.li_opcode_base - 1;
6760 if (*data == 0)
6761 printf (_("\n The Directory Table is empty.\n"));
6762 else
6764 printf (_("\n The Directory Table:\n"));
6766 while (*data != 0)
6768 printf (_(" %s\n"), data);
6770 data += strlen ((char *) data) + 1;
6774 /* Skip the NUL at the end of the table. */
6775 data++;
6777 /* Display the contents of the File Name table. */
6778 if (*data == 0)
6779 printf (_("\n The File Name Table is empty.\n"));
6780 else
6782 printf (_("\n The File Name Table:\n"));
6783 printf (_(" Entry\tDir\tTime\tSize\tName\n"));
6785 while (*data != 0)
6787 unsigned char *name;
6788 int bytes_read;
6790 printf (_(" %d\t"), ++state_machine_regs.last_file_entry);
6791 name = data;
6793 data += strlen ((char *) data) + 1;
6795 printf (_("%lu\t"), read_leb128 (data, & bytes_read, 0));
6796 data += bytes_read;
6797 printf (_("%lu\t"), read_leb128 (data, & bytes_read, 0));
6798 data += bytes_read;
6799 printf (_("%lu\t"), read_leb128 (data, & bytes_read, 0));
6800 data += bytes_read;
6801 printf (_("%s\n"), name);
6805 /* Skip the NUL at the end of the table. */
6806 data++;
6808 /* Now display the statements. */
6809 printf (_("\n Line Number Statements:\n"));
6812 while (data < end_of_sequence)
6814 unsigned char op_code;
6815 int adv;
6816 int bytes_read;
6818 op_code = *data++;
6820 if (op_code >= info.li_opcode_base)
6822 op_code -= info.li_opcode_base;
6823 adv = (op_code / info.li_line_range) * info.li_min_insn_length;
6824 state_machine_regs.address += adv;
6825 printf (_(" Special opcode %d: advance Address by %d to 0x%lx"),
6826 op_code, adv, state_machine_regs.address);
6827 adv = (op_code % info.li_line_range) + info.li_line_base;
6828 state_machine_regs.line += adv;
6829 printf (_(" and Line by %d to %d\n"),
6830 adv, state_machine_regs.line);
6832 else switch (op_code)
6834 case DW_LNS_extended_op:
6835 data += process_extended_line_op (data, info.li_default_is_stmt,
6836 pointer_size);
6837 break;
6839 case DW_LNS_copy:
6840 printf (_(" Copy\n"));
6841 break;
6843 case DW_LNS_advance_pc:
6844 adv = info.li_min_insn_length * read_leb128 (data, & bytes_read, 0);
6845 data += bytes_read;
6846 state_machine_regs.address += adv;
6847 printf (_(" Advance PC by %d to %lx\n"), adv,
6848 state_machine_regs.address);
6849 break;
6851 case DW_LNS_advance_line:
6852 adv = read_leb128 (data, & bytes_read, 1);
6853 data += bytes_read;
6854 state_machine_regs.line += adv;
6855 printf (_(" Advance Line by %d to %d\n"), adv,
6856 state_machine_regs.line);
6857 break;
6859 case DW_LNS_set_file:
6860 adv = read_leb128 (data, & bytes_read, 0);
6861 data += bytes_read;
6862 printf (_(" Set File Name to entry %d in the File Name Table\n"),
6863 adv);
6864 state_machine_regs.file = adv;
6865 break;
6867 case DW_LNS_set_column:
6868 adv = read_leb128 (data, & bytes_read, 0);
6869 data += bytes_read;
6870 printf (_(" Set column to %d\n"), adv);
6871 state_machine_regs.column = adv;
6872 break;
6874 case DW_LNS_negate_stmt:
6875 adv = state_machine_regs.is_stmt;
6876 adv = ! adv;
6877 printf (_(" Set is_stmt to %d\n"), adv);
6878 state_machine_regs.is_stmt = adv;
6879 break;
6881 case DW_LNS_set_basic_block:
6882 printf (_(" Set basic block\n"));
6883 state_machine_regs.basic_block = 1;
6884 break;
6886 case DW_LNS_const_add_pc:
6887 adv = (((255 - info.li_opcode_base) / info.li_line_range)
6888 * info.li_min_insn_length);
6889 state_machine_regs.address += adv;
6890 printf (_(" Advance PC by constant %d to 0x%lx\n"), adv,
6891 state_machine_regs.address);
6892 break;
6894 case DW_LNS_fixed_advance_pc:
6895 adv = byte_get (data, 2);
6896 data += 2;
6897 state_machine_regs.address += adv;
6898 printf (_(" Advance PC by fixed size amount %d to 0x%lx\n"),
6899 adv, state_machine_regs.address);
6900 break;
6902 case DW_LNS_set_prologue_end:
6903 printf (_(" Set prologue_end to true\n"));
6904 break;
6906 case DW_LNS_set_epilogue_begin:
6907 printf (_(" Set epilogue_begin to true\n"));
6908 break;
6910 case DW_LNS_set_isa:
6911 adv = read_leb128 (data, & bytes_read, 0);
6912 data += bytes_read;
6913 printf (_(" Set ISA to %d\n"), adv);
6914 break;
6916 default:
6917 printf (_(" Unknown opcode %d with operands: "), op_code);
6919 int i;
6920 for (i = standard_opcodes[op_code - 1]; i > 0 ; --i)
6922 printf ("0x%lx%s", read_leb128 (data, &bytes_read, 0),
6923 i == 1 ? "" : ", ");
6924 data += bytes_read;
6926 putchar ('\n');
6928 break;
6931 putchar ('\n');
6934 return 1;
6937 static int
6938 display_debug_pubnames (Elf_Internal_Shdr *section,
6939 unsigned char *start,
6940 FILE *file ATTRIBUTE_UNUSED)
6942 DWARF2_Internal_PubNames pubnames;
6943 unsigned char *end;
6945 end = start + section->sh_size;
6947 printf (_("Contents of the %s section:\n\n"), SECTION_NAME (section));
6949 while (start < end)
6951 unsigned char *data;
6952 unsigned long offset;
6953 int offset_size, initial_length_size;
6955 data = start;
6957 pubnames.pn_length = byte_get (data, 4);
6958 data += 4;
6959 if (pubnames.pn_length == 0xffffffff)
6961 pubnames.pn_length = byte_get (data, 8);
6962 data += 8;
6963 offset_size = 8;
6964 initial_length_size = 12;
6966 else
6968 offset_size = 4;
6969 initial_length_size = 4;
6972 pubnames.pn_version = byte_get (data, 2);
6973 data += 2;
6974 pubnames.pn_offset = byte_get (data, offset_size);
6975 data += offset_size;
6976 pubnames.pn_size = byte_get (data, offset_size);
6977 data += offset_size;
6979 start += pubnames.pn_length + initial_length_size;
6981 if (pubnames.pn_version != 2 && pubnames.pn_version != 3)
6983 static int warned = 0;
6985 if (! warned)
6987 warn (_("Only DWARF 2 and 3 pubnames are currently supported\n"));
6988 warned = 1;
6991 continue;
6994 printf (_(" Length: %ld\n"),
6995 pubnames.pn_length);
6996 printf (_(" Version: %d\n"),
6997 pubnames.pn_version);
6998 printf (_(" Offset into .debug_info section: %ld\n"),
6999 pubnames.pn_offset);
7000 printf (_(" Size of area in .debug_info section: %ld\n"),
7001 pubnames.pn_size);
7003 printf (_("\n Offset\tName\n"));
7007 offset = byte_get (data, offset_size);
7009 if (offset != 0)
7011 data += offset_size;
7012 printf (" %-6ld\t\t%s\n", offset, data);
7013 data += strlen ((char *) data) + 1;
7016 while (offset != 0);
7019 printf ("\n");
7020 return 1;
7023 static char *
7024 get_TAG_name (unsigned long tag)
7026 switch (tag)
7028 case DW_TAG_padding: return "DW_TAG_padding";
7029 case DW_TAG_array_type: return "DW_TAG_array_type";
7030 case DW_TAG_class_type: return "DW_TAG_class_type";
7031 case DW_TAG_entry_point: return "DW_TAG_entry_point";
7032 case DW_TAG_enumeration_type: return "DW_TAG_enumeration_type";
7033 case DW_TAG_formal_parameter: return "DW_TAG_formal_parameter";
7034 case DW_TAG_imported_declaration: return "DW_TAG_imported_declaration";
7035 case DW_TAG_label: return "DW_TAG_label";
7036 case DW_TAG_lexical_block: return "DW_TAG_lexical_block";
7037 case DW_TAG_member: return "DW_TAG_member";
7038 case DW_TAG_pointer_type: return "DW_TAG_pointer_type";
7039 case DW_TAG_reference_type: return "DW_TAG_reference_type";
7040 case DW_TAG_compile_unit: return "DW_TAG_compile_unit";
7041 case DW_TAG_string_type: return "DW_TAG_string_type";
7042 case DW_TAG_structure_type: return "DW_TAG_structure_type";
7043 case DW_TAG_subroutine_type: return "DW_TAG_subroutine_type";
7044 case DW_TAG_typedef: return "DW_TAG_typedef";
7045 case DW_TAG_union_type: return "DW_TAG_union_type";
7046 case DW_TAG_unspecified_parameters: return "DW_TAG_unspecified_parameters";
7047 case DW_TAG_variant: return "DW_TAG_variant";
7048 case DW_TAG_common_block: return "DW_TAG_common_block";
7049 case DW_TAG_common_inclusion: return "DW_TAG_common_inclusion";
7050 case DW_TAG_inheritance: return "DW_TAG_inheritance";
7051 case DW_TAG_inlined_subroutine: return "DW_TAG_inlined_subroutine";
7052 case DW_TAG_module: return "DW_TAG_module";
7053 case DW_TAG_ptr_to_member_type: return "DW_TAG_ptr_to_member_type";
7054 case DW_TAG_set_type: return "DW_TAG_set_type";
7055 case DW_TAG_subrange_type: return "DW_TAG_subrange_type";
7056 case DW_TAG_with_stmt: return "DW_TAG_with_stmt";
7057 case DW_TAG_access_declaration: return "DW_TAG_access_declaration";
7058 case DW_TAG_base_type: return "DW_TAG_base_type";
7059 case DW_TAG_catch_block: return "DW_TAG_catch_block";
7060 case DW_TAG_const_type: return "DW_TAG_const_type";
7061 case DW_TAG_constant: return "DW_TAG_constant";
7062 case DW_TAG_enumerator: return "DW_TAG_enumerator";
7063 case DW_TAG_file_type: return "DW_TAG_file_type";
7064 case DW_TAG_friend: return "DW_TAG_friend";
7065 case DW_TAG_namelist: return "DW_TAG_namelist";
7066 case DW_TAG_namelist_item: return "DW_TAG_namelist_item";
7067 case DW_TAG_packed_type: return "DW_TAG_packed_type";
7068 case DW_TAG_subprogram: return "DW_TAG_subprogram";
7069 case DW_TAG_template_type_param: return "DW_TAG_template_type_param";
7070 case DW_TAG_template_value_param: return "DW_TAG_template_value_param";
7071 case DW_TAG_thrown_type: return "DW_TAG_thrown_type";
7072 case DW_TAG_try_block: return "DW_TAG_try_block";
7073 case DW_TAG_variant_part: return "DW_TAG_variant_part";
7074 case DW_TAG_variable: return "DW_TAG_variable";
7075 case DW_TAG_volatile_type: return "DW_TAG_volatile_type";
7076 case DW_TAG_MIPS_loop: return "DW_TAG_MIPS_loop";
7077 case DW_TAG_format_label: return "DW_TAG_format_label";
7078 case DW_TAG_function_template: return "DW_TAG_function_template";
7079 case DW_TAG_class_template: return "DW_TAG_class_template";
7080 /* DWARF 2.1 values. */
7081 case DW_TAG_dwarf_procedure: return "DW_TAG_dwarf_procedure";
7082 case DW_TAG_restrict_type: return "DW_TAG_restrict_type";
7083 case DW_TAG_interface_type: return "DW_TAG_interface_type";
7084 case DW_TAG_namespace: return "DW_TAG_namespace";
7085 case DW_TAG_imported_module: return "DW_TAG_imported_module";
7086 case DW_TAG_unspecified_type: return "DW_TAG_unspecified_type";
7087 case DW_TAG_partial_unit: return "DW_TAG_partial_unit";
7088 case DW_TAG_imported_unit: return "DW_TAG_imported_unit";
7089 /* UPC values. */
7090 case DW_TAG_upc_shared_type: return "DW_TAG_upc_shared_type";
7091 case DW_TAG_upc_strict_type: return "DW_TAG_upc_strict_type";
7092 case DW_TAG_upc_relaxed_type: return "DW_TAG_upc_relaxed_type";
7093 default:
7095 static char buffer[100];
7097 sprintf (buffer, _("Unknown TAG value: %lx"), tag);
7098 return buffer;
7103 static char *
7104 get_AT_name (unsigned long attribute)
7106 switch (attribute)
7108 case DW_AT_sibling: return "DW_AT_sibling";
7109 case DW_AT_location: return "DW_AT_location";
7110 case DW_AT_name: return "DW_AT_name";
7111 case DW_AT_ordering: return "DW_AT_ordering";
7112 case DW_AT_subscr_data: return "DW_AT_subscr_data";
7113 case DW_AT_byte_size: return "DW_AT_byte_size";
7114 case DW_AT_bit_offset: return "DW_AT_bit_offset";
7115 case DW_AT_bit_size: return "DW_AT_bit_size";
7116 case DW_AT_element_list: return "DW_AT_element_list";
7117 case DW_AT_stmt_list: return "DW_AT_stmt_list";
7118 case DW_AT_low_pc: return "DW_AT_low_pc";
7119 case DW_AT_high_pc: return "DW_AT_high_pc";
7120 case DW_AT_language: return "DW_AT_language";
7121 case DW_AT_member: return "DW_AT_member";
7122 case DW_AT_discr: return "DW_AT_discr";
7123 case DW_AT_discr_value: return "DW_AT_discr_value";
7124 case DW_AT_visibility: return "DW_AT_visibility";
7125 case DW_AT_import: return "DW_AT_import";
7126 case DW_AT_string_length: return "DW_AT_string_length";
7127 case DW_AT_common_reference: return "DW_AT_common_reference";
7128 case DW_AT_comp_dir: return "DW_AT_comp_dir";
7129 case DW_AT_const_value: return "DW_AT_const_value";
7130 case DW_AT_containing_type: return "DW_AT_containing_type";
7131 case DW_AT_default_value: return "DW_AT_default_value";
7132 case DW_AT_inline: return "DW_AT_inline";
7133 case DW_AT_is_optional: return "DW_AT_is_optional";
7134 case DW_AT_lower_bound: return "DW_AT_lower_bound";
7135 case DW_AT_producer: return "DW_AT_producer";
7136 case DW_AT_prototyped: return "DW_AT_prototyped";
7137 case DW_AT_return_addr: return "DW_AT_return_addr";
7138 case DW_AT_start_scope: return "DW_AT_start_scope";
7139 case DW_AT_stride_size: return "DW_AT_stride_size";
7140 case DW_AT_upper_bound: return "DW_AT_upper_bound";
7141 case DW_AT_abstract_origin: return "DW_AT_abstract_origin";
7142 case DW_AT_accessibility: return "DW_AT_accessibility";
7143 case DW_AT_address_class: return "DW_AT_address_class";
7144 case DW_AT_artificial: return "DW_AT_artificial";
7145 case DW_AT_base_types: return "DW_AT_base_types";
7146 case DW_AT_calling_convention: return "DW_AT_calling_convention";
7147 case DW_AT_count: return "DW_AT_count";
7148 case DW_AT_data_member_location: return "DW_AT_data_member_location";
7149 case DW_AT_decl_column: return "DW_AT_decl_column";
7150 case DW_AT_decl_file: return "DW_AT_decl_file";
7151 case DW_AT_decl_line: return "DW_AT_decl_line";
7152 case DW_AT_declaration: return "DW_AT_declaration";
7153 case DW_AT_discr_list: return "DW_AT_discr_list";
7154 case DW_AT_encoding: return "DW_AT_encoding";
7155 case DW_AT_external: return "DW_AT_external";
7156 case DW_AT_frame_base: return "DW_AT_frame_base";
7157 case DW_AT_friend: return "DW_AT_friend";
7158 case DW_AT_identifier_case: return "DW_AT_identifier_case";
7159 case DW_AT_macro_info: return "DW_AT_macro_info";
7160 case DW_AT_namelist_items: return "DW_AT_namelist_items";
7161 case DW_AT_priority: return "DW_AT_priority";
7162 case DW_AT_segment: return "DW_AT_segment";
7163 case DW_AT_specification: return "DW_AT_specification";
7164 case DW_AT_static_link: return "DW_AT_static_link";
7165 case DW_AT_type: return "DW_AT_type";
7166 case DW_AT_use_location: return "DW_AT_use_location";
7167 case DW_AT_variable_parameter: return "DW_AT_variable_parameter";
7168 case DW_AT_virtuality: return "DW_AT_virtuality";
7169 case DW_AT_vtable_elem_location: return "DW_AT_vtable_elem_location";
7170 /* DWARF 2.1 values. */
7171 case DW_AT_allocated: return "DW_AT_allocated";
7172 case DW_AT_associated: return "DW_AT_associated";
7173 case DW_AT_data_location: return "DW_AT_data_location";
7174 case DW_AT_stride: return "DW_AT_stride";
7175 case DW_AT_entry_pc: return "DW_AT_entry_pc";
7176 case DW_AT_use_UTF8: return "DW_AT_use_UTF8";
7177 case DW_AT_extension: return "DW_AT_extension";
7178 case DW_AT_ranges: return "DW_AT_ranges";
7179 case DW_AT_trampoline: return "DW_AT_trampoline";
7180 case DW_AT_call_column: return "DW_AT_call_column";
7181 case DW_AT_call_file: return "DW_AT_call_file";
7182 case DW_AT_call_line: return "DW_AT_call_line";
7183 /* SGI/MIPS extensions. */
7184 case DW_AT_MIPS_fde: return "DW_AT_MIPS_fde";
7185 case DW_AT_MIPS_loop_begin: return "DW_AT_MIPS_loop_begin";
7186 case DW_AT_MIPS_tail_loop_begin: return "DW_AT_MIPS_tail_loop_begin";
7187 case DW_AT_MIPS_epilog_begin: return "DW_AT_MIPS_epilog_begin";
7188 case DW_AT_MIPS_loop_unroll_factor: return "DW_AT_MIPS_loop_unroll_factor";
7189 case DW_AT_MIPS_software_pipeline_depth:
7190 return "DW_AT_MIPS_software_pipeline_depth";
7191 case DW_AT_MIPS_linkage_name: return "DW_AT_MIPS_linkage_name";
7192 case DW_AT_MIPS_stride: return "DW_AT_MIPS_stride";
7193 case DW_AT_MIPS_abstract_name: return "DW_AT_MIPS_abstract_name";
7194 case DW_AT_MIPS_clone_origin: return "DW_AT_MIPS_clone_origin";
7195 case DW_AT_MIPS_has_inlines: return "DW_AT_MIPS_has_inlines";
7196 /* GNU extensions. */
7197 case DW_AT_sf_names: return "DW_AT_sf_names";
7198 case DW_AT_src_info: return "DW_AT_src_info";
7199 case DW_AT_mac_info: return "DW_AT_mac_info";
7200 case DW_AT_src_coords: return "DW_AT_src_coords";
7201 case DW_AT_body_begin: return "DW_AT_body_begin";
7202 case DW_AT_body_end: return "DW_AT_body_end";
7203 case DW_AT_GNU_vector: return "DW_AT_GNU_vector";
7204 /* UPC extension. */
7205 case DW_AT_upc_threads_scaled: return "DW_AT_upc_threads_scaled";
7206 default:
7208 static char buffer[100];
7210 sprintf (buffer, _("Unknown AT value: %lx"), attribute);
7211 return buffer;
7216 static char *
7217 get_FORM_name (unsigned long form)
7219 switch (form)
7221 case DW_FORM_addr: return "DW_FORM_addr";
7222 case DW_FORM_block2: return "DW_FORM_block2";
7223 case DW_FORM_block4: return "DW_FORM_block4";
7224 case DW_FORM_data2: return "DW_FORM_data2";
7225 case DW_FORM_data4: return "DW_FORM_data4";
7226 case DW_FORM_data8: return "DW_FORM_data8";
7227 case DW_FORM_string: return "DW_FORM_string";
7228 case DW_FORM_block: return "DW_FORM_block";
7229 case DW_FORM_block1: return "DW_FORM_block1";
7230 case DW_FORM_data1: return "DW_FORM_data1";
7231 case DW_FORM_flag: return "DW_FORM_flag";
7232 case DW_FORM_sdata: return "DW_FORM_sdata";
7233 case DW_FORM_strp: return "DW_FORM_strp";
7234 case DW_FORM_udata: return "DW_FORM_udata";
7235 case DW_FORM_ref_addr: return "DW_FORM_ref_addr";
7236 case DW_FORM_ref1: return "DW_FORM_ref1";
7237 case DW_FORM_ref2: return "DW_FORM_ref2";
7238 case DW_FORM_ref4: return "DW_FORM_ref4";
7239 case DW_FORM_ref8: return "DW_FORM_ref8";
7240 case DW_FORM_ref_udata: return "DW_FORM_ref_udata";
7241 case DW_FORM_indirect: return "DW_FORM_indirect";
7242 default:
7244 static char buffer[100];
7246 sprintf (buffer, _("Unknown FORM value: %lx"), form);
7247 return buffer;
7252 /* FIXME: There are better and more efficient ways to handle
7253 these structures. For now though, I just want something that
7254 is simple to implement. */
7255 typedef struct abbrev_attr
7257 unsigned long attribute;
7258 unsigned long form;
7259 struct abbrev_attr *next;
7261 abbrev_attr;
7263 typedef struct abbrev_entry
7265 unsigned long entry;
7266 unsigned long tag;
7267 int children;
7268 struct abbrev_attr *first_attr;
7269 struct abbrev_attr *last_attr;
7270 struct abbrev_entry *next;
7272 abbrev_entry;
7274 static abbrev_entry *first_abbrev = NULL;
7275 static abbrev_entry *last_abbrev = NULL;
7277 static void
7278 free_abbrevs (void)
7280 abbrev_entry *abbrev;
7282 for (abbrev = first_abbrev; abbrev;)
7284 abbrev_entry *next = abbrev->next;
7285 abbrev_attr *attr;
7287 for (attr = abbrev->first_attr; attr;)
7289 abbrev_attr *next = attr->next;
7291 free (attr);
7292 attr = next;
7295 free (abbrev);
7296 abbrev = next;
7299 last_abbrev = first_abbrev = NULL;
7302 static void
7303 add_abbrev (unsigned long number, unsigned long tag, int children)
7305 abbrev_entry *entry;
7307 entry = malloc (sizeof (*entry));
7309 if (entry == NULL)
7310 /* ugg */
7311 return;
7313 entry->entry = number;
7314 entry->tag = tag;
7315 entry->children = children;
7316 entry->first_attr = NULL;
7317 entry->last_attr = NULL;
7318 entry->next = NULL;
7320 if (first_abbrev == NULL)
7321 first_abbrev = entry;
7322 else
7323 last_abbrev->next = entry;
7325 last_abbrev = entry;
7328 static void
7329 add_abbrev_attr (unsigned long attribute, unsigned long form)
7331 abbrev_attr *attr;
7333 attr = malloc (sizeof (*attr));
7335 if (attr == NULL)
7336 /* ugg */
7337 return;
7339 attr->attribute = attribute;
7340 attr->form = form;
7341 attr->next = NULL;
7343 if (last_abbrev->first_attr == NULL)
7344 last_abbrev->first_attr = attr;
7345 else
7346 last_abbrev->last_attr->next = attr;
7348 last_abbrev->last_attr = attr;
7351 /* Processes the (partial) contents of a .debug_abbrev section.
7352 Returns NULL if the end of the section was encountered.
7353 Returns the address after the last byte read if the end of
7354 an abbreviation set was found. */
7356 static unsigned char *
7357 process_abbrev_section (unsigned char *start, unsigned char *end)
7359 if (first_abbrev != NULL)
7360 return NULL;
7362 while (start < end)
7364 int bytes_read;
7365 unsigned long entry;
7366 unsigned long tag;
7367 unsigned long attribute;
7368 int children;
7370 entry = read_leb128 (start, & bytes_read, 0);
7371 start += bytes_read;
7373 /* A single zero is supposed to end the section according
7374 to the standard. If there's more, then signal that to
7375 the caller. */
7376 if (entry == 0)
7377 return start == end ? NULL : start;
7379 tag = read_leb128 (start, & bytes_read, 0);
7380 start += bytes_read;
7382 children = *start++;
7384 add_abbrev (entry, tag, children);
7388 unsigned long form;
7390 attribute = read_leb128 (start, & bytes_read, 0);
7391 start += bytes_read;
7393 form = read_leb128 (start, & bytes_read, 0);
7394 start += bytes_read;
7396 if (attribute != 0)
7397 add_abbrev_attr (attribute, form);
7399 while (attribute != 0);
7402 return NULL;
7406 static int
7407 display_debug_macinfo (Elf_Internal_Shdr *section,
7408 unsigned char *start,
7409 FILE *file ATTRIBUTE_UNUSED)
7411 unsigned char *end = start + section->sh_size;
7412 unsigned char *curr = start;
7413 unsigned int bytes_read;
7414 enum dwarf_macinfo_record_type op;
7416 printf (_("Contents of the %s section:\n\n"), SECTION_NAME (section));
7418 while (curr < end)
7420 unsigned int lineno;
7421 const char *string;
7423 op = *curr;
7424 curr++;
7426 switch (op)
7428 case DW_MACINFO_start_file:
7430 unsigned int filenum;
7432 lineno = read_leb128 (curr, & bytes_read, 0);
7433 curr += bytes_read;
7434 filenum = read_leb128 (curr, & bytes_read, 0);
7435 curr += bytes_read;
7437 printf (_(" DW_MACINFO_start_file - lineno: %d filenum: %d\n"), lineno, filenum);
7439 break;
7441 case DW_MACINFO_end_file:
7442 printf (_(" DW_MACINFO_end_file\n"));
7443 break;
7445 case DW_MACINFO_define:
7446 lineno = read_leb128 (curr, & bytes_read, 0);
7447 curr += bytes_read;
7448 string = curr;
7449 curr += strlen (string) + 1;
7450 printf (_(" DW_MACINFO_define - lineno : %d macro : %s\n"), lineno, string);
7451 break;
7453 case DW_MACINFO_undef:
7454 lineno = read_leb128 (curr, & bytes_read, 0);
7455 curr += bytes_read;
7456 string = curr;
7457 curr += strlen (string) + 1;
7458 printf (_(" DW_MACINFO_undef - lineno : %d macro : %s\n"), lineno, string);
7459 break;
7461 case DW_MACINFO_vendor_ext:
7463 unsigned int constant;
7465 constant = read_leb128 (curr, & bytes_read, 0);
7466 curr += bytes_read;
7467 string = curr;
7468 curr += strlen (string) + 1;
7469 printf (_(" DW_MACINFO_vendor_ext - constant : %d string : %s\n"), constant, string);
7471 break;
7475 return 1;
7479 static int
7480 display_debug_abbrev (Elf_Internal_Shdr *section,
7481 unsigned char *start,
7482 FILE *file ATTRIBUTE_UNUSED)
7484 abbrev_entry *entry;
7485 unsigned char *end = start + section->sh_size;
7487 printf (_("Contents of the %s section:\n\n"), SECTION_NAME (section));
7491 start = process_abbrev_section (start, end);
7493 if (first_abbrev == NULL)
7494 continue;
7496 printf (_(" Number TAG\n"));
7498 for (entry = first_abbrev; entry; entry = entry->next)
7500 abbrev_attr *attr;
7502 printf (_(" %ld %s [%s]\n"),
7503 entry->entry,
7504 get_TAG_name (entry->tag),
7505 entry->children ? _("has children") : _("no children"));
7507 for (attr = entry->first_attr; attr; attr = attr->next)
7509 printf (_(" %-18s %s\n"),
7510 get_AT_name (attr->attribute),
7511 get_FORM_name (attr->form));
7515 free_abbrevs ();
7517 while (start);
7519 printf ("\n");
7521 return 1;
7525 static unsigned char *
7526 display_block (unsigned char *data, unsigned long length)
7528 printf (_(" %lu byte block: "), length);
7530 while (length --)
7531 printf ("%lx ", (unsigned long) byte_get (data++, 1));
7533 return data;
7536 static void
7537 decode_location_expression (unsigned char * data,
7538 unsigned int pointer_size,
7539 unsigned long length)
7541 unsigned op;
7542 int bytes_read;
7543 unsigned long uvalue;
7544 unsigned char *end = data + length;
7546 while (data < end)
7548 op = *data++;
7550 switch (op)
7552 case DW_OP_addr:
7553 printf ("DW_OP_addr: %lx",
7554 (unsigned long) byte_get (data, pointer_size));
7555 data += pointer_size;
7556 break;
7557 case DW_OP_deref:
7558 printf ("DW_OP_deref");
7559 break;
7560 case DW_OP_const1u:
7561 printf ("DW_OP_const1u: %lu", (unsigned long) byte_get (data++, 1));
7562 break;
7563 case DW_OP_const1s:
7564 printf ("DW_OP_const1s: %ld", (long) byte_get (data++, 1));
7565 break;
7566 case DW_OP_const2u:
7567 printf ("DW_OP_const2u: %lu", (unsigned long) byte_get (data, 2));
7568 data += 2;
7569 break;
7570 case DW_OP_const2s:
7571 printf ("DW_OP_const2s: %ld", (long) byte_get (data, 2));
7572 data += 2;
7573 break;
7574 case DW_OP_const4u:
7575 printf ("DW_OP_const4u: %lu", (unsigned long) byte_get (data, 4));
7576 data += 4;
7577 break;
7578 case DW_OP_const4s:
7579 printf ("DW_OP_const4s: %ld", (long) byte_get (data, 4));
7580 data += 4;
7581 break;
7582 case DW_OP_const8u:
7583 printf ("DW_OP_const8u: %lu %lu", (unsigned long) byte_get (data, 4),
7584 (unsigned long) byte_get (data + 4, 4));
7585 data += 8;
7586 break;
7587 case DW_OP_const8s:
7588 printf ("DW_OP_const8s: %ld %ld", (long) byte_get (data, 4),
7589 (long) byte_get (data + 4, 4));
7590 data += 8;
7591 break;
7592 case DW_OP_constu:
7593 printf ("DW_OP_constu: %lu", read_leb128 (data, &bytes_read, 0));
7594 data += bytes_read;
7595 break;
7596 case DW_OP_consts:
7597 printf ("DW_OP_consts: %ld", read_leb128 (data, &bytes_read, 1));
7598 data += bytes_read;
7599 break;
7600 case DW_OP_dup:
7601 printf ("DW_OP_dup");
7602 break;
7603 case DW_OP_drop:
7604 printf ("DW_OP_drop");
7605 break;
7606 case DW_OP_over:
7607 printf ("DW_OP_over");
7608 break;
7609 case DW_OP_pick:
7610 printf ("DW_OP_pick: %ld", (unsigned long) byte_get (data++, 1));
7611 break;
7612 case DW_OP_swap:
7613 printf ("DW_OP_swap");
7614 break;
7615 case DW_OP_rot:
7616 printf ("DW_OP_rot");
7617 break;
7618 case DW_OP_xderef:
7619 printf ("DW_OP_xderef");
7620 break;
7621 case DW_OP_abs:
7622 printf ("DW_OP_abs");
7623 break;
7624 case DW_OP_and:
7625 printf ("DW_OP_and");
7626 break;
7627 case DW_OP_div:
7628 printf ("DW_OP_div");
7629 break;
7630 case DW_OP_minus:
7631 printf ("DW_OP_minus");
7632 break;
7633 case DW_OP_mod:
7634 printf ("DW_OP_mod");
7635 break;
7636 case DW_OP_mul:
7637 printf ("DW_OP_mul");
7638 break;
7639 case DW_OP_neg:
7640 printf ("DW_OP_neg");
7641 break;
7642 case DW_OP_not:
7643 printf ("DW_OP_not");
7644 break;
7645 case DW_OP_or:
7646 printf ("DW_OP_or");
7647 break;
7648 case DW_OP_plus:
7649 printf ("DW_OP_plus");
7650 break;
7651 case DW_OP_plus_uconst:
7652 printf ("DW_OP_plus_uconst: %lu",
7653 read_leb128 (data, &bytes_read, 0));
7654 data += bytes_read;
7655 break;
7656 case DW_OP_shl:
7657 printf ("DW_OP_shl");
7658 break;
7659 case DW_OP_shr:
7660 printf ("DW_OP_shr");
7661 break;
7662 case DW_OP_shra:
7663 printf ("DW_OP_shra");
7664 break;
7665 case DW_OP_xor:
7666 printf ("DW_OP_xor");
7667 break;
7668 case DW_OP_bra:
7669 printf ("DW_OP_bra: %ld", (long) byte_get (data, 2));
7670 data += 2;
7671 break;
7672 case DW_OP_eq:
7673 printf ("DW_OP_eq");
7674 break;
7675 case DW_OP_ge:
7676 printf ("DW_OP_ge");
7677 break;
7678 case DW_OP_gt:
7679 printf ("DW_OP_gt");
7680 break;
7681 case DW_OP_le:
7682 printf ("DW_OP_le");
7683 break;
7684 case DW_OP_lt:
7685 printf ("DW_OP_lt");
7686 break;
7687 case DW_OP_ne:
7688 printf ("DW_OP_ne");
7689 break;
7690 case DW_OP_skip:
7691 printf ("DW_OP_skip: %ld", (long) byte_get (data, 2));
7692 data += 2;
7693 break;
7695 case DW_OP_lit0:
7696 case DW_OP_lit1:
7697 case DW_OP_lit2:
7698 case DW_OP_lit3:
7699 case DW_OP_lit4:
7700 case DW_OP_lit5:
7701 case DW_OP_lit6:
7702 case DW_OP_lit7:
7703 case DW_OP_lit8:
7704 case DW_OP_lit9:
7705 case DW_OP_lit10:
7706 case DW_OP_lit11:
7707 case DW_OP_lit12:
7708 case DW_OP_lit13:
7709 case DW_OP_lit14:
7710 case DW_OP_lit15:
7711 case DW_OP_lit16:
7712 case DW_OP_lit17:
7713 case DW_OP_lit18:
7714 case DW_OP_lit19:
7715 case DW_OP_lit20:
7716 case DW_OP_lit21:
7717 case DW_OP_lit22:
7718 case DW_OP_lit23:
7719 case DW_OP_lit24:
7720 case DW_OP_lit25:
7721 case DW_OP_lit26:
7722 case DW_OP_lit27:
7723 case DW_OP_lit28:
7724 case DW_OP_lit29:
7725 case DW_OP_lit30:
7726 case DW_OP_lit31:
7727 printf ("DW_OP_lit%d", op - DW_OP_lit0);
7728 break;
7730 case DW_OP_reg0:
7731 case DW_OP_reg1:
7732 case DW_OP_reg2:
7733 case DW_OP_reg3:
7734 case DW_OP_reg4:
7735 case DW_OP_reg5:
7736 case DW_OP_reg6:
7737 case DW_OP_reg7:
7738 case DW_OP_reg8:
7739 case DW_OP_reg9:
7740 case DW_OP_reg10:
7741 case DW_OP_reg11:
7742 case DW_OP_reg12:
7743 case DW_OP_reg13:
7744 case DW_OP_reg14:
7745 case DW_OP_reg15:
7746 case DW_OP_reg16:
7747 case DW_OP_reg17:
7748 case DW_OP_reg18:
7749 case DW_OP_reg19:
7750 case DW_OP_reg20:
7751 case DW_OP_reg21:
7752 case DW_OP_reg22:
7753 case DW_OP_reg23:
7754 case DW_OP_reg24:
7755 case DW_OP_reg25:
7756 case DW_OP_reg26:
7757 case DW_OP_reg27:
7758 case DW_OP_reg28:
7759 case DW_OP_reg29:
7760 case DW_OP_reg30:
7761 case DW_OP_reg31:
7762 printf ("DW_OP_reg%d", op - DW_OP_reg0);
7763 break;
7765 case DW_OP_breg0:
7766 case DW_OP_breg1:
7767 case DW_OP_breg2:
7768 case DW_OP_breg3:
7769 case DW_OP_breg4:
7770 case DW_OP_breg5:
7771 case DW_OP_breg6:
7772 case DW_OP_breg7:
7773 case DW_OP_breg8:
7774 case DW_OP_breg9:
7775 case DW_OP_breg10:
7776 case DW_OP_breg11:
7777 case DW_OP_breg12:
7778 case DW_OP_breg13:
7779 case DW_OP_breg14:
7780 case DW_OP_breg15:
7781 case DW_OP_breg16:
7782 case DW_OP_breg17:
7783 case DW_OP_breg18:
7784 case DW_OP_breg19:
7785 case DW_OP_breg20:
7786 case DW_OP_breg21:
7787 case DW_OP_breg22:
7788 case DW_OP_breg23:
7789 case DW_OP_breg24:
7790 case DW_OP_breg25:
7791 case DW_OP_breg26:
7792 case DW_OP_breg27:
7793 case DW_OP_breg28:
7794 case DW_OP_breg29:
7795 case DW_OP_breg30:
7796 case DW_OP_breg31:
7797 printf ("DW_OP_breg%d: %ld", op - DW_OP_breg0,
7798 read_leb128 (data, &bytes_read, 1));
7799 data += bytes_read;
7800 break;
7802 case DW_OP_regx:
7803 printf ("DW_OP_regx: %lu", read_leb128 (data, &bytes_read, 0));
7804 data += bytes_read;
7805 break;
7806 case DW_OP_fbreg:
7807 printf ("DW_OP_fbreg: %ld", read_leb128 (data, &bytes_read, 1));
7808 data += bytes_read;
7809 break;
7810 case DW_OP_bregx:
7811 uvalue = read_leb128 (data, &bytes_read, 0);
7812 data += bytes_read;
7813 printf ("DW_OP_bregx: %lu %ld", uvalue,
7814 read_leb128 (data, &bytes_read, 1));
7815 data += bytes_read;
7816 break;
7817 case DW_OP_piece:
7818 printf ("DW_OP_piece: %lu", read_leb128 (data, &bytes_read, 0));
7819 data += bytes_read;
7820 break;
7821 case DW_OP_deref_size:
7822 printf ("DW_OP_deref_size: %ld", (long) byte_get (data++, 1));
7823 break;
7824 case DW_OP_xderef_size:
7825 printf ("DW_OP_xderef_size: %ld", (long) byte_get (data++, 1));
7826 break;
7827 case DW_OP_nop:
7828 printf ("DW_OP_nop");
7829 break;
7831 /* DWARF 3 extensions. */
7832 case DW_OP_push_object_address:
7833 printf ("DW_OP_push_object_address");
7834 break;
7835 case DW_OP_call2:
7836 printf ("DW_OP_call2: <%lx>", (long) byte_get (data, 2));
7837 data += 2;
7838 break;
7839 case DW_OP_call4:
7840 printf ("DW_OP_call4: <%lx>", (long) byte_get (data, 4));
7841 data += 4;
7842 break;
7843 case DW_OP_call_ref:
7844 printf ("DW_OP_call_ref");
7845 break;
7847 /* GNU extensions. */
7848 case DW_OP_GNU_push_tls_address:
7849 printf ("DW_OP_GNU_push_tls_address");
7850 break;
7852 default:
7853 if (op >= DW_OP_lo_user
7854 && op <= DW_OP_hi_user)
7855 printf (_("(User defined location op)"));
7856 else
7857 printf (_("(Unknown location op)"));
7858 /* No way to tell where the next op is, so just bail. */
7859 return;
7862 /* Separate the ops. */
7863 if (data < end)
7864 printf ("; ");
7868 static const char *debug_loc_contents;
7869 static bfd_vma debug_loc_size;
7871 static void
7872 load_debug_loc (FILE *file)
7874 Elf_Internal_Shdr *sec;
7876 /* If it is already loaded, do nothing. */
7877 if (debug_loc_contents != NULL)
7878 return;
7880 /* Locate the .debug_loc section. */
7881 sec = find_section (".debug_loc");
7882 if (sec == NULL)
7883 return;
7885 debug_loc_size = sec->sh_size;
7887 debug_loc_contents = get_data (NULL, file, sec->sh_offset, sec->sh_size,
7888 _("debug_loc section data"));
7891 static void
7892 free_debug_loc (void)
7894 if (debug_loc_contents == NULL)
7895 return;
7897 free ((char *) debug_loc_contents);
7898 debug_loc_contents = NULL;
7899 debug_loc_size = 0;
7903 static int
7904 display_debug_loc (Elf_Internal_Shdr *section,
7905 unsigned char *start, FILE *file)
7907 unsigned char *section_end;
7908 unsigned long bytes;
7909 unsigned char *section_begin = start;
7910 bfd_vma addr;
7911 unsigned int comp_unit = 0;
7913 addr = section->sh_addr;
7914 bytes = section->sh_size;
7915 section_end = start + bytes;
7917 if (bytes == 0)
7919 printf (_("\nThe .debug_loc section is empty.\n"));
7920 return 0;
7923 if (num_debug_line_pointer_sizes == 0)
7924 get_debug_line_pointer_sizes (file);
7926 printf (_("Contents of the .debug_loc section:\n\n"));
7927 printf (_("\n Offset Begin End Expression\n"));
7929 while (start < section_end)
7931 unsigned long begin;
7932 unsigned long end;
7933 unsigned short length;
7934 unsigned long offset;
7935 unsigned int pointer_size;
7937 offset = start - section_begin;
7939 /* Get the pointer size from the comp unit associated
7940 with this block of location information. */
7941 if (comp_unit >= num_debug_line_pointer_sizes)
7943 error (_("Not enough comp units for .debug_loc section\n"));
7944 return 0;
7946 else
7948 pointer_size = debug_line_pointer_sizes [comp_unit];
7949 comp_unit ++;
7952 while (1)
7954 begin = byte_get (start, pointer_size);
7955 start += pointer_size;
7956 end = byte_get (start, pointer_size);
7957 start += pointer_size;
7959 if (begin == 0 && end == 0)
7960 break;
7962 /* For now, skip any base address specifiers. */
7963 if (begin == 0xffffffff)
7964 continue;
7966 begin += addr;
7967 end += addr;
7969 length = byte_get (start, 2);
7970 start += 2;
7972 printf (" %8.8lx %8.8lx %8.8lx (", offset, begin, end);
7973 decode_location_expression (start, pointer_size, length);
7974 printf (")\n");
7976 start += length;
7978 printf ("\n");
7980 return 1;
7983 static const char *debug_str_contents;
7984 static bfd_vma debug_str_size;
7986 static void
7987 load_debug_str (FILE *file)
7989 Elf_Internal_Shdr *sec;
7991 /* If it is already loaded, do nothing. */
7992 if (debug_str_contents != NULL)
7993 return;
7995 /* Locate the .debug_str section. */
7996 sec = find_section (".debug_str");
7997 if (sec == NULL)
7998 return;
8000 debug_str_size = sec->sh_size;
8002 debug_str_contents = get_data (NULL, file, sec->sh_offset, sec->sh_size,
8003 _("debug_str section data"));
8006 static void
8007 free_debug_str (void)
8009 if (debug_str_contents == NULL)
8010 return;
8012 free ((char *) debug_str_contents);
8013 debug_str_contents = NULL;
8014 debug_str_size = 0;
8017 static const char *
8018 fetch_indirect_string (unsigned long offset)
8020 if (debug_str_contents == NULL)
8021 return _("<no .debug_str section>");
8023 if (offset > debug_str_size)
8024 return _("<offset is too big>");
8026 return debug_str_contents + offset;
8029 static int
8030 display_debug_str (Elf_Internal_Shdr *section,
8031 unsigned char *start,
8032 FILE *file ATTRIBUTE_UNUSED)
8034 unsigned long bytes;
8035 bfd_vma addr;
8037 addr = section->sh_addr;
8038 bytes = section->sh_size;
8040 if (bytes == 0)
8042 printf (_("\nThe .debug_str section is empty.\n"));
8043 return 0;
8046 printf (_("Contents of the .debug_str section:\n\n"));
8048 while (bytes)
8050 int j;
8051 int k;
8052 int lbytes;
8054 lbytes = (bytes > 16 ? 16 : bytes);
8056 printf (" 0x%8.8lx ", (unsigned long) addr);
8058 for (j = 0; j < 16; j++)
8060 if (j < lbytes)
8061 printf ("%2.2x", start[j]);
8062 else
8063 printf (" ");
8065 if ((j & 3) == 3)
8066 printf (" ");
8069 for (j = 0; j < lbytes; j++)
8071 k = start[j];
8072 if (k >= ' ' && k < 0x80)
8073 printf ("%c", k);
8074 else
8075 printf (".");
8078 putchar ('\n');
8080 start += lbytes;
8081 addr += lbytes;
8082 bytes -= lbytes;
8085 return 1;
8088 static unsigned char *
8089 read_and_display_attr_value (unsigned long attribute,
8090 unsigned long form,
8091 unsigned char *data,
8092 unsigned long cu_offset,
8093 unsigned long pointer_size,
8094 unsigned long offset_size,
8095 int dwarf_version)
8097 unsigned long uvalue = 0;
8098 unsigned char *block_start = NULL;
8099 int bytes_read;
8101 switch (form)
8103 default:
8104 break;
8106 case DW_FORM_ref_addr:
8107 if (dwarf_version == 2)
8109 uvalue = byte_get (data, pointer_size);
8110 data += pointer_size;
8112 else if (dwarf_version == 3)
8114 uvalue = byte_get (data, offset_size);
8115 data += offset_size;
8117 else
8119 error (_("Internal error: DWARF version is not 2 or 3.\n"));
8121 break;
8123 case DW_FORM_addr:
8124 uvalue = byte_get (data, pointer_size);
8125 data += pointer_size;
8126 break;
8128 case DW_FORM_strp:
8129 uvalue = byte_get (data, offset_size);
8130 data += offset_size;
8131 break;
8133 case DW_FORM_ref1:
8134 case DW_FORM_flag:
8135 case DW_FORM_data1:
8136 uvalue = byte_get (data++, 1);
8137 break;
8139 case DW_FORM_ref2:
8140 case DW_FORM_data2:
8141 uvalue = byte_get (data, 2);
8142 data += 2;
8143 break;
8145 case DW_FORM_ref4:
8146 case DW_FORM_data4:
8147 uvalue = byte_get (data, 4);
8148 data += 4;
8149 break;
8151 case DW_FORM_sdata:
8152 uvalue = read_leb128 (data, & bytes_read, 1);
8153 data += bytes_read;
8154 break;
8156 case DW_FORM_ref_udata:
8157 case DW_FORM_udata:
8158 uvalue = read_leb128 (data, & bytes_read, 0);
8159 data += bytes_read;
8160 break;
8162 case DW_FORM_indirect:
8163 form = read_leb128 (data, & bytes_read, 0);
8164 data += bytes_read;
8165 printf (" %s", get_FORM_name (form));
8166 return read_and_display_attr_value (attribute, form, data, cu_offset,
8167 pointer_size, offset_size,
8168 dwarf_version);
8171 switch (form)
8173 case DW_FORM_ref_addr:
8174 printf (" <#%lx>", uvalue);
8175 break;
8177 case DW_FORM_ref1:
8178 case DW_FORM_ref2:
8179 case DW_FORM_ref4:
8180 case DW_FORM_ref_udata:
8181 printf (" <%lx>", uvalue + cu_offset);
8182 break;
8184 case DW_FORM_addr:
8185 printf (" %#lx", uvalue);
8186 break;
8188 case DW_FORM_flag:
8189 case DW_FORM_data1:
8190 case DW_FORM_data2:
8191 case DW_FORM_data4:
8192 case DW_FORM_sdata:
8193 case DW_FORM_udata:
8194 printf (" %ld", uvalue);
8195 break;
8197 case DW_FORM_ref8:
8198 case DW_FORM_data8:
8199 uvalue = byte_get (data, 4);
8200 printf (" %lx", uvalue);
8201 printf (" %lx", (unsigned long) byte_get (data + 4, 4));
8202 data += 8;
8203 break;
8205 case DW_FORM_string:
8206 printf (" %s", data);
8207 data += strlen ((char *) data) + 1;
8208 break;
8210 case DW_FORM_block:
8211 uvalue = read_leb128 (data, & bytes_read, 0);
8212 block_start = data + bytes_read;
8213 data = display_block (block_start, uvalue);
8214 break;
8216 case DW_FORM_block1:
8217 uvalue = byte_get (data, 1);
8218 block_start = data + 1;
8219 data = display_block (block_start, uvalue);
8220 break;
8222 case DW_FORM_block2:
8223 uvalue = byte_get (data, 2);
8224 block_start = data + 2;
8225 data = display_block (block_start, uvalue);
8226 break;
8228 case DW_FORM_block4:
8229 uvalue = byte_get (data, 4);
8230 block_start = data + 4;
8231 data = display_block (block_start, uvalue);
8232 break;
8234 case DW_FORM_strp:
8235 printf (_(" (indirect string, offset: 0x%lx): %s"),
8236 uvalue, fetch_indirect_string (uvalue));
8237 break;
8239 case DW_FORM_indirect:
8240 /* Handled above. */
8241 break;
8243 default:
8244 warn (_("Unrecognized form: %d\n"), form);
8245 break;
8248 /* For some attributes we can display further information. */
8250 printf ("\t");
8252 switch (attribute)
8254 case DW_AT_inline:
8255 switch (uvalue)
8257 case DW_INL_not_inlined:
8258 printf (_("(not inlined)"));
8259 break;
8260 case DW_INL_inlined:
8261 printf (_("(inlined)"));
8262 break;
8263 case DW_INL_declared_not_inlined:
8264 printf (_("(declared as inline but ignored)"));
8265 break;
8266 case DW_INL_declared_inlined:
8267 printf (_("(declared as inline and inlined)"));
8268 break;
8269 default:
8270 printf (_(" (Unknown inline attribute value: %lx)"), uvalue);
8271 break;
8273 break;
8275 case DW_AT_language:
8276 switch (uvalue)
8278 case DW_LANG_C: printf ("(non-ANSI C)"); break;
8279 case DW_LANG_C89: printf ("(ANSI C)"); break;
8280 case DW_LANG_C_plus_plus: printf ("(C++)"); break;
8281 case DW_LANG_Fortran77: printf ("(FORTRAN 77)"); break;
8282 case DW_LANG_Fortran90: printf ("(Fortran 90)"); break;
8283 case DW_LANG_Modula2: printf ("(Modula 2)"); break;
8284 case DW_LANG_Pascal83: printf ("(ANSI Pascal)"); break;
8285 case DW_LANG_Ada83: printf ("(Ada)"); break;
8286 case DW_LANG_Cobol74: printf ("(Cobol 74)"); break;
8287 case DW_LANG_Cobol85: printf ("(Cobol 85)"); break;
8288 /* DWARF 2.1 values. */
8289 case DW_LANG_C99: printf ("(ANSI C99)"); break;
8290 case DW_LANG_Ada95: printf ("(ADA 95)"); break;
8291 case DW_LANG_Fortran95: printf ("(Fortran 95)"); break;
8292 /* MIPS extension. */
8293 case DW_LANG_Mips_Assembler: printf ("(MIPS assembler)"); break;
8294 /* UPC extension. */
8295 case DW_LANG_Upc: printf ("(Unified Parallel C)"); break;
8296 default:
8297 printf ("(Unknown: %lx)", uvalue);
8298 break;
8300 break;
8302 case DW_AT_encoding:
8303 switch (uvalue)
8305 case DW_ATE_void: printf ("(void)"); break;
8306 case DW_ATE_address: printf ("(machine address)"); break;
8307 case DW_ATE_boolean: printf ("(boolean)"); break;
8308 case DW_ATE_complex_float: printf ("(complex float)"); break;
8309 case DW_ATE_float: printf ("(float)"); break;
8310 case DW_ATE_signed: printf ("(signed)"); break;
8311 case DW_ATE_signed_char: printf ("(signed char)"); break;
8312 case DW_ATE_unsigned: printf ("(unsigned)"); break;
8313 case DW_ATE_unsigned_char: printf ("(unsigned char)"); break;
8314 /* DWARF 2.1 value. */
8315 case DW_ATE_imaginary_float: printf ("(imaginary float)"); break;
8316 default:
8317 if (uvalue >= DW_ATE_lo_user
8318 && uvalue <= DW_ATE_hi_user)
8319 printf ("(user defined type)");
8320 else
8321 printf ("(unknown type)");
8322 break;
8324 break;
8326 case DW_AT_accessibility:
8327 switch (uvalue)
8329 case DW_ACCESS_public: printf ("(public)"); break;
8330 case DW_ACCESS_protected: printf ("(protected)"); break;
8331 case DW_ACCESS_private: printf ("(private)"); break;
8332 default:
8333 printf ("(unknown accessibility)");
8334 break;
8336 break;
8338 case DW_AT_visibility:
8339 switch (uvalue)
8341 case DW_VIS_local: printf ("(local)"); break;
8342 case DW_VIS_exported: printf ("(exported)"); break;
8343 case DW_VIS_qualified: printf ("(qualified)"); break;
8344 default: printf ("(unknown visibility)"); break;
8346 break;
8348 case DW_AT_virtuality:
8349 switch (uvalue)
8351 case DW_VIRTUALITY_none: printf ("(none)"); break;
8352 case DW_VIRTUALITY_virtual: printf ("(virtual)"); break;
8353 case DW_VIRTUALITY_pure_virtual:printf ("(pure_virtual)"); break;
8354 default: printf ("(unknown virtuality)"); break;
8356 break;
8358 case DW_AT_identifier_case:
8359 switch (uvalue)
8361 case DW_ID_case_sensitive: printf ("(case_sensitive)"); break;
8362 case DW_ID_up_case: printf ("(up_case)"); break;
8363 case DW_ID_down_case: printf ("(down_case)"); break;
8364 case DW_ID_case_insensitive: printf ("(case_insensitive)"); break;
8365 default: printf ("(unknown case)"); break;
8367 break;
8369 case DW_AT_calling_convention:
8370 switch (uvalue)
8372 case DW_CC_normal: printf ("(normal)"); break;
8373 case DW_CC_program: printf ("(program)"); break;
8374 case DW_CC_nocall: printf ("(nocall)"); break;
8375 default:
8376 if (uvalue >= DW_CC_lo_user
8377 && uvalue <= DW_CC_hi_user)
8378 printf ("(user defined)");
8379 else
8380 printf ("(unknown convention)");
8382 break;
8384 case DW_AT_ordering:
8385 switch (uvalue)
8387 case -1: printf ("(undefined)"); break;
8388 case 0: printf ("(row major)"); break;
8389 case 1: printf ("(column major)"); break;
8391 break;
8393 case DW_AT_frame_base:
8394 case DW_AT_location:
8395 case DW_AT_data_member_location:
8396 case DW_AT_vtable_elem_location:
8397 case DW_AT_allocated:
8398 case DW_AT_associated:
8399 case DW_AT_data_location:
8400 case DW_AT_stride:
8401 case DW_AT_upper_bound:
8402 case DW_AT_lower_bound:
8403 if (block_start)
8405 printf ("(");
8406 decode_location_expression (block_start, pointer_size, uvalue);
8407 printf (")");
8409 else if (form == DW_FORM_data4 || form == DW_FORM_data8)
8411 printf ("(");
8412 printf ("location list");
8413 printf (")");
8415 break;
8417 default:
8418 break;
8421 return data;
8424 static unsigned char *
8425 read_and_display_attr (unsigned long attribute,
8426 unsigned long form,
8427 unsigned char *data,
8428 unsigned long cu_offset,
8429 unsigned long pointer_size,
8430 unsigned long offset_size,
8431 int dwarf_version)
8433 printf (" %-18s:", get_AT_name (attribute));
8434 data = read_and_display_attr_value (attribute, form, data, cu_offset,
8435 pointer_size, offset_size, dwarf_version);
8436 printf ("\n");
8437 return data;
8440 static int
8441 display_debug_info (Elf_Internal_Shdr *section,
8442 unsigned char *start,
8443 FILE *file)
8445 unsigned char *end = start + section->sh_size;
8446 unsigned char *section_begin = start;
8448 printf (_("The section %s contains:\n\n"), SECTION_NAME (section));
8450 load_debug_str (file);
8451 load_debug_loc (file);
8453 while (start < end)
8455 DWARF2_Internal_CompUnit compunit;
8456 Elf_Internal_Shdr *relsec;
8457 unsigned char *hdrptr;
8458 unsigned char *cu_abbrev_offset_ptr;
8459 unsigned char *tags;
8460 int level;
8461 unsigned long cu_offset;
8462 int offset_size;
8463 int initial_length_size;
8465 hdrptr = start;
8467 compunit.cu_length = byte_get (hdrptr, 4);
8468 hdrptr += 4;
8470 if (compunit.cu_length == 0xffffffff)
8472 compunit.cu_length = byte_get (hdrptr, 8);
8473 hdrptr += 8;
8474 offset_size = 8;
8475 initial_length_size = 12;
8477 else
8479 offset_size = 4;
8480 initial_length_size = 4;
8483 compunit.cu_version = byte_get (hdrptr, 2);
8484 hdrptr += 2;
8486 /* Apply addends of RELA relocations. */
8487 for (relsec = section_headers;
8488 relsec < section_headers + elf_header.e_shnum;
8489 ++relsec)
8491 unsigned long nrelas;
8492 Elf_Internal_Rela *rela, *rp;
8493 Elf_Internal_Shdr *symsec;
8494 Elf_Internal_Sym *symtab;
8495 Elf_Internal_Sym *sym;
8497 if (relsec->sh_type != SHT_RELA
8498 || SECTION_HEADER (relsec->sh_info) != section
8499 || relsec->sh_size == 0)
8500 continue;
8502 if (!slurp_rela_relocs (file, relsec->sh_offset, relsec->sh_size,
8503 & rela, & nrelas))
8504 return 0;
8506 symsec = SECTION_HEADER (relsec->sh_link);
8507 symtab = GET_ELF_SYMBOLS (file, symsec);
8509 for (rp = rela; rp < rela + nrelas; ++rp)
8511 unsigned char *loc;
8513 if (rp->r_offset >= (bfd_vma) (hdrptr - section_begin)
8514 && section->sh_size > (bfd_vma) offset_size
8515 && rp->r_offset <= section->sh_size - offset_size)
8516 loc = section_begin + rp->r_offset;
8517 else
8518 continue;
8520 if (is_32bit_elf)
8522 sym = symtab + ELF32_R_SYM (rp->r_info);
8524 if (ELF32_R_SYM (rp->r_info) != 0
8525 && ELF32_ST_TYPE (sym->st_info) != STT_SECTION)
8527 warn (_("Skipping unexpected symbol type %u\n"),
8528 ELF32_ST_TYPE (sym->st_info));
8529 continue;
8532 else
8534 sym = symtab + ELF64_R_SYM (rp->r_info);
8536 if (ELF64_R_SYM (rp->r_info) != 0
8537 && ELF64_ST_TYPE (sym->st_info) != STT_SECTION)
8539 warn (_("Skipping unexpected symbol type %u\n"),
8540 ELF64_ST_TYPE (sym->st_info));
8541 continue;
8545 byte_put (loc, rp->r_addend, offset_size);
8548 free (rela);
8549 break;
8552 cu_abbrev_offset_ptr = hdrptr;
8553 compunit.cu_abbrev_offset = byte_get (hdrptr, offset_size);
8554 hdrptr += offset_size;
8556 compunit.cu_pointer_size = byte_get (hdrptr, 1);
8557 hdrptr += 1;
8559 tags = hdrptr;
8560 cu_offset = start - section_begin;
8561 start += compunit.cu_length + initial_length_size;
8563 printf (_(" Compilation Unit @ %lx:\n"), cu_offset);
8564 printf (_(" Length: %ld\n"), compunit.cu_length);
8565 printf (_(" Version: %d\n"), compunit.cu_version);
8566 printf (_(" Abbrev Offset: %ld\n"), compunit.cu_abbrev_offset);
8567 printf (_(" Pointer Size: %d\n"), compunit.cu_pointer_size);
8569 if (compunit.cu_version != 2 && compunit.cu_version != 3)
8571 warn (_("Only version 2 and 3 DWARF debug information is currently supported.\n"));
8572 continue;
8575 free_abbrevs ();
8577 /* Read in the abbrevs used by this compilation unit. */
8579 Elf_Internal_Shdr *sec;
8580 unsigned char *begin;
8582 /* Locate the .debug_abbrev section and process it. */
8583 sec = find_section (".debug_abbrev");
8584 if (sec == NULL)
8586 warn (_("Unable to locate .debug_abbrev section!\n"));
8587 return 0;
8590 begin = get_data (NULL, file, sec->sh_offset, sec->sh_size,
8591 _("debug_abbrev section data"));
8592 if (!begin)
8593 return 0;
8595 process_abbrev_section (begin + compunit.cu_abbrev_offset,
8596 begin + sec->sh_size);
8598 free (begin);
8601 level = 0;
8602 while (tags < start)
8604 int bytes_read;
8605 unsigned long abbrev_number;
8606 abbrev_entry *entry;
8607 abbrev_attr *attr;
8609 abbrev_number = read_leb128 (tags, & bytes_read, 0);
8610 tags += bytes_read;
8612 /* A null DIE marks the end of a list of children. */
8613 if (abbrev_number == 0)
8615 --level;
8616 continue;
8619 /* Scan through the abbreviation list until we reach the
8620 correct entry. */
8621 for (entry = first_abbrev;
8622 entry && entry->entry != abbrev_number;
8623 entry = entry->next)
8624 continue;
8626 if (entry == NULL)
8628 warn (_("Unable to locate entry %lu in the abbreviation table\n"),
8629 abbrev_number);
8630 return 0;
8633 printf (_(" <%d><%lx>: Abbrev Number: %lu (%s)\n"),
8634 level,
8635 (unsigned long) (tags - section_begin - bytes_read),
8636 abbrev_number,
8637 get_TAG_name (entry->tag));
8639 for (attr = entry->first_attr; attr; attr = attr->next)
8640 tags = read_and_display_attr (attr->attribute,
8641 attr->form,
8642 tags, cu_offset,
8643 compunit.cu_pointer_size,
8644 offset_size,
8645 compunit.cu_version);
8647 if (entry->children)
8648 ++level;
8652 free_debug_str ();
8653 free_debug_loc ();
8655 printf ("\n");
8657 return 1;
8660 static int
8661 display_debug_aranges (Elf_Internal_Shdr *section,
8662 unsigned char *start,
8663 FILE *file ATTRIBUTE_UNUSED)
8665 unsigned char *end = start + section->sh_size;
8667 printf (_("The section %s contains:\n\n"), SECTION_NAME (section));
8669 while (start < end)
8671 unsigned char *hdrptr;
8672 DWARF2_Internal_ARange arange;
8673 unsigned char *ranges;
8674 unsigned long length;
8675 unsigned long address;
8676 int excess;
8677 int offset_size;
8678 int initial_length_size;
8680 hdrptr = start;
8682 arange.ar_length = byte_get (hdrptr, 4);
8683 hdrptr += 4;
8685 if (arange.ar_length == 0xffffffff)
8687 arange.ar_length = byte_get (hdrptr, 8);
8688 hdrptr += 8;
8689 offset_size = 8;
8690 initial_length_size = 12;
8692 else
8694 offset_size = 4;
8695 initial_length_size = 4;
8698 arange.ar_version = byte_get (hdrptr, 2);
8699 hdrptr += 2;
8701 arange.ar_info_offset = byte_get (hdrptr, offset_size);
8702 hdrptr += offset_size;
8704 arange.ar_pointer_size = byte_get (hdrptr, 1);
8705 hdrptr += 1;
8707 arange.ar_segment_size = byte_get (hdrptr, 1);
8708 hdrptr += 1;
8710 if (arange.ar_version != 2 && arange.ar_version != 3)
8712 warn (_("Only DWARF 2 and 3 aranges are currently supported.\n"));
8713 break;
8716 printf (_(" Length: %ld\n"), arange.ar_length);
8717 printf (_(" Version: %d\n"), arange.ar_version);
8718 printf (_(" Offset into .debug_info: %lx\n"), arange.ar_info_offset);
8719 printf (_(" Pointer Size: %d\n"), arange.ar_pointer_size);
8720 printf (_(" Segment Size: %d\n"), arange.ar_segment_size);
8722 printf (_("\n Address Length\n"));
8724 ranges = hdrptr;
8726 /* Must pad to an alignment boundary that is twice the pointer size. */
8727 excess = (hdrptr - start) % (2 * arange.ar_pointer_size);
8728 if (excess)
8729 ranges += (2 * arange.ar_pointer_size) - excess;
8731 for (;;)
8733 address = byte_get (ranges, arange.ar_pointer_size);
8735 ranges += arange.ar_pointer_size;
8737 length = byte_get (ranges, arange.ar_pointer_size);
8739 ranges += arange.ar_pointer_size;
8741 /* A pair of zeros marks the end of the list. */
8742 if (address == 0 && length == 0)
8743 break;
8745 printf (" %8.8lx %lu\n", address, length);
8748 start += arange.ar_length + initial_length_size;
8751 printf ("\n");
8753 return 1;
8756 typedef struct Frame_Chunk
8758 struct Frame_Chunk *next;
8759 unsigned char *chunk_start;
8760 int ncols;
8761 /* DW_CFA_{undefined,same_value,offset,register,unreferenced} */
8762 short int *col_type;
8763 int *col_offset;
8764 char *augmentation;
8765 unsigned int code_factor;
8766 int data_factor;
8767 unsigned long pc_begin;
8768 unsigned long pc_range;
8769 int cfa_reg;
8770 int cfa_offset;
8771 int ra;
8772 unsigned char fde_encoding;
8773 unsigned char cfa_exp;
8775 Frame_Chunk;
8777 /* A marker for a col_type that means this column was never referenced
8778 in the frame info. */
8779 #define DW_CFA_unreferenced (-1)
8781 static void
8782 frame_need_space (Frame_Chunk *fc, int reg)
8784 int prev = fc->ncols;
8786 if (reg < fc->ncols)
8787 return;
8789 fc->ncols = reg + 1;
8790 fc->col_type = xrealloc (fc->col_type, fc->ncols * sizeof (short int));
8791 fc->col_offset = xrealloc (fc->col_offset, fc->ncols * sizeof (int));
8793 while (prev < fc->ncols)
8795 fc->col_type[prev] = DW_CFA_unreferenced;
8796 fc->col_offset[prev] = 0;
8797 prev++;
8801 static void
8802 frame_display_row (Frame_Chunk *fc, int *need_col_headers, int *max_regs)
8804 int r;
8805 char tmp[100];
8807 if (*max_regs < fc->ncols)
8808 *max_regs = fc->ncols;
8810 if (*need_col_headers)
8812 *need_col_headers = 0;
8814 printf (" LOC CFA ");
8816 for (r = 0; r < *max_regs; r++)
8817 if (fc->col_type[r] != DW_CFA_unreferenced)
8819 if (r == fc->ra)
8820 printf ("ra ");
8821 else
8822 printf ("r%-4d", r);
8825 printf ("\n");
8828 printf ("%08lx ", fc->pc_begin);
8829 if (fc->cfa_exp)
8830 strcpy (tmp, "exp");
8831 else
8832 sprintf (tmp, "r%d%+d", fc->cfa_reg, fc->cfa_offset);
8833 printf ("%-8s ", tmp);
8835 for (r = 0; r < fc->ncols; r++)
8837 if (fc->col_type[r] != DW_CFA_unreferenced)
8839 switch (fc->col_type[r])
8841 case DW_CFA_undefined:
8842 strcpy (tmp, "u");
8843 break;
8844 case DW_CFA_same_value:
8845 strcpy (tmp, "s");
8846 break;
8847 case DW_CFA_offset:
8848 sprintf (tmp, "c%+d", fc->col_offset[r]);
8849 break;
8850 case DW_CFA_register:
8851 sprintf (tmp, "r%d", fc->col_offset[r]);
8852 break;
8853 case DW_CFA_expression:
8854 strcpy (tmp, "exp");
8855 break;
8856 default:
8857 strcpy (tmp, "n/a");
8858 break;
8860 printf ("%-5s", tmp);
8863 printf ("\n");
8866 static int
8867 size_of_encoded_value (int encoding)
8869 switch (encoding & 0x7)
8871 default: /* ??? */
8872 case 0: return is_32bit_elf ? 4 : 8;
8873 case 2: return 2;
8874 case 3: return 4;
8875 case 4: return 8;
8879 static bfd_vma
8880 get_encoded_value (unsigned char *data, int encoding)
8882 int size = size_of_encoded_value (encoding);
8883 if (encoding & DW_EH_PE_signed)
8884 return byte_get_signed (data, size);
8885 else
8886 return byte_get (data, size);
8889 #define GET(N) byte_get (start, N); start += N
8890 #define LEB() read_leb128 (start, & length_return, 0); start += length_return
8891 #define SLEB() read_leb128 (start, & length_return, 1); start += length_return
8893 static int
8894 display_debug_frames (Elf_Internal_Shdr *section,
8895 unsigned char *start,
8896 FILE *file ATTRIBUTE_UNUSED)
8898 unsigned char *end = start + section->sh_size;
8899 unsigned char *section_start = start;
8900 Frame_Chunk *chunks = 0;
8901 Frame_Chunk *remembered_state = 0;
8902 Frame_Chunk *rs;
8903 int is_eh = (strcmp (SECTION_NAME (section), ".eh_frame") == 0);
8904 int length_return;
8905 int max_regs = 0;
8906 int addr_size = is_32bit_elf ? 4 : 8;
8908 printf (_("The section %s contains:\n"), SECTION_NAME (section));
8910 while (start < end)
8912 unsigned char *saved_start;
8913 unsigned char *block_end;
8914 unsigned long length;
8915 unsigned long cie_id;
8916 Frame_Chunk *fc;
8917 Frame_Chunk *cie;
8918 int need_col_headers = 1;
8919 unsigned char *augmentation_data = NULL;
8920 unsigned long augmentation_data_len = 0;
8921 int encoded_ptr_size = addr_size;
8922 int offset_size;
8923 int initial_length_size;
8925 saved_start = start;
8926 length = byte_get (start, 4); start += 4;
8928 if (length == 0)
8930 printf ("\n%08lx ZERO terminator\n\n",
8931 (unsigned long)(saved_start - section_start));
8932 return 1;
8935 if (length == 0xffffffff)
8937 length = byte_get (start, 8);
8938 start += 8;
8939 offset_size = 8;
8940 initial_length_size = 12;
8942 else
8944 offset_size = 4;
8945 initial_length_size = 4;
8948 block_end = saved_start + length + initial_length_size;
8949 cie_id = byte_get (start, offset_size); start += offset_size;
8951 if (is_eh ? (cie_id == 0) : (cie_id == DW_CIE_ID))
8953 int version;
8955 fc = xmalloc (sizeof (Frame_Chunk));
8956 memset (fc, 0, sizeof (Frame_Chunk));
8958 fc->next = chunks;
8959 chunks = fc;
8960 fc->chunk_start = saved_start;
8961 fc->ncols = 0;
8962 fc->col_type = xmalloc (sizeof (short int));
8963 fc->col_offset = xmalloc (sizeof (int));
8964 frame_need_space (fc, max_regs-1);
8966 version = *start++;
8968 fc->augmentation = start;
8969 start = strchr (start, '\0') + 1;
8971 if (fc->augmentation[0] == 'z')
8973 fc->code_factor = LEB ();
8974 fc->data_factor = SLEB ();
8975 if (version == 1)
8977 fc->ra = GET (1);
8979 else
8981 fc->ra = LEB ();
8983 augmentation_data_len = LEB ();
8984 augmentation_data = start;
8985 start += augmentation_data_len;
8987 else if (strcmp (fc->augmentation, "eh") == 0)
8989 start += addr_size;
8990 fc->code_factor = LEB ();
8991 fc->data_factor = SLEB ();
8992 if (version == 1)
8994 fc->ra = GET (1);
8996 else
8998 fc->ra = LEB ();
9001 else
9003 fc->code_factor = LEB ();
9004 fc->data_factor = SLEB ();
9005 if (version == 1)
9007 fc->ra = GET (1);
9009 else
9011 fc->ra = LEB ();
9014 cie = fc;
9016 if (do_debug_frames_interp)
9017 printf ("\n%08lx %08lx %08lx CIE \"%s\" cf=%d df=%d ra=%d\n",
9018 (unsigned long)(saved_start - section_start), length, cie_id,
9019 fc->augmentation, fc->code_factor, fc->data_factor,
9020 fc->ra);
9021 else
9023 printf ("\n%08lx %08lx %08lx CIE\n",
9024 (unsigned long)(saved_start - section_start), length, cie_id);
9025 printf (" Version: %d\n", version);
9026 printf (" Augmentation: \"%s\"\n", fc->augmentation);
9027 printf (" Code alignment factor: %u\n", fc->code_factor);
9028 printf (" Data alignment factor: %d\n", fc->data_factor);
9029 printf (" Return address column: %d\n", fc->ra);
9031 if (augmentation_data_len)
9033 unsigned long i;
9034 printf (" Augmentation data: ");
9035 for (i = 0; i < augmentation_data_len; ++i)
9036 printf (" %02x", augmentation_data[i]);
9037 putchar ('\n');
9039 putchar ('\n');
9042 if (augmentation_data_len)
9044 unsigned char *p, *q;
9045 p = fc->augmentation + 1;
9046 q = augmentation_data;
9048 while (1)
9050 if (*p == 'L')
9051 q++;
9052 else if (*p == 'P')
9053 q += 1 + size_of_encoded_value (*q);
9054 else if (*p == 'R')
9055 fc->fde_encoding = *q++;
9056 else
9057 break;
9058 p++;
9061 if (fc->fde_encoding)
9062 encoded_ptr_size = size_of_encoded_value (fc->fde_encoding);
9065 frame_need_space (fc, fc->ra);
9067 else
9069 unsigned char *look_for;
9070 static Frame_Chunk fde_fc;
9072 fc = & fde_fc;
9073 memset (fc, 0, sizeof (Frame_Chunk));
9075 look_for = is_eh ? start - 4 - cie_id : section_start + cie_id;
9077 for (cie = chunks; cie ; cie = cie->next)
9078 if (cie->chunk_start == look_for)
9079 break;
9081 if (!cie)
9083 warn ("Invalid CIE pointer %08lx in FDE at %08lx\n",
9084 cie_id, saved_start);
9085 start = block_end;
9086 fc->ncols = 0;
9087 fc->col_type = xmalloc (sizeof (short int));
9088 fc->col_offset = xmalloc (sizeof (int));
9089 frame_need_space (fc, max_regs - 1);
9090 cie = fc;
9091 fc->augmentation = "";
9092 fc->fde_encoding = 0;
9094 else
9096 fc->ncols = cie->ncols;
9097 fc->col_type = xmalloc (fc->ncols * sizeof (short int));
9098 fc->col_offset = xmalloc (fc->ncols * sizeof (int));
9099 memcpy (fc->col_type, cie->col_type, fc->ncols * sizeof (short int));
9100 memcpy (fc->col_offset, cie->col_offset, fc->ncols * sizeof (int));
9101 fc->augmentation = cie->augmentation;
9102 fc->code_factor = cie->code_factor;
9103 fc->data_factor = cie->data_factor;
9104 fc->cfa_reg = cie->cfa_reg;
9105 fc->cfa_offset = cie->cfa_offset;
9106 fc->ra = cie->ra;
9107 frame_need_space (fc, max_regs-1);
9108 fc->fde_encoding = cie->fde_encoding;
9111 if (fc->fde_encoding)
9112 encoded_ptr_size = size_of_encoded_value (fc->fde_encoding);
9114 fc->pc_begin = get_encoded_value (start, fc->fde_encoding);
9115 if ((fc->fde_encoding & 0x70) == DW_EH_PE_pcrel)
9116 fc->pc_begin += section->sh_addr + (start - section_start);
9117 start += encoded_ptr_size;
9118 fc->pc_range = byte_get (start, encoded_ptr_size);
9119 start += encoded_ptr_size;
9121 if (cie->augmentation[0] == 'z')
9123 augmentation_data_len = LEB ();
9124 augmentation_data = start;
9125 start += augmentation_data_len;
9128 printf ("\n%08lx %08lx %08lx FDE cie=%08lx pc=%08lx..%08lx\n",
9129 (unsigned long)(saved_start - section_start), length, cie_id,
9130 (unsigned long)(cie->chunk_start - section_start),
9131 fc->pc_begin, fc->pc_begin + fc->pc_range);
9132 if (! do_debug_frames_interp && augmentation_data_len)
9134 unsigned long i;
9135 printf (" Augmentation data: ");
9136 for (i = 0; i < augmentation_data_len; ++i)
9137 printf (" %02x", augmentation_data[i]);
9138 putchar ('\n');
9139 putchar ('\n');
9143 /* At this point, fc is the current chunk, cie (if any) is set, and we're
9144 about to interpret instructions for the chunk. */
9145 /* ??? At present we need to do this always, since this sizes the
9146 fc->col_type and fc->col_offset arrays, which we write into always.
9147 We should probably split the interpreted and non-interpreted bits
9148 into two different routines, since there's so much that doesn't
9149 really overlap between them. */
9150 if (1 || do_debug_frames_interp)
9152 /* Start by making a pass over the chunk, allocating storage
9153 and taking note of what registers are used. */
9154 unsigned char *tmp = start;
9156 while (start < block_end)
9158 unsigned op, opa;
9159 unsigned long reg, tmp;
9161 op = *start++;
9162 opa = op & 0x3f;
9163 if (op & 0xc0)
9164 op &= 0xc0;
9166 /* Warning: if you add any more cases to this switch, be
9167 sure to add them to the corresponding switch below. */
9168 switch (op)
9170 case DW_CFA_advance_loc:
9171 break;
9172 case DW_CFA_offset:
9173 LEB ();
9174 frame_need_space (fc, opa);
9175 fc->col_type[opa] = DW_CFA_undefined;
9176 break;
9177 case DW_CFA_restore:
9178 frame_need_space (fc, opa);
9179 fc->col_type[opa] = DW_CFA_undefined;
9180 break;
9181 case DW_CFA_set_loc:
9182 start += encoded_ptr_size;
9183 break;
9184 case DW_CFA_advance_loc1:
9185 start += 1;
9186 break;
9187 case DW_CFA_advance_loc2:
9188 start += 2;
9189 break;
9190 case DW_CFA_advance_loc4:
9191 start += 4;
9192 break;
9193 case DW_CFA_offset_extended:
9194 reg = LEB (); LEB ();
9195 frame_need_space (fc, reg);
9196 fc->col_type[reg] = DW_CFA_undefined;
9197 break;
9198 case DW_CFA_restore_extended:
9199 reg = LEB ();
9200 frame_need_space (fc, reg);
9201 fc->col_type[reg] = DW_CFA_undefined;
9202 break;
9203 case DW_CFA_undefined:
9204 reg = LEB ();
9205 frame_need_space (fc, reg);
9206 fc->col_type[reg] = DW_CFA_undefined;
9207 break;
9208 case DW_CFA_same_value:
9209 reg = LEB ();
9210 frame_need_space (fc, reg);
9211 fc->col_type[reg] = DW_CFA_undefined;
9212 break;
9213 case DW_CFA_register:
9214 reg = LEB (); LEB ();
9215 frame_need_space (fc, reg);
9216 fc->col_type[reg] = DW_CFA_undefined;
9217 break;
9218 case DW_CFA_def_cfa:
9219 LEB (); LEB ();
9220 break;
9221 case DW_CFA_def_cfa_register:
9222 LEB ();
9223 break;
9224 case DW_CFA_def_cfa_offset:
9225 LEB ();
9226 break;
9227 case DW_CFA_def_cfa_expression:
9228 tmp = LEB ();
9229 start += tmp;
9230 break;
9231 case DW_CFA_expression:
9232 reg = LEB ();
9233 tmp = LEB ();
9234 start += tmp;
9235 frame_need_space (fc, reg);
9236 fc->col_type[reg] = DW_CFA_undefined;
9237 break;
9238 case DW_CFA_offset_extended_sf:
9239 reg = LEB (); SLEB ();
9240 frame_need_space (fc, reg);
9241 fc->col_type[reg] = DW_CFA_undefined;
9242 break;
9243 case DW_CFA_def_cfa_sf:
9244 LEB (); SLEB ();
9245 break;
9246 case DW_CFA_def_cfa_offset_sf:
9247 SLEB ();
9248 break;
9249 case DW_CFA_MIPS_advance_loc8:
9250 start += 8;
9251 break;
9252 case DW_CFA_GNU_args_size:
9253 LEB ();
9254 break;
9255 case DW_CFA_GNU_negative_offset_extended:
9256 reg = LEB (); LEB ();
9257 frame_need_space (fc, reg);
9258 fc->col_type[reg] = DW_CFA_undefined;
9260 default:
9261 break;
9264 start = tmp;
9267 /* Now we know what registers are used, make a second pass over
9268 the chunk, this time actually printing out the info. */
9270 while (start < block_end)
9272 unsigned op, opa;
9273 unsigned long ul, reg, roffs;
9274 long l, ofs;
9275 bfd_vma vma;
9277 op = *start++;
9278 opa = op & 0x3f;
9279 if (op & 0xc0)
9280 op &= 0xc0;
9282 /* Warning: if you add any more cases to this switch, be
9283 sure to add them to the corresponding switch above. */
9284 switch (op)
9286 case DW_CFA_advance_loc:
9287 if (do_debug_frames_interp)
9288 frame_display_row (fc, &need_col_headers, &max_regs);
9289 else
9290 printf (" DW_CFA_advance_loc: %d to %08lx\n",
9291 opa * fc->code_factor,
9292 fc->pc_begin + opa * fc->code_factor);
9293 fc->pc_begin += opa * fc->code_factor;
9294 break;
9296 case DW_CFA_offset:
9297 roffs = LEB ();
9298 if (! do_debug_frames_interp)
9299 printf (" DW_CFA_offset: r%d at cfa%+ld\n",
9300 opa, roffs * fc->data_factor);
9301 fc->col_type[opa] = DW_CFA_offset;
9302 fc->col_offset[opa] = roffs * fc->data_factor;
9303 break;
9305 case DW_CFA_restore:
9306 if (! do_debug_frames_interp)
9307 printf (" DW_CFA_restore: r%d\n", opa);
9308 fc->col_type[opa] = cie->col_type[opa];
9309 fc->col_offset[opa] = cie->col_offset[opa];
9310 break;
9312 case DW_CFA_set_loc:
9313 vma = get_encoded_value (start, fc->fde_encoding);
9314 if ((fc->fde_encoding & 0x70) == DW_EH_PE_pcrel)
9315 vma += section->sh_addr + (start - section_start);
9316 start += encoded_ptr_size;
9317 if (do_debug_frames_interp)
9318 frame_display_row (fc, &need_col_headers, &max_regs);
9319 else
9320 printf (" DW_CFA_set_loc: %08lx\n", (unsigned long)vma);
9321 fc->pc_begin = vma;
9322 break;
9324 case DW_CFA_advance_loc1:
9325 ofs = byte_get (start, 1); start += 1;
9326 if (do_debug_frames_interp)
9327 frame_display_row (fc, &need_col_headers, &max_regs);
9328 else
9329 printf (" DW_CFA_advance_loc1: %ld to %08lx\n",
9330 ofs * fc->code_factor,
9331 fc->pc_begin + ofs * fc->code_factor);
9332 fc->pc_begin += ofs * fc->code_factor;
9333 break;
9335 case DW_CFA_advance_loc2:
9336 ofs = byte_get (start, 2); start += 2;
9337 if (do_debug_frames_interp)
9338 frame_display_row (fc, &need_col_headers, &max_regs);
9339 else
9340 printf (" DW_CFA_advance_loc2: %ld to %08lx\n",
9341 ofs * fc->code_factor,
9342 fc->pc_begin + ofs * fc->code_factor);
9343 fc->pc_begin += ofs * fc->code_factor;
9344 break;
9346 case DW_CFA_advance_loc4:
9347 ofs = byte_get (start, 4); start += 4;
9348 if (do_debug_frames_interp)
9349 frame_display_row (fc, &need_col_headers, &max_regs);
9350 else
9351 printf (" DW_CFA_advance_loc4: %ld to %08lx\n",
9352 ofs * fc->code_factor,
9353 fc->pc_begin + ofs * fc->code_factor);
9354 fc->pc_begin += ofs * fc->code_factor;
9355 break;
9357 case DW_CFA_offset_extended:
9358 reg = LEB ();
9359 roffs = LEB ();
9360 if (! do_debug_frames_interp)
9361 printf (" DW_CFA_offset_extended: r%ld at cfa%+ld\n",
9362 reg, roffs * fc->data_factor);
9363 fc->col_type[reg] = DW_CFA_offset;
9364 fc->col_offset[reg] = roffs * fc->data_factor;
9365 break;
9367 case DW_CFA_restore_extended:
9368 reg = LEB ();
9369 if (! do_debug_frames_interp)
9370 printf (" DW_CFA_restore_extended: r%ld\n", reg);
9371 fc->col_type[reg] = cie->col_type[reg];
9372 fc->col_offset[reg] = cie->col_offset[reg];
9373 break;
9375 case DW_CFA_undefined:
9376 reg = LEB ();
9377 if (! do_debug_frames_interp)
9378 printf (" DW_CFA_undefined: r%ld\n", reg);
9379 fc->col_type[reg] = DW_CFA_undefined;
9380 fc->col_offset[reg] = 0;
9381 break;
9383 case DW_CFA_same_value:
9384 reg = LEB ();
9385 if (! do_debug_frames_interp)
9386 printf (" DW_CFA_same_value: r%ld\n", reg);
9387 fc->col_type[reg] = DW_CFA_same_value;
9388 fc->col_offset[reg] = 0;
9389 break;
9391 case DW_CFA_register:
9392 reg = LEB ();
9393 roffs = LEB ();
9394 if (! do_debug_frames_interp)
9395 printf (" DW_CFA_register: r%ld in r%ld\n", reg, roffs);
9396 fc->col_type[reg] = DW_CFA_register;
9397 fc->col_offset[reg] = roffs;
9398 break;
9400 case DW_CFA_remember_state:
9401 if (! do_debug_frames_interp)
9402 printf (" DW_CFA_remember_state\n");
9403 rs = xmalloc (sizeof (Frame_Chunk));
9404 rs->ncols = fc->ncols;
9405 rs->col_type = xmalloc (rs->ncols * sizeof (short int));
9406 rs->col_offset = xmalloc (rs->ncols * sizeof (int));
9407 memcpy (rs->col_type, fc->col_type, rs->ncols);
9408 memcpy (rs->col_offset, fc->col_offset, rs->ncols * sizeof (int));
9409 rs->next = remembered_state;
9410 remembered_state = rs;
9411 break;
9413 case DW_CFA_restore_state:
9414 if (! do_debug_frames_interp)
9415 printf (" DW_CFA_restore_state\n");
9416 rs = remembered_state;
9417 if (rs)
9419 remembered_state = rs->next;
9420 frame_need_space (fc, rs->ncols-1);
9421 memcpy (fc->col_type, rs->col_type, rs->ncols);
9422 memcpy (fc->col_offset, rs->col_offset,
9423 rs->ncols * sizeof (int));
9424 free (rs->col_type);
9425 free (rs->col_offset);
9426 free (rs);
9428 else if (do_debug_frames_interp)
9429 printf ("Mismatched DW_CFA_restore_state\n");
9430 break;
9432 case DW_CFA_def_cfa:
9433 fc->cfa_reg = LEB ();
9434 fc->cfa_offset = LEB ();
9435 fc->cfa_exp = 0;
9436 if (! do_debug_frames_interp)
9437 printf (" DW_CFA_def_cfa: r%d ofs %d\n",
9438 fc->cfa_reg, fc->cfa_offset);
9439 break;
9441 case DW_CFA_def_cfa_register:
9442 fc->cfa_reg = LEB ();
9443 fc->cfa_exp = 0;
9444 if (! do_debug_frames_interp)
9445 printf (" DW_CFA_def_cfa_reg: r%d\n", fc->cfa_reg);
9446 break;
9448 case DW_CFA_def_cfa_offset:
9449 fc->cfa_offset = LEB ();
9450 if (! do_debug_frames_interp)
9451 printf (" DW_CFA_def_cfa_offset: %d\n", fc->cfa_offset);
9452 break;
9454 case DW_CFA_nop:
9455 if (! do_debug_frames_interp)
9456 printf (" DW_CFA_nop\n");
9457 break;
9459 case DW_CFA_def_cfa_expression:
9460 ul = LEB ();
9461 if (! do_debug_frames_interp)
9463 printf (" DW_CFA_def_cfa_expression (");
9464 decode_location_expression (start, addr_size, ul);
9465 printf (")\n");
9467 fc->cfa_exp = 1;
9468 start += ul;
9469 break;
9471 case DW_CFA_expression:
9472 reg = LEB ();
9473 ul = LEB ();
9474 if (! do_debug_frames_interp)
9476 printf (" DW_CFA_expression: r%ld (", reg);
9477 decode_location_expression (start, addr_size, ul);
9478 printf (")\n");
9480 fc->col_type[reg] = DW_CFA_expression;
9481 start += ul;
9482 break;
9484 case DW_CFA_offset_extended_sf:
9485 reg = LEB ();
9486 l = SLEB ();
9487 frame_need_space (fc, reg);
9488 if (! do_debug_frames_interp)
9489 printf (" DW_CFA_offset_extended_sf: r%ld at cfa%+ld\n",
9490 reg, l * fc->data_factor);
9491 fc->col_type[reg] = DW_CFA_offset;
9492 fc->col_offset[reg] = l * fc->data_factor;
9493 break;
9495 case DW_CFA_def_cfa_sf:
9496 fc->cfa_reg = LEB ();
9497 fc->cfa_offset = SLEB ();
9498 fc->cfa_exp = 0;
9499 if (! do_debug_frames_interp)
9500 printf (" DW_CFA_def_cfa_sf: r%d ofs %d\n",
9501 fc->cfa_reg, fc->cfa_offset);
9502 break;
9504 case DW_CFA_def_cfa_offset_sf:
9505 fc->cfa_offset = SLEB ();
9506 if (! do_debug_frames_interp)
9507 printf (" DW_CFA_def_cfa_offset_sf: %d\n", fc->cfa_offset);
9508 break;
9510 case DW_CFA_MIPS_advance_loc8:
9511 ofs = byte_get (start, 8); start += 8;
9512 if (do_debug_frames_interp)
9513 frame_display_row (fc, &need_col_headers, &max_regs);
9514 else
9515 printf (" DW_CFA_MIPS_advance_loc8: %ld to %08lx\n",
9516 ofs * fc->code_factor,
9517 fc->pc_begin + ofs * fc->code_factor);
9518 fc->pc_begin += ofs * fc->code_factor;
9519 break;
9521 case DW_CFA_GNU_window_save:
9522 if (! do_debug_frames_interp)
9523 printf (" DW_CFA_GNU_window_save\n");
9524 break;
9526 case DW_CFA_GNU_args_size:
9527 ul = LEB ();
9528 if (! do_debug_frames_interp)
9529 printf (" DW_CFA_GNU_args_size: %ld\n", ul);
9530 break;
9532 case DW_CFA_GNU_negative_offset_extended:
9533 reg = LEB ();
9534 l = - LEB ();
9535 frame_need_space (fc, reg);
9536 if (! do_debug_frames_interp)
9537 printf (" DW_CFA_GNU_negative_offset_extended: r%ld at cfa%+ld\n",
9538 reg, l * fc->data_factor);
9539 fc->col_type[reg] = DW_CFA_offset;
9540 fc->col_offset[reg] = l * fc->data_factor;
9541 break;
9543 default:
9544 fprintf (stderr, "unsupported or unknown DW_CFA_%d\n", op);
9545 start = block_end;
9549 if (do_debug_frames_interp)
9550 frame_display_row (fc, &need_col_headers, &max_regs);
9552 start = block_end;
9555 printf ("\n");
9557 return 1;
9560 #undef GET
9561 #undef LEB
9562 #undef SLEB
9564 static int
9565 display_debug_not_supported (Elf_Internal_Shdr *section,
9566 unsigned char *start ATTRIBUTE_UNUSED,
9567 FILE *file ATTRIBUTE_UNUSED)
9569 printf (_("Displaying the debug contents of section %s is not yet supported.\n"),
9570 SECTION_NAME (section));
9572 return 1;
9575 /* A structure containing the name of a debug section
9576 and a pointer to a function that can decode it. */
9577 struct
9579 const char *const name;
9580 int (*display) (Elf_Internal_Shdr *, unsigned char *, FILE *);
9582 debug_displays[] =
9584 { ".debug_abbrev", display_debug_abbrev },
9585 { ".debug_aranges", display_debug_aranges },
9586 { ".debug_frame", display_debug_frames },
9587 { ".debug_info", display_debug_info },
9588 { ".debug_line", display_debug_lines },
9589 { ".debug_pubnames", display_debug_pubnames },
9590 { ".eh_frame", display_debug_frames },
9591 { ".debug_macinfo", display_debug_macinfo },
9592 { ".debug_str", display_debug_str },
9593 { ".debug_loc", display_debug_loc },
9594 { ".debug_pubtypes", display_debug_pubnames },
9595 { ".debug_ranges", display_debug_not_supported },
9596 { ".debug_static_func", display_debug_not_supported },
9597 { ".debug_static_vars", display_debug_not_supported },
9598 { ".debug_types", display_debug_not_supported },
9599 { ".debug_weaknames", display_debug_not_supported }
9602 static int
9603 display_debug_section (Elf_Internal_Shdr *section, FILE *file)
9605 char *name = SECTION_NAME (section);
9606 bfd_size_type length;
9607 unsigned char *start;
9608 int i;
9610 length = section->sh_size;
9611 if (length == 0)
9613 printf (_("\nSection '%s' has no debugging data.\n"), name);
9614 return 0;
9617 start = get_data (NULL, file, section->sh_offset, length,
9618 _("debug section data"));
9619 if (!start)
9620 return 0;
9622 /* See if we know how to display the contents of this section. */
9623 if (strncmp (name, ".gnu.linkonce.wi.", 17) == 0)
9624 name = ".debug_info";
9626 for (i = NUM_ELEM (debug_displays); i--;)
9627 if (strcmp (debug_displays[i].name, name) == 0)
9629 debug_displays[i].display (section, start, file);
9630 break;
9633 if (i == -1)
9634 printf (_("Unrecognized debug section: %s\n"), name);
9636 free (start);
9638 /* If we loaded in the abbrev section at some point,
9639 we must release it here. */
9640 free_abbrevs ();
9642 return 1;
9645 static int
9646 process_section_contents (FILE *file)
9648 Elf_Internal_Shdr *section;
9649 unsigned int i;
9651 if (! do_dump)
9652 return 1;
9654 for (i = 0, section = section_headers;
9655 i < elf_header.e_shnum && i < num_dump_sects;
9656 i++, section++)
9658 #ifdef SUPPORT_DISASSEMBLY
9659 if (dump_sects[i] & DISASS_DUMP)
9660 disassemble_section (section, file);
9661 #endif
9662 if (dump_sects[i] & HEX_DUMP)
9663 dump_section (section, file);
9665 if (dump_sects[i] & DEBUG_DUMP)
9666 display_debug_section (section, file);
9669 if (i < num_dump_sects)
9670 warn (_("Some sections were not dumped because they do not exist!\n"));
9672 return 1;
9675 static void
9676 process_mips_fpe_exception (int mask)
9678 if (mask)
9680 int first = 1;
9681 if (mask & OEX_FPU_INEX)
9682 fputs ("INEX", stdout), first = 0;
9683 if (mask & OEX_FPU_UFLO)
9684 printf ("%sUFLO", first ? "" : "|"), first = 0;
9685 if (mask & OEX_FPU_OFLO)
9686 printf ("%sOFLO", first ? "" : "|"), first = 0;
9687 if (mask & OEX_FPU_DIV0)
9688 printf ("%sDIV0", first ? "" : "|"), first = 0;
9689 if (mask & OEX_FPU_INVAL)
9690 printf ("%sINVAL", first ? "" : "|");
9692 else
9693 fputs ("0", stdout);
9696 static int
9697 process_mips_specific (FILE *file)
9699 Elf_Internal_Dyn *entry;
9700 size_t liblist_offset = 0;
9701 size_t liblistno = 0;
9702 size_t conflictsno = 0;
9703 size_t options_offset = 0;
9704 size_t conflicts_offset = 0;
9706 /* We have a lot of special sections. Thanks SGI! */
9707 if (dynamic_segment == NULL)
9708 /* No information available. */
9709 return 0;
9711 for (entry = dynamic_segment; entry->d_tag != DT_NULL; ++entry)
9712 switch (entry->d_tag)
9714 case DT_MIPS_LIBLIST:
9715 liblist_offset
9716 = offset_from_vma (file, entry->d_un.d_val,
9717 liblistno * sizeof (Elf32_External_Lib));
9718 break;
9719 case DT_MIPS_LIBLISTNO:
9720 liblistno = entry->d_un.d_val;
9721 break;
9722 case DT_MIPS_OPTIONS:
9723 options_offset = offset_from_vma (file, entry->d_un.d_val, 0);
9724 break;
9725 case DT_MIPS_CONFLICT:
9726 conflicts_offset
9727 = offset_from_vma (file, entry->d_un.d_val,
9728 conflictsno * sizeof (Elf32_External_Conflict));
9729 break;
9730 case DT_MIPS_CONFLICTNO:
9731 conflictsno = entry->d_un.d_val;
9732 break;
9733 default:
9734 break;
9737 if (liblist_offset != 0 && liblistno != 0 && do_dynamic)
9739 Elf32_External_Lib *elib;
9740 size_t cnt;
9742 elib = get_data (NULL, file, liblist_offset,
9743 liblistno * sizeof (Elf32_External_Lib),
9744 _("liblist"));
9745 if (elib)
9747 printf ("\nSection '.liblist' contains %lu entries:\n",
9748 (unsigned long) liblistno);
9749 fputs (" Library Time Stamp Checksum Version Flags\n",
9750 stdout);
9752 for (cnt = 0; cnt < liblistno; ++cnt)
9754 Elf32_Lib liblist;
9755 time_t time;
9756 char timebuf[20];
9757 struct tm *tmp;
9759 liblist.l_name = BYTE_GET (elib[cnt].l_name);
9760 time = BYTE_GET (elib[cnt].l_time_stamp);
9761 liblist.l_checksum = BYTE_GET (elib[cnt].l_checksum);
9762 liblist.l_version = BYTE_GET (elib[cnt].l_version);
9763 liblist.l_flags = BYTE_GET (elib[cnt].l_flags);
9765 tmp = gmtime (&time);
9766 sprintf (timebuf, "%04u-%02u-%02uT%02u:%02u:%02u",
9767 tmp->tm_year + 1900, tmp->tm_mon + 1, tmp->tm_mday,
9768 tmp->tm_hour, tmp->tm_min, tmp->tm_sec);
9770 printf ("%3lu: ", (unsigned long) cnt);
9771 print_symbol (20, dynamic_strings + liblist.l_name);
9772 printf (" %s %#10lx %-7ld", timebuf, liblist.l_checksum,
9773 liblist.l_version);
9775 if (liblist.l_flags == 0)
9776 puts (" NONE");
9777 else
9779 static const struct
9781 const char *name;
9782 int bit;
9784 l_flags_vals[] =
9786 { " EXACT_MATCH", LL_EXACT_MATCH },
9787 { " IGNORE_INT_VER", LL_IGNORE_INT_VER },
9788 { " REQUIRE_MINOR", LL_REQUIRE_MINOR },
9789 { " EXPORTS", LL_EXPORTS },
9790 { " DELAY_LOAD", LL_DELAY_LOAD },
9791 { " DELTA", LL_DELTA }
9793 int flags = liblist.l_flags;
9794 size_t fcnt;
9796 for (fcnt = 0;
9797 fcnt < sizeof (l_flags_vals) / sizeof (l_flags_vals[0]);
9798 ++fcnt)
9799 if ((flags & l_flags_vals[fcnt].bit) != 0)
9801 fputs (l_flags_vals[fcnt].name, stdout);
9802 flags ^= l_flags_vals[fcnt].bit;
9804 if (flags != 0)
9805 printf (" %#x", (unsigned int) flags);
9807 puts ("");
9811 free (elib);
9815 if (options_offset != 0)
9817 Elf_External_Options *eopt;
9818 Elf_Internal_Shdr *sect = section_headers;
9819 Elf_Internal_Options *iopt;
9820 Elf_Internal_Options *option;
9821 size_t offset;
9822 int cnt;
9824 /* Find the section header so that we get the size. */
9825 while (sect->sh_type != SHT_MIPS_OPTIONS)
9826 ++sect;
9828 eopt = get_data (NULL, file, options_offset, sect->sh_size,
9829 _("options"));
9830 if (eopt)
9832 iopt = malloc ((sect->sh_size / sizeof (eopt)) * sizeof (*iopt));
9833 if (iopt == NULL)
9835 error (_("Out of memory"));
9836 return 0;
9839 offset = cnt = 0;
9840 option = iopt;
9842 while (offset < sect->sh_size)
9844 Elf_External_Options *eoption;
9846 eoption = (Elf_External_Options *) ((char *) eopt + offset);
9848 option->kind = BYTE_GET (eoption->kind);
9849 option->size = BYTE_GET (eoption->size);
9850 option->section = BYTE_GET (eoption->section);
9851 option->info = BYTE_GET (eoption->info);
9853 offset += option->size;
9855 ++option;
9856 ++cnt;
9859 printf (_("\nSection '%s' contains %d entries:\n"),
9860 SECTION_NAME (sect), cnt);
9862 option = iopt;
9864 while (cnt-- > 0)
9866 size_t len;
9868 switch (option->kind)
9870 case ODK_NULL:
9871 /* This shouldn't happen. */
9872 printf (" NULL %d %lx", option->section, option->info);
9873 break;
9874 case ODK_REGINFO:
9875 printf (" REGINFO ");
9876 if (elf_header.e_machine == EM_MIPS)
9878 /* 32bit form. */
9879 Elf32_External_RegInfo *ereg;
9880 Elf32_RegInfo reginfo;
9882 ereg = (Elf32_External_RegInfo *) (option + 1);
9883 reginfo.ri_gprmask = BYTE_GET (ereg->ri_gprmask);
9884 reginfo.ri_cprmask[0] = BYTE_GET (ereg->ri_cprmask[0]);
9885 reginfo.ri_cprmask[1] = BYTE_GET (ereg->ri_cprmask[1]);
9886 reginfo.ri_cprmask[2] = BYTE_GET (ereg->ri_cprmask[2]);
9887 reginfo.ri_cprmask[3] = BYTE_GET (ereg->ri_cprmask[3]);
9888 reginfo.ri_gp_value = BYTE_GET (ereg->ri_gp_value);
9890 printf ("GPR %08lx GP 0x%lx\n",
9891 reginfo.ri_gprmask,
9892 (unsigned long) reginfo.ri_gp_value);
9893 printf (" CPR0 %08lx CPR1 %08lx CPR2 %08lx CPR3 %08lx\n",
9894 reginfo.ri_cprmask[0], reginfo.ri_cprmask[1],
9895 reginfo.ri_cprmask[2], reginfo.ri_cprmask[3]);
9897 else
9899 /* 64 bit form. */
9900 Elf64_External_RegInfo *ereg;
9901 Elf64_Internal_RegInfo reginfo;
9903 ereg = (Elf64_External_RegInfo *) (option + 1);
9904 reginfo.ri_gprmask = BYTE_GET (ereg->ri_gprmask);
9905 reginfo.ri_cprmask[0] = BYTE_GET (ereg->ri_cprmask[0]);
9906 reginfo.ri_cprmask[1] = BYTE_GET (ereg->ri_cprmask[1]);
9907 reginfo.ri_cprmask[2] = BYTE_GET (ereg->ri_cprmask[2]);
9908 reginfo.ri_cprmask[3] = BYTE_GET (ereg->ri_cprmask[3]);
9909 reginfo.ri_gp_value = BYTE_GET8 (ereg->ri_gp_value);
9911 printf ("GPR %08lx GP 0x",
9912 reginfo.ri_gprmask);
9913 printf_vma (reginfo.ri_gp_value);
9914 printf ("\n");
9916 printf (" CPR0 %08lx CPR1 %08lx CPR2 %08lx CPR3 %08lx\n",
9917 reginfo.ri_cprmask[0], reginfo.ri_cprmask[1],
9918 reginfo.ri_cprmask[2], reginfo.ri_cprmask[3]);
9920 ++option;
9921 continue;
9922 case ODK_EXCEPTIONS:
9923 fputs (" EXCEPTIONS fpe_min(", stdout);
9924 process_mips_fpe_exception (option->info & OEX_FPU_MIN);
9925 fputs (") fpe_max(", stdout);
9926 process_mips_fpe_exception ((option->info & OEX_FPU_MAX) >> 8);
9927 fputs (")", stdout);
9929 if (option->info & OEX_PAGE0)
9930 fputs (" PAGE0", stdout);
9931 if (option->info & OEX_SMM)
9932 fputs (" SMM", stdout);
9933 if (option->info & OEX_FPDBUG)
9934 fputs (" FPDBUG", stdout);
9935 if (option->info & OEX_DISMISS)
9936 fputs (" DISMISS", stdout);
9937 break;
9938 case ODK_PAD:
9939 fputs (" PAD ", stdout);
9940 if (option->info & OPAD_PREFIX)
9941 fputs (" PREFIX", stdout);
9942 if (option->info & OPAD_POSTFIX)
9943 fputs (" POSTFIX", stdout);
9944 if (option->info & OPAD_SYMBOL)
9945 fputs (" SYMBOL", stdout);
9946 break;
9947 case ODK_HWPATCH:
9948 fputs (" HWPATCH ", stdout);
9949 if (option->info & OHW_R4KEOP)
9950 fputs (" R4KEOP", stdout);
9951 if (option->info & OHW_R8KPFETCH)
9952 fputs (" R8KPFETCH", stdout);
9953 if (option->info & OHW_R5KEOP)
9954 fputs (" R5KEOP", stdout);
9955 if (option->info & OHW_R5KCVTL)
9956 fputs (" R5KCVTL", stdout);
9957 break;
9958 case ODK_FILL:
9959 fputs (" FILL ", stdout);
9960 /* XXX Print content of info word? */
9961 break;
9962 case ODK_TAGS:
9963 fputs (" TAGS ", stdout);
9964 /* XXX Print content of info word? */
9965 break;
9966 case ODK_HWAND:
9967 fputs (" HWAND ", stdout);
9968 if (option->info & OHWA0_R4KEOP_CHECKED)
9969 fputs (" R4KEOP_CHECKED", stdout);
9970 if (option->info & OHWA0_R4KEOP_CLEAN)
9971 fputs (" R4KEOP_CLEAN", stdout);
9972 break;
9973 case ODK_HWOR:
9974 fputs (" HWOR ", stdout);
9975 if (option->info & OHWA0_R4KEOP_CHECKED)
9976 fputs (" R4KEOP_CHECKED", stdout);
9977 if (option->info & OHWA0_R4KEOP_CLEAN)
9978 fputs (" R4KEOP_CLEAN", stdout);
9979 break;
9980 case ODK_GP_GROUP:
9981 printf (" GP_GROUP %#06lx self-contained %#06lx",
9982 option->info & OGP_GROUP,
9983 (option->info & OGP_SELF) >> 16);
9984 break;
9985 case ODK_IDENT:
9986 printf (" IDENT %#06lx self-contained %#06lx",
9987 option->info & OGP_GROUP,
9988 (option->info & OGP_SELF) >> 16);
9989 break;
9990 default:
9991 /* This shouldn't happen. */
9992 printf (" %3d ??? %d %lx",
9993 option->kind, option->section, option->info);
9994 break;
9997 len = sizeof (*eopt);
9998 while (len < option->size)
9999 if (((char *) option)[len] >= ' '
10000 && ((char *) option)[len] < 0x7f)
10001 printf ("%c", ((char *) option)[len++]);
10002 else
10003 printf ("\\%03o", ((char *) option)[len++]);
10005 fputs ("\n", stdout);
10006 ++option;
10009 free (eopt);
10013 if (conflicts_offset != 0 && conflictsno != 0)
10015 Elf32_Conflict *iconf;
10016 size_t cnt;
10018 if (dynamic_symbols == NULL)
10020 error (_("conflict list found without a dynamic symbol table"));
10021 return 0;
10024 iconf = malloc (conflictsno * sizeof (*iconf));
10025 if (iconf == NULL)
10027 error (_("Out of memory"));
10028 return 0;
10031 if (is_32bit_elf)
10033 Elf32_External_Conflict *econf32;
10035 econf32 = get_data (NULL, file, conflicts_offset,
10036 conflictsno * sizeof (*econf32), _("conflict"));
10037 if (!econf32)
10038 return 0;
10040 for (cnt = 0; cnt < conflictsno; ++cnt)
10041 iconf[cnt] = BYTE_GET (econf32[cnt]);
10043 free (econf32);
10045 else
10047 Elf64_External_Conflict *econf64;
10049 econf64 = get_data (NULL, file, conflicts_offset,
10050 conflictsno * sizeof (*econf64), _("conflict"));
10051 if (!econf64)
10052 return 0;
10054 for (cnt = 0; cnt < conflictsno; ++cnt)
10055 iconf[cnt] = BYTE_GET (econf64[cnt]);
10057 free (econf64);
10060 printf (_("\nSection '.conflict' contains %lu entries:\n"),
10061 (unsigned long) conflictsno);
10062 puts (_(" Num: Index Value Name"));
10064 for (cnt = 0; cnt < conflictsno; ++cnt)
10066 Elf_Internal_Sym *psym = & dynamic_symbols[iconf[cnt]];
10068 printf ("%5lu: %8lu ", (unsigned long) cnt, iconf[cnt]);
10069 print_vma (psym->st_value, FULL_HEX);
10070 putchar (' ');
10071 print_symbol (25, dynamic_strings + psym->st_name);
10072 putchar ('\n');
10075 free (iconf);
10078 return 1;
10081 static int
10082 process_gnu_liblist (FILE *file)
10084 Elf_Internal_Shdr *section, *string_sec;
10085 Elf32_External_Lib *elib;
10086 char *strtab;
10087 size_t cnt;
10088 unsigned i;
10090 if (! do_arch)
10091 return 0;
10093 for (i = 0, section = section_headers;
10094 i < elf_header.e_shnum;
10095 i++, section++)
10097 switch (section->sh_type)
10099 case SHT_GNU_LIBLIST:
10100 elib = get_data (NULL, file, section->sh_offset, section->sh_size,
10101 _("liblist"));
10103 if (elib == NULL)
10104 break;
10105 string_sec = SECTION_HEADER (section->sh_link);
10107 strtab = get_data (NULL, file, string_sec->sh_offset,
10108 string_sec->sh_size, _("liblist string table"));
10110 if (strtab == NULL
10111 || section->sh_entsize != sizeof (Elf32_External_Lib))
10113 free (elib);
10114 break;
10117 printf (_("\nLibrary list section '%s' contains %lu entries:\n"),
10118 SECTION_NAME (section),
10119 (long) (section->sh_size / sizeof (Elf32_External_Lib)));
10121 puts (" Library Time Stamp Checksum Version Flags");
10123 for (cnt = 0; cnt < section->sh_size / sizeof (Elf32_External_Lib);
10124 ++cnt)
10126 Elf32_Lib liblist;
10127 time_t time;
10128 char timebuf[20];
10129 struct tm *tmp;
10131 liblist.l_name = BYTE_GET (elib[cnt].l_name);
10132 time = BYTE_GET (elib[cnt].l_time_stamp);
10133 liblist.l_checksum = BYTE_GET (elib[cnt].l_checksum);
10134 liblist.l_version = BYTE_GET (elib[cnt].l_version);
10135 liblist.l_flags = BYTE_GET (elib[cnt].l_flags);
10137 tmp = gmtime (&time);
10138 sprintf (timebuf, "%04u-%02u-%02uT%02u:%02u:%02u",
10139 tmp->tm_year + 1900, tmp->tm_mon + 1, tmp->tm_mday,
10140 tmp->tm_hour, tmp->tm_min, tmp->tm_sec);
10142 printf ("%3lu: ", (unsigned long) cnt);
10143 if (do_wide)
10144 printf ("%-20s", strtab + liblist.l_name);
10145 else
10146 printf ("%-20.20s", strtab + liblist.l_name);
10147 printf (" %s %#010lx %-7ld %-7ld\n", timebuf, liblist.l_checksum,
10148 liblist.l_version, liblist.l_flags);
10151 free (elib);
10155 return 1;
10158 static const char *
10159 get_note_type (unsigned e_type)
10161 static char buff[64];
10163 switch (e_type)
10165 case NT_AUXV: return _("NT_AUXV (auxiliary vector)");
10166 case NT_PRSTATUS: return _("NT_PRSTATUS (prstatus structure)");
10167 case NT_FPREGSET: return _("NT_FPREGSET (floating point registers)");
10168 case NT_PRPSINFO: return _("NT_PRPSINFO (prpsinfo structure)");
10169 case NT_TASKSTRUCT: return _("NT_TASKSTRUCT (task structure)");
10170 case NT_PRXFPREG: return _("NT_PRXFPREG (user_xfpregs structure)");
10171 case NT_PSTATUS: return _("NT_PSTATUS (pstatus structure)");
10172 case NT_FPREGS: return _("NT_FPREGS (floating point registers)");
10173 case NT_PSINFO: return _("NT_PSINFO (psinfo structure)");
10174 case NT_LWPSTATUS: return _("NT_LWPSTATUS (lwpstatus_t structure)");
10175 case NT_LWPSINFO: return _("NT_LWPSINFO (lwpsinfo_t structure)");
10176 case NT_WIN32PSTATUS: return _("NT_WIN32PSTATUS (win32_pstatus structure)");
10177 default:
10178 sprintf (buff, _("Unknown note type: (0x%08x)"), e_type);
10179 return buff;
10183 static const char *
10184 get_netbsd_elfcore_note_type (unsigned e_type)
10186 static char buff[64];
10188 if (e_type == NT_NETBSDCORE_PROCINFO)
10190 /* NetBSD core "procinfo" structure. */
10191 return _("NetBSD procinfo structure");
10194 /* As of Jan 2002 there are no other machine-independent notes
10195 defined for NetBSD core files. If the note type is less
10196 than the start of the machine-dependent note types, we don't
10197 understand it. */
10199 if (e_type < NT_NETBSDCORE_FIRSTMACH)
10201 sprintf (buff, _("Unknown note type: (0x%08x)"), e_type);
10202 return buff;
10205 switch (elf_header.e_machine)
10207 /* On the Alpha, SPARC (32-bit and 64-bit), PT_GETREGS == mach+0
10208 and PT_GETFPREGS == mach+2. */
10210 case EM_OLD_ALPHA:
10211 case EM_ALPHA:
10212 case EM_SPARC:
10213 case EM_SPARC32PLUS:
10214 case EM_SPARCV9:
10215 switch (e_type)
10217 case NT_NETBSDCORE_FIRSTMACH+0:
10218 return _("PT_GETREGS (reg structure)");
10219 case NT_NETBSDCORE_FIRSTMACH+2:
10220 return _("PT_GETFPREGS (fpreg structure)");
10221 default:
10222 break;
10224 break;
10226 /* On all other arch's, PT_GETREGS == mach+1 and
10227 PT_GETFPREGS == mach+3. */
10228 default:
10229 switch (e_type)
10231 case NT_NETBSDCORE_FIRSTMACH+1:
10232 return _("PT_GETREGS (reg structure)");
10233 case NT_NETBSDCORE_FIRSTMACH+3:
10234 return _("PT_GETFPREGS (fpreg structure)");
10235 default:
10236 break;
10240 sprintf (buff, _("PT_FIRSTMACH+%d"), e_type - NT_NETBSDCORE_FIRSTMACH);
10241 return buff;
10244 /* Note that by the ELF standard, the name field is already null byte
10245 terminated, and namesz includes the terminating null byte.
10246 I.E. the value of namesz for the name "FSF" is 4.
10248 If the value of namesz is zero, there is no name present. */
10249 static int
10250 process_note (Elf_Internal_Note *pnote)
10252 const char *nt;
10254 if (pnote->namesz == 0)
10256 /* If there is no note name, then use the default set of
10257 note type strings. */
10258 nt = get_note_type (pnote->type);
10260 else if (strncmp (pnote->namedata, "NetBSD-CORE", 11) == 0)
10262 /* NetBSD-specific core file notes. */
10263 nt = get_netbsd_elfcore_note_type (pnote->type);
10265 else
10267 /* Don't recognize this note name; just use the default set of
10268 note type strings. */
10269 nt = get_note_type (pnote->type);
10272 printf (" %s\t\t0x%08lx\t%s\n",
10273 pnote->namesz ? pnote->namedata : "(NONE)",
10274 pnote->descsz, nt);
10275 return 1;
10279 static int
10280 process_corefile_note_segment (FILE *file, bfd_vma offset, bfd_vma length)
10282 Elf_External_Note *pnotes;
10283 Elf_External_Note *external;
10284 int res = 1;
10286 if (length <= 0)
10287 return 0;
10289 pnotes = get_data (NULL, file, offset, length, _("notes"));
10290 if (!pnotes)
10291 return 0;
10293 external = pnotes;
10295 printf (_("\nNotes at offset 0x%08lx with length 0x%08lx:\n"),
10296 (unsigned long) offset, (unsigned long) length);
10297 printf (_(" Owner\t\tData size\tDescription\n"));
10299 while (external < (Elf_External_Note *)((char *) pnotes + length))
10301 Elf_External_Note *next;
10302 Elf_Internal_Note inote;
10303 char *temp = NULL;
10305 inote.type = BYTE_GET (external->type);
10306 inote.namesz = BYTE_GET (external->namesz);
10307 inote.namedata = external->name;
10308 inote.descsz = BYTE_GET (external->descsz);
10309 inote.descdata = inote.namedata + align_power (inote.namesz, 2);
10310 inote.descpos = offset + (inote.descdata - (char *) pnotes);
10312 next = (Elf_External_Note *)(inote.descdata + align_power (inote.descsz, 2));
10314 if (((char *) next) > (((char *) pnotes) + length))
10316 warn (_("corrupt note found at offset %x into core notes\n"),
10317 ((char *) external) - ((char *) pnotes));
10318 warn (_(" type: %x, namesize: %08lx, descsize: %08lx\n"),
10319 inote.type, inote.namesz, inote.descsz);
10320 break;
10323 external = next;
10325 /* Verify that name is null terminated. It appears that at least
10326 one version of Linux (RedHat 6.0) generates corefiles that don't
10327 comply with the ELF spec by failing to include the null byte in
10328 namesz. */
10329 if (inote.namedata[inote.namesz] != '\0')
10331 temp = malloc (inote.namesz + 1);
10333 if (temp == NULL)
10335 error (_("Out of memory\n"));
10336 res = 0;
10337 break;
10340 strncpy (temp, inote.namedata, inote.namesz);
10341 temp[inote.namesz] = 0;
10343 /* warn (_("'%s' NOTE name not properly null terminated\n"), temp); */
10344 inote.namedata = temp;
10347 res &= process_note (& inote);
10349 if (temp != NULL)
10351 free (temp);
10352 temp = NULL;
10356 free (pnotes);
10358 return res;
10361 static int
10362 process_corefile_note_segments (FILE *file)
10364 Elf_Internal_Phdr *segment;
10365 unsigned int i;
10366 int res = 1;
10368 if (! get_program_headers (file))
10369 return 0;
10371 for (i = 0, segment = program_headers;
10372 i < elf_header.e_phnum;
10373 i++, segment++)
10375 if (segment->p_type == PT_NOTE)
10376 res &= process_corefile_note_segment (file,
10377 (bfd_vma) segment->p_offset,
10378 (bfd_vma) segment->p_filesz);
10381 return res;
10384 static int
10385 process_corefile_contents (FILE *file)
10387 /* If we have not been asked to display the notes then do nothing. */
10388 if (! do_notes)
10389 return 1;
10391 /* If file is not a core file then exit. */
10392 if (elf_header.e_type != ET_CORE)
10393 return 1;
10395 /* No program headers means no NOTE segment. */
10396 if (elf_header.e_phnum == 0)
10398 printf (_("No note segments present in the core file.\n"));
10399 return 1;
10402 return process_corefile_note_segments (file);
10405 static int
10406 process_arch_specific (FILE *file)
10408 if (! do_arch)
10409 return 1;
10411 switch (elf_header.e_machine)
10413 case EM_MIPS:
10414 case EM_MIPS_RS3_LE:
10415 return process_mips_specific (file);
10416 break;
10417 default:
10418 break;
10420 return 1;
10423 static int
10424 get_file_header (FILE *file)
10426 /* Read in the identity array. */
10427 if (fread (elf_header.e_ident, EI_NIDENT, 1, file) != 1)
10428 return 0;
10430 /* Determine how to read the rest of the header. */
10431 switch (elf_header.e_ident[EI_DATA])
10433 default: /* fall through */
10434 case ELFDATANONE: /* fall through */
10435 case ELFDATA2LSB:
10436 byte_get = byte_get_little_endian;
10437 byte_put = byte_put_little_endian;
10438 break;
10439 case ELFDATA2MSB:
10440 byte_get = byte_get_big_endian;
10441 byte_put = byte_put_big_endian;
10442 break;
10445 /* For now we only support 32 bit and 64 bit ELF files. */
10446 is_32bit_elf = (elf_header.e_ident[EI_CLASS] != ELFCLASS64);
10448 /* Read in the rest of the header. */
10449 if (is_32bit_elf)
10451 Elf32_External_Ehdr ehdr32;
10453 if (fread (ehdr32.e_type, sizeof (ehdr32) - EI_NIDENT, 1, file) != 1)
10454 return 0;
10456 elf_header.e_type = BYTE_GET (ehdr32.e_type);
10457 elf_header.e_machine = BYTE_GET (ehdr32.e_machine);
10458 elf_header.e_version = BYTE_GET (ehdr32.e_version);
10459 elf_header.e_entry = BYTE_GET (ehdr32.e_entry);
10460 elf_header.e_phoff = BYTE_GET (ehdr32.e_phoff);
10461 elf_header.e_shoff = BYTE_GET (ehdr32.e_shoff);
10462 elf_header.e_flags = BYTE_GET (ehdr32.e_flags);
10463 elf_header.e_ehsize = BYTE_GET (ehdr32.e_ehsize);
10464 elf_header.e_phentsize = BYTE_GET (ehdr32.e_phentsize);
10465 elf_header.e_phnum = BYTE_GET (ehdr32.e_phnum);
10466 elf_header.e_shentsize = BYTE_GET (ehdr32.e_shentsize);
10467 elf_header.e_shnum = BYTE_GET (ehdr32.e_shnum);
10468 elf_header.e_shstrndx = BYTE_GET (ehdr32.e_shstrndx);
10470 else
10472 Elf64_External_Ehdr ehdr64;
10474 /* If we have been compiled with sizeof (bfd_vma) == 4, then
10475 we will not be able to cope with the 64bit data found in
10476 64 ELF files. Detect this now and abort before we start
10477 overwriting things. */
10478 if (sizeof (bfd_vma) < 8)
10480 error (_("This instance of readelf has been built without support for a\n\
10481 64 bit data type and so it cannot read 64 bit ELF files.\n"));
10482 return 0;
10485 if (fread (ehdr64.e_type, sizeof (ehdr64) - EI_NIDENT, 1, file) != 1)
10486 return 0;
10488 elf_header.e_type = BYTE_GET (ehdr64.e_type);
10489 elf_header.e_machine = BYTE_GET (ehdr64.e_machine);
10490 elf_header.e_version = BYTE_GET (ehdr64.e_version);
10491 elf_header.e_entry = BYTE_GET8 (ehdr64.e_entry);
10492 elf_header.e_phoff = BYTE_GET8 (ehdr64.e_phoff);
10493 elf_header.e_shoff = BYTE_GET8 (ehdr64.e_shoff);
10494 elf_header.e_flags = BYTE_GET (ehdr64.e_flags);
10495 elf_header.e_ehsize = BYTE_GET (ehdr64.e_ehsize);
10496 elf_header.e_phentsize = BYTE_GET (ehdr64.e_phentsize);
10497 elf_header.e_phnum = BYTE_GET (ehdr64.e_phnum);
10498 elf_header.e_shentsize = BYTE_GET (ehdr64.e_shentsize);
10499 elf_header.e_shnum = BYTE_GET (ehdr64.e_shnum);
10500 elf_header.e_shstrndx = BYTE_GET (ehdr64.e_shstrndx);
10503 if (elf_header.e_shoff)
10505 /* There may be some extensions in the first section header. Don't
10506 bomb if we can't read it. */
10507 if (is_32bit_elf)
10508 get_32bit_section_headers (file, 1);
10509 else
10510 get_64bit_section_headers (file, 1);
10513 return 1;
10516 /* Process one ELF object file according to the command line options.
10517 This file may actually be stored in an archive. The file is
10518 positioned at the start of the ELF object. */
10520 static int
10521 process_object (char *file_name, FILE *file)
10523 unsigned int i;
10525 if (! get_file_header (file))
10527 error (_("%s: Failed to read file header\n"), file_name);
10528 return 1;
10531 /* Initialise per file variables. */
10532 for (i = NUM_ELEM (version_info); i--;)
10533 version_info[i] = 0;
10535 for (i = NUM_ELEM (dynamic_info); i--;)
10536 dynamic_info[i] = 0;
10538 /* Process the file. */
10539 if (show_name)
10540 printf (_("\nFile: %s\n"), file_name);
10542 if (! process_file_header ())
10543 return 1;
10545 if (! process_section_headers (file)
10546 || ! process_section_groups (file))
10548 /* Without loaded section headers and section groups we
10549 cannot process lots of things. */
10550 do_unwind = do_version = do_dump = do_arch = 0;
10552 if (! do_using_dynamic)
10553 do_syms = do_reloc = 0;
10556 if (process_program_headers (file))
10557 process_dynamic_segment (file);
10559 process_relocs (file);
10561 process_unwind (file);
10563 process_symbol_table (file);
10565 process_syminfo (file);
10567 process_version_sections (file);
10569 process_section_contents (file);
10571 process_corefile_contents (file);
10573 process_gnu_liblist (file);
10575 process_arch_specific (file);
10577 if (program_headers)
10579 free (program_headers);
10580 program_headers = NULL;
10583 if (section_headers)
10585 free (section_headers);
10586 section_headers = NULL;
10589 if (string_table)
10591 free (string_table);
10592 string_table = NULL;
10593 string_table_length = 0;
10596 if (dynamic_strings)
10598 free (dynamic_strings);
10599 dynamic_strings = NULL;
10602 if (dynamic_symbols)
10604 free (dynamic_symbols);
10605 dynamic_symbols = NULL;
10606 num_dynamic_syms = 0;
10609 if (dynamic_syminfo)
10611 free (dynamic_syminfo);
10612 dynamic_syminfo = NULL;
10615 if (section_headers_groups)
10617 free (section_headers_groups);
10618 section_headers_groups = NULL;
10621 if (section_groups)
10623 struct group_list *g, *next;
10625 for (i = 0; i < group_count; i++)
10627 for (g = section_groups [i].root; g != NULL; g = next)
10629 next = g->next;
10630 free (g);
10634 free (section_groups);
10635 section_groups = NULL;
10638 return 0;
10641 /* Process an ELF archive. The file is positioned just after the
10642 ARMAG string. */
10644 static int
10645 process_archive (char *file_name, FILE *file)
10647 struct ar_hdr arhdr;
10648 size_t got;
10649 unsigned long size;
10650 char *longnames = NULL;
10651 unsigned long longnames_size = 0;
10652 size_t file_name_size;
10653 int ret;
10655 show_name = 1;
10657 got = fread (&arhdr, 1, sizeof arhdr, file);
10658 if (got != sizeof arhdr)
10660 if (got == 0)
10661 return 0;
10663 error (_("%s: failed to read archive header\n"), file_name);
10664 return 1;
10667 if (memcmp (arhdr.ar_name, "/ ", 16) == 0)
10669 /* This is the archive symbol table. Skip it.
10670 FIXME: We should have an option to dump it. */
10671 size = strtoul (arhdr.ar_size, NULL, 10);
10672 if (fseek (file, size + (size & 1), SEEK_CUR) != 0)
10674 error (_("%s: failed to skip archive symbol table\n"), file_name);
10675 return 1;
10678 got = fread (&arhdr, 1, sizeof arhdr, file);
10679 if (got != sizeof arhdr)
10681 if (got == 0)
10682 return 0;
10684 error (_("%s: failed to read archive header\n"), file_name);
10685 return 1;
10689 if (memcmp (arhdr.ar_name, "// ", 16) == 0)
10691 /* This is the archive string table holding long member
10692 names. */
10694 longnames_size = strtoul (arhdr.ar_size, NULL, 10);
10696 longnames = malloc (longnames_size);
10697 if (longnames == NULL)
10699 error (_("Out of memory\n"));
10700 return 1;
10703 if (fread (longnames, longnames_size, 1, file) != 1)
10705 free (longnames);
10706 error(_("%s: failed to read string table\n"), file_name);
10707 return 1;
10710 if ((longnames_size & 1) != 0)
10711 getc (file);
10713 got = fread (&arhdr, 1, sizeof arhdr, file);
10714 if (got != sizeof arhdr)
10716 free (longnames);
10718 if (got == 0)
10719 return 0;
10721 error (_("%s: failed to read archive header\n"), file_name);
10722 return 1;
10726 file_name_size = strlen (file_name);
10727 ret = 0;
10729 while (1)
10731 char *name;
10732 char *nameend;
10733 char *namealc;
10735 if (arhdr.ar_name[0] == '/')
10737 unsigned long off;
10739 off = strtoul (arhdr.ar_name + 1, NULL, 10);
10740 if (off >= longnames_size)
10742 error (_("%s: invalid archive string table offset %lu\n"), off);
10743 ret = 1;
10744 break;
10747 name = longnames + off;
10748 nameend = memchr (name, '/', longnames_size - off);
10750 else
10752 name = arhdr.ar_name;
10753 nameend = memchr (name, '/', 16);
10756 if (nameend == NULL)
10758 error (_("%s: bad archive file name\n"));
10759 ret = 1;
10760 break;
10763 namealc = malloc (file_name_size + (nameend - name) + 3);
10764 if (namealc == NULL)
10766 error (_("Out of memory\n"));
10767 ret = 1;
10768 break;
10771 memcpy (namealc, file_name, file_name_size);
10772 namealc[file_name_size] = '(';
10773 memcpy (namealc + file_name_size + 1, name, nameend - name);
10774 namealc[file_name_size + 1 + (nameend - name)] = ')';
10775 namealc[file_name_size + 2 + (nameend - name)] = '\0';
10777 archive_file_offset = ftell (file);
10778 archive_file_size = strtoul (arhdr.ar_size, NULL, 10);
10780 ret |= process_object (namealc, file);
10782 free (namealc);
10784 if (fseek (file,
10785 (archive_file_offset
10786 + archive_file_size
10787 + (archive_file_size & 1)),
10788 SEEK_SET) != 0)
10790 error (_("%s: failed to seek to next archive header\n"), file_name);
10791 ret = 1;
10792 break;
10795 got = fread (&arhdr, 1, sizeof arhdr, file);
10796 if (got != sizeof arhdr)
10798 if (got == 0)
10799 break;
10801 error (_("%s: failed to read archive header\n"), file_name);
10802 ret = 1;
10803 break;
10807 if (longnames != 0)
10808 free (longnames);
10810 return ret;
10813 static int
10814 process_file (char *file_name)
10816 FILE *file;
10817 struct stat statbuf;
10818 char armag[SARMAG];
10819 int ret;
10821 if (stat (file_name, &statbuf) < 0)
10823 if (errno == ENOENT)
10824 error (_("'%s': No such file\n"), file_name);
10825 else
10826 error (_("Could not locate '%s'. System error message: %s\n"),
10827 file_name, strerror (errno));
10828 return 1;
10831 if (! S_ISREG (statbuf.st_mode))
10833 error (_("'%s' is not an ordinary file\n"), file_name);
10834 return 1;
10837 file = fopen (file_name, "rb");
10838 if (file == NULL)
10840 error (_("Input file '%s' is not readable.\n"), file_name);
10841 return 1;
10844 if (fread (armag, SARMAG, 1, file) != 1)
10846 error (_("%s: Failed to read file header\n"), file_name);
10847 fclose (file);
10848 return 1;
10851 if (memcmp (armag, ARMAG, SARMAG) == 0)
10852 ret = process_archive (file_name, file);
10853 else
10855 rewind (file);
10856 archive_file_size = archive_file_offset = 0;
10857 ret = process_object (file_name, file);
10860 fclose (file);
10862 return ret;
10865 #ifdef SUPPORT_DISASSEMBLY
10866 /* Needed by the i386 disassembler. For extra credit, someone could
10867 fix this so that we insert symbolic addresses here, esp for GOT/PLT
10868 symbols. */
10870 void
10871 print_address (unsigned int addr, FILE *outfile)
10873 fprintf (outfile,"0x%8.8x", addr);
10876 /* Needed by the i386 disassembler. */
10877 void
10878 db_task_printsym (unsigned int addr)
10880 print_address (addr, stderr);
10882 #endif
10885 main (int argc, char **argv)
10887 int err;
10888 char *cmdline_dump_sects = NULL;
10889 unsigned num_cmdline_dump_sects = 0;
10891 #if defined (HAVE_SETLOCALE) && defined (HAVE_LC_MESSAGES)
10892 setlocale (LC_MESSAGES, "");
10893 #endif
10894 #if defined (HAVE_SETLOCALE)
10895 setlocale (LC_CTYPE, "");
10896 #endif
10897 bindtextdomain (PACKAGE, LOCALEDIR);
10898 textdomain (PACKAGE);
10900 parse_args (argc, argv);
10902 if (optind < (argc - 1))
10903 show_name = 1;
10905 /* When processing more than one file remember the dump requests
10906 issued on command line to reset them after each file. */
10907 if (optind + 1 < argc && dump_sects != NULL)
10909 cmdline_dump_sects = malloc (num_dump_sects);
10910 if (cmdline_dump_sects == NULL)
10911 error (_("Out of memory allocating dump request table."));
10912 else
10914 memcpy (cmdline_dump_sects, dump_sects, num_dump_sects);
10915 num_cmdline_dump_sects = num_dump_sects;
10919 err = 0;
10920 while (optind < argc)
10922 err |= process_file (argv[optind++]);
10924 /* Reset dump requests. */
10925 if (optind < argc && dump_sects != NULL)
10927 num_dump_sects = num_cmdline_dump_sects;
10928 if (num_cmdline_dump_sects > 0)
10929 memcpy (dump_sects, cmdline_dump_sects, num_cmdline_dump_sects);
10933 if (dump_sects != NULL)
10934 free (dump_sects);
10935 if (cmdline_dump_sects != NULL)
10936 free (cmdline_dump_sects);
10938 return err;