* objdump.c (disassemble_data): Handle the m88k.
[binutils-gdb.git] / binutils / objdump.c
1 /* objdump.c -- dump information about an object file.
2 Copyright 1990, 1991, 1992, 1993 Free Software Foundation, Inc.
3
4 This file is part of GNU Binutils.
5
6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2, or (at your option)
9 any later version.
10
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with this program; if not, write to the Free Software
18 Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
19
20 #include "bfd.h"
21 #include "sysdep.h"
22 #include "getopt.h"
23 #include <stdio.h>
24 #include <ctype.h>
25 #include "dis-asm.h"
26
27 #define ELF_STAB_DISPLAY /* This code works, but uses internal
28 bfd and elf stuff. Flip this define
29 off if you need to just use generic
30 BFD interfaces. */
31
32 #ifdef ELF_STAB_DISPLAY
33 /* Internal headers for the ELF .stab-dump code - sorry. */
34 #define BYTES_IN_WORD 32
35 #include "aout/aout64.h"
36 #include "elf/internal.h"
37 extern Elf_Internal_Shdr *bfd_elf_find_section();
38 #endif /* ELF_STAB_DISPLAY */
39
40 extern char *xmalloc ();
41 extern int fprintf PARAMS ((FILE *, CONST char *, ...));
42
43 char *default_target = NULL; /* default at runtime */
44
45 extern *program_version;
46 char *program_name = NULL;
47
48 int show_version = 0; /* show the version number */
49 int dump_section_contents; /* -s */
50 int dump_section_headers; /* -h */
51 boolean dump_file_header; /* -f */
52 int dump_symtab; /* -t */
53 int dump_reloc_info; /* -r */
54 int dump_ar_hdrs; /* -a */
55 int with_line_numbers; /* -l */
56 int dump_stab_section_info; /* -stabs */
57 boolean disassemble; /* -d */
58 boolean info; /* -i */
59 char *only;
60
61 char *machine = (char *) NULL;
62 asymbol **syms;
63
64 unsigned int storage;
65
66 unsigned int symcount = 0;
67
68 /* Forward declarations. */
69
70 static void
71 display_file PARAMS ((char *filename, char *target));
72
73 static void
74 dump_data PARAMS ((bfd *abfd));
75
76 static void
77 dump_relocs PARAMS ((bfd *abfd));
78
79 static void
80 dump_symbols PARAMS ((bfd *abfd));
81 \f
82 void
83 usage (stream, status)
84 FILE *stream;
85 int status;
86 {
87 fprintf (stream, "\
88 Usage: %s [-ahifdrtxsl] [-m machine] [-j section_name] [-b bfdname]\n\
89 [--syms] [--reloc] [--header] [--version] [--help] objfile...\n",
90 program_name);
91 exit (status);
92 }
93
94 static struct option long_options[]=
95 {
96 {"syms", no_argument, &dump_symtab, 1},
97 {"reloc", no_argument, &dump_reloc_info, 1},
98 {"header", no_argument, &dump_section_headers, 1},
99 {"version", no_argument, &show_version, 1},
100 {"help", no_argument, 0, 'H'},
101 #ifdef ELF_STAB_DISPLAY
102 {"stabs", no_argument, &dump_stab_section_info, 1},
103 #endif
104 {0, no_argument, 0, 0}
105 };
106
107
108 static void
109 dump_headers (abfd)
110 bfd *abfd;
111 {
112 asection *section;
113
114 for (section = abfd->sections;
115 section != (asection *) NULL;
116 section = section->next)
117 {
118 char *comma = "";
119
120 #define PF(x,y) \
121 if (section->flags & x) { printf("%s%s",comma,y); comma = ", "; }
122
123
124 printf ("SECTION %d [%s]\t: size %08x",
125 section->index,
126 section->name,
127 (unsigned) bfd_get_section_size_before_reloc (section));
128 printf (" vma ");
129 printf_vma (section->vma);
130 printf (" align 2**%u\n ",
131 section->alignment_power);
132 PF (SEC_ALLOC, "ALLOC");
133 PF (SEC_CONSTRUCTOR, "CONSTRUCTOR");
134 PF (SEC_CONSTRUCTOR_TEXT, "CONSTRUCTOR TEXT");
135 PF (SEC_CONSTRUCTOR_DATA, "CONSTRUCTOR DATA");
136 PF (SEC_CONSTRUCTOR_BSS, "CONSTRUCTOR BSS");
137 PF (SEC_LOAD, "LOAD");
138 PF (SEC_RELOC, "RELOC");
139 PF (SEC_BALIGN, "BALIGN");
140 PF (SEC_READONLY, "READONLY");
141 PF (SEC_CODE, "CODE");
142 PF (SEC_DATA, "DATA");
143 PF (SEC_ROM, "ROM");
144 printf ("\n");
145 #undef PF
146 }
147 }
148
149 static asymbol **
150 DEFUN (slurp_symtab, (abfd),
151 bfd * abfd)
152 {
153 asymbol **sy = (asymbol **) NULL;
154
155 if (!(bfd_get_file_flags (abfd) & HAS_SYMS))
156 {
157 (void) printf ("No symbols in \"%s\".\n", bfd_get_filename (abfd));
158 return (NULL);
159 }
160
161 storage = get_symtab_upper_bound (abfd);
162 if (storage)
163 {
164 sy = (asymbol **) malloc (storage);
165 if (sy == NULL)
166 {
167 fprintf (stderr, "%s: out of memory.\n", program_name);
168 exit (1);
169 }
170 }
171 symcount = bfd_canonicalize_symtab (abfd, sy);
172 if (symcount <= 0)
173 {
174 fprintf (stderr, "%s: Bad symbol table in \"%s\".\n",
175 program_name, bfd_get_filename (abfd));
176 exit (1);
177 }
178 return sy;
179 }
180
181 /* Filter out (in place) symbols that are useless for dis-assemble.
182 Return count of useful symbols. */
183
184 int remove_useless_symbols (syms, count)
185 asymbol **syms;
186 int count;
187 {
188 register asymbol **in_ptr = syms;
189 register asymbol **out_ptr = syms;
190
191 while ( --count >= 0 )
192 {
193 asymbol *sym = *in_ptr++;
194
195 if (sym->name == NULL || sym->name[0] == '\0')
196 continue;
197 if (sym->flags & (BSF_DEBUGGING))
198 continue;
199 if (sym->section == &bfd_und_section
200 || bfd_is_com_section (sym->section))
201 continue;
202
203 *out_ptr++ = sym;
204 }
205 return out_ptr - syms;
206 }
207
208
209 /* Sort symbols into value order */
210 static int
211 comp (ap, bp)
212 PTR ap;
213 PTR bp;
214 {
215 asymbol *a = *(asymbol **)ap;
216 asymbol *b = *(asymbol **)bp;
217
218 if (a->value > b->value)
219 return 1;
220 else if (a->value < b->value)
221 return -1;
222
223 if (a->section > b->section)
224 return 1;
225 else if (a->section < b->section)
226 return -1;
227 return 0;
228 }
229
230 /* Print the supplied address symbolically if possible */
231 void
232 objdump_print_address (vma, info)
233 bfd_vma vma;
234 struct disassemble_info *info;
235 {
236 /* Perform a binary search looking for the closest symbol to
237 the required value */
238
239 unsigned int min = 0;
240 unsigned int max = symcount;
241
242 unsigned int thisplace = 1;
243 unsigned int oldthisplace;
244
245 int vardiff;
246
247 fprintf_vma (info->stream, vma);
248
249 if (symcount > 0)
250 {
251 while (true)
252 {
253 asymbol *sym; asection *sym_sec;
254 oldthisplace = thisplace;
255 thisplace = (max + min) / 2;
256 if (thisplace == oldthisplace)
257 break;
258 sym = syms[thisplace];
259 vardiff = sym->value - vma;
260 sym_sec = sym->section;
261
262 if (vardiff > 0)
263 max = thisplace;
264 else if (vardiff < 0)
265 min = thisplace;
266 else
267 goto found;
268 }
269 /* We've run out of places to look, print the symbol before this one
270 see if this or the symbol before describes this location the best */
271
272 if (thisplace != 0)
273 {
274 if (syms[thisplace - 1]->value - vma >
275 syms[thisplace]->value - vma)
276 {
277 /* Previous symbol is in correct section and is closer */
278 thisplace--;
279 }
280 }
281
282 found:
283 fprintf (info->stream, " <%s", syms[thisplace]->name);
284 if (syms[thisplace]->value > vma)
285 {
286 char buf[30], *p = buf;
287 sprintf_vma (buf, syms[thisplace]->value - vma);
288 while (*p == '0')
289 p++;
290 fprintf (info->stream, "-%s", p);
291 }
292 else if (vma > syms[thisplace]->value)
293 {
294 char buf[30], *p = buf;
295 sprintf_vma (buf, vma - syms[thisplace]->value);
296 while (*p == '0')
297 p++;
298 fprintf (info->stream, "+%s", p);
299 }
300 fprintf (info->stream, ">");
301 }
302 }
303
304 void
305 disassemble_data (abfd)
306 bfd *abfd;
307 {
308 bfd_byte *data = NULL;
309 bfd_arch_info_type *info;
310 bfd_size_type datasize = 0;
311 bfd_size_type i;
312 unsigned int (*print) ()= 0; /* Old style */
313 disassembler_ftype disassemble = 0; /* New style */
314 enum bfd_architecture a;
315 struct disassemble_info disasm_info;
316
317 int prevline;
318 CONST char *prev_function = "";
319
320 asection *section;
321
322 /* Replace symbol section relative values with abs values */
323 boolean done_dot = false;
324
325 INIT_DISASSEMBLE_INFO(disasm_info, stdout);
326 disasm_info.print_address_func = objdump_print_address;
327
328 for (i = 0; i < symcount; i++)
329 {
330 syms[i]->value += syms[i]->section->vma;
331 }
332
333 symcount = remove_useless_symbols (syms, symcount);
334
335 /* Sort the symbols into section and symbol order */
336 (void) qsort (syms, symcount, sizeof (asymbol *), comp);
337
338 if (machine != (char *) NULL)
339 {
340 info = bfd_scan_arch (machine);
341 if (info == 0)
342 {
343 fprintf (stderr, "%s: Can't use supplied machine %s\n",
344 program_name,
345 machine);
346 exit (1);
347 }
348 abfd->arch_info = info;
349 }
350
351 /* See if we can disassemble using bfd */
352
353 if (abfd->arch_info->disassemble)
354 {
355 print = abfd->arch_info->disassemble;
356 }
357 else
358 {
359 a = bfd_get_arch (abfd);
360 switch (a)
361 {
362 case bfd_arch_sparc:
363 disassemble = print_insn_sparc;
364 break;
365 case bfd_arch_z8k:
366 if (bfd_get_mach(abfd) == bfd_mach_z8001)
367 disassemble = print_insn_z8001;
368 else
369 disassemble = print_insn_z8002;
370 break;
371 case bfd_arch_i386:
372 disassemble = print_insn_i386;
373 break;
374 case bfd_arch_h8500:
375 disassemble = print_insn_h8500;
376 break;
377 case bfd_arch_h8300:
378 if (bfd_get_mach(abfd) == bfd_mach_h8300h)
379 disassemble = print_insn_h8300h;
380 else
381 disassemble = print_insn_h8300;
382 break;
383 case bfd_arch_sh:
384 disassemble = print_insn_sh;
385 break;
386 case bfd_arch_alpha:
387 disassemble = print_insn_alpha;
388 break;
389 case bfd_arch_m68k:
390 disassemble = print_insn_m68k;
391 break;
392 case bfd_arch_a29k:
393 /* As far as I know we only handle big-endian 29k objects. */
394 disassemble = print_insn_big_a29k;
395 break;
396 case bfd_arch_i960:
397 disassemble = print_insn_i960;
398 break;
399 case bfd_arch_m88k:
400 disassemble = print_insn_m88k;
401 break;
402 case bfd_arch_mips:
403 if (abfd->xvec->byteorder_big_p)
404 disassemble = print_insn_big_mips;
405 else
406 disassemble = print_insn_little_mips;
407 break;
408 default:
409 fprintf (stderr, "%s: Can't disassemble for architecture %s\n",
410 program_name,
411 bfd_printable_arch_mach (bfd_get_arch (abfd), 0));
412 exit (1);
413 }
414
415 }
416
417 for (section = abfd->sections;
418 section != (asection *) NULL;
419 section = section->next)
420 {
421
422 if ((section->flags & SEC_LOAD)
423 && (only == (char *) NULL || strcmp (only, section->name) == 0))
424 {
425 printf ("Disassembly of section %s:\n", section->name);
426
427 if (bfd_get_section_size_before_reloc (section) == 0)
428 continue;
429
430 data = (bfd_byte *) malloc (bfd_get_section_size_before_reloc (section));
431
432 if (data == (bfd_byte *) NULL)
433 {
434 fprintf (stderr, "%s: memory exhausted.\n", program_name);
435 exit (1);
436 }
437 datasize = bfd_get_section_size_before_reloc (section);
438
439 bfd_get_section_contents (abfd, section, data, 0, bfd_get_section_size_before_reloc (section));
440
441 disasm_info.buffer = data;
442 disasm_info.buffer_vma = section->vma;
443 disasm_info.buffer_length =
444 bfd_get_section_size_before_reloc (section);
445 i = 0;
446 while (i < disasm_info.buffer_length)
447 {
448 if (data[i] == 0 && data[i + 1] == 0 && data[i + 2] == 0 &&
449 data[i + 3] == 0)
450 {
451 if (done_dot == false)
452 {
453 printf ("...\n");
454 done_dot = true;
455 }
456 i += 4;
457 }
458 else
459 {
460 done_dot = false;
461 if (with_line_numbers)
462 {
463 CONST char *filename;
464 CONST char *functionname;
465 unsigned int line;
466
467 if (bfd_find_nearest_line (abfd,
468 section,
469 syms,
470 section->vma + i,
471 &filename,
472 &functionname,
473 &line))
474 {
475 if (functionname && *functionname
476 && strcmp(functionname, prev_function))
477 {
478 printf ("%s():\n", functionname);
479 prev_function = functionname;
480 }
481 if (!filename)
482 filename = "???";
483 if (line && line != prevline)
484 {
485 printf ("%s:%u\n", filename, line);
486 prevline = line;
487 }
488 }
489 }
490 objdump_print_address (section->vma + i, &disasm_info);
491 printf (" ");
492
493 if (disassemble) /* New style */
494 {
495 int bytes = (*disassemble)(section->vma + i,
496 &disasm_info);
497 if (bytes < 0)
498 break;
499 i += bytes;
500 }
501 else /* Old style */
502 i += print (section->vma + i,
503 data + i,
504 stdout);
505 putchar ('\n');
506 }
507 }
508 free (data);
509 }
510 }
511 }
512 \f
513 #ifdef ELF_STAB_DISPLAY
514
515 /* Define a table of stab values and print-strings. We wish the initializer
516 could be a direct-mapped table, but instead we build one the first
517 time we need it. */
518
519 #define STAB_STRING_LENGTH 6
520
521 char stab_name[256][STAB_STRING_LENGTH];
522
523 struct stab_print {
524 int value;
525 char string[STAB_STRING_LENGTH];
526 };
527
528 struct stab_print stab_print[] = {
529 #define __define_stab(NAME, CODE, STRING) {CODE, STRING},
530 #include "aout/stab.def"
531 #undef __define_stab
532 {0, 0}
533 };
534
535 void dump_elf_stabs_1 ();
536
537 /* This is a kludge for dumping the stabs section from an ELF file that
538 uses Sun stabs encoding. It has to use some hooks into BFD because
539 string table sections are not normally visible to BFD callers. */
540
541 void
542 dump_elf_stabs (abfd)
543 bfd *abfd;
544 {
545 int i;
546
547 /* Initialize stab name array if first time. */
548 if (stab_name[0][0] == 0)
549 {
550 /* Fill in numeric values for all possible strings. */
551 for (i = 0; i < 256; i++)
552 {
553 sprintf (stab_name[i], "%d", i);
554 }
555 for (i = 0; stab_print[i].string[0]; i++)
556 strcpy (stab_name[stab_print[i].value], stab_print[i].string);
557 }
558
559 if (0 != strncmp ("elf", abfd->xvec->name, 3))
560 {
561 fprintf (stderr, "%s: %s is not in ELF format.\n", program_name,
562 abfd->filename);
563 return;
564 }
565
566 dump_elf_stabs_1 (abfd, ".stab", ".stabstr");
567 dump_elf_stabs_1 (abfd, ".stab.excl", ".stab.exclstr");
568 dump_elf_stabs_1 (abfd, ".stab.index", ".stab.indexstr");
569 }
570
571 void
572 dump_elf_stabs_1 (abfd, name1, name2)
573 bfd *abfd;
574 char *name1; /* Section name of .stab */
575 char *name2; /* Section name of its string section */
576 {
577 Elf_Internal_Shdr *stab_hdr, *stabstr_hdr;
578 char *strtab;
579 struct internal_nlist *stabs, *stabs_end;
580 int i;
581 unsigned file_string_table_offset, next_file_string_table_offset;
582
583 stab_hdr = bfd_elf_find_section (abfd, name1);
584 if (0 == stab_hdr)
585 {
586 printf ("Contents of %s section: none.\n\n", name1);
587 return;
588 }
589
590 stabstr_hdr = bfd_elf_find_section (abfd, name2);
591 if (0 == stabstr_hdr)
592 {
593 fprintf (stderr, "%s: %s has no %s section.\n", program_name,
594 abfd->filename, name2);
595 return;
596 }
597
598 stabs = (struct internal_nlist *) xmalloc (stab_hdr ->sh_size);
599 strtab = (char *) xmalloc (stabstr_hdr->sh_size);
600 stabs_end = (struct internal_nlist *) (stab_hdr->sh_size + (char *)stabs);
601
602 if (bfd_seek (abfd, stab_hdr->sh_offset, SEEK_SET) < 0 ||
603 stab_hdr->sh_size != bfd_read ((PTR)stabs, stab_hdr->sh_size, 1, abfd))
604 {
605 fprintf (stderr, "%s: reading %s section of %s failed.\n",
606 program_name, name1,
607 abfd->filename);
608 return;
609 }
610
611 if (bfd_seek (abfd, stabstr_hdr->sh_offset, SEEK_SET) < 0 ||
612 stabstr_hdr->sh_size != bfd_read ((PTR)strtab, stabstr_hdr->sh_size,
613 1, abfd))
614 {
615 fprintf (stderr, "%s: reading %s section of %s failed.\n",
616 program_name, name2,
617 abfd->filename);
618 return;
619 }
620
621 #define SWAP_SYMBOL(symp, abfd) \
622 { \
623 (symp)->n_strx = bfd_h_get_32(abfd, \
624 (unsigned char *)&(symp)->n_strx); \
625 (symp)->n_desc = bfd_h_get_16 (abfd, \
626 (unsigned char *)&(symp)->n_desc); \
627 (symp)->n_value = bfd_h_get_32 (abfd, \
628 (unsigned char *)&(symp)->n_value); \
629 }
630
631 printf ("Contents of %s section:\n\n", name1);
632 printf ("Symnum n_type n_othr n_desc n_value n_strx String\n");
633
634 file_string_table_offset = 0;
635 next_file_string_table_offset = 0;
636
637 /* Loop through all symbols and print them.
638
639 We start the index at -1 because there is a dummy symbol on
640 the front of Sun's stabs-in-elf sections. */
641
642 for (i = -1; stabs < stabs_end; stabs++, i++)
643 {
644 SWAP_SYMBOL (stabs, abfd);
645 printf ("\n%-6d %-6s %-6d %-6d %08x %-6d", i,
646 stab_name [stabs->n_type],
647 stabs->n_other, stabs->n_desc, stabs->n_value,
648 stabs->n_strx);
649
650 /* Symbols with type == 0 (N_UNDF) specify the length of the
651 string table associated with this file. We use that info
652 to know how to relocate the *next* file's string table indices. */
653
654 if (stabs->n_type == N_UNDF)
655 {
656 file_string_table_offset = next_file_string_table_offset;
657 next_file_string_table_offset += stabs->n_value;
658 }
659
660 /* Now, using the possibly updated string table offset, print the
661 string (if any) associated with this symbol. */
662
663 if ((stabs->n_strx + file_string_table_offset) < stabstr_hdr->sh_size)
664 printf (" %s", &strtab[stabs->n_strx + file_string_table_offset]);
665 else
666 printf (" *");
667 }
668 printf ("\n\n");
669 }
670 #endif /* ELF_STAB_DISPLAY */
671
672 display_bfd (abfd)
673 bfd *abfd;
674 {
675
676 if (!bfd_check_format (abfd, bfd_object))
677 {
678 fprintf (stderr, "%s:%s: %s\n", program_name, abfd->filename,
679 bfd_errmsg (bfd_error));
680 return;
681 }
682 printf ("\n%s: file format %s\n", abfd->filename, abfd->xvec->name);
683 if (dump_ar_hdrs)
684 print_arelt_descr (stdout, abfd, true);
685
686 if (dump_file_header)
687 {
688 char *comma = "";
689
690 printf ("architecture: %s, ",
691 bfd_printable_arch_mach (bfd_get_arch (abfd),
692 bfd_get_mach (abfd)));
693 printf ("flags 0x%08x:\n", abfd->flags);
694
695 #define PF(x, y) if (abfd->flags & x) {printf("%s%s", comma, y); comma=", ";}
696 PF (HAS_RELOC, "HAS_RELOC");
697 PF (EXEC_P, "EXEC_P");
698 PF (HAS_LINENO, "HAS_LINENO");
699 PF (HAS_DEBUG, "HAS_DEBUG");
700 PF (HAS_SYMS, "HAS_SYMS");
701 PF (HAS_LOCALS, "HAS_LOCALS");
702 PF (DYNAMIC, "DYNAMIC");
703 PF (WP_TEXT, "WP_TEXT");
704 PF (D_PAGED, "D_PAGED");
705 PF (BFD_IS_RELAXABLE, "BFD_IS_RELAXABLE");
706 printf ("\nstart address 0x");
707 printf_vma (abfd->start_address);
708 }
709 printf ("\n");
710
711 if (dump_section_headers)
712 dump_headers (abfd);
713 if (dump_symtab || dump_reloc_info || disassemble)
714 {
715 syms = slurp_symtab (abfd);
716 }
717 if (dump_symtab)
718 dump_symbols (abfd);
719 #ifdef ELF_STAB_DISPLAY
720 if (dump_stab_section_info)
721 dump_elf_stabs (abfd);
722 #endif
723 if (dump_reloc_info)
724 dump_relocs (abfd);
725 if (dump_section_contents)
726 dump_data (abfd);
727 /* Note that disassemble_data re-orders the syms table, but that is
728 safe - as long as it is done last! */
729 if (disassemble)
730 disassemble_data (abfd);
731 }
732
733 static void
734 display_file (filename, target)
735 char *filename;
736 char *target;
737 {
738 bfd *file, *arfile = (bfd *) NULL;
739
740 file = bfd_openr (filename, target);
741 if (file == NULL)
742 {
743 fprintf (stderr, "%s: ", program_name);
744 bfd_perror (filename);
745 return;
746 }
747
748 if (bfd_check_format (file, bfd_archive) == true)
749 {
750 printf ("In archive %s:\n", bfd_get_filename (file));
751 for (;;)
752 {
753 bfd_error = no_error;
754
755 arfile = bfd_openr_next_archived_file (file, arfile);
756 if (arfile == NULL)
757 {
758 if (bfd_error != no_more_archived_files)
759 {
760 fprintf (stderr, "%s: ", program_name);
761 bfd_perror (bfd_get_filename (file));
762 }
763 return;
764 }
765
766 display_bfd (arfile);
767 /* Don't close the archive elements; we need them for next_archive */
768 }
769 }
770 else
771 display_bfd (file);
772
773 bfd_close (file);
774 }
775 \f
776 /* Actually display the various requested regions */
777
778 static void
779 dump_data (abfd)
780 bfd *abfd;
781 {
782 asection *section;
783 bfd_byte *data = 0;
784 bfd_size_type datasize = 0;
785 bfd_size_type i;
786
787 for (section = abfd->sections; section != NULL; section =
788 section->next)
789 {
790 int onaline = 16;
791
792 if (only == (char *) NULL ||
793 strcmp (only, section->name) == 0)
794 {
795 if (section->flags & SEC_HAS_CONTENTS)
796 {
797 printf ("Contents of section %s:\n", section->name);
798
799 if (bfd_get_section_size_before_reloc (section) == 0)
800 continue;
801 data = (bfd_byte *) malloc (bfd_get_section_size_before_reloc (section));
802 if (data == (bfd_byte *) NULL)
803 {
804 fprintf (stderr, "%s: memory exhausted.\n", program_name);
805 exit (1);
806 }
807 datasize = bfd_get_section_size_before_reloc (section);
808
809
810 bfd_get_section_contents (abfd, section, (PTR) data, 0, bfd_get_section_size_before_reloc (section));
811
812 for (i = 0; i < bfd_get_section_size_before_reloc (section); i += onaline)
813 {
814 bfd_size_type j;
815
816 printf (" %04lx ", (unsigned long int) (i + section->vma));
817 for (j = i; j < i + onaline; j++)
818 {
819 if (j < bfd_get_section_size_before_reloc (section))
820 printf ("%02x", (unsigned) (data[j]));
821 else
822 printf (" ");
823 if ((j & 3) == 3)
824 printf (" ");
825 }
826
827 printf (" ");
828 for (j = i; j < i + onaline; j++)
829 {
830 if (j >= bfd_get_section_size_before_reloc (section))
831 printf (" ");
832 else
833 printf ("%c", isprint (data[j]) ? data[j] : '.');
834 }
835 putchar ('\n');
836 }
837 free (data);
838 }
839 }
840 }
841 }
842
843 /* Should perhaps share code and display with nm? */
844 static void
845 dump_symbols (abfd)
846 bfd *abfd;
847 {
848
849 unsigned int count;
850 asymbol **current = syms;
851
852 printf ("SYMBOL TABLE:\n");
853
854 for (count = 0; count < symcount; count++)
855 {
856
857 if (*current)
858 {
859 bfd *cur_bfd = bfd_asymbol_bfd(*current);
860 if (cur_bfd)
861 {
862 bfd_print_symbol (cur_bfd,
863 stdout,
864 *current, bfd_print_symbol_all);
865 printf ("\n");
866 }
867
868 }
869 current++;
870 }
871 printf ("\n");
872 printf ("\n");
873 }
874
875 static void
876 dump_relocs (abfd)
877 bfd *abfd;
878 {
879 arelent **relpp;
880 unsigned int relcount;
881 asection *a;
882
883 for (a = abfd->sections; a != (asection *) NULL; a = a->next)
884 {
885 if (a == &bfd_abs_section)
886 continue;
887 if (a == &bfd_und_section)
888 continue;
889 if (bfd_is_com_section (a))
890 continue;
891
892 printf ("RELOCATION RECORDS FOR [%s]:", a->name);
893
894 if (bfd_get_reloc_upper_bound (abfd, a) == 0)
895 {
896 printf (" (none)\n\n");
897 }
898 else
899 {
900 arelent **p;
901
902 relpp = (arelent **) xmalloc (bfd_get_reloc_upper_bound (abfd, a));
903 /* Note that this must be done *before* we sort the syms table. */
904 relcount = bfd_canonicalize_reloc (abfd, a, relpp, syms);
905 if (relcount == 0)
906 {
907 printf (" (none)\n\n");
908 }
909 else
910 {
911 printf ("\n");
912 printf ("OFFSET TYPE VALUE \n");
913
914 for (p = relpp; relcount && *p != (arelent *) NULL; p++,
915 relcount--)
916 {
917 arelent *q = *p;
918 CONST char *sym_name;
919
920 /* CONST char *section_name = q->section == (asection *)NULL ? "*abs" :*/
921 /* q->section->name;*/
922 CONST char *section_name = (*(q->sym_ptr_ptr))->section->name;
923
924 if (q->sym_ptr_ptr && *q->sym_ptr_ptr)
925 {
926 sym_name = (*(q->sym_ptr_ptr))->name;
927 }
928 else
929 {
930 sym_name = 0;
931 }
932 if (sym_name)
933 {
934 printf_vma (q->address);
935 printf (" %-8s %s",
936 q->howto->name,
937 sym_name);
938 }
939 else
940 {
941 printf_vma (q->address);
942 printf (" %-8s [%s]",
943 q->howto->name,
944 section_name);
945 }
946 if (q->addend)
947 {
948 printf ("+0x");
949 printf_vma (q->addend);
950 }
951 printf ("\n");
952 }
953 printf ("\n\n");
954 free (relpp);
955 }
956 }
957
958 }
959 }
960
961 #ifdef unix
962 #define _DUMMY_NAME_ "/dev/null"
963 #else
964 #define _DUMMY_NAME_ "##dummy"
965 #endif
966 static void
967 DEFUN (display_info_table, (first, last),
968 int first AND int last)
969 {
970 unsigned int i, j;
971 extern bfd_target *target_vector[];
972
973 printf ("\n%12s", " ");
974 for (i = first; i++ < last && target_vector[i];)
975 printf ("%s ", target_vector[i]->name);
976 printf ("\n");
977
978 for (j = (int) bfd_arch_obscure + 1; (int) j < (int) bfd_arch_last; j++)
979 if (strcmp (bfd_printable_arch_mach (j, 0), "UNKNOWN!") != 0)
980 {
981 printf ("%11s ", bfd_printable_arch_mach (j, 0));
982 for (i = first; i++ < last && target_vector[i];)
983 {
984 bfd_target *p = target_vector[i];
985 bfd *abfd = bfd_openw (_DUMMY_NAME_, p->name);
986 int l = strlen (p->name);
987 int ok;
988 bfd_set_format (abfd, bfd_object);
989 ok = bfd_set_arch_mach (abfd, j, 0);
990
991 if (ok)
992 printf ("%s ", p->name);
993 else
994 {
995 while (l--)
996 printf ("%c", ok ? '*' : '-');
997 printf (" ");
998 }
999 }
1000 printf ("\n");
1001 }
1002 }
1003
1004 static void
1005 DEFUN_VOID (display_info)
1006 {
1007 char *colum;
1008 unsigned int i, j, columns;
1009 extern bfd_target *target_vector[];
1010 extern char *getenv ();
1011
1012 printf ("BFD header file version %s\n", BFD_VERSION);
1013 for (i = 0; target_vector[i]; i++)
1014 {
1015 bfd_target *p = target_vector[i];
1016 bfd *abfd = bfd_openw (_DUMMY_NAME_, p->name);
1017 bfd_set_format (abfd, bfd_object);
1018 printf ("%s\n (header %s, data %s)\n", p->name,
1019 p->header_byteorder_big_p ? "big endian" : "little endian",
1020 p->byteorder_big_p ? "big endian" : "little endian");
1021 for (j = (int) bfd_arch_obscure + 1; j < (int) bfd_arch_last; j++)
1022 if (bfd_set_arch_mach (abfd, (enum bfd_architecture) j, 0))
1023 printf (" %s\n",
1024 bfd_printable_arch_mach ((enum bfd_architecture) j, 0));
1025 }
1026 columns = 0;
1027 if (colum = getenv ("COLUMNS"))
1028 columns = atoi (colum);
1029 if (!columns)
1030 columns = 80;
1031 for (i = 0; target_vector[i];)
1032 {
1033 int old;
1034 old = i;
1035 for (j = 12; target_vector[i] && j < columns; i++)
1036 j += strlen (target_vector[i]->name) + 1;
1037 i--;
1038 if (old == i)
1039 break;
1040 display_info_table (old, i);
1041 }
1042 }
1043
1044 /** main and like trivia */
1045 int
1046 main (argc, argv)
1047 int argc;
1048 char **argv;
1049 {
1050 int c;
1051 extern int optind;
1052 extern char *optarg;
1053 char *target = default_target;
1054 boolean seenflag = false;
1055
1056 bfd_init ();
1057 program_name = *argv;
1058
1059 while ((c = getopt_long (argc, argv, "ib:m:Vdlfahrtxsj:", long_options,
1060 (int *) 0))
1061 != EOF)
1062 {
1063 seenflag = true;
1064 switch (c)
1065 {
1066 case 0:
1067 break; /* we've been given a long option */
1068 case 'm':
1069 machine = optarg;
1070 break;
1071 case 'j':
1072 only = optarg;
1073 break;
1074 case 'l':
1075 with_line_numbers = 1;
1076 break;
1077 case 'b':
1078 target = optarg;
1079 break;
1080 case 'f':
1081 dump_file_header = true;
1082 break;
1083 case 'i':
1084 info = true;
1085 break;
1086 case 'x':
1087 dump_symtab = 1;
1088 dump_reloc_info = 1;
1089 dump_file_header = true;
1090 dump_ar_hdrs = 1;
1091 dump_section_headers = 1;
1092 break;
1093 case 't':
1094 dump_symtab = 1;
1095 break;
1096 case 'd':
1097 disassemble = true;
1098 break;
1099 case 's':
1100 dump_section_contents = 1;
1101 break;
1102 case 'r':
1103 dump_reloc_info = 1;
1104 break;
1105 case 'a':
1106 dump_ar_hdrs = 1;
1107 break;
1108 case 'h':
1109 dump_section_headers = 1;
1110 break;
1111 case 'H':
1112 usage (stdout, 0);
1113 case 'V':
1114 show_version = 1;
1115 break;
1116 default:
1117 usage (stderr, 1);
1118 }
1119 }
1120
1121 if (show_version)
1122 {
1123 printf ("GNU %s version %s\n", program_name, program_version);
1124 exit (0);
1125 }
1126
1127 if (seenflag == false)
1128 usage (stderr, 1);
1129
1130 if (info)
1131 {
1132 display_info ();
1133 }
1134 else
1135 {
1136 if (optind == argc)
1137 display_file ("a.out", target);
1138 else
1139 for (; optind < argc;)
1140 display_file (argv[optind++], target);
1141 }
1142 return 0;
1143 }