Home | History | Annotate | Line # | Download | only in bfd
elf32-arc.c revision 1.1.1.8
      1      1.1     skrll /* ARC-specific support for 32-bit ELF
      2  1.1.1.8  christos    Copyright (C) 1994-2024 Free Software Foundation, Inc.
      3  1.1.1.2  christos    Contributed by Cupertino Miranda (cmiranda (at) synopsys.com).
      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
     18      1.1     skrll    along with this program; if not, write to the Free Software
     19      1.1     skrll    Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
     20      1.1     skrll    MA 02110-1301, USA.  */
     21      1.1     skrll 
     22      1.1     skrll #include "sysdep.h"
     23      1.1     skrll #include "bfd.h"
     24      1.1     skrll #include "libbfd.h"
     25      1.1     skrll #include "elf-bfd.h"
     26      1.1     skrll #include "elf/arc.h"
     27      1.1     skrll #include "libiberty.h"
     28  1.1.1.2  christos #include "opcode/arc-func.h"
     29  1.1.1.3  christos #include "opcode/arc.h"
     30  1.1.1.3  christos #include "arc-plt.h"
     31  1.1.1.2  christos 
     32  1.1.1.4  christos #define FEATURE_LIST_NAME bfd_feature_list
     33  1.1.1.4  christos #define CONFLICT_LIST bfd_conflict_list
     34  1.1.1.4  christos #include "opcode/arc-attrs.h"
     35  1.1.1.4  christos 
     36  1.1.1.4  christos /* #define ARC_ENABLE_DEBUG 1  */
     37  1.1.1.4  christos #ifdef ARC_ENABLE_DEBUG
     38  1.1.1.4  christos static const char *
     39  1.1.1.3  christos name_for_global_symbol (struct elf_link_hash_entry *h)
     40  1.1.1.3  christos {
     41  1.1.1.3  christos   static char *local_str = "(local)";
     42  1.1.1.3  christos   if (h == NULL)
     43  1.1.1.3  christos     return local_str;
     44  1.1.1.4  christos   return h->root.root.string;
     45  1.1.1.3  christos }
     46  1.1.1.4  christos #define ARC_DEBUG(fmt, args...) fprintf (stderr, fmt, ##args)
     47  1.1.1.4  christos #else
     48  1.1.1.4  christos #define ARC_DEBUG(...)
     49  1.1.1.3  christos #endif
     50  1.1.1.2  christos 
     51  1.1.1.2  christos 
     52  1.1.1.3  christos #define ADD_RELA(BFD, SECTION, OFFSET, SYM_IDX, TYPE, ADDEND)		\
     53  1.1.1.3  christos   {									\
     54  1.1.1.3  christos     struct elf_link_hash_table *_htab = elf_hash_table (info);		\
     55  1.1.1.3  christos     Elf_Internal_Rela _rel;						\
     56  1.1.1.3  christos     bfd_byte * _loc;							\
     57  1.1.1.3  christos 									\
     58  1.1.1.7  christos     if (_htab->dynamic_sections_created)				\
     59  1.1.1.4  christos       {									\
     60  1.1.1.4  christos 	BFD_ASSERT (_htab->srel##SECTION &&_htab->srel##SECTION->contents); \
     61  1.1.1.4  christos 	_loc = _htab->srel##SECTION->contents				\
     62  1.1.1.4  christos 	  + ((_htab->srel##SECTION->reloc_count)			\
     63  1.1.1.4  christos 	     * sizeof (Elf32_External_Rela));				\
     64  1.1.1.4  christos 	_htab->srel##SECTION->reloc_count++;				\
     65  1.1.1.4  christos 	_rel.r_addend = ADDEND;						\
     66  1.1.1.4  christos 	_rel.r_offset = (_htab->s##SECTION)->output_section->vma	\
     67  1.1.1.4  christos 	  + (_htab->s##SECTION)->output_offset + OFFSET;		\
     68  1.1.1.4  christos 	BFD_ASSERT ((long) SYM_IDX != -1);				\
     69  1.1.1.4  christos 	_rel.r_info = ELF32_R_INFO (SYM_IDX, TYPE);			\
     70  1.1.1.4  christos 	bfd_elf32_swap_reloca_out (BFD, &_rel, _loc);			\
     71  1.1.1.4  christos       }									\
     72  1.1.1.3  christos   }
     73  1.1.1.2  christos 
     74  1.1.1.2  christos #define ARC_RELOC_HOWTO(TYPE, VALUE, SIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
     75  1.1.1.2  christos       case VALUE: \
     76  1.1.1.3  christos 	return "R_" #TYPE; \
     77  1.1.1.2  christos 	break;
     78  1.1.1.2  christos 
     79  1.1.1.2  christos static ATTRIBUTE_UNUSED const char *
     80  1.1.1.2  christos reloc_type_to_name (unsigned int type)
     81  1.1.1.2  christos {
     82  1.1.1.2  christos   switch (type)
     83  1.1.1.2  christos     {
     84  1.1.1.6  christos #include "elf/arc-reloc.def"
     85  1.1.1.2  christos 
     86  1.1.1.6  christos     default:
     87  1.1.1.6  christos       return "UNKNOWN";
     88  1.1.1.6  christos       break;
     89  1.1.1.2  christos     }
     90  1.1.1.2  christos }
     91  1.1.1.5  christos 
     92  1.1.1.2  christos #undef ARC_RELOC_HOWTO
     93      1.1     skrll 
     94      1.1     skrll /* Try to minimize the amount of space occupied by relocation tables
     95      1.1     skrll    on the ROM (not that the ROM won't be swamped by other ELF overhead).  */
     96      1.1     skrll 
     97  1.1.1.2  christos #define USE_REL 1
     98  1.1.1.2  christos 
     99  1.1.1.6  christos /* Similar with bfd_get_32 but taking into account the
    100  1.1.1.6  christos    middle-endianess of the ARC CPUs.  Only to be used in code
    101  1.1.1.6  christos    sections.  */
    102  1.1.1.6  christos 
    103  1.1.1.6  christos static bfd_vma
    104  1.1.1.6  christos bfd_get_32_me (bfd * abfd,const unsigned char * data)
    105  1.1.1.6  christos {
    106  1.1.1.6  christos   bfd_vma value = 0;
    107  1.1.1.6  christos 
    108  1.1.1.6  christos   if (bfd_big_endian (abfd))
    109  1.1.1.6  christos     value = bfd_get_32 (abfd, data);
    110  1.1.1.6  christos   else
    111  1.1.1.6  christos     {
    112  1.1.1.6  christos       value = ((bfd_get_8 (abfd, data) & 255) << 16);
    113  1.1.1.6  christos       value |= ((bfd_get_8 (abfd, data + 1) & 255) << 24);
    114  1.1.1.6  christos       value |= (bfd_get_8 (abfd, data + 2) & 255);
    115  1.1.1.6  christos       value |= ((bfd_get_8 (abfd, data + 3) & 255) << 8);
    116  1.1.1.6  christos     }
    117  1.1.1.6  christos 
    118  1.1.1.6  christos   return value;
    119  1.1.1.6  christos }
    120  1.1.1.6  christos 
    121  1.1.1.6  christos static void
    122  1.1.1.6  christos bfd_put_32_me (bfd *abfd, bfd_vma value,unsigned char *data)
    123  1.1.1.6  christos {
    124  1.1.1.6  christos   bfd_put_16 (abfd, (value & 0xffff0000) >> 16, data);
    125  1.1.1.6  christos   bfd_put_16 (abfd, value & 0xffff, data + 2);
    126  1.1.1.6  christos }
    127  1.1.1.6  christos 
    128  1.1.1.7  christos static ATTRIBUTE_UNUSED bool
    129  1.1.1.2  christos is_reloc_PC_relative (reloc_howto_type *howto)
    130  1.1.1.2  christos {
    131  1.1.1.7  christos   return strstr (howto->name, "PC") != NULL;
    132  1.1.1.2  christos }
    133  1.1.1.2  christos 
    134  1.1.1.7  christos static bool
    135  1.1.1.2  christos is_reloc_SDA_relative (reloc_howto_type *howto)
    136  1.1.1.2  christos {
    137  1.1.1.7  christos   return strstr (howto->name, "SDA") != NULL;
    138  1.1.1.2  christos }
    139  1.1.1.2  christos 
    140  1.1.1.7  christos static bool
    141  1.1.1.2  christos is_reloc_for_GOT (reloc_howto_type * howto)
    142  1.1.1.2  christos {
    143  1.1.1.3  christos   if (strstr (howto->name, "TLS") != NULL)
    144  1.1.1.7  christos     return false;
    145  1.1.1.7  christos   return strstr (howto->name, "GOT") != NULL;
    146  1.1.1.2  christos }
    147  1.1.1.2  christos 
    148  1.1.1.7  christos static bool
    149  1.1.1.2  christos is_reloc_for_PLT (reloc_howto_type * howto)
    150  1.1.1.2  christos {
    151  1.1.1.7  christos   return strstr (howto->name, "PLT") != NULL;
    152  1.1.1.2  christos }
    153  1.1.1.2  christos 
    154  1.1.1.7  christos static bool
    155  1.1.1.3  christos is_reloc_for_TLS (reloc_howto_type *howto)
    156  1.1.1.3  christos {
    157  1.1.1.7  christos   return strstr (howto->name, "TLS") != NULL;
    158  1.1.1.3  christos }
    159  1.1.1.3  christos 
    160  1.1.1.4  christos struct arc_relocation_data
    161  1.1.1.4  christos {
    162  1.1.1.7  christos   bfd_signed_vma reloc_offset;
    163  1.1.1.7  christos   bfd_signed_vma reloc_addend;
    164  1.1.1.7  christos   bfd_signed_vma got_offset_value;
    165  1.1.1.4  christos 
    166  1.1.1.7  christos   bfd_signed_vma sym_value;
    167  1.1.1.7  christos   asection *sym_section;
    168  1.1.1.4  christos 
    169  1.1.1.4  christos   reloc_howto_type *howto;
    170  1.1.1.4  christos 
    171  1.1.1.7  christos   asection *input_section;
    172  1.1.1.4  christos 
    173  1.1.1.7  christos   bfd_signed_vma sdata_begin_symbol_vma;
    174  1.1.1.7  christos   bool sdata_begin_symbol_vma_set;
    175  1.1.1.7  christos   bfd_signed_vma got_symbol_vma;
    176  1.1.1.4  christos 
    177  1.1.1.7  christos   bool should_relocate;
    178  1.1.1.4  christos 
    179  1.1.1.7  christos   const char *symbol_name;
    180  1.1.1.4  christos };
    181  1.1.1.4  christos 
    182  1.1.1.6  christos /* ARC ELF linker hash entry.  */
    183  1.1.1.6  christos struct elf_arc_link_hash_entry
    184  1.1.1.6  christos {
    185  1.1.1.6  christos   struct elf_link_hash_entry root;
    186  1.1.1.6  christos 
    187  1.1.1.6  christos   struct got_entry *got_ents;
    188  1.1.1.6  christos };
    189  1.1.1.6  christos 
    190  1.1.1.6  christos 
    191  1.1.1.4  christos /* Should be included at this location due to static declarations
    192  1.1.1.5  christos    defined before this point.  */
    193  1.1.1.4  christos #include "arc-got.h"
    194  1.1.1.4  christos 
    195  1.1.1.2  christos #define arc_bfd_get_8(A,B,C) bfd_get_8(A,B)
    196  1.1.1.2  christos #define arc_bfd_get_16(A,B,C) bfd_get_16(A,B)
    197  1.1.1.3  christos #define arc_bfd_get_32(A,B,C) bfd_get_32(A,B)
    198  1.1.1.2  christos #define arc_bfd_put_8(A,B,C,D) bfd_put_8(A,B,C)
    199  1.1.1.2  christos #define arc_bfd_put_16(A,B,C,D) bfd_put_16(A,B,C)
    200  1.1.1.3  christos #define arc_bfd_put_32(A,B,C,D) bfd_put_32(A,B,C)
    201  1.1.1.2  christos 
    202      1.1     skrll 
    203      1.1     skrll static bfd_reloc_status_type
    204  1.1.1.2  christos arc_elf_reloc (bfd *abfd ATTRIBUTE_UNUSED,
    205  1.1.1.2  christos 	       arelent *reloc_entry,
    206  1.1.1.2  christos 	       asymbol *symbol_in,
    207  1.1.1.2  christos 	       void *data ATTRIBUTE_UNUSED,
    208  1.1.1.2  christos 	       asection *input_section,
    209  1.1.1.2  christos 	       bfd *output_bfd,
    210  1.1.1.2  christos 	       char ** error_message ATTRIBUTE_UNUSED)
    211  1.1.1.2  christos {
    212  1.1.1.2  christos   if (output_bfd != NULL)
    213  1.1.1.2  christos     {
    214  1.1.1.2  christos       reloc_entry->address += input_section->output_offset;
    215  1.1.1.2  christos 
    216  1.1.1.2  christos       /* In case of relocateable link and if the reloc is against a
    217  1.1.1.2  christos 	 section symbol, the addend needs to be adjusted according to
    218  1.1.1.2  christos 	 where the section symbol winds up in the output section.  */
    219  1.1.1.2  christos       if ((symbol_in->flags & BSF_SECTION_SYM) && symbol_in->section)
    220  1.1.1.2  christos 	reloc_entry->addend += symbol_in->section->output_offset;
    221  1.1.1.2  christos 
    222  1.1.1.2  christos       return bfd_reloc_ok;
    223  1.1.1.2  christos     }
    224  1.1.1.2  christos 
    225  1.1.1.2  christos   return bfd_reloc_continue;
    226  1.1.1.2  christos }
    227  1.1.1.2  christos 
    228  1.1.1.2  christos 
    229  1.1.1.2  christos #define ARC_RELOC_HOWTO(TYPE, VALUE, SIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
    230  1.1.1.2  christos   TYPE = VALUE,
    231  1.1.1.5  christos 
    232  1.1.1.2  christos enum howto_list
    233  1.1.1.2  christos {
    234  1.1.1.2  christos #include "elf/arc-reloc.def"
    235  1.1.1.2  christos   HOWTO_LIST_LAST
    236      1.1     skrll };
    237  1.1.1.5  christos 
    238  1.1.1.2  christos #undef ARC_RELOC_HOWTO
    239  1.1.1.2  christos 
    240  1.1.1.2  christos #define ARC_RELOC_HOWTO(TYPE, VALUE, RSIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
    241  1.1.1.7  christos   [TYPE] = HOWTO (R_##TYPE, 0, RSIZE, BITSIZE, false, 0,		\
    242  1.1.1.4  christos 		  complain_overflow_##OVERFLOW, arc_elf_reloc,		\
    243  1.1.1.7  christos 		  "R_" #TYPE, false, 0, 0, false),
    244  1.1.1.2  christos 
    245  1.1.1.2  christos static struct reloc_howto_struct elf_arc_howto_table[] =
    246  1.1.1.2  christos {
    247  1.1.1.2  christos #include "elf/arc-reloc.def"
    248  1.1.1.3  christos /* Example of what is generated by the preprocessor.  Currently kept as an
    249  1.1.1.3  christos    example.
    250  1.1.1.2  christos  HOWTO (R_ARC_NONE, // Type.
    251  1.1.1.2  christos     0, // Rightshift.
    252  1.1.1.7  christos     4, // Size.
    253  1.1.1.2  christos     32, // Bitsize.
    254  1.1.1.7  christos     false, // PC_relative.
    255  1.1.1.2  christos     0, // Bitpos.
    256  1.1.1.2  christos     complain_overflow_bitfield, // Complain_on_overflow.
    257  1.1.1.2  christos     bfd_elf_generic_reloc, // Special_function.
    258  1.1.1.2  christos     "R_ARC_NONE", // Name.
    259  1.1.1.7  christos     true, // Partial_inplace.
    260  1.1.1.2  christos     0, // Src_mask.
    261  1.1.1.2  christos     0, // Dst_mask.
    262  1.1.1.7  christos     false), // PCrel_offset.
    263  1.1.1.2  christos */
    264  1.1.1.2  christos };
    265  1.1.1.2  christos #undef ARC_RELOC_HOWTO
    266  1.1.1.2  christos 
    267  1.1.1.5  christos static void
    268  1.1.1.5  christos arc_elf_howto_init (void)
    269  1.1.1.2  christos {
    270  1.1.1.2  christos #define ARC_RELOC_HOWTO(TYPE, VALUE, SIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
    271  1.1.1.5  christos   elf_arc_howto_table[TYPE].pc_relative =				\
    272  1.1.1.3  christos     (strstr (#FORMULA, " P ") != NULL || strstr (#FORMULA, " PDATA ") != NULL); \
    273  1.1.1.5  christos   elf_arc_howto_table[TYPE].dst_mask = RELOC_FUNCTION(0, ~0);		\
    274  1.1.1.5  christos   /* Only 32 bit data relocations should be marked as ME.  */		\
    275  1.1.1.5  christos   if (strstr (#FORMULA, " ME ") != NULL)				\
    276  1.1.1.5  christos     {									\
    277  1.1.1.7  christos       BFD_ASSERT (SIZE == 4);						\
    278  1.1.1.3  christos     }
    279  1.1.1.3  christos 
    280  1.1.1.3  christos #include "elf/arc-reloc.def"
    281  1.1.1.2  christos 
    282  1.1.1.2  christos }
    283  1.1.1.2  christos #undef ARC_RELOC_HOWTO
    284  1.1.1.2  christos 
    285  1.1.1.2  christos 
    286  1.1.1.2  christos #define ARC_RELOC_HOWTO(TYPE, VALUE, SIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
    287  1.1.1.2  christos   [TYPE] = VALUE,
    288  1.1.1.5  christos 
    289  1.1.1.2  christos const int howto_table_lookup[] =
    290  1.1.1.2  christos {
    291  1.1.1.3  christos #include "elf/arc-reloc.def"
    292  1.1.1.2  christos };
    293  1.1.1.5  christos 
    294  1.1.1.2  christos #undef ARC_RELOC_HOWTO
    295  1.1.1.2  christos 
    296  1.1.1.3  christos static reloc_howto_type *
    297  1.1.1.3  christos arc_elf_howto (unsigned int r_type)
    298  1.1.1.3  christos {
    299  1.1.1.3  christos   if (elf_arc_howto_table[R_ARC_32].dst_mask == 0)
    300  1.1.1.3  christos     arc_elf_howto_init ();
    301  1.1.1.3  christos   return &elf_arc_howto_table[r_type];
    302  1.1.1.3  christos }
    303      1.1     skrll 
    304      1.1     skrll /* Map BFD reloc types to ARC ELF reloc types.  */
    305      1.1     skrll 
    306      1.1     skrll struct arc_reloc_map
    307      1.1     skrll {
    308  1.1.1.3  christos   bfd_reloc_code_real_type  bfd_reloc_val;
    309  1.1.1.4  christos   unsigned char		    elf_reloc_val;
    310      1.1     skrll };
    311      1.1     skrll 
    312  1.1.1.4  christos /* ARC ELF linker hash table.  */
    313  1.1.1.4  christos struct elf_arc_link_hash_table
    314  1.1.1.4  christos {
    315  1.1.1.4  christos   struct elf_link_hash_table elf;
    316  1.1.1.4  christos };
    317  1.1.1.4  christos 
    318  1.1.1.4  christos static struct bfd_hash_entry *
    319  1.1.1.4  christos elf_arc_link_hash_newfunc (struct bfd_hash_entry *entry,
    320  1.1.1.4  christos 			   struct bfd_hash_table *table,
    321  1.1.1.4  christos 			   const char *string)
    322  1.1.1.4  christos {
    323  1.1.1.6  christos   struct elf_arc_link_hash_entry * ret =
    324  1.1.1.6  christos     (struct elf_arc_link_hash_entry *) entry;
    325  1.1.1.6  christos 
    326  1.1.1.4  christos   /* Allocate the structure if it has not already been allocated by a
    327  1.1.1.4  christos      subclass.  */
    328  1.1.1.6  christos   if (ret == NULL)
    329  1.1.1.6  christos     ret = (struct elf_arc_link_hash_entry *)
    330  1.1.1.6  christos 	bfd_hash_allocate (table, sizeof (struct elf_arc_link_hash_entry));
    331  1.1.1.6  christos   if (ret == NULL)
    332  1.1.1.6  christos     return (struct bfd_hash_entry *) ret;
    333  1.1.1.4  christos 
    334  1.1.1.4  christos   /* Call the allocation method of the superclass.  */
    335  1.1.1.6  christos   ret = ((struct elf_arc_link_hash_entry *)
    336  1.1.1.6  christos 	 _bfd_elf_link_hash_newfunc ((struct bfd_hash_entry *) ret,
    337  1.1.1.6  christos 				     table, string));
    338  1.1.1.6  christos   if (ret != NULL)
    339  1.1.1.4  christos     {
    340  1.1.1.6  christos       ret->got_ents = NULL;
    341  1.1.1.4  christos     }
    342  1.1.1.4  christos 
    343  1.1.1.6  christos   return (struct bfd_hash_entry *) ret;
    344  1.1.1.4  christos }
    345  1.1.1.4  christos 
    346  1.1.1.4  christos /* Destroy an ARC ELF linker hash table.  */
    347  1.1.1.4  christos static void
    348  1.1.1.4  christos elf_arc_link_hash_table_free (bfd *obfd)
    349  1.1.1.4  christos {
    350  1.1.1.4  christos   _bfd_elf_link_hash_table_free (obfd);
    351  1.1.1.4  christos }
    352  1.1.1.4  christos 
    353  1.1.1.4  christos /* Create an ARC ELF linker hash table.  */
    354  1.1.1.4  christos 
    355  1.1.1.4  christos static struct bfd_link_hash_table *
    356  1.1.1.4  christos arc_elf_link_hash_table_create (bfd *abfd)
    357  1.1.1.4  christos {
    358  1.1.1.4  christos   struct elf_arc_link_hash_table *ret;
    359  1.1.1.4  christos 
    360  1.1.1.4  christos   ret = (struct elf_arc_link_hash_table *) bfd_zmalloc (sizeof (*ret));
    361  1.1.1.4  christos   if (ret == NULL)
    362  1.1.1.4  christos     return NULL;
    363  1.1.1.4  christos 
    364  1.1.1.4  christos   if (!_bfd_elf_link_hash_table_init (&ret->elf, abfd,
    365  1.1.1.4  christos 				      elf_arc_link_hash_newfunc,
    366  1.1.1.4  christos 				      sizeof (struct elf_arc_link_hash_entry),
    367  1.1.1.4  christos 				      ARC_ELF_DATA))
    368  1.1.1.4  christos     {
    369  1.1.1.4  christos       free (ret);
    370  1.1.1.4  christos       return NULL;
    371  1.1.1.4  christos     }
    372  1.1.1.4  christos 
    373  1.1.1.4  christos   ret->elf.root.hash_table_free = elf_arc_link_hash_table_free;
    374  1.1.1.4  christos 
    375  1.1.1.4  christos   return &ret->elf.root;
    376  1.1.1.4  christos }
    377  1.1.1.4  christos 
    378  1.1.1.2  christos #define ARC_RELOC_HOWTO(TYPE, VALUE, SIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
    379  1.1.1.2  christos   { BFD_RELOC_##TYPE, R_##TYPE },
    380  1.1.1.5  christos 
    381      1.1     skrll static const struct arc_reloc_map arc_reloc_map[] =
    382      1.1     skrll {
    383  1.1.1.3  christos #include "elf/arc-reloc.def"
    384  1.1.1.3  christos 
    385  1.1.1.2  christos   {BFD_RELOC_NONE,  R_ARC_NONE},
    386  1.1.1.2  christos   {BFD_RELOC_8,  R_ARC_8},
    387  1.1.1.2  christos   {BFD_RELOC_16, R_ARC_16},
    388  1.1.1.2  christos   {BFD_RELOC_24, R_ARC_24},
    389  1.1.1.2  christos   {BFD_RELOC_32, R_ARC_32},
    390      1.1     skrll };
    391  1.1.1.5  christos 
    392  1.1.1.2  christos #undef ARC_RELOC_HOWTO
    393      1.1     skrll 
    394  1.1.1.7  christos typedef ATTRIBUTE_UNUSED unsigned (*replace_func) (unsigned, int ATTRIBUTE_UNUSED);
    395  1.1.1.3  christos 
    396  1.1.1.3  christos #define ARC_RELOC_HOWTO(TYPE, VALUE, SIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
    397  1.1.1.3  christos   case TYPE: \
    398  1.1.1.7  christos     func = RELOC_FUNCTION; \
    399  1.1.1.3  christos     break;
    400  1.1.1.5  christos 
    401  1.1.1.3  christos static replace_func
    402  1.1.1.3  christos get_replace_function (bfd *abfd, unsigned int r_type)
    403      1.1     skrll {
    404  1.1.1.7  christos   replace_func func = NULL;
    405  1.1.1.2  christos 
    406  1.1.1.3  christos   switch (r_type)
    407  1.1.1.2  christos     {
    408  1.1.1.3  christos       #include "elf/arc-reloc.def"
    409  1.1.1.2  christos     }
    410      1.1     skrll 
    411  1.1.1.3  christos   if (func == replace_bits24 && bfd_big_endian (abfd))
    412  1.1.1.5  christos     func = replace_bits24_be;
    413  1.1.1.3  christos 
    414  1.1.1.7  christos   return func;
    415  1.1.1.3  christos }
    416  1.1.1.3  christos #undef ARC_RELOC_HOWTO
    417  1.1.1.3  christos 
    418  1.1.1.3  christos static reloc_howto_type *
    419  1.1.1.3  christos arc_elf32_bfd_reloc_type_lookup (bfd * abfd ATTRIBUTE_UNUSED,
    420  1.1.1.3  christos 				 bfd_reloc_code_real_type code)
    421  1.1.1.3  christos {
    422  1.1.1.3  christos   unsigned int i;
    423  1.1.1.3  christos 
    424      1.1     skrll   for (i = ARRAY_SIZE (arc_reloc_map); i--;)
    425  1.1.1.2  christos     {
    426  1.1.1.2  christos       if (arc_reloc_map[i].bfd_reloc_val == code)
    427  1.1.1.3  christos 	return arc_elf_howto (arc_reloc_map[i].elf_reloc_val);
    428  1.1.1.2  christos     }
    429      1.1     skrll 
    430      1.1     skrll   return NULL;
    431      1.1     skrll }
    432      1.1     skrll 
    433  1.1.1.3  christos /* Function to set the ELF flag bits.  */
    434  1.1.1.7  christos static bool
    435  1.1.1.3  christos arc_elf_set_private_flags (bfd *abfd, flagword flags)
    436  1.1.1.3  christos {
    437  1.1.1.3  christos   elf_elfheader (abfd)->e_flags = flags;
    438  1.1.1.7  christos   elf_flags_init (abfd) = true;
    439  1.1.1.7  christos   return true;
    440  1.1.1.3  christos }
    441  1.1.1.3  christos 
    442  1.1.1.3  christos /* Print private flags.  */
    443  1.1.1.7  christos static bool
    444  1.1.1.3  christos arc_elf_print_private_bfd_data (bfd *abfd, void * ptr)
    445  1.1.1.3  christos {
    446  1.1.1.3  christos   FILE *file = (FILE *) ptr;
    447  1.1.1.3  christos   flagword flags;
    448  1.1.1.3  christos 
    449  1.1.1.3  christos   BFD_ASSERT (abfd != NULL && ptr != NULL);
    450  1.1.1.3  christos 
    451  1.1.1.3  christos   /* Print normal ELF private data.  */
    452  1.1.1.3  christos   _bfd_elf_print_private_bfd_data (abfd, ptr);
    453  1.1.1.3  christos 
    454  1.1.1.3  christos   flags = elf_elfheader (abfd)->e_flags;
    455  1.1.1.3  christos   fprintf (file, _("private flags = 0x%lx:"), (unsigned long) flags);
    456  1.1.1.3  christos 
    457  1.1.1.3  christos   switch (flags & EF_ARC_MACH_MSK)
    458  1.1.1.3  christos     {
    459  1.1.1.3  christos     case EF_ARC_CPU_ARCV2HS : fprintf (file, " -mcpu=ARCv2HS");    break;
    460  1.1.1.3  christos     case EF_ARC_CPU_ARCV2EM : fprintf (file, " -mcpu=ARCv2EM");    break;
    461  1.1.1.3  christos     case E_ARC_MACH_ARC600  : fprintf (file, " -mcpu=ARC600");     break;
    462  1.1.1.3  christos     case E_ARC_MACH_ARC601  : fprintf (file, " -mcpu=ARC601");     break;
    463  1.1.1.3  christos     case E_ARC_MACH_ARC700  : fprintf (file, " -mcpu=ARC700");     break;
    464  1.1.1.3  christos     default:
    465  1.1.1.3  christos       fprintf (file, "-mcpu=unknown");
    466  1.1.1.3  christos       break;
    467  1.1.1.3  christos     }
    468  1.1.1.3  christos 
    469  1.1.1.3  christos   switch (flags & EF_ARC_OSABI_MSK)
    470  1.1.1.3  christos     {
    471  1.1.1.3  christos     case E_ARC_OSABI_ORIG : fprintf (file, " (ABI:legacy)"); break;
    472  1.1.1.3  christos     case E_ARC_OSABI_V2   : fprintf (file, " (ABI:v2)");     break;
    473  1.1.1.3  christos     case E_ARC_OSABI_V3   : fprintf (file, " (ABI:v3)");     break;
    474  1.1.1.4  christos     case E_ARC_OSABI_V4   : fprintf (file, " (ABI:v4)");     break;
    475  1.1.1.3  christos     default:
    476  1.1.1.4  christos       fprintf (file, " (ABI:unknown)");
    477  1.1.1.3  christos       break;
    478  1.1.1.3  christos     }
    479  1.1.1.3  christos 
    480  1.1.1.3  christos   fputc ('\n', file);
    481  1.1.1.7  christos   return true;
    482  1.1.1.3  christos }
    483  1.1.1.3  christos 
    484  1.1.1.3  christos /* Copy backend specific data from one object module to another.  */
    485  1.1.1.3  christos 
    486  1.1.1.7  christos static bool
    487  1.1.1.3  christos arc_elf_copy_private_bfd_data (bfd *ibfd, bfd *obfd)
    488  1.1.1.3  christos {
    489  1.1.1.3  christos   if (bfd_get_flavour (ibfd) != bfd_target_elf_flavour
    490  1.1.1.3  christos       || bfd_get_flavour (obfd) != bfd_target_elf_flavour)
    491  1.1.1.7  christos     return true;
    492  1.1.1.3  christos 
    493  1.1.1.3  christos   BFD_ASSERT (!elf_flags_init (obfd)
    494  1.1.1.3  christos 	      || elf_elfheader (obfd)->e_flags == elf_elfheader (ibfd)->e_flags);
    495  1.1.1.3  christos 
    496  1.1.1.3  christos   elf_elfheader (obfd)->e_flags = elf_elfheader (ibfd)->e_flags;
    497  1.1.1.7  christos   elf_flags_init (obfd) = true;
    498  1.1.1.3  christos 
    499  1.1.1.3  christos   /* Copy object attributes.  */
    500  1.1.1.3  christos   _bfd_elf_copy_obj_attributes (ibfd, obfd);
    501  1.1.1.3  christos 
    502  1.1.1.3  christos   return _bfd_elf_copy_private_bfd_data (ibfd, obfd);
    503  1.1.1.3  christos }
    504  1.1.1.3  christos 
    505      1.1     skrll static reloc_howto_type *
    506  1.1.1.3  christos bfd_elf32_bfd_reloc_name_lookup (bfd * abfd ATTRIBUTE_UNUSED,
    507  1.1.1.3  christos 				 const char *r_name)
    508      1.1     skrll {
    509      1.1     skrll   unsigned int i;
    510      1.1     skrll 
    511  1.1.1.2  christos   for (i = 0; i < ARRAY_SIZE (elf_arc_howto_table); i++)
    512      1.1     skrll     if (elf_arc_howto_table[i].name != NULL
    513      1.1     skrll 	&& strcasecmp (elf_arc_howto_table[i].name, r_name) == 0)
    514  1.1.1.3  christos       return arc_elf_howto (i);
    515      1.1     skrll 
    516      1.1     skrll   return NULL;
    517      1.1     skrll }
    518      1.1     skrll 
    519  1.1.1.2  christos /* Set the howto pointer for an ARC ELF reloc.  */
    520  1.1.1.3  christos 
    521  1.1.1.7  christos static bool
    522  1.1.1.5  christos arc_info_to_howto_rel (bfd * abfd,
    523  1.1.1.2  christos 		       arelent * cache_ptr,
    524  1.1.1.2  christos 		       Elf_Internal_Rela * dst)
    525      1.1     skrll {
    526      1.1     skrll   unsigned int r_type;
    527      1.1     skrll 
    528      1.1     skrll   r_type = ELF32_R_TYPE (dst->r_info);
    529  1.1.1.5  christos   if (r_type >= (unsigned int) R_ARC_max)
    530  1.1.1.5  christos     {
    531  1.1.1.5  christos       /* xgettext:c-format */
    532  1.1.1.5  christos       _bfd_error_handler (_("%pB: unsupported relocation type %#x"),
    533  1.1.1.5  christos 			  abfd, r_type);
    534  1.1.1.5  christos       bfd_set_error (bfd_error_bad_value);
    535  1.1.1.7  christos       return false;
    536  1.1.1.5  christos     }
    537  1.1.1.5  christos 
    538  1.1.1.3  christos   cache_ptr->howto = arc_elf_howto (r_type);
    539  1.1.1.7  christos   return true;
    540  1.1.1.3  christos }
    541  1.1.1.3  christos 
    542  1.1.1.4  christos /* Extract CPU features from an NTBS.  */
    543  1.1.1.4  christos 
    544  1.1.1.4  christos static unsigned
    545  1.1.1.4  christos arc_extract_features (const char *p)
    546  1.1.1.4  christos {
    547  1.1.1.4  christos   unsigned i, r = 0;
    548  1.1.1.4  christos 
    549  1.1.1.4  christos   if (!p)
    550  1.1.1.4  christos     return 0;
    551  1.1.1.4  christos 
    552  1.1.1.4  christos   for (i = 0; i < ARRAY_SIZE (bfd_feature_list); i++)
    553  1.1.1.4  christos     {
    554  1.1.1.4  christos       char *t = strstr (p, bfd_feature_list[i].attr);
    555  1.1.1.4  christos       unsigned l = strlen (bfd_feature_list[i].attr);
    556  1.1.1.4  christos       if ((t != NULL)
    557  1.1.1.4  christos 	  && (t[l] == ','
    558  1.1.1.4  christos 	      || t[l] == '\0'))
    559  1.1.1.4  christos 	r |= bfd_feature_list[i].feature;
    560  1.1.1.4  christos     }
    561  1.1.1.4  christos 
    562  1.1.1.4  christos   return r;
    563  1.1.1.4  christos }
    564  1.1.1.4  christos 
    565  1.1.1.4  christos /* Concatenate two strings.  s1 can be NULL but not
    566  1.1.1.4  christos    s2.  */
    567  1.1.1.4  christos 
    568  1.1.1.4  christos static char *
    569  1.1.1.4  christos arc_stralloc (char * s1, const char * s2)
    570  1.1.1.4  christos {
    571  1.1.1.4  christos   char *p;
    572  1.1.1.4  christos 
    573  1.1.1.4  christos   /* Only s1 can be null.  */
    574  1.1.1.4  christos   BFD_ASSERT (s2);
    575  1.1.1.4  christos 
    576  1.1.1.4  christos   p = s1 ? concat (s1, ",", s2, NULL) : (char *)s2;
    577  1.1.1.4  christos 
    578  1.1.1.4  christos   return p;
    579  1.1.1.4  christos }
    580  1.1.1.4  christos 
    581  1.1.1.4  christos /* Merge ARC object attributes from IBFD into OBFD.  Raise an error if
    582  1.1.1.4  christos    there are conflicting attributes.  */
    583  1.1.1.4  christos 
    584  1.1.1.7  christos static bool
    585  1.1.1.4  christos arc_elf_merge_attributes (bfd *ibfd, struct bfd_link_info *info)
    586  1.1.1.4  christos {
    587  1.1.1.4  christos   bfd *obfd = info->output_bfd;
    588  1.1.1.4  christos   obj_attribute *in_attr;
    589  1.1.1.4  christos   obj_attribute *out_attr;
    590  1.1.1.4  christos   int i;
    591  1.1.1.7  christos   bool result = true;
    592  1.1.1.4  christos   const char *sec_name = get_elf_backend_data (ibfd)->obj_attrs_section;
    593  1.1.1.4  christos   char *tagname = NULL;
    594  1.1.1.4  christos 
    595  1.1.1.4  christos   /* Skip the linker stubs file.  This preserves previous behavior
    596  1.1.1.4  christos      of accepting unknown attributes in the first input file - but
    597  1.1.1.4  christos      is that a bug?  */
    598  1.1.1.4  christos   if (ibfd->flags & BFD_LINKER_CREATED)
    599  1.1.1.7  christos     return true;
    600  1.1.1.4  christos 
    601  1.1.1.4  christos   /* Skip any input that hasn't attribute section.
    602  1.1.1.4  christos      This enables to link object files without attribute section with
    603  1.1.1.4  christos      any others.  */
    604  1.1.1.4  christos   if (bfd_get_section_by_name (ibfd, sec_name) == NULL)
    605  1.1.1.7  christos     return true;
    606  1.1.1.4  christos 
    607  1.1.1.4  christos   if (!elf_known_obj_attributes_proc (obfd)[0].i)
    608  1.1.1.4  christos     {
    609  1.1.1.4  christos       /* This is the first object.  Copy the attributes.  */
    610  1.1.1.4  christos       _bfd_elf_copy_obj_attributes (ibfd, obfd);
    611  1.1.1.4  christos 
    612  1.1.1.4  christos       out_attr = elf_known_obj_attributes_proc (obfd);
    613  1.1.1.4  christos 
    614  1.1.1.4  christos       /* Use the Tag_null value to indicate the attributes have been
    615  1.1.1.4  christos 	 initialized.  */
    616  1.1.1.4  christos       out_attr[0].i = 1;
    617  1.1.1.4  christos 
    618  1.1.1.7  christos       return true;
    619  1.1.1.4  christos     }
    620  1.1.1.4  christos 
    621  1.1.1.4  christos   in_attr = elf_known_obj_attributes_proc (ibfd);
    622  1.1.1.4  christos   out_attr = elf_known_obj_attributes_proc (obfd);
    623  1.1.1.4  christos 
    624  1.1.1.4  christos   for (i = LEAST_KNOWN_OBJ_ATTRIBUTE; i < NUM_KNOWN_OBJ_ATTRIBUTES; i++)
    625  1.1.1.4  christos     {
    626  1.1.1.4  christos       /* Merge this attribute with existing attributes.  */
    627  1.1.1.4  christos       switch (i)
    628  1.1.1.4  christos 	{
    629  1.1.1.4  christos 	case Tag_ARC_PCS_config:
    630  1.1.1.4  christos 	  if (out_attr[i].i == 0)
    631  1.1.1.4  christos 	    out_attr[i].i = in_attr[i].i;
    632  1.1.1.4  christos 	  else if (in_attr[i].i != 0 && out_attr[i].i != in_attr[i].i)
    633  1.1.1.4  christos 	    {
    634  1.1.1.4  christos 	      const char *tagval[] = { "Absent", "Bare-metal/mwdt",
    635  1.1.1.4  christos 					"Bare-metal/newlib", "Linux/uclibc",
    636  1.1.1.4  christos 					"Linux/glibc" };
    637  1.1.1.4  christos 	      BFD_ASSERT (in_attr[i].i < 5);
    638  1.1.1.4  christos 	      BFD_ASSERT (out_attr[i].i < 5);
    639  1.1.1.4  christos 	      /* It's sometimes ok to mix different configs, so this is only
    640  1.1.1.4  christos 		 a warning.  */
    641  1.1.1.4  christos 	      _bfd_error_handler
    642  1.1.1.5  christos 		(_("warning: %pB: conflicting platform configuration "
    643  1.1.1.5  christos 		   "%s with %s"), ibfd,
    644  1.1.1.4  christos 		 tagval[in_attr[i].i],
    645  1.1.1.4  christos 		 tagval[out_attr[i].i]);
    646  1.1.1.4  christos 	    }
    647  1.1.1.4  christos 	  break;
    648  1.1.1.4  christos 
    649  1.1.1.4  christos 	case Tag_ARC_CPU_base:
    650  1.1.1.4  christos 	  if (out_attr[i].i == 0)
    651  1.1.1.4  christos 	    out_attr[i].i = in_attr[i].i;
    652  1.1.1.4  christos 	  else if (in_attr[i].i != 0 && out_attr[i].i != in_attr[i].i
    653  1.1.1.4  christos 		   && ((out_attr[i].i + in_attr[i].i) < 6))
    654  1.1.1.4  christos 	    {
    655  1.1.1.4  christos 	      const char *tagval[] = { "Absent", "ARC6xx", "ARC7xx",
    656  1.1.1.4  christos 					"ARCEM", "ARCHS" };
    657  1.1.1.4  christos 	      BFD_ASSERT (in_attr[i].i < 5);
    658  1.1.1.4  christos 	      BFD_ASSERT (out_attr[i].i < 5);
    659  1.1.1.4  christos 	      /* We cannot mix code for different CPUs.  */
    660  1.1.1.4  christos 	      _bfd_error_handler
    661  1.1.1.5  christos 		(_("error: %pB: unable to merge CPU base attributes "
    662  1.1.1.5  christos 		   "%s with %s"),
    663  1.1.1.4  christos 		 obfd,
    664  1.1.1.4  christos 		 tagval[in_attr[i].i],
    665  1.1.1.4  christos 		 tagval[out_attr[i].i]);
    666  1.1.1.7  christos 	      result = false;
    667  1.1.1.4  christos 	      break;
    668  1.1.1.4  christos 	    }
    669  1.1.1.4  christos 	  else
    670  1.1.1.4  christos 	    {
    671  1.1.1.4  christos 	      /* The CPUs may be different, check if we can still mix
    672  1.1.1.4  christos 		 the objects against the output choosen CPU.  */
    673  1.1.1.4  christos 	      unsigned in_feature = 0;
    674  1.1.1.4  christos 	      unsigned out_feature = 0;
    675  1.1.1.4  christos 	      char *p1 = in_attr[Tag_ARC_ISA_config].s;
    676  1.1.1.4  christos 	      char *p2 = out_attr[Tag_ARC_ISA_config].s;
    677  1.1.1.4  christos 	      unsigned j;
    678  1.1.1.4  christos 	      unsigned cpu_out;
    679  1.1.1.4  christos 	      unsigned opcode_map[] = {0, ARC_OPCODE_ARC600, ARC_OPCODE_ARC700,
    680  1.1.1.4  christos 				       ARC_OPCODE_ARCv2EM, ARC_OPCODE_ARCv2HS};
    681  1.1.1.4  christos 
    682  1.1.1.4  christos 	      BFD_ASSERT (in_attr[i].i < (sizeof (opcode_map)
    683  1.1.1.4  christos 					  / sizeof (unsigned)));
    684  1.1.1.4  christos 	      BFD_ASSERT (out_attr[i].i < (sizeof (opcode_map)
    685  1.1.1.4  christos 					   / sizeof (unsigned)));
    686  1.1.1.4  christos 	      cpu_out = opcode_map[out_attr[i].i];
    687  1.1.1.4  christos 
    688  1.1.1.4  christos 	      in_feature = arc_extract_features (p1);
    689  1.1.1.4  christos 	      out_feature = arc_extract_features (p2);
    690  1.1.1.4  christos 
    691  1.1.1.4  christos 	      /* First, check if a feature is compatible with the
    692  1.1.1.4  christos 		 output object chosen CPU.  */
    693  1.1.1.4  christos 	      for (j = 0; j < ARRAY_SIZE (bfd_feature_list); j++)
    694  1.1.1.4  christos 		if (((in_feature | out_feature) & bfd_feature_list[j].feature)
    695  1.1.1.4  christos 		    && (!(cpu_out & bfd_feature_list[j].cpus)))
    696  1.1.1.4  christos 		  {
    697  1.1.1.4  christos 		    _bfd_error_handler
    698  1.1.1.5  christos 		      (_("error: %pB: unable to merge ISA extension attributes "
    699  1.1.1.5  christos 			 "%s"),
    700  1.1.1.4  christos 		       obfd, bfd_feature_list[j].name);
    701  1.1.1.7  christos 		    result = false;
    702  1.1.1.4  christos 		    break;
    703  1.1.1.4  christos 		  }
    704  1.1.1.4  christos 	      /* Second, if we have compatible features with the
    705  1.1.1.4  christos 		 chosen CPU, check if they are compatible among
    706  1.1.1.4  christos 		 them.  */
    707  1.1.1.4  christos 	      for (j = 0; j < ARRAY_SIZE (bfd_conflict_list); j++)
    708  1.1.1.4  christos 		if (((in_feature | out_feature) & bfd_conflict_list[j])
    709  1.1.1.4  christos 		    == bfd_conflict_list[j])
    710  1.1.1.4  christos 		  {
    711  1.1.1.4  christos 		    unsigned k;
    712  1.1.1.4  christos 		    for (k = 0; k < ARRAY_SIZE (bfd_feature_list); k++)
    713  1.1.1.4  christos 		      {
    714  1.1.1.4  christos 			if (in_feature &  bfd_feature_list[k].feature
    715  1.1.1.4  christos 			    & bfd_conflict_list[j])
    716  1.1.1.4  christos 			  p1 = (char *) bfd_feature_list[k].name;
    717  1.1.1.4  christos 			if (out_feature &  bfd_feature_list[k].feature
    718  1.1.1.4  christos 			    & bfd_conflict_list[j])
    719  1.1.1.4  christos 			  p2 = (char *) bfd_feature_list[k].name;
    720  1.1.1.4  christos 		      }
    721  1.1.1.4  christos 		    _bfd_error_handler
    722  1.1.1.5  christos 		      (_("error: %pB: conflicting ISA extension attributes "
    723  1.1.1.5  christos 			 "%s with %s"),
    724  1.1.1.4  christos 		       obfd, p1, p2);
    725  1.1.1.7  christos 		    result = false;
    726  1.1.1.4  christos 		    break;
    727  1.1.1.4  christos 		  }
    728  1.1.1.4  christos 	      /* Everithing is alright.  */
    729  1.1.1.4  christos 	      out_feature |= in_feature;
    730  1.1.1.4  christos 	      p1 = NULL;
    731  1.1.1.4  christos 	      for (j = 0; j < ARRAY_SIZE (bfd_feature_list); j++)
    732  1.1.1.4  christos 		if (out_feature & bfd_feature_list[j].feature)
    733  1.1.1.4  christos 		  p1 = arc_stralloc (p1, bfd_feature_list[j].attr);
    734  1.1.1.4  christos 	      if (p1)
    735  1.1.1.4  christos 		out_attr[Tag_ARC_ISA_config].s =
    736  1.1.1.4  christos 		  _bfd_elf_attr_strdup (obfd, p1);
    737  1.1.1.4  christos 	    }
    738  1.1.1.4  christos 	  /* Fall through.  */
    739  1.1.1.4  christos 	case Tag_ARC_CPU_variation:
    740  1.1.1.4  christos 	case Tag_ARC_ISA_mpy_option:
    741  1.1.1.4  christos 	case Tag_ARC_ABI_osver:
    742  1.1.1.4  christos 	  /* Use the largest value specified.  */
    743  1.1.1.4  christos 	  if (in_attr[i].i > out_attr[i].i)
    744  1.1.1.4  christos 	    out_attr[i].i = in_attr[i].i;
    745  1.1.1.4  christos 	  break;
    746  1.1.1.4  christos 
    747  1.1.1.6  christos 	  /* The CPU name is given by the vendor, just choose an
    748  1.1.1.6  christos 	     existing one if missing or different.  There are no fail
    749  1.1.1.6  christos 	     criteria if they different or both missing.  */
    750  1.1.1.4  christos 	case Tag_ARC_CPU_name:
    751  1.1.1.6  christos 	  if (!out_attr[i].s && in_attr[i].s)
    752  1.1.1.6  christos 	    out_attr[i].s = _bfd_elf_attr_strdup (obfd, in_attr[i].s);
    753  1.1.1.4  christos 	  break;
    754  1.1.1.4  christos 
    755  1.1.1.4  christos 	case Tag_ARC_ABI_rf16:
    756  1.1.1.4  christos 	  if (out_attr[i].i == 0)
    757  1.1.1.4  christos 	    out_attr[i].i = in_attr[i].i;
    758  1.1.1.4  christos 	  else if (out_attr[i].i != in_attr[i].i)
    759  1.1.1.4  christos 	    {
    760  1.1.1.4  christos 	      /* We cannot mix code with rf16 and without.  */
    761  1.1.1.4  christos 	      _bfd_error_handler
    762  1.1.1.5  christos 		(_("error: %pB: cannot mix rf16 with full register set %pB"),
    763  1.1.1.4  christos 		 obfd, ibfd);
    764  1.1.1.7  christos 	      result = false;
    765  1.1.1.4  christos 	    }
    766  1.1.1.4  christos 	  break;
    767  1.1.1.4  christos 
    768  1.1.1.4  christos 	case Tag_ARC_ABI_pic:
    769  1.1.1.4  christos 	  tagname = "PIC";
    770  1.1.1.4  christos 	  /* fall through */
    771  1.1.1.4  christos 	case Tag_ARC_ABI_sda:
    772  1.1.1.4  christos 	  if (!tagname)
    773  1.1.1.4  christos 	    tagname = "SDA";
    774  1.1.1.4  christos 	  /* fall through */
    775  1.1.1.4  christos 	case Tag_ARC_ABI_tls:
    776  1.1.1.4  christos 	  {
    777  1.1.1.4  christos 	    const char *tagval[] = { "Absent", "MWDT", "GNU" };
    778  1.1.1.4  christos 
    779  1.1.1.4  christos 	    if (!tagname)
    780  1.1.1.4  christos 	      tagname = "TLS";
    781  1.1.1.4  christos 
    782  1.1.1.4  christos 	    BFD_ASSERT (in_attr[i].i < 3);
    783  1.1.1.4  christos 	    BFD_ASSERT (out_attr[i].i < 3);
    784  1.1.1.6  christos 	    if (out_attr[i].i == 0)
    785  1.1.1.6  christos 	      out_attr[i].i = in_attr[i].i;
    786  1.1.1.6  christos 	    else if (out_attr[i].i != 0 && in_attr[i].i != 0
    787  1.1.1.4  christos 		&& out_attr[i].i != in_attr[i].i)
    788  1.1.1.4  christos 	      {
    789  1.1.1.4  christos 		_bfd_error_handler
    790  1.1.1.5  christos 		  (_("error: %pB: conflicting attributes %s: %s with %s"),
    791  1.1.1.4  christos 		   obfd, tagname,
    792  1.1.1.4  christos 		   tagval[in_attr[i].i],
    793  1.1.1.4  christos 		   tagval[out_attr[i].i]);
    794  1.1.1.7  christos 		result = false;
    795  1.1.1.4  christos 	      }
    796  1.1.1.4  christos 	    tagname = NULL;
    797  1.1.1.4  christos 	    break;
    798  1.1.1.4  christos 	  }
    799  1.1.1.4  christos 
    800  1.1.1.4  christos 	case Tag_ARC_ABI_double_size:
    801  1.1.1.4  christos 	  tagname = "Double size";
    802  1.1.1.4  christos 	  /* fall through */
    803  1.1.1.4  christos 	case Tag_ARC_ABI_enumsize:
    804  1.1.1.4  christos 	  if (!tagname)
    805  1.1.1.4  christos 	    tagname = "Enum size";
    806  1.1.1.4  christos 	  /* fall through */
    807  1.1.1.4  christos 	case Tag_ARC_ABI_exceptions:
    808  1.1.1.4  christos 	  if (!tagname)
    809  1.1.1.4  christos 	    tagname = "ABI exceptions";
    810  1.1.1.4  christos 
    811  1.1.1.6  christos 	  if (out_attr[i].i == 0)
    812  1.1.1.6  christos 	    out_attr[i].i = in_attr[i].i;
    813  1.1.1.6  christos 	  else if (out_attr[i].i != 0 && in_attr[i].i != 0
    814  1.1.1.4  christos 	      && out_attr[i].i != in_attr[i].i)
    815  1.1.1.4  christos 	    {
    816  1.1.1.4  christos 	      _bfd_error_handler
    817  1.1.1.5  christos 		(_("error: %pB: conflicting attributes %s"),
    818  1.1.1.4  christos 		 obfd, tagname);
    819  1.1.1.7  christos 	      result = false;
    820  1.1.1.4  christos 	    }
    821  1.1.1.4  christos 	  break;
    822  1.1.1.4  christos 
    823  1.1.1.4  christos 	case Tag_ARC_ISA_apex:
    824  1.1.1.4  christos 	  break; /* Do nothing for APEX attributes.  */
    825  1.1.1.4  christos 
    826  1.1.1.4  christos 	case Tag_ARC_ISA_config:
    827  1.1.1.4  christos 	  /* It is handled in Tag_ARC_CPU_base.  */
    828  1.1.1.4  christos 	  break;
    829  1.1.1.4  christos 
    830  1.1.1.6  christos 	case Tag_ARC_ATR_version:
    831  1.1.1.6  christos 	  if (out_attr[i].i == 0)
    832  1.1.1.6  christos 	    out_attr[i].i = in_attr[i].i;
    833  1.1.1.6  christos 	  break;
    834  1.1.1.6  christos 
    835  1.1.1.4  christos 	default:
    836  1.1.1.4  christos 	  result
    837  1.1.1.4  christos 	    = result && _bfd_elf_merge_unknown_attribute_low (ibfd, obfd, i);
    838  1.1.1.4  christos 	}
    839  1.1.1.4  christos 
    840  1.1.1.4  christos       /* If out_attr was copied from in_attr then it won't have a type yet.  */
    841  1.1.1.4  christos       if (in_attr[i].type && !out_attr[i].type)
    842  1.1.1.4  christos 	out_attr[i].type = in_attr[i].type;
    843  1.1.1.4  christos     }
    844  1.1.1.4  christos 
    845  1.1.1.4  christos   /* Merge Tag_compatibility attributes and any common GNU ones.  */
    846  1.1.1.4  christos   if (!_bfd_elf_merge_object_attributes (ibfd, info))
    847  1.1.1.7  christos     return false;
    848  1.1.1.4  christos 
    849  1.1.1.4  christos   /* Check for any attributes not known on ARC.  */
    850  1.1.1.4  christos   result &= _bfd_elf_merge_unknown_attribute_list (ibfd, obfd);
    851  1.1.1.4  christos 
    852  1.1.1.4  christos   return result;
    853  1.1.1.4  christos }
    854  1.1.1.4  christos 
    855  1.1.1.3  christos /* Merge backend specific data from an object file to the output
    856  1.1.1.3  christos    object file when linking.  */
    857  1.1.1.3  christos 
    858  1.1.1.7  christos static bool
    859  1.1.1.4  christos arc_elf_merge_private_bfd_data (bfd *ibfd, struct bfd_link_info *info)
    860  1.1.1.3  christos {
    861  1.1.1.4  christos   bfd *obfd = info->output_bfd;
    862  1.1.1.3  christos   unsigned short mach_ibfd;
    863  1.1.1.3  christos   static unsigned short mach_obfd = EM_NONE;
    864  1.1.1.3  christos   flagword out_flags;
    865  1.1.1.3  christos   flagword in_flags;
    866  1.1.1.3  christos   asection *sec;
    867  1.1.1.3  christos 
    868  1.1.1.3  christos    /* Check if we have the same endianess.  */
    869  1.1.1.4  christos   if (! _bfd_generic_verify_endian_match (ibfd, info))
    870  1.1.1.7  christos     return false;
    871  1.1.1.4  christos 
    872  1.1.1.4  christos   if (bfd_get_flavour (ibfd) != bfd_target_elf_flavour
    873  1.1.1.4  christos       || bfd_get_flavour (obfd) != bfd_target_elf_flavour)
    874  1.1.1.7  christos     return true;
    875  1.1.1.3  christos 
    876  1.1.1.3  christos   /* Collect ELF flags.  */
    877  1.1.1.3  christos   in_flags = elf_elfheader (ibfd)->e_flags & EF_ARC_MACH_MSK;
    878  1.1.1.3  christos   out_flags = elf_elfheader (obfd)->e_flags & EF_ARC_MACH_MSK;
    879  1.1.1.3  christos 
    880  1.1.1.3  christos   if (!elf_flags_init (obfd)) /* First call, no flags set.  */
    881  1.1.1.3  christos     {
    882  1.1.1.7  christos       elf_flags_init (obfd) = true;
    883  1.1.1.3  christos       out_flags = in_flags;
    884  1.1.1.3  christos     }
    885  1.1.1.3  christos 
    886  1.1.1.4  christos   if (!arc_elf_merge_attributes (ibfd, info))
    887  1.1.1.7  christos     return false;
    888  1.1.1.3  christos 
    889  1.1.1.3  christos   /* Check to see if the input BFD actually contains any sections.  Do
    890  1.1.1.3  christos      not short-circuit dynamic objects; their section list may be
    891  1.1.1.3  christos      emptied by elf_link_add_object_symbols.  */
    892  1.1.1.3  christos   if (!(ibfd->flags & DYNAMIC))
    893  1.1.1.3  christos     {
    894  1.1.1.7  christos       bool null_input_bfd = true;
    895  1.1.1.7  christos       bool only_data_sections = true;
    896  1.1.1.3  christos 
    897  1.1.1.3  christos       for (sec = ibfd->sections; sec != NULL; sec = sec->next)
    898  1.1.1.3  christos 	{
    899  1.1.1.6  christos 	  if ((bfd_section_flags (sec)
    900  1.1.1.3  christos 	       & (SEC_LOAD | SEC_CODE | SEC_HAS_CONTENTS))
    901  1.1.1.3  christos 	      == (SEC_LOAD | SEC_CODE | SEC_HAS_CONTENTS))
    902  1.1.1.7  christos 	    only_data_sections = false;
    903  1.1.1.3  christos 
    904  1.1.1.7  christos 	  null_input_bfd = false;
    905  1.1.1.3  christos 	}
    906  1.1.1.3  christos 
    907  1.1.1.3  christos       if (null_input_bfd || only_data_sections)
    908  1.1.1.7  christos 	return true;
    909  1.1.1.3  christos     }
    910  1.1.1.3  christos 
    911  1.1.1.3  christos   /* Complain about various flag/architecture mismatches.  */
    912  1.1.1.3  christos   mach_ibfd = elf_elfheader (ibfd)->e_machine;
    913  1.1.1.3  christos   if (mach_obfd == EM_NONE)
    914  1.1.1.3  christos     {
    915  1.1.1.3  christos       mach_obfd = mach_ibfd;
    916  1.1.1.3  christos     }
    917  1.1.1.3  christos   else
    918  1.1.1.3  christos     {
    919  1.1.1.3  christos       if (mach_ibfd != mach_obfd)
    920  1.1.1.3  christos 	{
    921  1.1.1.4  christos 	  /* xgettext:c-format */
    922  1.1.1.5  christos 	  _bfd_error_handler (_("error: attempting to link %pB "
    923  1.1.1.5  christos 				"with a binary %pB of different architecture"),
    924  1.1.1.4  christos 			      ibfd, obfd);
    925  1.1.1.7  christos 	  return false;
    926  1.1.1.3  christos 	}
    927  1.1.1.4  christos       else if ((in_flags != out_flags)
    928  1.1.1.4  christos 	       /* If we have object attributes, then we already
    929  1.1.1.4  christos 		  checked the objects compatibility, skip it.  */
    930  1.1.1.4  christos 	       && !bfd_elf_get_obj_attr_int (ibfd, OBJ_ATTR_PROC,
    931  1.1.1.4  christos 					     Tag_ARC_CPU_base))
    932  1.1.1.3  christos 	{
    933  1.1.1.3  christos 	  if (in_flags && out_flags)
    934  1.1.1.6  christos 	    {
    935  1.1.1.6  christos 	      /* Warn if different flags.  */
    936  1.1.1.6  christos 	      _bfd_error_handler
    937  1.1.1.6  christos 		/* xgettext:c-format */
    938  1.1.1.6  christos 		(_("%pB: uses different e_flags (%#x) fields than "
    939  1.1.1.6  christos 		   "previous modules (%#x)"),
    940  1.1.1.6  christos 		 ibfd, in_flags, out_flags);
    941  1.1.1.7  christos 	      return false;
    942  1.1.1.6  christos 	    }
    943  1.1.1.3  christos 	  /* MWDT doesnt set the eflags hence make sure we choose the
    944  1.1.1.3  christos 	     eflags set by gcc.  */
    945  1.1.1.3  christos 	  in_flags = in_flags > out_flags ? in_flags : out_flags;
    946  1.1.1.3  christos 	}
    947  1.1.1.4  christos       else
    948  1.1.1.4  christos 	{
    949  1.1.1.4  christos 	  /* Everything is correct; don't change the output flags.  */
    950  1.1.1.4  christos 	  in_flags = out_flags;
    951  1.1.1.4  christos 	}
    952  1.1.1.3  christos     }
    953  1.1.1.3  christos 
    954  1.1.1.3  christos   /* Update the flags.  */
    955  1.1.1.3  christos   elf_elfheader (obfd)->e_flags = in_flags;
    956  1.1.1.3  christos 
    957  1.1.1.3  christos   if (bfd_get_mach (obfd) < bfd_get_mach (ibfd))
    958  1.1.1.3  christos     {
    959  1.1.1.3  christos       return bfd_set_arch_mach (obfd, bfd_arch_arc, bfd_get_mach (ibfd));
    960  1.1.1.3  christos     }
    961  1.1.1.3  christos 
    962  1.1.1.7  christos   return true;
    963      1.1     skrll }
    964      1.1     skrll 
    965  1.1.1.4  christos /* Return a best guess for the machine number based on the attributes.  */
    966  1.1.1.4  christos 
    967  1.1.1.4  christos static unsigned int
    968  1.1.1.4  christos bfd_arc_get_mach_from_attributes (bfd * abfd)
    969  1.1.1.4  christos {
    970  1.1.1.4  christos   int arch = bfd_elf_get_obj_attr_int (abfd, OBJ_ATTR_PROC, Tag_ARC_CPU_base);
    971  1.1.1.4  christos   unsigned e_machine = elf_elfheader (abfd)->e_machine;
    972  1.1.1.4  christos 
    973  1.1.1.4  christos   switch (arch)
    974  1.1.1.4  christos     {
    975  1.1.1.4  christos     case TAG_CPU_ARC6xx:
    976  1.1.1.4  christos       return bfd_mach_arc_arc600;
    977  1.1.1.4  christos     case TAG_CPU_ARC7xx:
    978  1.1.1.4  christos       return bfd_mach_arc_arc700;
    979  1.1.1.4  christos     case TAG_CPU_ARCEM:
    980  1.1.1.4  christos     case TAG_CPU_ARCHS:
    981  1.1.1.4  christos       return bfd_mach_arc_arcv2;
    982  1.1.1.4  christos     default:
    983  1.1.1.4  christos       break;
    984  1.1.1.4  christos     }
    985  1.1.1.4  christos   return (e_machine == EM_ARC_COMPACT)
    986  1.1.1.4  christos     ? bfd_mach_arc_arc700 : bfd_mach_arc_arcv2;
    987  1.1.1.4  christos }
    988  1.1.1.4  christos 
    989      1.1     skrll /* Set the right machine number for an ARC ELF file.  */
    990  1.1.1.7  christos static bool
    991  1.1.1.2  christos arc_elf_object_p (bfd * abfd)
    992      1.1     skrll {
    993  1.1.1.2  christos   /* Make sure this is initialised, or you'll have the potential of passing
    994  1.1.1.2  christos      garbage---or misleading values---into the call to
    995  1.1.1.2  christos      bfd_default_set_arch_mach ().  */
    996  1.1.1.4  christos   unsigned int	  mach = bfd_mach_arc_arc700;
    997  1.1.1.2  christos   unsigned long   arch = elf_elfheader (abfd)->e_flags & EF_ARC_MACH_MSK;
    998  1.1.1.2  christos   unsigned	  e_machine = elf_elfheader (abfd)->e_machine;
    999      1.1     skrll 
   1000  1.1.1.2  christos   if (e_machine == EM_ARC_COMPACT || e_machine == EM_ARC_COMPACT2)
   1001      1.1     skrll     {
   1002      1.1     skrll       switch (arch)
   1003      1.1     skrll 	{
   1004  1.1.1.6  christos 	case E_ARC_MACH_ARC600:
   1005  1.1.1.6  christos 	  mach = bfd_mach_arc_arc600;
   1006  1.1.1.6  christos 	  break;
   1007  1.1.1.6  christos 	case E_ARC_MACH_ARC601:
   1008  1.1.1.6  christos 	  mach = bfd_mach_arc_arc601;
   1009  1.1.1.6  christos 	  break;
   1010  1.1.1.6  christos 	case E_ARC_MACH_ARC700:
   1011  1.1.1.6  christos 	  mach = bfd_mach_arc_arc700;
   1012  1.1.1.6  christos 	  break;
   1013  1.1.1.6  christos 	case EF_ARC_CPU_ARCV2HS:
   1014  1.1.1.6  christos 	case EF_ARC_CPU_ARCV2EM:
   1015  1.1.1.6  christos 	  mach = bfd_mach_arc_arcv2;
   1016  1.1.1.6  christos 	  break;
   1017  1.1.1.6  christos 	default:
   1018  1.1.1.6  christos 	  mach = bfd_arc_get_mach_from_attributes (abfd);
   1019  1.1.1.6  christos 	  break;
   1020  1.1.1.2  christos 	}
   1021  1.1.1.2  christos     }
   1022  1.1.1.2  christos   else
   1023  1.1.1.2  christos     {
   1024  1.1.1.2  christos       if (e_machine == EM_ARC)
   1025  1.1.1.2  christos 	{
   1026  1.1.1.4  christos 	  _bfd_error_handler
   1027  1.1.1.5  christos 	    (_("error: the ARC4 architecture is no longer supported"));
   1028  1.1.1.7  christos 	  return false;
   1029  1.1.1.2  christos 	}
   1030  1.1.1.2  christos       else
   1031  1.1.1.2  christos 	{
   1032  1.1.1.4  christos 	  _bfd_error_handler
   1033  1.1.1.5  christos 	    (_("warning: unset or old architecture flags; "
   1034  1.1.1.5  christos 	       "use default machine"));
   1035      1.1     skrll 	}
   1036      1.1     skrll     }
   1037  1.1.1.2  christos 
   1038      1.1     skrll   return bfd_default_set_arch_mach (abfd, bfd_arch_arc, mach);
   1039      1.1     skrll }
   1040      1.1     skrll 
   1041      1.1     skrll /* The final processing done just before writing out an ARC ELF object file.
   1042      1.1     skrll    This gets the ARC architecture right based on the machine number.  */
   1043      1.1     skrll 
   1044  1.1.1.7  christos static bool
   1045  1.1.1.6  christos arc_elf_final_write_processing (bfd *abfd)
   1046      1.1     skrll {
   1047  1.1.1.2  christos   unsigned long emf;
   1048  1.1.1.4  christos   int osver = bfd_elf_get_obj_attr_int (abfd, OBJ_ATTR_PROC,
   1049  1.1.1.4  christos 					Tag_ARC_ABI_osver);
   1050  1.1.1.4  christos   flagword e_flags = elf_elfheader (abfd)->e_flags & ~EF_ARC_OSABI_MSK;
   1051      1.1     skrll 
   1052      1.1     skrll   switch (bfd_get_mach (abfd))
   1053      1.1     skrll     {
   1054  1.1.1.2  christos     case bfd_mach_arc_arcv2:
   1055  1.1.1.2  christos       emf = EM_ARC_COMPACT2;
   1056      1.1     skrll       break;
   1057  1.1.1.2  christos     default:
   1058  1.1.1.6  christos       emf = EM_ARC_COMPACT;
   1059  1.1.1.6  christos       break;
   1060      1.1     skrll     }
   1061  1.1.1.3  christos 
   1062  1.1.1.2  christos   elf_elfheader (abfd)->e_machine = emf;
   1063  1.1.1.2  christos 
   1064  1.1.1.2  christos   /* Record whatever is the current syscall ABI version.  */
   1065  1.1.1.4  christos   if (osver)
   1066  1.1.1.4  christos     e_flags |= ((osver & 0x0f) << 8);
   1067  1.1.1.4  christos   else
   1068  1.1.1.4  christos     e_flags |= E_ARC_OSABI_V3;
   1069  1.1.1.3  christos 
   1070  1.1.1.6  christos   elf_elfheader (abfd)->e_flags |= e_flags;
   1071  1.1.1.6  christos   return _bfd_elf_final_write_processing (abfd);
   1072      1.1     skrll }
   1073      1.1     skrll 
   1074  1.1.1.4  christos #ifdef ARC_ENABLE_DEBUG
   1075  1.1.1.4  christos #define DEBUG_ARC_RELOC(A) debug_arc_reloc (A)
   1076  1.1.1.2  christos 
   1077  1.1.1.2  christos static void
   1078  1.1.1.2  christos debug_arc_reloc (struct arc_relocation_data reloc_data)
   1079  1.1.1.2  christos {
   1080  1.1.1.4  christos   ARC_DEBUG ("Reloc type=%s, should_relocate = %s\n",
   1081  1.1.1.4  christos 	     reloc_data.howto->name,
   1082  1.1.1.4  christos 	     reloc_data.should_relocate ? "true" : "false");
   1083  1.1.1.4  christos   ARC_DEBUG ("  offset = 0x%x, addend = 0x%x\n",
   1084  1.1.1.4  christos 	     (unsigned int) reloc_data.reloc_offset,
   1085  1.1.1.4  christos 	     (unsigned int) reloc_data.reloc_addend);
   1086  1.1.1.4  christos   ARC_DEBUG (" Symbol:\n");
   1087  1.1.1.4  christos   ARC_DEBUG ("  value = 0x%08x\n",
   1088  1.1.1.4  christos 	     (unsigned int) reloc_data.sym_value);
   1089  1.1.1.2  christos   if (reloc_data.sym_section != NULL)
   1090  1.1.1.2  christos     {
   1091  1.1.1.4  christos       ARC_DEBUG (" Symbol Section:\n");
   1092  1.1.1.4  christos       ARC_DEBUG ("  section name = %s, output_offset 0x%08x",
   1093  1.1.1.4  christos 		 reloc_data.sym_section->name,
   1094  1.1.1.4  christos 		 (unsigned int) reloc_data.sym_section->output_offset);
   1095  1.1.1.3  christos       if (reloc_data.sym_section->output_section != NULL)
   1096  1.1.1.4  christos 	ARC_DEBUG (", output_section->vma = 0x%08x",
   1097  1.1.1.3  christos 		   ((unsigned int) reloc_data.sym_section->output_section->vma));
   1098  1.1.1.4  christos       ARC_DEBUG ("\n");
   1099  1.1.1.6  christos       if (reloc_data.sym_section->owner
   1100  1.1.1.6  christos 	  && reloc_data.sym_section->owner->filename)
   1101  1.1.1.4  christos 	ARC_DEBUG ("  file: %s\n", reloc_data.sym_section->owner->filename);
   1102  1.1.1.2  christos     }
   1103  1.1.1.2  christos   else
   1104  1.1.1.3  christos     {
   1105  1.1.1.4  christos       ARC_DEBUG ("  symbol section is NULL\n");
   1106  1.1.1.3  christos     }
   1107  1.1.1.2  christos 
   1108  1.1.1.4  christos   ARC_DEBUG (" Input_section:\n");
   1109  1.1.1.2  christos   if (reloc_data.input_section != NULL)
   1110  1.1.1.2  christos     {
   1111  1.1.1.4  christos       ARC_DEBUG ("  section name = %s, output_offset 0x%08x, output_section->vma = 0x%08x\n",
   1112  1.1.1.4  christos 		 reloc_data.input_section->name,
   1113  1.1.1.4  christos 		 (unsigned int) reloc_data.input_section->output_offset,
   1114  1.1.1.4  christos 		 (unsigned int) reloc_data.input_section->output_section->vma);
   1115  1.1.1.4  christos       ARC_DEBUG ("  changed_address = 0x%08x\n",
   1116  1.1.1.4  christos 		 (unsigned int) (reloc_data.input_section->output_section->vma
   1117  1.1.1.4  christos 				 + reloc_data.input_section->output_offset
   1118  1.1.1.4  christos 				 + reloc_data.reloc_offset));
   1119  1.1.1.4  christos       ARC_DEBUG ("  file: %s\n", reloc_data.input_section->owner->filename);
   1120  1.1.1.2  christos     }
   1121  1.1.1.2  christos   else
   1122  1.1.1.3  christos     {
   1123  1.1.1.4  christos       ARC_DEBUG ("	input section is NULL\n");
   1124  1.1.1.3  christos     }
   1125  1.1.1.2  christos }
   1126  1.1.1.4  christos #else
   1127  1.1.1.4  christos #define DEBUG_ARC_RELOC(A)
   1128  1.1.1.4  christos #endif /* ARC_ENABLE_DEBUG */
   1129  1.1.1.2  christos 
   1130  1.1.1.3  christos static bfd_vma
   1131  1.1.1.7  christos middle_endian_convert (bfd_vma insn, bool do_it)
   1132  1.1.1.2  christos {
   1133  1.1.1.3  christos   if (do_it)
   1134  1.1.1.3  christos     {
   1135  1.1.1.4  christos       insn
   1136  1.1.1.4  christos 	= ((insn & 0xffff0000) >> 16)
   1137  1.1.1.4  christos 	  | ((insn & 0xffff) << 16);
   1138  1.1.1.3  christos     }
   1139  1.1.1.3  christos   return insn;
   1140  1.1.1.2  christos }
   1141  1.1.1.2  christos 
   1142  1.1.1.3  christos /* This function is called for relocations that are otherwise marked as NOT
   1143  1.1.1.3  christos    requiring overflow checks.  In here we perform non-standard checks of
   1144  1.1.1.3  christos    the relocation value.  */
   1145  1.1.1.3  christos 
   1146  1.1.1.3  christos static inline bfd_reloc_status_type
   1147  1.1.1.3  christos arc_special_overflow_checks (const struct arc_relocation_data reloc_data,
   1148  1.1.1.4  christos 			     bfd_signed_vma relocation,
   1149  1.1.1.3  christos 			     struct bfd_link_info *info ATTRIBUTE_UNUSED)
   1150  1.1.1.3  christos {
   1151  1.1.1.3  christos   switch (reloc_data.howto->type)
   1152  1.1.1.3  christos     {
   1153  1.1.1.3  christos     case R_ARC_NPS_CMEM16:
   1154  1.1.1.3  christos       if (((relocation >> 16) & 0xffff) != NPS_CMEM_HIGH_VALUE)
   1155  1.1.1.4  christos 	{
   1156  1.1.1.4  christos 	  if (reloc_data.reloc_addend == 0)
   1157  1.1.1.4  christos 	    _bfd_error_handler
   1158  1.1.1.4  christos 	      /* xgettext:c-format */
   1159  1.1.1.5  christos 	      (_("%pB(%pA+%#" PRIx64 "): CMEM relocation to `%s' is invalid, "
   1160  1.1.1.5  christos 		 "16 MSB should be %#x (value is %#" PRIx64 ")"),
   1161  1.1.1.4  christos 	       reloc_data.input_section->owner,
   1162  1.1.1.4  christos 	       reloc_data.input_section,
   1163  1.1.1.5  christos 	       (uint64_t) reloc_data.reloc_offset,
   1164  1.1.1.4  christos 	       reloc_data.symbol_name,
   1165  1.1.1.4  christos 	       NPS_CMEM_HIGH_VALUE,
   1166  1.1.1.5  christos 	       (uint64_t) relocation);
   1167  1.1.1.4  christos 	  else
   1168  1.1.1.4  christos 	    _bfd_error_handler
   1169  1.1.1.4  christos 	      /* xgettext:c-format */
   1170  1.1.1.5  christos 	      (_("%pB(%pA+%#" PRIx64 "): CMEM relocation to `%s+%#" PRIx64
   1171  1.1.1.5  christos 		 "' is invalid, 16 MSB should be %#x (value is %#" PRIx64 ")"),
   1172  1.1.1.4  christos 	       reloc_data.input_section->owner,
   1173  1.1.1.4  christos 	       reloc_data.input_section,
   1174  1.1.1.5  christos 	       (uint64_t) reloc_data.reloc_offset,
   1175  1.1.1.4  christos 	       reloc_data.symbol_name,
   1176  1.1.1.5  christos 	       (uint64_t) reloc_data.reloc_addend,
   1177  1.1.1.4  christos 	       NPS_CMEM_HIGH_VALUE,
   1178  1.1.1.5  christos 	       (uint64_t) relocation);
   1179  1.1.1.4  christos 	  return bfd_reloc_overflow;
   1180  1.1.1.4  christos 	}
   1181  1.1.1.3  christos       break;
   1182  1.1.1.3  christos 
   1183  1.1.1.3  christos     default:
   1184  1.1.1.3  christos       break;
   1185  1.1.1.3  christos     }
   1186  1.1.1.2  christos 
   1187  1.1.1.3  christos   return bfd_reloc_ok;
   1188  1.1.1.3  christos }
   1189  1.1.1.3  christos 
   1190  1.1.1.3  christos #define ME(reloc) (reloc)
   1191  1.1.1.3  christos 
   1192  1.1.1.3  christos #define IS_ME(FORMULA,BFD) ((strstr (FORMULA, "ME") != NULL) \
   1193  1.1.1.3  christos 			    && (!bfd_big_endian (BFD)))
   1194  1.1.1.3  christos 
   1195  1.1.1.3  christos #define S ((bfd_signed_vma) (reloc_data.sym_value			\
   1196  1.1.1.3  christos 	   + (reloc_data.sym_section->output_section != NULL ?		\
   1197  1.1.1.3  christos 	      (reloc_data.sym_section->output_offset			\
   1198  1.1.1.3  christos 	       + reloc_data.sym_section->output_section->vma) : 0)))
   1199  1.1.1.3  christos #define L ((bfd_signed_vma) (reloc_data.sym_value			\
   1200  1.1.1.3  christos 	   + (reloc_data.sym_section->output_section != NULL ?		\
   1201  1.1.1.3  christos 	      (reloc_data.sym_section->output_offset			\
   1202  1.1.1.3  christos 	      + reloc_data.sym_section->output_section->vma) : 0)))
   1203  1.1.1.2  christos #define A (reloc_data.reloc_addend)
   1204  1.1.1.2  christos #define B (0)
   1205  1.1.1.2  christos #define G (reloc_data.got_offset_value)
   1206  1.1.1.3  christos #define GOT (reloc_data.got_symbol_vma)
   1207  1.1.1.3  christos #define GOT_BEGIN (htab->sgot->output_section->vma)
   1208  1.1.1.3  christos 
   1209  1.1.1.2  christos #define MES (0)
   1210  1.1.1.3  christos 	/* P: relative offset to PCL The offset should be to the
   1211  1.1.1.3  christos 	  current location aligned to 32 bits.  */
   1212  1.1.1.3  christos #define P ((bfd_signed_vma) (						\
   1213  1.1.1.3  christos 	   (								\
   1214  1.1.1.3  christos 	    (reloc_data.input_section->output_section != NULL ?		\
   1215  1.1.1.3  christos 	     reloc_data.input_section->output_section->vma : 0)		\
   1216  1.1.1.3  christos 	    + reloc_data.input_section->output_offset			\
   1217  1.1.1.3  christos 	    + (reloc_data.reloc_offset - (bitsize >= 32 ? 4 : 0)))	\
   1218  1.1.1.3  christos 	   & ~0x3))
   1219  1.1.1.3  christos #define PDATA ((bfd_signed_vma) ( \
   1220  1.1.1.2  christos 	    (reloc_data.input_section->output_section->vma \
   1221  1.1.1.2  christos 	     + reloc_data.input_section->output_offset \
   1222  1.1.1.3  christos 	     + (reloc_data.reloc_offset))))
   1223  1.1.1.3  christos #define SECTSTART (bfd_signed_vma) (reloc_data.sym_section->output_section->vma \
   1224  1.1.1.3  christos 				    + reloc_data.sym_section->output_offset)
   1225  1.1.1.6  christos #define FINAL_SECTSTART \
   1226  1.1.1.6  christos   (bfd_signed_vma) (reloc_data.sym_section->output_section->vma)
   1227  1.1.1.4  christos #define JLI (bfd_signed_vma) (reloc_data.sym_section->output_section->vma)
   1228  1.1.1.3  christos #define _SDA_BASE_ (bfd_signed_vma) (reloc_data.sdata_begin_symbol_vma)
   1229  1.1.1.8  christos #define TLS_REL (bfd_signed_vma)(tls_sec->output_section->vma)
   1230  1.1.1.8  christos #define TLS_TBSS (align_power (TCB_SIZE, tls_sec->alignment_power))
   1231  1.1.1.2  christos 
   1232  1.1.1.2  christos #define none (0)
   1233  1.1.1.2  christos 
   1234  1.1.1.4  christos #ifdef ARC_ENABLE_DEBUG
   1235  1.1.1.4  christos #define PRINT_DEBUG_RELOC_INFO_BEFORE(FORMULA, TYPE)			\
   1236  1.1.1.4  christos   do									\
   1237  1.1.1.4  christos     {									\
   1238  1.1.1.4  christos       asection *sym_section = reloc_data.sym_section;			\
   1239  1.1.1.4  christos       asection *input_section = reloc_data.input_section;		\
   1240  1.1.1.4  christos       ARC_DEBUG ("RELOC_TYPE = " TYPE "\n");				\
   1241  1.1.1.4  christos       ARC_DEBUG ("FORMULA = " FORMULA "\n");				\
   1242  1.1.1.4  christos       ARC_DEBUG ("S = %#lx\n", S);					\
   1243  1.1.1.4  christos       ARC_DEBUG ("A = %#lx\n", A);					\
   1244  1.1.1.4  christos       ARC_DEBUG ("L = %lx\n", L);					\
   1245  1.1.1.4  christos       if (sym_section->output_section != NULL)				\
   1246  1.1.1.4  christos 	ARC_DEBUG ("symbol_section->vma = %#lx\n",			\
   1247  1.1.1.4  christos 		   sym_section->output_section->vma			\
   1248  1.1.1.4  christos 		   + sym_section->output_offset);			\
   1249  1.1.1.4  christos       else								\
   1250  1.1.1.4  christos 	ARC_DEBUG ("symbol_section->vma = NULL\n");			\
   1251  1.1.1.4  christos       if (input_section->output_section != NULL)			\
   1252  1.1.1.7  christos 	ARC_DEBUG ("input_section->vma = %#lx\n",			\
   1253  1.1.1.4  christos 		   input_section->output_section->vma			\
   1254  1.1.1.4  christos 		   + input_section->output_offset);			\
   1255  1.1.1.4  christos       else								\
   1256  1.1.1.7  christos 	ARC_DEBUG ("input_section->vma = NULL\n");			\
   1257  1.1.1.4  christos       ARC_DEBUG ("PCL = %#lx\n", P);					\
   1258  1.1.1.4  christos       ARC_DEBUG ("P = %#lx\n", P);					\
   1259  1.1.1.4  christos       ARC_DEBUG ("G = %#lx\n", G);					\
   1260  1.1.1.4  christos       ARC_DEBUG ("SDA_OFFSET = %#lx\n", _SDA_BASE_);			\
   1261  1.1.1.3  christos       ARC_DEBUG ("SDA_SET = %d\n", reloc_data.sdata_begin_symbol_vma_set); \
   1262  1.1.1.4  christos       ARC_DEBUG ("GOT_OFFSET = %#lx\n", GOT);				\
   1263  1.1.1.4  christos       ARC_DEBUG ("relocation = %#08lx\n", relocation);			\
   1264  1.1.1.4  christos       ARC_DEBUG ("before = %#08x\n", (unsigned) insn);			\
   1265  1.1.1.4  christos       ARC_DEBUG ("data   = %08x (%u) (%d)\n", (unsigned) relocation,	\
   1266  1.1.1.4  christos 		 (unsigned) relocation, (int) relocation);		\
   1267  1.1.1.4  christos     }									\
   1268  1.1.1.4  christos   while (0)
   1269  1.1.1.4  christos 
   1270  1.1.1.4  christos #define PRINT_DEBUG_RELOC_INFO_AFTER				\
   1271  1.1.1.4  christos   do								\
   1272  1.1.1.4  christos     {								\
   1273  1.1.1.4  christos       ARC_DEBUG ("after  = 0x%08x\n", (unsigned int) insn);	\
   1274  1.1.1.4  christos     }								\
   1275  1.1.1.4  christos   while (0)
   1276  1.1.1.3  christos 
   1277  1.1.1.4  christos #else
   1278  1.1.1.4  christos 
   1279  1.1.1.4  christos #define PRINT_DEBUG_RELOC_INFO_BEFORE(...)
   1280  1.1.1.4  christos #define PRINT_DEBUG_RELOC_INFO_AFTER
   1281  1.1.1.4  christos 
   1282  1.1.1.4  christos #endif /* ARC_ENABLE_DEBUG */
   1283  1.1.1.3  christos 
   1284  1.1.1.2  christos #define ARC_RELOC_HOWTO(TYPE, VALUE, SIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
   1285  1.1.1.4  christos   case R_##TYPE:							\
   1286  1.1.1.4  christos     {									\
   1287  1.1.1.4  christos       bfd_signed_vma bitsize ATTRIBUTE_UNUSED = BITSIZE;		\
   1288  1.1.1.4  christos       relocation = FORMULA  ;						\
   1289  1.1.1.4  christos       PRINT_DEBUG_RELOC_INFO_BEFORE (#FORMULA, #TYPE);			\
   1290  1.1.1.4  christos       insn = middle_endian_convert (insn, IS_ME (#FORMULA, abfd));	\
   1291  1.1.1.4  christos       insn = (* get_replace_function (abfd, TYPE)) (insn, relocation);	\
   1292  1.1.1.4  christos       insn = middle_endian_convert (insn, IS_ME (#FORMULA, abfd));	\
   1293  1.1.1.4  christos       PRINT_DEBUG_RELOC_INFO_AFTER;					\
   1294  1.1.1.4  christos     }									\
   1295  1.1.1.2  christos     break;
   1296  1.1.1.2  christos 
   1297  1.1.1.2  christos static bfd_reloc_status_type
   1298  1.1.1.3  christos arc_do_relocation (bfd_byte * contents,
   1299  1.1.1.3  christos 		   struct arc_relocation_data reloc_data,
   1300  1.1.1.3  christos 		   struct bfd_link_info *info)
   1301  1.1.1.2  christos {
   1302  1.1.1.3  christos   bfd_signed_vma relocation = 0;
   1303  1.1.1.2  christos   bfd_vma insn;
   1304  1.1.1.2  christos   bfd_vma orig_insn ATTRIBUTE_UNUSED;
   1305  1.1.1.3  christos   bfd * abfd = reloc_data.input_section->owner;
   1306  1.1.1.3  christos   struct elf_link_hash_table *htab ATTRIBUTE_UNUSED = elf_hash_table (info);
   1307  1.1.1.3  christos   bfd_reloc_status_type flag;
   1308  1.1.1.8  christos   asection *tls_sec = htab->tls_sec;
   1309  1.1.1.2  christos 
   1310  1.1.1.4  christos   if (!reloc_data.should_relocate)
   1311  1.1.1.3  christos     return bfd_reloc_ok;
   1312  1.1.1.2  christos 
   1313  1.1.1.7  christos   switch (bfd_get_reloc_size (reloc_data.howto))
   1314  1.1.1.2  christos     {
   1315  1.1.1.7  christos     case 4:
   1316  1.1.1.6  christos       insn = arc_bfd_get_32 (abfd,
   1317  1.1.1.6  christos 			     contents + reloc_data.reloc_offset,
   1318  1.1.1.6  christos 			     reloc_data.input_section);
   1319  1.1.1.6  christos       break;
   1320  1.1.1.7  christos     case 2:
   1321  1.1.1.6  christos       insn = arc_bfd_get_16 (abfd,
   1322  1.1.1.6  christos 			     contents + reloc_data.reloc_offset,
   1323  1.1.1.6  christos 			     reloc_data.input_section);
   1324  1.1.1.6  christos       break;
   1325  1.1.1.7  christos     case 1:
   1326  1.1.1.6  christos       insn = arc_bfd_get_8 (abfd,
   1327  1.1.1.6  christos 			    contents + reloc_data.reloc_offset,
   1328  1.1.1.6  christos 			    reloc_data.input_section);
   1329  1.1.1.6  christos       break;
   1330  1.1.1.6  christos     default:
   1331  1.1.1.6  christos       insn = 0;
   1332  1.1.1.6  christos       BFD_ASSERT (0);
   1333  1.1.1.6  christos       break;
   1334  1.1.1.2  christos     }
   1335  1.1.1.2  christos 
   1336  1.1.1.2  christos   orig_insn = insn;
   1337  1.1.1.2  christos 
   1338  1.1.1.8  christos   /* If we resolve a TLS relocation, make sure we do have a valid TLS
   1339  1.1.1.8  christos      section.  */
   1340  1.1.1.8  christos   switch (reloc_data.howto->type)
   1341  1.1.1.8  christos     {
   1342  1.1.1.8  christos     case R_ARC_TLS_LE_32:
   1343  1.1.1.8  christos       if (tls_sec == NULL)
   1344  1.1.1.8  christos 	return bfd_reloc_notsupported;
   1345  1.1.1.8  christos       break;
   1346  1.1.1.8  christos 
   1347  1.1.1.8  christos     default:
   1348  1.1.1.8  christos       break;
   1349  1.1.1.8  christos     }
   1350  1.1.1.8  christos 
   1351  1.1.1.8  christos 
   1352  1.1.1.2  christos   switch (reloc_data.howto->type)
   1353  1.1.1.2  christos     {
   1354  1.1.1.3  christos #include "elf/arc-reloc.def"
   1355  1.1.1.2  christos 
   1356  1.1.1.6  christos     default:
   1357  1.1.1.6  christos       BFD_ASSERT (0);
   1358  1.1.1.6  christos       break;
   1359  1.1.1.2  christos     }
   1360  1.1.1.2  christos 
   1361  1.1.1.2  christos   /* Check for relocation overflow.  */
   1362  1.1.1.2  christos   if (reloc_data.howto->complain_on_overflow != complain_overflow_dont)
   1363  1.1.1.3  christos     flag = bfd_check_overflow (reloc_data.howto->complain_on_overflow,
   1364  1.1.1.4  christos 			       reloc_data.howto->bitsize,
   1365  1.1.1.4  christos 			       reloc_data.howto->rightshift,
   1366  1.1.1.4  christos 			       bfd_arch_bits_per_address (abfd),
   1367  1.1.1.4  christos 			       relocation);
   1368  1.1.1.3  christos   else
   1369  1.1.1.3  christos     flag = arc_special_overflow_checks (reloc_data, relocation, info);
   1370  1.1.1.2  christos 
   1371  1.1.1.3  christos   if (flag != bfd_reloc_ok)
   1372  1.1.1.3  christos     {
   1373  1.1.1.4  christos       ARC_DEBUG ("Relocation overflows !\n");
   1374  1.1.1.3  christos       DEBUG_ARC_RELOC (reloc_data);
   1375  1.1.1.4  christos       ARC_DEBUG ("Relocation value = signed -> %d, unsigned -> %u"
   1376  1.1.1.4  christos 		 ", hex -> (0x%08x)\n",
   1377  1.1.1.4  christos 		(int) relocation, (unsigned) relocation, (int) relocation);
   1378  1.1.1.2  christos 
   1379  1.1.1.3  christos       return flag;
   1380  1.1.1.2  christos     }
   1381  1.1.1.2  christos 
   1382  1.1.1.3  christos   /* Write updated instruction back to memory.  */
   1383  1.1.1.7  christos   switch (bfd_get_reloc_size (reloc_data.howto))
   1384  1.1.1.2  christos     {
   1385  1.1.1.7  christos     case 4:
   1386  1.1.1.6  christos       arc_bfd_put_32 (abfd, insn,
   1387  1.1.1.6  christos 		      contents + reloc_data.reloc_offset,
   1388  1.1.1.6  christos 		      reloc_data.input_section);
   1389  1.1.1.6  christos       break;
   1390  1.1.1.7  christos     case 2:
   1391  1.1.1.3  christos 	arc_bfd_put_16 (abfd, insn,
   1392  1.1.1.6  christos 			contents + reloc_data.reloc_offset,
   1393  1.1.1.6  christos 			reloc_data.input_section);
   1394  1.1.1.2  christos 	break;
   1395  1.1.1.7  christos     case 1:
   1396  1.1.1.6  christos       arc_bfd_put_8 (abfd, insn,
   1397  1.1.1.6  christos 		     contents + reloc_data.reloc_offset,
   1398  1.1.1.6  christos 		     reloc_data.input_section);
   1399  1.1.1.6  christos       break;
   1400  1.1.1.6  christos     default:
   1401  1.1.1.6  christos       ARC_DEBUG ("size = %d\n", reloc_data.howto->size);
   1402  1.1.1.6  christos       BFD_ASSERT (0);
   1403  1.1.1.6  christos       break;
   1404  1.1.1.2  christos     }
   1405  1.1.1.2  christos 
   1406  1.1.1.2  christos   return bfd_reloc_ok;
   1407  1.1.1.2  christos }
   1408  1.1.1.2  christos #undef S
   1409  1.1.1.2  christos #undef A
   1410  1.1.1.2  christos #undef B
   1411  1.1.1.2  christos #undef G
   1412  1.1.1.2  christos #undef GOT
   1413  1.1.1.2  christos #undef L
   1414  1.1.1.2  christos #undef MES
   1415  1.1.1.2  christos #undef P
   1416  1.1.1.2  christos #undef SECTSTAR
   1417  1.1.1.2  christos #undef SECTSTART
   1418  1.1.1.4  christos #undef JLI
   1419  1.1.1.2  christos #undef _SDA_BASE_
   1420  1.1.1.2  christos #undef none
   1421  1.1.1.2  christos 
   1422  1.1.1.2  christos #undef ARC_RELOC_HOWTO
   1423  1.1.1.2  christos 
   1424  1.1.1.2  christos 
   1425  1.1.1.2  christos /* Relocate an arc ELF section.
   1426  1.1.1.2  christos    Function : elf_arc_relocate_section
   1427  1.1.1.2  christos    Brief    : Relocate an arc section, by handling all the relocations
   1428  1.1.1.3  christos 	     appearing in that section.
   1429  1.1.1.2  christos    Args     : output_bfd    : The bfd being written to.
   1430  1.1.1.3  christos 	      info	    : Link information.
   1431  1.1.1.3  christos 	      input_bfd     : The input bfd.
   1432  1.1.1.3  christos 	      input_section : The section being relocated.
   1433  1.1.1.3  christos 	      contents	    : contents of the section being relocated.
   1434  1.1.1.3  christos 	      relocs	    : List of relocations in the section.
   1435  1.1.1.3  christos 	      local_syms    : is a pointer to the swapped in local symbols.
   1436  1.1.1.3  christos 	      local_section : is an array giving the section in the input file
   1437  1.1.1.3  christos 			      corresponding to the st_shndx field of each
   1438  1.1.1.3  christos 			      local symbol.  */
   1439  1.1.1.7  christos static int
   1440  1.1.1.4  christos elf_arc_relocate_section (bfd *			  output_bfd,
   1441  1.1.1.2  christos 			  struct bfd_link_info *  info,
   1442  1.1.1.4  christos 			  bfd *			  input_bfd,
   1443  1.1.1.4  christos 			  asection *		  input_section,
   1444  1.1.1.4  christos 			  bfd_byte *		  contents,
   1445  1.1.1.2  christos 			  Elf_Internal_Rela *     relocs,
   1446  1.1.1.2  christos 			  Elf_Internal_Sym *      local_syms,
   1447  1.1.1.4  christos 			  asection **		  local_sections)
   1448  1.1.1.2  christos {
   1449  1.1.1.4  christos   Elf_Internal_Shdr *		 symtab_hdr;
   1450  1.1.1.4  christos   struct elf_link_hash_entry **  sym_hashes;
   1451  1.1.1.4  christos   Elf_Internal_Rela *		 rel;
   1452  1.1.1.4  christos   Elf_Internal_Rela *		 wrel;
   1453  1.1.1.4  christos   Elf_Internal_Rela *		 relend;
   1454  1.1.1.4  christos   struct elf_link_hash_table *   htab = elf_hash_table (info);
   1455  1.1.1.2  christos 
   1456  1.1.1.2  christos   symtab_hdr = &((elf_tdata (input_bfd))->symtab_hdr);
   1457  1.1.1.2  christos   sym_hashes = elf_sym_hashes (input_bfd);
   1458  1.1.1.2  christos 
   1459  1.1.1.3  christos   rel = wrel = relocs;
   1460  1.1.1.2  christos   relend = relocs + input_section->reloc_count;
   1461  1.1.1.3  christos   for (; rel < relend; wrel++, rel++)
   1462  1.1.1.2  christos     {
   1463  1.1.1.7  christos       enum elf_arc_reloc_type r_type;
   1464  1.1.1.7  christos       reloc_howto_type *howto;
   1465  1.1.1.7  christos       unsigned long r_symndx;
   1466  1.1.1.7  christos       struct elf_link_hash_entry *h;
   1467  1.1.1.7  christos       Elf_Internal_Sym *sym;
   1468  1.1.1.7  christos       asection *sec;
   1469  1.1.1.7  christos       struct elf_link_hash_entry *h2;
   1470  1.1.1.7  christos       const char *msg;
   1471  1.1.1.7  christos       bool unresolved_reloc = false;
   1472  1.1.1.2  christos 
   1473  1.1.1.2  christos       struct arc_relocation_data reloc_data =
   1474  1.1.1.2  christos       {
   1475  1.1.1.3  christos 	.reloc_offset = 0,
   1476  1.1.1.3  christos 	.reloc_addend = 0,
   1477  1.1.1.3  christos 	.got_offset_value = 0,
   1478  1.1.1.4  christos 	.sym_value = 0,
   1479  1.1.1.3  christos 	.sym_section = NULL,
   1480  1.1.1.3  christos 	.howto = NULL,
   1481  1.1.1.3  christos 	.input_section = NULL,
   1482  1.1.1.3  christos 	.sdata_begin_symbol_vma = 0,
   1483  1.1.1.7  christos 	.sdata_begin_symbol_vma_set = false,
   1484  1.1.1.3  christos 	.got_symbol_vma = 0,
   1485  1.1.1.7  christos 	.should_relocate = false
   1486  1.1.1.2  christos       };
   1487  1.1.1.2  christos 
   1488  1.1.1.3  christos       r_type = ELF32_R_TYPE (rel->r_info);
   1489  1.1.1.3  christos 
   1490  1.1.1.3  christos       if (r_type >= (int) R_ARC_max)
   1491  1.1.1.3  christos 	{
   1492  1.1.1.3  christos 	  bfd_set_error (bfd_error_bad_value);
   1493  1.1.1.7  christos 	  return false;
   1494  1.1.1.3  christos 	}
   1495  1.1.1.3  christos       howto = arc_elf_howto (r_type);
   1496  1.1.1.3  christos 
   1497  1.1.1.3  christos       r_symndx = ELF32_R_SYM (rel->r_info);
   1498  1.1.1.3  christos 
   1499  1.1.1.3  christos       /* If we are generating another .o file and the symbol in not
   1500  1.1.1.3  christos 	 local, skip this relocation.  */
   1501  1.1.1.3  christos       if (bfd_link_relocatable (info))
   1502  1.1.1.3  christos 	{
   1503  1.1.1.3  christos 	  /* This is a relocateable link.  We don't have to change
   1504  1.1.1.3  christos 	     anything, unless the reloc is against a section symbol,
   1505  1.1.1.3  christos 	     in which case we have to adjust according to where the
   1506  1.1.1.3  christos 	     section symbol winds up in the output section.  */
   1507  1.1.1.3  christos 
   1508  1.1.1.3  christos 	  /* Checks if this is a local symbol and thus the reloc
   1509  1.1.1.3  christos 	     might (will??) be against a section symbol.  */
   1510  1.1.1.3  christos 	  if (r_symndx < symtab_hdr->sh_info)
   1511  1.1.1.3  christos 	    {
   1512  1.1.1.3  christos 	      sym = local_syms + r_symndx;
   1513  1.1.1.3  christos 	      if (ELF_ST_TYPE (sym->st_info) == STT_SECTION)
   1514  1.1.1.3  christos 		{
   1515  1.1.1.3  christos 		  sec = local_sections[r_symndx];
   1516  1.1.1.3  christos 
   1517  1.1.1.4  christos 		  /* For RELA relocs.  Just adjust the addend
   1518  1.1.1.3  christos 		     value in the relocation entry.  */
   1519  1.1.1.3  christos 		  rel->r_addend += sec->output_offset + sym->st_value;
   1520  1.1.1.3  christos 
   1521  1.1.1.4  christos 		  ARC_DEBUG ("local symbols reloc (section=%d %s) seen in %s\n",
   1522  1.1.1.4  christos 			     (int) r_symndx, local_sections[r_symndx]->name,
   1523  1.1.1.4  christos 			     __PRETTY_FUNCTION__);
   1524  1.1.1.3  christos 		}
   1525  1.1.1.3  christos 	    }
   1526  1.1.1.3  christos 	}
   1527  1.1.1.2  christos 
   1528  1.1.1.2  christos       h2 = elf_link_hash_lookup (elf_hash_table (info), "__SDATA_BEGIN__",
   1529  1.1.1.7  christos 				 false, false, true);
   1530  1.1.1.2  christos 
   1531  1.1.1.4  christos       if (!reloc_data.sdata_begin_symbol_vma_set
   1532  1.1.1.4  christos 	  && h2 != NULL && h2->root.type != bfd_link_hash_undefined
   1533  1.1.1.4  christos 	  && h2->root.u.def.section->output_section != NULL)
   1534  1.1.1.3  christos 	/* TODO: Verify this condition.  */
   1535  1.1.1.2  christos 	{
   1536  1.1.1.2  christos 	  reloc_data.sdata_begin_symbol_vma =
   1537  1.1.1.4  christos 	    (h2->root.u.def.value
   1538  1.1.1.4  christos 	     + h2->root.u.def.section->output_section->vma);
   1539  1.1.1.7  christos 	  reloc_data.sdata_begin_symbol_vma_set = true;
   1540  1.1.1.2  christos 	}
   1541  1.1.1.2  christos 
   1542  1.1.1.2  christos       reloc_data.input_section = input_section;
   1543  1.1.1.2  christos       reloc_data.howto = howto;
   1544  1.1.1.2  christos       reloc_data.reloc_offset = rel->r_offset;
   1545  1.1.1.2  christos       reloc_data.reloc_addend = rel->r_addend;
   1546  1.1.1.2  christos 
   1547  1.1.1.2  christos       /* This is a final link.  */
   1548  1.1.1.2  christos       h = NULL;
   1549  1.1.1.2  christos       sym = NULL;
   1550  1.1.1.2  christos       sec = NULL;
   1551  1.1.1.2  christos 
   1552  1.1.1.2  christos       if (r_symndx < symtab_hdr->sh_info) /* A local symbol.  */
   1553  1.1.1.2  christos 	{
   1554  1.1.1.2  christos 	  sym = local_syms + r_symndx;
   1555  1.1.1.2  christos 	  sec = local_sections[r_symndx];
   1556  1.1.1.2  christos 	}
   1557  1.1.1.3  christos       else
   1558  1.1.1.2  christos 	{
   1559  1.1.1.7  christos 	  bool warned, ignored;
   1560  1.1.1.4  christos 	  bfd_vma relocation ATTRIBUTE_UNUSED;
   1561  1.1.1.4  christos 
   1562  1.1.1.4  christos 	  RELOC_FOR_GLOBAL_SYMBOL (info, input_bfd, input_section, rel,
   1563  1.1.1.4  christos 				   r_symndx, symtab_hdr, sym_hashes,
   1564  1.1.1.4  christos 				   h, sec, relocation,
   1565  1.1.1.4  christos 				   unresolved_reloc, warned, ignored);
   1566  1.1.1.4  christos 
   1567  1.1.1.3  christos 	  /* TODO: This code is repeated from below.  We should
   1568  1.1.1.3  christos 	     clean it and remove duplications.
   1569  1.1.1.3  christos 	     Sec is used check for discarded sections.
   1570  1.1.1.3  christos 	     Need to redesign code below.  */
   1571  1.1.1.3  christos 
   1572  1.1.1.2  christos 	  /* Get the symbol's entry in the symtab.  */
   1573  1.1.1.2  christos 	  h = sym_hashes[r_symndx - symtab_hdr->sh_info];
   1574  1.1.1.2  christos 
   1575  1.1.1.2  christos 	  while (h->root.type == bfd_link_hash_indirect
   1576  1.1.1.2  christos 		 || h->root.type == bfd_link_hash_warning)
   1577  1.1.1.2  christos 	    h = (struct elf_link_hash_entry *) h->root.u.i.link;
   1578  1.1.1.2  christos 
   1579  1.1.1.2  christos 	  /* If we have encountered a definition for this symbol.  */
   1580  1.1.1.2  christos 	  if (h->root.type == bfd_link_hash_defined
   1581  1.1.1.2  christos 	      || h->root.type == bfd_link_hash_defweak)
   1582  1.1.1.2  christos 	    {
   1583  1.1.1.2  christos 	      reloc_data.sym_value = h->root.u.def.value;
   1584  1.1.1.3  christos 	      sec = h->root.u.def.section;
   1585  1.1.1.3  christos 	    }
   1586  1.1.1.3  christos 	}
   1587  1.1.1.2  christos 
   1588  1.1.1.3  christos       /* Clean relocs for symbols in discarded sections.  */
   1589  1.1.1.3  christos       if (sec != NULL && discarded_section (sec))
   1590  1.1.1.3  christos 	{
   1591  1.1.1.3  christos 	  _bfd_clear_contents (howto, input_bfd, input_section,
   1592  1.1.1.6  christos 			       contents, rel->r_offset);
   1593  1.1.1.3  christos 	  rel->r_info = 0;
   1594  1.1.1.3  christos 	  rel->r_addend = 0;
   1595  1.1.1.3  christos 
   1596  1.1.1.3  christos 	  /* For ld -r, remove relocations in debug sections against
   1597  1.1.1.3  christos 	     sections defined in discarded sections.  Not done for
   1598  1.1.1.3  christos 	     eh_frame editing code expects to be present.  */
   1599  1.1.1.3  christos 	   if (bfd_link_relocatable (info)
   1600  1.1.1.3  christos 	       && (input_section->flags & SEC_DEBUGGING))
   1601  1.1.1.3  christos 	     wrel--;
   1602  1.1.1.2  christos 
   1603  1.1.1.3  christos 	  continue;
   1604  1.1.1.3  christos 	}
   1605  1.1.1.2  christos 
   1606  1.1.1.3  christos       if (bfd_link_relocatable (info))
   1607  1.1.1.3  christos 	{
   1608  1.1.1.3  christos 	  if (wrel != rel)
   1609  1.1.1.3  christos 	    *wrel = *rel;
   1610  1.1.1.3  christos 	  continue;
   1611  1.1.1.3  christos 	}
   1612  1.1.1.2  christos 
   1613  1.1.1.3  christos       if (r_symndx < symtab_hdr->sh_info) /* A local symbol.  */
   1614  1.1.1.3  christos 	{
   1615  1.1.1.3  christos 	  reloc_data.sym_value = sym->st_value;
   1616  1.1.1.3  christos 	  reloc_data.sym_section = sec;
   1617  1.1.1.3  christos 	  reloc_data.symbol_name =
   1618  1.1.1.3  christos 	    bfd_elf_string_from_elf_section (input_bfd,
   1619  1.1.1.3  christos 					     symtab_hdr->sh_link,
   1620  1.1.1.3  christos 					     sym->st_name);
   1621  1.1.1.3  christos 
   1622  1.1.1.3  christos 	  /* Mergeable section handling.  */
   1623  1.1.1.3  christos 	  if ((sec->flags & SEC_MERGE)
   1624  1.1.1.3  christos 	      && ELF_ST_TYPE (sym->st_info) == STT_SECTION)
   1625  1.1.1.3  christos 	    {
   1626  1.1.1.3  christos 	      asection *msec;
   1627  1.1.1.3  christos 	      msec = sec;
   1628  1.1.1.3  christos 	      rel->r_addend = _bfd_elf_rel_local_sym (output_bfd, sym,
   1629  1.1.1.3  christos 						      &msec, rel->r_addend);
   1630  1.1.1.3  christos 	      rel->r_addend -= (sec->output_section->vma
   1631  1.1.1.3  christos 				+ sec->output_offset
   1632  1.1.1.3  christos 				+ sym->st_value);
   1633  1.1.1.3  christos 	      rel->r_addend += msec->output_section->vma + msec->output_offset;
   1634  1.1.1.3  christos 
   1635  1.1.1.3  christos 	      reloc_data.reloc_addend = rel->r_addend;
   1636  1.1.1.3  christos 	    }
   1637  1.1.1.3  christos 
   1638  1.1.1.3  christos 	  BFD_ASSERT (htab->sgot != NULL || !is_reloc_for_GOT (howto));
   1639  1.1.1.3  christos 	  if (htab->sgot != NULL)
   1640  1.1.1.3  christos 	    reloc_data.got_symbol_vma = htab->sgot->output_section->vma
   1641  1.1.1.3  christos 					+ htab->sgot->output_offset;
   1642  1.1.1.3  christos 
   1643  1.1.1.7  christos 	  reloc_data.should_relocate = true;
   1644  1.1.1.3  christos 	}
   1645  1.1.1.3  christos       else /* Global symbol.  */
   1646  1.1.1.3  christos 	{
   1647  1.1.1.4  christos 	  /* FIXME: We should use the RELOC_FOR_GLOBAL_SYMBOL macro
   1648  1.1.1.4  christos 	     (defined in elf-bfd.h) here.  */
   1649  1.1.1.4  christos 
   1650  1.1.1.3  christos 	  /* Get the symbol's entry in the symtab.  */
   1651  1.1.1.3  christos 	  h = sym_hashes[r_symndx - symtab_hdr->sh_info];
   1652  1.1.1.3  christos 
   1653  1.1.1.3  christos 	  while (h->root.type == bfd_link_hash_indirect
   1654  1.1.1.3  christos 		 || h->root.type == bfd_link_hash_warning)
   1655  1.1.1.4  christos 	  {
   1656  1.1.1.6  christos 	    struct elf_arc_link_hash_entry *ah_old =
   1657  1.1.1.6  christos 	      (struct elf_arc_link_hash_entry *) h;
   1658  1.1.1.3  christos 	    h = (struct elf_link_hash_entry *) h->root.u.i.link;
   1659  1.1.1.6  christos 	    struct elf_arc_link_hash_entry *ah =
   1660  1.1.1.6  christos 	      (struct elf_arc_link_hash_entry *) h;
   1661  1.1.1.6  christos 
   1662  1.1.1.6  christos 	    if (ah->got_ents == 0 && ah_old->got_ents != ah->got_ents)
   1663  1.1.1.6  christos 	      ah->got_ents = ah_old->got_ents;
   1664  1.1.1.4  christos 	  }
   1665  1.1.1.3  christos 
   1666  1.1.1.3  christos 	  /* TODO: Need to validate what was the intention.  */
   1667  1.1.1.3  christos 	  /* BFD_ASSERT ((h->dynindx == -1) || (h->forced_local != 0)); */
   1668  1.1.1.3  christos 	  reloc_data.symbol_name = h->root.root.string;
   1669  1.1.1.3  christos 
   1670  1.1.1.3  christos 	  /* If we have encountered a definition for this symbol.  */
   1671  1.1.1.3  christos 	  if (h->root.type == bfd_link_hash_defined
   1672  1.1.1.3  christos 	      || h->root.type == bfd_link_hash_defweak)
   1673  1.1.1.3  christos 	    {
   1674  1.1.1.3  christos 	      reloc_data.sym_value = h->root.u.def.value;
   1675  1.1.1.3  christos 	      reloc_data.sym_section = h->root.u.def.section;
   1676  1.1.1.3  christos 
   1677  1.1.1.7  christos 	      reloc_data.should_relocate = true;
   1678  1.1.1.3  christos 
   1679  1.1.1.3  christos 	      if (is_reloc_for_GOT (howto) && !bfd_link_pic (info))
   1680  1.1.1.3  christos 		{
   1681  1.1.1.6  christos 		  struct elf_arc_link_hash_entry *ah =
   1682  1.1.1.6  christos 		    (struct elf_arc_link_hash_entry *) h;
   1683  1.1.1.3  christos 		  /* TODO: Change it to use arc_do_relocation with
   1684  1.1.1.3  christos 		    ARC_32 reloc.  Try to use ADD_RELA macro.  */
   1685  1.1.1.3  christos 		  bfd_vma relocation =
   1686  1.1.1.3  christos 		    reloc_data.sym_value + reloc_data.reloc_addend
   1687  1.1.1.3  christos 		    + (reloc_data.sym_section->output_section != NULL ?
   1688  1.1.1.3  christos 			(reloc_data.sym_section->output_offset
   1689  1.1.1.3  christos 			 + reloc_data.sym_section->output_section->vma)
   1690  1.1.1.3  christos 		      : 0);
   1691  1.1.1.3  christos 
   1692  1.1.1.6  christos 		  BFD_ASSERT (ah->got_ents);
   1693  1.1.1.6  christos 		  bfd_vma got_offset = ah->got_ents->offset;
   1694  1.1.1.3  christos 		  bfd_put_32 (output_bfd, relocation,
   1695  1.1.1.3  christos 			      htab->sgot->contents + got_offset);
   1696  1.1.1.3  christos 		}
   1697  1.1.1.3  christos 	      if (is_reloc_for_PLT (howto) && h->plt.offset != (bfd_vma) -1)
   1698  1.1.1.3  christos 		{
   1699  1.1.1.3  christos 		  /* TODO: This is repeated up here.  */
   1700  1.1.1.3  christos 		  reloc_data.sym_value = h->plt.offset;
   1701  1.1.1.3  christos 		  reloc_data.sym_section = htab->splt;
   1702  1.1.1.3  christos 		}
   1703  1.1.1.3  christos 	    }
   1704  1.1.1.2  christos 	  else if (h->root.type == bfd_link_hash_undefweak)
   1705  1.1.1.2  christos 	    {
   1706  1.1.1.2  christos 	      /* Is weak symbol and has no definition.  */
   1707  1.1.1.3  christos 	      if (is_reloc_for_GOT (howto))
   1708  1.1.1.3  christos 		{
   1709  1.1.1.3  christos 		  reloc_data.sym_value = h->root.u.def.value;
   1710  1.1.1.3  christos 		  reloc_data.sym_section = htab->sgot;
   1711  1.1.1.7  christos 		  reloc_data.should_relocate = true;
   1712  1.1.1.3  christos 		}
   1713  1.1.1.3  christos 	      else if (is_reloc_for_PLT (howto)
   1714  1.1.1.3  christos 		       && h->plt.offset != (bfd_vma) -1)
   1715  1.1.1.3  christos 		{
   1716  1.1.1.3  christos 		  /* TODO: This is repeated up here.  */
   1717  1.1.1.3  christos 		  reloc_data.sym_value = h->plt.offset;
   1718  1.1.1.3  christos 		  reloc_data.sym_section = htab->splt;
   1719  1.1.1.7  christos 		  reloc_data.should_relocate = true;
   1720  1.1.1.3  christos 		}
   1721  1.1.1.3  christos 	      else
   1722  1.1.1.3  christos 		continue;
   1723  1.1.1.2  christos 	    }
   1724  1.1.1.2  christos 	  else
   1725  1.1.1.2  christos 	    {
   1726  1.1.1.2  christos 	      if (is_reloc_for_GOT (howto))
   1727  1.1.1.2  christos 		{
   1728  1.1.1.2  christos 		  reloc_data.sym_value = h->root.u.def.value;
   1729  1.1.1.3  christos 		  reloc_data.sym_section = htab->sgot;
   1730  1.1.1.2  christos 
   1731  1.1.1.7  christos 		  reloc_data.should_relocate = true;
   1732  1.1.1.2  christos 		}
   1733  1.1.1.2  christos 	      else if (is_reloc_for_PLT (howto))
   1734  1.1.1.2  christos 		{
   1735  1.1.1.3  christos 		  /* Fail if it is linking for PIE and the symbol is
   1736  1.1.1.3  christos 		     undefined.  */
   1737  1.1.1.3  christos 		  if (bfd_link_executable (info))
   1738  1.1.1.3  christos 		    (*info->callbacks->undefined_symbol)
   1739  1.1.1.3  christos 		      (info, h->root.root.string, input_bfd, input_section,
   1740  1.1.1.7  christos 		       rel->r_offset, true);
   1741  1.1.1.2  christos 		  reloc_data.sym_value = h->plt.offset;
   1742  1.1.1.3  christos 		  reloc_data.sym_section = htab->splt;
   1743  1.1.1.2  christos 
   1744  1.1.1.7  christos 		  reloc_data.should_relocate = true;
   1745  1.1.1.2  christos 		}
   1746  1.1.1.4  christos 	      else if (!bfd_link_pic (info) || bfd_link_executable (info))
   1747  1.1.1.3  christos 		(*info->callbacks->undefined_symbol)
   1748  1.1.1.3  christos 		  (info, h->root.root.string, input_bfd, input_section,
   1749  1.1.1.7  christos 		   rel->r_offset, true);
   1750  1.1.1.3  christos 	    }
   1751  1.1.1.3  christos 
   1752  1.1.1.4  christos 	  BFD_ASSERT (htab->sgot != NULL || !is_reloc_for_GOT (howto));
   1753  1.1.1.4  christos 	  if (htab->sgot != NULL)
   1754  1.1.1.4  christos 	    reloc_data.got_symbol_vma = htab->sgot->output_section->vma
   1755  1.1.1.4  christos 					+ htab->sgot->output_offset;
   1756  1.1.1.4  christos 	}
   1757  1.1.1.3  christos 
   1758  1.1.1.4  christos       if ((is_reloc_for_GOT (howto)
   1759  1.1.1.4  christos 	   || is_reloc_for_TLS (howto)))
   1760  1.1.1.4  christos 	{
   1761  1.1.1.7  christos 	  reloc_data.should_relocate = true;
   1762  1.1.1.3  christos 
   1763  1.1.1.4  christos 	  struct got_entry **list
   1764  1.1.1.6  christos 	    = get_got_entry_list_for_symbol (input_bfd, r_symndx, h);
   1765  1.1.1.3  christos 
   1766  1.1.1.4  christos 	  reloc_data.got_offset_value
   1767  1.1.1.4  christos 	    = relocate_fix_got_relocs_for_got_info (list,
   1768  1.1.1.4  christos 						    tls_type_for_reloc (howto),
   1769  1.1.1.4  christos 						    info,
   1770  1.1.1.4  christos 						    output_bfd,
   1771  1.1.1.4  christos 						    r_symndx,
   1772  1.1.1.4  christos 						    local_syms,
   1773  1.1.1.4  christos 						    local_sections,
   1774  1.1.1.4  christos 						    h,
   1775  1.1.1.4  christos 						    &reloc_data);
   1776  1.1.1.3  christos 
   1777  1.1.1.4  christos 	  if (h == NULL)
   1778  1.1.1.4  christos 	    {
   1779  1.1.1.4  christos 	      create_got_dynrelocs_for_single_entry (
   1780  1.1.1.4  christos 		  got_entry_for_type (list,
   1781  1.1.1.4  christos 				arc_got_entry_type_for_reloc (howto)),
   1782  1.1.1.4  christos 		  output_bfd, info, NULL);
   1783  1.1.1.2  christos 	    }
   1784  1.1.1.3  christos 	}
   1785  1.1.1.3  christos 
   1786  1.1.1.4  christos 
   1787  1.1.1.4  christos #define IS_ARC_PCREL_TYPE(TYPE) \
   1788  1.1.1.4  christos   (   (TYPE == R_ARC_PC32)      \
   1789  1.1.1.4  christos    || (TYPE == R_ARC_32_PCREL))
   1790  1.1.1.4  christos 
   1791  1.1.1.3  christos       switch (r_type)
   1792  1.1.1.3  christos 	{
   1793  1.1.1.3  christos 	  case R_ARC_32:
   1794  1.1.1.3  christos 	  case R_ARC_32_ME:
   1795  1.1.1.3  christos 	  case R_ARC_PC32:
   1796  1.1.1.3  christos 	  case R_ARC_32_PCREL:
   1797  1.1.1.4  christos 	    if (bfd_link_pic (info)
   1798  1.1.1.7  christos 		&& (input_section->flags & SEC_ALLOC) != 0
   1799  1.1.1.4  christos 		&& (!IS_ARC_PCREL_TYPE (r_type)
   1800  1.1.1.3  christos 		    || (h != NULL
   1801  1.1.1.3  christos 			&& h->dynindx != -1
   1802  1.1.1.4  christos 			&& !h->def_regular
   1803  1.1.1.3  christos 			&& (!info->symbolic || !h->def_regular))))
   1804  1.1.1.3  christos 	      {
   1805  1.1.1.3  christos 		Elf_Internal_Rela outrel;
   1806  1.1.1.3  christos 		bfd_byte *loc;
   1807  1.1.1.7  christos 		bool skip = false;
   1808  1.1.1.7  christos 		bool relocate = false;
   1809  1.1.1.3  christos 		asection *sreloc = _bfd_elf_get_dynamic_reloc_section
   1810  1.1.1.3  christos 				 (input_bfd, input_section,
   1811  1.1.1.7  christos 				  /*RELA*/ true);
   1812  1.1.1.3  christos 
   1813  1.1.1.3  christos 		BFD_ASSERT (sreloc != NULL);
   1814  1.1.1.3  christos 
   1815  1.1.1.3  christos 		outrel.r_offset = _bfd_elf_section_offset (output_bfd,
   1816  1.1.1.3  christos 							   info,
   1817  1.1.1.3  christos 							   input_section,
   1818  1.1.1.3  christos 							   rel->r_offset);
   1819  1.1.1.4  christos 
   1820  1.1.1.3  christos 		if (outrel.r_offset == (bfd_vma) -1)
   1821  1.1.1.7  christos 		  skip = true;
   1822  1.1.1.3  christos 
   1823  1.1.1.3  christos 		outrel.r_addend = rel->r_addend;
   1824  1.1.1.3  christos 		outrel.r_offset += (input_section->output_section->vma
   1825  1.1.1.3  christos 				    + input_section->output_offset);
   1826  1.1.1.3  christos 
   1827  1.1.1.3  christos 		if (skip)
   1828  1.1.1.3  christos 		  {
   1829  1.1.1.3  christos 		    memset (&outrel, 0, sizeof outrel);
   1830  1.1.1.7  christos 		    relocate = false;
   1831  1.1.1.3  christos 		  }
   1832  1.1.1.3  christos 		else if (h != NULL
   1833  1.1.1.3  christos 			 && h->dynindx != -1
   1834  1.1.1.4  christos 			 && (IS_ARC_PCREL_TYPE (r_type)
   1835  1.1.1.4  christos 			     || !(bfd_link_executable (info)
   1836  1.1.1.4  christos 				  || SYMBOLIC_BIND (info, h))
   1837  1.1.1.4  christos 			     || ! h->def_regular))
   1838  1.1.1.3  christos 		  {
   1839  1.1.1.3  christos 		    BFD_ASSERT (h != NULL);
   1840  1.1.1.3  christos 		    if ((input_section->flags & SEC_ALLOC) != 0)
   1841  1.1.1.7  christos 		      relocate = false;
   1842  1.1.1.3  christos 		    else
   1843  1.1.1.7  christos 		      relocate = true;
   1844  1.1.1.3  christos 
   1845  1.1.1.3  christos 		    BFD_ASSERT (h->dynindx != -1);
   1846  1.1.1.3  christos 		    outrel.r_info = ELF32_R_INFO (h->dynindx, r_type);
   1847  1.1.1.3  christos 		  }
   1848  1.1.1.3  christos 		else
   1849  1.1.1.3  christos 		  {
   1850  1.1.1.3  christos 		    /* Handle local symbols, they either do not have a
   1851  1.1.1.3  christos 		       global hash table entry (h == NULL), or are
   1852  1.1.1.3  christos 		       forced local due to a version script
   1853  1.1.1.3  christos 		       (h->forced_local), or the third condition is
   1854  1.1.1.3  christos 		       legacy, it appears to say something like, for
   1855  1.1.1.3  christos 		       links where we are pre-binding the symbols, or
   1856  1.1.1.3  christos 		       there's not an entry for this symbol in the
   1857  1.1.1.3  christos 		       dynamic symbol table, and it's a regular symbol
   1858  1.1.1.3  christos 		       not defined in a shared object, then treat the
   1859  1.1.1.3  christos 		       symbol as local, resolve it now.  */
   1860  1.1.1.7  christos 		    relocate = true;
   1861  1.1.1.3  christos 		    /* outrel.r_addend = 0; */
   1862  1.1.1.3  christos 		    outrel.r_info = ELF32_R_INFO (0, R_ARC_RELATIVE);
   1863  1.1.1.3  christos 		  }
   1864  1.1.1.3  christos 
   1865  1.1.1.3  christos 		BFD_ASSERT (sreloc->contents != 0);
   1866  1.1.1.3  christos 
   1867  1.1.1.3  christos 		loc = sreloc->contents;
   1868  1.1.1.3  christos 		loc += sreloc->reloc_count * sizeof (Elf32_External_Rela);
   1869  1.1.1.3  christos 		sreloc->reloc_count += 1;
   1870  1.1.1.3  christos 
   1871  1.1.1.3  christos 		bfd_elf32_swap_reloca_out (output_bfd, &outrel, loc);
   1872  1.1.1.3  christos 
   1873  1.1.1.4  christos 		if (!relocate)
   1874  1.1.1.3  christos 		  continue;
   1875  1.1.1.3  christos 	      }
   1876  1.1.1.3  christos 	    break;
   1877  1.1.1.3  christos 	  default:
   1878  1.1.1.3  christos 	    break;
   1879  1.1.1.2  christos 	}
   1880  1.1.1.2  christos 
   1881  1.1.1.3  christos       if (is_reloc_SDA_relative (howto)
   1882  1.1.1.4  christos 	  && !reloc_data.sdata_begin_symbol_vma_set)
   1883  1.1.1.2  christos 	{
   1884  1.1.1.4  christos 	  _bfd_error_handler
   1885  1.1.1.5  christos 	    ("error: linker symbol __SDATA_BEGIN__ not found");
   1886  1.1.1.2  christos 	  bfd_set_error (bfd_error_bad_value);
   1887  1.1.1.7  christos 	  return false;
   1888  1.1.1.2  christos 	}
   1889  1.1.1.2  christos 
   1890  1.1.1.2  christos       DEBUG_ARC_RELOC (reloc_data);
   1891  1.1.1.3  christos 
   1892  1.1.1.3  christos       /* Make sure we have with a dynamic linker.  In case of GOT and PLT
   1893  1.1.1.4  christos 	 the sym_section should point to .got or .plt respectively.  */
   1894  1.1.1.3  christos       if ((is_reloc_for_GOT (howto) || is_reloc_for_PLT (howto))
   1895  1.1.1.3  christos 	  && reloc_data.sym_section == NULL)
   1896  1.1.1.3  christos 	{
   1897  1.1.1.4  christos 	  _bfd_error_handler
   1898  1.1.1.5  christos 	    (_("GOT and PLT relocations cannot be fixed with a non dynamic linker"));
   1899  1.1.1.3  christos 	  bfd_set_error (bfd_error_bad_value);
   1900  1.1.1.7  christos 	  return false;
   1901  1.1.1.3  christos 	}
   1902  1.1.1.3  christos 
   1903  1.1.1.4  christos       msg = NULL;
   1904  1.1.1.4  christos       switch (arc_do_relocation (contents, reloc_data, info))
   1905  1.1.1.4  christos 	{
   1906  1.1.1.4  christos 	case bfd_reloc_ok:
   1907  1.1.1.4  christos 	  continue; /* The reloc processing loop.  */
   1908  1.1.1.2  christos 
   1909  1.1.1.4  christos 	case bfd_reloc_overflow:
   1910  1.1.1.4  christos 	  (*info->callbacks->reloc_overflow)
   1911  1.1.1.4  christos 	    (info, (h ? &h->root : NULL), reloc_data.symbol_name, howto->name, (bfd_vma) 0,
   1912  1.1.1.4  christos 	     input_bfd, input_section, rel->r_offset);
   1913  1.1.1.4  christos 	  break;
   1914  1.1.1.4  christos 
   1915  1.1.1.4  christos 	case bfd_reloc_undefined:
   1916  1.1.1.4  christos 	  (*info->callbacks->undefined_symbol)
   1917  1.1.1.7  christos 	    (info, reloc_data.symbol_name, input_bfd, input_section, rel->r_offset, true);
   1918  1.1.1.4  christos 	  break;
   1919  1.1.1.4  christos 
   1920  1.1.1.4  christos 	case bfd_reloc_other:
   1921  1.1.1.4  christos 	  /* xgettext:c-format */
   1922  1.1.1.5  christos 	  msg = _("%pB(%pA): warning: unaligned access to symbol '%s' in the small data area");
   1923  1.1.1.4  christos 	  break;
   1924  1.1.1.4  christos 
   1925  1.1.1.4  christos 	case bfd_reloc_outofrange:
   1926  1.1.1.4  christos 	  /* xgettext:c-format */
   1927  1.1.1.5  christos 	  msg = _("%pB(%pA): internal error: out of range error");
   1928  1.1.1.4  christos 	  break;
   1929  1.1.1.4  christos 
   1930  1.1.1.4  christos 	case bfd_reloc_notsupported:
   1931  1.1.1.4  christos 	  /* xgettext:c-format */
   1932  1.1.1.5  christos 	  msg = _("%pB(%pA): internal error: unsupported relocation error");
   1933  1.1.1.4  christos 	  break;
   1934  1.1.1.4  christos 
   1935  1.1.1.4  christos 	case bfd_reloc_dangerous:
   1936  1.1.1.4  christos 	  /* xgettext:c-format */
   1937  1.1.1.5  christos 	  msg = _("%pB(%pA): internal error: dangerous relocation");
   1938  1.1.1.4  christos 	  break;
   1939  1.1.1.4  christos 
   1940  1.1.1.4  christos 	default:
   1941  1.1.1.4  christos 	  /* xgettext:c-format */
   1942  1.1.1.5  christos 	  msg = _("%pB(%pA): internal error: unknown error");
   1943  1.1.1.4  christos 	  break;
   1944  1.1.1.4  christos 	}
   1945  1.1.1.3  christos 
   1946  1.1.1.4  christos       if (msg)
   1947  1.1.1.4  christos 	_bfd_error_handler (msg, input_bfd, input_section, reloc_data.symbol_name);
   1948  1.1.1.7  christos       return false;
   1949  1.1.1.3  christos     }
   1950  1.1.1.2  christos 
   1951  1.1.1.7  christos   return true;
   1952  1.1.1.2  christos }
   1953  1.1.1.2  christos 
   1954  1.1.1.4  christos #define elf_arc_hash_table(p) \
   1955  1.1.1.7  christos   ((is_elf_hash_table ((p)->hash)					\
   1956  1.1.1.7  christos     && elf_hash_table_id (elf_hash_table (p)) == ARC_ELF_DATA)		\
   1957  1.1.1.7  christos    ? (struct elf_arc_link_hash_table *) (p)->hash : NULL)
   1958  1.1.1.2  christos 
   1959  1.1.1.7  christos static bool
   1960  1.1.1.4  christos elf_arc_check_relocs (bfd *			 abfd,
   1961  1.1.1.2  christos 		      struct bfd_link_info *     info,
   1962  1.1.1.3  christos 		      asection *		 sec,
   1963  1.1.1.2  christos 		      const Elf_Internal_Rela *  relocs)
   1964  1.1.1.2  christos {
   1965  1.1.1.3  christos   Elf_Internal_Shdr *		symtab_hdr;
   1966  1.1.1.3  christos   struct elf_link_hash_entry **	sym_hashes;
   1967  1.1.1.3  christos   const Elf_Internal_Rela *	rel;
   1968  1.1.1.3  christos   const Elf_Internal_Rela *	rel_end;
   1969  1.1.1.3  christos   bfd *				dynobj;
   1970  1.1.1.3  christos   asection *			sreloc = NULL;
   1971  1.1.1.4  christos   struct elf_link_hash_table *	htab = elf_hash_table (info);
   1972  1.1.1.3  christos 
   1973  1.1.1.3  christos   if (bfd_link_relocatable (info))
   1974  1.1.1.7  christos     return true;
   1975  1.1.1.2  christos 
   1976  1.1.1.4  christos   if (htab->dynobj == NULL)
   1977  1.1.1.4  christos     htab->dynobj = abfd;
   1978  1.1.1.4  christos 
   1979  1.1.1.2  christos   dynobj = (elf_hash_table (info))->dynobj;
   1980  1.1.1.2  christos   symtab_hdr = &((elf_tdata (abfd))->symtab_hdr);
   1981  1.1.1.2  christos   sym_hashes = elf_sym_hashes (abfd);
   1982  1.1.1.2  christos 
   1983  1.1.1.2  christos   rel_end = relocs + sec->reloc_count;
   1984  1.1.1.2  christos   for (rel = relocs; rel < rel_end; rel++)
   1985  1.1.1.2  christos     {
   1986  1.1.1.2  christos       enum elf_arc_reloc_type r_type;
   1987  1.1.1.2  christos       reloc_howto_type *howto;
   1988  1.1.1.2  christos       unsigned long   r_symndx;
   1989  1.1.1.2  christos       struct elf_link_hash_entry *h;
   1990  1.1.1.2  christos 
   1991  1.1.1.2  christos       r_type = ELF32_R_TYPE (rel->r_info);
   1992  1.1.1.2  christos 
   1993  1.1.1.2  christos       if (r_type >= (int) R_ARC_max)
   1994  1.1.1.2  christos 	{
   1995  1.1.1.2  christos 	  bfd_set_error (bfd_error_bad_value);
   1996  1.1.1.7  christos 	  return false;
   1997  1.1.1.2  christos 	}
   1998  1.1.1.3  christos       howto = arc_elf_howto (r_type);
   1999  1.1.1.3  christos 
   2000  1.1.1.2  christos       /* Load symbol information.  */
   2001  1.1.1.2  christos       r_symndx = ELF32_R_SYM (rel->r_info);
   2002  1.1.1.2  christos       if (r_symndx < symtab_hdr->sh_info) /* Is a local symbol.  */
   2003  1.1.1.2  christos 	h = NULL;
   2004  1.1.1.2  christos       else /* Global one.  */
   2005  1.1.1.6  christos 	{
   2006  1.1.1.6  christos 	  h = sym_hashes[r_symndx - symtab_hdr->sh_info];
   2007  1.1.1.6  christos 	  while (h->root.type == bfd_link_hash_indirect
   2008  1.1.1.6  christos 		 || h->root.type == bfd_link_hash_warning)
   2009  1.1.1.6  christos 	    h = (struct elf_link_hash_entry *) h->root.u.i.link;
   2010  1.1.1.6  christos 	}
   2011  1.1.1.6  christos 
   2012  1.1.1.2  christos 
   2013  1.1.1.3  christos       switch (r_type)
   2014  1.1.1.3  christos 	{
   2015  1.1.1.6  christos 	case R_ARC_32:
   2016  1.1.1.6  christos 	case R_ARC_32_ME:
   2017  1.1.1.6  christos 	  /* During shared library creation, these relocs should not
   2018  1.1.1.6  christos 	     appear in a shared library (as memory will be read only
   2019  1.1.1.6  christos 	     and the dynamic linker can not resolve these.  However
   2020  1.1.1.6  christos 	     the error should not occur for e.g. debugging or
   2021  1.1.1.6  christos 	     non-readonly sections.  */
   2022  1.1.1.6  christos 	  if (h != NULL
   2023  1.1.1.6  christos 	      && (bfd_link_dll (info) && !bfd_link_pie (info))
   2024  1.1.1.6  christos 	      && (sec->flags & SEC_ALLOC) != 0
   2025  1.1.1.6  christos 	      && (sec->flags & SEC_READONLY) != 0
   2026  1.1.1.6  christos 	      && ((sec->flags & SEC_CODE) != 0
   2027  1.1.1.6  christos 		  || (sec->flags & SEC_DEBUGGING) != 0))
   2028  1.1.1.6  christos 	    {
   2029  1.1.1.6  christos 	      const char *name;
   2030  1.1.1.6  christos 	      if (h)
   2031  1.1.1.6  christos 		name = h->root.root.string;
   2032  1.1.1.6  christos 	      else
   2033  1.1.1.6  christos 		name = "UNKNOWN";
   2034  1.1.1.6  christos 	      _bfd_error_handler
   2035  1.1.1.6  christos 	      /* xgettext:c-format */
   2036  1.1.1.6  christos 	      (_("%pB: relocation %s against `%s' can not be used"
   2037  1.1.1.6  christos 		 " when making a shared object; recompile with -fPIC"),
   2038  1.1.1.6  christos 		 abfd,
   2039  1.1.1.6  christos 		 arc_elf_howto (r_type)->name,
   2040  1.1.1.6  christos 		 name);
   2041  1.1.1.6  christos 	      bfd_set_error (bfd_error_bad_value);
   2042  1.1.1.7  christos 	      return false;
   2043  1.1.1.6  christos 	    }
   2044  1.1.1.3  christos 
   2045  1.1.1.3  christos 	    /* In some cases we are not setting the 'non_got_ref'
   2046  1.1.1.3  christos 	       flag, even though the relocations don't require a GOT
   2047  1.1.1.3  christos 	       access.  We should extend the testing in this area to
   2048  1.1.1.3  christos 	       ensure that no significant cases are being missed.  */
   2049  1.1.1.3  christos 	    if (h)
   2050  1.1.1.3  christos 	      h->non_got_ref = 1;
   2051  1.1.1.3  christos 	    /* FALLTHROUGH */
   2052  1.1.1.3  christos 	  case R_ARC_PC32:
   2053  1.1.1.3  christos 	  case R_ARC_32_PCREL:
   2054  1.1.1.4  christos 	    if ((bfd_link_pic (info))
   2055  1.1.1.3  christos 		&& ((r_type != R_ARC_PC32 && r_type != R_ARC_32_PCREL)
   2056  1.1.1.3  christos 		    || (h != NULL
   2057  1.1.1.3  christos 			&& (!info->symbolic || !h->def_regular))))
   2058  1.1.1.3  christos 	      {
   2059  1.1.1.3  christos 		if (sreloc == NULL)
   2060  1.1.1.3  christos 		  {
   2061  1.1.1.4  christos 		    if (info->dynamic
   2062  1.1.1.4  christos 			&& ! htab->dynamic_sections_created
   2063  1.1.1.4  christos 			&& ! _bfd_elf_link_create_dynamic_sections (abfd, info))
   2064  1.1.1.7  christos 		      return false;
   2065  1.1.1.3  christos 		    sreloc = _bfd_elf_make_dynamic_reloc_section (sec, dynobj,
   2066  1.1.1.3  christos 								  2, abfd,
   2067  1.1.1.3  christos 								  /*rela*/
   2068  1.1.1.7  christos 								  true);
   2069  1.1.1.3  christos 
   2070  1.1.1.3  christos 		    if (sreloc == NULL)
   2071  1.1.1.7  christos 		      return false;
   2072  1.1.1.3  christos 		  }
   2073  1.1.1.3  christos 		sreloc->size += sizeof (Elf32_External_Rela);
   2074  1.1.1.3  christos 
   2075  1.1.1.3  christos 	      }
   2076  1.1.1.3  christos 	  default:
   2077  1.1.1.3  christos 	    break;
   2078  1.1.1.3  christos 	}
   2079  1.1.1.3  christos 
   2080  1.1.1.4  christos       if (is_reloc_for_PLT (howto))
   2081  1.1.1.2  christos 	{
   2082  1.1.1.2  christos 	  if (h == NULL)
   2083  1.1.1.2  christos 	    continue;
   2084  1.1.1.2  christos 	  else
   2085  1.1.1.6  christos 	    if (h->forced_local == 0)
   2086  1.1.1.6  christos 	      h->needs_plt = 1;
   2087  1.1.1.2  christos 	}
   2088  1.1.1.2  christos 
   2089  1.1.1.4  christos       /* Add info to the symbol got_entry_list.  */
   2090  1.1.1.4  christos       if (is_reloc_for_GOT (howto)
   2091  1.1.1.4  christos 	  || is_reloc_for_TLS (howto))
   2092  1.1.1.3  christos 	{
   2093  1.1.1.6  christos 	  if (bfd_link_dll (info) && !bfd_link_pie (info)
   2094  1.1.1.6  christos 	      && (r_type == R_ARC_TLS_LE_32 || r_type == R_ARC_TLS_LE_S9))
   2095  1.1.1.6  christos 	    {
   2096  1.1.1.6  christos 	      const char *name;
   2097  1.1.1.6  christos 	      if (h)
   2098  1.1.1.6  christos 		name = h->root.root.string;
   2099  1.1.1.6  christos 	      else
   2100  1.1.1.6  christos 		/* bfd_elf_sym_name (abfd, symtab_hdr, isym, NULL);  */
   2101  1.1.1.6  christos 		name = "UNKNOWN";
   2102  1.1.1.6  christos 	      _bfd_error_handler
   2103  1.1.1.6  christos 		/* xgettext:c-format */
   2104  1.1.1.6  christos 		(_("%pB: relocation %s against `%s' can not be used"
   2105  1.1.1.6  christos 		   " when making a shared object; recompile with -fPIC"),
   2106  1.1.1.6  christos 		   abfd,
   2107  1.1.1.6  christos 		   arc_elf_howto (r_type)->name,
   2108  1.1.1.6  christos 		   name);
   2109  1.1.1.6  christos 	      bfd_set_error (bfd_error_bad_value);
   2110  1.1.1.7  christos 	      return false;
   2111  1.1.1.6  christos 	    }
   2112  1.1.1.4  christos 	  if (! _bfd_elf_create_got_section (dynobj, info))
   2113  1.1.1.7  christos 	    return false;
   2114  1.1.1.2  christos 
   2115  1.1.1.4  christos 	  arc_fill_got_info_for_reloc (
   2116  1.1.1.4  christos 		  arc_got_entry_type_for_reloc (howto),
   2117  1.1.1.4  christos 		  get_got_entry_list_for_symbol (abfd, r_symndx, h),
   2118  1.1.1.4  christos 		  info,
   2119  1.1.1.4  christos 		  h);
   2120  1.1.1.3  christos 	}
   2121  1.1.1.3  christos     }
   2122  1.1.1.2  christos 
   2123  1.1.1.7  christos   return true;
   2124  1.1.1.3  christos }
   2125  1.1.1.2  christos 
   2126  1.1.1.3  christos #define ELF_DYNAMIC_INTERPRETER  "/sbin/ld-uClibc.so"
   2127  1.1.1.2  christos 
   2128  1.1.1.7  christos static const struct plt_version_t *
   2129  1.1.1.3  christos arc_get_plt_version (struct bfd_link_info *info)
   2130  1.1.1.2  christos {
   2131  1.1.1.3  christos   int i;
   2132  1.1.1.2  christos 
   2133  1.1.1.3  christos   for (i = 0; i < 1; i++)
   2134  1.1.1.3  christos     {
   2135  1.1.1.3  christos       ARC_DEBUG ("%d: size1 = %d, size2 = %d\n", i,
   2136  1.1.1.4  christos 		 (int) plt_versions[i].entry_size,
   2137  1.1.1.4  christos 		 (int) plt_versions[i].elem_size);
   2138  1.1.1.3  christos     }
   2139  1.1.1.2  christos 
   2140  1.1.1.3  christos   if (bfd_get_mach (info->output_bfd) == bfd_mach_arc_arcv2)
   2141  1.1.1.2  christos     {
   2142  1.1.1.3  christos       if (bfd_link_pic (info))
   2143  1.1.1.3  christos 	return &(plt_versions[ELF_ARCV2_PIC]);
   2144  1.1.1.3  christos       else
   2145  1.1.1.3  christos 	return &(plt_versions[ELF_ARCV2_ABS]);
   2146  1.1.1.3  christos     }
   2147  1.1.1.3  christos   else
   2148  1.1.1.2  christos     {
   2149  1.1.1.3  christos       if (bfd_link_pic (info))
   2150  1.1.1.3  christos 	return &(plt_versions[ELF_ARC_PIC]);
   2151  1.1.1.3  christos       else
   2152  1.1.1.3  christos 	return &(plt_versions[ELF_ARC_ABS]);
   2153  1.1.1.2  christos     }
   2154  1.1.1.2  christos }
   2155  1.1.1.2  christos 
   2156  1.1.1.2  christos static bfd_vma
   2157  1.1.1.2  christos add_symbol_to_plt (struct bfd_link_info *info)
   2158  1.1.1.2  christos {
   2159  1.1.1.3  christos   struct elf_link_hash_table *htab = elf_hash_table (info);
   2160  1.1.1.2  christos   bfd_vma ret;
   2161  1.1.1.2  christos 
   2162  1.1.1.7  christos   const struct plt_version_t *plt_data = arc_get_plt_version (info);
   2163  1.1.1.3  christos 
   2164  1.1.1.3  christos   /* If this is the first .plt entry, make room for the special first
   2165  1.1.1.3  christos      entry.  */
   2166  1.1.1.3  christos   if (htab->splt->size == 0)
   2167  1.1.1.3  christos     htab->splt->size += plt_data->entry_size;
   2168  1.1.1.3  christos 
   2169  1.1.1.3  christos   ret = htab->splt->size;
   2170  1.1.1.3  christos 
   2171  1.1.1.3  christos   htab->splt->size += plt_data->elem_size;
   2172  1.1.1.4  christos   ARC_DEBUG ("PLT_SIZE = %d\n", (int) htab->splt->size);
   2173  1.1.1.3  christos 
   2174  1.1.1.3  christos   htab->sgotplt->size += 4;
   2175  1.1.1.3  christos   htab->srelplt->size += sizeof (Elf32_External_Rela);
   2176  1.1.1.2  christos 
   2177  1.1.1.2  christos   return ret;
   2178  1.1.1.2  christos }
   2179  1.1.1.2  christos 
   2180  1.1.1.3  christos #define PLT_DO_RELOCS_FOR_ENTRY(ABFD, DS, RELOCS)	\
   2181  1.1.1.3  christos   plt_do_relocs_for_symbol (ABFD, DS, RELOCS, 0, 0)
   2182  1.1.1.2  christos 
   2183  1.1.1.2  christos static void
   2184  1.1.1.3  christos plt_do_relocs_for_symbol (bfd *abfd,
   2185  1.1.1.3  christos 			  struct elf_link_hash_table *htab,
   2186  1.1.1.3  christos 			  const struct plt_reloc *reloc,
   2187  1.1.1.2  christos 			  bfd_vma plt_offset,
   2188  1.1.1.2  christos 			  bfd_vma symbol_got_offset)
   2189  1.1.1.2  christos {
   2190  1.1.1.2  christos   while (SYM_ONLY (reloc->symbol) != LAST_RELOC)
   2191  1.1.1.2  christos     {
   2192  1.1.1.2  christos       bfd_vma relocation = 0;
   2193  1.1.1.2  christos 
   2194  1.1.1.2  christos       switch (SYM_ONLY (reloc->symbol))
   2195  1.1.1.2  christos 	{
   2196  1.1.1.2  christos 	  case SGOT:
   2197  1.1.1.4  christos 		relocation
   2198  1.1.1.4  christos 		  = htab->sgotplt->output_section->vma
   2199  1.1.1.4  christos 		    + htab->sgotplt->output_offset + symbol_got_offset;
   2200  1.1.1.2  christos 		break;
   2201  1.1.1.2  christos 	}
   2202  1.1.1.2  christos       relocation += reloc->addend;
   2203  1.1.1.2  christos 
   2204  1.1.1.3  christos       if (IS_RELATIVE (reloc->symbol))
   2205  1.1.1.3  christos 	{
   2206  1.1.1.3  christos 	  bfd_vma reloc_offset = reloc->offset;
   2207  1.1.1.3  christos 	  reloc_offset -= (IS_INSN_32 (reloc->symbol)) ? 4 : 0;
   2208  1.1.1.3  christos 	  reloc_offset -= (IS_INSN_24 (reloc->symbol)) ? 2 : 0;
   2209  1.1.1.2  christos 
   2210  1.1.1.3  christos 	  relocation -= htab->splt->output_section->vma
   2211  1.1.1.3  christos 			 + htab->splt->output_offset
   2212  1.1.1.3  christos 			 + plt_offset + reloc_offset;
   2213  1.1.1.3  christos 	}
   2214  1.1.1.3  christos 
   2215  1.1.1.3  christos       /* TODO: being ME is not a property of the relocation but of the
   2216  1.1.1.3  christos 	 section of which is applying the relocation. */
   2217  1.1.1.3  christos       if (IS_MIDDLE_ENDIAN (reloc->symbol) && !bfd_big_endian (abfd))
   2218  1.1.1.2  christos 	{
   2219  1.1.1.4  christos 	  relocation
   2220  1.1.1.4  christos 	    = ((relocation & 0xffff0000) >> 16)
   2221  1.1.1.4  christos 	      | ((relocation & 0xffff) << 16);
   2222  1.1.1.2  christos 	}
   2223  1.1.1.2  christos 
   2224  1.1.1.2  christos       switch (reloc->size)
   2225  1.1.1.2  christos 	{
   2226  1.1.1.2  christos 	  case 32:
   2227  1.1.1.3  christos 	    bfd_put_32 (htab->splt->output_section->owner,
   2228  1.1.1.2  christos 			relocation,
   2229  1.1.1.3  christos 			htab->splt->contents + plt_offset + reloc->offset);
   2230  1.1.1.2  christos 	    break;
   2231  1.1.1.2  christos 	}
   2232  1.1.1.2  christos 
   2233  1.1.1.3  christos       reloc = &(reloc[1]); /* Jump to next relocation.  */
   2234  1.1.1.2  christos     }
   2235  1.1.1.2  christos }
   2236  1.1.1.2  christos 
   2237  1.1.1.2  christos static void
   2238  1.1.1.3  christos relocate_plt_for_symbol (bfd *output_bfd,
   2239  1.1.1.3  christos 			 struct bfd_link_info *info,
   2240  1.1.1.2  christos 			 struct elf_link_hash_entry *h)
   2241  1.1.1.2  christos {
   2242  1.1.1.7  christos   const struct plt_version_t *plt_data = arc_get_plt_version (info);
   2243  1.1.1.3  christos   struct elf_link_hash_table *htab = elf_hash_table (info);
   2244  1.1.1.2  christos 
   2245  1.1.1.3  christos   bfd_vma plt_index = (h->plt.offset  - plt_data->entry_size)
   2246  1.1.1.3  christos 		      / plt_data->elem_size;
   2247  1.1.1.2  christos   bfd_vma got_offset = (plt_index + 3) * 4;
   2248  1.1.1.2  christos 
   2249  1.1.1.4  christos   ARC_DEBUG ("arc_info: PLT_OFFSET = %#lx, PLT_ENTRY_VMA = %#lx, \
   2250  1.1.1.4  christos GOT_ENTRY_OFFSET = %#lx, GOT_ENTRY_VMA = %#lx, for symbol %s\n",
   2251  1.1.1.4  christos 	     (long) h->plt.offset,
   2252  1.1.1.4  christos 	     (long) (htab->splt->output_section->vma
   2253  1.1.1.4  christos 		     + htab->splt->output_offset
   2254  1.1.1.4  christos 		     + h->plt.offset),
   2255  1.1.1.4  christos 	     (long) got_offset,
   2256  1.1.1.4  christos 	     (long) (htab->sgotplt->output_section->vma
   2257  1.1.1.4  christos 		     + htab->sgotplt->output_offset
   2258  1.1.1.4  christos 		     + got_offset),
   2259  1.1.1.3  christos 	     h->root.root.string);
   2260  1.1.1.3  christos 
   2261  1.1.1.3  christos   {
   2262  1.1.1.3  christos     bfd_vma i = 0;
   2263  1.1.1.3  christos     uint16_t *ptr = (uint16_t *) plt_data->elem;
   2264  1.1.1.4  christos 
   2265  1.1.1.3  christos     for (i = 0; i < plt_data->elem_size/2; i++)
   2266  1.1.1.3  christos       {
   2267  1.1.1.3  christos 	uint16_t data = ptr[i];
   2268  1.1.1.3  christos 	bfd_put_16 (output_bfd,
   2269  1.1.1.3  christos 		    (bfd_vma) data,
   2270  1.1.1.3  christos 		    htab->splt->contents + h->plt.offset + (i*2));
   2271  1.1.1.3  christos       }
   2272  1.1.1.3  christos   }
   2273  1.1.1.3  christos 
   2274  1.1.1.3  christos   plt_do_relocs_for_symbol (output_bfd, htab,
   2275  1.1.1.3  christos 			    plt_data->elem_relocs,
   2276  1.1.1.3  christos 			    h->plt.offset,
   2277  1.1.1.2  christos 			    got_offset);
   2278  1.1.1.3  christos 
   2279  1.1.1.3  christos   /* Fill in the entry in the global offset table.  */
   2280  1.1.1.3  christos   bfd_put_32 (output_bfd,
   2281  1.1.1.3  christos 	      (bfd_vma) (htab->splt->output_section->vma
   2282  1.1.1.3  christos 			 + htab->splt->output_offset),
   2283  1.1.1.3  christos 	      htab->sgotplt->contents + got_offset);
   2284  1.1.1.3  christos 
   2285  1.1.1.3  christos   /* TODO: Fill in the entry in the .rela.plt section.  */
   2286  1.1.1.3  christos   {
   2287  1.1.1.3  christos     Elf_Internal_Rela rel;
   2288  1.1.1.3  christos     bfd_byte *loc;
   2289  1.1.1.3  christos 
   2290  1.1.1.3  christos     rel.r_offset = (htab->sgotplt->output_section->vma
   2291  1.1.1.3  christos 		    + htab->sgotplt->output_offset
   2292  1.1.1.3  christos 		    + got_offset);
   2293  1.1.1.3  christos     rel.r_addend = 0;
   2294  1.1.1.3  christos 
   2295  1.1.1.3  christos     BFD_ASSERT (h->dynindx != -1);
   2296  1.1.1.3  christos     rel.r_info = ELF32_R_INFO (h->dynindx, R_ARC_JMP_SLOT);
   2297  1.1.1.3  christos 
   2298  1.1.1.3  christos     loc = htab->srelplt->contents;
   2299  1.1.1.3  christos     loc += plt_index * sizeof (Elf32_External_Rela); /* relA */
   2300  1.1.1.3  christos     bfd_elf32_swap_reloca_out (output_bfd, &rel, loc);
   2301  1.1.1.3  christos   }
   2302  1.1.1.2  christos }
   2303  1.1.1.2  christos 
   2304  1.1.1.2  christos static void
   2305  1.1.1.3  christos relocate_plt_for_entry (bfd *abfd,
   2306  1.1.1.3  christos 			struct bfd_link_info *info)
   2307  1.1.1.2  christos {
   2308  1.1.1.7  christos   const struct plt_version_t *plt_data = arc_get_plt_version (info);
   2309  1.1.1.3  christos   struct elf_link_hash_table *htab = elf_hash_table (info);
   2310  1.1.1.2  christos 
   2311  1.1.1.3  christos   {
   2312  1.1.1.3  christos     bfd_vma i = 0;
   2313  1.1.1.3  christos     uint16_t *ptr = (uint16_t *) plt_data->entry;
   2314  1.1.1.3  christos     for (i = 0; i < plt_data->entry_size/2; i++)
   2315  1.1.1.3  christos       {
   2316  1.1.1.3  christos 	uint16_t data = ptr[i];
   2317  1.1.1.3  christos 	bfd_put_16 (abfd,
   2318  1.1.1.3  christos 		    (bfd_vma) data,
   2319  1.1.1.3  christos 		    htab->splt->contents + (i*2));
   2320  1.1.1.3  christos       }
   2321  1.1.1.3  christos   }
   2322  1.1.1.3  christos   PLT_DO_RELOCS_FOR_ENTRY (abfd, htab, plt_data->entry_relocs);
   2323  1.1.1.2  christos }
   2324  1.1.1.2  christos 
   2325  1.1.1.3  christos /* Desc : Adjust a symbol defined by a dynamic object and referenced
   2326  1.1.1.3  christos    by a regular object.  The current definition is in some section of
   2327  1.1.1.3  christos    the dynamic object, but we're not including those sections.  We
   2328  1.1.1.3  christos    have to change the definition to something the rest of the link can
   2329  1.1.1.2  christos    understand.  */
   2330  1.1.1.2  christos 
   2331  1.1.1.7  christos static bool
   2332  1.1.1.2  christos elf_arc_adjust_dynamic_symbol (struct bfd_link_info *info,
   2333  1.1.1.2  christos 			      struct elf_link_hash_entry *h)
   2334  1.1.1.2  christos {
   2335  1.1.1.3  christos   asection *s;
   2336  1.1.1.2  christos   bfd *dynobj = (elf_hash_table (info))->dynobj;
   2337  1.1.1.3  christos   struct elf_link_hash_table *htab = elf_hash_table (info);
   2338  1.1.1.2  christos 
   2339  1.1.1.3  christos   if (h->type == STT_FUNC
   2340  1.1.1.3  christos       || h->type == STT_GNU_IFUNC
   2341  1.1.1.3  christos       || h->needs_plt == 1)
   2342  1.1.1.2  christos     {
   2343  1.1.1.2  christos       if (!bfd_link_pic (info) && !h->def_dynamic && !h->ref_dynamic)
   2344  1.1.1.2  christos 	{
   2345  1.1.1.2  christos 	  /* This case can occur if we saw a PLT32 reloc in an input
   2346  1.1.1.2  christos 	     file, but the symbol was never referred to by a dynamic
   2347  1.1.1.2  christos 	     object.  In such a case, we don't actually need to build
   2348  1.1.1.2  christos 	     a procedure linkage table, and we can just do a PC32
   2349  1.1.1.2  christos 	     reloc instead.  */
   2350  1.1.1.2  christos 	  BFD_ASSERT (h->needs_plt);
   2351  1.1.1.7  christos 	  return true;
   2352  1.1.1.2  christos 	}
   2353  1.1.1.2  christos 
   2354  1.1.1.2  christos       /* Make sure this symbol is output as a dynamic symbol.  */
   2355  1.1.1.2  christos       if (h->dynindx == -1 && !h->forced_local
   2356  1.1.1.2  christos 	  && !bfd_elf_link_record_dynamic_symbol (info, h))
   2357  1.1.1.7  christos 	return false;
   2358  1.1.1.2  christos 
   2359  1.1.1.3  christos       if (bfd_link_pic (info)
   2360  1.1.1.3  christos 	  || WILL_CALL_FINISH_DYNAMIC_SYMBOL (1, 0, h))
   2361  1.1.1.2  christos 	{
   2362  1.1.1.2  christos 	  bfd_vma loc = add_symbol_to_plt (info);
   2363  1.1.1.2  christos 
   2364  1.1.1.4  christos 	  if (bfd_link_executable (info) && !h->def_regular)
   2365  1.1.1.2  christos 	    {
   2366  1.1.1.3  christos 	      h->root.u.def.section = htab->splt;
   2367  1.1.1.2  christos 	      h->root.u.def.value = loc;
   2368  1.1.1.2  christos 	    }
   2369  1.1.1.2  christos 	  h->plt.offset = loc;
   2370  1.1.1.2  christos 	}
   2371  1.1.1.3  christos       else
   2372  1.1.1.3  christos 	{
   2373  1.1.1.3  christos 	  h->plt.offset = (bfd_vma) -1;
   2374  1.1.1.3  christos 	  h->needs_plt = 0;
   2375  1.1.1.3  christos 	}
   2376  1.1.1.7  christos       return true;
   2377  1.1.1.2  christos     }
   2378  1.1.1.3  christos 
   2379  1.1.1.3  christos   /* If this is a weak symbol, and there is a real definition, the
   2380  1.1.1.3  christos      processor independent code will have arranged for us to see the
   2381  1.1.1.3  christos      real definition first, and we can just use the same value.  */
   2382  1.1.1.4  christos   if (h->is_weakalias)
   2383  1.1.1.2  christos     {
   2384  1.1.1.4  christos       struct elf_link_hash_entry *def = weakdef (h);
   2385  1.1.1.4  christos       BFD_ASSERT (def->root.type == bfd_link_hash_defined);
   2386  1.1.1.4  christos       h->root.u.def.section = def->root.u.def.section;
   2387  1.1.1.4  christos       h->root.u.def.value = def->root.u.def.value;
   2388  1.1.1.7  christos       return true;
   2389  1.1.1.2  christos     }
   2390  1.1.1.2  christos 
   2391  1.1.1.3  christos   /* This is a reference to a symbol defined by a dynamic object which
   2392  1.1.1.3  christos      is not a function.  */
   2393  1.1.1.2  christos 
   2394  1.1.1.3  christos   /* If we are creating a shared library, we must presume that the
   2395  1.1.1.3  christos      only references to the symbol are via the global offset table.
   2396  1.1.1.3  christos      For such cases we need not do anything here; the relocations will
   2397  1.1.1.3  christos      be handled correctly by relocate_section.  */
   2398  1.1.1.3  christos   if (!bfd_link_executable (info))
   2399  1.1.1.7  christos     return true;
   2400  1.1.1.3  christos 
   2401  1.1.1.3  christos   /* If there are no non-GOT references, we do not need a copy
   2402  1.1.1.3  christos      relocation.  */
   2403  1.1.1.3  christos   if (!h->non_got_ref)
   2404  1.1.1.7  christos     return true;
   2405  1.1.1.3  christos 
   2406  1.1.1.3  christos   /* If -z nocopyreloc was given, we won't generate them either.  */
   2407  1.1.1.3  christos   if (info->nocopyreloc)
   2408  1.1.1.3  christos     {
   2409  1.1.1.3  christos       h->non_got_ref = 0;
   2410  1.1.1.7  christos       return true;
   2411  1.1.1.3  christos     }
   2412  1.1.1.3  christos 
   2413  1.1.1.3  christos   /* We must allocate the symbol in our .dynbss section, which will
   2414  1.1.1.3  christos      become part of the .bss section of the executable.  There will be
   2415  1.1.1.3  christos      an entry for this symbol in the .dynsym section.  The dynamic
   2416  1.1.1.3  christos      object will contain position independent code, so all references
   2417  1.1.1.3  christos      from the dynamic object to this symbol will go through the global
   2418  1.1.1.3  christos      offset table.  The dynamic linker will use the .dynsym entry to
   2419  1.1.1.3  christos      determine the address it must put in the global offset table, so
   2420  1.1.1.3  christos      both the dynamic object and the regular object will refer to the
   2421  1.1.1.3  christos      same memory location for the variable.  */
   2422  1.1.1.3  christos 
   2423  1.1.1.3  christos   if (htab == NULL)
   2424  1.1.1.7  christos     return false;
   2425  1.1.1.3  christos 
   2426  1.1.1.3  christos   /* We must generate a R_ARC_COPY reloc to tell the dynamic linker to
   2427  1.1.1.3  christos      copy the initial value out of the dynamic object and into the
   2428  1.1.1.3  christos      runtime process image.  We need to remember the offset into the
   2429  1.1.1.3  christos      .rela.bss section we are going to use.  */
   2430  1.1.1.3  christos   if ((h->root.u.def.section->flags & SEC_ALLOC) != 0)
   2431  1.1.1.3  christos     {
   2432  1.1.1.4  christos       struct elf_arc_link_hash_table *arc_htab = elf_arc_hash_table (info);
   2433  1.1.1.3  christos 
   2434  1.1.1.4  christos       BFD_ASSERT (arc_htab->elf.srelbss != NULL);
   2435  1.1.1.4  christos       arc_htab->elf.srelbss->size += sizeof (Elf32_External_Rela);
   2436  1.1.1.3  christos       h->needs_copy = 1;
   2437  1.1.1.3  christos     }
   2438  1.1.1.3  christos 
   2439  1.1.1.4  christos   /* TODO: Move this also to arc_hash_table.  */
   2440  1.1.1.3  christos   s = bfd_get_section_by_name (dynobj, ".dynbss");
   2441  1.1.1.3  christos   BFD_ASSERT (s != NULL);
   2442  1.1.1.3  christos 
   2443  1.1.1.3  christos   return _bfd_elf_adjust_dynamic_copy (info, h, s);
   2444  1.1.1.2  christos }
   2445  1.1.1.2  christos 
   2446  1.1.1.2  christos /* Function :  elf_arc_finish_dynamic_symbol
   2447  1.1.1.2  christos    Brief    :  Finish up dynamic symbol handling.  We set the
   2448  1.1.1.3  christos 	     contents of various dynamic sections here.
   2449  1.1.1.2  christos    Args     :  output_bfd :
   2450  1.1.1.3  christos 	       info	  :
   2451  1.1.1.3  christos 	       h	  :
   2452  1.1.1.3  christos 	       sym	  :
   2453  1.1.1.2  christos    Returns  : True/False as the return status.  */
   2454  1.1.1.3  christos 
   2455  1.1.1.7  christos static bool
   2456  1.1.1.2  christos elf_arc_finish_dynamic_symbol (bfd * output_bfd,
   2457  1.1.1.2  christos 			       struct bfd_link_info *info,
   2458  1.1.1.2  christos 			       struct elf_link_hash_entry *h,
   2459  1.1.1.2  christos 			       Elf_Internal_Sym * sym)
   2460  1.1.1.2  christos {
   2461  1.1.1.3  christos   if (h->plt.offset != (bfd_vma) -1)
   2462  1.1.1.2  christos     {
   2463  1.1.1.3  christos       relocate_plt_for_symbol (output_bfd, info, h);
   2464  1.1.1.3  christos 
   2465  1.1.1.3  christos       if (!h->def_regular)
   2466  1.1.1.2  christos 	{
   2467  1.1.1.3  christos 	  /* Mark the symbol as undefined, rather than as defined in
   2468  1.1.1.3  christos 	     the .plt section.  Leave the value alone.  */
   2469  1.1.1.3  christos 	  sym->st_shndx = SHN_UNDEF;
   2470  1.1.1.2  christos 	}
   2471  1.1.1.3  christos     }
   2472  1.1.1.3  christos 
   2473  1.1.1.3  christos 
   2474  1.1.1.4  christos   /* This function traverses list of GOT entries and
   2475  1.1.1.4  christos      create respective dynamic relocs.  */
   2476  1.1.1.4  christos   /* TODO: Make function to get list and not access the list directly.  */
   2477  1.1.1.4  christos   /* TODO: Move function to relocate_section create this relocs eagerly.  */
   2478  1.1.1.6  christos   struct elf_arc_link_hash_entry *ah =
   2479  1.1.1.6  christos     (struct elf_arc_link_hash_entry *) h;
   2480  1.1.1.6  christos   create_got_dynrelocs_for_got_info (&ah->got_ents,
   2481  1.1.1.4  christos 				     output_bfd,
   2482  1.1.1.4  christos 				     info,
   2483  1.1.1.4  christos 				     h);
   2484  1.1.1.3  christos 
   2485  1.1.1.3  christos   if (h->needs_copy)
   2486  1.1.1.3  christos     {
   2487  1.1.1.4  christos       struct elf_arc_link_hash_table *arc_htab = elf_arc_hash_table (info);
   2488  1.1.1.4  christos 
   2489  1.1.1.6  christos       if (arc_htab == NULL)
   2490  1.1.1.7  christos 	return false;
   2491  1.1.1.6  christos 
   2492  1.1.1.4  christos       if (h->dynindx == -1
   2493  1.1.1.4  christos 	  || (h->root.type != bfd_link_hash_defined
   2494  1.1.1.4  christos 	      && h->root.type != bfd_link_hash_defweak)
   2495  1.1.1.4  christos 	  || arc_htab->elf.srelbss == NULL)
   2496  1.1.1.4  christos 	abort ();
   2497  1.1.1.4  christos 
   2498  1.1.1.3  christos       bfd_vma rel_offset = (h->root.u.def.value
   2499  1.1.1.3  christos 			    + h->root.u.def.section->output_section->vma
   2500  1.1.1.3  christos 			    + h->root.u.def.section->output_offset);
   2501  1.1.1.3  christos 
   2502  1.1.1.4  christos       bfd_byte * loc = arc_htab->elf.srelbss->contents
   2503  1.1.1.4  christos 	+ (arc_htab->elf.srelbss->reloc_count * sizeof (Elf32_External_Rela));
   2504  1.1.1.4  christos       arc_htab->elf.srelbss->reloc_count++;
   2505  1.1.1.3  christos 
   2506  1.1.1.3  christos       Elf_Internal_Rela rel;
   2507  1.1.1.3  christos       rel.r_addend = 0;
   2508  1.1.1.3  christos       rel.r_offset = rel_offset;
   2509  1.1.1.3  christos 
   2510  1.1.1.3  christos       BFD_ASSERT (h->dynindx != -1);
   2511  1.1.1.3  christos       rel.r_info = ELF32_R_INFO (h->dynindx, R_ARC_COPY);
   2512  1.1.1.3  christos 
   2513  1.1.1.3  christos       bfd_elf32_swap_reloca_out (output_bfd, &rel, loc);
   2514  1.1.1.2  christos     }
   2515  1.1.1.2  christos 
   2516  1.1.1.2  christos   /* Mark _DYNAMIC and _GLOBAL_OFFSET_TABLE_ as absolute.  */
   2517  1.1.1.2  christos   if (strcmp (h->root.root.string, "_DYNAMIC") == 0
   2518  1.1.1.2  christos       || strcmp (h->root.root.string, "__DYNAMIC") == 0
   2519  1.1.1.2  christos       || strcmp (h->root.root.string, "_GLOBAL_OFFSET_TABLE_") == 0)
   2520  1.1.1.2  christos     sym->st_shndx = SHN_ABS;
   2521  1.1.1.2  christos 
   2522  1.1.1.7  christos   return true;
   2523  1.1.1.2  christos }
   2524  1.1.1.2  christos 
   2525  1.1.1.3  christos #define GET_SYMBOL_OR_SECTION(TAG, SYMBOL, SECTION)		\
   2526  1.1.1.3  christos   case TAG:							\
   2527  1.1.1.3  christos   if (SYMBOL != NULL)						\
   2528  1.1.1.3  christos     h = elf_link_hash_lookup (elf_hash_table (info),		\
   2529  1.1.1.7  christos 			      SYMBOL, false, false, true);	\
   2530  1.1.1.3  christos   else if (SECTION != NULL)					\
   2531  1.1.1.3  christos     s = bfd_get_linker_section (dynobj, SECTION);		\
   2532  1.1.1.3  christos   break;
   2533  1.1.1.2  christos 
   2534  1.1.1.6  christos 
   2535  1.1.1.6  christos struct obfd_info_group {
   2536  1.1.1.6  christos   bfd *output_bfd;
   2537  1.1.1.6  christos   struct bfd_link_info *info;
   2538  1.1.1.6  christos };
   2539  1.1.1.6  christos 
   2540  1.1.1.7  christos static bool
   2541  1.1.1.6  christos arc_create_forced_local_got_entries_for_tls (struct bfd_hash_entry *bh,
   2542  1.1.1.6  christos 					     void *data)
   2543  1.1.1.6  christos {
   2544  1.1.1.6  christos   struct elf_arc_link_hash_entry * h =
   2545  1.1.1.6  christos     (struct elf_arc_link_hash_entry *) bh;
   2546  1.1.1.6  christos   struct obfd_info_group *tmp = (struct obfd_info_group *) data;
   2547  1.1.1.6  christos 
   2548  1.1.1.6  christos   if (h->got_ents != NULL)
   2549  1.1.1.6  christos     {
   2550  1.1.1.6  christos       BFD_ASSERT (h);
   2551  1.1.1.6  christos 
   2552  1.1.1.6  christos       struct got_entry *list = h->got_ents;
   2553  1.1.1.6  christos 
   2554  1.1.1.6  christos       while (list != NULL)
   2555  1.1.1.6  christos 	{
   2556  1.1.1.6  christos 	  create_got_dynrelocs_for_single_entry (list, tmp->output_bfd,
   2557  1.1.1.6  christos 	    tmp->info,
   2558  1.1.1.6  christos 	    (struct elf_link_hash_entry *) h);
   2559  1.1.1.6  christos 	  list = list->next;
   2560  1.1.1.6  christos 	}
   2561  1.1.1.6  christos     }
   2562  1.1.1.6  christos 
   2563  1.1.1.7  christos   return true;
   2564  1.1.1.6  christos }
   2565  1.1.1.6  christos 
   2566  1.1.1.6  christos 
   2567  1.1.1.2  christos /* Function :  elf_arc_finish_dynamic_sections
   2568  1.1.1.2  christos    Brief    :  Finish up the dynamic sections handling.
   2569  1.1.1.2  christos    Args     :  output_bfd :
   2570  1.1.1.3  christos 	       info	  :
   2571  1.1.1.3  christos 	       h	  :
   2572  1.1.1.3  christos 	       sym	  :
   2573  1.1.1.2  christos    Returns  : True/False as the return status.  */
   2574  1.1.1.3  christos 
   2575  1.1.1.7  christos static bool
   2576  1.1.1.3  christos elf_arc_finish_dynamic_sections (bfd * output_bfd,
   2577  1.1.1.3  christos 				 struct bfd_link_info *info)
   2578  1.1.1.2  christos {
   2579  1.1.1.3  christos   struct elf_link_hash_table *htab = elf_hash_table (info);
   2580  1.1.1.2  christos   bfd *dynobj = (elf_hash_table (info))->dynobj;
   2581  1.1.1.4  christos   asection *sdyn = bfd_get_linker_section (dynobj, ".dynamic");
   2582  1.1.1.2  christos 
   2583  1.1.1.4  christos   if (sdyn)
   2584  1.1.1.2  christos     {
   2585  1.1.1.2  christos       Elf32_External_Dyn *dyncon, *dynconend;
   2586  1.1.1.2  christos 
   2587  1.1.1.4  christos       dyncon = (Elf32_External_Dyn *) sdyn->contents;
   2588  1.1.1.4  christos       dynconend
   2589  1.1.1.4  christos 	= (Elf32_External_Dyn *) (sdyn->contents + sdyn->size);
   2590  1.1.1.2  christos       for (; dyncon < dynconend; dyncon++)
   2591  1.1.1.2  christos 	{
   2592  1.1.1.2  christos 	  Elf_Internal_Dyn internal_dyn;
   2593  1.1.1.7  christos 	  bool do_it = false;
   2594  1.1.1.2  christos 
   2595  1.1.1.2  christos 	  struct elf_link_hash_entry *h = NULL;
   2596  1.1.1.2  christos 	  asection	 *s = NULL;
   2597  1.1.1.2  christos 
   2598  1.1.1.2  christos 	  bfd_elf32_swap_dyn_in (dynobj, dyncon, &internal_dyn);
   2599  1.1.1.2  christos 
   2600  1.1.1.2  christos 	  switch (internal_dyn.d_tag)
   2601  1.1.1.2  christos 	    {
   2602  1.1.1.4  christos 	      GET_SYMBOL_OR_SECTION (DT_INIT, info->init_function, NULL)
   2603  1.1.1.4  christos 	      GET_SYMBOL_OR_SECTION (DT_FINI, info->fini_function, NULL)
   2604  1.1.1.2  christos 	      GET_SYMBOL_OR_SECTION (DT_PLTGOT, NULL, ".plt")
   2605  1.1.1.2  christos 	      GET_SYMBOL_OR_SECTION (DT_JMPREL, NULL, ".rela.plt")
   2606  1.1.1.2  christos 	      GET_SYMBOL_OR_SECTION (DT_PLTRELSZ, NULL, ".rela.plt")
   2607  1.1.1.3  christos 	      GET_SYMBOL_OR_SECTION (DT_VERSYM, NULL, ".gnu.version")
   2608  1.1.1.3  christos 	      GET_SYMBOL_OR_SECTION (DT_VERDEF, NULL, ".gnu.version_d")
   2609  1.1.1.3  christos 	      GET_SYMBOL_OR_SECTION (DT_VERNEED, NULL, ".gnu.version_r")
   2610  1.1.1.2  christos 	      default:
   2611  1.1.1.2  christos 		break;
   2612  1.1.1.2  christos 	    }
   2613  1.1.1.2  christos 
   2614  1.1.1.3  christos 	  /* In case the dynamic symbols should be updated with a symbol.  */
   2615  1.1.1.2  christos 	  if (h != NULL
   2616  1.1.1.2  christos 	      && (h->root.type == bfd_link_hash_defined
   2617  1.1.1.3  christos 		  || h->root.type == bfd_link_hash_defweak))
   2618  1.1.1.2  christos 	    {
   2619  1.1.1.2  christos 	      asection	     *asec_ptr;
   2620  1.1.1.2  christos 
   2621  1.1.1.2  christos 	      internal_dyn.d_un.d_val = h->root.u.def.value;
   2622  1.1.1.2  christos 	      asec_ptr = h->root.u.def.section;
   2623  1.1.1.2  christos 	      if (asec_ptr->output_section != NULL)
   2624  1.1.1.2  christos 		{
   2625  1.1.1.2  christos 		  internal_dyn.d_un.d_val +=
   2626  1.1.1.4  christos 		    (asec_ptr->output_section->vma
   2627  1.1.1.4  christos 		     + asec_ptr->output_offset);
   2628  1.1.1.2  christos 		}
   2629  1.1.1.2  christos 	      else
   2630  1.1.1.2  christos 		{
   2631  1.1.1.3  christos 		  /* The symbol is imported from another shared
   2632  1.1.1.3  christos 		     library and does not apply to this one.  */
   2633  1.1.1.2  christos 		  internal_dyn.d_un.d_val = 0;
   2634  1.1.1.2  christos 		}
   2635  1.1.1.7  christos 	      do_it = true;
   2636  1.1.1.2  christos 	    }
   2637  1.1.1.2  christos 	  else if (s != NULL) /* With a section information.  */
   2638  1.1.1.2  christos 	    {
   2639  1.1.1.2  christos 	      switch (internal_dyn.d_tag)
   2640  1.1.1.2  christos 		{
   2641  1.1.1.2  christos 		  case DT_PLTGOT:
   2642  1.1.1.2  christos 		  case DT_JMPREL:
   2643  1.1.1.3  christos 		  case DT_VERSYM:
   2644  1.1.1.3  christos 		  case DT_VERDEF:
   2645  1.1.1.3  christos 		  case DT_VERNEED:
   2646  1.1.1.3  christos 		    internal_dyn.d_un.d_ptr = (s->output_section->vma
   2647  1.1.1.3  christos 					       + s->output_offset);
   2648  1.1.1.7  christos 		    do_it = true;
   2649  1.1.1.2  christos 		    break;
   2650  1.1.1.2  christos 
   2651  1.1.1.2  christos 		  case DT_PLTRELSZ:
   2652  1.1.1.2  christos 		    internal_dyn.d_un.d_val = s->size;
   2653  1.1.1.7  christos 		    do_it = true;
   2654  1.1.1.2  christos 		    break;
   2655  1.1.1.2  christos 
   2656  1.1.1.2  christos 		  default:
   2657  1.1.1.2  christos 		    break;
   2658  1.1.1.2  christos 		}
   2659  1.1.1.2  christos 	    }
   2660  1.1.1.2  christos 
   2661  1.1.1.3  christos 	  if (do_it)
   2662  1.1.1.2  christos 	    bfd_elf32_swap_dyn_out (output_bfd, &internal_dyn, dyncon);
   2663  1.1.1.2  christos 	}
   2664  1.1.1.2  christos 
   2665  1.1.1.3  christos       if (htab->splt->size > 0)
   2666  1.1.1.2  christos 	{
   2667  1.1.1.3  christos 	  relocate_plt_for_entry (output_bfd, info);
   2668  1.1.1.2  christos 	}
   2669  1.1.1.2  christos 
   2670  1.1.1.3  christos       /* TODO: Validate this.  */
   2671  1.1.1.4  christos       if (htab->srelplt->output_section != bfd_abs_section_ptr)
   2672  1.1.1.4  christos 	elf_section_data (htab->srelplt->output_section)
   2673  1.1.1.4  christos 	  ->this_hdr.sh_entsize = 12;
   2674  1.1.1.2  christos     }
   2675  1.1.1.2  christos 
   2676  1.1.1.2  christos   /* Fill in the first three entries in the global offset table.  */
   2677  1.1.1.3  christos   if (htab->sgot)
   2678  1.1.1.2  christos     {
   2679  1.1.1.3  christos       struct elf_link_hash_entry *h;
   2680  1.1.1.3  christos       h = elf_link_hash_lookup (elf_hash_table (info), "_GLOBAL_OFFSET_TABLE_",
   2681  1.1.1.7  christos 				 false, false, true);
   2682  1.1.1.3  christos 
   2683  1.1.1.3  christos 	if (h != NULL && h->root.type != bfd_link_hash_undefined
   2684  1.1.1.3  christos 	    && h->root.u.def.section != NULL)
   2685  1.1.1.2  christos 	{
   2686  1.1.1.3  christos 	  asection *sec = h->root.u.def.section;
   2687  1.1.1.3  christos 
   2688  1.1.1.4  christos 	  if (sdyn == NULL)
   2689  1.1.1.2  christos 	    bfd_put_32 (output_bfd, (bfd_vma) 0,
   2690  1.1.1.3  christos 			sec->contents);
   2691  1.1.1.2  christos 	  else
   2692  1.1.1.2  christos 	    bfd_put_32 (output_bfd,
   2693  1.1.1.4  christos 			sdyn->output_section->vma + sdyn->output_offset,
   2694  1.1.1.3  christos 			sec->contents);
   2695  1.1.1.3  christos 	  bfd_put_32 (output_bfd, (bfd_vma) 0, sec->contents + 4);
   2696  1.1.1.3  christos 	  bfd_put_32 (output_bfd, (bfd_vma) 0, sec->contents + 8);
   2697  1.1.1.2  christos 	}
   2698  1.1.1.2  christos     }
   2699  1.1.1.2  christos 
   2700  1.1.1.6  christos   struct obfd_info_group group;
   2701  1.1.1.6  christos   group.output_bfd = output_bfd;
   2702  1.1.1.6  christos   group.info = info;
   2703  1.1.1.6  christos   bfd_hash_traverse (&info->hash->table,
   2704  1.1.1.6  christos 		     arc_create_forced_local_got_entries_for_tls, &group);
   2705  1.1.1.6  christos 
   2706  1.1.1.7  christos   return true;
   2707  1.1.1.2  christos }
   2708  1.1.1.2  christos 
   2709  1.1.1.3  christos #define ADD_DYNAMIC_SYMBOL(NAME, TAG)					\
   2710  1.1.1.3  christos   h =  elf_link_hash_lookup (elf_hash_table (info),			\
   2711  1.1.1.7  christos 			     NAME, false, false, false);		\
   2712  1.1.1.3  christos   if ((h != NULL && (h->ref_regular || h->def_regular)))		\
   2713  1.1.1.3  christos     if (! _bfd_elf_add_dynamic_entry (info, TAG, 0))			\
   2714  1.1.1.7  christos       return false;
   2715  1.1.1.2  christos 
   2716  1.1.1.2  christos /* Set the sizes of the dynamic sections.  */
   2717  1.1.1.7  christos static bool
   2718  1.1.1.4  christos elf_arc_size_dynamic_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
   2719  1.1.1.3  christos 			       struct bfd_link_info *info)
   2720  1.1.1.2  christos {
   2721  1.1.1.4  christos   bfd *dynobj;
   2722  1.1.1.4  christos   asection *s;
   2723  1.1.1.7  christos   bool relocs_exist = false;
   2724  1.1.1.3  christos   struct elf_link_hash_table *htab = elf_hash_table (info);
   2725  1.1.1.2  christos 
   2726  1.1.1.4  christos   dynobj = htab->dynobj;
   2727  1.1.1.2  christos   BFD_ASSERT (dynobj != NULL);
   2728  1.1.1.2  christos 
   2729  1.1.1.4  christos   if (htab->dynamic_sections_created)
   2730  1.1.1.2  christos     {
   2731  1.1.1.2  christos       struct elf_link_hash_entry *h;
   2732  1.1.1.2  christos 
   2733  1.1.1.3  christos       /* Set the contents of the .interp section to the
   2734  1.1.1.3  christos 	 interpreter.  */
   2735  1.1.1.4  christos       if (bfd_link_executable (info) && !info->nointerp)
   2736  1.1.1.2  christos 	{
   2737  1.1.1.2  christos 	  s = bfd_get_section_by_name (dynobj, ".interp");
   2738  1.1.1.2  christos 	  BFD_ASSERT (s != NULL);
   2739  1.1.1.3  christos 	  s->size = sizeof (ELF_DYNAMIC_INTERPRETER);
   2740  1.1.1.2  christos 	  s->contents = (unsigned char *) ELF_DYNAMIC_INTERPRETER;
   2741  1.1.1.2  christos 	}
   2742  1.1.1.2  christos 
   2743  1.1.1.3  christos       /* Add some entries to the .dynamic section.  We fill in some of
   2744  1.1.1.3  christos 	 the values later, in elf_bfd_final_link, but we must add the
   2745  1.1.1.3  christos 	 entries now so that we know the final size of the .dynamic
   2746  1.1.1.3  christos 	 section.  Checking if the .init section is present.  We also
   2747  1.1.1.3  christos 	 create DT_INIT and DT_FINI entries if the init_str has been
   2748  1.1.1.3  christos 	 changed by the user.  */
   2749  1.1.1.4  christos       ADD_DYNAMIC_SYMBOL (info->init_function, DT_INIT);
   2750  1.1.1.4  christos       ADD_DYNAMIC_SYMBOL (info->fini_function, DT_FINI);
   2751  1.1.1.2  christos     }
   2752  1.1.1.2  christos   else
   2753  1.1.1.2  christos     {
   2754  1.1.1.3  christos       /* We may have created entries in the .rela.got section.
   2755  1.1.1.3  christos 	 However, if we are not creating the dynamic sections, we will
   2756  1.1.1.3  christos 	 not actually use these entries.  Reset the size of .rela.got,
   2757  1.1.1.3  christos 	 which will cause it to get stripped from the output file
   2758  1.1.1.3  christos 	 below.  */
   2759  1.1.1.3  christos       if (htab->srelgot != NULL)
   2760  1.1.1.3  christos 	htab->srelgot->size = 0;
   2761  1.1.1.2  christos     }
   2762  1.1.1.2  christos 
   2763  1.1.1.2  christos   for (s = dynobj->sections; s != NULL; s = s->next)
   2764  1.1.1.2  christos     {
   2765  1.1.1.3  christos       if ((s->flags & SEC_LINKER_CREATED) == 0)
   2766  1.1.1.2  christos 	continue;
   2767  1.1.1.2  christos 
   2768  1.1.1.4  christos       if (s == htab->splt
   2769  1.1.1.4  christos 	  || s == htab->sgot
   2770  1.1.1.4  christos 	  || s == htab->sgotplt
   2771  1.1.1.4  christos 	  || s == htab->sdynbss)
   2772  1.1.1.2  christos 	{
   2773  1.1.1.4  christos 	  /* Strip this section if we don't need it.  */
   2774  1.1.1.4  christos 	}
   2775  1.1.1.7  christos       else if (startswith (s->name, ".rela"))
   2776  1.1.1.4  christos 	{
   2777  1.1.1.4  christos 	  if (s->size != 0 && s != htab->srelplt)
   2778  1.1.1.7  christos 	    relocs_exist = true;
   2779  1.1.1.2  christos 
   2780  1.1.1.3  christos 	  /* We use the reloc_count field as a counter if we need to
   2781  1.1.1.3  christos 	     copy relocs into the output file.  */
   2782  1.1.1.3  christos 	  s->reloc_count = 0;
   2783  1.1.1.2  christos 	}
   2784  1.1.1.4  christos       else
   2785  1.1.1.4  christos 	{
   2786  1.1.1.4  christos 	  /* It's not one of our sections, so don't allocate space.  */
   2787  1.1.1.4  christos 	  continue;
   2788  1.1.1.4  christos 	}
   2789  1.1.1.3  christos 
   2790  1.1.1.4  christos       if (s->size == 0)
   2791  1.1.1.4  christos 	{
   2792  1.1.1.4  christos 	  s->flags |= SEC_EXCLUDE;
   2793  1.1.1.4  christos 	  continue;
   2794  1.1.1.4  christos 	}
   2795  1.1.1.3  christos 
   2796  1.1.1.4  christos       if ((s->flags & SEC_HAS_CONTENTS) == 0)
   2797  1.1.1.4  christos 	continue;
   2798  1.1.1.3  christos 
   2799  1.1.1.4  christos       /* Allocate memory for the section contents.  */
   2800  1.1.1.4  christos       s->contents = bfd_zalloc (dynobj, s->size);
   2801  1.1.1.4  christos       if (s->contents == NULL)
   2802  1.1.1.7  christos 	return false;
   2803  1.1.1.2  christos     }
   2804  1.1.1.2  christos 
   2805  1.1.1.7  christos   return _bfd_elf_add_dynamic_tags (output_bfd, info, relocs_exist);
   2806  1.1.1.2  christos }
   2807  1.1.1.2  christos 
   2808  1.1.1.2  christos 
   2809  1.1.1.3  christos /* Classify dynamic relocs such that -z combreloc can reorder and combine
   2810  1.1.1.3  christos    them.  */
   2811  1.1.1.3  christos static enum elf_reloc_type_class
   2812  1.1.1.3  christos elf32_arc_reloc_type_class (const struct bfd_link_info *info ATTRIBUTE_UNUSED,
   2813  1.1.1.3  christos 			    const asection *rel_sec ATTRIBUTE_UNUSED,
   2814  1.1.1.3  christos 			    const Elf_Internal_Rela *rela)
   2815  1.1.1.3  christos {
   2816  1.1.1.3  christos   switch ((int) ELF32_R_TYPE (rela->r_info))
   2817  1.1.1.3  christos     {
   2818  1.1.1.3  christos     case R_ARC_RELATIVE:
   2819  1.1.1.3  christos       return reloc_class_relative;
   2820  1.1.1.3  christos     case R_ARC_JMP_SLOT:
   2821  1.1.1.3  christos       return reloc_class_plt;
   2822  1.1.1.3  christos     case R_ARC_COPY:
   2823  1.1.1.3  christos       return reloc_class_copy;
   2824  1.1.1.3  christos     /* TODO: Needed in future to support ifunc.  */
   2825  1.1.1.3  christos     /*
   2826  1.1.1.3  christos     case R_ARC_IRELATIVE:
   2827  1.1.1.3  christos       return reloc_class_ifunc;
   2828  1.1.1.3  christos     */
   2829  1.1.1.3  christos     default:
   2830  1.1.1.3  christos       return reloc_class_normal;
   2831  1.1.1.3  christos     }
   2832  1.1.1.3  christos }
   2833  1.1.1.3  christos 
   2834  1.1.1.3  christos const struct elf_size_info arc_elf32_size_info =
   2835  1.1.1.3  christos {
   2836  1.1.1.3  christos   sizeof (Elf32_External_Ehdr),
   2837  1.1.1.3  christos   sizeof (Elf32_External_Phdr),
   2838  1.1.1.3  christos   sizeof (Elf32_External_Shdr),
   2839  1.1.1.3  christos   sizeof (Elf32_External_Rel),
   2840  1.1.1.3  christos   sizeof (Elf32_External_Rela),
   2841  1.1.1.3  christos   sizeof (Elf32_External_Sym),
   2842  1.1.1.3  christos   sizeof (Elf32_External_Dyn),
   2843  1.1.1.3  christos   sizeof (Elf_External_Note),
   2844  1.1.1.3  christos   4,
   2845  1.1.1.3  christos   1,
   2846  1.1.1.3  christos   32, 2,
   2847  1.1.1.3  christos   ELFCLASS32, EV_CURRENT,
   2848  1.1.1.3  christos   bfd_elf32_write_out_phdrs,
   2849  1.1.1.3  christos   bfd_elf32_write_shdrs_and_ehdr,
   2850  1.1.1.3  christos   bfd_elf32_checksum_contents,
   2851  1.1.1.3  christos   bfd_elf32_write_relocs,
   2852  1.1.1.3  christos   bfd_elf32_swap_symbol_in,
   2853  1.1.1.3  christos   bfd_elf32_swap_symbol_out,
   2854  1.1.1.3  christos   bfd_elf32_slurp_reloc_table,
   2855  1.1.1.3  christos   bfd_elf32_slurp_symbol_table,
   2856  1.1.1.3  christos   bfd_elf32_swap_dyn_in,
   2857  1.1.1.3  christos   bfd_elf32_swap_dyn_out,
   2858  1.1.1.3  christos   bfd_elf32_swap_reloc_in,
   2859  1.1.1.3  christos   bfd_elf32_swap_reloc_out,
   2860  1.1.1.3  christos   bfd_elf32_swap_reloca_in,
   2861  1.1.1.3  christos   bfd_elf32_swap_reloca_out
   2862  1.1.1.3  christos };
   2863  1.1.1.3  christos 
   2864  1.1.1.3  christos #define elf_backend_size_info		arc_elf32_size_info
   2865  1.1.1.3  christos 
   2866  1.1.1.4  christos /* GDB expects general purpose registers to be in section .reg.  However Linux
   2867  1.1.1.4  christos    kernel doesn't create this section and instead writes registers to NOTE
   2868  1.1.1.4  christos    section.  It is up to the binutils to create a pseudo-section .reg from the
   2869  1.1.1.4  christos    contents of NOTE.  Also BFD will read pid and signal number from NOTE.  This
   2870  1.1.1.4  christos    function relies on offsets inside elf_prstatus structure in Linux to be
   2871  1.1.1.4  christos    stable.  */
   2872  1.1.1.4  christos 
   2873  1.1.1.7  christos static bool
   2874  1.1.1.4  christos elf32_arc_grok_prstatus (bfd *abfd, Elf_Internal_Note *note)
   2875  1.1.1.4  christos {
   2876  1.1.1.4  christos   int offset;
   2877  1.1.1.4  christos   size_t size;
   2878  1.1.1.4  christos 
   2879  1.1.1.4  christos   switch (note->descsz)
   2880  1.1.1.4  christos     {
   2881  1.1.1.4  christos     default:
   2882  1.1.1.7  christos       return false;
   2883  1.1.1.4  christos 
   2884  1.1.1.4  christos     case 236: /* sizeof (struct elf_prstatus) on Linux/arc.  */
   2885  1.1.1.4  christos       /* pr_cursig */
   2886  1.1.1.4  christos       elf_tdata (abfd)->core->signal = bfd_get_16 (abfd, note->descdata + 12);
   2887  1.1.1.4  christos       /* pr_pid */
   2888  1.1.1.4  christos       elf_tdata (abfd)->core->lwpid = bfd_get_32 (abfd, note->descdata + 24);
   2889  1.1.1.4  christos       /* pr_regs */
   2890  1.1.1.4  christos       offset = 72;
   2891  1.1.1.4  christos       size = (40 * 4); /* There are 40 registers in user_regs_struct.  */
   2892  1.1.1.4  christos       break;
   2893  1.1.1.4  christos     }
   2894  1.1.1.4  christos   /* Make a ".reg/999" section.  */
   2895  1.1.1.4  christos   return _bfd_elfcore_make_pseudosection (abfd, ".reg", size,
   2896  1.1.1.4  christos 					  note->descpos + offset);
   2897  1.1.1.4  christos }
   2898  1.1.1.4  christos 
   2899  1.1.1.4  christos /* Determine whether an object attribute tag takes an integer, a
   2900  1.1.1.4  christos    string or both.  */
   2901  1.1.1.4  christos 
   2902  1.1.1.4  christos static int
   2903  1.1.1.4  christos elf32_arc_obj_attrs_arg_type (int tag)
   2904  1.1.1.4  christos {
   2905  1.1.1.4  christos   if (tag == Tag_ARC_CPU_name
   2906  1.1.1.4  christos 	   || tag == Tag_ARC_ISA_config
   2907  1.1.1.4  christos 	   || tag == Tag_ARC_ISA_apex)
   2908  1.1.1.4  christos     return ATTR_TYPE_FLAG_STR_VAL;
   2909  1.1.1.4  christos   else if (tag < (Tag_ARC_ISA_mpy_option + 1))
   2910  1.1.1.4  christos     return ATTR_TYPE_FLAG_INT_VAL;
   2911  1.1.1.4  christos   else
   2912  1.1.1.4  christos     return (tag & 1) != 0 ? ATTR_TYPE_FLAG_STR_VAL : ATTR_TYPE_FLAG_INT_VAL;
   2913  1.1.1.4  christos }
   2914  1.1.1.4  christos 
   2915  1.1.1.4  christos /* Attribute numbers >=14 can be safely ignored.  */
   2916  1.1.1.4  christos 
   2917  1.1.1.7  christos static bool
   2918  1.1.1.4  christos elf32_arc_obj_attrs_handle_unknown (bfd *abfd, int tag)
   2919  1.1.1.4  christos {
   2920  1.1.1.4  christos   if ((tag & 127) < (Tag_ARC_ISA_mpy_option + 1))
   2921  1.1.1.4  christos     {
   2922  1.1.1.4  christos       _bfd_error_handler
   2923  1.1.1.5  christos 	(_("%pB: unknown mandatory ARC object attribute %d"),
   2924  1.1.1.4  christos 	 abfd, tag);
   2925  1.1.1.4  christos       bfd_set_error (bfd_error_bad_value);
   2926  1.1.1.7  christos       return false;
   2927  1.1.1.4  christos     }
   2928  1.1.1.4  christos   else
   2929  1.1.1.4  christos     {
   2930  1.1.1.4  christos       _bfd_error_handler
   2931  1.1.1.5  christos 	(_("warning: %pB: unknown ARC object attribute %d"),
   2932  1.1.1.4  christos 	 abfd, tag);
   2933  1.1.1.7  christos       return true;
   2934  1.1.1.4  christos     }
   2935  1.1.1.4  christos }
   2936  1.1.1.4  christos 
   2937  1.1.1.4  christos /* Handle an ARC specific section when reading an object file.  This is
   2938  1.1.1.4  christos    called when bfd_section_from_shdr finds a section with an unknown
   2939  1.1.1.4  christos    type.  */
   2940  1.1.1.4  christos 
   2941  1.1.1.7  christos static bool
   2942  1.1.1.4  christos elf32_arc_section_from_shdr (bfd *abfd,
   2943  1.1.1.4  christos 			     Elf_Internal_Shdr * hdr,
   2944  1.1.1.4  christos 			     const char *name,
   2945  1.1.1.4  christos 			     int shindex)
   2946  1.1.1.4  christos {
   2947  1.1.1.4  christos   switch (hdr->sh_type)
   2948  1.1.1.4  christos     {
   2949  1.1.1.6  christos     case 0x0c: /* MWDT specific section, don't complain about it.  */
   2950  1.1.1.4  christos     case SHT_ARC_ATTRIBUTES:
   2951  1.1.1.4  christos       break;
   2952  1.1.1.4  christos 
   2953  1.1.1.4  christos     default:
   2954  1.1.1.7  christos       return false;
   2955  1.1.1.4  christos     }
   2956  1.1.1.4  christos 
   2957  1.1.1.4  christos   if (!_bfd_elf_make_section_from_shdr (abfd, hdr, name, shindex))
   2958  1.1.1.7  christos     return false;
   2959  1.1.1.4  christos 
   2960  1.1.1.7  christos   return true;
   2961  1.1.1.4  christos }
   2962  1.1.1.4  christos 
   2963  1.1.1.6  christos /* Relaxation hook.
   2964  1.1.1.6  christos 
   2965  1.1.1.6  christos    These are the current relaxing opportunities available:
   2966  1.1.1.6  christos 
   2967  1.1.1.6  christos    * R_ARC_GOTPC32 => R_ARC_PCREL.
   2968  1.1.1.6  christos 
   2969  1.1.1.6  christos */
   2970  1.1.1.6  christos 
   2971  1.1.1.7  christos static bool
   2972  1.1.1.6  christos arc_elf_relax_section (bfd *abfd, asection *sec,
   2973  1.1.1.7  christos 		       struct bfd_link_info *link_info, bool *again)
   2974  1.1.1.6  christos {
   2975  1.1.1.6  christos   Elf_Internal_Shdr *symtab_hdr;
   2976  1.1.1.6  christos   Elf_Internal_Rela *internal_relocs;
   2977  1.1.1.6  christos   Elf_Internal_Rela *irel, *irelend;
   2978  1.1.1.6  christos   bfd_byte *contents = NULL;
   2979  1.1.1.6  christos   Elf_Internal_Sym *isymbuf = NULL;
   2980  1.1.1.6  christos 
   2981  1.1.1.6  christos   /* Assume nothing changes.  */
   2982  1.1.1.7  christos   *again = false;
   2983  1.1.1.6  christos 
   2984  1.1.1.6  christos   /* We don't have to do anything for a relocatable link, if this
   2985  1.1.1.6  christos      section does not have relocs, or if this is not a code
   2986  1.1.1.6  christos      section.  */
   2987  1.1.1.6  christos   if (bfd_link_relocatable (link_info)
   2988  1.1.1.6  christos       || sec->reloc_count == 0
   2989  1.1.1.8  christos       || (sec->flags & SEC_RELOC) == 0
   2990  1.1.1.8  christos       || (sec->flags & SEC_HAS_CONTENTS) == 0
   2991  1.1.1.6  christos       || (sec->flags & SEC_CODE) == 0)
   2992  1.1.1.7  christos     return true;
   2993  1.1.1.6  christos 
   2994  1.1.1.6  christos   symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
   2995  1.1.1.6  christos 
   2996  1.1.1.6  christos   /* Get a copy of the native relocations.  */
   2997  1.1.1.6  christos   internal_relocs = _bfd_elf_link_read_relocs (abfd, sec, NULL, NULL,
   2998  1.1.1.6  christos                                                link_info->keep_memory);
   2999  1.1.1.6  christos   if (internal_relocs == NULL)
   3000  1.1.1.6  christos     goto error_return;
   3001  1.1.1.6  christos 
   3002  1.1.1.6  christos   /* Walk through them looking for relaxing opportunities.  */
   3003  1.1.1.6  christos   irelend = internal_relocs + sec->reloc_count;
   3004  1.1.1.6  christos   for (irel = internal_relocs; irel < irelend; irel++)
   3005  1.1.1.6  christos     {
   3006  1.1.1.6  christos       /* If this isn't something that can be relaxed, then ignore
   3007  1.1.1.6  christos          this reloc.  */
   3008  1.1.1.6  christos       if (ELF32_R_TYPE (irel->r_info) != (int) R_ARC_GOTPC32)
   3009  1.1.1.6  christos         continue;
   3010  1.1.1.6  christos 
   3011  1.1.1.6  christos       /* Get the section contents if we haven't done so already.  */
   3012  1.1.1.6  christos       if (contents == NULL)
   3013  1.1.1.6  christos         {
   3014  1.1.1.6  christos           /* Get cached copy if it exists.  */
   3015  1.1.1.6  christos           if (elf_section_data (sec)->this_hdr.contents != NULL)
   3016  1.1.1.6  christos             contents = elf_section_data (sec)->this_hdr.contents;
   3017  1.1.1.6  christos           /* Go get them off disk.  */
   3018  1.1.1.6  christos           else if (!bfd_malloc_and_get_section (abfd, sec, &contents))
   3019  1.1.1.6  christos             goto error_return;
   3020  1.1.1.6  christos         }
   3021  1.1.1.6  christos 
   3022  1.1.1.6  christos       /* Read this BFD's local symbols if we haven't done so already.  */
   3023  1.1.1.6  christos       if (isymbuf == NULL && symtab_hdr->sh_info != 0)
   3024  1.1.1.6  christos         {
   3025  1.1.1.6  christos           isymbuf = (Elf_Internal_Sym *) symtab_hdr->contents;
   3026  1.1.1.6  christos           if (isymbuf == NULL)
   3027  1.1.1.6  christos             isymbuf = bfd_elf_get_elf_syms (abfd, symtab_hdr,
   3028  1.1.1.6  christos                                             symtab_hdr->sh_info, 0,
   3029  1.1.1.6  christos                                             NULL, NULL, NULL);
   3030  1.1.1.6  christos           if (isymbuf == NULL)
   3031  1.1.1.6  christos             goto error_return;
   3032  1.1.1.6  christos         }
   3033  1.1.1.6  christos 
   3034  1.1.1.6  christos       struct elf_link_hash_entry *htop = NULL;
   3035  1.1.1.6  christos 
   3036  1.1.1.6  christos       if (ELF32_R_SYM (irel->r_info) >= symtab_hdr->sh_info)
   3037  1.1.1.6  christos 	{
   3038  1.1.1.6  christos 	  /* An external symbol.  */
   3039  1.1.1.6  christos 	  unsigned int indx = ELF32_R_SYM (irel->r_info) - symtab_hdr->sh_info;
   3040  1.1.1.6  christos 	  htop = elf_sym_hashes (abfd)[indx];
   3041  1.1.1.6  christos 	}
   3042  1.1.1.6  christos 
   3043  1.1.1.6  christos       if (ELF32_R_TYPE (irel->r_info) == (int) R_ARC_GOTPC32
   3044  1.1.1.6  christos 	  && SYMBOL_REFERENCES_LOCAL (link_info, htop))
   3045  1.1.1.6  christos 	{
   3046  1.1.1.6  christos 	  unsigned int code;
   3047  1.1.1.6  christos 
   3048  1.1.1.6  christos 	  /* Get the opcode.  */
   3049  1.1.1.6  christos 	  code = bfd_get_32_me (abfd, contents + irel->r_offset - 4);
   3050  1.1.1.6  christos 
   3051  1.1.1.6  christos 	  /* Note that we've changed the relocs, section contents, etc.  */
   3052  1.1.1.6  christos 	  elf_section_data (sec)->relocs = internal_relocs;
   3053  1.1.1.6  christos 	  elf_section_data (sec)->this_hdr.contents = contents;
   3054  1.1.1.6  christos 	  symtab_hdr->contents = (unsigned char *) isymbuf;
   3055  1.1.1.6  christos 
   3056  1.1.1.6  christos 	  /* Fix the relocation's type.  */
   3057  1.1.1.6  christos 	  irel->r_info = ELF32_R_INFO (ELF32_R_SYM (irel->r_info), R_ARC_PC32);
   3058  1.1.1.6  christos 
   3059  1.1.1.6  christos 	  /* ld rA,[pcl,symbol@tgot] -> add rA,pcl,symbol@pcl.  */
   3060  1.1.1.6  christos 	  /* 0010 0bbb aa11 0ZZX DBBB 1111 10AA AAAA.
   3061  1.1.1.6  christos 	           111 00    000 0111        xx xxxx*/
   3062  1.1.1.6  christos 	  code &= ~0x27307F80;
   3063  1.1.1.6  christos 	  BFD_ASSERT (code <= 62UL);
   3064  1.1.1.6  christos 	  code |= 0x27007F80;
   3065  1.1.1.6  christos 
   3066  1.1.1.6  christos 	  /* Write back the new instruction.  */
   3067  1.1.1.6  christos 	  bfd_put_32_me (abfd, code, contents + irel->r_offset - 4);
   3068  1.1.1.6  christos 
   3069  1.1.1.6  christos 	  /* The size isn't changed, don't redo.  */
   3070  1.1.1.7  christos 	  *again = false;
   3071  1.1.1.6  christos 	}
   3072  1.1.1.6  christos     }
   3073  1.1.1.6  christos 
   3074  1.1.1.6  christos   if (isymbuf != NULL
   3075  1.1.1.6  christos       && symtab_hdr->contents != (unsigned char *) isymbuf)
   3076  1.1.1.6  christos     {
   3077  1.1.1.6  christos       if (!link_info->keep_memory)
   3078  1.1.1.6  christos         free (isymbuf);
   3079  1.1.1.6  christos       else
   3080  1.1.1.6  christos        /* Cache the symbols for elf_link_input_bfd.  */
   3081  1.1.1.6  christos        symtab_hdr->contents = (unsigned char *) isymbuf;
   3082  1.1.1.6  christos     }
   3083  1.1.1.6  christos 
   3084  1.1.1.6  christos   if (contents != NULL
   3085  1.1.1.6  christos       && elf_section_data (sec)->this_hdr.contents != contents)
   3086  1.1.1.6  christos     {
   3087  1.1.1.6  christos       if (!link_info->keep_memory)
   3088  1.1.1.6  christos         free (contents);
   3089  1.1.1.6  christos       else
   3090  1.1.1.6  christos        /* Cache the section contents for elf_link_input_bfd.  */
   3091  1.1.1.6  christos        elf_section_data (sec)->this_hdr.contents = contents;
   3092  1.1.1.6  christos     }
   3093  1.1.1.6  christos 
   3094  1.1.1.7  christos   if (elf_section_data (sec)->relocs != internal_relocs)
   3095  1.1.1.6  christos     free (internal_relocs);
   3096  1.1.1.6  christos 
   3097  1.1.1.7  christos   return true;
   3098  1.1.1.6  christos 
   3099  1.1.1.6  christos  error_return:
   3100  1.1.1.7  christos   if (symtab_hdr->contents != (unsigned char *) isymbuf)
   3101  1.1.1.6  christos     free (isymbuf);
   3102  1.1.1.7  christos   if (elf_section_data (sec)->this_hdr.contents != contents)
   3103  1.1.1.6  christos     free (contents);
   3104  1.1.1.7  christos   if (elf_section_data (sec)->relocs != internal_relocs)
   3105  1.1.1.6  christos     free (internal_relocs);
   3106  1.1.1.6  christos 
   3107  1.1.1.7  christos   return false;
   3108  1.1.1.6  christos }
   3109  1.1.1.6  christos 
   3110  1.1.1.2  christos #define TARGET_LITTLE_SYM   arc_elf32_le_vec
   3111      1.1     skrll #define TARGET_LITTLE_NAME  "elf32-littlearc"
   3112  1.1.1.2  christos #define TARGET_BIG_SYM	    arc_elf32_be_vec
   3113  1.1.1.2  christos #define TARGET_BIG_NAME     "elf32-bigarc"
   3114  1.1.1.2  christos #define ELF_ARCH	    bfd_arch_arc
   3115  1.1.1.4  christos #define ELF_TARGET_ID	    ARC_ELF_DATA
   3116  1.1.1.2  christos #define ELF_MACHINE_CODE    EM_ARC_COMPACT
   3117  1.1.1.2  christos #define ELF_MACHINE_ALT1    EM_ARC_COMPACT2
   3118  1.1.1.2  christos #define ELF_MAXPAGESIZE     0x2000
   3119  1.1.1.2  christos 
   3120  1.1.1.3  christos #define bfd_elf32_bfd_link_hash_table_create	arc_elf_link_hash_table_create
   3121  1.1.1.3  christos 
   3122  1.1.1.3  christos #define bfd_elf32_bfd_merge_private_bfd_data    arc_elf_merge_private_bfd_data
   3123  1.1.1.3  christos #define bfd_elf32_bfd_reloc_type_lookup		arc_elf32_bfd_reloc_type_lookup
   3124  1.1.1.3  christos #define bfd_elf32_bfd_set_private_flags		arc_elf_set_private_flags
   3125  1.1.1.3  christos #define bfd_elf32_bfd_print_private_bfd_data    arc_elf_print_private_bfd_data
   3126  1.1.1.3  christos #define bfd_elf32_bfd_copy_private_bfd_data     arc_elf_copy_private_bfd_data
   3127  1.1.1.6  christos #define bfd_elf32_bfd_relax_section		arc_elf_relax_section
   3128  1.1.1.3  christos 
   3129  1.1.1.2  christos #define elf_info_to_howto_rel		     arc_info_to_howto_rel
   3130  1.1.1.2  christos #define elf_backend_object_p		     arc_elf_object_p
   3131  1.1.1.2  christos #define elf_backend_final_write_processing   arc_elf_final_write_processing
   3132  1.1.1.2  christos 
   3133  1.1.1.2  christos #define elf_backend_relocate_section	     elf_arc_relocate_section
   3134  1.1.1.2  christos #define elf_backend_check_relocs	     elf_arc_check_relocs
   3135  1.1.1.2  christos #define elf_backend_create_dynamic_sections  _bfd_elf_create_dynamic_sections
   3136  1.1.1.2  christos 
   3137  1.1.1.3  christos #define elf_backend_reloc_type_class		elf32_arc_reloc_type_class
   3138  1.1.1.3  christos 
   3139  1.1.1.2  christos #define elf_backend_adjust_dynamic_symbol    elf_arc_adjust_dynamic_symbol
   3140  1.1.1.2  christos #define elf_backend_finish_dynamic_symbol    elf_arc_finish_dynamic_symbol
   3141  1.1.1.2  christos 
   3142  1.1.1.2  christos #define elf_backend_finish_dynamic_sections  elf_arc_finish_dynamic_sections
   3143  1.1.1.2  christos #define elf_backend_size_dynamic_sections    elf_arc_size_dynamic_sections
   3144  1.1.1.2  christos 
   3145  1.1.1.2  christos #define elf_backend_can_gc_sections	1
   3146  1.1.1.2  christos #define elf_backend_want_got_plt	1
   3147  1.1.1.2  christos #define elf_backend_plt_readonly	1
   3148  1.1.1.3  christos #define elf_backend_rela_plts_and_copies_p 1
   3149  1.1.1.2  christos #define elf_backend_want_plt_sym	0
   3150  1.1.1.2  christos #define elf_backend_got_header_size	12
   3151  1.1.1.4  christos #define elf_backend_dtrel_excludes_plt	1
   3152  1.1.1.2  christos 
   3153  1.1.1.2  christos #define elf_backend_may_use_rel_p	0
   3154  1.1.1.2  christos #define elf_backend_may_use_rela_p	1
   3155  1.1.1.2  christos #define elf_backend_default_use_rela_p	1
   3156      1.1     skrll 
   3157  1.1.1.4  christos #define elf_backend_grok_prstatus elf32_arc_grok_prstatus
   3158  1.1.1.4  christos 
   3159  1.1.1.3  christos #define elf_backend_default_execstack	0
   3160  1.1.1.3  christos 
   3161  1.1.1.4  christos #undef  elf_backend_obj_attrs_vendor
   3162  1.1.1.4  christos #define elf_backend_obj_attrs_vendor		"ARC"
   3163  1.1.1.4  christos #undef  elf_backend_obj_attrs_section
   3164  1.1.1.4  christos #define elf_backend_obj_attrs_section		".ARC.attributes"
   3165  1.1.1.4  christos #undef  elf_backend_obj_attrs_arg_type
   3166  1.1.1.4  christos #define elf_backend_obj_attrs_arg_type		elf32_arc_obj_attrs_arg_type
   3167  1.1.1.4  christos #undef  elf_backend_obj_attrs_section_type
   3168  1.1.1.4  christos #define elf_backend_obj_attrs_section_type	SHT_ARC_ATTRIBUTES
   3169  1.1.1.4  christos #define elf_backend_obj_attrs_handle_unknown	elf32_arc_obj_attrs_handle_unknown
   3170  1.1.1.4  christos 
   3171  1.1.1.4  christos #define elf_backend_section_from_shdr		elf32_arc_section_from_shdr
   3172  1.1.1.4  christos 
   3173      1.1     skrll #include "elf32-target.h"
   3174