Home | History | Annotate | Line # | Download | only in bfd
elf32-spu.c revision 1.1.1.11
      1       1.1     skrll /* SPU specific support for 32-bit ELF
      2       1.1     skrll 
      3  1.1.1.11  christos    Copyright (C) 2006-2025 Free Software Foundation, Inc.
      4       1.1     skrll 
      5       1.1     skrll    This file is part of BFD, the Binary File Descriptor library.
      6       1.1     skrll 
      7       1.1     skrll    This program is free software; you can redistribute it and/or modify
      8       1.1     skrll    it under the terms of the GNU General Public License as published by
      9       1.1     skrll    the Free Software Foundation; either version 3 of the License, or
     10       1.1     skrll    (at your option) any later version.
     11       1.1     skrll 
     12       1.1     skrll    This program is distributed in the hope that it will be useful,
     13       1.1     skrll    but WITHOUT ANY WARRANTY; without even the implied warranty of
     14       1.1     skrll    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
     15       1.1     skrll    GNU General Public License for more details.
     16       1.1     skrll 
     17       1.1     skrll    You should have received a copy of the GNU General Public License along
     18       1.1     skrll    with this program; if not, write to the Free Software Foundation, Inc.,
     19       1.1     skrll    51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA.  */
     20       1.1     skrll 
     21       1.1     skrll #include "sysdep.h"
     22       1.1     skrll #include "libiberty.h"
     23       1.1     skrll #include "bfd.h"
     24       1.1     skrll #include "bfdlink.h"
     25       1.1     skrll #include "libbfd.h"
     26       1.1     skrll #include "elf-bfd.h"
     27       1.1     skrll #include "elf/spu.h"
     28       1.1     skrll #include "elf32-spu.h"
     29       1.1     skrll 
     30   1.1.1.8  christos /* All users of this file have bfd_octets_per_byte (abfd, sec) == 1.  */
     31   1.1.1.8  christos #define OCTETS_PER_BYTE(ABFD, SEC) 1
     32   1.1.1.8  christos 
     33       1.1     skrll /* We use RELA style relocs.  Don't define USE_REL.  */
     34       1.1     skrll 
     35       1.1     skrll static bfd_reloc_status_type spu_elf_rel9 (bfd *, arelent *, asymbol *,
     36       1.1     skrll 					   void *, asection *,
     37       1.1     skrll 					   bfd *, char **);
     38       1.1     skrll 
     39       1.1     skrll /* Values of type 'enum elf_spu_reloc_type' are used to index this
     40       1.1     skrll    array, so it must be declared in the order of that type.  */
     41       1.1     skrll 
     42       1.1     skrll static reloc_howto_type elf_howto_table[] = {
     43   1.1.1.9  christos   HOWTO (R_SPU_NONE,	   0, 0,  0, false,  0, complain_overflow_dont,
     44       1.1     skrll 	 bfd_elf_generic_reloc, "SPU_NONE",
     45   1.1.1.9  christos 	 false, 0, 0x00000000, false),
     46   1.1.1.9  christos   HOWTO (R_SPU_ADDR10,	   4, 4, 10, false, 14, complain_overflow_bitfield,
     47       1.1     skrll 	 bfd_elf_generic_reloc, "SPU_ADDR10",
     48   1.1.1.9  christos 	 false, 0, 0x00ffc000, false),
     49   1.1.1.9  christos   HOWTO (R_SPU_ADDR16,	   2, 4, 16, false,  7, complain_overflow_bitfield,
     50       1.1     skrll 	 bfd_elf_generic_reloc, "SPU_ADDR16",
     51   1.1.1.9  christos 	 false, 0, 0x007fff80, false),
     52   1.1.1.9  christos   HOWTO (R_SPU_ADDR16_HI, 16, 4, 16, false,  7, complain_overflow_bitfield,
     53       1.1     skrll 	 bfd_elf_generic_reloc, "SPU_ADDR16_HI",
     54   1.1.1.9  christos 	 false, 0, 0x007fff80, false),
     55   1.1.1.9  christos   HOWTO (R_SPU_ADDR16_LO,  0, 4, 16, false,  7, complain_overflow_dont,
     56       1.1     skrll 	 bfd_elf_generic_reloc, "SPU_ADDR16_LO",
     57   1.1.1.9  christos 	 false, 0, 0x007fff80, false),
     58   1.1.1.9  christos   HOWTO (R_SPU_ADDR18,	   0, 4, 18, false,  7, complain_overflow_bitfield,
     59       1.1     skrll 	 bfd_elf_generic_reloc, "SPU_ADDR18",
     60   1.1.1.9  christos 	 false, 0, 0x01ffff80, false),
     61   1.1.1.9  christos   HOWTO (R_SPU_ADDR32,	   0, 4, 32, false,  0, complain_overflow_dont,
     62       1.1     skrll 	 bfd_elf_generic_reloc, "SPU_ADDR32",
     63   1.1.1.9  christos 	 false, 0, 0xffffffff, false),
     64   1.1.1.9  christos   HOWTO (R_SPU_REL16,	   2, 4, 16,  true,  7, complain_overflow_bitfield,
     65       1.1     skrll 	 bfd_elf_generic_reloc, "SPU_REL16",
     66   1.1.1.9  christos 	 false, 0, 0x007fff80, true),
     67   1.1.1.9  christos   HOWTO (R_SPU_ADDR7,	   0, 4,  7, false, 14, complain_overflow_dont,
     68       1.1     skrll 	 bfd_elf_generic_reloc, "SPU_ADDR7",
     69   1.1.1.9  christos 	 false, 0, 0x001fc000, false),
     70   1.1.1.9  christos   HOWTO (R_SPU_REL9,	   2, 4,  9,  true,  0, complain_overflow_signed,
     71   1.1.1.6  christos 	 spu_elf_rel9,		"SPU_REL9",
     72   1.1.1.9  christos 	 false, 0, 0x0180007f, true),
     73   1.1.1.9  christos   HOWTO (R_SPU_REL9I,	   2, 4,  9,  true,  0, complain_overflow_signed,
     74   1.1.1.6  christos 	 spu_elf_rel9,		"SPU_REL9I",
     75   1.1.1.9  christos 	 false, 0, 0x0000c07f, true),
     76   1.1.1.9  christos   HOWTO (R_SPU_ADDR10I,	   0, 4, 10, false, 14, complain_overflow_signed,
     77       1.1     skrll 	 bfd_elf_generic_reloc, "SPU_ADDR10I",
     78   1.1.1.9  christos 	 false, 0, 0x00ffc000, false),
     79   1.1.1.9  christos   HOWTO (R_SPU_ADDR16I,	   0, 4, 16, false,  7, complain_overflow_signed,
     80       1.1     skrll 	 bfd_elf_generic_reloc, "SPU_ADDR16I",
     81   1.1.1.9  christos 	 false, 0, 0x007fff80, false),
     82   1.1.1.9  christos   HOWTO (R_SPU_REL32,	   0, 4, 32, true,  0, complain_overflow_dont,
     83       1.1     skrll 	 bfd_elf_generic_reloc, "SPU_REL32",
     84   1.1.1.9  christos 	 false, 0, 0xffffffff, true),
     85   1.1.1.9  christos   HOWTO (R_SPU_ADDR16X,	   0, 4, 16, false,  7, complain_overflow_bitfield,
     86       1.1     skrll 	 bfd_elf_generic_reloc, "SPU_ADDR16X",
     87   1.1.1.9  christos 	 false, 0, 0x007fff80, false),
     88   1.1.1.9  christos   HOWTO (R_SPU_PPU32,	   0, 4, 32, false,  0, complain_overflow_dont,
     89       1.1     skrll 	 bfd_elf_generic_reloc, "SPU_PPU32",
     90   1.1.1.9  christos 	 false, 0, 0xffffffff, false),
     91   1.1.1.9  christos   HOWTO (R_SPU_PPU64,	   0, 8, 64, false,  0, complain_overflow_dont,
     92       1.1     skrll 	 bfd_elf_generic_reloc, "SPU_PPU64",
     93   1.1.1.9  christos 	 false, 0, -1, false),
     94   1.1.1.9  christos   HOWTO (R_SPU_ADD_PIC,	   0, 0,  0, false,  0, complain_overflow_dont,
     95   1.1.1.2  christos 	 bfd_elf_generic_reloc, "SPU_ADD_PIC",
     96   1.1.1.9  christos 	 false, 0, 0x00000000, false),
     97       1.1     skrll };
     98       1.1     skrll 
     99       1.1     skrll static struct bfd_elf_special_section const spu_elf_special_sections[] = {
    100       1.1     skrll   { "._ea", 4, 0, SHT_PROGBITS, SHF_WRITE },
    101       1.1     skrll   { ".toe", 4, 0, SHT_NOBITS, SHF_ALLOC },
    102       1.1     skrll   { NULL, 0, 0, 0, 0 }
    103       1.1     skrll };
    104       1.1     skrll 
    105       1.1     skrll static enum elf_spu_reloc_type
    106       1.1     skrll spu_elf_bfd_to_reloc_type (bfd_reloc_code_real_type code)
    107       1.1     skrll {
    108       1.1     skrll   switch (code)
    109       1.1     skrll     {
    110       1.1     skrll     default:
    111   1.1.1.4  christos       return (enum elf_spu_reloc_type) -1;
    112   1.1.1.4  christos     case BFD_RELOC_NONE:
    113       1.1     skrll       return R_SPU_NONE;
    114       1.1     skrll     case BFD_RELOC_SPU_IMM10W:
    115       1.1     skrll       return R_SPU_ADDR10;
    116       1.1     skrll     case BFD_RELOC_SPU_IMM16W:
    117       1.1     skrll       return R_SPU_ADDR16;
    118       1.1     skrll     case BFD_RELOC_SPU_LO16:
    119       1.1     skrll       return R_SPU_ADDR16_LO;
    120       1.1     skrll     case BFD_RELOC_SPU_HI16:
    121       1.1     skrll       return R_SPU_ADDR16_HI;
    122       1.1     skrll     case BFD_RELOC_SPU_IMM18:
    123       1.1     skrll       return R_SPU_ADDR18;
    124       1.1     skrll     case BFD_RELOC_SPU_PCREL16:
    125       1.1     skrll       return R_SPU_REL16;
    126       1.1     skrll     case BFD_RELOC_SPU_IMM7:
    127       1.1     skrll       return R_SPU_ADDR7;
    128       1.1     skrll     case BFD_RELOC_SPU_IMM8:
    129       1.1     skrll       return R_SPU_NONE;
    130       1.1     skrll     case BFD_RELOC_SPU_PCREL9a:
    131       1.1     skrll       return R_SPU_REL9;
    132       1.1     skrll     case BFD_RELOC_SPU_PCREL9b:
    133       1.1     skrll       return R_SPU_REL9I;
    134       1.1     skrll     case BFD_RELOC_SPU_IMM10:
    135       1.1     skrll       return R_SPU_ADDR10I;
    136       1.1     skrll     case BFD_RELOC_SPU_IMM16:
    137       1.1     skrll       return R_SPU_ADDR16I;
    138       1.1     skrll     case BFD_RELOC_32:
    139       1.1     skrll       return R_SPU_ADDR32;
    140       1.1     skrll     case BFD_RELOC_32_PCREL:
    141       1.1     skrll       return R_SPU_REL32;
    142       1.1     skrll     case BFD_RELOC_SPU_PPU32:
    143       1.1     skrll       return R_SPU_PPU32;
    144       1.1     skrll     case BFD_RELOC_SPU_PPU64:
    145       1.1     skrll       return R_SPU_PPU64;
    146   1.1.1.2  christos     case BFD_RELOC_SPU_ADD_PIC:
    147   1.1.1.2  christos       return R_SPU_ADD_PIC;
    148       1.1     skrll     }
    149       1.1     skrll }
    150       1.1     skrll 
    151   1.1.1.9  christos static bool
    152   1.1.1.7  christos spu_elf_info_to_howto (bfd *abfd,
    153       1.1     skrll 		       arelent *cache_ptr,
    154       1.1     skrll 		       Elf_Internal_Rela *dst)
    155       1.1     skrll {
    156       1.1     skrll   enum elf_spu_reloc_type r_type;
    157       1.1     skrll 
    158       1.1     skrll   r_type = (enum elf_spu_reloc_type) ELF32_R_TYPE (dst->r_info);
    159   1.1.1.4  christos   /* PR 17512: file: 90c2a92e.  */
    160   1.1.1.4  christos   if (r_type >= R_SPU_max)
    161   1.1.1.4  christos     {
    162   1.1.1.6  christos       /* xgettext:c-format */
    163   1.1.1.7  christos       _bfd_error_handler (_("%pB: unsupported relocation type %#x"),
    164   1.1.1.6  christos 			  abfd, r_type);
    165   1.1.1.4  christos       bfd_set_error (bfd_error_bad_value);
    166   1.1.1.9  christos       return false;
    167   1.1.1.4  christos     }
    168       1.1     skrll   cache_ptr->howto = &elf_howto_table[(int) r_type];
    169   1.1.1.9  christos   return true;
    170       1.1     skrll }
    171       1.1     skrll 
    172       1.1     skrll static reloc_howto_type *
    173       1.1     skrll spu_elf_reloc_type_lookup (bfd *abfd ATTRIBUTE_UNUSED,
    174       1.1     skrll 			   bfd_reloc_code_real_type code)
    175       1.1     skrll {
    176       1.1     skrll   enum elf_spu_reloc_type r_type = spu_elf_bfd_to_reloc_type (code);
    177       1.1     skrll 
    178   1.1.1.4  christos   if (r_type == (enum elf_spu_reloc_type) -1)
    179       1.1     skrll     return NULL;
    180       1.1     skrll 
    181       1.1     skrll   return elf_howto_table + r_type;
    182       1.1     skrll }
    183       1.1     skrll 
    184       1.1     skrll static reloc_howto_type *
    185       1.1     skrll spu_elf_reloc_name_lookup (bfd *abfd ATTRIBUTE_UNUSED,
    186       1.1     skrll 			   const char *r_name)
    187       1.1     skrll {
    188       1.1     skrll   unsigned int i;
    189       1.1     skrll 
    190       1.1     skrll   for (i = 0; i < sizeof (elf_howto_table) / sizeof (elf_howto_table[0]); i++)
    191       1.1     skrll     if (elf_howto_table[i].name != NULL
    192       1.1     skrll 	&& strcasecmp (elf_howto_table[i].name, r_name) == 0)
    193       1.1     skrll       return &elf_howto_table[i];
    194       1.1     skrll 
    195       1.1     skrll   return NULL;
    196       1.1     skrll }
    197       1.1     skrll 
    198       1.1     skrll /* Apply R_SPU_REL9 and R_SPU_REL9I relocs.  */
    199       1.1     skrll 
    200       1.1     skrll static bfd_reloc_status_type
    201       1.1     skrll spu_elf_rel9 (bfd *abfd, arelent *reloc_entry, asymbol *symbol,
    202       1.1     skrll 	      void *data, asection *input_section,
    203       1.1     skrll 	      bfd *output_bfd, char **error_message)
    204       1.1     skrll {
    205       1.1     skrll   bfd_size_type octets;
    206       1.1     skrll   bfd_vma val;
    207       1.1     skrll   long insn;
    208       1.1     skrll 
    209       1.1     skrll   /* If this is a relocatable link (output_bfd test tells us), just
    210       1.1     skrll      call the generic function.  Any adjustment will be done at final
    211       1.1     skrll      link time.  */
    212       1.1     skrll   if (output_bfd != NULL)
    213       1.1     skrll     return bfd_elf_generic_reloc (abfd, reloc_entry, symbol, data,
    214       1.1     skrll 				  input_section, output_bfd, error_message);
    215       1.1     skrll 
    216       1.1     skrll   if (reloc_entry->address > bfd_get_section_limit (abfd, input_section))
    217       1.1     skrll     return bfd_reloc_outofrange;
    218   1.1.1.8  christos   octets = reloc_entry->address * OCTETS_PER_BYTE (abfd, input_section);
    219       1.1     skrll 
    220       1.1     skrll   /* Get symbol value.  */
    221       1.1     skrll   val = 0;
    222       1.1     skrll   if (!bfd_is_com_section (symbol->section))
    223       1.1     skrll     val = symbol->value;
    224       1.1     skrll   if (symbol->section->output_section)
    225       1.1     skrll     val += symbol->section->output_section->vma;
    226       1.1     skrll 
    227       1.1     skrll   val += reloc_entry->addend;
    228       1.1     skrll 
    229       1.1     skrll   /* Make it pc-relative.  */
    230       1.1     skrll   val -= input_section->output_section->vma + input_section->output_offset;
    231       1.1     skrll 
    232       1.1     skrll   val >>= 2;
    233       1.1     skrll   if (val + 256 >= 512)
    234       1.1     skrll     return bfd_reloc_overflow;
    235       1.1     skrll 
    236       1.1     skrll   insn = bfd_get_32 (abfd, (bfd_byte *) data + octets);
    237       1.1     skrll 
    238       1.1     skrll   /* Move two high bits of value to REL9I and REL9 position.
    239       1.1     skrll      The mask will take care of selecting the right field.  */
    240       1.1     skrll   val = (val & 0x7f) | ((val & 0x180) << 7) | ((val & 0x180) << 16);
    241       1.1     skrll   insn &= ~reloc_entry->howto->dst_mask;
    242       1.1     skrll   insn |= val & reloc_entry->howto->dst_mask;
    243       1.1     skrll   bfd_put_32 (abfd, insn, (bfd_byte *) data + octets);
    244       1.1     skrll   return bfd_reloc_ok;
    245       1.1     skrll }
    246       1.1     skrll 
    247   1.1.1.9  christos static bool
    248       1.1     skrll spu_elf_new_section_hook (bfd *abfd, asection *sec)
    249       1.1     skrll {
    250  1.1.1.11  christos   struct _spu_elf_section_data *sdata;
    251       1.1     skrll 
    252  1.1.1.11  christos   sdata = bfd_zalloc (abfd, sizeof (*sdata));
    253  1.1.1.11  christos   if (sdata == NULL)
    254  1.1.1.11  christos     return false;
    255  1.1.1.11  christos   sec->used_by_bfd = sdata;
    256       1.1     skrll 
    257       1.1     skrll   return _bfd_elf_new_section_hook (abfd, sec);
    258       1.1     skrll }
    259       1.1     skrll 
    260       1.1     skrll /* Set up overlay info for executables.  */
    261       1.1     skrll 
    262   1.1.1.9  christos static bool
    263       1.1     skrll spu_elf_object_p (bfd *abfd)
    264       1.1     skrll {
    265       1.1     skrll   if ((abfd->flags & (EXEC_P | DYNAMIC)) != 0)
    266       1.1     skrll     {
    267       1.1     skrll       unsigned int i, num_ovl, num_buf;
    268       1.1     skrll       Elf_Internal_Phdr *phdr = elf_tdata (abfd)->phdr;
    269       1.1     skrll       Elf_Internal_Ehdr *ehdr = elf_elfheader (abfd);
    270       1.1     skrll       Elf_Internal_Phdr *last_phdr = NULL;
    271       1.1     skrll 
    272       1.1     skrll       for (num_buf = 0, num_ovl = 0, i = 0; i < ehdr->e_phnum; i++, phdr++)
    273       1.1     skrll 	if (phdr->p_type == PT_LOAD && (phdr->p_flags & PF_OVERLAY) != 0)
    274       1.1     skrll 	  {
    275       1.1     skrll 	    unsigned int j;
    276       1.1     skrll 
    277       1.1     skrll 	    ++num_ovl;
    278       1.1     skrll 	    if (last_phdr == NULL
    279       1.1     skrll 		|| ((last_phdr->p_vaddr ^ phdr->p_vaddr) & 0x3ffff) != 0)
    280       1.1     skrll 	      ++num_buf;
    281       1.1     skrll 	    last_phdr = phdr;
    282       1.1     skrll 	    for (j = 1; j < elf_numsections (abfd); j++)
    283       1.1     skrll 	      {
    284       1.1     skrll 		Elf_Internal_Shdr *shdr = elf_elfsections (abfd)[j];
    285       1.1     skrll 
    286  1.1.1.10  christos 		if (shdr->bfd_section != NULL
    287  1.1.1.10  christos 		    && ELF_SECTION_SIZE (shdr, phdr) != 0
    288   1.1.1.2  christos 		    && ELF_SECTION_IN_SEGMENT (shdr, phdr))
    289       1.1     skrll 		  {
    290       1.1     skrll 		    asection *sec = shdr->bfd_section;
    291       1.1     skrll 		    spu_elf_section_data (sec)->u.o.ovl_index = num_ovl;
    292       1.1     skrll 		    spu_elf_section_data (sec)->u.o.ovl_buf = num_buf;
    293       1.1     skrll 		  }
    294       1.1     skrll 	      }
    295       1.1     skrll 	  }
    296       1.1     skrll     }
    297   1.1.1.9  christos   return true;
    298       1.1     skrll }
    299       1.1     skrll 
    300       1.1     skrll /* Specially mark defined symbols named _EAR_* with BSF_KEEP so that
    301       1.1     skrll    strip --strip-unneeded will not remove them.  */
    302       1.1     skrll 
    303       1.1     skrll static void
    304       1.1     skrll spu_elf_backend_symbol_processing (bfd *abfd ATTRIBUTE_UNUSED, asymbol *sym)
    305       1.1     skrll {
    306       1.1     skrll   if (sym->name != NULL
    307       1.1     skrll       && sym->section != bfd_abs_section_ptr
    308   1.1.1.9  christos       && startswith (sym->name, "_EAR_"))
    309       1.1     skrll     sym->flags |= BSF_KEEP;
    310       1.1     skrll }
    311       1.1     skrll 
    312       1.1     skrll /* SPU ELF linker hash table.  */
    313       1.1     skrll 
    314       1.1     skrll struct spu_link_hash_table
    315       1.1     skrll {
    316       1.1     skrll   struct elf_link_hash_table elf;
    317       1.1     skrll 
    318   1.1.1.2  christos   struct spu_elf_params *params;
    319   1.1.1.2  christos 
    320       1.1     skrll   /* Shortcuts to overlay sections.  */
    321       1.1     skrll   asection *ovtab;
    322   1.1.1.2  christos   asection *init;
    323       1.1     skrll   asection *toe;
    324       1.1     skrll   asection **ovl_sec;
    325       1.1     skrll 
    326       1.1     skrll   /* Count of stubs in each overlay section.  */
    327       1.1     skrll   unsigned int *stub_count;
    328       1.1     skrll 
    329       1.1     skrll   /* The stub section for each overlay section.  */
    330       1.1     skrll   asection **stub_sec;
    331       1.1     skrll 
    332   1.1.1.2  christos   struct elf_link_hash_entry *ovly_entry[2];
    333       1.1     skrll 
    334       1.1     skrll   /* Number of overlay buffers.  */
    335       1.1     skrll   unsigned int num_buf;
    336       1.1     skrll 
    337       1.1     skrll   /* Total number of overlays.  */
    338       1.1     skrll   unsigned int num_overlays;
    339       1.1     skrll 
    340   1.1.1.2  christos   /* For soft icache.  */
    341   1.1.1.2  christos   unsigned int line_size_log2;
    342   1.1.1.2  christos   unsigned int num_lines_log2;
    343   1.1.1.2  christos   unsigned int fromelem_size_log2;
    344   1.1.1.2  christos 
    345       1.1     skrll   /* How much memory we have.  */
    346       1.1     skrll   unsigned int local_store;
    347   1.1.1.2  christos 
    348       1.1     skrll   /* Count of overlay stubs needed in non-overlay area.  */
    349       1.1     skrll   unsigned int non_ovly_stub;
    350       1.1     skrll 
    351   1.1.1.2  christos   /* Pointer to the fixup section */
    352   1.1.1.2  christos   asection *sfixup;
    353       1.1     skrll 
    354       1.1     skrll   /* Set on error.  */
    355       1.1     skrll   unsigned int stub_err : 1;
    356       1.1     skrll };
    357       1.1     skrll 
    358       1.1     skrll /* Hijack the generic got fields for overlay stub accounting.  */
    359       1.1     skrll 
    360       1.1     skrll struct got_entry
    361       1.1     skrll {
    362       1.1     skrll   struct got_entry *next;
    363       1.1     skrll   unsigned int ovl;
    364   1.1.1.2  christos   union {
    365   1.1.1.2  christos     bfd_vma addend;
    366   1.1.1.2  christos     bfd_vma br_addr;
    367   1.1.1.2  christos   };
    368       1.1     skrll   bfd_vma stub_addr;
    369       1.1     skrll };
    370       1.1     skrll 
    371       1.1     skrll #define spu_hash_table(p) \
    372   1.1.1.9  christos   ((is_elf_hash_table ((p)->hash)					\
    373   1.1.1.9  christos     && elf_hash_table_id (elf_hash_table (p)) == SPU_ELF_DATA)		\
    374   1.1.1.9  christos    ? (struct spu_link_hash_table *) (p)->hash : NULL)
    375   1.1.1.2  christos 
    376   1.1.1.2  christos struct call_info
    377   1.1.1.2  christos {
    378   1.1.1.2  christos   struct function_info *fun;
    379   1.1.1.2  christos   struct call_info *next;
    380   1.1.1.2  christos   unsigned int count;
    381   1.1.1.2  christos   unsigned int max_depth;
    382   1.1.1.2  christos   unsigned int is_tail : 1;
    383   1.1.1.2  christos   unsigned int is_pasted : 1;
    384   1.1.1.2  christos   unsigned int broken_cycle : 1;
    385   1.1.1.2  christos   unsigned int priority : 13;
    386   1.1.1.2  christos };
    387   1.1.1.2  christos 
    388   1.1.1.2  christos struct function_info
    389   1.1.1.2  christos {
    390   1.1.1.2  christos   /* List of functions called.  Also branches to hot/cold part of
    391   1.1.1.2  christos      function.  */
    392   1.1.1.2  christos   struct call_info *call_list;
    393   1.1.1.2  christos   /* For hot/cold part of function, point to owner.  */
    394   1.1.1.2  christos   struct function_info *start;
    395   1.1.1.2  christos   /* Symbol at start of function.  */
    396   1.1.1.2  christos   union {
    397   1.1.1.2  christos     Elf_Internal_Sym *sym;
    398   1.1.1.2  christos     struct elf_link_hash_entry *h;
    399   1.1.1.2  christos   } u;
    400   1.1.1.2  christos   /* Function section.  */
    401   1.1.1.2  christos   asection *sec;
    402   1.1.1.2  christos   asection *rodata;
    403   1.1.1.2  christos   /* Where last called from, and number of sections called from.  */
    404   1.1.1.2  christos   asection *last_caller;
    405   1.1.1.2  christos   unsigned int call_count;
    406   1.1.1.2  christos   /* Address range of (this part of) function.  */
    407   1.1.1.2  christos   bfd_vma lo, hi;
    408   1.1.1.2  christos   /* Offset where we found a store of lr, or -1 if none found.  */
    409   1.1.1.2  christos   bfd_vma lr_store;
    410   1.1.1.2  christos   /* Offset where we found the stack adjustment insn.  */
    411   1.1.1.2  christos   bfd_vma sp_adjust;
    412   1.1.1.2  christos   /* Stack usage.  */
    413   1.1.1.2  christos   int stack;
    414   1.1.1.2  christos   /* Distance from root of call tree.  Tail and hot/cold branches
    415   1.1.1.2  christos      count as one deeper.  We aren't counting stack frames here.  */
    416   1.1.1.2  christos   unsigned int depth;
    417   1.1.1.2  christos   /* Set if global symbol.  */
    418   1.1.1.2  christos   unsigned int global : 1;
    419   1.1.1.2  christos   /* Set if known to be start of function (as distinct from a hunk
    420   1.1.1.2  christos      in hot/cold section.  */
    421   1.1.1.2  christos   unsigned int is_func : 1;
    422   1.1.1.2  christos   /* Set if not a root node.  */
    423   1.1.1.2  christos   unsigned int non_root : 1;
    424   1.1.1.2  christos   /* Flags used during call tree traversal.  It's cheaper to replicate
    425   1.1.1.2  christos      the visit flags than have one which needs clearing after a traversal.  */
    426   1.1.1.2  christos   unsigned int visit1 : 1;
    427   1.1.1.2  christos   unsigned int visit2 : 1;
    428   1.1.1.2  christos   unsigned int marking : 1;
    429   1.1.1.2  christos   unsigned int visit3 : 1;
    430   1.1.1.2  christos   unsigned int visit4 : 1;
    431   1.1.1.2  christos   unsigned int visit5 : 1;
    432   1.1.1.2  christos   unsigned int visit6 : 1;
    433   1.1.1.2  christos   unsigned int visit7 : 1;
    434   1.1.1.2  christos };
    435   1.1.1.2  christos 
    436   1.1.1.2  christos struct spu_elf_stack_info
    437   1.1.1.2  christos {
    438   1.1.1.2  christos   int num_fun;
    439   1.1.1.2  christos   int max_fun;
    440   1.1.1.2  christos   /* Variable size array describing functions, one per contiguous
    441   1.1.1.2  christos      address range belonging to a function.  */
    442   1.1.1.2  christos   struct function_info fun[1];
    443   1.1.1.2  christos };
    444   1.1.1.2  christos 
    445   1.1.1.2  christos static struct function_info *find_function (asection *, bfd_vma,
    446   1.1.1.2  christos 					    struct bfd_link_info *);
    447       1.1     skrll 
    448       1.1     skrll /* Create a spu ELF linker hash table.  */
    449       1.1     skrll 
    450       1.1     skrll static struct bfd_link_hash_table *
    451       1.1     skrll spu_elf_link_hash_table_create (bfd *abfd)
    452       1.1     skrll {
    453       1.1     skrll   struct spu_link_hash_table *htab;
    454       1.1     skrll 
    455   1.1.1.4  christos   htab = bfd_zmalloc (sizeof (*htab));
    456       1.1     skrll   if (htab == NULL)
    457       1.1     skrll     return NULL;
    458       1.1     skrll 
    459       1.1     skrll   if (!_bfd_elf_link_hash_table_init (&htab->elf, abfd,
    460       1.1     skrll 				      _bfd_elf_link_hash_newfunc,
    461  1.1.1.11  christos 				      sizeof (struct elf_link_hash_entry)))
    462       1.1     skrll     {
    463       1.1     skrll       free (htab);
    464       1.1     skrll       return NULL;
    465       1.1     skrll     }
    466       1.1     skrll 
    467       1.1     skrll   htab->elf.init_got_refcount.refcount = 0;
    468       1.1     skrll   htab->elf.init_got_refcount.glist = NULL;
    469       1.1     skrll   htab->elf.init_got_offset.offset = 0;
    470       1.1     skrll   htab->elf.init_got_offset.glist = NULL;
    471       1.1     skrll   return &htab->elf.root;
    472       1.1     skrll }
    473       1.1     skrll 
    474   1.1.1.2  christos void
    475   1.1.1.2  christos spu_elf_setup (struct bfd_link_info *info, struct spu_elf_params *params)
    476   1.1.1.2  christos {
    477   1.1.1.2  christos   bfd_vma max_branch_log2;
    478   1.1.1.2  christos 
    479   1.1.1.2  christos   struct spu_link_hash_table *htab = spu_hash_table (info);
    480   1.1.1.2  christos   htab->params = params;
    481   1.1.1.2  christos   htab->line_size_log2 = bfd_log2 (htab->params->line_size);
    482   1.1.1.2  christos   htab->num_lines_log2 = bfd_log2 (htab->params->num_lines);
    483   1.1.1.2  christos 
    484   1.1.1.2  christos   /* For the software i-cache, we provide a "from" list whose size
    485   1.1.1.2  christos      is a power-of-two number of quadwords, big enough to hold one
    486   1.1.1.2  christos      byte per outgoing branch.  Compute this number here.  */
    487   1.1.1.2  christos   max_branch_log2 = bfd_log2 (htab->params->max_branch);
    488   1.1.1.2  christos   htab->fromelem_size_log2 = max_branch_log2 > 4 ? max_branch_log2 - 4 : 0;
    489   1.1.1.2  christos }
    490   1.1.1.2  christos 
    491       1.1     skrll /* Find the symbol for the given R_SYMNDX in IBFD and set *HP and *SYMP
    492       1.1     skrll    to (hash, NULL) for global symbols, and (NULL, sym) for locals.  Set
    493       1.1     skrll    *SYMSECP to the symbol's section.  *LOCSYMSP caches local syms.  */
    494       1.1     skrll 
    495   1.1.1.9  christos static bool
    496       1.1     skrll get_sym_h (struct elf_link_hash_entry **hp,
    497       1.1     skrll 	   Elf_Internal_Sym **symp,
    498       1.1     skrll 	   asection **symsecp,
    499       1.1     skrll 	   Elf_Internal_Sym **locsymsp,
    500       1.1     skrll 	   unsigned long r_symndx,
    501       1.1     skrll 	   bfd *ibfd)
    502       1.1     skrll {
    503       1.1     skrll   Elf_Internal_Shdr *symtab_hdr = &elf_tdata (ibfd)->symtab_hdr;
    504       1.1     skrll 
    505       1.1     skrll   if (r_symndx >= symtab_hdr->sh_info)
    506       1.1     skrll     {
    507       1.1     skrll       struct elf_link_hash_entry **sym_hashes = elf_sym_hashes (ibfd);
    508       1.1     skrll       struct elf_link_hash_entry *h;
    509       1.1     skrll 
    510       1.1     skrll       h = sym_hashes[r_symndx - symtab_hdr->sh_info];
    511       1.1     skrll       while (h->root.type == bfd_link_hash_indirect
    512       1.1     skrll 	     || h->root.type == bfd_link_hash_warning)
    513       1.1     skrll 	h = (struct elf_link_hash_entry *) h->root.u.i.link;
    514       1.1     skrll 
    515       1.1     skrll       if (hp != NULL)
    516       1.1     skrll 	*hp = h;
    517       1.1     skrll 
    518       1.1     skrll       if (symp != NULL)
    519       1.1     skrll 	*symp = NULL;
    520       1.1     skrll 
    521       1.1     skrll       if (symsecp != NULL)
    522       1.1     skrll 	{
    523       1.1     skrll 	  asection *symsec = NULL;
    524       1.1     skrll 	  if (h->root.type == bfd_link_hash_defined
    525       1.1     skrll 	      || h->root.type == bfd_link_hash_defweak)
    526       1.1     skrll 	    symsec = h->root.u.def.section;
    527       1.1     skrll 	  *symsecp = symsec;
    528       1.1     skrll 	}
    529       1.1     skrll     }
    530       1.1     skrll   else
    531       1.1     skrll     {
    532       1.1     skrll       Elf_Internal_Sym *sym;
    533       1.1     skrll       Elf_Internal_Sym *locsyms = *locsymsp;
    534       1.1     skrll 
    535       1.1     skrll       if (locsyms == NULL)
    536       1.1     skrll 	{
    537       1.1     skrll 	  locsyms = (Elf_Internal_Sym *) symtab_hdr->contents;
    538       1.1     skrll 	  if (locsyms == NULL)
    539       1.1     skrll 	    locsyms = bfd_elf_get_elf_syms (ibfd, symtab_hdr,
    540       1.1     skrll 					    symtab_hdr->sh_info,
    541       1.1     skrll 					    0, NULL, NULL, NULL);
    542       1.1     skrll 	  if (locsyms == NULL)
    543   1.1.1.9  christos 	    return false;
    544       1.1     skrll 	  *locsymsp = locsyms;
    545       1.1     skrll 	}
    546       1.1     skrll       sym = locsyms + r_symndx;
    547       1.1     skrll 
    548       1.1     skrll       if (hp != NULL)
    549       1.1     skrll 	*hp = NULL;
    550       1.1     skrll 
    551       1.1     skrll       if (symp != NULL)
    552       1.1     skrll 	*symp = sym;
    553       1.1     skrll 
    554       1.1     skrll       if (symsecp != NULL)
    555       1.1     skrll 	*symsecp = bfd_section_from_elf_index (ibfd, sym->st_shndx);
    556       1.1     skrll     }
    557       1.1     skrll 
    558   1.1.1.9  christos   return true;
    559       1.1     skrll }
    560       1.1     skrll 
    561       1.1     skrll /* Create the note section if not already present.  This is done early so
    562       1.1     skrll    that the linker maps the sections to the right place in the output.  */
    563       1.1     skrll 
    564   1.1.1.9  christos bool
    565   1.1.1.2  christos spu_elf_create_sections (struct bfd_link_info *info)
    566       1.1     skrll {
    567       1.1     skrll   struct spu_link_hash_table *htab = spu_hash_table (info);
    568   1.1.1.2  christos   bfd *ibfd;
    569       1.1     skrll 
    570   1.1.1.4  christos   for (ibfd = info->input_bfds; ibfd != NULL; ibfd = ibfd->link.next)
    571       1.1     skrll     if (bfd_get_section_by_name (ibfd, SPU_PTNOTE_SPUNAME) != NULL)
    572       1.1     skrll       break;
    573       1.1     skrll 
    574       1.1     skrll   if (ibfd == NULL)
    575       1.1     skrll     {
    576       1.1     skrll       /* Make SPU_PTNOTE_SPUNAME section.  */
    577       1.1     skrll       asection *s;
    578       1.1     skrll       size_t name_len;
    579       1.1     skrll       size_t size;
    580       1.1     skrll       bfd_byte *data;
    581       1.1     skrll       flagword flags;
    582       1.1     skrll 
    583       1.1     skrll       ibfd = info->input_bfds;
    584   1.1.1.8  christos       /* This should really be SEC_LINKER_CREATED, but then we'd need
    585   1.1.1.8  christos 	 to write out the section ourselves.  */
    586       1.1     skrll       flags = SEC_LOAD | SEC_READONLY | SEC_HAS_CONTENTS | SEC_IN_MEMORY;
    587       1.1     skrll       s = bfd_make_section_anyway_with_flags (ibfd, SPU_PTNOTE_SPUNAME, flags);
    588       1.1     skrll       if (s == NULL
    589   1.1.1.8  christos 	  || !bfd_set_section_alignment (s, 4))
    590   1.1.1.9  christos 	return false;
    591   1.1.1.8  christos       /* Because we didn't set SEC_LINKER_CREATED we need to set the
    592   1.1.1.8  christos 	 proper section type.  */
    593   1.1.1.8  christos       elf_section_type (s) = SHT_NOTE;
    594       1.1     skrll 
    595       1.1     skrll       name_len = strlen (bfd_get_filename (info->output_bfd)) + 1;
    596       1.1     skrll       size = 12 + ((sizeof (SPU_PLUGIN_NAME) + 3) & -4);
    597       1.1     skrll       size += (name_len + 3) & -4;
    598       1.1     skrll 
    599   1.1.1.8  christos       if (!bfd_set_section_size (s, size))
    600   1.1.1.9  christos 	return false;
    601       1.1     skrll 
    602       1.1     skrll       data = bfd_zalloc (ibfd, size);
    603       1.1     skrll       if (data == NULL)
    604   1.1.1.9  christos 	return false;
    605       1.1     skrll 
    606       1.1     skrll       bfd_put_32 (ibfd, sizeof (SPU_PLUGIN_NAME), data + 0);
    607       1.1     skrll       bfd_put_32 (ibfd, name_len, data + 4);
    608       1.1     skrll       bfd_put_32 (ibfd, 1, data + 8);
    609       1.1     skrll       memcpy (data + 12, SPU_PLUGIN_NAME, sizeof (SPU_PLUGIN_NAME));
    610       1.1     skrll       memcpy (data + 12 + ((sizeof (SPU_PLUGIN_NAME) + 3) & -4),
    611       1.1     skrll 	      bfd_get_filename (info->output_bfd), name_len);
    612       1.1     skrll       s->contents = data;
    613  1.1.1.11  christos       s->alloced = 1;
    614       1.1     skrll     }
    615       1.1     skrll 
    616   1.1.1.2  christos   if (htab->params->emit_fixups)
    617   1.1.1.2  christos     {
    618   1.1.1.2  christos       asection *s;
    619   1.1.1.2  christos       flagword flags;
    620   1.1.1.2  christos 
    621   1.1.1.2  christos       if (htab->elf.dynobj == NULL)
    622   1.1.1.2  christos 	htab->elf.dynobj = ibfd;
    623   1.1.1.2  christos       ibfd = htab->elf.dynobj;
    624   1.1.1.2  christos       flags = (SEC_LOAD | SEC_ALLOC | SEC_READONLY | SEC_HAS_CONTENTS
    625   1.1.1.2  christos 	       | SEC_IN_MEMORY | SEC_LINKER_CREATED);
    626   1.1.1.2  christos       s = bfd_make_section_anyway_with_flags (ibfd, ".fixup", flags);
    627   1.1.1.8  christos       if (s == NULL || !bfd_set_section_alignment (s, 2))
    628   1.1.1.9  christos 	return false;
    629   1.1.1.2  christos       htab->sfixup = s;
    630   1.1.1.2  christos     }
    631   1.1.1.2  christos 
    632   1.1.1.9  christos   return true;
    633       1.1     skrll }
    634       1.1     skrll 
    635       1.1     skrll /* qsort predicate to sort sections by vma.  */
    636       1.1     skrll 
    637       1.1     skrll static int
    638       1.1     skrll sort_sections (const void *a, const void *b)
    639       1.1     skrll {
    640       1.1     skrll   const asection *const *s1 = a;
    641       1.1     skrll   const asection *const *s2 = b;
    642       1.1     skrll   bfd_signed_vma delta = (*s1)->vma - (*s2)->vma;
    643       1.1     skrll 
    644       1.1     skrll   if (delta != 0)
    645       1.1     skrll     return delta < 0 ? -1 : 1;
    646       1.1     skrll 
    647       1.1     skrll   return (*s1)->index - (*s2)->index;
    648       1.1     skrll }
    649       1.1     skrll 
    650   1.1.1.2  christos /* Identify overlays in the output bfd, and number them.
    651   1.1.1.2  christos    Returns 0 on error, 1 if no overlays, 2 if overlays.  */
    652       1.1     skrll 
    653   1.1.1.2  christos int
    654       1.1     skrll spu_elf_find_overlays (struct bfd_link_info *info)
    655       1.1     skrll {
    656       1.1     skrll   struct spu_link_hash_table *htab = spu_hash_table (info);
    657       1.1     skrll   asection **alloc_sec;
    658       1.1     skrll   unsigned int i, n, ovl_index, num_buf;
    659       1.1     skrll   asection *s;
    660       1.1     skrll   bfd_vma ovl_end;
    661   1.1.1.2  christos   static const char *const entry_names[2][2] = {
    662   1.1.1.2  christos     { "__ovly_load", "__icache_br_handler" },
    663   1.1.1.2  christos     { "__ovly_return", "__icache_call_handler" }
    664   1.1.1.2  christos   };
    665       1.1     skrll 
    666       1.1     skrll   if (info->output_bfd->section_count < 2)
    667   1.1.1.2  christos     return 1;
    668       1.1     skrll 
    669       1.1     skrll   alloc_sec
    670       1.1     skrll     = bfd_malloc (info->output_bfd->section_count * sizeof (*alloc_sec));
    671       1.1     skrll   if (alloc_sec == NULL)
    672   1.1.1.2  christos     return 0;
    673       1.1     skrll 
    674       1.1     skrll   /* Pick out all the alloced sections.  */
    675       1.1     skrll   for (n = 0, s = info->output_bfd->sections; s != NULL; s = s->next)
    676       1.1     skrll     if ((s->flags & SEC_ALLOC) != 0
    677       1.1     skrll 	&& (s->flags & (SEC_LOAD | SEC_THREAD_LOCAL)) != SEC_THREAD_LOCAL
    678       1.1     skrll 	&& s->size != 0)
    679       1.1     skrll       alloc_sec[n++] = s;
    680       1.1     skrll 
    681       1.1     skrll   if (n == 0)
    682       1.1     skrll     {
    683       1.1     skrll       free (alloc_sec);
    684   1.1.1.2  christos       return 1;
    685       1.1     skrll     }
    686       1.1     skrll 
    687       1.1     skrll   /* Sort them by vma.  */
    688       1.1     skrll   qsort (alloc_sec, n, sizeof (*alloc_sec), sort_sections);
    689       1.1     skrll 
    690       1.1     skrll   ovl_end = alloc_sec[0]->vma + alloc_sec[0]->size;
    691   1.1.1.2  christos   if (htab->params->ovly_flavour == ovly_soft_icache)
    692       1.1     skrll     {
    693   1.1.1.2  christos       unsigned int prev_buf = 0, set_id = 0;
    694   1.1.1.2  christos 
    695   1.1.1.2  christos       /* Look for an overlapping vma to find the first overlay section.  */
    696   1.1.1.2  christos       bfd_vma vma_start = 0;
    697   1.1.1.2  christos 
    698   1.1.1.2  christos       for (i = 1; i < n; i++)
    699   1.1.1.2  christos 	{
    700   1.1.1.2  christos 	  s = alloc_sec[i];
    701   1.1.1.2  christos 	  if (s->vma < ovl_end)
    702   1.1.1.2  christos 	    {
    703   1.1.1.2  christos 	      asection *s0 = alloc_sec[i - 1];
    704   1.1.1.2  christos 	      vma_start = s0->vma;
    705   1.1.1.2  christos 	      ovl_end = (s0->vma
    706   1.1.1.2  christos 			 + ((bfd_vma) 1
    707   1.1.1.2  christos 			    << (htab->num_lines_log2 + htab->line_size_log2)));
    708   1.1.1.2  christos 	      --i;
    709   1.1.1.2  christos 	      break;
    710   1.1.1.2  christos 	    }
    711   1.1.1.2  christos 	  else
    712   1.1.1.2  christos 	    ovl_end = s->vma + s->size;
    713   1.1.1.2  christos 	}
    714   1.1.1.2  christos 
    715   1.1.1.2  christos       /* Now find any sections within the cache area.  */
    716   1.1.1.2  christos       for (ovl_index = 0, num_buf = 0; i < n; i++)
    717       1.1     skrll 	{
    718   1.1.1.2  christos 	  s = alloc_sec[i];
    719   1.1.1.2  christos 	  if (s->vma >= ovl_end)
    720   1.1.1.2  christos 	    break;
    721       1.1     skrll 
    722   1.1.1.2  christos 	  /* A section in an overlay area called .ovl.init is not
    723   1.1.1.2  christos 	     an overlay, in the sense that it might be loaded in
    724   1.1.1.2  christos 	     by the overlay manager, but rather the initial
    725   1.1.1.2  christos 	     section contents for the overlay buffer.  */
    726   1.1.1.9  christos 	  if (!startswith (s->name, ".ovl.init"))
    727       1.1     skrll 	    {
    728   1.1.1.2  christos 	      num_buf = ((s->vma - vma_start) >> htab->line_size_log2) + 1;
    729   1.1.1.2  christos 	      set_id = (num_buf == prev_buf)? set_id + 1 : 0;
    730   1.1.1.2  christos 	      prev_buf = num_buf;
    731   1.1.1.2  christos 
    732   1.1.1.2  christos 	      if ((s->vma - vma_start) & (htab->params->line_size - 1))
    733   1.1.1.2  christos 		{
    734   1.1.1.7  christos 		  info->callbacks->einfo (_("%X%P: overlay section %pA "
    735   1.1.1.7  christos 					    "does not start on a cache line\n"),
    736   1.1.1.2  christos 					  s);
    737   1.1.1.2  christos 		  bfd_set_error (bfd_error_bad_value);
    738   1.1.1.2  christos 		  return 0;
    739   1.1.1.2  christos 		}
    740   1.1.1.2  christos 	      else if (s->size > htab->params->line_size)
    741   1.1.1.2  christos 		{
    742   1.1.1.7  christos 		  info->callbacks->einfo (_("%X%P: overlay section %pA "
    743   1.1.1.7  christos 					    "is larger than a cache line\n"),
    744   1.1.1.2  christos 					  s);
    745   1.1.1.2  christos 		  bfd_set_error (bfd_error_bad_value);
    746   1.1.1.2  christos 		  return 0;
    747   1.1.1.2  christos 		}
    748   1.1.1.2  christos 
    749   1.1.1.2  christos 	      alloc_sec[ovl_index++] = s;
    750   1.1.1.2  christos 	      spu_elf_section_data (s)->u.o.ovl_index
    751   1.1.1.2  christos 		= (set_id << htab->num_lines_log2) + num_buf;
    752   1.1.1.2  christos 	      spu_elf_section_data (s)->u.o.ovl_buf = num_buf;
    753       1.1     skrll 	    }
    754   1.1.1.2  christos 	}
    755   1.1.1.2  christos 
    756   1.1.1.2  christos       /* Ensure there are no more overlay sections.  */
    757   1.1.1.2  christos       for ( ; i < n; i++)
    758   1.1.1.2  christos 	{
    759   1.1.1.2  christos 	  s = alloc_sec[i];
    760   1.1.1.2  christos 	  if (s->vma < ovl_end)
    761       1.1     skrll 	    {
    762   1.1.1.7  christos 	      info->callbacks->einfo (_("%X%P: overlay section %pA "
    763   1.1.1.7  christos 					"is not in cache area\n"),
    764   1.1.1.2  christos 				      alloc_sec[i-1]);
    765   1.1.1.2  christos 	      bfd_set_error (bfd_error_bad_value);
    766   1.1.1.2  christos 	      return 0;
    767       1.1     skrll 	    }
    768   1.1.1.2  christos 	  else
    769   1.1.1.2  christos 	    ovl_end = s->vma + s->size;
    770   1.1.1.2  christos 	}
    771   1.1.1.2  christos     }
    772   1.1.1.2  christos   else
    773   1.1.1.2  christos     {
    774   1.1.1.2  christos       /* Look for overlapping vmas.  Any with overlap must be overlays.
    775   1.1.1.2  christos 	 Count them.  Also count the number of overlay regions.  */
    776   1.1.1.2  christos       for (ovl_index = 0, num_buf = 0, i = 1; i < n; i++)
    777   1.1.1.2  christos 	{
    778   1.1.1.2  christos 	  s = alloc_sec[i];
    779   1.1.1.2  christos 	  if (s->vma < ovl_end)
    780   1.1.1.2  christos 	    {
    781   1.1.1.2  christos 	      asection *s0 = alloc_sec[i - 1];
    782   1.1.1.2  christos 
    783   1.1.1.2  christos 	      if (spu_elf_section_data (s0)->u.o.ovl_index == 0)
    784   1.1.1.2  christos 		{
    785   1.1.1.2  christos 		  ++num_buf;
    786   1.1.1.9  christos 		  if (!startswith (s0->name, ".ovl.init"))
    787   1.1.1.2  christos 		    {
    788   1.1.1.2  christos 		      alloc_sec[ovl_index] = s0;
    789   1.1.1.2  christos 		      spu_elf_section_data (s0)->u.o.ovl_index = ++ovl_index;
    790   1.1.1.2  christos 		      spu_elf_section_data (s0)->u.o.ovl_buf = num_buf;
    791   1.1.1.2  christos 		    }
    792   1.1.1.2  christos 		  else
    793   1.1.1.2  christos 		    ovl_end = s->vma + s->size;
    794   1.1.1.2  christos 		}
    795   1.1.1.9  christos 	      if (!startswith (s->name, ".ovl.init"))
    796   1.1.1.2  christos 		{
    797   1.1.1.2  christos 		  alloc_sec[ovl_index] = s;
    798   1.1.1.2  christos 		  spu_elf_section_data (s)->u.o.ovl_index = ++ovl_index;
    799   1.1.1.2  christos 		  spu_elf_section_data (s)->u.o.ovl_buf = num_buf;
    800   1.1.1.2  christos 		  if (s0->vma != s->vma)
    801   1.1.1.2  christos 		    {
    802   1.1.1.6  christos 		      /* xgettext:c-format */
    803   1.1.1.7  christos 		      info->callbacks->einfo (_("%X%P: overlay sections %pA "
    804   1.1.1.7  christos 						"and %pA do not start at the "
    805   1.1.1.7  christos 						"same address\n"),
    806   1.1.1.2  christos 					      s0, s);
    807   1.1.1.2  christos 		      bfd_set_error (bfd_error_bad_value);
    808   1.1.1.2  christos 		      return 0;
    809   1.1.1.2  christos 		    }
    810   1.1.1.2  christos 		  if (ovl_end < s->vma + s->size)
    811   1.1.1.2  christos 		    ovl_end = s->vma + s->size;
    812   1.1.1.2  christos 		}
    813   1.1.1.2  christos 	    }
    814   1.1.1.2  christos 	  else
    815       1.1     skrll 	    ovl_end = s->vma + s->size;
    816       1.1     skrll 	}
    817       1.1     skrll     }
    818       1.1     skrll 
    819       1.1     skrll   htab->num_overlays = ovl_index;
    820       1.1     skrll   htab->num_buf = num_buf;
    821       1.1     skrll   htab->ovl_sec = alloc_sec;
    822   1.1.1.2  christos 
    823   1.1.1.2  christos   if (ovl_index == 0)
    824   1.1.1.2  christos     return 1;
    825   1.1.1.2  christos 
    826   1.1.1.2  christos   for (i = 0; i < 2; i++)
    827   1.1.1.2  christos     {
    828   1.1.1.2  christos       const char *name;
    829   1.1.1.2  christos       struct elf_link_hash_entry *h;
    830   1.1.1.2  christos 
    831   1.1.1.2  christos       name = entry_names[i][htab->params->ovly_flavour];
    832   1.1.1.9  christos       h = elf_link_hash_lookup (&htab->elf, name, true, false, false);
    833   1.1.1.2  christos       if (h == NULL)
    834   1.1.1.2  christos 	return 0;
    835   1.1.1.2  christos 
    836   1.1.1.2  christos       if (h->root.type == bfd_link_hash_new)
    837   1.1.1.2  christos 	{
    838   1.1.1.2  christos 	  h->root.type = bfd_link_hash_undefined;
    839   1.1.1.2  christos 	  h->ref_regular = 1;
    840   1.1.1.2  christos 	  h->ref_regular_nonweak = 1;
    841   1.1.1.2  christos 	  h->non_elf = 0;
    842   1.1.1.2  christos 	}
    843   1.1.1.2  christos       htab->ovly_entry[i] = h;
    844   1.1.1.2  christos     }
    845   1.1.1.2  christos 
    846   1.1.1.2  christos   return 2;
    847       1.1     skrll }
    848       1.1     skrll 
    849   1.1.1.2  christos /* Non-zero to use bra in overlay stubs rather than br.  */
    850   1.1.1.2  christos #define BRA_STUBS 0
    851   1.1.1.2  christos 
    852   1.1.1.2  christos #define BRA	0x30000000
    853   1.1.1.2  christos #define BRASL	0x31000000
    854       1.1     skrll #define BR	0x32000000
    855   1.1.1.2  christos #define BRSL	0x33000000
    856       1.1     skrll #define NOP	0x40200000
    857       1.1     skrll #define LNOP	0x00200000
    858       1.1     skrll #define ILA	0x42000000
    859       1.1     skrll 
    860       1.1     skrll /* Return true for all relative and absolute branch instructions.
    861       1.1     skrll    bra   00110000 0..
    862       1.1     skrll    brasl 00110001 0..
    863       1.1     skrll    br    00110010 0..
    864       1.1     skrll    brsl  00110011 0..
    865       1.1     skrll    brz   00100000 0..
    866       1.1     skrll    brnz  00100001 0..
    867       1.1     skrll    brhz  00100010 0..
    868       1.1     skrll    brhnz 00100011 0..  */
    869       1.1     skrll 
    870   1.1.1.9  christos static bool
    871       1.1     skrll is_branch (const unsigned char *insn)
    872       1.1     skrll {
    873       1.1     skrll   return (insn[0] & 0xec) == 0x20 && (insn[1] & 0x80) == 0;
    874       1.1     skrll }
    875       1.1     skrll 
    876       1.1     skrll /* Return true for all indirect branch instructions.
    877       1.1     skrll    bi     00110101 000
    878       1.1     skrll    bisl   00110101 001
    879       1.1     skrll    iret   00110101 010
    880       1.1     skrll    bisled 00110101 011
    881       1.1     skrll    biz    00100101 000
    882       1.1     skrll    binz   00100101 001
    883       1.1     skrll    bihz   00100101 010
    884       1.1     skrll    bihnz  00100101 011  */
    885       1.1     skrll 
    886   1.1.1.9  christos static bool
    887       1.1     skrll is_indirect_branch (const unsigned char *insn)
    888       1.1     skrll {
    889       1.1     skrll   return (insn[0] & 0xef) == 0x25 && (insn[1] & 0x80) == 0;
    890       1.1     skrll }
    891       1.1     skrll 
    892       1.1     skrll /* Return true for branch hint instructions.
    893       1.1     skrll    hbra  0001000..
    894       1.1     skrll    hbrr  0001001..  */
    895       1.1     skrll 
    896   1.1.1.9  christos static bool
    897       1.1     skrll is_hint (const unsigned char *insn)
    898       1.1     skrll {
    899       1.1     skrll   return (insn[0] & 0xfc) == 0x10;
    900       1.1     skrll }
    901       1.1     skrll 
    902       1.1     skrll /* True if INPUT_SECTION might need overlay stubs.  */
    903       1.1     skrll 
    904   1.1.1.9  christos static bool
    905   1.1.1.2  christos maybe_needs_stubs (asection *input_section)
    906       1.1     skrll {
    907       1.1     skrll   /* No stubs for debug sections and suchlike.  */
    908       1.1     skrll   if ((input_section->flags & SEC_ALLOC) == 0)
    909   1.1.1.9  christos     return false;
    910       1.1     skrll 
    911       1.1     skrll   /* No stubs for link-once sections that will be discarded.  */
    912   1.1.1.2  christos   if (input_section->output_section == bfd_abs_section_ptr)
    913   1.1.1.9  christos     return false;
    914       1.1     skrll 
    915       1.1     skrll   /* Don't create stubs for .eh_frame references.  */
    916       1.1     skrll   if (strcmp (input_section->name, ".eh_frame") == 0)
    917   1.1.1.9  christos     return false;
    918       1.1     skrll 
    919   1.1.1.9  christos   return true;
    920       1.1     skrll }
    921       1.1     skrll 
    922       1.1     skrll enum _stub_type
    923       1.1     skrll {
    924       1.1     skrll   no_stub,
    925   1.1.1.2  christos   call_ovl_stub,
    926   1.1.1.2  christos   br000_ovl_stub,
    927   1.1.1.2  christos   br001_ovl_stub,
    928   1.1.1.2  christos   br010_ovl_stub,
    929   1.1.1.2  christos   br011_ovl_stub,
    930   1.1.1.2  christos   br100_ovl_stub,
    931   1.1.1.2  christos   br101_ovl_stub,
    932   1.1.1.2  christos   br110_ovl_stub,
    933   1.1.1.2  christos   br111_ovl_stub,
    934       1.1     skrll   nonovl_stub,
    935       1.1     skrll   stub_error
    936       1.1     skrll };
    937       1.1     skrll 
    938       1.1     skrll /* Return non-zero if this reloc symbol should go via an overlay stub.
    939       1.1     skrll    Return 2 if the stub must be in non-overlay area.  */
    940       1.1     skrll 
    941       1.1     skrll static enum _stub_type
    942       1.1     skrll needs_ovl_stub (struct elf_link_hash_entry *h,
    943       1.1     skrll 		Elf_Internal_Sym *sym,
    944       1.1     skrll 		asection *sym_sec,
    945       1.1     skrll 		asection *input_section,
    946       1.1     skrll 		Elf_Internal_Rela *irela,
    947       1.1     skrll 		bfd_byte *contents,
    948       1.1     skrll 		struct bfd_link_info *info)
    949       1.1     skrll {
    950       1.1     skrll   struct spu_link_hash_table *htab = spu_hash_table (info);
    951       1.1     skrll   enum elf_spu_reloc_type r_type;
    952       1.1     skrll   unsigned int sym_type;
    953   1.1.1.9  christos   bool branch, hint, call;
    954       1.1     skrll   enum _stub_type ret = no_stub;
    955   1.1.1.2  christos   bfd_byte insn[4];
    956       1.1     skrll 
    957       1.1     skrll   if (sym_sec == NULL
    958   1.1.1.2  christos       || sym_sec->output_section == bfd_abs_section_ptr
    959       1.1     skrll       || spu_elf_section_data (sym_sec->output_section) == NULL)
    960       1.1     skrll     return ret;
    961       1.1     skrll 
    962       1.1     skrll   if (h != NULL)
    963       1.1     skrll     {
    964       1.1     skrll       /* Ensure no stubs for user supplied overlay manager syms.  */
    965   1.1.1.2  christos       if (h == htab->ovly_entry[0] || h == htab->ovly_entry[1])
    966       1.1     skrll 	return ret;
    967       1.1     skrll 
    968       1.1     skrll       /* setjmp always goes via an overlay stub, because then the return
    969       1.1     skrll 	 and hence the longjmp goes via __ovly_return.  That magically
    970       1.1     skrll 	 makes setjmp/longjmp between overlays work.  */
    971   1.1.1.9  christos       if (startswith (h->root.root.string, "setjmp")
    972       1.1     skrll 	  && (h->root.root.string[6] == '\0' || h->root.root.string[6] == '@'))
    973   1.1.1.2  christos 	ret = call_ovl_stub;
    974       1.1     skrll     }
    975       1.1     skrll 
    976       1.1     skrll   if (h != NULL)
    977       1.1     skrll     sym_type = h->type;
    978       1.1     skrll   else
    979       1.1     skrll     sym_type = ELF_ST_TYPE (sym->st_info);
    980       1.1     skrll 
    981       1.1     skrll   r_type = ELF32_R_TYPE (irela->r_info);
    982   1.1.1.9  christos   branch = false;
    983   1.1.1.9  christos   hint = false;
    984   1.1.1.9  christos   call = false;
    985       1.1     skrll   if (r_type == R_SPU_REL16 || r_type == R_SPU_ADDR16)
    986       1.1     skrll     {
    987       1.1     skrll       if (contents == NULL)
    988       1.1     skrll 	{
    989       1.1     skrll 	  contents = insn;
    990       1.1     skrll 	  if (!bfd_get_section_contents (input_section->owner,
    991       1.1     skrll 					 input_section,
    992       1.1     skrll 					 contents,
    993       1.1     skrll 					 irela->r_offset, 4))
    994       1.1     skrll 	    return stub_error;
    995       1.1     skrll 	}
    996       1.1     skrll       else
    997       1.1     skrll 	contents += irela->r_offset;
    998       1.1     skrll 
    999   1.1.1.2  christos       branch = is_branch (contents);
   1000   1.1.1.2  christos       hint = is_hint (contents);
   1001   1.1.1.2  christos       if (branch || hint)
   1002       1.1     skrll 	{
   1003   1.1.1.2  christos 	  call = (contents[0] & 0xfd) == 0x31;
   1004   1.1.1.2  christos 	  if (call
   1005       1.1     skrll 	      && sym_type != STT_FUNC
   1006       1.1     skrll 	      && contents != insn)
   1007       1.1     skrll 	    {
   1008       1.1     skrll 	      /* It's common for people to write assembly and forget
   1009       1.1     skrll 		 to give function symbols the right type.  Handle
   1010       1.1     skrll 		 calls to such symbols, but warn so that (hopefully)
   1011       1.1     skrll 		 people will fix their code.  We need the symbol
   1012       1.1     skrll 		 type to be correct to distinguish function pointer
   1013       1.1     skrll 		 initialisation from other pointer initialisations.  */
   1014       1.1     skrll 	      const char *sym_name;
   1015       1.1     skrll 
   1016       1.1     skrll 	      if (h != NULL)
   1017       1.1     skrll 		sym_name = h->root.root.string;
   1018       1.1     skrll 	      else
   1019       1.1     skrll 		{
   1020       1.1     skrll 		  Elf_Internal_Shdr *symtab_hdr;
   1021       1.1     skrll 		  symtab_hdr = &elf_tdata (input_section->owner)->symtab_hdr;
   1022       1.1     skrll 		  sym_name = bfd_elf_sym_name (input_section->owner,
   1023       1.1     skrll 					       symtab_hdr,
   1024       1.1     skrll 					       sym,
   1025       1.1     skrll 					       sym_sec);
   1026       1.1     skrll 		}
   1027   1.1.1.6  christos 	      _bfd_error_handler
   1028   1.1.1.6  christos 		/* xgettext:c-format */
   1029   1.1.1.7  christos 		(_("warning: call to non-function symbol %s defined in %pB"),
   1030   1.1.1.6  christos 		 sym_name, sym_sec->owner);
   1031       1.1     skrll 
   1032       1.1     skrll 	    }
   1033       1.1     skrll 	}
   1034       1.1     skrll     }
   1035       1.1     skrll 
   1036   1.1.1.2  christos   if ((!branch && htab->params->ovly_flavour == ovly_soft_icache)
   1037   1.1.1.2  christos       || (sym_type != STT_FUNC
   1038   1.1.1.2  christos 	  && !(branch || hint)
   1039   1.1.1.2  christos 	  && (sym_sec->flags & SEC_CODE) == 0))
   1040   1.1.1.2  christos     return no_stub;
   1041   1.1.1.2  christos 
   1042   1.1.1.2  christos   /* Usually, symbols in non-overlay sections don't need stubs.  */
   1043   1.1.1.2  christos   if (spu_elf_section_data (sym_sec->output_section)->u.o.ovl_index == 0
   1044   1.1.1.2  christos       && !htab->params->non_overlay_stubs)
   1045       1.1     skrll     return ret;
   1046       1.1     skrll 
   1047       1.1     skrll   /* A reference from some other section to a symbol in an overlay
   1048       1.1     skrll      section needs a stub.  */
   1049       1.1     skrll   if (spu_elf_section_data (sym_sec->output_section)->u.o.ovl_index
   1050       1.1     skrll        != spu_elf_section_data (input_section->output_section)->u.o.ovl_index)
   1051   1.1.1.2  christos     {
   1052   1.1.1.2  christos       unsigned int lrlive = 0;
   1053   1.1.1.2  christos       if (branch)
   1054   1.1.1.2  christos 	lrlive = (contents[1] & 0x70) >> 4;
   1055   1.1.1.2  christos 
   1056   1.1.1.2  christos       if (!lrlive && (call || sym_type == STT_FUNC))
   1057   1.1.1.2  christos 	ret = call_ovl_stub;
   1058   1.1.1.2  christos       else
   1059   1.1.1.2  christos 	ret = br000_ovl_stub + lrlive;
   1060   1.1.1.2  christos     }
   1061       1.1     skrll 
   1062       1.1     skrll   /* If this insn isn't a branch then we are possibly taking the
   1063   1.1.1.2  christos      address of a function and passing it out somehow.  Soft-icache code
   1064   1.1.1.2  christos      always generates inline code to do indirect branches.  */
   1065   1.1.1.2  christos   if (!(branch || hint)
   1066   1.1.1.2  christos       && sym_type == STT_FUNC
   1067   1.1.1.2  christos       && htab->params->ovly_flavour != ovly_soft_icache)
   1068   1.1.1.2  christos     ret = nonovl_stub;
   1069   1.1.1.2  christos 
   1070   1.1.1.2  christos   return ret;
   1071       1.1     skrll }
   1072       1.1     skrll 
   1073   1.1.1.9  christos static bool
   1074       1.1     skrll count_stub (struct spu_link_hash_table *htab,
   1075       1.1     skrll 	    bfd *ibfd,
   1076       1.1     skrll 	    asection *isec,
   1077       1.1     skrll 	    enum _stub_type stub_type,
   1078       1.1     skrll 	    struct elf_link_hash_entry *h,
   1079       1.1     skrll 	    const Elf_Internal_Rela *irela)
   1080       1.1     skrll {
   1081       1.1     skrll   unsigned int ovl = 0;
   1082       1.1     skrll   struct got_entry *g, **head;
   1083       1.1     skrll   bfd_vma addend;
   1084       1.1     skrll 
   1085       1.1     skrll   /* If this instruction is a branch or call, we need a stub
   1086       1.1     skrll      for it.  One stub per function per overlay.
   1087       1.1     skrll      If it isn't a branch, then we are taking the address of
   1088       1.1     skrll      this function so need a stub in the non-overlay area
   1089       1.1     skrll      for it.  One stub per function.  */
   1090       1.1     skrll   if (stub_type != nonovl_stub)
   1091       1.1     skrll     ovl = spu_elf_section_data (isec->output_section)->u.o.ovl_index;
   1092       1.1     skrll 
   1093       1.1     skrll   if (h != NULL)
   1094       1.1     skrll     head = &h->got.glist;
   1095       1.1     skrll   else
   1096       1.1     skrll     {
   1097       1.1     skrll       if (elf_local_got_ents (ibfd) == NULL)
   1098       1.1     skrll 	{
   1099       1.1     skrll 	  bfd_size_type amt = (elf_tdata (ibfd)->symtab_hdr.sh_info
   1100       1.1     skrll 			       * sizeof (*elf_local_got_ents (ibfd)));
   1101       1.1     skrll 	  elf_local_got_ents (ibfd) = bfd_zmalloc (amt);
   1102       1.1     skrll 	  if (elf_local_got_ents (ibfd) == NULL)
   1103   1.1.1.9  christos 	    return false;
   1104       1.1     skrll 	}
   1105       1.1     skrll       head = elf_local_got_ents (ibfd) + ELF32_R_SYM (irela->r_info);
   1106       1.1     skrll     }
   1107       1.1     skrll 
   1108   1.1.1.2  christos   if (htab->params->ovly_flavour == ovly_soft_icache)
   1109   1.1.1.2  christos     {
   1110   1.1.1.2  christos       htab->stub_count[ovl] += 1;
   1111   1.1.1.9  christos       return true;
   1112   1.1.1.2  christos     }
   1113   1.1.1.2  christos 
   1114       1.1     skrll   addend = 0;
   1115       1.1     skrll   if (irela != NULL)
   1116       1.1     skrll     addend = irela->r_addend;
   1117       1.1     skrll 
   1118       1.1     skrll   if (ovl == 0)
   1119       1.1     skrll     {
   1120       1.1     skrll       struct got_entry *gnext;
   1121       1.1     skrll 
   1122       1.1     skrll       for (g = *head; g != NULL; g = g->next)
   1123       1.1     skrll 	if (g->addend == addend && g->ovl == 0)
   1124       1.1     skrll 	  break;
   1125       1.1     skrll 
   1126       1.1     skrll       if (g == NULL)
   1127       1.1     skrll 	{
   1128       1.1     skrll 	  /* Need a new non-overlay area stub.  Zap other stubs.  */
   1129       1.1     skrll 	  for (g = *head; g != NULL; g = gnext)
   1130       1.1     skrll 	    {
   1131       1.1     skrll 	      gnext = g->next;
   1132       1.1     skrll 	      if (g->addend == addend)
   1133       1.1     skrll 		{
   1134       1.1     skrll 		  htab->stub_count[g->ovl] -= 1;
   1135       1.1     skrll 		  free (g);
   1136       1.1     skrll 		}
   1137       1.1     skrll 	    }
   1138       1.1     skrll 	}
   1139       1.1     skrll     }
   1140       1.1     skrll   else
   1141       1.1     skrll     {
   1142       1.1     skrll       for (g = *head; g != NULL; g = g->next)
   1143       1.1     skrll 	if (g->addend == addend && (g->ovl == ovl || g->ovl == 0))
   1144       1.1     skrll 	  break;
   1145       1.1     skrll     }
   1146       1.1     skrll 
   1147       1.1     skrll   if (g == NULL)
   1148       1.1     skrll     {
   1149       1.1     skrll       g = bfd_malloc (sizeof *g);
   1150       1.1     skrll       if (g == NULL)
   1151   1.1.1.9  christos 	return false;
   1152       1.1     skrll       g->ovl = ovl;
   1153       1.1     skrll       g->addend = addend;
   1154       1.1     skrll       g->stub_addr = (bfd_vma) -1;
   1155       1.1     skrll       g->next = *head;
   1156       1.1     skrll       *head = g;
   1157       1.1     skrll 
   1158       1.1     skrll       htab->stub_count[ovl] += 1;
   1159       1.1     skrll     }
   1160       1.1     skrll 
   1161   1.1.1.9  christos   return true;
   1162       1.1     skrll }
   1163       1.1     skrll 
   1164   1.1.1.2  christos /* Support two sizes of overlay stubs, a slower more compact stub of two
   1165   1.1.1.4  christos    instructions, and a faster stub of four instructions.
   1166   1.1.1.2  christos    Soft-icache stubs are four or eight words.  */
   1167   1.1.1.2  christos 
   1168   1.1.1.2  christos static unsigned int
   1169   1.1.1.2  christos ovl_stub_size (struct spu_elf_params *params)
   1170   1.1.1.2  christos {
   1171   1.1.1.2  christos   return 16 << params->ovly_flavour >> params->compact_stub;
   1172   1.1.1.2  christos }
   1173   1.1.1.2  christos 
   1174   1.1.1.2  christos static unsigned int
   1175   1.1.1.2  christos ovl_stub_size_log2 (struct spu_elf_params *params)
   1176   1.1.1.2  christos {
   1177   1.1.1.2  christos   return 4 + params->ovly_flavour - params->compact_stub;
   1178   1.1.1.2  christos }
   1179   1.1.1.2  christos 
   1180       1.1     skrll /* Two instruction overlay stubs look like:
   1181       1.1     skrll 
   1182       1.1     skrll    brsl $75,__ovly_load
   1183       1.1     skrll    .word target_ovl_and_address
   1184       1.1     skrll 
   1185       1.1     skrll    ovl_and_address is a word with the overlay number in the top 14 bits
   1186       1.1     skrll    and local store address in the bottom 18 bits.
   1187       1.1     skrll 
   1188       1.1     skrll    Four instruction overlay stubs look like:
   1189       1.1     skrll 
   1190       1.1     skrll    ila $78,ovl_number
   1191       1.1     skrll    lnop
   1192       1.1     skrll    ila $79,target_address
   1193   1.1.1.2  christos    br __ovly_load
   1194   1.1.1.2  christos 
   1195   1.1.1.2  christos    Software icache stubs are:
   1196   1.1.1.2  christos 
   1197   1.1.1.2  christos    .word target_index
   1198   1.1.1.2  christos    .word target_ia;
   1199   1.1.1.2  christos    .word lrlive_branchlocalstoreaddr;
   1200   1.1.1.2  christos    brasl $75,__icache_br_handler
   1201   1.1.1.2  christos    .quad xor_pattern
   1202   1.1.1.2  christos */
   1203       1.1     skrll 
   1204   1.1.1.9  christos static bool
   1205   1.1.1.2  christos build_stub (struct bfd_link_info *info,
   1206       1.1     skrll 	    bfd *ibfd,
   1207       1.1     skrll 	    asection *isec,
   1208       1.1     skrll 	    enum _stub_type stub_type,
   1209       1.1     skrll 	    struct elf_link_hash_entry *h,
   1210       1.1     skrll 	    const Elf_Internal_Rela *irela,
   1211       1.1     skrll 	    bfd_vma dest,
   1212       1.1     skrll 	    asection *dest_sec)
   1213       1.1     skrll {
   1214   1.1.1.2  christos   struct spu_link_hash_table *htab = spu_hash_table (info);
   1215   1.1.1.2  christos   unsigned int ovl, dest_ovl, set_id;
   1216       1.1     skrll   struct got_entry *g, **head;
   1217       1.1     skrll   asection *sec;
   1218   1.1.1.2  christos   bfd_vma addend, from, to, br_dest, patt;
   1219   1.1.1.2  christos   unsigned int lrlive;
   1220       1.1     skrll 
   1221       1.1     skrll   ovl = 0;
   1222       1.1     skrll   if (stub_type != nonovl_stub)
   1223       1.1     skrll     ovl = spu_elf_section_data (isec->output_section)->u.o.ovl_index;
   1224       1.1     skrll 
   1225       1.1     skrll   if (h != NULL)
   1226       1.1     skrll     head = &h->got.glist;
   1227       1.1     skrll   else
   1228       1.1     skrll     head = elf_local_got_ents (ibfd) + ELF32_R_SYM (irela->r_info);
   1229       1.1     skrll 
   1230       1.1     skrll   addend = 0;
   1231       1.1     skrll   if (irela != NULL)
   1232       1.1     skrll     addend = irela->r_addend;
   1233       1.1     skrll 
   1234   1.1.1.2  christos   if (htab->params->ovly_flavour == ovly_soft_icache)
   1235   1.1.1.2  christos     {
   1236   1.1.1.2  christos       g = bfd_malloc (sizeof *g);
   1237   1.1.1.2  christos       if (g == NULL)
   1238   1.1.1.9  christos 	return false;
   1239   1.1.1.2  christos       g->ovl = ovl;
   1240   1.1.1.2  christos       g->br_addr = 0;
   1241   1.1.1.2  christos       if (irela != NULL)
   1242   1.1.1.2  christos 	g->br_addr = (irela->r_offset
   1243   1.1.1.2  christos 		      + isec->output_offset
   1244   1.1.1.2  christos 		      + isec->output_section->vma);
   1245   1.1.1.2  christos       g->next = *head;
   1246   1.1.1.2  christos       *head = g;
   1247   1.1.1.2  christos     }
   1248   1.1.1.2  christos   else
   1249   1.1.1.2  christos     {
   1250   1.1.1.2  christos       for (g = *head; g != NULL; g = g->next)
   1251   1.1.1.2  christos 	if (g->addend == addend && (g->ovl == ovl || g->ovl == 0))
   1252   1.1.1.2  christos 	  break;
   1253   1.1.1.2  christos       if (g == NULL)
   1254   1.1.1.2  christos 	abort ();
   1255       1.1     skrll 
   1256   1.1.1.2  christos       if (g->ovl == 0 && ovl != 0)
   1257   1.1.1.9  christos 	return true;
   1258       1.1     skrll 
   1259   1.1.1.2  christos       if (g->stub_addr != (bfd_vma) -1)
   1260   1.1.1.9  christos 	return true;
   1261   1.1.1.2  christos     }
   1262       1.1     skrll 
   1263       1.1     skrll   sec = htab->stub_sec[ovl];
   1264       1.1     skrll   dest += dest_sec->output_offset + dest_sec->output_section->vma;
   1265       1.1     skrll   from = sec->size + sec->output_offset + sec->output_section->vma;
   1266       1.1     skrll   g->stub_addr = from;
   1267   1.1.1.2  christos   to = (htab->ovly_entry[0]->root.u.def.value
   1268   1.1.1.2  christos 	+ htab->ovly_entry[0]->root.u.def.section->output_offset
   1269   1.1.1.2  christos 	+ htab->ovly_entry[0]->root.u.def.section->output_section->vma);
   1270   1.1.1.2  christos 
   1271   1.1.1.2  christos   if (((dest | to | from) & 3) != 0)
   1272       1.1     skrll     {
   1273       1.1     skrll       htab->stub_err = 1;
   1274   1.1.1.9  christos       return false;
   1275       1.1     skrll     }
   1276   1.1.1.2  christos   dest_ovl = spu_elf_section_data (dest_sec->output_section)->u.o.ovl_index;
   1277       1.1     skrll 
   1278   1.1.1.2  christos   if (htab->params->ovly_flavour == ovly_normal
   1279   1.1.1.2  christos       && !htab->params->compact_stub)
   1280       1.1     skrll     {
   1281   1.1.1.2  christos       bfd_put_32 (sec->owner, ILA + ((dest_ovl << 7) & 0x01ffff80) + 78,
   1282       1.1     skrll 		  sec->contents + sec->size);
   1283       1.1     skrll       bfd_put_32 (sec->owner, LNOP,
   1284       1.1     skrll 		  sec->contents + sec->size + 4);
   1285       1.1     skrll       bfd_put_32 (sec->owner, ILA + ((dest << 7) & 0x01ffff80) + 79,
   1286       1.1     skrll 		  sec->contents + sec->size + 8);
   1287   1.1.1.2  christos       if (!BRA_STUBS)
   1288   1.1.1.2  christos 	bfd_put_32 (sec->owner, BR + (((to - (from + 12)) << 5) & 0x007fff80),
   1289   1.1.1.2  christos 		    sec->contents + sec->size + 12);
   1290   1.1.1.2  christos       else
   1291   1.1.1.2  christos 	bfd_put_32 (sec->owner, BRA + ((to << 5) & 0x007fff80),
   1292   1.1.1.2  christos 		    sec->contents + sec->size + 12);
   1293       1.1     skrll     }
   1294   1.1.1.2  christos   else if (htab->params->ovly_flavour == ovly_normal
   1295   1.1.1.2  christos 	   && htab->params->compact_stub)
   1296       1.1     skrll     {
   1297   1.1.1.2  christos       if (!BRA_STUBS)
   1298   1.1.1.2  christos 	bfd_put_32 (sec->owner, BRSL + (((to - from) << 5) & 0x007fff80) + 75,
   1299   1.1.1.2  christos 		    sec->contents + sec->size);
   1300   1.1.1.2  christos       else
   1301   1.1.1.2  christos 	bfd_put_32 (sec->owner, BRASL + ((to << 5) & 0x007fff80) + 75,
   1302   1.1.1.2  christos 		    sec->contents + sec->size);
   1303   1.1.1.2  christos       bfd_put_32 (sec->owner, (dest & 0x3ffff) | (dest_ovl << 18),
   1304   1.1.1.2  christos 		  sec->contents + sec->size + 4);
   1305   1.1.1.2  christos     }
   1306   1.1.1.2  christos   else if (htab->params->ovly_flavour == ovly_soft_icache
   1307   1.1.1.2  christos 	   && htab->params->compact_stub)
   1308   1.1.1.2  christos     {
   1309   1.1.1.2  christos       lrlive = 0;
   1310   1.1.1.2  christos       if (stub_type == nonovl_stub)
   1311   1.1.1.2  christos 	;
   1312   1.1.1.2  christos       else if (stub_type == call_ovl_stub)
   1313   1.1.1.2  christos 	/* A brsl makes lr live and *(*sp+16) is live.
   1314   1.1.1.2  christos 	   Tail calls have the same liveness.  */
   1315   1.1.1.2  christos 	lrlive = 5;
   1316   1.1.1.2  christos       else if (!htab->params->lrlive_analysis)
   1317   1.1.1.2  christos 	/* Assume stack frame and lr save.  */
   1318   1.1.1.2  christos 	lrlive = 1;
   1319   1.1.1.2  christos       else if (irela != NULL)
   1320   1.1.1.2  christos 	{
   1321   1.1.1.2  christos 	  /* Analyse branch instructions.  */
   1322   1.1.1.2  christos 	  struct function_info *caller;
   1323   1.1.1.2  christos 	  bfd_vma off;
   1324   1.1.1.2  christos 
   1325   1.1.1.2  christos 	  caller = find_function (isec, irela->r_offset, info);
   1326   1.1.1.2  christos 	  if (caller->start == NULL)
   1327   1.1.1.2  christos 	    off = irela->r_offset;
   1328   1.1.1.2  christos 	  else
   1329   1.1.1.2  christos 	    {
   1330   1.1.1.2  christos 	      struct function_info *found = NULL;
   1331   1.1.1.2  christos 
   1332   1.1.1.2  christos 	      /* Find the earliest piece of this function that
   1333   1.1.1.2  christos 		 has frame adjusting instructions.  We might
   1334   1.1.1.2  christos 		 see dynamic frame adjustment (eg. for alloca)
   1335   1.1.1.2  christos 		 in some later piece, but functions using
   1336   1.1.1.2  christos 		 alloca always set up a frame earlier.  Frame
   1337   1.1.1.2  christos 		 setup instructions are always in one piece.  */
   1338   1.1.1.2  christos 	      if (caller->lr_store != (bfd_vma) -1
   1339   1.1.1.2  christos 		  || caller->sp_adjust != (bfd_vma) -1)
   1340   1.1.1.2  christos 		found = caller;
   1341   1.1.1.2  christos 	      while (caller->start != NULL)
   1342   1.1.1.2  christos 		{
   1343   1.1.1.2  christos 		  caller = caller->start;
   1344   1.1.1.2  christos 		  if (caller->lr_store != (bfd_vma) -1
   1345   1.1.1.2  christos 		      || caller->sp_adjust != (bfd_vma) -1)
   1346   1.1.1.2  christos 		    found = caller;
   1347   1.1.1.2  christos 		}
   1348   1.1.1.2  christos 	      if (found != NULL)
   1349   1.1.1.2  christos 		caller = found;
   1350   1.1.1.2  christos 	      off = (bfd_vma) -1;
   1351   1.1.1.2  christos 	    }
   1352   1.1.1.2  christos 
   1353   1.1.1.2  christos 	  if (off > caller->sp_adjust)
   1354   1.1.1.2  christos 	    {
   1355   1.1.1.2  christos 	      if (off > caller->lr_store)
   1356   1.1.1.2  christos 		/* Only *(*sp+16) is live.  */
   1357   1.1.1.2  christos 		lrlive = 1;
   1358   1.1.1.2  christos 	      else
   1359   1.1.1.2  christos 		/* If no lr save, then we must be in a
   1360   1.1.1.2  christos 		   leaf function with a frame.
   1361   1.1.1.2  christos 		   lr is still live.  */
   1362   1.1.1.2  christos 		lrlive = 4;
   1363   1.1.1.2  christos 	    }
   1364   1.1.1.2  christos 	  else if (off > caller->lr_store)
   1365   1.1.1.2  christos 	    {
   1366   1.1.1.2  christos 	      /* Between lr save and stack adjust.  */
   1367   1.1.1.2  christos 	      lrlive = 3;
   1368   1.1.1.2  christos 	      /* This should never happen since prologues won't
   1369   1.1.1.2  christos 		 be split here.  */
   1370   1.1.1.2  christos 	      BFD_ASSERT (0);
   1371   1.1.1.2  christos 	    }
   1372   1.1.1.2  christos 	  else
   1373   1.1.1.2  christos 	    /* On entry to function.  */
   1374   1.1.1.2  christos 	    lrlive = 5;
   1375   1.1.1.2  christos 
   1376   1.1.1.2  christos 	  if (stub_type != br000_ovl_stub
   1377   1.1.1.2  christos 	      && lrlive != stub_type - br000_ovl_stub)
   1378   1.1.1.6  christos 	    /* xgettext:c-format */
   1379   1.1.1.7  christos 	    info->callbacks->einfo (_("%pA:0x%v lrlive .brinfo (%u) differs "
   1380   1.1.1.2  christos 				      "from analysis (%u)\n"),
   1381   1.1.1.2  christos 				    isec, irela->r_offset, lrlive,
   1382   1.1.1.2  christos 				    stub_type - br000_ovl_stub);
   1383   1.1.1.2  christos 	}
   1384   1.1.1.2  christos 
   1385   1.1.1.2  christos       /* If given lrlive info via .brinfo, use it.  */
   1386   1.1.1.2  christos       if (stub_type > br000_ovl_stub)
   1387   1.1.1.2  christos 	lrlive = stub_type - br000_ovl_stub;
   1388   1.1.1.2  christos 
   1389   1.1.1.2  christos       if (ovl == 0)
   1390   1.1.1.2  christos 	to = (htab->ovly_entry[1]->root.u.def.value
   1391   1.1.1.2  christos 	      + htab->ovly_entry[1]->root.u.def.section->output_offset
   1392   1.1.1.2  christos 	      + htab->ovly_entry[1]->root.u.def.section->output_section->vma);
   1393   1.1.1.2  christos 
   1394   1.1.1.2  christos       /* The branch that uses this stub goes to stub_addr + 4.  We'll
   1395   1.1.1.2  christos 	 set up an xor pattern that can be used by the icache manager
   1396   1.1.1.2  christos 	 to modify this branch to go directly to its destination.  */
   1397   1.1.1.2  christos       g->stub_addr += 4;
   1398   1.1.1.2  christos       br_dest = g->stub_addr;
   1399   1.1.1.2  christos       if (irela == NULL)
   1400   1.1.1.2  christos 	{
   1401   1.1.1.2  christos 	  /* Except in the case of _SPUEAR_ stubs, the branch in
   1402   1.1.1.2  christos 	     question is the one in the stub itself.  */
   1403   1.1.1.2  christos 	  BFD_ASSERT (stub_type == nonovl_stub);
   1404   1.1.1.2  christos 	  g->br_addr = g->stub_addr;
   1405   1.1.1.2  christos 	  br_dest = to;
   1406   1.1.1.2  christos 	}
   1407       1.1     skrll 
   1408   1.1.1.2  christos       set_id = ((dest_ovl - 1) >> htab->num_lines_log2) + 1;
   1409   1.1.1.2  christos       bfd_put_32 (sec->owner, (set_id << 18) | (dest & 0x3ffff),
   1410   1.1.1.2  christos 		  sec->contents + sec->size);
   1411   1.1.1.2  christos       bfd_put_32 (sec->owner, BRASL + ((to << 5) & 0x007fff80) + 75,
   1412       1.1     skrll 		  sec->contents + sec->size + 4);
   1413   1.1.1.2  christos       bfd_put_32 (sec->owner, (lrlive << 29) | (g->br_addr & 0x3ffff),
   1414   1.1.1.2  christos 		  sec->contents + sec->size + 8);
   1415   1.1.1.2  christos       patt = dest ^ br_dest;
   1416   1.1.1.2  christos       if (irela != NULL && ELF32_R_TYPE (irela->r_info) == R_SPU_REL16)
   1417   1.1.1.2  christos 	patt = (dest - g->br_addr) ^ (br_dest - g->br_addr);
   1418   1.1.1.2  christos       bfd_put_32 (sec->owner, (patt << 5) & 0x007fff80,
   1419   1.1.1.2  christos 		  sec->contents + sec->size + 12);
   1420   1.1.1.2  christos 
   1421   1.1.1.2  christos       if (ovl == 0)
   1422   1.1.1.2  christos 	/* Extra space for linked list entries.  */
   1423   1.1.1.2  christos 	sec->size += 16;
   1424       1.1     skrll     }
   1425       1.1     skrll   else
   1426       1.1     skrll     abort ();
   1427       1.1     skrll 
   1428   1.1.1.2  christos   sec->size += ovl_stub_size (htab->params);
   1429   1.1.1.2  christos 
   1430   1.1.1.2  christos   if (htab->params->emit_stub_syms)
   1431       1.1     skrll     {
   1432       1.1     skrll       size_t len;
   1433       1.1     skrll       char *name;
   1434       1.1     skrll       int add;
   1435       1.1     skrll 
   1436       1.1     skrll       len = 8 + sizeof (".ovl_call.") - 1;
   1437       1.1     skrll       if (h != NULL)
   1438       1.1     skrll 	len += strlen (h->root.root.string);
   1439       1.1     skrll       else
   1440       1.1     skrll 	len += 8 + 1 + 8;
   1441       1.1     skrll       add = 0;
   1442       1.1     skrll       if (irela != NULL)
   1443       1.1     skrll 	add = (int) irela->r_addend & 0xffffffff;
   1444       1.1     skrll       if (add != 0)
   1445       1.1     skrll 	len += 1 + 8;
   1446   1.1.1.3  christos       name = bfd_malloc (len + 1);
   1447       1.1     skrll       if (name == NULL)
   1448   1.1.1.9  christos 	return false;
   1449       1.1     skrll 
   1450       1.1     skrll       sprintf (name, "%08x.ovl_call.", g->ovl);
   1451       1.1     skrll       if (h != NULL)
   1452       1.1     skrll 	strcpy (name + 8 + sizeof (".ovl_call.") - 1, h->root.root.string);
   1453       1.1     skrll       else
   1454       1.1     skrll 	sprintf (name + 8 + sizeof (".ovl_call.") - 1, "%x:%x",
   1455       1.1     skrll 		 dest_sec->id & 0xffffffff,
   1456       1.1     skrll 		 (int) ELF32_R_SYM (irela->r_info) & 0xffffffff);
   1457       1.1     skrll       if (add != 0)
   1458       1.1     skrll 	sprintf (name + len - 9, "+%x", add);
   1459       1.1     skrll 
   1460   1.1.1.9  christos       h = elf_link_hash_lookup (&htab->elf, name, true, true, false);
   1461       1.1     skrll       free (name);
   1462       1.1     skrll       if (h == NULL)
   1463   1.1.1.9  christos 	return false;
   1464       1.1     skrll       if (h->root.type == bfd_link_hash_new)
   1465       1.1     skrll 	{
   1466       1.1     skrll 	  h->root.type = bfd_link_hash_defined;
   1467       1.1     skrll 	  h->root.u.def.section = sec;
   1468   1.1.1.2  christos 	  h->size = ovl_stub_size (htab->params);
   1469   1.1.1.2  christos 	  h->root.u.def.value = sec->size - h->size;
   1470       1.1     skrll 	  h->type = STT_FUNC;
   1471       1.1     skrll 	  h->ref_regular = 1;
   1472       1.1     skrll 	  h->def_regular = 1;
   1473       1.1     skrll 	  h->ref_regular_nonweak = 1;
   1474       1.1     skrll 	  h->forced_local = 1;
   1475       1.1     skrll 	  h->non_elf = 0;
   1476       1.1     skrll 	}
   1477       1.1     skrll     }
   1478       1.1     skrll 
   1479   1.1.1.9  christos   return true;
   1480       1.1     skrll }
   1481       1.1     skrll 
   1482       1.1     skrll /* Called via elf_link_hash_traverse to allocate stubs for any _SPUEAR_
   1483       1.1     skrll    symbols.  */
   1484       1.1     skrll 
   1485   1.1.1.9  christos static bool
   1486       1.1     skrll allocate_spuear_stubs (struct elf_link_hash_entry *h, void *inf)
   1487       1.1     skrll {
   1488       1.1     skrll   /* Symbols starting with _SPUEAR_ need a stub because they may be
   1489       1.1     skrll      invoked by the PPU.  */
   1490       1.1     skrll   struct bfd_link_info *info = inf;
   1491       1.1     skrll   struct spu_link_hash_table *htab = spu_hash_table (info);
   1492       1.1     skrll   asection *sym_sec;
   1493       1.1     skrll 
   1494       1.1     skrll   if ((h->root.type == bfd_link_hash_defined
   1495       1.1     skrll        || h->root.type == bfd_link_hash_defweak)
   1496       1.1     skrll       && h->def_regular
   1497   1.1.1.9  christos       && startswith (h->root.root.string, "_SPUEAR_")
   1498       1.1     skrll       && (sym_sec = h->root.u.def.section) != NULL
   1499   1.1.1.2  christos       && sym_sec->output_section != bfd_abs_section_ptr
   1500       1.1     skrll       && spu_elf_section_data (sym_sec->output_section) != NULL
   1501       1.1     skrll       && (spu_elf_section_data (sym_sec->output_section)->u.o.ovl_index != 0
   1502   1.1.1.2  christos 	  || htab->params->non_overlay_stubs))
   1503       1.1     skrll     {
   1504       1.1     skrll       return count_stub (htab, NULL, NULL, nonovl_stub, h, NULL);
   1505       1.1     skrll     }
   1506   1.1.1.4  christos 
   1507   1.1.1.9  christos   return true;
   1508       1.1     skrll }
   1509       1.1     skrll 
   1510   1.1.1.9  christos static bool
   1511       1.1     skrll build_spuear_stubs (struct elf_link_hash_entry *h, void *inf)
   1512       1.1     skrll {
   1513       1.1     skrll   /* Symbols starting with _SPUEAR_ need a stub because they may be
   1514       1.1     skrll      invoked by the PPU.  */
   1515       1.1     skrll   struct bfd_link_info *info = inf;
   1516       1.1     skrll   struct spu_link_hash_table *htab = spu_hash_table (info);
   1517       1.1     skrll   asection *sym_sec;
   1518       1.1     skrll 
   1519       1.1     skrll   if ((h->root.type == bfd_link_hash_defined
   1520       1.1     skrll        || h->root.type == bfd_link_hash_defweak)
   1521       1.1     skrll       && h->def_regular
   1522   1.1.1.9  christos       && startswith (h->root.root.string, "_SPUEAR_")
   1523       1.1     skrll       && (sym_sec = h->root.u.def.section) != NULL
   1524   1.1.1.2  christos       && sym_sec->output_section != bfd_abs_section_ptr
   1525       1.1     skrll       && spu_elf_section_data (sym_sec->output_section) != NULL
   1526       1.1     skrll       && (spu_elf_section_data (sym_sec->output_section)->u.o.ovl_index != 0
   1527   1.1.1.2  christos 	  || htab->params->non_overlay_stubs))
   1528       1.1     skrll     {
   1529   1.1.1.2  christos       return build_stub (info, NULL, NULL, nonovl_stub, h, NULL,
   1530       1.1     skrll 			 h->root.u.def.value, sym_sec);
   1531       1.1     skrll     }
   1532   1.1.1.4  christos 
   1533   1.1.1.9  christos   return true;
   1534       1.1     skrll }
   1535       1.1     skrll 
   1536       1.1     skrll /* Size or build stubs.  */
   1537       1.1     skrll 
   1538   1.1.1.9  christos static bool
   1539   1.1.1.9  christos process_stubs (struct bfd_link_info *info, bool build)
   1540       1.1     skrll {
   1541       1.1     skrll   struct spu_link_hash_table *htab = spu_hash_table (info);
   1542       1.1     skrll   bfd *ibfd;
   1543       1.1     skrll 
   1544   1.1.1.4  christos   for (ibfd = info->input_bfds; ibfd != NULL; ibfd = ibfd->link.next)
   1545       1.1     skrll     {
   1546   1.1.1.4  christos       extern const bfd_target spu_elf32_vec;
   1547       1.1     skrll       Elf_Internal_Shdr *symtab_hdr;
   1548       1.1     skrll       asection *isec;
   1549       1.1     skrll       Elf_Internal_Sym *local_syms = NULL;
   1550       1.1     skrll 
   1551   1.1.1.4  christos       if (ibfd->xvec != &spu_elf32_vec)
   1552       1.1     skrll 	continue;
   1553       1.1     skrll 
   1554       1.1     skrll       /* We'll need the symbol table in a second.  */
   1555       1.1     skrll       symtab_hdr = &elf_tdata (ibfd)->symtab_hdr;
   1556       1.1     skrll       if (symtab_hdr->sh_info == 0)
   1557       1.1     skrll 	continue;
   1558       1.1     skrll 
   1559       1.1     skrll       /* Walk over each section attached to the input bfd.  */
   1560       1.1     skrll       for (isec = ibfd->sections; isec != NULL; isec = isec->next)
   1561       1.1     skrll 	{
   1562       1.1     skrll 	  Elf_Internal_Rela *internal_relocs, *irelaend, *irela;
   1563       1.1     skrll 
   1564       1.1     skrll 	  /* If there aren't any relocs, then there's nothing more to do.  */
   1565       1.1     skrll 	  if ((isec->flags & SEC_RELOC) == 0
   1566       1.1     skrll 	      || isec->reloc_count == 0)
   1567       1.1     skrll 	    continue;
   1568       1.1     skrll 
   1569   1.1.1.2  christos 	  if (!maybe_needs_stubs (isec))
   1570       1.1     skrll 	    continue;
   1571       1.1     skrll 
   1572       1.1     skrll 	  /* Get the relocs.  */
   1573       1.1     skrll 	  internal_relocs = _bfd_elf_link_read_relocs (ibfd, isec, NULL, NULL,
   1574       1.1     skrll 						       info->keep_memory);
   1575       1.1     skrll 	  if (internal_relocs == NULL)
   1576       1.1     skrll 	    goto error_ret_free_local;
   1577       1.1     skrll 
   1578       1.1     skrll 	  /* Now examine each relocation.  */
   1579       1.1     skrll 	  irela = internal_relocs;
   1580       1.1     skrll 	  irelaend = irela + isec->reloc_count;
   1581       1.1     skrll 	  for (; irela < irelaend; irela++)
   1582       1.1     skrll 	    {
   1583       1.1     skrll 	      enum elf_spu_reloc_type r_type;
   1584       1.1     skrll 	      unsigned int r_indx;
   1585       1.1     skrll 	      asection *sym_sec;
   1586       1.1     skrll 	      Elf_Internal_Sym *sym;
   1587       1.1     skrll 	      struct elf_link_hash_entry *h;
   1588       1.1     skrll 	      enum _stub_type stub_type;
   1589       1.1     skrll 
   1590       1.1     skrll 	      r_type = ELF32_R_TYPE (irela->r_info);
   1591       1.1     skrll 	      r_indx = ELF32_R_SYM (irela->r_info);
   1592       1.1     skrll 
   1593       1.1     skrll 	      if (r_type >= R_SPU_max)
   1594       1.1     skrll 		{
   1595       1.1     skrll 		  bfd_set_error (bfd_error_bad_value);
   1596       1.1     skrll 		error_ret_free_internal:
   1597       1.1     skrll 		  if (elf_section_data (isec)->relocs != internal_relocs)
   1598       1.1     skrll 		    free (internal_relocs);
   1599       1.1     skrll 		error_ret_free_local:
   1600   1.1.1.9  christos 		  if (symtab_hdr->contents != (unsigned char *) local_syms)
   1601       1.1     skrll 		    free (local_syms);
   1602   1.1.1.9  christos 		  return false;
   1603       1.1     skrll 		}
   1604       1.1     skrll 
   1605       1.1     skrll 	      /* Determine the reloc target section.  */
   1606       1.1     skrll 	      if (!get_sym_h (&h, &sym, &sym_sec, &local_syms, r_indx, ibfd))
   1607       1.1     skrll 		goto error_ret_free_internal;
   1608       1.1     skrll 
   1609       1.1     skrll 	      stub_type = needs_ovl_stub (h, sym, sym_sec, isec, irela,
   1610       1.1     skrll 					  NULL, info);
   1611       1.1     skrll 	      if (stub_type == no_stub)
   1612       1.1     skrll 		continue;
   1613       1.1     skrll 	      else if (stub_type == stub_error)
   1614       1.1     skrll 		goto error_ret_free_internal;
   1615       1.1     skrll 
   1616       1.1     skrll 	      if (htab->stub_count == NULL)
   1617       1.1     skrll 		{
   1618       1.1     skrll 		  bfd_size_type amt;
   1619       1.1     skrll 		  amt = (htab->num_overlays + 1) * sizeof (*htab->stub_count);
   1620       1.1     skrll 		  htab->stub_count = bfd_zmalloc (amt);
   1621       1.1     skrll 		  if (htab->stub_count == NULL)
   1622       1.1     skrll 		    goto error_ret_free_internal;
   1623       1.1     skrll 		}
   1624       1.1     skrll 
   1625       1.1     skrll 	      if (!build)
   1626       1.1     skrll 		{
   1627       1.1     skrll 		  if (!count_stub (htab, ibfd, isec, stub_type, h, irela))
   1628       1.1     skrll 		    goto error_ret_free_internal;
   1629       1.1     skrll 		}
   1630       1.1     skrll 	      else
   1631       1.1     skrll 		{
   1632       1.1     skrll 		  bfd_vma dest;
   1633       1.1     skrll 
   1634       1.1     skrll 		  if (h != NULL)
   1635       1.1     skrll 		    dest = h->root.u.def.value;
   1636       1.1     skrll 		  else
   1637       1.1     skrll 		    dest = sym->st_value;
   1638       1.1     skrll 		  dest += irela->r_addend;
   1639   1.1.1.2  christos 		  if (!build_stub (info, ibfd, isec, stub_type, h, irela,
   1640       1.1     skrll 				   dest, sym_sec))
   1641       1.1     skrll 		    goto error_ret_free_internal;
   1642       1.1     skrll 		}
   1643       1.1     skrll 	    }
   1644       1.1     skrll 
   1645       1.1     skrll 	  /* We're done with the internal relocs, free them.  */
   1646       1.1     skrll 	  if (elf_section_data (isec)->relocs != internal_relocs)
   1647       1.1     skrll 	    free (internal_relocs);
   1648       1.1     skrll 	}
   1649       1.1     skrll 
   1650       1.1     skrll       if (local_syms != NULL
   1651       1.1     skrll 	  && symtab_hdr->contents != (unsigned char *) local_syms)
   1652       1.1     skrll 	{
   1653       1.1     skrll 	  if (!info->keep_memory)
   1654       1.1     skrll 	    free (local_syms);
   1655       1.1     skrll 	  else
   1656       1.1     skrll 	    symtab_hdr->contents = (unsigned char *) local_syms;
   1657       1.1     skrll 	}
   1658       1.1     skrll     }
   1659       1.1     skrll 
   1660   1.1.1.9  christos   return true;
   1661       1.1     skrll }
   1662       1.1     skrll 
   1663   1.1.1.2  christos /* Allocate space for overlay call and return stubs.
   1664   1.1.1.2  christos    Return 0 on error, 1 if no overlays, 2 otherwise.  */
   1665       1.1     skrll 
   1666       1.1     skrll int
   1667   1.1.1.2  christos spu_elf_size_stubs (struct bfd_link_info *info)
   1668       1.1     skrll {
   1669   1.1.1.2  christos   struct spu_link_hash_table *htab;
   1670       1.1     skrll   bfd *ibfd;
   1671       1.1     skrll   bfd_size_type amt;
   1672       1.1     skrll   flagword flags;
   1673       1.1     skrll   unsigned int i;
   1674       1.1     skrll   asection *stub;
   1675       1.1     skrll 
   1676   1.1.1.9  christos   if (!process_stubs (info, false))
   1677       1.1     skrll     return 0;
   1678       1.1     skrll 
   1679   1.1.1.2  christos   htab = spu_hash_table (info);
   1680       1.1     skrll   elf_link_hash_traverse (&htab->elf, allocate_spuear_stubs, info);
   1681       1.1     skrll   if (htab->stub_err)
   1682       1.1     skrll     return 0;
   1683       1.1     skrll 
   1684       1.1     skrll   ibfd = info->input_bfds;
   1685   1.1.1.2  christos   if (htab->stub_count != NULL)
   1686       1.1     skrll     {
   1687   1.1.1.2  christos       amt = (htab->num_overlays + 1) * sizeof (*htab->stub_sec);
   1688   1.1.1.2  christos       htab->stub_sec = bfd_zmalloc (amt);
   1689   1.1.1.2  christos       if (htab->stub_sec == NULL)
   1690   1.1.1.2  christos 	return 0;
   1691   1.1.1.2  christos 
   1692   1.1.1.2  christos       flags = (SEC_ALLOC | SEC_LOAD | SEC_CODE | SEC_READONLY
   1693   1.1.1.2  christos 	       | SEC_HAS_CONTENTS | SEC_IN_MEMORY);
   1694       1.1     skrll       stub = bfd_make_section_anyway_with_flags (ibfd, ".stub", flags);
   1695   1.1.1.2  christos       htab->stub_sec[0] = stub;
   1696       1.1     skrll       if (stub == NULL
   1697   1.1.1.8  christos 	  || !bfd_set_section_alignment (stub,
   1698   1.1.1.2  christos 					 ovl_stub_size_log2 (htab->params)))
   1699       1.1     skrll 	return 0;
   1700   1.1.1.2  christos       stub->size = htab->stub_count[0] * ovl_stub_size (htab->params);
   1701   1.1.1.2  christos       if (htab->params->ovly_flavour == ovly_soft_icache)
   1702   1.1.1.2  christos 	/* Extra space for linked list entries.  */
   1703   1.1.1.2  christos 	stub->size += htab->stub_count[0] * 16;
   1704   1.1.1.2  christos 
   1705   1.1.1.2  christos       for (i = 0; i < htab->num_overlays; ++i)
   1706   1.1.1.2  christos 	{
   1707   1.1.1.2  christos 	  asection *osec = htab->ovl_sec[i];
   1708   1.1.1.2  christos 	  unsigned int ovl = spu_elf_section_data (osec)->u.o.ovl_index;
   1709   1.1.1.2  christos 	  stub = bfd_make_section_anyway_with_flags (ibfd, ".stub", flags);
   1710   1.1.1.2  christos 	  htab->stub_sec[ovl] = stub;
   1711   1.1.1.2  christos 	  if (stub == NULL
   1712   1.1.1.8  christos 	      || !bfd_set_section_alignment (stub,
   1713   1.1.1.2  christos 					     ovl_stub_size_log2 (htab->params)))
   1714   1.1.1.2  christos 	    return 0;
   1715   1.1.1.2  christos 	  stub->size = htab->stub_count[ovl] * ovl_stub_size (htab->params);
   1716   1.1.1.2  christos 	}
   1717       1.1     skrll     }
   1718       1.1     skrll 
   1719   1.1.1.2  christos   if (htab->params->ovly_flavour == ovly_soft_icache)
   1720   1.1.1.2  christos     {
   1721   1.1.1.2  christos       /* Space for icache manager tables.
   1722   1.1.1.2  christos 	 a) Tag array, one quadword per cache line.
   1723   1.1.1.2  christos 	 b) Rewrite "to" list, one quadword per cache line.
   1724   1.1.1.2  christos 	 c) Rewrite "from" list, one byte per outgoing branch (rounded up to
   1725   1.1.1.2  christos 	    a power-of-two number of full quadwords) per cache line.  */
   1726   1.1.1.2  christos 
   1727   1.1.1.2  christos       flags = SEC_ALLOC;
   1728   1.1.1.2  christos       htab->ovtab = bfd_make_section_anyway_with_flags (ibfd, ".ovtab", flags);
   1729   1.1.1.2  christos       if (htab->ovtab == NULL
   1730   1.1.1.8  christos 	  || !bfd_set_section_alignment (htab->ovtab, 4))
   1731   1.1.1.2  christos 	return 0;
   1732   1.1.1.2  christos 
   1733   1.1.1.2  christos       htab->ovtab->size = (16 + 16 + (16 << htab->fromelem_size_log2))
   1734   1.1.1.2  christos 			  << htab->num_lines_log2;
   1735       1.1     skrll 
   1736   1.1.1.2  christos       flags = SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS | SEC_IN_MEMORY;
   1737   1.1.1.2  christos       htab->init = bfd_make_section_anyway_with_flags (ibfd, ".ovini", flags);
   1738   1.1.1.2  christos       if (htab->init == NULL
   1739   1.1.1.8  christos 	  || !bfd_set_section_alignment (htab->init, 4))
   1740   1.1.1.2  christos 	return 0;
   1741   1.1.1.2  christos 
   1742   1.1.1.2  christos       htab->init->size = 16;
   1743   1.1.1.2  christos     }
   1744   1.1.1.2  christos   else if (htab->stub_count == NULL)
   1745   1.1.1.2  christos     return 1;
   1746   1.1.1.2  christos   else
   1747   1.1.1.2  christos     {
   1748   1.1.1.2  christos       /* htab->ovtab consists of two arrays.
   1749   1.1.1.2  christos 	 .	struct {
   1750   1.1.1.2  christos 	 .	  u32 vma;
   1751   1.1.1.2  christos 	 .	  u32 size;
   1752   1.1.1.2  christos 	 .	  u32 file_off;
   1753   1.1.1.2  christos 	 .	  u32 buf;
   1754   1.1.1.2  christos 	 .	} _ovly_table[];
   1755   1.1.1.2  christos 	 .
   1756   1.1.1.2  christos 	 .	struct {
   1757   1.1.1.2  christos 	 .	  u32 mapped;
   1758   1.1.1.2  christos 	 .	} _ovly_buf_table[];
   1759   1.1.1.2  christos 	 .  */
   1760   1.1.1.2  christos 
   1761   1.1.1.2  christos       flags = SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS | SEC_IN_MEMORY;
   1762   1.1.1.2  christos       htab->ovtab = bfd_make_section_anyway_with_flags (ibfd, ".ovtab", flags);
   1763   1.1.1.2  christos       if (htab->ovtab == NULL
   1764   1.1.1.8  christos 	  || !bfd_set_section_alignment (htab->ovtab, 4))
   1765   1.1.1.2  christos 	return 0;
   1766   1.1.1.2  christos 
   1767   1.1.1.2  christos       htab->ovtab->size = htab->num_overlays * 16 + 16 + htab->num_buf * 4;
   1768   1.1.1.2  christos     }
   1769       1.1     skrll 
   1770       1.1     skrll   htab->toe = bfd_make_section_anyway_with_flags (ibfd, ".toe", SEC_ALLOC);
   1771       1.1     skrll   if (htab->toe == NULL
   1772   1.1.1.8  christos       || !bfd_set_section_alignment (htab->toe, 4))
   1773       1.1     skrll     return 0;
   1774       1.1     skrll   htab->toe->size = 16;
   1775       1.1     skrll 
   1776       1.1     skrll   return 2;
   1777       1.1     skrll }
   1778       1.1     skrll 
   1779   1.1.1.2  christos /* Called from ld to place overlay manager data sections.  This is done
   1780   1.1.1.2  christos    after the overlay manager itself is loaded, mainly so that the
   1781   1.1.1.2  christos    linker's htab->init section is placed after any other .ovl.init
   1782   1.1.1.2  christos    sections.  */
   1783   1.1.1.2  christos 
   1784   1.1.1.2  christos void
   1785   1.1.1.2  christos spu_elf_place_overlay_data (struct bfd_link_info *info)
   1786   1.1.1.2  christos {
   1787   1.1.1.2  christos   struct spu_link_hash_table *htab = spu_hash_table (info);
   1788   1.1.1.2  christos   unsigned int i;
   1789   1.1.1.2  christos 
   1790   1.1.1.2  christos   if (htab->stub_sec != NULL)
   1791   1.1.1.2  christos     {
   1792   1.1.1.2  christos       (*htab->params->place_spu_section) (htab->stub_sec[0], NULL, ".text");
   1793   1.1.1.2  christos 
   1794   1.1.1.2  christos       for (i = 0; i < htab->num_overlays; ++i)
   1795   1.1.1.2  christos 	{
   1796   1.1.1.2  christos 	  asection *osec = htab->ovl_sec[i];
   1797   1.1.1.2  christos 	  unsigned int ovl = spu_elf_section_data (osec)->u.o.ovl_index;
   1798   1.1.1.2  christos 	  (*htab->params->place_spu_section) (htab->stub_sec[ovl], osec, NULL);
   1799   1.1.1.2  christos 	}
   1800   1.1.1.2  christos     }
   1801   1.1.1.2  christos 
   1802   1.1.1.2  christos   if (htab->params->ovly_flavour == ovly_soft_icache)
   1803   1.1.1.2  christos     (*htab->params->place_spu_section) (htab->init, NULL, ".ovl.init");
   1804   1.1.1.2  christos 
   1805   1.1.1.2  christos   if (htab->ovtab != NULL)
   1806   1.1.1.2  christos     {
   1807   1.1.1.2  christos       const char *ovout = ".data";
   1808   1.1.1.2  christos       if (htab->params->ovly_flavour == ovly_soft_icache)
   1809   1.1.1.2  christos 	ovout = ".bss";
   1810   1.1.1.2  christos       (*htab->params->place_spu_section) (htab->ovtab, NULL, ovout);
   1811   1.1.1.2  christos     }
   1812   1.1.1.2  christos 
   1813   1.1.1.2  christos   if (htab->toe != NULL)
   1814   1.1.1.2  christos     (*htab->params->place_spu_section) (htab->toe, NULL, ".toe");
   1815   1.1.1.2  christos }
   1816   1.1.1.2  christos 
   1817       1.1     skrll /* Functions to handle embedded spu_ovl.o object.  */
   1818       1.1     skrll 
   1819       1.1     skrll static void *
   1820       1.1     skrll ovl_mgr_open (struct bfd *nbfd ATTRIBUTE_UNUSED, void *stream)
   1821       1.1     skrll {
   1822       1.1     skrll   return stream;
   1823       1.1     skrll }
   1824       1.1     skrll 
   1825       1.1     skrll static file_ptr
   1826       1.1     skrll ovl_mgr_pread (struct bfd *abfd ATTRIBUTE_UNUSED,
   1827       1.1     skrll 	       void *stream,
   1828       1.1     skrll 	       void *buf,
   1829       1.1     skrll 	       file_ptr nbytes,
   1830       1.1     skrll 	       file_ptr offset)
   1831       1.1     skrll {
   1832       1.1     skrll   struct _ovl_stream *os;
   1833       1.1     skrll   size_t count;
   1834       1.1     skrll   size_t max;
   1835       1.1     skrll 
   1836       1.1     skrll   os = (struct _ovl_stream *) stream;
   1837       1.1     skrll   max = (const char *) os->end - (const char *) os->start;
   1838       1.1     skrll 
   1839       1.1     skrll   if ((ufile_ptr) offset >= max)
   1840       1.1     skrll     return 0;
   1841       1.1     skrll 
   1842       1.1     skrll   count = nbytes;
   1843       1.1     skrll   if (count > max - offset)
   1844       1.1     skrll     count = max - offset;
   1845       1.1     skrll 
   1846       1.1     skrll   memcpy (buf, (const char *) os->start + offset, count);
   1847       1.1     skrll   return count;
   1848       1.1     skrll }
   1849       1.1     skrll 
   1850   1.1.1.4  christos static int
   1851   1.1.1.4  christos ovl_mgr_stat (struct bfd *abfd ATTRIBUTE_UNUSED,
   1852   1.1.1.4  christos 	      void *stream,
   1853   1.1.1.4  christos 	      struct stat *sb)
   1854   1.1.1.4  christos {
   1855   1.1.1.4  christos   struct _ovl_stream *os = (struct _ovl_stream *) stream;
   1856   1.1.1.4  christos 
   1857   1.1.1.4  christos   memset (sb, 0, sizeof (*sb));
   1858   1.1.1.4  christos   sb->st_size = (const char *) os->end - (const char *) os->start;
   1859   1.1.1.4  christos   return 0;
   1860   1.1.1.4  christos }
   1861   1.1.1.4  christos 
   1862   1.1.1.9  christos bool
   1863       1.1     skrll spu_elf_open_builtin_lib (bfd **ovl_bfd, const struct _ovl_stream *stream)
   1864       1.1     skrll {
   1865       1.1     skrll   *ovl_bfd = bfd_openr_iovec ("builtin ovl_mgr",
   1866       1.1     skrll 			      "elf32-spu",
   1867       1.1     skrll 			      ovl_mgr_open,
   1868       1.1     skrll 			      (void *) stream,
   1869       1.1     skrll 			      ovl_mgr_pread,
   1870       1.1     skrll 			      NULL,
   1871   1.1.1.4  christos 			      ovl_mgr_stat);
   1872       1.1     skrll   return *ovl_bfd != NULL;
   1873       1.1     skrll }
   1874       1.1     skrll 
   1875   1.1.1.2  christos static unsigned int
   1876   1.1.1.2  christos overlay_index (asection *sec)
   1877   1.1.1.2  christos {
   1878   1.1.1.2  christos   if (sec == NULL
   1879   1.1.1.2  christos       || sec->output_section == bfd_abs_section_ptr)
   1880   1.1.1.2  christos     return 0;
   1881   1.1.1.2  christos   return spu_elf_section_data (sec->output_section)->u.o.ovl_index;
   1882   1.1.1.2  christos }
   1883   1.1.1.2  christos 
   1884       1.1     skrll /* Define an STT_OBJECT symbol.  */
   1885       1.1     skrll 
   1886       1.1     skrll static struct elf_link_hash_entry *
   1887       1.1     skrll define_ovtab_symbol (struct spu_link_hash_table *htab, const char *name)
   1888       1.1     skrll {
   1889       1.1     skrll   struct elf_link_hash_entry *h;
   1890       1.1     skrll 
   1891   1.1.1.9  christos   h = elf_link_hash_lookup (&htab->elf, name, true, false, false);
   1892       1.1     skrll   if (h == NULL)
   1893       1.1     skrll     return NULL;
   1894       1.1     skrll 
   1895       1.1     skrll   if (h->root.type != bfd_link_hash_defined
   1896       1.1     skrll       || !h->def_regular)
   1897       1.1     skrll     {
   1898       1.1     skrll       h->root.type = bfd_link_hash_defined;
   1899       1.1     skrll       h->root.u.def.section = htab->ovtab;
   1900       1.1     skrll       h->type = STT_OBJECT;
   1901       1.1     skrll       h->ref_regular = 1;
   1902       1.1     skrll       h->def_regular = 1;
   1903       1.1     skrll       h->ref_regular_nonweak = 1;
   1904       1.1     skrll       h->non_elf = 0;
   1905       1.1     skrll     }
   1906   1.1.1.2  christos   else if (h->root.u.def.section->owner != NULL)
   1907       1.1     skrll     {
   1908   1.1.1.6  christos       /* xgettext:c-format */
   1909   1.1.1.7  christos       _bfd_error_handler (_("%pB is not allowed to define %s"),
   1910   1.1.1.6  christos 			  h->root.u.def.section->owner,
   1911   1.1.1.6  christos 			  h->root.root.string);
   1912       1.1     skrll       bfd_set_error (bfd_error_bad_value);
   1913       1.1     skrll       return NULL;
   1914       1.1     skrll     }
   1915   1.1.1.2  christos   else
   1916   1.1.1.2  christos     {
   1917   1.1.1.6  christos       _bfd_error_handler (_("you are not allowed to define %s in a script"),
   1918   1.1.1.6  christos 			  h->root.root.string);
   1919   1.1.1.2  christos       bfd_set_error (bfd_error_bad_value);
   1920   1.1.1.2  christos       return NULL;
   1921   1.1.1.2  christos     }
   1922       1.1     skrll 
   1923       1.1     skrll   return h;
   1924       1.1     skrll }
   1925       1.1     skrll 
   1926       1.1     skrll /* Fill in all stubs and the overlay tables.  */
   1927       1.1     skrll 
   1928   1.1.1.9  christos static bool
   1929   1.1.1.2  christos spu_elf_build_stubs (struct bfd_link_info *info)
   1930       1.1     skrll {
   1931       1.1     skrll   struct spu_link_hash_table *htab = spu_hash_table (info);
   1932       1.1     skrll   struct elf_link_hash_entry *h;
   1933       1.1     skrll   bfd_byte *p;
   1934       1.1     skrll   asection *s;
   1935       1.1     skrll   bfd *obfd;
   1936       1.1     skrll   unsigned int i;
   1937       1.1     skrll 
   1938   1.1.1.2  christos   if (htab->num_overlays != 0)
   1939   1.1.1.2  christos     {
   1940   1.1.1.2  christos       for (i = 0; i < 2; i++)
   1941   1.1.1.2  christos 	{
   1942   1.1.1.2  christos 	  h = htab->ovly_entry[i];
   1943   1.1.1.2  christos 	  if (h != NULL
   1944       1.1     skrll 	      && (h->root.type == bfd_link_hash_defined
   1945       1.1     skrll 		  || h->root.type == bfd_link_hash_defweak)
   1946   1.1.1.2  christos 	      && h->def_regular)
   1947   1.1.1.2  christos 	    {
   1948   1.1.1.2  christos 	      s = h->root.u.def.section->output_section;
   1949   1.1.1.2  christos 	      if (spu_elf_section_data (s)->u.o.ovl_index)
   1950   1.1.1.2  christos 		{
   1951   1.1.1.6  christos 		  _bfd_error_handler (_("%s in overlay section"),
   1952   1.1.1.6  christos 				      h->root.root.string);
   1953   1.1.1.2  christos 		  bfd_set_error (bfd_error_bad_value);
   1954   1.1.1.9  christos 		  return false;
   1955   1.1.1.2  christos 		}
   1956   1.1.1.2  christos 	    }
   1957   1.1.1.2  christos 	}
   1958       1.1     skrll     }
   1959       1.1     skrll 
   1960   1.1.1.2  christos   if (htab->stub_sec != NULL)
   1961       1.1     skrll     {
   1962   1.1.1.2  christos       for (i = 0; i <= htab->num_overlays; i++)
   1963   1.1.1.2  christos 	if (htab->stub_sec[i]->size != 0)
   1964   1.1.1.2  christos 	  {
   1965   1.1.1.2  christos 	    htab->stub_sec[i]->contents = bfd_zalloc (htab->stub_sec[i]->owner,
   1966   1.1.1.2  christos 						      htab->stub_sec[i]->size);
   1967   1.1.1.2  christos 	    if (htab->stub_sec[i]->contents == NULL)
   1968   1.1.1.9  christos 	      return false;
   1969  1.1.1.11  christos 	    htab->stub_sec[i]->alloced = 1;
   1970   1.1.1.2  christos 	    htab->stub_sec[i]->rawsize = htab->stub_sec[i]->size;
   1971   1.1.1.2  christos 	    htab->stub_sec[i]->size = 0;
   1972   1.1.1.2  christos 	  }
   1973       1.1     skrll 
   1974   1.1.1.2  christos       /* Fill in all the stubs.  */
   1975   1.1.1.9  christos       process_stubs (info, true);
   1976   1.1.1.2  christos       if (!htab->stub_err)
   1977   1.1.1.2  christos 	elf_link_hash_traverse (&htab->elf, build_spuear_stubs, info);
   1978   1.1.1.2  christos 
   1979   1.1.1.2  christos       if (htab->stub_err)
   1980       1.1     skrll 	{
   1981   1.1.1.6  christos 	  _bfd_error_handler (_("overlay stub relocation overflow"));
   1982       1.1     skrll 	  bfd_set_error (bfd_error_bad_value);
   1983   1.1.1.9  christos 	  return false;
   1984       1.1     skrll 	}
   1985   1.1.1.2  christos 
   1986   1.1.1.2  christos       for (i = 0; i <= htab->num_overlays; i++)
   1987   1.1.1.2  christos 	{
   1988   1.1.1.2  christos 	  if (htab->stub_sec[i]->size != htab->stub_sec[i]->rawsize)
   1989   1.1.1.2  christos 	    {
   1990   1.1.1.6  christos 	      _bfd_error_handler  (_("stubs don't match calculated size"));
   1991   1.1.1.2  christos 	      bfd_set_error (bfd_error_bad_value);
   1992   1.1.1.9  christos 	      return false;
   1993   1.1.1.2  christos 	    }
   1994   1.1.1.2  christos 	  htab->stub_sec[i]->rawsize = 0;
   1995   1.1.1.2  christos 	}
   1996       1.1     skrll     }
   1997       1.1     skrll 
   1998   1.1.1.2  christos   if (htab->ovtab == NULL || htab->ovtab->size == 0)
   1999   1.1.1.9  christos     return true;
   2000   1.1.1.2  christos 
   2001       1.1     skrll   htab->ovtab->contents = bfd_zalloc (htab->ovtab->owner, htab->ovtab->size);
   2002       1.1     skrll   if (htab->ovtab->contents == NULL)
   2003   1.1.1.9  christos     return false;
   2004  1.1.1.11  christos   htab->ovtab->alloced = 1;
   2005       1.1     skrll 
   2006       1.1     skrll   p = htab->ovtab->contents;
   2007   1.1.1.2  christos   if (htab->params->ovly_flavour == ovly_soft_icache)
   2008       1.1     skrll     {
   2009   1.1.1.2  christos       bfd_vma off;
   2010   1.1.1.2  christos 
   2011   1.1.1.2  christos       h = define_ovtab_symbol (htab, "__icache_tag_array");
   2012   1.1.1.2  christos       if (h == NULL)
   2013   1.1.1.9  christos 	return false;
   2014   1.1.1.2  christos       h->root.u.def.value = 0;
   2015   1.1.1.2  christos       h->size = 16 << htab->num_lines_log2;
   2016   1.1.1.2  christos       off = h->size;
   2017   1.1.1.2  christos 
   2018   1.1.1.2  christos       h = define_ovtab_symbol (htab, "__icache_tag_array_size");
   2019   1.1.1.2  christos       if (h == NULL)
   2020   1.1.1.9  christos 	return false;
   2021   1.1.1.2  christos       h->root.u.def.value = 16 << htab->num_lines_log2;
   2022   1.1.1.2  christos       h->root.u.def.section = bfd_abs_section_ptr;
   2023   1.1.1.2  christos 
   2024   1.1.1.2  christos       h = define_ovtab_symbol (htab, "__icache_rewrite_to");
   2025   1.1.1.2  christos       if (h == NULL)
   2026   1.1.1.9  christos 	return false;
   2027   1.1.1.2  christos       h->root.u.def.value = off;
   2028   1.1.1.2  christos       h->size = 16 << htab->num_lines_log2;
   2029   1.1.1.2  christos       off += h->size;
   2030   1.1.1.2  christos 
   2031   1.1.1.2  christos       h = define_ovtab_symbol (htab, "__icache_rewrite_to_size");
   2032   1.1.1.2  christos       if (h == NULL)
   2033   1.1.1.9  christos 	return false;
   2034   1.1.1.2  christos       h->root.u.def.value = 16 << htab->num_lines_log2;
   2035   1.1.1.2  christos       h->root.u.def.section = bfd_abs_section_ptr;
   2036   1.1.1.2  christos 
   2037   1.1.1.2  christos       h = define_ovtab_symbol (htab, "__icache_rewrite_from");
   2038   1.1.1.2  christos       if (h == NULL)
   2039   1.1.1.9  christos 	return false;
   2040   1.1.1.2  christos       h->root.u.def.value = off;
   2041   1.1.1.2  christos       h->size = 16 << (htab->fromelem_size_log2 + htab->num_lines_log2);
   2042   1.1.1.2  christos       off += h->size;
   2043   1.1.1.2  christos 
   2044   1.1.1.2  christos       h = define_ovtab_symbol (htab, "__icache_rewrite_from_size");
   2045   1.1.1.2  christos       if (h == NULL)
   2046   1.1.1.9  christos 	return false;
   2047   1.1.1.2  christos       h->root.u.def.value = 16 << (htab->fromelem_size_log2
   2048   1.1.1.2  christos 				   + htab->num_lines_log2);
   2049   1.1.1.2  christos       h->root.u.def.section = bfd_abs_section_ptr;
   2050   1.1.1.2  christos 
   2051   1.1.1.2  christos       h = define_ovtab_symbol (htab, "__icache_log2_fromelemsize");
   2052   1.1.1.2  christos       if (h == NULL)
   2053   1.1.1.9  christos 	return false;
   2054   1.1.1.2  christos       h->root.u.def.value = htab->fromelem_size_log2;
   2055   1.1.1.2  christos       h->root.u.def.section = bfd_abs_section_ptr;
   2056   1.1.1.2  christos 
   2057   1.1.1.2  christos       h = define_ovtab_symbol (htab, "__icache_base");
   2058   1.1.1.2  christos       if (h == NULL)
   2059   1.1.1.9  christos 	return false;
   2060   1.1.1.2  christos       h->root.u.def.value = htab->ovl_sec[0]->vma;
   2061   1.1.1.2  christos       h->root.u.def.section = bfd_abs_section_ptr;
   2062   1.1.1.2  christos       h->size = htab->num_buf << htab->line_size_log2;
   2063   1.1.1.2  christos 
   2064   1.1.1.2  christos       h = define_ovtab_symbol (htab, "__icache_linesize");
   2065   1.1.1.2  christos       if (h == NULL)
   2066   1.1.1.9  christos 	return false;
   2067   1.1.1.2  christos       h->root.u.def.value = 1 << htab->line_size_log2;
   2068   1.1.1.2  christos       h->root.u.def.section = bfd_abs_section_ptr;
   2069   1.1.1.2  christos 
   2070   1.1.1.2  christos       h = define_ovtab_symbol (htab, "__icache_log2_linesize");
   2071   1.1.1.2  christos       if (h == NULL)
   2072   1.1.1.9  christos 	return false;
   2073   1.1.1.2  christos       h->root.u.def.value = htab->line_size_log2;
   2074   1.1.1.2  christos       h->root.u.def.section = bfd_abs_section_ptr;
   2075   1.1.1.2  christos 
   2076   1.1.1.2  christos       h = define_ovtab_symbol (htab, "__icache_neg_log2_linesize");
   2077   1.1.1.2  christos       if (h == NULL)
   2078   1.1.1.9  christos 	return false;
   2079   1.1.1.2  christos       h->root.u.def.value = -htab->line_size_log2;
   2080   1.1.1.2  christos       h->root.u.def.section = bfd_abs_section_ptr;
   2081   1.1.1.2  christos 
   2082   1.1.1.2  christos       h = define_ovtab_symbol (htab, "__icache_cachesize");
   2083   1.1.1.2  christos       if (h == NULL)
   2084   1.1.1.9  christos 	return false;
   2085   1.1.1.2  christos       h->root.u.def.value = 1 << (htab->num_lines_log2 + htab->line_size_log2);
   2086   1.1.1.2  christos       h->root.u.def.section = bfd_abs_section_ptr;
   2087   1.1.1.2  christos 
   2088   1.1.1.2  christos       h = define_ovtab_symbol (htab, "__icache_log2_cachesize");
   2089   1.1.1.2  christos       if (h == NULL)
   2090   1.1.1.9  christos 	return false;
   2091   1.1.1.2  christos       h->root.u.def.value = htab->num_lines_log2 + htab->line_size_log2;
   2092   1.1.1.2  christos       h->root.u.def.section = bfd_abs_section_ptr;
   2093       1.1     skrll 
   2094   1.1.1.2  christos       h = define_ovtab_symbol (htab, "__icache_neg_log2_cachesize");
   2095   1.1.1.2  christos       if (h == NULL)
   2096   1.1.1.9  christos 	return false;
   2097   1.1.1.2  christos       h->root.u.def.value = -(htab->num_lines_log2 + htab->line_size_log2);
   2098   1.1.1.2  christos       h->root.u.def.section = bfd_abs_section_ptr;
   2099   1.1.1.2  christos 
   2100   1.1.1.2  christos       if (htab->init != NULL && htab->init->size != 0)
   2101       1.1     skrll 	{
   2102   1.1.1.2  christos 	  htab->init->contents = bfd_zalloc (htab->init->owner,
   2103   1.1.1.2  christos 					     htab->init->size);
   2104   1.1.1.2  christos 	  if (htab->init->contents == NULL)
   2105   1.1.1.9  christos 	    return false;
   2106  1.1.1.11  christos 	  htab->init->alloced = 1;
   2107       1.1     skrll 
   2108   1.1.1.2  christos 	  h = define_ovtab_symbol (htab, "__icache_fileoff");
   2109   1.1.1.2  christos 	  if (h == NULL)
   2110   1.1.1.9  christos 	    return false;
   2111   1.1.1.2  christos 	  h->root.u.def.value = 0;
   2112   1.1.1.2  christos 	  h->root.u.def.section = htab->init;
   2113   1.1.1.2  christos 	  h->size = 8;
   2114       1.1     skrll 	}
   2115       1.1     skrll     }
   2116   1.1.1.2  christos   else
   2117   1.1.1.2  christos     {
   2118   1.1.1.2  christos       /* Write out _ovly_table.  */
   2119   1.1.1.2  christos       /* set low bit of .size to mark non-overlay area as present.  */
   2120   1.1.1.2  christos       p[7] = 1;
   2121   1.1.1.2  christos       obfd = htab->ovtab->output_section->owner;
   2122   1.1.1.2  christos       for (s = obfd->sections; s != NULL; s = s->next)
   2123   1.1.1.2  christos 	{
   2124   1.1.1.2  christos 	  unsigned int ovl_index = spu_elf_section_data (s)->u.o.ovl_index;
   2125       1.1     skrll 
   2126   1.1.1.2  christos 	  if (ovl_index != 0)
   2127   1.1.1.2  christos 	    {
   2128   1.1.1.2  christos 	      unsigned long off = ovl_index * 16;
   2129   1.1.1.2  christos 	      unsigned int ovl_buf = spu_elf_section_data (s)->u.o.ovl_buf;
   2130       1.1     skrll 
   2131   1.1.1.2  christos 	      bfd_put_32 (htab->ovtab->owner, s->vma, p + off);
   2132   1.1.1.2  christos 	      bfd_put_32 (htab->ovtab->owner, (s->size + 15) & -16,
   2133   1.1.1.2  christos 			  p + off + 4);
   2134   1.1.1.8  christos 	      /* file_off written later in spu_elf_modify_headers.  */
   2135   1.1.1.2  christos 	      bfd_put_32 (htab->ovtab->owner, ovl_buf, p + off + 12);
   2136   1.1.1.2  christos 	    }
   2137   1.1.1.2  christos 	}
   2138       1.1     skrll 
   2139   1.1.1.2  christos       h = define_ovtab_symbol (htab, "_ovly_table");
   2140   1.1.1.2  christos       if (h == NULL)
   2141   1.1.1.9  christos 	return false;
   2142   1.1.1.2  christos       h->root.u.def.value = 16;
   2143   1.1.1.2  christos       h->size = htab->num_overlays * 16;
   2144       1.1     skrll 
   2145   1.1.1.2  christos       h = define_ovtab_symbol (htab, "_ovly_table_end");
   2146   1.1.1.2  christos       if (h == NULL)
   2147   1.1.1.9  christos 	return false;
   2148   1.1.1.2  christos       h->root.u.def.value = htab->num_overlays * 16 + 16;
   2149   1.1.1.2  christos       h->size = 0;
   2150   1.1.1.2  christos 
   2151   1.1.1.2  christos       h = define_ovtab_symbol (htab, "_ovly_buf_table");
   2152   1.1.1.2  christos       if (h == NULL)
   2153   1.1.1.9  christos 	return false;
   2154   1.1.1.2  christos       h->root.u.def.value = htab->num_overlays * 16 + 16;
   2155   1.1.1.2  christos       h->size = htab->num_buf * 4;
   2156   1.1.1.2  christos 
   2157   1.1.1.2  christos       h = define_ovtab_symbol (htab, "_ovly_buf_table_end");
   2158   1.1.1.2  christos       if (h == NULL)
   2159   1.1.1.9  christos 	return false;
   2160   1.1.1.2  christos       h->root.u.def.value = htab->num_overlays * 16 + 16 + htab->num_buf * 4;
   2161   1.1.1.2  christos       h->size = 0;
   2162   1.1.1.2  christos     }
   2163       1.1     skrll 
   2164       1.1     skrll   h = define_ovtab_symbol (htab, "_EAR_");
   2165       1.1     skrll   if (h == NULL)
   2166   1.1.1.9  christos     return false;
   2167       1.1     skrll   h->root.u.def.section = htab->toe;
   2168       1.1     skrll   h->root.u.def.value = 0;
   2169       1.1     skrll   h->size = 16;
   2170       1.1     skrll 
   2171   1.1.1.9  christos   return true;
   2172       1.1     skrll }
   2173       1.1     skrll 
   2174       1.1     skrll /* Check that all loadable section VMAs lie in the range
   2175       1.1     skrll    LO .. HI inclusive, and stash some parameters for --auto-overlay.  */
   2176       1.1     skrll 
   2177       1.1     skrll asection *
   2178   1.1.1.2  christos spu_elf_check_vma (struct bfd_link_info *info)
   2179       1.1     skrll {
   2180       1.1     skrll   struct elf_segment_map *m;
   2181       1.1     skrll   unsigned int i;
   2182       1.1     skrll   struct spu_link_hash_table *htab = spu_hash_table (info);
   2183       1.1     skrll   bfd *abfd = info->output_bfd;
   2184   1.1.1.2  christos   bfd_vma hi = htab->params->local_store_hi;
   2185   1.1.1.2  christos   bfd_vma lo = htab->params->local_store_lo;
   2186       1.1     skrll 
   2187       1.1     skrll   htab->local_store = hi + 1 - lo;
   2188       1.1     skrll 
   2189   1.1.1.4  christos   for (m = elf_seg_map (abfd); m != NULL; m = m->next)
   2190       1.1     skrll     if (m->p_type == PT_LOAD)
   2191       1.1     skrll       for (i = 0; i < m->count; i++)
   2192       1.1     skrll 	if (m->sections[i]->size != 0
   2193       1.1     skrll 	    && (m->sections[i]->vma < lo
   2194       1.1     skrll 		|| m->sections[i]->vma > hi
   2195       1.1     skrll 		|| m->sections[i]->vma + m->sections[i]->size - 1 > hi))
   2196       1.1     skrll 	  return m->sections[i];
   2197       1.1     skrll 
   2198       1.1     skrll   return NULL;
   2199       1.1     skrll }
   2200       1.1     skrll 
   2201       1.1     skrll /* OFFSET in SEC (presumably) is the beginning of a function prologue.
   2202   1.1.1.2  christos    Search for stack adjusting insns, and return the sp delta.
   2203   1.1.1.2  christos    If a store of lr is found save the instruction offset to *LR_STORE.
   2204   1.1.1.2  christos    If a stack adjusting instruction is found, save that offset to
   2205   1.1.1.2  christos    *SP_ADJUST.  */
   2206       1.1     skrll 
   2207       1.1     skrll static int
   2208   1.1.1.2  christos find_function_stack_adjust (asection *sec,
   2209   1.1.1.2  christos 			    bfd_vma offset,
   2210   1.1.1.2  christos 			    bfd_vma *lr_store,
   2211   1.1.1.2  christos 			    bfd_vma *sp_adjust)
   2212       1.1     skrll {
   2213   1.1.1.9  christos   int32_t reg[128];
   2214       1.1     skrll 
   2215       1.1     skrll   memset (reg, 0, sizeof (reg));
   2216   1.1.1.2  christos   for ( ; offset + 4 <= sec->size; offset += 4)
   2217       1.1     skrll     {
   2218       1.1     skrll       unsigned char buf[4];
   2219       1.1     skrll       int rt, ra;
   2220   1.1.1.9  christos       uint32_t imm;
   2221       1.1     skrll 
   2222       1.1     skrll       /* Assume no relocs on stack adjusing insns.  */
   2223       1.1     skrll       if (!bfd_get_section_contents (sec->owner, sec, buf, offset, 4))
   2224       1.1     skrll 	break;
   2225       1.1     skrll 
   2226       1.1     skrll       rt = buf[3] & 0x7f;
   2227       1.1     skrll       ra = ((buf[2] & 0x3f) << 1) | (buf[3] >> 7);
   2228   1.1.1.2  christos 
   2229   1.1.1.2  christos       if (buf[0] == 0x24 /* stqd */)
   2230   1.1.1.2  christos 	{
   2231   1.1.1.2  christos 	  if (rt == 0 /* lr */ && ra == 1 /* sp */)
   2232   1.1.1.2  christos 	    *lr_store = offset;
   2233   1.1.1.2  christos 	  continue;
   2234   1.1.1.2  christos 	}
   2235   1.1.1.2  christos 
   2236       1.1     skrll       /* Partly decoded immediate field.  */
   2237       1.1     skrll       imm = (buf[1] << 9) | (buf[2] << 1) | (buf[3] >> 7);
   2238       1.1     skrll 
   2239       1.1     skrll       if (buf[0] == 0x1c /* ai */)
   2240       1.1     skrll 	{
   2241       1.1     skrll 	  imm >>= 7;
   2242       1.1     skrll 	  imm = (imm ^ 0x200) - 0x200;
   2243       1.1     skrll 	  reg[rt] = reg[ra] + imm;
   2244       1.1     skrll 
   2245       1.1     skrll 	  if (rt == 1 /* sp */)
   2246       1.1     skrll 	    {
   2247   1.1.1.2  christos 	      if (reg[rt] > 0)
   2248       1.1     skrll 		break;
   2249   1.1.1.2  christos 	      *sp_adjust = offset;
   2250       1.1     skrll 	      return reg[rt];
   2251       1.1     skrll 	    }
   2252       1.1     skrll 	}
   2253       1.1     skrll       else if (buf[0] == 0x18 && (buf[1] & 0xe0) == 0 /* a */)
   2254       1.1     skrll 	{
   2255       1.1     skrll 	  int rb = ((buf[1] & 0x1f) << 2) | ((buf[2] & 0xc0) >> 6);
   2256       1.1     skrll 
   2257       1.1     skrll 	  reg[rt] = reg[ra] + reg[rb];
   2258       1.1     skrll 	  if (rt == 1)
   2259   1.1.1.2  christos 	    {
   2260   1.1.1.2  christos 	      if (reg[rt] > 0)
   2261   1.1.1.2  christos 		break;
   2262   1.1.1.2  christos 	      *sp_adjust = offset;
   2263   1.1.1.2  christos 	      return reg[rt];
   2264   1.1.1.2  christos 	    }
   2265   1.1.1.2  christos 	}
   2266   1.1.1.2  christos       else if (buf[0] == 0x08 && (buf[1] & 0xe0) == 0 /* sf */)
   2267   1.1.1.2  christos 	{
   2268   1.1.1.2  christos 	  int rb = ((buf[1] & 0x1f) << 2) | ((buf[2] & 0xc0) >> 6);
   2269   1.1.1.2  christos 
   2270   1.1.1.2  christos 	  reg[rt] = reg[rb] - reg[ra];
   2271   1.1.1.2  christos 	  if (rt == 1)
   2272   1.1.1.2  christos 	    {
   2273   1.1.1.2  christos 	      if (reg[rt] > 0)
   2274   1.1.1.2  christos 		break;
   2275   1.1.1.2  christos 	      *sp_adjust = offset;
   2276   1.1.1.2  christos 	      return reg[rt];
   2277   1.1.1.2  christos 	    }
   2278       1.1     skrll 	}
   2279       1.1     skrll       else if ((buf[0] & 0xfc) == 0x40 /* il, ilh, ilhu, ila */)
   2280       1.1     skrll 	{
   2281       1.1     skrll 	  if (buf[0] >= 0x42 /* ila */)
   2282       1.1     skrll 	    imm |= (buf[0] & 1) << 17;
   2283       1.1     skrll 	  else
   2284       1.1     skrll 	    {
   2285       1.1     skrll 	      imm &= 0xffff;
   2286       1.1     skrll 
   2287       1.1     skrll 	      if (buf[0] == 0x40 /* il */)
   2288       1.1     skrll 		{
   2289       1.1     skrll 		  if ((buf[1] & 0x80) == 0)
   2290   1.1.1.2  christos 		    continue;
   2291       1.1     skrll 		  imm = (imm ^ 0x8000) - 0x8000;
   2292       1.1     skrll 		}
   2293       1.1     skrll 	      else if ((buf[1] & 0x80) == 0 /* ilhu */)
   2294       1.1     skrll 		imm <<= 16;
   2295       1.1     skrll 	    }
   2296       1.1     skrll 	  reg[rt] = imm;
   2297       1.1     skrll 	  continue;
   2298       1.1     skrll 	}
   2299       1.1     skrll       else if (buf[0] == 0x60 && (buf[1] & 0x80) != 0 /* iohl */)
   2300       1.1     skrll 	{
   2301       1.1     skrll 	  reg[rt] |= imm & 0xffff;
   2302       1.1     skrll 	  continue;
   2303       1.1     skrll 	}
   2304       1.1     skrll       else if (buf[0] == 0x04 /* ori */)
   2305       1.1     skrll 	{
   2306       1.1     skrll 	  imm >>= 7;
   2307       1.1     skrll 	  imm = (imm ^ 0x200) - 0x200;
   2308       1.1     skrll 	  reg[rt] = reg[ra] | imm;
   2309       1.1     skrll 	  continue;
   2310       1.1     skrll 	}
   2311   1.1.1.2  christos       else if (buf[0] == 0x32 && (buf[1] & 0x80) != 0 /* fsmbi */)
   2312       1.1     skrll 	{
   2313   1.1.1.2  christos 	  reg[rt] = (  ((imm & 0x8000) ? 0xff000000 : 0)
   2314   1.1.1.2  christos 		     | ((imm & 0x4000) ? 0x00ff0000 : 0)
   2315   1.1.1.2  christos 		     | ((imm & 0x2000) ? 0x0000ff00 : 0)
   2316   1.1.1.2  christos 		     | ((imm & 0x1000) ? 0x000000ff : 0));
   2317   1.1.1.2  christos 	  continue;
   2318   1.1.1.2  christos 	}
   2319   1.1.1.2  christos       else if (buf[0] == 0x16 /* andbi */)
   2320   1.1.1.2  christos 	{
   2321   1.1.1.2  christos 	  imm >>= 7;
   2322   1.1.1.2  christos 	  imm &= 0xff;
   2323   1.1.1.2  christos 	  imm |= imm << 8;
   2324   1.1.1.2  christos 	  imm |= imm << 16;
   2325   1.1.1.2  christos 	  reg[rt] = reg[ra] & imm;
   2326   1.1.1.2  christos 	  continue;
   2327   1.1.1.2  christos 	}
   2328   1.1.1.2  christos       else if (buf[0] == 0x33 && imm == 1 /* brsl .+4 */)
   2329   1.1.1.2  christos 	{
   2330   1.1.1.2  christos 	  /* Used in pic reg load.  Say rt is trashed.  Won't be used
   2331   1.1.1.2  christos 	     in stack adjust, but we need to continue past this branch.  */
   2332       1.1     skrll 	  reg[rt] = 0;
   2333       1.1     skrll 	  continue;
   2334       1.1     skrll 	}
   2335       1.1     skrll       else if (is_branch (buf) || is_indirect_branch (buf))
   2336       1.1     skrll 	/* If we hit a branch then we must be out of the prologue.  */
   2337       1.1     skrll 	break;
   2338       1.1     skrll     }
   2339       1.1     skrll 
   2340       1.1     skrll   return 0;
   2341       1.1     skrll }
   2342       1.1     skrll 
   2343       1.1     skrll /* qsort predicate to sort symbols by section and value.  */
   2344       1.1     skrll 
   2345       1.1     skrll static Elf_Internal_Sym *sort_syms_syms;
   2346       1.1     skrll static asection **sort_syms_psecs;
   2347       1.1     skrll 
   2348       1.1     skrll static int
   2349       1.1     skrll sort_syms (const void *a, const void *b)
   2350       1.1     skrll {
   2351       1.1     skrll   Elf_Internal_Sym *const *s1 = a;
   2352       1.1     skrll   Elf_Internal_Sym *const *s2 = b;
   2353       1.1     skrll   asection *sec1,*sec2;
   2354       1.1     skrll   bfd_signed_vma delta;
   2355       1.1     skrll 
   2356       1.1     skrll   sec1 = sort_syms_psecs[*s1 - sort_syms_syms];
   2357       1.1     skrll   sec2 = sort_syms_psecs[*s2 - sort_syms_syms];
   2358       1.1     skrll 
   2359       1.1     skrll   if (sec1 != sec2)
   2360       1.1     skrll     return sec1->index - sec2->index;
   2361       1.1     skrll 
   2362       1.1     skrll   delta = (*s1)->st_value - (*s2)->st_value;
   2363       1.1     skrll   if (delta != 0)
   2364       1.1     skrll     return delta < 0 ? -1 : 1;
   2365       1.1     skrll 
   2366       1.1     skrll   delta = (*s2)->st_size - (*s1)->st_size;
   2367       1.1     skrll   if (delta != 0)
   2368       1.1     skrll     return delta < 0 ? -1 : 1;
   2369       1.1     skrll 
   2370       1.1     skrll   return *s1 < *s2 ? -1 : 1;
   2371       1.1     skrll }
   2372       1.1     skrll 
   2373       1.1     skrll /* Allocate a struct spu_elf_stack_info with MAX_FUN struct function_info
   2374       1.1     skrll    entries for section SEC.  */
   2375       1.1     skrll 
   2376       1.1     skrll static struct spu_elf_stack_info *
   2377       1.1     skrll alloc_stack_info (asection *sec, int max_fun)
   2378       1.1     skrll {
   2379       1.1     skrll   struct _spu_elf_section_data *sec_data = spu_elf_section_data (sec);
   2380       1.1     skrll   bfd_size_type amt;
   2381       1.1     skrll 
   2382       1.1     skrll   amt = sizeof (struct spu_elf_stack_info);
   2383       1.1     skrll   amt += (max_fun - 1) * sizeof (struct function_info);
   2384       1.1     skrll   sec_data->u.i.stack_info = bfd_zmalloc (amt);
   2385       1.1     skrll   if (sec_data->u.i.stack_info != NULL)
   2386       1.1     skrll     sec_data->u.i.stack_info->max_fun = max_fun;
   2387       1.1     skrll   return sec_data->u.i.stack_info;
   2388       1.1     skrll }
   2389       1.1     skrll 
   2390       1.1     skrll /* Add a new struct function_info describing a (part of a) function
   2391       1.1     skrll    starting at SYM_H.  Keep the array sorted by address.  */
   2392       1.1     skrll 
   2393       1.1     skrll static struct function_info *
   2394       1.1     skrll maybe_insert_function (asection *sec,
   2395       1.1     skrll 		       void *sym_h,
   2396   1.1.1.9  christos 		       bool global,
   2397   1.1.1.9  christos 		       bool is_func)
   2398       1.1     skrll {
   2399       1.1     skrll   struct _spu_elf_section_data *sec_data = spu_elf_section_data (sec);
   2400       1.1     skrll   struct spu_elf_stack_info *sinfo = sec_data->u.i.stack_info;
   2401       1.1     skrll   int i;
   2402       1.1     skrll   bfd_vma off, size;
   2403       1.1     skrll 
   2404       1.1     skrll   if (sinfo == NULL)
   2405       1.1     skrll     {
   2406       1.1     skrll       sinfo = alloc_stack_info (sec, 20);
   2407       1.1     skrll       if (sinfo == NULL)
   2408       1.1     skrll 	return NULL;
   2409       1.1     skrll     }
   2410       1.1     skrll 
   2411       1.1     skrll   if (!global)
   2412       1.1     skrll     {
   2413       1.1     skrll       Elf_Internal_Sym *sym = sym_h;
   2414       1.1     skrll       off = sym->st_value;
   2415       1.1     skrll       size = sym->st_size;
   2416       1.1     skrll     }
   2417       1.1     skrll   else
   2418       1.1     skrll     {
   2419       1.1     skrll       struct elf_link_hash_entry *h = sym_h;
   2420       1.1     skrll       off = h->root.u.def.value;
   2421       1.1     skrll       size = h->size;
   2422       1.1     skrll     }
   2423       1.1     skrll 
   2424       1.1     skrll   for (i = sinfo->num_fun; --i >= 0; )
   2425       1.1     skrll     if (sinfo->fun[i].lo <= off)
   2426       1.1     skrll       break;
   2427       1.1     skrll 
   2428       1.1     skrll   if (i >= 0)
   2429       1.1     skrll     {
   2430       1.1     skrll       /* Don't add another entry for an alias, but do update some
   2431       1.1     skrll 	 info.  */
   2432       1.1     skrll       if (sinfo->fun[i].lo == off)
   2433       1.1     skrll 	{
   2434       1.1     skrll 	  /* Prefer globals over local syms.  */
   2435       1.1     skrll 	  if (global && !sinfo->fun[i].global)
   2436       1.1     skrll 	    {
   2437   1.1.1.9  christos 	      sinfo->fun[i].global = true;
   2438       1.1     skrll 	      sinfo->fun[i].u.h = sym_h;
   2439       1.1     skrll 	    }
   2440       1.1     skrll 	  if (is_func)
   2441   1.1.1.9  christos 	    sinfo->fun[i].is_func = true;
   2442       1.1     skrll 	  return &sinfo->fun[i];
   2443       1.1     skrll 	}
   2444       1.1     skrll       /* Ignore a zero-size symbol inside an existing function.  */
   2445       1.1     skrll       else if (sinfo->fun[i].hi > off && size == 0)
   2446       1.1     skrll 	return &sinfo->fun[i];
   2447       1.1     skrll     }
   2448       1.1     skrll 
   2449       1.1     skrll   if (sinfo->num_fun >= sinfo->max_fun)
   2450       1.1     skrll     {
   2451       1.1     skrll       bfd_size_type amt = sizeof (struct spu_elf_stack_info);
   2452       1.1     skrll       bfd_size_type old = amt;
   2453       1.1     skrll 
   2454       1.1     skrll       old += (sinfo->max_fun - 1) * sizeof (struct function_info);
   2455       1.1     skrll       sinfo->max_fun += 20 + (sinfo->max_fun >> 1);
   2456       1.1     skrll       amt += (sinfo->max_fun - 1) * sizeof (struct function_info);
   2457       1.1     skrll       sinfo = bfd_realloc (sinfo, amt);
   2458       1.1     skrll       if (sinfo == NULL)
   2459       1.1     skrll 	return NULL;
   2460       1.1     skrll       memset ((char *) sinfo + old, 0, amt - old);
   2461       1.1     skrll       sec_data->u.i.stack_info = sinfo;
   2462       1.1     skrll     }
   2463       1.1     skrll 
   2464       1.1     skrll   if (++i < sinfo->num_fun)
   2465       1.1     skrll     memmove (&sinfo->fun[i + 1], &sinfo->fun[i],
   2466       1.1     skrll 	     (sinfo->num_fun - i) * sizeof (sinfo->fun[i]));
   2467       1.1     skrll   sinfo->fun[i].is_func = is_func;
   2468       1.1     skrll   sinfo->fun[i].global = global;
   2469       1.1     skrll   sinfo->fun[i].sec = sec;
   2470       1.1     skrll   if (global)
   2471       1.1     skrll     sinfo->fun[i].u.h = sym_h;
   2472       1.1     skrll   else
   2473       1.1     skrll     sinfo->fun[i].u.sym = sym_h;
   2474       1.1     skrll   sinfo->fun[i].lo = off;
   2475       1.1     skrll   sinfo->fun[i].hi = off + size;
   2476   1.1.1.2  christos   sinfo->fun[i].lr_store = -1;
   2477   1.1.1.2  christos   sinfo->fun[i].sp_adjust = -1;
   2478   1.1.1.2  christos   sinfo->fun[i].stack = -find_function_stack_adjust (sec, off,
   2479   1.1.1.2  christos 						     &sinfo->fun[i].lr_store,
   2480   1.1.1.2  christos 						     &sinfo->fun[i].sp_adjust);
   2481       1.1     skrll   sinfo->num_fun += 1;
   2482       1.1     skrll   return &sinfo->fun[i];
   2483       1.1     skrll }
   2484       1.1     skrll 
   2485       1.1     skrll /* Return the name of FUN.  */
   2486       1.1     skrll 
   2487       1.1     skrll static const char *
   2488       1.1     skrll func_name (struct function_info *fun)
   2489       1.1     skrll {
   2490       1.1     skrll   asection *sec;
   2491       1.1     skrll   bfd *ibfd;
   2492       1.1     skrll   Elf_Internal_Shdr *symtab_hdr;
   2493       1.1     skrll 
   2494       1.1     skrll   while (fun->start != NULL)
   2495       1.1     skrll     fun = fun->start;
   2496       1.1     skrll 
   2497       1.1     skrll   if (fun->global)
   2498       1.1     skrll     return fun->u.h->root.root.string;
   2499       1.1     skrll 
   2500       1.1     skrll   sec = fun->sec;
   2501       1.1     skrll   if (fun->u.sym->st_name == 0)
   2502       1.1     skrll     {
   2503       1.1     skrll       size_t len = strlen (sec->name);
   2504       1.1     skrll       char *name = bfd_malloc (len + 10);
   2505       1.1     skrll       if (name == NULL)
   2506       1.1     skrll 	return "(null)";
   2507       1.1     skrll       sprintf (name, "%s+%lx", sec->name,
   2508       1.1     skrll 	       (unsigned long) fun->u.sym->st_value & 0xffffffff);
   2509       1.1     skrll       return name;
   2510       1.1     skrll     }
   2511       1.1     skrll   ibfd = sec->owner;
   2512       1.1     skrll   symtab_hdr = &elf_tdata (ibfd)->symtab_hdr;
   2513       1.1     skrll   return bfd_elf_sym_name (ibfd, symtab_hdr, fun->u.sym, sec);
   2514       1.1     skrll }
   2515       1.1     skrll 
   2516       1.1     skrll /* Read the instruction at OFF in SEC.  Return true iff the instruction
   2517       1.1     skrll    is a nop, lnop, or stop 0 (all zero insn).  */
   2518       1.1     skrll 
   2519   1.1.1.9  christos static bool
   2520       1.1     skrll is_nop (asection *sec, bfd_vma off)
   2521       1.1     skrll {
   2522       1.1     skrll   unsigned char insn[4];
   2523       1.1     skrll 
   2524       1.1     skrll   if (off + 4 > sec->size
   2525       1.1     skrll       || !bfd_get_section_contents (sec->owner, sec, insn, off, 4))
   2526   1.1.1.9  christos     return false;
   2527       1.1     skrll   if ((insn[0] & 0xbf) == 0 && (insn[1] & 0xe0) == 0x20)
   2528   1.1.1.9  christos     return true;
   2529       1.1     skrll   if (insn[0] == 0 && insn[1] == 0 && insn[2] == 0 && insn[3] == 0)
   2530   1.1.1.9  christos     return true;
   2531   1.1.1.9  christos   return false;
   2532       1.1     skrll }
   2533       1.1     skrll 
   2534       1.1     skrll /* Extend the range of FUN to cover nop padding up to LIMIT.
   2535       1.1     skrll    Return TRUE iff some instruction other than a NOP was found.  */
   2536       1.1     skrll 
   2537   1.1.1.9  christos static bool
   2538       1.1     skrll insns_at_end (struct function_info *fun, bfd_vma limit)
   2539       1.1     skrll {
   2540       1.1     skrll   bfd_vma off = (fun->hi + 3) & -4;
   2541       1.1     skrll 
   2542       1.1     skrll   while (off < limit && is_nop (fun->sec, off))
   2543       1.1     skrll     off += 4;
   2544       1.1     skrll   if (off < limit)
   2545       1.1     skrll     {
   2546       1.1     skrll       fun->hi = off;
   2547   1.1.1.9  christos       return true;
   2548       1.1     skrll     }
   2549       1.1     skrll   fun->hi = limit;
   2550   1.1.1.9  christos   return false;
   2551       1.1     skrll }
   2552       1.1     skrll 
   2553       1.1     skrll /* Check and fix overlapping function ranges.  Return TRUE iff there
   2554       1.1     skrll    are gaps in the current info we have about functions in SEC.  */
   2555       1.1     skrll 
   2556   1.1.1.9  christos static bool
   2557       1.1     skrll check_function_ranges (asection *sec, struct bfd_link_info *info)
   2558       1.1     skrll {
   2559       1.1     skrll   struct _spu_elf_section_data *sec_data = spu_elf_section_data (sec);
   2560       1.1     skrll   struct spu_elf_stack_info *sinfo = sec_data->u.i.stack_info;
   2561       1.1     skrll   int i;
   2562   1.1.1.9  christos   bool gaps = false;
   2563       1.1     skrll 
   2564       1.1     skrll   if (sinfo == NULL)
   2565   1.1.1.9  christos     return false;
   2566       1.1     skrll 
   2567       1.1     skrll   for (i = 1; i < sinfo->num_fun; i++)
   2568       1.1     skrll     if (sinfo->fun[i - 1].hi > sinfo->fun[i].lo)
   2569       1.1     skrll       {
   2570       1.1     skrll 	/* Fix overlapping symbols.  */
   2571       1.1     skrll 	const char *f1 = func_name (&sinfo->fun[i - 1]);
   2572       1.1     skrll 	const char *f2 = func_name (&sinfo->fun[i]);
   2573       1.1     skrll 
   2574   1.1.1.6  christos 	/* xgettext:c-format */
   2575       1.1     skrll 	info->callbacks->einfo (_("warning: %s overlaps %s\n"), f1, f2);
   2576       1.1     skrll 	sinfo->fun[i - 1].hi = sinfo->fun[i].lo;
   2577       1.1     skrll       }
   2578       1.1     skrll     else if (insns_at_end (&sinfo->fun[i - 1], sinfo->fun[i].lo))
   2579   1.1.1.9  christos       gaps = true;
   2580       1.1     skrll 
   2581       1.1     skrll   if (sinfo->num_fun == 0)
   2582   1.1.1.9  christos     gaps = true;
   2583       1.1     skrll   else
   2584       1.1     skrll     {
   2585       1.1     skrll       if (sinfo->fun[0].lo != 0)
   2586   1.1.1.9  christos 	gaps = true;
   2587       1.1     skrll       if (sinfo->fun[sinfo->num_fun - 1].hi > sec->size)
   2588       1.1     skrll 	{
   2589       1.1     skrll 	  const char *f1 = func_name (&sinfo->fun[sinfo->num_fun - 1]);
   2590       1.1     skrll 
   2591       1.1     skrll 	  info->callbacks->einfo (_("warning: %s exceeds section size\n"), f1);
   2592       1.1     skrll 	  sinfo->fun[sinfo->num_fun - 1].hi = sec->size;
   2593       1.1     skrll 	}
   2594       1.1     skrll       else if (insns_at_end (&sinfo->fun[sinfo->num_fun - 1], sec->size))
   2595   1.1.1.9  christos 	gaps = true;
   2596       1.1     skrll     }
   2597       1.1     skrll   return gaps;
   2598       1.1     skrll }
   2599       1.1     skrll 
   2600       1.1     skrll /* Search current function info for a function that contains address
   2601       1.1     skrll    OFFSET in section SEC.  */
   2602       1.1     skrll 
   2603       1.1     skrll static struct function_info *
   2604       1.1     skrll find_function (asection *sec, bfd_vma offset, struct bfd_link_info *info)
   2605       1.1     skrll {
   2606       1.1     skrll   struct _spu_elf_section_data *sec_data = spu_elf_section_data (sec);
   2607       1.1     skrll   struct spu_elf_stack_info *sinfo = sec_data->u.i.stack_info;
   2608       1.1     skrll   int lo, hi, mid;
   2609       1.1     skrll 
   2610       1.1     skrll   lo = 0;
   2611       1.1     skrll   hi = sinfo->num_fun;
   2612       1.1     skrll   while (lo < hi)
   2613       1.1     skrll     {
   2614       1.1     skrll       mid = (lo + hi) / 2;
   2615       1.1     skrll       if (offset < sinfo->fun[mid].lo)
   2616       1.1     skrll 	hi = mid;
   2617       1.1     skrll       else if (offset >= sinfo->fun[mid].hi)
   2618       1.1     skrll 	lo = mid + 1;
   2619       1.1     skrll       else
   2620       1.1     skrll 	return &sinfo->fun[mid];
   2621       1.1     skrll     }
   2622   1.1.1.6  christos   /* xgettext:c-format */
   2623   1.1.1.7  christos   info->callbacks->einfo (_("%pA:0x%v not found in function table\n"),
   2624       1.1     skrll 			  sec, offset);
   2625   1.1.1.2  christos   bfd_set_error (bfd_error_bad_value);
   2626       1.1     skrll   return NULL;
   2627       1.1     skrll }
   2628       1.1     skrll 
   2629       1.1     skrll /* Add CALLEE to CALLER call list if not already present.  Return TRUE
   2630       1.1     skrll    if CALLEE was new.  If this function return FALSE, CALLEE should
   2631       1.1     skrll    be freed.  */
   2632       1.1     skrll 
   2633   1.1.1.9  christos static bool
   2634       1.1     skrll insert_callee (struct function_info *caller, struct call_info *callee)
   2635       1.1     skrll {
   2636       1.1     skrll   struct call_info **pp, *p;
   2637       1.1     skrll 
   2638       1.1     skrll   for (pp = &caller->call_list; (p = *pp) != NULL; pp = &p->next)
   2639       1.1     skrll     if (p->fun == callee->fun)
   2640       1.1     skrll       {
   2641       1.1     skrll 	/* Tail calls use less stack than normal calls.  Retain entry
   2642       1.1     skrll 	   for normal call over one for tail call.  */
   2643       1.1     skrll 	p->is_tail &= callee->is_tail;
   2644       1.1     skrll 	if (!p->is_tail)
   2645       1.1     skrll 	  {
   2646       1.1     skrll 	    p->fun->start = NULL;
   2647   1.1.1.9  christos 	    p->fun->is_func = true;
   2648       1.1     skrll 	  }
   2649   1.1.1.2  christos 	p->count += callee->count;
   2650       1.1     skrll 	/* Reorder list so most recent call is first.  */
   2651       1.1     skrll 	*pp = p->next;
   2652       1.1     skrll 	p->next = caller->call_list;
   2653       1.1     skrll 	caller->call_list = p;
   2654   1.1.1.9  christos 	return false;
   2655       1.1     skrll       }
   2656       1.1     skrll   callee->next = caller->call_list;
   2657       1.1     skrll   caller->call_list = callee;
   2658   1.1.1.9  christos   return true;
   2659       1.1     skrll }
   2660       1.1     skrll 
   2661       1.1     skrll /* Copy CALL and insert the copy into CALLER.  */
   2662       1.1     skrll 
   2663   1.1.1.9  christos static bool
   2664       1.1     skrll copy_callee (struct function_info *caller, const struct call_info *call)
   2665       1.1     skrll {
   2666       1.1     skrll   struct call_info *callee;
   2667       1.1     skrll   callee = bfd_malloc (sizeof (*callee));
   2668       1.1     skrll   if (callee == NULL)
   2669   1.1.1.9  christos     return false;
   2670       1.1     skrll   *callee = *call;
   2671       1.1     skrll   if (!insert_callee (caller, callee))
   2672       1.1     skrll     free (callee);
   2673   1.1.1.9  christos   return true;
   2674       1.1     skrll }
   2675       1.1     skrll 
   2676       1.1     skrll /* We're only interested in code sections.  Testing SEC_IN_MEMORY excludes
   2677       1.1     skrll    overlay stub sections.  */
   2678       1.1     skrll 
   2679   1.1.1.9  christos static bool
   2680   1.1.1.2  christos interesting_section (asection *s)
   2681       1.1     skrll {
   2682   1.1.1.2  christos   return (s->output_section != bfd_abs_section_ptr
   2683       1.1     skrll 	  && ((s->flags & (SEC_ALLOC | SEC_LOAD | SEC_CODE | SEC_IN_MEMORY))
   2684       1.1     skrll 	      == (SEC_ALLOC | SEC_LOAD | SEC_CODE))
   2685       1.1     skrll 	  && s->size != 0);
   2686       1.1     skrll }
   2687       1.1     skrll 
   2688       1.1     skrll /* Rummage through the relocs for SEC, looking for function calls.
   2689       1.1     skrll    If CALL_TREE is true, fill in call graph.  If CALL_TREE is false,
   2690       1.1     skrll    mark destination symbols on calls as being functions.  Also
   2691       1.1     skrll    look at branches, which may be tail calls or go to hot/cold
   2692       1.1     skrll    section part of same function.  */
   2693       1.1     skrll 
   2694   1.1.1.9  christos static bool
   2695       1.1     skrll mark_functions_via_relocs (asection *sec,
   2696       1.1     skrll 			   struct bfd_link_info *info,
   2697       1.1     skrll 			   int call_tree)
   2698       1.1     skrll {
   2699       1.1     skrll   Elf_Internal_Rela *internal_relocs, *irelaend, *irela;
   2700       1.1     skrll   Elf_Internal_Shdr *symtab_hdr;
   2701       1.1     skrll   void *psyms;
   2702   1.1.1.2  christos   unsigned int priority = 0;
   2703   1.1.1.9  christos   static bool warned;
   2704       1.1     skrll 
   2705   1.1.1.2  christos   if (!interesting_section (sec)
   2706       1.1     skrll       || sec->reloc_count == 0)
   2707   1.1.1.9  christos     return true;
   2708       1.1     skrll 
   2709       1.1     skrll   internal_relocs = _bfd_elf_link_read_relocs (sec->owner, sec, NULL, NULL,
   2710       1.1     skrll 					       info->keep_memory);
   2711       1.1     skrll   if (internal_relocs == NULL)
   2712   1.1.1.9  christos     return false;
   2713       1.1     skrll 
   2714       1.1     skrll   symtab_hdr = &elf_tdata (sec->owner)->symtab_hdr;
   2715       1.1     skrll   psyms = &symtab_hdr->contents;
   2716       1.1     skrll   irela = internal_relocs;
   2717       1.1     skrll   irelaend = irela + sec->reloc_count;
   2718       1.1     skrll   for (; irela < irelaend; irela++)
   2719       1.1     skrll     {
   2720       1.1     skrll       enum elf_spu_reloc_type r_type;
   2721       1.1     skrll       unsigned int r_indx;
   2722       1.1     skrll       asection *sym_sec;
   2723       1.1     skrll       Elf_Internal_Sym *sym;
   2724       1.1     skrll       struct elf_link_hash_entry *h;
   2725       1.1     skrll       bfd_vma val;
   2726   1.1.1.9  christos       bool nonbranch, is_call;
   2727       1.1     skrll       struct function_info *caller;
   2728       1.1     skrll       struct call_info *callee;
   2729       1.1     skrll 
   2730       1.1     skrll       r_type = ELF32_R_TYPE (irela->r_info);
   2731   1.1.1.2  christos       nonbranch = r_type != R_SPU_REL16 && r_type != R_SPU_ADDR16;
   2732       1.1     skrll 
   2733       1.1     skrll       r_indx = ELF32_R_SYM (irela->r_info);
   2734       1.1     skrll       if (!get_sym_h (&h, &sym, &sym_sec, psyms, r_indx, sec->owner))
   2735   1.1.1.9  christos 	return false;
   2736       1.1     skrll 
   2737       1.1     skrll       if (sym_sec == NULL
   2738   1.1.1.2  christos 	  || sym_sec->output_section == bfd_abs_section_ptr)
   2739       1.1     skrll 	continue;
   2740       1.1     skrll 
   2741   1.1.1.9  christos       is_call = false;
   2742   1.1.1.2  christos       if (!nonbranch)
   2743       1.1     skrll 	{
   2744       1.1     skrll 	  unsigned char insn[4];
   2745       1.1     skrll 
   2746       1.1     skrll 	  if (!bfd_get_section_contents (sec->owner, sec, insn,
   2747       1.1     skrll 					 irela->r_offset, 4))
   2748   1.1.1.9  christos 	    return false;
   2749       1.1     skrll 	  if (is_branch (insn))
   2750       1.1     skrll 	    {
   2751       1.1     skrll 	      is_call = (insn[0] & 0xfd) == 0x31;
   2752   1.1.1.2  christos 	      priority = insn[1] & 0x0f;
   2753   1.1.1.2  christos 	      priority <<= 8;
   2754   1.1.1.2  christos 	      priority |= insn[2];
   2755   1.1.1.2  christos 	      priority <<= 8;
   2756   1.1.1.2  christos 	      priority |= insn[3];
   2757   1.1.1.2  christos 	      priority >>= 7;
   2758       1.1     skrll 	      if ((sym_sec->flags & (SEC_ALLOC | SEC_LOAD | SEC_CODE))
   2759       1.1     skrll 		  != (SEC_ALLOC | SEC_LOAD | SEC_CODE))
   2760       1.1     skrll 		{
   2761       1.1     skrll 		  if (!warned)
   2762       1.1     skrll 		    info->callbacks->einfo
   2763   1.1.1.6  christos 		      /* xgettext:c-format */
   2764   1.1.1.7  christos 		      (_("%pB(%pA+0x%v): call to non-code section"
   2765   1.1.1.7  christos 			 " %pB(%pA), analysis incomplete\n"),
   2766       1.1     skrll 		       sec->owner, sec, irela->r_offset,
   2767       1.1     skrll 		       sym_sec->owner, sym_sec);
   2768   1.1.1.9  christos 		  warned = true;
   2769       1.1     skrll 		  continue;
   2770       1.1     skrll 		}
   2771       1.1     skrll 	    }
   2772       1.1     skrll 	  else
   2773       1.1     skrll 	    {
   2774   1.1.1.9  christos 	      nonbranch = true;
   2775   1.1.1.2  christos 	      if (is_hint (insn))
   2776       1.1     skrll 		continue;
   2777       1.1     skrll 	    }
   2778       1.1     skrll 	}
   2779       1.1     skrll 
   2780   1.1.1.2  christos       if (nonbranch)
   2781       1.1     skrll 	{
   2782       1.1     skrll 	  /* For --auto-overlay, count possible stubs we need for
   2783       1.1     skrll 	     function pointer references.  */
   2784       1.1     skrll 	  unsigned int sym_type;
   2785       1.1     skrll 	  if (h)
   2786       1.1     skrll 	    sym_type = h->type;
   2787       1.1     skrll 	  else
   2788       1.1     skrll 	    sym_type = ELF_ST_TYPE (sym->st_info);
   2789       1.1     skrll 	  if (sym_type == STT_FUNC)
   2790   1.1.1.2  christos 	    {
   2791   1.1.1.2  christos 	      if (call_tree && spu_hash_table (info)->params->auto_overlay)
   2792   1.1.1.2  christos 		spu_hash_table (info)->non_ovly_stub += 1;
   2793   1.1.1.2  christos 	      /* If the symbol type is STT_FUNC then this must be a
   2794   1.1.1.2  christos 		 function pointer initialisation.  */
   2795   1.1.1.2  christos 	      continue;
   2796   1.1.1.2  christos 	    }
   2797   1.1.1.2  christos 	  /* Ignore data references.  */
   2798   1.1.1.2  christos 	  if ((sym_sec->flags & (SEC_ALLOC | SEC_LOAD | SEC_CODE))
   2799   1.1.1.2  christos 	      != (SEC_ALLOC | SEC_LOAD | SEC_CODE))
   2800   1.1.1.2  christos 	    continue;
   2801   1.1.1.2  christos 	  /* Otherwise we probably have a jump table reloc for
   2802   1.1.1.2  christos 	     a switch statement or some other reference to a
   2803   1.1.1.2  christos 	     code label.  */
   2804       1.1     skrll 	}
   2805       1.1     skrll 
   2806       1.1     skrll       if (h)
   2807       1.1     skrll 	val = h->root.u.def.value;
   2808       1.1     skrll       else
   2809       1.1     skrll 	val = sym->st_value;
   2810       1.1     skrll       val += irela->r_addend;
   2811       1.1     skrll 
   2812       1.1     skrll       if (!call_tree)
   2813       1.1     skrll 	{
   2814       1.1     skrll 	  struct function_info *fun;
   2815       1.1     skrll 
   2816       1.1     skrll 	  if (irela->r_addend != 0)
   2817       1.1     skrll 	    {
   2818       1.1     skrll 	      Elf_Internal_Sym *fake = bfd_zmalloc (sizeof (*fake));
   2819       1.1     skrll 	      if (fake == NULL)
   2820   1.1.1.9  christos 		return false;
   2821       1.1     skrll 	      fake->st_value = val;
   2822       1.1     skrll 	      fake->st_shndx
   2823       1.1     skrll 		= _bfd_elf_section_from_bfd_section (sym_sec->owner, sym_sec);
   2824       1.1     skrll 	      sym = fake;
   2825       1.1     skrll 	    }
   2826       1.1     skrll 	  if (sym)
   2827   1.1.1.9  christos 	    fun = maybe_insert_function (sym_sec, sym, false, is_call);
   2828       1.1     skrll 	  else
   2829   1.1.1.9  christos 	    fun = maybe_insert_function (sym_sec, h, true, is_call);
   2830       1.1     skrll 	  if (fun == NULL)
   2831   1.1.1.9  christos 	    return false;
   2832       1.1     skrll 	  if (irela->r_addend != 0
   2833       1.1     skrll 	      && fun->u.sym != sym)
   2834       1.1     skrll 	    free (sym);
   2835       1.1     skrll 	  continue;
   2836       1.1     skrll 	}
   2837       1.1     skrll 
   2838       1.1     skrll       caller = find_function (sec, irela->r_offset, info);
   2839       1.1     skrll       if (caller == NULL)
   2840   1.1.1.9  christos 	return false;
   2841       1.1     skrll       callee = bfd_malloc (sizeof *callee);
   2842       1.1     skrll       if (callee == NULL)
   2843   1.1.1.9  christos 	return false;
   2844       1.1     skrll 
   2845       1.1     skrll       callee->fun = find_function (sym_sec, val, info);
   2846       1.1     skrll       if (callee->fun == NULL)
   2847   1.1.1.9  christos 	return false;
   2848       1.1     skrll       callee->is_tail = !is_call;
   2849   1.1.1.9  christos       callee->is_pasted = false;
   2850   1.1.1.9  christos       callee->broken_cycle = false;
   2851   1.1.1.2  christos       callee->priority = priority;
   2852   1.1.1.2  christos       callee->count = nonbranch? 0 : 1;
   2853       1.1     skrll       if (callee->fun->last_caller != sec)
   2854       1.1     skrll 	{
   2855       1.1     skrll 	  callee->fun->last_caller = sec;
   2856       1.1     skrll 	  callee->fun->call_count += 1;
   2857       1.1     skrll 	}
   2858       1.1     skrll       if (!insert_callee (caller, callee))
   2859       1.1     skrll 	free (callee);
   2860       1.1     skrll       else if (!is_call
   2861       1.1     skrll 	       && !callee->fun->is_func
   2862       1.1     skrll 	       && callee->fun->stack == 0)
   2863       1.1     skrll 	{
   2864       1.1     skrll 	  /* This is either a tail call or a branch from one part of
   2865       1.1     skrll 	     the function to another, ie. hot/cold section.  If the
   2866       1.1     skrll 	     destination has been called by some other function then
   2867       1.1     skrll 	     it is a separate function.  We also assume that functions
   2868       1.1     skrll 	     are not split across input files.  */
   2869       1.1     skrll 	  if (sec->owner != sym_sec->owner)
   2870       1.1     skrll 	    {
   2871       1.1     skrll 	      callee->fun->start = NULL;
   2872   1.1.1.9  christos 	      callee->fun->is_func = true;
   2873       1.1     skrll 	    }
   2874       1.1     skrll 	  else if (callee->fun->start == NULL)
   2875   1.1.1.2  christos 	    {
   2876   1.1.1.2  christos 	      struct function_info *caller_start = caller;
   2877   1.1.1.2  christos 	      while (caller_start->start)
   2878   1.1.1.2  christos 		caller_start = caller_start->start;
   2879   1.1.1.2  christos 
   2880   1.1.1.2  christos 	      if (caller_start != callee->fun)
   2881   1.1.1.2  christos 		callee->fun->start = caller_start;
   2882   1.1.1.2  christos 	    }
   2883       1.1     skrll 	  else
   2884       1.1     skrll 	    {
   2885       1.1     skrll 	      struct function_info *callee_start;
   2886       1.1     skrll 	      struct function_info *caller_start;
   2887       1.1     skrll 	      callee_start = callee->fun;
   2888       1.1     skrll 	      while (callee_start->start)
   2889       1.1     skrll 		callee_start = callee_start->start;
   2890       1.1     skrll 	      caller_start = caller;
   2891       1.1     skrll 	      while (caller_start->start)
   2892       1.1     skrll 		caller_start = caller_start->start;
   2893       1.1     skrll 	      if (caller_start != callee_start)
   2894       1.1     skrll 		{
   2895       1.1     skrll 		  callee->fun->start = NULL;
   2896   1.1.1.9  christos 		  callee->fun->is_func = true;
   2897       1.1     skrll 		}
   2898       1.1     skrll 	    }
   2899       1.1     skrll 	}
   2900       1.1     skrll     }
   2901       1.1     skrll 
   2902   1.1.1.9  christos   return true;
   2903       1.1     skrll }
   2904       1.1     skrll 
   2905       1.1     skrll /* Handle something like .init or .fini, which has a piece of a function.
   2906       1.1     skrll    These sections are pasted together to form a single function.  */
   2907       1.1     skrll 
   2908   1.1.1.9  christos static bool
   2909   1.1.1.2  christos pasted_function (asection *sec)
   2910       1.1     skrll {
   2911       1.1     skrll   struct bfd_link_order *l;
   2912       1.1     skrll   struct _spu_elf_section_data *sec_data;
   2913       1.1     skrll   struct spu_elf_stack_info *sinfo;
   2914       1.1     skrll   Elf_Internal_Sym *fake;
   2915       1.1     skrll   struct function_info *fun, *fun_start;
   2916       1.1     skrll 
   2917       1.1     skrll   fake = bfd_zmalloc (sizeof (*fake));
   2918       1.1     skrll   if (fake == NULL)
   2919   1.1.1.9  christos     return false;
   2920       1.1     skrll   fake->st_value = 0;
   2921       1.1     skrll   fake->st_size = sec->size;
   2922       1.1     skrll   fake->st_shndx
   2923       1.1     skrll     = _bfd_elf_section_from_bfd_section (sec->owner, sec);
   2924   1.1.1.9  christos   fun = maybe_insert_function (sec, fake, false, false);
   2925       1.1     skrll   if (!fun)
   2926   1.1.1.9  christos     return false;
   2927       1.1     skrll 
   2928       1.1     skrll   /* Find a function immediately preceding this section.  */
   2929       1.1     skrll   fun_start = NULL;
   2930       1.1     skrll   for (l = sec->output_section->map_head.link_order; l != NULL; l = l->next)
   2931       1.1     skrll     {
   2932       1.1     skrll       if (l->u.indirect.section == sec)
   2933       1.1     skrll 	{
   2934       1.1     skrll 	  if (fun_start != NULL)
   2935       1.1     skrll 	    {
   2936       1.1     skrll 	      struct call_info *callee = bfd_malloc (sizeof *callee);
   2937       1.1     skrll 	      if (callee == NULL)
   2938   1.1.1.9  christos 		return false;
   2939       1.1     skrll 
   2940       1.1     skrll 	      fun->start = fun_start;
   2941       1.1     skrll 	      callee->fun = fun;
   2942   1.1.1.9  christos 	      callee->is_tail = true;
   2943   1.1.1.9  christos 	      callee->is_pasted = true;
   2944   1.1.1.9  christos 	      callee->broken_cycle = false;
   2945   1.1.1.2  christos 	      callee->priority = 0;
   2946   1.1.1.2  christos 	      callee->count = 1;
   2947       1.1     skrll 	      if (!insert_callee (fun_start, callee))
   2948       1.1     skrll 		free (callee);
   2949   1.1.1.9  christos 	      return true;
   2950       1.1     skrll 	    }
   2951       1.1     skrll 	  break;
   2952       1.1     skrll 	}
   2953       1.1     skrll       if (l->type == bfd_indirect_link_order
   2954       1.1     skrll 	  && (sec_data = spu_elf_section_data (l->u.indirect.section)) != NULL
   2955       1.1     skrll 	  && (sinfo = sec_data->u.i.stack_info) != NULL
   2956       1.1     skrll 	  && sinfo->num_fun != 0)
   2957       1.1     skrll 	fun_start = &sinfo->fun[sinfo->num_fun - 1];
   2958       1.1     skrll     }
   2959       1.1     skrll 
   2960   1.1.1.2  christos   /* Don't return an error if we did not find a function preceding this
   2961   1.1.1.2  christos      section.  The section may have incorrect flags.  */
   2962   1.1.1.9  christos   return true;
   2963       1.1     skrll }
   2964       1.1     skrll 
   2965       1.1     skrll /* Map address ranges in code sections to functions.  */
   2966       1.1     skrll 
   2967   1.1.1.9  christos static bool
   2968       1.1     skrll discover_functions (struct bfd_link_info *info)
   2969       1.1     skrll {
   2970       1.1     skrll   bfd *ibfd;
   2971       1.1     skrll   int bfd_idx;
   2972       1.1     skrll   Elf_Internal_Sym ***psym_arr;
   2973       1.1     skrll   asection ***sec_arr;
   2974   1.1.1.9  christos   bool gaps = false;
   2975       1.1     skrll 
   2976       1.1     skrll   bfd_idx = 0;
   2977   1.1.1.4  christos   for (ibfd = info->input_bfds; ibfd != NULL; ibfd = ibfd->link.next)
   2978       1.1     skrll     bfd_idx++;
   2979       1.1     skrll 
   2980       1.1     skrll   psym_arr = bfd_zmalloc (bfd_idx * sizeof (*psym_arr));
   2981       1.1     skrll   if (psym_arr == NULL)
   2982   1.1.1.9  christos     return false;
   2983       1.1     skrll   sec_arr = bfd_zmalloc (bfd_idx * sizeof (*sec_arr));
   2984       1.1     skrll   if (sec_arr == NULL)
   2985   1.1.1.9  christos     return false;
   2986   1.1.1.4  christos 
   2987       1.1     skrll   for (ibfd = info->input_bfds, bfd_idx = 0;
   2988       1.1     skrll        ibfd != NULL;
   2989   1.1.1.4  christos        ibfd = ibfd->link.next, bfd_idx++)
   2990       1.1     skrll     {
   2991   1.1.1.4  christos       extern const bfd_target spu_elf32_vec;
   2992       1.1     skrll       Elf_Internal_Shdr *symtab_hdr;
   2993       1.1     skrll       asection *sec;
   2994       1.1     skrll       size_t symcount;
   2995       1.1     skrll       Elf_Internal_Sym *syms, *sy, **psyms, **psy;
   2996       1.1     skrll       asection **psecs, **p;
   2997       1.1     skrll 
   2998   1.1.1.4  christos       if (ibfd->xvec != &spu_elf32_vec)
   2999       1.1     skrll 	continue;
   3000       1.1     skrll 
   3001       1.1     skrll       /* Read all the symbols.  */
   3002       1.1     skrll       symtab_hdr = &elf_tdata (ibfd)->symtab_hdr;
   3003       1.1     skrll       symcount = symtab_hdr->sh_size / symtab_hdr->sh_entsize;
   3004       1.1     skrll       if (symcount == 0)
   3005       1.1     skrll 	{
   3006       1.1     skrll 	  if (!gaps)
   3007       1.1     skrll 	    for (sec = ibfd->sections; sec != NULL && !gaps; sec = sec->next)
   3008   1.1.1.2  christos 	      if (interesting_section (sec))
   3009       1.1     skrll 		{
   3010   1.1.1.9  christos 		  gaps = true;
   3011       1.1     skrll 		  break;
   3012       1.1     skrll 		}
   3013       1.1     skrll 	  continue;
   3014       1.1     skrll 	}
   3015       1.1     skrll 
   3016   1.1.1.9  christos       /* Don't use cached symbols since the generic ELF linker
   3017   1.1.1.9  christos 	 code only reads local symbols, and we need globals too.  */
   3018   1.1.1.9  christos       free (symtab_hdr->contents);
   3019   1.1.1.9  christos       symtab_hdr->contents = NULL;
   3020       1.1     skrll       syms = bfd_elf_get_elf_syms (ibfd, symtab_hdr, symcount, 0,
   3021       1.1     skrll 				   NULL, NULL, NULL);
   3022       1.1     skrll       symtab_hdr->contents = (void *) syms;
   3023       1.1     skrll       if (syms == NULL)
   3024   1.1.1.9  christos 	return false;
   3025       1.1     skrll 
   3026       1.1     skrll       /* Select defined function symbols that are going to be output.  */
   3027       1.1     skrll       psyms = bfd_malloc ((symcount + 1) * sizeof (*psyms));
   3028       1.1     skrll       if (psyms == NULL)
   3029   1.1.1.9  christos 	return false;
   3030       1.1     skrll       psym_arr[bfd_idx] = psyms;
   3031       1.1     skrll       psecs = bfd_malloc (symcount * sizeof (*psecs));
   3032       1.1     skrll       if (psecs == NULL)
   3033   1.1.1.9  christos 	return false;
   3034       1.1     skrll       sec_arr[bfd_idx] = psecs;
   3035       1.1     skrll       for (psy = psyms, p = psecs, sy = syms; sy < syms + symcount; ++p, ++sy)
   3036       1.1     skrll 	if (ELF_ST_TYPE (sy->st_info) == STT_NOTYPE
   3037       1.1     skrll 	    || ELF_ST_TYPE (sy->st_info) == STT_FUNC)
   3038       1.1     skrll 	  {
   3039       1.1     skrll 	    asection *s;
   3040       1.1     skrll 
   3041       1.1     skrll 	    *p = s = bfd_section_from_elf_index (ibfd, sy->st_shndx);
   3042   1.1.1.2  christos 	    if (s != NULL && interesting_section (s))
   3043       1.1     skrll 	      *psy++ = sy;
   3044       1.1     skrll 	  }
   3045       1.1     skrll       symcount = psy - psyms;
   3046       1.1     skrll       *psy = NULL;
   3047       1.1     skrll 
   3048       1.1     skrll       /* Sort them by section and offset within section.  */
   3049       1.1     skrll       sort_syms_syms = syms;
   3050       1.1     skrll       sort_syms_psecs = psecs;
   3051       1.1     skrll       qsort (psyms, symcount, sizeof (*psyms), sort_syms);
   3052       1.1     skrll 
   3053       1.1     skrll       /* Now inspect the function symbols.  */
   3054       1.1     skrll       for (psy = psyms; psy < psyms + symcount; )
   3055       1.1     skrll 	{
   3056       1.1     skrll 	  asection *s = psecs[*psy - syms];
   3057       1.1     skrll 	  Elf_Internal_Sym **psy2;
   3058       1.1     skrll 
   3059       1.1     skrll 	  for (psy2 = psy; ++psy2 < psyms + symcount; )
   3060       1.1     skrll 	    if (psecs[*psy2 - syms] != s)
   3061       1.1     skrll 	      break;
   3062       1.1     skrll 
   3063       1.1     skrll 	  if (!alloc_stack_info (s, psy2 - psy))
   3064   1.1.1.9  christos 	    return false;
   3065       1.1     skrll 	  psy = psy2;
   3066       1.1     skrll 	}
   3067       1.1     skrll 
   3068       1.1     skrll       /* First install info about properly typed and sized functions.
   3069       1.1     skrll 	 In an ideal world this will cover all code sections, except
   3070       1.1     skrll 	 when partitioning functions into hot and cold sections,
   3071       1.1     skrll 	 and the horrible pasted together .init and .fini functions.  */
   3072       1.1     skrll       for (psy = psyms; psy < psyms + symcount; ++psy)
   3073       1.1     skrll 	{
   3074       1.1     skrll 	  sy = *psy;
   3075       1.1     skrll 	  if (ELF_ST_TYPE (sy->st_info) == STT_FUNC)
   3076       1.1     skrll 	    {
   3077       1.1     skrll 	      asection *s = psecs[sy - syms];
   3078   1.1.1.9  christos 	      if (!maybe_insert_function (s, sy, false, true))
   3079   1.1.1.9  christos 		return false;
   3080       1.1     skrll 	    }
   3081       1.1     skrll 	}
   3082       1.1     skrll 
   3083       1.1     skrll       for (sec = ibfd->sections; sec != NULL && !gaps; sec = sec->next)
   3084   1.1.1.2  christos 	if (interesting_section (sec))
   3085       1.1     skrll 	  gaps |= check_function_ranges (sec, info);
   3086       1.1     skrll     }
   3087       1.1     skrll 
   3088       1.1     skrll   if (gaps)
   3089       1.1     skrll     {
   3090       1.1     skrll       /* See if we can discover more function symbols by looking at
   3091       1.1     skrll 	 relocations.  */
   3092       1.1     skrll       for (ibfd = info->input_bfds, bfd_idx = 0;
   3093       1.1     skrll 	   ibfd != NULL;
   3094   1.1.1.4  christos 	   ibfd = ibfd->link.next, bfd_idx++)
   3095       1.1     skrll 	{
   3096       1.1     skrll 	  asection *sec;
   3097       1.1     skrll 
   3098       1.1     skrll 	  if (psym_arr[bfd_idx] == NULL)
   3099       1.1     skrll 	    continue;
   3100       1.1     skrll 
   3101       1.1     skrll 	  for (sec = ibfd->sections; sec != NULL; sec = sec->next)
   3102   1.1.1.9  christos 	    if (!mark_functions_via_relocs (sec, info, false))
   3103   1.1.1.9  christos 	      return false;
   3104       1.1     skrll 	}
   3105       1.1     skrll 
   3106       1.1     skrll       for (ibfd = info->input_bfds, bfd_idx = 0;
   3107       1.1     skrll 	   ibfd != NULL;
   3108   1.1.1.4  christos 	   ibfd = ibfd->link.next, bfd_idx++)
   3109       1.1     skrll 	{
   3110       1.1     skrll 	  Elf_Internal_Shdr *symtab_hdr;
   3111       1.1     skrll 	  asection *sec;
   3112       1.1     skrll 	  Elf_Internal_Sym *syms, *sy, **psyms, **psy;
   3113       1.1     skrll 	  asection **psecs;
   3114       1.1     skrll 
   3115       1.1     skrll 	  if ((psyms = psym_arr[bfd_idx]) == NULL)
   3116       1.1     skrll 	    continue;
   3117       1.1     skrll 
   3118       1.1     skrll 	  psecs = sec_arr[bfd_idx];
   3119       1.1     skrll 
   3120       1.1     skrll 	  symtab_hdr = &elf_tdata (ibfd)->symtab_hdr;
   3121       1.1     skrll 	  syms = (Elf_Internal_Sym *) symtab_hdr->contents;
   3122       1.1     skrll 
   3123   1.1.1.9  christos 	  gaps = false;
   3124       1.1     skrll 	  for (sec = ibfd->sections; sec != NULL && !gaps; sec = sec->next)
   3125   1.1.1.2  christos 	    if (interesting_section (sec))
   3126       1.1     skrll 	      gaps |= check_function_ranges (sec, info);
   3127       1.1     skrll 	  if (!gaps)
   3128       1.1     skrll 	    continue;
   3129       1.1     skrll 
   3130       1.1     skrll 	  /* Finally, install all globals.  */
   3131       1.1     skrll 	  for (psy = psyms; (sy = *psy) != NULL; ++psy)
   3132       1.1     skrll 	    {
   3133       1.1     skrll 	      asection *s;
   3134       1.1     skrll 
   3135       1.1     skrll 	      s = psecs[sy - syms];
   3136       1.1     skrll 
   3137       1.1     skrll 	      /* Global syms might be improperly typed functions.  */
   3138       1.1     skrll 	      if (ELF_ST_TYPE (sy->st_info) != STT_FUNC
   3139       1.1     skrll 		  && ELF_ST_BIND (sy->st_info) == STB_GLOBAL)
   3140       1.1     skrll 		{
   3141   1.1.1.9  christos 		  if (!maybe_insert_function (s, sy, false, false))
   3142   1.1.1.9  christos 		    return false;
   3143       1.1     skrll 		}
   3144       1.1     skrll 	    }
   3145       1.1     skrll 	}
   3146       1.1     skrll 
   3147   1.1.1.4  christos       for (ibfd = info->input_bfds; ibfd != NULL; ibfd = ibfd->link.next)
   3148       1.1     skrll 	{
   3149   1.1.1.4  christos 	  extern const bfd_target spu_elf32_vec;
   3150       1.1     skrll 	  asection *sec;
   3151       1.1     skrll 
   3152   1.1.1.4  christos 	  if (ibfd->xvec != &spu_elf32_vec)
   3153       1.1     skrll 	    continue;
   3154       1.1     skrll 
   3155       1.1     skrll 	  /* Some of the symbols we've installed as marking the
   3156       1.1     skrll 	     beginning of functions may have a size of zero.  Extend
   3157       1.1     skrll 	     the range of such functions to the beginning of the
   3158       1.1     skrll 	     next symbol of interest.  */
   3159       1.1     skrll 	  for (sec = ibfd->sections; sec != NULL; sec = sec->next)
   3160   1.1.1.2  christos 	    if (interesting_section (sec))
   3161       1.1     skrll 	      {
   3162       1.1     skrll 		struct _spu_elf_section_data *sec_data;
   3163       1.1     skrll 		struct spu_elf_stack_info *sinfo;
   3164       1.1     skrll 
   3165       1.1     skrll 		sec_data = spu_elf_section_data (sec);
   3166       1.1     skrll 		sinfo = sec_data->u.i.stack_info;
   3167   1.1.1.2  christos 		if (sinfo != NULL && sinfo->num_fun != 0)
   3168       1.1     skrll 		  {
   3169       1.1     skrll 		    int fun_idx;
   3170       1.1     skrll 		    bfd_vma hi = sec->size;
   3171       1.1     skrll 
   3172       1.1     skrll 		    for (fun_idx = sinfo->num_fun; --fun_idx >= 0; )
   3173       1.1     skrll 		      {
   3174       1.1     skrll 			sinfo->fun[fun_idx].hi = hi;
   3175       1.1     skrll 			hi = sinfo->fun[fun_idx].lo;
   3176       1.1     skrll 		      }
   3177   1.1.1.2  christos 
   3178   1.1.1.2  christos 		    sinfo->fun[0].lo = 0;
   3179       1.1     skrll 		  }
   3180       1.1     skrll 		/* No symbols in this section.  Must be .init or .fini
   3181       1.1     skrll 		   or something similar.  */
   3182   1.1.1.2  christos 		else if (!pasted_function (sec))
   3183   1.1.1.9  christos 		  return false;
   3184       1.1     skrll 	      }
   3185       1.1     skrll 	}
   3186       1.1     skrll     }
   3187       1.1     skrll 
   3188       1.1     skrll   for (ibfd = info->input_bfds, bfd_idx = 0;
   3189       1.1     skrll        ibfd != NULL;
   3190   1.1.1.4  christos        ibfd = ibfd->link.next, bfd_idx++)
   3191       1.1     skrll     {
   3192       1.1     skrll       if (psym_arr[bfd_idx] == NULL)
   3193       1.1     skrll 	continue;
   3194       1.1     skrll 
   3195       1.1     skrll       free (psym_arr[bfd_idx]);
   3196       1.1     skrll       free (sec_arr[bfd_idx]);
   3197       1.1     skrll     }
   3198       1.1     skrll 
   3199       1.1     skrll   free (psym_arr);
   3200       1.1     skrll   free (sec_arr);
   3201       1.1     skrll 
   3202   1.1.1.9  christos   return true;
   3203       1.1     skrll }
   3204       1.1     skrll 
   3205       1.1     skrll /* Iterate over all function_info we have collected, calling DOIT on
   3206       1.1     skrll    each node if ROOT_ONLY is false.  Only call DOIT on root nodes
   3207       1.1     skrll    if ROOT_ONLY.  */
   3208       1.1     skrll 
   3209   1.1.1.9  christos static bool
   3210   1.1.1.9  christos for_each_node (bool (*doit) (struct function_info *,
   3211   1.1.1.9  christos 			     struct bfd_link_info *,
   3212   1.1.1.9  christos 			     void *),
   3213       1.1     skrll 	       struct bfd_link_info *info,
   3214       1.1     skrll 	       void *param,
   3215       1.1     skrll 	       int root_only)
   3216       1.1     skrll {
   3217       1.1     skrll   bfd *ibfd;
   3218       1.1     skrll 
   3219   1.1.1.4  christos   for (ibfd = info->input_bfds; ibfd != NULL; ibfd = ibfd->link.next)
   3220       1.1     skrll     {
   3221   1.1.1.4  christos       extern const bfd_target spu_elf32_vec;
   3222       1.1     skrll       asection *sec;
   3223       1.1     skrll 
   3224   1.1.1.4  christos       if (ibfd->xvec != &spu_elf32_vec)
   3225       1.1     skrll 	continue;
   3226       1.1     skrll 
   3227       1.1     skrll       for (sec = ibfd->sections; sec != NULL; sec = sec->next)
   3228       1.1     skrll 	{
   3229       1.1     skrll 	  struct _spu_elf_section_data *sec_data;
   3230       1.1     skrll 	  struct spu_elf_stack_info *sinfo;
   3231       1.1     skrll 
   3232       1.1     skrll 	  if ((sec_data = spu_elf_section_data (sec)) != NULL
   3233       1.1     skrll 	      && (sinfo = sec_data->u.i.stack_info) != NULL)
   3234       1.1     skrll 	    {
   3235       1.1     skrll 	      int i;
   3236       1.1     skrll 	      for (i = 0; i < sinfo->num_fun; ++i)
   3237       1.1     skrll 		if (!root_only || !sinfo->fun[i].non_root)
   3238       1.1     skrll 		  if (!doit (&sinfo->fun[i], info, param))
   3239   1.1.1.9  christos 		    return false;
   3240       1.1     skrll 	    }
   3241       1.1     skrll 	}
   3242       1.1     skrll     }
   3243   1.1.1.9  christos   return true;
   3244       1.1     skrll }
   3245       1.1     skrll 
   3246       1.1     skrll /* Transfer call info attached to struct function_info entries for
   3247       1.1     skrll    all of a given function's sections to the first entry.  */
   3248       1.1     skrll 
   3249   1.1.1.9  christos static bool
   3250       1.1     skrll transfer_calls (struct function_info *fun,
   3251       1.1     skrll 		struct bfd_link_info *info ATTRIBUTE_UNUSED,
   3252       1.1     skrll 		void *param ATTRIBUTE_UNUSED)
   3253       1.1     skrll {
   3254       1.1     skrll   struct function_info *start = fun->start;
   3255       1.1     skrll 
   3256       1.1     skrll   if (start != NULL)
   3257       1.1     skrll     {
   3258       1.1     skrll       struct call_info *call, *call_next;
   3259       1.1     skrll 
   3260       1.1     skrll       while (start->start != NULL)
   3261       1.1     skrll 	start = start->start;
   3262       1.1     skrll       for (call = fun->call_list; call != NULL; call = call_next)
   3263       1.1     skrll 	{
   3264       1.1     skrll 	  call_next = call->next;
   3265       1.1     skrll 	  if (!insert_callee (start, call))
   3266       1.1     skrll 	    free (call);
   3267       1.1     skrll 	}
   3268       1.1     skrll       fun->call_list = NULL;
   3269       1.1     skrll     }
   3270   1.1.1.9  christos   return true;
   3271       1.1     skrll }
   3272       1.1     skrll 
   3273       1.1     skrll /* Mark nodes in the call graph that are called by some other node.  */
   3274       1.1     skrll 
   3275   1.1.1.9  christos static bool
   3276       1.1     skrll mark_non_root (struct function_info *fun,
   3277       1.1     skrll 	       struct bfd_link_info *info ATTRIBUTE_UNUSED,
   3278       1.1     skrll 	       void *param ATTRIBUTE_UNUSED)
   3279       1.1     skrll {
   3280       1.1     skrll   struct call_info *call;
   3281       1.1     skrll 
   3282       1.1     skrll   if (fun->visit1)
   3283   1.1.1.9  christos     return true;
   3284   1.1.1.9  christos   fun->visit1 = true;
   3285       1.1     skrll   for (call = fun->call_list; call; call = call->next)
   3286       1.1     skrll     {
   3287   1.1.1.9  christos       call->fun->non_root = true;
   3288       1.1     skrll       mark_non_root (call->fun, 0, 0);
   3289       1.1     skrll     }
   3290   1.1.1.9  christos   return true;
   3291       1.1     skrll }
   3292       1.1     skrll 
   3293       1.1     skrll /* Remove cycles from the call graph.  Set depth of nodes.  */
   3294       1.1     skrll 
   3295   1.1.1.9  christos static bool
   3296       1.1     skrll remove_cycles (struct function_info *fun,
   3297       1.1     skrll 	       struct bfd_link_info *info,
   3298       1.1     skrll 	       void *param)
   3299       1.1     skrll {
   3300       1.1     skrll   struct call_info **callp, *call;
   3301       1.1     skrll   unsigned int depth = *(unsigned int *) param;
   3302       1.1     skrll   unsigned int max_depth = depth;
   3303       1.1     skrll 
   3304       1.1     skrll   fun->depth = depth;
   3305   1.1.1.9  christos   fun->visit2 = true;
   3306   1.1.1.9  christos   fun->marking = true;
   3307       1.1     skrll 
   3308       1.1     skrll   callp = &fun->call_list;
   3309       1.1     skrll   while ((call = *callp) != NULL)
   3310       1.1     skrll     {
   3311   1.1.1.2  christos       call->max_depth = depth + !call->is_pasted;
   3312       1.1     skrll       if (!call->fun->visit2)
   3313       1.1     skrll 	{
   3314       1.1     skrll 	  if (!remove_cycles (call->fun, info, &call->max_depth))
   3315   1.1.1.9  christos 	    return false;
   3316       1.1     skrll 	  if (max_depth < call->max_depth)
   3317       1.1     skrll 	    max_depth = call->max_depth;
   3318       1.1     skrll 	}
   3319       1.1     skrll       else if (call->fun->marking)
   3320       1.1     skrll 	{
   3321   1.1.1.2  christos 	  struct spu_link_hash_table *htab = spu_hash_table (info);
   3322   1.1.1.2  christos 
   3323   1.1.1.2  christos 	  if (!htab->params->auto_overlay
   3324   1.1.1.2  christos 	      && htab->params->stack_analysis)
   3325       1.1     skrll 	    {
   3326       1.1     skrll 	      const char *f1 = func_name (fun);
   3327       1.1     skrll 	      const char *f2 = func_name (call->fun);
   3328       1.1     skrll 
   3329   1.1.1.6  christos 	      /* xgettext:c-format */
   3330   1.1.1.7  christos 	      info->callbacks->info (_("stack analysis will ignore the call "
   3331       1.1     skrll 				       "from %s to %s\n"),
   3332       1.1     skrll 				     f1, f2);
   3333       1.1     skrll 	    }
   3334   1.1.1.2  christos 
   3335   1.1.1.9  christos 	  call->broken_cycle = true;
   3336       1.1     skrll 	}
   3337       1.1     skrll       callp = &call->next;
   3338       1.1     skrll     }
   3339   1.1.1.9  christos   fun->marking = false;
   3340       1.1     skrll   *(unsigned int *) param = max_depth;
   3341   1.1.1.9  christos   return true;
   3342       1.1     skrll }
   3343       1.1     skrll 
   3344   1.1.1.2  christos /* Check that we actually visited all nodes in remove_cycles.  If we
   3345   1.1.1.2  christos    didn't, then there is some cycle in the call graph not attached to
   3346   1.1.1.2  christos    any root node.  Arbitrarily choose a node in the cycle as a new
   3347   1.1.1.2  christos    root and break the cycle.  */
   3348   1.1.1.2  christos 
   3349   1.1.1.9  christos static bool
   3350   1.1.1.2  christos mark_detached_root (struct function_info *fun,
   3351   1.1.1.2  christos 		    struct bfd_link_info *info,
   3352   1.1.1.2  christos 		    void *param)
   3353   1.1.1.2  christos {
   3354   1.1.1.2  christos   if (fun->visit2)
   3355   1.1.1.9  christos     return true;
   3356   1.1.1.9  christos   fun->non_root = false;
   3357   1.1.1.2  christos   *(unsigned int *) param = 0;
   3358   1.1.1.2  christos   return remove_cycles (fun, info, param);
   3359   1.1.1.2  christos }
   3360   1.1.1.2  christos 
   3361       1.1     skrll /* Populate call_list for each function.  */
   3362       1.1     skrll 
   3363   1.1.1.9  christos static bool
   3364       1.1     skrll build_call_tree (struct bfd_link_info *info)
   3365       1.1     skrll {
   3366       1.1     skrll   bfd *ibfd;
   3367       1.1     skrll   unsigned int depth;
   3368       1.1     skrll 
   3369   1.1.1.4  christos   for (ibfd = info->input_bfds; ibfd != NULL; ibfd = ibfd->link.next)
   3370       1.1     skrll     {
   3371   1.1.1.4  christos       extern const bfd_target spu_elf32_vec;
   3372       1.1     skrll       asection *sec;
   3373       1.1     skrll 
   3374   1.1.1.4  christos       if (ibfd->xvec != &spu_elf32_vec)
   3375       1.1     skrll 	continue;
   3376       1.1     skrll 
   3377       1.1     skrll       for (sec = ibfd->sections; sec != NULL; sec = sec->next)
   3378   1.1.1.9  christos 	if (!mark_functions_via_relocs (sec, info, true))
   3379   1.1.1.9  christos 	  return false;
   3380       1.1     skrll     }
   3381       1.1     skrll 
   3382       1.1     skrll   /* Transfer call info from hot/cold section part of function
   3383       1.1     skrll      to main entry.  */
   3384   1.1.1.2  christos   if (!spu_hash_table (info)->params->auto_overlay
   3385   1.1.1.9  christos       && !for_each_node (transfer_calls, info, 0, false))
   3386   1.1.1.9  christos     return false;
   3387       1.1     skrll 
   3388       1.1     skrll   /* Find the call graph root(s).  */
   3389   1.1.1.9  christos   if (!for_each_node (mark_non_root, info, 0, false))
   3390   1.1.1.9  christos     return false;
   3391       1.1     skrll 
   3392       1.1     skrll   /* Remove cycles from the call graph.  We start from the root node(s)
   3393       1.1     skrll      so that we break cycles in a reasonable place.  */
   3394       1.1     skrll   depth = 0;
   3395   1.1.1.9  christos   if (!for_each_node (remove_cycles, info, &depth, true))
   3396   1.1.1.9  christos     return false;
   3397   1.1.1.2  christos 
   3398   1.1.1.9  christos   return for_each_node (mark_detached_root, info, &depth, false);
   3399       1.1     skrll }
   3400       1.1     skrll 
   3401   1.1.1.2  christos /* qsort predicate to sort calls by priority, max_depth then count.  */
   3402       1.1     skrll 
   3403       1.1     skrll static int
   3404       1.1     skrll sort_calls (const void *a, const void *b)
   3405       1.1     skrll {
   3406       1.1     skrll   struct call_info *const *c1 = a;
   3407       1.1     skrll   struct call_info *const *c2 = b;
   3408       1.1     skrll   int delta;
   3409       1.1     skrll 
   3410   1.1.1.2  christos   delta = (*c2)->priority - (*c1)->priority;
   3411   1.1.1.2  christos   if (delta != 0)
   3412   1.1.1.2  christos     return delta;
   3413   1.1.1.2  christos 
   3414       1.1     skrll   delta = (*c2)->max_depth - (*c1)->max_depth;
   3415       1.1     skrll   if (delta != 0)
   3416       1.1     skrll     return delta;
   3417       1.1     skrll 
   3418       1.1     skrll   delta = (*c2)->count - (*c1)->count;
   3419       1.1     skrll   if (delta != 0)
   3420       1.1     skrll     return delta;
   3421       1.1     skrll 
   3422   1.1.1.2  christos   return (char *) c1 - (char *) c2;
   3423       1.1     skrll }
   3424       1.1     skrll 
   3425       1.1     skrll struct _mos_param {
   3426       1.1     skrll   unsigned int max_overlay_size;
   3427       1.1     skrll };
   3428       1.1     skrll 
   3429       1.1     skrll /* Set linker_mark and gc_mark on any sections that we will put in
   3430       1.1     skrll    overlays.  These flags are used by the generic ELF linker, but we
   3431       1.1     skrll    won't be continuing on to bfd_elf_final_link so it is OK to use
   3432       1.1     skrll    them.  linker_mark is clear before we get here.  Set segment_mark
   3433       1.1     skrll    on sections that are part of a pasted function (excluding the last
   3434       1.1     skrll    section).
   3435       1.1     skrll 
   3436       1.1     skrll    Set up function rodata section if --overlay-rodata.  We don't
   3437       1.1     skrll    currently include merged string constant rodata sections since
   3438       1.1     skrll 
   3439       1.1     skrll    Sort the call graph so that the deepest nodes will be visited
   3440       1.1     skrll    first.  */
   3441       1.1     skrll 
   3442   1.1.1.9  christos static bool
   3443       1.1     skrll mark_overlay_section (struct function_info *fun,
   3444       1.1     skrll 		      struct bfd_link_info *info,
   3445       1.1     skrll 		      void *param)
   3446       1.1     skrll {
   3447       1.1     skrll   struct call_info *call;
   3448       1.1     skrll   unsigned int count;
   3449       1.1     skrll   struct _mos_param *mos_param = param;
   3450   1.1.1.2  christos   struct spu_link_hash_table *htab = spu_hash_table (info);
   3451       1.1     skrll 
   3452       1.1     skrll   if (fun->visit4)
   3453   1.1.1.9  christos     return true;
   3454       1.1     skrll 
   3455   1.1.1.9  christos   fun->visit4 = true;
   3456   1.1.1.2  christos   if (!fun->sec->linker_mark
   3457   1.1.1.2  christos       && (htab->params->ovly_flavour != ovly_soft_icache
   3458   1.1.1.2  christos 	  || htab->params->non_ia_text
   3459   1.1.1.9  christos 	  || startswith (fun->sec->name, ".text.ia.")
   3460   1.1.1.2  christos 	  || strcmp (fun->sec->name, ".init") == 0
   3461   1.1.1.2  christos 	  || strcmp (fun->sec->name, ".fini") == 0))
   3462       1.1     skrll     {
   3463       1.1     skrll       unsigned int size;
   3464       1.1     skrll 
   3465       1.1     skrll       fun->sec->linker_mark = 1;
   3466       1.1     skrll       fun->sec->gc_mark = 1;
   3467       1.1     skrll       fun->sec->segment_mark = 0;
   3468       1.1     skrll       /* Ensure SEC_CODE is set on this text section (it ought to
   3469       1.1     skrll 	 be!), and SEC_CODE is clear on rodata sections.  We use
   3470       1.1     skrll 	 this flag to differentiate the two overlay section types.  */
   3471       1.1     skrll       fun->sec->flags |= SEC_CODE;
   3472       1.1     skrll 
   3473   1.1.1.2  christos       size = fun->sec->size;
   3474   1.1.1.2  christos       if (htab->params->auto_overlay & OVERLAY_RODATA)
   3475       1.1     skrll 	{
   3476       1.1     skrll 	  char *name = NULL;
   3477       1.1     skrll 
   3478       1.1     skrll 	  /* Find the rodata section corresponding to this function's
   3479       1.1     skrll 	     text section.  */
   3480       1.1     skrll 	  if (strcmp (fun->sec->name, ".text") == 0)
   3481       1.1     skrll 	    {
   3482       1.1     skrll 	      name = bfd_malloc (sizeof (".rodata"));
   3483       1.1     skrll 	      if (name == NULL)
   3484   1.1.1.9  christos 		return false;
   3485       1.1     skrll 	      memcpy (name, ".rodata", sizeof (".rodata"));
   3486       1.1     skrll 	    }
   3487   1.1.1.9  christos 	  else if (startswith (fun->sec->name, ".text."))
   3488       1.1     skrll 	    {
   3489       1.1     skrll 	      size_t len = strlen (fun->sec->name);
   3490       1.1     skrll 	      name = bfd_malloc (len + 3);
   3491       1.1     skrll 	      if (name == NULL)
   3492   1.1.1.9  christos 		return false;
   3493       1.1     skrll 	      memcpy (name, ".rodata", sizeof (".rodata"));
   3494       1.1     skrll 	      memcpy (name + 7, fun->sec->name + 5, len - 4);
   3495       1.1     skrll 	    }
   3496   1.1.1.9  christos 	  else if (startswith (fun->sec->name, ".gnu.linkonce.t."))
   3497       1.1     skrll 	    {
   3498       1.1     skrll 	      size_t len = strlen (fun->sec->name) + 1;
   3499       1.1     skrll 	      name = bfd_malloc (len);
   3500       1.1     skrll 	      if (name == NULL)
   3501   1.1.1.9  christos 		return false;
   3502       1.1     skrll 	      memcpy (name, fun->sec->name, len);
   3503       1.1     skrll 	      name[14] = 'r';
   3504       1.1     skrll 	    }
   3505       1.1     skrll 
   3506       1.1     skrll 	  if (name != NULL)
   3507       1.1     skrll 	    {
   3508       1.1     skrll 	      asection *rodata = NULL;
   3509       1.1     skrll 	      asection *group_sec = elf_section_data (fun->sec)->next_in_group;
   3510       1.1     skrll 	      if (group_sec == NULL)
   3511       1.1     skrll 		rodata = bfd_get_section_by_name (fun->sec->owner, name);
   3512       1.1     skrll 	      else
   3513       1.1     skrll 		while (group_sec != NULL && group_sec != fun->sec)
   3514       1.1     skrll 		  {
   3515       1.1     skrll 		    if (strcmp (group_sec->name, name) == 0)
   3516       1.1     skrll 		      {
   3517       1.1     skrll 			rodata = group_sec;
   3518       1.1     skrll 			break;
   3519       1.1     skrll 		      }
   3520       1.1     skrll 		    group_sec = elf_section_data (group_sec)->next_in_group;
   3521       1.1     skrll 		  }
   3522       1.1     skrll 	      fun->rodata = rodata;
   3523       1.1     skrll 	      if (fun->rodata)
   3524       1.1     skrll 		{
   3525   1.1.1.2  christos 		  size += fun->rodata->size;
   3526   1.1.1.2  christos 		  if (htab->params->line_size != 0
   3527   1.1.1.2  christos 		      && size > htab->params->line_size)
   3528   1.1.1.2  christos 		    {
   3529   1.1.1.2  christos 		      size -= fun->rodata->size;
   3530   1.1.1.2  christos 		      fun->rodata = NULL;
   3531   1.1.1.2  christos 		    }
   3532   1.1.1.2  christos 		  else
   3533   1.1.1.2  christos 		    {
   3534   1.1.1.2  christos 		      fun->rodata->linker_mark = 1;
   3535   1.1.1.2  christos 		      fun->rodata->gc_mark = 1;
   3536   1.1.1.2  christos 		      fun->rodata->flags &= ~SEC_CODE;
   3537   1.1.1.2  christos 		    }
   3538       1.1     skrll 		}
   3539       1.1     skrll 	      free (name);
   3540       1.1     skrll 	    }
   3541       1.1     skrll 	}
   3542       1.1     skrll       if (mos_param->max_overlay_size < size)
   3543       1.1     skrll 	mos_param->max_overlay_size = size;
   3544       1.1     skrll     }
   3545       1.1     skrll 
   3546       1.1     skrll   for (count = 0, call = fun->call_list; call != NULL; call = call->next)
   3547       1.1     skrll     count += 1;
   3548       1.1     skrll 
   3549       1.1     skrll   if (count > 1)
   3550       1.1     skrll     {
   3551       1.1     skrll       struct call_info **calls = bfd_malloc (count * sizeof (*calls));
   3552       1.1     skrll       if (calls == NULL)
   3553   1.1.1.9  christos 	return false;
   3554       1.1     skrll 
   3555       1.1     skrll       for (count = 0, call = fun->call_list; call != NULL; call = call->next)
   3556       1.1     skrll 	calls[count++] = call;
   3557       1.1     skrll 
   3558       1.1     skrll       qsort (calls, count, sizeof (*calls), sort_calls);
   3559       1.1     skrll 
   3560       1.1     skrll       fun->call_list = NULL;
   3561       1.1     skrll       while (count != 0)
   3562       1.1     skrll 	{
   3563       1.1     skrll 	  --count;
   3564       1.1     skrll 	  calls[count]->next = fun->call_list;
   3565       1.1     skrll 	  fun->call_list = calls[count];
   3566       1.1     skrll 	}
   3567       1.1     skrll       free (calls);
   3568       1.1     skrll     }
   3569       1.1     skrll 
   3570       1.1     skrll   for (call = fun->call_list; call != NULL; call = call->next)
   3571       1.1     skrll     {
   3572       1.1     skrll       if (call->is_pasted)
   3573       1.1     skrll 	{
   3574       1.1     skrll 	  /* There can only be one is_pasted call per function_info.  */
   3575       1.1     skrll 	  BFD_ASSERT (!fun->sec->segment_mark);
   3576       1.1     skrll 	  fun->sec->segment_mark = 1;
   3577       1.1     skrll 	}
   3578   1.1.1.2  christos       if (!call->broken_cycle
   3579   1.1.1.2  christos 	  && !mark_overlay_section (call->fun, info, param))
   3580   1.1.1.9  christos 	return false;
   3581       1.1     skrll     }
   3582       1.1     skrll 
   3583       1.1     skrll   /* Don't put entry code into an overlay.  The overlay manager needs
   3584   1.1.1.2  christos      a stack!  Also, don't mark .ovl.init as an overlay.  */
   3585       1.1     skrll   if (fun->lo + fun->sec->output_offset + fun->sec->output_section->vma
   3586   1.1.1.2  christos       == info->output_bfd->start_address
   3587   1.1.1.9  christos       || startswith (fun->sec->output_section->name, ".ovl.init"))
   3588       1.1     skrll     {
   3589       1.1     skrll       fun->sec->linker_mark = 0;
   3590       1.1     skrll       if (fun->rodata != NULL)
   3591       1.1     skrll 	fun->rodata->linker_mark = 0;
   3592       1.1     skrll     }
   3593   1.1.1.9  christos   return true;
   3594       1.1     skrll }
   3595       1.1     skrll 
   3596       1.1     skrll /* If non-zero then unmark functions called from those within sections
   3597       1.1     skrll    that we need to unmark.  Unfortunately this isn't reliable since the
   3598       1.1     skrll    call graph cannot know the destination of function pointer calls.  */
   3599       1.1     skrll #define RECURSE_UNMARK 0
   3600       1.1     skrll 
   3601       1.1     skrll struct _uos_param {
   3602       1.1     skrll   asection *exclude_input_section;
   3603       1.1     skrll   asection *exclude_output_section;
   3604       1.1     skrll   unsigned long clearing;
   3605       1.1     skrll };
   3606       1.1     skrll 
   3607       1.1     skrll /* Undo some of mark_overlay_section's work.  */
   3608       1.1     skrll 
   3609   1.1.1.9  christos static bool
   3610       1.1     skrll unmark_overlay_section (struct function_info *fun,
   3611       1.1     skrll 			struct bfd_link_info *info,
   3612       1.1     skrll 			void *param)
   3613       1.1     skrll {
   3614       1.1     skrll   struct call_info *call;
   3615       1.1     skrll   struct _uos_param *uos_param = param;
   3616       1.1     skrll   unsigned int excluded = 0;
   3617       1.1     skrll 
   3618       1.1     skrll   if (fun->visit5)
   3619   1.1.1.9  christos     return true;
   3620       1.1     skrll 
   3621   1.1.1.9  christos   fun->visit5 = true;
   3622       1.1     skrll 
   3623       1.1     skrll   excluded = 0;
   3624       1.1     skrll   if (fun->sec == uos_param->exclude_input_section
   3625       1.1     skrll       || fun->sec->output_section == uos_param->exclude_output_section)
   3626       1.1     skrll     excluded = 1;
   3627       1.1     skrll 
   3628       1.1     skrll   if (RECURSE_UNMARK)
   3629       1.1     skrll     uos_param->clearing += excluded;
   3630       1.1     skrll 
   3631       1.1     skrll   if (RECURSE_UNMARK ? uos_param->clearing : excluded)
   3632       1.1     skrll     {
   3633       1.1     skrll       fun->sec->linker_mark = 0;
   3634       1.1     skrll       if (fun->rodata)
   3635       1.1     skrll 	fun->rodata->linker_mark = 0;
   3636       1.1     skrll     }
   3637       1.1     skrll 
   3638       1.1     skrll   for (call = fun->call_list; call != NULL; call = call->next)
   3639   1.1.1.2  christos     if (!call->broken_cycle
   3640   1.1.1.2  christos 	&& !unmark_overlay_section (call->fun, info, param))
   3641   1.1.1.9  christos       return false;
   3642       1.1     skrll 
   3643       1.1     skrll   if (RECURSE_UNMARK)
   3644       1.1     skrll     uos_param->clearing -= excluded;
   3645   1.1.1.9  christos   return true;
   3646       1.1     skrll }
   3647       1.1     skrll 
   3648       1.1     skrll struct _cl_param {
   3649       1.1     skrll   unsigned int lib_size;
   3650       1.1     skrll   asection **lib_sections;
   3651       1.1     skrll };
   3652       1.1     skrll 
   3653       1.1     skrll /* Add sections we have marked as belonging to overlays to an array
   3654       1.1     skrll    for consideration as non-overlay sections.  The array consist of
   3655       1.1     skrll    pairs of sections, (text,rodata), for functions in the call graph.  */
   3656       1.1     skrll 
   3657   1.1.1.9  christos static bool
   3658       1.1     skrll collect_lib_sections (struct function_info *fun,
   3659       1.1     skrll 		      struct bfd_link_info *info,
   3660       1.1     skrll 		      void *param)
   3661       1.1     skrll {
   3662       1.1     skrll   struct _cl_param *lib_param = param;
   3663       1.1     skrll   struct call_info *call;
   3664       1.1     skrll   unsigned int size;
   3665       1.1     skrll 
   3666       1.1     skrll   if (fun->visit6)
   3667   1.1.1.9  christos     return true;
   3668       1.1     skrll 
   3669   1.1.1.9  christos   fun->visit6 = true;
   3670       1.1     skrll   if (!fun->sec->linker_mark || !fun->sec->gc_mark || fun->sec->segment_mark)
   3671   1.1.1.9  christos     return true;
   3672       1.1     skrll 
   3673       1.1     skrll   size = fun->sec->size;
   3674       1.1     skrll   if (fun->rodata)
   3675       1.1     skrll     size += fun->rodata->size;
   3676       1.1     skrll 
   3677   1.1.1.2  christos   if (size <= lib_param->lib_size)
   3678       1.1     skrll     {
   3679   1.1.1.2  christos       *lib_param->lib_sections++ = fun->sec;
   3680   1.1.1.2  christos       fun->sec->gc_mark = 0;
   3681   1.1.1.2  christos       if (fun->rodata && fun->rodata->linker_mark && fun->rodata->gc_mark)
   3682   1.1.1.2  christos 	{
   3683   1.1.1.2  christos 	  *lib_param->lib_sections++ = fun->rodata;
   3684   1.1.1.2  christos 	  fun->rodata->gc_mark = 0;
   3685   1.1.1.2  christos 	}
   3686   1.1.1.2  christos       else
   3687   1.1.1.2  christos 	*lib_param->lib_sections++ = NULL;
   3688       1.1     skrll     }
   3689       1.1     skrll 
   3690       1.1     skrll   for (call = fun->call_list; call != NULL; call = call->next)
   3691   1.1.1.2  christos     if (!call->broken_cycle)
   3692   1.1.1.2  christos       collect_lib_sections (call->fun, info, param);
   3693       1.1     skrll 
   3694   1.1.1.9  christos   return true;
   3695       1.1     skrll }
   3696       1.1     skrll 
   3697       1.1     skrll /* qsort predicate to sort sections by call count.  */
   3698       1.1     skrll 
   3699       1.1     skrll static int
   3700       1.1     skrll sort_lib (const void *a, const void *b)
   3701       1.1     skrll {
   3702       1.1     skrll   asection *const *s1 = a;
   3703       1.1     skrll   asection *const *s2 = b;
   3704       1.1     skrll   struct _spu_elf_section_data *sec_data;
   3705       1.1     skrll   struct spu_elf_stack_info *sinfo;
   3706       1.1     skrll   int delta;
   3707       1.1     skrll 
   3708       1.1     skrll   delta = 0;
   3709       1.1     skrll   if ((sec_data = spu_elf_section_data (*s1)) != NULL
   3710       1.1     skrll       && (sinfo = sec_data->u.i.stack_info) != NULL)
   3711       1.1     skrll     {
   3712       1.1     skrll       int i;
   3713       1.1     skrll       for (i = 0; i < sinfo->num_fun; ++i)
   3714       1.1     skrll 	delta -= sinfo->fun[i].call_count;
   3715       1.1     skrll     }
   3716       1.1     skrll 
   3717       1.1     skrll   if ((sec_data = spu_elf_section_data (*s2)) != NULL
   3718       1.1     skrll       && (sinfo = sec_data->u.i.stack_info) != NULL)
   3719       1.1     skrll     {
   3720       1.1     skrll       int i;
   3721       1.1     skrll       for (i = 0; i < sinfo->num_fun; ++i)
   3722       1.1     skrll 	delta += sinfo->fun[i].call_count;
   3723       1.1     skrll     }
   3724       1.1     skrll 
   3725       1.1     skrll   if (delta != 0)
   3726       1.1     skrll     return delta;
   3727       1.1     skrll 
   3728       1.1     skrll   return s1 - s2;
   3729       1.1     skrll }
   3730       1.1     skrll 
   3731       1.1     skrll /* Remove some sections from those marked to be in overlays.  Choose
   3732       1.1     skrll    those that are called from many places, likely library functions.  */
   3733       1.1     skrll 
   3734       1.1     skrll static unsigned int
   3735       1.1     skrll auto_ovl_lib_functions (struct bfd_link_info *info, unsigned int lib_size)
   3736       1.1     skrll {
   3737       1.1     skrll   bfd *ibfd;
   3738       1.1     skrll   asection **lib_sections;
   3739       1.1     skrll   unsigned int i, lib_count;
   3740       1.1     skrll   struct _cl_param collect_lib_param;
   3741       1.1     skrll   struct function_info dummy_caller;
   3742   1.1.1.2  christos   struct spu_link_hash_table *htab;
   3743       1.1     skrll 
   3744       1.1     skrll   memset (&dummy_caller, 0, sizeof (dummy_caller));
   3745       1.1     skrll   lib_count = 0;
   3746   1.1.1.4  christos   for (ibfd = info->input_bfds; ibfd != NULL; ibfd = ibfd->link.next)
   3747       1.1     skrll     {
   3748   1.1.1.4  christos       extern const bfd_target spu_elf32_vec;
   3749       1.1     skrll       asection *sec;
   3750       1.1     skrll 
   3751   1.1.1.4  christos       if (ibfd->xvec != &spu_elf32_vec)
   3752       1.1     skrll 	continue;
   3753       1.1     skrll 
   3754       1.1     skrll       for (sec = ibfd->sections; sec != NULL; sec = sec->next)
   3755       1.1     skrll 	if (sec->linker_mark
   3756       1.1     skrll 	    && sec->size < lib_size
   3757       1.1     skrll 	    && (sec->flags & SEC_CODE) != 0)
   3758       1.1     skrll 	  lib_count += 1;
   3759       1.1     skrll     }
   3760       1.1     skrll   lib_sections = bfd_malloc (lib_count * 2 * sizeof (*lib_sections));
   3761       1.1     skrll   if (lib_sections == NULL)
   3762       1.1     skrll     return (unsigned int) -1;
   3763       1.1     skrll   collect_lib_param.lib_size = lib_size;
   3764       1.1     skrll   collect_lib_param.lib_sections = lib_sections;
   3765       1.1     skrll   if (!for_each_node (collect_lib_sections, info, &collect_lib_param,
   3766   1.1.1.9  christos 		      true))
   3767       1.1     skrll     return (unsigned int) -1;
   3768       1.1     skrll   lib_count = (collect_lib_param.lib_sections - lib_sections) / 2;
   3769       1.1     skrll 
   3770       1.1     skrll   /* Sort sections so that those with the most calls are first.  */
   3771       1.1     skrll   if (lib_count > 1)
   3772       1.1     skrll     qsort (lib_sections, lib_count, 2 * sizeof (*lib_sections), sort_lib);
   3773       1.1     skrll 
   3774   1.1.1.2  christos   htab = spu_hash_table (info);
   3775       1.1     skrll   for (i = 0; i < lib_count; i++)
   3776       1.1     skrll     {
   3777       1.1     skrll       unsigned int tmp, stub_size;
   3778       1.1     skrll       asection *sec;
   3779       1.1     skrll       struct _spu_elf_section_data *sec_data;
   3780       1.1     skrll       struct spu_elf_stack_info *sinfo;
   3781       1.1     skrll 
   3782       1.1     skrll       sec = lib_sections[2 * i];
   3783       1.1     skrll       /* If this section is OK, its size must be less than lib_size.  */
   3784       1.1     skrll       tmp = sec->size;
   3785       1.1     skrll       /* If it has a rodata section, then add that too.  */
   3786       1.1     skrll       if (lib_sections[2 * i + 1])
   3787       1.1     skrll 	tmp += lib_sections[2 * i + 1]->size;
   3788       1.1     skrll       /* Add any new overlay call stubs needed by the section.  */
   3789       1.1     skrll       stub_size = 0;
   3790       1.1     skrll       if (tmp < lib_size
   3791       1.1     skrll 	  && (sec_data = spu_elf_section_data (sec)) != NULL
   3792       1.1     skrll 	  && (sinfo = sec_data->u.i.stack_info) != NULL)
   3793       1.1     skrll 	{
   3794       1.1     skrll 	  int k;
   3795       1.1     skrll 	  struct call_info *call;
   3796       1.1     skrll 
   3797       1.1     skrll 	  for (k = 0; k < sinfo->num_fun; ++k)
   3798       1.1     skrll 	    for (call = sinfo->fun[k].call_list; call; call = call->next)
   3799       1.1     skrll 	      if (call->fun->sec->linker_mark)
   3800       1.1     skrll 		{
   3801       1.1     skrll 		  struct call_info *p;
   3802       1.1     skrll 		  for (p = dummy_caller.call_list; p; p = p->next)
   3803       1.1     skrll 		    if (p->fun == call->fun)
   3804       1.1     skrll 		      break;
   3805       1.1     skrll 		  if (!p)
   3806   1.1.1.2  christos 		    stub_size += ovl_stub_size (htab->params);
   3807       1.1     skrll 		}
   3808       1.1     skrll 	}
   3809       1.1     skrll       if (tmp + stub_size < lib_size)
   3810       1.1     skrll 	{
   3811       1.1     skrll 	  struct call_info **pp, *p;
   3812       1.1     skrll 
   3813       1.1     skrll 	  /* This section fits.  Mark it as non-overlay.  */
   3814       1.1     skrll 	  lib_sections[2 * i]->linker_mark = 0;
   3815       1.1     skrll 	  if (lib_sections[2 * i + 1])
   3816       1.1     skrll 	    lib_sections[2 * i + 1]->linker_mark = 0;
   3817       1.1     skrll 	  lib_size -= tmp + stub_size;
   3818       1.1     skrll 	  /* Call stubs to the section we just added are no longer
   3819       1.1     skrll 	     needed.  */
   3820       1.1     skrll 	  pp = &dummy_caller.call_list;
   3821       1.1     skrll 	  while ((p = *pp) != NULL)
   3822       1.1     skrll 	    if (!p->fun->sec->linker_mark)
   3823       1.1     skrll 	      {
   3824   1.1.1.2  christos 		lib_size += ovl_stub_size (htab->params);
   3825       1.1     skrll 		*pp = p->next;
   3826       1.1     skrll 		free (p);
   3827       1.1     skrll 	      }
   3828       1.1     skrll 	    else
   3829       1.1     skrll 	      pp = &p->next;
   3830       1.1     skrll 	  /* Add new call stubs to dummy_caller.  */
   3831       1.1     skrll 	  if ((sec_data = spu_elf_section_data (sec)) != NULL
   3832       1.1     skrll 	      && (sinfo = sec_data->u.i.stack_info) != NULL)
   3833       1.1     skrll 	    {
   3834       1.1     skrll 	      int k;
   3835       1.1     skrll 	      struct call_info *call;
   3836       1.1     skrll 
   3837       1.1     skrll 	      for (k = 0; k < sinfo->num_fun; ++k)
   3838       1.1     skrll 		for (call = sinfo->fun[k].call_list;
   3839       1.1     skrll 		     call;
   3840       1.1     skrll 		     call = call->next)
   3841       1.1     skrll 		  if (call->fun->sec->linker_mark)
   3842       1.1     skrll 		    {
   3843       1.1     skrll 		      struct call_info *callee;
   3844       1.1     skrll 		      callee = bfd_malloc (sizeof (*callee));
   3845       1.1     skrll 		      if (callee == NULL)
   3846       1.1     skrll 			return (unsigned int) -1;
   3847       1.1     skrll 		      *callee = *call;
   3848       1.1     skrll 		      if (!insert_callee (&dummy_caller, callee))
   3849       1.1     skrll 			free (callee);
   3850       1.1     skrll 		    }
   3851       1.1     skrll 	    }
   3852       1.1     skrll 	}
   3853       1.1     skrll     }
   3854       1.1     skrll   while (dummy_caller.call_list != NULL)
   3855       1.1     skrll     {
   3856       1.1     skrll       struct call_info *call = dummy_caller.call_list;
   3857       1.1     skrll       dummy_caller.call_list = call->next;
   3858       1.1     skrll       free (call);
   3859       1.1     skrll     }
   3860       1.1     skrll   for (i = 0; i < 2 * lib_count; i++)
   3861       1.1     skrll     if (lib_sections[i])
   3862       1.1     skrll       lib_sections[i]->gc_mark = 1;
   3863       1.1     skrll   free (lib_sections);
   3864       1.1     skrll   return lib_size;
   3865       1.1     skrll }
   3866       1.1     skrll 
   3867       1.1     skrll /* Build an array of overlay sections.  The deepest node's section is
   3868       1.1     skrll    added first, then its parent node's section, then everything called
   3869       1.1     skrll    from the parent section.  The idea being to group sections to
   3870       1.1     skrll    minimise calls between different overlays.  */
   3871       1.1     skrll 
   3872   1.1.1.9  christos static bool
   3873       1.1     skrll collect_overlays (struct function_info *fun,
   3874       1.1     skrll 		  struct bfd_link_info *info,
   3875       1.1     skrll 		  void *param)
   3876       1.1     skrll {
   3877       1.1     skrll   struct call_info *call;
   3878   1.1.1.9  christos   bool added_fun;
   3879       1.1     skrll   asection ***ovly_sections = param;
   3880       1.1     skrll 
   3881       1.1     skrll   if (fun->visit7)
   3882   1.1.1.9  christos     return true;
   3883       1.1     skrll 
   3884   1.1.1.9  christos   fun->visit7 = true;
   3885       1.1     skrll   for (call = fun->call_list; call != NULL; call = call->next)
   3886   1.1.1.2  christos     if (!call->is_pasted && !call->broken_cycle)
   3887       1.1     skrll       {
   3888       1.1     skrll 	if (!collect_overlays (call->fun, info, ovly_sections))
   3889   1.1.1.9  christos 	  return false;
   3890       1.1     skrll 	break;
   3891       1.1     skrll       }
   3892       1.1     skrll 
   3893   1.1.1.9  christos   added_fun = false;
   3894       1.1     skrll   if (fun->sec->linker_mark && fun->sec->gc_mark)
   3895       1.1     skrll     {
   3896       1.1     skrll       fun->sec->gc_mark = 0;
   3897       1.1     skrll       *(*ovly_sections)++ = fun->sec;
   3898       1.1     skrll       if (fun->rodata && fun->rodata->linker_mark && fun->rodata->gc_mark)
   3899       1.1     skrll 	{
   3900       1.1     skrll 	  fun->rodata->gc_mark = 0;
   3901       1.1     skrll 	  *(*ovly_sections)++ = fun->rodata;
   3902       1.1     skrll 	}
   3903       1.1     skrll       else
   3904       1.1     skrll 	*(*ovly_sections)++ = NULL;
   3905   1.1.1.9  christos       added_fun = true;
   3906       1.1     skrll 
   3907       1.1     skrll       /* Pasted sections must stay with the first section.  We don't
   3908       1.1     skrll 	 put pasted sections in the array, just the first section.
   3909       1.1     skrll 	 Mark subsequent sections as already considered.  */
   3910       1.1     skrll       if (fun->sec->segment_mark)
   3911       1.1     skrll 	{
   3912       1.1     skrll 	  struct function_info *call_fun = fun;
   3913       1.1     skrll 	  do
   3914       1.1     skrll 	    {
   3915       1.1     skrll 	      for (call = call_fun->call_list; call != NULL; call = call->next)
   3916       1.1     skrll 		if (call->is_pasted)
   3917       1.1     skrll 		  {
   3918       1.1     skrll 		    call_fun = call->fun;
   3919       1.1     skrll 		    call_fun->sec->gc_mark = 0;
   3920       1.1     skrll 		    if (call_fun->rodata)
   3921       1.1     skrll 		      call_fun->rodata->gc_mark = 0;
   3922       1.1     skrll 		    break;
   3923       1.1     skrll 		  }
   3924       1.1     skrll 	      if (call == NULL)
   3925       1.1     skrll 		abort ();
   3926       1.1     skrll 	    }
   3927       1.1     skrll 	  while (call_fun->sec->segment_mark);
   3928       1.1     skrll 	}
   3929       1.1     skrll     }
   3930       1.1     skrll 
   3931       1.1     skrll   for (call = fun->call_list; call != NULL; call = call->next)
   3932   1.1.1.2  christos     if (!call->broken_cycle
   3933   1.1.1.2  christos 	&& !collect_overlays (call->fun, info, ovly_sections))
   3934   1.1.1.9  christos       return false;
   3935       1.1     skrll 
   3936       1.1     skrll   if (added_fun)
   3937       1.1     skrll     {
   3938       1.1     skrll       struct _spu_elf_section_data *sec_data;
   3939       1.1     skrll       struct spu_elf_stack_info *sinfo;
   3940       1.1     skrll 
   3941       1.1     skrll       if ((sec_data = spu_elf_section_data (fun->sec)) != NULL
   3942       1.1     skrll 	  && (sinfo = sec_data->u.i.stack_info) != NULL)
   3943       1.1     skrll 	{
   3944       1.1     skrll 	  int i;
   3945       1.1     skrll 	  for (i = 0; i < sinfo->num_fun; ++i)
   3946       1.1     skrll 	    if (!collect_overlays (&sinfo->fun[i], info, ovly_sections))
   3947   1.1.1.9  christos 	      return false;
   3948       1.1     skrll 	}
   3949       1.1     skrll     }
   3950       1.1     skrll 
   3951   1.1.1.9  christos   return true;
   3952       1.1     skrll }
   3953       1.1     skrll 
   3954       1.1     skrll struct _sum_stack_param {
   3955       1.1     skrll   size_t cum_stack;
   3956       1.1     skrll   size_t overall_stack;
   3957   1.1.1.9  christos   bool emit_stack_syms;
   3958       1.1     skrll };
   3959       1.1     skrll 
   3960       1.1     skrll /* Descend the call graph for FUN, accumulating total stack required.  */
   3961       1.1     skrll 
   3962   1.1.1.9  christos static bool
   3963       1.1     skrll sum_stack (struct function_info *fun,
   3964       1.1     skrll 	   struct bfd_link_info *info,
   3965       1.1     skrll 	   void *param)
   3966       1.1     skrll {
   3967       1.1     skrll   struct call_info *call;
   3968       1.1     skrll   struct function_info *max;
   3969       1.1     skrll   size_t stack, cum_stack;
   3970       1.1     skrll   const char *f1;
   3971   1.1.1.9  christos   bool has_call;
   3972       1.1     skrll   struct _sum_stack_param *sum_stack_param = param;
   3973       1.1     skrll   struct spu_link_hash_table *htab;
   3974       1.1     skrll 
   3975       1.1     skrll   cum_stack = fun->stack;
   3976       1.1     skrll   sum_stack_param->cum_stack = cum_stack;
   3977       1.1     skrll   if (fun->visit3)
   3978   1.1.1.9  christos     return true;
   3979       1.1     skrll 
   3980   1.1.1.9  christos   has_call = false;
   3981       1.1     skrll   max = NULL;
   3982       1.1     skrll   for (call = fun->call_list; call; call = call->next)
   3983       1.1     skrll     {
   3984   1.1.1.2  christos       if (call->broken_cycle)
   3985   1.1.1.2  christos 	continue;
   3986       1.1     skrll       if (!call->is_pasted)
   3987   1.1.1.9  christos 	has_call = true;
   3988       1.1     skrll       if (!sum_stack (call->fun, info, sum_stack_param))
   3989   1.1.1.9  christos 	return false;
   3990       1.1     skrll       stack = sum_stack_param->cum_stack;
   3991       1.1     skrll       /* Include caller stack for normal calls, don't do so for
   3992       1.1     skrll 	 tail calls.  fun->stack here is local stack usage for
   3993       1.1     skrll 	 this function.  */
   3994       1.1     skrll       if (!call->is_tail || call->is_pasted || call->fun->start != NULL)
   3995       1.1     skrll 	stack += fun->stack;
   3996       1.1     skrll       if (cum_stack < stack)
   3997       1.1     skrll 	{
   3998       1.1     skrll 	  cum_stack = stack;
   3999       1.1     skrll 	  max = call->fun;
   4000       1.1     skrll 	}
   4001       1.1     skrll     }
   4002       1.1     skrll 
   4003       1.1     skrll   sum_stack_param->cum_stack = cum_stack;
   4004       1.1     skrll   stack = fun->stack;
   4005       1.1     skrll   /* Now fun->stack holds cumulative stack.  */
   4006       1.1     skrll   fun->stack = cum_stack;
   4007   1.1.1.9  christos   fun->visit3 = true;
   4008       1.1     skrll 
   4009       1.1     skrll   if (!fun->non_root
   4010       1.1     skrll       && sum_stack_param->overall_stack < cum_stack)
   4011       1.1     skrll     sum_stack_param->overall_stack = cum_stack;
   4012       1.1     skrll 
   4013       1.1     skrll   htab = spu_hash_table (info);
   4014   1.1.1.2  christos   if (htab->params->auto_overlay)
   4015   1.1.1.9  christos     return true;
   4016       1.1     skrll 
   4017       1.1     skrll   f1 = func_name (fun);
   4018   1.1.1.2  christos   if (htab->params->stack_analysis)
   4019   1.1.1.2  christos     {
   4020   1.1.1.2  christos       if (!fun->non_root)
   4021   1.1.1.6  christos 	info->callbacks->info ("  %s: 0x%v\n", f1, (bfd_vma) cum_stack);
   4022   1.1.1.6  christos       info->callbacks->minfo ("%s: 0x%v 0x%v\n",
   4023   1.1.1.2  christos 			      f1, (bfd_vma) stack, (bfd_vma) cum_stack);
   4024   1.1.1.2  christos 
   4025   1.1.1.2  christos       if (has_call)
   4026   1.1.1.2  christos 	{
   4027   1.1.1.2  christos 	  info->callbacks->minfo (_("  calls:\n"));
   4028   1.1.1.2  christos 	  for (call = fun->call_list; call; call = call->next)
   4029   1.1.1.2  christos 	    if (!call->is_pasted && !call->broken_cycle)
   4030   1.1.1.2  christos 	      {
   4031   1.1.1.2  christos 		const char *f2 = func_name (call->fun);
   4032   1.1.1.2  christos 		const char *ann1 = call->fun == max ? "*" : " ";
   4033   1.1.1.2  christos 		const char *ann2 = call->is_tail ? "t" : " ";
   4034       1.1     skrll 
   4035   1.1.1.6  christos 		info->callbacks->minfo ("   %s%s %s\n", ann1, ann2, f2);
   4036   1.1.1.2  christos 	      }
   4037   1.1.1.2  christos 	}
   4038       1.1     skrll     }
   4039       1.1     skrll 
   4040       1.1     skrll   if (sum_stack_param->emit_stack_syms)
   4041       1.1     skrll     {
   4042       1.1     skrll       char *name = bfd_malloc (18 + strlen (f1));
   4043       1.1     skrll       struct elf_link_hash_entry *h;
   4044       1.1     skrll 
   4045       1.1     skrll       if (name == NULL)
   4046   1.1.1.9  christos 	return false;
   4047       1.1     skrll 
   4048       1.1     skrll       if (fun->global || ELF_ST_BIND (fun->u.sym->st_info) == STB_GLOBAL)
   4049       1.1     skrll 	sprintf (name, "__stack_%s", f1);
   4050       1.1     skrll       else
   4051       1.1     skrll 	sprintf (name, "__stack_%x_%s", fun->sec->id & 0xffffffff, f1);
   4052       1.1     skrll 
   4053   1.1.1.9  christos       h = elf_link_hash_lookup (&htab->elf, name, true, true, false);
   4054       1.1     skrll       free (name);
   4055       1.1     skrll       if (h != NULL
   4056       1.1     skrll 	  && (h->root.type == bfd_link_hash_new
   4057       1.1     skrll 	      || h->root.type == bfd_link_hash_undefined
   4058       1.1     skrll 	      || h->root.type == bfd_link_hash_undefweak))
   4059       1.1     skrll 	{
   4060       1.1     skrll 	  h->root.type = bfd_link_hash_defined;
   4061       1.1     skrll 	  h->root.u.def.section = bfd_abs_section_ptr;
   4062       1.1     skrll 	  h->root.u.def.value = cum_stack;
   4063       1.1     skrll 	  h->size = 0;
   4064       1.1     skrll 	  h->type = 0;
   4065       1.1     skrll 	  h->ref_regular = 1;
   4066       1.1     skrll 	  h->def_regular = 1;
   4067       1.1     skrll 	  h->ref_regular_nonweak = 1;
   4068       1.1     skrll 	  h->forced_local = 1;
   4069       1.1     skrll 	  h->non_elf = 0;
   4070       1.1     skrll 	}
   4071       1.1     skrll     }
   4072       1.1     skrll 
   4073   1.1.1.9  christos   return true;
   4074       1.1     skrll }
   4075       1.1     skrll 
   4076       1.1     skrll /* SEC is part of a pasted function.  Return the call_info for the
   4077       1.1     skrll    next section of this function.  */
   4078       1.1     skrll 
   4079       1.1     skrll static struct call_info *
   4080       1.1     skrll find_pasted_call (asection *sec)
   4081       1.1     skrll {
   4082       1.1     skrll   struct _spu_elf_section_data *sec_data = spu_elf_section_data (sec);
   4083       1.1     skrll   struct spu_elf_stack_info *sinfo = sec_data->u.i.stack_info;
   4084       1.1     skrll   struct call_info *call;
   4085       1.1     skrll   int k;
   4086       1.1     skrll 
   4087       1.1     skrll   for (k = 0; k < sinfo->num_fun; ++k)
   4088       1.1     skrll     for (call = sinfo->fun[k].call_list; call != NULL; call = call->next)
   4089       1.1     skrll       if (call->is_pasted)
   4090       1.1     skrll 	return call;
   4091       1.1     skrll   abort ();
   4092       1.1     skrll   return 0;
   4093       1.1     skrll }
   4094       1.1     skrll 
   4095       1.1     skrll /* qsort predicate to sort bfds by file name.  */
   4096       1.1     skrll 
   4097   1.1.1.2  christos static int
   4098   1.1.1.2  christos sort_bfds (const void *a, const void *b)
   4099   1.1.1.2  christos {
   4100   1.1.1.2  christos   bfd *const *abfd1 = a;
   4101   1.1.1.2  christos   bfd *const *abfd2 = b;
   4102   1.1.1.2  christos 
   4103   1.1.1.9  christos   return filename_cmp (bfd_get_filename (*abfd1), bfd_get_filename (*abfd2));
   4104   1.1.1.2  christos }
   4105   1.1.1.2  christos 
   4106   1.1.1.2  christos static unsigned int
   4107   1.1.1.2  christos print_one_overlay_section (FILE *script,
   4108   1.1.1.2  christos 			   unsigned int base,
   4109   1.1.1.2  christos 			   unsigned int count,
   4110   1.1.1.2  christos 			   unsigned int ovlynum,
   4111   1.1.1.2  christos 			   unsigned int *ovly_map,
   4112   1.1.1.2  christos 			   asection **ovly_sections,
   4113   1.1.1.2  christos 			   struct bfd_link_info *info)
   4114   1.1.1.2  christos {
   4115   1.1.1.2  christos   unsigned int j;
   4116   1.1.1.4  christos 
   4117   1.1.1.2  christos   for (j = base; j < count && ovly_map[j] == ovlynum; j++)
   4118   1.1.1.2  christos     {
   4119   1.1.1.2  christos       asection *sec = ovly_sections[2 * j];
   4120   1.1.1.2  christos 
   4121   1.1.1.2  christos       if (fprintf (script, "   %s%c%s (%s)\n",
   4122   1.1.1.2  christos 		   (sec->owner->my_archive != NULL
   4123   1.1.1.9  christos 		    ? bfd_get_filename (sec->owner->my_archive) : ""),
   4124   1.1.1.2  christos 		   info->path_separator,
   4125   1.1.1.9  christos 		   bfd_get_filename (sec->owner),
   4126   1.1.1.2  christos 		   sec->name) <= 0)
   4127   1.1.1.2  christos 	return -1;
   4128   1.1.1.2  christos       if (sec->segment_mark)
   4129   1.1.1.2  christos 	{
   4130   1.1.1.2  christos 	  struct call_info *call = find_pasted_call (sec);
   4131   1.1.1.2  christos 	  while (call != NULL)
   4132   1.1.1.2  christos 	    {
   4133   1.1.1.2  christos 	      struct function_info *call_fun = call->fun;
   4134   1.1.1.2  christos 	      sec = call_fun->sec;
   4135   1.1.1.2  christos 	      if (fprintf (script, "   %s%c%s (%s)\n",
   4136   1.1.1.2  christos 			   (sec->owner->my_archive != NULL
   4137   1.1.1.9  christos 			    ? bfd_get_filename (sec->owner->my_archive) : ""),
   4138   1.1.1.2  christos 			   info->path_separator,
   4139   1.1.1.9  christos 			   bfd_get_filename (sec->owner),
   4140   1.1.1.2  christos 			   sec->name) <= 0)
   4141   1.1.1.2  christos 		return -1;
   4142   1.1.1.2  christos 	      for (call = call_fun->call_list; call; call = call->next)
   4143   1.1.1.2  christos 		if (call->is_pasted)
   4144   1.1.1.2  christos 		  break;
   4145   1.1.1.2  christos 	    }
   4146   1.1.1.2  christos 	}
   4147   1.1.1.2  christos     }
   4148   1.1.1.2  christos 
   4149   1.1.1.2  christos   for (j = base; j < count && ovly_map[j] == ovlynum; j++)
   4150   1.1.1.2  christos     {
   4151   1.1.1.2  christos       asection *sec = ovly_sections[2 * j + 1];
   4152   1.1.1.2  christos       if (sec != NULL
   4153   1.1.1.2  christos 	  && fprintf (script, "   %s%c%s (%s)\n",
   4154   1.1.1.2  christos 		      (sec->owner->my_archive != NULL
   4155   1.1.1.9  christos 		       ? bfd_get_filename (sec->owner->my_archive) : ""),
   4156   1.1.1.2  christos 		      info->path_separator,
   4157   1.1.1.9  christos 		      bfd_get_filename (sec->owner),
   4158   1.1.1.2  christos 		      sec->name) <= 0)
   4159   1.1.1.2  christos 	return -1;
   4160   1.1.1.2  christos 
   4161   1.1.1.2  christos       sec = ovly_sections[2 * j];
   4162   1.1.1.2  christos       if (sec->segment_mark)
   4163   1.1.1.2  christos 	{
   4164   1.1.1.2  christos 	  struct call_info *call = find_pasted_call (sec);
   4165   1.1.1.2  christos 	  while (call != NULL)
   4166   1.1.1.2  christos 	    {
   4167   1.1.1.2  christos 	      struct function_info *call_fun = call->fun;
   4168   1.1.1.2  christos 	      sec = call_fun->rodata;
   4169   1.1.1.2  christos 	      if (sec != NULL
   4170   1.1.1.2  christos 		  && fprintf (script, "   %s%c%s (%s)\n",
   4171   1.1.1.2  christos 			      (sec->owner->my_archive != NULL
   4172   1.1.1.9  christos 			       ? bfd_get_filename (sec->owner->my_archive) : ""),
   4173   1.1.1.2  christos 			      info->path_separator,
   4174   1.1.1.9  christos 			      bfd_get_filename (sec->owner),
   4175   1.1.1.2  christos 			      sec->name) <= 0)
   4176   1.1.1.2  christos 		return -1;
   4177   1.1.1.2  christos 	      for (call = call_fun->call_list; call; call = call->next)
   4178   1.1.1.2  christos 		if (call->is_pasted)
   4179   1.1.1.2  christos 		  break;
   4180   1.1.1.2  christos 	    }
   4181   1.1.1.2  christos 	}
   4182   1.1.1.2  christos     }
   4183       1.1     skrll 
   4184   1.1.1.2  christos   return j;
   4185       1.1     skrll }
   4186       1.1     skrll 
   4187       1.1     skrll /* Handle --auto-overlay.  */
   4188       1.1     skrll 
   4189       1.1     skrll static void
   4190   1.1.1.2  christos spu_elf_auto_overlay (struct bfd_link_info *info)
   4191       1.1     skrll {
   4192       1.1     skrll   bfd *ibfd;
   4193       1.1     skrll   bfd **bfd_arr;
   4194       1.1     skrll   struct elf_segment_map *m;
   4195       1.1     skrll   unsigned int fixed_size, lo, hi;
   4196   1.1.1.2  christos   unsigned int reserved;
   4197       1.1     skrll   struct spu_link_hash_table *htab;
   4198       1.1     skrll   unsigned int base, i, count, bfd_count;
   4199   1.1.1.2  christos   unsigned int region, ovlynum;
   4200       1.1     skrll   asection **ovly_sections, **ovly_p;
   4201   1.1.1.2  christos   unsigned int *ovly_map;
   4202       1.1     skrll   FILE *script;
   4203       1.1     skrll   unsigned int total_overlay_size, overlay_size;
   4204   1.1.1.2  christos   const char *ovly_mgr_entry;
   4205       1.1     skrll   struct elf_link_hash_entry *h;
   4206       1.1     skrll   struct _mos_param mos_param;
   4207       1.1     skrll   struct _uos_param uos_param;
   4208       1.1     skrll   struct function_info dummy_caller;
   4209       1.1     skrll 
   4210       1.1     skrll   /* Find the extents of our loadable image.  */
   4211       1.1     skrll   lo = (unsigned int) -1;
   4212       1.1     skrll   hi = 0;
   4213   1.1.1.4  christos   for (m = elf_seg_map (info->output_bfd); m != NULL; m = m->next)
   4214       1.1     skrll     if (m->p_type == PT_LOAD)
   4215       1.1     skrll       for (i = 0; i < m->count; i++)
   4216       1.1     skrll 	if (m->sections[i]->size != 0)
   4217       1.1     skrll 	  {
   4218       1.1     skrll 	    if (m->sections[i]->vma < lo)
   4219       1.1     skrll 	      lo = m->sections[i]->vma;
   4220       1.1     skrll 	    if (m->sections[i]->vma + m->sections[i]->size - 1 > hi)
   4221       1.1     skrll 	      hi = m->sections[i]->vma + m->sections[i]->size - 1;
   4222       1.1     skrll 	  }
   4223       1.1     skrll   fixed_size = hi + 1 - lo;
   4224       1.1     skrll 
   4225       1.1     skrll   if (!discover_functions (info))
   4226       1.1     skrll     goto err_exit;
   4227       1.1     skrll 
   4228       1.1     skrll   if (!build_call_tree (info))
   4229       1.1     skrll     goto err_exit;
   4230       1.1     skrll 
   4231   1.1.1.2  christos   htab = spu_hash_table (info);
   4232   1.1.1.2  christos   reserved = htab->params->auto_overlay_reserved;
   4233   1.1.1.2  christos   if (reserved == 0)
   4234   1.1.1.2  christos     {
   4235   1.1.1.2  christos       struct _sum_stack_param sum_stack_param;
   4236   1.1.1.2  christos 
   4237   1.1.1.2  christos       sum_stack_param.emit_stack_syms = 0;
   4238   1.1.1.2  christos       sum_stack_param.overall_stack = 0;
   4239   1.1.1.9  christos       if (!for_each_node (sum_stack, info, &sum_stack_param, true))
   4240   1.1.1.2  christos 	goto err_exit;
   4241   1.1.1.2  christos       reserved = (sum_stack_param.overall_stack
   4242   1.1.1.2  christos 		  + htab->params->extra_stack_space);
   4243   1.1.1.2  christos     }
   4244   1.1.1.2  christos 
   4245   1.1.1.2  christos   /* No need for overlays if everything already fits.  */
   4246   1.1.1.2  christos   if (fixed_size + reserved <= htab->local_store
   4247   1.1.1.2  christos       && htab->params->ovly_flavour != ovly_soft_icache)
   4248   1.1.1.2  christos     {
   4249   1.1.1.2  christos       htab->params->auto_overlay = 0;
   4250   1.1.1.2  christos       return;
   4251   1.1.1.2  christos     }
   4252   1.1.1.2  christos 
   4253       1.1     skrll   uos_param.exclude_input_section = 0;
   4254       1.1     skrll   uos_param.exclude_output_section
   4255       1.1     skrll     = bfd_get_section_by_name (info->output_bfd, ".interrupt");
   4256       1.1     skrll 
   4257   1.1.1.2  christos   ovly_mgr_entry = "__ovly_load";
   4258   1.1.1.2  christos   if (htab->params->ovly_flavour == ovly_soft_icache)
   4259   1.1.1.2  christos     ovly_mgr_entry = "__icache_br_handler";
   4260   1.1.1.2  christos   h = elf_link_hash_lookup (&htab->elf, ovly_mgr_entry,
   4261   1.1.1.9  christos 			    false, false, false);
   4262       1.1     skrll   if (h != NULL
   4263       1.1     skrll       && (h->root.type == bfd_link_hash_defined
   4264       1.1     skrll 	  || h->root.type == bfd_link_hash_defweak)
   4265       1.1     skrll       && h->def_regular)
   4266       1.1     skrll     {
   4267       1.1     skrll       /* We have a user supplied overlay manager.  */
   4268       1.1     skrll       uos_param.exclude_input_section = h->root.u.def.section;
   4269       1.1     skrll     }
   4270       1.1     skrll   else
   4271       1.1     skrll     {
   4272       1.1     skrll       /* If no user overlay manager, spu_elf_load_ovl_mgr will add our
   4273       1.1     skrll 	 builtin version to .text, and will adjust .text size.  */
   4274   1.1.1.2  christos       fixed_size += (*htab->params->spu_elf_load_ovl_mgr) ();
   4275       1.1     skrll     }
   4276       1.1     skrll 
   4277       1.1     skrll   /* Mark overlay sections, and find max overlay section size.  */
   4278       1.1     skrll   mos_param.max_overlay_size = 0;
   4279   1.1.1.9  christos   if (!for_each_node (mark_overlay_section, info, &mos_param, true))
   4280       1.1     skrll     goto err_exit;
   4281       1.1     skrll 
   4282       1.1     skrll   /* We can't put the overlay manager or interrupt routines in
   4283       1.1     skrll      overlays.  */
   4284       1.1     skrll   uos_param.clearing = 0;
   4285       1.1     skrll   if ((uos_param.exclude_input_section
   4286       1.1     skrll        || uos_param.exclude_output_section)
   4287   1.1.1.9  christos       && !for_each_node (unmark_overlay_section, info, &uos_param, true))
   4288       1.1     skrll     goto err_exit;
   4289       1.1     skrll 
   4290       1.1     skrll   bfd_count = 0;
   4291   1.1.1.4  christos   for (ibfd = info->input_bfds; ibfd != NULL; ibfd = ibfd->link.next)
   4292       1.1     skrll     ++bfd_count;
   4293       1.1     skrll   bfd_arr = bfd_malloc (bfd_count * sizeof (*bfd_arr));
   4294       1.1     skrll   if (bfd_arr == NULL)
   4295       1.1     skrll     goto err_exit;
   4296       1.1     skrll 
   4297       1.1     skrll   /* Count overlay sections, and subtract their sizes from "fixed_size".  */
   4298       1.1     skrll   count = 0;
   4299       1.1     skrll   bfd_count = 0;
   4300       1.1     skrll   total_overlay_size = 0;
   4301   1.1.1.4  christos   for (ibfd = info->input_bfds; ibfd != NULL; ibfd = ibfd->link.next)
   4302       1.1     skrll     {
   4303   1.1.1.4  christos       extern const bfd_target spu_elf32_vec;
   4304       1.1     skrll       asection *sec;
   4305       1.1     skrll       unsigned int old_count;
   4306       1.1     skrll 
   4307   1.1.1.4  christos       if (ibfd->xvec != &spu_elf32_vec)
   4308       1.1     skrll 	continue;
   4309       1.1     skrll 
   4310       1.1     skrll       old_count = count;
   4311       1.1     skrll       for (sec = ibfd->sections; sec != NULL; sec = sec->next)
   4312       1.1     skrll 	if (sec->linker_mark)
   4313       1.1     skrll 	  {
   4314       1.1     skrll 	    if ((sec->flags & SEC_CODE) != 0)
   4315       1.1     skrll 	      count += 1;
   4316       1.1     skrll 	    fixed_size -= sec->size;
   4317       1.1     skrll 	    total_overlay_size += sec->size;
   4318       1.1     skrll 	  }
   4319   1.1.1.2  christos 	else if ((sec->flags & (SEC_ALLOC | SEC_LOAD)) == (SEC_ALLOC | SEC_LOAD)
   4320   1.1.1.2  christos 		 && sec->output_section->owner == info->output_bfd
   4321   1.1.1.9  christos 		 && startswith (sec->output_section->name, ".ovl.init"))
   4322   1.1.1.2  christos 	  fixed_size -= sec->size;
   4323       1.1     skrll       if (count != old_count)
   4324       1.1     skrll 	bfd_arr[bfd_count++] = ibfd;
   4325       1.1     skrll     }
   4326       1.1     skrll 
   4327       1.1     skrll   /* Since the overlay link script selects sections by file name and
   4328       1.1     skrll      section name, ensure that file names are unique.  */
   4329       1.1     skrll   if (bfd_count > 1)
   4330       1.1     skrll     {
   4331   1.1.1.9  christos       bool ok = true;
   4332       1.1     skrll 
   4333       1.1     skrll       qsort (bfd_arr, bfd_count, sizeof (*bfd_arr), sort_bfds);
   4334       1.1     skrll       for (i = 1; i < bfd_count; ++i)
   4335   1.1.1.9  christos 	if (filename_cmp (bfd_get_filename (bfd_arr[i - 1]),
   4336   1.1.1.9  christos 			  bfd_get_filename (bfd_arr[i])) == 0)
   4337       1.1     skrll 	  {
   4338       1.1     skrll 	    if (bfd_arr[i - 1]->my_archive == bfd_arr[i]->my_archive)
   4339       1.1     skrll 	      {
   4340       1.1     skrll 		if (bfd_arr[i - 1]->my_archive && bfd_arr[i]->my_archive)
   4341   1.1.1.6  christos 		  /* xgettext:c-format */
   4342       1.1     skrll 		  info->callbacks->einfo (_("%s duplicated in %s\n"),
   4343   1.1.1.9  christos 					  bfd_get_filename (bfd_arr[i]),
   4344   1.1.1.9  christos 					  bfd_get_filename (bfd_arr[i]->my_archive));
   4345       1.1     skrll 		else
   4346       1.1     skrll 		  info->callbacks->einfo (_("%s duplicated\n"),
   4347   1.1.1.9  christos 					  bfd_get_filename (bfd_arr[i]));
   4348   1.1.1.9  christos 		ok = false;
   4349       1.1     skrll 	      }
   4350       1.1     skrll 	  }
   4351       1.1     skrll       if (!ok)
   4352       1.1     skrll 	{
   4353       1.1     skrll 	  info->callbacks->einfo (_("sorry, no support for duplicate "
   4354       1.1     skrll 				    "object files in auto-overlay script\n"));
   4355       1.1     skrll 	  bfd_set_error (bfd_error_bad_value);
   4356       1.1     skrll 	  goto err_exit;
   4357       1.1     skrll 	}
   4358       1.1     skrll     }
   4359       1.1     skrll   free (bfd_arr);
   4360       1.1     skrll 
   4361   1.1.1.2  christos   fixed_size += reserved;
   4362   1.1.1.2  christos   fixed_size += htab->non_ovly_stub * ovl_stub_size (htab->params);
   4363       1.1     skrll   if (fixed_size + mos_param.max_overlay_size <= htab->local_store)
   4364       1.1     skrll     {
   4365   1.1.1.2  christos       if (htab->params->ovly_flavour == ovly_soft_icache)
   4366   1.1.1.2  christos 	{
   4367   1.1.1.2  christos 	  /* Stubs in the non-icache area are bigger.  */
   4368   1.1.1.2  christos 	  fixed_size += htab->non_ovly_stub * 16;
   4369   1.1.1.2  christos 	  /* Space for icache manager tables.
   4370   1.1.1.2  christos 	     a) Tag array, one quadword per cache line.
   4371   1.1.1.2  christos 	     - word 0: ia address of present line, init to zero.  */
   4372   1.1.1.2  christos 	  fixed_size += 16 << htab->num_lines_log2;
   4373   1.1.1.2  christos 	  /* b) Rewrite "to" list, one quadword per cache line.  */
   4374   1.1.1.2  christos 	  fixed_size += 16 << htab->num_lines_log2;
   4375   1.1.1.2  christos 	  /* c) Rewrite "from" list, one byte per outgoing branch (rounded up
   4376   1.1.1.2  christos 		to a power-of-two number of full quadwords) per cache line.  */
   4377   1.1.1.2  christos 	  fixed_size += 16 << (htab->fromelem_size_log2
   4378   1.1.1.2  christos 			       + htab->num_lines_log2);
   4379   1.1.1.2  christos 	  /* d) Pointer to __ea backing store (toe), 1 quadword.  */
   4380   1.1.1.2  christos 	  fixed_size += 16;
   4381   1.1.1.2  christos 	}
   4382   1.1.1.2  christos       else
   4383   1.1.1.2  christos 	{
   4384   1.1.1.2  christos 	  /* Guess number of overlays.  Assuming overlay buffer is on
   4385   1.1.1.2  christos 	     average only half full should be conservative.  */
   4386   1.1.1.2  christos 	  ovlynum = (total_overlay_size * 2 * htab->params->num_lines
   4387   1.1.1.2  christos 		     / (htab->local_store - fixed_size));
   4388   1.1.1.2  christos 	  /* Space for _ovly_table[], _ovly_buf_table[] and toe.  */
   4389   1.1.1.2  christos 	  fixed_size += ovlynum * 16 + 16 + 4 + 16;
   4390   1.1.1.2  christos 	}
   4391       1.1     skrll     }
   4392       1.1     skrll 
   4393       1.1     skrll   if (fixed_size + mos_param.max_overlay_size > htab->local_store)
   4394   1.1.1.6  christos     /* xgettext:c-format */
   4395       1.1     skrll     info->callbacks->einfo (_("non-overlay size of 0x%v plus maximum overlay "
   4396       1.1     skrll 			      "size of 0x%v exceeds local store\n"),
   4397       1.1     skrll 			    (bfd_vma) fixed_size,
   4398       1.1     skrll 			    (bfd_vma) mos_param.max_overlay_size);
   4399       1.1     skrll 
   4400       1.1     skrll   /* Now see if we should put some functions in the non-overlay area.  */
   4401   1.1.1.2  christos   else if (fixed_size < htab->params->auto_overlay_fixed)
   4402       1.1     skrll     {
   4403       1.1     skrll       unsigned int max_fixed, lib_size;
   4404       1.1     skrll 
   4405       1.1     skrll       max_fixed = htab->local_store - mos_param.max_overlay_size;
   4406   1.1.1.2  christos       if (max_fixed > htab->params->auto_overlay_fixed)
   4407   1.1.1.2  christos 	max_fixed = htab->params->auto_overlay_fixed;
   4408       1.1     skrll       lib_size = max_fixed - fixed_size;
   4409       1.1     skrll       lib_size = auto_ovl_lib_functions (info, lib_size);
   4410       1.1     skrll       if (lib_size == (unsigned int) -1)
   4411       1.1     skrll 	goto err_exit;
   4412       1.1     skrll       fixed_size = max_fixed - lib_size;
   4413       1.1     skrll     }
   4414       1.1     skrll 
   4415       1.1     skrll   /* Build an array of sections, suitably sorted to place into
   4416       1.1     skrll      overlays.  */
   4417       1.1     skrll   ovly_sections = bfd_malloc (2 * count * sizeof (*ovly_sections));
   4418       1.1     skrll   if (ovly_sections == NULL)
   4419       1.1     skrll     goto err_exit;
   4420       1.1     skrll   ovly_p = ovly_sections;
   4421   1.1.1.9  christos   if (!for_each_node (collect_overlays, info, &ovly_p, true))
   4422       1.1     skrll     goto err_exit;
   4423       1.1     skrll   count = (size_t) (ovly_p - ovly_sections) / 2;
   4424   1.1.1.2  christos   ovly_map = bfd_malloc (count * sizeof (*ovly_map));
   4425   1.1.1.2  christos   if (ovly_map == NULL)
   4426   1.1.1.2  christos     goto err_exit;
   4427       1.1     skrll 
   4428       1.1     skrll   memset (&dummy_caller, 0, sizeof (dummy_caller));
   4429   1.1.1.2  christos   overlay_size = (htab->local_store - fixed_size) / htab->params->num_lines;
   4430   1.1.1.2  christos   if (htab->params->line_size != 0)
   4431   1.1.1.2  christos     overlay_size = htab->params->line_size;
   4432       1.1     skrll   base = 0;
   4433       1.1     skrll   ovlynum = 0;
   4434       1.1     skrll   while (base < count)
   4435       1.1     skrll     {
   4436   1.1.1.2  christos       unsigned int size = 0, rosize = 0, roalign = 0;
   4437       1.1     skrll 
   4438       1.1     skrll       for (i = base; i < count; i++)
   4439       1.1     skrll 	{
   4440   1.1.1.2  christos 	  asection *sec, *rosec;
   4441   1.1.1.2  christos 	  unsigned int tmp, rotmp;
   4442   1.1.1.2  christos 	  unsigned int num_stubs;
   4443       1.1     skrll 	  struct call_info *call, *pasty;
   4444       1.1     skrll 	  struct _spu_elf_section_data *sec_data;
   4445       1.1     skrll 	  struct spu_elf_stack_info *sinfo;
   4446   1.1.1.2  christos 	  unsigned int k;
   4447       1.1     skrll 
   4448       1.1     skrll 	  /* See whether we can add this section to the current
   4449       1.1     skrll 	     overlay without overflowing our overlay buffer.  */
   4450       1.1     skrll 	  sec = ovly_sections[2 * i];
   4451   1.1.1.2  christos 	  tmp = align_power (size, sec->alignment_power) + sec->size;
   4452   1.1.1.2  christos 	  rotmp = rosize;
   4453   1.1.1.2  christos 	  rosec = ovly_sections[2 * i + 1];
   4454   1.1.1.2  christos 	  if (rosec != NULL)
   4455   1.1.1.2  christos 	    {
   4456   1.1.1.2  christos 	      rotmp = align_power (rotmp, rosec->alignment_power) + rosec->size;
   4457   1.1.1.2  christos 	      if (roalign < rosec->alignment_power)
   4458   1.1.1.2  christos 		roalign = rosec->alignment_power;
   4459   1.1.1.2  christos 	    }
   4460   1.1.1.2  christos 	  if (align_power (tmp, roalign) + rotmp > overlay_size)
   4461       1.1     skrll 	    break;
   4462       1.1     skrll 	  if (sec->segment_mark)
   4463       1.1     skrll 	    {
   4464       1.1     skrll 	      /* Pasted sections must stay together, so add their
   4465       1.1     skrll 		 sizes too.  */
   4466   1.1.1.2  christos 	      pasty = find_pasted_call (sec);
   4467       1.1     skrll 	      while (pasty != NULL)
   4468       1.1     skrll 		{
   4469       1.1     skrll 		  struct function_info *call_fun = pasty->fun;
   4470   1.1.1.2  christos 		  tmp = (align_power (tmp, call_fun->sec->alignment_power)
   4471   1.1.1.2  christos 			 + call_fun->sec->size);
   4472       1.1     skrll 		  if (call_fun->rodata)
   4473   1.1.1.2  christos 		    {
   4474   1.1.1.2  christos 		      rotmp = (align_power (rotmp,
   4475   1.1.1.2  christos 					    call_fun->rodata->alignment_power)
   4476   1.1.1.2  christos 			       + call_fun->rodata->size);
   4477   1.1.1.2  christos 		      if (roalign < rosec->alignment_power)
   4478   1.1.1.2  christos 			roalign = rosec->alignment_power;
   4479   1.1.1.2  christos 		    }
   4480       1.1     skrll 		  for (pasty = call_fun->call_list; pasty; pasty = pasty->next)
   4481       1.1     skrll 		    if (pasty->is_pasted)
   4482       1.1     skrll 		      break;
   4483       1.1     skrll 		}
   4484       1.1     skrll 	    }
   4485   1.1.1.2  christos 	  if (align_power (tmp, roalign) + rotmp > overlay_size)
   4486       1.1     skrll 	    break;
   4487       1.1     skrll 
   4488       1.1     skrll 	  /* If we add this section, we might need new overlay call
   4489       1.1     skrll 	     stubs.  Add any overlay section calls to dummy_call.  */
   4490       1.1     skrll 	  pasty = NULL;
   4491       1.1     skrll 	  sec_data = spu_elf_section_data (sec);
   4492       1.1     skrll 	  sinfo = sec_data->u.i.stack_info;
   4493   1.1.1.2  christos 	  for (k = 0; k < (unsigned) sinfo->num_fun; ++k)
   4494       1.1     skrll 	    for (call = sinfo->fun[k].call_list; call; call = call->next)
   4495       1.1     skrll 	      if (call->is_pasted)
   4496       1.1     skrll 		{
   4497       1.1     skrll 		  BFD_ASSERT (pasty == NULL);
   4498       1.1     skrll 		  pasty = call;
   4499       1.1     skrll 		}
   4500       1.1     skrll 	      else if (call->fun->sec->linker_mark)
   4501       1.1     skrll 		{
   4502       1.1     skrll 		  if (!copy_callee (&dummy_caller, call))
   4503       1.1     skrll 		    goto err_exit;
   4504       1.1     skrll 		}
   4505       1.1     skrll 	  while (pasty != NULL)
   4506       1.1     skrll 	    {
   4507       1.1     skrll 	      struct function_info *call_fun = pasty->fun;
   4508       1.1     skrll 	      pasty = NULL;
   4509       1.1     skrll 	      for (call = call_fun->call_list; call; call = call->next)
   4510       1.1     skrll 		if (call->is_pasted)
   4511       1.1     skrll 		  {
   4512       1.1     skrll 		    BFD_ASSERT (pasty == NULL);
   4513       1.1     skrll 		    pasty = call;
   4514       1.1     skrll 		  }
   4515       1.1     skrll 		else if (!copy_callee (&dummy_caller, call))
   4516       1.1     skrll 		  goto err_exit;
   4517       1.1     skrll 	    }
   4518       1.1     skrll 
   4519       1.1     skrll 	  /* Calculate call stub size.  */
   4520   1.1.1.2  christos 	  num_stubs = 0;
   4521       1.1     skrll 	  for (call = dummy_caller.call_list; call; call = call->next)
   4522       1.1     skrll 	    {
   4523   1.1.1.2  christos 	      unsigned int stub_delta = 1;
   4524   1.1.1.2  christos 
   4525   1.1.1.2  christos 	      if (htab->params->ovly_flavour == ovly_soft_icache)
   4526   1.1.1.2  christos 		stub_delta = call->count;
   4527   1.1.1.2  christos 	      num_stubs += stub_delta;
   4528       1.1     skrll 
   4529       1.1     skrll 	      /* If the call is within this overlay, we won't need a
   4530       1.1     skrll 		 stub.  */
   4531       1.1     skrll 	      for (k = base; k < i + 1; k++)
   4532       1.1     skrll 		if (call->fun->sec == ovly_sections[2 * k])
   4533       1.1     skrll 		  {
   4534   1.1.1.2  christos 		    num_stubs -= stub_delta;
   4535       1.1     skrll 		    break;
   4536       1.1     skrll 		  }
   4537       1.1     skrll 	    }
   4538   1.1.1.2  christos 	  if (htab->params->ovly_flavour == ovly_soft_icache
   4539   1.1.1.2  christos 	      && num_stubs > htab->params->max_branch)
   4540   1.1.1.2  christos 	    break;
   4541   1.1.1.2  christos 	  if (align_power (tmp, roalign) + rotmp
   4542   1.1.1.2  christos 	      + num_stubs * ovl_stub_size (htab->params) > overlay_size)
   4543       1.1     skrll 	    break;
   4544       1.1     skrll 	  size = tmp;
   4545   1.1.1.2  christos 	  rosize = rotmp;
   4546       1.1     skrll 	}
   4547       1.1     skrll 
   4548       1.1     skrll       if (i == base)
   4549       1.1     skrll 	{
   4550   1.1.1.6  christos 	  /* xgettext:c-format */
   4551   1.1.1.7  christos 	  info->callbacks->einfo (_("%pB:%pA%s exceeds overlay size\n"),
   4552       1.1     skrll 				  ovly_sections[2 * i]->owner,
   4553       1.1     skrll 				  ovly_sections[2 * i],
   4554       1.1     skrll 				  ovly_sections[2 * i + 1] ? " + rodata" : "");
   4555       1.1     skrll 	  bfd_set_error (bfd_error_bad_value);
   4556       1.1     skrll 	  goto err_exit;
   4557       1.1     skrll 	}
   4558       1.1     skrll 
   4559   1.1.1.2  christos       while (dummy_caller.call_list != NULL)
   4560       1.1     skrll 	{
   4561   1.1.1.2  christos 	  struct call_info *call = dummy_caller.call_list;
   4562   1.1.1.2  christos 	  dummy_caller.call_list = call->next;
   4563   1.1.1.2  christos 	  free (call);
   4564   1.1.1.2  christos 	}
   4565   1.1.1.2  christos 
   4566   1.1.1.2  christos       ++ovlynum;
   4567   1.1.1.2  christos       while (base < i)
   4568   1.1.1.2  christos 	ovly_map[base++] = ovlynum;
   4569   1.1.1.2  christos     }
   4570   1.1.1.2  christos 
   4571   1.1.1.2  christos   script = htab->params->spu_elf_open_overlay_script ();
   4572   1.1.1.2  christos 
   4573   1.1.1.2  christos   if (htab->params->ovly_flavour == ovly_soft_icache)
   4574   1.1.1.2  christos     {
   4575   1.1.1.2  christos       if (fprintf (script, "SECTIONS\n{\n") <= 0)
   4576   1.1.1.2  christos 	goto file_err;
   4577   1.1.1.2  christos 
   4578   1.1.1.2  christos       if (fprintf (script,
   4579   1.1.1.2  christos 		   " . = ALIGN (%u);\n"
   4580   1.1.1.2  christos 		   " .ovl.init : { *(.ovl.init) }\n"
   4581   1.1.1.2  christos 		   " . = ABSOLUTE (ADDR (.ovl.init));\n",
   4582   1.1.1.2  christos 		   htab->params->line_size) <= 0)
   4583   1.1.1.2  christos 	goto file_err;
   4584       1.1     skrll 
   4585   1.1.1.2  christos       base = 0;
   4586   1.1.1.2  christos       ovlynum = 1;
   4587   1.1.1.2  christos       while (base < count)
   4588   1.1.1.2  christos 	{
   4589   1.1.1.2  christos 	  unsigned int indx = ovlynum - 1;
   4590   1.1.1.2  christos 	  unsigned int vma, lma;
   4591   1.1.1.2  christos 
   4592   1.1.1.2  christos 	  vma = (indx & (htab->params->num_lines - 1)) << htab->line_size_log2;
   4593   1.1.1.2  christos 	  lma = vma + (((indx >> htab->num_lines_log2) + 1) << 18);
   4594   1.1.1.2  christos 
   4595   1.1.1.2  christos 	  if (fprintf (script, " .ovly%u ABSOLUTE (ADDR (.ovl.init)) + %u "
   4596   1.1.1.2  christos 			       ": AT (LOADADDR (.ovl.init) + %u) {\n",
   4597   1.1.1.2  christos 		       ovlynum, vma, lma) <= 0)
   4598       1.1     skrll 	    goto file_err;
   4599       1.1     skrll 
   4600   1.1.1.2  christos 	  base = print_one_overlay_section (script, base, count, ovlynum,
   4601   1.1.1.2  christos 					    ovly_map, ovly_sections, info);
   4602   1.1.1.2  christos 	  if (base == (unsigned) -1)
   4603       1.1     skrll 	    goto file_err;
   4604       1.1     skrll 
   4605   1.1.1.2  christos 	  if (fprintf (script, "  }\n") <= 0)
   4606   1.1.1.2  christos 	    goto file_err;
   4607   1.1.1.2  christos 
   4608   1.1.1.2  christos 	  ovlynum++;
   4609       1.1     skrll 	}
   4610       1.1     skrll 
   4611   1.1.1.2  christos       if (fprintf (script, " . = ABSOLUTE (ADDR (.ovl.init)) + %u;\n",
   4612   1.1.1.2  christos 		   1 << (htab->num_lines_log2 + htab->line_size_log2)) <= 0)
   4613       1.1     skrll 	goto file_err;
   4614       1.1     skrll 
   4615   1.1.1.2  christos       if (fprintf (script, "}\nINSERT AFTER .toe;\n") <= 0)
   4616   1.1.1.2  christos 	goto file_err;
   4617   1.1.1.2  christos     }
   4618   1.1.1.2  christos   else
   4619   1.1.1.2  christos     {
   4620   1.1.1.2  christos       if (fprintf (script, "SECTIONS\n{\n") <= 0)
   4621   1.1.1.2  christos 	goto file_err;
   4622   1.1.1.2  christos 
   4623   1.1.1.2  christos       if (fprintf (script,
   4624   1.1.1.2  christos 		   " . = ALIGN (16);\n"
   4625   1.1.1.2  christos 		   " .ovl.init : { *(.ovl.init) }\n"
   4626   1.1.1.2  christos 		   " . = ABSOLUTE (ADDR (.ovl.init));\n") <= 0)
   4627   1.1.1.2  christos 	goto file_err;
   4628   1.1.1.2  christos 
   4629   1.1.1.2  christos       for (region = 1; region <= htab->params->num_lines; region++)
   4630       1.1     skrll 	{
   4631   1.1.1.2  christos 	  ovlynum = region;
   4632   1.1.1.2  christos 	  base = 0;
   4633   1.1.1.2  christos 	  while (base < count && ovly_map[base] < ovlynum)
   4634   1.1.1.2  christos 	    base++;
   4635   1.1.1.2  christos 
   4636   1.1.1.2  christos 	  if (base == count)
   4637   1.1.1.2  christos 	    break;
   4638   1.1.1.2  christos 
   4639   1.1.1.2  christos 	  if (region == 1)
   4640   1.1.1.2  christos 	    {
   4641   1.1.1.2  christos 	      /* We need to set lma since we are overlaying .ovl.init.  */
   4642   1.1.1.2  christos 	      if (fprintf (script,
   4643   1.1.1.2  christos 			   " OVERLAY : AT (ALIGN (LOADADDR (.ovl.init) + SIZEOF (.ovl.init), 16))\n {\n") <= 0)
   4644   1.1.1.2  christos 		goto file_err;
   4645   1.1.1.2  christos 	    }
   4646   1.1.1.2  christos 	  else
   4647   1.1.1.2  christos 	    {
   4648   1.1.1.2  christos 	      if (fprintf (script, " OVERLAY :\n {\n") <= 0)
   4649   1.1.1.2  christos 		goto file_err;
   4650   1.1.1.2  christos 	    }
   4651   1.1.1.2  christos 
   4652   1.1.1.2  christos 	  while (base < count)
   4653   1.1.1.2  christos 	    {
   4654   1.1.1.2  christos 	      if (fprintf (script, "  .ovly%u {\n", ovlynum) <= 0)
   4655   1.1.1.2  christos 		goto file_err;
   4656   1.1.1.2  christos 
   4657   1.1.1.2  christos 	      base = print_one_overlay_section (script, base, count, ovlynum,
   4658   1.1.1.2  christos 						ovly_map, ovly_sections, info);
   4659   1.1.1.2  christos 	      if (base == (unsigned) -1)
   4660   1.1.1.2  christos 		goto file_err;
   4661   1.1.1.2  christos 
   4662   1.1.1.2  christos 	      if (fprintf (script, "  }\n") <= 0)
   4663   1.1.1.2  christos 		goto file_err;
   4664   1.1.1.2  christos 
   4665   1.1.1.2  christos 	      ovlynum += htab->params->num_lines;
   4666   1.1.1.2  christos 	      while (base < count && ovly_map[base] < ovlynum)
   4667   1.1.1.2  christos 		base++;
   4668   1.1.1.2  christos 	    }
   4669   1.1.1.2  christos 
   4670   1.1.1.2  christos 	  if (fprintf (script, " }\n") <= 0)
   4671   1.1.1.2  christos 	    goto file_err;
   4672       1.1     skrll 	}
   4673       1.1     skrll 
   4674   1.1.1.2  christos       if (fprintf (script, "}\nINSERT BEFORE .text;\n") <= 0)
   4675   1.1.1.2  christos 	goto file_err;
   4676       1.1     skrll     }
   4677   1.1.1.2  christos 
   4678   1.1.1.2  christos   free (ovly_map);
   4679       1.1     skrll   free (ovly_sections);
   4680       1.1     skrll 
   4681       1.1     skrll   if (fclose (script) != 0)
   4682       1.1     skrll     goto file_err;
   4683       1.1     skrll 
   4684   1.1.1.2  christos   if (htab->params->auto_overlay & AUTO_RELINK)
   4685   1.1.1.2  christos     (*htab->params->spu_elf_relink) ();
   4686       1.1     skrll 
   4687       1.1     skrll   xexit (0);
   4688       1.1     skrll 
   4689       1.1     skrll  file_err:
   4690       1.1     skrll   bfd_set_error (bfd_error_system_call);
   4691       1.1     skrll  err_exit:
   4692  1.1.1.11  christos   info->callbacks->fatal (_("%P: auto overlay error: %E\n"));
   4693       1.1     skrll }
   4694       1.1     skrll 
   4695       1.1     skrll /* Provide an estimate of total stack required.  */
   4696       1.1     skrll 
   4697   1.1.1.9  christos static bool
   4698   1.1.1.2  christos spu_elf_stack_analysis (struct bfd_link_info *info)
   4699       1.1     skrll {
   4700   1.1.1.2  christos   struct spu_link_hash_table *htab;
   4701       1.1     skrll   struct _sum_stack_param sum_stack_param;
   4702       1.1     skrll 
   4703       1.1     skrll   if (!discover_functions (info))
   4704   1.1.1.9  christos     return false;
   4705       1.1     skrll 
   4706       1.1     skrll   if (!build_call_tree (info))
   4707   1.1.1.9  christos     return false;
   4708       1.1     skrll 
   4709   1.1.1.2  christos   htab = spu_hash_table (info);
   4710   1.1.1.2  christos   if (htab->params->stack_analysis)
   4711   1.1.1.2  christos     {
   4712   1.1.1.2  christos       info->callbacks->info (_("Stack size for call graph root nodes.\n"));
   4713   1.1.1.2  christos       info->callbacks->minfo (_("\nStack size for functions.  "
   4714   1.1.1.2  christos 				"Annotations: '*' max stack, 't' tail call\n"));
   4715   1.1.1.2  christos     }
   4716       1.1     skrll 
   4717   1.1.1.2  christos   sum_stack_param.emit_stack_syms = htab->params->emit_stack_syms;
   4718       1.1     skrll   sum_stack_param.overall_stack = 0;
   4719   1.1.1.9  christos   if (!for_each_node (sum_stack, info, &sum_stack_param, true))
   4720   1.1.1.9  christos     return false;
   4721       1.1     skrll 
   4722   1.1.1.2  christos   if (htab->params->stack_analysis)
   4723   1.1.1.2  christos     info->callbacks->info (_("Maximum stack required is 0x%v\n"),
   4724   1.1.1.2  christos 			   (bfd_vma) sum_stack_param.overall_stack);
   4725   1.1.1.9  christos   return true;
   4726       1.1     skrll }
   4727       1.1     skrll 
   4728       1.1     skrll /* Perform a final link.  */
   4729       1.1     skrll 
   4730   1.1.1.9  christos static bool
   4731       1.1     skrll spu_elf_final_link (bfd *output_bfd, struct bfd_link_info *info)
   4732       1.1     skrll {
   4733       1.1     skrll   struct spu_link_hash_table *htab = spu_hash_table (info);
   4734       1.1     skrll 
   4735   1.1.1.2  christos   if (htab->params->auto_overlay)
   4736   1.1.1.2  christos     spu_elf_auto_overlay (info);
   4737       1.1     skrll 
   4738   1.1.1.2  christos   if ((htab->params->stack_analysis
   4739   1.1.1.2  christos        || (htab->params->ovly_flavour == ovly_soft_icache
   4740   1.1.1.2  christos 	   && htab->params->lrlive_analysis))
   4741   1.1.1.2  christos       && !spu_elf_stack_analysis (info))
   4742   1.1.1.6  christos     info->callbacks->einfo (_("%X%P: stack/lrlive analysis error: %E\n"));
   4743   1.1.1.2  christos 
   4744   1.1.1.2  christos   if (!spu_elf_build_stubs (info))
   4745  1.1.1.11  christos     info->callbacks->fatal (_("%P: can not build overlay stubs: %E\n"));
   4746       1.1     skrll 
   4747       1.1     skrll   return bfd_elf_final_link (output_bfd, info);
   4748       1.1     skrll }
   4749       1.1     skrll 
   4750   1.1.1.4  christos /* Called when not normally emitting relocs, ie. !bfd_link_relocatable (info)
   4751       1.1     skrll    and !info->emitrelocations.  Returns a count of special relocs
   4752       1.1     skrll    that need to be emitted.  */
   4753       1.1     skrll 
   4754       1.1     skrll static unsigned int
   4755   1.1.1.2  christos spu_elf_count_relocs (struct bfd_link_info *info, asection *sec)
   4756       1.1     skrll {
   4757   1.1.1.2  christos   Elf_Internal_Rela *relocs;
   4758       1.1     skrll   unsigned int count = 0;
   4759       1.1     skrll 
   4760   1.1.1.2  christos   relocs = _bfd_elf_link_read_relocs (sec->owner, sec, NULL, NULL,
   4761   1.1.1.2  christos 				      info->keep_memory);
   4762   1.1.1.2  christos   if (relocs != NULL)
   4763       1.1     skrll     {
   4764   1.1.1.2  christos       Elf_Internal_Rela *rel;
   4765   1.1.1.2  christos       Elf_Internal_Rela *relend = relocs + sec->reloc_count;
   4766   1.1.1.2  christos 
   4767   1.1.1.2  christos       for (rel = relocs; rel < relend; rel++)
   4768   1.1.1.2  christos 	{
   4769   1.1.1.2  christos 	  int r_type = ELF32_R_TYPE (rel->r_info);
   4770   1.1.1.2  christos 	  if (r_type == R_SPU_PPU32 || r_type == R_SPU_PPU64)
   4771   1.1.1.2  christos 	    ++count;
   4772   1.1.1.2  christos 	}
   4773   1.1.1.2  christos 
   4774   1.1.1.2  christos       if (elf_section_data (sec)->relocs != relocs)
   4775   1.1.1.2  christos 	free (relocs);
   4776       1.1     skrll     }
   4777       1.1     skrll 
   4778       1.1     skrll   return count;
   4779       1.1     skrll }
   4780       1.1     skrll 
   4781   1.1.1.2  christos /* Functions for adding fixup records to .fixup */
   4782   1.1.1.2  christos 
   4783   1.1.1.2  christos #define FIXUP_RECORD_SIZE 4
   4784   1.1.1.2  christos 
   4785   1.1.1.2  christos #define FIXUP_PUT(output_bfd,htab,index,addr) \
   4786   1.1.1.2  christos 	  bfd_put_32 (output_bfd, addr, \
   4787   1.1.1.2  christos 		      htab->sfixup->contents + FIXUP_RECORD_SIZE * (index))
   4788   1.1.1.2  christos #define FIXUP_GET(output_bfd,htab,index) \
   4789   1.1.1.2  christos 	  bfd_get_32 (output_bfd, \
   4790   1.1.1.2  christos 		      htab->sfixup->contents + FIXUP_RECORD_SIZE * (index))
   4791   1.1.1.2  christos 
   4792   1.1.1.2  christos /* Store OFFSET in .fixup.  This assumes it will be called with an
   4793   1.1.1.2  christos    increasing OFFSET.  When this OFFSET fits with the last base offset,
   4794   1.1.1.2  christos    it just sets a bit, otherwise it adds a new fixup record.  */
   4795   1.1.1.2  christos static void
   4796   1.1.1.2  christos spu_elf_emit_fixup (bfd * output_bfd, struct bfd_link_info *info,
   4797   1.1.1.2  christos 		    bfd_vma offset)
   4798   1.1.1.2  christos {
   4799   1.1.1.2  christos   struct spu_link_hash_table *htab = spu_hash_table (info);
   4800   1.1.1.2  christos   asection *sfixup = htab->sfixup;
   4801   1.1.1.2  christos   bfd_vma qaddr = offset & ~(bfd_vma) 15;
   4802   1.1.1.2  christos   bfd_vma bit = ((bfd_vma) 8) >> ((offset & 15) >> 2);
   4803   1.1.1.2  christos   if (sfixup->reloc_count == 0)
   4804   1.1.1.2  christos     {
   4805   1.1.1.2  christos       FIXUP_PUT (output_bfd, htab, 0, qaddr | bit);
   4806   1.1.1.2  christos       sfixup->reloc_count++;
   4807   1.1.1.2  christos     }
   4808   1.1.1.2  christos   else
   4809   1.1.1.2  christos     {
   4810   1.1.1.2  christos       bfd_vma base = FIXUP_GET (output_bfd, htab, sfixup->reloc_count - 1);
   4811   1.1.1.2  christos       if (qaddr != (base & ~(bfd_vma) 15))
   4812   1.1.1.2  christos 	{
   4813   1.1.1.2  christos 	  if ((sfixup->reloc_count + 1) * FIXUP_RECORD_SIZE > sfixup->size)
   4814   1.1.1.6  christos 	    _bfd_error_handler (_("fatal error while creating .fixup"));
   4815   1.1.1.2  christos 	  FIXUP_PUT (output_bfd, htab, sfixup->reloc_count, qaddr | bit);
   4816   1.1.1.2  christos 	  sfixup->reloc_count++;
   4817   1.1.1.2  christos 	}
   4818   1.1.1.2  christos       else
   4819   1.1.1.2  christos 	FIXUP_PUT (output_bfd, htab, sfixup->reloc_count - 1, base | bit);
   4820   1.1.1.2  christos     }
   4821   1.1.1.2  christos }
   4822   1.1.1.2  christos 
   4823       1.1     skrll /* Apply RELOCS to CONTENTS of INPUT_SECTION from INPUT_BFD.  */
   4824       1.1     skrll 
   4825       1.1     skrll static int
   4826       1.1     skrll spu_elf_relocate_section (bfd *output_bfd,
   4827       1.1     skrll 			  struct bfd_link_info *info,
   4828       1.1     skrll 			  bfd *input_bfd,
   4829       1.1     skrll 			  asection *input_section,
   4830       1.1     skrll 			  bfd_byte *contents,
   4831       1.1     skrll 			  Elf_Internal_Rela *relocs,
   4832       1.1     skrll 			  Elf_Internal_Sym *local_syms,
   4833       1.1     skrll 			  asection **local_sections)
   4834       1.1     skrll {
   4835       1.1     skrll   Elf_Internal_Shdr *symtab_hdr;
   4836       1.1     skrll   struct elf_link_hash_entry **sym_hashes;
   4837       1.1     skrll   Elf_Internal_Rela *rel, *relend;
   4838       1.1     skrll   struct spu_link_hash_table *htab;
   4839   1.1.1.2  christos   asection *ea;
   4840   1.1.1.9  christos   int ret = true;
   4841   1.1.1.9  christos   bool emit_these_relocs = false;
   4842   1.1.1.9  christos   bool is_ea_sym;
   4843   1.1.1.9  christos   bool stubs;
   4844   1.1.1.2  christos   unsigned int iovl = 0;
   4845       1.1     skrll 
   4846       1.1     skrll   htab = spu_hash_table (info);
   4847       1.1     skrll   stubs = (htab->stub_sec != NULL
   4848   1.1.1.2  christos 	   && maybe_needs_stubs (input_section));
   4849   1.1.1.2  christos   iovl = overlay_index (input_section);
   4850   1.1.1.2  christos   ea = bfd_get_section_by_name (output_bfd, "._ea");
   4851       1.1     skrll   symtab_hdr = &elf_tdata (input_bfd)->symtab_hdr;
   4852       1.1     skrll   sym_hashes = (struct elf_link_hash_entry **) (elf_sym_hashes (input_bfd));
   4853       1.1     skrll 
   4854       1.1     skrll   rel = relocs;
   4855       1.1     skrll   relend = relocs + input_section->reloc_count;
   4856       1.1     skrll   for (; rel < relend; rel++)
   4857       1.1     skrll     {
   4858       1.1     skrll       int r_type;
   4859       1.1     skrll       reloc_howto_type *howto;
   4860       1.1     skrll       unsigned int r_symndx;
   4861       1.1     skrll       Elf_Internal_Sym *sym;
   4862       1.1     skrll       asection *sec;
   4863       1.1     skrll       struct elf_link_hash_entry *h;
   4864       1.1     skrll       const char *sym_name;
   4865       1.1     skrll       bfd_vma relocation;
   4866       1.1     skrll       bfd_vma addend;
   4867       1.1     skrll       bfd_reloc_status_type r;
   4868   1.1.1.9  christos       bool unresolved_reloc;
   4869       1.1     skrll       enum _stub_type stub_type;
   4870       1.1     skrll 
   4871       1.1     skrll       r_symndx = ELF32_R_SYM (rel->r_info);
   4872       1.1     skrll       r_type = ELF32_R_TYPE (rel->r_info);
   4873       1.1     skrll       howto = elf_howto_table + r_type;
   4874   1.1.1.9  christos       unresolved_reloc = false;
   4875       1.1     skrll       h = NULL;
   4876       1.1     skrll       sym = NULL;
   4877       1.1     skrll       sec = NULL;
   4878       1.1     skrll       if (r_symndx < symtab_hdr->sh_info)
   4879       1.1     skrll 	{
   4880       1.1     skrll 	  sym = local_syms + r_symndx;
   4881       1.1     skrll 	  sec = local_sections[r_symndx];
   4882       1.1     skrll 	  sym_name = bfd_elf_sym_name (input_bfd, symtab_hdr, sym, sec);
   4883       1.1     skrll 	  relocation = _bfd_elf_rela_local_sym (output_bfd, sym, &sec, rel);
   4884       1.1     skrll 	}
   4885       1.1     skrll       else
   4886       1.1     skrll 	{
   4887       1.1     skrll 	  if (sym_hashes == NULL)
   4888   1.1.1.9  christos 	    return false;
   4889       1.1     skrll 
   4890       1.1     skrll 	  h = sym_hashes[r_symndx - symtab_hdr->sh_info];
   4891       1.1     skrll 
   4892   1.1.1.4  christos 	  if (info->wrap_hash != NULL
   4893   1.1.1.4  christos 	      && (input_section->flags & SEC_DEBUGGING) != 0)
   4894   1.1.1.4  christos 	    h = ((struct elf_link_hash_entry *)
   4895   1.1.1.4  christos 		 unwrap_hash_lookup (info, input_bfd, &h->root));
   4896   1.1.1.4  christos 
   4897       1.1     skrll 	  while (h->root.type == bfd_link_hash_indirect
   4898       1.1     skrll 		 || h->root.type == bfd_link_hash_warning)
   4899       1.1     skrll 	    h = (struct elf_link_hash_entry *) h->root.u.i.link;
   4900       1.1     skrll 
   4901       1.1     skrll 	  relocation = 0;
   4902       1.1     skrll 	  if (h->root.type == bfd_link_hash_defined
   4903       1.1     skrll 	      || h->root.type == bfd_link_hash_defweak)
   4904       1.1     skrll 	    {
   4905       1.1     skrll 	      sec = h->root.u.def.section;
   4906       1.1     skrll 	      if (sec == NULL
   4907       1.1     skrll 		  || sec->output_section == NULL)
   4908       1.1     skrll 		/* Set a flag that will be cleared later if we find a
   4909       1.1     skrll 		   relocation value for this symbol.  output_section
   4910       1.1     skrll 		   is typically NULL for symbols satisfied by a shared
   4911       1.1     skrll 		   library.  */
   4912   1.1.1.9  christos 		unresolved_reloc = true;
   4913       1.1     skrll 	      else
   4914       1.1     skrll 		relocation = (h->root.u.def.value
   4915       1.1     skrll 			      + sec->output_section->vma
   4916       1.1     skrll 			      + sec->output_offset);
   4917       1.1     skrll 	    }
   4918       1.1     skrll 	  else if (h->root.type == bfd_link_hash_undefweak)
   4919       1.1     skrll 	    ;
   4920       1.1     skrll 	  else if (info->unresolved_syms_in_objects == RM_IGNORE
   4921       1.1     skrll 		   && ELF_ST_VISIBILITY (h->other) == STV_DEFAULT)
   4922       1.1     skrll 	    ;
   4923   1.1.1.4  christos 	  else if (!bfd_link_relocatable (info)
   4924       1.1     skrll 		   && !(r_type == R_SPU_PPU32 || r_type == R_SPU_PPU64))
   4925       1.1     skrll 	    {
   4926   1.1.1.9  christos 	      bool err;
   4927   1.1.1.9  christos 
   4928   1.1.1.9  christos 	      err = (info->unresolved_syms_in_objects == RM_DIAGNOSE
   4929   1.1.1.9  christos 		     && !info->warn_unresolved_syms)
   4930   1.1.1.9  christos 		|| ELF_ST_VISIBILITY (h->other) != STV_DEFAULT;
   4931   1.1.1.9  christos 
   4932   1.1.1.9  christos 	      info->callbacks->undefined_symbol
   4933   1.1.1.9  christos 		(info, h->root.root.string, input_bfd,
   4934   1.1.1.9  christos 		 input_section, rel->r_offset, err);
   4935       1.1     skrll 	    }
   4936       1.1     skrll 	  sym_name = h->root.root.string;
   4937       1.1     skrll 	}
   4938       1.1     skrll 
   4939   1.1.1.3  christos       if (sec != NULL && discarded_section (sec))
   4940   1.1.1.2  christos 	RELOC_AGAINST_DISCARDED_SECTION (info, input_bfd, input_section,
   4941   1.1.1.3  christos 					 rel, 1, relend, howto, 0, contents);
   4942       1.1     skrll 
   4943   1.1.1.4  christos       if (bfd_link_relocatable (info))
   4944       1.1     skrll 	continue;
   4945       1.1     skrll 
   4946   1.1.1.2  christos       /* Change "a rt,ra,rb" to "ai rt,ra,0". */
   4947   1.1.1.2  christos       if (r_type == R_SPU_ADD_PIC
   4948   1.1.1.2  christos 	  && h != NULL
   4949   1.1.1.2  christos 	  && !(h->def_regular || ELF_COMMON_DEF_P (h)))
   4950   1.1.1.2  christos 	{
   4951   1.1.1.2  christos 	  bfd_byte *loc = contents + rel->r_offset;
   4952   1.1.1.4  christos 	  loc[0] = 0x1c;
   4953   1.1.1.4  christos 	  loc[1] = 0x00;
   4954   1.1.1.2  christos 	  loc[2] &= 0x3f;
   4955   1.1.1.2  christos 	}
   4956   1.1.1.2  christos 
   4957       1.1     skrll       is_ea_sym = (ea != NULL
   4958       1.1     skrll 		   && sec != NULL
   4959       1.1     skrll 		   && sec->output_section == ea);
   4960       1.1     skrll 
   4961   1.1.1.2  christos       /* If this symbol is in an overlay area, we may need to relocate
   4962   1.1.1.2  christos 	 to the overlay stub.  */
   4963   1.1.1.2  christos       addend = rel->r_addend;
   4964   1.1.1.2  christos       if (stubs
   4965   1.1.1.2  christos 	  && !is_ea_sym
   4966   1.1.1.2  christos 	  && (stub_type = needs_ovl_stub (h, sym, sec, input_section, rel,
   4967   1.1.1.2  christos 					  contents, info)) != no_stub)
   4968   1.1.1.2  christos 	{
   4969   1.1.1.2  christos 	  unsigned int ovl = 0;
   4970   1.1.1.2  christos 	  struct got_entry *g, **head;
   4971   1.1.1.2  christos 
   4972   1.1.1.2  christos 	  if (stub_type != nonovl_stub)
   4973   1.1.1.2  christos 	    ovl = iovl;
   4974   1.1.1.2  christos 
   4975   1.1.1.2  christos 	  if (h != NULL)
   4976   1.1.1.2  christos 	    head = &h->got.glist;
   4977   1.1.1.2  christos 	  else
   4978   1.1.1.2  christos 	    head = elf_local_got_ents (input_bfd) + r_symndx;
   4979   1.1.1.2  christos 
   4980   1.1.1.2  christos 	  for (g = *head; g != NULL; g = g->next)
   4981   1.1.1.2  christos 	    if (htab->params->ovly_flavour == ovly_soft_icache
   4982   1.1.1.2  christos 		? (g->ovl == ovl
   4983   1.1.1.2  christos 		   && g->br_addr == (rel->r_offset
   4984   1.1.1.2  christos 				     + input_section->output_offset
   4985   1.1.1.2  christos 				     + input_section->output_section->vma))
   4986   1.1.1.2  christos 		: g->addend == addend && (g->ovl == ovl || g->ovl == 0))
   4987   1.1.1.2  christos 	      break;
   4988   1.1.1.2  christos 	  if (g == NULL)
   4989   1.1.1.2  christos 	    abort ();
   4990   1.1.1.2  christos 
   4991   1.1.1.2  christos 	  relocation = g->stub_addr;
   4992   1.1.1.2  christos 	  addend = 0;
   4993   1.1.1.2  christos 	}
   4994   1.1.1.2  christos       else
   4995   1.1.1.2  christos 	{
   4996   1.1.1.2  christos 	  /* For soft icache, encode the overlay index into addresses.  */
   4997   1.1.1.2  christos 	  if (htab->params->ovly_flavour == ovly_soft_icache
   4998   1.1.1.2  christos 	      && (r_type == R_SPU_ADDR16_HI
   4999   1.1.1.2  christos 		  || r_type == R_SPU_ADDR32 || r_type == R_SPU_REL32)
   5000   1.1.1.2  christos 	      && !is_ea_sym)
   5001   1.1.1.2  christos 	    {
   5002   1.1.1.2  christos 	      unsigned int ovl = overlay_index (sec);
   5003   1.1.1.2  christos 	      if (ovl != 0)
   5004   1.1.1.2  christos 		{
   5005   1.1.1.2  christos 		  unsigned int set_id = ((ovl - 1) >> htab->num_lines_log2) + 1;
   5006   1.1.1.2  christos 		  relocation += set_id << 18;
   5007   1.1.1.2  christos 		}
   5008   1.1.1.2  christos 	    }
   5009   1.1.1.2  christos 	}
   5010   1.1.1.2  christos 
   5011   1.1.1.4  christos       if (htab->params->emit_fixups && !bfd_link_relocatable (info)
   5012   1.1.1.2  christos 	  && (input_section->flags & SEC_ALLOC) != 0
   5013   1.1.1.2  christos 	  && r_type == R_SPU_ADDR32)
   5014   1.1.1.2  christos 	{
   5015   1.1.1.2  christos 	  bfd_vma offset;
   5016   1.1.1.2  christos 	  offset = rel->r_offset + input_section->output_section->vma
   5017   1.1.1.2  christos 		   + input_section->output_offset;
   5018   1.1.1.2  christos 	  spu_elf_emit_fixup (output_bfd, info, offset);
   5019   1.1.1.2  christos 	}
   5020   1.1.1.2  christos 
   5021   1.1.1.2  christos       if (unresolved_reloc)
   5022   1.1.1.2  christos 	;
   5023   1.1.1.2  christos       else if (r_type == R_SPU_PPU32 || r_type == R_SPU_PPU64)
   5024       1.1     skrll 	{
   5025       1.1     skrll 	  if (is_ea_sym)
   5026       1.1     skrll 	    {
   5027       1.1     skrll 	      /* ._ea is a special section that isn't allocated in SPU
   5028       1.1     skrll 		 memory, but rather occupies space in PPU memory as
   5029       1.1     skrll 		 part of an embedded ELF image.  If this reloc is
   5030       1.1     skrll 		 against a symbol defined in ._ea, then transform the
   5031       1.1     skrll 		 reloc into an equivalent one without a symbol
   5032       1.1     skrll 		 relative to the start of the ELF image.  */
   5033       1.1     skrll 	      rel->r_addend += (relocation
   5034       1.1     skrll 				- ea->vma
   5035       1.1     skrll 				+ elf_section_data (ea)->this_hdr.sh_offset);
   5036       1.1     skrll 	      rel->r_info = ELF32_R_INFO (0, r_type);
   5037       1.1     skrll 	    }
   5038   1.1.1.9  christos 	  emit_these_relocs = true;
   5039       1.1     skrll 	  continue;
   5040       1.1     skrll 	}
   5041   1.1.1.2  christos       else if (is_ea_sym)
   5042   1.1.1.9  christos 	unresolved_reloc = true;
   5043       1.1     skrll 
   5044   1.1.1.3  christos       if (unresolved_reloc
   5045   1.1.1.3  christos 	  && _bfd_elf_section_offset (output_bfd, info, input_section,
   5046   1.1.1.3  christos 				      rel->r_offset) != (bfd_vma) -1)
   5047       1.1     skrll 	{
   5048   1.1.1.6  christos 	  _bfd_error_handler
   5049   1.1.1.6  christos 	    /* xgettext:c-format */
   5050   1.1.1.7  christos 	    (_("%pB(%s+%#" PRIx64 "): "
   5051   1.1.1.7  christos 	       "unresolvable %s relocation against symbol `%s'"),
   5052       1.1     skrll 	     input_bfd,
   5053   1.1.1.8  christos 	     bfd_section_name (input_section),
   5054   1.1.1.7  christos 	     (uint64_t) rel->r_offset,
   5055       1.1     skrll 	     howto->name,
   5056       1.1     skrll 	     sym_name);
   5057   1.1.1.9  christos 	  ret = false;
   5058       1.1     skrll 	}
   5059       1.1     skrll 
   5060       1.1     skrll       r = _bfd_final_link_relocate (howto,
   5061       1.1     skrll 				    input_bfd,
   5062       1.1     skrll 				    input_section,
   5063       1.1     skrll 				    contents,
   5064       1.1     skrll 				    rel->r_offset, relocation, addend);
   5065       1.1     skrll 
   5066       1.1     skrll       if (r != bfd_reloc_ok)
   5067       1.1     skrll 	{
   5068       1.1     skrll 	  const char *msg = (const char *) 0;
   5069       1.1     skrll 
   5070       1.1     skrll 	  switch (r)
   5071       1.1     skrll 	    {
   5072       1.1     skrll 	    case bfd_reloc_overflow:
   5073   1.1.1.5  christos 	      (*info->callbacks->reloc_overflow)
   5074   1.1.1.5  christos 		(info, (h ? &h->root : NULL), sym_name, howto->name,
   5075   1.1.1.5  christos 		 (bfd_vma) 0, input_bfd, input_section, rel->r_offset);
   5076       1.1     skrll 	      break;
   5077       1.1     skrll 
   5078       1.1     skrll 	    case bfd_reloc_undefined:
   5079   1.1.1.5  christos 	      (*info->callbacks->undefined_symbol)
   5080   1.1.1.9  christos 		(info, sym_name, input_bfd, input_section, rel->r_offset, true);
   5081       1.1     skrll 	      break;
   5082       1.1     skrll 
   5083       1.1     skrll 	    case bfd_reloc_outofrange:
   5084       1.1     skrll 	      msg = _("internal error: out of range error");
   5085       1.1     skrll 	      goto common_error;
   5086       1.1     skrll 
   5087       1.1     skrll 	    case bfd_reloc_notsupported:
   5088       1.1     skrll 	      msg = _("internal error: unsupported relocation error");
   5089       1.1     skrll 	      goto common_error;
   5090       1.1     skrll 
   5091       1.1     skrll 	    case bfd_reloc_dangerous:
   5092       1.1     skrll 	      msg = _("internal error: dangerous error");
   5093       1.1     skrll 	      goto common_error;
   5094       1.1     skrll 
   5095       1.1     skrll 	    default:
   5096       1.1     skrll 	      msg = _("internal error: unknown error");
   5097       1.1     skrll 	      /* fall through */
   5098       1.1     skrll 
   5099       1.1     skrll 	    common_error:
   5100   1.1.1.9  christos 	      ret = false;
   5101   1.1.1.5  christos 	      (*info->callbacks->warning) (info, msg, sym_name, input_bfd,
   5102   1.1.1.5  christos 					   input_section, rel->r_offset);
   5103       1.1     skrll 	      break;
   5104       1.1     skrll 	    }
   5105       1.1     skrll 	}
   5106       1.1     skrll     }
   5107       1.1     skrll 
   5108       1.1     skrll   if (ret
   5109       1.1     skrll       && emit_these_relocs
   5110       1.1     skrll       && !info->emitrelocations)
   5111       1.1     skrll     {
   5112       1.1     skrll       Elf_Internal_Rela *wrel;
   5113       1.1     skrll       Elf_Internal_Shdr *rel_hdr;
   5114       1.1     skrll 
   5115       1.1     skrll       wrel = rel = relocs;
   5116       1.1     skrll       relend = relocs + input_section->reloc_count;
   5117       1.1     skrll       for (; rel < relend; rel++)
   5118       1.1     skrll 	{
   5119       1.1     skrll 	  int r_type;
   5120       1.1     skrll 
   5121       1.1     skrll 	  r_type = ELF32_R_TYPE (rel->r_info);
   5122       1.1     skrll 	  if (r_type == R_SPU_PPU32 || r_type == R_SPU_PPU64)
   5123       1.1     skrll 	    *wrel++ = *rel;
   5124       1.1     skrll 	}
   5125       1.1     skrll       input_section->reloc_count = wrel - relocs;
   5126       1.1     skrll       /* Backflips for _bfd_elf_link_output_relocs.  */
   5127   1.1.1.2  christos       rel_hdr = _bfd_elf_single_rel_hdr (input_section);
   5128       1.1     skrll       rel_hdr->sh_size = input_section->reloc_count * rel_hdr->sh_entsize;
   5129       1.1     skrll       ret = 2;
   5130       1.1     skrll     }
   5131       1.1     skrll 
   5132       1.1     skrll   return ret;
   5133       1.1     skrll }
   5134       1.1     skrll 
   5135   1.1.1.9  christos static bool
   5136   1.1.1.2  christos spu_elf_finish_dynamic_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
   5137   1.1.1.2  christos 				 struct bfd_link_info *info ATTRIBUTE_UNUSED)
   5138   1.1.1.2  christos {
   5139   1.1.1.9  christos   return true;
   5140   1.1.1.2  christos }
   5141   1.1.1.2  christos 
   5142       1.1     skrll /* Adjust _SPUEAR_ syms to point at their overlay stubs.  */
   5143       1.1     skrll 
   5144   1.1.1.2  christos static int
   5145       1.1     skrll spu_elf_output_symbol_hook (struct bfd_link_info *info,
   5146       1.1     skrll 			    const char *sym_name ATTRIBUTE_UNUSED,
   5147       1.1     skrll 			    Elf_Internal_Sym *sym,
   5148       1.1     skrll 			    asection *sym_sec ATTRIBUTE_UNUSED,
   5149       1.1     skrll 			    struct elf_link_hash_entry *h)
   5150       1.1     skrll {
   5151       1.1     skrll   struct spu_link_hash_table *htab = spu_hash_table (info);
   5152       1.1     skrll 
   5153   1.1.1.4  christos   if (!bfd_link_relocatable (info)
   5154       1.1     skrll       && htab->stub_sec != NULL
   5155       1.1     skrll       && h != NULL
   5156       1.1     skrll       && (h->root.type == bfd_link_hash_defined
   5157       1.1     skrll 	  || h->root.type == bfd_link_hash_defweak)
   5158       1.1     skrll       && h->def_regular
   5159   1.1.1.9  christos       && startswith (h->root.root.string, "_SPUEAR_"))
   5160       1.1     skrll     {
   5161       1.1     skrll       struct got_entry *g;
   5162       1.1     skrll 
   5163       1.1     skrll       for (g = h->got.glist; g != NULL; g = g->next)
   5164   1.1.1.2  christos 	if (htab->params->ovly_flavour == ovly_soft_icache
   5165   1.1.1.2  christos 	    ? g->br_addr == g->stub_addr
   5166   1.1.1.2  christos 	    : g->addend == 0 && g->ovl == 0)
   5167       1.1     skrll 	  {
   5168       1.1     skrll 	    sym->st_shndx = (_bfd_elf_section_from_bfd_section
   5169       1.1     skrll 			     (htab->stub_sec[0]->output_section->owner,
   5170       1.1     skrll 			      htab->stub_sec[0]->output_section));
   5171       1.1     skrll 	    sym->st_value = g->stub_addr;
   5172       1.1     skrll 	    break;
   5173       1.1     skrll 	  }
   5174       1.1     skrll     }
   5175       1.1     skrll 
   5176   1.1.1.2  christos   return 1;
   5177       1.1     skrll }
   5178       1.1     skrll 
   5179       1.1     skrll static int spu_plugin = 0;
   5180       1.1     skrll 
   5181       1.1     skrll void
   5182       1.1     skrll spu_elf_plugin (int val)
   5183       1.1     skrll {
   5184       1.1     skrll   spu_plugin = val;
   5185       1.1     skrll }
   5186       1.1     skrll 
   5187       1.1     skrll /* Set ELF header e_type for plugins.  */
   5188       1.1     skrll 
   5189   1.1.1.9  christos static bool
   5190   1.1.1.8  christos spu_elf_init_file_header (bfd *abfd, struct bfd_link_info *info)
   5191       1.1     skrll {
   5192   1.1.1.8  christos   if (!_bfd_elf_init_file_header (abfd, info))
   5193   1.1.1.9  christos     return false;
   5194   1.1.1.8  christos 
   5195       1.1     skrll   if (spu_plugin)
   5196       1.1     skrll     {
   5197       1.1     skrll       Elf_Internal_Ehdr *i_ehdrp = elf_elfheader (abfd);
   5198       1.1     skrll 
   5199       1.1     skrll       i_ehdrp->e_type = ET_DYN;
   5200       1.1     skrll     }
   5201   1.1.1.9  christos   return true;
   5202       1.1     skrll }
   5203       1.1     skrll 
   5204       1.1     skrll /* We may add an extra PT_LOAD segment for .toe.  We also need extra
   5205       1.1     skrll    segments for overlays.  */
   5206       1.1     skrll 
   5207       1.1     skrll static int
   5208       1.1     skrll spu_elf_additional_program_headers (bfd *abfd, struct bfd_link_info *info)
   5209       1.1     skrll {
   5210       1.1     skrll   int extra = 0;
   5211       1.1     skrll   asection *sec;
   5212       1.1     skrll 
   5213       1.1     skrll   if (info != NULL)
   5214       1.1     skrll     {
   5215       1.1     skrll       struct spu_link_hash_table *htab = spu_hash_table (info);
   5216       1.1     skrll       extra = htab->num_overlays;
   5217       1.1     skrll     }
   5218       1.1     skrll 
   5219       1.1     skrll   if (extra)
   5220       1.1     skrll     ++extra;
   5221       1.1     skrll 
   5222       1.1     skrll   sec = bfd_get_section_by_name (abfd, ".toe");
   5223       1.1     skrll   if (sec != NULL && (sec->flags & SEC_LOAD) != 0)
   5224       1.1     skrll     ++extra;
   5225       1.1     skrll 
   5226       1.1     skrll   return extra;
   5227       1.1     skrll }
   5228       1.1     skrll 
   5229       1.1     skrll /* Remove .toe section from other PT_LOAD segments and put it in
   5230       1.1     skrll    a segment of its own.  Put overlays in separate segments too.  */
   5231       1.1     skrll 
   5232   1.1.1.9  christos static bool
   5233       1.1     skrll spu_elf_modify_segment_map (bfd *abfd, struct bfd_link_info *info)
   5234       1.1     skrll {
   5235       1.1     skrll   asection *toe, *s;
   5236   1.1.1.2  christos   struct elf_segment_map *m, *m_overlay;
   5237   1.1.1.8  christos   struct elf_segment_map **p, **p_overlay, **first_load;
   5238       1.1     skrll   unsigned int i;
   5239       1.1     skrll 
   5240       1.1     skrll   if (info == NULL)
   5241   1.1.1.9  christos     return true;
   5242       1.1     skrll 
   5243       1.1     skrll   toe = bfd_get_section_by_name (abfd, ".toe");
   5244   1.1.1.4  christos   for (m = elf_seg_map (abfd); m != NULL; m = m->next)
   5245       1.1     skrll     if (m->p_type == PT_LOAD && m->count > 1)
   5246       1.1     skrll       for (i = 0; i < m->count; i++)
   5247       1.1     skrll 	if ((s = m->sections[i]) == toe
   5248       1.1     skrll 	    || spu_elf_section_data (s)->u.o.ovl_index != 0)
   5249       1.1     skrll 	  {
   5250       1.1     skrll 	    struct elf_segment_map *m2;
   5251       1.1     skrll 	    bfd_vma amt;
   5252       1.1     skrll 
   5253       1.1     skrll 	    if (i + 1 < m->count)
   5254       1.1     skrll 	      {
   5255       1.1     skrll 		amt = sizeof (struct elf_segment_map);
   5256       1.1     skrll 		amt += (m->count - (i + 2)) * sizeof (m->sections[0]);
   5257       1.1     skrll 		m2 = bfd_zalloc (abfd, amt);
   5258       1.1     skrll 		if (m2 == NULL)
   5259   1.1.1.9  christos 		  return false;
   5260       1.1     skrll 		m2->count = m->count - (i + 1);
   5261       1.1     skrll 		memcpy (m2->sections, m->sections + i + 1,
   5262       1.1     skrll 			m2->count * sizeof (m->sections[0]));
   5263       1.1     skrll 		m2->p_type = PT_LOAD;
   5264       1.1     skrll 		m2->next = m->next;
   5265       1.1     skrll 		m->next = m2;
   5266       1.1     skrll 	      }
   5267       1.1     skrll 	    m->count = 1;
   5268       1.1     skrll 	    if (i != 0)
   5269       1.1     skrll 	      {
   5270       1.1     skrll 		m->count = i;
   5271       1.1     skrll 		amt = sizeof (struct elf_segment_map);
   5272       1.1     skrll 		m2 = bfd_zalloc (abfd, amt);
   5273       1.1     skrll 		if (m2 == NULL)
   5274   1.1.1.9  christos 		  return false;
   5275       1.1     skrll 		m2->p_type = PT_LOAD;
   5276       1.1     skrll 		m2->count = 1;
   5277       1.1     skrll 		m2->sections[0] = s;
   5278       1.1     skrll 		m2->next = m->next;
   5279       1.1     skrll 		m->next = m2;
   5280       1.1     skrll 	      }
   5281       1.1     skrll 	    break;
   5282       1.1     skrll 	  }
   5283       1.1     skrll 
   5284   1.1.1.2  christos 
   5285   1.1.1.2  christos   /* Some SPU ELF loaders ignore the PF_OVERLAY flag and just load all
   5286   1.1.1.2  christos      PT_LOAD segments.  This can cause the .ovl.init section to be
   5287   1.1.1.2  christos      overwritten with the contents of some overlay segment.  To work
   5288   1.1.1.2  christos      around this issue, we ensure that all PF_OVERLAY segments are
   5289   1.1.1.2  christos      sorted first amongst the program headers; this ensures that even
   5290   1.1.1.2  christos      with a broken loader, the .ovl.init section (which is not marked
   5291   1.1.1.2  christos      as PF_OVERLAY) will be placed into SPU local store on startup.  */
   5292   1.1.1.2  christos 
   5293   1.1.1.2  christos   /* Move all overlay segments onto a separate list.  */
   5294   1.1.1.4  christos   p = &elf_seg_map (abfd);
   5295   1.1.1.2  christos   p_overlay = &m_overlay;
   5296   1.1.1.8  christos   m_overlay = NULL;
   5297   1.1.1.8  christos   first_load = NULL;
   5298   1.1.1.2  christos   while (*p != NULL)
   5299   1.1.1.2  christos     {
   5300   1.1.1.8  christos       if ((*p)->p_type == PT_LOAD)
   5301   1.1.1.2  christos 	{
   5302   1.1.1.8  christos 	  if (!first_load)
   5303   1.1.1.8  christos 	    first_load = p;
   5304   1.1.1.8  christos 	  if ((*p)->count == 1
   5305   1.1.1.8  christos 	      && spu_elf_section_data ((*p)->sections[0])->u.o.ovl_index != 0)
   5306   1.1.1.8  christos 	    {
   5307   1.1.1.8  christos 	      m = *p;
   5308   1.1.1.8  christos 	      m->no_sort_lma = 1;
   5309   1.1.1.8  christos 	      *p = m->next;
   5310   1.1.1.8  christos 	      *p_overlay = m;
   5311   1.1.1.8  christos 	      p_overlay = &m->next;
   5312   1.1.1.8  christos 	      continue;
   5313   1.1.1.8  christos 	    }
   5314   1.1.1.2  christos 	}
   5315   1.1.1.2  christos       p = &((*p)->next);
   5316   1.1.1.2  christos     }
   5317   1.1.1.2  christos 
   5318   1.1.1.2  christos   /* Re-insert overlay segments at the head of the segment map.  */
   5319   1.1.1.8  christos   if (m_overlay != NULL)
   5320   1.1.1.8  christos     {
   5321   1.1.1.8  christos       p = first_load;
   5322   1.1.1.8  christos       if (*p != NULL && (*p)->p_type == PT_LOAD && (*p)->includes_filehdr)
   5323   1.1.1.8  christos 	/* It doesn't really make sense for someone to include the ELF
   5324   1.1.1.8  christos 	   file header into an spu image, but if they do the code that
   5325   1.1.1.8  christos 	   assigns p_offset needs to see the segment containing the
   5326   1.1.1.8  christos 	   header first.  */
   5327   1.1.1.8  christos 	p = &(*p)->next;
   5328   1.1.1.8  christos       *p_overlay = *p;
   5329   1.1.1.8  christos       *p = m_overlay;
   5330   1.1.1.8  christos     }
   5331   1.1.1.2  christos 
   5332   1.1.1.9  christos   return true;
   5333       1.1     skrll }
   5334       1.1     skrll 
   5335       1.1     skrll /* Tweak the section type of .note.spu_name.  */
   5336       1.1     skrll 
   5337   1.1.1.9  christos static bool
   5338       1.1     skrll spu_elf_fake_sections (bfd *obfd ATTRIBUTE_UNUSED,
   5339       1.1     skrll 		       Elf_Internal_Shdr *hdr,
   5340       1.1     skrll 		       asection *sec)
   5341       1.1     skrll {
   5342       1.1     skrll   if (strcmp (sec->name, SPU_PTNOTE_SPUNAME) == 0)
   5343       1.1     skrll     hdr->sh_type = SHT_NOTE;
   5344   1.1.1.9  christos   return true;
   5345       1.1     skrll }
   5346       1.1     skrll 
   5347       1.1     skrll /* Tweak phdrs before writing them out.  */
   5348       1.1     skrll 
   5349   1.1.1.9  christos static bool
   5350   1.1.1.8  christos spu_elf_modify_headers (bfd *abfd, struct bfd_link_info *info)
   5351       1.1     skrll {
   5352   1.1.1.8  christos   if (info != NULL)
   5353       1.1     skrll     {
   5354   1.1.1.8  christos       const struct elf_backend_data *bed;
   5355   1.1.1.8  christos       struct elf_obj_tdata *tdata;
   5356   1.1.1.8  christos       Elf_Internal_Phdr *phdr, *last;
   5357   1.1.1.8  christos       struct spu_link_hash_table *htab;
   5358   1.1.1.8  christos       unsigned int count;
   5359   1.1.1.8  christos       unsigned int i;
   5360   1.1.1.8  christos 
   5361   1.1.1.8  christos       bed = get_elf_backend_data (abfd);
   5362   1.1.1.8  christos       tdata = elf_tdata (abfd);
   5363   1.1.1.8  christos       phdr = tdata->phdr;
   5364   1.1.1.8  christos       count = elf_program_header_size (abfd) / bed->s->sizeof_phdr;
   5365   1.1.1.8  christos       htab = spu_hash_table (info);
   5366   1.1.1.8  christos       if (htab->num_overlays != 0)
   5367   1.1.1.8  christos 	{
   5368   1.1.1.8  christos 	  struct elf_segment_map *m;
   5369   1.1.1.8  christos 	  unsigned int o;
   5370   1.1.1.8  christos 
   5371   1.1.1.8  christos 	  for (i = 0, m = elf_seg_map (abfd); m; ++i, m = m->next)
   5372   1.1.1.8  christos 	    if (m->count != 0
   5373   1.1.1.8  christos 		&& ((o = spu_elf_section_data (m->sections[0])->u.o.ovl_index)
   5374   1.1.1.8  christos 		    != 0))
   5375       1.1     skrll 	      {
   5376   1.1.1.8  christos 		/* Mark this as an overlay header.  */
   5377   1.1.1.8  christos 		phdr[i].p_flags |= PF_OVERLAY;
   5378   1.1.1.8  christos 
   5379   1.1.1.8  christos 		if (htab->ovtab != NULL && htab->ovtab->size != 0
   5380   1.1.1.8  christos 		    && htab->params->ovly_flavour != ovly_soft_icache)
   5381   1.1.1.8  christos 		  {
   5382   1.1.1.8  christos 		    bfd_byte *p = htab->ovtab->contents;
   5383   1.1.1.8  christos 		    unsigned int off = o * 16 + 8;
   5384       1.1     skrll 
   5385   1.1.1.8  christos 		    /* Write file_off into _ovly_table.  */
   5386   1.1.1.8  christos 		    bfd_put_32 (htab->ovtab->owner, phdr[i].p_offset, p + off);
   5387   1.1.1.8  christos 		  }
   5388       1.1     skrll 	      }
   5389   1.1.1.8  christos 	  /* Soft-icache has its file offset put in .ovl.init.  */
   5390   1.1.1.8  christos 	  if (htab->init != NULL && htab->init->size != 0)
   5391   1.1.1.8  christos 	    {
   5392   1.1.1.8  christos 	      bfd_vma val
   5393   1.1.1.8  christos 		= elf_section_data (htab->ovl_sec[0])->this_hdr.sh_offset;
   5394   1.1.1.2  christos 
   5395   1.1.1.8  christos 	      bfd_put_32 (htab->init->owner, val, htab->init->contents + 4);
   5396   1.1.1.8  christos 	    }
   5397   1.1.1.2  christos 	}
   5398       1.1     skrll 
   5399   1.1.1.8  christos       /* Round up p_filesz and p_memsz of PT_LOAD segments to multiples
   5400   1.1.1.8  christos 	 of 16.  This should always be possible when using the standard
   5401   1.1.1.8  christos 	 linker scripts, but don't create overlapping segments if
   5402   1.1.1.8  christos 	 someone is playing games with linker scripts.  */
   5403   1.1.1.8  christos       last = NULL;
   5404   1.1.1.8  christos       for (i = count; i-- != 0; )
   5405   1.1.1.8  christos 	if (phdr[i].p_type == PT_LOAD)
   5406   1.1.1.8  christos 	  {
   5407   1.1.1.8  christos 	    unsigned adjust;
   5408       1.1     skrll 
   5409   1.1.1.8  christos 	    adjust = -phdr[i].p_filesz & 15;
   5410   1.1.1.8  christos 	    if (adjust != 0
   5411   1.1.1.8  christos 		&& last != NULL
   5412   1.1.1.8  christos 		&& (phdr[i].p_offset + phdr[i].p_filesz
   5413   1.1.1.8  christos 		    > last->p_offset - adjust))
   5414   1.1.1.8  christos 	      break;
   5415       1.1     skrll 
   5416   1.1.1.8  christos 	    adjust = -phdr[i].p_memsz & 15;
   5417   1.1.1.8  christos 	    if (adjust != 0
   5418   1.1.1.8  christos 		&& last != NULL
   5419   1.1.1.8  christos 		&& phdr[i].p_filesz != 0
   5420   1.1.1.8  christos 		&& phdr[i].p_vaddr + phdr[i].p_memsz > last->p_vaddr - adjust
   5421   1.1.1.8  christos 		&& phdr[i].p_vaddr + phdr[i].p_memsz <= last->p_vaddr)
   5422   1.1.1.8  christos 	      break;
   5423       1.1     skrll 
   5424   1.1.1.8  christos 	    if (phdr[i].p_filesz != 0)
   5425   1.1.1.8  christos 	      last = &phdr[i];
   5426   1.1.1.8  christos 	  }
   5427       1.1     skrll 
   5428   1.1.1.8  christos       if (i == (unsigned int) -1)
   5429   1.1.1.8  christos 	for (i = count; i-- != 0; )
   5430   1.1.1.8  christos 	  if (phdr[i].p_type == PT_LOAD)
   5431   1.1.1.8  christos 	    {
   5432   1.1.1.8  christos 	      unsigned adjust;
   5433       1.1     skrll 
   5434   1.1.1.8  christos 	      adjust = -phdr[i].p_filesz & 15;
   5435   1.1.1.8  christos 	      phdr[i].p_filesz += adjust;
   5436       1.1     skrll 
   5437   1.1.1.8  christos 	      adjust = -phdr[i].p_memsz & 15;
   5438   1.1.1.8  christos 	      phdr[i].p_memsz += adjust;
   5439   1.1.1.8  christos 	    }
   5440   1.1.1.8  christos     }
   5441       1.1     skrll 
   5442   1.1.1.8  christos   return _bfd_elf_modify_headers (abfd, info);
   5443       1.1     skrll }
   5444       1.1     skrll 
   5445   1.1.1.9  christos bool
   5446   1.1.1.8  christos spu_elf_size_sections (bfd *obfd ATTRIBUTE_UNUSED, struct bfd_link_info *info)
   5447   1.1.1.2  christos {
   5448   1.1.1.2  christos   struct spu_link_hash_table *htab = spu_hash_table (info);
   5449   1.1.1.2  christos   if (htab->params->emit_fixups)
   5450   1.1.1.2  christos     {
   5451   1.1.1.2  christos       asection *sfixup = htab->sfixup;
   5452   1.1.1.2  christos       int fixup_count = 0;
   5453   1.1.1.2  christos       bfd *ibfd;
   5454   1.1.1.2  christos       size_t size;
   5455   1.1.1.2  christos 
   5456   1.1.1.4  christos       for (ibfd = info->input_bfds; ibfd != NULL; ibfd = ibfd->link.next)
   5457   1.1.1.2  christos 	{
   5458   1.1.1.2  christos 	  asection *isec;
   5459   1.1.1.2  christos 
   5460   1.1.1.2  christos 	  if (bfd_get_flavour (ibfd) != bfd_target_elf_flavour)
   5461   1.1.1.2  christos 	    continue;
   5462   1.1.1.2  christos 
   5463   1.1.1.2  christos 	  /* Walk over each section attached to the input bfd.  */
   5464   1.1.1.2  christos 	  for (isec = ibfd->sections; isec != NULL; isec = isec->next)
   5465   1.1.1.2  christos 	    {
   5466   1.1.1.2  christos 	      Elf_Internal_Rela *internal_relocs, *irelaend, *irela;
   5467   1.1.1.2  christos 	      bfd_vma base_end;
   5468   1.1.1.2  christos 
   5469   1.1.1.2  christos 	      /* If there aren't any relocs, then there's nothing more
   5470   1.1.1.6  christos 		 to do.  */
   5471   1.1.1.2  christos 	      if ((isec->flags & SEC_ALLOC) == 0
   5472   1.1.1.2  christos 		  || (isec->flags & SEC_RELOC) == 0
   5473   1.1.1.2  christos 		  || isec->reloc_count == 0)
   5474   1.1.1.2  christos 		continue;
   5475   1.1.1.2  christos 
   5476   1.1.1.2  christos 	      /* Get the relocs.  */
   5477   1.1.1.2  christos 	      internal_relocs =
   5478   1.1.1.2  christos 		_bfd_elf_link_read_relocs (ibfd, isec, NULL, NULL,
   5479   1.1.1.2  christos 					   info->keep_memory);
   5480   1.1.1.2  christos 	      if (internal_relocs == NULL)
   5481   1.1.1.9  christos 		return false;
   5482   1.1.1.2  christos 
   5483   1.1.1.2  christos 	      /* 1 quadword can contain up to 4 R_SPU_ADDR32
   5484   1.1.1.6  christos 		 relocations.  They are stored in a single word by
   5485   1.1.1.6  christos 		 saving the upper 28 bits of the address and setting the
   5486   1.1.1.6  christos 		 lower 4 bits to a bit mask of the words that have the
   5487   1.1.1.6  christos 		 relocation.  BASE_END keeps track of the next quadword. */
   5488   1.1.1.2  christos 	      irela = internal_relocs;
   5489   1.1.1.2  christos 	      irelaend = irela + isec->reloc_count;
   5490   1.1.1.2  christos 	      base_end = 0;
   5491   1.1.1.2  christos 	      for (; irela < irelaend; irela++)
   5492   1.1.1.2  christos 		if (ELF32_R_TYPE (irela->r_info) == R_SPU_ADDR32
   5493   1.1.1.2  christos 		    && irela->r_offset >= base_end)
   5494   1.1.1.2  christos 		  {
   5495   1.1.1.2  christos 		    base_end = (irela->r_offset & ~(bfd_vma) 15) + 16;
   5496   1.1.1.2  christos 		    fixup_count++;
   5497   1.1.1.2  christos 		  }
   5498   1.1.1.2  christos 	    }
   5499   1.1.1.2  christos 	}
   5500   1.1.1.2  christos 
   5501   1.1.1.2  christos       /* We always have a NULL fixup as a sentinel */
   5502   1.1.1.2  christos       size = (fixup_count + 1) * FIXUP_RECORD_SIZE;
   5503   1.1.1.8  christos       if (!bfd_set_section_size (sfixup, size))
   5504   1.1.1.9  christos 	return false;
   5505   1.1.1.2  christos       sfixup->contents = (bfd_byte *) bfd_zalloc (info->input_bfds, size);
   5506   1.1.1.2  christos       if (sfixup->contents == NULL)
   5507   1.1.1.9  christos 	return false;
   5508  1.1.1.11  christos       sfixup->alloced = 1;
   5509   1.1.1.2  christos     }
   5510   1.1.1.9  christos   return true;
   5511   1.1.1.2  christos }
   5512   1.1.1.2  christos 
   5513   1.1.1.4  christos #define TARGET_BIG_SYM		spu_elf32_vec
   5514       1.1     skrll #define TARGET_BIG_NAME		"elf32-spu"
   5515       1.1     skrll #define ELF_ARCH		bfd_arch_spu
   5516   1.1.1.2  christos #define ELF_TARGET_ID		SPU_ELF_DATA
   5517       1.1     skrll #define ELF_MACHINE_CODE	EM_SPU
   5518       1.1     skrll /* This matches the alignment need for DMA.  */
   5519       1.1     skrll #define ELF_MAXPAGESIZE		0x80
   5520   1.1.1.6  christos #define elf_backend_rela_normal		1
   5521       1.1     skrll #define elf_backend_can_gc_sections	1
   5522       1.1     skrll 
   5523       1.1     skrll #define bfd_elf32_bfd_reloc_type_lookup		spu_elf_reloc_type_lookup
   5524   1.1.1.2  christos #define bfd_elf32_bfd_reloc_name_lookup		spu_elf_reloc_name_lookup
   5525       1.1     skrll #define elf_info_to_howto			spu_elf_info_to_howto
   5526       1.1     skrll #define elf_backend_count_relocs		spu_elf_count_relocs
   5527       1.1     skrll #define elf_backend_relocate_section		spu_elf_relocate_section
   5528   1.1.1.2  christos #define elf_backend_finish_dynamic_sections	spu_elf_finish_dynamic_sections
   5529       1.1     skrll #define elf_backend_symbol_processing		spu_elf_backend_symbol_processing
   5530       1.1     skrll #define elf_backend_link_output_symbol_hook	spu_elf_output_symbol_hook
   5531       1.1     skrll #define elf_backend_object_p			spu_elf_object_p
   5532       1.1     skrll #define bfd_elf32_new_section_hook		spu_elf_new_section_hook
   5533       1.1     skrll #define bfd_elf32_bfd_link_hash_table_create	spu_elf_link_hash_table_create
   5534       1.1     skrll 
   5535       1.1     skrll #define elf_backend_additional_program_headers	spu_elf_additional_program_headers
   5536       1.1     skrll #define elf_backend_modify_segment_map		spu_elf_modify_segment_map
   5537   1.1.1.8  christos #define elf_backend_modify_headers		spu_elf_modify_headers
   5538   1.1.1.8  christos #define elf_backend_init_file_header		spu_elf_init_file_header
   5539       1.1     skrll #define elf_backend_fake_sections		spu_elf_fake_sections
   5540       1.1     skrll #define elf_backend_special_sections		spu_elf_special_sections
   5541       1.1     skrll #define bfd_elf32_bfd_final_link		spu_elf_final_link
   5542       1.1     skrll 
   5543       1.1     skrll #include "elf32-target.h"
   5544