# This shell script emits a C file. -*- C -*-
#   Copyright 2001, 2002, 2003, 2004, 2006, 2007, 2008
#   Free Software Foundation, Inc.
#
# This file is part of the GNU Binutils.
#
# 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 3 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., 51 Franklin Street - Fifth Floor, Boston,
# MA 02110-1301, USA.
#

# This file is sourced from generic.em.

fragment <<EOF
/* Need to have this macro defined before mmix-elfnmmo, which uses the
   name for the before_allocation function, defined in ldemul.c (for
   the mmo "emulation") or in elf32.em (for the elf64mmix
   "emulation").  */
#define gldmmo_before_allocation before_allocation_default

/* We include this header *not* because we expect to handle ELF here
   but because we re-use the map_segments function in elf-generic.em,
   a file which is rightly somewhat ELF-centric.  But this is only to
   get a weird testcase right; ld-mmix/bpo-22, forcing ELF to be
   output from the mmo emulation: -m mmo --oformat elf64-mmix!  */
#include "elf-bfd.h"
EOF

source_em ${srcdir}/emultempl/elf-generic.em
source_em ${srcdir}/emultempl/mmix-elfnmmo.em

fragment <<EOF

/* Place an orphan section.  We use this to put random SEC_CODE or
   SEC_READONLY sections right after MMO_TEXT_SECTION_NAME.  Much borrowed
   from elf32.em.  */

static lang_output_section_statement_type *
mmo_place_orphan (asection *s,
		  const char *secname,
		  int constraint ATTRIBUTE_UNUSED)
{
  static struct orphan_save hold_text =
    {
      MMO_TEXT_SECTION_NAME,
      SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD | SEC_READONLY | SEC_CODE,
      0, 0, 0, 0
    };
  struct orphan_save *place;
  lang_output_section_statement_type *after;
  lang_output_section_statement_type *os;

  /* We have nothing to say for anything other than a final link.  */
  if (link_info.relocatable
      || (s->flags & (SEC_EXCLUDE | SEC_LOAD)) != SEC_LOAD)
    return NULL;

  /* Only care for sections we're going to load.  */
  os = lang_output_section_find (secname);

  /* We have an output section by this name.  Place the section inside it
     (regardless of whether the linker script lists it as input).  */
  if (os != NULL)
    {
      lang_add_section (&os->children, s, os);
      return os;
    }

  /* If this section does not have .text-type section flags or there's no
     MMO_TEXT_SECTION_NAME, we don't have anything to say.  */
  if ((s->flags & (SEC_CODE | SEC_READONLY)) == 0)
    return NULL;

  if (hold_text.os == NULL)
    hold_text.os = lang_output_section_find (hold_text.name);

  place = &hold_text;
  if (hold_text.os != NULL)
    after = hold_text.os;
  else
    after = &lang_output_section_statement.head->output_section_statement;

  /* If there's an output section by this name, we'll use it, regardless
     of section flags, in contrast to what's done in elf32.em.  */
  os = lang_insert_orphan (s, secname, 0, after, place, NULL, NULL);

  /* We need an output section for .text as a root, so if there was none
     (might happen with a peculiar linker script such as in "map
     addresses", map-address.exp), we grab the output section created
     above.  */
  if (hold_text.os == NULL)
    hold_text.os = os;

  return os;
}

/* Remove the spurious settings of SEC_RELOC that make it to the output at
   link time.  We are as confused as elflink.h:elf_bfd_final_link, and
   paper over the bug similarly.  */

static void
mmo_wipe_sec_reloc_flag (bfd *abfd, asection *sec, void *ptr ATTRIBUTE_UNUSED)
{
  bfd_set_section_flags (abfd, sec,
			 bfd_get_section_flags (abfd, sec) & ~SEC_RELOC);
}

/* Iterate with bfd_map_over_sections over mmo_wipe_sec_reloc_flag... */

static void
mmo_finish (void)
{
  bfd_map_over_sections (link_info.output_bfd, mmo_wipe_sec_reloc_flag, NULL);
  gld${EMULATION_NAME}_map_segments (FALSE);
  finish_default ();
}

/* To get on-demand global register allocation right, we need to parse the
   relocs, like what happens when linking to ELF.  It needs to be done
   before all input sections are supposed to be present.  When linking to
   ELF, it's done when reading symbols.  When linking to mmo, we do it
   when all input files are seen, which is equivalent.  */

static void
mmo_after_open (void)
{
  /* When there's a mismatch between the output format and the emulation
     (using weird combinations like "-m mmo --oformat elf64-mmix" for
     example), we'd count relocs twice because they'd also be counted
     along the usual route for ELF-only linking, which would lead to an
     internal accounting error.  */
  if (bfd_get_flavour (link_info.output_bfd) != bfd_target_elf_flavour)
    {
      LANG_FOR_EACH_INPUT_STATEMENT (is)
	{
	  if (bfd_get_flavour (is->the_bfd) == bfd_target_elf_flavour
	      && !_bfd_mmix_check_all_relocs (is->the_bfd, &link_info))
	    einfo ("%X%P: Internal problems scanning %B after opening it",
		   is->the_bfd);
	}
    }
}
EOF

LDEMUL_PLACE_ORPHAN=mmo_place_orphan
LDEMUL_FINISH=mmo_finish
LDEMUL_AFTER_OPEN=mmo_after_open
