+2005-04-11 Nick Clifton <nickc@redhat.com>
+
+ * aout-target.h: Convert to ISO C.
+ * aoutf1.h: Convert to ISO C.
+ * aoutx.h: Convert to ISO C.
+ * bout.c: Convert to ISO C.
+ * dwarf1.c: Convert to ISO C.
+ * ecoffswap.h: Convert to ISO C.
+ * freebsd.h: Convert to ISO C.
+ * genlink.h: Convert to ISO C.
+ * ieee.c: Convert to ISO C.
+ * ihex.c: Convert to ISO C.
+ * libcoff-in.h: Convert to ISO C.
+ * mach-o.c: Convert to ISO C.
+ * mach-o.h: Convert to ISO C.
+ * netbsd.h: Convert to ISO C.
+ * ns32k.h: Convert to ISO C.
+ * ns32knetbsd.c: Convert to ISO C.
+ * oasys.c: Convert to ISO C.
+ * pdp11.c: Convert to ISO C.
+ * pef-traceback.h: Convert to ISO C.
+ * pef.c: Convert to ISO C.
+ * pef.h: Convert to ISO C.
+ * riscix.c: Convert to ISO C.
+ * som.c: Convert to ISO C.
+ * som.h: Convert to ISO C.
+ * srec.c: Convert to ISO C.
+ * stabs.c: Convert to ISO C.
+ * sunos.c: Convert to ISO C.
+ * tekhex.c: Convert to ISO C.
+ * versados.c: Convert to ISO C.
+ * version.h: Convert to ISO C.
+ * xcoff-target.h: Convert to ISO C.
+ * xcofflink.c: Convert to ISO C.
+ * xsym.c: Convert to ISO C.
+ * xsym.h: Convert to ISO C.
+
2005-04-08 Paul Brook <paul@codesourcery.com>
* elf32-arm.c (ARM2THUMB_GLUE_SIZE): Rename...
2000, 2001, 2002, 2003, 2004, 2005
Free Software Foundation, Inc.
-This file is part of BFD, the Binary File Descriptor library.
+ This file is part of BFD, the Binary File Descriptor library.
-This program is free software; you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation; either version 2 of the License, or
-(at your option) any later version.
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-GNU General Public License for more details.
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
-You should have received a copy of the GNU General Public License
-along with this program; if not, write to the Free Software
-Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
#include "aout/aout64.h"
#include "aout/stab_gnu.h"
#define SEGMENT_SIZE TARGET_PAGE_SIZE
#endif
-extern reloc_howto_type * NAME(aout,reloc_type_lookup)
- PARAMS ((bfd *, bfd_reloc_code_real_type));
+extern reloc_howto_type * NAME (aout, reloc_type_lookup) (bfd *, bfd_reloc_code_real_type);
/* Set parameters about this a.out file that are machine-dependent.
This routine is called from some_aout_object_p just before it returns. */
#ifndef MY_callback
-static const bfd_target *MY(callback) PARAMS ((bfd *));
-
static const bfd_target *
-MY(callback) (abfd)
- bfd *abfd;
+MY (callback) (bfd *abfd)
{
struct internal_exec *execp = exec_hdr (abfd);
unsigned int arch_align_power;
unsigned long arch_align;
- /* Calculate the file positions of the parts of a newly read aout header */
- obj_textsec (abfd)->size = N_TXTSIZE(*execp);
+ /* Calculate the file positions of the parts of a newly read aout header. */
+ obj_textsec (abfd)->size = N_TXTSIZE (*execp);
- /* The virtual memory addresses of the sections */
- obj_textsec (abfd)->vma = N_TXTADDR(*execp);
- obj_datasec (abfd)->vma = N_DATADDR(*execp);
- obj_bsssec (abfd)->vma = N_BSSADDR(*execp);
+ /* The virtual memory addresses of the sections. */
+ obj_textsec (abfd)->vma = N_TXTADDR (*execp);
+ obj_datasec (abfd)->vma = N_DATADDR (*execp);
+ obj_bsssec (abfd)->vma = N_BSSADDR (*execp);
/* For some targets, if the entry point is not in the same page
as the start of the text, then adjust the VMA so that it is.
obj_datasec (abfd)->lma = obj_datasec (abfd)->vma;
obj_bsssec (abfd)->lma = obj_bsssec (abfd)->vma;
- /* The file offsets of the sections */
+ /* The file offsets of the sections. */
obj_textsec (abfd)->filepos = N_TXTOFF (*execp);
obj_datasec (abfd)->filepos = N_DATOFF (*execp);
- /* The file offsets of the relocation info */
- obj_textsec (abfd)->rel_filepos = N_TRELOFF(*execp);
- obj_datasec (abfd)->rel_filepos = N_DRELOFF(*execp);
+ /* The file offsets of the relocation info. */
+ obj_textsec (abfd)->rel_filepos = N_TRELOFF (*execp);
+ obj_datasec (abfd)->rel_filepos = N_DRELOFF (*execp);
/* The file offsets of the string table and symbol table. */
obj_sym_filepos (abfd) = N_SYMOFF (*execp);
execp->a_drsize / obj_reloc_entry_size (abfd);
/* Now that we know the architecture, set the alignments of the
- sections. This is normally done by NAME(aout,new_section_hook),
+ sections. This is normally done by NAME (aout,new_section_hook),
but when the initial sections were created the architecture had
not yet been set. However, for backward compatibility, we don't
set the alignment power any higher than as required by the size
#endif
#ifndef MY_object_p
-/* Finish up the reading of an a.out file header */
-
-static const bfd_target *MY(object_p) PARAMS ((bfd *));
+/* Finish up the reading of an a.out file header. */
static const bfd_target *
-MY(object_p) (abfd)
- bfd *abfd;
+MY (object_p) (bfd *abfd)
{
- struct external_exec exec_bytes; /* Raw exec header from file */
- struct internal_exec exec; /* Cleaned-up exec header */
+ struct external_exec exec_bytes; /* Raw exec header from file. */
+ struct internal_exec exec; /* Cleaned-up exec header. */
const bfd_target *target;
bfd_size_type amt = EXEC_BYTES_SIZE;
- if (bfd_bread ((PTR) &exec_bytes, amt, abfd) != amt)
+ if (bfd_bread ((void *) &exec_bytes, amt, abfd) != amt)
{
if (bfd_get_error () != bfd_error_system_call)
bfd_set_error (bfd_error_wrong_format);
exec.a_info = SWAP_MAGIC (exec_bytes.e_info);
#else
exec.a_info = GET_MAGIC (abfd, exec_bytes.e_info);
-#endif /* SWAP_MAGIC */
+#endif
+
+ if (N_BADMAG (exec))
+ return 0;
- if (N_BADMAG (exec)) return 0;
#ifdef MACHTYPE_OK
- if (!(MACHTYPE_OK (N_MACHTYPE (exec)))) return 0;
+ if (!(MACHTYPE_OK (N_MACHTYPE (exec))))
+ return 0;
#endif
- NAME(aout,swap_exec_header_in) (abfd, &exec_bytes, &exec);
+ NAME (aout, swap_exec_header_in) (abfd, &exec_bytes, &exec);
#ifdef SWAP_MAGIC
- /* swap_exec_header_in read in a_info with the wrong byte order */
+ /* Swap_exec_header_in read in a_info with the wrong byte order. */
exec.a_info = SWAP_MAGIC (exec_bytes.e_info);
-#endif /* SWAP_MAGIC */
+#endif
- target = NAME(aout,some_aout_object_p) (abfd, &exec, MY(callback));
+ target = NAME (aout, some_aout_object_p) (abfd, &exec, MY (callback));
#ifdef ENTRY_CAN_BE_ZERO
/* The NEWSOS3 entry-point is/was 0, which (amongst other lossage)
- * means that it isn't obvious if EXEC_P should be set.
- * All of the following must be true for an executable:
- * There must be no relocations, the bfd can be neither an
- * archive nor an archive element, and the file must be executable. */
+ means that it isn't obvious if EXEC_P should be set.
+ All of the following must be true for an executable:
+ There must be no relocations, the bfd can be neither an
+ archive nor an archive element, and the file must be executable. */
if (exec.a_trsize + exec.a_drsize == 0
&& bfd_get_format(abfd) == bfd_object && abfd->my_archive == NULL)
return target;
}
-#define MY_object_p MY(object_p)
+#define MY_object_p MY (object_p)
#endif
#ifndef MY_mkobject
-static bfd_boolean MY(mkobject) PARAMS ((bfd *));
-
static bfd_boolean
-MY(mkobject) (abfd)
- bfd *abfd;
+MY (mkobject) (bfd *abfd)
{
return NAME (aout, mkobject (abfd));
}
-#define MY_mkobject MY(mkobject)
+#define MY_mkobject MY (mkobject)
#endif
#ifndef MY_bfd_copy_private_section_data
section contents, and copy_private_bfd_data is not called until
after the section contents have been set. */
-static bfd_boolean MY_bfd_copy_private_section_data
- PARAMS ((bfd *, asection *, bfd *, asection *));
-
static bfd_boolean
-MY_bfd_copy_private_section_data (ibfd, isec, obfd, osec)
- bfd *ibfd;
- asection *isec ATTRIBUTE_UNUSED;
- bfd *obfd;
- asection *osec ATTRIBUTE_UNUSED;
+MY_bfd_copy_private_section_data (bfd *ibfd,
+ asection *isec ATTRIBUTE_UNUSED,
+ bfd *obfd,
+ asection *osec ATTRIBUTE_UNUSED)
{
if (bfd_get_flavour (ibfd) == bfd_target_aout_flavour
&& bfd_get_flavour (obfd) == bfd_target_aout_flavour)
file header, symbols, and relocation. */
#ifndef MY_write_object_contents
-static bfd_boolean MY(write_object_contents) PARAMS ((bfd *));
static bfd_boolean
-MY(write_object_contents) (abfd)
- bfd *abfd;
+MY (write_object_contents) (bfd *abfd)
{
struct external_exec exec_bytes;
struct internal_exec *execp = exec_hdr (abfd);
obj_reloc_entry_size (abfd) = RELOC_STD_SIZE;
- WRITE_HEADERS(abfd, execp);
+ WRITE_HEADERS (abfd, execp);
return TRUE;
}
-#define MY_write_object_contents MY(write_object_contents)
+#define MY_write_object_contents MY (write_object_contents)
#endif
#ifndef MY_set_sizes
-static bfd_boolean MY(set_sizes) PARAMS ((bfd *));
-
static bfd_boolean
-MY(set_sizes) (abfd)
- bfd *abfd;
+MY (set_sizes) (bfd *abfd)
{
adata(abfd).page_size = TARGET_PAGE_SIZE;
adata(abfd).segment_size = SEGMENT_SIZE;
adata(abfd).exec_bytes_size = EXEC_BYTES_SIZE;
return TRUE;
}
-#define MY_set_sizes MY(set_sizes)
+#define MY_set_sizes MY (set_sizes)
#endif
#ifndef MY_exec_hdr_flags
#define MY_finish_dynamic_link 0
#endif
-static const struct aout_backend_data MY(backend_data) = {
+static const struct aout_backend_data MY (backend_data) =
+{
MY_zmagic_contiguous,
MY_text_includes_header,
MY_entry_is_text_address,
MY_exec_hdr_flags,
- 0, /* text vma? */
+ 0, /* Text vma? */
MY_set_sizes,
MY_exec_header_not_counted,
MY_add_dynamic_symbols,
MY_check_dynamic_reloc,
MY_finish_dynamic_link
};
-#define MY_backend_data &MY(backend_data)
+#define MY_backend_data &MY (backend_data)
#endif
#ifndef MY_final_link_callback
/* Callback for the final_link routine to set the section offsets. */
-static void MY_final_link_callback
- PARAMS ((bfd *, file_ptr *, file_ptr *, file_ptr *));
-
static void
-MY_final_link_callback (abfd, ptreloff, pdreloff, psymoff)
- bfd *abfd;
- file_ptr *ptreloff;
- file_ptr *pdreloff;
- file_ptr *psymoff;
+MY_final_link_callback (bfd *abfd,
+ file_ptr *ptreloff,
+ file_ptr *pdreloff,
+ file_ptr *psymoff)
{
struct internal_exec *execp = exec_hdr (abfd);
/* Final link routine. We need to use a call back to get the correct
offsets in the output file. */
-static bfd_boolean MY_bfd_final_link PARAMS ((bfd *, struct bfd_link_info *));
-
static bfd_boolean
-MY_bfd_final_link (abfd, info)
- bfd *abfd;
- struct bfd_link_info *info;
+MY_bfd_final_link (bfd *abfd, struct bfd_link_info *info)
{
- return NAME(aout,final_link) (abfd, info, MY_final_link_callback);
+ return NAME (aout, final_link) (abfd, info, MY_final_link_callback);
}
#endif
#endif
#ifndef MY_bfd_debug_info_accumulate
#define MY_bfd_debug_info_accumulate \
- (void (*) PARAMS ((bfd*, struct bfd_section *))) bfd_void
+ (void (*) (bfd *, struct bfd_section *)) bfd_void
#endif
#ifndef MY_core_file_failing_command
-#define MY_core_file_failing_command NAME(aout,core_file_failing_command)
+#define MY_core_file_failing_command NAME (aout, core_file_failing_command)
#endif
#ifndef MY_core_file_failing_signal
-#define MY_core_file_failing_signal NAME(aout,core_file_failing_signal)
+#define MY_core_file_failing_signal NAME (aout, core_file_failing_signal)
#endif
#ifndef MY_core_file_matches_executable_p
-#define MY_core_file_matches_executable_p NAME(aout,core_file_matches_executable_p)
+#define MY_core_file_matches_executable_p NAME (aout, core_file_matches_executable_p)
#endif
#ifndef MY_set_section_contents
-#define MY_set_section_contents NAME(aout,set_section_contents)
+#define MY_set_section_contents NAME (aout, set_section_contents)
#endif
#ifndef MY_get_section_contents
-#define MY_get_section_contents NAME(aout,get_section_contents)
+#define MY_get_section_contents NAME (aout, get_section_contents)
#endif
#ifndef MY_get_section_contents_in_window
#define MY_get_section_contents_in_window _bfd_generic_get_section_contents_in_window
#endif
#ifndef MY_new_section_hook
-#define MY_new_section_hook NAME(aout,new_section_hook)
+#define MY_new_section_hook NAME (aout, new_section_hook)
#endif
#ifndef MY_get_symtab_upper_bound
-#define MY_get_symtab_upper_bound NAME(aout,get_symtab_upper_bound)
+#define MY_get_symtab_upper_bound NAME (aout, get_symtab_upper_bound)
#endif
#ifndef MY_canonicalize_symtab
-#define MY_canonicalize_symtab NAME(aout,canonicalize_symtab)
+#define MY_canonicalize_symtab NAME (aout, canonicalize_symtab)
#endif
#ifndef MY_get_reloc_upper_bound
-#define MY_get_reloc_upper_bound NAME(aout,get_reloc_upper_bound)
+#define MY_get_reloc_upper_bound NAME (aout,get_reloc_upper_bound)
#endif
#ifndef MY_canonicalize_reloc
-#define MY_canonicalize_reloc NAME(aout,canonicalize_reloc)
+#define MY_canonicalize_reloc NAME (aout, canonicalize_reloc)
#endif
#ifndef MY_make_empty_symbol
-#define MY_make_empty_symbol NAME(aout,make_empty_symbol)
+#define MY_make_empty_symbol NAME (aout, make_empty_symbol)
#endif
#ifndef MY_print_symbol
-#define MY_print_symbol NAME(aout,print_symbol)
+#define MY_print_symbol NAME (aout, print_symbol)
#endif
#ifndef MY_get_symbol_info
-#define MY_get_symbol_info NAME(aout,get_symbol_info)
+#define MY_get_symbol_info NAME (aout, get_symbol_info)
#endif
#ifndef MY_get_lineno
-#define MY_get_lineno NAME(aout,get_lineno)
+#define MY_get_lineno NAME (aout, get_lineno)
#endif
#ifndef MY_set_arch_mach
-#define MY_set_arch_mach NAME(aout,set_arch_mach)
+#define MY_set_arch_mach NAME (aout, set_arch_mach)
#endif
#ifndef MY_find_nearest_line
-#define MY_find_nearest_line NAME(aout,find_nearest_line)
+#define MY_find_nearest_line NAME (aout, find_nearest_line)
#endif
#ifndef MY_sizeof_headers
-#define MY_sizeof_headers NAME(aout,sizeof_headers)
+#define MY_sizeof_headers NAME (aout, sizeof_headers)
#endif
#ifndef MY_bfd_get_relocated_section_contents
#define MY_bfd_get_relocated_section_contents \
_bfd_generic_section_already_linked
#endif
#ifndef MY_bfd_reloc_type_lookup
-#define MY_bfd_reloc_type_lookup NAME(aout,reloc_type_lookup)
+#define MY_bfd_reloc_type_lookup NAME (aout, reloc_type_lookup)
#endif
#ifndef MY_bfd_make_debug_symbol
#define MY_bfd_make_debug_symbol 0
#endif
#ifndef MY_read_minisymbols
-#define MY_read_minisymbols NAME(aout,read_minisymbols)
+#define MY_read_minisymbols NAME (aout, read_minisymbols)
#endif
#ifndef MY_minisymbol_to_symbol
-#define MY_minisymbol_to_symbol NAME(aout,minisymbol_to_symbol)
+#define MY_minisymbol_to_symbol NAME (aout, minisymbol_to_symbol)
#endif
#ifndef MY_bfd_link_hash_table_create
-#define MY_bfd_link_hash_table_create NAME(aout,link_hash_table_create)
+#define MY_bfd_link_hash_table_create NAME (aout, link_hash_table_create)
#endif
#ifndef MY_bfd_link_hash_table_free
#define MY_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
#endif
#ifndef MY_bfd_link_add_symbols
-#define MY_bfd_link_add_symbols NAME(aout,link_add_symbols)
+#define MY_bfd_link_add_symbols NAME (aout, link_add_symbols)
#endif
#ifndef MY_bfd_link_just_syms
#define MY_bfd_link_just_syms _bfd_generic_link_just_syms
#endif
#ifndef MY_bfd_free_cached_info
-#define MY_bfd_free_cached_info NAME(aout,bfd_free_cached_info)
+#define MY_bfd_free_cached_info NAME (aout, bfd_free_cached_info)
#endif
#ifndef MY_close_and_cleanup
_bfd_nodynamic_canonicalize_dynamic_reloc
#endif
-/* Aout symbols normally have leading underscores */
+/* Aout symbols normally have leading underscores. */
#ifndef MY_symbol_leading_char
#define MY_symbol_leading_char '_'
#endif
-/* Aout archives normally use spaces for padding */
+/* Aout archives normally use spaces for padding. */
#ifndef AR_PAD_CHAR
#define AR_PAD_CHAR ' '
#endif
#ifndef MY_BFD_TARGET
-const bfd_target MY(vec) =
+const bfd_target MY (vec) =
{
- TARGETNAME, /* name */
+ TARGETNAME, /* Name. */
bfd_target_aout_flavour,
#ifdef TARGET_IS_BIG_ENDIAN_P
- BFD_ENDIAN_BIG, /* target byte order (big) */
- BFD_ENDIAN_BIG, /* target headers byte order (big) */
+ BFD_ENDIAN_BIG, /* Target byte order (big). */
+ BFD_ENDIAN_BIG, /* Target headers byte order (big). */
#else
- BFD_ENDIAN_LITTLE, /* target byte order (little) */
- BFD_ENDIAN_LITTLE, /* target headers byte order (little) */
+ BFD_ENDIAN_LITTLE, /* Target byte order (little). */
+ BFD_ENDIAN_LITTLE, /* Target headers byte order (little). */
#endif
- (HAS_RELOC | EXEC_P | /* object flags */
+ (HAS_RELOC | EXEC_P | /* Object flags. */
HAS_LINENO | HAS_DEBUG |
HAS_SYMS | HAS_LOCALS | DYNAMIC | WP_TEXT | D_PAGED),
(SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD | SEC_RELOC | SEC_CODE | SEC_DATA),
MY_symbol_leading_char,
- AR_PAD_CHAR, /* ar_pad_char */
- 15, /* ar_max_namelen */
+ AR_PAD_CHAR, /* AR_pad_char. */
+ 15, /* AR_max_namelen. */
#ifdef TARGET_IS_BIG_ENDIAN_P
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* data */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Data. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* hdrs */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Headers. */
#else
bfd_getl64, bfd_getl_signed_64, bfd_putl64,
bfd_getl32, bfd_getl_signed_32, bfd_putl32,
- bfd_getl16, bfd_getl_signed_16, bfd_putl16, /* data */
+ bfd_getl16, bfd_getl_signed_16, bfd_putl16, /* Data. */
bfd_getl64, bfd_getl_signed_64, bfd_putl64,
bfd_getl32, bfd_getl_signed_32, bfd_putl32,
- bfd_getl16, bfd_getl_signed_16, bfd_putl16, /* hdrs */
+ bfd_getl16, bfd_getl_signed_16, bfd_putl16, /* Headers. */
#endif
- {_bfd_dummy_target, MY_object_p, /* bfd_check_format */
+ {_bfd_dummy_target, MY_object_p, /* bfd_check_format. */
bfd_generic_archive_p, MY_core_file_p},
- {bfd_false, MY_mkobject, /* bfd_set_format */
+ {bfd_false, MY_mkobject, /* bfd_set_format. */
_bfd_generic_mkarchive, bfd_false},
- {bfd_false, MY_write_object_contents, /* bfd_write_contents */
+ {bfd_false, MY_write_object_contents, /* bfd_write_contents. */
_bfd_write_archive_contents, bfd_false},
BFD_JUMP_TABLE_GENERIC (MY),
BFD_JUMP_TABLE_LINK (MY),
BFD_JUMP_TABLE_DYNAMIC (MY),
- /* Alternative_target */
+ /* Alternative_target. */
NULL,
- (PTR) MY_backend_data
+ MY_backend_data
};
#endif /* MY_BFD_TARGET */
/* A.out "format 1" file handling code for BFD.
Copyright 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1997, 1998, 2000,
- 2001, 2002, 2003, 2004
+ 2001, 2002, 2003, 2004, 2005
Free Software Foundation, Inc.
Written by Cygnus Support.
-This file is part of BFD, the Binary File Descriptor library.
+ This file is part of BFD, the Binary File Descriptor library.
-This program is free software; you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation; either version 2 of the License, or
-(at your option) any later version.
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-GNU General Public License for more details.
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
-You should have received a copy of the GNU General Public License
-along with this program; if not, write to the Free Software
-Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
#include "bfd.h"
#include "sysdep.h"
#include "libbfd.h"
#include "aout/sun4.h"
-#include "libaout.h" /* BFD a.out internal data structures */
+#include "libaout.h" /* BFD a.out internal data structures. */
#include "aout/aout64.h"
#include "aout/stab_gnu.h"
&& bfd_lookup_arch (bfd_arch_m68k, 0) != NULL))
#endif
-/*
-The file @code{aoutf1.h} contains the code for BFD's
-a.out back end. Control over the generated back end is given by these
-two preprocessor names:
-@table @code
-@item ARCH_SIZE
-This value should be either 32 or 64, depending upon the size of an
-int in the target format. It changes the sizes of the structs which
-perform the memory/disk mapping of structures.
-
-The 64 bit backend may only be used if the host compiler supports 64
-ints (eg long long with gcc), by defining the name @code{BFD_HOST_64_BIT} in @code{bfd.h}.
-With this name defined, @emph{all} bfd operations are performed with 64bit
-arithmetic, not just those to a 64bit target.
-
-@item TARGETNAME
-The name put into the target vector.
-@item
-@end table
-
-*/
-
-/*SUPPRESS558*/
-/*SUPPRESS529*/
+/* The file @code{aoutf1.h} contains the code for BFD's
+ a.out back end. Control over the generated back end is given by these
+ two preprocessor names:
+ @table @code
+ @item ARCH_SIZE
+ This value should be either 32 or 64, depending upon the size of an
+ int in the target format. It changes the sizes of the structs which
+ perform the memory/disk mapping of structures.
+
+ The 64 bit backend may only be used if the host compiler supports 64
+ ints (eg long long with gcc), by defining the name @code{BFD_HOST_64_BIT} in @code{bfd.h}.
+ With this name defined, @emph{all} bfd operations are performed with 64bit
+ arithmetic, not just those to a 64bit target.
+
+ @item TARGETNAME
+ The name put into the target vector.
+ @item
+ @end table. */
#if ARCH_SIZE == 64
#define sunos_set_arch_mach sunos_64_set_arch_mach
#define sunos_write_object_contents aout_32_sunos4_write_object_contents
#endif
-static bfd_boolean sunos_merge_private_bfd_data
- PARAMS ((bfd *, bfd *));
-static void sunos_set_arch_mach
- PARAMS ((bfd *, enum machine_type));
-static void choose_reloc_size
- PARAMS ((bfd *));
-static bfd_boolean sunos_write_object_contents
- PARAMS ((bfd *));
-static const bfd_target *sunos4_core_file_p
- PARAMS ((bfd *));
-static char *sunos4_core_file_failing_command
- PARAMS ((bfd *));
-static int sunos4_core_file_failing_signal
- PARAMS ((bfd *));
-static bfd_boolean sunos4_core_file_matches_executable_p
- PARAMS ((bfd *, bfd *));
-static bfd_boolean sunos4_set_sizes
- PARAMS ((bfd *));
-
/* Merge backend data into the output file.
This is necessary on sparclet-aout where we want the resultant machine
number to be M_SPARCLET if any input file is M_SPARCLET. */
#define MY_bfd_merge_private_bfd_data sunos_merge_private_bfd_data
static bfd_boolean
-sunos_merge_private_bfd_data (ibfd, obfd)
- bfd *ibfd, *obfd;
+sunos_merge_private_bfd_data (bfd *ibfd, bfd *obfd)
{
if (bfd_get_flavour (ibfd) != bfd_target_aout_flavour
|| bfd_get_flavour (obfd) != bfd_target_aout_flavour)
depending upon ARCH_SIZE. */
static void
-sunos_set_arch_mach (abfd, machtype)
- bfd *abfd;
- enum machine_type machtype;
+sunos_set_arch_mach (bfd *abfd, enum machine_type machtype)
{
/* Determine the architecture and machine type of the object file. */
enum bfd_architecture arch;
unsigned long machine;
+
switch (machtype)
{
-
case M_UNKNOWN:
/* Some Sun3s make magic numbers without cpu types in them, so
we'll default to the 68000. */
NAME(sunos,set_arch_mach) (ABFD, N_MACHTYPE (EXEC)); \
choose_reloc_size(ABFD);
-/* Determine the size of a relocation entry, based on the architecture */
+/* Determine the size of a relocation entry, based on the architecture. */
+
static void
-choose_reloc_size (abfd)
- bfd *abfd;
+choose_reloc_size (bfd *abfd)
{
switch (bfd_get_arch (abfd))
{
aout_32_sunos4_write_object_contents, depending upon ARCH_SIZE. */
static bfd_boolean
-sunos_write_object_contents (abfd)
- bfd *abfd;
+sunos_write_object_contents (bfd *abfd)
{
struct external_exec exec_bytes;
struct internal_exec *execp = exec_hdr (abfd);
return TRUE;
}
\f
-/* core files */
+/* Core files. */
-#define CORE_MAGIC 0x080456
+#define CORE_MAGIC 0x080456
#define CORE_NAMELEN 16
/* The core structure is taken from the Sun documentation.
even portably access the stuff in between! */
struct external_sparc_core
- {
- int c_magic; /* Corefile magic number */
- int c_len; /* Sizeof (struct core) */
+{
+ int c_magic; /* Corefile magic number. */
+ int c_len; /* Sizeof (struct core). */
#define SPARC_CORE_LEN 432
- int c_regs[19]; /* General purpose registers -- MACHDEP SIZE */
- struct external_exec c_aouthdr; /* A.out header */
- int c_signo; /* Killing signal, if any */
- int c_tsize; /* Text size (bytes) */
- int c_dsize; /* Data size (bytes) */
- int c_ssize; /* Stack size (bytes) */
- char c_cmdname[CORE_NAMELEN + 1]; /* Command name */
- double fp_stuff[1]; /* external FPU state (size unknown by us) */
- /* The type "double" is critical here, for alignment.
- SunOS declares a struct here, but the struct's alignment
- is double since it contains doubles. */
- int c_ucode; /* Exception no. from u_code */
- /* (this member is not accessible by name since we don't
- portably know the size of fp_stuff.) */
- };
+ int c_regs[19]; /* General purpose registers -- MACHDEP SIZE. */
+ struct external_exec c_aouthdr; /* A.out header. */
+ int c_signo; /* Killing signal, if any. */
+ int c_tsize; /* Text size (bytes). */
+ int c_dsize; /* Data size (bytes). */
+ int c_ssize; /* Stack size (bytes). */
+ char c_cmdname[CORE_NAMELEN + 1]; /* Command name. */
+ double fp_stuff[1]; /* External FPU state (size unknown by us). */
+ /* The type "double" is critical here, for alignment.
+ SunOS declares a struct here, but the struct's
+ alignment is double since it contains doubles. */
+ int c_ucode; /* Exception no. from u_code. */
+ /* This member is not accessible by name since
+ we don't portably know the size of fp_stuff. */
+};
/* Core files generated by the BCP (the part of Solaris which allows
it to run SunOS4 a.out files). */
struct external_solaris_bcp_core
- {
- int c_magic; /* Corefile magic number */
- int c_len; /* Sizeof (struct core) */
+{
+ int c_magic; /* Corefile magic number. */
+ int c_len; /* Sizeof (struct core). */
#define SOLARIS_BCP_CORE_LEN 456
- int c_regs[19]; /* General purpose registers -- MACHDEP SIZE */
- int c_exdata_vp; /* exdata structure */
- int c_exdata_tsize;
- int c_exdata_dsize;
- int c_exdata_bsize;
- int c_exdata_lsize;
- int c_exdata_nshlibs;
- short c_exdata_mach;
- short c_exdata_mag;
- int c_exdata_toffset;
- int c_exdata_doffset;
- int c_exdata_loffset;
- int c_exdata_txtorg;
- int c_exdata_datorg;
- int c_exdata_entloc;
- int c_signo; /* Killing signal, if any */
- int c_tsize; /* Text size (bytes) */
- int c_dsize; /* Data size (bytes) */
- int c_ssize; /* Stack size (bytes) */
- char c_cmdname[CORE_NAMELEN + 1]; /* Command name */
- double fp_stuff[1]; /* external FPU state (size unknown by us) */
- /* The type "double" is critical here, for alignment.
- SunOS declares a struct here, but the struct's alignment
- is double since it contains doubles. */
- int c_ucode; /* Exception no. from u_code */
- /* (this member is not accessible by name since we don't
- portably know the size of fp_stuff.) */
- };
+ int c_regs[19]; /* General purpose registers -- MACHDEP SIZE. */
+ int c_exdata_vp; /* Exdata structure. */
+ int c_exdata_tsize;
+ int c_exdata_dsize;
+ int c_exdata_bsize;
+ int c_exdata_lsize;
+ int c_exdata_nshlibs;
+ short c_exdata_mach;
+ short c_exdata_mag;
+ int c_exdata_toffset;
+ int c_exdata_doffset;
+ int c_exdata_loffset;
+ int c_exdata_txtorg;
+ int c_exdata_datorg;
+ int c_exdata_entloc;
+ int c_signo; /* Killing signal, if any. */
+ int c_tsize; /* Text size (bytes). */
+ int c_dsize; /* Data size (bytes). */
+ int c_ssize; /* Stack size (bytes). */
+ char c_cmdname[CORE_NAMELEN + 1]; /* Command name. */
+ double fp_stuff[1]; /* External FPU state (size unknown by us). */
+ /* The type "double" is critical here, for alignment.
+ SunOS declares a struct here, but the struct's
+ alignment is double since it contains doubles. */
+ int c_ucode; /* Exception no. from u_code. */
+ /* This member is not accessible by name since
+ we don't portably know the size of fp_stuff. */
+};
struct external_sun3_core
- {
- int c_magic; /* Corefile magic number */
- int c_len; /* Sizeof (struct core) */
-#define SUN3_CORE_LEN 826 /* As of SunOS 4.1.1 */
- int c_regs[18]; /* General purpose registers -- MACHDEP SIZE */
- struct external_exec c_aouthdr; /* A.out header */
- int c_signo; /* Killing signal, if any */
- int c_tsize; /* Text size (bytes) */
- int c_dsize; /* Data size (bytes) */
- int c_ssize; /* Stack size (bytes) */
- char c_cmdname[CORE_NAMELEN + 1]; /* Command name */
- double fp_stuff[1]; /* external FPU state (size unknown by us) */
- /* The type "double" is critical here, for alignment.
- SunOS declares a struct here, but the struct's alignment
- is double since it contains doubles. */
- int c_ucode; /* Exception no. from u_code */
- /* (this member is not accessible by name since we don't
- portably know the size of fp_stuff.) */
- };
+{
+ int c_magic; /* Corefile magic number. */
+ int c_len; /* Sizeof (struct core). */
+#define SUN3_CORE_LEN 826 /* As of SunOS 4.1.1. */
+ int c_regs[18]; /* General purpose registers -- MACHDEP SIZE. */
+ struct external_exec c_aouthdr; /* A.out header. */
+ int c_signo; /* Killing signal, if any. */
+ int c_tsize; /* Text size (bytes). */
+ int c_dsize; /* Data size (bytes). */
+ int c_ssize; /* Stack size (bytes). */
+ char c_cmdname[CORE_NAMELEN + 1]; /* Command name. */
+ double fp_stuff[1]; /* External FPU state (size unknown by us). */
+ /* The type "double" is critical here, for alignment.
+ SunOS declares a struct here, but the struct's
+ alignment is double since it contains doubles. */
+ int c_ucode; /* Exception no. from u_code. */
+ /* This member is not accessible by name since
+ we don't portably know the size of fp_stuff. */
+};
struct internal_sunos_core
- {
- int c_magic; /* Corefile magic number */
- int c_len; /* Sizeof (struct core) */
- long c_regs_pos; /* file offset of General purpose registers */
- int c_regs_size; /* size of General purpose registers */
- struct internal_exec c_aouthdr; /* A.out header */
- int c_signo; /* Killing signal, if any */
- int c_tsize; /* Text size (bytes) */
- int c_dsize; /* Data size (bytes) */
- bfd_vma c_data_addr; /* Data start (address) */
- int c_ssize; /* Stack size (bytes) */
- bfd_vma c_stacktop; /* Stack top (address) */
- char c_cmdname[CORE_NAMELEN + 1]; /* Command name */
- long fp_stuff_pos; /* file offset of external FPU state (regs) */
- int fp_stuff_size; /* Size of it */
- int c_ucode; /* Exception no. from u_code */
- };
-
-static void swapcore_sun3
- PARAMS ((bfd *, char *, struct internal_sunos_core *));
-static void swapcore_sparc
- PARAMS ((bfd *, char *, struct internal_sunos_core *));
-static void swapcore_solaris_bcp
- PARAMS ((bfd *, char *, struct internal_sunos_core *));
-
-/* byte-swap in the Sun-3 core structure */
+{
+ int c_magic; /* Corefile magic number. */
+ int c_len; /* Sizeof (struct core). */
+ long c_regs_pos; /* File offset of General purpose registers. */
+ int c_regs_size; /* Size of General purpose registers. */
+ struct internal_exec c_aouthdr; /* A.out header. */
+ int c_signo; /* Killing signal, if any. */
+ int c_tsize; /* Text size (bytes). */
+ int c_dsize; /* Data size (bytes). */
+ bfd_vma c_data_addr; /* Data start (address). */
+ int c_ssize; /* Stack size (bytes). */
+ bfd_vma c_stacktop; /* Stack top (address). */
+ char c_cmdname[CORE_NAMELEN + 1]; /* Command name. */
+ long fp_stuff_pos; /* File offset of external FPU state (regs). */
+ int fp_stuff_size; /* Size of it. */
+ int c_ucode; /* Exception no. from u_code. */
+};
+
+/* Byte-swap in the Sun-3 core structure. */
+
static void
-swapcore_sun3 (abfd, ext, intcore)
- bfd *abfd;
- char *ext;
- struct internal_sunos_core *intcore;
+swapcore_sun3 (bfd *abfd, char *ext, struct internal_sunos_core *intcore)
{
struct external_sun3_core *extcore = (struct external_sun3_core *) ext;
/* FP stuff takes up whole rest of struct, except c_ucode. */
intcore->fp_stuff_size = intcore->c_len - (sizeof extcore->c_ucode) -
(file_ptr) (((struct external_sun3_core *) 0)->fp_stuff);
- /* Ucode is the last thing in the struct -- just before the end */
+ /* Ucode is the last thing in the struct -- just before the end. */
intcore->c_ucode = H_GET_32 (abfd,
(intcore->c_len
- sizeof (extcore->c_ucode)
+ (unsigned char *) extcore));
- intcore->c_stacktop = 0x0E000000; /* By experimentation */
+ intcore->c_stacktop = 0x0E000000; /* By experimentation. */
}
-/* byte-swap in the Sparc core structure */
+/* Byte-swap in the Sparc core structure. */
+
static void
-swapcore_sparc (abfd, ext, intcore)
- bfd *abfd;
- char *ext;
- struct internal_sunos_core *intcore;
+swapcore_sparc (bfd *abfd, char *ext, struct internal_sunos_core *intcore)
{
struct external_sparc_core *extcore = (struct external_sparc_core *) ext;
/* FP stuff takes up whole rest of struct, except c_ucode. */
intcore->fp_stuff_size = intcore->c_len - (sizeof extcore->c_ucode) -
(file_ptr) (((struct external_sparc_core *) 0)->fp_stuff);
- /* Ucode is the last thing in the struct -- just before the end */
+ /* Ucode is the last thing in the struct -- just before the end. */
intcore->c_ucode = H_GET_32 (abfd,
(intcore->c_len
- sizeof (extcore->c_ucode)
}
}
-/* byte-swap in the Solaris BCP core structure */
+/* Byte-swap in the Solaris BCP core structure. */
+
static void
-swapcore_solaris_bcp (abfd, ext, intcore)
- bfd *abfd;
- char *ext;
- struct internal_sunos_core *intcore;
+swapcore_solaris_bcp (bfd *abfd, char *ext, struct internal_sunos_core *intcore)
{
struct external_solaris_bcp_core *extcore =
(struct external_solaris_bcp_core *) ext;
are buggy. The exdata structure is not properly filled in, and
the data section is written from address zero instead of the data
start address. */
- memset ((PTR) &intcore->c_aouthdr, 0, sizeof (struct internal_exec));
+ memset ((void *) &intcore->c_aouthdr, 0, sizeof (struct internal_exec));
intcore->c_data_addr = H_GET_32 (abfd, &extcore->c_exdata_datorg);
intcore->c_signo = H_GET_32 (abfd, &extcore->c_signo);
intcore->c_tsize = H_GET_32 (abfd, &extcore->c_tsize);
}
}
-/* need this cast because ptr is really void * */
-#define core_hdr(bfd) ((bfd)->tdata.sun_core_data)
-#define core_datasec(bfd) (core_hdr(bfd)->data_section)
-#define core_stacksec(bfd) (core_hdr(bfd)->stack_section)
-#define core_regsec(bfd) (core_hdr(bfd)->reg_section)
-#define core_reg2sec(bfd) (core_hdr(bfd)->reg2_section)
+/* Need this cast because ptr is really void *. */
+#define core_hdr(bfd) ((bfd)->tdata.sun_core_data)
+#define core_datasec(bfd) (core_hdr (bfd)->data_section)
+#define core_stacksec(bfd) (core_hdr (bfd)->stack_section)
+#define core_regsec(bfd) (core_hdr (bfd)->reg_section)
+#define core_reg2sec(bfd) (core_hdr (bfd)->reg2_section)
-/* These are stored in the bfd's tdata */
+/* These are stored in the bfd's tdata. */
struct sun_core_struct
{
- struct internal_sunos_core *hdr; /* core file header */
+ struct internal_sunos_core *hdr; /* Core file header. */
asection *data_section;
asection *stack_section;
asection *reg_section;
};
static const bfd_target *
-sunos4_core_file_p (abfd)
- bfd *abfd;
+sunos4_core_file_p (bfd *abfd)
{
- unsigned char longbuf[4]; /* Raw bytes of various header fields */
+ unsigned char longbuf[4]; /* Raw bytes of various header fields. */
bfd_size_type core_size, amt;
unsigned long core_mag;
struct internal_sunos_core *core;
char external_core[1];
} *mergem;
- if (bfd_bread ((PTR) longbuf, (bfd_size_type) sizeof (longbuf), abfd)
+ if (bfd_bread ((void *) longbuf, (bfd_size_type) sizeof (longbuf), abfd)
!= sizeof (longbuf))
- return 0;
+ return NULL;
core_mag = H_GET_32 (abfd, longbuf);
if (core_mag != CORE_MAGIC)
- return 0;
+ return NULL;
/* SunOS core headers can vary in length; second word is size; */
- if (bfd_bread ((PTR) longbuf, (bfd_size_type) sizeof (longbuf), abfd)
+ if (bfd_bread ((void *) longbuf, (bfd_size_type) sizeof (longbuf), abfd)
!= sizeof (longbuf))
- return 0;
+ return NULL;
core_size = H_GET_32 (abfd, longbuf);
- /* Sanity check */
+ /* Sanity check. */
if (core_size > 20000)
- return 0;
+ return NULL;
if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) != 0)
- return 0;
+ return NULL;
amt = core_size + sizeof (struct mergem);
- mergem = (struct mergem *) bfd_zalloc (abfd, amt);
+ mergem = bfd_zalloc (abfd, amt);
if (mergem == NULL)
- return 0;
+ return NULL;
extcore = mergem->external_core;
- if ((bfd_bread ((PTR) extcore, core_size, abfd)) != core_size)
+ if ((bfd_bread ((void *) extcore, core_size, abfd)) != core_size)
{
loser:
bfd_release (abfd, (char *) mergem);
abfd->tdata.any = NULL;
bfd_section_list_clear (abfd);
- return 0;
+ return NULL;
}
/* Validate that it's a core file we know how to handle, due to sun
swapcore_solaris_bcp (abfd, extcore, core);
break;
default:
- bfd_set_error (bfd_error_system_call); /* FIXME */
+ bfd_set_error (bfd_error_system_call); /* FIXME. */
goto loser;
}
core_stacksec (abfd)->filepos = core->c_len + core->c_dsize;
core_datasec (abfd)->filepos = core->c_len;
- /* We'll access the regs afresh in the core file, like any section: */
+ /* We'll access the regs afresh in the core file, like any section: */
core_regsec (abfd)->filepos = (file_ptr) core->c_regs_pos;
core_reg2sec (abfd)->filepos = (file_ptr) core->fp_stuff_pos;
- /* Align to word at least */
+ /* Align to word at least. */
core_stacksec (abfd)->alignment_power = 2;
core_datasec (abfd)->alignment_power = 2;
core_regsec (abfd)->alignment_power = 2;
}
static char *
-sunos4_core_file_failing_command (abfd)
- bfd *abfd;
+sunos4_core_file_failing_command (bfd *abfd)
{
return core_hdr (abfd)->hdr->c_cmdname;
}
static int
-sunos4_core_file_failing_signal (abfd)
- bfd *abfd;
+sunos4_core_file_failing_signal (bfd *abfd)
{
return core_hdr (abfd)->hdr->c_signo;
}
static bfd_boolean
-sunos4_core_file_matches_executable_p (core_bfd, exec_bfd)
- bfd *core_bfd;
- bfd *exec_bfd;
+sunos4_core_file_matches_executable_p (bfd *core_bfd, bfd *exec_bfd)
{
if (core_bfd->xvec != exec_bfd->xvec)
{
if ((core_hdr (core_bfd)->hdr)->c_len == SOLARIS_BCP_CORE_LEN)
return TRUE;
- return (memcmp ((char *) &((core_hdr (core_bfd)->hdr)->c_aouthdr),
- (char *) exec_hdr (exec_bfd),
- sizeof (struct internal_exec)) == 0);
+ return memcmp ((char *) &((core_hdr (core_bfd)->hdr)->c_aouthdr),
+ (char *) exec_hdr (exec_bfd),
+ sizeof (struct internal_exec)) == 0;
}
#define MY_set_sizes sunos4_set_sizes
+
static bfd_boolean
-sunos4_set_sizes (abfd)
- bfd *abfd;
+sunos4_set_sizes (bfd *abfd)
{
switch (bfd_get_arch (abfd))
{
static const struct aout_backend_data sunos4_aout_backend =
{
- 0, /* zmagic files are not contiguous */
- 1, /* text includes header */
+ 0, /* Zmagic files are not contiguous. */
+ 1, /* Text includes header. */
MY_entry_is_text_address,
MY_exec_hdr_flags,
- 0, /* default text vma */
+ 0, /* Default text vma. */
sunos4_set_sizes,
- 0, /* header is counted in zmagic text */
+ 0, /* Header is counted in zmagic text. */
MY_add_dynamic_symbols,
MY_add_one_symbol,
MY_link_dynamic_object,
#define MY_bfd_debug_info_start bfd_void
#define MY_bfd_debug_info_end bfd_void
-#define MY_bfd_debug_info_accumulate \
- (void (*) PARAMS ((bfd *, struct bfd_section *))) bfd_void
+#define MY_bfd_debug_info_accumulate (void (*) (bfd *, struct bfd_section *)) bfd_void
#define MY_core_file_p sunos4_core_file_p
-#define MY_write_object_contents NAME(aout,sunos4_write_object_contents)
-#define MY_backend_data &sunos4_aout_backend
+#define MY_write_object_contents NAME(aout, sunos4_write_object_contents)
+#define MY_backend_data & sunos4_aout_backend
#ifndef TARGET_IS_LITTLE_ENDIAN_P
#define TARGET_IS_BIG_ENDIAN_P
#include "aout/stab_gnu.h"
#include "aout/ar.h"
-static bfd_boolean aout_get_external_symbols
- PARAMS ((bfd *));
-static bfd_boolean translate_from_native_sym_flags
- PARAMS ((bfd *, aout_symbol_type *));
-static bfd_boolean translate_to_native_sym_flags
- PARAMS ((bfd *, asymbol *, struct external_nlist *));
-static void adjust_o_magic
- PARAMS ((bfd *, struct internal_exec *));
-static void adjust_z_magic
- PARAMS ((bfd *, struct internal_exec *));
-static void adjust_n_magic
- PARAMS ((bfd *, struct internal_exec *));
-reloc_howto_type * NAME(aout,reloc_type_lookup)
- PARAMS ((bfd *, bfd_reloc_code_real_type));
+reloc_howto_type * NAME (aout, reloc_type_lookup) (bfd *, bfd_reloc_code_real_type);
/*
SUBSECTION
#endif
#ifndef MY_swap_std_reloc_in
-#define MY_swap_std_reloc_in NAME(aout,swap_std_reloc_in)
+#define MY_swap_std_reloc_in NAME (aout, swap_std_reloc_in)
#endif
#ifndef MY_swap_ext_reloc_in
-#define MY_swap_ext_reloc_in NAME(aout,swap_ext_reloc_in)
+#define MY_swap_ext_reloc_in NAME (aout, swap_ext_reloc_in)
#endif
#ifndef MY_swap_std_reloc_out
-#define MY_swap_std_reloc_out NAME(aout,swap_std_reloc_out)
+#define MY_swap_std_reloc_out NAME (aout, swap_std_reloc_out)
#endif
#ifndef MY_swap_ext_reloc_out
-#define MY_swap_ext_reloc_out NAME(aout,swap_ext_reloc_out)
+#define MY_swap_ext_reloc_out NAME (aout, swap_ext_reloc_out)
#endif
#ifndef MY_final_link_relocate
#define MY_relocate_contents _bfd_relocate_contents
#endif
-#define howto_table_ext NAME(aout,ext_howto_table)
-#define howto_table_std NAME(aout,std_howto_table)
+#define howto_table_ext NAME (aout, ext_howto_table)
+#define howto_table_std NAME (aout, std_howto_table)
reloc_howto_type howto_table_ext[] =
{
- /* type rs size bsz pcrel bitpos ovrf sf name part_inpl readmask setmask pcdone. */
- HOWTO(RELOC_8, 0, 0, 8, FALSE, 0, complain_overflow_bitfield,0,"8", FALSE, 0,0x000000ff, FALSE),
- HOWTO(RELOC_16, 0, 1, 16, FALSE, 0, complain_overflow_bitfield,0,"16", FALSE, 0,0x0000ffff, FALSE),
- HOWTO(RELOC_32, 0, 2, 32, FALSE, 0, complain_overflow_bitfield,0,"32", FALSE, 0,0xffffffff, FALSE),
- HOWTO(RELOC_DISP8, 0, 0, 8, TRUE, 0, complain_overflow_signed,0,"DISP8", FALSE, 0,0x000000ff, FALSE),
- HOWTO(RELOC_DISP16, 0, 1, 16, TRUE, 0, complain_overflow_signed,0,"DISP16", FALSE, 0,0x0000ffff, FALSE),
- HOWTO(RELOC_DISP32, 0, 2, 32, TRUE, 0, complain_overflow_signed,0,"DISP32", FALSE, 0,0xffffffff, FALSE),
- HOWTO(RELOC_WDISP30,2, 2, 30, TRUE, 0, complain_overflow_signed,0,"WDISP30", FALSE, 0,0x3fffffff, FALSE),
- HOWTO(RELOC_WDISP22,2, 2, 22, TRUE, 0, complain_overflow_signed,0,"WDISP22", FALSE, 0,0x003fffff, FALSE),
- HOWTO(RELOC_HI22, 10, 2, 22, FALSE, 0, complain_overflow_bitfield,0,"HI22", FALSE, 0,0x003fffff, FALSE),
- HOWTO(RELOC_22, 0, 2, 22, FALSE, 0, complain_overflow_bitfield,0,"22", FALSE, 0,0x003fffff, FALSE),
- HOWTO(RELOC_13, 0, 2, 13, FALSE, 0, complain_overflow_bitfield,0,"13", FALSE, 0,0x00001fff, FALSE),
- HOWTO(RELOC_LO10, 0, 2, 10, FALSE, 0, complain_overflow_dont,0,"LO10", FALSE, 0,0x000003ff, FALSE),
- HOWTO(RELOC_SFA_BASE,0, 2, 32, FALSE, 0, complain_overflow_bitfield,0,"SFA_BASE", FALSE, 0,0xffffffff, FALSE),
- HOWTO(RELOC_SFA_OFF13,0,2, 32, FALSE, 0, complain_overflow_bitfield,0,"SFA_OFF13",FALSE, 0,0xffffffff, FALSE),
- HOWTO(RELOC_BASE10, 0, 2, 10, FALSE, 0, complain_overflow_dont,0,"BASE10", FALSE, 0,0x000003ff, FALSE),
- HOWTO(RELOC_BASE13, 0, 2, 13, FALSE, 0, complain_overflow_signed,0,"BASE13", FALSE, 0,0x00001fff, FALSE),
- HOWTO(RELOC_BASE22, 10, 2, 22, FALSE, 0, complain_overflow_bitfield,0,"BASE22", FALSE, 0,0x003fffff, FALSE),
- HOWTO(RELOC_PC10, 0, 2, 10, TRUE, 0, complain_overflow_dont,0,"PC10", FALSE, 0,0x000003ff, TRUE),
- HOWTO(RELOC_PC22, 10, 2, 22, TRUE, 0, complain_overflow_signed,0,"PC22", FALSE, 0,0x003fffff, TRUE),
- HOWTO(RELOC_JMP_TBL,2, 2, 30, TRUE, 0, complain_overflow_signed,0,"JMP_TBL", FALSE, 0,0x3fffffff, FALSE),
- HOWTO(RELOC_SEGOFF16,0, 2, 0, FALSE, 0, complain_overflow_bitfield,0,"SEGOFF16", FALSE, 0,0x00000000, FALSE),
- HOWTO(RELOC_GLOB_DAT,0, 2, 0, FALSE, 0, complain_overflow_bitfield,0,"GLOB_DAT", FALSE, 0,0x00000000, FALSE),
- HOWTO(RELOC_JMP_SLOT,0, 2, 0, FALSE, 0, complain_overflow_bitfield,0,"JMP_SLOT", FALSE, 0,0x00000000, FALSE),
- HOWTO(RELOC_RELATIVE,0, 2, 0, FALSE, 0, complain_overflow_bitfield,0,"RELATIVE", FALSE, 0,0x00000000, FALSE),
- HOWTO(0, 0, 0, 0, FALSE, 0, complain_overflow_dont, 0, "R_SPARC_NONE", FALSE,0,0x00000000,TRUE),
- HOWTO(0, 0, 0, 0, FALSE, 0, complain_overflow_dont, 0, "R_SPARC_NONE", FALSE,0,0x00000000,TRUE),
+ /* Type rs size bsz pcrel bitpos ovrf sf name part_inpl readmask setmask pcdone. */
+ HOWTO (RELOC_8, 0, 0, 8, FALSE, 0, complain_overflow_bitfield, 0, "8", FALSE, 0, 0x000000ff, FALSE),
+ HOWTO (RELOC_16, 0, 1, 16, FALSE, 0, complain_overflow_bitfield, 0, "16", FALSE, 0, 0x0000ffff, FALSE),
+ HOWTO (RELOC_32, 0, 2, 32, FALSE, 0, complain_overflow_bitfield, 0, "32", FALSE, 0, 0xffffffff, FALSE),
+ HOWTO (RELOC_DISP8, 0, 0, 8, TRUE, 0, complain_overflow_signed, 0, "DISP8", FALSE, 0, 0x000000ff, FALSE),
+ HOWTO (RELOC_DISP16, 0, 1, 16, TRUE, 0, complain_overflow_signed, 0, "DISP16", FALSE, 0, 0x0000ffff, FALSE),
+ HOWTO (RELOC_DISP32, 0, 2, 32, TRUE, 0, complain_overflow_signed, 0, "DISP32", FALSE, 0, 0xffffffff, FALSE),
+ HOWTO (RELOC_WDISP30, 2, 2, 30, TRUE, 0, complain_overflow_signed, 0, "WDISP30", FALSE, 0, 0x3fffffff, FALSE),
+ HOWTO (RELOC_WDISP22, 2, 2, 22, TRUE, 0, complain_overflow_signed, 0, "WDISP22", FALSE, 0, 0x003fffff, FALSE),
+ HOWTO (RELOC_HI22, 10, 2, 22, FALSE, 0, complain_overflow_bitfield, 0, "HI22", FALSE, 0, 0x003fffff, FALSE),
+ HOWTO (RELOC_22, 0, 2, 22, FALSE, 0, complain_overflow_bitfield, 0, "22", FALSE, 0, 0x003fffff, FALSE),
+ HOWTO (RELOC_13, 0, 2, 13, FALSE, 0, complain_overflow_bitfield, 0, "13", FALSE, 0, 0x00001fff, FALSE),
+ HOWTO (RELOC_LO10, 0, 2, 10, FALSE, 0, complain_overflow_dont, 0, "LO10", FALSE, 0, 0x000003ff, FALSE),
+ HOWTO (RELOC_SFA_BASE,0, 2, 32, FALSE, 0, complain_overflow_bitfield, 0, "SFA_BASE", FALSE, 0, 0xffffffff, FALSE),
+ HOWTO (RELOC_SFA_OFF13,0, 2, 32, FALSE, 0, complain_overflow_bitfield, 0, "SFA_OFF13", FALSE, 0, 0xffffffff, FALSE),
+ HOWTO (RELOC_BASE10, 0, 2, 10, FALSE, 0, complain_overflow_dont, 0, "BASE10", FALSE, 0, 0x000003ff, FALSE),
+ HOWTO (RELOC_BASE13, 0, 2, 13, FALSE, 0, complain_overflow_signed, 0, "BASE13", FALSE, 0, 0x00001fff, FALSE),
+ HOWTO (RELOC_BASE22, 10, 2, 22, FALSE, 0, complain_overflow_bitfield, 0, "BASE22", FALSE, 0, 0x003fffff, FALSE),
+ HOWTO (RELOC_PC10, 0, 2, 10, TRUE, 0, complain_overflow_dont, 0, "PC10", FALSE, 0, 0x000003ff, TRUE),
+ HOWTO (RELOC_PC22, 10, 2, 22, TRUE, 0, complain_overflow_signed, 0, "PC22", FALSE, 0, 0x003fffff, TRUE),
+ HOWTO (RELOC_JMP_TBL, 2, 2, 30, TRUE, 0, complain_overflow_signed, 0, "JMP_TBL", FALSE, 0, 0x3fffffff, FALSE),
+ HOWTO (RELOC_SEGOFF16,0, 2, 0, FALSE, 0, complain_overflow_bitfield, 0, "SEGOFF16", FALSE, 0, 0x00000000, FALSE),
+ HOWTO (RELOC_GLOB_DAT,0, 2, 0, FALSE, 0, complain_overflow_bitfield, 0, "GLOB_DAT", FALSE, 0, 0x00000000, FALSE),
+ HOWTO (RELOC_JMP_SLOT,0, 2, 0, FALSE, 0, complain_overflow_bitfield, 0, "JMP_SLOT", FALSE, 0, 0x00000000, FALSE),
+ HOWTO (RELOC_RELATIVE,0, 2, 0, FALSE, 0, complain_overflow_bitfield, 0, "RELATIVE", FALSE, 0, 0x00000000, FALSE),
+ HOWTO (0, 0, 0, 0, FALSE, 0, complain_overflow_dont, 0, "R_SPARC_NONE",FALSE, 0, 0x00000000, TRUE),
+ HOWTO (0, 0, 0, 0, FALSE, 0, complain_overflow_dont, 0, "R_SPARC_NONE",FALSE, 0, 0x00000000, TRUE),
#define RELOC_SPARC_REV32 RELOC_WDISP19
- HOWTO(RELOC_SPARC_REV32, 0, 2, 32, FALSE, 0, complain_overflow_dont,0,"R_SPARC_REV32", FALSE, 0,0xffffffff, FALSE),
+ HOWTO (RELOC_SPARC_REV32, 0, 2, 32, FALSE, 0, complain_overflow_dont, 0,"R_SPARC_REV32",FALSE, 0, 0xffffffff, FALSE),
};
/* Convert standard reloc records to "arelent" format (incl byte swap). */
#define TABLE_SIZE(TABLE) (sizeof (TABLE) / sizeof (TABLE[0]))
reloc_howto_type *
-NAME(aout,reloc_type_lookup) (abfd,code)
- bfd *abfd;
- bfd_reloc_code_real_type code;
+NAME (aout, reloc_type_lookup) (bfd *abfd, bfd_reloc_code_real_type code)
{
-#define EXT(i, j) case i: return &howto_table_ext[j]
-#define STD(i, j) case i: return &howto_table_std[j]
+#define EXT(i, j) case i: return & howto_table_ext [j]
+#define STD(i, j) case i: return & howto_table_std [j]
int ext = obj_reloc_entry_size (abfd) == RELOC_EXT_SIZE;
if (code == BFD_RELOC_CTOR)
EXT (BFD_RELOC_SPARC_PC22, 18);
EXT (BFD_RELOC_SPARC_WPLT30, 19);
EXT (BFD_RELOC_SPARC_REV32, 26);
- default: return (reloc_howto_type *) NULL;
+ default:
+ return NULL;
}
else
/* std relocs. */
STD (BFD_RELOC_32_PCREL, 6);
STD (BFD_RELOC_16_BASEREL, 9);
STD (BFD_RELOC_32_BASEREL, 10);
- default: return (reloc_howto_type *) NULL;
+ default:
+ return NULL;
}
}
@file{aoutx.h} exports several routines for accessing the
contents of an a.out file, which are gathered and exported in
turn by various format specific files (eg sunos.c).
-
*/
/*
SYNOPSIS
void aout_@var{size}_swap_exec_header_in,
(bfd *abfd,
- struct external_exec *raw_bytes,
+ struct external_exec *bytes,
struct internal_exec *execp);
DESCRIPTION
#ifndef NAME_swap_exec_header_in
void
-NAME(aout,swap_exec_header_in) (abfd, raw_bytes, execp)
- bfd *abfd;
- struct external_exec *raw_bytes;
- struct internal_exec *execp;
+NAME (aout, swap_exec_header_in) (bfd *abfd,
+ struct external_exec *bytes,
+ struct internal_exec *execp)
{
- struct external_exec *bytes = (struct external_exec *)raw_bytes;
-
/* The internal_exec structure has some fields that are unused in this
configuration (IE for i960), so ensure that all such uninitialized
fields are zero'd out. There are places where two of these structs
are memcmp'd, and thus the contents do matter. */
- memset ((PTR) execp, 0, sizeof (struct internal_exec));
+ memset ((void *) execp, 0, sizeof (struct internal_exec));
/* Now fill in fields in the execp, from the bytes in the raw data. */
execp->a_info = H_GET_32 (abfd, bytes->e_info);
execp->a_text = GET_WORD (abfd, bytes->e_text);
execp->a_trsize = GET_WORD (abfd, bytes->e_trsize);
execp->a_drsize = GET_WORD (abfd, bytes->e_drsize);
}
-#define NAME_swap_exec_header_in NAME(aout,swap_exec_header_in)
+#define NAME_swap_exec_header_in NAME (aout, swap_exec_header_in)
#endif
/*
@var{execp} into the buffer @var{raw_bytes} ready for writing to disk.
*/
void
-NAME(aout,swap_exec_header_out) (abfd, execp, raw_bytes)
- bfd *abfd;
- struct internal_exec *execp;
- struct external_exec *raw_bytes;
+NAME (aout, swap_exec_header_out) (bfd *abfd,
+ struct internal_exec *execp,
+ struct external_exec *bytes)
{
- struct external_exec *bytes = (struct external_exec *)raw_bytes;
-
/* Now fill in fields in the raw data, from the fields in the exec struct. */
H_PUT_32 (abfd, execp->a_info , bytes->e_info);
PUT_WORD (abfd, execp->a_text , bytes->e_text);
/* Make all the section for an a.out file. */
bfd_boolean
-NAME(aout,make_sections) (abfd)
- bfd *abfd;
+NAME (aout, make_sections) (bfd *abfd)
{
- if (obj_textsec (abfd) == (asection *) NULL
- && bfd_make_section (abfd, ".text") == (asection *) NULL)
+ if (obj_textsec (abfd) == NULL && bfd_make_section (abfd, ".text") == NULL)
return FALSE;
- if (obj_datasec (abfd) == (asection *) NULL
- && bfd_make_section (abfd, ".data") == (asection *) NULL)
+ if (obj_datasec (abfd) == NULL && bfd_make_section (abfd, ".data") == NULL)
return FALSE;
- if (obj_bsssec (abfd) == (asection *) NULL
- && bfd_make_section (abfd, ".bss") == (asection *) NULL)
+ if (obj_bsssec (abfd) == NULL && bfd_make_section (abfd, ".bss") == NULL)
return FALSE;
return TRUE;
}
SYNOPSIS
const bfd_target *aout_@var{size}_some_aout_object_p
(bfd *abfd,
- const bfd_target *(*callback_to_real_object_p) ());
+ struct internal_exec *execp,
+ const bfd_target *(*callback_to_real_object_p) (bfd *));
DESCRIPTION
Some a.out variant thinks that the file open in @var{abfd}
*/
const bfd_target *
-NAME(aout,some_aout_object_p) (abfd, execp, callback_to_real_object_p)
- bfd *abfd;
- struct internal_exec *execp;
- const bfd_target *(*callback_to_real_object_p) PARAMS ((bfd *));
+NAME (aout, some_aout_object_p) (bfd *abfd,
+ struct internal_exec *execp,
+ const bfd_target *(*callback_to_real_object_p) (bfd *))
{
struct aout_data_struct *rawptr, *oldrawptr;
const bfd_target *result;
- bfd_size_type amt = sizeof (struct aout_data_struct);
+ bfd_size_type amt = sizeof (* rawptr);
- rawptr = (struct aout_data_struct *) bfd_zalloc (abfd, amt);
+ rawptr = bfd_zalloc (abfd, amt);
if (rawptr == NULL)
- return 0;
+ return NULL;
oldrawptr = abfd->tdata.aout_data;
abfd->tdata.aout_data = rawptr;
|| N_MAGIC (*execp) == BMAGIC)
adata (abfd).magic = o_magic;
else
- {
- /* Should have been checked with N_BADMAG before this routine
- was called. */
- abort ();
- }
+ /* Should have been checked with N_BADMAG before this routine
+ was called. */
+ abort ();
bfd_get_start_address (abfd) = execp->a_entry;
- obj_aout_symbols (abfd) = (aout_symbol_type *)NULL;
+ obj_aout_symbols (abfd) = NULL;
bfd_get_symcount (abfd) = execp->a_syms / sizeof (struct external_nlist);
/* The default relocation entry size is that of traditional V7 Unix. */
obj_aout_external_strings (abfd) = NULL;
obj_aout_sym_hashes (abfd) = NULL;
- if (! NAME(aout,make_sections) (abfd))
+ if (! NAME (aout, make_sections) (abfd))
goto error_ret;
obj_datasec (abfd)->size = execp->a_data;
*/
bfd_boolean
-NAME(aout,mkobject) (abfd)
- bfd *abfd;
+NAME (aout, mkobject) (bfd *abfd)
{
struct aout_data_struct *rawptr;
- bfd_size_type amt = sizeof (struct aout_data_struct);
+ bfd_size_type amt = sizeof (* rawptr);
bfd_set_error (bfd_error_system_call);
- rawptr = (struct aout_data_struct *) bfd_zalloc (abfd, amt);
+ rawptr = bfd_zalloc (abfd, amt);
if (rawptr == NULL)
return FALSE;
abfd->tdata.aout_data = rawptr;
exec_hdr (abfd) = &(rawptr->e);
- obj_textsec (abfd) = (asection *) NULL;
- obj_datasec (abfd) = (asection *) NULL;
- obj_bsssec (abfd) = (asection *) NULL;
+ obj_textsec (abfd) = NULL;
+ obj_datasec (abfd) = NULL;
+ obj_bsssec (abfd) = NULL;
return TRUE;
}
SYNOPSIS
enum machine_type aout_@var{size}_machine_type
(enum bfd_architecture arch,
- unsigned long machine));
+ unsigned long machine,
+ bfd_boolean *unknown);
DESCRIPTION
Keep track of machine architecture and machine type for
*/
enum machine_type
-NAME(aout,machine_type) (arch, machine, unknown)
- enum bfd_architecture arch;
- unsigned long machine;
- bfd_boolean *unknown;
+NAME (aout, machine_type) (enum bfd_architecture arch,
+ unsigned long machine,
+ bfd_boolean *unknown)
{
enum machine_type arch_flags;
bfd_boolean aout_@var{size}_set_arch_mach,
(bfd *,
enum bfd_architecture arch,
- unsigned long machine));
+ unsigned long machine);
DESCRIPTION
Set the architecture and the machine of the BFD @var{abfd} to the
*/
bfd_boolean
-NAME(aout,set_arch_mach) (abfd, arch, machine)
- bfd *abfd;
- enum bfd_architecture arch;
- unsigned long machine;
+NAME (aout, set_arch_mach) (bfd *abfd,
+ enum bfd_architecture arch,
+ unsigned long machine)
{
if (! bfd_default_set_arch_mach (abfd, arch, machine))
return FALSE;
{
bfd_boolean unknown;
- NAME(aout,machine_type) (arch, machine, &unknown);
+ NAME (aout, machine_type) (arch, machine, &unknown);
if (unknown)
return FALSE;
}
}
static void
-adjust_o_magic (abfd, execp)
- bfd *abfd;
- struct internal_exec *execp;
+adjust_o_magic (bfd *abfd, struct internal_exec *execp)
{
file_ptr pos = adata (abfd).exec_bytes_size;
bfd_vma vma = 0;
}
static void
-adjust_z_magic (abfd, execp)
- bfd *abfd;
- struct internal_exec *execp;
+adjust_z_magic (bfd *abfd, struct internal_exec *execp)
{
bfd_size_type data_pad, text_pad;
file_ptr text_end;
const struct aout_backend_data *abdp;
- int ztih; /* Nonzero if text includes exec header. */
+ /* TRUE if text includes exec header. */
+ bfd_boolean ztih;
abdp = aout_backend_info (abfd);
}
static void
-adjust_n_magic (abfd, execp)
- bfd *abfd;
- struct internal_exec *execp;
+adjust_n_magic (bfd *abfd, struct internal_exec *execp)
{
file_ptr pos = adata (abfd).exec_bytes_size;
bfd_vma vma = 0;
}
bfd_boolean
-NAME(aout,adjust_sizes_and_vmas) (abfd, text_size, text_end)
- bfd *abfd;
- bfd_size_type *text_size;
- file_ptr *text_end ATTRIBUTE_UNUSED;
+NAME (aout, adjust_sizes_and_vmas) (bfd *abfd,
+ bfd_size_type *text_size,
+ file_ptr *text_end ATTRIBUTE_UNUSED)
{
struct internal_exec *execp = exec_hdr (abfd);
- if (! NAME(aout,make_sections) (abfd))
+ if (! NAME (aout, make_sections) (abfd))
return FALSE;
if (adata (abfd).magic != undecided_magic)
SYNOPSIS
bfd_boolean aout_@var{size}_new_section_hook,
(bfd *abfd,
- asection *newsect));
+ asection *newsect);
DESCRIPTION
Called by the BFD in response to a @code{bfd_make_section}
request.
*/
bfd_boolean
-NAME(aout,new_section_hook) (abfd, newsect)
- bfd *abfd;
- asection *newsect;
+NAME (aout, new_section_hook) (bfd *abfd, asection *newsect)
{
/* Align to double at least. */
newsect->alignment_power = bfd_get_arch_info (abfd)->section_align_power;
}
bfd_boolean
-NAME(aout,set_section_contents) (abfd, section, location, offset, count)
- bfd *abfd;
- sec_ptr section;
- const PTR location;
- file_ptr offset;
- bfd_size_type count;
+NAME (aout, set_section_contents) (bfd *abfd,
+ sec_ptr section,
+ const void * location,
+ file_ptr offset,
+ bfd_size_type count)
{
file_ptr text_end;
bfd_size_type text_size;
if (! abfd->output_has_begun)
{
- if (! NAME(aout,adjust_sizes_and_vmas) (abfd, &text_size, &text_end))
+ if (! NAME (aout, adjust_sizes_and_vmas) (abfd, &text_size, &text_end))
return FALSE;
}
/* Read the external symbols from an a.out file. */
static bfd_boolean
-aout_get_external_symbols (abfd)
- bfd *abfd;
+aout_get_external_symbols (bfd *abfd)
{
- if (obj_aout_external_syms (abfd) == (struct external_nlist *) NULL)
+ if (obj_aout_external_syms (abfd) == NULL)
{
bfd_size_type count;
struct external_nlist *syms;
/* We allocate using malloc to make the values easy to free
later on. If we put them on the objalloc it might not be
possible to free them. */
- syms = ((struct external_nlist *)
- bfd_malloc (count * EXTERNAL_NLIST_SIZE));
- if (syms == (struct external_nlist *) NULL && count != 0)
+ syms = bfd_malloc (count * EXTERNAL_NLIST_SIZE);
+ if (syms == NULL && count != 0)
return FALSE;
amt = exec_hdr (abfd)->a_syms;
/* Get the size of the strings. */
if (bfd_seek (abfd, obj_str_filepos (abfd), SEEK_SET) != 0
- || bfd_bread ((PTR) string_chars, amt, abfd) != amt)
+ || bfd_bread ((void *) string_chars, amt, abfd) != amt)
return FALSE;
stringsize = GET_WORD (abfd, string_chars);
return FALSE;
strings = (char *) obj_aout_string_window (abfd).data;
#else
- strings = (char *) bfd_malloc (stringsize + 1);
+ strings = bfd_malloc (stringsize + 1);
if (strings == NULL)
return FALSE;
symbol->flags and symbol->section, and adjusting symbol->value. */
static bfd_boolean
-translate_from_native_sym_flags (abfd, cache_ptr)
- bfd *abfd;
- aout_symbol_type *cache_ptr;
+translate_from_native_sym_flags (bfd *abfd, aout_symbol_type *cache_ptr)
{
flagword visible;
/* Set the fields of SYM_POINTER according to CACHE_PTR. */
static bfd_boolean
-translate_to_native_sym_flags (abfd, cache_ptr, sym_pointer)
- bfd *abfd;
- asymbol *cache_ptr;
- struct external_nlist *sym_pointer;
+translate_to_native_sym_flags (bfd *abfd,
+ asymbol *cache_ptr,
+ struct external_nlist *sym_pointer)
{
bfd_vma value = cache_ptr->value;
asection *sec;
/* Native-level interface to symbols. */
asymbol *
-NAME(aout,make_empty_symbol) (abfd)
- bfd *abfd;
+NAME (aout, make_empty_symbol) (bfd *abfd)
{
bfd_size_type amt = sizeof (aout_symbol_type);
- aout_symbol_type *new = (aout_symbol_type *) bfd_zalloc (abfd, amt);
+
+ aout_symbol_type *new = bfd_zalloc (abfd, amt);
if (!new)
return NULL;
new->symbol.the_bfd = abfd;
/* Translate a set of internal symbols into external symbols. */
bfd_boolean
-NAME(aout,translate_symbol_table) (abfd, in, ext, count, str, strsize, dynamic)
- bfd *abfd;
- aout_symbol_type *in;
- struct external_nlist *ext;
- bfd_size_type count;
- char *str;
- bfd_size_type strsize;
- bfd_boolean dynamic;
+NAME (aout, translate_symbol_table) (bfd *abfd,
+ aout_symbol_type *in,
+ struct external_nlist *ext,
+ bfd_size_type count,
+ char *str,
+ bfd_size_type strsize,
+ bfd_boolean dynamic)
{
struct external_nlist *ext_end;
hold them all plus all the cached symbol entries. */
bfd_boolean
-NAME(aout,slurp_symbol_table) (abfd)
- bfd *abfd;
+NAME (aout, slurp_symbol_table) (bfd *abfd)
{
struct external_nlist *old_external_syms;
aout_symbol_type *cached;
bfd_size_type cached_size;
/* If there's no work to be done, don't do any. */
- if (obj_aout_symbols (abfd) != (aout_symbol_type *) NULL)
+ if (obj_aout_symbols (abfd) != NULL)
return TRUE;
old_external_syms = obj_aout_external_syms (abfd);
cached_size = obj_aout_external_sym_count (abfd);
cached_size *= sizeof (aout_symbol_type);
- cached = (aout_symbol_type *) bfd_zmalloc (cached_size);
+ cached = bfd_zmalloc (cached_size);
if (cached == NULL && cached_size != 0)
return FALSE;
/* Convert from external symbol information to internal. */
- if (! (NAME(aout,translate_symbol_table)
+ if (! (NAME (aout, translate_symbol_table)
(abfd, cached,
obj_aout_external_syms (abfd),
obj_aout_external_sym_count (abfd),
want the external symbol information, so if it was allocated
because of our call to aout_get_external_symbols, we free it up
right away to save space. */
- if (old_external_syms == (struct external_nlist *) NULL
- && obj_aout_external_syms (abfd) != (struct external_nlist *) NULL)
+ if (old_external_syms == NULL
+ && obj_aout_external_syms (abfd) != NULL)
{
#ifdef USE_MMAP
bfd_free_window (&obj_aout_sym_window (abfd));
This hash table code breaks dbx on SunOS 4.1.3, so we don't do it
if BFD_TRADITIONAL_FORMAT is set. */
-static bfd_size_type add_to_stringtab
- PARAMS ((bfd *, struct bfd_strtab_hash *, const char *, bfd_boolean));
-static bfd_boolean emit_stringtab
- PARAMS ((bfd *, struct bfd_strtab_hash *));
-
/* Get the index of a string in a strtab, adding it if it is not
already present. */
-static INLINE bfd_size_type
-add_to_stringtab (abfd, tab, str, copy)
- bfd *abfd;
- struct bfd_strtab_hash *tab;
- const char *str;
- bfd_boolean copy;
+static inline bfd_size_type
+add_to_stringtab (bfd *abfd,
+ struct bfd_strtab_hash *tab,
+ const char *str,
+ bfd_boolean copy)
{
bfd_boolean hash;
bfd_size_type index;
index = _bfd_stringtab_add (tab, str, hash, copy);
if (index != (bfd_size_type) -1)
- {
- /* Add BYTES_IN_WORD to the return value to account for the
- space taken up by the string table size. */
- index += BYTES_IN_WORD;
- }
+ /* Add BYTES_IN_WORD to the return value to account for the
+ space taken up by the string table size. */
+ index += BYTES_IN_WORD;
return index;
}
file. */
static bfd_boolean
-emit_stringtab (abfd, tab)
- register bfd *abfd;
- struct bfd_strtab_hash *tab;
+emit_stringtab (bfd *abfd, struct bfd_strtab_hash *tab)
{
bfd_byte buffer[BYTES_IN_WORD];
bfd_size_type amt = BYTES_IN_WORD;
/* The string table starts with the size. */
PUT_WORD (abfd, _bfd_stringtab_size (tab) + BYTES_IN_WORD, buffer);
- if (bfd_bwrite ((PTR) buffer, amt, abfd) != amt)
+ if (bfd_bwrite ((void *) buffer, amt, abfd) != amt)
return FALSE;
return _bfd_stringtab_emit (abfd, tab);
}
\f
bfd_boolean
-NAME(aout,write_syms) (abfd)
- bfd *abfd;
+NAME (aout, write_syms) (bfd *abfd)
{
unsigned int count ;
asymbol **generic = bfd_get_outsymbols (abfd);
goto error_return;
amt = EXTERNAL_NLIST_SIZE;
- if (bfd_bwrite ((PTR) &nsp, amt, abfd) != amt)
+ if (bfd_bwrite ((void *) &nsp, amt, abfd) != amt)
goto error_return;
/* NB: `KEEPIT' currently overlays `udata.p', so set this only
}
\f
long
-NAME(aout,canonicalize_symtab) (abfd, location)
- bfd *abfd;
- asymbol **location;
+NAME (aout, canonicalize_symtab) (bfd *abfd, asymbol **location)
{
- unsigned int counter = 0;
- aout_symbol_type *symbase;
+ unsigned int counter = 0;
+ aout_symbol_type *symbase;
- if (!NAME(aout,slurp_symbol_table) (abfd))
- return -1;
+ if (!NAME (aout, slurp_symbol_table) (abfd))
+ return -1;
- for (symbase = obj_aout_symbols (abfd);
- counter++ < bfd_get_symcount (abfd);
- )
- *(location++) = (asymbol *) (symbase++);
- *location++ =0;
- return bfd_get_symcount (abfd);
+ for (symbase = obj_aout_symbols (abfd);
+ counter++ < bfd_get_symcount (abfd);
+ )
+ *(location++) = (asymbol *) (symbase++);
+ *location++ =0;
+ return bfd_get_symcount (abfd);
}
\f
/* Standard reloc stuff. */
/* Output standard relocation information to a file in target byte order. */
-extern void NAME(aout,swap_std_reloc_out)
- PARAMS ((bfd *, arelent *, struct reloc_std_external *));
+extern void NAME (aout, swap_std_reloc_out)
+ (bfd *, arelent *, struct reloc_std_external *);
void
-NAME(aout,swap_std_reloc_out) (abfd, g, natptr)
- bfd *abfd;
- arelent *g;
- struct reloc_std_external *natptr;
+NAME (aout, swap_std_reloc_out) (bfd *abfd,
+ arelent *g,
+ struct reloc_std_external *natptr)
{
int r_index;
asymbol *sym = *(g->sym_ptr_ptr);
/* Extended stuff. */
/* Output extended relocation information to a file in target byte order. */
-extern void NAME(aout,swap_ext_reloc_out)
- PARAMS ((bfd *, arelent *, struct reloc_ext_external *));
+extern void NAME (aout, swap_ext_reloc_out)
+ (bfd *, arelent *, struct reloc_ext_external *);
void
-NAME(aout,swap_ext_reloc_out) (abfd, g, natptr)
- bfd *abfd;
- arelent *g;
- register struct reloc_ext_external *natptr;
+NAME (aout, swap_ext_reloc_out) (bfd *abfd,
+ arelent *g,
+ struct reloc_ext_external *natptr)
{
int r_index;
int r_extern;
}
void
-NAME(aout,swap_ext_reloc_in) (abfd, bytes, cache_ptr, symbols, symcount)
- bfd *abfd;
- struct reloc_ext_external *bytes;
- arelent *cache_ptr;
- asymbol **symbols;
- bfd_size_type symcount;
+NAME (aout, swap_ext_reloc_in) (bfd *abfd,
+ struct reloc_ext_external *bytes,
+ arelent *cache_ptr,
+ asymbol **symbols,
+ bfd_size_type symcount)
{
unsigned int r_index;
int r_extern;
}
void
-NAME(aout,swap_std_reloc_in) (abfd, bytes, cache_ptr, symbols, symcount)
- bfd *abfd;
- struct reloc_std_external *bytes;
- arelent *cache_ptr;
- asymbol **symbols;
- bfd_size_type symcount;
+NAME (aout, swap_std_reloc_in) (bfd *abfd,
+ struct reloc_std_external *bytes,
+ arelent *cache_ptr,
+ asymbol **symbols,
+ bfd_size_type symcount)
{
unsigned int r_index;
int r_extern;
/* Read and swap the relocs for a section. */
bfd_boolean
-NAME(aout,slurp_reloc_table) (abfd, asect, symbols)
- bfd *abfd;
- sec_ptr asect;
- asymbol **symbols;
+NAME (aout, slurp_reloc_table) (bfd *abfd, sec_ptr asect, asymbol **symbols)
{
bfd_size_type count;
bfd_size_type reloc_size;
- PTR relocs;
+ void * relocs;
arelent *reloc_cache;
size_t each_size;
unsigned int counter = 0;
count = reloc_size / each_size;
amt = count * sizeof (arelent);
- reloc_cache = (arelent *) bfd_zmalloc (amt);
+ reloc_cache = bfd_zmalloc (amt);
if (reloc_cache == NULL && count != 0)
return FALSE;
/* Write out a relocation section into an object file. */
bfd_boolean
-NAME(aout,squirt_out_relocs) (abfd, section)
- bfd *abfd;
- asection *section;
+NAME (aout, squirt_out_relocs) (bfd *abfd, asection *section)
{
arelent **generic;
unsigned char *native, *natptr;
each_size = obj_reloc_entry_size (abfd);
natsize = (bfd_size_type) each_size * count;
- native = (unsigned char *) bfd_zalloc (abfd, natsize);
+ native = bfd_zalloc (abfd, natsize);
if (!native)
return FALSE;
(struct reloc_std_external *) natptr);
}
- if (bfd_bwrite ((PTR) native, natsize, abfd) != natsize)
+ if (bfd_bwrite ((void *) native, natsize, abfd) != natsize)
{
bfd_release (abfd, native);
return FALSE;
/* This is stupid. This function should be a boolean predicate. */
long
-NAME(aout,canonicalize_reloc) (abfd, section, relptr, symbols)
- bfd *abfd;
- sec_ptr section;
- arelent **relptr;
- asymbol **symbols;
+NAME (aout, canonicalize_reloc) (bfd *abfd,
+ sec_ptr section,
+ arelent **relptr,
+ asymbol **symbols)
{
arelent *tblptr = section->relocation;
unsigned int count;
return 0;
}
- if (!(tblptr || NAME(aout,slurp_reloc_table) (abfd, section, symbols)))
+ if (!(tblptr || NAME (aout, slurp_reloc_table) (abfd, section, symbols)))
return -1;
if (section->flags & SEC_CONSTRUCTOR)
}
long
-NAME(aout,get_reloc_upper_bound) (abfd, asect)
- bfd *abfd;
- sec_ptr asect;
+NAME (aout, get_reloc_upper_bound) (bfd *abfd, sec_ptr asect)
{
if (bfd_get_format (abfd) != bfd_object)
{
}
if (asect->flags & SEC_CONSTRUCTOR)
- return (sizeof (arelent *) * (asect->reloc_count+1));
+ return sizeof (arelent *) * (asect->reloc_count + 1);
if (asect == obj_datasec (abfd))
- return (sizeof (arelent *)
- * ((exec_hdr (abfd)->a_drsize / obj_reloc_entry_size (abfd))
- + 1));
+ return sizeof (arelent *)
+ * ((exec_hdr (abfd)->a_drsize / obj_reloc_entry_size (abfd))
+ + 1);
if (asect == obj_textsec (abfd))
- return (sizeof (arelent *)
- * ((exec_hdr (abfd)->a_trsize / obj_reloc_entry_size (abfd))
- + 1));
+ return sizeof (arelent *)
+ * ((exec_hdr (abfd)->a_trsize / obj_reloc_entry_size (abfd))
+ + 1);
if (asect == obj_bsssec (abfd))
return sizeof (arelent *);
}
\f
long
-NAME(aout,get_symtab_upper_bound) (abfd)
- bfd *abfd;
+NAME (aout, get_symtab_upper_bound) (bfd *abfd)
{
- if (!NAME(aout,slurp_symbol_table) (abfd))
+ if (!NAME (aout, slurp_symbol_table) (abfd))
return -1;
return (bfd_get_symcount (abfd)+1) * (sizeof (aout_symbol_type *));
}
alent *
-NAME(aout,get_lineno) (ignore_abfd, ignore_symbol)
- bfd *ignore_abfd ATTRIBUTE_UNUSED;
- asymbol *ignore_symbol ATTRIBUTE_UNUSED;
+NAME (aout, get_lineno) (bfd *ignore_abfd ATTRIBUTE_UNUSED,
+ asymbol *ignore_symbol ATTRIBUTE_UNUSED)
{
- return (alent *)NULL;
+ return NULL;
}
void
-NAME(aout,get_symbol_info) (ignore_abfd, symbol, ret)
- bfd *ignore_abfd ATTRIBUTE_UNUSED;
- asymbol *symbol;
- symbol_info *ret;
+NAME (aout, get_symbol_info) (bfd *ignore_abfd ATTRIBUTE_UNUSED,
+ asymbol *symbol,
+ symbol_info *ret)
{
bfd_symbol_info (symbol, ret);
}
void
-NAME(aout,print_symbol) (abfd, afile, symbol, how)
- bfd *abfd;
- PTR afile;
- asymbol *symbol;
- bfd_print_symbol_type how;
+NAME (aout, print_symbol) (bfd *abfd,
+ void * afile,
+ asymbol *symbol,
+ bfd_print_symbol_type how)
{
FILE *file = (FILE *)afile;
{
const char *section_name = symbol->section->name;
- bfd_print_symbol_vandf (abfd, (PTR)file, symbol);
+ bfd_print_symbol_vandf (abfd, (void *)file, symbol);
fprintf (file," %-5s %04x %02x %02x",
section_name,
BFD asymbol structures. */
long
-NAME(aout,read_minisymbols) (abfd, dynamic, minisymsp, sizep)
- bfd *abfd;
- bfd_boolean dynamic;
- PTR *minisymsp;
- unsigned int *sizep;
+NAME (aout, read_minisymbols) (bfd *abfd,
+ bfd_boolean dynamic,
+ void * *minisymsp,
+ unsigned int *sizep)
{
if (dynamic)
- {
- /* We could handle the dynamic symbols here as well, but it's
- easier to hand them off. */
- return _bfd_generic_read_minisymbols (abfd, dynamic, minisymsp, sizep);
- }
+ /* We could handle the dynamic symbols here as well, but it's
+ easier to hand them off. */
+ return _bfd_generic_read_minisymbols (abfd, dynamic, minisymsp, sizep);
if (! aout_get_external_symbols (abfd))
return -1;
if (obj_aout_external_sym_count (abfd) < MINISYM_THRESHOLD)
return _bfd_generic_read_minisymbols (abfd, dynamic, minisymsp, sizep);
- *minisymsp = (PTR) obj_aout_external_syms (abfd);
+ *minisymsp = (void *) obj_aout_external_syms (abfd);
/* By passing the external symbols back from this routine, we are
giving up control over the memory block. Clear
by bfd_make_empty_symbol, which we fill in here. */
asymbol *
-NAME(aout,minisymbol_to_symbol) (abfd, dynamic, minisym, sym)
- bfd *abfd;
- bfd_boolean dynamic;
- const PTR minisym;
- asymbol *sym;
+NAME (aout, minisymbol_to_symbol) (bfd *abfd,
+ bfd_boolean dynamic,
+ const void * minisym,
+ asymbol *sym)
{
if (dynamic
|| obj_aout_external_sym_count (abfd) < MINISYM_THRESHOLD)
memset (sym, 0, sizeof (aout_symbol_type));
/* We call translate_symbol_table to translate a single symbol. */
- if (! (NAME(aout,translate_symbol_table)
+ if (! (NAME (aout, translate_symbol_table)
(abfd,
(aout_symbol_type *) sym,
(struct external_nlist *) minisym,
wanted location. */
bfd_boolean
-NAME(aout,find_nearest_line)
- (abfd, section, symbols, offset, filename_ptr, functionname_ptr, line_ptr)
- bfd *abfd;
- asection *section;
- asymbol **symbols;
- bfd_vma offset;
- const char **filename_ptr;
- const char **functionname_ptr;
- unsigned int *line_ptr;
+NAME (aout, find_nearest_line) (bfd *abfd,
+ asection *section,
+ asymbol **symbols,
+ bfd_vma offset,
+ const char **filename_ptr,
+ const char **functionname_ptr,
+ unsigned int *line_ptr)
{
/* Run down the file looking for the filename, function and linenumber. */
asymbol **p;
const char *directory_name = NULL;
const char *main_file_name = NULL;
const char *current_file_name = NULL;
- const char *line_file_name = NULL; /* Value of current_file_name at line number. */
+ const char *line_file_name = NULL; /* Value of current_file_name at line number. */
const char *line_directory_name = NULL; /* Value of directory_name at line number. */
bfd_vma low_line_vma = 0;
bfd_vma low_func_vma = 0;
*functionname_ptr = 0;
*line_ptr = 0;
- if (symbols != (asymbol **)NULL)
+ if (symbols != NULL)
{
for (p = symbols; *p; p++)
{
adata (abfd).line_buf = buf = NULL;
else
{
- buf = (char *) bfd_malloc (filelen + funclen + 3);
+ buf = bfd_malloc (filelen + funclen + 3);
adata (abfd).line_buf = buf;
if (buf == NULL)
return FALSE;
}
int
-NAME(aout,sizeof_headers) (abfd, execable)
- bfd *abfd;
- bfd_boolean execable ATTRIBUTE_UNUSED;
+NAME (aout, sizeof_headers) (bfd *abfd, bfd_boolean execable ATTRIBUTE_UNUSED)
{
return adata (abfd).exec_bytes_size;
}
read it again later if we need it. */
bfd_boolean
-NAME(aout,bfd_free_cached_info) (abfd)
- bfd *abfd;
+NAME (aout, bfd_free_cached_info) (bfd *abfd)
{
asection *o;
BFCI_FREE (obj_aout_external_syms (abfd));
BFCI_FREE (obj_aout_external_strings (abfd));
#endif
- for (o = abfd->sections; o != (asection *) NULL; o = o->next)
+ for (o = abfd->sections; o != NULL; o = o->next)
BFCI_FREE (o->relocation);
#undef BFCI_FREE
\f
/* a.out link code. */
-static bfd_boolean aout_link_add_object_symbols
- PARAMS ((bfd *, struct bfd_link_info *));
-static bfd_boolean aout_link_check_archive_element
- PARAMS ((bfd *, struct bfd_link_info *, bfd_boolean *));
-static bfd_boolean aout_link_free_symbols
- PARAMS ((bfd *));
-static bfd_boolean aout_link_check_ar_symbols
- PARAMS ((bfd *, struct bfd_link_info *, bfd_boolean *pneeded));
-static bfd_boolean aout_link_add_symbols
- PARAMS ((bfd *, struct bfd_link_info *));
-
/* Routine to create an entry in an a.out link hash table. */
struct bfd_hash_entry *
-NAME(aout,link_hash_newfunc) (entry, table, string)
- struct bfd_hash_entry *entry;
- struct bfd_hash_table *table;
- const char *string;
+NAME (aout, link_hash_newfunc) (struct bfd_hash_entry *entry,
+ struct bfd_hash_table *table,
+ const char *string)
{
struct aout_link_hash_entry *ret = (struct aout_link_hash_entry *) entry;
/* Allocate the structure if it has not already been allocated by a
subclass. */
- if (ret == (struct aout_link_hash_entry *) NULL)
- ret = ((struct aout_link_hash_entry *)
- bfd_hash_allocate (table, sizeof (struct aout_link_hash_entry)));
- if (ret == (struct aout_link_hash_entry *) NULL)
- return (struct bfd_hash_entry *) ret;
+ if (ret == NULL)
+ ret = bfd_hash_allocate (table, sizeof (* ret));
+ if (ret == NULL)
+ return NULL;
/* Call the allocation method of the superclass. */
ret = ((struct aout_link_hash_entry *)
/* Initialize an a.out link hash table. */
bfd_boolean
-NAME(aout,link_hash_table_init) (table, abfd, newfunc)
- struct aout_link_hash_table *table;
- bfd *abfd;
- struct bfd_hash_entry *(*newfunc)
- PARAMS ((struct bfd_hash_entry *, struct bfd_hash_table *,
- const char *));
+NAME (aout, link_hash_table_init) (struct aout_link_hash_table *table,
+ bfd *abfd,
+ struct bfd_hash_entry *(*newfunc)
+ (struct bfd_hash_entry *, struct bfd_hash_table *,
+ const char *))
{
return _bfd_link_hash_table_init (&table->root, abfd, newfunc);
}
/* Create an a.out link hash table. */
struct bfd_link_hash_table *
-NAME(aout,link_hash_table_create) (abfd)
- bfd *abfd;
+NAME (aout, link_hash_table_create) (bfd *abfd)
{
struct aout_link_hash_table *ret;
- bfd_size_type amt = sizeof (struct aout_link_hash_table);
+ bfd_size_type amt = sizeof (* ret);
- ret = (struct aout_link_hash_table *) bfd_malloc (amt);
+ ret = bfd_malloc (amt);
if (ret == NULL)
- return (struct bfd_link_hash_table *) NULL;
+ return NULL;
- if (! NAME(aout,link_hash_table_init) (ret, abfd,
- NAME(aout,link_hash_newfunc)))
+ if (! NAME (aout, link_hash_table_init) (ret, abfd,
+ NAME (aout, link_hash_newfunc)))
{
free (ret);
- return (struct bfd_link_hash_table *) NULL;
+ return NULL;
}
return &ret->root;
}
-/* Given an a.out BFD, add symbols to the global hash table as
- appropriate. */
-
-bfd_boolean
-NAME(aout,link_add_symbols) (abfd, info)
- bfd *abfd;
- struct bfd_link_info *info;
-{
- switch (bfd_get_format (abfd))
- {
- case bfd_object:
- return aout_link_add_object_symbols (abfd, info);
- case bfd_archive:
- return _bfd_generic_link_add_archive_symbols
- (abfd, info, aout_link_check_archive_element);
- default:
- bfd_set_error (bfd_error_wrong_format);
- return FALSE;
- }
-}
-
-/* Add symbols from an a.out object file. */
-
-static bfd_boolean
-aout_link_add_object_symbols (abfd, info)
- bfd *abfd;
- struct bfd_link_info *info;
-{
- if (! aout_get_external_symbols (abfd))
- return FALSE;
- if (! aout_link_add_symbols (abfd, info))
- return FALSE;
- if (! info->keep_memory)
- {
- if (! aout_link_free_symbols (abfd))
- return FALSE;
- }
- return TRUE;
-}
-
-/* Check a single archive element to see if we need to include it in
- the link. *PNEEDED is set according to whether this element is
- needed in the link or not. This is called from
- _bfd_generic_link_add_archive_symbols. */
+/* Add all symbols from an object file to the hash table. */
static bfd_boolean
-aout_link_check_archive_element (abfd, info, pneeded)
- bfd *abfd;
- struct bfd_link_info *info;
- bfd_boolean *pneeded;
+aout_link_add_symbols (bfd *abfd, struct bfd_link_info *info)
{
- if (! aout_get_external_symbols (abfd))
- return FALSE;
-
- if (! aout_link_check_ar_symbols (abfd, info, pneeded))
- return FALSE;
+ bfd_boolean (*add_one_symbol)
+ (struct bfd_link_info *, bfd *, const char *, flagword, asection *,
+ bfd_vma, const char *, bfd_boolean, bfd_boolean,
+ struct bfd_link_hash_entry **);
+ struct external_nlist *syms;
+ bfd_size_type sym_count;
+ char *strings;
+ bfd_boolean copy;
+ struct aout_link_hash_entry **sym_hash;
+ struct external_nlist *p;
+ struct external_nlist *pend;
+ bfd_size_type amt;
- if (*pneeded)
- {
- if (! aout_link_add_symbols (abfd, info))
- return FALSE;
- }
+ syms = obj_aout_external_syms (abfd);
+ sym_count = obj_aout_external_sym_count (abfd);
+ strings = obj_aout_external_strings (abfd);
+ if (info->keep_memory)
+ copy = FALSE;
+ else
+ copy = TRUE;
- if (! info->keep_memory || ! *pneeded)
+ if (aout_backend_info (abfd)->add_dynamic_symbols != NULL)
{
- if (! aout_link_free_symbols (abfd))
+ if (! ((*aout_backend_info (abfd)->add_dynamic_symbols)
+ (abfd, info, &syms, &sym_count, &strings)))
return FALSE;
}
- return TRUE;
-}
-
-/* Free up the internal symbols read from an a.out file. */
-
-static bfd_boolean
-aout_link_free_symbols (abfd)
- bfd *abfd;
-{
- if (obj_aout_external_syms (abfd) != (struct external_nlist *) NULL)
- {
-#ifdef USE_MMAP
- bfd_free_window (&obj_aout_sym_window (abfd));
-#else
- free ((PTR) obj_aout_external_syms (abfd));
-#endif
- obj_aout_external_syms (abfd) = (struct external_nlist *) NULL;
- }
- if (obj_aout_external_strings (abfd) != (char *) NULL)
- {
-#ifdef USE_MMAP
- bfd_free_window (&obj_aout_string_window (abfd));
-#else
- free ((PTR) obj_aout_external_strings (abfd));
-#endif
- obj_aout_external_strings (abfd) = (char *) NULL;
- }
- return TRUE;
-}
-
-/* Look through the internal symbols to see if this object file should
- be included in the link. We should include this object file if it
- defines any symbols which are currently undefined. If this object
- file defines a common symbol, then we may adjust the size of the
- known symbol but we do not include the object file in the link
- (unless there is some other reason to include it). */
-
-static bfd_boolean
-aout_link_check_ar_symbols (abfd, info, pneeded)
- bfd *abfd;
- struct bfd_link_info *info;
- bfd_boolean *pneeded;
-{
- register struct external_nlist *p;
- struct external_nlist *pend;
- char *strings;
+ /* We keep a list of the linker hash table entries that correspond
+ to particular symbols. We could just look them up in the hash
+ table, but keeping the list is more efficient. Perhaps this
+ should be conditional on info->keep_memory. */
+ amt = sym_count * sizeof (struct aout_link_hash_entry *);
+ sym_hash = bfd_alloc (abfd, amt);
+ if (sym_hash == NULL && sym_count != 0)
+ return FALSE;
+ obj_aout_sym_hashes (abfd) = sym_hash;
- *pneeded = FALSE;
+ add_one_symbol = aout_backend_info (abfd)->add_one_symbol;
+ if (add_one_symbol == NULL)
+ add_one_symbol = _bfd_generic_link_add_one_symbol;
- /* Look through all the symbols. */
- p = obj_aout_external_syms (abfd);
- pend = p + obj_aout_external_sym_count (abfd);
- strings = obj_aout_external_strings (abfd);
- for (; p < pend; p++)
+ p = syms;
+ pend = p + sym_count;
+ for (; p < pend; p++, sym_hash++)
{
- int type = H_GET_8 (abfd, p->e_type);
+ int type;
const char *name;
- struct bfd_link_hash_entry *h;
+ bfd_vma value;
+ asection *section;
+ flagword flags;
+ const char *string;
- /* Ignore symbols that are not externally visible. This is an
- optimization only, as we check the type more thoroughly
- below. */
- if (((type & N_EXT) == 0
- || (type & N_STAB) != 0
- || type == N_FN)
- && type != N_WEAKA
- && type != N_WEAKT
- && type != N_WEAKD
- && type != N_WEAKB)
- {
- if (type == N_WARNING
- || type == N_INDR)
- ++p;
- continue;
- }
+ *sym_hash = NULL;
- name = strings + GET_WORD (abfd, p->e_strx);
- h = bfd_link_hash_lookup (info->hash, name, FALSE, FALSE, TRUE);
+ type = H_GET_8 (abfd, p->e_type);
- /* We are only interested in symbols that are currently
- undefined or common. */
- if (h == (struct bfd_link_hash_entry *) NULL
- || (h->type != bfd_link_hash_undefined
- && h->type != bfd_link_hash_common))
- {
- if (type == (N_INDR | N_EXT))
- ++p;
- continue;
- }
+ /* Ignore debugging symbols. */
+ if ((type & N_STAB) != 0)
+ continue;
- if (type == (N_TEXT | N_EXT)
- || type == (N_DATA | N_EXT)
- || type == (N_BSS | N_EXT)
- || type == (N_ABS | N_EXT)
- || type == (N_INDR | N_EXT))
+ name = strings + GET_WORD (abfd, p->e_strx);
+ value = GET_WORD (abfd, p->e_value);
+ flags = BSF_GLOBAL;
+ string = NULL;
+ switch (type)
{
- /* This object file defines this symbol. We must link it
- in. This is true regardless of whether the current
- definition of the symbol is undefined or common.
+ default:
+ abort ();
- If the current definition is common, we have a case in
- which we have already seen an object file including:
- int a;
- and this object file from the archive includes:
- int a = 5;
- In such a case, whether to include this object is target
- dependant for backward compatibility.
+ case N_UNDF:
+ case N_ABS:
+ case N_TEXT:
+ case N_DATA:
+ case N_BSS:
+ case N_FN_SEQ:
+ case N_COMM:
+ case N_SETV:
+ case N_FN:
+ /* Ignore symbols that are not externally visible. */
+ continue;
+ case N_INDR:
+ /* Ignore local indirect symbol. */
+ ++p;
+ ++sym_hash;
+ continue;
- FIXME: The SunOS 4.1.3 linker will pull in the archive
- element if the symbol is defined in the .data section,
- but not if it is defined in the .text section. That
- seems a bit crazy to me, and it has not been implemented
- yet. However, it might be correct. */
- if (h->type == bfd_link_hash_common)
+ case N_UNDF | N_EXT:
+ if (value == 0)
{
- int skip = 0;
-
- switch (info->common_skip_ar_aymbols)
- {
- case bfd_link_common_skip_text:
- skip = (type == (N_TEXT | N_EXT));
- break;
- case bfd_link_common_skip_data:
- skip = (type == (N_DATA | N_EXT));
- break;
- default:
- case bfd_link_common_skip_all:
- skip = 1;
- break;
- }
-
- if (skip)
- continue;
- }
-
- if (! (*info->callbacks->add_archive_element) (info, abfd, name))
- return FALSE;
- *pneeded = TRUE;
- return TRUE;
- }
-
- if (type == (N_UNDF | N_EXT))
- {
- bfd_vma value;
-
- value = GET_WORD (abfd, p->e_value);
- if (value != 0)
- {
- /* This symbol is common in the object from the archive
- file. */
- if (h->type == bfd_link_hash_undefined)
- {
- bfd *symbfd;
- unsigned int power;
-
- symbfd = h->u.undef.abfd;
- if (symbfd == (bfd *) NULL)
- {
- /* This symbol was created as undefined from
- outside BFD. We assume that we should link
- in the object file. This is done for the -u
- option in the linker. */
- if (! (*info->callbacks->add_archive_element) (info,
- abfd,
- name))
- return FALSE;
- *pneeded = TRUE;
- return TRUE;
- }
- /* Turn the current link symbol into a common
- symbol. It is already on the undefs list. */
- h->type = bfd_link_hash_common;
- h->u.c.p = ((struct bfd_link_hash_common_entry *)
- bfd_hash_allocate (&info->hash->table,
- sizeof (struct bfd_link_hash_common_entry)));
- if (h->u.c.p == NULL)
- return FALSE;
-
- h->u.c.size = value;
-
- /* FIXME: This isn't quite right. The maximum
- alignment of a common symbol should be set by the
- architecture of the output file, not of the input
- file. */
- power = bfd_log2 (value);
- if (power > bfd_get_arch_info (abfd)->section_align_power)
- power = bfd_get_arch_info (abfd)->section_align_power;
- h->u.c.p->alignment_power = power;
-
- h->u.c.p->section = bfd_make_section_old_way (symbfd,
- "COMMON");
- }
- else
- {
- /* Adjust the size of the common symbol if
- necessary. */
- if (value > h->u.c.size)
- h->u.c.size = value;
- }
- }
- }
-
- if (type == N_WEAKA
- || type == N_WEAKT
- || type == N_WEAKD
- || type == N_WEAKB)
- {
- /* This symbol is weak but defined. We must pull it in if
- the current link symbol is undefined, but we don't want
- it if the current link symbol is common. */
- if (h->type == bfd_link_hash_undefined)
- {
- if (! (*info->callbacks->add_archive_element) (info, abfd, name))
- return FALSE;
- *pneeded = TRUE;
- return TRUE;
- }
- }
- }
-
- /* We do not need this object file. */
- return TRUE;
-}
-
-/* Add all symbols from an object file to the hash table. */
-
-static bfd_boolean
-aout_link_add_symbols (abfd, info)
- bfd *abfd;
- struct bfd_link_info *info;
-{
- bfd_boolean (*add_one_symbol)
- PARAMS ((struct bfd_link_info *, bfd *, const char *, flagword, asection *,
- bfd_vma, const char *, bfd_boolean, bfd_boolean,
- struct bfd_link_hash_entry **));
- struct external_nlist *syms;
- bfd_size_type sym_count;
- char *strings;
- bfd_boolean copy;
- struct aout_link_hash_entry **sym_hash;
- register struct external_nlist *p;
- struct external_nlist *pend;
- bfd_size_type amt;
-
- syms = obj_aout_external_syms (abfd);
- sym_count = obj_aout_external_sym_count (abfd);
- strings = obj_aout_external_strings (abfd);
- if (info->keep_memory)
- copy = FALSE;
- else
- copy = TRUE;
-
- if (aout_backend_info (abfd)->add_dynamic_symbols != NULL)
- {
- if (! ((*aout_backend_info (abfd)->add_dynamic_symbols)
- (abfd, info, &syms, &sym_count, &strings)))
- return FALSE;
- }
-
- /* We keep a list of the linker hash table entries that correspond
- to particular symbols. We could just look them up in the hash
- table, but keeping the list is more efficient. Perhaps this
- should be conditional on info->keep_memory. */
- amt = sym_count * sizeof (struct aout_link_hash_entry *);
- sym_hash = (struct aout_link_hash_entry **) bfd_alloc (abfd, amt);
- if (sym_hash == NULL && sym_count != 0)
- return FALSE;
- obj_aout_sym_hashes (abfd) = sym_hash;
-
- add_one_symbol = aout_backend_info (abfd)->add_one_symbol;
- if (add_one_symbol == NULL)
- add_one_symbol = _bfd_generic_link_add_one_symbol;
-
- p = syms;
- pend = p + sym_count;
- for (; p < pend; p++, sym_hash++)
- {
- int type;
- const char *name;
- bfd_vma value;
- asection *section;
- flagword flags;
- const char *string;
-
- *sym_hash = NULL;
-
- type = H_GET_8 (abfd, p->e_type);
-
- /* Ignore debugging symbols. */
- if ((type & N_STAB) != 0)
- continue;
-
- name = strings + GET_WORD (abfd, p->e_strx);
- value = GET_WORD (abfd, p->e_value);
- flags = BSF_GLOBAL;
- string = NULL;
- switch (type)
- {
- default:
- abort ();
-
- case N_UNDF:
- case N_ABS:
- case N_TEXT:
- case N_DATA:
- case N_BSS:
- case N_FN_SEQ:
- case N_COMM:
- case N_SETV:
- case N_FN:
- /* Ignore symbols that are not externally visible. */
- continue;
- case N_INDR:
- /* Ignore local indirect symbol. */
- ++p;
- ++sym_hash;
- continue;
-
- case N_UNDF | N_EXT:
- if (value == 0)
- {
- section = bfd_und_section_ptr;
- flags = 0;
+ section = bfd_und_section_ptr;
+ flags = 0;
}
else
section = bfd_com_section_ptr;
return TRUE;
}
-\f
-/* A hash table used for header files with N_BINCL entries. */
-struct aout_link_includes_table
+/* Free up the internal symbols read from an a.out file. */
+
+static bfd_boolean
+aout_link_free_symbols (bfd *abfd)
{
- struct bfd_hash_table root;
-};
+ if (obj_aout_external_syms (abfd) != NULL)
+ {
+#ifdef USE_MMAP
+ bfd_free_window (&obj_aout_sym_window (abfd));
+#else
+ free ((void *) obj_aout_external_syms (abfd));
+#endif
+ obj_aout_external_syms (abfd) = NULL;
+ }
+ if (obj_aout_external_strings (abfd) != NULL)
+ {
+#ifdef USE_MMAP
+ bfd_free_window (&obj_aout_string_window (abfd));
+#else
+ free ((void *) obj_aout_external_strings (abfd));
+#endif
+ obj_aout_external_strings (abfd) = NULL;
+ }
+ return TRUE;
+}
-/* A linked list of totals that we have found for a particular header
- file. */
+/* Add symbols from an a.out object file. */
-struct aout_link_includes_totals
+static bfd_boolean
+aout_link_add_object_symbols (bfd *abfd, struct bfd_link_info *info)
{
- struct aout_link_includes_totals *next;
- bfd_vma total;
-};
+ if (! aout_get_external_symbols (abfd))
+ return FALSE;
+ if (! aout_link_add_symbols (abfd, info))
+ return FALSE;
+ if (! info->keep_memory)
+ {
+ if (! aout_link_free_symbols (abfd))
+ return FALSE;
+ }
+ return TRUE;
+}
-/* An entry in the header file hash table. */
+/* Look through the internal symbols to see if this object file should
+ be included in the link. We should include this object file if it
+ defines any symbols which are currently undefined. If this object
+ file defines a common symbol, then we may adjust the size of the
+ known symbol but we do not include the object file in the link
+ (unless there is some other reason to include it). */
-struct aout_link_includes_entry
+static bfd_boolean
+aout_link_check_ar_symbols (bfd *abfd,
+ struct bfd_link_info *info,
+ bfd_boolean *pneeded)
{
- struct bfd_hash_entry root;
- /* List of totals we have found for this file. */
- struct aout_link_includes_totals *totals;
-};
-
-/* Look up an entry in an the header file hash table. */
+ struct external_nlist *p;
+ struct external_nlist *pend;
+ char *strings;
-#define aout_link_includes_lookup(table, string, create, copy) \
- ((struct aout_link_includes_entry *) \
- bfd_hash_lookup (&(table)->root, (string), (create), (copy)))
+ *pneeded = FALSE;
-/* During the final link step we need to pass around a bunch of
- information, so we do it in an instance of this structure. */
+ /* Look through all the symbols. */
+ p = obj_aout_external_syms (abfd);
+ pend = p + obj_aout_external_sym_count (abfd);
+ strings = obj_aout_external_strings (abfd);
+ for (; p < pend; p++)
+ {
+ int type = H_GET_8 (abfd, p->e_type);
+ const char *name;
+ struct bfd_link_hash_entry *h;
-struct aout_final_link_info
-{
- /* General link information. */
- struct bfd_link_info *info;
- /* Output bfd. */
+ /* Ignore symbols that are not externally visible. This is an
+ optimization only, as we check the type more thoroughly
+ below. */
+ if (((type & N_EXT) == 0
+ || (type & N_STAB) != 0
+ || type == N_FN)
+ && type != N_WEAKA
+ && type != N_WEAKT
+ && type != N_WEAKD
+ && type != N_WEAKB)
+ {
+ if (type == N_WARNING
+ || type == N_INDR)
+ ++p;
+ continue;
+ }
+
+ name = strings + GET_WORD (abfd, p->e_strx);
+ h = bfd_link_hash_lookup (info->hash, name, FALSE, FALSE, TRUE);
+
+ /* We are only interested in symbols that are currently
+ undefined or common. */
+ if (h == NULL
+ || (h->type != bfd_link_hash_undefined
+ && h->type != bfd_link_hash_common))
+ {
+ if (type == (N_INDR | N_EXT))
+ ++p;
+ continue;
+ }
+
+ if (type == (N_TEXT | N_EXT)
+ || type == (N_DATA | N_EXT)
+ || type == (N_BSS | N_EXT)
+ || type == (N_ABS | N_EXT)
+ || type == (N_INDR | N_EXT))
+ {
+ /* This object file defines this symbol. We must link it
+ in. This is true regardless of whether the current
+ definition of the symbol is undefined or common.
+
+ If the current definition is common, we have a case in
+ which we have already seen an object file including:
+ int a;
+ and this object file from the archive includes:
+ int a = 5;
+ In such a case, whether to include this object is target
+ dependant for backward compatibility.
+
+ FIXME: The SunOS 4.1.3 linker will pull in the archive
+ element if the symbol is defined in the .data section,
+ but not if it is defined in the .text section. That
+ seems a bit crazy to me, and it has not been implemented
+ yet. However, it might be correct. */
+ if (h->type == bfd_link_hash_common)
+ {
+ int skip = 0;
+
+ switch (info->common_skip_ar_aymbols)
+ {
+ case bfd_link_common_skip_text:
+ skip = (type == (N_TEXT | N_EXT));
+ break;
+ case bfd_link_common_skip_data:
+ skip = (type == (N_DATA | N_EXT));
+ break;
+ default:
+ case bfd_link_common_skip_all:
+ skip = 1;
+ break;
+ }
+
+ if (skip)
+ continue;
+ }
+
+ if (! (*info->callbacks->add_archive_element) (info, abfd, name))
+ return FALSE;
+ *pneeded = TRUE;
+ return TRUE;
+ }
+
+ if (type == (N_UNDF | N_EXT))
+ {
+ bfd_vma value;
+
+ value = GET_WORD (abfd, p->e_value);
+ if (value != 0)
+ {
+ /* This symbol is common in the object from the archive
+ file. */
+ if (h->type == bfd_link_hash_undefined)
+ {
+ bfd *symbfd;
+ unsigned int power;
+
+ symbfd = h->u.undef.abfd;
+ if (symbfd == NULL)
+ {
+ /* This symbol was created as undefined from
+ outside BFD. We assume that we should link
+ in the object file. This is done for the -u
+ option in the linker. */
+ if (! (*info->callbacks->add_archive_element) (info,
+ abfd,
+ name))
+ return FALSE;
+ *pneeded = TRUE;
+ return TRUE;
+ }
+ /* Turn the current link symbol into a common
+ symbol. It is already on the undefs list. */
+ h->type = bfd_link_hash_common;
+ h->u.c.p = bfd_hash_allocate (&info->hash->table,
+ sizeof (struct bfd_link_hash_common_entry));
+ if (h->u.c.p == NULL)
+ return FALSE;
+
+ h->u.c.size = value;
+
+ /* FIXME: This isn't quite right. The maximum
+ alignment of a common symbol should be set by the
+ architecture of the output file, not of the input
+ file. */
+ power = bfd_log2 (value);
+ if (power > bfd_get_arch_info (abfd)->section_align_power)
+ power = bfd_get_arch_info (abfd)->section_align_power;
+ h->u.c.p->alignment_power = power;
+
+ h->u.c.p->section = bfd_make_section_old_way (symbfd,
+ "COMMON");
+ }
+ else
+ {
+ /* Adjust the size of the common symbol if
+ necessary. */
+ if (value > h->u.c.size)
+ h->u.c.size = value;
+ }
+ }
+ }
+
+ if (type == N_WEAKA
+ || type == N_WEAKT
+ || type == N_WEAKD
+ || type == N_WEAKB)
+ {
+ /* This symbol is weak but defined. We must pull it in if
+ the current link symbol is undefined, but we don't want
+ it if the current link symbol is common. */
+ if (h->type == bfd_link_hash_undefined)
+ {
+ if (! (*info->callbacks->add_archive_element) (info, abfd, name))
+ return FALSE;
+ *pneeded = TRUE;
+ return TRUE;
+ }
+ }
+ }
+
+ /* We do not need this object file. */
+ return TRUE;
+}
+/* Check a single archive element to see if we need to include it in
+ the link. *PNEEDED is set according to whether this element is
+ needed in the link or not. This is called from
+ _bfd_generic_link_add_archive_symbols. */
+
+static bfd_boolean
+aout_link_check_archive_element (bfd *abfd,
+ struct bfd_link_info *info,
+ bfd_boolean *pneeded)
+{
+ if (! aout_get_external_symbols (abfd))
+ return FALSE;
+
+ if (! aout_link_check_ar_symbols (abfd, info, pneeded))
+ return FALSE;
+
+ if (*pneeded)
+ {
+ if (! aout_link_add_symbols (abfd, info))
+ return FALSE;
+ }
+
+ if (! info->keep_memory || ! *pneeded)
+ {
+ if (! aout_link_free_symbols (abfd))
+ return FALSE;
+ }
+
+ return TRUE;
+}
+
+/* Given an a.out BFD, add symbols to the global hash table as
+ appropriate. */
+
+bfd_boolean
+NAME (aout, link_add_symbols) (bfd *abfd, struct bfd_link_info *info)
+{
+ switch (bfd_get_format (abfd))
+ {
+ case bfd_object:
+ return aout_link_add_object_symbols (abfd, info);
+ case bfd_archive:
+ return _bfd_generic_link_add_archive_symbols
+ (abfd, info, aout_link_check_archive_element);
+ default:
+ bfd_set_error (bfd_error_wrong_format);
+ return FALSE;
+ }
+}
+\f
+/* A hash table used for header files with N_BINCL entries. */
+
+struct aout_link_includes_table
+{
+ struct bfd_hash_table root;
+};
+
+/* A linked list of totals that we have found for a particular header
+ file. */
+
+struct aout_link_includes_totals
+{
+ struct aout_link_includes_totals *next;
+ bfd_vma total;
+};
+
+/* An entry in the header file hash table. */
+
+struct aout_link_includes_entry
+{
+ struct bfd_hash_entry root;
+ /* List of totals we have found for this file. */
+ struct aout_link_includes_totals *totals;
+};
+
+/* Look up an entry in an the header file hash table. */
+
+#define aout_link_includes_lookup(table, string, create, copy) \
+ ((struct aout_link_includes_entry *) \
+ bfd_hash_lookup (&(table)->root, (string), (create), (copy)))
+
+/* During the final link step we need to pass around a bunch of
+ information, so we do it in an instance of this structure. */
+
+struct aout_final_link_info
+{
+ /* General link information. */
+ struct bfd_link_info *info;
+ /* Output bfd. */
bfd *output_bfd;
/* Reloc file positions. */
file_ptr treloff, dreloff;
/* A buffer large enough to hold the contents of any section. */
bfd_byte *contents;
/* A buffer large enough to hold the relocs of any section. */
- PTR relocs;
+ void * relocs;
/* A buffer large enough to hold the symbol map of any input BFD. */
int *symbol_map;
/* A buffer large enough to hold output symbols of any input BFD. */
struct external_nlist *output_syms;
};
-static struct bfd_hash_entry *aout_link_includes_newfunc
- PARAMS ((struct bfd_hash_entry *, struct bfd_hash_table *, const char *));
-static bfd_boolean aout_link_input_bfd
- PARAMS ((struct aout_final_link_info *, bfd *input_bfd));
-static bfd_boolean aout_link_write_symbols
- PARAMS ((struct aout_final_link_info *, bfd *input_bfd));
-static bfd_boolean aout_link_write_other_symbol
- PARAMS ((struct aout_link_hash_entry *, PTR));
-static bfd_boolean aout_link_input_section
- PARAMS ((struct aout_final_link_info *, bfd *input_bfd,
- asection *input_section, file_ptr *reloff_ptr,
- bfd_size_type rel_size));
-static bfd_boolean aout_link_input_section_std
- PARAMS ((struct aout_final_link_info *, bfd *input_bfd,
- asection *input_section, struct reloc_std_external *,
- bfd_size_type rel_size, bfd_byte *contents));
-static bfd_boolean aout_link_input_section_ext
- PARAMS ((struct aout_final_link_info *, bfd *input_bfd,
- asection *input_section, struct reloc_ext_external *,
- bfd_size_type rel_size, bfd_byte *contents));
-static INLINE asection *aout_reloc_index_to_section
- PARAMS ((bfd *, int));
-static bfd_boolean aout_link_reloc_link_order
- PARAMS ((struct aout_final_link_info *, asection *,
- struct bfd_link_order *));
-
/* The function to create a new entry in the header file hash table. */
static struct bfd_hash_entry *
-aout_link_includes_newfunc (entry, table, string)
- struct bfd_hash_entry *entry;
- struct bfd_hash_table *table;
- const char *string;
+aout_link_includes_newfunc (struct bfd_hash_entry *entry,
+ struct bfd_hash_table *table,
+ const char *string)
{
struct aout_link_includes_entry *ret =
(struct aout_link_includes_entry *) entry;
/* Allocate the structure if it has not already been allocated by a
subclass. */
- if (ret == (struct aout_link_includes_entry *) NULL)
- ret = ((struct aout_link_includes_entry *)
- bfd_hash_allocate (table,
- sizeof (struct aout_link_includes_entry)));
- if (ret == (struct aout_link_includes_entry *) NULL)
- return (struct bfd_hash_entry *) ret;
+ if (ret == NULL)
+ ret = bfd_hash_allocate (table, sizeof (* ret));
+ if (ret == NULL)
+ return NULL;
/* Call the allocation method of the superclass. */
ret = ((struct aout_link_includes_entry *)
return (struct bfd_hash_entry *) ret;
}
-/* Do the final link step. This is called on the output BFD. The
- INFO structure should point to a list of BFDs linked through the
- link_next field which can be used to find each BFD which takes part
- in the output. Also, each section in ABFD should point to a list
- of bfd_link_order structures which list all the input sections for
- the output section. */
+/* Write out a symbol that was not associated with an a.out input
+ object. */
-bfd_boolean
-NAME(aout,final_link) (abfd, info, callback)
- bfd *abfd;
- struct bfd_link_info *info;
- void (*callback) PARAMS ((bfd *, file_ptr *, file_ptr *, file_ptr *));
+static bfd_boolean
+aout_link_write_other_symbol (struct aout_link_hash_entry *h, void * data)
{
- struct aout_final_link_info aout_info;
- bfd_boolean includes_hash_initialized = FALSE;
- register bfd *sub;
- bfd_size_type trsize, drsize;
- bfd_size_type max_contents_size;
- bfd_size_type max_relocs_size;
- bfd_size_type max_sym_count;
- bfd_size_type text_size;
- file_ptr text_end;
- register struct bfd_link_order *p;
- asection *o;
- bfd_boolean have_link_order_relocs;
-
- if (info->shared)
- abfd->flags |= DYNAMIC;
+ struct aout_final_link_info *finfo = (struct aout_final_link_info *) data;
+ bfd *output_bfd;
+ int type;
+ bfd_vma val;
+ struct external_nlist outsym;
+ bfd_size_type indx;
+ bfd_size_type amt;
- aout_info.info = info;
- aout_info.output_bfd = abfd;
- aout_info.contents = NULL;
- aout_info.relocs = NULL;
- aout_info.symbol_map = NULL;
- aout_info.output_syms = NULL;
+ if (h->root.type == bfd_link_hash_warning)
+ {
+ h = (struct aout_link_hash_entry *) h->root.u.i.link;
+ if (h->root.type == bfd_link_hash_new)
+ return TRUE;
+ }
- if (! bfd_hash_table_init_n (&aout_info.includes.root,
- aout_link_includes_newfunc,
- 251))
- goto error_return;
- includes_hash_initialized = TRUE;
+ output_bfd = finfo->output_bfd;
- /* Figure out the largest section size. Also, if generating
- relocatable output, count the relocs. */
- trsize = 0;
- drsize = 0;
- max_contents_size = 0;
- max_relocs_size = 0;
- max_sym_count = 0;
- for (sub = info->input_bfds; sub != NULL; sub = sub->link_next)
+ if (aout_backend_info (output_bfd)->write_dynamic_symbol != NULL)
{
- bfd_size_type sz;
-
- if (info->relocatable)
+ if (! ((*aout_backend_info (output_bfd)->write_dynamic_symbol)
+ (output_bfd, finfo->info, h)))
{
- if (bfd_get_flavour (sub) == bfd_target_aout_flavour)
- {
- trsize += exec_hdr (sub)->a_trsize;
- drsize += exec_hdr (sub)->a_drsize;
- }
- else
- {
- /* FIXME: We need to identify the .text and .data sections
- and call get_reloc_upper_bound and canonicalize_reloc to
- work out the number of relocs needed, and then multiply
- by the reloc size. */
- (*_bfd_error_handler)
- (_("%s: relocatable link from %s to %s not supported"),
- bfd_get_filename (abfd),
- sub->xvec->name, abfd->xvec->name);
- bfd_set_error (bfd_error_invalid_operation);
- goto error_return;
- }
+ /* FIXME: No way to handle errors. */
+ abort ();
}
+ }
- if (bfd_get_flavour (sub) == bfd_target_aout_flavour)
- {
- sz = obj_textsec (sub)->size;
- if (sz > max_contents_size)
- max_contents_size = sz;
- sz = obj_datasec (sub)->size;
- if (sz > max_contents_size)
- max_contents_size = sz;
+ if (h->written)
+ return TRUE;
- sz = exec_hdr (sub)->a_trsize;
- if (sz > max_relocs_size)
- max_relocs_size = sz;
- sz = exec_hdr (sub)->a_drsize;
- if (sz > max_relocs_size)
- max_relocs_size = sz;
+ h->written = TRUE;
- sz = obj_aout_external_sym_count (sub);
- if (sz > max_sym_count)
- max_sym_count = sz;
- }
- }
+ /* An indx of -2 means the symbol must be written. */
+ if (h->indx != -2
+ && (finfo->info->strip == strip_all
+ || (finfo->info->strip == strip_some
+ && bfd_hash_lookup (finfo->info->keep_hash, h->root.root.string,
+ FALSE, FALSE) == NULL)))
+ return TRUE;
- if (info->relocatable)
+ switch (h->root.type)
{
- if (obj_textsec (abfd) != (asection *) NULL)
- trsize += (_bfd_count_link_order_relocs (obj_textsec (abfd)
- ->link_order_head)
- * obj_reloc_entry_size (abfd));
- if (obj_datasec (abfd) != (asection *) NULL)
- drsize += (_bfd_count_link_order_relocs (obj_datasec (abfd)
- ->link_order_head)
- * obj_reloc_entry_size (abfd));
- }
+ default:
+ case bfd_link_hash_warning:
+ abort ();
+ /* Avoid variable not initialized warnings. */
+ return TRUE;
+ case bfd_link_hash_new:
+ /* This can happen for set symbols when sets are not being
+ built. */
+ return TRUE;
+ case bfd_link_hash_undefined:
+ type = N_UNDF | N_EXT;
+ val = 0;
+ break;
+ case bfd_link_hash_defined:
+ case bfd_link_hash_defweak:
+ {
+ asection *sec;
- exec_hdr (abfd)->a_trsize = trsize;
- exec_hdr (abfd)->a_drsize = drsize;
+ sec = h->root.u.def.section->output_section;
+ BFD_ASSERT (bfd_is_abs_section (sec)
+ || sec->owner == output_bfd);
+ if (sec == obj_textsec (output_bfd))
+ type = h->root.type == bfd_link_hash_defined ? N_TEXT : N_WEAKT;
+ else if (sec == obj_datasec (output_bfd))
+ type = h->root.type == bfd_link_hash_defined ? N_DATA : N_WEAKD;
+ else if (sec == obj_bsssec (output_bfd))
+ type = h->root.type == bfd_link_hash_defined ? N_BSS : N_WEAKB;
+ else
+ type = h->root.type == bfd_link_hash_defined ? N_ABS : N_WEAKA;
+ type |= N_EXT;
+ val = (h->root.u.def.value
+ + sec->vma
+ + h->root.u.def.section->output_offset);
+ }
+ break;
+ case bfd_link_hash_common:
+ type = N_UNDF | N_EXT;
+ val = h->root.u.c.size;
+ break;
+ case bfd_link_hash_undefweak:
+ type = N_WEAKU;
+ val = 0;
+ case bfd_link_hash_indirect:
+ /* We ignore these symbols, since the indirected symbol is
+ already in the hash table. */
+ return TRUE;
+ }
- exec_hdr (abfd)->a_entry = bfd_get_start_address (abfd);
+ H_PUT_8 (output_bfd, type, outsym.e_type);
+ H_PUT_8 (output_bfd, 0, outsym.e_other);
+ H_PUT_16 (output_bfd, 0, outsym.e_desc);
+ indx = add_to_stringtab (output_bfd, finfo->strtab, h->root.root.string,
+ FALSE);
+ if (indx == - (bfd_size_type) 1)
+ /* FIXME: No way to handle errors. */
+ abort ();
- /* Adjust the section sizes and vmas according to the magic number.
- This sets a_text, a_data and a_bss in the exec_hdr and sets the
- filepos for each section. */
- if (! NAME(aout,adjust_sizes_and_vmas) (abfd, &text_size, &text_end))
- goto error_return;
+ PUT_WORD (output_bfd, indx, outsym.e_strx);
+ PUT_WORD (output_bfd, val, outsym.e_value);
- /* The relocation and symbol file positions differ among a.out
- targets. We are passed a callback routine from the backend
- specific code to handle this.
- FIXME: At this point we do not know how much space the symbol
- table will require. This will not work for any (nonstandard)
- a.out target that needs to know the symbol table size before it
- can compute the relocation file positions. This may or may not
- be the case for the hp300hpux target, for example. */
- (*callback) (abfd, &aout_info.treloff, &aout_info.dreloff,
- &aout_info.symoff);
- obj_textsec (abfd)->rel_filepos = aout_info.treloff;
- obj_datasec (abfd)->rel_filepos = aout_info.dreloff;
- obj_sym_filepos (abfd) = aout_info.symoff;
+ amt = EXTERNAL_NLIST_SIZE;
+ if (bfd_seek (output_bfd, finfo->symoff, SEEK_SET) != 0
+ || bfd_bwrite ((void *) &outsym, amt, output_bfd) != amt)
+ /* FIXME: No way to handle errors. */
+ abort ();
- /* We keep a count of the symbols as we output them. */
- obj_aout_external_sym_count (abfd) = 0;
+ finfo->symoff += EXTERNAL_NLIST_SIZE;
+ h->indx = obj_aout_external_sym_count (output_bfd);
+ ++obj_aout_external_sym_count (output_bfd);
- /* We accumulate the string table as we write out the symbols. */
- aout_info.strtab = _bfd_stringtab_init ();
- if (aout_info.strtab == NULL)
- goto error_return;
+ return TRUE;
+}
- /* Allocate buffers to hold section contents and relocs. */
- aout_info.contents = (bfd_byte *) bfd_malloc (max_contents_size);
- aout_info.relocs = (PTR) bfd_malloc (max_relocs_size);
- aout_info.symbol_map = (int *) bfd_malloc (max_sym_count * sizeof (int *));
- aout_info.output_syms = ((struct external_nlist *)
- bfd_malloc ((max_sym_count + 1)
- * sizeof (struct external_nlist)));
- if ((aout_info.contents == NULL && max_contents_size != 0)
- || (aout_info.relocs == NULL && max_relocs_size != 0)
- || (aout_info.symbol_map == NULL && max_sym_count != 0)
- || aout_info.output_syms == NULL)
- goto error_return;
+/* Handle a link order which is supposed to generate a reloc. */
- /* If we have a symbol named __DYNAMIC, force it out now. This is
- required by SunOS. Doing this here rather than in sunos.c is a
- hack, but it's easier than exporting everything which would be
- needed. */
- {
- struct aout_link_hash_entry *h;
+static bfd_boolean
+aout_link_reloc_link_order (struct aout_final_link_info *finfo,
+ asection *o,
+ struct bfd_link_order *p)
+{
+ struct bfd_link_order_reloc *pr;
+ int r_index;
+ int r_extern;
+ reloc_howto_type *howto;
+ file_ptr *reloff_ptr = NULL;
+ struct reloc_std_external srel;
+ struct reloc_ext_external erel;
+ void * rel_ptr;
+ bfd_size_type amt;
- h = aout_link_hash_lookup (aout_hash_table (info), "__DYNAMIC",
- FALSE, FALSE, FALSE);
- if (h != NULL)
- aout_link_write_other_symbol (h, &aout_info);
- }
+ pr = p->u.reloc.p;
- /* The most time efficient way to do the link would be to read all
- the input object files into memory and then sort out the
- information into the output file. Unfortunately, that will
- probably use too much memory. Another method would be to step
- through everything that composes the text section and write it
- out, and then everything that composes the data section and write
- it out, and then write out the relocs, and then write out the
- symbols. Unfortunately, that requires reading stuff from each
- input file several times, and we will not be able to keep all the
- input files open simultaneously, and reopening them will be slow.
+ if (p->type == bfd_section_reloc_link_order)
+ {
+ r_extern = 0;
+ if (bfd_is_abs_section (pr->u.section))
+ r_index = N_ABS | N_EXT;
+ else
+ {
+ BFD_ASSERT (pr->u.section->owner == finfo->output_bfd);
+ r_index = pr->u.section->target_index;
+ }
+ }
+ else
+ {
+ struct aout_link_hash_entry *h;
- What we do is basically process one input file at a time. We do
- everything we need to do with an input file once--copy over the
- section contents, handle the relocation information, and write
- out the symbols--and then we throw away the information we read
- from it. This approach requires a lot of lseeks of the output
- file, which is unfortunate but still faster than reopening a lot
- of files.
-
- We use the output_has_begun field of the input BFDs to see
- whether we have already handled it. */
- for (sub = info->input_bfds; sub != (bfd *) NULL; sub = sub->link_next)
- sub->output_has_begun = FALSE;
+ BFD_ASSERT (p->type == bfd_symbol_reloc_link_order);
+ r_extern = 1;
+ h = ((struct aout_link_hash_entry *)
+ bfd_wrapped_link_hash_lookup (finfo->output_bfd, finfo->info,
+ pr->u.name, FALSE, FALSE, TRUE));
+ if (h != NULL
+ && h->indx >= 0)
+ r_index = h->indx;
+ else if (h != NULL)
+ {
+ /* We decided to strip this symbol, but it turns out that we
+ can't. Note that we lose the other and desc information
+ here. I don't think that will ever matter for a global
+ symbol. */
+ h->indx = -2;
+ h->written = FALSE;
+ if (! aout_link_write_other_symbol (h, (void *) finfo))
+ return FALSE;
+ r_index = h->indx;
+ }
+ else
+ {
+ if (! ((*finfo->info->callbacks->unattached_reloc)
+ (finfo->info, pr->u.name, NULL, NULL, (bfd_vma) 0)))
+ return FALSE;
+ r_index = 0;
+ }
+ }
- /* Mark all sections which are to be included in the link. This
- will normally be every section. We need to do this so that we
- can identify any sections which the linker has decided to not
- include. */
- for (o = abfd->sections; o != NULL; o = o->next)
+ howto = bfd_reloc_type_lookup (finfo->output_bfd, pr->reloc);
+ if (howto == 0)
{
- for (p = o->link_order_head; p != NULL; p = p->next)
- if (p->type == bfd_indirect_link_order)
- p->u.indirect.section->linker_mark = TRUE;
+ bfd_set_error (bfd_error_bad_value);
+ return FALSE;
}
- have_link_order_relocs = FALSE;
- for (o = abfd->sections; o != (asection *) NULL; o = o->next)
+ if (o == obj_textsec (finfo->output_bfd))
+ reloff_ptr = &finfo->treloff;
+ else if (o == obj_datasec (finfo->output_bfd))
+ reloff_ptr = &finfo->dreloff;
+ else
+ abort ();
+
+ if (obj_reloc_entry_size (finfo->output_bfd) == RELOC_STD_SIZE)
{
- for (p = o->link_order_head;
- p != (struct bfd_link_order *) NULL;
- p = p->next)
- {
- if (p->type == bfd_indirect_link_order
- && (bfd_get_flavour (p->u.indirect.section->owner)
- == bfd_target_aout_flavour))
- {
- bfd *input_bfd;
+#ifdef MY_put_reloc
+ MY_put_reloc (finfo->output_bfd, r_extern, r_index, p->offset, howto,
+ &srel);
+#else
+ {
+ int r_pcrel;
+ int r_baserel;
+ int r_jmptable;
+ int r_relative;
+ int r_length;
- input_bfd = p->u.indirect.section->owner;
- if (! input_bfd->output_has_begun)
- {
- if (! aout_link_input_bfd (&aout_info, input_bfd))
- goto error_return;
- input_bfd->output_has_begun = TRUE;
- }
- }
- else if (p->type == bfd_section_reloc_link_order
- || p->type == bfd_symbol_reloc_link_order)
- {
- /* These are handled below. */
- have_link_order_relocs = TRUE;
- }
- else
- {
- if (! _bfd_default_link_order (abfd, info, o, p))
- goto error_return;
- }
- }
- }
+ r_pcrel = (int) howto->pc_relative;
+ r_baserel = (howto->type & 8) != 0;
+ r_jmptable = (howto->type & 16) != 0;
+ r_relative = (howto->type & 32) != 0;
+ r_length = howto->size;
- /* Write out any symbols that we have not already written out. */
- aout_link_hash_traverse (aout_hash_table (info),
- aout_link_write_other_symbol,
- (PTR) &aout_info);
+ PUT_WORD (finfo->output_bfd, p->offset, srel.r_address);
+ if (bfd_header_big_endian (finfo->output_bfd))
+ {
+ srel.r_index[0] = r_index >> 16;
+ srel.r_index[1] = r_index >> 8;
+ srel.r_index[2] = r_index;
+ srel.r_type[0] =
+ ((r_extern ? RELOC_STD_BITS_EXTERN_BIG : 0)
+ | (r_pcrel ? RELOC_STD_BITS_PCREL_BIG : 0)
+ | (r_baserel ? RELOC_STD_BITS_BASEREL_BIG : 0)
+ | (r_jmptable ? RELOC_STD_BITS_JMPTABLE_BIG : 0)
+ | (r_relative ? RELOC_STD_BITS_RELATIVE_BIG : 0)
+ | (r_length << RELOC_STD_BITS_LENGTH_SH_BIG));
+ }
+ else
+ {
+ srel.r_index[2] = r_index >> 16;
+ srel.r_index[1] = r_index >> 8;
+ srel.r_index[0] = r_index;
+ srel.r_type[0] =
+ ((r_extern ? RELOC_STD_BITS_EXTERN_LITTLE : 0)
+ | (r_pcrel ? RELOC_STD_BITS_PCREL_LITTLE : 0)
+ | (r_baserel ? RELOC_STD_BITS_BASEREL_LITTLE : 0)
+ | (r_jmptable ? RELOC_STD_BITS_JMPTABLE_LITTLE : 0)
+ | (r_relative ? RELOC_STD_BITS_RELATIVE_LITTLE : 0)
+ | (r_length << RELOC_STD_BITS_LENGTH_SH_LITTLE));
+ }
+ }
+#endif
+ rel_ptr = (void *) &srel;
- /* Now handle any relocs we were asked to create by the linker.
- These did not come from any input file. We must do these after
- we have written out all the symbols, so that we know the symbol
- indices to use. */
- if (have_link_order_relocs)
- {
- for (o = abfd->sections; o != (asection *) NULL; o = o->next)
+ /* We have to write the addend into the object file, since
+ standard a.out relocs are in place. It would be more
+ reliable if we had the current contents of the file here,
+ rather than assuming zeroes, but we can't read the file since
+ it was opened using bfd_openw. */
+ if (pr->addend != 0)
{
- for (p = o->link_order_head;
- p != (struct bfd_link_order *) NULL;
- p = p->next)
+ bfd_size_type size;
+ bfd_reloc_status_type r;
+ bfd_byte *buf;
+ bfd_boolean ok;
+
+ size = bfd_get_reloc_size (howto);
+ buf = bfd_zmalloc (size);
+ if (buf == NULL)
+ return FALSE;
+ r = MY_relocate_contents (howto, finfo->output_bfd,
+ (bfd_vma) pr->addend, buf);
+ switch (r)
{
- if (p->type == bfd_section_reloc_link_order
- || p->type == bfd_symbol_reloc_link_order)
+ case bfd_reloc_ok:
+ break;
+ default:
+ case bfd_reloc_outofrange:
+ abort ();
+ case bfd_reloc_overflow:
+ if (! ((*finfo->info->callbacks->reloc_overflow)
+ (finfo->info, NULL,
+ (p->type == bfd_section_reloc_link_order
+ ? bfd_section_name (finfo->output_bfd,
+ pr->u.section)
+ : pr->u.name),
+ howto->name, pr->addend, NULL, NULL, (bfd_vma) 0)))
{
- if (! aout_link_reloc_link_order (&aout_info, o, p))
- goto error_return;
+ free (buf);
+ return FALSE;
}
+ break;
}
+ ok = bfd_set_section_contents (finfo->output_bfd, o, (void *) buf,
+ (file_ptr) p->offset, size);
+ free (buf);
+ if (! ok)
+ return FALSE;
}
}
-
- if (aout_info.contents != NULL)
- {
- free (aout_info.contents);
- aout_info.contents = NULL;
- }
- if (aout_info.relocs != NULL)
- {
- free (aout_info.relocs);
- aout_info.relocs = NULL;
- }
- if (aout_info.symbol_map != NULL)
- {
- free (aout_info.symbol_map);
- aout_info.symbol_map = NULL;
- }
- if (aout_info.output_syms != NULL)
- {
- free (aout_info.output_syms);
- aout_info.output_syms = NULL;
- }
- if (includes_hash_initialized)
+ else
{
- bfd_hash_table_free (&aout_info.includes.root);
- includes_hash_initialized = FALSE;
- }
+#ifdef MY_put_ext_reloc
+ MY_put_ext_reloc (finfo->output_bfd, r_extern, r_index, p->offset,
+ howto, &erel, pr->addend);
+#else
+ PUT_WORD (finfo->output_bfd, p->offset, erel.r_address);
- /* Finish up any dynamic linking we may be doing. */
- if (aout_backend_info (abfd)->finish_dynamic_link != NULL)
- {
- if (! (*aout_backend_info (abfd)->finish_dynamic_link) (abfd, info))
- goto error_return;
- }
+ if (bfd_header_big_endian (finfo->output_bfd))
+ {
+ erel.r_index[0] = r_index >> 16;
+ erel.r_index[1] = r_index >> 8;
+ erel.r_index[2] = r_index;
+ erel.r_type[0] =
+ ((r_extern ? RELOC_EXT_BITS_EXTERN_BIG : 0)
+ | (howto->type << RELOC_EXT_BITS_TYPE_SH_BIG));
+ }
+ else
+ {
+ erel.r_index[2] = r_index >> 16;
+ erel.r_index[1] = r_index >> 8;
+ erel.r_index[0] = r_index;
+ erel.r_type[0] =
+ (r_extern ? RELOC_EXT_BITS_EXTERN_LITTLE : 0)
+ | (howto->type << RELOC_EXT_BITS_TYPE_SH_LITTLE);
+ }
- /* Update the header information. */
- abfd->symcount = obj_aout_external_sym_count (abfd);
- exec_hdr (abfd)->a_syms = abfd->symcount * EXTERNAL_NLIST_SIZE;
- obj_str_filepos (abfd) = obj_sym_filepos (abfd) + exec_hdr (abfd)->a_syms;
- obj_textsec (abfd)->reloc_count =
- exec_hdr (abfd)->a_trsize / obj_reloc_entry_size (abfd);
- obj_datasec (abfd)->reloc_count =
- exec_hdr (abfd)->a_drsize / obj_reloc_entry_size (abfd);
+ PUT_WORD (finfo->output_bfd, (bfd_vma) pr->addend, erel.r_addend);
+#endif /* MY_put_ext_reloc */
- /* Write out the string table, unless there are no symbols. */
- if (abfd->symcount > 0)
- {
- if (bfd_seek (abfd, obj_str_filepos (abfd), SEEK_SET) != 0
- || ! emit_stringtab (abfd, aout_info.strtab))
- goto error_return;
+ rel_ptr = (void *) &erel;
}
- else if (obj_textsec (abfd)->reloc_count == 0
- && obj_datasec (abfd)->reloc_count == 0)
- {
- bfd_byte b;
- file_ptr pos;
- b = 0;
- pos = obj_datasec (abfd)->filepos + exec_hdr (abfd)->a_data - 1;
- if (bfd_seek (abfd, pos, SEEK_SET) != 0
- || bfd_bwrite (&b, (bfd_size_type) 1, abfd) != 1)
- goto error_return;
- }
+ amt = obj_reloc_entry_size (finfo->output_bfd);
+ if (bfd_seek (finfo->output_bfd, *reloff_ptr, SEEK_SET) != 0
+ || bfd_bwrite (rel_ptr, amt, finfo->output_bfd) != amt)
+ return FALSE;
- return TRUE;
+ *reloff_ptr += obj_reloc_entry_size (finfo->output_bfd);
- error_return:
- if (aout_info.contents != NULL)
- free (aout_info.contents);
- if (aout_info.relocs != NULL)
- free (aout_info.relocs);
- if (aout_info.symbol_map != NULL)
- free (aout_info.symbol_map);
- if (aout_info.output_syms != NULL)
- free (aout_info.output_syms);
- if (includes_hash_initialized)
- bfd_hash_table_free (&aout_info.includes.root);
- return FALSE;
+ /* Assert that the relocs have not run into the symbols, and that n
+ the text relocs have not run into the data relocs. */
+ BFD_ASSERT (*reloff_ptr <= obj_sym_filepos (finfo->output_bfd)
+ && (reloff_ptr != &finfo->treloff
+ || (*reloff_ptr
+ <= obj_datasec (finfo->output_bfd)->rel_filepos)));
+
+ return TRUE;
}
-/* Link an a.out input BFD into the output file. */
+/* Get the section corresponding to a reloc index. */
-static bfd_boolean
-aout_link_input_bfd (finfo, input_bfd)
- struct aout_final_link_info *finfo;
- bfd *input_bfd;
+static INLINE asection *
+aout_reloc_index_to_section (bfd *abfd, int indx)
{
- bfd_size_type sym_count;
-
- BFD_ASSERT (bfd_get_format (input_bfd) == bfd_object);
-
- /* If this is a dynamic object, it may need special handling. */
- if ((input_bfd->flags & DYNAMIC) != 0
- && aout_backend_info (input_bfd)->link_dynamic_object != NULL)
- {
- return ((*aout_backend_info (input_bfd)->link_dynamic_object)
- (finfo->info, input_bfd));
- }
-
- /* Get the symbols. We probably have them already, unless
- finfo->info->keep_memory is FALSE. */
- if (! aout_get_external_symbols (input_bfd))
- return FALSE;
-
- sym_count = obj_aout_external_sym_count (input_bfd);
-
- /* Write out the symbols and get a map of the new indices. The map
- is placed into finfo->symbol_map. */
- if (! aout_link_write_symbols (finfo, input_bfd))
- return FALSE;
-
- /* Relocate and write out the sections. These functions use the
- symbol map created by aout_link_write_symbols. The linker_mark
- field will be set if these sections are to be included in the
- link, which will normally be the case. */
- if (obj_textsec (input_bfd)->linker_mark)
- {
- if (! aout_link_input_section (finfo, input_bfd,
- obj_textsec (input_bfd),
- &finfo->treloff,
- exec_hdr (input_bfd)->a_trsize))
- return FALSE;
- }
- if (obj_datasec (input_bfd)->linker_mark)
- {
- if (! aout_link_input_section (finfo, input_bfd,
- obj_datasec (input_bfd),
- &finfo->dreloff,
- exec_hdr (input_bfd)->a_drsize))
- return FALSE;
- }
-
- /* If we are not keeping memory, we don't need the symbols any
- longer. We still need them if we are keeping memory, because the
- strings in the hash table point into them. */
- if (! finfo->info->keep_memory)
+ switch (indx & N_TYPE)
{
- if (! aout_link_free_symbols (input_bfd))
- return FALSE;
+ case N_TEXT: return obj_textsec (abfd);
+ case N_DATA: return obj_datasec (abfd);
+ case N_BSS: return obj_bsssec (abfd);
+ case N_ABS:
+ case N_UNDF: return bfd_abs_section_ptr;
+ default: abort ();
}
-
- return TRUE;
+ return NULL;
}
-/* Adjust and write out the symbols for an a.out file. Set the new
- symbol indices into a symbol_map. */
+/* Relocate an a.out section using standard a.out relocs. */
static bfd_boolean
-aout_link_write_symbols (finfo, input_bfd)
- struct aout_final_link_info *finfo;
- bfd *input_bfd;
+aout_link_input_section_std (struct aout_final_link_info *finfo,
+ bfd *input_bfd,
+ asection *input_section,
+ struct reloc_std_external *relocs,
+ bfd_size_type rel_size,
+ bfd_byte *contents)
{
+ bfd_boolean (*check_dynamic_reloc)
+ (struct bfd_link_info *, bfd *, asection *,
+ struct aout_link_hash_entry *, void *, bfd_byte *, bfd_boolean *,
+ bfd_vma *);
bfd *output_bfd;
- bfd_size_type sym_count;
+ bfd_boolean relocatable;
+ struct external_nlist *syms;
char *strings;
- enum bfd_link_strip strip;
- enum bfd_link_discard discard;
- struct external_nlist *outsym;
- bfd_size_type strtab_index;
- register struct external_nlist *sym;
- struct external_nlist *sym_end;
- struct aout_link_hash_entry **sym_hash;
+ struct aout_link_hash_entry **sym_hashes;
int *symbol_map;
- bfd_boolean pass;
- bfd_boolean skip_next;
+ bfd_size_type reloc_count;
+ struct reloc_std_external *rel;
+ struct reloc_std_external *rel_end;
output_bfd = finfo->output_bfd;
- sym_count = obj_aout_external_sym_count (input_bfd);
- strings = obj_aout_external_strings (input_bfd);
- strip = finfo->info->strip;
- discard = finfo->info->discard;
- outsym = finfo->output_syms;
+ check_dynamic_reloc = aout_backend_info (output_bfd)->check_dynamic_reloc;
- /* First write out a symbol for this object file, unless we are
- discarding such symbols. */
- if (strip != strip_all
- && (strip != strip_some
- || bfd_hash_lookup (finfo->info->keep_hash, input_bfd->filename,
- FALSE, FALSE) != NULL)
- && discard != discard_all)
- {
- H_PUT_8 (output_bfd, N_TEXT, outsym->e_type);
- H_PUT_8 (output_bfd, 0, outsym->e_other);
- H_PUT_16 (output_bfd, 0, outsym->e_desc);
- strtab_index = add_to_stringtab (output_bfd, finfo->strtab,
- input_bfd->filename, FALSE);
- if (strtab_index == (bfd_size_type) -1)
- return FALSE;
- PUT_WORD (output_bfd, strtab_index, outsym->e_strx);
- PUT_WORD (output_bfd,
- (bfd_get_section_vma (output_bfd,
- obj_textsec (input_bfd)->output_section)
- + obj_textsec (input_bfd)->output_offset),
- outsym->e_value);
- ++obj_aout_external_sym_count (output_bfd);
- ++outsym;
- }
+ BFD_ASSERT (obj_reloc_entry_size (input_bfd) == RELOC_STD_SIZE);
+ BFD_ASSERT (input_bfd->xvec->header_byteorder
+ == output_bfd->xvec->header_byteorder);
- pass = FALSE;
- skip_next = FALSE;
- sym = obj_aout_external_syms (input_bfd);
- sym_end = sym + sym_count;
- sym_hash = obj_aout_sym_hashes (input_bfd);
+ relocatable = finfo->info->relocatable;
+ syms = obj_aout_external_syms (input_bfd);
+ strings = obj_aout_external_strings (input_bfd);
+ sym_hashes = obj_aout_sym_hashes (input_bfd);
symbol_map = finfo->symbol_map;
- memset (symbol_map, 0, (size_t) sym_count * sizeof *symbol_map);
- for (; sym < sym_end; sym++, sym_hash++, symbol_map++)
+
+ reloc_count = rel_size / RELOC_STD_SIZE;
+ rel = relocs;
+ rel_end = rel + reloc_count;
+ for (; rel < rel_end; rel++)
{
- const char *name;
- int type;
- struct aout_link_hash_entry *h;
- bfd_boolean skip;
- asection *symsec;
- bfd_vma val = 0;
- bfd_boolean copy;
+ bfd_vma r_addr;
+ int r_index;
+ int r_extern;
+ int r_pcrel;
+ int r_baserel = 0;
+ reloc_howto_type *howto;
+ struct aout_link_hash_entry *h = NULL;
+ bfd_vma relocation;
+ bfd_reloc_status_type r;
- /* We set *symbol_map to 0 above for all symbols. If it has
- already been set to -1 for this symbol, it means that we are
- discarding it because it appears in a duplicate header file.
- See the N_BINCL code below. */
- if (*symbol_map == -1)
- continue;
+ r_addr = GET_SWORD (input_bfd, rel->r_address);
- /* Initialize *symbol_map to -1, which means that the symbol was
- not copied into the output file. We will change it later if
- we do copy the symbol over. */
- *symbol_map = -1;
+#ifdef MY_reloc_howto
+ howto = MY_reloc_howto (input_bfd, rel, r_index, r_extern, r_pcrel);
+#else
+ {
+ int r_jmptable;
+ int r_relative;
+ int r_length;
+ unsigned int howto_idx;
- type = H_GET_8 (input_bfd, sym->e_type);
- name = strings + GET_WORD (input_bfd, sym->e_strx);
+ if (bfd_header_big_endian (input_bfd))
+ {
+ r_index = (((unsigned int) rel->r_index[0] << 16)
+ | ((unsigned int) rel->r_index[1] << 8)
+ | rel->r_index[2]);
+ r_extern = (0 != (rel->r_type[0] & RELOC_STD_BITS_EXTERN_BIG));
+ r_pcrel = (0 != (rel->r_type[0] & RELOC_STD_BITS_PCREL_BIG));
+ r_baserel = (0 != (rel->r_type[0] & RELOC_STD_BITS_BASEREL_BIG));
+ r_jmptable= (0 != (rel->r_type[0] & RELOC_STD_BITS_JMPTABLE_BIG));
+ r_relative= (0 != (rel->r_type[0] & RELOC_STD_BITS_RELATIVE_BIG));
+ r_length = ((rel->r_type[0] & RELOC_STD_BITS_LENGTH_BIG)
+ >> RELOC_STD_BITS_LENGTH_SH_BIG);
+ }
+ else
+ {
+ r_index = (((unsigned int) rel->r_index[2] << 16)
+ | ((unsigned int) rel->r_index[1] << 8)
+ | rel->r_index[0]);
+ r_extern = (0 != (rel->r_type[0] & RELOC_STD_BITS_EXTERN_LITTLE));
+ r_pcrel = (0 != (rel->r_type[0] & RELOC_STD_BITS_PCREL_LITTLE));
+ r_baserel = (0 != (rel->r_type[0]
+ & RELOC_STD_BITS_BASEREL_LITTLE));
+ r_jmptable= (0 != (rel->r_type[0]
+ & RELOC_STD_BITS_JMPTABLE_LITTLE));
+ r_relative= (0 != (rel->r_type[0]
+ & RELOC_STD_BITS_RELATIVE_LITTLE));
+ r_length = ((rel->r_type[0] & RELOC_STD_BITS_LENGTH_LITTLE)
+ >> RELOC_STD_BITS_LENGTH_SH_LITTLE);
+ }
- h = NULL;
+ howto_idx = (r_length + 4 * r_pcrel + 8 * r_baserel
+ + 16 * r_jmptable + 32 * r_relative);
+ BFD_ASSERT (howto_idx < TABLE_SIZE (howto_table_std));
+ howto = howto_table_std + howto_idx;
+ }
+#endif
- if (pass)
- {
- /* Pass this symbol through. It is the target of an
- indirect or warning symbol. */
- val = GET_WORD (input_bfd, sym->e_value);
- pass = FALSE;
- }
- else if (skip_next)
- {
- /* Skip this symbol, which is the target of an indirect
- symbol that we have changed to no longer be an indirect
- symbol. */
- skip_next = FALSE;
- continue;
- }
- else
+ if (relocatable)
{
- struct aout_link_hash_entry *hresolve;
-
- /* We have saved the hash table entry for this symbol, if
- there is one. Note that we could just look it up again
- in the hash table, provided we first check that it is an
- external symbol. */
- h = *sym_hash;
-
- /* Use the name from the hash table, in case the symbol was
- wrapped. */
- if (h != NULL
- && h->root.type != bfd_link_hash_warning)
- name = h->root.root.string;
-
- /* If this is an indirect or warning symbol, then change
- hresolve to the base symbol. We also change *sym_hash so
- that the relocation routines relocate against the real
- symbol. */
- hresolve = h;
- if (h != (struct aout_link_hash_entry *) NULL
- && (h->root.type == bfd_link_hash_indirect
- || h->root.type == bfd_link_hash_warning))
- {
- hresolve = (struct aout_link_hash_entry *) h->root.u.i.link;
- while (hresolve->root.type == bfd_link_hash_indirect
- || hresolve->root.type == bfd_link_hash_warning)
- hresolve = ((struct aout_link_hash_entry *)
- hresolve->root.u.i.link);
- *sym_hash = hresolve;
- }
-
- /* If the symbol has already been written out, skip it. */
- if (h != (struct aout_link_hash_entry *) NULL
- && h->written)
- {
- if ((type & N_TYPE) == N_INDR
- || type == N_WARNING)
- skip_next = TRUE;
- *symbol_map = h->indx;
- continue;
- }
-
- /* See if we are stripping this symbol. */
- skip = FALSE;
- switch (strip)
- {
- case strip_none:
- break;
- case strip_debugger:
- if ((type & N_STAB) != 0)
- skip = TRUE;
- break;
- case strip_some:
- if (bfd_hash_lookup (finfo->info->keep_hash, name, FALSE, FALSE)
- == NULL)
- skip = TRUE;
- break;
- case strip_all:
- skip = TRUE;
- break;
- }
- if (skip)
- {
- if (h != (struct aout_link_hash_entry *) NULL)
- h->written = TRUE;
- continue;
- }
-
- /* Get the value of the symbol. */
- if ((type & N_TYPE) == N_TEXT
- || type == N_WEAKT)
- symsec = obj_textsec (input_bfd);
- else if ((type & N_TYPE) == N_DATA
- || type == N_WEAKD)
- symsec = obj_datasec (input_bfd);
- else if ((type & N_TYPE) == N_BSS
- || type == N_WEAKB)
- symsec = obj_bsssec (input_bfd);
- else if ((type & N_TYPE) == N_ABS
- || type == N_WEAKA)
- symsec = bfd_abs_section_ptr;
- else if (((type & N_TYPE) == N_INDR
- && (hresolve == (struct aout_link_hash_entry *) NULL
- || (hresolve->root.type != bfd_link_hash_defined
- && hresolve->root.type != bfd_link_hash_defweak
- && hresolve->root.type != bfd_link_hash_common)))
- || type == N_WARNING)
- {
- /* Pass the next symbol through unchanged. The
- condition above for indirect symbols is so that if
- the indirect symbol was defined, we output it with
- the correct definition so the debugger will
- understand it. */
- pass = TRUE;
- val = GET_WORD (input_bfd, sym->e_value);
- symsec = NULL;
- }
- else if ((type & N_STAB) != 0)
- {
- val = GET_WORD (input_bfd, sym->e_value);
- symsec = NULL;
- }
- else
+ /* We are generating a relocatable output file, and must
+ modify the reloc accordingly. */
+ if (r_extern)
{
- /* If we get here with an indirect symbol, it means that
- we are outputting it with a real definition. In such
- a case we do not want to output the next symbol,
- which is the target of the indirection. */
- if ((type & N_TYPE) == N_INDR)
- skip_next = TRUE;
-
- symsec = NULL;
-
- /* We need to get the value from the hash table. We use
- hresolve so that if we have defined an indirect
- symbol we output the final definition. */
- if (h == (struct aout_link_hash_entry *) NULL)
- {
- switch (type & N_TYPE)
- {
- case N_SETT:
- symsec = obj_textsec (input_bfd);
- break;
- case N_SETD:
- symsec = obj_datasec (input_bfd);
- break;
- case N_SETB:
- symsec = obj_bsssec (input_bfd);
- break;
- case N_SETA:
- symsec = bfd_abs_section_ptr;
- break;
- default:
- val = 0;
- break;
- }
- }
- else if (hresolve->root.type == bfd_link_hash_defined
- || hresolve->root.type == bfd_link_hash_defweak)
+ /* If we know the symbol this relocation is against,
+ convert it into a relocation against a section. This
+ is what the native linker does. */
+ h = sym_hashes[r_index];
+ if (h != NULL
+ && (h->root.type == bfd_link_hash_defined
+ || h->root.type == bfd_link_hash_defweak))
{
- asection *input_section;
asection *output_section;
- /* This case usually means a common symbol which was
- turned into a defined symbol. */
- input_section = hresolve->root.u.def.section;
- output_section = input_section->output_section;
- BFD_ASSERT (bfd_is_abs_section (output_section)
- || output_section->owner == output_bfd);
- val = (hresolve->root.u.def.value
- + bfd_get_section_vma (output_bfd, output_section)
- + input_section->output_offset);
-
- /* Get the correct type based on the section. If
- this is a constructed set, force it to be
- globally visible. */
- if (type == N_SETT
- || type == N_SETD
- || type == N_SETB
- || type == N_SETA)
- type |= N_EXT;
-
- type &=~ N_TYPE;
+ /* Change the r_extern value. */
+ if (bfd_header_big_endian (output_bfd))
+ rel->r_type[0] &=~ RELOC_STD_BITS_EXTERN_BIG;
+ else
+ rel->r_type[0] &=~ RELOC_STD_BITS_EXTERN_LITTLE;
+ /* Compute a new r_index. */
+ output_section = h->root.u.def.section->output_section;
if (output_section == obj_textsec (output_bfd))
- type |= (hresolve->root.type == bfd_link_hash_defined
- ? N_TEXT
- : N_WEAKT);
+ r_index = N_TEXT;
else if (output_section == obj_datasec (output_bfd))
- type |= (hresolve->root.type == bfd_link_hash_defined
- ? N_DATA
- : N_WEAKD);
+ r_index = N_DATA;
else if (output_section == obj_bsssec (output_bfd))
- type |= (hresolve->root.type == bfd_link_hash_defined
- ? N_BSS
- : N_WEAKB);
+ r_index = N_BSS;
else
- type |= (hresolve->root.type == bfd_link_hash_defined
- ? N_ABS
- : N_WEAKA);
- }
- else if (hresolve->root.type == bfd_link_hash_common)
- val = hresolve->root.u.c.size;
- else if (hresolve->root.type == bfd_link_hash_undefweak)
- {
- val = 0;
- type = N_WEAKU;
- }
- else
- val = 0;
- }
- if (symsec != (asection *) NULL)
- val = (symsec->output_section->vma
- + symsec->output_offset
- + (GET_WORD (input_bfd, sym->e_value)
- - symsec->vma));
+ r_index = N_ABS;
- /* If this is a global symbol set the written flag, and if
- it is a local symbol see if we should discard it. */
- if (h != (struct aout_link_hash_entry *) NULL)
- {
- h->written = TRUE;
- h->indx = obj_aout_external_sym_count (output_bfd);
- }
- else if ((type & N_TYPE) != N_SETT
- && (type & N_TYPE) != N_SETD
- && (type & N_TYPE) != N_SETB
- && (type & N_TYPE) != N_SETA)
- {
- switch (discard)
- {
- case discard_none:
- case discard_sec_merge:
- break;
- case discard_l:
- if ((type & N_STAB) == 0
- && bfd_is_local_label_name (input_bfd, name))
- skip = TRUE;
- break;
- case discard_all:
- skip = TRUE;
- break;
- }
- if (skip)
- {
- pass = FALSE;
- continue;
+ /* Add the symbol value and the section VMA to the
+ addend stored in the contents. */
+ relocation = (h->root.u.def.value
+ + output_section->vma
+ + h->root.u.def.section->output_offset);
}
- }
-
- /* An N_BINCL symbol indicates the start of the stabs
- entries for a header file. We need to scan ahead to the
- next N_EINCL symbol, ignoring nesting, adding up all the
- characters in the symbol names, not including the file
- numbers in types (the first number after an open
- parenthesis). */
- if (type == (int) N_BINCL)
- {
- struct external_nlist *incl_sym;
- int nest;
- struct aout_link_includes_entry *incl_entry;
- struct aout_link_includes_totals *t;
-
- val = 0;
- nest = 0;
- for (incl_sym = sym + 1; incl_sym < sym_end; incl_sym++)
+ else
{
- int incl_type;
+ /* We must change r_index according to the symbol
+ map. */
+ r_index = symbol_map[r_index];
- incl_type = H_GET_8 (input_bfd, incl_sym->e_type);
- if (incl_type == (int) N_EINCL)
- {
- if (nest == 0)
- break;
- --nest;
- }
- else if (incl_type == (int) N_BINCL)
- ++nest;
- else if (nest == 0)
+ if (r_index == -1)
{
- const char *s;
-
- s = strings + GET_WORD (input_bfd, incl_sym->e_strx);
- for (; *s != '\0'; s++)
+ if (h != NULL)
{
- val += *s;
- if (*s == '(')
+ /* We decided to strip this symbol, but it
+ turns out that we can't. Note that we
+ lose the other and desc information here.
+ I don't think that will ever matter for a
+ global symbol. */
+ if (h->indx < 0)
{
- /* Skip the file number. */
- ++s;
- while (ISDIGIT (*s))
- ++s;
- --s;
+ h->indx = -2;
+ h->written = FALSE;
+ if (! aout_link_write_other_symbol (h,
+ (void *) finfo))
+ return FALSE;
}
+ r_index = h->indx;
+ }
+ else
+ {
+ const char *name;
+
+ name = strings + GET_WORD (input_bfd,
+ syms[r_index].e_strx);
+ if (! ((*finfo->info->callbacks->unattached_reloc)
+ (finfo->info, name, input_bfd, input_section,
+ r_addr)))
+ return FALSE;
+ r_index = 0;
}
}
+
+ relocation = 0;
}
- /* If we have already included a header file with the
- same value, then replace this one with an N_EXCL
- symbol. */
- copy = (bfd_boolean) (! finfo->info->keep_memory);
- incl_entry = aout_link_includes_lookup (&finfo->includes,
- name, TRUE, copy);
- if (incl_entry == NULL)
- return FALSE;
- for (t = incl_entry->totals; t != NULL; t = t->next)
- if (t->total == val)
- break;
- if (t == NULL)
+ /* Write out the new r_index value. */
+ if (bfd_header_big_endian (output_bfd))
{
- /* This is the first time we have seen this header
- file with this set of stabs strings. */
- t = ((struct aout_link_includes_totals *)
- bfd_hash_allocate (&finfo->includes.root,
- sizeof *t));
- if (t == NULL)
- return FALSE;
- t->total = val;
- t->next = incl_entry->totals;
- incl_entry->totals = t;
+ rel->r_index[0] = r_index >> 16;
+ rel->r_index[1] = r_index >> 8;
+ rel->r_index[2] = r_index;
}
else
{
- int *incl_map;
-
- /* This is a duplicate header file. We must change
- it to be an N_EXCL entry, and mark all the
- included symbols to prevent outputting them. */
- type = (int) N_EXCL;
-
- nest = 0;
- for (incl_sym = sym + 1, incl_map = symbol_map + 1;
- incl_sym < sym_end;
- incl_sym++, incl_map++)
- {
- int incl_type;
-
- incl_type = H_GET_8 (input_bfd, incl_sym->e_type);
- if (incl_type == (int) N_EINCL)
- {
- if (nest == 0)
- {
- *incl_map = -1;
- break;
- }
- --nest;
- }
- else if (incl_type == (int) N_BINCL)
- ++nest;
- else if (nest == 0)
- *incl_map = -1;
- }
+ rel->r_index[2] = r_index >> 16;
+ rel->r_index[1] = r_index >> 8;
+ rel->r_index[0] = r_index;
}
}
- }
-
- /* Copy this symbol into the list of symbols we are going to
- write out. */
- H_PUT_8 (output_bfd, type, outsym->e_type);
- H_PUT_8 (output_bfd, H_GET_8 (input_bfd, sym->e_other), outsym->e_other);
- H_PUT_16 (output_bfd, H_GET_16 (input_bfd, sym->e_desc), outsym->e_desc);
- copy = FALSE;
- if (! finfo->info->keep_memory)
- {
- /* name points into a string table which we are going to
- free. If there is a hash table entry, use that string.
- Otherwise, copy name into memory. */
- if (h != (struct aout_link_hash_entry *) NULL)
- name = h->root.root.string;
else
- copy = TRUE;
- }
- strtab_index = add_to_stringtab (output_bfd, finfo->strtab,
- name, copy);
- if (strtab_index == (bfd_size_type) -1)
- return FALSE;
- PUT_WORD (output_bfd, strtab_index, outsym->e_strx);
- PUT_WORD (output_bfd, val, outsym->e_value);
- *symbol_map = obj_aout_external_sym_count (output_bfd);
- ++obj_aout_external_sym_count (output_bfd);
- ++outsym;
- }
-
- /* Write out the output symbols we have just constructed. */
- if (outsym > finfo->output_syms)
- {
- bfd_size_type outsym_size;
-
- if (bfd_seek (output_bfd, finfo->symoff, SEEK_SET) != 0)
- return FALSE;
- outsym_size = outsym - finfo->output_syms;
- outsym_size *= EXTERNAL_NLIST_SIZE;
- if (bfd_bwrite ((PTR) finfo->output_syms, outsym_size, output_bfd)
- != outsym_size)
- return FALSE;
- finfo->symoff += outsym_size;
- }
-
- return TRUE;
-}
+ {
+ asection *section;
-/* Write out a symbol that was not associated with an a.out input
- object. */
+ /* This is a relocation against a section. We must
+ adjust by the amount that the section moved. */
+ section = aout_reloc_index_to_section (input_bfd, r_index);
+ relocation = (section->output_section->vma
+ + section->output_offset
+ - section->vma);
+ }
-static bfd_boolean
-aout_link_write_other_symbol (h, data)
- struct aout_link_hash_entry *h;
- PTR data;
-{
- struct aout_final_link_info *finfo = (struct aout_final_link_info *) data;
- bfd *output_bfd;
- int type;
- bfd_vma val;
- struct external_nlist outsym;
- bfd_size_type indx;
- bfd_size_type amt;
+ /* Change the address of the relocation. */
+ PUT_WORD (output_bfd,
+ r_addr + input_section->output_offset,
+ rel->r_address);
- if (h->root.type == bfd_link_hash_warning)
- {
- h = (struct aout_link_hash_entry *) h->root.u.i.link;
- if (h->root.type == bfd_link_hash_new)
- return TRUE;
- }
+ /* Adjust a PC relative relocation by removing the reference
+ to the original address in the section and including the
+ reference to the new address. */
+ if (r_pcrel)
+ relocation -= (input_section->output_section->vma
+ + input_section->output_offset
+ - input_section->vma);
- output_bfd = finfo->output_bfd;
+#ifdef MY_relocatable_reloc
+ MY_relocatable_reloc (howto, output_bfd, rel, relocation, r_addr);
+#endif
- if (aout_backend_info (output_bfd)->write_dynamic_symbol != NULL)
- {
- if (! ((*aout_backend_info (output_bfd)->write_dynamic_symbol)
- (output_bfd, finfo->info, h)))
- {
- /* FIXME: No way to handle errors. */
- abort ();
+ if (relocation == 0)
+ r = bfd_reloc_ok;
+ else
+ r = MY_relocate_contents (howto,
+ input_bfd, relocation,
+ contents + r_addr);
}
- }
-
- if (h->written)
- return TRUE;
-
- h->written = TRUE;
-
- /* An indx of -2 means the symbol must be written. */
- if (h->indx != -2
- && (finfo->info->strip == strip_all
- || (finfo->info->strip == strip_some
- && bfd_hash_lookup (finfo->info->keep_hash, h->root.root.string,
- FALSE, FALSE) == NULL)))
- return TRUE;
-
- switch (h->root.type)
- {
- default:
- case bfd_link_hash_warning:
- abort ();
- /* Avoid variable not initialized warnings. */
- return TRUE;
- case bfd_link_hash_new:
- /* This can happen for set symbols when sets are not being
- built. */
- return TRUE;
- case bfd_link_hash_undefined:
- type = N_UNDF | N_EXT;
- val = 0;
- break;
- case bfd_link_hash_defined:
- case bfd_link_hash_defweak:
- {
- asection *sec;
+ else
+ {
+ bfd_boolean hundef;
- sec = h->root.u.def.section->output_section;
- BFD_ASSERT (bfd_is_abs_section (sec)
- || sec->owner == output_bfd);
- if (sec == obj_textsec (output_bfd))
- type = h->root.type == bfd_link_hash_defined ? N_TEXT : N_WEAKT;
- else if (sec == obj_datasec (output_bfd))
- type = h->root.type == bfd_link_hash_defined ? N_DATA : N_WEAKD;
- else if (sec == obj_bsssec (output_bfd))
- type = h->root.type == bfd_link_hash_defined ? N_BSS : N_WEAKB;
- else
- type = h->root.type == bfd_link_hash_defined ? N_ABS : N_WEAKA;
- type |= N_EXT;
- val = (h->root.u.def.value
- + sec->vma
- + h->root.u.def.section->output_offset);
- }
- break;
- case bfd_link_hash_common:
- type = N_UNDF | N_EXT;
- val = h->root.u.c.size;
- break;
- case bfd_link_hash_undefweak:
- type = N_WEAKU;
- val = 0;
- case bfd_link_hash_indirect:
- /* We ignore these symbols, since the indirected symbol is
- already in the hash table. */
- return TRUE;
- }
+ /* We are generating an executable, and must do a full
+ relocation. */
+ hundef = FALSE;
- H_PUT_8 (output_bfd, type, outsym.e_type);
- H_PUT_8 (output_bfd, 0, outsym.e_other);
- H_PUT_16 (output_bfd, 0, outsym.e_desc);
- indx = add_to_stringtab (output_bfd, finfo->strtab, h->root.root.string,
- FALSE);
- if (indx == - (bfd_size_type) 1)
- {
- /* FIXME: No way to handle errors. */
- abort ();
- }
- PUT_WORD (output_bfd, indx, outsym.e_strx);
- PUT_WORD (output_bfd, val, outsym.e_value);
+ if (r_extern)
+ {
+ h = sym_hashes[r_index];
- amt = EXTERNAL_NLIST_SIZE;
- if (bfd_seek (output_bfd, finfo->symoff, SEEK_SET) != 0
- || bfd_bwrite ((PTR) &outsym, amt, output_bfd) != amt)
- {
- /* FIXME: No way to handle errors. */
- abort ();
- }
+ if (h != NULL
+ && (h->root.type == bfd_link_hash_defined
+ || h->root.type == bfd_link_hash_defweak))
+ {
+ relocation = (h->root.u.def.value
+ + h->root.u.def.section->output_section->vma
+ + h->root.u.def.section->output_offset);
+ }
+ else if (h != NULL
+ && h->root.type == bfd_link_hash_undefweak)
+ relocation = 0;
+ else
+ {
+ hundef = TRUE;
+ relocation = 0;
+ }
+ }
+ else
+ {
+ asection *section;
- finfo->symoff += EXTERNAL_NLIST_SIZE;
- h->indx = obj_aout_external_sym_count (output_bfd);
- ++obj_aout_external_sym_count (output_bfd);
+ section = aout_reloc_index_to_section (input_bfd, r_index);
+ relocation = (section->output_section->vma
+ + section->output_offset
+ - section->vma);
+ if (r_pcrel)
+ relocation += input_section->vma;
+ }
- return TRUE;
-}
+ if (check_dynamic_reloc != NULL)
+ {
+ bfd_boolean skip;
-/* Link an a.out section into the output file. */
+ if (! ((*check_dynamic_reloc)
+ (finfo->info, input_bfd, input_section, h,
+ (void *) rel, contents, &skip, &relocation)))
+ return FALSE;
+ if (skip)
+ continue;
+ }
-static bfd_boolean
-aout_link_input_section (finfo, input_bfd, input_section, reloff_ptr,
- rel_size)
- struct aout_final_link_info *finfo;
- bfd *input_bfd;
- asection *input_section;
- file_ptr *reloff_ptr;
- bfd_size_type rel_size;
-{
- bfd_size_type input_size;
- PTR relocs;
+ /* Now warn if a global symbol is undefined. We could not
+ do this earlier, because check_dynamic_reloc might want
+ to skip this reloc. */
+ if (hundef && ! finfo->info->shared && ! r_baserel)
+ {
+ const char *name;
- /* Get the section contents. */
- input_size = input_section->size;
- if (! bfd_get_section_contents (input_bfd, input_section,
- (PTR) finfo->contents,
- (file_ptr) 0, input_size))
- return FALSE;
+ if (h != NULL)
+ name = h->root.root.string;
+ else
+ name = strings + GET_WORD (input_bfd, syms[r_index].e_strx);
+ if (! ((*finfo->info->callbacks->undefined_symbol)
+ (finfo->info, name, input_bfd, input_section,
+ r_addr, TRUE)))
+ return FALSE;
+ }
- /* Read in the relocs if we haven't already done it. */
- if (aout_section_data (input_section) != NULL
- && aout_section_data (input_section)->relocs != NULL)
- relocs = aout_section_data (input_section)->relocs;
- else
- {
- relocs = finfo->relocs;
- if (rel_size > 0)
- {
- if (bfd_seek (input_bfd, input_section->rel_filepos, SEEK_SET) != 0
- || bfd_bread (relocs, rel_size, input_bfd) != rel_size)
- return FALSE;
+ r = MY_final_link_relocate (howto,
+ input_bfd, input_section,
+ contents, r_addr, relocation,
+ (bfd_vma) 0);
}
- }
-
- /* Relocate the section contents. */
- if (obj_reloc_entry_size (input_bfd) == RELOC_STD_SIZE)
- {
- if (! aout_link_input_section_std (finfo, input_bfd, input_section,
- (struct reloc_std_external *) relocs,
- rel_size, finfo->contents))
- return FALSE;
- }
- else
- {
- if (! aout_link_input_section_ext (finfo, input_bfd, input_section,
- (struct reloc_ext_external *) relocs,
- rel_size, finfo->contents))
- return FALSE;
- }
- /* Write out the section contents. */
- if (! bfd_set_section_contents (finfo->output_bfd,
- input_section->output_section,
- (PTR) finfo->contents,
- (file_ptr) input_section->output_offset,
- input_size))
- return FALSE;
+ if (r != bfd_reloc_ok)
+ {
+ switch (r)
+ {
+ default:
+ case bfd_reloc_outofrange:
+ abort ();
+ case bfd_reloc_overflow:
+ {
+ const char *name;
- /* If we are producing relocatable output, the relocs were
- modified, and we now write them out. */
- if (finfo->info->relocatable && rel_size > 0)
- {
- if (bfd_seek (finfo->output_bfd, *reloff_ptr, SEEK_SET) != 0)
- return FALSE;
- if (bfd_bwrite (relocs, rel_size, finfo->output_bfd) != rel_size)
- return FALSE;
- *reloff_ptr += rel_size;
+ if (h != NULL)
+ name = NULL;
+ else if (r_extern)
+ name = strings + GET_WORD (input_bfd,
+ syms[r_index].e_strx);
+ else
+ {
+ asection *s;
- /* Assert that the relocs have not run into the symbols, and
- that if these are the text relocs they have not run into the
- data relocs. */
- BFD_ASSERT (*reloff_ptr <= obj_sym_filepos (finfo->output_bfd)
- && (reloff_ptr != &finfo->treloff
- || (*reloff_ptr
- <= obj_datasec (finfo->output_bfd)->rel_filepos)));
+ s = aout_reloc_index_to_section (input_bfd, r_index);
+ name = bfd_section_name (input_bfd, s);
+ }
+ if (! ((*finfo->info->callbacks->reloc_overflow)
+ (finfo->info, (h ? &h->root : NULL), name,
+ howto->name, (bfd_vma) 0, input_bfd,
+ input_section, r_addr)))
+ return FALSE;
+ }
+ break;
+ }
+ }
}
return TRUE;
}
-/* Get the section corresponding to a reloc index. */
-
-static INLINE asection *
-aout_reloc_index_to_section (abfd, indx)
- bfd *abfd;
- int indx;
-{
- switch (indx & N_TYPE)
- {
- case N_TEXT:
- return obj_textsec (abfd);
- case N_DATA:
- return obj_datasec (abfd);
- case N_BSS:
- return obj_bsssec (abfd);
- case N_ABS:
- case N_UNDF:
- return bfd_abs_section_ptr;
- default:
- abort ();
- }
- /*NOTREACHED*/
- return NULL;
-}
-
-/* Relocate an a.out section using standard a.out relocs. */
+/* Relocate an a.out section using extended a.out relocs. */
static bfd_boolean
-aout_link_input_section_std (finfo, input_bfd, input_section, relocs,
- rel_size, contents)
- struct aout_final_link_info *finfo;
- bfd *input_bfd;
- asection *input_section;
- struct reloc_std_external *relocs;
- bfd_size_type rel_size;
- bfd_byte *contents;
+aout_link_input_section_ext (struct aout_final_link_info *finfo,
+ bfd *input_bfd,
+ asection *input_section,
+ struct reloc_ext_external *relocs,
+ bfd_size_type rel_size,
+ bfd_byte *contents)
{
bfd_boolean (*check_dynamic_reloc)
- PARAMS ((struct bfd_link_info *, bfd *, asection *,
- struct aout_link_hash_entry *, PTR, bfd_byte *, bfd_boolean *,
- bfd_vma *));
+ (struct bfd_link_info *, bfd *, asection *,
+ struct aout_link_hash_entry *, void *, bfd_byte *, bfd_boolean *,
+ bfd_vma *);
bfd *output_bfd;
bfd_boolean relocatable;
struct external_nlist *syms;
struct aout_link_hash_entry **sym_hashes;
int *symbol_map;
bfd_size_type reloc_count;
- register struct reloc_std_external *rel;
- struct reloc_std_external *rel_end;
+ struct reloc_ext_external *rel;
+ struct reloc_ext_external *rel_end;
output_bfd = finfo->output_bfd;
check_dynamic_reloc = aout_backend_info (output_bfd)->check_dynamic_reloc;
- BFD_ASSERT (obj_reloc_entry_size (input_bfd) == RELOC_STD_SIZE);
+ BFD_ASSERT (obj_reloc_entry_size (input_bfd) == RELOC_EXT_SIZE);
BFD_ASSERT (input_bfd->xvec->header_byteorder
== output_bfd->xvec->header_byteorder);
sym_hashes = obj_aout_sym_hashes (input_bfd);
symbol_map = finfo->symbol_map;
- reloc_count = rel_size / RELOC_STD_SIZE;
+ reloc_count = rel_size / RELOC_EXT_SIZE;
rel = relocs;
rel_end = rel + reloc_count;
for (; rel < rel_end; rel++)
bfd_vma r_addr;
int r_index;
int r_extern;
- int r_pcrel;
- int r_baserel = 0;
- reloc_howto_type *howto;
+ unsigned int r_type;
+ bfd_vma r_addend;
struct aout_link_hash_entry *h = NULL;
+ asection *r_section = NULL;
bfd_vma relocation;
- bfd_reloc_status_type r;
r_addr = GET_SWORD (input_bfd, rel->r_address);
-#ifdef MY_reloc_howto
- howto = MY_reloc_howto (input_bfd, rel, r_index, r_extern, r_pcrel);
-#else
- {
- int r_jmptable;
- int r_relative;
- int r_length;
- unsigned int howto_idx;
+ if (bfd_header_big_endian (input_bfd))
+ {
+ r_index = (((unsigned int) rel->r_index[0] << 16)
+ | ((unsigned int) rel->r_index[1] << 8)
+ | rel->r_index[2]);
+ r_extern = (0 != (rel->r_type[0] & RELOC_EXT_BITS_EXTERN_BIG));
+ r_type = ((rel->r_type[0] & RELOC_EXT_BITS_TYPE_BIG)
+ >> RELOC_EXT_BITS_TYPE_SH_BIG);
+ }
+ else
+ {
+ r_index = (((unsigned int) rel->r_index[2] << 16)
+ | ((unsigned int) rel->r_index[1] << 8)
+ | rel->r_index[0]);
+ r_extern = (0 != (rel->r_type[0] & RELOC_EXT_BITS_EXTERN_LITTLE));
+ r_type = ((rel->r_type[0] & RELOC_EXT_BITS_TYPE_LITTLE)
+ >> RELOC_EXT_BITS_TYPE_SH_LITTLE);
+ }
- if (bfd_header_big_endian (input_bfd))
- {
- r_index = (((unsigned int) rel->r_index[0] << 16)
- | ((unsigned int) rel->r_index[1] << 8)
- | rel->r_index[2]);
- r_extern = (0 != (rel->r_type[0] & RELOC_STD_BITS_EXTERN_BIG));
- r_pcrel = (0 != (rel->r_type[0] & RELOC_STD_BITS_PCREL_BIG));
- r_baserel = (0 != (rel->r_type[0] & RELOC_STD_BITS_BASEREL_BIG));
- r_jmptable= (0 != (rel->r_type[0] & RELOC_STD_BITS_JMPTABLE_BIG));
- r_relative= (0 != (rel->r_type[0] & RELOC_STD_BITS_RELATIVE_BIG));
- r_length = ((rel->r_type[0] & RELOC_STD_BITS_LENGTH_BIG)
- >> RELOC_STD_BITS_LENGTH_SH_BIG);
- }
- else
- {
- r_index = (((unsigned int) rel->r_index[2] << 16)
- | ((unsigned int) rel->r_index[1] << 8)
- | rel->r_index[0]);
- r_extern = (0 != (rel->r_type[0] & RELOC_STD_BITS_EXTERN_LITTLE));
- r_pcrel = (0 != (rel->r_type[0] & RELOC_STD_BITS_PCREL_LITTLE));
- r_baserel = (0 != (rel->r_type[0]
- & RELOC_STD_BITS_BASEREL_LITTLE));
- r_jmptable= (0 != (rel->r_type[0]
- & RELOC_STD_BITS_JMPTABLE_LITTLE));
- r_relative= (0 != (rel->r_type[0]
- & RELOC_STD_BITS_RELATIVE_LITTLE));
- r_length = ((rel->r_type[0] & RELOC_STD_BITS_LENGTH_LITTLE)
- >> RELOC_STD_BITS_LENGTH_SH_LITTLE);
- }
+ r_addend = GET_SWORD (input_bfd, rel->r_addend);
- howto_idx = (r_length + 4 * r_pcrel + 8 * r_baserel
- + 16 * r_jmptable + 32 * r_relative);
- BFD_ASSERT (howto_idx < TABLE_SIZE (howto_table_std));
- howto = howto_table_std + howto_idx;
- }
-#endif
+ BFD_ASSERT (r_type < TABLE_SIZE (howto_table_ext));
if (relocatable)
{
/* We are generating a relocatable output file, and must
modify the reloc accordingly. */
- if (r_extern)
+ if (r_extern
+ || r_type == (unsigned int) RELOC_BASE10
+ || r_type == (unsigned int) RELOC_BASE13
+ || r_type == (unsigned int) RELOC_BASE22)
{
/* If we know the symbol this relocation is against,
convert it into a relocation against a section. This
is what the native linker does. */
- h = sym_hashes[r_index];
- if (h != (struct aout_link_hash_entry *) NULL
+ if (r_type == (unsigned int) RELOC_BASE10
+ || r_type == (unsigned int) RELOC_BASE13
+ || r_type == (unsigned int) RELOC_BASE22)
+ h = NULL;
+ else
+ h = sym_hashes[r_index];
+ if (h != NULL
&& (h->root.type == bfd_link_hash_defined
|| h->root.type == bfd_link_hash_defweak))
{
/* Change the r_extern value. */
if (bfd_header_big_endian (output_bfd))
- rel->r_type[0] &=~ RELOC_STD_BITS_EXTERN_BIG;
+ rel->r_type[0] &=~ RELOC_EXT_BITS_EXTERN_BIG;
else
- rel->r_type[0] &=~ RELOC_STD_BITS_EXTERN_LITTLE;
+ rel->r_type[0] &=~ RELOC_EXT_BITS_EXTERN_LITTLE;
/* Compute a new r_index. */
output_section = h->root.u.def.section->output_section;
r_index = N_ABS;
/* Add the symbol value and the section VMA to the
- addend stored in the contents. */
+ addend. */
relocation = (h->root.u.def.value
+ output_section->vma
+ h->root.u.def.section->output_offset);
+
+ /* Now RELOCATION is the VMA of the final
+ destination. If this is a PC relative reloc,
+ then ADDEND is the negative of the source VMA.
+ We want to set ADDEND to the difference between
+ the destination VMA and the source VMA, which
+ means we must adjust RELOCATION by the change in
+ the source VMA. This is done below. */
}
else
{
h->indx = -2;
h->written = FALSE;
if (! aout_link_write_other_symbol (h,
- (PTR) finfo))
+ (void *) finfo))
return FALSE;
}
r_index = h->indx;
}
relocation = 0;
+
+ /* If this is a PC relative reloc, then the addend
+ is the negative of the source VMA. We must
+ adjust it by the change in the source VMA. This
+ is done below. */
}
/* Write out the new r_index value. */
}
else
{
- asection *section;
-
/* This is a relocation against a section. We must
adjust by the amount that the section moved. */
- section = aout_reloc_index_to_section (input_bfd, r_index);
- relocation = (section->output_section->vma
- + section->output_offset
- - section->vma);
- }
+ r_section = aout_reloc_index_to_section (input_bfd, r_index);
+ relocation = (r_section->output_section->vma
+ + r_section->output_offset
+ - r_section->vma);
- /* Change the address of the relocation. */
- PUT_WORD (output_bfd,
- r_addr + input_section->output_offset,
- rel->r_address);
+ /* If this is a PC relative reloc, then the addend is
+ the difference in VMA between the destination and the
+ source. We have just adjusted for the change in VMA
+ of the destination, so we must also adjust by the
+ change in VMA of the source. This is done below. */
+ }
- /* Adjust a PC relative relocation by removing the reference
- to the original address in the section and including the
- reference to the new address. */
- if (r_pcrel)
+ /* As described above, we must always adjust a PC relative
+ reloc by the change in VMA of the source. However, if
+ pcrel_offset is set, then the addend does not include the
+ location within the section, in which case we don't need
+ to adjust anything. */
+ if (howto_table_ext[r_type].pc_relative
+ && ! howto_table_ext[r_type].pcrel_offset)
relocation -= (input_section->output_section->vma
+ input_section->output_offset
- input_section->vma);
-#ifdef MY_relocatable_reloc
- MY_relocatable_reloc (howto, output_bfd, rel, relocation, r_addr);
-#endif
+ /* Change the addend if necessary. */
+ if (relocation != 0)
+ PUT_WORD (output_bfd, r_addend + relocation, rel->r_addend);
- if (relocation == 0)
- r = bfd_reloc_ok;
- else
- r = MY_relocate_contents (howto,
- input_bfd, relocation,
- contents + r_addr);
+ /* Change the address of the relocation. */
+ PUT_WORD (output_bfd,
+ r_addr + input_section->output_offset,
+ rel->r_address);
}
else
{
bfd_boolean hundef;
+ bfd_reloc_status_type r;
/* We are generating an executable, and must do a full
relocation. */
{
h = sym_hashes[r_index];
- if (h != (struct aout_link_hash_entry *) NULL
+ if (h != NULL
&& (h->root.type == bfd_link_hash_defined
|| h->root.type == bfd_link_hash_defweak))
{
+ h->root.u.def.section->output_section->vma
+ h->root.u.def.section->output_offset);
}
- else if (h != (struct aout_link_hash_entry *) NULL
+ else if (h != NULL
&& h->root.type == bfd_link_hash_undefweak)
relocation = 0;
else
relocation = 0;
}
}
+ else if (r_type == (unsigned int) RELOC_BASE10
+ || r_type == (unsigned int) RELOC_BASE13
+ || r_type == (unsigned int) RELOC_BASE22)
+ {
+ struct external_nlist *sym;
+ int type;
+
+ /* For base relative relocs, r_index is always an index
+ into the symbol table, even if r_extern is 0. */
+ sym = syms + r_index;
+ type = H_GET_8 (input_bfd, sym->e_type);
+ if ((type & N_TYPE) == N_TEXT
+ || type == N_WEAKT)
+ r_section = obj_textsec (input_bfd);
+ else if ((type & N_TYPE) == N_DATA
+ || type == N_WEAKD)
+ r_section = obj_datasec (input_bfd);
+ else if ((type & N_TYPE) == N_BSS
+ || type == N_WEAKB)
+ r_section = obj_bsssec (input_bfd);
+ else if ((type & N_TYPE) == N_ABS
+ || type == N_WEAKA)
+ r_section = bfd_abs_section_ptr;
+ else
+ abort ();
+ relocation = (r_section->output_section->vma
+ + r_section->output_offset
+ + (GET_WORD (input_bfd, sym->e_value)
+ - r_section->vma));
+ }
else
{
- asection *section;
+ r_section = aout_reloc_index_to_section (input_bfd, r_index);
- section = aout_reloc_index_to_section (input_bfd, r_index);
- relocation = (section->output_section->vma
- + section->output_offset
- - section->vma);
- if (r_pcrel)
+ /* If this is a PC relative reloc, then R_ADDEND is the
+ difference between the two vmas, or
+ old_dest_sec + old_dest_off - (old_src_sec + old_src_off)
+ where
+ old_dest_sec == section->vma
+ and
+ old_src_sec == input_section->vma
+ and
+ old_src_off == r_addr
+
+ _bfd_final_link_relocate expects RELOCATION +
+ R_ADDEND to be the VMA of the destination minus
+ r_addr (the minus r_addr is because this relocation
+ is not pcrel_offset, which is a bit confusing and
+ should, perhaps, be changed), or
+ new_dest_sec
+ where
+ new_dest_sec == output_section->vma + output_offset
+ We arrange for this to happen by setting RELOCATION to
+ new_dest_sec + old_src_sec - old_dest_sec
+
+ If this is not a PC relative reloc, then R_ADDEND is
+ simply the VMA of the destination, so we set
+ RELOCATION to the change in the destination VMA, or
+ new_dest_sec - old_dest_sec
+ */
+ relocation = (r_section->output_section->vma
+ + r_section->output_offset
+ - r_section->vma);
+ if (howto_table_ext[r_type].pc_relative)
relocation += input_section->vma;
}
if (! ((*check_dynamic_reloc)
(finfo->info, input_bfd, input_section, h,
- (PTR) rel, contents, &skip, &relocation)))
+ (void *) rel, contents, &skip, &relocation)))
return FALSE;
if (skip)
continue;
/* Now warn if a global symbol is undefined. We could not
do this earlier, because check_dynamic_reloc might want
to skip this reloc. */
- if (hundef && ! finfo->info->shared && ! r_baserel)
+ if (hundef
+ && ! finfo->info->shared
+ && r_type != (unsigned int) RELOC_BASE10
+ && r_type != (unsigned int) RELOC_BASE13
+ && r_type != (unsigned int) RELOC_BASE22)
{
const char *name;
return FALSE;
}
- r = MY_final_link_relocate (howto,
- input_bfd, input_section,
- contents, r_addr, relocation,
- (bfd_vma) 0);
- }
-
- if (r != bfd_reloc_ok)
- {
- switch (r)
+ if (r_type != (unsigned int) RELOC_SPARC_REV32)
+ r = MY_final_link_relocate (howto_table_ext + r_type,
+ input_bfd, input_section,
+ contents, r_addr, relocation,
+ r_addend);
+ else
{
- default:
- case bfd_reloc_outofrange:
- abort ();
- case bfd_reloc_overflow:
- {
- const char *name;
+ bfd_vma x;
- if (h != NULL)
- name = NULL;
- else if (r_extern)
- name = strings + GET_WORD (input_bfd,
- syms[r_index].e_strx);
- else
+ x = bfd_get_32 (input_bfd, contents + r_addr);
+ x = x + relocation + r_addend;
+ bfd_putl32 (/*input_bfd,*/ x, contents + r_addr);
+ r = bfd_reloc_ok;
+ }
+
+ if (r != bfd_reloc_ok)
+ {
+ switch (r)
+ {
+ default:
+ case bfd_reloc_outofrange:
+ abort ();
+ case bfd_reloc_overflow:
{
- asection *s;
+ const char *name;
- s = aout_reloc_index_to_section (input_bfd, r_index);
- name = bfd_section_name (input_bfd, s);
+ if (h != NULL)
+ name = NULL;
+ else if (r_extern
+ || r_type == (unsigned int) RELOC_BASE10
+ || r_type == (unsigned int) RELOC_BASE13
+ || r_type == (unsigned int) RELOC_BASE22)
+ name = strings + GET_WORD (input_bfd,
+ syms[r_index].e_strx);
+ else
+ {
+ asection *s;
+
+ s = aout_reloc_index_to_section (input_bfd, r_index);
+ name = bfd_section_name (input_bfd, s);
+ }
+ if (! ((*finfo->info->callbacks->reloc_overflow)
+ (finfo->info, (h ? &h->root : NULL), name,
+ howto_table_ext[r_type].name,
+ r_addend, input_bfd, input_section, r_addr)))
+ return FALSE;
}
- if (! ((*finfo->info->callbacks->reloc_overflow)
- (finfo->info, (h ? &h->root : NULL), name,
- howto->name, (bfd_vma) 0, input_bfd,
- input_section, r_addr)))
- return FALSE;
- }
- break;
+ break;
+ }
}
}
}
return TRUE;
}
-/* Relocate an a.out section using extended a.out relocs. */
+/* Link an a.out section into the output file. */
+
+static bfd_boolean
+aout_link_input_section (struct aout_final_link_info *finfo,
+ bfd *input_bfd,
+ asection *input_section,
+ file_ptr *reloff_ptr,
+ bfd_size_type rel_size)
+{
+ bfd_size_type input_size;
+ void * relocs;
+
+ /* Get the section contents. */
+ input_size = input_section->size;
+ if (! bfd_get_section_contents (input_bfd, input_section,
+ (void *) finfo->contents,
+ (file_ptr) 0, input_size))
+ return FALSE;
+
+ /* Read in the relocs if we haven't already done it. */
+ if (aout_section_data (input_section) != NULL
+ && aout_section_data (input_section)->relocs != NULL)
+ relocs = aout_section_data (input_section)->relocs;
+ else
+ {
+ relocs = finfo->relocs;
+ if (rel_size > 0)
+ {
+ if (bfd_seek (input_bfd, input_section->rel_filepos, SEEK_SET) != 0
+ || bfd_bread (relocs, rel_size, input_bfd) != rel_size)
+ return FALSE;
+ }
+ }
+
+ /* Relocate the section contents. */
+ if (obj_reloc_entry_size (input_bfd) == RELOC_STD_SIZE)
+ {
+ if (! aout_link_input_section_std (finfo, input_bfd, input_section,
+ (struct reloc_std_external *) relocs,
+ rel_size, finfo->contents))
+ return FALSE;
+ }
+ else
+ {
+ if (! aout_link_input_section_ext (finfo, input_bfd, input_section,
+ (struct reloc_ext_external *) relocs,
+ rel_size, finfo->contents))
+ return FALSE;
+ }
+
+ /* Write out the section contents. */
+ if (! bfd_set_section_contents (finfo->output_bfd,
+ input_section->output_section,
+ (void *) finfo->contents,
+ (file_ptr) input_section->output_offset,
+ input_size))
+ return FALSE;
+
+ /* If we are producing relocatable output, the relocs were
+ modified, and we now write them out. */
+ if (finfo->info->relocatable && rel_size > 0)
+ {
+ if (bfd_seek (finfo->output_bfd, *reloff_ptr, SEEK_SET) != 0)
+ return FALSE;
+ if (bfd_bwrite (relocs, rel_size, finfo->output_bfd) != rel_size)
+ return FALSE;
+ *reloff_ptr += rel_size;
+
+ /* Assert that the relocs have not run into the symbols, and
+ that if these are the text relocs they have not run into the
+ data relocs. */
+ BFD_ASSERT (*reloff_ptr <= obj_sym_filepos (finfo->output_bfd)
+ && (reloff_ptr != &finfo->treloff
+ || (*reloff_ptr
+ <= obj_datasec (finfo->output_bfd)->rel_filepos)));
+ }
+
+ return TRUE;
+}
+
+/* Adjust and write out the symbols for an a.out file. Set the new
+ symbol indices into a symbol_map. */
static bfd_boolean
-aout_link_input_section_ext (finfo, input_bfd, input_section, relocs,
- rel_size, contents)
- struct aout_final_link_info *finfo;
- bfd *input_bfd;
- asection *input_section;
- struct reloc_ext_external *relocs;
- bfd_size_type rel_size;
- bfd_byte *contents;
+aout_link_write_symbols (struct aout_final_link_info *finfo, bfd *input_bfd)
{
- bfd_boolean (*check_dynamic_reloc)
- PARAMS ((struct bfd_link_info *, bfd *, asection *,
- struct aout_link_hash_entry *, PTR, bfd_byte *, bfd_boolean *,
- bfd_vma *));
bfd *output_bfd;
- bfd_boolean relocatable;
- struct external_nlist *syms;
+ bfd_size_type sym_count;
char *strings;
- struct aout_link_hash_entry **sym_hashes;
+ enum bfd_link_strip strip;
+ enum bfd_link_discard discard;
+ struct external_nlist *outsym;
+ bfd_size_type strtab_index;
+ struct external_nlist *sym;
+ struct external_nlist *sym_end;
+ struct aout_link_hash_entry **sym_hash;
int *symbol_map;
- bfd_size_type reloc_count;
- register struct reloc_ext_external *rel;
- struct reloc_ext_external *rel_end;
+ bfd_boolean pass;
+ bfd_boolean skip_next;
output_bfd = finfo->output_bfd;
- check_dynamic_reloc = aout_backend_info (output_bfd)->check_dynamic_reloc;
+ sym_count = obj_aout_external_sym_count (input_bfd);
+ strings = obj_aout_external_strings (input_bfd);
+ strip = finfo->info->strip;
+ discard = finfo->info->discard;
+ outsym = finfo->output_syms;
- BFD_ASSERT (obj_reloc_entry_size (input_bfd) == RELOC_EXT_SIZE);
- BFD_ASSERT (input_bfd->xvec->header_byteorder
- == output_bfd->xvec->header_byteorder);
+ /* First write out a symbol for this object file, unless we are
+ discarding such symbols. */
+ if (strip != strip_all
+ && (strip != strip_some
+ || bfd_hash_lookup (finfo->info->keep_hash, input_bfd->filename,
+ FALSE, FALSE) != NULL)
+ && discard != discard_all)
+ {
+ H_PUT_8 (output_bfd, N_TEXT, outsym->e_type);
+ H_PUT_8 (output_bfd, 0, outsym->e_other);
+ H_PUT_16 (output_bfd, 0, outsym->e_desc);
+ strtab_index = add_to_stringtab (output_bfd, finfo->strtab,
+ input_bfd->filename, FALSE);
+ if (strtab_index == (bfd_size_type) -1)
+ return FALSE;
+ PUT_WORD (output_bfd, strtab_index, outsym->e_strx);
+ PUT_WORD (output_bfd,
+ (bfd_get_section_vma (output_bfd,
+ obj_textsec (input_bfd)->output_section)
+ + obj_textsec (input_bfd)->output_offset),
+ outsym->e_value);
+ ++obj_aout_external_sym_count (output_bfd);
+ ++outsym;
+ }
- relocatable = finfo->info->relocatable;
- syms = obj_aout_external_syms (input_bfd);
- strings = obj_aout_external_strings (input_bfd);
- sym_hashes = obj_aout_sym_hashes (input_bfd);
+ pass = FALSE;
+ skip_next = FALSE;
+ sym = obj_aout_external_syms (input_bfd);
+ sym_end = sym + sym_count;
+ sym_hash = obj_aout_sym_hashes (input_bfd);
symbol_map = finfo->symbol_map;
-
- reloc_count = rel_size / RELOC_EXT_SIZE;
- rel = relocs;
- rel_end = rel + reloc_count;
- for (; rel < rel_end; rel++)
+ memset (symbol_map, 0, (size_t) sym_count * sizeof *symbol_map);
+ for (; sym < sym_end; sym++, sym_hash++, symbol_map++)
{
- bfd_vma r_addr;
- int r_index;
- int r_extern;
- unsigned int r_type;
- bfd_vma r_addend;
- struct aout_link_hash_entry *h = NULL;
- asection *r_section = NULL;
- bfd_vma relocation;
+ const char *name;
+ int type;
+ struct aout_link_hash_entry *h;
+ bfd_boolean skip;
+ asection *symsec;
+ bfd_vma val = 0;
+ bfd_boolean copy;
- r_addr = GET_SWORD (input_bfd, rel->r_address);
+ /* We set *symbol_map to 0 above for all symbols. If it has
+ already been set to -1 for this symbol, it means that we are
+ discarding it because it appears in a duplicate header file.
+ See the N_BINCL code below. */
+ if (*symbol_map == -1)
+ continue;
- if (bfd_header_big_endian (input_bfd))
+ /* Initialize *symbol_map to -1, which means that the symbol was
+ not copied into the output file. We will change it later if
+ we do copy the symbol over. */
+ *symbol_map = -1;
+
+ type = H_GET_8 (input_bfd, sym->e_type);
+ name = strings + GET_WORD (input_bfd, sym->e_strx);
+
+ h = NULL;
+
+ if (pass)
{
- r_index = (((unsigned int) rel->r_index[0] << 16)
- | ((unsigned int) rel->r_index[1] << 8)
- | rel->r_index[2]);
- r_extern = (0 != (rel->r_type[0] & RELOC_EXT_BITS_EXTERN_BIG));
- r_type = ((rel->r_type[0] & RELOC_EXT_BITS_TYPE_BIG)
- >> RELOC_EXT_BITS_TYPE_SH_BIG);
+ /* Pass this symbol through. It is the target of an
+ indirect or warning symbol. */
+ val = GET_WORD (input_bfd, sym->e_value);
+ pass = FALSE;
}
- else
+ else if (skip_next)
{
- r_index = (((unsigned int) rel->r_index[2] << 16)
- | ((unsigned int) rel->r_index[1] << 8)
- | rel->r_index[0]);
- r_extern = (0 != (rel->r_type[0] & RELOC_EXT_BITS_EXTERN_LITTLE));
- r_type = ((rel->r_type[0] & RELOC_EXT_BITS_TYPE_LITTLE)
- >> RELOC_EXT_BITS_TYPE_SH_LITTLE);
+ /* Skip this symbol, which is the target of an indirect
+ symbol that we have changed to no longer be an indirect
+ symbol. */
+ skip_next = FALSE;
+ continue;
}
+ else
+ {
+ struct aout_link_hash_entry *hresolve;
- r_addend = GET_SWORD (input_bfd, rel->r_addend);
+ /* We have saved the hash table entry for this symbol, if
+ there is one. Note that we could just look it up again
+ in the hash table, provided we first check that it is an
+ external symbol. */
+ h = *sym_hash;
- BFD_ASSERT (r_type < TABLE_SIZE (howto_table_ext));
+ /* Use the name from the hash table, in case the symbol was
+ wrapped. */
+ if (h != NULL
+ && h->root.type != bfd_link_hash_warning)
+ name = h->root.root.string;
- if (relocatable)
- {
- /* We are generating a relocatable output file, and must
- modify the reloc accordingly. */
- if (r_extern
- || r_type == (unsigned int) RELOC_BASE10
- || r_type == (unsigned int) RELOC_BASE13
- || r_type == (unsigned int) RELOC_BASE22)
+ /* If this is an indirect or warning symbol, then change
+ hresolve to the base symbol. We also change *sym_hash so
+ that the relocation routines relocate against the real
+ symbol. */
+ hresolve = h;
+ if (h != (struct aout_link_hash_entry *) NULL
+ && (h->root.type == bfd_link_hash_indirect
+ || h->root.type == bfd_link_hash_warning))
{
- /* If we know the symbol this relocation is against,
- convert it into a relocation against a section. This
- is what the native linker does. */
- if (r_type == (unsigned int) RELOC_BASE10
- || r_type == (unsigned int) RELOC_BASE13
- || r_type == (unsigned int) RELOC_BASE22)
- h = NULL;
- else
- h = sym_hashes[r_index];
- if (h != (struct aout_link_hash_entry *) NULL
- && (h->root.type == bfd_link_hash_defined
- || h->root.type == bfd_link_hash_defweak))
+ hresolve = (struct aout_link_hash_entry *) h->root.u.i.link;
+ while (hresolve->root.type == bfd_link_hash_indirect
+ || hresolve->root.type == bfd_link_hash_warning)
+ hresolve = ((struct aout_link_hash_entry *)
+ hresolve->root.u.i.link);
+ *sym_hash = hresolve;
+ }
+
+ /* If the symbol has already been written out, skip it. */
+ if (h != NULL
+ && h->written)
+ {
+ if ((type & N_TYPE) == N_INDR
+ || type == N_WARNING)
+ skip_next = TRUE;
+ *symbol_map = h->indx;
+ continue;
+ }
+
+ /* See if we are stripping this symbol. */
+ skip = FALSE;
+ switch (strip)
+ {
+ case strip_none:
+ break;
+ case strip_debugger:
+ if ((type & N_STAB) != 0)
+ skip = TRUE;
+ break;
+ case strip_some:
+ if (bfd_hash_lookup (finfo->info->keep_hash, name, FALSE, FALSE)
+ == NULL)
+ skip = TRUE;
+ break;
+ case strip_all:
+ skip = TRUE;
+ break;
+ }
+ if (skip)
+ {
+ if (h != NULL)
+ h->written = TRUE;
+ continue;
+ }
+
+ /* Get the value of the symbol. */
+ if ((type & N_TYPE) == N_TEXT
+ || type == N_WEAKT)
+ symsec = obj_textsec (input_bfd);
+ else if ((type & N_TYPE) == N_DATA
+ || type == N_WEAKD)
+ symsec = obj_datasec (input_bfd);
+ else if ((type & N_TYPE) == N_BSS
+ || type == N_WEAKB)
+ symsec = obj_bsssec (input_bfd);
+ else if ((type & N_TYPE) == N_ABS
+ || type == N_WEAKA)
+ symsec = bfd_abs_section_ptr;
+ else if (((type & N_TYPE) == N_INDR
+ && (hresolve == NULL
+ || (hresolve->root.type != bfd_link_hash_defined
+ && hresolve->root.type != bfd_link_hash_defweak
+ && hresolve->root.type != bfd_link_hash_common)))
+ || type == N_WARNING)
+ {
+ /* Pass the next symbol through unchanged. The
+ condition above for indirect symbols is so that if
+ the indirect symbol was defined, we output it with
+ the correct definition so the debugger will
+ understand it. */
+ pass = TRUE;
+ val = GET_WORD (input_bfd, sym->e_value);
+ symsec = NULL;
+ }
+ else if ((type & N_STAB) != 0)
+ {
+ val = GET_WORD (input_bfd, sym->e_value);
+ symsec = NULL;
+ }
+ else
+ {
+ /* If we get here with an indirect symbol, it means that
+ we are outputting it with a real definition. In such
+ a case we do not want to output the next symbol,
+ which is the target of the indirection. */
+ if ((type & N_TYPE) == N_INDR)
+ skip_next = TRUE;
+
+ symsec = NULL;
+
+ /* We need to get the value from the hash table. We use
+ hresolve so that if we have defined an indirect
+ symbol we output the final definition. */
+ if (h == NULL)
+ {
+ switch (type & N_TYPE)
+ {
+ case N_SETT:
+ symsec = obj_textsec (input_bfd);
+ break;
+ case N_SETD:
+ symsec = obj_datasec (input_bfd);
+ break;
+ case N_SETB:
+ symsec = obj_bsssec (input_bfd);
+ break;
+ case N_SETA:
+ symsec = bfd_abs_section_ptr;
+ break;
+ default:
+ val = 0;
+ break;
+ }
+ }
+ else if (hresolve->root.type == bfd_link_hash_defined
+ || hresolve->root.type == bfd_link_hash_defweak)
{
+ asection *input_section;
asection *output_section;
- /* Change the r_extern value. */
- if (bfd_header_big_endian (output_bfd))
- rel->r_type[0] &=~ RELOC_EXT_BITS_EXTERN_BIG;
- else
- rel->r_type[0] &=~ RELOC_EXT_BITS_EXTERN_LITTLE;
+ /* This case usually means a common symbol which was
+ turned into a defined symbol. */
+ input_section = hresolve->root.u.def.section;
+ output_section = input_section->output_section;
+ BFD_ASSERT (bfd_is_abs_section (output_section)
+ || output_section->owner == output_bfd);
+ val = (hresolve->root.u.def.value
+ + bfd_get_section_vma (output_bfd, output_section)
+ + input_section->output_offset);
+
+ /* Get the correct type based on the section. If
+ this is a constructed set, force it to be
+ globally visible. */
+ if (type == N_SETT
+ || type == N_SETD
+ || type == N_SETB
+ || type == N_SETA)
+ type |= N_EXT;
+
+ type &=~ N_TYPE;
- /* Compute a new r_index. */
- output_section = h->root.u.def.section->output_section;
if (output_section == obj_textsec (output_bfd))
- r_index = N_TEXT;
+ type |= (hresolve->root.type == bfd_link_hash_defined
+ ? N_TEXT
+ : N_WEAKT);
else if (output_section == obj_datasec (output_bfd))
- r_index = N_DATA;
+ type |= (hresolve->root.type == bfd_link_hash_defined
+ ? N_DATA
+ : N_WEAKD);
else if (output_section == obj_bsssec (output_bfd))
- r_index = N_BSS;
+ type |= (hresolve->root.type == bfd_link_hash_defined
+ ? N_BSS
+ : N_WEAKB);
else
- r_index = N_ABS;
-
- /* Add the symbol value and the section VMA to the
- addend. */
- relocation = (h->root.u.def.value
- + output_section->vma
- + h->root.u.def.section->output_offset);
-
- /* Now RELOCATION is the VMA of the final
- destination. If this is a PC relative reloc,
- then ADDEND is the negative of the source VMA.
- We want to set ADDEND to the difference between
- the destination VMA and the source VMA, which
- means we must adjust RELOCATION by the change in
- the source VMA. This is done below. */
+ type |= (hresolve->root.type == bfd_link_hash_defined
+ ? N_ABS
+ : N_WEAKA);
+ }
+ else if (hresolve->root.type == bfd_link_hash_common)
+ val = hresolve->root.u.c.size;
+ else if (hresolve->root.type == bfd_link_hash_undefweak)
+ {
+ val = 0;
+ type = N_WEAKU;
}
else
+ val = 0;
+ }
+ if (symsec != NULL)
+ val = (symsec->output_section->vma
+ + symsec->output_offset
+ + (GET_WORD (input_bfd, sym->e_value)
+ - symsec->vma));
+
+ /* If this is a global symbol set the written flag, and if
+ it is a local symbol see if we should discard it. */
+ if (h != NULL)
+ {
+ h->written = TRUE;
+ h->indx = obj_aout_external_sym_count (output_bfd);
+ }
+ else if ((type & N_TYPE) != N_SETT
+ && (type & N_TYPE) != N_SETD
+ && (type & N_TYPE) != N_SETB
+ && (type & N_TYPE) != N_SETA)
+ {
+ switch (discard)
{
- /* We must change r_index according to the symbol
- map. */
- r_index = symbol_map[r_index];
+ case discard_none:
+ case discard_sec_merge:
+ break;
+ case discard_l:
+ if ((type & N_STAB) == 0
+ && bfd_is_local_label_name (input_bfd, name))
+ skip = TRUE;
+ break;
+ case discard_all:
+ skip = TRUE;
+ break;
+ }
+ if (skip)
+ {
+ pass = FALSE;
+ continue;
+ }
+ }
- if (r_index == -1)
+ /* An N_BINCL symbol indicates the start of the stabs
+ entries for a header file. We need to scan ahead to the
+ next N_EINCL symbol, ignoring nesting, adding up all the
+ characters in the symbol names, not including the file
+ numbers in types (the first number after an open
+ parenthesis). */
+ if (type == (int) N_BINCL)
+ {
+ struct external_nlist *incl_sym;
+ int nest;
+ struct aout_link_includes_entry *incl_entry;
+ struct aout_link_includes_totals *t;
+
+ val = 0;
+ nest = 0;
+ for (incl_sym = sym + 1; incl_sym < sym_end; incl_sym++)
+ {
+ int incl_type;
+
+ incl_type = H_GET_8 (input_bfd, incl_sym->e_type);
+ if (incl_type == (int) N_EINCL)
{
- if (h != NULL)
+ if (nest == 0)
+ break;
+ --nest;
+ }
+ else if (incl_type == (int) N_BINCL)
+ ++nest;
+ else if (nest == 0)
+ {
+ const char *s;
+
+ s = strings + GET_WORD (input_bfd, incl_sym->e_strx);
+ for (; *s != '\0'; s++)
{
- /* We decided to strip this symbol, but it
- turns out that we can't. Note that we
- lose the other and desc information here.
- I don't think that will ever matter for a
- global symbol. */
- if (h->indx < 0)
+ val += *s;
+ if (*s == '(')
{
- h->indx = -2;
- h->written = FALSE;
- if (! aout_link_write_other_symbol (h,
- (PTR) finfo))
- return FALSE;
+ /* Skip the file number. */
+ ++s;
+ while (ISDIGIT (*s))
+ ++s;
+ --s;
}
- r_index = h->indx;
}
- else
- {
- const char *name;
+ }
+ }
- name = strings + GET_WORD (input_bfd,
- syms[r_index].e_strx);
- if (! ((*finfo->info->callbacks->unattached_reloc)
- (finfo->info, name, input_bfd, input_section,
- r_addr)))
- return FALSE;
- r_index = 0;
+ /* If we have already included a header file with the
+ same value, then replace this one with an N_EXCL
+ symbol. */
+ copy = (bfd_boolean) (! finfo->info->keep_memory);
+ incl_entry = aout_link_includes_lookup (&finfo->includes,
+ name, TRUE, copy);
+ if (incl_entry == NULL)
+ return FALSE;
+ for (t = incl_entry->totals; t != NULL; t = t->next)
+ if (t->total == val)
+ break;
+ if (t == NULL)
+ {
+ /* This is the first time we have seen this header
+ file with this set of stabs strings. */
+ t = bfd_hash_allocate (&finfo->includes.root,
+ sizeof *t);
+ if (t == NULL)
+ return FALSE;
+ t->total = val;
+ t->next = incl_entry->totals;
+ incl_entry->totals = t;
+ }
+ else
+ {
+ int *incl_map;
+
+ /* This is a duplicate header file. We must change
+ it to be an N_EXCL entry, and mark all the
+ included symbols to prevent outputting them. */
+ type = (int) N_EXCL;
+
+ nest = 0;
+ for (incl_sym = sym + 1, incl_map = symbol_map + 1;
+ incl_sym < sym_end;
+ incl_sym++, incl_map++)
+ {
+ int incl_type;
+
+ incl_type = H_GET_8 (input_bfd, incl_sym->e_type);
+ if (incl_type == (int) N_EINCL)
+ {
+ if (nest == 0)
+ {
+ *incl_map = -1;
+ break;
+ }
+ --nest;
}
+ else if (incl_type == (int) N_BINCL)
+ ++nest;
+ else if (nest == 0)
+ *incl_map = -1;
}
-
- relocation = 0;
-
- /* If this is a PC relative reloc, then the addend
- is the negative of the source VMA. We must
- adjust it by the change in the source VMA. This
- is done below. */
- }
-
- /* Write out the new r_index value. */
- if (bfd_header_big_endian (output_bfd))
- {
- rel->r_index[0] = r_index >> 16;
- rel->r_index[1] = r_index >> 8;
- rel->r_index[2] = r_index;
- }
- else
- {
- rel->r_index[2] = r_index >> 16;
- rel->r_index[1] = r_index >> 8;
- rel->r_index[0] = r_index;
}
}
+ }
+
+ /* Copy this symbol into the list of symbols we are going to
+ write out. */
+ H_PUT_8 (output_bfd, type, outsym->e_type);
+ H_PUT_8 (output_bfd, H_GET_8 (input_bfd, sym->e_other), outsym->e_other);
+ H_PUT_16 (output_bfd, H_GET_16 (input_bfd, sym->e_desc), outsym->e_desc);
+ copy = FALSE;
+ if (! finfo->info->keep_memory)
+ {
+ /* name points into a string table which we are going to
+ free. If there is a hash table entry, use that string.
+ Otherwise, copy name into memory. */
+ if (h != NULL)
+ name = h->root.root.string;
else
- {
- /* This is a relocation against a section. We must
- adjust by the amount that the section moved. */
- r_section = aout_reloc_index_to_section (input_bfd, r_index);
- relocation = (r_section->output_section->vma
- + r_section->output_offset
- - r_section->vma);
+ copy = TRUE;
+ }
+ strtab_index = add_to_stringtab (output_bfd, finfo->strtab,
+ name, copy);
+ if (strtab_index == (bfd_size_type) -1)
+ return FALSE;
+ PUT_WORD (output_bfd, strtab_index, outsym->e_strx);
+ PUT_WORD (output_bfd, val, outsym->e_value);
+ *symbol_map = obj_aout_external_sym_count (output_bfd);
+ ++obj_aout_external_sym_count (output_bfd);
+ ++outsym;
+ }
- /* If this is a PC relative reloc, then the addend is
- the difference in VMA between the destination and the
- source. We have just adjusted for the change in VMA
- of the destination, so we must also adjust by the
- change in VMA of the source. This is done below. */
- }
+ /* Write out the output symbols we have just constructed. */
+ if (outsym > finfo->output_syms)
+ {
+ bfd_size_type outsym_size;
- /* As described above, we must always adjust a PC relative
- reloc by the change in VMA of the source. However, if
- pcrel_offset is set, then the addend does not include the
- location within the section, in which case we don't need
- to adjust anything. */
- if (howto_table_ext[r_type].pc_relative
- && ! howto_table_ext[r_type].pcrel_offset)
- relocation -= (input_section->output_section->vma
- + input_section->output_offset
- - input_section->vma);
+ if (bfd_seek (output_bfd, finfo->symoff, SEEK_SET) != 0)
+ return FALSE;
+ outsym_size = outsym - finfo->output_syms;
+ outsym_size *= EXTERNAL_NLIST_SIZE;
+ if (bfd_bwrite ((void *) finfo->output_syms, outsym_size, output_bfd)
+ != outsym_size)
+ return FALSE;
+ finfo->symoff += outsym_size;
+ }
- /* Change the addend if necessary. */
- if (relocation != 0)
- PUT_WORD (output_bfd, r_addend + relocation, rel->r_addend);
+ return TRUE;
+}
- /* Change the address of the relocation. */
- PUT_WORD (output_bfd,
- r_addr + input_section->output_offset,
- rel->r_address);
- }
- else
- {
- bfd_boolean hundef;
- bfd_reloc_status_type r;
+/* Link an a.out input BFD into the output file. */
- /* We are generating an executable, and must do a full
- relocation. */
- hundef = FALSE;
+static bfd_boolean
+aout_link_input_bfd (struct aout_final_link_info *finfo, bfd *input_bfd)
+{
+ bfd_size_type sym_count;
- if (r_extern)
- {
- h = sym_hashes[r_index];
+ BFD_ASSERT (bfd_get_format (input_bfd) == bfd_object);
- if (h != (struct aout_link_hash_entry *) NULL
- && (h->root.type == bfd_link_hash_defined
- || h->root.type == bfd_link_hash_defweak))
- {
- relocation = (h->root.u.def.value
- + h->root.u.def.section->output_section->vma
- + h->root.u.def.section->output_offset);
- }
- else if (h != (struct aout_link_hash_entry *) NULL
- && h->root.type == bfd_link_hash_undefweak)
- relocation = 0;
- else
- {
- hundef = TRUE;
- relocation = 0;
- }
- }
- else if (r_type == (unsigned int) RELOC_BASE10
- || r_type == (unsigned int) RELOC_BASE13
- || r_type == (unsigned int) RELOC_BASE22)
- {
- struct external_nlist *sym;
- int type;
+ /* If this is a dynamic object, it may need special handling. */
+ if ((input_bfd->flags & DYNAMIC) != 0
+ && aout_backend_info (input_bfd)->link_dynamic_object != NULL)
+ return ((*aout_backend_info (input_bfd)->link_dynamic_object)
+ (finfo->info, input_bfd));
- /* For base relative relocs, r_index is always an index
- into the symbol table, even if r_extern is 0. */
- sym = syms + r_index;
- type = H_GET_8 (input_bfd, sym->e_type);
- if ((type & N_TYPE) == N_TEXT
- || type == N_WEAKT)
- r_section = obj_textsec (input_bfd);
- else if ((type & N_TYPE) == N_DATA
- || type == N_WEAKD)
- r_section = obj_datasec (input_bfd);
- else if ((type & N_TYPE) == N_BSS
- || type == N_WEAKB)
- r_section = obj_bsssec (input_bfd);
- else if ((type & N_TYPE) == N_ABS
- || type == N_WEAKA)
- r_section = bfd_abs_section_ptr;
- else
- abort ();
- relocation = (r_section->output_section->vma
- + r_section->output_offset
- + (GET_WORD (input_bfd, sym->e_value)
- - r_section->vma));
- }
- else
- {
- r_section = aout_reloc_index_to_section (input_bfd, r_index);
+ /* Get the symbols. We probably have them already, unless
+ finfo->info->keep_memory is FALSE. */
+ if (! aout_get_external_symbols (input_bfd))
+ return FALSE;
- /* If this is a PC relative reloc, then R_ADDEND is the
- difference between the two vmas, or
- old_dest_sec + old_dest_off - (old_src_sec + old_src_off)
- where
- old_dest_sec == section->vma
- and
- old_src_sec == input_section->vma
- and
- old_src_off == r_addr
+ sym_count = obj_aout_external_sym_count (input_bfd);
- _bfd_final_link_relocate expects RELOCATION +
- R_ADDEND to be the VMA of the destination minus
- r_addr (the minus r_addr is because this relocation
- is not pcrel_offset, which is a bit confusing and
- should, perhaps, be changed), or
- new_dest_sec
- where
- new_dest_sec == output_section->vma + output_offset
- We arrange for this to happen by setting RELOCATION to
- new_dest_sec + old_src_sec - old_dest_sec
+ /* Write out the symbols and get a map of the new indices. The map
+ is placed into finfo->symbol_map. */
+ if (! aout_link_write_symbols (finfo, input_bfd))
+ return FALSE;
- If this is not a PC relative reloc, then R_ADDEND is
- simply the VMA of the destination, so we set
- RELOCATION to the change in the destination VMA, or
- new_dest_sec - old_dest_sec
- */
- relocation = (r_section->output_section->vma
- + r_section->output_offset
- - r_section->vma);
- if (howto_table_ext[r_type].pc_relative)
- relocation += input_section->vma;
- }
+ /* Relocate and write out the sections. These functions use the
+ symbol map created by aout_link_write_symbols. The linker_mark
+ field will be set if these sections are to be included in the
+ link, which will normally be the case. */
+ if (obj_textsec (input_bfd)->linker_mark)
+ {
+ if (! aout_link_input_section (finfo, input_bfd,
+ obj_textsec (input_bfd),
+ &finfo->treloff,
+ exec_hdr (input_bfd)->a_trsize))
+ return FALSE;
+ }
+ if (obj_datasec (input_bfd)->linker_mark)
+ {
+ if (! aout_link_input_section (finfo, input_bfd,
+ obj_datasec (input_bfd),
+ &finfo->dreloff,
+ exec_hdr (input_bfd)->a_drsize))
+ return FALSE;
+ }
+
+ /* If we are not keeping memory, we don't need the symbols any
+ longer. We still need them if we are keeping memory, because the
+ strings in the hash table point into them. */
+ if (! finfo->info->keep_memory)
+ {
+ if (! aout_link_free_symbols (input_bfd))
+ return FALSE;
+ }
+
+ return TRUE;
+}
+
+/* Do the final link step. This is called on the output BFD. The
+ INFO structure should point to a list of BFDs linked through the
+ link_next field which can be used to find each BFD which takes part
+ in the output. Also, each section in ABFD should point to a list
+ of bfd_link_order structures which list all the input sections for
+ the output section. */
+
+bfd_boolean
+NAME (aout, final_link) (bfd *abfd,
+ struct bfd_link_info *info,
+ void (*callback) (bfd *, file_ptr *, file_ptr *, file_ptr *))
+{
+ struct aout_final_link_info aout_info;
+ bfd_boolean includes_hash_initialized = FALSE;
+ bfd *sub;
+ bfd_size_type trsize, drsize;
+ bfd_size_type max_contents_size;
+ bfd_size_type max_relocs_size;
+ bfd_size_type max_sym_count;
+ bfd_size_type text_size;
+ file_ptr text_end;
+ struct bfd_link_order *p;
+ asection *o;
+ bfd_boolean have_link_order_relocs;
+
+ if (info->shared)
+ abfd->flags |= DYNAMIC;
+
+ aout_info.info = info;
+ aout_info.output_bfd = abfd;
+ aout_info.contents = NULL;
+ aout_info.relocs = NULL;
+ aout_info.symbol_map = NULL;
+ aout_info.output_syms = NULL;
- if (check_dynamic_reloc != NULL)
- {
- bfd_boolean skip;
+ if (! bfd_hash_table_init_n (&aout_info.includes.root,
+ aout_link_includes_newfunc,
+ 251))
+ goto error_return;
+ includes_hash_initialized = TRUE;
- if (! ((*check_dynamic_reloc)
- (finfo->info, input_bfd, input_section, h,
- (PTR) rel, contents, &skip, &relocation)))
- return FALSE;
- if (skip)
- continue;
- }
+ /* Figure out the largest section size. Also, if generating
+ relocatable output, count the relocs. */
+ trsize = 0;
+ drsize = 0;
+ max_contents_size = 0;
+ max_relocs_size = 0;
+ max_sym_count = 0;
+ for (sub = info->input_bfds; sub != NULL; sub = sub->link_next)
+ {
+ bfd_size_type sz;
- /* Now warn if a global symbol is undefined. We could not
- do this earlier, because check_dynamic_reloc might want
- to skip this reloc. */
- if (hundef
- && ! finfo->info->shared
- && r_type != (unsigned int) RELOC_BASE10
- && r_type != (unsigned int) RELOC_BASE13
- && r_type != (unsigned int) RELOC_BASE22)
+ if (info->relocatable)
+ {
+ if (bfd_get_flavour (sub) == bfd_target_aout_flavour)
{
- const char *name;
-
- if (h != NULL)
- name = h->root.root.string;
- else
- name = strings + GET_WORD (input_bfd, syms[r_index].e_strx);
- if (! ((*finfo->info->callbacks->undefined_symbol)
- (finfo->info, name, input_bfd, input_section,
- r_addr, TRUE)))
- return FALSE;
+ trsize += exec_hdr (sub)->a_trsize;
+ drsize += exec_hdr (sub)->a_drsize;
}
-
- if (r_type != (unsigned int) RELOC_SPARC_REV32)
- r = MY_final_link_relocate (howto_table_ext + r_type,
- input_bfd, input_section,
- contents, r_addr, relocation,
- r_addend);
else
{
- bfd_vma x;
-
- x = bfd_get_32 (input_bfd, contents + r_addr);
- x = x + relocation + r_addend;
- bfd_putl32 (/*input_bfd,*/ x, contents + r_addr);
- r = bfd_reloc_ok;
+ /* FIXME: We need to identify the .text and .data sections
+ and call get_reloc_upper_bound and canonicalize_reloc to
+ work out the number of relocs needed, and then multiply
+ by the reloc size. */
+ (*_bfd_error_handler)
+ (_("%s: relocatable link from %s to %s not supported"),
+ bfd_get_filename (abfd),
+ sub->xvec->name, abfd->xvec->name);
+ bfd_set_error (bfd_error_invalid_operation);
+ goto error_return;
}
+ }
- if (r != bfd_reloc_ok)
- {
- switch (r)
- {
- default:
- case bfd_reloc_outofrange:
- abort ();
- case bfd_reloc_overflow:
- {
- const char *name;
+ if (bfd_get_flavour (sub) == bfd_target_aout_flavour)
+ {
+ sz = obj_textsec (sub)->size;
+ if (sz > max_contents_size)
+ max_contents_size = sz;
+ sz = obj_datasec (sub)->size;
+ if (sz > max_contents_size)
+ max_contents_size = sz;
- if (h != NULL)
- name = NULL;
- else if (r_extern
- || r_type == (unsigned int) RELOC_BASE10
- || r_type == (unsigned int) RELOC_BASE13
- || r_type == (unsigned int) RELOC_BASE22)
- name = strings + GET_WORD (input_bfd,
- syms[r_index].e_strx);
- else
- {
- asection *s;
+ sz = exec_hdr (sub)->a_trsize;
+ if (sz > max_relocs_size)
+ max_relocs_size = sz;
+ sz = exec_hdr (sub)->a_drsize;
+ if (sz > max_relocs_size)
+ max_relocs_size = sz;
- s = aout_reloc_index_to_section (input_bfd, r_index);
- name = bfd_section_name (input_bfd, s);
- }
- if (! ((*finfo->info->callbacks->reloc_overflow)
- (finfo->info, (h ? &h->root : NULL), name,
- howto_table_ext[r_type].name,
- r_addend, input_bfd, input_section, r_addr)))
- return FALSE;
- }
- break;
- }
- }
+ sz = obj_aout_external_sym_count (sub);
+ if (sz > max_sym_count)
+ max_sym_count = sz;
}
}
- return TRUE;
-}
+ if (info->relocatable)
+ {
+ if (obj_textsec (abfd) != NULL)
+ trsize += (_bfd_count_link_order_relocs (obj_textsec (abfd)
+ ->link_order_head)
+ * obj_reloc_entry_size (abfd));
+ if (obj_datasec (abfd) != NULL)
+ drsize += (_bfd_count_link_order_relocs (obj_datasec (abfd)
+ ->link_order_head)
+ * obj_reloc_entry_size (abfd));
+ }
-/* Handle a link order which is supposed to generate a reloc. */
+ exec_hdr (abfd)->a_trsize = trsize;
+ exec_hdr (abfd)->a_drsize = drsize;
-static bfd_boolean
-aout_link_reloc_link_order (finfo, o, p)
- struct aout_final_link_info *finfo;
- asection *o;
- struct bfd_link_order *p;
-{
- struct bfd_link_order_reloc *pr;
- int r_index;
- int r_extern;
- reloc_howto_type *howto;
- file_ptr *reloff_ptr = NULL;
- struct reloc_std_external srel;
- struct reloc_ext_external erel;
- PTR rel_ptr;
- bfd_size_type amt;
+ exec_hdr (abfd)->a_entry = bfd_get_start_address (abfd);
- pr = p->u.reloc.p;
+ /* Adjust the section sizes and vmas according to the magic number.
+ This sets a_text, a_data and a_bss in the exec_hdr and sets the
+ filepos for each section. */
+ if (! NAME (aout, adjust_sizes_and_vmas) (abfd, &text_size, &text_end))
+ goto error_return;
- if (p->type == bfd_section_reloc_link_order)
- {
- r_extern = 0;
- if (bfd_is_abs_section (pr->u.section))
- r_index = N_ABS | N_EXT;
- else
- {
- BFD_ASSERT (pr->u.section->owner == finfo->output_bfd);
- r_index = pr->u.section->target_index;
- }
- }
- else
- {
- struct aout_link_hash_entry *h;
+ /* The relocation and symbol file positions differ among a.out
+ targets. We are passed a callback routine from the backend
+ specific code to handle this.
+ FIXME: At this point we do not know how much space the symbol
+ table will require. This will not work for any (nonstandard)
+ a.out target that needs to know the symbol table size before it
+ can compute the relocation file positions. This may or may not
+ be the case for the hp300hpux target, for example. */
+ (*callback) (abfd, &aout_info.treloff, &aout_info.dreloff,
+ &aout_info.symoff);
+ obj_textsec (abfd)->rel_filepos = aout_info.treloff;
+ obj_datasec (abfd)->rel_filepos = aout_info.dreloff;
+ obj_sym_filepos (abfd) = aout_info.symoff;
- BFD_ASSERT (p->type == bfd_symbol_reloc_link_order);
- r_extern = 1;
- h = ((struct aout_link_hash_entry *)
- bfd_wrapped_link_hash_lookup (finfo->output_bfd, finfo->info,
- pr->u.name, FALSE, FALSE, TRUE));
- if (h != (struct aout_link_hash_entry *) NULL
- && h->indx >= 0)
- r_index = h->indx;
- else if (h != NULL)
- {
- /* We decided to strip this symbol, but it turns out that we
- can't. Note that we lose the other and desc information
- here. I don't think that will ever matter for a global
- symbol. */
- h->indx = -2;
- h->written = FALSE;
- if (! aout_link_write_other_symbol (h, (PTR) finfo))
- return FALSE;
- r_index = h->indx;
- }
- else
- {
- if (! ((*finfo->info->callbacks->unattached_reloc)
- (finfo->info, pr->u.name, (bfd *) NULL,
- (asection *) NULL, (bfd_vma) 0)))
- return FALSE;
- r_index = 0;
- }
- }
+ /* We keep a count of the symbols as we output them. */
+ obj_aout_external_sym_count (abfd) = 0;
+
+ /* We accumulate the string table as we write out the symbols. */
+ aout_info.strtab = _bfd_stringtab_init ();
+ if (aout_info.strtab == NULL)
+ goto error_return;
+
+ /* Allocate buffers to hold section contents and relocs. */
+ aout_info.contents = bfd_malloc (max_contents_size);
+ aout_info.relocs = bfd_malloc (max_relocs_size);
+ aout_info.symbol_map = bfd_malloc (max_sym_count * sizeof (int *));
+ aout_info.output_syms = bfd_malloc ((max_sym_count + 1)
+ * sizeof (struct external_nlist));
+ if ((aout_info.contents == NULL && max_contents_size != 0)
+ || (aout_info.relocs == NULL && max_relocs_size != 0)
+ || (aout_info.symbol_map == NULL && max_sym_count != 0)
+ || aout_info.output_syms == NULL)
+ goto error_return;
+
+ /* If we have a symbol named __DYNAMIC, force it out now. This is
+ required by SunOS. Doing this here rather than in sunos.c is a
+ hack, but it's easier than exporting everything which would be
+ needed. */
+ {
+ struct aout_link_hash_entry *h;
+
+ h = aout_link_hash_lookup (aout_hash_table (info), "__DYNAMIC",
+ FALSE, FALSE, FALSE);
+ if (h != NULL)
+ aout_link_write_other_symbol (h, &aout_info);
+ }
+
+ /* The most time efficient way to do the link would be to read all
+ the input object files into memory and then sort out the
+ information into the output file. Unfortunately, that will
+ probably use too much memory. Another method would be to step
+ through everything that composes the text section and write it
+ out, and then everything that composes the data section and write
+ it out, and then write out the relocs, and then write out the
+ symbols. Unfortunately, that requires reading stuff from each
+ input file several times, and we will not be able to keep all the
+ input files open simultaneously, and reopening them will be slow.
+
+ What we do is basically process one input file at a time. We do
+ everything we need to do with an input file once--copy over the
+ section contents, handle the relocation information, and write
+ out the symbols--and then we throw away the information we read
+ from it. This approach requires a lot of lseeks of the output
+ file, which is unfortunate but still faster than reopening a lot
+ of files.
+
+ We use the output_has_begun field of the input BFDs to see
+ whether we have already handled it. */
+ for (sub = info->input_bfds; sub != NULL; sub = sub->link_next)
+ sub->output_has_begun = FALSE;
- howto = bfd_reloc_type_lookup (finfo->output_bfd, pr->reloc);
- if (howto == 0)
+ /* Mark all sections which are to be included in the link. This
+ will normally be every section. We need to do this so that we
+ can identify any sections which the linker has decided to not
+ include. */
+ for (o = abfd->sections; o != NULL; o = o->next)
{
- bfd_set_error (bfd_error_bad_value);
- return FALSE;
+ for (p = o->link_order_head; p != NULL; p = p->next)
+ if (p->type == bfd_indirect_link_order)
+ p->u.indirect.section->linker_mark = TRUE;
}
- if (o == obj_textsec (finfo->output_bfd))
- reloff_ptr = &finfo->treloff;
- else if (o == obj_datasec (finfo->output_bfd))
- reloff_ptr = &finfo->dreloff;
- else
- abort ();
-
- if (obj_reloc_entry_size (finfo->output_bfd) == RELOC_STD_SIZE)
+ have_link_order_relocs = FALSE;
+ for (o = abfd->sections; o != NULL; o = o->next)
{
-#ifdef MY_put_reloc
- MY_put_reloc (finfo->output_bfd, r_extern, r_index, p->offset, howto,
- &srel);
-#else
- {
- int r_pcrel;
- int r_baserel;
- int r_jmptable;
- int r_relative;
- int r_length;
-
- r_pcrel = (int) howto->pc_relative;
- r_baserel = (howto->type & 8) != 0;
- r_jmptable = (howto->type & 16) != 0;
- r_relative = (howto->type & 32) != 0;
- r_length = howto->size;
-
- PUT_WORD (finfo->output_bfd, p->offset, srel.r_address);
- if (bfd_header_big_endian (finfo->output_bfd))
- {
- srel.r_index[0] = r_index >> 16;
- srel.r_index[1] = r_index >> 8;
- srel.r_index[2] = r_index;
- srel.r_type[0] =
- ((r_extern ? RELOC_STD_BITS_EXTERN_BIG : 0)
- | (r_pcrel ? RELOC_STD_BITS_PCREL_BIG : 0)
- | (r_baserel ? RELOC_STD_BITS_BASEREL_BIG : 0)
- | (r_jmptable ? RELOC_STD_BITS_JMPTABLE_BIG : 0)
- | (r_relative ? RELOC_STD_BITS_RELATIVE_BIG : 0)
- | (r_length << RELOC_STD_BITS_LENGTH_SH_BIG));
- }
- else
- {
- srel.r_index[2] = r_index >> 16;
- srel.r_index[1] = r_index >> 8;
- srel.r_index[0] = r_index;
- srel.r_type[0] =
- ((r_extern ? RELOC_STD_BITS_EXTERN_LITTLE : 0)
- | (r_pcrel ? RELOC_STD_BITS_PCREL_LITTLE : 0)
- | (r_baserel ? RELOC_STD_BITS_BASEREL_LITTLE : 0)
- | (r_jmptable ? RELOC_STD_BITS_JMPTABLE_LITTLE : 0)
- | (r_relative ? RELOC_STD_BITS_RELATIVE_LITTLE : 0)
- | (r_length << RELOC_STD_BITS_LENGTH_SH_LITTLE));
- }
- }
-#endif
- rel_ptr = (PTR) &srel;
-
- /* We have to write the addend into the object file, since
- standard a.out relocs are in place. It would be more
- reliable if we had the current contents of the file here,
- rather than assuming zeroes, but we can't read the file since
- it was opened using bfd_openw. */
- if (pr->addend != 0)
+ for (p = o->link_order_head;
+ p != NULL;
+ p = p->next)
{
- bfd_size_type size;
- bfd_reloc_status_type r;
- bfd_byte *buf;
- bfd_boolean ok;
-
- size = bfd_get_reloc_size (howto);
- buf = (bfd_byte *) bfd_zmalloc (size);
- if (buf == (bfd_byte *) NULL)
- return FALSE;
- r = MY_relocate_contents (howto, finfo->output_bfd,
- (bfd_vma) pr->addend, buf);
- switch (r)
+ if (p->type == bfd_indirect_link_order
+ && (bfd_get_flavour (p->u.indirect.section->owner)
+ == bfd_target_aout_flavour))
{
- case bfd_reloc_ok:
- break;
- default:
- case bfd_reloc_outofrange:
- abort ();
- case bfd_reloc_overflow:
- if (! ((*finfo->info->callbacks->reloc_overflow)
- (finfo->info, NULL,
- (p->type == bfd_section_reloc_link_order
- ? bfd_section_name (finfo->output_bfd,
- pr->u.section)
- : pr->u.name),
- howto->name, pr->addend, (bfd *) NULL,
- (asection *) NULL, (bfd_vma) 0)))
+ bfd *input_bfd;
+
+ input_bfd = p->u.indirect.section->owner;
+ if (! input_bfd->output_has_begun)
{
- free (buf);
- return FALSE;
+ if (! aout_link_input_bfd (&aout_info, input_bfd))
+ goto error_return;
+ input_bfd->output_has_begun = TRUE;
}
- break;
}
- ok = bfd_set_section_contents (finfo->output_bfd, o, (PTR) buf,
- (file_ptr) p->offset, size);
- free (buf);
- if (! ok)
- return FALSE;
+ else if (p->type == bfd_section_reloc_link_order
+ || p->type == bfd_symbol_reloc_link_order)
+ {
+ /* These are handled below. */
+ have_link_order_relocs = TRUE;
+ }
+ else
+ {
+ if (! _bfd_default_link_order (abfd, info, o, p))
+ goto error_return;
+ }
}
}
- else
- {
-#ifdef MY_put_ext_reloc
- MY_put_ext_reloc (finfo->output_bfd, r_extern, r_index, p->offset,
- howto, &erel, pr->addend);
-#else
- PUT_WORD (finfo->output_bfd, p->offset, erel.r_address);
- if (bfd_header_big_endian (finfo->output_bfd))
- {
- erel.r_index[0] = r_index >> 16;
- erel.r_index[1] = r_index >> 8;
- erel.r_index[2] = r_index;
- erel.r_type[0] =
- ((r_extern ? RELOC_EXT_BITS_EXTERN_BIG : 0)
- | (howto->type << RELOC_EXT_BITS_TYPE_SH_BIG));
- }
- else
+ /* Write out any symbols that we have not already written out. */
+ aout_link_hash_traverse (aout_hash_table (info),
+ aout_link_write_other_symbol,
+ (void *) &aout_info);
+
+ /* Now handle any relocs we were asked to create by the linker.
+ These did not come from any input file. We must do these after
+ we have written out all the symbols, so that we know the symbol
+ indices to use. */
+ if (have_link_order_relocs)
+ {
+ for (o = abfd->sections; o != NULL; o = o->next)
{
- erel.r_index[2] = r_index >> 16;
- erel.r_index[1] = r_index >> 8;
- erel.r_index[0] = r_index;
- erel.r_type[0] =
- (r_extern ? RELOC_EXT_BITS_EXTERN_LITTLE : 0)
- | (howto->type << RELOC_EXT_BITS_TYPE_SH_LITTLE);
+ for (p = o->link_order_head;
+ p != NULL;
+ p = p->next)
+ {
+ if (p->type == bfd_section_reloc_link_order
+ || p->type == bfd_symbol_reloc_link_order)
+ {
+ if (! aout_link_reloc_link_order (&aout_info, o, p))
+ goto error_return;
+ }
+ }
}
+ }
- PUT_WORD (finfo->output_bfd, (bfd_vma) pr->addend, erel.r_addend);
-#endif /* MY_put_ext_reloc */
+ if (aout_info.contents != NULL)
+ {
+ free (aout_info.contents);
+ aout_info.contents = NULL;
+ }
+ if (aout_info.relocs != NULL)
+ {
+ free (aout_info.relocs);
+ aout_info.relocs = NULL;
+ }
+ if (aout_info.symbol_map != NULL)
+ {
+ free (aout_info.symbol_map);
+ aout_info.symbol_map = NULL;
+ }
+ if (aout_info.output_syms != NULL)
+ {
+ free (aout_info.output_syms);
+ aout_info.output_syms = NULL;
+ }
+ if (includes_hash_initialized)
+ {
+ bfd_hash_table_free (&aout_info.includes.root);
+ includes_hash_initialized = FALSE;
+ }
- rel_ptr = (PTR) &erel;
+ /* Finish up any dynamic linking we may be doing. */
+ if (aout_backend_info (abfd)->finish_dynamic_link != NULL)
+ {
+ if (! (*aout_backend_info (abfd)->finish_dynamic_link) (abfd, info))
+ goto error_return;
}
- amt = obj_reloc_entry_size (finfo->output_bfd);
- if (bfd_seek (finfo->output_bfd, *reloff_ptr, SEEK_SET) != 0
- || bfd_bwrite (rel_ptr, amt, finfo->output_bfd) != amt)
- return FALSE;
+ /* Update the header information. */
+ abfd->symcount = obj_aout_external_sym_count (abfd);
+ exec_hdr (abfd)->a_syms = abfd->symcount * EXTERNAL_NLIST_SIZE;
+ obj_str_filepos (abfd) = obj_sym_filepos (abfd) + exec_hdr (abfd)->a_syms;
+ obj_textsec (abfd)->reloc_count =
+ exec_hdr (abfd)->a_trsize / obj_reloc_entry_size (abfd);
+ obj_datasec (abfd)->reloc_count =
+ exec_hdr (abfd)->a_drsize / obj_reloc_entry_size (abfd);
- *reloff_ptr += obj_reloc_entry_size (finfo->output_bfd);
+ /* Write out the string table, unless there are no symbols. */
+ if (abfd->symcount > 0)
+ {
+ if (bfd_seek (abfd, obj_str_filepos (abfd), SEEK_SET) != 0
+ || ! emit_stringtab (abfd, aout_info.strtab))
+ goto error_return;
+ }
+ else if (obj_textsec (abfd)->reloc_count == 0
+ && obj_datasec (abfd)->reloc_count == 0)
+ {
+ bfd_byte b;
+ file_ptr pos;
- /* Assert that the relocs have not run into the symbols, and that n
- the text relocs have not run into the data relocs. */
- BFD_ASSERT (*reloff_ptr <= obj_sym_filepos (finfo->output_bfd)
- && (reloff_ptr != &finfo->treloff
- || (*reloff_ptr
- <= obj_datasec (finfo->output_bfd)->rel_filepos)));
+ b = 0;
+ pos = obj_datasec (abfd)->filepos + exec_hdr (abfd)->a_data - 1;
+ if (bfd_seek (abfd, pos, SEEK_SET) != 0
+ || bfd_bwrite (&b, (bfd_size_type) 1, abfd) != 1)
+ goto error_return;
+ }
return TRUE;
+
+ error_return:
+ if (aout_info.contents != NULL)
+ free (aout_info.contents);
+ if (aout_info.relocs != NULL)
+ free (aout_info.relocs);
+ if (aout_info.symbol_map != NULL)
+ free (aout_info.symbol_map);
+ if (aout_info.output_syms != NULL)
+ free (aout_info.output_syms);
+ if (includes_hash_initialized)
+ bfd_hash_table_free (&aout_info.includes.root);
+ return FALSE;
}
Free Software Foundation, Inc.
Written by Cygnus Support.
-This file is part of BFD, the Binary File Descriptor library.
+ This file is part of BFD, the Binary File Descriptor library.
-This program is free software; you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation; either version 2 of the License, or
-(at your option) any later version.
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-GNU General Public License for more details.
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
-You should have received a copy of the GNU General Public License
-along with this program; if not, write to the Free Software
-Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
#include "bfd.h"
#include "sysdep.h"
#include "bfdlink.h"
#include "genlink.h"
#include "bout.h"
+#include "libiberty.h"
#include "aout/stab_gnu.h"
#include "libaout.h" /* BFD a.out internal data structures. */
-static int aligncode
- PARAMS ((bfd *abfd, asection *input_section, arelent *r,
- unsigned int shrink));
-static void perform_slip
- PARAMS ((bfd *abfd, unsigned int slip, asection *input_section,
- bfd_vma value));
-static bfd_boolean b_out_squirt_out_relocs
- PARAMS ((bfd *abfd, asection *section));
-static const bfd_target *b_out_callback
- PARAMS ((bfd *));
-static bfd_reloc_status_type calljx_callback
- PARAMS ((bfd *, struct bfd_link_info *, arelent *, PTR src, PTR dst,
- asection *));
-static bfd_reloc_status_type callj_callback
- PARAMS ((bfd *, struct bfd_link_info *, arelent *, PTR data,
- unsigned int srcidx, unsigned int dstidx, asection *, bfd_boolean));
-static bfd_vma get_value
- PARAMS ((arelent *, struct bfd_link_info *, asection *));
-static int abs32code
- PARAMS ((bfd *, asection *, arelent *, unsigned int,
- struct bfd_link_info *));
-static bfd_boolean b_out_bfd_relax_section
- PARAMS ((bfd *, asection *, struct bfd_link_info *, bfd_boolean *));
-static bfd_byte *b_out_bfd_get_relocated_section_contents
- PARAMS ((bfd *, struct bfd_link_info *, struct bfd_link_order *, bfd_byte *,
- bfd_boolean, asymbol **));
-static int b_out_sizeof_headers
- PARAMS ((bfd *, bfd_boolean));
-static bfd_boolean b_out_set_arch_mach
- PARAMS ((bfd *, enum bfd_architecture, unsigned long));
-static bfd_boolean b_out_set_section_contents
- PARAMS ((bfd *, asection *, const PTR, file_ptr, bfd_size_type));
-static long b_out_get_reloc_upper_bound
- PARAMS ((bfd *, sec_ptr));
-static long b_out_canonicalize_reloc
- PARAMS ((bfd *, sec_ptr, arelent **, asymbol **));
-static bfd_boolean b_out_slurp_reloc_table
- PARAMS ((bfd *, sec_ptr, asymbol **));
-static reloc_howto_type *b_out_bfd_reloc_type_lookup
- PARAMS ((bfd *, bfd_reloc_code_real_type));
-static bfd_boolean b_out_write_object_contents
- PARAMS ((bfd *));
-static int b_out_symbol_cmp
- PARAMS ((const void *, const void *));
-static bfd_boolean b_out_mkobject
- PARAMS ((bfd *));
-static const bfd_target *b_out_object_p
- PARAMS ((bfd *));
-
-void bout_swap_exec_header_in
- PARAMS ((bfd *, struct external_exec *, struct internal_exec *));
-void bout_swap_exec_header_out
- PARAMS ((bfd *, struct internal_exec *, struct external_exec *));
+#define ABS32CODE 0
+#define ABS32CODE_SHRUNK 1
+#define PCREL24 2
+#define CALLJ 3
+#define ABS32 4
+#define PCREL13 5
+#define ABS32_MAYBE_RELAXABLE 1
+#define ABS32_WAS_RELAXABLE 2
+
+#define ALIGNER 10
+#define ALIGNDONE 11
+
+static reloc_howto_type howto_reloc_callj =
+ HOWTO (CALLJ, 0, 2, 24, TRUE, 0, complain_overflow_signed, 0,"callj", TRUE, 0x00ffffff, 0x00ffffff,FALSE);
+static reloc_howto_type howto_reloc_abs32 =
+ HOWTO (ABS32, 0, 2, 32, FALSE, 0, complain_overflow_bitfield,0,"abs32", TRUE, 0xffffffff,0xffffffff,FALSE);
+static reloc_howto_type howto_reloc_pcrel24 =
+ HOWTO (PCREL24, 0, 2, 24, TRUE, 0, complain_overflow_signed,0,"pcrel24", TRUE, 0x00ffffff,0x00ffffff,FALSE);
+static reloc_howto_type howto_reloc_pcrel13 =
+ HOWTO (PCREL13, 0, 2, 13, TRUE, 0, complain_overflow_signed,0,"pcrel13", TRUE, 0x00001fff,0x00001fff,FALSE);
+static reloc_howto_type howto_reloc_abs32codeshrunk =
+ HOWTO (ABS32CODE_SHRUNK, 0, 2, 24, TRUE, 0, complain_overflow_signed, 0,"callx->callj", TRUE, 0x00ffffff, 0x00ffffff,FALSE);
+static reloc_howto_type howto_reloc_abs32code =
+ HOWTO (ABS32CODE, 0, 2, 32, FALSE, 0, complain_overflow_bitfield,0,"callx", TRUE, 0xffffffff,0xffffffff,FALSE);
+
+static reloc_howto_type howto_align_table[] =
+{
+ HOWTO (ALIGNER, 0, 0x1, 0, FALSE, 0, complain_overflow_dont, 0, "align16", FALSE, 0, 0, FALSE),
+ HOWTO (ALIGNER, 0, 0x3, 0, FALSE, 0, complain_overflow_dont, 0, "align32", FALSE, 0, 0, FALSE),
+ HOWTO (ALIGNER, 0, 0x7, 0, FALSE, 0, complain_overflow_dont, 0, "align64", FALSE, 0, 0, FALSE),
+ HOWTO (ALIGNER, 0, 0xf, 0, FALSE, 0, complain_overflow_dont, 0, "align128", FALSE, 0, 0, FALSE),
+};
+
+static reloc_howto_type howto_done_align_table[] =
+{
+ HOWTO (ALIGNDONE, 0x1, 0x1, 0, FALSE, 0, complain_overflow_dont, 0, "donealign16", FALSE, 0, 0, FALSE),
+ HOWTO (ALIGNDONE, 0x3, 0x3, 0, FALSE, 0, complain_overflow_dont, 0, "donealign32", FALSE, 0, 0, FALSE),
+ HOWTO (ALIGNDONE, 0x7, 0x7, 0, FALSE, 0, complain_overflow_dont, 0, "donealign64", FALSE, 0, 0, FALSE),
+ HOWTO (ALIGNDONE, 0xf, 0xf, 0, FALSE, 0, complain_overflow_dont, 0, "donealign128", FALSE, 0, 0, FALSE),
+};
/* Swaps the information in an executable header taken from a raw byte
stream memory image, into the internal exec_header structure. */
-void
-bout_swap_exec_header_in (abfd, raw_bytes, execp)
- bfd *abfd;
- struct external_exec *raw_bytes;
- struct internal_exec *execp;
+static void
+bout_swap_exec_header_in (bfd *abfd,
+ struct external_exec *bytes,
+ struct internal_exec *execp)
{
- struct external_exec *bytes = (struct external_exec *)raw_bytes;
-
/* Now fill in fields in the execp, from the bytes in the raw data. */
- execp->a_info = H_GET_32 (abfd, bytes->e_info);
- execp->a_text = GET_WORD (abfd, bytes->e_text);
- execp->a_data = GET_WORD (abfd, bytes->e_data);
- execp->a_bss = GET_WORD (abfd, bytes->e_bss);
- execp->a_syms = GET_WORD (abfd, bytes->e_syms);
- execp->a_entry = GET_WORD (abfd, bytes->e_entry);
- execp->a_trsize = GET_WORD (abfd, bytes->e_trsize);
- execp->a_drsize = GET_WORD (abfd, bytes->e_drsize);
- execp->a_tload = GET_WORD (abfd, bytes->e_tload);
- execp->a_dload = GET_WORD (abfd, bytes->e_dload);
- execp->a_talign = bytes->e_talign[0];
- execp->a_dalign = bytes->e_dalign[0];
- execp->a_balign = bytes->e_balign[0];
+ execp->a_info = H_GET_32 (abfd, bytes->e_info);
+ execp->a_text = GET_WORD (abfd, bytes->e_text);
+ execp->a_data = GET_WORD (abfd, bytes->e_data);
+ execp->a_bss = GET_WORD (abfd, bytes->e_bss);
+ execp->a_syms = GET_WORD (abfd, bytes->e_syms);
+ execp->a_entry = GET_WORD (abfd, bytes->e_entry);
+ execp->a_trsize = GET_WORD (abfd, bytes->e_trsize);
+ execp->a_drsize = GET_WORD (abfd, bytes->e_drsize);
+ execp->a_tload = GET_WORD (abfd, bytes->e_tload);
+ execp->a_dload = GET_WORD (abfd, bytes->e_dload);
+ execp->a_talign = bytes->e_talign[0];
+ execp->a_dalign = bytes->e_dalign[0];
+ execp->a_balign = bytes->e_balign[0];
execp->a_relaxable = bytes->e_relaxable[0];
}
/* Swaps the information in an internal exec header structure into the
supplied buffer ready for writing to disk. */
-void
-bout_swap_exec_header_out (abfd, execp, raw_bytes)
- bfd *abfd;
- struct internal_exec *execp;
- struct external_exec *raw_bytes;
+static void
+bout_swap_exec_header_out (bfd *abfd,
+ struct internal_exec *execp,
+ struct external_exec *bytes)
{
- struct external_exec *bytes = (struct external_exec *)raw_bytes;
-
/* Now fill in fields in the raw data, from the fields in the exec struct. */
H_PUT_32 (abfd, execp->a_info , bytes->e_info);
PUT_WORD (abfd, execp->a_text , bytes->e_text);
PUT_WORD (abfd, execp->a_drsize, bytes->e_drsize);
PUT_WORD (abfd, execp->a_tload , bytes->e_tload);
PUT_WORD (abfd, execp->a_dload , bytes->e_dload);
- bytes->e_talign[0] = execp->a_talign;
- bytes->e_dalign[0] = execp->a_dalign;
- bytes->e_balign[0] = execp->a_balign;
+ bytes->e_talign[0] = execp->a_talign;
+ bytes->e_dalign[0] = execp->a_dalign;
+ bytes->e_balign[0] = execp->a_balign;
bytes->e_relaxable[0] = execp->a_relaxable;
}
-static const bfd_target *
-b_out_object_p (abfd)
- bfd *abfd;
-{
- struct internal_exec anexec;
- struct external_exec exec_bytes;
- bfd_size_type amt = EXEC_BYTES_SIZE;
-
- if (bfd_bread ((PTR) &exec_bytes, amt, abfd) != amt)
- {
- if (bfd_get_error () != bfd_error_system_call)
- bfd_set_error (bfd_error_wrong_format);
- return 0;
- }
-
- anexec.a_info = H_GET_32 (abfd, exec_bytes.e_info);
-
- if (N_BADMAG (anexec))
- {
- bfd_set_error (bfd_error_wrong_format);
- return 0;
- }
-
- bout_swap_exec_header_in (abfd, &exec_bytes, &anexec);
- return aout_32_some_aout_object_p (abfd, &anexec, b_out_callback);
-}
-
/* Finish up the opening of a b.out file for reading. Fill in all the
fields that are not handled by common code. */
static const bfd_target *
-b_out_callback (abfd)
- bfd *abfd;
+b_out_callback (bfd *abfd)
{
struct internal_exec *execp = exec_hdr (abfd);
unsigned long bss_start;
/* Architecture and machine type. */
- bfd_set_arch_mach(abfd,
- bfd_arch_i960, /* B.out only used on i960 */
- bfd_mach_i960_core /* Default */
- );
+ bfd_set_arch_mach (abfd,
+ bfd_arch_i960, /* B.out only used on i960. */
+ bfd_mach_i960_core /* Default. */
+ );
/* The positions of the string table and symbol table. */
obj_str_filepos (abfd) = N_STROFF (*execp);
/* And reload the sizes, since the aout module zaps them. */
obj_textsec (abfd)->size = execp->a_text;
- bss_start = execp->a_dload + execp->a_data; /* BSS = end of data section */
+ bss_start = execp->a_dload + execp->a_data; /* BSS = end of data section. */
obj_bsssec (abfd)->vma = align_power (bss_start, execp->a_balign);
obj_bsssec (abfd)->lma = obj_bsssec (abfd)->vma;
/* The file positions of the sections. */
- obj_textsec (abfd)->filepos = N_TXTOFF(*execp);
- obj_datasec (abfd)->filepos = N_DATOFF(*execp);
+ obj_textsec (abfd)->filepos = N_TXTOFF (*execp);
+ obj_datasec (abfd)->filepos = N_DATOFF (*execp);
/* The file positions of the relocation info. */
- obj_textsec (abfd)->rel_filepos = N_TROFF(*execp);
- obj_datasec (abfd)->rel_filepos = N_DROFF(*execp);
+ obj_textsec (abfd)->rel_filepos = N_TROFF (*execp);
+ obj_datasec (abfd)->rel_filepos = N_DROFF (*execp);
- adata(abfd).page_size = 1; /* Not applicable. */
- adata(abfd).segment_size = 1; /* Not applicable. */
- adata(abfd).exec_bytes_size = EXEC_BYTES_SIZE;
+ adata (abfd).page_size = 1; /* Not applicable. */
+ adata (abfd).segment_size = 1; /* Not applicable. */
+ adata (abfd).exec_bytes_size = EXEC_BYTES_SIZE;
if (execp->a_relaxable)
abfd->flags |= BFD_IS_RELAXABLE;
return abfd->xvec;
}
+static const bfd_target *
+b_out_object_p (bfd *abfd)
+{
+ struct internal_exec anexec;
+ struct external_exec exec_bytes;
+ bfd_size_type amt = EXEC_BYTES_SIZE;
+
+ if (bfd_bread ((void *) &exec_bytes, amt, abfd) != amt)
+ {
+ if (bfd_get_error () != bfd_error_system_call)
+ bfd_set_error (bfd_error_wrong_format);
+ return 0;
+ }
+
+ anexec.a_info = H_GET_32 (abfd, exec_bytes.e_info);
+
+ if (N_BADMAG (anexec))
+ {
+ bfd_set_error (bfd_error_wrong_format);
+ return 0;
+ }
+
+ bout_swap_exec_header_in (abfd, &exec_bytes, &anexec);
+ return aout_32_some_aout_object_p (abfd, &anexec, b_out_callback);
+}
+
struct bout_data_struct
{
struct aoutdata a;
};
static bfd_boolean
-b_out_mkobject (abfd)
- bfd *abfd;
+b_out_mkobject (bfd *abfd)
{
struct bout_data_struct *rawptr;
bfd_size_type amt = sizeof (struct bout_data_struct);
- rawptr = (struct bout_data_struct *) bfd_zalloc (abfd, amt);
+ rawptr = bfd_zalloc (abfd, amt);
if (rawptr == NULL)
return FALSE;
abfd->tdata.bout_data = rawptr;
exec_hdr (abfd) = &rawptr->e;
- obj_textsec (abfd) = (asection *) NULL;
- obj_datasec (abfd) = (asection *) NULL;
- obj_bsssec (abfd) = (asection *) NULL;
+ obj_textsec (abfd) = NULL;
+ obj_datasec (abfd) = NULL;
+ obj_bsssec (abfd) = NULL;
return TRUE;
}
static int
-b_out_symbol_cmp (a_ptr, b_ptr)
- const void * a_ptr;
- const void * b_ptr;
+b_out_symbol_cmp (const void * a_ptr, const void * b_ptr)
{
struct aout_symbol ** a = (struct aout_symbol **) a_ptr;
struct aout_symbol ** b = (struct aout_symbol **) b_ptr;
if (av > bv)
return 1;
- /* Secondary key puts CALLNAME syms last and BALNAME syms first, so
- that they have the best chance of being contiguous. */
+ /* Secondary key puts CALLNAME syms last and BALNAME syms first,
+ so that they have the best chance of being contiguous. */
if (IS_BALNAME ((*a)->other) || IS_CALLNAME ((*b)->other))
return -1;
if (IS_CALLNAME ((*a)->other) || IS_BALNAME ((*b)->other))
}
static bfd_boolean
-b_out_write_object_contents (abfd)
- bfd *abfd;
+b_out_squirt_out_relocs (bfd *abfd, asection *section)
+{
+ arelent **generic;
+ int r_extern = 0;
+ int r_idx;
+ int incode_mask;
+ int len_1;
+ unsigned int count = section->reloc_count;
+ struct relocation_info *native, *natptr;
+ bfd_size_type natsize;
+ int extern_mask, pcrel_mask, len_2, callj_mask;
+
+ if (count == 0)
+ return TRUE;
+
+ generic = section->orelocation;
+ natsize = (bfd_size_type) count * sizeof (struct relocation_info);
+ native = bfd_malloc (natsize);
+ if (!native && natsize != 0)
+ return FALSE;
+
+ if (bfd_header_big_endian (abfd))
+ {
+ /* Big-endian bit field allocation order. */
+ pcrel_mask = 0x80;
+ extern_mask = 0x10;
+ len_2 = 0x40;
+ len_1 = 0x20;
+ callj_mask = 0x02;
+ incode_mask = 0x08;
+ }
+ else
+ {
+ /* Little-endian bit field allocation order. */
+ pcrel_mask = 0x01;
+ extern_mask = 0x08;
+ len_2 = 0x04;
+ len_1 = 0x02;
+ callj_mask = 0x40;
+ incode_mask = 0x10;
+ }
+
+ for (natptr = native; count > 0; --count, ++natptr, ++generic)
+ {
+ arelent *g = *generic;
+ unsigned char *raw = (unsigned char *) natptr;
+ asymbol *sym = *(g->sym_ptr_ptr);
+ asection *output_section = sym->section->output_section;
+
+ H_PUT_32 (abfd, g->address, raw);
+ /* Find a type in the output format which matches the input howto -
+ at the moment we assume input format == output format FIXME!! */
+ r_idx = 0;
+ /* FIXME: Need callj stuff here, and to check the howto entries to
+ be sure they are real for this architecture. */
+ if (g->howto== &howto_reloc_callj)
+ raw[7] = callj_mask + pcrel_mask + len_2;
+ else if (g->howto == &howto_reloc_pcrel24)
+ raw[7] = pcrel_mask + len_2;
+ else if (g->howto == &howto_reloc_pcrel13)
+ raw[7] = pcrel_mask + len_1;
+ else if (g->howto == &howto_reloc_abs32code)
+ raw[7] = len_2 + incode_mask;
+ else if (g->howto >= howto_align_table
+ && g->howto <= (howto_align_table + ARRAY_SIZE (howto_align_table) - 1))
+ {
+ /* symnum == -2; extern_mask not set, pcrel_mask set. */
+ r_idx = -2;
+ r_extern = 0;
+ raw[7] = (pcrel_mask
+ | ((g->howto - howto_align_table) << 1));
+ }
+ else
+ raw[7] = len_2;
+
+ if (r_idx != 0)
+ /* Already mucked with r_extern, r_idx. */;
+ else if (bfd_is_com_section (output_section)
+ || bfd_is_abs_section (output_section)
+ || bfd_is_und_section (output_section))
+ {
+ if (bfd_abs_section_ptr->symbol == sym)
+ {
+ /* Whoops, looked like an abs symbol, but is really an offset
+ from the abs section. */
+ r_idx = 0;
+ r_extern = 0;
+ }
+ else
+ {
+ /* Fill in symbol. */
+ r_extern = 1;
+ r_idx = (*g->sym_ptr_ptr)->udata.i;
+ }
+ }
+ else
+ {
+ /* Just an ordinary section. */
+ r_extern = 0;
+ r_idx = output_section->target_index;
+ }
+
+ if (bfd_header_big_endian (abfd))
+ {
+ raw[4] = (unsigned char) (r_idx >> 16);
+ raw[5] = (unsigned char) (r_idx >> 8);
+ raw[6] = (unsigned char) (r_idx );
+ }
+ else
+ {
+ raw[6] = (unsigned char) (r_idx >> 16);
+ raw[5] = (unsigned char) (r_idx>> 8);
+ raw[4] = (unsigned char) (r_idx );
+ }
+
+ if (r_extern)
+ raw[7] |= extern_mask;
+ }
+
+ if (bfd_bwrite ((void *) native, natsize, abfd) != natsize)
+ {
+ free (native);
+ return FALSE;
+ }
+
+ free (native);
+
+ return TRUE;
+}
+
+static bfd_boolean
+b_out_write_object_contents (bfd *abfd)
{
struct external_exec swapped_hdr;
bfd_size_type amt;
amt = EXEC_BYTES_SIZE;
if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) != 0
- || bfd_bwrite ((PTR) &swapped_hdr, amt, abfd) != amt)
+ || bfd_bwrite ((void *) &swapped_hdr, amt, abfd) != amt)
return FALSE;
/* Now write out reloc info, followed by syms and strings */
b_out_symbol_cmp);
/* Back to your regularly scheduled program. */
- if (bfd_seek (abfd, (file_ptr) (N_SYMOFF(*exec_hdr(abfd))), SEEK_SET)
+ if (bfd_seek (abfd, (file_ptr) (N_SYMOFF (*exec_hdr (abfd))), SEEK_SET)
!= 0)
return FALSE;
if (! aout_32_write_syms (abfd))
return FALSE;
- if (bfd_seek (abfd, (file_ptr) (N_TROFF(*exec_hdr(abfd))), SEEK_SET)
+ if (bfd_seek (abfd, (file_ptr) (N_TROFF (*exec_hdr (abfd))), SEEK_SET)
!= 0)
return FALSE;
if (!b_out_squirt_out_relocs (abfd, obj_textsec (abfd)))
return FALSE;
- if (bfd_seek (abfd, (file_ptr) (N_DROFF(*exec_hdr(abfd))), SEEK_SET)
+ if (bfd_seek (abfd, (file_ptr) (N_DROFF (*exec_hdr (abfd))), SEEK_SET)
!= 0)
return FALSE;
#define output_addr(sec) ((sec)->output_offset+(sec)->output_section->vma)
+static bfd_vma
+get_value (arelent *reloc,
+ struct bfd_link_info *link_info,
+ asection *input_section)
+{
+ bfd_vma value;
+ asymbol *symbol = *(reloc->sym_ptr_ptr);
+
+ /* A symbol holds a pointer to a section, and an offset from the
+ base of the section. To relocate, we find where the section will
+ live in the output and add that in. */
+ if (bfd_is_und_section (symbol->section))
+ {
+ struct bfd_link_hash_entry *h;
+
+ /* The symbol is undefined in this BFD. Look it up in the
+ global linker hash table. FIXME: This should be changed when
+ we convert b.out to use a specific final_link function and
+ change the interface to bfd_relax_section to not require the
+ generic symbols. */
+ h = bfd_wrapped_link_hash_lookup (input_section->owner, link_info,
+ bfd_asymbol_name (symbol),
+ FALSE, FALSE, TRUE);
+ if (h != (struct bfd_link_hash_entry *) NULL
+ && (h->type == bfd_link_hash_defined
+ || h->type == bfd_link_hash_defweak))
+ value = h->u.def.value + output_addr (h->u.def.section);
+ else if (h != (struct bfd_link_hash_entry *) NULL
+ && h->type == bfd_link_hash_common)
+ value = h->u.c.size;
+ else
+ {
+ if (! ((*link_info->callbacks->undefined_symbol)
+ (link_info, bfd_asymbol_name (symbol),
+ input_section->owner, input_section, reloc->address,
+ TRUE)))
+ abort ();
+ value = 0;
+ }
+ }
+ else
+ value = symbol->value + output_addr (symbol->section);
+
+ /* Add the value contained in the relocation. */
+ value += reloc->addend;
+
+ return value;
+}
+
/* Magic to turn callx into calljx. */
static bfd_reloc_status_type
-calljx_callback (abfd, link_info, reloc_entry, src, dst, input_section)
- bfd *abfd;
- struct bfd_link_info *link_info;
- arelent *reloc_entry;
- PTR src;
- PTR dst;
- asection *input_section;
+calljx_callback (bfd *abfd,
+ struct bfd_link_info *link_info,
+ arelent *reloc_entry,
+ void * src,
+ void * dst,
+ asection *input_section)
{
int word = bfd_get_32 (abfd, src);
asymbol *symbol_in = *(reloc_entry->sym_ptr_ptr);
{
aout_symbol_type *balsym = symbol+1;
int inst = bfd_get_32 (abfd, (bfd_byte *) src-4);
+
/* The next symbol should be an N_BALNAME. */
BFD_ASSERT (IS_BALNAME (balsym->other));
inst &= BALX_MASK;
/* Magic to turn call into callj. */
static bfd_reloc_status_type
-callj_callback (abfd, link_info, reloc_entry, data, srcidx, dstidx,
- input_section, shrinking)
- bfd *abfd;
- struct bfd_link_info *link_info;
- arelent *reloc_entry;
- PTR data;
- unsigned int srcidx;
- unsigned int dstidx;
- asection *input_section;
- bfd_boolean shrinking;
+callj_callback (bfd *abfd,
+ struct bfd_link_info *link_info,
+ arelent *reloc_entry,
+ void * data,
+ unsigned int srcidx,
+ unsigned int dstidx,
+ asection *input_section,
+ bfd_boolean shrinking)
{
int word = bfd_get_32 (abfd, (bfd_byte *) data + srcidx);
asymbol *symbol_in = *(reloc_entry->sym_ptr_ptr);
value = get_value (reloc_entry, link_info, input_section);
- if (IS_OTHER(symbol->other))
- {
- /* Call to a system procedure - replace code with system
- procedure number. */
- word = CALLS | (symbol->other - 1);
- }
- else if (IS_CALLNAME(symbol->other))
+ if (IS_OTHER (symbol->other))
+ /* Call to a system procedure - replace code with system
+ procedure number. */
+ word = CALLS | (symbol->other - 1);
+
+ else if (IS_CALLNAME (symbol->other))
{
aout_symbol_type *balsym = symbol+1;
/* The next symbol should be an N_BALNAME. */
- BFD_ASSERT(IS_BALNAME(balsym->other));
+ BFD_ASSERT (IS_BALNAME (balsym->other));
/* We are calling a leaf, so replace the call instruction with a
bal. */
BFD_ASSERT (symbol->symbol.section == input_section);
}
else
- {
- word = CALL | (((word & BAL_MASK)
- + value
- + reloc_entry->addend
- - (shrinking ? dstidx : 0)
- - output_addr (input_section))
- & BAL_MASK);
- }
+ word = CALL | (((word & BAL_MASK)
+ + value
+ + reloc_entry->addend
+ - (shrinking ? dstidx : 0)
+ - output_addr (input_section))
+ & BAL_MASK);
+
bfd_put_32 (abfd, (bfd_vma) word, (bfd_byte *) data + dstidx);
return bfd_reloc_ok;
}
-/* type rshift size bitsize pcrel bitpos absolute overflow check*/
-
-#define ABS32CODE 0
-#define ABS32CODE_SHRUNK 1
-#define PCREL24 2
-#define CALLJ 3
-#define ABS32 4
-#define PCREL13 5
-#define ABS32_MAYBE_RELAXABLE 1
-#define ABS32_WAS_RELAXABLE 2
-
-#define ALIGNER 10
-#define ALIGNDONE 11
-static reloc_howto_type howto_reloc_callj =
-HOWTO(CALLJ, 0, 2, 24, TRUE, 0, complain_overflow_signed, 0,"callj", TRUE, 0x00ffffff, 0x00ffffff,FALSE);
-static reloc_howto_type howto_reloc_abs32 =
-HOWTO(ABS32, 0, 2, 32, FALSE, 0, complain_overflow_bitfield,0,"abs32", TRUE, 0xffffffff,0xffffffff,FALSE);
-static reloc_howto_type howto_reloc_pcrel24 =
-HOWTO(PCREL24, 0, 2, 24, TRUE, 0, complain_overflow_signed,0,"pcrel24", TRUE, 0x00ffffff,0x00ffffff,FALSE);
-
-static reloc_howto_type howto_reloc_pcrel13 =
-HOWTO(PCREL13, 0, 2, 13, TRUE, 0, complain_overflow_signed,0,"pcrel13", TRUE, 0x00001fff,0x00001fff,FALSE);
-
-static reloc_howto_type howto_reloc_abs32codeshrunk =
-HOWTO(ABS32CODE_SHRUNK, 0, 2, 24, TRUE, 0, complain_overflow_signed, 0,"callx->callj", TRUE, 0x00ffffff, 0x00ffffff,FALSE);
-
-static reloc_howto_type howto_reloc_abs32code =
-HOWTO(ABS32CODE, 0, 2, 32, FALSE, 0, complain_overflow_bitfield,0,"callx", TRUE, 0xffffffff,0xffffffff,FALSE);
-
-static reloc_howto_type howto_align_table[] = {
- HOWTO (ALIGNER, 0, 0x1, 0, FALSE, 0, complain_overflow_dont, 0, "align16", FALSE, 0, 0, FALSE),
- HOWTO (ALIGNER, 0, 0x3, 0, FALSE, 0, complain_overflow_dont, 0, "align32", FALSE, 0, 0, FALSE),
- HOWTO (ALIGNER, 0, 0x7, 0, FALSE, 0, complain_overflow_dont, 0, "align64", FALSE, 0, 0, FALSE),
- HOWTO (ALIGNER, 0, 0xf, 0, FALSE, 0, complain_overflow_dont, 0, "align128", FALSE, 0, 0, FALSE),
-};
-
-static reloc_howto_type howto_done_align_table[] = {
- HOWTO (ALIGNDONE, 0x1, 0x1, 0, FALSE, 0, complain_overflow_dont, 0, "donealign16", FALSE, 0, 0, FALSE),
- HOWTO (ALIGNDONE, 0x3, 0x3, 0, FALSE, 0, complain_overflow_dont, 0, "donealign32", FALSE, 0, 0, FALSE),
- HOWTO (ALIGNDONE, 0x7, 0x7, 0, FALSE, 0, complain_overflow_dont, 0, "donealign64", FALSE, 0, 0, FALSE),
- HOWTO (ALIGNDONE, 0xf, 0xf, 0, FALSE, 0, complain_overflow_dont, 0, "donealign128", FALSE, 0, 0, FALSE),
-};
-
static reloc_howto_type *
-b_out_bfd_reloc_type_lookup (abfd, code)
- bfd *abfd ATTRIBUTE_UNUSED;
- bfd_reloc_code_real_type code;
+b_out_bfd_reloc_type_lookup (bfd *abfd ATTRIBUTE_UNUSED, bfd_reloc_code_real_type code)
{
switch (code)
{
/* Allocate enough room for all the reloc entries, plus pointers to them all. */
static bfd_boolean
-b_out_slurp_reloc_table (abfd, asect, symbols)
- bfd *abfd;
- sec_ptr asect;
- asymbol **symbols;
+b_out_slurp_reloc_table (bfd *abfd, sec_ptr asect, asymbol **symbols)
{
- register struct relocation_info *rptr;
+ struct relocation_info *rptr;
unsigned int counter;
arelent *cache_ptr;
int extern_mask, pcrel_mask, callj_mask, length_shift;
return FALSE;
if (asect == obj_datasec (abfd))
+ reloc_size = exec_hdr (abfd)->a_drsize;
+ else if (asect == obj_textsec (abfd))
+ reloc_size = exec_hdr (abfd)->a_trsize;
+ else if (asect == obj_bsssec (abfd))
+ reloc_size = 0;
+ else
{
- reloc_size = exec_hdr(abfd)->a_drsize;
- goto doit;
- }
-
- if (asect == obj_textsec (abfd))
- {
- reloc_size = exec_hdr(abfd)->a_trsize;
- goto doit;
- }
-
- if (asect == obj_bsssec (abfd))
- {
- reloc_size = 0;
- goto doit;
+ bfd_set_error (bfd_error_invalid_operation);
+ return FALSE;
}
- bfd_set_error (bfd_error_invalid_operation);
- return FALSE;
-
- doit:
if (bfd_seek (abfd, asect->rel_filepos, SEEK_SET) != 0)
return FALSE;
count = reloc_size / sizeof (struct relocation_info);
- relocs = (struct relocation_info *) bfd_malloc (reloc_size);
+ relocs = bfd_malloc (reloc_size);
if (!relocs && reloc_size != 0)
return FALSE;
amt = ((bfd_size_type) count + 1) * sizeof (arelent);
- reloc_cache = (arelent *) bfd_malloc (amt);
+ reloc_cache = bfd_malloc (amt);
if (!reloc_cache)
{
if (relocs != NULL)
return FALSE;
}
- if (bfd_bread ((PTR) relocs, reloc_size, abfd) != reloc_size)
+ if (bfd_bread ((void *) relocs, reloc_size, abfd) != reloc_size)
{
free (reloc_cache);
if (relocs != NULL)
cache_ptr->addend = 0;
break;
default:
- BFD_ASSERT(0);
+ BFD_ASSERT (FALSE);
break;
}
}
cursor[1] = tmp;
}
else
- {
- prev_addr = cache_ptr->address;
- }
+ prev_addr = cache_ptr->address;
}
if (relocs != NULL)
return TRUE;
}
-static bfd_boolean
-b_out_squirt_out_relocs (abfd, section)
- bfd *abfd;
- asection *section;
-{
- arelent **generic;
- int r_extern = 0;
- int r_idx;
- int incode_mask;
- int len_1;
- unsigned int count = section->reloc_count;
- struct relocation_info *native, *natptr;
- bfd_size_type natsize;
- int extern_mask, pcrel_mask, len_2, callj_mask;
-
- if (count == 0)
- return TRUE;
-
- generic = section->orelocation;
- natsize = (bfd_size_type) count * sizeof (struct relocation_info);
- native = ((struct relocation_info *) bfd_malloc (natsize));
- if (!native && natsize != 0)
- return FALSE;
-
- if (bfd_header_big_endian (abfd))
- {
- /* Big-endian bit field allocation order. */
- pcrel_mask = 0x80;
- extern_mask = 0x10;
- len_2 = 0x40;
- len_1 = 0x20;
- callj_mask = 0x02;
- incode_mask = 0x08;
- }
- else
- {
- /* Little-endian bit field allocation order. */
- pcrel_mask = 0x01;
- extern_mask = 0x08;
- len_2 = 0x04;
- len_1 = 0x02;
- callj_mask = 0x40;
- incode_mask = 0x10;
- }
-
- for (natptr = native; count > 0; --count, ++natptr, ++generic)
- {
- arelent *g = *generic;
- unsigned char *raw = (unsigned char *)natptr;
- asymbol *sym = *(g->sym_ptr_ptr);
- asection *output_section = sym->section->output_section;
-
- H_PUT_32 (abfd, g->address, raw);
- /* Find a type in the output format which matches the input howto -
- at the moment we assume input format == output format FIXME!! */
- r_idx = 0;
- /* FIXME: Need callj stuff here, and to check the howto entries to
- be sure they are real for this architecture. */
- if (g->howto== &howto_reloc_callj)
- raw[7] = callj_mask + pcrel_mask + len_2;
- else if (g->howto == &howto_reloc_pcrel24)
- raw[7] = pcrel_mask + len_2;
- else if (g->howto == &howto_reloc_pcrel13)
- raw[7] = pcrel_mask + len_1;
- else if (g->howto == &howto_reloc_abs32code)
- raw[7] = len_2 + incode_mask;
- else if (g->howto >= howto_align_table
- && g->howto <= (howto_align_table
- + sizeof (howto_align_table) / sizeof (howto_align_table[0])
- - 1))
- {
- /* symnum == -2; extern_mask not set, pcrel_mask set. */
- r_idx = -2;
- r_extern = 0;
- raw[7] = (pcrel_mask
- | ((g->howto - howto_align_table) << 1));
- }
- else
- raw[7] = len_2;
-
- if (r_idx != 0)
- /* Already mucked with r_extern, r_idx. */;
- else if (bfd_is_com_section (output_section)
- || bfd_is_abs_section (output_section)
- || bfd_is_und_section (output_section))
- {
- if (bfd_abs_section_ptr->symbol == sym)
- {
- /* Whoops, looked like an abs symbol, but is really an offset
- from the abs section. */
- r_idx = 0;
- r_extern = 0;
- }
- else
- {
- /* Fill in symbol. */
- r_extern = 1;
- r_idx = (*g->sym_ptr_ptr)->udata.i;
- }
- }
- else
- {
- /* Just an ordinary section. */
- r_extern = 0;
- r_idx = output_section->target_index;
- }
-
- if (bfd_header_big_endian (abfd))
- {
- raw[4] = (unsigned char) (r_idx >> 16);
- raw[5] = (unsigned char) (r_idx >> 8);
- raw[6] = (unsigned char) (r_idx );
- }
- else
- {
- raw[6] = (unsigned char) (r_idx >> 16);
- raw[5] = (unsigned char) (r_idx>> 8);
- raw[4] = (unsigned char) (r_idx );
- }
-
- if (r_extern)
- raw[7] |= extern_mask;
- }
-
- if (bfd_bwrite ((PTR) native, natsize, abfd) != natsize)
- {
- free ((PTR)native);
- return FALSE;
- }
-
- free ((PTR)native);
-
- return TRUE;
-}
-
/* This is stupid. This function should be a boolean predicate. */
static long
-b_out_canonicalize_reloc (abfd, section, relptr, symbols)
- bfd *abfd;
- sec_ptr section;
- arelent **relptr;
- asymbol **symbols;
+b_out_canonicalize_reloc (bfd *abfd,
+ sec_ptr section,
+ arelent **relptr,
+ asymbol **symbols)
{
arelent *tblptr;
unsigned int count;
}
static long
-b_out_get_reloc_upper_bound (abfd, asect)
- bfd *abfd;
- sec_ptr asect;
+b_out_get_reloc_upper_bound (bfd *abfd, sec_ptr asect)
{
if (bfd_get_format (abfd) != bfd_object)
{
if (asect == obj_datasec (abfd))
return (sizeof (arelent *) *
- ((exec_hdr(abfd)->a_drsize / sizeof (struct relocation_info))
- +1));
+ ((exec_hdr (abfd)->a_drsize / sizeof (struct relocation_info))
+ + 1));
if (asect == obj_textsec (abfd))
return (sizeof (arelent *) *
- ((exec_hdr(abfd)->a_trsize / sizeof (struct relocation_info))
- +1));
+ ((exec_hdr (abfd)->a_trsize / sizeof (struct relocation_info))
+ + 1));
if (asect == obj_bsssec (abfd))
return 0;
\f
static bfd_boolean
-b_out_set_section_contents (abfd, section, location, offset, count)
- bfd *abfd;
- asection *section;
- const PTR location;
- file_ptr offset;
- bfd_size_type count;
+b_out_set_section_contents (bfd *abfd,
+ asection *section,
+ const void * location,
+ file_ptr offset,
+ bfd_size_type count)
{
if (! abfd->output_has_begun)
{
return FALSE;
obj_textsec (abfd)->filepos = sizeof (struct external_exec);
- obj_datasec(abfd)->filepos = obj_textsec(abfd)->filepos
+ obj_datasec (abfd)->filepos = obj_textsec (abfd)->filepos
+ obj_textsec (abfd)->size;
}
if (count == 0)
return TRUE;
- return bfd_bwrite ((PTR) location, count, abfd) == count;
+ return bfd_bwrite ((void *) location, count, abfd) == count;
}
static bfd_boolean
-b_out_set_arch_mach (abfd, arch, machine)
- bfd *abfd;
- enum bfd_architecture arch;
- unsigned long machine;
+b_out_set_arch_mach (bfd *abfd,
+ enum bfd_architecture arch,
+ unsigned long machine)
{
- bfd_default_set_arch_mach(abfd, arch, machine);
+ bfd_default_set_arch_mach (abfd, arch, machine);
if (arch == bfd_arch_unknown) /* Unknown machine arch is OK. */
return TRUE;
}
static int
-b_out_sizeof_headers (ignore_abfd, ignore)
- bfd *ignore_abfd ATTRIBUTE_UNUSED;
- bfd_boolean ignore ATTRIBUTE_UNUSED;
+b_out_sizeof_headers (bfd *ignore_abfd ATTRIBUTE_UNUSED, bfd_boolean ignore ATTRIBUTE_UNUSED)
{
return sizeof (struct external_exec);
}
\f
-
-static bfd_vma
-get_value (reloc, link_info, input_section)
- arelent *reloc;
- struct bfd_link_info *link_info;
- asection *input_section;
-{
- bfd_vma value;
- asymbol *symbol = *(reloc->sym_ptr_ptr);
-
- /* A symbol holds a pointer to a section, and an offset from the
- base of the section. To relocate, we find where the section will
- live in the output and add that in. */
- if (bfd_is_und_section (symbol->section))
- {
- struct bfd_link_hash_entry *h;
-
- /* The symbol is undefined in this BFD. Look it up in the
- global linker hash table. FIXME: This should be changed when
- we convert b.out to use a specific final_link function and
- change the interface to bfd_relax_section to not require the
- generic symbols. */
- h = bfd_wrapped_link_hash_lookup (input_section->owner, link_info,
- bfd_asymbol_name (symbol),
- FALSE, FALSE, TRUE);
- if (h != (struct bfd_link_hash_entry *) NULL
- && (h->type == bfd_link_hash_defined
- || h->type == bfd_link_hash_defweak))
- value = h->u.def.value + output_addr (h->u.def.section);
- else if (h != (struct bfd_link_hash_entry *) NULL
- && h->type == bfd_link_hash_common)
- value = h->u.c.size;
- else
- {
- if (! ((*link_info->callbacks->undefined_symbol)
- (link_info, bfd_asymbol_name (symbol),
- input_section->owner, input_section, reloc->address,
- TRUE)))
- abort ();
- value = 0;
- }
- }
- else
- {
- value = symbol->value + output_addr (symbol->section);
- }
-
- /* Add the value contained in the relocation. */
- value += reloc->addend;
-
- return value;
-}
-
static void
-perform_slip (abfd, slip, input_section, value)
- bfd *abfd;
- unsigned int slip;
- asection *input_section;
- bfd_vma value;
+perform_slip (bfd *abfd,
+ unsigned int slip,
+ asection *input_section,
+ bfd_vma value)
{
asymbol **s;
If it can, then it changes the amode. */
static int
-abs32code (abfd, input_section, r, shrink, link_info)
- bfd *abfd;
- asection *input_section;
- arelent *r;
- unsigned int shrink;
- struct bfd_link_info *link_info;
+abs32code (bfd *abfd,
+ asection *input_section,
+ arelent *r,
+ unsigned int shrink,
+ struct bfd_link_info *link_info)
{
bfd_vma value = get_value (r, link_info, input_section);
bfd_vma dot = output_addr (input_section) + r->address;
}
static int
-aligncode (abfd, input_section, r, shrink)
- bfd *abfd;
- asection *input_section;
- arelent *r;
- unsigned int shrink;
+aligncode (bfd *abfd,
+ asection *input_section,
+ arelent *r,
+ unsigned int shrink)
{
bfd_vma dot = output_addr (input_section) + r->address;
bfd_vma gap;
}
static bfd_boolean
-b_out_bfd_relax_section (abfd, i, link_info, again)
- bfd *abfd;
- asection *i;
- struct bfd_link_info *link_info;
- bfd_boolean *again;
+b_out_bfd_relax_section (bfd *abfd,
+ asection *i,
+ struct bfd_link_info *link_info,
+ bfd_boolean *again)
{
/* Get enough memory to hold the stuff. */
bfd *input_bfd = i->owner;
asection *input_section = i;
unsigned int shrink = 0 ;
arelent **reloc_vector = NULL;
- long reloc_size = bfd_get_reloc_upper_bound (input_bfd,
- input_section);
+ long reloc_size = bfd_get_reloc_upper_bound (input_bfd, input_section);
if (reloc_size < 0)
return FALSE;
{
long reloc_count;
- reloc_vector = (arelent **) bfd_malloc ((bfd_size_type) reloc_size);
+ reloc_vector = bfd_malloc ((bfd_size_type) reloc_size);
if (reloc_vector == NULL && reloc_size != 0)
goto error_return;
}
static bfd_byte *
-b_out_bfd_get_relocated_section_contents (output_bfd, link_info, link_order,
- data, relocatable, symbols)
- bfd *output_bfd;
- struct bfd_link_info *link_info;
- struct bfd_link_order *link_order;
- bfd_byte *data;
- bfd_boolean relocatable;
- asymbol **symbols;
+b_out_bfd_get_relocated_section_contents (bfd *output_bfd,
+ struct bfd_link_info *link_info,
+ struct bfd_link_order *link_order,
+ bfd_byte *data,
+ bfd_boolean relocatable,
+ asymbol **symbols)
{
/* Get enough memory to hold the stuff. */
bfd *input_bfd = link_order->u.indirect.section->owner;
asection *input_section = link_order->u.indirect.section;
- long reloc_size = bfd_get_reloc_upper_bound (input_bfd,
- input_section);
+ long reloc_size = bfd_get_reloc_upper_bound (input_bfd, input_section);
arelent **reloc_vector = NULL;
long reloc_count;
data, relocatable,
symbols);
- reloc_vector = (arelent **) bfd_malloc ((bfd_size_type) reloc_size);
+ reloc_vector = bfd_malloc ((bfd_size_type) reloc_size);
if (reloc_vector == NULL && reloc_size != 0)
goto error_return;
parent++;
}
else
- {
- run = link_order->size - dst_address;
- }
+ run = link_order->size - dst_address;
/* Copy the bytes. */
for (idx = 0; idx < run; idx++)
/* Build the transfer vectors for Big and Little-Endian B.OUT files. */
-#define aout_32_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
-#define aout_32_close_and_cleanup aout_32_bfd_free_cached_info
-
-#define b_out_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
-#define b_out_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
-#define b_out_bfd_link_add_symbols _bfd_generic_link_add_symbols
-#define b_out_bfd_link_just_syms _bfd_generic_link_just_syms
-#define b_out_bfd_final_link _bfd_generic_final_link
-#define b_out_bfd_link_split_section _bfd_generic_link_split_section
-#define b_out_bfd_gc_sections bfd_generic_gc_sections
-#define b_out_bfd_merge_sections bfd_generic_merge_sections
-#define b_out_bfd_is_group_section bfd_generic_is_group_section
-#define b_out_bfd_discard_group bfd_generic_discard_group
-#define b_out_section_already_linked \
- _bfd_generic_section_already_linked
-
-#define aout_32_get_section_contents_in_window \
- _bfd_generic_get_section_contents_in_window
+#define aout_32_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
+#define aout_32_close_and_cleanup aout_32_bfd_free_cached_info
+#define b_out_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
+#define b_out_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
+#define b_out_bfd_link_add_symbols _bfd_generic_link_add_symbols
+#define b_out_bfd_link_just_syms _bfd_generic_link_just_syms
+#define b_out_bfd_final_link _bfd_generic_final_link
+#define b_out_bfd_link_split_section _bfd_generic_link_split_section
+#define b_out_bfd_gc_sections bfd_generic_gc_sections
+#define b_out_bfd_merge_sections bfd_generic_merge_sections
+#define b_out_bfd_is_group_section bfd_generic_is_group_section
+#define b_out_bfd_discard_group bfd_generic_discard_group
+#define b_out_section_already_linked _bfd_generic_section_already_linked
+#define aout_32_get_section_contents_in_window _bfd_generic_get_section_contents_in_window
extern const bfd_target b_out_vec_little_host;
const bfd_target b_out_vec_big_host =
{
- "b.out.big", /* name */
+ "b.out.big", /* Name. */
bfd_target_aout_flavour,
- BFD_ENDIAN_LITTLE, /* data byte order is little */
- BFD_ENDIAN_BIG, /* hdr byte order is big */
- (HAS_RELOC | EXEC_P | /* object flags */
+ BFD_ENDIAN_LITTLE, /* Data byte order. */
+ BFD_ENDIAN_BIG, /* Header byte order. */
+ (HAS_RELOC | EXEC_P | /* Object flags. */
HAS_LINENO | HAS_DEBUG |
HAS_SYMS | HAS_LOCALS | WP_TEXT | BFD_IS_RELAXABLE ),
(SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD | SEC_RELOC | SEC_CODE | SEC_DATA),
- '_', /* symbol leading char */
- ' ', /* ar_pad_char */
- 16, /* ar_max_namelen */
+ '_', /* Symbol leading char. */
+ ' ', /* AR_pad_char. */
+ 16, /* AR_max_namelen. */
bfd_getl64, bfd_getl_signed_64, bfd_putl64,
bfd_getl32, bfd_getl_signed_32, bfd_putl32,
- bfd_getl16, bfd_getl_signed_16, bfd_putl16, /* data */
+ bfd_getl16, bfd_getl_signed_16, bfd_putl16, /* Data. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* hdrs */
- {_bfd_dummy_target, b_out_object_p, /* bfd_check_format */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Headers. */
+ {_bfd_dummy_target, b_out_object_p, /* bfd_check_format. */
bfd_generic_archive_p, _bfd_dummy_target},
- {bfd_false, b_out_mkobject, /* bfd_set_format */
+ {bfd_false, b_out_mkobject, /* bfd_set_format. */
_bfd_generic_mkarchive, bfd_false},
- {bfd_false, b_out_write_object_contents, /* bfd_write_contents */
+ {bfd_false, b_out_write_object_contents, /* bfd_write_contents. */
_bfd_write_archive_contents, bfd_false},
BFD_JUMP_TABLE_GENERIC (aout_32),
& b_out_vec_little_host,
- (PTR) 0,
+ NULL
};
const bfd_target b_out_vec_little_host =
{
- "b.out.little", /* name */
+ "b.out.little", /* Name. */
bfd_target_aout_flavour,
- BFD_ENDIAN_LITTLE, /* data byte order is little */
- BFD_ENDIAN_LITTLE, /* header byte order is little */
- (HAS_RELOC | EXEC_P | /* object flags */
+ BFD_ENDIAN_LITTLE, /* Data byte order. */
+ BFD_ENDIAN_LITTLE, /* Header byte order. */
+ (HAS_RELOC | EXEC_P | /* Object flags. */
HAS_LINENO | HAS_DEBUG |
HAS_SYMS | HAS_LOCALS | WP_TEXT | BFD_IS_RELAXABLE ),
(SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD | SEC_RELOC | SEC_CODE | SEC_DATA),
- '_', /* symbol leading char */
- ' ', /* ar_pad_char */
- 16, /* ar_max_namelen */
+ '_', /* Symbol leading char. */
+ ' ', /* AR_pad_char. */
+ 16, /* AR_max_namelen. */
bfd_getl64, bfd_getl_signed_64, bfd_putl64,
bfd_getl32, bfd_getl_signed_32, bfd_putl32,
- bfd_getl16, bfd_getl_signed_16, bfd_putl16, /* data */
+ bfd_getl16, bfd_getl_signed_16, bfd_putl16, /* Data. */
bfd_getl64, bfd_getl_signed_64, bfd_putl64,
bfd_getl32, bfd_getl_signed_32, bfd_putl32,
- bfd_getl16, bfd_getl_signed_16, bfd_putl16, /* hdrs */
+ bfd_getl16, bfd_getl_signed_16, bfd_putl16, /* Headers. */
- {_bfd_dummy_target, b_out_object_p, /* bfd_check_format */
+ {_bfd_dummy_target, b_out_object_p, /* bfd_check_format. */
bfd_generic_archive_p, _bfd_dummy_target},
- {bfd_false, b_out_mkobject, /* bfd_set_format */
+ {bfd_false, b_out_mkobject, /* bfd_set_format. */
_bfd_generic_mkarchive, bfd_false},
- {bfd_false, b_out_write_object_contents, /* bfd_write_contents */
+ {bfd_false, b_out_write_object_contents, /* bfd_write_contents. */
_bfd_write_archive_contents, bfd_false},
BFD_JUMP_TABLE_GENERIC (aout_32),
& b_out_vec_big_host,
- (PTR) 0
+ NULL
};
/* DWARF 1 find nearest line (_bfd_dwarf1_find_nearest_line).
- Copyright 1998, 1999, 2000, 2001, 2002, 2004 Free Software Foundation, Inc.
+ Copyright 1998, 1999, 2000, 2001, 2002, 2004, 2005
+ Free Software Foundation, Inc.
-Written by Gavin Romig-Koch of Cygnus Solutions (gavin@cygnus.com).
+ Written by Gavin Romig-Koch of Cygnus Solutions (gavin@cygnus.com).
-This file is part of BFD.
+ This file is part of BFD.
-This program is free software; you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation; either version 2 of the License, or (at
-your option) any later version.
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or (at
+ your option) any later version.
-This program is distributed in the hope that it will be useful, but
-WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
-General Public License for more details.
+ This program is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
-You should have received a copy of the GNU General Public License
-along with this program; if not, write to the Free Software
-Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
#include "bfd.h"
#include "sysdep.h"
/* dwarf1_debug is the starting point for all dwarf1 info. */
-struct dwarf1_debug {
-
+struct dwarf1_debug
+{
/* The bfd we are working with. */
bfd* abfd;
/* One dwarf1_unit for each parsed compilation unit die. */
-struct dwarf1_unit {
+struct dwarf1_unit
+{
/* Linked starting from stash->lastUnit. */
struct dwarf1_unit* prev;
unsigned long low_pc;
unsigned long high_pc;
- /* Does this unit have a statement list? */
+ /* Does this unit have a statement list? */
int has_stmt_list;
/* If any, the offset of the line number table in the .line section. */
/* If non-zero, a pointer to the first child of this unit. */
char* first_child;
- /* How many line entries? */
+ /* How many line entries? */
unsigned long line_count;
/* The decoded line number table (line_count entries). */
/* One dwarf1_func for each parsed function die. */
-struct dwarf1_func {
+struct dwarf1_func
+{
/* Linked starting from aUnit->func_list. */
struct dwarf1_func* prev;
};
/* Used to return info about a parsed die. */
-struct die_info {
+struct die_info
+{
unsigned long length;
unsigned long sibling;
unsigned long low_pc;
};
/* Parsed line number information. */
-struct linenumber {
+struct linenumber
+{
/* First address in the line. */
unsigned long addr;
};
/* Find the form of an attr, from the attr field. */
-#define FORM_FROM_ATTR(attr) ((attr) & 0xF) /* Implicitly specified */
-
-static struct dwarf1_unit *alloc_dwarf1_unit
- PARAMS ((struct dwarf1_debug *));
-static struct dwarf1_func *alloc_dwarf1_func
- PARAMS ((struct dwarf1_debug *, struct dwarf1_unit *));
-static bfd_boolean parse_die
- PARAMS ((bfd *, struct die_info *, char *, char *));
-static bfd_boolean parse_line_table
- PARAMS ((struct dwarf1_debug *, struct dwarf1_unit *));
-static bfd_boolean parse_functions_in_unit
- PARAMS ((struct dwarf1_debug *, struct dwarf1_unit *));
-static bfd_boolean dwarf1_unit_find_nearest_line
- PARAMS ((struct dwarf1_debug *, struct dwarf1_unit *, unsigned long,
- const char **, const char **, unsigned int *));
+#define FORM_FROM_ATTR(attr) ((attr) & 0xF) /* Implicitly specified. */
/* Return a newly allocated dwarf1_unit. It should be cleared and
then attached into the 'stash' at 'stash->lastUnit'. */
static struct dwarf1_unit*
-alloc_dwarf1_unit (stash)
- struct dwarf1_debug* stash;
+alloc_dwarf1_unit (struct dwarf1_debug* stash)
{
bfd_size_type amt = sizeof (struct dwarf1_unit);
- struct dwarf1_unit* x = (struct dwarf1_unit*) bfd_zalloc (stash->abfd, amt);
+ struct dwarf1_unit* x = bfd_zalloc (stash->abfd, amt);
x->prev = stash->lastUnit;
stash->lastUnit = x;
/* Return a newly allocated dwarf1_func. It must be cleared and
attached into 'aUnit' at 'aUnit->func_list'. */
-static struct dwarf1_func*
-alloc_dwarf1_func (stash, aUnit)
- struct dwarf1_debug* stash;
- struct dwarf1_unit* aUnit;
+static struct dwarf1_func *
+alloc_dwarf1_func (struct dwarf1_debug* stash, struct dwarf1_unit* aUnit)
{
bfd_size_type amt = sizeof (struct dwarf1_func);
- struct dwarf1_func* x = (struct dwarf1_func*) bfd_zalloc (stash->abfd, amt);
+ struct dwarf1_func* x = bfd_zalloc (stash->abfd, amt);
x->prev = aUnit->func_list;
aUnit->func_list = x;
Return FALSE if the die is invalidly formatted; TRUE otherwise. */
static bfd_boolean
-parse_die (abfd, aDieInfo, aDiePtr, aDiePtrEnd)
- bfd* abfd;
- struct die_info* aDieInfo;
- char* aDiePtr;
- char* aDiePtrEnd;
+parse_die (bfd * abfd,
+ struct die_info * aDieInfo,
+ char * aDiePtr,
+ char * aDiePtrEnd)
{
char* this_die = aDiePtr;
char* xptr = this_die;
- memset (aDieInfo,0,sizeof (*aDieInfo));
+ memset (aDieInfo, 0, sizeof (* aDieInfo));
/* First comes the length. */
aDieInfo->length = bfd_get_32 (abfd, (bfd_byte *) xptr);
/* Parse the attribute based on its form. This section
must handle all dwarf1 forms, but need only handle the
actual attributes that we care about. */
-
attr = bfd_get_16 (abfd, (bfd_byte *) xptr);
xptr += 2;
occurs; TRUE otherwise. */
static bfd_boolean
-parse_line_table (stash, aUnit)
- struct dwarf1_debug* stash;
- struct dwarf1_unit* aUnit;
+parse_line_table (struct dwarf1_debug* stash, struct dwarf1_unit* aUnit)
{
char* xptr;
return FALSE;
size = msec->rawsize ? msec->rawsize : msec->size;
- stash->line_section = (char *) bfd_alloc (stash->abfd, size);
+ stash->line_section = bfd_alloc (stash->abfd, size);
if (! stash->line_section)
return FALSE;
xptr += 4;
/* How many line entrys?
- 10 = 4 (line number) + 2 (pos in line) + 4 (address in line) */
+ 10 = 4 (line number) + 2 (pos in line) + 4 (address in line). */
aUnit->line_count = (tblend - xptr) / 10;
/* Allocate an array for the entries. */
amt = sizeof (struct linenumber) * aUnit->line_count;
- aUnit->linenumber_table = ((struct linenumber *)
- bfd_alloc (stash->abfd, amt));
+ aUnit->linenumber_table = bfd_alloc (stash->abfd, amt);
for (eachLine = 0; eachLine < aUnit->line_count; eachLine++)
{
Return FALSE if error; TRUE otherwise. */
static bfd_boolean
-parse_functions_in_unit (stash, aUnit)
- struct dwarf1_debug* stash;
- struct dwarf1_unit* aUnit;
+parse_functions_in_unit (struct dwarf1_debug* stash, struct dwarf1_unit* aUnit)
{
char* eachDie;
if (aUnit->first_child)
for (eachDie = aUnit->first_child;
- eachDie < stash->debug_section_end;
+ eachDie < stash->debug_section_end;
)
{
struct die_info eachDieInfo;
Return whether we found the line (or a function) without error. */
static bfd_boolean
-dwarf1_unit_find_nearest_line (stash, aUnit, addr,
- filename_ptr, functionname_ptr,
- linenumber_ptr)
- struct dwarf1_debug* stash;
- struct dwarf1_unit* aUnit;
- unsigned long addr;
- const char **filename_ptr;
- const char **functionname_ptr;
- unsigned int *linenumber_ptr;
+dwarf1_unit_find_nearest_line (struct dwarf1_debug* stash,
+ struct dwarf1_unit* aUnit,
+ unsigned long addr,
+ const char **filename_ptr,
+ const char **functionname_ptr,
+ unsigned int *linenumber_ptr)
{
int line_p = FALSE;
int func_p = FALSE;
Return TRUE if the line is found without error. */
bfd_boolean
-_bfd_dwarf1_find_nearest_line (abfd, section, symbols, offset,
- filename_ptr, functionname_ptr, linenumber_ptr)
- bfd *abfd;
- asection *section;
- asymbol **symbols ATTRIBUTE_UNUSED;
- bfd_vma offset;
- const char **filename_ptr;
- const char **functionname_ptr;
- unsigned int *linenumber_ptr;
+_bfd_dwarf1_find_nearest_line (bfd *abfd,
+ asection *section,
+ asymbol **symbols ATTRIBUTE_UNUSED,
+ bfd_vma offset,
+ const char **filename_ptr,
+ const char **functionname_ptr,
+ unsigned int *linenumber_ptr)
{
struct dwarf1_debug *stash = elf_tdata (abfd)->dwarf1_find_line_info;
bfd_size_type size = sizeof (struct dwarf1_debug);
stash = elf_tdata (abfd)->dwarf1_find_line_info
- = (struct dwarf1_debug *) bfd_zalloc (abfd, size);
+ = bfd_zalloc (abfd, size);
if (! stash)
return FALSE;
msec = bfd_get_section_by_name (abfd, ".debug");
if (! msec)
- {
- /* No dwarf1 info. Note that at this point the stash
- has been allocated, but contains zeros, this lets
- future calls to this function fail quicker. */
- return FALSE;
- }
+ /* No dwarf1 info. Note that at this point the stash
+ has been allocated, but contains zeros, this lets
+ future calls to this function fail quicker. */
+ return FALSE;
size = msec->rawsize ? msec->rawsize : msec->size;
- stash->debug_section = (char *) bfd_alloc (abfd, size);
+ stash->debug_section = bfd_alloc (abfd, size);
if (! stash->debug_section)
return FALSE;
/* Look at the previously parsed units to see if any contain
the addr. */
for (eachUnit = stash->lastUnit; eachUnit; eachUnit = eachUnit->prev)
- {
- if (eachUnit->low_pc <= addr && addr < eachUnit->high_pc)
- return dwarf1_unit_find_nearest_line (stash, eachUnit, addr,
- filename_ptr,
- functionname_ptr,
- linenumber_ptr);
- }
+ if (eachUnit->low_pc <= addr && addr < eachUnit->high_pc)
+ return dwarf1_unit_find_nearest_line (stash, eachUnit, addr,
+ filename_ptr,
+ functionname_ptr,
+ linenumber_ptr);
while (stash->currentDie < stash->debug_section_end)
{
return FALSE;
}
-
-/* EOF */
/* Generic ECOFF swapping routines, for BFD.
- Copyright 1992, 1993, 1994, 1995, 1996, 2000, 2001, 2002, 2004
+ Copyright 1992, 1993, 1994, 1995, 1996, 2000, 2001, 2002, 2004, 2005
Free Software Foundation, Inc.
Written by Cygnus Support.
for all ECOFF targets, so they are defined in ecofflink.c. */
extern void _bfd_ecoff_swap_tir_in
- PARAMS ((int, const struct tir_ext *, TIR *));
+ (int, const struct tir_ext *, TIR *);
extern void _bfd_ecoff_swap_tir_out
- PARAMS ((int, const TIR *, struct tir_ext *));
+ (int, const TIR *, struct tir_ext *);
extern void _bfd_ecoff_swap_rndx_in
- PARAMS ((int, const struct rndx_ext *, RNDXR *));
+ (int, const struct rndx_ext *, RNDXR *);
extern void _bfd_ecoff_swap_rndx_out
- PARAMS ((int, const RNDXR *, struct rndx_ext *));
+ (int, const RNDXR *, struct rndx_ext *);
/* Prototypes for functions defined in this file. */
-static void ecoff_swap_hdr_in PARAMS ((bfd *, PTR, HDRR *));
-static void ecoff_swap_hdr_out PARAMS ((bfd *, const HDRR *, PTR));
-static void ecoff_swap_fdr_in PARAMS ((bfd *, PTR, FDR *));
-static void ecoff_swap_fdr_out PARAMS ((bfd *, const FDR *, PTR));
-static void ecoff_swap_pdr_in PARAMS ((bfd *, PTR, PDR *));
-static void ecoff_swap_pdr_out PARAMS ((bfd *, const PDR *, PTR));
-static void ecoff_swap_sym_in PARAMS ((bfd *, PTR, SYMR *));
-static void ecoff_swap_sym_out PARAMS ((bfd *, const SYMR *, PTR));
-static void ecoff_swap_ext_in PARAMS ((bfd *, PTR, EXTR *));
-static void ecoff_swap_ext_out PARAMS ((bfd *, const EXTR *, PTR));
-static void ecoff_swap_rfd_in PARAMS ((bfd *, PTR, RFDT *));
-static void ecoff_swap_rfd_out PARAMS ((bfd *, const RFDT *, PTR));
-static void ecoff_swap_opt_in PARAMS ((bfd *, PTR, OPTR *));
-static void ecoff_swap_opt_out PARAMS ((bfd *, const OPTR *, PTR));
-static void ecoff_swap_dnr_in PARAMS ((bfd *, PTR, DNR *));
-static void ecoff_swap_dnr_out PARAMS ((bfd *, const DNR *, PTR));
+static void ecoff_swap_hdr_in (bfd *, void *, HDRR *);
+static void ecoff_swap_hdr_out (bfd *, const HDRR *, void *);
+static void ecoff_swap_fdr_in (bfd *, void *, FDR *);
+static void ecoff_swap_fdr_out (bfd *, const FDR *, void *);
+static void ecoff_swap_pdr_in (bfd *, void *, PDR *);
+static void ecoff_swap_pdr_out (bfd *, const PDR *, void *);
+static void ecoff_swap_sym_in (bfd *, void *, SYMR *);
+static void ecoff_swap_sym_out (bfd *, const SYMR *, void *);
+static void ecoff_swap_ext_in (bfd *, void *, EXTR *);
+static void ecoff_swap_ext_out (bfd *, const EXTR *, void *);
+static void ecoff_swap_rfd_in (bfd *, void *, RFDT *);
+static void ecoff_swap_rfd_out (bfd *, const RFDT *, void *);
+static void ecoff_swap_opt_in (bfd *, void *, OPTR *);
+static void ecoff_swap_opt_out (bfd *, const OPTR *, void *);
+static void ecoff_swap_dnr_in (bfd *, void *, DNR *);
+static void ecoff_swap_dnr_out (bfd *, const DNR *, void *);
/* Swap in the symbolic header. */
static void
-ecoff_swap_hdr_in (abfd, ext_copy, intern)
- bfd *abfd;
- PTR ext_copy;
- HDRR *intern;
+ecoff_swap_hdr_in (bfd *abfd, void * ext_copy, HDRR *intern)
{
struct hdr_ext ext[1];
intern->cbExtOffset = ECOFF_GET_OFF (abfd, ext->h_cbExtOffset);
#ifdef TEST
- if (memcmp ((char *)ext, (char *)intern, sizeof (*intern)) != 0)
+ if (memcmp ((char *) ext, (char *) intern, sizeof (*intern)) != 0)
abort ();
#endif
}
/* Swap out the symbolic header. */
static void
-ecoff_swap_hdr_out (abfd, intern_copy, ext_ptr)
- bfd *abfd;
- const HDRR *intern_copy;
- PTR ext_ptr;
+ecoff_swap_hdr_out (bfd *abfd, const HDRR *intern_copy, void * ext_ptr)
{
struct hdr_ext *ext = (struct hdr_ext *) ext_ptr;
HDRR intern[1];
/* Swap in the file descriptor record. */
static void
-ecoff_swap_fdr_in (abfd, ext_copy, intern)
- bfd *abfd;
- PTR ext_copy;
- FDR *intern;
+ecoff_swap_fdr_in (bfd *abfd, void * ext_copy, FDR *intern)
{
struct fdr_ext ext[1];
intern->cbLine = ECOFF_GET_OFF (abfd, ext->f_cbLine);
#ifdef TEST
- if (memcmp ((char *)ext, (char *)intern, sizeof (*intern)) != 0)
+ if (memcmp ((char *) ext, (char *) intern, sizeof (*intern)) != 0)
abort ();
#endif
}
/* Swap out the file descriptor record. */
static void
-ecoff_swap_fdr_out (abfd, intern_copy, ext_ptr)
- bfd *abfd;
- const FDR *intern_copy;
- PTR ext_ptr;
+ecoff_swap_fdr_out (bfd *abfd, const FDR *intern_copy, void * ext_ptr)
{
struct fdr_ext *ext = (struct fdr_ext *) ext_ptr;
FDR intern[1];
ECOFF_PUT_OFF (abfd, intern->cbLine, ext->f_cbLine);
#ifdef TEST
- if (memcmp ((char *)ext, (char *)intern, sizeof (*intern)) != 0)
+ if (memcmp ((char *) ext, (char *) intern, sizeof (*intern)) != 0)
abort ();
#endif
}
/* Swap in the procedure descriptor record. */
static void
-ecoff_swap_pdr_in (abfd, ext_copy, intern)
- bfd *abfd;
- PTR ext_copy;
- PDR *intern;
+ecoff_swap_pdr_in (bfd *abfd, void * ext_copy, PDR *intern)
{
struct pdr_ext ext[1];
*ext = *(struct pdr_ext *) ext_copy;
- memset ((PTR) intern, 0, sizeof (*intern));
+ memset ((void *) intern, 0, sizeof (*intern));
intern->adr = ECOFF_GET_OFF (abfd, ext->p_adr);
intern->isym = H_GET_32 (abfd, ext->p_isym);
#endif
#ifdef TEST
- if (memcmp ((char *)ext, (char *)intern, sizeof (*intern)) != 0)
+ if (memcmp ((char *) ext, (char *) intern, sizeof (*intern)) != 0)
abort ();
#endif
}
/* Swap out the procedure descriptor record. */
static void
-ecoff_swap_pdr_out (abfd, intern_copy, ext_ptr)
- bfd *abfd;
- const PDR *intern_copy;
- PTR ext_ptr;
+ecoff_swap_pdr_out (bfd *abfd, const PDR *intern_copy, void * ext_ptr)
{
struct pdr_ext *ext = (struct pdr_ext *) ext_ptr;
PDR intern[1];
#endif
#ifdef TEST
- if (memcmp ((char *)ext, (char *)intern, sizeof (*intern)) != 0)
+ if (memcmp ((char *) ext, (char *) intern, sizeof (*intern)) != 0)
abort ();
#endif
}
/* Swap in a symbol record. */
static void
-ecoff_swap_sym_in (abfd, ext_copy, intern)
- bfd *abfd;
- PTR ext_copy;
- SYMR *intern;
+ecoff_swap_sym_in (bfd *abfd, void * ext_copy, SYMR *intern)
{
struct sym_ext ext[1];
}
#ifdef TEST
- if (memcmp ((char *)ext, (char *)intern, sizeof (*intern)) != 0)
+ if (memcmp ((char *) ext, (char *) intern, sizeof (*intern)) != 0)
abort ();
#endif
}
/* Swap out a symbol record. */
static void
-ecoff_swap_sym_out (abfd, intern_copy, ext_ptr)
- bfd *abfd;
- const SYMR *intern_copy;
- PTR ext_ptr;
+ecoff_swap_sym_out (bfd *abfd, const SYMR *intern_copy, void * ext_ptr)
{
struct sym_ext *ext = (struct sym_ext *) ext_ptr;
SYMR intern[1];
}
#ifdef TEST
- if (memcmp ((char *)ext, (char *)intern, sizeof (*intern)) != 0)
+ if (memcmp ((char *) ext, (char *) intern, sizeof (*intern)) != 0)
abort ();
#endif
}
/* Swap in an external symbol record. */
static void
-ecoff_swap_ext_in (abfd, ext_copy, intern)
- bfd *abfd;
- PTR ext_copy;
- EXTR *intern;
+ecoff_swap_ext_in (bfd *abfd, void * ext_copy, EXTR *intern)
{
struct ext_ext ext[1];
ecoff_swap_sym_in (abfd, &ext->es_asym, &intern->asym);
#ifdef TEST
- if (memcmp ((char *)ext, (char *)intern, sizeof (*intern)) != 0)
+ if (memcmp ((char *) ext, (char *) intern, sizeof (*intern)) != 0)
abort ();
#endif
}
/* Swap out an external symbol record. */
static void
-ecoff_swap_ext_out (abfd, intern_copy, ext_ptr)
- bfd *abfd;
- const EXTR *intern_copy;
- PTR ext_ptr;
+ecoff_swap_ext_out (bfd *abfd, const EXTR *intern_copy, void * ext_ptr)
{
struct ext_ext *ext = (struct ext_ext *) ext_ptr;
EXTR intern[1];
ecoff_swap_sym_out (abfd, &intern->asym, &ext->es_asym);
#ifdef TEST
- if (memcmp ((char *)ext, (char *)intern, sizeof (*intern)) != 0)
+ if (memcmp ((char *) ext, (char *) intern, sizeof (*intern)) != 0)
abort ();
#endif
}
/* Swap in a relative file descriptor. */
static void
-ecoff_swap_rfd_in (abfd, ext_ptr, intern)
- bfd *abfd;
- PTR ext_ptr;
- RFDT *intern;
+ecoff_swap_rfd_in (bfd *abfd, void * ext_ptr, RFDT *intern)
{
struct rfd_ext *ext = (struct rfd_ext *) ext_ptr;
*intern = H_GET_32 (abfd, ext->rfd);
#ifdef TEST
- if (memcmp ((char *)ext, (char *)intern, sizeof (*intern)) != 0)
+ if (memcmp ((char *) ext, (char *) intern, sizeof (*intern)) != 0)
abort ();
#endif
}
/* Swap out a relative file descriptor. */
static void
-ecoff_swap_rfd_out (abfd, intern, ext_ptr)
- bfd *abfd;
- const RFDT *intern;
- PTR ext_ptr;
+ecoff_swap_rfd_out (bfd *abfd, const RFDT *intern, void * ext_ptr)
{
struct rfd_ext *ext = (struct rfd_ext *) ext_ptr;
H_PUT_32 (abfd, *intern, ext->rfd);
#ifdef TEST
- if (memcmp ((char *)ext, (char *)intern, sizeof (*intern)) != 0)
+ if (memcmp ((char *) ext, (char *) intern, sizeof (*intern)) != 0)
abort ();
#endif
}
/* Swap in an optimization symbol. */
static void
-ecoff_swap_opt_in (abfd, ext_copy, intern)
- bfd *abfd;
- PTR ext_copy;
- OPTR *intern;
+ecoff_swap_opt_in (bfd *abfd, void * ext_copy, OPTR * intern)
{
struct opt_ext ext[1];
intern->offset = H_GET_32 (abfd, ext->o_offset);
#ifdef TEST
- if (memcmp ((char *)ext, (char *)intern, sizeof (*intern)) != 0)
+ if (memcmp ((char *) ext, (char *) intern, sizeof (*intern)) != 0)
abort ();
#endif
}
/* Swap out an optimization symbol. */
static void
-ecoff_swap_opt_out (abfd, intern_copy, ext_ptr)
- bfd *abfd;
- const OPTR *intern_copy;
- PTR ext_ptr;
+ecoff_swap_opt_out (bfd *abfd, const OPTR *intern_copy, void * ext_ptr)
{
struct opt_ext *ext = (struct opt_ext *) ext_ptr;
OPTR intern[1];
H_PUT_32 (abfd, intern->value, ext->o_offset);
#ifdef TEST
- if (memcmp ((char *)ext, (char *)intern, sizeof (*intern)) != 0)
+ if (memcmp ((char *) ext, (char *) intern, sizeof (*intern)) != 0)
abort ();
#endif
}
/* Swap in a dense number. */
static void
-ecoff_swap_dnr_in (abfd, ext_copy, intern)
- bfd *abfd;
- PTR ext_copy;
- DNR *intern;
+ecoff_swap_dnr_in (bfd *abfd, void * ext_copy, DNR *intern)
{
struct dnr_ext ext[1];
intern->index = H_GET_32 (abfd, ext->d_index);
#ifdef TEST
- if (memcmp ((char *)ext, (char *)intern, sizeof (*intern)) != 0)
+ if (memcmp ((char *) ext, (char *) intern, sizeof (*intern)) != 0)
abort ();
#endif
}
/* Swap out a dense number. */
static void
-ecoff_swap_dnr_out (abfd, intern_copy, ext_ptr)
- bfd *abfd;
- const DNR *intern_copy;
- PTR ext_ptr;
+ecoff_swap_dnr_out (bfd *abfd, const DNR *intern_copy, void * ext_ptr)
{
struct dnr_ext *ext = (struct dnr_ext *) ext_ptr;
DNR intern[1];
H_PUT_32 (abfd, intern->index, ext->d_index);
#ifdef TEST
- if (memcmp ((char *)ext, (char *)intern, sizeof (*intern)) != 0)
+ if (memcmp ((char *) ext, (char *) intern, sizeof (*intern)) != 0)
abort ();
#endif
}
/* BFD back-end definitions used by all FreeBSD targets.
- Copyright 1990, 1991, 1992, 1996, 1997, 2000, 2001, 2002
+ Copyright 1990, 1991, 1992, 1996, 1997, 2000, 2001, 2002, 2005
Free Software Foundation, Inc.
-This file is part of BFD, the Binary File Descriptor library.
+ This file is part of BFD, the Binary File Descriptor library.
-This program is free software; you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation; either version 2 of the License, or
-(at your option) any later version.
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-GNU General Public License for more details.
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
-You should have received a copy of the GNU General Public License
-along with this program; if not, write to the Free Software
-Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
-*/
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
+ USA. */
/* FreeBSD ZMAGIC files never have the header in the text. */
#define N_HEADER_IN_TEXT(x) 0
| (((flags) & 0x3f) << 26))
#define N_SET_MACHTYPE(exec, machtype) \
((exec).a_info = \
- ((exec).a_info & 0xfb00ffff) | ((((int)(machtype))&0x3ff) << 16))
+ ((exec).a_info & 0xfb00ffff) | ((((int) (machtype)) & 0x3ff) << 16))
#define N_SET_FLAGS(exec, flags) \
((exec).a_info = \
((exec).a_info & 0x03ffffff) | ((flags & 0x03f) << 26))
format. I think. */
#define SWAP_MAGIC(ext) bfd_getl32 (ext)
-#define MY_write_object_contents MY(write_object_contents)
-static bfd_boolean MY(write_object_contents) PARAMS ((bfd *abfd));
+#define MY_write_object_contents MY (write_object_contents)
+static bfd_boolean MY (write_object_contents) (bfd *);
#include "aout-target.h"
file header, symbols, and relocation. */
static bfd_boolean
-MY(write_object_contents) (abfd)
- bfd *abfd;
+MY (write_object_contents) (bfd *abfd)
{
struct external_exec exec_bytes;
struct internal_exec *execp = exec_hdr (abfd);
obj_reloc_entry_size (abfd) = RELOC_STD_SIZE;
/* Magic number, maestro, please! */
- switch (bfd_get_arch(abfd)) {
- case bfd_arch_m68k:
- if (strcmp (abfd->xvec->name, "a.out-m68k4k-netbsd") == 0)
- N_SET_MACHTYPE(*execp, M_68K4K_NETBSD);
- else
- N_SET_MACHTYPE(*execp, M_68K_NETBSD);
- break;
- case bfd_arch_sparc:
- N_SET_MACHTYPE(*execp, M_SPARC_NETBSD);
- break;
- case bfd_arch_i386:
- N_SET_MACHTYPE(*execp, M_386_NETBSD);
- break;
- case bfd_arch_ns32k:
- N_SET_MACHTYPE(*execp, M_532_NETBSD);
- break;
- default:
- N_SET_MACHTYPE(*execp, M_UNKNOWN);
- break;
- }
+ switch (bfd_get_arch(abfd))
+ {
+ case bfd_arch_m68k:
+ if (strcmp (abfd->xvec->name, "a.out-m68k4k-netbsd") == 0)
+ N_SET_MACHTYPE (*execp, M_68K4K_NETBSD);
+ else
+ N_SET_MACHTYPE (*execp, M_68K_NETBSD);
+ break;
+ case bfd_arch_sparc:
+ N_SET_MACHTYPE (*execp, M_SPARC_NETBSD);
+ break;
+ case bfd_arch_i386:
+ N_SET_MACHTYPE (*execp, M_386_NETBSD);
+ break;
+ case bfd_arch_ns32k:
+ N_SET_MACHTYPE (*execp, M_532_NETBSD);
+ break;
+ default:
+ N_SET_MACHTYPE (*execp, M_UNKNOWN);
+ break;
+ }
WRITE_HEADERS(abfd, execp);
/* genlink.h -- interface to the BFD generic linker
- Copyright 1993, 1994, 1996, 2002 Free Software Foundation, Inc.
+ Copyright 1993, 1994, 1996, 2002, 2005 Free Software Foundation, Inc.
Written by Ian Lance Taylor, Cygnus Support.
-This file is part of BFD, the Binary File Descriptor library.
+ This file is part of BFD, the Binary File Descriptor library.
-This program is free software; you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation; either version 2 of the License, or
-(at your option) any later version.
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-GNU General Public License for more details.
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
-You should have received a copy of the GNU General Public License
-along with this program; if not, write to the Free Software
-Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
#ifndef GENLINK_H
#define GENLINK_H
#define _bfd_generic_link_hash_traverse(table, func, info) \
(bfd_link_hash_traverse \
(&(table)->root, \
- (bfd_boolean (*) PARAMS ((struct bfd_link_hash_entry *, PTR))) (func), \
+ (bfd_boolean (*) (struct bfd_link_hash_entry *, void *)) (func), \
(info)))
/* Get the generic link hash table from the info structure. This is
/* The generic linker reads in the asymbol structures for an input BFD
and keeps them in the outsymbol and symcount fields. */
-#define _bfd_generic_link_get_symbols(abfd) ((abfd)->outsymbols)
+#define _bfd_generic_link_get_symbols(abfd) ((abfd)->outsymbols)
#define _bfd_generic_link_get_symcount(abfd) ((abfd)->symcount)
/* Add the symbols of input_bfd to the symbols being built for
output_bfd. */
extern bfd_boolean _bfd_generic_link_output_symbols
- PARAMS ((bfd *output_bfd, bfd *input_bfd, struct bfd_link_info *,
- size_t *psymalloc));
+ (bfd *, bfd *, struct bfd_link_info *, size_t *);
/* This structure is used to pass information to
_bfd_generic_link_write_global_symbol, which may be called via
via _bfd_generic_link_hash_traverse. The second argument must
actually be a struct generic_write_global_symbol_info *. */
extern bfd_boolean _bfd_generic_link_write_global_symbol
- PARAMS ((struct generic_link_hash_entry *, PTR));
+ (struct generic_link_hash_entry *, void *);
/* Generic link hash table entry creation routine. */
struct bfd_hash_entry *_bfd_generic_link_hash_newfunc
- PARAMS ((struct bfd_hash_entry *, struct bfd_hash_table *,
- const char *));
+ (struct bfd_hash_entry *, struct bfd_hash_table *, const char *);
#endif
bfd_boolean pcrel = FALSE;
asection *section;
ieee_reloc_type *r;
- bfd_size_type amt = sizeof (ieee_reloc_type);
- r = bfd_alloc (ieee->h.abfd, amt);
+ r = bfd_alloc (ieee->h.abfd, sizeof (* r));
if (!r)
return FALSE;
#define ieee_slurp_extended_name_table bfd_true
#define ieee_construct_extended_name_table \
((bfd_boolean (*) \
- PARAMS ((bfd *, char **, bfd_size_type *, const char **))) \
+ (bfd *, char **, bfd_size_type *, const char **)) \
bfd_true)
#define ieee_truncate_arname bfd_dont_truncate_arname
#define ieee_write_armap \
((bfd_boolean (*) \
- PARAMS ((bfd *, unsigned int, struct orl *, unsigned int, int))) \
+ (bfd *, unsigned int, struct orl *, unsigned int, int)) \
bfd_true)
#define ieee_read_ar_hdr bfd_nullvoidptr
#define ieee_update_armap_timestamp bfd_true
const bfd_target ieee_vec =
{
- "ieee", /* name */
+ "ieee", /* Name. */
bfd_target_ieee_flavour,
- BFD_ENDIAN_UNKNOWN, /* target byte order */
- BFD_ENDIAN_UNKNOWN, /* target headers byte order */
- (HAS_RELOC | EXEC_P | /* object flags */
+ BFD_ENDIAN_UNKNOWN, /* Target byte order. */
+ BFD_ENDIAN_UNKNOWN, /* Target headers byte order. */
+ (HAS_RELOC | EXEC_P | /* Object flags. */
HAS_LINENO | HAS_DEBUG |
HAS_SYMS | HAS_LOCALS | WP_TEXT | D_PAGED),
(SEC_CODE | SEC_DATA | SEC_ROM | SEC_HAS_CONTENTS
- | SEC_ALLOC | SEC_LOAD | SEC_RELOC), /* section flags */
- '_', /* leading underscore */
- ' ', /* ar_pad_char */
- 16, /* ar_max_namelen */
+ | SEC_ALLOC | SEC_LOAD | SEC_RELOC), /* Section flags. */
+ '_', /* Leading underscore. */
+ ' ', /* AR_pad_char. */
+ 16, /* AR_max_namelen. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* data */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Data. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* hdrs */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Headers. */
{_bfd_dummy_target,
- ieee_object_p, /* bfd_check_format */
+ ieee_object_p, /* bfd_check_format. */
ieee_archive_p,
_bfd_dummy_target,
},
NULL,
- (void *) 0
+ NULL
};
/* BFD back-end for Intel Hex objects.
- Copyright 1995, 1996, 1998, 1999, 2000, 2001, 2002, 2003, 2004
+ Copyright 1995, 1996, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005
Free Software Foundation, Inc.
Written by Ian Lance Taylor of Cygnus Support <ian@cygnus.com>.
10..13 Upper 16 bits of start address
14..17 Lower 16 bits of start address
18..19 Checksum in hex notation
- 20..21 Carriage return, line feed
-*/
+ 20..21 Carriage return, line feed. */
#include "bfd.h"
#include "sysdep.h"
#include "libiberty.h"
#include "safe-ctype.h"
-static void ihex_init
- PARAMS ((void));
-static bfd_boolean ihex_mkobject
- PARAMS ((bfd *));
-static INLINE int ihex_get_byte
- PARAMS ((bfd *, bfd_boolean *));
-static void ihex_bad_byte
- PARAMS ((bfd *, unsigned int, int, bfd_boolean));
-static bfd_boolean ihex_scan
- PARAMS ((bfd *));
-static const bfd_target *ihex_object_p
- PARAMS ((bfd *));
-static bfd_boolean ihex_read_section
- PARAMS ((bfd *, asection *, bfd_byte *));
-static bfd_boolean ihex_get_section_contents
- PARAMS ((bfd *, asection *, PTR, file_ptr, bfd_size_type));
-static bfd_boolean ihex_set_section_contents
- PARAMS ((bfd *, asection *, const PTR, file_ptr, bfd_size_type));
-static bfd_boolean ihex_write_record
- PARAMS ((bfd *, size_t, unsigned int, unsigned int, bfd_byte *));
-static bfd_boolean ihex_write_object_contents
- PARAMS ((bfd *));
-static bfd_boolean ihex_set_arch_mach
- PARAMS ((bfd *, enum bfd_architecture, unsigned long));
-static int ihex_sizeof_headers
- PARAMS ((bfd *, bfd_boolean));
-
/* The number of bytes we put on one line during output. */
#define CHUNK 16
/* Initialize by filling in the hex conversion array. */
static void
-ihex_init ()
+ihex_init (void)
{
static bfd_boolean inited;
/* Create an ihex object. */
static bfd_boolean
-ihex_mkobject (abfd)
- bfd *abfd;
+ihex_mkobject (bfd *abfd)
{
struct ihex_data_struct *tdata;
- bfd_size_type amt = sizeof (struct ihex_data_struct);
- tdata = (struct ihex_data_struct *) bfd_alloc (abfd, amt);
+ tdata = bfd_alloc (abfd, sizeof (* tdata));
if (tdata == NULL)
return FALSE;
Return EOF on error or end of file. */
static INLINE int
-ihex_get_byte (abfd, errorptr)
- bfd *abfd;
- bfd_boolean *errorptr;
+ihex_get_byte (bfd *abfd, bfd_boolean *errorptr)
{
bfd_byte c;
/* Report a problem in an Intel Hex file. */
static void
-ihex_bad_byte (abfd, lineno, c, error)
- bfd *abfd;
- unsigned int lineno;
- int c;
- bfd_boolean error;
+ihex_bad_byte (bfd *abfd, unsigned int lineno, int c, bfd_boolean error)
{
if (c == EOF)
{
section for each contiguous set of bytes. */
static bfd_boolean
-ihex_scan (abfd)
- bfd *abfd;
+ihex_scan (bfd *abfd)
{
bfd_vma segbase;
bfd_vma extbase;
chars = len * 2 + 2;
if (chars >= bufsize)
{
- buf = (bfd_byte *) bfd_realloc (buf, (bfd_size_type) chars);
+ buf = bfd_realloc (buf, (bfd_size_type) chars);
if (buf == NULL)
goto error_return;
bufsize = chars;
sprintf (secbuf, ".sec%d", bfd_count_sections (abfd) + 1);
amt = strlen (secbuf) + 1;
- secname = (char *) bfd_alloc (abfd, amt);
+ secname = bfd_alloc (abfd, amt);
if (secname == NULL)
goto error_return;
strcpy (secname, secbuf);
/* Try to recognize an Intel Hex file. */
static const bfd_target *
-ihex_object_p (abfd)
- bfd *abfd;
+ihex_object_p (bfd *abfd)
{
- PTR tdata_save;
+ void * tdata_save;
bfd_byte b[9];
unsigned int i;
unsigned int type;
/* Read the contents of a section in an Intel Hex file. */
static bfd_boolean
-ihex_read_section (abfd, section, contents)
- bfd *abfd;
- asection *section;
- bfd_byte *contents;
+ihex_read_section (bfd *abfd, asection *section, bfd_byte *contents)
{
int c;
bfd_byte *p;
if (len * 2 > bufsize)
{
- buf = (bfd_byte *) bfd_realloc (buf, (bfd_size_type) len * 2);
+ buf = bfd_realloc (buf, (bfd_size_type) len * 2);
if (buf == NULL)
goto error_return;
bufsize = len * 2;
/* Get the contents of a section in an Intel Hex file. */
static bfd_boolean
-ihex_get_section_contents (abfd, section, location, offset, count)
- bfd *abfd;
- asection *section;
- PTR location;
- file_ptr offset;
- bfd_size_type count;
+ihex_get_section_contents (bfd *abfd,
+ asection *section,
+ void * location,
+ file_ptr offset,
+ bfd_size_type count)
{
if (section->used_by_bfd == NULL)
{
/* Set the contents of a section in an Intel Hex file. */
static bfd_boolean
-ihex_set_section_contents (abfd, section, location, offset, count)
- bfd *abfd;
- asection *section;
- const PTR location;
- file_ptr offset;
- bfd_size_type count;
+ihex_set_section_contents (bfd *abfd,
+ asection *section,
+ const void * location,
+ file_ptr offset,
+ bfd_size_type count)
{
struct ihex_data_list *n;
bfd_byte *data;
struct ihex_data_struct *tdata;
- bfd_size_type amt;
if (count == 0
|| (section->flags & SEC_ALLOC) == 0
|| (section->flags & SEC_LOAD) == 0)
return TRUE;
- amt = sizeof (struct ihex_data_list);
- n = (struct ihex_data_list *) bfd_alloc (abfd, amt);
+ n = bfd_alloc (abfd, sizeof (* n));
if (n == NULL)
return FALSE;
- data = (bfd_byte *) bfd_alloc (abfd, count);
+ data = bfd_alloc (abfd, count);
if (data == NULL)
return FALSE;
memcpy (data, location, (size_t) count);
}
else
{
- register struct ihex_data_list **pp;
+ struct ihex_data_list **pp;
for (pp = &tdata->head;
*pp != NULL && (*pp)->where < n->where;
/* Write a record out to an Intel Hex file. */
static bfd_boolean
-ihex_write_record (abfd, count, addr, type, data)
- bfd *abfd;
- size_t count;
- unsigned int addr;
- unsigned int type;
- bfd_byte *data;
+ihex_write_record (bfd *abfd,
+ size_t count,
+ unsigned int addr,
+ unsigned int type,
+ bfd_byte *data)
{
static const char digs[] = "0123456789ABCDEF";
char buf[9 + CHUNK * 2 + 4];
/* Write out an Intel Hex file. */
static bfd_boolean
-ihex_write_object_contents (abfd)
- bfd *abfd;
+ihex_write_object_contents (bfd *abfd)
{
bfd_vma segbase;
bfd_vma extbase;
where = l->where;
p = l->data;
count = l->size;
+
while (count > 0)
{
size_t now;
irrelevant, so we ignore errors about unknown architectures. */
static bfd_boolean
-ihex_set_arch_mach (abfd, arch, mach)
- bfd *abfd;
- enum bfd_architecture arch;
- unsigned long mach;
+ihex_set_arch_mach (bfd *abfd,
+ enum bfd_architecture arch,
+ unsigned long mach)
{
if (! bfd_default_set_arch_mach (abfd, arch, mach))
{
/* Get the size of the headers, for the linker. */
static int
-ihex_sizeof_headers (abfd, exec)
- bfd *abfd ATTRIBUTE_UNUSED;
- bfd_boolean exec ATTRIBUTE_UNUSED;
+ihex_sizeof_headers (bfd *abfd ATTRIBUTE_UNUSED, bfd_boolean exec ATTRIBUTE_UNUSED)
{
return 0;
}
/* Some random definitions for the target vector. */
-#define ihex_close_and_cleanup _bfd_generic_close_and_cleanup
-#define ihex_bfd_free_cached_info _bfd_generic_bfd_free_cached_info
-#define ihex_new_section_hook _bfd_generic_new_section_hook
-#define ihex_get_section_contents_in_window \
- _bfd_generic_get_section_contents_in_window
-
-#define ihex_get_symtab_upper_bound bfd_0l
-#define ihex_canonicalize_symtab \
- ((long (*) PARAMS ((bfd *, asymbol **))) bfd_0l)
-#define ihex_make_empty_symbol _bfd_generic_make_empty_symbol
-#define ihex_print_symbol _bfd_nosymbols_print_symbol
-#define ihex_get_symbol_info _bfd_nosymbols_get_symbol_info
-#define ihex_bfd_is_target_special_symbol ((bfd_boolean (*) (bfd *, asymbol *)) bfd_false)
-#define ihex_bfd_is_local_label_name _bfd_nosymbols_bfd_is_local_label_name
-#define ihex_get_lineno _bfd_nosymbols_get_lineno
-#define ihex_find_nearest_line _bfd_nosymbols_find_nearest_line
-#define ihex_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
-#define ihex_read_minisymbols _bfd_nosymbols_read_minisymbols
-#define ihex_minisymbol_to_symbol _bfd_nosymbols_minisymbol_to_symbol
-
-#define ihex_get_reloc_upper_bound \
- ((long (*) PARAMS ((bfd *, asection *))) bfd_0l)
-#define ihex_canonicalize_reloc \
- ((long (*) PARAMS ((bfd *, asection *, arelent **, asymbol **))) bfd_0l)
-#define ihex_bfd_reloc_type_lookup _bfd_norelocs_bfd_reloc_type_lookup
-
-#define ihex_bfd_get_relocated_section_contents \
- bfd_generic_get_relocated_section_contents
-#define ihex_bfd_relax_section bfd_generic_relax_section
-#define ihex_bfd_gc_sections bfd_generic_gc_sections
-#define ihex_bfd_merge_sections bfd_generic_merge_sections
-#define ihex_bfd_is_group_section bfd_generic_is_group_section
-#define ihex_bfd_discard_group bfd_generic_discard_group
-#define ihex_section_already_linked \
- _bfd_generic_section_already_linked
-#define ihex_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
-#define ihex_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
-#define ihex_bfd_link_add_symbols _bfd_generic_link_add_symbols
-#define ihex_bfd_link_just_syms _bfd_generic_link_just_syms
-#define ihex_bfd_final_link _bfd_generic_final_link
-#define ihex_bfd_link_split_section _bfd_generic_link_split_section
+#define ihex_close_and_cleanup _bfd_generic_close_and_cleanup
+#define ihex_bfd_free_cached_info _bfd_generic_bfd_free_cached_info
+#define ihex_new_section_hook _bfd_generic_new_section_hook
+#define ihex_get_section_contents_in_window _bfd_generic_get_section_contents_in_window
+#define ihex_get_symtab_upper_bound bfd_0l
+#define ihex_canonicalize_symtab ((long (*) (bfd *, asymbol **)) bfd_0l)
+#define ihex_make_empty_symbol _bfd_generic_make_empty_symbol
+#define ihex_print_symbol _bfd_nosymbols_print_symbol
+#define ihex_get_symbol_info _bfd_nosymbols_get_symbol_info
+#define ihex_bfd_is_target_special_symbol ((bfd_boolean (*) (bfd *, asymbol *)) bfd_false)
+#define ihex_bfd_is_local_label_name _bfd_nosymbols_bfd_is_local_label_name
+#define ihex_get_lineno _bfd_nosymbols_get_lineno
+#define ihex_find_nearest_line _bfd_nosymbols_find_nearest_line
+#define ihex_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
+#define ihex_read_minisymbols _bfd_nosymbols_read_minisymbols
+#define ihex_minisymbol_to_symbol _bfd_nosymbols_minisymbol_to_symbol
+#define ihex_get_reloc_upper_bound ((long (*) (bfd *, asection *)) bfd_0l)
+#define ihex_canonicalize_reloc ((long (*) (bfd *, asection *, arelent **, asymbol **)) bfd_0l)
+#define ihex_bfd_reloc_type_lookup _bfd_norelocs_bfd_reloc_type_lookup
+#define ihex_bfd_get_relocated_section_contents bfd_generic_get_relocated_section_contents
+#define ihex_bfd_relax_section bfd_generic_relax_section
+#define ihex_bfd_gc_sections bfd_generic_gc_sections
+#define ihex_bfd_merge_sections bfd_generic_merge_sections
+#define ihex_bfd_is_group_section bfd_generic_is_group_section
+#define ihex_bfd_discard_group bfd_generic_discard_group
+#define ihex_section_already_linked _bfd_generic_section_already_linked
+#define ihex_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
+#define ihex_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
+#define ihex_bfd_link_add_symbols _bfd_generic_link_add_symbols
+#define ihex_bfd_link_just_syms _bfd_generic_link_just_syms
+#define ihex_bfd_final_link _bfd_generic_final_link
+#define ihex_bfd_link_split_section _bfd_generic_link_split_section
/* The Intel Hex target vector. */
const bfd_target ihex_vec =
{
- "ihex", /* name */
+ "ihex", /* Name. */
bfd_target_ihex_flavour,
- BFD_ENDIAN_UNKNOWN, /* target byte order */
- BFD_ENDIAN_UNKNOWN, /* target headers byte order */
- 0, /* object flags */
- (SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD), /* section flags */
- 0, /* leading underscore */
- ' ', /* ar_pad_char */
- 16, /* ar_max_namelen */
+ BFD_ENDIAN_UNKNOWN, /* Target byte order. */
+ BFD_ENDIAN_UNKNOWN, /* Target headers byte order. */
+ 0, /* Object flags. */
+ (SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD), /* Section flags. */
+ 0, /* Leading underscore. */
+ ' ', /* AR_pad_char. */
+ 16, /* AR_max_namelen. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* data */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Data. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* hdrs */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Headers. */
{
_bfd_dummy_target,
- ihex_object_p, /* bfd_check_format */
+ ihex_object_p, /* bfd_check_format. */
_bfd_dummy_target,
_bfd_dummy_target,
},
_bfd_generic_mkarchive,
bfd_false,
},
- { /* bfd_write_contents */
+ { /* bfd_write_contents. */
bfd_false,
ihex_write_object_contents,
_bfd_write_archive_contents,
NULL,
- (PTR) 0
+ NULL
};
/* Functions and types in cofflink.c. */
-#define STRING_SIZE_SIZE (4)
+#define STRING_SIZE_SIZE 4
/* We use a hash table to merge identical enum, struct, and union
definitions in the linker. */
#define BFD_IO_FUNCS 0
#endif
-#define bfd_mach_o_mkarchive _bfd_noarchive_mkarchive
-#define bfd_mach_o_read_ar_hdr _bfd_noarchive_read_ar_hdr
-#define bfd_mach_o_slurp_armap _bfd_noarchive_slurp_armap
-#define bfd_mach_o_slurp_extended_name_table _bfd_noarchive_slurp_extended_name_table
-#define bfd_mach_o_construct_extended_name_table _bfd_noarchive_construct_extended_name_table
-#define bfd_mach_o_truncate_arname _bfd_noarchive_truncate_arname
-#define bfd_mach_o_write_armap _bfd_noarchive_write_armap
-#define bfd_mach_o_get_elt_at_index _bfd_noarchive_get_elt_at_index
-#define bfd_mach_o_generic_stat_arch_elt _bfd_noarchive_generic_stat_arch_elt
-#define bfd_mach_o_update_armap_timestamp _bfd_noarchive_update_armap_timestamp
-#define bfd_mach_o_close_and_cleanup _bfd_generic_close_and_cleanup
-#define bfd_mach_o_bfd_free_cached_info _bfd_generic_bfd_free_cached_info
-#define bfd_mach_o_new_section_hook _bfd_generic_new_section_hook
-#define bfd_mach_o_get_section_contents_in_window _bfd_generic_get_section_contents_in_window
-#define bfd_mach_o_bfd_is_local_label_name _bfd_nosymbols_bfd_is_local_label_name
-#define bfd_mach_o_bfd_is_target_special_symbol ((bfd_boolean (*) (bfd *, asymbol *)) bfd_false)
-#define bfd_mach_o_bfd_is_local_label_name _bfd_nosymbols_bfd_is_local_label_name
-#define bfd_mach_o_get_lineno _bfd_nosymbols_get_lineno
-#define bfd_mach_o_find_nearest_line _bfd_nosymbols_find_nearest_line
-#define bfd_mach_o_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
-#define bfd_mach_o_read_minisymbols _bfd_generic_read_minisymbols
-#define bfd_mach_o_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol
-#define bfd_mach_o_get_reloc_upper_bound _bfd_norelocs_get_reloc_upper_bound
-#define bfd_mach_o_canonicalize_reloc _bfd_norelocs_canonicalize_reloc
-#define bfd_mach_o_bfd_reloc_type_lookup _bfd_norelocs_bfd_reloc_type_lookup
+#define bfd_mach_o_mkarchive _bfd_noarchive_mkarchive
+#define bfd_mach_o_read_ar_hdr _bfd_noarchive_read_ar_hdr
+#define bfd_mach_o_slurp_armap _bfd_noarchive_slurp_armap
+#define bfd_mach_o_slurp_extended_name_table _bfd_noarchive_slurp_extended_name_table
+#define bfd_mach_o_construct_extended_name_table _bfd_noarchive_construct_extended_name_table
+#define bfd_mach_o_truncate_arname _bfd_noarchive_truncate_arname
+#define bfd_mach_o_write_armap _bfd_noarchive_write_armap
+#define bfd_mach_o_get_elt_at_index _bfd_noarchive_get_elt_at_index
+#define bfd_mach_o_generic_stat_arch_elt _bfd_noarchive_generic_stat_arch_elt
+#define bfd_mach_o_update_armap_timestamp _bfd_noarchive_update_armap_timestamp
+#define bfd_mach_o_close_and_cleanup _bfd_generic_close_and_cleanup
+#define bfd_mach_o_bfd_free_cached_info _bfd_generic_bfd_free_cached_info
+#define bfd_mach_o_new_section_hook _bfd_generic_new_section_hook
+#define bfd_mach_o_get_section_contents_in_window _bfd_generic_get_section_contents_in_window
+#define bfd_mach_o_bfd_is_local_label_name _bfd_nosymbols_bfd_is_local_label_name
+#define bfd_mach_o_bfd_is_target_special_symbol ((bfd_boolean (*) (bfd *, asymbol *)) bfd_false)
+#define bfd_mach_o_bfd_is_local_label_name _bfd_nosymbols_bfd_is_local_label_name
+#define bfd_mach_o_get_lineno _bfd_nosymbols_get_lineno
+#define bfd_mach_o_find_nearest_line _bfd_nosymbols_find_nearest_line
+#define bfd_mach_o_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
+#define bfd_mach_o_read_minisymbols _bfd_generic_read_minisymbols
+#define bfd_mach_o_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol
+#define bfd_mach_o_get_reloc_upper_bound _bfd_norelocs_get_reloc_upper_bound
+#define bfd_mach_o_canonicalize_reloc _bfd_norelocs_canonicalize_reloc
+#define bfd_mach_o_bfd_reloc_type_lookup _bfd_norelocs_bfd_reloc_type_lookup
#define bfd_mach_o_bfd_get_relocated_section_contents bfd_generic_get_relocated_section_contents
-#define bfd_mach_o_bfd_relax_section bfd_generic_relax_section
-#define bfd_mach_o_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
-#define bfd_mach_o_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
-#define bfd_mach_o_bfd_link_add_symbols _bfd_generic_link_add_symbols
-#define bfd_mach_o_bfd_link_just_syms _bfd_generic_link_just_syms
-#define bfd_mach_o_bfd_final_link _bfd_generic_final_link
-#define bfd_mach_o_bfd_link_split_section _bfd_generic_link_split_section
-#define bfd_mach_o_set_arch_mach bfd_default_set_arch_mach
-#define bfd_mach_o_bfd_merge_private_bfd_data _bfd_generic_bfd_merge_private_bfd_data
-#define bfd_mach_o_bfd_set_private_flags _bfd_generic_bfd_set_private_flags
-#define bfd_mach_o_bfd_print_private_bfd_data _bfd_generic_bfd_print_private_bfd_data
-#define bfd_mach_o_get_section_contents _bfd_generic_get_section_contents
-#define bfd_mach_o_set_section_contents _bfd_generic_set_section_contents
-#define bfd_mach_o_bfd_gc_sections bfd_generic_gc_sections
-#define bfd_mach_o_bfd_merge_sections bfd_generic_merge_sections
-#define bfd_mach_o_bfd_is_group_section bfd_generic_is_group_section
-#define bfd_mach_o_bfd_discard_group bfd_generic_discard_group
-#define bfd_mach_o_section_already_linked \
- _bfd_generic_section_already_linked
-#define bfd_mach_o_bfd_copy_private_header_data _bfd_generic_bfd_copy_private_header_data
-
-static bfd_boolean bfd_mach_o_bfd_copy_private_symbol_data
- PARAMS ((bfd *, asymbol *, bfd *, asymbol *));
-static bfd_boolean bfd_mach_o_bfd_copy_private_section_data
- PARAMS ((bfd *, asection *, bfd *, asection *));
-static bfd_boolean bfd_mach_o_bfd_copy_private_bfd_data
- PARAMS ((bfd *, bfd *));
-static long bfd_mach_o_count_symbols
- PARAMS ((bfd *));
-static long bfd_mach_o_get_symtab_upper_bound
- PARAMS ((bfd *));
-static long bfd_mach_o_canonicalize_symtab
- PARAMS ((bfd *, asymbol **));
-static void bfd_mach_o_get_symbol_info
- PARAMS ((bfd *, asymbol *, symbol_info *));
-static void bfd_mach_o_print_symbol
- PARAMS ((bfd *, PTR, asymbol *, bfd_print_symbol_type));
-static void bfd_mach_o_convert_architecture
- PARAMS ((bfd_mach_o_cpu_type, bfd_mach_o_cpu_subtype,
- enum bfd_architecture *, unsigned long *));
-static bfd_boolean bfd_mach_o_write_contents
- PARAMS ((bfd *));
-static int bfd_mach_o_sizeof_headers
- PARAMS ((bfd *, bfd_boolean));
-static asymbol * bfd_mach_o_make_empty_symbol
- PARAMS ((bfd *));
-static int bfd_mach_o_write_header
- PARAMS ((bfd *, bfd_mach_o_header *));
-static int bfd_mach_o_read_header
- PARAMS ((bfd *, bfd_mach_o_header *));
-static asection * bfd_mach_o_make_bfd_section
- PARAMS ((bfd *, bfd_mach_o_section *));
-static int bfd_mach_o_scan_read_section
- PARAMS ((bfd *, bfd_mach_o_section *, bfd_vma));
-static int bfd_mach_o_scan_write_section
- PARAMS ((bfd *, bfd_mach_o_section *, bfd_vma));
-static int bfd_mach_o_scan_write_symtab_symbols
- PARAMS ((bfd *, bfd_mach_o_load_command *));
-static int bfd_mach_o_scan_write_thread
- PARAMS ((bfd *, bfd_mach_o_load_command *));
-static int bfd_mach_o_scan_read_dylinker
- PARAMS ((bfd *, bfd_mach_o_load_command *));
-static int bfd_mach_o_scan_read_dylib
- PARAMS ((bfd *, bfd_mach_o_load_command *));
-static int bfd_mach_o_scan_read_prebound_dylib
- PARAMS ((bfd *, bfd_mach_o_load_command *));
-static int bfd_mach_o_scan_read_thread
- PARAMS ((bfd *, bfd_mach_o_load_command *));
-static int bfd_mach_o_scan_write_symtab
- PARAMS ((bfd *, bfd_mach_o_load_command *));
-static int bfd_mach_o_scan_read_dysymtab
- PARAMS ((bfd *, bfd_mach_o_load_command *));
-static int bfd_mach_o_scan_read_symtab
- PARAMS ((bfd *, bfd_mach_o_load_command *));
-static int bfd_mach_o_scan_read_segment
- PARAMS ((bfd *, bfd_mach_o_load_command *));
-static int bfd_mach_o_scan_write_segment
- PARAMS ((bfd *, bfd_mach_o_load_command *));
-static int bfd_mach_o_scan_read_command
- PARAMS ((bfd *, bfd_mach_o_load_command *));
-static void bfd_mach_o_flatten_sections
- PARAMS ((bfd *));
-static const char * bfd_mach_o_i386_flavour_string
- PARAMS ((unsigned int));
-static const char * bfd_mach_o_ppc_flavour_string
- PARAMS ((unsigned int));
+#define bfd_mach_o_bfd_relax_section bfd_generic_relax_section
+#define bfd_mach_o_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
+#define bfd_mach_o_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
+#define bfd_mach_o_bfd_link_add_symbols _bfd_generic_link_add_symbols
+#define bfd_mach_o_bfd_link_just_syms _bfd_generic_link_just_syms
+#define bfd_mach_o_bfd_final_link _bfd_generic_final_link
+#define bfd_mach_o_bfd_link_split_section _bfd_generic_link_split_section
+#define bfd_mach_o_set_arch_mach bfd_default_set_arch_mach
+#define bfd_mach_o_bfd_merge_private_bfd_data _bfd_generic_bfd_merge_private_bfd_data
+#define bfd_mach_o_bfd_set_private_flags _bfd_generic_bfd_set_private_flags
+#define bfd_mach_o_bfd_print_private_bfd_data _bfd_generic_bfd_print_private_bfd_data
+#define bfd_mach_o_get_section_contents _bfd_generic_get_section_contents
+#define bfd_mach_o_set_section_contents _bfd_generic_set_section_contents
+#define bfd_mach_o_bfd_gc_sections bfd_generic_gc_sections
+#define bfd_mach_o_bfd_merge_sections bfd_generic_merge_sections
+#define bfd_mach_o_bfd_is_group_section bfd_generic_is_group_section
+#define bfd_mach_o_bfd_discard_group bfd_generic_discard_group
+#define bfd_mach_o_section_already_linked _bfd_generic_section_already_linked
+#define bfd_mach_o_bfd_copy_private_header_data _bfd_generic_bfd_copy_private_header_data
+
/* The flags field of a section structure is separated into two parts a section
type and section attributes. The section types are mutually exclusive (it
#define N_INDR 0xa
bfd_boolean
-bfd_mach_o_valid (abfd)
- bfd *abfd;
+bfd_mach_o_valid (bfd *abfd)
{
if (abfd == NULL || abfd->xvec == NULL)
return 0;
to the output symbol. */
static bfd_boolean
-bfd_mach_o_bfd_copy_private_symbol_data (ibfd, isymbol, obfd, osymbol)
- bfd *ibfd ATTRIBUTE_UNUSED;
- asymbol *isymbol ATTRIBUTE_UNUSED;
- bfd *obfd ATTRIBUTE_UNUSED;
- asymbol *osymbol ATTRIBUTE_UNUSED;
+bfd_mach_o_bfd_copy_private_symbol_data (bfd *ibfd ATTRIBUTE_UNUSED,
+ asymbol *isymbol ATTRIBUTE_UNUSED,
+ bfd *obfd ATTRIBUTE_UNUSED,
+ asymbol *osymbol ATTRIBUTE_UNUSED)
{
return TRUE;
}
to the output section. */
static bfd_boolean
-bfd_mach_o_bfd_copy_private_section_data (ibfd, isection, obfd, osection)
- bfd *ibfd ATTRIBUTE_UNUSED;
- asection *isection ATTRIBUTE_UNUSED;
- bfd *obfd ATTRIBUTE_UNUSED;
- asection *osection ATTRIBUTE_UNUSED;
+bfd_mach_o_bfd_copy_private_section_data (bfd *ibfd ATTRIBUTE_UNUSED,
+ asection *isection ATTRIBUTE_UNUSED,
+ bfd *obfd ATTRIBUTE_UNUSED,
+ asection *osection ATTRIBUTE_UNUSED)
{
return TRUE;
}
to the output bfd. */
static bfd_boolean
-bfd_mach_o_bfd_copy_private_bfd_data (ibfd, obfd)
- bfd *ibfd;
- bfd *obfd;
+bfd_mach_o_bfd_copy_private_bfd_data (bfd *ibfd, bfd *obfd)
{
BFD_ASSERT (bfd_mach_o_valid (ibfd));
BFD_ASSERT (bfd_mach_o_valid (obfd));
}
static long
-bfd_mach_o_count_symbols (abfd)
- bfd *abfd;
+bfd_mach_o_count_symbols (bfd *abfd)
{
bfd_mach_o_data_struct *mdata = NULL;
long nsyms = 0;
}
static long
-bfd_mach_o_get_symtab_upper_bound (abfd)
- bfd *abfd;
+bfd_mach_o_get_symtab_upper_bound (bfd *abfd)
{
long nsyms = bfd_mach_o_count_symbols (abfd);
}
static long
-bfd_mach_o_canonicalize_symtab (abfd, alocation)
- bfd *abfd;
- asymbol **alocation;
+bfd_mach_o_canonicalize_symtab (bfd *abfd, asymbol **alocation)
{
bfd_mach_o_data_struct *mdata = abfd->tdata.mach_o_data;
long nsyms = bfd_mach_o_count_symbols (abfd);
}
static void
-bfd_mach_o_get_symbol_info (abfd, symbol, ret)
- bfd *abfd ATTRIBUTE_UNUSED;
- asymbol *symbol;
- symbol_info *ret;
+bfd_mach_o_get_symbol_info (bfd *abfd ATTRIBUTE_UNUSED,
+ asymbol *symbol,
+ symbol_info *ret)
{
bfd_symbol_info (symbol, ret);
}
static void
-bfd_mach_o_print_symbol (abfd, afile, symbol, how)
- bfd *abfd;
- PTR afile;
- asymbol *symbol;
- bfd_print_symbol_type how;
+bfd_mach_o_print_symbol (bfd *abfd,
+ PTR afile,
+ asymbol *symbol,
+ bfd_print_symbol_type how)
{
FILE *file = (FILE *) afile;
}
static void
-bfd_mach_o_convert_architecture (mtype, msubtype, type, subtype)
- bfd_mach_o_cpu_type mtype;
- bfd_mach_o_cpu_subtype msubtype ATTRIBUTE_UNUSED;
- enum bfd_architecture *type;
- unsigned long *subtype;
+bfd_mach_o_convert_architecture (bfd_mach_o_cpu_type mtype,
+ bfd_mach_o_cpu_subtype msubtype ATTRIBUTE_UNUSED,
+ enum bfd_architecture *type,
+ unsigned long *subtype)
{
*subtype = bfd_arch_unknown;
}
}
+static int
+bfd_mach_o_write_header (bfd *abfd, bfd_mach_o_header *header)
+{
+ unsigned char buf[28];
+
+ bfd_h_put_32 (abfd, header->magic, buf + 0);
+ bfd_h_put_32 (abfd, header->cputype, buf + 4);
+ bfd_h_put_32 (abfd, header->cpusubtype, buf + 8);
+ bfd_h_put_32 (abfd, header->filetype, buf + 12);
+ bfd_h_put_32 (abfd, header->ncmds, buf + 16);
+ bfd_h_put_32 (abfd, header->sizeofcmds, buf + 20);
+ bfd_h_put_32 (abfd, header->flags, buf + 24);
+
+ bfd_seek (abfd, 0, SEEK_SET);
+ if (bfd_bwrite ((PTR) buf, 28, abfd) != 28)
+ return -1;
+
+ return 0;
+}
+
+static int
+bfd_mach_o_scan_write_thread (bfd *abfd,
+ bfd_mach_o_load_command *command)
+{
+ bfd_mach_o_thread_command *cmd = &command->command.thread;
+ unsigned int i;
+ unsigned char buf[8];
+ bfd_vma offset;
+ unsigned int nflavours;
+
+ BFD_ASSERT ((command->type == BFD_MACH_O_LC_THREAD)
+ || (command->type == BFD_MACH_O_LC_UNIXTHREAD));
+
+ offset = 8;
+ nflavours = 0;
+ for (i = 0; i < cmd->nflavours; i++)
+ {
+ BFD_ASSERT ((cmd->flavours[i].size % 4) == 0);
+ BFD_ASSERT (cmd->flavours[i].offset == (command->offset + offset + 8));
+
+ bfd_h_put_32 (abfd, cmd->flavours[i].flavour, buf);
+ bfd_h_put_32 (abfd, (cmd->flavours[i].size / 4), buf + 4);
+
+ bfd_seek (abfd, command->offset + offset, SEEK_SET);
+ if (bfd_bwrite ((PTR) buf, 8, abfd) != 8)
+ return -1;
+
+ offset += cmd->flavours[i].size + 8;
+ }
+
+ return 0;
+}
+
+static int
+bfd_mach_o_scan_write_section (bfd *abfd,
+ bfd_mach_o_section *section,
+ bfd_vma offset)
+{
+ unsigned char buf[68];
+
+ memcpy (buf, section->sectname, 16);
+ memcpy (buf + 16, section->segname, 16);
+ bfd_h_put_32 (abfd, section->addr, buf + 32);
+ bfd_h_put_32 (abfd, section->size, buf + 36);
+ bfd_h_put_32 (abfd, section->offset, buf + 40);
+ bfd_h_put_32 (abfd, section->align, buf + 44);
+ bfd_h_put_32 (abfd, section->reloff, buf + 48);
+ bfd_h_put_32 (abfd, section->nreloc, buf + 52);
+ bfd_h_put_32 (abfd, section->flags, buf + 56);
+ /* bfd_h_put_32 (abfd, section->reserved1, buf + 60); */
+ /* bfd_h_put_32 (abfd, section->reserved2, buf + 64); */
+
+ bfd_seek (abfd, offset, SEEK_SET);
+ if (bfd_bwrite ((PTR) buf, 68, abfd) != 68)
+ return -1;
+
+ return 0;
+}
+
+static int
+bfd_mach_o_scan_write_segment (bfd *abfd, bfd_mach_o_load_command *command)
+{
+ unsigned char buf[48];
+ bfd_mach_o_segment_command *seg = &command->command.segment;
+ unsigned long i;
+
+ BFD_ASSERT (command->type == BFD_MACH_O_LC_SEGMENT);
+
+ memcpy (buf, seg->segname, 16);
+ bfd_h_put_32 (abfd, seg->vmaddr, buf + 16);
+ bfd_h_put_32 (abfd, seg->vmsize, buf + 20);
+ bfd_h_put_32 (abfd, seg->fileoff, buf + 24);
+ bfd_h_put_32 (abfd, seg->filesize, buf + 28);
+ bfd_h_put_32 (abfd, 0 /* seg->maxprot */, buf + 32);
+ bfd_h_put_32 (abfd, 0 /* seg->initprot */, buf + 36);
+ bfd_h_put_32 (abfd, seg->nsects, buf + 40);
+ bfd_h_put_32 (abfd, seg->flags, buf + 44);
+
+ bfd_seek (abfd, command->offset + 8, SEEK_SET);
+ if (bfd_bwrite ((PTR) buf, 48, abfd) != 48)
+ return -1;
+
+ {
+ char buf[1024];
+ bfd_vma nbytes = seg->filesize;
+ bfd_vma curoff = seg->fileoff;
+
+ while (nbytes > 0)
+ {
+ bfd_vma thisread = nbytes;
+
+ if (thisread > 1024)
+ thisread = 1024;
+
+ bfd_seek (abfd, curoff, SEEK_SET);
+ if (bfd_bread ((PTR) buf, thisread, abfd) != thisread)
+ return -1;
+
+ bfd_seek (abfd, curoff, SEEK_SET);
+ if (bfd_bwrite ((PTR) buf, thisread, abfd) != thisread)
+ return -1;
+
+ nbytes -= thisread;
+ curoff += thisread;
+ }
+ }
+
+ for (i = 0; i < seg->nsects; i++)
+ {
+ bfd_vma segoff = command->offset + 48 + 8 + (i * 68);
+
+ if (bfd_mach_o_scan_write_section (abfd, &seg->sections[i], segoff) != 0)
+ return -1;
+ }
+
+ return 0;
+}
+
+static int
+bfd_mach_o_scan_write_symtab_symbols (bfd *abfd,
+ bfd_mach_o_load_command *command)
+{
+ bfd_mach_o_symtab_command *sym = &command->command.symtab;
+ asymbol *s = NULL;
+ unsigned long i;
+
+ for (i = 0; i < sym->nsyms; i++)
+ {
+ unsigned char buf[12];
+ bfd_vma symoff = sym->symoff + (i * 12);
+ unsigned char ntype = 0;
+ unsigned char nsect = 0;
+ short ndesc = 0;
+
+ s = &sym->symbols[i];
+
+ /* Instead just set from the stored values. */
+ ntype = (s->udata.i >> 24) & 0xff;
+ nsect = (s->udata.i >> 16) & 0xff;
+ ndesc = s->udata.i & 0xffff;
+
+ bfd_h_put_32 (abfd, s->name - sym->strtab, buf);
+ bfd_h_put_8 (abfd, ntype, buf + 4);
+ bfd_h_put_8 (abfd, nsect, buf + 5);
+ bfd_h_put_16 (abfd, ndesc, buf + 6);
+ bfd_h_put_32 (abfd, s->section->vma + s->value, buf + 8);
+
+ bfd_seek (abfd, symoff, SEEK_SET);
+ if (bfd_bwrite ((PTR) buf, 12, abfd) != 12)
+ {
+ fprintf (stderr, "bfd_mach_o_scan_write_symtab_symbols: unable to write %d bytes at %lu\n",
+ 12, (unsigned long) symoff);
+ return -1;
+ }
+ }
+
+ return 0;
+}
+
+static int
+bfd_mach_o_scan_write_symtab (bfd *abfd, bfd_mach_o_load_command *command)
+{
+ bfd_mach_o_symtab_command *seg = &command->command.symtab;
+ unsigned char buf[16];
+
+ BFD_ASSERT (command->type == BFD_MACH_O_LC_SYMTAB);
+
+ bfd_h_put_32 (abfd, seg->symoff, buf);
+ bfd_h_put_32 (abfd, seg->nsyms, buf + 4);
+ bfd_h_put_32 (abfd, seg->stroff, buf + 8);
+ bfd_h_put_32 (abfd, seg->strsize, buf + 12);
+
+ bfd_seek (abfd, command->offset + 8, SEEK_SET);
+ if (bfd_bwrite ((PTR) buf, 16, abfd) != 16)
+ return -1;
+
+ if (bfd_mach_o_scan_write_symtab_symbols (abfd, command) != 0)
+ return -1;
+
+ return 0;
+}
+
static bfd_boolean
-bfd_mach_o_write_contents (abfd)
- bfd *abfd;
+bfd_mach_o_write_contents (bfd *abfd)
{
unsigned int i;
asection *s;
}
static int
-bfd_mach_o_sizeof_headers (a, b)
- bfd *a ATTRIBUTE_UNUSED;
- bfd_boolean b ATTRIBUTE_UNUSED;
+bfd_mach_o_sizeof_headers (bfd *a ATTRIBUTE_UNUSED,
+ bfd_boolean b ATTRIBUTE_UNUSED)
{
return 0;
}
bfd_make_section_anyway wants to create a symbol for the section. */
static asymbol *
-bfd_mach_o_make_empty_symbol (abfd)
- bfd *abfd;
+bfd_mach_o_make_empty_symbol (bfd *abfd)
{
asymbol *new;
- new = (asymbol *) bfd_zalloc (abfd, sizeof (asymbol));
+ new = bfd_zalloc (abfd, sizeof (* new));
if (new == NULL)
return new;
new->the_bfd = abfd;
}
static int
-bfd_mach_o_write_header (abfd, header)
- bfd *abfd;
- bfd_mach_o_header *header;
-{
- unsigned char buf[28];
-
- bfd_h_put_32 (abfd, header->magic, buf + 0);
- bfd_h_put_32 (abfd, header->cputype, buf + 4);
- bfd_h_put_32 (abfd, header->cpusubtype, buf + 8);
- bfd_h_put_32 (abfd, header->filetype, buf + 12);
- bfd_h_put_32 (abfd, header->ncmds, buf + 16);
- bfd_h_put_32 (abfd, header->sizeofcmds, buf + 20);
- bfd_h_put_32 (abfd, header->flags, buf + 24);
-
- bfd_seek (abfd, 0, SEEK_SET);
- if (bfd_bwrite ((PTR) buf, 28, abfd) != 28)
- return -1;
-
- return 0;
-}
-
-static int
-bfd_mach_o_read_header (abfd, header)
- bfd *abfd;
- bfd_mach_o_header *header;
+bfd_mach_o_read_header (bfd *abfd, bfd_mach_o_header *header)
{
unsigned char buf[28];
bfd_vma (*get32) (const void *) = NULL;
}
static asection *
-bfd_mach_o_make_bfd_section (abfd, section)
- bfd *abfd;
- bfd_mach_o_section *section;
+bfd_mach_o_make_bfd_section (bfd *abfd, bfd_mach_o_section *section)
{
asection *bfdsec;
char *sname;
+ strlen (section->segname) + 1
+ strlen (section->sectname) + 1;
- sname = (char *) bfd_alloc (abfd, snamelen);
+ sname = bfd_alloc (abfd, snamelen);
if (sname == NULL)
return NULL;
sprintf (sname, "%s.%s.%s", prefix, section->segname, section->sectname);
}
static int
-bfd_mach_o_scan_read_section (abfd, section, offset)
- bfd *abfd;
- bfd_mach_o_section *section;
- bfd_vma offset;
+bfd_mach_o_scan_read_section (bfd *abfd,
+ bfd_mach_o_section *section,
+ bfd_vma offset)
{
unsigned char buf[68];
return 0;
}
-static int
-bfd_mach_o_scan_write_section (abfd, section, offset)
- bfd *abfd;
- bfd_mach_o_section *section;
- bfd_vma offset;
-{
- unsigned char buf[68];
-
- memcpy (buf, section->sectname, 16);
- memcpy (buf + 16, section->segname, 16);
- bfd_h_put_32 (abfd, section->addr, buf + 32);
- bfd_h_put_32 (abfd, section->size, buf + 36);
- bfd_h_put_32 (abfd, section->offset, buf + 40);
- bfd_h_put_32 (abfd, section->align, buf + 44);
- bfd_h_put_32 (abfd, section->reloff, buf + 48);
- bfd_h_put_32 (abfd, section->nreloc, buf + 52);
- bfd_h_put_32 (abfd, section->flags, buf + 56);
- /* bfd_h_put_32 (abfd, section->reserved1, buf + 60); */
- /* bfd_h_put_32 (abfd, section->reserved2, buf + 64); */
-
- bfd_seek (abfd, offset, SEEK_SET);
- if (bfd_bwrite ((PTR) buf, 68, abfd) != 68)
- return -1;
-
- return 0;
-}
-
-static int
-bfd_mach_o_scan_write_symtab_symbols (abfd, command)
- bfd *abfd;
- bfd_mach_o_load_command *command;
-{
- bfd_mach_o_symtab_command *sym = &command->command.symtab;
- asymbol *s = NULL;
- unsigned long i;
-
- for (i = 0; i < sym->nsyms; i++)
- {
- unsigned char buf[12];
- bfd_vma symoff = sym->symoff + (i * 12);
- unsigned char ntype = 0;
- unsigned char nsect = 0;
- short ndesc = 0;
-
- s = &sym->symbols[i];
-
- /* Instead just set from the stored values. */
- ntype = (s->udata.i >> 24) & 0xff;
- nsect = (s->udata.i >> 16) & 0xff;
- ndesc = s->udata.i & 0xffff;
-
- bfd_h_put_32 (abfd, s->name - sym->strtab, buf);
- bfd_h_put_8 (abfd, ntype, buf + 4);
- bfd_h_put_8 (abfd, nsect, buf + 5);
- bfd_h_put_16 (abfd, ndesc, buf + 6);
- bfd_h_put_32 (abfd, s->section->vma + s->value, buf + 8);
-
- bfd_seek (abfd, symoff, SEEK_SET);
- if (bfd_bwrite ((PTR) buf, 12, abfd) != 12)
- {
- fprintf (stderr, "bfd_mach_o_scan_write_symtab_symbols: unable to write %d bytes at %lu\n",
- 12, (unsigned long) symoff);
- return -1;
- }
- }
-
- return 0;
-}
-
int
-bfd_mach_o_scan_read_symtab_symbol (abfd, sym, s, i)
- bfd *abfd;
- bfd_mach_o_symtab_command *sym;
- asymbol *s;
- unsigned long i;
+bfd_mach_o_scan_read_symtab_symbol (bfd *abfd,
+ bfd_mach_o_symtab_command *sym,
+ asymbol *s,
+ unsigned long i)
{
bfd_mach_o_data_struct *mdata = abfd->tdata.mach_o_data;
bfd_vma symoff = sym->symoff + (i * 12);
}
int
-bfd_mach_o_scan_read_symtab_strtab (abfd, sym)
- bfd *abfd;
- bfd_mach_o_symtab_command *sym;
+bfd_mach_o_scan_read_symtab_strtab (bfd *abfd,
+ bfd_mach_o_symtab_command *sym)
{
BFD_ASSERT (sym->strtab == NULL);
}
int
-bfd_mach_o_scan_read_symtab_symbols (abfd, sym)
- bfd *abfd;
- bfd_mach_o_symtab_command *sym;
+bfd_mach_o_scan_read_symtab_symbols (bfd *abfd,
+ bfd_mach_o_symtab_command *sym)
{
unsigned long i;
int ret;
}
int
-bfd_mach_o_scan_read_dysymtab_symbol (abfd, dysym, sym, s, i)
- bfd *abfd;
- bfd_mach_o_dysymtab_command *dysym;
- bfd_mach_o_symtab_command *sym;
- asymbol *s;
- unsigned long i;
+bfd_mach_o_scan_read_dysymtab_symbol (bfd *abfd,
+ bfd_mach_o_dysymtab_command *dysym,
+ bfd_mach_o_symtab_command *sym,
+ asymbol *s,
+ unsigned long i)
{
unsigned long isymoff = dysym->indirectsymoff + (i * 4);
unsigned long symindex;
}
static const char *
-bfd_mach_o_i386_flavour_string (flavour)
- unsigned int flavour;
+bfd_mach_o_i386_flavour_string (unsigned int flavour)
{
switch ((int) flavour)
{
}
static const char *
-bfd_mach_o_ppc_flavour_string (flavour)
- unsigned int flavour;
+bfd_mach_o_ppc_flavour_string (unsigned int flavour)
{
switch ((int) flavour)
{
}
static int
-bfd_mach_o_scan_write_thread (abfd, command)
- bfd *abfd;
- bfd_mach_o_load_command *command;
-{
- bfd_mach_o_thread_command *cmd = &command->command.thread;
- unsigned int i;
- unsigned char buf[8];
- bfd_vma offset;
- unsigned int nflavours;
-
- BFD_ASSERT ((command->type == BFD_MACH_O_LC_THREAD)
- || (command->type == BFD_MACH_O_LC_UNIXTHREAD));
-
- offset = 8;
- nflavours = 0;
- for (i = 0; i < cmd->nflavours; i++)
- {
- BFD_ASSERT ((cmd->flavours[i].size % 4) == 0);
- BFD_ASSERT (cmd->flavours[i].offset == (command->offset + offset + 8));
-
- bfd_h_put_32 (abfd, cmd->flavours[i].flavour, buf);
- bfd_h_put_32 (abfd, (cmd->flavours[i].size / 4), buf + 4);
-
- bfd_seek (abfd, command->offset + offset, SEEK_SET);
- if (bfd_bwrite ((PTR) buf, 8, abfd) != 8)
- return -1;
-
- offset += cmd->flavours[i].size + 8;
- }
-
- return 0;
-}
-
-static int
-bfd_mach_o_scan_read_dylinker (abfd, command)
- bfd *abfd;
- bfd_mach_o_load_command *command;
+bfd_mach_o_scan_read_dylinker (bfd *abfd,
+ bfd_mach_o_load_command *command)
{
bfd_mach_o_dylinker_command *cmd = &command->command.dylinker;
unsigned char buf[4];
else
abort ();
- sname = (char *) bfd_alloc (abfd, strlen (prefix) + 1);
+ sname = bfd_alloc (abfd, strlen (prefix) + 1);
if (sname == NULL)
return -1;
strcpy (sname, prefix);
}
static int
-bfd_mach_o_scan_read_dylib (abfd, command)
- bfd *abfd;
- bfd_mach_o_load_command *command;
+bfd_mach_o_scan_read_dylib (bfd *abfd, bfd_mach_o_load_command *command)
{
bfd_mach_o_dylib_command *cmd = &command->command.dylib;
unsigned char buf[16];
else
abort ();
- sname = (char *) bfd_alloc (abfd, strlen (prefix) + 1);
+ sname = bfd_alloc (abfd, strlen (prefix) + 1);
if (sname == NULL)
return -1;
strcpy (sname, prefix);
}
static int
-bfd_mach_o_scan_read_prebound_dylib (abfd, command)
- bfd *abfd ATTRIBUTE_UNUSED;
- bfd_mach_o_load_command *command ATTRIBUTE_UNUSED;
+bfd_mach_o_scan_read_prebound_dylib (bfd *abfd ATTRIBUTE_UNUSED,
+ bfd_mach_o_load_command *command ATTRIBUTE_UNUSED)
{
/* bfd_mach_o_prebound_dylib_command *cmd = &command->command.prebound_dylib; */
}
static int
-bfd_mach_o_scan_read_thread (abfd, command)
- bfd *abfd;
- bfd_mach_o_load_command *command;
+bfd_mach_o_scan_read_thread (bfd *abfd, bfd_mach_o_load_command *command)
{
bfd_mach_o_data_struct *mdata = NULL;
bfd_mach_o_thread_command *cmd = &command->command.thread;
nflavours++;
}
- cmd->flavours =
- ((bfd_mach_o_thread_flavour *)
- bfd_alloc (abfd, nflavours * sizeof (bfd_mach_o_thread_flavour)));
+ cmd->flavours = bfd_alloc (abfd, nflavours * sizeof (bfd_mach_o_thread_flavour));
if (cmd->flavours == NULL)
return -1;
cmd->nflavours = nflavours;
}
snamelen = strlen (prefix) + 1 + 20 + 1 + strlen (flavourstr) + 1;
- sname = (char *) bfd_alloc (abfd, snamelen);
+ sname = bfd_alloc (abfd, snamelen);
if (sname == NULL)
return -1;
}
static int
-bfd_mach_o_scan_write_symtab (abfd, command)
- bfd *abfd;
- bfd_mach_o_load_command *command;
-{
- bfd_mach_o_symtab_command *seg = &command->command.symtab;
- unsigned char buf[16];
-
- BFD_ASSERT (command->type == BFD_MACH_O_LC_SYMTAB);
-
- bfd_h_put_32 (abfd, seg->symoff, buf);
- bfd_h_put_32 (abfd, seg->nsyms, buf + 4);
- bfd_h_put_32 (abfd, seg->stroff, buf + 8);
- bfd_h_put_32 (abfd, seg->strsize, buf + 12);
-
- bfd_seek (abfd, command->offset + 8, SEEK_SET);
- if (bfd_bwrite ((PTR) buf, 16, abfd) != 16)
- return -1;
-
- if (bfd_mach_o_scan_write_symtab_symbols (abfd, command) != 0)
- return -1;
-
- return 0;
-}
-
-static int
-bfd_mach_o_scan_read_dysymtab (abfd, command)
- bfd *abfd;
- bfd_mach_o_load_command *command;
+bfd_mach_o_scan_read_dysymtab (bfd *abfd, bfd_mach_o_load_command *command)
{
bfd_mach_o_dysymtab_command *seg = &command->command.dysymtab;
unsigned char buf[72];
}
static int
-bfd_mach_o_scan_read_symtab (abfd, command)
- bfd *abfd;
- bfd_mach_o_load_command *command;
+bfd_mach_o_scan_read_symtab (bfd *abfd, bfd_mach_o_load_command *command)
{
bfd_mach_o_symtab_command *seg = &command->command.symtab;
unsigned char buf[16];
seg->symbols = NULL;
seg->strtab = NULL;
- sname = (char *) bfd_alloc (abfd, strlen (prefix) + 1);
+ sname = bfd_alloc (abfd, strlen (prefix) + 1);
if (sname == NULL)
return -1;
strcpy (sname, prefix);
seg->stabs_segment = bfdsec;
prefix = "LC_SYMTAB.stabstr";
- sname = (char *) bfd_alloc (abfd, strlen (prefix) + 1);
+ sname = bfd_alloc (abfd, strlen (prefix) + 1);
if (sname == NULL)
return -1;
strcpy (sname, prefix);
}
static int
-bfd_mach_o_scan_read_segment (abfd, command)
- bfd *abfd;
- bfd_mach_o_load_command *command;
+bfd_mach_o_scan_read_segment (bfd *abfd, bfd_mach_o_load_command *command)
{
unsigned char buf[48];
bfd_mach_o_segment_command *seg = &command->command.segment;
seg->flags = bfd_h_get_32 (abfd, buf + 44);
snamelen = strlen (prefix) + 1 + strlen (seg->segname) + 1;
- sname = (char *) bfd_alloc (abfd, snamelen);
+ sname = bfd_alloc (abfd, snamelen);
if (sname == NULL)
return -1;
sprintf (sname, "%s.%s", prefix, seg->segname);
if (seg->nsects != 0)
{
- seg->sections =
- ((bfd_mach_o_section *)
- bfd_alloc (abfd, seg->nsects * sizeof (bfd_mach_o_section)));
+ seg->sections = bfd_alloc (abfd, seg->nsects * sizeof (bfd_mach_o_section));
if (seg->sections == NULL)
return -1;
}
static int
-bfd_mach_o_scan_write_segment (abfd, command)
- bfd *abfd;
- bfd_mach_o_load_command *command;
-{
- unsigned char buf[48];
- bfd_mach_o_segment_command *seg = &command->command.segment;
- unsigned long i;
-
- BFD_ASSERT (command->type == BFD_MACH_O_LC_SEGMENT);
-
- memcpy (buf, seg->segname, 16);
- bfd_h_put_32 (abfd, seg->vmaddr, buf + 16);
- bfd_h_put_32 (abfd, seg->vmsize, buf + 20);
- bfd_h_put_32 (abfd, seg->fileoff, buf + 24);
- bfd_h_put_32 (abfd, seg->filesize, buf + 28);
- bfd_h_put_32 (abfd, 0 /* seg->maxprot */, buf + 32);
- bfd_h_put_32 (abfd, 0 /* seg->initprot */, buf + 36);
- bfd_h_put_32 (abfd, seg->nsects, buf + 40);
- bfd_h_put_32 (abfd, seg->flags, buf + 44);
-
- bfd_seek (abfd, command->offset + 8, SEEK_SET);
- if (bfd_bwrite ((PTR) buf, 48, abfd) != 48)
- return -1;
-
- {
- char buf[1024];
- bfd_vma nbytes = seg->filesize;
- bfd_vma curoff = seg->fileoff;
-
- while (nbytes > 0)
- {
- bfd_vma thisread = nbytes;
-
- if (thisread > 1024)
- thisread = 1024;
-
- bfd_seek (abfd, curoff, SEEK_SET);
- if (bfd_bread ((PTR) buf, thisread, abfd) != thisread)
- return -1;
-
- bfd_seek (abfd, curoff, SEEK_SET);
- if (bfd_bwrite ((PTR) buf, thisread, abfd) != thisread)
- return -1;
-
- nbytes -= thisread;
- curoff += thisread;
- }
- }
-
- for (i = 0; i < seg->nsects; i++)
- {
- bfd_vma segoff = command->offset + 48 + 8 + (i * 68);
-
- if (bfd_mach_o_scan_write_section (abfd, &seg->sections[i], segoff) != 0)
- return -1;
- }
-
- return 0;
-}
-
-static int
-bfd_mach_o_scan_read_command (abfd, command)
- bfd *abfd;
- bfd_mach_o_load_command *command;
+bfd_mach_o_scan_read_command (bfd *abfd, bfd_mach_o_load_command *command)
{
unsigned char buf[8];
}
static void
-bfd_mach_o_flatten_sections (abfd)
- bfd *abfd;
+bfd_mach_o_flatten_sections (bfd *abfd)
{
bfd_mach_o_data_struct *mdata = abfd->tdata.mach_o_data;
long csect = 0;
}
int
-bfd_mach_o_scan_start_address (abfd)
- bfd *abfd;
+bfd_mach_o_scan_start_address (bfd *abfd)
{
bfd_mach_o_data_struct *mdata = abfd->tdata.mach_o_data;
bfd_mach_o_thread_command *cmd = NULL;
}
int
-bfd_mach_o_scan (abfd, header, mdata)
- bfd *abfd;
- bfd_mach_o_header *header;
- bfd_mach_o_data_struct *mdata;
+bfd_mach_o_scan (bfd *abfd,
+ bfd_mach_o_header *header,
+ bfd_mach_o_data_struct *mdata)
{
unsigned int i;
enum bfd_architecture cputype;
if (header->ncmds != 0)
{
- mdata->commands =
- ((bfd_mach_o_load_command *)
- bfd_alloc (abfd, header->ncmds * sizeof (bfd_mach_o_load_command)));
+ mdata->commands = bfd_alloc (abfd, header->ncmds * sizeof (bfd_mach_o_load_command));
if (mdata->commands == NULL)
return -1;
}
bfd_boolean
-bfd_mach_o_mkobject (abfd)
- bfd *abfd;
+bfd_mach_o_mkobject (bfd *abfd)
{
bfd_mach_o_data_struct *mdata = NULL;
- mdata = ((bfd_mach_o_data_struct *)
- bfd_alloc (abfd, sizeof (bfd_mach_o_data_struct)));
+ mdata = bfd_alloc (abfd, sizeof (bfd_mach_o_data_struct));
if (mdata == NULL)
return FALSE;
abfd->tdata.mach_o_data = mdata;
}
const bfd_target *
-bfd_mach_o_object_p (abfd)
- bfd *abfd;
+bfd_mach_o_object_p (bfd *abfd)
{
struct bfd_preserve preserve;
bfd_mach_o_header header;
}
const bfd_target *
-bfd_mach_o_core_p (abfd)
- bfd *abfd;
+bfd_mach_o_core_p (bfd *abfd)
{
struct bfd_preserve preserve;
bfd_mach_o_header header;
} mach_o_fat_data_struct;
const bfd_target *
-bfd_mach_o_archive_p (abfd)
- bfd *abfd;
+bfd_mach_o_archive_p (bfd *abfd)
{
mach_o_fat_data_struct *adata = NULL;
unsigned char buf[20];
if (bfd_bread ((PTR) buf, 8, abfd) != 8)
goto error;
- adata = (mach_o_fat_data_struct *)
- bfd_alloc (abfd, sizeof (mach_o_fat_data_struct));
+ adata = bfd_alloc (abfd, sizeof (mach_o_fat_data_struct));
if (adata == NULL)
goto error;
if (adata->magic != 0xcafebabe)
goto error;
- adata->archentries = (mach_o_fat_archentry *)
+ adata->archentries =
bfd_alloc (abfd, adata->nfat_arch * sizeof (mach_o_fat_archentry));
if (adata->archentries == NULL)
goto error;
}
bfd *
-bfd_mach_o_openr_next_archived_file (archive, prev)
- bfd *archive;
- bfd *prev;
+bfd_mach_o_openr_next_archived_file (bfd *archive, bfd *prev)
{
mach_o_fat_data_struct *adata;
mach_o_fat_archentry *entry = NULL;
}
int
-bfd_mach_o_lookup_section (abfd, section, mcommand, msection)
- bfd *abfd;
- asection *section;
- bfd_mach_o_load_command **mcommand;
- bfd_mach_o_section **msection;
+bfd_mach_o_lookup_section (bfd *abfd,
+ asection *section,
+ bfd_mach_o_load_command **mcommand,
+ bfd_mach_o_section **msection)
{
struct mach_o_data_struct *md = abfd->tdata.mach_o_data;
unsigned int i, j, num;
}
int
-bfd_mach_o_lookup_command (abfd, type, mcommand)
- bfd *abfd;
- bfd_mach_o_load_command_type type;
- bfd_mach_o_load_command **mcommand;
+bfd_mach_o_lookup_command (bfd *abfd,
+ bfd_mach_o_load_command_type type,
+ bfd_mach_o_load_command **mcommand)
{
struct mach_o_data_struct *md = NULL;
bfd_mach_o_load_command *ncmd = NULL;
}
unsigned long
-bfd_mach_o_stack_addr (type)
- enum bfd_mach_o_cpu_type type;
+bfd_mach_o_stack_addr (enum bfd_mach_o_cpu_type type)
{
switch (type)
{
}
int
-bfd_mach_o_core_fetch_environment (abfd, rbuf, rlen)
- bfd *abfd;
- unsigned char **rbuf;
- unsigned int *rlen;
+bfd_mach_o_core_fetch_environment (bfd *abfd,
+ unsigned char **rbuf,
+ unsigned int *rlen)
{
bfd_mach_o_data_struct *mdata = abfd->tdata.mach_o_data;
unsigned long stackaddr = bfd_mach_o_stack_addr (mdata->header.cputype);
}
char *
-bfd_mach_o_core_file_failing_command (abfd)
- bfd *abfd;
+bfd_mach_o_core_file_failing_command (bfd *abfd)
{
unsigned char *buf = NULL;
unsigned int len = 0;
}
int
-bfd_mach_o_core_file_failing_signal (abfd)
- bfd *abfd ATTRIBUTE_UNUSED;
+bfd_mach_o_core_file_failing_signal (bfd *abfd ATTRIBUTE_UNUSED)
{
return 0;
}
bfd_boolean
-bfd_mach_o_core_file_matches_executable_p (core_bfd, exec_bfd)
- bfd *core_bfd ATTRIBUTE_UNUSED;
- bfd *exec_bfd ATTRIBUTE_UNUSED;
+bfd_mach_o_core_file_matches_executable_p (bfd *core_bfd ATTRIBUTE_UNUSED,
+ bfd *exec_bfd ATTRIBUTE_UNUSED)
{
return TRUE;
}
-#define TARGET_NAME mach_o_be_vec
-#define TARGET_STRING "mach-o-be"
-#define TARGET_BIG_ENDIAN 1
-#define TARGET_ARCHIVE 0
+#define TARGET_NAME mach_o_be_vec
+#define TARGET_STRING "mach-o-be"
+#define TARGET_BIG_ENDIAN 1
+#define TARGET_ARCHIVE 0
#include "mach-o-target.c"
#undef TARGET_BIG_ENDIAN
#undef TARGET_ARCHIVE
-#define TARGET_NAME mach_o_le_vec
-#define TARGET_STRING "mach-o-le"
-#define TARGET_BIG_ENDIAN 0
-#define TARGET_ARCHIVE 0
+#define TARGET_NAME mach_o_le_vec
+#define TARGET_STRING "mach-o-le"
+#define TARGET_BIG_ENDIAN 0
+#define TARGET_ARCHIVE 0
#include "mach-o-target.c"
#undef TARGET_BIG_ENDIAN
#undef TARGET_ARCHIVE
-#define TARGET_NAME mach_o_fat_vec
-#define TARGET_STRING "mach-o-fat"
-#define TARGET_BIG_ENDIAN 1
-#define TARGET_ARCHIVE 1
+#define TARGET_NAME mach_o_fat_vec
+#define TARGET_STRING "mach-o-fat"
+#define TARGET_BIG_ENDIAN 1
+#define TARGET_ARCHIVE 1
#include "mach-o-target.c"
/* Mach-O support for BFD.
- Copyright 1999, 2000, 2001, 2002, 2003
+ Copyright 1999, 2000, 2001, 2002, 2003, 2005
Free Software Foundation, Inc.
This file is part of BFD, the Binary File Descriptor library.
#define BFD_MACH_O_N_INDR 0x0a /* Indirect. */
typedef enum bfd_mach_o_ppc_thread_flavour
- {
- BFD_MACH_O_PPC_THREAD_STATE = 1,
- BFD_MACH_O_PPC_FLOAT_STATE = 2,
- BFD_MACH_O_PPC_EXCEPTION_STATE = 3,
- BFD_MACH_O_PPC_VECTOR_STATE = 4
- }
+{
+ BFD_MACH_O_PPC_THREAD_STATE = 1,
+ BFD_MACH_O_PPC_FLOAT_STATE = 2,
+ BFD_MACH_O_PPC_EXCEPTION_STATE = 3,
+ BFD_MACH_O_PPC_VECTOR_STATE = 4
+}
bfd_mach_o_ppc_thread_flavour;
typedef enum bfd_mach_o_i386_thread_flavour
- {
- BFD_MACH_O_i386_NEW_THREAD_STATE = 1,
- BFD_MACH_O_i386_FLOAT_STATE = 2,
- BFD_MACH_O_i386_ISA_PORT_MAP_STATE = 3,
- BFD_MACH_O_i386_V86_ASSIST_STATE = 4,
- BFD_MACH_O_i386_REGS_SEGS_STATE = 5,
- BFD_MACH_O_i386_THREAD_SYSCALL_STATE = 6,
- BFD_MACH_O_i386_THREAD_STATE_NONE = 7,
- BFD_MACH_O_i386_SAVED_STATE = 8,
- BFD_MACH_O_i386_THREAD_STATE = -1,
- BFD_MACH_O_i386_THREAD_FPSTATE = -2,
- BFD_MACH_O_i386_THREAD_EXCEPTSTATE = -3,
- BFD_MACH_O_i386_THREAD_CTHREADSTATE = -4,
- }
+{
+ BFD_MACH_O_i386_NEW_THREAD_STATE = 1,
+ BFD_MACH_O_i386_FLOAT_STATE = 2,
+ BFD_MACH_O_i386_ISA_PORT_MAP_STATE = 3,
+ BFD_MACH_O_i386_V86_ASSIST_STATE = 4,
+ BFD_MACH_O_i386_REGS_SEGS_STATE = 5,
+ BFD_MACH_O_i386_THREAD_SYSCALL_STATE = 6,
+ BFD_MACH_O_i386_THREAD_STATE_NONE = 7,
+ BFD_MACH_O_i386_SAVED_STATE = 8,
+ BFD_MACH_O_i386_THREAD_STATE = -1,
+ BFD_MACH_O_i386_THREAD_FPSTATE = -2,
+ BFD_MACH_O_i386_THREAD_EXCEPTSTATE = -3,
+ BFD_MACH_O_i386_THREAD_CTHREADSTATE = -4,
+}
bfd_mach_o_i386_thread_flavour;
#define BFD_MACH_O_LC_REQ_DYLD 0x80000000
typedef enum bfd_mach_o_load_command_type
- {
- BFD_MACH_O_LC_SEGMENT = 0x1, /* File segment to be mapped. */
- BFD_MACH_O_LC_SYMTAB = 0x2, /* Link-edit stab symbol table info (obsolete). */
- BFD_MACH_O_LC_SYMSEG = 0x3, /* Link-edit gdb symbol table info. */
- BFD_MACH_O_LC_THREAD = 0x4, /* Thread. */
- BFD_MACH_O_LC_UNIXTHREAD = 0x5, /* UNIX thread (includes a stack). */
- BFD_MACH_O_LC_LOADFVMLIB = 0x6, /* Load a fixed VM shared library. */
- BFD_MACH_O_LC_IDFVMLIB = 0x7, /* Fixed VM shared library id. */
- BFD_MACH_O_LC_IDENT = 0x8, /* Object identification information (obsolete). */
- BFD_MACH_O_LC_FVMFILE = 0x9, /* Fixed VM file inclusion. */
- BFD_MACH_O_LC_PREPAGE = 0xa, /* Prepage command (internal use). */
- BFD_MACH_O_LC_DYSYMTAB = 0xb, /* Dynamic link-edit symbol table info. */
- BFD_MACH_O_LC_LOAD_DYLIB = 0xc, /* Load a dynamically linked shared library. */
- BFD_MACH_O_LC_ID_DYLIB = 0xd, /* Dynamically linked shared lib identification. */
- BFD_MACH_O_LC_LOAD_DYLINKER = 0xe, /* Load a dynamic linker. */
- BFD_MACH_O_LC_ID_DYLINKER = 0xf, /* Dynamic linker identification. */
- BFD_MACH_O_LC_PREBOUND_DYLIB = 0x10,/* Modules prebound for a dynamically. */
- BFD_MACH_O_LC_ROUTINES = 0x11, /* Image routines. */
- BFD_MACH_O_LC_SUB_FRAMEWORK = 0x12, /* Sub framework. */
- BFD_MACH_O_LC_SUB_UMBRELLA = 0x13, /* Sub umbrella. */
- BFD_MACH_O_LC_SUB_CLIENT = 0x14, /* Sub client. */
- BFD_MACH_O_LC_SUB_LIBRARY = 0x15, /* Sub library. */
- BFD_MACH_O_LC_TWOLEVEL_HINTS = 0x16,/* Two-level namespace lookup hints. */
- BFD_MACH_O_LC_PREBIND_CKSUM = 0x17, /* Prebind checksum. */
- /* Load a dynamically linked shared library that is allowed to be
+{
+ BFD_MACH_O_LC_SEGMENT = 0x1, /* File segment to be mapped. */
+ BFD_MACH_O_LC_SYMTAB = 0x2, /* Link-edit stab symbol table info (obsolete). */
+ BFD_MACH_O_LC_SYMSEG = 0x3, /* Link-edit gdb symbol table info. */
+ BFD_MACH_O_LC_THREAD = 0x4, /* Thread. */
+ BFD_MACH_O_LC_UNIXTHREAD = 0x5, /* UNIX thread (includes a stack). */
+ BFD_MACH_O_LC_LOADFVMLIB = 0x6, /* Load a fixed VM shared library. */
+ BFD_MACH_O_LC_IDFVMLIB = 0x7, /* Fixed VM shared library id. */
+ BFD_MACH_O_LC_IDENT = 0x8, /* Object identification information (obsolete). */
+ BFD_MACH_O_LC_FVMFILE = 0x9, /* Fixed VM file inclusion. */
+ BFD_MACH_O_LC_PREPAGE = 0xa, /* Prepage command (internal use). */
+ BFD_MACH_O_LC_DYSYMTAB = 0xb, /* Dynamic link-edit symbol table info. */
+ BFD_MACH_O_LC_LOAD_DYLIB = 0xc, /* Load a dynamically linked shared library. */
+ BFD_MACH_O_LC_ID_DYLIB = 0xd, /* Dynamically linked shared lib identification. */
+ BFD_MACH_O_LC_LOAD_DYLINKER = 0xe, /* Load a dynamic linker. */
+ BFD_MACH_O_LC_ID_DYLINKER = 0xf, /* Dynamic linker identification. */
+ BFD_MACH_O_LC_PREBOUND_DYLIB = 0x10, /* Modules prebound for a dynamically. */
+ BFD_MACH_O_LC_ROUTINES = 0x11, /* Image routines. */
+ BFD_MACH_O_LC_SUB_FRAMEWORK = 0x12, /* Sub framework. */
+ BFD_MACH_O_LC_SUB_UMBRELLA = 0x13, /* Sub umbrella. */
+ BFD_MACH_O_LC_SUB_CLIENT = 0x14, /* Sub client. */
+ BFD_MACH_O_LC_SUB_LIBRARY = 0x15, /* Sub library. */
+ BFD_MACH_O_LC_TWOLEVEL_HINTS = 0x16, /* Two-level namespace lookup hints. */
+ BFD_MACH_O_LC_PREBIND_CKSUM = 0x17, /* Prebind checksum. */
+ /* Load a dynamically linked shared library that is allowed to be
missing (weak). */
- BFD_MACH_O_LC_LOAD_WEAK_DYLIB = 0x18
- }
+ BFD_MACH_O_LC_LOAD_WEAK_DYLIB = 0x18
+}
bfd_mach_o_load_command_type;
typedef enum bfd_mach_o_cpu_type
- {
- BFD_MACH_O_CPU_TYPE_VAX = 1,
- BFD_MACH_O_CPU_TYPE_MC680x0 = 6,
- BFD_MACH_O_CPU_TYPE_I386 = 7,
- BFD_MACH_O_CPU_TYPE_MIPS = 8,
- BFD_MACH_O_CPU_TYPE_MC98000 = 10,
- BFD_MACH_O_CPU_TYPE_HPPA = 11,
- BFD_MACH_O_CPU_TYPE_ARM = 12,
- BFD_MACH_O_CPU_TYPE_MC88000 = 13,
- BFD_MACH_O_CPU_TYPE_SPARC = 14,
- BFD_MACH_O_CPU_TYPE_I860 = 15,
- BFD_MACH_O_CPU_TYPE_ALPHA = 16,
- BFD_MACH_O_CPU_TYPE_POWERPC = 18
- }
+{
+ BFD_MACH_O_CPU_TYPE_VAX = 1,
+ BFD_MACH_O_CPU_TYPE_MC680x0 = 6,
+ BFD_MACH_O_CPU_TYPE_I386 = 7,
+ BFD_MACH_O_CPU_TYPE_MIPS = 8,
+ BFD_MACH_O_CPU_TYPE_MC98000 = 10,
+ BFD_MACH_O_CPU_TYPE_HPPA = 11,
+ BFD_MACH_O_CPU_TYPE_ARM = 12,
+ BFD_MACH_O_CPU_TYPE_MC88000 = 13,
+ BFD_MACH_O_CPU_TYPE_SPARC = 14,
+ BFD_MACH_O_CPU_TYPE_I860 = 15,
+ BFD_MACH_O_CPU_TYPE_ALPHA = 16,
+ BFD_MACH_O_CPU_TYPE_POWERPC = 18
+}
bfd_mach_o_cpu_type;
typedef enum bfd_mach_o_filetype
- {
- BFD_MACH_O_MH_OBJECT = 1,
- BFD_MACH_O_MH_EXECUTE = 2,
- BFD_MACH_O_MH_FVMLIB = 3,
- BFD_MACH_O_MH_CORE = 4,
- BFD_MACH_O_MH_PRELOAD = 5,
- BFD_MACH_O_MH_DYLIB = 6,
- BFD_MACH_O_MH_DYLINKER = 7,
- BFD_MACH_O_MH_BUNDLE = 8
- }
+{
+ BFD_MACH_O_MH_OBJECT = 1,
+ BFD_MACH_O_MH_EXECUTE = 2,
+ BFD_MACH_O_MH_FVMLIB = 3,
+ BFD_MACH_O_MH_CORE = 4,
+ BFD_MACH_O_MH_PRELOAD = 5,
+ BFD_MACH_O_MH_DYLIB = 6,
+ BFD_MACH_O_MH_DYLINKER = 7,
+ BFD_MACH_O_MH_BUNDLE = 8
+}
bfd_mach_o_filetype;
/* Constants for the type of a section. */
typedef enum bfd_mach_o_section_type
- {
- /* Regular section. */
- BFD_MACH_O_S_REGULAR = 0x0,
+{
+ /* Regular section. */
+ BFD_MACH_O_S_REGULAR = 0x0,
- /* Zero fill on demand section. */
- BFD_MACH_O_S_ZEROFILL = 0x1,
+ /* Zero fill on demand section. */
+ BFD_MACH_O_S_ZEROFILL = 0x1,
- /* Section with only literal C strings. */
- BFD_MACH_O_S_CSTRING_LITERALS = 0x2,
+ /* Section with only literal C strings. */
+ BFD_MACH_O_S_CSTRING_LITERALS = 0x2,
- /* Section with only 4 byte literals. */
- BFD_MACH_O_S_4BYTE_LITERALS = 0x3,
+ /* Section with only 4 byte literals. */
+ BFD_MACH_O_S_4BYTE_LITERALS = 0x3,
- /* Section with only 8 byte literals. */
- BFD_MACH_O_S_8BYTE_LITERALS = 0x4,
+ /* Section with only 8 byte literals. */
+ BFD_MACH_O_S_8BYTE_LITERALS = 0x4,
- /* Section with only pointers to literals. */
- BFD_MACH_O_S_LITERAL_POINTERS = 0x5,
+ /* Section with only pointers to literals. */
+ BFD_MACH_O_S_LITERAL_POINTERS = 0x5,
- /* For the two types of symbol pointers sections and the symbol stubs
- section they have indirect symbol table entries. For each of the
- entries in the section the indirect symbol table entries, in
- corresponding order in the indirect symbol table, start at the index
- stored in the reserved1 field of the section structure. Since the
- indirect symbol table entries correspond to the entries in the
- section the number of indirect symbol table entries is inferred from
- the size of the section divided by the size of the entries in the
- section. For symbol pointers sections the size of the entries in
- the section is 4 bytes and for symbol stubs sections the byte size
- of the stubs is stored in the reserved2 field of the section
- structure. */
+ /* For the two types of symbol pointers sections and the symbol stubs
+ section they have indirect symbol table entries. For each of the
+ entries in the section the indirect symbol table entries, in
+ corresponding order in the indirect symbol table, start at the index
+ stored in the reserved1 field of the section structure. Since the
+ indirect symbol table entries correspond to the entries in the
+ section the number of indirect symbol table entries is inferred from
+ the size of the section divided by the size of the entries in the
+ section. For symbol pointers sections the size of the entries in
+ the section is 4 bytes and for symbol stubs sections the byte size
+ of the stubs is stored in the reserved2 field of the section
+ structure. */
- /* Section with only non-lazy symbol pointers. */
- BFD_MACH_O_S_NON_LAZY_SYMBOL_POINTERS = 0x6,
+ /* Section with only non-lazy symbol pointers. */
+ BFD_MACH_O_S_NON_LAZY_SYMBOL_POINTERS = 0x6,
- /* Section with only lazy symbol pointers. */
- BFD_MACH_O_S_LAZY_SYMBOL_POINTERS = 0x7,
+ /* Section with only lazy symbol pointers. */
+ BFD_MACH_O_S_LAZY_SYMBOL_POINTERS = 0x7,
- /* Section with only symbol stubs, byte size of stub in the reserved2 field. */
- BFD_MACH_O_S_SYMBOL_STUBS = 0x8,
+ /* Section with only symbol stubs, byte size of stub in the reserved2 field. */
+ BFD_MACH_O_S_SYMBOL_STUBS = 0x8,
- /* Section with only function pointers for initialization. */
- BFD_MACH_O_S_MOD_INIT_FUNC_POINTERS = 0x9
- }
+ /* Section with only function pointers for initialization. */
+ BFD_MACH_O_S_MOD_INIT_FUNC_POINTERS = 0x9
+}
bfd_mach_o_section_type;
typedef unsigned long bfd_mach_o_cpu_subtype;
typedef struct mach_o_data_struct bfd_mach_o_data_struct;
-bfd_boolean bfd_mach_o_valid
- PARAMS ((bfd *));
-int bfd_mach_o_scan_read_symtab_symbol
- PARAMS ((bfd *, bfd_mach_o_symtab_command *, asymbol *, unsigned long));
-int bfd_mach_o_scan_read_symtab_strtab
- PARAMS ((bfd *, bfd_mach_o_symtab_command *));
-int bfd_mach_o_scan_read_symtab_symbols
- PARAMS ((bfd *, bfd_mach_o_symtab_command *));
-int bfd_mach_o_scan_read_dysymtab_symbol
- PARAMS ((bfd *, bfd_mach_o_dysymtab_command *, bfd_mach_o_symtab_command *,
- asymbol *, unsigned long));
-int bfd_mach_o_scan_start_address
- PARAMS ((bfd *));
-int bfd_mach_o_scan
- PARAMS ((bfd *, bfd_mach_o_header *, bfd_mach_o_data_struct *));
-bfd_boolean bfd_mach_o_mkobject
- PARAMS ((bfd *));
-const bfd_target * bfd_mach_o_object_p
- PARAMS ((bfd *));
-const bfd_target * bfd_mach_o_core_p
- PARAMS ((bfd *));
-const bfd_target * bfd_mach_o_archive_p
- PARAMS ((bfd *));
-bfd * bfd_mach_o_openr_next_archived_file
- PARAMS ((bfd *, bfd *));
-int bfd_mach_o_lookup_section
- PARAMS ((bfd *, asection *, bfd_mach_o_load_command **,
- bfd_mach_o_section **));
-int bfd_mach_o_lookup_command
- PARAMS ((bfd *, bfd_mach_o_load_command_type, bfd_mach_o_load_command **));
-unsigned long bfd_mach_o_stack_addr
- PARAMS ((enum bfd_mach_o_cpu_type));
-int bfd_mach_o_core_fetch_environment
- PARAMS ((bfd *, unsigned char **, unsigned int *));
-char * bfd_mach_o_core_file_failing_command
- PARAMS ((bfd *));
-int bfd_mach_o_core_file_failing_signal
- PARAMS ((bfd *));
-bfd_boolean bfd_mach_o_core_file_matches_executable_p
- PARAMS ((bfd *, bfd *));
+bfd_boolean bfd_mach_o_valid (bfd *);
+int bfd_mach_o_scan_read_symtab_symbol (bfd *, bfd_mach_o_symtab_command *, asymbol *, unsigned long);
+int bfd_mach_o_scan_read_symtab_strtab (bfd *, bfd_mach_o_symtab_command *);
+int bfd_mach_o_scan_read_symtab_symbols (bfd *, bfd_mach_o_symtab_command *);
+int bfd_mach_o_scan_read_dysymtab_symbol (bfd *, bfd_mach_o_dysymtab_command *, bfd_mach_o_symtab_command *, asymbol *, unsigned long);
+int bfd_mach_o_scan_start_address (bfd *);
+int bfd_mach_o_scan (bfd *, bfd_mach_o_header *, bfd_mach_o_data_struct *);
+bfd_boolean bfd_mach_o_mkobject (bfd *);
+const bfd_target * bfd_mach_o_object_p (bfd *);
+const bfd_target * bfd_mach_o_core_p (bfd *);
+const bfd_target * bfd_mach_o_archive_p (bfd *);
+bfd * bfd_mach_o_openr_next_archived_file (bfd *, bfd *);
+int bfd_mach_o_lookup_section (bfd *, asection *, bfd_mach_o_load_command **, bfd_mach_o_section **);
+int bfd_mach_o_lookup_command (bfd *, bfd_mach_o_load_command_type, bfd_mach_o_load_command **);
+unsigned long bfd_mach_o_stack_addr (enum bfd_mach_o_cpu_type);
+int bfd_mach_o_core_fetch_environment (bfd *, unsigned char **, unsigned int *);
+char * bfd_mach_o_core_file_failing_command (bfd *);
+int bfd_mach_o_core_file_failing_signal (bfd *);
+bfd_boolean bfd_mach_o_core_file_matches_executable_p (bfd *, bfd *);
extern const bfd_target mach_o_be_vec;
extern const bfd_target mach_o_le_vec;
/* BFD back-end definitions used by all NetBSD targets.
- Copyright 1990, 1991, 1992, 1994, 1995, 1996, 1997, 1998, 2000, 2002
+ Copyright 1990, 1991, 1992, 1994, 1995, 1996, 1997, 1998, 2000, 2002, 2005
Free Software Foundation, Inc.
-This file is part of BFD, the Binary File Descriptor library.
+ This file is part of BFD, the Binary File Descriptor library.
-This program is free software; you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation; either version 2 of the License, or
-(at your option) any later version.
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-GNU General Public License for more details.
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
-You should have received a copy of the GNU General Public License
-along with this program; if not, write to the Free Software
-Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
-USA. */
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
+ USA. */
/* Check for our machine type (part of magic number). */
#ifndef MACHTYPE_OK
#define N_HEADER_IN_TEXT(x) 1
/* Determine if this is a shared library using the flags. */
-#define N_SHARED_LIB(x) (N_DYNAMIC(x))
+#define N_SHARED_LIB(x) (N_DYNAMIC (x))
/* We have 6 bits of flags and 10 bits of machine ID. */
#define N_MACHTYPE(exec) \
| (((flags) & 0x3f) << 24))
#define N_SET_MACHTYPE(exec, machtype) \
((exec).a_info = \
- ((exec).a_info & 0xfb00ffff) | ((((int) (machtype))&0x3ff) << 16))
+ ((exec).a_info & 0xfb00ffff) | ((((int) (machtype)) & 0x3ff) << 16))
#define N_SET_FLAGS(exec, flags) \
((exec).a_info = \
((exec).a_info & 0x03ffffff) | ((flags & 0x03f) << 26))
section. */
#define MY_entry_is_text_address 1
-#define MY_write_object_contents MY(write_object_contents)
-static bfd_boolean MY(write_object_contents) PARAMS ((bfd *abfd));
+#define MY_write_object_contents MY (write_object_contents)
+static bfd_boolean MY (write_object_contents) (bfd *);
+
#define MY_text_includes_header 1
#include "aout-target.h"
file header, symbols, and relocation. */
static bfd_boolean
-MY(write_object_contents) (abfd)
- bfd *abfd;
+MY (write_object_contents) (bfd *abfd)
{
struct external_exec exec_bytes;
struct internal_exec *execp = exec_hdr (abfd);
bfd_size_type text_size;
file_ptr text_end;
- NAME(aout,adjust_sizes_and_vmas) (abfd, &text_size, &text_end);
+ NAME (aout, adjust_sizes_and_vmas) (abfd, & text_size, & text_end);
}
obj_reloc_entry_size (abfd) = RELOC_STD_SIZE;
/* Magic number, maestro, please! */
- switch (bfd_get_arch(abfd)) {
- case DEFAULT_ARCH:
- N_SET_MACHTYPE(*execp, DEFAULT_MID);
- break;
- default:
- N_SET_MACHTYPE(*execp, M_UNKNOWN);
- break;
- }
+ switch (bfd_get_arch(abfd))
+ {
+ case DEFAULT_ARCH:
+ N_SET_MACHTYPE(*execp, DEFAULT_MID);
+ break;
+ default:
+ N_SET_MACHTYPE(*execp, M_UNKNOWN);
+ break;
+ }
/* The NetBSD magic number is always big-endian */
#ifndef TARGET_IS_BIG_ENDIAN_P
| (execp->a_info & 0xff0000) >> 8 | (execp->a_info & 0xff000000) >> 24;
#endif
- WRITE_HEADERS(abfd, execp);
+ WRITE_HEADERS (abfd, execp);
return TRUE;
}
/* Header file for ns32k routines.
- Copyright 1996, 2001, 2002 Free Software Foundation, Inc.
+ Copyright 1996, 2001, 2002, 2005 Free Software Foundation, Inc.
Written by Cygnus Support.
This file is part of BFD, the Binary File Descriptor library.
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
-extern bfd_reloc_status_type _bfd_ns32k_relocate_contents
- PARAMS ((reloc_howto_type *, bfd *, bfd_vma, bfd_byte *));
-
-extern bfd_reloc_status_type _bfd_do_ns32k_reloc_contents
- PARAMS ((reloc_howto_type *, bfd *, bfd_vma, bfd_byte *,
- bfd_vma (*) (bfd_byte *, int),
- void (*) (bfd_vma, bfd_byte *, int)));
-
-extern bfd_reloc_status_type _bfd_ns32k_final_link_relocate
- PARAMS ((reloc_howto_type *, bfd *, asection *, bfd_byte *, bfd_vma,
- bfd_vma, bfd_vma));
-
-extern bfd_vma _bfd_ns32k_get_displacement PARAMS ((bfd_byte *, int));
-extern bfd_vma _bfd_ns32k_get_immediate PARAMS ((bfd_byte *, int));
-extern void _bfd_ns32k_put_displacement PARAMS ((bfd_vma, bfd_byte *, int));
-extern void _bfd_ns32k_put_immediate PARAMS ((bfd_vma, bfd_byte *, int));
-
-extern bfd_reloc_status_type _bfd_ns32k_reloc_disp
- PARAMS ((bfd *, arelent *, asymbol *, PTR, asection *, bfd *, char **));
-extern bfd_reloc_status_type _bfd_ns32k_reloc_imm
- PARAMS ((bfd *, arelent *, asymbol *, PTR, asection *, bfd *, char **));
+extern bfd_reloc_status_type _bfd_ns32k_relocate_contents (reloc_howto_type *, bfd *, bfd_vma, bfd_byte *);
+extern bfd_reloc_status_type _bfd_do_ns32k_reloc_contents (reloc_howto_type *, bfd *, bfd_vma, bfd_byte *, bfd_vma (*) (bfd_byte *, int), void (*) (bfd_vma, bfd_byte *, int));
+extern bfd_reloc_status_type _bfd_ns32k_final_link_relocate (reloc_howto_type *, bfd *, asection *, bfd_byte *, bfd_vma, bfd_vma, bfd_vma);
+extern bfd_vma _bfd_ns32k_get_displacement (bfd_byte *, int);
+extern bfd_vma _bfd_ns32k_get_immediate (bfd_byte *, int);
+extern void _bfd_ns32k_put_displacement (bfd_vma, bfd_byte *, int);
+extern void _bfd_ns32k_put_immediate (bfd_vma, bfd_byte *, int);
+extern bfd_reloc_status_type _bfd_ns32k_reloc_disp (bfd *, arelent *, asymbol *, void *, asection *, bfd *, char **);
+extern bfd_reloc_status_type _bfd_ns32k_reloc_imm (bfd *, arelent *, asymbol *, void *, asection *, bfd *, char **);
/* BFD back-end for NetBSD/ns32k a.out-ish binaries.
- Copyright 1990, 1991, 1992, 1994, 1995, 1998, 2000, 2001, 2002
+ Copyright 1990, 1991, 1992, 1994, 1995, 1998, 2000, 2001, 2002, 2005
Free Software Foundation, Inc.
-This file is part of BFD, the Binary File Descriptor library.
+ This file is part of BFD, the Binary File Descriptor library.
-This program is free software; you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation; either version 2 of the License, or
-(at your option) any later version.
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-GNU General Public License for more details.
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
-You should have received a copy of the GNU General Public License
-along with this program; if not, write to the Free Software
-Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
-#define BYTES_IN_WORD 4
+#define BYTES_IN_WORD 4
#undef TARGET_IS_BIG_ENDIAN_P
#define TARGET_PAGE_SIZE 4096
-#define SEGMENT_SIZE 4096
+#define SEGMENT_SIZE 4096
-#define DEFAULT_ARCH bfd_arch_ns32k
-#define DEFAULT_MID M_532_NETBSD
+#define DEFAULT_ARCH bfd_arch_ns32k
+#define DEFAULT_MID M_532_NETBSD
/* Do not "beautify" the CONCAT* macro args. Traditional C will not
remove whitespace added here, and thus will fail to concatenate
#define MY_text_includes_header 1
/* We can`t use the MYNS macro here for cpp reasons too subtle
- * for me -- IWD
- */
+ for me -- IWD. */
#define MY_bfd_reloc_type_lookup ns32kaout_bfd_reloc_type_lookup
-#include "bfd.h" /* To ensure following declaration is OK */
+#include "bfd.h" /* To ensure following declaration is OK. */
-const struct reloc_howto_struct *
-MY_bfd_reloc_type_lookup
- PARAMS((bfd *abfd AND
- bfd_reloc_code_real_type code));
+const struct reloc_howto_struct * MY_bfd_reloc_type_lookup (bfd *, bfd_reloc_code_real_type);
#include "netbsd.h"
#include "oasys.h"
#include "liboasys.h"
-static bfd_boolean oasys_slurp_section_data
- PARAMS ((bfd * const));
-static bfd_boolean oasys_read_record
- PARAMS ((bfd *, oasys_record_union_type *));
-static bfd_boolean oasys_write_sections
- PARAMS ((bfd *));
-static bfd_boolean oasys_write_record
- PARAMS ((bfd *, oasys_record_enum_type, oasys_record_union_type *, size_t));
-static bfd_boolean oasys_write_syms
- PARAMS ((bfd *));
-static bfd_boolean oasys_write_header
- PARAMS ((bfd *));
-static bfd_boolean oasys_write_end
- PARAMS ((bfd *));
-static bfd_boolean oasys_write_data
- PARAMS ((bfd *));
-static size_t oasys_string_length
- PARAMS ((oasys_record_union_type *));
-static bfd_boolean oasys_slurp_symbol_table
- PARAMS ((bfd *const));
-static long int oasys_get_symtab_upper_bound
- PARAMS ((bfd *const));
-static const bfd_target *oasys_archive_p
- PARAMS ((bfd *));
-static bfd_boolean oasys_mkobject
- PARAMS ((bfd *));
-static const bfd_target *oasys_object_p
- PARAMS ((bfd *));
-static void oasys_get_symbol_info
- PARAMS ((bfd *, asymbol *, symbol_info *));
-static void oasys_print_symbol
- PARAMS ((bfd *, void *, asymbol *, bfd_print_symbol_type));
-static bfd_boolean oasys_new_section_hook
- PARAMS ((bfd *, asection *));
-static long int oasys_get_reloc_upper_bound
- PARAMS ((bfd *, sec_ptr));
-static bfd_boolean oasys_get_section_contents
- PARAMS ((bfd *, sec_ptr, void *, file_ptr, bfd_size_type));
-static int comp
- PARAMS ((const void *, const void *));
-static bfd_boolean oasys_write_object_contents
- PARAMS ((bfd *));
-static bfd_boolean oasys_set_section_contents
- PARAMS ((bfd *, sec_ptr, const void *, file_ptr, bfd_size_type));
-static asymbol *oasys_make_empty_symbol
- PARAMS ((bfd *));
-static bfd *oasys_openr_next_archived_file
- PARAMS ((bfd *, bfd *));
-static bfd_boolean oasys_find_nearest_line
- PARAMS ((bfd *, asection *, asymbol **, bfd_vma,
- const char **, const char **, unsigned int *));
-static int oasys_generic_stat_arch_elt
- PARAMS ((bfd *, struct stat *));
-static int oasys_sizeof_headers
- PARAMS ((bfd *, bfd_boolean));
-
-long oasys_canonicalize_symtab
- PARAMS ((bfd *, asymbol **));
-long oasys_canonicalize_reloc
- PARAMS ((bfd *, sec_ptr, arelent **, asymbol **));
-
/* Read in all the section data and relocation stuff too. */
static bfd_boolean
-oasys_read_record (abfd, record)
- bfd *abfd;
- oasys_record_union_type *record;
+oasys_read_record (bfd *abfd, oasys_record_union_type *record)
{
bfd_size_type amt = sizeof (record->header);
- if (bfd_bread ((PTR) record, amt, abfd) != amt)
+
+ if (bfd_bread ((void *) record, amt, abfd) != amt)
return FALSE;
amt = record->header.length - sizeof (record->header);
if ((long) amt <= 0)
return TRUE;
- if (bfd_bread ((PTR) ((char *) record + sizeof (record->header)), amt, abfd)
+ if (bfd_bread ((void *) ((char *) record + sizeof (record->header)), amt, abfd)
!= amt)
return FALSE;
return TRUE;
}
static size_t
-oasys_string_length (record)
- oasys_record_union_type *record;
+oasys_string_length (oasys_record_union_type *record)
{
return record->header.length
- ((char *) record->symbol.name - (char *) record);
}
-/*****************************************************************************/
-
-/*
-
-Slurp the symbol table by reading in all the records at the start file
-till we get to the first section record.
+/* Slurp the symbol table by reading in all the records at the start file
+ till we get to the first section record.
-We'll sort the symbolss into two lists, defined and undefined. The
-undefined symbols will be placed into the table according to their
-refno.
+ We'll sort the symbolss into two lists, defined and undefined. The
+ undefined symbols will be placed into the table according to their
+ refno.
-We do this by placing all undefined symbols at the front of the table
-moving in, and the defined symbols at the end of the table moving back.
-
-*/
+ We do this by placing all undefined symbols at the front of the table
+ moving in, and the defined symbols at the end of the table moving back. */
static bfd_boolean
-oasys_slurp_symbol_table (abfd)
- bfd *const abfd;
+oasys_slurp_symbol_table (bfd *const abfd)
{
oasys_record_union_type record;
oasys_data_type *data = OASYS_DATA (abfd);
char *string_ptr;
bfd_size_type amt;
- if (data->symbols != (asymbol *) NULL)
- {
- return TRUE;
- }
- /* Buy enough memory for all the symbols and all the names */
+ if (data->symbols != NULL)
+ return TRUE;
+
+ /* Buy enough memory for all the symbols and all the names. */
amt = abfd->symcount;
amt *= sizeof (asymbol);
- data->symbols = (asymbol *) bfd_alloc (abfd, amt);
+ data->symbols = bfd_alloc (abfd, amt);
amt = data->symbol_string_length;
#ifdef UNDERSCORE_HACK
- /* buy 1 more char for each symbol to keep the underscore in*/
+ /* Buy 1 more char for each symbol to keep the underscore in. */
amt += abfd->symcount;
#endif
data->strings = bfd_alloc (abfd, amt);
return FALSE;
while (loop)
{
-
if (! oasys_read_record (abfd, &record))
return FALSE;
+
switch (record.header.type)
{
case oasys_record_is_header_enum:
int flag = record.header.type == (int) oasys_record_is_local_enum ?
(BSF_LOCAL) : (BSF_GLOBAL | BSF_EXPORT);
-
size_t length = oasys_string_length (&record);
switch (record.symbol.relb & RELOCATION_TYPE_BITS)
{
}
}
else
- {
-
- dest->flags = flag;
- }
+ dest->flags = flag;
break;
case RELOCATION_TYPE_UND:
dest = data->symbols + H_GET_16 (abfd, record.symbol.refno);
dest = dest_defined--;
dest->name = string_ptr;
dest->the_bfd = abfd;
-
dest->section = bfd_com_section_ptr;
-
break;
default:
dest = dest_defined--;
- BFD_ASSERT (0);
+ BFD_ASSERT (FALSE);
break;
}
dest->name = string_ptr;
dest->the_bfd = abfd;
- dest->udata.p = (PTR) NULL;
+ dest->udata.p = NULL;
dest->value = H_GET_32 (abfd, record.symbol.value);
#ifdef UNDERSCORE_HACK
#endif
memcpy (string_ptr, record.symbol.name, length);
-
string_ptr[length] = 0;
string_ptr += length + 1;
}
}
static long
-oasys_get_symtab_upper_bound (abfd)
- bfd *const abfd;
+oasys_get_symtab_upper_bound (bfd *const abfd)
{
if (! oasys_slurp_symbol_table (abfd))
return -1;
extern const bfd_target oasys_vec;
-long
-oasys_canonicalize_symtab (abfd, location)
- bfd *abfd;
- asymbol **location;
+static long
+oasys_canonicalize_symtab (bfd *abfd, asymbol **location)
{
asymbol *symbase;
unsigned int counter;
+
if (! oasys_slurp_symbol_table (abfd))
- {
- return -1;
- }
+ return -1;
+
symbase = OASYS_DATA (abfd)->symbols;
for (counter = 0; counter < abfd->symcount; counter++)
- {
- *(location++) = symbase++;
- }
+ *(location++) = symbase++;
+
*location = 0;
return abfd->symcount;
}
-/***********************************************************************
-* archive stuff
-*/
+/* Archive stuff. */
static const bfd_target *
-oasys_archive_p (abfd)
- bfd *abfd;
+oasys_archive_p (bfd *abfd)
{
oasys_archive_header_type header;
oasys_extarchive_header_type header_ext;
amt = sizeof (header_ext);
if (bfd_seek (abfd, (file_ptr) 0, 0) != 0
- || bfd_bread ((PTR) &header_ext, amt, abfd) != amt)
+ || bfd_bread ((void *) &header_ext, amt, abfd) != amt)
{
if (bfd_get_error () != bfd_error_system_call)
bfd_set_error (bfd_error_wrong_format);
header.xref_count = H_GET_32 (abfd, header_ext.xref_count);
header.xref_lst_offset = H_GET_32 (abfd, header_ext.xref_lst_offset);
- /*
- There isn't a magic number in an Oasys archive, so the best we
- can do to verify reasonableness is to make sure that the values in
- the header are too weird
- */
-
- if (header.version > 10000 ||
- header.mod_count > 10000 ||
- header.sym_count > 100000 ||
- header.xref_count > 100000)
- return (const bfd_target *) NULL;
-
- /*
- That all worked, let's buy the space for the header and read in
- the headers.
- */
+ /* There isn't a magic number in an Oasys archive, so the best we
+ can do to verify reasonableness is to make sure that the values in
+ the header are too weird. */
+
+ if (header.version > 10000
+ || header.mod_count > 10000
+ || header.sym_count > 100000
+ || header.xref_count > 100000)
+ return NULL;
+
+ /* That all worked, let's buy the space for the header and read in
+ the headers. */
{
oasys_ar_data_type *ar;
oasys_module_info_type *module;
oasys_module_table_type record;
amt = sizeof (oasys_ar_data_type);
- ar = (oasys_ar_data_type *) bfd_alloc (abfd, amt);
+ ar = bfd_alloc (abfd, amt);
amt = header.mod_count;
amt *= sizeof (oasys_module_info_type);
- module = (oasys_module_info_type *) bfd_alloc (abfd, amt);
+ module = bfd_alloc (abfd, amt);
if (!ar || !module)
return NULL;
if (bfd_seek (abfd, filepos, SEEK_SET) != 0)
return NULL;
- /* There are two ways of specifying the archive header */
-
- if (0)
- {
- oasys_extmodule_table_type_a_type record_ext;
-
- amt = sizeof (record_ext);
- if (bfd_bread ((PTR) &record_ext, amt, abfd) != amt)
- return NULL;
-
- record.mod_size = H_GET_32 (abfd, record_ext.mod_size);
- record.file_offset = H_GET_32 (abfd, record_ext.file_offset);
-
- record.dep_count = H_GET_32 (abfd, record_ext.dep_count);
- record.depee_count = H_GET_32 (abfd, record_ext.depee_count);
- record.sect_count = H_GET_32 (abfd, record_ext.sect_count);
-
- module[i].name = bfd_alloc (abfd, (bfd_size_type) 33);
- if (!module[i].name)
- return NULL;
-
- memcpy (module[i].name, record_ext.mod_name, 33);
- filepos +=
- sizeof (record_ext) +
- record.dep_count * 4 +
- record.depee_count * 4 +
- record.sect_count * 8 + 187;
- }
- else
+ /* There are two ways of specifying the archive header. */
{
oasys_extmodule_table_type_b_type record_ext;
amt = sizeof (record_ext);
- if (bfd_bread ((PTR) &record_ext, amt, abfd) != amt)
+ if (bfd_bread ((void *) &record_ext, amt, abfd) != amt)
return NULL;
record.mod_size = H_GET_32 (abfd, record_ext.mod_size);
module[i].name = bfd_alloc (abfd, amt + 1);
if (!module[i].name)
return NULL;
- if (bfd_bread ((PTR) module[i].name, amt, abfd) != amt)
+ if (bfd_bread ((void *) module[i].name, amt, abfd) != amt)
return NULL;
module[i].name[record.module_name_size] = 0;
filepos += (sizeof (record_ext)
}
static bfd_boolean
-oasys_mkobject (abfd)
- bfd *abfd;
+oasys_mkobject (bfd *abfd)
{
bfd_size_type amt = sizeof (oasys_data_type);
- abfd->tdata.oasys_obj_data = (oasys_data_type *) bfd_alloc (abfd, amt);
- return abfd->tdata.oasys_obj_data != NULL;
-}
-
-#define MAX_SECS 16
-static const bfd_target *
-oasys_object_p (abfd)
- bfd *abfd;
-{
- oasys_data_type *oasys;
- oasys_data_type *save = OASYS_DATA (abfd);
- bfd_boolean loop = TRUE;
- bfd_boolean had_usefull = FALSE;
-
- abfd->tdata.oasys_obj_data = 0;
- oasys_mkobject (abfd);
- oasys = OASYS_DATA (abfd);
- memset ((PTR) oasys->sections, 0xff, sizeof (oasys->sections));
-
- /* Point to the start of the file */
- if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) != 0)
- goto fail;
- oasys->symbol_string_length = 0;
- /* Inspect the records, but only keep the section info -
- remember the size of the symbols
- */
- oasys->first_data_record = 0;
- while (loop)
- {
- oasys_record_union_type record;
- if (! oasys_read_record (abfd, &record))
- goto fail;
- if ((size_t) record.header.length < (size_t) sizeof (record.header))
- goto fail;
-
-
- switch ((oasys_record_enum_type) (record.header.type))
- {
- case oasys_record_is_header_enum:
- had_usefull = TRUE;
- break;
- case oasys_record_is_symbol_enum:
- case oasys_record_is_local_enum:
- /* Count symbols and remember their size for a future malloc */
- abfd->symcount++;
- oasys->symbol_string_length += 1 + oasys_string_length (&record);
- had_usefull = TRUE;
- break;
- case oasys_record_is_section_enum:
- {
- asection *s;
- char *buffer;
- unsigned int section_number;
- if (record.section.header.length != sizeof (record.section))
- {
- goto fail;
- }
- buffer = bfd_alloc (abfd, (bfd_size_type) 3);
- if (!buffer)
- goto fail;
- section_number = record.section.relb & RELOCATION_SECT_BITS;
- sprintf (buffer, "%u", section_number);
- s = bfd_make_section (abfd, buffer);
- oasys->sections[section_number] = s;
- switch (record.section.relb & RELOCATION_TYPE_BITS)
- {
- case RELOCATION_TYPE_ABS:
- case RELOCATION_TYPE_REL:
- break;
- case RELOCATION_TYPE_UND:
- case RELOCATION_TYPE_COM:
- BFD_FAIL ();
- }
-
- s->size = H_GET_32 (abfd, record.section.value);
- s->vma = H_GET_32 (abfd, record.section.vma);
- s->flags = 0;
- had_usefull = TRUE;
- }
- break;
- case oasys_record_is_data_enum:
- oasys->first_data_record = bfd_tell (abfd) - record.header.length;
- case oasys_record_is_debug_enum:
- case oasys_record_is_module_enum:
- case oasys_record_is_named_section_enum:
- case oasys_record_is_end_enum:
- if (! had_usefull)
- goto fail;
- loop = FALSE;
- break;
- default:
- goto fail;
- }
- }
- oasys->symbols = (asymbol *) NULL;
- /*
- Oasys support several architectures, but I can't see a simple way
- to discover which one is in a particular file - we'll guess
- */
- bfd_default_set_arch_mach (abfd, bfd_arch_m68k, 0);
- if (abfd->symcount != 0)
- {
- abfd->flags |= HAS_SYMS;
- }
-
- /*
- We don't know if a section has data until we've read it..
- */
-
- oasys_slurp_section_data (abfd);
+ abfd->tdata.oasys_obj_data = bfd_alloc (abfd, amt);
- return abfd->xvec;
-
-fail:
- (void) bfd_release (abfd, oasys);
- abfd->tdata.oasys_obj_data = save;
- return (const bfd_target *) NULL;
-}
-
-
-static void
-oasys_get_symbol_info (ignore_abfd, symbol, ret)
- bfd *ignore_abfd ATTRIBUTE_UNUSED;
- asymbol *symbol;
- symbol_info *ret;
-{
- bfd_symbol_info (symbol, ret);
- if (!symbol->section)
- ret->type = (symbol->flags & BSF_LOCAL) ? 'a' : 'A';
+ return abfd->tdata.oasys_obj_data != NULL;
}
-static void
-oasys_print_symbol (abfd, afile, symbol, how)
- bfd *abfd;
- PTR afile;
- asymbol *symbol;
- bfd_print_symbol_type how;
-{
- FILE *file = (FILE *) afile;
+/* The howto table is build using the top two bits of a reloc byte to
+ index into it. The bits are PCREL,WORD/LONG. */
- switch (how)
- {
- case bfd_print_symbol_name:
- case bfd_print_symbol_more:
- fprintf (file, "%s", symbol->name);
- break;
- case bfd_print_symbol_all:
- {
- const char *section_name = symbol->section == (asection *) NULL ?
- (const char *) "*abs" : symbol->section->name;
-
- bfd_print_symbol_vandf (abfd, (PTR) file, symbol);
-
- fprintf (file, " %-5s %s",
- section_name,
- symbol->name);
- }
- break;
- }
-}
-/*
- The howto table is build using the top two bits of a reloc byte to
- index into it. The bits are PCREL,WORD/LONG
-*/
static reloc_howto_type howto_table[] =
{
- HOWTO (0, 0, 1, 16, FALSE, 0, complain_overflow_bitfield, 0, "abs16", TRUE, 0x0000ffff, 0x0000ffff, FALSE),
- HOWTO (0, 0, 2, 32, FALSE, 0, complain_overflow_bitfield, 0, "abs32", TRUE, 0xffffffff, 0xffffffff, FALSE),
- HOWTO (0, 0, 1, 16, TRUE, 0, complain_overflow_signed, 0, "pcrel16", TRUE, 0x0000ffff, 0x0000ffff, FALSE),
- HOWTO (0, 0, 2, 32, TRUE, 0, complain_overflow_signed, 0, "pcrel32", TRUE, 0xffffffff, 0xffffffff, FALSE)
+ HOWTO (0, 0, 1, 16, FALSE, 0, complain_overflow_bitfield, 0, "abs16", TRUE, 0x0000ffff, 0x0000ffff, FALSE),
+ HOWTO (0, 0, 2, 32, FALSE, 0, complain_overflow_bitfield, 0, "abs32", TRUE, 0xffffffff, 0xffffffff, FALSE),
+ HOWTO (0, 0, 1, 16, TRUE, 0, complain_overflow_signed, 0, "pcrel16", TRUE, 0x0000ffff, 0x0000ffff, FALSE),
+ HOWTO (0, 0, 2, 32, TRUE, 0, complain_overflow_signed, 0, "pcrel32", TRUE, 0xffffffff, 0xffffffff, FALSE)
};
-/* Read in all the section data and relocation stuff too */
+/* Read in all the section data and relocation stuff too. */
+
static bfd_boolean
-oasys_slurp_section_data (abfd)
- bfd *const abfd;
+oasys_slurp_section_data (bfd *const abfd)
{
oasys_record_union_type record;
oasys_data_type *data = OASYS_DATA (abfd);
asection *s;
bfd_size_type amt;
- /* See if the data has been slurped already .. */
- for (s = abfd->sections; s != (asection *) NULL; s = s->next)
+ /* See if the data has been slurped already. */
+ for (s = abfd->sections; s != NULL; s = s->next)
{
per = oasys_per_section (s);
if (per->initialized)
if (bfd_seek (abfd, data->first_data_record, SEEK_SET) != 0)
return FALSE;
+
while (loop)
{
if (! oasys_read_record (abfd, &record))
return FALSE;
+
switch (record.header.type)
{
case oasys_record_is_header_enum:
break;
case oasys_record_is_data_enum:
{
-
bfd_byte *src = record.data.data;
bfd_byte *end_src = ((bfd_byte *) & record) + record.header.length;
bfd_byte *dst_ptr;
if (! per->initialized)
{
- per->data = (bfd_byte *) bfd_zalloc (abfd, section->size);
+ per->data = bfd_zalloc (abfd, section->size);
if (!per->data)
return FALSE;
per->reloc_tail_ptr
dst_offset = H_GET_32 (abfd, record.data.addr);
if (! per->had_vma)
{
- /* Take the first vma we see as the base */
+ /* Take the first vma we see as the base. */
section->vma = dst_offset;
per->had_vma = TRUE;
}
dst_offset;
if (src < end_src)
- {
- section->flags |= SEC_LOAD | SEC_HAS_CONTENTS;
- }
+ section->flags |= SEC_LOAD | SEC_HAS_CONTENTS;
+
while (src < end_src)
{
unsigned char mod_byte = *src++;
if (relbit & mod_byte)
{
unsigned char reloc = *src;
- /* This item needs to be relocated */
+ /* This item needs to be relocated. */
switch (reloc & RELOCATION_TYPE_BITS)
{
case RELOCATION_TYPE_ABS:
-
break;
case RELOCATION_TYPE_REL:
{
- /* Relocate the item relative to the section */
+ /* Relocate the item relative to the section. */
oasys_reloc_type *r;
amt = sizeof (oasys_reloc_type);
- r = (oasys_reloc_type *) bfd_alloc (abfd,
- amt);
+ r = bfd_alloc (abfd, amt);
if (!r)
return FALSE;
*(per->reloc_tail_ptr) = r;
per->reloc_tail_ptr = &r->next;
- r->next = (oasys_reloc_type *) NULL;
- /* Reference to undefined symbol */
+ r->next = NULL;
+ /* Reference to undefined symbol. */
src++;
- /* There is no symbol */
+ /* There is no symbol. */
r->symbol = 0;
- /* Work out the howto */
+ /* Work out the howto. */
abort ();
r->relent.address = dst_ptr - dst_base_ptr;
r->relent.howto = &howto_table[reloc >> 6];
- r->relent.sym_ptr_ptr = (asymbol **) NULL;
+ r->relent.sym_ptr_ptr = NULL;
section->reloc_count++;
/* Fake up the data to look like
}
break;
-
case RELOCATION_TYPE_UND:
{
oasys_reloc_type *r;
amt = sizeof (oasys_reloc_type);
- r = (oasys_reloc_type *) bfd_alloc (abfd,
- amt);
+ r = bfd_alloc (abfd, amt);
if (!r)
return FALSE;
*(per->reloc_tail_ptr) = r;
per->reloc_tail_ptr = &r->next;
- r->next = (oasys_reloc_type *) NULL;
- /* Reference to undefined symbol */
+ r->next = NULL;
+ /* Reference to undefined symbol. */
src++;
- /* Get symbol number */
+ /* Get symbol number. */
r->symbol = (src[0] << 8) | src[1];
- /* Work out the howto */
+ /* Work out the howto. */
abort ();
r->relent.addend = 0;
r->relent.address = dst_ptr - dst_base_ptr;
r->relent.howto = &howto_table[reloc >> 6];
- r->relent.sym_ptr_ptr = (asymbol **) NULL;
+ r->relent.sym_ptr_ptr = NULL;
section->reloc_count++;
src += 2;
}
+#define MAX_SECS 16
+
+static const bfd_target *
+oasys_object_p (bfd *abfd)
+{
+ oasys_data_type *oasys;
+ oasys_data_type *save = OASYS_DATA (abfd);
+ bfd_boolean loop = TRUE;
+ bfd_boolean had_usefull = FALSE;
+
+ abfd->tdata.oasys_obj_data = 0;
+ oasys_mkobject (abfd);
+ oasys = OASYS_DATA (abfd);
+ memset ((void *) oasys->sections, 0xff, sizeof (oasys->sections));
+
+ /* Point to the start of the file. */
+ if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) != 0)
+ goto fail;
+ oasys->symbol_string_length = 0;
+
+ /* Inspect the records, but only keep the section info -
+ remember the size of the symbols. */
+ oasys->first_data_record = 0;
+ while (loop)
+ {
+ oasys_record_union_type record;
+ if (! oasys_read_record (abfd, &record))
+ goto fail;
+ if ((size_t) record.header.length < (size_t) sizeof (record.header))
+ goto fail;
+
+ switch ((oasys_record_enum_type) (record.header.type))
+ {
+ case oasys_record_is_header_enum:
+ had_usefull = TRUE;
+ break;
+ case oasys_record_is_symbol_enum:
+ case oasys_record_is_local_enum:
+ /* Count symbols and remember their size for a future malloc. */
+ abfd->symcount++;
+ oasys->symbol_string_length += 1 + oasys_string_length (&record);
+ had_usefull = TRUE;
+ break;
+ case oasys_record_is_section_enum:
+ {
+ asection *s;
+ char *buffer;
+ unsigned int section_number;
+
+ if (record.section.header.length != sizeof (record.section))
+ goto fail;
+
+ buffer = bfd_alloc (abfd, (bfd_size_type) 3);
+ if (!buffer)
+ goto fail;
+ section_number = record.section.relb & RELOCATION_SECT_BITS;
+ sprintf (buffer, "%u", section_number);
+ s = bfd_make_section (abfd, buffer);
+ oasys->sections[section_number] = s;
+ switch (record.section.relb & RELOCATION_TYPE_BITS)
+ {
+ case RELOCATION_TYPE_ABS:
+ case RELOCATION_TYPE_REL:
+ break;
+ case RELOCATION_TYPE_UND:
+ case RELOCATION_TYPE_COM:
+ BFD_FAIL ();
+ }
+
+ s->size = H_GET_32 (abfd, record.section.value);
+ s->vma = H_GET_32 (abfd, record.section.vma);
+ s->flags = 0;
+ had_usefull = TRUE;
+ }
+ break;
+ case oasys_record_is_data_enum:
+ oasys->first_data_record = bfd_tell (abfd) - record.header.length;
+ case oasys_record_is_debug_enum:
+ case oasys_record_is_module_enum:
+ case oasys_record_is_named_section_enum:
+ case oasys_record_is_end_enum:
+ if (! had_usefull)
+ goto fail;
+ loop = FALSE;
+ break;
+ default:
+ goto fail;
+ }
+ }
+ oasys->symbols = NULL;
+
+ /* Oasys support several architectures, but I can't see a simple way
+ to discover which one is in a particular file - we'll guess. */
+ bfd_default_set_arch_mach (abfd, bfd_arch_m68k, 0);
+ if (abfd->symcount != 0)
+ abfd->flags |= HAS_SYMS;
+
+ /* We don't know if a section has data until we've read it. */
+ oasys_slurp_section_data (abfd);
+
+ return abfd->xvec;
+
+fail:
+ (void) bfd_release (abfd, oasys);
+ abfd->tdata.oasys_obj_data = save;
+ return NULL;
+}
+
+
+static void
+oasys_get_symbol_info (bfd *ignore_abfd ATTRIBUTE_UNUSED,
+ asymbol *symbol,
+ symbol_info *ret)
+{
+ bfd_symbol_info (symbol, ret);
+
+ if (!symbol->section)
+ ret->type = (symbol->flags & BSF_LOCAL) ? 'a' : 'A';
+}
+
+static void
+oasys_print_symbol (bfd *abfd, void * afile, asymbol *symbol, bfd_print_symbol_type how)
+{
+ FILE *file = (FILE *) afile;
+
+ switch (how)
+ {
+ case bfd_print_symbol_name:
+ case bfd_print_symbol_more:
+ fprintf (file, "%s", symbol->name);
+ break;
+ case bfd_print_symbol_all:
+ {
+ const char *section_name = symbol->section == NULL ?
+ (const char *) "*abs" : symbol->section->name;
+
+ bfd_print_symbol_vandf (abfd, (void *) file, symbol);
+
+ fprintf (file, " %-5s %s",
+ section_name,
+ symbol->name);
+ }
+ break;
+ }
+}
+
static bfd_boolean
-oasys_new_section_hook (abfd, newsect)
- bfd *abfd;
- asection *newsect;
+oasys_new_section_hook (bfd *abfd, asection *newsect)
{
- newsect->used_by_bfd = (PTR)
- bfd_alloc (abfd, (bfd_size_type) sizeof (oasys_per_section_type));
+ newsect->used_by_bfd = bfd_alloc (abfd, (bfd_size_type) sizeof (oasys_per_section_type));
if (!newsect->used_by_bfd)
return FALSE;
- oasys_per_section (newsect)->data = (bfd_byte *) NULL;
+ oasys_per_section (newsect)->data = NULL;
oasys_per_section (newsect)->section = newsect;
oasys_per_section (newsect)->offset = 0;
oasys_per_section (newsect)->initialized = FALSE;
newsect->alignment_power = 1;
- /* Turn the section string into an index */
+ /* Turn the section string into an index. */
sscanf (newsect->name, "%u", &newsect->target_index);
return TRUE;
static long
-oasys_get_reloc_upper_bound (abfd, asect)
- bfd *abfd;
- sec_ptr asect;
+oasys_get_reloc_upper_bound (bfd *abfd, sec_ptr asect)
{
if (! oasys_slurp_section_data (abfd))
return -1;
}
static bfd_boolean
-oasys_get_section_contents (abfd, section, location, offset, count)
- bfd *abfd;
- sec_ptr section;
- PTR location;
- file_ptr offset;
- bfd_size_type count;
+oasys_get_section_contents (bfd *abfd,
+ sec_ptr section,
+ void * location,
+ file_ptr offset,
+ bfd_size_type count)
{
oasys_per_section_type *p = oasys_per_section (section);
+
oasys_slurp_section_data (abfd);
+
if (! p->initialized)
- {
- (void) memset (location, 0, (size_t) count);
- }
+ (void) memset (location, 0, (size_t) count);
else
- {
- (void) memcpy (location, (PTR) (p->data + offset), (size_t) count);
- }
+ (void) memcpy (location, (void *) (p->data + offset), (size_t) count);
+
return TRUE;
}
-
-long
-oasys_canonicalize_reloc (ignore_abfd, section, relptr, symbols)
- bfd *ignore_abfd ATTRIBUTE_UNUSED;
- sec_ptr section;
- arelent **relptr;
- asymbol **symbols ATTRIBUTE_UNUSED;
+static long
+oasys_canonicalize_reloc (bfd *ignore_abfd ATTRIBUTE_UNUSED,
+ sec_ptr section,
+ arelent **relptr,
+ asymbol **symbols ATTRIBUTE_UNUSED)
{
unsigned int reloc_count = 0;
oasys_reloc_type *src = (oasys_reloc_type *) (section->relocation);
- while (src != (oasys_reloc_type *) NULL)
- {
- abort ();
- *relptr++ = &src->relent;
- src = src->next;
- reloc_count++;
- }
- *relptr = (arelent *) NULL;
+ if (src != NULL)
+ abort ();
+
+ *relptr = NULL;
return section->reloc_count = reloc_count;
}
+/* Writing. */
+/* Calculate the checksum and write one record. */
-/* Writing */
-
-
-/* Calculate the checksum and write one record */
static bfd_boolean
-oasys_write_record (abfd, type, record, size)
- bfd *abfd;
- oasys_record_enum_type type;
- oasys_record_union_type *record;
- size_t size;
+oasys_write_record (bfd *abfd,
+ oasys_record_enum_type type,
+ oasys_record_union_type *record,
+ size_t size)
{
int checksum;
size_t i;
ptr = (unsigned char *) &record->pad[0];
checksum = 0;
for (i = 0; i < size; i++)
- {
- checksum += *ptr++;
- }
+ checksum += *ptr++;
record->header.check_sum = 0xff & (-checksum);
- if (bfd_bwrite ((PTR) record, (bfd_size_type) size, abfd) != size)
+ if (bfd_bwrite ((void *) record, (bfd_size_type) size, abfd) != size)
return FALSE;
return TRUE;
}
-/* Write out all the symbols */
+/* Write out all the symbols. */
+
static bfd_boolean
-oasys_write_syms (abfd)
- bfd *abfd;
+oasys_write_syms (bfd *abfd)
{
unsigned int count;
asymbol **generic = bfd_get_outsymbols (abfd);
unsigned int index = 0;
+
for (count = 0; count < bfd_get_symcount (abfd); count++)
{
-
oasys_symbol_record_type symbol;
asymbol *const g = generic[count];
-
const char *src = g->name;
char *dst = symbol.name;
unsigned int l = 0;
{
symbol.relb = RELOCATION_TYPE_ABS;
H_PUT_16 (abfd, 0, symbol.refno);
-
}
else if (bfd_is_und_section (g->section))
{
index++;
}
else if (g->flags & BSF_DEBUGGING)
- {
- /* throw it away */
- continue;
- }
+ /* Throw it away. */
+ continue;
else
{
- if (g->section == (asection *) NULL)
- {
- /* Sometime, the oasys tools give out a symbol with illegal
- bits in it, we'll output it in the same broken way */
-
- symbol.relb = RELOCATION_TYPE_REL | 0;
- }
+ if (g->section == NULL)
+ /* Sometime, the oasys tools give out a symbol with illegal
+ bits in it, we'll output it in the same broken way. */
+ symbol.relb = RELOCATION_TYPE_REL | 0;
else
- {
- symbol.relb = RELOCATION_TYPE_REL | g->section->output_section->target_index;
- }
+ symbol.relb = RELOCATION_TYPE_REL | g->section->output_section->target_index;
+
H_PUT_16 (abfd, 0, symbol.refno);
}
+
#ifdef UNDERSCORE_HACK
if (src[l] == '_')
dst[l++] = '.';
H_PUT_32 (abfd, g->value, symbol.value);
-
if (g->flags & BSF_LOCAL)
{
if (! oasys_write_record (abfd,
return TRUE;
}
+/* Write a section header for each section. */
- /* Write a section header for each section */
static bfd_boolean
-oasys_write_sections (abfd)
- bfd *abfd;
+oasys_write_sections (bfd *abfd)
{
asection *s;
static oasys_section_record_type out;
- for (s = abfd->sections; s != (asection *) NULL; s = s->next)
+ for (s = abfd->sections; s != NULL; s = s->next)
{
if (!ISDIGIT (s->name[0]))
{
}
static bfd_boolean
-oasys_write_header (abfd)
- bfd *abfd;
+oasys_write_header (bfd *abfd)
{
- /* Create and write the header */
+ /* Create and write the header. */
oasys_header_record_type r;
size_t length = strlen (abfd->filename);
+
if (length > (size_t) sizeof (r.module_name))
- {
- length = sizeof (r.module_name);
- }
+ length = sizeof (r.module_name);
- (void) memcpy (r.module_name,
- abfd->filename,
- length);
- (void) memset (r.module_name + length,
- ' ',
- sizeof (r.module_name) - length);
+ (void) memcpy (r.module_name, abfd->filename, length);
+ (void) memset (r.module_name + length, ' ', sizeof (r.module_name) - length);
r.version_number = OASYS_VERSION_NUMBER;
r.rev_number = OASYS_REV_NUMBER;
- if (! oasys_write_record (abfd,
- oasys_record_is_header_enum,
- (oasys_record_union_type *) & r,
- offsetof (oasys_header_record_type,
- description[0])))
- return FALSE;
- return TRUE;
+ return oasys_write_record (abfd, oasys_record_is_header_enum,
+ (oasys_record_union_type *) & r,
+ offsetof (oasys_header_record_type,
+ description[0]));
}
static bfd_boolean
-oasys_write_end (abfd)
- bfd *abfd;
+oasys_write_end (bfd *abfd)
{
oasys_end_record_type end;
unsigned char null = 0;
+
end.relb = RELOCATION_TYPE_ABS;
H_PUT_32 (abfd, abfd->start_address, end.entry);
H_PUT_16 (abfd, 0, end.fill);
(oasys_record_union_type *) & end,
sizeof (end)))
return FALSE;
- if (bfd_bwrite ((PTR) &null, (bfd_size_type) 1, abfd) != 1)
- return FALSE;
- return TRUE;
+
+ return bfd_bwrite ((void *) &null, (bfd_size_type) 1, abfd) == 1;
}
static int
-comp (ap, bp)
- const PTR ap;
- const PTR bp;
+comp (const void * ap, const void * bp)
{
arelent *a = *((arelent **) ap);
arelent *b = *((arelent **) bp);
+
return a->address - b->address;
}
-/*
- Writing data..
-
-*/
static bfd_boolean
-oasys_write_data (abfd)
- bfd *abfd;
+oasys_write_data (bfd *abfd)
{
asection *s;
- for (s = abfd->sections; s != (asection *) NULL; s = s->next)
+
+ for (s = abfd->sections; s != NULL; s = s->next)
{
if (s->flags & SEC_LOAD)
{
bfd_size_type current_byte_index = 0;
unsigned int relocs_to_go = s->reloc_count;
arelent **p = s->orelocation;
+
if (s->reloc_count != 0)
- {
-/* Sort the reloc records so it's easy to insert the relocs into the
- data */
+ /* Sort the reloc records so it's easy to insert the relocs into the
+ data. */
+ qsort (s->orelocation, s->reloc_count, sizeof (arelent **), comp);
- qsort (s->orelocation,
- s->reloc_count,
- sizeof (arelent **),
- comp);
- }
current_byte_index = 0;
processed_data.relb = s->target_index | RELOCATION_TYPE_REL;
while (current_byte_index < s->size)
{
/* Scan forwards by eight bytes or however much is left and see if
- there are any relocations going on */
+ there are any relocations going on. */
bfd_byte *mod = &processed_data.data[0];
bfd_byte *dst = &processed_data.data[1];
unsigned int i = 0;
*mod = 0;
-
H_PUT_32 (abfd, s->vma + current_byte_index,
processed_data.addr);
/* Don't start a relocation unless you're sure you can finish it
- within the same data record. The worst case relocation is a
- 4-byte relocatable value which is split across two modification
- bytes (1 relocation byte + 2 symbol reference bytes + 2 data +
- 1 modification byte + 2 data = 8 bytes total). That's where
- the magic number 8 comes from.
- */
+ within the same data record. The worst case relocation is a
+ 4-byte relocatable value which is split across two modification
+ bytes (1 relocation byte + 2 symbol reference bytes + 2 data +
+ 1 modification byte + 2 data = 8 bytes total). That's where
+ the magic number 8 comes from. */
while (current_byte_index < s->size && dst <=
- &processed_data.data[sizeof (processed_data.data) - 8])
+ & processed_data.data[sizeof (processed_data.data) - 8])
{
-
-
if (relocs_to_go != 0)
{
arelent *r = *p;
- reloc_howto_type *const how = r->howto;
- /* There is a relocation, is it for this byte ? */
- if (r->address == current_byte_index)
- {
- unsigned char rel_byte;
-
- p++;
- relocs_to_go--;
-
- *mod |= (1 << i);
- if (how->pc_relative)
- {
- rel_byte = RELOCATION_PCREL_BIT;
- /* Also patch the raw data so that it doesn't have
- the -ve stuff any more */
- if (how->size != 2)
- {
- bfd_put_16 (abfd,
- bfd_get_16 (abfd, raw_data) +
- current_byte_index, raw_data);
- }
-
- else
- {
- bfd_put_32 (abfd,
- bfd_get_32 (abfd, raw_data) +
- current_byte_index, raw_data);
- }
- }
- else
- {
- rel_byte = 0;
- }
- if (how->size == 2)
- {
- rel_byte |= RELOCATION_32BIT_BIT;
- }
-
- /* Is this a section relative relocation, or a symbol
- relative relocation ? */
- abort ();
-
- {
- asymbol *sym = *(r->sym_ptr_ptr);
-
- /* If this symbol has a section attached, then it
- has already been resolved. Change from a symbol
- ref to a section ref */
- if (sym->section != (asection *) NULL)
- {
- rel_byte |= RELOCATION_TYPE_REL;
- rel_byte |=
- sym->section->output_section->target_index;
- *dst++ = rel_byte;
- }
- else
- {
- rel_byte |= RELOCATION_TYPE_UND;
- *dst++ = rel_byte;
- /* Next two bytes are a symbol index - we can get
- this from the symbol value which has been zapped
- into the symbol index in the table when the
- symbol table was written
- */
- *dst++ = sym->value >> 8;
- *dst++ = sym->value;
- }
- }
-#define ADVANCE { if (++i >= 8) { i = 0; mod = dst++; *mod = 0; } current_byte_index++; }
- /* relocations never occur from an unloadable section,
- so we can assume that raw_data is not NULL
- */
- *dst++ = *raw_data++;
- ADVANCE
- * dst++ = *raw_data++;
- ADVANCE
- if (how->size == 2)
- {
- *dst++ = *raw_data++;
- ADVANCE
- * dst++ = *raw_data++;
- ADVANCE
- }
- continue;
- }
+ /* There is a relocation, is it for this byte ? */
+ if (r->address == current_byte_index)
+ abort ();
}
+
/* If this is coming from an unloadable section then copy
- zeros */
+ zeros. */
if (raw_data == NULL)
- {
- *dst++ = 0;
- }
+ *dst++ = 0;
else
+ *dst++ = *raw_data++;
+
+ if (++i >= 8)
{
- *dst++ = *raw_data++;
+ i = 0;
+ mod = dst++;
+ *mod = 0;
}
- ADVANCE
+ current_byte_index++;
}
- /* Don't write a useless null modification byte */
+ /* Don't write a useless null modification byte. */
if (dst == mod + 1)
- {
- --dst;
- }
+ --dst;
if (! (oasys_write_record
(abfd, oasys_record_is_data_enum,
}
static bfd_boolean
-oasys_write_object_contents (abfd)
- bfd *abfd;
+oasys_write_object_contents (bfd *abfd)
{
if (! oasys_write_header (abfd))
return FALSE;
return TRUE;
}
+/* Set section contents is complicated with OASYS since the format is
+ not a byte image, but a record stream. */
-
-
-/** exec and core file sections */
-
-/* set section contents is complicated with OASYS since the format is
-* not a byte image, but a record stream.
-*/
static bfd_boolean
-oasys_set_section_contents (abfd, section, location, offset, count)
- bfd *abfd;
- sec_ptr section;
- const PTR location;
- file_ptr offset;
- bfd_size_type count;
+oasys_set_section_contents (bfd *abfd,
+ sec_ptr section,
+ const void * location,
+ file_ptr offset,
+ bfd_size_type count)
{
if (count != 0)
{
- if (oasys_per_section (section)->data == (bfd_byte *) NULL)
+ if (oasys_per_section (section)->data == NULL)
{
- oasys_per_section (section)->data =
- (bfd_byte *) (bfd_alloc (abfd, section->size));
+ oasys_per_section (section)->data = bfd_alloc (abfd, section->size);
if (!oasys_per_section (section)->data)
return FALSE;
}
- (void) memcpy ((PTR) (oasys_per_section (section)->data + offset),
- location,
- (size_t) count);
+ (void) memcpy ((void *) (oasys_per_section (section)->data + offset),
+ location, (size_t) count);
}
return TRUE;
}
-/* Native-level interface to symbols. */
+/* Native-level interface to symbols. */
/* We read the symbols into a buffer, which is discarded when this
-function exits. We read the strings into a buffer large enough to
-hold them all plus all the cached symbol entries. */
+ function exits. We read the strings into a buffer large enough to
+ hold them all plus all the cached symbol entries. */
static asymbol *
-oasys_make_empty_symbol (abfd)
- bfd *abfd;
+oasys_make_empty_symbol (bfd *abfd)
{
bfd_size_type amt = sizeof (oasys_symbol_type);
- oasys_symbol_type *new = (oasys_symbol_type *) bfd_zalloc (abfd, amt);
+ oasys_symbol_type *new = bfd_zalloc (abfd, amt);
+
if (!new)
return NULL;
new->symbol.the_bfd = abfd;
return &new->symbol;
}
-\f
-
-
/* User should have checked the file flags; perhaps we should return
-BFD_NO_MORE_SYMBOLS if there are none? */
+ BFD_NO_MORE_SYMBOLS if there are none? */
static bfd *
-oasys_openr_next_archived_file (arch, prev)
- bfd *arch;
- bfd *prev;
+oasys_openr_next_archived_file (bfd *arch, bfd *prev)
{
oasys_ar_data_type *ar = OASYS_AR_DATA (arch);
oasys_module_info_type *p;
- /* take the next one from the arch state, or reset */
- if (prev == (bfd *) NULL)
- {
- /* Reset the index - the first two entries are bogus*/
- ar->module_index = 0;
- }
+
+ /* Take the next one from the arch state, or reset. */
+ if (prev == NULL)
+ /* Reset the index - the first two entries are bogus. */
+ ar->module_index = 0;
p = ar->module + ar->module_index;
ar->module_index++;
if (ar->module_index <= ar->module_count)
{
- if (p->abfd == (bfd *) NULL)
+ if (p->abfd == NULL)
{
p->abfd = _bfd_create_empty_archive_element_shell (arch);
p->abfd->origin = p->pos;
p->abfd->filename = p->name;
- /* Fixup a pointer to this element for the member */
- p->abfd->arelt_data = (PTR) p;
+ /* Fixup a pointer to this element for the member. */
+ p->abfd->arelt_data = (void *) p;
}
return p->abfd;
}
- else
- {
- bfd_set_error (bfd_error_no_more_archived_files);
- return (bfd *) NULL;
- }
+
+ bfd_set_error (bfd_error_no_more_archived_files);
+ return NULL;
}
static bfd_boolean
-oasys_find_nearest_line (abfd, section, symbols, offset,
- filename_ptr, functionname_ptr, line_ptr)
- bfd *abfd ATTRIBUTE_UNUSED;
- asection *section ATTRIBUTE_UNUSED;
- asymbol **symbols ATTRIBUTE_UNUSED;
- bfd_vma offset ATTRIBUTE_UNUSED;
- const char **filename_ptr ATTRIBUTE_UNUSED;
- const char **functionname_ptr ATTRIBUTE_UNUSED;
- unsigned int *line_ptr ATTRIBUTE_UNUSED;
+oasys_find_nearest_line (bfd *abfd ATTRIBUTE_UNUSED,
+ asection *section ATTRIBUTE_UNUSED,
+ asymbol **symbols ATTRIBUTE_UNUSED,
+ bfd_vma offset ATTRIBUTE_UNUSED,
+ const char **filename_ptr ATTRIBUTE_UNUSED,
+ const char **functionname_ptr ATTRIBUTE_UNUSED,
+ unsigned int *line_ptr ATTRIBUTE_UNUSED)
{
return FALSE;
-
}
static int
-oasys_generic_stat_arch_elt (abfd, buf)
- bfd *abfd;
- struct stat *buf;
+oasys_generic_stat_arch_elt (bfd *abfd, struct stat *buf)
{
oasys_module_info_type *mod = (oasys_module_info_type *) abfd->arelt_data;
- if (mod == (oasys_module_info_type *) NULL)
+
+ if (mod == NULL)
{
bfd_set_error (bfd_error_invalid_operation);
return -1;
}
- else
- {
- buf->st_size = mod->size;
- buf->st_mode = 0666;
- return 0;
- }
+
+ buf->st_size = mod->size;
+ buf->st_mode = 0666;
+ return 0;
}
static int
-oasys_sizeof_headers (abfd, exec)
- bfd *abfd ATTRIBUTE_UNUSED;
- bfd_boolean exec ATTRIBUTE_UNUSED;
+oasys_sizeof_headers (bfd *abfd ATTRIBUTE_UNUSED, bfd_boolean exec ATTRIBUTE_UNUSED)
{
return 0;
}
-#define oasys_close_and_cleanup _bfd_generic_close_and_cleanup
-#define oasys_bfd_free_cached_info _bfd_generic_bfd_free_cached_info
-
-#define oasys_slurp_armap bfd_true
-#define oasys_slurp_extended_name_table bfd_true
-#define oasys_construct_extended_name_table \
- ((bfd_boolean (*) PARAMS ((bfd *, char **, bfd_size_type *, const char **))) \
- bfd_true)
-#define oasys_truncate_arname bfd_dont_truncate_arname
-#define oasys_write_armap \
- ((bfd_boolean (*) \
- PARAMS ((bfd *, unsigned int, struct orl *, unsigned int, int))) \
- bfd_true)
-#define oasys_read_ar_hdr bfd_nullvoidptr
-#define oasys_get_elt_at_index _bfd_generic_get_elt_at_index
-#define oasys_update_armap_timestamp bfd_true
-
-#define oasys_bfd_is_local_label_name bfd_generic_is_local_label_name
-#define oasys_bfd_is_target_special_symbol ((bfd_boolean (*) (bfd *, asymbol *)) bfd_false)
-#define oasys_get_lineno _bfd_nosymbols_get_lineno
-#define oasys_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
-#define oasys_read_minisymbols _bfd_generic_read_minisymbols
-#define oasys_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol
-
-#define oasys_bfd_reloc_type_lookup _bfd_norelocs_bfd_reloc_type_lookup
-
-#define oasys_set_arch_mach bfd_default_set_arch_mach
-
-#define oasys_get_section_contents_in_window \
- _bfd_generic_get_section_contents_in_window
-
-#define oasys_bfd_get_relocated_section_contents \
- bfd_generic_get_relocated_section_contents
-#define oasys_bfd_relax_section bfd_generic_relax_section
-#define oasys_bfd_gc_sections bfd_generic_gc_sections
-#define oasys_bfd_merge_sections bfd_generic_merge_sections
-#define oasys_bfd_is_group_section bfd_generic_is_group_section
-#define oasys_bfd_discard_group bfd_generic_discard_group
-#define oasys_section_already_linked \
- _bfd_generic_section_already_linked
-#define oasys_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
-#define oasys_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
-#define oasys_bfd_link_add_symbols _bfd_generic_link_add_symbols
-#define oasys_bfd_link_just_syms _bfd_generic_link_just_syms
-#define oasys_bfd_final_link _bfd_generic_final_link
-#define oasys_bfd_link_split_section _bfd_generic_link_split_section
-
-/*SUPPRESS 460 */
+#define oasys_close_and_cleanup _bfd_generic_close_and_cleanup
+#define oasys_bfd_free_cached_info _bfd_generic_bfd_free_cached_info
+#define oasys_slurp_armap bfd_true
+#define oasys_slurp_extended_name_table bfd_true
+#define oasys_construct_extended_name_table ((bfd_boolean (*) (bfd *, char **, bfd_size_type *, const char **)) bfd_true)
+#define oasys_truncate_arname bfd_dont_truncate_arname
+#define oasys_write_armap ((bfd_boolean (*) (bfd *, unsigned int, struct orl *, unsigned int, int)) bfd_true)
+#define oasys_read_ar_hdr bfd_nullvoidptr
+#define oasys_get_elt_at_index _bfd_generic_get_elt_at_index
+#define oasys_update_armap_timestamp bfd_true
+#define oasys_bfd_is_local_label_name bfd_generic_is_local_label_name
+#define oasys_bfd_is_target_special_symbol ((bfd_boolean (*) (bfd *, asymbol *)) bfd_false)
+#define oasys_get_lineno _bfd_nosymbols_get_lineno
+#define oasys_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
+#define oasys_read_minisymbols _bfd_generic_read_minisymbols
+#define oasys_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol
+#define oasys_bfd_reloc_type_lookup _bfd_norelocs_bfd_reloc_type_lookup
+#define oasys_set_arch_mach bfd_default_set_arch_mach
+#define oasys_get_section_contents_in_window _bfd_generic_get_section_contents_in_window
+#define oasys_bfd_get_relocated_section_contents bfd_generic_get_relocated_section_contents
+#define oasys_bfd_relax_section bfd_generic_relax_section
+#define oasys_bfd_gc_sections bfd_generic_gc_sections
+#define oasys_bfd_merge_sections bfd_generic_merge_sections
+#define oasys_bfd_is_group_section bfd_generic_is_group_section
+#define oasys_bfd_discard_group bfd_generic_discard_group
+#define oasys_section_already_linked _bfd_generic_section_already_linked
+#define oasys_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
+#define oasys_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
+#define oasys_bfd_link_add_symbols _bfd_generic_link_add_symbols
+#define oasys_bfd_link_just_syms _bfd_generic_link_just_syms
+#define oasys_bfd_final_link _bfd_generic_final_link
+#define oasys_bfd_link_split_section _bfd_generic_link_split_section
+
const bfd_target oasys_vec =
{
- "oasys", /* name */
+ "oasys", /* Name. */
bfd_target_oasys_flavour,
- BFD_ENDIAN_BIG, /* target byte order */
- BFD_ENDIAN_BIG, /* target headers byte order */
- (HAS_RELOC | EXEC_P | /* object flags */
+ BFD_ENDIAN_BIG, /* Target byte order. */
+ BFD_ENDIAN_BIG, /* Target headers byte order. */
+ (HAS_RELOC | EXEC_P | /* Object flags. */
HAS_LINENO | HAS_DEBUG |
HAS_SYMS | HAS_LOCALS | WP_TEXT | D_PAGED),
(SEC_CODE | SEC_DATA | SEC_ROM | SEC_HAS_CONTENTS
- | SEC_ALLOC | SEC_LOAD | SEC_RELOC), /* section flags */
- 0, /* leading underscore */
- ' ', /* ar_pad_char */
- 16, /* ar_max_namelen */
+ | SEC_ALLOC | SEC_LOAD | SEC_RELOC), /* Section flags. */
+ 0, /* Leading underscore. */
+ ' ', /* AR_pad_char. */
+ 16, /* AR_max_namelen. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* data */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Data. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* hdrs */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Headers. */
{_bfd_dummy_target,
- oasys_object_p, /* bfd_check_format */
+ oasys_object_p, /* bfd_check_format. */
oasys_archive_p,
_bfd_dummy_target,
},
- { /* bfd_set_format */
+ { /* bfd_set_format. */
bfd_false,
oasys_mkobject,
_bfd_generic_mkarchive,
bfd_false
},
- { /* bfd_write_contents */
+ { /* bfd_write_contents. */
bfd_false,
oasys_write_object_contents,
_bfd_write_archive_contents,
NULL,
- (PTR) 0
+ NULL
};
#define N_FLAGS(exec) 0
#define N_SET_FLAGS(exec, flags) do { } while (0)
-#define N_BADMAG(x) (((x).a_info != OMAGIC) && \
- ((x).a_info != NMAGIC) && \
- ((x).a_info != A_MAGIC3) && \
- ((x).a_info != A_MAGIC4) && \
- ((x).a_info != A_MAGIC5) && \
- ((x).a_info != A_MAGIC6))
+#define N_BADMAG(x) (((x).a_info != OMAGIC) \
+ && ((x).a_info != NMAGIC) \
+ && ((x).a_info != A_MAGIC3) \
+ && ((x).a_info != A_MAGIC4) \
+ && ((x).a_info != A_MAGIC5) \
+ && ((x).a_info != A_MAGIC6))
#include "bfd.h"
#define external_exec pdp11_external_exec
struct pdp11_external_exec
- {
- bfd_byte e_info[2]; /* magic number */
- bfd_byte e_text[2]; /* length of text section in bytes */
- bfd_byte e_data[2]; /* length of data section in bytes */
- bfd_byte e_bss[2]; /* length of bss area in bytes */
- bfd_byte e_syms[2]; /* length of symbol table in bytes */
- bfd_byte e_entry[2]; /* start address */
- bfd_byte e_unused[2]; /* not used */
- bfd_byte e_flag[2]; /* relocation info stripped */
- bfd_byte e_relocatable; /* ugly hack */
- };
+{
+ bfd_byte e_info[2]; /* Magic number. */
+ bfd_byte e_text[2]; /* Length of text section in bytes. */
+ bfd_byte e_data[2]; /* Length of data section in bytes. */
+ bfd_byte e_bss[2]; /* Length of bss area in bytes. */
+ bfd_byte e_syms[2]; /* Length of symbol table in bytes. */
+ bfd_byte e_entry[2]; /* Start address. */
+ bfd_byte e_unused[2]; /* Not used. */
+ bfd_byte e_flag[2]; /* Relocation info stripped. */
+ bfd_byte e_relocatable; /* Ugly hack. */
+};
#define EXEC_BYTES_SIZE (8 * 2)
#define A_MAGIC1 OMAGIC
#define OMAGIC 0407 /* ...object file or impure executable. */
#define A_MAGIC2 NMAGIC
-#define NMAGIC 0410 /* pure executable. */
-#define ZMAGIC 0413 /* demand-paged executable. */
-#define A_MAGIC3 0411 /* separated I&D */
-#define A_MAGIC4 0405 /* overlay */
-#define A_MAGIC5 0430 /* auto-overlay (nonseparate) */
-#define A_MAGIC6 0431 /* auto-overlay (separate) */
+#define NMAGIC 0410 /* Pure executable. */
+#define ZMAGIC 0413 /* Demand-paged executable. */
+#define A_MAGIC3 0411 /* Separated I&D. */
+#define A_MAGIC4 0405 /* Overlay. */
+#define A_MAGIC5 0430 /* Auto-overlay (nonseparate). */
+#define A_MAGIC6 0431 /* Auto-overlay (separate). */
#define QMAGIC 0
#define BMAGIC 0
#define external_nlist pdp11_external_nlist
struct pdp11_external_nlist
- {
- bfd_byte e_unused[2]; /* unused */
- bfd_byte e_strx[2]; /* index into string table of name */
- bfd_byte e_type[1]; /* type of symbol */
- bfd_byte e_ovly[1]; /* overlay number */
- bfd_byte e_value[2]; /* value of symbol */
- };
+{
+ bfd_byte e_unused[2]; /* Unused. */
+ bfd_byte e_strx[2]; /* Index into string table of name. */
+ bfd_byte e_type[1]; /* Type of symbol. */
+ bfd_byte e_ovly[1]; /* Overlay number. */
+ bfd_byte e_value[2]; /* Value of symbol. */
+};
#define EXTERNAL_NLIST_SIZE 8
#define MY_entry_is_text_address 1
#define MY_write_object_contents MY(write_object_contents)
-static bfd_boolean MY(write_object_contents) PARAMS ((bfd *abfd));
+static bfd_boolean MY(write_object_contents) (bfd *);
#define MY_text_includes_header 1
-static bfd_vma bfd_getp32 (const void *);
-static bfd_signed_vma bfd_getp_signed_32 (const void *);
-static void bfd_putp32 (bfd_vma, void *);
-
#define MY_BFD_TARGET
#include "aout-target.h"
-const bfd_target MY(vec) =
-{
- TARGETNAME, /* name */
- bfd_target_aout_flavour,
- BFD_ENDIAN_LITTLE, /* target byte order (little) */
- BFD_ENDIAN_LITTLE, /* target headers byte order (little) */
- (HAS_RELOC | EXEC_P | /* object flags */
- HAS_LINENO | HAS_DEBUG |
- HAS_SYMS | HAS_LOCALS | WP_TEXT),
- (SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD | SEC_RELOC | SEC_CODE | SEC_DATA),
- MY_symbol_leading_char,
- AR_PAD_CHAR, /* ar_pad_char */
- 15, /* ar_max_namelen */
- bfd_getl64, bfd_getl_signed_64, bfd_putl64,
- bfd_getp32, bfd_getp_signed_32, bfd_putp32,
- bfd_getl16, bfd_getl_signed_16, bfd_putl16, /* data */
- bfd_getl64, bfd_getl_signed_64, bfd_putl64,
- bfd_getp32, bfd_getp_signed_32, bfd_putp32,
- bfd_getl16, bfd_getl_signed_16, bfd_putl16, /* hdrs */
- {_bfd_dummy_target, MY_object_p, /* bfd_check_format */
- bfd_generic_archive_p, MY_core_file_p},
- {bfd_false, MY_mkobject, /* bfd_set_format */
- _bfd_generic_mkarchive, bfd_false},
- {bfd_false, MY_write_object_contents, /* bfd_write_contents */
- _bfd_write_archive_contents, bfd_false},
-
- BFD_JUMP_TABLE_GENERIC (MY),
- BFD_JUMP_TABLE_COPY (MY),
- BFD_JUMP_TABLE_CORE (MY),
- BFD_JUMP_TABLE_ARCHIVE (MY),
- BFD_JUMP_TABLE_SYMBOLS (MY),
- BFD_JUMP_TABLE_RELOCS (MY),
- BFD_JUMP_TABLE_WRITE (MY),
- BFD_JUMP_TABLE_LINK (MY),
- BFD_JUMP_TABLE_DYNAMIC (MY),
-
- /* Alternative_target */
- NULL,
-
- (PTR) MY_backend_data,
-};
-
-/* start of modified aoutx.h */
-/* BFD semi-generic back-end for a.out binaries.
- Copyright 1990, 91, 92, 93, 94, 95, 96, 97, 1998
- Free Software Foundation, Inc.
- Written by Cygnus Support.
-
-This file is part of BFD, the Binary File Descriptor library.
-
-This program is free software; you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation; either version 2 of the License, or
-(at your option) any later version.
-
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with this program; if not, write to the Free Software
-Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
-
-/*
-SECTION
- a.out backends
-
-
-DESCRIPTION
-
- BFD supports a number of different flavours of a.out format,
- though the major differences are only the sizes of the
- structures on disk, and the shape of the relocation
- information.
-
- The support is split into a basic support file @file{aoutx.h}
- and other files which derive functions from the base. One
- derivation file is @file{aoutf1.h} (for a.out flavour 1), and
- adds to the basic a.out functions support for sun3, sun4, 386
- and 29k a.out files, to create a target jump vector for a
- specific target.
-
- This information is further split out into more specific files
- for each machine, including @file{sunos.c} for sun3 and sun4,
- @file{newsos3.c} for the Sony NEWS, and @file{demo64.c} for a
- demonstration of a 64 bit a.out format.
-
- The base file @file{aoutx.h} defines general mechanisms for
- reading and writing records to and from disk and various
- other methods which BFD requires. It is included by
- @file{aout32.c} and @file{aout64.c} to form the names
- <<aout_32_swap_exec_header_in>>, <<aout_64_swap_exec_header_in>>, etc.
-
- As an example, this is what goes on to make the back end for a
- sun4, from @file{aout32.c}:
-
-| #define ARCH_SIZE 32
-| #include "aoutx.h"
-
- Which exports names:
-
-| ...
-| aout_32_canonicalize_reloc
-| aout_32_find_nearest_line
-| aout_32_get_lineno
-| aout_32_get_reloc_upper_bound
-| ...
-
- from @file{sunos.c}:
-
-| #define TARGET_NAME "a.out-sunos-big"
-| #define VECNAME sunos_big_vec
-| #include "aoutf1.h"
-
- requires all the names from @file{aout32.c}, and produces the jump vector
-
-| sunos_big_vec
-
- The file @file{host-aout.c} is a special case. It is for a large set
- of hosts that use ``more or less standard'' a.out files, and
- for which cross-debugging is not interesting. It uses the
- standard 32-bit a.out support routines, but determines the
- file offsets and addresses of the text, data, and BSS
- sections, the machine architecture and machine type, and the
- entry point address, in a host-dependent manner. Once these
- values have been determined, generic code is used to handle
- the object file.
-
- When porting it to run on a new system, you must supply:
-
-| HOST_PAGE_SIZE
-| HOST_SEGMENT_SIZE
-| HOST_MACHINE_ARCH (optional)
-| HOST_MACHINE_MACHINE (optional)
-| HOST_TEXT_START_ADDR
-| HOST_STACK_END_ADDR
-
- in the file @file{../include/sys/h-@var{XXX}.h} (for your host). These
- values, plus the structures and macros defined in @file{a.out.h} on
- your host system, will produce a BFD target that will access
- ordinary a.out files on your host. To configure a new machine
- to use @file{host-aout.c}, specify:
-
-| TDEFAULTS = -DDEFAULT_VECTOR=host_aout_big_vec
-| TDEPFILES= host-aout.o trad-core.o
-
- in the @file{config/@var{XXX}.mt} file, and modify @file{configure.in}
- to use the
- @file{@var{XXX}.mt} file (by setting "<<bfd_target=XXX>>") when your
- configuration is selected.
-
-*/
-
-/* Some assumptions:
- * Any BFD with D_PAGED set is ZMAGIC, and vice versa.
- Doesn't matter what the setting of WP_TEXT is on output, but it'll
- get set on input.
- * Any BFD with D_PAGED clear and WP_TEXT set is NMAGIC.
- * Any BFD with both flags clear is OMAGIC.
- (Just want to make these explicit, so the conditions tested in this
- file make sense if you're more familiar with a.out than with BFD.) */
-
+/* Start of modified aoutx.h. */
#define KEEPIT udata.i
-#include <string.h> /* For strchr and friends */
+#include <string.h> /* For strchr and friends. */
#include "bfd.h"
#include "sysdep.h"
#include "safe-ctype.h"
#include "bfdlink.h"
#include "libaout.h"
-/*#include "libbfd.h"*/
#include "aout/aout64.h"
#include "aout/stab_gnu.h"
#include "aout/ar.h"
#undef N_REG
#undef N_FN
#undef N_EXT
-#define N_TYPE 0x1f /* type mask */
-#define N_UNDF 0x00 /* undefined */
-#define N_ABS 0x01 /* absolute */
-#define N_TEXT 0x02 /* text segment */
-#define N_DATA 0x03 /* data segment */
-#define N_BSS 0x04 /* bss segment */
-#define N_REG 0x14 /* register symbol */
-#define N_FN 0x1f /* file name */
-
-#define N_EXT 0x20 /* external flag */
+#define N_TYPE 0x1f /* Type mask. */
+#define N_UNDF 0x00 /* Undefined. */
+#define N_ABS 0x01 /* Absolute. */
+#define N_TEXT 0x02 /* Text segment. */
+#define N_DATA 0x03 /* Data segment. */
+#define N_BSS 0x04 /* Bss segment. */
+#define N_REG 0x14 /* Register symbol. */
+#define N_FN 0x1f /* File name. */
+#define N_EXT 0x20 /* External flag. */
#define RELOC_SIZE 2
-#define RELFLG 0x0001 /* pc-relative flag */
-#define RTYPE 0x000e /* type mask */
-#define RIDXMASK 0xfff0 /* index mask */
+#define RELFLG 0x0001 /* PC-relative flag. */
+#define RTYPE 0x000e /* Type mask. */
+#define RIDXMASK 0xfff0 /* Index mask. */
-#define RABS 0x00 /* absolute */
-#define RTEXT 0x02 /* text */
-#define RDATA 0x04 /* data */
-#define RBSS 0x06 /* bss */
-#define REXT 0x08 /* external */
+#define RABS 0x00 /* Absolute. */
+#define RTEXT 0x02 /* Text. */
+#define RDATA 0x04 /* Data. */
+#define RBSS 0x06 /* Bss. */
+#define REXT 0x08 /* External. */
#define RINDEX(x) (((x) & 0xfff0) >> 4)
-static bfd_boolean aout_get_external_symbols PARAMS ((bfd *));
-static bfd_boolean translate_from_native_sym_flags
- PARAMS ((bfd *, aout_symbol_type *));
-static bfd_boolean translate_to_native_sym_flags
- PARAMS ((bfd *, asymbol *, struct external_nlist *));
-static void adjust_o_magic PARAMS ((bfd *, struct internal_exec *));
-static void adjust_z_magic PARAMS ((bfd *, struct internal_exec *));
-static void adjust_n_magic PARAMS ((bfd *, struct internal_exec *));
-
-static int pdp11_aout_write_headers PARAMS ((bfd *, struct internal_exec *));
-void pdp11_aout_swap_reloc_out PARAMS ((bfd *, arelent *, bfd_byte *));
-void pdp11_aout_swap_reloc_in
-PARAMS ((bfd *, bfd_byte *, arelent *,
- bfd_size_type, asymbol **, bfd_size_type));
-
-/*
-SUBSECTION
- Relocations
-
-DESCRIPTION
- The file @file{aoutx.h} provides for both the @emph{standard}
- and @emph{extended} forms of a.out relocation records.
-
- The standard records contain only an
- address, a symbol index, and a type field. The extended records
- (used on 29ks and sparcs) also have a full integer for an
- addend.
-
-*/
-
#ifndef MY_final_link_relocate
#define MY_final_link_relocate _bfd_final_link_relocate
#endif
#define MY_relocate_contents _bfd_relocate_contents
#endif
+/* A hash table used for header files with N_BINCL entries. */
+
+struct aout_link_includes_table
+{
+ struct bfd_hash_table root;
+};
+
+/* A linked list of totals that we have found for a particular header
+ file. */
+
+struct aout_link_includes_totals
+{
+ struct aout_link_includes_totals *next;
+ bfd_vma total;
+};
+
+/* An entry in the header file hash table. */
+
+struct aout_link_includes_entry
+{
+ struct bfd_hash_entry root;
+ /* List of totals we have found for this file. */
+ struct aout_link_includes_totals *totals;
+};
+
+/* During the final link step we need to pass around a bunch of
+ information, so we do it in an instance of this structure. */
+
+struct aout_final_link_info
+{
+ /* General link information. */
+ struct bfd_link_info *info;
+ /* Output bfd. */
+ bfd *output_bfd;
+ /* Reloc file positions. */
+ file_ptr treloff, dreloff;
+ /* File position of symbols. */
+ file_ptr symoff;
+ /* String table. */
+ struct bfd_strtab_hash *strtab;
+ /* Header file hash table. */
+ struct aout_link_includes_table includes;
+ /* A buffer large enough to hold the contents of any section. */
+ bfd_byte *contents;
+ /* A buffer large enough to hold the relocs of any section. */
+ void * relocs;
+ /* A buffer large enough to hold the symbol map of any input BFD. */
+ int *symbol_map;
+ /* A buffer large enough to hold output symbols of any input BFD. */
+ struct external_nlist *output_syms;
+};
+
reloc_howto_type howto_table_pdp11[] =
{
/* type rs size bsz pcrel bitpos ovrf sf name part_inpl readmask setmask pcdone */
#define TABLE_SIZE(TABLE) (sizeof(TABLE)/sizeof(TABLE[0]))
+
+static bfd_boolean aout_link_check_archive_element (bfd *, struct bfd_link_info *, bfd_boolean *);
+static bfd_boolean aout_link_add_object_symbols (bfd *, struct bfd_link_info *);
+static bfd_boolean aout_link_add_symbols (bfd *, struct bfd_link_info *);
+static bfd_boolean aout_link_write_symbols (struct aout_final_link_info *, bfd *);
+
+
reloc_howto_type *
-NAME(aout,reloc_type_lookup) (abfd,code)
- bfd * abfd ATTRIBUTE_UNUSED;
- bfd_reloc_code_real_type code;
+NAME (aout, reloc_type_lookup) (bfd * abfd ATTRIBUTE_UNUSED,
+ bfd_reloc_code_real_type code)
{
switch (code)
{
case BFD_RELOC_16_PCREL:
return &howto_table_pdp11[1];
default:
- return (reloc_howto_type *)NULL;
+ return NULL;
}
}
static int
-pdp11_aout_write_headers (abfd, execp)
- bfd *abfd;
- struct internal_exec *execp;
+pdp11_aout_write_headers (bfd *abfd, struct internal_exec *execp)
{
struct external_exec exec_bytes;
bfd_size_type text_size;
file_ptr text_end;
if (adata(abfd).magic == undecided_magic)
- NAME(aout,adjust_sizes_and_vmas) (abfd, &text_size, &text_end);
+ NAME (aout, adjust_sizes_and_vmas) (abfd, &text_size, &text_end);
execp->a_syms = bfd_get_symcount (abfd) * EXTERNAL_NLIST_SIZE;
execp->a_entry = bfd_get_start_address (abfd);
- if (obj_textsec (abfd)->reloc_count > 0 ||
- obj_datasec (abfd)->reloc_count > 0)
+ if (obj_textsec (abfd)->reloc_count > 0
+ || obj_datasec (abfd)->reloc_count > 0)
{
execp->a_trsize = execp->a_text;
execp->a_drsize = execp->a_data;
execp->a_drsize = 0;
}
- NAME(aout,swap_exec_header_out) (abfd, execp, &exec_bytes);
+ NAME (aout, swap_exec_header_out) (abfd, execp, & exec_bytes);
if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) != 0)
return FALSE;
- if (bfd_bwrite ((PTR) &exec_bytes, (bfd_size_type) EXEC_BYTES_SIZE, abfd)
+ if (bfd_bwrite ((void *) &exec_bytes, (bfd_size_type) EXEC_BYTES_SIZE, abfd)
!= EXEC_BYTES_SIZE)
return FALSE;
- /* Now write out reloc info, followed by syms and strings */
-
- if (bfd_get_outsymbols (abfd) != (asymbol **) NULL
+ /* Now write out reloc info, followed by syms and strings. */
+ if (bfd_get_outsymbols (abfd) != NULL
&& bfd_get_symcount (abfd) != 0)
{
if (bfd_seek (abfd, (file_ptr) (N_SYMOFF(*execp)), SEEK_SET) != 0)
return FALSE;
- if (! NAME(aout,write_syms) (abfd))
+ if (! NAME (aout, write_syms) (abfd))
return FALSE;
}
- if (obj_textsec (abfd)->reloc_count > 0 ||
- obj_datasec (abfd)->reloc_count > 0)
+ if (obj_textsec (abfd)->reloc_count > 0
+ || obj_datasec (abfd)->reloc_count > 0)
{
- if (bfd_seek (abfd, (file_ptr) (N_TRELOFF(*execp)), SEEK_SET) != 0)
- return FALSE;
- if (!NAME(aout,squirt_out_relocs) (abfd, obj_textsec (abfd)))
- return FALSE;
-
- if (bfd_seek (abfd, (file_ptr) (N_DRELOFF(*execp)), SEEK_SET) != 0)
- return FALSE;
- if (!NAME(aout,squirt_out_relocs) (abfd, obj_datasec (abfd)))
+ if (bfd_seek (abfd, (file_ptr) (N_TRELOFF(*execp)), SEEK_SET) != 0
+ || !NAME (aout, squirt_out_relocs) (abfd, obj_textsec (abfd))
+ || bfd_seek (abfd, (file_ptr) (N_DRELOFF(*execp)), SEEK_SET) != 0
+ || !NAME (aout, squirt_out_relocs) (abfd, obj_datasec (abfd)))
return FALSE;
}
file header, symbols, and relocation. */
static bfd_boolean
-MY(write_object_contents) (abfd)
- bfd *abfd;
+MY(write_object_contents) (bfd *abfd)
{
struct internal_exec *execp = exec_hdr (abfd);
bfd_size_type text_size;
file_ptr text_end;
- NAME(aout,adjust_sizes_and_vmas) (abfd, &text_size, &text_end);
+ NAME (aout, adjust_sizes_and_vmas) (abfd, &text_size, &text_end);
}
obj_reloc_entry_size (abfd) = RELOC_SIZE;
- return WRITE_HEADERS(abfd, execp);
+ return WRITE_HEADERS (abfd, execp);
}
-/*
-SUBSECTION
- Internal entry points
-
-DESCRIPTION
- @file{aoutx.h} exports several routines for accessing the
- contents of an a.out file, which are gathered and exported in
- turn by various format specific files (eg sunos.c).
-
-*/
-
-/*
-FUNCTION
- aout_@var{size}_swap_exec_header_in
-
-SYNOPSIS
- void aout_@var{size}_swap_exec_header_in,
- (bfd *abfd,
- struct external_exec *raw_bytes,
- struct internal_exec *execp);
-
-DESCRIPTION
- Swap the information in an executable header @var{raw_bytes} taken
- from a raw byte stream memory image into the internal exec header
- structure @var{execp}.
-*/
+/* Swap the information in an executable header @var{raw_bytes} taken
+ from a raw byte stream memory image into the internal exec header
+ structure "execp". */
#ifndef NAME_swap_exec_header_in
void
-NAME(aout,swap_exec_header_in) (abfd, raw_bytes, execp)
- bfd *abfd;
- struct external_exec *raw_bytes;
- struct internal_exec *execp;
+NAME (aout, swap_exec_header_in) (bfd *abfd,
+ struct external_exec *bytes,
+ struct internal_exec *execp)
{
- struct external_exec *bytes = (struct external_exec *)raw_bytes;
-
/* The internal_exec structure has some fields that are unused in this
configuration (IE for i960), so ensure that all such uninitialized
fields are zero'd out. There are places where two of these structs
- are memcmp'd, and thus the contents do matter. */
- memset ((PTR) execp, 0, sizeof (struct internal_exec));
+ are memcmp'd, and thus the contents do matter. */
+ memset ((void *) execp, 0, sizeof (struct internal_exec));
/* Now fill in fields in the execp, from the bytes in the raw data. */
execp->a_info = GET_MAGIC (abfd, bytes->e_info);
execp->a_text = GET_WORD (abfd, bytes->e_text);
execp->a_drsize = execp->a_data;
}
}
-#define NAME_swap_exec_header_in NAME(aout,swap_exec_header_in)
+#define NAME_swap_exec_header_in NAME (aout, swap_exec_header_in)
#endif
-/*
-FUNCTION
- aout_@var{size}_swap_exec_header_out
-
-SYNOPSIS
- void aout_@var{size}_swap_exec_header_out
- (bfd *abfd,
- struct internal_exec *execp,
- struct external_exec *raw_bytes);
-
-DESCRIPTION
- Swap the information in an internal exec header structure
- @var{execp} into the buffer @var{raw_bytes} ready for writing to disk.
-*/
+/* Swap the information in an internal exec header structure
+ "execp" into the buffer "bytes" ready for writing to disk. */
void
-NAME(aout,swap_exec_header_out) (abfd, execp, raw_bytes)
- bfd *abfd;
- struct internal_exec *execp;
- struct external_exec *raw_bytes;
+NAME (aout, swap_exec_header_out) (bfd *abfd,
+ struct internal_exec *execp,
+ struct external_exec *bytes)
{
- struct external_exec *bytes = (struct external_exec *)raw_bytes;
-
- /* Now fill in fields in the raw data, from the fields in the exec struct. */
+ /* Now fill in fields in the raw data, from the fields in the exec struct. */
PUT_MAGIC (abfd, execp->a_info, bytes->e_info);
PUT_WORD (abfd, execp->a_text, bytes->e_text);
PUT_WORD (abfd, execp->a_data, bytes->e_data);
PUT_WORD (abfd, execp->a_entry, bytes->e_entry);
PUT_WORD (abfd, 0, bytes->e_unused);
- if ((execp->a_trsize == 0 || execp->a_text == 0) &&
- (execp->a_drsize == 0 || execp->a_data == 0))
- PUT_WORD (abfd, A_FLAG_RELOC_STRIPPED, bytes->e_flag);
- else if (execp->a_trsize == execp->a_text &&
- execp->a_drsize == execp->a_data)
- PUT_WORD (abfd, 0, bytes->e_flag);
+ if ((execp->a_trsize == 0 || execp->a_text == 0)
+ && (execp->a_drsize == 0 || execp->a_data == 0))
+ PUT_WORD (abfd, A_FLAG_RELOC_STRIPPED, bytes->e_flag);
+ else if (execp->a_trsize == execp->a_text
+ && execp->a_drsize == execp->a_data)
+ PUT_WORD (abfd, 0, bytes->e_flag);
else
{
- /* TODO: print a proper warning message */
+ /* TODO: print a proper warning message. */
fprintf (stderr, "BFD:%s:%d: internal error\n", __FILE__, __LINE__);
PUT_WORD (abfd, 0, bytes->e_flag);
}
/* Make all the section for an a.out file. */
bfd_boolean
-NAME(aout,make_sections) (abfd)
- bfd *abfd;
+NAME (aout, make_sections) (bfd *abfd)
{
- if (obj_textsec (abfd) == (asection *) NULL
- && bfd_make_section (abfd, ".text") == (asection *) NULL)
+ if (obj_textsec (abfd) == NULL && bfd_make_section (abfd, ".text") == NULL)
return FALSE;
- if (obj_datasec (abfd) == (asection *) NULL
- && bfd_make_section (abfd, ".data") == (asection *) NULL)
+ if (obj_datasec (abfd) == NULL && bfd_make_section (abfd, ".data") == NULL)
return FALSE;
- if (obj_bsssec (abfd) == (asection *) NULL
- && bfd_make_section (abfd, ".bss") == (asection *) NULL)
+ if (obj_bsssec (abfd) == NULL && bfd_make_section (abfd, ".bss") == NULL)
return FALSE;
return TRUE;
}
-/*
-FUNCTION
- aout_@var{size}_some_aout_object_p
-
-SYNOPSIS
- const bfd_target *aout_@var{size}_some_aout_object_p
- (bfd *abfd,
- const bfd_target *(*callback_to_real_object_p)());
-
-DESCRIPTION
- Some a.out variant thinks that the file open in @var{abfd}
- checking is an a.out file. Do some more checking, and set up
- for access if it really is. Call back to the calling
- environment's "finish up" function just before returning, to
- handle any last-minute setup.
-*/
+/* Some a.out variant thinks that the file open in ABFD
+ checking is an a.out file. Do some more checking, and set up
+ for access if it really is. Call back to the calling
+ environment's "finish up" function just before returning, to
+ handle any last-minute setup. */
const bfd_target *
-NAME(aout,some_aout_object_p) (abfd, execp, callback_to_real_object_p)
- bfd *abfd;
- struct internal_exec *execp;
- const bfd_target *(*callback_to_real_object_p) PARAMS ((bfd *));
+NAME (aout, some_aout_object_p) (bfd *abfd,
+ struct internal_exec *execp,
+ const bfd_target *(*callback_to_real_object_p) (bfd *))
{
struct aout_data_struct *rawptr, *oldrawptr;
const bfd_target *result;
bfd_size_type amt = sizeof (struct aout_data_struct);
- rawptr = (struct aout_data_struct *) bfd_zalloc (abfd, amt);
+ rawptr = bfd_zalloc (abfd, amt);
if (rawptr == NULL)
return 0;
*abfd->tdata.aout_data = *oldrawptr;
abfd->tdata.aout_data->a.hdr = &rawptr->e;
- *(abfd->tdata.aout_data->a.hdr) = *execp; /* Copy in the internal_exec struct */
+ *(abfd->tdata.aout_data->a.hdr) = *execp; /* Copy in the internal_exec struct. */
execp = abfd->tdata.aout_data->a.hdr;
- /* Set the file flags */
+ /* Set the file flags. */
abfd->flags = BFD_NO_FLAGS;
if (execp->a_drsize || execp->a_trsize)
abfd->flags |= HAS_RELOC;
- /* Setting of EXEC_P has been deferred to the bottom of this function */
+ /* Setting of EXEC_P has been deferred to the bottom of this function. */
if (execp->a_syms)
abfd->flags |= HAS_LINENO | HAS_DEBUG | HAS_SYMS | HAS_LOCALS;
if (N_DYNAMIC(*execp))
bfd_get_start_address (abfd) = execp->a_entry;
- obj_aout_symbols (abfd) = (aout_symbol_type *)NULL;
+ obj_aout_symbols (abfd) = NULL;
bfd_get_symcount (abfd) = execp->a_syms / sizeof (struct external_nlist);
/* The default relocation entry size is that of traditional V7 Unix. */
obj_reloc_entry_size (abfd) = RELOC_SIZE;
- /* The default symbol entry size is that of traditional Unix. */
+ /* The default symbol entry size is that of traditional Unix. */
obj_symbol_entry_size (abfd) = EXTERNAL_NLIST_SIZE;
#ifdef USE_MMAP
bfd_init_window (&obj_aout_sym_window (abfd));
bfd_init_window (&obj_aout_string_window (abfd));
#endif
+
obj_aout_external_syms (abfd) = NULL;
obj_aout_external_strings (abfd) = NULL;
obj_aout_sym_hashes (abfd) = NULL;
- if (! NAME(aout,make_sections) (abfd))
+ if (! NAME (aout, make_sections) (abfd))
return NULL;
obj_datasec (abfd)->size = execp->a_data;
/* Call back to the format-dependent code to fill in the rest of the
fields and do any further cleanup. Things that should be filled
in by the callback: */
-
struct exec *execp = exec_hdr (abfd);
obj_textsec (abfd)->size = N_TXTSIZE(*execp);
- /* data and bss are already filled in since they're so standard */
+ /* Data and bss are already filled in since they're so standard. */
- /* The virtual memory addresses of the sections */
+ /* The virtual memory addresses of the sections. */
obj_textsec (abfd)->vma = N_TXTADDR(*execp);
obj_datasec (abfd)->vma = N_DATADDR(*execp);
obj_bsssec (abfd)->vma = N_BSSADDR(*execp);
- /* The file offsets of the sections */
+ /* The file offsets of the sections. */
obj_textsec (abfd)->filepos = N_TXTOFF(*execp);
obj_datasec (abfd)->filepos = N_DATOFF(*execp);
- /* The file offsets of the relocation info */
+ /* The file offsets of the relocation info. */
obj_textsec (abfd)->rel_filepos = N_TRELOFF(*execp);
obj_datasec (abfd)->rel_filepos = N_DRELOFF(*execp);
Formats such as b.out, which have additional fields in the a.out
header, should cope with them in this callback as well. */
-#endif /* DOCUMENTATION */
+#endif /* DOCUMENTATION */
result = (*callback_to_real_object_p)(abfd);
return result;
}
-/*
-FUNCTION
- aout_@var{size}_mkobject
-
-SYNOPSIS
- bfd_boolean aout_@var{size}_mkobject, (bfd *abfd);
-
-DESCRIPTION
- Initialize BFD @var{abfd} for use with a.out files.
-*/
+/* Initialize ABFD for use with a.out files. */
bfd_boolean
-NAME(aout,mkobject) (abfd)
- bfd *abfd;
+NAME (aout, mkobject) (bfd *abfd)
{
struct aout_data_struct *rawptr;
bfd_size_type amt = sizeof (struct aout_data_struct);
bfd_set_error (bfd_error_system_call);
- /* Use an intermediate variable for clarity */
- rawptr = (struct aout_data_struct *) bfd_zalloc (abfd, amt);
+ /* Use an intermediate variable for clarity. */
+ rawptr = bfd_zalloc (abfd, amt);
if (rawptr == NULL)
return FALSE;
abfd->tdata.aout_data = rawptr;
exec_hdr (abfd) = &(rawptr->e);
- obj_textsec (abfd) = (asection *)NULL;
- obj_datasec (abfd) = (asection *)NULL;
- obj_bsssec (abfd) = (asection *)NULL;
+ obj_textsec (abfd) = NULL;
+ obj_datasec (abfd) = NULL;
+ obj_bsssec (abfd) = NULL;
return TRUE;
}
+/* Keep track of machine architecture and machine type for
+ a.out's. Return the <<machine_type>> for a particular
+ architecture and machine, or <<M_UNKNOWN>> if that exact architecture
+ and machine can't be represented in a.out format.
-/*
-FUNCTION
- aout_@var{size}_machine_type
-
-SYNOPSIS
- enum machine_type aout_@var{size}_machine_type
- (enum bfd_architecture arch,
- unsigned long machine));
-
-DESCRIPTION
- Keep track of machine architecture and machine type for
- a.out's. Return the <<machine_type>> for a particular
- architecture and machine, or <<M_UNKNOWN>> if that exact architecture
- and machine can't be represented in a.out format.
-
- If the architecture is understood, machine type 0 (default)
- is always understood.
-*/
+ If the architecture is understood, machine type 0 (default)
+ is always understood. */
enum machine_type
-NAME(aout,machine_type) (arch, machine, unknown)
- enum bfd_architecture arch;
- unsigned long machine;
- bfd_boolean *unknown;
+NAME (aout, machine_type) (enum bfd_architecture arch,
+ unsigned long machine,
+ bfd_boolean *unknown)
{
enum machine_type arch_flags;
case bfd_mach_mips3000:
arch_flags = M_MIPS1;
break;
- case bfd_mach_mips4000: /* mips3 */
+ case bfd_mach_mips4000: /* MIPS3 */
case bfd_mach_mips4400:
- case bfd_mach_mips8000: /* mips4 */
- case bfd_mach_mips6000: /* real mips2: */
+ case bfd_mach_mips8000: /* MIPS4 */
+ case bfd_mach_mips6000: /* Real MIPS2: */
arch_flags = M_MIPS2;
break;
default:
return arch_flags;
}
-
-/*
-FUNCTION
- aout_@var{size}_set_arch_mach
-
-SYNOPSIS
- bfd_boolean aout_@var{size}_set_arch_mach,
- (bfd *,
- enum bfd_architecture arch,
- unsigned long machine));
-
-DESCRIPTION
- Set the architecture and the machine of the BFD @var{abfd} to the
- values @var{arch} and @var{machine}. Verify that @var{abfd}'s format
- can support the architecture required.
-*/
+/* Set the architecture and the machine of the ABFD to the
+ values ARCH and MACHINE. Verify that @ABFD's format
+ can support the architecture required. */
bfd_boolean
-NAME(aout,set_arch_mach) (abfd, arch, machine)
- bfd *abfd;
- enum bfd_architecture arch;
- unsigned long machine;
+NAME (aout, set_arch_mach) (bfd *abfd,
+ enum bfd_architecture arch,
+ unsigned long machine)
{
if (! bfd_default_set_arch_mach (abfd, arch, machine))
return FALSE;
{
bfd_boolean unknown;
- NAME(aout,machine_type) (arch, machine, &unknown);
+ NAME (aout, machine_type) (arch, machine, &unknown);
if (unknown)
return FALSE;
}
}
static void
-adjust_o_magic (abfd, execp)
- bfd *abfd;
- struct internal_exec *execp;
+adjust_o_magic (bfd *abfd, struct internal_exec *execp)
{
file_ptr pos = adata (abfd).exec_bytes_size;
bfd_vma vma = 0;
}
static void
-adjust_z_magic (abfd, execp)
- bfd *abfd;
- struct internal_exec *execp;
+adjust_z_magic (bfd *abfd, struct internal_exec *execp)
{
bfd_size_type data_pad, text_pad;
file_ptr text_end;
}
static void
-adjust_n_magic (abfd, execp)
- bfd *abfd;
- struct internal_exec *execp;
+adjust_n_magic (bfd *abfd, struct internal_exec *execp)
{
file_ptr pos = adata(abfd).exec_bytes_size;
bfd_vma vma = 0;
}
bfd_boolean
-NAME(aout,adjust_sizes_and_vmas) (abfd, text_size, text_end)
- bfd *abfd;
- bfd_size_type *text_size;
- file_ptr * text_end ATTRIBUTE_UNUSED;
+NAME (aout, adjust_sizes_and_vmas) (bfd *abfd,
+ bfd_size_type *text_size,
+ file_ptr * text_end ATTRIBUTE_UNUSED)
{
struct internal_exec *execp = exec_hdr (abfd);
- if (! NAME(aout,make_sections) (abfd))
+ if (! NAME (aout, make_sections) (abfd))
return FALSE;
if (adata(abfd).magic != undecided_magic)
return TRUE;
}
-/*
-FUNCTION
- aout_@var{size}_new_section_hook
-
-SYNOPSIS
- bfd_boolean aout_@var{size}_new_section_hook,
- (bfd *abfd,
- asection *newsect));
+/* Called by the BFD in response to a bfd_make_section request. */
-DESCRIPTION
- Called by the BFD in response to a @code{bfd_make_section}
- request.
-*/
bfd_boolean
-NAME(aout,new_section_hook) (abfd, newsect)
- bfd *abfd;
- asection *newsect;
+NAME (aout, new_section_hook) (bfd *abfd, asection *newsect)
{
- /* align to double at least */
+ /* Align to double at least. */
newsect->alignment_power = bfd_get_arch_info(abfd)->section_align_power;
-
if (bfd_get_format (abfd) == bfd_object)
{
if (obj_textsec (abfd) == NULL
}
}
- /* We allow more than three sections internally */
+ /* We allow more than three sections internally. */
return TRUE;
}
bfd_boolean
-NAME(aout,set_section_contents) (abfd, section, location, offset, count)
- bfd *abfd;
- sec_ptr section;
- const PTR location;
- file_ptr offset;
- bfd_size_type count;
+NAME (aout, set_section_contents) (bfd *abfd,
+ sec_ptr section,
+ const void * location,
+ file_ptr offset,
+ bfd_size_type count)
{
file_ptr text_end;
bfd_size_type text_size;
if (! abfd->output_has_begun)
{
- if (! NAME(aout,adjust_sizes_and_vmas) (abfd, &text_size, &text_end))
+ if (! NAME (aout, adjust_sizes_and_vmas) (abfd, & text_size, & text_end))
return FALSE;
}
/* Read the external symbols from an a.out file. */
static bfd_boolean
-aout_get_external_symbols (abfd)
- bfd *abfd;
+aout_get_external_symbols (bfd *abfd)
{
- if (obj_aout_external_syms (abfd) == (struct external_nlist *) NULL)
+ if (obj_aout_external_syms (abfd) == NULL)
{
bfd_size_type count;
struct external_nlist *syms;
/* We allocate using malloc to make the values easy to free
later on. If we put them on the objalloc it might not be
possible to free them. */
- syms = (struct external_nlist *) bfd_malloc (count * EXTERNAL_NLIST_SIZE);
- if (syms == (struct external_nlist *) NULL && count != 0)
+ syms = bfd_malloc (count * EXTERNAL_NLIST_SIZE);
+ if (syms == NULL && count != 0)
return FALSE;
if (bfd_seek (abfd, obj_sym_filepos (abfd), SEEK_SET) != 0
/* Get the size of the strings. */
if (bfd_seek (abfd, obj_str_filepos (abfd), SEEK_SET) != 0
- || (bfd_bread ((PTR) string_chars, (bfd_size_type) BYTES_IN_LONG,
+ || (bfd_bread ((void *) string_chars, (bfd_size_type) BYTES_IN_LONG,
abfd) != BYTES_IN_LONG))
return FALSE;
stringsize = H_GET_32 (abfd, string_chars);
return FALSE;
strings = (char *) obj_aout_string_window (abfd).data;
#else
- strings = (char *) bfd_malloc (stringsize + 1);
+ strings = bfd_malloc (stringsize + 1);
if (strings == NULL)
return FALSE;
return FALSE;
}
#endif
-
/* Ensure that a zero index yields an empty string. */
strings[0] = '\0';
symbol->flags and symbol->section, and adjusting symbol->value. */
static bfd_boolean
-translate_from_native_sym_flags (abfd, cache_ptr)
- bfd *abfd;
- aout_symbol_type *cache_ptr;
+translate_from_native_sym_flags (bfd *abfd,
+ aout_symbol_type *cache_ptr)
{
flagword visible;
asection *sec;
/* This is a debugging symbol. */
-
cache_ptr->symbol.flags = BSF_DEBUGGING;
/* Work out the symbol section. */
/* Set the fields of SYM_POINTER according to CACHE_PTR. */
static bfd_boolean
-translate_to_native_sym_flags (abfd, cache_ptr, sym_pointer)
- bfd *abfd;
- asymbol *cache_ptr;
- struct external_nlist *sym_pointer;
+translate_to_native_sym_flags (bfd *abfd,
+ asymbol *cache_ptr,
+ struct external_nlist *sym_pointer)
{
bfd_vma value = cache_ptr->value;
asection *sec;
/* Native-level interface to symbols. */
asymbol *
-NAME(aout,make_empty_symbol) (abfd)
- bfd *abfd;
+NAME (aout, make_empty_symbol) (bfd *abfd)
{
bfd_size_type amt = sizeof (aout_symbol_type);
- aout_symbol_type *new = (aout_symbol_type *) bfd_zalloc (abfd, amt);
+ aout_symbol_type *new = bfd_zalloc (abfd, amt);
+
if (!new)
return NULL;
new->symbol.the_bfd = abfd;
/* Translate a set of internal symbols into external symbols. */
bfd_boolean
-NAME(aout,translate_symbol_table) (abfd, in, ext, count, str, strsize, dynamic)
- bfd *abfd;
- aout_symbol_type *in;
- struct external_nlist *ext;
- bfd_size_type count;
- char *str;
- bfd_size_type strsize;
- bfd_boolean dynamic;
+NAME (aout, translate_symbol_table) (bfd *abfd,
+ aout_symbol_type *in,
+ struct external_nlist *ext,
+ bfd_size_type count,
+ char *str,
+ bfd_size_type strsize,
+ bfd_boolean dynamic)
{
struct external_nlist *ext_end;
return FALSE;
in->symbol.value = GET_SWORD (abfd, ext->e_value);
- /* TODO: is 0 a safe value here? */
+ /* TODO: is 0 a safe value here? */
in->desc = 0;
in->other = 0;
in->type = H_GET_8 (abfd, ext->e_type);
/* We read the symbols into a buffer, which is discarded when this
function exits. We read the strings into a buffer large enough to
- hold them all plus all the cached symbol entries. */
+ hold them all plus all the cached symbol entries. */
bfd_boolean
-NAME(aout,slurp_symbol_table) (abfd)
- bfd *abfd;
+NAME (aout, slurp_symbol_table) (bfd *abfd)
{
struct external_nlist *old_external_syms;
aout_symbol_type *cached;
bfd_size_type cached_size;
- /* If there's no work to be done, don't do any */
- if (obj_aout_symbols (abfd) != (aout_symbol_type *) NULL)
+ /* If there's no work to be done, don't do any. */
+ if (obj_aout_symbols (abfd) != NULL)
return TRUE;
old_external_syms = obj_aout_external_syms (abfd);
cached_size = obj_aout_external_sym_count (abfd);
cached_size *= sizeof (aout_symbol_type);
- cached = (aout_symbol_type *) bfd_zmalloc (cached_size);
+ cached = bfd_zmalloc (cached_size);
if (cached == NULL && cached_size != 0)
return FALSE;
/* Convert from external symbol information to internal. */
- if (! (NAME(aout,translate_symbol_table)
+ if (! (NAME (aout, translate_symbol_table)
(abfd, cached,
obj_aout_external_syms (abfd),
obj_aout_external_sym_count (abfd),
want the external symbol information, so if it was allocated
because of our call to aout_get_external_symbols, we free it up
right away to save space. */
- if (old_external_syms == (struct external_nlist *) NULL
- && obj_aout_external_syms (abfd) != (struct external_nlist *) NULL)
+ if (old_external_syms == NULL
+ && obj_aout_external_syms (abfd) != NULL)
{
#ifdef USE_MMAP
bfd_free_window (&obj_aout_sym_window (abfd));
This hash table code breaks dbx on SunOS 4.1.3, so we don't do it
if BFD_TRADITIONAL_FORMAT is set. */
-static bfd_size_type add_to_stringtab
- PARAMS ((bfd *, struct bfd_strtab_hash *, const char *, bfd_boolean));
-static bfd_boolean emit_stringtab PARAMS ((bfd *, struct bfd_strtab_hash *));
-
/* Get the index of a string in a strtab, adding it if it is not
already present. */
static INLINE bfd_size_type
-add_to_stringtab (abfd, tab, str, copy)
- bfd *abfd;
- struct bfd_strtab_hash *tab;
- const char *str;
- bfd_boolean copy;
+add_to_stringtab (bfd *abfd,
+ struct bfd_strtab_hash *tab,
+ const char *str,
+ bfd_boolean copy)
{
bfd_boolean hash;
bfd_size_type index;
index = _bfd_stringtab_add (tab, str, hash, copy);
if (index != (bfd_size_type) -1)
- {
- /* Add BYTES_IN_LONG to the return value to account for the
- space taken up by the string table size. */
- index += BYTES_IN_LONG;
- }
+ /* Add BYTES_IN_LONG to the return value to account for the
+ space taken up by the string table size. */
+ index += BYTES_IN_LONG;
return index;
}
file. */
static bfd_boolean
-emit_stringtab (abfd, tab)
- register bfd *abfd;
- struct bfd_strtab_hash *tab;
+emit_stringtab (bfd *abfd, struct bfd_strtab_hash *tab)
{
bfd_byte buffer[BYTES_IN_LONG];
/* The string table starts with the size. */
H_PUT_32 (abfd, _bfd_stringtab_size (tab) + BYTES_IN_LONG, buffer);
- if (bfd_bwrite ((PTR) buffer, (bfd_size_type) BYTES_IN_LONG, abfd)
+ if (bfd_bwrite ((void *) buffer, (bfd_size_type) BYTES_IN_LONG, abfd)
!= BYTES_IN_LONG)
return FALSE;
}
\f
bfd_boolean
-NAME(aout,write_syms) (abfd)
- bfd *abfd;
+NAME (aout, write_syms) (bfd *abfd)
{
unsigned int count ;
asymbol **generic = bfd_get_outsymbols (abfd);
H_PUT_8 (abfd, 0, nsp.e_ovly);
- if (bfd_bwrite ((PTR)&nsp, (bfd_size_type) EXTERNAL_NLIST_SIZE, abfd)
+ if (bfd_bwrite ((void *)&nsp, (bfd_size_type) EXTERNAL_NLIST_SIZE, abfd)
!= EXTERNAL_NLIST_SIZE)
goto error_return;
\f
long
-NAME(aout,canonicalize_symtab) (abfd, location)
- bfd *abfd;
- asymbol **location;
+NAME (aout, canonicalize_symtab) (bfd *abfd, asymbol **location)
{
- unsigned int counter = 0;
- aout_symbol_type *symbase;
+ unsigned int counter = 0;
+ aout_symbol_type *symbase;
- if (!NAME(aout,slurp_symbol_table)(abfd))
- return -1;
+ if (!NAME (aout, slurp_symbol_table) (abfd))
+ return -1;
- for (symbase = obj_aout_symbols(abfd); counter++ < bfd_get_symcount (abfd);)
- *(location++) = (asymbol *)( symbase++);
- *location++ =0;
- return bfd_get_symcount (abfd);
+ for (symbase = obj_aout_symbols (abfd); counter++ < bfd_get_symcount (abfd);)
+ *(location++) = (asymbol *)(symbase++);
+ *location++ =0;
+ return bfd_get_symcount (abfd);
}
\f
-/* Standard reloc stuff */
+/* Output extended relocation information to a file in target byte order. */
-/* Extended stuff */
-/* Output extended relocation information to a file in target byte order. */
-
-void
-pdp11_aout_swap_reloc_out (abfd, g, natptr)
- bfd *abfd;
- arelent *g;
- bfd_byte *natptr;
+static void
+pdp11_aout_swap_reloc_out (bfd *abfd, arelent *g, bfd_byte *natptr)
{
int r_index;
int r_pcrel;
} \
}
-void
-pdp11_aout_swap_reloc_in (abfd, bytes, cache_ptr, offset,
- symbols, symcount)
- bfd *abfd;
- bfd_byte *bytes;
- arelent *cache_ptr;
- bfd_size_type offset;
- asymbol **symbols;
- bfd_size_type symcount;
+static void
+pdp11_aout_swap_reloc_in (bfd * abfd,
+ bfd_byte * bytes,
+ arelent * cache_ptr,
+ bfd_size_type offset,
+ asymbol ** symbols,
+ bfd_size_type symcount)
{
struct aoutdata *su = &(abfd->tdata.aout_data->a);
unsigned int r_index;
int r_extern;
int r_pcrel;
- reloc_entry = GET_WORD (abfd, (PTR)bytes);
+ reloc_entry = GET_WORD (abfd, (void *) bytes);
r_pcrel = reloc_entry & RELFLG;
/* Read and swap the relocs for a section. */
bfd_boolean
-NAME(aout,slurp_reloc_table) (abfd, asect, symbols)
- bfd *abfd;
- sec_ptr asect;
- asymbol **symbols;
+NAME (aout, slurp_reloc_table) (bfd *abfd, sec_ptr asect, asymbol **symbols)
{
bfd_byte *rptr;
bfd_size_type count;
bfd_size_type reloc_size;
- PTR relocs;
+ void * relocs;
arelent *reloc_cache;
size_t each_size;
unsigned int counter = 0;
count = reloc_size / each_size;
- /* Count the number of NON-ZERO relocs, this is the count we want. */
+ /* Count the number of NON-ZERO relocs, this is the count we want. */
{
unsigned int real_count = 0;
count = real_count;
}
- reloc_cache = (arelent *) bfd_zmalloc (count * sizeof (arelent));
+ reloc_cache = bfd_zmalloc (count * sizeof (arelent));
if (reloc_cache == NULL && count != 0)
return FALSE;
counter < count;
counter++, rptr += RELOC_SIZE, cache_ptr++)
{
- while (GET_WORD (abfd, (PTR)rptr) == 0)
+ while (GET_WORD (abfd, (void *) rptr) == 0)
{
rptr += RELOC_SIZE;
if ((char *) rptr >= (char *) relocs + reloc_size)
}
done:
/* Just in case, if rptr >= relocs + reloc_size should happen
- too early. */
+ too early. */
BFD_ASSERT (counter == count);
free (relocs);
/* Write out a relocation section into an object file. */
bfd_boolean
-NAME(aout,squirt_out_relocs) (abfd, section)
- bfd *abfd;
- asection *section;
+NAME (aout, squirt_out_relocs) (bfd *abfd, asection *section)
{
arelent **generic;
unsigned char *native;
bfd_size_type natsize;
natsize = section->size;
- native = (unsigned char *) bfd_zalloc (abfd, natsize);
+ native = bfd_zalloc (abfd, natsize);
if (!native)
return FALSE;
}
}
- if (bfd_bwrite ((PTR) native, natsize, abfd) != natsize)
+ if (bfd_bwrite ((void *) native, natsize, abfd) != natsize)
{
bfd_release (abfd, native);
return FALSE;
return TRUE;
}
-/* This is stupid. This function should be a boolean predicate */
+/* This is stupid. This function should be a boolean predicate. */
+
long
-NAME(aout,canonicalize_reloc) (abfd, section, relptr, symbols)
- bfd *abfd;
- sec_ptr section;
- arelent **relptr;
- asymbol **symbols;
+NAME (aout, canonicalize_reloc) (bfd *abfd,
+ sec_ptr section,
+ arelent **relptr,
+ asymbol **symbols)
{
arelent *tblptr = section->relocation;
unsigned int count;
return 0;
}
- if (!(tblptr || NAME(aout,slurp_reloc_table)(abfd, section, symbols)))
+ if (!(tblptr || NAME (aout, slurp_reloc_table)(abfd, section, symbols)))
return -1;
if (section->flags & SEC_CONSTRUCTOR)
}
long
-NAME(aout,get_reloc_upper_bound) (abfd, asect)
- bfd *abfd;
- sec_ptr asect;
+NAME (aout, get_reloc_upper_bound) (bfd *abfd, sec_ptr asect)
{
if (bfd_get_format (abfd) != bfd_object)
{
}
if (asect->flags & SEC_CONSTRUCTOR)
- return (sizeof (arelent *) * (asect->reloc_count+1));
+ return (sizeof (arelent *) * (asect->reloc_count + 1));
if (asect == obj_datasec (abfd))
return (sizeof (arelent *)
- * ((exec_hdr(abfd)->a_drsize / obj_reloc_entry_size (abfd))
+ * ((exec_hdr (abfd)->a_drsize / obj_reloc_entry_size (abfd))
+ 1));
if (asect == obj_textsec (abfd))
return (sizeof (arelent *)
- * ((exec_hdr(abfd)->a_trsize / obj_reloc_entry_size (abfd))
+ * ((exec_hdr (abfd)->a_trsize / obj_reloc_entry_size (abfd))
+ 1));
/* TODO: why are there two if statements for obj_bsssec()? */
\f
long
-NAME(aout,get_symtab_upper_bound) (abfd)
- bfd *abfd;
+NAME (aout, get_symtab_upper_bound) (bfd *abfd)
{
- if (!NAME(aout,slurp_symbol_table)(abfd))
+ if (!NAME (aout, slurp_symbol_table) (abfd))
return -1;
return (bfd_get_symcount (abfd) + 1) * (sizeof (aout_symbol_type *));
}
alent *
-NAME(aout,get_lineno) (abfd, symbol)
- bfd * abfd ATTRIBUTE_UNUSED;
- asymbol * symbol ATTRIBUTE_UNUSED;
+NAME (aout, get_lineno) (bfd * abfd ATTRIBUTE_UNUSED,
+ asymbol * symbol ATTRIBUTE_UNUSED)
{
- return (alent *)NULL;
+ return NULL;
}
void
-NAME(aout,get_symbol_info) (abfd, symbol, ret)
- bfd * abfd ATTRIBUTE_UNUSED;
- asymbol *symbol;
- symbol_info *ret;
+NAME (aout, get_symbol_info) (bfd * abfd ATTRIBUTE_UNUSED,
+ asymbol *symbol,
+ symbol_info *ret)
{
bfd_symbol_info (symbol, ret);
stab_name = buf;
}
ret->type = '-';
- ret->stab_type = type_code;
- ret->stab_other = (unsigned)(aout_symbol(symbol)->other & 0xff);
- ret->stab_desc = (unsigned)(aout_symbol(symbol)->desc & 0xffff);
- ret->stab_name = stab_name;
+ ret->stab_type = type_code;
+ ret->stab_other = (unsigned) (aout_symbol(symbol)->other & 0xff);
+ ret->stab_desc = (unsigned) (aout_symbol(symbol)->desc & 0xffff);
+ ret->stab_name = stab_name;
}
}
void
-NAME(aout,print_symbol) (abfd, afile, symbol, how)
- bfd * abfd;
- PTR afile;
- asymbol *symbol;
- bfd_print_symbol_type how;
+NAME (aout, print_symbol) (bfd * abfd,
+ void * afile,
+ asymbol *symbol,
+ bfd_print_symbol_type how)
{
- FILE *file = (FILE *)afile;
+ FILE *file = (FILE *) afile;
switch (how)
{
fprintf(file,"%s", symbol->name);
break;
case bfd_print_symbol_more:
- fprintf(file,"%4x %2x %2x",(unsigned)(aout_symbol(symbol)->desc & 0xffff),
- (unsigned)(aout_symbol(symbol)->other & 0xff),
- (unsigned)(aout_symbol(symbol)->type));
+ fprintf(file,"%4x %2x %2x",
+ (unsigned) (aout_symbol (symbol)->desc & 0xffff),
+ (unsigned) (aout_symbol (symbol)->other & 0xff),
+ (unsigned) (aout_symbol (symbol)->type));
break;
case bfd_print_symbol_all:
{
const char *section_name = symbol->section->name;
- bfd_print_symbol_vandf (abfd, (PTR)file, symbol);
+ bfd_print_symbol_vandf (abfd, (void *) file, symbol);
fprintf (file," %-5s %04x %02x %02x",
section_name,
- (unsigned)(aout_symbol(symbol)->desc & 0xffff),
- (unsigned)(aout_symbol(symbol)->other & 0xff),
- (unsigned)(aout_symbol(symbol)->type & 0xff));
+ (unsigned) (aout_symbol (symbol)->desc & 0xffff),
+ (unsigned) (aout_symbol (symbol)->other & 0xff),
+ (unsigned) (aout_symbol (symbol)->type & 0xff));
if (symbol->name)
fprintf(file," %s", symbol->name);
}
BFD asymbol structures. */
long
-NAME(aout,read_minisymbols) (abfd, dynamic, minisymsp, sizep)
- bfd *abfd;
- bfd_boolean dynamic;
- PTR *minisymsp;
- unsigned int *sizep;
+NAME (aout, read_minisymbols) (bfd *abfd,
+ bfd_boolean dynamic,
+ void * *minisymsp,
+ unsigned int *sizep)
{
if (dynamic)
- {
- /* We could handle the dynamic symbols here as well, but it's
- easier to hand them off. */
- return _bfd_generic_read_minisymbols (abfd, dynamic, minisymsp, sizep);
- }
+ /* We could handle the dynamic symbols here as well, but it's
+ easier to hand them off. */
+ return _bfd_generic_read_minisymbols (abfd, dynamic, minisymsp, sizep);
if (! aout_get_external_symbols (abfd))
return -1;
if (obj_aout_external_sym_count (abfd) < MINISYM_THRESHOLD)
return _bfd_generic_read_minisymbols (abfd, dynamic, minisymsp, sizep);
- *minisymsp = (PTR) obj_aout_external_syms (abfd);
+ *minisymsp = (void *) obj_aout_external_syms (abfd);
/* By passing the external symbols back from this routine, we are
giving up control over the memory block. Clear
by bfd_make_empty_symbol, which we fill in here. */
asymbol *
-NAME(aout,minisymbol_to_symbol) (abfd, dynamic, minisym, sym)
- bfd *abfd;
- bfd_boolean dynamic;
- const PTR minisym;
- asymbol *sym;
+NAME (aout, minisymbol_to_symbol) (bfd *abfd,
+ bfd_boolean dynamic,
+ const void * minisym,
+ asymbol *sym)
{
if (dynamic
|| obj_aout_external_sym_count (abfd) < MINISYM_THRESHOLD)
memset (sym, 0, sizeof (aout_symbol_type));
/* We call translate_symbol_table to translate a single symbol. */
- if (! (NAME(aout,translate_symbol_table)
+ if (! (NAME (aout, translate_symbol_table)
(abfd,
(aout_symbol_type *) sym,
(struct external_nlist *) minisym,
return sym;
}
-/*
- provided a BFD, a section and an offset into the section, calculate
- and return the name of the source file and the line nearest to the
- wanted location.
-*/
+/* Provided a BFD, a section and an offset into the section, calculate
+ and return the name of the source file and the line nearest to the
+ wanted location. */
bfd_boolean
-NAME(aout,find_nearest_line)
- (abfd, section, symbols, offset, filename_ptr, functionname_ptr, line_ptr)
- bfd *abfd;
- asection *section;
- asymbol **symbols;
- bfd_vma offset;
- const char **filename_ptr;
- const char **functionname_ptr;
- unsigned int *line_ptr;
+NAME (aout, find_nearest_line) (bfd *abfd,
+ asection *section,
+ asymbol **symbols,
+ bfd_vma offset,
+ const char **filename_ptr,
+ const char **functionname_ptr,
+ unsigned int *line_ptr)
{
- /* Run down the file looking for the filename, function and linenumber */
+ /* Run down the file looking for the filename, function and linenumber. */
asymbol **p;
const char *directory_name = NULL;
const char *main_file_name = NULL;
const char *current_file_name = NULL;
- const char *line_file_name = NULL; /* Value of current_file_name at line number. */
+ const char *line_file_name = NULL; /* Value of current_file_name at line number. */
bfd_vma low_line_vma = 0;
bfd_vma low_func_vma = 0;
asymbol *func = 0;
*functionname_ptr = 0;
*line_ptr = 0;
- if (symbols != (asymbol **)NULL)
+ if (symbols != NULL)
{
for (p = symbols; *p; p++)
{
}
main_file_name = current_file_name = q->symbol.name;
- /* Look ahead to next symbol to check if that too is an N_SO. */
+ /* Look ahead to next symbol to check if that too is an N_SO. */
p++;
if (*p == NULL)
break;
q = (aout_symbol_type *)(*p);
- if (q->type != (int)N_SO)
+ if (q->type != (int) N_SO)
goto next;
- /* Found a second N_SO First is directory; second is filename. */
+ /* Found a second N_SO First is directory; second is filename. */
directory_name = current_file_name;
main_file_name = current_file_name = q->symbol.name;
if (obj_textsec(abfd) != section)
case N_FUN:
{
- /* We'll keep this if it is nearer than the one we have already */
+ /* We'll keep this if it is nearer than the one we have already. */
if (q->symbol.value >= low_func_vma &&
q->symbol.value <= offset)
{
low_func_vma = q->symbol.value;
- func = (asymbol *)q;
+ func = (asymbol *) q;
}
else if (q->symbol.value > offset)
goto done;
adata (abfd).line_buf = buf = NULL;
else
{
- buf = (char *) bfd_malloc ((bfd_size_type) filelen + funclen + 3);
+ buf = bfd_malloc ((bfd_size_type) filelen + funclen + 3);
adata (abfd).line_buf = buf;
if (buf == NULL)
return FALSE;
}
int
-NAME(aout,sizeof_headers) (abfd, execable)
- bfd *abfd;
- bfd_boolean execable ATTRIBUTE_UNUSED;
+NAME (aout, sizeof_headers) (bfd *abfd, bfd_boolean execable ATTRIBUTE_UNUSED)
{
- return adata(abfd).exec_bytes_size;
+ return adata (abfd).exec_bytes_size;
}
/* Free all information we have cached for this BFD. We can always
read it again later if we need it. */
bfd_boolean
-NAME(aout,bfd_free_cached_info) (abfd)
- bfd *abfd;
+NAME (aout, bfd_free_cached_info) (bfd *abfd)
{
asection *o;
#define BFCI_FREE(x) if (x != NULL) { free (x); x = NULL; }
BFCI_FREE (obj_aout_symbols (abfd));
+
#ifdef USE_MMAP
obj_aout_external_syms (abfd) = 0;
bfd_free_window (&obj_aout_sym_window (abfd));
BFCI_FREE (obj_aout_external_syms (abfd));
BFCI_FREE (obj_aout_external_strings (abfd));
#endif
- for (o = abfd->sections; o != (asection *) NULL; o = o->next)
+ for (o = abfd->sections; o != NULL; o = o->next)
BFCI_FREE (o->relocation);
#undef BFCI_FREE
return TRUE;
}
\f
-/* a.out link code. */
-
-static bfd_boolean aout_link_add_object_symbols
- PARAMS ((bfd *, struct bfd_link_info *));
-static bfd_boolean aout_link_check_archive_element
- PARAMS ((bfd *, struct bfd_link_info *, bfd_boolean *));
-static bfd_boolean aout_link_free_symbols PARAMS ((bfd *));
-static bfd_boolean aout_link_check_ar_symbols
- PARAMS ((bfd *, struct bfd_link_info *, bfd_boolean *pneeded));
-static bfd_boolean aout_link_add_symbols
- PARAMS ((bfd *, struct bfd_link_info *));
-
/* Routine to create an entry in an a.out link hash table. */
struct bfd_hash_entry *
-NAME(aout,link_hash_newfunc) (entry, table, string)
- struct bfd_hash_entry *entry;
- struct bfd_hash_table *table;
- const char *string;
+NAME (aout, link_hash_newfunc) (struct bfd_hash_entry *entry,
+ struct bfd_hash_table *table,
+ const char *string)
{
struct aout_link_hash_entry *ret = (struct aout_link_hash_entry *) entry;
/* Allocate the structure if it has not already been allocated by a
subclass. */
- if (ret == (struct aout_link_hash_entry *) NULL)
- ret = ((struct aout_link_hash_entry *)
- bfd_hash_allocate (table, sizeof (struct aout_link_hash_entry)));
- if (ret == (struct aout_link_hash_entry *) NULL)
- return (struct bfd_hash_entry *) ret;
+ if (ret == NULL)
+ ret = bfd_hash_allocate (table, sizeof (* ret));
+ if (ret == NULL)
+ return NULL;
/* Call the allocation method of the superclass. */
- ret = ((struct aout_link_hash_entry *)
- _bfd_link_hash_newfunc ((struct bfd_hash_entry *) ret,
- table, string));
+ ret = (struct aout_link_hash_entry *)
+ _bfd_link_hash_newfunc ((struct bfd_hash_entry *) ret, table, string);
if (ret)
{
/* Set local fields. */
/* Initialize an a.out link hash table. */
bfd_boolean
-NAME(aout,link_hash_table_init) (table, abfd, newfunc)
- struct aout_link_hash_table *table;
- bfd *abfd;
- struct bfd_hash_entry *(*newfunc) PARAMS ((struct bfd_hash_entry *,
- struct bfd_hash_table *,
- const char *));
+NAME (aout, link_hash_table_init) (struct aout_link_hash_table *table,
+ bfd *abfd,
+ struct bfd_hash_entry *(*newfunc) (struct bfd_hash_entry *,
+ struct bfd_hash_table *,
+ const char *))
{
return _bfd_link_hash_table_init (&table->root, abfd, newfunc);
}
/* Create an a.out link hash table. */
struct bfd_link_hash_table *
-NAME(aout,link_hash_table_create) (abfd)
- bfd *abfd;
+NAME (aout, link_hash_table_create) (bfd *abfd)
{
struct aout_link_hash_table *ret;
bfd_size_type amt = sizeof (struct aout_link_hash_table);
- ret = ((struct aout_link_hash_table *) bfd_alloc (abfd, amt));
+ ret = bfd_alloc (abfd, amt);
if (ret == NULL)
- return (struct bfd_link_hash_table *) NULL;
- if (! NAME(aout,link_hash_table_init) (ret, abfd,
- NAME(aout,link_hash_newfunc)))
+ return NULL;
+ if (! NAME (aout, link_hash_table_init) (ret, abfd,
+ NAME (aout, link_hash_newfunc)))
{
free (ret);
- return (struct bfd_link_hash_table *) NULL;
+ return NULL;
}
return &ret->root;
}
+/* Free up the internal symbols read from an a.out file. */
+
+static bfd_boolean
+aout_link_free_symbols (bfd *abfd)
+{
+ if (obj_aout_external_syms (abfd) != NULL)
+ {
+#ifdef USE_MMAP
+ bfd_free_window (&obj_aout_sym_window (abfd));
+#else
+ free ((void *) obj_aout_external_syms (abfd));
+#endif
+ obj_aout_external_syms (abfd) = NULL;
+ }
+
+ if (obj_aout_external_strings (abfd) != NULL)
+ {
+#ifdef USE_MMAP
+ bfd_free_window (&obj_aout_string_window (abfd));
+#else
+ free ((void *) obj_aout_external_strings (abfd));
+#endif
+ obj_aout_external_strings (abfd) = NULL;
+ }
+ return TRUE;
+}
+
/* Given an a.out BFD, add symbols to the global hash table as
appropriate. */
bfd_boolean
-NAME(aout,link_add_symbols) (abfd, info)
- bfd *abfd;
- struct bfd_link_info *info;
+NAME (aout, link_add_symbols) (bfd *abfd, struct bfd_link_info *info)
{
switch (bfd_get_format (abfd))
{
/* Add symbols from an a.out object file. */
static bfd_boolean
-aout_link_add_object_symbols (abfd, info)
- bfd *abfd;
- struct bfd_link_info *info;
+aout_link_add_object_symbols (bfd *abfd, struct bfd_link_info *info)
{
if (! aout_get_external_symbols (abfd))
return FALSE;
return TRUE;
}
-/* Check a single archive element to see if we need to include it in
- the link. *PNEEDED is set according to whether this element is
- needed in the link or not. This is called from
- _bfd_generic_link_add_archive_symbols. */
-
-static bfd_boolean
-aout_link_check_archive_element (abfd, info, pneeded)
- bfd *abfd;
- struct bfd_link_info *info;
- bfd_boolean *pneeded;
-{
- if (! aout_get_external_symbols (abfd))
- return FALSE;
-
- if (! aout_link_check_ar_symbols (abfd, info, pneeded))
- return FALSE;
-
- if (*pneeded)
- {
- if (! aout_link_add_symbols (abfd, info))
- return FALSE;
- }
-
- if (! info->keep_memory || ! *pneeded)
- {
- if (! aout_link_free_symbols (abfd))
- return FALSE;
- }
-
- return TRUE;
-}
-
-/* Free up the internal symbols read from an a.out file. */
-
-static bfd_boolean
-aout_link_free_symbols (abfd)
- bfd *abfd;
-{
- if (obj_aout_external_syms (abfd) != (struct external_nlist *) NULL)
- {
-#ifdef USE_MMAP
- bfd_free_window (&obj_aout_sym_window (abfd));
-#else
- free ((PTR) obj_aout_external_syms (abfd));
-#endif
- obj_aout_external_syms (abfd) = (struct external_nlist *) NULL;
- }
- if (obj_aout_external_strings (abfd) != (char *) NULL)
- {
-#ifdef USE_MMAP
- bfd_free_window (&obj_aout_string_window (abfd));
-#else
- free ((PTR) obj_aout_external_strings (abfd));
-#endif
- obj_aout_external_strings (abfd) = (char *) NULL;
- }
- return TRUE;
-}
-
/* Look through the internal symbols to see if this object file should
be included in the link. We should include this object file if it
defines any symbols which are currently undefined. If this object
(unless there is some other reason to include it). */
static bfd_boolean
-aout_link_check_ar_symbols (abfd, info, pneeded)
- bfd *abfd;
- struct bfd_link_info *info;
- bfd_boolean *pneeded;
+aout_link_check_ar_symbols (bfd *abfd,
+ struct bfd_link_info *info,
+ bfd_boolean *pneeded)
{
- register struct external_nlist *p;
+ struct external_nlist *p;
struct external_nlist *pend;
char *strings;
/* We are only interested in symbols that are currently
undefined or common. */
- if (h == (struct bfd_link_hash_entry *) NULL
+ if (h == NULL
|| (h->type != bfd_link_hash_undefined
&& h->type != bfd_link_hash_common))
continue;
unsigned int power;
symbfd = h->u.undef.abfd;
- if (symbfd == (bfd *) NULL)
+ if (symbfd == NULL)
{
/* This symbol was created as undefined from
outside BFD. We assume that we should link
in the object file. This is done for the -u
option in the linker. */
- if (! (*info->callbacks->add_archive_element) (info,
- abfd,
- name))
+ if (! (*info->callbacks->add_archive_element)
+ (info, abfd, name))
return FALSE;
*pneeded = TRUE;
return TRUE;
/* Turn the current link symbol into a common
symbol. It is already on the undefs list. */
h->type = bfd_link_hash_common;
- h->u.c.p = ((struct bfd_link_hash_common_entry *)
- bfd_hash_allocate (&info->hash->table,
- sizeof (struct bfd_link_hash_common_entry)));
+ h->u.c.p = bfd_hash_allocate (&info->hash->table,
+ sizeof (struct bfd_link_hash_common_entry));
if (h->u.c.p == NULL)
return FALSE;
return TRUE;
}
+/* Check a single archive element to see if we need to include it in
+ the link. *PNEEDED is set according to whether this element is
+ needed in the link or not. This is called from
+ _bfd_generic_link_add_archive_symbols. */
+
+static bfd_boolean
+aout_link_check_archive_element (bfd *abfd,
+ struct bfd_link_info *info,
+ bfd_boolean *pneeded)
+{
+ if (! aout_get_external_symbols (abfd))
+ return FALSE;
+
+ if (! aout_link_check_ar_symbols (abfd, info, pneeded))
+ return FALSE;
+
+ if (*pneeded)
+ {
+ if (! aout_link_add_symbols (abfd, info))
+ return FALSE;
+ }
+
+ if (! info->keep_memory || ! *pneeded)
+ {
+ if (! aout_link_free_symbols (abfd))
+ return FALSE;
+ }
+
+ return TRUE;
+}
+
/* Add all symbols from an object file to the hash table. */
static bfd_boolean
-aout_link_add_symbols (abfd, info)
- bfd *abfd;
- struct bfd_link_info *info;
+aout_link_add_symbols (bfd *abfd, struct bfd_link_info *info)
{
bfd_boolean (*add_one_symbol)
- PARAMS ((struct bfd_link_info *, bfd *, const char *, flagword, asection *,
- bfd_vma, const char *, bfd_boolean, bfd_boolean,
- struct bfd_link_hash_entry **));
+ (struct bfd_link_info *, bfd *, const char *, flagword, asection *,
+ bfd_vma, const char *, bfd_boolean, bfd_boolean,
+ struct bfd_link_hash_entry **);
struct external_nlist *syms;
bfd_size_type sym_count;
char *strings;
bfd_boolean copy;
struct aout_link_hash_entry **sym_hash;
- register struct external_nlist *p;
+ struct external_nlist *p;
struct external_nlist *pend;
syms = obj_aout_external_syms (abfd);
to particular symbols. We could just look them up in the hash
table, but keeping the list is more efficient. Perhaps this
should be conditional on info->keep_memory. */
- sym_hash = ((struct aout_link_hash_entry **)
- bfd_alloc (abfd,
- sym_count * sizeof (struct aout_link_hash_entry *)));
+ sym_hash = bfd_alloc (abfd,
+ sym_count * sizeof (struct aout_link_hash_entry *));
if (sym_hash == NULL && sym_count != 0)
return FALSE;
obj_aout_sym_hashes (abfd) = sym_hash;
return TRUE;
}
\f
-/* A hash table used for header files with N_BINCL entries. */
-
-struct aout_link_includes_table
-{
- struct bfd_hash_table root;
-};
-
-/* A linked list of totals that we have found for a particular header
- file. */
-
-struct aout_link_includes_totals
-{
- struct aout_link_includes_totals *next;
- bfd_vma total;
-};
-
-/* An entry in the header file hash table. */
-
-struct aout_link_includes_entry
-{
- struct bfd_hash_entry root;
- /* List of totals we have found for this file. */
- struct aout_link_includes_totals *totals;
-};
-
-/* Look up an entry in an the header file hash table. */
+/* Look up an entry in an the header file hash table. */
#define aout_link_includes_lookup(table, string, create, copy) \
((struct aout_link_includes_entry *) \
bfd_hash_lookup (&(table)->root, (string), (create), (copy)))
-/* During the final link step we need to pass around a bunch of
- information, so we do it in an instance of this structure. */
-
-struct aout_final_link_info
-{
- /* General link information. */
- struct bfd_link_info *info;
- /* Output bfd. */
- bfd *output_bfd;
- /* Reloc file positions. */
- file_ptr treloff, dreloff;
- /* File position of symbols. */
- file_ptr symoff;
- /* String table. */
- struct bfd_strtab_hash *strtab;
- /* Header file hash table. */
- struct aout_link_includes_table includes;
- /* A buffer large enough to hold the contents of any section. */
- bfd_byte *contents;
- /* A buffer large enough to hold the relocs of any section. */
- PTR relocs;
- /* A buffer large enough to hold the symbol map of any input BFD. */
- int *symbol_map;
- /* A buffer large enough to hold output symbols of any input BFD. */
- struct external_nlist *output_syms;
-};
-
-static struct bfd_hash_entry *aout_link_includes_newfunc
- PARAMS ((struct bfd_hash_entry *, struct bfd_hash_table *, const char *));
-static bfd_boolean aout_link_input_bfd
- PARAMS ((struct aout_final_link_info *, bfd *input_bfd));
-static bfd_boolean aout_link_write_symbols
- PARAMS ((struct aout_final_link_info *, bfd *input_bfd));
-static bfd_boolean aout_link_write_other_symbol
- PARAMS ((struct aout_link_hash_entry *, PTR));
-static bfd_boolean aout_link_input_section
- PARAMS ((struct aout_final_link_info *, bfd *input_bfd,
- asection *input_section, file_ptr *reloff_ptr,
- bfd_size_type rel_size));
-static INLINE asection *aout_reloc_type_to_section
- PARAMS ((bfd *, int));
-static bfd_boolean aout_link_reloc_link_order
- PARAMS ((struct aout_final_link_info *, asection *,
- struct bfd_link_order *));
-static bfd_boolean pdp11_aout_link_input_section
- PARAMS ((struct aout_final_link_info *finfo,
- bfd *input_bfd,
- asection *input_section,
- bfd_byte *relocs,
- bfd_size_type rel_size,
- bfd_byte *contents));
-
/* The function to create a new entry in the header file hash table. */
static struct bfd_hash_entry *
-aout_link_includes_newfunc (entry, table, string)
- struct bfd_hash_entry *entry;
- struct bfd_hash_table *table;
- const char *string;
+aout_link_includes_newfunc (struct bfd_hash_entry *entry,
+ struct bfd_hash_table *table,
+ const char *string)
{
- struct aout_link_includes_entry *ret =
+ struct aout_link_includes_entry * ret =
(struct aout_link_includes_entry *) entry;
/* Allocate the structure if it has not already been allocated by a
subclass. */
- if (ret == (struct aout_link_includes_entry *) NULL)
- ret = ((struct aout_link_includes_entry *)
- bfd_hash_allocate (table,
- sizeof (struct aout_link_includes_entry)));
- if (ret == (struct aout_link_includes_entry *) NULL)
- return (struct bfd_hash_entry *) ret;
+ if (ret == NULL)
+ ret = bfd_hash_allocate (table,
+ sizeof (struct aout_link_includes_entry));
+ if (ret == NULL)
+ return NULL;
/* Call the allocation method of the superclass. */
ret = ((struct aout_link_includes_entry *)
bfd_hash_newfunc ((struct bfd_hash_entry *) ret, table, string));
if (ret)
- {
- /* Set local fields. */
- ret->totals = NULL;
- }
+ /* Set local fields. */
+ ret->totals = NULL;
return (struct bfd_hash_entry *) ret;
}
-/* Do the final link step. This is called on the output BFD. The
- INFO structure should point to a list of BFDs linked through the
- link_next field which can be used to find each BFD which takes part
- in the output. Also, each section in ABFD should point to a list
- of bfd_link_order structures which list all the input sections for
- the output section. */
-
-bfd_boolean
-NAME(aout,final_link) (abfd, info, callback)
- bfd *abfd;
- struct bfd_link_info *info;
- void (*callback) PARAMS ((bfd *, file_ptr *, file_ptr *, file_ptr *));
+static bfd_boolean
+aout_link_write_other_symbol (struct aout_link_hash_entry *h, void * data)
{
- struct aout_final_link_info aout_info;
- bfd_boolean includes_hash_initialized = FALSE;
- register bfd *sub;
- bfd_size_type trsize, drsize;
- bfd_size_type max_contents_size;
- bfd_size_type max_relocs_size;
- bfd_size_type max_sym_count;
- bfd_size_type text_size;
- file_ptr text_end;
- register struct bfd_link_order *p;
- asection *o;
- bfd_boolean have_link_order_relocs;
-
- if (info->shared)
- abfd->flags |= DYNAMIC;
+ struct aout_final_link_info *finfo = (struct aout_final_link_info *) data;
+ bfd *output_bfd;
+ int type;
+ bfd_vma val;
+ struct external_nlist outsym;
+ bfd_size_type indx;
+ bfd_size_type amt;
- aout_info.info = info;
- aout_info.output_bfd = abfd;
- aout_info.contents = NULL;
- aout_info.relocs = NULL;
- aout_info.symbol_map = NULL;
- aout_info.output_syms = NULL;
+ if (h->root.type == bfd_link_hash_warning)
+ {
+ h = (struct aout_link_hash_entry *) h->root.u.i.link;
+ if (h->root.type == bfd_link_hash_new)
+ return TRUE;
+ }
- if (! bfd_hash_table_init_n (&aout_info.includes.root,
- aout_link_includes_newfunc,
- 251))
- goto error_return;
- includes_hash_initialized = TRUE;
+ output_bfd = finfo->output_bfd;
- /* Figure out the largest section size. Also, if generating
- relocatable output, count the relocs. */
- trsize = 0;
- drsize = 0;
- max_contents_size = 0;
- max_relocs_size = 0;
- max_sym_count = 0;
- for (sub = info->input_bfds; sub != NULL; sub = sub->link_next)
+ if (aout_backend_info (output_bfd)->write_dynamic_symbol != NULL)
{
- size_t sz;
-
- if (info->relocatable)
+ if (! ((*aout_backend_info (output_bfd)->write_dynamic_symbol)
+ (output_bfd, finfo->info, h)))
{
- if (bfd_get_flavour (sub) == bfd_target_aout_flavour)
- {
- trsize += exec_hdr (sub)->a_trsize;
- drsize += exec_hdr (sub)->a_drsize;
- }
- else
- {
- /* FIXME: We need to identify the .text and .data sections
- and call get_reloc_upper_bound and canonicalize_reloc to
- work out the number of relocs needed, and then multiply
- by the reloc size. */
- (*_bfd_error_handler)
- ("%s: relocatable link from %s to %s not supported",
- bfd_get_filename (abfd),
- sub->xvec->name, abfd->xvec->name);
- bfd_set_error (bfd_error_invalid_operation);
- goto error_return;
- }
+ /* FIXME: No way to handle errors. */
+ abort ();
}
+ }
- if (bfd_get_flavour (sub) == bfd_target_aout_flavour)
- {
- sz = obj_textsec (sub)->size;
- if (sz > max_contents_size)
- max_contents_size = sz;
- sz = obj_datasec (sub)->size;
- if (sz > max_contents_size)
- max_contents_size = sz;
+ if (h->written)
+ return TRUE;
- sz = exec_hdr (sub)->a_trsize;
- if (sz > max_relocs_size)
- max_relocs_size = sz;
- sz = exec_hdr (sub)->a_drsize;
- if (sz > max_relocs_size)
- max_relocs_size = sz;
+ h->written = TRUE;
- sz = obj_aout_external_sym_count (sub);
- if (sz > max_sym_count)
- max_sym_count = sz;
- }
- }
+ /* An indx of -2 means the symbol must be written. */
+ if (h->indx != -2
+ && (finfo->info->strip == strip_all
+ || (finfo->info->strip == strip_some
+ && bfd_hash_lookup (finfo->info->keep_hash, h->root.root.string,
+ FALSE, FALSE) == NULL)))
+ return TRUE;
- if (info->relocatable)
+ switch (h->root.type)
{
- if (obj_textsec (abfd) != (asection *) NULL)
- trsize += (_bfd_count_link_order_relocs (obj_textsec (abfd)
- ->link_order_head)
- * obj_reloc_entry_size (abfd));
- if (obj_datasec (abfd) != (asection *) NULL)
- drsize += (_bfd_count_link_order_relocs (obj_datasec (abfd)
- ->link_order_head)
- * obj_reloc_entry_size (abfd));
+ default:
+ abort ();
+ /* Avoid variable not initialized warnings. */
+ return TRUE;
+ case bfd_link_hash_new:
+ /* This can happen for set symbols when sets are not being
+ built. */
+ return TRUE;
+ case bfd_link_hash_undefined:
+ type = N_UNDF | N_EXT;
+ val = 0;
+ break;
+ case bfd_link_hash_defined:
+ case bfd_link_hash_defweak:
+ {
+ asection *sec;
+
+ sec = h->root.u.def.section->output_section;
+ BFD_ASSERT (bfd_is_abs_section (sec)
+ || sec->owner == output_bfd);
+ if (sec == obj_textsec (output_bfd))
+ type = h->root.type == bfd_link_hash_defined ? N_TEXT : N_WEAKT;
+ else if (sec == obj_datasec (output_bfd))
+ type = h->root.type == bfd_link_hash_defined ? N_DATA : N_WEAKD;
+ else if (sec == obj_bsssec (output_bfd))
+ type = h->root.type == bfd_link_hash_defined ? N_BSS : N_WEAKB;
+ else
+ type = h->root.type == bfd_link_hash_defined ? N_ABS : N_WEAKA;
+ type |= N_EXT;
+ val = (h->root.u.def.value
+ + sec->vma
+ + h->root.u.def.section->output_offset);
+ }
+ break;
+ case bfd_link_hash_common:
+ type = N_UNDF | N_EXT;
+ val = h->root.u.c.size;
+ break;
+ case bfd_link_hash_undefweak:
+ type = N_WEAKU;
+ val = 0;
+ case bfd_link_hash_indirect:
+ case bfd_link_hash_warning:
+ /* FIXME: Ignore these for now. The circumstances under which
+ they should be written out are not clear to me. */
+ return TRUE;
}
- exec_hdr (abfd)->a_trsize = trsize;
- exec_hdr (abfd)->a_drsize = drsize;
+ H_PUT_8 (output_bfd, type, outsym.e_type);
+ indx = add_to_stringtab (output_bfd, finfo->strtab, h->root.root.string,
+ FALSE);
+ if (indx == (bfd_size_type) -1)
+ /* FIXME: No way to handle errors. */
+ abort ();
- exec_hdr (abfd)->a_entry = bfd_get_start_address (abfd);
+ PUT_WORD (output_bfd, indx, outsym.e_strx);
+ PUT_WORD (output_bfd, val, outsym.e_value);
- /* Adjust the section sizes and vmas according to the magic number.
- This sets a_text, a_data and a_bss in the exec_hdr and sets the
- filepos for each section. */
- if (! NAME(aout,adjust_sizes_and_vmas) (abfd, &text_size, &text_end))
- goto error_return;
+ amt = EXTERNAL_NLIST_SIZE;
+ if (bfd_seek (output_bfd, finfo->symoff, SEEK_SET) != 0
+ || bfd_bwrite ((void *) &outsym, amt, output_bfd) != amt)
+ /* FIXME: No way to handle errors. */
+ abort ();
- /* The relocation and symbol file positions differ among a.out
- targets. We are passed a callback routine from the backend
- specific code to handle this.
- FIXME: At this point we do not know how much space the symbol
- table will require. This will not work for any (nonstandard)
- a.out target that needs to know the symbol table size before it
- can compute the relocation file positions. This may or may not
- be the case for the hp300hpux target, for example. */
- (*callback) (abfd, &aout_info.treloff, &aout_info.dreloff,
- &aout_info.symoff);
- obj_textsec (abfd)->rel_filepos = aout_info.treloff;
- obj_datasec (abfd)->rel_filepos = aout_info.dreloff;
- obj_sym_filepos (abfd) = aout_info.symoff;
+ finfo->symoff += amt;
+ h->indx = obj_aout_external_sym_count (output_bfd);
+ ++obj_aout_external_sym_count (output_bfd);
- /* We keep a count of the symbols as we output them. */
- obj_aout_external_sym_count (abfd) = 0;
+ return TRUE;
+}
- /* We accumulate the string table as we write out the symbols. */
- aout_info.strtab = _bfd_stringtab_init ();
- if (aout_info.strtab == NULL)
- goto error_return;
-
- /* Allocate buffers to hold section contents and relocs. */
- aout_info.contents = (bfd_byte *) bfd_malloc (max_contents_size);
- aout_info.relocs = (PTR) bfd_malloc (max_relocs_size);
- aout_info.symbol_map = (int *) bfd_malloc (max_sym_count * sizeof (int *));
- aout_info.output_syms = ((struct external_nlist *)
- bfd_malloc ((max_sym_count + 1)
- * sizeof (struct external_nlist)));
- if ((aout_info.contents == NULL && max_contents_size != 0)
- || (aout_info.relocs == NULL && max_relocs_size != 0)
- || (aout_info.symbol_map == NULL && max_sym_count != 0)
- || aout_info.output_syms == NULL)
- goto error_return;
-
- /* If we have a symbol named __DYNAMIC, force it out now. This is
- required by SunOS. Doing this here rather than in sunos.c is a
- hack, but it's easier than exporting everything which would be
- needed. */
- {
- struct aout_link_hash_entry *h;
-
- h = aout_link_hash_lookup (aout_hash_table (info), "__DYNAMIC",
- FALSE, FALSE, FALSE);
- if (h != NULL)
- aout_link_write_other_symbol (h, &aout_info);
- }
-
- /* The most time efficient way to do the link would be to read all
- the input object files into memory and then sort out the
- information into the output file. Unfortunately, that will
- probably use too much memory. Another method would be to step
- through everything that composes the text section and write it
- out, and then everything that composes the data section and write
- it out, and then write out the relocs, and then write out the
- symbols. Unfortunately, that requires reading stuff from each
- input file several times, and we will not be able to keep all the
- input files open simultaneously, and reopening them will be slow.
+/* Handle a link order which is supposed to generate a reloc. */
- What we do is basically process one input file at a time. We do
- everything we need to do with an input file once--copy over the
- section contents, handle the relocation information, and write
- out the symbols--and then we throw away the information we read
- from it. This approach requires a lot of lseeks of the output
- file, which is unfortunate but still faster than reopening a lot
- of files.
+static bfd_boolean
+aout_link_reloc_link_order (struct aout_final_link_info *finfo,
+ asection *o,
+ struct bfd_link_order *p)
+{
+ struct bfd_link_order_reloc *pr;
+ int r_index;
+ int r_extern;
+ reloc_howto_type *howto;
+ file_ptr *reloff_ptr;
+ struct reloc_std_external srel;
+ void * rel_ptr;
+ bfd_size_type rel_size;
- We use the output_has_begun field of the input BFDs to see
- whether we have already handled it. */
- for (sub = info->input_bfds; sub != (bfd *) NULL; sub = sub->link_next)
- sub->output_has_begun = FALSE;
+ pr = p->u.reloc.p;
- /* Mark all sections which are to be included in the link. This
- will normally be every section. We need to do this so that we
- can identify any sections which the linker has decided to not
- include. */
- for (o = abfd->sections; o != NULL; o = o->next)
+ if (p->type == bfd_section_reloc_link_order)
{
- for (p = o->link_order_head; p != NULL; p = p->next)
+ r_extern = 0;
+ if (bfd_is_abs_section (pr->u.section))
+ r_index = N_ABS | N_EXT;
+ else
{
- if (p->type == bfd_indirect_link_order)
- p->u.indirect.section->linker_mark = TRUE;
+ BFD_ASSERT (pr->u.section->owner == finfo->output_bfd);
+ r_index = pr->u.section->target_index;
}
}
-
- have_link_order_relocs = FALSE;
- for (o = abfd->sections; o != (asection *) NULL; o = o->next)
+ else
{
- for (p = o->link_order_head;
- p != (struct bfd_link_order *) NULL;
- p = p->next)
- {
- if (p->type == bfd_indirect_link_order
- && (bfd_get_flavour (p->u.indirect.section->owner)
- == bfd_target_aout_flavour))
- {
- bfd *input_bfd;
+ struct aout_link_hash_entry *h;
- input_bfd = p->u.indirect.section->owner;
- if (! input_bfd->output_has_begun)
- {
- if (! aout_link_input_bfd (&aout_info, input_bfd))
- goto error_return;
- input_bfd->output_has_begun = TRUE;
- }
- }
- else if (p->type == bfd_section_reloc_link_order
- || p->type == bfd_symbol_reloc_link_order)
- {
- /* These are handled below. */
- have_link_order_relocs = TRUE;
- }
- else
- {
- if (! _bfd_default_link_order (abfd, info, o, p))
- goto error_return;
- }
+ BFD_ASSERT (p->type == bfd_symbol_reloc_link_order);
+ r_extern = 1;
+ h = ((struct aout_link_hash_entry *)
+ bfd_wrapped_link_hash_lookup (finfo->output_bfd, finfo->info,
+ pr->u.name, FALSE, FALSE, TRUE));
+ if (h != NULL
+ && h->indx >= 0)
+ r_index = h->indx;
+ else if (h != NULL)
+ {
+ /* We decided to strip this symbol, but it turns out that we
+ can't. Note that we lose the other and desc information
+ here. I don't think that will ever matter for a global
+ symbol. */
+ h->indx = -2;
+ h->written = FALSE;
+ if (! aout_link_write_other_symbol (h, (void *) finfo))
+ return FALSE;
+ r_index = h->indx;
}
- }
-
- /* Write out any symbols that we have not already written out. */
- aout_link_hash_traverse (aout_hash_table (info),
- aout_link_write_other_symbol,
- (PTR) &aout_info);
-
- /* Now handle any relocs we were asked to create by the linker.
- These did not come from any input file. We must do these after
- we have written out all the symbols, so that we know the symbol
- indices to use. */
- if (have_link_order_relocs)
- {
- for (o = abfd->sections; o != (asection *) NULL; o = o->next)
+ else
{
- for (p = o->link_order_head;
- p != (struct bfd_link_order *) NULL;
- p = p->next)
- {
- if (p->type == bfd_section_reloc_link_order
- || p->type == bfd_symbol_reloc_link_order)
- {
- if (! aout_link_reloc_link_order (&aout_info, o, p))
- goto error_return;
- }
- }
+ if (! ((*finfo->info->callbacks->unattached_reloc)
+ (finfo->info, pr->u.name, NULL, NULL, (bfd_vma) 0)))
+ return FALSE;
+ r_index = 0;
}
}
- if (aout_info.contents != NULL)
- {
- free (aout_info.contents);
- aout_info.contents = NULL;
- }
- if (aout_info.relocs != NULL)
- {
- free (aout_info.relocs);
- aout_info.relocs = NULL;
- }
- if (aout_info.symbol_map != NULL)
- {
- free (aout_info.symbol_map);
- aout_info.symbol_map = NULL;
- }
- if (aout_info.output_syms != NULL)
- {
- free (aout_info.output_syms);
- aout_info.output_syms = NULL;
- }
- if (includes_hash_initialized)
+ howto = bfd_reloc_type_lookup (finfo->output_bfd, pr->reloc);
+ if (howto == 0)
{
- bfd_hash_table_free (&aout_info.includes.root);
- includes_hash_initialized = FALSE;
+ bfd_set_error (bfd_error_bad_value);
+ return FALSE;
}
- /* Finish up any dynamic linking we may be doing. */
- if (aout_backend_info (abfd)->finish_dynamic_link != NULL)
- {
- if (! (*aout_backend_info (abfd)->finish_dynamic_link) (abfd, info))
- goto error_return;
- }
+ if (o == obj_textsec (finfo->output_bfd))
+ reloff_ptr = &finfo->treloff;
+ else if (o == obj_datasec (finfo->output_bfd))
+ reloff_ptr = &finfo->dreloff;
+ else
+ abort ();
- /* Update the header information. */
- abfd->symcount = obj_aout_external_sym_count (abfd);
- exec_hdr (abfd)->a_syms = abfd->symcount * EXTERNAL_NLIST_SIZE;
- obj_str_filepos (abfd) = obj_sym_filepos (abfd) + exec_hdr (abfd)->a_syms;
- obj_textsec (abfd)->reloc_count =
- exec_hdr (abfd)->a_trsize / obj_reloc_entry_size (abfd);
- obj_datasec (abfd)->reloc_count =
- exec_hdr (abfd)->a_drsize / obj_reloc_entry_size (abfd);
+#ifdef MY_put_reloc
+ MY_put_reloc(finfo->output_bfd, r_extern, r_index, p->offset, howto,
+ &srel);
+#else
+ {
+ int r_pcrel;
+ int r_baserel;
+ int r_jmptable;
+ int r_relative;
+ int r_length;
- /* Write out the string table, unless there are no symbols. */
- if (abfd->symcount > 0)
- {
- if (bfd_seek (abfd, obj_str_filepos (abfd), SEEK_SET) != 0
- || ! emit_stringtab (abfd, aout_info.strtab))
- goto error_return;
- }
- else if (obj_textsec (abfd)->reloc_count == 0
- && obj_datasec (abfd)->reloc_count == 0)
- {
- bfd_byte b;
+ fprintf (stderr, "TODO: line %d in bfd/pdp11.c\n", __LINE__);
- b = 0;
- if (bfd_seek (abfd,
- (file_ptr) (obj_datasec (abfd)->filepos
- + exec_hdr (abfd)->a_data
- - 1),
- SEEK_SET) != 0
- || bfd_bwrite (&b, (bfd_size_type) 1, abfd) != 1)
- goto error_return;
- }
+ r_pcrel = howto->pc_relative;
+ r_baserel = (howto->type & 8) != 0;
+ r_jmptable = (howto->type & 16) != 0;
+ r_relative = (howto->type & 32) != 0;
+ r_length = howto->size;
- return TRUE;
+ PUT_WORD (finfo->output_bfd, p->offset, srel.r_address);
+ if (bfd_header_big_endian (finfo->output_bfd))
+ {
+ srel.r_index[0] = r_index >> 16;
+ srel.r_index[1] = r_index >> 8;
+ srel.r_index[2] = r_index;
+ srel.r_type[0] =
+ ((r_extern ? RELOC_STD_BITS_EXTERN_BIG : 0)
+ | (r_pcrel ? RELOC_STD_BITS_PCREL_BIG : 0)
+ | (r_baserel ? RELOC_STD_BITS_BASEREL_BIG : 0)
+ | (r_jmptable ? RELOC_STD_BITS_JMPTABLE_BIG : 0)
+ | (r_relative ? RELOC_STD_BITS_RELATIVE_BIG : 0)
+ | (r_length << RELOC_STD_BITS_LENGTH_SH_BIG));
+ }
+ else
+ {
+ srel.r_index[2] = r_index >> 16;
+ srel.r_index[1] = r_index >> 8;
+ srel.r_index[0] = r_index;
+ srel.r_type[0] =
+ ((r_extern ? RELOC_STD_BITS_EXTERN_LITTLE : 0)
+ | (r_pcrel ? RELOC_STD_BITS_PCREL_LITTLE : 0)
+ | (r_baserel ? RELOC_STD_BITS_BASEREL_LITTLE : 0)
+ | (r_jmptable ? RELOC_STD_BITS_JMPTABLE_LITTLE : 0)
+ | (r_relative ? RELOC_STD_BITS_RELATIVE_LITTLE : 0)
+ | (r_length << RELOC_STD_BITS_LENGTH_SH_LITTLE));
+ }
+ }
+#endif
+ rel_ptr = (void *) &srel;
- error_return:
- if (aout_info.contents != NULL)
- free (aout_info.contents);
- if (aout_info.relocs != NULL)
- free (aout_info.relocs);
- if (aout_info.symbol_map != NULL)
- free (aout_info.symbol_map);
- if (aout_info.output_syms != NULL)
- free (aout_info.output_syms);
- if (includes_hash_initialized)
- bfd_hash_table_free (&aout_info.includes.root);
- return FALSE;
-}
-
-/* Link an a.out input BFD into the output file. */
-
-static bfd_boolean
-aout_link_input_bfd (finfo, input_bfd)
- struct aout_final_link_info *finfo;
- bfd *input_bfd;
-{
- bfd_size_type sym_count;
-
- BFD_ASSERT (bfd_get_format (input_bfd) == bfd_object);
-
- /* If this is a dynamic object, it may need special handling. */
- if ((input_bfd->flags & DYNAMIC) != 0
- && aout_backend_info (input_bfd)->link_dynamic_object != NULL)
+ /* We have to write the addend into the object file, since
+ standard a.out relocs are in place. It would be more
+ reliable if we had the current contents of the file here,
+ rather than assuming zeroes, but we can't read the file since
+ it was opened using bfd_openw. */
+ if (pr->addend != 0)
{
- return ((*aout_backend_info (input_bfd)->link_dynamic_object)
- (finfo->info, input_bfd));
+ bfd_size_type size;
+ bfd_reloc_status_type r;
+ bfd_byte *buf;
+ bfd_boolean ok;
+
+ size = bfd_get_reloc_size (howto);
+ buf = bfd_zmalloc (size);
+ if (buf == NULL)
+ return FALSE;
+ r = MY_relocate_contents (howto, finfo->output_bfd,
+ pr->addend, buf);
+ switch (r)
+ {
+ case bfd_reloc_ok:
+ break;
+ default:
+ case bfd_reloc_outofrange:
+ abort ();
+ case bfd_reloc_overflow:
+ if (! ((*finfo->info->callbacks->reloc_overflow)
+ (finfo->info, NULL,
+ (p->type == bfd_section_reloc_link_order
+ ? bfd_section_name (finfo->output_bfd,
+ pr->u.section)
+ : pr->u.name),
+ howto->name, pr->addend, NULL,
+ (asection *) NULL, (bfd_vma) 0)))
+ {
+ free (buf);
+ return FALSE;
+ }
+ break;
+ }
+ ok = bfd_set_section_contents (finfo->output_bfd, o,
+ (void *) buf,
+ (file_ptr) p->offset,
+ size);
+ free (buf);
+ if (! ok)
+ return FALSE;
}
- /* Get the symbols. We probably have them already, unless
- finfo->info->keep_memory is FALSE. */
- if (! aout_get_external_symbols (input_bfd))
+ rel_size = obj_reloc_entry_size (finfo->output_bfd);
+ if (bfd_seek (finfo->output_bfd, *reloff_ptr, SEEK_SET) != 0
+ || bfd_bwrite (rel_ptr, rel_size, finfo->output_bfd) != rel_size)
return FALSE;
- sym_count = obj_aout_external_sym_count (input_bfd);
+ *reloff_ptr += rel_size;
- /* Write out the symbols and get a map of the new indices. The map
- is placed into finfo->symbol_map. */
- if (! aout_link_write_symbols (finfo, input_bfd))
- return FALSE;
+ /* Assert that the relocs have not run into the symbols, and that n
+ the text relocs have not run into the data relocs. */
+ BFD_ASSERT (*reloff_ptr <= obj_sym_filepos (finfo->output_bfd)
+ && (reloff_ptr != &finfo->treloff
+ || (*reloff_ptr
+ <= obj_datasec (finfo->output_bfd)->rel_filepos)));
- /* Relocate and write out the sections. These functions use the
- symbol map created by aout_link_write_symbols. The linker_mark
- field will be set if these sections are to be included in the
- link, which will normally be the case. */
- if (obj_textsec (input_bfd)->linker_mark)
- {
- if (! aout_link_input_section (finfo, input_bfd,
- obj_textsec (input_bfd),
- &finfo->treloff,
- exec_hdr (input_bfd)->a_trsize))
- return FALSE;
- }
- if (obj_datasec (input_bfd)->linker_mark)
- {
- if (! aout_link_input_section (finfo, input_bfd,
- obj_datasec (input_bfd),
- &finfo->dreloff,
- exec_hdr (input_bfd)->a_drsize))
- return FALSE;
- }
+ return TRUE;
+}
- /* If we are not keeping memory, we don't need the symbols any
- longer. We still need them if we are keeping memory, because the
- strings in the hash table point into them. */
- if (! finfo->info->keep_memory)
+/* Get the section corresponding to a reloc index. */
+
+static inline asection *
+aout_reloc_type_to_section (bfd *abfd, int type)
+{
+ switch (type)
{
- if (! aout_link_free_symbols (input_bfd))
- return FALSE;
+ case RTEXT: return obj_textsec (abfd);
+ case RDATA: return obj_datasec (abfd);
+ case RBSS: return obj_bsssec (abfd);
+ case RABS: return bfd_abs_section_ptr;
+ case REXT: return bfd_und_section_ptr;
+ default: abort ();
}
-
- return TRUE;
}
-/* Adjust and write out the symbols for an a.out file. Set the new
- symbol indices into a symbol_map. */
-
static bfd_boolean
-aout_link_write_symbols (finfo, input_bfd)
- struct aout_final_link_info *finfo;
- bfd *input_bfd;
+pdp11_aout_link_input_section (struct aout_final_link_info *finfo,
+ bfd *input_bfd,
+ asection *input_section,
+ bfd_byte *relocs,
+ bfd_size_type rel_size,
+ bfd_byte *contents)
{
+ bfd_boolean (*check_dynamic_reloc)
+ (struct bfd_link_info *, bfd *, asection *,
+ struct aout_link_hash_entry *, void *, bfd_byte *, bfd_boolean *,
+ bfd_vma *);
bfd *output_bfd;
- bfd_size_type sym_count;
+ bfd_boolean relocatable;
+ struct external_nlist *syms;
char *strings;
- enum bfd_link_strip strip;
- enum bfd_link_discard discard;
- struct external_nlist *outsym;
- bfd_size_type strtab_index;
- register struct external_nlist *sym;
- struct external_nlist *sym_end;
- struct aout_link_hash_entry **sym_hash;
+ struct aout_link_hash_entry **sym_hashes;
int *symbol_map;
- bfd_boolean pass;
- bfd_boolean skip_next;
+ bfd_size_type reloc_count;
+ bfd_byte *rel;
+ bfd_byte *rel_end;
output_bfd = finfo->output_bfd;
- sym_count = obj_aout_external_sym_count (input_bfd);
- strings = obj_aout_external_strings (input_bfd);
- strip = finfo->info->strip;
- discard = finfo->info->discard;
- outsym = finfo->output_syms;
+ check_dynamic_reloc = aout_backend_info (output_bfd)->check_dynamic_reloc;
- /* First write out a symbol for this object file, unless we are
- discarding such symbols. */
- if (strip != strip_all
- && (strip != strip_some
- || bfd_hash_lookup (finfo->info->keep_hash, input_bfd->filename,
- FALSE, FALSE) != NULL)
- && discard != discard_all)
- {
- H_PUT_8 (output_bfd, N_TEXT, outsym->e_type);
- strtab_index = add_to_stringtab (output_bfd, finfo->strtab,
- input_bfd->filename, FALSE);
- if (strtab_index == (bfd_size_type) -1)
- return FALSE;
- PUT_WORD (output_bfd, strtab_index, outsym->e_strx);
- PUT_WORD (output_bfd,
- (bfd_get_section_vma (output_bfd,
- obj_textsec (input_bfd)->output_section)
- + obj_textsec (input_bfd)->output_offset),
- outsym->e_value);
- ++obj_aout_external_sym_count (output_bfd);
- ++outsym;
- }
+ BFD_ASSERT (obj_reloc_entry_size (input_bfd) == RELOC_SIZE);
+ BFD_ASSERT (input_bfd->xvec->header_byteorder
+ == output_bfd->xvec->header_byteorder);
- pass = FALSE;
- skip_next = FALSE;
- sym = obj_aout_external_syms (input_bfd);
- sym_end = sym + sym_count;
- sym_hash = obj_aout_sym_hashes (input_bfd);
+ relocatable = finfo->info->relocatable;
+ syms = obj_aout_external_syms (input_bfd);
+ strings = obj_aout_external_strings (input_bfd);
+ sym_hashes = obj_aout_sym_hashes (input_bfd);
symbol_map = finfo->symbol_map;
- memset (symbol_map, 0, (size_t) sym_count * sizeof *symbol_map);
- for (; sym < sym_end; sym++, sym_hash++, symbol_map++)
+
+ reloc_count = rel_size / RELOC_SIZE;
+ rel = relocs;
+ rel_end = rel + rel_size;
+ for (; rel < rel_end; rel += RELOC_SIZE)
{
- const char *name;
- int type;
- struct aout_link_hash_entry *h;
- bfd_boolean skip;
- asection *symsec;
- bfd_vma val = 0;
- bfd_boolean copy;
+ bfd_vma r_addr;
+ int r_index;
+ int r_type;
+ int r_pcrel;
+ int r_extern;
+ reloc_howto_type *howto;
+ struct aout_link_hash_entry *h = NULL;
+ bfd_vma relocation;
+ bfd_reloc_status_type r;
+ int reloc_entry;
- /* We set *symbol_map to 0 above for all symbols. If it has
- already been set to -1 for this symbol, it means that we are
- discarding it because it appears in a duplicate header file.
- See the N_BINCL code below. */
- if (*symbol_map == -1)
+ reloc_entry = GET_WORD (input_bfd, (void *) rel);
+ if (reloc_entry == 0)
continue;
- /* Initialize *symbol_map to -1, which means that the symbol was
- not copied into the output file. We will change it later if
- we do copy the symbol over. */
- *symbol_map = -1;
+ {
+ unsigned int howto_idx;
- type = H_GET_8 (input_bfd, sym->e_type);
- name = strings + GET_WORD (input_bfd, sym->e_strx);
+ r_index = (reloc_entry & RIDXMASK) >> 4;
+ r_type = reloc_entry & RTYPE;
+ r_pcrel = reloc_entry & RELFLG;
+ r_addr = (char *) rel - (char *) relocs;
- h = NULL;
+ r_extern = (r_type == REXT);
- if (pass)
- {
- /* Pass this symbol through. It is the target of an
- indirect or warning symbol. */
- val = GET_WORD (input_bfd, sym->e_value);
- pass = FALSE;
- }
- else if (skip_next)
- {
- /* Skip this symbol, which is the target of an indirect
- symbol that we have changed to no longer be an indirect
- symbol. */
- skip_next = FALSE;
- continue;
- }
- else
+ howto_idx = r_pcrel;
+ BFD_ASSERT (howto_idx < TABLE_SIZE (howto_table_pdp11));
+ howto = howto_table_pdp11 + howto_idx;
+ }
+
+ if (relocatable)
{
- struct aout_link_hash_entry *hresolve;
-
- /* We have saved the hash table entry for this symbol, if
- there is one. Note that we could just look it up again
- in the hash table, provided we first check that it is an
- external symbol. */
- h = *sym_hash;
-
- /* Use the name from the hash table, in case the symbol was
- wrapped. */
- if (h != NULL)
- name = h->root.root.string;
-
- /* If this is an indirect or warning symbol, then change
- hresolve to the base symbol. We also change *sym_hash so
- that the relocation routines relocate against the real
- symbol. */
- hresolve = h;
- if (h != (struct aout_link_hash_entry *) NULL
- && (h->root.type == bfd_link_hash_indirect
- || h->root.type == bfd_link_hash_warning))
- {
- hresolve = (struct aout_link_hash_entry *) h->root.u.i.link;
- while (hresolve->root.type == bfd_link_hash_indirect
- || hresolve->root.type == bfd_link_hash_warning)
- hresolve = ((struct aout_link_hash_entry *)
- hresolve->root.u.i.link);
- *sym_hash = hresolve;
- }
-
- /* If the symbol has already been written out, skip it. */
- if (h != (struct aout_link_hash_entry *) NULL
- && h->root.type != bfd_link_hash_warning
- && h->written)
- {
- if ((type & N_TYPE) == N_INDR
- || type == N_WARNING)
- skip_next = TRUE;
- *symbol_map = h->indx;
- continue;
- }
-
- /* See if we are stripping this symbol. */
- skip = FALSE;
- switch (strip)
- {
- case strip_none:
- break;
- case strip_debugger:
- if ((type & N_STAB) != 0)
- skip = TRUE;
- break;
- case strip_some:
- if (bfd_hash_lookup (finfo->info->keep_hash, name, FALSE, FALSE)
- == NULL)
- skip = TRUE;
- break;
- case strip_all:
- skip = TRUE;
- break;
- }
- if (skip)
- {
- if (h != (struct aout_link_hash_entry *) NULL)
- h->written = TRUE;
- continue;
- }
-
- /* Get the value of the symbol. */
- if ((type & N_TYPE) == N_TEXT
- || type == N_WEAKT)
- symsec = obj_textsec (input_bfd);
- else if ((type & N_TYPE) == N_DATA
- || type == N_WEAKD)
- symsec = obj_datasec (input_bfd);
- else if ((type & N_TYPE) == N_BSS
- || type == N_WEAKB)
- symsec = obj_bsssec (input_bfd);
- else if ((type & N_TYPE) == N_ABS
- || type == N_WEAKA)
- symsec = bfd_abs_section_ptr;
- else if (((type & N_TYPE) == N_INDR
- && (hresolve == (struct aout_link_hash_entry *) NULL
- || (hresolve->root.type != bfd_link_hash_defined
- && hresolve->root.type != bfd_link_hash_defweak
- && hresolve->root.type != bfd_link_hash_common)))
- || type == N_WARNING)
- {
- /* Pass the next symbol through unchanged. The
- condition above for indirect symbols is so that if
- the indirect symbol was defined, we output it with
- the correct definition so the debugger will
- understand it. */
- pass = TRUE;
- val = GET_WORD (input_bfd, sym->e_value);
- symsec = NULL;
- }
- else if ((type & N_STAB) != 0)
- {
- val = GET_WORD (input_bfd, sym->e_value);
- symsec = NULL;
- }
- else
- {
- /* If we get here with an indirect symbol, it means that
- we are outputting it with a real definition. In such
- a case we do not want to output the next symbol,
- which is the target of the indirection. */
- if ((type & N_TYPE) == N_INDR)
- skip_next = TRUE;
-
- symsec = NULL;
-
- /* We need to get the value from the hash table. We use
- hresolve so that if we have defined an indirect
- symbol we output the final definition. */
- if (h == (struct aout_link_hash_entry *) NULL)
- {
- switch (type & N_TYPE)
- {
- case N_SETT:
- symsec = obj_textsec (input_bfd);
- break;
- case N_SETD:
- symsec = obj_datasec (input_bfd);
- break;
- case N_SETB:
- symsec = obj_bsssec (input_bfd);
- break;
- case N_SETA:
- symsec = bfd_abs_section_ptr;
- break;
- default:
- val = 0;
- break;
- }
- }
- else if (hresolve->root.type == bfd_link_hash_defined
- || hresolve->root.type == bfd_link_hash_defweak)
- {
- asection *input_section;
- asection *output_section;
-
- /* This case usually means a common symbol which was
- turned into a defined symbol. */
- input_section = hresolve->root.u.def.section;
- output_section = input_section->output_section;
- BFD_ASSERT (bfd_is_abs_section (output_section)
- || output_section->owner == output_bfd);
- val = (hresolve->root.u.def.value
- + bfd_get_section_vma (output_bfd, output_section)
- + input_section->output_offset);
-
- /* Get the correct type based on the section. If
- this is a constructed set, force it to be
- globally visible. */
- if (type == N_SETT
- || type == N_SETD
- || type == N_SETB
- || type == N_SETA)
- type |= N_EXT;
-
- type &=~ N_TYPE;
+ /* We are generating a relocatable output file, and must
+ modify the reloc accordingly. */
+ if (r_extern)
+ {
+ /* If we know the symbol this relocation is against,
+ convert it into a relocation against a section. This
+ is what the native linker does. */
+ h = sym_hashes[r_index];
+ if (h != NULL
+ && (h->root.type == bfd_link_hash_defined
+ || h->root.type == bfd_link_hash_defweak))
+ {
+ asection *output_section;
+ /* Compute a new r_index. */
+ output_section = h->root.u.def.section->output_section;
if (output_section == obj_textsec (output_bfd))
- type |= (hresolve->root.type == bfd_link_hash_defined
- ? N_TEXT
- : N_WEAKT);
+ r_type = N_TEXT;
else if (output_section == obj_datasec (output_bfd))
- type |= (hresolve->root.type == bfd_link_hash_defined
- ? N_DATA
- : N_WEAKD);
+ r_type = N_DATA;
else if (output_section == obj_bsssec (output_bfd))
- type |= (hresolve->root.type == bfd_link_hash_defined
- ? N_BSS
- : N_WEAKB);
+ r_type = N_BSS;
else
- type |= (hresolve->root.type == bfd_link_hash_defined
- ? N_ABS
- : N_WEAKA);
- }
- else if (hresolve->root.type == bfd_link_hash_common)
- val = hresolve->root.u.c.size;
- else if (hresolve->root.type == bfd_link_hash_undefweak)
- {
- val = 0;
- type = N_WEAKU;
- }
- else
- val = 0;
- }
- if (symsec != (asection *) NULL)
- val = (symsec->output_section->vma
- + symsec->output_offset
- + (GET_WORD (input_bfd, sym->e_value)
- - symsec->vma));
+ r_type = N_ABS;
- /* If this is a global symbol set the written flag, and if
- it is a local symbol see if we should discard it. */
- if (h != (struct aout_link_hash_entry *) NULL)
- {
- h->written = TRUE;
- h->indx = obj_aout_external_sym_count (output_bfd);
- }
- else if ((type & N_TYPE) != N_SETT
- && (type & N_TYPE) != N_SETD
- && (type & N_TYPE) != N_SETB
- && (type & N_TYPE) != N_SETA)
- {
- switch (discard)
- {
- case discard_none:
- case discard_sec_merge:
- break;
- case discard_l:
- if ((type & N_STAB) == 0
- && bfd_is_local_label_name (input_bfd, name))
- skip = TRUE;
- break;
- case discard_all:
- skip = TRUE;
- break;
- }
- if (skip)
- {
- pass = FALSE;
- continue;
+ /* Add the symbol value and the section VMA to the
+ addend stored in the contents. */
+ relocation = (h->root.u.def.value
+ + output_section->vma
+ + h->root.u.def.section->output_offset);
}
- }
-
- /* An N_BINCL symbol indicates the start of the stabs
- entries for a header file. We need to scan ahead to the
- next N_EINCL symbol, ignoring nesting, adding up all the
- characters in the symbol names, not including the file
- numbers in types (the first number after an open
- parenthesis). */
- if (type == N_BINCL)
- {
- struct external_nlist *incl_sym;
- int nest;
- struct aout_link_includes_entry *incl_entry;
- struct aout_link_includes_totals *t;
-
- val = 0;
- nest = 0;
- for (incl_sym = sym + 1; incl_sym < sym_end; incl_sym++)
+ else
{
- int incl_type;
+ /* We must change r_index according to the symbol
+ map. */
+ r_index = symbol_map[r_index];
- incl_type = H_GET_8 (input_bfd, incl_sym->e_type);
- if (incl_type == N_EINCL)
- {
- if (nest == 0)
- break;
- --nest;
- }
- else if (incl_type == N_BINCL)
- ++nest;
- else if (nest == 0)
+ if (r_index == -1)
{
- const char *s;
-
- s = strings + GET_WORD (input_bfd, incl_sym->e_strx);
- for (; *s != '\0'; s++)
+ if (h != NULL)
{
- val += *s;
- if (*s == '(')
+ /* We decided to strip this symbol, but it
+ turns out that we can't. Note that we
+ lose the other and desc information here.
+ I don't think that will ever matter for a
+ global symbol. */
+ if (h->indx < 0)
{
- /* Skip the file number. */
- ++s;
- while (ISDIGIT (*s))
- ++s;
- --s;
+ h->indx = -2;
+ h->written = FALSE;
+ if (! aout_link_write_other_symbol (h,
+ (void *) finfo))
+ return FALSE;
}
+ r_index = h->indx;
+ }
+ else
+ {
+ const char *name;
+
+ name = strings + GET_WORD (input_bfd,
+ syms[r_index].e_strx);
+ if (! ((*finfo->info->callbacks->unattached_reloc)
+ (finfo->info, name, input_bfd, input_section,
+ r_addr)))
+ return FALSE;
+ r_index = 0;
}
}
+
+ relocation = 0;
}
- /* If we have already included a header file with the
- same value, then replace this one with an N_EXCL
- symbol. */
- copy = ! finfo->info->keep_memory;
- incl_entry = aout_link_includes_lookup (&finfo->includes,
- name, TRUE, copy);
- if (incl_entry == NULL)
- return FALSE;
- for (t = incl_entry->totals; t != NULL; t = t->next)
- if (t->total == val)
- break;
- if (t == NULL)
+ /* Write out the new r_index value. */
+ reloc_entry = GET_WORD (input_bfd, rel);
+ reloc_entry &= RIDXMASK;
+ reloc_entry |= r_index << 4;
+ PUT_WORD (input_bfd, reloc_entry, rel);
+ }
+ else
+ {
+ asection *section;
+
+ /* This is a relocation against a section. We must
+ adjust by the amount that the section moved. */
+ section = aout_reloc_type_to_section (input_bfd, r_type);
+ relocation = (section->output_section->vma
+ + section->output_offset
+ - section->vma);
+ }
+
+ /* Change the address of the relocation. */
+ fprintf (stderr, "TODO: change the address of the relocation\n");
+
+ /* Adjust a PC relative relocation by removing the reference
+ to the original address in the section and including the
+ reference to the new address. */
+ if (r_pcrel)
+ relocation -= (input_section->output_section->vma
+ + input_section->output_offset
+ - input_section->vma);
+
+#ifdef MY_relocatable_reloc
+ MY_relocatable_reloc (howto, output_bfd, rel, relocation, r_addr);
+#endif
+
+ if (relocation == 0)
+ r = bfd_reloc_ok;
+ else
+ r = MY_relocate_contents (howto,
+ input_bfd, relocation,
+ contents + r_addr);
+ }
+ else
+ {
+ bfd_boolean hundef;
+
+ /* We are generating an executable, and must do a full
+ relocation. */
+ hundef = FALSE;
+ if (r_extern)
+ {
+ h = sym_hashes[r_index];
+
+ if (h != NULL
+ && (h->root.type == bfd_link_hash_defined
+ || h->root.type == bfd_link_hash_defweak))
{
- /* This is the first time we have seen this header
- file with this set of stabs strings. */
- t = ((struct aout_link_includes_totals *)
- bfd_hash_allocate (&finfo->includes.root,
- sizeof *t));
- if (t == NULL)
- return FALSE;
- t->total = val;
- t->next = incl_entry->totals;
- incl_entry->totals = t;
+ relocation = (h->root.u.def.value
+ + h->root.u.def.section->output_section->vma
+ + h->root.u.def.section->output_offset);
}
+ else if (h != NULL
+ && h->root.type == bfd_link_hash_undefweak)
+ relocation = 0;
else
{
- int *incl_map;
+ hundef = TRUE;
+ relocation = 0;
+ }
+ }
+ else
+ {
+ asection *section;
- /* This is a duplicate header file. We must change
- it to be an N_EXCL entry, and mark all the
- included symbols to prevent outputting them. */
- type = N_EXCL;
+ section = aout_reloc_type_to_section (input_bfd, r_type);
+ relocation = (section->output_section->vma
+ + section->output_offset
+ - section->vma);
+ if (r_pcrel)
+ relocation += input_section->vma;
+ }
- nest = 0;
- for (incl_sym = sym + 1, incl_map = symbol_map + 1;
- incl_sym < sym_end;
- incl_sym++, incl_map++)
- {
- int incl_type;
+ if (check_dynamic_reloc != NULL)
+ {
+ bfd_boolean skip;
- incl_type = H_GET_8 (input_bfd, incl_sym->e_type);
- if (incl_type == N_EINCL)
- {
- if (nest == 0)
- {
- *incl_map = -1;
- break;
- }
- --nest;
- }
- else if (incl_type == N_BINCL)
- ++nest;
- else if (nest == 0)
- *incl_map = -1;
- }
- }
+ if (! ((*check_dynamic_reloc)
+ (finfo->info, input_bfd, input_section, h,
+ (void *) rel, contents, &skip, &relocation)))
+ return FALSE;
+ if (skip)
+ continue;
+ }
+
+ /* Now warn if a global symbol is undefined. We could not
+ do this earlier, because check_dynamic_reloc might want
+ to skip this reloc. */
+ if (hundef && ! finfo->info->shared)
+ {
+ const char *name;
+
+ if (h != NULL)
+ name = h->root.root.string;
+ else
+ name = strings + GET_WORD (input_bfd, syms[r_index].e_strx);
+ if (! ((*finfo->info->callbacks->undefined_symbol)
+ (finfo->info, name, input_bfd, input_section,
+ r_addr, TRUE)))
+ return FALSE;
}
+
+ r = MY_final_link_relocate (howto,
+ input_bfd, input_section,
+ contents, r_addr, relocation,
+ (bfd_vma) 0);
}
- /* Copy this symbol into the list of symbols we are going to
- write out. */
- H_PUT_8 (output_bfd, type, outsym->e_type);
- copy = FALSE;
- if (! finfo->info->keep_memory)
+ if (r != bfd_reloc_ok)
{
- /* name points into a string table which we are going to
- free. If there is a hash table entry, use that string.
- Otherwise, copy name into memory. */
- if (h != (struct aout_link_hash_entry *) NULL)
- name = h->root.root.string;
- else
- copy = TRUE;
+ switch (r)
+ {
+ default:
+ case bfd_reloc_outofrange:
+ abort ();
+ case bfd_reloc_overflow:
+ {
+ const char *name;
+
+ if (h != NULL)
+ name = NULL;
+ else if (r_extern)
+ name = strings + GET_WORD (input_bfd,
+ syms[r_index].e_strx);
+ else
+ {
+ asection *s;
+
+ s = aout_reloc_type_to_section (input_bfd, r_type);
+ name = bfd_section_name (input_bfd, s);
+ }
+ if (! ((*finfo->info->callbacks->reloc_overflow)
+ (finfo->info, (h ? &h->root : NULL), name,
+ howto->name, (bfd_vma) 0, input_bfd,
+ input_section, r_addr)))
+ return FALSE;
+ }
+ break;
+ }
}
- strtab_index = add_to_stringtab (output_bfd, finfo->strtab,
- name, copy);
- if (strtab_index == (bfd_size_type) -1)
- return FALSE;
- PUT_WORD (output_bfd, strtab_index, outsym->e_strx);
- PUT_WORD (output_bfd, val, outsym->e_value);
- *symbol_map = obj_aout_external_sym_count (output_bfd);
- ++obj_aout_external_sym_count (output_bfd);
- ++outsym;
}
- /* Write out the output symbols we have just constructed. */
- if (outsym > finfo->output_syms)
+ return TRUE;
+}
+
+/* Link an a.out section into the output file. */
+
+static bfd_boolean
+aout_link_input_section (struct aout_final_link_info *finfo,
+ bfd *input_bfd,
+ asection *input_section,
+ file_ptr *reloff_ptr,
+ bfd_size_type rel_size)
+{
+ bfd_size_type input_size;
+ void * relocs;
+
+ /* Get the section contents. */
+ input_size = input_section->size;
+ if (! bfd_get_section_contents (input_bfd, input_section,
+ (void *) finfo->contents,
+ (file_ptr) 0, input_size))
+ return FALSE;
+
+ /* Read in the relocs if we haven't already done it. */
+ if (aout_section_data (input_section) != NULL
+ && aout_section_data (input_section)->relocs != NULL)
+ relocs = aout_section_data (input_section)->relocs;
+ else
{
- bfd_size_type size;
+ relocs = finfo->relocs;
+ if (rel_size > 0)
+ {
+ if (bfd_seek (input_bfd, input_section->rel_filepos, SEEK_SET) != 0
+ || bfd_bread (relocs, rel_size, input_bfd) != rel_size)
+ return FALSE;
+ }
+ }
- if (bfd_seek (output_bfd, finfo->symoff, SEEK_SET) != 0)
+ /* Relocate the section contents. */
+ if (! pdp11_aout_link_input_section (finfo, input_bfd, input_section,
+ (bfd_byte *) relocs,
+ rel_size, finfo->contents))
+ return FALSE;
+
+ /* Write out the section contents. */
+ if (! bfd_set_section_contents (finfo->output_bfd,
+ input_section->output_section,
+ (void *) finfo->contents,
+ (file_ptr) input_section->output_offset,
+ input_size))
+ return FALSE;
+
+ /* If we are producing relocatable output, the relocs were
+ modified, and we now write them out. */
+ if (finfo->info->relocatable && rel_size > 0)
+ {
+ if (bfd_seek (finfo->output_bfd, *reloff_ptr, SEEK_SET) != 0)
+ return FALSE;
+ if (bfd_bwrite (relocs, rel_size, finfo->output_bfd) != rel_size)
+ return FALSE;
+ *reloff_ptr += rel_size;
+
+ /* Assert that the relocs have not run into the symbols, and
+ that if these are the text relocs they have not run into the
+ data relocs. */
+ BFD_ASSERT (*reloff_ptr <= obj_sym_filepos (finfo->output_bfd)
+ && (reloff_ptr != &finfo->treloff
+ || (*reloff_ptr
+ <= obj_datasec (finfo->output_bfd)->rel_filepos)));
+ }
+
+ return TRUE;
+}
+
+/* Link an a.out input BFD into the output file. */
+
+static bfd_boolean
+aout_link_input_bfd (struct aout_final_link_info *finfo, bfd *input_bfd)
+{
+ bfd_size_type sym_count;
+
+ BFD_ASSERT (bfd_get_format (input_bfd) == bfd_object);
+
+ /* If this is a dynamic object, it may need special handling. */
+ if ((input_bfd->flags & DYNAMIC) != 0
+ && aout_backend_info (input_bfd)->link_dynamic_object != NULL)
+ return ((*aout_backend_info (input_bfd)->link_dynamic_object)
+ (finfo->info, input_bfd));
+
+ /* Get the symbols. We probably have them already, unless
+ finfo->info->keep_memory is FALSE. */
+ if (! aout_get_external_symbols (input_bfd))
+ return FALSE;
+
+ sym_count = obj_aout_external_sym_count (input_bfd);
+
+ /* Write out the symbols and get a map of the new indices. The map
+ is placed into finfo->symbol_map. */
+ if (! aout_link_write_symbols (finfo, input_bfd))
+ return FALSE;
+
+ /* Relocate and write out the sections. These functions use the
+ symbol map created by aout_link_write_symbols. The linker_mark
+ field will be set if these sections are to be included in the
+ link, which will normally be the case. */
+ if (obj_textsec (input_bfd)->linker_mark)
+ {
+ if (! aout_link_input_section (finfo, input_bfd,
+ obj_textsec (input_bfd),
+ &finfo->treloff,
+ exec_hdr (input_bfd)->a_trsize))
+ return FALSE;
+ }
+ if (obj_datasec (input_bfd)->linker_mark)
+ {
+ if (! aout_link_input_section (finfo, input_bfd,
+ obj_datasec (input_bfd),
+ &finfo->dreloff,
+ exec_hdr (input_bfd)->a_drsize))
return FALSE;
- size = outsym - finfo->output_syms;
- size *= EXTERNAL_NLIST_SIZE;
- if (bfd_bwrite ((PTR) finfo->output_syms, size, output_bfd) != size)
+ }
+
+ /* If we are not keeping memory, we don't need the symbols any
+ longer. We still need them if we are keeping memory, because the
+ strings in the hash table point into them. */
+ if (! finfo->info->keep_memory)
+ {
+ if (! aout_link_free_symbols (input_bfd))
return FALSE;
- finfo->symoff += size;
}
return TRUE;
}
-/* Write out a symbol that was not associated with an a.out input
- object. */
+/* Do the final link step. This is called on the output BFD. The
+ INFO structure should point to a list of BFDs linked through the
+ link_next field which can be used to find each BFD which takes part
+ in the output. Also, each section in ABFD should point to a list
+ of bfd_link_order structures which list all the input sections for
+ the output section. */
-static bfd_boolean
-aout_link_write_other_symbol (h, data)
- struct aout_link_hash_entry *h;
- PTR data;
+bfd_boolean
+NAME (aout, final_link) (bfd *abfd,
+ struct bfd_link_info *info,
+ void (*callback) (bfd *, file_ptr *, file_ptr *, file_ptr *))
{
- struct aout_final_link_info *finfo = (struct aout_final_link_info *) data;
- bfd *output_bfd;
- int type;
- bfd_vma val;
- struct external_nlist outsym;
- bfd_size_type indx;
- bfd_size_type amt;
+ struct aout_final_link_info aout_info;
+ bfd_boolean includes_hash_initialized = FALSE;
+ bfd *sub;
+ bfd_size_type trsize, drsize;
+ bfd_size_type max_contents_size;
+ bfd_size_type max_relocs_size;
+ bfd_size_type max_sym_count;
+ bfd_size_type text_size;
+ file_ptr text_end;
+ struct bfd_link_order *p;
+ asection *o;
+ bfd_boolean have_link_order_relocs;
- if (h->root.type == bfd_link_hash_warning)
- {
- h = (struct aout_link_hash_entry *) h->root.u.i.link;
- if (h->root.type == bfd_link_hash_new)
- return TRUE;
- }
+ if (info->shared)
+ abfd->flags |= DYNAMIC;
- output_bfd = finfo->output_bfd;
+ aout_info.info = info;
+ aout_info.output_bfd = abfd;
+ aout_info.contents = NULL;
+ aout_info.relocs = NULL;
+ aout_info.symbol_map = NULL;
+ aout_info.output_syms = NULL;
- if (aout_backend_info (output_bfd)->write_dynamic_symbol != NULL)
+ if (! bfd_hash_table_init_n (&aout_info.includes.root,
+ aout_link_includes_newfunc,
+ 251))
+ goto error_return;
+ includes_hash_initialized = TRUE;
+
+ /* Figure out the largest section size. Also, if generating
+ relocatable output, count the relocs. */
+ trsize = 0;
+ drsize = 0;
+ max_contents_size = 0;
+ max_relocs_size = 0;
+ max_sym_count = 0;
+ for (sub = info->input_bfds; sub != NULL; sub = sub->link_next)
{
- if (! ((*aout_backend_info (output_bfd)->write_dynamic_symbol)
- (output_bfd, finfo->info, h)))
+ size_t sz;
+
+ if (info->relocatable)
{
- /* FIXME: No way to handle errors. */
- abort ();
+ if (bfd_get_flavour (sub) == bfd_target_aout_flavour)
+ {
+ trsize += exec_hdr (sub)->a_trsize;
+ drsize += exec_hdr (sub)->a_drsize;
+ }
+ else
+ {
+ /* FIXME: We need to identify the .text and .data sections
+ and call get_reloc_upper_bound and canonicalize_reloc to
+ work out the number of relocs needed, and then multiply
+ by the reloc size. */
+ (*_bfd_error_handler)
+ ("%s: relocatable link from %s to %s not supported",
+ bfd_get_filename (abfd),
+ sub->xvec->name, abfd->xvec->name);
+ bfd_set_error (bfd_error_invalid_operation);
+ goto error_return;
+ }
}
- }
-
- if (h->written)
- return TRUE;
-
- h->written = TRUE;
- /* An indx of -2 means the symbol must be written. */
- if (h->indx != -2
- && (finfo->info->strip == strip_all
- || (finfo->info->strip == strip_some
- && bfd_hash_lookup (finfo->info->keep_hash, h->root.root.string,
- FALSE, FALSE) == NULL)))
- return TRUE;
+ if (bfd_get_flavour (sub) == bfd_target_aout_flavour)
+ {
+ sz = obj_textsec (sub)->size;
+ if (sz > max_contents_size)
+ max_contents_size = sz;
+ sz = obj_datasec (sub)->size;
+ if (sz > max_contents_size)
+ max_contents_size = sz;
- switch (h->root.type)
- {
- default:
- abort ();
- /* Avoid variable not initialized warnings. */
- return TRUE;
- case bfd_link_hash_new:
- /* This can happen for set symbols when sets are not being
- built. */
- return TRUE;
- case bfd_link_hash_undefined:
- type = N_UNDF | N_EXT;
- val = 0;
- break;
- case bfd_link_hash_defined:
- case bfd_link_hash_defweak:
- {
- asection *sec;
+ sz = exec_hdr (sub)->a_trsize;
+ if (sz > max_relocs_size)
+ max_relocs_size = sz;
+ sz = exec_hdr (sub)->a_drsize;
+ if (sz > max_relocs_size)
+ max_relocs_size = sz;
- sec = h->root.u.def.section->output_section;
- BFD_ASSERT (bfd_is_abs_section (sec)
- || sec->owner == output_bfd);
- if (sec == obj_textsec (output_bfd))
- type = h->root.type == bfd_link_hash_defined ? N_TEXT : N_WEAKT;
- else if (sec == obj_datasec (output_bfd))
- type = h->root.type == bfd_link_hash_defined ? N_DATA : N_WEAKD;
- else if (sec == obj_bsssec (output_bfd))
- type = h->root.type == bfd_link_hash_defined ? N_BSS : N_WEAKB;
- else
- type = h->root.type == bfd_link_hash_defined ? N_ABS : N_WEAKA;
- type |= N_EXT;
- val = (h->root.u.def.value
- + sec->vma
- + h->root.u.def.section->output_offset);
- }
- break;
- case bfd_link_hash_common:
- type = N_UNDF | N_EXT;
- val = h->root.u.c.size;
- break;
- case bfd_link_hash_undefweak:
- type = N_WEAKU;
- val = 0;
- case bfd_link_hash_indirect:
- case bfd_link_hash_warning:
- /* FIXME: Ignore these for now. The circumstances under which
- they should be written out are not clear to me. */
- return TRUE;
+ sz = obj_aout_external_sym_count (sub);
+ if (sz > max_sym_count)
+ max_sym_count = sz;
+ }
}
- H_PUT_8 (output_bfd, type, outsym.e_type);
- indx = add_to_stringtab (output_bfd, finfo->strtab, h->root.root.string,
- FALSE);
- if (indx == (bfd_size_type) -1)
+ if (info->relocatable)
{
- /* FIXME: No way to handle errors. */
- abort ();
+ if (obj_textsec (abfd) != NULL)
+ trsize += (_bfd_count_link_order_relocs (obj_textsec (abfd)
+ ->link_order_head)
+ * obj_reloc_entry_size (abfd));
+ if (obj_datasec (abfd) != NULL)
+ drsize += (_bfd_count_link_order_relocs (obj_datasec (abfd)
+ ->link_order_head)
+ * obj_reloc_entry_size (abfd));
}
- PUT_WORD (output_bfd, indx, outsym.e_strx);
- PUT_WORD (output_bfd, val, outsym.e_value);
- amt = EXTERNAL_NLIST_SIZE;
- if (bfd_seek (output_bfd, finfo->symoff, SEEK_SET) != 0
- || bfd_bwrite ((PTR) &outsym, amt, output_bfd) != amt)
+ exec_hdr (abfd)->a_trsize = trsize;
+ exec_hdr (abfd)->a_drsize = drsize;
+ exec_hdr (abfd)->a_entry = bfd_get_start_address (abfd);
+
+ /* Adjust the section sizes and vmas according to the magic number.
+ This sets a_text, a_data and a_bss in the exec_hdr and sets the
+ filepos for each section. */
+ if (! NAME (aout, adjust_sizes_and_vmas) (abfd, &text_size, &text_end))
+ goto error_return;
+
+ /* The relocation and symbol file positions differ among a.out
+ targets. We are passed a callback routine from the backend
+ specific code to handle this.
+ FIXME: At this point we do not know how much space the symbol
+ table will require. This will not work for any (nonstandard)
+ a.out target that needs to know the symbol table size before it
+ can compute the relocation file positions. This may or may not
+ be the case for the hp300hpux target, for example. */
+ (*callback) (abfd, &aout_info.treloff, &aout_info.dreloff,
+ &aout_info.symoff);
+ obj_textsec (abfd)->rel_filepos = aout_info.treloff;
+ obj_datasec (abfd)->rel_filepos = aout_info.dreloff;
+ obj_sym_filepos (abfd) = aout_info.symoff;
+
+ /* We keep a count of the symbols as we output them. */
+ obj_aout_external_sym_count (abfd) = 0;
+
+ /* We accumulate the string table as we write out the symbols. */
+ aout_info.strtab = _bfd_stringtab_init ();
+ if (aout_info.strtab == NULL)
+ goto error_return;
+
+ /* Allocate buffers to hold section contents and relocs. */
+ aout_info.contents = bfd_malloc (max_contents_size);
+ aout_info.relocs = bfd_malloc (max_relocs_size);
+ aout_info.symbol_map = bfd_malloc (max_sym_count * sizeof (int *));
+ aout_info.output_syms = bfd_malloc ((max_sym_count + 1)
+ * sizeof (struct external_nlist));
+ if ((aout_info.contents == NULL && max_contents_size != 0)
+ || (aout_info.relocs == NULL && max_relocs_size != 0)
+ || (aout_info.symbol_map == NULL && max_sym_count != 0)
+ || aout_info.output_syms == NULL)
+ goto error_return;
+
+ /* If we have a symbol named __DYNAMIC, force it out now. This is
+ required by SunOS. Doing this here rather than in sunos.c is a
+ hack, but it's easier than exporting everything which would be
+ needed. */
+ {
+ struct aout_link_hash_entry *h;
+
+ h = aout_link_hash_lookup (aout_hash_table (info), "__DYNAMIC",
+ FALSE, FALSE, FALSE);
+ if (h != NULL)
+ aout_link_write_other_symbol (h, &aout_info);
+ }
+
+ /* The most time efficient way to do the link would be to read all
+ the input object files into memory and then sort out the
+ information into the output file. Unfortunately, that will
+ probably use too much memory. Another method would be to step
+ through everything that composes the text section and write it
+ out, and then everything that composes the data section and write
+ it out, and then write out the relocs, and then write out the
+ symbols. Unfortunately, that requires reading stuff from each
+ input file several times, and we will not be able to keep all the
+ input files open simultaneously, and reopening them will be slow.
+
+ What we do is basically process one input file at a time. We do
+ everything we need to do with an input file once--copy over the
+ section contents, handle the relocation information, and write
+ out the symbols--and then we throw away the information we read
+ from it. This approach requires a lot of lseeks of the output
+ file, which is unfortunate but still faster than reopening a lot
+ of files.
+
+ We use the output_has_begun field of the input BFDs to see
+ whether we have already handled it. */
+ for (sub = info->input_bfds; sub != NULL; sub = sub->link_next)
+ sub->output_has_begun = FALSE;
+
+ /* Mark all sections which are to be included in the link. This
+ will normally be every section. We need to do this so that we
+ can identify any sections which the linker has decided to not
+ include. */
+ for (o = abfd->sections; o != NULL; o = o->next)
{
- /* FIXME: No way to handle errors. */
- abort ();
+ for (p = o->link_order_head; p != NULL; p = p->next)
+ if (p->type == bfd_indirect_link_order)
+ p->u.indirect.section->linker_mark = TRUE;
}
- finfo->symoff += amt;
- h->indx = obj_aout_external_sym_count (output_bfd);
- ++obj_aout_external_sym_count (output_bfd);
-
- return TRUE;
-}
-
-/* Link an a.out section into the output file. */
+ have_link_order_relocs = FALSE;
+ for (o = abfd->sections; o != NULL; o = o->next)
+ {
+ for (p = o->link_order_head;
+ p != NULL;
+ p = p->next)
+ {
+ if (p->type == bfd_indirect_link_order
+ && (bfd_get_flavour (p->u.indirect.section->owner)
+ == bfd_target_aout_flavour))
+ {
+ bfd *input_bfd;
-static bfd_boolean
-aout_link_input_section (finfo, input_bfd, input_section, reloff_ptr,
- rel_size)
- struct aout_final_link_info *finfo;
- bfd *input_bfd;
- asection *input_section;
- file_ptr *reloff_ptr;
- bfd_size_type rel_size;
-{
- bfd_size_type input_size;
- PTR relocs;
+ input_bfd = p->u.indirect.section->owner;
+ if (! input_bfd->output_has_begun)
+ {
+ if (! aout_link_input_bfd (&aout_info, input_bfd))
+ goto error_return;
+ input_bfd->output_has_begun = TRUE;
+ }
+ }
+ else if (p->type == bfd_section_reloc_link_order
+ || p->type == bfd_symbol_reloc_link_order)
+ /* These are handled below. */
+ have_link_order_relocs = TRUE;
+ else
+ {
+ if (! _bfd_default_link_order (abfd, info, o, p))
+ goto error_return;
+ }
+ }
+ }
- /* Get the section contents. */
- input_size = input_section->size;
- if (! bfd_get_section_contents (input_bfd, input_section,
- (PTR) finfo->contents,
- (file_ptr) 0, input_size))
- return FALSE;
+ /* Write out any symbols that we have not already written out. */
+ aout_link_hash_traverse (aout_hash_table (info),
+ aout_link_write_other_symbol,
+ (void *) &aout_info);
- /* Read in the relocs if we haven't already done it. */
- if (aout_section_data (input_section) != NULL
- && aout_section_data (input_section)->relocs != NULL)
- relocs = aout_section_data (input_section)->relocs;
- else
+ /* Now handle any relocs we were asked to create by the linker.
+ These did not come from any input file. We must do these after
+ we have written out all the symbols, so that we know the symbol
+ indices to use. */
+ if (have_link_order_relocs)
{
- relocs = finfo->relocs;
- if (rel_size > 0)
+ for (o = abfd->sections; o != NULL; o = o->next)
{
- if (bfd_seek (input_bfd, input_section->rel_filepos, SEEK_SET) != 0
- || bfd_bread (relocs, rel_size, input_bfd) != rel_size)
- return FALSE;
+ for (p = o->link_order_head;
+ p != NULL;
+ p = p->next)
+ {
+ if (p->type == bfd_section_reloc_link_order
+ || p->type == bfd_symbol_reloc_link_order)
+ {
+ if (! aout_link_reloc_link_order (&aout_info, o, p))
+ goto error_return;
+ }
+ }
}
}
- /* Relocate the section contents. */
- if (! pdp11_aout_link_input_section (finfo, input_bfd, input_section,
- (bfd_byte *) relocs,
- rel_size, finfo->contents))
- return FALSE;
+ if (aout_info.contents != NULL)
+ {
+ free (aout_info.contents);
+ aout_info.contents = NULL;
+ }
+ if (aout_info.relocs != NULL)
+ {
+ free (aout_info.relocs);
+ aout_info.relocs = NULL;
+ }
+ if (aout_info.symbol_map != NULL)
+ {
+ free (aout_info.symbol_map);
+ aout_info.symbol_map = NULL;
+ }
+ if (aout_info.output_syms != NULL)
+ {
+ free (aout_info.output_syms);
+ aout_info.output_syms = NULL;
+ }
+ if (includes_hash_initialized)
+ {
+ bfd_hash_table_free (&aout_info.includes.root);
+ includes_hash_initialized = FALSE;
+ }
- /* Write out the section contents. */
- if (! bfd_set_section_contents (finfo->output_bfd,
- input_section->output_section,
- (PTR) finfo->contents,
- (file_ptr) input_section->output_offset,
- input_size))
- return FALSE;
+ /* Finish up any dynamic linking we may be doing. */
+ if (aout_backend_info (abfd)->finish_dynamic_link != NULL)
+ {
+ if (! (*aout_backend_info (abfd)->finish_dynamic_link) (abfd, info))
+ goto error_return;
+ }
- /* If we are producing relocatable output, the relocs were
- modified, and we now write them out. */
- if (finfo->info->relocatable && rel_size > 0)
+ /* Update the header information. */
+ abfd->symcount = obj_aout_external_sym_count (abfd);
+ exec_hdr (abfd)->a_syms = abfd->symcount * EXTERNAL_NLIST_SIZE;
+ obj_str_filepos (abfd) = obj_sym_filepos (abfd) + exec_hdr (abfd)->a_syms;
+ obj_textsec (abfd)->reloc_count =
+ exec_hdr (abfd)->a_trsize / obj_reloc_entry_size (abfd);
+ obj_datasec (abfd)->reloc_count =
+ exec_hdr (abfd)->a_drsize / obj_reloc_entry_size (abfd);
+
+ /* Write out the string table, unless there are no symbols. */
+ if (abfd->symcount > 0)
{
- if (bfd_seek (finfo->output_bfd, *reloff_ptr, SEEK_SET) != 0)
- return FALSE;
- if (bfd_bwrite (relocs, rel_size, finfo->output_bfd) != rel_size)
- return FALSE;
- *reloff_ptr += rel_size;
+ if (bfd_seek (abfd, obj_str_filepos (abfd), SEEK_SET) != 0
+ || ! emit_stringtab (abfd, aout_info.strtab))
+ goto error_return;
+ }
+ else if (obj_textsec (abfd)->reloc_count == 0
+ && obj_datasec (abfd)->reloc_count == 0)
+ {
+ bfd_byte b;
- /* Assert that the relocs have not run into the symbols, and
- that if these are the text relocs they have not run into the
- data relocs. */
- BFD_ASSERT (*reloff_ptr <= obj_sym_filepos (finfo->output_bfd)
- && (reloff_ptr != &finfo->treloff
- || (*reloff_ptr
- <= obj_datasec (finfo->output_bfd)->rel_filepos)));
+ b = 0;
+ if (bfd_seek (abfd,
+ (file_ptr) (obj_datasec (abfd)->filepos
+ + exec_hdr (abfd)->a_data
+ - 1),
+ SEEK_SET) != 0
+ || bfd_bwrite (&b, (bfd_size_type) 1, abfd) != 1)
+ goto error_return;
}
return TRUE;
-}
-
-/* Get the section corresponding to a reloc index. */
-static INLINE asection *
-aout_reloc_type_to_section (abfd, type)
- bfd *abfd;
- int type;
-{
- switch (type)
- {
- case RTEXT:
- return obj_textsec (abfd);
- case RDATA:
- return obj_datasec (abfd);
- case RBSS:
- return obj_bsssec (abfd);
- case RABS:
- return bfd_abs_section_ptr;
- case REXT:
- return bfd_und_section_ptr;
- default:
- abort ();
- }
+ error_return:
+ if (aout_info.contents != NULL)
+ free (aout_info.contents);
+ if (aout_info.relocs != NULL)
+ free (aout_info.relocs);
+ if (aout_info.symbol_map != NULL)
+ free (aout_info.symbol_map);
+ if (aout_info.output_syms != NULL)
+ free (aout_info.output_syms);
+ if (includes_hash_initialized)
+ bfd_hash_table_free (&aout_info.includes.root);
+ return FALSE;
}
+/* Adjust and write out the symbols for an a.out file. Set the new
+ symbol indices into a symbol_map. */
+
static bfd_boolean
-pdp11_aout_link_input_section (finfo, input_bfd, input_section, relocs,
- rel_size, contents)
- struct aout_final_link_info *finfo;
- bfd *input_bfd;
- asection *input_section;
- bfd_byte *relocs;
- bfd_size_type rel_size;
- bfd_byte *contents;
+aout_link_write_symbols (struct aout_final_link_info *finfo, bfd *input_bfd)
{
- bfd_boolean (*check_dynamic_reloc)
- PARAMS ((struct bfd_link_info *, bfd *, asection *,
- struct aout_link_hash_entry *, PTR, bfd_byte *, bfd_boolean *,
- bfd_vma *));
bfd *output_bfd;
- bfd_boolean relocatable;
- struct external_nlist *syms;
+ bfd_size_type sym_count;
char *strings;
- struct aout_link_hash_entry **sym_hashes;
+ enum bfd_link_strip strip;
+ enum bfd_link_discard discard;
+ struct external_nlist *outsym;
+ bfd_size_type strtab_index;
+ struct external_nlist *sym;
+ struct external_nlist *sym_end;
+ struct aout_link_hash_entry **sym_hash;
int *symbol_map;
- bfd_size_type reloc_count;
- bfd_byte *rel;
- bfd_byte *rel_end;
+ bfd_boolean pass;
+ bfd_boolean skip_next;
output_bfd = finfo->output_bfd;
- check_dynamic_reloc = aout_backend_info (output_bfd)->check_dynamic_reloc;
-
- BFD_ASSERT (obj_reloc_entry_size (input_bfd) == RELOC_SIZE);
- BFD_ASSERT (input_bfd->xvec->header_byteorder
- == output_bfd->xvec->header_byteorder);
-
- relocatable = finfo->info->relocatable;
- syms = obj_aout_external_syms (input_bfd);
+ sym_count = obj_aout_external_sym_count (input_bfd);
strings = obj_aout_external_strings (input_bfd);
- sym_hashes = obj_aout_sym_hashes (input_bfd);
- symbol_map = finfo->symbol_map;
+ strip = finfo->info->strip;
+ discard = finfo->info->discard;
+ outsym = finfo->output_syms;
- reloc_count = rel_size / RELOC_SIZE;
- rel = relocs;
- rel_end = rel + rel_size;
- for (; rel < rel_end; rel += RELOC_SIZE)
+ /* First write out a symbol for this object file, unless we are
+ discarding such symbols. */
+ if (strip != strip_all
+ && (strip != strip_some
+ || bfd_hash_lookup (finfo->info->keep_hash, input_bfd->filename,
+ FALSE, FALSE) != NULL)
+ && discard != discard_all)
+ {
+ H_PUT_8 (output_bfd, N_TEXT, outsym->e_type);
+ strtab_index = add_to_stringtab (output_bfd, finfo->strtab,
+ input_bfd->filename, FALSE);
+ if (strtab_index == (bfd_size_type) -1)
+ return FALSE;
+ PUT_WORD (output_bfd, strtab_index, outsym->e_strx);
+ PUT_WORD (output_bfd,
+ (bfd_get_section_vma (output_bfd,
+ obj_textsec (input_bfd)->output_section)
+ + obj_textsec (input_bfd)->output_offset),
+ outsym->e_value);
+ ++obj_aout_external_sym_count (output_bfd);
+ ++outsym;
+ }
+
+ pass = FALSE;
+ skip_next = FALSE;
+ sym = obj_aout_external_syms (input_bfd);
+ sym_end = sym + sym_count;
+ sym_hash = obj_aout_sym_hashes (input_bfd);
+ symbol_map = finfo->symbol_map;
+ memset (symbol_map, 0, (size_t) sym_count * sizeof *symbol_map);
+ for (; sym < sym_end; sym++, sym_hash++, symbol_map++)
{
- bfd_vma r_addr;
- int r_index;
- int r_type;
- int r_pcrel;
- int r_extern;
- reloc_howto_type *howto;
- struct aout_link_hash_entry *h = NULL;
- bfd_vma relocation;
- bfd_reloc_status_type r;
- int reloc_entry;
+ const char *name;
+ int type;
+ struct aout_link_hash_entry *h;
+ bfd_boolean skip;
+ asection *symsec;
+ bfd_vma val = 0;
+ bfd_boolean copy;
- reloc_entry = GET_WORD (input_bfd, (PTR)rel);
- if (reloc_entry == 0)
+ /* We set *symbol_map to 0 above for all symbols. If it has
+ already been set to -1 for this symbol, it means that we are
+ discarding it because it appears in a duplicate header file.
+ See the N_BINCL code below. */
+ if (*symbol_map == -1)
continue;
- {
- unsigned int howto_idx;
-
- r_index = (reloc_entry & RIDXMASK) >> 4;
- r_type = reloc_entry & RTYPE;
- r_pcrel = reloc_entry & RELFLG;
- r_addr = (char *)rel - (char *)relocs;
+ /* Initialize *symbol_map to -1, which means that the symbol was
+ not copied into the output file. We will change it later if
+ we do copy the symbol over. */
+ *symbol_map = -1;
- r_extern = (r_type == REXT);
+ type = H_GET_8 (input_bfd, sym->e_type);
+ name = strings + GET_WORD (input_bfd, sym->e_strx);
- howto_idx = r_pcrel;
- BFD_ASSERT (howto_idx < TABLE_SIZE (howto_table_pdp11));
- howto = howto_table_pdp11 + howto_idx;
- }
+ h = NULL;
- if (relocatable)
+ if (pass)
{
- /* We are generating a relocatable output file, and must
- modify the reloc accordingly. */
- if (r_extern)
- {
- /* If we know the symbol this relocation is against,
- convert it into a relocation against a section. This
- is what the native linker does. */
- h = sym_hashes[r_index];
- if (h != (struct aout_link_hash_entry *) NULL
- && (h->root.type == bfd_link_hash_defined
- || h->root.type == bfd_link_hash_defweak))
- {
- asection *output_section;
-
- /* Compute a new r_index. */
- output_section = h->root.u.def.section->output_section;
- if (output_section == obj_textsec (output_bfd))
- r_type = N_TEXT;
- else if (output_section == obj_datasec (output_bfd))
- r_type = N_DATA;
- else if (output_section == obj_bsssec (output_bfd))
- r_type = N_BSS;
- else
- r_type = N_ABS;
+ /* Pass this symbol through. It is the target of an
+ indirect or warning symbol. */
+ val = GET_WORD (input_bfd, sym->e_value);
+ pass = FALSE;
+ }
+ else if (skip_next)
+ {
+ /* Skip this symbol, which is the target of an indirect
+ symbol that we have changed to no longer be an indirect
+ symbol. */
+ skip_next = FALSE;
+ continue;
+ }
+ else
+ {
+ struct aout_link_hash_entry *hresolve;
- /* Add the symbol value and the section VMA to the
- addend stored in the contents. */
- relocation = (h->root.u.def.value
- + output_section->vma
- + h->root.u.def.section->output_offset);
- }
- else
- {
- /* We must change r_index according to the symbol
- map. */
- r_index = symbol_map[r_index];
+ /* We have saved the hash table entry for this symbol, if
+ there is one. Note that we could just look it up again
+ in the hash table, provided we first check that it is an
+ external symbol. */
+ h = *sym_hash;
- if (r_index == -1)
- {
- if (h != NULL)
- {
- /* We decided to strip this symbol, but it
- turns out that we can't. Note that we
- lose the other and desc information here.
- I don't think that will ever matter for a
- global symbol. */
- if (h->indx < 0)
- {
- h->indx = -2;
- h->written = FALSE;
- if (! aout_link_write_other_symbol (h,
- (PTR) finfo))
- return FALSE;
- }
- r_index = h->indx;
- }
- else
- {
- const char *name;
+ /* Use the name from the hash table, in case the symbol was
+ wrapped. */
+ if (h != NULL)
+ name = h->root.root.string;
- name = strings + GET_WORD (input_bfd,
- syms[r_index].e_strx);
- if (! ((*finfo->info->callbacks->unattached_reloc)
- (finfo->info, name, input_bfd, input_section,
- r_addr)))
- return FALSE;
- r_index = 0;
- }
- }
+ /* If this is an indirect or warning symbol, then change
+ hresolve to the base symbol. We also change *sym_hash so
+ that the relocation routines relocate against the real
+ symbol. */
+ hresolve = h;
+ if (h != NULL
+ && (h->root.type == bfd_link_hash_indirect
+ || h->root.type == bfd_link_hash_warning))
+ {
+ hresolve = (struct aout_link_hash_entry *) h->root.u.i.link;
+ while (hresolve->root.type == bfd_link_hash_indirect
+ || hresolve->root.type == bfd_link_hash_warning)
+ hresolve = ((struct aout_link_hash_entry *)
+ hresolve->root.u.i.link);
+ *sym_hash = hresolve;
+ }
- relocation = 0;
- }
+ /* If the symbol has already been written out, skip it. */
+ if (h != NULL
+ && h->root.type != bfd_link_hash_warning
+ && h->written)
+ {
+ if ((type & N_TYPE) == N_INDR
+ || type == N_WARNING)
+ skip_next = TRUE;
+ *symbol_map = h->indx;
+ continue;
+ }
- /* Write out the new r_index value. */
- reloc_entry = GET_WORD (input_bfd, rel);
- reloc_entry &= RIDXMASK;
- reloc_entry |= r_index << 4;
- PUT_WORD (input_bfd, reloc_entry, rel);
+ /* See if we are stripping this symbol. */
+ skip = FALSE;
+ switch (strip)
+ {
+ case strip_none:
+ break;
+ case strip_debugger:
+ if ((type & N_STAB) != 0)
+ skip = TRUE;
+ break;
+ case strip_some:
+ if (bfd_hash_lookup (finfo->info->keep_hash, name, FALSE, FALSE)
+ == NULL)
+ skip = TRUE;
+ break;
+ case strip_all:
+ skip = TRUE;
+ break;
}
- else
+ if (skip)
{
- asection *section;
+ if (h != NULL)
+ h->written = TRUE;
+ continue;
+ }
- /* This is a relocation against a section. We must
- adjust by the amount that the section moved. */
- section = aout_reloc_type_to_section (input_bfd, r_type);
- relocation = (section->output_section->vma
- + section->output_offset
- - section->vma);
+ /* Get the value of the symbol. */
+ if ((type & N_TYPE) == N_TEXT
+ || type == N_WEAKT)
+ symsec = obj_textsec (input_bfd);
+ else if ((type & N_TYPE) == N_DATA
+ || type == N_WEAKD)
+ symsec = obj_datasec (input_bfd);
+ else if ((type & N_TYPE) == N_BSS
+ || type == N_WEAKB)
+ symsec = obj_bsssec (input_bfd);
+ else if ((type & N_TYPE) == N_ABS
+ || type == N_WEAKA)
+ symsec = bfd_abs_section_ptr;
+ else if (((type & N_TYPE) == N_INDR
+ && (hresolve == NULL
+ || (hresolve->root.type != bfd_link_hash_defined
+ && hresolve->root.type != bfd_link_hash_defweak
+ && hresolve->root.type != bfd_link_hash_common)))
+ || type == N_WARNING)
+ {
+ /* Pass the next symbol through unchanged. The
+ condition above for indirect symbols is so that if
+ the indirect symbol was defined, we output it with
+ the correct definition so the debugger will
+ understand it. */
+ pass = TRUE;
+ val = GET_WORD (input_bfd, sym->e_value);
+ symsec = NULL;
+ }
+ else if ((type & N_STAB) != 0)
+ {
+ val = GET_WORD (input_bfd, sym->e_value);
+ symsec = NULL;
}
+ else
+ {
+ /* If we get here with an indirect symbol, it means that
+ we are outputting it with a real definition. In such
+ a case we do not want to output the next symbol,
+ which is the target of the indirection. */
+ if ((type & N_TYPE) == N_INDR)
+ skip_next = TRUE;
- /* Change the address of the relocation. */
- fprintf (stderr, "TODO: change the address of the relocation\n");
+ symsec = NULL;
- /* Adjust a PC relative relocation by removing the reference
- to the original address in the section and including the
- reference to the new address. */
- if (r_pcrel)
- relocation -= (input_section->output_section->vma
- + input_section->output_offset
- - input_section->vma);
+ /* We need to get the value from the hash table. We use
+ hresolve so that if we have defined an indirect
+ symbol we output the final definition. */
+ if (h == NULL)
+ {
+ switch (type & N_TYPE)
+ {
+ case N_SETT:
+ symsec = obj_textsec (input_bfd);
+ break;
+ case N_SETD:
+ symsec = obj_datasec (input_bfd);
+ break;
+ case N_SETB:
+ symsec = obj_bsssec (input_bfd);
+ break;
+ case N_SETA:
+ symsec = bfd_abs_section_ptr;
+ break;
+ default:
+ val = 0;
+ break;
+ }
+ }
+ else if (hresolve->root.type == bfd_link_hash_defined
+ || hresolve->root.type == bfd_link_hash_defweak)
+ {
+ asection *input_section;
+ asection *output_section;
-#ifdef MY_relocatable_reloc
- MY_relocatable_reloc (howto, output_bfd, rel, relocation, r_addr);
-#endif
+ /* This case usually means a common symbol which was
+ turned into a defined symbol. */
+ input_section = hresolve->root.u.def.section;
+ output_section = input_section->output_section;
+ BFD_ASSERT (bfd_is_abs_section (output_section)
+ || output_section->owner == output_bfd);
+ val = (hresolve->root.u.def.value
+ + bfd_get_section_vma (output_bfd, output_section)
+ + input_section->output_offset);
- if (relocation == 0)
- r = bfd_reloc_ok;
- else
- r = MY_relocate_contents (howto,
- input_bfd, relocation,
- contents + r_addr);
- }
- else
- {
- bfd_boolean hundef;
+ /* Get the correct type based on the section. If
+ this is a constructed set, force it to be
+ globally visible. */
+ if (type == N_SETT
+ || type == N_SETD
+ || type == N_SETB
+ || type == N_SETA)
+ type |= N_EXT;
- /* We are generating an executable, and must do a full
- relocation. */
- hundef = FALSE;
- if (r_extern)
- {
- h = sym_hashes[r_index];
+ type &=~ N_TYPE;
- if (h != (struct aout_link_hash_entry *) NULL
- && (h->root.type == bfd_link_hash_defined
- || h->root.type == bfd_link_hash_defweak))
- {
- relocation = (h->root.u.def.value
- + h->root.u.def.section->output_section->vma
- + h->root.u.def.section->output_offset);
+ if (output_section == obj_textsec (output_bfd))
+ type |= (hresolve->root.type == bfd_link_hash_defined
+ ? N_TEXT
+ : N_WEAKT);
+ else if (output_section == obj_datasec (output_bfd))
+ type |= (hresolve->root.type == bfd_link_hash_defined
+ ? N_DATA
+ : N_WEAKD);
+ else if (output_section == obj_bsssec (output_bfd))
+ type |= (hresolve->root.type == bfd_link_hash_defined
+ ? N_BSS
+ : N_WEAKB);
+ else
+ type |= (hresolve->root.type == bfd_link_hash_defined
+ ? N_ABS
+ : N_WEAKA);
}
- else if (h != (struct aout_link_hash_entry *) NULL
- && h->root.type == bfd_link_hash_undefweak)
- relocation = 0;
- else
+ else if (hresolve->root.type == bfd_link_hash_common)
+ val = hresolve->root.u.c.size;
+ else if (hresolve->root.type == bfd_link_hash_undefweak)
{
- hundef = TRUE;
- relocation = 0;
+ val = 0;
+ type = N_WEAKU;
}
+ else
+ val = 0;
}
- else
- {
- asection *section;
-
- section = aout_reloc_type_to_section (input_bfd, r_type);
- relocation = (section->output_section->vma
- + section->output_offset
- - section->vma);
- if (r_pcrel)
- relocation += input_section->vma;
- }
+ if (symsec != NULL)
+ val = (symsec->output_section->vma
+ + symsec->output_offset
+ + (GET_WORD (input_bfd, sym->e_value)
+ - symsec->vma));
- if (check_dynamic_reloc != NULL)
+ /* If this is a global symbol set the written flag, and if
+ it is a local symbol see if we should discard it. */
+ if (h != NULL)
{
- bfd_boolean skip;
-
- if (! ((*check_dynamic_reloc)
- (finfo->info, input_bfd, input_section, h,
- (PTR) rel, contents, &skip, &relocation)))
- return FALSE;
- if (skip)
- continue;
+ h->written = TRUE;
+ h->indx = obj_aout_external_sym_count (output_bfd);
}
-
- /* Now warn if a global symbol is undefined. We could not
- do this earlier, because check_dynamic_reloc might want
- to skip this reloc. */
- if (hundef && ! finfo->info->shared)
+ else if ((type & N_TYPE) != N_SETT
+ && (type & N_TYPE) != N_SETD
+ && (type & N_TYPE) != N_SETB
+ && (type & N_TYPE) != N_SETA)
{
- const char *name;
-
- if (h != NULL)
- name = h->root.root.string;
- else
- name = strings + GET_WORD (input_bfd, syms[r_index].e_strx);
- if (! ((*finfo->info->callbacks->undefined_symbol)
- (finfo->info, name, input_bfd, input_section,
- r_addr, TRUE)))
- return FALSE;
+ switch (discard)
+ {
+ case discard_none:
+ case discard_sec_merge:
+ break;
+ case discard_l:
+ if ((type & N_STAB) == 0
+ && bfd_is_local_label_name (input_bfd, name))
+ skip = TRUE;
+ break;
+ case discard_all:
+ skip = TRUE;
+ break;
+ }
+ if (skip)
+ {
+ pass = FALSE;
+ continue;
+ }
}
- r = MY_final_link_relocate (howto,
- input_bfd, input_section,
- contents, r_addr, relocation,
- (bfd_vma) 0);
- }
-
- if (r != bfd_reloc_ok)
- {
- switch (r)
+ /* An N_BINCL symbol indicates the start of the stabs
+ entries for a header file. We need to scan ahead to the
+ next N_EINCL symbol, ignoring nesting, adding up all the
+ characters in the symbol names, not including the file
+ numbers in types (the first number after an open
+ parenthesis). */
+ if (type == N_BINCL)
{
- default:
- case bfd_reloc_outofrange:
- abort ();
- case bfd_reloc_overflow:
- {
- const char *name;
+ struct external_nlist *incl_sym;
+ int nest;
+ struct aout_link_includes_entry *incl_entry;
+ struct aout_link_includes_totals *t;
- if (h != NULL)
- name = NULL;
- else if (r_extern)
- name = strings + GET_WORD (input_bfd,
- syms[r_index].e_strx);
- else
- {
- asection *s;
+ val = 0;
+ nest = 0;
+ for (incl_sym = sym + 1; incl_sym < sym_end; incl_sym++)
+ {
+ int incl_type;
- s = aout_reloc_type_to_section (input_bfd, r_type);
- name = bfd_section_name (input_bfd, s);
- }
- if (! ((*finfo->info->callbacks->reloc_overflow)
- (finfo->info, (h ? &h->root : NULL), name,
- howto->name, (bfd_vma) 0, input_bfd,
- input_section, r_addr)))
- return FALSE;
- }
- break;
- }
- }
- }
+ incl_type = H_GET_8 (input_bfd, incl_sym->e_type);
+ if (incl_type == N_EINCL)
+ {
+ if (nest == 0)
+ break;
+ --nest;
+ }
+ else if (incl_type == N_BINCL)
+ ++nest;
+ else if (nest == 0)
+ {
+ const char *s;
- return TRUE;
-}
+ s = strings + GET_WORD (input_bfd, incl_sym->e_strx);
+ for (; *s != '\0'; s++)
+ {
+ val += *s;
+ if (*s == '(')
+ {
+ /* Skip the file number. */
+ ++s;
+ while (ISDIGIT (*s))
+ ++s;
+ --s;
+ }
+ }
+ }
+ }
-/* Handle a link order which is supposed to generate a reloc. */
+ /* If we have already included a header file with the
+ same value, then replace this one with an N_EXCL
+ symbol. */
+ copy = ! finfo->info->keep_memory;
+ incl_entry = aout_link_includes_lookup (&finfo->includes,
+ name, TRUE, copy);
+ if (incl_entry == NULL)
+ return FALSE;
+ for (t = incl_entry->totals; t != NULL; t = t->next)
+ if (t->total == val)
+ break;
+ if (t == NULL)
+ {
+ /* This is the first time we have seen this header
+ file with this set of stabs strings. */
+ t = bfd_hash_allocate (&finfo->includes.root,
+ sizeof *t);
+ if (t == NULL)
+ return FALSE;
+ t->total = val;
+ t->next = incl_entry->totals;
+ incl_entry->totals = t;
+ }
+ else
+ {
+ int *incl_map;
-static bfd_boolean
-aout_link_reloc_link_order (finfo, o, p)
- struct aout_final_link_info *finfo;
- asection *o;
- struct bfd_link_order *p;
-{
- struct bfd_link_order_reloc *pr;
- int r_index;
- int r_extern;
- reloc_howto_type *howto;
- file_ptr *reloff_ptr;
- struct reloc_std_external srel;
- PTR rel_ptr;
- bfd_size_type rel_size;
+ /* This is a duplicate header file. We must change
+ it to be an N_EXCL entry, and mark all the
+ included symbols to prevent outputting them. */
+ type = N_EXCL;
- pr = p->u.reloc.p;
+ nest = 0;
+ for (incl_sym = sym + 1, incl_map = symbol_map + 1;
+ incl_sym < sym_end;
+ incl_sym++, incl_map++)
+ {
+ int incl_type;
- if (p->type == bfd_section_reloc_link_order)
- {
- r_extern = 0;
- if (bfd_is_abs_section (pr->u.section))
- r_index = N_ABS | N_EXT;
- else
- {
- BFD_ASSERT (pr->u.section->owner == finfo->output_bfd);
- r_index = pr->u.section->target_index;
+ incl_type = H_GET_8 (input_bfd, incl_sym->e_type);
+ if (incl_type == N_EINCL)
+ {
+ if (nest == 0)
+ {
+ *incl_map = -1;
+ break;
+ }
+ --nest;
+ }
+ else if (incl_type == N_BINCL)
+ ++nest;
+ else if (nest == 0)
+ *incl_map = -1;
+ }
+ }
+ }
}
- }
- else
- {
- struct aout_link_hash_entry *h;
- BFD_ASSERT (p->type == bfd_symbol_reloc_link_order);
- r_extern = 1;
- h = ((struct aout_link_hash_entry *)
- bfd_wrapped_link_hash_lookup (finfo->output_bfd, finfo->info,
- pr->u.name, FALSE, FALSE, TRUE));
- if (h != (struct aout_link_hash_entry *) NULL
- && h->indx >= 0)
- r_index = h->indx;
- else if (h != NULL)
- {
- /* We decided to strip this symbol, but it turns out that we
- can't. Note that we lose the other and desc information
- here. I don't think that will ever matter for a global
- symbol. */
- h->indx = -2;
- h->written = FALSE;
- if (! aout_link_write_other_symbol (h, (PTR) finfo))
- return FALSE;
- r_index = h->indx;
- }
- else
+ /* Copy this symbol into the list of symbols we are going to
+ write out. */
+ H_PUT_8 (output_bfd, type, outsym->e_type);
+ copy = FALSE;
+ if (! finfo->info->keep_memory)
{
- if (! ((*finfo->info->callbacks->unattached_reloc)
- (finfo->info, pr->u.name, (bfd *) NULL,
- (asection *) NULL, (bfd_vma) 0)))
- return FALSE;
- r_index = 0;
+ /* name points into a string table which we are going to
+ free. If there is a hash table entry, use that string.
+ Otherwise, copy name into memory. */
+ if (h != NULL)
+ name = h->root.root.string;
+ else
+ copy = TRUE;
}
+ strtab_index = add_to_stringtab (output_bfd, finfo->strtab,
+ name, copy);
+ if (strtab_index == (bfd_size_type) -1)
+ return FALSE;
+ PUT_WORD (output_bfd, strtab_index, outsym->e_strx);
+ PUT_WORD (output_bfd, val, outsym->e_value);
+ *symbol_map = obj_aout_external_sym_count (output_bfd);
+ ++obj_aout_external_sym_count (output_bfd);
+ ++outsym;
}
- howto = bfd_reloc_type_lookup (finfo->output_bfd, pr->reloc);
- if (howto == 0)
- {
- bfd_set_error (bfd_error_bad_value);
- return FALSE;
- }
-
- if (o == obj_textsec (finfo->output_bfd))
- reloff_ptr = &finfo->treloff;
- else if (o == obj_datasec (finfo->output_bfd))
- reloff_ptr = &finfo->dreloff;
- else
- abort ();
-
-#ifdef MY_put_reloc
- MY_put_reloc(finfo->output_bfd, r_extern, r_index, p->offset, howto,
- &srel);
-#else
- {
- int r_pcrel;
- int r_baserel;
- int r_jmptable;
- int r_relative;
- int r_length;
-
- fprintf (stderr, "TODO: line %d in bfd/pdp11.c\n", __LINE__);
-
- r_pcrel = howto->pc_relative;
- r_baserel = (howto->type & 8) != 0;
- r_jmptable = (howto->type & 16) != 0;
- r_relative = (howto->type & 32) != 0;
- r_length = howto->size;
-
- PUT_WORD (finfo->output_bfd, p->offset, srel.r_address);
- if (bfd_header_big_endian (finfo->output_bfd))
- {
- srel.r_index[0] = r_index >> 16;
- srel.r_index[1] = r_index >> 8;
- srel.r_index[2] = r_index;
- srel.r_type[0] =
- ((r_extern ? RELOC_STD_BITS_EXTERN_BIG : 0)
- | (r_pcrel ? RELOC_STD_BITS_PCREL_BIG : 0)
- | (r_baserel ? RELOC_STD_BITS_BASEREL_BIG : 0)
- | (r_jmptable ? RELOC_STD_BITS_JMPTABLE_BIG : 0)
- | (r_relative ? RELOC_STD_BITS_RELATIVE_BIG : 0)
- | (r_length << RELOC_STD_BITS_LENGTH_SH_BIG));
- }
- else
- {
- srel.r_index[2] = r_index >> 16;
- srel.r_index[1] = r_index >> 8;
- srel.r_index[0] = r_index;
- srel.r_type[0] =
- ((r_extern ? RELOC_STD_BITS_EXTERN_LITTLE : 0)
- | (r_pcrel ? RELOC_STD_BITS_PCREL_LITTLE : 0)
- | (r_baserel ? RELOC_STD_BITS_BASEREL_LITTLE : 0)
- | (r_jmptable ? RELOC_STD_BITS_JMPTABLE_LITTLE : 0)
- | (r_relative ? RELOC_STD_BITS_RELATIVE_LITTLE : 0)
- | (r_length << RELOC_STD_BITS_LENGTH_SH_LITTLE));
- }
- }
-#endif
- rel_ptr = (PTR) &srel;
-
- /* We have to write the addend into the object file, since
- standard a.out relocs are in place. It would be more
- reliable if we had the current contents of the file here,
- rather than assuming zeroes, but we can't read the file since
- it was opened using bfd_openw. */
- if (pr->addend != 0)
+ /* Write out the output symbols we have just constructed. */
+ if (outsym > finfo->output_syms)
{
bfd_size_type size;
- bfd_reloc_status_type r;
- bfd_byte *buf;
- bfd_boolean ok;
- size = bfd_get_reloc_size (howto);
- buf = (bfd_byte *) bfd_zmalloc (size);
- if (buf == (bfd_byte *) NULL)
+ if (bfd_seek (output_bfd, finfo->symoff, SEEK_SET) != 0)
return FALSE;
- r = MY_relocate_contents (howto, finfo->output_bfd,
- pr->addend, buf);
- switch (r)
- {
- case bfd_reloc_ok:
- break;
- default:
- case bfd_reloc_outofrange:
- abort ();
- case bfd_reloc_overflow:
- if (! ((*finfo->info->callbacks->reloc_overflow)
- (finfo->info, NULL,
- (p->type == bfd_section_reloc_link_order
- ? bfd_section_name (finfo->output_bfd,
- pr->u.section)
- : pr->u.name),
- howto->name, pr->addend, (bfd *) NULL,
- (asection *) NULL, (bfd_vma) 0)))
- {
- free (buf);
- return FALSE;
- }
- break;
- }
- ok = bfd_set_section_contents (finfo->output_bfd, o,
- (PTR) buf,
- (file_ptr) p->offset,
- size);
- free (buf);
- if (! ok)
+ size = outsym - finfo->output_syms;
+ size *= EXTERNAL_NLIST_SIZE;
+ if (bfd_bwrite ((void *) finfo->output_syms, size, output_bfd) != size)
return FALSE;
+ finfo->symoff += size;
}
- rel_size = obj_reloc_entry_size (finfo->output_bfd);
- if (bfd_seek (finfo->output_bfd, *reloff_ptr, SEEK_SET) != 0
- || bfd_bwrite (rel_ptr, rel_size, finfo->output_bfd) != rel_size)
- return FALSE;
-
- *reloff_ptr += rel_size;
-
- /* Assert that the relocs have not run into the symbols, and that n
- the text relocs have not run into the data relocs. */
- BFD_ASSERT (*reloff_ptr <= obj_sym_filepos (finfo->output_bfd)
- && (reloff_ptr != &finfo->treloff
- || (*reloff_ptr
- <= obj_datasec (finfo->output_bfd)->rel_filepos)));
-
return TRUE;
}
-/* end of modified aoutx.h */
+
+/* Write out a symbol that was not associated with an a.out input
+ object. */
static bfd_vma
bfd_getp32 (const void *p)
{
const bfd_byte *addr = p;
unsigned long v;
+
v = (unsigned long) addr[1] << 24;
v |= (unsigned long) addr[0] << 16;
v |= (unsigned long) addr[3] << 8;
{
const bfd_byte *addr = p;
unsigned long v;
+
v = (unsigned long) addr[1] << 24;
v |= (unsigned long) addr[0] << 16;
v |= (unsigned long) addr[3] << 8;
bfd_putp32 (bfd_vma data, void *p)
{
bfd_byte *addr = p;
+
addr[0] = (data >> 16) & 0xff;
addr[1] = (data >> 24) & 0xff;
addr[2] = (data >> 0) & 0xff;
addr[3] = (data >> 8) & 0xff;
}
+
+const bfd_target MY (vec) =
+{
+ TARGETNAME, /* Name. */
+ bfd_target_aout_flavour,
+ BFD_ENDIAN_LITTLE, /* Target byte order (little). */
+ BFD_ENDIAN_LITTLE, /* Target headers byte order (little). */
+ (HAS_RELOC | EXEC_P | /* Object flags. */
+ HAS_LINENO | HAS_DEBUG |
+ HAS_SYMS | HAS_LOCALS | WP_TEXT),
+ (SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD | SEC_RELOC | SEC_CODE | SEC_DATA),
+ MY_symbol_leading_char,
+ AR_PAD_CHAR, /* AR_pad_char. */
+ 15, /* AR_max_namelen. */
+ bfd_getl64, bfd_getl_signed_64, bfd_putl64,
+ bfd_getp32, bfd_getp_signed_32, bfd_putp32,
+ bfd_getl16, bfd_getl_signed_16, bfd_putl16, /* Data. */
+ bfd_getl64, bfd_getl_signed_64, bfd_putl64,
+ bfd_getp32, bfd_getp_signed_32, bfd_putp32,
+ bfd_getl16, bfd_getl_signed_16, bfd_putl16, /* Headers. */
+ {_bfd_dummy_target, MY_object_p, /* bfd_check_format. */
+ bfd_generic_archive_p, MY_core_file_p},
+ {bfd_false, MY_mkobject, /* bfd_set_format. */
+ _bfd_generic_mkarchive, bfd_false},
+ {bfd_false, MY_write_object_contents, /* bfd_write_contents. */
+ _bfd_write_archive_contents, bfd_false},
+
+ BFD_JUMP_TABLE_GENERIC (MY),
+ BFD_JUMP_TABLE_COPY (MY),
+ BFD_JUMP_TABLE_CORE (MY),
+ BFD_JUMP_TABLE_ARCHIVE (MY),
+ BFD_JUMP_TABLE_SYMBOLS (MY),
+ BFD_JUMP_TABLE_RELOCS (MY),
+ BFD_JUMP_TABLE_WRITE (MY),
+ BFD_JUMP_TABLE_LINK (MY),
+ BFD_JUMP_TABLE_DYNAMIC (MY),
+
+ /* Alternative_target. */
+ NULL,
+
+ (void *) MY_backend_data
+};
/* PowerPC traceback table support for BFD.
- Copyright 1993, 1998, 1999, 2000, 2001, 2002
+ Copyright 1993, 1998, 1999, 2000, 2001, 2002, 2005
Free Software Foundation, Inc.
This file is part of BFD, the Binary File Descriptor library.
#define TB_PL8 11U /* PL8 */
#define TB_ASM 12U /* Asm */
-/* flags 1 */
+/* Flags 1. */
#define TB_GLOBALLINK 0x80U /* Routine is Global Linkage. */
#define TB_is_eprol 0x40U /* Out-of-line prolog or epilog routine. */
#define TB_FP_PRESENT 0x02U /* Routine has floating point ops. */
#define TB_LOG_ABORT 0x01U /* fp_present && log/abort compiler opt. */
-/* flags 2 */
+/* Flags 2. */
#define TB_INT_HNDL 0x80U /* Routine is an interrupt handler. */
#define TB_NAME_PRESENT 0x40U /* Name_len/name set (extension field). */
#define TB_SAVES_CR 0x02U /* Routine saves the CR. */
#define TB_SAVES_LR 0x01U /* Routine saves the LR. */
-/* cl_dis_inv "on condition" settings: */
+/* cl_dis_inv "on condition" settings: */
#define TB_CL_DIS_INV(x) (((x) & cl_dis_inv) >> 2U)
#define TB_DISCARD_ONCOND 1U /* Walk stack and discard. */
#define TB_INVOKE_ONCOND 2U /* Invoke a specific system routine. */
-/* flags 3 */
+/* Flags 3. */
#define TB_STORES_BC 0x80U /* Routine saves frame ptr of caller. */
#define TB_SPARE2 0X40U /* Spare bit. */
#define TB_NUM_FPR_SAVED(x) ((x) & fpr_saved)
-/* flags 4 */
+/* Flags 4. */
#define TB_HAS_VEC_INFO 0x80U /* Routine uses vectors. */
#define TB_SPARE3 0X40U /* Spare bit. */
#define TB_NUM_GPR_SAVED(x) ((x) & gpr_saved)
-/* flags 5 */
+/* Flags 5. */
#define TB_FLOATPARAMS 0xfeU /* Number of floating point parameters. */
#define TB_PARAMSONSTK 0X01U /* All parameters are on the stack. */
#define TB_NUM_FLOATPARAMS(X) (((x) & floatparams) >> 1U)
-/* traceback_table (fixed portion). */
+/* Traceback_table (fixed portion). */
struct traceback_table
{
Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
#include "safe-ctype.h"
-
#include "pef.h"
#include "pef-traceback.h"
-
#include "bfd.h"
#include "sysdep.h"
#include "libbfd.h"
-
#include "libiberty.h"
#ifndef BFD_IO_FUNCS
#define bfd_pef_bfd_merge_sections bfd_generic_merge_sections
#define bfd_pef_bfd_is_group_section bfd_generic_is_group_section
#define bfd_pef_bfd_discard_group bfd_generic_discard_group
-#define bfd_pef_section_already_linked _bfd_generic_section_already_linked
+#define bfd_pef_section_already_linked _bfd_generic_section_already_linked
#define bfd_pef_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
#define bfd_pef_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
#define bfd_pef_bfd_link_add_symbols _bfd_generic_link_add_symbols
#define bfd_pef_bfd_link_split_section _bfd_generic_link_split_section
#define bfd_pef_get_section_contents_in_window _bfd_generic_get_section_contents_in_window
-static void bfd_pef_print_symbol PARAMS ((bfd *, PTR, asymbol *, bfd_print_symbol_type));
-static void bfd_pef_convert_architecture PARAMS ((unsigned long, enum bfd_architecture *, unsigned long *));
-static bfd_boolean bfd_pef_mkobject PARAMS ((bfd *));
-static int bfd_pef_parse_traceback_table PARAMS ((bfd *, asection *, unsigned char *, size_t, size_t, asymbol *, FILE *));
-static const char *bfd_pef_section_name PARAMS ((bfd_pef_section *));
-static unsigned long bfd_pef_section_flags PARAMS ((bfd_pef_section *));
-static asection *bfd_pef_make_bfd_section PARAMS ((bfd *, bfd_pef_section *));
-static int bfd_pef_read_header PARAMS ((bfd *, bfd_pef_header *));
-static const bfd_target *bfd_pef_object_p PARAMS ((bfd *));
-static int bfd_pef_parse_traceback_tables PARAMS ((bfd *, asection *, unsigned char *, size_t, long *, asymbol **));
-static int bfd_pef_parse_function_stub PARAMS ((bfd *, unsigned char *, size_t, unsigned long *));
-static int bfd_pef_parse_function_stubs PARAMS ((bfd *, asection *, unsigned char *, size_t, unsigned char *, size_t, unsigned long *, asymbol **));
-static long bfd_pef_parse_symbols PARAMS ((bfd *, asymbol **));
-static long bfd_pef_count_symbols PARAMS ((bfd *));
-static long bfd_pef_get_symtab_upper_bound PARAMS ((bfd *));
-static long bfd_pef_canonicalize_symtab PARAMS ((bfd *, asymbol **));
-static asymbol *bfd_pef_make_empty_symbol PARAMS ((bfd *));
-static void bfd_pef_get_symbol_info PARAMS ((bfd *, asymbol *, symbol_info *));
-static int bfd_pef_sizeof_headers PARAMS ((bfd *, bfd_boolean));
-static int bfd_pef_xlib_read_header PARAMS ((bfd *, bfd_pef_xlib_header *));
-static int bfd_pef_xlib_scan PARAMS ((bfd *, bfd_pef_xlib_header *));
-static const bfd_target *bfd_pef_xlib_object_p PARAMS ((bfd *));
-
-static void
-bfd_pef_print_symbol (abfd, afile, symbol, how)
- bfd *abfd;
- PTR afile;
- asymbol *symbol;
- bfd_print_symbol_type how;
-{
- FILE *file = (FILE *) afile;
-
- switch (how)
- {
- case bfd_print_symbol_name:
- fprintf (file, "%s", symbol->name);
- break;
- default:
- bfd_print_symbol_vandf (abfd, (PTR) file, symbol);
- fprintf (file, " %-5s %s", symbol->section->name, symbol->name);
- if (strncmp (symbol->name, "__traceback_", strlen ("__traceback_")) == 0)
- {
- unsigned char *buf = alloca (symbol->udata.i);
- size_t offset = symbol->value + 4;
- size_t len = symbol->udata.i;
- int ret;
-
- bfd_get_section_contents (abfd, symbol->section, buf, offset, len);
- ret = bfd_pef_parse_traceback_table (abfd, symbol->section, buf,
- len, 0, NULL, file);
- if (ret < 0)
- fprintf (file, " [ERROR]");
- }
- }
-}
-
-static void
-bfd_pef_convert_architecture (architecture, type, subtype)
- unsigned long architecture;
- enum bfd_architecture *type;
- unsigned long *subtype;
-{
- const unsigned long ARCH_POWERPC = 0x70777063; /* 'pwpc' */
- const unsigned long ARCH_M68K = 0x6d36386b; /* 'm68k' */
-
- *subtype = bfd_arch_unknown;
- *type = bfd_arch_unknown;
-
- if (architecture == ARCH_POWERPC)
- *type = bfd_arch_powerpc;
- else if (architecture == ARCH_M68K)
- *type = bfd_arch_m68k;
-}
-
-static bfd_boolean
-bfd_pef_mkobject (abfd)
- bfd *abfd ATTRIBUTE_UNUSED;
-{
- return TRUE;
-}
-
static int
-bfd_pef_parse_traceback_table (abfd, section, buf, len, pos, sym, file)
- bfd *abfd;
- asection *section;
- unsigned char *buf;
- size_t len;
- size_t pos;
- asymbol *sym;
- FILE *file;
+bfd_pef_parse_traceback_table (bfd *abfd,
+ asection *section,
+ unsigned char *buf,
+ size_t len,
+ size_t pos,
+ asymbol *sym,
+ FILE *file)
{
struct traceback_table table;
size_t offset;
asymbol tmpsymbol;
if (sym == NULL)
- sym = &tmpsymbol;
+ sym = & tmpsymbol;
sym->name = NULL;
sym->value = 0;
sym->udata.i = 0;
/* memcpy is fine since all fields are unsigned char. */
-
if ((pos + 8) > len)
return -1;
memcpy (&table, buf + pos, 8);
/* Calling code relies on returned symbols having a name and
correct offset. */
-
if ((table.lang != TB_C) && (table.lang != TB_CPLUSPLUS))
return -1;
/* Need to subtract 4 because the offset includes the 0x0L
preceding the table. */
-
if (file != NULL)
fprintf (file, " [offset = 0x%lx]", off.tb_offset);
if ((pos + offset + name.name_len) > len)
return -1;
- namebuf = (char *) bfd_alloc (abfd, name.name_len + 1);
+ namebuf = bfd_alloc (abfd, name.name_len + 1);
if (namebuf == NULL)
return -1;
return offset;
}
-static const char *bfd_pef_section_name (section)
- bfd_pef_section *section;
+static void
+bfd_pef_print_symbol (bfd *abfd,
+ void * afile,
+ asymbol *symbol,
+ bfd_print_symbol_type how)
+{
+ FILE *file = (FILE *) afile;
+
+ switch (how)
+ {
+ case bfd_print_symbol_name:
+ fprintf (file, "%s", symbol->name);
+ break;
+ default:
+ bfd_print_symbol_vandf (abfd, (void *) file, symbol);
+ fprintf (file, " %-5s %s", symbol->section->name, symbol->name);
+ if (strncmp (symbol->name, "__traceback_", strlen ("__traceback_")) == 0)
+ {
+ unsigned char *buf = alloca (symbol->udata.i);
+ size_t offset = symbol->value + 4;
+ size_t len = symbol->udata.i;
+ int ret;
+
+ bfd_get_section_contents (abfd, symbol->section, buf, offset, len);
+ ret = bfd_pef_parse_traceback_table (abfd, symbol->section, buf,
+ len, 0, NULL, file);
+ if (ret < 0)
+ fprintf (file, " [ERROR]");
+ }
+ }
+}
+
+static void
+bfd_pef_convert_architecture (unsigned long architecture,
+ enum bfd_architecture *type,
+ unsigned long *subtype)
+{
+ const unsigned long ARCH_POWERPC = 0x70777063; /* 'pwpc'. */
+ const unsigned long ARCH_M68K = 0x6d36386b; /* 'm68k'. */
+
+ *subtype = bfd_arch_unknown;
+ *type = bfd_arch_unknown;
+
+ if (architecture == ARCH_POWERPC)
+ *type = bfd_arch_powerpc;
+ else if (architecture == ARCH_M68K)
+ *type = bfd_arch_m68k;
+}
+
+static bfd_boolean
+bfd_pef_mkobject (bfd *abfd ATTRIBUTE_UNUSED)
+{
+ return TRUE;
+}
+
+static const char *bfd_pef_section_name (bfd_pef_section *section)
{
switch (section->section_kind)
{
}
}
-static unsigned long bfd_pef_section_flags (section)
- bfd_pef_section *section;
+static unsigned long bfd_pef_section_flags (bfd_pef_section *section)
{
switch (section->section_kind)
{
}
static asection *
-bfd_pef_make_bfd_section (abfd, section)
- bfd *abfd;
- bfd_pef_section *section;
+bfd_pef_make_bfd_section (bfd *abfd, bfd_pef_section *section)
{
asection *bfdsec;
const char *name = bfd_pef_section_name (section);
return bfdsec;
}
-int bfd_pef_parse_loader_header (abfd, buf, len, header)
- bfd *abfd ATTRIBUTE_UNUSED;
- unsigned char *buf;
- size_t len;
- bfd_pef_loader_header *header;
+int
+bfd_pef_parse_loader_header (bfd *abfd ATTRIBUTE_UNUSED,
+ unsigned char *buf,
+ size_t len,
+ bfd_pef_loader_header *header)
{
BFD_ASSERT (len == 56);
return 0;
}
-int bfd_pef_parse_imported_library (abfd, buf, len, header)
- bfd *abfd ATTRIBUTE_UNUSED;
- unsigned char *buf;
- size_t len;
- bfd_pef_imported_library *header;
+int
+bfd_pef_parse_imported_library (bfd *abfd ATTRIBUTE_UNUSED,
+ unsigned char *buf,
+ size_t len,
+ bfd_pef_imported_library *header)
{
BFD_ASSERT (len == 24);
return 0;
}
-int bfd_pef_parse_imported_symbol (abfd, buf, len, symbol)
- bfd *abfd ATTRIBUTE_UNUSED;
- unsigned char *buf;
- size_t len;
- bfd_pef_imported_symbol *symbol;
+int
+bfd_pef_parse_imported_symbol (bfd *abfd ATTRIBUTE_UNUSED,
+ unsigned char *buf,
+ size_t len,
+ bfd_pef_imported_symbol *symbol)
{
unsigned long value;
return 0;
}
-int bfd_pef_scan_section (abfd, section)
- bfd *abfd;
- bfd_pef_section *section;
+int
+bfd_pef_scan_section (bfd *abfd, bfd_pef_section *section)
{
unsigned char buf[28];
bfd_seek (abfd, section->header_offset, SEEK_SET);
- if (bfd_bread ((PTR) buf, 28, abfd) != 28)
+ if (bfd_bread ((void *) buf, 28, abfd) != 28)
return -1;
section->name_offset = bfd_h_get_32 (abfd, buf);
}
void
-bfd_pef_print_loader_header (abfd, header, file)
- bfd *abfd ATTRIBUTE_UNUSED;
- bfd_pef_loader_header *header;
- FILE *file;
+bfd_pef_print_loader_header (bfd *abfd ATTRIBUTE_UNUSED,
+ bfd_pef_loader_header *header,
+ FILE *file)
{
fprintf (file, "main_section: %ld\n", header->main_section);
fprintf (file, "main_offset: %lu\n", header->main_offset);
}
int
-bfd_pef_print_loader_section (abfd, file)
- bfd *abfd;
- FILE *file;
+bfd_pef_print_loader_section (bfd *abfd, FILE *file)
{
bfd_pef_loader_header header;
asection *loadersec = NULL;
unsigned char *loaderbuf = NULL;
size_t loaderlen = 0;
- int ret;
loadersec = bfd_get_section_by_name (abfd, "loader");
if (loadersec == NULL)
return -1;
loaderlen = loadersec->size;
- loaderbuf = (unsigned char *) bfd_malloc (loaderlen);
- if (bfd_seek (abfd, loadersec->filepos, SEEK_SET) < 0)
- {
- free (loaderbuf);
- return -1;
- }
- if (bfd_bread ((PTR) loaderbuf, loaderlen, abfd) != loaderlen)
- {
- free (loaderbuf);
- return -1;
- }
+ loaderbuf = bfd_malloc (loaderlen);
- if (loaderlen < 56)
- {
- free (loaderbuf);
- return -1;
- }
- ret = bfd_pef_parse_loader_header (abfd, loaderbuf, 56, &header);
- if (ret < 0)
+ if (bfd_seek (abfd, loadersec->filepos, SEEK_SET) < 0
+ || bfd_bread ((void *) loaderbuf, loaderlen, abfd) != loaderlen
+ || loaderlen < 56
+ || bfd_pef_parse_loader_header (abfd, loaderbuf, 56, &header) < 0)
{
free (loaderbuf);
return -1;
}
int
-bfd_pef_scan_start_address (abfd)
- bfd *abfd;
+bfd_pef_scan_start_address (bfd *abfd)
{
bfd_pef_loader_header header;
asection *section;
goto end;
loaderlen = loadersec->size;
- loaderbuf = (unsigned char *) bfd_malloc (loaderlen);
+ loaderbuf = bfd_malloc (loaderlen);
if (bfd_seek (abfd, loadersec->filepos, SEEK_SET) < 0)
goto error;
- if (bfd_bread ((PTR) loaderbuf, loaderlen, abfd) != loaderlen)
+ if (bfd_bread ((void *) loaderbuf, loaderlen, abfd) != loaderlen)
goto error;
if (loaderlen < 56)
if (header->section_count != 0)
{
- mdata->sections =
- ((bfd_pef_section *)
- bfd_alloc (abfd, header->section_count * sizeof (bfd_pef_section)));
+ mdata->sections = bfd_alloc (abfd, header->section_count * sizeof (bfd_pef_section));
if (mdata->sections == NULL)
return -1;
}
static int
-bfd_pef_read_header (abfd, header)
- bfd *abfd;
- bfd_pef_header *header;
+bfd_pef_read_header (bfd *abfd, bfd_pef_header *header)
{
unsigned char buf[40];
bfd_seek (abfd, 0, SEEK_SET);
- if (bfd_bread ((PTR) buf, 40, abfd) != 40)
+ if (bfd_bread ((void *) buf, 40, abfd) != 40)
return -1;
header->tag1 = bfd_getb32 (buf);
}
static const bfd_target *
-bfd_pef_object_p (abfd)
- bfd *abfd;
+bfd_pef_object_p (bfd *abfd)
{
struct bfd_preserve preserve;
bfd_pef_header header;
return NULL;
}
-static int bfd_pef_parse_traceback_tables (abfd, sec, buf, len, nsym, csym)
- bfd *abfd;
- asection *sec;
- unsigned char *buf;
- size_t len;
- long *nsym;
- asymbol **csym;
+static int
+bfd_pef_parse_traceback_tables (bfd *abfd,
+ asection *sec,
+ unsigned char *buf,
+ size_t len,
+ long *nsym,
+ asymbol **csym)
{
char *name;
/* Don't bother to compute the name if we are just
counting symbols. */
-
if (csym)
{
tbnamelen = strlen (tbprefix) + strlen (function.name);
name = bfd_alloc (abfd, tbnamelen + 1);
if (name == NULL)
{
- bfd_release (abfd, (PTR) function.name);
+ bfd_release (abfd, (void *) function.name);
function.name = NULL;
break;
}
return 0;
}
-static int bfd_pef_parse_function_stub (abfd, buf, len, offset)
- bfd *abfd ATTRIBUTE_UNUSED;
- unsigned char *buf;
- size_t len;
- unsigned long *offset;
+static int
+bfd_pef_parse_function_stub (bfd *abfd ATTRIBUTE_UNUSED,
+ unsigned char *buf,
+ size_t len,
+ unsigned long *offset)
{
BFD_ASSERT (len == 24);
return 0;
}
-static int bfd_pef_parse_function_stubs (abfd, codesec, codebuf, codelen,
- loaderbuf, loaderlen, nsym, csym)
- bfd *abfd;
- asection *codesec;
- unsigned char *codebuf;
- size_t codelen;
- unsigned char *loaderbuf;
- size_t loaderlen;
- unsigned long *nsym;
- asymbol **csym;
+static int
+bfd_pef_parse_function_stubs (bfd *abfd,
+ asection *codesec,
+ unsigned char *codebuf,
+ size_t codelen,
+ unsigned char *loaderbuf,
+ size_t loaderlen,
+ unsigned long *nsym,
+ asymbol **csym)
{
const char *const sprefix = "__stub_";
if (ret < 0)
goto error;
- libraries = (bfd_pef_imported_library *) bfd_malloc
+ libraries = bfd_malloc
(header.imported_library_count * sizeof (bfd_pef_imported_library));
- imports = (bfd_pef_imported_symbol *) bfd_malloc
+ imports = bfd_malloc
(header.total_imported_symbol_count * sizeof (bfd_pef_imported_symbol));
if (loaderlen < (56 + (header.imported_library_count * 24)))
return -1;
}
-static long bfd_pef_parse_symbols (abfd, csym)
- bfd *abfd;
- asymbol **csym;
+static long
+bfd_pef_parse_symbols (bfd *abfd, asymbol **csym)
{
unsigned long count = 0;
if (codesec != NULL)
{
codelen = codesec->size;
- codebuf = (unsigned char *) bfd_malloc (codelen);
+ codebuf = bfd_malloc (codelen);
if (bfd_seek (abfd, codesec->filepos, SEEK_SET) < 0)
goto end;
- if (bfd_bread ((PTR) codebuf, codelen, abfd) != codelen)
+ if (bfd_bread ((void *) codebuf, codelen, abfd) != codelen)
goto end;
}
if (loadersec != NULL)
{
loaderlen = loadersec->size;
- loaderbuf = (unsigned char *) bfd_malloc (loaderlen);
+ loaderbuf = bfd_malloc (loaderlen);
if (bfd_seek (abfd, loadersec->filepos, SEEK_SET) < 0)
goto end;
- if (bfd_bread ((PTR) loaderbuf, loaderlen, abfd) != loaderlen)
+ if (bfd_bread ((void *) loaderbuf, loaderlen, abfd) != loaderlen)
goto end;
}
}
static long
-bfd_pef_count_symbols (abfd)
- bfd *abfd;
+bfd_pef_count_symbols (bfd *abfd)
{
return bfd_pef_parse_symbols (abfd, NULL);
}
static long
-bfd_pef_get_symtab_upper_bound (abfd)
- bfd *abfd;
+bfd_pef_get_symtab_upper_bound (bfd *abfd)
{
long nsyms = bfd_pef_count_symbols (abfd);
+
if (nsyms < 0)
return nsyms;
return ((nsyms + 1) * sizeof (asymbol *));
}
static long
-bfd_pef_canonicalize_symtab (abfd, alocation)
- bfd *abfd;
- asymbol **alocation;
+bfd_pef_canonicalize_symtab (bfd *abfd, asymbol **alocation)
{
long i;
asymbol *syms;
long ret;
-
long nsyms = bfd_pef_count_symbols (abfd);
+
if (nsyms < 0)
return nsyms;
}
static asymbol *
-bfd_pef_make_empty_symbol (abfd)
- bfd *abfd;
+bfd_pef_make_empty_symbol (bfd *abfd)
{
- return (asymbol *) bfd_alloc (abfd, sizeof (asymbol));
+ return bfd_alloc (abfd, sizeof (asymbol));
}
static void
-bfd_pef_get_symbol_info (abfd, symbol, ret)
- bfd *abfd ATTRIBUTE_UNUSED;
- asymbol *symbol;
- symbol_info *ret;
+bfd_pef_get_symbol_info (bfd *abfd ATTRIBUTE_UNUSED,
+ asymbol *symbol,
+ symbol_info *ret)
{
bfd_symbol_info (symbol, ret);
}
static int
-bfd_pef_sizeof_headers (abfd, exec)
- bfd *abfd ATTRIBUTE_UNUSED;
- bfd_boolean exec ATTRIBUTE_UNUSED;
+bfd_pef_sizeof_headers (bfd *abfd ATTRIBUTE_UNUSED, bfd_boolean exec ATTRIBUTE_UNUSED)
{
return 0;
}
const bfd_target pef_vec =
{
- "pef", /* name */
- bfd_target_pef_flavour, /* flavour */
- BFD_ENDIAN_BIG, /* byteorder */
- BFD_ENDIAN_BIG, /* header_byteorder */
- (HAS_RELOC | EXEC_P | /* object flags */
+ "pef", /* Name. */
+ bfd_target_pef_flavour, /* Flavour. */
+ BFD_ENDIAN_BIG, /* Byteorder. */
+ BFD_ENDIAN_BIG, /* Header_byteorder. */
+ (HAS_RELOC | EXEC_P | /* Object flags. */
HAS_LINENO | HAS_DEBUG |
HAS_SYMS | HAS_LOCALS | DYNAMIC | WP_TEXT | D_PAGED),
(SEC_ALLOC | SEC_LOAD | SEC_READONLY | SEC_CODE | SEC_DATA
- | SEC_ROM | SEC_HAS_CONTENTS), /* section_flags */
- 0, /* symbol_leading_char */
- ' ', /* ar_pad_char */
- 16, /* ar_max_namelen */
+ | SEC_ROM | SEC_HAS_CONTENTS), /* Section_flags. */
+ 0, /* Symbol_leading_char. */
+ ' ', /* AR_pad_char. */
+ 16, /* AR_max_namelen. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* data */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Data. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* hdrs */
- { /* bfd_check_format */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Headers. */
+ { /* bfd_check_format. */
_bfd_dummy_target,
- bfd_pef_object_p, /* bfd_check_format */
+ bfd_pef_object_p, /* bfd_check_format. */
_bfd_dummy_target,
_bfd_dummy_target,
},
- { /* bfd_set_format */
+ { /* bfd_set_format. */
bfd_false,
bfd_pef_mkobject,
bfd_false,
bfd_false,
},
- { /* bfd_write_contents */
+ { /* bfd_write_contents. */
bfd_false,
bfd_true,
bfd_false,
NULL
};
-#define bfd_pef_xlib_close_and_cleanup _bfd_generic_close_and_cleanup
-#define bfd_pef_xlib_bfd_free_cached_info _bfd_generic_bfd_free_cached_info
-#define bfd_pef_xlib_new_section_hook _bfd_generic_new_section_hook
-#define bfd_pef_xlib_get_section_contents _bfd_generic_get_section_contents
-#define bfd_pef_xlib_set_section_contents _bfd_generic_set_section_contents
+#define bfd_pef_xlib_close_and_cleanup _bfd_generic_close_and_cleanup
+#define bfd_pef_xlib_bfd_free_cached_info _bfd_generic_bfd_free_cached_info
+#define bfd_pef_xlib_new_section_hook _bfd_generic_new_section_hook
+#define bfd_pef_xlib_get_section_contents _bfd_generic_get_section_contents
+#define bfd_pef_xlib_set_section_contents _bfd_generic_set_section_contents
#define bfd_pef_xlib_get_section_contents_in_window _bfd_generic_get_section_contents_in_window
#define bfd_pef_xlib_set_section_contents_in_window _bfd_generic_set_section_contents_in_window
static int
-bfd_pef_xlib_read_header (abfd, header)
- bfd *abfd;
- bfd_pef_xlib_header *header;
+bfd_pef_xlib_read_header (bfd *abfd, bfd_pef_xlib_header *header)
{
unsigned char buf[76];
bfd_seek (abfd, 0, SEEK_SET);
- if (bfd_bread ((PTR) buf, 76, abfd) != 76)
+ if (bfd_bread ((void *) buf, 76, abfd) != 76)
return -1;
header->tag1 = bfd_getb32 (buf);
return 0;
}
-int
-bfd_pef_xlib_scan (abfd, header)
- bfd *abfd;
- bfd_pef_xlib_header *header;
+static int
+bfd_pef_xlib_scan (bfd *abfd, bfd_pef_xlib_header *header)
{
bfd_pef_xlib_data_struct *mdata = NULL;
- mdata = ((bfd_pef_xlib_data_struct *)
- bfd_alloc (abfd, sizeof (bfd_pef_xlib_data_struct)));
+ mdata = bfd_alloc (abfd, sizeof (* mdata));
if (mdata == NULL)
return -1;
}
static const bfd_target *
-bfd_pef_xlib_object_p (abfd)
- bfd *abfd;
+bfd_pef_xlib_object_p (bfd *abfd)
{
struct bfd_preserve preserve;
bfd_pef_xlib_header header;
const bfd_target pef_xlib_vec =
{
- "pef-xlib", /* name */
- bfd_target_pef_xlib_flavour, /* flavour */
- BFD_ENDIAN_BIG, /* byteorder */
- BFD_ENDIAN_BIG, /* header_byteorder */
- (HAS_RELOC | EXEC_P | /* object flags */
+ "pef-xlib", /* Name. */
+ bfd_target_pef_xlib_flavour, /* Flavour. */
+ BFD_ENDIAN_BIG, /* Byteorder */
+ BFD_ENDIAN_BIG, /* Header_byteorder. */
+ (HAS_RELOC | EXEC_P | /* Object flags. */
HAS_LINENO | HAS_DEBUG |
HAS_SYMS | HAS_LOCALS | DYNAMIC | WP_TEXT | D_PAGED),
(SEC_ALLOC | SEC_LOAD | SEC_READONLY | SEC_CODE | SEC_DATA
- | SEC_ROM | SEC_HAS_CONTENTS), /* section_flags */
- 0, /* symbol_leading_char */
- ' ', /* ar_pad_char */
- 16, /* ar_max_namelen */
+ | SEC_ROM | SEC_HAS_CONTENTS),/* Section_flags. */
+ 0, /* Symbol_leading_char. */
+ ' ', /* AR_pad_char. */
+ 16, /* AR_max_namelen. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* data */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Data. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* hdrs */
- { /* bfd_check_format */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Headers. */
+ { /* bfd_check_format. */
_bfd_dummy_target,
- bfd_pef_xlib_object_p, /* bfd_check_format */
+ bfd_pef_xlib_object_p, /* bfd_check_format. */
_bfd_dummy_target,
_bfd_dummy_target,
},
- { /* bfd_set_format */
+ { /* bfd_set_format. */
bfd_false,
bfd_pef_mkobject,
bfd_false,
bfd_false,
},
- { /* bfd_write_contents */
+ { /* bfd_write_contents. */
bfd_false,
bfd_true,
bfd_false,
};
typedef struct bfd_pef_xlib_data_struct bfd_pef_xlib_data_struct;
-int bfd_pef_parse_loader_header PARAMS ((bfd *, unsigned char *, size_t, bfd_pef_loader_header *));
-int bfd_pef_print_loader_section PARAMS ((bfd *, FILE *));
-void bfd_pef_print_loader_header PARAMS ((bfd *, bfd_pef_loader_header *, FILE *));
-int bfd_pef_parse_imported_library PARAMS ((bfd *, unsigned char *, size_t, bfd_pef_imported_library *));
-int bfd_pef_parse_imported_symbol PARAMS ((bfd *, unsigned char *, size_t, bfd_pef_imported_symbol *));
-int bfd_pef_scan_section PARAMS ((bfd *, bfd_pef_section *));
-int bfd_pef_scan_start_address PARAMS ((bfd *));
-int bfd_pef_scan PARAMS ((bfd *, bfd_pef_header *, bfd_pef_data_struct *));
+int bfd_pef_parse_loader_header (bfd *, unsigned char *, size_t, bfd_pef_loader_header *);
+int bfd_pef_print_loader_section (bfd *, FILE *);
+void bfd_pef_print_loader_header (bfd *, bfd_pef_loader_header *, FILE *);
+int bfd_pef_parse_imported_library (bfd *, unsigned char *, size_t, bfd_pef_imported_library *);
+int bfd_pef_parse_imported_symbol (bfd *, unsigned char *, size_t, bfd_pef_imported_symbol *);
+int bfd_pef_scan_section (bfd *, bfd_pef_section *);
+int bfd_pef_scan_start_address (bfd *);
+int bfd_pef_scan (bfd *, bfd_pef_header *, bfd_pef_data_struct *);
2005 Free Software Foundation, Inc.
Contributed by Richard Earnshaw (rwe@pegasus.esprit.ec.org)
-This file is part of BFD, the Binary File Descriptor library.
+ This file is part of BFD, the Binary File Descriptor library.
-This program is free software; you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation; either version 2 of the License, or
-(at your option) any later version.
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-GNU General Public License for more details.
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
-You should have received a copy of the GNU General Public License
-along with this program; if not, write to the Free Software
-Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
/* RISC iX overloads the MAGIC field to indicate more than just the usual
[ZNO]MAGIC values. Also included are squeezing information and
#define MF_IS_SL 04000
/* Common combinations. */
-#define IMAGIC (MF_IMPURE|ZMAGIC) /* Demand load (impure text) */
-#define SPOMAGIC (MF_USES_SL|OMAGIC) /* OMAGIC with large header */
- /* -- may contain a ref to a */
- /* shared lib required by the */
- /* object. */
-#define SLOMAGIC (MF_IS_SL|OMAGIC) /* A reference to a shared library */
- /* The text portion of the object */
- /* contains "overflow text" from */
- /* the shared library to be linked */
- /* in with an object */
-#define QMAGIC (MF_SQUEEZED|ZMAGIC) /* Sqeezed demand paged. */
- /* NOTE: This interpretation of */
- /* QMAGIC seems to be at variance */
- /* With that used on other */
- /* architectures. */
-#define SPZMAGIC (MF_USES_SL|ZMAGIC) /* program which uses sl */
-#define SPQMAGIC (MF_USES_SL|QMAGIC) /* sqeezed ditto */
-#define SLZMAGIC (MF_IS_SL|ZMAGIC) /* shared lib part of prog */
-#define SLPZMAGIC (MF_USES_SL|SLZMAGIC) /* sl which uses another */
+
+/* Demand load (impure text). */
+#define IMAGIC (MF_IMPURE | ZMAGIC)
+
+/* OMAGIC with large header.
+ May contain a ref to a shared lib required by the object. */
+#define SPOMAGIC (MF_USES_SL | OMAGIC)
+
+/* A reference to a shared library.
+ The text portion of the object contains "overflow text" from
+ the shared library to be linked in with an object. */
+#define SLOMAGIC (MF_IS_SL | OMAGIC)
+
+/* Sqeezed demand paged.
+ NOTE: This interpretation of QMAGIC seems to be at variance
+ with that used on other architectures. */
+#define QMAGIC (MF_SQUEEZED | ZMAGIC)
+
+/* Program which uses sl. */
+#define SPZMAGIC (MF_USES_SL | ZMAGIC)
+
+/* Sqeezed ditto. */
+#define SPQMAGIC (MF_USES_SL | QMAGIC)
+
+/* Shared lib part of prog. */
+#define SLZMAGIC (MF_IS_SL | ZMAGIC)
+
+/* Sl which uses another. */
+#define SLPZMAGIC (MF_USES_SL | SLZMAGIC)
#define N_SHARED_LIB(x) ((x).a_info & MF_USES_SL)
-/* Only a pure OMAGIC file has the minimal header */
+/* Only a pure OMAGIC file has the minimal header. */
#define N_TXTOFF(x) \
((x).a_info == OMAGIC \
? 32 \
#define N_STROFF(x) (N_SYMOFF (x) + (x).a_syms)
-#define TEXT_START_ADDR 32768
-#define TARGET_PAGE_SIZE 32768
-#define SEGMENT_SIZE TARGET_PAGE_SIZE
-#define DEFAULT_ARCH bfd_arch_arm
+#define TEXT_START_ADDR 32768
+#define TARGET_PAGE_SIZE 32768
+#define SEGMENT_SIZE TARGET_PAGE_SIZE
+#define DEFAULT_ARCH bfd_arch_arm
/* Do not "beautify" the CONCAT* macro args. Traditional C will not
remove whitespace added here, and thus will fail to concatenate
the tokens. */
#define MY(OP) CONCAT2 (riscix_,OP)
#define TARGETNAME "a.out-riscix"
-#define N_BADMAG(x) ((((x).a_info & ~007200) != ZMAGIC) && \
- (((x).a_info & ~006000) != OMAGIC) && \
- ((x).a_info != NMAGIC))
+#define N_BADMAG(x) ((((x).a_info & ~007200) != ZMAGIC) \
+ && (((x).a_info & ~006000) != OMAGIC) \
+ && ((x).a_info != NMAGIC))
#define N_MAGIC(x) ((x).a_info & ~07200)
#include "bfd.h"
#define WRITE_HEADERS(abfd, execp) \
{ \
- bfd_size_type text_size; /* dummy vars */ \
+ bfd_size_type text_size; /* Dummy vars. */ \
file_ptr text_end; \
- if (adata(abfd).magic == undecided_magic) \
- NAME(aout,adjust_sizes_and_vmas) (abfd, &text_size, &text_end); \
+ \
+ if (adata (abfd).magic == undecided_magic) \
+ NAME (aout, adjust_sizes_and_vmas) (abfd, & text_size, & text_end); \
\
execp->a_syms = bfd_get_symcount (abfd) * EXTERNAL_NLIST_SIZE; \
execp->a_entry = bfd_get_start_address (abfd); \
obj_reloc_entry_size (abfd)); \
execp->a_drsize = ((obj_datasec (abfd)->reloc_count) * \
obj_reloc_entry_size (abfd)); \
- NAME(aout,swap_exec_header_out) (abfd, execp, &exec_bytes); \
+ NAME (aout, swap_exec_header_out) (abfd, execp, & exec_bytes); \
\
if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) != 0 \
- || bfd_bwrite ((PTR) &exec_bytes, (bfd_size_type) EXEC_BYTES_SIZE, \
+ || bfd_bwrite ((void *) & exec_bytes, (bfd_size_type) EXEC_BYTES_SIZE, \
abfd) != EXEC_BYTES_SIZE) \
return FALSE; \
- /* Now write out reloc info, followed by syms and strings */ \
+ /* Now write out reloc info, followed by syms and strings. */ \
\
- if (bfd_get_outsymbols (abfd) != (asymbol **) NULL \
+ if (bfd_get_outsymbols (abfd) != NULL \
&& bfd_get_symcount (abfd) != 0) \
{ \
- if (bfd_seek (abfd, (file_ptr) (N_SYMOFF(*execp)), SEEK_SET) != 0) \
+ if (bfd_seek (abfd, (file_ptr) (N_SYMOFF (* execp)), SEEK_SET) != 0)\
return FALSE; \
\
- if (! NAME(aout,write_syms) (abfd)) return FALSE; \
+ if (! NAME (aout, write_syms) (abfd)) \
+ return FALSE; \
\
- if (bfd_seek (abfd, (file_ptr) (N_TRELOFF(*execp)), SEEK_SET) != 0) \
+ if (bfd_seek (abfd, (file_ptr) (N_TRELOFF (* execp)), SEEK_SET) != 0)\
return FALSE; \
\
if (! riscix_squirt_out_relocs (abfd, obj_textsec (abfd))) \
return FALSE; \
- if (bfd_seek (abfd, (file_ptr) (N_DRELOFF(*execp)), SEEK_SET) != 0) \
+ if (bfd_seek (abfd, (file_ptr) (N_DRELOFF (* execp)), SEEK_SET) != 0)\
return FALSE; \
\
- if (!NAME(aout,squirt_out_relocs) (abfd, obj_datasec (abfd))) \
+ if (!NAME (aout, squirt_out_relocs) (abfd, obj_datasec (abfd))) \
return FALSE; \
} \
}
#include "aout/aout64.h"
static bfd_reloc_status_type
-riscix_fix_pcrel_26_done PARAMS ((bfd *, arelent *, asymbol *, PTR,
- asection *, bfd *, char **));
-
-static bfd_reloc_status_type
-riscix_fix_pcrel_26 PARAMS ((bfd *, arelent *, asymbol *, PTR,
- asection *, bfd *, char **));
-static const bfd_target *
-MY (object_p) PARAMS ((bfd *));
-
-reloc_howto_type *
-riscix_reloc_type_lookup PARAMS ((bfd *, bfd_reloc_code_real_type));
-
-void
-riscix_swap_std_reloc_out PARAMS ((bfd *, arelent *, struct reloc_std_external *));
-
-bfd_boolean
-riscix_squirt_out_relocs PARAMS ((bfd *, asection *));
-
-long
-MY (canonicalize_reloc) PARAMS ((bfd *, sec_ptr, arelent **, asymbol **));
-
-const bfd_target *
-riscix_some_aout_object_p PARAMS ((bfd *, struct internal_exec *, const bfd_target *(*) (bfd *)));
+riscix_fix_pcrel_26_done (bfd *abfd ATTRIBUTE_UNUSED,
+ arelent *reloc_entry ATTRIBUTE_UNUSED,
+ asymbol *symbol ATTRIBUTE_UNUSED,
+ void * data ATTRIBUTE_UNUSED,
+ asection *input_section ATTRIBUTE_UNUSED,
+ bfd *output_bfd ATTRIBUTE_UNUSED,
+ char **error_message ATTRIBUTE_UNUSED)
+{
+ /* This is dead simple at present. */
+ return bfd_reloc_ok;
+}
+static bfd_reloc_status_type riscix_fix_pcrel_26 (bfd *, arelent *, asymbol *, void *, asection *, bfd *, char **);
+static const bfd_target *riscix_callback (bfd *);
-static reloc_howto_type riscix_std_reloc_howto[] = {
- /* type rs size bsz pcrel bitpos ovrf sf name part_inpl readmask setmask pcdone */
- HOWTO( 0, 0, 0, 8, FALSE, 0, complain_overflow_bitfield,0,"8", TRUE, 0x000000ff,0x000000ff, FALSE),
+static reloc_howto_type riscix_std_reloc_howto[] =
+{
+ /* Type rs size bsz pcrel bitpos ovrf sf name part_inpl readmask setmask pcdone */
+ HOWTO( 0, 0, 0, 8, FALSE, 0, complain_overflow_bitfield,0,"8", TRUE, 0x000000ff,0x000000ff, FALSE),
HOWTO( 1, 0, 1, 16, FALSE, 0, complain_overflow_bitfield,0,"16", TRUE, 0x0000ffff,0x0000ffff, FALSE),
HOWTO( 2, 0, 2, 32, FALSE, 0, complain_overflow_bitfield,0,"32", TRUE, 0xffffffff,0xffffffff, FALSE),
- HOWTO( 3, 2, 3, 26, TRUE, 0, complain_overflow_signed, riscix_fix_pcrel_26 , "ARM26", TRUE, 0x00ffffff,0x00ffffff, FALSE),
+ HOWTO( 3, 2, 3, 26, TRUE, 0, complain_overflow_signed, riscix_fix_pcrel_26 , "ARM26", TRUE, 0x00ffffff,0x00ffffff, FALSE),
HOWTO( 4, 0, 0, 8, TRUE, 0, complain_overflow_signed, 0,"DISP8", TRUE, 0x000000ff,0x000000ff, TRUE),
HOWTO( 5, 0, 1, 16, TRUE, 0, complain_overflow_signed, 0,"DISP16", TRUE, 0x0000ffff,0x0000ffff, TRUE),
HOWTO( 6, 0, 2, 32, TRUE, 0, complain_overflow_signed, 0,"DISP32", TRUE, 0xffffffff,0xffffffff, TRUE),
HOWTO( 7, 2, 3, 26, FALSE, 0, complain_overflow_signed, riscix_fix_pcrel_26_done, "ARM26D",TRUE,0x00ffffff,0x00ffffff, FALSE),
EMPTY_HOWTO (-1),
- HOWTO( 9, 0, -1, 16, FALSE, 0, complain_overflow_bitfield,0,"NEG16", TRUE, 0x0000ffff,0x0000ffff, FALSE),
- HOWTO( 10, 0, -2, 32, FALSE, 0, complain_overflow_bitfield,0,"NEG32", TRUE, 0xffffffff,0xffffffff, FALSE)
+ HOWTO( 9, 0, -1, 16, FALSE, 0, complain_overflow_bitfield,0,"NEG16", TRUE, 0x0000ffff,0x0000ffff, FALSE),
+ HOWTO( 10, 0, -2, 32, FALSE, 0, complain_overflow_bitfield,0,"NEG32", TRUE, 0xffffffff,0xffffffff, FALSE)
};
#define RISCIX_TABLE_SIZE \
(sizeof (riscix_std_reloc_howto) / sizeof (reloc_howto_type))
static bfd_reloc_status_type
-riscix_fix_pcrel_26_done (abfd, reloc_entry, symbol, data, input_section,
- output_bfd, error_message)
- bfd *abfd ATTRIBUTE_UNUSED;
- arelent *reloc_entry ATTRIBUTE_UNUSED;
- asymbol *symbol ATTRIBUTE_UNUSED;
- PTR data ATTRIBUTE_UNUSED;
- asection *input_section ATTRIBUTE_UNUSED;
- bfd *output_bfd ATTRIBUTE_UNUSED;
- char **error_message ATTRIBUTE_UNUSED;
-{
- /* This is dead simple at present. */
- return bfd_reloc_ok;
-}
-
-static bfd_reloc_status_type
-riscix_fix_pcrel_26 (abfd, reloc_entry, symbol, data, input_section,
- output_bfd, error_message)
- bfd *abfd;
- arelent *reloc_entry;
- asymbol *symbol;
- PTR data;
- asection *input_section;
- bfd *output_bfd;
- char **error_message ATTRIBUTE_UNUSED;
+riscix_fix_pcrel_26 (bfd *abfd,
+ arelent *reloc_entry,
+ asymbol *symbol,
+ void * data,
+ asection *input_section,
+ bfd *output_bfd,
+ char **error_message ATTRIBUTE_UNUSED)
{
bfd_vma relocation;
bfd_size_type addr = reloc_entry->address;
long target = bfd_get_32 (abfd, (bfd_byte *) data + addr);
bfd_reloc_status_type flag = bfd_reloc_ok;
- /* If this is an undefined symbol, return error */
+ /* If this is an undefined symbol, return error. */
if (symbol->section == &bfd_und_section
&& (symbol->flags & BSF_WEAK) == 0)
return output_bfd ? bfd_reloc_continue : bfd_reloc_undefined;
/* If the sections are different, and we are doing a partial relocation,
just ignore it for now. */
if (symbol->section->name != input_section->name
- && output_bfd != (bfd *)NULL)
+ && output_bfd != NULL)
return bfd_reloc_continue;
relocation = (target & 0x00ffffff) << 2;
- relocation = (relocation ^ 0x02000000) - 0x02000000; /* Sign extend */
+ relocation = (relocation ^ 0x02000000) - 0x02000000; /* Sign extend. */
relocation += symbol->value;
relocation += symbol->section->output_section->vma;
relocation += symbol->section->output_offset;
if (relocation & 3)
return bfd_reloc_overflow;
- /* Check for overflow */
+ /* Check for overflow. */
if (relocation & 0x02000000)
{
if ((relocation & ~ (bfd_vma) 0x03ffffff) != ~ (bfd_vma) 0x03ffffff)
return flag;
}
-reloc_howto_type *
-riscix_reloc_type_lookup (abfd, code)
- bfd *abfd;
- bfd_reloc_code_real_type code;
+static reloc_howto_type *
+riscix_reloc_type_lookup (bfd *abfd, bfd_reloc_code_real_type code)
{
#define ASTD(i,j) case i: return &riscix_std_reloc_howto[j]
if (code == BFD_RELOC_CTOR)
case 32:
code = BFD_RELOC_32;
break;
- default: return (reloc_howto_type *) NULL;
+ default:
+ return NULL;
}
switch (code)
ASTD (BFD_RELOC_8_PCREL, 4);
ASTD (BFD_RELOC_16_PCREL, 5);
ASTD (BFD_RELOC_32_PCREL, 6);
- default: return (reloc_howto_type *) NULL;
+ default:
+ return NULL;
}
}
-#define MY_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
-#define MY_bfd_link_add_symbols _bfd_generic_link_add_symbols
-#define MY_final_link_callback should_not_be_used
-#define MY_bfd_final_link _bfd_generic_final_link
+#define MY_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
+#define MY_bfd_link_add_symbols _bfd_generic_link_add_symbols
+#define MY_final_link_callback should_not_be_used
+#define MY_bfd_final_link _bfd_generic_final_link
-#define MY_bfd_reloc_type_lookup riscix_reloc_type_lookup
-#define MY_canonicalize_reloc riscix_canonicalize_reloc
-#define MY_object_p riscix_object_p
+#define MY_bfd_reloc_type_lookup riscix_reloc_type_lookup
+#define MY_canonicalize_reloc riscix_canonicalize_reloc
+#define MY_object_p riscix_object_p
-static const bfd_target *riscix_callback PARAMS ((bfd *));
-
-void
-riscix_swap_std_reloc_out (abfd, g, natptr)
- bfd *abfd;
- arelent *g;
- struct reloc_std_external *natptr;
+static void
+riscix_swap_std_reloc_out (bfd *abfd,
+ arelent *g,
+ struct reloc_std_external *natptr)
{
int r_index;
asymbol *sym = *(g->sym_ptr_ptr);
PUT_WORD(abfd, g->address, natptr->r_address);
- r_length = g->howto->size ; /* Size as a power of two */
+ r_length = g->howto->size ; /* Size as a power of two. */
if (r_length < 0)
{
r_length = -r_length;
r_neg = 1;
}
- r_pcrel = (int) g->howto->pc_relative; /* Relative to PC? */
+ r_pcrel = (int) g->howto->pc_relative; /* Relative to PC? */
/* For RISC iX, in pc-relative relocs the r_pcrel bit means that the
- relocation has been done already (Only for the 26-bit one I think)???!!!
- */
-
+ relocation has been done already (Only for the 26-bit one I think)? */
if (r_length == 3)
r_pcrel = r_pcrel ? 0 : 1;
- /* name was clobbered by aout_write_syms to be symbol index */
+ /* Name was clobbered by aout_write_syms to be symbol index. */
/* If this relocation is relative to a symbol then set the
r_index to the symbols index, and the r_extern bit.
Absolute symbols can come in in two ways, either as an offset
from the abs section, or as a symbol which has an abs value.
- check for that here
- */
+ check for that here. */
if (bfd_is_com_section (output_section)
- || output_section == &bfd_abs_section
- || output_section == &bfd_und_section)
+ || output_section == & bfd_abs_section
+ || output_section == & bfd_und_section)
{
if (bfd_abs_section.symbol == sym)
{
/* Whoops, looked like an abs symbol, but is really an offset
- from the abs section */
+ from the abs section. */
r_index = 0;
r_extern = 0;
}
else
{
- /* Fill in symbol */
+ /* Fill in symbol. */
r_extern = 1;
r_index = (*g->sym_ptr_ptr)->udata.i;
}
}
else
{
- /* Just an ordinary section */
+ /* Just an ordinary section. */
r_extern = 0;
r_index = output_section->target_index;
}
- /* now the fun stuff */
+ /* Now the fun stuff. */
if (bfd_header_big_endian (abfd))
{
natptr->r_index[0] = r_index >> 16;
}
}
-bfd_boolean
-riscix_squirt_out_relocs (abfd, section)
- bfd *abfd;
- asection *section;
+static bfd_boolean
+riscix_squirt_out_relocs (bfd *abfd, asection *section)
{
arelent **generic;
unsigned char *native, *natptr;
size_t each_size;
-
unsigned int count = section->reloc_count;
bfd_size_type natsize;
each_size = obj_reloc_entry_size (abfd);
natsize = each_size;
natsize *= count;
- native = (unsigned char *) bfd_zalloc (abfd, natsize);
+ native = bfd_zalloc (abfd, natsize);
if (!native)
return FALSE;
riscix_swap_std_reloc_out (abfd, *generic,
(struct reloc_std_external *) natptr);
- if (bfd_bwrite ((PTR) native, natsize, abfd) != natsize)
+ if (bfd_bwrite ((void *) native, natsize, abfd) != natsize)
{
bfd_release (abfd, native);
return FALSE;
return TRUE;
}
-/*
- * This is just like the standard aoutx.h version but we need to do our
- * own mapping of external reloc type values to howto entries.
- */
-long
-MY(canonicalize_reloc) (abfd, section, relptr, symbols)
- bfd *abfd;
- sec_ptr section;
- arelent **relptr;
- asymbol **symbols;
+/* This is just like the standard aoutx.h version but we need to do our
+ own mapping of external reloc type values to howto entries. */
+
+static long
+MY (canonicalize_reloc) (bfd *abfd,
+ sec_ptr section,
+ arelent **relptr,
+ asymbol **symbols)
{
arelent *tblptr = section->relocation;
unsigned int count, c;
- extern reloc_howto_type NAME(aout,std_howto_table)[];
+ extern reloc_howto_type NAME (aout, std_howto_table)[];
/* If we have already read in the relocation table, return the values. */
- if (section->flags & SEC_CONSTRUCTOR) {
- arelent_chain *chain = section->constructor_chain;
+ if (section->flags & SEC_CONSTRUCTOR)
+ {
+ arelent_chain *chain = section->constructor_chain;
- for (count = 0; count < section->reloc_count; count++) {
- *relptr++ = &chain->relent;
- chain = chain->next;
+ for (count = 0; count < section->reloc_count; count++)
+ {
+ *relptr++ = &chain->relent;
+ chain = chain->next;
+ }
+ *relptr = 0;
+ return section->reloc_count;
}
- *relptr = 0;
- return section->reloc_count;
- }
- if (tblptr && section->reloc_count) {
- for (count = 0; count++ < section->reloc_count;)
- *relptr++ = tblptr++;
- *relptr = 0;
- return section->reloc_count;
- }
- if (!NAME(aout,slurp_reloc_table) (abfd, section, symbols))
+ if (tblptr && section->reloc_count)
+ {
+ for (count = 0; count++ < section->reloc_count;)
+ *relptr++ = tblptr++;
+ *relptr = 0;
+ return section->reloc_count;
+ }
+
+ if (!NAME (aout, slurp_reloc_table) (abfd, section, symbols))
return -1;
tblptr = section->relocation;
- /* fix up howto entries */
+ /* Fix up howto entries. */
for (count = 0; count++ < section->reloc_count;)
{
c = tblptr->howto - NAME(aout,std_howto_table);
/* This is the same as NAME(aout,some_aout_object_p), but has different
expansions of the macro definitions. */
-const bfd_target *
-riscix_some_aout_object_p (abfd, execp, callback_to_real_object_p)
- bfd *abfd;
- struct internal_exec *execp;
- const bfd_target *(*callback_to_real_object_p) PARAMS ((bfd *));
+static const bfd_target *
+riscix_some_aout_object_p (bfd *abfd,
+ struct internal_exec *execp,
+ const bfd_target *(*callback_to_real_object_p) (bfd *))
{
struct aout_data_struct *rawptr, *oldrawptr;
const bfd_target *result;
bfd_size_type amt = sizeof (struct aout_data_struct);
- rawptr = (struct aout_data_struct *) bfd_zalloc (abfd, amt);
+ rawptr = bfd_zalloc (abfd, amt);
if (rawptr == NULL)
- return 0;
+ return NULL;
oldrawptr = abfd->tdata.aout_data;
abfd->tdata.aout_data = rawptr;
*abfd->tdata.aout_data = *oldrawptr;
abfd->tdata.aout_data->a.hdr = &rawptr->e;
- *(abfd->tdata.aout_data->a.hdr) = *execp; /* Copy in the internal_exec
- struct */
+ /* Copy in the internal_exec struct. */
+ *(abfd->tdata.aout_data->a.hdr) = *execp;
execp = abfd->tdata.aout_data->a.hdr;
- /* Set the file flags */
+ /* Set the file flags. */
abfd->flags = BFD_NO_FLAGS;
if (execp->a_drsize || execp->a_trsize)
abfd->flags |= HAS_RELOC;
- /* Setting of EXEC_P has been deferred to the bottom of this function */
+ /* Setting of EXEC_P has been deferred to the bottom of this function. */
if (execp->a_syms)
abfd->flags |= HAS_LINENO | HAS_DEBUG | HAS_SYMS | HAS_LOCALS;
if (N_DYNAMIC(*execp))
abfd->flags |= DYNAMIC;
- if ((execp->a_info & MF_SQUEEZED) != 0) /* Squeezed files aren't supported
- (yet)! */
+ /* Squeezed files aren't supported (yet)! */
+ if ((execp->a_info & MF_SQUEEZED) != 0)
{
bfd_set_error (bfd_error_wrong_format);
return NULL;
}
- else if ((execp->a_info & MF_IS_SL) != 0) /* Nor are shared libraries */
+ else if ((execp->a_info & MF_IS_SL) != 0)
{
+ /* Nor are shared libraries. */
bfd_set_error (bfd_error_wrong_format);
return NULL;
}
else if (N_MAGIC (*execp) == OMAGIC)
adata (abfd).magic = o_magic;
else
- {
- /* Should have been checked with N_BADMAG before this routine
- was called. */
- abort ();
- }
+ /* Should have been checked with N_BADMAG before this routine
+ was called. */
+ abort ();
bfd_get_start_address (abfd) = execp->a_entry;
- obj_aout_symbols (abfd) = (aout_symbol_type *)NULL;
+ obj_aout_symbols (abfd) = NULL;
bfd_get_symcount (abfd) = execp->a_syms / sizeof (struct external_nlist);
/* The default relocation entry size is that of traditional V7 Unix. */
obj_aout_external_strings (abfd) = NULL;
obj_aout_sym_hashes (abfd) = NULL;
- if (! NAME(aout,make_sections) (abfd))
+ if (! NAME (aout, make_sections) (abfd))
return NULL;
obj_datasec (abfd)->size = execp->a_data;
#if defined(MACH) || defined(STAT_FOR_EXEC)
/* The original heuristic doesn't work in some important cases. The
- * a.out file has no information about the text start address. For
- * files (like kernels) linked to non-standard addresses (ld -Ttext
- * nnn) the entry point may not be between the default text start
- * (obj_textsec(abfd)->vma) and (obj_textsec(abfd)->vma) + text size
- * This is not just a mach issue. Many kernels are loaded at non
- * standard addresses.
- */
+ a.out file has no information about the text start address. For
+ files (like kernels) linked to non-standard addresses (ld -Ttext
+ nnn) the entry point may not be between the default text start
+ (obj_textsec(abfd)->vma) and (obj_textsec(abfd)->vma) + text size
+ This is not just a mach issue. Many kernels are loaded at non
+ standard addresses. */
{
struct stat stat_buf;
+
if (abfd->iostream != NULL
&& (abfd->flags & BFD_IN_MEMORY) == 0
&& (fstat(fileno((FILE *) (abfd->iostream)), &stat_buf) == 0)
(execp->a_entry < obj_textsec(abfd)->vma + obj_textsec(abfd)->size))
abfd->flags |= EXEC_P;
#endif /* MACH */
- if (result)
- {
- }
- else
+ if (result == NULL)
{
free (rawptr);
abfd->tdata.aout_data = oldrawptr;
}
static const bfd_target *
-MY(object_p) (abfd)
- bfd *abfd;
+MY (object_p) (bfd *abfd)
{
- struct external_exec exec_bytes; /* Raw exec header from file */
- struct internal_exec exec; /* Cleaned-up exec header */
+ struct external_exec exec_bytes; /* Raw exec header from file. */
+ struct internal_exec exec; /* Cleaned-up exec header. */
const bfd_target *target;
- if (bfd_bread ((PTR) &exec_bytes, (bfd_size_type) EXEC_BYTES_SIZE, abfd)
+ if (bfd_bread ((void *) &exec_bytes, (bfd_size_type) EXEC_BYTES_SIZE, abfd)
!= EXEC_BYTES_SIZE)
{
if (bfd_get_error () != bfd_error_system_call)
bfd_set_error (bfd_error_wrong_format);
- return 0;
+ return NULL;
}
exec.a_info = H_GET_32 (abfd, exec_bytes.e_info);
- if (N_BADMAG (exec)) return 0;
+ if (N_BADMAG (exec))
+ return NULL;
+
#ifdef MACHTYPE_OK
- if (!(MACHTYPE_OK (N_MACHTYPE (exec)))) return 0;
+ if (!(MACHTYPE_OK (N_MACHTYPE (exec))))
+ return NULL;
#endif
- NAME(aout,swap_exec_header_in) (abfd, &exec_bytes, &exec);
+ NAME (aout, swap_exec_header_in) (abfd, & exec_bytes, & exec);
- target = riscix_some_aout_object_p (abfd, &exec, MY(callback));
+ target = riscix_some_aout_object_p (abfd, & exec, MY (callback));
return target;
}
Note one side effect of using a R_PREV_FIXUP is the relocation that
is being repeated moves to the front of the queue. */
-struct reloc_queue {
+struct reloc_queue
+{
unsigned char *reloc;
unsigned int size;
} reloc_queue[4];
/* This fully describes the symbol types which may be attached to
an EXPORT or IMPORT directive. Only SOM uses this formation
(ELF has no need for it). */
-typedef enum {
+typedef enum
+{
SYMBOL_TYPE_UNKNOWN,
SYMBOL_TYPE_ABSOLUTE,
SYMBOL_TYPE_CODE,
SYMBOL_TYPE_SEC_PROG,
} pa_symbol_type;
-struct section_to_type {
+struct section_to_type
+{
char *section;
char type;
};
/* Assorted symbol information that needs to be derived from the BFD symbol
and/or the BFD backend private symbol data. */
-struct som_misc_symbol_info {
+struct som_misc_symbol_info
+{
unsigned int symbol_type;
unsigned int symbol_scope;
unsigned int arg_reloc;
unsigned int dup_common;
};
-/* Forward declarations. */
-
-static bfd_boolean som_mkobject
- PARAMS ((bfd *));
-static const bfd_target * som_object_setup
- PARAMS ((bfd *, struct header *, struct som_exec_auxhdr *, unsigned long));
-static bfd_boolean setup_sections
- PARAMS ((bfd *, struct header *, unsigned long));
-static const bfd_target * som_object_p
- PARAMS ((bfd *));
-static bfd_boolean som_write_object_contents
- PARAMS ((bfd *));
-static bfd_boolean som_slurp_string_table
- PARAMS ((bfd *));
-static unsigned int som_slurp_symbol_table
- PARAMS ((bfd *));
-static long som_get_symtab_upper_bound
- PARAMS ((bfd *));
-static long som_canonicalize_reloc
- PARAMS ((bfd *, sec_ptr, arelent **, asymbol **));
-static long som_get_reloc_upper_bound
- PARAMS ((bfd *, sec_ptr));
-static unsigned int som_set_reloc_info
- PARAMS ((unsigned char *, unsigned int, arelent *, asection *,
- asymbol **, bfd_boolean));
-static bfd_boolean som_slurp_reloc_table
- PARAMS ((bfd *, asection *, asymbol **, bfd_boolean));
-static long som_canonicalize_symtab
- PARAMS ((bfd *, asymbol **));
-static asymbol * som_make_empty_symbol
- PARAMS ((bfd *));
-static void som_print_symbol
- PARAMS ((bfd *, PTR, asymbol *, bfd_print_symbol_type));
-static bfd_boolean som_new_section_hook
- PARAMS ((bfd *, asection *));
-static bfd_boolean som_bfd_copy_private_symbol_data
- PARAMS ((bfd *, asymbol *, bfd *, asymbol *));
-static bfd_boolean som_bfd_copy_private_section_data
- PARAMS ((bfd *, asection *, bfd *, asection *));
-static bfd_boolean som_bfd_copy_private_bfd_data
- PARAMS ((bfd *, bfd *));
-#define som_bfd_copy_private_header_data \
- _bfd_generic_bfd_copy_private_header_data
-#define som_bfd_merge_private_bfd_data _bfd_generic_bfd_merge_private_bfd_data
-#define som_bfd_set_private_flags _bfd_generic_bfd_set_private_flags
-static bfd_boolean som_bfd_print_private_bfd_data
- (bfd *, void *);
-static bfd_boolean som_bfd_is_local_label_name
- PARAMS ((bfd *, const char *));
-static bfd_boolean som_set_section_contents
- PARAMS ((bfd *, sec_ptr, const PTR, file_ptr, bfd_size_type));
-static bfd_boolean som_get_section_contents
- PARAMS ((bfd *, sec_ptr, PTR, file_ptr, bfd_size_type));
-static bfd_boolean som_set_arch_mach
- PARAMS ((bfd *, enum bfd_architecture, unsigned long));
-static bfd_boolean som_find_nearest_line
- PARAMS ((bfd *, asection *, asymbol **, bfd_vma, const char **,
- const char **, unsigned int *));
-static void som_get_symbol_info
- PARAMS ((bfd *, asymbol *, symbol_info *));
-static asection * bfd_section_from_som_symbol
- PARAMS ((bfd *, struct symbol_dictionary_record *));
-static int exact_log2
- PARAMS ((unsigned int));
-static bfd_reloc_status_type hppa_som_reloc
- PARAMS ((bfd *, arelent *, asymbol *, PTR, asection *, bfd *, char **));
-static void som_initialize_reloc_queue
- PARAMS ((struct reloc_queue *));
-static void som_reloc_queue_insert
- PARAMS ((unsigned char *, unsigned int, struct reloc_queue *));
-static void som_reloc_queue_fix
- PARAMS ((struct reloc_queue *, unsigned int));
-static int som_reloc_queue_find
- PARAMS ((unsigned char *, unsigned int, struct reloc_queue *));
-static unsigned char * try_prev_fixup
- PARAMS ((bfd *, int *, unsigned char *, unsigned int, struct reloc_queue *));
-static unsigned char * som_reloc_skip
- PARAMS ((bfd *, unsigned int, unsigned char *, unsigned int *,
- struct reloc_queue *));
-static unsigned char * som_reloc_addend
- PARAMS ((bfd *, bfd_vma, unsigned char *, unsigned int *,
- struct reloc_queue *));
-static unsigned char * som_reloc_call
- PARAMS ((bfd *, unsigned char *, unsigned int *, arelent *, int,
- struct reloc_queue *));
-static unsigned long som_count_spaces
- PARAMS ((bfd *));
-static unsigned long som_count_subspaces
- PARAMS ((bfd *));
-static int compare_syms
- PARAMS ((const void *, const void *));
-static int compare_subspaces
- PARAMS ((const void *, const void *));
-static unsigned long som_compute_checksum
- PARAMS ((bfd *));
-static bfd_boolean som_prep_headers
- PARAMS ((bfd *));
-static int som_sizeof_headers
- PARAMS ((bfd *, bfd_boolean));
-static bfd_boolean som_finish_writing
- PARAMS ((bfd *));
-static bfd_boolean som_build_and_write_symbol_table
- PARAMS ((bfd *));
-static void som_prep_for_fixups
- PARAMS ((bfd *, asymbol **, unsigned long));
-static bfd_boolean som_write_fixups
- PARAMS ((bfd *, unsigned long, unsigned int *));
-static bfd_boolean som_write_space_strings
- PARAMS ((bfd *, unsigned long, unsigned int *));
-static bfd_boolean som_write_symbol_strings
- PARAMS ((bfd *, unsigned long, asymbol **, unsigned int, unsigned *,
- COMPUNIT *));
-static bfd_boolean som_begin_writing
- PARAMS ((bfd *));
-static reloc_howto_type * som_bfd_reloc_type_lookup
- PARAMS ((bfd *, bfd_reloc_code_real_type));
-static char som_section_type
- PARAMS ((const char *));
-static int som_decode_symclass
- PARAMS ((asymbol *));
-static bfd_boolean som_bfd_count_ar_symbols
- PARAMS ((bfd *, struct lst_header *, symindex *));
-static bfd_boolean som_bfd_fill_in_ar_symbols
- PARAMS ((bfd *, struct lst_header *, carsym **));
-static bfd_boolean som_slurp_armap
- PARAMS ((bfd *));
-static bfd_boolean som_write_armap
- PARAMS ((bfd *, unsigned int, struct orl *, unsigned int, int));
-static void som_bfd_derive_misc_symbol_info
- PARAMS ((bfd *, asymbol *, struct som_misc_symbol_info *));
-static bfd_boolean som_bfd_prep_for_ar_write
- PARAMS ((bfd *, unsigned int *, unsigned int *));
-static unsigned int som_bfd_ar_symbol_hash
- PARAMS ((asymbol *));
-static bfd_boolean som_bfd_ar_write_symbol_stuff
- PARAMS ((bfd *, unsigned int, unsigned int, struct lst_header,
- unsigned int));
-static bfd_boolean som_is_space
- PARAMS ((asection *));
-static bfd_boolean som_is_subspace
- PARAMS ((asection *));
-static bfd_boolean som_is_container
- PARAMS ((asection *, asection *));
-static bfd_boolean som_bfd_free_cached_info
- PARAMS ((bfd *));
-static bfd_boolean som_bfd_link_split_section
- PARAMS ((bfd *, asection *));
-
/* Map SOM section names to POSIX/BSD single-character symbol types.
This table includes all the standard subspaces as defined in the
current "PRO ABI for PA-RISC Systems", $UNWIND$ which for
some reason was left out, and sections specific to embedded stabs. */
-static const struct section_to_type stt[] = {
+static const struct section_to_type stt[] =
+{
{"$TEXT$", 't'},
{"$SHLIB_INFO$", 't'},
{"$MILLICODE$", 't'},
addil foo-$global$-0x1234 would use an override for "0x1234" rather
than storing it into the addil itself. */
-struct fixup_format {
+struct fixup_format
+{
int D;
const char *format;
};
-static const struct fixup_format som_fixup_formats[256] = {
- /* R_NO_RELOCATION */
+static const struct fixup_format som_fixup_formats[256] =
+{
+ /* R_NO_RELOCATION. */
{ 0, "LD1+4*=" }, /* 0x00 */
{ 1, "LD1+4*=" }, /* 0x01 */
{ 2, "LD1+4*=" }, /* 0x02 */
{ 1, "LD16<c+1+4*=" }, /* 0x1d */
{ 2, "LD16<c+1+4*=" }, /* 0x1e */
{ 0, "Ld1+=" }, /* 0x1f */
- /* R_ZEROES */
+ /* R_ZEROES. */
{ 0, "Lb1+4*=" }, /* 0x20 */
{ 1, "Ld1+=" }, /* 0x21 */
- /* R_UNINIT */
+ /* R_UNINIT. */
{ 0, "Lb1+4*=" }, /* 0x22 */
{ 1, "Ld1+=" }, /* 0x23 */
- /* R_RELOCATION */
+ /* R_RELOCATION. */
{ 0, "L4=" }, /* 0x24 */
- /* R_DATA_ONE_SYMBOL */
+ /* R_DATA_ONE_SYMBOL. */
{ 0, "L4=Sb=" }, /* 0x25 */
{ 1, "L4=Sd=" }, /* 0x26 */
- /* R_DATA_PLEBEL */
+ /* R_DATA_PLEBEL. */
{ 0, "L4=Sb=" }, /* 0x27 */
{ 1, "L4=Sd=" }, /* 0x28 */
- /* R_SPACE_REF */
+ /* R_SPACE_REF. */
{ 0, "L4=" }, /* 0x29 */
- /* R_REPEATED_INIT */
+ /* R_REPEATED_INIT. */
{ 0, "L4=Mb1+4*=" }, /* 0x2a */
{ 1, "Lb4*=Mb1+L*=" }, /* 0x2b */
{ 2, "Lb4*=Md1+4*=" }, /* 0x2c */
{ 3, "Ld1+=Me1+=" }, /* 0x2d */
{ 0, "" }, /* 0x2e */
{ 0, "" }, /* 0x2f */
- /* R_PCREL_CALL */
+ /* R_PCREL_CALL. */
{ 0, "L4=RD=Sb=" }, /* 0x30 */
{ 1, "L4=RD=Sb=" }, /* 0x31 */
{ 2, "L4=RD=Sb=" }, /* 0x32 */
{ 1, "L4=RD8<b+=Sb=" }, /* 0x3b */
{ 0, "L4=RD8<b+=Sd=" }, /* 0x3c */
{ 1, "L4=RD8<b+=Sd=" }, /* 0x3d */
- /* R_SHORT_PCREL_MODE */
+ /* R_SHORT_PCREL_MODE. */
{ 0, "" }, /* 0x3e */
- /* R_LONG_PCREL_MODE */
+ /* R_LONG_PCREL_MODE. */
{ 0, "" }, /* 0x3f */
- /* R_ABS_CALL */
+ /* R_ABS_CALL. */
{ 0, "L4=RD=Sb=" }, /* 0x40 */
{ 1, "L4=RD=Sb=" }, /* 0x41 */
{ 2, "L4=RD=Sb=" }, /* 0x42 */
{ 1, "L4=RD8<b+=Sb=" }, /* 0x4b */
{ 0, "L4=RD8<b+=Sd=" }, /* 0x4c */
{ 1, "L4=RD8<b+=Sd=" }, /* 0x4d */
- /* R_RESERVED */
+ /* R_RESERVED. */
{ 0, "" }, /* 0x4e */
{ 0, "" }, /* 0x4f */
- /* R_DP_RELATIVE */
+ /* R_DP_RELATIVE. */
{ 0, "L4=SD=" }, /* 0x50 */
{ 1, "L4=SD=" }, /* 0x51 */
{ 2, "L4=SD=" }, /* 0x52 */
{ 31, "L4=SD=" }, /* 0x6f */
{ 32, "L4=Sb=" }, /* 0x70 */
{ 33, "L4=Sd=" }, /* 0x71 */
- /* R_RESERVED */
+ /* R_RESERVED. */
{ 0, "" }, /* 0x72 */
{ 0, "" }, /* 0x73 */
{ 0, "" }, /* 0x74 */
{ 0, "" }, /* 0x75 */
{ 0, "" }, /* 0x76 */
{ 0, "" }, /* 0x77 */
- /* R_DLT_REL */
+ /* R_DLT_REL. */
{ 0, "L4=Sb=" }, /* 0x78 */
{ 1, "L4=Sd=" }, /* 0x79 */
- /* R_RESERVED */
+ /* R_RESERVED. */
{ 0, "" }, /* 0x7a */
{ 0, "" }, /* 0x7b */
{ 0, "" }, /* 0x7c */
{ 0, "" }, /* 0x7d */
{ 0, "" }, /* 0x7e */
{ 0, "" }, /* 0x7f */
- /* R_CODE_ONE_SYMBOL */
+ /* R_CODE_ONE_SYMBOL. */
{ 0, "L4=SD=" }, /* 0x80 */
{ 1, "L4=SD=" }, /* 0x81 */
{ 2, "L4=SD=" }, /* 0x82 */
{ 31, "L4=SD=" }, /* 0x9f */
{ 32, "L4=Sb=" }, /* 0xa0 */
{ 33, "L4=Sd=" }, /* 0xa1 */
- /* R_RESERVED */
+ /* R_RESERVED. */
{ 0, "" }, /* 0xa2 */
{ 0, "" }, /* 0xa3 */
{ 0, "" }, /* 0xa4 */
{ 0, "" }, /* 0xab */
{ 0, "" }, /* 0xac */
{ 0, "" }, /* 0xad */
- /* R_MILLI_REL */
+ /* R_MILLI_REL. */
{ 0, "L4=Sb=" }, /* 0xae */
{ 1, "L4=Sd=" }, /* 0xaf */
- /* R_CODE_PLABEL */
+ /* R_CODE_PLABEL. */
{ 0, "L4=Sb=" }, /* 0xb0 */
{ 1, "L4=Sd=" }, /* 0xb1 */
- /* R_BREAKPOINT */
+ /* R_BREAKPOINT. */
{ 0, "L4=" }, /* 0xb2 */
- /* R_ENTRY */
+ /* R_ENTRY. */
{ 0, "Te=Ue=" }, /* 0xb3 */
{ 1, "Uf=" }, /* 0xb4 */
- /* R_ALT_ENTRY */
+ /* R_ALT_ENTRY. */
{ 0, "" }, /* 0xb5 */
- /* R_EXIT */
+ /* R_EXIT. */
{ 0, "" }, /* 0xb6 */
- /* R_BEGIN_TRY */
+ /* R_BEGIN_TRY. */
{ 0, "" }, /* 0xb7 */
- /* R_END_TRY */
+ /* R_END_TRY. */
{ 0, "R0=" }, /* 0xb8 */
{ 1, "Rb4*=" }, /* 0xb9 */
{ 2, "Rd4*=" }, /* 0xba */
- /* R_BEGIN_BRTAB */
+ /* R_BEGIN_BRTAB. */
{ 0, "" }, /* 0xbb */
- /* R_END_BRTAB */
+ /* R_END_BRTAB. */
{ 0, "" }, /* 0xbc */
- /* R_STATEMENT */
+ /* R_STATEMENT. */
{ 0, "Nb=" }, /* 0xbd */
{ 1, "Nc=" }, /* 0xbe */
{ 2, "Nd=" }, /* 0xbf */
- /* R_DATA_EXPR */
+ /* R_DATA_EXPR. */
{ 0, "L4=" }, /* 0xc0 */
- /* R_CODE_EXPR */
+ /* R_CODE_EXPR. */
{ 0, "L4=" }, /* 0xc1 */
- /* R_FSEL */
+ /* R_FSEL. */
{ 0, "" }, /* 0xc2 */
- /* R_LSEL */
+ /* R_LSEL. */
{ 0, "" }, /* 0xc3 */
- /* R_RSEL */
+ /* R_RSEL. */
{ 0, "" }, /* 0xc4 */
- /* R_N_MODE */
+ /* R_N_MODE. */
{ 0, "" }, /* 0xc5 */
- /* R_S_MODE */
+ /* R_S_MODE. */
{ 0, "" }, /* 0xc6 */
- /* R_D_MODE */
+ /* R_D_MODE. */
{ 0, "" }, /* 0xc7 */
- /* R_R_MODE */
+ /* R_R_MODE. */
{ 0, "" }, /* 0xc8 */
- /* R_DATA_OVERRIDE */
+ /* R_DATA_OVERRIDE. */
{ 0, "V0=" }, /* 0xc9 */
{ 1, "Vb=" }, /* 0xca */
{ 2, "Vc=" }, /* 0xcb */
{ 3, "Vd=" }, /* 0xcc */
{ 4, "Ve=" }, /* 0xcd */
- /* R_TRANSLATED */
+ /* R_TRANSLATED. */
{ 0, "" }, /* 0xce */
- /* R_AUX_UNWIND */
+ /* R_AUX_UNWIND. */
{ 0,"Sd=Ve=Ee=" }, /* 0xcf */
- /* R_COMP1 */
+ /* R_COMP1. */
{ 0, "Ob=" }, /* 0xd0 */
- /* R_COMP2 */
+ /* R_COMP2. */
{ 0, "Ob=Sd=" }, /* 0xd1 */
- /* R_COMP3 */
+ /* R_COMP3. */
{ 0, "Ob=Ve=" }, /* 0xd2 */
- /* R_PREV_FIXUP */
+ /* R_PREV_FIXUP. */
{ 0, "P" }, /* 0xd3 */
{ 1, "P" }, /* 0xd4 */
{ 2, "P" }, /* 0xd5 */
{ 3, "P" }, /* 0xd6 */
- /* R_SEC_STMT */
+ /* R_SEC_STMT. */
{ 0, "" }, /* 0xd7 */
- /* R_N0SEL */
+ /* R_N0SEL. */
{ 0, "" }, /* 0xd8 */
- /* R_N1SEL */
+ /* R_N1SEL. */
{ 0, "" }, /* 0xd9 */
- /* R_LINETAB */
+ /* R_LINETAB. */
{ 0, "Eb=Sd=Ve=" }, /* 0xda */
- /* R_LINETAB_ESC */
+ /* R_LINETAB_ESC. */
{ 0, "Eb=Mb=" }, /* 0xdb */
- /* R_LTP_OVERRIDE */
+ /* R_LTP_OVERRIDE. */
{ 0, "" }, /* 0xdc */
- /* R_COMMENT */
+ /* R_COMMENT. */
{ 0, "Ob=Vf=" }, /* 0xdd */
- /* R_RESERVED */
+ /* R_RESERVED. */
{ 0, "" }, /* 0xde */
{ 0, "" }, /* 0xdf */
{ 0, "" }, /* 0xe0 */
{ 0, "" }, /* 0xff */
};
-static const int comp1_opcodes[] = {
+static const int comp1_opcodes[] =
+{
0x00,
0x40,
0x41,
-1
};
-static const int comp2_opcodes[] = {
+static const int comp2_opcodes[] =
+{
0x00,
0x80,
0x82,
-1
};
-static const int comp3_opcodes[] = {
+static const int comp3_opcodes[] =
+{
0x00,
0x02,
-1
#define SOM_HOWTO(TYPE, NAME) \
HOWTO(TYPE, 0, 0, 32, FALSE, 0, 0, hppa_som_reloc, NAME, FALSE, 0, 0, FALSE)
-static reloc_howto_type som_hppa_howto_table[] = {
+static reloc_howto_type som_hppa_howto_table[] =
+{
SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
the last four multibyte fixups. */
static void
-som_initialize_reloc_queue (queue)
- struct reloc_queue *queue;
+som_initialize_reloc_queue (struct reloc_queue *queue)
{
queue[0].reloc = NULL;
queue[0].size = 0;
/* Insert a new relocation into the relocation queue. */
static void
-som_reloc_queue_insert (p, size, queue)
- unsigned char *p;
- unsigned int size;
- struct reloc_queue *queue;
+som_reloc_queue_insert (unsigned char *p,
+ unsigned int size,
+ struct reloc_queue *queue)
{
queue[3].reloc = queue[2].reloc;
queue[3].size = queue[2].size;
to the front of the queue. */
static void
-som_reloc_queue_fix (queue, index)
- struct reloc_queue *queue;
- unsigned int index;
+som_reloc_queue_fix (struct reloc_queue *queue, unsigned int index)
{
if (index == 0)
return;
{
unsigned char *tmp1 = queue[0].reloc;
unsigned int tmp2 = queue[0].size;
+
queue[0].reloc = queue[1].reloc;
queue[0].size = queue[1].size;
queue[1].reloc = tmp1;
{
unsigned char *tmp1 = queue[0].reloc;
unsigned int tmp2 = queue[0].size;
+
queue[0].reloc = queue[2].reloc;
queue[0].size = queue[2].size;
queue[2].reloc = queue[1].reloc;
{
unsigned char *tmp1 = queue[0].reloc;
unsigned int tmp2 = queue[0].size;
+
queue[0].reloc = queue[3].reloc;
queue[0].size = queue[3].size;
queue[3].reloc = queue[2].reloc;
/* Search for a particular relocation in the relocation queue. */
static int
-som_reloc_queue_find (p, size, queue)
- unsigned char *p;
- unsigned int size;
- struct reloc_queue *queue;
+som_reloc_queue_find (unsigned char *p,
+ unsigned int size,
+ struct reloc_queue *queue)
{
if (queue[0].reloc && !memcmp (p, queue[0].reloc, size)
&& size == queue[0].size)
}
static unsigned char *
-try_prev_fixup (abfd, subspace_reloc_sizep, p, size, queue)
- bfd *abfd ATTRIBUTE_UNUSED;
- int *subspace_reloc_sizep;
- unsigned char *p;
- unsigned int size;
- struct reloc_queue *queue;
+try_prev_fixup (bfd *abfd ATTRIBUTE_UNUSED,
+ int *subspace_reloc_sizep,
+ unsigned char *p,
+ unsigned int size,
+ struct reloc_queue *queue)
{
int queue_index = som_reloc_queue_find (p, size, queue);
current pointer into the relocation stream. */
static unsigned char *
-som_reloc_skip (abfd, skip, p, subspace_reloc_sizep, queue)
- bfd *abfd;
- unsigned int skip;
- unsigned char *p;
- unsigned int *subspace_reloc_sizep;
- struct reloc_queue *queue;
+som_reloc_skip (bfd *abfd,
+ unsigned int skip,
+ unsigned char *p,
+ unsigned int *subspace_reloc_sizep,
+ struct reloc_queue *queue)
{
/* Use a 4 byte R_NO_RELOCATION entry with a maximal value
then R_PREV_FIXUPs to get the difference down to a
into the relocation stream. */
static unsigned char *
-som_reloc_addend (abfd, addend, p, subspace_reloc_sizep, queue)
- bfd *abfd;
- bfd_vma addend;
- unsigned char *p;
- unsigned int *subspace_reloc_sizep;
- struct reloc_queue *queue;
+som_reloc_addend (bfd *abfd,
+ bfd_vma addend,
+ unsigned char *p,
+ unsigned int *subspace_reloc_sizep,
+ struct reloc_queue *queue)
{
if (addend + 0x80 < 0x100)
{
/* Handle a single function call relocation. */
static unsigned char *
-som_reloc_call (abfd, p, subspace_reloc_sizep, bfd_reloc, sym_num, queue)
- bfd *abfd;
- unsigned char *p;
- unsigned int *subspace_reloc_sizep;
- arelent *bfd_reloc;
- int sym_num;
- struct reloc_queue *queue;
+som_reloc_call (bfd *abfd,
+ unsigned char *p,
+ unsigned int *subspace_reloc_sizep,
+ arelent *bfd_reloc,
+ int sym_num,
+ struct reloc_queue *queue)
{
int arg_bits = HPPA_R_ARG_RELOC (bfd_reloc->addend);
int rtn_bits = arg_bits & 0x3;
if X is a power of 2. Otherwise, returns -1. */
static int
-exact_log2 (x)
- unsigned int x;
+exact_log2 (unsigned int x)
{
int log = 0;
}
static bfd_reloc_status_type
-hppa_som_reloc (abfd, reloc_entry, symbol_in, data,
- input_section, output_bfd, error_message)
- bfd *abfd ATTRIBUTE_UNUSED;
- arelent *reloc_entry;
- asymbol *symbol_in ATTRIBUTE_UNUSED;
- PTR data ATTRIBUTE_UNUSED;
- asection *input_section;
- bfd *output_bfd;
- char **error_message ATTRIBUTE_UNUSED;
+hppa_som_reloc (bfd *abfd ATTRIBUTE_UNUSED,
+ arelent *reloc_entry,
+ asymbol *symbol_in ATTRIBUTE_UNUSED,
+ void * data ATTRIBUTE_UNUSED,
+ asection *input_section,
+ bfd *output_bfd,
+ char **error_message ATTRIBUTE_UNUSED)
{
if (output_bfd)
- {
- reloc_entry->address += input_section->output_offset;
- return bfd_reloc_ok;
- }
+ reloc_entry->address += input_section->output_offset;
+
return bfd_reloc_ok;
}
and a field selector, return one or more appropriate SOM relocations. */
int **
-hppa_som_gen_reloc_type (abfd, base_type, format, field, sym_diff, sym)
- bfd *abfd;
- int base_type;
- int format;
- enum hppa_reloc_field_selector_type_alt field;
- int sym_diff;
- asymbol *sym;
+hppa_som_gen_reloc_type (bfd *abfd,
+ int base_type,
+ int format,
+ enum hppa_reloc_field_selector_type_alt field,
+ int sym_diff,
+ asymbol *sym)
{
int *final_type, **final_types;
- final_types = (int **) bfd_alloc (abfd, (bfd_size_type) sizeof (int *) * 6);
- final_type = (int *) bfd_alloc (abfd, (bfd_size_type) sizeof (int));
+ final_types = bfd_alloc (abfd, (bfd_size_type) sizeof (int *) * 6);
+ final_type = bfd_alloc (abfd, (bfd_size_type) sizeof (int));
if (!final_types || !final_type)
return NULL;
case e_tsel:
case e_ltsel:
case e_rtsel:
- final_types[0] = (int *) bfd_alloc (abfd, (bfd_size_type) sizeof (int));
+ final_types[0] = bfd_alloc (abfd, (bfd_size_type) sizeof (int));
if (!final_types[0])
return NULL;
if (field == e_tsel)
case e_lssel:
case e_rssel:
- final_types[0] = (int *) bfd_alloc (abfd, (bfd_size_type) sizeof (int));
+ final_types[0] = bfd_alloc (abfd, (bfd_size_type) sizeof (int));
if (!final_types[0])
return NULL;
*final_types[0] = R_S_MODE;
case e_lsel:
case e_rsel:
- final_types[0] = (int *) bfd_alloc (abfd, (bfd_size_type) sizeof (int));
+ final_types[0] = bfd_alloc (abfd, (bfd_size_type) sizeof (int));
if (!final_types[0])
return NULL;
*final_types[0] = R_N_MODE;
case e_ldsel:
case e_rdsel:
- final_types[0] = (int *) bfd_alloc (abfd, (bfd_size_type) sizeof (int));
+ final_types[0] = bfd_alloc (abfd, (bfd_size_type) sizeof (int));
if (!final_types[0])
return NULL;
*final_types[0] = R_D_MODE;
case e_lrsel:
case e_rrsel:
- final_types[0] = (int *) bfd_alloc (abfd, (bfd_size_type) sizeof (int));
+ final_types[0] = bfd_alloc (abfd, (bfd_size_type) sizeof (int));
if (!final_types[0])
return NULL;
*final_types[0] = R_R_MODE;
break;
case e_nsel:
- final_types[0] = (int *) bfd_alloc (abfd, (bfd_size_type) sizeof (int));
+ final_types[0] = bfd_alloc (abfd, (bfd_size_type) sizeof (int));
if (!final_types[0])
return NULL;
*final_types[0] = R_N1SEL;
case e_nlsel:
case e_nlrsel:
- final_types[0] = (int *) bfd_alloc (abfd, (bfd_size_type) sizeof (int));
+ final_types[0] = bfd_alloc (abfd, (bfd_size_type) sizeof (int));
if (!final_types[0])
return NULL;
*final_types[0] = R_N0SEL;
- final_types[1] = (int *) bfd_alloc (abfd, (bfd_size_type) sizeof (int));
+ final_types[1] = bfd_alloc (abfd, (bfd_size_type) sizeof (int));
if (!final_types[1])
return NULL;
if (field == e_nlsel)
if (sym_diff)
{
bfd_size_type amt = sizeof (int);
- final_types[0] = (int *) bfd_alloc (abfd, amt);
- final_types[1] = (int *) bfd_alloc (abfd, amt);
- final_types[2] = (int *) bfd_alloc (abfd, amt);
- final_types[3] = (int *) bfd_alloc (abfd, amt);
+
+ final_types[0] = bfd_alloc (abfd, amt);
+ final_types[1] = bfd_alloc (abfd, amt);
+ final_types[2] = bfd_alloc (abfd, amt);
+ final_types[3] = bfd_alloc (abfd, amt);
if (!final_types[0] || !final_types[1] || !final_types[2])
return NULL;
if (field == e_fsel)
if (sym_diff)
{
bfd_size_type amt = sizeof (int);
- final_types[0] = (int *) bfd_alloc (abfd, amt);
- final_types[1] = (int *) bfd_alloc (abfd, amt);
- final_types[2] = (int *) bfd_alloc (abfd, amt);
- final_types[3] = (int *) bfd_alloc (abfd, amt);
+
+ final_types[0] = bfd_alloc (abfd, amt);
+ final_types[1] = bfd_alloc (abfd, amt);
+ final_types[2] = bfd_alloc (abfd, amt);
+ final_types[3] = bfd_alloc (abfd, amt);
if (!final_types[0] || !final_types[1] || !final_types[2])
return NULL;
if (field == e_fsel)
mode selector, then the pcrel relocation. Redundant selectors
will be eliminated as the relocs are sized and emitted. */
bfd_size_type amt = sizeof (int);
- final_types[0] = (int *) bfd_alloc (abfd, amt);
+
+ final_types[0] = bfd_alloc (abfd, amt);
if (!final_types[0])
return NULL;
if (format == 17)
howto table. */
static reloc_howto_type *
-som_bfd_reloc_type_lookup (abfd, code)
- bfd *abfd ATTRIBUTE_UNUSED;
- bfd_reloc_code_real_type code;
+som_bfd_reloc_type_lookup (bfd *abfd ATTRIBUTE_UNUSED,
+ bfd_reloc_code_real_type code)
{
if ((int) code < (int) R_NO_RELOCATION + 255)
{
return &som_hppa_howto_table[(int) code];
}
- return (reloc_howto_type *) 0;
+ return NULL;
}
/* Perform some initialization for an object. Save results of this
initialization in the BFD. */
static const bfd_target *
-som_object_setup (abfd, file_hdrp, aux_hdrp, current_offset)
- bfd *abfd;
- struct header *file_hdrp;
- struct som_exec_auxhdr *aux_hdrp;
- unsigned long current_offset;
+som_object_setup (bfd *abfd,
+ struct header *file_hdrp,
+ struct som_exec_auxhdr *aux_hdrp,
+ unsigned long current_offset)
{
asection *section;
/* som_mkobject will set bfd_error if som_mkobject fails. */
if (! som_mkobject (abfd))
- return 0;
+ return NULL;
/* Set BFD flags based on what information is available in the SOM. */
abfd->flags = BFD_NO_FLAGS;
obj_som_exec_hdr (abfd) = aux_hdrp;
/* Allocate space to hold the saved exec header information. */
- obj_som_exec_data (abfd) = (struct som_exec_data *)
- bfd_zalloc (abfd, (bfd_size_type) sizeof (struct som_exec_data));
+ obj_som_exec_data (abfd) = bfd_zalloc (abfd, (bfd_size_type) sizeof (struct som_exec_data));
if (obj_som_exec_data (abfd) == NULL)
return NULL;
/* Initialize the saved symbol table and string table to NULL.
Save important offsets and sizes from the SOM header into
the BFD. */
- obj_som_stringtab (abfd) = (char *) NULL;
- obj_som_symtab (abfd) = (som_symbol_type *) NULL;
+ obj_som_stringtab (abfd) = NULL;
+ obj_som_symtab (abfd) = NULL;
obj_som_sorted_syms (abfd) = NULL;
obj_som_stringtab_size (abfd) = file_hdrp->symbol_strings_size;
obj_som_sym_filepos (abfd) = file_hdrp->symbol_location + current_offset;
associated subspaces. */
static bfd_boolean
-setup_sections (abfd, file_hdr, current_offset)
- bfd *abfd;
- struct header *file_hdr;
- unsigned long current_offset;
+setup_sections (bfd *abfd,
+ struct header *file_hdr,
+ unsigned long current_offset)
{
char *space_strings;
unsigned int space_index, i;
bfd_size_type amt;
/* First, read in space names. */
-
amt = file_hdr->space_strings_size;
space_strings = bfd_malloc (amt);
if (!space_strings && amt != 0)
a target index to each subspace. */
amt = total_subspaces;
amt *= sizeof (asection *);
- subspace_sections = (asection **) bfd_malloc (amt);
+ subspace_sections = bfd_malloc (amt);
if (subspace_sections == NULL)
goto error_return;
/* Read in a SOM object and make it into a BFD. */
static const bfd_target *
-som_object_p (abfd)
- bfd *abfd;
+som_object_p (bfd *abfd)
{
struct header file_hdr;
struct som_exec_auxhdr *aux_hdr_ptr = NULL;
#define ENTRY_SIZE sizeof (struct som_entry)
amt = FILE_HDR_SIZE;
- if (bfd_bread ((PTR) &file_hdr, amt, abfd) != amt)
+ if (bfd_bread ((void *) &file_hdr, amt, abfd) != amt)
{
if (bfd_get_error () != bfd_error_system_call)
bfd_set_error (bfd_error_wrong_format);
- return 0;
+ return NULL;
}
if (!_PA_RISC_ID (file_hdr.system_id))
{
bfd_set_error (bfd_error_wrong_format);
- return 0;
+ return NULL;
}
switch (file_hdr.a_magic)
{
if (bfd_get_error () != bfd_error_system_call)
bfd_set_error (bfd_error_wrong_format);
- return 0;
+ return NULL;
}
amt = SLSTHDR;
- if (bfd_bread ((PTR) &lst_header, amt, abfd) != amt)
+ if (bfd_bread ((void *) &lst_header, amt, abfd) != amt)
{
if (bfd_get_error () != bfd_error_system_call)
bfd_set_error (bfd_error_wrong_format);
- return 0;
+ return NULL;
}
/* Position to and read the first directory entry. */
{
if (bfd_get_error () != bfd_error_system_call)
bfd_set_error (bfd_error_wrong_format);
- return 0;
+ return NULL;
}
amt = ENTRY_SIZE;
- if (bfd_bread ((PTR) &som_entry, amt, abfd) != amt)
+ if (bfd_bread ((void *) &som_entry, amt, abfd) != amt)
{
if (bfd_get_error () != bfd_error_system_call)
bfd_set_error (bfd_error_wrong_format);
- return 0;
+ return NULL;
}
/* Now position to the first SOM. */
{
if (bfd_get_error () != bfd_error_system_call)
bfd_set_error (bfd_error_wrong_format);
- return 0;
+ return NULL;
}
current_offset = som_entry.location;
/* And finally, re-read the som header. */
amt = FILE_HDR_SIZE;
- if (bfd_bread ((PTR) &file_hdr, amt, abfd) != amt)
+ if (bfd_bread ((void *) &file_hdr, amt, abfd) != amt)
{
if (bfd_get_error () != bfd_error_system_call)
bfd_set_error (bfd_error_wrong_format);
- return 0;
+ return NULL;
}
break;
default:
bfd_set_error (bfd_error_wrong_format);
- return 0;
+ return NULL;
}
if (file_hdr.version_id != VERSION_ID
&& file_hdr.version_id != NEW_VERSION_ID)
{
bfd_set_error (bfd_error_wrong_format);
- return 0;
+ return NULL;
}
/* If the aux_header_size field in the file header is zero, then this
if (aux_hdr_ptr == NULL)
return NULL;
amt = AUX_HDR_SIZE;
- if (bfd_bread ((PTR) aux_hdr_ptr, amt, abfd) != amt)
+ if (bfd_bread ((void *) aux_hdr_ptr, amt, abfd) != amt)
{
if (bfd_get_error () != bfd_error_system_call)
bfd_set_error (bfd_error_wrong_format);
- return 0;
+ return NULL;
}
}
{
/* setup_sections does not bubble up a bfd error code. */
bfd_set_error (bfd_error_bad_value);
- return 0;
+ return NULL;
}
/* This appears to be a valid SOM object. Do some initialization. */
/* Create a SOM object. */
static bfd_boolean
-som_mkobject (abfd)
- bfd *abfd;
+som_mkobject (bfd *abfd)
{
/* Allocate memory to hold backend information. */
- abfd->tdata.som_data = (struct som_data_struct *)
- bfd_zalloc (abfd, (bfd_size_type) sizeof (struct som_data_struct));
+ abfd->tdata.som_data = bfd_zalloc (abfd, (bfd_size_type) sizeof (struct som_data_struct));
if (abfd->tdata.som_data == NULL)
return FALSE;
return TRUE;
is only meant to handle relocatable objects. */
static bfd_boolean
-som_prep_headers (abfd)
- bfd *abfd;
+som_prep_headers (bfd *abfd)
{
struct header *file_hdr;
asection *section;
bfd_size_type amt = sizeof (struct header);
/* Make and attach a file header to the BFD. */
- file_hdr = (struct header *) bfd_zalloc (abfd, amt);
+ file_hdr = bfd_zalloc (abfd, amt);
if (file_hdr == NULL)
return FALSE;
obj_som_file_hdr (abfd) = file_hdr;
{
/* Make and attach an exec header to the BFD. */
amt = sizeof (struct som_exec_auxhdr);
- obj_som_exec_hdr (abfd) =
- (struct som_exec_auxhdr *) bfd_zalloc (abfd, amt);
+ obj_som_exec_hdr (abfd) = bfd_zalloc (abfd, amt);
if (obj_som_exec_hdr (abfd) == NULL)
return FALSE;
/* Now iterate over the sections translating information from
BFD sections to SOM spaces/subspaces. */
-
for (section = abfd->sections; section != NULL; section = section->next)
{
/* Ignore anything which has not been marked as a space or
{
/* Allocate space for the space dictionary. */
amt = sizeof (struct space_dictionary_record);
- som_section_data (section)->space_dict =
- (struct space_dictionary_record *) bfd_zalloc (abfd, amt);
+ som_section_data (section)->space_dict = bfd_zalloc (abfd, amt);
if (som_section_data (section)->space_dict == NULL)
return FALSE;
/* Set space attributes. Note most attributes of SOM spaces
{
/* Allocate space for the subspace dictionary. */
amt = sizeof (struct som_subspace_dictionary_record);
- som_section_data (section)->subspace_dict =
- (struct som_subspace_dictionary_record *) bfd_zalloc (abfd, amt);
+ som_section_data (section)->subspace_dict = bfd_zalloc (abfd, amt);
if (som_section_data (section)->subspace_dict == NULL)
return FALSE;
/* Return TRUE if the given section is a SOM space, FALSE otherwise. */
static bfd_boolean
-som_is_space (section)
- asection *section;
+som_is_space (asection *section)
{
/* If no copy data is available, then it's neither a space nor a
subspace. */
/* Return TRUE if the given section is a SOM subspace, FALSE otherwise. */
static bfd_boolean
-som_is_subspace (section)
- asection *section;
+som_is_subspace (asection *section)
{
/* If no copy data is available, then it's neither a space nor a
subspace. */
is a subspace. */
static bfd_boolean
-som_is_container (space, subspace)
- asection *space, *subspace;
+som_is_container (asection *space, asection *subspace)
{
- return (som_section_data (subspace)->copy_data->container == space
- || (som_section_data (subspace)->copy_data->container->output_section
- == space));
+ return (som_section_data (subspace)->copy_data->container == space)
+ || (som_section_data (subspace)->copy_data->container->output_section
+ == space);
}
/* Count and return the number of spaces attached to the given BFD. */
static unsigned long
-som_count_spaces (abfd)
- bfd *abfd;
+som_count_spaces (bfd *abfd)
{
int count = 0;
asection *section;
/* Count the number of subspaces attached to the given BFD. */
static unsigned long
-som_count_subspaces (abfd)
- bfd *abfd;
+som_count_subspaces (bfd *abfd)
{
int count = 0;
asection *section;
count. Doing so compacts the relocation stream. */
static int
-compare_syms (arg1, arg2)
- const PTR arg1;
- const PTR arg2;
-
+compare_syms (const void * arg1, const void * arg2)
{
asymbol **sym1 = (asymbol **) arg1;
asymbol **sym2 = (asymbol **) arg2;
and subspace. */
static int
-compare_subspaces (arg1, arg2)
- const PTR arg1;
- const PTR arg2;
-
+compare_subspaces (const void * arg1, const void * arg2)
{
asection **subspace1 = (asection **) arg1;
asection **subspace2 = (asection **) arg2;
/* Perform various work in preparation for emitting the fixup stream. */
static void
-som_prep_for_fixups (abfd, syms, num_syms)
- bfd *abfd;
- asymbol **syms;
- unsigned long num_syms;
+som_prep_for_fixups (bfd *abfd, asymbol **syms, unsigned long num_syms)
{
unsigned long i;
asection *section;
output symbol table. */
amt = num_syms;
amt *= sizeof (asymbol *);
- sorted_syms = (asymbol **) bfd_zalloc (abfd, amt);
+ sorted_syms = bfd_zalloc (abfd, amt);
memcpy (sorted_syms, syms, num_syms * sizeof (asymbol *));
qsort (sorted_syms, num_syms, sizeof (asymbol *), compare_syms);
obj_som_sorted_syms (abfd) = sorted_syms;
}
static bfd_boolean
-som_write_fixups (abfd, current_offset, total_reloc_sizep)
- bfd *abfd;
- unsigned long current_offset;
- unsigned int *total_reloc_sizep;
+som_write_fixups (bfd *abfd,
+ unsigned long current_offset,
+ unsigned int *total_reloc_sizep)
{
unsigned int i, j;
/* Chunk of memory that we can use as buffer space, then throw
if (p - tmp_space + 100 > SOM_TMP_BUFSIZE)
{
amt = p - tmp_space;
- if (bfd_bwrite ((PTR) tmp_space, amt, abfd) != amt)
+ if (bfd_bwrite ((void *) tmp_space, amt, abfd) != amt)
return FALSE;
p = tmp_space;
/* Scribble out the relocations. */
amt = p - tmp_space;
- if (bfd_bwrite ((PTR) tmp_space, amt, abfd) != amt)
+ if (bfd_bwrite ((void *) tmp_space, amt, abfd) != amt)
return FALSE;
p = tmp_space;
/* Write out the space/subspace string table. */
static bfd_boolean
-som_write_space_strings (abfd, current_offset, string_sizep)
- bfd *abfd;
- unsigned long current_offset;
- unsigned int *string_sizep;
+som_write_space_strings (bfd *abfd,
+ unsigned long current_offset,
+ unsigned int *string_sizep)
{
/* Chunk of memory that we can use as buffer space, then throw
away. */
{
/* Flush buffer before refilling or reallocating. */
amt = p - tmp_space;
- if (bfd_bwrite ((PTR) &tmp_space[0], amt, abfd) != amt)
+ if (bfd_bwrite ((void *) &tmp_space[0], amt, abfd) != amt)
return FALSE;
/* Reallocate if now empty buffer still too small. */
/* Done with the space/subspace strings. Write out any information
contained in a partial block. */
amt = p - tmp_space;
- if (bfd_bwrite ((PTR) &tmp_space[0], amt, abfd) != amt)
+ if (bfd_bwrite ((void *) &tmp_space[0], amt, abfd) != amt)
return FALSE;
*string_sizep = strings_size;
return TRUE;
/* Write out the symbol string table. */
static bfd_boolean
-som_write_symbol_strings (abfd, current_offset, syms, num_syms, string_sizep,
- compilation_unit)
- bfd *abfd;
- unsigned long current_offset;
- asymbol **syms;
- unsigned int num_syms;
- unsigned int *string_sizep;
- COMPUNIT *compilation_unit;
+som_write_symbol_strings (bfd *abfd,
+ unsigned long current_offset,
+ asymbol **syms,
+ unsigned int num_syms,
+ unsigned int *string_sizep,
+ COMPUNIT *compilation_unit)
{
unsigned int i;
{
/* Flush buffer before refilling or reallocating. */
amt = p - tmp_space;
- if (bfd_bwrite ((PTR) &tmp_space[0], amt, abfd) != amt)
+ if (bfd_bwrite ((void *) &tmp_space[0], amt, abfd) != amt)
return FALSE;
/* Reallocate if now empty buffer still too small. */
{
/* Flush buffer before refilling or reallocating. */
amt = p - tmp_space;
- if (bfd_bwrite ((PTR) &tmp_space[0], amt, abfd) != amt)
+ if (bfd_bwrite ((void *) &tmp_space[0], amt, abfd) != amt)
return FALSE;
/* Reallocate if now empty buffer still too small. */
/* Scribble out any partial block. */
amt = p - tmp_space;
- if (bfd_bwrite ((PTR) &tmp_space[0], amt, abfd) != amt)
+ if (bfd_bwrite ((void *) &tmp_space[0], amt, abfd) != amt)
return FALSE;
*string_sizep = strings_size;
writing parts of the object file. */
static bfd_boolean
-som_begin_writing (abfd)
- bfd *abfd;
+som_begin_writing (bfd *abfd)
{
unsigned long current_offset = 0;
int strings_size = 0;
len = sizeof (struct aux_id) + sizeof (unsigned int);
obj_som_file_hdr (abfd)->aux_header_size += len;
current_offset += len;
- if (bfd_bwrite ((PTR) obj_som_version_hdr (abfd), len, abfd) != len)
+ if (bfd_bwrite ((void *) obj_som_version_hdr (abfd), len, abfd) != len)
return FALSE;
/* Write the version string. */
len = obj_som_version_hdr (abfd)->header_id.length - sizeof (int);
obj_som_file_hdr (abfd)->aux_header_size += len;
current_offset += len;
- if (bfd_bwrite ((PTR) obj_som_version_hdr (abfd)->user_string, len, abfd)
+ if (bfd_bwrite ((void *) obj_som_version_hdr (abfd)->user_string, len, abfd)
!= len)
return FALSE;
}
len = sizeof (struct aux_id) + sizeof (unsigned int);
obj_som_file_hdr (abfd)->aux_header_size += len;
current_offset += len;
- if (bfd_bwrite ((PTR) obj_som_copyright_hdr (abfd), len, abfd) != len)
+ if (bfd_bwrite ((void *) obj_som_copyright_hdr (abfd), len, abfd) != len)
return FALSE;
/* Write the copyright string. */
len = obj_som_copyright_hdr (abfd)->header_id.length - sizeof (int);
obj_som_file_hdr (abfd)->aux_header_size += len;
current_offset += len;
- if (bfd_bwrite ((PTR) obj_som_copyright_hdr (abfd)->copyright, len, abfd)
+ if (bfd_bwrite ((void *) obj_som_copyright_hdr (abfd)->copyright, len, abfd)
!= len)
return FALSE;
}
current_offset = SOM_ALIGN (current_offset, PA_PAGESIZE);
if (bfd_seek (abfd, (file_ptr) current_offset - 1, SEEK_SET) != 0)
return FALSE;
- if (bfd_bwrite ((PTR) "", (bfd_size_type) 1, abfd) != 1)
+ if (bfd_bwrite ((void *) "", (bfd_size_type) 1, abfd) != 1)
return FALSE;
obj_som_file_hdr (abfd)->unloadable_sp_size
/* Finally, scribble out the various headers to the disk. */
static bfd_boolean
-som_finish_writing (abfd)
- bfd *abfd;
+som_finish_writing (bfd *abfd)
{
int num_spaces = som_count_spaces (abfd);
asymbol **syms = bfd_get_outsymbols (abfd);
/* Dump the current subspace header. */
amt = sizeof (struct som_subspace_dictionary_record);
- if (bfd_bwrite ((PTR) som_section_data (subsection)->subspace_dict,
+ if (bfd_bwrite ((void *) som_section_data (subsection)->subspace_dict,
amt, abfd) != amt)
return FALSE;
}
/* Dump this subspace header. */
amt = sizeof (struct som_subspace_dictionary_record);
- if (bfd_bwrite ((PTR) som_section_data (subsection)->subspace_dict,
+ if (bfd_bwrite ((void *) som_section_data (subsection)->subspace_dict,
amt, abfd) != amt)
return FALSE;
}
/* Dump its header. */
amt = sizeof (struct space_dictionary_record);
- if (bfd_bwrite ((PTR) som_section_data (section)->space_dict,
+ if (bfd_bwrite ((void *) som_section_data (section)->space_dict,
amt, abfd) != amt)
return FALSE;
return FALSE;
amt = COMPUNITSZ;
- if (bfd_bwrite ((PTR) obj_som_compilation_unit (abfd), amt, abfd) != amt)
+ if (bfd_bwrite ((void *) obj_som_compilation_unit (abfd), amt, abfd) != amt)
return FALSE;
}
if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) != 0)
return FALSE;
amt = sizeof (struct header);
- if (bfd_bwrite ((PTR) obj_som_file_hdr (abfd), amt, abfd) != amt)
+ if (bfd_bwrite ((void *) obj_som_file_hdr (abfd), amt, abfd) != amt)
return FALSE;
/* Now write the exec header. */
return FALSE;
amt = AUX_HDR_SIZE;
- if (bfd_bwrite ((PTR) exec_header, amt, abfd) != amt)
+ if (bfd_bwrite ((void *) exec_header, amt, abfd) != amt)
return FALSE;
}
return TRUE;
/* Compute and return the checksum for a SOM file header. */
static unsigned long
-som_compute_checksum (abfd)
- bfd *abfd;
+som_compute_checksum (bfd *abfd)
{
unsigned long checksum, count, i;
unsigned long *buffer = (unsigned long *) obj_som_file_hdr (abfd);
}
static void
-som_bfd_derive_misc_symbol_info (abfd, sym, info)
- bfd *abfd ATTRIBUTE_UNUSED;
- asymbol *sym;
- struct som_misc_symbol_info *info;
+som_bfd_derive_misc_symbol_info (bfd *abfd ATTRIBUTE_UNUSED,
+ asymbol *sym,
+ struct som_misc_symbol_info *info)
{
/* Initialize. */
memset (info, 0, sizeof (struct som_misc_symbol_info));
this BFD. */
static bfd_boolean
-som_build_and_write_symbol_table (abfd)
- bfd *abfd;
+som_build_and_write_symbol_table (bfd *abfd)
{
unsigned int num_syms = bfd_get_symcount (abfd);
file_ptr symtab_location = obj_som_file_hdr (abfd)->symbol_location;
to hold the symbol table as we build it. */
symtab_size = num_syms;
symtab_size *= sizeof (struct symbol_dictionary_record);
- som_symtab = (struct symbol_dictionary_record *) bfd_zmalloc (symtab_size);
+ som_symtab = bfd_zmalloc (symtab_size);
if (som_symtab == NULL && symtab_size != 0)
goto error_return;
if (bfd_seek (abfd, symtab_location, SEEK_SET) != 0)
return FALSE;
- if (bfd_bwrite ((PTR) som_symtab, symtab_size, abfd) != symtab_size)
+ if (bfd_bwrite ((void *) som_symtab, symtab_size, abfd) != symtab_size)
goto error_return;
if (som_symtab != NULL)
/* Write an object in SOM format. */
static bfd_boolean
-som_write_object_contents (abfd)
- bfd *abfd;
+som_write_object_contents (bfd *abfd)
{
if (! abfd->output_has_begun)
{
som_begin_writing (abfd);
}
- return (som_finish_writing (abfd));
+ return som_finish_writing (abfd);
}
\f
/* Read and save the string table associated with the given BFD. */
static bfd_boolean
-som_slurp_string_table (abfd)
- bfd *abfd;
+som_slurp_string_table (bfd *abfd)
{
char *stringtab;
bfd_size_type amt;
table for this object. */
static long
-som_get_symtab_upper_bound (abfd)
- bfd *abfd;
+som_get_symtab_upper_bound (bfd *abfd)
{
if (!som_slurp_symbol_table (abfd))
return -1;
- return (bfd_get_symcount (abfd) + 1) * (sizeof (asymbol *));
+ return (bfd_get_symcount (abfd) + 1) * sizeof (asymbol *);
}
/* Convert from a SOM subspace index to a BFD section. */
static asection *
-bfd_section_from_som_symbol (abfd, symbol)
- bfd *abfd;
- struct symbol_dictionary_record *symbol;
+bfd_section_from_som_symbol (bfd *abfd, struct symbol_dictionary_record *symbol)
{
asection *section;
&& symbol->symbol_type != ST_MILLICODE))
{
int index = symbol->symbol_info;
+
for (section = abfd->sections; section != NULL; section = section->next)
if (section->target_index == index && som_is_subspace (section))
return section;
-
- /* Could be a symbol from an external library (such as an OMOS
- shared library). Don't abort. */
- return bfd_abs_section_ptr;
-
}
else
{
/* For executables we will have to use the symbol's address and
find out what section would contain that address. Yuk. */
for (section = abfd->sections; section; section = section->next)
- {
- if (value >= section->vma
- && value <= section->vma + section->size
- && som_is_subspace (section))
- return section;
- }
-
- /* Could be a symbol from an external library (such as an OMOS
- shared library). Don't abort. */
- return bfd_abs_section_ptr;
-
+ if (value >= section->vma
+ && value <= section->vma + section->size
+ && som_is_subspace (section))
+ return section;
}
+
+ /* Could be a symbol from an external library (such as an OMOS
+ shared library). Don't abort. */
+ return bfd_abs_section_ptr;
}
/* Read and save the symbol table associated with the given BFD. */
static unsigned int
-som_slurp_symbol_table (abfd)
- bfd *abfd;
+som_slurp_symbol_table (bfd *abfd)
{
int symbol_count = bfd_get_symcount (abfd);
int symsize = sizeof (struct symbol_dictionary_record);
amt = symbol_count;
amt *= sizeof (som_symbol_type);
- symbase = (som_symbol_type *) bfd_zmalloc (amt);
+ symbase = bfd_zmalloc (amt);
if (symbase == NULL)
goto error_return;
endbufp = buf + symbol_count;
for (bufp = buf, sym = symbase; bufp < endbufp; ++bufp)
{
-
/* I don't think we care about these. */
if (bufp->symbol_type == ST_SYM_EXT
|| bufp->symbol_type == ST_ARG_EXT)
in the symbol table. */
static long
-som_canonicalize_symtab (abfd, location)
- bfd *abfd;
- asymbol **location;
+som_canonicalize_symtab (bfd *abfd, asymbol **location)
{
int i;
som_symbol_type *symbase;
/* Make a SOM symbol. There is nothing special to do here. */
static asymbol *
-som_make_empty_symbol (abfd)
- bfd *abfd;
+som_make_empty_symbol (bfd *abfd)
{
bfd_size_type amt = sizeof (som_symbol_type);
- som_symbol_type *new = (som_symbol_type *) bfd_zalloc (abfd, amt);
+ som_symbol_type *new = bfd_zalloc (abfd, amt);
+
if (new == NULL)
- return 0;
+ return NULL;
new->symbol.the_bfd = abfd;
return &new->symbol;
/* Print symbol information. */
static void
-som_print_symbol (abfd, afile, symbol, how)
- bfd *abfd;
- PTR afile;
- asymbol *symbol;
- bfd_print_symbol_type how;
+som_print_symbol (bfd *abfd,
+ void * afile,
+ asymbol *symbol,
+ bfd_print_symbol_type how)
{
FILE *file = (FILE *) afile;
+
switch (how)
{
case bfd_print_symbol_name:
case bfd_print_symbol_all:
{
const char *section_name;
+
section_name = symbol->section ? symbol->section->name : "(*none*)";
- bfd_print_symbol_vandf (abfd, (PTR) file, symbol);
+ bfd_print_symbol_vandf (abfd, (void *) file, symbol);
fprintf (file, " %s\t%s", section_name, symbol->name);
break;
}
}
static bfd_boolean
-som_bfd_is_local_label_name (abfd, name)
- bfd *abfd ATTRIBUTE_UNUSED;
- const char *name;
+som_bfd_is_local_label_name (bfd *abfd ATTRIBUTE_UNUSED,
+ const char *name)
{
- return (name[0] == 'L' && name[1] == '$');
+ return name[0] == 'L' && name[1] == '$';
}
/* Count or process variable-length SOM fixup records.
This needs at least two or three more passes to get it cleaned up. */
static unsigned int
-som_set_reloc_info (fixup, end, internal_relocs, section, symbols, just_count)
- unsigned char *fixup;
- unsigned int end;
- arelent *internal_relocs;
- asection *section;
- asymbol **symbols;
- bfd_boolean just_count;
+som_set_reloc_info (unsigned char *fixup,
+ unsigned int end,
+ arelent *internal_relocs,
+ asection *section,
+ asymbol **symbols,
+ bfd_boolean just_count)
{
unsigned int op, varname, deallocate_contents = 0;
unsigned char *end_fixups = &fixup[end];
while (fixup < end_fixups)
{
-
/* Save pointer to the start of this fixup. We'll use
it later to determine if it is necessary to put this fixup
on the queue. */
of actual relocations. */
static bfd_boolean
-som_slurp_reloc_table (abfd, section, symbols, just_count)
- bfd *abfd;
- asection *section;
- asymbol **symbols;
- bfd_boolean just_count;
+som_slurp_reloc_table (bfd *abfd,
+ asection *section,
+ asymbol **symbols,
+ bfd_boolean just_count)
{
char *external_relocs;
unsigned int fixup_stream_size;
if (section->reloc_count == (unsigned) -1)
{
amt = fixup_stream_size;
- external_relocs = (char *) bfd_malloc (amt);
- if (external_relocs == (char *) NULL)
+ external_relocs = bfd_malloc (amt);
+ if (external_relocs == NULL)
return FALSE;
/* Read in the external forms. */
if (bfd_seek (abfd,
num_relocs = section->reloc_count;
external_relocs = som_section_data (section)->reloc_stream;
/* Return saved information about the relocations if it is available. */
- if (section->relocation != (arelent *) NULL)
+ if (section->relocation != NULL)
return TRUE;
amt = num_relocs;
amt *= sizeof (arelent);
- internal_relocs = (arelent *) bfd_zalloc (abfd, (amt));
- if (internal_relocs == (arelent *) NULL)
+ internal_relocs = bfd_zalloc (abfd, (amt));
+ if (internal_relocs == NULL)
return FALSE;
/* Process and internalize the relocations. */
information associated with the given section. */
static long
-som_get_reloc_upper_bound (abfd, asect)
- bfd *abfd;
- sec_ptr asect;
+som_get_reloc_upper_bound (bfd *abfd, sec_ptr asect)
{
/* If section has relocations, then read in the relocation stream
and parse it to determine how many relocations exist. */
form. Return the number of relocations. */
static long
-som_canonicalize_reloc (abfd, section, relptr, symbols)
- bfd *abfd;
- sec_ptr section;
- arelent **relptr;
- asymbol **symbols;
+som_canonicalize_reloc (bfd *abfd,
+ sec_ptr section,
+ arelent **relptr,
+ asymbol **symbols)
{
arelent *tblptr;
int count;
while (count--)
*relptr++ = tblptr++;
- *relptr = (arelent *) NULL;
+ *relptr = NULL;
return section->reloc_count;
}
/* A hook to set up object file dependent section information. */
static bfd_boolean
-som_new_section_hook (abfd, newsect)
- bfd *abfd;
- asection *newsect;
+som_new_section_hook (bfd *abfd, asection *newsect)
{
bfd_size_type amt = sizeof (struct som_section_data_struct);
- newsect->used_by_bfd = (PTR) bfd_zalloc (abfd, amt);
+
+ newsect->used_by_bfd = bfd_zalloc (abfd, amt);
if (!newsect->used_by_bfd)
return FALSE;
newsect->alignment_power = 3;
to the output symbol. */
static bfd_boolean
-som_bfd_copy_private_symbol_data (ibfd, isymbol, obfd, osymbol)
- bfd *ibfd;
- asymbol *isymbol;
- bfd *obfd;
- asymbol *osymbol;
+som_bfd_copy_private_symbol_data (bfd *ibfd,
+ asymbol *isymbol,
+ bfd *obfd,
+ asymbol *osymbol)
{
struct som_symbol *input_symbol = (struct som_symbol *) isymbol;
struct som_symbol *output_symbol = (struct som_symbol *) osymbol;
to the output section. */
static bfd_boolean
-som_bfd_copy_private_section_data (ibfd, isection, obfd, osection)
- bfd *ibfd;
- asection *isection;
- bfd *obfd;
- asection *osection;
+som_bfd_copy_private_section_data (bfd *ibfd,
+ asection *isection,
+ bfd *obfd,
+ asection *osection)
{
bfd_size_type amt;
return TRUE;
amt = sizeof (struct som_copyable_section_data_struct);
- som_section_data (osection)->copy_data =
- (struct som_copyable_section_data_struct *) bfd_zalloc (obfd, amt);
+ som_section_data (osection)->copy_data = bfd_zalloc (obfd, amt);
if (som_section_data (osection)->copy_data == NULL)
return FALSE;
to the output bfd. */
static bfd_boolean
-som_bfd_copy_private_bfd_data (ibfd, obfd)
- bfd *ibfd, *obfd;
+som_bfd_copy_private_bfd_data (bfd *ibfd, bfd *obfd)
{
/* One day we may try to grok other private data. */
if (ibfd->xvec->flavour != bfd_target_som_flavour
return TRUE;
/* Allocate some memory to hold the data we need. */
- obj_som_exec_data (obfd) = (struct som_exec_data *)
- bfd_zalloc (obfd, (bfd_size_type) sizeof (struct som_exec_data));
+ obj_som_exec_data (obfd) = bfd_zalloc (obfd, (bfd_size_type) sizeof (struct som_exec_data));
if (obj_som_exec_data (obfd) == NULL)
return FALSE;
in the BFD data structures. */
bfd_boolean
-bfd_som_set_section_attributes (section, defined, private, sort_key, spnum)
- asection *section;
- int defined;
- int private;
- unsigned int sort_key;
- int spnum;
+bfd_som_set_section_attributes (asection *section,
+ int defined,
+ int private,
+ unsigned int sort_key,
+ int spnum)
{
/* Allocate memory to hold the magic information. */
if (som_section_data (section)->copy_data == NULL)
{
bfd_size_type amt = sizeof (struct som_copyable_section_data_struct);
- som_section_data (section)->copy_data =
- (struct som_copyable_section_data_struct *) bfd_zalloc (section->owner,
- amt);
+
+ som_section_data (section)->copy_data = bfd_zalloc (section->owner, amt);
if (som_section_data (section)->copy_data == NULL)
return FALSE;
}
in the BFD data structures. */
bfd_boolean
-bfd_som_set_subsection_attributes (section, container, access,
- sort_key, quadrant, comdat,
- common, dup_common)
- asection *section;
- asection *container;
- int access;
- unsigned int sort_key;
- int quadrant, comdat, common, dup_common;
+bfd_som_set_subsection_attributes (asection *section,
+ asection *container,
+ int access,
+ unsigned int sort_key,
+ int quadrant,
+ int comdat,
+ int common,
+ int dup_common)
{
/* Allocate memory to hold the magic information. */
if (som_section_data (section)->copy_data == NULL)
{
bfd_size_type amt = sizeof (struct som_copyable_section_data_struct);
- som_section_data (section)->copy_data =
- (struct som_copyable_section_data_struct *) bfd_zalloc (section->owner,
- amt);
+
+ som_section_data (section)->copy_data = bfd_zalloc (section->owner, amt);
if (som_section_data (section)->copy_data == NULL)
return FALSE;
}
the symbol type wrong your program will not link. */
void
-bfd_som_set_symbol_type (symbol, type)
- asymbol *symbol;
- unsigned int type;
+bfd_som_set_symbol_type (asymbol *symbol, unsigned int type)
{
som_symbol_data (symbol)->som_type = type;
}
written into the object file. */
bfd_boolean
-bfd_som_attach_aux_hdr (abfd, type, string)
- bfd *abfd;
- int type;
- char *string;
+bfd_som_attach_aux_hdr (bfd *abfd, int type, char *string)
{
bfd_size_type amt;
if (len % 4)
pad = (4 - (len % 4));
amt = sizeof (struct aux_id) + sizeof (unsigned int) + len + pad;
- obj_som_version_hdr (abfd) =
- (struct user_string_aux_hdr *) bfd_zalloc (abfd, amt);
+ obj_som_version_hdr (abfd) = bfd_zalloc (abfd, amt);
if (!obj_som_version_hdr (abfd))
return FALSE;
obj_som_version_hdr (abfd)->header_id.type = VERSION_AUX_ID;
if (len % 4)
pad = (4 - (len % 4));
amt = sizeof (struct aux_id) + sizeof (unsigned int) + len + pad;
- obj_som_copyright_hdr (abfd) =
- (struct copyright_aux_hdr *) bfd_zalloc (abfd, amt);
+ obj_som_copyright_hdr (abfd) = bfd_zalloc (abfd, amt);
if (!obj_som_copyright_hdr (abfd))
return FALSE;
obj_som_copyright_hdr (abfd)->header_id.type = COPYRIGHT_AUX_ID;
written into the object file. */
bfd_boolean
-bfd_som_attach_compilation_unit (abfd, name, language_name, product_id,
- version_id)
- bfd *abfd;
- const char *name;
- const char *language_name;
- const char *product_id;
- const char *version_id;
+bfd_som_attach_compilation_unit (bfd *abfd,
+ const char *name,
+ const char *language_name,
+ const char *product_id,
+ const char *version_id)
{
COMPUNIT *n = (COMPUNIT *) bfd_zalloc (abfd, (bfd_size_type) COMPUNITSZ);
+
if (n == NULL)
return FALSE;
}
static bfd_boolean
-som_get_section_contents (abfd, section, location, offset, count)
- bfd *abfd;
- sec_ptr section;
- PTR location;
- file_ptr offset;
- bfd_size_type count;
+som_get_section_contents (bfd *abfd,
+ sec_ptr section,
+ void * location,
+ file_ptr offset,
+ bfd_size_type count)
{
if (count == 0 || ((section->flags & SEC_HAS_CONTENTS) == 0))
return TRUE;
}
static bfd_boolean
-som_set_section_contents (abfd, section, location, offset, count)
- bfd *abfd;
- sec_ptr section;
- const PTR location;
- file_ptr offset;
- bfd_size_type count;
+som_set_section_contents (bfd *abfd,
+ sec_ptr section,
+ const void * location,
+ file_ptr offset,
+ bfd_size_type count)
{
if (! abfd->output_has_begun)
{
}
static bfd_boolean
-som_set_arch_mach (abfd, arch, machine)
- bfd *abfd;
- enum bfd_architecture arch;
- unsigned long machine;
+som_set_arch_mach (bfd *abfd,
+ enum bfd_architecture arch,
+ unsigned long machine)
{
/* Allow any architecture to be supported by the SOM backend. */
return bfd_default_set_arch_mach (abfd, arch, machine);
}
static bfd_boolean
-som_find_nearest_line (abfd, section, symbols, offset, filename_ptr,
- functionname_ptr, line_ptr)
- bfd *abfd ATTRIBUTE_UNUSED;
- asection *section ATTRIBUTE_UNUSED;
- asymbol **symbols ATTRIBUTE_UNUSED;
- bfd_vma offset ATTRIBUTE_UNUSED;
- const char **filename_ptr ATTRIBUTE_UNUSED;
- const char **functionname_ptr ATTRIBUTE_UNUSED;
- unsigned int *line_ptr ATTRIBUTE_UNUSED;
+som_find_nearest_line (bfd *abfd ATTRIBUTE_UNUSED,
+ asection *section ATTRIBUTE_UNUSED,
+ asymbol **symbols ATTRIBUTE_UNUSED,
+ bfd_vma offset ATTRIBUTE_UNUSED,
+ const char **filename_ptr ATTRIBUTE_UNUSED,
+ const char **functionname_ptr ATTRIBUTE_UNUSED,
+ unsigned int *line_ptr ATTRIBUTE_UNUSED)
{
return FALSE;
}
static int
-som_sizeof_headers (abfd, reloc)
- bfd *abfd ATTRIBUTE_UNUSED;
- bfd_boolean reloc ATTRIBUTE_UNUSED;
+som_sizeof_headers (bfd *abfd ATTRIBUTE_UNUSED,
+ bfd_boolean reloc ATTRIBUTE_UNUSED)
{
(*_bfd_error_handler) (_("som_sizeof_headers unimplemented"));
fflush (stderr);
SOM section S, or '?' for an unknown SOM section. */
static char
-som_section_type (s)
- const char *s;
+som_section_type (const char *s)
{
const struct section_to_type *t;
}
static int
-som_decode_symclass (symbol)
- asymbol *symbol;
+som_decode_symclass (asymbol *symbol)
{
char c;
/* Return information about SOM symbol SYMBOL in RET. */
static void
-som_get_symbol_info (ignore_abfd, symbol, ret)
- bfd *ignore_abfd ATTRIBUTE_UNUSED;
- asymbol *symbol;
- symbol_info *ret;
+som_get_symbol_info (bfd *ignore_abfd ATTRIBUTE_UNUSED,
+ asymbol *symbol,
+ symbol_info *ret)
{
ret->type = som_decode_symclass (symbol);
if (ret->type != 'U')
so that we can allocate space for all the carsyms at once. */
static bfd_boolean
-som_bfd_count_ar_symbols (abfd, lst_header, count)
- bfd *abfd;
- struct lst_header *lst_header;
- symindex *count;
+som_bfd_count_ar_symbols (bfd *abfd,
+ struct lst_header *lst_header,
+ symindex *count)
{
unsigned int i;
unsigned int *hash_table = NULL;
amt = lst_header->hash_size;
amt *= sizeof (unsigned int);
- hash_table = (unsigned int *) bfd_malloc (amt);
+ hash_table = bfd_malloc (amt);
if (hash_table == NULL && lst_header->hash_size != 0)
goto error_return;
/* Read in the hash table. The has table is an array of 32bit file offsets
which point to the hash chains. */
- if (bfd_bread ((PTR) hash_table, amt, abfd) != amt)
+ if (bfd_bread ((void *) hash_table, amt, abfd) != amt)
goto error_return;
/* Walk each chain counting the number of symbols found on that particular
/* Read in this symbol and update the counter. */
amt = sizeof (lst_symbol);
- if (bfd_bread ((PTR) &lst_symbol, amt, abfd) != amt)
+ if (bfd_bread ((void *) &lst_symbol, amt, abfd) != amt)
goto error_return;
(*count)++;
/* Read the symbol in and update the counter. */
amt = sizeof (lst_symbol);
- if (bfd_bread ((PTR) &lst_symbol, amt, abfd) != amt)
+ if (bfd_bread ((void *) &lst_symbol, amt, abfd) != amt)
goto error_return;
(*count)++;
by ABFD and LST_HEADER. */
static bfd_boolean
-som_bfd_fill_in_ar_symbols (abfd, lst_header, syms)
- bfd *abfd;
- struct lst_header *lst_header;
- carsym **syms;
+som_bfd_fill_in_ar_symbols (bfd *abfd,
+ struct lst_header *lst_header,
+ carsym **syms)
{
unsigned int i, len;
carsym *set = syms[0];
amt = lst_header->hash_size;
amt *= sizeof (unsigned int);
- hash_table = (unsigned int *) bfd_malloc (amt);
+ hash_table = bfd_malloc (amt);
if (hash_table == NULL && lst_header->hash_size != 0)
goto error_return;
/* Read in the hash table. The has table is an array of 32bit file offsets
which point to the hash chains. */
- if (bfd_bread ((PTR) hash_table, amt, abfd) != amt)
+ if (bfd_bread ((void *) hash_table, amt, abfd) != amt)
goto error_return;
/* Seek to and read in the SOM dictionary. We will need this to fill
amt = lst_header->module_count;
amt *= sizeof (struct som_entry);
- som_dict = (struct som_entry *) bfd_malloc (amt);
+ som_dict = bfd_malloc (amt);
if (som_dict == NULL && lst_header->module_count != 0)
goto error_return;
- if (bfd_bread ((PTR) som_dict, amt, abfd) != amt)
+ if (bfd_bread ((void *) som_dict, amt, abfd) != amt)
goto error_return;
/* Walk each chain filling in the carsyms as we go along. */
goto error_return;
amt = sizeof (lst_symbol);
- if (bfd_bread ((PTR) &lst_symbol, amt, abfd) != amt)
+ if (bfd_bread ((void *) &lst_symbol, amt, abfd) != amt)
goto error_return;
/* Get the name of the symbol, first get the length which is stored
goto error_return;
amt = sizeof (lst_symbol);
- if (bfd_bread ((PTR) &lst_symbol, amt, abfd) != amt)
+ if (bfd_bread ((void *) &lst_symbol, amt, abfd) != amt)
goto error_return;
/* Seek to the name length & string and read them in. */
/* Read in the LST from the archive. */
static bfd_boolean
-som_slurp_armap (abfd)
- bfd *abfd;
+som_slurp_armap (bfd *abfd)
{
struct lst_header lst_header;
struct ar_hdr ar_header;
struct artdata *ardata = bfd_ardata (abfd);
char nextname[17];
bfd_size_type amt = 16;
- int i = bfd_bread ((PTR) nextname, amt, abfd);
+ int i = bfd_bread ((void *) nextname, amt, abfd);
/* Special cases. */
if (i == 0)
/* Read in and sanity check the archive header. */
amt = sizeof (struct ar_hdr);
- if (bfd_bread ((PTR) &ar_header, amt, abfd) != amt)
+ if (bfd_bread ((void *) &ar_header, amt, abfd) != amt)
return FALSE;
if (strncmp (ar_header.ar_fmag, ARFMAG, 2))
/* Read in the library symbol table. We'll make heavy use of this
in just a minute. */
amt = sizeof (struct lst_header);
- if (bfd_bread ((PTR) &lst_header, amt, abfd) != amt)
+ if (bfd_bread ((void *) &lst_header, amt, abfd) != amt)
return FALSE;
/* Sanity check. */
ardata->cache = 0;
amt = ardata->symdef_count;
amt *= sizeof (carsym);
- ardata->symdefs = (carsym *) bfd_alloc (abfd, amt);
+ ardata->symdefs = bfd_alloc (abfd, amt);
if (!ardata->symdefs)
return FALSE;
and the size of the associated string section. */
static bfd_boolean
-som_bfd_prep_for_ar_write (abfd, num_syms, stringsize)
- bfd *abfd;
- unsigned int *num_syms, *stringsize;
+som_bfd_prep_for_ar_write (bfd *abfd,
+ unsigned int *num_syms,
+ unsigned int *stringsize)
{
bfd *curr_bfd = abfd->archive_head;
SOM ABI. */
static unsigned int
-som_bfd_ar_symbol_hash (symbol)
- asymbol *symbol;
+som_bfd_ar_symbol_hash (asymbol *symbol)
{
unsigned int len = strlen (symbol->name);
symbol table. */
static bfd_boolean
-som_bfd_ar_write_symbol_stuff (abfd, nsyms, string_size, lst, elength)
- bfd *abfd;
- unsigned int nsyms, string_size;
- struct lst_header lst;
- unsigned elength;
+som_bfd_ar_write_symbol_stuff (bfd *abfd,
+ unsigned int nsyms,
+ unsigned int string_size,
+ struct lst_header lst,
+ unsigned elength)
{
file_ptr lst_filepos;
char *strings = NULL, *p;
amt = lst.hash_size;
amt *= sizeof (unsigned int);
- hash_table = (unsigned int *) bfd_zmalloc (amt);
+ hash_table = bfd_zmalloc (amt);
if (hash_table == NULL && lst.hash_size != 0)
goto error_return;
amt = lst.module_count;
amt *= sizeof (struct som_entry);
- som_dict = (struct som_entry *) bfd_zmalloc (amt);
+ som_dict = bfd_zmalloc (amt);
if (som_dict == NULL && lst.module_count != 0)
goto error_return;
amt = lst.hash_size;
amt *= sizeof (struct lst_symbol_record *);
- last_hash_entry = ((struct lst_symbol_record **) bfd_zmalloc (amt));
+ last_hash_entry = bfd_zmalloc (amt);
if (last_hash_entry == NULL && lst.hash_size != 0)
goto error_return;
+ sizeof (struct lst_header);
}
else
- {
- /* First entry in this hash chain. */
- hash_table[curr_lst_sym->symbol_key % lst.hash_size]
- = (curr_lst_sym - lst_syms) * sizeof (struct lst_symbol_record)
- + lst.hash_size * 4
- + lst.module_count * sizeof (struct som_entry)
- + sizeof (struct lst_header);
- }
+ /* First entry in this hash chain. */
+ hash_table[curr_lst_sym->symbol_key % lst.hash_size]
+ = (curr_lst_sym - lst_syms) * sizeof (struct lst_symbol_record)
+ + lst.hash_size * 4
+ + lst.module_count * sizeof (struct som_entry)
+ + sizeof (struct lst_header);
/* Keep track of the last symbol we added to this chain so we can
easily update its next_entry pointer. */
/* Now scribble out the hash table. */
amt = lst.hash_size * 4;
- if (bfd_bwrite ((PTR) hash_table, amt, abfd) != amt)
+ if (bfd_bwrite ((void *) hash_table, amt, abfd) != amt)
goto error_return;
/* Then the SOM dictionary. */
amt = lst.module_count * sizeof (struct som_entry);
- if (bfd_bwrite ((PTR) som_dict, amt, abfd) != amt)
+ if (bfd_bwrite ((void *) som_dict, amt, abfd) != amt)
goto error_return;
/* The library symbols. */
amt = nsyms * sizeof (struct lst_symbol_record);
- if (bfd_bwrite ((PTR) lst_syms, amt, abfd) != amt)
+ if (bfd_bwrite ((void *) lst_syms, amt, abfd) != amt)
goto error_return;
/* And finally the strings. */
amt = string_size;
- if (bfd_bwrite ((PTR) strings, amt, abfd) != amt)
+ if (bfd_bwrite ((void *) strings, amt, abfd) != amt)
goto error_return;
if (hash_table != NULL)
You'll never believe this is really how armaps are handled in SOM... */
static bfd_boolean
-som_write_armap (abfd, elength, map, orl_count, stridx)
- bfd *abfd;
- unsigned int elength;
- struct orl *map ATTRIBUTE_UNUSED;
- unsigned int orl_count ATTRIBUTE_UNUSED;
- int stridx ATTRIBUTE_UNUSED;
+som_write_armap (bfd *abfd,
+ unsigned int elength,
+ struct orl *map ATTRIBUTE_UNUSED,
+ unsigned int orl_count ATTRIBUTE_UNUSED,
+ int stridx ATTRIBUTE_UNUSED)
{
bfd *curr_bfd;
struct stat statbuf;
/* Scribble out the ar header. */
amt = sizeof (struct ar_hdr);
- if (bfd_bwrite ((PTR) &hdr, amt, abfd) != amt)
+ if (bfd_bwrite ((void *) &hdr, amt, abfd) != amt)
return FALSE;
/* Now scribble out the lst header. */
amt = sizeof (struct lst_header);
- if (bfd_bwrite ((PTR) &lst, amt, abfd) != amt)
+ if (bfd_bwrite ((void *) &lst, amt, abfd) != amt)
return FALSE;
/* Build and write the armap. */
read it again later if we need it. */
static bfd_boolean
-som_bfd_free_cached_info (abfd)
- bfd *abfd;
+som_bfd_free_cached_info (bfd *abfd)
{
asection *o;
/* Free the native string and symbol tables. */
FREE (obj_som_symtab (abfd));
FREE (obj_som_stringtab (abfd));
- for (o = abfd->sections; o != (asection *) NULL; o = o->next)
+ for (o = abfd->sections; o != NULL; o = o->next)
{
/* Free the native relocations. */
o->reloc_count = (unsigned) -1;
/* Linker support functions. */
static bfd_boolean
-som_bfd_link_split_section (abfd, sec)
- bfd *abfd ATTRIBUTE_UNUSED;
- asection *sec;
+som_bfd_link_split_section (bfd *abfd ATTRIBUTE_UNUSED, asection *sec)
{
- return (som_is_subspace (sec) && sec->size > 240000);
+ return som_is_subspace (sec) && sec->size > 240000;
}
-#define som_close_and_cleanup som_bfd_free_cached_info
-
-#define som_read_ar_hdr _bfd_generic_read_ar_hdr
-#define som_openr_next_archived_file bfd_generic_openr_next_archived_file
-#define som_get_elt_at_index _bfd_generic_get_elt_at_index
-#define som_generic_stat_arch_elt bfd_generic_stat_arch_elt
-#define som_truncate_arname bfd_bsd_truncate_arname
-#define som_slurp_extended_name_table _bfd_slurp_extended_name_table
-#define som_construct_extended_name_table \
- _bfd_archive_coff_construct_extended_name_table
-#define som_update_armap_timestamp bfd_true
-
-#define som_bfd_is_target_special_symbol \
- ((bfd_boolean (*) (bfd *, asymbol *)) bfd_false)
-#define som_get_lineno _bfd_nosymbols_get_lineno
-#define som_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
-#define som_read_minisymbols _bfd_generic_read_minisymbols
-#define som_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol
-#define som_get_section_contents_in_window \
- _bfd_generic_get_section_contents_in_window
-
-#define som_bfd_get_relocated_section_contents \
- bfd_generic_get_relocated_section_contents
-#define som_bfd_relax_section bfd_generic_relax_section
-#define som_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
-#define som_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
-#define som_bfd_link_add_symbols _bfd_generic_link_add_symbols
-#define som_bfd_link_just_syms _bfd_generic_link_just_syms
-#define som_bfd_final_link _bfd_generic_final_link
-
-#define som_bfd_gc_sections bfd_generic_gc_sections
-#define som_bfd_merge_sections bfd_generic_merge_sections
-#define som_bfd_is_group_section bfd_generic_is_group_section
-#define som_bfd_discard_group bfd_generic_discard_group
-#define som_section_already_linked \
- _bfd_generic_section_already_linked
-
-const bfd_target som_vec = {
- "som", /* name */
+#define som_close_and_cleanup som_bfd_free_cached_info
+#define som_read_ar_hdr _bfd_generic_read_ar_hdr
+#define som_openr_next_archived_file bfd_generic_openr_next_archived_file
+#define som_get_elt_at_index _bfd_generic_get_elt_at_index
+#define som_generic_stat_arch_elt bfd_generic_stat_arch_elt
+#define som_truncate_arname bfd_bsd_truncate_arname
+#define som_slurp_extended_name_table _bfd_slurp_extended_name_table
+#define som_construct_extended_name_table _bfd_archive_coff_construct_extended_name_table
+#define som_update_armap_timestamp bfd_true
+#define som_bfd_is_target_special_symbol ((bfd_boolean (*) (bfd *, asymbol *)) bfd_false)
+#define som_get_lineno _bfd_nosymbols_get_lineno
+#define som_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
+#define som_read_minisymbols _bfd_generic_read_minisymbols
+#define som_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol
+#define som_get_section_contents_in_window _bfd_generic_get_section_contents_in_window
+#define som_bfd_get_relocated_section_contents bfd_generic_get_relocated_section_contents
+#define som_bfd_relax_section bfd_generic_relax_section
+#define som_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
+#define som_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
+#define som_bfd_link_add_symbols _bfd_generic_link_add_symbols
+#define som_bfd_link_just_syms _bfd_generic_link_just_syms
+#define som_bfd_final_link _bfd_generic_final_link
+#define som_bfd_gc_sections bfd_generic_gc_sections
+#define som_bfd_merge_sections bfd_generic_merge_sections
+#define som_bfd_is_group_section bfd_generic_is_group_section
+#define som_bfd_discard_group bfd_generic_discard_group
+#define som_section_already_linked _bfd_generic_section_already_linked
+
+const bfd_target som_vec =
+{
+ "som", /* Name. */
bfd_target_som_flavour,
- BFD_ENDIAN_BIG, /* target byte order */
- BFD_ENDIAN_BIG, /* target headers byte order */
- (HAS_RELOC | EXEC_P | /* object flags */
+ BFD_ENDIAN_BIG, /* Target byte order. */
+ BFD_ENDIAN_BIG, /* Target headers byte order. */
+ (HAS_RELOC | EXEC_P | /* Object flags. */
HAS_LINENO | HAS_DEBUG |
HAS_SYMS | HAS_LOCALS | WP_TEXT | D_PAGED | DYNAMIC),
(SEC_CODE | SEC_DATA | SEC_ROM | SEC_HAS_CONTENTS | SEC_LINK_ONCE
- | SEC_ALLOC | SEC_LOAD | SEC_RELOC), /* section flags */
+ | SEC_ALLOC | SEC_LOAD | SEC_RELOC), /* Section flags. */
-/* leading_symbol_char: is the first char of a user symbol
- predictable, and if so what is it. */
+ /* Leading_symbol_char: is the first char of a user symbol
+ predictable, and if so what is it. */
0,
- '/', /* ar_pad_char */
- 14, /* ar_max_namelen */
+ '/', /* AR_pad_char. */
+ 14, /* AR_max_namelen. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* data */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Data. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* hdrs */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Headers. */
{_bfd_dummy_target,
- som_object_p, /* bfd_check_format */
+ som_object_p, /* bfd_check_format. */
bfd_generic_archive_p,
_bfd_dummy_target
},
NULL,
- (PTR) 0
+ NULL
};
#endif /* HOST_HPPAHPUX || HOST_HPPABSD || HOST_HPPAOSF */
/* HP PA-RISC SOM object file format: definitions internal to BFD.
Copyright 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1998, 2000, 2001,
- 2002, 2003, 2004 Free Software Foundation, Inc.
+ 2002, 2003, 2004, 2005 Free Software Foundation, Inc.
Contributed by the Center for Software Science at the
University of Utah (pa-gdb-bugs@cs.utah.edu).
#define AUX_HDR_SIZE sizeof (struct som_exec_auxhdr)
typedef struct som_symbol
+{
+ asymbol symbol;
+ unsigned int som_type;
+
+ /* Structured like the ELF tc_data union. Allows more code sharing
+ in GAS this way. */
+ union
{
- asymbol symbol;
- unsigned int som_type;
-
- /* Structured like the ELF tc_data union. Allows more code sharing
- in GAS this way. */
- union
- {
- struct
- {
- unsigned int hppa_arg_reloc;
- unsigned int hppa_priv_level;
- } ap;
- PTR any;
- }
- tc_data;
-
- /* Index of this symbol in the symbol table. Only used when
- building relocation streams for incomplete objects. */
- int index;
-
- /* How many times this symbol is used in a relocation. By sorting
- the symbols from most used to least used we can significantly
- reduce the size of the relocation stream for incomplete objects. */
- int reloc_count;
-
- /* During object file writing, the offset of the name of this symbol
- in the SOM string table. */
- int stringtab_offset;
+ struct
+ {
+ unsigned int hppa_arg_reloc;
+ unsigned int hppa_priv_level;
+ } ap;
+ PTR any;
}
+ tc_data;
+
+ /* Index of this symbol in the symbol table. Only used when
+ building relocation streams for incomplete objects. */
+ int index;
+
+ /* How many times this symbol is used in a relocation. By sorting
+ the symbols from most used to least used we can significantly
+ reduce the size of the relocation stream for incomplete objects. */
+ int reloc_count;
+
+ /* During object file writing, the offset of the name of this symbol
+ in the SOM string table. */
+ int stringtab_offset;
+}
som_symbol_type;
/* A structure containing all the magic information stored in a BFD's
private data which needs to be copied during an objcopy/strip run. */
struct som_exec_data
- {
- /* Sort-of a magic number. BSD uses it to distinguish between
- native executables and hpux executables. */
- short system_id;
+{
+ /* Sort-of a magic number. BSD uses it to distinguish between
+ native executables and hpux executables. */
+ short system_id;
- /* Magic exec flags. These control things like whether or not
- null pointer dereferencing is allowed and the like. */
- long exec_flags;
+ /* Magic exec flags. These control things like whether or not
+ null pointer dereferencing is allowed and the like. */
+ long exec_flags;
- /* We must preserve the version identifier too. Some versions
- of the HP linker do not grok NEW_VERSION_ID for reasons unknown. */
- unsigned int version_id;
+ /* We must preserve the version identifier too. Some versions
+ of the HP linker do not grok NEW_VERSION_ID for reasons unknown. */
+ unsigned int version_id;
- /* Add more stuff here as needed. Good examples of information
- we might want to pass would be presumed_dp, entry_* and maybe
- others from the file header. */
- };
+ /* Add more stuff here as needed. Good examples of information
+ we might want to pass would be presumed_dp, entry_* and maybe
+ others from the file header. */
+};
struct somdata
- {
- /* All the magic information about an executable which lives
- in the private BFD structure and needs to be copied from
- the input bfd to the output bfd during an objcopy/strip. */
- struct som_exec_data *exec_data;
-
- /* These three fields are only used when writing files and are
- generated from scratch. They need not be copied for objcopy
- or strip to work. */
- struct header *file_hdr;
- struct copyright_aux_hdr *copyright_aux_hdr;
- struct user_string_aux_hdr *version_aux_hdr;
- struct som_exec_auxhdr *exec_hdr;
- COMPUNIT *comp_unit;
-
- /* Pointers to a saved copy of the symbol and string tables. These
- need not be copied for objcopy or strip to work. */
- som_symbol_type *symtab;
- char *stringtab;
- asymbol **sorted_syms;
-
- /* We remember these offsets so that after check_file_format, we have
- no dependencies on the particular format of the exec_hdr.
- These offsets need not be copied for objcopy or strip to work. */
-
- file_ptr sym_filepos;
- file_ptr str_filepos;
- file_ptr reloc_filepos;
- unsigned stringtab_size;
- };
+{
+ /* All the magic information about an executable which lives
+ in the private BFD structure and needs to be copied from
+ the input bfd to the output bfd during an objcopy/strip. */
+ struct som_exec_data *exec_data;
+
+ /* These three fields are only used when writing files and are
+ generated from scratch. They need not be copied for objcopy
+ or strip to work. */
+ struct header *file_hdr;
+ struct copyright_aux_hdr *copyright_aux_hdr;
+ struct user_string_aux_hdr *version_aux_hdr;
+ struct som_exec_auxhdr *exec_hdr;
+ COMPUNIT *comp_unit;
+
+ /* Pointers to a saved copy of the symbol and string tables. These
+ need not be copied for objcopy or strip to work. */
+ som_symbol_type *symtab;
+ char *stringtab;
+ asymbol **sorted_syms;
+
+ /* We remember these offsets so that after check_file_format, we have
+ no dependencies on the particular format of the exec_hdr.
+ These offsets need not be copied for objcopy or strip to work. */
+
+ file_ptr sym_filepos;
+ file_ptr str_filepos;
+ file_ptr reloc_filepos;
+ unsigned stringtab_size;
+};
struct som_data_struct
- {
- struct somdata a;
- };
+{
+ struct somdata a;
+};
struct som_subspace_dictionary_record
- {
- int space_index;
- unsigned int access_control_bits : 7;
- unsigned int memory_resident : 1;
- unsigned int dup_common : 1;
- unsigned int is_common : 1;
- unsigned int is_loadable : 1;
- unsigned int quadrant : 2;
- unsigned int initially_frozen : 1;
- unsigned int is_first : 1;
- unsigned int code_only : 1;
- unsigned int sort_key : 8;
- unsigned int replicate_init : 1;
- unsigned int continuation : 1;
- unsigned int is_tspecific : 1;
- unsigned int is_comdat : 1;
- unsigned int reserved : 4;
- int file_loc_init_value;
- unsigned int initialization_length;
- unsigned int subspace_start;
- unsigned int subspace_length;
- unsigned int reserved2 : 5;
- unsigned int alignment :27;
- union name_pt name;
- int fixup_request_index;
- unsigned int fixup_request_quantity;
- };
+{
+ int space_index;
+ unsigned int access_control_bits : 7;
+ unsigned int memory_resident : 1;
+ unsigned int dup_common : 1;
+ unsigned int is_common : 1;
+ unsigned int is_loadable : 1;
+ unsigned int quadrant : 2;
+ unsigned int initially_frozen : 1;
+ unsigned int is_first : 1;
+ unsigned int code_only : 1;
+ unsigned int sort_key : 8;
+ unsigned int replicate_init : 1;
+ unsigned int continuation : 1;
+ unsigned int is_tspecific : 1;
+ unsigned int is_comdat : 1;
+ unsigned int reserved : 4;
+ int file_loc_init_value;
+ unsigned int initialization_length;
+ unsigned int subspace_start;
+ unsigned int subspace_length;
+ unsigned int reserved2 : 5;
+ unsigned int alignment :27;
+ union name_pt name;
+ int fixup_request_index;
+ unsigned int fixup_request_quantity;
+};
/* Substructure of som_section_data_struct used to hold information
which can't be represented by the generic BFD section structure,
but which must be copied during objcopy or strip. */
struct som_copyable_section_data_struct
- {
- /* Various fields in space and subspace headers that we need
- to pass around. */
- unsigned int sort_key : 8;
- unsigned int access_control_bits : 7;
- unsigned int is_defined : 1;
- unsigned int is_private : 1;
- unsigned int quadrant : 2;
- unsigned int is_comdat : 1;
- unsigned int is_common : 1;
- unsigned int dup_common : 1;
-
- /* For subspaces, this points to the section which represents the
- space in which the subspace is contained. For spaces it points
- back to the section for this space. */
- asection *container;
-
- /* The user-specified space number. It is wrong to use this as
- an index since duplicates and holes are allowed. */
- int space_number;
-
- /* Add more stuff here as needed. Good examples of information
- we might want to pass would be initialization pointers,
- and the many subspace flags we do not represent yet. */
- };
+{
+ /* Various fields in space and subspace headers that we need
+ to pass around. */
+ unsigned int sort_key : 8;
+ unsigned int access_control_bits : 7;
+ unsigned int is_defined : 1;
+ unsigned int is_private : 1;
+ unsigned int quadrant : 2;
+ unsigned int is_comdat : 1;
+ unsigned int is_common : 1;
+ unsigned int dup_common : 1;
+
+ /* For subspaces, this points to the section which represents the
+ space in which the subspace is contained. For spaces it points
+ back to the section for this space. */
+ asection *container;
+
+ /* The user-specified space number. It is wrong to use this as
+ an index since duplicates and holes are allowed. */
+ int space_number;
+
+ /* Add more stuff here as needed. Good examples of information
+ we might want to pass would be initialization pointers,
+ and the many subspace flags we do not represent yet. */
+};
/* Used to keep extra SOM specific information for a given section.
reloc_stream is the actual stream of relocation entries. */
struct som_section_data_struct
- {
- struct som_copyable_section_data_struct *copy_data;
- unsigned int reloc_size;
- char *reloc_stream;
- struct space_dictionary_record *space_dict;
- struct som_subspace_dictionary_record *subspace_dict;
- };
+{
+ struct som_copyable_section_data_struct *copy_data;
+ unsigned int reloc_size;
+ char *reloc_stream;
+ struct space_dictionary_record *space_dict;
+ struct som_subspace_dictionary_record *subspace_dict;
+};
#define somdata(bfd) ((bfd)->tdata.som_data->a)
-#define obj_som_exec_data(bfd) (somdata(bfd).exec_data)
-#define obj_som_file_hdr(bfd) (somdata(bfd).file_hdr)
-#define obj_som_exec_hdr(bfd) (somdata(bfd).exec_hdr)
-#define obj_som_copyright_hdr(bfd) (somdata(bfd).copyright_aux_hdr)
-#define obj_som_version_hdr(bfd) (somdata(bfd).version_aux_hdr)
-#define obj_som_compilation_unit(bfd) (somdata(bfd).comp_unit)
-#define obj_som_symtab(bfd) (somdata(bfd).symtab)
-#define obj_som_stringtab(bfd) (somdata(bfd).stringtab)
-#define obj_som_sym_filepos(bfd) (somdata(bfd).sym_filepos)
-#define obj_som_str_filepos(bfd) (somdata(bfd).str_filepos)
-#define obj_som_stringtab_size(bfd) (somdata(bfd).stringtab_size)
-#define obj_som_reloc_filepos(bfd) (somdata(bfd).reloc_filepos)
-#define obj_som_sorted_syms(bfd) (somdata(bfd).sorted_syms)
-#define som_section_data(sec) \
- ((struct som_section_data_struct *)sec->used_by_bfd)
+#define obj_som_exec_data(bfd) (somdata (bfd).exec_data)
+#define obj_som_file_hdr(bfd) (somdata (bfd).file_hdr)
+#define obj_som_exec_hdr(bfd) (somdata (bfd).exec_hdr)
+#define obj_som_copyright_hdr(bfd) (somdata (bfd).copyright_aux_hdr)
+#define obj_som_version_hdr(bfd) (somdata (bfd).version_aux_hdr)
+#define obj_som_compilation_unit(bfd) (somdata (bfd).comp_unit)
+#define obj_som_symtab(bfd) (somdata (bfd).symtab)
+#define obj_som_stringtab(bfd) (somdata (bfd).stringtab)
+#define obj_som_sym_filepos(bfd) (somdata (bfd).sym_filepos)
+#define obj_som_str_filepos(bfd) (somdata (bfd).str_filepos)
+#define obj_som_stringtab_size(bfd) (somdata (bfd).stringtab_size)
+#define obj_som_reloc_filepos(bfd) (somdata (bfd).reloc_filepos)
+#define obj_som_sorted_syms(bfd) (somdata (bfd).sorted_syms)
+#define som_section_data(sec) ((struct som_section_data_struct *) sec->used_by_bfd)
#define som_symbol_data(symbol) ((som_symbol_type *) symbol)
/* Defines groups of basic relocations. FIXME: These should
#define R_HPPA_END_TRY R_END_TRY
/* Exported functions, mostly for use by GAS. */
-bfd_boolean bfd_som_set_section_attributes
- PARAMS ((asection *, int, int, unsigned int, int));
-bfd_boolean bfd_som_set_subsection_attributes
- PARAMS ((asection *, asection *, int, unsigned int, int, int, int, int));
-void bfd_som_set_symbol_type PARAMS ((asymbol *, unsigned int));
-bfd_boolean bfd_som_attach_aux_hdr PARAMS ((bfd *, int, char *));
-int ** hppa_som_gen_reloc_type
- PARAMS ((bfd *, int, int, enum hppa_reloc_field_selector_type_alt,
- int, asymbol *));
-bfd_boolean bfd_som_attach_compilation_unit
- PARAMS ((bfd *, const char *, const char *, const char *, const char *));
+bfd_boolean bfd_som_set_section_attributes (asection *, int, int, unsigned int, int);
+bfd_boolean bfd_som_set_subsection_attributes (asection *, asection *, int, unsigned int, int, int, int, int);
+void bfd_som_set_symbol_type (asymbol *, unsigned int);
+bfd_boolean bfd_som_attach_aux_hdr (bfd *, int, char *);
+int ** hppa_som_gen_reloc_type (bfd *, int, int, enum hppa_reloc_field_selector_type_alt, int, asymbol *);
+bfd_boolean bfd_som_attach_compilation_unit (bfd *, const char *, const char *, const char *, const char *);
#endif /* _SOM_H */
Free Software Foundation, Inc.
Written by Steve Chamberlain of Cygnus Support <sac@cygnus.com>.
-This file is part of BFD, the Binary File Descriptor library.
+ This file is part of BFD, the Binary File Descriptor library.
-This program is free software; you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation; either version 2 of the License, or
-(at your option) any later version.
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-GNU General Public License for more details.
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
-You should have received a copy of the GNU General Public License
-along with this program; if not, write to the Free Software
-Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
-/*
-SUBSECTION
+/* SUBSECTION
S-Record handling
-DESCRIPTION
+ DESCRIPTION
Ordinary S-Records cannot hold anything but addresses and
data, so that's all that we implement.
An s record looks like:
-EXAMPLE
+ EXAMPLE
S<type><length><address><data><checksum>
-DESCRIPTION
+ DESCRIPTION
Where
o length
is the number of bytes following upto the checksum. Note that
is the sum of all the raw byte data in the record, from the length
upwards, modulo 256 and subtracted from 255.
-SUBSECTION
+ SUBSECTION
Symbol S-Record handling
-DESCRIPTION
+ DESCRIPTION
Some ICE equipment understands an addition to the standard
S-Record format; symbols and their addresses can be sent
before the data.
so a short symbol table could look like:
-EXAMPLE
+ EXAMPLE
$$ flash.x
$$ flash.c
_port6 $0
_end $8036
$$
-DESCRIPTION
+ DESCRIPTION
We allow symbols to be anywhere in the data stream - the module names
- are always ignored.
-
-*/
+ are always ignored. */
#include "bfd.h"
#include "sysdep.h"
#include "libiberty.h"
#include "safe-ctype.h"
-static void srec_get_symbol_info PARAMS ((bfd *, asymbol *, symbol_info *));
-static void srec_print_symbol
- PARAMS ((bfd *, PTR, asymbol *, bfd_print_symbol_type));
-static void srec_init PARAMS ((void));
-static bfd_boolean srec_mkobject PARAMS ((bfd *));
-static int srec_get_byte PARAMS ((bfd *, bfd_boolean *));
-static void srec_bad_byte PARAMS ((bfd *, unsigned int, int, bfd_boolean));
-static bfd_boolean srec_scan PARAMS ((bfd *));
-static const bfd_target *srec_object_p PARAMS ((bfd *));
-static const bfd_target *symbolsrec_object_p PARAMS ((bfd *));
-static bfd_boolean srec_read_section PARAMS ((bfd *, asection *, bfd_byte *));
-
-static bfd_boolean srec_write_record
- PARAMS ((bfd *, unsigned int, bfd_vma, const bfd_byte *, const bfd_byte *));
-static bfd_boolean srec_write_header PARAMS ((bfd *));
-static bfd_boolean srec_write_symbols PARAMS ((bfd *));
-static bfd_boolean srec_new_symbol PARAMS ((bfd *, const char *, bfd_vma));
-static bfd_boolean srec_get_section_contents
- PARAMS ((bfd *, asection *, PTR, file_ptr, bfd_size_type));
-static bfd_boolean srec_set_arch_mach
- PARAMS ((bfd *, enum bfd_architecture, unsigned long));
-static bfd_boolean srec_set_section_contents
- PARAMS ((bfd *, sec_ptr, const PTR, file_ptr, bfd_size_type));
-static bfd_boolean internal_srec_write_object_contents PARAMS ((bfd *, int));
-static bfd_boolean srec_write_object_contents PARAMS ((bfd *));
-static bfd_boolean symbolsrec_write_object_contents PARAMS ((bfd *));
-static int srec_sizeof_headers PARAMS ((bfd *, bfd_boolean));
-static long srec_get_symtab_upper_bound PARAMS ((bfd *));
-static long srec_canonicalize_symtab PARAMS ((bfd *, asymbol **));
/* Macros for converting between hex and binary. */
static const char digs[] = "0123456789ABCDEF";
-#define NIBBLE(x) hex_value(x)
-#define HEX(buffer) ((NIBBLE((buffer)[0])<<4) + NIBBLE((buffer)[1]))
+#define NIBBLE(x) hex_value(x)
+#define HEX(buffer) ((NIBBLE ((buffer)[0])<<4) + NIBBLE ((buffer)[1]))
#define TOHEX(d, x, ch) \
d[1] = digs[(x) & 0xf]; \
d[0] = digs[((x)>>4)&0xf]; \
ch += ((x) & 0xff);
-#define ISHEX(x) hex_p(x)
-
-/* Initialize by filling in the hex conversion array. */
-
-static void
-srec_init ()
-{
- static bfd_boolean inited = FALSE;
-
- if (! inited)
- {
- inited = TRUE;
- hex_init ();
- }
-}
+#define ISHEX(x) hex_p(x)
/* The maximum number of address+data+crc bytes on a line is FF. */
#define MAXCHUNK 0xff
}
tdata_type;
-static bfd_boolean srec_write_section
- PARAMS ((bfd *, tdata_type *, srec_data_list_type *));
-static bfd_boolean srec_write_terminator
- PARAMS ((bfd *, tdata_type *));
+/* Initialize by filling in the hex conversion array. */
+
+static void
+srec_init (void)
+{
+ static bfd_boolean inited = FALSE;
+
+ if (! inited)
+ {
+ inited = TRUE;
+ hex_init ();
+ }
+}
/* Set up the S-record tdata information. */
static bfd_boolean
-srec_mkobject (abfd)
- bfd *abfd;
+srec_mkobject (bfd *abfd)
{
- bfd_size_type amt;
tdata_type *tdata;
srec_init ();
- amt = sizeof (tdata_type);
- tdata = (tdata_type *) bfd_alloc (abfd, amt);
+ tdata = bfd_alloc (abfd, sizeof (tdata_type));
if (tdata == NULL)
return FALSE;
occurred. Return EOF on error or end of file. */
static int
-srec_get_byte (abfd, errorptr)
- bfd *abfd;
- bfd_boolean *errorptr;
+srec_get_byte (bfd *abfd, bfd_boolean *errorptr)
{
bfd_byte c;
error messages. */
static void
-srec_bad_byte (abfd, lineno, c, error)
- bfd *abfd;
- unsigned int lineno;
- int c;
- bfd_boolean error;
+srec_bad_byte (bfd *abfd,
+ unsigned int lineno,
+ int c,
+ bfd_boolean error)
{
if (c == EOF)
{
/* Add a new symbol found in an S-record file. */
static bfd_boolean
-srec_new_symbol (abfd, name, val)
- bfd *abfd;
- const char *name;
- bfd_vma val;
+srec_new_symbol (bfd *abfd, const char *name, bfd_vma val)
{
struct srec_symbol *n;
- bfd_size_type amt = sizeof (struct srec_symbol);
- n = (struct srec_symbol *) bfd_alloc (abfd, amt);
+ n = bfd_alloc (abfd, sizeof (* n));
if (n == NULL)
return FALSE;
section for each contiguous set of bytes. */
static bfd_boolean
-srec_scan (abfd)
- bfd *abfd;
+srec_scan (bfd *abfd)
{
int c;
unsigned int lineno = 1;
}
++lineno;
-
break;
case ' ':
}
alc = 10;
- symbuf = (char *) bfd_malloc (alc + 1);
+ symbuf = bfd_malloc (alc + 1);
if (symbuf == NULL)
goto error_return;
char *n;
alc *= 2;
- n = (char *) bfd_realloc (symbuf, alc + 1);
+ n = bfd_realloc (symbuf, alc + 1);
if (n == NULL)
goto error_return;
p = n + (p - symbuf);
{
if (buf != NULL)
free (buf);
- buf = (bfd_byte *) bfd_malloc ((bfd_size_type) bytes * 2);
+ buf = bfd_malloc ((bfd_size_type) bytes * 2);
if (buf == NULL)
goto error_return;
bufsize = bytes * 2;
sprintf (secbuf, ".sec%d", bfd_count_sections (abfd) + 1);
amt = strlen (secbuf) + 1;
- secname = (char *) bfd_alloc (abfd, amt);
+ secname = bfd_alloc (abfd, amt);
strcpy (secname, secbuf);
sec = bfd_make_section (abfd, secname);
if (sec == NULL)
sec->size = bytes;
sec->filepos = pos;
}
-
break;
case '7':
/* Check whether an existing file is an S-record file. */
static const bfd_target *
-srec_object_p (abfd)
- bfd *abfd;
+srec_object_p (bfd *abfd)
{
- PTR tdata_save;
+ void * tdata_save;
bfd_byte b[4];
srec_init ();
/* Check whether an existing file is an S-record file with symbols. */
static const bfd_target *
-symbolsrec_object_p (abfd)
- bfd *abfd;
+symbolsrec_object_p (bfd *abfd)
{
- PTR tdata_save;
+ void * tdata_save;
char b[2];
srec_init ();
/* Read in the contents of a section in an S-record file. */
static bfd_boolean
-srec_read_section (abfd, section, contents)
- bfd *abfd;
- asection *section;
- bfd_byte *contents;
+srec_read_section (bfd *abfd, asection *section, bfd_byte *contents)
{
int c;
bfd_size_type sofar = 0;
{
if (buf != NULL)
free (buf);
- buf = (bfd_byte *) bfd_malloc ((bfd_size_type) bytes * 2);
+ buf = bfd_malloc ((bfd_size_type) bytes * 2);
if (buf == NULL)
goto error_return;
bufsize = bytes * 2;
/* Get the contents of a section in an S-record file. */
static bfd_boolean
-srec_get_section_contents (abfd, section, location, offset, count)
- bfd *abfd;
- asection *section;
- PTR location;
- file_ptr offset;
- bfd_size_type count;
+srec_get_section_contents (bfd *abfd,
+ asection *section,
+ void * location,
+ file_ptr offset,
+ bfd_size_type count)
{
if (section->used_by_bfd == NULL)
{
/* Set the architecture. We accept an unknown architecture here. */
static bfd_boolean
-srec_set_arch_mach (abfd, arch, mach)
- bfd *abfd;
- enum bfd_architecture arch;
- unsigned long mach;
+srec_set_arch_mach (bfd *abfd, enum bfd_architecture arch, unsigned long mach)
{
- if (arch == bfd_arch_unknown)
- {
- abfd->arch_info = &bfd_default_arch_struct;
- return TRUE;
- }
- return bfd_default_set_arch_mach (abfd, arch, mach);
+ if (arch != bfd_arch_unknown)
+ return bfd_default_set_arch_mach (abfd, arch, mach);
+
+ abfd->arch_info = & bfd_default_arch_struct;
+ return TRUE;
}
/* We have to save up all the Srecords for a splurge before output. */
static bfd_boolean
-srec_set_section_contents (abfd, section, location, offset, bytes_to_do)
- bfd *abfd;
- sec_ptr section;
- const PTR location;
- file_ptr offset;
- bfd_size_type bytes_to_do;
+srec_set_section_contents (bfd *abfd,
+ sec_ptr section,
+ const void * location,
+ file_ptr offset,
+ bfd_size_type bytes_to_do)
{
tdata_type *tdata = abfd->tdata.srec_data;
- register srec_data_list_type *entry;
+ srec_data_list_type *entry;
- entry = ((srec_data_list_type *)
- bfd_alloc (abfd, (bfd_size_type) sizeof (srec_data_list_type)));
+ entry = bfd_alloc (abfd, sizeof (* entry));
if (entry == NULL)
return FALSE;
{
bfd_byte *data;
- data = (bfd_byte *) bfd_alloc (abfd, bytes_to_do);
+ data = bfd_alloc (abfd, bytes_to_do);
if (data == NULL)
return FALSE;
- memcpy ((PTR) data, location, (size_t) bytes_to_do);
+ memcpy ((void *) data, location, (size_t) bytes_to_do);
/* Ff S3Forced is TRUE then always select S3 records,
regardless of the siez of the addresses. */
}
else
{
- register srec_data_list_type **look;
+ srec_data_list_type **look;
for (look = &tdata->head;
*look != NULL && (*look)->where < entry->where;
here. */
static bfd_boolean
-srec_write_record (abfd, type, address, data, end)
- bfd *abfd;
- unsigned int type;
- bfd_vma address;
- const bfd_byte *data;
- const bfd_byte *end;
+srec_write_record (bfd *abfd,
+ unsigned int type,
+ bfd_vma address,
+ const bfd_byte *data,
+ const bfd_byte *end)
{
char buffer[2 * MAXCHUNK + 6];
unsigned int check_sum = 0;
*dst++ = '\r';
*dst++ = '\n';
wrlen = dst - buffer;
- if (bfd_bwrite ((PTR) buffer, wrlen, abfd) != wrlen)
- return FALSE;
- return TRUE;
+
+ return bfd_bwrite ((void *) buffer, wrlen, abfd) == wrlen;
}
static bfd_boolean
-srec_write_header (abfd)
- bfd *abfd;
+srec_write_header (bfd *abfd)
{
unsigned int len = strlen (abfd->filename);
}
static bfd_boolean
-srec_write_section (abfd, tdata, list)
- bfd *abfd;
- tdata_type *tdata;
- srec_data_list_type *list;
+srec_write_section (bfd *abfd,
+ tdata_type *tdata,
+ srec_data_list_type *list)
{
unsigned int octets_written = 0;
bfd_byte *location = list->data;
}
static bfd_boolean
-srec_write_terminator (abfd, tdata)
- bfd *abfd;
- tdata_type *tdata;
+srec_write_terminator (bfd *abfd, tdata_type *tdata)
{
return srec_write_record (abfd, 10 - tdata->type,
abfd->start_address, NULL, NULL);
}
static bfd_boolean
-srec_write_symbols (abfd)
- bfd *abfd;
+srec_write_symbols (bfd *abfd)
{
/* Dump out the symbols of a bfd. */
int i;
{
bfd_size_type len;
asymbol **table = bfd_get_outsymbols (abfd);
+
len = strlen (abfd->filename);
if (bfd_bwrite ("$$ ", (bfd_size_type) 3, abfd) != 3
|| bfd_bwrite (abfd->filename, len, abfd) != len
}
static bfd_boolean
-internal_srec_write_object_contents (abfd, symbols)
- bfd *abfd;
- int symbols;
+internal_srec_write_object_contents (bfd *abfd, int symbols)
{
tdata_type *tdata = abfd->tdata.srec_data;
srec_data_list_type *list;
}
static bfd_boolean
-srec_write_object_contents (abfd)
- bfd *abfd;
+srec_write_object_contents (bfd *abfd)
{
return internal_srec_write_object_contents (abfd, 0);
}
static bfd_boolean
-symbolsrec_write_object_contents (abfd)
- bfd *abfd;
+symbolsrec_write_object_contents (bfd *abfd)
{
return internal_srec_write_object_contents (abfd, 1);
}
static int
-srec_sizeof_headers (abfd, exec)
- bfd *abfd ATTRIBUTE_UNUSED;
- bfd_boolean exec ATTRIBUTE_UNUSED;
+srec_sizeof_headers (bfd *abfd ATTRIBUTE_UNUSED,
+ bfd_boolean exec ATTRIBUTE_UNUSED)
{
return 0;
}
/* Return the amount of memory needed to read the symbol table. */
static long
-srec_get_symtab_upper_bound (abfd)
- bfd *abfd;
+srec_get_symtab_upper_bound (bfd *abfd)
{
return (bfd_get_symcount (abfd) + 1) * sizeof (asymbol *);
}
/* Return the symbol table. */
static long
-srec_canonicalize_symtab (abfd, alocation)
- bfd *abfd;
- asymbol **alocation;
+srec_canonicalize_symtab (bfd *abfd, asymbol **alocation)
{
bfd_size_type symcount = bfd_get_symcount (abfd);
asymbol *csymbols;
asymbol *c;
struct srec_symbol *s;
- csymbols = (asymbol *) bfd_alloc (abfd, symcount * sizeof (asymbol));
+ csymbols = bfd_alloc (abfd, symcount * sizeof (asymbol));
if (csymbols == NULL && symcount != 0)
return 0;
abfd->tdata.srec_data->csymbols = csymbols;
}
static void
-srec_get_symbol_info (ignore_abfd, symbol, ret)
- bfd *ignore_abfd ATTRIBUTE_UNUSED;
- asymbol *symbol;
- symbol_info *ret;
+srec_get_symbol_info (bfd *ignore_abfd ATTRIBUTE_UNUSED,
+ asymbol *symbol,
+ symbol_info *ret)
{
bfd_symbol_info (symbol, ret);
}
static void
-srec_print_symbol (abfd, afile, symbol, how)
- bfd *abfd;
- PTR afile;
- asymbol *symbol;
- bfd_print_symbol_type how;
+srec_print_symbol (bfd *abfd,
+ void * afile,
+ asymbol *symbol,
+ bfd_print_symbol_type how)
{
FILE *file = (FILE *) afile;
+
switch (how)
{
case bfd_print_symbol_name:
fprintf (file, "%s", symbol->name);
break;
default:
- bfd_print_symbol_vandf (abfd, (PTR) file, symbol);
+ bfd_print_symbol_vandf (abfd, (void *) file, symbol);
fprintf (file, " %-5s %s",
symbol->section->name,
symbol->name);
-
}
}
-#define srec_close_and_cleanup _bfd_generic_close_and_cleanup
-#define srec_bfd_free_cached_info _bfd_generic_bfd_free_cached_info
-#define srec_new_section_hook _bfd_generic_new_section_hook
-
-#define srec_bfd_is_target_special_symbol ((bfd_boolean (*) (bfd *, asymbol *)) bfd_false)
-#define srec_bfd_is_local_label_name bfd_generic_is_local_label_name
-#define srec_get_lineno _bfd_nosymbols_get_lineno
-#define srec_find_nearest_line _bfd_nosymbols_find_nearest_line
-#define srec_make_empty_symbol _bfd_generic_make_empty_symbol
-#define srec_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
-#define srec_read_minisymbols _bfd_generic_read_minisymbols
-#define srec_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol
-
-#define srec_get_reloc_upper_bound \
- ((long (*) PARAMS ((bfd *, asection *))) bfd_0l)
-#define srec_canonicalize_reloc \
- ((long (*) PARAMS ((bfd *, asection *, arelent **, asymbol **))) bfd_0l)
-#define srec_bfd_reloc_type_lookup _bfd_norelocs_bfd_reloc_type_lookup
-
-#define srec_get_section_contents_in_window \
- _bfd_generic_get_section_contents_in_window
-
-#define srec_bfd_get_relocated_section_contents \
- bfd_generic_get_relocated_section_contents
-#define srec_bfd_relax_section bfd_generic_relax_section
-#define srec_bfd_gc_sections bfd_generic_gc_sections
-#define srec_bfd_merge_sections bfd_generic_merge_sections
-#define srec_bfd_is_group_section bfd_generic_is_group_section
-#define srec_bfd_discard_group bfd_generic_discard_group
-#define srec_section_already_linked \
- _bfd_generic_section_already_linked
-#define srec_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
-#define srec_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
-#define srec_bfd_link_add_symbols _bfd_generic_link_add_symbols
-#define srec_bfd_link_just_syms _bfd_generic_link_just_syms
-#define srec_bfd_final_link _bfd_generic_final_link
-#define srec_bfd_link_split_section _bfd_generic_link_split_section
+#define srec_close_and_cleanup _bfd_generic_close_and_cleanup
+#define srec_bfd_free_cached_info _bfd_generic_bfd_free_cached_info
+#define srec_new_section_hook _bfd_generic_new_section_hook
+#define srec_bfd_is_target_special_symbol ((bfd_boolean (*) (bfd *, asymbol *)) bfd_false)
+#define srec_bfd_is_local_label_name bfd_generic_is_local_label_name
+#define srec_get_lineno _bfd_nosymbols_get_lineno
+#define srec_find_nearest_line _bfd_nosymbols_find_nearest_line
+#define srec_make_empty_symbol _bfd_generic_make_empty_symbol
+#define srec_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
+#define srec_read_minisymbols _bfd_generic_read_minisymbols
+#define srec_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol
+#define srec_get_reloc_upper_bound ((long (*) (bfd *, asection *)) bfd_0l)
+#define srec_canonicalize_reloc ((long (*) (bfd *, asection *, arelent **, asymbol **)) bfd_0l)
+#define srec_bfd_reloc_type_lookup _bfd_norelocs_bfd_reloc_type_lookup
+#define srec_get_section_contents_in_window _bfd_generic_get_section_contents_in_window
+#define srec_bfd_get_relocated_section_contents bfd_generic_get_relocated_section_contents
+#define srec_bfd_relax_section bfd_generic_relax_section
+#define srec_bfd_gc_sections bfd_generic_gc_sections
+#define srec_bfd_merge_sections bfd_generic_merge_sections
+#define srec_bfd_is_group_section bfd_generic_is_group_section
+#define srec_bfd_discard_group bfd_generic_discard_group
+#define srec_section_already_linked _bfd_generic_section_already_linked
+#define srec_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
+#define srec_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
+#define srec_bfd_link_add_symbols _bfd_generic_link_add_symbols
+#define srec_bfd_link_just_syms _bfd_generic_link_just_syms
+#define srec_bfd_final_link _bfd_generic_final_link
+#define srec_bfd_link_split_section _bfd_generic_link_split_section
const bfd_target srec_vec =
{
- "srec", /* name */
+ "srec", /* Name. */
bfd_target_srec_flavour,
- BFD_ENDIAN_UNKNOWN, /* target byte order */
- BFD_ENDIAN_UNKNOWN, /* target headers byte order */
- (HAS_RELOC | EXEC_P | /* object flags */
+ BFD_ENDIAN_UNKNOWN, /* Target byte order. */
+ BFD_ENDIAN_UNKNOWN, /* Target headers byte order. */
+ (HAS_RELOC | EXEC_P | /* Object flags. */
HAS_LINENO | HAS_DEBUG |
HAS_SYMS | HAS_LOCALS | WP_TEXT | D_PAGED),
(SEC_CODE | SEC_DATA | SEC_ROM | SEC_HAS_CONTENTS
- | SEC_ALLOC | SEC_LOAD | SEC_RELOC), /* section flags */
- 0, /* leading underscore */
- ' ', /* ar_pad_char */
- 16, /* ar_max_namelen */
+ | SEC_ALLOC | SEC_LOAD | SEC_RELOC), /* Section flags. */
+ 0, /* Leading underscore. */
+ ' ', /* AR_pad_char. */
+ 16, /* AR_max_namelen. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* data */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Data. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* hdrs */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Hdrs. */
{
_bfd_dummy_target,
- srec_object_p, /* bfd_check_format */
+ srec_object_p, /* bfd_check_format. */
_bfd_dummy_target,
_bfd_dummy_target,
},
_bfd_generic_mkarchive,
bfd_false,
},
- { /* bfd_write_contents */
+ { /* bfd_write_contents. */
bfd_false,
srec_write_object_contents,
_bfd_write_archive_contents,
NULL,
- (PTR) 0
+ NULL
};
const bfd_target symbolsrec_vec =
{
- "symbolsrec", /* name */
+ "symbolsrec", /* Name. */
bfd_target_srec_flavour,
- BFD_ENDIAN_UNKNOWN, /* target byte order */
- BFD_ENDIAN_UNKNOWN, /* target headers byte order */
- (HAS_RELOC | EXEC_P | /* object flags */
+ BFD_ENDIAN_UNKNOWN, /* Target byte order. */
+ BFD_ENDIAN_UNKNOWN, /* Target headers byte order. */
+ (HAS_RELOC | EXEC_P | /* Object flags. */
HAS_LINENO | HAS_DEBUG |
HAS_SYMS | HAS_LOCALS | WP_TEXT | D_PAGED),
(SEC_CODE | SEC_DATA | SEC_ROM | SEC_HAS_CONTENTS
- | SEC_ALLOC | SEC_LOAD | SEC_RELOC), /* section flags */
- 0, /* leading underscore */
- ' ', /* ar_pad_char */
- 16, /* ar_max_namelen */
+ | SEC_ALLOC | SEC_LOAD | SEC_RELOC), /* Section flags. */
+ 0, /* Leading underscore. */
+ ' ', /* AR_pad_char. */
+ 16, /* AR_max_namelen. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* data */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Data. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* hdrs */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Headers. */
{
_bfd_dummy_target,
- symbolsrec_object_p, /* bfd_check_format */
+ symbolsrec_object_p, /* bfd_check_format. */
_bfd_dummy_target,
_bfd_dummy_target,
},
_bfd_generic_mkarchive,
bfd_false,
},
- { /* bfd_write_contents */
+ { /* bfd_write_contents. */
bfd_false,
symbolsrec_write_object_contents,
_bfd_write_archive_contents,
NULL,
- (PTR) 0
+ NULL
};
/* Stabs in sections linking support.
- Copyright 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004
+ Copyright 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005
Free Software Foundation, Inc.
Written by Ian Lance Taylor, Cygnus Support.
the string table for this unit, and the desc field is the number of
stabs symbols for this unit. */
-#define STRDXOFF (0)
-#define TYPEOFF (4)
-#define OTHEROFF (5)
-#define DESCOFF (6)
-#define VALOFF (8)
-#define STABSIZE (12)
+#define STRDXOFF 0
+#define TYPEOFF 4
+#define OTHEROFF 5
+#define DESCOFF 6
+#define VALOFF 8
+#define STABSIZE 12
/* A linked list of totals that we have found for a particular header
file. A total is a unique identifier for a particular BINCL...EINCL
bfd_size_type stridxs[1];
};
-static struct bfd_hash_entry *stab_link_includes_newfunc
- PARAMS ((struct bfd_hash_entry *, struct bfd_hash_table *, const char *));
\f
/* The function to create a new entry in the header file hash table. */
static struct bfd_hash_entry *
-stab_link_includes_newfunc (entry, table, string)
- struct bfd_hash_entry *entry;
- struct bfd_hash_table *table;
- const char *string;
+stab_link_includes_newfunc (struct bfd_hash_entry *entry,
+ struct bfd_hash_table *table,
+ const char *string)
{
struct stab_link_includes_entry *ret =
(struct stab_link_includes_entry *) entry;
/* Allocate the structure if it has not already been allocated by a
subclass. */
- if (ret == (struct stab_link_includes_entry *) NULL)
- ret = ((struct stab_link_includes_entry *)
- bfd_hash_allocate (table,
- sizeof (struct stab_link_includes_entry)));
- if (ret == (struct stab_link_includes_entry *) NULL)
- return (struct bfd_hash_entry *) ret;
+ if (ret == NULL)
+ ret = bfd_hash_allocate (table,
+ sizeof (struct stab_link_includes_entry));
+ if (ret == NULL)
+ return NULL;
/* Call the allocation method of the superclass. */
ret = ((struct stab_link_includes_entry *)
bfd_hash_newfunc ((struct bfd_hash_entry *) ret, table, string));
if (ret)
- {
- /* Set local fields. */
- ret->totals = NULL;
- }
+ /* Set local fields. */
+ ret->totals = NULL;
return (struct bfd_hash_entry *) ret;
}
pass of the linker. */
bfd_boolean
-_bfd_link_section_stabs (abfd, sinfo, stabsec, stabstrsec, psecinfo, pstring_offset)
- bfd *abfd;
- struct stab_info *sinfo;
- asection *stabsec;
- asection *stabstrsec;
- PTR *psecinfo;
- bfd_size_type *pstring_offset;
+_bfd_link_section_stabs (bfd *abfd,
+ struct stab_info *sinfo,
+ asection *stabsec,
+ asection *stabstrsec,
+ void * *psecinfo,
+ bfd_size_type *pstring_offset)
{
bfd_boolean first;
bfd_size_type count, amt;
if (stabsec->size == 0
|| stabstrsec->size == 0)
- {
- /* This file does not contain stabs debugging information. */
- return TRUE;
- }
+ /* This file does not contain stabs debugging information. */
+ return TRUE;
if (stabsec->size % STABSIZE != 0)
- {
- /* Something is wrong with the format of these stab symbols.
- Don't try to optimize them. */
- return TRUE;
- }
+ /* Something is wrong with the format of these stab symbols.
+ Don't try to optimize them. */
+ return TRUE;
if ((stabstrsec->flags & SEC_RELOC) != 0)
- {
- /* We shouldn't see relocations in the strings, and we aren't
- prepared to handle them. */
- return TRUE;
- }
+ /* We shouldn't see relocations in the strings, and we aren't
+ prepared to handle them. */
+ return TRUE;
if ((stabsec->output_section != NULL
&& bfd_is_abs_section (stabsec->output_section))
|| (stabstrsec->output_section != NULL
&& bfd_is_abs_section (stabstrsec->output_section)))
- {
- /* At least one of the sections is being discarded from the
- link, so we should just ignore them. */
- return TRUE;
- }
+ /* At least one of the sections is being discarded from the
+ link, so we should just ignore them. */
+ return TRUE;
first = FALSE;
/* Initialize the information we are going to store for this .stab
section. */
-
count = stabsec->size / STABSIZE;
amt = sizeof (struct stab_section_info);
memset (secinfo->stridxs, 0, (size_t) count * sizeof (bfd_size_type));
/* Read the stabs information from abfd. */
-
if (!bfd_malloc_and_get_section (abfd, stabsec, &stabbuf)
|| !bfd_malloc_and_get_section (abfd, stabstrsec, &stabstrbuf))
goto error_return;
/* Look through the stabs symbols, work out the new string indices,
and identify N_BINCL symbols which can be eliminated. */
-
stroff = 0;
/* The stabs sections can be split when
-split-by-reloc/-split-by-file is used. We must keep track of
const char *string;
if (*pstridx != 0)
- {
- /* This symbol has already been handled by an N_BINCL pass. */
- continue;
- }
+ /* This symbol has already been handled by an N_BINCL pass. */
+ continue;
type = sym[TYPEOFF];
/* Record this symbol, so that we can set the value
correctly. */
amt = sizeof *ne;
- ne = (struct stab_excl_list *) bfd_alloc (abfd, amt);
+ ne = bfd_alloc (abfd, amt);
if (ne == NULL)
goto error_return;
ne->offset = sym - stabbuf;
{
/* This is the first time we have seen this header file
with this set of stabs strings. */
- t = ((struct stab_link_includes_totals *)
- bfd_hash_allocate (&sinfo->includes, sizeof *t));
+ t = bfd_hash_allocate (&sinfo->includes, sizeof *t);
if (t == NULL)
goto error_return;
t->sum_chars = sum_chars;
bfd_size_type *pskips;
amt = count * sizeof (bfd_size_type);
- secinfo->cumulative_skips = (bfd_size_type *) bfd_alloc (abfd, amt);
+ secinfo->cumulative_skips = bfd_alloc (abfd, amt);
if (secinfo->cumulative_skips == NULL)
goto error_return;
*/
bfd_boolean
-_bfd_discard_section_stabs (abfd, stabsec, psecinfo,
- reloc_symbol_deleted_p, cookie)
- bfd *abfd;
- asection *stabsec;
- PTR psecinfo;
- bfd_boolean (*reloc_symbol_deleted_p) PARAMS ((bfd_vma, PTR));
- PTR cookie;
+_bfd_discard_section_stabs (bfd *abfd,
+ asection *stabsec,
+ void * psecinfo,
+ bfd_boolean (*reloc_symbol_deleted_p) (bfd_vma, void *),
+ void * cookie)
{
bfd_size_type count, amt;
struct stab_section_info *secinfo;
int deleting;
if (stabsec->size == 0)
- {
- /* This file does not contain stabs debugging information. */
- return FALSE;
- }
+ /* This file does not contain stabs debugging information. */
+ return FALSE;
if (stabsec->size % STABSIZE != 0)
- {
- /* Something is wrong with the format of these stab symbols.
- Don't try to optimize them. */
- return FALSE;
- }
+ /* Something is wrong with the format of these stab symbols.
+ Don't try to optimize them. */
+ return FALSE;
if ((stabsec->output_section != NULL
&& bfd_is_abs_section (stabsec->output_section)))
- {
- /* At least one of the sections is being discarded from the
- link, so we should just ignore them. */
- return FALSE;
- }
+ /* At least one of the sections is being discarded from the
+ link, so we should just ignore them. */
+ return FALSE;
/* We should have initialized our data in _bfd_link_stab_sections.
If there was some bizarre error reading the string sections, though,
secinfo = (struct stab_section_info *) psecinfo;
/* Read the stabs information from abfd. */
-
if (!bfd_malloc_and_get_section (abfd, stabsec, &stabbuf))
goto error_return;
/* Look through the stabs symbols and discard any information for
discarded functions. */
-
skip = 0;
deleting = -1;
int type;
if (*pstridx == (bfd_size_type) -1)
- {
- /* This stab was deleted in a previous pass. */
- continue;
- }
+ /* This stab was deleted in a previous pass. */
+ continue;
type = sym[TYPEOFF];
if (secinfo->cumulative_skips == NULL)
{
amt = count * sizeof (bfd_size_type);
- secinfo->cumulative_skips = (bfd_size_type *) bfd_alloc (abfd, amt);
+ secinfo->cumulative_skips = bfd_alloc (abfd, amt);
if (secinfo->cumulative_skips == NULL)
goto error_return;
}
contents. */
bfd_boolean
-_bfd_write_section_stabs (output_bfd, sinfo, stabsec, psecinfo, contents)
- bfd *output_bfd;
- struct stab_info *sinfo;
- asection *stabsec;
- PTR *psecinfo;
- bfd_byte *contents;
+_bfd_write_section_stabs (bfd *output_bfd,
+ struct stab_info *sinfo,
+ asection *stabsec,
+ void * *psecinfo,
+ bfd_byte *contents)
{
struct stab_section_info *secinfo;
struct stab_excl_list *e;
/* Write out the .stabstr section. */
bfd_boolean
-_bfd_write_stab_strings (output_bfd, sinfo)
- bfd *output_bfd;
- struct stab_info *sinfo;
+_bfd_write_stab_strings (bfd *output_bfd, struct stab_info *sinfo)
{
if (bfd_is_abs_section (sinfo->stabstr->output_section))
- {
- /* The section was discarded from the link. */
- return TRUE;
- }
+ /* The section was discarded from the link. */
+ return TRUE;
BFD_ASSERT ((sinfo->stabstr->output_offset
+ _bfd_stringtab_size (sinfo->strings))
or -1 if the address refers to a stab which has been removed. */
bfd_vma
-_bfd_stab_section_offset (stabsec, psecinfo, offset)
- asection *stabsec;
- PTR psecinfo;
- bfd_vma offset;
+_bfd_stab_section_offset (asection *stabsec,
+ void * psecinfo,
+ bfd_vma offset)
{
struct stab_section_info *secinfo;
/* BFD backend for SunOS binaries.
Copyright 1990, 1991, 1992, 1994, 1995, 1996, 1997, 1998, 1999, 2000,
- 2001, 2002, 2003, 2004 Free Software Foundation, Inc.
+ 2001, 2002, 2003, 2004, 2005 Free Software Foundation, Inc.
Written by Cygnus Support.
-This file is part of BFD, the Binary File Descriptor library.
+ This file is part of BFD, the Binary File Descriptor library.
-This program is free software; you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation; either version 2 of the License, or
-(at your option) any later version.
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-GNU General Public License for more details.
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
-You should have received a copy of the GNU General Public License
-along with this program; if not, write to the Free Software
-Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
#define TARGETNAME "a.out-sunos-big"
#include "bfdlink.h"
#include "libaout.h"
-/* Static routines defined in this file. */
-
-static bfd_boolean sunos_read_dynamic_info PARAMS ((bfd *));
-static long sunos_get_dynamic_symtab_upper_bound PARAMS ((bfd *));
-static bfd_boolean sunos_slurp_dynamic_symtab PARAMS ((bfd *));
-static long sunos_canonicalize_dynamic_symtab PARAMS ((bfd *, asymbol **));
-static long sunos_get_dynamic_reloc_upper_bound PARAMS ((bfd *));
-static long sunos_canonicalize_dynamic_reloc
- PARAMS ((bfd *, arelent **, asymbol **));
-static struct bfd_hash_entry *sunos_link_hash_newfunc
- PARAMS ((struct bfd_hash_entry *, struct bfd_hash_table *, const char *));
-static struct bfd_link_hash_table *sunos_link_hash_table_create
- PARAMS ((bfd *));
-static bfd_boolean sunos_create_dynamic_sections
- PARAMS ((bfd *, struct bfd_link_info *, bfd_boolean));
-static bfd_boolean sunos_add_dynamic_symbols
- PARAMS ((bfd *, struct bfd_link_info *, struct external_nlist **,
- bfd_size_type *, char **));
-static bfd_boolean sunos_add_one_symbol
- PARAMS ((struct bfd_link_info *, bfd *, const char *, flagword, asection *,
- bfd_vma, const char *, bfd_boolean, bfd_boolean,
- struct bfd_link_hash_entry **));
-static bfd_boolean sunos_scan_relocs
- PARAMS ((struct bfd_link_info *, bfd *, asection *, bfd_size_type));
-static bfd_boolean sunos_scan_std_relocs
- PARAMS ((struct bfd_link_info *, bfd *, asection *,
- const struct reloc_std_external *, bfd_size_type));
-static bfd_boolean sunos_scan_ext_relocs
- PARAMS ((struct bfd_link_info *, bfd *, asection *,
- const struct reloc_ext_external *, bfd_size_type));
-static bfd_boolean sunos_link_dynamic_object
- PARAMS ((struct bfd_link_info *, bfd *));
-static bfd_boolean sunos_write_dynamic_symbol
- PARAMS ((bfd *, struct bfd_link_info *, struct aout_link_hash_entry *));
-static bfd_boolean sunos_check_dynamic_reloc
- PARAMS ((struct bfd_link_info *, bfd *, asection *,
- struct aout_link_hash_entry *, PTR, bfd_byte *, bfd_boolean *,
- bfd_vma *));
-static bfd_boolean sunos_finish_dynamic_link
- PARAMS ((bfd *, struct bfd_link_info *));
-
-#define MY_get_dynamic_symtab_upper_bound sunos_get_dynamic_symtab_upper_bound
-#define MY_canonicalize_dynamic_symtab sunos_canonicalize_dynamic_symtab
-#define MY_get_synthetic_symtab _bfd_nodynamic_get_synthetic_symtab
-#define MY_get_dynamic_reloc_upper_bound sunos_get_dynamic_reloc_upper_bound
-#define MY_canonicalize_dynamic_reloc sunos_canonicalize_dynamic_reloc
-#define MY_bfd_link_hash_table_create sunos_link_hash_table_create
-#define MY_add_dynamic_symbols sunos_add_dynamic_symbols
-#define MY_add_one_symbol sunos_add_one_symbol
-#define MY_link_dynamic_object sunos_link_dynamic_object
-#define MY_write_dynamic_symbol sunos_write_dynamic_symbol
-#define MY_check_dynamic_reloc sunos_check_dynamic_reloc
-#define MY_finish_dynamic_link sunos_finish_dynamic_link
-
/* ??? Where should this go? */
#define MACHTYPE_OK(mtype) \
(((mtype) == M_SPARC && bfd_lookup_arch (bfd_arch_sparc, 0) != NULL) \
|| (((mtype) == M_UNKNOWN || (mtype) == M_68010 || (mtype) == M_68020) \
&& bfd_lookup_arch (bfd_arch_m68k, 0) != NULL))
+#define MY_get_dynamic_symtab_upper_bound sunos_get_dynamic_symtab_upper_bound
+#define MY_canonicalize_dynamic_symtab sunos_canonicalize_dynamic_symtab
+#define MY_get_synthetic_symtab _bfd_nodynamic_get_synthetic_symtab
+#define MY_get_dynamic_reloc_upper_bound sunos_get_dynamic_reloc_upper_bound
+#define MY_canonicalize_dynamic_reloc sunos_canonicalize_dynamic_reloc
+#define MY_bfd_link_hash_table_create sunos_link_hash_table_create
+#define MY_add_dynamic_symbols sunos_add_dynamic_symbols
+#define MY_add_one_symbol sunos_add_one_symbol
+#define MY_link_dynamic_object sunos_link_dynamic_object
+#define MY_write_dynamic_symbol sunos_write_dynamic_symbol
+#define MY_check_dynamic_reloc sunos_check_dynamic_reloc
+#define MY_finish_dynamic_link sunos_finish_dynamic_link
+
+static bfd_boolean sunos_add_dynamic_symbols (bfd *, struct bfd_link_info *, struct external_nlist **, bfd_size_type *, char **);
+static bfd_boolean sunos_add_one_symbol (struct bfd_link_info *, bfd *, const char *, flagword, asection *, bfd_vma, const char *, bfd_boolean, bfd_boolean, struct bfd_link_hash_entry **);
+static bfd_boolean sunos_link_dynamic_object (struct bfd_link_info *, bfd *);
+static bfd_boolean sunos_write_dynamic_symbol (bfd *, struct bfd_link_info *, struct aout_link_hash_entry *);
+static bfd_boolean sunos_check_dynamic_reloc (struct bfd_link_info *, bfd *, asection *, struct aout_link_hash_entry *, void *, bfd_byte *, bfd_boolean *, bfd_vma *);
+static bfd_boolean sunos_finish_dynamic_link (bfd *, struct bfd_link_info *);
+static struct bfd_link_hash_table *sunos_link_hash_table_create (bfd *);
+static long sunos_get_dynamic_symtab_upper_bound (bfd *);
+static long sunos_canonicalize_dynamic_symtab (bfd *, asymbol **);
+static long sunos_get_dynamic_reloc_upper_bound (bfd *);
+static long sunos_canonicalize_dynamic_reloc (bfd *, arelent **, asymbol **);
+
/* Include the usual a.out support. */
#include "aoutf1.h"
unsigned long dynrel_count;
/* Read in dynamic relocs. This may be reloc_std_external or
reloc_ext_external. */
- PTR dynrel;
+ void * dynrel;
/* arelent structures for dynamic relocs. */
arelent *canonical_dynrel;
};
structure to FALSE to avoid doing this work again. */
static bfd_boolean
-sunos_read_dynamic_info (abfd)
- bfd *abfd;
+sunos_read_dynamic_info (bfd *abfd)
{
struct sunos_dynamic_info *info;
asection *dynsec;
struct external_sun4_dynamic_link linkinfo;
bfd_size_type amt;
- if (obj_aout_dynamic_info (abfd) != (PTR) NULL)
+ if (obj_aout_dynamic_info (abfd) != NULL)
return TRUE;
if ((abfd->flags & DYNAMIC) == 0)
}
amt = sizeof (struct sunos_dynamic_info);
- info = (struct sunos_dynamic_info *) bfd_zalloc (abfd, amt);
+ info = bfd_zalloc (abfd, amt);
if (!info)
return FALSE;
info->valid = FALSE;
info->canonical_dynsym = NULL;
info->dynrel = NULL;
info->canonical_dynrel = NULL;
- obj_aout_dynamic_info (abfd) = (PTR) info;
+ obj_aout_dynamic_info (abfd) = (void *) info;
/* This code used to look for the __DYNAMIC symbol to locate the dynamic
linking information.
symbols for the __DYNAMIC symbol. */
if ((abfd->flags & DYNAMIC) == 0)
return TRUE;
- if (! bfd_get_section_contents (abfd, obj_datasec (abfd), (PTR) &dyninfo,
+ if (! bfd_get_section_contents (abfd, obj_datasec (abfd), (void *) &dyninfo,
(file_ptr) 0,
(bfd_size_type) sizeof dyninfo))
return TRUE;
/* This executable appears to be dynamically linked in a way that we
can understand. */
- if (! bfd_get_section_contents (abfd, dynsec, (PTR) &linkinfo,
+ if (! bfd_get_section_contents (abfd, dynsec, (void *) &linkinfo,
(file_ptr) dynoff,
(bfd_size_type) sizeof linkinfo))
return TRUE;
/* Return the amount of memory required for the dynamic symbols. */
static long
-sunos_get_dynamic_symtab_upper_bound (abfd)
- bfd *abfd;
+sunos_get_dynamic_symtab_upper_bound (bfd *abfd)
{
struct sunos_dynamic_info *info;
/* Read the external dynamic symbols. */
static bfd_boolean
-sunos_slurp_dynamic_symtab (abfd)
- bfd *abfd;
+sunos_slurp_dynamic_symtab (bfd *abfd)
{
struct sunos_dynamic_info *info;
bfd_size_type amt;
}
/* Get the dynamic nlist structures. */
- if (info->dynsym == (struct external_nlist *) NULL)
+ if (info->dynsym == NULL)
{
amt = (bfd_size_type) info->dynsym_count * EXTERNAL_NLIST_SIZE;
- info->dynsym = (struct external_nlist *) bfd_alloc (abfd, amt);
+ info->dynsym = bfd_alloc (abfd, amt);
if (info->dynsym == NULL && info->dynsym_count != 0)
return FALSE;
if (bfd_seek (abfd, (file_ptr) info->dyninfo.ld_stab, SEEK_SET) != 0
- || bfd_bread ((PTR) info->dynsym, amt, abfd) != amt)
+ || bfd_bread ((void *) info->dynsym, amt, abfd) != amt)
{
if (info->dynsym != NULL)
{
}
/* Get the dynamic strings. */
- if (info->dynstr == (char *) NULL)
+ if (info->dynstr == NULL)
{
amt = info->dyninfo.ld_symb_size;
- info->dynstr = (char *) bfd_alloc (abfd, amt);
+ info->dynstr = bfd_alloc (abfd, amt);
if (info->dynstr == NULL && info->dyninfo.ld_symb_size != 0)
return FALSE;
if (bfd_seek (abfd, (file_ptr) info->dyninfo.ld_symbols, SEEK_SET) != 0
- || bfd_bread ((PTR) info->dynstr, amt, abfd) != amt)
+ || bfd_bread ((void *) info->dynstr, amt, abfd) != amt)
{
if (info->dynstr != NULL)
{
/* Read in the dynamic symbols. */
static long
-sunos_canonicalize_dynamic_symtab (abfd, storage)
- bfd *abfd;
- asymbol **storage;
+sunos_canonicalize_dynamic_symtab (bfd *abfd, asymbol **storage)
{
struct sunos_dynamic_info *info;
unsigned long i;
if (info->dyninfo.ld_buckets > info->dynsym_count)
abort ();
table_size = info->dyninfo.ld_stab - info->dyninfo.ld_hash;
- table = (bfd_byte *) bfd_malloc (table_size);
+ table = bfd_malloc (table_size);
if (table == NULL && table_size != 0)
abort ();
if (bfd_seek (abfd, (file_ptr) info->dyninfo.ld_hash, SEEK_SET) != 0
- || bfd_bread ((PTR) table, table_size, abfd) != table_size)
+ || bfd_bread ((void *) table, table_size, abfd) != table_size)
abort ();
for (i = 0; i < info->dynsym_count; i++)
{
/* Get the asymbol structures corresponding to the dynamic nlist
structures. */
- if (info->canonical_dynsym == (aout_symbol_type *) NULL)
+ if (info->canonical_dynsym == NULL)
{
bfd_size_type size;
bfd_size_type strsize = info->dyninfo.ld_symb_size;
size = (bfd_size_type) info->dynsym_count * sizeof (aout_symbol_type);
- info->canonical_dynsym = (aout_symbol_type *) bfd_alloc (abfd, size);
+ info->canonical_dynsym = bfd_alloc (abfd, size);
if (info->canonical_dynsym == NULL && info->dynsym_count != 0)
return -1;
/* Return the amount of memory required for the dynamic relocs. */
static long
-sunos_get_dynamic_reloc_upper_bound (abfd)
- bfd *abfd;
+sunos_get_dynamic_reloc_upper_bound (bfd *abfd)
{
struct sunos_dynamic_info *info;
/* Read in the dynamic relocs. */
static long
-sunos_canonicalize_dynamic_reloc (abfd, storage, syms)
- bfd *abfd;
- arelent **storage;
- asymbol **syms;
+sunos_canonicalize_dynamic_reloc (bfd *abfd, arelent **storage, asymbol **syms)
{
struct sunos_dynamic_info *info;
unsigned long i;
bfd_size_type size;
/* Get the general dynamic information. */
- if (obj_aout_dynamic_info (abfd) == (PTR) NULL)
+ if (obj_aout_dynamic_info (abfd) == NULL)
{
if (! sunos_read_dynamic_info (abfd))
return -1;
if (info->dynrel == NULL)
{
size = (bfd_size_type) info->dynrel_count * obj_reloc_entry_size (abfd);
- info->dynrel = (PTR) bfd_alloc (abfd, size);
+ info->dynrel = bfd_alloc (abfd, size);
if (info->dynrel == NULL && size != 0)
return -1;
if (bfd_seek (abfd, (file_ptr) info->dyninfo.ld_rel, SEEK_SET) != 0
- || bfd_bread ((PTR) info->dynrel, size, abfd) != size)
+ || bfd_bread ((void *) info->dynrel, size, abfd) != size)
{
if (info->dynrel != NULL)
{
/* Get the arelent structures corresponding to the dynamic reloc
information. */
- if (info->canonical_dynrel == (arelent *) NULL)
+ if (info->canonical_dynrel == NULL)
{
arelent *to;
size = (bfd_size_type) info->dynrel_count * sizeof (arelent);
- info->canonical_dynrel = (arelent *) bfd_alloc (abfd, size);
+ info->canonical_dynrel = bfd_alloc (abfd, size);
if (info->canonical_dynrel == NULL && info->dynrel_count != 0)
return -1;
if (obj_reloc_entry_size (abfd) == RELOC_EXT_SIZE)
{
- register struct reloc_ext_external *p;
+ struct reloc_ext_external *p;
struct reloc_ext_external *pend;
p = (struct reloc_ext_external *) info->dynrel;
pend = p + info->dynrel_count;
for (; p < pend; p++, to++)
- NAME(aout,swap_ext_reloc_in) (abfd, p, to, syms,
- (bfd_size_type) info->dynsym_count);
+ NAME (aout, swap_ext_reloc_in) (abfd, p, to, syms,
+ (bfd_size_type) info->dynsym_count);
}
else
{
- register struct reloc_std_external *p;
+ struct reloc_std_external *p;
struct reloc_std_external *pend;
p = (struct reloc_std_external *) info->dynrel;
pend = p + info->dynrel_count;
for (; p < pend; p++, to++)
- NAME(aout,swap_std_reloc_in) (abfd, p, to, syms,
- (bfd_size_type) info->dynsym_count);
+ NAME (aout, swap_std_reloc_in) (abfd, p, to, syms,
+ (bfd_size_type) info->dynsym_count);
}
}
/* Routine to create an entry in an SunOS link hash table. */
static struct bfd_hash_entry *
-sunos_link_hash_newfunc (entry, table, string)
- struct bfd_hash_entry *entry;
- struct bfd_hash_table *table;
- const char *string;
+sunos_link_hash_newfunc (struct bfd_hash_entry *entry,
+ struct bfd_hash_table *table,
+ const char *string)
{
struct sunos_link_hash_entry *ret = (struct sunos_link_hash_entry *) entry;
/* Allocate the structure if it has not already been allocated by a
subclass. */
- if (ret == (struct sunos_link_hash_entry *) NULL)
- ret = ((struct sunos_link_hash_entry *)
- bfd_hash_allocate (table, sizeof (struct sunos_link_hash_entry)));
- if (ret == (struct sunos_link_hash_entry *) NULL)
- return (struct bfd_hash_entry *) ret;
+ if (ret == NULL)
+ ret = bfd_hash_allocate (table, sizeof (* ret));
+ if (ret == NULL)
+ return NULL;
/* Call the allocation method of the superclass. */
ret = ((struct sunos_link_hash_entry *)
- NAME(aout,link_hash_newfunc) ((struct bfd_hash_entry *) ret,
- table, string));
+ NAME (aout, link_hash_newfunc) ((struct bfd_hash_entry *) ret,
+ table, string));
if (ret != NULL)
{
/* Set local fields. */
/* Create a SunOS link hash table. */
static struct bfd_link_hash_table *
-sunos_link_hash_table_create (abfd)
- bfd *abfd;
+sunos_link_hash_table_create (bfd *abfd)
{
struct sunos_link_hash_table *ret;
bfd_size_type amt = sizeof (struct sunos_link_hash_table);
- ret = (struct sunos_link_hash_table *) bfd_malloc (amt);
- if (ret == (struct sunos_link_hash_table *) NULL)
- return (struct bfd_link_hash_table *) NULL;
- if (! NAME(aout,link_hash_table_init) (&ret->root, abfd,
- sunos_link_hash_newfunc))
+ ret = bfd_malloc (amt);
+ if (ret == NULL)
+ return NULL;
+ if (! NAME (aout, link_hash_table_init) (&ret->root, abfd,
+ sunos_link_hash_newfunc))
{
free (ret);
- return (struct bfd_link_hash_table *) NULL;
+ return NULL;
}
ret->dynobj = NULL;
#define sunos_link_hash_traverse(table, func, info) \
(aout_link_hash_traverse \
(&(table)->root, \
- (bfd_boolean (*) PARAMS ((struct aout_link_hash_entry *, PTR))) (func), \
+ (bfd_boolean (*) (struct aout_link_hash_entry *, void *)) (func), \
(info)))
/* Get the SunOS link hash table from the info structure. This is
#define sunos_hash_table(p) ((struct sunos_link_hash_table *) ((p)->hash))
-static bfd_boolean sunos_scan_dynamic_symbol
- PARAMS ((struct sunos_link_hash_entry *, PTR));
-
/* Create the dynamic sections needed if we are linking against a
dynamic object, or if we are linking PIC compiled code. ABFD is a
bfd we can attach the dynamic sections to. The linker script will
of the dynamic linking information. */
static bfd_boolean
-sunos_create_dynamic_sections (abfd, info, needed)
- bfd *abfd;
- struct bfd_link_info *info;
- bfd_boolean needed;
+sunos_create_dynamic_sections (bfd *abfd,
+ struct bfd_link_info *info,
+ bfd_boolean needed)
{
asection *s;
backend linker for each object it encounters. */
static bfd_boolean
-sunos_add_dynamic_symbols (abfd, info, symsp, sym_countp, stringsp)
- bfd *abfd;
- struct bfd_link_info *info;
- struct external_nlist **symsp;
- bfd_size_type *sym_countp;
- char **stringsp;
+sunos_add_dynamic_symbols (bfd *abfd,
+ struct bfd_link_info *info,
+ struct external_nlist **symsp,
+ bfd_size_type *sym_countp,
+ char **stringsp)
{
bfd *dynobj;
struct sunos_dynamic_info *dinfo;
/* For the format of an ld_need entry, see aout/sun4.h. We
should probably define structs for this manipulation. */
-
name = bfd_get_32 (abfd, buf);
flags = bfd_get_32 (abfd, buf + 4);
major_vno = (unsigned short) bfd_get_16 (abfd, buf + 8);
need = bfd_get_32 (abfd, buf + 12);
alc = sizeof (struct bfd_link_needed_list);
- needed = (struct bfd_link_needed_list *) bfd_alloc (abfd, alc);
+ needed = bfd_alloc (abfd, alc);
if (needed == NULL)
return FALSE;
needed->by = abfd;
/* We return the name as [-l]name[.maj][.min]. */
alc = 30;
- namebuf = (char *) bfd_malloc (alc + 1);
+ namebuf = bfd_malloc (alc + 1);
if (namebuf == NULL)
return FALSE;
p = namebuf;
char *n;
alc *= 2;
- n = (char *) bfd_realloc (namebuf, alc + 1);
+ n = bfd_realloc (namebuf, alc + 1);
if (n == NULL)
{
free (namebuf);
char *n;
alc = (p - namebuf) + strlen (majbuf) + strlen (minbuf);
- n = (char *) bfd_realloc (namebuf, alc + 1);
+ n = bfd_realloc (namebuf, alc + 1);
if (n == NULL)
{
free (namebuf);
tweaking needed for dynamic linking support. */
static bfd_boolean
-sunos_add_one_symbol (info, abfd, name, flags, section, value, string,
- copy, collect, hashp)
- struct bfd_link_info *info;
- bfd *abfd;
- const char *name;
- flagword flags;
- asection *section;
- bfd_vma value;
- const char *string;
- bfd_boolean copy;
- bfd_boolean collect;
- struct bfd_link_hash_entry **hashp;
+sunos_add_one_symbol (struct bfd_link_info *info,
+ bfd *abfd,
+ const char *name,
+ flagword flags,
+ asection *section,
+ bfd_vma value,
+ const char *string,
+ bfd_boolean copy,
+ bfd_boolean collect,
+ struct bfd_link_hash_entry **hashp)
{
struct sunos_link_hash_entry *h;
int new_flag;
if ((abfd->flags & DYNAMIC) != 0
&& abfd->xvec == info->hash->creator
&& (h->flags & SUNOS_CONSTRUCTOR) != 0)
- {
- /* The existing symbol is a constructor symbol, and this symbol
- is from a dynamic object. A constructor symbol is actually a
- definition, although the type will be bfd_link_hash_undefined
- at this point. We want to ignore the definition from the
- dynamic object. */
- section = bfd_und_section_ptr;
- }
+ /* The existing symbol is a constructor symbol, and this symbol
+ is from a dynamic object. A constructor symbol is actually a
+ definition, although the type will be bfd_link_hash_undefined
+ at this point. We want to ignore the definition from the
+ dynamic object. */
+ section = bfd_und_section_ptr;
else if ((flags & BSF_CONSTRUCTOR) != 0
&& (abfd->flags & DYNAMIC) == 0
&& h->root.root.type == bfd_link_hash_defined
&& h->root.root.u.def.section->owner != NULL
&& (h->root.root.u.def.section->owner->flags & DYNAMIC) != 0)
- {
- /* The existing symbol is defined by a dynamic object, and this
- is a constructor symbol. As above, we want to force the use
- of the constructor symbol from the regular object. */
- h->root.root.type = bfd_link_hash_new;
- }
+ /* The existing symbol is defined by a dynamic object, and this
+ is a constructor symbol. As above, we want to force the use
+ of the constructor symbol from the regular object. */
+ h->root.root.type = bfd_link_hash_new;
/* Do the usual procedure for adding a symbol. */
if (! _bfd_generic_link_add_one_symbol (info, abfd, name, flags, section,
return TRUE;
}
+extern const bfd_target MY (vec);
+
/* Return the list of objects needed by BFD. */
struct bfd_link_needed_list *
-bfd_sunos_get_needed_list (abfd, info)
- bfd *abfd ATTRIBUTE_UNUSED;
- struct bfd_link_info *info;
+bfd_sunos_get_needed_list (bfd *abfd ATTRIBUTE_UNUSED,
+ struct bfd_link_info *info)
{
- if (info->hash->creator != &MY(vec))
+ if (info->hash->creator != &MY (vec))
return NULL;
return sunos_hash_table (info)->needed;
}
this in case some dynamic object refers to this symbol. */
bfd_boolean
-bfd_sunos_record_link_assignment (output_bfd, info, name)
- bfd *output_bfd;
- struct bfd_link_info *info;
- const char *name;
+bfd_sunos_record_link_assignment (bfd *output_bfd,
+ struct bfd_link_info *info,
+ const char *name)
{
struct sunos_link_hash_entry *h;
return TRUE;
}
-/* Set up the sizes and contents of the dynamic sections created in
- sunos_add_dynamic_symbols. This is called by the SunOS linker
- emulation before_allocation routine. We must set the sizes of the
- sections before the linker sets the addresses of the various
- sections. This unfortunately requires reading all the relocs so
- that we can work out which ones need to become dynamic relocs. If
- info->keep_memory is TRUE, we keep the relocs in memory; otherwise,
- we discard them, and will read them again later. */
+/* Scan the relocs for an input section using standard relocs. We
+ need to figure out what to do for each reloc against a dynamic
+ symbol. If the symbol is in the .text section, an entry is made in
+ the procedure linkage table. Note that this will do the wrong
+ thing if the symbol is actually data; I don't think the Sun 3
+ native linker handles this case correctly either. If the symbol is
+ not in the .text section, we must preserve the reloc as a dynamic
+ reloc. FIXME: We should also handle the PIC relocs here by
+ building global offset table entries. */
-bfd_boolean
-bfd_sunos_size_dynamic_sections (output_bfd, info, sdynptr, sneedptr,
- srulesptr)
- bfd *output_bfd;
- struct bfd_link_info *info;
- asection **sdynptr;
- asection **sneedptr;
- asection **srulesptr;
+static bfd_boolean
+sunos_scan_std_relocs (struct bfd_link_info *info,
+ bfd *abfd,
+ asection *sec ATTRIBUTE_UNUSED,
+ const struct reloc_std_external *relocs,
+ bfd_size_type rel_size)
{
bfd *dynobj;
- bfd_size_type dynsymcount;
- struct sunos_link_hash_entry *h;
- asection *s;
- size_t bucketcount;
- bfd_size_type hashalloc;
- size_t i;
- bfd *sub;
-
- *sdynptr = NULL;
- *sneedptr = NULL;
- *srulesptr = NULL;
-
- if (info->relocatable)
- return TRUE;
-
- if (output_bfd->xvec != &MY(vec))
- return TRUE;
+ asection *splt = NULL;
+ asection *srel = NULL;
+ struct sunos_link_hash_entry **sym_hashes;
+ const struct reloc_std_external *rel, *relend;
- /* Look through all the input BFD's and read their relocs. It would
- be better if we didn't have to do this, but there is no other way
- to determine the number of dynamic relocs we need, and, more
- importantly, there is no other way to know which symbols should
- get an entry in the procedure linkage table. */
- for (sub = info->input_bfds; sub != NULL; sub = sub->link_next)
+ /* We only know how to handle m68k plt entries. */
+ if (bfd_get_arch (abfd) != bfd_arch_m68k)
{
- if ((sub->flags & DYNAMIC) == 0
- && sub->xvec == output_bfd->xvec)
- {
- if (! sunos_scan_relocs (info, sub, obj_textsec (sub),
- exec_hdr (sub)->a_trsize)
- || ! sunos_scan_relocs (info, sub, obj_datasec (sub),
- exec_hdr (sub)->a_drsize))
- return FALSE;
- }
+ bfd_set_error (bfd_error_invalid_target);
+ return FALSE;
}
- dynobj = sunos_hash_table (info)->dynobj;
- dynsymcount = sunos_hash_table (info)->dynsymcount;
+ dynobj = NULL;
- /* If there were no dynamic objects in the link, and we don't need
- to build a global offset table, there is nothing to do here. */
- if (! sunos_hash_table (info)->dynamic_sections_needed
- && ! sunos_hash_table (info)->got_needed)
- return TRUE;
+ sym_hashes = (struct sunos_link_hash_entry **) obj_aout_sym_hashes (abfd);
- /* If __GLOBAL_OFFSET_TABLE_ was mentioned, define it. */
- h = sunos_link_hash_lookup (sunos_hash_table (info),
- "__GLOBAL_OFFSET_TABLE_", FALSE, FALSE, FALSE);
- if (h != NULL && (h->flags & SUNOS_REF_REGULAR) != 0)
+ relend = relocs + rel_size / RELOC_STD_SIZE;
+ for (rel = relocs; rel < relend; rel++)
{
- h->flags |= SUNOS_DEF_REGULAR;
- if (h->dynindx == -1)
+ int r_index;
+ struct sunos_link_hash_entry *h;
+
+ /* We only want relocs against external symbols. */
+ if (bfd_header_big_endian (abfd))
{
- ++sunos_hash_table (info)->dynsymcount;
- h->dynindx = -2;
+ if ((rel->r_type[0] & RELOC_STD_BITS_EXTERN_BIG) == 0)
+ continue;
}
- h->root.root.type = bfd_link_hash_defined;
- h->root.root.u.def.section = bfd_get_section_by_name (dynobj, ".got");
-
- /* If the .got section is more than 0x1000 bytes, we set
- __GLOBAL_OFFSET_TABLE_ to be 0x1000 bytes into the section,
- so that 13 bit relocations have a greater chance of working. */
- s = bfd_get_section_by_name (dynobj, ".got");
- BFD_ASSERT (s != NULL);
- if (s->size >= 0x1000)
- h->root.root.u.def.value = 0x1000;
else
- h->root.root.u.def.value = 0;
-
- sunos_hash_table (info)->got_base = h->root.root.u.def.value;
- }
-
- /* If there are any shared objects in the link, then we need to set
- up the dynamic linking information. */
- if (sunos_hash_table (info)->dynamic_sections_needed)
- {
- *sdynptr = bfd_get_section_by_name (dynobj, ".dynamic");
-
- /* The .dynamic section is always the same size. */
- s = *sdynptr;
- BFD_ASSERT (s != NULL);
- s->size = (sizeof (struct external_sun4_dynamic)
- + EXTERNAL_SUN4_DYNAMIC_DEBUGGER_SIZE
- + sizeof (struct external_sun4_dynamic_link));
-
- /* Set the size of the .dynsym and .hash sections. We counted
- the number of dynamic symbols as we read the input files. We
- will build the dynamic symbol table (.dynsym) and the hash
- table (.hash) when we build the final symbol table, because
- until then we do not know the correct value to give the
- symbols. We build the dynamic symbol string table (.dynstr)
- in a traversal of the symbol table using
- sunos_scan_dynamic_symbol. */
- s = bfd_get_section_by_name (dynobj, ".dynsym");
- BFD_ASSERT (s != NULL);
- s->size = dynsymcount * sizeof (struct external_nlist);
- s->contents = (bfd_byte *) bfd_alloc (output_bfd, s->size);
- if (s->contents == NULL && s->size != 0)
- return FALSE;
+ {
+ if ((rel->r_type[0] & RELOC_STD_BITS_EXTERN_LITTLE) == 0)
+ continue;
+ }
- /* The number of buckets is just the number of symbols divided
- by four. To compute the final size of the hash table, we
- must actually compute the hash table. Normally we need
- exactly as many entries in the hash table as there are
- dynamic symbols, but if some of the buckets are not used we
- will need additional entries. In the worst case, every
- symbol will hash to the same bucket, and we will need
- BUCKETCOUNT - 1 extra entries. */
- if (dynsymcount >= 4)
- bucketcount = dynsymcount / 4;
- else if (dynsymcount > 0)
- bucketcount = dynsymcount;
+ /* Get the symbol index. */
+ if (bfd_header_big_endian (abfd))
+ r_index = ((rel->r_index[0] << 16)
+ | (rel->r_index[1] << 8)
+ | rel->r_index[2]);
else
- bucketcount = 1;
- s = bfd_get_section_by_name (dynobj, ".hash");
- BFD_ASSERT (s != NULL);
- hashalloc = (dynsymcount + bucketcount - 1) * HASH_ENTRY_SIZE;
- s->contents = (bfd_byte *) bfd_zalloc (dynobj, hashalloc);
- if (s->contents == NULL && dynsymcount > 0)
- return FALSE;
- for (i = 0; i < bucketcount; i++)
- PUT_WORD (output_bfd, (bfd_vma) -1, s->contents + i * HASH_ENTRY_SIZE);
- s->size = bucketcount * HASH_ENTRY_SIZE;
+ r_index = ((rel->r_index[2] << 16)
+ | (rel->r_index[1] << 8)
+ | rel->r_index[0]);
- sunos_hash_table (info)->bucketcount = bucketcount;
+ /* Get the hash table entry. */
+ h = sym_hashes[r_index];
+ if (h == NULL)
+ /* This should not normally happen, but it will in any case
+ be caught in the relocation phase. */
+ continue;
- /* Scan all the symbols, place them in the dynamic symbol table,
- and build the dynamic hash table. We reuse dynsymcount as a
- counter for the number of symbols we have added so far. */
- sunos_hash_table (info)->dynsymcount = 0;
- sunos_link_hash_traverse (sunos_hash_table (info),
- sunos_scan_dynamic_symbol,
- (PTR) info);
- BFD_ASSERT (sunos_hash_table (info)->dynsymcount == dynsymcount);
+ /* At this point common symbols have already been allocated, so
+ we don't have to worry about them. We need to consider that
+ we may have already seen this symbol and marked it undefined;
+ if the symbol is really undefined, then SUNOS_DEF_DYNAMIC
+ will be zero. */
+ if (h->root.root.type != bfd_link_hash_defined
+ && h->root.root.type != bfd_link_hash_defweak
+ && h->root.root.type != bfd_link_hash_undefined)
+ continue;
- /* The SunOS native linker seems to align the total size of the
- symbol strings to a multiple of 8. I don't know if this is
- important, but it can't hurt much. */
- s = bfd_get_section_by_name (dynobj, ".dynstr");
- BFD_ASSERT (s != NULL);
- if ((s->size & 7) != 0)
+ if ((h->flags & SUNOS_DEF_DYNAMIC) == 0
+ || (h->flags & SUNOS_DEF_REGULAR) != 0)
+ continue;
+
+ if (dynobj == NULL)
{
- bfd_size_type add;
- bfd_byte *contents;
+ asection *sgot;
- add = 8 - (s->size & 7);
- contents = (bfd_byte *) bfd_realloc (s->contents,
- s->size + add);
- if (contents == NULL)
+ if (! sunos_create_dynamic_sections (abfd, info, FALSE))
return FALSE;
- memset (contents + s->size, 0, (size_t) add);
- s->contents = contents;
- s->size += add;
+ dynobj = sunos_hash_table (info)->dynobj;
+ splt = bfd_get_section_by_name (dynobj, ".plt");
+ srel = bfd_get_section_by_name (dynobj, ".dynrel");
+ BFD_ASSERT (splt != NULL && srel != NULL);
+
+ sgot = bfd_get_section_by_name (dynobj, ".got");
+ BFD_ASSERT (sgot != NULL);
+ if (sgot->size == 0)
+ sgot->size = BYTES_IN_WORD;
+ sunos_hash_table (info)->got_needed = TRUE;
}
- }
- /* Now that we have worked out the sizes of the procedure linkage
- table and the dynamic relocs, allocate storage for them. */
- s = bfd_get_section_by_name (dynobj, ".plt");
- BFD_ASSERT (s != NULL);
- if (s->size != 0)
- {
- s->contents = (bfd_byte *) bfd_alloc (dynobj, s->size);
- if (s->contents == NULL)
- return FALSE;
+ BFD_ASSERT ((h->flags & SUNOS_REF_REGULAR) != 0);
+ BFD_ASSERT (h->plt_offset != 0
+ || ((h->root.root.type == bfd_link_hash_defined
+ || h->root.root.type == bfd_link_hash_defweak)
+ ? (h->root.root.u.def.section->owner->flags
+ & DYNAMIC) != 0
+ : (h->root.root.u.undef.abfd->flags & DYNAMIC) != 0));
- /* Fill in the first entry in the table. */
- switch (bfd_get_arch (dynobj))
+ /* This reloc is against a symbol defined only by a dynamic
+ object. */
+ if (h->root.root.type == bfd_link_hash_undefined)
+ /* Presumably this symbol was marked as being undefined by
+ an earlier reloc. */
+ srel->size += RELOC_STD_SIZE;
+ else if ((h->root.root.u.def.section->flags & SEC_CODE) == 0)
{
- case bfd_arch_sparc:
- memcpy (s->contents, sparc_plt_first_entry, SPARC_PLT_ENTRY_SIZE);
- break;
-
- case bfd_arch_m68k:
- memcpy (s->contents, m68k_plt_first_entry, M68K_PLT_ENTRY_SIZE);
- break;
-
- default:
- abort ();
- }
- }
-
- s = bfd_get_section_by_name (dynobj, ".dynrel");
- if (s->size != 0)
- {
- s->contents = (bfd_byte *) bfd_alloc (dynobj, s->size);
- if (s->contents == NULL)
- return FALSE;
- }
- /* We use the reloc_count field to keep track of how many of the
- relocs we have output so far. */
- s->reloc_count = 0;
-
- /* Make space for the global offset table. */
- s = bfd_get_section_by_name (dynobj, ".got");
- s->contents = (bfd_byte *) bfd_alloc (dynobj, s->size);
- if (s->contents == NULL)
- return FALSE;
-
- *sneedptr = bfd_get_section_by_name (dynobj, ".need");
- *srulesptr = bfd_get_section_by_name (dynobj, ".rules");
-
- return TRUE;
-}
-
-/* Scan the relocs for an input section. */
-
-static bfd_boolean
-sunos_scan_relocs (info, abfd, sec, rel_size)
- struct bfd_link_info *info;
- bfd *abfd;
- asection *sec;
- bfd_size_type rel_size;
-{
- PTR relocs;
- PTR free_relocs = NULL;
-
- if (rel_size == 0)
- return TRUE;
-
- if (! info->keep_memory)
- relocs = free_relocs = bfd_malloc (rel_size);
- else
- {
- struct aout_section_data_struct *n;
- bfd_size_type amt = sizeof (struct aout_section_data_struct);
-
- n = (struct aout_section_data_struct *) bfd_alloc (abfd, amt);
- if (n == NULL)
- relocs = NULL;
- else
- {
- set_aout_section_data (sec, n);
- relocs = bfd_malloc (rel_size);
- aout_section_data (sec)->relocs = relocs;
- }
- }
- if (relocs == NULL)
- return FALSE;
-
- if (bfd_seek (abfd, sec->rel_filepos, SEEK_SET) != 0
- || bfd_bread (relocs, rel_size, abfd) != rel_size)
- goto error_return;
-
- if (obj_reloc_entry_size (abfd) == RELOC_STD_SIZE)
- {
- if (! sunos_scan_std_relocs (info, abfd, sec,
- (struct reloc_std_external *) relocs,
- rel_size))
- goto error_return;
- }
- else
- {
- if (! sunos_scan_ext_relocs (info, abfd, sec,
- (struct reloc_ext_external *) relocs,
- rel_size))
- goto error_return;
- }
-
- if (free_relocs != NULL)
- free (free_relocs);
-
- return TRUE;
-
- error_return:
- if (free_relocs != NULL)
- free (free_relocs);
- return FALSE;
-}
-
-/* Scan the relocs for an input section using standard relocs. We
- need to figure out what to do for each reloc against a dynamic
- symbol. If the symbol is in the .text section, an entry is made in
- the procedure linkage table. Note that this will do the wrong
- thing if the symbol is actually data; I don't think the Sun 3
- native linker handles this case correctly either. If the symbol is
- not in the .text section, we must preserve the reloc as a dynamic
- reloc. FIXME: We should also handle the PIC relocs here by
- building global offset table entries. */
-
-static bfd_boolean
-sunos_scan_std_relocs (info, abfd, sec, relocs, rel_size)
- struct bfd_link_info *info;
- bfd *abfd;
- asection *sec ATTRIBUTE_UNUSED;
- const struct reloc_std_external *relocs;
- bfd_size_type rel_size;
-{
- bfd *dynobj;
- asection *splt = NULL;
- asection *srel = NULL;
- struct sunos_link_hash_entry **sym_hashes;
- const struct reloc_std_external *rel, *relend;
-
- /* We only know how to handle m68k plt entries. */
- if (bfd_get_arch (abfd) != bfd_arch_m68k)
- {
- bfd_set_error (bfd_error_invalid_target);
- return FALSE;
- }
-
- dynobj = NULL;
-
- sym_hashes = (struct sunos_link_hash_entry **) obj_aout_sym_hashes (abfd);
-
- relend = relocs + rel_size / RELOC_STD_SIZE;
- for (rel = relocs; rel < relend; rel++)
- {
- int r_index;
- struct sunos_link_hash_entry *h;
-
- /* We only want relocs against external symbols. */
- if (bfd_header_big_endian (abfd))
- {
- if ((rel->r_type[0] & RELOC_STD_BITS_EXTERN_BIG) == 0)
- continue;
- }
- else
- {
- if ((rel->r_type[0] & RELOC_STD_BITS_EXTERN_LITTLE) == 0)
- continue;
- }
-
- /* Get the symbol index. */
- if (bfd_header_big_endian (abfd))
- r_index = ((rel->r_index[0] << 16)
- | (rel->r_index[1] << 8)
- | rel->r_index[2]);
- else
- r_index = ((rel->r_index[2] << 16)
- | (rel->r_index[1] << 8)
- | rel->r_index[0]);
-
- /* Get the hash table entry. */
- h = sym_hashes[r_index];
- if (h == NULL)
- {
- /* This should not normally happen, but it will in any case
- be caught in the relocation phase. */
- continue;
- }
-
- /* At this point common symbols have already been allocated, so
- we don't have to worry about them. We need to consider that
- we may have already seen this symbol and marked it undefined;
- if the symbol is really undefined, then SUNOS_DEF_DYNAMIC
- will be zero. */
- if (h->root.root.type != bfd_link_hash_defined
- && h->root.root.type != bfd_link_hash_defweak
- && h->root.root.type != bfd_link_hash_undefined)
- continue;
-
- if ((h->flags & SUNOS_DEF_DYNAMIC) == 0
- || (h->flags & SUNOS_DEF_REGULAR) != 0)
- continue;
-
- if (dynobj == NULL)
- {
- asection *sgot;
-
- if (! sunos_create_dynamic_sections (abfd, info, FALSE))
- return FALSE;
- dynobj = sunos_hash_table (info)->dynobj;
- splt = bfd_get_section_by_name (dynobj, ".plt");
- srel = bfd_get_section_by_name (dynobj, ".dynrel");
- BFD_ASSERT (splt != NULL && srel != NULL);
-
- sgot = bfd_get_section_by_name (dynobj, ".got");
- BFD_ASSERT (sgot != NULL);
- if (sgot->size == 0)
- sgot->size = BYTES_IN_WORD;
- sunos_hash_table (info)->got_needed = TRUE;
- }
-
- BFD_ASSERT ((h->flags & SUNOS_REF_REGULAR) != 0);
- BFD_ASSERT (h->plt_offset != 0
- || ((h->root.root.type == bfd_link_hash_defined
- || h->root.root.type == bfd_link_hash_defweak)
- ? (h->root.root.u.def.section->owner->flags
- & DYNAMIC) != 0
- : (h->root.root.u.undef.abfd->flags & DYNAMIC) != 0));
-
- /* This reloc is against a symbol defined only by a dynamic
- object. */
-
- if (h->root.root.type == bfd_link_hash_undefined)
- {
- /* Presumably this symbol was marked as being undefined by
- an earlier reloc. */
- srel->size += RELOC_STD_SIZE;
- }
- else if ((h->root.root.u.def.section->flags & SEC_CODE) == 0)
- {
- bfd *sub;
+ bfd *sub;
/* This reloc is not in the .text section. It must be
copied into the dynamic relocs. We mark the symbol as
Otherwise, we must preserve the reloc as a dynamic reloc. */
static bfd_boolean
-sunos_scan_ext_relocs (info, abfd, sec, relocs, rel_size)
- struct bfd_link_info *info;
- bfd *abfd;
- asection *sec ATTRIBUTE_UNUSED;
- const struct reloc_ext_external *relocs;
- bfd_size_type rel_size;
+sunos_scan_ext_relocs (struct bfd_link_info *info,
+ bfd *abfd,
+ asection *sec ATTRIBUTE_UNUSED,
+ const struct reloc_ext_external *relocs,
+ bfd_size_type rel_size)
{
bfd *dynobj;
struct sunos_link_hash_entry **sym_hashes;
else
{
if (r_index >= bfd_get_symcount (abfd))
- {
- /* This is abnormal, but should be caught in the
- relocation phase. */
- continue;
- }
+ /* This is abnormal, but should be caught in the
+ relocation phase. */
+ continue;
if (adata (abfd).local_got_offsets == NULL)
{
amt = bfd_get_symcount (abfd);
amt *= sizeof (bfd_vma);
- adata (abfd).local_got_offsets =
- (bfd_vma *) bfd_zalloc (abfd, amt);
+ adata (abfd).local_got_offsets = bfd_zalloc (abfd, amt);
if (adata (abfd).local_got_offsets == NULL)
return FALSE;
}
if (r_type != RELOC_JMP_TBL
&& h->root.root.type == bfd_link_hash_undefined)
- {
- /* Presumably this symbol was marked as being undefined by
- an earlier reloc. */
- srel->size += RELOC_EXT_SIZE;
- }
+ /* Presumably this symbol was marked as being undefined by
+ an earlier reloc. */
+ srel->size += RELOC_EXT_SIZE;
+
else if (r_type != RELOC_JMP_TBL
&& (h->root.root.u.def.section->flags & SEC_CODE) == 0)
{
return TRUE;
}
+/* Scan the relocs for an input section. */
+
+static bfd_boolean
+sunos_scan_relocs (struct bfd_link_info *info,
+ bfd *abfd,
+ asection *sec,
+ bfd_size_type rel_size)
+{
+ void * relocs;
+ void * free_relocs = NULL;
+
+ if (rel_size == 0)
+ return TRUE;
+
+ if (! info->keep_memory)
+ relocs = free_relocs = bfd_malloc (rel_size);
+ else
+ {
+ struct aout_section_data_struct *n;
+ bfd_size_type amt = sizeof (struct aout_section_data_struct);
+
+ n = bfd_alloc (abfd, amt);
+ if (n == NULL)
+ relocs = NULL;
+ else
+ {
+ set_aout_section_data (sec, n);
+ relocs = bfd_malloc (rel_size);
+ aout_section_data (sec)->relocs = relocs;
+ }
+ }
+ if (relocs == NULL)
+ return FALSE;
+
+ if (bfd_seek (abfd, sec->rel_filepos, SEEK_SET) != 0
+ || bfd_bread (relocs, rel_size, abfd) != rel_size)
+ goto error_return;
+
+ if (obj_reloc_entry_size (abfd) == RELOC_STD_SIZE)
+ {
+ if (! sunos_scan_std_relocs (info, abfd, sec,
+ (struct reloc_std_external *) relocs,
+ rel_size))
+ goto error_return;
+ }
+ else
+ {
+ if (! sunos_scan_ext_relocs (info, abfd, sec,
+ (struct reloc_ext_external *) relocs,
+ rel_size))
+ goto error_return;
+ }
+
+ if (free_relocs != NULL)
+ free (free_relocs);
+
+ return TRUE;
+
+ error_return:
+ if (free_relocs != NULL)
+ free (free_relocs);
+ return FALSE;
+}
+
/* Build the hash table of dynamic symbols, and to mark as written all
symbols from dynamic objects which we do not plan to write out. */
static bfd_boolean
-sunos_scan_dynamic_symbol (h, data)
- struct sunos_link_hash_entry *h;
- PTR data;
+sunos_scan_dynamic_symbol (struct sunos_link_hash_entry *h, void * data)
{
struct bfd_link_info *info = (struct bfd_link_info *) data;
/* If this symbol is defined by a dynamic object and referenced by a
regular object, see whether we gave it a reasonable value while
scanning the relocs. */
-
if ((h->flags & SUNOS_DEF_REGULAR) == 0
&& (h->flags & SUNOS_DEF_DYNAMIC) != 0
&& (h->flags & SUNOS_REF_REGULAR) != 0)
There are no debugging symbols in the dynamic symbols. */
s = bfd_get_section_by_name (dynobj, ".dynstr");
BFD_ASSERT (s != NULL);
- contents = (bfd_byte *) bfd_realloc (s->contents,
- s->size + len + 1);
+ contents = bfd_realloc (s->contents, s->size + len + 1);
if (contents == NULL)
return FALSE;
s->contents = contents;
return TRUE;
}
+/* Set up the sizes and contents of the dynamic sections created in
+ sunos_add_dynamic_symbols. This is called by the SunOS linker
+ emulation before_allocation routine. We must set the sizes of the
+ sections before the linker sets the addresses of the various
+ sections. This unfortunately requires reading all the relocs so
+ that we can work out which ones need to become dynamic relocs. If
+ info->keep_memory is TRUE, we keep the relocs in memory; otherwise,
+ we discard them, and will read them again later. */
+
+bfd_boolean
+bfd_sunos_size_dynamic_sections (bfd *output_bfd,
+ struct bfd_link_info *info,
+ asection **sdynptr,
+ asection **sneedptr,
+ asection **srulesptr)
+{
+ bfd *dynobj;
+ bfd_size_type dynsymcount;
+ struct sunos_link_hash_entry *h;
+ asection *s;
+ size_t bucketcount;
+ bfd_size_type hashalloc;
+ size_t i;
+ bfd *sub;
+
+ *sdynptr = NULL;
+ *sneedptr = NULL;
+ *srulesptr = NULL;
+
+ if (info->relocatable)
+ return TRUE;
+
+ if (output_bfd->xvec != &MY(vec))
+ return TRUE;
+
+ /* Look through all the input BFD's and read their relocs. It would
+ be better if we didn't have to do this, but there is no other way
+ to determine the number of dynamic relocs we need, and, more
+ importantly, there is no other way to know which symbols should
+ get an entry in the procedure linkage table. */
+ for (sub = info->input_bfds; sub != NULL; sub = sub->link_next)
+ {
+ if ((sub->flags & DYNAMIC) == 0
+ && sub->xvec == output_bfd->xvec)
+ {
+ if (! sunos_scan_relocs (info, sub, obj_textsec (sub),
+ exec_hdr (sub)->a_trsize)
+ || ! sunos_scan_relocs (info, sub, obj_datasec (sub),
+ exec_hdr (sub)->a_drsize))
+ return FALSE;
+ }
+ }
+
+ dynobj = sunos_hash_table (info)->dynobj;
+ dynsymcount = sunos_hash_table (info)->dynsymcount;
+
+ /* If there were no dynamic objects in the link, and we don't need
+ to build a global offset table, there is nothing to do here. */
+ if (! sunos_hash_table (info)->dynamic_sections_needed
+ && ! sunos_hash_table (info)->got_needed)
+ return TRUE;
+
+ /* If __GLOBAL_OFFSET_TABLE_ was mentioned, define it. */
+ h = sunos_link_hash_lookup (sunos_hash_table (info),
+ "__GLOBAL_OFFSET_TABLE_", FALSE, FALSE, FALSE);
+ if (h != NULL && (h->flags & SUNOS_REF_REGULAR) != 0)
+ {
+ h->flags |= SUNOS_DEF_REGULAR;
+ if (h->dynindx == -1)
+ {
+ ++sunos_hash_table (info)->dynsymcount;
+ h->dynindx = -2;
+ }
+ h->root.root.type = bfd_link_hash_defined;
+ h->root.root.u.def.section = bfd_get_section_by_name (dynobj, ".got");
+
+ /* If the .got section is more than 0x1000 bytes, we set
+ __GLOBAL_OFFSET_TABLE_ to be 0x1000 bytes into the section,
+ so that 13 bit relocations have a greater chance of working. */
+ s = bfd_get_section_by_name (dynobj, ".got");
+ BFD_ASSERT (s != NULL);
+ if (s->size >= 0x1000)
+ h->root.root.u.def.value = 0x1000;
+ else
+ h->root.root.u.def.value = 0;
+
+ sunos_hash_table (info)->got_base = h->root.root.u.def.value;
+ }
+
+ /* If there are any shared objects in the link, then we need to set
+ up the dynamic linking information. */
+ if (sunos_hash_table (info)->dynamic_sections_needed)
+ {
+ *sdynptr = bfd_get_section_by_name (dynobj, ".dynamic");
+
+ /* The .dynamic section is always the same size. */
+ s = *sdynptr;
+ BFD_ASSERT (s != NULL);
+ s->size = (sizeof (struct external_sun4_dynamic)
+ + EXTERNAL_SUN4_DYNAMIC_DEBUGGER_SIZE
+ + sizeof (struct external_sun4_dynamic_link));
+
+ /* Set the size of the .dynsym and .hash sections. We counted
+ the number of dynamic symbols as we read the input files. We
+ will build the dynamic symbol table (.dynsym) and the hash
+ table (.hash) when we build the final symbol table, because
+ until then we do not know the correct value to give the
+ symbols. We build the dynamic symbol string table (.dynstr)
+ in a traversal of the symbol table using
+ sunos_scan_dynamic_symbol. */
+ s = bfd_get_section_by_name (dynobj, ".dynsym");
+ BFD_ASSERT (s != NULL);
+ s->size = dynsymcount * sizeof (struct external_nlist);
+ s->contents = bfd_alloc (output_bfd, s->size);
+ if (s->contents == NULL && s->size != 0)
+ return FALSE;
+
+ /* The number of buckets is just the number of symbols divided
+ by four. To compute the final size of the hash table, we
+ must actually compute the hash table. Normally we need
+ exactly as many entries in the hash table as there are
+ dynamic symbols, but if some of the buckets are not used we
+ will need additional entries. In the worst case, every
+ symbol will hash to the same bucket, and we will need
+ BUCKETCOUNT - 1 extra entries. */
+ if (dynsymcount >= 4)
+ bucketcount = dynsymcount / 4;
+ else if (dynsymcount > 0)
+ bucketcount = dynsymcount;
+ else
+ bucketcount = 1;
+ s = bfd_get_section_by_name (dynobj, ".hash");
+ BFD_ASSERT (s != NULL);
+ hashalloc = (dynsymcount + bucketcount - 1) * HASH_ENTRY_SIZE;
+ s->contents = bfd_zalloc (dynobj, hashalloc);
+ if (s->contents == NULL && dynsymcount > 0)
+ return FALSE;
+ for (i = 0; i < bucketcount; i++)
+ PUT_WORD (output_bfd, (bfd_vma) -1, s->contents + i * HASH_ENTRY_SIZE);
+ s->size = bucketcount * HASH_ENTRY_SIZE;
+
+ sunos_hash_table (info)->bucketcount = bucketcount;
+
+ /* Scan all the symbols, place them in the dynamic symbol table,
+ and build the dynamic hash table. We reuse dynsymcount as a
+ counter for the number of symbols we have added so far. */
+ sunos_hash_table (info)->dynsymcount = 0;
+ sunos_link_hash_traverse (sunos_hash_table (info),
+ sunos_scan_dynamic_symbol,
+ (void *) info);
+ BFD_ASSERT (sunos_hash_table (info)->dynsymcount == dynsymcount);
+
+ /* The SunOS native linker seems to align the total size of the
+ symbol strings to a multiple of 8. I don't know if this is
+ important, but it can't hurt much. */
+ s = bfd_get_section_by_name (dynobj, ".dynstr");
+ BFD_ASSERT (s != NULL);
+ if ((s->size & 7) != 0)
+ {
+ bfd_size_type add;
+ bfd_byte *contents;
+
+ add = 8 - (s->size & 7);
+ contents = bfd_realloc (s->contents, s->size + add);
+ if (contents == NULL)
+ return FALSE;
+ memset (contents + s->size, 0, (size_t) add);
+ s->contents = contents;
+ s->size += add;
+ }
+ }
+
+ /* Now that we have worked out the sizes of the procedure linkage
+ table and the dynamic relocs, allocate storage for them. */
+ s = bfd_get_section_by_name (dynobj, ".plt");
+ BFD_ASSERT (s != NULL);
+ if (s->size != 0)
+ {
+ s->contents = bfd_alloc (dynobj, s->size);
+ if (s->contents == NULL)
+ return FALSE;
+
+ /* Fill in the first entry in the table. */
+ switch (bfd_get_arch (dynobj))
+ {
+ case bfd_arch_sparc:
+ memcpy (s->contents, sparc_plt_first_entry, SPARC_PLT_ENTRY_SIZE);
+ break;
+
+ case bfd_arch_m68k:
+ memcpy (s->contents, m68k_plt_first_entry, M68K_PLT_ENTRY_SIZE);
+ break;
+
+ default:
+ abort ();
+ }
+ }
+
+ s = bfd_get_section_by_name (dynobj, ".dynrel");
+ if (s->size != 0)
+ {
+ s->contents = bfd_alloc (dynobj, s->size);
+ if (s->contents == NULL)
+ return FALSE;
+ }
+ /* We use the reloc_count field to keep track of how many of the
+ relocs we have output so far. */
+ s->reloc_count = 0;
+
+ /* Make space for the global offset table. */
+ s = bfd_get_section_by_name (dynobj, ".got");
+ s->contents = bfd_alloc (dynobj, s->size);
+ if (s->contents == NULL)
+ return FALSE;
+
+ *sneedptr = bfd_get_section_by_name (dynobj, ".need");
+ *srulesptr = bfd_get_section_by_name (dynobj, ".rules");
+
+ return TRUE;
+}
+
/* Link a dynamic object. We actually don't have anything to do at
this point. This entry point exists to prevent the regular linker
code from doing anything with the object. */
static bfd_boolean
-sunos_link_dynamic_object (info, abfd)
- struct bfd_link_info *info ATTRIBUTE_UNUSED;
- bfd *abfd ATTRIBUTE_UNUSED;
+sunos_link_dynamic_object (struct bfd_link_info *info ATTRIBUTE_UNUSED,
+ bfd *abfd ATTRIBUTE_UNUSED)
{
return TRUE;
}
over the symbol table. */
static bfd_boolean
-sunos_write_dynamic_symbol (output_bfd, info, harg)
- bfd *output_bfd;
- struct bfd_link_info *info;
- struct aout_link_hash_entry *harg;
+sunos_write_dynamic_symbol (bfd *output_bfd,
+ struct bfd_link_info *info,
+ struct aout_link_hash_entry *harg)
{
struct sunos_link_hash_entry *h = (struct sunos_link_hash_entry *) harg;
int type;
reloc. */
static bfd_boolean
-sunos_check_dynamic_reloc (info, input_bfd, input_section, harg, reloc,
- contents, skip, relocationp)
- struct bfd_link_info *info;
- bfd *input_bfd;
- asection *input_section;
- struct aout_link_hash_entry *harg;
- PTR reloc;
- bfd_byte *contents ATTRIBUTE_UNUSED;
- bfd_boolean *skip;
- bfd_vma *relocationp;
+sunos_check_dynamic_reloc (struct bfd_link_info *info,
+ bfd *input_bfd,
+ asection *input_section,
+ struct aout_link_hash_entry *harg,
+ void * reloc,
+ bfd_byte *contents ATTRIBUTE_UNUSED,
+ bfd_boolean *skip,
+ bfd_vma *relocationp)
{
struct sunos_link_hash_entry *h = (struct sunos_link_hash_entry *) harg;
bfd *dynobj;
/* Finish up the dynamic linking information. */
static bfd_boolean
-sunos_finish_dynamic_link (abfd, info)
- bfd *abfd;
- struct bfd_link_info *info;
+sunos_finish_dynamic_link (bfd *abfd, struct bfd_link_info *info)
{
bfd *dynobj;
asection *o;
2003, 2004 Free Software Foundation, Inc.
Written by Steve Chamberlain of Cygnus Support <sac@cygnus.com>.
-This file is part of BFD, the Binary File Descriptor library.
+ This file is part of BFD, the Binary File Descriptor library.
-This program is free software; you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation; either version 2 of the License, or
-(at your option) any later version.
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-GNU General Public License for more details.
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
-You should have received a copy of the GNU General Public License
-along with this program; if not, write to the Free Software
-Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
-/*
-SUBSECTION
+/* SUBSECTION
Tektronix Hex Format handling
-DESCRIPTION
+ DESCRIPTION
Tek Hex records can hold symbols and data, but not
relocations. Their main application is communication with
up and output them when it's time to close the bfd.
A TekHex record looks like:
-EXAMPLE
+ EXAMPLE
%<block length><type><checksum><stuff><cr>
-DESCRIPTION
+ DESCRIPTION
Where
o length
is the number of bytes in the record not including the % sign.
6) data record
8) termination record
-The data can come out of order, and may be discontigous. This is a
-serial protocol, so big files are unlikely, so we keep a list of 8k chunks
-*/
+ The data can come out of order, and may be discontigous. This is a
+ serial protocol, so big files are unlikely, so we keep a list of 8k chunks. */
#include "bfd.h"
#include "sysdep.h"
#include "libiberty.h"
typedef struct
- {
- bfd_vma low;
- bfd_vma high;
- } addr_range_type;
+{
+ bfd_vma low;
+ bfd_vma high;
+} addr_range_type;
typedef struct tekhex_symbol_struct
- {
-
- asymbol symbol;
- struct tekhex_symbol_struct *prev;
-
- } tekhex_symbol_type;
+{
+ asymbol symbol;
+ struct tekhex_symbol_struct *prev;
+} tekhex_symbol_type;
static const char digs[] = "0123456789ABCDEF";
static char sum_block[256];
-#define NOT_HEX 20
-#define NIBBLE(x) hex_value(x)
-#define HEX(buffer) ((NIBBLE((buffer)[0])<<4) + NIBBLE((buffer)[1]))
-#define TOHEX(d,x) \
-(d)[1] = digs[(x) & 0xf]; \
-(d)[0] = digs[((x)>>4)&0xf];
-#define ISHEX(x) hex_p(x)
-
-static void tekhex_init PARAMS ((void));
-static bfd_vma getvalue PARAMS ((char **));
-static void tekhex_print_symbol
- PARAMS ((bfd *, PTR, asymbol *, bfd_print_symbol_type));
-static void tekhex_get_symbol_info PARAMS ((bfd *, asymbol *, symbol_info *));
-static asymbol *tekhex_make_empty_symbol PARAMS ((bfd *));
-static int tekhex_sizeof_headers PARAMS ((bfd *, bfd_boolean));
-static bfd_boolean tekhex_write_object_contents PARAMS ((bfd *));
-static void out PARAMS ((bfd *, int, char *, char *));
-static void writesym PARAMS ((char **, const char *));
-static void writevalue PARAMS ((char **, bfd_vma));
-static bfd_boolean tekhex_set_section_contents
- PARAMS ((bfd*, sec_ptr, const PTR, file_ptr, bfd_size_type));
-static bfd_boolean tekhex_set_arch_mach
- PARAMS ((bfd *, enum bfd_architecture, unsigned long));
-static bfd_boolean tekhex_get_section_contents
- PARAMS ((bfd *, asection *, PTR, file_ptr, bfd_size_type));
-static void move_section_contents
- PARAMS ((bfd *, asection *, const PTR, file_ptr, bfd_size_type, bfd_boolean));
-static const bfd_target *tekhex_object_p PARAMS ((bfd *));
-static bfd_boolean tekhex_mkobject PARAMS ((bfd *));
-static long tekhex_get_symtab_upper_bound PARAMS ((bfd *));
-static long tekhex_canonicalize_symtab PARAMS ((bfd *, asymbol **));
-static void pass_over PARAMS ((bfd *, void (*) (bfd*, int, char *)));
-static void first_phase PARAMS ((bfd *, int, char *));
-static void insert_byte PARAMS ((bfd *, int, bfd_vma));
-static struct data_struct *find_chunk PARAMS ((bfd *, bfd_vma));
-static unsigned int getsym PARAMS ((char *, char **));
-
-/*
-Here's an example
-%3A6C6480004E56FFFC4E717063B0AEFFFC6D0652AEFFFC60F24E5E4E75
-%1B3709T_SEGMENT1108FFFFFFFF
-%2B3AB9T_SEGMENT7Dgcc_compiled$1087hello$c10
-%373829T_SEGMENT80int$t1$r1$$214741080char$t2$r2$0$12710
-%373769T_SEGMENT80long$int$t3$r1$$1080unsigned$int$t4$10
-%373CA9T_SEGMENT80long$unsigned$in1080short$int$t6$r1$10
-%373049T_SEGMENT80long$long$int$t71080short$unsigned$i10
-%373A29T_SEGMENT80long$long$unsign1080signed$char$t10$10
-%373D69T_SEGMENT80unsigned$char$t11080float$t12$r1$4$010
-%373D19T_SEGMENT80double$t13$r1$8$1080long$double$t14$10
-%2734D9T_SEGMENT8Bvoid$t15$151035_main10
-%2F3CA9T_SEGMENT81$1081$1681$1E81$21487main$F110
-%2832F9T_SEGMENT83i$18FFFFFFFC81$1481$214
-%07 8 10 10
-
-explanation:
-%3A6C6480004E56FFFC4E717063B0AEFFFC6D0652AEFFFC60F24E5E4E75
- ^ ^^ ^ ^-data
- | || +------ 4 char integer 0x8000
- | |+-------- checksum
- | +--------- type 6 (data record)
- +----------- length 3a chars
- <---------------------- 3a (58 chars) ------------------->
-
-%1B3709T_SEGMENT1108FFFFFFFF
- ^ ^^ ^- 8 character integer 0xffffffff
- | |+- 1 character integer 0
- | +-- type 1 symbol (section definition)
- +------------ 9 char symbol T_SEGMENT
-
-%2B3AB9T_SEGMENT7Dgcc_compiled$1087hello$c10
-%373829T_SEGMENT80int$t1$r1$$214741080char$t2$r2$0$12710
-%373769T_SEGMENT80long$int$t3$r1$$1080unsigned$int$t4$10
-%373CA9T_SEGMENT80long$unsigned$in1080short$int$t6$r1$10
-%373049T_SEGMENT80long$long$int$t71080short$unsigned$i10
-%373A29T_SEGMENT80long$long$unsign1080signed$char$t10$10
-%373D69T_SEGMENT80unsigned$char$t11080float$t12$r1$4$010
-%373D19T_SEGMENT80double$t13$r1$8$1080long$double$t14$10
-%2734D9T_SEGMENT8Bvoid$t15$151035_main10
-%2F3CA9T_SEGMENT81$1081$1681$1E81$21487main$F110
-%2832F9T_SEGMENT83i$18FFFFFFFC81$1481$214
-%0781010
-
-Turns into
-sac@thepub$ ./objdump -dx -m m68k f
-
-f: file format tekhex
------x--- 9/55728 -134219416 Sep 29 15:13 1995 f
-architecture: UNKNOWN!, flags 0x00000010:
-HAS_SYMS
-start address 0x00000000
-SECTION 0 [D00000000] : size 00020000 vma 00000000 align 2**0
- ALLOC, LOAD
-SECTION 1 [D00008000] : size 00002001 vma 00008000 align 2**0
-
-SECTION 2 [T_SEGMENT] : size ffffffff vma 00000000 align 2**0
-
-SYMBOL TABLE:
-00000000 g T_SEGMENT gcc_compiled$
-00000000 g T_SEGMENT hello$c
-00000000 g T_SEGMENT int$t1$r1$$21474
-00000000 g T_SEGMENT char$t2$r2$0$127
-00000000 g T_SEGMENT long$int$t3$r1$$
-00000000 g T_SEGMENT unsigned$int$t4$
-00000000 g T_SEGMENT long$unsigned$in
-00000000 g T_SEGMENT short$int$t6$r1$
-00000000 g T_SEGMENT long$long$int$t7
-00000000 g T_SEGMENT short$unsigned$i
-00000000 g T_SEGMENT long$long$unsign
-00000000 g T_SEGMENT signed$char$t10$
-00000000 g T_SEGMENT unsigned$char$t1
-00000000 g T_SEGMENT float$t12$r1$4$0
-00000000 g T_SEGMENT double$t13$r1$8$
-00000000 g T_SEGMENT long$double$t14$
-00000000 g T_SEGMENT void$t15$15
-00000000 g T_SEGMENT _main
-00000000 g T_SEGMENT $
-00000000 g T_SEGMENT $
-00000000 g T_SEGMENT $
-00000010 g T_SEGMENT $
-00000000 g T_SEGMENT main$F1
-fcffffff g T_SEGMENT i$1
-00000000 g T_SEGMENT $
-00000010 g T_SEGMENT $
-
-RELOCATION RECORDS FOR [D00000000]: (none)
-
-RELOCATION RECORDS FOR [D00008000]: (none)
-
-RELOCATION RECORDS FOR [T_SEGMENT]: (none)
-
-Disassembly of section D00000000:
-...
-00008000 ($+)7ff0 linkw fp,#-4
-00008004 ($+)7ff4 nop
-00008006 ($+)7ff6 movel #99,d0
-00008008 ($+)7ff8 cmpl fp@(-4),d0
-0000800c ($+)7ffc blts 00008014 ($+)8004
-0000800e ($+)7ffe addql #1,fp@(-4)
-00008012 ($+)8002 bras 00008006 ($+)7ff6
-00008014 ($+)8004 unlk fp
-00008016 ($+)8006 rts
-...
-
-*/
+#define NOT_HEX 20
+#define NIBBLE(x) hex_value(x)
+#define HEX(buffer) ((NIBBLE ((buffer)[0]) << 4) + NIBBLE ((buffer)[1]))
+#define ISHEX(x) hex_p(x)
+#define TOHEX(d, x) \
+ (d)[1] = digs[(x) & 0xf]; \
+ (d)[0] = digs[((x)>>4)&0xf];
+
+/* Here's an example
+ %3A6C6480004E56FFFC4E717063B0AEFFFC6D0652AEFFFC60F24E5E4E75
+ %1B3709T_SEGMENT1108FFFFFFFF
+ %2B3AB9T_SEGMENT7Dgcc_compiled$1087hello$c10
+ %373829T_SEGMENT80int$t1$r1$$214741080char$t2$r2$0$12710
+ %373769T_SEGMENT80long$int$t3$r1$$1080unsigned$int$t4$10
+ %373CA9T_SEGMENT80long$unsigned$in1080short$int$t6$r1$10
+ %373049T_SEGMENT80long$long$int$t71080short$unsigned$i10
+ %373A29T_SEGMENT80long$long$unsign1080signed$char$t10$10
+ %373D69T_SEGMENT80unsigned$char$t11080float$t12$r1$4$010
+ %373D19T_SEGMENT80double$t13$r1$8$1080long$double$t14$10
+ %2734D9T_SEGMENT8Bvoid$t15$151035_main10
+ %2F3CA9T_SEGMENT81$1081$1681$1E81$21487main$F110
+ %2832F9T_SEGMENT83i$18FFFFFFFC81$1481$214
+ %07 8 10 10
+
+ explanation:
+ %3A6C6480004E56FFFC4E717063B0AEFFFC6D0652AEFFFC60F24E5E4E75
+ ^ ^^ ^ ^-data
+ | || +------ 4 char integer 0x8000
+ | |+-------- checksum
+ | +--------- type 6 (data record)
+ +----------- length 3a chars
+ <---------------------- 3a (58 chars) ------------------->
+
+ %1B3709T_SEGMENT1108FFFFFFFF
+ ^ ^^ ^- 8 character integer 0xffffffff
+ | |+- 1 character integer 0
+ | +-- type 1 symbol (section definition)
+ +------------ 9 char symbol T_SEGMENT
+
+ %2B3AB9T_SEGMENT7Dgcc_compiled$1087hello$c10
+ %373829T_SEGMENT80int$t1$r1$$214741080char$t2$r2$0$12710
+ %373769T_SEGMENT80long$int$t3$r1$$1080unsigned$int$t4$10
+ %373CA9T_SEGMENT80long$unsigned$in1080short$int$t6$r1$10
+ %373049T_SEGMENT80long$long$int$t71080short$unsigned$i10
+ %373A29T_SEGMENT80long$long$unsign1080signed$char$t10$10
+ %373D69T_SEGMENT80unsigned$char$t11080float$t12$r1$4$010
+ %373D19T_SEGMENT80double$t13$r1$8$1080long$double$t14$10
+ %2734D9T_SEGMENT8Bvoid$t15$151035_main10
+ %2F3CA9T_SEGMENT81$1081$1681$1E81$21487main$F110
+ %2832F9T_SEGMENT83i$18FFFFFFFC81$1481$214
+ %0781010
+
+ Turns into
+ sac@thepub$ ./objdump -dx -m m68k f
+
+ f: file format tekhex
+ -----x--- 9/55728 -134219416 Sep 29 15:13 1995 f
+ architecture: UNKNOWN!, flags 0x00000010:
+ HAS_SYMS
+ start address 0x00000000
+ SECTION 0 [D00000000] : size 00020000 vma 00000000 align 2**0
+ ALLOC, LOAD
+ SECTION 1 [D00008000] : size 00002001 vma 00008000 align 2**0
+
+ SECTION 2 [T_SEGMENT] : size ffffffff vma 00000000 align 2**0
+
+ SYMBOL TABLE:
+ 00000000 g T_SEGMENT gcc_compiled$
+ 00000000 g T_SEGMENT hello$c
+ 00000000 g T_SEGMENT int$t1$r1$$21474
+ 00000000 g T_SEGMENT char$t2$r2$0$127
+ 00000000 g T_SEGMENT long$int$t3$r1$$
+ 00000000 g T_SEGMENT unsigned$int$t4$
+ 00000000 g T_SEGMENT long$unsigned$in
+ 00000000 g T_SEGMENT short$int$t6$r1$
+ 00000000 g T_SEGMENT long$long$int$t7
+ 00000000 g T_SEGMENT short$unsigned$i
+ 00000000 g T_SEGMENT long$long$unsign
+ 00000000 g T_SEGMENT signed$char$t10$
+ 00000000 g T_SEGMENT unsigned$char$t1
+ 00000000 g T_SEGMENT float$t12$r1$4$0
+ 00000000 g T_SEGMENT double$t13$r1$8$
+ 00000000 g T_SEGMENT long$double$t14$
+ 00000000 g T_SEGMENT void$t15$15
+ 00000000 g T_SEGMENT _main
+ 00000000 g T_SEGMENT $
+ 00000000 g T_SEGMENT $
+ 00000000 g T_SEGMENT $
+ 00000010 g T_SEGMENT $
+ 00000000 g T_SEGMENT main$F1
+ fcffffff g T_SEGMENT i$1
+ 00000000 g T_SEGMENT $
+ 00000010 g T_SEGMENT $
+
+ RELOCATION RECORDS FOR [D00000000]: (none)
+
+ RELOCATION RECORDS FOR [D00008000]: (none)
+
+ RELOCATION RECORDS FOR [T_SEGMENT]: (none)
+
+ Disassembly of section D00000000:
+ ...
+ 00008000 ($+)7ff0 linkw fp,#-4
+ 00008004 ($+)7ff4 nop
+ 00008006 ($+)7ff6 movel #99,d0
+ 00008008 ($+)7ff8 cmpl fp@(-4),d0
+ 0000800c ($+)7ffc blts 00008014 ($+)8004
+ 0000800e ($+)7ffe addql #1,fp@(-4)
+ 00008012 ($+)8002 bras 00008006 ($+)7ff6
+ 00008014 ($+)8004 unlk fp
+ 00008016 ($+)8006 rts
+ ... */
static void
-tekhex_init ()
+tekhex_init (void)
{
unsigned int i;
static bfd_boolean inited = FALSE;
hex_init ();
val = 0;
for (i = 0; i < 10; i++)
- {
- sum_block[i + '0'] = val++;
- }
+ sum_block[i + '0'] = val++;
+
for (i = 'A'; i <= 'Z'; i++)
- {
- sum_block[i] = val++;
- }
+ sum_block[i] = val++;
+
sum_block['$'] = val++;
sum_block['%'] = val++;
sum_block['.'] = val++;
sum_block['_'] = val++;
for (i = 'a'; i <= 'z'; i++)
- {
- sum_block[i] = val++;
- }
+ sum_block[i] = val++;
}
}
-/* The maximum number of bytes on a line is FF */
+/* The maximum number of bytes on a line is FF. */
#define MAXCHUNK 0xff
-/* The number of bytes we fit onto a line on output */
+/* The number of bytes we fit onto a line on output. */
#define CHUNK 21
/* We cannot output our tekhexords as we see them, we have to glue them
#define CHUNK_MASK 0x1fff
struct data_struct
- {
- char chunk_data[CHUNK_MASK + 1];
- char chunk_init[CHUNK_MASK + 1];
- bfd_vma vma;
- struct data_struct *next;
- };
+{
+ char chunk_data[CHUNK_MASK + 1];
+ char chunk_init[CHUNK_MASK + 1];
+ bfd_vma vma;
+ struct data_struct *next;
+};
typedef struct tekhex_data_struct
{
#define enda(x) (x->vma + x->size)
static bfd_vma
-getvalue (srcp)
- char **srcp;
+getvalue (char **srcp)
{
char *src = *srcp;
bfd_vma value = 0;
if (len == 0)
len = 16;
while (len--)
- {
- value = value << 4 | hex_value(*src++);
- }
+ value = value << 4 | hex_value(*src++);
+
*srcp = src;
return value;
}
static unsigned int
-getsym (dstp, srcp)
- char *dstp;
- char **srcp;
+getsym (char *dstp, char **srcp)
{
char *src = *srcp;
unsigned int i;
}
static struct data_struct *
-find_chunk (abfd, vma)
- bfd *abfd;
- bfd_vma vma;
+find_chunk (bfd *abfd, bfd_vma vma)
{
struct data_struct *d = abfd->tdata.tekhex_data->data;
vma &= ~CHUNK_MASK;
while (d && (d->vma) != vma)
- {
- d = d->next;
- }
+ d = d->next;
+
if (!d)
{
- /* No chunk for this address, so make one up */
- d = ((struct data_struct *)
- bfd_zalloc (abfd, (bfd_size_type) sizeof (struct data_struct)));
+ /* No chunk for this address, so make one up. */
+ d = bfd_zalloc (abfd, (bfd_size_type) sizeof (struct data_struct));
if (!d)
return NULL;
}
static void
-insert_byte (abfd, value, addr)
- bfd *abfd;
- int value;
- bfd_vma addr;
+insert_byte (bfd *abfd, int value, bfd_vma addr)
{
- /* Find the chunk that this byte needs and put it in */
+ /* Find the chunk that this byte needs and put it in. */
struct data_struct *d = find_chunk (abfd, addr);
d->chunk_data[addr & CHUNK_MASK] = value;
}
/* The first pass is to find the names of all the sections, and see
- how big the data is */
+ how big the data is. */
+
static void
-first_phase (abfd, type, src)
- bfd *abfd;
- int type;
- char *src;
+first_phase (bfd *abfd, int type, char *src)
{
asection *section = bfd_abs_section_ptr;
unsigned int len;
- char sym[17]; /* A symbol can only be 16chars long */
+ char sym[17]; /* A symbol can only be 16chars long. */
switch (type)
{
case '6':
- /* Data record - read it and store it */
+ /* Data record - read it and store it. */
{
bfd_vma addr = getvalue (&src);
return;
case '3':
- /* Symbol record, read the segment */
+ /* Symbol record, read the segment. */
len = getsym (sym, &src);
section = bfd_get_section_by_name (abfd, sym);
- if (section == (asection *) NULL)
+ if (section == NULL)
{
char *n = bfd_alloc (abfd, (bfd_size_type) len + 1);
if (!n)
- abort (); /* FIXME */
+ abort (); /* FIXME. */
memcpy (n, sym, len + 1);
section = bfd_make_section (abfd, n);
}
{
switch (*src)
{
- case '1': /* section range */
+ case '1': /* Section range. */
src++;
section->vma = getvalue (&src);
section->size = getvalue (&src) - section->vma;
case '6':
case '7':
case '8':
- /* Symbols, add to section */
+ /* Symbols, add to section. */
{
bfd_size_type amt = sizeof (tekhex_symbol_type);
- tekhex_symbol_type *new =
- (tekhex_symbol_type *) bfd_alloc (abfd, amt);
+ tekhex_symbol_type *new = bfd_alloc (abfd, amt);
char stype = (*src);
if (!new)
- abort (); /* FIXME */
+ abort (); /* FIXME. */
new->symbol.the_bfd = abfd;
src++;
abfd->symcount++;
len = getsym (sym, &src);
new->symbol.name = bfd_alloc (abfd, (bfd_size_type) len + 1);
if (!new->symbol.name)
- abort (); /* FIXME */
+ abort (); /* FIXME. */
memcpy ((char *) (new->symbol.name), sym, len + 1);
new->symbol.section = section;
if (stype <= '4')
record. */
static void
-pass_over (abfd, func)
- bfd *abfd;
- void (*func) PARAMS ((bfd *, int, char *));
+pass_over (bfd *abfd, void (*func) (bfd *, int, char *))
{
unsigned int chars_on_line;
bfd_boolean eof = FALSE;
- /* To the front of the file */
+ /* To the front of the file. */
if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) != 0)
abort ();
while (! eof)
char *src = buffer;
char type;
- /* Find first '%' */
+ /* Find first '%'. */
eof = (bfd_boolean) (bfd_bread (src, (bfd_size_type) 1, abfd) != 1);
while (*src != '%' && !eof)
- {
- eof = (bfd_boolean) (bfd_bread (src, (bfd_size_type) 1, abfd) != 1);
- }
+ eof = (bfd_boolean) (bfd_bread (src, (bfd_size_type) 1, abfd) != 1);
+
if (eof)
break;
src++;
- /* Fetch the type and the length and the checksum */
+ /* Fetch the type and the length and the checksum. */
if (bfd_bread (src, (bfd_size_type) 5, abfd) != 5)
- abort (); /* FIXME */
+ abort (); /* FIXME. */
type = src[2];
if (!ISHEX (src[0]) || !ISHEX (src[1]))
break;
- chars_on_line = HEX (src) - 5; /* Already read five char */
+ /* Already read five char. */
+ chars_on_line = HEX (src) - 5;
if (bfd_bread (src, (bfd_size_type) chars_on_line, abfd) != chars_on_line)
- abort (); /* FIXME */
- src[chars_on_line] = 0; /* put a null at the end */
+ abort (); /* FIXME. */
+
+ /* Put a null at the end. */
+ src[chars_on_line] = 0;
func (abfd, type, src);
}
-
}
static long
-tekhex_canonicalize_symtab (abfd, table)
- bfd *abfd;
- asymbol **table;
+tekhex_canonicalize_symtab (bfd *abfd, asymbol **table)
{
tekhex_symbol_type *p = abfd->tdata.tekhex_data->symbols;
unsigned int c = bfd_get_symcount (abfd);
}
static long
-tekhex_get_symtab_upper_bound (abfd)
- bfd *abfd;
+tekhex_get_symtab_upper_bound (bfd *abfd)
{
return (abfd->symcount + 1) * (sizeof (struct tekhex_asymbol_struct *));
}
static bfd_boolean
-tekhex_mkobject (abfd)
- bfd *abfd;
+tekhex_mkobject (bfd *abfd)
{
tdata_type *tdata;
- tdata = (tdata_type *) bfd_alloc (abfd, (bfd_size_type) sizeof (tdata_type));
+ tdata = bfd_alloc (abfd, (bfd_size_type) sizeof (tdata_type));
if (!tdata)
return FALSE;
abfd->tdata.tekhex_data = tdata;
tdata->type = 1;
- tdata->head = (tekhex_data_list_type *) NULL;
- tdata->symbols = (struct tekhex_symbol_struct *) NULL;
- tdata->data = (struct data_struct *) NULL;
+ tdata->head = NULL;
+ tdata->symbols = NULL;
+ tdata->data = NULL;
return TRUE;
}
-/*
- Return TRUE if the file looks like it's in TekHex format. Just look
- for a percent sign and some hex digits */
+/* Return TRUE if the file looks like it's in TekHex format. Just look
+ for a percent sign and some hex digits. */
static const bfd_target *
-tekhex_object_p (abfd)
- bfd *abfd;
+tekhex_object_p (bfd *abfd)
{
char b[4];
return NULL;
if (b[0] != '%' || !ISHEX (b[1]) || !ISHEX (b[2]) || !ISHEX (b[3]))
- return (const bfd_target *) NULL;
+ return NULL;
tekhex_mkobject (abfd);
}
static void
-move_section_contents (abfd, section, locationp, offset, count, get)
- bfd *abfd;
- asection *section;
- const PTR locationp;
- file_ptr offset;
- bfd_size_type count;
- bfd_boolean get;
+move_section_contents (bfd *abfd,
+ asection *section,
+ const void * locationp,
+ file_ptr offset,
+ bfd_size_type count,
+ bfd_boolean get)
{
bfd_vma addr;
char *location = (char *) locationp;
- bfd_vma prev_number = 1; /* Nothing can have this as a high bit*/
- struct data_struct *d = (struct data_struct *) NULL;
+ bfd_vma prev_number = 1; /* Nothing can have this as a high bit. */
+ struct data_struct *d = NULL;
BFD_ASSERT (offset == 0);
for (addr = section->vma; count != 0; count--, addr++)
bfd_vma low_bits = addr & CHUNK_MASK;
if (chunk_number != prev_number)
- {
- /* Different chunk, so move pointer */
- d = find_chunk (abfd, chunk_number);
- }
+ /* Different chunk, so move pointer. */
+ d = find_chunk (abfd, chunk_number);
if (get)
{
if (d->chunk_init[low_bits])
- {
- *location = d->chunk_data[low_bits];
- }
+ *location = d->chunk_data[low_bits];
else
- {
- *location = 0;
- }
+ *location = 0;
}
else
{
}
location++;
-
}
-
}
static bfd_boolean
-tekhex_get_section_contents (abfd, section, locationp, offset, count)
- bfd *abfd;
- asection *section;
- PTR locationp;
- file_ptr offset;
- bfd_size_type count;
+tekhex_get_section_contents (bfd *abfd,
+ asection *section,
+ void * locationp,
+ file_ptr offset,
+ bfd_size_type count)
{
if (section->flags & (SEC_LOAD | SEC_ALLOC))
{
move_section_contents (abfd, section, locationp, offset, count, TRUE);
return TRUE;
}
- else
- return FALSE;
+
+ return FALSE;
}
static bfd_boolean
-tekhex_set_arch_mach (abfd, arch, machine)
- bfd *abfd;
- enum bfd_architecture arch;
- unsigned long machine;
+tekhex_set_arch_mach (bfd *abfd,
+ enum bfd_architecture arch,
+ unsigned long machine)
{
return bfd_default_set_arch_mach (abfd, arch, machine);
}
-/* we have to save up all the Tekhexords for a splurge before output,
- */
+/* We have to save up all the Tekhexords for a splurge before output. */
static bfd_boolean
-tekhex_set_section_contents (abfd, section, locationp, offset, bytes_to_do)
- bfd *abfd;
- sec_ptr section;
- const PTR locationp;
- file_ptr offset;
- bfd_size_type bytes_to_do;
+tekhex_set_section_contents (bfd *abfd,
+ sec_ptr section,
+ const void * locationp,
+ file_ptr offset,
+ bfd_size_type bytes_to_do)
{
-
if (! abfd->output_has_begun)
{
- /* The first time around, allocate enough sections to hold all the chunks */
+ /* The first time around, allocate enough sections to hold all the chunks. */
asection *s = abfd->sections;
bfd_vma vma;
find_chunk (abfd, vma);
}
}
-
}
+
if (section->flags & (SEC_LOAD | SEC_ALLOC))
{
move_section_contents (abfd, section, locationp, offset, bytes_to_do,
FALSE);
return TRUE;
}
- else
- return FALSE;
+ return FALSE;
}
static void
-writevalue (dst, value)
- char **dst;
- bfd_vma value;
+writevalue (char **dst, bfd_vma value)
{
char *p = *dst;
int len;
}
static void
-writesym (dst, sym)
- char **dst;
- const char *sym;
+writesym (char **dst, const char *sym)
{
char *p = *dst;
int len = (sym ? strlen (sym) : 0);
*p++ = '0';
len = 16;
}
-
else
{
if (len == 0)
len = 1;
}
else
- {
- *p++ = digs[len];
- }
+ *p++ = digs[len];
}
while (len--)
- {
- *p++ = *sym++;
- }
+ *p++ = *sym++;
+
*dst = p;
}
static void
-out (abfd, type, start, end)
- bfd *abfd;
- int type;
- char *start;
- char *end;
+out (bfd *abfd, int type, char *start, char *end)
{
int sum = 0;
char *s;
front[3] = type;
for (s = start; s < end; s++)
- {
- sum += sum_block[(unsigned char) *s];
- }
+ sum += sum_block[(unsigned char) *s];
- sum += sum_block[(unsigned char) front[1]]; /* length */
+ sum += sum_block[(unsigned char) front[1]]; /* Length. */
sum += sum_block[(unsigned char) front[2]];
- sum += sum_block[(unsigned char) front[3]]; /* type */
+ sum += sum_block[(unsigned char) front[3]]; /* Type. */
TOHEX (front + 4, sum);
if (bfd_bwrite (front, (bfd_size_type) 6, abfd) != 6)
abort ();
}
static bfd_boolean
-tekhex_write_object_contents (abfd)
- bfd *abfd;
+tekhex_write_object_contents (bfd *abfd)
{
int bytes_written;
char buffer[100];
bytes_written = 0;
- /* And the raw data */
+ /* And the raw data. */
for (d = abfd->tdata.tekhex_data->data;
- d != (struct data_struct *) NULL;
+ d != NULL;
d = d->next)
{
int low;
const int span = 32;
int addr;
- /* Write it in blocks of 32 bytes */
-
+ /* Write it in blocks of 32 bytes. */
for (addr = 0; addr < CHUNK_MASK + 1; addr += span)
{
int need = 0;
- /* Check to see if necessary */
+ /* Check to see if necessary. */
for (low = 0; !need && low < span; low++)
- {
- if (d->chunk_init[addr + low])
- need = 1;
- }
+ if (d->chunk_init[addr + low])
+ need = 1;
+
if (need)
{
char *dst = buffer;
}
}
}
- /* write all the section headers for the sections */
- for (s = abfd->sections; s != (asection *) NULL; s = s->next)
+
+ /* Write all the section headers for the sections. */
+ for (s = abfd->sections; s != NULL; s = s->next)
{
char *dst = buffer;
out (abfd, '3', buffer, dst);
}
- /* And the symbols */
+ /* And the symbols. */
if (abfd->outsymbols)
{
for (p = abfd->outsymbols; *p; p++)
int section_code = bfd_decode_symclass (*p);
if (section_code != '?')
- { /* do not include debug symbols */
+ {
+ /* Do not include debug symbols. */
asymbol *sym = *p;
char *dst = buffer;
}
}
- /* And the terminator */
+ /* And the terminator. */
if (bfd_bwrite ("%0781010\n", (bfd_size_type) 9, abfd) != 9)
abort ();
return TRUE;
}
static int
-tekhex_sizeof_headers (abfd, exec)
- bfd *abfd ATTRIBUTE_UNUSED;
- bfd_boolean exec ATTRIBUTE_UNUSED;
-
+tekhex_sizeof_headers (bfd *abfd ATTRIBUTE_UNUSED,
+ bfd_boolean exec ATTRIBUTE_UNUSED)
{
return 0;
}
static asymbol *
-tekhex_make_empty_symbol (abfd)
- bfd *abfd;
+tekhex_make_empty_symbol (bfd *abfd)
{
bfd_size_type amt = sizeof (struct tekhex_symbol_struct);
- tekhex_symbol_type *new = (tekhex_symbol_type *) bfd_zalloc (abfd, amt);
+ tekhex_symbol_type *new = bfd_zalloc (abfd, amt);
if (!new)
return NULL;
new->symbol.the_bfd = abfd;
- new->prev = (struct tekhex_symbol_struct *) NULL;
+ new->prev = NULL;
return &(new->symbol);
}
static void
-tekhex_get_symbol_info (ignore_abfd, symbol, ret)
- bfd *ignore_abfd ATTRIBUTE_UNUSED;
- asymbol *symbol;
- symbol_info *ret;
+tekhex_get_symbol_info (bfd *abfd ATTRIBUTE_UNUSED,
+ asymbol *symbol,
+ symbol_info *ret)
{
bfd_symbol_info (symbol, ret);
}
static void
-tekhex_print_symbol (abfd, filep, symbol, how)
- bfd *abfd;
- PTR filep;
- asymbol *symbol;
- bfd_print_symbol_type how;
+tekhex_print_symbol (bfd *abfd,
+ void * filep,
+ asymbol *symbol,
+ bfd_print_symbol_type how)
{
FILE *file = (FILE *) filep;
{
const char *section_name = symbol->section->name;
- bfd_print_symbol_vandf (abfd, (PTR) file, symbol);
+ bfd_print_symbol_vandf (abfd, (void *) file, symbol);
fprintf (file, " %-5s %s",
- section_name,
- symbol->name);
+ section_name, symbol->name);
}
}
}
-#define tekhex_close_and_cleanup _bfd_generic_close_and_cleanup
-#define tekhex_bfd_free_cached_info _bfd_generic_bfd_free_cached_info
-#define tekhex_new_section_hook _bfd_generic_new_section_hook
-
+#define tekhex_close_and_cleanup _bfd_generic_close_and_cleanup
+#define tekhex_bfd_free_cached_info _bfd_generic_bfd_free_cached_info
+#define tekhex_new_section_hook _bfd_generic_new_section_hook
#define tekhex_bfd_is_target_special_symbol ((bfd_boolean (*) (bfd *, asymbol *)) bfd_false)
-#define tekhex_bfd_is_local_label_name bfd_generic_is_local_label_name
-#define tekhex_get_lineno _bfd_nosymbols_get_lineno
-#define tekhex_find_nearest_line _bfd_nosymbols_find_nearest_line
-#define tekhex_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
-#define tekhex_read_minisymbols _bfd_generic_read_minisymbols
-#define tekhex_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol
-
-#define tekhex_bfd_get_relocated_section_contents \
- bfd_generic_get_relocated_section_contents
-#define tekhex_bfd_relax_section bfd_generic_relax_section
-#define tekhex_bfd_gc_sections bfd_generic_gc_sections
-#define tekhex_bfd_merge_sections bfd_generic_merge_sections
-#define tekhex_bfd_is_group_section bfd_generic_is_group_section
-#define tekhex_bfd_discard_group bfd_generic_discard_group
-#define tekhex_section_already_linked \
- _bfd_generic_section_already_linked
-#define tekhex_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
-#define tekhex_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
-#define tekhex_bfd_link_add_symbols _bfd_generic_link_add_symbols
-#define tekhex_bfd_link_just_syms _bfd_generic_link_just_syms
-#define tekhex_bfd_final_link _bfd_generic_final_link
-#define tekhex_bfd_link_split_section _bfd_generic_link_split_section
-
-#define tekhex_get_section_contents_in_window \
- _bfd_generic_get_section_contents_in_window
+#define tekhex_bfd_is_local_label_name bfd_generic_is_local_label_name
+#define tekhex_get_lineno _bfd_nosymbols_get_lineno
+#define tekhex_find_nearest_line _bfd_nosymbols_find_nearest_line
+#define tekhex_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
+#define tekhex_read_minisymbols _bfd_generic_read_minisymbols
+#define tekhex_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol
+#define tekhex_bfd_get_relocated_section_contents bfd_generic_get_relocated_section_contents
+#define tekhex_bfd_relax_section bfd_generic_relax_section
+#define tekhex_bfd_gc_sections bfd_generic_gc_sections
+#define tekhex_bfd_merge_sections bfd_generic_merge_sections
+#define tekhex_bfd_is_group_section bfd_generic_is_group_section
+#define tekhex_bfd_discard_group bfd_generic_discard_group
+#define tekhex_section_already_linked _bfd_generic_section_already_linked
+#define tekhex_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
+#define tekhex_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
+#define tekhex_bfd_link_add_symbols _bfd_generic_link_add_symbols
+#define tekhex_bfd_link_just_syms _bfd_generic_link_just_syms
+#define tekhex_bfd_final_link _bfd_generic_final_link
+#define tekhex_bfd_link_split_section _bfd_generic_link_split_section
+#define tekhex_get_section_contents_in_window _bfd_generic_get_section_contents_in_window
const bfd_target tekhex_vec =
{
- "tekhex", /* name */
+ "tekhex", /* Name. */
bfd_target_tekhex_flavour,
- BFD_ENDIAN_UNKNOWN, /* target byte order */
- BFD_ENDIAN_UNKNOWN, /* target headers byte order */
- (EXEC_P | /* object flags */
- HAS_SYMS | HAS_LINENO | HAS_DEBUG | HAS_RELOC | HAS_LOCALS |
- WP_TEXT | D_PAGED),
+ BFD_ENDIAN_UNKNOWN, /* Target byte order. */
+ BFD_ENDIAN_UNKNOWN, /* Target headers byte order. */
+ (EXEC_P | /* Object flags. */
+ HAS_SYMS | HAS_LINENO | HAS_DEBUG |
+ HAS_RELOC | HAS_LOCALS | WP_TEXT | D_PAGED),
(SEC_CODE | SEC_DATA | SEC_ROM | SEC_HAS_CONTENTS
- | SEC_ALLOC | SEC_LOAD | SEC_RELOC), /* section flags */
- 0, /* leading underscore */
- ' ', /* ar_pad_char */
- 16, /* ar_max_namelen */
+ | SEC_ALLOC | SEC_LOAD | SEC_RELOC), /* Section flags. */
+ 0, /* Leading underscore. */
+ ' ', /* AR_pad_char. */
+ 16, /* AR_max_namelen. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* data */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Data. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* hdrs */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Headers. */
{
_bfd_dummy_target,
- tekhex_object_p, /* bfd_check_format */
+ tekhex_object_p, /* bfd_check_format. */
_bfd_dummy_target,
_bfd_dummy_target,
},
_bfd_generic_mkarchive,
bfd_false,
},
- { /* bfd_write_contents */
+ { /* bfd_write_contents. */
bfd_false,
tekhex_write_object_contents,
_bfd_write_archive_contents,
NULL,
- (PTR) 0
+ NULL
};
o Identification Record
o External Symbol Definition Record
o Object Text Record
- o End Record
-
- */
+ o End Record. */
#include "bfd.h"
#include "sysdep.h"
#include "libbfd.h"
#include "libiberty.h"
-static bfd_boolean versados_mkobject PARAMS ((bfd *));
-static bfd_boolean versados_scan PARAMS ((bfd *));
-static const bfd_target *versados_object_p PARAMS ((bfd *));
-static asymbol *versados_new_symbol
- PARAMS ((bfd *, int, const char *, bfd_vma, asection *));
-static char *new_symbol_string PARAMS ((bfd *, const char *));
-static const bfd_target *versados_object_p PARAMS ((bfd *));
-static bfd_boolean versados_pass_2 PARAMS ((bfd *));
-static bfd_boolean versados_get_section_contents
- PARAMS ((bfd *, asection *, void *, file_ptr, bfd_size_type));
-static bfd_boolean versados_set_section_contents
- PARAMS ((bfd *, sec_ptr, const void *, file_ptr, bfd_size_type));
-static int versados_sizeof_headers PARAMS ((bfd *, bfd_boolean));
-static long int versados_get_symtab_upper_bound PARAMS ((bfd *));
-static long int versados_canonicalize_symtab PARAMS ((bfd *, asymbol **));
-static void versados_get_symbol_info
- PARAMS ((bfd *, asymbol *, symbol_info *));
-static void versados_print_symbol
- PARAMS ((bfd *, PTR, asymbol *, bfd_print_symbol_type));
-static long versados_get_reloc_upper_bound
- PARAMS ((bfd *, sec_ptr));
-static long versados_canonicalize_reloc
- PARAMS ((bfd *, sec_ptr, arelent **, asymbol **));
#define VHEADER '1'
#define VESTDEF '2'
#define VOTR '3'
#define VEND '4'
-#define ES_BASE 17 /* first symbol has esdid 17 */
+#define ES_BASE 17 /* First symbol has esdid 17. */
-/* Per file target dependent information */
+/* Per file target dependent information. */
-/* one for each section */
+/* One for each section. */
struct esdid
- {
- asection *section; /* ptr to bfd version */
- unsigned char *contents; /* used to build image */
- int pc;
- int relocs; /* reloc count, valid end of pass 1 */
- int donerel; /* have relocs been translated */
- };
+{
+ asection *section; /* Ptr to bfd version. */
+ unsigned char *contents; /* Used to build image. */
+ int pc;
+ int relocs; /* Reloc count, valid end of pass 1. */
+ int donerel; /* Have relocs been translated. */
+};
typedef struct versados_data_struct
- {
- int es_done; /* count of symbol index, starts at ES_BASE */
- asymbol *symbols; /* pointer to local symbols */
- char *strings; /* strings of all the above */
- int stringlen; /* len of string table (valid end of pass1) */
- int nsecsyms; /* number of sections */
-
- int ndefs; /* number of exported symbols (they dont get esdids) */
- int nrefs; /* number of imported symbols (valid end of pass1) */
+{
+ int es_done; /* Count of symbol index, starts at ES_BASE. */
+ asymbol *symbols; /* Pointer to local symbols. */
+ char *strings; /* Strings of all the above. */
+ int stringlen; /* Len of string table (valid end of pass1). */
+ int nsecsyms; /* Number of sections. */
- int ref_idx; /* current processed value of the above */
- int def_idx;
+ int ndefs; /* Number of exported symbols (they dont get esdids). */
+ int nrefs; /* Number of imported symbols (valid end of pass1). */
- int pass_2_done;
+ int ref_idx; /* Current processed value of the above. */
+ int def_idx;
- struct esdid e[16]; /* per section info */
- int alert; /* to see if we're trampling */
- asymbol *rest[256 - 16]; /* per symbol info */
+ int pass_2_done;
- }
+ struct esdid e[16]; /* Per section info. */
+ int alert; /* To see if we're trampling. */
+ asymbol *rest[256 - 16]; /* Per symbol info. */
+}
tdata_type;
#define VDATA(abfd) (abfd->tdata.versados_data)
#define RDATA(abfd, n) (abfd->tdata.versados_data->rest[n])
struct ext_otr
- {
- unsigned char size;
- char type;
- unsigned char map[4];
- unsigned char esdid;
- unsigned char data[200];
- };
+{
+ unsigned char size;
+ char type;
+ unsigned char map[4];
+ unsigned char esdid;
+ unsigned char data[200];
+};
struct ext_vheader
- {
- unsigned char size;
- char type; /* record type */
- char name[10]; /* module name */
- char rev; /* module rev number */
- char lang;
- char vol[4];
- char user[2];
- char cat[8];
- char fname[8];
- char ext[2];
- char time[3];
- char date[3];
- char rest[211];
- };
+{
+ unsigned char size;
+ char type; /* Record type. */
+ char name[10]; /* Module name. */
+ char rev; /* Module rev number. */
+ char lang;
+ char vol[4];
+ char user[2];
+ char cat[8];
+ char fname[8];
+ char ext[2];
+ char time[3];
+ char date[3];
+ char rest[211];
+};
struct ext_esd
- {
- unsigned char size;
- char type;
- unsigned char esd_entries[1];
- };
-#define ESD_ABS 0
-#define ESD_COMMON 1
-#define ESD_STD_REL_SEC 2
-#define ESD_SHRT_REL_SEC 3
-#define ESD_XDEF_IN_SEC 4
-#define ESD_XREF_SYM 7
-#define ESD_XREF_SEC 6
-#define ESD_XDEF_IN_ABS 5
+{
+ unsigned char size;
+ char type;
+ unsigned char esd_entries[1];
+};
+
+#define ESD_ABS 0
+#define ESD_COMMON 1
+#define ESD_STD_REL_SEC 2
+#define ESD_SHRT_REL_SEC 3
+#define ESD_XDEF_IN_SEC 4
+#define ESD_XDEF_IN_ABS 5
+#define ESD_XREF_SEC 6
+#define ESD_XREF_SYM 7
+
union ext_any
- {
- unsigned char size;
- struct ext_vheader header;
- struct ext_esd esd;
- struct ext_otr otr;
- };
-
-static int get_record PARAMS ((bfd *, union ext_any *));
-static int get_4 PARAMS ((unsigned char **));
-static void get_10 PARAMS ((unsigned char **, char *));
-static void process_esd PARAMS ((bfd *, struct ext_esd *, int));
-static int get_offset PARAMS ((int, unsigned char *));
-static void process_otr PARAMS ((bfd *, struct ext_otr *, int));
+{
+ unsigned char size;
+ struct ext_vheader header;
+ struct ext_esd esd;
+ struct ext_otr otr;
+};
/* Initialize by filling in the hex conversion array. */
/* Set up the tdata information. */
static bfd_boolean
-versados_mkobject (abfd)
- bfd *abfd;
+versados_mkobject (bfd *abfd)
{
if (abfd->tdata.versados_data == NULL)
{
bfd_size_type amt = sizeof (tdata_type);
- tdata_type *tdata = (tdata_type *) bfd_alloc (abfd, amt);
+ tdata_type *tdata = bfd_alloc (abfd, amt);
+
if (tdata == NULL)
return FALSE;
abfd->tdata.versados_data = tdata;
error messages. */
static asymbol *
-versados_new_symbol (abfd, snum, name, val, sec)
- bfd *abfd;
- int snum;
- const char *name;
- bfd_vma val;
- asection *sec;
+versados_new_symbol (bfd *abfd,
+ int snum,
+ const char *name,
+ bfd_vma val,
+ asection *sec)
{
asymbol *n = VDATA (abfd)->symbols + snum;
n->name = name;
}
static int
-get_record (abfd, ptr)
- bfd *abfd;
- union ext_any *ptr;
+get_record (bfd *abfd, union ext_any *ptr)
{
if (bfd_bread (&ptr->size, (bfd_size_type) 1, abfd) != 1
|| (bfd_bread ((char *) ptr + 1, (bfd_size_type) ptr->size, abfd)
}
static int
-get_4 (pp)
- unsigned char **pp;
+get_4 (unsigned char **pp)
{
unsigned char *p = *pp;
+
*pp += 4;
return (p[0] << 24) | (p[1] << 16) | (p[2] << 8) | (p[3] << 0);
}
static void
-get_10 (pp, name)
- unsigned char **pp;
- char *name;
+get_10 (unsigned char **pp, char *name)
{
char *p = (char *) *pp;
int len = 10;
+
*pp += len;
- while (*p != ' '
- && len)
+ while (*p != ' ' && len)
{
*name++ = *p++;
len--;
}
static char *
-new_symbol_string (abfd, name)
- bfd *abfd;
- const char *name;
+new_symbol_string (bfd *abfd, const char *name)
{
char *n = VDATA (abfd)->strings;
+
strcpy (VDATA (abfd)->strings, name);
VDATA (abfd)->strings += strlen (VDATA (abfd)->strings) + 1;
return n;
}
static void
-process_esd (abfd, esd, pass)
- bfd *abfd;
- struct ext_esd *esd;
- int pass;
+process_esd (bfd *abfd, struct ext_esd *esd, int pass)
{
- /* Read through the ext def for the est entries */
+ /* Read through the ext def for the est entries. */
int togo = esd->size - 2;
bfd_vma size;
bfd_vma start;
char name[11];
unsigned char *ptr = esd->esd_entries;
unsigned char *end = ptr + togo;
+
while (ptr < end)
{
int scn = *ptr & 0xf;
int typ = (*ptr >> 4) & 0xf;
- /* Declare this section */
+ /* Declare this section. */
sprintf (name, "%d", scn);
sec = bfd_make_section_old_way (abfd, strdup (name));
sec->target_index = scn;
EDATA (abfd, scn).section = sec;
ptr++;
+
switch (typ)
{
default:
int snum = VDATA (abfd)->ref_idx++;
get_10 (&ptr, name);
if (pass == 1)
- {
- VDATA (abfd)->stringlen += strlen (name) + 1;
- }
+ VDATA (abfd)->stringlen += strlen (name) + 1;
else
{
int esidx;
asymbol *s;
char *n = new_symbol_string (abfd, name);
+
s = versados_new_symbol (abfd, snum, n, (bfd_vma) 0,
bfd_und_section_ptr);
esidx = VDATA (abfd)->es_done++;
break;
case ESD_STD_REL_SEC:
case ESD_SHRT_REL_SEC:
- {
- sec->size = get_4 (&ptr);
- sec->flags |= SEC_ALLOC;
- }
+ sec->size = get_4 (&ptr);
+ sec->flags |= SEC_ALLOC;
break;
case ESD_XDEF_IN_ABS:
sec = (asection *) & bfd_abs_section;
{
int snum = VDATA (abfd)->def_idx++;
bfd_vma val;
+
get_10 (&ptr, name);
val = get_4 (&ptr);
if (pass == 1)
- {
- /* Just remember the symbol */
- VDATA (abfd)->stringlen += strlen (name) + 1;
- }
+ /* Just remember the symbol. */
+ VDATA (abfd)->stringlen += strlen (name) + 1;
else
{
asymbol *s;
char *n = new_symbol_string (abfd, name);
+
s = versados_new_symbol (abfd, snum + VDATA (abfd)->nrefs, n,
val, sec);
s->flags |= BSF_GLOBAL;
}
}
-#define R_RELWORD 1
-#define R_RELLONG 2
+#define R_RELWORD 1
+#define R_RELLONG 2
#define R_RELWORD_NEG 3
#define R_RELLONG_NEG 4
};
static int
-get_offset (len, ptr)
- int len;
- unsigned char *ptr;
+get_offset (int len, unsigned char *ptr)
{
int val = 0;
+
if (len)
{
int i;
+
val = *ptr++;
if (val & 0x80)
val |= ~0xff;
}
static void
-process_otr (abfd, otr, pass)
- bfd *abfd;
- struct ext_otr *otr;
- int pass;
+process_otr (bfd *abfd, struct ext_otr *otr, int pass)
{
unsigned long shift;
unsigned char *srcp = otr->data;
if (esdids == 0)
{
- /* A zero esdid means the new pc is the offset given */
+ /* A zero esdid means the new pc is the offset given. */
dst_idx += get_offset (offsetlen, srcp);
srcp += offsetlen;
}
else
{
int val = get_offset (offsetlen, srcp + esdids);
+
if (pass == 1)
need_contents = 1;
else
if (esdid)
{
int rn = EDATA (abfd, otr->esdid - 1).relocs++;
+
if (pass == 1)
{
- /* this is the first pass over the data,
- just remember that we need a reloc */
+ /* This is the first pass over the data,
+ just remember that we need a reloc. */
}
else
{
if (dst_idx < esdid->section->size)
if (pass == 2)
{
- /* absolute code, comes in 16 bit lumps */
+ /* Absolute code, comes in 16 bit lumps. */
contents[dst_idx] = srcp[0];
contents[dst_idx + 1] = srcp[1];
}
if (!contents && need_contents)
{
bfd_size_type size = esdid->section->size;
- esdid->contents = (unsigned char *) bfd_alloc (abfd, size);
+ esdid->contents = bfd_alloc (abfd, size);
}
}
static bfd_boolean
-versados_scan (abfd)
- bfd *abfd;
+versados_scan (bfd *abfd)
{
int loop = 1;
int i;
while (loop)
{
union ext_any any;
+
if (!get_record (abfd, &any))
return TRUE;
switch (any.header.type)
}
}
- /* Now allocate space for the relocs and sections */
-
+ /* Now allocate space for the relocs and sections. */
VDATA (abfd)->nrefs = VDATA (abfd)->ref_idx;
VDATA (abfd)->ndefs = VDATA (abfd)->def_idx;
VDATA (abfd)->ref_idx = 0;
for (i = 0; i < 16; i++)
{
struct esdid *esdid = &EDATA (abfd, i);
+
if (esdid->section)
{
amt = (bfd_size_type) esdid->relocs * sizeof (arelent);
- esdid->section->relocation = (arelent *) bfd_alloc (abfd, amt);
+ esdid->section->relocation = bfd_alloc (abfd, amt);
esdid->pc = 0;
esdid->relocs = 0;
- /* Add an entry into the symbol table for it */
+ /* Add an entry into the symbol table for it. */
nsecs++;
VDATA (abfd)->stringlen += strlen (esdid->section->name) + 1;
}
amt = abfd->symcount;
amt *= sizeof (asymbol);
- VDATA (abfd)->symbols = (asymbol *) bfd_alloc (abfd, amt);
+ VDATA (abfd)->symbols = bfd_alloc (abfd, amt);
amt = VDATA (abfd)->stringlen;
VDATA (abfd)->strings = bfd_alloc (abfd, amt);
return FALSE;
/* Actually fill in the section symbols,
- we stick them at the end of the table */
-
+ we stick them at the end of the table. */
for (j = VDATA (abfd)->nrefs + VDATA (abfd)->ndefs, i = 0; i < 16; i++)
{
struct esdid *esdid = &EDATA (abfd, i);
asection *sec = esdid->section;
+
if (sec)
{
asymbol *s = VDATA (abfd)->symbols + j;
j++;
}
}
+
if (abfd->symcount)
abfd->flags |= HAS_SYMS;
/* Set this to nsecs - since we've already planted the section
- symbols */
+ symbols. */
VDATA (abfd)->nsecsyms = nsecs;
VDATA (abfd)->ref_idx = 0;
/* Check whether an existing file is a versados file. */
static const bfd_target *
-versados_object_p (abfd)
- bfd *abfd;
+versados_object_p (bfd *abfd)
{
struct ext_vheader ext;
unsigned char len;
}
/* OK, looks like a record, build the tdata and read in. */
-
tdata_save = abfd->tdata.versados_data;
if (!versados_mkobject (abfd) || !versados_scan (abfd))
{
}
static bfd_boolean
-versados_pass_2 (abfd)
- bfd *abfd;
+versados_pass_2 (bfd *abfd)
{
union ext_any any;
VDATA (abfd)->es_done = ES_BASE;
- /* read records till we get to where we want to be */
-
+ /* Read records till we get to where we want to be. */
while (1)
{
get_record (abfd, &any);
}
static bfd_boolean
-versados_get_section_contents (abfd, section, location, offset, count)
- bfd *abfd;
- asection *section;
- PTR location;
- file_ptr offset;
- bfd_size_type count;
+versados_get_section_contents (bfd *abfd,
+ asection *section,
+ void * location,
+ file_ptr offset,
+ bfd_size_type count)
{
if (!versados_pass_2 (abfd))
return FALSE;
_bfd_generic_get_section_contents_in_window
static bfd_boolean
-versados_set_section_contents (abfd, section, location, offset, bytes_to_do)
- bfd *abfd ATTRIBUTE_UNUSED;
- sec_ptr section ATTRIBUTE_UNUSED;
- const PTR location ATTRIBUTE_UNUSED;
- file_ptr offset ATTRIBUTE_UNUSED;
- bfd_size_type bytes_to_do ATTRIBUTE_UNUSED;
+versados_set_section_contents (bfd *abfd ATTRIBUTE_UNUSED,
+ sec_ptr section ATTRIBUTE_UNUSED,
+ const void * location ATTRIBUTE_UNUSED,
+ file_ptr offset ATTRIBUTE_UNUSED,
+ bfd_size_type bytes_to_do ATTRIBUTE_UNUSED)
{
return FALSE;
}
static int
-versados_sizeof_headers (abfd, exec)
- bfd *abfd ATTRIBUTE_UNUSED;
- bfd_boolean exec ATTRIBUTE_UNUSED;
+versados_sizeof_headers (bfd *abfd ATTRIBUTE_UNUSED,
+ bfd_boolean exec ATTRIBUTE_UNUSED)
{
return 0;
}
/* Return the amount of memory needed to read the symbol table. */
static long
-versados_get_symtab_upper_bound (abfd)
- bfd *abfd;
+versados_get_symtab_upper_bound (bfd *abfd)
{
return (bfd_get_symcount (abfd) + 1) * sizeof (asymbol *);
}
/* Return the symbol table. */
static long
-versados_canonicalize_symtab (abfd, alocation)
- bfd *abfd;
- asymbol **alocation;
+versados_canonicalize_symtab (bfd *abfd, asymbol **alocation)
{
unsigned int symcount = bfd_get_symcount (abfd);
unsigned int i;
for (i = 0, s = VDATA (abfd)->symbols;
i < symcount;
s++, i++)
- {
- *alocation++ = s;
- }
+ *alocation++ = s;
*alocation = NULL;
}
static void
-versados_get_symbol_info (ignore_abfd, symbol, ret)
- bfd *ignore_abfd ATTRIBUTE_UNUSED;
- asymbol *symbol;
- symbol_info *ret;
+versados_get_symbol_info (bfd *abfd ATTRIBUTE_UNUSED,
+ asymbol *symbol,
+ symbol_info *ret)
{
bfd_symbol_info (symbol, ret);
}
static void
-versados_print_symbol (abfd, afile, symbol, how)
- bfd *abfd;
- PTR afile;
- asymbol *symbol;
- bfd_print_symbol_type how;
+versados_print_symbol (bfd *abfd,
+ void * afile,
+ asymbol *symbol,
+ bfd_print_symbol_type how)
{
FILE *file = (FILE *) afile;
+
switch (how)
{
case bfd_print_symbol_name:
fprintf (file, "%s", symbol->name);
break;
default:
- bfd_print_symbol_vandf (abfd, (PTR) file, symbol);
+ bfd_print_symbol_vandf (abfd, (void *) file, symbol);
fprintf (file, " %-5s %s",
symbol->section->name,
symbol->name);
-
}
}
static long
-versados_get_reloc_upper_bound (abfd, asect)
- bfd *abfd ATTRIBUTE_UNUSED;
- sec_ptr asect;
+versados_get_reloc_upper_bound (bfd *abfd ATTRIBUTE_UNUSED,
+ sec_ptr asect)
{
return (asect->reloc_count + 1) * sizeof (arelent *);
}
static long
-versados_canonicalize_reloc (abfd, section, relptr, symbols)
- bfd *abfd;
- sec_ptr section;
- arelent **relptr;
- asymbol **symbols;
+versados_canonicalize_reloc (bfd *abfd,
+ sec_ptr section,
+ arelent **relptr,
+ asymbol **symbols)
{
unsigned int count;
arelent *src;
if (!EDATA (abfd, section->target_index).donerel)
{
EDATA (abfd, section->target_index).donerel = 1;
- /* translate from indexes to symptr ptrs */
+ /* Translate from indexes to symptr ptrs. */
for (count = 0; count < section->reloc_count; count++)
{
int esdid = (int) (size_t) src[count].sym_ptr_ptr;
if (esdid == 0)
+ src[count].sym_ptr_ptr = bfd_abs_section.symbol_ptr_ptr;
+ else if (esdid < ES_BASE)
{
- src[count].sym_ptr_ptr = bfd_abs_section.symbol_ptr_ptr;
- }
- else if (esdid < ES_BASE) /* Section relative thing */
- {
+ /* Section relative thing. */
struct esdid *e = &EDATA (abfd, esdid - 1);
- if (!section)
- {
- /** relocation relative to section which was
- never declared ! */
- }
+
src[count].sym_ptr_ptr = e->section->symbol_ptr_ptr;
}
else
- {
- src[count].sym_ptr_ptr = symbols + esdid - ES_BASE;
- }
-
+ src[count].sym_ptr_ptr = symbols + esdid - ES_BASE;
}
}
for (count = 0; count < section->reloc_count; count++)
- {
- *relptr++ = src++;
- }
+ *relptr++ = src++;
+
*relptr = 0;
return section->reloc_count;
}
-#define versados_close_and_cleanup _bfd_generic_close_and_cleanup
-#define versados_bfd_free_cached_info _bfd_generic_bfd_free_cached_info
-#define versados_new_section_hook _bfd_generic_new_section_hook
-
-#define versados_bfd_is_target_special_symbol \
- ((bfd_boolean (*) (bfd *, asymbol *)) bfd_false)
-#define versados_bfd_is_local_label_name bfd_generic_is_local_label_name
-#define versados_get_lineno _bfd_nosymbols_get_lineno
-#define versados_find_nearest_line _bfd_nosymbols_find_nearest_line
-#define versados_make_empty_symbol _bfd_generic_make_empty_symbol
-#define versados_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
-#define versados_read_minisymbols _bfd_generic_read_minisymbols
-#define versados_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol
-
-#define versados_bfd_reloc_type_lookup _bfd_norelocs_bfd_reloc_type_lookup
-
-#define versados_set_arch_mach bfd_default_set_arch_mach
-
-#define versados_bfd_get_relocated_section_contents \
- bfd_generic_get_relocated_section_contents
-#define versados_bfd_relax_section bfd_generic_relax_section
-#define versados_bfd_gc_sections bfd_generic_gc_sections
-#define versados_bfd_merge_sections bfd_generic_merge_sections
-#define versados_bfd_is_group_section bfd_generic_is_group_section
-#define versados_bfd_discard_group bfd_generic_discard_group
-#define versados_section_already_linked \
- _bfd_generic_section_already_linked
-#define versados_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
-#define versados_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
-#define versados_bfd_link_add_symbols _bfd_generic_link_add_symbols
-#define versados_bfd_link_just_syms _bfd_generic_link_just_syms
-#define versados_bfd_final_link _bfd_generic_final_link
-#define versados_bfd_link_split_section _bfd_generic_link_split_section
+#define versados_close_and_cleanup _bfd_generic_close_and_cleanup
+#define versados_bfd_free_cached_info _bfd_generic_bfd_free_cached_info
+#define versados_new_section_hook _bfd_generic_new_section_hook
+#define versados_bfd_is_target_special_symbol ((bfd_boolean (*) (bfd *, asymbol *)) bfd_false)
+#define versados_bfd_is_local_label_name bfd_generic_is_local_label_name
+#define versados_get_lineno _bfd_nosymbols_get_lineno
+#define versados_find_nearest_line _bfd_nosymbols_find_nearest_line
+#define versados_make_empty_symbol _bfd_generic_make_empty_symbol
+#define versados_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
+#define versados_read_minisymbols _bfd_generic_read_minisymbols
+#define versados_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol
+#define versados_bfd_reloc_type_lookup _bfd_norelocs_bfd_reloc_type_lookup
+#define versados_set_arch_mach bfd_default_set_arch_mach
+#define versados_bfd_get_relocated_section_contents bfd_generic_get_relocated_section_contents
+#define versados_bfd_relax_section bfd_generic_relax_section
+#define versados_bfd_gc_sections bfd_generic_gc_sections
+#define versados_bfd_merge_sections bfd_generic_merge_sections
+#define versados_bfd_is_group_section bfd_generic_is_group_section
+#define versados_bfd_discard_group bfd_generic_discard_group
+#define versados_section_already_linked _bfd_generic_section_already_linked
+#define versados_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
+#define versados_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
+#define versados_bfd_link_add_symbols _bfd_generic_link_add_symbols
+#define versados_bfd_link_just_syms _bfd_generic_link_just_syms
+#define versados_bfd_final_link _bfd_generic_final_link
+#define versados_bfd_link_split_section _bfd_generic_link_split_section
const bfd_target versados_vec =
{
- "versados", /* name */
+ "versados", /* Name. */
bfd_target_versados_flavour,
- BFD_ENDIAN_BIG, /* target byte order */
- BFD_ENDIAN_BIG, /* target headers byte order */
- (HAS_RELOC | EXEC_P | /* object flags */
+ BFD_ENDIAN_BIG, /* Target byte order. */
+ BFD_ENDIAN_BIG, /* Target headers byte order. */
+ (HAS_RELOC | EXEC_P | /* Object flags. */
HAS_LINENO | HAS_DEBUG |
HAS_SYMS | HAS_LOCALS | WP_TEXT | D_PAGED),
(SEC_CODE | SEC_DATA | SEC_ROM | SEC_HAS_CONTENTS
- | SEC_ALLOC | SEC_LOAD | SEC_RELOC), /* section flags */
- 0, /* leading underscore */
- ' ', /* ar_pad_char */
- 16, /* ar_max_namelen */
+ | SEC_ALLOC | SEC_LOAD | SEC_RELOC), /* Section flags. */
+ 0, /* Leading underscore. */
+ ' ', /* AR_pad_char. */
+ 16, /* AR_max_namelen. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* data */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Data. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* hdrs */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Headers. */
{
_bfd_dummy_target,
- versados_object_p, /* bfd_check_format */
+ versados_object_p, /* bfd_check_format. */
_bfd_dummy_target,
_bfd_dummy_target,
},
_bfd_generic_mkarchive,
bfd_false,
},
- { /* bfd_write_contents */
+ { /* bfd_write_contents. */
bfd_false,
bfd_false,
_bfd_write_archive_contents,
NULL,
- (PTR) 0
+ NULL
};
/* Common definitions for backends based on IBM RS/6000 "XCOFF64" files.
- Copyright 2000, 2001, 2002, 2004
+ Copyright 2000, 2001, 2002, 2004, 2005
Free Software Foundation, Inc.
Contributed by Cygnus Support.
-This file is part of BFD, the Binary File Descriptor library.
+ This file is part of BFD, the Binary File Descriptor library.
-This program is free software; you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation; either version 2 of the License, or
-(at your option) any later version.
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-GNU General Public License for more details.
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
-You should have received a copy of the GNU General Public License
-along with this program; if not, write to the Free Software
-Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
/* Internalcoff.h and coffcode.h modify themselves based on this flag. */
#define RS6000COFF_C 1
| (howto->bitsize - 1)); \
}
\f
-#define COFF_DEFAULT_SECTION_ALIGNMENT_POWER (3)
+#define COFF_DEFAULT_SECTION_ALIGNMENT_POWER 3
#define COFF_LONG_FILENAMES
#define RTYPE2HOWTO(cache_ptr, dst) _bfd_xcoff_rtype2howto (cache_ptr, dst)
-#define coff_mkobject _bfd_xcoff_mkobject
-#define coff_bfd_copy_private_bfd_data _bfd_xcoff_copy_private_bfd_data
-#define coff_bfd_is_local_label_name _bfd_xcoff_is_local_label_name
+#define coff_mkobject _bfd_xcoff_mkobject
+#define coff_bfd_copy_private_bfd_data _bfd_xcoff_copy_private_bfd_data
+#define coff_bfd_is_local_label_name _bfd_xcoff_is_local_label_name
#define coff_bfd_is_target_special_symbol ((bfd_boolean (*) (bfd *, asymbol *)) bfd_false)
-#define coff_bfd_reloc_type_lookup _bfd_xcoff_reloc_type_lookup
-#define coff_relocate_section _bfd_ppc_xcoff_relocate_section
+#define coff_bfd_reloc_type_lookup _bfd_xcoff_reloc_type_lookup
+#define coff_relocate_section _bfd_ppc_xcoff_relocate_section
+#define coff_core_file_failing_command _bfd_nocore_core_file_failing_command
+#define coff_core_file_failing_signal _bfd_nocore_core_file_failing_signal
+#define coff_core_file_matches_executable_p _bfd_nocore_core_file_matches_executable_p
+#define _bfd_xcoff_bfd_get_relocated_section_contents coff_bfd_get_relocated_section_contents
+#define _bfd_xcoff_bfd_relax_section coff_bfd_relax_section
+#define _bfd_xcoff_bfd_gc_sections coff_bfd_gc_sections
+#define _bfd_xcoff_bfd_merge_sections coff_bfd_merge_sections
+#define _bfd_xcoff_bfd_discard_group bfd_generic_discard_group
+#define _bfd_xcoff_section_already_linked _bfd_generic_section_already_linked
+#define _bfd_xcoff_bfd_link_split_section coff_bfd_link_split_section
#define CORE_FILE_P _bfd_dummy_target
-#define coff_core_file_failing_command _bfd_nocore_core_file_failing_command
-#define coff_core_file_failing_signal _bfd_nocore_core_file_failing_signal
-#define coff_core_file_matches_executable_p \
- _bfd_nocore_core_file_matches_executable_p
-
#ifdef AIX_CORE
-#undef CORE_FILE_P
+
+#undef CORE_FILE_P
#define CORE_FILE_P rs6000coff_core_p
-extern const bfd_target * rs6000coff_core_p ();
-extern bfd_boolean rs6000coff_core_file_matches_executable_p ();
+extern const bfd_target * rs6000coff_core_p (void);
+extern bfd_boolean rs6000coff_core_file_matches_executable_p (void);
#undef coff_core_file_matches_executable_p
#define coff_core_file_matches_executable_p \
rs6000coff_core_file_matches_executable_p
-extern char *rs6000coff_core_file_failing_command PARAMS ((bfd *abfd));
-#undef coff_core_file_failing_command
+extern char *rs6000coff_core_file_failing_command (bfd *);
+#undef coff_core_file_failing_command
#define coff_core_file_failing_command rs6000coff_core_file_failing_command
-extern int rs6000coff_core_file_failing_signal PARAMS ((bfd *abfd));
-#undef coff_core_file_failing_signal
+extern int rs6000coff_core_file_failing_signal (bfd *);
+#undef coff_core_file_failing_signal
#define coff_core_file_failing_signal rs6000coff_core_file_failing_signal
#endif /* AIX_CORE */
#ifdef LYNX_CORE
-#undef CORE_FILE_P
+#undef CORE_FILE_P
#define CORE_FILE_P lynx_core_file_p
-extern const bfd_target *lynx_core_file_p PARAMS ((bfd *abfd));
+extern const bfd_target *lynx_core_file_p (bfd *);
-extern bfd_boolean lynx_core_file_matches_executable_p
- PARAMS ((bfd *core_bfd, bfd *exec_bfd));
+extern bfd_boolean lynx_core_file_matches_executable_p (bfd *, bfd *);
#undef coff_core_file_matches_executable_p
#define coff_core_file_matches_executable_p lynx_core_file_matches_executable_p
-extern char *lynx_core_file_failing_command PARAMS ((bfd *abfd));
-#undef coff_core_file_failing_command
+extern char *lynx_core_file_failing_command (bfd *);
+#undef coff_core_file_failing_command
#define coff_core_file_failing_command lynx_core_file_failing_command
-extern int lynx_core_file_failing_signal PARAMS ((bfd *abfd));
-#undef coff_core_file_failing_signal
+extern int lynx_core_file_failing_signal (bfd *);
+#undef coff_core_file_failing_signal
#define coff_core_file_failing_signal lynx_core_file_failing_signal
#endif /* LYNX_CORE */
-#define _bfd_xcoff_bfd_get_relocated_section_contents \
- coff_bfd_get_relocated_section_contents
-#define _bfd_xcoff_bfd_relax_section coff_bfd_relax_section
-#define _bfd_xcoff_bfd_gc_sections coff_bfd_gc_sections
-#define _bfd_xcoff_bfd_merge_sections coff_bfd_merge_sections
-#define _bfd_xcoff_bfd_discard_group bfd_generic_discard_group
-#define _bfd_xcoff_section_already_linked \
- _bfd_generic_section_already_linked
-#define _bfd_xcoff_bfd_link_split_section coff_bfd_link_split_section
-
/* XCOFF archives do not have anything which corresponds to an
extended name table. */
#define _bfd_xcoff_slurp_extended_name_table bfd_false
#define _bfd_xcoff_construct_extended_name_table \
- ((bfd_boolean (*) PARAMS ((bfd *, char **, bfd_size_type *, const char **))) \
- bfd_false)
+ ((bfd_boolean (*) (bfd *, char **, bfd_size_type *, const char **)) bfd_false)
#define _bfd_xcoff_truncate_arname bfd_dont_truncate_arname
/* We can use the standard get_elt_at_index routine. */
#define _bfd_xcoff_update_armap_timestamp bfd_true
-extern bfd_boolean _bfd_xcoff_mkobject PARAMS ((bfd *));
-extern bfd_boolean _bfd_xcoff_copy_private_bfd_data PARAMS ((bfd *, bfd *));
-extern bfd_boolean _bfd_xcoff_is_local_label_name PARAMS ((bfd *, const char *));
-extern void _bfd_xcoff_rtype2howto
- PARAMS ((arelent *, struct internal_reloc *));
-extern reloc_howto_type *_bfd_xcoff_reloc_type_lookup
- PARAMS ((bfd *, bfd_reloc_code_real_type));
-extern bfd_boolean _bfd_xcoff_slurp_armap PARAMS ((bfd *));
-extern const bfd_target *_bfd_xcoff_archive_p PARAMS ((bfd *));
-extern PTR _bfd_xcoff_read_ar_hdr PARAMS ((bfd *));
-extern bfd *_bfd_xcoff_openr_next_archived_file PARAMS ((bfd *, bfd *));
-extern int _bfd_xcoff_generic_stat_arch_elt PARAMS ((bfd *, struct stat *));
-extern bfd_boolean _bfd_xcoff_write_armap
- PARAMS ((bfd *, unsigned int, struct orl *, unsigned int, int));
-extern bfd_boolean _bfd_xcoff_write_archive_contents PARAMS ((bfd *));
-extern int _bfd_xcoff_sizeof_headers PARAMS ((bfd *, bfd_boolean));
-extern void _bfd_xcoff_swap_sym_in PARAMS ((bfd *, PTR, PTR));
-extern unsigned int _bfd_xcoff_swap_sym_out PARAMS ((bfd *, PTR, PTR));
-extern void _bfd_xcoff_swap_aux_in PARAMS ((bfd *, PTR, int, int, int, int, PTR));
-extern unsigned int _bfd_xcoff_swap_aux_out PARAMS ((bfd *, PTR, int, int, int, int, PTR));
+extern bfd_boolean _bfd_xcoff_mkobject (bfd *);
+extern bfd_boolean _bfd_xcoff_copy_private_bfd_data (bfd *, bfd *);
+extern bfd_boolean _bfd_xcoff_is_local_label_name (bfd *, const char *);
+extern void _bfd_xcoff_rtype2howto (arelent *, struct internal_reloc *);
+extern bfd_boolean _bfd_xcoff_slurp_armap (bfd *);
+extern void * _bfd_xcoff_read_ar_hdr (bfd *);
+extern bfd * _bfd_xcoff_openr_next_archived_file (bfd *, bfd *);
+extern int _bfd_xcoff_generic_stat_arch_elt (bfd *, struct stat *);
+extern bfd_boolean _bfd_xcoff_write_armap (bfd *, unsigned int, struct orl *, unsigned int, int);
+extern bfd_boolean _bfd_xcoff_write_archive_contents (bfd *);
+extern int _bfd_xcoff_sizeof_headers (bfd *, bfd_boolean);
+extern void _bfd_xcoff_swap_sym_in (bfd *, void *, void *);
+extern unsigned int _bfd_xcoff_swap_sym_out (bfd *, void *, void *);
+extern void _bfd_xcoff_swap_aux_in (bfd *, void *, int, int, int, int, void *);
+extern unsigned int _bfd_xcoff_swap_aux_out (bfd *, void *, int, int, int, int, void *);
+extern reloc_howto_type * _bfd_xcoff_reloc_type_lookup (bfd *, bfd_reloc_code_real_type);
+extern const bfd_target * _bfd_xcoff_archive_p (bfd *);
#ifndef coff_SWAP_sym_in
-#define coff_SWAP_sym_in _bfd_xcoff_swap_sym_in
+#define coff_SWAP_sym_in _bfd_xcoff_swap_sym_in
#define coff_SWAP_sym_out _bfd_xcoff_swap_sym_out
-#define coff_SWAP_aux_in _bfd_xcoff_swap_aux_in
+#define coff_SWAP_aux_in _bfd_xcoff_swap_aux_in
#define coff_SWAP_aux_out _bfd_xcoff_swap_aux_out
#endif
{
TARGET_NAME,
bfd_target_xcoff_flavour,
- BFD_ENDIAN_BIG, /* data byte order is big */
- BFD_ENDIAN_BIG, /* header byte order is big */
+ BFD_ENDIAN_BIG, /* Data byte order is big. */
+ BFD_ENDIAN_BIG, /* Header byte order is big. */
- (HAS_RELOC | EXEC_P | /* object flags */
+ (HAS_RELOC | EXEC_P | /* Object flags. */
HAS_LINENO | HAS_DEBUG | DYNAMIC |
HAS_SYMS | HAS_LOCALS | WP_TEXT),
- (SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD | SEC_RELOC), /* section flags */
- 0, /* leading char */
- '/', /* ar_pad_char */
- 15, /* ar_max_namelen??? FIXMEmgo */
+ (SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD | SEC_RELOC), /* Section flags. */
+ 0, /* Leading char. */
+ '/', /* AR_pad_char. */
+ 15, /* AR_max_namelen??? FIXME. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* data */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16,/* Data. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* hdrs */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16,/* Headers. */
- {_bfd_dummy_target, coff_object_p, /* bfd_check_format */
+ {_bfd_dummy_target, coff_object_p, /* bfd_check_format. */
_bfd_xcoff_archive_p, CORE_FILE_P},
- {bfd_false, coff_mkobject, /* bfd_set_format */
+ {bfd_false, coff_mkobject, /* bfd_set_format. */
_bfd_generic_mkarchive, bfd_false},
- {bfd_false, coff_write_object_contents, /* bfd_write_contents */
+ {bfd_false, coff_write_object_contents, /* bfd_write_contents. */
_bfd_xcoff_write_archive_contents, bfd_false},
BFD_JUMP_TABLE_GENERIC (coff),
/* POWER/PowerPC XCOFF linker support.
- Copyright 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004
+ Copyright 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005
Free Software Foundation, Inc.
Written by Ian Lance Taylor <ian@cygnus.com>, Cygnus Support.
/* This file holds the XCOFF linker code. */
-#define STRING_SIZE_SIZE (4)
+#undef STRING_SIZE_SIZE
+#define STRING_SIZE_SIZE 4
/* We reuse the SEC_ROM flag as a mark flag for garbage collection.
This flag will only be used on input sections. */
index of the TOC symbol is not known when the reloc was handled,
an entry is added to this linked list. This is not an array,
like rel_hashes, because this case is quite uncommon. */
- struct xcoff_toc_rel_hash {
+ struct xcoff_toc_rel_hash
+ {
struct xcoff_toc_rel_hash *next;
struct xcoff_link_hash_entry *h;
struct internal_reloc *rel;
bfd_byte *external_relocs;
};
-static struct bfd_hash_entry *xcoff_link_hash_newfunc
- PARAMS ((struct bfd_hash_entry *, struct bfd_hash_table *, const char *));
-static bfd_boolean xcoff_get_section_contents PARAMS ((bfd *, asection *));
-static struct internal_reloc *xcoff_read_internal_relocs
- PARAMS ((bfd *, asection *, bfd_boolean, bfd_byte *, bfd_boolean,
- struct internal_reloc *));
-static bfd_boolean xcoff_link_add_object_symbols
- PARAMS ((bfd *, struct bfd_link_info *));
-static bfd_boolean xcoff_link_check_archive_element
- PARAMS ((bfd *, struct bfd_link_info *, bfd_boolean *));
-static bfd_boolean xcoff_link_check_ar_symbols
- PARAMS ((bfd *, struct bfd_link_info *, bfd_boolean *));
-static bfd_boolean xcoff_link_check_dynamic_ar_symbols
- PARAMS ((bfd *, struct bfd_link_info *, bfd_boolean *));
-static bfd_size_type xcoff_find_reloc
- PARAMS ((struct internal_reloc *, bfd_size_type, bfd_vma));
-static bfd_boolean xcoff_link_add_symbols
- PARAMS ((bfd *, struct bfd_link_info *));
-static bfd_boolean xcoff_link_add_dynamic_symbols
- PARAMS ((bfd *, struct bfd_link_info *));
-static bfd_boolean xcoff_mark_symbol
- PARAMS ((struct bfd_link_info *, struct xcoff_link_hash_entry *));
-static bfd_boolean xcoff_mark PARAMS ((struct bfd_link_info *, asection *));
-static void xcoff_sweep PARAMS ((struct bfd_link_info *));
-static bfd_boolean xcoff_build_ldsyms
- PARAMS ((struct xcoff_link_hash_entry *, PTR));
-static bfd_boolean xcoff_link_input_bfd
- PARAMS ((struct xcoff_final_link_info *, bfd *));
-static bfd_boolean xcoff_write_global_symbol
- PARAMS ((struct xcoff_link_hash_entry *, PTR));
-static bfd_boolean xcoff_reloc_link_order
- PARAMS ((bfd *, struct xcoff_final_link_info *, asection *,
- struct bfd_link_order *));
-static int xcoff_sort_relocs PARAMS ((const PTR, const PTR));
+static bfd_boolean xcoff_mark (struct bfd_link_info *, asection *);
+
\f
/* Routines to read XCOFF dynamic information. This don't really
/* Read the contents of a section. */
static bfd_boolean
-xcoff_get_section_contents (abfd, sec)
- bfd *abfd;
- asection *sec;
+xcoff_get_section_contents (bfd *abfd, asection *sec)
{
-
if (coff_section_data (abfd, sec) == NULL)
{
bfd_size_type amt = sizeof (struct coff_section_tdata);
+
sec->used_by_bfd = bfd_zalloc (abfd, amt);
if (sec->used_by_bfd == NULL)
return FALSE;
if (coff_section_data (abfd, sec)->contents == NULL)
{
bfd_byte *contents;
- if (!bfd_malloc_and_get_section (abfd, sec, &contents))
+
+ if (! bfd_malloc_and_get_section (abfd, sec, &contents))
{
if (contents != NULL)
free (contents);
/* Get the size required to hold the dynamic symbols. */
long
-_bfd_xcoff_get_dynamic_symtab_upper_bound (abfd)
- bfd *abfd;
+_bfd_xcoff_get_dynamic_symtab_upper_bound (bfd *abfd)
{
asection *lsec;
bfd_byte *contents;
return -1;
contents = coff_section_data (abfd, lsec)->contents;
- bfd_xcoff_swap_ldhdr_in (abfd, (PTR) contents, &ldhdr);
+ bfd_xcoff_swap_ldhdr_in (abfd, (void *) contents, &ldhdr);
return (ldhdr.l_nsyms + 1) * sizeof (asymbol *);
}
/* Get the dynamic symbols. */
long
-_bfd_xcoff_canonicalize_dynamic_symtab (abfd, psyms)
- bfd *abfd;
- asymbol **psyms;
+_bfd_xcoff_canonicalize_dynamic_symtab (bfd *abfd, asymbol **psyms)
{
asection *lsec;
bfd_byte *contents;
strings = (char *) contents + ldhdr.l_stoff;
- symbuf = ((coff_symbol_type *)
- bfd_zalloc (abfd, ldhdr.l_nsyms * sizeof (coff_symbol_type)));
+ symbuf = bfd_zalloc (abfd, ldhdr.l_nsyms * sizeof (* symbuf));
if (symbuf == NULL)
return -1;
/* FIXME: We have no way to record the other information stored
with the loader symbol. */
-
*psyms = (asymbol *) symbuf;
}
/* Get the size required to hold the dynamic relocs. */
long
-_bfd_xcoff_get_dynamic_reloc_upper_bound (abfd)
- bfd *abfd;
+_bfd_xcoff_get_dynamic_reloc_upper_bound (bfd *abfd)
{
asection *lsec;
bfd_byte *contents;
/* Get the dynamic relocs. */
long
-_bfd_xcoff_canonicalize_dynamic_reloc (abfd, prelocs, syms)
- bfd *abfd;
- arelent **prelocs;
- asymbol **syms;
+_bfd_xcoff_canonicalize_dynamic_reloc (bfd *abfd,
+ arelent **prelocs,
+ asymbol **syms)
{
asection *lsec;
bfd_byte *contents;
bfd_xcoff_swap_ldhdr_in (abfd, contents, &ldhdr);
- relbuf = (arelent *) bfd_alloc (abfd, ldhdr.l_nreloc * sizeof (arelent));
+ relbuf = bfd_alloc (abfd, ldhdr.l_nreloc * sizeof (arelent));
if (relbuf == NULL)
return -1;
/* Routine to create an entry in an XCOFF link hash table. */
static struct bfd_hash_entry *
-xcoff_link_hash_newfunc (entry, table, string)
- struct bfd_hash_entry *entry;
- struct bfd_hash_table *table;
- const char *string;
+xcoff_link_hash_newfunc (struct bfd_hash_entry *entry,
+ struct bfd_hash_table *table,
+ const char *string)
{
struct xcoff_link_hash_entry *ret = (struct xcoff_link_hash_entry *) entry;
/* Allocate the structure if it has not already been allocated by a
subclass. */
- if (ret == (struct xcoff_link_hash_entry *) NULL)
- ret = ((struct xcoff_link_hash_entry *)
- bfd_hash_allocate (table, sizeof (struct xcoff_link_hash_entry)));
- if (ret == (struct xcoff_link_hash_entry *) NULL)
- return (struct bfd_hash_entry *) ret;
+ if (ret == NULL)
+ ret = bfd_hash_allocate (table, sizeof (* ret));
+ if (ret == NULL)
+ return NULL;
/* Call the allocation method of the superclass. */
ret = ((struct xcoff_link_hash_entry *)
/* Create a XCOFF link hash table. */
struct bfd_link_hash_table *
-_bfd_xcoff_bfd_link_hash_table_create (abfd)
- bfd *abfd;
+_bfd_xcoff_bfd_link_hash_table_create (bfd *abfd)
{
struct xcoff_link_hash_table *ret;
- bfd_size_type amt = sizeof (struct xcoff_link_hash_table);
+ bfd_size_type amt = sizeof (* ret);
- ret = (struct xcoff_link_hash_table *) bfd_malloc (amt);
- if (ret == (struct xcoff_link_hash_table *) NULL)
- return (struct bfd_link_hash_table *) NULL;
+ ret = bfd_malloc (amt);
+ if (ret == NULL)
+ return NULL;
if (! _bfd_link_hash_table_init (&ret->root, abfd, xcoff_link_hash_newfunc))
{
free (ret);
- return (struct bfd_link_hash_table *) NULL;
+ return NULL;
}
ret->debug_strtab = _bfd_xcoff_stringtab_init ();
/* Free a XCOFF link hash table. */
void
-_bfd_xcoff_bfd_link_hash_table_free (hash)
- struct bfd_link_hash_table *hash;
+_bfd_xcoff_bfd_link_hash_table_free (struct bfd_link_hash_table *hash)
{
struct xcoff_link_hash_table *ret = (struct xcoff_link_hash_table *) hash;
relocs which may have been cached for the enclosing section. */
static struct internal_reloc *
-xcoff_read_internal_relocs (abfd, sec, cache, external_relocs,
- require_internal, internal_relocs)
- bfd *abfd;
- asection *sec;
- bfd_boolean cache;
- bfd_byte *external_relocs;
- bfd_boolean require_internal;
- struct internal_reloc *internal_relocs;
+xcoff_read_internal_relocs (bfd *abfd,
+ asection *sec,
+ bfd_boolean cache,
+ bfd_byte *external_relocs,
+ bfd_boolean require_internal,
+ struct internal_reloc *internal_relocs)
{
-
if (coff_section_data (abfd, sec) != NULL
&& coff_section_data (abfd, sec)->relocs == NULL
&& xcoff_section_data (abfd, sec) != NULL)
&& enclosing->reloc_count > 0)
{
if (_bfd_coff_read_internal_relocs (abfd, enclosing, TRUE,
- external_relocs, FALSE,
- (struct internal_reloc *) NULL)
+ external_relocs, FALSE, NULL)
== NULL)
return NULL;
}
require_internal, internal_relocs);
}
\f
-/* Given an XCOFF BFD, add symbols to the global hash table as
- appropriate. */
-
-bfd_boolean
-_bfd_xcoff_bfd_link_add_symbols (abfd, info)
- bfd *abfd;
- struct bfd_link_info *info;
-{
-
- switch (bfd_get_format (abfd))
- {
- case bfd_object:
- return xcoff_link_add_object_symbols (abfd, info);
-
- case bfd_archive:
- /* If the archive has a map, do the usual search. We then need
- to check the archive for dynamic objects, because they may not
- appear in the archive map even though they should, perhaps, be
- included. If the archive has no map, we just consider each object
- file in turn, since that apparently is what the AIX native linker
- does. */
- if (bfd_has_map (abfd))
- {
- if (! (_bfd_generic_link_add_archive_symbols
- (abfd, info, xcoff_link_check_archive_element)))
- return FALSE;
- }
-
- {
- bfd *member;
-
- member = bfd_openr_next_archived_file (abfd, (bfd *) NULL);
- while (member != NULL)
- {
- if (bfd_check_format (member, bfd_object)
- && (info->hash->creator == member->xvec)
- && (! bfd_has_map (abfd) || (member->flags & DYNAMIC) != 0))
- {
- bfd_boolean needed;
-
- if (! xcoff_link_check_archive_element (member, info,
- &needed))
- return FALSE;
- if (needed)
- member->archive_pass = -1;
- }
- member = bfd_openr_next_archived_file (abfd, member);
- }
- }
-
- return TRUE;
-
- default:
- bfd_set_error (bfd_error_wrong_format);
- return FALSE;
- }
-}
-
-/* Add symbols from an XCOFF object file. */
-
-static bfd_boolean
-xcoff_link_add_object_symbols (abfd, info)
- bfd *abfd;
- struct bfd_link_info *info;
-{
-
- if (! _bfd_coff_get_external_symbols (abfd))
- return FALSE;
- if (! xcoff_link_add_symbols (abfd, info))
- return FALSE;
- if (! info->keep_memory)
- {
- if (! _bfd_coff_free_symbols (abfd))
- return FALSE;
- }
- return TRUE;
-}
-
-/* Check a single archive element to see if we need to include it in
- the link. *PNEEDED is set according to whether this element is
- needed in the link or not. This is called via
- _bfd_generic_link_add_archive_symbols. */
-
-static bfd_boolean
-xcoff_link_check_archive_element (abfd, info, pneeded)
- bfd *abfd;
- struct bfd_link_info *info;
- bfd_boolean *pneeded;
-{
-
- if (! _bfd_coff_get_external_symbols (abfd))
- return FALSE;
-
- if (! xcoff_link_check_ar_symbols (abfd, info, pneeded))
- return FALSE;
-
- if (*pneeded)
- {
- if (! xcoff_link_add_symbols (abfd, info))
- return FALSE;
- }
-
- if (! info->keep_memory || ! *pneeded)
- {
- if (! _bfd_coff_free_symbols (abfd))
- return FALSE;
- }
-
- return TRUE;
-}
-
-/* Look through the symbols to see if this object file should be
- included in the link. */
-
-static bfd_boolean
-xcoff_link_check_ar_symbols (abfd, info, pneeded)
- bfd *abfd;
- struct bfd_link_info *info;
- bfd_boolean *pneeded;
-{
- bfd_size_type symesz;
- bfd_byte *esym;
- bfd_byte *esym_end;
-
- *pneeded = FALSE;
-
- if ((abfd->flags & DYNAMIC) != 0
- && ! info->static_link
- && info->hash->creator == abfd->xvec)
- return xcoff_link_check_dynamic_ar_symbols (abfd, info, pneeded);
-
- symesz = bfd_coff_symesz (abfd);
- esym = (bfd_byte *) obj_coff_external_syms (abfd);
- esym_end = esym + obj_raw_syment_count (abfd) * symesz;
- while (esym < esym_end)
- {
- struct internal_syment sym;
-
- bfd_coff_swap_sym_in (abfd, (PTR) esym, (PTR) &sym);
-
- if (sym.n_sclass == C_EXT && sym.n_scnum != N_UNDEF)
- {
- const char *name;
- char buf[SYMNMLEN + 1];
- struct bfd_link_hash_entry *h;
-
- /* This symbol is externally visible, and is defined by this
- object file. */
-
- name = _bfd_coff_internal_syment_name (abfd, &sym, buf);
-
- if (name == NULL)
- return FALSE;
- h = bfd_link_hash_lookup (info->hash, name, FALSE, FALSE, TRUE);
-
- /* We are only interested in symbols that are currently
- undefined. If a symbol is currently known to be common,
- XCOFF linkers do not bring in an object file which
- defines it. We also don't bring in symbols to satisfy
- undefined references in shared objects. */
- if (h != (struct bfd_link_hash_entry *) NULL
- && h->type == bfd_link_hash_undefined
- && (info->hash->creator != abfd->xvec
- || (((struct xcoff_link_hash_entry *) h)->flags
- & XCOFF_DEF_DYNAMIC) == 0))
- {
- if (! (*info->callbacks->add_archive_element) (info, abfd, name))
- return FALSE;
- *pneeded = TRUE;
- return TRUE;
- }
- }
-
- esym += (sym.n_numaux + 1) * symesz;
- }
-
- /* We do not need this object file. */
- return TRUE;
-}
-
-/* Look through the loader symbols to see if this dynamic object
- should be included in the link. The native linker uses the loader
- symbols, not the normal symbol table, so we do too. */
+/* This function is used to add symbols from a dynamic object to the
+ global symbol table. */
static bfd_boolean
-xcoff_link_check_dynamic_ar_symbols (abfd, info, pneeded)
- bfd *abfd;
- struct bfd_link_info *info;
- bfd_boolean *pneeded;
+xcoff_link_add_dynamic_symbols (bfd *abfd, struct bfd_link_info *info)
{
asection *lsec;
bfd_byte *contents;
struct internal_ldhdr ldhdr;
const char *strings;
bfd_byte *elsym, *elsymend;
+ struct xcoff_import_file *n;
+ const char *bname;
+ const char *mname;
+ const char *s;
+ unsigned int c;
+ struct xcoff_import_file **pp;
- *pneeded = FALSE;
+ /* We can only handle a dynamic object if we are generating an XCOFF
+ output file. */
+ if (info->hash->creator != abfd->xvec)
+ {
+ (*_bfd_error_handler)
+ (_("%s: XCOFF shared object when not producing XCOFF output"),
+ bfd_get_filename (abfd));
+ bfd_set_error (bfd_error_invalid_operation);
+ return FALSE;
+ }
+ /* The symbols we use from a dynamic object are not the symbols in
+ the normal symbol table, but, rather, the symbols in the export
+ table. If there is a global symbol in a dynamic object which is
+ not in the export table, the loader will not be able to find it,
+ so we don't want to find it either. Also, on AIX 4.1.3, shr.o in
+ libc.a has symbols in the export table which are not in the
+ symbol table. */
+
+ /* Read in the .loader section. FIXME: We should really use the
+ o_snloader field in the a.out header, rather than grabbing the
+ section by name. */
lsec = bfd_get_section_by_name (abfd, ".loader");
if (lsec == NULL)
{
- /* There are no symbols, so don't try to include it. */
- return TRUE;
+ (*_bfd_error_handler)
+ (_("%s: dynamic object with no .loader section"),
+ bfd_get_filename (abfd));
+ bfd_set_error (bfd_error_no_symbols);
+ return FALSE;
}
if (! xcoff_get_section_contents (abfd, lsec))
return FALSE;
contents = coff_section_data (abfd, lsec)->contents;
+ /* Remove the sections from this object, so that they do not get
+ included in the link. */
+ bfd_section_list_clear (abfd);
+
bfd_xcoff_swap_ldhdr_in (abfd, contents, &ldhdr);
strings = (char *) contents + ldhdr.l_stoff;
elsym = contents + bfd_xcoff_loader_symbol_offset(abfd, &ldhdr);
elsymend = elsym + ldhdr.l_nsyms * bfd_xcoff_ldsymsz(abfd);
+
for (; elsym < elsymend; elsym += bfd_xcoff_ldsymsz(abfd))
{
struct internal_ldsym ldsym;
char nambuf[SYMNMLEN + 1];
const char *name;
- struct bfd_link_hash_entry *h;
+ struct xcoff_link_hash_entry *h;
bfd_xcoff_swap_ldsym_in (abfd, elsym, &ldsym);
name = nambuf;
}
- h = bfd_link_hash_lookup (info->hash, name, FALSE, FALSE, TRUE);
-
- /* We are only interested in symbols that are currently
- undefined. At this point we know that we are using an XCOFF
+ /* Normally we could not call xcoff_link_hash_lookup in an add
+ symbols routine, since we might not be using an XCOFF hash
+ table. However, we verified above that we are using an XCOFF
hash table. */
- if (h != NULL
- && h->type == bfd_link_hash_undefined
- && (((struct xcoff_link_hash_entry *) h)->flags
- & XCOFF_DEF_DYNAMIC) == 0)
- {
- if (! (*info->callbacks->add_archive_element) (info, abfd, name))
- return FALSE;
- *pneeded = TRUE;
- return TRUE;
- }
- }
- /* We do not need this shared object. */
+ h = xcoff_link_hash_lookup (xcoff_hash_table (info), name, TRUE,
+ TRUE, TRUE);
+ if (h == NULL)
+ return FALSE;
- if (contents != NULL && ! coff_section_data (abfd, lsec)->keep_contents)
- {
- free (coff_section_data (abfd, lsec)->contents);
- coff_section_data (abfd, lsec)->contents = NULL;
- }
+ h->flags |= XCOFF_DEF_DYNAMIC;
- return TRUE;
-}
+ /* If the symbol is undefined, and the BFD it was found in is
+ not a dynamic object, change the BFD to this dynamic object,
+ so that we can get the correct import file ID. */
+ if ((h->root.type == bfd_link_hash_undefined
+ || h->root.type == bfd_link_hash_undefweak)
+ && (h->root.u.undef.abfd == NULL
+ || (h->root.u.undef.abfd->flags & DYNAMIC) == 0))
+ h->root.u.undef.abfd = abfd;
-/* Returns the index of reloc in RELOCS with the least address greater
- than or equal to ADDRESS. The relocs are sorted by address. */
+ if (h->root.type == bfd_link_hash_new)
+ {
+ h->root.type = bfd_link_hash_undefined;
+ h->root.u.undef.abfd = abfd;
+ /* We do not want to add this to the undefined symbol list. */
+ }
-static bfd_size_type
-xcoff_find_reloc (relocs, count, address)
- struct internal_reloc *relocs;
- bfd_size_type count;
- bfd_vma address;
-{
- bfd_size_type min, max, this;
+ if (h->smclas == XMC_UA
+ || h->root.type == bfd_link_hash_undefined
+ || h->root.type == bfd_link_hash_undefweak)
+ h->smclas = ldsym.l_smclas;
- if (count < 2)
+ /* Unless this is an XMC_XO symbol, we don't bother to actually
+ define it, since we don't have a section to put it in anyhow.
+ Instead, the relocation routines handle the DEF_DYNAMIC flag
+ correctly. */
+
+ if (h->smclas == XMC_XO
+ && (h->root.type == bfd_link_hash_undefined
+ || h->root.type == bfd_link_hash_undefweak))
+ {
+ /* This symbol has an absolute value. */
+ h->root.type = bfd_link_hash_defined;
+ h->root.u.def.section = bfd_abs_section_ptr;
+ h->root.u.def.value = ldsym.l_value;
+ }
+
+ /* If this symbol defines a function descriptor, then it
+ implicitly defines the function code as well. */
+ if (h->smclas == XMC_DS
+ || (h->smclas == XMC_XO && name[0] != '.'))
+ h->flags |= XCOFF_DESCRIPTOR;
+ if ((h->flags & XCOFF_DESCRIPTOR) != 0)
+ {
+ struct xcoff_link_hash_entry *hds;
+
+ hds = h->descriptor;
+ if (hds == NULL)
+ {
+ char *dsnm;
+
+ dsnm = bfd_malloc ((bfd_size_type) strlen (name) + 2);
+ if (dsnm == NULL)
+ return FALSE;
+ dsnm[0] = '.';
+ strcpy (dsnm + 1, name);
+ hds = xcoff_link_hash_lookup (xcoff_hash_table (info), dsnm,
+ TRUE, TRUE, TRUE);
+ free (dsnm);
+ if (hds == NULL)
+ return FALSE;
+
+ if (hds->root.type == bfd_link_hash_new)
+ {
+ hds->root.type = bfd_link_hash_undefined;
+ hds->root.u.undef.abfd = abfd;
+ /* We do not want to add this to the undefined
+ symbol list. */
+ }
+
+ hds->descriptor = h;
+ h->descriptor = hds;
+ }
+
+ hds->flags |= XCOFF_DEF_DYNAMIC;
+ if (hds->smclas == XMC_UA)
+ hds->smclas = XMC_PR;
+
+ /* An absolute symbol appears to actually define code, not a
+ function descriptor. This is how some math functions are
+ implemented on AIX 4.1. */
+ if (h->smclas == XMC_XO
+ && (hds->root.type == bfd_link_hash_undefined
+ || hds->root.type == bfd_link_hash_undefweak))
+ {
+ hds->smclas = XMC_XO;
+ hds->root.type = bfd_link_hash_defined;
+ hds->root.u.def.section = bfd_abs_section_ptr;
+ hds->root.u.def.value = ldsym.l_value;
+ }
+ }
+ }
+
+ if (contents != NULL && ! coff_section_data (abfd, lsec)->keep_contents)
{
- if (count == 1 && relocs[0].r_vaddr < address)
- return 1;
- else
- return 0;
+ free (coff_section_data (abfd, lsec)->contents);
+ coff_section_data (abfd, lsec)->contents = NULL;
}
- min = 0;
- max = count;
+ /* Record this file in the import files. */
+ n = bfd_alloc (abfd, (bfd_size_type) sizeof (struct xcoff_import_file));
+ if (n == NULL)
+ return FALSE;
+ n->next = NULL;
- /* Do a binary search over (min,max]. */
- while (min + 1 < max)
+ /* For some reason, the path entry in the import file list for a
+ shared object appears to always be empty. The file name is the
+ base name. */
+ n->path = "";
+ if (abfd->my_archive == NULL)
{
- bfd_vma raddr;
-
- this = (max + min) / 2;
- raddr = relocs[this].r_vaddr;
- if (raddr > address)
- max = this;
- else if (raddr < address)
- min = this;
- else
- {
- min = this;
- break;
- }
+ bname = bfd_get_filename (abfd);
+ mname = "";
+ }
+ else
+ {
+ bname = bfd_get_filename (abfd->my_archive);
+ mname = bfd_get_filename (abfd);
}
+ s = strrchr (bname, '/');
+ if (s != NULL)
+ bname = s + 1;
+ n->file = bname;
+ n->member = mname;
- if (relocs[min].r_vaddr < address)
- return min + 1;
+ /* We start c at 1 because the first import file number is reserved
+ for LIBPATH. */
+ for (pp = &xcoff_hash_table (info)->imports, c = 1;
+ *pp != NULL;
+ pp = &(*pp)->next, ++c)
+ ;
+ *pp = n;
- while (min > 0
- && relocs[min - 1].r_vaddr == address)
- --min;
+ xcoff_data (abfd)->import_file_id = c;
- return min;
+ return TRUE;
}
-
/* xcoff_link_create_extra_sections
Takes care of creating the .loader, .gl, .ds, .debug and sections. */
static bfd_boolean
-xcoff_link_create_extra_sections(bfd * abfd, struct bfd_link_info *info)
+xcoff_link_create_extra_sections (bfd * abfd, struct bfd_link_info *info)
{
-
bfd_boolean return_value = FALSE;
if (info->hash->creator == abfd->xvec)
{
-
/* We need to build a .loader section, so we do it here. This
won't work if we're producing an XCOFF output file with no
XCOFF input files. FIXME. */
lsec = bfd_make_section_anyway (abfd, ".loader");
if (lsec == NULL)
- {
- goto end_return;
- }
+ goto end_return;
+
xcoff_hash_table (info)->loader_section = lsec;
lsec->flags |= SEC_HAS_CONTENTS | SEC_IN_MEMORY;
}
lsec = bfd_make_section_anyway (abfd, ".gl");
if (lsec == NULL)
- {
- goto end_return;
- }
+ goto end_return;
xcoff_hash_table (info)->linkage_section = lsec;
lsec->flags |= (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS
tsec = bfd_make_section_anyway (abfd, ".tc");
if (tsec == NULL)
- {
- goto end_return;
- }
+ goto end_return;
xcoff_hash_table (info)->toc_section = tsec;
tsec->flags |= (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS
dsec = bfd_make_section_anyway (abfd, ".ds");
if (dsec == NULL)
- {
- goto end_return;
- }
+ goto end_return;
xcoff_hash_table (info)->descriptor_section = dsec;
dsec->flags |= (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS
dsec = bfd_make_section_anyway (abfd, ".debug");
if (dsec == NULL)
- {
- goto end_return;
- }
+ goto end_return;
+
xcoff_hash_table (info)->debug_section = dsec;
dsec->flags |= SEC_HAS_CONTENTS | SEC_IN_MEMORY;
}
return return_value;
}
+/* Returns the index of reloc in RELOCS with the least address greater
+ than or equal to ADDRESS. The relocs are sorted by address. */
+
+static bfd_size_type
+xcoff_find_reloc (struct internal_reloc *relocs,
+ bfd_size_type count,
+ bfd_vma address)
+{
+ bfd_size_type min, max, this;
+
+ if (count < 2)
+ {
+ if (count == 1 && relocs[0].r_vaddr < address)
+ return 1;
+ else
+ return 0;
+ }
+
+ min = 0;
+ max = count;
+
+ /* Do a binary search over (min,max]. */
+ while (min + 1 < max)
+ {
+ bfd_vma raddr;
+
+ this = (max + min) / 2;
+ raddr = relocs[this].r_vaddr;
+ if (raddr > address)
+ max = this;
+ else if (raddr < address)
+ min = this;
+ else
+ {
+ min = this;
+ break;
+ }
+ }
+
+ if (relocs[min].r_vaddr < address)
+ return min + 1;
+
+ while (min > 0
+ && relocs[min - 1].r_vaddr == address)
+ --min;
+
+ return min;
+}
+
/* Add all the symbols from an object file to the hash table.
XCOFF is a weird format. A normal XCOFF .o files will have three
csect they belong to is to examine the address. */
static bfd_boolean
-xcoff_link_add_symbols (abfd, info)
- bfd *abfd;
- struct bfd_link_info *info;
+xcoff_link_add_symbols (bfd *abfd, struct bfd_link_info *info)
{
unsigned int n_tmask;
unsigned int n_btshft;
return FALSE;
}
- /* create the loader, toc, gl, ds and debug sections, if needed */
+ /* Create the loader, toc, gl, ds and debug sections, if needed. */
if (! xcoff_link_create_extra_sections (abfd, info))
goto error_return;
/* We keep a list of the linker hash table entries that correspond
to each external symbol. */
amt = symcount * sizeof (struct xcoff_link_hash_entry *);
- sym_hash = (struct xcoff_link_hash_entry **) bfd_zalloc (abfd, amt);
+ sym_hash = bfd_zalloc (abfd, amt);
if (sym_hash == NULL && symcount != 0)
goto error_return;
coff_data (abfd)->sym_hashes = (struct coff_link_hash_entry **) sym_hash;
not easily determine which section a symbol is in, so we store
the information in the tdata for the input file. */
amt = symcount * sizeof (asection *);
- csect_cache = (asection **) bfd_zalloc (abfd, amt);
+ csect_cache = bfd_zalloc (abfd, amt);
if (csect_cache == NULL && symcount != 0)
goto error_return;
xcoff_data (abfd)->csects = csect_cache;
into reloc_info using the section target_index. */
amt = abfd->section_count + 1;
amt *= sizeof (struct reloc_info_struct);
- reloc_info = (struct reloc_info_struct *) bfd_zmalloc (amt);
+ reloc_info = bfd_zmalloc (amt);
if (reloc_info == NULL)
goto error_return;
last_real = NULL;
for (o = abfd->sections; o != NULL; o = o->next)
{
-
last_real = o;
+
if ((o->flags & SEC_RELOC) != 0)
{
-
reloc_info[o->target_index].relocs =
- xcoff_read_internal_relocs (abfd, o, TRUE, (bfd_byte *) NULL,
- FALSE, (struct internal_reloc *) NULL);
+ xcoff_read_internal_relocs (abfd, o, TRUE, NULL, FALSE, NULL);
amt = o->reloc_count;
amt *= sizeof (asection *);
- reloc_info[o->target_index].csects = (asection **) bfd_zmalloc (amt);
+ reloc_info[o->target_index].csects = bfd_zmalloc (amt);
if (reloc_info[o->target_index].csects == NULL)
goto error_return;
}
if ((info->strip == strip_none || info->strip == strip_some)
&& o->lineno_count > 0)
{
-
bfd_byte *linenos;
amt = linesz * o->lineno_count;
- linenos = (bfd_byte *) bfd_malloc (amt);
+ linenos = bfd_malloc (amt);
if (linenos == NULL)
goto error_return;
reloc_info[o->target_index].linenos = linenos;
if (bfd_seek (abfd, o->line_filepos, SEEK_SET) != 0
|| bfd_bread (linenos, amt, abfd) != amt)
goto error_return;
-
}
}
bfd_vma value;
struct xcoff_link_hash_entry *set_toc;
- bfd_coff_swap_sym_in (abfd, (PTR) esym, (PTR) &sym);
+ bfd_coff_swap_sym_in (abfd, (void *) esym, (void *) &sym);
/* In this pass we are only interested in symbols with csect
information. */
if (sym.n_sclass != C_EXT && sym.n_sclass != C_HIDEXT)
{
-
/* Set csect_cache,
Normally csect is a .pr, .rw etc. created in the loop
If C_FILE or first time, handle special
&& csect != NULL
&& ISFCN (sym.n_type))
{
-
union internal_auxent auxlin;
- bfd_coff_swap_aux_in (abfd, (PTR) (esym + symesz),
+ bfd_coff_swap_aux_in (abfd, (void *) (esym + symesz),
sym.n_type, sym.n_sclass,
- 0, sym.n_numaux, (PTR) &auxlin);
+ 0, sym.n_numaux, (void *) &auxlin);
if (auxlin.x_sym.x_fcnary.x_fcn.x_lnnoptr != 0)
{
}
linoff = (auxlin.x_sym.x_fcnary.x_fcn.x_lnnoptr
- enclosing->line_filepos);
- /* explicit cast to bfd_signed_vma for compiler */
+ /* Explicit cast to bfd_signed_vma for compiler. */
if (linoff < (bfd_signed_vma) (enclosing->lineno_count * linesz))
{
struct internal_lineno lin;
linpstart = (reloc_info[enclosing->target_index].linenos
+ linoff);
- bfd_coff_swap_lineno_in (abfd, (PTR) linpstart, (PTR) &lin);
+ bfd_coff_swap_lineno_in (abfd, (void *) linpstart, (void *) &lin);
if (lin.l_lnno == 0
&& ((bfd_size_type) lin.l_addr.l_symndx
== ((esym
linp < linpend;
linp += linesz)
{
- bfd_coff_swap_lineno_in (abfd, (PTR) linp,
- (PTR) &lin);
+ bfd_coff_swap_lineno_in (abfd, (void *) linp,
+ (void *) &lin);
if (lin.l_lnno == 0)
break;
}
}
/* Pick up the csect auxiliary information. */
-
if (sym.n_numaux == 0)
{
(*_bfd_error_handler)
}
bfd_coff_swap_aux_in (abfd,
- (PTR) (esym + symesz * sym.n_numaux),
+ (void *) (esym + symesz * sym.n_numaux),
sym.n_type, sym.n_sclass,
sym.n_numaux - 1, sym.n_numaux,
- (PTR) &aux);
+ (void *) &aux);
smtyp = SMTYP_SMTYP (aux.x_csect.x_smtyp);
erelsym = ((bfd_byte *) obj_coff_external_syms (abfd)
+ rel->r_symndx * symesz);
- bfd_coff_swap_sym_in (abfd, (PTR) erelsym, (PTR) &relsym);
+ bfd_coff_swap_sym_in (abfd, (void *) erelsym, (void *) &relsym);
if (relsym.n_sclass == C_EXT)
{
const char *relname;
/* At this point we know that the TOC entry is
for an externally visible symbol. */
-
relname = _bfd_coff_internal_syment_name (abfd, &relsym,
relbuf);
if (relname == NULL)
the normal case, but not common cases like
SYM.P4 which gcc generates to store SYM + 4
in the TOC. FIXME. */
-
if (strcmp (name, relname) == 0)
{
copy = (! info->keep_memory
/* We are about to create a TOC entry for
this symbol. */
set_toc = h;
- } /* merge toc reloc */
- } /* c_ext */
- } /* reloc */
- } /* merge toc */
+ }
+ }
+ }
+ }
{
-
asection *enclosing;
/* We need to create a new section. We get the name from
csect = bfd_xcoff_create_csect_from_smclas(abfd, &aux, name);
if (NULL == csect)
- {
- goto error_return;
- }
+ goto error_return;
/* The enclosing section is the main section : .data, .text
or .bss that the csect is coming from. */
/* Record the enclosing section in the tdata for this new
section. */
amt = sizeof (struct coff_section_tdata);
- csect->used_by_bfd = (PTR) bfd_zalloc (abfd, amt);
+ csect->used_by_bfd = bfd_zalloc (abfd, amt);
if (csect->used_by_bfd == NULL)
goto error_return;
amt = sizeof (struct xcoff_section_tdata);
/* The linker script puts the .td section in the data
section after the .tc section. */
csect = bfd_make_section_anyway (abfd, ".td");
-
}
else
- {
- csect = bfd_make_section_anyway (abfd, ".bss");
- }
+ csect = bfd_make_section_anyway (abfd, ".bss");
+
if (csect == NULL)
goto error_return;
csect->vma = sym.n_value;
/ symesz);
amt = sizeof (struct coff_section_tdata);
- csect->used_by_bfd = (PTR) bfd_zalloc (abfd, amt);
+ csect->used_by_bfd = bfd_zalloc (abfd, amt);
if (csect->used_by_bfd == NULL)
goto error_return;
amt = sizeof (struct xcoff_section_tdata);
&& aux.x_csect.x_smclas != XMC_TC
&& aux.x_csect.x_smclas != XMC_TD)
{
-
int i = -1;
if (name[0] == '_')
i = XCOFF_SPECIAL_SECTION_END;
}
else if (name[0] == 'e' && strcmp (name, "end") == 0)
- {
- i = XCOFF_SPECIAL_SECTION_END2;
- }
+ i = XCOFF_SPECIAL_SECTION_END2;
if (i != -1)
- {
- xcoff_hash_table (info)->special_sections[i] = csect;
- }
+ xcoff_hash_table (info)->special_sections[i] = csect;
}
/* Now we have enough information to add the symbol to the
if (info->hash->creator == abfd->xvec)
{
if (! bfd_is_und_section (section))
- {
- *sym_hash = xcoff_link_hash_lookup (xcoff_hash_table (info),
- name, TRUE, copy, FALSE);
- }
+ *sym_hash = xcoff_link_hash_lookup (xcoff_hash_table (info),
+ name, TRUE, copy, FALSE);
else
- {
- /* Make a copy of the symbol name to prevent problems with
- merging symbols. */
- *sym_hash = ((struct xcoff_link_hash_entry *)
- bfd_wrapped_link_hash_lookup (abfd, info, name,
- TRUE, TRUE,
- FALSE));
- }
+ /* Make a copy of the symbol name to prevent problems with
+ merging symbols. */
+ *sym_hash = ((struct xcoff_link_hash_entry *)
+ bfd_wrapped_link_hash_lookup (abfd, info, name,
+ TRUE, TRUE, FALSE));
+
if (*sym_hash == NULL)
goto error_return;
if (((*sym_hash)->root.type == bfd_link_hash_defined
not an error. */
if (! ((*info->callbacks->multiple_definition)
(info, (*sym_hash)->root.root.string,
- (bfd *) NULL, (asection *) NULL, (bfd_vma) 0,
+ NULL, NULL, (bfd_vma) 0,
(*sym_hash)->root.u.def.section->owner,
(*sym_hash)->root.u.def.section,
(*sym_hash)->root.u.def.value)))
last_real->next = NULL;
if (! (_bfd_generic_link_add_one_symbol
(info, abfd, name, flags, section, value,
- (const char *) NULL, copy, TRUE,
+ NULL, copy, TRUE,
(struct bfd_link_hash_entry **) sym_hash)))
goto error_return;
last_real->next = first_csect;
{
if ((*sym_hash)->root.type != bfd_link_hash_common
|| (*sym_hash)->root.u.c.p->section != csect)
- {
- /* We don't need the common csect we just created. */
- csect->size = 0;
- }
+ /* We don't need the common csect we just created. */
+ csect->size = 0;
else
- {
- (*sym_hash)->root.u.c.p->alignment_power
- = csect->alignment_power;
- }
+ (*sym_hash)->root.u.c.p->alignment_power
+ = csect->alignment_power;
}
if (info->hash->creator == abfd->xvec)
for (i = 0; i < o->reloc_count; i++, rel++, rel_csect++)
{
-
if (*rel_csect == NULL)
{
(*_bfd_error_handler)
if (! (_bfd_generic_link_add_one_symbol
(info, abfd, hds->root.root.string,
(flagword) 0, bfd_und_section_ptr,
- (bfd_vma) 0, (const char *) NULL, FALSE,
+ (bfd_vma) 0, NULL, FALSE,
TRUE, &bh)))
goto error_return;
hds = (struct xcoff_link_hash_entry *) bh;
#undef N_TMASK
#undef N_BTSHFT
-/* This function is used to add symbols from a dynamic object to the
- global symbol table. */
+/* Add symbols from an XCOFF object file. */
static bfd_boolean
-xcoff_link_add_dynamic_symbols (abfd, info)
- bfd *abfd;
- struct bfd_link_info *info;
+xcoff_link_add_object_symbols (bfd *abfd, struct bfd_link_info *info)
{
- asection *lsec;
- bfd_byte *contents;
- struct internal_ldhdr ldhdr;
- const char *strings;
- bfd_byte *elsym, *elsymend;
- struct xcoff_import_file *n;
- const char *bname;
- const char *mname;
- const char *s;
- unsigned int c;
- struct xcoff_import_file **pp;
-
- /* We can only handle a dynamic object if we are generating an XCOFF
- output file. */
- if (info->hash->creator != abfd->xvec)
+ if (! _bfd_coff_get_external_symbols (abfd))
+ return FALSE;
+ if (! xcoff_link_add_symbols (abfd, info))
+ return FALSE;
+ if (! info->keep_memory)
{
- (*_bfd_error_handler)
- (_("%s: XCOFF shared object when not producing XCOFF output"),
- bfd_get_filename (abfd));
- bfd_set_error (bfd_error_invalid_operation);
- return FALSE;
+ if (! _bfd_coff_free_symbols (abfd))
+ return FALSE;
}
+ return TRUE;
+}
- /* The symbols we use from a dynamic object are not the symbols in
- the normal symbol table, but, rather, the symbols in the export
- table. If there is a global symbol in a dynamic object which is
- not in the export table, the loader will not be able to find it,
- so we don't want to find it either. Also, on AIX 4.1.3, shr.o in
- libc.a has symbols in the export table which are not in the
- symbol table. */
+/* Look through the loader symbols to see if this dynamic object
+ should be included in the link. The native linker uses the loader
+ symbols, not the normal symbol table, so we do too. */
+
+static bfd_boolean
+xcoff_link_check_dynamic_ar_symbols (bfd *abfd,
+ struct bfd_link_info *info,
+ bfd_boolean *pneeded)
+{
+ asection *lsec;
+ bfd_byte *contents;
+ struct internal_ldhdr ldhdr;
+ const char *strings;
+ bfd_byte *elsym, *elsymend;
+
+ *pneeded = FALSE;
- /* Read in the .loader section. FIXME: We should really use the
- o_snloader field in the a.out header, rather than grabbing the
- section by name. */
lsec = bfd_get_section_by_name (abfd, ".loader");
if (lsec == NULL)
- {
- (*_bfd_error_handler)
- (_("%s: dynamic object with no .loader section"),
- bfd_get_filename (abfd));
- bfd_set_error (bfd_error_no_symbols);
- return FALSE;
- }
-
+ /* There are no symbols, so don't try to include it. */
+ return TRUE;
if (! xcoff_get_section_contents (abfd, lsec))
return FALSE;
contents = coff_section_data (abfd, lsec)->contents;
- /* Remove the sections from this object, so that they do not get
- included in the link. */
- bfd_section_list_clear (abfd);
-
bfd_xcoff_swap_ldhdr_in (abfd, contents, &ldhdr);
strings = (char *) contents + ldhdr.l_stoff;
- elsym = contents + bfd_xcoff_loader_symbol_offset(abfd, &ldhdr);
-
- elsymend = elsym + ldhdr.l_nsyms * bfd_xcoff_ldsymsz(abfd);
+ elsym = contents + bfd_xcoff_loader_symbol_offset (abfd, &ldhdr);
- for (; elsym < elsymend; elsym += bfd_xcoff_ldsymsz(abfd))
+ elsymend = elsym + ldhdr.l_nsyms * bfd_xcoff_ldsymsz (abfd);
+ for (; elsym < elsymend; elsym += bfd_xcoff_ldsymsz (abfd))
{
struct internal_ldsym ldsym;
char nambuf[SYMNMLEN + 1];
const char *name;
- struct xcoff_link_hash_entry *h;
+ struct bfd_link_hash_entry *h;
bfd_xcoff_swap_ldsym_in (abfd, elsym, &ldsym);
name = nambuf;
}
- /* Normally we could not call xcoff_link_hash_lookup in an add
- symbols routine, since we might not be using an XCOFF hash
- table. However, we verified above that we are using an XCOFF
- hash table. */
-
- h = xcoff_link_hash_lookup (xcoff_hash_table (info), name, TRUE,
- TRUE, TRUE);
- if (h == NULL)
- return FALSE;
-
- h->flags |= XCOFF_DEF_DYNAMIC;
-
- /* If the symbol is undefined, and the BFD it was found in is
- not a dynamic object, change the BFD to this dynamic object,
- so that we can get the correct import file ID. */
- if ((h->root.type == bfd_link_hash_undefined
- || h->root.type == bfd_link_hash_undefweak)
- && (h->root.u.undef.abfd == NULL
- || (h->root.u.undef.abfd->flags & DYNAMIC) == 0))
- h->root.u.undef.abfd = abfd;
+ h = bfd_link_hash_lookup (info->hash, name, FALSE, FALSE, TRUE);
- if (h->root.type == bfd_link_hash_new)
+ /* We are only interested in symbols that are currently
+ undefined. At this point we know that we are using an XCOFF
+ hash table. */
+ if (h != NULL
+ && h->type == bfd_link_hash_undefined
+ && (((struct xcoff_link_hash_entry *) h)->flags
+ & XCOFF_DEF_DYNAMIC) == 0)
{
- h->root.type = bfd_link_hash_undefined;
- h->root.u.undef.abfd = abfd;
- /* We do not want to add this to the undefined symbol list. */
+ if (! (*info->callbacks->add_archive_element) (info, abfd, name))
+ return FALSE;
+ *pneeded = TRUE;
+ return TRUE;
}
+ }
- if (h->smclas == XMC_UA
- || h->root.type == bfd_link_hash_undefined
- || h->root.type == bfd_link_hash_undefweak)
- h->smclas = ldsym.l_smclas;
+ /* We do not need this shared object. */
+ if (contents != NULL && ! coff_section_data (abfd, lsec)->keep_contents)
+ {
+ free (coff_section_data (abfd, lsec)->contents);
+ coff_section_data (abfd, lsec)->contents = NULL;
+ }
- /* Unless this is an XMC_XO symbol, we don't bother to actually
- define it, since we don't have a section to put it in anyhow.
- Instead, the relocation routines handle the DEF_DYNAMIC flag
- correctly. */
+ return TRUE;
+}
- if (h->smclas == XMC_XO
- && (h->root.type == bfd_link_hash_undefined
- || h->root.type == bfd_link_hash_undefweak))
- {
- /* This symbol has an absolute value. */
- h->root.type = bfd_link_hash_defined;
- h->root.u.def.section = bfd_abs_section_ptr;
- h->root.u.def.value = ldsym.l_value;
- }
+/* Look through the symbols to see if this object file should be
+ included in the link. */
- /* If this symbol defines a function descriptor, then it
- implicitly defines the function code as well. */
- if (h->smclas == XMC_DS
- || (h->smclas == XMC_XO && name[0] != '.'))
- h->flags |= XCOFF_DESCRIPTOR;
- if ((h->flags & XCOFF_DESCRIPTOR) != 0)
- {
- struct xcoff_link_hash_entry *hds;
+static bfd_boolean
+xcoff_link_check_ar_symbols (bfd *abfd,
+ struct bfd_link_info *info,
+ bfd_boolean *pneeded)
+{
+ bfd_size_type symesz;
+ bfd_byte *esym;
+ bfd_byte *esym_end;
- hds = h->descriptor;
- if (hds == NULL)
- {
- char *dsnm;
+ *pneeded = FALSE;
- dsnm = bfd_malloc ((bfd_size_type) strlen (name) + 2);
- if (dsnm == NULL)
- return FALSE;
- dsnm[0] = '.';
- strcpy (dsnm + 1, name);
- hds = xcoff_link_hash_lookup (xcoff_hash_table (info), dsnm,
- TRUE, TRUE, TRUE);
- free (dsnm);
- if (hds == NULL)
- return FALSE;
+ if ((abfd->flags & DYNAMIC) != 0
+ && ! info->static_link
+ && info->hash->creator == abfd->xvec)
+ return xcoff_link_check_dynamic_ar_symbols (abfd, info, pneeded);
- if (hds->root.type == bfd_link_hash_new)
- {
- hds->root.type = bfd_link_hash_undefined;
- hds->root.u.undef.abfd = abfd;
- /* We do not want to add this to the undefined
- symbol list. */
- }
+ symesz = bfd_coff_symesz (abfd);
+ esym = (bfd_byte *) obj_coff_external_syms (abfd);
+ esym_end = esym + obj_raw_syment_count (abfd) * symesz;
+ while (esym < esym_end)
+ {
+ struct internal_syment sym;
- hds->descriptor = h;
- h->descriptor = hds;
- }
+ bfd_coff_swap_sym_in (abfd, (void *) esym, (void *) &sym);
- hds->flags |= XCOFF_DEF_DYNAMIC;
- if (hds->smclas == XMC_UA)
- hds->smclas = XMC_PR;
+ if (sym.n_sclass == C_EXT && sym.n_scnum != N_UNDEF)
+ {
+ const char *name;
+ char buf[SYMNMLEN + 1];
+ struct bfd_link_hash_entry *h;
- /* An absolute symbol appears to actually define code, not a
- function descriptor. This is how some math functions are
- implemented on AIX 4.1. */
- if (h->smclas == XMC_XO
- && (hds->root.type == bfd_link_hash_undefined
- || hds->root.type == bfd_link_hash_undefweak))
+ /* This symbol is externally visible, and is defined by this
+ object file. */
+ name = _bfd_coff_internal_syment_name (abfd, &sym, buf);
+
+ if (name == NULL)
+ return FALSE;
+ h = bfd_link_hash_lookup (info->hash, name, FALSE, FALSE, TRUE);
+
+ /* We are only interested in symbols that are currently
+ undefined. If a symbol is currently known to be common,
+ XCOFF linkers do not bring in an object file which
+ defines it. We also don't bring in symbols to satisfy
+ undefined references in shared objects. */
+ if (h != NULL
+ && h->type == bfd_link_hash_undefined
+ && (info->hash->creator != abfd->xvec
+ || (((struct xcoff_link_hash_entry *) h)->flags
+ & XCOFF_DEF_DYNAMIC) == 0))
{
- hds->smclas = XMC_XO;
- hds->root.type = bfd_link_hash_defined;
- hds->root.u.def.section = bfd_abs_section_ptr;
- hds->root.u.def.value = ldsym.l_value;
+ if (! (*info->callbacks->add_archive_element) (info, abfd, name))
+ return FALSE;
+ *pneeded = TRUE;
+ return TRUE;
}
}
- }
- if (contents != NULL && ! coff_section_data (abfd, lsec)->keep_contents)
- {
- free (coff_section_data (abfd, lsec)->contents);
- coff_section_data (abfd, lsec)->contents = NULL;
+ esym += (sym.n_numaux + 1) * symesz;
}
- /* Record this file in the import files. */
+ /* We do not need this object file. */
+ return TRUE;
+}
- n = ((struct xcoff_import_file *)
- bfd_alloc (abfd, (bfd_size_type) sizeof (struct xcoff_import_file)));
- if (n == NULL)
+/* Check a single archive element to see if we need to include it in
+ the link. *PNEEDED is set according to whether this element is
+ needed in the link or not. This is called via
+ _bfd_generic_link_add_archive_symbols. */
+
+static bfd_boolean
+xcoff_link_check_archive_element (bfd *abfd,
+ struct bfd_link_info *info,
+ bfd_boolean *pneeded)
+{
+ if (! _bfd_coff_get_external_symbols (abfd))
return FALSE;
- n->next = NULL;
- /* For some reason, the path entry in the import file list for a
- shared object appears to always be empty. The file name is the
- base name. */
- n->path = "";
- if (abfd->my_archive == NULL)
+ if (! xcoff_link_check_ar_symbols (abfd, info, pneeded))
+ return FALSE;
+
+ if (*pneeded)
{
- bname = bfd_get_filename (abfd);
- mname = "";
+ if (! xcoff_link_add_symbols (abfd, info))
+ return FALSE;
}
- else
+
+ if (! info->keep_memory || ! *pneeded)
{
- bname = bfd_get_filename (abfd->my_archive);
- mname = bfd_get_filename (abfd);
+ if (! _bfd_coff_free_symbols (abfd))
+ return FALSE;
}
- s = strrchr (bname, '/');
- if (s != NULL)
- bname = s + 1;
- n->file = bname;
- n->member = mname;
- /* We start c at 1 because the first import file number is reserved
- for LIBPATH. */
- for (pp = &xcoff_hash_table (info)->imports, c = 1;
- *pp != NULL;
- pp = &(*pp)->next, ++c)
- ;
- *pp = n;
+ return TRUE;
+}
- xcoff_data (abfd)->import_file_id = c;
+/* Given an XCOFF BFD, add symbols to the global hash table as
+ appropriate. */
- return TRUE;
+bfd_boolean
+_bfd_xcoff_bfd_link_add_symbols (bfd *abfd, struct bfd_link_info *info)
+{
+ switch (bfd_get_format (abfd))
+ {
+ case bfd_object:
+ return xcoff_link_add_object_symbols (abfd, info);
+
+ case bfd_archive:
+ /* If the archive has a map, do the usual search. We then need
+ to check the archive for dynamic objects, because they may not
+ appear in the archive map even though they should, perhaps, be
+ included. If the archive has no map, we just consider each object
+ file in turn, since that apparently is what the AIX native linker
+ does. */
+ if (bfd_has_map (abfd))
+ {
+ if (! (_bfd_generic_link_add_archive_symbols
+ (abfd, info, xcoff_link_check_archive_element)))
+ return FALSE;
+ }
+
+ {
+ bfd *member;
+
+ member = bfd_openr_next_archived_file (abfd, NULL);
+ while (member != NULL)
+ {
+ if (bfd_check_format (member, bfd_object)
+ && (info->hash->creator == member->xvec)
+ && (! bfd_has_map (abfd) || (member->flags & DYNAMIC) != 0))
+ {
+ bfd_boolean needed;
+
+ if (! xcoff_link_check_archive_element (member, info,
+ &needed))
+ return FALSE;
+ if (needed)
+ member->archive_pass = -1;
+ }
+ member = bfd_openr_next_archived_file (abfd, member);
+ }
+ }
+
+ return TRUE;
+
+ default:
+ bfd_set_error (bfd_error_wrong_format);
+ return FALSE;
+ }
}
\f
-/* Routines that are called after all the input files have been
- handled, but before the sections are laid out in memory. */
-
/* Mark a symbol as not being garbage, including the section in which
it is defined. */
-static INLINE bfd_boolean
-xcoff_mark_symbol (info, h)
- struct bfd_link_info *info;
- struct xcoff_link_hash_entry *h;
+static inline bfd_boolean
+xcoff_mark_symbol (struct bfd_link_info *info, struct xcoff_link_hash_entry *h)
{
-
if ((h->flags & XCOFF_MARK) != 0)
return TRUE;
section. */
static bfd_boolean
-xcoff_mark (info, sec)
- struct bfd_link_info *info;
- asection *sec;
+xcoff_mark (struct bfd_link_info *info, asection *sec)
{
if (bfd_is_abs_section (sec)
|| (sec->flags & SEC_MARK) != 0)
&& coff_section_data (sec->owner, sec) != NULL
&& xcoff_section_data (sec->owner, sec) != NULL)
{
- register struct xcoff_link_hash_entry **hp, **hpend;
+ struct xcoff_link_hash_entry **hp, **hpend;
struct internal_reloc *rel, *relend;
/* Mark all the symbols in this section. */
-
hp = (obj_xcoff_sym_hashes (sec->owner)
+ xcoff_section_data (sec->owner, sec)->first_symndx);
hpend = (obj_xcoff_sym_hashes (sec->owner)
+ xcoff_section_data (sec->owner, sec)->last_symndx);
for (; hp < hpend; hp++)
{
- register struct xcoff_link_hash_entry *h;
+ struct xcoff_link_hash_entry *h;
h = *hp;
if (h != NULL
}
/* Look through the section relocs. */
-
if ((sec->flags & SEC_RELOC) != 0
&& sec->reloc_count > 0)
{
rel = xcoff_read_internal_relocs (sec->owner, sec, TRUE,
- (bfd_byte *) NULL, FALSE,
- (struct internal_reloc *) NULL);
+ NULL, FALSE, NULL);
if (rel == NULL)
return FALSE;
relend = rel + sec->reloc_count;
return TRUE;
}
+/* Routines that are called after all the input files have been
+ handled, but before the sections are laid out in memory. */
+
/* The sweep phase of garbage collection. Remove all garbage
sections. */
static void
-xcoff_sweep (info)
- struct bfd_link_info *info;
+xcoff_sweep (struct bfd_link_info *info)
{
bfd *sub;
correct csect length. */
bfd_boolean
-bfd_xcoff_link_record_set (output_bfd, info, harg, size)
- bfd *output_bfd;
- struct bfd_link_info *info;
- struct bfd_link_hash_entry *harg;
- bfd_size_type size;
+bfd_xcoff_link_record_set (bfd *output_bfd,
+ struct bfd_link_info *info,
+ struct bfd_link_hash_entry *harg,
+ bfd_size_type size)
{
struct xcoff_link_hash_entry *h = (struct xcoff_link_hash_entry *) harg;
struct xcoff_link_size_list *n;
/* This will hardly ever be called. I don't want to burn four bytes
per global symbol, so instead the size is kept on a linked list
attached to the hash table. */
-
- amt = sizeof (struct xcoff_link_size_list);
- n = (struct xcoff_link_size_list *) bfd_alloc (output_bfd, amt);
+ amt = sizeof (* n);
+ n = bfd_alloc (output_bfd, amt);
if (n == NULL)
return FALSE;
n->next = xcoff_hash_table (info)->size_list;
/* Import a symbol. */
bfd_boolean
-bfd_xcoff_import_symbol (output_bfd, info, harg, val, imppath, impfile,
- impmember, syscall_flag)
- bfd *output_bfd;
- struct bfd_link_info *info;
- struct bfd_link_hash_entry *harg;
- bfd_vma val;
- const char *imppath;
- const char *impfile;
- const char *impmember;
- unsigned int syscall_flag;
+bfd_xcoff_import_symbol (bfd *output_bfd,
+ struct bfd_link_info *info,
+ struct bfd_link_hash_entry *harg,
+ bfd_vma val,
+ const char *imppath,
+ const char *impfile,
+ const char *impmember,
+ unsigned int syscall_flag)
{
struct xcoff_link_hash_entry *h = (struct xcoff_link_hash_entry *) harg;
if (*pp == NULL)
{
struct xcoff_import_file *n;
- bfd_size_type amt = sizeof (struct xcoff_import_file);
+ bfd_size_type amt = sizeof (* n);
- n = (struct xcoff_import_file *) bfd_alloc (output_bfd, amt);
+ n = bfd_alloc (output_bfd, amt);
if (n == NULL)
return FALSE;
n->next = NULL;
/* Export a symbol. */
bfd_boolean
-bfd_xcoff_export_symbol (output_bfd, info, harg)
- bfd *output_bfd;
- struct bfd_link_info *info;
- struct bfd_link_hash_entry *harg;
+bfd_xcoff_export_symbol (bfd *output_bfd,
+ struct bfd_link_info *info,
+ struct bfd_link_hash_entry *harg)
{
struct xcoff_link_hash_entry *h = (struct xcoff_link_hash_entry *) harg;
struct xcoff_link_hash_entry *hfn;
bfd_size_type amt = strlen (h->root.root.string) + 2;
- fnname = (char *) bfd_malloc (amt);
+ fnname = bfd_malloc (amt);
if (fnname == NULL)
return FALSE;
fnname[0] = '.';
and destructors. */
bfd_boolean
-bfd_xcoff_link_count_reloc (output_bfd, info, name)
- bfd *output_bfd;
- struct bfd_link_info *info;
- const char *name;
+bfd_xcoff_link_count_reloc (bfd *output_bfd,
+ struct bfd_link_info *info,
+ const char *name)
{
struct xcoff_link_hash_entry *h;
assigns a value. */
bfd_boolean
-bfd_xcoff_record_link_assignment (output_bfd, info, name)
- bfd *output_bfd;
- struct bfd_link_info *info;
- const char *name;
+bfd_xcoff_record_link_assignment (bfd *output_bfd,
+ struct bfd_link_info *info,
+ const char *name)
{
struct xcoff_link_hash_entry *h;
return TRUE;
}
-/* Build the .loader section. This is called by the XCOFF linker
- emulation before_allocation routine. We must set the size of the
- .loader section before the linker lays out the output file.
- LIBPATH is the library path to search for shared objects; this is
- normally built from the -L arguments passed to the linker. ENTRY
- is the name of the entry point symbol (the -e linker option).
- FILE_ALIGN is the alignment to use for sections within the file
- (the -H linker option). MAXSTACK is the maximum stack size (the
- -bmaxstack linker option). MAXDATA is the maximum data size (the
- -bmaxdata linker option). GC is whether to do garbage collection
- (the -bgc linker option). MODTYPE is the module type (the
- -bmodtype linker option). TEXTRO is whether the text section must
- be read only (the -btextro linker option). EXPORT_DEFINEDS is
- whether all defined symbols should be exported (the -unix linker
- option). SPECIAL_SECTIONS is set by this routine to csects with
- magic names like _end. */
+/* Add a symbol to the .loader symbols, if necessary. */
-bfd_boolean
-bfd_xcoff_size_dynamic_sections (output_bfd, info, libpath, entry,
- file_align, maxstack, maxdata, gc,
- modtype, textro, export_defineds,
- special_sections, rtld)
- bfd *output_bfd;
- struct bfd_link_info *info;
- const char *libpath;
- const char *entry;
- unsigned long file_align;
- unsigned long maxstack;
- unsigned long maxdata;
- bfd_boolean gc;
- int modtype;
- bfd_boolean textro;
- bfd_boolean export_defineds;
- asection **special_sections;
- bfd_boolean rtld;
+static bfd_boolean
+xcoff_build_ldsyms (struct xcoff_link_hash_entry *h, void * p)
{
- struct xcoff_link_hash_entry *hentry;
- asection *lsec;
- struct xcoff_loader_info ldinfo;
- int i;
- size_t impsize, impcount;
- struct xcoff_import_file *fl;
- struct internal_ldhdr *ldhdr;
- bfd_size_type stoff;
- register char *out;
- asection *sec;
- bfd *sub;
- struct bfd_strtab_hash *debug_strtab;
- bfd_byte *debug_contents = NULL;
+ struct xcoff_loader_info *ldinfo = (struct xcoff_loader_info *) p;
bfd_size_type amt;
- if (bfd_get_flavour (output_bfd) != bfd_target_xcoff_flavour)
- {
- for (i = 0; i < XCOFF_NUMBER_OF_SPECIAL_SECTIONS; i++)
- special_sections[i] = NULL;
- return TRUE;
- }
-
- ldinfo.failed = FALSE;
- ldinfo.output_bfd = output_bfd;
- ldinfo.info = info;
- ldinfo.export_defineds = export_defineds;
- ldinfo.ldsym_count = 0;
- ldinfo.string_size = 0;
- ldinfo.strings = NULL;
- ldinfo.string_alc = 0;
-
- xcoff_data (output_bfd)->maxstack = maxstack;
- xcoff_data (output_bfd)->maxdata = maxdata;
- xcoff_data (output_bfd)->modtype = modtype;
-
- xcoff_hash_table (info)->file_align = file_align;
- xcoff_hash_table (info)->textro = textro;
-
- hentry = NULL;
- if (entry != NULL)
- {
- hentry = xcoff_link_hash_lookup (xcoff_hash_table (info), entry,
- FALSE, FALSE, TRUE);
- if (hentry != NULL)
- hentry->flags |= XCOFF_ENTRY;
- }
-
- /* __rtinit */
- if (info->init_function || info->fini_function || rtld)
- {
- struct xcoff_link_hash_entry *hsym;
- struct internal_ldsym *ldsym;
-
- hsym = xcoff_link_hash_lookup (xcoff_hash_table (info),
- "__rtinit", FALSE, FALSE, TRUE);
- if (hsym == NULL)
- {
- (*_bfd_error_handler)
- (_("error: undefined symbol __rtinit"));
- return FALSE;
- }
-
- xcoff_mark_symbol (info, hsym);
- hsym->flags |= (XCOFF_DEF_REGULAR | XCOFF_RTINIT);
-
- /* __rtinit initialized */
- amt = sizeof (struct internal_ldsym);
- ldsym = (struct internal_ldsym *) bfd_malloc (amt);
-
- ldsym->l_value = 0; /* will be filled in later */
- ldsym->l_scnum = 2; /* data section */
- ldsym->l_smtype = XTY_SD; /* csect section definition */
- ldsym->l_smclas = 5; /* .rw */
- ldsym->l_ifile = 0; /* special system loader symbol */
- ldsym->l_parm = 0; /* NA */
-
- /* Force __rtinit to be the first symbol in the loader symbol table
- See xcoff_build_ldsyms
-
- The first 3 symbol table indices are reserved to indicate the data,
- text and bss sections. */
- BFD_ASSERT (0 == ldinfo.ldsym_count);
-
- hsym->ldindx = 3;
- ldinfo.ldsym_count = 1;
- hsym->ldsym = ldsym;
+ if (h->root.type == bfd_link_hash_warning)
+ h = (struct xcoff_link_hash_entry *) h->root.u.i.link;
- if (! bfd_xcoff_put_ldsymbol_name (ldinfo.output_bfd, &ldinfo,
- hsym->ldsym, hsym->root.root.string))
- return FALSE;
+ /* __rtinit, this symbol has special handling. */
+ if (h->flags & XCOFF_RTINIT)
+ return TRUE;
- /* This symbol is written out by xcoff_write_global_symbol
- Set stuff up so xcoff_write_global_symbol logic works. */
- hsym->flags |= XCOFF_DEF_REGULAR | XCOFF_MARK;
- hsym->root.type = bfd_link_hash_defined;
- hsym->root.u.def.value = 0;
- }
+ /* If this is a final link, and the symbol was defined as a common
+ symbol in a regular object file, and there was no definition in
+ any dynamic object, then the linker will have allocated space for
+ the symbol in a common section but the XCOFF_DEF_REGULAR flag
+ will not have been set. */
+ if (h->root.type == bfd_link_hash_defined
+ && (h->flags & XCOFF_DEF_REGULAR) == 0
+ && (h->flags & XCOFF_REF_REGULAR) != 0
+ && (h->flags & XCOFF_DEF_DYNAMIC) == 0
+ && (bfd_is_abs_section (h->root.u.def.section)
+ || (h->root.u.def.section->owner->flags & DYNAMIC) == 0))
+ h->flags |= XCOFF_DEF_REGULAR;
- /* Garbage collect unused sections. */
- if (info->relocatable
- || ! gc
- || hentry == NULL
- || (hentry->root.type != bfd_link_hash_defined
- && hentry->root.type != bfd_link_hash_defweak))
+ /* If all defined symbols should be exported, mark them now. We
+ don't want to export the actual functions, just the function
+ descriptors. */
+ if (ldinfo->export_defineds
+ && (h->flags & XCOFF_DEF_REGULAR) != 0
+ && h->root.root.string[0] != '.')
{
- gc = FALSE;
- xcoff_hash_table (info)->gc = FALSE;
+ bfd_boolean export;
- /* We still need to call xcoff_mark, in order to set ldrel_count
- correctly. */
- for (sub = info->input_bfds; sub != NULL; sub = sub->link_next)
+ /* We don't export a symbol which is being defined by an object
+ included from an archive which contains a shared object. The
+ rationale is that if an archive contains both an unshared and
+ a shared object, then there must be some reason that the
+ unshared object is unshared, and we don't want to start
+ providing a shared version of it. In particular, this solves
+ a bug involving the _savefNN set of functions. gcc will call
+ those functions without providing a slot to restore the TOC,
+ so it is essential that these functions be linked in directly
+ and not from a shared object, which means that a shared
+ object which also happens to link them in must not export
+ them. This is confusing, but I haven't been able to think of
+ a different approach. Note that the symbols can, of course,
+ be exported explicitly. */
+ export = TRUE;
+ if ((h->root.type == bfd_link_hash_defined
+ || h->root.type == bfd_link_hash_defweak)
+ && h->root.u.def.section->owner != NULL
+ && h->root.u.def.section->owner->my_archive != NULL)
{
- asection *o;
+ bfd *arbfd, *member;
- for (o = sub->sections; o != NULL; o = o->next)
+ arbfd = h->root.u.def.section->owner->my_archive;
+ member = bfd_openr_next_archived_file (arbfd, NULL);
+ while (member != NULL)
{
- if ((o->flags & SEC_MARK) == 0)
+ if ((member->flags & DYNAMIC) != 0)
{
- if (! xcoff_mark (info, o))
- goto error_return;
+ export = FALSE;
+ break;
}
+ member = bfd_openr_next_archived_file (arbfd, member);
}
}
- }
- else
- {
- if (! xcoff_mark (info, hentry->root.u.def.section))
- goto error_return;
- xcoff_sweep (info);
- xcoff_hash_table (info)->gc = TRUE;
+
+ if (export)
+ h->flags |= XCOFF_EXPORT;
}
- /* Return special sections to the caller. */
- for (i = 0; i < XCOFF_NUMBER_OF_SPECIAL_SECTIONS; i++)
+ /* We don't want to garbage collect symbols which are not defined in
+ XCOFF files. This is a convenient place to mark them. */
+ if (xcoff_hash_table (ldinfo->info)->gc
+ && (h->flags & XCOFF_MARK) == 0
+ && (h->root.type == bfd_link_hash_defined
+ || h->root.type == bfd_link_hash_defweak)
+ && (h->root.u.def.section->owner == NULL
+ || (h->root.u.def.section->owner->xvec
+ != ldinfo->info->hash->creator)))
+ h->flags |= XCOFF_MARK;
+
+ /* If this symbol is called and defined in a dynamic object, or it
+ is imported, then we need to set up global linkage code for it.
+ (Unless we did garbage collection and we didn't need this
+ symbol.) */
+ if ((h->flags & XCOFF_CALLED) != 0
+ && (h->root.type == bfd_link_hash_undefined
+ || h->root.type == bfd_link_hash_undefweak)
+ && h->root.root.string[0] == '.'
+ && h->descriptor != NULL
+ && ((h->descriptor->flags & XCOFF_DEF_DYNAMIC) != 0
+ || ((h->descriptor->flags & XCOFF_IMPORT) != 0
+ && (h->descriptor->flags & XCOFF_DEF_REGULAR) == 0))
+ && (! xcoff_hash_table (ldinfo->info)->gc
+ || (h->flags & XCOFF_MARK) != 0))
{
- sec = xcoff_hash_table (info)->special_sections[i];
+ asection *sec;
+ struct xcoff_link_hash_entry *hds;
- if (sec != NULL
- && gc
- && (sec->flags & SEC_MARK) == 0)
+ sec = xcoff_hash_table (ldinfo->info)->linkage_section;
+ h->root.type = bfd_link_hash_defined;
+ h->root.u.def.section = sec;
+ h->root.u.def.value = sec->size;
+ h->smclas = XMC_GL;
+ h->flags |= XCOFF_DEF_REGULAR;
+ sec->size += bfd_xcoff_glink_code_size(ldinfo->output_bfd);
+
+ /* The global linkage code requires a TOC entry for the
+ descriptor. */
+ hds = h->descriptor;
+ BFD_ASSERT ((hds->root.type == bfd_link_hash_undefined
+ || hds->root.type == bfd_link_hash_undefweak)
+ && (hds->flags & XCOFF_DEF_REGULAR) == 0);
+ hds->flags |= XCOFF_MARK;
+ if (hds->toc_section == NULL)
{
- sec = NULL;
- }
- special_sections[i] = sec;
- }
+ int byte_size;
- if (info->input_bfds == NULL)
- {
- /* I'm not sure what to do in this bizarre case. */
- return TRUE;
- }
+ /* 32 vs 64
+ xcoff32 uses 4 bytes in the toc.
+ xcoff64 uses 8 bytes in the toc. */
+ if (bfd_xcoff_is_xcoff64 (ldinfo->output_bfd))
+ byte_size = 8;
+ else if (bfd_xcoff_is_xcoff32 (ldinfo->output_bfd))
+ byte_size = 4;
+ else
+ return FALSE;
- xcoff_link_hash_traverse (xcoff_hash_table (info), xcoff_build_ldsyms,
- (PTR) &ldinfo);
- if (ldinfo.failed)
- goto error_return;
+ hds->toc_section = xcoff_hash_table (ldinfo->info)->toc_section;
+ hds->u.toc_offset = hds->toc_section->size;
+ hds->toc_section->size += byte_size;
+ ++xcoff_hash_table (ldinfo->info)->ldrel_count;
+ ++hds->toc_section->reloc_count;
+ hds->indx = -2;
+ hds->flags |= XCOFF_SET_TOC | XCOFF_LDREL;
- /* Work out the size of the import file names. Each import file ID
- consists of three null terminated strings: the path, the file
- name, and the archive member name. The first entry in the list
- of names is the path to use to find objects, which the linker has
- passed in as the libpath argument. For some reason, the path
- entry in the other import file names appears to always be empty. */
- impsize = strlen (libpath) + 3;
- impcount = 1;
- for (fl = xcoff_hash_table (info)->imports; fl != NULL; fl = fl->next)
- {
- ++impcount;
- impsize += (strlen (fl->path)
- + strlen (fl->file)
- + strlen (fl->member)
- + 3);
+ /* We need to call xcoff_build_ldsyms recursively here,
+ because we may already have passed hds on the traversal. */
+ xcoff_build_ldsyms (hds, p);
+ }
}
- /* Set up the .loader section header. */
- ldhdr = &xcoff_hash_table (info)->ldhdr;
- ldhdr->l_version = bfd_xcoff_ldhdr_version(output_bfd);
- ldhdr->l_nsyms = ldinfo.ldsym_count;
- ldhdr->l_nreloc = xcoff_hash_table (info)->ldrel_count;
- ldhdr->l_istlen = impsize;
- ldhdr->l_nimpid = impcount;
- ldhdr->l_impoff = (bfd_xcoff_ldhdrsz(output_bfd)
- + ldhdr->l_nsyms * bfd_xcoff_ldsymsz(output_bfd)
- + ldhdr->l_nreloc * bfd_xcoff_ldrelsz(output_bfd));
- ldhdr->l_stlen = ldinfo.string_size;
- stoff = ldhdr->l_impoff + impsize;
- if (ldinfo.string_size == 0)
- ldhdr->l_stoff = 0;
- else
- ldhdr->l_stoff = stoff;
-
- /* 64 bit elements to ldhdr
- The swap out routine for 32 bit will ignore them.
- Nothing fancy, symbols come after the header and relocs come
- after symbols. */
- ldhdr->l_symoff = bfd_xcoff_ldhdrsz (output_bfd);
- ldhdr->l_rldoff = (bfd_xcoff_ldhdrsz (output_bfd)
- + ldhdr->l_nsyms * bfd_xcoff_ldsymsz (output_bfd));
+ /* If this symbol is exported, but not defined, we need to try to
+ define it. */
+ if ((h->flags & XCOFF_EXPORT) != 0
+ && (h->flags & XCOFF_IMPORT) == 0
+ && (h->flags & XCOFF_DEF_REGULAR) == 0
+ && (h->flags & XCOFF_DEF_DYNAMIC) == 0
+ && (h->root.type == bfd_link_hash_undefined
+ || h->root.type == bfd_link_hash_undefweak))
+ {
+ if ((h->flags & XCOFF_DESCRIPTOR) != 0
+ && (h->descriptor->root.type == bfd_link_hash_defined
+ || h->descriptor->root.type == bfd_link_hash_defweak))
+ {
+ asection *sec;
- /* We now know the final size of the .loader section. Allocate
- space for it. */
- lsec = xcoff_hash_table (info)->loader_section;
- lsec->size = stoff + ldhdr->l_stlen;
- lsec->contents = (bfd_byte *) bfd_zalloc (output_bfd, lsec->size);
- if (lsec->contents == NULL)
- goto error_return;
+ /* This is an undefined function descriptor associated with
+ a defined entry point. We can build up a function
+ descriptor ourselves. Believe it or not, the AIX linker
+ actually does this, and there are cases where we need to
+ do it as well. */
+ sec = xcoff_hash_table (ldinfo->info)->descriptor_section;
+ h->root.type = bfd_link_hash_defined;
+ h->root.u.def.section = sec;
+ h->root.u.def.value = sec->size;
+ h->smclas = XMC_DS;
+ h->flags |= XCOFF_DEF_REGULAR;
- /* Set up the header. */
- bfd_xcoff_swap_ldhdr_out (output_bfd, ldhdr, lsec->contents);
+ /* The size of the function descriptor depends if this is an
+ xcoff32 (12) or xcoff64 (24). */
+ sec->size +=
+ bfd_xcoff_function_descriptor_size(ldinfo->output_bfd);
- /* Set up the import file names. */
- out = (char *) lsec->contents + ldhdr->l_impoff;
- strcpy (out, libpath);
- out += strlen (libpath) + 1;
- *out++ = '\0';
- *out++ = '\0';
- for (fl = xcoff_hash_table (info)->imports; fl != NULL; fl = fl->next)
- {
- register const char *s;
+ /* A function descriptor uses two relocs: one for the
+ associated code, and one for the TOC address. */
+ xcoff_hash_table (ldinfo->info)->ldrel_count += 2;
+ sec->reloc_count += 2;
- s = fl->path;
- while ((*out++ = *s++) != '\0')
- ;
- s = fl->file;
- while ((*out++ = *s++) != '\0')
- ;
- s = fl->member;
- while ((*out++ = *s++) != '\0')
- ;
+ /* We handle writing out the contents of the descriptor in
+ xcoff_write_global_symbol. */
+ }
+ else
+ {
+ (*_bfd_error_handler)
+ (_("warning: attempt to export undefined symbol `%s'"),
+ h->root.root.string);
+ h->ldsym = NULL;
+ return TRUE;
+ }
}
- BFD_ASSERT ((bfd_size_type) ((bfd_byte *) out - lsec->contents) == stoff);
-
- /* Set up the symbol string table. */
- if (ldinfo.string_size > 0)
+ /* If this is still a common symbol, and it wasn't garbage
+ collected, we need to actually allocate space for it in the .bss
+ section. */
+ if (h->root.type == bfd_link_hash_common
+ && (! xcoff_hash_table (ldinfo->info)->gc
+ || (h->flags & XCOFF_MARK) != 0)
+ && h->root.u.c.p->section->size == 0)
{
- memcpy (out, ldinfo.strings, ldinfo.string_size);
- free (ldinfo.strings);
- ldinfo.strings = NULL;
+ BFD_ASSERT (bfd_is_com_section (h->root.u.c.p->section));
+ h->root.u.c.p->section->size = h->root.u.c.size;
}
- /* We can't set up the symbol table or the relocs yet, because we
- don't yet know the final position of the various sections. The
- .loader symbols are written out when the corresponding normal
- symbols are written out in xcoff_link_input_bfd or
- xcoff_write_global_symbol. The .loader relocs are written out
- when the corresponding normal relocs are handled in
- xcoff_link_input_bfd.
- */
+ /* We need to add a symbol to the .loader section if it is mentioned
+ in a reloc which we are copying to the .loader section and it was
+ not defined or common, or if it is the entry point, or if it is
+ being exported. */
- /* Allocate space for the magic sections. */
- sec = xcoff_hash_table (info)->linkage_section;
- if (sec->size > 0)
- {
- sec->contents = (bfd_byte *) bfd_zalloc (output_bfd, sec->size);
- if (sec->contents == NULL)
- goto error_return;
- }
- sec = xcoff_hash_table (info)->toc_section;
- if (sec->size > 0)
+ if (((h->flags & XCOFF_LDREL) == 0
+ || h->root.type == bfd_link_hash_defined
+ || h->root.type == bfd_link_hash_defweak
+ || h->root.type == bfd_link_hash_common)
+ && (h->flags & XCOFF_ENTRY) == 0
+ && (h->flags & XCOFF_EXPORT) == 0)
{
- sec->contents = (bfd_byte *) bfd_zalloc (output_bfd, sec->size);
- if (sec->contents == NULL)
- goto error_return;
+ h->ldsym = NULL;
+ return TRUE;
}
- sec = xcoff_hash_table (info)->descriptor_section;
- if (sec->size > 0)
+
+ /* We don't need to add this symbol if we did garbage collection and
+ we did not mark this symbol. */
+ if (xcoff_hash_table (ldinfo->info)->gc
+ && (h->flags & XCOFF_MARK) == 0)
{
- sec->contents = (bfd_byte *) bfd_zalloc (output_bfd, sec->size);
- if (sec->contents == NULL)
- goto error_return;
+ h->ldsym = NULL;
+ return TRUE;
}
- /* Now that we've done garbage collection, figure out the contents
- of the .debug section. */
- debug_strtab = xcoff_hash_table (info)->debug_strtab;
+ /* We may have already processed this symbol due to the recursive
+ call above. */
+ if ((h->flags & XCOFF_BUILT_LDSYM) != 0)
+ return TRUE;
- for (sub = info->input_bfds; sub != NULL; sub = sub->link_next)
+ /* We need to add this symbol to the .loader symbols. */
+
+ BFD_ASSERT (h->ldsym == NULL);
+ amt = sizeof (struct internal_ldsym);
+ h->ldsym = bfd_zalloc (ldinfo->output_bfd, amt);
+ if (h->ldsym == NULL)
{
- asection *subdeb;
- bfd_size_type symcount;
- unsigned long *debug_index;
- asection **csectpp;
- bfd_byte *esym, *esymend;
- bfd_size_type symesz;
-
- if (sub->xvec != info->hash->creator)
- continue;
- subdeb = bfd_get_section_by_name (sub, ".debug");
- if (subdeb == NULL || subdeb->size == 0)
- continue;
-
- if (info->strip == strip_all
- || info->strip == strip_debugger
- || info->discard == discard_all)
- {
- subdeb->size = 0;
- continue;
- }
+ ldinfo->failed = TRUE;
+ return FALSE;
+ }
- if (! _bfd_coff_get_external_symbols (sub))
- goto error_return;
+ if ((h->flags & XCOFF_IMPORT) != 0)
+ h->ldsym->l_ifile = h->ldindx;
- symcount = obj_raw_syment_count (sub);
- debug_index = ((unsigned long *)
- bfd_zalloc (sub, symcount * sizeof (unsigned long)));
- if (debug_index == NULL)
- goto error_return;
- xcoff_data (sub)->debug_indices = debug_index;
+ /* The first 3 symbol table indices are reserved to indicate the
+ data, text and bss sections. */
+ h->ldindx = ldinfo->ldsym_count + 3;
- /* Grab the contents of the .debug section. We use malloc and
- copy the names into the debug stringtab, rather than
- bfd_alloc, because I expect that, when linking many files
- together, many of the strings will be the same. Storing the
- strings in the hash table should save space in this case. */
- if (!bfd_malloc_and_get_section (sub, subdeb, &debug_contents))
- goto error_return;
+ ++ldinfo->ldsym_count;
- csectpp = xcoff_data (sub)->csects;
+ if (! bfd_xcoff_put_ldsymbol_name (ldinfo->output_bfd, ldinfo,
+ h->ldsym, h->root.root.string))
+ return FALSE;
- /* Dynamic object do not have csectpp's. */
- if (NULL != csectpp)
- {
- symesz = bfd_coff_symesz (sub);
- esym = (bfd_byte *) obj_coff_external_syms (sub);
- esymend = esym + symcount * symesz;
+ h->flags |= XCOFF_BUILT_LDSYM;
- while (esym < esymend)
- {
- struct internal_syment sym;
+ return TRUE;
+}
+/* Build the .loader section. This is called by the XCOFF linker
+ emulation before_allocation routine. We must set the size of the
+ .loader section before the linker lays out the output file.
+ LIBPATH is the library path to search for shared objects; this is
+ normally built from the -L arguments passed to the linker. ENTRY
+ is the name of the entry point symbol (the -e linker option).
+ FILE_ALIGN is the alignment to use for sections within the file
+ (the -H linker option). MAXSTACK is the maximum stack size (the
+ -bmaxstack linker option). MAXDATA is the maximum data size (the
+ -bmaxdata linker option). GC is whether to do garbage collection
+ (the -bgc linker option). MODTYPE is the module type (the
+ -bmodtype linker option). TEXTRO is whether the text section must
+ be read only (the -btextro linker option). EXPORT_DEFINEDS is
+ whether all defined symbols should be exported (the -unix linker
+ option). SPECIAL_SECTIONS is set by this routine to csects with
+ magic names like _end. */
- bfd_coff_swap_sym_in (sub, (PTR) esym, (PTR) &sym);
+bfd_boolean
+bfd_xcoff_size_dynamic_sections (bfd *output_bfd,
+ struct bfd_link_info *info,
+ const char *libpath,
+ const char *entry,
+ unsigned long file_align,
+ unsigned long maxstack,
+ unsigned long maxdata,
+ bfd_boolean gc,
+ int modtype,
+ bfd_boolean textro,
+ bfd_boolean export_defineds,
+ asection **special_sections,
+ bfd_boolean rtld)
+{
+ struct xcoff_link_hash_entry *hentry;
+ asection *lsec;
+ struct xcoff_loader_info ldinfo;
+ int i;
+ size_t impsize, impcount;
+ struct xcoff_import_file *fl;
+ struct internal_ldhdr *ldhdr;
+ bfd_size_type stoff;
+ char *out;
+ asection *sec;
+ bfd *sub;
+ struct bfd_strtab_hash *debug_strtab;
+ bfd_byte *debug_contents = NULL;
+ bfd_size_type amt;
- *debug_index = (unsigned long) -1;
+ if (bfd_get_flavour (output_bfd) != bfd_target_xcoff_flavour)
+ {
+ for (i = 0; i < XCOFF_NUMBER_OF_SPECIAL_SECTIONS; i++)
+ special_sections[i] = NULL;
+ return TRUE;
+ }
- if (sym._n._n_n._n_zeroes == 0
- && *csectpp != NULL
- && (! gc
- || ((*csectpp)->flags & SEC_MARK) != 0
- || *csectpp == bfd_abs_section_ptr)
- && bfd_coff_symname_in_debug (sub, &sym))
- {
- char *name;
- bfd_size_type indx;
+ ldinfo.failed = FALSE;
+ ldinfo.output_bfd = output_bfd;
+ ldinfo.info = info;
+ ldinfo.export_defineds = export_defineds;
+ ldinfo.ldsym_count = 0;
+ ldinfo.string_size = 0;
+ ldinfo.strings = NULL;
+ ldinfo.string_alc = 0;
- name = (char *) debug_contents + sym._n._n_n._n_offset;
- indx = _bfd_stringtab_add (debug_strtab, name, TRUE, TRUE);
- if (indx == (bfd_size_type) -1)
- goto error_return;
- *debug_index = indx;
- }
+ xcoff_data (output_bfd)->maxstack = maxstack;
+ xcoff_data (output_bfd)->maxdata = maxdata;
+ xcoff_data (output_bfd)->modtype = modtype;
- esym += (sym.n_numaux + 1) * symesz;
- csectpp += sym.n_numaux + 1;
- debug_index += sym.n_numaux + 1;
- }
- }
+ xcoff_hash_table (info)->file_align = file_align;
+ xcoff_hash_table (info)->textro = textro;
- free (debug_contents);
- debug_contents = NULL;
+ hentry = NULL;
+ if (entry != NULL)
+ {
+ hentry = xcoff_link_hash_lookup (xcoff_hash_table (info), entry,
+ FALSE, FALSE, TRUE);
+ if (hentry != NULL)
+ hentry->flags |= XCOFF_ENTRY;
+ }
- /* Clear the size of subdeb, so that it is not included directly
- in the output file. */
- subdeb->size = 0;
+ /* __rtinit */
+ if (info->init_function || info->fini_function || rtld)
+ {
+ struct xcoff_link_hash_entry *hsym;
+ struct internal_ldsym *ldsym;
- if (! info->keep_memory)
+ hsym = xcoff_link_hash_lookup (xcoff_hash_table (info),
+ "__rtinit", FALSE, FALSE, TRUE);
+ if (hsym == NULL)
{
- if (! _bfd_coff_free_symbols (sub))
- goto error_return;
+ (*_bfd_error_handler)
+ (_("error: undefined symbol __rtinit"));
+ return FALSE;
}
- }
- if (info->strip != strip_all)
- xcoff_hash_table (info)->debug_section->size =
- _bfd_stringtab_size (debug_strtab);
+ xcoff_mark_symbol (info, hsym);
+ hsym->flags |= (XCOFF_DEF_REGULAR | XCOFF_RTINIT);
- return TRUE;
+ /* __rtinit initialized. */
+ amt = sizeof (* ldsym);
+ ldsym = bfd_malloc (amt);
- error_return:
- if (ldinfo.strings != NULL)
- free (ldinfo.strings);
- if (debug_contents != NULL)
- free (debug_contents);
- return FALSE;
-}
+ ldsym->l_value = 0; /* Will be filled in later. */
+ ldsym->l_scnum = 2; /* Data section. */
+ ldsym->l_smtype = XTY_SD; /* Csect section definition. */
+ ldsym->l_smclas = 5; /* .rw. */
+ ldsym->l_ifile = 0; /* Special system loader symbol. */
+ ldsym->l_parm = 0; /* NA. */
-bfd_boolean
-bfd_xcoff_link_generate_rtinit (abfd, init, fini, rtld)
- bfd *abfd;
- const char *init;
- const char *fini;
- bfd_boolean rtld;
-{
- struct bfd_in_memory *bim;
+ /* Force __rtinit to be the first symbol in the loader symbol table
+ See xcoff_build_ldsyms
- bim = ((struct bfd_in_memory *)
- bfd_malloc ((bfd_size_type) sizeof (struct bfd_in_memory)));
- if (bim == NULL)
- return FALSE;
+ The first 3 symbol table indices are reserved to indicate the data,
+ text and bss sections. */
+ BFD_ASSERT (0 == ldinfo.ldsym_count);
- bim->size = 0;
- bim->buffer = 0;
+ hsym->ldindx = 3;
+ ldinfo.ldsym_count = 1;
+ hsym->ldsym = ldsym;
- abfd->link_next = 0;
- abfd->format = bfd_object;
- abfd->iostream = (PTR) bim;
- abfd->flags = BFD_IN_MEMORY;
- abfd->direction = write_direction;
- abfd->where = 0;
+ if (! bfd_xcoff_put_ldsymbol_name (ldinfo.output_bfd, &ldinfo,
+ hsym->ldsym, hsym->root.root.string))
+ return FALSE;
- if (! bfd_xcoff_generate_rtinit (abfd, init, fini, rtld))
- return FALSE;
+ /* This symbol is written out by xcoff_write_global_symbol
+ Set stuff up so xcoff_write_global_symbol logic works. */
+ hsym->flags |= XCOFF_DEF_REGULAR | XCOFF_MARK;
+ hsym->root.type = bfd_link_hash_defined;
+ hsym->root.u.def.value = 0;
+ }
- /* need to reset to unknown or it will not be read back in correctly */
- abfd->format = bfd_unknown;
- abfd->direction = read_direction;
- abfd->where = 0;
+ /* Garbage collect unused sections. */
+ if (info->relocatable
+ || ! gc
+ || hentry == NULL
+ || (hentry->root.type != bfd_link_hash_defined
+ && hentry->root.type != bfd_link_hash_defweak))
+ {
+ gc = FALSE;
+ xcoff_hash_table (info)->gc = FALSE;
- return TRUE;
-}
+ /* We still need to call xcoff_mark, in order to set ldrel_count
+ correctly. */
+ for (sub = info->input_bfds; sub != NULL; sub = sub->link_next)
+ {
+ asection *o;
+ for (o = sub->sections; o != NULL; o = o->next)
+ {
+ if ((o->flags & SEC_MARK) == 0)
+ {
+ if (! xcoff_mark (info, o))
+ goto error_return;
+ }
+ }
+ }
+ }
+ else
+ {
+ if (! xcoff_mark (info, hentry->root.u.def.section))
+ goto error_return;
+ xcoff_sweep (info);
+ xcoff_hash_table (info)->gc = TRUE;
+ }
-/* Add a symbol to the .loader symbols, if necessary. */
+ /* Return special sections to the caller. */
+ for (i = 0; i < XCOFF_NUMBER_OF_SPECIAL_SECTIONS; i++)
+ {
+ sec = xcoff_hash_table (info)->special_sections[i];
-static bfd_boolean
-xcoff_build_ldsyms (h, p)
- struct xcoff_link_hash_entry *h;
- PTR p;
-{
- struct xcoff_loader_info *ldinfo = (struct xcoff_loader_info *) p;
- bfd_size_type amt;
+ if (sec != NULL
+ && gc
+ && (sec->flags & SEC_MARK) == 0)
+ sec = NULL;
- if (h->root.type == bfd_link_hash_warning)
- h = (struct xcoff_link_hash_entry *) h->root.u.i.link;
+ special_sections[i] = sec;
+ }
- /* __rtinit, this symbol has special handling. */
- if (h->flags & XCOFF_RTINIT)
- return TRUE;
+ if (info->input_bfds == NULL)
+ /* I'm not sure what to do in this bizarre case. */
+ return TRUE;
- /* If this is a final link, and the symbol was defined as a common
- symbol in a regular object file, and there was no definition in
- any dynamic object, then the linker will have allocated space for
- the symbol in a common section but the XCOFF_DEF_REGULAR flag
- will not have been set. */
- if (h->root.type == bfd_link_hash_defined
- && (h->flags & XCOFF_DEF_REGULAR) == 0
- && (h->flags & XCOFF_REF_REGULAR) != 0
- && (h->flags & XCOFF_DEF_DYNAMIC) == 0
- && (bfd_is_abs_section (h->root.u.def.section)
- || (h->root.u.def.section->owner->flags & DYNAMIC) == 0))
- h->flags |= XCOFF_DEF_REGULAR;
+ xcoff_link_hash_traverse (xcoff_hash_table (info), xcoff_build_ldsyms,
+ (void *) &ldinfo);
+ if (ldinfo.failed)
+ goto error_return;
- /* If all defined symbols should be exported, mark them now. We
- don't want to export the actual functions, just the function
- descriptors. */
- if (ldinfo->export_defineds
- && (h->flags & XCOFF_DEF_REGULAR) != 0
- && h->root.root.string[0] != '.')
+ /* Work out the size of the import file names. Each import file ID
+ consists of three null terminated strings: the path, the file
+ name, and the archive member name. The first entry in the list
+ of names is the path to use to find objects, which the linker has
+ passed in as the libpath argument. For some reason, the path
+ entry in the other import file names appears to always be empty. */
+ impsize = strlen (libpath) + 3;
+ impcount = 1;
+ for (fl = xcoff_hash_table (info)->imports; fl != NULL; fl = fl->next)
{
- bfd_boolean export;
+ ++impcount;
+ impsize += (strlen (fl->path)
+ + strlen (fl->file)
+ + strlen (fl->member)
+ + 3);
+ }
- /* We don't export a symbol which is being defined by an object
- included from an archive which contains a shared object. The
- rationale is that if an archive contains both an unshared and
- a shared object, then there must be some reason that the
- unshared object is unshared, and we don't want to start
- providing a shared version of it. In particular, this solves
- a bug involving the _savefNN set of functions. gcc will call
- those functions without providing a slot to restore the TOC,
- so it is essential that these functions be linked in directly
- and not from a shared object, which means that a shared
- object which also happens to link them in must not export
- them. This is confusing, but I haven't been able to think of
- a different approach. Note that the symbols can, of course,
- be exported explicitly. */
- export = TRUE;
- if ((h->root.type == bfd_link_hash_defined
- || h->root.type == bfd_link_hash_defweak)
- && h->root.u.def.section->owner != NULL
- && h->root.u.def.section->owner->my_archive != NULL)
- {
- bfd *arbfd, *member;
+ /* Set up the .loader section header. */
+ ldhdr = &xcoff_hash_table (info)->ldhdr;
+ ldhdr->l_version = bfd_xcoff_ldhdr_version(output_bfd);
+ ldhdr->l_nsyms = ldinfo.ldsym_count;
+ ldhdr->l_nreloc = xcoff_hash_table (info)->ldrel_count;
+ ldhdr->l_istlen = impsize;
+ ldhdr->l_nimpid = impcount;
+ ldhdr->l_impoff = (bfd_xcoff_ldhdrsz(output_bfd)
+ + ldhdr->l_nsyms * bfd_xcoff_ldsymsz(output_bfd)
+ + ldhdr->l_nreloc * bfd_xcoff_ldrelsz(output_bfd));
+ ldhdr->l_stlen = ldinfo.string_size;
+ stoff = ldhdr->l_impoff + impsize;
+ if (ldinfo.string_size == 0)
+ ldhdr->l_stoff = 0;
+ else
+ ldhdr->l_stoff = stoff;
- arbfd = h->root.u.def.section->owner->my_archive;
- member = bfd_openr_next_archived_file (arbfd, (bfd *) NULL);
- while (member != NULL)
- {
- if ((member->flags & DYNAMIC) != 0)
- {
- export = FALSE;
- break;
- }
- member = bfd_openr_next_archived_file (arbfd, member);
- }
- }
+ /* 64 bit elements to ldhdr
+ The swap out routine for 32 bit will ignore them.
+ Nothing fancy, symbols come after the header and relocs come
+ after symbols. */
+ ldhdr->l_symoff = bfd_xcoff_ldhdrsz (output_bfd);
+ ldhdr->l_rldoff = (bfd_xcoff_ldhdrsz (output_bfd)
+ + ldhdr->l_nsyms * bfd_xcoff_ldsymsz (output_bfd));
- if (export)
- h->flags |= XCOFF_EXPORT;
- }
+ /* We now know the final size of the .loader section. Allocate
+ space for it. */
+ lsec = xcoff_hash_table (info)->loader_section;
+ lsec->size = stoff + ldhdr->l_stlen;
+ lsec->contents = bfd_zalloc (output_bfd, lsec->size);
+ if (lsec->contents == NULL)
+ goto error_return;
- /* We don't want to garbage collect symbols which are not defined in
- XCOFF files. This is a convenient place to mark them. */
- if (xcoff_hash_table (ldinfo->info)->gc
- && (h->flags & XCOFF_MARK) == 0
- && (h->root.type == bfd_link_hash_defined
- || h->root.type == bfd_link_hash_defweak)
- && (h->root.u.def.section->owner == NULL
- || (h->root.u.def.section->owner->xvec
- != ldinfo->info->hash->creator)))
- h->flags |= XCOFF_MARK;
+ /* Set up the header. */
+ bfd_xcoff_swap_ldhdr_out (output_bfd, ldhdr, lsec->contents);
- /* If this symbol is called and defined in a dynamic object, or it
- is imported, then we need to set up global linkage code for it.
- (Unless we did garbage collection and we didn't need this
- symbol.) */
- if ((h->flags & XCOFF_CALLED) != 0
- && (h->root.type == bfd_link_hash_undefined
- || h->root.type == bfd_link_hash_undefweak)
- && h->root.root.string[0] == '.'
- && h->descriptor != NULL
- && ((h->descriptor->flags & XCOFF_DEF_DYNAMIC) != 0
- || ((h->descriptor->flags & XCOFF_IMPORT) != 0
- && (h->descriptor->flags & XCOFF_DEF_REGULAR) == 0))
- && (! xcoff_hash_table (ldinfo->info)->gc
- || (h->flags & XCOFF_MARK) != 0))
+ /* Set up the import file names. */
+ out = (char *) lsec->contents + ldhdr->l_impoff;
+ strcpy (out, libpath);
+ out += strlen (libpath) + 1;
+ *out++ = '\0';
+ *out++ = '\0';
+ for (fl = xcoff_hash_table (info)->imports; fl != NULL; fl = fl->next)
{
- asection *sec;
- struct xcoff_link_hash_entry *hds;
+ const char *s;
- sec = xcoff_hash_table (ldinfo->info)->linkage_section;
- h->root.type = bfd_link_hash_defined;
- h->root.u.def.section = sec;
- h->root.u.def.value = sec->size;
- h->smclas = XMC_GL;
- h->flags |= XCOFF_DEF_REGULAR;
- sec->size += bfd_xcoff_glink_code_size(ldinfo->output_bfd);
+ s = fl->path;
+ while ((*out++ = *s++) != '\0')
+ ;
+ s = fl->file;
+ while ((*out++ = *s++) != '\0')
+ ;
+ s = fl->member;
+ while ((*out++ = *s++) != '\0')
+ ;
+ }
- /* The global linkage code requires a TOC entry for the
- descriptor. */
- hds = h->descriptor;
- BFD_ASSERT ((hds->root.type == bfd_link_hash_undefined
- || hds->root.type == bfd_link_hash_undefweak)
- && (hds->flags & XCOFF_DEF_REGULAR) == 0);
- hds->flags |= XCOFF_MARK;
- if (hds->toc_section == NULL)
- {
- int byte_size;
+ BFD_ASSERT ((bfd_size_type) ((bfd_byte *) out - lsec->contents) == stoff);
- /* 32 vs 64
- xcoff32 uses 4 bytes in the toc.
- xcoff64 uses 8 bytes in the toc. */
- if (bfd_xcoff_is_xcoff64 (ldinfo->output_bfd))
- byte_size = 8;
- else if (bfd_xcoff_is_xcoff32 (ldinfo->output_bfd))
- byte_size = 4;
- else
- return FALSE;
+ /* Set up the symbol string table. */
+ if (ldinfo.string_size > 0)
+ {
+ memcpy (out, ldinfo.strings, ldinfo.string_size);
+ free (ldinfo.strings);
+ ldinfo.strings = NULL;
+ }
- hds->toc_section = xcoff_hash_table (ldinfo->info)->toc_section;
- hds->u.toc_offset = hds->toc_section->size;
- hds->toc_section->size += byte_size;
- ++xcoff_hash_table (ldinfo->info)->ldrel_count;
- ++hds->toc_section->reloc_count;
- hds->indx = -2;
- hds->flags |= XCOFF_SET_TOC | XCOFF_LDREL;
+ /* We can't set up the symbol table or the relocs yet, because we
+ don't yet know the final position of the various sections. The
+ .loader symbols are written out when the corresponding normal
+ symbols are written out in xcoff_link_input_bfd or
+ xcoff_write_global_symbol. The .loader relocs are written out
+ when the corresponding normal relocs are handled in
+ xcoff_link_input_bfd. */
- /* We need to call xcoff_build_ldsyms recursively here,
- because we may already have passed hds on the traversal. */
- xcoff_build_ldsyms (hds, p);
- }
+ /* Allocate space for the magic sections. */
+ sec = xcoff_hash_table (info)->linkage_section;
+ if (sec->size > 0)
+ {
+ sec->contents = bfd_zalloc (output_bfd, sec->size);
+ if (sec->contents == NULL)
+ goto error_return;
}
-
- /* If this symbol is exported, but not defined, we need to try to
- define it. */
- if ((h->flags & XCOFF_EXPORT) != 0
- && (h->flags & XCOFF_IMPORT) == 0
- && (h->flags & XCOFF_DEF_REGULAR) == 0
- && (h->flags & XCOFF_DEF_DYNAMIC) == 0
- && (h->root.type == bfd_link_hash_undefined
- || h->root.type == bfd_link_hash_undefweak))
+ sec = xcoff_hash_table (info)->toc_section;
+ if (sec->size > 0)
{
- if ((h->flags & XCOFF_DESCRIPTOR) != 0
- && (h->descriptor->root.type == bfd_link_hash_defined
- || h->descriptor->root.type == bfd_link_hash_defweak))
- {
- asection *sec;
+ sec->contents = bfd_zalloc (output_bfd, sec->size);
+ if (sec->contents == NULL)
+ goto error_return;
+ }
+ sec = xcoff_hash_table (info)->descriptor_section;
+ if (sec->size > 0)
+ {
+ sec->contents = bfd_zalloc (output_bfd, sec->size);
+ if (sec->contents == NULL)
+ goto error_return;
+ }
- /* This is an undefined function descriptor associated with
- a defined entry point. We can build up a function
- descriptor ourselves. Believe it or not, the AIX linker
- actually does this, and there are cases where we need to
- do it as well. */
- sec = xcoff_hash_table (ldinfo->info)->descriptor_section;
- h->root.type = bfd_link_hash_defined;
- h->root.u.def.section = sec;
- h->root.u.def.value = sec->size;
- h->smclas = XMC_DS;
- h->flags |= XCOFF_DEF_REGULAR;
+ /* Now that we've done garbage collection, figure out the contents
+ of the .debug section. */
+ debug_strtab = xcoff_hash_table (info)->debug_strtab;
- /* The size of the function descriptor depends if this is an
- xcoff32 (12) or xcoff64 (24). */
- sec->size +=
- bfd_xcoff_function_descriptor_size(ldinfo->output_bfd);
+ for (sub = info->input_bfds; sub != NULL; sub = sub->link_next)
+ {
+ asection *subdeb;
+ bfd_size_type symcount;
+ unsigned long *debug_index;
+ asection **csectpp;
+ bfd_byte *esym, *esymend;
+ bfd_size_type symesz;
- /* A function descriptor uses two relocs: one for the
- associated code, and one for the TOC address. */
- xcoff_hash_table (ldinfo->info)->ldrel_count += 2;
- sec->reloc_count += 2;
+ if (sub->xvec != info->hash->creator)
+ continue;
+ subdeb = bfd_get_section_by_name (sub, ".debug");
+ if (subdeb == NULL || subdeb->size == 0)
+ continue;
- /* We handle writing out the contents of the descriptor in
- xcoff_write_global_symbol. */
- }
- else
+ if (info->strip == strip_all
+ || info->strip == strip_debugger
+ || info->discard == discard_all)
{
- (*_bfd_error_handler)
- (_("warning: attempt to export undefined symbol `%s'"),
- h->root.root.string);
- h->ldsym = NULL;
- return TRUE;
+ subdeb->size = 0;
+ continue;
}
- }
- /* If this is still a common symbol, and it wasn't garbage
- collected, we need to actually allocate space for it in the .bss
- section. */
- if (h->root.type == bfd_link_hash_common
- && (! xcoff_hash_table (ldinfo->info)->gc
- || (h->flags & XCOFF_MARK) != 0)
- && h->root.u.c.p->section->size == 0)
- {
- BFD_ASSERT (bfd_is_com_section (h->root.u.c.p->section));
- h->root.u.c.p->section->size = h->root.u.c.size;
- }
+ if (! _bfd_coff_get_external_symbols (sub))
+ goto error_return;
- /* We need to add a symbol to the .loader section if it is mentioned
- in a reloc which we are copying to the .loader section and it was
- not defined or common, or if it is the entry point, or if it is
- being exported. */
+ symcount = obj_raw_syment_count (sub);
+ debug_index = bfd_zalloc (sub, symcount * sizeof (unsigned long));
+ if (debug_index == NULL)
+ goto error_return;
+ xcoff_data (sub)->debug_indices = debug_index;
- if (((h->flags & XCOFF_LDREL) == 0
- || h->root.type == bfd_link_hash_defined
- || h->root.type == bfd_link_hash_defweak
- || h->root.type == bfd_link_hash_common)
- && (h->flags & XCOFF_ENTRY) == 0
- && (h->flags & XCOFF_EXPORT) == 0)
- {
- h->ldsym = NULL;
- return TRUE;
- }
+ /* Grab the contents of the .debug section. We use malloc and
+ copy the names into the debug stringtab, rather than
+ bfd_alloc, because I expect that, when linking many files
+ together, many of the strings will be the same. Storing the
+ strings in the hash table should save space in this case. */
+ if (! bfd_malloc_and_get_section (sub, subdeb, &debug_contents))
+ goto error_return;
- /* We don't need to add this symbol if we did garbage collection and
- we did not mark this symbol. */
- if (xcoff_hash_table (ldinfo->info)->gc
- && (h->flags & XCOFF_MARK) == 0)
- {
- h->ldsym = NULL;
- return TRUE;
- }
+ csectpp = xcoff_data (sub)->csects;
- /* We may have already processed this symbol due to the recursive
- call above. */
- if ((h->flags & XCOFF_BUILT_LDSYM) != 0)
- return TRUE;
+ /* Dynamic object do not have csectpp's. */
+ if (NULL != csectpp)
+ {
+ symesz = bfd_coff_symesz (sub);
+ esym = (bfd_byte *) obj_coff_external_syms (sub);
+ esymend = esym + symcount * symesz;
- /* We need to add this symbol to the .loader symbols. */
+ while (esym < esymend)
+ {
+ struct internal_syment sym;
- BFD_ASSERT (h->ldsym == NULL);
- amt = sizeof (struct internal_ldsym);
- h->ldsym = (struct internal_ldsym *) bfd_zalloc (ldinfo->output_bfd, amt);
- if (h->ldsym == NULL)
- {
- ldinfo->failed = TRUE;
- return FALSE;
- }
+ bfd_coff_swap_sym_in (sub, (void *) esym, (void *) &sym);
- if ((h->flags & XCOFF_IMPORT) != 0)
- h->ldsym->l_ifile = h->ldindx;
+ *debug_index = (unsigned long) -1;
- /* The first 3 symbol table indices are reserved to indicate the
- data, text and bss sections. */
- h->ldindx = ldinfo->ldsym_count + 3;
+ if (sym._n._n_n._n_zeroes == 0
+ && *csectpp != NULL
+ && (! gc
+ || ((*csectpp)->flags & SEC_MARK) != 0
+ || *csectpp == bfd_abs_section_ptr)
+ && bfd_coff_symname_in_debug (sub, &sym))
+ {
+ char *name;
+ bfd_size_type indx;
- ++ldinfo->ldsym_count;
+ name = (char *) debug_contents + sym._n._n_n._n_offset;
+ indx = _bfd_stringtab_add (debug_strtab, name, TRUE, TRUE);
+ if (indx == (bfd_size_type) -1)
+ goto error_return;
+ *debug_index = indx;
+ }
- if (! bfd_xcoff_put_ldsymbol_name (ldinfo->output_bfd, ldinfo,
- h->ldsym, h->root.root.string))
- {
- return FALSE;
+ esym += (sym.n_numaux + 1) * symesz;
+ csectpp += sym.n_numaux + 1;
+ debug_index += sym.n_numaux + 1;
+ }
+ }
+
+ free (debug_contents);
+ debug_contents = NULL;
+
+ /* Clear the size of subdeb, so that it is not included directly
+ in the output file. */
+ subdeb->size = 0;
+
+ if (! info->keep_memory)
+ {
+ if (! _bfd_coff_free_symbols (sub))
+ goto error_return;
+ }
}
- h->flags |= XCOFF_BUILT_LDSYM;
+ if (info->strip != strip_all)
+ xcoff_hash_table (info)->debug_section->size =
+ _bfd_stringtab_size (debug_strtab);
return TRUE;
+
+ error_return:
+ if (ldinfo.strings != NULL)
+ free (ldinfo.strings);
+ if (debug_contents != NULL)
+ free (debug_contents);
+ return FALSE;
}
-\f
-/* Do the final link step. */
bfd_boolean
-_bfd_xcoff_bfd_final_link (abfd, info)
- bfd *abfd;
- struct bfd_link_info *info;
+bfd_xcoff_link_generate_rtinit (bfd *abfd,
+ const char *init,
+ const char *fini,
+ bfd_boolean rtld)
{
- bfd_size_type symesz;
- struct xcoff_final_link_info finfo;
- asection *o;
- struct bfd_link_order *p;
- bfd_size_type max_contents_size;
- bfd_size_type max_sym_count;
- bfd_size_type max_lineno_count;
- bfd_size_type max_reloc_count;
- bfd_size_type max_output_reloc_count;
- file_ptr rel_filepos;
- unsigned int relsz;
- file_ptr line_filepos;
- unsigned int linesz;
- bfd *sub;
- bfd_byte *external_relocs = NULL;
- char strbuf[STRING_SIZE_SIZE];
- file_ptr pos;
- bfd_size_type amt;
+ struct bfd_in_memory *bim;
- if (info->shared)
- abfd->flags |= DYNAMIC;
+ bim = bfd_malloc ((bfd_size_type) sizeof (* bim));
+ if (bim == NULL)
+ return FALSE;
- symesz = bfd_coff_symesz (abfd);
+ bim->size = 0;
+ bim->buffer = 0;
- finfo.info = info;
- finfo.output_bfd = abfd;
- finfo.strtab = NULL;
- finfo.section_info = NULL;
- finfo.last_file_index = -1;
- finfo.toc_symindx = -1;
- finfo.internal_syms = NULL;
- finfo.sym_indices = NULL;
- finfo.outsyms = NULL;
- finfo.linenos = NULL;
- finfo.contents = NULL;
- finfo.external_relocs = NULL;
+ abfd->link_next = 0;
+ abfd->format = bfd_object;
+ abfd->iostream = (void *) bim;
+ abfd->flags = BFD_IN_MEMORY;
+ abfd->direction = write_direction;
+ abfd->where = 0;
- finfo.ldsym = (xcoff_hash_table (info)->loader_section->contents
- + bfd_xcoff_ldhdrsz (abfd));
- finfo.ldrel = (xcoff_hash_table (info)->loader_section->contents
- + bfd_xcoff_ldhdrsz(abfd)
- + (xcoff_hash_table (info)->ldhdr.l_nsyms
- * bfd_xcoff_ldsymsz(abfd)));
+ if (! bfd_xcoff_generate_rtinit (abfd, init, fini, rtld))
+ return FALSE;
- xcoff_data (abfd)->coff.link_info = info;
+ /* need to reset to unknown or it will not be read back in correctly */
+ abfd->format = bfd_unknown;
+ abfd->direction = read_direction;
+ abfd->where = 0;
- finfo.strtab = _bfd_stringtab_init ();
- if (finfo.strtab == NULL)
- goto error_return;
+ return TRUE;
+}
+\f
+/* Link an input file into the linker output file. This function
+ handles all the sections and relocations of the input file at once. */
- /* Count the line number and relocation entries required for the
- output file. Determine a few maximum sizes. */
- max_contents_size = 0;
- max_lineno_count = 0;
- max_reloc_count = 0;
- for (o = abfd->sections; o != NULL; o = o->next)
- {
- o->reloc_count = 0;
- o->lineno_count = 0;
- for (p = o->link_order_head; p != NULL; p = p->next)
- {
- if (p->type == bfd_indirect_link_order)
- {
- asection *sec;
+static bfd_boolean
+xcoff_link_input_bfd (struct xcoff_final_link_info *finfo,
+ bfd *input_bfd)
+{
+ bfd *output_bfd;
+ const char *strings;
+ bfd_size_type syment_base;
+ unsigned int n_tmask;
+ unsigned int n_btshft;
+ bfd_boolean copy, hash;
+ bfd_size_type isymesz;
+ bfd_size_type osymesz;
+ bfd_size_type linesz;
+ bfd_byte *esym;
+ bfd_byte *esym_end;
+ struct xcoff_link_hash_entry **sym_hash;
+ struct internal_syment *isymp;
+ asection **csectpp;
+ unsigned long *debug_index;
+ long *indexp;
+ unsigned long output_index;
+ bfd_byte *outsym;
+ unsigned int incls;
+ asection *oline;
+ bfd_boolean keep_syms;
+ asection *o;
- sec = p->u.indirect.section;
+ /* We can just skip DYNAMIC files, unless this is a static link. */
+ if ((input_bfd->flags & DYNAMIC) != 0
+ && ! finfo->info->static_link)
+ return TRUE;
- /* Mark all sections which are to be included in the
- link. This will normally be every section. We need
- to do this so that we can identify any sections which
- the linker has decided to not include. */
- sec->linker_mark = TRUE;
+ /* Move all the symbols to the output file. */
+ output_bfd = finfo->output_bfd;
+ strings = NULL;
+ syment_base = obj_raw_syment_count (output_bfd);
+ isymesz = bfd_coff_symesz (input_bfd);
+ osymesz = bfd_coff_symesz (output_bfd);
+ linesz = bfd_coff_linesz (input_bfd);
+ BFD_ASSERT (linesz == bfd_coff_linesz (output_bfd));
- if (info->strip == strip_none
- || info->strip == strip_some)
- o->lineno_count += sec->lineno_count;
+ n_tmask = coff_data (input_bfd)->local_n_tmask;
+ n_btshft = coff_data (input_bfd)->local_n_btshft;
- o->reloc_count += sec->reloc_count;
+ /* Define macros so that ISFCN, et. al., macros work correctly. */
+#define N_TMASK n_tmask
+#define N_BTSHFT n_btshft
- if (sec->rawsize > max_contents_size)
- max_contents_size = sec->rawsize;
- if (sec->size > max_contents_size)
- max_contents_size = sec->size;
- if (sec->lineno_count > max_lineno_count)
- max_lineno_count = sec->lineno_count;
- if (coff_section_data (sec->owner, sec) != NULL
- && xcoff_section_data (sec->owner, sec) != NULL
- && (xcoff_section_data (sec->owner, sec)->lineno_count
- > max_lineno_count))
- max_lineno_count =
- xcoff_section_data (sec->owner, sec)->lineno_count;
- if (sec->reloc_count > max_reloc_count)
- max_reloc_count = sec->reloc_count;
- }
- else if (p->type == bfd_section_reloc_link_order
- || p->type == bfd_symbol_reloc_link_order)
- ++o->reloc_count;
- }
- }
+ copy = FALSE;
+ if (! finfo->info->keep_memory)
+ copy = TRUE;
+ hash = TRUE;
+ if ((output_bfd->flags & BFD_TRADITIONAL_FORMAT) != 0)
+ hash = FALSE;
- /* Compute the file positions for all the sections. */
- if (abfd->output_has_begun)
- {
- if (xcoff_hash_table (info)->file_align != 0)
- abort ();
- }
- else
+ if (! _bfd_coff_get_external_symbols (input_bfd))
+ return FALSE;
+
+ esym = (bfd_byte *) obj_coff_external_syms (input_bfd);
+ esym_end = esym + obj_raw_syment_count (input_bfd) * isymesz;
+ sym_hash = obj_xcoff_sym_hashes (input_bfd);
+ csectpp = xcoff_data (input_bfd)->csects;
+ debug_index = xcoff_data (input_bfd)->debug_indices;
+ isymp = finfo->internal_syms;
+ indexp = finfo->sym_indices;
+ output_index = syment_base;
+ outsym = finfo->outsyms;
+ incls = 0;
+ oline = NULL;
+
+ while (esym < esym_end)
{
- bfd_vma file_align;
+ struct internal_syment isym;
+ union internal_auxent aux;
+ int smtyp = 0;
+ bfd_boolean skip;
+ bfd_boolean require;
+ int add;
- file_align = xcoff_hash_table (info)->file_align;
- if (file_align != 0)
- {
- bfd_boolean saw_contents;
- int indx;
- asection **op;
- file_ptr sofar;
+ bfd_coff_swap_sym_in (input_bfd, (void *) esym, (void *) isymp);
- /* Insert .pad sections before every section which has
- contents and is loaded, if it is preceded by some other
- section which has contents and is loaded. */
- saw_contents = TRUE;
- for (op = &abfd->sections; *op != NULL; op = &(*op)->next)
- {
- if (strcmp ((*op)->name, ".pad") == 0)
- saw_contents = FALSE;
- else if (((*op)->flags & SEC_HAS_CONTENTS) != 0
- && ((*op)->flags & SEC_LOAD) != 0)
- {
- if (! saw_contents)
- saw_contents = TRUE;
- else
- {
- asection *n, **st;
+ /* If this is a C_EXT or C_HIDEXT symbol, we need the csect
+ information. */
+ if (isymp->n_sclass == C_EXT || isymp->n_sclass == C_HIDEXT)
+ {
+ BFD_ASSERT (isymp->n_numaux > 0);
+ bfd_coff_swap_aux_in (input_bfd,
+ (void *) (esym + isymesz * isymp->n_numaux),
+ isymp->n_type, isymp->n_sclass,
+ isymp->n_numaux - 1, isymp->n_numaux,
+ (void *) &aux);
- /* Create a pad section and place it before the section
- that needs padding. This requires unlinking and
- relinking the bfd's section list. */
+ smtyp = SMTYP_SMTYP (aux.x_csect.x_smtyp);
+ }
- st = abfd->section_tail;
- n = bfd_make_section_anyway (abfd, ".pad");
- n->flags = SEC_HAS_CONTENTS;
- n->alignment_power = 0;
+ /* Make a copy of *isymp so that the relocate_section function
+ always sees the original values. This is more reliable than
+ always recomputing the symbol value even if we are stripping
+ the symbol. */
+ isym = *isymp;
- BFD_ASSERT (*st == n);
- bfd_section_list_remove (abfd, st);
- bfd_section_list_insert (abfd, op, n);
+ /* If this symbol is in the .loader section, swap out the
+ .loader symbol information. If this is an external symbol
+ reference to a defined symbol, though, then wait until we get
+ to the definition. */
+ if (isym.n_sclass == C_EXT
+ && *sym_hash != NULL
+ && (*sym_hash)->ldsym != NULL
+ && (smtyp != XTY_ER
+ || (*sym_hash)->root.type == bfd_link_hash_undefined))
+ {
+ struct xcoff_link_hash_entry *h;
+ struct internal_ldsym *ldsym;
- op = &n->next;
- saw_contents = FALSE;
- }
- }
+ h = *sym_hash;
+ ldsym = h->ldsym;
+ if (isym.n_scnum > 0)
+ {
+ ldsym->l_scnum = (*csectpp)->output_section->target_index;
+ ldsym->l_value = (isym.n_value
+ + (*csectpp)->output_section->vma
+ + (*csectpp)->output_offset
+ - (*csectpp)->vma);
}
-
- /* Reset the section indices after inserting the new
- sections. */
- indx = 0;
- for (o = abfd->sections; o != NULL; o = o->next)
+ else
{
- ++indx;
- o->target_index = indx;
+ ldsym->l_scnum = isym.n_scnum;
+ ldsym->l_value = isym.n_value;
}
- BFD_ASSERT ((unsigned int) indx == abfd->section_count);
- /* Work out appropriate sizes for the .pad sections to force
- each section to land on a page boundary. This bit of
- code knows what compute_section_file_positions is going
- to do. */
- sofar = bfd_coff_filhsz (abfd);
- sofar += bfd_coff_aoutsz (abfd);
- sofar += abfd->section_count * bfd_coff_scnhsz (abfd);
- for (o = abfd->sections; o != NULL; o = o->next)
- if ((bfd_xcoff_is_reloc_count_overflow
- (abfd, (bfd_vma) o->reloc_count))
- || (bfd_xcoff_is_lineno_count_overflow
- (abfd, (bfd_vma) o->lineno_count)))
- /* 64 does not overflow, need to check if 32 does */
- sofar += bfd_coff_scnhsz (abfd);
+ ldsym->l_smtype = smtyp;
+ if (((h->flags & XCOFF_DEF_REGULAR) == 0
+ && (h->flags & XCOFF_DEF_DYNAMIC) != 0)
+ || (h->flags & XCOFF_IMPORT) != 0)
+ ldsym->l_smtype |= L_IMPORT;
+ if (((h->flags & XCOFF_DEF_REGULAR) != 0
+ && (h->flags & XCOFF_DEF_DYNAMIC) != 0)
+ || (h->flags & XCOFF_EXPORT) != 0)
+ ldsym->l_smtype |= L_EXPORT;
+ if ((h->flags & XCOFF_ENTRY) != 0)
+ ldsym->l_smtype |= L_ENTRY;
- for (o = abfd->sections; o != NULL; o = o->next)
+ ldsym->l_smclas = aux.x_csect.x_smclas;
+
+ if (ldsym->l_ifile == (bfd_size_type) -1)
+ ldsym->l_ifile = 0;
+ else if (ldsym->l_ifile == 0)
{
- if (strcmp (o->name, ".pad") == 0)
+ if ((ldsym->l_smtype & L_IMPORT) == 0)
+ ldsym->l_ifile = 0;
+ else
{
- bfd_vma pageoff;
+ bfd *impbfd;
- BFD_ASSERT (o->size == 0);
- pageoff = sofar & (file_align - 1);
- if (pageoff != 0)
+ if (h->root.type == bfd_link_hash_defined
+ || h->root.type == bfd_link_hash_defweak)
+ impbfd = h->root.u.def.section->owner;
+ else if (h->root.type == bfd_link_hash_undefined
+ || h->root.type == bfd_link_hash_undefweak)
+ impbfd = h->root.u.undef.abfd;
+ else
+ impbfd = NULL;
+
+ if (impbfd == NULL)
+ ldsym->l_ifile = 0;
+ else
{
- o->size = file_align - pageoff;
- sofar += file_align - pageoff;
- o->flags |= SEC_HAS_CONTENTS;
+ BFD_ASSERT (impbfd->xvec == finfo->output_bfd->xvec);
+ ldsym->l_ifile = xcoff_data (impbfd)->import_file_id;
}
}
- else
- {
- if ((o->flags & SEC_HAS_CONTENTS) != 0)
- sofar += BFD_ALIGN (o->size,
- 1 << o->alignment_power);
- }
+ }
+
+ ldsym->l_parm = 0;
+
+ BFD_ASSERT (h->ldindx >= 0);
+ bfd_xcoff_swap_ldsym_out (finfo->output_bfd, ldsym,
+ (finfo->ldsym
+ + ((h->ldindx - 3)
+ * bfd_xcoff_ldsymsz (finfo->output_bfd))));
+ h->ldsym = NULL;
+
+ /* Fill in snentry now that we know the target_index. */
+ if ((h->flags & XCOFF_ENTRY) != 0
+ && (h->root.type == bfd_link_hash_defined
+ || h->root.type == bfd_link_hash_defweak))
+ {
+ xcoff_data (output_bfd)->snentry =
+ h->root.u.def.section->output_section->target_index;
}
}
- if (! bfd_coff_compute_section_file_positions (abfd))
- goto error_return;
- }
+ *indexp = -1;
- /* Allocate space for the pointers we need to keep for the relocs. */
- {
- unsigned int i;
+ skip = FALSE;
+ require = FALSE;
+ add = 1 + isym.n_numaux;
- /* We use section_count + 1, rather than section_count, because
- the target_index fields are 1 based. */
- amt = abfd->section_count + 1;
- amt *= sizeof (struct xcoff_link_section_info);
- finfo.section_info = (struct xcoff_link_section_info *) bfd_malloc (amt);
- if (finfo.section_info == NULL)
- goto error_return;
- for (i = 0; i <= abfd->section_count; i++)
- {
- finfo.section_info[i].relocs = NULL;
- finfo.section_info[i].rel_hashes = NULL;
- finfo.section_info[i].toc_rel_hashes = NULL;
- }
- }
+ /* If we are skipping this csect, we want to skip this symbol. */
+ if (*csectpp == NULL)
+ skip = TRUE;
- /* Set the file positions for the relocs. */
- rel_filepos = obj_relocbase (abfd);
- relsz = bfd_coff_relsz (abfd);
- max_output_reloc_count = 0;
- for (o = abfd->sections; o != NULL; o = o->next)
- {
- if (o->reloc_count == 0)
- o->rel_filepos = 0;
- else
+ /* If we garbage collected this csect, we want to skip this
+ symbol. */
+ if (! skip
+ && xcoff_hash_table (finfo->info)->gc
+ && ((*csectpp)->flags & SEC_MARK) == 0
+ && *csectpp != bfd_abs_section_ptr)
+ skip = TRUE;
+
+ /* An XCOFF linker always skips C_STAT symbols. */
+ if (! skip
+ && isymp->n_sclass == C_STAT)
+ skip = TRUE;
+
+ /* We skip all but the first TOC anchor. */
+ if (! skip
+ && isymp->n_sclass == C_HIDEXT
+ && aux.x_csect.x_smclas == XMC_TC0)
{
- /* A stripped file has no relocs. However, we still
- allocate the buffers, so that later code doesn't have to
- worry about whether we are stripping or not. */
- if (info->strip == strip_all)
- o->rel_filepos = 0;
+ if (finfo->toc_symindx != -1)
+ skip = TRUE;
else
{
- o->flags |= SEC_RELOC;
- o->rel_filepos = rel_filepos;
- rel_filepos += o->reloc_count * relsz;
- }
+ bfd_vma tocval, tocend;
+ bfd *inp;
- /* We don't know the indices of global symbols until we have
- written out all the local symbols. For each section in
- the output file, we keep an array of pointers to hash
- table entries. Each entry in the array corresponds to a
- reloc. When we find a reloc against a global symbol, we
- set the corresponding entry in this array so that we can
- fix up the symbol index after we have written out all the
- local symbols.
+ tocval = ((*csectpp)->output_section->vma
+ + (*csectpp)->output_offset
+ + isym.n_value
+ - (*csectpp)->vma);
- Because of this problem, we also keep the relocs in
- memory until the end of the link. This wastes memory.
- We could backpatch the file later, I suppose, although it
- would be slow. */
- amt = o->reloc_count;
- amt *= sizeof (struct internal_reloc);
- finfo.section_info[o->target_index].relocs =
- (struct internal_reloc *) bfd_malloc (amt);
+ /* We want to find out if tocval is a good value to use
+ as the TOC anchor--that is, whether we can access all
+ of the TOC using a 16 bit offset from tocval. This
+ test assumes that the TOC comes at the end of the
+ output section, as it does in the default linker
+ script. */
+ tocend = ((*csectpp)->output_section->vma
+ + (*csectpp)->output_section->size);
+ for (inp = finfo->info->input_bfds;
+ inp != NULL;
+ inp = inp->link_next)
+ {
- amt = o->reloc_count;
- amt *= sizeof (struct xcoff_link_hash_entry *);
- finfo.section_info[o->target_index].rel_hashes =
- (struct xcoff_link_hash_entry **) bfd_malloc (amt);
+ for (o = inp->sections; o != NULL; o = o->next)
+ if (strcmp (o->name, ".tocbss") == 0)
+ {
+ bfd_vma new_toc_end;
+ new_toc_end = (o->output_section->vma
+ + o->output_offset
+ + o->size);
+ if (new_toc_end > tocend)
+ tocend = new_toc_end;
+ }
- if (finfo.section_info[o->target_index].relocs == NULL
- || finfo.section_info[o->target_index].rel_hashes == NULL)
- goto error_return;
+ }
- if (o->reloc_count > max_output_reloc_count)
- max_output_reloc_count = o->reloc_count;
- }
- }
+ if (tocval + 0x10000 < tocend)
+ {
+ (*_bfd_error_handler)
+ (_("TOC overflow: 0x%lx > 0x10000; try -mminimal-toc when compiling"),
+ (unsigned long) (tocend - tocval));
+ bfd_set_error (bfd_error_file_too_big);
+ return FALSE;
+ }
- /* We now know the size of the relocs, so we can determine the file
- positions of the line numbers. */
- line_filepos = rel_filepos;
- finfo.line_filepos = line_filepos;
- linesz = bfd_coff_linesz (abfd);
- for (o = abfd->sections; o != NULL; o = o->next)
- {
- if (o->lineno_count == 0)
- o->line_filepos = 0;
- else
- {
- o->line_filepos = line_filepos;
- line_filepos += o->lineno_count * linesz;
- }
+ if (tocval + 0x8000 < tocend)
+ {
+ bfd_vma tocadd;
- /* Reset the reloc and lineno counts, so that we can use them to
- count the number of entries we have output so far. */
- o->reloc_count = 0;
- o->lineno_count = 0;
- }
+ tocadd = tocend - (tocval + 0x8000);
+ tocval += tocadd;
+ isym.n_value += tocadd;
+ }
- obj_sym_filepos (abfd) = line_filepos;
+ finfo->toc_symindx = output_index;
+ xcoff_data (finfo->output_bfd)->toc = tocval;
+ xcoff_data (finfo->output_bfd)->sntoc =
+ (*csectpp)->output_section->target_index;
+ require = TRUE;
- /* Figure out the largest number of symbols in an input BFD. Take
- the opportunity to clear the output_has_begun fields of all the
- input BFD's. We want at least 6 symbols, since that is the
- number which xcoff_write_global_symbol may need. */
- max_sym_count = 6;
- for (sub = info->input_bfds; sub != NULL; sub = sub->link_next)
- {
- bfd_size_type sz;
+ }
+ }
- sub->output_has_begun = FALSE;
- sz = obj_raw_syment_count (sub);
- if (sz > max_sym_count)
- max_sym_count = sz;
- }
+ /* If we are stripping all symbols, we want to skip this one. */
+ if (! skip
+ && finfo->info->strip == strip_all)
+ skip = TRUE;
- /* Allocate some buffers used while linking. */
- amt = max_sym_count * sizeof (struct internal_syment);
- finfo.internal_syms = (struct internal_syment *) bfd_malloc (amt);
+ /* We can skip resolved external references. */
+ if (! skip
+ && isym.n_sclass == C_EXT
+ && smtyp == XTY_ER
+ && (*sym_hash)->root.type != bfd_link_hash_undefined)
+ skip = TRUE;
- amt = max_sym_count * sizeof (long);
- finfo.sym_indices = (long *) bfd_malloc (amt);
+ /* We can skip common symbols if they got defined somewhere
+ else. */
+ if (! skip
+ && isym.n_sclass == C_EXT
+ && smtyp == XTY_CM
+ && ((*sym_hash)->root.type != bfd_link_hash_common
+ || (*sym_hash)->root.u.c.p->section != *csectpp)
+ && ((*sym_hash)->root.type != bfd_link_hash_defined
+ || (*sym_hash)->root.u.def.section != *csectpp))
+ skip = TRUE;
- amt = (max_sym_count + 1) * symesz;
- finfo.outsyms = (bfd_byte *) bfd_malloc (amt);
+ /* Skip local symbols if we are discarding them. */
+ if (! skip
+ && finfo->info->discard == discard_all
+ && isym.n_sclass != C_EXT
+ && (isym.n_sclass != C_HIDEXT
+ || smtyp != XTY_SD))
+ skip = TRUE;
- amt = max_lineno_count * bfd_coff_linesz (abfd);
- finfo.linenos = (bfd_byte *) bfd_malloc (amt);
+ /* If we stripping debugging symbols, and this is a debugging
+ symbol, then skip it. */
+ if (! skip
+ && finfo->info->strip == strip_debugger
+ && isym.n_scnum == N_DEBUG)
+ skip = TRUE;
- amt = max_contents_size;
- finfo.contents = (bfd_byte *) bfd_malloc (amt);
+ /* If some symbols are stripped based on the name, work out the
+ name and decide whether to skip this symbol. We don't handle
+ this correctly for symbols whose names are in the .debug
+ section; to get it right we would need a new bfd_strtab_hash
+ function to return the string given the index. */
+ if (! skip
+ && (finfo->info->strip == strip_some
+ || finfo->info->discard == discard_l)
+ && (debug_index == NULL || *debug_index == (unsigned long) -1))
+ {
+ const char *name;
+ char buf[SYMNMLEN + 1];
- amt = max_reloc_count * relsz;
- finfo.external_relocs = (bfd_byte *) bfd_malloc (amt);
+ name = _bfd_coff_internal_syment_name (input_bfd, &isym, buf);
- if ((finfo.internal_syms == NULL && max_sym_count > 0)
- || (finfo.sym_indices == NULL && max_sym_count > 0)
- || finfo.outsyms == NULL
- || (finfo.linenos == NULL && max_lineno_count > 0)
- || (finfo.contents == NULL && max_contents_size > 0)
- || (finfo.external_relocs == NULL && max_reloc_count > 0))
- goto error_return;
+ if (name == NULL)
+ return FALSE;
- obj_raw_syment_count (abfd) = 0;
- xcoff_data (abfd)->toc = (bfd_vma) -1;
+ if ((finfo->info->strip == strip_some
+ && (bfd_hash_lookup (finfo->info->keep_hash, name, FALSE,
+ FALSE) == NULL))
+ || (finfo->info->discard == discard_l
+ && (isym.n_sclass != C_EXT
+ && (isym.n_sclass != C_HIDEXT
+ || smtyp != XTY_SD))
+ && bfd_is_local_label_name (input_bfd, name)))
+ skip = TRUE;
+ }
- /* We now know the position of everything in the file, except that
- we don't know the size of the symbol table and therefore we don't
- know where the string table starts. We just build the string
- table in memory as we go along. We process all the relocations
- for a single input file at once. */
- for (o = abfd->sections; o != NULL; o = o->next)
- {
- for (p = o->link_order_head; p != NULL; p = p->next)
+ /* We can not skip the first TOC anchor. */
+ if (skip
+ && require
+ && finfo->info->strip != strip_all)
+ skip = FALSE;
+
+ /* We now know whether we are to skip this symbol or not. */
+ if (! skip)
{
- if (p->type == bfd_indirect_link_order
- && p->u.indirect.section->owner->xvec == abfd->xvec)
+ /* Adjust the symbol in order to output it. */
+
+ if (isym._n._n_n._n_zeroes == 0
+ && isym._n._n_n._n_offset != 0)
{
- sub = p->u.indirect.section->owner;
- if (! sub->output_has_begun)
- {
- if (! xcoff_link_input_bfd (&finfo, sub))
- goto error_return;
- sub->output_has_begun = TRUE;
+ /* This symbol has a long name. Enter it in the string
+ table we are building. If *debug_index != -1, the
+ name has already been entered in the .debug section. */
+ if (debug_index != NULL && *debug_index != (unsigned long) -1)
+ isym._n._n_n._n_offset = *debug_index;
+ else
+ {
+ const char *name;
+ bfd_size_type indx;
+
+ name = _bfd_coff_internal_syment_name (input_bfd, &isym, NULL);
+
+ if (name == NULL)
+ return FALSE;
+ indx = _bfd_stringtab_add (finfo->strtab, name, hash, copy);
+ if (indx == (bfd_size_type) -1)
+ return FALSE;
+ isym._n._n_n._n_offset = STRING_SIZE_SIZE + indx;
}
}
- else if (p->type == bfd_section_reloc_link_order
- || p->type == bfd_symbol_reloc_link_order)
- {
- if (! xcoff_reloc_link_order (abfd, &finfo, o, p))
- goto error_return;
- }
- else
+
+ if (isym.n_sclass != C_BSTAT
+ && isym.n_sclass != C_ESTAT
+ && isym.n_sclass != C_DECL
+ && isym.n_scnum > 0)
{
- if (! _bfd_default_link_order (abfd, info, o, p))
- goto error_return;
+ isym.n_scnum = (*csectpp)->output_section->target_index;
+ isym.n_value += ((*csectpp)->output_section->vma
+ + (*csectpp)->output_offset
+ - (*csectpp)->vma);
}
- }
- }
-
- /* Free up the buffers used by xcoff_link_input_bfd. */
-
- if (finfo.internal_syms != NULL)
- {
- free (finfo.internal_syms);
- finfo.internal_syms = NULL;
- }
- if (finfo.sym_indices != NULL)
- {
- free (finfo.sym_indices);
- finfo.sym_indices = NULL;
- }
- if (finfo.linenos != NULL)
- {
- free (finfo.linenos);
- finfo.linenos = NULL;
- }
- if (finfo.contents != NULL)
- {
- free (finfo.contents);
- finfo.contents = NULL;
- }
- if (finfo.external_relocs != NULL)
- {
- free (finfo.external_relocs);
- finfo.external_relocs = NULL;
- }
+ /* The value of a C_FILE symbol is the symbol index of the
+ next C_FILE symbol. The value of the last C_FILE symbol
+ is -1. We try to get this right, below, just before we
+ write the symbols out, but in the general case we may
+ have to write the symbol out twice. */
+ if (isym.n_sclass == C_FILE)
+ {
+ if (finfo->last_file_index != -1
+ && finfo->last_file.n_value != (bfd_vma) output_index)
+ {
+ /* We must correct the value of the last C_FILE entry. */
+ finfo->last_file.n_value = output_index;
+ if ((bfd_size_type) finfo->last_file_index >= syment_base)
+ {
+ /* The last C_FILE symbol is in this input file. */
+ bfd_coff_swap_sym_out (output_bfd,
+ (void *) &finfo->last_file,
+ (void *) (finfo->outsyms
+ + ((finfo->last_file_index
+ - syment_base)
+ * osymesz)));
+ }
+ else
+ {
+ /* We have already written out the last C_FILE
+ symbol. We need to write it out again. We
+ borrow *outsym temporarily. */
+ file_ptr pos;
- /* The value of the last C_FILE symbol is supposed to be -1. Write
- it out again. */
- if (finfo.last_file_index != -1)
- {
- finfo.last_file.n_value = -(bfd_vma) 1;
- bfd_coff_swap_sym_out (abfd, (PTR) &finfo.last_file,
- (PTR) finfo.outsyms);
- pos = obj_sym_filepos (abfd) + finfo.last_file_index * symesz;
- if (bfd_seek (abfd, pos, SEEK_SET) != 0
- || bfd_bwrite (finfo.outsyms, symesz, abfd) != symesz)
- goto error_return;
- }
+ bfd_coff_swap_sym_out (output_bfd,
+ (void *) &finfo->last_file,
+ (void *) outsym);
- /* Write out all the global symbols which do not come from XCOFF
- input files. */
- xcoff_link_hash_traverse (xcoff_hash_table (info),
- xcoff_write_global_symbol,
- (PTR) &finfo);
+ pos = obj_sym_filepos (output_bfd);
+ pos += finfo->last_file_index * osymesz;
+ if (bfd_seek (output_bfd, pos, SEEK_SET) != 0
+ || (bfd_bwrite (outsym, osymesz, output_bfd)
+ != osymesz))
+ return FALSE;
+ }
+ }
- if (finfo.outsyms != NULL)
- {
- free (finfo.outsyms);
- finfo.outsyms = NULL;
- }
+ finfo->last_file_index = output_index;
+ finfo->last_file = isym;
+ }
- /* Now that we have written out all the global symbols, we know the
- symbol indices to use for relocs against them, and we can finally
- write out the relocs. */
- amt = max_output_reloc_count * relsz;
- external_relocs = (bfd_byte *) bfd_malloc (amt);
- if (external_relocs == NULL && max_output_reloc_count != 0)
- goto error_return;
+ /* The value of a C_BINCL or C_EINCL symbol is a file offset
+ into the line numbers. We update the symbol values when
+ we handle the line numbers. */
+ if (isym.n_sclass == C_BINCL
+ || isym.n_sclass == C_EINCL)
+ {
+ isym.n_value = finfo->line_filepos;
+ ++incls;
+ }
- for (o = abfd->sections; o != NULL; o = o->next)
- {
- struct internal_reloc *irel;
- struct internal_reloc *irelend;
- struct xcoff_link_hash_entry **rel_hash;
- struct xcoff_toc_rel_hash *toc_rel_hash;
- bfd_byte *erel;
- bfd_size_type rel_size;
+ /* Output the symbol. */
- /* A stripped file has no relocs. */
- if (info->strip == strip_all)
- {
- o->reloc_count = 0;
- continue;
- }
+ bfd_coff_swap_sym_out (output_bfd, (void *) &isym, (void *) outsym);
- if (o->reloc_count == 0)
- continue;
+ *indexp = output_index;
- irel = finfo.section_info[o->target_index].relocs;
- irelend = irel + o->reloc_count;
- rel_hash = finfo.section_info[o->target_index].rel_hashes;
- for (; irel < irelend; irel++, rel_hash++, erel += relsz)
- {
- if (*rel_hash != NULL)
+ if (isym.n_sclass == C_EXT)
{
- if ((*rel_hash)->indx < 0)
- {
- if (! ((*info->callbacks->unattached_reloc)
- (info, (*rel_hash)->root.root.string,
- (bfd *) NULL, o, irel->r_vaddr)))
- goto error_return;
- (*rel_hash)->indx = 0;
- }
- irel->r_symndx = (*rel_hash)->indx;
+ long indx;
+ struct xcoff_link_hash_entry *h;
+
+ indx = ((esym - (bfd_byte *) obj_coff_external_syms (input_bfd))
+ / isymesz);
+ h = obj_xcoff_sym_hashes (input_bfd)[indx];
+ BFD_ASSERT (h != NULL);
+ h->indx = output_index;
}
- }
- for (toc_rel_hash = finfo.section_info[o->target_index].toc_rel_hashes;
- toc_rel_hash != NULL;
- toc_rel_hash = toc_rel_hash->next)
- {
- if (toc_rel_hash->h->u.toc_indx < 0)
+ /* If this is a symbol in the TOC which we may have merged
+ (class XMC_TC), remember the symbol index of the TOC
+ symbol. */
+ if (isym.n_sclass == C_HIDEXT
+ && aux.x_csect.x_smclas == XMC_TC
+ && *sym_hash != NULL)
{
- if (! ((*info->callbacks->unattached_reloc)
- (info, toc_rel_hash->h->root.root.string,
- (bfd *) NULL, o, toc_rel_hash->rel->r_vaddr)))
- goto error_return;
- toc_rel_hash->h->u.toc_indx = 0;
+ BFD_ASSERT (((*sym_hash)->flags & XCOFF_SET_TOC) == 0);
+ BFD_ASSERT ((*sym_hash)->toc_section != NULL);
+ (*sym_hash)->u.toc_indx = output_index;
}
- toc_rel_hash->rel->r_symndx = toc_rel_hash->h->u.toc_indx;
- }
-
- /* XCOFF requires that the relocs be sorted by address. We tend
- to produce them in the order in which their containing csects
- appear in the symbol table, which is not necessarily by
- address. So we sort them here. There may be a better way to
- do this. */
- qsort ((PTR) finfo.section_info[o->target_index].relocs,
- o->reloc_count, sizeof (struct internal_reloc),
- xcoff_sort_relocs);
- irel = finfo.section_info[o->target_index].relocs;
- irelend = irel + o->reloc_count;
- erel = external_relocs;
- for (; irel < irelend; irel++, rel_hash++, erel += relsz)
- bfd_coff_swap_reloc_out (abfd, (PTR) irel, (PTR) erel);
+ output_index += add;
+ outsym += add * osymesz;
+ }
- rel_size = relsz * o->reloc_count;
- if (bfd_seek (abfd, o->rel_filepos, SEEK_SET) != 0
- || bfd_bwrite ((PTR) external_relocs, rel_size, abfd) != rel_size)
- goto error_return;
+ esym += add * isymesz;
+ isymp += add;
+ csectpp += add;
+ sym_hash += add;
+ if (debug_index != NULL)
+ debug_index += add;
+ ++indexp;
+ for (--add; add > 0; --add)
+ *indexp++ = -1;
}
- if (external_relocs != NULL)
- {
- free (external_relocs);
- external_relocs = NULL;
- }
+ /* Fix up the aux entries and the C_BSTAT symbols. This must be
+ done in a separate pass, because we don't know the correct symbol
+ indices until we have already decided which symbols we are going
+ to keep. */
- /* Free up the section information. */
- if (finfo.section_info != NULL)
+ esym = (bfd_byte *) obj_coff_external_syms (input_bfd);
+ esym_end = esym + obj_raw_syment_count (input_bfd) * isymesz;
+ isymp = finfo->internal_syms;
+ indexp = finfo->sym_indices;
+ csectpp = xcoff_data (input_bfd)->csects;
+ outsym = finfo->outsyms;
+ while (esym < esym_end)
{
- unsigned int i;
+ int add;
- for (i = 0; i < abfd->section_count; i++)
+ add = 1 + isymp->n_numaux;
+
+ if (*indexp < 0)
+ esym += add * isymesz;
+ else
{
- if (finfo.section_info[i].relocs != NULL)
- free (finfo.section_info[i].relocs);
- if (finfo.section_info[i].rel_hashes != NULL)
- free (finfo.section_info[i].rel_hashes);
- }
- free (finfo.section_info);
- finfo.section_info = NULL;
- }
-
- /* Write out the loader section contents. */
- BFD_ASSERT ((bfd_byte *) finfo.ldrel
- == (xcoff_hash_table (info)->loader_section->contents
- + xcoff_hash_table (info)->ldhdr.l_impoff));
- o = xcoff_hash_table (info)->loader_section;
- if (! bfd_set_section_contents (abfd, o->output_section, o->contents,
- (file_ptr) o->output_offset, o->size))
- goto error_return;
+ int i;
- /* Write out the magic sections. */
- o = xcoff_hash_table (info)->linkage_section;
- if (o->size > 0
- && ! bfd_set_section_contents (abfd, o->output_section, o->contents,
- (file_ptr) o->output_offset,
- o->size))
- goto error_return;
- o = xcoff_hash_table (info)->toc_section;
- if (o->size > 0
- && ! bfd_set_section_contents (abfd, o->output_section, o->contents,
- (file_ptr) o->output_offset,
- o->size))
- goto error_return;
- o = xcoff_hash_table (info)->descriptor_section;
- if (o->size > 0
- && ! bfd_set_section_contents (abfd, o->output_section, o->contents,
- (file_ptr) o->output_offset,
- o->size))
- goto error_return;
+ if (isymp->n_sclass == C_BSTAT)
+ {
+ struct internal_syment isym;
- /* Write out the string table. */
- pos = obj_sym_filepos (abfd) + obj_raw_syment_count (abfd) * symesz;
- if (bfd_seek (abfd, pos, SEEK_SET) != 0)
- goto error_return;
- H_PUT_32 (abfd,
- _bfd_stringtab_size (finfo.strtab) + STRING_SIZE_SIZE,
- strbuf);
- amt = STRING_SIZE_SIZE;
- if (bfd_bwrite (strbuf, amt, abfd) != amt)
- goto error_return;
- if (! _bfd_stringtab_emit (abfd, finfo.strtab))
- goto error_return;
+ bfd_vma indx;
- _bfd_stringtab_free (finfo.strtab);
+ /* The value of a C_BSTAT symbol is the symbol table
+ index of the containing csect. */
+ bfd_coff_swap_sym_in (output_bfd, (void *) outsym, (void *) &isym);
+ indx = isym.n_value;
+ if (indx < obj_raw_syment_count (input_bfd))
+ {
+ long symindx;
- /* Write out the debugging string table. */
- o = xcoff_hash_table (info)->debug_section;
- if (o != NULL)
- {
- struct bfd_strtab_hash *debug_strtab;
+ symindx = finfo->sym_indices[indx];
+ if (symindx < 0)
+ isym.n_value = 0;
+ else
+ isym.n_value = symindx;
+ bfd_coff_swap_sym_out (output_bfd, (void *) &isym,
+ (void *) outsym);
+ }
+ }
- debug_strtab = xcoff_hash_table (info)->debug_strtab;
- BFD_ASSERT (o->output_section->size - o->output_offset
- >= _bfd_stringtab_size (debug_strtab));
- pos = o->output_section->filepos + o->output_offset;
- if (bfd_seek (abfd, pos, SEEK_SET) != 0)
- goto error_return;
- if (! _bfd_stringtab_emit (abfd, debug_strtab))
- goto error_return;
- }
+ esym += isymesz;
+ outsym += osymesz;
- /* Setting bfd_get_symcount to 0 will cause write_object_contents to
- not try to write out the symbols. */
- bfd_get_symcount (abfd) = 0;
+ for (i = 0; i < isymp->n_numaux && esym < esym_end; i++)
+ {
+ union internal_auxent aux;
- return TRUE;
+ bfd_coff_swap_aux_in (input_bfd, (void *) esym, isymp->n_type,
+ isymp->n_sclass, i, isymp->n_numaux,
+ (void *) &aux);
- error_return:
- if (finfo.strtab != NULL)
- _bfd_stringtab_free (finfo.strtab);
+ if (isymp->n_sclass == C_FILE)
+ {
+ /* This is the file name (or some comment put in by
+ the compiler). If it is long, we must put it in
+ the string table. */
+ if (aux.x_file.x_n.x_zeroes == 0
+ && aux.x_file.x_n.x_offset != 0)
+ {
+ const char *filename;
+ bfd_size_type indx;
- if (finfo.section_info != NULL)
- {
- unsigned int i;
+ BFD_ASSERT (aux.x_file.x_n.x_offset
+ >= STRING_SIZE_SIZE);
+ if (strings == NULL)
+ {
+ strings = _bfd_coff_read_string_table (input_bfd);
+ if (strings == NULL)
+ return FALSE;
+ }
+ filename = strings + aux.x_file.x_n.x_offset;
+ indx = _bfd_stringtab_add (finfo->strtab, filename,
+ hash, copy);
+ if (indx == (bfd_size_type) -1)
+ return FALSE;
+ aux.x_file.x_n.x_offset = STRING_SIZE_SIZE + indx;
+ }
+ }
+ else if ((isymp->n_sclass == C_EXT
+ || isymp->n_sclass == C_HIDEXT)
+ && i + 1 == isymp->n_numaux)
+ {
- for (i = 0; i < abfd->section_count; i++)
- {
- if (finfo.section_info[i].relocs != NULL)
- free (finfo.section_info[i].relocs);
- if (finfo.section_info[i].rel_hashes != NULL)
- free (finfo.section_info[i].rel_hashes);
- }
- free (finfo.section_info);
- }
+ /* We don't support type checking. I don't know if
+ anybody does. */
+ aux.x_csect.x_parmhash = 0;
+ /* I don't think anybody uses these fields, but we'd
+ better clobber them just in case. */
+ aux.x_csect.x_stab = 0;
+ aux.x_csect.x_snstab = 0;
- if (finfo.internal_syms != NULL)
- free (finfo.internal_syms);
- if (finfo.sym_indices != NULL)
- free (finfo.sym_indices);
- if (finfo.outsyms != NULL)
- free (finfo.outsyms);
- if (finfo.linenos != NULL)
- free (finfo.linenos);
- if (finfo.contents != NULL)
- free (finfo.contents);
- if (finfo.external_relocs != NULL)
- free (finfo.external_relocs);
- if (external_relocs != NULL)
- free (external_relocs);
- return FALSE;
-}
+ if (SMTYP_SMTYP (aux.x_csect.x_smtyp) == XTY_LD)
+ {
+ unsigned long indx;
-/* Link an input file into the linker output file. This function
- handles all the sections and relocations of the input file at once. */
+ indx = aux.x_csect.x_scnlen.l;
+ if (indx < obj_raw_syment_count (input_bfd))
+ {
+ long symindx;
-static bfd_boolean
-xcoff_link_input_bfd (finfo, input_bfd)
- struct xcoff_final_link_info *finfo;
- bfd *input_bfd;
-{
- bfd *output_bfd;
- const char *strings;
- bfd_size_type syment_base;
- unsigned int n_tmask;
- unsigned int n_btshft;
- bfd_boolean copy, hash;
- bfd_size_type isymesz;
- bfd_size_type osymesz;
- bfd_size_type linesz;
- bfd_byte *esym;
- bfd_byte *esym_end;
- struct xcoff_link_hash_entry **sym_hash;
- struct internal_syment *isymp;
- asection **csectpp;
- unsigned long *debug_index;
- long *indexp;
- unsigned long output_index;
- bfd_byte *outsym;
- unsigned int incls;
- asection *oline;
- bfd_boolean keep_syms;
- asection *o;
+ symindx = finfo->sym_indices[indx];
+ if (symindx < 0)
+ {
+ aux.x_csect.x_scnlen.l = 0;
+ }
+ else
+ {
+ aux.x_csect.x_scnlen.l = symindx;
+ }
+ }
+ }
+ }
+ else if (isymp->n_sclass != C_STAT || isymp->n_type != T_NULL)
+ {
+ unsigned long indx;
- /* We can just skip DYNAMIC files, unless this is a static link. */
- if ((input_bfd->flags & DYNAMIC) != 0
- && ! finfo->info->static_link)
- return TRUE;
+ if (ISFCN (isymp->n_type)
+ || ISTAG (isymp->n_sclass)
+ || isymp->n_sclass == C_BLOCK
+ || isymp->n_sclass == C_FCN)
+ {
+ indx = aux.x_sym.x_fcnary.x_fcn.x_endndx.l;
+ if (indx > 0
+ && indx < obj_raw_syment_count (input_bfd))
+ {
+ /* We look forward through the symbol for
+ the index of the next symbol we are going
+ to include. I don't know if this is
+ entirely right. */
+ while (finfo->sym_indices[indx] < 0
+ && indx < obj_raw_syment_count (input_bfd))
+ ++indx;
+ if (indx >= obj_raw_syment_count (input_bfd))
+ indx = output_index;
+ else
+ indx = finfo->sym_indices[indx];
+ aux.x_sym.x_fcnary.x_fcn.x_endndx.l = indx;
- /* Move all the symbols to the output file. */
+ }
+ }
- output_bfd = finfo->output_bfd;
- strings = NULL;
- syment_base = obj_raw_syment_count (output_bfd);
- isymesz = bfd_coff_symesz (input_bfd);
- osymesz = bfd_coff_symesz (output_bfd);
- linesz = bfd_coff_linesz (input_bfd);
- BFD_ASSERT (linesz == bfd_coff_linesz (output_bfd));
+ indx = aux.x_sym.x_tagndx.l;
+ if (indx > 0 && indx < obj_raw_syment_count (input_bfd))
+ {
+ long symindx;
- n_tmask = coff_data (input_bfd)->local_n_tmask;
- n_btshft = coff_data (input_bfd)->local_n_btshft;
+ symindx = finfo->sym_indices[indx];
+ if (symindx < 0)
+ aux.x_sym.x_tagndx.l = 0;
+ else
+ aux.x_sym.x_tagndx.l = symindx;
+ }
- /* Define macros so that ISFCN, et. al., macros work correctly. */
-#define N_TMASK n_tmask
-#define N_BTSHFT n_btshft
+ }
- copy = FALSE;
- if (! finfo->info->keep_memory)
- copy = TRUE;
- hash = TRUE;
- if ((output_bfd->flags & BFD_TRADITIONAL_FORMAT) != 0)
- hash = FALSE;
-
- if (! _bfd_coff_get_external_symbols (input_bfd))
- return FALSE;
-
- esym = (bfd_byte *) obj_coff_external_syms (input_bfd);
- esym_end = esym + obj_raw_syment_count (input_bfd) * isymesz;
- sym_hash = obj_xcoff_sym_hashes (input_bfd);
- csectpp = xcoff_data (input_bfd)->csects;
- debug_index = xcoff_data (input_bfd)->debug_indices;
- isymp = finfo->internal_syms;
- indexp = finfo->sym_indices;
- output_index = syment_base;
- outsym = finfo->outsyms;
- incls = 0;
- oline = NULL;
+ /* Copy over the line numbers, unless we are stripping
+ them. We do this on a symbol by symbol basis in
+ order to more easily handle garbage collection. */
+ if ((isymp->n_sclass == C_EXT
+ || isymp->n_sclass == C_HIDEXT)
+ && i == 0
+ && isymp->n_numaux > 1
+ && ISFCN (isymp->n_type)
+ && aux.x_sym.x_fcnary.x_fcn.x_lnnoptr != 0)
+ {
+ if (finfo->info->strip != strip_none
+ && finfo->info->strip != strip_some)
+ aux.x_sym.x_fcnary.x_fcn.x_lnnoptr = 0;
+ else
+ {
+ asection *enclosing;
+ unsigned int enc_count;
+ bfd_signed_vma linoff;
+ struct internal_lineno lin;
- while (esym < esym_end)
- {
+ o = *csectpp;
+ enclosing = xcoff_section_data (abfd, o)->enclosing;
+ enc_count = xcoff_section_data (abfd, o)->lineno_count;
+ if (oline != enclosing)
+ {
+ file_ptr pos = enclosing->line_filepos;
+ bfd_size_type amt = linesz * enc_count;
+ if (bfd_seek (input_bfd, pos, SEEK_SET) != 0
+ || (bfd_bread (finfo->linenos, amt, input_bfd)
+ != amt))
+ return FALSE;
+ oline = enclosing;
+ }
- struct internal_syment isym;
- union internal_auxent aux;
- int smtyp = 0;
- bfd_boolean skip;
- bfd_boolean require;
- int add;
+ linoff = (aux.x_sym.x_fcnary.x_fcn.x_lnnoptr
+ - enclosing->line_filepos);
- bfd_coff_swap_sym_in (input_bfd, (PTR) esym, (PTR) isymp);
+ bfd_coff_swap_lineno_in (input_bfd,
+ (void *) (finfo->linenos + linoff),
+ (void *) &lin);
+ if (lin.l_lnno != 0
+ || ((bfd_size_type) lin.l_addr.l_symndx
+ != ((esym
+ - isymesz
+ - ((bfd_byte *)
+ obj_coff_external_syms (input_bfd)))
+ / isymesz)))
+ aux.x_sym.x_fcnary.x_fcn.x_lnnoptr = 0;
+ else
+ {
+ bfd_byte *linpend, *linp;
+ bfd_vma offset;
+ bfd_size_type count;
- /* If this is a C_EXT or C_HIDEXT symbol, we need the csect
- information. */
- if (isymp->n_sclass == C_EXT || isymp->n_sclass == C_HIDEXT)
- {
- BFD_ASSERT (isymp->n_numaux > 0);
- bfd_coff_swap_aux_in (input_bfd,
- (PTR) (esym + isymesz * isymp->n_numaux),
- isymp->n_type, isymp->n_sclass,
- isymp->n_numaux - 1, isymp->n_numaux,
- (PTR) &aux);
+ lin.l_addr.l_symndx = *indexp;
+ bfd_coff_swap_lineno_out (output_bfd, (void *) &lin,
+ (void *) (finfo->linenos
+ + linoff));
- smtyp = SMTYP_SMTYP (aux.x_csect.x_smtyp);
- }
+ linpend = (finfo->linenos
+ + enc_count * linesz);
+ offset = (o->output_section->vma
+ + o->output_offset
+ - o->vma);
+ for (linp = finfo->linenos + linoff + linesz;
+ linp < linpend;
+ linp += linesz)
+ {
+ bfd_coff_swap_lineno_in (input_bfd, (void *) linp,
+ (void *) &lin);
+ if (lin.l_lnno == 0)
+ break;
+ lin.l_addr.l_paddr += offset;
+ bfd_coff_swap_lineno_out (output_bfd,
+ (void *) &lin,
+ (void *) linp);
+ }
- /* Make a copy of *isymp so that the relocate_section function
- always sees the original values. This is more reliable than
- always recomputing the symbol value even if we are stripping
- the symbol. */
- isym = *isymp;
+ count = (linp - (finfo->linenos + linoff)) / linesz;
- /* If this symbol is in the .loader section, swap out the
- .loader symbol information. If this is an external symbol
- reference to a defined symbol, though, then wait until we get
- to the definition. */
- if (isym.n_sclass == C_EXT
- && *sym_hash != NULL
- && (*sym_hash)->ldsym != NULL
- && (smtyp != XTY_ER
- || (*sym_hash)->root.type == bfd_link_hash_undefined))
- {
- struct xcoff_link_hash_entry *h;
- struct internal_ldsym *ldsym;
+ aux.x_sym.x_fcnary.x_fcn.x_lnnoptr =
+ (o->output_section->line_filepos
+ + o->output_section->lineno_count * linesz);
- h = *sym_hash;
- ldsym = h->ldsym;
- if (isym.n_scnum > 0)
- {
- ldsym->l_scnum = (*csectpp)->output_section->target_index;
- ldsym->l_value = (isym.n_value
- + (*csectpp)->output_section->vma
- + (*csectpp)->output_offset
- - (*csectpp)->vma);
- }
- else
- {
- ldsym->l_scnum = isym.n_scnum;
- ldsym->l_value = isym.n_value;
- }
+ if (bfd_seek (output_bfd,
+ aux.x_sym.x_fcnary.x_fcn.x_lnnoptr,
+ SEEK_SET) != 0
+ || (bfd_bwrite (finfo->linenos + linoff,
+ linesz * count, output_bfd)
+ != linesz * count))
+ return FALSE;
- ldsym->l_smtype = smtyp;
- if (((h->flags & XCOFF_DEF_REGULAR) == 0
- && (h->flags & XCOFF_DEF_DYNAMIC) != 0)
- || (h->flags & XCOFF_IMPORT) != 0)
- ldsym->l_smtype |= L_IMPORT;
- if (((h->flags & XCOFF_DEF_REGULAR) != 0
- && (h->flags & XCOFF_DEF_DYNAMIC) != 0)
- || (h->flags & XCOFF_EXPORT) != 0)
- ldsym->l_smtype |= L_EXPORT;
- if ((h->flags & XCOFF_ENTRY) != 0)
- ldsym->l_smtype |= L_ENTRY;
+ o->output_section->lineno_count += count;
- ldsym->l_smclas = aux.x_csect.x_smclas;
+ if (incls > 0)
+ {
+ struct internal_syment *iisp, *iispend;
+ long *iindp;
+ bfd_byte *oos;
+ int iiadd;
- if (ldsym->l_ifile == (bfd_size_type) -1)
- ldsym->l_ifile = 0;
- else if (ldsym->l_ifile == 0)
- {
- if ((ldsym->l_smtype & L_IMPORT) == 0)
- ldsym->l_ifile = 0;
- else
- {
- bfd *impbfd;
+ /* Update any C_BINCL or C_EINCL symbols
+ that refer to a line number in the
+ range we just output. */
+ iisp = finfo->internal_syms;
+ iispend = (iisp
+ + obj_raw_syment_count (input_bfd));
+ iindp = finfo->sym_indices;
+ oos = finfo->outsyms;
+ while (iisp < iispend)
+ {
+ if (*iindp >= 0
+ && (iisp->n_sclass == C_BINCL
+ || iisp->n_sclass == C_EINCL)
+ && ((bfd_size_type) iisp->n_value
+ >= (bfd_size_type)(enclosing->line_filepos + linoff))
+ && ((bfd_size_type) iisp->n_value
+ < (enclosing->line_filepos
+ + enc_count * linesz)))
+ {
+ struct internal_syment iis;
- if (h->root.type == bfd_link_hash_defined
- || h->root.type == bfd_link_hash_defweak)
- impbfd = h->root.u.def.section->owner;
- else if (h->root.type == bfd_link_hash_undefined
- || h->root.type == bfd_link_hash_undefweak)
- impbfd = h->root.u.undef.abfd;
- else
- impbfd = NULL;
+ bfd_coff_swap_sym_in (output_bfd,
+ (void *) oos,
+ (void *) &iis);
+ iis.n_value =
+ (iisp->n_value
+ - enclosing->line_filepos
+ - linoff
+ + aux.x_sym.x_fcnary.x_fcn.x_lnnoptr);
+ bfd_coff_swap_sym_out (output_bfd,
+ (void *) &iis,
+ (void *) oos);
+ --incls;
+ }
- if (impbfd == NULL)
- ldsym->l_ifile = 0;
- else
- {
- BFD_ASSERT (impbfd->xvec == finfo->output_bfd->xvec);
- ldsym->l_ifile = xcoff_data (impbfd)->import_file_id;
+ iiadd = 1 + iisp->n_numaux;
+ if (*iindp >= 0)
+ oos += iiadd * osymesz;
+ iisp += iiadd;
+ iindp += iiadd;
+ }
+ }
+ }
}
}
- }
-
- ldsym->l_parm = 0;
-
- BFD_ASSERT (h->ldindx >= 0);
- bfd_xcoff_swap_ldsym_out (finfo->output_bfd, ldsym,
- (finfo->ldsym
- + ((h->ldindx - 3)
- * bfd_xcoff_ldsymsz (finfo->output_bfd))));
- h->ldsym = NULL;
- /* Fill in snentry now that we know the target_index. */
- if ((h->flags & XCOFF_ENTRY) != 0
- && (h->root.type == bfd_link_hash_defined
- || h->root.type == bfd_link_hash_defweak))
- {
- xcoff_data (output_bfd)->snentry =
- h->root.u.def.section->output_section->target_index;
+ bfd_coff_swap_aux_out (output_bfd, (void *) &aux, isymp->n_type,
+ isymp->n_sclass, i, isymp->n_numaux,
+ (void *) outsym);
+ outsym += osymesz;
+ esym += isymesz;
}
}
- *indexp = -1;
-
- skip = FALSE;
- require = FALSE;
- add = 1 + isym.n_numaux;
+ indexp += add;
+ isymp += add;
+ csectpp += add;
+ }
- /* If we are skipping this csect, we want to skip this symbol. */
- if (*csectpp == NULL)
- skip = TRUE;
-
- /* If we garbage collected this csect, we want to skip this
- symbol. */
- if (! skip
- && xcoff_hash_table (finfo->info)->gc
- && ((*csectpp)->flags & SEC_MARK) == 0
- && *csectpp != bfd_abs_section_ptr)
- skip = TRUE;
-
- /* An XCOFF linker always skips C_STAT symbols. */
- if (! skip
- && isymp->n_sclass == C_STAT)
- skip = TRUE;
-
- /* We skip all but the first TOC anchor. */
- if (! skip
- && isymp->n_sclass == C_HIDEXT
- && aux.x_csect.x_smclas == XMC_TC0)
- {
- if (finfo->toc_symindx != -1)
- skip = TRUE;
- else
- {
- bfd_vma tocval, tocend;
- bfd *inp;
-
- tocval = ((*csectpp)->output_section->vma
- + (*csectpp)->output_offset
- + isym.n_value
- - (*csectpp)->vma);
+ /* If we swapped out a C_FILE symbol, guess that the next C_FILE
+ symbol will be the first symbol in the next input file. In the
+ normal case, this will save us from writing out the C_FILE symbol
+ again. */
+ if (finfo->last_file_index != -1
+ && (bfd_size_type) finfo->last_file_index >= syment_base)
+ {
+ finfo->last_file.n_value = output_index;
+ bfd_coff_swap_sym_out (output_bfd, (void *) &finfo->last_file,
+ (void *) (finfo->outsyms
+ + ((finfo->last_file_index - syment_base)
+ * osymesz)));
+ }
- /* We want to find out if tocval is a good value to use
- as the TOC anchor--that is, whether we can access all
- of the TOC using a 16 bit offset from tocval. This
- test assumes that the TOC comes at the end of the
- output section, as it does in the default linker
- script. */
- tocend = ((*csectpp)->output_section->vma
- + (*csectpp)->output_section->size);
- for (inp = finfo->info->input_bfds;
- inp != NULL;
- inp = inp->link_next)
- {
+ /* Write the modified symbols to the output file. */
+ if (outsym > finfo->outsyms)
+ {
+ file_ptr pos = obj_sym_filepos (output_bfd) + syment_base * osymesz;
+ bfd_size_type amt = outsym - finfo->outsyms;
+ if (bfd_seek (output_bfd, pos, SEEK_SET) != 0
+ || bfd_bwrite (finfo->outsyms, amt, output_bfd) != amt)
+ return FALSE;
- for (o = inp->sections; o != NULL; o = o->next)
- if (strcmp (o->name, ".tocbss") == 0)
- {
- bfd_vma new_toc_end;
- new_toc_end = (o->output_section->vma
- + o->output_offset
- + o->size);
- if (new_toc_end > tocend)
- tocend = new_toc_end;
- }
+ BFD_ASSERT ((obj_raw_syment_count (output_bfd)
+ + (outsym - finfo->outsyms) / osymesz)
+ == output_index);
- }
+ obj_raw_syment_count (output_bfd) = output_index;
+ }
- if (tocval + 0x10000 < tocend)
- {
- (*_bfd_error_handler)
- (_("TOC overflow: 0x%lx > 0x10000; try -mminimal-toc when compiling"),
- (unsigned long) (tocend - tocval));
- bfd_set_error (bfd_error_file_too_big);
- return FALSE;
- }
+ /* Don't let the linker relocation routines discard the symbols. */
+ keep_syms = obj_coff_keep_syms (input_bfd);
+ obj_coff_keep_syms (input_bfd) = TRUE;
- if (tocval + 0x8000 < tocend)
- {
- bfd_vma tocadd;
+ /* Relocate the contents of each section. */
+ for (o = input_bfd->sections; o != NULL; o = o->next)
+ {
+ bfd_byte *contents;
- tocadd = tocend - (tocval + 0x8000);
- tocval += tocadd;
- isym.n_value += tocadd;
- }
+ if (! o->linker_mark)
+ /* This section was omitted from the link. */
+ continue;
- finfo->toc_symindx = output_index;
- xcoff_data (finfo->output_bfd)->toc = tocval;
- xcoff_data (finfo->output_bfd)->sntoc =
- (*csectpp)->output_section->target_index;
- require = TRUE;
+ if ((o->flags & SEC_HAS_CONTENTS) == 0
+ || o->size == 0
+ || (o->flags & SEC_IN_MEMORY) != 0)
+ continue;
- }
+ /* We have set filepos correctly for the sections we created to
+ represent csects, so bfd_get_section_contents should work. */
+ if (coff_section_data (input_bfd, o) != NULL
+ && coff_section_data (input_bfd, o)->contents != NULL)
+ contents = coff_section_data (input_bfd, o)->contents;
+ else
+ {
+ bfd_size_type sz = o->rawsize ? o->rawsize : o->size;
+ if (!bfd_get_section_contents (input_bfd, o, finfo->contents, 0, sz))
+ return FALSE;
+ contents = finfo->contents;
}
- /* If we are stripping all symbols, we want to skip this one. */
- if (! skip
- && finfo->info->strip == strip_all)
- skip = TRUE;
-
- /* We can skip resolved external references. */
- if (! skip
- && isym.n_sclass == C_EXT
- && smtyp == XTY_ER
- && (*sym_hash)->root.type != bfd_link_hash_undefined)
- skip = TRUE;
-
- /* We can skip common symbols if they got defined somewhere
- else. */
- if (! skip
- && isym.n_sclass == C_EXT
- && smtyp == XTY_CM
- && ((*sym_hash)->root.type != bfd_link_hash_common
- || (*sym_hash)->root.u.c.p->section != *csectpp)
- && ((*sym_hash)->root.type != bfd_link_hash_defined
- || (*sym_hash)->root.u.def.section != *csectpp))
- skip = TRUE;
-
- /* Skip local symbols if we are discarding them. */
- if (! skip
- && finfo->info->discard == discard_all
- && isym.n_sclass != C_EXT
- && (isym.n_sclass != C_HIDEXT
- || smtyp != XTY_SD))
- skip = TRUE;
-
- /* If we stripping debugging symbols, and this is a debugging
- symbol, then skip it. */
- if (! skip
- && finfo->info->strip == strip_debugger
- && isym.n_scnum == N_DEBUG)
- skip = TRUE;
-
- /* If some symbols are stripped based on the name, work out the
- name and decide whether to skip this symbol. We don't handle
- this correctly for symbols whose names are in the .debug
- section; to get it right we would need a new bfd_strtab_hash
- function to return the string given the index. */
- if (! skip
- && (finfo->info->strip == strip_some
- || finfo->info->discard == discard_l)
- && (debug_index == NULL || *debug_index == (unsigned long) -1))
+ if ((o->flags & SEC_RELOC) != 0)
{
- const char *name;
- char buf[SYMNMLEN + 1];
+ int target_index;
+ struct internal_reloc *internal_relocs;
+ struct internal_reloc *irel;
+ bfd_vma offset;
+ struct internal_reloc *irelend;
+ struct xcoff_link_hash_entry **rel_hash;
+ long r_symndx;
- name = _bfd_coff_internal_syment_name (input_bfd, &isym, buf);
+ /* Read in the relocs. */
+ target_index = o->output_section->target_index;
+ internal_relocs = (xcoff_read_internal_relocs
+ (input_bfd, o, FALSE, finfo->external_relocs,
+ TRUE,
+ (finfo->section_info[target_index].relocs
+ + o->output_section->reloc_count)));
+ if (internal_relocs == NULL)
+ return FALSE;
- if (name == NULL)
+ /* Call processor specific code to relocate the section
+ contents. */
+ if (! bfd_coff_relocate_section (output_bfd, finfo->info,
+ input_bfd, o,
+ contents,
+ internal_relocs,
+ finfo->internal_syms,
+ xcoff_data (input_bfd)->csects))
return FALSE;
- if ((finfo->info->strip == strip_some
- && (bfd_hash_lookup (finfo->info->keep_hash, name, FALSE,
- FALSE) == NULL))
- || (finfo->info->discard == discard_l
- && (isym.n_sclass != C_EXT
- && (isym.n_sclass != C_HIDEXT
- || smtyp != XTY_SD))
- && bfd_is_local_label_name (input_bfd, name)))
- skip = TRUE;
- }
+ offset = o->output_section->vma + o->output_offset - o->vma;
+ irel = internal_relocs;
+ irelend = irel + o->reloc_count;
+ rel_hash = (finfo->section_info[target_index].rel_hashes
+ + o->output_section->reloc_count);
+ for (; irel < irelend; irel++, rel_hash++)
+ {
+ struct xcoff_link_hash_entry *h = NULL;
+ struct internal_ldrel ldrel;
+ bfd_boolean quiet;
- /* We can not skip the first TOC anchor. */
- if (skip
- && require
- && finfo->info->strip != strip_all)
- skip = FALSE;
+ *rel_hash = NULL;
- /* We now know whether we are to skip this symbol or not. */
- if (! skip)
- {
- /* Adjust the symbol in order to output it. */
+ /* Adjust the reloc address and symbol index. */
- if (isym._n._n_n._n_zeroes == 0
- && isym._n._n_n._n_offset != 0)
- {
- /* This symbol has a long name. Enter it in the string
- table we are building. If *debug_index != -1, the
- name has already been entered in the .debug section. */
- if (debug_index != NULL && *debug_index != (unsigned long) -1)
- isym._n._n_n._n_offset = *debug_index;
- else
- {
- const char *name;
- bfd_size_type indx;
+ irel->r_vaddr += offset;
- name = _bfd_coff_internal_syment_name (input_bfd, &isym,
- (char *) NULL);
+ r_symndx = irel->r_symndx;
- if (name == NULL)
- return FALSE;
- indx = _bfd_stringtab_add (finfo->strtab, name, hash, copy);
- if (indx == (bfd_size_type) -1)
- return FALSE;
- isym._n._n_n._n_offset = STRING_SIZE_SIZE + indx;
- }
- }
+ if (r_symndx == -1)
+ h = NULL;
+ else
+ h = obj_xcoff_sym_hashes (input_bfd)[r_symndx];
- if (isym.n_sclass != C_BSTAT
- && isym.n_sclass != C_ESTAT
- && isym.n_sclass != C_DECL
- && isym.n_scnum > 0)
- {
- isym.n_scnum = (*csectpp)->output_section->target_index;
- isym.n_value += ((*csectpp)->output_section->vma
- + (*csectpp)->output_offset
- - (*csectpp)->vma);
- }
-
- /* The value of a C_FILE symbol is the symbol index of the
- next C_FILE symbol. The value of the last C_FILE symbol
- is -1. We try to get this right, below, just before we
- write the symbols out, but in the general case we may
- have to write the symbol out twice. */
- if (isym.n_sclass == C_FILE)
- {
- if (finfo->last_file_index != -1
- && finfo->last_file.n_value != (bfd_vma) output_index)
+ if (r_symndx != -1 && finfo->info->strip != strip_all)
{
- /* We must correct the value of the last C_FILE entry. */
- finfo->last_file.n_value = output_index;
- if ((bfd_size_type) finfo->last_file_index >= syment_base)
+ if (h != NULL
+ && h->smclas != XMC_TD
+ && (irel->r_type == R_TOC
+ || irel->r_type == R_GL
+ || irel->r_type == R_TCL
+ || irel->r_type == R_TRL
+ || irel->r_type == R_TRLA))
{
- /* The last C_FILE symbol is in this input file. */
- bfd_coff_swap_sym_out (output_bfd,
- (PTR) &finfo->last_file,
- (PTR) (finfo->outsyms
- + ((finfo->last_file_index
- - syment_base)
- * osymesz)));
+ /* This is a TOC relative reloc with a symbol
+ attached. The symbol should be the one which
+ this reloc is for. We want to make this
+ reloc against the TOC address of the symbol,
+ not the symbol itself. */
+ BFD_ASSERT (h->toc_section != NULL);
+ BFD_ASSERT ((h->flags & XCOFF_SET_TOC) == 0);
+ if (h->u.toc_indx != -1)
+ irel->r_symndx = h->u.toc_indx;
+ else
+ {
+ struct xcoff_toc_rel_hash *n;
+ struct xcoff_link_section_info *si;
+ bfd_size_type amt;
+
+ amt = sizeof (* n);
+ n = bfd_alloc (finfo->output_bfd, amt);
+ if (n == NULL)
+ return FALSE;
+ si = finfo->section_info + target_index;
+ n->next = si->toc_rel_hashes;
+ n->h = h;
+ n->rel = irel;
+ si->toc_rel_hashes = n;
+ }
}
- else
+ else if (h != NULL)
{
- /* We have already written out the last C_FILE
- symbol. We need to write it out again. We
- borrow *outsym temporarily. */
- file_ptr pos;
-
- bfd_coff_swap_sym_out (output_bfd,
- (PTR) &finfo->last_file,
- (PTR) outsym);
-
- pos = obj_sym_filepos (output_bfd);
- pos += finfo->last_file_index * osymesz;
- if (bfd_seek (output_bfd, pos, SEEK_SET) != 0
- || (bfd_bwrite (outsym, osymesz, output_bfd)
- != osymesz))
- return FALSE;
+ /* This is a global symbol. */
+ if (h->indx >= 0)
+ irel->r_symndx = h->indx;
+ else
+ {
+ /* This symbol is being written at the end
+ of the file, and we do not yet know the
+ symbol index. We save the pointer to the
+ hash table entry in the rel_hash list.
+ We set the indx field to -2 to indicate
+ that this symbol must not be stripped. */
+ *rel_hash = h;
+ h->indx = -2;
+ }
}
- }
-
- finfo->last_file_index = output_index;
- finfo->last_file = isym;
- }
-
- /* The value of a C_BINCL or C_EINCL symbol is a file offset
- into the line numbers. We update the symbol values when
- we handle the line numbers. */
- if (isym.n_sclass == C_BINCL
- || isym.n_sclass == C_EINCL)
- {
- isym.n_value = finfo->line_filepos;
- ++incls;
- }
-
- /* Output the symbol. */
-
- bfd_coff_swap_sym_out (output_bfd, (PTR) &isym, (PTR) outsym);
-
- *indexp = output_index;
-
- if (isym.n_sclass == C_EXT)
- {
- long indx;
- struct xcoff_link_hash_entry *h;
-
- indx = ((esym - (bfd_byte *) obj_coff_external_syms (input_bfd))
- / isymesz);
- h = obj_xcoff_sym_hashes (input_bfd)[indx];
- BFD_ASSERT (h != NULL);
- h->indx = output_index;
- }
+ else
+ {
+ long indx;
- /* If this is a symbol in the TOC which we may have merged
- (class XMC_TC), remember the symbol index of the TOC
- symbol. */
- if (isym.n_sclass == C_HIDEXT
- && aux.x_csect.x_smclas == XMC_TC
- && *sym_hash != NULL)
- {
- BFD_ASSERT (((*sym_hash)->flags & XCOFF_SET_TOC) == 0);
- BFD_ASSERT ((*sym_hash)->toc_section != NULL);
- (*sym_hash)->u.toc_indx = output_index;
- }
+ indx = finfo->sym_indices[r_symndx];
- output_index += add;
- outsym += add * osymesz;
- }
+ if (indx == -1)
+ {
+ struct internal_syment *is;
- esym += add * isymesz;
- isymp += add;
- csectpp += add;
- sym_hash += add;
- if (debug_index != NULL)
- debug_index += add;
- ++indexp;
- for (--add; add > 0; --add)
- *indexp++ = -1;
- }
+ /* Relocations against a TC0 TOC anchor are
+ automatically transformed to be against
+ the TOC anchor in the output file. */
+ is = finfo->internal_syms + r_symndx;
+ if (is->n_sclass == C_HIDEXT
+ && is->n_numaux > 0)
+ {
+ void * auxptr;
+ union internal_auxent aux;
- /* Fix up the aux entries and the C_BSTAT symbols. This must be
- done in a separate pass, because we don't know the correct symbol
- indices until we have already decided which symbols we are going
- to keep. */
+ auxptr = ((void *)
+ (((bfd_byte *)
+ obj_coff_external_syms (input_bfd))
+ + ((r_symndx + is->n_numaux)
+ * isymesz)));
+ bfd_coff_swap_aux_in (input_bfd, auxptr,
+ is->n_type, is->n_sclass,
+ is->n_numaux - 1,
+ is->n_numaux,
+ (void *) &aux);
+ if (SMTYP_SMTYP (aux.x_csect.x_smtyp) == XTY_SD
+ && aux.x_csect.x_smclas == XMC_TC0)
+ indx = finfo->toc_symindx;
+ }
+ }
- esym = (bfd_byte *) obj_coff_external_syms (input_bfd);
- esym_end = esym + obj_raw_syment_count (input_bfd) * isymesz;
- isymp = finfo->internal_syms;
- indexp = finfo->sym_indices;
- csectpp = xcoff_data (input_bfd)->csects;
- outsym = finfo->outsyms;
- while (esym < esym_end)
- {
- int add;
+ if (indx != -1)
+ irel->r_symndx = indx;
+ else
+ {
- add = 1 + isymp->n_numaux;
+ struct internal_syment *is;
- if (*indexp < 0)
- esym += add * isymesz;
- else
- {
- int i;
+ const char *name;
+ char buf[SYMNMLEN + 1];
- if (isymp->n_sclass == C_BSTAT)
- {
- struct internal_syment isym;
+ /* This reloc is against a symbol we are
+ stripping. It would be possible to handle
+ this case, but I don't think it's worth it. */
+ is = finfo->internal_syms + r_symndx;
- bfd_vma indx;
+ name = (_bfd_coff_internal_syment_name
+ (input_bfd, is, buf));
- /* The value of a C_BSTAT symbol is the symbol table
- index of the containing csect. */
- bfd_coff_swap_sym_in (output_bfd, (PTR) outsym, (PTR) &isym);
- indx = isym.n_value;
- if (indx < obj_raw_syment_count (input_bfd))
- {
- long symindx;
+ if (name == NULL)
+ return FALSE;
- symindx = finfo->sym_indices[indx];
- if (symindx < 0)
- isym.n_value = 0;
- else
- isym.n_value = symindx;
- bfd_coff_swap_sym_out (output_bfd, (PTR) &isym,
- (PTR) outsym);
+ if (! ((*finfo->info->callbacks->unattached_reloc)
+ (finfo->info, name, input_bfd, o,
+ irel->r_vaddr)))
+ return FALSE;
+ }
+ }
}
- }
-
- esym += isymesz;
- outsym += osymesz;
-
- for (i = 0; i < isymp->n_numaux && esym < esym_end; i++)
- {
- union internal_auxent aux;
-
- bfd_coff_swap_aux_in (input_bfd, (PTR) esym, isymp->n_type,
- isymp->n_sclass, i, isymp->n_numaux,
- (PTR) &aux);
- if (isymp->n_sclass == C_FILE)
+ quiet = FALSE;
+ switch (irel->r_type)
{
- /* This is the file name (or some comment put in by
- the compiler). If it is long, we must put it in
- the string table. */
- if (aux.x_file.x_n.x_zeroes == 0
- && aux.x_file.x_n.x_offset != 0)
- {
- const char *filename;
- bfd_size_type indx;
-
- BFD_ASSERT (aux.x_file.x_n.x_offset
- >= STRING_SIZE_SIZE);
- if (strings == NULL)
- {
- strings = _bfd_coff_read_string_table (input_bfd);
- if (strings == NULL)
- return FALSE;
- }
- filename = strings + aux.x_file.x_n.x_offset;
- indx = _bfd_stringtab_add (finfo->strtab, filename,
- hash, copy);
- if (indx == (bfd_size_type) -1)
- return FALSE;
- aux.x_file.x_n.x_offset = STRING_SIZE_SIZE + indx;
- }
- }
- else if ((isymp->n_sclass == C_EXT
- || isymp->n_sclass == C_HIDEXT)
- && i + 1 == isymp->n_numaux)
- {
-
- /* We don't support type checking. I don't know if
- anybody does. */
- aux.x_csect.x_parmhash = 0;
- /* I don't think anybody uses these fields, but we'd
- better clobber them just in case. */
- aux.x_csect.x_stab = 0;
- aux.x_csect.x_snstab = 0;
-
- if (SMTYP_SMTYP (aux.x_csect.x_smtyp) == XTY_LD)
+ default:
+ if (h == NULL
+ || h->root.type == bfd_link_hash_defined
+ || h->root.type == bfd_link_hash_defweak
+ || h->root.type == bfd_link_hash_common)
+ break;
+ /* Fall through. */
+ case R_POS:
+ case R_NEG:
+ case R_RL:
+ case R_RLA:
+ /* This reloc needs to be copied into the .loader
+ section. */
+ ldrel.l_vaddr = irel->r_vaddr;
+ if (r_symndx == -1)
+ ldrel.l_symndx = -(bfd_size_type ) 1;
+ else if (h == NULL
+ || (h->root.type == bfd_link_hash_defined
+ || h->root.type == bfd_link_hash_defweak
+ || h->root.type == bfd_link_hash_common))
{
- unsigned long indx;
+ asection *sec;
- indx = aux.x_csect.x_scnlen.l;
- if (indx < obj_raw_syment_count (input_bfd))
- {
- long symindx;
+ if (h == NULL)
+ sec = xcoff_data (input_bfd)->csects[r_symndx];
+ else if (h->root.type == bfd_link_hash_common)
+ sec = h->root.u.c.p->section;
+ else
+ sec = h->root.u.def.section;
+ sec = sec->output_section;
- symindx = finfo->sym_indices[indx];
- if (symindx < 0)
- {
- aux.x_csect.x_scnlen.l = 0;
- }
- else
- {
- aux.x_csect.x_scnlen.l = symindx;
- }
+ if (strcmp (sec->name, ".text") == 0)
+ ldrel.l_symndx = 0;
+ else if (strcmp (sec->name, ".data") == 0)
+ ldrel.l_symndx = 1;
+ else if (strcmp (sec->name, ".bss") == 0)
+ ldrel.l_symndx = 2;
+ else
+ {
+ (*_bfd_error_handler)
+ (_("%B: loader reloc in unrecognized section `%A'"),
+ input_bfd, sec);
+ bfd_set_error (bfd_error_nonrepresentable_section);
+ return FALSE;
}
}
- }
- else if (isymp->n_sclass != C_STAT || isymp->n_type != T_NULL)
- {
- unsigned long indx;
-
- if (ISFCN (isymp->n_type)
- || ISTAG (isymp->n_sclass)
- || isymp->n_sclass == C_BLOCK
- || isymp->n_sclass == C_FCN)
+ else
{
- indx = aux.x_sym.x_fcnary.x_fcn.x_endndx.l;
- if (indx > 0
- && indx < obj_raw_syment_count (input_bfd))
+ if (! finfo->info->relocatable
+ && (h->flags & XCOFF_DEF_DYNAMIC) == 0
+ && (h->flags & XCOFF_IMPORT) == 0)
{
- /* We look forward through the symbol for
- the index of the next symbol we are going
- to include. I don't know if this is
- entirely right. */
- while (finfo->sym_indices[indx] < 0
- && indx < obj_raw_syment_count (input_bfd))
- ++indx;
- if (indx >= obj_raw_syment_count (input_bfd))
- indx = output_index;
- else
- indx = finfo->sym_indices[indx];
- aux.x_sym.x_fcnary.x_fcn.x_endndx.l = indx;
-
+ /* We already called the undefined_symbol
+ callback for this relocation, in
+ _bfd_ppc_xcoff_relocate_section. Don't
+ issue any more warnings. */
+ quiet = TRUE;
}
+ if (h->ldindx < 0 && ! quiet)
+ {
+ (*_bfd_error_handler)
+ (_("%B: `%s' in loader reloc but not loader sym"),
+ input_bfd,
+ h->root.root.string);
+ bfd_set_error (bfd_error_bad_value);
+ return FALSE;
+ }
+ ldrel.l_symndx = h->ldindx;
}
-
- indx = aux.x_sym.x_tagndx.l;
- if (indx > 0 && indx < obj_raw_syment_count (input_bfd))
+ ldrel.l_rtype = (irel->r_size << 8) | irel->r_type;
+ ldrel.l_rsecnm = o->output_section->target_index;
+ if (xcoff_hash_table (finfo->info)->textro
+ && strcmp (o->output_section->name, ".text") == 0
+ && ! quiet)
{
- long symindx;
-
- symindx = finfo->sym_indices[indx];
- if (symindx < 0)
- aux.x_sym.x_tagndx.l = 0;
- else
- aux.x_sym.x_tagndx.l = symindx;
+ (*_bfd_error_handler)
+ (_("%B: loader reloc in read-only section %A"),
+ input_bfd, o->output_section);
+ bfd_set_error (bfd_error_invalid_operation);
+ return FALSE;
}
+ bfd_xcoff_swap_ldrel_out (output_bfd, &ldrel,
+ finfo->ldrel);
- }
+ finfo->ldrel += bfd_xcoff_ldrelsz(output_bfd);
+ break;
- /* Copy over the line numbers, unless we are stripping
- them. We do this on a symbol by symbol basis in
- order to more easily handle garbage collection. */
- if ((isymp->n_sclass == C_EXT
- || isymp->n_sclass == C_HIDEXT)
- && i == 0
- && isymp->n_numaux > 1
- && ISFCN (isymp->n_type)
- && aux.x_sym.x_fcnary.x_fcn.x_lnnoptr != 0)
- {
- if (finfo->info->strip != strip_none
- && finfo->info->strip != strip_some)
- aux.x_sym.x_fcnary.x_fcn.x_lnnoptr = 0;
- else
- {
- asection *enclosing;
- unsigned int enc_count;
- bfd_signed_vma linoff;
- struct internal_lineno lin;
+ case R_TOC:
+ case R_GL:
+ case R_TCL:
+ case R_TRL:
+ case R_TRLA:
+ /* We should never need a .loader reloc for a TOC
+ relative reloc. */
+ break;
+ }
+ }
- o = *csectpp;
- enclosing = xcoff_section_data (abfd, o)->enclosing;
- enc_count = xcoff_section_data (abfd, o)->lineno_count;
- if (oline != enclosing)
- {
- file_ptr pos = enclosing->line_filepos;
- bfd_size_type amt = linesz * enc_count;
- if (bfd_seek (input_bfd, pos, SEEK_SET) != 0
- || (bfd_bread (finfo->linenos, amt, input_bfd)
- != amt))
- return FALSE;
- oline = enclosing;
- }
+ o->output_section->reloc_count += o->reloc_count;
+ }
- linoff = (aux.x_sym.x_fcnary.x_fcn.x_lnnoptr
- - enclosing->line_filepos);
+ /* Write out the modified section contents. */
+ if (! bfd_set_section_contents (output_bfd, o->output_section,
+ contents, (file_ptr) o->output_offset,
+ o->size))
+ return FALSE;
+ }
- bfd_coff_swap_lineno_in (input_bfd,
- (PTR) (finfo->linenos + linoff),
- (PTR) &lin);
- if (lin.l_lnno != 0
- || ((bfd_size_type) lin.l_addr.l_symndx
- != ((esym
- - isymesz
- - ((bfd_byte *)
- obj_coff_external_syms (input_bfd)))
- / isymesz)))
- aux.x_sym.x_fcnary.x_fcn.x_lnnoptr = 0;
- else
- {
- bfd_byte *linpend, *linp;
- bfd_vma offset;
- bfd_size_type count;
+ obj_coff_keep_syms (input_bfd) = keep_syms;
- lin.l_addr.l_symndx = *indexp;
- bfd_coff_swap_lineno_out (output_bfd, (PTR) &lin,
- (PTR) (finfo->linenos
- + linoff));
+ if (! finfo->info->keep_memory)
+ {
+ if (! _bfd_coff_free_symbols (input_bfd))
+ return FALSE;
+ }
- linpend = (finfo->linenos
- + enc_count * linesz);
- offset = (o->output_section->vma
- + o->output_offset
- - o->vma);
- for (linp = finfo->linenos + linoff + linesz;
- linp < linpend;
- linp += linesz)
- {
- bfd_coff_swap_lineno_in (input_bfd, (PTR) linp,
- (PTR) &lin);
- if (lin.l_lnno == 0)
- break;
- lin.l_addr.l_paddr += offset;
- bfd_coff_swap_lineno_out (output_bfd,
- (PTR) &lin,
- (PTR) linp);
- }
+ return TRUE;
+}
- count = (linp - (finfo->linenos + linoff)) / linesz;
+#undef N_TMASK
+#undef N_BTSHFT
- aux.x_sym.x_fcnary.x_fcn.x_lnnoptr =
- (o->output_section->line_filepos
- + o->output_section->lineno_count * linesz);
+/* Sort relocs by VMA. This is called via qsort. */
- if (bfd_seek (output_bfd,
- aux.x_sym.x_fcnary.x_fcn.x_lnnoptr,
- SEEK_SET) != 0
- || (bfd_bwrite (finfo->linenos + linoff,
- linesz * count, output_bfd)
- != linesz * count))
- return FALSE;
+static int
+xcoff_sort_relocs (const void * p1, const void * p2)
+{
+ const struct internal_reloc *r1 = (const struct internal_reloc *) p1;
+ const struct internal_reloc *r2 = (const struct internal_reloc *) p2;
- o->output_section->lineno_count += count;
-
- if (incls > 0)
- {
- struct internal_syment *iisp, *iispend;
- long *iindp;
- bfd_byte *oos;
- int iiadd;
-
- /* Update any C_BINCL or C_EINCL symbols
- that refer to a line number in the
- range we just output. */
- iisp = finfo->internal_syms;
- iispend = (iisp
- + obj_raw_syment_count (input_bfd));
- iindp = finfo->sym_indices;
- oos = finfo->outsyms;
- while (iisp < iispend)
- {
- if (*iindp >= 0
- && (iisp->n_sclass == C_BINCL
- || iisp->n_sclass == C_EINCL)
- && ((bfd_size_type) iisp->n_value
- >= (bfd_size_type)(enclosing->line_filepos + linoff))
- && ((bfd_size_type) iisp->n_value
- < (enclosing->line_filepos
- + enc_count * linesz)))
- {
- struct internal_syment iis;
-
- bfd_coff_swap_sym_in (output_bfd,
- (PTR) oos,
- (PTR) &iis);
- iis.n_value =
- (iisp->n_value
- - enclosing->line_filepos
- - linoff
- + aux.x_sym.x_fcnary.x_fcn.x_lnnoptr);
- bfd_coff_swap_sym_out (output_bfd,
- (PTR) &iis,
- (PTR) oos);
- --incls;
- }
+ if (r1->r_vaddr > r2->r_vaddr)
+ return 1;
+ else if (r1->r_vaddr < r2->r_vaddr)
+ return -1;
+ else
+ return 0;
+}
- iiadd = 1 + iisp->n_numaux;
- if (*iindp >= 0)
- oos += iiadd * osymesz;
- iisp += iiadd;
- iindp += iiadd;
- }
- }
- }
- }
- }
+/* Write out a non-XCOFF global symbol. */
- bfd_coff_swap_aux_out (output_bfd, (PTR) &aux, isymp->n_type,
- isymp->n_sclass, i, isymp->n_numaux,
- (PTR) outsym);
- outsym += osymesz;
- esym += isymesz;
- }
- }
+static bfd_boolean
+xcoff_write_global_symbol (struct xcoff_link_hash_entry *h, void * inf)
+{
+ struct xcoff_final_link_info *finfo = (struct xcoff_final_link_info *) inf;
+ bfd *output_bfd;
+ bfd_byte *outsym;
+ struct internal_syment isym;
+ union internal_auxent aux;
+ bfd_boolean result;
+ file_ptr pos;
+ bfd_size_type amt;
- indexp += add;
- isymp += add;
- csectpp += add;
- }
+ output_bfd = finfo->output_bfd;
+ outsym = finfo->outsyms;
- /* If we swapped out a C_FILE symbol, guess that the next C_FILE
- symbol will be the first symbol in the next input file. In the
- normal case, this will save us from writing out the C_FILE symbol
- again. */
- if (finfo->last_file_index != -1
- && (bfd_size_type) finfo->last_file_index >= syment_base)
+ if (h->root.type == bfd_link_hash_warning)
{
- finfo->last_file.n_value = output_index;
- bfd_coff_swap_sym_out (output_bfd, (PTR) &finfo->last_file,
- (PTR) (finfo->outsyms
- + ((finfo->last_file_index - syment_base)
- * osymesz)));
+ h = (struct xcoff_link_hash_entry *) h->root.u.i.link;
+ if (h->root.type == bfd_link_hash_new)
+ return TRUE;
}
- /* Write the modified symbols to the output file. */
- if (outsym > finfo->outsyms)
+ /* If this symbol was garbage collected, just skip it. */
+ if (xcoff_hash_table (finfo->info)->gc
+ && (h->flags & XCOFF_MARK) == 0)
+ return TRUE;
+
+ /* If we need a .loader section entry, write it out. */
+ if (h->ldsym != NULL)
{
- file_ptr pos = obj_sym_filepos (output_bfd) + syment_base * osymesz;
- bfd_size_type amt = outsym - finfo->outsyms;
- if (bfd_seek (output_bfd, pos, SEEK_SET) != 0
- || bfd_bwrite (finfo->outsyms, amt, output_bfd) != amt)
- return FALSE;
+ struct internal_ldsym *ldsym;
+ bfd *impbfd;
- BFD_ASSERT ((obj_raw_syment_count (output_bfd)
- + (outsym - finfo->outsyms) / osymesz)
- == output_index);
+ ldsym = h->ldsym;
- obj_raw_syment_count (output_bfd) = output_index;
- }
+ if (h->root.type == bfd_link_hash_undefined
+ || h->root.type == bfd_link_hash_undefweak)
+ {
- /* Don't let the linker relocation routines discard the symbols. */
- keep_syms = obj_coff_keep_syms (input_bfd);
- obj_coff_keep_syms (input_bfd) = TRUE;
+ ldsym->l_value = 0;
+ ldsym->l_scnum = N_UNDEF;
+ ldsym->l_smtype = XTY_ER;
+ impbfd = h->root.u.undef.abfd;
- /* Relocate the contents of each section. */
- for (o = input_bfd->sections; o != NULL; o = o->next)
- {
+ }
+ else if (h->root.type == bfd_link_hash_defined
+ || h->root.type == bfd_link_hash_defweak)
+ {
+ asection *sec;
- bfd_byte *contents;
+ sec = h->root.u.def.section;
+ ldsym->l_value = (sec->output_section->vma
+ + sec->output_offset
+ + h->root.u.def.value);
+ ldsym->l_scnum = sec->output_section->target_index;
+ ldsym->l_smtype = XTY_SD;
+ impbfd = sec->owner;
- if (! o->linker_mark)
- {
- /* This section was omitted from the link. */
- continue;
}
+ else
+ abort ();
- if ((o->flags & SEC_HAS_CONTENTS) == 0
- || o->size == 0
- || (o->flags & SEC_IN_MEMORY) != 0)
- continue;
+ if (((h->flags & XCOFF_DEF_REGULAR) == 0
+ && (h->flags & XCOFF_DEF_DYNAMIC) != 0)
+ || (h->flags & XCOFF_IMPORT) != 0)
+ /* Clear l_smtype
+ Import symbols are defined so the check above will make
+ the l_smtype XTY_SD. But this is not correct, it should
+ be cleared. */
+ ldsym->l_smtype |= L_IMPORT;
- /* We have set filepos correctly for the sections we created to
- represent csects, so bfd_get_section_contents should work. */
- if (coff_section_data (input_bfd, o) != NULL
- && coff_section_data (input_bfd, o)->contents != NULL)
- contents = coff_section_data (input_bfd, o)->contents;
- else
- {
- bfd_size_type sz = o->rawsize ? o->rawsize : o->size;
- if (!bfd_get_section_contents (input_bfd, o, finfo->contents, 0, sz))
- return FALSE;
- contents = finfo->contents;
- }
+ if (((h->flags & XCOFF_DEF_REGULAR) != 0
+ && (h->flags & XCOFF_DEF_DYNAMIC) != 0)
+ || (h->flags & XCOFF_EXPORT) != 0)
+ ldsym->l_smtype |= L_EXPORT;
- if ((o->flags & SEC_RELOC) != 0)
+ if ((h->flags & XCOFF_ENTRY) != 0)
+ ldsym->l_smtype |= L_ENTRY;
+
+ if ((h->flags & XCOFF_RTINIT) != 0)
+ ldsym->l_smtype = XTY_SD;
+
+ ldsym->l_smclas = h->smclas;
+
+ if (ldsym->l_smtype & L_IMPORT)
{
- int target_index;
- struct internal_reloc *internal_relocs;
- struct internal_reloc *irel;
- bfd_vma offset;
- struct internal_reloc *irelend;
- struct xcoff_link_hash_entry **rel_hash;
- long r_symndx;
+ if ((h->root.type == bfd_link_hash_defined
+ || h->root.type == bfd_link_hash_defweak)
+ && (h->root.u.def.value != 0))
+ ldsym->l_smclas = XMC_XO;
- /* Read in the relocs. */
- target_index = o->output_section->target_index;
- internal_relocs = (xcoff_read_internal_relocs
- (input_bfd, o, FALSE, finfo->external_relocs,
- TRUE,
- (finfo->section_info[target_index].relocs
- + o->output_section->reloc_count)));
- if (internal_relocs == NULL)
- return FALSE;
+ else if ((h->flags & (XCOFF_SYSCALL32 | XCOFF_SYSCALL64)) ==
+ (XCOFF_SYSCALL32 | XCOFF_SYSCALL64))
+ ldsym->l_smclas = XMC_SV3264;
- /* Call processor specific code to relocate the section
- contents. */
- if (! bfd_coff_relocate_section (output_bfd, finfo->info,
- input_bfd, o,
- contents,
- internal_relocs,
- finfo->internal_syms,
- xcoff_data (input_bfd)->csects))
- return FALSE;
+ else if (h->flags & XCOFF_SYSCALL32)
+ ldsym->l_smclas = XMC_SV;
- offset = o->output_section->vma + o->output_offset - o->vma;
- irel = internal_relocs;
- irelend = irel + o->reloc_count;
- rel_hash = (finfo->section_info[target_index].rel_hashes
- + o->output_section->reloc_count);
- for (; irel < irelend; irel++, rel_hash++)
+ else if (h->flags & XCOFF_SYSCALL64)
+ ldsym->l_smclas = XMC_SV64;
+ }
+
+ if (ldsym->l_ifile == -(bfd_size_type) 1)
+ {
+ ldsym->l_ifile = 0;
+ }
+ else if (ldsym->l_ifile == 0)
+ {
+ if ((ldsym->l_smtype & L_IMPORT) == 0)
+ ldsym->l_ifile = 0;
+ else if (impbfd == NULL)
+ ldsym->l_ifile = 0;
+ else
{
- struct xcoff_link_hash_entry *h = NULL;
- struct internal_ldrel ldrel;
- bfd_boolean quiet;
+ BFD_ASSERT (impbfd->xvec == output_bfd->xvec);
+ ldsym->l_ifile = xcoff_data (impbfd)->import_file_id;
+ }
+ }
- *rel_hash = NULL;
+ ldsym->l_parm = 0;
- /* Adjust the reloc address and symbol index. */
+ BFD_ASSERT (h->ldindx >= 0);
- irel->r_vaddr += offset;
+ bfd_xcoff_swap_ldsym_out (output_bfd, ldsym,
+ (finfo->ldsym +
+ (h->ldindx - 3)
+ * bfd_xcoff_ldsymsz(finfo->output_bfd)));
+ h->ldsym = NULL;
+ }
- r_symndx = irel->r_symndx;
+ /* If this symbol needs global linkage code, write it out. */
+ if (h->root.type == bfd_link_hash_defined
+ && (h->root.u.def.section
+ == xcoff_hash_table (finfo->info)->linkage_section))
+ {
+ bfd_byte *p;
+ bfd_vma tocoff;
+ unsigned int i;
- if (r_symndx == -1)
- h = NULL;
- else
- h = obj_xcoff_sym_hashes (input_bfd)[r_symndx];
+ p = h->root.u.def.section->contents + h->root.u.def.value;
- if (r_symndx != -1 && finfo->info->strip != strip_all)
- {
- if (h != NULL
- && h->smclas != XMC_TD
- && (irel->r_type == R_TOC
- || irel->r_type == R_GL
- || irel->r_type == R_TCL
- || irel->r_type == R_TRL
- || irel->r_type == R_TRLA))
- {
- /* This is a TOC relative reloc with a symbol
- attached. The symbol should be the one which
- this reloc is for. We want to make this
- reloc against the TOC address of the symbol,
- not the symbol itself. */
- BFD_ASSERT (h->toc_section != NULL);
- BFD_ASSERT ((h->flags & XCOFF_SET_TOC) == 0);
- if (h->u.toc_indx != -1)
- irel->r_symndx = h->u.toc_indx;
- else
- {
- struct xcoff_toc_rel_hash *n;
- struct xcoff_link_section_info *si;
- bfd_size_type amt;
+ /* The first instruction in the global linkage code loads a
+ specific TOC element. */
+ tocoff = (h->descriptor->toc_section->output_section->vma
+ + h->descriptor->toc_section->output_offset
+ - xcoff_data (output_bfd)->toc);
- amt = sizeof (struct xcoff_toc_rel_hash);
- n = ((struct xcoff_toc_rel_hash *)
- bfd_alloc (finfo->output_bfd, amt));
- if (n == NULL)
- return FALSE;
- si = finfo->section_info + target_index;
- n->next = si->toc_rel_hashes;
- n->h = h;
- n->rel = irel;
- si->toc_rel_hashes = n;
- }
- }
- else if (h != NULL)
- {
- /* This is a global symbol. */
- if (h->indx >= 0)
- irel->r_symndx = h->indx;
- else
- {
- /* This symbol is being written at the end
- of the file, and we do not yet know the
- symbol index. We save the pointer to the
- hash table entry in the rel_hash list.
- We set the indx field to -2 to indicate
- that this symbol must not be stripped. */
- *rel_hash = h;
- h->indx = -2;
- }
- }
- else
- {
- long indx;
+ if ((h->descriptor->flags & XCOFF_SET_TOC) != 0)
+ tocoff += h->descriptor->u.toc_offset;
- indx = finfo->sym_indices[r_symndx];
+ /* The first instruction in the glink code needs to be
+ cooked to to hold the correct offset in the toc. The
+ rest are just output raw. */
+ bfd_put_32 (output_bfd,
+ bfd_xcoff_glink_code(output_bfd, 0) | (tocoff & 0xffff), p);
- if (indx == -1)
- {
- struct internal_syment *is;
+ /* Start with i == 1 to get past the first instruction done above
+ The /4 is because the glink code is in bytes and we are going
+ 4 at a pop. */
+ for (i = 1; i < bfd_xcoff_glink_code_size(output_bfd) / 4; i++)
+ bfd_put_32 (output_bfd,
+ (bfd_vma) bfd_xcoff_glink_code(output_bfd, i),
+ &p[4 * i]);
+ }
- /* Relocations against a TC0 TOC anchor are
- automatically transformed to be against
- the TOC anchor in the output file. */
- is = finfo->internal_syms + r_symndx;
- if (is->n_sclass == C_HIDEXT
- && is->n_numaux > 0)
- {
- PTR auxptr;
- union internal_auxent aux;
+ /* If we created a TOC entry for this symbol, write out the required
+ relocs. */
+ if ((h->flags & XCOFF_SET_TOC) != 0)
+ {
+ asection *tocsec;
+ asection *osec;
+ int oindx;
+ struct internal_reloc *irel;
+ struct internal_ldrel ldrel;
+ struct internal_syment irsym;
+ union internal_auxent iraux;
- auxptr = ((PTR)
- (((bfd_byte *)
- obj_coff_external_syms (input_bfd))
- + ((r_symndx + is->n_numaux)
- * isymesz)));
- bfd_coff_swap_aux_in (input_bfd, auxptr,
- is->n_type, is->n_sclass,
- is->n_numaux - 1,
- is->n_numaux,
- (PTR) &aux);
- if (SMTYP_SMTYP (aux.x_csect.x_smtyp) == XTY_SD
- && aux.x_csect.x_smclas == XMC_TC0)
- indx = finfo->toc_symindx;
- }
- }
+ tocsec = h->toc_section;
+ osec = tocsec->output_section;
+ oindx = osec->target_index;
+ irel = finfo->section_info[oindx].relocs + osec->reloc_count;
+ irel->r_vaddr = (osec->vma
+ + tocsec->output_offset
+ + h->u.toc_offset);
+
+ if (h->indx >= 0)
+ irel->r_symndx = h->indx;
+ else
+ {
+ h->indx = -2;
+ irel->r_symndx = obj_raw_syment_count (output_bfd);
+ }
+
+ BFD_ASSERT (h->ldindx >= 0);
+
+ /* Initialize the aux union here instead of closer to when it is
+ written out below because the length of the csect depends on
+ whether the output is 32 or 64 bit. */
+ memset (&iraux, 0, sizeof iraux);
+ iraux.x_csect.x_smtyp = XTY_SD;
+ /* iraux.x_csect.x_scnlen.l = 4 or 8, see below. */
+ iraux.x_csect.x_smclas = XMC_TC;
+
+ /* 32 bit uses a 32 bit R_POS to do the relocations
+ 64 bit uses a 64 bit R_POS to do the relocations
+
+ Also needs to change the csect size : 4 for 32 bit, 8 for 64 bit
+
+ Which one is determined by the backend. */
+ if (bfd_xcoff_is_xcoff64 (output_bfd))
+ {
+ irel->r_size = 63;
+ iraux.x_csect.x_scnlen.l = 8;
+ }
+ else if (bfd_xcoff_is_xcoff32 (output_bfd))
+ {
+ irel->r_size = 31;
+ iraux.x_csect.x_scnlen.l = 4;
+ }
+ else
+ return FALSE;
+
+ irel->r_type = R_POS;
+ finfo->section_info[oindx].rel_hashes[osec->reloc_count] = NULL;
+ ++osec->reloc_count;
+
+ ldrel.l_vaddr = irel->r_vaddr;
+ ldrel.l_symndx = h->ldindx;
+ ldrel.l_rtype = (irel->r_size << 8) | R_POS;
+ ldrel.l_rsecnm = oindx;
+ bfd_xcoff_swap_ldrel_out (output_bfd, &ldrel, finfo->ldrel);
+ finfo->ldrel += bfd_xcoff_ldrelsz(output_bfd);
+
+ /* We need to emit a symbol to define a csect which holds
+ the reloc. */
+ if (finfo->info->strip != strip_all)
+ {
+ result = bfd_xcoff_put_symbol_name (output_bfd, finfo->strtab,
+ &irsym, h->root.root.string);
+ if (!result)
+ return FALSE;
+
+ irsym.n_value = irel->r_vaddr;
+ irsym.n_scnum = osec->target_index;
+ irsym.n_sclass = C_HIDEXT;
+ irsym.n_type = T_NULL;
+ irsym.n_numaux = 1;
+
+ bfd_coff_swap_sym_out (output_bfd, (void *) &irsym, (void *) outsym);
+ outsym += bfd_coff_symesz (output_bfd);
+
+ /* Note : iraux is initialized above. */
+ bfd_coff_swap_aux_out (output_bfd, (void *) &iraux, T_NULL, C_HIDEXT,
+ 0, 1, (void *) outsym);
+ outsym += bfd_coff_auxesz (output_bfd);
+
+ if (h->indx >= 0)
+ {
+ /* We aren't going to write out the symbols below, so we
+ need to write them out now. */
+ pos = obj_sym_filepos (output_bfd);
+ pos += (obj_raw_syment_count (output_bfd)
+ * bfd_coff_symesz (output_bfd));
+ amt = outsym - finfo->outsyms;
+ if (bfd_seek (output_bfd, pos, SEEK_SET) != 0
+ || bfd_bwrite (finfo->outsyms, amt, output_bfd) != amt)
+ return FALSE;
+ obj_raw_syment_count (output_bfd) +=
+ (outsym - finfo->outsyms) / bfd_coff_symesz (output_bfd);
+
+ outsym = finfo->outsyms;
+ }
+ }
+ }
+
+ /* If this symbol is a specially defined function descriptor, write
+ it out. The first word is the address of the function code
+ itself, the second word is the address of the TOC, and the third
+ word is zero.
+
+ 32 bit vs 64 bit
+ The addresses for the 32 bit will take 4 bytes and the addresses
+ for 64 bit will take 8 bytes. Similar for the relocs. This type
+ of logic was also done above to create a TOC entry in
+ xcoff_write_global_symbol. */
+ if ((h->flags & XCOFF_DESCRIPTOR) != 0
+ && h->root.type == bfd_link_hash_defined
+ && (h->root.u.def.section
+ == xcoff_hash_table (finfo->info)->descriptor_section))
+ {
+ asection *sec;
+ asection *osec;
+ int oindx;
+ bfd_byte *p;
+ struct xcoff_link_hash_entry *hentry;
+ asection *esec;
+ struct internal_reloc *irel;
+ struct internal_ldrel ldrel;
+ asection *tsec;
+ unsigned int reloc_size, byte_size;
+
+ if (bfd_xcoff_is_xcoff64 (output_bfd))
+ {
+ reloc_size = 63;
+ byte_size = 8;
+ }
+ else if (bfd_xcoff_is_xcoff32 (output_bfd))
+ {
+ reloc_size = 31;
+ byte_size = 4;
+ }
+ else
+ return FALSE;
+
+ sec = h->root.u.def.section;
+ osec = sec->output_section;
+ oindx = osec->target_index;
+ p = sec->contents + h->root.u.def.value;
+
+ hentry = h->descriptor;
+ BFD_ASSERT (hentry != NULL
+ && (hentry->root.type == bfd_link_hash_defined
+ || hentry->root.type == bfd_link_hash_defweak));
+ esec = hentry->root.u.def.section;
+
+ irel = finfo->section_info[oindx].relocs + osec->reloc_count;
+ irel->r_vaddr = (osec->vma
+ + sec->output_offset
+ + h->root.u.def.value);
+ irel->r_symndx = esec->output_section->target_index;
+ irel->r_type = R_POS;
+ irel->r_size = reloc_size;
+ finfo->section_info[oindx].rel_hashes[osec->reloc_count] = NULL;
+ ++osec->reloc_count;
+
+ ldrel.l_vaddr = irel->r_vaddr;
+ if (strcmp (esec->output_section->name, ".text") == 0)
+ ldrel.l_symndx = 0;
+ else if (strcmp (esec->output_section->name, ".data") == 0)
+ ldrel.l_symndx = 1;
+ else if (strcmp (esec->output_section->name, ".bss") == 0)
+ ldrel.l_symndx = 2;
+ else
+ {
+ (*_bfd_error_handler)
+ (_("%s: loader reloc in unrecognized section `%s'"),
+ bfd_get_filename (output_bfd),
+ esec->output_section->name);
+ bfd_set_error (bfd_error_nonrepresentable_section);
+ return FALSE;
+ }
+ ldrel.l_rtype = (reloc_size << 8) | R_POS;
+ ldrel.l_rsecnm = oindx;
+ bfd_xcoff_swap_ldrel_out (output_bfd, &ldrel, finfo->ldrel);
+ finfo->ldrel += bfd_xcoff_ldrelsz(output_bfd);
+
+ /* There are three items to write out,
+ the address of the code
+ the address of the toc anchor
+ the environment pointer.
+ We are ignoring the environment pointer. So set it to zero. */
+ if (bfd_xcoff_is_xcoff64 (output_bfd))
+ {
+ bfd_put_64 (output_bfd,
+ (esec->output_section->vma + esec->output_offset
+ + hentry->root.u.def.value),
+ p);
+ bfd_put_64 (output_bfd, xcoff_data (output_bfd)->toc, p + 8);
+ bfd_put_64 (output_bfd, (bfd_vma) 0, p + 16);
+ }
+ else
+ {
+ /* 32 bit backend
+ This logic was already called above so the error case where
+ the backend is neither has already been checked. */
+ bfd_put_32 (output_bfd,
+ (esec->output_section->vma + esec->output_offset
+ + hentry->root.u.def.value),
+ p);
+ bfd_put_32 (output_bfd, xcoff_data (output_bfd)->toc, p + 4);
+ bfd_put_32 (output_bfd, (bfd_vma) 0, p + 8);
+ }
- if (indx != -1)
- irel->r_symndx = indx;
- else
- {
+ tsec = coff_section_from_bfd_index (output_bfd,
+ xcoff_data (output_bfd)->sntoc);
- struct internal_syment *is;
+ ++irel;
+ irel->r_vaddr = (osec->vma
+ + sec->output_offset
+ + h->root.u.def.value
+ + byte_size);
+ irel->r_symndx = tsec->output_section->target_index;
+ irel->r_type = R_POS;
+ irel->r_size = reloc_size;
+ finfo->section_info[oindx].rel_hashes[osec->reloc_count] = NULL;
+ ++osec->reloc_count;
- const char *name;
- char buf[SYMNMLEN + 1];
+ ldrel.l_vaddr = irel->r_vaddr;
+ if (strcmp (tsec->output_section->name, ".text") == 0)
+ ldrel.l_symndx = 0;
+ else if (strcmp (tsec->output_section->name, ".data") == 0)
+ ldrel.l_symndx = 1;
+ else if (strcmp (tsec->output_section->name, ".bss") == 0)
+ ldrel.l_symndx = 2;
+ else
+ {
+ (*_bfd_error_handler)
+ (_("%s: loader reloc in unrecognized section `%s'"),
+ bfd_get_filename (output_bfd),
+ tsec->output_section->name);
+ bfd_set_error (bfd_error_nonrepresentable_section);
+ return FALSE;
+ }
+ ldrel.l_rtype = (reloc_size << 8) | R_POS;
+ ldrel.l_rsecnm = oindx;
+ bfd_xcoff_swap_ldrel_out (output_bfd, &ldrel, finfo->ldrel);
+ finfo->ldrel += bfd_xcoff_ldrelsz(output_bfd);
+ }
- /* This reloc is against a symbol we are
- stripping. It would be possible to handle
- this case, but I don't think it's worth it. */
- is = finfo->internal_syms + r_symndx;
+ if (h->indx >= 0 || finfo->info->strip == strip_all)
+ {
+ BFD_ASSERT (outsym == finfo->outsyms);
+ return TRUE;
+ }
- name = (_bfd_coff_internal_syment_name
- (input_bfd, is, buf));
+ if (h->indx != -2
+ && (finfo->info->strip == strip_all
+ || (finfo->info->strip == strip_some
+ && bfd_hash_lookup (finfo->info->keep_hash, h->root.root.string,
+ FALSE, FALSE) == NULL)))
+ {
+ BFD_ASSERT (outsym == finfo->outsyms);
+ return TRUE;
+ }
- if (name == NULL)
- return FALSE;
+ if (h->indx != -2
+ && (h->flags & (XCOFF_REF_REGULAR | XCOFF_DEF_REGULAR)) == 0)
+ {
+ BFD_ASSERT (outsym == finfo->outsyms);
+ return TRUE;
+ }
- if (! ((*finfo->info->callbacks->unattached_reloc)
- (finfo->info, name, input_bfd, o,
- irel->r_vaddr)))
- return FALSE;
- }
- }
- }
+ memset (&aux, 0, sizeof aux);
- quiet = FALSE;
- switch (irel->r_type)
- {
- default:
- if (h == NULL
- || h->root.type == bfd_link_hash_defined
- || h->root.type == bfd_link_hash_defweak
- || h->root.type == bfd_link_hash_common)
- break;
- /* Fall through. */
- case R_POS:
- case R_NEG:
- case R_RL:
- case R_RLA:
- /* This reloc needs to be copied into the .loader
- section. */
- ldrel.l_vaddr = irel->r_vaddr;
- if (r_symndx == -1)
- ldrel.l_symndx = -(bfd_size_type ) 1;
- else if (h == NULL
- || (h->root.type == bfd_link_hash_defined
- || h->root.type == bfd_link_hash_defweak
- || h->root.type == bfd_link_hash_common))
- {
- asection *sec;
+ h->indx = obj_raw_syment_count (output_bfd);
- if (h == NULL)
- sec = xcoff_data (input_bfd)->csects[r_symndx];
- else if (h->root.type == bfd_link_hash_common)
- sec = h->root.u.c.p->section;
- else
- sec = h->root.u.def.section;
- sec = sec->output_section;
+ result = bfd_xcoff_put_symbol_name (output_bfd, finfo->strtab, &isym,
+ h->root.root.string);
+ if (!result)
+ return FALSE;
- if (strcmp (sec->name, ".text") == 0)
- ldrel.l_symndx = 0;
- else if (strcmp (sec->name, ".data") == 0)
- ldrel.l_symndx = 1;
- else if (strcmp (sec->name, ".bss") == 0)
- ldrel.l_symndx = 2;
- else
- {
- (*_bfd_error_handler)
- (_("%B: loader reloc in unrecognized section `%A'"),
- input_bfd, sec);
- bfd_set_error (bfd_error_nonrepresentable_section);
- return FALSE;
- }
- }
- else
- {
- if (! finfo->info->relocatable
- && (h->flags & XCOFF_DEF_DYNAMIC) == 0
- && (h->flags & XCOFF_IMPORT) == 0)
- {
- /* We already called the undefined_symbol
- callback for this relocation, in
- _bfd_ppc_xcoff_relocate_section. Don't
- issue any more warnings. */
- quiet = TRUE;
- }
- if (h->ldindx < 0 && ! quiet)
- {
- (*_bfd_error_handler)
- (_("%B: `%s' in loader reloc but not loader sym"),
- input_bfd,
- h->root.root.string);
- bfd_set_error (bfd_error_bad_value);
- return FALSE;
- }
- ldrel.l_symndx = h->ldindx;
- }
- ldrel.l_rtype = (irel->r_size << 8) | irel->r_type;
- ldrel.l_rsecnm = o->output_section->target_index;
- if (xcoff_hash_table (finfo->info)->textro
- && strcmp (o->output_section->name, ".text") == 0
- && ! quiet)
- {
- (*_bfd_error_handler)
- (_("%B: loader reloc in read-only section %A"),
- input_bfd, o->output_section);
- bfd_set_error (bfd_error_invalid_operation);
- return FALSE;
- }
- bfd_xcoff_swap_ldrel_out (output_bfd, &ldrel,
- finfo->ldrel);
+ if (h->root.type == bfd_link_hash_undefined
+ || h->root.type == bfd_link_hash_undefweak)
+ {
+ isym.n_value = 0;
+ isym.n_scnum = N_UNDEF;
+ isym.n_sclass = C_EXT;
+ aux.x_csect.x_smtyp = XTY_ER;
+ }
+ else if ((h->root.type == bfd_link_hash_defined
+ || h->root.type == bfd_link_hash_defweak)
+ && h->smclas == XMC_XO)
+ {
+ BFD_ASSERT (bfd_is_abs_section (h->root.u.def.section));
+ isym.n_value = h->root.u.def.value;
+ isym.n_scnum = N_UNDEF;
+ isym.n_sclass = C_EXT;
+ aux.x_csect.x_smtyp = XTY_ER;
+ }
+ else if (h->root.type == bfd_link_hash_defined
+ || h->root.type == bfd_link_hash_defweak)
+ {
+ struct xcoff_link_size_list *l;
- finfo->ldrel += bfd_xcoff_ldrelsz(output_bfd);
- break;
+ isym.n_value = (h->root.u.def.section->output_section->vma
+ + h->root.u.def.section->output_offset
+ + h->root.u.def.value);
+ if (bfd_is_abs_section (h->root.u.def.section->output_section))
+ isym.n_scnum = N_ABS;
+ else
+ isym.n_scnum = h->root.u.def.section->output_section->target_index;
+ isym.n_sclass = C_HIDEXT;
+ aux.x_csect.x_smtyp = XTY_SD;
- case R_TOC:
- case R_GL:
- case R_TCL:
- case R_TRL:
- case R_TRLA:
- /* We should never need a .loader reloc for a TOC
- relative reloc. */
+ if ((h->flags & XCOFF_HAS_SIZE) != 0)
+ {
+ for (l = xcoff_hash_table (finfo->info)->size_list;
+ l != NULL;
+ l = l->next)
+ {
+ if (l->h == h)
+ {
+ aux.x_csect.x_scnlen.l = l->size;
break;
}
}
-
- o->output_section->reloc_count += o->reloc_count;
}
-
- /* Write out the modified section contents. */
- if (! bfd_set_section_contents (output_bfd, o->output_section,
- contents, (file_ptr) o->output_offset,
- o->size))
- return FALSE;
}
+ else if (h->root.type == bfd_link_hash_common)
+ {
+ isym.n_value = (h->root.u.c.p->section->output_section->vma
+ + h->root.u.c.p->section->output_offset);
+ isym.n_scnum = h->root.u.c.p->section->output_section->target_index;
+ isym.n_sclass = C_EXT;
+ aux.x_csect.x_smtyp = XTY_CM;
+ aux.x_csect.x_scnlen.l = h->root.u.c.size;
+ }
+ else
+ abort ();
+
+ isym.n_type = T_NULL;
+ isym.n_numaux = 1;
+
+ bfd_coff_swap_sym_out (output_bfd, (void *) &isym, (void *) outsym);
+ outsym += bfd_coff_symesz (output_bfd);
+
+ aux.x_csect.x_smclas = h->smclas;
+ bfd_coff_swap_aux_out (output_bfd, (void *) &aux, T_NULL, isym.n_sclass, 0, 1,
+ (void *) outsym);
+ outsym += bfd_coff_auxesz (output_bfd);
+
+ if ((h->root.type == bfd_link_hash_defined
+ || h->root.type == bfd_link_hash_defweak)
+ && h->smclas != XMC_XO)
+ {
+ /* We just output an SD symbol. Now output an LD symbol. */
+ h->indx += 2;
- obj_coff_keep_syms (input_bfd) = keep_syms;
+ isym.n_sclass = C_EXT;
+ bfd_coff_swap_sym_out (output_bfd, (void *) &isym, (void *) outsym);
+ outsym += bfd_coff_symesz (output_bfd);
- if (! finfo->info->keep_memory)
- {
- if (! _bfd_coff_free_symbols (input_bfd))
- return FALSE;
+ aux.x_csect.x_smtyp = XTY_LD;
+ aux.x_csect.x_scnlen.l = obj_raw_syment_count (output_bfd);
+ bfd_coff_swap_aux_out (output_bfd, (void *) &aux, T_NULL, C_EXT, 0, 1,
+ (void *) outsym);
+ outsym += bfd_coff_auxesz (output_bfd);
}
+ pos = obj_sym_filepos (output_bfd);
+ pos += obj_raw_syment_count (output_bfd) * bfd_coff_symesz (output_bfd);
+ amt = outsym - finfo->outsyms;
+ if (bfd_seek (output_bfd, pos, SEEK_SET) != 0
+ || bfd_bwrite (finfo->outsyms, amt, output_bfd) != amt)
+ return FALSE;
+ obj_raw_syment_count (output_bfd) +=
+ (outsym - finfo->outsyms) / bfd_coff_symesz (output_bfd);
+
return TRUE;
}
-#undef N_TMASK
-#undef N_BTSHFT
-
-/* Write out a non-XCOFF global symbol. */
-
+/* Handle a link order which is supposed to generate a reloc. */
static bfd_boolean
-xcoff_write_global_symbol (h, inf)
- struct xcoff_link_hash_entry *h;
- PTR inf;
+xcoff_reloc_link_order (bfd *output_bfd,
+ struct xcoff_final_link_info *finfo,
+ asection *output_section,
+ struct bfd_link_order *link_order)
{
- struct xcoff_final_link_info *finfo = (struct xcoff_final_link_info *) inf;
- bfd *output_bfd;
- bfd_byte *outsym;
- struct internal_syment isym;
- union internal_auxent aux;
- bfd_boolean result;
- file_ptr pos;
- bfd_size_type amt;
+ reloc_howto_type *howto;
+ struct xcoff_link_hash_entry *h;
+ asection *hsec;
+ bfd_vma hval;
+ bfd_vma addend;
+ struct internal_reloc *irel;
+ struct xcoff_link_hash_entry **rel_hash_ptr;
+ struct internal_ldrel ldrel;
- output_bfd = finfo->output_bfd;
- outsym = finfo->outsyms;
+ if (link_order->type == bfd_section_reloc_link_order)
+ /* We need to somehow locate a symbol in the right section. The
+ symbol must either have a value of zero, or we must adjust
+ the addend by the value of the symbol. FIXME: Write this
+ when we need it. The old linker couldn't handle this anyhow. */
+ abort ();
- if (h->root.type == bfd_link_hash_warning)
+ howto = bfd_reloc_type_lookup (output_bfd, link_order->u.reloc.p->reloc);
+ if (howto == NULL)
{
- h = (struct xcoff_link_hash_entry *) h->root.u.i.link;
- if (h->root.type == bfd_link_hash_new)
- return TRUE;
+ bfd_set_error (bfd_error_bad_value);
+ return FALSE;
}
- /* If this symbol was garbage collected, just skip it. */
- if (xcoff_hash_table (finfo->info)->gc
- && (h->flags & XCOFF_MARK) == 0)
- return TRUE;
+ h = ((struct xcoff_link_hash_entry *)
+ bfd_wrapped_link_hash_lookup (output_bfd, finfo->info,
+ link_order->u.reloc.p->u.name,
+ FALSE, FALSE, TRUE));
+ if (h == NULL)
+ {
+ if (! ((*finfo->info->callbacks->unattached_reloc)
+ (finfo->info, link_order->u.reloc.p->u.name, NULL, NULL, (bfd_vma) 0)))
+ return FALSE;
+ return TRUE;
+ }
- /* If we need a .loader section entry, write it out. */
- if (h->ldsym != NULL)
+ if (h->root.type == bfd_link_hash_common)
{
- struct internal_ldsym *ldsym;
- bfd *impbfd;
+ hsec = h->root.u.c.p->section;
+ hval = 0;
+ }
+ else if (h->root.type == bfd_link_hash_defined
+ || h->root.type == bfd_link_hash_defweak)
+ {
+ hsec = h->root.u.def.section;
+ hval = h->root.u.def.value;
+ }
+ else
+ {
+ hsec = NULL;
+ hval = 0;
+ }
- ldsym = h->ldsym;
+ addend = link_order->u.reloc.p->addend;
+ if (hsec != NULL)
+ addend += (hsec->output_section->vma
+ + hsec->output_offset
+ + hval);
- if (h->root.type == bfd_link_hash_undefined
- || h->root.type == bfd_link_hash_undefweak)
- {
+ if (addend != 0)
+ {
+ bfd_size_type size;
+ bfd_byte *buf;
+ bfd_reloc_status_type rstat;
+ bfd_boolean ok;
- ldsym->l_value = 0;
- ldsym->l_scnum = N_UNDEF;
- ldsym->l_smtype = XTY_ER;
- impbfd = h->root.u.undef.abfd;
+ size = bfd_get_reloc_size (howto);
+ buf = bfd_zmalloc (size);
+ if (buf == NULL)
+ return FALSE;
- }
- else if (h->root.type == bfd_link_hash_defined
- || h->root.type == bfd_link_hash_defweak)
+ rstat = _bfd_relocate_contents (howto, output_bfd, addend, buf);
+ switch (rstat)
{
+ case bfd_reloc_ok:
+ break;
+ default:
+ case bfd_reloc_outofrange:
+ abort ();
+ case bfd_reloc_overflow:
+ if (! ((*finfo->info->callbacks->reloc_overflow)
+ (finfo->info, NULL, link_order->u.reloc.p->u.name,
+ howto->name, addend, NULL, NULL, (bfd_vma) 0)))
+ {
+ free (buf);
+ return FALSE;
+ }
+ break;
+ }
+ ok = bfd_set_section_contents (output_bfd, output_section, (void *) buf,
+ (file_ptr) link_order->offset, size);
+ free (buf);
+ if (! ok)
+ return FALSE;
+ }
- asection *sec;
+ /* Store the reloc information in the right place. It will get
+ swapped and written out at the end of the final_link routine. */
+ irel = (finfo->section_info[output_section->target_index].relocs
+ + output_section->reloc_count);
+ rel_hash_ptr = (finfo->section_info[output_section->target_index].rel_hashes
+ + output_section->reloc_count);
- sec = h->root.u.def.section;
- ldsym->l_value = (sec->output_section->vma
- + sec->output_offset
- + h->root.u.def.value);
- ldsym->l_scnum = sec->output_section->target_index;
- ldsym->l_smtype = XTY_SD;
- impbfd = sec->owner;
+ memset (irel, 0, sizeof (struct internal_reloc));
+ *rel_hash_ptr = NULL;
- }
- else
- abort ();
+ irel->r_vaddr = output_section->vma + link_order->offset;
- if (((h->flags & XCOFF_DEF_REGULAR) == 0
- && (h->flags & XCOFF_DEF_DYNAMIC) != 0)
- || (h->flags & XCOFF_IMPORT) != 0)
- {
- /* Clear l_smtype
- Import symbols are defined so the check above will make
- the l_smtype XTY_SD. But this is not correct, it should
- be cleared. */
- ldsym->l_smtype |= L_IMPORT;
- }
+ if (h->indx >= 0)
+ irel->r_symndx = h->indx;
+ else
+ {
+ /* Set the index to -2 to force this symbol to get written out. */
+ h->indx = -2;
+ *rel_hash_ptr = h;
+ irel->r_symndx = 0;
+ }
- if (((h->flags & XCOFF_DEF_REGULAR) != 0
- && (h->flags & XCOFF_DEF_DYNAMIC) != 0)
- || (h->flags & XCOFF_EXPORT) != 0)
- {
- ldsym->l_smtype |= L_EXPORT;
- }
+ irel->r_type = howto->type;
+ irel->r_size = howto->bitsize - 1;
+ if (howto->complain_on_overflow == complain_overflow_signed)
+ irel->r_size |= 0x80;
- if ((h->flags & XCOFF_ENTRY) != 0)
- {
- ldsym->l_smtype |= L_ENTRY;
- }
+ ++output_section->reloc_count;
- if ((h->flags & XCOFF_RTINIT) != 0)
- {
- ldsym->l_smtype = XTY_SD;
- }
+ /* Now output the reloc to the .loader section. */
- ldsym->l_smclas = h->smclas;
+ ldrel.l_vaddr = irel->r_vaddr;
- if (ldsym->l_smtype & L_IMPORT)
- {
- if ((h->root.type == bfd_link_hash_defined
- || h->root.type == bfd_link_hash_defweak)
- && (h->root.u.def.value != 0))
- {
- ldsym->l_smclas = XMC_XO;
- }
- else if ((h->flags & (XCOFF_SYSCALL32 | XCOFF_SYSCALL64)) ==
- (XCOFF_SYSCALL32 | XCOFF_SYSCALL64))
- {
- ldsym->l_smclas = XMC_SV3264;
- }
- else if (h->flags & XCOFF_SYSCALL32)
- {
- ldsym->l_smclas = XMC_SV;
- }
- else if (h->flags & XCOFF_SYSCALL64)
- {
- ldsym->l_smclas = XMC_SV64;
- }
- }
+ if (hsec != NULL)
+ {
+ const char *secname;
- if (ldsym->l_ifile == -(bfd_size_type) 1)
+ secname = hsec->output_section->name;
+
+ if (strcmp (secname, ".text") == 0)
+ ldrel.l_symndx = 0;
+ else if (strcmp (secname, ".data") == 0)
+ ldrel.l_symndx = 1;
+ else if (strcmp (secname, ".bss") == 0)
+ ldrel.l_symndx = 2;
+ else
{
- ldsym->l_ifile = 0;
+ (*_bfd_error_handler)
+ (_("%s: loader reloc in unrecognized section `%s'"),
+ bfd_get_filename (output_bfd), secname);
+ bfd_set_error (bfd_error_nonrepresentable_section);
+ return FALSE;
}
- else if (ldsym->l_ifile == 0)
+ }
+ else
+ {
+ if (h->ldindx < 0)
{
- if ((ldsym->l_smtype & L_IMPORT) == 0)
- {
- ldsym->l_ifile = 0;
- }
- else if (impbfd == NULL)
- {
- ldsym->l_ifile = 0;
- }
- else
- {
- BFD_ASSERT (impbfd->xvec == output_bfd->xvec);
- ldsym->l_ifile = xcoff_data (impbfd)->import_file_id;
- }
- }
-
- ldsym->l_parm = 0;
-
- BFD_ASSERT (h->ldindx >= 0);
-
- bfd_xcoff_swap_ldsym_out (output_bfd, ldsym,
- (finfo->ldsym +
- (h->ldindx - 3)
- * bfd_xcoff_ldsymsz(finfo->output_bfd)));
- h->ldsym = NULL;
+ (*_bfd_error_handler)
+ (_("%s: `%s' in loader reloc but not loader sym"),
+ bfd_get_filename (output_bfd),
+ h->root.root.string);
+ bfd_set_error (bfd_error_bad_value);
+ return FALSE;
+ }
+ ldrel.l_symndx = h->ldindx;
}
- /* If this symbol needs global linkage code, write it out. */
- if (h->root.type == bfd_link_hash_defined
- && (h->root.u.def.section
- == xcoff_hash_table (finfo->info)->linkage_section))
- {
- bfd_byte *p;
- bfd_vma tocoff;
- unsigned int i;
+ ldrel.l_rtype = (irel->r_size << 8) | irel->r_type;
+ ldrel.l_rsecnm = output_section->target_index;
+ bfd_xcoff_swap_ldrel_out (output_bfd, &ldrel, finfo->ldrel);
+ finfo->ldrel += bfd_xcoff_ldrelsz(output_bfd);
- p = h->root.u.def.section->contents + h->root.u.def.value;
+ return TRUE;
+}
- /* The first instruction in the global linkage code loads a
- specific TOC element. */
- tocoff = (h->descriptor->toc_section->output_section->vma
- + h->descriptor->toc_section->output_offset
- - xcoff_data (output_bfd)->toc);
+/* Do the final link step. */
- if ((h->descriptor->flags & XCOFF_SET_TOC) != 0)
- {
- tocoff += h->descriptor->u.toc_offset;
- }
+bfd_boolean
+_bfd_xcoff_bfd_final_link (bfd *abfd, struct bfd_link_info *info)
+{
+ bfd_size_type symesz;
+ struct xcoff_final_link_info finfo;
+ asection *o;
+ struct bfd_link_order *p;
+ bfd_size_type max_contents_size;
+ bfd_size_type max_sym_count;
+ bfd_size_type max_lineno_count;
+ bfd_size_type max_reloc_count;
+ bfd_size_type max_output_reloc_count;
+ file_ptr rel_filepos;
+ unsigned int relsz;
+ file_ptr line_filepos;
+ unsigned int linesz;
+ bfd *sub;
+ bfd_byte *external_relocs = NULL;
+ char strbuf[STRING_SIZE_SIZE];
+ file_ptr pos;
+ bfd_size_type amt;
+ if (info->shared)
+ abfd->flags |= DYNAMIC;
- /* The first instruction in the glink code needs to be
- cooked to to hold the correct offset in the toc. The
- rest are just output raw. */
- bfd_put_32 (output_bfd,
- bfd_xcoff_glink_code(output_bfd, 0) | (tocoff & 0xffff), p);
+ symesz = bfd_coff_symesz (abfd);
- /* Start with i == 1 to get past the first instruction done above
- The /4 is because the glink code is in bytes and we are going
- 4 at a pop. */
- for (i = 1; i < bfd_xcoff_glink_code_size(output_bfd) / 4; i++)
- {
- bfd_put_32 (output_bfd,
- (bfd_vma) bfd_xcoff_glink_code(output_bfd, i),
- &p[4 * i]);
- }
- }
+ finfo.info = info;
+ finfo.output_bfd = abfd;
+ finfo.strtab = NULL;
+ finfo.section_info = NULL;
+ finfo.last_file_index = -1;
+ finfo.toc_symindx = -1;
+ finfo.internal_syms = NULL;
+ finfo.sym_indices = NULL;
+ finfo.outsyms = NULL;
+ finfo.linenos = NULL;
+ finfo.contents = NULL;
+ finfo.external_relocs = NULL;
- /* If we created a TOC entry for this symbol, write out the required
- relocs. */
- if ((h->flags & XCOFF_SET_TOC) != 0)
- {
- asection *tocsec;
- asection *osec;
- int oindx;
- struct internal_reloc *irel;
- struct internal_ldrel ldrel;
- struct internal_syment irsym;
- union internal_auxent iraux;
+ finfo.ldsym = (xcoff_hash_table (info)->loader_section->contents
+ + bfd_xcoff_ldhdrsz (abfd));
+ finfo.ldrel = (xcoff_hash_table (info)->loader_section->contents
+ + bfd_xcoff_ldhdrsz(abfd)
+ + (xcoff_hash_table (info)->ldhdr.l_nsyms
+ * bfd_xcoff_ldsymsz(abfd)));
- tocsec = h->toc_section;
- osec = tocsec->output_section;
- oindx = osec->target_index;
- irel = finfo->section_info[oindx].relocs + osec->reloc_count;
- irel->r_vaddr = (osec->vma
- + tocsec->output_offset
- + h->u.toc_offset);
+ xcoff_data (abfd)->coff.link_info = info;
+ finfo.strtab = _bfd_stringtab_init ();
+ if (finfo.strtab == NULL)
+ goto error_return;
- if (h->indx >= 0)
- {
- irel->r_symndx = h->indx;
- }
- else
+ /* Count the line number and relocation entries required for the
+ output file. Determine a few maximum sizes. */
+ max_contents_size = 0;
+ max_lineno_count = 0;
+ max_reloc_count = 0;
+ for (o = abfd->sections; o != NULL; o = o->next)
+ {
+ o->reloc_count = 0;
+ o->lineno_count = 0;
+ for (p = o->link_order_head; p != NULL; p = p->next)
{
- h->indx = -2;
- irel->r_symndx = obj_raw_syment_count (output_bfd);
- }
+ if (p->type == bfd_indirect_link_order)
+ {
+ asection *sec;
- BFD_ASSERT (h->ldindx >= 0);
+ sec = p->u.indirect.section;
- /* Initialize the aux union here instead of closer to when it is
- written out below because the length of the csect depends on
- whether the output is 32 or 64 bit. */
- memset (&iraux, 0, sizeof iraux);
- iraux.x_csect.x_smtyp = XTY_SD;
- /* iraux.x_csect.x_scnlen.l = 4 or 8, see below */
- iraux.x_csect.x_smclas = XMC_TC;
+ /* Mark all sections which are to be included in the
+ link. This will normally be every section. We need
+ to do this so that we can identify any sections which
+ the linker has decided to not include. */
+ sec->linker_mark = TRUE;
- /* 32 bit uses a 32 bit R_POS to do the relocations
- 64 bit uses a 64 bit R_POS to do the relocations
+ if (info->strip == strip_none
+ || info->strip == strip_some)
+ o->lineno_count += sec->lineno_count;
- Also needs to change the csect size : 4 for 32 bit, 8 for 64 bit
+ o->reloc_count += sec->reloc_count;
- Which one is determined by the backend. */
- if (bfd_xcoff_is_xcoff64 (output_bfd))
- {
- irel->r_size = 63;
- iraux.x_csect.x_scnlen.l = 8;
- }
- else if (bfd_xcoff_is_xcoff32 (output_bfd))
- {
- irel->r_size = 31;
- iraux.x_csect.x_scnlen.l = 4;
- }
- else
- {
- return FALSE;
+ if (sec->rawsize > max_contents_size)
+ max_contents_size = sec->rawsize;
+ if (sec->size > max_contents_size)
+ max_contents_size = sec->size;
+ if (sec->lineno_count > max_lineno_count)
+ max_lineno_count = sec->lineno_count;
+ if (coff_section_data (sec->owner, sec) != NULL
+ && xcoff_section_data (sec->owner, sec) != NULL
+ && (xcoff_section_data (sec->owner, sec)->lineno_count
+ > max_lineno_count))
+ max_lineno_count =
+ xcoff_section_data (sec->owner, sec)->lineno_count;
+ if (sec->reloc_count > max_reloc_count)
+ max_reloc_count = sec->reloc_count;
+ }
+ else if (p->type == bfd_section_reloc_link_order
+ || p->type == bfd_symbol_reloc_link_order)
+ ++o->reloc_count;
}
- irel->r_type = R_POS;
- finfo->section_info[oindx].rel_hashes[osec->reloc_count] = NULL;
- ++osec->reloc_count;
+ }
- ldrel.l_vaddr = irel->r_vaddr;
- ldrel.l_symndx = h->ldindx;
- ldrel.l_rtype = (irel->r_size << 8) | R_POS;
- ldrel.l_rsecnm = oindx;
- bfd_xcoff_swap_ldrel_out (output_bfd, &ldrel, finfo->ldrel);
- finfo->ldrel += bfd_xcoff_ldrelsz(output_bfd);
+ /* Compute the file positions for all the sections. */
+ if (abfd->output_has_begun)
+ {
+ if (xcoff_hash_table (info)->file_align != 0)
+ abort ();
+ }
+ else
+ {
+ bfd_vma file_align;
- /* We need to emit a symbol to define a csect which holds
- the reloc. */
- if (finfo->info->strip != strip_all)
+ file_align = xcoff_hash_table (info)->file_align;
+ if (file_align != 0)
{
+ bfd_boolean saw_contents;
+ int indx;
+ asection **op;
+ file_ptr sofar;
- result = bfd_xcoff_put_symbol_name (output_bfd, finfo->strtab,
- &irsym, h->root.root.string);
- if (!result)
- return FALSE;
+ /* Insert .pad sections before every section which has
+ contents and is loaded, if it is preceded by some other
+ section which has contents and is loaded. */
+ saw_contents = TRUE;
+ for (op = &abfd->sections; *op != NULL; op = &(*op)->next)
+ {
+ if (strcmp ((*op)->name, ".pad") == 0)
+ saw_contents = FALSE;
+ else if (((*op)->flags & SEC_HAS_CONTENTS) != 0
+ && ((*op)->flags & SEC_LOAD) != 0)
+ {
+ if (! saw_contents)
+ saw_contents = TRUE;
+ else
+ {
+ asection *n, **st;
- irsym.n_value = irel->r_vaddr;
- irsym.n_scnum = osec->target_index;
- irsym.n_sclass = C_HIDEXT;
- irsym.n_type = T_NULL;
- irsym.n_numaux = 1;
+ /* Create a pad section and place it before the section
+ that needs padding. This requires unlinking and
+ relinking the bfd's section list. */
- bfd_coff_swap_sym_out (output_bfd, (PTR) &irsym, (PTR) outsym);
- outsym += bfd_coff_symesz (output_bfd);
+ st = abfd->section_tail;
+ n = bfd_make_section_anyway (abfd, ".pad");
+ n->flags = SEC_HAS_CONTENTS;
+ n->alignment_power = 0;
- /* note : iraux is initialized above */
- bfd_coff_swap_aux_out (output_bfd, (PTR) &iraux, T_NULL, C_HIDEXT,
- 0, 1, (PTR) outsym);
- outsym += bfd_coff_auxesz (output_bfd);
+ BFD_ASSERT (*st == n);
+ bfd_section_list_remove (abfd, st);
+ bfd_section_list_insert (abfd, op, n);
+
+ op = &n->next;
+ saw_contents = FALSE;
+ }
+ }
+ }
+
+ /* Reset the section indices after inserting the new
+ sections. */
+ indx = 0;
+ for (o = abfd->sections; o != NULL; o = o->next)
+ {
+ ++indx;
+ o->target_index = indx;
+ }
+ BFD_ASSERT ((unsigned int) indx == abfd->section_count);
+
+ /* Work out appropriate sizes for the .pad sections to force
+ each section to land on a page boundary. This bit of
+ code knows what compute_section_file_positions is going
+ to do. */
+ sofar = bfd_coff_filhsz (abfd);
+ sofar += bfd_coff_aoutsz (abfd);
+ sofar += abfd->section_count * bfd_coff_scnhsz (abfd);
+ for (o = abfd->sections; o != NULL; o = o->next)
+ if ((bfd_xcoff_is_reloc_count_overflow
+ (abfd, (bfd_vma) o->reloc_count))
+ || (bfd_xcoff_is_lineno_count_overflow
+ (abfd, (bfd_vma) o->lineno_count)))
+ /* 64 does not overflow, need to check if 32 does */
+ sofar += bfd_coff_scnhsz (abfd);
- if (h->indx >= 0)
+ for (o = abfd->sections; o != NULL; o = o->next)
{
- /* We aren't going to write out the symbols below, so we
- need to write them out now. */
- pos = obj_sym_filepos (output_bfd);
- pos += (obj_raw_syment_count (output_bfd)
- * bfd_coff_symesz (output_bfd));
- amt = outsym - finfo->outsyms;
- if (bfd_seek (output_bfd, pos, SEEK_SET) != 0
- || bfd_bwrite (finfo->outsyms, amt, output_bfd) != amt)
- return FALSE;
- obj_raw_syment_count (output_bfd) +=
- (outsym - finfo->outsyms) / bfd_coff_symesz (output_bfd);
+ if (strcmp (o->name, ".pad") == 0)
+ {
+ bfd_vma pageoff;
- outsym = finfo->outsyms;
+ BFD_ASSERT (o->size == 0);
+ pageoff = sofar & (file_align - 1);
+ if (pageoff != 0)
+ {
+ o->size = file_align - pageoff;
+ sofar += file_align - pageoff;
+ o->flags |= SEC_HAS_CONTENTS;
+ }
+ }
+ else
+ {
+ if ((o->flags & SEC_HAS_CONTENTS) != 0)
+ sofar += BFD_ALIGN (o->size,
+ 1 << o->alignment_power);
+ }
}
}
+
+ if (! bfd_coff_compute_section_file_positions (abfd))
+ goto error_return;
}
- /* If this symbol is a specially defined function descriptor, write
- it out. The first word is the address of the function code
- itself, the second word is the address of the TOC, and the third
- word is zero.
+ /* Allocate space for the pointers we need to keep for the relocs. */
+ {
+ unsigned int i;
- 32 bit vs 64 bit
- The addresses for the 32 bit will take 4 bytes and the addresses
- for 64 bit will take 8 bytes. Similar for the relocs. This type
- of logic was also done above to create a TOC entry in
- xcoff_write_global_symbol. */
- if ((h->flags & XCOFF_DESCRIPTOR) != 0
- && h->root.type == bfd_link_hash_defined
- && (h->root.u.def.section
- == xcoff_hash_table (finfo->info)->descriptor_section))
- {
- asection *sec;
- asection *osec;
- int oindx;
- bfd_byte *p;
- struct xcoff_link_hash_entry *hentry;
- asection *esec;
- struct internal_reloc *irel;
- struct internal_ldrel ldrel;
- asection *tsec;
- unsigned int reloc_size, byte_size;
+ /* We use section_count + 1, rather than section_count, because
+ the target_index fields are 1 based. */
+ amt = abfd->section_count + 1;
+ amt *= sizeof (struct xcoff_link_section_info);
+ finfo.section_info = bfd_malloc (amt);
+ if (finfo.section_info == NULL)
+ goto error_return;
+ for (i = 0; i <= abfd->section_count; i++)
+ {
+ finfo.section_info[i].relocs = NULL;
+ finfo.section_info[i].rel_hashes = NULL;
+ finfo.section_info[i].toc_rel_hashes = NULL;
+ }
+ }
- if (bfd_xcoff_is_xcoff64 (output_bfd))
- {
- reloc_size = 63;
- byte_size = 8;
- }
- else if (bfd_xcoff_is_xcoff32 (output_bfd))
- {
- reloc_size = 31;
- byte_size = 4;
- }
+ /* Set the file positions for the relocs. */
+ rel_filepos = obj_relocbase (abfd);
+ relsz = bfd_coff_relsz (abfd);
+ max_output_reloc_count = 0;
+ for (o = abfd->sections; o != NULL; o = o->next)
+ {
+ if (o->reloc_count == 0)
+ o->rel_filepos = 0;
else
{
- return FALSE;
- }
+ /* A stripped file has no relocs. However, we still
+ allocate the buffers, so that later code doesn't have to
+ worry about whether we are stripping or not. */
+ if (info->strip == strip_all)
+ o->rel_filepos = 0;
+ else
+ {
+ o->flags |= SEC_RELOC;
+ o->rel_filepos = rel_filepos;
+ rel_filepos += o->reloc_count * relsz;
+ }
- sec = h->root.u.def.section;
- osec = sec->output_section;
- oindx = osec->target_index;
- p = sec->contents + h->root.u.def.value;
+ /* We don't know the indices of global symbols until we have
+ written out all the local symbols. For each section in
+ the output file, we keep an array of pointers to hash
+ table entries. Each entry in the array corresponds to a
+ reloc. When we find a reloc against a global symbol, we
+ set the corresponding entry in this array so that we can
+ fix up the symbol index after we have written out all the
+ local symbols.
- hentry = h->descriptor;
- BFD_ASSERT (hentry != NULL
- && (hentry->root.type == bfd_link_hash_defined
- || hentry->root.type == bfd_link_hash_defweak));
- esec = hentry->root.u.def.section;
+ Because of this problem, we also keep the relocs in
+ memory until the end of the link. This wastes memory.
+ We could backpatch the file later, I suppose, although it
+ would be slow. */
+ amt = o->reloc_count;
+ amt *= sizeof (struct internal_reloc);
+ finfo.section_info[o->target_index].relocs = bfd_malloc (amt);
- irel = finfo->section_info[oindx].relocs + osec->reloc_count;
- irel->r_vaddr = (osec->vma
- + sec->output_offset
- + h->root.u.def.value);
- irel->r_symndx = esec->output_section->target_index;
- irel->r_type = R_POS;
- irel->r_size = reloc_size;
- finfo->section_info[oindx].rel_hashes[osec->reloc_count] = NULL;
- ++osec->reloc_count;
+ amt = o->reloc_count;
+ amt *= sizeof (struct xcoff_link_hash_entry *);
+ finfo.section_info[o->target_index].rel_hashes = bfd_malloc (amt);
- ldrel.l_vaddr = irel->r_vaddr;
- if (strcmp (esec->output_section->name, ".text") == 0)
- ldrel.l_symndx = 0;
- else if (strcmp (esec->output_section->name, ".data") == 0)
- ldrel.l_symndx = 1;
- else if (strcmp (esec->output_section->name, ".bss") == 0)
- ldrel.l_symndx = 2;
- else
- {
- (*_bfd_error_handler)
- (_("%s: loader reloc in unrecognized section `%s'"),
- bfd_get_filename (output_bfd),
- esec->output_section->name);
- bfd_set_error (bfd_error_nonrepresentable_section);
- return FALSE;
- }
- ldrel.l_rtype = (reloc_size << 8) | R_POS;
- ldrel.l_rsecnm = oindx;
- bfd_xcoff_swap_ldrel_out (output_bfd, &ldrel, finfo->ldrel);
- finfo->ldrel += bfd_xcoff_ldrelsz(output_bfd);
+ if (finfo.section_info[o->target_index].relocs == NULL
+ || finfo.section_info[o->target_index].rel_hashes == NULL)
+ goto error_return;
- /* There are three items to write out,
- the address of the code
- the address of the toc anchor
- the environment pointer.
- We are ignoring the environment pointer. So set it to zero. */
- if (bfd_xcoff_is_xcoff64 (output_bfd))
- {
- bfd_put_64 (output_bfd,
- (esec->output_section->vma + esec->output_offset
- + hentry->root.u.def.value),
- p);
- bfd_put_64 (output_bfd, xcoff_data (output_bfd)->toc, p + 8);
- bfd_put_64 (output_bfd, (bfd_vma) 0, p + 16);
- }
- else
- {
- /* 32 bit backend
- This logic was already called above so the error case where
- the backend is neither has already been checked. */
- bfd_put_32 (output_bfd,
- (esec->output_section->vma + esec->output_offset
- + hentry->root.u.def.value),
- p);
- bfd_put_32 (output_bfd, xcoff_data (output_bfd)->toc, p + 4);
- bfd_put_32 (output_bfd, (bfd_vma) 0, p + 8);
+ if (o->reloc_count > max_output_reloc_count)
+ max_output_reloc_count = o->reloc_count;
}
+ }
- tsec = coff_section_from_bfd_index (output_bfd,
- xcoff_data (output_bfd)->sntoc);
-
- ++irel;
- irel->r_vaddr = (osec->vma
- + sec->output_offset
- + h->root.u.def.value
- + byte_size);
- irel->r_symndx = tsec->output_section->target_index;
- irel->r_type = R_POS;
- irel->r_size = reloc_size;
- finfo->section_info[oindx].rel_hashes[osec->reloc_count] = NULL;
- ++osec->reloc_count;
-
- ldrel.l_vaddr = irel->r_vaddr;
- if (strcmp (tsec->output_section->name, ".text") == 0)
- ldrel.l_symndx = 0;
- else if (strcmp (tsec->output_section->name, ".data") == 0)
- ldrel.l_symndx = 1;
- else if (strcmp (tsec->output_section->name, ".bss") == 0)
- ldrel.l_symndx = 2;
+ /* We now know the size of the relocs, so we can determine the file
+ positions of the line numbers. */
+ line_filepos = rel_filepos;
+ finfo.line_filepos = line_filepos;
+ linesz = bfd_coff_linesz (abfd);
+ for (o = abfd->sections; o != NULL; o = o->next)
+ {
+ if (o->lineno_count == 0)
+ o->line_filepos = 0;
else
{
- (*_bfd_error_handler)
- (_("%s: loader reloc in unrecognized section `%s'"),
- bfd_get_filename (output_bfd),
- tsec->output_section->name);
- bfd_set_error (bfd_error_nonrepresentable_section);
- return FALSE;
+ o->line_filepos = line_filepos;
+ line_filepos += o->lineno_count * linesz;
}
- ldrel.l_rtype = (reloc_size << 8) | R_POS;
- ldrel.l_rsecnm = oindx;
- bfd_xcoff_swap_ldrel_out (output_bfd, &ldrel, finfo->ldrel);
- finfo->ldrel += bfd_xcoff_ldrelsz(output_bfd);
- }
- if (h->indx >= 0 || finfo->info->strip == strip_all)
- {
- BFD_ASSERT (outsym == finfo->outsyms);
- return TRUE;
+ /* Reset the reloc and lineno counts, so that we can use them to
+ count the number of entries we have output so far. */
+ o->reloc_count = 0;
+ o->lineno_count = 0;
}
- if (h->indx != -2
- && (finfo->info->strip == strip_all
- || (finfo->info->strip == strip_some
- && bfd_hash_lookup (finfo->info->keep_hash, h->root.root.string,
- FALSE, FALSE) == NULL)))
- {
- BFD_ASSERT (outsym == finfo->outsyms);
- return TRUE;
- }
+ obj_sym_filepos (abfd) = line_filepos;
- if (h->indx != -2
- && (h->flags & (XCOFF_REF_REGULAR | XCOFF_DEF_REGULAR)) == 0)
+ /* Figure out the largest number of symbols in an input BFD. Take
+ the opportunity to clear the output_has_begun fields of all the
+ input BFD's. We want at least 6 symbols, since that is the
+ number which xcoff_write_global_symbol may need. */
+ max_sym_count = 6;
+ for (sub = info->input_bfds; sub != NULL; sub = sub->link_next)
{
- BFD_ASSERT (outsym == finfo->outsyms);
- return TRUE;
+ bfd_size_type sz;
+
+ sub->output_has_begun = FALSE;
+ sz = obj_raw_syment_count (sub);
+ if (sz > max_sym_count)
+ max_sym_count = sz;
}
- memset (&aux, 0, sizeof aux);
+ /* Allocate some buffers used while linking. */
+ amt = max_sym_count * sizeof (struct internal_syment);
+ finfo.internal_syms = bfd_malloc (amt);
- h->indx = obj_raw_syment_count (output_bfd);
+ amt = max_sym_count * sizeof (long);
+ finfo.sym_indices = bfd_malloc (amt);
- result = bfd_xcoff_put_symbol_name (output_bfd, finfo->strtab, &isym,
- h->root.root.string);
- if (!result)
- return FALSE;
+ amt = (max_sym_count + 1) * symesz;
+ finfo.outsyms = bfd_malloc (amt);
- if (h->root.type == bfd_link_hash_undefined
- || h->root.type == bfd_link_hash_undefweak)
- {
- isym.n_value = 0;
- isym.n_scnum = N_UNDEF;
- isym.n_sclass = C_EXT;
- aux.x_csect.x_smtyp = XTY_ER;
- }
- else if ((h->root.type == bfd_link_hash_defined
- || h->root.type == bfd_link_hash_defweak)
- && h->smclas == XMC_XO)
- {
- BFD_ASSERT (bfd_is_abs_section (h->root.u.def.section));
- isym.n_value = h->root.u.def.value;
- isym.n_scnum = N_UNDEF;
- isym.n_sclass = C_EXT;
- aux.x_csect.x_smtyp = XTY_ER;
- }
- else if (h->root.type == bfd_link_hash_defined
- || h->root.type == bfd_link_hash_defweak)
- {
- struct xcoff_link_size_list *l;
+ amt = max_lineno_count * bfd_coff_linesz (abfd);
+ finfo.linenos = bfd_malloc (amt);
- isym.n_value = (h->root.u.def.section->output_section->vma
- + h->root.u.def.section->output_offset
- + h->root.u.def.value);
- if (bfd_is_abs_section (h->root.u.def.section->output_section))
- isym.n_scnum = N_ABS;
- else
- isym.n_scnum = h->root.u.def.section->output_section->target_index;
- isym.n_sclass = C_HIDEXT;
- aux.x_csect.x_smtyp = XTY_SD;
+ amt = max_contents_size;
+ finfo.contents = bfd_malloc (amt);
- if ((h->flags & XCOFF_HAS_SIZE) != 0)
+ amt = max_reloc_count * relsz;
+ finfo.external_relocs = bfd_malloc (amt);
+
+ if ((finfo.internal_syms == NULL && max_sym_count > 0)
+ || (finfo.sym_indices == NULL && max_sym_count > 0)
+ || finfo.outsyms == NULL
+ || (finfo.linenos == NULL && max_lineno_count > 0)
+ || (finfo.contents == NULL && max_contents_size > 0)
+ || (finfo.external_relocs == NULL && max_reloc_count > 0))
+ goto error_return;
+
+ obj_raw_syment_count (abfd) = 0;
+ xcoff_data (abfd)->toc = (bfd_vma) -1;
+
+ /* We now know the position of everything in the file, except that
+ we don't know the size of the symbol table and therefore we don't
+ know where the string table starts. We just build the string
+ table in memory as we go along. We process all the relocations
+ for a single input file at once. */
+ for (o = abfd->sections; o != NULL; o = o->next)
+ {
+ for (p = o->link_order_head; p != NULL; p = p->next)
{
- for (l = xcoff_hash_table (finfo->info)->size_list;
- l != NULL;
- l = l->next)
+ if (p->type == bfd_indirect_link_order
+ && p->u.indirect.section->owner->xvec == abfd->xvec)
{
- if (l->h == h)
+ sub = p->u.indirect.section->owner;
+ if (! sub->output_has_begun)
{
- aux.x_csect.x_scnlen.l = l->size;
- break;
+ if (! xcoff_link_input_bfd (&finfo, sub))
+ goto error_return;
+ sub->output_has_begun = TRUE;
}
}
+ else if (p->type == bfd_section_reloc_link_order
+ || p->type == bfd_symbol_reloc_link_order)
+ {
+ if (! xcoff_reloc_link_order (abfd, &finfo, o, p))
+ goto error_return;
+ }
+ else
+ {
+ if (! _bfd_default_link_order (abfd, info, o, p))
+ goto error_return;
+ }
}
}
- else if (h->root.type == bfd_link_hash_common)
+
+ /* Free up the buffers used by xcoff_link_input_bfd. */
+ if (finfo.internal_syms != NULL)
{
- isym.n_value = (h->root.u.c.p->section->output_section->vma
- + h->root.u.c.p->section->output_offset);
- isym.n_scnum = h->root.u.c.p->section->output_section->target_index;
- isym.n_sclass = C_EXT;
- aux.x_csect.x_smtyp = XTY_CM;
- aux.x_csect.x_scnlen.l = h->root.u.c.size;
+ free (finfo.internal_syms);
+ finfo.internal_syms = NULL;
+ }
+ if (finfo.sym_indices != NULL)
+ {
+ free (finfo.sym_indices);
+ finfo.sym_indices = NULL;
+ }
+ if (finfo.linenos != NULL)
+ {
+ free (finfo.linenos);
+ finfo.linenos = NULL;
+ }
+ if (finfo.contents != NULL)
+ {
+ free (finfo.contents);
+ finfo.contents = NULL;
+ }
+ if (finfo.external_relocs != NULL)
+ {
+ free (finfo.external_relocs);
+ finfo.external_relocs = NULL;
}
- else
- abort ();
-
- isym.n_type = T_NULL;
- isym.n_numaux = 1;
- bfd_coff_swap_sym_out (output_bfd, (PTR) &isym, (PTR) outsym);
- outsym += bfd_coff_symesz (output_bfd);
+ /* The value of the last C_FILE symbol is supposed to be -1. Write
+ it out again. */
+ if (finfo.last_file_index != -1)
+ {
+ finfo.last_file.n_value = -(bfd_vma) 1;
+ bfd_coff_swap_sym_out (abfd, (void *) &finfo.last_file,
+ (void *) finfo.outsyms);
+ pos = obj_sym_filepos (abfd) + finfo.last_file_index * symesz;
+ if (bfd_seek (abfd, pos, SEEK_SET) != 0
+ || bfd_bwrite (finfo.outsyms, symesz, abfd) != symesz)
+ goto error_return;
+ }
- aux.x_csect.x_smclas = h->smclas;
- bfd_coff_swap_aux_out (output_bfd, (PTR) &aux, T_NULL, isym.n_sclass, 0, 1,
- (PTR) outsym);
- outsym += bfd_coff_auxesz (output_bfd);
+ /* Write out all the global symbols which do not come from XCOFF
+ input files. */
+ xcoff_link_hash_traverse (xcoff_hash_table (info),
+ xcoff_write_global_symbol,
+ (void *) &finfo);
- if ((h->root.type == bfd_link_hash_defined
- || h->root.type == bfd_link_hash_defweak)
- && h->smclas != XMC_XO)
+ if (finfo.outsyms != NULL)
{
- /* We just output an SD symbol. Now output an LD symbol. */
-
- h->indx += 2;
+ free (finfo.outsyms);
+ finfo.outsyms = NULL;
+ }
- isym.n_sclass = C_EXT;
- bfd_coff_swap_sym_out (output_bfd, (PTR) &isym, (PTR) outsym);
- outsym += bfd_coff_symesz (output_bfd);
+ /* Now that we have written out all the global symbols, we know the
+ symbol indices to use for relocs against them, and we can finally
+ write out the relocs. */
+ amt = max_output_reloc_count * relsz;
+ external_relocs = bfd_malloc (amt);
+ if (external_relocs == NULL && max_output_reloc_count != 0)
+ goto error_return;
- aux.x_csect.x_smtyp = XTY_LD;
- aux.x_csect.x_scnlen.l = obj_raw_syment_count (output_bfd);
- bfd_coff_swap_aux_out (output_bfd, (PTR) &aux, T_NULL, C_EXT, 0, 1,
- (PTR) outsym);
- outsym += bfd_coff_auxesz (output_bfd);
- }
+ for (o = abfd->sections; o != NULL; o = o->next)
+ {
+ struct internal_reloc *irel;
+ struct internal_reloc *irelend;
+ struct xcoff_link_hash_entry **rel_hash;
+ struct xcoff_toc_rel_hash *toc_rel_hash;
+ bfd_byte *erel;
+ bfd_size_type rel_size;
- pos = obj_sym_filepos (output_bfd);
- pos += obj_raw_syment_count (output_bfd) * bfd_coff_symesz (output_bfd);
- amt = outsym - finfo->outsyms;
- if (bfd_seek (output_bfd, pos, SEEK_SET) != 0
- || bfd_bwrite (finfo->outsyms, amt, output_bfd) != amt)
- return FALSE;
- obj_raw_syment_count (output_bfd) +=
- (outsym - finfo->outsyms) / bfd_coff_symesz (output_bfd);
+ /* A stripped file has no relocs. */
+ if (info->strip == strip_all)
+ {
+ o->reloc_count = 0;
+ continue;
+ }
- return TRUE;
-}
+ if (o->reloc_count == 0)
+ continue;
-/* Handle a link order which is supposed to generate a reloc. */
+ irel = finfo.section_info[o->target_index].relocs;
+ irelend = irel + o->reloc_count;
+ rel_hash = finfo.section_info[o->target_index].rel_hashes;
+ for (; irel < irelend; irel++, rel_hash++, erel += relsz)
+ {
+ if (*rel_hash != NULL)
+ {
+ if ((*rel_hash)->indx < 0)
+ {
+ if (! ((*info->callbacks->unattached_reloc)
+ (info, (*rel_hash)->root.root.string,
+ NULL, o, irel->r_vaddr)))
+ goto error_return;
+ (*rel_hash)->indx = 0;
+ }
+ irel->r_symndx = (*rel_hash)->indx;
+ }
+ }
-static bfd_boolean
-xcoff_reloc_link_order (output_bfd, finfo, output_section, link_order)
- bfd *output_bfd;
- struct xcoff_final_link_info *finfo;
- asection *output_section;
- struct bfd_link_order *link_order;
-{
- reloc_howto_type *howto;
- struct xcoff_link_hash_entry *h;
- asection *hsec;
- bfd_vma hval;
- bfd_vma addend;
- struct internal_reloc *irel;
- struct xcoff_link_hash_entry **rel_hash_ptr;
- struct internal_ldrel ldrel;
+ for (toc_rel_hash = finfo.section_info[o->target_index].toc_rel_hashes;
+ toc_rel_hash != NULL;
+ toc_rel_hash = toc_rel_hash->next)
+ {
+ if (toc_rel_hash->h->u.toc_indx < 0)
+ {
+ if (! ((*info->callbacks->unattached_reloc)
+ (info, toc_rel_hash->h->root.root.string,
+ NULL, o, toc_rel_hash->rel->r_vaddr)))
+ goto error_return;
+ toc_rel_hash->h->u.toc_indx = 0;
+ }
+ toc_rel_hash->rel->r_symndx = toc_rel_hash->h->u.toc_indx;
+ }
- if (link_order->type == bfd_section_reloc_link_order)
- {
- /* We need to somehow locate a symbol in the right section. The
- symbol must either have a value of zero, or we must adjust
- the addend by the value of the symbol. FIXME: Write this
- when we need it. The old linker couldn't handle this anyhow. */
- abort ();
- }
+ /* XCOFF requires that the relocs be sorted by address. We tend
+ to produce them in the order in which their containing csects
+ appear in the symbol table, which is not necessarily by
+ address. So we sort them here. There may be a better way to
+ do this. */
+ qsort ((void *) finfo.section_info[o->target_index].relocs,
+ o->reloc_count, sizeof (struct internal_reloc),
+ xcoff_sort_relocs);
- howto = bfd_reloc_type_lookup (output_bfd, link_order->u.reloc.p->reloc);
- if (howto == NULL)
- {
- bfd_set_error (bfd_error_bad_value);
- return FALSE;
- }
+ irel = finfo.section_info[o->target_index].relocs;
+ irelend = irel + o->reloc_count;
+ erel = external_relocs;
+ for (; irel < irelend; irel++, rel_hash++, erel += relsz)
+ bfd_coff_swap_reloc_out (abfd, (void *) irel, (void *) erel);
- h = ((struct xcoff_link_hash_entry *)
- bfd_wrapped_link_hash_lookup (output_bfd, finfo->info,
- link_order->u.reloc.p->u.name,
- FALSE, FALSE, TRUE));
- if (h == NULL)
- {
- if (! ((*finfo->info->callbacks->unattached_reloc)
- (finfo->info, link_order->u.reloc.p->u.name, (bfd *) NULL,
- (asection *) NULL, (bfd_vma) 0)))
- return FALSE;
- return TRUE;
+ rel_size = relsz * o->reloc_count;
+ if (bfd_seek (abfd, o->rel_filepos, SEEK_SET) != 0
+ || bfd_bwrite ((void *) external_relocs, rel_size, abfd) != rel_size)
+ goto error_return;
}
- if (h->root.type == bfd_link_hash_common)
- {
- hsec = h->root.u.c.p->section;
- hval = 0;
- }
- else if (h->root.type == bfd_link_hash_defined
- || h->root.type == bfd_link_hash_defweak)
- {
- hsec = h->root.u.def.section;
- hval = h->root.u.def.value;
- }
- else
+ if (external_relocs != NULL)
{
- hsec = NULL;
- hval = 0;
+ free (external_relocs);
+ external_relocs = NULL;
}
- addend = link_order->u.reloc.p->addend;
- if (hsec != NULL)
- addend += (hsec->output_section->vma
- + hsec->output_offset
- + hval);
-
- if (addend != 0)
+ /* Free up the section information. */
+ if (finfo.section_info != NULL)
{
- bfd_size_type size;
- bfd_byte *buf;
- bfd_reloc_status_type rstat;
- bfd_boolean ok;
-
- size = bfd_get_reloc_size (howto);
- buf = (bfd_byte *) bfd_zmalloc (size);
- if (buf == NULL)
- return FALSE;
+ unsigned int i;
- rstat = _bfd_relocate_contents (howto, output_bfd, addend, buf);
- switch (rstat)
+ for (i = 0; i < abfd->section_count; i++)
{
- case bfd_reloc_ok:
- break;
- default:
- case bfd_reloc_outofrange:
- abort ();
- case bfd_reloc_overflow:
- if (! ((*finfo->info->callbacks->reloc_overflow)
- (finfo->info, NULL, link_order->u.reloc.p->u.name,
- howto->name, addend, (bfd *) NULL, (asection *) NULL,
- (bfd_vma) 0)))
- {
- free (buf);
- return FALSE;
- }
- break;
+ if (finfo.section_info[i].relocs != NULL)
+ free (finfo.section_info[i].relocs);
+ if (finfo.section_info[i].rel_hashes != NULL)
+ free (finfo.section_info[i].rel_hashes);
}
- ok = bfd_set_section_contents (output_bfd, output_section, (PTR) buf,
- (file_ptr) link_order->offset, size);
- free (buf);
- if (! ok)
- return FALSE;
+ free (finfo.section_info);
+ finfo.section_info = NULL;
}
- /* Store the reloc information in the right place. It will get
- swapped and written out at the end of the final_link routine. */
+ /* Write out the loader section contents. */
+ BFD_ASSERT ((bfd_byte *) finfo.ldrel
+ == (xcoff_hash_table (info)->loader_section->contents
+ + xcoff_hash_table (info)->ldhdr.l_impoff));
+ o = xcoff_hash_table (info)->loader_section;
+ if (! bfd_set_section_contents (abfd, o->output_section, o->contents,
+ (file_ptr) o->output_offset, o->size))
+ goto error_return;
- irel = (finfo->section_info[output_section->target_index].relocs
- + output_section->reloc_count);
- rel_hash_ptr = (finfo->section_info[output_section->target_index].rel_hashes
- + output_section->reloc_count);
+ /* Write out the magic sections. */
+ o = xcoff_hash_table (info)->linkage_section;
+ if (o->size > 0
+ && ! bfd_set_section_contents (abfd, o->output_section, o->contents,
+ (file_ptr) o->output_offset,
+ o->size))
+ goto error_return;
+ o = xcoff_hash_table (info)->toc_section;
+ if (o->size > 0
+ && ! bfd_set_section_contents (abfd, o->output_section, o->contents,
+ (file_ptr) o->output_offset,
+ o->size))
+ goto error_return;
+ o = xcoff_hash_table (info)->descriptor_section;
+ if (o->size > 0
+ && ! bfd_set_section_contents (abfd, o->output_section, o->contents,
+ (file_ptr) o->output_offset,
+ o->size))
+ goto error_return;
- memset (irel, 0, sizeof (struct internal_reloc));
- *rel_hash_ptr = NULL;
+ /* Write out the string table. */
+ pos = obj_sym_filepos (abfd) + obj_raw_syment_count (abfd) * symesz;
+ if (bfd_seek (abfd, pos, SEEK_SET) != 0)
+ goto error_return;
+ H_PUT_32 (abfd,
+ _bfd_stringtab_size (finfo.strtab) + STRING_SIZE_SIZE,
+ strbuf);
+ amt = STRING_SIZE_SIZE;
+ if (bfd_bwrite (strbuf, amt, abfd) != amt)
+ goto error_return;
+ if (! _bfd_stringtab_emit (abfd, finfo.strtab))
+ goto error_return;
- irel->r_vaddr = output_section->vma + link_order->offset;
+ _bfd_stringtab_free (finfo.strtab);
- if (h->indx >= 0)
- irel->r_symndx = h->indx;
- else
+ /* Write out the debugging string table. */
+ o = xcoff_hash_table (info)->debug_section;
+ if (o != NULL)
{
- /* Set the index to -2 to force this symbol to get written out. */
- h->indx = -2;
- *rel_hash_ptr = h;
- irel->r_symndx = 0;
- }
+ struct bfd_strtab_hash *debug_strtab;
- irel->r_type = howto->type;
- irel->r_size = howto->bitsize - 1;
- if (howto->complain_on_overflow == complain_overflow_signed)
- irel->r_size |= 0x80;
+ debug_strtab = xcoff_hash_table (info)->debug_strtab;
+ BFD_ASSERT (o->output_section->size - o->output_offset
+ >= _bfd_stringtab_size (debug_strtab));
+ pos = o->output_section->filepos + o->output_offset;
+ if (bfd_seek (abfd, pos, SEEK_SET) != 0)
+ goto error_return;
+ if (! _bfd_stringtab_emit (abfd, debug_strtab))
+ goto error_return;
+ }
- ++output_section->reloc_count;
+ /* Setting bfd_get_symcount to 0 will cause write_object_contents to
+ not try to write out the symbols. */
+ bfd_get_symcount (abfd) = 0;
- /* Now output the reloc to the .loader section. */
+ return TRUE;
- ldrel.l_vaddr = irel->r_vaddr;
+ error_return:
+ if (finfo.strtab != NULL)
+ _bfd_stringtab_free (finfo.strtab);
- if (hsec != NULL)
+ if (finfo.section_info != NULL)
{
- const char *secname;
-
- secname = hsec->output_section->name;
+ unsigned int i;
- if (strcmp (secname, ".text") == 0)
- ldrel.l_symndx = 0;
- else if (strcmp (secname, ".data") == 0)
- ldrel.l_symndx = 1;
- else if (strcmp (secname, ".bss") == 0)
- ldrel.l_symndx = 2;
- else
- {
- (*_bfd_error_handler)
- (_("%s: loader reloc in unrecognized section `%s'"),
- bfd_get_filename (output_bfd), secname);
- bfd_set_error (bfd_error_nonrepresentable_section);
- return FALSE;
- }
- }
- else
- {
- if (h->ldindx < 0)
+ for (i = 0; i < abfd->section_count; i++)
{
- (*_bfd_error_handler)
- (_("%s: `%s' in loader reloc but not loader sym"),
- bfd_get_filename (output_bfd),
- h->root.root.string);
- bfd_set_error (bfd_error_bad_value);
- return FALSE;
+ if (finfo.section_info[i].relocs != NULL)
+ free (finfo.section_info[i].relocs);
+ if (finfo.section_info[i].rel_hashes != NULL)
+ free (finfo.section_info[i].rel_hashes);
}
- ldrel.l_symndx = h->ldindx;
+ free (finfo.section_info);
}
- ldrel.l_rtype = (irel->r_size << 8) | irel->r_type;
- ldrel.l_rsecnm = output_section->target_index;
- bfd_xcoff_swap_ldrel_out (output_bfd, &ldrel, finfo->ldrel);
- finfo->ldrel += bfd_xcoff_ldrelsz(output_bfd);
-
- return TRUE;
-}
-
-/* Sort relocs by VMA. This is called via qsort. */
-
-static int
-xcoff_sort_relocs (p1, p2)
- const PTR p1;
- const PTR p2;
-{
- const struct internal_reloc *r1 = (const struct internal_reloc *) p1;
- const struct internal_reloc *r2 = (const struct internal_reloc *) p2;
-
- if (r1->r_vaddr > r2->r_vaddr)
- return 1;
- else if (r1->r_vaddr < r2->r_vaddr)
- return -1;
- else
- return 0;
+ if (finfo.internal_syms != NULL)
+ free (finfo.internal_syms);
+ if (finfo.sym_indices != NULL)
+ free (finfo.sym_indices);
+ if (finfo.outsyms != NULL)
+ free (finfo.outsyms);
+ if (finfo.linenos != NULL)
+ free (finfo.linenos);
+ if (finfo.contents != NULL)
+ free (finfo.contents);
+ if (finfo.external_relocs != NULL)
+ free (finfo.external_relocs);
+ if (external_relocs != NULL)
+ free (external_relocs);
+ return FALSE;
}
-
-
-
-
#include "sysdep.h"
#include "libbfd.h"
-#define bfd_sym_close_and_cleanup _bfd_generic_close_and_cleanup
-#define bfd_sym_bfd_free_cached_info _bfd_generic_bfd_free_cached_info
-#define bfd_sym_new_section_hook _bfd_generic_new_section_hook
-#define bfd_sym_bfd_is_local_label_name bfd_generic_is_local_label_name
-#define bfd_sym_bfd_is_target_special_symbol ((bfd_boolean (*) (bfd *, asymbol *)) bfd_false)
-#define bfd_sym_get_lineno _bfd_nosymbols_get_lineno
-#define bfd_sym_find_nearest_line _bfd_nosymbols_find_nearest_line
-#define bfd_sym_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
-#define bfd_sym_read_minisymbols _bfd_generic_read_minisymbols
-#define bfd_sym_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol
-#define bfd_sym_get_reloc_upper_bound _bfd_norelocs_get_reloc_upper_bound
-#define bfd_sym_canonicalize_reloc _bfd_norelocs_canonicalize_reloc
-#define bfd_sym_bfd_reloc_type_lookup _bfd_norelocs_bfd_reloc_type_lookup
-#define bfd_sym_set_arch_mach _bfd_generic_set_arch_mach
-#define bfd_sym_get_section_contents _bfd_generic_get_section_contents
-#define bfd_sym_set_section_contents _bfd_generic_set_section_contents
-#define bfd_sym_bfd_get_relocated_section_contents bfd_generic_get_relocated_section_contents
-#define bfd_sym_bfd_relax_section bfd_generic_relax_section
-#define bfd_sym_bfd_gc_sections bfd_generic_gc_sections
-#define bfd_sym_bfd_merge_sections bfd_generic_merge_sections
-#define bfd_sym_bfd_is_group_section bfd_generic_is_group_section
-#define bfd_sym_bfd_discard_group bfd_generic_discard_group
-#define bfd_sym_section_already_linked \
- _bfd_generic_section_already_linked
-#define bfd_sym_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
-#define bfd_sym_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
-#define bfd_sym_bfd_link_add_symbols _bfd_generic_link_add_symbols
-#define bfd_sym_bfd_link_just_syms _bfd_generic_link_just_syms
-#define bfd_sym_bfd_final_link _bfd_generic_final_link
-#define bfd_sym_bfd_link_split_section _bfd_generic_link_split_section
-#define bfd_sym_get_section_contents_in_window _bfd_generic_get_section_contents_in_window
-
-static unsigned long compute_offset
- PARAMS ((unsigned long, unsigned long, unsigned long, unsigned long));
+#define bfd_sym_close_and_cleanup _bfd_generic_close_and_cleanup
+#define bfd_sym_bfd_free_cached_info _bfd_generic_bfd_free_cached_info
+#define bfd_sym_new_section_hook _bfd_generic_new_section_hook
+#define bfd_sym_bfd_is_local_label_name bfd_generic_is_local_label_name
+#define bfd_sym_bfd_is_target_special_symbol ((bfd_boolean (*) (bfd *, asymbol *)) bfd_false)
+#define bfd_sym_get_lineno _bfd_nosymbols_get_lineno
+#define bfd_sym_find_nearest_line _bfd_nosymbols_find_nearest_line
+#define bfd_sym_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
+#define bfd_sym_read_minisymbols _bfd_generic_read_minisymbols
+#define bfd_sym_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol
+#define bfd_sym_get_reloc_upper_bound _bfd_norelocs_get_reloc_upper_bound
+#define bfd_sym_canonicalize_reloc _bfd_norelocs_canonicalize_reloc
+#define bfd_sym_bfd_reloc_type_lookup _bfd_norelocs_bfd_reloc_type_lookup
+#define bfd_sym_set_arch_mach _bfd_generic_set_arch_mach
+#define bfd_sym_get_section_contents _bfd_generic_get_section_contents
+#define bfd_sym_set_section_contents _bfd_generic_set_section_contents
+#define bfd_sym_bfd_get_relocated_section_contents bfd_generic_get_relocated_section_contents
+#define bfd_sym_bfd_relax_section bfd_generic_relax_section
+#define bfd_sym_bfd_gc_sections bfd_generic_gc_sections
+#define bfd_sym_bfd_merge_sections bfd_generic_merge_sections
+#define bfd_sym_bfd_is_group_section bfd_generic_is_group_section
+#define bfd_sym_bfd_discard_group bfd_generic_discard_group
+#define bfd_sym_section_already_linked _bfd_generic_section_already_linked
+#define bfd_sym_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
+#define bfd_sym_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
+#define bfd_sym_bfd_link_add_symbols _bfd_generic_link_add_symbols
+#define bfd_sym_bfd_link_just_syms _bfd_generic_link_just_syms
+#define bfd_sym_bfd_final_link _bfd_generic_final_link
+#define bfd_sym_bfd_link_split_section _bfd_generic_link_split_section
+#define bfd_sym_get_section_contents_in_window _bfd_generic_get_section_contents_in_window
extern const bfd_target sym_vec;
}
static unsigned long
-compute_offset (first_page, page_size, entry_size, index)
- unsigned long first_page;
- unsigned long page_size;
- unsigned long entry_size;
- unsigned long index;
+compute_offset (unsigned long first_page,
+ unsigned long page_size,
+ unsigned long entry_size,
+ unsigned long index)
{
unsigned long entries_per_page = page_size / entry_size;
unsigned long page_number = first_page + (index / entries_per_page);
}
bfd_boolean
-bfd_sym_mkobject (abfd)
- bfd *abfd ATTRIBUTE_UNUSED;
+bfd_sym_mkobject (bfd *abfd ATTRIBUTE_UNUSED)
{
return 1;
}
void
-bfd_sym_print_symbol (abfd, afile, symbol, how)
- bfd *abfd ATTRIBUTE_UNUSED;
- PTR afile ATTRIBUTE_UNUSED;
- asymbol *symbol ATTRIBUTE_UNUSED;
- bfd_print_symbol_type how ATTRIBUTE_UNUSED;
+bfd_sym_print_symbol (bfd *abfd ATTRIBUTE_UNUSED,
+ void * afile ATTRIBUTE_UNUSED,
+ asymbol *symbol ATTRIBUTE_UNUSED,
+ bfd_print_symbol_type how ATTRIBUTE_UNUSED)
{
return;
}
bfd_boolean
-bfd_sym_valid (abfd)
- bfd *abfd;
+bfd_sym_valid (bfd *abfd)
{
if (abfd == NULL || abfd->xvec == NULL)
return 0;
}
unsigned char *
-bfd_sym_read_name_table (abfd, dshb)
- bfd *abfd;
- bfd_sym_header_block *dshb;
+bfd_sym_read_name_table (bfd *abfd, bfd_sym_header_block *dshb)
{
unsigned char *rstr;
long ret;
size_t table_size = dshb->dshb_nte.dti_page_count * dshb->dshb_page_size;
size_t table_offset = dshb->dshb_nte.dti_first_page * dshb->dshb_page_size;
- rstr = (unsigned char *) bfd_alloc (abfd, table_size);
+ rstr = bfd_alloc (abfd, table_size);
if (rstr == NULL)
return rstr;
}
void
-bfd_sym_parse_file_reference_v32 (buf, len, entry)
- unsigned char *buf;
- size_t len;
- bfd_sym_file_reference *entry;
+bfd_sym_parse_file_reference_v32 (unsigned char *buf,
+ size_t len,
+ bfd_sym_file_reference *entry)
{
BFD_ASSERT (len == 6);
}
void
-bfd_sym_parse_disk_table_v32 (buf, len, table)
- unsigned char *buf;
- size_t len;
- bfd_sym_table_info *table;
+bfd_sym_parse_disk_table_v32 (unsigned char *buf,
+ size_t len,
+ bfd_sym_table_info *table)
{
BFD_ASSERT (len == 8);
}
void
-bfd_sym_parse_header_v32 (buf, len, header)
- unsigned char *buf;
- size_t len;
- bfd_sym_header_block *header;
+bfd_sym_parse_header_v32 (unsigned char *buf,
+ size_t len,
+ bfd_sym_header_block *header)
{
BFD_ASSERT (len == 154);
}
int
-bfd_sym_read_header_v32 (abfd, header)
- bfd *abfd;
- bfd_sym_header_block *header;
+bfd_sym_read_header_v32 (bfd *abfd, bfd_sym_header_block *header)
{
unsigned char buf[154];
long ret;
}
int
-bfd_sym_read_header_v34 (abfd, header)
- bfd *abfd ATTRIBUTE_UNUSED;
- bfd_sym_header_block *header ATTRIBUTE_UNUSED;
+bfd_sym_read_header_v34 (bfd *abfd ATTRIBUTE_UNUSED,
+ bfd_sym_header_block *header ATTRIBUTE_UNUSED)
{
abort ();
}
int
-bfd_sym_read_header (abfd, header, version)
- bfd *abfd;
- bfd_sym_header_block *header;
- bfd_sym_version version;
+bfd_sym_read_header (bfd *abfd,
+ bfd_sym_header_block *header,
+ bfd_sym_version version)
{
switch (version)
{
return bfd_sym_read_header_v32 (abfd, header);
case BFD_SYM_VERSION_3_1:
default:
- return FALSE;
+ return 0;
}
}
int
-bfd_sym_read_version (abfd, version)
- bfd *abfd;
- bfd_sym_version *version;
+bfd_sym_read_version (bfd *abfd, bfd_sym_version *version)
{
char version_string[32];
long ret;
}
void
-bfd_sym_display_table_summary (f, dti, name)
- FILE *f;
- bfd_sym_table_info *dti;
- const char *name;
+bfd_sym_display_table_summary (FILE *f,
+ bfd_sym_table_info *dti,
+ const char *name)
{
fprintf (f, "%-6s %13ld %13ld %13ld\n",
name,
}
void
-bfd_sym_display_header (f, dshb)
- FILE *f;
- bfd_sym_header_block *dshb;
+bfd_sym_display_header (FILE *f, bfd_sym_header_block *dshb)
{
fprintf (f, " Version: %.*s\n", dshb->dshb_id[0], dshb->dshb_id + 1);
fprintf (f, " Page Size: 0x%x\n", dshb->dshb_page_size);
}
void
-bfd_sym_parse_resources_table_entry_v32 (buf, len, entry)
- unsigned char *buf;
- size_t len;
- bfd_sym_resources_table_entry *entry;
+bfd_sym_parse_resources_table_entry_v32 (unsigned char *buf,
+ size_t len,
+ bfd_sym_resources_table_entry *entry)
{
BFD_ASSERT (len == 18);
}
void
-bfd_sym_parse_modules_table_entry_v33 (buf, len, entry)
- unsigned char *buf;
- size_t len;
- bfd_sym_modules_table_entry *entry;
+bfd_sym_parse_modules_table_entry_v33 (unsigned char *buf,
+ size_t len,
+ bfd_sym_modules_table_entry *entry)
{
BFD_ASSERT (len == 46);
}
void
-bfd_sym_parse_file_references_table_entry_v32 (buf, len, entry)
- unsigned char *buf;
- size_t len;
- bfd_sym_file_references_table_entry *entry;
+bfd_sym_parse_file_references_table_entry_v32 (unsigned char *buf,
+ size_t len,
+ bfd_sym_file_references_table_entry *entry)
{
unsigned int type;
}
void
-bfd_sym_parse_contained_modules_table_entry_v32 (buf, len, entry)
- unsigned char *buf;
- size_t len;
- bfd_sym_contained_modules_table_entry *entry;
+bfd_sym_parse_contained_modules_table_entry_v32 (unsigned char *buf,
+ size_t len,
+ bfd_sym_contained_modules_table_entry *entry)
{
unsigned int type;
}
void
-bfd_sym_parse_contained_variables_table_entry_v32 (buf, len, entry)
- unsigned char *buf;
- size_t len;
- bfd_sym_contained_variables_table_entry *entry;
+bfd_sym_parse_contained_variables_table_entry_v32 (unsigned char *buf,
+ size_t len,
+ bfd_sym_contained_variables_table_entry *entry)
{
unsigned int type;
else if (entry->entry.la_size <= BFD_SYM_CVTE_SCA)
{
#if BFD_SYM_CVTE_SCA > 0
- memcpy (&entry->entry.address.lastruct.la, buf + 10, BFD_SYM_CVTE_SCA);
+ memcpy (&entry->entry.address.lastruct.la, buf + 10,
+ BFD_SYM_CVTE_SCA);
#endif
entry->entry.address.lastruct.la_kind = buf[23];
}
}
void
-bfd_sym_parse_contained_statements_table_entry_v32 (buf, len, entry)
- unsigned char *buf;
- size_t len;
- bfd_sym_contained_statements_table_entry *entry;
+bfd_sym_parse_contained_statements_table_entry_v32 (unsigned char *buf,
+ size_t len,
+ bfd_sym_contained_statements_table_entry *entry)
{
unsigned int type;
}
void
-bfd_sym_parse_contained_labels_table_entry_v32 (buf, len, entry)
- unsigned char *buf;
- size_t len;
- bfd_sym_contained_labels_table_entry *entry;
+bfd_sym_parse_contained_labels_table_entry_v32 (unsigned char *buf,
+ size_t len,
+ bfd_sym_contained_labels_table_entry *entry)
{
unsigned int type;
}
void
-bfd_sym_parse_type_table_entry_v32 (buf, len, entry)
- unsigned char *buf;
- size_t len;
- bfd_sym_type_table_entry *entry;
+bfd_sym_parse_type_table_entry_v32 (unsigned char *buf,
+ size_t len,
+ bfd_sym_type_table_entry *entry)
{
BFD_ASSERT (len == 4);
}
int
-bfd_sym_fetch_resources_table_entry (abfd, entry, index)
- bfd *abfd;
- bfd_sym_resources_table_entry *entry;
- unsigned long index;
+bfd_sym_fetch_resources_table_entry (bfd *abfd,
+ bfd_sym_resources_table_entry *entry,
+ unsigned long index)
{
- void (*parser) PARAMS ((unsigned char *, size_t,
- bfd_sym_resources_table_entry *));
+ void (*parser) (unsigned char *, size_t, bfd_sym_resources_table_entry *);
unsigned long offset;
unsigned long entry_size;
unsigned char buf[18];
}
int
-bfd_sym_fetch_modules_table_entry (abfd, entry, index)
- bfd *abfd;
- bfd_sym_modules_table_entry *entry;
- unsigned long index;
+bfd_sym_fetch_modules_table_entry (bfd *abfd,
+ bfd_sym_modules_table_entry *entry,
+ unsigned long index)
{
- void (*parser) PARAMS ((unsigned char *, size_t,
- bfd_sym_modules_table_entry *));
+ void (*parser) (unsigned char *, size_t, bfd_sym_modules_table_entry *);
unsigned long offset;
unsigned long entry_size;
unsigned char buf[46];
}
int
-bfd_sym_fetch_file_references_table_entry (abfd, entry, index)
- bfd *abfd;
- bfd_sym_file_references_table_entry *entry;
- unsigned long index;
+bfd_sym_fetch_file_references_table_entry (bfd *abfd,
+ bfd_sym_file_references_table_entry *entry,
+ unsigned long index)
{
- void (*parser) PARAMS ((unsigned char *, size_t,
- bfd_sym_file_references_table_entry *));
+ void (*parser) (unsigned char *, size_t, bfd_sym_file_references_table_entry *);
unsigned long offset;
unsigned long entry_size = 0;
unsigned char buf[8];
}
int
-bfd_sym_fetch_contained_modules_table_entry (abfd, entry, index)
- bfd *abfd;
- bfd_sym_contained_modules_table_entry *entry;
- unsigned long index;
+bfd_sym_fetch_contained_modules_table_entry (bfd *abfd,
+ bfd_sym_contained_modules_table_entry *entry,
+ unsigned long index)
{
- void (*parser) PARAMS ((unsigned char *, size_t,
- bfd_sym_contained_modules_table_entry *));
+ void (*parser) (unsigned char *, size_t, bfd_sym_contained_modules_table_entry *);
unsigned long offset;
unsigned long entry_size = 0;
unsigned char buf[6];
}
int
-bfd_sym_fetch_contained_variables_table_entry (abfd, entry, index)
- bfd *abfd;
- bfd_sym_contained_variables_table_entry *entry;
- unsigned long index;
+bfd_sym_fetch_contained_variables_table_entry (bfd *abfd,
+ bfd_sym_contained_variables_table_entry *entry,
+ unsigned long index)
{
- void (*parser) PARAMS ((unsigned char *, size_t,
- bfd_sym_contained_variables_table_entry *));
+ void (*parser) (unsigned char *, size_t, bfd_sym_contained_variables_table_entry *);
unsigned long offset;
unsigned long entry_size = 0;
unsigned char buf[26];
}
int
-bfd_sym_fetch_contained_statements_table_entry (abfd, entry, index)
- bfd *abfd;
- bfd_sym_contained_statements_table_entry *entry;
- unsigned long index;
+bfd_sym_fetch_contained_statements_table_entry (bfd *abfd,
+ bfd_sym_contained_statements_table_entry *entry,
+ unsigned long index)
{
- void (*parser) PARAMS ((unsigned char *, size_t,
- bfd_sym_contained_statements_table_entry *));
+ void (*parser) (unsigned char *, size_t, bfd_sym_contained_statements_table_entry *);
unsigned long offset;
unsigned long entry_size = 0;
unsigned char buf[8];
}
int
-bfd_sym_fetch_contained_labels_table_entry (abfd, entry, index)
- bfd *abfd;
- bfd_sym_contained_labels_table_entry *entry;
- unsigned long index;
+bfd_sym_fetch_contained_labels_table_entry (bfd *abfd,
+ bfd_sym_contained_labels_table_entry *entry,
+ unsigned long index)
{
- void (*parser) PARAMS ((unsigned char *, size_t,
- bfd_sym_contained_labels_table_entry *));
+ void (*parser) (unsigned char *, size_t, bfd_sym_contained_labels_table_entry *);
unsigned long offset;
unsigned long entry_size = 0;
unsigned char buf[12];
}
int
-bfd_sym_fetch_contained_types_table_entry (abfd, entry, index)
- bfd *abfd;
- bfd_sym_contained_types_table_entry *entry;
- unsigned long index;
+bfd_sym_fetch_contained_types_table_entry (bfd *abfd,
+ bfd_sym_contained_types_table_entry *entry,
+ unsigned long index)
{
- void (*parser) PARAMS ((unsigned char *, size_t,
- bfd_sym_contained_types_table_entry *));
+ void (*parser) (unsigned char *, size_t, bfd_sym_contained_types_table_entry *);
unsigned long offset;
unsigned long entry_size = 0;
unsigned char buf[0];
}
int
-bfd_sym_fetch_file_references_index_table_entry (abfd, entry, index)
- bfd *abfd;
- bfd_sym_file_references_index_table_entry *entry;
- unsigned long index;
+bfd_sym_fetch_file_references_index_table_entry (bfd *abfd,
+ bfd_sym_file_references_index_table_entry *entry,
+ unsigned long index)
{
- void (*parser) PARAMS ((unsigned char *, size_t,
- bfd_sym_file_references_index_table_entry *));
+ void (*parser) (unsigned char *, size_t, bfd_sym_file_references_index_table_entry *);
unsigned long offset;
unsigned long entry_size = 0;
unsigned char buf[0];
}
int
-bfd_sym_fetch_constant_pool_entry (abfd, entry, index)
- bfd *abfd;
- bfd_sym_constant_pool_entry *entry;
- unsigned long index;
+bfd_sym_fetch_constant_pool_entry (bfd *abfd,
+ bfd_sym_constant_pool_entry *entry,
+ unsigned long index)
{
- void (*parser) PARAMS ((unsigned char *, size_t,
- bfd_sym_constant_pool_entry *));
+ void (*parser) (unsigned char *, size_t, bfd_sym_constant_pool_entry *);
unsigned long offset;
unsigned long entry_size = 0;
unsigned char buf[0];
}
int
-bfd_sym_fetch_type_table_entry (abfd, entry, index)
- bfd *abfd;
- bfd_sym_type_table_entry *entry;
- unsigned long index;
+bfd_sym_fetch_type_table_entry (bfd *abfd,
+ bfd_sym_type_table_entry *entry,
+ unsigned long index)
{
- void (*parser) PARAMS ((unsigned char *, size_t,
- bfd_sym_type_table_entry *));
+ void (*parser) (unsigned char *, size_t, bfd_sym_type_table_entry *);
unsigned long offset;
unsigned long entry_size = 0;
unsigned char buf[4];
}
int
-bfd_sym_fetch_type_information_table_entry (abfd, entry, offset)
- bfd *abfd;
- bfd_sym_type_information_table_entry *entry;
- unsigned long offset;
+bfd_sym_fetch_type_information_table_entry (bfd *abfd,
+ bfd_sym_type_information_table_entry *entry,
+ unsigned long offset)
{
unsigned char buf[4];
bfd_sym_data_struct *sdata = NULL;
}
int
-bfd_sym_fetch_type_table_information (abfd, entry, index)
- bfd *abfd;
- bfd_sym_type_information_table_entry *entry;
- unsigned long index;
+bfd_sym_fetch_type_table_information (bfd *abfd,
+ bfd_sym_type_information_table_entry *entry,
+ unsigned long index)
{
bfd_sym_type_table_entry tindex;
bfd_sym_data_struct *sdata = NULL;
}
const unsigned char *
-bfd_sym_symbol_name (abfd, index)
- bfd *abfd;
- unsigned long index;
+bfd_sym_symbol_name (bfd *abfd, unsigned long index)
{
bfd_sym_data_struct *sdata = NULL;
}
const unsigned char *
-bfd_sym_module_name (abfd, index)
- bfd *abfd;
- unsigned long index;
+bfd_sym_module_name (bfd *abfd, unsigned long index)
{
bfd_sym_modules_table_entry entry;
}
const char *
-bfd_sym_unparse_storage_kind (kind)
- enum bfd_sym_storage_kind kind;
+bfd_sym_unparse_storage_kind (enum bfd_sym_storage_kind kind)
{
switch (kind)
{
}
const char *
-bfd_sym_unparse_storage_class (kind)
- enum bfd_sym_storage_class kind;
+bfd_sym_unparse_storage_class (enum bfd_sym_storage_class kind)
{
switch (kind)
{
}
const char *
-bfd_sym_unparse_module_kind (kind)
- enum bfd_sym_module_kind kind;
+bfd_sym_unparse_module_kind (enum bfd_sym_module_kind kind)
{
switch (kind)
{
}
const char *
-bfd_sym_unparse_symbol_scope (scope)
- enum bfd_sym_symbol_scope scope;
+bfd_sym_unparse_symbol_scope (enum bfd_sym_symbol_scope scope)
{
switch (scope)
{
}
void
-bfd_sym_print_file_reference (abfd, f, entry)
- bfd *abfd;
- FILE *f;
- bfd_sym_file_reference *entry;
+bfd_sym_print_file_reference (bfd *abfd,
+ FILE *f,
+ bfd_sym_file_reference *entry)
{
bfd_sym_file_references_table_entry frtentry;
int ret;
}
void
-bfd_sym_print_resources_table_entry (abfd, f, entry)
- bfd *abfd;
- FILE *f;
- bfd_sym_resources_table_entry *entry;
+bfd_sym_print_resources_table_entry (bfd *abfd,
+ FILE *f,
+ bfd_sym_resources_table_entry *entry)
{
fprintf (f, " \"%.*s\" (NTE %lu), type \"%.4s\", num %u, size %lu, MTE %lu -- %lu",
bfd_sym_symbol_name (abfd, entry->rte_nte_index)[0],
}
void
-bfd_sym_print_modules_table_entry (abfd, f, entry)
- bfd *abfd;
- FILE *f;
- bfd_sym_modules_table_entry *entry;
+bfd_sym_print_modules_table_entry (bfd *abfd,
+ FILE *f,
+ bfd_sym_modules_table_entry *entry)
{
fprintf (f, "\"%.*s\" (NTE %lu)",
bfd_sym_symbol_name (abfd, entry->mte_nte_index)[0],
}
void
-bfd_sym_print_file_references_table_entry (abfd, f, entry)
- bfd *abfd;
- FILE *f;
- bfd_sym_file_references_table_entry *entry;
+bfd_sym_print_file_references_table_entry (bfd *abfd,
+ FILE *f,
+ bfd_sym_file_references_table_entry *entry)
{
switch (entry->generic.type)
{
}
void
-bfd_sym_print_contained_modules_table_entry (abfd, f, entry)
- bfd *abfd;
- FILE *f;
- bfd_sym_contained_modules_table_entry *entry;
+bfd_sym_print_contained_modules_table_entry (bfd *abfd,
+ FILE *f,
+ bfd_sym_contained_modules_table_entry *entry)
{
switch (entry->generic.type)
{
}
void
-bfd_sym_print_contained_variables_table_entry (abfd, f, entry)
- bfd *abfd;
- FILE *f;
- bfd_sym_contained_variables_table_entry *entry;
+bfd_sym_print_contained_variables_table_entry (bfd *abfd,
+ FILE *f,
+ bfd_sym_contained_variables_table_entry *entry)
{
if (entry->generic.type == BFD_SYM_END_OF_LIST)
{
}
void
-bfd_sym_print_contained_statements_table_entry (abfd, f, entry)
- bfd *abfd;
- FILE *f;
- bfd_sym_contained_statements_table_entry *entry;
+bfd_sym_print_contained_statements_table_entry (bfd *abfd,
+ FILE *f,
+ bfd_sym_contained_statements_table_entry *entry)
{
if (entry->generic.type == BFD_SYM_END_OF_LIST)
{
}
void
-bfd_sym_print_contained_labels_table_entry (abfd, f, entry)
- bfd *abfd;
- FILE *f;
- bfd_sym_contained_labels_table_entry *entry;
+bfd_sym_print_contained_labels_table_entry (bfd *abfd,
+ FILE *f,
+ bfd_sym_contained_labels_table_entry *entry)
{
if (entry->generic.type == BFD_SYM_END_OF_LIST)
{
}
void
-bfd_sym_print_contained_types_table_entry (abfd, f, entry)
- bfd *abfd ATTRIBUTE_UNUSED;
- FILE *f;
- bfd_sym_contained_types_table_entry *entry ATTRIBUTE_UNUSED;
+bfd_sym_print_contained_types_table_entry (bfd *abfd ATTRIBUTE_UNUSED,
+ FILE *f,
+ bfd_sym_contained_types_table_entry *entry ATTRIBUTE_UNUSED)
{
fprintf (f, "[UNIMPLEMENTED]");
}
const char *
-bfd_sym_type_operator_name (num)
- unsigned char num;
+bfd_sym_type_operator_name (unsigned char num)
{
switch (num)
{
}
const char *
-bfd_sym_type_basic_name (num)
- unsigned char num;
+bfd_sym_type_basic_name (unsigned char num)
{
switch (num)
{
}
int
-bfd_sym_fetch_long (buf, len, offset, offsetptr, value)
- unsigned char *buf;
- unsigned long len;
- unsigned long offset;
- unsigned long *offsetptr;
- long *value;
+bfd_sym_fetch_long (unsigned char *buf,
+ unsigned long len,
+ unsigned long offset,
+ unsigned long *offsetptr,
+ long *value)
{
int ret;
}
void
-bfd_sym_print_type_information (abfd, f, buf, len, offset, offsetptr)
- bfd *abfd;
- FILE *f;
- unsigned char *buf;
- unsigned long len;
- unsigned long offset;
- unsigned long *offsetptr;
+bfd_sym_print_type_information (bfd *abfd,
+ FILE *f,
+ unsigned char *buf,
+ unsigned long len,
+ unsigned long offset,
+ unsigned long *offsetptr)
{
unsigned int type;
}
void
-bfd_sym_print_type_information_table_entry (abfd, f, entry)
- bfd *abfd;
- FILE *f;
- bfd_sym_type_information_table_entry *entry;
+bfd_sym_print_type_information_table_entry (bfd *abfd,
+ FILE *f,
+ bfd_sym_type_information_table_entry *entry)
{
unsigned char *buf;
unsigned long offset;
bfd_sym_print_type_information (abfd, f, buf, entry->physical_size, 0, &offset);
if (offset != entry->physical_size)
- fprintf (f, "\n [parser used %lu bytes instead of %lu]", offset, entry->physical_size); }
+ fprintf (f, "\n [parser used %lu bytes instead of %lu]", offset, entry->physical_size);
+}
void
-bfd_sym_print_file_references_index_table_entry (abfd, f, entry)
- bfd *abfd ATTRIBUTE_UNUSED;
- FILE *f;
- bfd_sym_file_references_index_table_entry *entry ATTRIBUTE_UNUSED;
+bfd_sym_print_file_references_index_table_entry (bfd *abfd ATTRIBUTE_UNUSED,
+ FILE *f,
+ bfd_sym_file_references_index_table_entry *entry ATTRIBUTE_UNUSED)
{
fprintf (f, "[UNIMPLEMENTED]");
}
void
-bfd_sym_print_constant_pool_entry (abfd, f, entry)
- bfd *abfd ATTRIBUTE_UNUSED;
- FILE *f;
- bfd_sym_constant_pool_entry *entry ATTRIBUTE_UNUSED;
+bfd_sym_print_constant_pool_entry (bfd *abfd ATTRIBUTE_UNUSED,
+ FILE *f,
+ bfd_sym_constant_pool_entry *entry ATTRIBUTE_UNUSED)
{
fprintf (f, "[UNIMPLEMENTED]");
}
unsigned char *
-bfd_sym_display_name_table_entry (abfd, f, entry)
- bfd *abfd;
- FILE *f;
- unsigned char *entry;
+bfd_sym_display_name_table_entry (bfd *abfd,
+ FILE *f,
+ unsigned char *entry)
{
unsigned long index;
unsigned long offset;
}
void
-bfd_sym_display_name_table (abfd, f)
- bfd *abfd;
- FILE *f;
+bfd_sym_display_name_table (bfd *abfd, FILE *f)
{
unsigned long name_table_len;
unsigned char *name_table, *name_table_end, *cur;
}
void
-bfd_sym_display_resources_table (abfd, f)
- bfd *abfd;
- FILE *f;
+bfd_sym_display_resources_table (bfd *abfd, FILE *f)
{
unsigned long i;
bfd_sym_resources_table_entry entry;
}
void
-bfd_sym_display_modules_table (abfd, f)
- bfd *abfd;
- FILE *f;
+bfd_sym_display_modules_table (bfd *abfd, FILE *f)
{
unsigned long i;
bfd_sym_modules_table_entry entry;
}
void
-bfd_sym_display_file_references_table (abfd, f)
- bfd *abfd;
- FILE *f;
+bfd_sym_display_file_references_table (bfd *abfd, FILE *f)
{
unsigned long i;
bfd_sym_file_references_table_entry entry;
}
void
-bfd_sym_display_contained_modules_table (abfd, f)
- bfd *abfd;
- FILE *f;
+bfd_sym_display_contained_modules_table (bfd *abfd, FILE *f)
{
unsigned long i;
bfd_sym_contained_modules_table_entry entry;
}
void
-bfd_sym_display_contained_variables_table (abfd, f)
- bfd *abfd;
- FILE *f;
+bfd_sym_display_contained_variables_table (bfd *abfd, FILE *f)
{
unsigned long i;
bfd_sym_contained_variables_table_entry entry;
}
void
-bfd_sym_display_contained_statements_table (abfd, f)
- bfd *abfd;
- FILE *f;
+bfd_sym_display_contained_statements_table (bfd *abfd, FILE *f)
{
unsigned long i;
bfd_sym_contained_statements_table_entry entry;
}
void
-bfd_sym_display_contained_labels_table (abfd, f)
- bfd *abfd;
- FILE *f;
+bfd_sym_display_contained_labels_table (bfd *abfd, FILE *f)
{
unsigned long i;
bfd_sym_contained_labels_table_entry entry;
}
void
-bfd_sym_display_contained_types_table (abfd, f)
- bfd *abfd;
- FILE *f;
+bfd_sym_display_contained_types_table (bfd *abfd, FILE *f)
{
unsigned long i;
bfd_sym_contained_types_table_entry entry;
}
void
-bfd_sym_display_file_references_index_table (abfd, f)
- bfd *abfd;
- FILE *f;
+bfd_sym_display_file_references_index_table (bfd *abfd, FILE *f)
{
unsigned long i;
bfd_sym_file_references_index_table_entry entry;
}
void
-bfd_sym_display_constant_pool (abfd, f)
- bfd *abfd;
- FILE *f;
+bfd_sym_display_constant_pool (bfd *abfd, FILE *f)
{
unsigned long i;
bfd_sym_constant_pool_entry entry;
}
void
-bfd_sym_display_type_information_table (abfd, f)
- bfd *abfd;
- FILE *f;
+bfd_sym_display_type_information_table (bfd *abfd, FILE *f)
{
unsigned long i;
bfd_sym_type_table_entry index;
}
int
-bfd_sym_scan (abfd, version, mdata)
- bfd *abfd;
- bfd_sym_version version;
- bfd_sym_data_struct *mdata;
+bfd_sym_scan (bfd *abfd, bfd_sym_version version, bfd_sym_data_struct *mdata)
{
asection *bfdsec;
const char *name = "symbols";
}
const bfd_target *
-bfd_sym_object_p (abfd)
- bfd *abfd;
+bfd_sym_object_p (bfd *abfd)
{
struct bfd_preserve preserve;
bfd_sym_version version = -1;
}
asymbol *
-bfd_sym_make_empty_symbol (abfd)
- bfd *abfd;
+bfd_sym_make_empty_symbol (bfd *abfd)
{
- return (asymbol *) bfd_alloc (abfd, sizeof (asymbol));
+ return bfd_alloc (abfd, sizeof (asymbol));
}
void
-bfd_sym_get_symbol_info (abfd, symbol, ret)
- bfd *abfd ATTRIBUTE_UNUSED;
- asymbol *symbol;
- symbol_info *ret;
+bfd_sym_get_symbol_info (bfd *abfd ATTRIBUTE_UNUSED, asymbol *symbol, symbol_info *ret)
{
bfd_symbol_info (symbol, ret);
}
long
-bfd_sym_get_symtab_upper_bound (abfd)
- bfd *abfd ATTRIBUTE_UNUSED;
+bfd_sym_get_symtab_upper_bound (bfd *abfd ATTRIBUTE_UNUSED)
{
return 0;
}
long
-bfd_sym_canonicalize_symtab (abfd, sym)
- bfd *abfd ATTRIBUTE_UNUSED;
- asymbol **sym ATTRIBUTE_UNUSED;
+bfd_sym_canonicalize_symtab (bfd *abfd ATTRIBUTE_UNUSED, asymbol **sym ATTRIBUTE_UNUSED)
{
return 0;
}
int
-bfd_sym_sizeof_headers (abfd, exec)
- bfd *abfd ATTRIBUTE_UNUSED;
- bfd_boolean exec ATTRIBUTE_UNUSED;
+bfd_sym_sizeof_headers (bfd *abfd ATTRIBUTE_UNUSED, bfd_boolean exec ATTRIBUTE_UNUSED)
{
return 0;
}
const bfd_target sym_vec =
{
- "sym", /* name */
- bfd_target_sym_flavour, /* flavour */
- BFD_ENDIAN_BIG, /* byteorder */
- BFD_ENDIAN_BIG, /* header_byteorder */
- (HAS_RELOC | EXEC_P | /* object flags */
+ "sym", /* Name. */
+ bfd_target_sym_flavour, /* Flavour. */
+ BFD_ENDIAN_BIG, /* Byteorder. */
+ BFD_ENDIAN_BIG, /* Header byteorder. */
+ (HAS_RELOC | EXEC_P | /* Object flags. */
HAS_LINENO | HAS_DEBUG |
HAS_SYMS | HAS_LOCALS | DYNAMIC | WP_TEXT | D_PAGED),
(SEC_ALLOC | SEC_LOAD | SEC_READONLY | SEC_CODE | SEC_DATA
- | SEC_ROM | SEC_HAS_CONTENTS), /* section_flags */
- 0, /* symbol_leading_char */
- ' ', /* ar_pad_char */
- 16, /* ar_max_namelen */
+ | SEC_ROM | SEC_HAS_CONTENTS), /* Section_flags. */
+ 0, /* Symbol_leading_char. */
+ ' ', /* AR_pad_char. */
+ 16, /* AR_max_namelen. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* data */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Data. */
bfd_getb64, bfd_getb_signed_64, bfd_putb64,
bfd_getb32, bfd_getb_signed_32, bfd_putb32,
- bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* hdrs */
- { /* bfd_check_format */
+ bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Hdrs. */
+ { /* bfd_check_format. */
_bfd_dummy_target,
- bfd_sym_object_p, /* bfd_check_format */
+ bfd_sym_object_p, /* bfd_check_format. */
_bfd_dummy_target,
_bfd_dummy_target,
},
- { /* bfd_set_format */
+ { /* bfd_set_format. */
bfd_false,
bfd_sym_mkobject,
bfd_false,
bfd_false,
},
- { /* bfd_write_contents */
+ { /* bfd_write_contents. */
bfd_false,
bfd_true,
bfd_false,
NULL
};
-
/* xSYM symbol-file support for BFD.
- Copyright 1999, 2000, 2001, 2002, 2003
+ Copyright 1999, 2000, 2001, 2002, 2003, 2005
Free Software Foundation, Inc.
This file is part of BFD, the Binary File Descriptor library.
typedef struct bfd_sym_data_struct bfd_sym_data_struct;
extern bfd_boolean bfd_sym_mkobject
- PARAMS ((bfd *));
+ (bfd *);
extern void bfd_sym_print_symbol
- PARAMS ((bfd *, PTR, asymbol *, bfd_print_symbol_type));
+ (bfd *, PTR, asymbol *, bfd_print_symbol_type);
extern bfd_boolean bfd_sym_valid
- PARAMS ((bfd *));
+ (bfd *);
extern unsigned char * bfd_sym_read_name_table
- PARAMS ((bfd *, bfd_sym_header_block *));
+ (bfd *, bfd_sym_header_block *);
extern void bfd_sym_parse_file_reference_v32
- PARAMS ((unsigned char *, size_t, bfd_sym_file_reference *));
+ (unsigned char *, size_t, bfd_sym_file_reference *);
extern void bfd_sym_parse_disk_table_v32
- PARAMS ((unsigned char *, size_t, bfd_sym_table_info *));
+ (unsigned char *, size_t, bfd_sym_table_info *);
extern void bfd_sym_parse_header_v32
- PARAMS ((unsigned char *, size_t, bfd_sym_header_block *));
+ (unsigned char *, size_t, bfd_sym_header_block *);
extern int bfd_sym_read_header_v32
- PARAMS ((bfd *, bfd_sym_header_block *));
+ (bfd *, bfd_sym_header_block *);
extern int bfd_sym_read_header_v34
- PARAMS ((bfd *, bfd_sym_header_block *));
+ (bfd *, bfd_sym_header_block *);
extern int bfd_sym_read_header
- PARAMS ((bfd *, bfd_sym_header_block *, bfd_sym_version));
+ (bfd *, bfd_sym_header_block *, bfd_sym_version);
extern int bfd_sym_read_version
- PARAMS ((bfd *, bfd_sym_version *));
+ (bfd *, bfd_sym_version *);
extern void bfd_sym_display_table_summary
- PARAMS ((FILE *, bfd_sym_table_info *, const char *));
+ (FILE *, bfd_sym_table_info *, const char *);
extern void bfd_sym_display_header
- PARAMS ((FILE *, bfd_sym_header_block *));
+ (FILE *, bfd_sym_header_block *);
extern void bfd_sym_parse_resources_table_entry_v32
- PARAMS ((unsigned char *, size_t, bfd_sym_resources_table_entry *));
+ (unsigned char *, size_t, bfd_sym_resources_table_entry *);
extern void bfd_sym_parse_modules_table_entry_v33
- PARAMS ((unsigned char *, size_t, bfd_sym_modules_table_entry *));
+ (unsigned char *, size_t, bfd_sym_modules_table_entry *);
extern void bfd_sym_parse_file_references_table_entry_v32
- PARAMS ((unsigned char *, size_t, bfd_sym_file_references_table_entry *));
+ (unsigned char *, size_t, bfd_sym_file_references_table_entry *);
extern void bfd_sym_parse_contained_modules_table_entry_v32
- PARAMS ((unsigned char *, size_t, bfd_sym_contained_modules_table_entry *));
+ (unsigned char *, size_t, bfd_sym_contained_modules_table_entry *);
extern void bfd_sym_parse_contained_variables_table_entry_v32
- PARAMS ((unsigned char *, size_t, bfd_sym_contained_variables_table_entry *));
+ (unsigned char *, size_t, bfd_sym_contained_variables_table_entry *);
extern void bfd_sym_parse_contained_statements_table_entry_v32
- PARAMS ((unsigned char *, size_t, bfd_sym_contained_statements_table_entry *));
+ (unsigned char *, size_t, bfd_sym_contained_statements_table_entry *);
extern void bfd_sym_parse_contained_labels_table_entry_v32
- PARAMS ((unsigned char *, size_t, bfd_sym_contained_labels_table_entry *));
+ (unsigned char *, size_t, bfd_sym_contained_labels_table_entry *);
extern void bfd_sym_parse_type_table_entry_v32
- PARAMS ((unsigned char *, size_t, bfd_sym_type_table_entry *));
+ (unsigned char *, size_t, bfd_sym_type_table_entry *);
extern int bfd_sym_fetch_resources_table_entry
- PARAMS ((bfd *, bfd_sym_resources_table_entry *, unsigned long));
+ (bfd *, bfd_sym_resources_table_entry *, unsigned long);
extern int bfd_sym_fetch_modules_table_entry
- PARAMS ((bfd *, bfd_sym_modules_table_entry *, unsigned long));
+ (bfd *, bfd_sym_modules_table_entry *, unsigned long);
extern int bfd_sym_fetch_file_references_table_entry
- PARAMS ((bfd *, bfd_sym_file_references_table_entry *, unsigned long));
+ (bfd *, bfd_sym_file_references_table_entry *, unsigned long);
extern int bfd_sym_fetch_contained_modules_table_entry
- PARAMS ((bfd *, bfd_sym_contained_modules_table_entry *, unsigned long));
+ (bfd *, bfd_sym_contained_modules_table_entry *, unsigned long);
extern int bfd_sym_fetch_contained_variables_table_entry
- PARAMS ((bfd *, bfd_sym_contained_variables_table_entry *, unsigned long));
+ (bfd *, bfd_sym_contained_variables_table_entry *, unsigned long);
extern int bfd_sym_fetch_contained_statements_table_entry
- PARAMS ((bfd *, bfd_sym_contained_statements_table_entry *, unsigned long));
+ (bfd *, bfd_sym_contained_statements_table_entry *, unsigned long);
extern int bfd_sym_fetch_contained_labels_table_entry
- PARAMS ((bfd *, bfd_sym_contained_labels_table_entry *, unsigned long));
+ (bfd *, bfd_sym_contained_labels_table_entry *, unsigned long);
extern int bfd_sym_fetch_contained_types_table_entry
- PARAMS ((bfd *, bfd_sym_contained_types_table_entry *, unsigned long));
+ (bfd *, bfd_sym_contained_types_table_entry *, unsigned long);
extern int bfd_sym_fetch_file_references_index_table_entry
- PARAMS ((bfd *, bfd_sym_file_references_index_table_entry *, unsigned long));
+ (bfd *, bfd_sym_file_references_index_table_entry *, unsigned long);
extern int bfd_sym_fetch_constant_pool_entry
- PARAMS ((bfd *, bfd_sym_constant_pool_entry *, unsigned long));
+ (bfd *, bfd_sym_constant_pool_entry *, unsigned long);
extern int bfd_sym_fetch_type_table_entry
- PARAMS ((bfd *, bfd_sym_type_table_entry *, unsigned long));
+ (bfd *, bfd_sym_type_table_entry *, unsigned long);
extern int bfd_sym_fetch_type_information_table_entry
- PARAMS ((bfd *, bfd_sym_type_information_table_entry *, unsigned long));
+ (bfd *, bfd_sym_type_information_table_entry *, unsigned long);
extern int bfd_sym_fetch_type_table_information
- PARAMS ((bfd *, bfd_sym_type_information_table_entry *, unsigned long));
+ (bfd *, bfd_sym_type_information_table_entry *, unsigned long);
extern const unsigned char * bfd_sym_symbol_name
- PARAMS ((bfd *, unsigned long));
+ (bfd *, unsigned long);
extern const unsigned char * bfd_sym_module_name
- PARAMS ((bfd *, unsigned long));
+ (bfd *, unsigned long);
extern const char * bfd_sym_unparse_storage_kind
- PARAMS ((enum bfd_sym_storage_kind));
+ (enum bfd_sym_storage_kind);
extern const char * bfd_sym_unparse_storage_class
- PARAMS ((enum bfd_sym_storage_class));
+ (enum bfd_sym_storage_class);
extern const char * bfd_sym_unparse_module_kind
- PARAMS ((enum bfd_sym_module_kind));
+ (enum bfd_sym_module_kind);
extern const char * bfd_sym_unparse_symbol_scope
- PARAMS ((enum bfd_sym_symbol_scope));
+ (enum bfd_sym_symbol_scope);
extern void bfd_sym_print_file_reference
- PARAMS ((bfd *, FILE *, bfd_sym_file_reference *));
+ (bfd *, FILE *, bfd_sym_file_reference *);
extern void bfd_sym_print_resources_table_entry
- PARAMS ((bfd *, FILE *, bfd_sym_resources_table_entry *));
+ (bfd *, FILE *, bfd_sym_resources_table_entry *);
extern void bfd_sym_print_modules_table_entry
- PARAMS ((bfd *, FILE *, bfd_sym_modules_table_entry *));
+ (bfd *, FILE *, bfd_sym_modules_table_entry *);
extern void bfd_sym_print_file_references_table_entry
- PARAMS ((bfd *, FILE *, bfd_sym_file_references_table_entry *));
+ (bfd *, FILE *, bfd_sym_file_references_table_entry *);
extern void bfd_sym_print_contained_modules_table_entry
- PARAMS ((bfd *, FILE *, bfd_sym_contained_modules_table_entry *));
+ (bfd *, FILE *, bfd_sym_contained_modules_table_entry *);
extern void bfd_sym_print_contained_variables_table_entry
- PARAMS ((bfd *, FILE *f, bfd_sym_contained_variables_table_entry *));
+ (bfd *, FILE *f, bfd_sym_contained_variables_table_entry *);
extern void bfd_sym_print_contained_statements_table_entry
- PARAMS ((bfd *, FILE *, bfd_sym_contained_statements_table_entry *));
+ (bfd *, FILE *, bfd_sym_contained_statements_table_entry *);
extern void bfd_sym_print_contained_labels_table_entry
- PARAMS ((bfd *, FILE *, bfd_sym_contained_labels_table_entry *));
+ (bfd *, FILE *, bfd_sym_contained_labels_table_entry *);
extern void bfd_sym_print_contained_types_table_entry
- PARAMS ((bfd *, FILE *, bfd_sym_contained_types_table_entry *));
+ (bfd *, FILE *, bfd_sym_contained_types_table_entry *);
extern const char * bfd_sym_type_operator_name
- PARAMS ((unsigned char));
+ (unsigned char);
extern const char * bfd_sym_type_basic_name
- PARAMS ((unsigned char));
+ (unsigned char);
extern int bfd_sym_fetch_long
- PARAMS ((unsigned char *, unsigned long, unsigned long, unsigned long *, long *));
+ (unsigned char *, unsigned long, unsigned long, unsigned long *, long *);
extern void bfd_sym_print_type_information
- PARAMS ((bfd *, FILE *, unsigned char *, unsigned long, unsigned long, unsigned long *));
+ (bfd *, FILE *, unsigned char *, unsigned long, unsigned long, unsigned long *);
extern void bfd_sym_print_type_information_table_entry
- PARAMS ((bfd *, FILE *, bfd_sym_type_information_table_entry *));
+ (bfd *, FILE *, bfd_sym_type_information_table_entry *);
extern void bfd_sym_print_file_references_index_table_entry
- PARAMS ((bfd *, FILE *, bfd_sym_file_references_index_table_entry *));
+ (bfd *, FILE *, bfd_sym_file_references_index_table_entry *);
extern void bfd_sym_print_constant_pool_entry
- PARAMS ((bfd *, FILE *, bfd_sym_constant_pool_entry *));
+ (bfd *, FILE *, bfd_sym_constant_pool_entry *);
extern unsigned char * bfd_sym_display_name_table_entry
- PARAMS ((bfd *, FILE *, unsigned char *));
+ (bfd *, FILE *, unsigned char *);
extern void bfd_sym_display_name_table
- PARAMS ((bfd *, FILE *));
+ (bfd *, FILE *);
extern void bfd_sym_display_resources_table
- PARAMS ((bfd *, FILE *));
+ (bfd *, FILE *);
extern void bfd_sym_display_modules_table
- PARAMS ((bfd *, FILE *));
+ (bfd *, FILE *);
extern void bfd_sym_display_file_references_table
- PARAMS ((bfd *, FILE *));
+ (bfd *, FILE *);
extern void bfd_sym_display_contained_modules_table
- PARAMS ((bfd *, FILE *));
+ (bfd *, FILE *);
extern void bfd_sym_display_contained_variables_table
- PARAMS ((bfd *, FILE *));
+ (bfd *, FILE *);
extern void bfd_sym_display_contained_statements_table
- PARAMS ((bfd *, FILE *));
+ (bfd *, FILE *);
extern void bfd_sym_display_contained_labels_table
- PARAMS ((bfd *, FILE *));
+ (bfd *, FILE *);
extern void bfd_sym_display_contained_types_table
- PARAMS ((bfd *, FILE *));
+ (bfd *, FILE *);
extern void bfd_sym_display_file_references_index_table
- PARAMS ((bfd *, FILE *));
+ (bfd *, FILE *);
extern void bfd_sym_display_constant_pool
- PARAMS ((bfd *, FILE *));
+ (bfd *, FILE *);
extern void bfd_sym_display_type_information_table
- PARAMS ((bfd *, FILE *));
+ (bfd *, FILE *);
extern int bfd_sym_scan
- PARAMS ((bfd *, bfd_sym_version, bfd_sym_data_struct *));
+ (bfd *, bfd_sym_version, bfd_sym_data_struct *);
extern const bfd_target * bfd_sym_object_p
- PARAMS ((bfd *));
+ (bfd *);
extern asymbol * bfd_sym_make_empty_symbol
- PARAMS ((bfd *));
+ (bfd *);
extern void bfd_sym_get_symbol_info
- PARAMS ((bfd *, asymbol *, symbol_info *));
+ (bfd *, asymbol *, symbol_info *);
extern long bfd_sym_get_symtab_upper_bound
- PARAMS ((bfd *));
+ (bfd *);
extern long bfd_sym_canonicalize_symtab
- PARAMS ((bfd *, asymbol **));
+ (bfd *, asymbol **);
extern int bfd_sym_sizeof_headers
- PARAMS ((bfd *, bfd_boolean));
+ (bfd *, bfd_boolean);
#endif /* __xSYM_H__ */