* external.h (GET_LINENO_LNNO): Use H_GET_32/16.
[deliverable/binutils-gdb.git] / binutils / nm.c
CommitLineData
252b5132 1/* nm.c -- Describe symbol table of a rel file.
8c2bc687
NC
2 Copyright 1991, 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000,
3 2001
252b5132
RH
4 Free Software Foundation, Inc.
5
6 This file is part of GNU Binutils.
7
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2 of the License, or
11 (at your option) any later version.
12
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
17
18 You should have received a copy of the GNU General Public License
19 along with this program; if not, write to the Free Software
20 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
21 02111-1307, USA. */
22
23#include "bfd.h"
24#include "progress.h"
25#include "bucomm.h"
26#include "getopt.h"
27#include "aout/stab_gnu.h"
28#include "aout/ranlib.h"
29#include "demangle.h"
30#include "libiberty.h"
31
32/* When sorting by size, we use this structure to hold the size and a
33 pointer to the minisymbol. */
34
35struct size_sym
36{
37 const PTR minisym;
38 bfd_vma size;
39};
40
41/* When fetching relocs, we use this structure to pass information to
42 get_relocs. */
43
44struct get_relocs_info
45{
46 asection **secs;
47 arelent ***relocs;
48 long *relcount;
49 asymbol **syms;
50};
51
52static void
53usage PARAMS ((FILE *, int));
54
55static void
56set_print_radix PARAMS ((char *));
57
58static void
59set_output_format PARAMS ((char *));
60
61static void
62display_archive PARAMS ((bfd *));
63
64static boolean
65display_file PARAMS ((char *filename));
66
67static void
68display_rel_file PARAMS ((bfd * file, bfd * archive));
69
70static long
71filter_symbols PARAMS ((bfd *, boolean, PTR, long, unsigned int));
72
73static long
74sort_symbols_by_size PARAMS ((bfd *, boolean, PTR, long, unsigned int,
75 struct size_sym **));
76
77static void
78print_symbols PARAMS ((bfd *, boolean, PTR, long, unsigned int, bfd *));
79
80static void
81print_size_symbols PARAMS ((bfd *, boolean, struct size_sym *, long, bfd *));
82
83static void
84print_symname PARAMS ((const char *, const char *, bfd *));
85
86static void
87print_symbol PARAMS ((bfd *, asymbol *, bfd *));
88
89static void
90print_symdef_entry PARAMS ((bfd * abfd));
91
92/* The sorting functions. */
93
94static int
95numeric_forward PARAMS ((const PTR, const PTR));
96
97static int
98numeric_reverse PARAMS ((const PTR, const PTR));
99
100static int
101non_numeric_forward PARAMS ((const PTR, const PTR));
102
103static int
104non_numeric_reverse PARAMS ((const PTR, const PTR));
105
106static int
107size_forward1 PARAMS ((const PTR, const PTR));
108
109static int
110size_forward2 PARAMS ((const PTR, const PTR));
111
112/* The output formatting functions. */
113
114static void
115print_object_filename_bsd PARAMS ((char *filename));
116
117static void
118print_object_filename_sysv PARAMS ((char *filename));
119
120static void
121print_object_filename_posix PARAMS ((char *filename));
122
123
124static void
125print_archive_filename_bsd PARAMS ((char *filename));
126
127static void
128print_archive_filename_sysv PARAMS ((char *filename));
129
130static void
131print_archive_filename_posix PARAMS ((char *filename));
132
133
134static void
135print_archive_member_bsd PARAMS ((char *archive, CONST char *filename));
136
137static void
138print_archive_member_sysv PARAMS ((char *archive, CONST char *filename));
139
140static void
141print_archive_member_posix PARAMS ((char *archive, CONST char *filename));
142
143
144static void
145print_symbol_filename_bsd PARAMS ((bfd * archive_bfd, bfd * abfd));
146
147static void
148print_symbol_filename_sysv PARAMS ((bfd * archive_bfd, bfd * abfd));
149
150static void
151print_symbol_filename_posix PARAMS ((bfd * archive_bfd, bfd * abfd));
152
153
154static void
d8180c76 155print_value PARAMS ((bfd *, bfd_vma));
252b5132
RH
156
157static void
158print_symbol_info_bsd PARAMS ((symbol_info * info, bfd * abfd));
159
160static void
161print_symbol_info_sysv PARAMS ((symbol_info * info, bfd * abfd));
162
163static void
164print_symbol_info_posix PARAMS ((symbol_info * info, bfd * abfd));
165
166static void
167get_relocs PARAMS ((bfd *, asection *, PTR));
168
169/* Support for different output formats. */
170struct output_fns
171 {
172 /* Print the name of an object file given on the command line. */
173 void (*print_object_filename) PARAMS ((char *filename));
174
175 /* Print the name of an archive file given on the command line. */
176 void (*print_archive_filename) PARAMS ((char *filename));
177
178 /* Print the name of an archive member file. */
179 void (*print_archive_member) PARAMS ((char *archive, CONST char *filename));
180
181 /* Print the name of the file (and archive, if there is one)
182 containing a symbol. */
183 void (*print_symbol_filename) PARAMS ((bfd * archive_bfd, bfd * abfd));
184
185 /* Print a line of information about a symbol. */
186 void (*print_symbol_info) PARAMS ((symbol_info * info, bfd * abfd));
187 };
188static struct output_fns formats[] =
189{
190 {print_object_filename_bsd,
191 print_archive_filename_bsd,
192 print_archive_member_bsd,
193 print_symbol_filename_bsd,
194 print_symbol_info_bsd},
195 {print_object_filename_sysv,
196 print_archive_filename_sysv,
197 print_archive_member_sysv,
198 print_symbol_filename_sysv,
199 print_symbol_info_sysv},
200 {print_object_filename_posix,
201 print_archive_filename_posix,
202 print_archive_member_posix,
203 print_symbol_filename_posix,
204 print_symbol_info_posix}
205};
206
207/* Indices in `formats'. */
208#define FORMAT_BSD 0
209#define FORMAT_SYSV 1
210#define FORMAT_POSIX 2
211#define FORMAT_DEFAULT FORMAT_BSD
212
213/* The output format to use. */
214static struct output_fns *format = &formats[FORMAT_DEFAULT];
215
216
217/* Command options. */
218
219static int do_demangle = 0; /* Pretty print C++ symbol names. */
220static int external_only = 0; /* print external symbols only */
221static int defined_only = 0; /* Print defined symbols only */
222static int no_sort = 0; /* don't sort; print syms in order found */
223static int print_debug_syms = 0; /* print debugger-only symbols too */
224static int print_armap = 0; /* describe __.SYMDEF data in archive files. */
225static int reverse_sort = 0; /* sort in downward(alpha or numeric) order */
226static int sort_numerically = 0; /* sort in numeric rather than alpha order */
227static int sort_by_size = 0; /* sort by size of symbol */
228static int undefined_only = 0; /* print undefined symbols only */
229static int dynamic = 0; /* print dynamic symbols. */
230static int show_version = 0; /* show the version number */
231static int show_stats = 0; /* show statistics */
232static int line_numbers = 0; /* print line numbers for symbols */
233
234/* When to print the names of files. Not mutually exclusive in SYSV format. */
235static int filename_per_file = 0; /* Once per file, on its own line. */
236static int filename_per_symbol = 0; /* Once per symbol, at start of line. */
237
238/* Print formats for printing a symbol value. */
239#ifndef BFD64
240static char value_format[] = "%08lx";
241#else
242#if BFD_HOST_64BIT_LONG
243static char value_format[] = "%016lx";
244#else
245/* We don't use value_format for this case. */
246#endif
247#endif
62a5a82d
L
248#ifdef BFD64
249static int print_width = 16;
250#else
251static int print_width = 8;
252#endif
252b5132
RH
253static int print_radix = 16;
254/* Print formats for printing stab info. */
255static char other_format[] = "%02x";
256static char desc_format[] = "%04x";
257
258static char *target = NULL;
259
260/* Used to cache the line numbers for a BFD. */
261static bfd *lineno_cache_bfd;
262static bfd *lineno_cache_rel_bfd;
263
c20f4f8c
AM
264#define OPTION_TARGET 200
265
252b5132
RH
266static struct option long_options[] =
267{
268 {"debug-syms", no_argument, &print_debug_syms, 1},
28c309a2 269 {"demangle", optional_argument, 0, 'C'},
252b5132
RH
270 {"dynamic", no_argument, &dynamic, 1},
271 {"extern-only", no_argument, &external_only, 1},
272 {"format", required_argument, 0, 'f'},
273 {"help", no_argument, 0, 'h'},
274 {"line-numbers", no_argument, 0, 'l'},
275 {"no-cplus", no_argument, &do_demangle, 0}, /* Linux compatibility. */
276 {"no-demangle", no_argument, &do_demangle, 0},
277 {"no-sort", no_argument, &no_sort, 1},
278 {"numeric-sort", no_argument, &sort_numerically, 1},
279 {"portability", no_argument, 0, 'P'},
280 {"print-armap", no_argument, &print_armap, 1},
281 {"print-file-name", no_argument, 0, 'o'},
282 {"radix", required_argument, 0, 't'},
283 {"reverse-sort", no_argument, &reverse_sort, 1},
284 {"size-sort", no_argument, &sort_by_size, 1},
285 {"stats", no_argument, &show_stats, 1},
c20f4f8c 286 {"target", required_argument, 0, OPTION_TARGET},
252b5132
RH
287 {"defined-only", no_argument, &defined_only, 1},
288 {"undefined-only", no_argument, &undefined_only, 1},
289 {"version", no_argument, &show_version, 1},
290 {0, no_argument, 0, 0}
291};
292\f
293/* Some error-reporting functions */
294
295static void
296usage (stream, status)
297 FILE *stream;
298 int status;
299{
b56f55ce
NC
300 fprintf (stream, _("Usage: %s [OPTION]... [FILE]...\n"), program_name);
301 fprintf (stream, _("List symbols from FILEs (a.out by default).\n"));
302 fprintf (stream, _("\n\
303 -a, --debug-syms Display debugger-only symbols\n\
304 -A, --print-file-name Print name of the input file before every symbol\n\
305 -B Same as --format=bsd\n\
28c309a2
NC
306 -C, --demangle[=STYLE] Decode low-level symbol names into user-level names\n\
307 The STYLE, if specified, can be `auto' (the default),\n\
308 `gnu', 'lucid', 'arm', 'hp', 'edg' or 'gnu-new-abi'\n\
b56f55ce
NC
309 --no-demangle Do not demangle low-level symbol names\n\
310 -D, --dynamic Display dynamic symbols instead of normal symbols\n\
311 --defined-only Display only defined symbols\n\
312 -e (ignored)\n\
313 -f, --format=FORMAT Use the output format FORMAT. FORMAT can be `bsd',\n\
314 `sysv' or `posix'. The default is `bsd'\n\
315 -g, --extern-only Display only external symbols\n\
316 -h, --help Display this information\n\
317 -l, --line-numbers Use debugging information to find a filename and\n\
318 line number for each symbol\n\
319 -n, --numeric-sort Sort symbols numerically by address\n\
320 -o Same as -A\n\
321 -p, --no-sort Do not sort the symbols\n\
322 -P, --portability Same as --format=posix\n\
323 -r, --reverse-sort Reverse the sense of the sort\n\
324 -s, --print-armap Include index for symbols from archive members\n\
325 --size-sort Sort symbols by size\n\
326 -t, --radix=RADIX Use RADIX for printing symbol values\n\
327 --target=BFDNAME Specify the target object format as BFDNAME\n\
328 -u, --undefined-only Display only undefined symbols\n\
329 -V, --version Display this program's version number\n\
6e800839 330 -X 32_64 (ignored)\n\
b56f55ce 331\n"));
252b5132
RH
332 list_supported_targets (program_name, stream);
333 if (status == 0)
b56f55ce 334 fprintf (stream, _("Report bugs to %s.\n"), REPORT_BUGS_TO);
252b5132
RH
335 exit (status);
336}
337
338/* Set the radix for the symbol value and size according to RADIX. */
339
340static void
341set_print_radix (radix)
342 char *radix;
343{
344 switch (*radix)
345 {
346 case 'x':
347 break;
348 case 'd':
349 case 'o':
350 if (*radix == 'd')
351 print_radix = 10;
352 else
353 print_radix = 8;
354#ifndef BFD64
355 value_format[4] = *radix;
356#else
357#if BFD_HOST_64BIT_LONG
358 value_format[5] = *radix;
359#else
360 /* This case requires special handling for octal and decimal
361 printing. */
362#endif
363#endif
364 other_format[3] = desc_format[3] = *radix;
365 break;
366 default:
37cc8ec1 367 fatal (_("%s: invalid radix"), radix);
252b5132
RH
368 }
369}
370
371static void
372set_output_format (f)
373 char *f;
374{
375 int i;
376
377 switch (*f)
378 {
379 case 'b':
380 case 'B':
381 i = FORMAT_BSD;
382 break;
383 case 'p':
384 case 'P':
385 i = FORMAT_POSIX;
386 break;
387 case 's':
388 case 'S':
389 i = FORMAT_SYSV;
390 break;
391 default:
37cc8ec1 392 fatal (_("%s: invalid output format"), f);
252b5132
RH
393 }
394 format = &formats[i];
395}
396\f
397int
398main (argc, argv)
399 int argc;
400 char **argv;
401{
402 int c;
403 int retval;
404
405#if defined (HAVE_SETLOCALE) && defined (HAVE_LC_MESSAGES)
406 setlocale (LC_MESSAGES, "");
407#endif
408 bindtextdomain (PACKAGE, LOCALEDIR);
409 textdomain (PACKAGE);
410
411 program_name = *argv;
412 xmalloc_set_program_name (program_name);
413
414 START_PROGRESS (program_name, 0);
415
416 bfd_init ();
417 set_default_bfd_target ();
418
6e800839 419 while ((c = getopt_long (argc, argv, "aABCDef:glnopPrst:uvVX:",
28c309a2 420 long_options, (int *) 0)) != EOF)
252b5132
RH
421 {
422 switch (c)
423 {
424 case 'a':
425 print_debug_syms = 1;
426 break;
427 case 'A':
428 case 'o':
429 filename_per_symbol = 1;
430 break;
431 case 'B': /* For MIPS compatibility. */
432 set_output_format ("bsd");
433 break;
434 case 'C':
435 do_demangle = 1;
28c309a2
NC
436 if (optarg != NULL)
437 {
438 enum demangling_styles style;
439
440 style = cplus_demangle_name_to_style (optarg);
441 if (style == unknown_demangling)
442 fatal (_("unknown demangling style `%s'"),
443 optarg);
444
445 cplus_demangle_set_style (style);
446 }
252b5132
RH
447 break;
448 case 'D':
449 dynamic = 1;
450 break;
451 case 'e':
452 /* Ignored for HP/UX compatibility. */
453 break;
454 case 'f':
455 set_output_format (optarg);
456 break;
457 case 'g':
458 external_only = 1;
459 break;
460 case 'h':
461 usage (stdout, 0);
462 case 'l':
463 line_numbers = 1;
464 break;
465 case 'n':
466 case 'v':
467 sort_numerically = 1;
468 break;
469 case 'p':
470 no_sort = 1;
471 break;
472 case 'P':
473 set_output_format ("posix");
474 break;
475 case 'r':
476 reverse_sort = 1;
477 break;
478 case 's':
479 print_armap = 1;
480 break;
481 case 't':
482 set_print_radix (optarg);
483 break;
484 case 'u':
485 undefined_only = 1;
486 break;
487 case 'V':
488 show_version = 1;
489 break;
6e800839
GK
490 case 'X':
491 /* Ignored for (partial) AIX compatibility. On AIX, the
492 argument has values 32, 64, or 32_64, and specfies that
493 only 32-bit, only 64-bit, or both kinds of objects should
494 be examined. The default is 32. So plain AIX nm on a
495 library archive with both kinds of objects will ignore
496 the 64-bit ones. For GNU nm, the default is and always
497 has been -X 32_64, and other options are not supported. */
498 if (strcmp (optarg, "32_64") != 0)
499 fatal (_("Only -X 32_64 is supported"));
500 break;
252b5132 501
c20f4f8c 502 case OPTION_TARGET: /* --target */
252b5132
RH
503 target = optarg;
504 break;
505
506 case 0: /* A long option that just sets a flag. */
507 break;
508
509 default:
510 usage (stderr, 1);
511 }
512 }
513
514 if (show_version)
515 print_version ("nm");
516
517 /* OK, all options now parsed. If no filename specified, do a.out. */
518 if (optind == argc)
519 return !display_file ("a.out");
520
521 retval = 0;
522
523 if (argc - optind > 1)
524 filename_per_file = 1;
525
526 /* We were given several filenames to do. */
527 while (optind < argc)
528 {
529 PROGRESS (1);
530 if (!display_file (argv[optind++]))
531 retval++;
532 }
533
534 END_PROGRESS (program_name);
535
536#ifdef HAVE_SBRK
537 if (show_stats)
538 {
539 char *lim = (char *) sbrk (0);
540
37cc8ec1 541 non_fatal (_("data size %ld"), (long) (lim - (char *) &environ));
252b5132
RH
542 }
543#endif
544
545 exit (retval);
546 return retval;
547}
548\f
549static void
550display_archive (file)
551 bfd *file;
552{
553 bfd *arfile = NULL;
554 bfd *last_arfile = NULL;
555 char **matching;
556
557 (*format->print_archive_filename) (bfd_get_filename (file));
558
559 if (print_armap)
560 print_symdef_entry (file);
561
562 for (;;)
563 {
564 PROGRESS (1);
565
566 arfile = bfd_openr_next_archived_file (file, arfile);
567
568 if (arfile == NULL)
569 {
570 if (bfd_get_error () != bfd_error_no_more_archived_files)
571 bfd_fatal (bfd_get_filename (file));
572 break;
573 }
574
575 if (bfd_check_format_matches (arfile, bfd_object, &matching))
576 {
577 (*format->print_archive_member) (bfd_get_filename (file),
578 bfd_get_filename (arfile));
579 display_rel_file (arfile, file);
580 }
581 else
582 {
583 bfd_nonfatal (bfd_get_filename (arfile));
584 if (bfd_get_error () == bfd_error_file_ambiguously_recognized)
585 {
586 list_matching_formats (matching);
587 free (matching);
588 }
589 }
590
591 if (last_arfile != NULL)
592 {
593 bfd_close (last_arfile);
594 lineno_cache_bfd = NULL;
595 lineno_cache_rel_bfd = NULL;
596 }
597 last_arfile = arfile;
598 }
599
600 if (last_arfile != NULL)
601 {
602 bfd_close (last_arfile);
603 lineno_cache_bfd = NULL;
604 lineno_cache_rel_bfd = NULL;
605 }
606}
607
608static boolean
609display_file (filename)
610 char *filename;
611{
612 boolean retval = true;
613 bfd *file;
614 char **matching;
615
616 file = bfd_openr (filename, target);
617 if (file == NULL)
618 {
619 bfd_nonfatal (filename);
620 return false;
621 }
622
623 if (bfd_check_format (file, bfd_archive))
624 {
625 display_archive (file);
626 }
627 else if (bfd_check_format_matches (file, bfd_object, &matching))
628 {
629 (*format->print_object_filename) (filename);
630 display_rel_file (file, NULL);
631 }
632 else
633 {
634 bfd_nonfatal (filename);
635 if (bfd_get_error () == bfd_error_file_ambiguously_recognized)
636 {
637 list_matching_formats (matching);
638 free (matching);
639 }
640 retval = false;
641 }
642
643 if (bfd_close (file) == false)
644 bfd_fatal (filename);
645
646 lineno_cache_bfd = NULL;
647 lineno_cache_rel_bfd = NULL;
648
649 return retval;
650}
651\f
652/* These globals are used to pass information into the sorting
653 routines. */
654static bfd *sort_bfd;
655static boolean sort_dynamic;
656static asymbol *sort_x;
657static asymbol *sort_y;
658
659/* Symbol-sorting predicates */
660#define valueof(x) ((x)->section->vma + (x)->value)
661
662/* Numeric sorts. Undefined symbols are always considered "less than"
663 defined symbols with zero values. Common symbols are not treated
664 specially -- i.e., their sizes are used as their "values". */
665
666static int
667numeric_forward (P_x, P_y)
668 const PTR P_x;
669 const PTR P_y;
670{
671 asymbol *x, *y;
672 asection *xs, *ys;
673
674 x = bfd_minisymbol_to_symbol (sort_bfd, sort_dynamic, P_x, sort_x);
675 y = bfd_minisymbol_to_symbol (sort_bfd, sort_dynamic, P_y, sort_y);
676 if (x == NULL || y == NULL)
677 bfd_fatal (bfd_get_filename (sort_bfd));
678
679 xs = bfd_get_section (x);
680 ys = bfd_get_section (y);
681
682 if (bfd_is_und_section (xs))
683 {
684 if (! bfd_is_und_section (ys))
685 return -1;
686 }
687 else if (bfd_is_und_section (ys))
688 return 1;
689 else if (valueof (x) != valueof (y))
690 return valueof (x) < valueof (y) ? -1 : 1;
691
692 return non_numeric_forward (P_x, P_y);
693}
694
695static int
696numeric_reverse (x, y)
697 const PTR x;
698 const PTR y;
699{
700 return - numeric_forward (x, y);
701}
702
703static int
704non_numeric_forward (P_x, P_y)
705 const PTR P_x;
706 const PTR P_y;
707{
708 asymbol *x, *y;
709 const char *xn, *yn;
710
711 x = bfd_minisymbol_to_symbol (sort_bfd, sort_dynamic, P_x, sort_x);
712 y = bfd_minisymbol_to_symbol (sort_bfd, sort_dynamic, P_y, sort_y);
713 if (x == NULL || y == NULL)
714 bfd_fatal (bfd_get_filename (sort_bfd));
715
716 xn = bfd_asymbol_name (x);
717 yn = bfd_asymbol_name (y);
718
719 return ((xn == NULL) ? ((yn == NULL) ? 0 : -1) :
720 ((yn == NULL) ? 1 : strcmp (xn, yn)));
721}
722
723static int
724non_numeric_reverse (x, y)
725 const PTR x;
726 const PTR y;
727{
728 return - non_numeric_forward (x, y);
729}
730
731static int (*(sorters[2][2])) PARAMS ((const PTR, const PTR)) =
732{
733 { non_numeric_forward, non_numeric_reverse },
734 { numeric_forward, numeric_reverse }
735};
736
737/* This sort routine is used by sort_symbols_by_size. It is similar
738 to numeric_forward, but when symbols have the same value it sorts
739 by section VMA. This simplifies the sort_symbols_by_size code
740 which handles symbols at the end of sections. Also, this routine
741 tries to sort file names before other symbols with the same value.
742 That will make the file name have a zero size, which will make
743 sort_symbols_by_size choose the non file name symbol, leading to
744 more meaningful output. For similar reasons, this code sorts
745 gnu_compiled_* and gcc2_compiled before other symbols with the same
746 value. */
747
748static int
749size_forward1 (P_x, P_y)
750 const PTR P_x;
751 const PTR P_y;
752{
753 asymbol *x, *y;
754 asection *xs, *ys;
755 const char *xn, *yn;
756 size_t xnl, ynl;
757 int xf, yf;
758
759 x = bfd_minisymbol_to_symbol (sort_bfd, sort_dynamic, P_x, sort_x);
760 y = bfd_minisymbol_to_symbol (sort_bfd, sort_dynamic, P_y, sort_y);
761 if (x == NULL || y == NULL)
762 bfd_fatal (bfd_get_filename (sort_bfd));
763
764 xs = bfd_get_section (x);
765 ys = bfd_get_section (y);
766
767 if (bfd_is_und_section (xs))
768 abort ();
769 if (bfd_is_und_section (ys))
770 abort ();
771
772 if (valueof (x) != valueof (y))
773 return valueof (x) < valueof (y) ? -1 : 1;
774
775 if (xs->vma != ys->vma)
776 return xs->vma < ys->vma ? -1 : 1;
777
778 xn = bfd_asymbol_name (x);
779 yn = bfd_asymbol_name (y);
780 xnl = strlen (xn);
781 ynl = strlen (yn);
782
783 /* The symbols gnu_compiled and gcc2_compiled convey even less
784 information than the file name, so sort them out first. */
785
786 xf = (strstr (xn, "gnu_compiled") != NULL
787 || strstr (xn, "gcc2_compiled") != NULL);
788 yf = (strstr (yn, "gnu_compiled") != NULL
789 || strstr (yn, "gcc2_compiled") != NULL);
790
791 if (xf && ! yf)
792 return -1;
793 if (! xf && yf)
794 return 1;
795
796 /* We use a heuristic for the file name. It may not work on non
797 Unix systems, but it doesn't really matter; the only difference
798 is precisely which symbol names get printed. */
799
800#define file_symbol(s, sn, snl) \
801 (((s)->flags & BSF_FILE) != 0 \
802 || ((sn)[(snl) - 2] == '.' \
803 && ((sn)[(snl) - 1] == 'o' \
804 || (sn)[(snl) - 1] == 'a')))
805
806 xf = file_symbol (x, xn, xnl);
807 yf = file_symbol (y, yn, ynl);
808
809 if (xf && ! yf)
810 return -1;
811 if (! xf && yf)
812 return 1;
813
814 return non_numeric_forward (P_x, P_y);
815}
816
817/* This sort routine is used by sort_symbols_by_size. It is sorting
818 an array of size_sym structures into size order. */
819
820static int
821size_forward2 (P_x, P_y)
822 const PTR P_x;
823 const PTR P_y;
824{
825 const struct size_sym *x = (const struct size_sym *) P_x;
826 const struct size_sym *y = (const struct size_sym *) P_y;
827
828 if (x->size < y->size)
829 return reverse_sort ? 1 : -1;
830 else if (x->size > y->size)
831 return reverse_sort ? -1 : 1;
832 else
833 return sorters[0][reverse_sort] (x->minisym, y->minisym);
834}
835
836/* Sort the symbols by size. We guess the size by assuming that the
837 difference between the address of a symbol and the address of the
838 next higher symbol is the size. FIXME: ELF actually stores a size
839 with each symbol. We should use it. */
840
841static long
842sort_symbols_by_size (abfd, dynamic, minisyms, symcount, size, symsizesp)
843 bfd *abfd;
844 boolean dynamic;
845 PTR minisyms;
846 long symcount;
847 unsigned int size;
848 struct size_sym **symsizesp;
849{
850 struct size_sym *symsizes;
851 bfd_byte *from, *fromend;
852 asymbol *sym = NULL;
853 asymbol *store_sym, *store_next;
854
855 qsort (minisyms, symcount, size, size_forward1);
856
857 /* We are going to return a special set of symbols and sizes to
858 print. */
859 symsizes = (struct size_sym *) xmalloc (symcount * sizeof (struct size_sym));
860 *symsizesp = symsizes;
861
862 /* Note that filter_symbols has already removed all absolute and
863 undefined symbols. Here we remove all symbols whose size winds
864 up as zero. */
865
866 from = (bfd_byte *) minisyms;
867 fromend = from + symcount * size;
868
869 store_sym = sort_x;
870 store_next = sort_y;
871
872 if (from < fromend)
873 {
874 sym = bfd_minisymbol_to_symbol (abfd, dynamic, (const PTR) from,
875 store_sym);
876 if (sym == NULL)
877 bfd_fatal (bfd_get_filename (abfd));
878 }
879
880 for (; from < fromend; from += size)
881 {
882 asymbol *next;
883 asection *sec;
884 bfd_vma sz;
885 asymbol *temp;
886
887 if (from + size < fromend)
888 {
889 next = bfd_minisymbol_to_symbol (abfd,
890 dynamic,
891 (const PTR) (from + size),
892 store_next);
893 if (next == NULL)
894 bfd_fatal (bfd_get_filename (abfd));
895 }
896 else
897 next = NULL;
898
899 sec = bfd_get_section (sym);
900
901 if (bfd_is_com_section (sec))
902 sz = sym->value;
903 else
904 {
905 if (from + size < fromend
906 && sec == bfd_get_section (next))
907 sz = valueof (next) - valueof (sym);
908 else
909 sz = (bfd_get_section_vma (abfd, sec)
910 + bfd_section_size (abfd, sec)
911 - valueof (sym));
912 }
913
914 if (sz != 0)
915 {
916 symsizes->minisym = (const PTR) from;
917 symsizes->size = sz;
918 ++symsizes;
919 }
920
921 sym = next;
922
923 temp = store_sym;
924 store_sym = store_next;
925 store_next = temp;
926 }
927
928 symcount = symsizes - *symsizesp;
929
930 /* We must now sort again by size. */
931 qsort ((PTR) *symsizesp, symcount, sizeof (struct size_sym), size_forward2);
932
933 return symcount;
934}
935\f
936/* If ARCHIVE_BFD is non-NULL, it is the archive containing ABFD. */
937
938static void
939display_rel_file (abfd, archive_bfd)
940 bfd *abfd;
941 bfd *archive_bfd;
942{
943 long symcount;
944 PTR minisyms;
945 unsigned int size;
946 struct size_sym *symsizes;
62a5a82d 947 char buf[30];
252b5132
RH
948
949 if (! dynamic)
950 {
951 if (!(bfd_get_file_flags (abfd) & HAS_SYMS))
952 {
37cc8ec1 953 non_fatal (_("%s: no symbols"), bfd_get_filename (abfd));
252b5132
RH
954 return;
955 }
956 }
957
958 symcount = bfd_read_minisymbols (abfd, dynamic, &minisyms, &size);
959 if (symcount < 0)
960 bfd_fatal (bfd_get_filename (abfd));
961
962 if (symcount == 0)
963 {
37cc8ec1 964 non_fatal (_("%s: no symbols"), bfd_get_filename (abfd));
252b5132
RH
965 return;
966 }
967
62a5a82d
L
968 bfd_sprintf_vma (abfd, buf, (bfd_vma) -1);
969 print_width = strlen (buf);
970
252b5132
RH
971 /* Discard the symbols we don't want to print.
972 It's OK to do this in place; we'll free the storage anyway
973 (after printing). */
974
975 symcount = filter_symbols (abfd, dynamic, minisyms, symcount, size);
976
977 symsizes = NULL;
978 if (! no_sort)
979 {
980 sort_bfd = abfd;
981 sort_dynamic = dynamic;
982 sort_x = bfd_make_empty_symbol (abfd);
983 sort_y = bfd_make_empty_symbol (abfd);
984 if (sort_x == NULL || sort_y == NULL)
985 bfd_fatal (bfd_get_filename (abfd));
986
987 if (! sort_by_size)
988 qsort (minisyms, symcount, size,
989 sorters[sort_numerically][reverse_sort]);
990 else
991 symcount = sort_symbols_by_size (abfd, dynamic, minisyms, symcount,
992 size, &symsizes);
993 }
994
995 if (! sort_by_size)
996 print_symbols (abfd, dynamic, minisyms, symcount, size, archive_bfd);
997 else
998 print_size_symbols (abfd, dynamic, symsizes, symcount, archive_bfd);
999
1000 free (minisyms);
1001}
1002\f
1003/* Choose which symbol entries to print;
1004 compact them downward to get rid of the rest.
1005 Return the number of symbols to be printed. */
1006
1007static long
1008filter_symbols (abfd, dynamic, minisyms, symcount, size)
1009 bfd *abfd;
1010 boolean dynamic;
1011 PTR minisyms;
1012 long symcount;
1013 unsigned int size;
1014{
1015 bfd_byte *from, *fromend, *to;
1016 asymbol *store;
1017
1018 store = bfd_make_empty_symbol (abfd);
1019 if (store == NULL)
1020 bfd_fatal (bfd_get_filename (abfd));
1021
1022 from = (bfd_byte *) minisyms;
1023 fromend = from + symcount * size;
1024 to = (bfd_byte *) minisyms;
1025
1026 for (; from < fromend; from += size)
1027 {
1028 int keep = 0;
1029 asymbol *sym;
1030
1031 PROGRESS (1);
1032
1033 sym = bfd_minisymbol_to_symbol (abfd, dynamic, (const PTR) from, store);
1034 if (sym == NULL)
1035 bfd_fatal (bfd_get_filename (abfd));
1036
1037 if (undefined_only)
1038 keep = bfd_is_und_section (sym->section);
1039 else if (external_only)
1040 keep = ((sym->flags & BSF_GLOBAL) != 0
1041 || (sym->flags & BSF_WEAK) != 0
1042 || bfd_is_und_section (sym->section)
1043 || bfd_is_com_section (sym->section));
1044 else
1045 keep = 1;
1046
1047 if (keep
1048 && ! print_debug_syms
1049 && (sym->flags & BSF_DEBUGGING) != 0)
1050 keep = 0;
1051
1052 if (keep
1053 && sort_by_size
1054 && (bfd_is_abs_section (sym->section)
1055 || bfd_is_und_section (sym->section)))
1056 keep = 0;
1057
1058 if (keep
1059 && defined_only)
1060 {
1061 if (bfd_is_und_section (sym->section))
1062 keep = 0;
1063 }
1064
1065 if (keep)
1066 {
1067 memcpy (to, from, size);
1068 to += size;
1069 }
1070 }
1071
1072 return (to - (bfd_byte *) minisyms) / size;
1073}
1074\f
1075/* Print symbol name NAME, read from ABFD, with printf format FORMAT,
1076 demangling it if requested. */
1077
1078static void
1079print_symname (format, name, abfd)
1080 const char *format;
1081 const char *name;
1082 bfd *abfd;
1083{
1084 if (do_demangle && *name)
1085 {
1086 char *res;
1087
1088 /* In this mode, give a user-level view of the symbol name
1089 even if it's not mangled; strip off any leading
1090 underscore. */
1091 if (bfd_get_symbol_leading_char (abfd) == name[0])
1092 name++;
1093
1094 res = cplus_demangle (name, DMGL_ANSI | DMGL_PARAMS);
1095 if (res)
1096 {
1097 printf (format, res);
1098 free (res);
1099 return;
1100 }
1101 }
1102
1103 printf (format, name);
1104}
1105
1106/* Print the symbols. If ARCHIVE_BFD is non-NULL, it is the archive
1107 containing ABFD. */
1108
1109static void
1110print_symbols (abfd, dynamic, minisyms, symcount, size, archive_bfd)
1111 bfd *abfd;
1112 boolean dynamic;
1113 PTR minisyms;
1114 long symcount;
1115 unsigned int size;
1116 bfd *archive_bfd;
1117{
1118 asymbol *store;
1119 bfd_byte *from, *fromend;
1120
1121 store = bfd_make_empty_symbol (abfd);
1122 if (store == NULL)
1123 bfd_fatal (bfd_get_filename (abfd));
1124
1125 from = (bfd_byte *) minisyms;
1126 fromend = from + symcount * size;
1127 for (; from < fromend; from += size)
1128 {
1129 asymbol *sym;
1130
1131 sym = bfd_minisymbol_to_symbol (abfd, dynamic, from, store);
1132 if (sym == NULL)
1133 bfd_fatal (bfd_get_filename (abfd));
1134
1135 print_symbol (abfd, sym, archive_bfd);
1136 }
1137}
1138
1139/* Print the symbols when sorting by size. */
1140
1141static void
1142print_size_symbols (abfd, dynamic, symsizes, symcount, archive_bfd)
1143 bfd *abfd;
1144 boolean dynamic;
1145 struct size_sym *symsizes;
1146 long symcount;
1147 bfd *archive_bfd;
1148{
1149 asymbol *store;
1150 struct size_sym *from, *fromend;
1151
1152 store = bfd_make_empty_symbol (abfd);
1153 if (store == NULL)
1154 bfd_fatal (bfd_get_filename (abfd));
1155
1156 from = symsizes;
1157 fromend = from + symcount;
1158 for (; from < fromend; from++)
1159 {
1160 asymbol *sym;
1161
1162 sym = bfd_minisymbol_to_symbol (abfd, dynamic, from->minisym, store);
1163 if (sym == NULL)
1164 bfd_fatal (bfd_get_filename (abfd));
1165
1166 /* Set the symbol value so that we actually display the symbol
1167 size. */
1168 sym->value = from->size - bfd_section_vma (abfd, bfd_get_section (sym));
1169
1170 print_symbol (abfd, sym, archive_bfd);
1171 }
1172}
1173
1174/* Print a single symbol. */
1175
1176static void
1177print_symbol (abfd, sym, archive_bfd)
1178 bfd *abfd;
1179 asymbol *sym;
1180 bfd *archive_bfd;
1181{
1182 PROGRESS (1);
1183
1184 (*format->print_symbol_filename) (archive_bfd, abfd);
1185
1186 if (undefined_only)
1187 {
1188 if (bfd_is_und_section (bfd_get_section (sym)))
1189 print_symname ("%s", bfd_asymbol_name (sym), abfd);
1190 }
1191 else
1192 {
1193 symbol_info syminfo;
1194
1195 bfd_get_symbol_info (abfd, sym, &syminfo);
1196 (*format->print_symbol_info) (&syminfo, abfd);
1197 }
1198
1199 if (line_numbers)
1200 {
1201 static asymbol **syms;
1202 static long symcount;
1203 const char *filename, *functionname;
1204 unsigned int lineno;
1205
1206 /* We need to get the canonical symbols in order to call
1207 bfd_find_nearest_line. This is inefficient, but, then, you
1208 don't have to use --line-numbers. */
1209 if (abfd != lineno_cache_bfd && syms != NULL)
1210 {
1211 free (syms);
1212 syms = NULL;
1213 }
1214 if (syms == NULL)
1215 {
1216 long symsize;
1217
1218 symsize = bfd_get_symtab_upper_bound (abfd);
1219 if (symsize < 0)
1220 bfd_fatal (bfd_get_filename (abfd));
1221 syms = (asymbol **) xmalloc (symsize);
1222 symcount = bfd_canonicalize_symtab (abfd, syms);
1223 if (symcount < 0)
1224 bfd_fatal (bfd_get_filename (abfd));
1225 lineno_cache_bfd = abfd;
1226 }
1227
1228 if (bfd_is_und_section (bfd_get_section (sym)))
1229 {
1230 static asection **secs;
1231 static arelent ***relocs;
1232 static long *relcount;
1233 static unsigned int seccount;
1234 unsigned int i;
1235 const char *symname;
1236
1237 /* For an undefined symbol, we try to find a reloc for the
1238 symbol, and print the line number of the reloc. */
1239
1240 if (abfd != lineno_cache_rel_bfd && relocs != NULL)
1241 {
1242 for (i = 0; i < seccount; i++)
1243 if (relocs[i] != NULL)
1244 free (relocs[i]);
1245 free (secs);
1246 free (relocs);
1247 free (relcount);
1248 secs = NULL;
1249 relocs = NULL;
1250 relcount = NULL;
1251 }
1252
1253 if (relocs == NULL)
1254 {
1255 struct get_relocs_info info;
1256
1257 seccount = bfd_count_sections (abfd);
1258
1259 secs = (asection **) xmalloc (seccount * sizeof *secs);
1260 relocs = (arelent ***) xmalloc (seccount * sizeof *relocs);
1261 relcount = (long *) xmalloc (seccount * sizeof *relcount);
1262
1263 info.secs = secs;
1264 info.relocs = relocs;
1265 info.relcount = relcount;
1266 info.syms = syms;
1267 bfd_map_over_sections (abfd, get_relocs, (PTR) &info);
1268 lineno_cache_rel_bfd = abfd;
1269 }
1270
1271 symname = bfd_asymbol_name (sym);
1272 for (i = 0; i < seccount; i++)
1273 {
1274 long j;
1275
1276 for (j = 0; j < relcount[i]; j++)
1277 {
1278 arelent *r;
1279
1280 r = relocs[i][j];
1281 if (r->sym_ptr_ptr != NULL
1282 && (*r->sym_ptr_ptr)->section == sym->section
1283 && (*r->sym_ptr_ptr)->value == sym->value
1284 && strcmp (symname,
1285 bfd_asymbol_name (*r->sym_ptr_ptr)) == 0
1286 && bfd_find_nearest_line (abfd, secs[i], syms,
1287 r->address, &filename,
1288 &functionname, &lineno))
1289 {
1290 /* We only print the first one we find. */
1291 printf ("\t%s:%u", filename, lineno);
1292 i = seccount;
1293 break;
1294 }
1295 }
1296 }
1297 }
1298 else if (bfd_get_section (sym)->owner == abfd)
1299 {
1300 if (bfd_find_nearest_line (abfd, bfd_get_section (sym), syms,
1301 sym->value, &filename, &functionname,
1302 &lineno)
1303 && filename != NULL
1304 && lineno != 0)
1305 {
1306 printf ("\t%s:%u", filename, lineno);
1307 }
1308 }
1309 }
1310
1311 putchar ('\n');
1312}
1313\f
1314/* The following 3 groups of functions are called unconditionally,
1315 once at the start of processing each file of the appropriate type.
1316 They should check `filename_per_file' and `filename_per_symbol',
1317 as appropriate for their output format, to determine whether to
1318 print anything. */
1319\f
1320/* Print the name of an object file given on the command line. */
1321
1322static void
1323print_object_filename_bsd (filename)
1324 char *filename;
1325{
1326 if (filename_per_file && !filename_per_symbol)
1327 printf ("\n%s:\n", filename);
1328}
1329
1330static void
1331print_object_filename_sysv (filename)
1332 char *filename;
1333{
1334 if (undefined_only)
1335 printf (_("\n\nUndefined symbols from %s:\n\n"), filename);
1336 else
1337 printf (_("\n\nSymbols from %s:\n\n"), filename);
1338 printf (_("\
1339Name Value Class Type Size Line Section\n\n"));
1340}
1341
1342static void
1343print_object_filename_posix (filename)
1344 char *filename;
1345{
1346 if (filename_per_file && !filename_per_symbol)
1347 printf ("%s:\n", filename);
1348}
1349\f
1350/* Print the name of an archive file given on the command line. */
1351
1352static void
1353print_archive_filename_bsd (filename)
1354 char *filename;
1355{
1356 if (filename_per_file)
1357 printf ("\n%s:\n", filename);
1358}
1359
1360static void
1361print_archive_filename_sysv (filename)
b4c96d0d 1362 char *filename ATTRIBUTE_UNUSED;
252b5132
RH
1363{
1364}
1365
1366static void
1367print_archive_filename_posix (filename)
b4c96d0d 1368 char *filename ATTRIBUTE_UNUSED;
252b5132
RH
1369{
1370}
1371\f
1372/* Print the name of an archive member file. */
1373
1374static void
1375print_archive_member_bsd (archive, filename)
b4c96d0d 1376 char *archive ATTRIBUTE_UNUSED;
252b5132
RH
1377 CONST char *filename;
1378{
1379 if (!filename_per_symbol)
1380 printf ("\n%s:\n", filename);
1381}
1382
1383static void
1384print_archive_member_sysv (archive, filename)
1385 char *archive;
1386 CONST char *filename;
1387{
1388 if (undefined_only)
1389 printf (_("\n\nUndefined symbols from %s[%s]:\n\n"), archive, filename);
1390 else
1391 printf (_("\n\nSymbols from %s[%s]:\n\n"), archive, filename);
1392 printf (_("\
1393Name Value Class Type Size Line Section\n\n"));
1394}
1395
1396static void
1397print_archive_member_posix (archive, filename)
1398 char *archive;
1399 CONST char *filename;
1400{
1401 if (!filename_per_symbol)
1402 printf ("%s[%s]:\n", archive, filename);
1403}
1404\f
1405/* Print the name of the file (and archive, if there is one)
1406 containing a symbol. */
1407
1408static void
1409print_symbol_filename_bsd (archive_bfd, abfd)
1410 bfd *archive_bfd, *abfd;
1411{
1412 if (filename_per_symbol)
1413 {
1414 if (archive_bfd)
1415 printf ("%s:", bfd_get_filename (archive_bfd));
1416 printf ("%s:", bfd_get_filename (abfd));
1417 }
1418}
1419
1420static void
1421print_symbol_filename_sysv (archive_bfd, abfd)
1422 bfd *archive_bfd, *abfd;
1423{
1424 if (filename_per_symbol)
1425 {
1426 if (archive_bfd)
1427 printf ("%s:", bfd_get_filename (archive_bfd));
1428 printf ("%s:", bfd_get_filename (abfd));
1429 }
1430}
1431
1432static void
1433print_symbol_filename_posix (archive_bfd, abfd)
1434 bfd *archive_bfd, *abfd;
1435{
1436 if (filename_per_symbol)
1437 {
1438 if (archive_bfd)
1439 printf ("%s[%s]: ", bfd_get_filename (archive_bfd),
1440 bfd_get_filename (abfd));
1441 else
1442 printf ("%s: ", bfd_get_filename (abfd));
1443 }
1444}
1445\f
1446/* Print a symbol value. */
1447
1448static void
d8180c76
L
1449print_value (abfd, val)
1450 bfd *abfd;
252b5132
RH
1451 bfd_vma val;
1452{
1453#if ! defined (BFD64) || BFD_HOST_64BIT_LONG
1454 printf (value_format, val);
1455#else
1456 /* We have a 64 bit value to print, but the host is only 32 bit. */
1457 if (print_radix == 16)
d8180c76 1458 bfd_fprintf_vma (abfd, stdout, val);
252b5132
RH
1459 else
1460 {
1461 char buf[30];
1462 char *s;
1463
1464 s = buf + sizeof buf;
1465 *--s = '\0';
1466 while (val > 0)
1467 {
1468 *--s = (val % print_radix) + '0';
1469 val /= print_radix;
1470 }
1471 while ((buf + sizeof buf - 1) - s < 16)
1472 *--s = '0';
1473 printf ("%s", s);
1474 }
1475#endif
1476}
1477
1478/* Print a line of information about a symbol. */
1479
1480static void
1481print_symbol_info_bsd (info, abfd)
1482 symbol_info *info;
1483 bfd *abfd;
1484{
fad6fcbb 1485 if (bfd_is_undefined_symclass (info->type))
252b5132 1486 {
62a5a82d
L
1487 if (print_width == 16)
1488 printf (" ");
21211521 1489 printf (" ");
252b5132
RH
1490 }
1491 else
d8180c76 1492 print_value (abfd, info->value);
252b5132
RH
1493 printf (" %c", info->type);
1494 if (info->type == '-')
1495 {
1496 /* A stab. */
1497 printf (" ");
1498 printf (other_format, info->stab_other);
1499 printf (" ");
1500 printf (desc_format, info->stab_desc);
1501 printf (" %5s", info->stab_name);
1502 }
1503 print_symname (" %s", info->name, abfd);
1504}
1505
1506static void
1507print_symbol_info_sysv (info, abfd)
1508 symbol_info *info;
1509 bfd *abfd;
1510{
1511 print_symname ("%-20s|", info->name, abfd); /* Name */
fad6fcbb 1512 if (bfd_is_undefined_symclass (info->type))
252b5132
RH
1513 printf (" "); /* Value */
1514 else
d8180c76 1515 print_value (abfd, info->value);
252b5132
RH
1516 printf ("| %c |", info->type); /* Class */
1517 if (info->type == '-')
1518 {
1519 /* A stab. */
1520 printf ("%18s| ", info->stab_name); /* (C) Type */
1521 printf (desc_format, info->stab_desc); /* Size */
1522 printf ("| |"); /* Line, Section */
1523 }
1524 else
1525 printf (" | | |"); /* Type, Size, Line, Section */
1526}
1527
1528static void
1529print_symbol_info_posix (info, abfd)
1530 symbol_info *info;
1531 bfd *abfd;
1532{
1533 print_symname ("%s ", info->name, abfd);
1534 printf ("%c ", info->type);
fad6fcbb 1535 if (bfd_is_undefined_symclass (info->type))
252b5132
RH
1536 printf (" ");
1537 else
d8180c76 1538 print_value (abfd, info->value);
252b5132
RH
1539 /* POSIX.2 wants the symbol size printed here, when applicable;
1540 BFD currently doesn't provide it, so we take the easy way out by
1541 considering it to never be applicable. */
1542}
1543\f
1544static void
1545print_symdef_entry (abfd)
1546 bfd *abfd;
1547{
1548 symindex idx = BFD_NO_MORE_SYMBOLS;
1549 carsym *thesym;
1550 boolean everprinted = false;
1551
1552 for (idx = bfd_get_next_mapent (abfd, idx, &thesym);
1553 idx != BFD_NO_MORE_SYMBOLS;
1554 idx = bfd_get_next_mapent (abfd, idx, &thesym))
1555 {
1556 bfd *elt;
1557 if (!everprinted)
1558 {
1559 printf (_("\nArchive index:\n"));
1560 everprinted = true;
1561 }
1562 elt = bfd_get_elt_at_index (abfd, idx);
1563 if (elt == NULL)
1564 bfd_fatal ("bfd_get_elt_at_index");
1565 if (thesym->name != (char *) NULL)
1566 {
1567 print_symname ("%s", thesym->name, abfd);
1568 printf (" in %s\n", bfd_get_filename (elt));
1569 }
1570 }
1571}
1572\f
1573/* This function is used to get the relocs for a particular section.
1574 It is called via bfd_map_over_sections. */
1575
1576static void
1577get_relocs (abfd, sec, dataarg)
1578 bfd *abfd;
1579 asection *sec;
1580 PTR dataarg;
1581{
1582 struct get_relocs_info *data = (struct get_relocs_info *) dataarg;
1583
1584 *data->secs = sec;
1585
1586 if ((sec->flags & SEC_RELOC) == 0)
1587 {
1588 *data->relocs = NULL;
1589 *data->relcount = 0;
1590 }
1591 else
1592 {
1593 long relsize;
1594
1595 relsize = bfd_get_reloc_upper_bound (abfd, sec);
1596 if (relsize < 0)
1597 bfd_fatal (bfd_get_filename (abfd));
1598
1599 *data->relocs = (arelent **) xmalloc (relsize);
1600 *data->relcount = bfd_canonicalize_reloc (abfd, sec, *data->relocs,
1601 data->syms);
1602 if (*data->relcount < 0)
1603 bfd_fatal (bfd_get_filename (abfd));
1604 }
1605
1606 ++data->secs;
1607 ++data->relocs;
1608 ++data->relcount;
1609}
This page took 0.138547 seconds and 4 git commands to generate.