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