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