Home | History | Annotate | Download | only in emultempl
      1 # This shell script emits a C file. -*- C -*-
      2 #   Copyright (C) 2001-2016 Free Software Foundation, Inc.
      3 #
      4 # This file is part of the GNU Binutils.
      5 #
      6 # This program is free software; you can redistribute it and/or modify
      7 # it under the terms of the GNU General Public License as published by
      8 # the Free Software Foundation; either version 3 of the License, or
      9 # (at your option) any later version.
     10 #
     11 # This program is distributed in the hope that it will be useful,
     12 # but WITHOUT ANY WARRANTY; without even the implied warranty of
     13 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
     14 # GNU General Public License for more details.
     15 #
     16 # You should have received a copy of the GNU General Public License
     17 # along with this program; if not, write to the Free Software
     18 # Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
     19 # MA 02110-1301, USA.
     20 #
     21 
     22 # This file is sourced from generic.em.
     23 
     24 fragment <<EOF
     25 /* Need to have this macro defined before mmix-elfnmmo, which uses the
     26    name for the before_allocation function, defined in ldemul.c (for
     27    the mmo "emulation") or in elf32.em (for the elf64mmix
     28    "emulation").  */
     29 #define gldmmo_before_allocation before_allocation_default
     30 
     31 /* We include this header *not* because we expect to handle ELF here
     32    but because we re-use the map_segments function in elf-generic.em,
     33    a file which is rightly somewhat ELF-centric.  But this is only to
     34    get a weird testcase right; ld-mmix/bpo-22, forcing ELF to be
     35    output from the mmo emulation: -m mmo --oformat elf64-mmix!  */
     36 #include "elf-bfd.h"
     37 
     38 static void gld${EMULATION_NAME}_after_allocation (void);
     39 EOF
     40 
     41 source_em ${srcdir}/emultempl/elf-generic.em
     42 source_em ${srcdir}/emultempl/mmix-elfnmmo.em
     43 
     44 fragment <<EOF
     45 
     46 /* Place an orphan section.  We use this to put random SEC_CODE or
     47    SEC_READONLY sections right after MMO_TEXT_SECTION_NAME.  Much borrowed
     48    from elf32.em.  */
     49 
     50 static lang_output_section_statement_type *
     51 mmo_place_orphan (asection *s,
     52 		  const char *secname,
     53 		  int constraint ATTRIBUTE_UNUSED)
     54 {
     55   static struct
     56   {
     57     flagword nonzero_flags;
     58     struct orphan_save orphansave;
     59   } holds[] =
     60       {
     61 	{
     62 	  SEC_CODE | SEC_READONLY,
     63 	  {
     64 	    MMO_TEXT_SECTION_NAME,
     65 	    SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD | SEC_READONLY | SEC_CODE,
     66 	    0, 0, 0, 0
     67 	  }
     68 	},
     69 	{
     70 	  SEC_LOAD | SEC_DATA,
     71 	  {
     72 	    MMO_DATA_SECTION_NAME,
     73 	    SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD | SEC_DATA,
     74 	    0, 0, 0, 0
     75 	  }
     76 	},
     77 	{
     78 	  SEC_ALLOC,
     79 	  {
     80 	    ".bss",
     81 	    SEC_ALLOC,
     82 	    0, 0, 0, 0
     83 	  }
     84 	}
     85       };
     86 
     87   struct orphan_save *place = NULL;
     88   lang_output_section_statement_type *after;
     89   lang_output_section_statement_type *os;
     90   size_t i;
     91   flagword flags;
     92   asection *nexts;
     93 
     94   /* We have nothing to say for anything other than a final link or
     95      for sections that are excluded.  */
     96   if (bfd_link_relocatable (&link_info)
     97       || (s->flags & SEC_EXCLUDE) != 0)
     98     return NULL;
     99 
    100   os = lang_output_section_find (secname);
    101 
    102   /* We have an output section by this name.  Place the section inside it
    103      (regardless of whether the linker script lists it as input).  */
    104   if (os != NULL)
    105     {
    106       lang_add_section (&os->children, s, NULL, os);
    107       return os;
    108     }
    109 
    110   flags = s->flags;
    111   if (!bfd_link_relocatable (&link_info))
    112     {
    113       nexts = s;
    114       while ((nexts = bfd_get_next_section_by_name (nexts->owner, nexts))
    115 	     != NULL)
    116 	if (nexts->output_section == NULL
    117 	    && (nexts->flags & SEC_EXCLUDE) == 0
    118 	    && ((nexts->flags ^ flags) & (SEC_LOAD | SEC_ALLOC)) == 0
    119 	    && (nexts->owner->flags & DYNAMIC) == 0
    120 	    && nexts->owner->usrdata != NULL
    121 	    && !(((lang_input_statement_type *) nexts->owner->usrdata)
    122 		 ->flags.just_syms))
    123 	  flags = (((flags ^ SEC_READONLY) | (nexts->flags ^ SEC_READONLY))
    124 		   ^ SEC_READONLY);
    125     }
    126 
    127   /* Check for matching section type flags for sections we care about.
    128      A section without contents can have SEC_LOAD == 0, but we still
    129      want it attached to a sane section so the symbols appear as
    130      expected.  */
    131 
    132   if ((flags & (SEC_ALLOC | SEC_READONLY)) != SEC_READONLY)
    133     for (i = 0; i < sizeof (holds) / sizeof (holds[0]); i++)
    134       if ((flags & holds[i].nonzero_flags) != 0)
    135 	{
    136 	  place = &holds[i].orphansave;
    137 	  if (place->os == NULL)
    138 	    place->os = lang_output_section_find (place->name);
    139 	  break;
    140 	}
    141 
    142   if (place == NULL)
    143     {
    144       /* For other combinations, we have to give up, except we make
    145 	 sure not to place the orphan section after the
    146 	 linker-generated register section; that'd make it continue
    147 	 the reg section and we never want that to happen for orphan
    148 	 sections.  */
    149       lang_output_section_statement_type *before;
    150       lang_output_section_statement_type *lookup;
    151       static struct orphan_save hold_nonreg =
    152 	{
    153 	  NULL,
    154 	  SEC_READONLY,
    155 	  0, 0, 0, 0
    156 	};
    157 
    158       if (hold_nonreg.os == NULL)
    159 	{
    160 	  before = lang_output_section_find (MMIX_REG_CONTENTS_SECTION_NAME);
    161 
    162 	  /* If we have no such section, all fine; we don't care where
    163 	     it's placed.  */
    164 	  if (before == NULL)
    165 	    return NULL;
    166 
    167 	  /* We have to find the oss before this one, so we can use that as
    168 	     "after".  */
    169 	  for (lookup = &lang_output_section_statement.head->output_section_statement;
    170 	       lookup != NULL && lookup->next != before;
    171 	       lookup = lookup->next)
    172 	    ;
    173 
    174 	  hold_nonreg.os = lookup;
    175 	}
    176 
    177       place = &hold_nonreg;
    178     }
    179 
    180   after = place->os;
    181   if (after == NULL)
    182     return NULL;
    183 
    184   /* If there's an output section by *this* name, we'll use it, regardless
    185      of actual section flags, in contrast to what's done in elf32.em.  */
    186   os = lang_insert_orphan (s, secname, 0, after, place, NULL, NULL);
    187 
    188   return os;
    189 }
    190 
    191 /* Remove the spurious settings of SEC_RELOC that make it to the output at
    192    link time.  We are as confused as elflink.h:elf_bfd_final_link, and
    193    paper over the bug similarly.  */
    194 
    195 static void
    196 mmo_wipe_sec_reloc_flag (bfd *abfd, asection *sec, void *ptr ATTRIBUTE_UNUSED)
    197 {
    198   bfd_set_section_flags (abfd, sec,
    199 			 bfd_get_section_flags (abfd, sec) & ~SEC_RELOC);
    200 }
    201 
    202 /* Iterate with bfd_map_over_sections over mmo_wipe_sec_reloc_flag... */
    203 
    204 static void
    205 gld${EMULATION_NAME}_after_allocation (void)
    206 {
    207   bfd_map_over_sections (link_info.output_bfd, mmo_wipe_sec_reloc_flag, NULL);
    208   gld${EMULATION_NAME}_map_segments (FALSE);
    209 }
    210 
    212 /* To get on-demand global register allocation right, we need to parse the
    213    relocs, like what happens when linking to ELF.  It needs to be done
    214    before all input sections are supposed to be present.  When linking to
    215    ELF, it's done when reading symbols.  When linking to mmo, we do it
    216    when all input files are seen, which is equivalent.  */
    217 
    218 static void
    219 mmo_after_open (void)
    220 {
    221   /* When there's a mismatch between the output format and the emulation
    222      (using weird combinations like "-m mmo --oformat elf64-mmix" for
    223      example), we'd count relocs twice because they'd also be counted
    224      along the usual route for ELF-only linking, which would lead to an
    225      internal accounting error.  */
    226   if (bfd_get_flavour (link_info.output_bfd) != bfd_target_elf_flavour)
    227     {
    228       LANG_FOR_EACH_INPUT_STATEMENT (is)
    229 	{
    230 	  if (bfd_get_flavour (is->the_bfd) == bfd_target_elf_flavour
    231 	      && !_bfd_mmix_check_all_relocs (is->the_bfd, &link_info))
    232 	    einfo ("%X%P: Internal problems scanning %B after opening it",
    233 		   is->the_bfd);
    234 	}
    235     }
    236   after_open_default ();
    237 }
    238 EOF
    239 
    240 LDEMUL_PLACE_ORPHAN=mmo_place_orphan
    241 LDEMUL_AFTER_OPEN=mmo_after_open
    242