Develop and Download Open Source Software

Browse Subversion Repository

Diff of /trunk/bfd/elf32-score.c

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 20 by monamour, Thu Dec 4 05:12:56 2008 UTC revision 21 by monamour, Mon Jul 27 20:34:36 2009 UTC
# Line 1  Line 1 
1  /* 32-bit ELF support for S+core.  /* 32-bit ELF support for S+core.
2     Copyright 2006, 2007 Free Software Foundation, Inc.     Copyright 2006, 2007, 2008, 2009 Free Software Foundation, Inc.
3     Contributed by     Contributed by
4       Brain.lin (brain.lin@sunplusct.com)
5     Mei Ligang (ligang@sunnorth.com.cn)     Mei Ligang (ligang@sunnorth.com.cn)
6     Pei-Lin Tsai (pltsai@sunplus.com)     Pei-Lin Tsai (pltsai@sunplus.com)
7    
# Line 30  Line 31 
31  #include "elf/common.h"  #include "elf/common.h"
32  #include "elf/internal.h"  #include "elf/internal.h"
33  #include "hashtab.h"  #include "hashtab.h"
34    #include "elf32-score.h"
35    
36    
37  /* Score ELF linker hash table.  */  int score3 = 0;
38    int score7 = 1;
39    
40    /* Score ELF linker hash table.  */
41  struct score_elf_link_hash_table  struct score_elf_link_hash_table
42  {  {
43    /* The main hash table.  */    /* The main hash table.  */
# Line 42  struct score_elf_link_hash_table Line 46  struct score_elf_link_hash_table
46    
47  /* The SCORE ELF linker needs additional information for each symbol in  /* The SCORE ELF linker needs additional information for each symbol in
48     the global hash table.  */     the global hash table.  */
   
49  struct score_elf_link_hash_entry  struct score_elf_link_hash_entry
50  {  {
51    struct elf_link_hash_entry root;    struct elf_link_hash_entry root;
# Line 175  struct _score_elf_section_data Line 178  struct _score_elf_section_data
178  #define SCORE_ELF_STUB_SECTION_NAME  (".SCORE.stub")  #define SCORE_ELF_STUB_SECTION_NAME  (".SCORE.stub")
179  #define SCORE_FUNCTION_STUB_SIZE (16)  #define SCORE_FUNCTION_STUB_SIZE (16)
180    
181  #define STUB_LW      0xc3bcc010     /* lw r29, [r28, -0x3ff0]  */  #define STUB_LW      0xc3bcc010     /* lw r29, [r28, -0x3ff0]  */
182  #define STUB_MOVE    0x8363bc56     /* mv r27, r3  */  #define STUB_MOVE    0x8363bc56     /* mv r27, r3  */
183  #define STUB_LI16    0x87548000     /* ori r26, .dynsym_index  */  #define STUB_LI16    0x87548000     /* ori r26, .dynsym_index  */
184  #define STUB_BRL     0x801dbc09     /* brl r29  */  #define STUB_BRL     0x801dbc09     /* brl r29  */
# Line 198  struct _score_elf_section_data Line 201  struct _score_elf_section_data
201  #define SCORE_ELF_LOG_FILE_ALIGN(abfd)\  #define SCORE_ELF_LOG_FILE_ALIGN(abfd)\
202    (get_elf_backend_data (abfd)->s->log_file_align)    (get_elf_backend_data (abfd)->s->log_file_align)
203    
 #ifndef NUM_ELEM  
 #define NUM_ELEM(a)  (sizeof (a) / (sizeof (a)[0]))  
 #endif  
   
204  static bfd_byte *hi16_rel_addr;  static bfd_byte *hi16_rel_addr;
205    
206  /* This will be used when we sort the dynamic relocation records.  */  /* This will be used when we sort the dynamic relocation records.  */
# Line 216  static asection score_elf_scom_section; Line 215  static asection score_elf_scom_section;
215  static asymbol  score_elf_scom_symbol;  static asymbol  score_elf_scom_symbol;
216  static asymbol  *score_elf_scom_symbol_ptr;  static asymbol  *score_elf_scom_symbol_ptr;
217    
218    static bfd_vma
219    score_bfd_get_16 (bfd *abfd, const void *data)
220    {
221      return bfd_get_16 (abfd, data);
222    }
223    
224    static bfd_vma
225    score3_bfd_getl32 (const void *p)
226    {
227      const bfd_byte *addr = p;
228      unsigned long v;
229    
230      v = (unsigned long) addr[2];
231      v |= (unsigned long) addr[3] << 8;
232      v |= (unsigned long) addr[0] << 16;
233      v |= (unsigned long) addr[1] << 24;
234      return v;
235    }
236    
237    static bfd_vma
238    score3_bfd_getl48 (const void *p)
239    {
240      const bfd_byte *addr = p;
241      unsigned long long v;
242    
243      v = (unsigned long long) addr[4];
244      v |= (unsigned long long) addr[5] << 8;
245      v |= (unsigned long long) addr[2] << 16;
246      v |= (unsigned long long) addr[3] << 24;
247      v |= (unsigned long long) addr[0] << 32;
248      v |= (unsigned long long) addr[1] << 40;
249      return v;
250    }
251    
252    static bfd_vma
253    score_bfd_get_32 (bfd *abfd, const void *data)
254    {
255      if (/* score3 && */ abfd->xvec->byteorder == BFD_ENDIAN_LITTLE)
256        return score3_bfd_getl32 (data);
257      else
258        return bfd_get_32 (abfd, data);
259    }
260    
261    static bfd_vma
262    score_bfd_get_48 (bfd *abfd, const void *p)
263    {
264      if (/* score3 && */ abfd->xvec->byteorder == BFD_ENDIAN_LITTLE)
265        return score3_bfd_getl48 (p);
266      else
267        return bfd_get_bits (p, 48, 1);
268    }
269    
270    static void
271    score_bfd_put_16 (bfd *abfd, bfd_vma addr, void *data)
272    {
273      return bfd_put_16 (abfd, addr, data);
274    }
275    
276    static void
277    score3_bfd_putl32 (bfd_vma data, void *p)
278    {
279      bfd_byte *addr = p;
280      addr[0] = (data >> 16) & 0xff;
281      addr[1] = (data >> 24) & 0xff;
282      addr[2] = data & 0xff;
283      addr[3] = (data >>  8) & 0xff;
284    }
285    
286    static void
287    score3_bfd_putl48 (bfd_vma data, void *p)
288    {
289      bfd_byte *addr = p;
290      addr[0] = (data >> 32) & 0xff;
291      addr[1] = (data >> 40) & 0xff;
292      addr[2] = (data >> 16) & 0xff;
293      addr[3] = (data >> 24) & 0xff;
294      addr[4] = data & 0xff;
295      addr[5] = (data >>  8) & 0xff;
296    }
297    
298    static void
299    score_bfd_put_32 (bfd *abfd, bfd_vma addr, void *data)
300    {
301      if (/* score3 && */ abfd->xvec->byteorder == BFD_ENDIAN_LITTLE)
302        return score3_bfd_putl32 (addr, data);
303      else
304        return bfd_put_32 (abfd, addr, data);
305    }
306    
307    static void
308    score_bfd_put_48 (bfd *abfd, bfd_vma val, void *p)
309    {
310      if (/* score3 && */ abfd->xvec->byteorder == BFD_ENDIAN_LITTLE)
311        return score3_bfd_putl48 (val, p);
312      else
313        return bfd_put_bits (val, p, 48, 1);
314    }
315    
316  static bfd_reloc_status_type  static bfd_reloc_status_type
317  score_elf_hi16_reloc (bfd *abfd ATTRIBUTE_UNUSED,  score_elf_hi16_reloc (bfd *abfd ATTRIBUTE_UNUSED,
318                        arelent *reloc_entry,                        arelent *reloc_entry,
319                        asymbol *symbol ATTRIBUTE_UNUSED,                        asymbol *symbol ATTRIBUTE_UNUSED,
320                        void * data,                        void * data,
321                        asection *input_section ATTRIBUTE_UNUSED,                        asection *input_section ATTRIBUTE_UNUSED,
322                        bfd *output_bfd ATTRIBUTE_UNUSED,                        bfd *output_bfd ATTRIBUTE_UNUSED,
323                        char **error_message ATTRIBUTE_UNUSED)                        char **error_message ATTRIBUTE_UNUSED)
324  {  {
325    hi16_rel_addr = (bfd_byte *) data + reloc_entry->address;    hi16_rel_addr = (bfd_byte *) data + reloc_entry->address;
326    return bfd_reloc_ok;    return bfd_reloc_ok;
# Line 231  score_elf_hi16_reloc (bfd *abfd ATTRIBUT Line 328  score_elf_hi16_reloc (bfd *abfd ATTRIBUT
328    
329  static bfd_reloc_status_type  static bfd_reloc_status_type
330  score_elf_lo16_reloc (bfd *abfd,  score_elf_lo16_reloc (bfd *abfd,
331                        arelent *reloc_entry,                        arelent *reloc_entry,
332                        asymbol *symbol ATTRIBUTE_UNUSED,                        asymbol *symbol ATTRIBUTE_UNUSED,
333                        void * data,                        void * data,
334                        asection *input_section,                        asection *input_section,
335                        bfd *output_bfd ATTRIBUTE_UNUSED,                        bfd *output_bfd ATTRIBUTE_UNUSED,
336                        char **error_message ATTRIBUTE_UNUSED)                        char **error_message ATTRIBUTE_UNUSED)
337  {  {
338    bfd_vma addend = 0, offset = 0;    bfd_vma addend = 0, offset = 0;
339    unsigned long val;    unsigned long val;
340    unsigned long hi16_offset, hi16_value, uvalue;    unsigned long hi16_offset, hi16_value, uvalue;
341    
342    hi16_value = bfd_get_32 (abfd, hi16_rel_addr);    hi16_value = score_bfd_get_32 (abfd, hi16_rel_addr);
343    hi16_offset = ((((hi16_value >> 16) & 0x3) << 15) | (hi16_value & 0x7fff)) >> 1;    hi16_offset = ((((hi16_value >> 16) & 0x3) << 15) | (hi16_value & 0x7fff)) >> 1;
344    addend = bfd_get_32 (abfd, (bfd_byte *) data + reloc_entry->address);    addend = score_bfd_get_32 (abfd, (bfd_byte *) data + reloc_entry->address);
345    offset = ((((addend >> 16) & 0x3) << 15) | (addend & 0x7fff)) >> 1;    offset = ((((addend >> 16) & 0x3) << 15) | (addend & 0x7fff)) >> 1;
346    val = reloc_entry->addend;    val = reloc_entry->addend;
347    if (reloc_entry->address > input_section->size)    if (reloc_entry->address > input_section->size)
# Line 252  score_elf_lo16_reloc (bfd *abfd, Line 349  score_elf_lo16_reloc (bfd *abfd,
349    uvalue = ((hi16_offset << 16) | (offset & 0xffff)) + val;    uvalue = ((hi16_offset << 16) | (offset & 0xffff)) + val;
350    hi16_offset = (uvalue >> 16) << 1;    hi16_offset = (uvalue >> 16) << 1;
351    hi16_value = (hi16_value & ~0x37fff) | (hi16_offset & 0x7fff) | ((hi16_offset << 1) & 0x30000);    hi16_value = (hi16_value & ~0x37fff) | (hi16_offset & 0x7fff) | ((hi16_offset << 1) & 0x30000);
352    bfd_put_32 (abfd, hi16_value, hi16_rel_addr);    score_bfd_put_32 (abfd, hi16_value, hi16_rel_addr);
353    offset = (uvalue & 0xffff) << 1;    offset = (uvalue & 0xffff) << 1;
354    addend = (addend & ~0x37fff) | (offset & 0x7fff) | ((offset << 1) & 0x30000);    addend = (addend & ~0x37fff) | (offset & 0x7fff) | ((offset << 1) & 0x30000);
355    bfd_put_32 (abfd, addend, (bfd_byte *) data + reloc_entry->address);    score_bfd_put_32 (abfd, addend, (bfd_byte *) data + reloc_entry->address);
356    return bfd_reloc_ok;    return bfd_reloc_ok;
357  }  }
358    
# Line 284  score_elf_assign_gp (bfd *output_bfd, bf Line 381  score_elf_assign_gp (bfd *output_bfd, bf
381    else    else
382      {      {
383        for (i = 0; i < count; i++, sym++)        for (i = 0; i < count; i++, sym++)
384          {          {
385            const char *name;            const char *name;
386    
387            name = bfd_asymbol_name (*sym);            name = bfd_asymbol_name (*sym);
388            if (*name == '_' && strcmp (name, "_gp") == 0)            if (*name == '_' && strcmp (name, "_gp") == 0)
389              {              {
390                *pgp = bfd_asymbol_value (*sym);                *pgp = bfd_asymbol_value (*sym);
391                _bfd_set_gp_value (output_bfd, *pgp);                _bfd_set_gp_value (output_bfd, *pgp);
392                break;                break;
393              }              }
394          }          }
395      }      }
396    
397    if (i >= count)    if (i >= count)
# Line 313  score_elf_assign_gp (bfd *output_bfd, bf Line 410  score_elf_assign_gp (bfd *output_bfd, bf
410     BFD.  If we can't find it, we're stuck.  We cache it in the ELF     BFD.  If we can't find it, we're stuck.  We cache it in the ELF
411     target data.  We don't need to adjust the symbol value for an     target data.  We don't need to adjust the symbol value for an
412     external symbol if we are producing relocatable output.  */     external symbol if we are producing relocatable output.  */
   
413  static bfd_reloc_status_type  static bfd_reloc_status_type
414  score_elf_final_gp (bfd *output_bfd,  score_elf_final_gp (bfd *output_bfd,
415                      asymbol *symbol,                      asymbol *symbol,
416                      bfd_boolean relocatable,                      bfd_boolean relocatable,
417                      char **error_message,                       char **error_message,
418                      bfd_vma *pgp)                      bfd_vma *pgp)
419  {  {
420    if (bfd_is_und_section (symbol->section)    if (bfd_is_und_section (symbol->section)
421        && ! relocatable)        && ! relocatable)
# Line 331  score_elf_final_gp (bfd *output_bfd, Line 427  score_elf_final_gp (bfd *output_bfd,
427    *pgp = _bfd_get_gp_value (output_bfd);    *pgp = _bfd_get_gp_value (output_bfd);
428    if (*pgp == 0    if (*pgp == 0
429        && (! relocatable        && (! relocatable
430            || (symbol->flags & BSF_SECTION_SYM) != 0))            || (symbol->flags & BSF_SECTION_SYM) != 0))
431      {      {
432        if (relocatable)        if (relocatable)
433          {          {
434            /* Make up a value.  */            /* Make up a value.  */
435            *pgp = symbol->section->output_section->vma + 0x4000;            *pgp = symbol->section->output_section->vma + 0x4000;
436            _bfd_set_gp_value (output_bfd, *pgp);            _bfd_set_gp_value (output_bfd, *pgp);
437          }          }
438        else if (!score_elf_assign_gp (output_bfd, pgp))        else if (!score_elf_assign_gp (output_bfd, pgp))
439          {          {
440              *error_message =              *error_message =
441                (char *) _("GP relative relocation when _gp not defined");                (char *) _("GP relative relocation when _gp not defined");
442              return bfd_reloc_dangerous;              return bfd_reloc_dangerous;
443          }          }
444      }      }
445    
446    return bfd_reloc_ok;    return bfd_reloc_ok;
# Line 352  score_elf_final_gp (bfd *output_bfd, Line 448  score_elf_final_gp (bfd *output_bfd,
448    
449  static bfd_reloc_status_type  static bfd_reloc_status_type
450  score_elf_gprel15_with_gp (bfd *abfd,  score_elf_gprel15_with_gp (bfd *abfd,
451                             asymbol *symbol,                             asymbol *symbol,
452                             arelent *reloc_entry,                             arelent *reloc_entry,
453                             asection *input_section,                             asection *input_section,
454                             bfd_boolean relocateable,                             bfd_boolean relocateable,
455                             void * data,                             void * data,
456                             bfd_vma gp ATTRIBUTE_UNUSED)                             bfd_vma gp ATTRIBUTE_UNUSED)
457  {  {
458    bfd_vma relocation;    bfd_vma relocation;
459    unsigned long insn;    unsigned long insn;
# Line 372  score_elf_gprel15_with_gp (bfd *abfd, Line 468  score_elf_gprel15_with_gp (bfd *abfd,
468    if (reloc_entry->address > input_section->size)    if (reloc_entry->address > input_section->size)
469      return bfd_reloc_outofrange;      return bfd_reloc_outofrange;
470    
471    insn = bfd_get_32 (abfd, (bfd_byte *) data + reloc_entry->address);    insn = score_bfd_get_32 (abfd, (bfd_byte *) data + reloc_entry->address);
472    if (((reloc_entry->addend & 0xffffc000) != 0)    if (((reloc_entry->addend & 0xffffc000) != 0)
473        && ((reloc_entry->addend & 0xffffc000) != 0xffffc000))        && ((reloc_entry->addend & 0xffffc000) != 0xffffc000))
474      return bfd_reloc_overflow;      return bfd_reloc_overflow;
475    
476    insn = (insn & ~0x7fff) | (reloc_entry->addend & 0x7fff);    insn = (insn & ~0x7fff) | (reloc_entry->addend & 0x7fff);
477    bfd_put_32 (abfd, insn, (bfd_byte *) data + reloc_entry->address);    score_bfd_put_32 (abfd, insn, (bfd_byte *) data + reloc_entry->address);
478    if (relocateable)    if (relocateable)
479      reloc_entry->address += input_section->output_offset;      reloc_entry->address += input_section->output_offset;
480    
# Line 387  score_elf_gprel15_with_gp (bfd *abfd, Line 483  score_elf_gprel15_with_gp (bfd *abfd,
483    
484  static bfd_reloc_status_type  static bfd_reloc_status_type
485  gprel32_with_gp (bfd *abfd, asymbol *symbol, arelent *reloc_entry,  gprel32_with_gp (bfd *abfd, asymbol *symbol, arelent *reloc_entry,
486                   asection *input_section, bfd_boolean relocatable,                   asection *input_section, bfd_boolean relocatable,
487                   void *data, bfd_vma gp)                   void *data, bfd_vma gp)
488  {  {
489    bfd_vma relocation;    bfd_vma relocation;
490    bfd_vma val;    bfd_vma val;
# Line 408  gprel32_with_gp (bfd *abfd, asymbol *sym Line 504  gprel32_with_gp (bfd *abfd, asymbol *sym
504    val = reloc_entry->addend;    val = reloc_entry->addend;
505    
506    if (reloc_entry->howto->partial_inplace)    if (reloc_entry->howto->partial_inplace)
507      val += bfd_get_32 (abfd, (bfd_byte *) data + reloc_entry->address);      val += score_bfd_get_32 (abfd, (bfd_byte *) data + reloc_entry->address);
508    
509    /* Adjust val for the final section location and GP value.  If we    /* Adjust val for the final section location and GP value.  If we
510       are producing relocatable output, we don't want to do this for       are producing relocatable output, we don't want to do this for
# Line 418  gprel32_with_gp (bfd *abfd, asymbol *sym Line 514  gprel32_with_gp (bfd *abfd, asymbol *sym
514      val += relocation - gp;      val += relocation - gp;
515    
516    if (reloc_entry->howto->partial_inplace)    if (reloc_entry->howto->partial_inplace)
517      bfd_put_32 (abfd, val, (bfd_byte *) data + reloc_entry->address);      score_bfd_put_32 (abfd, val, (bfd_byte *) data + reloc_entry->address);
518    else    else
519      reloc_entry->addend = val;      reloc_entry->addend = val;
520    
# Line 430  gprel32_with_gp (bfd *abfd, asymbol *sym Line 526  gprel32_with_gp (bfd *abfd, asymbol *sym
526    
527  static bfd_reloc_status_type  static bfd_reloc_status_type
528  score_elf_gprel15_reloc (bfd *abfd,  score_elf_gprel15_reloc (bfd *abfd,
529                           arelent *reloc_entry,                           arelent *reloc_entry,
530                           asymbol *symbol,                           asymbol *symbol,
531                           void * data,                           void * data,
532                           asection *input_section,                           asection *input_section,
533                           bfd *output_bfd,                           bfd *output_bfd,
534                           char **error_message)                           char **error_message)
535  {  {
536    bfd_boolean relocateable;    bfd_boolean relocateable;
537    bfd_reloc_status_type ret;    bfd_reloc_status_type ret;
538    bfd_vma gp;    bfd_vma gp;
539    
540    if (output_bfd != (bfd *) NULL    if (output_bfd != NULL
541        && (symbol->flags & BSF_SECTION_SYM) == 0 && reloc_entry->addend == 0)        && (symbol->flags & BSF_SECTION_SYM) == 0 && reloc_entry->addend == 0)
542      {      {
543        reloc_entry->address += input_section->output_offset;        reloc_entry->address += input_section->output_offset;
544        return bfd_reloc_ok;        return bfd_reloc_ok;
545      }      }
546    if (output_bfd != (bfd *) NULL)    if (output_bfd != NULL)
547      relocateable = TRUE;      relocateable = TRUE;
548    else    else
549      {      {
# Line 468  score_elf_gprel15_reloc (bfd *abfd, Line 564  score_elf_gprel15_reloc (bfd *abfd,
564    
565  static bfd_reloc_status_type  static bfd_reloc_status_type
566  score_elf_gprel32_reloc (bfd *abfd, arelent *reloc_entry, asymbol *symbol,  score_elf_gprel32_reloc (bfd *abfd, arelent *reloc_entry, asymbol *symbol,
567                          void *data, asection *input_section, bfd *output_bfd,                          void *data, asection *input_section, bfd *output_bfd,
568                          char **error_message)                          char **error_message)
569  {  {
570    bfd_boolean relocatable;    bfd_boolean relocatable;
571    bfd_reloc_status_type ret;    bfd_reloc_status_type ret;
# Line 481  score_elf_gprel32_reloc (bfd *abfd, arel Line 577  score_elf_gprel32_reloc (bfd *abfd, arel
577        && (symbol->flags & BSF_LOCAL) != 0)        && (symbol->flags & BSF_LOCAL) != 0)
578      {      {
579        *error_message = (char *)        *error_message = (char *)
580          _("32bits gp relative relocation occurs for an external symbol");          _("32bits gp relative relocation occurs for an external symbol");
581        return bfd_reloc_outofrange;        return bfd_reloc_outofrange;
582      }      }
583    
# Line 497  score_elf_gprel32_reloc (bfd *abfd, arel Line 593  score_elf_gprel32_reloc (bfd *abfd, arel
593    if (ret != bfd_reloc_ok)    if (ret != bfd_reloc_ok)
594      return ret;      return ret;
595    
596    gp = 0;   /* FIXME.  */    gp = 0;
597    return gprel32_with_gp (abfd, symbol, reloc_entry, input_section,    return gprel32_with_gp (abfd, symbol, reloc_entry, input_section,
598                            relocatable, data, gp);                            relocatable, data, gp);
599  }  }
600    
601  /* A howto special_function for R_SCORE_GOT15 relocations.  This is just  /* A howto special_function for R_SCORE_GOT15 relocations.  This is just
602     like any other 16-bit relocation when applied to global symbols, but is     like any other 16-bit relocation when applied to global symbols, but is
603     treated in the same as R_SCORE_HI16 when applied to local symbols.  */     treated in the same as R_SCORE_HI16 when applied to local symbols.  */
   
604  static bfd_reloc_status_type  static bfd_reloc_status_type
605  score_elf_got15_reloc (bfd *abfd, arelent *reloc_entry, asymbol *symbol,  score_elf_got15_reloc (bfd *abfd, arelent *reloc_entry, asymbol *symbol,
606                         void *data, asection *input_section,                         void *data, asection *input_section,
607                         bfd *output_bfd, char **error_message)                         bfd *output_bfd, char **error_message)
608  {  {
609    if ((symbol->flags & (BSF_GLOBAL | BSF_WEAK)) != 0    if ((symbol->flags & (BSF_GLOBAL | BSF_WEAK)) != 0
610        || bfd_is_und_section (bfd_get_section (symbol))        || bfd_is_und_section (bfd_get_section (symbol))
611        || bfd_is_com_section (bfd_get_section (symbol)))        || bfd_is_com_section (bfd_get_section (symbol)))
612      /* The relocation is against a global symbol.  */      /* The relocation is against a global symbol.  */
613      return bfd_elf_generic_reloc (abfd, reloc_entry, symbol, data,      return bfd_elf_generic_reloc (abfd, reloc_entry, symbol, data,
614                                    input_section, output_bfd,                                    input_section, output_bfd,
615                                    error_message);                                    error_message);
616    
617    return score_elf_hi16_reloc (abfd, reloc_entry, symbol, data,    return score_elf_hi16_reloc (abfd, reloc_entry, symbol, data,
618                                 input_section, output_bfd, error_message);                                 input_section, output_bfd, error_message);
619  }  }
620    
621  static bfd_reloc_status_type  static bfd_reloc_status_type
622  score_elf_got_lo16_reloc (bfd *abfd,  score_elf_got_lo16_reloc (bfd *abfd,
623                            arelent *reloc_entry,                            arelent *reloc_entry,
624                            asymbol *symbol ATTRIBUTE_UNUSED,                            asymbol *symbol ATTRIBUTE_UNUSED,
625                            void * data,                            void * data,
626                            asection *input_section,                            asection *input_section,
627                            bfd *output_bfd ATTRIBUTE_UNUSED,                            bfd *output_bfd ATTRIBUTE_UNUSED,
628                            char **error_message ATTRIBUTE_UNUSED)                            char **error_message ATTRIBUTE_UNUSED)
629  {  {
630    bfd_vma addend = 0, offset = 0;    bfd_vma addend = 0, offset = 0;
631    signed long val;    signed long val;
632    signed long hi16_offset, hi16_value, uvalue;    signed long hi16_offset, hi16_value, uvalue;
633    
634    hi16_value = bfd_get_32 (abfd, hi16_rel_addr);    hi16_value = score_bfd_get_32 (abfd, hi16_rel_addr);
635    hi16_offset = ((((hi16_value >> 16) & 0x3) << 15) | (hi16_value & 0x7fff)) >> 1;    hi16_offset = ((((hi16_value >> 16) & 0x3) << 15) | (hi16_value & 0x7fff)) >> 1;
636    addend = bfd_get_32 (abfd, (bfd_byte *) data + reloc_entry->address);    addend = score_bfd_get_32 (abfd, (bfd_byte *) data + reloc_entry->address);
637    offset = ((((addend >> 16) & 0x3) << 15) | (addend & 0x7fff)) >> 1;    offset = ((((addend >> 16) & 0x3) << 15) | (addend & 0x7fff)) >> 1;
638    val = reloc_entry->addend;    val = reloc_entry->addend;
639    if (reloc_entry->address > input_section->size)    if (reloc_entry->address > input_section->size)
# Line 549  score_elf_got_lo16_reloc (bfd *abfd, Line 644  score_elf_got_lo16_reloc (bfd *abfd,
644    else    else
645      hi16_offset = (uvalue >> 16) & 0x7fff;      hi16_offset = (uvalue >> 16) & 0x7fff;
646    hi16_value = (hi16_value & ~0x37fff) | (hi16_offset & 0x7fff) | ((hi16_offset << 1) & 0x30000);    hi16_value = (hi16_value & ~0x37fff) | (hi16_offset & 0x7fff) | ((hi16_offset << 1) & 0x30000);
647    bfd_put_32 (abfd, hi16_value, hi16_rel_addr);    score_bfd_put_32 (abfd, hi16_value, hi16_rel_addr);
648    offset = (uvalue & 0xffff) << 1;    offset = (uvalue & 0xffff) << 1;
649    addend = (addend & ~0x37fff) | (offset & 0x7fff) | ((offset << 1) & 0x30000);    addend = (addend & ~0x37fff) | (offset & 0x7fff) | ((offset << 1) & 0x30000);
650    bfd_put_32 (abfd, addend, (bfd_byte *) data + reloc_entry->address);    score_bfd_put_32 (abfd, addend, (bfd_byte *) data + reloc_entry->address);
651    return bfd_reloc_ok;    return bfd_reloc_ok;
652  }  }
653    
# Line 581  static reloc_howto_type elf32_score_howt Line 676  static reloc_howto_type elf32_score_howt
676           FALSE,                 /* pc_relative */           FALSE,                 /* pc_relative */
677           1,                     /* bitpos */           1,                     /* bitpos */
678           complain_overflow_dont,/* complain_on_overflow */           complain_overflow_dont,/* complain_on_overflow */
679           score_elf_hi16_reloc,  /* special_function */           score_elf_hi16_reloc,  /* special_function */
680           "R_SCORE_HI16",        /* name */           "R_SCORE_HI16",        /* name */
681           TRUE,                  /* partial_inplace */           TRUE,                  /* partial_inplace */
682           0x37fff,               /* src_mask */           0x37fff,               /* src_mask */
# Line 603  static reloc_howto_type elf32_score_howt Line 698  static reloc_howto_type elf32_score_howt
698           0x37fff,               /* dst_mask */           0x37fff,               /* dst_mask */
699           FALSE),                /* pcrel_offset */           FALSE),                /* pcrel_offset */
700    
701    /*  R_SCORE_DUMMY1 */    /*  R_SCORE_BCMP */
702    HOWTO (R_SCORE_DUMMY1,        /* type */    HOWTO (R_SCORE_BCMP,          /* type */
703           0,                     /* rightshift */           1,                     /* rightshift */
704           2,                     /* size (0 = byte, 1 = short, 2 = long) */           2,                     /* size (0 = byte, 1 = short, 2 = long) */
705           16,                    /* bitsize */           16,                    /* bitsize */
706           FALSE,                 /* pc_relative */           TRUE,                  /* pc_relative */
707           1,                     /* bitpos */           1,                     /* bitpos */
708           complain_overflow_dont,/* complain_on_overflow */           complain_overflow_dont,/* complain_on_overflow */
709           bfd_elf_generic_reloc, /* special_function */           bfd_elf_generic_reloc, /* special_function */
710           "R_SCORE_DUMMY1",      /* name */           "R_SCORE_BCMP",        /* name */
711           TRUE,                  /* partial_inplace */           FALSE,                 /* partial_inplace */
712           0x0000ffff,            /* src_mask */           0x03e00381,            /* src_mask */
713           0x0000ffff,            /* dst_mask */           0x03e00381,            /* dst_mask */
714           FALSE),                /* pcrel_offset */           FALSE),                /* pcrel_offset */
715    
716    /*R_SCORE_24 */    /*R_SCORE_24 */
# Line 667  static reloc_howto_type elf32_score_howt Line 762  static reloc_howto_type elf32_score_howt
762    HOWTO (R_SCORE16_PC8,         /* type */    HOWTO (R_SCORE16_PC8,         /* type */
763           1,                     /* rightshift */           1,                     /* rightshift */
764           1,                     /* size (0 = byte, 1 = short, 2 = long) */           1,                     /* size (0 = byte, 1 = short, 2 = long) */
765           8,                     /* bitsize */           9,                     /* bitsize */
766           TRUE,                  /* pc_relative */           TRUE,                  /* pc_relative */
767           0,                     /* bitpos */           0,                     /* bitpos */
768           complain_overflow_dont,/* complain_on_overflow */           complain_overflow_dont,/* complain_on_overflow */
769           bfd_elf_generic_reloc, /* special_function */           bfd_elf_generic_reloc, /* special_function */
770           "R_SCORE16_PC8",       /* name */           "R_SCORE16_PC8",       /* name */
771           FALSE,                 /* partial_inplace */           FALSE,                 /* partial_inplace */
772           0x000000ff,            /* src_mask */           0x000001ff,            /* src_mask */
773           0x000000ff,            /* dst_mask */           0x000001ff,            /* dst_mask */
774           FALSE),                /* pcrel_offset */           FALSE),                /* pcrel_offset */
775    
776    /* 32 bit absolute */    /* 32 bit absolute */
# Line 830  static reloc_howto_type elf32_score_howt Line 925  static reloc_howto_type elf32_score_howt
925    
926    /* 32 bit symbol relative relocation.  */    /* 32 bit symbol relative relocation.  */
927    HOWTO (R_SCORE_REL32,         /* type */    HOWTO (R_SCORE_REL32,         /* type */
928           0,                     /* rightshift */           0,                     /* rightshift */
929           2,                     /* size (0 = byte, 1 = short, 2 = long) */           2,                     /* size (0 = byte, 1 = short, 2 = long) */
930           32,                    /* bitsize */           32,                    /* bitsize */
931           FALSE,                 /* pc_relative */           FALSE,                 /* pc_relative */
932           0,                     /* bitpos */           0,                     /* bitpos */
933           complain_overflow_dont,/* complain_on_overflow */           complain_overflow_dont,/* complain_on_overflow */
934           bfd_elf_generic_reloc, /* special_function */           bfd_elf_generic_reloc, /* special_function */
935           "R_SCORE_REL32",       /* name */           "R_SCORE_REL32",       /* name */
936           TRUE,                  /* partial_inplace */           TRUE,                  /* partial_inplace */
937           0xffffffff,            /* src_mask */           0xffffffff,            /* src_mask */
938           0xffffffff,            /* dst_mask */           0xffffffff,            /* dst_mask */
939           FALSE),                /* pcrel_offset */           FALSE),                /* pcrel_offset */
940    
941    /* R_SCORE_DUMMY_HI16 */    /* R_SCORE_DUMMY_HI16 */
942    HOWTO (R_SCORE_DUMMY_HI16,    /* type */    HOWTO (R_SCORE_DUMMY_HI16,    /* type */
# Line 851  static reloc_howto_type elf32_score_howt Line 946  static reloc_howto_type elf32_score_howt
946           FALSE,                 /* pc_relative */           FALSE,                 /* pc_relative */
947           1,                     /* bitpos */           1,                     /* bitpos */
948           complain_overflow_dont,/* complain_on_overflow */           complain_overflow_dont,/* complain_on_overflow */
949           score_elf_hi16_reloc,  /* special_function */           score_elf_hi16_reloc,  /* special_function */
950           "R_SCORE_DUMMY_HI16",  /* name */           "R_SCORE_DUMMY_HI16",  /* name */
951           TRUE,                  /* partial_inplace */           TRUE,                  /* partial_inplace */
952           0x37fff,               /* src_mask */           0x37fff,               /* src_mask */
953           0x37fff,               /* dst_mask */           0x37fff,               /* dst_mask */
954           FALSE),                /* pcrel_offset */           FALSE),                /* pcrel_offset */
955    
956      /* R_SCORE_IMM30 */
957      HOWTO (R_SCORE_IMM30,         /* type */
958             2,                     /* rightshift */
959             2,                     /* size (0 = byte, 1 = short, 2 = long) */
960             30,                    /* bitsize */
961             FALSE,                 /* pc_relative */
962             7,                     /* bitpos */
963             complain_overflow_dont,/* complain_on_overflow */
964             bfd_elf_generic_reloc, /* special_function */
965             "R_SCORE_IMM30",       /* name */
966             FALSE,                 /* partial_inplace */
967             0x7f7fff7f80LL,        /* src_mask */
968             0x7f7fff7f80LL,        /* dst_mask */
969             FALSE),                /* pcrel_offset */
970    
971      /* R_SCORE_IMM32 */
972      HOWTO (R_SCORE_IMM32,         /* type */
973             0,                     /* rightshift */
974             2,                     /* size (0 = byte, 1 = short, 2 = long) */
975             32,                    /* bitsize */
976             FALSE,                 /* pc_relative */
977             5,                     /* bitpos */
978             complain_overflow_dont,/* complain_on_overflow */
979             bfd_elf_generic_reloc, /* special_function */
980             "R_SCORE_IMM32",       /* name */
981             FALSE,                 /* partial_inplace */
982             0x7f7fff7fe0LL,        /* src_mask */
983             0x7f7fff7fe0LL,        /* dst_mask */
984             FALSE),                /* pcrel_offset */
985  };  };
986    
987  struct score_reloc_map  struct score_reloc_map
# Line 870  static const struct score_reloc_map elf3 Line 995  static const struct score_reloc_map elf3
995    {BFD_RELOC_NONE,               R_SCORE_NONE},    {BFD_RELOC_NONE,               R_SCORE_NONE},
996    {BFD_RELOC_HI16_S,             R_SCORE_HI16},    {BFD_RELOC_HI16_S,             R_SCORE_HI16},
997    {BFD_RELOC_LO16,               R_SCORE_LO16},    {BFD_RELOC_LO16,               R_SCORE_LO16},
998    {BFD_RELOC_SCORE_DUMMY1,       R_SCORE_DUMMY1},    {BFD_RELOC_SCORE_BCMP,         R_SCORE_BCMP},
999    {BFD_RELOC_SCORE_JMP,          R_SCORE_24},    {BFD_RELOC_SCORE_JMP,          R_SCORE_24},
1000    {BFD_RELOC_SCORE_BRANCH,       R_SCORE_PC19},    {BFD_RELOC_SCORE_BRANCH,       R_SCORE_PC19},
1001    {BFD_RELOC_SCORE16_JMP,        R_SCORE16_11},    {BFD_RELOC_SCORE16_JMP,        R_SCORE16_11},
# Line 887  static const struct score_reloc_map elf3 Line 1012  static const struct score_reloc_map elf3
1012    {BFD_RELOC_GPREL32,            R_SCORE_GPREL32},    {BFD_RELOC_GPREL32,            R_SCORE_GPREL32},
1013    {BFD_RELOC_32_PCREL,           R_SCORE_REL32},    {BFD_RELOC_32_PCREL,           R_SCORE_REL32},
1014    {BFD_RELOC_SCORE_DUMMY_HI16,   R_SCORE_DUMMY_HI16},    {BFD_RELOC_SCORE_DUMMY_HI16,   R_SCORE_DUMMY_HI16},
1015      {BFD_RELOC_SCORE_IMM30,        R_SCORE_IMM30},
1016      {BFD_RELOC_SCORE_IMM32,        R_SCORE_IMM32},
1017  };  };
1018    
1019  /* got_entries only match if they're identical, except for gotidx, so  /* got_entries only match if they're identical, except for gotidx, so
1020     use all fields to compute the hash, and compare the appropriate     use all fields to compute the hash, and compare the appropriate
1021     union members.  */     union members.  */
   
1022  static hashval_t  static hashval_t
1023  score_elf_got_entry_hash (const void *entry_)  score_elf_got_entry_hash (const void *entry_)
1024  {  {
# Line 910  score_elf_got_entry_eq (const void *entr Line 1036  score_elf_got_entry_eq (const void *entr
1036    
1037    return e1->abfd == e2->abfd && e1->symndx == e2->symndx    return e1->abfd == e2->abfd && e1->symndx == e2->symndx
1038      && (! e1->abfd ? e1->d.address == e2->d.address      && (! e1->abfd ? e1->d.address == e2->d.address
1039          : e1->symndx >= 0 ? e1->d.addend == e2->d.addend          : e1->symndx >= 0 ? e1->d.addend == e2->d.addend
1040          : e1->d.h == e2->d.h);          : e1->d.h == e2->d.h);
1041  }  }
1042    
1043  /* If H needs a GOT entry, assign it the highest available dynamic  /* If H needs a GOT entry, assign it the highest available dynamic
1044     index.  Otherwise, assign it the lowest available dynamic     index.  Otherwise, assign it the lowest available dynamic
1045     index.  */     index.  */
   
1046  static bfd_boolean  static bfd_boolean
1047  score_elf_sort_hash_table_f (struct score_elf_link_hash_entry *h, void *data)  score_elf_sort_hash_table_f (struct score_elf_link_hash_entry *h, void *data)
1048  {  {
# Line 937  score_elf_sort_hash_table_f (struct scor Line 1062  score_elf_sort_hash_table_f (struct scor
1062    if (h->root.got.offset == 2)    if (h->root.got.offset == 2)
1063      {      {
1064        if (hsd->max_unref_got_dynindx == hsd->min_got_dynindx)        if (hsd->max_unref_got_dynindx == hsd->min_got_dynindx)
1065          hsd->low = (struct elf_link_hash_entry *) h;          hsd->low = (struct elf_link_hash_entry *) h;
1066        h->root.dynindx = hsd->max_unref_got_dynindx++;        h->root.dynindx = hsd->max_unref_got_dynindx++;
1067      }      }
1068    else if (h->root.got.offset != 1)    else if (h->root.got.offset != 1)
# Line 963  score_elf_got_section (bfd *abfd, bfd_bo Line 1088  score_elf_got_section (bfd *abfd, bfd_bo
1088    
1089  /* Returns the GOT information associated with the link indicated by  /* Returns the GOT information associated with the link indicated by
1090     INFO.  If SGOTP is non-NULL, it is filled in with the GOT section.  */     INFO.  If SGOTP is non-NULL, it is filled in with the GOT section.  */
   
1091  static struct score_got_info *  static struct score_got_info *
1092  score_elf_got_info (bfd *abfd, asection **sgotp)  score_elf_got_info (bfd *abfd, asection **sgotp)
1093  {  {
# Line 985  score_elf_got_info (bfd *abfd, asection Line 1109  score_elf_got_info (bfd *abfd, asection
1109     appear towards the end.  This reduces the amount of GOT space     appear towards the end.  This reduces the amount of GOT space
1110     required.  MAX_LOCAL is used to set the number of local symbols     required.  MAX_LOCAL is used to set the number of local symbols
1111     known to be in the dynamic symbol table.  During     known to be in the dynamic symbol table.  During
1112     _bfd_score_elf_size_dynamic_sections, this value is 1.  Afterward, the     s3_bfd_score_elf_size_dynamic_sections, this value is 1.  Afterward, the
1113     section symbols are added and the count is higher.  */     section symbols are added and the count is higher.  */
   
1114  static bfd_boolean  static bfd_boolean
1115  score_elf_sort_hash_table (struct bfd_link_info *info,  score_elf_sort_hash_table (struct bfd_link_info *info,
1116                             unsigned long max_local)                             unsigned long max_local)
1117  {  {
1118    struct score_elf_hash_sort_data hsd;    struct score_elf_hash_sort_data hsd;
1119    struct score_got_info *g;    struct score_got_info *g;
# Line 1013  score_elf_sort_hash_table (struct bfd_li Line 1136  score_elf_sort_hash_table (struct bfd_li
1136      - (g->next ? g->assigned_gotno : 0);      - (g->next ? g->assigned_gotno : 0);
1137    hsd.max_non_got_dynindx = max_local;    hsd.max_non_got_dynindx = max_local;
1138    score_elf_link_hash_traverse (((struct score_elf_link_hash_table *)    score_elf_link_hash_traverse (((struct score_elf_link_hash_table *)
1139                                   elf_hash_table (info)),                                   elf_hash_table (info)),
1140                                   score_elf_sort_hash_table_f,                                   score_elf_sort_hash_table_f,
1141                                   &hsd);                                   &hsd);
1142    
1143    /* There should have been enough room in the symbol table to    /* There should have been enough room in the symbol table to
1144       accommodate both the GOT and non-GOT symbols.  */       accommodate both the GOT and non-GOT symbols.  */
1145    BFD_ASSERT (hsd.max_non_got_dynindx <= hsd.min_got_dynindx);    BFD_ASSERT (hsd.max_non_got_dynindx <= hsd.min_got_dynindx);
1146    BFD_ASSERT ((unsigned long)hsd.max_unref_got_dynindx    BFD_ASSERT ((unsigned long)hsd.max_unref_got_dynindx
1147                <= elf_hash_table (info)->dynsymcount);                <= elf_hash_table (info)->dynsymcount);
1148    
1149    /* Now we know which dynamic symbol has the lowest dynamic symbol    /* Now we know which dynamic symbol has the lowest dynamic symbol
1150       table index in the GOT.  */       table index in the GOT.  */
# Line 1031  score_elf_sort_hash_table (struct bfd_li Line 1154  score_elf_sort_hash_table (struct bfd_li
1154  }  }
1155    
1156  /* Create an entry in an score ELF linker hash table.  */  /* Create an entry in an score ELF linker hash table.  */
   
1157  static struct bfd_hash_entry *  static struct bfd_hash_entry *
1158  score_elf_link_hash_newfunc (struct bfd_hash_entry *entry,  score_elf_link_hash_newfunc (struct bfd_hash_entry *entry,
1159                               struct bfd_hash_table *table,                               struct bfd_hash_table *table,
1160                               const char *string)                               const char *string)
1161  {  {
1162    struct score_elf_link_hash_entry *ret = (struct score_elf_link_hash_entry *)entry;    struct score_elf_link_hash_entry *ret = (struct score_elf_link_hash_entry *)entry;
1163    
# Line 1062  score_elf_link_hash_newfunc (struct bfd_ Line 1184  score_elf_link_hash_newfunc (struct bfd_
1184    
1185  /* Returns the first relocation of type r_type found, beginning with  /* Returns the first relocation of type r_type found, beginning with
1186     RELOCATION.  RELEND is one-past-the-end of the relocation table.  */     RELOCATION.  RELEND is one-past-the-end of the relocation table.  */
   
1187  static const Elf_Internal_Rela *  static const Elf_Internal_Rela *
1188  score_elf_next_relocation (bfd *abfd ATTRIBUTE_UNUSED, unsigned int r_type,  score_elf_next_relocation (bfd *abfd ATTRIBUTE_UNUSED, unsigned int r_type,
1189                             const Elf_Internal_Rela *relocation,                              const Elf_Internal_Rela *relocation,
1190                             const Elf_Internal_Rela *relend)                             const Elf_Internal_Rela *relend)
1191  {  {
1192    while (relocation < relend)    while (relocation < relend)
1193      {      {
1194        if (ELF32_R_TYPE (relocation->r_info) == r_type)        if (ELF32_R_TYPE (relocation->r_info) == r_type)
1195          return relocation;          return relocation;
1196    
1197        ++relocation;        ++relocation;
1198      }      }
# Line 1083  score_elf_next_relocation (bfd *abfd ATT Line 1204  score_elf_next_relocation (bfd *abfd ATT
1204    
1205  /* This function is called via qsort() to sort the dynamic relocation  /* This function is called via qsort() to sort the dynamic relocation
1206     entries by increasing r_symndx value.  */     entries by increasing r_symndx value.  */
   
1207  static int  static int
1208  score_elf_sort_dynamic_relocs (const void *arg1, const void *arg2)  score_elf_sort_dynamic_relocs (const void *arg1, const void *arg2)
1209  {  {
# Line 1097  score_elf_sort_dynamic_relocs (const voi Line 1217  score_elf_sort_dynamic_relocs (const voi
1217  }  }
1218    
1219  /* Return whether a relocation is against a local symbol.  */  /* Return whether a relocation is against a local symbol.  */
   
1220  static bfd_boolean  static bfd_boolean
1221  score_elf_local_relocation_p (bfd *input_bfd,  score_elf_local_relocation_p (bfd *input_bfd,
1222                                const Elf_Internal_Rela *relocation,                                const Elf_Internal_Rela *relocation,
1223                                bfd_boolean check_forced)                                asection **local_sections,
1224                                  bfd_boolean check_forced)
1225  {  {
1226    unsigned long r_symndx;    unsigned long r_symndx;
1227    Elf_Internal_Shdr *symtab_hdr;    Elf_Internal_Shdr *symtab_hdr;
# Line 1110  score_elf_local_relocation_p (bfd *input Line 1230  score_elf_local_relocation_p (bfd *input
1230    
1231    r_symndx = ELF32_R_SYM (relocation->r_info);    r_symndx = ELF32_R_SYM (relocation->r_info);
1232    symtab_hdr = &elf_tdata (input_bfd)->symtab_hdr;    symtab_hdr = &elf_tdata (input_bfd)->symtab_hdr;
1233    extsymoff = symtab_hdr->sh_info;    extsymoff = (elf_bad_symtab (input_bfd)) ? 0 : symtab_hdr->sh_info;
1234    
1235    if (r_symndx < extsymoff)    if (r_symndx < extsymoff)
1236      return TRUE;      return TRUE;
1237      if (elf_bad_symtab (input_bfd) && local_sections[r_symndx] != NULL)
1238        return TRUE;
1239    
1240    if (check_forced)    if (check_forced)
1241      {      {
1242        /* Look up the hash table to check whether the symbol was forced local.  */        /* Look up the hash table to check whether the symbol was forced local.  */
1243        h = (struct score_elf_link_hash_entry *)        h = (struct score_elf_link_hash_entry *)
1244          elf_sym_hashes (input_bfd) [r_symndx - extsymoff];          elf_sym_hashes (input_bfd) [r_symndx - extsymoff];
1245        /* Find the real hash-table entry for this symbol.  */        /* Find the real hash-table entry for this symbol.  */
1246        while (h->root.root.type == bfd_link_hash_indirect        while (h->root.root.type == bfd_link_hash_indirect
1247               || h->root.root.type == bfd_link_hash_warning)               || h->root.root.type == bfd_link_hash_warning)
1248          h = (struct score_elf_link_hash_entry *) h->root.root.u.i.link;          h = (struct score_elf_link_hash_entry *) h->root.root.u.i.link;
1249        if (h->root.forced_local)        if (h->root.forced_local)
1250          return TRUE;          return TRUE;
1251      }      }
1252    
1253    return FALSE;    return FALSE;
1254  }  }
1255    
1256  /* Returns the dynamic relocation section for DYNOBJ.  */  /* Returns the dynamic relocation section for DYNOBJ.  */
   
1257  static asection *  static asection *
1258  score_elf_rel_dyn_section (bfd *dynobj, bfd_boolean create_p)  score_elf_rel_dyn_section (bfd *dynobj, bfd_boolean create_p)
1259  {  {
# Line 1150  score_elf_rel_dyn_section (bfd *dynobj, Line 1271  score_elf_rel_dyn_section (bfd *dynobj,
1271                                               | SEC_LINKER_CREATED                                               | SEC_LINKER_CREATED
1272                                               | SEC_READONLY));                                               | SEC_READONLY));
1273        if (sreloc == NULL        if (sreloc == NULL
1274            || ! bfd_set_section_alignment (dynobj, sreloc,            || ! bfd_set_section_alignment (dynobj, sreloc,
1275                                            SCORE_ELF_LOG_FILE_ALIGN (dynobj)))                                            SCORE_ELF_LOG_FILE_ALIGN (dynobj)))
1276          return NULL;          return NULL;
1277      }      }
1278    return sreloc;    return sreloc;
1279  }  }
1280    
1281  static void  static void
# Line 1178  score_elf_allocate_dynamic_relocations ( Line 1299  score_elf_allocate_dynamic_relocations (
1299     is the original relocation, which is now being transformed into a     is the original relocation, which is now being transformed into a
1300     dynamic relocation.  The ADDENDP is adjusted if necessary; the     dynamic relocation.  The ADDENDP is adjusted if necessary; the
1301     caller should store the result in place of the original addend.  */     caller should store the result in place of the original addend.  */
   
1302  static bfd_boolean  static bfd_boolean
1303  score_elf_create_dynamic_relocation (bfd *output_bfd,  score_elf_create_dynamic_relocation (bfd *output_bfd,
1304                                       struct bfd_link_info *info,                                       struct bfd_link_info *info,
1305                                       const Elf_Internal_Rela *rel,                                       const Elf_Internal_Rela *rel,
1306                                       struct score_elf_link_hash_entry *h,                                       struct score_elf_link_hash_entry *h,
1307                                       bfd_vma symbol,                                       bfd_vma symbol,
1308                                       bfd_vma *addendp, asection *input_section)                                       bfd_vma *addendp, asection *input_section)
1309  {  {
1310    Elf_Internal_Rela outrel[3];    Elf_Internal_Rela outrel[3];
1311    asection *sreloc;    asection *sreloc;
# Line 1215  score_elf_create_dynamic_relocation (bfd Line 1335  score_elf_create_dynamic_relocation (bfd
1335    if (outrel[0].r_offset == MINUS_TWO)    if (outrel[0].r_offset == MINUS_TWO)
1336      {      {
1337        /* The relocation field has been converted into a relative value of        /* The relocation field has been converted into a relative value of
1338           some sort.  Functions like _bfd_elf_write_section_eh_frame expect           some sort.  Functions like _bfd_elf_write_section_eh_frame expect
1339           the field to be fully relocated, so add in the symbol's value.  */           the field to be fully relocated, so add in the symbol's value.  */
1340        *addendp += symbol;        *addendp += symbol;
1341        return TRUE;        return TRUE;
1342      }      }
# Line 1226  score_elf_create_dynamic_relocation (bfd Line 1346  score_elf_create_dynamic_relocation (bfd
1346    if (h != NULL    if (h != NULL
1347        && (! info->symbolic || !h->root.def_regular)        && (! info->symbolic || !h->root.def_regular)
1348        /* h->root.dynindx may be -1 if this symbol was marked to        /* h->root.dynindx may be -1 if this symbol was marked to
1349           become local.  */           become local.  */
1350        && h->root.dynindx != -1)        && h->root.dynindx != -1)
1351      {      {
1352        indx = h->root.dynindx;        indx = h->root.dynindx;
1353          /* ??? glibc's ld.so just adds the final GOT entry to the          /* ??? glibc's ld.so just adds the final GOT entry to the
1354             relocation field.  It therefore treats relocs against             relocation field.  It therefore treats relocs against
1355             defined symbols in the same way as relocs against             defined symbols in the same way as relocs against
1356             undefined symbols.  */             undefined symbols.  */
1357        defined_p = FALSE;        defined_p = FALSE;
1358      }      }
1359    else    else
# Line 1271  score_elf_create_dynamic_relocation (bfd Line 1391  score_elf_create_dynamic_relocation (bfd
1391    /* Adjust the output offset of the relocation to reference the    /* Adjust the output offset of the relocation to reference the
1392       correct location in the output file.  */       correct location in the output file.  */
1393    outrel[0].r_offset += (input_section->output_section->vma    outrel[0].r_offset += (input_section->output_section->vma
1394                           + input_section->output_offset);                           + input_section->output_offset);
1395    outrel[1].r_offset += (input_section->output_section->vma    outrel[1].r_offset += (input_section->output_section->vma
1396                           + input_section->output_offset);                           + input_section->output_offset);
1397    outrel[2].r_offset += (input_section->output_section->vma    outrel[2].r_offset += (input_section->output_section->vma
1398                           + input_section->output_offset);                           + input_section->output_offset);
1399    
1400    /* Put the relocation back out.  We have to use the special    /* Put the relocation back out.  We have to use the special
1401       relocation outputter in the 64-bit case since the 64-bit       relocation outputter in the 64-bit case since the 64-bit
# Line 1297  score_elf_create_dynamic_relocation (bfd Line 1417  score_elf_create_dynamic_relocation (bfd
1417  static bfd_boolean  static bfd_boolean
1418  score_elf_create_got_section (bfd *abfd,  score_elf_create_got_section (bfd *abfd,
1419                                struct bfd_link_info *info,                                struct bfd_link_info *info,
1420                                bfd_boolean maybe_exclude)                                bfd_boolean maybe_exclude)
1421  {  {
1422    flagword flags;    flagword flags;
1423    asection *s;    asection *s;
# Line 1311  score_elf_create_got_section (bfd *abfd, Line 1431  score_elf_create_got_section (bfd *abfd,
1431    if (s)    if (s)
1432      {      {
1433        if (! maybe_exclude)        if (! maybe_exclude)
1434          s->flags &= ~SEC_EXCLUDE;          s->flags &= ~SEC_EXCLUDE;
1435        return TRUE;        return TRUE;
1436      }      }
1437    
# Line 1332  score_elf_create_got_section (bfd *abfd, Line 1452  score_elf_create_got_section (bfd *abfd,
1452       are not creating a global offset table.  */       are not creating a global offset table.  */
1453    bh = NULL;    bh = NULL;
1454    if (! (_bfd_generic_link_add_one_symbol    if (! (_bfd_generic_link_add_one_symbol
1455           (info, abfd, "_GLOBAL_OFFSET_TABLE_", BSF_GLOBAL, s,           (info, abfd, "_GLOBAL_OFFSET_TABLE_", BSF_GLOBAL, s,
1456            0, NULL, FALSE, get_elf_backend_data (abfd)->collect, &bh)))            0, NULL, FALSE, get_elf_backend_data (abfd)->collect, &bh)))
1457      return FALSE;      return FALSE;
1458    
1459    h = (struct elf_link_hash_entry *) bh;    h = (struct elf_link_hash_entry *) bh;
# Line 1357  score_elf_create_got_section (bfd *abfd, Line 1477  score_elf_create_got_section (bfd *abfd,
1477    g->next = NULL;    g->next = NULL;
1478    
1479    g->got_entries = htab_try_create (1, score_elf_got_entry_hash,    g->got_entries = htab_try_create (1, score_elf_got_entry_hash,
1480                                      score_elf_got_entry_eq, NULL);                                      score_elf_got_entry_eq, NULL);
1481    if (g->got_entries == NULL)    if (g->got_entries == NULL)
1482      return FALSE;      return FALSE;
1483    score_elf_section_data (s)->u.got_info = g;    score_elf_section_data (s)->u.got_info = g;
# Line 1367  score_elf_create_got_section (bfd *abfd, Line 1487  score_elf_create_got_section (bfd *abfd,
1487  }  }
1488    
1489  /* Calculate the %high function.  */  /* Calculate the %high function.  */
   
1490  static bfd_vma  static bfd_vma
1491  score_elf_high (bfd_vma value)  score_elf_high (bfd_vma value)
1492  {  {
# Line 1376  score_elf_high (bfd_vma value) Line 1495  score_elf_high (bfd_vma value)
1495    
1496  /* Create a local GOT entry for VALUE.  Return the index of the entry,  /* Create a local GOT entry for VALUE.  Return the index of the entry,
1497     or -1 if it could not be created.  */     or -1 if it could not be created.  */
   
1498  static struct score_got_entry *  static struct score_got_entry *
1499  score_elf_create_local_got_entry (bfd *abfd,  score_elf_create_local_got_entry (bfd *abfd,
1500                                    bfd *ibfd ATTRIBUTE_UNUSED,                                    bfd *ibfd ATTRIBUTE_UNUSED,
1501                                    struct score_got_info *gg,                                    struct score_got_info *gg,
1502                                    asection *sgot, bfd_vma value,                                    asection *sgot, bfd_vma value,
1503                                    unsigned long r_symndx ATTRIBUTE_UNUSED,                                    unsigned long r_symndx ATTRIBUTE_UNUSED,
1504                                    struct score_elf_link_hash_entry *h ATTRIBUTE_UNUSED,                                    struct score_elf_link_hash_entry *h ATTRIBUTE_UNUSED,
1505                                    int r_type ATTRIBUTE_UNUSED)                                    int r_type ATTRIBUTE_UNUSED)
1506  {  {
1507    struct score_got_entry entry, **loc;    struct score_got_entry entry, **loc;
1508    struct score_got_info *g;    struct score_got_info *g;
# Line 1412  score_elf_create_local_got_entry (bfd *a Line 1530  score_elf_create_local_got_entry (bfd *a
1530        (*loc)->gotidx = -1;        (*loc)->gotidx = -1;
1531        /* We didn't allocate enough space in the GOT.  */        /* We didn't allocate enough space in the GOT.  */
1532        (*_bfd_error_handler)        (*_bfd_error_handler)
1533          (_("not enough GOT space for local GOT entries"));          (_("not enough GOT space for local GOT entries"));
1534        bfd_set_error (bfd_error_bad_value);        bfd_set_error (bfd_error_bad_value);
1535        return NULL;        return NULL;
1536      }      }
1537    
1538    bfd_put_32 (abfd, value, (sgot->contents + entry.gotidx));    score_bfd_put_32 (abfd, value, (sgot->contents + entry.gotidx));
1539    
1540    return *loc;    return *loc;
1541  }  }
1542    
1543  /* Find a GOT entry whose higher-order 16 bits are the same as those  /* Find a GOT entry whose higher-order 16 bits are the same as those
1544     for value.  Return the index into the GOT for this entry.  */     for value.  Return the index into the GOT for this entry.  */
   
1545  static bfd_vma  static bfd_vma
1546  score_elf_got16_entry (bfd *abfd, bfd *ibfd, struct bfd_link_info *info,  score_elf_got16_entry (bfd *abfd, bfd *ibfd, struct bfd_link_info *info,
1547                        bfd_vma value, bfd_boolean external)                         bfd_vma value, bfd_boolean external)
1548  {  {
1549    asection *sgot;    asection *sgot;
1550    struct score_got_info *g;    struct score_got_info *g;
# Line 1436  score_elf_got16_entry (bfd *abfd, bfd *i Line 1553  score_elf_got16_entry (bfd *abfd, bfd *i
1553    if (!external)    if (!external)
1554      {      {
1555        /* Although the ABI says that it is "the high-order 16 bits" that we        /* Although the ABI says that it is "the high-order 16 bits" that we
1556           want, it is really the %high value.  The complete value is           want, it is really the %high value.  The complete value is
1557           calculated with a `addiu' of a LO16 relocation, just as with a           calculated with a `addiu' of a LO16 relocation, just as with a
1558           HI16/LO16 pair.  */           HI16/LO16 pair.  */
1559        value = score_elf_high (value) << 16;        value = score_elf_high (value) << 16;
1560      }      }
1561    
1562    g = score_elf_got_info (elf_hash_table (info)->dynobj, &sgot);    g = score_elf_got_info (elf_hash_table (info)->dynobj, &sgot);
1563    
1564    entry = score_elf_create_local_got_entry (abfd, ibfd, g, sgot, value, 0, NULL,    entry = score_elf_create_local_got_entry (abfd, ibfd, g, sgot, value, 0, NULL,
1565                                              R_SCORE_GOT15);                                              R_SCORE_GOT15);
1566    if (entry)    if (entry)
1567      return entry->gotidx;      return entry->gotidx;
1568    else    else
# Line 1453  score_elf_got16_entry (bfd *abfd, bfd *i Line 1570  score_elf_got16_entry (bfd *abfd, bfd *i
1570  }  }
1571    
1572  static void  static void
1573  _bfd_score_elf_hide_symbol (struct bfd_link_info *info,  s3_bfd_score_elf_hide_symbol (struct bfd_link_info *info,
1574                              struct elf_link_hash_entry *entry,                                struct elf_link_hash_entry *entry,
1575                              bfd_boolean force_local)                                bfd_boolean force_local)
1576  {  {
1577    bfd *dynobj;    bfd *dynobj;
1578    asection *got;    asection *got;
# Line 1472  _bfd_score_elf_hide_symbol (struct bfd_l Line 1589  _bfd_score_elf_hide_symbol (struct bfd_l
1589      {      {
1590        got = score_elf_got_section (dynobj, FALSE);        got = score_elf_got_section (dynobj, FALSE);
1591        if (got == NULL)        if (got == NULL)
1592          return;          return;
1593        g = score_elf_section_data (got)->u.got_info;        g = score_elf_section_data (got)->u.got_info;
1594    
1595        if (g->next)        if (g->next)
1596          {          {
1597            struct score_got_entry e;            struct score_got_entry e;
1598            struct score_got_info *gg = g;            struct score_got_info *gg = g;
1599    
1600            /* Since we're turning what used to be a global symbol into a            /* Since we're turning what used to be a global symbol into a
1601               local one, bump up the number of local entries of each GOT               local one, bump up the number of local entries of each GOT
1602               that had an entry for it.  This will automatically decrease               that had an entry for it.  This will automatically decrease
1603               the number of global entries, since global_gotno is actually               the number of global entries, since global_gotno is actually
1604               the upper limit of global entries.  */               the upper limit of global entries.  */
1605            e.abfd = dynobj;            e.abfd = dynobj;
1606            e.symndx = -1;            e.symndx = -1;
1607            e.d.h = h;            e.d.h = h;
1608    
1609            for (g = g->next; g != gg; g = g->next)            for (g = g->next; g != gg; g = g->next)
1610              if (htab_find (g->got_entries, &e))              if (htab_find (g->got_entries, &e))
1611                {                {
1612                  BFD_ASSERT (g->global_gotno > 0);                  BFD_ASSERT (g->global_gotno > 0);
1613                  g->local_gotno++;                  g->local_gotno++;
1614                  g->global_gotno--;                  g->global_gotno--;
1615                }                }
1616    
1617            /* If this was a global symbol forced into the primary GOT, we            /* If this was a global symbol forced into the primary GOT, we
1618               no longer need an entry for it.  We can't release the entry               no longer need an entry for it.  We can't release the entry
1619               at this point, but we must at least stop counting it as one               at this point, but we must at least stop counting it as one
1620               of the symbols that required a forced got entry.  */               of the symbols that required a forced got entry.  */
1621            if (h->root.got.offset == 2)            if (h->root.got.offset == 2)
1622              {              {
1623                BFD_ASSERT (gg->assigned_gotno > 0);                BFD_ASSERT (gg->assigned_gotno > 0);
1624                gg->assigned_gotno--;                gg->assigned_gotno--;
1625              }              }
1626          }          }
1627        else if (g->global_gotno == 0 && g->global_gotsym == NULL)        else if (g->global_gotno == 0 && g->global_gotsym == NULL)
1628          /* If we haven't got through GOT allocation yet, just bump up the          /* If we haven't got through GOT allocation yet, just bump up the
1629                number of local entries, as this symbol won't be counted as                number of local entries, as this symbol won't be counted as
1630                global.  */                global.  */
1631          g->local_gotno++;          g->local_gotno++;
1632        else if (h->root.got.offset == 1)        else if (h->root.got.offset == 1)
1633          {          {
1634            /* If we're past non-multi-GOT allocation and this symbol had            /* If we're past non-multi-GOT allocation and this symbol had
1635                    been marked for a global got entry, give it a local entry                    been marked for a global got entry, give it a local entry
1636                    instead.  */                    instead.  */
1637            BFD_ASSERT (g->global_gotno > 0);            BFD_ASSERT (g->global_gotno > 0);
1638            g->local_gotno++;            g->local_gotno++;
1639            g->global_gotno--;            g->global_gotno--;
1640          }          }
1641      }      }
1642    
1643    _bfd_elf_link_hash_hide_symbol (info, &h->root, force_local);    _bfd_elf_link_hash_hide_symbol (info, &h->root, force_local);
# Line 1529  _bfd_score_elf_hide_symbol (struct bfd_l Line 1646  _bfd_score_elf_hide_symbol (struct bfd_l
1646  /* If H is a symbol that needs a global GOT entry, but has a dynamic  /* If H is a symbol that needs a global GOT entry, but has a dynamic
1647     symbol table index lower than any we've seen to date, record it for     symbol table index lower than any we've seen to date, record it for
1648     posterity.  */     posterity.  */
   
1649  static bfd_boolean  static bfd_boolean
1650  score_elf_record_global_got_symbol (struct elf_link_hash_entry *h,  score_elf_record_global_got_symbol (struct elf_link_hash_entry *h,
1651                                      bfd *abfd,                                      bfd *abfd,
1652                                      struct bfd_link_info *info,                                      struct bfd_link_info *info,
1653                                      struct score_got_info *g)                                      struct score_got_info *g)
1654  {  {
1655    struct score_got_entry entry, **loc;    struct score_got_entry entry, **loc;
1656    
# Line 1542  score_elf_record_global_got_symbol (stru Line 1658  score_elf_record_global_got_symbol (stru
1658    if (h->dynindx == -1)    if (h->dynindx == -1)
1659      {      {
1660        switch (ELF_ST_VISIBILITY (h->other))        switch (ELF_ST_VISIBILITY (h->other))
1661          {          {
1662          case STV_INTERNAL:          case STV_INTERNAL:
1663          case STV_HIDDEN:          case STV_HIDDEN:
1664            _bfd_score_elf_hide_symbol (info, h, TRUE);            s3_bfd_score_elf_hide_symbol (info, h, TRUE);
1665            break;            break;
1666          }          }
1667        if (!bfd_elf_link_record_dynamic_symbol (info, h))        if (!bfd_elf_link_record_dynamic_symbol (info, h))
1668          return FALSE;          return FALSE;
1669      }      }
1670    
1671    entry.abfd = abfd;    entry.abfd = abfd;
# Line 1584  score_elf_record_global_got_symbol (stru Line 1700  score_elf_record_global_got_symbol (stru
1700    
1701  /* Reserve space in G for a GOT entry containing the value of symbol  /* Reserve space in G for a GOT entry containing the value of symbol
1702     SYMNDX in input bfd ABDF, plus ADDEND.  */     SYMNDX in input bfd ABDF, plus ADDEND.  */
   
1703  static bfd_boolean  static bfd_boolean
1704  score_elf_record_local_got_symbol (bfd *abfd,  score_elf_record_local_got_symbol (bfd *abfd,
1705                                     long symndx,                                     long symndx,
1706                                     bfd_vma addend,                                     bfd_vma addend,
1707                                     struct score_got_info *g)                                     struct score_got_info *g)
1708  {  {
1709    struct score_got_entry entry, **loc;    struct score_got_entry entry, **loc;
1710    
# Line 1615  score_elf_record_local_got_symbol (bfd * Line 1730  score_elf_record_local_got_symbol (bfd *
1730  /* Returns the GOT offset at which the indicated address can be found.  /* Returns the GOT offset at which the indicated address can be found.
1731     If there is not yet a GOT entry for this value, create one.     If there is not yet a GOT entry for this value, create one.
1732     Returns -1 if no satisfactory GOT offset can be found.  */     Returns -1 if no satisfactory GOT offset can be found.  */
   
1733  static bfd_vma  static bfd_vma
1734  score_elf_local_got_index (bfd *abfd, bfd *ibfd, struct bfd_link_info *info,  score_elf_local_got_index (bfd *abfd, bfd *ibfd, struct bfd_link_info *info,
1735                            bfd_vma value, unsigned long r_symndx,                             bfd_vma value, unsigned long r_symndx,
1736                            struct score_elf_link_hash_entry *h, int r_type)                             struct score_elf_link_hash_entry *h, int r_type)
1737  {  {
1738    asection *sgot;    asection *sgot;
1739    struct score_got_info *g;    struct score_got_info *g;
# Line 1628  score_elf_local_got_index (bfd *abfd, bf Line 1742  score_elf_local_got_index (bfd *abfd, bf
1742    g = score_elf_got_info (elf_hash_table (info)->dynobj, &sgot);    g = score_elf_got_info (elf_hash_table (info)->dynobj, &sgot);
1743    
1744    entry = score_elf_create_local_got_entry (abfd, ibfd, g, sgot, value,    entry = score_elf_create_local_got_entry (abfd, ibfd, g, sgot, value,
1745                                              r_symndx, h, r_type);                                               r_symndx, h, r_type);
1746    if (!entry)    if (!entry)
1747      return MINUS_ONE;      return MINUS_ONE;
1748    
# Line 1662  score_elf_global_got_index (bfd *abfd, s Line 1776  score_elf_global_got_index (bfd *abfd, s
1776  }  }
1777    
1778  /* Returns the offset for the entry at the INDEXth position in the GOT.  */  /* Returns the offset for the entry at the INDEXth position in the GOT.  */
   
1779  static bfd_vma  static bfd_vma
1780  score_elf_got_offset_from_index (bfd *dynobj, bfd *output_bfd,  score_elf_got_offset_from_index (bfd *dynobj, bfd *output_bfd,
1781                                   bfd *input_bfd ATTRIBUTE_UNUSED, bfd_vma index)                                   bfd *input_bfd ATTRIBUTE_UNUSED, bfd_vma index)
1782  {  {
1783    asection *sgot;    asection *sgot;
1784    bfd_vma gp;    bfd_vma gp;
# Line 1694  score_elf_resolve_final_got_entry (void Line 1807  score_elf_resolve_final_got_entry (void
1807        struct score_elf_link_hash_entry *h = entry->d.h;        struct score_elf_link_hash_entry *h = entry->d.h;
1808    
1809        while (h->root.root.type == bfd_link_hash_indirect        while (h->root.root.type == bfd_link_hash_indirect
1810               || h->root.root.type == bfd_link_hash_warning)               || h->root.root.type == bfd_link_hash_warning)
1811          h = (struct score_elf_link_hash_entry *) h->root.root.u.i.link;          h = (struct score_elf_link_hash_entry *) h->root.root.u.i.link;
1812    
1813        if (entry->d.h == h)        if (entry->d.h == h)
1814          return 1;          return 1;
1815    
1816        entry->d.h = h;        entry->d.h = h;
1817    
1818        /* If we can't find this entry with the new bfd hash, re-insert        /* If we can't find this entry with the new bfd hash, re-insert
1819           it, and get the traversal restarted.  */           it, and get the traversal restarted.  */
1820        if (! htab_find (got_entries, entry))        if (! htab_find (got_entries, entry))
1821          {          {
1822            htab_clear_slot (got_entries, entryp);            htab_clear_slot (got_entries, entryp);
1823            entryp = htab_find_slot (got_entries, entry, INSERT);            entryp = htab_find_slot (got_entries, entry, INSERT);
1824            if (! *entryp)            if (! *entryp)
1825              *entryp = entry;              *entryp = entry;
1826            /* Abort the traversal, since the whole table may have            /* Abort the traversal, since the whole table may have
1827               moved, and leave it up to the parent to restart the               moved, and leave it up to the parent to restart the
1828               process.  */               process.  */
1829            *(htab_t *)p = NULL;            *(htab_t *)p = NULL;
1830            return 0;            return 0;
1831          }          }
1832        /* We might want to decrement the global_gotno count, but it's        /* We might want to decrement the global_gotno count, but it's
1833           either too early or too late for that at this point.  */           either too early or too late for that at this point.  */
1834      }      }
1835    
1836    return 1;    return 1;
# Line 1734  score_elf_resolve_final_got_entries (str Line 1847  score_elf_resolve_final_got_entries (str
1847        got_entries = g->got_entries;        got_entries = g->got_entries;
1848    
1849        htab_traverse (got_entries,        htab_traverse (got_entries,
1850                       score_elf_resolve_final_got_entry,                       score_elf_resolve_final_got_entry,
1851                       &got_entries);                       &got_entries);
1852      }      }
1853    while (got_entries == NULL);    while (got_entries == NULL);
1854  }  }
1855    
1856  /* Add INCREMENT to the reloc (of type HOWTO) at ADDRESS. for -r  */  /* Add INCREMENT to the reloc (of type HOWTO) at ADDRESS. for -r  */
   
1857  static void  static void
1858  score_elf_add_to_rel (bfd *abfd,  score_elf_add_to_rel (bfd *abfd,
1859                        bfd_byte *address,                        bfd_byte *address,
1860                        reloc_howto_type *howto,                        reloc_howto_type *howto,
1861                        bfd_signed_vma increment)                        bfd_signed_vma increment)
1862  {  {
1863    bfd_signed_vma addend;    bfd_signed_vma addend;
1864    bfd_vma contents;    bfd_vma contents;
# Line 1754  score_elf_add_to_rel (bfd *abfd, Line 1866  score_elf_add_to_rel (bfd *abfd,
1866    unsigned long r_type = howto->type;    unsigned long r_type = howto->type;
1867    unsigned long hi16_addend, hi16_offset, hi16_value, uvalue;    unsigned long hi16_addend, hi16_offset, hi16_value, uvalue;
1868    
1869    contents = bfd_get_32 (abfd, address);    contents = score_bfd_get_32 (abfd, address);
1870    /* Get the (signed) value from the instruction.  */    /* Get the (signed) value from the instruction.  */
1871    addend = contents & howto->src_mask;    addend = contents & howto->src_mask;
1872    if (addend & ((howto->src_mask + 1) >> 1))    if (addend & ((howto->src_mask + 1) >> 1))
# Line 1775  score_elf_add_to_rel (bfd *abfd, Line 1887  score_elf_add_to_rel (bfd *abfd,
1887        contents =        contents =
1888          (contents & ~howto->          (contents & ~howto->
1889           src_mask) | (((offset << 6) & howto->src_mask) & 0x3ff0000) | (offset & 0x3ff);           src_mask) | (((offset << 6) & howto->src_mask) & 0x3ff0000) | (offset & 0x3ff);
1890        bfd_put_32 (abfd, contents, address);        score_bfd_put_32 (abfd, contents, address);
1891        break;        break;
1892      case R_SCORE_HI16:      case R_SCORE_HI16:
1893        break;        break;
1894      case R_SCORE_LO16:      case R_SCORE_LO16:
1895        hi16_addend = bfd_get_32 (abfd, address - 4);        hi16_addend = score_bfd_get_32 (abfd, address - 4);
1896        hi16_offset = ((((hi16_addend >> 16) & 0x3) << 15) | (hi16_addend & 0x7fff)) >> 1;        hi16_offset = ((((hi16_addend >> 16) & 0x3) << 15) | (hi16_addend & 0x7fff)) >> 1;
1897        offset = ((((contents >> 16) & 0x3) << 15) | (contents & 0x7fff)) >> 1;        offset = ((((contents >> 16) & 0x3) << 15) | (contents & 0x7fff)) >> 1;
1898        offset = (hi16_offset << 16) | (offset & 0xffff);        offset = (hi16_offset << 16) | (offset & 0xffff);
# Line 1788  score_elf_add_to_rel (bfd *abfd, Line 1900  score_elf_add_to_rel (bfd *abfd,
1900        hi16_offset = (uvalue >> 16) << 1;        hi16_offset = (uvalue >> 16) << 1;
1901        hi16_value = (hi16_addend & (~(howto->dst_mask)))        hi16_value = (hi16_addend & (~(howto->dst_mask)))
1902          | (hi16_offset & 0x7fff) | ((hi16_offset << 1) & 0x30000);          | (hi16_offset & 0x7fff) | ((hi16_offset << 1) & 0x30000);
1903        bfd_put_32 (abfd, hi16_value, address - 4);        score_bfd_put_32 (abfd, hi16_value, address - 4);
1904        offset = (uvalue & 0xffff) << 1;        offset = (uvalue & 0xffff) << 1;
1905        contents = (contents & (~(howto->dst_mask))) | (offset & 0x7fff) | ((offset << 1) & 0x30000);        contents = (contents & (~(howto->dst_mask))) | (offset & 0x7fff) | ((offset << 1) & 0x30000);
1906        bfd_put_32 (abfd, contents, address);        score_bfd_put_32 (abfd, contents, address);
1907        break;        break;
1908      case R_SCORE_24:      case R_SCORE_24:
1909        offset =        offset =
# Line 1800  score_elf_add_to_rel (bfd *abfd, Line 1912  score_elf_add_to_rel (bfd *abfd,
1912        contents =        contents =
1913          (contents & ~howto->          (contents & ~howto->
1914           src_mask) | (((offset << 1) & howto->src_mask) & 0x3ff0000) | (offset & 0x7fff);           src_mask) | (((offset << 1) & howto->src_mask) & 0x3ff0000) | (offset & 0x7fff);
1915        bfd_put_32 (abfd, contents, address);        score_bfd_put_32 (abfd, contents, address);
1916        break;        break;
1917    
1918      case R_SCORE16_11:      case R_SCORE16_11:
1919    
1920        contents = bfd_get_16 (abfd, address);        contents = score_bfd_get_16 (abfd, address);
1921        offset = contents & howto->src_mask;        offset = contents & howto->src_mask;
1922        offset += increment;        offset += increment;
1923        contents = (contents & ~howto->src_mask) | (offset & howto->src_mask);        contents = (contents & ~howto->src_mask) | (offset & howto->src_mask);
1924        bfd_put_16 (abfd, contents, address);        score_bfd_put_16 (abfd, contents, address);
1925    
1926        break;        break;
1927      case R_SCORE16_PC8:      case R_SCORE16_PC8:
1928    
1929        contents = bfd_get_16 (abfd, address);        contents = score_bfd_get_16 (abfd, address);
1930        offset = (contents & howto->src_mask) + ((increment >> 1) & 0xff);        offset = (contents & howto->src_mask) + ((increment >> 1) & 0x1ff);
1931          contents = (contents & (~howto->src_mask)) | (offset & howto->src_mask);
1932          score_bfd_put_16 (abfd, contents, address);
1933    
1934          break;
1935    
1936        case R_SCORE_BCMP:
1937          contents = score_bfd_get_32 (abfd, address);
1938          offset = (contents & howto->src_mask);
1939          offset <<= howto->rightshift;
1940          offset += increment;
1941          offset >>= howto->rightshift;
1942          contents = (contents & (~howto->src_mask)) | (offset & howto->src_mask);
1943          score_bfd_put_32 (abfd, contents, address);
1944          break;
1945    
1946        case R_SCORE_IMM30:
1947          contents = score_bfd_get_48 (abfd, address);
1948          offset = (contents & howto->src_mask);
1949          offset <<= howto->rightshift;
1950          offset += increment;
1951          offset >>= howto->rightshift;
1952        contents = (contents & (~howto->src_mask)) | (offset & howto->src_mask);        contents = (contents & (~howto->src_mask)) | (offset & howto->src_mask);
1953        bfd_put_16 (abfd, contents, address);        score_bfd_put_48 (abfd, contents, address);
1954          break;
1955    
1956        case R_SCORE_IMM32:
1957          contents = score_bfd_get_48 (abfd, address);
1958          offset = (contents & howto->src_mask);
1959          offset += increment;
1960          contents = (contents & (~howto->src_mask)) | (offset & howto->src_mask);
1961          score_bfd_put_48 (abfd, contents, address);
1962        break;        break;
1963    
1964      default:      default:
1965        addend += increment;        addend += increment;
1966        contents = (contents & ~howto->dst_mask) | (addend & howto->dst_mask);        contents = (contents & ~howto->dst_mask) | (addend & howto->dst_mask);
1967        bfd_put_32 (abfd, contents, address);        score_bfd_put_32 (abfd, contents, address);
1968        break;        break;
1969      }      }
1970  }  }
1971    
1972  /* Perform a relocation as part of a final link.  */  /* Perform a relocation as part of a final link.  */
   
1973  static bfd_reloc_status_type  static bfd_reloc_status_type
1974  score_elf_final_link_relocate (reloc_howto_type *howto,  score_elf_final_link_relocate (reloc_howto_type *howto,
1975                                 bfd *input_bfd,                                 bfd *input_bfd,
1976                                 bfd *output_bfd,                                 bfd *output_bfd,
1977                                 asection *input_section,                                 asection *input_section,
1978                                 bfd_byte *contents,                                 bfd_byte *contents,
1979                                 Elf_Internal_Rela *rel,                                 Elf_Internal_Rela *rel,
1980                                 Elf_Internal_Rela *relocs,                                 Elf_Internal_Rela *relocs,
1981                                 bfd_vma symbol,                                 bfd_vma symbol,
1982                                 struct bfd_link_info *info,                                 struct bfd_link_info *info,
1983                                 const char *sym_name ATTRIBUTE_UNUSED,                                 const char *sym_name ATTRIBUTE_UNUSED,
1984                                 int sym_flags ATTRIBUTE_UNUSED,                                 int sym_flags ATTRIBUTE_UNUSED,
1985                                 struct score_elf_link_hash_entry *h,                                 struct score_elf_link_hash_entry *h,
1986                                   asection **local_sections,
1987                                 bfd_boolean gp_disp_p)                                 bfd_boolean gp_disp_p)
1988  {  {
1989    unsigned long r_type;    unsigned long r_type;
# Line 1864  score_elf_final_link_relocate (reloc_how Line 2006  score_elf_final_link_relocate (reloc_how
2006    bfd_vma value = symbol;    bfd_vma value = symbol;
2007    unsigned long hi16_addend, hi16_offset, hi16_value, uvalue, offset, abs_value = 0;    unsigned long hi16_addend, hi16_offset, hi16_value, uvalue, offset, abs_value = 0;
2008    
2009    
2010    if (elf_gp (output_bfd) == 0)    if (elf_gp (output_bfd) == 0)
2011      {      {
2012        struct bfd_link_hash_entry *bh;        struct bfd_link_hash_entry *bh;
2013        asection *o;        asection *o;
2014    
2015        bh = bfd_link_hash_lookup (info->hash, "_gp", 0, 0, 1);        bh = bfd_link_hash_lookup (info->hash, "_gp", 0, 0, 1);
2016        if (bh != (struct bfd_link_hash_entry *)NULL && bh->type == bfd_link_hash_defined)        if (bh != NULL && bh->type == bfd_link_hash_defined)
2017          elf_gp (output_bfd) = (bh->u.def.value          elf_gp (output_bfd) = (bh->u.def.value
2018                                 + bh->u.def.section->output_section->vma                                 + bh->u.def.section->output_section->vma
2019                                 + bh->u.def.section->output_offset);                                 + bh->u.def.section->output_offset);
# Line 1879  score_elf_final_link_relocate (reloc_how Line 2022  score_elf_final_link_relocate (reloc_how
2022            bfd_vma lo = -1;            bfd_vma lo = -1;
2023    
2024            /* Find the GP-relative section with the lowest offset.  */            /* Find the GP-relative section with the lowest offset.  */
2025            for (o = output_bfd->sections; o != (asection *) NULL; o = o->next)            for (o = output_bfd->sections; o != NULL; o = o->next)
2026              if (o->vma < lo)              if (o->vma < lo)
2027                lo = o->vma;                lo = o->vma;
2028            /* And calculate GP relative to that.  */            /* And calculate GP relative to that.  */
# Line 1897  score_elf_final_link_relocate (reloc_how Line 2040  score_elf_final_link_relocate (reloc_how
2040    r_symndx = ELF32_R_SYM (rel->r_info);    r_symndx = ELF32_R_SYM (rel->r_info);
2041    r_type = ELF32_R_TYPE (rel->r_info);    r_type = ELF32_R_TYPE (rel->r_info);
2042    rel_addr = (input_section->output_section->vma + input_section->output_offset + rel->r_offset);    rel_addr = (input_section->output_section->vma + input_section->output_offset + rel->r_offset);
2043    local_p = score_elf_local_relocation_p (input_bfd, rel, TRUE);    local_p = score_elf_local_relocation_p (input_bfd, rel, local_sections, TRUE);
2044    
2045    if (r_type == R_SCORE_GOT15)    if (r_type == R_SCORE_GOT15)
2046      {      {
# Line 1910  score_elf_final_link_relocate (reloc_how Line 2053  score_elf_final_link_relocate (reloc_how
2053        relend = relocs + input_section->reloc_count * bed->s->int_rels_per_ext_rel;        relend = relocs + input_section->reloc_count * bed->s->int_rels_per_ext_rel;
2054        lo16_rel = score_elf_next_relocation (input_bfd, R_SCORE_GOT_LO16, rel, relend);        lo16_rel = score_elf_next_relocation (input_bfd, R_SCORE_GOT_LO16, rel, relend);
2055        if ((local_p) && (lo16_rel != NULL))        if ((local_p) && (lo16_rel != NULL))
2056          {          {
2057            bfd_vma tmp = 0;            bfd_vma tmp = 0;
2058            tmp = bfd_get_32 (input_bfd, contents + lo16_rel->r_offset);            tmp = score_bfd_get_32 (input_bfd, contents + lo16_rel->r_offset);
2059            lo_value = (((tmp >> 16) & 0x3) << 14) | ((tmp & 0x7fff) >> 1);            lo_value = (((tmp >> 16) & 0x3) << 14) | ((tmp & 0x7fff) >> 1);
2060          }          }
2061        addend = lo_value;        addend = lo_value;
2062      }      }
2063    else    /* For score3 R_SCORE_ABS32.  */
2064      else if (r_type == R_SCORE_ABS32 || r_type == R_SCORE_REL32)
2065      {      {
2066        addend = (bfd_get_32 (input_bfd, hit_data) >> howto->bitpos) & howto->src_mask;        addend = (bfd_get_32 (input_bfd, hit_data) >> howto->bitpos) & howto->src_mask;
2067      }      }
2068      else
2069        {
2070          addend = (score_bfd_get_32 (input_bfd, hit_data) >> howto->bitpos) & howto->src_mask;
2071        }
2072    
2073    /* If we haven't already determined the GOT offset, or the GP value,    /* If we haven't already determined the GOT offset, or the GP value,
2074       and we're going to need it, get it now.  */       and we're going to need it, get it now.  */
# Line 1942  score_elf_final_link_relocate (reloc_how Line 2090  score_elf_final_link_relocate (reloc_how
2090                   We must initialize this entry in the GOT.  */                   We must initialize this entry in the GOT.  */
2091                bfd *tmpbfd = elf_hash_table (info)->dynobj;                bfd *tmpbfd = elf_hash_table (info)->dynobj;
2092                asection *sgot = score_elf_got_section (tmpbfd, FALSE);                asection *sgot = score_elf_got_section (tmpbfd, FALSE);
2093                bfd_put_32 (tmpbfd, value, sgot->contents + g);                score_bfd_put_32 (tmpbfd, value, sgot->contents + g);
2094              }              }
2095          }          }
2096        else if (r_type == R_SCORE_GOT15 || r_type == R_SCORE_CALL15)        else if (r_type == R_SCORE_GOT15 || r_type == R_SCORE_CALL15)
2097          {          {
2098            /* There's no need to create a local GOT entry here; the            /* There's no need to create a local GOT entry here; the
2099               calculation for a local GOT15 entry does not involve G.  */               calculation for a local GOT15 entry does not involve G.  */
2100            ;            ;
2101          }          }
2102        else        else
2103          {          {
2104            g = score_elf_local_got_index (output_bfd, input_bfd, info,            g = score_elf_local_got_index (output_bfd, input_bfd, info,
2105                                           symbol + addend, r_symndx, h, r_type);                                           symbol + addend, r_symndx, h, r_type);
2106            if (g == MINUS_ONE)              if (g == MINUS_ONE)
2107              return bfd_reloc_outofrange;              return bfd_reloc_outofrange;
2108          }          }
2109    
2110        /* Convert GOT indices to actual offsets.  */        /* Convert GOT indices to actual offsets.  */
2111        g = score_elf_got_offset_from_index (elf_hash_table (info)->dynobj,        g = score_elf_got_offset_from_index (elf_hash_table (info)->dynobj,
2112                                             output_bfd, input_bfd, g);                                             output_bfd, input_bfd, g);
2113        break;        break;
2114    
2115      case R_SCORE_HI16:      case R_SCORE_HI16:
# Line 1986  score_elf_final_link_relocate (reloc_how Line 2134  score_elf_final_link_relocate (reloc_how
2134      case R_SCORE_ABS32:      case R_SCORE_ABS32:
2135      case R_SCORE_REL32:      case R_SCORE_REL32:
2136        if ((info->shared        if ((info->shared
2137             || (elf_hash_table (info)->dynamic_sections_created             || (elf_hash_table (info)->dynamic_sections_created
2138                 && h != NULL                 && h != NULL
2139                 && h->root.def_dynamic                 && h->root.def_dynamic
2140                 && !h->root.def_regular))                 && !h->root.def_regular))
2141             && r_symndx != 0             && r_symndx != 0
2142             && (input_section->flags & SEC_ALLOC) != 0)             && (input_section->flags & SEC_ALLOC) != 0)
2143          {          {
2144            /* If we're creating a shared library, or this relocation is against a symbol            /* If we're creating a shared library, or this relocation is against a symbol
2145               in a shared library, then we can't know where the symbol will end up.               in a shared library, then we can't know where the symbol will end up.
2146               So, we create a relocation record in the output, and leave the job up               So, we create a relocation record in the output, and leave the job up
2147               to the dynamic linker.  */               to the dynamic linker.  */
2148            value = addend;            value = addend;
2149            if (!score_elf_create_dynamic_relocation (output_bfd, info, rel, h,            if (!score_elf_create_dynamic_relocation (output_bfd, info, rel, h,
2150                                                      symbol, &value,                                                      symbol, &value,
2151                                                      input_section))                                                      input_section))
2152              return bfd_reloc_undefined;              return bfd_reloc_undefined;
2153          }          }
2154          else if (r_symndx == 0)
2155            /* r_symndx will be zero only for relocs against symbols
2156               from removed linkonce sections, or sections discarded by
2157               a linker script.  */
2158            value = 0;
2159        else        else
2160          {          {
2161            if (r_type != R_SCORE_REL32)            if (r_type != R_SCORE_REL32)
2162              value = symbol + addend;              value = symbol + addend;
2163            else            else
2164              value = addend;              value = addend;
2165          }          }
2166        value &= howto->dst_mask;        value &= howto->dst_mask;
2167        bfd_put_32 (input_bfd, value, hit_data);        bfd_put_32 (input_bfd, value, hit_data);
2168        return bfd_reloc_ok;        return bfd_reloc_ok;
# Line 2018  score_elf_final_link_relocate (reloc_how Line 2171  score_elf_final_link_relocate (reloc_how
2171        value += addend;        value += addend;
2172        if ((long)value > 0x7fff || (long)value < -0x8000)        if ((long)value > 0x7fff || (long)value < -0x8000)
2173          return bfd_reloc_overflow;          return bfd_reloc_overflow;
2174        bfd_put_16 (input_bfd, value, hit_data);        score_bfd_put_16 (input_bfd, value, hit_data);
2175        return bfd_reloc_ok;        return bfd_reloc_ok;
2176    
2177      case R_SCORE_24:      case R_SCORE_24:
2178        addend = bfd_get_32 (input_bfd, hit_data);        addend = score_bfd_get_32 (input_bfd, hit_data);
2179        offset = (((addend & howto->src_mask) >> 1) & 0x1ff8000) | ((addend & howto->src_mask) & 0x7fff);        offset = (((addend & howto->src_mask) >> 1) & 0x1ff8000) | ((addend & howto->src_mask) & 0x7fff);
2180        if ((offset & 0x1000000) != 0)        if ((offset & 0x1000000) != 0)
2181          offset |= 0xfe000000;          offset |= 0xfe000000;
2182        value += offset;        value += offset;
2183          abs_value = abs (value - rel_addr);
2184          if ((abs_value & 0xfe000000) != 0)
2185            return bfd_reloc_overflow;
2186        addend = (addend & ~howto->src_mask)        addend = (addend & ~howto->src_mask)
2187                  | (((value << 1) & howto->src_mask) & 0x3ff0000) | (value & 0x7fff);                  | (((value << 1) & howto->src_mask) & 0x3ff0000) | (value & 0x7fff);
2188        bfd_put_32 (input_bfd, addend, hit_data);        score_bfd_put_32 (input_bfd, addend, hit_data);
2189        return bfd_reloc_ok;        return bfd_reloc_ok;
2190    
2191        /* signed imm32.  */
2192        case R_SCORE_IMM30:
2193          {
2194            int not_word_align_p = 0;
2195            bfd_vma imm_offset = 0;
2196            addend = score_bfd_get_48 (input_bfd, hit_data);
2197            imm_offset = ((addend >> 7) & 0xff)
2198                         | (((addend >> 16) & 0x7fff) << 8)
2199                         | (((addend >> 32) & 0x7f) << 23);
2200            imm_offset <<= howto->rightshift;
2201            value += imm_offset;
2202            value &= 0xffffffff;
2203    
2204            /* Check lw48/sw48 rd, value/label word align.  */
2205            if ((value & 0x3) != 0)
2206              not_word_align_p = 1;
2207    
2208            value >>= howto->rightshift;
2209            addend = (addend & ~howto->src_mask)
2210                     | (((value & 0xff) >> 0) << 7)
2211                     | (((value & 0x7fff00) >> 8) << 16)
2212                     | (((value & 0x3f800000) >> 23) << 32);
2213            score_bfd_put_48 (input_bfd, addend, hit_data);
2214            if (not_word_align_p)
2215              return bfd_reloc_other;
2216            else
2217              return bfd_reloc_ok;
2218          }
2219    
2220        case R_SCORE_IMM32:
2221          {
2222            bfd_vma imm_offset = 0;
2223            addend = score_bfd_get_48 (input_bfd, hit_data);
2224            imm_offset = ((addend >> 5) & 0x3ff)
2225                         | (((addend >> 16) & 0x7fff) << 10)
2226                         | (((addend >> 32) & 0x7f) << 25);
2227            value += imm_offset;
2228            value &= 0xffffffff;
2229            addend = (addend & ~howto->src_mask)
2230                     | ((value & 0x3ff) << 5)
2231                     | (((value >> 10) & 0x7fff) << 16)
2232                     | (((value >> 25) & 0x7f) << 32);
2233            score_bfd_put_48 (input_bfd, addend, hit_data);
2234            return bfd_reloc_ok;
2235          }
2236    
2237      case R_SCORE_PC19:      case R_SCORE_PC19:
2238        addend = bfd_get_32 (input_bfd, hit_data);        addend = score_bfd_get_32 (input_bfd, hit_data);
2239        offset = (((addend & howto->src_mask) & 0x3ff0000) >> 6) | ((addend & howto->src_mask) & 0x3ff);        offset = (((addend & howto->src_mask) & 0x3ff0000) >> 6) | ((addend & howto->src_mask) & 0x3ff);
2240        if ((offset & 0x80000) != 0)        if ((offset & 0x80000) != 0)
2241          offset |= 0xfff00000;          offset |= 0xfff00000;
# Line 2045  score_elf_final_link_relocate (reloc_how Line 2247  score_elf_final_link_relocate (reloc_how
2247          return bfd_reloc_overflow;          return bfd_reloc_overflow;
2248        addend = (addend & ~howto->src_mask)        addend = (addend & ~howto->src_mask)
2249                  | (((value << 6) & howto->src_mask) & 0x3ff0000) | (value & 0x3ff);                  | (((value << 6) & howto->src_mask) & 0x3ff0000) | (value & 0x3ff);
2250        bfd_put_32 (input_bfd, addend, hit_data);        score_bfd_put_32 (input_bfd, addend, hit_data);
2251        return bfd_reloc_ok;        return bfd_reloc_ok;
2252    
2253      case R_SCORE16_11:      case R_SCORE16_11:
2254        addend = bfd_get_16 (input_bfd, hit_data);        addend = score_bfd_get_16 (input_bfd, hit_data);
2255        offset = addend & howto->src_mask;        offset = addend & howto->src_mask;
2256        if ((offset & 0x800) != 0)        /* Offset is negative.  */        if ((offset & 0x800) != 0)        /* Offset is negative.  */
2257          offset |= 0xfffff000;          offset |= 0xfffff000;
2258        value += offset;        value += offset;
2259          abs_value = abs (value - rel_addr);
2260          if ((abs_value & 0xfffff000) != 0)
2261            return bfd_reloc_overflow;
2262        addend = (addend & ~howto->src_mask) | (value & howto->src_mask);        addend = (addend & ~howto->src_mask) | (value & howto->src_mask);
2263        bfd_put_16 (input_bfd, addend, hit_data);        score_bfd_put_16 (input_bfd, addend, hit_data);
2264        return bfd_reloc_ok;        return bfd_reloc_ok;
2265    
2266      case R_SCORE16_PC8:      case R_SCORE16_PC8:
2267        addend = bfd_get_16 (input_bfd, hit_data);        addend = score_bfd_get_16 (input_bfd, hit_data);
2268        offset = (addend & howto->src_mask) << 1;        offset = (addend & howto->src_mask) << 1;
2269        if ((offset & 0x100) != 0)        /* Offset is negative.  */        if ((offset & 0x200) != 0)        /* Offset is negative.  */
2270          offset |= 0xfffffe00;          offset |= 0xfffffe00;
2271        abs_value = value = value - rel_addr + offset;        abs_value = value = value - rel_addr + offset;
2272        /* Sign bit + exceed 9 bit.  */        /* Sign bit + exceed 9 bit.  */
2273        if (((value & 0xffffff00) != 0) && ((value & 0xffffff00) != 0xffffff00))        if (((value & 0xfffffe00) != 0) && ((value & 0xfffffe00) != 0xfffffe00))
2274          return bfd_reloc_overflow;          return bfd_reloc_overflow;
2275        value >>= 1;        value >>= 1;
2276        addend = (addend & ~howto->src_mask) | (value & howto->src_mask);        addend = (addend & ~howto->src_mask) | (value & howto->src_mask);
2277        bfd_put_16 (input_bfd, addend, hit_data);        score_bfd_put_16 (input_bfd, addend, hit_data);
2278          return bfd_reloc_ok;
2279    
2280        case R_SCORE_BCMP:
2281          addend = score_bfd_get_32 (input_bfd, hit_data);
2282          offset = (addend & howto->src_mask) << howto->rightshift;
2283          if ((offset & 0x200) != 0)        /* Offset is negative.  */
2284            offset |= 0xfffffe00;
2285          value = value - rel_addr + offset;
2286          /* Sign bit + exceed 9 bit.  */
2287          if (((value & 0xfffffe00) != 0) && ((value & 0xfffffe00) != 0xfffffe00))
2288            return bfd_reloc_overflow;
2289          value >>= howto->rightshift;
2290          addend = (addend & ~howto->src_mask)
2291                   | (value & 0x1)
2292                   | (((value >> 1) & 0x7) << 7)
2293                   | (((value >> 4) & 0x1f) << 21);
2294          score_bfd_put_32 (input_bfd, addend, hit_data);
2295        return bfd_reloc_ok;        return bfd_reloc_ok;
2296    
2297      case R_SCORE_HI16:      case R_SCORE_HI16:
2298        return bfd_reloc_ok;        return bfd_reloc_ok;
2299    
2300      case R_SCORE_LO16:      case R_SCORE_LO16:
2301        hi16_addend = bfd_get_32 (input_bfd, hit_data - 4);        hi16_addend = score_bfd_get_32 (input_bfd, hit_data - 4);
2302        hi16_offset = ((((hi16_addend >> 16) & 0x3) << 15) | (hi16_addend & 0x7fff)) >> 1;        hi16_offset = ((((hi16_addend >> 16) & 0x3) << 15) | (hi16_addend & 0x7fff)) >> 1;
2303        addend = bfd_get_32 (input_bfd, hit_data);        addend = score_bfd_get_32 (input_bfd, hit_data);
2304        offset = ((((addend >> 16) & 0x3) << 15) | (addend & 0x7fff)) >> 1;        offset = ((((addend >> 16) & 0x3) << 15) | (addend & 0x7fff)) >> 1;
2305        offset = (hi16_offset << 16) | (offset & 0xffff);        offset = (hi16_offset << 16) | (offset & 0xffff);
2306    
2307        if (!gp_disp_p)        if (!gp_disp_p)
2308          uvalue = value + offset;          uvalue = value + offset;
2309        else        else
2310          uvalue = offset + gp - rel_addr + 4;          uvalue = offset + gp - rel_addr + 4;
2311    
2312        hi16_offset = (uvalue >> 16) << 1;        hi16_offset = (uvalue >> 16) << 1;
2313        hi16_value = (hi16_addend & (~(howto->dst_mask)))        hi16_value = (hi16_addend & (~(howto->dst_mask)))
2314                          | (hi16_offset & 0x7fff) | ((hi16_offset << 1) & 0x30000);                          | (hi16_offset & 0x7fff) | ((hi16_offset << 1) & 0x30000);
2315        bfd_put_32 (input_bfd, hi16_value, hit_data - 4);        score_bfd_put_32 (input_bfd, hi16_value, hit_data - 4);
2316        offset = (uvalue & 0xffff) << 1;        offset = (uvalue & 0xffff) << 1;
2317        value = (addend & (~(howto->dst_mask))) | (offset & 0x7fff) | ((offset << 1) & 0x30000);        value = (addend & (~(howto->dst_mask))) | (offset & 0x7fff) | ((offset << 1) & 0x30000);
2318        bfd_put_32 (input_bfd, value, hit_data);        score_bfd_put_32 (input_bfd, value, hit_data);
2319        return bfd_reloc_ok;        return bfd_reloc_ok;
2320    
2321      case R_SCORE_GP15:      case R_SCORE_GP15:
2322        addend = bfd_get_32 (input_bfd, hit_data);        addend = score_bfd_get_32 (input_bfd, hit_data);
2323        offset = addend & 0x7fff;        offset = addend & 0x7fff;
2324        if ((offset & 0x4000) == 0x4000)        if ((offset & 0x4000) == 0x4000)
2325          offset |= 0xffffc000;          offset |= 0xffffc000;
# Line 2105  score_elf_final_link_relocate (reloc_how Line 2327  score_elf_final_link_relocate (reloc_how
2327        if (((value & 0xffffc000) != 0) && ((value & 0xffffc000) != 0xffffc000))        if (((value & 0xffffc000) != 0) && ((value & 0xffffc000) != 0xffffc000))
2328          return bfd_reloc_overflow;          return bfd_reloc_overflow;
2329        value = (addend & ~howto->src_mask) | (value & howto->src_mask);        value = (addend & ~howto->src_mask) | (value & howto->src_mask);
2330        bfd_put_32 (input_bfd, value, hit_data);        score_bfd_put_32 (input_bfd, value, hit_data);
2331        return bfd_reloc_ok;        return bfd_reloc_ok;
2332    
2333      case R_SCORE_GOT15:      case R_SCORE_GOT15:
2334      case R_SCORE_CALL15:      case R_SCORE_CALL15:
2335        if (local_p)        if (local_p)
2336          {          {
2337            bfd_boolean forced;            bfd_boolean forced;
2338    
2339            /* The special case is when the symbol is forced to be local.  We need the            /* The special case is when the symbol is forced to be local.  We need the
2340               full address in the GOT since no R_SCORE_GOT_LO16 relocation follows.  */               full address in the GOT since no R_SCORE_GOT_LO16 relocation follows.  */
2341            forced = ! score_elf_local_relocation_p (input_bfd, rel, FALSE);            forced = ! score_elf_local_relocation_p (input_bfd, rel,
2342            value = score_elf_got16_entry (output_bfd, input_bfd, info,                                                     local_sections, FALSE);
2343                                           symbol + addend, forced);            value = score_elf_got16_entry (output_bfd, input_bfd, info,
2344            if (value == MINUS_ONE)                                           symbol + addend, forced);
2345              return bfd_reloc_outofrange;            if (value == MINUS_ONE)
2346            value = score_elf_got_offset_from_index (elf_hash_table (info)->dynobj,              return bfd_reloc_outofrange;
2347                                                     output_bfd, input_bfd, value);            value = score_elf_got_offset_from_index (elf_hash_table (info)->dynobj,
2348          }                                                     output_bfd, input_bfd, value);
2349            }
2350        else        else
2351          {          {
2352            value = g;            value = g;
2353          }          }
2354    
2355        if ((long) value > 0x3fff || (long) value < -0x4000)        if ((long) value > 0x3fff || (long) value < -0x4000)
2356          return bfd_reloc_overflow;          return bfd_reloc_overflow;
2357    
2358        addend = bfd_get_32 (input_bfd, hit_data);        addend = score_bfd_get_32 (input_bfd, hit_data);
2359        value = (addend & ~howto->dst_mask) | (value & howto->dst_mask);        value = (addend & ~howto->dst_mask) | (value & howto->dst_mask);
2360        bfd_put_32 (input_bfd, value, hit_data);        score_bfd_put_32 (input_bfd, value, hit_data);
2361        return bfd_reloc_ok;        return bfd_reloc_ok;
2362    
2363      case R_SCORE_GPREL32:      case R_SCORE_GPREL32:
2364        value = (addend + symbol - gp);        value = (addend + symbol - gp);
2365        value &= howto->dst_mask;        value &= howto->dst_mask;
2366        bfd_put_32 (input_bfd, value, hit_data);        score_bfd_put_32 (input_bfd, value, hit_data);
2367        return bfd_reloc_ok;        return bfd_reloc_ok;
2368    
2369      case R_SCORE_GOT_LO16:      case R_SCORE_GOT_LO16:
2370        addend = bfd_get_32 (input_bfd, hit_data);        addend = score_bfd_get_32 (input_bfd, hit_data);
2371        value = (((addend >> 16) & 0x3) << 14) | ((addend & 0x7fff) >> 1);        value = (((addend >> 16) & 0x3) << 14) | ((addend & 0x7fff) >> 1);
2372        value += symbol;        value += symbol;
2373        value = (addend & (~(howto->dst_mask))) | ((value & 0x3fff) << 1)          value = (addend & (~(howto->dst_mask))) | ((value & 0x3fff) << 1)
2374                 | (((value >> 14) & 0x3) << 16);                 | (((value >> 14) & 0x3) << 16);
2375    
2376        bfd_put_32 (input_bfd, value, hit_data);        score_bfd_put_32 (input_bfd, value, hit_data);
2377        return bfd_reloc_ok;        return bfd_reloc_ok;
2378    
2379      case R_SCORE_DUMMY_HI16:      case R_SCORE_DUMMY_HI16:
# Line 2167  score_elf_final_link_relocate (reloc_how Line 2390  score_elf_final_link_relocate (reloc_how
2390  }  }
2391    
2392  /* Score backend functions.  */  /* Score backend functions.  */
   
2393  static void  static void
2394  _bfd_score_info_to_howto (bfd *abfd ATTRIBUTE_UNUSED,  s3_bfd_score_info_to_howto (bfd *abfd ATTRIBUTE_UNUSED,
2395                            arelent *bfd_reloc,                              arelent *bfd_reloc,
2396                            Elf_Internal_Rela *elf_reloc)                              Elf_Internal_Rela *elf_reloc)
2397  {  {
2398    unsigned int r_type;    unsigned int r_type;
2399    
2400    r_type = ELF32_R_TYPE (elf_reloc->r_info);    r_type = ELF32_R_TYPE (elf_reloc->r_info);
2401    if (r_type >= NUM_ELEM (elf32_score_howto_table))    if (r_type >= ARRAY_SIZE (elf32_score_howto_table))
2402      bfd_reloc->howto = NULL;      bfd_reloc->howto = NULL;
2403    else    else
2404      bfd_reloc->howto = &elf32_score_howto_table[r_type];      bfd_reloc->howto = &elf32_score_howto_table[r_type];
2405  }  }
2406    
2407  /* Relocate an score ELF section.  */  /* Relocate an score ELF section.  */
   
2408  static bfd_boolean  static bfd_boolean
2409  _bfd_score_elf_relocate_section (bfd *output_bfd,  s3_bfd_score_elf_relocate_section (bfd *output_bfd,
2410                                   struct bfd_link_info *info,                                     struct bfd_link_info *info,
2411                                   bfd *input_bfd,                                     bfd *input_bfd,
2412                                   asection *input_section,                                     asection *input_section,
2413                                   bfd_byte *contents,                                     bfd_byte *contents,
2414                                   Elf_Internal_Rela *relocs,                                     Elf_Internal_Rela *relocs,
2415                                   Elf_Internal_Sym *local_syms,                                     Elf_Internal_Sym *local_syms,
2416                                   asection **local_sections)                                     asection **local_sections)
2417  {  {
2418    Elf_Internal_Shdr *symtab_hdr;    Elf_Internal_Shdr *symtab_hdr;
2419    struct elf_link_hash_entry **sym_hashes;    struct elf_link_hash_entry **sym_hashes;
# Line 2209  _bfd_score_elf_relocate_section (bfd *ou Line 2430  _bfd_score_elf_relocate_section (bfd *ou
2430      {      {
2431        bfd_size_type dynsecsymcount = 0;        bfd_size_type dynsecsymcount = 0;
2432        if (info->shared)        if (info->shared)
2433          {          {
2434            asection * p;            asection * p;
2435            const struct elf_backend_data *bed = get_elf_backend_data (output_bfd);            const struct elf_backend_data *bed = get_elf_backend_data (output_bfd);
2436    
2437            for (p = output_bfd->sections; p ; p = p->next)            for (p = output_bfd->sections; p ; p = p->next)
2438              if ((p->flags & SEC_EXCLUDE) == 0              if ((p->flags & SEC_EXCLUDE) == 0
2439                  && (p->flags & SEC_ALLOC) != 0                  && (p->flags & SEC_ALLOC) != 0
2440                  && !(*bed->elf_backend_omit_section_dynsym) (output_bfd, info, p))                  && !(*bed->elf_backend_omit_section_dynsym) (output_bfd, info, p))
2441                ++ dynsecsymcount;                ++ dynsecsymcount;
2442          }          }
2443    
2444        if (!score_elf_sort_hash_table (info, dynsecsymcount + 1))        if (!score_elf_sort_hash_table (info, dynsecsymcount + 1))
2445          return FALSE;          return FALSE;
2446      }      }
2447    
2448    symtab_hdr = &elf_tdata (input_bfd)->symtab_hdr;    symtab_hdr = &elf_tdata (input_bfd)->symtab_hdr;
2449    extsymoff = symtab_hdr->sh_info;    extsymoff = (elf_bad_symtab (input_bfd)) ? 0 : symtab_hdr->sh_info;
2450    sym_hashes = elf_sym_hashes (input_bfd);    sym_hashes = elf_sym_hashes (input_bfd);
2451    rel = relocs;    rel = relocs;
2452    relend = relocs + input_section->reloc_count;    relend = relocs + input_section->reloc_count;
# Line 2244  _bfd_score_elf_relocate_section (bfd *ou Line 2465  _bfd_score_elf_relocate_section (bfd *ou
2465        r_symndx = ELF32_R_SYM (rel->r_info);        r_symndx = ELF32_R_SYM (rel->r_info);
2466        r_type = ELF32_R_TYPE (rel->r_info);        r_type = ELF32_R_TYPE (rel->r_info);
2467    
2468        _bfd_score_info_to_howto (input_bfd, &bfd_reloc, (Elf_Internal_Rela *) rel);        s3_bfd_score_info_to_howto (input_bfd, &bfd_reloc, (Elf_Internal_Rela *) rel);
2469        howto = bfd_reloc.howto;        howto = bfd_reloc.howto;
2470    
2471        h = NULL;        h = NULL;
# Line 2256  _bfd_score_elf_relocate_section (bfd *ou Line 2477  _bfd_score_elf_relocate_section (bfd *ou
2477            sym = local_syms + r_symndx;            sym = local_syms + r_symndx;
2478            sec = local_sections[r_symndx];            sec = local_sections[r_symndx];
2479            relocation = (sec->output_section->vma            relocation = (sec->output_section->vma
2480                          + sec->output_offset                          + sec->output_offset
2481                          + sym->st_value);                          + sym->st_value);
2482            name = bfd_elf_sym_name (input_bfd, symtab_hdr, sym, sec);            name = bfd_elf_sym_name (input_bfd, symtab_hdr, sym, sec);
2483    
2484            if (!info->relocatable            if (!info->relocatable
2485                && (sec->flags & SEC_MERGE) != 0                && (sec->flags & SEC_MERGE)
2486                && ELF_ST_TYPE (sym->st_info) == STT_SECTION)                && ELF_ST_TYPE (sym->st_info) == STT_SECTION)
2487              {              {
2488                asection *msec;                asection *msec;
2489                bfd_vma addend, value;                bfd_vma addend, value;
# Line 2272  _bfd_score_elf_relocate_section (bfd *ou Line 2493  _bfd_score_elf_relocate_section (bfd *ou
2493                  case R_SCORE_HI16:                  case R_SCORE_HI16:
2494                    break;                    break;
2495                  case R_SCORE_LO16:                  case R_SCORE_LO16:
2496                    hi16_addend = bfd_get_32 (input_bfd, contents + rel->r_offset - 4);                    hi16_addend = score_bfd_get_32 (input_bfd, contents + rel->r_offset - 4);
2497                    hi16_offset = ((((hi16_addend >> 16) & 0x3) << 15) | (hi16_addend & 0x7fff)) >> 1;                    hi16_offset = ((((hi16_addend >> 16) & 0x3) << 15) | (hi16_addend & 0x7fff)) >> 1;
2498                    value = bfd_get_32 (input_bfd, contents + rel->r_offset);                    value = score_bfd_get_32 (input_bfd, contents + rel->r_offset);
2499                    offset = ((((value >> 16) & 0x3) << 15) | (value & 0x7fff)) >> 1;                    offset = ((((value >> 16) & 0x3) << 15) | (value & 0x7fff)) >> 1;
2500                    addend = (hi16_offset << 16) | (offset & 0xffff);                    addend = (hi16_offset << 16) | (offset & 0xffff);
2501                    msec = sec;                    msec = sec;
# Line 2285  _bfd_score_elf_relocate_section (bfd *ou Line 2506  _bfd_score_elf_relocate_section (bfd *ou
2506                    hi16_offset = (uvalue >> 16) << 1;                    hi16_offset = (uvalue >> 16) << 1;
2507                    hi16_value = (hi16_addend & (~(howto->dst_mask)))                    hi16_value = (hi16_addend & (~(howto->dst_mask)))
2508                      | (hi16_offset & 0x7fff) | ((hi16_offset << 1) & 0x30000);                      | (hi16_offset & 0x7fff) | ((hi16_offset << 1) & 0x30000);
2509                    bfd_put_32 (input_bfd, hi16_value, contents + rel->r_offset - 4);                    score_bfd_put_32 (input_bfd, hi16_value, contents + rel->r_offset - 4);
2510                    offset = (uvalue & 0xffff) << 1;                    offset = (uvalue & 0xffff) << 1;
2511                    value = (value & (~(howto->dst_mask)))                    value = (value & (~(howto->dst_mask)))
2512                      | (offset & 0x7fff) | ((offset << 1) & 0x30000);                      | (offset & 0x7fff) | ((offset << 1) & 0x30000);
2513                    bfd_put_32 (input_bfd, value, contents + rel->r_offset);                    score_bfd_put_32 (input_bfd, value, contents + rel->r_offset);
2514                    break;                    break;
2515    
2516                    case R_SCORE_IMM32:
2517                      {
2518                        value = score_bfd_get_48 (input_bfd, contents + rel->r_offset);
2519                        addend = ((value >> 5) & 0x3ff)
2520                                  | (((value >> 16) & 0x7fff) << 10)
2521                                  | (((value >> 32) & 0x7f) << 25);
2522                        msec = sec;
2523                        addend = _bfd_elf_rel_local_sym (output_bfd, sym, &msec, addend);
2524                        addend -= relocation;
2525                        addend += msec->output_section->vma + msec->output_offset;
2526                        addend &= 0xffffffff;
2527                        value = (value & ~howto->src_mask)
2528                                 | ((addend & 0x3ff) << 5)
2529                                 | (((addend >> 10) & 0x7fff) << 16)
2530                                 | (((addend >> 25) & 0x7f) << 32);
2531                        score_bfd_put_48 (input_bfd, value, contents + rel->r_offset);
2532                        break;
2533                      }
2534    
2535                    case R_SCORE_IMM30:
2536                      {
2537                        int not_word_align_p = 0;
2538                        value = score_bfd_get_48 (input_bfd, contents + rel->r_offset);
2539                        addend = ((value >> 7) & 0xff)
2540                                  | (((value >> 16) & 0x7fff) << 8)
2541                                  | (((value >> 32) & 0x7f) << 23);
2542                        addend <<= howto->rightshift;
2543                        msec = sec;
2544                        addend = _bfd_elf_rel_local_sym (output_bfd, sym, &msec, addend);
2545                        addend -= relocation;
2546                        addend += msec->output_section->vma + msec->output_offset;
2547                        addend &= 0xffffffff;
2548    
2549                        /* Check lw48/sw48 rd, value/label word align.  */
2550                        if ((addend & 0x3) != 0)
2551                          not_word_align_p = 1;
2552    
2553                        addend >>= howto->rightshift;
2554                        value = (value & ~howto->src_mask)
2555                                 | (((addend & 0xff) >> 0) << 7)
2556                                 | (((addend & 0x7fff00) >> 8) << 16)
2557                                 | (((addend & 0x3f800000) >> 23) << 32);
2558                        score_bfd_put_48 (input_bfd, value, contents + rel->r_offset);
2559    
2560                        if (not_word_align_p)
2561                          return bfd_reloc_other;
2562                        else
2563                          break;
2564                      }
2565    
2566                  case R_SCORE_GOT_LO16:                  case R_SCORE_GOT_LO16:
2567                    value = bfd_get_32 (input_bfd, contents + rel->r_offset);                    value = score_bfd_get_32 (input_bfd, contents + rel->r_offset);
2568                    addend = (((value >> 16) & 0x3) << 14) | ((value & 0x7fff) >> 1);                    addend = (((value >> 16) & 0x3) << 14) | ((value & 0x7fff) >> 1);
2569                    msec = sec;                    msec = sec;
2570                    addend = _bfd_elf_rel_local_sym (output_bfd, sym, &msec, addend) - relocation;                    addend = _bfd_elf_rel_local_sym (output_bfd, sym, &msec, addend) - relocation;
# Line 2300  _bfd_score_elf_relocate_section (bfd *ou Line 2572  _bfd_score_elf_relocate_section (bfd *ou
2572                    value = (value & (~(howto->dst_mask))) | ((addend & 0x3fff) << 1)                    value = (value & (~(howto->dst_mask))) | ((addend & 0x3fff) << 1)
2573                             | (((addend >> 14) & 0x3) << 16);                             | (((addend >> 14) & 0x3) << 16);
2574    
2575                    bfd_put_32 (input_bfd, value, contents + rel->r_offset);                    score_bfd_put_32 (input_bfd, value, contents + rel->r_offset);
2576                    break;                    break;
2577                  default:  
2578                    case R_SCORE_ABS32:
2579                    case R_SCORE_REL32:
2580                    value = bfd_get_32 (input_bfd, contents + rel->r_offset);                    value = bfd_get_32 (input_bfd, contents + rel->r_offset);
2581                    /* Get the (signed) value from the instruction.  */                    /* Get the (signed) value from the instruction.  */
2582                    addend = value & howto->src_mask;                    addend = value & howto->src_mask;
# Line 2320  _bfd_score_elf_relocate_section (bfd *ou Line 2594  _bfd_score_elf_relocate_section (bfd *ou
2594                    value = (value & ~howto->dst_mask) | (addend & howto->dst_mask);                    value = (value & ~howto->dst_mask) | (addend & howto->dst_mask);
2595                    bfd_put_32 (input_bfd, value, contents + rel->r_offset);                    bfd_put_32 (input_bfd, value, contents + rel->r_offset);
2596                    break;                    break;
2597    
2598                    default:
2599                      value = score_bfd_get_32 (input_bfd, contents + rel->r_offset);
2600                      /* Get the (signed) value from the instruction.  */
2601                      addend = value & howto->src_mask;
2602                      if (addend & ((howto->src_mask + 1) >> 1))
2603                        {
2604                          bfd_signed_vma mask;
2605    
2606                          mask = -1;
2607                          mask &= ~howto->src_mask;
2608                          addend |= mask;
2609                        }
2610                      msec = sec;
2611                      addend = _bfd_elf_rel_local_sym (output_bfd, sym, &msec, addend) - relocation;
2612                      addend += msec->output_section->vma + msec->output_offset;
2613                      value = (value & ~howto->dst_mask) | (addend & howto->dst_mask);
2614                      score_bfd_put_32 (input_bfd, value, contents + rel->r_offset);
2615                      break;
2616                  }                  }
2617              }              }
2618          }          }
2619        else        else
2620          {          {
2621            /* For global symbols we look up the symbol in the hash-table.  */            /* For global symbols we look up the symbol in the hash-table.  */
2622            h = ((struct score_elf_link_hash_entry *)            h = ((struct score_elf_link_hash_entry *)
2623                 elf_sym_hashes (input_bfd) [r_symndx - extsymoff]);                 elf_sym_hashes (input_bfd) [r_symndx - extsymoff]);
2624            /* Find the real hash-table entry for this symbol.  */            /* Find the real hash-table entry for this symbol.  */
2625            while (h->root.root.type == bfd_link_hash_indirect            while (h->root.root.type == bfd_link_hash_indirect
2626                   || h->root.root.type == bfd_link_hash_warning)                   || h->root.root.type == bfd_link_hash_warning)
2627              h = (struct score_elf_link_hash_entry *) h->root.root.u.i.link;              h = (struct score_elf_link_hash_entry *) h->root.root.u.i.link;
2628    
2629            /* Record the name of this symbol, for our caller.  */            /* Record the name of this symbol, for our caller.  */
2630            name = h->root.root.root.string;            name = h->root.root.root.string;
2631    
2632            /* See if this is the special GP_DISP_LABEL symbol.  Note that such a            /* See if this is the special GP_DISP_LABEL symbol.  Note that such a
2633               symbol must always be a global symbol.  */               symbol must always be a global symbol.  */
2634            if (strcmp (name, GP_DISP_LABEL) == 0)            if (strcmp (name, GP_DISP_LABEL) == 0)
2635              {              {
2636                /* Relocations against GP_DISP_LABEL are permitted only with                /* Relocations against GP_DISP_LABEL are permitted only with
2637                   R_SCORE_HI16 and R_SCORE_LO16 relocations.  */                   R_SCORE_HI16 and R_SCORE_LO16 relocations.  */
2638                if (r_type != R_SCORE_HI16 && r_type != R_SCORE_LO16)                if (r_type != R_SCORE_HI16 && r_type != R_SCORE_LO16)
2639                  return bfd_reloc_notsupported;                  return bfd_reloc_notsupported;
2640    
2641                gp_disp_p = TRUE;                gp_disp_p = TRUE;
2642              }              }
2643    
2644            /* If this symbol is defined, calculate its address.  Note that            /* If this symbol is defined, calculate its address.  Note that
2645                GP_DISP_LABEL is a magic symbol, always implicitly defined by the                GP_DISP_LABEL is a magic symbol, always implicitly defined by the
2646                linker, so it's inappropriate to check to see whether or not                linker, so it's inappropriate to check to see whether or not
2647                its defined.  */                its defined.  */
2648            else if ((h->root.root.type == bfd_link_hash_defined            else if ((h->root.root.type == bfd_link_hash_defined
2649                      || h->root.root.type == bfd_link_hash_defweak)                      || h->root.root.type == bfd_link_hash_defweak)
2650                     && h->root.root.u.def.section)                     && h->root.root.u.def.section)
2651              {              {
2652                sec = h->root.root.u.def.section;                sec = h->root.root.u.def.section;
2653                if (sec->output_section)                if (sec->output_section)
2654                  relocation = (h->root.root.u.def.value                  relocation = (h->root.root.u.def.value
2655                                + sec->output_section->vma                                + sec->output_section->vma
2656                                + sec->output_offset);                                + sec->output_offset);
2657                else                else
2658                  {                  {
2659                    relocation = h->root.root.u.def.value;                    relocation = h->root.root.u.def.value;
2660                  }                  }
2661              }              }
2662            else if (h->root.root.type == bfd_link_hash_undefweak)            else if (h->root.root.type == bfd_link_hash_undefweak)
2663              /* We allow relocations against undefined weak symbols, giving              /* We allow relocations against undefined weak symbols, giving
2664                 it the value zero, so that you can undefined weak functions                 it the value zero, so that you can undefined weak functions
2665                 and check to see if they exist by looking at their addresses.  */                 and check to see if they exist by looking at their addresses.  */
2666              relocation = 0;              relocation = 0;
2667            else if (info->unresolved_syms_in_objects == RM_IGNORE            else if (info->unresolved_syms_in_objects == RM_IGNORE
2668                     && ELF_ST_VISIBILITY (h->root.other) == STV_DEFAULT)                     && ELF_ST_VISIBILITY (h->root.other) == STV_DEFAULT)
2669              relocation = 0;              relocation = 0;
2670            else if (strcmp (name, "_DYNAMIC_LINK") == 0)            else if (strcmp (name, "_DYNAMIC_LINK") == 0)
2671              {              {
2672                /* If this is a dynamic link, we should have created a _DYNAMIC_LINK symbol                /* If this is a dynamic link, we should have created a _DYNAMIC_LINK symbol
2673                   in _bfd_score_elf_create_dynamic_sections.  Otherwise, we should define                   in s3_bfd_score_elf_create_dynamic_sections.  Otherwise, we should define
2674                   the symbol with a value of 0.  */                   the symbol with a value of 0.  */
2675                BFD_ASSERT (! info->shared);                BFD_ASSERT (! info->shared);
2676                BFD_ASSERT (bfd_get_section_by_name (output_bfd, ".dynamic") == NULL);                BFD_ASSERT (bfd_get_section_by_name (output_bfd, ".dynamic") == NULL);
2677                relocation = 0;                relocation = 0;
2678              }              }
2679            else if (!info->relocatable)            else if (!info->relocatable)
2680              {              {
2681                if (! ((*info->callbacks->undefined_symbol)                if (! ((*info->callbacks->undefined_symbol)
2682                       (info, h->root.root.root.string, input_bfd,                       (info, h->root.root.root.string, input_bfd,
2683                        input_section, rel->r_offset,                        input_section, rel->r_offset,
2684                        (info->unresolved_syms_in_objects == RM_GENERATE_ERROR)                        (info->unresolved_syms_in_objects == RM_GENERATE_ERROR)
2685                        || ELF_ST_VISIBILITY (h->root.other))))                        || ELF_ST_VISIBILITY (h->root.other))))
2686                  return bfd_reloc_undefined;                  return bfd_reloc_undefined;
2687                relocation = 0;                relocation = 0;
2688              }              }
2689          }          }
2690    
2691        if (sec != NULL && elf_discarded_section (sec))        if (sec != NULL && elf_discarded_section (sec))
2692          {          {
2693            /* For relocs against symbols from removed linkonce sections,            /* For relocs against symbols from removed linkonce sections,
2694               or sections discarded by a linker script, we just want the               or sections discarded by a linker script, we just want the
2695               section contents zeroed.  Avoid any special processing.  */               section contents zeroed.  Avoid any special processing.  */
2696            _bfd_clear_contents (howto, input_bfd, contents + rel->r_offset);            _bfd_clear_contents (howto, input_bfd, contents + rel->r_offset);
2697            rel->r_info = 0;            rel->r_info = 0;
2698            rel->r_addend = 0;            rel->r_addend = 0;
2699            continue;            continue;
2700          }          }
2701    
2702        if (info->relocatable)        if (info->relocatable)
2703          {          {
# Line 2412  _bfd_score_elf_relocate_section (bfd *ou Line 2705  _bfd_score_elf_relocate_section (bfd *ou
2705               anything, unless the reloc is against a section symbol,               anything, unless the reloc is against a section symbol,
2706               in which case we have to adjust according to where the               in which case we have to adjust according to where the
2707               section symbol winds up in the output section.  */               section symbol winds up in the output section.  */
2708            if (sym != NULL && ELF_ST_TYPE (sym->st_info) == STT_SECTION)            if (r_symndx < symtab_hdr->sh_info)
2709              score_elf_add_to_rel (input_bfd, contents + rel->r_offset,              {
2710                                    howto, (bfd_signed_vma) sec->output_offset);                sym = local_syms + r_symndx;
2711                  if (ELF_ST_TYPE (sym->st_info) == STT_SECTION)
2712                    {
2713                      sec = local_sections[r_symndx];
2714                      score_elf_add_to_rel (input_bfd, contents + rel->r_offset,
2715                                        howto, (bfd_signed_vma) (sec->output_offset + sym->st_value));
2716                    }
2717                }
2718            continue;            continue;
2719          }          }
2720    
2721          /* This is a final link.  */
2722        r = score_elf_final_link_relocate (howto, input_bfd, output_bfd,        r = score_elf_final_link_relocate (howto, input_bfd, output_bfd,
2723                                           input_section, contents, rel, relocs,                                           input_section, contents, rel, relocs,
2724                                           relocation, info, name,                                           relocation, info, name,
2725                                           (h ? ELF_ST_TYPE ((unsigned int)h->root.root.type) :                                           (h ? ELF_ST_TYPE ((unsigned int)h->root.root.type) :
2726                                           ELF_ST_TYPE ((unsigned int)sym->st_info)), h,                                           ELF_ST_TYPE ((unsigned int)sym->st_info)), h, local_sections,
2727                                           gp_disp_p);                                           gp_disp_p);
2728    
2729        if (r != bfd_reloc_ok)        if (r != bfd_reloc_ok)
# Line 2459  _bfd_score_elf_relocate_section (bfd *ou Line 2760  _bfd_score_elf_relocate_section (bfd *ou
2760                msg = _("internal error: dangerous error");                msg = _("internal error: dangerous error");
2761                goto common_error;                goto common_error;
2762    
2763                /* Use bfd_reloc_other to check lw48, sw48 word align.  */
2764                case bfd_reloc_other:
2765                  msg = _("address not word align");
2766                  goto common_error;
2767    
2768              default:              default:
2769                msg = _("internal error: unknown error");                msg = _("internal error: unknown error");
2770                /* fall through */                /* fall through */
# Line 2477  _bfd_score_elf_relocate_section (bfd *ou Line 2783  _bfd_score_elf_relocate_section (bfd *ou
2783    
2784  /* Look through the relocs for a section during the first phase, and  /* Look through the relocs for a section during the first phase, and
2785     allocate space in the global offset table.  */     allocate space in the global offset table.  */
   
2786  static bfd_boolean  static bfd_boolean
2787  _bfd_score_elf_check_relocs (bfd *abfd,  s3_bfd_score_elf_check_relocs (bfd *abfd,
2788                               struct bfd_link_info *info,                                 struct bfd_link_info *info,
2789                               asection *sec,                                 asection *sec,
2790                               const Elf_Internal_Rela *relocs)                                 const Elf_Internal_Rela *relocs)
2791  {  {
2792    const char *name;    const char *name;
2793    bfd *dynobj;    bfd *dynobj;
# Line 2502  _bfd_score_elf_check_relocs (bfd *abfd, Line 2807  _bfd_score_elf_check_relocs (bfd *abfd,
2807    dynobj = elf_hash_table (info)->dynobj;    dynobj = elf_hash_table (info)->dynobj;
2808    symtab_hdr = &elf_tdata (abfd)->symtab_hdr;    symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
2809    sym_hashes = elf_sym_hashes (abfd);    sym_hashes = elf_sym_hashes (abfd);
2810    extsymoff = symtab_hdr->sh_info;    extsymoff = (elf_bad_symtab (abfd)) ? 0 : symtab_hdr->sh_info;
2811    
2812    name = bfd_get_section_name (abfd, sec);    name = bfd_get_section_name (abfd, sec);
2813    
# Line 2537  _bfd_score_elf_check_relocs (bfd *abfd, Line 2842  _bfd_score_elf_check_relocs (bfd *abfd,
2842        r_type = ELF32_R_TYPE (rel->r_info);        r_type = ELF32_R_TYPE (rel->r_info);
2843    
2844        if (r_symndx < extsymoff)        if (r_symndx < extsymoff)
2845          {          {
2846            h = NULL;            h = NULL;
2847          }          }
2848        else if (r_symndx >= extsymoff + NUM_SHDR_ENTRIES (symtab_hdr))        else if (r_symndx >= extsymoff + NUM_SHDR_ENTRIES (symtab_hdr))
2849          {          {
2850            (*_bfd_error_handler) (_("%s: Malformed reloc detected for section %s"), abfd, name);            (*_bfd_error_handler) (_("%s: Malformed reloc detected for section %s"), abfd, name);
# Line 2583  _bfd_score_elf_check_relocs (bfd *abfd, Line 2888  _bfd_score_elf_check_relocs (bfd *abfd,
2888    
2889        if (!h && (r_type == R_SCORE_GOT_LO16))        if (!h && (r_type == R_SCORE_GOT_LO16))
2890          {          {
2891            if (! score_elf_record_local_got_symbol (abfd, r_symndx, rel->r_addend, g))            if (! score_elf_record_local_got_symbol (abfd, r_symndx, rel->r_addend, g))
2892              return FALSE;              return FALSE;
2893          }          }
2894    
2895        switch (r_type)        switch (r_type)
2896          {          {
2897          case R_SCORE_CALL15:          case R_SCORE_CALL15:
2898            if (h == NULL)            if (h == NULL)
2899              {              {
2900                (*_bfd_error_handler)                (*_bfd_error_handler)
2901                  (_("%B: CALL15 reloc at 0x%lx not against global symbol"),                  (_("%B: CALL15 reloc at 0x%lx not against global symbol"),
2902                   abfd, (unsigned long) rel->r_offset);                   abfd, (unsigned long) rel->r_offset);
2903                bfd_set_error (bfd_error_bad_value);                bfd_set_error (bfd_error_bad_value);
2904                return FALSE;                return FALSE;
2905              }              }
2906            else            else
2907              {              {
2908                /* This symbol requires a global offset table entry.  */                /* This symbol requires a global offset table entry.  */
2909                if (! score_elf_record_global_got_symbol (h, abfd, info, g))                if (! score_elf_record_global_got_symbol (h, abfd, info, g))
2910                  return FALSE;                  return FALSE;
2911    
2912                /* We need a stub, not a plt entry for the undefined function.  But we record                /* We need a stub, not a plt entry for the undefined function.  But we record
2913                   it as if it needs plt.  See _bfd_elf_adjust_dynamic_symbol.  */                   it as if it needs plt.  See _bfd_elf_adjust_dynamic_symbol.  */
2914                h->needs_plt = 1;                h->needs_plt = 1;
2915                h->type = STT_FUNC;                h->type = STT_FUNC;
2916              }              }
2917              break;
2918            case R_SCORE_GOT15:
2919              if (h && ! score_elf_record_global_got_symbol (h, abfd, info, g))
2920                return FALSE;
2921            break;            break;
         case R_SCORE_GOT15:  
           if (h && ! score_elf_record_global_got_symbol (h, abfd, info, g))  
             return FALSE;  
           break;  
2922          case R_SCORE_ABS32:          case R_SCORE_ABS32:
2923          case R_SCORE_REL32:          case R_SCORE_REL32:
2924            if ((info->shared || h != NULL) && (sec->flags & SEC_ALLOC) != 0)            if ((info->shared || h != NULL) && (sec->flags & SEC_ALLOC) != 0)
2925              {              {
2926                if (sreloc == NULL)                if (sreloc == NULL)
2927                  {                  {
2928                    sreloc = score_elf_rel_dyn_section (dynobj, TRUE);                    sreloc = score_elf_rel_dyn_section (dynobj, TRUE);
2929                    if (sreloc == NULL)                    if (sreloc == NULL)
2930                      return FALSE;                      return FALSE;
2931                  }                  }
2932  #define SCORE_READONLY_SECTION (SEC_ALLOC | SEC_LOAD | SEC_READONLY)  #define SCORE_READONLY_SECTION (SEC_ALLOC | SEC_LOAD | SEC_READONLY)
2933                if (info->shared)                if (info->shared)
2934                  {                  {
2935                    /* When creating a shared object, we must copy these reloc types into                    /* When creating a shared object, we must copy these reloc types into
2936                       the output file as R_SCORE_REL32 relocs.  We make room for this reloc                       the output file as R_SCORE_REL32 relocs.  We make room for this reloc
2937                       in the .rel.dyn reloc section.  */                       in the .rel.dyn reloc section.  */
2938                    score_elf_allocate_dynamic_relocations (dynobj, 1);                    score_elf_allocate_dynamic_relocations (dynobj, 1);
2939                    if ((sec->flags & SCORE_READONLY_SECTION)                    if ((sec->flags & SCORE_READONLY_SECTION)
2940                        == SCORE_READONLY_SECTION)                        == SCORE_READONLY_SECTION)
2941                      /* We tell the dynamic linker that there are                      /* We tell the dynamic linker that there are
2942                         relocations against the text segment.  */                         relocations against the text segment.  */
2943                      info->flags |= DF_TEXTREL;                      info->flags |= DF_TEXTREL;
2944                  }                  }
2945                else                else
2946                  {                  {
2947                    struct score_elf_link_hash_entry *hscore;                    struct score_elf_link_hash_entry *hscore;
2948    
2949                    /* We only need to copy this reloc if the symbol is                    /* We only need to copy this reloc if the symbol is
2950                       defined in a dynamic object.  */                       defined in a dynamic object.  */
2951                    hscore = (struct score_elf_link_hash_entry *)h;                    hscore = (struct score_elf_link_hash_entry *)h;
2952                    ++hscore->possibly_dynamic_relocs;                    ++hscore->possibly_dynamic_relocs;
2953                    if ((sec->flags & SCORE_READONLY_SECTION)                    if ((sec->flags & SCORE_READONLY_SECTION)
2954                        == SCORE_READONLY_SECTION)                        == SCORE_READONLY_SECTION)
2955                      /* We need it to tell the dynamic linker if there                      /* We need it to tell the dynamic linker if there
2956                         are relocations against the text segment.  */                         are relocations against the text segment.  */
2957                      hscore->readonly_reloc = TRUE;                      hscore->readonly_reloc = TRUE;
2958                  }                  }
2959    
2960                /* Even though we don't directly need a GOT entry for this symbol,                /* Even though we don't directly need a GOT entry for this symbol,
2961                   a symbol must have a dynamic symbol table index greater that                   a symbol must have a dynamic symbol table index greater that
2962                   DT_SCORE_GOTSYM if there are dynamic relocations against it.  */                   DT_SCORE_GOTSYM if there are dynamic relocations against it.  */
2963                if (h != NULL)                if (h != NULL)
2964                  {                  {
2965                    if (dynobj == NULL)                    if (dynobj == NULL)
2966                      elf_hash_table (info)->dynobj = dynobj = abfd;                      elf_hash_table (info)->dynobj = dynobj = abfd;
2967                    if (! score_elf_create_got_section (dynobj, info, TRUE))                    if (! score_elf_create_got_section (dynobj, info, TRUE))
2968                      return FALSE;                      return FALSE;
2969                    g = score_elf_got_info (dynobj, &sgot);                    g = score_elf_got_info (dynobj, &sgot);
2970                    if (! score_elf_record_global_got_symbol (h, abfd, info, g))                    if (! score_elf_record_global_got_symbol (h, abfd, info, g))
2971                      return FALSE;                      return FALSE;
2972                  }                  }
2973              }              }
2974            break;            break;
2975    
2976            /* This relocation describes the C++ object vtable hierarchy.            /* This relocation describes the C++ object vtable hierarchy.
2977               Reconstruct it for later use during GC.  */               Reconstruct it for later use during GC.  */
# Line 2678  _bfd_score_elf_check_relocs (bfd *abfd, Line 2983  _bfd_score_elf_check_relocs (bfd *abfd,
2983            /* This relocation describes which C++ vtable entries are actually            /* This relocation describes which C++ vtable entries are actually
2984               used.  Record for later use during GC.  */               used.  Record for later use during GC.  */
2985          case R_SCORE_GNU_VTENTRY:          case R_SCORE_GNU_VTENTRY:
2986            BFD_ASSERT (h != NULL);            if (!bfd_elf_gc_record_vtentry (abfd, sec, h, rel->r_offset))
           if (h != NULL  
               && !bfd_elf_gc_record_vtentry (abfd, sec, h, rel->r_offset))  
2987              return FALSE;              return FALSE;
2988            break;            break;
2989          default:          default:
# Line 2690  _bfd_score_elf_check_relocs (bfd *abfd, Line 2993  _bfd_score_elf_check_relocs (bfd *abfd,
2993        /* We must not create a stub for a symbol that has relocations        /* We must not create a stub for a symbol that has relocations
2994           related to taking the function's address.  */           related to taking the function's address.  */
2995        switch (r_type)        switch (r_type)
2996          {          {
2997          default:          default:
2998            if (h != NULL)            if (h != NULL)
2999              {              {
3000                struct score_elf_link_hash_entry *sh;                struct score_elf_link_hash_entry *sh;
3001    
3002                sh = (struct score_elf_link_hash_entry *) h;                sh = (struct score_elf_link_hash_entry *) h;
3003                sh->no_fn_stub = TRUE;                sh->no_fn_stub = TRUE;
3004              }              }
3005            break;            break;
3006          case R_SCORE_CALL15:          case R_SCORE_CALL15:
3007            break;            break;
3008          }          }
3009      }      }
3010    
3011    return TRUE;    return TRUE;
3012  }  }
3013    
3014  static bfd_boolean  static bfd_boolean
3015  _bfd_score_elf_add_symbol_hook (bfd *abfd,  s3_bfd_score_elf_add_symbol_hook (bfd *abfd,
3016                                  struct bfd_link_info *info ATTRIBUTE_UNUSED,                                    struct bfd_link_info *info ATTRIBUTE_UNUSED,
3017                                  Elf_Internal_Sym *sym,                                    Elf_Internal_Sym *sym,
3018                                  const char **namep ATTRIBUTE_UNUSED,                                    const char **namep ATTRIBUTE_UNUSED,
3019                                  flagword *flagsp ATTRIBUTE_UNUSED,                                    flagword *flagsp ATTRIBUTE_UNUSED,
3020                                  asection **secp,                                    asection **secp,
3021                                  bfd_vma *valp)                                    bfd_vma *valp)
3022  {  {
3023    switch (sym->st_shndx)    switch (sym->st_shndx)
3024      {      {
# Line 2734  _bfd_score_elf_add_symbol_hook (bfd *abf Line 3037  _bfd_score_elf_add_symbol_hook (bfd *abf
3037  }  }
3038    
3039  static void  static void
3040  _bfd_score_elf_symbol_processing (bfd *abfd, asymbol *asym)  s3_bfd_score_elf_symbol_processing (bfd *abfd, asymbol *asym)
3041  {  {
3042    elf_symbol_type *elfsym;    elf_symbol_type *elfsym;
3043    
# Line 2765  _bfd_score_elf_symbol_processing (bfd *a Line 3068  _bfd_score_elf_symbol_processing (bfd *a
3068      }      }
3069  }  }
3070    
3071  static bfd_boolean  static int
3072  _bfd_score_elf_link_output_symbol_hook (struct bfd_link_info *info ATTRIBUTE_UNUSED,  s3_bfd_score_elf_link_output_symbol_hook (struct bfd_link_info *info ATTRIBUTE_UNUSED,
3073       const char *name ATTRIBUTE_UNUSED,                                            const char *name ATTRIBUTE_UNUSED,
3074       Elf_Internal_Sym *sym,                                            Elf_Internal_Sym *sym,
3075       asection *input_sec,                                            asection *input_sec,
3076       struct elf_link_hash_entry *h ATTRIBUTE_UNUSED)                                            struct elf_link_hash_entry *h ATTRIBUTE_UNUSED)
3077  {  {
3078    /* If we see a common symbol, which implies a relocatable link, then    /* If we see a common symbol, which implies a relocatable link, then
3079       if a symbol was small common in an input file, mark it as small       if a symbol was small common in an input file, mark it as small
# Line 2778  _bfd_score_elf_link_output_symbol_hook ( Line 3081  _bfd_score_elf_link_output_symbol_hook (
3081    if (sym->st_shndx == SHN_COMMON && strcmp (input_sec->name, ".scommon") == 0)    if (sym->st_shndx == SHN_COMMON && strcmp (input_sec->name, ".scommon") == 0)
3082      sym->st_shndx = SHN_SCORE_SCOMMON;      sym->st_shndx = SHN_SCORE_SCOMMON;
3083    
3084    return TRUE;    return 1;
3085  }  }
3086    
3087  static bfd_boolean  static bfd_boolean
3088  _bfd_score_elf_section_from_bfd_section (bfd *abfd ATTRIBUTE_UNUSED,  s3_bfd_score_elf_section_from_bfd_section (bfd *abfd ATTRIBUTE_UNUSED,
3089                                           asection *sec,                                             asection *sec,
3090                                           int *retval)                                             int *retval)
3091  {  {
3092    if (strcmp (bfd_get_section_name (abfd, sec), ".scommon") == 0)    if (strcmp (bfd_get_section_name (abfd, sec), ".scommon") == 0)
3093      {      {
# Line 2799  _bfd_score_elf_section_from_bfd_section Line 3102  _bfd_score_elf_section_from_bfd_section
3102     regular object.  The current definition is in some section of the     regular object.  The current definition is in some section of the
3103     dynamic object, but we're not including those sections.  We have to     dynamic object, but we're not including those sections.  We have to
3104     change the definition to something the rest of the link can understand.  */     change the definition to something the rest of the link can understand.  */
   
3105  static bfd_boolean  static bfd_boolean
3106  _bfd_score_elf_adjust_dynamic_symbol (struct bfd_link_info *info,  s3_bfd_score_elf_adjust_dynamic_symbol (struct bfd_link_info *info,
3107                                        struct elf_link_hash_entry *h)                                          struct elf_link_hash_entry *h)
3108  {  {
3109    bfd *dynobj;    bfd *dynobj;
3110    struct score_elf_link_hash_entry *hscore;    struct score_elf_link_hash_entry *hscore;
# Line 2888  _bfd_score_elf_adjust_dynamic_symbol (st Line 3190  _bfd_score_elf_adjust_dynamic_symbol (st
3190    
3191  /* This function is called after all the input files have been read,  /* This function is called after all the input files have been read,
3192     and the input sections have been assigned to output sections.  */     and the input sections have been assigned to output sections.  */
   
3193  static bfd_boolean  static bfd_boolean
3194  _bfd_score_elf_always_size_sections (bfd *output_bfd,  s3_bfd_score_elf_always_size_sections (bfd *output_bfd,
3195                                       struct bfd_link_info *info)                                         struct bfd_link_info *info)
3196  {  {
3197    bfd *dynobj;    bfd *dynobj;
3198    asection *s;    asection *s;
# Line 2917  _bfd_score_elf_always_size_sections (bfd Line 3218  _bfd_score_elf_always_size_sections (bfd
3218        asection *subsection;        asection *subsection;
3219    
3220        for (subsection = sub->sections;        for (subsection = sub->sections;
3221             subsection;             subsection;
3222             subsection = subsection->next)             subsection = subsection->next)
3223          {          {
3224            if ((subsection->flags & SEC_ALLOC) == 0)            if ((subsection->flags & SEC_ALLOC) == 0)
3225              continue;              continue;
3226            loadable_size += ((subsection->size + 0xf)            loadable_size += ((subsection->size + 0xf)
3227                              &~ (bfd_size_type) 0xf);                              &~ (bfd_size_type) 0xf);
3228          }          }
3229      }      }
3230    
3231    /* There has to be a global GOT entry for every symbol with    /* There has to be a global GOT entry for every symbol with
# Line 2966  _bfd_score_elf_always_size_sections (bfd Line 3267  _bfd_score_elf_always_size_sections (bfd
3267  }  }
3268    
3269  /* Set the sizes of the dynamic sections.  */  /* Set the sizes of the dynamic sections.  */
   
3270  static bfd_boolean  static bfd_boolean
3271  _bfd_score_elf_size_dynamic_sections (bfd *output_bfd, struct bfd_link_info *info)  s3_bfd_score_elf_size_dynamic_sections (bfd *output_bfd, struct bfd_link_info *info)
3272  {  {
3273    bfd *dynobj;    bfd *dynobj;
3274    asection *s;    asection *s;
# Line 3045  _bfd_score_elf_size_dynamic_sections (bf Line 3345  _bfd_score_elf_size_dynamic_sections (bf
3345          }          }
3346        else if (CONST_STRNEQ (name, ".got"))        else if (CONST_STRNEQ (name, ".got"))
3347          {          {
3348            /* _bfd_score_elf_always_size_sections() has already done            /* s3_bfd_score_elf_always_size_sections() has already done
3349               most of the work, but some symbols may have been mapped               most of the work, but some symbols may have been mapped
3350               to versions that we must now resolve in the got_entries               to versions that we must now resolve in the got_entries
3351               hash tables.  */               hash tables.  */
3352          }          }
3353        else if (strcmp (name, SCORE_ELF_STUB_SECTION_NAME) == 0)        else if (strcmp (name, SCORE_ELF_STUB_SECTION_NAME) == 0)
3354          {          {
# Line 3074  _bfd_score_elf_size_dynamic_sections (bf Line 3374  _bfd_score_elf_size_dynamic_sections (bf
3374    if (elf_hash_table (info)->dynamic_sections_created)    if (elf_hash_table (info)->dynamic_sections_created)
3375      {      {
3376        /* Add some entries to the .dynamic section.  We fill in the        /* Add some entries to the .dynamic section.  We fill in the
3377           values later, in _bfd_score_elf_finish_dynamic_sections, but we           values later, in s3_bfd_score_elf_finish_dynamic_sections, but we
3378           must add the entries now so that we get the correct size for           must add the entries now so that we get the correct size for
3379           the .dynamic section.  The DT_DEBUG entry is filled in by the           the .dynamic section.  The DT_DEBUG entry is filled in by the
3380           dynamic linker and used by the debugger.  */           dynamic linker and used by the debugger.  */
3381    
3382        if (!SCORE_ELF_ADD_DYNAMIC_ENTRY (info, DT_DEBUG, 0))        if (!SCORE_ELF_ADD_DYNAMIC_ENTRY (info, DT_DEBUG, 0))
3383          return FALSE;          return FALSE;
3384    
3385        if (reltext)        if (reltext)
3386          info->flags |= DF_TEXTREL;          info->flags |= DF_TEXTREL;
3387    
3388        if ((info->flags & DF_TEXTREL) != 0)        if ((info->flags & DF_TEXTREL) != 0)
3389          {          {
3390            if (!SCORE_ELF_ADD_DYNAMIC_ENTRY (info, DT_TEXTREL, 0))            if (!SCORE_ELF_ADD_DYNAMIC_ENTRY (info, DT_TEXTREL, 0))
3391              return FALSE;              return FALSE;
3392          }          }
3393    
3394        if (! SCORE_ELF_ADD_DYNAMIC_ENTRY (info, DT_PLTGOT, 0))        if (! SCORE_ELF_ADD_DYNAMIC_ENTRY (info, DT_PLTGOT, 0))
3395          return FALSE;          return FALSE;
3396    
3397        if (score_elf_rel_dyn_section (dynobj, FALSE))        if (score_elf_rel_dyn_section (dynobj, FALSE))
3398          {          {
3399            if (!SCORE_ELF_ADD_DYNAMIC_ENTRY (info, DT_REL, 0))            if (!SCORE_ELF_ADD_DYNAMIC_ENTRY (info, DT_REL, 0))
3400              return FALSE;              return FALSE;
3401    
3402            if (!SCORE_ELF_ADD_DYNAMIC_ENTRY (info, DT_RELSZ, 0))            if (!SCORE_ELF_ADD_DYNAMIC_ENTRY (info, DT_RELSZ, 0))
3403              return FALSE;              return FALSE;
3404    
3405            if (!SCORE_ELF_ADD_DYNAMIC_ENTRY (info, DT_RELENT, 0))            if (!SCORE_ELF_ADD_DYNAMIC_ENTRY (info, DT_RELENT, 0))
3406              return FALSE;              return FALSE;
3407          }          }
3408    
3409        if (!SCORE_ELF_ADD_DYNAMIC_ENTRY (info, DT_SCORE_BASE_ADDRESS, 0))        if (!SCORE_ELF_ADD_DYNAMIC_ENTRY (info, DT_SCORE_BASE_ADDRESS, 0))
3410          return FALSE;          return FALSE;
# Line 3122  _bfd_score_elf_size_dynamic_sections (bf Line 3422  _bfd_score_elf_size_dynamic_sections (bf
3422          return FALSE;          return FALSE;
3423    
3424        if (!SCORE_ELF_ADD_DYNAMIC_ENTRY (info, DT_SCORE_HIPAGENO, 0))        if (!SCORE_ELF_ADD_DYNAMIC_ENTRY (info, DT_SCORE_HIPAGENO, 0))
3425          return FALSE;          return FALSE;
3426      }      }
3427    
3428    return TRUE;    return TRUE;
3429  }  }
3430    
3431  static bfd_boolean  static bfd_boolean
3432  _bfd_score_elf_create_dynamic_sections (bfd *abfd, struct bfd_link_info *info)  s3_bfd_score_elf_create_dynamic_sections (bfd *abfd, struct bfd_link_info *info)
3433  {  {
3434    struct elf_link_hash_entry *h;    struct elf_link_hash_entry *h;
3435    struct bfd_link_hash_entry *bh;    struct bfd_link_hash_entry *bh;
# Line 3173  _bfd_score_elf_create_dynamic_sections ( Line 3473  _bfd_score_elf_create_dynamic_sections (
3473        bh = NULL;        bh = NULL;
3474        if (!(_bfd_generic_link_add_one_symbol        if (!(_bfd_generic_link_add_one_symbol
3475              (info, abfd, name, BSF_GLOBAL, bfd_abs_section_ptr,              (info, abfd, name, BSF_GLOBAL, bfd_abs_section_ptr,
3476               (bfd_vma) 0, (const char *)NULL, FALSE, get_elf_backend_data (abfd)->collect, &bh)))               (bfd_vma) 0, NULL, FALSE, get_elf_backend_data (abfd)->collect, &bh)))
3477          return FALSE;          return FALSE;
3478    
3479        h = (struct elf_link_hash_entry *)bh;        h = (struct elf_link_hash_entry *)bh;
# Line 3191  _bfd_score_elf_create_dynamic_sections ( Line 3491  _bfd_score_elf_create_dynamic_sections (
3491    
3492  /* Finish up dynamic symbol handling.  We set the contents of various  /* Finish up dynamic symbol handling.  We set the contents of various
3493     dynamic sections here.  */     dynamic sections here.  */
   
3494  static bfd_boolean  static bfd_boolean
3495  _bfd_score_elf_finish_dynamic_symbol (bfd *output_bfd,  s3_bfd_score_elf_finish_dynamic_symbol (bfd *output_bfd,
3496                                        struct bfd_link_info *info,                                          struct bfd_link_info *info,
3497                                        struct elf_link_hash_entry *h,                                          struct elf_link_hash_entry *h,
3498                                        Elf_Internal_Sym *sym)                                          Elf_Internal_Sym *sym)
3499  {  {
3500    bfd *dynobj;    bfd *dynobj;
3501    asection *sgot;    asection *sgot;
# Line 3218  _bfd_score_elf_finish_dynamic_symbol (bf Line 3517  _bfd_score_elf_finish_dynamic_symbol (bf
3517    
3518        /* FIXME: Can h->dynindex be more than 64K?  */        /* FIXME: Can h->dynindex be more than 64K?  */
3519        if (h->dynindx & 0xffff0000)        if (h->dynindx & 0xffff0000)
3520          return FALSE;          return FALSE;
3521    
3522        /* Fill the stub.  */        /* Fill the stub.  */
3523        bfd_put_32 (output_bfd, STUB_LW, stub);        score_bfd_put_32 (output_bfd, STUB_LW, stub);
3524        bfd_put_32 (output_bfd, STUB_MOVE, stub + 4);        score_bfd_put_32 (output_bfd, STUB_MOVE, stub + 4);
3525        bfd_put_32 (output_bfd, STUB_LI16 | (h->dynindx << 1), stub + 8);        score_bfd_put_32 (output_bfd, STUB_LI16 | (h->dynindx << 1), stub + 8);
3526        bfd_put_32 (output_bfd, STUB_BRL, stub + 12);        score_bfd_put_32 (output_bfd, STUB_BRL, stub + 12);
3527    
3528        BFD_ASSERT (h->plt.offset <= s->size);        BFD_ASSERT (h->plt.offset <= s->size);
3529        memcpy (s->contents + h->plt.offset, stub, SCORE_FUNCTION_STUB_SIZE);        memcpy (s->contents + h->plt.offset, stub, SCORE_FUNCTION_STUB_SIZE);
3530    
3531        /* Mark the symbol as undefined.  plt.offset != -1 occurs        /* Mark the symbol as undefined.  plt.offset != -1 occurs
3532           only for the referenced symbol.  */           only for the referenced symbol.  */
3533        sym->st_shndx = SHN_UNDEF;        sym->st_shndx = SHN_UNDEF;
3534    
3535        /* The run-time linker uses the st_value field of the symbol        /* The run-time linker uses the st_value field of the symbol
3536            to reset the global offset table entry for this external            to reset the global offset table entry for this external
3537            to its stub address when unlinking a shared object.  */            to its stub address when unlinking a shared object.  */
3538        sym->st_value = (s->output_section->vma + s->output_offset + h->plt.offset);        sym->st_value = (s->output_section->vma + s->output_offset + h->plt.offset);
3539      }      }
3540    
# Line 3256  _bfd_score_elf_finish_dynamic_symbol (bf Line 3555  _bfd_score_elf_finish_dynamic_symbol (bf
3555    
3556        value = sym->st_value;        value = sym->st_value;
3557        offset = score_elf_global_got_index (dynobj, h);        offset = score_elf_global_got_index (dynobj, h);
3558        bfd_put_32 (output_bfd, value, sgot->contents + offset);        score_bfd_put_32 (output_bfd, value, sgot->contents + offset);
3559      }      }
3560    
3561    /* Mark _DYNAMIC and _GLOBAL_OFFSET_TABLE_ as absolute.  */    /* Mark _DYNAMIC and _GLOBAL_OFFSET_TABLE_ as absolute.  */
# Line 3280  _bfd_score_elf_finish_dynamic_symbol (bf Line 3579  _bfd_score_elf_finish_dynamic_symbol (bf
3579  }  }
3580    
3581  /* Finish up the dynamic sections.  */  /* Finish up the dynamic sections.  */
   
3582  static bfd_boolean  static bfd_boolean
3583  _bfd_score_elf_finish_dynamic_sections (bfd *output_bfd,  s3_bfd_score_elf_finish_dynamic_sections (bfd *output_bfd,
3584                                          struct bfd_link_info *info)                                            struct bfd_link_info *info)
3585  {  {
3586    bfd *dynobj;    bfd *dynobj;
3587    asection *sdyn;    asection *sdyn;
# Line 3313  _bfd_score_elf_finish_dynamic_sections ( Line 3611  _bfd_score_elf_finish_dynamic_sections (
3611        BFD_ASSERT (g != NULL);        BFD_ASSERT (g != NULL);
3612    
3613        for (b = sdyn->contents;        for (b = sdyn->contents;
3614             b < sdyn->contents + sdyn->size;             b < sdyn->contents + sdyn->size;
3615             b += SCORE_ELF_DYN_SIZE (dynobj))             b += SCORE_ELF_DYN_SIZE (dynobj))
3616          {          {
3617            Elf_Internal_Dyn dyn;            Elf_Internal_Dyn dyn;
3618            const char *name;            const char *name;
3619            size_t elemsize;            size_t elemsize;
3620            bfd_boolean swap_out_p;            bfd_boolean swap_out_p;
3621    
3622            /* Read in the current dynamic entry.  */            /* Read in the current dynamic entry.  */
3623            (*get_elf_backend_data (dynobj)->s->swap_dyn_in) (dynobj, b, &dyn);            (*get_elf_backend_data (dynobj)->s->swap_dyn_in) (dynobj, b, &dyn);
3624    
3625            /* Assume that we're going to modify it and write it out.  */            /* Assume that we're going to modify it and write it out.  */
3626            swap_out_p = TRUE;            swap_out_p = TRUE;
3627    
3628            switch (dyn.d_tag)            switch (dyn.d_tag)
3629              {              {
3630              case DT_RELENT:              case DT_RELENT:
3631                s = score_elf_rel_dyn_section (dynobj, FALSE);                s = score_elf_rel_dyn_section (dynobj, FALSE);
3632                BFD_ASSERT (s != NULL);                BFD_ASSERT (s != NULL);
3633                dyn.d_un.d_val = SCORE_ELF_REL_SIZE (dynobj);                dyn.d_un.d_val = SCORE_ELF_REL_SIZE (dynobj);
3634                break;                break;
3635    
3636              case DT_STRSZ:              case DT_STRSZ:
3637                /* Rewrite DT_STRSZ.  */                /* Rewrite DT_STRSZ.  */
3638                dyn.d_un.d_val = _bfd_elf_strtab_size (elf_hash_table (info)->dynstr);                dyn.d_un.d_val = _bfd_elf_strtab_size (elf_hash_table (info)->dynstr);
3639                      break;                      break;
3640    
3641              case DT_PLTGOT:              case DT_PLTGOT:
3642                name = ".got";                name = ".got";
3643                s = bfd_get_section_by_name (output_bfd, name);                s = bfd_get_section_by_name (output_bfd, name);
3644                BFD_ASSERT (s != NULL);                BFD_ASSERT (s != NULL);
3645                dyn.d_un.d_ptr = s->vma;                dyn.d_un.d_ptr = s->vma;
3646                break;                break;
3647    
3648              case DT_SCORE_BASE_ADDRESS:              case DT_SCORE_BASE_ADDRESS:
3649                s = output_bfd->sections;                s = output_bfd->sections;
3650                BFD_ASSERT (s != NULL);                BFD_ASSERT (s != NULL);
3651                dyn.d_un.d_ptr = s->vma & ~(bfd_vma) 0xffff;                dyn.d_un.d_ptr = s->vma & ~(bfd_vma) 0xffff;
3652                break;                break;
3653    
3654              case DT_SCORE_LOCAL_GOTNO:              case DT_SCORE_LOCAL_GOTNO:
3655                dyn.d_un.d_val = g->local_gotno;                dyn.d_un.d_val = g->local_gotno;
3656                break;                break;
3657    
3658              case DT_SCORE_UNREFEXTNO:              case DT_SCORE_UNREFEXTNO:
3659                /* The index into the dynamic symbol table which is the                /* The index into the dynamic symbol table which is the
3660                   entry of the first external symbol that is not                   entry of the first external symbol that is not
3661                   referenced within the same object.  */                   referenced within the same object.  */
3662                dyn.d_un.d_val = bfd_count_sections (output_bfd) + 1;                dyn.d_un.d_val = bfd_count_sections (output_bfd) + 1;
3663                break;                break;
3664    
3665              case DT_SCORE_GOTSYM:              case DT_SCORE_GOTSYM:
3666                if (g->global_gotsym)                if (g->global_gotsym)
3667                  {                  {
3668                    dyn.d_un.d_val = g->global_gotsym->dynindx;                    dyn.d_un.d_val = g->global_gotsym->dynindx;
3669                    break;                    break;
3670                  }                  }
3671                /* In case if we don't have global got symbols we default                /* In case if we don't have global got symbols we default
3672                    to setting DT_SCORE_GOTSYM to the same value as                    to setting DT_SCORE_GOTSYM to the same value as
3673                    DT_SCORE_SYMTABNO, so we just fall through.  */                    DT_SCORE_SYMTABNO, so we just fall through.  */
3674    
3675              case DT_SCORE_SYMTABNO:              case DT_SCORE_SYMTABNO:
3676                name = ".dynsym";                name = ".dynsym";
3677                elemsize = SCORE_ELF_SYM_SIZE (output_bfd);                elemsize = SCORE_ELF_SYM_SIZE (output_bfd);
3678                s = bfd_get_section_by_name (output_bfd, name);                s = bfd_get_section_by_name (output_bfd, name);
3679                BFD_ASSERT (s != NULL);                BFD_ASSERT (s != NULL);
3680    
3681                dyn.d_un.d_val = s->size / elemsize;                dyn.d_un.d_val = s->size / elemsize;
3682                break;                break;
3683    
3684              case DT_SCORE_HIPAGENO:              case DT_SCORE_HIPAGENO:
3685                dyn.d_un.d_val = g->local_gotno - SCORE_RESERVED_GOTNO;                dyn.d_un.d_val = g->local_gotno - SCORE_RESERVED_GOTNO;
3686                break;                break;
3687    
3688              default:              default:
3689                swap_out_p = FALSE;                swap_out_p = FALSE;
3690                break;                break;
3691              }              }
3692    
3693            if (swap_out_p)            if (swap_out_p)
3694              (*get_elf_backend_data (dynobj)->s->swap_dyn_out) (dynobj, &dyn, b);              (*get_elf_backend_data (dynobj)->s->swap_dyn_out) (dynobj, &dyn, b);
3695          }          }
3696      }      }
3697    
3698    /* The first entry of the global offset table will be filled at    /* The first entry of the global offset table will be filled at
# Line 3402  _bfd_score_elf_finish_dynamic_sections ( Line 3700  _bfd_score_elf_finish_dynamic_sections (
3700       This isn't the case of IRIX rld.  */       This isn't the case of IRIX rld.  */
3701    if (sgot != NULL && sgot->size > 0)    if (sgot != NULL && sgot->size > 0)
3702      {      {
3703        bfd_put_32 (output_bfd, 0, sgot->contents);        score_bfd_put_32 (output_bfd, 0, sgot->contents);
3704        bfd_put_32 (output_bfd, 0x80000000, sgot->contents + SCORE_ELF_GOT_SIZE (output_bfd));        score_bfd_put_32 (output_bfd, 0x80000000, sgot->contents + SCORE_ELF_GOT_SIZE (output_bfd));
3705      }      }
3706    
3707    if (sgot != NULL)    if (sgot != NULL)
# Line 3418  _bfd_score_elf_finish_dynamic_sections ( Line 3716  _bfd_score_elf_finish_dynamic_sections (
3716      {      {
3717        reldyn_sorting_bfd = output_bfd;        reldyn_sorting_bfd = output_bfd;
3718        qsort ((Elf32_External_Rel *) s->contents + 1, s->reloc_count - 1,        qsort ((Elf32_External_Rel *) s->contents + 1, s->reloc_count - 1,
3719               sizeof (Elf32_External_Rel), score_elf_sort_dynamic_relocs);               sizeof (Elf32_External_Rel), score_elf_sort_dynamic_relocs);
3720      }      }
3721    
3722    return TRUE;    return TRUE;
# Line 3426  _bfd_score_elf_finish_dynamic_sections ( Line 3724  _bfd_score_elf_finish_dynamic_sections (
3724    
3725  /* This function set up the ELF section header for a BFD section in preparation for writing  /* This function set up the ELF section header for a BFD section in preparation for writing
3726     it out.  This is where the flags and type fields are set for unusual sections.  */     it out.  This is where the flags and type fields are set for unusual sections.  */
   
3727  static bfd_boolean  static bfd_boolean
3728  _bfd_score_elf_fake_sections (bfd *abfd ATTRIBUTE_UNUSED,  s3_bfd_score_elf_fake_sections (bfd *abfd ATTRIBUTE_UNUSED,
3729                                Elf_Internal_Shdr *hdr,                                  Elf_Internal_Shdr *hdr,
3730                                asection *sec)                                  asection *sec)
3731  {  {
3732    const char *name;    const char *name;
3733    
# Line 3452  _bfd_score_elf_fake_sections (bfd *abfd Line 3749  _bfd_score_elf_fake_sections (bfd *abfd
3749     warning message will be issued.  backend_fake_section is called before     warning message will be issued.  backend_fake_section is called before
3750     assign_file_positions_except_relocs(); backend_section_processing after it.  so, we     assign_file_positions_except_relocs(); backend_section_processing after it.  so, we
3751     modify section flag there, but not backend_fake_section.  */     modify section flag there, but not backend_fake_section.  */
   
3752  static bfd_boolean  static bfd_boolean
3753  _bfd_score_elf_section_processing (bfd *abfd ATTRIBUTE_UNUSED, Elf_Internal_Shdr *hdr)  s3_bfd_score_elf_section_processing (bfd *abfd ATTRIBUTE_UNUSED, Elf_Internal_Shdr *hdr)
3754  {  {
3755    if (hdr->bfd_section != NULL)    if (hdr->bfd_section != NULL)
3756      {      {
3757        const char *name = bfd_get_section_name (abfd, hdr->bfd_section);        const char *name = bfd_get_section_name (abfd, hdr->bfd_section);
3758    
3759        if (strcmp (name, ".sdata") == 0)        if (strcmp (name, ".sdata") == 0)
3760          {          {
3761            hdr->sh_flags |= SHF_ALLOC | SHF_WRITE | SHF_SCORE_GPREL;            hdr->sh_flags |= SHF_ALLOC | SHF_WRITE | SHF_SCORE_GPREL;
3762            hdr->sh_type = SHT_PROGBITS;            hdr->sh_type = SHT_PROGBITS;
3763          }          }
3764        else if (strcmp (name, ".sbss") == 0)        else if (strcmp (name, ".sbss") == 0)
3765          {          {
3766            hdr->sh_flags |= SHF_ALLOC | SHF_WRITE | SHF_SCORE_GPREL;            hdr->sh_flags |= SHF_ALLOC | SHF_WRITE | SHF_SCORE_GPREL;
3767            hdr->sh_type = SHT_NOBITS;            hdr->sh_type = SHT_NOBITS;
3768          }          }
3769        else if (strcmp (name, ".srdata") == 0)        else if (strcmp (name, ".srdata") == 0)
3770          {          {
3771            hdr->sh_flags |= SHF_ALLOC | SHF_SCORE_GPREL;            hdr->sh_flags |= SHF_ALLOC | SHF_SCORE_GPREL;
3772            hdr->sh_type = SHT_PROGBITS;            hdr->sh_type = SHT_PROGBITS;
3773          }          }
3774      }      }
3775    
3776    return TRUE;    return TRUE;
3777  }  }
3778    
3779  static bfd_boolean  static bfd_boolean
3780  _bfd_score_elf_write_section (bfd *output_bfd,  s3_bfd_score_elf_write_section (bfd *output_bfd, asection *sec, bfd_byte *contents)
                               struct bfd_link_info *link_info ATTRIBUTE_UNUSED,  
                               asection *sec, bfd_byte *contents)  
3781  {  {
3782    bfd_byte *to, *from, *end;    bfd_byte *to, *from, *end;
3783    int i;    int i;
# Line 3514  _bfd_score_elf_write_section (bfd *outpu Line 3808  _bfd_score_elf_write_section (bfd *outpu
3808    
3809  /* Copy data from a SCORE ELF indirect symbol to its direct symbol, hiding the old  /* Copy data from a SCORE ELF indirect symbol to its direct symbol, hiding the old
3810     indirect symbol.  Process additional relocation information.  */     indirect symbol.  Process additional relocation information.  */
   
3811  static void  static void
3812  _bfd_score_elf_copy_indirect_symbol (struct bfd_link_info *info,  s3_bfd_score_elf_copy_indirect_symbol (struct bfd_link_info *info,
3813                                       struct elf_link_hash_entry *dir,                                         struct elf_link_hash_entry *dir,
3814                                       struct elf_link_hash_entry *ind)                                         struct elf_link_hash_entry *ind)
3815  {  {
3816    struct score_elf_link_hash_entry *dirscore, *indscore;    struct score_elf_link_hash_entry *dirscore, *indscore;
3817    
# Line 3539  _bfd_score_elf_copy_indirect_symbol (str Line 3832  _bfd_score_elf_copy_indirect_symbol (str
3832  }  }
3833    
3834  /* Remove information about discarded functions from other sections which mention them.  */  /* Remove information about discarded functions from other sections which mention them.  */
   
3835  static bfd_boolean  static bfd_boolean
3836  _bfd_score_elf_discard_info (bfd *abfd, struct elf_reloc_cookie *cookie,  s3_bfd_score_elf_discard_info (bfd *abfd, struct elf_reloc_cookie *cookie,
3837                           struct bfd_link_info *info)                                 struct bfd_link_info *info)
3838  {  {
3839    asection *o;    asection *o;
3840    bfd_boolean ret = FALSE;    bfd_boolean ret = FALSE;
# Line 3593  _bfd_score_elf_discard_info (bfd *abfd, Line 3885  _bfd_score_elf_discard_info (bfd *abfd,
3885  }  }
3886    
3887  /* Signal that discard_info() has removed the discarded relocations for this section.  */  /* Signal that discard_info() has removed the discarded relocations for this section.  */
   
3888  static bfd_boolean  static bfd_boolean
3889  _bfd_score_elf_ignore_discarded_relocs (asection *sec)  s3_bfd_score_elf_ignore_discarded_relocs (asection *sec)
3890  {  {
3891    if (strcmp (sec->name, ".pdr") == 0)    if (strcmp (sec->name, ".pdr") == 0)
3892      return TRUE;      return TRUE;
# Line 3604  _bfd_score_elf_ignore_discarded_relocs ( Line 3895  _bfd_score_elf_ignore_discarded_relocs (
3895    
3896  /* Return the section that should be marked against GC for a given  /* Return the section that should be marked against GC for a given
3897     relocation.  */     relocation.  */
   
3898  static asection *  static asection *
3899  _bfd_score_elf_gc_mark_hook (asection *sec,  s3_bfd_score_elf_gc_mark_hook (asection *sec,
3900                               struct bfd_link_info *info,                                 struct bfd_link_info *info,
3901                               Elf_Internal_Rela *rel,                                 Elf_Internal_Rela *rel,
3902                               struct elf_link_hash_entry *h,                                 struct elf_link_hash_entry *h,
3903                               Elf_Internal_Sym *sym)                                 Elf_Internal_Sym *sym)
3904  {  {
3905    if (h != NULL)    if (h != NULL)
3906      switch (ELF32_R_TYPE (rel->r_info))      switch (ELF32_R_TYPE (rel->r_info))
3907        {        {
3908        case R_SCORE_GNU_VTINHERIT:        case R_SCORE_GNU_VTINHERIT:
3909        case R_SCORE_GNU_VTENTRY:        case R_SCORE_GNU_VTENTRY:
3910          return NULL;          return NULL;
3911        }        }
3912    
3913    return _bfd_elf_gc_mark_hook (sec, info, rel, h, sym);    return _bfd_elf_gc_mark_hook (sec, info, rel, h, sym);
# Line 3626  _bfd_score_elf_gc_mark_hook (asection *s Line 3916  _bfd_score_elf_gc_mark_hook (asection *s
3916  /* Support for core dump NOTE sections.  */  /* Support for core dump NOTE sections.  */
3917    
3918  static bfd_boolean  static bfd_boolean
3919  _bfd_score_elf_grok_prstatus (bfd *abfd, Elf_Internal_Note *note)  s3_bfd_score_elf_grok_prstatus (bfd *abfd, Elf_Internal_Note *note)
3920  {  {
3921    int offset;    int offset;
3922    unsigned int raw_size;    unsigned int raw_size;
# Line 3638  _bfd_score_elf_grok_prstatus (bfd *abfd, Line 3928  _bfd_score_elf_grok_prstatus (bfd *abfd,
3928    
3929      case 148:                  /* Linux/Score 32-bit.  */      case 148:                  /* Linux/Score 32-bit.  */
3930        /* pr_cursig */        /* pr_cursig */
3931        elf_tdata (abfd)->core_signal = bfd_get_16 (abfd, note->descdata + 12);        elf_tdata (abfd)->core_signal = score_bfd_get_16 (abfd, note->descdata + 12);
3932    
3933        /* pr_pid */        /* pr_pid */
3934        elf_tdata (abfd)->core_pid = bfd_get_32 (abfd, note->descdata + 24);        elf_tdata (abfd)->core_pid = score_bfd_get_32 (abfd, note->descdata + 24);
3935    
3936        /* pr_reg */        /* pr_reg */
3937        offset = 72;        offset = 72;
# Line 3655  _bfd_score_elf_grok_prstatus (bfd *abfd, Line 3945  _bfd_score_elf_grok_prstatus (bfd *abfd,
3945  }  }
3946    
3947  static bfd_boolean  static bfd_boolean
3948  _bfd_score_elf_grok_psinfo (bfd *abfd, Elf_Internal_Note *note)  s3_bfd_score_elf_grok_psinfo (bfd *abfd, Elf_Internal_Note *note)
3949  {  {
3950    switch (note->descsz)    switch (note->descsz)
3951      {      {
# Line 3684  _bfd_score_elf_grok_psinfo (bfd *abfd, E Line 3974  _bfd_score_elf_grok_psinfo (bfd *abfd, E
3974    
3975    
3976  /* Score BFD functions.  */  /* Score BFD functions.  */
   
3977  static reloc_howto_type *  static reloc_howto_type *
3978  elf32_score_reloc_type_lookup (bfd *abfd ATTRIBUTE_UNUSED, bfd_reloc_code_real_type code)  s3_elf32_score_reloc_type_lookup (bfd *abfd ATTRIBUTE_UNUSED, bfd_reloc_code_real_type code)
3979  {  {
3980    unsigned int i;    unsigned int i;
3981    
3982    for (i = 0; i < NUM_ELEM (elf32_score_reloc_map); i++)    for (i = 0; i < ARRAY_SIZE (elf32_score_reloc_map); i++)
3983      if (elf32_score_reloc_map[i].bfd_reloc_val == code)      if (elf32_score_reloc_map[i].bfd_reloc_val == code)
3984        return &elf32_score_howto_table[elf32_score_reloc_map[i].elf_reloc_val];        return &elf32_score_howto_table[elf32_score_reloc_map[i].elf_reloc_val];
3985    
# Line 3699  elf32_score_reloc_type_lookup (bfd *abfd Line 3988  elf32_score_reloc_type_lookup (bfd *abfd
3988    
3989  static reloc_howto_type *  static reloc_howto_type *
3990  elf32_score_reloc_name_lookup (bfd *abfd ATTRIBUTE_UNUSED,  elf32_score_reloc_name_lookup (bfd *abfd ATTRIBUTE_UNUSED,
3991                                 const char *r_name)                                 const char *r_name)
3992  {  {
3993    unsigned int i;    unsigned int i;
3994    
3995    for (i = 0;    for (i = 0;
3996         i < (sizeof (elf32_score_howto_table)         i < (sizeof (elf32_score_howto_table)
3997              / sizeof (elf32_score_howto_table[0]));              / sizeof (elf32_score_howto_table[0]));
3998         i++)         i++)
3999      if (elf32_score_howto_table[i].name != NULL      if (elf32_score_howto_table[i].name != NULL
4000          && strcasecmp (elf32_score_howto_table[i].name, r_name) == 0)          && strcasecmp (elf32_score_howto_table[i].name, r_name) == 0)
4001        return &elf32_score_howto_table[i];        return &elf32_score_howto_table[i];
4002    
4003    return NULL;    return NULL;
# Line 3717  elf32_score_reloc_name_lookup (bfd *abfd Line 4006  elf32_score_reloc_name_lookup (bfd *abfd
4006  /* Create a score elf linker hash table.  */  /* Create a score elf linker hash table.  */
4007    
4008  static struct bfd_link_hash_table *  static struct bfd_link_hash_table *
4009  elf32_score_link_hash_table_create (bfd *abfd)  s3_elf32_score_link_hash_table_create (bfd *abfd)
4010  {  {
4011    struct score_elf_link_hash_table *ret;    struct score_elf_link_hash_table *ret;
4012    bfd_size_type amt = sizeof (struct score_elf_link_hash_table);    bfd_size_type amt = sizeof (struct score_elf_link_hash_table);
# Line 3727  elf32_score_link_hash_table_create (bfd Line 4016  elf32_score_link_hash_table_create (bfd
4016      return NULL;      return NULL;
4017    
4018    if (!_bfd_elf_link_hash_table_init (&ret->root, abfd, score_elf_link_hash_newfunc,    if (!_bfd_elf_link_hash_table_init (&ret->root, abfd, score_elf_link_hash_newfunc,
4019                                        sizeof (struct score_elf_link_hash_entry)))                                        sizeof (struct score_elf_link_hash_entry)))
4020      {      {
4021        free (ret);        free (ret);
4022        return NULL;        return NULL;
# Line 3737  elf32_score_link_hash_table_create (bfd Line 4026  elf32_score_link_hash_table_create (bfd
4026  }  }
4027    
4028  static bfd_boolean  static bfd_boolean
4029  elf32_score_print_private_bfd_data (bfd *abfd, void * ptr)  s3_elf32_score_print_private_bfd_data (bfd *abfd, void * ptr)
4030  {  {
4031    FILE *file = (FILE *) ptr;    FILE *file = (FILE *) ptr;
4032    
# Line 3762  elf32_score_print_private_bfd_data (bfd Line 4051  elf32_score_print_private_bfd_data (bfd
4051  }  }
4052    
4053  static bfd_boolean  static bfd_boolean
4054  elf32_score_merge_private_bfd_data (bfd *ibfd, bfd *obfd)  s3_elf32_score_merge_private_bfd_data (bfd *ibfd, bfd *obfd)
4055  {  {
4056    flagword in_flags;    flagword in_flags;
4057    flagword out_flags;    flagword out_flags;
# Line 3786  elf32_score_merge_private_bfd_data (bfd Line 4075  elf32_score_merge_private_bfd_data (bfd
4075        elf_elfheader (obfd)->e_flags = in_flags;        elf_elfheader (obfd)->e_flags = in_flags;
4076    
4077        if (bfd_get_arch (obfd) == bfd_get_arch (ibfd)        if (bfd_get_arch (obfd) == bfd_get_arch (ibfd)
4078            && bfd_get_arch_info (obfd)->the_default)            && bfd_get_arch_info (obfd)->the_default)
4079          {          {
4080            return bfd_set_arch_mach (obfd, bfd_get_arch (ibfd), bfd_get_mach (ibfd));            return bfd_set_arch_mach (obfd, bfd_get_arch (ibfd), bfd_get_mach (ibfd));
4081          }          }
4082    
4083        return TRUE;        return TRUE;
4084      }      }
# Line 3805  elf32_score_merge_private_bfd_data (bfd Line 4094  elf32_score_merge_private_bfd_data (bfd
4094  }  }
4095    
4096  static bfd_boolean  static bfd_boolean
4097  elf32_score_new_section_hook (bfd *abfd, asection *sec)  s3_elf32_score_new_section_hook (bfd *abfd, asection *sec)
4098  {  {
4099    struct _score_elf_section_data *sdata;    struct _score_elf_section_data *sdata;
4100    bfd_size_type amt = sizeof (*sdata);    bfd_size_type amt = sizeof (*sdata);
# Line 3818  elf32_score_new_section_hook (bfd *abfd, Line 4107  elf32_score_new_section_hook (bfd *abfd,
4107    return _bfd_elf_new_section_hook (abfd, sec);    return _bfd_elf_new_section_hook (abfd, sec);
4108  }  }
4109    
4110    /*****************************************************************************/
4111    
4112    /* s3_s7: backend hooks.  */
4113    static void
4114    _bfd_score_info_to_howto (bfd *abfd ATTRIBUTE_UNUSED,
4115                              arelent *bfd_reloc,
4116                              Elf_Internal_Rela *elf_reloc)
4117    {
4118      if (bfd_get_mach (abfd) == bfd_mach_score3)
4119        return s3_bfd_score_info_to_howto (abfd, bfd_reloc, elf_reloc);
4120      else
4121        return s7_bfd_score_info_to_howto (abfd, bfd_reloc, elf_reloc);
4122    }
4123    
4124    static bfd_boolean
4125    _bfd_score_elf_relocate_section (bfd *output_bfd,
4126                                     struct bfd_link_info *info,
4127                                     bfd *input_bfd,
4128                                     asection *input_section,
4129                                     bfd_byte *contents,
4130                                     Elf_Internal_Rela *relocs,
4131                                     Elf_Internal_Sym *local_syms,
4132                                     asection **local_sections)
4133    {
4134      if (bfd_get_mach (output_bfd) == bfd_mach_score3)
4135        return s3_bfd_score_elf_relocate_section (output_bfd,
4136                 info, input_bfd, input_section, contents, relocs,
4137                 local_syms, local_sections);
4138      else
4139        return s7_bfd_score_elf_relocate_section (output_bfd,
4140                 info, input_bfd, input_section, contents, relocs,
4141                 local_syms, local_sections);
4142    }
4143    
4144    static bfd_boolean
4145    _bfd_score_elf_check_relocs (bfd *abfd,
4146                                 struct bfd_link_info *info,
4147                                 asection *sec,
4148                                 const Elf_Internal_Rela *relocs)
4149    {
4150      if (bfd_get_mach (abfd) == bfd_mach_score3)
4151        return s3_bfd_score_elf_check_relocs (abfd, info, sec, relocs);
4152      else
4153        return s7_bfd_score_elf_check_relocs (abfd, info, sec, relocs);
4154    }
4155    
4156    static bfd_boolean
4157    _bfd_score_elf_add_symbol_hook (bfd *abfd,
4158                                    struct bfd_link_info *info ATTRIBUTE_UNUSED,
4159                                    Elf_Internal_Sym *sym,
4160                                    const char **namep ATTRIBUTE_UNUSED,
4161                                    flagword *flagsp ATTRIBUTE_UNUSED,
4162                                    asection **secp,
4163                                    bfd_vma *valp)
4164    {
4165      if (bfd_get_mach (abfd) == bfd_mach_score3)
4166        return s3_bfd_score_elf_add_symbol_hook (abfd, info, sym, namep, flagsp,
4167                                                 secp, valp);
4168      else
4169        return s7_bfd_score_elf_add_symbol_hook (abfd, info, sym, namep, flagsp,
4170                                                 secp, valp);
4171    }
4172    
4173    static void
4174    _bfd_score_elf_symbol_processing (bfd *abfd, asymbol *asym)
4175    {
4176      if (bfd_get_mach (abfd) == bfd_mach_score3)
4177        return s3_bfd_score_elf_symbol_processing (abfd, asym);
4178      else
4179        return s7_bfd_score_elf_symbol_processing (abfd, asym);
4180    }
4181    
4182    static int
4183    _bfd_score_elf_link_output_symbol_hook (struct bfd_link_info *info ATTRIBUTE_UNUSED,
4184         const char *name ATTRIBUTE_UNUSED,
4185         Elf_Internal_Sym *sym,
4186         asection *input_sec,
4187         struct elf_link_hash_entry *h ATTRIBUTE_UNUSED)
4188    {
4189      /* If link a empty .o, then this filed is NULL.  */
4190      if (info->input_bfds == NULL)
4191        {
4192          /* If we see a common symbol, which implies a relocatable link, then
4193             if a symbol was small common in an input file, mark it as small
4194             common in the output file.  */
4195          if (sym->st_shndx == SHN_COMMON && strcmp (input_sec->name, ".scommon") == 0)
4196            sym->st_shndx = SHN_SCORE_SCOMMON;
4197          return 1;
4198        }
4199    
4200      if (bfd_get_mach (info->input_bfds) == bfd_mach_score3)
4201        return s3_bfd_score_elf_link_output_symbol_hook (info, name, sym, input_sec, h);
4202      else
4203        return s7_bfd_score_elf_link_output_symbol_hook (info, name, sym, input_sec, h);
4204    }
4205    
4206    static bfd_boolean
4207    _bfd_score_elf_section_from_bfd_section (bfd *abfd ATTRIBUTE_UNUSED,
4208                                             asection *sec,
4209                                             int *retval)
4210    {
4211      if (bfd_get_mach (abfd) == bfd_mach_score3)
4212        return s3_bfd_score_elf_section_from_bfd_section (abfd, sec, retval);
4213      else
4214        return s7_bfd_score_elf_section_from_bfd_section (abfd, sec, retval);
4215    }
4216    
4217    static bfd_boolean
4218    _bfd_score_elf_adjust_dynamic_symbol (struct bfd_link_info *info,
4219                                          struct elf_link_hash_entry *h)
4220    {
4221      if (bfd_get_mach (info->input_bfds) == bfd_mach_score3)
4222        return s3_bfd_score_elf_adjust_dynamic_symbol (info, h);
4223      else
4224        return s7_bfd_score_elf_adjust_dynamic_symbol (info, h);
4225    }
4226    
4227    static bfd_boolean
4228    _bfd_score_elf_always_size_sections (bfd *output_bfd,
4229                                         struct bfd_link_info *info)
4230    {
4231      if (bfd_get_mach (output_bfd) == bfd_mach_score3)
4232        return s3_bfd_score_elf_always_size_sections (output_bfd, info);
4233      else
4234        return s7_bfd_score_elf_always_size_sections (output_bfd, info);
4235    }
4236    
4237    static bfd_boolean
4238    _bfd_score_elf_size_dynamic_sections (bfd *output_bfd, struct bfd_link_info *info)
4239    {
4240      if (bfd_get_mach (output_bfd) == bfd_mach_score3)
4241        return s3_bfd_score_elf_size_dynamic_sections (output_bfd, info);
4242      else
4243        return s7_bfd_score_elf_size_dynamic_sections (output_bfd, info);
4244    }
4245    
4246    static bfd_boolean
4247    _bfd_score_elf_create_dynamic_sections (bfd *abfd, struct bfd_link_info *info)
4248    {
4249      if (bfd_get_mach (abfd) == bfd_mach_score3)
4250        return s3_bfd_score_elf_create_dynamic_sections (abfd, info);
4251      else
4252        return s7_bfd_score_elf_create_dynamic_sections (abfd, info);
4253    }
4254    
4255    static bfd_boolean
4256    _bfd_score_elf_finish_dynamic_symbol (bfd *output_bfd,
4257                                          struct bfd_link_info *info,
4258                                          struct elf_link_hash_entry *h,
4259                                          Elf_Internal_Sym *sym)
4260    {
4261      if (bfd_get_mach (output_bfd) == bfd_mach_score3)
4262        return s3_bfd_score_elf_finish_dynamic_symbol (output_bfd, info, h, sym);
4263      else
4264        return s7_bfd_score_elf_finish_dynamic_symbol (output_bfd, info, h, sym);
4265    }
4266    
4267    static bfd_boolean
4268    _bfd_score_elf_finish_dynamic_sections (bfd *output_bfd,
4269                                            struct bfd_link_info *info)
4270    {
4271      if (bfd_get_mach (output_bfd) == bfd_mach_score3)
4272        return s3_bfd_score_elf_finish_dynamic_sections (output_bfd, info);
4273      else
4274        return s7_bfd_score_elf_finish_dynamic_sections (output_bfd, info);
4275    }
4276    
4277    static bfd_boolean
4278    _bfd_score_elf_fake_sections (bfd *abfd ATTRIBUTE_UNUSED,
4279                                  Elf_Internal_Shdr *hdr,
4280                                  asection *sec)
4281    {
4282      if (bfd_get_mach (abfd) == bfd_mach_score3)
4283        return s3_bfd_score_elf_fake_sections (abfd, hdr, sec);
4284      else
4285        return s7_bfd_score_elf_fake_sections (abfd, hdr, sec);
4286    }
4287    
4288    static bfd_boolean
4289    _bfd_score_elf_section_processing (bfd *abfd ATTRIBUTE_UNUSED, Elf_Internal_Shdr *hdr)
4290    {
4291      if (bfd_get_mach (abfd) == bfd_mach_score3)
4292        return s3_bfd_score_elf_section_processing (abfd, hdr);
4293      else
4294        return s7_bfd_score_elf_section_processing (abfd, hdr);
4295    }
4296    
4297    static bfd_boolean
4298    _bfd_score_elf_write_section (bfd *output_bfd,
4299                                  struct bfd_link_info *link_info ATTRIBUTE_UNUSED,
4300                                  asection *sec, bfd_byte *contents)
4301    {
4302      if (bfd_get_mach (output_bfd) == bfd_mach_score3)
4303        return s3_bfd_score_elf_write_section (output_bfd, sec, contents);
4304      else
4305        return s7_bfd_score_elf_write_section (output_bfd, sec, contents);
4306    }
4307    
4308    static void
4309    _bfd_score_elf_copy_indirect_symbol (struct bfd_link_info *info,
4310                                         struct elf_link_hash_entry *dir,
4311                                         struct elf_link_hash_entry *ind)
4312    {
4313      if (bfd_get_mach (info->input_bfds) == bfd_mach_score3)
4314        return s3_bfd_score_elf_copy_indirect_symbol (info, dir, ind);
4315      else
4316        return s7_bfd_score_elf_copy_indirect_symbol (info, dir, ind);
4317    }
4318    
4319    static void
4320    _bfd_score_elf_hide_symbol (struct bfd_link_info *info,
4321                                struct elf_link_hash_entry *entry,
4322                                bfd_boolean force_local)
4323    {
4324      if (bfd_get_mach (info->input_bfds) == bfd_mach_score3)
4325        return s3_bfd_score_elf_hide_symbol (info, entry, force_local);
4326      else
4327        return s7_bfd_score_elf_hide_symbol (info, entry, force_local);
4328    }
4329    
4330    static bfd_boolean
4331    _bfd_score_elf_discard_info (bfd *abfd, struct elf_reloc_cookie *cookie,
4332                             struct bfd_link_info *info)
4333    {
4334      if (bfd_get_mach (abfd) == bfd_mach_score3)
4335        return s3_bfd_score_elf_discard_info (abfd, cookie, info);
4336      else
4337        return s7_bfd_score_elf_discard_info (abfd, cookie, info);
4338    }
4339    
4340    static bfd_boolean
4341    _bfd_score_elf_ignore_discarded_relocs (asection *sec)
4342    {
4343      if (bfd_get_mach (sec->owner) == bfd_mach_score3)
4344        return s3_bfd_score_elf_ignore_discarded_relocs (sec);
4345      else
4346        return s7_bfd_score_elf_ignore_discarded_relocs (sec);
4347    }
4348    
4349    static asection *
4350    _bfd_score_elf_gc_mark_hook (asection *sec,
4351                                 struct bfd_link_info *info,
4352                                 Elf_Internal_Rela *rel,
4353                                 struct elf_link_hash_entry *h,
4354                                 Elf_Internal_Sym *sym)
4355    {
4356      if (bfd_get_mach (info->input_bfds) == bfd_mach_score3)
4357        return s3_bfd_score_elf_gc_mark_hook (sec, info, rel, h, sym);
4358      else
4359        return s7_bfd_score_elf_gc_mark_hook (sec, info, rel, h, sym);
4360    }
4361    
4362    static bfd_boolean
4363    _bfd_score_elf_grok_prstatus (bfd *abfd, Elf_Internal_Note *note)
4364    {
4365      if (bfd_get_mach (abfd) == bfd_mach_score3)
4366        return s3_bfd_score_elf_grok_prstatus (abfd, note);
4367      else
4368        return s7_bfd_score_elf_grok_prstatus (abfd, note);
4369    }
4370    
4371    static bfd_boolean
4372    _bfd_score_elf_grok_psinfo (bfd *abfd, Elf_Internal_Note *note)
4373    {
4374      if (bfd_get_mach (abfd) == bfd_mach_score3)
4375        return s3_bfd_score_elf_grok_psinfo (abfd, note);
4376      else
4377        return s7_bfd_score_elf_grok_psinfo (abfd, note);
4378    }
4379    
4380    static reloc_howto_type *
4381    elf32_score_reloc_type_lookup (bfd *abfd ATTRIBUTE_UNUSED, bfd_reloc_code_real_type code)
4382    {
4383      /* s3: NOTE!!!
4384         gas will call elf32_score_reloc_type_lookup, and don't write elf file.
4385         So just using score3, but we don't know ld will call this or not.
4386         If so, this way can't work.  */
4387    
4388      if (score3)
4389        return s3_elf32_score_reloc_type_lookup (abfd, code);
4390      else
4391        return s7_elf32_score_reloc_type_lookup (abfd, code);
4392    }
4393    
4394    static struct bfd_link_hash_table *
4395    elf32_score_link_hash_table_create (bfd *abfd)
4396    {
4397      if (bfd_get_mach (abfd) == bfd_mach_score3)
4398        return s3_elf32_score_link_hash_table_create (abfd);
4399      else
4400        return s7_elf32_score_link_hash_table_create (abfd);
4401    }
4402    
4403    static bfd_boolean
4404    elf32_score_print_private_bfd_data (bfd *abfd, void * ptr)
4405    {
4406      if (bfd_get_mach (abfd) == bfd_mach_score3)
4407        return s3_elf32_score_print_private_bfd_data (abfd, ptr);
4408      else
4409        return s7_elf32_score_print_p