1 /* ARC-specific support for 32-bit ELF
2 Copyright (C) 1994-2016 Free Software Foundation, Inc.
3 Contributed by Cupertino Miranda (cmiranda@synopsys.com).
5 This file is part of BFD, the Binary File Descriptor library.
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 3 of the License, or
10 (at your option) any later version.
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
20 MA 02110-1301, USA. */
27 #include "libiberty.h"
28 #include "opcode/arc-func.h"
29 #include "opcode/arc.h"
33 # define PR_DEBUG(fmt, args...) fprintf (stderr, fmt, ##args)
35 # define PR_DEBUG(fmt, args...)
38 /* #define ARC_ENABLE_DEBUG 1 */
39 #ifndef ARC_ENABLE_DEBUG
40 #define ARC_DEBUG(...)
43 name_for_global_symbol (struct elf_link_hash_entry
*h
)
45 static char *local_str
= "(local)";
49 return h
->root
.root
.string
;
51 #define ARC_DEBUG(args...) fprintf (stderr, ##args)
55 #define ADD_RELA(BFD, SECTION, OFFSET, SYM_IDX, TYPE, ADDEND) \
57 struct elf_link_hash_table *_htab = elf_hash_table (info); \
58 Elf_Internal_Rela _rel; \
61 _loc = _htab->srel##SECTION->contents \
62 + ((_htab->srel##SECTION->reloc_count) \
63 * sizeof (Elf32_External_Rela)); \
64 _htab->srel##SECTION->reloc_count++; \
65 _rel.r_addend = ADDEND; \
66 _rel.r_offset = (_htab->s##SECTION)->output_section->vma \
67 + (_htab->s##SECTION)->output_offset + OFFSET; \
68 BFD_ASSERT ((long) SYM_IDX != -1); \
69 _rel.r_info = ELF32_R_INFO (SYM_IDX, TYPE); \
70 bfd_elf32_swap_reloca_out (BFD, &_rel, _loc); \
75 bfd_vma sdata_begin_symbol_vma
;
76 asection
* sdata_output_section
;
77 bfd_vma got_symbol_vma
;
80 struct arc_local_data global_arc_data
=
82 .sdata_begin_symbol_vma
= 0,
83 .sdata_output_section
= NULL
,
87 struct dynamic_sections
89 bfd_boolean initialized
;
93 asection
* srelgotplt
;
99 enum dyn_section_types
107 DYN_SECTION_TYPES_END
110 const char * dyn_section_names
[DYN_SECTION_TYPES_END
] =
139 struct got_entry
*next
;
140 enum tls_type_e type
;
142 bfd_boolean processed
;
143 bfd_boolean created_dyn_relocation
;
144 enum tls_got_entries existing_entries
;
148 new_got_entry_to_list (struct got_entry
**list
,
149 enum tls_type_e type
,
151 enum tls_got_entries existing_entries
)
153 /* Find list end. Avoid having multiple entries of the same
155 struct got_entry
**p
= list
;
158 if ((*p
)->type
== type
)
163 struct got_entry
*entry
=
164 (struct got_entry
*) malloc (sizeof(struct got_entry
));
167 entry
->offset
= offset
;
169 entry
->processed
= FALSE
;
170 entry
->created_dyn_relocation
= FALSE
;
171 entry
->existing_entries
= existing_entries
;
173 /* Add the entry to the end of the list. */
178 symbol_has_entry_of_type (struct got_entry
*list
, enum tls_type_e type
)
182 if (list
->type
== type
)
190 /* The default symbols representing the init and fini dyn values.
191 TODO: Check what is the relation of those strings with arclinux.em
193 #define INIT_SYM_STRING "_init"
194 #define FINI_SYM_STRING "_fini"
196 char * init_str
= INIT_SYM_STRING
;
197 char * fini_str
= FINI_SYM_STRING
;
199 #define ARC_RELOC_HOWTO(TYPE, VALUE, SIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
204 static ATTRIBUTE_UNUSED
const char *
205 reloc_type_to_name (unsigned int type
)
209 #include "elf/arc-reloc.def"
216 #undef ARC_RELOC_HOWTO
218 /* Try to minimize the amount of space occupied by relocation tables
219 on the ROM (not that the ROM won't be swamped by other ELF overhead). */
223 static ATTRIBUTE_UNUSED bfd_boolean
224 is_reloc_PC_relative (reloc_howto_type
*howto
)
226 return (strstr (howto
->name
, "PC") != NULL
) ? TRUE
: FALSE
;
230 is_reloc_SDA_relative (reloc_howto_type
*howto
)
232 return (strstr (howto
->name
, "SDA") != NULL
) ? TRUE
: FALSE
;
236 is_reloc_for_GOT (reloc_howto_type
* howto
)
238 if (strstr (howto
->name
, "TLS") != NULL
)
240 return (strstr (howto
->name
, "GOT") != NULL
) ? TRUE
: FALSE
;
244 is_reloc_for_PLT (reloc_howto_type
* howto
)
246 return (strstr (howto
->name
, "PLT") != NULL
) ? TRUE
: FALSE
;
250 is_reloc_for_TLS (reloc_howto_type
*howto
)
252 return (strstr (howto
->name
, "TLS") != NULL
) ? TRUE
: FALSE
;
255 #define arc_bfd_get_8(A,B,C) bfd_get_8(A,B)
256 #define arc_bfd_get_16(A,B,C) bfd_get_16(A,B)
257 #define arc_bfd_get_32(A,B,C) bfd_get_32(A,B)
258 #define arc_bfd_put_8(A,B,C,D) bfd_put_8(A,B,C)
259 #define arc_bfd_put_16(A,B,C,D) bfd_put_16(A,B,C)
260 #define arc_bfd_put_32(A,B,C,D) bfd_put_32(A,B,C)
263 static bfd_reloc_status_type
264 arc_elf_reloc (bfd
*abfd ATTRIBUTE_UNUSED
,
265 arelent
*reloc_entry
,
267 void *data ATTRIBUTE_UNUSED
,
268 asection
*input_section
,
270 char ** error_message ATTRIBUTE_UNUSED
)
272 if (output_bfd
!= NULL
)
274 reloc_entry
->address
+= input_section
->output_offset
;
276 /* In case of relocateable link and if the reloc is against a
277 section symbol, the addend needs to be adjusted according to
278 where the section symbol winds up in the output section. */
279 if ((symbol_in
->flags
& BSF_SECTION_SYM
) && symbol_in
->section
)
280 reloc_entry
->addend
+= symbol_in
->section
->output_offset
;
285 return bfd_reloc_continue
;
289 #define ARC_RELOC_HOWTO(TYPE, VALUE, SIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
293 #include "elf/arc-reloc.def"
296 #undef ARC_RELOC_HOWTO
298 #define ARC_RELOC_HOWTO(TYPE, VALUE, RSIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
299 [TYPE] = HOWTO (R_##TYPE, 0, RSIZE, BITSIZE, FALSE, 0, complain_overflow_##OVERFLOW, arc_elf_reloc, "R_" #TYPE, FALSE, 0, 0, FALSE),
301 static struct reloc_howto_struct elf_arc_howto_table
[] =
303 #include "elf/arc-reloc.def"
304 /* Example of what is generated by the preprocessor. Currently kept as an
306 HOWTO (R_ARC_NONE, // Type.
308 2, // Size (0 = byte, 1 = short, 2 = long).
310 FALSE, // PC_relative.
312 complain_overflow_bitfield, // Complain_on_overflow.
313 bfd_elf_generic_reloc, // Special_function.
314 "R_ARC_NONE", // Name.
315 TRUE, // Partial_inplace.
318 FALSE), // PCrel_offset.
321 #undef ARC_RELOC_HOWTO
323 static void arc_elf_howto_init (void)
325 #define ARC_RELOC_HOWTO(TYPE, VALUE, SIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
326 elf_arc_howto_table[TYPE].pc_relative = \
327 (strstr (#FORMULA, " P ") != NULL || strstr (#FORMULA, " PDATA ") != NULL); \
328 elf_arc_howto_table[TYPE].dst_mask = RELOC_FUNCTION(0, ~0); \
329 /* Only 32 bit data relocations should be marked as ME. */ \
330 if (strstr (#FORMULA, " ME ") != NULL) \
332 BFD_ASSERT (SIZE == 2); \
335 #include "elf/arc-reloc.def"
338 #undef ARC_RELOC_HOWTO
341 #define ARC_RELOC_HOWTO(TYPE, VALUE, SIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
343 const int howto_table_lookup
[] =
345 #include "elf/arc-reloc.def"
347 #undef ARC_RELOC_HOWTO
349 static reloc_howto_type
*
350 arc_elf_howto (unsigned int r_type
)
352 if (elf_arc_howto_table
[R_ARC_32
].dst_mask
== 0)
353 arc_elf_howto_init ();
354 return &elf_arc_howto_table
[r_type
];
357 /* Map BFD reloc types to ARC ELF reloc types. */
361 bfd_reloc_code_real_type bfd_reloc_val
;
362 unsigned char elf_reloc_val
;
365 #define ARC_RELOC_HOWTO(TYPE, VALUE, SIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
366 { BFD_RELOC_##TYPE, R_##TYPE },
367 static const struct arc_reloc_map arc_reloc_map
[] =
369 #include "elf/arc-reloc.def"
371 {BFD_RELOC_NONE
, R_ARC_NONE
},
372 {BFD_RELOC_8
, R_ARC_8
},
373 {BFD_RELOC_16
, R_ARC_16
},
374 {BFD_RELOC_24
, R_ARC_24
},
375 {BFD_RELOC_32
, R_ARC_32
},
377 #undef ARC_RELOC_HOWTO
379 typedef ATTRIBUTE_UNUSED
bfd_vma (*replace_func
) (unsigned, int ATTRIBUTE_UNUSED
);
381 #define ARC_RELOC_HOWTO(TYPE, VALUE, SIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
383 func = (void *) RELOC_FUNCTION; \
386 get_replace_function (bfd
*abfd
, unsigned int r_type
)
392 #include "elf/arc-reloc.def"
395 if (func
== replace_bits24
&& bfd_big_endian (abfd
))
396 return (replace_func
) replace_bits24_be
;
398 return (replace_func
) func
;
400 #undef ARC_RELOC_HOWTO
402 static reloc_howto_type
*
403 arc_elf32_bfd_reloc_type_lookup (bfd
* abfd ATTRIBUTE_UNUSED
,
404 bfd_reloc_code_real_type code
)
408 for (i
= ARRAY_SIZE (arc_reloc_map
); i
--;)
410 if (arc_reloc_map
[i
].bfd_reloc_val
== code
)
411 return arc_elf_howto (arc_reloc_map
[i
].elf_reloc_val
);
417 /* Function to set the ELF flag bits. */
419 arc_elf_set_private_flags (bfd
*abfd
, flagword flags
)
421 elf_elfheader (abfd
)->e_flags
= flags
;
422 elf_flags_init (abfd
) = TRUE
;
426 /* Print private flags. */
428 arc_elf_print_private_bfd_data (bfd
*abfd
, void * ptr
)
430 FILE *file
= (FILE *) ptr
;
433 BFD_ASSERT (abfd
!= NULL
&& ptr
!= NULL
);
435 /* Print normal ELF private data. */
436 _bfd_elf_print_private_bfd_data (abfd
, ptr
);
438 flags
= elf_elfheader (abfd
)->e_flags
;
439 fprintf (file
, _("private flags = 0x%lx:"), (unsigned long) flags
);
441 switch (flags
& EF_ARC_MACH_MSK
)
443 case EF_ARC_CPU_ARCV2HS
: fprintf (file
, " -mcpu=ARCv2HS"); break;
444 case EF_ARC_CPU_ARCV2EM
: fprintf (file
, " -mcpu=ARCv2EM"); break;
445 case E_ARC_MACH_ARC600
: fprintf (file
, " -mcpu=ARC600"); break;
446 case E_ARC_MACH_ARC601
: fprintf (file
, " -mcpu=ARC601"); break;
447 case E_ARC_MACH_ARC700
: fprintf (file
, " -mcpu=ARC700"); break;
449 fprintf (file
, "-mcpu=unknown");
453 switch (flags
& EF_ARC_OSABI_MSK
)
455 case E_ARC_OSABI_ORIG
: fprintf (file
, " (ABI:legacy)"); break;
456 case E_ARC_OSABI_V2
: fprintf (file
, " (ABI:v2)"); break;
457 case E_ARC_OSABI_V3
: fprintf (file
, " (ABI:v3)"); break;
459 fprintf (file
, "(ABI:unknown)");
467 /* Copy backend specific data from one object module to another. */
470 arc_elf_copy_private_bfd_data (bfd
*ibfd
, bfd
*obfd
)
472 if (bfd_get_flavour (ibfd
) != bfd_target_elf_flavour
473 || bfd_get_flavour (obfd
) != bfd_target_elf_flavour
)
476 BFD_ASSERT (!elf_flags_init (obfd
)
477 || elf_elfheader (obfd
)->e_flags
== elf_elfheader (ibfd
)->e_flags
);
479 elf_elfheader (obfd
)->e_flags
= elf_elfheader (ibfd
)->e_flags
;
480 elf_flags_init (obfd
) = TRUE
;
482 /* Copy object attributes. */
483 _bfd_elf_copy_obj_attributes (ibfd
, obfd
);
485 return _bfd_elf_copy_private_bfd_data (ibfd
, obfd
);
488 static reloc_howto_type
*
489 bfd_elf32_bfd_reloc_name_lookup (bfd
* abfd ATTRIBUTE_UNUSED
,
494 for (i
= 0; i
< ARRAY_SIZE (elf_arc_howto_table
); i
++)
495 if (elf_arc_howto_table
[i
].name
!= NULL
496 && strcasecmp (elf_arc_howto_table
[i
].name
, r_name
) == 0)
497 return arc_elf_howto (i
);
502 /* Set the howto pointer for an ARC ELF reloc. */
505 arc_info_to_howto_rel (bfd
* abfd ATTRIBUTE_UNUSED
,
507 Elf_Internal_Rela
* dst
)
511 r_type
= ELF32_R_TYPE (dst
->r_info
);
512 BFD_ASSERT (r_type
< (unsigned int) R_ARC_max
);
513 cache_ptr
->howto
= arc_elf_howto (r_type
);
516 /* Merge backend specific data from an object file to the output
517 object file when linking. */
520 arc_elf_merge_private_bfd_data (bfd
*ibfd
, bfd
*obfd
)
522 unsigned short mach_ibfd
;
523 static unsigned short mach_obfd
= EM_NONE
;
528 /* Check if we have the same endianess. */
529 if (! _bfd_generic_verify_endian_match (ibfd
, obfd
))
531 _bfd_error_handler (_("ERROR: Endian Match failed. Attempting to link "
532 "%B with binary %s of opposite endian-ness"),
533 ibfd
, bfd_get_filename (obfd
));
537 /* Collect ELF flags. */
538 in_flags
= elf_elfheader (ibfd
)->e_flags
& EF_ARC_MACH_MSK
;
539 out_flags
= elf_elfheader (obfd
)->e_flags
& EF_ARC_MACH_MSK
;
541 if (!elf_flags_init (obfd
)) /* First call, no flags set. */
543 elf_flags_init (obfd
) = TRUE
;
544 out_flags
= in_flags
;
547 if (bfd_get_flavour (ibfd
) != bfd_target_elf_flavour
548 || bfd_get_flavour (obfd
) != bfd_target_elf_flavour
)
551 /* Check to see if the input BFD actually contains any sections. Do
552 not short-circuit dynamic objects; their section list may be
553 emptied by elf_link_add_object_symbols. */
554 if (!(ibfd
->flags
& DYNAMIC
))
556 bfd_boolean null_input_bfd
= TRUE
;
557 bfd_boolean only_data_sections
= TRUE
;
559 for (sec
= ibfd
->sections
; sec
!= NULL
; sec
= sec
->next
)
561 if ((bfd_get_section_flags (ibfd
, sec
)
562 & (SEC_LOAD
| SEC_CODE
| SEC_HAS_CONTENTS
))
563 == (SEC_LOAD
| SEC_CODE
| SEC_HAS_CONTENTS
))
564 only_data_sections
= FALSE
;
566 null_input_bfd
= FALSE
;
569 if (null_input_bfd
|| only_data_sections
)
573 /* Complain about various flag/architecture mismatches. */
574 mach_ibfd
= elf_elfheader (ibfd
)->e_machine
;
575 if (mach_obfd
== EM_NONE
)
577 mach_obfd
= mach_ibfd
;
581 if (mach_ibfd
!= mach_obfd
)
583 _bfd_error_handler (_("ERROR: Attempting to link %B "
584 "with a binary %s of different architecture"),
585 ibfd
, bfd_get_filename (obfd
));
588 else if (in_flags
!= out_flags
)
590 /* Warn if different flags. */
591 (*_bfd_error_handler
)
592 (_("%s: uses different e_flags (0x%lx) fields than "
593 "previous modules (0x%lx)"),
594 bfd_get_filename (ibfd
), (long)in_flags
, (long)out_flags
);
595 if (in_flags
&& out_flags
)
597 /* MWDT doesnt set the eflags hence make sure we choose the
598 eflags set by gcc. */
599 in_flags
= in_flags
> out_flags
? in_flags
: out_flags
;
603 /* Update the flags. */
604 elf_elfheader (obfd
)->e_flags
= in_flags
;
606 if (bfd_get_mach (obfd
) < bfd_get_mach (ibfd
))
608 return bfd_set_arch_mach (obfd
, bfd_arch_arc
, bfd_get_mach (ibfd
));
614 /* Set the right machine number for an ARC ELF file. */
616 arc_elf_object_p (bfd
* abfd
)
618 /* Make sure this is initialised, or you'll have the potential of passing
619 garbage---or misleading values---into the call to
620 bfd_default_set_arch_mach (). */
621 int mach
= bfd_mach_arc_arc700
;
622 unsigned long arch
= elf_elfheader (abfd
)->e_flags
& EF_ARC_MACH_MSK
;
623 unsigned e_machine
= elf_elfheader (abfd
)->e_machine
;
625 if (e_machine
== EM_ARC_COMPACT
|| e_machine
== EM_ARC_COMPACT2
)
629 case E_ARC_MACH_ARC600
:
630 mach
= bfd_mach_arc_arc600
;
632 case E_ARC_MACH_ARC601
:
633 mach
= bfd_mach_arc_arc601
;
635 case E_ARC_MACH_ARC700
:
636 mach
= bfd_mach_arc_arc700
;
638 case E_ARC_MACH_NPS400
:
639 mach
= bfd_mach_arc_nps400
;
641 case EF_ARC_CPU_ARCV2HS
:
642 case EF_ARC_CPU_ARCV2EM
:
643 mach
= bfd_mach_arc_arcv2
;
646 mach
= (e_machine
== EM_ARC_COMPACT
) ?
647 bfd_mach_arc_arc700
: bfd_mach_arc_arcv2
;
653 if (e_machine
== EM_ARC
)
655 (*_bfd_error_handler
)
656 (_("Error: The ARC4 architecture is no longer supported.\n"));
661 (*_bfd_error_handler
)
662 (_("Warning: unset or old architecture flags. \n"
663 " Use default machine.\n"));
667 return bfd_default_set_arch_mach (abfd
, bfd_arch_arc
, mach
);
670 /* The final processing done just before writing out an ARC ELF object file.
671 This gets the ARC architecture right based on the machine number. */
674 arc_elf_final_write_processing (bfd
* abfd
,
675 bfd_boolean linker ATTRIBUTE_UNUSED
)
679 switch (bfd_get_mach (abfd
))
681 case bfd_mach_arc_arc600
:
682 emf
= EM_ARC_COMPACT
;
684 case bfd_mach_arc_arc601
:
685 emf
= EM_ARC_COMPACT
;
687 case bfd_mach_arc_arc700
:
688 emf
= EM_ARC_COMPACT
;
690 case bfd_mach_arc_nps400
:
691 emf
= EM_ARC_COMPACT
;
693 case bfd_mach_arc_arcv2
:
694 emf
= EM_ARC_COMPACT2
;
700 elf_elfheader (abfd
)->e_machine
= emf
;
702 /* Record whatever is the current syscall ABI version. */
703 elf_elfheader (abfd
)->e_flags
|= E_ARC_OSABI_CURRENT
;
709 #define BFD_DEBUG_PIC(...)
711 struct arc_relocation_data
713 bfd_signed_vma reloc_offset
;
714 bfd_signed_vma reloc_addend
;
715 bfd_signed_vma got_offset_value
;
717 bfd_signed_vma sym_value
;
718 asection
* sym_section
;
720 reloc_howto_type
*howto
;
722 asection
* input_section
;
724 bfd_signed_vma sdata_begin_symbol_vma
;
725 bfd_boolean sdata_begin_symbol_vma_set
;
726 bfd_signed_vma got_symbol_vma
;
728 bfd_boolean should_relocate
;
730 const char * symbol_name
;
734 debug_arc_reloc (struct arc_relocation_data reloc_data
)
736 PR_DEBUG ("Reloc type=%s, should_relocate = %s\n",
737 reloc_data
.howto
->name
,
738 reloc_data
.should_relocate
? "true" : "false");
739 PR_DEBUG (" offset = 0x%x, addend = 0x%x\n",
740 (unsigned int) reloc_data
.reloc_offset
,
741 (unsigned int) reloc_data
.reloc_addend
);
742 PR_DEBUG (" Symbol:\n");
743 PR_DEBUG (" value = 0x%08x\n",
744 (unsigned int) reloc_data
.sym_value
);
745 if (reloc_data
.sym_section
!= NULL
)
747 PR_DEBUG (" Symbol Section:\n");
749 " section name = %s, output_offset 0x%08x",
750 reloc_data
.sym_section
->name
,
751 (unsigned int) reloc_data
.sym_section
->output_offset
);
752 if (reloc_data
.sym_section
->output_section
!= NULL
)
755 ", output_section->vma = 0x%08x",
756 ((unsigned int) reloc_data
.sym_section
->output_section
->vma
));
759 PR_DEBUG (" file: %s\n", reloc_data
.sym_section
->owner
->filename
);
763 PR_DEBUG ( " symbol section is NULL\n");
766 PR_DEBUG ( " Input_section:\n");
767 if (reloc_data
.input_section
!= NULL
)
770 " section name = %s, output_offset 0x%08x, output_section->vma = 0x%08x\n",
771 reloc_data
.input_section
->name
,
772 (unsigned int) reloc_data
.input_section
->output_offset
,
773 (unsigned int) reloc_data
.input_section
->output_section
->vma
);
774 PR_DEBUG ( " changed_address = 0x%08x\n",
775 (unsigned int) (reloc_data
.input_section
->output_section
->vma
+
776 reloc_data
.input_section
->output_offset
+
777 reloc_data
.reloc_offset
));
778 PR_DEBUG (" file: %s\n", reloc_data
.input_section
->owner
->filename
);
782 PR_DEBUG ( " input section is NULL\n");
787 middle_endian_convert (bfd_vma insn
, bfd_boolean do_it
)
792 ((insn
& 0xffff0000) >> 16) |
793 ((insn
& 0xffff) << 16);
798 /* This function is called for relocations that are otherwise marked as NOT
799 requiring overflow checks. In here we perform non-standard checks of
800 the relocation value. */
802 static inline bfd_reloc_status_type
803 arc_special_overflow_checks (const struct arc_relocation_data reloc_data
,
804 bfd_signed_vma relocation
,
805 struct bfd_link_info
*info ATTRIBUTE_UNUSED
)
807 switch (reloc_data
.howto
->type
)
809 case R_ARC_NPS_CMEM16
:
810 if (((relocation
>> 16) & 0xffff) != NPS_CMEM_HIGH_VALUE
)
812 if (reloc_data
.reloc_addend
== 0)
813 (*_bfd_error_handler
)
814 (_("%B(%A+0x%lx): CMEM relocation to `%s' is invalid, "
815 "16 MSB should be 0x%04x (value is 0x%lx)"),
816 reloc_data
.input_section
->owner
,
817 reloc_data
.input_section
,
818 reloc_data
.reloc_offset
,
819 reloc_data
.symbol_name
,
823 (*_bfd_error_handler
)
824 (_("%B(%A+0x%lx): CMEM relocation to `%s+0x%lx' is invalid, "
825 "16 MSB should be 0x%04x (value is 0x%lx)"),
826 reloc_data
.input_section
->owner
,
827 reloc_data
.input_section
,
828 reloc_data
.reloc_offset
,
829 reloc_data
.symbol_name
,
830 reloc_data
.reloc_addend
,
833 return bfd_reloc_overflow
;
844 #define ME(reloc) (reloc)
846 #define IS_ME(FORMULA,BFD) ((strstr (FORMULA, "ME") != NULL) \
847 && (!bfd_big_endian (BFD)))
849 #define S ((bfd_signed_vma) (reloc_data.sym_value \
850 + (reloc_data.sym_section->output_section != NULL ? \
851 (reloc_data.sym_section->output_offset \
852 + reloc_data.sym_section->output_section->vma) : 0)))
853 #define L ((bfd_signed_vma) (reloc_data.sym_value \
854 + (reloc_data.sym_section->output_section != NULL ? \
855 (reloc_data.sym_section->output_offset \
856 + reloc_data.sym_section->output_section->vma) : 0)))
857 #define A (reloc_data.reloc_addend)
859 #define G (reloc_data.got_offset_value)
860 #define GOT (reloc_data.got_symbol_vma)
861 #define GOT_BEGIN (htab->sgot->output_section->vma)
864 /* P: relative offset to PCL The offset should be to the
865 current location aligned to 32 bits. */
866 #define P ((bfd_signed_vma) ( \
868 (reloc_data.input_section->output_section != NULL ? \
869 reloc_data.input_section->output_section->vma : 0) \
870 + reloc_data.input_section->output_offset \
871 + (reloc_data.reloc_offset - (bitsize >= 32 ? 4 : 0))) \
873 #define PDATA ((bfd_signed_vma) ( \
874 (reloc_data.input_section->output_section->vma \
875 + reloc_data.input_section->output_offset \
876 + (reloc_data.reloc_offset))))
877 #define SECTSTART (bfd_signed_vma) (reloc_data.input_section->output_offset)
878 #define _SDA_BASE_ (bfd_signed_vma) (reloc_data.sdata_begin_symbol_vma)
879 #define TLS_REL (bfd_signed_vma) \
880 ((elf_hash_table (info))->tls_sec->output_section->vma)
886 #define PRINT_DEBUG_RELOC_INFO_BEFORE(FORMULA, TYPE) \
888 asection *sym_section = reloc_data.sym_section; \
889 asection *input_section = reloc_data.input_section; \
890 ARC_DEBUG ("RELOC_TYPE = " TYPE "\n"); \
891 ARC_DEBUG ("FORMULA = " FORMULA "\n"); \
892 ARC_DEBUG ("S = 0x%x\n", S); \
893 ARC_DEBUG ("A = 0x%x\n", A); \
894 ARC_DEBUG ("L = 0x%x\n", L); \
895 if (sym_section->output_section != NULL) \
897 ARC_DEBUG ("symbol_section->vma = 0x%x\n", \
898 sym_section->output_section->vma + sym_section->output_offset); \
902 ARC_DEBUG ("symbol_section->vma = NULL\n"); \
904 if (input_section->output_section != NULL) \
906 ARC_DEBUG ("symbol_section->vma = 0x%x\n", \
907 input_section->output_section->vma + input_section->output_offset); \
911 ARC_DEBUG ("symbol_section->vma = NULL\n"); \
913 ARC_DEBUG ("PCL = 0x%x\n", P); \
914 ARC_DEBUG ("P = 0x%x\n", P); \
915 ARC_DEBUG ("G = 0x%x\n", G); \
916 ARC_DEBUG ("SDA_OFFSET = 0x%x\n", _SDA_BASE_); \
917 ARC_DEBUG ("SDA_SET = %d\n", reloc_data.sdata_begin_symbol_vma_set); \
918 ARC_DEBUG ("GOT_OFFSET = 0x%x\n", GOT); \
919 ARC_DEBUG ("relocation = 0x%08x\n", relocation); \
920 ARC_DEBUG ("before = 0x%08x\n", (unsigned int) insn); \
921 ARC_DEBUG ("data = 0x%08x (%u) (%d)\n", (unsigned int) relocation, (unsigned int) relocation, (int) relocation); \
924 #define PRINT_DEBUG_RELOC_INFO_AFTER \
926 ARC_DEBUG ("after = 0x%08x\n", (unsigned int) insn); \
929 #define ARC_RELOC_HOWTO(TYPE, VALUE, SIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
932 bfd_signed_vma bitsize ATTRIBUTE_UNUSED = BITSIZE; \
933 relocation = FORMULA ; \
934 PRINT_DEBUG_RELOC_INFO_BEFORE (#FORMULA, #TYPE); \
935 insn = middle_endian_convert (insn, IS_ME (#FORMULA, abfd)); \
936 insn = (* get_replace_function (abfd, TYPE)) (insn, relocation); \
937 insn = middle_endian_convert (insn, IS_ME (#FORMULA, abfd)); \
938 PRINT_DEBUG_RELOC_INFO_AFTER \
942 static bfd_reloc_status_type
943 arc_do_relocation (bfd_byte
* contents
,
944 struct arc_relocation_data reloc_data
,
945 struct bfd_link_info
*info
)
947 bfd_signed_vma relocation
= 0;
949 bfd_vma orig_insn ATTRIBUTE_UNUSED
;
950 bfd
* abfd
= reloc_data
.input_section
->owner
;
951 struct elf_link_hash_table
*htab ATTRIBUTE_UNUSED
= elf_hash_table (info
);
952 bfd_reloc_status_type flag
;
954 if (reloc_data
.should_relocate
== FALSE
)
957 switch (reloc_data
.howto
->size
)
960 insn
= arc_bfd_get_32 (abfd
,
961 contents
+ reloc_data
.reloc_offset
,
962 reloc_data
.input_section
);
965 insn
= arc_bfd_get_16 (abfd
,
966 contents
+ reloc_data
.reloc_offset
,
967 reloc_data
.input_section
);
970 insn
= arc_bfd_get_8 (abfd
,
971 contents
+ reloc_data
.reloc_offset
,
972 reloc_data
.input_section
);
982 switch (reloc_data
.howto
->type
)
984 #include "elf/arc-reloc.def"
991 /* Check for relocation overflow. */
992 if (reloc_data
.howto
->complain_on_overflow
!= complain_overflow_dont
)
993 flag
= bfd_check_overflow (reloc_data
.howto
->complain_on_overflow
,
994 reloc_data
.howto
->bitsize
,
995 reloc_data
.howto
->rightshift
,
996 bfd_arch_bits_per_address (abfd
),
999 flag
= arc_special_overflow_checks (reloc_data
, relocation
, info
);
1001 #undef DEBUG_ARC_RELOC
1002 #define DEBUG_ARC_RELOC(A) debug_arc_reloc (A)
1003 if (flag
!= bfd_reloc_ok
)
1005 PR_DEBUG ( "Relocation overflows !!!!\n");
1007 DEBUG_ARC_RELOC (reloc_data
);
1010 "Relocation value = signed -> %d, unsigned -> %u"
1011 ", hex -> (0x%08x)\n",
1013 (unsigned int) relocation
,
1014 (unsigned int) relocation
);
1017 #undef DEBUG_ARC_RELOC
1018 #define DEBUG_ARC_RELOC(A)
1020 /* Write updated instruction back to memory. */
1021 switch (reloc_data
.howto
->size
)
1024 arc_bfd_put_32 (abfd
, insn
,
1025 contents
+ reloc_data
.reloc_offset
,
1026 reloc_data
.input_section
);
1029 arc_bfd_put_16 (abfd
, insn
,
1030 contents
+ reloc_data
.reloc_offset
,
1031 reloc_data
.input_section
);
1034 arc_bfd_put_8 (abfd
, insn
,
1035 contents
+ reloc_data
.reloc_offset
,
1036 reloc_data
.input_section
);
1039 ARC_DEBUG ("size = %d\n", reloc_data
.howto
->size
);
1044 return bfd_reloc_ok
;
1059 #undef ARC_RELOC_HOWTO
1061 static struct got_entry
**
1062 arc_get_local_got_ents (bfd
* abfd
)
1064 static struct got_entry
**local_got_ents
= NULL
;
1066 if (local_got_ents
== NULL
)
1069 Elf_Internal_Shdr
*symtab_hdr
= &((elf_tdata (abfd
))->symtab_hdr
);
1071 size
= symtab_hdr
->sh_info
* sizeof (bfd_vma
);
1072 local_got_ents
= (struct got_entry
**)
1073 bfd_alloc (abfd
, sizeof(struct got_entry
*) * size
);
1074 if (local_got_ents
== NULL
)
1077 memset (local_got_ents
, 0, sizeof(struct got_entry
*) * size
);
1078 elf_local_got_ents (abfd
) = local_got_ents
;
1081 return local_got_ents
;
1084 /* Relocate an arc ELF section.
1085 Function : elf_arc_relocate_section
1086 Brief : Relocate an arc section, by handling all the relocations
1087 appearing in that section.
1088 Args : output_bfd : The bfd being written to.
1089 info : Link information.
1090 input_bfd : The input bfd.
1091 input_section : The section being relocated.
1092 contents : contents of the section being relocated.
1093 relocs : List of relocations in the section.
1094 local_syms : is a pointer to the swapped in local symbols.
1095 local_section : is an array giving the section in the input file
1096 corresponding to the st_shndx field of each
1099 elf_arc_relocate_section (bfd
* output_bfd
,
1100 struct bfd_link_info
* info
,
1102 asection
* input_section
,
1103 bfd_byte
* contents
,
1104 Elf_Internal_Rela
* relocs
,
1105 Elf_Internal_Sym
* local_syms
,
1106 asection
** local_sections
)
1108 Elf_Internal_Shdr
* symtab_hdr
;
1109 struct elf_link_hash_entry
** sym_hashes
;
1110 struct got_entry
** local_got_ents
;
1111 Elf_Internal_Rela
* rel
;
1112 Elf_Internal_Rela
* wrel
;
1113 Elf_Internal_Rela
* relend
;
1114 struct elf_link_hash_table
*htab
= elf_hash_table (info
);
1116 symtab_hdr
= &((elf_tdata (input_bfd
))->symtab_hdr
);
1117 sym_hashes
= elf_sym_hashes (input_bfd
);
1119 rel
= wrel
= relocs
;
1120 relend
= relocs
+ input_section
->reloc_count
;
1121 for (; rel
< relend
; wrel
++, rel
++)
1123 enum elf_arc_reloc_type r_type
;
1124 reloc_howto_type
* howto
;
1125 unsigned long r_symndx
;
1126 struct elf_link_hash_entry
* h
;
1127 Elf_Internal_Sym
* sym
;
1129 struct elf_link_hash_entry
*h2
;
1131 struct arc_relocation_data reloc_data
=
1135 .got_offset_value
= 0,
1137 .sym_section
= NULL
,
1139 .input_section
= NULL
,
1140 .sdata_begin_symbol_vma
= 0,
1141 .sdata_begin_symbol_vma_set
= FALSE
,
1142 .got_symbol_vma
= 0,
1143 .should_relocate
= FALSE
1146 r_type
= ELF32_R_TYPE (rel
->r_info
);
1148 if (r_type
>= (int) R_ARC_max
)
1150 bfd_set_error (bfd_error_bad_value
);
1153 howto
= arc_elf_howto (r_type
);
1155 r_symndx
= ELF32_R_SYM (rel
->r_info
);
1157 /* If we are generating another .o file and the symbol in not
1158 local, skip this relocation. */
1159 if (bfd_link_relocatable (info
))
1161 /* This is a relocateable link. We don't have to change
1162 anything, unless the reloc is against a section symbol,
1163 in which case we have to adjust according to where the
1164 section symbol winds up in the output section. */
1166 /* Checks if this is a local symbol and thus the reloc
1167 might (will??) be against a section symbol. */
1168 if (r_symndx
< symtab_hdr
->sh_info
)
1170 sym
= local_syms
+ r_symndx
;
1171 if (ELF_ST_TYPE (sym
->st_info
) == STT_SECTION
)
1173 sec
= local_sections
[r_symndx
];
1175 /* for RELA relocs.Just adjust the addend
1176 value in the relocation entry. */
1177 rel
->r_addend
+= sec
->output_offset
+ sym
->st_value
;
1180 PR_DEBUG ("local symbols reloc "
1181 "(section=%d %s) seen in %s\n",
1183 local_sections
[r_symndx
]->name
,
1184 __PRETTY_FUNCTION__
)
1190 h2
= elf_link_hash_lookup (elf_hash_table (info
), "__SDATA_BEGIN__",
1191 FALSE
, FALSE
, TRUE
);
1193 if (reloc_data
.sdata_begin_symbol_vma_set
== FALSE
1194 && h2
!= NULL
&& h2
->root
.type
!= bfd_link_hash_undefined
1195 && h2
->root
.u
.def
.section
->output_section
!= NULL
)
1196 /* TODO: Verify this condition. */
1198 reloc_data
.sdata_begin_symbol_vma
=
1199 (h2
->root
.u
.def
.value
+
1200 h2
->root
.u
.def
.section
->output_section
->vma
);
1201 reloc_data
.sdata_begin_symbol_vma_set
= TRUE
;
1204 reloc_data
.input_section
= input_section
;
1205 reloc_data
.howto
= howto
;
1206 reloc_data
.reloc_offset
= rel
->r_offset
;
1207 reloc_data
.reloc_addend
= rel
->r_addend
;
1209 /* This is a final link. */
1214 if (r_symndx
< symtab_hdr
->sh_info
) /* A local symbol. */
1216 sym
= local_syms
+ r_symndx
;
1217 sec
= local_sections
[r_symndx
];
1221 /* TODO: This code is repeated from below. We should
1222 clean it and remove duplications.
1223 Sec is used check for discarded sections.
1224 Need to redesign code below. */
1226 /* Get the symbol's entry in the symtab. */
1227 h
= sym_hashes
[r_symndx
- symtab_hdr
->sh_info
];
1229 while (h
->root
.type
== bfd_link_hash_indirect
1230 || h
->root
.type
== bfd_link_hash_warning
)
1231 h
= (struct elf_link_hash_entry
*) h
->root
.u
.i
.link
;
1233 /* If we have encountered a definition for this symbol. */
1234 if (h
->root
.type
== bfd_link_hash_defined
1235 || h
->root
.type
== bfd_link_hash_defweak
)
1237 reloc_data
.sym_value
= h
->root
.u
.def
.value
;
1238 sec
= h
->root
.u
.def
.section
;
1242 /* Clean relocs for symbols in discarded sections. */
1243 if (sec
!= NULL
&& discarded_section (sec
))
1245 _bfd_clear_contents (howto
, input_bfd
, input_section
,
1246 contents
+ rel
->r_offset
);
1247 rel
->r_offset
= rel
->r_offset
;
1251 /* For ld -r, remove relocations in debug sections against
1252 sections defined in discarded sections. Not done for
1253 eh_frame editing code expects to be present. */
1254 if (bfd_link_relocatable (info
)
1255 && (input_section
->flags
& SEC_DEBUGGING
))
1261 if (bfd_link_relocatable (info
))
1268 if (r_symndx
< symtab_hdr
->sh_info
) /* A local symbol. */
1270 struct got_entry
*entry
;
1272 local_got_ents
= arc_get_local_got_ents (output_bfd
);
1273 entry
= local_got_ents
[r_symndx
];
1275 reloc_data
.sym_value
= sym
->st_value
;
1276 reloc_data
.sym_section
= sec
;
1277 reloc_data
.symbol_name
=
1278 bfd_elf_string_from_elf_section (input_bfd
,
1279 symtab_hdr
->sh_link
,
1282 /* Mergeable section handling. */
1283 if ((sec
->flags
& SEC_MERGE
)
1284 && ELF_ST_TYPE (sym
->st_info
) == STT_SECTION
)
1288 rel
->r_addend
= _bfd_elf_rel_local_sym (output_bfd
, sym
,
1289 &msec
, rel
->r_addend
);
1290 rel
->r_addend
-= (sec
->output_section
->vma
1291 + sec
->output_offset
1293 rel
->r_addend
+= msec
->output_section
->vma
+ msec
->output_offset
;
1295 reloc_data
.reloc_addend
= rel
->r_addend
;
1298 if ((is_reloc_for_GOT (howto
)
1299 || is_reloc_for_TLS (howto
)) && entry
!= NULL
)
1301 if (is_reloc_for_TLS (howto
))
1302 while (entry
->type
== GOT_NORMAL
&& entry
->next
!= NULL
)
1303 entry
= entry
->next
;
1305 if (is_reloc_for_GOT (howto
))
1306 while (entry
->type
!= GOT_NORMAL
&& entry
->next
!= NULL
)
1307 entry
= entry
->next
;
1309 if (entry
->type
== GOT_TLS_GD
&& entry
->processed
== FALSE
)
1311 bfd_vma sym_vma
= sym
->st_value
1312 + sec
->output_section
->vma
1313 + sec
->output_offset
;
1315 /* Create dynamic relocation for local sym. */
1316 ADD_RELA (output_bfd
, got
, entry
->offset
, 0,
1317 R_ARC_TLS_DTPMOD
, 0);
1318 ADD_RELA (output_bfd
, got
, entry
->offset
+4, 0,
1319 R_ARC_TLS_DTPOFF
, 0);
1321 bfd_vma sec_vma
= sec
->output_section
->vma
1322 + sec
->output_offset
;
1323 bfd_put_32 (output_bfd
, sym_vma
- sec_vma
,
1324 htab
->sgot
->contents
+ entry
->offset
+ 4);
1326 ARC_DEBUG ("arc_info: FIXED -> GOT_TLS_GD value "
1327 "= 0x%x @ 0x%x, for symbol %s\n",
1329 htab
->sgot
->contents
+ entry
->offset
+ 4,
1332 entry
->processed
= TRUE
;
1334 if (entry
->type
== GOT_TLS_IE
&& entry
->processed
== FALSE
)
1336 bfd_vma sym_vma
= sym
->st_value
1337 + sec
->output_section
->vma
1338 + sec
->output_offset
;
1339 bfd_vma sec_vma
= htab
->tls_sec
->output_section
->vma
;
1340 bfd_put_32 (output_bfd
, sym_vma
- sec_vma
,
1341 htab
->sgot
->contents
+ entry
->offset
);
1342 /* TODO: Check if this type of relocs is the cause
1343 for all the ARC_NONE dynamic relocs. */
1345 ARC_DEBUG ("arc_info: FIXED -> GOT_TLS_IE value = "
1346 "0x%x @ 0x%x, for symbol %s\n",
1348 htab
->sgot
->contents
+ entry
->offset
,
1351 entry
->processed
= TRUE
;
1353 if (entry
->type
== GOT_NORMAL
&& entry
->processed
== FALSE
)
1355 bfd_vma sec_vma
= reloc_data
.sym_section
->output_section
->vma
1356 + reloc_data
.sym_section
->output_offset
;
1358 bfd_put_32 (output_bfd
, reloc_data
.sym_value
+ sec_vma
,
1359 htab
->sgot
->contents
+ entry
->offset
);
1361 ARC_DEBUG ("arc_info: PATCHED: 0x%08x @ 0x%08x for "
1362 "sym %s in got offset 0x%x\n",
1363 reloc_data
.sym_value
+ sec_vma
,
1364 htab
->sgot
->output_section
->vma
1365 + htab
->sgot
->output_offset
+ entry
->offset
,
1368 entry
->processed
= TRUE
;
1371 reloc_data
.got_offset_value
= entry
->offset
;
1372 ARC_DEBUG ("arc_info: GOT_ENTRY = %d, offset = 0x%x, "
1373 "vma = 0x%x for symbol %s\n",
1374 entry
->type
, entry
->offset
,
1375 htab
->sgot
->output_section
->vma
1376 + htab
->sgot
->output_offset
+ entry
->offset
,
1380 BFD_ASSERT (htab
->sgot
!= NULL
|| !is_reloc_for_GOT (howto
));
1381 if (htab
->sgot
!= NULL
)
1382 reloc_data
.got_symbol_vma
= htab
->sgot
->output_section
->vma
1383 + htab
->sgot
->output_offset
;
1385 reloc_data
.should_relocate
= TRUE
;
1387 else /* Global symbol. */
1389 /* Get the symbol's entry in the symtab. */
1390 h
= sym_hashes
[r_symndx
- symtab_hdr
->sh_info
];
1392 while (h
->root
.type
== bfd_link_hash_indirect
1393 || h
->root
.type
== bfd_link_hash_warning
)
1394 h
= (struct elf_link_hash_entry
*) h
->root
.u
.i
.link
;
1396 /* TODO: Need to validate what was the intention. */
1397 /* BFD_ASSERT ((h->dynindx == -1) || (h->forced_local != 0)); */
1398 reloc_data
.symbol_name
= h
->root
.root
.string
;
1400 /* If we have encountered a definition for this symbol. */
1401 if (h
->root
.type
== bfd_link_hash_defined
1402 || h
->root
.type
== bfd_link_hash_defweak
)
1404 reloc_data
.sym_value
= h
->root
.u
.def
.value
;
1405 reloc_data
.sym_section
= h
->root
.u
.def
.section
;
1407 reloc_data
.should_relocate
= TRUE
;
1409 if (is_reloc_for_GOT (howto
) && !bfd_link_pic (info
))
1411 /* TODO: Change it to use arc_do_relocation with
1412 ARC_32 reloc. Try to use ADD_RELA macro. */
1413 bfd_vma relocation
=
1414 reloc_data
.sym_value
+ reloc_data
.reloc_addend
1415 + (reloc_data
.sym_section
->output_section
!= NULL
?
1416 (reloc_data
.sym_section
->output_offset
1417 + reloc_data
.sym_section
->output_section
->vma
)
1420 BFD_ASSERT (h
->got
.glist
);
1421 bfd_vma got_offset
= h
->got
.glist
->offset
;
1422 bfd_put_32 (output_bfd
, relocation
,
1423 htab
->sgot
->contents
+ got_offset
);
1425 if (is_reloc_for_PLT (howto
) && h
->plt
.offset
!= (bfd_vma
) -1)
1427 /* TODO: This is repeated up here. */
1428 reloc_data
.sym_value
= h
->plt
.offset
;
1429 reloc_data
.sym_section
= htab
->splt
;
1432 else if (h
->root
.type
== bfd_link_hash_undefweak
)
1434 /* Is weak symbol and has no definition. */
1435 if (is_reloc_for_GOT (howto
))
1437 reloc_data
.sym_value
= h
->root
.u
.def
.value
;
1438 reloc_data
.sym_section
= htab
->sgot
;
1439 reloc_data
.should_relocate
= TRUE
;
1441 else if (is_reloc_for_PLT (howto
)
1442 && h
->plt
.offset
!= (bfd_vma
) -1)
1444 /* TODO: This is repeated up here. */
1445 reloc_data
.sym_value
= h
->plt
.offset
;
1446 reloc_data
.sym_section
= htab
->splt
;
1447 reloc_data
.should_relocate
= TRUE
;
1454 if (is_reloc_for_GOT (howto
))
1456 reloc_data
.sym_value
= h
->root
.u
.def
.value
;
1457 reloc_data
.sym_section
= htab
->sgot
;
1459 reloc_data
.should_relocate
= TRUE
;
1461 else if (is_reloc_for_PLT (howto
))
1463 /* Fail if it is linking for PIE and the symbol is
1465 if (bfd_link_executable (info
))
1466 (*info
->callbacks
->undefined_symbol
)
1467 (info
, h
->root
.root
.string
, input_bfd
, input_section
,
1468 rel
->r_offset
, TRUE
);
1469 reloc_data
.sym_value
= h
->plt
.offset
;
1470 reloc_data
.sym_section
= htab
->splt
;
1472 reloc_data
.should_relocate
= TRUE
;
1474 else if (!bfd_link_pic (info
))
1475 (*info
->callbacks
->undefined_symbol
)
1476 (info
, h
->root
.root
.string
, input_bfd
, input_section
,
1477 rel
->r_offset
, TRUE
);
1480 if (h
->got
.glist
!= NULL
)
1482 struct got_entry
*entry
= h
->got
.glist
;
1484 if (is_reloc_for_GOT (howto
) || is_reloc_for_TLS (howto
))
1486 if (! elf_hash_table (info
)->dynamic_sections_created
1487 || (bfd_link_pic (info
)
1488 && SYMBOL_REFERENCES_LOCAL (info
, h
)))
1490 reloc_data
.sym_value
= h
->root
.u
.def
.value
;
1491 reloc_data
.sym_section
= h
->root
.u
.def
.section
;
1493 if (is_reloc_for_TLS (howto
))
1494 while (entry
->type
== GOT_NORMAL
&& entry
->next
!= NULL
)
1495 entry
= entry
->next
;
1497 if (entry
->processed
== FALSE
1498 && (entry
->type
== GOT_TLS_GD
1499 || entry
->type
== GOT_TLS_IE
))
1501 bfd_vma sym_value
= h
->root
.u
.def
.value
1502 + h
->root
.u
.def
.section
->output_section
->vma
1503 + h
->root
.u
.def
.section
->output_offset
;
1506 elf_hash_table (info
)->tls_sec
->output_section
->vma
;
1508 bfd_put_32 (output_bfd
,
1509 sym_value
- sec_vma
,
1510 htab
->sgot
->contents
+ entry
->offset
1511 + (entry
->existing_entries
== TLS_GOT_MOD_AND_OFF
? 4 : 0));
1513 ARC_DEBUG ("arc_info: FIXED -> %s value = 0x%x "
1514 "@ 0x%x, for symbol %s\n",
1515 (entry
->type
== GOT_TLS_GD
? "GOT_TLS_GD" :
1517 sym_value
- sec_vma
,
1518 htab
->sgot
->contents
+ entry
->offset
1519 + (entry
->existing_entries
== TLS_GOT_MOD_AND_OFF
? 4 : 0),
1520 h
->root
.root
.string
);
1522 entry
->processed
= TRUE
;
1525 if (entry
->type
== GOT_TLS_IE
&& entry
->processed
== FALSE
)
1527 bfd_vma sec_vma
= htab
->tls_sec
->output_section
->vma
;
1528 bfd_put_32 (output_bfd
,
1529 reloc_data
.sym_value
- sec_vma
,
1530 htab
->sgot
->contents
+ entry
->offset
);
1533 if (entry
->type
== GOT_NORMAL
&& entry
->processed
== FALSE
)
1536 reloc_data
.sym_section
->output_section
->vma
1537 + reloc_data
.sym_section
->output_offset
;
1539 if (h
->root
.type
!= bfd_link_hash_undefweak
)
1541 bfd_put_32 (output_bfd
,
1542 reloc_data
.sym_value
+ sec_vma
,
1543 htab
->sgot
->contents
+ entry
->offset
);
1545 ARC_DEBUG ("arc_info: PATCHED: 0x%08x "
1546 "@ 0x%08x for sym %s in got offset 0x%x\n",
1547 reloc_data
.sym_value
+ sec_vma
,
1548 htab
->sgot
->output_section
->vma
1549 + htab
->sgot
->output_offset
+ entry
->offset
,
1550 h
->root
.root
.string
,
1555 ARC_DEBUG ("arc_info: PATCHED: NOT_PATCHED "
1556 "@ 0x%08x for sym %s in got offset 0x%x "
1558 htab
->sgot
->output_section
->vma
1559 + htab
->sgot
->output_offset
+ entry
->offset
,
1560 h
->root
.root
.string
,
1564 entry
->processed
= TRUE
;
1569 reloc_data
.got_offset_value
= entry
->offset
;
1571 ARC_DEBUG ("arc_info: GOT_ENTRY = %d, offset = 0x%x, "
1572 "vma = 0x%x for symbol %s\n",
1573 entry
->type
, entry
->offset
,
1574 htab
->sgot
->output_section
->vma
1575 + htab
->sgot
->output_offset
+ entry
->offset
,
1576 h
->root
.root
.string
);
1579 BFD_ASSERT (htab
->sgot
!= NULL
|| !is_reloc_for_GOT (howto
));
1580 if (htab
->sgot
!= NULL
)
1581 reloc_data
.got_symbol_vma
= htab
->sgot
->output_section
->vma
1582 + htab
->sgot
->output_offset
;
1590 case R_ARC_32_PCREL
:
1591 if (bfd_link_pic (info
) && !bfd_link_pie (info
)
1592 && ((r_type
!= R_ARC_PC32
&& r_type
!= R_ARC_32_PCREL
)
1595 && (!info
->symbolic
|| !h
->def_regular
))))
1597 Elf_Internal_Rela outrel
;
1599 bfd_boolean skip
= FALSE
;
1600 bfd_boolean relocate
= FALSE
;
1601 asection
*sreloc
= _bfd_elf_get_dynamic_reloc_section
1602 (input_bfd
, input_section
,
1605 BFD_ASSERT (sreloc
!= NULL
);
1607 outrel
.r_offset
= _bfd_elf_section_offset (output_bfd
,
1611 if (outrel
.r_offset
== (bfd_vma
) -1)
1614 outrel
.r_addend
= rel
->r_addend
;
1615 outrel
.r_offset
+= (input_section
->output_section
->vma
1616 + input_section
->output_offset
);
1618 #define IS_ARC_PCREL_TYPE(TYPE) \
1619 ( (TYPE == R_ARC_PC32) \
1620 || (TYPE == R_ARC_32_PCREL))
1623 memset (&outrel
, 0, sizeof outrel
);
1628 && ((IS_ARC_PCREL_TYPE (r_type
))
1629 || !(bfd_link_executable (info
)
1630 || SYMBOLIC_BIND (info
, h
))
1631 || ! h
->def_regular
))
1633 BFD_ASSERT (h
!= NULL
);
1634 if ((input_section
->flags
& SEC_ALLOC
) != 0)
1639 BFD_ASSERT (h
->dynindx
!= -1);
1640 outrel
.r_info
= ELF32_R_INFO (h
->dynindx
, r_type
);
1644 /* Handle local symbols, they either do not have a
1645 global hash table entry (h == NULL), or are
1646 forced local due to a version script
1647 (h->forced_local), or the third condition is
1648 legacy, it appears to say something like, for
1649 links where we are pre-binding the symbols, or
1650 there's not an entry for this symbol in the
1651 dynamic symbol table, and it's a regular symbol
1652 not defined in a shared object, then treat the
1653 symbol as local, resolve it now. */
1655 /* outrel.r_addend = 0; */
1656 outrel
.r_info
= ELF32_R_INFO (0, R_ARC_RELATIVE
);
1659 BFD_ASSERT (sreloc
->contents
!= 0);
1661 loc
= sreloc
->contents
;
1662 loc
+= sreloc
->reloc_count
* sizeof (Elf32_External_Rela
);
1663 sreloc
->reloc_count
+= 1;
1665 bfd_elf32_swap_reloca_out (output_bfd
, &outrel
, loc
);
1667 if (relocate
== FALSE
)
1675 if (is_reloc_SDA_relative (howto
)
1676 && (reloc_data
.sdata_begin_symbol_vma_set
== FALSE
))
1678 (*_bfd_error_handler
)
1679 ("Error: Linker symbol __SDATA_BEGIN__ not found");
1680 bfd_set_error (bfd_error_bad_value
);
1684 DEBUG_ARC_RELOC (reloc_data
);
1686 if (arc_do_relocation (contents
, reloc_data
, info
) != bfd_reloc_ok
)
1693 static struct dynamic_sections
1694 arc_create_dynamic_sections (bfd
* abfd
, struct bfd_link_info
*info
)
1696 struct elf_link_hash_table
*htab
;
1698 struct dynamic_sections ds
=
1700 .initialized
= FALSE
,
1710 htab
= elf_hash_table (info
);
1713 /* Create dynamic sections for relocatable executables so that we
1714 can copy relocations. */
1715 if (! htab
->dynamic_sections_created
&& bfd_link_pic (info
))
1717 if (! _bfd_elf_link_create_dynamic_sections (abfd
, info
))
1721 dynobj
= (elf_hash_table (info
))->dynobj
;
1725 ds
.sgot
= htab
->sgot
;
1726 ds
.srelgot
= htab
->srelgot
;
1728 ds
.sgotplt
= bfd_get_section_by_name (dynobj
, ".got.plt");
1729 ds
.srelgotplt
= ds
.srelplt
;
1731 ds
.splt
= bfd_get_section_by_name (dynobj
, ".plt");
1732 ds
.srelplt
= bfd_get_section_by_name (dynobj
, ".rela.plt");
1735 if (htab
->dynamic_sections_created
)
1737 ds
.sdyn
= bfd_get_section_by_name (dynobj
, ".dynamic");
1740 ds
.initialized
= TRUE
;
1745 #define ADD_SYMBOL_REF_SEC_AND_RELOC(SECNAME, COND_FOR_RELOC, H) \
1746 htab->s##SECNAME->size; \
1748 if (COND_FOR_RELOC) \
1750 htab->srel##SECNAME->size += sizeof (Elf32_External_Rela); \
1751 ARC_DEBUG ("arc_info: Added reloc space in " \
1752 #SECNAME " section at " __FILE__ \
1753 ":%d for symbol\n", \
1754 __LINE__, name_for_global_symbol (H)); \
1757 if (h->dynindx == -1 && !h->forced_local) \
1758 if (! bfd_elf_link_record_dynamic_symbol (info, H)) \
1760 htab->s##SECNAME->size += 4; \
1764 elf_arc_check_relocs (bfd
* abfd
,
1765 struct bfd_link_info
* info
,
1767 const Elf_Internal_Rela
* relocs
)
1769 Elf_Internal_Shdr
* symtab_hdr
;
1770 struct elf_link_hash_entry
** sym_hashes
;
1771 struct got_entry
** local_got_ents
;
1772 const Elf_Internal_Rela
* rel
;
1773 const Elf_Internal_Rela
* rel_end
;
1775 asection
* sreloc
= NULL
;
1776 struct elf_link_hash_table
* htab
= elf_hash_table (info
);
1778 if (bfd_link_relocatable (info
))
1781 dynobj
= (elf_hash_table (info
))->dynobj
;
1782 symtab_hdr
= &((elf_tdata (abfd
))->symtab_hdr
);
1783 sym_hashes
= elf_sym_hashes (abfd
);
1784 local_got_ents
= arc_get_local_got_ents (abfd
);
1786 rel_end
= relocs
+ sec
->reloc_count
;
1787 for (rel
= relocs
; rel
< rel_end
; rel
++)
1789 enum elf_arc_reloc_type r_type
;
1790 reloc_howto_type
*howto
;
1791 unsigned long r_symndx
;
1792 struct elf_link_hash_entry
*h
;
1794 r_type
= ELF32_R_TYPE (rel
->r_info
);
1796 if (r_type
>= (int) R_ARC_max
)
1798 bfd_set_error (bfd_error_bad_value
);
1801 howto
= arc_elf_howto (r_type
);
1804 && (is_reloc_for_GOT (howto
) == TRUE
1805 || is_reloc_for_TLS (howto
) == TRUE
))
1807 dynobj
= elf_hash_table (info
)->dynobj
= abfd
;
1808 if (! _bfd_elf_create_got_section (abfd
, info
))
1812 /* Load symbol information. */
1813 r_symndx
= ELF32_R_SYM (rel
->r_info
);
1814 if (r_symndx
< symtab_hdr
->sh_info
) /* Is a local symbol. */
1816 else /* Global one. */
1817 h
= sym_hashes
[r_symndx
- symtab_hdr
->sh_info
];
1823 /* During shared library creation, these relocs should not
1824 appear in a shared library (as memory will be read only
1825 and the dynamic linker can not resolve these. However
1826 the error should not occur for e.g. debugging or
1827 non-readonly sections. */
1828 if (bfd_link_dll (info
) && !bfd_link_pie (info
)
1829 && (sec
->flags
& SEC_ALLOC
) != 0
1830 && (sec
->flags
& SEC_READONLY
) != 0
1831 && ((sec
->flags
& SEC_CODE
) != 0
1832 || (sec
->flags
& SEC_DEBUGGING
) != 0))
1836 name
= h
->root
.root
.string
;
1838 /* bfd_elf_sym_name (abfd, symtab_hdr, isym, NULL); */
1840 (*_bfd_error_handler
)
1842 %B: relocation %s against `%s' can not be used when making a shared object; recompile with -fPIC"),
1844 arc_elf_howto (r_type
)->name
,
1846 bfd_set_error (bfd_error_bad_value
);
1850 /* In some cases we are not setting the 'non_got_ref'
1851 flag, even though the relocations don't require a GOT
1852 access. We should extend the testing in this area to
1853 ensure that no significant cases are being missed. */
1858 case R_ARC_32_PCREL
:
1859 if (bfd_link_pic (info
) && !bfd_link_pie (info
)
1860 && ((r_type
!= R_ARC_PC32
&& r_type
!= R_ARC_32_PCREL
)
1863 && (!info
->symbolic
|| !h
->def_regular
))))
1867 sreloc
= _bfd_elf_make_dynamic_reloc_section (sec
, dynobj
,
1875 sreloc
->size
+= sizeof (Elf32_External_Rela
);
1882 if (is_reloc_for_PLT (howto
) == TRUE
)
1890 if (is_reloc_for_GOT (howto
) == TRUE
)
1895 if (local_got_ents
[r_symndx
] == NULL
)
1898 ADD_SYMBOL_REF_SEC_AND_RELOC (got
,
1899 bfd_link_pic (info
),
1901 new_got_entry_to_list (&(local_got_ents
[r_symndx
]),
1902 GOT_NORMAL
, offset
, TLS_GOT_NONE
);
1907 /* Global symbol. */
1908 h
= sym_hashes
[r_symndx
- symtab_hdr
->sh_info
];
1909 if (h
->got
.glist
== NULL
)
1912 ADD_SYMBOL_REF_SEC_AND_RELOC (got
, TRUE
, h
);
1913 new_got_entry_to_list (&h
->got
.glist
,
1914 GOT_NORMAL
, offset
, TLS_GOT_NONE
);
1919 if (is_reloc_for_TLS (howto
) == TRUE
)
1921 enum tls_type_e type
= GOT_UNKNOWN
;
1925 case R_ARC_TLS_GD_GOT
:
1928 case R_ARC_TLS_IE_GOT
:
1935 struct got_entry
**list
= NULL
;
1937 list
= &(h
->got
.glist
);
1939 list
= &(local_got_ents
[r_symndx
]);
1941 if (type
!= GOT_UNKNOWN
&& !symbol_has_entry_of_type (*list
, type
))
1943 enum tls_got_entries entries
= TLS_GOT_NONE
;
1945 ADD_SYMBOL_REF_SEC_AND_RELOC (got
, TRUE
, h
);
1947 if (type
== GOT_TLS_GD
)
1949 bfd_vma ATTRIBUTE_UNUSED notneeded
=
1950 ADD_SYMBOL_REF_SEC_AND_RELOC (got
, TRUE
, h
);
1951 entries
= TLS_GOT_MOD_AND_OFF
;
1954 if (entries
== TLS_GOT_NONE
)
1955 entries
= TLS_GOT_OFF
;
1957 new_got_entry_to_list (list
, type
, offset
, entries
);
1965 #define ELF_DYNAMIC_INTERPRETER "/sbin/ld-uClibc.so"
1967 static struct plt_version_t
*
1968 arc_get_plt_version (struct bfd_link_info
*info
)
1972 for (i
= 0; i
< 1; i
++)
1974 ARC_DEBUG ("%d: size1 = %d, size2 = %d\n", i
,
1975 plt_versions
[i
].entry_size
,
1976 plt_versions
[i
].elem_size
);
1979 if (bfd_get_mach (info
->output_bfd
) == bfd_mach_arc_arcv2
)
1981 if (bfd_link_pic (info
))
1982 return &(plt_versions
[ELF_ARCV2_PIC
]);
1984 return &(plt_versions
[ELF_ARCV2_ABS
]);
1988 if (bfd_link_pic (info
))
1989 return &(plt_versions
[ELF_ARC_PIC
]);
1991 return &(plt_versions
[ELF_ARC_ABS
]);
1996 add_symbol_to_plt (struct bfd_link_info
*info
)
1998 struct elf_link_hash_table
*htab
= elf_hash_table (info
);
2001 struct plt_version_t
*plt_data
= arc_get_plt_version (info
);
2003 /* If this is the first .plt entry, make room for the special first
2005 if (htab
->splt
->size
== 0)
2006 htab
->splt
->size
+= plt_data
->entry_size
;
2008 ret
= htab
->splt
->size
;
2010 htab
->splt
->size
+= plt_data
->elem_size
;
2011 ARC_DEBUG ("PLT_SIZE = %d\n", htab
->splt
->size
);
2013 htab
->sgotplt
->size
+= 4;
2014 htab
->srelplt
->size
+= sizeof (Elf32_External_Rela
);
2019 #define PLT_DO_RELOCS_FOR_ENTRY(ABFD, DS, RELOCS) \
2020 plt_do_relocs_for_symbol (ABFD, DS, RELOCS, 0, 0)
2023 plt_do_relocs_for_symbol (bfd
*abfd
,
2024 struct elf_link_hash_table
*htab
,
2025 const struct plt_reloc
*reloc
,
2027 bfd_vma symbol_got_offset
)
2029 while (SYM_ONLY (reloc
->symbol
) != LAST_RELOC
)
2031 bfd_vma relocation
= 0;
2033 switch (SYM_ONLY (reloc
->symbol
))
2037 htab
->sgotplt
->output_section
->vma
+
2038 htab
->sgotplt
->output_offset
+ symbol_got_offset
;
2041 relocation
+= reloc
->addend
;
2043 if (IS_RELATIVE (reloc
->symbol
))
2045 bfd_vma reloc_offset
= reloc
->offset
;
2046 reloc_offset
-= (IS_INSN_32 (reloc
->symbol
)) ? 4 : 0;
2047 reloc_offset
-= (IS_INSN_24 (reloc
->symbol
)) ? 2 : 0;
2049 relocation
-= htab
->splt
->output_section
->vma
2050 + htab
->splt
->output_offset
2051 + plt_offset
+ reloc_offset
;
2054 /* TODO: being ME is not a property of the relocation but of the
2055 section of which is applying the relocation. */
2056 if (IS_MIDDLE_ENDIAN (reloc
->symbol
) && !bfd_big_endian (abfd
))
2059 ((relocation
& 0xffff0000) >> 16) |
2060 ((relocation
& 0xffff) << 16);
2063 switch (reloc
->size
)
2066 bfd_put_32 (htab
->splt
->output_section
->owner
,
2068 htab
->splt
->contents
+ plt_offset
+ reloc
->offset
);
2072 reloc
= &(reloc
[1]); /* Jump to next relocation. */
2077 relocate_plt_for_symbol (bfd
*output_bfd
,
2078 struct bfd_link_info
*info
,
2079 struct elf_link_hash_entry
*h
)
2081 struct plt_version_t
*plt_data
= arc_get_plt_version (info
);
2082 struct elf_link_hash_table
*htab
= elf_hash_table (info
);
2084 bfd_vma plt_index
= (h
->plt
.offset
- plt_data
->entry_size
)
2085 / plt_data
->elem_size
;
2086 bfd_vma got_offset
= (plt_index
+ 3) * 4;
2088 ARC_DEBUG ("arc_info: PLT_OFFSET = 0x%x, PLT_ENTRY_VMA = 0x%x, \
2089 GOT_ENTRY_OFFSET = 0x%x, GOT_ENTRY_VMA = 0x%x, for symbol %s\n",
2091 htab
->splt
->output_section
->vma
2092 + htab
->splt
->output_offset
2095 htab
->sgotplt
->output_section
->vma
2096 + htab
->sgotplt
->output_offset
2098 h
->root
.root
.string
);
2103 uint16_t *ptr
= (uint16_t *) plt_data
->elem
;
2104 for (i
= 0; i
< plt_data
->elem_size
/2; i
++)
2106 uint16_t data
= ptr
[i
];
2107 bfd_put_16 (output_bfd
,
2109 htab
->splt
->contents
+ h
->plt
.offset
+ (i
*2));
2113 plt_do_relocs_for_symbol (output_bfd
, htab
,
2114 plt_data
->elem_relocs
,
2118 /* Fill in the entry in the global offset table. */
2119 bfd_put_32 (output_bfd
,
2120 (bfd_vma
) (htab
->splt
->output_section
->vma
2121 + htab
->splt
->output_offset
),
2122 htab
->sgotplt
->contents
+ got_offset
);
2124 /* TODO: Fill in the entry in the .rela.plt section. */
2126 Elf_Internal_Rela rel
;
2129 rel
.r_offset
= (htab
->sgotplt
->output_section
->vma
2130 + htab
->sgotplt
->output_offset
2134 BFD_ASSERT (h
->dynindx
!= -1);
2135 rel
.r_info
= ELF32_R_INFO (h
->dynindx
, R_ARC_JMP_SLOT
);
2137 loc
= htab
->srelplt
->contents
;
2138 loc
+= plt_index
* sizeof (Elf32_External_Rela
); /* relA */
2139 bfd_elf32_swap_reloca_out (output_bfd
, &rel
, loc
);
2144 relocate_plt_for_entry (bfd
*abfd
,
2145 struct bfd_link_info
*info
)
2147 struct plt_version_t
*plt_data
= arc_get_plt_version (info
);
2148 struct elf_link_hash_table
*htab
= elf_hash_table (info
);
2152 uint16_t *ptr
= (uint16_t *) plt_data
->entry
;
2153 for (i
= 0; i
< plt_data
->entry_size
/2; i
++)
2155 uint16_t data
= ptr
[i
];
2158 htab
->splt
->contents
+ (i
*2));
2161 PLT_DO_RELOCS_FOR_ENTRY (abfd
, htab
, plt_data
->entry_relocs
);
2164 /* Desc : Adjust a symbol defined by a dynamic object and referenced
2165 by a regular object. The current definition is in some section of
2166 the dynamic object, but we're not including those sections. We
2167 have to change the definition to something the rest of the link can
2171 elf_arc_adjust_dynamic_symbol (struct bfd_link_info
*info
,
2172 struct elf_link_hash_entry
*h
)
2175 bfd
*dynobj
= (elf_hash_table (info
))->dynobj
;
2176 struct elf_link_hash_table
*htab
= elf_hash_table (info
);
2178 if (h
->type
== STT_FUNC
2179 || h
->type
== STT_GNU_IFUNC
2180 || h
->needs_plt
== 1)
2182 if (!bfd_link_pic (info
) && !h
->def_dynamic
&& !h
->ref_dynamic
)
2184 /* This case can occur if we saw a PLT32 reloc in an input
2185 file, but the symbol was never referred to by a dynamic
2186 object. In such a case, we don't actually need to build
2187 a procedure linkage table, and we can just do a PC32
2189 BFD_ASSERT (h
->needs_plt
);
2193 /* Make sure this symbol is output as a dynamic symbol. */
2194 if (h
->dynindx
== -1 && !h
->forced_local
2195 && !bfd_elf_link_record_dynamic_symbol (info
, h
))
2198 if (bfd_link_pic (info
)
2199 || WILL_CALL_FINISH_DYNAMIC_SYMBOL (1, 0, h
))
2201 bfd_vma loc
= add_symbol_to_plt (info
);
2203 if (!bfd_link_pic (info
) && !h
->def_regular
)
2205 h
->root
.u
.def
.section
= htab
->splt
;
2206 h
->root
.u
.def
.value
= loc
;
2208 h
->plt
.offset
= loc
;
2212 h
->plt
.offset
= (bfd_vma
) -1;
2218 /* If this is a weak symbol, and there is a real definition, the
2219 processor independent code will have arranged for us to see the
2220 real definition first, and we can just use the same value. */
2221 if (h
->u
.weakdef
!= NULL
)
2223 BFD_ASSERT (h
->u
.weakdef
->root
.type
== bfd_link_hash_defined
2224 || h
->u
.weakdef
->root
.type
== bfd_link_hash_defweak
);
2225 h
->root
.u
.def
.section
= h
->u
.weakdef
->root
.u
.def
.section
;
2226 h
->root
.u
.def
.value
= h
->u
.weakdef
->root
.u
.def
.value
;
2230 /* This is a reference to a symbol defined by a dynamic object which
2231 is not a function. */
2233 /* If we are creating a shared library, we must presume that the
2234 only references to the symbol are via the global offset table.
2235 For such cases we need not do anything here; the relocations will
2236 be handled correctly by relocate_section. */
2237 if (!bfd_link_executable (info
))
2240 /* If there are no non-GOT references, we do not need a copy
2242 if (!h
->non_got_ref
)
2245 /* If -z nocopyreloc was given, we won't generate them either. */
2246 if (info
->nocopyreloc
)
2252 /* We must allocate the symbol in our .dynbss section, which will
2253 become part of the .bss section of the executable. There will be
2254 an entry for this symbol in the .dynsym section. The dynamic
2255 object will contain position independent code, so all references
2256 from the dynamic object to this symbol will go through the global
2257 offset table. The dynamic linker will use the .dynsym entry to
2258 determine the address it must put in the global offset table, so
2259 both the dynamic object and the regular object will refer to the
2260 same memory location for the variable. */
2265 /* We must generate a R_ARC_COPY reloc to tell the dynamic linker to
2266 copy the initial value out of the dynamic object and into the
2267 runtime process image. We need to remember the offset into the
2268 .rela.bss section we are going to use. */
2269 if ((h
->root
.u
.def
.section
->flags
& SEC_ALLOC
) != 0)
2273 srel
= bfd_get_section_by_name (dynobj
, ".rela.bss");
2274 BFD_ASSERT (srel
!= NULL
);
2275 srel
->size
+= sizeof (Elf32_External_Rela
);
2279 s
= bfd_get_section_by_name (dynobj
, ".dynbss");
2280 BFD_ASSERT (s
!= NULL
);
2282 return _bfd_elf_adjust_dynamic_copy (info
, h
, s
);
2285 /* Function : elf_arc_finish_dynamic_symbol
2286 Brief : Finish up dynamic symbol handling. We set the
2287 contents of various dynamic sections here.
2292 Returns : True/False as the return status. */
2295 elf_arc_finish_dynamic_symbol (bfd
* output_bfd
,
2296 struct bfd_link_info
*info
,
2297 struct elf_link_hash_entry
*h
,
2298 Elf_Internal_Sym
* sym
)
2300 if (h
->plt
.offset
!= (bfd_vma
) -1)
2302 relocate_plt_for_symbol (output_bfd
, info
, h
);
2304 if (!h
->def_regular
)
2306 /* Mark the symbol as undefined, rather than as defined in
2307 the .plt section. Leave the value alone. */
2308 sym
->st_shndx
= SHN_UNDEF
;
2312 if (h
->got
.glist
!= NULL
)
2314 struct got_entry
*list
= h
->got
.glist
;
2316 /* Traverse the list of got entries for this symbol. */
2319 bfd_vma got_offset
= h
->got
.glist
->offset
;
2321 if (list
->type
== GOT_NORMAL
2322 && list
->created_dyn_relocation
== FALSE
)
2324 if (bfd_link_pic (info
)
2325 && (info
->symbolic
|| h
->dynindx
== -1)
2328 ADD_RELA (output_bfd
, got
, got_offset
, 0, R_ARC_RELATIVE
, 0);
2330 /* Do not fully understand the side effects of this condition.
2331 The relocation space might still being reserved. Perhaps
2332 I should clear its value. */
2333 else if (h
->dynindx
!= -1)
2335 ADD_RELA (output_bfd
, got
, got_offset
, h
->dynindx
,
2338 list
->created_dyn_relocation
= TRUE
;
2340 else if (list
->existing_entries
!= TLS_GOT_NONE
)
2342 struct elf_link_hash_table
*htab
= elf_hash_table (info
);
2343 enum tls_got_entries e
= list
->existing_entries
;
2345 BFD_ASSERT (list
->type
!= GOT_TLS_GD
2346 || list
->existing_entries
== TLS_GOT_MOD_AND_OFF
);
2348 bfd_vma dynindx
= h
->dynindx
== -1 ? 0 : h
->dynindx
;
2349 if (e
== TLS_GOT_MOD_AND_OFF
|| e
== TLS_GOT_MOD
)
2351 ADD_RELA (output_bfd
, got
, got_offset
, dynindx
,
2352 R_ARC_TLS_DTPMOD
, 0);
2353 ARC_DEBUG ("arc_info: TLS_DYNRELOC: type = %d, \
2354 GOT_OFFSET = 0x%x, GOT_VMA = 0x%x, INDEX = %d, ADDEND = 0x%x\n",
2357 htab
->sgot
->output_section
->vma
2358 + htab
->sgot
->output_offset
+ got_offset
,
2361 if (e
== TLS_GOT_MOD_AND_OFF
|| e
== TLS_GOT_OFF
)
2364 if (list
->type
== GOT_TLS_IE
)
2365 addend
= bfd_get_32 (output_bfd
,
2366 htab
->sgot
->contents
+ got_offset
);
2368 ADD_RELA (output_bfd
, got
,
2369 got_offset
+ (e
== TLS_GOT_MOD_AND_OFF
? 4 : 0),
2371 (list
->type
== GOT_TLS_IE
?
2372 R_ARC_TLS_TPOFF
: R_ARC_TLS_DTPOFF
),
2375 ARC_DEBUG ("arc_info: TLS_DYNRELOC: type = %d, \
2376 GOT_OFFSET = 0x%x, GOT_VMA = 0x%x, INDEX = %d, ADDEND = 0x%x\n",
2379 htab
->sgot
->output_section
->vma
2380 + htab
->sgot
->output_offset
+ got_offset
,
2388 h
->got
.glist
= NULL
;
2393 bfd_vma rel_offset
= (h
->root
.u
.def
.value
2394 + h
->root
.u
.def
.section
->output_section
->vma
2395 + h
->root
.u
.def
.section
->output_offset
);
2398 bfd_get_section_by_name (h
->root
.u
.def
.section
->owner
,
2401 bfd_byte
* loc
= srelbss
->contents
2402 + (srelbss
->reloc_count
* sizeof (Elf32_External_Rela
));
2403 srelbss
->reloc_count
++;
2405 Elf_Internal_Rela rel
;
2407 rel
.r_offset
= rel_offset
;
2409 BFD_ASSERT (h
->dynindx
!= -1);
2410 rel
.r_info
= ELF32_R_INFO (h
->dynindx
, R_ARC_COPY
);
2412 bfd_elf32_swap_reloca_out (output_bfd
, &rel
, loc
);
2415 /* Mark _DYNAMIC and _GLOBAL_OFFSET_TABLE_ as absolute. */
2416 if (strcmp (h
->root
.root
.string
, "_DYNAMIC") == 0
2417 || strcmp (h
->root
.root
.string
, "__DYNAMIC") == 0
2418 || strcmp (h
->root
.root
.string
, "_GLOBAL_OFFSET_TABLE_") == 0)
2419 sym
->st_shndx
= SHN_ABS
;
2424 #define GET_SYMBOL_OR_SECTION(TAG, SYMBOL, SECTION) \
2426 if (SYMBOL != NULL) \
2427 h = elf_link_hash_lookup (elf_hash_table (info), \
2428 SYMBOL, FALSE, FALSE, TRUE); \
2429 else if (SECTION != NULL) \
2430 s = bfd_get_linker_section (dynobj, SECTION); \
2433 /* Function : elf_arc_finish_dynamic_sections
2434 Brief : Finish up the dynamic sections handling.
2439 Returns : True/False as the return status. */
2442 elf_arc_finish_dynamic_sections (bfd
* output_bfd
,
2443 struct bfd_link_info
*info
)
2445 struct dynamic_sections ds
= arc_create_dynamic_sections (output_bfd
, info
);
2446 struct elf_link_hash_table
*htab
= elf_hash_table (info
);
2447 bfd
*dynobj
= (elf_hash_table (info
))->dynobj
;
2451 Elf32_External_Dyn
*dyncon
, *dynconend
;
2453 dyncon
= (Elf32_External_Dyn
*) ds
.sdyn
->contents
;
2455 (Elf32_External_Dyn
*) (ds
.sdyn
->contents
+ ds
.sdyn
->size
);
2456 for (; dyncon
< dynconend
; dyncon
++)
2458 Elf_Internal_Dyn internal_dyn
;
2459 bfd_boolean do_it
= FALSE
;
2461 struct elf_link_hash_entry
*h
= NULL
;
2464 bfd_elf32_swap_dyn_in (dynobj
, dyncon
, &internal_dyn
);
2466 switch (internal_dyn
.d_tag
)
2468 GET_SYMBOL_OR_SECTION (DT_INIT
, "_init", NULL
)
2469 GET_SYMBOL_OR_SECTION (DT_FINI
, "_fini", NULL
)
2470 GET_SYMBOL_OR_SECTION (DT_PLTGOT
, NULL
, ".plt")
2471 GET_SYMBOL_OR_SECTION (DT_JMPREL
, NULL
, ".rela.plt")
2472 GET_SYMBOL_OR_SECTION (DT_PLTRELSZ
, NULL
, ".rela.plt")
2473 GET_SYMBOL_OR_SECTION (DT_RELASZ
, NULL
, ".rela.plt")
2474 GET_SYMBOL_OR_SECTION (DT_VERSYM
, NULL
, ".gnu.version")
2475 GET_SYMBOL_OR_SECTION (DT_VERDEF
, NULL
, ".gnu.version_d")
2476 GET_SYMBOL_OR_SECTION (DT_VERNEED
, NULL
, ".gnu.version_r")
2481 /* In case the dynamic symbols should be updated with a symbol. */
2483 && (h
->root
.type
== bfd_link_hash_defined
2484 || h
->root
.type
== bfd_link_hash_defweak
))
2488 internal_dyn
.d_un
.d_val
= h
->root
.u
.def
.value
;
2489 asec_ptr
= h
->root
.u
.def
.section
;
2490 if (asec_ptr
->output_section
!= NULL
)
2492 internal_dyn
.d_un
.d_val
+=
2493 (asec_ptr
->output_section
->vma
+
2494 asec_ptr
->output_offset
);
2498 /* The symbol is imported from another shared
2499 library and does not apply to this one. */
2500 internal_dyn
.d_un
.d_val
= 0;
2504 else if (s
!= NULL
) /* With a section information. */
2506 switch (internal_dyn
.d_tag
)
2513 internal_dyn
.d_un
.d_ptr
= (s
->output_section
->vma
2514 + s
->output_offset
);
2519 internal_dyn
.d_un
.d_val
= s
->size
;
2525 internal_dyn
.d_un
.d_val
-= s
->size
;
2535 bfd_elf32_swap_dyn_out (output_bfd
, &internal_dyn
, dyncon
);
2538 if (htab
->splt
->size
> 0)
2540 relocate_plt_for_entry (output_bfd
, info
);
2543 /* TODO: Validate this. */
2544 elf_section_data (htab
->srelplt
->output_section
)->this_hdr
.sh_entsize
2548 /* Fill in the first three entries in the global offset table. */
2551 if (htab
->sgot
->size
> 0 || htab
->sgotplt
->size
> 0)
2553 if (ds
.sdyn
== NULL
)
2554 bfd_put_32 (output_bfd
, (bfd_vma
) 0,
2555 htab
->sgotplt
->contents
);
2557 bfd_put_32 (output_bfd
,
2558 ds
.sdyn
->output_section
->vma
+ ds
.sdyn
->output_offset
,
2559 htab
->sgotplt
->contents
);
2560 bfd_put_32 (output_bfd
, (bfd_vma
) 0, htab
->sgotplt
->contents
+ 4);
2561 bfd_put_32 (output_bfd
, (bfd_vma
) 0, htab
->sgotplt
->contents
+ 8);
2568 #define ADD_DYNAMIC_SYMBOL(NAME, TAG) \
2569 h = elf_link_hash_lookup (elf_hash_table (info), \
2570 NAME, FALSE, FALSE, FALSE); \
2571 if ((h != NULL && (h->ref_regular || h->def_regular))) \
2572 if (! _bfd_elf_add_dynamic_entry (info, TAG, 0)) \
2575 /* Set the sizes of the dynamic sections. */
2577 elf_arc_size_dynamic_sections (bfd
* output_bfd
,
2578 struct bfd_link_info
*info
)
2582 bfd_boolean relocs_exist
= FALSE
;
2583 bfd_boolean reltext_exist
= FALSE
;
2584 struct dynamic_sections ds
= arc_create_dynamic_sections (output_bfd
, info
);
2585 struct elf_link_hash_table
*htab
= elf_hash_table (info
);
2587 dynobj
= (elf_hash_table (info
))->dynobj
;
2588 BFD_ASSERT (dynobj
!= NULL
);
2590 if ((elf_hash_table (info
))->dynamic_sections_created
)
2592 struct elf_link_hash_entry
*h
;
2594 /* Set the contents of the .interp section to the
2596 if (!bfd_link_pic (info
))
2598 s
= bfd_get_section_by_name (dynobj
, ".interp");
2599 BFD_ASSERT (s
!= NULL
);
2600 s
->size
= sizeof (ELF_DYNAMIC_INTERPRETER
);
2601 s
->contents
= (unsigned char *) ELF_DYNAMIC_INTERPRETER
;
2604 /* Add some entries to the .dynamic section. We fill in some of
2605 the values later, in elf_bfd_final_link, but we must add the
2606 entries now so that we know the final size of the .dynamic
2607 section. Checking if the .init section is present. We also
2608 create DT_INIT and DT_FINI entries if the init_str has been
2609 changed by the user. */
2610 ADD_DYNAMIC_SYMBOL ("init", DT_INIT
);
2611 ADD_DYNAMIC_SYMBOL ("fini", DT_FINI
);
2615 /* We may have created entries in the .rela.got section.
2616 However, if we are not creating the dynamic sections, we will
2617 not actually use these entries. Reset the size of .rela.got,
2618 which will cause it to get stripped from the output file
2620 if (htab
->srelgot
!= NULL
)
2621 htab
->srelgot
->size
= 0;
2624 if (htab
->splt
!= NULL
&& htab
->splt
->size
== 0)
2625 htab
->splt
->flags
|= SEC_EXCLUDE
;
2626 for (s
= dynobj
->sections
; s
!= NULL
; s
= s
->next
)
2628 if ((s
->flags
& SEC_LINKER_CREATED
) == 0)
2631 if (strncmp (s
->name
, ".rela", 5) == 0)
2635 s
->flags
|= SEC_EXCLUDE
;
2639 if (strcmp (s
->name
, ".rela.plt") != 0)
2641 const char *outname
=
2642 bfd_get_section_name (output_bfd
,
2643 htab
->srelplt
->output_section
);
2645 asection
*target
= bfd_get_section_by_name (output_bfd
,
2648 relocs_exist
= TRUE
;
2649 if (target
!= NULL
&& target
->size
!= 0
2650 && (target
->flags
& SEC_READONLY
) != 0
2651 && (target
->flags
& SEC_ALLOC
) != 0)
2652 reltext_exist
= TRUE
;
2656 /* We use the reloc_count field as a counter if we need to
2657 copy relocs into the output file. */
2661 if (strcmp (s
->name
, ".dynamic") == 0)
2665 s
->contents
= (bfd_byte
*) bfd_zalloc (dynobj
, s
->size
);
2667 if (s
->contents
== NULL
&& s
->size
!= 0)
2673 /* TODO: Check if this is needed. */
2674 if (!bfd_link_pic (info
))
2675 if (!_bfd_elf_add_dynamic_entry (info
, DT_DEBUG
, 0))
2678 if (htab
->splt
&& (htab
->splt
->flags
& SEC_EXCLUDE
) == 0)
2679 if (!_bfd_elf_add_dynamic_entry (info
, DT_PLTGOT
, 0)
2680 || !_bfd_elf_add_dynamic_entry (info
, DT_PLTRELSZ
, 0)
2681 || !_bfd_elf_add_dynamic_entry (info
, DT_PLTREL
, DT_RELA
)
2682 || !_bfd_elf_add_dynamic_entry (info
, DT_JMPREL
, 0)
2686 if (relocs_exist
== TRUE
)
2687 if (!_bfd_elf_add_dynamic_entry (info
, DT_RELA
, 0)
2688 || !_bfd_elf_add_dynamic_entry (info
, DT_RELASZ
, 0)
2689 || !_bfd_elf_add_dynamic_entry (info
, DT_RELENT
,
2690 sizeof (Elf32_External_Rela
))
2694 if (reltext_exist
== TRUE
)
2695 if (!_bfd_elf_add_dynamic_entry (info
, DT_TEXTREL
, 0))
2702 const struct elf_size_info arc_elf32_size_info
=
2704 sizeof (Elf32_External_Ehdr
),
2705 sizeof (Elf32_External_Phdr
),
2706 sizeof (Elf32_External_Shdr
),
2707 sizeof (Elf32_External_Rel
),
2708 sizeof (Elf32_External_Rela
),
2709 sizeof (Elf32_External_Sym
),
2710 sizeof (Elf32_External_Dyn
),
2711 sizeof (Elf_External_Note
),
2715 ELFCLASS32
, EV_CURRENT
,
2716 bfd_elf32_write_out_phdrs
,
2717 bfd_elf32_write_shdrs_and_ehdr
,
2718 bfd_elf32_checksum_contents
,
2719 bfd_elf32_write_relocs
,
2720 bfd_elf32_swap_symbol_in
,
2721 bfd_elf32_swap_symbol_out
,
2722 bfd_elf32_slurp_reloc_table
,
2723 bfd_elf32_slurp_symbol_table
,
2724 bfd_elf32_swap_dyn_in
,
2725 bfd_elf32_swap_dyn_out
,
2726 bfd_elf32_swap_reloc_in
,
2727 bfd_elf32_swap_reloc_out
,
2728 bfd_elf32_swap_reloca_in
,
2729 bfd_elf32_swap_reloca_out
2732 #define elf_backend_size_info arc_elf32_size_info
2734 static struct bfd_link_hash_table
*
2735 arc_elf_link_hash_table_create (bfd
*abfd
)
2737 struct elf_link_hash_table
*htab
;
2739 htab
= bfd_zmalloc (sizeof (*htab
));
2743 if (!_bfd_elf_link_hash_table_init (htab
, abfd
,
2744 _bfd_elf_link_hash_newfunc
,
2745 sizeof (struct elf_link_hash_entry
),
2752 htab
->init_got_refcount
.refcount
= 0;
2753 htab
->init_got_refcount
.glist
= NULL
;
2754 htab
->init_got_offset
.offset
= 0;
2755 htab
->init_got_offset
.glist
= NULL
;
2756 return (struct bfd_link_hash_table
*) htab
;
2759 /* Hook called by the linker routine which adds symbols from an object
2763 elf_arc_add_symbol_hook (bfd
* abfd
,
2764 struct bfd_link_info
* info
,
2765 Elf_Internal_Sym
* sym
,
2766 const char ** namep ATTRIBUTE_UNUSED
,
2767 flagword
* flagsp ATTRIBUTE_UNUSED
,
2768 asection
** secp ATTRIBUTE_UNUSED
,
2769 bfd_vma
* valp ATTRIBUTE_UNUSED
)
2771 if (ELF_ST_TYPE (sym
->st_info
) == STT_GNU_IFUNC
2772 && (abfd
->flags
& DYNAMIC
) == 0
2773 && bfd_get_flavour (info
->output_bfd
) == bfd_target_elf_flavour
)
2774 elf_tdata (info
->output_bfd
)->has_gnu_symbols
|= elf_gnu_symbol_ifunc
;
2779 #define TARGET_LITTLE_SYM arc_elf32_le_vec
2780 #define TARGET_LITTLE_NAME "elf32-littlearc"
2781 #define TARGET_BIG_SYM arc_elf32_be_vec
2782 #define TARGET_BIG_NAME "elf32-bigarc"
2783 #define ELF_ARCH bfd_arch_arc
2784 #define ELF_MACHINE_CODE EM_ARC_COMPACT
2785 #define ELF_MACHINE_ALT1 EM_ARC_COMPACT2
2786 #define ELF_MAXPAGESIZE 0x2000
2788 #define bfd_elf32_bfd_link_hash_table_create arc_elf_link_hash_table_create
2790 #define bfd_elf32_bfd_merge_private_bfd_data arc_elf_merge_private_bfd_data
2791 #define bfd_elf32_bfd_reloc_type_lookup arc_elf32_bfd_reloc_type_lookup
2792 #define bfd_elf32_bfd_set_private_flags arc_elf_set_private_flags
2793 #define bfd_elf32_bfd_print_private_bfd_data arc_elf_print_private_bfd_data
2794 #define bfd_elf32_bfd_copy_private_bfd_data arc_elf_copy_private_bfd_data
2796 #define elf_info_to_howto_rel arc_info_to_howto_rel
2797 #define elf_backend_object_p arc_elf_object_p
2798 #define elf_backend_final_write_processing arc_elf_final_write_processing
2800 #define elf_backend_relocate_section elf_arc_relocate_section
2801 #define elf_backend_check_relocs elf_arc_check_relocs
2802 #define elf_backend_create_dynamic_sections _bfd_elf_create_dynamic_sections
2804 #define elf_backend_adjust_dynamic_symbol elf_arc_adjust_dynamic_symbol
2805 #define elf_backend_finish_dynamic_symbol elf_arc_finish_dynamic_symbol
2807 #define elf_backend_finish_dynamic_sections elf_arc_finish_dynamic_sections
2808 #define elf_backend_size_dynamic_sections elf_arc_size_dynamic_sections
2809 #define elf_backend_add_symbol_hook elf_arc_add_symbol_hook
2811 #define elf_backend_can_gc_sections 1
2812 #define elf_backend_want_got_plt 1
2813 #define elf_backend_plt_readonly 1
2814 #define elf_backend_rela_plts_and_copies_p 1
2815 #define elf_backend_want_plt_sym 0
2816 #define elf_backend_got_header_size 12
2818 #define elf_backend_may_use_rel_p 0
2819 #define elf_backend_may_use_rela_p 1
2820 #define elf_backend_default_use_rela_p 1
2822 #define elf_backend_default_execstack 0
2824 #include "elf32-target.h"