* emultempl/aix.em: Include ldctor.h.

(gld${EMULATION_NAME}_after_open): New static function.
	(gld${EMULATION_NAME}_before_allocation): Call find_relocs.
	(gld${EMULATION_NAME}_find_relocs): New static function.
	(gld${EMULATION_NAME}_find_exp_assignment): New static function.
	(ld_${EMULATION_NAME}_emulation): Use new after_open function.
	* scripttempl/aix.sc: Use CONSTRUCTORS in .data.
	* ldctor.c (struct set_info): Move definition into ldctor.h.
	(struct set_element): Likewise.
	(sets): Make non-static.
	(ldctor_add_set_entry): Add name parameter.  Save it in the new
	set element.
	(ldctor_build_sets): Avoid being called twice.  Pass set element
	name to lang_add_reloc.
	* ldctor.h (struct set_info): Move definition here from ldctor.c.
	(struct set_element): Likewise.  Add new field name.
	(sets): Declare.
	(ldctor_add_set_entry): Declare new name parameter.
	* ldwrite.c (build_link_order): Don't insist that either name or
	section be NULL in a lang_reloc_statement.
	* ldmain.c (add_to_set): Pass NULL to ldctor_add_new_set_entry for
	new name parameter.
	(constructor_callback): Pass name to ldctor_add_new_set_entry for
	new name parameter.
This commit is contained in:
Ian Lance Taylor 1995-10-27 22:21:43 +00:00
parent 2d7de17d61
commit cf79773cb1
2 changed files with 153 additions and 1 deletions

View File

@ -1,3 +1,32 @@
Fri Oct 27 17:59:09 1995 Ian Lance Taylor <ian@cygnus.com>
* emultempl/aix.em: Include ldctor.h.
(gld${EMULATION_NAME}_after_open): New static function.
(gld${EMULATION_NAME}_before_allocation): Call find_relocs.
(gld${EMULATION_NAME}_find_relocs): New static function.
(gld${EMULATION_NAME}_find_exp_assignment): New static function.
(ld_${EMULATION_NAME}_emulation): Use new after_open function.
* scripttempl/aix.sc: Use CONSTRUCTORS in .data.
* ldctor.c (struct set_info): Move definition into ldctor.h.
(struct set_element): Likewise.
(sets): Make non-static.
(ldctor_add_set_entry): Add name parameter. Save it in the new
set element.
(ldctor_build_sets): Avoid being called twice. Pass set element
name to lang_add_reloc.
* ldctor.h (struct set_info): Move definition here from ldctor.c.
(struct set_element): Likewise. Add new field name.
(sets): Declare.
(ldctor_add_set_entry): Declare new name parameter.
* ldwrite.c (build_link_order): Don't insist that either name or
section be NULL in a lang_reloc_statement.
* ldmain.c (add_to_set): Pass NULL to ldctor_add_new_set_entry for
new name parameter.
(constructor_callback): Pass name to ldctor_add_new_set_entry for
new name parameter.
* ldmisc.c (demangle): Fix indentation. Remove a leading period.
Thu Oct 26 22:22:49 1995 Stan Shebs <shebs@andros.cygnus.com>
* mpw-config.in: Add PowerMac target support, generate config.h.

View File

@ -41,12 +41,17 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
#include "ldmisc.h"
#include "ldexp.h"
#include "ldlang.h"
#include "ldctor.h"
static void gld${EMULATION_NAME}_before_parse PARAMS ((void));
static int gld${EMULATION_NAME}_parse_args PARAMS ((int, char **));
static void gld${EMULATION_NAME}_after_open PARAMS ((void));
static void gld${EMULATION_NAME}_before_allocation PARAMS ((void));
static void gld${EMULATION_NAME}_read_file PARAMS ((const char *, boolean));
static void gld${EMULATION_NAME}_free PARAMS ((PTR));
static void gld${EMULATION_NAME}_find_relocs
PARAMS ((lang_statement_union_type *));
static void gld${EMULATION_NAME}_find_exp_assignment PARAMS ((etree_type *));
static char *gld${EMULATION_NAME}_get_script PARAMS ((int *isfile));
/* The file alignment required for each section. */
@ -313,6 +318,48 @@ gld${EMULATION_NAME}_parse_args (argc, argv)
return 1;
}
/* This is called after the input files have been opened. */
static void
gld${EMULATION_NAME}_after_open ()
{
boolean r;
struct set_info *p;
/* Call ldctor_build_sets, after pretending that this is a
relocateable link. We do this because AIX requires relocation
entries for all references to symbols, even in a final
executable. */
r = link_info.relocateable;
link_info.relocateable = true;
ldctor_build_sets ();
link_info.relocateable = r;
/* For each set, record the size, so that the XCOFF backend can
output the correct csect length. */
for (p = sets; p != (struct set_info *) NULL; p = p->next)
{
bfd_size_type size;
/* If the symbol is defined, we may have been invoked from
collect, and the sets may already have been built, so we do
not do anything. */
if (p->h->type == bfd_link_hash_defined
|| p->h->type == bfd_link_hash_defweak)
continue;
if (p->reloc != BFD_RELOC_CTOR)
{
/* Handle this if we need to. */
abort ();
}
size = (p->count + 2) * 4;
if (! bfd_xcoff_link_record_set (output_bfd, &link_info, p->h, size))
einfo ("%F%P: bfd_xcoff_link_record_set failed: %E\n");
}
}
/* This is called after the sections have been attached to output
sections, but before any sizes or addresses have been set. */
@ -328,6 +375,12 @@ gld${EMULATION_NAME}_before_allocation ()
for (fl = export_files; fl != NULL; fl = fl->next)
gld${EMULATION_NAME}_read_file (fl->name, false);
/* Track down all relocations called for by the linker script (these
are typically constructor/destructor entries created by
CONSTRUCTORS) and let the backend know it will need to create
.loader relocs for them. */
lang_for_each_statement (gld${EMULATION_NAME}_find_relocs);
/* We need to build LIBPATH from the -L arguments. If any -rpath
arguments were used, though, we use -rpath instead, as a GNU
extension. */
@ -592,6 +645,76 @@ gld${EMULATION_NAME}_free (p)
free (p);
}
/* This is called by the before_allocation routine via
lang_for_each_statement. It looks for relocations and assignments
to symbols. */
static void
gld${EMULATION_NAME}_find_relocs (s)
lang_statement_union_type *s;
{
if (s->header.type == lang_reloc_statement_enum)
{
lang_reloc_statement_type *rs;
rs = &s->reloc_statement;
if (rs->name == NULL)
einfo ("%F%P: only relocations against symbols are permitted\n");
if (! bfd_xcoff_link_count_reloc (output_bfd, &link_info, rs->name))
einfo ("%F%P: bfd_xcoff_link_count_reloc failed: %E\n");
}
if (s->header.type == lang_assignment_statement_enum)
gld${EMULATION_NAME}_find_exp_assignment (s->assignment_statement.exp);
}
/* Look through an expression for an assignment statement. */
static void
gld${EMULATION_NAME}_find_exp_assignment (exp)
etree_type *exp;
{
struct bfd_link_hash_entry *h;
switch (exp->type.node_class)
{
case etree_provide:
h = bfd_link_hash_lookup (link_info.hash, exp->assign.dst,
false, false, false);
if (h == NULL)
break;
/* Fall through. */
case etree_assign:
if (strcmp (exp->assign.dst, ".") != 0)
{
if (! bfd_xcoff_record_link_assignment (output_bfd, &link_info,
exp->assign.dst))
einfo ("%P%F: failed to record assignment to %s: %E\n",
exp->assign.dst);
}
gld${EMULATION_NAME}_find_exp_assignment (exp->assign.src);
break;
case etree_binary:
gld${EMULATION_NAME}_find_exp_assignment (exp->binary.lhs);
gld${EMULATION_NAME}_find_exp_assignment (exp->binary.rhs);
break;
case etree_trinary:
gld${EMULATION_NAME}_find_exp_assignment (exp->trinary.cond);
gld${EMULATION_NAME}_find_exp_assignment (exp->trinary.lhs);
gld${EMULATION_NAME}_find_exp_assignment (exp->trinary.rhs);
break;
case etree_unary:
gld${EMULATION_NAME}_find_exp_assignment (exp->unary.child);
break;
default:
break;
}
}
static char *
gld${EMULATION_NAME}_get_script(isfile)
int *isfile;
@ -652,7 +775,7 @@ struct ld_emulation_xfer_struct ld_${EMULATION_NAME}_emulation =
syslib_default,
hll_default,
after_parse_default,
after_open_default,
gld${EMULATION_NAME}_after_open,
after_allocation_default,
set_output_arch_default,
ldemul_default_target,