* xcofflink.c: Numerous changes to get closer to a working XCOFF

linker.
	* libcoff-in.h (struct xcoff_tdata): Add full_aouthdr,
	toc_section, and entry_section fields.
	(struct xcoff_section_tdata): Remove ldrel_count field.
	* libcoff.h: Rebuild.
	* coffcode.h (coff_mkobject_hook): Initialize new xcoff_data
	fields.
	(coff_compute_section_file_positions): If RS6000COFF_C, generate
	full a.out header if full_aouthdr is set in xcoff_data.
	(coff_write_object_contents): Likewise.  Set o_snentry and o_sntoc
	based on sections stored in xcoff_data.
	* coff-rs6000.c (xcoff_copy_private_bfd_data): Copy new xcoff_data
	fields.
	* coffgen.c (coff_get_symbol_info): If fix_value is set, fix the
	value stored in ret rather than returning a pointer value.
This commit is contained in:
Ian Lance Taylor
1995-10-26 18:25:13 +00:00
parent 328e5a48e8
commit 867d923d18
7 changed files with 466 additions and 183 deletions

View File

@@ -1002,7 +1002,18 @@ coff_mkobject_hook (abfd, filehdr, aouthdr)
struct xcoff_tdata *xcoff;
xcoff = xcoff_data (abfd);
xcoff->full_aouthdr = true;
xcoff->toc = internal_a->o_toc;
if (internal_a->o_sntoc == 0)
xcoff->toc_section = NULL;
else
xcoff->toc_section =
coff_section_from_bfd_index (abfd, internal_a->o_sntoc);
if (internal_a->o_snentry == 0)
xcoff->entry_section = NULL;
else
xcoff->entry_section =
coff_section_from_bfd_index (abfd, internal_a->o_snentry);
xcoff->text_align_power = internal_a->o_algntext;
xcoff->data_align_power = internal_a->o_algndata;
xcoff->modtype = internal_a->o_modtype;
@@ -1764,6 +1775,8 @@ coff_compute_section_file_positions (abfd)
if (abfd->flags & EXEC_P)
sofar += AOUTSZ;
#ifdef RS6000COFF_C
else if (xcoff_data (abfd)->full_aouthdr)
sofar += AOUTSZ;
else
sofar += SMALL_AOUTSZ;
#endif
@@ -2003,7 +2016,10 @@ coff_write_object_contents (abfd)
{
scn_base = FILHSZ;
#ifdef RS6000COFF_C
scn_base += SMALL_AOUTSZ;
if (xcoff_data (abfd)->full_aouthdr)
scn_base += AOUTSZ;
else
scn_base += SMALL_AOUTSZ;
#endif
}
@@ -2135,8 +2151,10 @@ coff_write_object_contents (abfd)
{
internal_f.f_opthdr = 0;
#ifdef RS6000COFF_C
/* XCOFF seems to always write at least a small a.out header. */
internal_f.f_opthdr = SMALL_AOUTSZ;
if (xcoff_data (abfd)->full_aouthdr)
internal_f.f_opthdr = AOUTSZ;
else
internal_f.f_opthdr = SMALL_AOUTSZ;
#endif
}
@@ -2311,22 +2329,20 @@ coff_write_object_contents (abfd)
internal_f.f_nsyms = obj_raw_syment_count (abfd);
#ifdef RS6000COFF_C
if ((abfd->flags & EXEC_P) != 0)
if (xcoff_data (abfd)->full_aouthdr)
{
bfd_vma entry, toc;
bfd_vma toc;
asection *loader_sec;
entry = bfd_get_start_address (abfd);
if (text_sec != NULL
&& entry >= text_sec->vma
&& entry < text_sec->vma + bfd_section_size (abfd, text_sec))
internal_a.o_snentry = text_sec->target_index;
else if (data_sec != NULL
&& entry >= data_sec->vma
&& entry < data_sec->vma + bfd_section_size (abfd, data_sec))
internal_a.o_snentry = data_sec->target_index;
if (xcoff_data (abfd)->entry_section != NULL)
internal_a.o_snentry = xcoff_data (abfd)->entry_section->target_index;
else
internal_a.o_snentry = 0;
{
internal_a.o_snentry = 0;
if (internal_a.entry == 0)
internal_a.entry = (bfd_vma) -1;
}
if (text_sec != NULL)
{
internal_a.o_sntext = text_sec->target_index;
@@ -2359,16 +2375,10 @@ coff_write_object_contents (abfd)
toc = xcoff_data (abfd)->toc;
internal_a.o_toc = toc;
if (text_sec != NULL
&& toc >= text_sec->vma
&& toc < text_sec->vma + bfd_section_size (abfd, text_sec))
internal_a.o_sntoc = text_sec->target_index;
else if (data_sec != NULL
&& toc >= data_sec->vma
&& toc < data_sec->vma + bfd_section_size (abfd, data_sec))
internal_a.o_sntoc = data_sec->target_index;
else
if (xcoff_data (abfd)->toc_section == NULL)
internal_a.o_sntoc = 0;
else
internal_a.o_sntoc = xcoff_data (abfd)->toc_section->target_index;
internal_a.o_modtype = xcoff_data (abfd)->modtype;
if (xcoff_data (abfd)->cputype != -1)
@@ -2415,9 +2425,15 @@ coff_write_object_contents (abfd)
else
{
AOUTHDR buff;
size_t size;
/* XCOFF seems to always write at least a small a.out header. */
coff_swap_aouthdr_out (abfd, (PTR) &internal_a, (PTR) &buff);
if (bfd_write ((PTR) &buff, 1, SMALL_AOUTSZ, abfd) != SMALL_AOUTSZ)
if (xcoff_data (abfd)->full_aouthdr)
size = AOUTSZ;
else
size = SMALL_AOUTSZ;
if (bfd_write ((PTR) &buff, 1, size, abfd) != size)
return false;
}
#endif