Fixes done to TLS.
[binutils-gdb.git] / bfd / elf32-arc.c
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).
4
5 This file is part of BFD, the Binary File Descriptor library.
6
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.
11
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.
16
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. */
21
22 #include "sysdep.h"
23 #include "bfd.h"
24 #include "libbfd.h"
25 #include "elf-bfd.h"
26 #include "elf/arc.h"
27 #include "libiberty.h"
28 #include "opcode/arc-func.h"
29 #include "opcode/arc.h"
30 #include "arc-plt.h"
31
32 #ifdef DEBUG
33 # define PR_DEBUG(fmt, args...) fprintf (stderr, fmt, ##args)
34 #else
35 # define PR_DEBUG(fmt, args...)
36 #endif
37
38 /* #define ARC_ENABLE_DEBUG 1 */
39 #ifndef ARC_ENABLE_DEBUG
40 #define ARC_DEBUG(...)
41 #else
42 static char *
43 name_for_global_symbol (struct elf_link_hash_entry *h)
44 {
45 static char *local_str = "(local)";
46 if (h == NULL)
47 return local_str;
48 else
49 return h->root.root.string;
50 }
51 #define ARC_DEBUG(args...) fprintf (stderr, ##args)
52 #endif
53
54
55 #define ADD_RELA(BFD, SECTION, OFFSET, SYM_IDX, TYPE, ADDEND) \
56 { \
57 struct elf_link_hash_table *_htab = elf_hash_table (info); \
58 Elf_Internal_Rela _rel; \
59 bfd_byte * _loc; \
60 \
61 BFD_ASSERT (_htab->srel##SECTION &&_htab->srel##SECTION->contents); \
62 _loc = _htab->srel##SECTION->contents \
63 + ((_htab->srel##SECTION->reloc_count) \
64 * sizeof (Elf32_External_Rela)); \
65 _htab->srel##SECTION->reloc_count++; \
66 _rel.r_addend = ADDEND; \
67 _rel.r_offset = (_htab->s##SECTION)->output_section->vma \
68 + (_htab->s##SECTION)->output_offset + OFFSET; \
69 BFD_ASSERT ((long) SYM_IDX != -1); \
70 _rel.r_info = ELF32_R_INFO (SYM_IDX, TYPE); \
71 bfd_elf32_swap_reloca_out (BFD, &_rel, _loc); \
72 }
73
74 struct dynamic_sections
75 {
76 bfd_boolean initialized;
77 asection * sgot;
78 asection * srelgot;
79 asection * sgotplt;
80 asection * srelgotplt;
81 asection * sdyn;
82 asection * splt;
83 asection * srelplt;
84 };
85
86 enum dyn_section_types
87 {
88 got = 0,
89 relgot,
90 gotplt,
91 dyn,
92 plt,
93 relplt,
94 DYN_SECTION_TYPES_END
95 };
96
97 const char * dyn_section_names[DYN_SECTION_TYPES_END] =
98 {
99 ".got",
100 ".rela.got",
101 ".got.plt",
102 ".dynamic",
103 ".plt",
104 ".rela.plt"
105 };
106
107
108 /* The default symbols representing the init and fini dyn values.
109 TODO: Check what is the relation of those strings with arclinux.em
110 and DT_INIT. */
111 #define INIT_SYM_STRING "_init"
112 #define FINI_SYM_STRING "_fini"
113
114 char * init_str = INIT_SYM_STRING;
115 char * fini_str = FINI_SYM_STRING;
116
117 #define ARC_RELOC_HOWTO(TYPE, VALUE, SIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
118 case VALUE: \
119 return "R_" #TYPE; \
120 break;
121
122 static ATTRIBUTE_UNUSED const char *
123 reloc_type_to_name (unsigned int type)
124 {
125 switch (type)
126 {
127 #include "elf/arc-reloc.def"
128
129 default:
130 return "UNKNOWN";
131 break;
132 }
133 }
134 #undef ARC_RELOC_HOWTO
135
136 /* Try to minimize the amount of space occupied by relocation tables
137 on the ROM (not that the ROM won't be swamped by other ELF overhead). */
138
139 #define USE_REL 1
140
141 static ATTRIBUTE_UNUSED bfd_boolean
142 is_reloc_PC_relative (reloc_howto_type *howto)
143 {
144 return (strstr (howto->name, "PC") != NULL) ? TRUE : FALSE;
145 }
146
147 static bfd_boolean
148 is_reloc_SDA_relative (reloc_howto_type *howto)
149 {
150 return (strstr (howto->name, "SDA") != NULL) ? TRUE : FALSE;
151 }
152
153 static bfd_boolean
154 is_reloc_for_GOT (reloc_howto_type * howto)
155 {
156 if (strstr (howto->name, "TLS") != NULL)
157 return FALSE;
158 return (strstr (howto->name, "GOT") != NULL) ? TRUE : FALSE;
159 }
160
161 static bfd_boolean
162 is_reloc_for_PLT (reloc_howto_type * howto)
163 {
164 return (strstr (howto->name, "PLT") != NULL) ? TRUE : FALSE;
165 }
166
167 static bfd_boolean
168 is_reloc_for_TLS (reloc_howto_type *howto)
169 {
170 return (strstr (howto->name, "TLS") != NULL) ? TRUE : FALSE;
171 }
172
173 struct arc_relocation_data
174 {
175 bfd_signed_vma reloc_offset;
176 bfd_signed_vma reloc_addend;
177 bfd_signed_vma got_offset_value;
178
179 bfd_signed_vma sym_value;
180 asection * sym_section;
181
182 reloc_howto_type *howto;
183
184 asection * input_section;
185
186 bfd_signed_vma sdata_begin_symbol_vma;
187 bfd_boolean sdata_begin_symbol_vma_set;
188 bfd_signed_vma got_symbol_vma;
189
190 bfd_boolean should_relocate;
191
192 const char * symbol_name;
193 };
194
195 /* Should be included at this location due to static declarations
196 * defined before this point. */
197 #include "arc-got.h"
198
199 #define arc_bfd_get_8(A,B,C) bfd_get_8(A,B)
200 #define arc_bfd_get_16(A,B,C) bfd_get_16(A,B)
201 #define arc_bfd_get_32(A,B,C) bfd_get_32(A,B)
202 #define arc_bfd_put_8(A,B,C,D) bfd_put_8(A,B,C)
203 #define arc_bfd_put_16(A,B,C,D) bfd_put_16(A,B,C)
204 #define arc_bfd_put_32(A,B,C,D) bfd_put_32(A,B,C)
205
206
207 static bfd_reloc_status_type
208 arc_elf_reloc (bfd *abfd ATTRIBUTE_UNUSED,
209 arelent *reloc_entry,
210 asymbol *symbol_in,
211 void *data ATTRIBUTE_UNUSED,
212 asection *input_section,
213 bfd *output_bfd,
214 char ** error_message ATTRIBUTE_UNUSED)
215 {
216 if (output_bfd != NULL)
217 {
218 reloc_entry->address += input_section->output_offset;
219
220 /* In case of relocateable link and if the reloc is against a
221 section symbol, the addend needs to be adjusted according to
222 where the section symbol winds up in the output section. */
223 if ((symbol_in->flags & BSF_SECTION_SYM) && symbol_in->section)
224 reloc_entry->addend += symbol_in->section->output_offset;
225
226 return bfd_reloc_ok;
227 }
228
229 return bfd_reloc_continue;
230 }
231
232
233 #define ARC_RELOC_HOWTO(TYPE, VALUE, SIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
234 TYPE = VALUE,
235 enum howto_list
236 {
237 #include "elf/arc-reloc.def"
238 HOWTO_LIST_LAST
239 };
240 #undef ARC_RELOC_HOWTO
241
242 #define ARC_RELOC_HOWTO(TYPE, VALUE, RSIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
243 [TYPE] = HOWTO (R_##TYPE, 0, RSIZE, BITSIZE, FALSE, 0, complain_overflow_##OVERFLOW, arc_elf_reloc, "R_" #TYPE, FALSE, 0, 0, FALSE),
244
245 static struct reloc_howto_struct elf_arc_howto_table[] =
246 {
247 #include "elf/arc-reloc.def"
248 /* Example of what is generated by the preprocessor. Currently kept as an
249 example.
250 HOWTO (R_ARC_NONE, // Type.
251 0, // Rightshift.
252 2, // Size (0 = byte, 1 = short, 2 = long).
253 32, // Bitsize.
254 FALSE, // PC_relative.
255 0, // Bitpos.
256 complain_overflow_bitfield, // Complain_on_overflow.
257 bfd_elf_generic_reloc, // Special_function.
258 "R_ARC_NONE", // Name.
259 TRUE, // Partial_inplace.
260 0, // Src_mask.
261 0, // Dst_mask.
262 FALSE), // PCrel_offset.
263 */
264 };
265 #undef ARC_RELOC_HOWTO
266
267 static void arc_elf_howto_init (void)
268 {
269 #define ARC_RELOC_HOWTO(TYPE, VALUE, SIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
270 elf_arc_howto_table[TYPE].pc_relative = \
271 (strstr (#FORMULA, " P ") != NULL || strstr (#FORMULA, " PDATA ") != NULL); \
272 elf_arc_howto_table[TYPE].dst_mask = RELOC_FUNCTION(0, ~0); \
273 /* Only 32 bit data relocations should be marked as ME. */ \
274 if (strstr (#FORMULA, " ME ") != NULL) \
275 { \
276 BFD_ASSERT (SIZE == 2); \
277 }
278
279 #include "elf/arc-reloc.def"
280
281 }
282 #undef ARC_RELOC_HOWTO
283
284
285 #define ARC_RELOC_HOWTO(TYPE, VALUE, SIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
286 [TYPE] = VALUE,
287 const int howto_table_lookup[] =
288 {
289 #include "elf/arc-reloc.def"
290 };
291 #undef ARC_RELOC_HOWTO
292
293 static reloc_howto_type *
294 arc_elf_howto (unsigned int r_type)
295 {
296 if (elf_arc_howto_table[R_ARC_32].dst_mask == 0)
297 arc_elf_howto_init ();
298 return &elf_arc_howto_table[r_type];
299 }
300
301 /* Map BFD reloc types to ARC ELF reloc types. */
302
303 struct arc_reloc_map
304 {
305 bfd_reloc_code_real_type bfd_reloc_val;
306 unsigned char elf_reloc_val;
307 };
308
309 #define ARC_RELOC_HOWTO(TYPE, VALUE, SIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
310 { BFD_RELOC_##TYPE, R_##TYPE },
311 static const struct arc_reloc_map arc_reloc_map[] =
312 {
313 #include "elf/arc-reloc.def"
314
315 {BFD_RELOC_NONE, R_ARC_NONE},
316 {BFD_RELOC_8, R_ARC_8},
317 {BFD_RELOC_16, R_ARC_16},
318 {BFD_RELOC_24, R_ARC_24},
319 {BFD_RELOC_32, R_ARC_32},
320 };
321 #undef ARC_RELOC_HOWTO
322
323 typedef ATTRIBUTE_UNUSED bfd_vma (*replace_func) (unsigned, int ATTRIBUTE_UNUSED);
324
325 #define ARC_RELOC_HOWTO(TYPE, VALUE, SIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
326 case TYPE: \
327 func = (void *) RELOC_FUNCTION; \
328 break;
329 static replace_func
330 get_replace_function (bfd *abfd, unsigned int r_type)
331 {
332 void *func = NULL;
333
334 switch (r_type)
335 {
336 #include "elf/arc-reloc.def"
337 }
338
339 if (func == replace_bits24 && bfd_big_endian (abfd))
340 return (replace_func) replace_bits24_be;
341
342 return (replace_func) func;
343 }
344 #undef ARC_RELOC_HOWTO
345
346 static reloc_howto_type *
347 arc_elf32_bfd_reloc_type_lookup (bfd * abfd ATTRIBUTE_UNUSED,
348 bfd_reloc_code_real_type code)
349 {
350 unsigned int i;
351
352 for (i = ARRAY_SIZE (arc_reloc_map); i--;)
353 {
354 if (arc_reloc_map[i].bfd_reloc_val == code)
355 return arc_elf_howto (arc_reloc_map[i].elf_reloc_val);
356 }
357
358 return NULL;
359 }
360
361 /* Function to set the ELF flag bits. */
362 static bfd_boolean
363 arc_elf_set_private_flags (bfd *abfd, flagword flags)
364 {
365 elf_elfheader (abfd)->e_flags = flags;
366 elf_flags_init (abfd) = TRUE;
367 return TRUE;
368 }
369
370 /* Print private flags. */
371 static bfd_boolean
372 arc_elf_print_private_bfd_data (bfd *abfd, void * ptr)
373 {
374 FILE *file = (FILE *) ptr;
375 flagword flags;
376
377 BFD_ASSERT (abfd != NULL && ptr != NULL);
378
379 /* Print normal ELF private data. */
380 _bfd_elf_print_private_bfd_data (abfd, ptr);
381
382 flags = elf_elfheader (abfd)->e_flags;
383 fprintf (file, _("private flags = 0x%lx:"), (unsigned long) flags);
384
385 switch (flags & EF_ARC_MACH_MSK)
386 {
387 case EF_ARC_CPU_ARCV2HS : fprintf (file, " -mcpu=ARCv2HS"); break;
388 case EF_ARC_CPU_ARCV2EM : fprintf (file, " -mcpu=ARCv2EM"); break;
389 case E_ARC_MACH_ARC600 : fprintf (file, " -mcpu=ARC600"); break;
390 case E_ARC_MACH_ARC601 : fprintf (file, " -mcpu=ARC601"); break;
391 case E_ARC_MACH_ARC700 : fprintf (file, " -mcpu=ARC700"); break;
392 default:
393 fprintf (file, "-mcpu=unknown");
394 break;
395 }
396
397 switch (flags & EF_ARC_OSABI_MSK)
398 {
399 case E_ARC_OSABI_ORIG : fprintf (file, " (ABI:legacy)"); break;
400 case E_ARC_OSABI_V2 : fprintf (file, " (ABI:v2)"); break;
401 case E_ARC_OSABI_V3 : fprintf (file, " (ABI:v3)"); break;
402 default:
403 fprintf (file, "(ABI:unknown)");
404 break;
405 }
406
407 fputc ('\n', file);
408 return TRUE;
409 }
410
411 /* Copy backend specific data from one object module to another. */
412
413 static bfd_boolean
414 arc_elf_copy_private_bfd_data (bfd *ibfd, bfd *obfd)
415 {
416 if (bfd_get_flavour (ibfd) != bfd_target_elf_flavour
417 || bfd_get_flavour (obfd) != bfd_target_elf_flavour)
418 return TRUE;
419
420 BFD_ASSERT (!elf_flags_init (obfd)
421 || elf_elfheader (obfd)->e_flags == elf_elfheader (ibfd)->e_flags);
422
423 elf_elfheader (obfd)->e_flags = elf_elfheader (ibfd)->e_flags;
424 elf_flags_init (obfd) = TRUE;
425
426 /* Copy object attributes. */
427 _bfd_elf_copy_obj_attributes (ibfd, obfd);
428
429 return _bfd_elf_copy_private_bfd_data (ibfd, obfd);
430 }
431
432 static reloc_howto_type *
433 bfd_elf32_bfd_reloc_name_lookup (bfd * abfd ATTRIBUTE_UNUSED,
434 const char *r_name)
435 {
436 unsigned int i;
437
438 for (i = 0; i < ARRAY_SIZE (elf_arc_howto_table); i++)
439 if (elf_arc_howto_table[i].name != NULL
440 && strcasecmp (elf_arc_howto_table[i].name, r_name) == 0)
441 return arc_elf_howto (i);
442
443 return NULL;
444 }
445
446 /* Set the howto pointer for an ARC ELF reloc. */
447
448 static void
449 arc_info_to_howto_rel (bfd * abfd ATTRIBUTE_UNUSED,
450 arelent * cache_ptr,
451 Elf_Internal_Rela * dst)
452 {
453 unsigned int r_type;
454
455 r_type = ELF32_R_TYPE (dst->r_info);
456 BFD_ASSERT (r_type < (unsigned int) R_ARC_max);
457 cache_ptr->howto = arc_elf_howto (r_type);
458 }
459
460 /* Merge backend specific data from an object file to the output
461 object file when linking. */
462
463 static bfd_boolean
464 arc_elf_merge_private_bfd_data (bfd *ibfd, bfd *obfd)
465 {
466 unsigned short mach_ibfd;
467 static unsigned short mach_obfd = EM_NONE;
468 flagword out_flags;
469 flagword in_flags;
470 asection *sec;
471
472 /* Check if we have the same endianess. */
473 if (! _bfd_generic_verify_endian_match (ibfd, obfd))
474 {
475 _bfd_error_handler (_("ERROR: Endian Match failed. Attempting to link "
476 "%B with binary %s of opposite endian-ness"),
477 ibfd, bfd_get_filename (obfd));
478 return FALSE;
479 }
480
481 /* Collect ELF flags. */
482 in_flags = elf_elfheader (ibfd)->e_flags & EF_ARC_MACH_MSK;
483 out_flags = elf_elfheader (obfd)->e_flags & EF_ARC_MACH_MSK;
484
485 if (!elf_flags_init (obfd)) /* First call, no flags set. */
486 {
487 elf_flags_init (obfd) = TRUE;
488 out_flags = in_flags;
489 }
490
491 if (bfd_get_flavour (ibfd) != bfd_target_elf_flavour
492 || bfd_get_flavour (obfd) != bfd_target_elf_flavour)
493 return TRUE;
494
495 /* Check to see if the input BFD actually contains any sections. Do
496 not short-circuit dynamic objects; their section list may be
497 emptied by elf_link_add_object_symbols. */
498 if (!(ibfd->flags & DYNAMIC))
499 {
500 bfd_boolean null_input_bfd = TRUE;
501 bfd_boolean only_data_sections = TRUE;
502
503 for (sec = ibfd->sections; sec != NULL; sec = sec->next)
504 {
505 if ((bfd_get_section_flags (ibfd, sec)
506 & (SEC_LOAD | SEC_CODE | SEC_HAS_CONTENTS))
507 == (SEC_LOAD | SEC_CODE | SEC_HAS_CONTENTS))
508 only_data_sections = FALSE;
509
510 null_input_bfd = FALSE;
511 }
512
513 if (null_input_bfd || only_data_sections)
514 return TRUE;
515 }
516
517 /* Complain about various flag/architecture mismatches. */
518 mach_ibfd = elf_elfheader (ibfd)->e_machine;
519 if (mach_obfd == EM_NONE)
520 {
521 mach_obfd = mach_ibfd;
522 }
523 else
524 {
525 if (mach_ibfd != mach_obfd)
526 {
527 _bfd_error_handler (_("ERROR: Attempting to link %B "
528 "with a binary %s of different architecture"),
529 ibfd, bfd_get_filename (obfd));
530 return FALSE;
531 }
532 else if (in_flags != out_flags)
533 {
534 /* Warn if different flags. */
535 (*_bfd_error_handler)
536 (_("%s: uses different e_flags (0x%lx) fields than "
537 "previous modules (0x%lx)"),
538 bfd_get_filename (ibfd), (long)in_flags, (long)out_flags);
539 if (in_flags && out_flags)
540 return FALSE;
541 /* MWDT doesnt set the eflags hence make sure we choose the
542 eflags set by gcc. */
543 in_flags = in_flags > out_flags ? in_flags : out_flags;
544 }
545 }
546
547 /* Update the flags. */
548 elf_elfheader (obfd)->e_flags = in_flags;
549
550 if (bfd_get_mach (obfd) < bfd_get_mach (ibfd))
551 {
552 return bfd_set_arch_mach (obfd, bfd_arch_arc, bfd_get_mach (ibfd));
553 }
554
555 return TRUE;
556 }
557
558 /* Set the right machine number for an ARC ELF file. */
559 static bfd_boolean
560 arc_elf_object_p (bfd * abfd)
561 {
562 /* Make sure this is initialised, or you'll have the potential of passing
563 garbage---or misleading values---into the call to
564 bfd_default_set_arch_mach (). */
565 int mach = bfd_mach_arc_arc700;
566 unsigned long arch = elf_elfheader (abfd)->e_flags & EF_ARC_MACH_MSK;
567 unsigned e_machine = elf_elfheader (abfd)->e_machine;
568
569 if (e_machine == EM_ARC_COMPACT || e_machine == EM_ARC_COMPACT2)
570 {
571 switch (arch)
572 {
573 case E_ARC_MACH_ARC600:
574 mach = bfd_mach_arc_arc600;
575 break;
576 case E_ARC_MACH_ARC601:
577 mach = bfd_mach_arc_arc601;
578 break;
579 case E_ARC_MACH_ARC700:
580 mach = bfd_mach_arc_arc700;
581 break;
582 case EF_ARC_CPU_ARCV2HS:
583 case EF_ARC_CPU_ARCV2EM:
584 mach = bfd_mach_arc_arcv2;
585 break;
586 default:
587 mach = (e_machine == EM_ARC_COMPACT)
588 ? bfd_mach_arc_arc700 : bfd_mach_arc_arcv2;
589 break;
590 }
591 }
592 else
593 {
594 if (e_machine == EM_ARC)
595 {
596 (*_bfd_error_handler)
597 (_("Error: The ARC4 architecture is no longer supported.\n"));
598 return FALSE;
599 }
600 else
601 {
602 (*_bfd_error_handler)
603 (_("Warning: unset or old architecture flags. \n"
604 " Use default machine.\n"));
605 }
606 }
607
608 return bfd_default_set_arch_mach (abfd, bfd_arch_arc, mach);
609 }
610
611 /* The final processing done just before writing out an ARC ELF object file.
612 This gets the ARC architecture right based on the machine number. */
613
614 static void
615 arc_elf_final_write_processing (bfd * abfd,
616 bfd_boolean linker ATTRIBUTE_UNUSED)
617 {
618 unsigned long emf;
619
620 switch (bfd_get_mach (abfd))
621 {
622 case bfd_mach_arc_arc600:
623 emf = EM_ARC_COMPACT;
624 break;
625 case bfd_mach_arc_arc601:
626 emf = EM_ARC_COMPACT;
627 break;
628 case bfd_mach_arc_arc700:
629 emf = EM_ARC_COMPACT;
630 break;
631 case bfd_mach_arc_arcv2:
632 emf = EM_ARC_COMPACT2;
633 break;
634 default:
635 goto DO_NOTHING;
636 }
637
638 elf_elfheader (abfd)->e_machine = emf;
639
640 /* Record whatever is the current syscall ABI version. */
641 elf_elfheader (abfd)->e_flags |= E_ARC_OSABI_CURRENT;
642
643 DO_NOTHING:
644 return;
645 }
646
647 #define BFD_DEBUG_PIC(...)
648
649
650 static void
651 debug_arc_reloc (struct arc_relocation_data reloc_data)
652 {
653 PR_DEBUG ("Reloc type=%s, should_relocate = %s\n",
654 reloc_data.howto->name,
655 reloc_data.should_relocate ? "true" : "false");
656 PR_DEBUG (" offset = 0x%x, addend = 0x%x\n",
657 (unsigned int) reloc_data.reloc_offset,
658 (unsigned int) reloc_data.reloc_addend);
659 PR_DEBUG (" Symbol:\n");
660 PR_DEBUG (" value = 0x%08x\n",
661 (unsigned int) reloc_data.sym_value);
662 if (reloc_data.sym_section != NULL)
663 {
664 PR_DEBUG (" Symbol Section:\n");
665 PR_DEBUG (
666 " section name = %s, output_offset 0x%08x",
667 reloc_data.sym_section->name,
668 (unsigned int) reloc_data.sym_section->output_offset);
669 if (reloc_data.sym_section->output_section != NULL)
670 {
671 PR_DEBUG (
672 ", output_section->vma = 0x%08x",
673 ((unsigned int) reloc_data.sym_section->output_section->vma));
674 }
675 PR_DEBUG ( "\n");
676 PR_DEBUG (" file: %s\n", reloc_data.sym_section->owner->filename);
677 }
678 else
679 {
680 PR_DEBUG ( " symbol section is NULL\n");
681 }
682
683 PR_DEBUG ( " Input_section:\n");
684 if (reloc_data.input_section != NULL)
685 {
686 PR_DEBUG (
687 " section name = %s, output_offset 0x%08x, output_section->vma = 0x%08x\n",
688 reloc_data.input_section->name,
689 (unsigned int) reloc_data.input_section->output_offset,
690 (unsigned int) reloc_data.input_section->output_section->vma);
691 PR_DEBUG ( " changed_address = 0x%08x\n",
692 (unsigned int) (reloc_data.input_section->output_section->vma
693 + reloc_data.input_section->output_offset
694 + reloc_data.reloc_offset));
695 PR_DEBUG (" file: %s\n", reloc_data.input_section->owner->filename);
696 }
697 else
698 {
699 PR_DEBUG ( " input section is NULL\n");
700 }
701 }
702
703 static bfd_vma
704 middle_endian_convert (bfd_vma insn, bfd_boolean do_it)
705 {
706 if (do_it)
707 {
708 insn
709 = ((insn & 0xffff0000) >> 16)
710 | ((insn & 0xffff) << 16);
711 }
712 return insn;
713 }
714
715 /* This function is called for relocations that are otherwise marked as NOT
716 requiring overflow checks. In here we perform non-standard checks of
717 the relocation value. */
718
719 static inline bfd_reloc_status_type
720 arc_special_overflow_checks (const struct arc_relocation_data reloc_data,
721 bfd_signed_vma relocation,
722 struct bfd_link_info *info ATTRIBUTE_UNUSED)
723 {
724 switch (reloc_data.howto->type)
725 {
726 case R_ARC_NPS_CMEM16:
727 if (((relocation >> 16) & 0xffff) != NPS_CMEM_HIGH_VALUE)
728 {
729 if (reloc_data.reloc_addend == 0)
730 (*_bfd_error_handler)
731 (_("%B(%A+0x%lx): CMEM relocation to `%s' is invalid, "
732 "16 MSB should be 0x%04x (value is 0x%lx)"),
733 reloc_data.input_section->owner,
734 reloc_data.input_section,
735 reloc_data.reloc_offset,
736 reloc_data.symbol_name,
737 NPS_CMEM_HIGH_VALUE,
738 (relocation));
739 else
740 (*_bfd_error_handler)
741 (_("%B(%A+0x%lx): CMEM relocation to `%s+0x%lx' is invalid, "
742 "16 MSB should be 0x%04x (value is 0x%lx)"),
743 reloc_data.input_section->owner,
744 reloc_data.input_section,
745 reloc_data.reloc_offset,
746 reloc_data.symbol_name,
747 reloc_data.reloc_addend,
748 NPS_CMEM_HIGH_VALUE,
749 (relocation));
750 return bfd_reloc_overflow;
751 }
752 break;
753
754 default:
755 break;
756 }
757
758 return bfd_reloc_ok;
759 }
760
761 #define ME(reloc) (reloc)
762
763 #define IS_ME(FORMULA,BFD) ((strstr (FORMULA, "ME") != NULL) \
764 && (!bfd_big_endian (BFD)))
765
766 #define S ((bfd_signed_vma) (reloc_data.sym_value \
767 + (reloc_data.sym_section->output_section != NULL ? \
768 (reloc_data.sym_section->output_offset \
769 + reloc_data.sym_section->output_section->vma) : 0)))
770 #define L ((bfd_signed_vma) (reloc_data.sym_value \
771 + (reloc_data.sym_section->output_section != NULL ? \
772 (reloc_data.sym_section->output_offset \
773 + reloc_data.sym_section->output_section->vma) : 0)))
774 #define A (reloc_data.reloc_addend)
775 #define B (0)
776 #define G (reloc_data.got_offset_value)
777 #define GOT (reloc_data.got_symbol_vma)
778 #define GOT_BEGIN (htab->sgot->output_section->vma)
779
780 #define MES (0)
781 /* P: relative offset to PCL The offset should be to the
782 current location aligned to 32 bits. */
783 #define P ((bfd_signed_vma) ( \
784 ( \
785 (reloc_data.input_section->output_section != NULL ? \
786 reloc_data.input_section->output_section->vma : 0) \
787 + reloc_data.input_section->output_offset \
788 + (reloc_data.reloc_offset - (bitsize >= 32 ? 4 : 0))) \
789 & ~0x3))
790 #define PDATA ((bfd_signed_vma) ( \
791 (reloc_data.input_section->output_section->vma \
792 + reloc_data.input_section->output_offset \
793 + (reloc_data.reloc_offset))))
794 #define SECTSTART (bfd_signed_vma) (reloc_data.sym_section->output_section->vma \
795 + reloc_data.sym_section->output_offset)
796
797 #define _SDA_BASE_ (bfd_signed_vma) (reloc_data.sdata_begin_symbol_vma)
798 #define TLS_REL (bfd_signed_vma) \
799 ((elf_hash_table (info))->tls_sec->output_section->vma)
800 #define TLS_TBSS (8)
801 #define TCB_SIZE (8)
802
803 #define none (0)
804
805 #define PRINT_DEBUG_RELOC_INFO_BEFORE(FORMULA, TYPE) \
806 {\
807 asection *sym_section = reloc_data.sym_section; \
808 asection *input_section = reloc_data.input_section; \
809 ARC_DEBUG ("RELOC_TYPE = " TYPE "\n"); \
810 ARC_DEBUG ("FORMULA = " FORMULA "\n"); \
811 ARC_DEBUG ("S = 0x%x\n", S); \
812 ARC_DEBUG ("A = 0x%x\n", A); \
813 ARC_DEBUG ("L = 0x%x\n", L); \
814 if (sym_section->output_section != NULL) \
815 { \
816 ARC_DEBUG ("symbol_section->vma = 0x%x\n", \
817 sym_section->output_section->vma + sym_section->output_offset); \
818 } \
819 else \
820 { \
821 ARC_DEBUG ("symbol_section->vma = NULL\n"); \
822 } \
823 if (input_section->output_section != NULL) \
824 { \
825 ARC_DEBUG ("symbol_section->vma = 0x%x\n", \
826 input_section->output_section->vma + input_section->output_offset); \
827 } \
828 else \
829 { \
830 ARC_DEBUG ("symbol_section->vma = NULL\n"); \
831 } \
832 ARC_DEBUG ("PCL = 0x%x\n", P); \
833 ARC_DEBUG ("P = 0x%x\n", P); \
834 ARC_DEBUG ("G = 0x%x\n", G); \
835 ARC_DEBUG ("SDA_OFFSET = 0x%x\n", _SDA_BASE_); \
836 ARC_DEBUG ("SDA_SET = %d\n", reloc_data.sdata_begin_symbol_vma_set); \
837 ARC_DEBUG ("GOT_OFFSET = 0x%x\n", GOT); \
838 ARC_DEBUG ("relocation = 0x%08x\n", relocation); \
839 ARC_DEBUG ("before = 0x%08x\n", (unsigned int) insn); \
840 ARC_DEBUG ("data = 0x%08x (%u) (%d)\n", (unsigned int) relocation, (unsigned int) relocation, (int) relocation); \
841 }
842
843 #define PRINT_DEBUG_RELOC_INFO_AFTER \
844 { \
845 ARC_DEBUG ("after = 0x%08x\n", (unsigned int) insn); \
846 }
847
848 #define ARC_RELOC_HOWTO(TYPE, VALUE, SIZE, BITSIZE, RELOC_FUNCTION, OVERFLOW, FORMULA) \
849 case R_##TYPE: \
850 { \
851 bfd_signed_vma bitsize ATTRIBUTE_UNUSED = BITSIZE; \
852 relocation = FORMULA ; \
853 PRINT_DEBUG_RELOC_INFO_BEFORE (#FORMULA, #TYPE); \
854 insn = middle_endian_convert (insn, IS_ME (#FORMULA, abfd)); \
855 insn = (* get_replace_function (abfd, TYPE)) (insn, relocation); \
856 insn = middle_endian_convert (insn, IS_ME (#FORMULA, abfd)); \
857 PRINT_DEBUG_RELOC_INFO_AFTER \
858 } \
859 break;
860
861 static bfd_reloc_status_type
862 arc_do_relocation (bfd_byte * contents,
863 struct arc_relocation_data reloc_data,
864 struct bfd_link_info *info)
865 {
866 bfd_signed_vma relocation = 0;
867 bfd_vma insn;
868 bfd_vma orig_insn ATTRIBUTE_UNUSED;
869 bfd * abfd = reloc_data.input_section->owner;
870 struct elf_link_hash_table *htab ATTRIBUTE_UNUSED = elf_hash_table (info);
871 bfd_reloc_status_type flag;
872
873 if (reloc_data.should_relocate == FALSE)
874 return bfd_reloc_ok;
875
876 switch (reloc_data.howto->size)
877 {
878 case 2:
879 insn = arc_bfd_get_32 (abfd,
880 contents + reloc_data.reloc_offset,
881 reloc_data.input_section);
882 break;
883 case 1:
884 insn = arc_bfd_get_16 (abfd,
885 contents + reloc_data.reloc_offset,
886 reloc_data.input_section);
887 break;
888 case 0:
889 insn = arc_bfd_get_8 (abfd,
890 contents + reloc_data.reloc_offset,
891 reloc_data.input_section);
892 break;
893 default:
894 insn = 0;
895 BFD_ASSERT (0);
896 break;
897 }
898
899 orig_insn = insn;
900
901 switch (reloc_data.howto->type)
902 {
903 #include "elf/arc-reloc.def"
904
905 default:
906 BFD_ASSERT (0);
907 break;
908 }
909
910 /* Check for relocation overflow. */
911 if (reloc_data.howto->complain_on_overflow != complain_overflow_dont)
912 flag = bfd_check_overflow (reloc_data.howto->complain_on_overflow,
913 reloc_data.howto->bitsize,
914 reloc_data.howto->rightshift,
915 bfd_arch_bits_per_address (abfd),
916 relocation);
917 else
918 flag = arc_special_overflow_checks (reloc_data, relocation, info);
919
920 #undef DEBUG_ARC_RELOC
921 #define DEBUG_ARC_RELOC(A) debug_arc_reloc (A)
922 if (flag != bfd_reloc_ok)
923 {
924 PR_DEBUG ( "Relocation overflows !!!!\n");
925
926 DEBUG_ARC_RELOC (reloc_data);
927
928 PR_DEBUG (
929 "Relocation value = signed -> %d, unsigned -> %u"
930 ", hex -> (0x%08x)\n",
931 (int) relocation,
932 (unsigned int) relocation,
933 (unsigned int) relocation);
934 return flag;
935 }
936 #undef DEBUG_ARC_RELOC
937 #define DEBUG_ARC_RELOC(A)
938
939 /* Write updated instruction back to memory. */
940 switch (reloc_data.howto->size)
941 {
942 case 2:
943 arc_bfd_put_32 (abfd, insn,
944 contents + reloc_data.reloc_offset,
945 reloc_data.input_section);
946 break;
947 case 1:
948 arc_bfd_put_16 (abfd, insn,
949 contents + reloc_data.reloc_offset,
950 reloc_data.input_section);
951 break;
952 case 0:
953 arc_bfd_put_8 (abfd, insn,
954 contents + reloc_data.reloc_offset,
955 reloc_data.input_section);
956 break;
957 default:
958 ARC_DEBUG ("size = %d\n", reloc_data.howto->size);
959 BFD_ASSERT (0);
960 break;
961 }
962
963 return bfd_reloc_ok;
964 }
965 #undef S
966 #undef A
967 #undef B
968 #undef G
969 #undef GOT
970 #undef L
971 #undef MES
972 #undef P
973 #undef SECTSTAR
974 #undef SECTSTART
975 #undef _SDA_BASE_
976 #undef none
977
978 #undef ARC_RELOC_HOWTO
979
980
981 /* Relocate an arc ELF section.
982 Function : elf_arc_relocate_section
983 Brief : Relocate an arc section, by handling all the relocations
984 appearing in that section.
985 Args : output_bfd : The bfd being written to.
986 info : Link information.
987 input_bfd : The input bfd.
988 input_section : The section being relocated.
989 contents : contents of the section being relocated.
990 relocs : List of relocations in the section.
991 local_syms : is a pointer to the swapped in local symbols.
992 local_section : is an array giving the section in the input file
993 corresponding to the st_shndx field of each
994 local symbol. */
995 static bfd_boolean
996 elf_arc_relocate_section (bfd * output_bfd,
997 struct bfd_link_info * info,
998 bfd * input_bfd,
999 asection * input_section,
1000 bfd_byte * contents,
1001 Elf_Internal_Rela * relocs,
1002 Elf_Internal_Sym * local_syms,
1003 asection ** local_sections)
1004 {
1005 Elf_Internal_Shdr * symtab_hdr;
1006 struct elf_link_hash_entry ** sym_hashes;
1007 Elf_Internal_Rela * rel;
1008 Elf_Internal_Rela * wrel;
1009 Elf_Internal_Rela * relend;
1010 struct elf_link_hash_table *htab = elf_hash_table (info);
1011
1012 symtab_hdr = &((elf_tdata (input_bfd))->symtab_hdr);
1013 sym_hashes = elf_sym_hashes (input_bfd);
1014
1015 rel = wrel = relocs;
1016 relend = relocs + input_section->reloc_count;
1017 for (; rel < relend; wrel++, rel++)
1018 {
1019 enum elf_arc_reloc_type r_type;
1020 reloc_howto_type * howto;
1021 unsigned long r_symndx;
1022 struct elf_link_hash_entry * h;
1023 Elf_Internal_Sym * sym;
1024 asection * sec;
1025 struct elf_link_hash_entry *h2;
1026
1027 struct arc_relocation_data reloc_data =
1028 {
1029 .reloc_offset = 0,
1030 .reloc_addend = 0,
1031 .got_offset_value = 0,
1032 .sym_value = 0,
1033 .sym_section = NULL,
1034 .howto = NULL,
1035 .input_section = NULL,
1036 .sdata_begin_symbol_vma = 0,
1037 .sdata_begin_symbol_vma_set = FALSE,
1038 .got_symbol_vma = 0,
1039 .should_relocate = FALSE
1040 };
1041
1042 r_type = ELF32_R_TYPE (rel->r_info);
1043
1044 if (r_type >= (int) R_ARC_max)
1045 {
1046 bfd_set_error (bfd_error_bad_value);
1047 return FALSE;
1048 }
1049 howto = arc_elf_howto (r_type);
1050
1051 r_symndx = ELF32_R_SYM (rel->r_info);
1052
1053 /* If we are generating another .o file and the symbol in not
1054 local, skip this relocation. */
1055 if (bfd_link_relocatable (info))
1056 {
1057 /* This is a relocateable link. We don't have to change
1058 anything, unless the reloc is against a section symbol,
1059 in which case we have to adjust according to where the
1060 section symbol winds up in the output section. */
1061
1062 /* Checks if this is a local symbol and thus the reloc
1063 might (will??) be against a section symbol. */
1064 if (r_symndx < symtab_hdr->sh_info)
1065 {
1066 sym = local_syms + r_symndx;
1067 if (ELF_ST_TYPE (sym->st_info) == STT_SECTION)
1068 {
1069 sec = local_sections[r_symndx];
1070
1071 /* for RELA relocs.Just adjust the addend
1072 value in the relocation entry. */
1073 rel->r_addend += sec->output_offset + sym->st_value;
1074
1075 BFD_DEBUG_PIC (
1076 PR_DEBUG ("local symbols reloc "
1077 "(section=%d %s) seen in %s\n",
1078 r_symndx,
1079 local_sections[r_symndx]->name,
1080 __PRETTY_FUNCTION__)
1081 );
1082 }
1083 }
1084 }
1085
1086 h2 = elf_link_hash_lookup (elf_hash_table (info), "__SDATA_BEGIN__",
1087 FALSE, FALSE, TRUE);
1088
1089 if (reloc_data.sdata_begin_symbol_vma_set == FALSE
1090 && h2 != NULL && h2->root.type != bfd_link_hash_undefined
1091 && h2->root.u.def.section->output_section != NULL)
1092 /* TODO: Verify this condition. */
1093 {
1094 reloc_data.sdata_begin_symbol_vma =
1095 (h2->root.u.def.value
1096 + h2->root.u.def.section->output_section->vma);
1097 reloc_data.sdata_begin_symbol_vma_set = TRUE;
1098 }
1099
1100 reloc_data.input_section = input_section;
1101 reloc_data.howto = howto;
1102 reloc_data.reloc_offset = rel->r_offset;
1103 reloc_data.reloc_addend = rel->r_addend;
1104
1105 /* This is a final link. */
1106 h = NULL;
1107 sym = NULL;
1108 sec = NULL;
1109
1110 if (r_symndx < symtab_hdr->sh_info) /* A local symbol. */
1111 {
1112 sym = local_syms + r_symndx;
1113 sec = local_sections[r_symndx];
1114 }
1115 else
1116 {
1117 /* TODO: This code is repeated from below. We should
1118 clean it and remove duplications.
1119 Sec is used check for discarded sections.
1120 Need to redesign code below. */
1121
1122 /* Get the symbol's entry in the symtab. */
1123 h = sym_hashes[r_symndx - symtab_hdr->sh_info];
1124
1125 while (h->root.type == bfd_link_hash_indirect
1126 || h->root.type == bfd_link_hash_warning)
1127 h = (struct elf_link_hash_entry *) h->root.u.i.link;
1128
1129 /* If we have encountered a definition for this symbol. */
1130 if (h->root.type == bfd_link_hash_defined
1131 || h->root.type == bfd_link_hash_defweak)
1132 {
1133 reloc_data.sym_value = h->root.u.def.value;
1134 sec = h->root.u.def.section;
1135 }
1136 }
1137
1138 /* Clean relocs for symbols in discarded sections. */
1139 if (sec != NULL && discarded_section (sec))
1140 {
1141 _bfd_clear_contents (howto, input_bfd, input_section,
1142 contents + rel->r_offset);
1143 rel->r_offset = rel->r_offset;
1144 rel->r_info = 0;
1145 rel->r_addend = 0;
1146
1147 /* For ld -r, remove relocations in debug sections against
1148 sections defined in discarded sections. Not done for
1149 eh_frame editing code expects to be present. */
1150 if (bfd_link_relocatable (info)
1151 && (input_section->flags & SEC_DEBUGGING))
1152 wrel--;
1153
1154 continue;
1155 }
1156
1157 if (bfd_link_relocatable (info))
1158 {
1159 if (wrel != rel)
1160 *wrel = *rel;
1161 continue;
1162 }
1163
1164 if (r_symndx < symtab_hdr->sh_info) /* A local symbol. */
1165 {
1166 reloc_data.sym_value = sym->st_value;
1167 reloc_data.sym_section = sec;
1168 reloc_data.symbol_name =
1169 bfd_elf_string_from_elf_section (input_bfd,
1170 symtab_hdr->sh_link,
1171 sym->st_name);
1172
1173 /* Mergeable section handling. */
1174 if ((sec->flags & SEC_MERGE)
1175 && ELF_ST_TYPE (sym->st_info) == STT_SECTION)
1176 {
1177 asection *msec;
1178 msec = sec;
1179 rel->r_addend = _bfd_elf_rel_local_sym (output_bfd, sym,
1180 &msec, rel->r_addend);
1181 rel->r_addend -= (sec->output_section->vma
1182 + sec->output_offset
1183 + sym->st_value);
1184 rel->r_addend += msec->output_section->vma + msec->output_offset;
1185
1186 reloc_data.reloc_addend = rel->r_addend;
1187 }
1188
1189 BFD_ASSERT (htab->sgot != NULL || !is_reloc_for_GOT (howto));
1190 if (htab->sgot != NULL)
1191 reloc_data.got_symbol_vma = htab->sgot->output_section->vma
1192 + htab->sgot->output_offset;
1193
1194 reloc_data.should_relocate = TRUE;
1195 }
1196 else /* Global symbol. */
1197 {
1198 /* Get the symbol's entry in the symtab. */
1199 h = sym_hashes[r_symndx - symtab_hdr->sh_info];
1200
1201 while (h->root.type == bfd_link_hash_indirect
1202 || h->root.type == bfd_link_hash_warning)
1203 h = (struct elf_link_hash_entry *) h->root.u.i.link;
1204
1205 /* TODO: Need to validate what was the intention. */
1206 /* BFD_ASSERT ((h->dynindx == -1) || (h->forced_local != 0)); */
1207 reloc_data.symbol_name = h->root.root.string;
1208
1209 /* If we have encountered a definition for this symbol. */
1210 if (h->root.type == bfd_link_hash_defined
1211 || h->root.type == bfd_link_hash_defweak)
1212 {
1213 reloc_data.sym_value = h->root.u.def.value;
1214 reloc_data.sym_section = h->root.u.def.section;
1215
1216 reloc_data.should_relocate = TRUE;
1217
1218 if (is_reloc_for_GOT (howto) && !bfd_link_pic (info))
1219 {
1220 /* TODO: Change it to use arc_do_relocation with
1221 ARC_32 reloc. Try to use ADD_RELA macro. */
1222 bfd_vma relocation =
1223 reloc_data.sym_value + reloc_data.reloc_addend
1224 + (reloc_data.sym_section->output_section != NULL ?
1225 (reloc_data.sym_section->output_offset
1226 + reloc_data.sym_section->output_section->vma)
1227 : 0);
1228
1229 BFD_ASSERT (h->got.glist);
1230 bfd_vma got_offset = h->got.glist->offset;
1231 bfd_put_32 (output_bfd, relocation,
1232 htab->sgot->contents + got_offset);
1233 }
1234 if (is_reloc_for_PLT (howto) && h->plt.offset != (bfd_vma) -1)
1235 {
1236 /* TODO: This is repeated up here. */
1237 reloc_data.sym_value = h->plt.offset;
1238 reloc_data.sym_section = htab->splt;
1239 }
1240 }
1241 else if (h->root.type == bfd_link_hash_undefweak)
1242 {
1243 /* Is weak symbol and has no definition. */
1244 if (is_reloc_for_GOT (howto))
1245 {
1246 reloc_data.sym_value = h->root.u.def.value;
1247 reloc_data.sym_section = htab->sgot;
1248 reloc_data.should_relocate = TRUE;
1249 }
1250 else if (is_reloc_for_PLT (howto)
1251 && h->plt.offset != (bfd_vma) -1)
1252 {
1253 /* TODO: This is repeated up here. */
1254 reloc_data.sym_value = h->plt.offset;
1255 reloc_data.sym_section = htab->splt;
1256 reloc_data.should_relocate = TRUE;
1257 }
1258 else
1259 continue;
1260 }
1261 else
1262 {
1263 if (is_reloc_for_GOT (howto))
1264 {
1265 reloc_data.sym_value = h->root.u.def.value;
1266 reloc_data.sym_section = htab->sgot;
1267
1268 reloc_data.should_relocate = TRUE;
1269 }
1270 else if (is_reloc_for_PLT (howto))
1271 {
1272 /* Fail if it is linking for PIE and the symbol is
1273 undefined. */
1274 if (bfd_link_executable (info))
1275 (*info->callbacks->undefined_symbol)
1276 (info, h->root.root.string, input_bfd, input_section,
1277 rel->r_offset, TRUE);
1278 reloc_data.sym_value = h->plt.offset;
1279 reloc_data.sym_section = htab->splt;
1280
1281 reloc_data.should_relocate = TRUE;
1282 }
1283 else if (!bfd_link_pic (info))
1284 (*info->callbacks->undefined_symbol)
1285 (info, h->root.root.string, input_bfd, input_section,
1286 rel->r_offset, TRUE);
1287 }
1288
1289 BFD_ASSERT (htab->sgot != NULL || !is_reloc_for_GOT (howto));
1290 if (htab->sgot != NULL)
1291 reloc_data.got_symbol_vma = htab->sgot->output_section->vma
1292 + htab->sgot->output_offset;
1293 }
1294
1295 if ((is_reloc_for_GOT (howto)
1296 || is_reloc_for_TLS (howto)))
1297 {
1298 struct got_entry **list
1299 = get_got_entry_list_for_symbol (output_bfd, r_symndx, h);
1300
1301 reloc_data.got_offset_value
1302 = relocate_fix_got_relocs_for_got_info (list,
1303 tls_type_for_reloc (howto),
1304 info,
1305 output_bfd,
1306 r_symndx,
1307 local_syms,
1308 local_sections,
1309 h,
1310 &reloc_data);
1311
1312 if (h == NULL)
1313 {
1314 create_got_dynrelocs_for_single_entry (
1315 got_entry_for_type (list,
1316 arc_got_entry_type_for_reloc (howto)),
1317 output_bfd, info, NULL);
1318 }
1319 }
1320 switch (r_type)
1321 {
1322 case R_ARC_32:
1323 case R_ARC_32_ME:
1324 case R_ARC_PC32:
1325 case R_ARC_32_PCREL:
1326 if ((bfd_link_pic (info))// || bfd_link_pie (info))
1327 && ((r_type != R_ARC_PC32 && r_type != R_ARC_32_PCREL)
1328 || (h != NULL
1329 && h->dynindx != -1
1330 && (!info->symbolic || !h->def_regular))))
1331 {
1332 Elf_Internal_Rela outrel;
1333 bfd_byte *loc;
1334 bfd_boolean skip = FALSE;
1335 bfd_boolean relocate = FALSE;
1336 asection *sreloc = _bfd_elf_get_dynamic_reloc_section
1337 (input_bfd, input_section,
1338 /*RELA*/ TRUE);
1339
1340 BFD_ASSERT (sreloc != NULL);
1341
1342 outrel.r_offset = _bfd_elf_section_offset (output_bfd,
1343 info,
1344 input_section,
1345 rel->r_offset);
1346 if (outrel.r_offset == (bfd_vma) -1)
1347 skip = TRUE;
1348
1349 outrel.r_addend = rel->r_addend;
1350 outrel.r_offset += (input_section->output_section->vma
1351 + input_section->output_offset);
1352
1353 #define IS_ARC_PCREL_TYPE(TYPE) \
1354 ( (TYPE == R_ARC_PC32) \
1355 || (TYPE == R_ARC_32_PCREL))
1356 if (skip)
1357 {
1358 memset (&outrel, 0, sizeof outrel);
1359 relocate = FALSE;
1360 }
1361 else if (h != NULL
1362 && h->dynindx != -1
1363 && ((IS_ARC_PCREL_TYPE (r_type))
1364 || !(bfd_link_executable (info)
1365 || SYMBOLIC_BIND (info, h))
1366 || ! h->def_regular))
1367 {
1368 BFD_ASSERT (h != NULL);
1369 if ((input_section->flags & SEC_ALLOC) != 0)
1370 relocate = FALSE;
1371 else
1372 relocate = TRUE;
1373
1374 BFD_ASSERT (h->dynindx != -1);
1375 outrel.r_info = ELF32_R_INFO (h->dynindx, r_type);
1376 }
1377 else
1378 {
1379 /* Handle local symbols, they either do not have a
1380 global hash table entry (h == NULL), or are
1381 forced local due to a version script
1382 (h->forced_local), or the third condition is
1383 legacy, it appears to say something like, for
1384 links where we are pre-binding the symbols, or
1385 there's not an entry for this symbol in the
1386 dynamic symbol table, and it's a regular symbol
1387 not defined in a shared object, then treat the
1388 symbol as local, resolve it now. */
1389 relocate = TRUE;
1390 /* outrel.r_addend = 0; */
1391 outrel.r_info = ELF32_R_INFO (0, R_ARC_RELATIVE);
1392 }
1393
1394 BFD_ASSERT (sreloc->contents != 0);
1395
1396 loc = sreloc->contents;
1397 loc += sreloc->reloc_count * sizeof (Elf32_External_Rela);
1398 sreloc->reloc_count += 1;
1399
1400 bfd_elf32_swap_reloca_out (output_bfd, &outrel, loc);
1401
1402 if (relocate == FALSE)
1403 continue;
1404 }
1405 break;
1406 default:
1407 break;
1408 }
1409
1410 if (is_reloc_SDA_relative (howto)
1411 && (reloc_data.sdata_begin_symbol_vma_set == FALSE))
1412 {
1413 (*_bfd_error_handler)
1414 ("Error: Linker symbol __SDATA_BEGIN__ not found");
1415 bfd_set_error (bfd_error_bad_value);
1416 return FALSE;
1417 }
1418
1419 DEBUG_ARC_RELOC (reloc_data);
1420
1421 /* Make sure we have with a dynamic linker. In case of GOT and PLT
1422 the sym_section should point to .got or .plt respectively. */
1423 if ((is_reloc_for_GOT (howto) || is_reloc_for_PLT (howto))
1424 && reloc_data.sym_section == NULL)
1425 {
1426 (*_bfd_error_handler)
1427 (_("GOT and PLT relocations cannot be fixed with a non dynamic linker."));
1428 bfd_set_error (bfd_error_bad_value);
1429 return FALSE;
1430 }
1431
1432 if (arc_do_relocation (contents, reloc_data, info) != bfd_reloc_ok)
1433 return FALSE;
1434 }
1435
1436 return TRUE;
1437 }
1438
1439 static struct dynamic_sections
1440 arc_create_dynamic_sections (bfd * abfd, struct bfd_link_info *info)
1441 {
1442 struct elf_link_hash_table *htab;
1443 bfd *dynobj;
1444 struct dynamic_sections ds =
1445 {
1446 .initialized = FALSE,
1447 .sgot = NULL,
1448 .srelgot = NULL,
1449 .sgotplt = NULL,
1450 .srelgotplt = NULL,
1451 .sdyn = NULL,
1452 .splt = NULL,
1453 .srelplt = NULL
1454 };
1455
1456 htab = elf_hash_table (info);
1457 BFD_ASSERT (htab);
1458
1459 /* Create dynamic sections for relocatable executables so that we
1460 can copy relocations. */
1461 if (! htab->dynamic_sections_created && bfd_link_pic (info))
1462 {
1463 if (! _bfd_elf_link_create_dynamic_sections (abfd, info))
1464 BFD_ASSERT (0);
1465 }
1466
1467 dynobj = (elf_hash_table (info))->dynobj;
1468
1469 if (dynobj)
1470 {
1471 ds.sgot = htab->sgot;
1472 ds.srelgot = htab->srelgot;
1473
1474 ds.sgotplt = bfd_get_section_by_name (dynobj, ".got.plt");
1475 ds.srelgotplt = ds.srelplt;
1476
1477 ds.splt = bfd_get_section_by_name (dynobj, ".plt");
1478 ds.srelplt = bfd_get_section_by_name (dynobj, ".rela.plt");
1479 }
1480
1481 if (htab->dynamic_sections_created)
1482 {
1483 ds.sdyn = bfd_get_section_by_name (dynobj, ".dynamic");
1484 }
1485
1486 ds.initialized = TRUE;
1487
1488 return ds;
1489 }
1490
1491 static bfd_boolean
1492 elf_arc_check_relocs (bfd * abfd,
1493 struct bfd_link_info * info,
1494 asection * sec,
1495 const Elf_Internal_Rela * relocs)
1496 {
1497 Elf_Internal_Shdr * symtab_hdr;
1498 struct elf_link_hash_entry ** sym_hashes;
1499 const Elf_Internal_Rela * rel;
1500 const Elf_Internal_Rela * rel_end;
1501 bfd * dynobj;
1502 asection * sreloc = NULL;
1503
1504 if (bfd_link_relocatable (info))
1505 return TRUE;
1506
1507 dynobj = (elf_hash_table (info))->dynobj;
1508 symtab_hdr = &((elf_tdata (abfd))->symtab_hdr);
1509 sym_hashes = elf_sym_hashes (abfd);
1510
1511 rel_end = relocs + sec->reloc_count;
1512 for (rel = relocs; rel < rel_end; rel++)
1513 {
1514 enum elf_arc_reloc_type r_type;
1515 reloc_howto_type *howto;
1516 unsigned long r_symndx;
1517 struct elf_link_hash_entry *h;
1518
1519 r_type = ELF32_R_TYPE (rel->r_info);
1520
1521 if (r_type >= (int) R_ARC_max)
1522 {
1523 bfd_set_error (bfd_error_bad_value);
1524 return FALSE;
1525 }
1526 howto = arc_elf_howto (r_type);
1527
1528 if (dynobj == NULL
1529 && (is_reloc_for_GOT (howto) == TRUE
1530 || is_reloc_for_TLS (howto) == TRUE))
1531 {
1532 dynobj = elf_hash_table (info)->dynobj = abfd;
1533 if (! _bfd_elf_create_got_section (abfd, info))
1534 return FALSE;
1535 }
1536
1537 /* Load symbol information. */
1538 r_symndx = ELF32_R_SYM (rel->r_info);
1539 if (r_symndx < symtab_hdr->sh_info) /* Is a local symbol. */
1540 h = NULL;
1541 else /* Global one. */
1542 h = sym_hashes[r_symndx - symtab_hdr->sh_info];
1543
1544 switch (r_type)
1545 {
1546 case R_ARC_32:
1547 case R_ARC_32_ME:
1548 /* During shared library creation, these relocs should not
1549 appear in a shared library (as memory will be read only
1550 and the dynamic linker can not resolve these. However
1551 the error should not occur for e.g. debugging or
1552 non-readonly sections. */
1553 if ((bfd_link_dll (info) && !bfd_link_pie (info))
1554 && (sec->flags & SEC_ALLOC) != 0
1555 && (sec->flags & SEC_READONLY) != 0
1556 && ((sec->flags & SEC_CODE) != 0
1557 || (sec->flags & SEC_DEBUGGING) != 0))
1558 {
1559 const char *name;
1560 if (h)
1561 name = h->root.root.string;
1562 else
1563 /* bfd_elf_sym_name (abfd, symtab_hdr, isym, NULL); */
1564 name = "UNKNOWN";
1565 (*_bfd_error_handler)
1566 (_("\
1567 %B: relocation %s against `%s' can not be used when making a shared object; recompile with -fPIC"),
1568 abfd,
1569 arc_elf_howto (r_type)->name,
1570 name);
1571 bfd_set_error (bfd_error_bad_value);
1572 return FALSE;
1573 }
1574
1575 /* In some cases we are not setting the 'non_got_ref'
1576 flag, even though the relocations don't require a GOT
1577 access. We should extend the testing in this area to
1578 ensure that no significant cases are being missed. */
1579 if (h)
1580 h->non_got_ref = 1;
1581 /* FALLTHROUGH */
1582 case R_ARC_PC32:
1583 case R_ARC_32_PCREL:
1584 if ((bfd_link_pic (info))// || bfd_link_pie (info))
1585 && ((r_type != R_ARC_PC32 && r_type != R_ARC_32_PCREL)
1586 || (h != NULL
1587 && h->dynindx != -1
1588 && (!info->symbolic || !h->def_regular))))
1589 {
1590 if (sreloc == NULL)
1591 {
1592 sreloc = _bfd_elf_make_dynamic_reloc_section (sec, dynobj,
1593 2, abfd,
1594 /*rela*/
1595 TRUE);
1596
1597 if (sreloc == NULL)
1598 return FALSE;
1599 }
1600 sreloc->size += sizeof (Elf32_External_Rela);
1601
1602 }
1603 default:
1604 break;
1605 }
1606
1607 if (is_reloc_for_PLT (howto) == TRUE)
1608 {
1609 if (h == NULL)
1610 continue;
1611 else
1612 h->needs_plt = 1;
1613 }
1614
1615 /* Add info to the symbol got_entry_list. */
1616 if (is_reloc_for_GOT (howto) == TRUE
1617 || is_reloc_for_TLS (howto) == TRUE)
1618 {
1619 arc_fill_got_info_for_reloc (
1620 arc_got_entry_type_for_reloc (howto),
1621 get_got_entry_list_for_symbol (abfd, r_symndx, h),
1622 info,
1623 h);
1624 }
1625 }
1626
1627 return TRUE;
1628 }
1629
1630 #define ELF_DYNAMIC_INTERPRETER "/sbin/ld-uClibc.so"
1631
1632 static struct plt_version_t *
1633 arc_get_plt_version (struct bfd_link_info *info)
1634 {
1635 int i;
1636
1637 for (i = 0; i < 1; i++)
1638 {
1639 ARC_DEBUG ("%d: size1 = %d, size2 = %d\n", i,
1640 plt_versions[i].entry_size,
1641 plt_versions[i].elem_size);
1642 }
1643
1644 if (bfd_get_mach (info->output_bfd) == bfd_mach_arc_arcv2)
1645 {
1646 if (bfd_link_pic (info))
1647 return &(plt_versions[ELF_ARCV2_PIC]);
1648 else
1649 return &(plt_versions[ELF_ARCV2_ABS]);
1650 }
1651 else
1652 {
1653 if (bfd_link_pic (info))
1654 return &(plt_versions[ELF_ARC_PIC]);
1655 else
1656 return &(plt_versions[ELF_ARC_ABS]);
1657 }
1658 }
1659
1660 static bfd_vma
1661 add_symbol_to_plt (struct bfd_link_info *info)
1662 {
1663 struct elf_link_hash_table *htab = elf_hash_table (info);
1664 bfd_vma ret;
1665
1666 struct plt_version_t *plt_data = arc_get_plt_version (info);
1667
1668 /* If this is the first .plt entry, make room for the special first
1669 entry. */
1670 if (htab->splt->size == 0)
1671 htab->splt->size += plt_data->entry_size;
1672
1673 ret = htab->splt->size;
1674
1675 htab->splt->size += plt_data->elem_size;
1676 ARC_DEBUG ("PLT_SIZE = %d\n", htab->splt->size);
1677
1678 htab->sgotplt->size += 4;
1679 htab->srelplt->size += sizeof (Elf32_External_Rela);
1680
1681 return ret;
1682 }
1683
1684 #define PLT_DO_RELOCS_FOR_ENTRY(ABFD, DS, RELOCS) \
1685 plt_do_relocs_for_symbol (ABFD, DS, RELOCS, 0, 0)
1686
1687 static void
1688 plt_do_relocs_for_symbol (bfd *abfd,
1689 struct elf_link_hash_table *htab,
1690 const struct plt_reloc *reloc,
1691 bfd_vma plt_offset,
1692 bfd_vma symbol_got_offset)
1693 {
1694 while (SYM_ONLY (reloc->symbol) != LAST_RELOC)
1695 {
1696 bfd_vma relocation = 0;
1697
1698 switch (SYM_ONLY (reloc->symbol))
1699 {
1700 case SGOT:
1701 relocation
1702 = htab->sgotplt->output_section->vma
1703 + htab->sgotplt->output_offset + symbol_got_offset;
1704 break;
1705 }
1706 relocation += reloc->addend;
1707
1708 if (IS_RELATIVE (reloc->symbol))
1709 {
1710 bfd_vma reloc_offset = reloc->offset;
1711 reloc_offset -= (IS_INSN_32 (reloc->symbol)) ? 4 : 0;
1712 reloc_offset -= (IS_INSN_24 (reloc->symbol)) ? 2 : 0;
1713
1714 relocation -= htab->splt->output_section->vma
1715 + htab->splt->output_offset
1716 + plt_offset + reloc_offset;
1717 }
1718
1719 /* TODO: being ME is not a property of the relocation but of the
1720 section of which is applying the relocation. */
1721 if (IS_MIDDLE_ENDIAN (reloc->symbol) && !bfd_big_endian (abfd))
1722 {
1723 relocation
1724 = ((relocation & 0xffff0000) >> 16)
1725 | ((relocation & 0xffff) << 16);
1726 }
1727
1728 switch (reloc->size)
1729 {
1730 case 32:
1731 bfd_put_32 (htab->splt->output_section->owner,
1732 relocation,
1733 htab->splt->contents + plt_offset + reloc->offset);
1734 break;
1735 }
1736
1737 reloc = &(reloc[1]); /* Jump to next relocation. */
1738 }
1739 }
1740
1741 static void
1742 relocate_plt_for_symbol (bfd *output_bfd,
1743 struct bfd_link_info *info,
1744 struct elf_link_hash_entry *h)
1745 {
1746 struct plt_version_t *plt_data = arc_get_plt_version (info);
1747 struct elf_link_hash_table *htab = elf_hash_table (info);
1748
1749 bfd_vma plt_index = (h->plt.offset - plt_data->entry_size)
1750 / plt_data->elem_size;
1751 bfd_vma got_offset = (plt_index + 3) * 4;
1752
1753 ARC_DEBUG ("arc_info: PLT_OFFSET = 0x%x, PLT_ENTRY_VMA = 0x%x, \
1754 GOT_ENTRY_OFFSET = 0x%x, GOT_ENTRY_VMA = 0x%x, for symbol %s\n",
1755 h->plt.offset,
1756 htab->splt->output_section->vma
1757 + htab->splt->output_offset
1758 + h->plt.offset,
1759 got_offset,
1760 htab->sgotplt->output_section->vma
1761 + htab->sgotplt->output_offset
1762 + got_offset,
1763 h->root.root.string);
1764
1765
1766 {
1767 bfd_vma i = 0;
1768 uint16_t *ptr = (uint16_t *) plt_data->elem;
1769 for (i = 0; i < plt_data->elem_size/2; i++)
1770 {
1771 uint16_t data = ptr[i];
1772 bfd_put_16 (output_bfd,
1773 (bfd_vma) data,
1774 htab->splt->contents + h->plt.offset + (i*2));
1775 }
1776 }
1777
1778 plt_do_relocs_for_symbol (output_bfd, htab,
1779 plt_data->elem_relocs,
1780 h->plt.offset,
1781 got_offset);
1782
1783 /* Fill in the entry in the global offset table. */
1784 bfd_put_32 (output_bfd,
1785 (bfd_vma) (htab->splt->output_section->vma
1786 + htab->splt->output_offset),
1787 htab->sgotplt->contents + got_offset);
1788
1789 /* TODO: Fill in the entry in the .rela.plt section. */
1790 {
1791 Elf_Internal_Rela rel;
1792 bfd_byte *loc;
1793
1794 rel.r_offset = (htab->sgotplt->output_section->vma
1795 + htab->sgotplt->output_offset
1796 + got_offset);
1797 rel.r_addend = 0;
1798
1799 BFD_ASSERT (h->dynindx != -1);
1800 rel.r_info = ELF32_R_INFO (h->dynindx, R_ARC_JMP_SLOT);
1801
1802 loc = htab->srelplt->contents;
1803 loc += plt_index * sizeof (Elf32_External_Rela); /* relA */
1804 bfd_elf32_swap_reloca_out (output_bfd, &rel, loc);
1805 }
1806 }
1807
1808 static void
1809 relocate_plt_for_entry (bfd *abfd,
1810 struct bfd_link_info *info)
1811 {
1812 struct plt_version_t *plt_data = arc_get_plt_version (info);
1813 struct elf_link_hash_table *htab = elf_hash_table (info);
1814
1815 {
1816 bfd_vma i = 0;
1817 uint16_t *ptr = (uint16_t *) plt_data->entry;
1818 for (i = 0; i < plt_data->entry_size/2; i++)
1819 {
1820 uint16_t data = ptr[i];
1821 bfd_put_16 (abfd,
1822 (bfd_vma) data,
1823 htab->splt->contents + (i*2));
1824 }
1825 }
1826 PLT_DO_RELOCS_FOR_ENTRY (abfd, htab, plt_data->entry_relocs);
1827 }
1828
1829 /* Desc : Adjust a symbol defined by a dynamic object and referenced
1830 by a regular object. The current definition is in some section of
1831 the dynamic object, but we're not including those sections. We
1832 have to change the definition to something the rest of the link can
1833 understand. */
1834
1835 static bfd_boolean
1836 elf_arc_adjust_dynamic_symbol (struct bfd_link_info *info,
1837 struct elf_link_hash_entry *h)
1838 {
1839 asection *s;
1840 bfd *dynobj = (elf_hash_table (info))->dynobj;
1841 struct elf_link_hash_table *htab = elf_hash_table (info);
1842
1843 if (h->type == STT_FUNC
1844 || h->type == STT_GNU_IFUNC
1845 || h->needs_plt == 1)
1846 {
1847 if (!bfd_link_pic (info) && !h->def_dynamic && !h->ref_dynamic)
1848 {
1849 /* This case can occur if we saw a PLT32 reloc in an input
1850 file, but the symbol was never referred to by a dynamic
1851 object. In such a case, we don't actually need to build
1852 a procedure linkage table, and we can just do a PC32
1853 reloc instead. */
1854 BFD_ASSERT (h->needs_plt);
1855 return TRUE;
1856 }
1857
1858 /* Make sure this symbol is output as a dynamic symbol. */
1859 if (h->dynindx == -1 && !h->forced_local
1860 && !bfd_elf_link_record_dynamic_symbol (info, h))
1861 return FALSE;
1862
1863 if (bfd_link_pic (info)
1864 || WILL_CALL_FINISH_DYNAMIC_SYMBOL (1, 0, h))
1865 {
1866 bfd_vma loc = add_symbol_to_plt (info);
1867
1868 if (bfd_link_executable (info) && !h->def_regular)
1869 {
1870 h->root.u.def.section = htab->splt;
1871 h->root.u.def.value = loc;
1872 }
1873 h->plt.offset = loc;
1874 }
1875 else
1876 {
1877 h->plt.offset = (bfd_vma) -1;
1878 h->needs_plt = 0;
1879 }
1880 return TRUE;
1881 }
1882
1883 /* If this is a weak symbol, and there is a real definition, the
1884 processor independent code will have arranged for us to see the
1885 real definition first, and we can just use the same value. */
1886 if (h->u.weakdef != NULL)
1887 {
1888 BFD_ASSERT (h->u.weakdef->root.type == bfd_link_hash_defined
1889 || h->u.weakdef->root.type == bfd_link_hash_defweak);
1890 h->root.u.def.section = h->u.weakdef->root.u.def.section;
1891 h->root.u.def.value = h->u.weakdef->root.u.def.value;
1892 return TRUE;
1893 }
1894
1895 /* This is a reference to a symbol defined by a dynamic object which
1896 is not a function. */
1897
1898 /* If we are creating a shared library, we must presume that the
1899 only references to the symbol are via the global offset table.
1900 For such cases we need not do anything here; the relocations will
1901 be handled correctly by relocate_section. */
1902 if (!bfd_link_executable (info))
1903 return TRUE;
1904
1905 /* If there are no non-GOT references, we do not need a copy
1906 relocation. */
1907 if (!h->non_got_ref)
1908 return TRUE;
1909
1910 /* If -z nocopyreloc was given, we won't generate them either. */
1911 if (info->nocopyreloc)
1912 {
1913 h->non_got_ref = 0;
1914 return TRUE;
1915 }
1916
1917 /* We must allocate the symbol in our .dynbss section, which will
1918 become part of the .bss section of the executable. There will be
1919 an entry for this symbol in the .dynsym section. The dynamic
1920 object will contain position independent code, so all references
1921 from the dynamic object to this symbol will go through the global
1922 offset table. The dynamic linker will use the .dynsym entry to
1923 determine the address it must put in the global offset table, so
1924 both the dynamic object and the regular object will refer to the
1925 same memory location for the variable. */
1926
1927 if (htab == NULL)
1928 return FALSE;
1929
1930 /* We must generate a R_ARC_COPY reloc to tell the dynamic linker to
1931 copy the initial value out of the dynamic object and into the
1932 runtime process image. We need to remember the offset into the
1933 .rela.bss section we are going to use. */
1934 if ((h->root.u.def.section->flags & SEC_ALLOC) != 0)
1935 {
1936 asection *srel;
1937
1938 srel = bfd_get_section_by_name (dynobj, ".rela.bss");
1939 BFD_ASSERT (srel != NULL);
1940 srel->size += sizeof (Elf32_External_Rela);
1941 h->needs_copy = 1;
1942 }
1943
1944 s = bfd_get_section_by_name (dynobj, ".dynbss");
1945 BFD_ASSERT (s != NULL);
1946
1947 return _bfd_elf_adjust_dynamic_copy (info, h, s);
1948 }
1949
1950 /* Function : elf_arc_finish_dynamic_symbol
1951 Brief : Finish up dynamic symbol handling. We set the
1952 contents of various dynamic sections here.
1953 Args : output_bfd :
1954 info :
1955 h :
1956 sym :
1957 Returns : True/False as the return status. */
1958
1959 static bfd_boolean
1960 elf_arc_finish_dynamic_symbol (bfd * output_bfd,
1961 struct bfd_link_info *info,
1962 struct elf_link_hash_entry *h,
1963 Elf_Internal_Sym * sym)
1964 {
1965 if (h->plt.offset != (bfd_vma) -1)
1966 {
1967 relocate_plt_for_symbol (output_bfd, info, h);
1968
1969 if (!h->def_regular)
1970 {
1971 /* Mark the symbol as undefined, rather than as defined in
1972 the .plt section. Leave the value alone. */
1973 sym->st_shndx = SHN_UNDEF;
1974 }
1975 }
1976
1977
1978 /* This function traverses list of GOT entries and
1979 create respective dynamic relocs. */
1980 /* TODO: Make function to get list and not access the list directly. */
1981 /* TODO: Move function to relocate_section create this relocs eagerly. */
1982 create_got_dynrelocs_for_got_info (&h->got.glist,
1983 output_bfd,
1984 info,
1985 h);
1986
1987 if (h->needs_copy)
1988 {
1989 bfd_vma rel_offset = (h->root.u.def.value
1990 + h->root.u.def.section->output_section->vma
1991 + h->root.u.def.section->output_offset);
1992
1993 asection *srelbss
1994 = bfd_get_section_by_name (h->root.u.def.section->owner,
1995 ".rela.bss");
1996
1997 bfd_byte * loc = srelbss->contents
1998 + (srelbss->reloc_count * sizeof (Elf32_External_Rela));
1999 srelbss->reloc_count++;
2000
2001 Elf_Internal_Rela rel;
2002 rel.r_addend = 0;
2003 rel.r_offset = rel_offset;
2004
2005 BFD_ASSERT (h->dynindx != -1);
2006 rel.r_info = ELF32_R_INFO (h->dynindx, R_ARC_COPY);
2007
2008 bfd_elf32_swap_reloca_out (output_bfd, &rel, loc);
2009 }
2010
2011 /* Mark _DYNAMIC and _GLOBAL_OFFSET_TABLE_ as absolute. */
2012 if (strcmp (h->root.root.string, "_DYNAMIC") == 0
2013 || strcmp (h->root.root.string, "__DYNAMIC") == 0
2014 || strcmp (h->root.root.string, "_GLOBAL_OFFSET_TABLE_") == 0)
2015 sym->st_shndx = SHN_ABS;
2016
2017 return TRUE;
2018 }
2019
2020 #define GET_SYMBOL_OR_SECTION(TAG, SYMBOL, SECTION) \
2021 case TAG: \
2022 if (SYMBOL != NULL) \
2023 h = elf_link_hash_lookup (elf_hash_table (info), \
2024 SYMBOL, FALSE, FALSE, TRUE); \
2025 else if (SECTION != NULL) \
2026 s = bfd_get_linker_section (dynobj, SECTION); \
2027 break;
2028
2029 /* Function : elf_arc_finish_dynamic_sections
2030 Brief : Finish up the dynamic sections handling.
2031 Args : output_bfd :
2032 info :
2033 h :
2034 sym :
2035 Returns : True/False as the return status. */
2036
2037 static bfd_boolean
2038 elf_arc_finish_dynamic_sections (bfd * output_bfd,
2039 struct bfd_link_info *info)
2040 {
2041 struct dynamic_sections ds = arc_create_dynamic_sections (output_bfd, info);
2042 struct elf_link_hash_table *htab = elf_hash_table (info);
2043 bfd *dynobj = (elf_hash_table (info))->dynobj;
2044
2045 if (ds.sdyn)
2046 {
2047 Elf32_External_Dyn *dyncon, *dynconend;
2048
2049 dyncon = (Elf32_External_Dyn *) ds.sdyn->contents;
2050 dynconend
2051 = (Elf32_External_Dyn *) (ds.sdyn->contents + ds.sdyn->size);
2052 for (; dyncon < dynconend; dyncon++)
2053 {
2054 Elf_Internal_Dyn internal_dyn;
2055 bfd_boolean do_it = FALSE;
2056
2057 struct elf_link_hash_entry *h = NULL;
2058 asection *s = NULL;
2059
2060 bfd_elf32_swap_dyn_in (dynobj, dyncon, &internal_dyn);
2061
2062 switch (internal_dyn.d_tag)
2063 {
2064 GET_SYMBOL_OR_SECTION (DT_INIT, "_init", NULL)
2065 GET_SYMBOL_OR_SECTION (DT_FINI, "_fini", NULL)
2066 GET_SYMBOL_OR_SECTION (DT_PLTGOT, NULL, ".plt")
2067 GET_SYMBOL_OR_SECTION (DT_JMPREL, NULL, ".rela.plt")
2068 GET_SYMBOL_OR_SECTION (DT_PLTRELSZ, NULL, ".rela.plt")
2069 GET_SYMBOL_OR_SECTION (DT_RELASZ, NULL, ".rela.plt")
2070 GET_SYMBOL_OR_SECTION (DT_VERSYM, NULL, ".gnu.version")
2071 GET_SYMBOL_OR_SECTION (DT_VERDEF, NULL, ".gnu.version_d")
2072 GET_SYMBOL_OR_SECTION (DT_VERNEED, NULL, ".gnu.version_r")
2073 default:
2074 break;
2075 }
2076
2077 /* In case the dynamic symbols should be updated with a symbol. */
2078 if (h != NULL
2079 && (h->root.type == bfd_link_hash_defined
2080 || h->root.type == bfd_link_hash_defweak))
2081 {
2082 asection *asec_ptr;
2083
2084 internal_dyn.d_un.d_val = h->root.u.def.value;
2085 asec_ptr = h->root.u.def.section;
2086 if (asec_ptr->output_section != NULL)
2087 {
2088 internal_dyn.d_un.d_val +=
2089 (asec_ptr->output_section->vma
2090 + asec_ptr->output_offset);
2091 }
2092 else
2093 {
2094 /* The symbol is imported from another shared
2095 library and does not apply to this one. */
2096 internal_dyn.d_un.d_val = 0;
2097 }
2098 do_it = TRUE;
2099 }
2100 else if (s != NULL) /* With a section information. */
2101 {
2102 switch (internal_dyn.d_tag)
2103 {
2104 case DT_PLTGOT:
2105 case DT_JMPREL:
2106 case DT_VERSYM:
2107 case DT_VERDEF:
2108 case DT_VERNEED:
2109 internal_dyn.d_un.d_ptr = (s->output_section->vma
2110 + s->output_offset);
2111 do_it = TRUE;
2112 break;
2113
2114 case DT_PLTRELSZ:
2115 internal_dyn.d_un.d_val = s->size;
2116 do_it = TRUE;
2117 break;
2118
2119 case DT_RELASZ:
2120 if (s != NULL)
2121 internal_dyn.d_un.d_val -= s->size;
2122 do_it = TRUE;
2123 break;
2124
2125 default:
2126 break;
2127 }
2128 }
2129
2130 if (do_it)
2131 bfd_elf32_swap_dyn_out (output_bfd, &internal_dyn, dyncon);
2132 }
2133
2134 if (htab->splt->size > 0)
2135 {
2136 relocate_plt_for_entry (output_bfd, info);
2137 }
2138
2139 /* TODO: Validate this. */
2140 elf_section_data (htab->srelplt->output_section)->this_hdr.sh_entsize
2141 = 0xc;
2142 }
2143
2144 /* Fill in the first three entries in the global offset table. */
2145 if (htab->sgot)
2146 {
2147 struct elf_link_hash_entry *h;
2148 h = elf_link_hash_lookup (elf_hash_table (info), "_GLOBAL_OFFSET_TABLE_",
2149 FALSE, FALSE, TRUE);
2150
2151 if (h != NULL && h->root.type != bfd_link_hash_undefined
2152 && h->root.u.def.section != NULL)
2153 {
2154 asection *sec = h->root.u.def.section;
2155
2156 if (ds.sdyn == NULL)
2157 bfd_put_32 (output_bfd, (bfd_vma) 0,
2158 sec->contents);
2159 else
2160 bfd_put_32 (output_bfd,
2161 ds.sdyn->output_section->vma + ds.sdyn->output_offset,
2162 sec->contents);
2163 bfd_put_32 (output_bfd, (bfd_vma) 0, sec->contents + 4);
2164 bfd_put_32 (output_bfd, (bfd_vma) 0, sec->contents + 8);
2165 }
2166 }
2167
2168 return TRUE;
2169 }
2170
2171 #define ADD_DYNAMIC_SYMBOL(NAME, TAG) \
2172 h = elf_link_hash_lookup (elf_hash_table (info), \
2173 NAME, FALSE, FALSE, FALSE); \
2174 if ((h != NULL && (h->ref_regular || h->def_regular))) \
2175 if (! _bfd_elf_add_dynamic_entry (info, TAG, 0)) \
2176 return FALSE;
2177
2178 /* Set the sizes of the dynamic sections. */
2179 static bfd_boolean
2180 elf_arc_size_dynamic_sections (bfd * output_bfd,
2181 struct bfd_link_info *info)
2182 {
2183 bfd * dynobj;
2184 asection * s;
2185 bfd_boolean relocs_exist = FALSE;
2186 bfd_boolean reltext_exist = FALSE;
2187 struct dynamic_sections ds = arc_create_dynamic_sections (output_bfd, info);
2188 struct elf_link_hash_table *htab = elf_hash_table (info);
2189
2190 dynobj = (elf_hash_table (info))->dynobj;
2191 BFD_ASSERT (dynobj != NULL);
2192
2193 if ((elf_hash_table (info))->dynamic_sections_created)
2194 {
2195 struct elf_link_hash_entry *h;
2196
2197 /* Set the contents of the .interp section to the
2198 interpreter. */
2199 if (!bfd_link_pic (info))
2200 {
2201 s = bfd_get_section_by_name (dynobj, ".interp");
2202 BFD_ASSERT (s != NULL);
2203 s->size = sizeof (ELF_DYNAMIC_INTERPRETER);
2204 s->contents = (unsigned char *) ELF_DYNAMIC_INTERPRETER;
2205 }
2206
2207 /* Add some entries to the .dynamic section. We fill in some of
2208 the values later, in elf_bfd_final_link, but we must add the
2209 entries now so that we know the final size of the .dynamic
2210 section. Checking if the .init section is present. We also
2211 create DT_INIT and DT_FINI entries if the init_str has been
2212 changed by the user. */
2213 ADD_DYNAMIC_SYMBOL ("init", DT_INIT);
2214 ADD_DYNAMIC_SYMBOL ("fini", DT_FINI);
2215 }
2216 else
2217 {
2218 /* We may have created entries in the .rela.got section.
2219 However, if we are not creating the dynamic sections, we will
2220 not actually use these entries. Reset the size of .rela.got,
2221 which will cause it to get stripped from the output file
2222 below. */
2223 if (htab->srelgot != NULL)
2224 htab->srelgot->size = 0;
2225 }
2226
2227 if (htab->splt != NULL && htab->splt->size == 0)
2228 htab->splt->flags |= SEC_EXCLUDE;
2229 for (s = dynobj->sections; s != NULL; s = s->next)
2230 {
2231 if ((s->flags & SEC_LINKER_CREATED) == 0)
2232 continue;
2233
2234 if (strncmp (s->name, ".rela", 5) == 0)
2235 {
2236 if (s->size == 0)
2237 {
2238 s->flags |= SEC_EXCLUDE;
2239 }
2240 else
2241 {
2242 if (strcmp (s->name, ".rela.plt") != 0)
2243 {
2244 const char *outname =
2245 bfd_get_section_name (output_bfd,
2246 htab->srelplt->output_section);
2247
2248 asection *target = bfd_get_section_by_name (output_bfd,
2249 outname + 4);
2250
2251 relocs_exist = TRUE;
2252 if (target != NULL && target->size != 0
2253 && (target->flags & SEC_READONLY) != 0
2254 && (target->flags & SEC_ALLOC) != 0)
2255 reltext_exist = TRUE;
2256 }
2257 }
2258
2259 /* We use the reloc_count field as a counter if we need to
2260 copy relocs into the output file. */
2261 s->reloc_count = 0;
2262 }
2263
2264 if (strcmp (s->name, ".dynamic") == 0)
2265 continue;
2266
2267 if (s->size != 0)
2268 s->contents = (bfd_byte *) bfd_zalloc (dynobj, s->size);
2269
2270 if (s->contents == NULL && s->size != 0)
2271 return FALSE;
2272 }
2273
2274 if (ds.sdyn)
2275 {
2276 /* TODO: Check if this is needed. */
2277 if (!bfd_link_pic (info))
2278 if (!_bfd_elf_add_dynamic_entry (info, DT_DEBUG, 0))
2279 return FALSE;
2280
2281 if (htab->splt && (htab->splt->flags & SEC_EXCLUDE) == 0)
2282 if (!_bfd_elf_add_dynamic_entry (info, DT_PLTGOT, 0)
2283 || !_bfd_elf_add_dynamic_entry (info, DT_PLTRELSZ, 0)
2284 || !_bfd_elf_add_dynamic_entry (info, DT_PLTREL, DT_RELA)
2285 || !_bfd_elf_add_dynamic_entry (info, DT_JMPREL, 0)
2286 )
2287 return FALSE;
2288
2289 if (relocs_exist == TRUE)
2290 if (!_bfd_elf_add_dynamic_entry (info, DT_RELA, 0)
2291 || !_bfd_elf_add_dynamic_entry (info, DT_RELASZ, 0)
2292 || !_bfd_elf_add_dynamic_entry (info, DT_RELAENT,
2293 sizeof (Elf32_External_Rela))
2294 )
2295 return FALSE;
2296
2297 if (reltext_exist == TRUE)
2298 if (!_bfd_elf_add_dynamic_entry (info, DT_TEXTREL, 0))
2299 return FALSE;
2300 }
2301
2302 return TRUE;
2303 }
2304
2305
2306 /* Classify dynamic relocs such that -z combreloc can reorder and combine
2307 them. */
2308 static enum elf_reloc_type_class
2309 elf32_arc_reloc_type_class (const struct bfd_link_info *info ATTRIBUTE_UNUSED,
2310 const asection *rel_sec ATTRIBUTE_UNUSED,
2311 const Elf_Internal_Rela *rela)
2312 {
2313 switch ((int) ELF32_R_TYPE (rela->r_info))
2314 {
2315 case R_ARC_RELATIVE:
2316 return reloc_class_relative;
2317 case R_ARC_JMP_SLOT:
2318 return reloc_class_plt;
2319 case R_ARC_COPY:
2320 return reloc_class_copy;
2321 /* TODO: Needed in future to support ifunc. */
2322 /*
2323 case R_ARC_IRELATIVE:
2324 return reloc_class_ifunc;
2325 */
2326 default:
2327 return reloc_class_normal;
2328 }
2329 }
2330
2331 const struct elf_size_info arc_elf32_size_info =
2332 {
2333 sizeof (Elf32_External_Ehdr),
2334 sizeof (Elf32_External_Phdr),
2335 sizeof (Elf32_External_Shdr),
2336 sizeof (Elf32_External_Rel),
2337 sizeof (Elf32_External_Rela),
2338 sizeof (Elf32_External_Sym),
2339 sizeof (Elf32_External_Dyn),
2340 sizeof (Elf_External_Note),
2341 4,
2342 1,
2343 32, 2,
2344 ELFCLASS32, EV_CURRENT,
2345 bfd_elf32_write_out_phdrs,
2346 bfd_elf32_write_shdrs_and_ehdr,
2347 bfd_elf32_checksum_contents,
2348 bfd_elf32_write_relocs,
2349 bfd_elf32_swap_symbol_in,
2350 bfd_elf32_swap_symbol_out,
2351 bfd_elf32_slurp_reloc_table,
2352 bfd_elf32_slurp_symbol_table,
2353 bfd_elf32_swap_dyn_in,
2354 bfd_elf32_swap_dyn_out,
2355 bfd_elf32_swap_reloc_in,
2356 bfd_elf32_swap_reloc_out,
2357 bfd_elf32_swap_reloca_in,
2358 bfd_elf32_swap_reloca_out
2359 };
2360
2361 #define elf_backend_size_info arc_elf32_size_info
2362
2363 static struct bfd_link_hash_table *
2364 arc_elf_link_hash_table_create (bfd *abfd)
2365 {
2366 struct elf_link_hash_table *htab;
2367
2368 htab = bfd_zmalloc (sizeof (*htab));
2369 if (htab == NULL)
2370 return NULL;
2371
2372 if (!_bfd_elf_link_hash_table_init (htab, abfd,
2373 _bfd_elf_link_hash_newfunc,
2374 sizeof (struct elf_link_hash_entry),
2375 GENERIC_ELF_DATA))
2376 {
2377 free (htab);
2378 return NULL;
2379 }
2380
2381 htab->init_got_refcount.refcount = 0;
2382 htab->init_got_refcount.glist = NULL;
2383 htab->init_got_offset.offset = 0;
2384 htab->init_got_offset.glist = NULL;
2385 return (struct bfd_link_hash_table *) htab;
2386 }
2387
2388 /* Hook called by the linker routine which adds symbols from an object
2389 file. */
2390
2391 static bfd_boolean
2392 elf_arc_add_symbol_hook (bfd * abfd,
2393 struct bfd_link_info * info,
2394 Elf_Internal_Sym * sym,
2395 const char ** namep ATTRIBUTE_UNUSED,
2396 flagword * flagsp ATTRIBUTE_UNUSED,
2397 asection ** secp ATTRIBUTE_UNUSED,
2398 bfd_vma * valp ATTRIBUTE_UNUSED)
2399 {
2400 if (ELF_ST_TYPE (sym->st_info) == STT_GNU_IFUNC
2401 && (abfd->flags & DYNAMIC) == 0
2402 && bfd_get_flavour (info->output_bfd) == bfd_target_elf_flavour)
2403 elf_tdata (info->output_bfd)->has_gnu_symbols |= elf_gnu_symbol_ifunc;
2404
2405 return TRUE;
2406 }
2407
2408 #define TARGET_LITTLE_SYM arc_elf32_le_vec
2409 #define TARGET_LITTLE_NAME "elf32-littlearc"
2410 #define TARGET_BIG_SYM arc_elf32_be_vec
2411 #define TARGET_BIG_NAME "elf32-bigarc"
2412 #define ELF_ARCH bfd_arch_arc
2413 #define ELF_MACHINE_CODE EM_ARC_COMPACT
2414 #define ELF_MACHINE_ALT1 EM_ARC_COMPACT2
2415 #define ELF_MAXPAGESIZE 0x2000
2416
2417 #define bfd_elf32_bfd_link_hash_table_create arc_elf_link_hash_table_create
2418
2419 #define bfd_elf32_bfd_merge_private_bfd_data arc_elf_merge_private_bfd_data
2420 #define bfd_elf32_bfd_reloc_type_lookup arc_elf32_bfd_reloc_type_lookup
2421 #define bfd_elf32_bfd_set_private_flags arc_elf_set_private_flags
2422 #define bfd_elf32_bfd_print_private_bfd_data arc_elf_print_private_bfd_data
2423 #define bfd_elf32_bfd_copy_private_bfd_data arc_elf_copy_private_bfd_data
2424
2425 #define elf_info_to_howto_rel arc_info_to_howto_rel
2426 #define elf_backend_object_p arc_elf_object_p
2427 #define elf_backend_final_write_processing arc_elf_final_write_processing
2428
2429 #define elf_backend_relocate_section elf_arc_relocate_section
2430 #define elf_backend_check_relocs elf_arc_check_relocs
2431 #define elf_backend_create_dynamic_sections _bfd_elf_create_dynamic_sections
2432
2433 #define elf_backend_reloc_type_class elf32_arc_reloc_type_class
2434
2435 #define elf_backend_adjust_dynamic_symbol elf_arc_adjust_dynamic_symbol
2436 #define elf_backend_finish_dynamic_symbol elf_arc_finish_dynamic_symbol
2437
2438 #define elf_backend_finish_dynamic_sections elf_arc_finish_dynamic_sections
2439 #define elf_backend_size_dynamic_sections elf_arc_size_dynamic_sections
2440 #define elf_backend_add_symbol_hook elf_arc_add_symbol_hook
2441
2442 #define elf_backend_can_gc_sections 1
2443 #define elf_backend_want_got_plt 1
2444 #define elf_backend_plt_readonly 1
2445 #define elf_backend_rela_plts_and_copies_p 1
2446 #define elf_backend_want_plt_sym 0
2447 #define elf_backend_got_header_size 12
2448
2449 #define elf_backend_may_use_rel_p 0
2450 #define elf_backend_may_use_rela_p 1
2451 #define elf_backend_default_use_rela_p 1
2452
2453 #define elf_backend_default_execstack 0
2454
2455 #include "elf32-target.h"