elf32-bfin.c revision 1.1.1.11 1 1.1 christos /* ADI Blackfin BFD support for 32-bit ELF.
2 1.1.1.11 christos Copyright (C) 2005-2024 Free Software Foundation, Inc.
3 1.1 christos
4 1.1 christos This file is part of BFD, the Binary File Descriptor library.
5 1.1 christos
6 1.1 christos This program is free software; you can redistribute it and/or modify
7 1.1 christos it under the terms of the GNU General Public License as published by
8 1.1 christos the Free Software Foundation; either version 3 of the License, or
9 1.1 christos (at your option) any later version.
10 1.1 christos
11 1.1 christos This program is distributed in the hope that it will be useful,
12 1.1 christos but WITHOUT ANY WARRANTY; without even the implied warranty of
13 1.1 christos MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 1.1 christos GNU General Public License for more details.
15 1.1 christos
16 1.1 christos You should have received a copy of the GNU General Public License
17 1.1 christos along with this program; if not, write to the Free Software
18 1.1 christos Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
19 1.1 christos MA 02110-1301, USA. */
20 1.1 christos
21 1.1 christos #include "sysdep.h"
22 1.1 christos #include "bfd.h"
23 1.1 christos #include "libbfd.h"
24 1.1 christos #include "elf-bfd.h"
25 1.1 christos #include "elf/bfin.h"
26 1.1 christos #include "dwarf2.h"
27 1.1 christos #include "hashtab.h"
28 1.1.1.9 christos #include "elf32-bfin.h"
29 1.1 christos
30 1.1 christos /* FUNCTION : bfin_pltpc_reloc
31 1.1 christos ABSTRACT : TODO : figure out how to handle pltpc relocs. */
32 1.1 christos static bfd_reloc_status_type
33 1.1 christos bfin_pltpc_reloc (
34 1.1 christos bfd *abfd ATTRIBUTE_UNUSED,
35 1.1 christos arelent *reloc_entry ATTRIBUTE_UNUSED,
36 1.1 christos asymbol *symbol ATTRIBUTE_UNUSED,
37 1.1.1.2 christos void * data ATTRIBUTE_UNUSED,
38 1.1 christos asection *input_section ATTRIBUTE_UNUSED,
39 1.1 christos bfd *output_bfd ATTRIBUTE_UNUSED,
40 1.1 christos char **error_message ATTRIBUTE_UNUSED)
41 1.1 christos {
42 1.1 christos bfd_reloc_status_type flag = bfd_reloc_ok;
43 1.1 christos return flag;
44 1.1 christos }
45 1.1 christos
46 1.1 christos
48 1.1 christos static bfd_reloc_status_type
49 1.1.1.8 christos bfin_pcrel24_reloc (bfd *abfd,
50 1.1.1.8 christos arelent *reloc_entry,
51 1.1.1.8 christos asymbol *symbol,
52 1.1.1.8 christos void * data,
53 1.1.1.8 christos asection *input_section,
54 1.1.1.8 christos bfd *output_bfd,
55 1.1 christos char **error_message ATTRIBUTE_UNUSED)
56 1.1 christos {
57 1.1 christos bfd_vma relocation;
58 1.1 christos bfd_size_type addr = reloc_entry->address;
59 1.1 christos bfd_vma output_base = 0;
60 1.1 christos reloc_howto_type *howto = reloc_entry->howto;
61 1.1.1.10 christos asection *output_section;
62 1.1 christos bool relocatable = (output_bfd != NULL);
63 1.1.1.10 christos
64 1.1 christos if (!bfd_reloc_offset_in_range (howto, abfd, input_section, addr - 2))
65 1.1 christos return bfd_reloc_outofrange;
66 1.1 christos
67 1.1 christos if (bfd_is_und_section (symbol->section)
68 1.1 christos && (symbol->flags & BSF_WEAK) == 0
69 1.1 christos && !relocatable)
70 1.1 christos return bfd_reloc_undefined;
71 1.1 christos
72 1.1 christos if (bfd_is_com_section (symbol->section))
73 1.1 christos relocation = 0;
74 1.1 christos else
75 1.1 christos relocation = symbol->value;
76 1.1 christos
77 1.1 christos output_section = symbol->section->output_section;
78 1.1 christos
79 1.1 christos if (relocatable)
80 1.1 christos output_base = 0;
81 1.1 christos else
82 1.1 christos output_base = output_section->vma;
83 1.1 christos
84 1.1 christos if (!relocatable || !strcmp (symbol->name, symbol->section->name))
85 1.1 christos relocation += output_base + symbol->section->output_offset;
86 1.1 christos
87 1.1 christos if (!relocatable && !strcmp (symbol->name, symbol->section->name))
88 1.1 christos relocation += reloc_entry->addend;
89 1.1 christos
90 1.1 christos relocation -= input_section->output_section->vma + input_section->output_offset;
91 1.1 christos relocation -= reloc_entry->address;
92 1.1 christos
93 1.1 christos if (howto->complain_on_overflow != complain_overflow_dont)
94 1.1 christos {
95 1.1 christos bfd_reloc_status_type status;
96 1.1 christos status = bfd_check_overflow (howto->complain_on_overflow,
97 1.1 christos howto->bitsize,
98 1.1 christos howto->rightshift,
99 1.1 christos bfd_arch_bits_per_address(abfd),
100 1.1 christos relocation);
101 1.1 christos if (status != bfd_reloc_ok)
102 1.1 christos return status;
103 1.1 christos }
104 1.1 christos
105 1.1 christos /* if rightshift is 1 and the number odd, return error. */
106 1.1 christos if (howto->rightshift && (relocation & 0x01))
107 1.1.1.7 christos {
108 1.1 christos _bfd_error_handler (_("relocation should be even number"));
109 1.1 christos return bfd_reloc_overflow;
110 1.1 christos }
111 1.1 christos
112 1.1 christos relocation >>= (bfd_vma) howto->rightshift;
113 1.1 christos /* Shift everything up to where it's going to be used. */
114 1.1 christos
115 1.1 christos relocation <<= (bfd_vma) howto->bitpos;
116 1.1 christos
117 1.1 christos if (relocatable)
118 1.1 christos {
119 1.1 christos reloc_entry->address += input_section->output_offset;
120 1.1 christos reloc_entry->addend += symbol->section->output_offset;
121 1.1 christos }
122 1.1 christos
123 1.1 christos {
124 1.1 christos short x;
125 1.1 christos
126 1.1 christos /* We are getting reloc_entry->address 2 byte off from
127 1.1 christos the start of instruction. Assuming absolute postion
128 1.1 christos of the reloc data. But, following code had been written assuming
129 1.1 christos reloc address is starting at begining of instruction.
130 1.1 christos To compensate that I have increased the value of
131 1.1 christos relocation by 1 (effectively 2) and used the addr -2 instead of addr. */
132 1.1 christos
133 1.1 christos relocation += 1;
134 1.1 christos x = bfd_get_16 (abfd, (bfd_byte *) data + addr - 2);
135 1.1 christos x = (x & 0xff00) | ((relocation >> 16) & 0xff);
136 1.1 christos bfd_put_16 (abfd, x, (unsigned char *) data + addr - 2);
137 1.1 christos
138 1.1 christos x = bfd_get_16 (abfd, (bfd_byte *) data + addr);
139 1.1 christos x = relocation & 0xFFFF;
140 1.1 christos bfd_put_16 (abfd, x, (unsigned char *) data + addr );
141 1.1 christos }
142 1.1 christos return bfd_reloc_ok;
143 1.1 christos }
144 1.1 christos
145 1.1 christos static bfd_reloc_status_type
146 1.1.1.9 christos bfin_imm16_reloc (bfd *abfd,
147 1.1.1.9 christos arelent *reloc_entry,
148 1.1.1.9 christos asymbol *symbol,
149 1.1.1.9 christos void * data,
150 1.1.1.9 christos asection *input_section,
151 1.1.1.9 christos bfd *output_bfd,
152 1.1 christos char **error_message ATTRIBUTE_UNUSED)
153 1.1 christos {
154 1.1 christos bfd_vma relocation, x;
155 1.1 christos bfd_size_type reloc_addr = reloc_entry->address;
156 1.1 christos bfd_vma output_base = 0;
157 1.1 christos reloc_howto_type *howto = reloc_entry->howto;
158 1.1.1.10 christos asection *output_section;
159 1.1 christos bool relocatable = (output_bfd != NULL);
160 1.1 christos
161 1.1.1.10 christos /* Is the address of the relocation really within the section? */
162 1.1 christos if (!bfd_reloc_offset_in_range (howto, abfd, input_section, reloc_addr))
163 1.1 christos return bfd_reloc_outofrange;
164 1.1 christos
165 1.1 christos if (bfd_is_und_section (symbol->section)
166 1.1 christos && (symbol->flags & BSF_WEAK) == 0
167 1.1 christos && !relocatable)
168 1.1 christos return bfd_reloc_undefined;
169 1.1 christos
170 1.1 christos output_section = symbol->section->output_section;
171 1.1 christos relocation = symbol->value;
172 1.1 christos
173 1.1 christos /* Convert input-section-relative symbol value to absolute. */
174 1.1 christos if (relocatable)
175 1.1 christos output_base = 0;
176 1.1 christos else
177 1.1 christos output_base = output_section->vma;
178 1.1 christos
179 1.1 christos if (!relocatable || !strcmp (symbol->name, symbol->section->name))
180 1.1 christos relocation += output_base + symbol->section->output_offset;
181 1.1 christos
182 1.1 christos /* Add in supplied addend. */
183 1.1 christos relocation += reloc_entry->addend;
184 1.1 christos
185 1.1 christos if (relocatable)
186 1.1 christos {
187 1.1 christos reloc_entry->address += input_section->output_offset;
188 1.1 christos reloc_entry->addend += symbol->section->output_offset;
189 1.1 christos }
190 1.1 christos else
191 1.1 christos {
192 1.1 christos reloc_entry->addend = 0;
193 1.1 christos }
194 1.1 christos
195 1.1 christos if (howto->complain_on_overflow != complain_overflow_dont)
196 1.1 christos {
197 1.1 christos bfd_reloc_status_type flag;
198 1.1 christos flag = bfd_check_overflow (howto->complain_on_overflow,
199 1.1 christos howto->bitsize,
200 1.1 christos howto->rightshift,
201 1.1 christos bfd_arch_bits_per_address(abfd),
202 1.1 christos relocation);
203 1.1 christos if (flag != bfd_reloc_ok)
204 1.1 christos return flag;
205 1.1 christos }
206 1.1 christos
207 1.1 christos /* Here the variable relocation holds the final address of the
208 1.1 christos symbol we are relocating against, plus any addend. */
209 1.1 christos
210 1.1 christos relocation >>= (bfd_vma) howto->rightshift;
211 1.1 christos x = relocation;
212 1.1 christos bfd_put_16 (abfd, x, (unsigned char *) data + reloc_addr);
213 1.1 christos return bfd_reloc_ok;
214 1.1 christos }
215 1.1 christos
216 1.1 christos
217 1.1 christos static bfd_reloc_status_type
218 1.1.1.8 christos bfin_byte4_reloc (bfd *abfd,
219 1.1.1.8 christos arelent *reloc_entry,
220 1.1.1.8 christos asymbol *symbol,
221 1.1.1.8 christos void * data,
222 1.1.1.8 christos asection *input_section,
223 1.1.1.8 christos bfd *output_bfd,
224 1.1 christos char **error_message ATTRIBUTE_UNUSED)
225 1.1 christos {
226 1.1 christos bfd_vma relocation, x;
227 1.1 christos bfd_size_type addr = reloc_entry->address;
228 1.1 christos bfd_vma output_base = 0;
229 1.1.1.10 christos asection *output_section;
230 1.1 christos bool relocatable = (output_bfd != NULL);
231 1.1 christos
232 1.1.1.10 christos /* Is the address of the relocation really within the section? */
233 1.1.1.10 christos if (!bfd_reloc_offset_in_range (reloc_entry->howto, abfd, input_section,
234 1.1 christos addr))
235 1.1 christos return bfd_reloc_outofrange;
236 1.1 christos
237 1.1 christos if (bfd_is_und_section (symbol->section)
238 1.1 christos && (symbol->flags & BSF_WEAK) == 0
239 1.1 christos && !relocatable)
240 1.1 christos return bfd_reloc_undefined;
241 1.1 christos
242 1.1 christos output_section = symbol->section->output_section;
243 1.1 christos relocation = symbol->value;
244 1.1 christos /* Convert input-section-relative symbol value to absolute. */
245 1.1 christos if (relocatable)
246 1.1 christos output_base = 0;
247 1.1 christos else
248 1.1 christos output_base = output_section->vma;
249 1.1 christos
250 1.1 christos if ((symbol->name
251 1.1 christos && symbol->section->name
252 1.1 christos && !strcmp (symbol->name, symbol->section->name))
253 1.1 christos || !relocatable)
254 1.1 christos {
255 1.1 christos relocation += output_base + symbol->section->output_offset;
256 1.1 christos }
257 1.1 christos
258 1.1 christos relocation += reloc_entry->addend;
259 1.1 christos
260 1.1 christos if (relocatable)
261 1.1 christos {
262 1.1 christos /* This output will be relocatable ... like ld -r. */
263 1.1 christos reloc_entry->address += input_section->output_offset;
264 1.1 christos reloc_entry->addend += symbol->section->output_offset;
265 1.1 christos }
266 1.1 christos else
267 1.1 christos {
268 1.1 christos reloc_entry->addend = 0;
269 1.1 christos }
270 1.1 christos
271 1.1 christos /* Here the variable relocation holds the final address of the
272 1.1 christos symbol we are relocating against, plus any addend. */
273 1.1 christos x = relocation & 0xFFFF0000;
274 1.1 christos x >>=16;
275 1.1 christos bfd_put_16 (abfd, x, (unsigned char *) data + addr + 2);
276 1.1 christos
277 1.1 christos x = relocation & 0x0000FFFF;
278 1.1 christos bfd_put_16 (abfd, x, (unsigned char *) data + addr);
279 1.1 christos return bfd_reloc_ok;
280 1.1 christos }
281 1.1 christos
282 1.1 christos /* bfin_bfd_reloc handles the blackfin arithmetic relocations.
283 1.1 christos Use this instead of bfd_perform_relocation. */
284 1.1 christos static bfd_reloc_status_type
285 1.1 christos bfin_bfd_reloc (bfd *abfd,
286 1.1.1.9 christos arelent *reloc_entry,
287 1.1.1.9 christos asymbol *symbol,
288 1.1.1.9 christos void * data,
289 1.1.1.9 christos asection *input_section,
290 1.1.1.9 christos bfd *output_bfd,
291 1.1 christos char **error_message ATTRIBUTE_UNUSED)
292 1.1 christos {
293 1.1 christos bfd_vma relocation;
294 1.1 christos bfd_size_type addr = reloc_entry->address;
295 1.1 christos bfd_vma output_base = 0;
296 1.1 christos reloc_howto_type *howto = reloc_entry->howto;
297 1.1.1.10 christos asection *output_section;
298 1.1 christos bool relocatable = (output_bfd != NULL);
299 1.1 christos
300 1.1.1.10 christos /* Is the address of the relocation really within the section? */
301 1.1 christos if (!bfd_reloc_offset_in_range (howto, abfd, input_section, addr))
302 1.1 christos return bfd_reloc_outofrange;
303 1.1 christos
304 1.1 christos if (bfd_is_und_section (symbol->section)
305 1.1 christos && (symbol->flags & BSF_WEAK) == 0
306 1.1 christos && !relocatable)
307 1.1 christos return bfd_reloc_undefined;
308 1.1 christos
309 1.1 christos /* Get symbol value. (Common symbols are special.) */
310 1.1 christos if (bfd_is_com_section (symbol->section))
311 1.1 christos relocation = 0;
312 1.1 christos else
313 1.1 christos relocation = symbol->value;
314 1.1 christos
315 1.1 christos output_section = symbol->section->output_section;
316 1.1 christos
317 1.1 christos /* Convert input-section-relative symbol value to absolute. */
318 1.1 christos if (relocatable)
319 1.1 christos output_base = 0;
320 1.1 christos else
321 1.1 christos output_base = output_section->vma;
322 1.1 christos
323 1.1 christos if (!relocatable || !strcmp (symbol->name, symbol->section->name))
324 1.1 christos relocation += output_base + symbol->section->output_offset;
325 1.1 christos
326 1.1 christos if (!relocatable && !strcmp (symbol->name, symbol->section->name))
327 1.1 christos {
328 1.1 christos /* Add in supplied addend. */
329 1.1 christos relocation += reloc_entry->addend;
330 1.1 christos }
331 1.1 christos
332 1.1 christos /* Here the variable relocation holds the final address of the
333 1.1 christos symbol we are relocating against, plus any addend. */
334 1.1.1.8 christos
335 1.1 christos if (howto->pc_relative)
336 1.1 christos {
337 1.1 christos relocation -= input_section->output_section->vma + input_section->output_offset;
338 1.1.1.8 christos
339 1.1.1.8 christos if (howto->pcrel_offset)
340 1.1 christos relocation -= reloc_entry->address;
341 1.1 christos }
342 1.1 christos
343 1.1 christos if (relocatable)
344 1.1 christos {
345 1.1 christos reloc_entry->address += input_section->output_offset;
346 1.1 christos reloc_entry->addend += symbol->section->output_offset;
347 1.1 christos }
348 1.1 christos
349 1.1 christos if (howto->complain_on_overflow != complain_overflow_dont)
350 1.1 christos {
351 1.1 christos bfd_reloc_status_type status;
352 1.1 christos
353 1.1.1.8 christos status = bfd_check_overflow (howto->complain_on_overflow,
354 1.1.1.8 christos howto->bitsize,
355 1.1.1.8 christos howto->rightshift,
356 1.1.1.8 christos bfd_arch_bits_per_address(abfd),
357 1.1 christos relocation);
358 1.1 christos if (status != bfd_reloc_ok)
359 1.1 christos return status;
360 1.1 christos }
361 1.1 christos
362 1.1 christos /* If rightshift is 1 and the number odd, return error. */
363 1.1 christos if (howto->rightshift && (relocation & 0x01))
364 1.1.1.7 christos {
365 1.1 christos _bfd_error_handler (_("relocation should be even number"));
366 1.1 christos return bfd_reloc_overflow;
367 1.1 christos }
368 1.1 christos
369 1.1 christos relocation >>= (bfd_vma) howto->rightshift;
370 1.1 christos
371 1.1 christos /* Shift everything up to where it's going to be used. */
372 1.1 christos
373 1.1 christos relocation <<= (bfd_vma) howto->bitpos;
374 1.1 christos
375 1.1 christos #define DOIT(x) \
376 1.1 christos x = ( (x & ~howto->dst_mask) | (relocation & howto->dst_mask))
377 1.1 christos
378 1.1.1.10 christos /* handle 8 and 16 bit relocations here. */
379 1.1 christos switch (bfd_get_reloc_size (howto))
380 1.1.1.10 christos {
381 1.1 christos case 1:
382 1.1.1.8 christos {
383 1.1.1.8 christos char x = bfd_get_8 (abfd, (char *) data + addr);
384 1.1.1.8 christos DOIT (x);
385 1.1 christos bfd_put_8 (abfd, x, (unsigned char *) data + addr);
386 1.1 christos }
387 1.1 christos break;
388 1.1.1.10 christos
389 1.1 christos case 2:
390 1.1.1.8 christos {
391 1.1.1.8 christos unsigned short x = bfd_get_16 (abfd, (bfd_byte *) data + addr);
392 1.1.1.8 christos DOIT (x);
393 1.1 christos bfd_put_16 (abfd, (bfd_vma) x, (unsigned char *) data + addr);
394 1.1 christos }
395 1.1 christos break;
396 1.1 christos
397 1.1 christos default:
398 1.1 christos return bfd_reloc_other;
399 1.1 christos }
400 1.1 christos
401 1.1 christos return bfd_reloc_ok;
402 1.1 christos }
403 1.1 christos
404 1.1 christos /* HOWTO Table for blackfin.
405 1.1 christos Blackfin relocations are fairly complicated.
406 1.1 christos Some of the salient features are
407 1.1 christos a. Even numbered offsets. A number of (not all) relocations are
408 1.1 christos even numbered. This means that the rightmost bit is not stored.
409 1.1 christos Needs to right shift by 1 and check to see if value is not odd
410 1.1 christos b. A relocation can be an expression. An expression takes on
411 1.1 christos a variety of relocations arranged in a stack.
412 1.1 christos As a result, we cannot use the standard generic function as special
413 1.1 christos function. We will have our own, which is very similar to the standard
414 1.1 christos generic function except that it understands how to get the value from
415 1.1 christos the relocation stack. . */
416 1.1 christos
417 1.1 christos #define BFIN_RELOC_MIN 0
418 1.1 christos #define BFIN_RELOC_MAX 0x21
419 1.1 christos #define BFIN_GNUEXT_RELOC_MIN 0x40
420 1.1 christos #define BFIN_GNUEXT_RELOC_MAX 0x43
421 1.1 christos #define BFIN_ARELOC_MIN 0xE0
422 1.1 christos #define BFIN_ARELOC_MAX 0xF3
423 1.1 christos
424 1.1 christos static reloc_howto_type bfin_howto_table [] =
425 1.1 christos {
426 1.1 christos /* This reloc does nothing. . */
427 1.1 christos HOWTO (R_BFIN_UNUSED0, /* type. */
428 1.1.1.10 christos 0, /* rightshift. */
429 1.1.1.5 christos 0, /* size. */
430 1.1.1.10 christos 0, /* bitsize. */
431 1.1 christos false, /* pc_relative. */
432 1.1.1.5 christos 0, /* bitpos. */
433 1.1 christos complain_overflow_dont, /* complain_on_overflow. */
434 1.1 christos bfd_elf_generic_reloc, /* special_function. */
435 1.1.1.10 christos "R_BFIN_UNUSED0", /* name. */
436 1.1 christos false, /* partial_inplace. */
437 1.1 christos 0, /* src_mask. */
438 1.1.1.10 christos 0, /* dst_mask. */
439 1.1 christos false), /* pcrel_offset. */
440 1.1 christos
441 1.1 christos HOWTO (R_BFIN_PCREL5M2, /* type. */
442 1.1.1.10 christos 1, /* rightshift. */
443 1.1 christos 2, /* size. */
444 1.1.1.10 christos 4, /* bitsize. */
445 1.1 christos true, /* pc_relative. */
446 1.1 christos 0, /* bitpos. */
447 1.1 christos complain_overflow_unsigned, /* complain_on_overflow. */
448 1.1 christos bfin_bfd_reloc, /* special_function. */
449 1.1.1.10 christos "R_BFIN_PCREL5M2", /* name. */
450 1.1 christos false, /* partial_inplace. */
451 1.1 christos 0, /* src_mask. */
452 1.1.1.10 christos 0x0000000F, /* dst_mask. */
453 1.1 christos false), /* pcrel_offset. */
454 1.1 christos
455 1.1 christos HOWTO (R_BFIN_UNUSED1, /* type. */
456 1.1.1.10 christos 0, /* rightshift. */
457 1.1.1.5 christos 0, /* size. */
458 1.1.1.10 christos 0, /* bitsize. */
459 1.1 christos false, /* pc_relative. */
460 1.1.1.5 christos 0, /* bitpos. */
461 1.1 christos complain_overflow_dont, /* complain_on_overflow. */
462 1.1 christos bfd_elf_generic_reloc, /* special_function. */
463 1.1.1.10 christos "R_BFIN_UNUSED1", /* name. */
464 1.1 christos false, /* partial_inplace. */
465 1.1 christos 0, /* src_mask. */
466 1.1.1.10 christos 0, /* dst_mask. */
467 1.1 christos false), /* pcrel_offset. */
468 1.1 christos
469 1.1 christos HOWTO (R_BFIN_PCREL10, /* type. */
470 1.1.1.10 christos 1, /* rightshift. */
471 1.1 christos 2, /* size. */
472 1.1.1.10 christos 10, /* bitsize. */
473 1.1 christos true, /* pc_relative. */
474 1.1 christos 0, /* bitpos. */
475 1.1 christos complain_overflow_signed, /* complain_on_overflow. */
476 1.1 christos bfin_bfd_reloc, /* special_function. */
477 1.1.1.10 christos "R_BFIN_PCREL10", /* name. */
478 1.1 christos false, /* partial_inplace. */
479 1.1 christos 0, /* src_mask. */
480 1.1.1.10 christos 0x000003FF, /* dst_mask. */
481 1.1 christos true), /* pcrel_offset. */
482 1.1 christos
483 1.1 christos HOWTO (R_BFIN_PCREL12_JUMP, /* type. */
484 1.1 christos 1, /* rightshift. */
485 1.1 christos /* the offset is actually 13 bit
486 1.1 christos aligned on a word boundary so
487 1.1 christos only 12 bits have to be used.
488 1.1.1.10 christos Right shift the rightmost bit.. */
489 1.1 christos 2, /* size. */
490 1.1.1.10 christos 12, /* bitsize. */
491 1.1 christos true, /* pc_relative. */
492 1.1 christos 0, /* bitpos. */
493 1.1 christos complain_overflow_signed, /* complain_on_overflow. */
494 1.1 christos bfin_bfd_reloc, /* special_function. */
495 1.1.1.10 christos "R_BFIN_PCREL12_JUMP", /* name. */
496 1.1 christos false, /* partial_inplace. */
497 1.1 christos 0, /* src_mask. */
498 1.1.1.10 christos 0x0FFF, /* dst_mask. */
499 1.1 christos true), /* pcrel_offset. */
500 1.1 christos
501 1.1 christos HOWTO (R_BFIN_RIMM16, /* type. */
502 1.1.1.10 christos 0, /* rightshift. */
503 1.1 christos 2, /* size. */
504 1.1.1.10 christos 16, /* bitsize. */
505 1.1 christos false, /* pc_relative. */
506 1.1 christos 0, /* bitpos. */
507 1.1 christos complain_overflow_signed, /* complain_on_overflow. */
508 1.1 christos bfin_imm16_reloc, /* special_function. */
509 1.1.1.10 christos "R_BFIN_RIMM16", /* name. */
510 1.1 christos false, /* partial_inplace. */
511 1.1 christos 0, /* src_mask. */
512 1.1.1.10 christos 0x0000FFFF, /* dst_mask. */
513 1.1 christos true), /* pcrel_offset. */
514 1.1 christos
515 1.1 christos HOWTO (R_BFIN_LUIMM16, /* type. */
516 1.1.1.10 christos 0, /* rightshift. */
517 1.1 christos 2, /* size. */
518 1.1.1.10 christos 16, /* bitsize. */
519 1.1 christos false, /* pc_relative. */
520 1.1 christos 0, /* bitpos. */
521 1.1 christos complain_overflow_dont, /* complain_on_overflow. */
522 1.1 christos bfin_imm16_reloc, /* special_function. */
523 1.1.1.10 christos "R_BFIN_LUIMM16", /* name. */
524 1.1 christos false, /* partial_inplace. */
525 1.1 christos 0, /* src_mask. */
526 1.1.1.10 christos 0x0000FFFF, /* dst_mask. */
527 1.1 christos true), /* pcrel_offset. */
528 1.1 christos
529 1.1 christos HOWTO (R_BFIN_HUIMM16, /* type. */
530 1.1.1.10 christos 16, /* rightshift. */
531 1.1 christos 2, /* size. */
532 1.1.1.10 christos 16, /* bitsize. */
533 1.1 christos false, /* pc_relative. */
534 1.1 christos 0, /* bitpos. */
535 1.1 christos complain_overflow_unsigned, /* complain_on_overflow. */
536 1.1 christos bfin_imm16_reloc, /* special_function. */
537 1.1.1.10 christos "R_BFIN_HUIMM16", /* name. */
538 1.1 christos false, /* partial_inplace. */
539 1.1 christos 0, /* src_mask. */
540 1.1.1.10 christos 0x0000FFFF, /* dst_mask. */
541 1.1 christos true), /* pcrel_offset. */
542 1.1 christos
543 1.1 christos HOWTO (R_BFIN_PCREL12_JUMP_S, /* type. */
544 1.1.1.10 christos 1, /* rightshift. */
545 1.1 christos 2, /* size. */
546 1.1.1.10 christos 12, /* bitsize. */
547 1.1 christos true, /* pc_relative. */
548 1.1 christos 0, /* bitpos. */
549 1.1 christos complain_overflow_signed, /* complain_on_overflow. */
550 1.1 christos bfin_bfd_reloc, /* special_function. */
551 1.1.1.10 christos "R_BFIN_PCREL12_JUMP_S", /* name. */
552 1.1 christos false, /* partial_inplace. */
553 1.1 christos 0, /* src_mask. */
554 1.1.1.10 christos 0x00000FFF, /* dst_mask. */
555 1.1 christos true), /* pcrel_offset. */
556 1.1 christos
557 1.1.1.8 christos HOWTO (R_BFIN_PCREL24_JUMP_X, /* type. */
558 1.1.1.10 christos 1, /* rightshift. */
559 1.1.1.8 christos 4, /* size. */
560 1.1.1.10 christos 24, /* bitsize. */
561 1.1.1.8 christos true, /* pc_relative. */
562 1.1.1.8 christos 0, /* bitpos. */
563 1.1.1.8 christos complain_overflow_signed, /* complain_on_overflow. */
564 1.1 christos bfin_pcrel24_reloc, /* special_function. */
565 1.1.1.10 christos "R_BFIN_PCREL24_JUMP_X", /* name. */
566 1.1 christos false, /* partial_inplace. */
567 1.1 christos 0, /* src_mask. */
568 1.1.1.10 christos 0x00FFFFFF, /* dst_mask. */
569 1.1 christos true), /* pcrel_offset. */
570 1.1 christos
571 1.1 christos HOWTO (R_BFIN_PCREL24, /* type. */
572 1.1.1.10 christos 1, /* rightshift. */
573 1.1 christos 4, /* size. */
574 1.1.1.10 christos 24, /* bitsize. */
575 1.1 christos true, /* pc_relative. */
576 1.1 christos 0, /* bitpos. */
577 1.1 christos complain_overflow_signed, /* complain_on_overflow. */
578 1.1 christos bfin_pcrel24_reloc, /* special_function. */
579 1.1.1.10 christos "R_BFIN_PCREL24", /* name. */
580 1.1 christos false, /* partial_inplace. */
581 1.1 christos 0, /* src_mask. */
582 1.1.1.10 christos 0x00FFFFFF, /* dst_mask. */
583 1.1 christos true), /* pcrel_offset. */
584 1.1 christos
585 1.1 christos HOWTO (R_BFIN_UNUSEDB, /* type. */
586 1.1.1.10 christos 0, /* rightshift. */
587 1.1.1.5 christos 0, /* size. */
588 1.1.1.10 christos 0, /* bitsize. */
589 1.1 christos false, /* pc_relative. */
590 1.1 christos 0, /* bitpos. */
591 1.1 christos complain_overflow_dont, /* complain_on_overflow. */
592 1.1 christos bfd_elf_generic_reloc, /* special_function. */
593 1.1.1.10 christos "R_BFIN_UNUSEDB", /* name. */
594 1.1 christos false, /* partial_inplace. */
595 1.1 christos 0, /* src_mask. */
596 1.1.1.10 christos 0, /* dst_mask. */
597 1.1 christos false), /* pcrel_offset. */
598 1.1 christos
599 1.1 christos HOWTO (R_BFIN_UNUSEDC, /* type. */
600 1.1.1.10 christos 0, /* rightshift. */
601 1.1.1.5 christos 0, /* size. */
602 1.1.1.10 christos 0, /* bitsize. */
603 1.1 christos false, /* pc_relative. */
604 1.1 christos 0, /* bitpos. */
605 1.1 christos complain_overflow_dont, /* complain_on_overflow. */
606 1.1 christos bfd_elf_generic_reloc, /* special_function. */
607 1.1.1.10 christos "R_BFIN_UNUSEDC", /* name. */
608 1.1 christos false, /* partial_inplace. */
609 1.1 christos 0, /* src_mask. */
610 1.1.1.10 christos 0, /* dst_mask. */
611 1.1 christos false), /* pcrel_offset. */
612 1.1 christos
613 1.1 christos HOWTO (R_BFIN_PCREL24_JUMP_L, /* type. */
614 1.1.1.10 christos 1, /* rightshift. */
615 1.1 christos 4, /* size. */
616 1.1.1.10 christos 24, /* bitsize. */
617 1.1 christos true, /* pc_relative. */
618 1.1 christos 0, /* bitpos. */
619 1.1 christos complain_overflow_signed, /* complain_on_overflow. */
620 1.1 christos bfin_pcrel24_reloc, /* special_function. */
621 1.1.1.10 christos "R_BFIN_PCREL24_JUMP_L", /* name. */
622 1.1 christos false, /* partial_inplace. */
623 1.1 christos 0, /* src_mask. */
624 1.1.1.10 christos 0x00FFFFFF, /* dst_mask. */
625 1.1 christos true), /* pcrel_offset. */
626 1.1 christos
627 1.1 christos HOWTO (R_BFIN_PCREL24_CALL_X, /* type. */
628 1.1.1.10 christos 1, /* rightshift. */
629 1.1 christos 4, /* size. */
630 1.1.1.10 christos 24, /* bitsize. */
631 1.1 christos true, /* pc_relative. */
632 1.1 christos 0, /* bitpos. */
633 1.1 christos complain_overflow_signed, /* complain_on_overflow. */
634 1.1 christos bfin_pcrel24_reloc, /* special_function. */
635 1.1.1.10 christos "R_BFIN_PCREL24_CALL_X", /* name. */
636 1.1 christos false, /* partial_inplace. */
637 1.1 christos 0, /* src_mask. */
638 1.1.1.10 christos 0x00FFFFFF, /* dst_mask. */
639 1.1 christos true), /* pcrel_offset. */
640 1.1 christos
641 1.1 christos HOWTO (R_BFIN_VAR_EQ_SYMB, /* type. */
642 1.1.1.10 christos 0, /* rightshift. */
643 1.1 christos 4, /* size. */
644 1.1.1.10 christos 32, /* bitsize. */
645 1.1 christos false, /* pc_relative. */
646 1.1 christos 0, /* bitpos. */
647 1.1 christos complain_overflow_bitfield, /* complain_on_overflow. */
648 1.1 christos bfin_bfd_reloc, /* special_function. */
649 1.1.1.10 christos "R_BFIN_VAR_EQ_SYMB", /* name. */
650 1.1 christos false, /* partial_inplace. */
651 1.1 christos 0, /* src_mask. */
652 1.1.1.10 christos 0, /* dst_mask. */
653 1.1 christos false), /* pcrel_offset. */
654 1.1 christos
655 1.1 christos HOWTO (R_BFIN_BYTE_DATA, /* type. */
656 1.1.1.10 christos 0, /* rightshift. */
657 1.1 christos 1, /* size. */
658 1.1.1.10 christos 8, /* bitsize. */
659 1.1 christos false, /* pc_relative. */
660 1.1 christos 0, /* bitpos. */
661 1.1 christos complain_overflow_unsigned, /* complain_on_overflow. */
662 1.1 christos bfin_bfd_reloc, /* special_function. */
663 1.1.1.10 christos "R_BFIN_BYTE_DATA", /* name. */
664 1.1 christos false, /* partial_inplace. */
665 1.1 christos 0, /* src_mask. */
666 1.1.1.10 christos 0xFF, /* dst_mask. */
667 1.1 christos true), /* pcrel_offset. */
668 1.1 christos
669 1.1 christos HOWTO (R_BFIN_BYTE2_DATA, /* type. */
670 1.1.1.10 christos 0, /* rightshift. */
671 1.1 christos 2, /* size. */
672 1.1.1.10 christos 16, /* bitsize. */
673 1.1 christos false, /* pc_relative. */
674 1.1 christos 0, /* bitpos. */
675 1.1 christos complain_overflow_signed, /* complain_on_overflow. */
676 1.1 christos bfin_bfd_reloc, /* special_function. */
677 1.1.1.10 christos "R_BFIN_BYTE2_DATA", /* name. */
678 1.1 christos false, /* partial_inplace. */
679 1.1 christos 0, /* src_mask. */
680 1.1.1.10 christos 0xFFFF, /* dst_mask. */
681 1.1 christos true), /* pcrel_offset. */
682 1.1 christos
683 1.1 christos HOWTO (R_BFIN_BYTE4_DATA, /* type. */
684 1.1.1.10 christos 0, /* rightshift. */
685 1.1 christos 4, /* size. */
686 1.1.1.10 christos 32, /* bitsize. */
687 1.1 christos false, /* pc_relative. */
688 1.1 christos 0, /* bitpos. */
689 1.1 christos complain_overflow_unsigned, /* complain_on_overflow. */
690 1.1 christos bfin_byte4_reloc, /* special_function. */
691 1.1.1.10 christos "R_BFIN_BYTE4_DATA", /* name. */
692 1.1 christos false, /* partial_inplace. */
693 1.1 christos 0, /* src_mask. */
694 1.1.1.10 christos 0xFFFFFFFF, /* dst_mask. */
695 1.1 christos true), /* pcrel_offset. */
696 1.1 christos
697 1.1 christos HOWTO (R_BFIN_PCREL11, /* type. */
698 1.1.1.10 christos 1, /* rightshift. */
699 1.1 christos 2, /* size. */
700 1.1.1.10 christos 10, /* bitsize. */
701 1.1 christos true, /* pc_relative. */
702 1.1 christos 0, /* bitpos. */
703 1.1 christos complain_overflow_unsigned, /* complain_on_overflow. */
704 1.1 christos bfin_bfd_reloc, /* special_function. */
705 1.1.1.10 christos "R_BFIN_PCREL11", /* name. */
706 1.1 christos false, /* partial_inplace. */
707 1.1 christos 0, /* src_mask. */
708 1.1.1.10 christos 0x000003FF, /* dst_mask. */
709 1.1 christos false), /* pcrel_offset. */
710 1.1 christos
711 1.1 christos
712 1.1 christos /* A 18-bit signed operand with the GOT offset for the address of
713 1.1.1.8 christos the symbol. */
714 1.1 christos HOWTO (R_BFIN_GOT17M4, /* type */
715 1.1.1.10 christos 2, /* rightshift */
716 1.1 christos 2, /* size */
717 1.1.1.10 christos 16, /* bitsize */
718 1.1 christos false, /* pc_relative */
719 1.1 christos 0, /* bitpos */
720 1.1 christos complain_overflow_signed, /* complain_on_overflow */
721 1.1 christos bfd_elf_generic_reloc, /* special_function */
722 1.1.1.10 christos "R_BFIN_GOT17M4", /* name */
723 1.1.1.8 christos false, /* partial_inplace */
724 1.1.1.8 christos 0xffff, /* src_mask */
725 1.1.1.10 christos 0xffff, /* dst_mask */
726 1.1 christos false), /* pcrel_offset */
727 1.1 christos
728 1.1 christos /* The upper 16 bits of the GOT offset for the address of the
729 1.1.1.8 christos symbol. */
730 1.1 christos HOWTO (R_BFIN_GOTHI, /* type */
731 1.1.1.10 christos 0, /* rightshift */
732 1.1 christos 2, /* size */
733 1.1.1.10 christos 16, /* bitsize */
734 1.1 christos false, /* pc_relative */
735 1.1 christos 0, /* bitpos */
736 1.1 christos complain_overflow_dont, /* complain_on_overflow */
737 1.1 christos bfd_elf_generic_reloc, /* special_function */
738 1.1.1.10 christos "R_BFIN_GOTHI", /* name */
739 1.1.1.8 christos false, /* partial_inplace */
740 1.1 christos 0xffff, /* src_mask */
741 1.1.1.10 christos 0xffff, /* dst_mask */
742 1.1 christos false), /* pcrel_offset */
743 1.1 christos
744 1.1 christos /* The lower 16 bits of the GOT offset for the address of the
745 1.1.1.8 christos symbol. */
746 1.1 christos HOWTO (R_BFIN_GOTLO, /* type */
747 1.1.1.10 christos 0, /* rightshift */
748 1.1 christos 2, /* size */
749 1.1.1.10 christos 16, /* bitsize */
750 1.1 christos false, /* pc_relative */
751 1.1 christos 0, /* bitpos */
752 1.1 christos complain_overflow_dont, /* complain_on_overflow */
753 1.1 christos bfd_elf_generic_reloc, /* special_function */
754 1.1.1.10 christos "R_BFIN_GOTLO", /* name */
755 1.1 christos false, /* partial_inplace */
756 1.1 christos 0xffff, /* src_mask */
757 1.1.1.10 christos 0xffff, /* dst_mask */
758 1.1 christos false), /* pcrel_offset */
759 1.1 christos
760 1.1 christos /* The 32-bit address of the canonical descriptor of a function. */
761 1.1 christos HOWTO (R_BFIN_FUNCDESC, /* type */
762 1.1.1.10 christos 0, /* rightshift */
763 1.1 christos 4, /* size */
764 1.1.1.10 christos 32, /* bitsize */
765 1.1 christos false, /* pc_relative */
766 1.1 christos 0, /* bitpos */
767 1.1 christos complain_overflow_bitfield, /* complain_on_overflow */
768 1.1 christos bfd_elf_generic_reloc, /* special_function */
769 1.1.1.10 christos "R_BFIN_FUNCDESC", /* name */
770 1.1 christos false, /* partial_inplace */
771 1.1 christos 0xffffffff, /* src_mask */
772 1.1.1.10 christos 0xffffffff, /* dst_mask */
773 1.1 christos false), /* pcrel_offset */
774 1.1 christos
775 1.1 christos /* A 12-bit signed operand with the GOT offset for the address of
776 1.1 christos canonical descriptor of a function. */
777 1.1 christos HOWTO (R_BFIN_FUNCDESC_GOT17M4, /* type */
778 1.1.1.10 christos 2, /* rightshift */
779 1.1 christos 2, /* size */
780 1.1.1.10 christos 16, /* bitsize */
781 1.1 christos false, /* pc_relative */
782 1.1 christos 0, /* bitpos */
783 1.1 christos complain_overflow_signed, /* complain_on_overflow */
784 1.1 christos bfd_elf_generic_reloc, /* special_function */
785 1.1.1.10 christos "R_BFIN_FUNCDESC_GOT17M4", /* name */
786 1.1.1.8 christos false, /* partial_inplace */
787 1.1.1.8 christos 0xffff, /* src_mask */
788 1.1.1.10 christos 0xffff, /* dst_mask */
789 1.1 christos false), /* pcrel_offset */
790 1.1 christos
791 1.1 christos /* The upper 16 bits of the GOT offset for the address of the
792 1.1 christos canonical descriptor of a function. */
793 1.1 christos HOWTO (R_BFIN_FUNCDESC_GOTHI, /* type */
794 1.1.1.10 christos 0, /* rightshift */
795 1.1 christos 2, /* size */
796 1.1.1.10 christos 16, /* bitsize */
797 1.1 christos false, /* pc_relative */
798 1.1 christos 0, /* bitpos */
799 1.1 christos complain_overflow_dont, /* complain_on_overflow */
800 1.1 christos bfd_elf_generic_reloc, /* special_function */
801 1.1.1.10 christos "R_BFIN_FUNCDESC_GOTHI", /* name */
802 1.1 christos false, /* partial_inplace */
803 1.1 christos 0xffff, /* src_mask */
804 1.1.1.10 christos 0xffff, /* dst_mask */
805 1.1 christos false), /* pcrel_offset */
806 1.1 christos
807 1.1 christos /* The lower 16 bits of the GOT offset for the address of the
808 1.1 christos canonical descriptor of a function. */
809 1.1 christos HOWTO (R_BFIN_FUNCDESC_GOTLO, /* type */
810 1.1.1.10 christos 0, /* rightshift */
811 1.1 christos 2, /* size */
812 1.1.1.10 christos 16, /* bitsize */
813 1.1 christos false, /* pc_relative */
814 1.1 christos 0, /* bitpos */
815 1.1 christos complain_overflow_dont, /* complain_on_overflow */
816 1.1 christos bfd_elf_generic_reloc, /* special_function */
817 1.1.1.10 christos "R_BFIN_FUNCDESC_GOTLO", /* name */
818 1.1 christos false, /* partial_inplace */
819 1.1 christos 0xffff, /* src_mask */
820 1.1.1.10 christos 0xffff, /* dst_mask */
821 1.1 christos false), /* pcrel_offset */
822 1.1 christos
823 1.1 christos /* The 32-bit address of the canonical descriptor of a function. */
824 1.1 christos HOWTO (R_BFIN_FUNCDESC_VALUE, /* type */
825 1.1.1.10 christos 0, /* rightshift */
826 1.1 christos 4, /* size */
827 1.1.1.10 christos 64, /* bitsize */
828 1.1 christos false, /* pc_relative */
829 1.1 christos 0, /* bitpos */
830 1.1 christos complain_overflow_bitfield, /* complain_on_overflow */
831 1.1 christos bfd_elf_generic_reloc, /* special_function */
832 1.1.1.10 christos "R_BFIN_FUNCDESC_VALUE", /* name */
833 1.1 christos false, /* partial_inplace */
834 1.1 christos 0xffffffff, /* src_mask */
835 1.1.1.10 christos 0xffffffff, /* dst_mask */
836 1.1 christos false), /* pcrel_offset */
837 1.1 christos
838 1.1 christos /* A 12-bit signed operand with the GOT offset for the address of
839 1.1 christos canonical descriptor of a function. */
840 1.1 christos HOWTO (R_BFIN_FUNCDESC_GOTOFF17M4, /* type */
841 1.1.1.10 christos 2, /* rightshift */
842 1.1 christos 2, /* size */
843 1.1.1.10 christos 16, /* bitsize */
844 1.1 christos false, /* pc_relative */
845 1.1 christos 0, /* bitpos */
846 1.1 christos complain_overflow_signed, /* complain_on_overflow */
847 1.1 christos bfd_elf_generic_reloc, /* special_function */
848 1.1.1.10 christos "R_BFIN_FUNCDESC_GOTOFF17M4", /* name */
849 1.1.1.8 christos false, /* partial_inplace */
850 1.1.1.8 christos 0xffff, /* src_mask */
851 1.1.1.10 christos 0xffff, /* dst_mask */
852 1.1 christos false), /* pcrel_offset */
853 1.1 christos
854 1.1 christos /* The upper 16 bits of the GOT offset for the address of the
855 1.1 christos canonical descriptor of a function. */
856 1.1 christos HOWTO (R_BFIN_FUNCDESC_GOTOFFHI, /* type */
857 1.1.1.10 christos 0, /* rightshift */
858 1.1 christos 2, /* size */
859 1.1.1.10 christos 16, /* bitsize */
860 1.1 christos false, /* pc_relative */
861 1.1 christos 0, /* bitpos */
862 1.1 christos complain_overflow_dont, /* complain_on_overflow */
863 1.1 christos bfd_elf_generic_reloc, /* special_function */
864 1.1.1.10 christos "R_BFIN_FUNCDESC_GOTOFFHI", /* name */
865 1.1 christos false, /* partial_inplace */
866 1.1 christos 0xffff, /* src_mask */
867 1.1.1.10 christos 0xffff, /* dst_mask */
868 1.1 christos false), /* pcrel_offset */
869 1.1 christos
870 1.1 christos /* The lower 16 bits of the GOT offset for the address of the
871 1.1 christos canonical descriptor of a function. */
872 1.1 christos HOWTO (R_BFIN_FUNCDESC_GOTOFFLO, /* type */
873 1.1.1.10 christos 0, /* rightshift */
874 1.1 christos 2, /* size */
875 1.1.1.10 christos 16, /* bitsize */
876 1.1 christos false, /* pc_relative */
877 1.1 christos 0, /* bitpos */
878 1.1 christos complain_overflow_dont, /* complain_on_overflow */
879 1.1 christos bfd_elf_generic_reloc, /* special_function */
880 1.1.1.10 christos "R_BFIN_FUNCDESC_GOTOFFLO", /* name */
881 1.1 christos false, /* partial_inplace */
882 1.1 christos 0xffff, /* src_mask */
883 1.1.1.10 christos 0xffff, /* dst_mask */
884 1.1 christos false), /* pcrel_offset */
885 1.1 christos
886 1.1 christos /* A 12-bit signed operand with the GOT offset for the address of
887 1.1.1.8 christos the symbol. */
888 1.1 christos HOWTO (R_BFIN_GOTOFF17M4, /* type */
889 1.1.1.10 christos 2, /* rightshift */
890 1.1 christos 2, /* size */
891 1.1.1.10 christos 16, /* bitsize */
892 1.1 christos false, /* pc_relative */
893 1.1 christos 0, /* bitpos */
894 1.1 christos complain_overflow_signed, /* complain_on_overflow */
895 1.1 christos bfd_elf_generic_reloc, /* special_function */
896 1.1.1.10 christos "R_BFIN_GOTOFF17M4", /* name */
897 1.1.1.8 christos false, /* partial_inplace */
898 1.1.1.8 christos 0xffff, /* src_mask */
899 1.1.1.10 christos 0xffff, /* dst_mask */
900 1.1 christos false), /* pcrel_offset */
901 1.1 christos
902 1.1 christos /* The upper 16 bits of the GOT offset for the address of the
903 1.1.1.8 christos symbol. */
904 1.1 christos HOWTO (R_BFIN_GOTOFFHI, /* type */
905 1.1.1.10 christos 0, /* rightshift */
906 1.1 christos 2, /* size */
907 1.1.1.10 christos 16, /* bitsize */
908 1.1 christos false, /* pc_relative */
909 1.1 christos 0, /* bitpos */
910 1.1 christos complain_overflow_dont, /* complain_on_overflow */
911 1.1 christos bfd_elf_generic_reloc, /* special_function */
912 1.1.1.10 christos "R_BFIN_GOTOFFHI", /* name */
913 1.1 christos false, /* partial_inplace */
914 1.1 christos 0xffff, /* src_mask */
915 1.1.1.10 christos 0xffff, /* dst_mask */
916 1.1 christos false), /* pcrel_offset */
917 1.1 christos
918 1.1 christos /* The lower 16 bits of the GOT offset for the address of the
919 1.1 christos symbol. */
920 1.1 christos HOWTO (R_BFIN_GOTOFFLO, /* type */
921 1.1.1.10 christos 0, /* rightshift */
922 1.1 christos 2, /* size */
923 1.1.1.10 christos 16, /* bitsize */
924 1.1 christos false, /* pc_relative */
925 1.1 christos 0, /* bitpos */
926 1.1 christos complain_overflow_dont, /* complain_on_overflow */
927 1.1 christos bfd_elf_generic_reloc, /* special_function */
928 1.1.1.10 christos "R_BFIN_GOTOFFLO", /* name */
929 1.1 christos false, /* partial_inplace */
930 1.1 christos 0xffff, /* src_mask */
931 1.1.1.10 christos 0xffff, /* dst_mask */
932 1.1 christos false), /* pcrel_offset */
933 1.1 christos };
934 1.1 christos
935 1.1 christos static reloc_howto_type bfin_gnuext_howto_table [] =
936 1.1 christos {
937 1.1 christos HOWTO (R_BFIN_PLTPC, /* type. */
938 1.1.1.10 christos 0, /* rightshift. */
939 1.1 christos 2, /* size. */
940 1.1.1.10 christos 16, /* bitsize. */
941 1.1 christos false, /* pc_relative. */
942 1.1 christos 0, /* bitpos. */
943 1.1 christos complain_overflow_bitfield, /* complain_on_overflow. */
944 1.1 christos bfin_pltpc_reloc, /* special_function. */
945 1.1.1.10 christos "R_BFIN_PLTPC", /* name. */
946 1.1 christos false, /* partial_inplace. */
947 1.1 christos 0xffff, /* src_mask. */
948 1.1.1.10 christos 0xffff, /* dst_mask. */
949 1.1 christos false), /* pcrel_offset. */
950 1.1 christos
951 1.1 christos HOWTO (R_BFIN_GOT, /* type. */
952 1.1.1.10 christos 0, /* rightshift. */
953 1.1 christos 2, /* size. */
954 1.1.1.10 christos 16, /* bitsize. */
955 1.1 christos false, /* pc_relative. */
956 1.1 christos 0, /* bitpos. */
957 1.1 christos complain_overflow_bitfield, /* complain_on_overflow. */
958 1.1 christos bfd_elf_generic_reloc, /* special_function. */
959 1.1.1.10 christos "R_BFIN_GOT", /* name. */
960 1.1 christos false, /* partial_inplace. */
961 1.1 christos 0x7fff, /* src_mask. */
962 1.1.1.10 christos 0x7fff, /* dst_mask. */
963 1.1 christos false), /* pcrel_offset. */
964 1.1 christos
965 1.1.1.8 christos /* GNU extension to record C++ vtable hierarchy. */
966 1.1.1.8 christos HOWTO (R_BFIN_GNU_VTINHERIT, /* type. */
967 1.1.1.10 christos 0, /* rightshift. */
968 1.1.1.8 christos 4, /* size. */
969 1.1.1.10 christos 0, /* bitsize. */
970 1.1.1.8 christos false, /* pc_relative. */
971 1.1.1.8 christos 0, /* bitpos. */
972 1.1.1.8 christos complain_overflow_dont, /* complain_on_overflow. */
973 1.1.1.8 christos NULL, /* special_function. */
974 1.1.1.10 christos "R_BFIN_GNU_VTINHERIT", /* name. */
975 1.1.1.8 christos false, /* partial_inplace. */
976 1.1.1.8 christos 0, /* src_mask. */
977 1.1.1.10 christos 0, /* dst_mask. */
978 1.1 christos false), /* pcrel_offset. */
979 1.1 christos
980 1.1 christos /* GNU extension to record C++ vtable member usage. */
981 1.1.1.8 christos HOWTO (R_BFIN_GNU_VTENTRY, /* type. */
982 1.1.1.10 christos 0, /* rightshift. */
983 1.1.1.8 christos 4, /* size. */
984 1.1.1.10 christos 0, /* bitsize. */
985 1.1.1.8 christos false, /* pc_relative. */
986 1.1.1.8 christos 0, /* bitpos. */
987 1.1.1.8 christos complain_overflow_dont, /* complain_on_overflow. */
988 1.1.1.8 christos _bfd_elf_rel_vtable_reloc_fn, /* special_function. */
989 1.1.1.10 christos "R_BFIN_GNU_VTENTRY", /* name. */
990 1.1.1.8 christos false, /* partial_inplace. */
991 1.1.1.8 christos 0, /* src_mask. */
992 1.1.1.10 christos 0, /* dst_mask. */
993 1.1 christos false) /* pcrel_offset. */
994 1.1 christos };
995 1.1 christos
996 1.1 christos struct bfin_reloc_map
997 1.1.1.8 christos {
998 1.1 christos bfd_reloc_code_real_type bfd_reloc_val;
999 1.1 christos unsigned int bfin_reloc_val;
1000 1.1 christos };
1001 1.1 christos
1002 1.1 christos static const struct bfin_reloc_map bfin_reloc_map [] =
1003 1.1 christos {
1004 1.1 christos { BFD_RELOC_NONE, R_BFIN_UNUSED0 },
1005 1.1 christos { BFD_RELOC_BFIN_5_PCREL, R_BFIN_PCREL5M2 },
1006 1.1 christos { BFD_RELOC_NONE, R_BFIN_UNUSED1 },
1007 1.1 christos { BFD_RELOC_BFIN_10_PCREL, R_BFIN_PCREL10 },
1008 1.1 christos { BFD_RELOC_BFIN_12_PCREL_JUMP, R_BFIN_PCREL12_JUMP },
1009 1.1 christos { BFD_RELOC_BFIN_16_IMM, R_BFIN_RIMM16 },
1010 1.1 christos { BFD_RELOC_BFIN_16_LOW, R_BFIN_LUIMM16 },
1011 1.1 christos { BFD_RELOC_BFIN_16_HIGH, R_BFIN_HUIMM16 },
1012 1.1 christos { BFD_RELOC_BFIN_12_PCREL_JUMP_S, R_BFIN_PCREL12_JUMP_S },
1013 1.1 christos { BFD_RELOC_24_PCREL, R_BFIN_PCREL24 },
1014 1.1 christos { BFD_RELOC_24_PCREL, R_BFIN_PCREL24 },
1015 1.1 christos { BFD_RELOC_BFIN_24_PCREL_JUMP_L, R_BFIN_PCREL24_JUMP_L },
1016 1.1 christos { BFD_RELOC_NONE, R_BFIN_UNUSEDB },
1017 1.1 christos { BFD_RELOC_NONE, R_BFIN_UNUSEDC },
1018 1.1 christos { BFD_RELOC_BFIN_24_PCREL_CALL_X, R_BFIN_PCREL24_CALL_X },
1019 1.1 christos { BFD_RELOC_8, R_BFIN_BYTE_DATA },
1020 1.1 christos { BFD_RELOC_16, R_BFIN_BYTE2_DATA },
1021 1.1 christos { BFD_RELOC_32, R_BFIN_BYTE4_DATA },
1022 1.1 christos { BFD_RELOC_BFIN_11_PCREL, R_BFIN_PCREL11 },
1023 1.1 christos { BFD_RELOC_BFIN_GOT, R_BFIN_GOT },
1024 1.1 christos { BFD_RELOC_BFIN_PLTPC, R_BFIN_PLTPC },
1025 1.1 christos
1026 1.1 christos { BFD_RELOC_BFIN_GOT17M4, R_BFIN_GOT17M4 },
1027 1.1 christos { BFD_RELOC_BFIN_GOTHI, R_BFIN_GOTHI },
1028 1.1 christos { BFD_RELOC_BFIN_GOTLO, R_BFIN_GOTLO },
1029 1.1 christos { BFD_RELOC_BFIN_FUNCDESC, R_BFIN_FUNCDESC },
1030 1.1 christos { BFD_RELOC_BFIN_FUNCDESC_GOT17M4, R_BFIN_FUNCDESC_GOT17M4 },
1031 1.1 christos { BFD_RELOC_BFIN_FUNCDESC_GOTHI, R_BFIN_FUNCDESC_GOTHI },
1032 1.1 christos { BFD_RELOC_BFIN_FUNCDESC_GOTLO, R_BFIN_FUNCDESC_GOTLO },
1033 1.1 christos { BFD_RELOC_BFIN_FUNCDESC_VALUE, R_BFIN_FUNCDESC_VALUE },
1034 1.1 christos { BFD_RELOC_BFIN_FUNCDESC_GOTOFF17M4, R_BFIN_FUNCDESC_GOTOFF17M4 },
1035 1.1 christos { BFD_RELOC_BFIN_FUNCDESC_GOTOFFHI, R_BFIN_FUNCDESC_GOTOFFHI },
1036 1.1 christos { BFD_RELOC_BFIN_FUNCDESC_GOTOFFLO, R_BFIN_FUNCDESC_GOTOFFLO },
1037 1.1 christos { BFD_RELOC_BFIN_GOTOFF17M4, R_BFIN_GOTOFF17M4 },
1038 1.1 christos { BFD_RELOC_BFIN_GOTOFFHI, R_BFIN_GOTOFFHI },
1039 1.1 christos { BFD_RELOC_BFIN_GOTOFFLO, R_BFIN_GOTOFFLO },
1040 1.1 christos
1041 1.1 christos { BFD_RELOC_VTABLE_INHERIT, R_BFIN_GNU_VTINHERIT },
1042 1.1 christos { BFD_RELOC_VTABLE_ENTRY, R_BFIN_GNU_VTENTRY },
1043 1.1 christos };
1044 1.1 christos
1045 1.1.1.10 christos
1046 1.1.1.8 christos static bool
1047 1.1.1.8 christos bfin_info_to_howto (bfd *abfd,
1048 1.1.1.8 christos arelent *cache_ptr,
1049 1.1 christos Elf_Internal_Rela *dst)
1050 1.1 christos {
1051 1.1 christos unsigned int r_type;
1052 1.1 christos
1053 1.1 christos r_type = ELF32_R_TYPE (dst->r_info);
1054 1.1 christos
1055 1.1 christos if (r_type <= BFIN_RELOC_MAX)
1056 1.1 christos cache_ptr->howto = &bfin_howto_table [r_type];
1057 1.1 christos
1058 1.1 christos else if (r_type >= BFIN_GNUEXT_RELOC_MIN && r_type <= BFIN_GNUEXT_RELOC_MAX)
1059 1.1 christos cache_ptr->howto = &bfin_gnuext_howto_table [r_type - BFIN_GNUEXT_RELOC_MIN];
1060 1.1 christos
1061 1.1.1.8 christos else
1062 1.1.1.8 christos {
1063 1.1.1.8 christos /* xgettext:c-format */
1064 1.1.1.8 christos _bfd_error_handler (_("%pB: unsupported relocation type %#x"),
1065 1.1.1.8 christos abfd, r_type);
1066 1.1.1.10 christos bfd_set_error (bfd_error_bad_value);
1067 1.1.1.8 christos return false;
1068 1.1.1.8 christos }
1069 1.1.1.10 christos
1070 1.1 christos return true;
1071 1.1 christos }
1072 1.1 christos
1073 1.1 christos /* Given a BFD reloc type, return the howto. */
1074 1.1 christos static reloc_howto_type *
1075 1.1 christos bfin_bfd_reloc_type_lookup (bfd * abfd ATTRIBUTE_UNUSED,
1076 1.1 christos bfd_reloc_code_real_type code)
1077 1.1 christos {
1078 1.1.1.5 christos unsigned int i;
1079 1.1 christos unsigned int r_type = (unsigned int) -1;
1080 1.1.1.5 christos
1081 1.1 christos for (i = sizeof (bfin_reloc_map) / sizeof (bfin_reloc_map[0]); i--;)
1082 1.1 christos if (bfin_reloc_map[i].bfd_reloc_val == code)
1083 1.1 christos r_type = bfin_reloc_map[i].bfin_reloc_val;
1084 1.1.1.5 christos
1085 1.1 christos if (r_type <= BFIN_RELOC_MAX)
1086 1.1 christos return &bfin_howto_table [r_type];
1087 1.1 christos
1088 1.1 christos else if (r_type >= BFIN_GNUEXT_RELOC_MIN && r_type <= BFIN_GNUEXT_RELOC_MAX)
1089 1.1 christos return &bfin_gnuext_howto_table [r_type - BFIN_GNUEXT_RELOC_MIN];
1090 1.1 christos
1091 1.1 christos return (reloc_howto_type *) NULL;
1092 1.1 christos }
1093 1.1 christos
1094 1.1 christos static reloc_howto_type *
1095 1.1 christos bfin_bfd_reloc_name_lookup (bfd *abfd ATTRIBUTE_UNUSED,
1096 1.1 christos const char *r_name)
1097 1.1 christos {
1098 1.1 christos unsigned int i;
1099 1.1 christos
1100 1.1 christos for (i = 0;
1101 1.1 christos i < (sizeof (bfin_howto_table)
1102 1.1 christos / sizeof (bfin_howto_table[0]));
1103 1.1 christos i++)
1104 1.1 christos if (bfin_howto_table[i].name != NULL
1105 1.1 christos && strcasecmp (bfin_howto_table[i].name, r_name) == 0)
1106 1.1 christos return &bfin_howto_table[i];
1107 1.1 christos
1108 1.1 christos for (i = 0;
1109 1.1 christos i < (sizeof (bfin_gnuext_howto_table)
1110 1.1 christos / sizeof (bfin_gnuext_howto_table[0]));
1111 1.1 christos i++)
1112 1.1 christos if (bfin_gnuext_howto_table[i].name != NULL
1113 1.1 christos && strcasecmp (bfin_gnuext_howto_table[i].name, r_name) == 0)
1114 1.1 christos return &bfin_gnuext_howto_table[i];
1115 1.1 christos
1116 1.1 christos return NULL;
1117 1.1 christos }
1118 1.1 christos
1119 1.1 christos /* Given a bfin relocation type, return the howto. */
1120 1.1 christos static reloc_howto_type *
1121 1.1.1.2 christos bfin_reloc_type_lookup (bfd * abfd ATTRIBUTE_UNUSED,
1122 1.1 christos unsigned int r_type)
1123 1.1 christos {
1124 1.1 christos if (r_type <= BFIN_RELOC_MAX)
1125 1.1 christos return &bfin_howto_table [r_type];
1126 1.1 christos
1127 1.1 christos else if (r_type >= BFIN_GNUEXT_RELOC_MIN && r_type <= BFIN_GNUEXT_RELOC_MAX)
1128 1.1 christos return &bfin_gnuext_howto_table [r_type - BFIN_GNUEXT_RELOC_MIN];
1129 1.1 christos
1130 1.1 christos return (reloc_howto_type *) NULL;
1131 1.1 christos }
1132 1.1 christos
1133 1.1.1.10 christos /* Set by ld emulation if --code-in-l1. */
1134 1.1 christos bool elf32_bfin_code_in_l1 = 0;
1135 1.1 christos
1136 1.1.1.10 christos /* Set by ld emulation if --data-in-l1. */
1137 1.1 christos bool elf32_bfin_data_in_l1 = 0;
1138 1.1.1.10 christos
1139 1.1.1.9 christos static bool
1140 1.1 christos elf32_bfin_final_write_processing (bfd *abfd)
1141 1.1 christos {
1142 1.1 christos if (elf32_bfin_code_in_l1)
1143 1.1 christos elf_elfheader (abfd)->e_flags |= EF_BFIN_CODE_IN_L1;
1144 1.1 christos if (elf32_bfin_data_in_l1)
1145 1.1.1.9 christos elf_elfheader (abfd)->e_flags |= EF_BFIN_DATA_IN_L1;
1146 1.1 christos return _bfd_elf_final_write_processing (abfd);
1147 1.1 christos }
1148 1.1 christos
1149 1.1 christos /* Return TRUE if the name is a local label.
1150 1.1.1.10 christos bfin local labels begin with L$. */
1151 1.1.1.2 christos static bool
1152 1.1 christos bfin_is_local_label_name (bfd *abfd, const char *label)
1153 1.1 christos {
1154 1.1.1.10 christos if (label[0] == 'L' && label[1] == '$' )
1155 1.1 christos return true;
1156 1.1 christos
1157 1.1 christos return _bfd_elf_is_local_label_name (abfd, label);
1158 1.1 christos }
1159 1.1 christos
1160 1.1 christos /* Look through the relocs for a section during the first phase, and
1162 1.1 christos allocate space in the global offset table or procedure linkage
1163 1.1.1.10 christos table. */
1164 1.1 christos
1165 1.1 christos static bool
1166 1.1 christos bfin_check_relocs (bfd * abfd,
1167 1.1.1.8 christos struct bfd_link_info *info,
1168 1.1 christos asection *sec,
1169 1.1 christos const Elf_Internal_Rela *relocs)
1170 1.1 christos {
1171 1.1 christos bfd *dynobj;
1172 1.1 christos Elf_Internal_Shdr *symtab_hdr;
1173 1.1 christos struct elf_link_hash_entry **sym_hashes;
1174 1.1 christos bfd_signed_vma *local_got_refcounts;
1175 1.1 christos const Elf_Internal_Rela *rel;
1176 1.1 christos const Elf_Internal_Rela *rel_end;
1177 1.1.1.2 christos asection *sgot;
1178 1.1.1.6 christos asection *srelgot;
1179 1.1.1.10 christos
1180 1.1 christos if (bfd_link_relocatable (info))
1181 1.1 christos return true;
1182 1.1 christos
1183 1.1 christos dynobj = elf_hash_table (info)->dynobj;
1184 1.1 christos symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
1185 1.1 christos sym_hashes = elf_sym_hashes (abfd);
1186 1.1 christos local_got_refcounts = elf_local_got_refcounts (abfd);
1187 1.1 christos
1188 1.1 christos sgot = NULL;
1189 1.1 christos srelgot = NULL;
1190 1.1 christos
1191 1.1 christos rel_end = relocs + sec->reloc_count;
1192 1.1 christos for (rel = relocs; rel < rel_end; rel++)
1193 1.1 christos {
1194 1.1 christos unsigned long r_symndx;
1195 1.1 christos struct elf_link_hash_entry *h;
1196 1.1 christos
1197 1.1 christos r_symndx = ELF32_R_SYM (rel->r_info);
1198 1.1 christos if (r_symndx < symtab_hdr->sh_info)
1199 1.1.1.3 christos h = NULL;
1200 1.1.1.3 christos else
1201 1.1.1.10 christos {
1202 1.1.1.10 christos h = sym_hashes[r_symndx - symtab_hdr->sh_info];
1203 1.1.1.10 christos while (h->root.type == bfd_link_hash_indirect
1204 1.1.1.3 christos || h->root.type == bfd_link_hash_warning)
1205 1.1 christos h = (struct elf_link_hash_entry *)h->root.u.i.link;
1206 1.1 christos }
1207 1.1 christos
1208 1.1 christos switch (ELF32_R_TYPE (rel->r_info))
1209 1.1.1.8 christos {
1210 1.1.1.8 christos /* This relocation describes the C++ object vtable hierarchy.
1211 1.1.1.8 christos Reconstruct it for later use during GC. */
1212 1.1.1.10 christos case R_BFIN_GNU_VTINHERIT:
1213 1.1.1.8 christos if (!bfd_elf_gc_record_vtinherit (abfd, sec, h, rel->r_offset))
1214 1.1.1.8 christos return false;
1215 1.1.1.8 christos break;
1216 1.1.1.8 christos
1217 1.1.1.8 christos /* This relocation describes which C++ vtable entries
1218 1.1.1.9 christos are actually used. Record for later use during GC. */
1219 1.1.1.10 christos case R_BFIN_GNU_VTENTRY:
1220 1.1.1.8 christos if (!bfd_elf_gc_record_vtentry (abfd, sec, h, rel->r_addend))
1221 1.1 christos return false;
1222 1.1 christos break;
1223 1.1 christos
1224 1.1 christos case R_BFIN_GOT:
1225 1.1 christos if (h != NULL
1226 1.1 christos && strcmp (h->root.root.string, "__GLOBAL_OFFSET_TABLE_") == 0)
1227 1.1 christos break;
1228 1.1 christos /* Fall through. */
1229 1.1 christos
1230 1.1 christos if (dynobj == NULL)
1231 1.1 christos {
1232 1.1 christos /* Create the .got section. */
1233 1.1.1.10 christos elf_hash_table (info)->dynobj = dynobj = abfd;
1234 1.1 christos if (!_bfd_elf_create_got_section (dynobj, info))
1235 1.1 christos return false;
1236 1.1.1.7 christos }
1237 1.1.1.7 christos
1238 1.1.1.7 christos sgot = elf_hash_table (info)->sgot;
1239 1.1 christos srelgot = elf_hash_table (info)->srelgot;
1240 1.1 christos BFD_ASSERT (sgot != NULL);
1241 1.1 christos
1242 1.1 christos if (h != NULL)
1243 1.1 christos {
1244 1.1 christos if (h->got.refcount == 0)
1245 1.1 christos {
1246 1.1 christos /* Make sure this symbol is output as a dynamic symbol. */
1247 1.1 christos if (h->dynindx == -1 && !h->forced_local)
1248 1.1.1.10 christos {
1249 1.1 christos if (!bfd_elf_link_record_dynamic_symbol (info, h))
1250 1.1 christos return false;
1251 1.1 christos }
1252 1.1 christos
1253 1.1 christos /* Allocate space in the .got section. */
1254 1.1 christos sgot->size += 4;
1255 1.1 christos /* Allocate relocation space. */
1256 1.1 christos srelgot->size += sizeof (Elf32_External_Rela);
1257 1.1 christos }
1258 1.1 christos h->got.refcount++;
1259 1.1 christos }
1260 1.1 christos else
1261 1.1 christos {
1262 1.1 christos /* This is a global offset table entry for a local symbol. */
1263 1.1 christos if (local_got_refcounts == NULL)
1264 1.1 christos {
1265 1.1 christos bfd_size_type size;
1266 1.1 christos
1267 1.1 christos size = symtab_hdr->sh_info;
1268 1.1 christos size *= sizeof (bfd_signed_vma);
1269 1.1 christos local_got_refcounts = ((bfd_signed_vma *)
1270 1.1.1.10 christos bfd_zalloc (abfd, size));
1271 1.1 christos if (local_got_refcounts == NULL)
1272 1.1 christos return false;
1273 1.1 christos elf_local_got_refcounts (abfd) = local_got_refcounts;
1274 1.1 christos }
1275 1.1 christos if (local_got_refcounts[r_symndx] == 0)
1276 1.1.1.6 christos {
1277 1.1 christos sgot->size += 4;
1278 1.1 christos if (bfd_link_pic (info))
1279 1.1.1.8 christos {
1280 1.1.1.8 christos /* If we are generating a shared object, we need to
1281 1.1 christos output a R_68K_RELATIVE reloc so that the dynamic
1282 1.1 christos linker can adjust this GOT entry. */
1283 1.1 christos srelgot->size += sizeof (Elf32_External_Rela);
1284 1.1 christos }
1285 1.1 christos }
1286 1.1 christos local_got_refcounts[r_symndx]++;
1287 1.1 christos }
1288 1.1 christos break;
1289 1.1 christos
1290 1.1 christos default:
1291 1.1 christos break;
1292 1.1 christos }
1293 1.1.1.10 christos }
1294 1.1 christos
1295 1.1 christos return true;
1296 1.1 christos }
1297 1.1.1.3 christos
1298 1.1.1.3 christos static enum elf_reloc_type_class
1299 1.1.1.3 christos elf32_bfin_reloc_type_class (const struct bfd_link_info *info ATTRIBUTE_UNUSED,
1300 1.1 christos const asection *rel_sec ATTRIBUTE_UNUSED,
1301 1.1 christos const Elf_Internal_Rela * rela)
1302 1.1 christos {
1303 1.1 christos switch ((int) ELF32_R_TYPE (rela->r_info))
1304 1.1 christos {
1305 1.1 christos default:
1306 1.1 christos return reloc_class_normal;
1307 1.1 christos }
1308 1.1 christos }
1309 1.1 christos
1310 1.1 christos static bfd_reloc_status_type
1312 1.1 christos bfin_final_link_relocate (Elf_Internal_Rela *rel, reloc_howto_type *howto,
1313 1.1 christos bfd *input_bfd, asection *input_section,
1314 1.1 christos bfd_byte *contents, bfd_vma address,
1315 1.1 christos bfd_vma value, bfd_vma addend)
1316 1.1 christos {
1317 1.1 christos int r_type = ELF32_R_TYPE (rel->r_info);
1318 1.1 christos
1319 1.1 christos if (r_type == R_BFIN_PCREL24 || r_type == R_BFIN_PCREL24_JUMP_L)
1320 1.1 christos {
1321 1.1.1.10 christos bfd_reloc_status_type r = bfd_reloc_ok;
1322 1.1.1.10 christos bfd_vma x;
1323 1.1.1.10 christos
1324 1.1 christos if (!bfd_reloc_offset_in_range (howto, input_bfd, input_section,
1325 1.1 christos address - 2))
1326 1.1 christos return bfd_reloc_outofrange;
1327 1.1 christos
1328 1.1 christos value += addend;
1329 1.1 christos
1330 1.1 christos /* Perform usual pc-relative correction. */
1331 1.1 christos value -= input_section->output_section->vma + input_section->output_offset;
1332 1.1 christos value -= address;
1333 1.1 christos
1334 1.1 christos /* We are getting reloc_entry->address 2 byte off from
1335 1.1 christos the start of instruction. Assuming absolute postion
1336 1.1 christos of the reloc data. But, following code had been written assuming
1337 1.1 christos reloc address is starting at begining of instruction.
1338 1.1 christos To compensate that I have increased the value of
1339 1.1 christos relocation by 1 (effectively 2) and used the addr -2 instead of addr. */
1340 1.1 christos
1341 1.1 christos value += 2;
1342 1.1 christos address -= 2;
1343 1.1 christos
1344 1.1 christos if ((value & 0xFF000000) != 0
1345 1.1 christos && (value & 0xFF000000) != 0xFF000000)
1346 1.1 christos r = bfd_reloc_overflow;
1347 1.1 christos
1348 1.1 christos value >>= 1;
1349 1.1 christos
1350 1.1 christos x = bfd_get_16 (input_bfd, contents + address);
1351 1.1 christos x = (x & 0xff00) | ((value >> 16) & 0xff);
1352 1.1 christos bfd_put_16 (input_bfd, x, contents + address);
1353 1.1 christos
1354 1.1 christos x = bfd_get_16 (input_bfd, contents + address + 2);
1355 1.1 christos x = value & 0xFFFF;
1356 1.1 christos bfd_put_16 (input_bfd, x, contents + address + 2);
1357 1.1 christos return r;
1358 1.1 christos }
1359 1.1 christos
1360 1.1 christos return _bfd_final_link_relocate (howto, input_bfd, input_section, contents,
1361 1.1 christos rel->r_offset, value, addend);
1362 1.1.1.10 christos
1363 1.1 christos }
1364 1.1 christos
1365 1.1 christos static int
1366 1.1 christos bfin_relocate_section (bfd * output_bfd,
1367 1.1 christos struct bfd_link_info *info,
1368 1.1 christos bfd * input_bfd,
1369 1.1 christos asection * input_section,
1370 1.1 christos bfd_byte * contents,
1371 1.1 christos Elf_Internal_Rela * relocs,
1372 1.1 christos Elf_Internal_Sym * local_syms,
1373 1.1 christos asection ** local_sections)
1374 1.1 christos {
1375 1.1 christos bfd *dynobj;
1376 1.1 christos Elf_Internal_Shdr *symtab_hdr;
1377 1.1 christos struct elf_link_hash_entry **sym_hashes;
1378 1.1 christos bfd_vma *local_got_offsets;
1379 1.1 christos asection *sgot;
1380 1.1 christos Elf_Internal_Rela *rel;
1381 1.1 christos Elf_Internal_Rela *relend;
1382 1.1 christos int i = 0;
1383 1.1 christos
1384 1.1 christos dynobj = elf_hash_table (info)->dynobj;
1385 1.1 christos symtab_hdr = &elf_tdata (input_bfd)->symtab_hdr;
1386 1.1 christos sym_hashes = elf_sym_hashes (input_bfd);
1387 1.1 christos local_got_offsets = elf_local_got_offsets (input_bfd);
1388 1.1 christos
1389 1.1 christos sgot = NULL;
1390 1.1 christos
1391 1.1 christos rel = relocs;
1392 1.1 christos relend = relocs + input_section->reloc_count;
1393 1.1 christos for (; rel < relend; rel++, i++)
1394 1.1 christos {
1395 1.1 christos int r_type;
1396 1.1 christos reloc_howto_type *howto;
1397 1.1 christos unsigned long r_symndx;
1398 1.1 christos struct elf_link_hash_entry *h;
1399 1.1.1.10 christos Elf_Internal_Sym *sym;
1400 1.1 christos asection *sec;
1401 1.1 christos bfd_vma relocation = 0;
1402 1.1 christos bool unresolved_reloc;
1403 1.1 christos bfd_reloc_status_type r;
1404 1.1 christos bfd_vma address;
1405 1.1 christos
1406 1.1 christos r_type = ELF32_R_TYPE (rel->r_info);
1407 1.1.1.10 christos if (r_type < 0 || r_type >= 243)
1408 1.1 christos {
1409 1.1 christos bfd_set_error (bfd_error_bad_value);
1410 1.1 christos return false;
1411 1.1.1.8 christos }
1412 1.1 christos
1413 1.1 christos if (r_type == R_BFIN_GNU_VTENTRY
1414 1.1 christos || r_type == R_BFIN_GNU_VTINHERIT)
1415 1.1 christos continue;
1416 1.1 christos
1417 1.1 christos howto = bfin_reloc_type_lookup (input_bfd, r_type);
1418 1.1.1.10 christos if (howto == NULL)
1419 1.1 christos {
1420 1.1 christos bfd_set_error (bfd_error_bad_value);
1421 1.1 christos return false;
1422 1.1 christos }
1423 1.1 christos r_symndx = ELF32_R_SYM (rel->r_info);
1424 1.1 christos
1425 1.1.1.10 christos h = NULL;
1426 1.1 christos sym = NULL;
1427 1.1 christos sec = NULL;
1428 1.1 christos unresolved_reloc = false;
1429 1.1 christos
1430 1.1 christos if (r_symndx < symtab_hdr->sh_info)
1431 1.1 christos {
1432 1.1 christos sym = local_syms + r_symndx;
1433 1.1 christos sec = local_sections[r_symndx];
1434 1.1 christos relocation = _bfd_elf_rela_local_sym (output_bfd, sym, &sec, rel);
1435 1.1.1.10 christos }
1436 1.1 christos else
1437 1.1 christos {
1438 1.1 christos bool warned, ignored;
1439 1.1 christos
1440 1.1.1.3 christos RELOC_FOR_GLOBAL_SYMBOL (info, input_bfd, input_section, rel,
1441 1.1 christos r_symndx, symtab_hdr, sym_hashes,
1442 1.1 christos h, sec, relocation,
1443 1.1.1.2 christos unresolved_reloc, warned, ignored);
1444 1.1 christos }
1445 1.1.1.2 christos
1446 1.1 christos if (sec != NULL && discarded_section (sec))
1447 1.1.1.6 christos RELOC_AGAINST_DISCARDED_SECTION (info, input_bfd, input_section,
1448 1.1 christos rel, 1, relend, howto, 0, contents);
1449 1.1 christos
1450 1.1 christos if (bfd_link_relocatable (info))
1451 1.1 christos continue;
1452 1.1 christos
1453 1.1 christos address = rel->r_offset;
1454 1.1 christos
1455 1.1 christos /* Then, process normally. */
1456 1.1 christos switch (r_type)
1457 1.1 christos {
1458 1.1 christos case R_BFIN_GNU_VTINHERIT:
1459 1.1 christos case R_BFIN_GNU_VTENTRY:
1460 1.1 christos return bfd_reloc_ok;
1461 1.1 christos
1462 1.1 christos case R_BFIN_GOT:
1463 1.1 christos /* Relocation is to the address of the entry for this symbol
1464 1.1 christos in the global offset table. */
1465 1.1 christos if (h != NULL
1466 1.1 christos && strcmp (h->root.root.string, "__GLOBAL_OFFSET_TABLE_") == 0)
1467 1.1 christos goto do_default;
1468 1.1 christos /* Fall through. */
1469 1.1 christos /* Relocation is the offset of the entry for this symbol in
1470 1.1 christos the global offset table. */
1471 1.1 christos
1472 1.1.1.7 christos {
1473 1.1 christos bfd_vma off;
1474 1.1.1.7 christos
1475 1.1.1.7 christos if (dynobj == NULL)
1476 1.1.1.7 christos {
1477 1.1.1.10 christos /* Create the .got section. */
1478 1.1 christos elf_hash_table (info)->dynobj = dynobj = output_bfd;
1479 1.1 christos if (!_bfd_elf_create_got_section (dynobj, info))
1480 1.1.1.7 christos return false;
1481 1.1.1.7 christos }
1482 1.1.1.7 christos
1483 1.1 christos sgot = elf_hash_table (info)->sgot;
1484 1.1 christos BFD_ASSERT (sgot != NULL);
1485 1.1.1.10 christos
1486 1.1 christos if (h != NULL)
1487 1.1 christos {
1488 1.1 christos bool dyn;
1489 1.1 christos
1490 1.1 christos off = h->got.offset;
1491 1.1.1.6 christos BFD_ASSERT (off != (bfd_vma) - 1);
1492 1.1.1.6 christos dyn = elf_hash_table (info)->dynamic_sections_created;
1493 1.1.1.6 christos
1494 1.1.1.6 christos if (!WILL_CALL_FINISH_DYNAMIC_SYMBOL (dyn,
1495 1.1 christos bfd_link_pic (info),
1496 1.1 christos h)
1497 1.1 christos || (bfd_link_pic (info)
1498 1.1 christos && (info->symbolic
1499 1.1 christos || h->dynindx == -1
1500 1.1 christos || h->forced_local)
1501 1.1 christos && h->def_regular))
1502 1.1 christos {
1503 1.1 christos /* This is actually a static link, or it is a
1504 1.1 christos -Bsymbolic link and the symbol is defined
1505 1.1 christos locally, or the symbol was forced to be local
1506 1.1 christos because of a version file.. We must initialize
1507 1.1 christos this entry in the global offset table. Since
1508 1.1 christos the offset must always be a multiple of 4, we
1509 1.1 christos use the least significant bit to record whether
1510 1.1 christos we have initialized it already.
1511 1.1 christos
1512 1.1 christos When doing a dynamic link, we create a .rela.got
1513 1.1 christos relocation entry to initialize the value. This
1514 1.1 christos is done in the finish_dynamic_symbol routine. */
1515 1.1 christos if ((off & 1) != 0)
1516 1.1 christos off &= ~1;
1517 1.1 christos else
1518 1.1 christos {
1519 1.1 christos bfd_put_32 (output_bfd, relocation,
1520 1.1 christos sgot->contents + off);
1521 1.1 christos h->got.offset |= 1;
1522 1.1.1.10 christos }
1523 1.1 christos }
1524 1.1 christos else
1525 1.1 christos unresolved_reloc = false;
1526 1.1 christos }
1527 1.1 christos else
1528 1.1 christos {
1529 1.1 christos BFD_ASSERT (local_got_offsets != NULL);
1530 1.1 christos off = local_got_offsets[r_symndx];
1531 1.1 christos BFD_ASSERT (off != (bfd_vma) - 1);
1532 1.1 christos
1533 1.1 christos /* The offset must always be a multiple of 4. We use
1534 1.1 christos the least significant bit to record whether we have
1535 1.1 christos already generated the necessary reloc. */
1536 1.1 christos if ((off & 1) != 0)
1537 1.1 christos off &= ~1;
1538 1.1 christos else
1539 1.1.1.6 christos {
1540 1.1 christos bfd_put_32 (output_bfd, relocation, sgot->contents + off);
1541 1.1 christos
1542 1.1 christos if (bfd_link_pic (info))
1543 1.1 christos {
1544 1.1 christos asection *s;
1545 1.1.1.7 christos Elf_Internal_Rela outrel;
1546 1.1 christos bfd_byte *loc;
1547 1.1 christos
1548 1.1 christos s = elf_hash_table (info)->srelgot;
1549 1.1 christos BFD_ASSERT (s != NULL);
1550 1.1 christos
1551 1.1 christos outrel.r_offset = (sgot->output_section->vma
1552 1.1 christos + sgot->output_offset + off);
1553 1.1 christos outrel.r_info =
1554 1.1 christos ELF32_R_INFO (0, R_BFIN_PCREL24);
1555 1.1 christos outrel.r_addend = relocation;
1556 1.1 christos loc = s->contents;
1557 1.1 christos loc +=
1558 1.1 christos s->reloc_count++ * sizeof (Elf32_External_Rela);
1559 1.1 christos bfd_elf32_swap_reloca_out (output_bfd, &outrel, loc);
1560 1.1 christos }
1561 1.1 christos
1562 1.1 christos local_got_offsets[r_symndx] |= 1;
1563 1.1 christos }
1564 1.1 christos }
1565 1.1.1.8 christos
1566 1.1.1.8 christos relocation = sgot->output_offset + off;
1567 1.1 christos rel->r_addend = 0;
1568 1.1 christos /* bfin : preg = [preg + 17bitdiv4offset] relocation is div by 4. */
1569 1.1 christos relocation /= 4;
1570 1.1 christos }
1571 1.1 christos goto do_default;
1572 1.1 christos
1573 1.1 christos default:
1574 1.1 christos do_default:
1575 1.1 christos r = bfin_final_link_relocate (rel, howto, input_bfd, input_section,
1576 1.1 christos contents, address,
1577 1.1 christos relocation, rel->r_addend);
1578 1.1 christos
1579 1.1 christos break;
1580 1.1.1.8 christos }
1581 1.1.1.8 christos
1582 1.1 christos /* Dynamic relocs are not propagated for SEC_DEBUGGING sections
1583 1.1.1.2 christos because such sections are not SEC_ALLOC and thus ld.so will
1584 1.1.1.2 christos not process them. */
1585 1.1.1.2 christos if (unresolved_reloc
1586 1.1 christos && !((input_section->flags & SEC_DEBUGGING) != 0 && h->def_dynamic)
1587 1.1.1.7 christos && _bfd_elf_section_offset (output_bfd, info, input_section,
1588 1.1.1.7 christos rel->r_offset) != (bfd_vma) -1)
1589 1.1.1.8 christos {
1590 1.1.1.8 christos _bfd_error_handler
1591 1.1.1.8 christos /* xgettext:c-format */
1592 1.1.1.8 christos (_("%pB(%pA+%#" PRIx64 "): "
1593 1.1.1.10 christos "unresolvable relocation against symbol `%s'"),
1594 1.1 christos input_bfd, input_section, (uint64_t) rel->r_offset,
1595 1.1 christos h->root.root.string);
1596 1.1 christos return false;
1597 1.1 christos }
1598 1.1 christos
1599 1.1 christos if (r != bfd_reloc_ok)
1600 1.1 christos {
1601 1.1 christos const char *name;
1602 1.1 christos
1603 1.1 christos if (h != NULL)
1604 1.1 christos name = h->root.root.string;
1605 1.1 christos else
1606 1.1 christos {
1607 1.1 christos name = bfd_elf_string_from_elf_section (input_bfd,
1608 1.1.1.10 christos symtab_hdr->sh_link,
1609 1.1 christos sym->st_name);
1610 1.1.1.9 christos if (name == NULL)
1611 1.1 christos return false;
1612 1.1 christos if (*name == '\0')
1613 1.1 christos name = bfd_section_name (sec);
1614 1.1.1.6 christos }
1615 1.1.1.6 christos
1616 1.1.1.6 christos if (r == bfd_reloc_overflow)
1617 1.1 christos (*info->callbacks->reloc_overflow)
1618 1.1 christos (info, (h ? &h->root : NULL), name, howto->name,
1619 1.1.1.7 christos (bfd_vma) 0, input_bfd, input_section, rel->r_offset);
1620 1.1.1.7 christos else
1621 1.1.1.8 christos {
1622 1.1.1.8 christos _bfd_error_handler
1623 1.1.1.8 christos /* xgettext:c-format */
1624 1.1.1.10 christos (_("%pB(%pA+%#" PRIx64 "): reloc against `%s': error %d"),
1625 1.1 christos input_bfd, input_section, (uint64_t) rel->r_offset,
1626 1.1 christos name, (int) r);
1627 1.1 christos return false;
1628 1.1 christos }
1629 1.1.1.10 christos }
1630 1.1 christos }
1631 1.1 christos
1632 1.1 christos return true;
1633 1.1 christos }
1634 1.1 christos
1635 1.1 christos static asection *
1636 1.1 christos bfin_gc_mark_hook (asection * sec,
1637 1.1.1.8 christos struct bfd_link_info *info,
1638 1.1 christos Elf_Internal_Rela * rel,
1639 1.1 christos struct elf_link_hash_entry *h,
1640 1.1 christos Elf_Internal_Sym * sym)
1641 1.1 christos {
1642 1.1 christos if (h != NULL)
1643 1.1 christos switch (ELF32_R_TYPE (rel->r_info))
1644 1.1 christos {
1645 1.1 christos case R_BFIN_GNU_VTINHERIT:
1646 1.1 christos case R_BFIN_GNU_VTENTRY:
1647 1.1 christos return NULL;
1648 1.1 christos }
1649 1.1 christos
1650 1.1.1.4 christos return _bfd_elf_gc_mark_hook (sec, info, rel, h, sym);
1651 1.1.1.4 christos }
1652 1.1 christos
1653 1.1 christos extern const bfd_target bfin_elf32_fdpic_vec;
1655 1.1 christos #define IS_FDPIC(bfd) ((bfd)->xvec == &bfin_elf32_fdpic_vec)
1656 1.1 christos
1657 1.1 christos /* An extension of the elf hash table data structure,
1658 1.1 christos containing some additional Blackfin-specific data. */
1659 1.1 christos struct bfinfdpic_elf_link_hash_table
1660 1.1 christos {
1661 1.1 christos struct elf_link_hash_table elf;
1662 1.1 christos
1663 1.1 christos /* A pointer to the .rofixup section. */
1664 1.1 christos asection *sgotfixup;
1665 1.1 christos /* GOT base offset. */
1666 1.1 christos bfd_vma got0;
1667 1.1 christos /* Location of the first non-lazy PLT entry, i.e., the number of
1668 1.1 christos bytes taken by lazy PLT entries. */
1669 1.1 christos bfd_vma plt0;
1670 1.1 christos /* A hash table holding information about which symbols were
1671 1.1 christos referenced with which PIC-related relocations. */
1672 1.1 christos struct htab *relocs_info;
1673 1.1 christos /* Summary reloc information collected by
1674 1.1 christos _bfinfdpic_count_got_plt_entries. */
1675 1.1 christos struct _bfinfdpic_dynamic_got_info *g;
1676 1.1.1.9 christos };
1677 1.1.1.9 christos
1678 1.1.1.9 christos /* Get the Blackfin ELF linker hash table from a link_info structure. */
1679 1.1.1.9 christos
1680 1.1 christos #define bfinfdpic_hash_table(p) \
1681 1.1 christos ((is_elf_hash_table ((p)->hash) \
1682 1.1.1.7 christos && elf_hash_table_id (elf_hash_table (p)) == BFIN_ELF_DATA) \
1683 1.1 christos ? (struct bfinfdpic_elf_link_hash_table *) (p)->hash : NULL)
1684 1.1.1.7 christos
1685 1.1 christos #define bfinfdpic_got_section(info) \
1686 1.1 christos (bfinfdpic_hash_table (info)->elf.sgot)
1687 1.1 christos #define bfinfdpic_gotrel_section(info) \
1688 1.1.1.7 christos (bfinfdpic_hash_table (info)->elf.srelgot)
1689 1.1 christos #define bfinfdpic_gotfixup_section(info) \
1690 1.1.1.7 christos (bfinfdpic_hash_table (info)->sgotfixup)
1691 1.1 christos #define bfinfdpic_plt_section(info) \
1692 1.1 christos (bfinfdpic_hash_table (info)->elf.splt)
1693 1.1 christos #define bfinfdpic_pltrel_section(info) \
1694 1.1 christos (bfinfdpic_hash_table (info)->elf.srelplt)
1695 1.1 christos #define bfinfdpic_relocs_info(info) \
1696 1.1 christos (bfinfdpic_hash_table (info)->relocs_info)
1697 1.1 christos #define bfinfdpic_got_initial_offset(info) \
1698 1.1 christos (bfinfdpic_hash_table (info)->got0)
1699 1.1 christos #define bfinfdpic_plt_initial_offset(info) \
1700 1.1 christos (bfinfdpic_hash_table (info)->plt0)
1701 1.1 christos #define bfinfdpic_dynamic_got_plt_info(info) \
1702 1.1 christos (bfinfdpic_hash_table (info)->g)
1703 1.1 christos
1704 1.1 christos /* The name of the dynamic interpreter. This is put in the .interp
1705 1.1 christos section. */
1706 1.1 christos
1707 1.1 christos #define ELF_DYNAMIC_INTERPRETER "/lib/ld.so.1"
1708 1.1 christos
1709 1.1 christos #define DEFAULT_STACK_SIZE 0x20000
1710 1.1 christos
1711 1.1 christos /* This structure is used to collect the number of entries present in
1712 1.1 christos each addressable range of the got. */
1713 1.1 christos struct _bfinfdpic_dynamic_got_info
1714 1.1 christos {
1715 1.1 christos /* Several bits of information about the current link. */
1716 1.1 christos struct bfd_link_info *info;
1717 1.1 christos /* Total size needed for GOT entries within the 18- or 32-bit
1718 1.1 christos ranges. */
1719 1.1 christos bfd_vma got17m4, gothilo;
1720 1.1 christos /* Total size needed for function descriptor entries within the 18-
1721 1.1 christos or 32-bit ranges. */
1722 1.1 christos bfd_vma fd17m4, fdhilo;
1723 1.1 christos /* Total size needed function descriptor entries referenced in PLT
1724 1.1 christos entries, that would be profitable to place in offsets close to
1725 1.1 christos the PIC register. */
1726 1.1 christos bfd_vma fdplt;
1727 1.1 christos /* Total size needed by lazy PLT entries. */
1728 1.1 christos bfd_vma lzplt;
1729 1.1 christos /* Number of relocations carried over from input object files. */
1730 1.1 christos unsigned long relocs;
1731 1.1 christos /* Number of fixups introduced by relocations in input object files. */
1732 1.1 christos unsigned long fixups;
1733 1.1 christos };
1734 1.1 christos
1735 1.1 christos /* Create a Blackfin ELF linker hash table. */
1736 1.1 christos
1737 1.1.1.9 christos static struct bfd_link_hash_table *
1738 1.1 christos bfinfdpic_elf_link_hash_table_create (bfd *abfd)
1739 1.1.1.2 christos {
1740 1.1 christos struct bfinfdpic_elf_link_hash_table *ret;
1741 1.1 christos size_t amt = sizeof (struct bfinfdpic_elf_link_hash_table);
1742 1.1 christos
1743 1.1 christos ret = bfd_zmalloc (amt);
1744 1.1 christos if (ret == NULL)
1745 1.1 christos return NULL;
1746 1.1 christos
1747 1.1 christos if (!_bfd_elf_link_hash_table_init (&ret->elf, abfd,
1748 1.1 christos _bfd_elf_link_hash_newfunc,
1749 1.1 christos sizeof (struct elf_link_hash_entry),
1750 1.1 christos BFIN_ELF_DATA))
1751 1.1 christos {
1752 1.1 christos free (ret);
1753 1.1 christos return NULL;
1754 1.1 christos }
1755 1.1 christos
1756 1.1 christos return &ret->elf.root;
1757 1.1 christos }
1758 1.1 christos
1759 1.1 christos /* Decide whether a reference to a symbol can be resolved locally or
1760 1.1 christos not. If the symbol is protected, we want the local address, but
1761 1.1 christos its function descriptor must be assigned by the dynamic linker. */
1762 1.1 christos #define BFINFDPIC_SYM_LOCAL(INFO, H) \
1763 1.1 christos (_bfd_elf_symbol_refs_local_p ((H), (INFO), 1) \
1764 1.1 christos || ! elf_hash_table (INFO)->dynamic_sections_created)
1765 1.1 christos #define BFINFDPIC_FUNCDESC_LOCAL(INFO, H) \
1766 1.1 christos ((H)->dynindx == -1 || ! elf_hash_table (INFO)->dynamic_sections_created)
1767 1.1 christos
1768 1.1 christos /* This structure collects information on what kind of GOT, PLT or
1769 1.1 christos function descriptors are required by relocations that reference a
1770 1.1 christos certain symbol. */
1771 1.1 christos struct bfinfdpic_relocs_info
1772 1.1 christos {
1773 1.1 christos /* The index of the symbol, as stored in the relocation r_info, if
1774 1.1 christos we have a local symbol; -1 otherwise. */
1775 1.1 christos long symndx;
1776 1.1 christos union
1777 1.1 christos {
1778 1.1 christos /* The input bfd in which the symbol is defined, if it's a local
1779 1.1 christos symbol. */
1780 1.1 christos bfd *abfd;
1781 1.1 christos /* If symndx == -1, the hash table entry corresponding to a global
1782 1.1 christos symbol (even if it turns out to bind locally, in which case it
1783 1.1 christos should ideally be replaced with section's symndx + addend). */
1784 1.1 christos struct elf_link_hash_entry *h;
1785 1.1 christos } d;
1786 1.1 christos /* The addend of the relocation that references the symbol. */
1787 1.1 christos bfd_vma addend;
1788 1.1 christos
1789 1.1 christos /* The fields above are used to identify an entry. The fields below
1790 1.1 christos contain information on how an entry is used and, later on, which
1791 1.1 christos locations it was assigned. */
1792 1.1 christos /* The following 2 fields record whether the symbol+addend above was
1793 1.1 christos ever referenced with a GOT relocation. The 17M4 suffix indicates a
1794 1.1 christos GOT17M4 relocation; hilo is used for GOTLO/GOTHI pairs. */
1795 1.1 christos unsigned got17m4;
1796 1.1 christos unsigned gothilo;
1797 1.1 christos /* Whether a FUNCDESC relocation references symbol+addend. */
1798 1.1 christos unsigned fd;
1799 1.1 christos /* Whether a FUNCDESC_GOT relocation references symbol+addend. */
1800 1.1 christos unsigned fdgot17m4;
1801 1.1 christos unsigned fdgothilo;
1802 1.1 christos /* Whether a FUNCDESC_GOTOFF relocation references symbol+addend. */
1803 1.1 christos unsigned fdgoff17m4;
1804 1.1 christos unsigned fdgoffhilo;
1805 1.1 christos /* Whether symbol+addend is referenced with GOTOFF17M4, GOTOFFLO or
1806 1.1 christos GOTOFFHI relocations. The addend doesn't really matter, since we
1807 1.1 christos envision that this will only be used to check whether the symbol
1808 1.1 christos is mapped to the same segment as the got. */
1809 1.1 christos unsigned gotoff;
1810 1.1 christos /* Whether symbol+addend is referenced by a LABEL24 relocation. */
1811 1.1 christos unsigned call;
1812 1.1 christos /* Whether symbol+addend is referenced by a 32 or FUNCDESC_VALUE
1813 1.1 christos relocation. */
1814 1.1 christos unsigned sym;
1815 1.1 christos /* Whether we need a PLT entry for a symbol. Should be implied by
1816 1.1 christos something like:
1817 1.1 christos (call && symndx == -1 && ! BFINFDPIC_SYM_LOCAL (info, d.h)) */
1818 1.1 christos unsigned plt:1;
1819 1.1.1.8 christos /* Whether a function descriptor should be created in this link unit
1820 1.1 christos for symbol+addend. Should be implied by something like:
1821 1.1 christos (plt || fdgotoff17m4 || fdgotofflohi
1822 1.1 christos || ((fd || fdgot17m4 || fdgothilo)
1823 1.1 christos && (symndx != -1 || BFINFDPIC_FUNCDESC_LOCAL (info, d.h)))) */
1824 1.1 christos unsigned privfd:1;
1825 1.1 christos /* Whether a lazy PLT entry is needed for this symbol+addend.
1826 1.1 christos Should be implied by something like:
1827 1.1 christos (privfd && symndx == -1 && ! BFINFDPIC_SYM_LOCAL (info, d.h)
1828 1.1 christos && ! (info->flags & DF_BIND_NOW)) */
1829 1.1 christos unsigned lazyplt:1;
1830 1.1 christos /* Whether we've already emitted GOT relocations and PLT entries as
1831 1.1 christos needed for this symbol. */
1832 1.1 christos unsigned done:1;
1833 1.1 christos
1834 1.1 christos /* The number of R_BFIN_BYTE4_DATA, R_BFIN_FUNCDESC and R_BFIN_FUNCDESC_VALUE
1835 1.1 christos relocations referencing the symbol. */
1836 1.1 christos unsigned relocs32, relocsfd, relocsfdv;
1837 1.1 christos
1838 1.1 christos /* The number of .rofixups entries and dynamic relocations allocated
1839 1.1 christos for this symbol, minus any that might have already been used. */
1840 1.1 christos unsigned fixups, dynrelocs;
1841 1.1 christos
1842 1.1 christos /* The offsets of the GOT entries assigned to symbol+addend, to the
1843 1.1 christos function descriptor's address, and to a function descriptor,
1844 1.1 christos respectively. Should be zero if unassigned. The offsets are
1845 1.1 christos counted from the value that will be assigned to the PIC register,
1846 1.1 christos not from the beginning of the .got section. */
1847 1.1 christos bfd_signed_vma got_entry, fdgot_entry, fd_entry;
1848 1.1 christos /* The offsets of the PLT entries assigned to symbol+addend,
1849 1.1 christos non-lazy and lazy, respectively. If unassigned, should be
1850 1.1 christos (bfd_vma)-1. */
1851 1.1 christos bfd_vma plt_entry, lzplt_entry;
1852 1.1 christos };
1853 1.1 christos
1854 1.1 christos /* Compute a hash with the key fields of an bfinfdpic_relocs_info entry. */
1855 1.1 christos static hashval_t
1856 1.1 christos bfinfdpic_relocs_info_hash (const void *entry_)
1857 1.1 christos {
1858 1.1 christos const struct bfinfdpic_relocs_info *entry = entry_;
1859 1.1 christos
1860 1.1 christos return (entry->symndx == -1
1861 1.1 christos ? (long) entry->d.h->root.root.hash
1862 1.1 christos : entry->symndx + (long) entry->d.abfd->id * 257) + entry->addend;
1863 1.1 christos }
1864 1.1 christos
1865 1.1 christos /* Test whether the key fields of two bfinfdpic_relocs_info entries are
1866 1.1 christos identical. */
1867 1.1 christos static int
1868 1.1 christos bfinfdpic_relocs_info_eq (const void *entry1, const void *entry2)
1869 1.1 christos {
1870 1.1 christos const struct bfinfdpic_relocs_info *e1 = entry1;
1871 1.1 christos const struct bfinfdpic_relocs_info *e2 = entry2;
1872 1.1 christos
1873 1.1 christos return e1->symndx == e2->symndx && e1->addend == e2->addend
1874 1.1 christos && (e1->symndx == -1 ? e1->d.h == e2->d.h : e1->d.abfd == e2->d.abfd);
1875 1.1 christos }
1876 1.1 christos
1877 1.1 christos /* Find or create an entry in a hash table HT that matches the key
1878 1.1 christos fields of the given ENTRY. If it's not found, memory for a new
1879 1.1 christos entry is allocated in ABFD's obstack. */
1880 1.1 christos static struct bfinfdpic_relocs_info *
1881 1.1 christos bfinfdpic_relocs_info_find (struct htab *ht,
1882 1.1 christos bfd *abfd,
1883 1.1 christos const struct bfinfdpic_relocs_info *entry,
1884 1.1 christos enum insert_option insert)
1885 1.1 christos {
1886 1.1 christos struct bfinfdpic_relocs_info **loc;
1887 1.1 christos
1888 1.1 christos if (!ht)
1889 1.1 christos return NULL;
1890 1.1 christos
1891 1.1 christos loc = (struct bfinfdpic_relocs_info **) htab_find_slot (ht, entry, insert);
1892 1.1 christos
1893 1.1 christos if (! loc)
1894 1.1 christos return NULL;
1895 1.1 christos
1896 1.1 christos if (*loc)
1897 1.1 christos return *loc;
1898 1.1 christos
1899 1.1 christos *loc = bfd_zalloc (abfd, sizeof (**loc));
1900 1.1 christos
1901 1.1 christos if (! *loc)
1902 1.1 christos return *loc;
1903 1.1 christos
1904 1.1 christos (*loc)->symndx = entry->symndx;
1905 1.1 christos (*loc)->d = entry->d;
1906 1.1 christos (*loc)->addend = entry->addend;
1907 1.1 christos (*loc)->plt_entry = (bfd_vma)-1;
1908 1.1 christos (*loc)->lzplt_entry = (bfd_vma)-1;
1909 1.1 christos
1910 1.1 christos return *loc;
1911 1.1 christos }
1912 1.1 christos
1913 1.1 christos /* Obtain the address of the entry in HT associated with H's symbol +
1914 1.1.1.2 christos addend, creating a new entry if none existed. ABFD is only used
1915 1.1.1.2 christos for memory allocation purposes. */
1916 1.1.1.2 christos inline static struct bfinfdpic_relocs_info *
1917 1.1.1.2 christos bfinfdpic_relocs_info_for_global (struct htab *ht,
1918 1.1 christos bfd *abfd,
1919 1.1 christos struct elf_link_hash_entry *h,
1920 1.1 christos bfd_vma addend,
1921 1.1 christos enum insert_option insert)
1922 1.1 christos {
1923 1.1 christos struct bfinfdpic_relocs_info entry;
1924 1.1 christos
1925 1.1 christos entry.symndx = -1;
1926 1.1 christos entry.d.h = h;
1927 1.1 christos entry.addend = addend;
1928 1.1 christos
1929 1.1 christos return bfinfdpic_relocs_info_find (ht, abfd, &entry, insert);
1930 1.1 christos }
1931 1.1 christos
1932 1.1 christos /* Obtain the address of the entry in HT associated with the SYMNDXth
1933 1.1 christos local symbol of the input bfd ABFD, plus the addend, creating a new
1934 1.1 christos entry if none existed. */
1935 1.1 christos inline static struct bfinfdpic_relocs_info *
1936 1.1 christos bfinfdpic_relocs_info_for_local (struct htab *ht,
1937 1.1 christos bfd *abfd,
1938 1.1 christos long symndx,
1939 1.1 christos bfd_vma addend,
1940 1.1 christos enum insert_option insert)
1941 1.1 christos {
1942 1.1 christos struct bfinfdpic_relocs_info entry;
1943 1.1 christos
1944 1.1 christos entry.symndx = symndx;
1945 1.1 christos entry.d.abfd = abfd;
1946 1.1 christos entry.addend = addend;
1947 1.1 christos
1948 1.1 christos return bfinfdpic_relocs_info_find (ht, abfd, &entry, insert);
1949 1.1 christos }
1950 1.1 christos
1951 1.1 christos /* Merge fields set by check_relocs() of two entries that end up being
1952 1.1.1.2 christos mapped to the same (presumably global) symbol. */
1953 1.1 christos
1954 1.1 christos inline static void
1955 1.1 christos bfinfdpic_pic_merge_early_relocs_info (struct bfinfdpic_relocs_info *e2,
1956 1.1 christos struct bfinfdpic_relocs_info const *e1)
1957 1.1 christos {
1958 1.1 christos e2->got17m4 |= e1->got17m4;
1959 1.1 christos e2->gothilo |= e1->gothilo;
1960 1.1 christos e2->fd |= e1->fd;
1961 1.1 christos e2->fdgot17m4 |= e1->fdgot17m4;
1962 1.1 christos e2->fdgothilo |= e1->fdgothilo;
1963 1.1 christos e2->fdgoff17m4 |= e1->fdgoff17m4;
1964 1.1 christos e2->fdgoffhilo |= e1->fdgoffhilo;
1965 1.1 christos e2->gotoff |= e1->gotoff;
1966 1.1 christos e2->call |= e1->call;
1967 1.1 christos e2->sym |= e1->sym;
1968 1.1 christos }
1969 1.1 christos
1970 1.1 christos /* Every block of 65535 lazy PLT entries shares a single call to the
1971 1.1 christos resolver, inserted in the 32768th lazy PLT entry (i.e., entry #
1972 1.1 christos 32767, counting from 0). All other lazy PLT entries branch to it
1973 1.1 christos in a single instruction. */
1974 1.1 christos
1975 1.1 christos #define LZPLT_RESOLVER_EXTRA 10
1976 1.1 christos #define LZPLT_NORMAL_SIZE 6
1977 1.1 christos #define LZPLT_ENTRIES 1362
1978 1.1 christos
1979 1.1 christos #define BFINFDPIC_LZPLT_BLOCK_SIZE ((bfd_vma) LZPLT_NORMAL_SIZE * LZPLT_ENTRIES + LZPLT_RESOLVER_EXTRA)
1980 1.1 christos #define BFINFDPIC_LZPLT_RESOLV_LOC (LZPLT_NORMAL_SIZE * LZPLT_ENTRIES / 2)
1981 1.1 christos
1982 1.1 christos /* Add a dynamic relocation to the SRELOC section. */
1983 1.1 christos
1984 1.1 christos inline static bfd_vma
1985 1.1 christos _bfinfdpic_add_dyn_reloc (bfd *output_bfd, asection *sreloc, bfd_vma offset,
1986 1.1 christos int reloc_type, long dynindx, bfd_vma addend,
1987 1.1 christos struct bfinfdpic_relocs_info *entry)
1988 1.1 christos {
1989 1.1 christos Elf_Internal_Rela outrel;
1990 1.1 christos bfd_vma reloc_offset;
1991 1.1 christos
1992 1.1 christos outrel.r_offset = offset;
1993 1.1 christos outrel.r_info = ELF32_R_INFO (dynindx, reloc_type);
1994 1.1 christos outrel.r_addend = addend;
1995 1.1 christos
1996 1.1 christos reloc_offset = sreloc->reloc_count * sizeof (Elf32_External_Rel);
1997 1.1 christos BFD_ASSERT (reloc_offset < sreloc->size);
1998 1.1 christos bfd_elf32_swap_reloc_out (output_bfd, &outrel,
1999 1.1 christos sreloc->contents + reloc_offset);
2000 1.1 christos sreloc->reloc_count++;
2001 1.1 christos
2002 1.1 christos /* If the entry's index is zero, this relocation was probably to a
2003 1.1 christos linkonce section that got discarded. We reserved a dynamic
2004 1.1 christos relocation, but it was for another entry than the one we got at
2005 1.1 christos the time of emitting the relocation. Unfortunately there's no
2006 1.1 christos simple way for us to catch this situation, since the relocation
2007 1.1 christos is cleared right before calling relocate_section, at which point
2008 1.1 christos we no longer know what the relocation used to point to. */
2009 1.1 christos if (entry->symndx)
2010 1.1 christos {
2011 1.1 christos BFD_ASSERT (entry->dynrelocs > 0);
2012 1.1 christos entry->dynrelocs--;
2013 1.1 christos }
2014 1.1 christos
2015 1.1 christos return reloc_offset;
2016 1.1 christos }
2017 1.1 christos
2018 1.1.1.2 christos /* Add a fixup to the ROFIXUP section. */
2019 1.1 christos
2020 1.1 christos static bfd_vma
2021 1.1 christos _bfinfdpic_add_rofixup (bfd *output_bfd, asection *rofixup, bfd_vma offset,
2022 1.1 christos struct bfinfdpic_relocs_info *entry)
2023 1.1 christos {
2024 1.1 christos bfd_vma fixup_offset;
2025 1.1 christos
2026 1.1 christos if (rofixup->flags & SEC_EXCLUDE)
2027 1.1 christos return -1;
2028 1.1 christos
2029 1.1 christos fixup_offset = rofixup->reloc_count * 4;
2030 1.1 christos if (rofixup->contents)
2031 1.1 christos {
2032 1.1 christos BFD_ASSERT (fixup_offset < rofixup->size);
2033 1.1 christos bfd_put_32 (output_bfd, offset, rofixup->contents + fixup_offset);
2034 1.1 christos }
2035 1.1 christos rofixup->reloc_count++;
2036 1.1 christos
2037 1.1 christos if (entry && entry->symndx)
2038 1.1 christos {
2039 1.1 christos /* See discussion about symndx == 0 in _bfinfdpic_add_dyn_reloc
2040 1.1 christos above. */
2041 1.1 christos BFD_ASSERT (entry->fixups > 0);
2042 1.1 christos entry->fixups--;
2043 1.1 christos }
2044 1.1 christos
2045 1.1 christos return fixup_offset;
2046 1.1 christos }
2047 1.1 christos
2048 1.1 christos /* Find the segment number in which OSEC, and output section, is
2049 1.1 christos located. */
2050 1.1 christos
2051 1.1 christos static unsigned
2052 1.1 christos _bfinfdpic_osec_to_segment (bfd *output_bfd, asection *osec)
2053 1.1 christos {
2054 1.1 christos Elf_Internal_Phdr *p = _bfd_elf_find_segment_containing_section (output_bfd, osec);
2055 1.1.1.10 christos
2056 1.1 christos return (p != NULL) ? p - elf_tdata (output_bfd)->phdr : -1;
2057 1.1 christos }
2058 1.1 christos
2059 1.1 christos inline static bool
2060 1.1 christos _bfinfdpic_osec_readonly_p (bfd *output_bfd, asection *osec)
2061 1.1 christos {
2062 1.1 christos unsigned seg = _bfinfdpic_osec_to_segment (output_bfd, osec);
2063 1.1 christos
2064 1.1 christos return ! (elf_tdata (output_bfd)->phdr[seg].p_flags & PF_W);
2065 1.1 christos }
2066 1.1.1.10 christos
2067 1.1 christos /* Generate relocations for GOT entries, function descriptors, and
2068 1.1 christos code for PLT and lazy PLT entries. */
2069 1.1 christos
2070 1.1 christos inline static bool
2071 1.1 christos _bfinfdpic_emit_got_relocs_plt_entries (struct bfinfdpic_relocs_info *entry,
2072 1.1 christos bfd *output_bfd,
2073 1.1 christos struct bfd_link_info *info,
2074 1.1.1.2 christos asection *sec,
2075 1.1 christos Elf_Internal_Sym *sym,
2076 1.1 christos bfd_vma addend)
2077 1.1 christos {
2078 1.1.1.10 christos bfd_vma fd_lazy_rel_offset = (bfd_vma) -1;
2079 1.1 christos int dynindx = -1;
2080 1.1 christos
2081 1.1 christos if (entry->done)
2082 1.1 christos return true;
2083 1.1 christos entry->done = 1;
2084 1.1 christos
2085 1.1 christos if (entry->got_entry || entry->fdgot_entry || entry->fd_entry)
2086 1.1 christos {
2087 1.1 christos /* If the symbol is dynamic, consider it for dynamic
2088 1.1 christos relocations, otherwise decay to section + offset. */
2089 1.1 christos if (entry->symndx == -1 && entry->d.h->dynindx != -1)
2090 1.1 christos dynindx = entry->d.h->dynindx;
2091 1.1 christos else
2092 1.1 christos {
2093 1.1 christos if (sec
2094 1.1 christos && sec->output_section
2095 1.1 christos && ! bfd_is_abs_section (sec->output_section)
2096 1.1 christos && ! bfd_is_und_section (sec->output_section))
2097 1.1 christos dynindx = elf_section_data (sec->output_section)->dynindx;
2098 1.1 christos else
2099 1.1 christos dynindx = 0;
2100 1.1 christos }
2101 1.1 christos }
2102 1.1 christos
2103 1.1 christos /* Generate relocation for GOT entry pointing to the symbol. */
2104 1.1 christos if (entry->got_entry)
2105 1.1 christos {
2106 1.1 christos int idx = dynindx;
2107 1.1 christos bfd_vma ad = addend;
2108 1.1 christos
2109 1.1 christos /* If the symbol is dynamic but binds locally, use
2110 1.1 christos section+offset. */
2111 1.1 christos if (sec && (entry->symndx != -1
2112 1.1 christos || BFINFDPIC_SYM_LOCAL (info, entry->d.h)))
2113 1.1 christos {
2114 1.1 christos if (entry->symndx == -1)
2115 1.1 christos ad += entry->d.h->root.u.def.value;
2116 1.1 christos else
2117 1.1 christos ad += sym->st_value;
2118 1.1 christos ad += sec->output_offset;
2119 1.1 christos if (sec->output_section && elf_section_data (sec->output_section))
2120 1.1 christos idx = elf_section_data (sec->output_section)->dynindx;
2121 1.1 christos else
2122 1.1 christos idx = 0;
2123 1.1 christos }
2124 1.1.1.6 christos
2125 1.1 christos /* If we're linking an executable at a fixed address, we can
2126 1.1 christos omit the dynamic relocation as long as the symbol is local to
2127 1.1 christos this module. */
2128 1.1 christos if (bfd_link_pde (info)
2129 1.1 christos && (entry->symndx != -1
2130 1.1 christos || BFINFDPIC_SYM_LOCAL (info, entry->d.h)))
2131 1.1 christos {
2132 1.1 christos if (sec)
2133 1.1 christos ad += sec->output_section->vma;
2134 1.1 christos if (entry->symndx != -1
2135 1.1 christos || entry->d.h->root.type != bfd_link_hash_undefweak)
2136 1.1 christos _bfinfdpic_add_rofixup (output_bfd,
2137 1.1 christos bfinfdpic_gotfixup_section (info),
2138 1.1 christos bfinfdpic_got_section (info)->output_section
2139 1.1 christos ->vma
2140 1.1 christos + bfinfdpic_got_section (info)->output_offset
2141 1.1 christos + bfinfdpic_got_initial_offset (info)
2142 1.1 christos + entry->got_entry, entry);
2143 1.1 christos }
2144 1.1 christos else
2145 1.1 christos _bfinfdpic_add_dyn_reloc (output_bfd, bfinfdpic_gotrel_section (info),
2146 1.1 christos _bfd_elf_section_offset
2147 1.1 christos (output_bfd, info,
2148 1.1 christos bfinfdpic_got_section (info),
2149 1.1 christos bfinfdpic_got_initial_offset (info)
2150 1.1 christos + entry->got_entry)
2151 1.1 christos + bfinfdpic_got_section (info)
2152 1.1 christos ->output_section->vma
2153 1.1 christos + bfinfdpic_got_section (info)->output_offset,
2154 1.1 christos R_BFIN_BYTE4_DATA, idx, ad, entry);
2155 1.1 christos
2156 1.1 christos bfd_put_32 (output_bfd, ad,
2157 1.1 christos bfinfdpic_got_section (info)->contents
2158 1.1 christos + bfinfdpic_got_initial_offset (info)
2159 1.1 christos + entry->got_entry);
2160 1.1 christos }
2161 1.1 christos
2162 1.1 christos /* Generate relocation for GOT entry pointing to a canonical
2163 1.1 christos function descriptor. */
2164 1.1 christos if (entry->fdgot_entry)
2165 1.1 christos {
2166 1.1 christos int reloc, idx;
2167 1.1 christos bfd_vma ad = 0;
2168 1.1 christos
2169 1.1 christos if (! (entry->symndx == -1
2170 1.1 christos && entry->d.h->root.type == bfd_link_hash_undefweak
2171 1.1 christos && BFINFDPIC_SYM_LOCAL (info, entry->d.h)))
2172 1.1 christos {
2173 1.1 christos /* If the symbol is dynamic and there may be dynamic symbol
2174 1.1 christos resolution because we are, or are linked with, a shared
2175 1.1 christos library, emit a FUNCDESC relocation such that the dynamic
2176 1.1 christos linker will allocate the function descriptor. If the
2177 1.1 christos symbol needs a non-local function descriptor but binds
2178 1.1 christos locally (e.g., its visibility is protected, emit a
2179 1.1.1.6 christos dynamic relocation decayed to section+offset. */
2180 1.1 christos if (entry->symndx == -1
2181 1.1 christos && ! BFINFDPIC_FUNCDESC_LOCAL (info, entry->d.h)
2182 1.1 christos && BFINFDPIC_SYM_LOCAL (info, entry->d.h)
2183 1.1 christos && !bfd_link_pde (info))
2184 1.1 christos {
2185 1.1 christos reloc = R_BFIN_FUNCDESC;
2186 1.1 christos idx = elf_section_data (entry->d.h->root.u.def.section
2187 1.1 christos ->output_section)->dynindx;
2188 1.1 christos ad = entry->d.h->root.u.def.section->output_offset
2189 1.1 christos + entry->d.h->root.u.def.value;
2190 1.1 christos }
2191 1.1 christos else if (entry->symndx == -1
2192 1.1 christos && ! BFINFDPIC_FUNCDESC_LOCAL (info, entry->d.h))
2193 1.1 christos {
2194 1.1.1.10 christos reloc = R_BFIN_FUNCDESC;
2195 1.1 christos idx = dynindx;
2196 1.1 christos ad = addend;
2197 1.1 christos if (ad)
2198 1.1 christos return false;
2199 1.1 christos }
2200 1.1 christos else
2201 1.1 christos {
2202 1.1 christos /* Otherwise, we know we have a private function descriptor,
2203 1.1 christos so reference it directly. */
2204 1.1 christos if (elf_hash_table (info)->dynamic_sections_created)
2205 1.1 christos BFD_ASSERT (entry->privfd);
2206 1.1 christos reloc = R_BFIN_BYTE4_DATA;
2207 1.1 christos idx = elf_section_data (bfinfdpic_got_section (info)
2208 1.1 christos ->output_section)->dynindx;
2209 1.1 christos ad = bfinfdpic_got_section (info)->output_offset
2210 1.1 christos + bfinfdpic_got_initial_offset (info) + entry->fd_entry;
2211 1.1 christos }
2212 1.1 christos
2213 1.1 christos /* If there is room for dynamic symbol resolution, emit the
2214 1.1 christos dynamic relocation. However, if we're linking an
2215 1.1.1.6 christos executable at a fixed location, we won't have emitted a
2216 1.1 christos dynamic symbol entry for the got section, so idx will be
2217 1.1 christos zero, which means we can and should compute the address
2218 1.1 christos of the private descriptor ourselves. */
2219 1.1 christos if (bfd_link_pde (info)
2220 1.1 christos && (entry->symndx != -1
2221 1.1 christos || BFINFDPIC_FUNCDESC_LOCAL (info, entry->d.h)))
2222 1.1 christos {
2223 1.1 christos ad += bfinfdpic_got_section (info)->output_section->vma;
2224 1.1 christos _bfinfdpic_add_rofixup (output_bfd,
2225 1.1 christos bfinfdpic_gotfixup_section (info),
2226 1.1 christos bfinfdpic_got_section (info)
2227 1.1 christos ->output_section->vma
2228 1.1 christos + bfinfdpic_got_section (info)
2229 1.1 christos ->output_offset
2230 1.1 christos + bfinfdpic_got_initial_offset (info)
2231 1.1 christos + entry->fdgot_entry, entry);
2232 1.1 christos }
2233 1.1 christos else
2234 1.1 christos _bfinfdpic_add_dyn_reloc (output_bfd,
2235 1.1 christos bfinfdpic_gotrel_section (info),
2236 1.1 christos _bfd_elf_section_offset
2237 1.1 christos (output_bfd, info,
2238 1.1 christos bfinfdpic_got_section (info),
2239 1.1 christos bfinfdpic_got_initial_offset (info)
2240 1.1 christos + entry->fdgot_entry)
2241 1.1 christos + bfinfdpic_got_section (info)
2242 1.1 christos ->output_section->vma
2243 1.1 christos + bfinfdpic_got_section (info)
2244 1.1 christos ->output_offset,
2245 1.1 christos reloc, idx, ad, entry);
2246 1.1 christos }
2247 1.1 christos
2248 1.1 christos bfd_put_32 (output_bfd, ad,
2249 1.1 christos bfinfdpic_got_section (info)->contents
2250 1.1 christos + bfinfdpic_got_initial_offset (info)
2251 1.1 christos + entry->fdgot_entry);
2252 1.1 christos }
2253 1.1 christos
2254 1.1 christos /* Generate relocation to fill in a private function descriptor in
2255 1.1 christos the GOT. */
2256 1.1 christos if (entry->fd_entry)
2257 1.1 christos {
2258 1.1 christos int idx = dynindx;
2259 1.1 christos bfd_vma ad = addend;
2260 1.1 christos bfd_vma ofst;
2261 1.1 christos long lowword, highword;
2262 1.1 christos
2263 1.1 christos /* If the symbol is dynamic but binds locally, use
2264 1.1 christos section+offset. */
2265 1.1 christos if (sec && (entry->symndx != -1
2266 1.1 christos || BFINFDPIC_SYM_LOCAL (info, entry->d.h)))
2267 1.1 christos {
2268 1.1 christos if (entry->symndx == -1)
2269 1.1 christos ad += entry->d.h->root.u.def.value;
2270 1.1 christos else
2271 1.1 christos ad += sym->st_value;
2272 1.1 christos ad += sec->output_offset;
2273 1.1 christos if (sec->output_section && elf_section_data (sec->output_section))
2274 1.1 christos idx = elf_section_data (sec->output_section)->dynindx;
2275 1.1 christos else
2276 1.1 christos idx = 0;
2277 1.1 christos }
2278 1.1.1.6 christos
2279 1.1 christos /* If we're linking an executable at a fixed address, we can
2280 1.1 christos omit the dynamic relocation as long as the symbol is local to
2281 1.1 christos this module. */
2282 1.1 christos if (bfd_link_pde (info)
2283 1.1 christos && (entry->symndx != -1 || BFINFDPIC_SYM_LOCAL (info, entry->d.h)))
2284 1.1 christos {
2285 1.1 christos if (sec)
2286 1.1 christos ad += sec->output_section->vma;
2287 1.1 christos ofst = 0;
2288 1.1 christos if (entry->symndx != -1
2289 1.1 christos || entry->d.h->root.type != bfd_link_hash_undefweak)
2290 1.1 christos {
2291 1.1 christos _bfinfdpic_add_rofixup (output_bfd,
2292 1.1 christos bfinfdpic_gotfixup_section (info),
2293 1.1 christos bfinfdpic_got_section (info)
2294 1.1 christos ->output_section->vma
2295 1.1 christos + bfinfdpic_got_section (info)
2296 1.1 christos ->output_offset
2297 1.1 christos + bfinfdpic_got_initial_offset (info)
2298 1.1 christos + entry->fd_entry, entry);
2299 1.1 christos _bfinfdpic_add_rofixup (output_bfd,
2300 1.1 christos bfinfdpic_gotfixup_section (info),
2301 1.1 christos bfinfdpic_got_section (info)
2302 1.1 christos ->output_section->vma
2303 1.1 christos + bfinfdpic_got_section (info)
2304 1.1 christos ->output_offset
2305 1.1 christos + bfinfdpic_got_initial_offset (info)
2306 1.1 christos + entry->fd_entry + 4, entry);
2307 1.1 christos }
2308 1.1 christos }
2309 1.1 christos else
2310 1.1 christos {
2311 1.1 christos ofst
2312 1.1 christos = _bfinfdpic_add_dyn_reloc (output_bfd,
2313 1.1 christos entry->lazyplt
2314 1.1 christos ? bfinfdpic_pltrel_section (info)
2315 1.1 christos : bfinfdpic_gotrel_section (info),
2316 1.1 christos _bfd_elf_section_offset
2317 1.1 christos (output_bfd, info,
2318 1.1 christos bfinfdpic_got_section (info),
2319 1.1 christos bfinfdpic_got_initial_offset (info)
2320 1.1 christos + entry->fd_entry)
2321 1.1 christos + bfinfdpic_got_section (info)
2322 1.1 christos ->output_section->vma
2323 1.1 christos + bfinfdpic_got_section (info)
2324 1.1 christos ->output_offset,
2325 1.1 christos R_BFIN_FUNCDESC_VALUE, idx, ad, entry);
2326 1.1.1.6 christos }
2327 1.1.1.6 christos
2328 1.1.1.6 christos /* If we've omitted the dynamic relocation, just emit the fixed
2329 1.1 christos addresses of the symbol and of the local GOT base offset. */
2330 1.1 christos if (bfd_link_pde (info)
2331 1.1 christos && sec
2332 1.1 christos && sec->output_section)
2333 1.1 christos {
2334 1.1 christos lowword = ad;
2335 1.1 christos highword = bfinfdpic_got_section (info)->output_section->vma
2336 1.1 christos + bfinfdpic_got_section (info)->output_offset
2337 1.1 christos + bfinfdpic_got_initial_offset (info);
2338 1.1.1.10 christos }
2339 1.1 christos else if (entry->lazyplt)
2340 1.1 christos {
2341 1.1 christos if (ad)
2342 1.1 christos return false;
2343 1.1 christos
2344 1.1 christos fd_lazy_rel_offset = ofst;
2345 1.1 christos
2346 1.1 christos /* A function descriptor used for lazy or local resolving is
2347 1.1 christos initialized such that its high word contains the output
2348 1.1 christos section index in which the PLT entries are located, and
2349 1.1 christos the low word contains the address of the lazy PLT entry
2350 1.1 christos entry point, that must be within the memory region
2351 1.1 christos assigned to that section. */
2352 1.1 christos lowword = entry->lzplt_entry + 4
2353 1.1 christos + bfinfdpic_plt_section (info)->output_offset
2354 1.1 christos + bfinfdpic_plt_section (info)->output_section->vma;
2355 1.1 christos highword = _bfinfdpic_osec_to_segment
2356 1.1 christos (output_bfd, bfinfdpic_plt_section (info)->output_section);
2357 1.1 christos }
2358 1.1 christos else
2359 1.1 christos {
2360 1.1 christos /* A function descriptor for a local function gets the index
2361 1.1 christos of the section. For a non-local function, it's
2362 1.1 christos disregarded. */
2363 1.1 christos lowword = ad;
2364 1.1 christos if (sec == NULL
2365 1.1 christos || (entry->symndx == -1 && entry->d.h->dynindx != -1
2366 1.1 christos && entry->d.h->dynindx == idx))
2367 1.1 christos highword = 0;
2368 1.1 christos else
2369 1.1 christos highword = _bfinfdpic_osec_to_segment
2370 1.1 christos (output_bfd, sec->output_section);
2371 1.1 christos }
2372 1.1 christos
2373 1.1 christos bfd_put_32 (output_bfd, lowword,
2374 1.1 christos bfinfdpic_got_section (info)->contents
2375 1.1 christos + bfinfdpic_got_initial_offset (info)
2376 1.1 christos + entry->fd_entry);
2377 1.1 christos bfd_put_32 (output_bfd, highword,
2378 1.1 christos bfinfdpic_got_section (info)->contents
2379 1.1 christos + bfinfdpic_got_initial_offset (info)
2380 1.1 christos + entry->fd_entry + 4);
2381 1.1 christos }
2382 1.1 christos
2383 1.1 christos /* Generate code for the PLT entry. */
2384 1.1 christos if (entry->plt_entry != (bfd_vma) -1)
2385 1.1 christos {
2386 1.1 christos bfd_byte *plt_code = bfinfdpic_plt_section (info)->contents
2387 1.1 christos + entry->plt_entry;
2388 1.1 christos
2389 1.1 christos BFD_ASSERT (entry->fd_entry);
2390 1.1 christos
2391 1.1 christos /* Figure out what kind of PLT entry we need, depending on the
2392 1.1 christos location of the function descriptor within the GOT. */
2393 1.1 christos if (entry->fd_entry >= -(1 << (18 - 1))
2394 1.1 christos && entry->fd_entry + 4 < (1 << (18 - 1)))
2395 1.1 christos {
2396 1.1 christos /* P1 = [P3 + fd_entry]; P3 = [P3 + fd_entry + 4] */
2397 1.1 christos bfd_put_32 (output_bfd,
2398 1.1 christos 0xe519 | ((entry->fd_entry << 14) & 0xFFFF0000),
2399 1.1 christos plt_code);
2400 1.1 christos bfd_put_32 (output_bfd,
2401 1.1 christos 0xe51b | (((entry->fd_entry + 4) << 14) & 0xFFFF0000),
2402 1.1 christos plt_code + 4);
2403 1.1 christos plt_code += 8;
2404 1.1 christos }
2405 1.1 christos else
2406 1.1 christos {
2407 1.1 christos /* P1.L = fd_entry; P1.H = fd_entry;
2408 1.1 christos P3 = P3 + P1;
2409 1.1 christos P1 = [P3];
2410 1.1 christos P3 = [P3 + 4]; */
2411 1.1 christos bfd_put_32 (output_bfd,
2412 1.1 christos 0xe109 | (entry->fd_entry << 16),
2413 1.1 christos plt_code);
2414 1.1 christos bfd_put_32 (output_bfd,
2415 1.1 christos 0xe149 | (entry->fd_entry & 0xFFFF0000),
2416 1.1 christos plt_code + 4);
2417 1.1 christos bfd_put_16 (output_bfd, 0x5ad9, plt_code + 8);
2418 1.1 christos bfd_put_16 (output_bfd, 0x9159, plt_code + 10);
2419 1.1 christos bfd_put_16 (output_bfd, 0xac5b, plt_code + 12);
2420 1.1 christos plt_code += 14;
2421 1.1 christos }
2422 1.1 christos /* JUMP (P1) */
2423 1.1 christos bfd_put_16 (output_bfd, 0x0051, plt_code);
2424 1.1 christos }
2425 1.1 christos
2426 1.1 christos /* Generate code for the lazy PLT entry. */
2427 1.1 christos if (entry->lzplt_entry != (bfd_vma) -1)
2428 1.1 christos {
2429 1.1 christos bfd_byte *lzplt_code = bfinfdpic_plt_section (info)->contents
2430 1.1 christos + entry->lzplt_entry;
2431 1.1 christos bfd_vma resolverStub_addr;
2432 1.1 christos
2433 1.1 christos bfd_put_32 (output_bfd, fd_lazy_rel_offset, lzplt_code);
2434 1.1 christos lzplt_code += 4;
2435 1.1 christos
2436 1.1 christos resolverStub_addr = entry->lzplt_entry / BFINFDPIC_LZPLT_BLOCK_SIZE
2437 1.1 christos * BFINFDPIC_LZPLT_BLOCK_SIZE + BFINFDPIC_LZPLT_RESOLV_LOC;
2438 1.1 christos if (resolverStub_addr >= bfinfdpic_plt_initial_offset (info))
2439 1.1 christos resolverStub_addr = bfinfdpic_plt_initial_offset (info) - LZPLT_NORMAL_SIZE - LZPLT_RESOLVER_EXTRA;
2440 1.1 christos
2441 1.1 christos if (entry->lzplt_entry == resolverStub_addr)
2442 1.1 christos {
2443 1.1 christos /* This is a lazy PLT entry that includes a resolver call.
2444 1.1 christos P2 = [P3];
2445 1.1 christos R3 = [P3 + 4];
2446 1.1 christos JUMP (P2); */
2447 1.1 christos bfd_put_32 (output_bfd,
2448 1.1 christos 0xa05b915a,
2449 1.1 christos lzplt_code);
2450 1.1 christos bfd_put_16 (output_bfd, 0x0052, lzplt_code + 4);
2451 1.1 christos }
2452 1.1 christos else
2453 1.1 christos {
2454 1.1 christos /* JUMP.S resolverStub */
2455 1.1 christos bfd_put_16 (output_bfd,
2456 1.1 christos 0x2000
2457 1.1 christos | (((resolverStub_addr - entry->lzplt_entry)
2458 1.1 christos / 2) & (((bfd_vma)1 << 12) - 1)),
2459 1.1.1.10 christos lzplt_code);
2460 1.1 christos }
2461 1.1 christos }
2462 1.1 christos
2463 1.1 christos return true;
2464 1.1 christos }
2465 1.1 christos
2466 1.1 christos /* Relocate an Blackfin ELF section.
2468 1.1 christos
2469 1.1 christos The RELOCATE_SECTION function is called by the new ELF backend linker
2470 1.1 christos to handle the relocations for a section.
2471 1.1 christos
2472 1.1 christos The relocs are always passed as Rela structures; if the section
2473 1.1 christos actually uses Rel structures, the r_addend field will always be
2474 1.1 christos zero.
2475 1.1 christos
2476 1.1 christos This function is responsible for adjusting the section contents as
2477 1.1 christos necessary, and (if using Rela relocs and generating a relocatable
2478 1.1 christos output file) adjusting the reloc addend as necessary.
2479 1.1 christos
2480 1.1 christos This function does not have to worry about setting the reloc
2481 1.1 christos address or the reloc symbol index.
2482 1.1 christos
2483 1.1 christos LOCAL_SYMS is a pointer to the swapped in local symbols.
2484 1.1 christos
2485 1.1 christos LOCAL_SECTIONS is an array giving the section in the input file
2486 1.1 christos corresponding to the st_shndx field of each local symbol.
2487 1.1 christos
2488 1.1 christos The global hash table entry for the global symbols can be found
2489 1.1 christos via elf_sym_hashes (input_bfd).
2490 1.1 christos
2491 1.1 christos When generating relocatable output, this function must handle
2492 1.1.1.10 christos STB_LOCAL/STT_SECTION symbols specially. The output symbol is
2493 1.1 christos going to be the section symbol corresponding to the output
2494 1.1 christos section, which means that the addend must be adjusted
2495 1.1 christos accordingly. */
2496 1.1 christos
2497 1.1 christos static int
2498 1.1 christos bfinfdpic_relocate_section (bfd * output_bfd,
2499 1.1 christos struct bfd_link_info *info,
2500 1.1 christos bfd * input_bfd,
2501 1.1 christos asection * input_section,
2502 1.1 christos bfd_byte * contents,
2503 1.1 christos Elf_Internal_Rela * relocs,
2504 1.1 christos Elf_Internal_Sym * local_syms,
2505 1.1 christos asection ** local_sections)
2506 1.1 christos {
2507 1.1 christos Elf_Internal_Shdr *symtab_hdr;
2508 1.1.1.6 christos struct elf_link_hash_entry **sym_hashes;
2509 1.1 christos Elf_Internal_Rela *rel;
2510 1.1 christos Elf_Internal_Rela *relend;
2511 1.1 christos unsigned isec_segment, got_segment, plt_segment,
2512 1.1 christos check_segment[2];
2513 1.1 christos int silence_segment_error = !bfd_link_pic (info);
2514 1.1 christos
2515 1.1 christos symtab_hdr = & elf_tdata (input_bfd)->symtab_hdr;
2516 1.1 christos sym_hashes = elf_sym_hashes (input_bfd);
2517 1.1 christos relend = relocs + input_section->reloc_count;
2518 1.1 christos
2519 1.1 christos isec_segment = _bfinfdpic_osec_to_segment (output_bfd,
2520 1.1 christos input_section->output_section);
2521 1.1 christos if (IS_FDPIC (output_bfd) && bfinfdpic_got_section (info))
2522 1.1 christos got_segment = _bfinfdpic_osec_to_segment (output_bfd,
2523 1.1 christos bfinfdpic_got_section (info)
2524 1.1 christos ->output_section);
2525 1.1 christos else
2526 1.1 christos got_segment = -1;
2527 1.1 christos if (IS_FDPIC (output_bfd) && elf_hash_table (info)->dynamic_sections_created)
2528 1.1 christos plt_segment = _bfinfdpic_osec_to_segment (output_bfd,
2529 1.1 christos bfinfdpic_plt_section (info)
2530 1.1 christos ->output_section);
2531 1.1 christos else
2532 1.1 christos plt_segment = -1;
2533 1.1 christos
2534 1.1 christos for (rel = relocs; rel < relend; rel ++)
2535 1.1 christos {
2536 1.1 christos reloc_howto_type *howto;
2537 1.1 christos unsigned long r_symndx;
2538 1.1 christos Elf_Internal_Sym *sym;
2539 1.1 christos asection *sec;
2540 1.1 christos struct elf_link_hash_entry *h;
2541 1.1 christos bfd_vma relocation;
2542 1.1 christos bfd_reloc_status_type r;
2543 1.1 christos const char * name = NULL;
2544 1.1 christos int r_type;
2545 1.1 christos asection *osec;
2546 1.1 christos struct bfinfdpic_relocs_info *picrel;
2547 1.1 christos bfd_vma orig_addend = rel->r_addend;
2548 1.1 christos
2549 1.1 christos r_type = ELF32_R_TYPE (rel->r_info);
2550 1.1 christos
2551 1.1 christos if (r_type == R_BFIN_GNU_VTINHERIT
2552 1.1 christos || r_type == R_BFIN_GNU_VTENTRY)
2553 1.1 christos continue;
2554 1.1 christos
2555 1.1.1.10 christos r_symndx = ELF32_R_SYM (rel->r_info);
2556 1.1 christos howto = bfin_reloc_type_lookup (input_bfd, r_type);
2557 1.1 christos if (howto == NULL)
2558 1.1 christos {
2559 1.1 christos bfd_set_error (bfd_error_bad_value);
2560 1.1 christos return false;
2561 1.1.1.9 christos }
2562 1.1 christos
2563 1.1 christos h = NULL;
2564 1.1 christos sym = NULL;
2565 1.1 christos sec = NULL;
2566 1.1 christos picrel = NULL;
2567 1.1 christos
2568 1.1 christos if (r_symndx < symtab_hdr->sh_info)
2569 1.1 christos {
2570 1.1 christos sym = local_syms + r_symndx;
2571 1.1.1.9 christos osec = sec = local_sections [r_symndx];
2572 1.1 christos relocation = _bfd_elf_rela_local_sym (output_bfd, sym, &sec, rel);
2573 1.1 christos
2574 1.1 christos name = bfd_elf_string_from_elf_section
2575 1.1.1.10 christos (input_bfd, symtab_hdr->sh_link, sym->st_name);
2576 1.1.1.10 christos name = name == NULL ? bfd_section_name (sec) : name;
2577 1.1 christos }
2578 1.1 christos else
2579 1.1 christos {
2580 1.1 christos bool warned, ignored;
2581 1.1.1.3 christos bool unresolved_reloc;
2582 1.1 christos
2583 1.1 christos RELOC_FOR_GLOBAL_SYMBOL (info, input_bfd, input_section, rel,
2584 1.1 christos r_symndx, symtab_hdr, sym_hashes,
2585 1.1.1.2 christos h, sec, relocation,
2586 1.1 christos unresolved_reloc, warned, ignored);
2587 1.1.1.2 christos osec = sec;
2588 1.1 christos }
2589 1.1.1.6 christos
2590 1.1 christos if (sec != NULL && discarded_section (sec))
2591 1.1 christos RELOC_AGAINST_DISCARDED_SECTION (info, input_bfd, input_section,
2592 1.1 christos rel, 1, relend, howto, 0, contents);
2593 1.1 christos
2594 1.1 christos if (bfd_link_relocatable (info))
2595 1.1 christos continue;
2596 1.1 christos
2597 1.1 christos if (h != NULL
2598 1.1 christos && (h->root.type == bfd_link_hash_defined
2599 1.1 christos || h->root.type == bfd_link_hash_defweak)
2600 1.1 christos && !BFINFDPIC_SYM_LOCAL (info, h))
2601 1.1 christos {
2602 1.1 christos osec = sec = NULL;
2603 1.1 christos relocation = 0;
2604 1.1 christos }
2605 1.1 christos
2606 1.1 christos switch (r_type)
2607 1.1 christos {
2608 1.1.1.7 christos case R_BFIN_PCREL24:
2609 1.1 christos case R_BFIN_PCREL24_JUMP_L:
2610 1.1 christos case R_BFIN_BYTE4_DATA:
2611 1.1 christos if (! IS_FDPIC (output_bfd))
2612 1.1 christos goto non_fdpic;
2613 1.1 christos /* Fall through. */
2614 1.1 christos
2615 1.1 christos case R_BFIN_GOT17M4:
2616 1.1 christos case R_BFIN_GOTHI:
2617 1.1 christos case R_BFIN_GOTLO:
2618 1.1 christos case R_BFIN_FUNCDESC_GOT17M4:
2619 1.1 christos case R_BFIN_FUNCDESC_GOTHI:
2620 1.1 christos case R_BFIN_FUNCDESC_GOTLO:
2621 1.1 christos case R_BFIN_GOTOFF17M4:
2622 1.1 christos case R_BFIN_GOTOFFHI:
2623 1.1 christos case R_BFIN_GOTOFFLO:
2624 1.1.1.9 christos case R_BFIN_FUNCDESC_GOTOFF17M4:
2625 1.1.1.9 christos case R_BFIN_FUNCDESC_GOTOFFHI:
2626 1.1.1.9 christos case R_BFIN_FUNCDESC_GOTOFFLO:
2627 1.1 christos case R_BFIN_FUNCDESC:
2628 1.1 christos case R_BFIN_FUNCDESC_VALUE:
2629 1.1 christos if ((input_section->flags & SEC_ALLOC) == 0)
2630 1.1 christos break;
2631 1.1 christos
2632 1.1 christos if (h != NULL)
2633 1.1 christos picrel = bfinfdpic_relocs_info_for_global (bfinfdpic_relocs_info
2634 1.1 christos (info), input_bfd, h,
2635 1.1 christos orig_addend, INSERT);
2636 1.1 christos else
2637 1.1 christos /* In order to find the entry we created before, we must
2638 1.1 christos use the original addend, not the one that may have been
2639 1.1.1.10 christos modified by _bfd_elf_rela_local_sym(). */
2640 1.1 christos picrel = bfinfdpic_relocs_info_for_local (bfinfdpic_relocs_info
2641 1.1 christos (info), input_bfd, r_symndx,
2642 1.1 christos orig_addend, INSERT);
2643 1.1 christos if (! picrel)
2644 1.1 christos return false;
2645 1.1.1.7 christos
2646 1.1.1.7 christos if (!_bfinfdpic_emit_got_relocs_plt_entries (picrel, output_bfd, info,
2647 1.1.1.8 christos osec, sym,
2648 1.1.1.8 christos rel->r_addend))
2649 1.1.1.8 christos {
2650 1.1.1.10 christos _bfd_error_handler
2651 1.1 christos /* xgettext:c-format */
2652 1.1 christos (_("%pB: relocation at `%pA+%#" PRIx64 "' "
2653 1.1 christos "references symbol `%s' with nonzero addend"),
2654 1.1 christos input_bfd, input_section, (uint64_t) rel->r_offset, name);
2655 1.1 christos return false;
2656 1.1 christos
2657 1.1 christos }
2658 1.1 christos
2659 1.1.1.2 christos break;
2660 1.1.1.2 christos
2661 1.1.1.2 christos default:
2662 1.1 christos non_fdpic:
2663 1.1 christos picrel = NULL;
2664 1.1 christos if (h && ! BFINFDPIC_SYM_LOCAL (info, h)
2665 1.1 christos && _bfd_elf_section_offset (output_bfd, info, input_section,
2666 1.1.1.10 christos rel->r_offset) != (bfd_vma) -1)
2667 1.1 christos {
2668 1.1 christos info->callbacks->warning
2669 1.1 christos (info, _("relocation references symbol not defined in the module"),
2670 1.1 christos name, input_bfd, input_section, rel->r_offset);
2671 1.1 christos return false;
2672 1.1 christos }
2673 1.1 christos break;
2674 1.1 christos }
2675 1.1 christos
2676 1.1 christos switch (r_type)
2677 1.1 christos {
2678 1.1 christos case R_BFIN_PCREL24:
2679 1.1 christos case R_BFIN_PCREL24_JUMP_L:
2680 1.1 christos check_segment[0] = isec_segment;
2681 1.1 christos if (! IS_FDPIC (output_bfd))
2682 1.1 christos check_segment[1] = isec_segment;
2683 1.1 christos else if (picrel->plt)
2684 1.1 christos {
2685 1.1 christos relocation = bfinfdpic_plt_section (info)->output_section->vma
2686 1.1 christos + bfinfdpic_plt_section (info)->output_offset
2687 1.1 christos + picrel->plt_entry;
2688 1.1 christos check_segment[1] = plt_segment;
2689 1.1 christos }
2690 1.1 christos /* We don't want to warn on calls to undefined weak symbols,
2691 1.1 christos as calls to them must be protected by non-NULL tests
2692 1.1 christos anyway, and unprotected calls would invoke undefined
2693 1.1 christos behavior. */
2694 1.1 christos else if (picrel->symndx == -1
2695 1.1 christos && picrel->d.h->root.type == bfd_link_hash_undefweak)
2696 1.1 christos check_segment[1] = check_segment[0];
2697 1.1 christos else
2698 1.1 christos check_segment[1] = sec
2699 1.1 christos ? _bfinfdpic_osec_to_segment (output_bfd, sec->output_section)
2700 1.1 christos : (unsigned)-1;
2701 1.1 christos break;
2702 1.1 christos
2703 1.1 christos case R_BFIN_GOT17M4:
2704 1.1 christos case R_BFIN_GOTHI:
2705 1.1 christos case R_BFIN_GOTLO:
2706 1.1 christos relocation = picrel->got_entry;
2707 1.1 christos check_segment[0] = check_segment[1] = got_segment;
2708 1.1 christos break;
2709 1.1 christos
2710 1.1 christos case R_BFIN_FUNCDESC_GOT17M4:
2711 1.1 christos case R_BFIN_FUNCDESC_GOTHI:
2712 1.1 christos case R_BFIN_FUNCDESC_GOTLO:
2713 1.1 christos relocation = picrel->fdgot_entry;
2714 1.1 christos check_segment[0] = check_segment[1] = got_segment;
2715 1.1 christos break;
2716 1.1 christos
2717 1.1 christos case R_BFIN_GOTOFFHI:
2718 1.1 christos case R_BFIN_GOTOFF17M4:
2719 1.1 christos case R_BFIN_GOTOFFLO:
2720 1.1 christos relocation -= bfinfdpic_got_section (info)->output_section->vma
2721 1.1 christos + bfinfdpic_got_section (info)->output_offset
2722 1.1 christos + bfinfdpic_got_initial_offset (info);
2723 1.1 christos check_segment[0] = got_segment;
2724 1.1 christos check_segment[1] = sec
2725 1.1 christos ? _bfinfdpic_osec_to_segment (output_bfd, sec->output_section)
2726 1.1 christos : (unsigned)-1;
2727 1.1 christos break;
2728 1.1 christos
2729 1.1 christos case R_BFIN_FUNCDESC_GOTOFF17M4:
2730 1.1 christos case R_BFIN_FUNCDESC_GOTOFFHI:
2731 1.1 christos case R_BFIN_FUNCDESC_GOTOFFLO:
2732 1.1.1.10 christos relocation = picrel->fd_entry;
2733 1.1.1.10 christos check_segment[0] = check_segment[1] = got_segment;
2734 1.1.1.10 christos break;
2735 1.1.1.10 christos
2736 1.1 christos case R_BFIN_FUNCDESC:
2737 1.1.1.10 christos if ((input_section->flags & SEC_ALLOC) != 0)
2738 1.1.1.10 christos {
2739 1.1.1.10 christos int dynindx;
2740 1.1.1.10 christos bfd_vma addend = rel->r_addend;
2741 1.1.1.10 christos
2742 1.1.1.10 christos if (! (h && h->root.type == bfd_link_hash_undefweak
2743 1.1.1.10 christos && BFINFDPIC_SYM_LOCAL (info, h)))
2744 1.1.1.10 christos {
2745 1.1.1.10 christos /* If the symbol is dynamic and there may be dynamic
2746 1.1.1.10 christos symbol resolution because we are or are linked with a
2747 1.1.1.10 christos shared library, emit a FUNCDESC relocation such that
2748 1.1.1.10 christos the dynamic linker will allocate the function
2749 1.1.1.10 christos descriptor. If the symbol needs a non-local function
2750 1.1.1.10 christos descriptor but binds locally (e.g., its visibility is
2751 1.1.1.10 christos protected, emit a dynamic relocation decayed to
2752 1.1.1.10 christos section+offset. */
2753 1.1.1.10 christos if (h && ! BFINFDPIC_FUNCDESC_LOCAL (info, h)
2754 1.1.1.10 christos && BFINFDPIC_SYM_LOCAL (info, h)
2755 1.1.1.10 christos && !bfd_link_pde (info))
2756 1.1.1.10 christos {
2757 1.1.1.10 christos dynindx = elf_section_data (h->root.u.def.section
2758 1.1.1.10 christos ->output_section)->dynindx;
2759 1.1.1.10 christos addend += h->root.u.def.section->output_offset
2760 1.1.1.10 christos + h->root.u.def.value;
2761 1.1.1.10 christos }
2762 1.1.1.10 christos else if (h && ! BFINFDPIC_FUNCDESC_LOCAL (info, h))
2763 1.1.1.10 christos {
2764 1.1.1.10 christos if (addend)
2765 1.1.1.10 christos {
2766 1.1.1.10 christos info->callbacks->warning
2767 1.1.1.10 christos (info, _("R_BFIN_FUNCDESC references dynamic symbol with nonzero addend"),
2768 1.1.1.10 christos name, input_bfd, input_section, rel->r_offset);
2769 1.1.1.10 christos return false;
2770 1.1.1.10 christos }
2771 1.1.1.10 christos dynindx = h->dynindx;
2772 1.1.1.10 christos }
2773 1.1.1.10 christos else
2774 1.1.1.10 christos {
2775 1.1.1.10 christos /* Otherwise, we know we have a private function
2776 1.1.1.10 christos descriptor, so reference it directly. */
2777 1.1.1.10 christos BFD_ASSERT (picrel->privfd);
2778 1.1.1.10 christos r_type = R_BFIN_BYTE4_DATA;
2779 1.1.1.10 christos dynindx = elf_section_data (bfinfdpic_got_section (info)
2780 1.1 christos ->output_section)->dynindx;
2781 1.1.1.10 christos addend = bfinfdpic_got_section (info)->output_offset
2782 1.1.1.10 christos + bfinfdpic_got_initial_offset (info)
2783 1.1.1.10 christos + picrel->fd_entry;
2784 1.1.1.10 christos }
2785 1.1.1.10 christos
2786 1.1.1.10 christos /* If there is room for dynamic symbol resolution, emit
2787 1.1.1.10 christos the dynamic relocation. However, if we're linking an
2788 1.1.1.10 christos executable at a fixed location, we won't have emitted a
2789 1.1.1.10 christos dynamic symbol entry for the got section, so idx will
2790 1.1.1.10 christos be zero, which means we can and should compute the
2791 1.1 christos address of the private descriptor ourselves. */
2792 1.1.1.10 christos if (bfd_link_pde (info)
2793 1.1.1.10 christos && (!h || BFINFDPIC_FUNCDESC_LOCAL (info, h)))
2794 1.1.1.10 christos {
2795 1.1.1.10 christos bfd_vma offset;
2796 1.1.1.10 christos
2797 1.1.1.10 christos addend += bfinfdpic_got_section (info)->output_section->vma;
2798 1.1.1.10 christos if ((bfd_section_flags (input_section->output_section)
2799 1.1.1.10 christos & (SEC_ALLOC | SEC_LOAD)) == (SEC_ALLOC | SEC_LOAD))
2800 1.1.1.10 christos {
2801 1.1.1.10 christos if (_bfinfdpic_osec_readonly_p (output_bfd,
2802 1.1.1.10 christos input_section
2803 1.1.1.10 christos ->output_section))
2804 1.1.1.10 christos {
2805 1.1.1.10 christos info->callbacks->warning
2806 1.1.1.10 christos (info,
2807 1.1.1.10 christos _("cannot emit fixups in read-only section"),
2808 1.1.1.10 christos name, input_bfd, input_section, rel->r_offset);
2809 1.1.1.10 christos return false;
2810 1.1 christos }
2811 1.1.1.10 christos
2812 1.1.1.10 christos offset = _bfd_elf_section_offset
2813 1.1.1.10 christos (output_bfd, info,
2814 1.1.1.10 christos input_section, rel->r_offset);
2815 1.1.1.10 christos
2816 1.1.1.10 christos if (offset != (bfd_vma)-1)
2817 1.1.1.10 christos _bfinfdpic_add_rofixup (output_bfd,
2818 1.1.1.10 christos bfinfdpic_gotfixup_section
2819 1.1.1.10 christos (info),
2820 1.1.1.10 christos offset + input_section
2821 1.1.1.10 christos ->output_section->vma
2822 1.1.1.10 christos + input_section->output_offset,
2823 1.1.1.10 christos picrel);
2824 1.1.1.10 christos }
2825 1.1 christos }
2826 1.1.1.10 christos else if ((bfd_section_flags (input_section->output_section)
2827 1.1.1.10 christos & (SEC_ALLOC | SEC_LOAD)) == (SEC_ALLOC | SEC_LOAD))
2828 1.1.1.10 christos {
2829 1.1.1.10 christos bfd_vma offset;
2830 1.1.1.10 christos
2831 1.1.1.10 christos if (_bfinfdpic_osec_readonly_p (output_bfd,
2832 1.1.1.10 christos input_section
2833 1.1.1.10 christos ->output_section))
2834 1.1.1.10 christos {
2835 1.1.1.10 christos info->callbacks->warning
2836 1.1.1.10 christos (info,
2837 1.1.1.10 christos _("cannot emit dynamic relocations in read-only section"),
2838 1.1.1.10 christos name, input_bfd, input_section, rel->r_offset);
2839 1.1.1.10 christos return false;
2840 1.1.1.10 christos }
2841 1.1.1.10 christos offset = _bfd_elf_section_offset (output_bfd, info,
2842 1.1 christos input_section, rel->r_offset);
2843 1.1 christos
2844 1.1 christos if (offset != (bfd_vma)-1)
2845 1.1.1.10 christos _bfinfdpic_add_dyn_reloc (output_bfd,
2846 1.1.1.10 christos bfinfdpic_gotrel_section (info),
2847 1.1.1.10 christos offset + input_section
2848 1.1.1.10 christos ->output_section->vma
2849 1.1.1.10 christos + input_section->output_offset,
2850 1.1.1.10 christos r_type,
2851 1.1 christos dynindx, addend, picrel);
2852 1.1.1.10 christos }
2853 1.1.1.10 christos else
2854 1.1.1.10 christos addend += bfinfdpic_got_section (info)->output_section->vma;
2855 1.1.1.10 christos }
2856 1.1 christos
2857 1.1 christos /* We want the addend in-place because dynamic
2858 1.1 christos relocations are REL. Setting relocation to it should
2859 1.1 christos arrange for it to be installed. */
2860 1.1 christos relocation = addend - rel->r_addend;
2861 1.1 christos }
2862 1.1 christos check_segment[0] = check_segment[1] = got_segment;
2863 1.1 christos break;
2864 1.1 christos
2865 1.1 christos case R_BFIN_BYTE4_DATA:
2866 1.1 christos if (! IS_FDPIC (output_bfd))
2867 1.1 christos {
2868 1.1 christos check_segment[0] = check_segment[1] = -1;
2869 1.1 christos break;
2870 1.1 christos }
2871 1.1 christos /* Fall through. */
2872 1.1 christos case R_BFIN_FUNCDESC_VALUE:
2873 1.1 christos {
2874 1.1 christos int dynindx;
2875 1.1 christos bfd_vma addend = rel->r_addend;
2876 1.1 christos bfd_vma offset;
2877 1.1 christos offset = _bfd_elf_section_offset (output_bfd, info,
2878 1.1 christos input_section, rel->r_offset);
2879 1.1 christos
2880 1.1 christos /* If the symbol is dynamic but binds locally, use
2881 1.1 christos section+offset. */
2882 1.1 christos if (h && ! BFINFDPIC_SYM_LOCAL (info, h))
2883 1.1 christos {
2884 1.1.1.10 christos if (addend && r_type == R_BFIN_FUNCDESC_VALUE)
2885 1.1 christos {
2886 1.1 christos info->callbacks->warning
2887 1.1 christos (info, _("R_BFIN_FUNCDESC_VALUE references dynamic symbol with nonzero addend"),
2888 1.1 christos name, input_bfd, input_section, rel->r_offset);
2889 1.1 christos return false;
2890 1.1 christos }
2891 1.1 christos dynindx = h->dynindx;
2892 1.1 christos }
2893 1.1 christos else
2894 1.1 christos {
2895 1.1 christos if (h)
2896 1.1 christos addend += h->root.u.def.value;
2897 1.1 christos else
2898 1.1 christos addend += sym->st_value;
2899 1.1 christos if (osec)
2900 1.1 christos addend += osec->output_offset;
2901 1.1 christos if (osec && osec->output_section
2902 1.1 christos && ! bfd_is_abs_section (osec->output_section)
2903 1.1 christos && ! bfd_is_und_section (osec->output_section))
2904 1.1 christos dynindx = elf_section_data (osec->output_section)->dynindx;
2905 1.1 christos else
2906 1.1 christos dynindx = 0;
2907 1.1 christos }
2908 1.1.1.6 christos
2909 1.1 christos /* If we're linking an executable at a fixed address, we
2910 1.1 christos can omit the dynamic relocation as long as the symbol
2911 1.1 christos is defined in the current link unit (which is implied
2912 1.1 christos by its output section not being NULL). */
2913 1.1 christos if (bfd_link_pde (info)
2914 1.1.1.9 christos && (!h || BFINFDPIC_SYM_LOCAL (info, h)))
2915 1.1 christos {
2916 1.1 christos if (osec)
2917 1.1 christos addend += osec->output_section->vma;
2918 1.1 christos if (IS_FDPIC (input_bfd)
2919 1.1 christos && (bfd_section_flags (input_section->output_section)
2920 1.1 christos & (SEC_ALLOC | SEC_LOAD)) == (SEC_ALLOC | SEC_LOAD))
2921 1.1 christos {
2922 1.1 christos if (_bfinfdpic_osec_readonly_p (output_bfd,
2923 1.1 christos input_section
2924 1.1 christos ->output_section))
2925 1.1.1.10 christos {
2926 1.1 christos info->callbacks->warning
2927 1.1 christos (info,
2928 1.1 christos _("cannot emit fixups in read-only section"),
2929 1.1 christos name, input_bfd, input_section, rel->r_offset);
2930 1.1 christos return false;
2931 1.1 christos }
2932 1.1 christos if (!h || h->root.type != bfd_link_hash_undefweak)
2933 1.1 christos {
2934 1.1 christos if (offset != (bfd_vma)-1)
2935 1.1 christos {
2936 1.1 christos _bfinfdpic_add_rofixup (output_bfd,
2937 1.1 christos bfinfdpic_gotfixup_section
2938 1.1 christos (info),
2939 1.1 christos offset + input_section
2940 1.1 christos ->output_section->vma
2941 1.1 christos + input_section->output_offset,
2942 1.1 christos picrel);
2943 1.1 christos
2944 1.1 christos if (r_type == R_BFIN_FUNCDESC_VALUE)
2945 1.1 christos _bfinfdpic_add_rofixup
2946 1.1 christos (output_bfd,
2947 1.1 christos bfinfdpic_gotfixup_section (info),
2948 1.1 christos offset + input_section->output_section->vma
2949 1.1 christos + input_section->output_offset + 4, picrel);
2950 1.1 christos }
2951 1.1.1.9 christos }
2952 1.1 christos }
2953 1.1 christos }
2954 1.1 christos else
2955 1.1 christos {
2956 1.1 christos if ((bfd_section_flags (input_section->output_section)
2957 1.1 christos & (SEC_ALLOC | SEC_LOAD)) == (SEC_ALLOC | SEC_LOAD))
2958 1.1 christos {
2959 1.1 christos if (_bfinfdpic_osec_readonly_p (output_bfd,
2960 1.1 christos input_section
2961 1.1 christos ->output_section))
2962 1.1.1.10 christos {
2963 1.1 christos info->callbacks->warning
2964 1.1 christos (info,
2965 1.1 christos _("cannot emit dynamic relocations in read-only section"),
2966 1.1 christos name, input_bfd, input_section, rel->r_offset);
2967 1.1 christos return false;
2968 1.1 christos }
2969 1.1 christos
2970 1.1 christos if (offset != (bfd_vma)-1)
2971 1.1 christos _bfinfdpic_add_dyn_reloc (output_bfd,
2972 1.1 christos bfinfdpic_gotrel_section (info),
2973 1.1 christos offset
2974 1.1 christos + input_section->output_section->vma
2975 1.1 christos + input_section->output_offset,
2976 1.1 christos r_type, dynindx, addend, picrel);
2977 1.1 christos }
2978 1.1 christos else if (osec)
2979 1.1 christos addend += osec->output_section->vma;
2980 1.1 christos /* We want the addend in-place because dynamic
2981 1.1 christos relocations are REL. Setting relocation to it
2982 1.1 christos should arrange for it to be installed. */
2983 1.1 christos relocation = addend - rel->r_addend;
2984 1.1 christos }
2985 1.1 christos
2986 1.1.1.6 christos if (r_type == R_BFIN_FUNCDESC_VALUE)
2987 1.1 christos {
2988 1.1 christos /* If we've omitted the dynamic relocation, just emit
2989 1.1 christos the fixed addresses of the symbol and of the local
2990 1.1 christos GOT base offset. */
2991 1.1 christos if (bfd_link_pde (info)
2992 1.1 christos && (!h || BFINFDPIC_SYM_LOCAL (info, h)))
2993 1.1 christos bfd_put_32 (output_bfd,
2994 1.1 christos bfinfdpic_got_section (info)->output_section->vma
2995 1.1 christos + bfinfdpic_got_section (info)->output_offset
2996 1.1 christos + bfinfdpic_got_initial_offset (info),
2997 1.1 christos contents + rel->r_offset + 4);
2998 1.1 christos else
2999 1.1 christos /* A function descriptor used for lazy or local
3000 1.1 christos resolving is initialized such that its high word
3001 1.1 christos contains the output section index in which the
3002 1.1 christos PLT entries are located, and the low word
3003 1.1 christos contains the offset of the lazy PLT entry entry
3004 1.1 christos point into that section. */
3005 1.1 christos bfd_put_32 (output_bfd,
3006 1.1 christos h && ! BFINFDPIC_SYM_LOCAL (info, h)
3007 1.1 christos ? 0
3008 1.1 christos : _bfinfdpic_osec_to_segment (output_bfd,
3009 1.1 christos sec
3010 1.1 christos ->output_section),
3011 1.1 christos contents + rel->r_offset + 4);
3012 1.1 christos }
3013 1.1 christos }
3014 1.1 christos check_segment[0] = check_segment[1] = got_segment;
3015 1.1 christos break;
3016 1.1 christos
3017 1.1 christos default:
3018 1.1 christos check_segment[0] = isec_segment;
3019 1.1 christos check_segment[1] = sec
3020 1.1 christos ? _bfinfdpic_osec_to_segment (output_bfd, sec->output_section)
3021 1.1 christos : (unsigned)-1;
3022 1.1 christos break;
3023 1.1 christos }
3024 1.1 christos
3025 1.1 christos if (check_segment[0] != check_segment[1] && IS_FDPIC (output_bfd))
3026 1.1 christos {
3027 1.1 christos #if 1 /* If you take this out, remove the #error from fdpic-static-6.d
3028 1.1 christos in the ld testsuite. */
3029 1.1.1.9 christos /* This helps catch problems in GCC while we can't do more
3030 1.1.1.9 christos than static linking. The idea is to test whether the
3031 1.1.1.9 christos input file basename is crt0.o only once. */
3032 1.1.1.9 christos if (silence_segment_error == 1)
3033 1.1.1.9 christos silence_segment_error =
3034 1.1 christos (strlen (bfd_get_filename (input_bfd)) == 6
3035 1.1 christos && filename_cmp (bfd_get_filename (input_bfd), "crt0.o") == 0)
3036 1.1 christos || (strlen (bfd_get_filename (input_bfd)) > 6
3037 1.1 christos && filename_cmp (bfd_get_filename (input_bfd)
3038 1.1 christos + strlen (bfd_get_filename (input_bfd)) - 7,
3039 1.1 christos "/crt0.o") == 0)
3040 1.1 christos ? -1 : 0;
3041 1.1 christos #endif
3042 1.1 christos if (!silence_segment_error
3043 1.1 christos /* We don't want duplicate errors for undefined
3044 1.1.1.6 christos symbols. */
3045 1.1 christos && !(picrel && picrel->symndx == -1
3046 1.1 christos && picrel->d.h->root.type == bfd_link_hash_undefined))
3047 1.1 christos info->callbacks->warning
3048 1.1.1.6 christos (info,
3049 1.1.1.10 christos bfd_link_pic (info)
3050 1.1 christos ? _("relocations between different segments are not supported")
3051 1.1 christos : _("warning: relocation references a different segment"),
3052 1.1 christos name, input_bfd, input_section, rel->r_offset);
3053 1.1 christos if (!silence_segment_error && bfd_link_pic (info))
3054 1.1 christos return false;
3055 1.1 christos elf_elfheader (output_bfd)->e_flags |= EF_BFIN_PIC;
3056 1.1 christos }
3057 1.1 christos
3058 1.1 christos switch (r_type)
3059 1.1 christos {
3060 1.1 christos case R_BFIN_GOTOFFHI:
3061 1.1 christos /* We need the addend to be applied before we shift the
3062 1.1 christos value right. */
3063 1.1 christos relocation += rel->r_addend;
3064 1.1 christos /* Fall through. */
3065 1.1 christos case R_BFIN_GOTHI:
3066 1.1 christos case R_BFIN_FUNCDESC_GOTHI:
3067 1.1 christos case R_BFIN_FUNCDESC_GOTOFFHI:
3068 1.1 christos relocation >>= 16;
3069 1.1 christos /* Fall through. */
3070 1.1 christos
3071 1.1 christos case R_BFIN_GOTLO:
3072 1.1 christos case R_BFIN_FUNCDESC_GOTLO:
3073 1.1 christos case R_BFIN_GOTOFFLO:
3074 1.1 christos case R_BFIN_FUNCDESC_GOTOFFLO:
3075 1.1 christos relocation &= 0xffff;
3076 1.1 christos break;
3077 1.1 christos
3078 1.1 christos default:
3079 1.1 christos break;
3080 1.1 christos }
3081 1.1 christos
3082 1.1 christos switch (r_type)
3083 1.1 christos {
3084 1.1 christos case R_BFIN_PCREL24:
3085 1.1 christos case R_BFIN_PCREL24_JUMP_L:
3086 1.1 christos if (! IS_FDPIC (output_bfd) || ! picrel->plt)
3087 1.1 christos break;
3088 1.1 christos /* Fall through. */
3089 1.1 christos
3090 1.1 christos /* When referencing a GOT entry, a function descriptor or a
3091 1.1 christos PLT, we don't want the addend to apply to the reference,
3092 1.1 christos but rather to the referenced symbol. The actual entry
3093 1.1 christos will have already been created taking the addend into
3094 1.1 christos account, so cancel it out here. */
3095 1.1 christos case R_BFIN_GOT17M4:
3096 1.1 christos case R_BFIN_GOTHI:
3097 1.1 christos case R_BFIN_GOTLO:
3098 1.1 christos case R_BFIN_FUNCDESC_GOT17M4:
3099 1.1 christos case R_BFIN_FUNCDESC_GOTHI:
3100 1.1 christos case R_BFIN_FUNCDESC_GOTLO:
3101 1.1 christos case R_BFIN_FUNCDESC_GOTOFF17M4:
3102 1.1 christos case R_BFIN_FUNCDESC_GOTOFFHI:
3103 1.1 christos case R_BFIN_FUNCDESC_GOTOFFLO:
3104 1.1 christos /* Note that we only want GOTOFFHI, not GOTOFFLO or GOTOFF17M4
3105 1.1 christos here, since we do want to apply the addend to the others.
3106 1.1 christos Note that we've applied the addend to GOTOFFHI before we
3107 1.1 christos shifted it right. */
3108 1.1 christos case R_BFIN_GOTOFFHI:
3109 1.1 christos relocation -= rel->r_addend;
3110 1.1 christos break;
3111 1.1 christos
3112 1.1 christos default:
3113 1.1 christos break;
3114 1.1 christos }
3115 1.1 christos
3116 1.1 christos r = bfin_final_link_relocate (rel, howto, input_bfd, input_section,
3117 1.1 christos contents, rel->r_offset,
3118 1.1 christos relocation, rel->r_addend);
3119 1.1 christos
3120 1.1 christos if (r != bfd_reloc_ok)
3121 1.1 christos {
3122 1.1.1.6 christos const char * msg = (const char *) NULL;
3123 1.1 christos
3124 1.1 christos switch (r)
3125 1.1 christos {
3126 1.1 christos case bfd_reloc_overflow:
3127 1.1 christos (*info->callbacks->reloc_overflow)
3128 1.1.1.6 christos (info, (h ? &h->root : NULL), name, howto->name,
3129 1.1.1.10 christos (bfd_vma) 0, input_bfd, input_section, rel->r_offset);
3130 1.1 christos break;
3131 1.1 christos
3132 1.1 christos case bfd_reloc_undefined:
3133 1.1 christos (*info->callbacks->undefined_symbol)
3134 1.1 christos (info, name, input_bfd, input_section, rel->r_offset, true);
3135 1.1 christos break;
3136 1.1 christos
3137 1.1 christos case bfd_reloc_outofrange:
3138 1.1 christos msg = _("internal error: out of range error");
3139 1.1 christos break;
3140 1.1 christos
3141 1.1 christos case bfd_reloc_notsupported:
3142 1.1 christos msg = _("internal error: unsupported relocation error");
3143 1.1 christos break;
3144 1.1 christos
3145 1.1 christos case bfd_reloc_dangerous:
3146 1.1 christos msg = _("internal error: dangerous relocation");
3147 1.1 christos break;
3148 1.1 christos
3149 1.1 christos default:
3150 1.1.1.6 christos msg = _("internal error: unknown error");
3151 1.1.1.6 christos break;
3152 1.1 christos }
3153 1.1 christos
3154 1.1 christos if (msg)
3155 1.1.1.10 christos (*info->callbacks->warning) (info, msg, name, input_bfd,
3156 1.1 christos input_section, rel->r_offset);
3157 1.1 christos }
3158 1.1 christos }
3159 1.1 christos
3160 1.1.1.10 christos return true;
3161 1.1 christos }
3162 1.1 christos
3163 1.1 christos /* We need dynamic symbols for every section, since segments can
3164 1.1 christos relocate independently. */
3165 1.1 christos static bool
3166 1.1 christos _bfinfdpic_link_omit_section_dynsym (bfd *output_bfd ATTRIBUTE_UNUSED,
3167 1.1 christos struct bfd_link_info *info ATTRIBUTE_UNUSED,
3168 1.1 christos asection *p)
3169 1.1 christos {
3170 1.1 christos switch (elf_section_data (p)->this_hdr.sh_type)
3171 1.1 christos {
3172 1.1.1.10 christos case SHT_PROGBITS:
3173 1.1 christos case SHT_NOBITS:
3174 1.1 christos /* If sh_type is yet undecided, assume it could be
3175 1.1 christos SHT_PROGBITS/SHT_NOBITS. */
3176 1.1 christos case SHT_NULL:
3177 1.1.1.10 christos return false;
3178 1.1 christos
3179 1.1 christos /* There shouldn't be section relative relocations
3180 1.1 christos against any other section. */
3181 1.1 christos default:
3182 1.1 christos return true;
3183 1.1 christos }
3184 1.1 christos }
3185 1.1.1.10 christos
3186 1.1 christos /* Create a .got section, as well as its additional info field. This
3187 1.1 christos is almost entirely copied from
3188 1.1 christos elflink.c:_bfd_elf_create_got_section(). */
3189 1.1 christos
3190 1.1 christos static bool
3191 1.1 christos _bfin_create_got_section (bfd *abfd, struct bfd_link_info *info)
3192 1.1 christos {
3193 1.1 christos flagword flags, pltflags;
3194 1.1 christos asection *s;
3195 1.1.1.7 christos struct elf_link_hash_entry *h;
3196 1.1.1.2 christos const struct elf_backend_data *bed = get_elf_backend_data (abfd);
3197 1.1.1.10 christos int ptralign;
3198 1.1 christos
3199 1.1 christos /* This function may be called more than once. */
3200 1.1 christos s = elf_hash_table (info)->sgot;
3201 1.1 christos if (s != NULL)
3202 1.1 christos return true;
3203 1.1 christos
3204 1.1 christos /* Machine specific: although pointers are 32-bits wide, we want the
3205 1.1 christos GOT to be aligned to a 64-bit boundary, such that function
3206 1.1 christos descriptors in it can be accessed with 64-bit loads and
3207 1.1 christos stores. */
3208 1.1 christos ptralign = 3;
3209 1.1.1.2 christos
3210 1.1.1.7 christos flags = (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS | SEC_IN_MEMORY
3211 1.1 christos | SEC_LINKER_CREATED);
3212 1.1.1.9 christos pltflags = flags;
3213 1.1.1.10 christos
3214 1.1 christos s = bfd_make_section_anyway_with_flags (abfd, ".got", flags);
3215 1.1 christos elf_hash_table (info)->sgot = s;
3216 1.1 christos if (s == NULL
3217 1.1 christos || !bfd_set_section_alignment (s, ptralign))
3218 1.1 christos return false;
3219 1.1 christos
3220 1.1 christos if (bed->want_got_sym)
3221 1.1 christos {
3222 1.1 christos /* Define the symbol _GLOBAL_OFFSET_TABLE_ at the start of the .got
3223 1.1 christos (or .got.plt) section. We don't do this in the linker script
3224 1.1.1.10 christos because we don't want to define the symbol if we are not creating
3225 1.1 christos a global offset table. */
3226 1.1 christos h = _bfd_elf_define_linkage_sym (abfd, info, s, "__GLOBAL_OFFSET_TABLE_");
3227 1.1 christos elf_hash_table (info)->hgot = h;
3228 1.1 christos if (h == NULL)
3229 1.1.1.10 christos return false;
3230 1.1 christos
3231 1.1 christos /* Machine-specific: we want the symbol for executables as
3232 1.1 christos well. */
3233 1.1 christos if (! bfd_elf_link_record_dynamic_symbol (info, h))
3234 1.1 christos return false;
3235 1.1 christos }
3236 1.1 christos
3237 1.1 christos /* The first bit of the global offset table is the header. */
3238 1.1 christos s->size += bed->got_header_size;
3239 1.1 christos
3240 1.1 christos /* This is the machine-specific part. Create and initialize section
3241 1.1 christos data for the got. */
3242 1.1 christos if (IS_FDPIC (abfd))
3243 1.1 christos {
3244 1.1.1.10 christos bfinfdpic_relocs_info (info) = htab_try_create (1,
3245 1.1 christos bfinfdpic_relocs_info_hash,
3246 1.1.1.2 christos bfinfdpic_relocs_info_eq,
3247 1.1.1.2 christos (htab_del) NULL);
3248 1.1 christos if (! bfinfdpic_relocs_info (info))
3249 1.1.1.9 christos return false;
3250 1.1.1.10 christos
3251 1.1 christos s = bfd_make_section_anyway_with_flags (abfd, ".rel.got",
3252 1.1 christos (flags | SEC_READONLY));
3253 1.1 christos if (s == NULL
3254 1.1 christos || !bfd_set_section_alignment (s, 2))
3255 1.1.1.2 christos return false;
3256 1.1.1.2 christos
3257 1.1 christos bfinfdpic_gotrel_section (info) = s;
3258 1.1.1.9 christos
3259 1.1.1.10 christos /* Machine-specific. */
3260 1.1 christos s = bfd_make_section_anyway_with_flags (abfd, ".rofixup",
3261 1.1 christos (flags | SEC_READONLY));
3262 1.1 christos if (s == NULL
3263 1.1 christos || !bfd_set_section_alignment (s, 2))
3264 1.1 christos return false;
3265 1.1 christos
3266 1.1 christos bfinfdpic_gotfixup_section (info) = s;
3267 1.1 christos }
3268 1.1 christos
3269 1.1 christos pltflags |= SEC_CODE;
3270 1.1.1.2 christos if (bed->plt_not_loaded)
3271 1.1 christos pltflags &= ~ (SEC_CODE | SEC_LOAD | SEC_HAS_CONTENTS);
3272 1.1.1.9 christos if (bed->plt_readonly)
3273 1.1.1.10 christos pltflags |= SEC_READONLY;
3274 1.1 christos
3275 1.1 christos s = bfd_make_section_anyway_with_flags (abfd, ".plt", pltflags);
3276 1.1 christos if (s == NULL
3277 1.1 christos || !bfd_set_section_alignment (s, bed->plt_alignment))
3278 1.1 christos return false;
3279 1.1 christos /* Blackfin-specific: remember it. */
3280 1.1 christos bfinfdpic_plt_section (info) = s;
3281 1.1 christos
3282 1.1 christos if (bed->want_plt_sym)
3283 1.1 christos {
3284 1.1 christos /* Define the symbol _PROCEDURE_LINKAGE_TABLE_ at the start of the
3285 1.1.1.10 christos .plt section. */
3286 1.1.1.10 christos struct bfd_link_hash_entry *bh = NULL;
3287 1.1 christos
3288 1.1 christos if (! (_bfd_generic_link_add_one_symbol
3289 1.1 christos (info, abfd, "__PROCEDURE_LINKAGE_TABLE_", BSF_GLOBAL, s, 0, NULL,
3290 1.1 christos false, get_elf_backend_data (abfd)->collect, &bh)))
3291 1.1.1.6 christos return false;
3292 1.1 christos h = (struct elf_link_hash_entry *) bh;
3293 1.1.1.10 christos h->def_regular = 1;
3294 1.1 christos h->type = STT_OBJECT;
3295 1.1 christos
3296 1.1 christos if (! bfd_link_executable (info)
3297 1.1.1.2 christos && ! bfd_elf_link_record_dynamic_symbol (info, h))
3298 1.1.1.2 christos return false;
3299 1.1 christos }
3300 1.1.1.9 christos
3301 1.1.1.10 christos /* Blackfin-specific: we want rel relocations for the plt. */
3302 1.1 christos s = bfd_make_section_anyway_with_flags (abfd, ".rel.plt",
3303 1.1 christos flags | SEC_READONLY);
3304 1.1 christos if (s == NULL
3305 1.1.1.10 christos || !bfd_set_section_alignment (s, bed->s->log_file_align))
3306 1.1 christos return false;
3307 1.1 christos /* Blackfin-specific: remember it. */
3308 1.1 christos bfinfdpic_pltrel_section (info) = s;
3309 1.1 christos
3310 1.1 christos return true;
3311 1.1.1.10 christos }
3312 1.1 christos
3313 1.1 christos /* Make sure the got and plt sections exist, and that our pointers in
3314 1.1 christos the link hash table point to them. */
3315 1.1 christos
3316 1.1 christos static bool
3317 1.1 christos elf32_bfinfdpic_create_dynamic_sections (bfd *abfd, struct bfd_link_info *info)
3318 1.1 christos {
3319 1.1 christos /* This is mostly copied from
3320 1.1 christos elflink.c:_bfd_elf_create_dynamic_sections(). */
3321 1.1 christos flagword flags;
3322 1.1 christos asection *s;
3323 1.1 christos const struct elf_backend_data *bed = get_elf_backend_data (abfd);
3324 1.1 christos
3325 1.1 christos flags = (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS | SEC_IN_MEMORY
3326 1.1 christos | SEC_LINKER_CREATED);
3327 1.1 christos
3328 1.1.1.10 christos /* We need to create .plt, .rel[a].plt, .got, .got.plt, .dynbss, and
3329 1.1 christos .rel[a].bss sections. */
3330 1.1 christos
3331 1.1 christos /* Blackfin-specific: we want to create the GOT in the Blackfin way. */
3332 1.1 christos if (! _bfin_create_got_section (abfd, info))
3333 1.1 christos return false;
3334 1.1 christos
3335 1.1 christos /* Blackfin-specific: make sure we created everything we wanted. */
3336 1.1 christos BFD_ASSERT (bfinfdpic_got_section (info) && bfinfdpic_gotrel_section (info)
3337 1.1 christos /* && bfinfdpic_gotfixup_section (info) */
3338 1.1 christos && bfinfdpic_plt_section (info)
3339 1.1 christos && bfinfdpic_pltrel_section (info));
3340 1.1 christos
3341 1.1 christos if (bed->want_dynbss)
3342 1.1 christos {
3343 1.1 christos /* The .dynbss section is a place to put symbols which are defined
3344 1.1.1.2 christos by dynamic objects, are referenced by regular objects, and are
3345 1.1.1.2 christos not functions. We must allocate space for them in the process
3346 1.1 christos image and use a R_*_COPY reloc to tell the dynamic linker to
3347 1.1.1.10 christos initialize them at run time. The linker script puts the .dynbss
3348 1.1 christos section into the .bss section of the final image. */
3349 1.1 christos s = bfd_make_section_anyway_with_flags (abfd, ".dynbss",
3350 1.1.1.2 christos SEC_ALLOC | SEC_LINKER_CREATED);
3351 1.1.1.2 christos if (s == NULL)
3352 1.1.1.2 christos return false;
3353 1.1.1.2 christos
3354 1.1.1.2 christos /* The .rel[a].bss section holds copy relocs. This section is not
3355 1.1.1.2 christos normally needed. We need to create it here, though, so that the
3356 1.1.1.2 christos linker will map it to an output section. We can't just create it
3357 1.1.1.2 christos only if we need it, because we will not know whether we need it
3358 1.1.1.2 christos until we have seen all the input files, and the first time the
3359 1.1.1.2 christos main linker code calls BFD after examining all the input files
3360 1.1.1.6 christos (size_dynamic_sections) the input sections have already been
3361 1.1 christos mapped to the output sections. If the section turns out not to
3362 1.1.1.2 christos be needed, we can discard it later. We will never need this
3363 1.1.1.2 christos section when generating a shared object, since they do not use
3364 1.1.1.2 christos copy relocs. */
3365 1.1 christos if (! bfd_link_pic (info))
3366 1.1.1.9 christos {
3367 1.1.1.10 christos s = bfd_make_section_anyway_with_flags (abfd,
3368 1.1 christos ".rela.bss",
3369 1.1 christos flags | SEC_READONLY);
3370 1.1 christos if (s == NULL
3371 1.1.1.10 christos || !bfd_set_section_alignment (s, bed->s->log_file_align))
3372 1.1 christos return false;
3373 1.1 christos }
3374 1.1 christos }
3375 1.1 christos
3376 1.1 christos return true;
3377 1.1 christos }
3378 1.1 christos
3379 1.1 christos /* Compute the total GOT size required by each symbol in each range.
3380 1.1 christos Symbols may require up to 4 words in the GOT: an entry pointing to
3381 1.1 christos the symbol, an entry pointing to its function descriptor, and a
3382 1.1 christos private function descriptors taking two words. */
3383 1.1 christos
3384 1.1 christos static void
3385 1.1 christos _bfinfdpic_count_nontls_entries (struct bfinfdpic_relocs_info *entry,
3386 1.1 christos struct _bfinfdpic_dynamic_got_info *dinfo)
3387 1.1 christos {
3388 1.1 christos /* Allocate space for a GOT entry pointing to the symbol. */
3389 1.1 christos if (entry->got17m4)
3390 1.1 christos dinfo->got17m4 += 4;
3391 1.1 christos else if (entry->gothilo)
3392 1.1 christos dinfo->gothilo += 4;
3393 1.1 christos else
3394 1.1 christos entry->relocs32--;
3395 1.1 christos entry->relocs32++;
3396 1.1 christos
3397 1.1 christos /* Allocate space for a GOT entry pointing to the function
3398 1.1 christos descriptor. */
3399 1.1 christos if (entry->fdgot17m4)
3400 1.1 christos dinfo->got17m4 += 4;
3401 1.1 christos else if (entry->fdgothilo)
3402 1.1 christos dinfo->gothilo += 4;
3403 1.1 christos else
3404 1.1 christos entry->relocsfd--;
3405 1.1 christos entry->relocsfd++;
3406 1.1 christos
3407 1.1 christos /* Decide whether we need a PLT entry, a function descriptor in the
3408 1.1 christos GOT, and a lazy PLT entry for this symbol. */
3409 1.1 christos entry->plt = entry->call
3410 1.1 christos && entry->symndx == -1 && ! BFINFDPIC_SYM_LOCAL (dinfo->info, entry->d.h)
3411 1.1 christos && elf_hash_table (dinfo->info)->dynamic_sections_created;
3412 1.1 christos entry->privfd = entry->plt
3413 1.1 christos || entry->fdgoff17m4 || entry->fdgoffhilo
3414 1.1 christos || ((entry->fd || entry->fdgot17m4 || entry->fdgothilo)
3415 1.1 christos && (entry->symndx != -1
3416 1.1 christos || BFINFDPIC_FUNCDESC_LOCAL (dinfo->info, entry->d.h)));
3417 1.1 christos entry->lazyplt = entry->privfd
3418 1.1 christos && entry->symndx == -1 && ! BFINFDPIC_SYM_LOCAL (dinfo->info, entry->d.h)
3419 1.1 christos && ! (dinfo->info->flags & DF_BIND_NOW)
3420 1.1 christos && elf_hash_table (dinfo->info)->dynamic_sections_created;
3421 1.1 christos
3422 1.1 christos /* Allocate space for a function descriptor. */
3423 1.1 christos if (entry->fdgoff17m4)
3424 1.1 christos dinfo->fd17m4 += 8;
3425 1.1 christos else if (entry->privfd && entry->plt)
3426 1.1 christos dinfo->fdplt += 8;
3427 1.1 christos else if (entry->privfd)
3428 1.1 christos dinfo->fdhilo += 8;
3429 1.1 christos else
3430 1.1 christos entry->relocsfdv--;
3431 1.1 christos entry->relocsfdv++;
3432 1.1 christos
3433 1.1 christos if (entry->lazyplt)
3434 1.1 christos dinfo->lzplt += LZPLT_NORMAL_SIZE;
3435 1.1 christos }
3436 1.1 christos
3437 1.1 christos /* Compute the number of dynamic relocations and fixups that a symbol
3438 1.1 christos requires, and add (or subtract) from the grand and per-symbol
3439 1.1.1.10 christos totals. */
3440 1.1 christos
3441 1.1 christos static void
3442 1.1 christos _bfinfdpic_count_relocs_fixups (struct bfinfdpic_relocs_info *entry,
3443 1.1.1.6 christos struct _bfinfdpic_dynamic_got_info *dinfo,
3444 1.1 christos bool subtract)
3445 1.1 christos {
3446 1.1 christos bfd_vma relocs = 0, fixups = 0;
3447 1.1 christos
3448 1.1 christos if (!bfd_link_pde (dinfo->info))
3449 1.1 christos relocs = entry->relocs32 + entry->relocsfd + entry->relocsfdv;
3450 1.1 christos else
3451 1.1 christos {
3452 1.1 christos if (entry->symndx != -1 || BFINFDPIC_SYM_LOCAL (dinfo->info, entry->d.h))
3453 1.1 christos {
3454 1.1 christos if (entry->symndx != -1
3455 1.1 christos || entry->d.h->root.type != bfd_link_hash_undefweak)
3456 1.1 christos fixups += entry->relocs32 + 2 * entry->relocsfdv;
3457 1.1 christos }
3458 1.1 christos else
3459 1.1 christos relocs += entry->relocs32 + entry->relocsfdv;
3460 1.1 christos
3461 1.1 christos if (entry->symndx != -1
3462 1.1 christos || BFINFDPIC_FUNCDESC_LOCAL (dinfo->info, entry->d.h))
3463 1.1 christos {
3464 1.1 christos if (entry->symndx != -1
3465 1.1 christos || entry->d.h->root.type != bfd_link_hash_undefweak)
3466 1.1 christos fixups += entry->relocsfd;
3467 1.1 christos }
3468 1.1 christos else
3469 1.1 christos relocs += entry->relocsfd;
3470 1.1 christos }
3471 1.1 christos
3472 1.1 christos if (subtract)
3473 1.1 christos {
3474 1.1 christos relocs = - relocs;
3475 1.1 christos fixups = - fixups;
3476 1.1 christos }
3477 1.1 christos
3478 1.1 christos entry->dynrelocs += relocs;
3479 1.1 christos entry->fixups += fixups;
3480 1.1 christos dinfo->relocs += relocs;
3481 1.1 christos dinfo->fixups += fixups;
3482 1.1 christos }
3483 1.1 christos
3484 1.1 christos /* Compute the total GOT and PLT size required by each symbol in each range. *
3485 1.1 christos Symbols may require up to 4 words in the GOT: an entry pointing to
3486 1.1 christos the symbol, an entry pointing to its function descriptor, and a
3487 1.1 christos private function descriptors taking two words. */
3488 1.1 christos
3489 1.1 christos static int
3490 1.1 christos _bfinfdpic_count_got_plt_entries (void **entryp, void *dinfo_)
3491 1.1 christos {
3492 1.1.1.10 christos struct bfinfdpic_relocs_info *entry = *entryp;
3493 1.1 christos struct _bfinfdpic_dynamic_got_info *dinfo = dinfo_;
3494 1.1 christos
3495 1.1 christos _bfinfdpic_count_nontls_entries (entry, dinfo);
3496 1.1 christos
3497 1.1 christos _bfinfdpic_count_relocs_fixups (entry, dinfo, false);
3498 1.1 christos
3499 1.1 christos return 1;
3500 1.1 christos }
3501 1.1 christos
3502 1.1 christos /* This structure is used to assign offsets to got entries, function
3503 1.1 christos descriptors, plt entries and lazy plt entries. */
3504 1.1 christos
3505 1.1 christos struct _bfinfdpic_dynamic_got_plt_info
3506 1.1 christos {
3507 1.1 christos /* Summary information collected with _bfinfdpic_count_got_plt_entries. */
3508 1.1 christos struct _bfinfdpic_dynamic_got_info g;
3509 1.1 christos
3510 1.1 christos /* For each addressable range, we record a MAX (positive) and MIN
3511 1.1 christos (negative) value. CUR is used to assign got entries, and it's
3512 1.1 christos incremented from an initial positive value to MAX, then from MIN
3513 1.1 christos to FDCUR (unless FDCUR wraps around first). FDCUR is used to
3514 1.1 christos assign function descriptors, and it's decreased from an initial
3515 1.1 christos non-positive value to MIN, then from MAX down to CUR (unless CUR
3516 1.1 christos wraps around first). All of MIN, MAX, CUR and FDCUR always point
3517 1.1 christos to even words. ODD, if non-zero, indicates an odd word to be
3518 1.1 christos used for the next got entry, otherwise CUR is used and
3519 1.1 christos incremented by a pair of words, wrapping around when it reaches
3520 1.1 christos MAX. FDCUR is decremented (and wrapped) before the next function
3521 1.1 christos descriptor is chosen. FDPLT indicates the number of remaining
3522 1.1 christos slots that can be used for function descriptors used only by PLT
3523 1.1 christos entries. */
3524 1.1 christos struct _bfinfdpic_dynamic_got_alloc_data
3525 1.1 christos {
3526 1.1 christos bfd_signed_vma max, cur, odd, fdcur, min;
3527 1.1 christos bfd_vma fdplt;
3528 1.1 christos } got17m4, gothilo;
3529 1.1 christos };
3530 1.1 christos
3531 1.1 christos /* Determine the positive and negative ranges to be used by each
3532 1.1 christos offset range in the GOT. FDCUR and CUR, that must be aligned to a
3533 1.1 christos double-word boundary, are the minimum (negative) and maximum
3534 1.1 christos (positive) GOT offsets already used by previous ranges, except for
3535 1.1 christos an ODD entry that may have been left behind. GOT and FD indicate
3536 1.1 christos the size of GOT entries and function descriptors that must be
3537 1.1 christos placed within the range from -WRAP to WRAP. If there's room left,
3538 1.1 christos up to FDPLT bytes should be reserved for additional function
3539 1.1 christos descriptors. */
3540 1.1 christos
3541 1.1 christos inline static bfd_signed_vma
3542 1.1 christos _bfinfdpic_compute_got_alloc_data (struct _bfinfdpic_dynamic_got_alloc_data *gad,
3543 1.1 christos bfd_signed_vma fdcur,
3544 1.1 christos bfd_signed_vma odd,
3545 1.1 christos bfd_signed_vma cur,
3546 1.1 christos bfd_vma got,
3547 1.1 christos bfd_vma fd,
3548 1.1 christos bfd_vma fdplt,
3549 1.1 christos bfd_vma wrap)
3550 1.1 christos {
3551 1.1 christos bfd_signed_vma wrapmin = -wrap;
3552 1.1 christos
3553 1.1 christos /* Start at the given initial points. */
3554 1.1 christos gad->fdcur = fdcur;
3555 1.1 christos gad->cur = cur;
3556 1.1 christos
3557 1.1 christos /* If we had an incoming odd word and we have any got entries that
3558 1.1 christos are going to use it, consume it, otherwise leave gad->odd at
3559 1.1 christos zero. We might force gad->odd to zero and return the incoming
3560 1.1 christos odd such that it is used by the next range, but then GOT entries
3561 1.1 christos might appear to be out of order and we wouldn't be able to
3562 1.1 christos shorten the GOT by one word if it turns out to end with an
3563 1.1 christos unpaired GOT entry. */
3564 1.1 christos if (odd && got)
3565 1.1 christos {
3566 1.1 christos gad->odd = odd;
3567 1.1 christos got -= 4;
3568 1.1 christos odd = 0;
3569 1.1 christos }
3570 1.1 christos else
3571 1.1 christos gad->odd = 0;
3572 1.1 christos
3573 1.1 christos /* If we're left with an unpaired GOT entry, compute its location
3574 1.1 christos such that we can return it. Otherwise, if got doesn't require an
3575 1.1 christos odd number of words here, either odd was already zero in the
3576 1.1 christos block above, or it was set to zero because got was non-zero, or
3577 1.1 christos got was already zero. In the latter case, we want the value of
3578 1.1 christos odd to carry over to the return statement, so we don't want to
3579 1.1 christos reset odd unless the condition below is true. */
3580 1.1 christos if (got & 4)
3581 1.1 christos {
3582 1.1 christos odd = cur + got;
3583 1.1 christos got += 4;
3584 1.1 christos }
3585 1.1 christos
3586 1.1 christos /* Compute the tentative boundaries of this range. */
3587 1.1 christos gad->max = cur + got;
3588 1.1 christos gad->min = fdcur - fd;
3589 1.1 christos gad->fdplt = 0;
3590 1.1 christos
3591 1.1 christos /* If function descriptors took too much space, wrap some of them
3592 1.1 christos around. */
3593 1.1 christos if (gad->min < wrapmin)
3594 1.1 christos {
3595 1.1 christos gad->max += wrapmin - gad->min;
3596 1.1 christos gad->min = wrapmin;
3597 1.1 christos }
3598 1.1 christos /* If there is space left and we have function descriptors
3599 1.1 christos referenced in PLT entries that could take advantage of shorter
3600 1.1 christos offsets, place them here. */
3601 1.1 christos else if (fdplt && gad->min > wrapmin)
3602 1.1 christos {
3603 1.1 christos bfd_vma fds;
3604 1.1 christos if ((bfd_vma) (gad->min - wrapmin) < fdplt)
3605 1.1 christos fds = gad->min - wrapmin;
3606 1.1 christos else
3607 1.1 christos fds = fdplt;
3608 1.1 christos
3609 1.1 christos fdplt -= fds;
3610 1.1 christos gad->min -= fds;
3611 1.1 christos gad->fdplt += fds;
3612 1.1 christos }
3613 1.1 christos
3614 1.1 christos /* If GOT entries took too much space, wrap some of them around.
3615 1.1 christos This may well cause gad->min to become lower than wrapmin. This
3616 1.1 christos will cause a relocation overflow later on, so we don't have to
3617 1.1 christos report it here . */
3618 1.1 christos if ((bfd_vma) gad->max > wrap)
3619 1.1 christos {
3620 1.1 christos gad->min -= gad->max - wrap;
3621 1.1 christos gad->max = wrap;
3622 1.1 christos }
3623 1.1 christos /* If there is more space left, try to place some more function
3624 1.1 christos descriptors for PLT entries. */
3625 1.1 christos else if (fdplt && (bfd_vma) gad->max < wrap)
3626 1.1 christos {
3627 1.1 christos bfd_vma fds;
3628 1.1 christos if ((bfd_vma) (wrap - gad->max) < fdplt)
3629 1.1 christos fds = wrap - gad->max;
3630 1.1 christos else
3631 1.1 christos fds = fdplt;
3632 1.1 christos
3633 1.1 christos fdplt -= fds;
3634 1.1 christos gad->max += fds;
3635 1.1 christos gad->fdplt += fds;
3636 1.1 christos }
3637 1.1 christos
3638 1.1 christos /* If odd was initially computed as an offset past the wrap point,
3639 1.1 christos wrap it around. */
3640 1.1 christos if (odd > gad->max)
3641 1.1 christos odd = gad->min + odd - gad->max;
3642 1.1 christos
3643 1.1 christos /* _bfinfdpic_get_got_entry() below will always wrap gad->cur if needed
3644 1.1 christos before returning, so do it here too. This guarantees that,
3645 1.1 christos should cur and fdcur meet at the wrap point, they'll both be
3646 1.1 christos equal to min. */
3647 1.1 christos if (gad->cur == gad->max)
3648 1.1 christos gad->cur = gad->min;
3649 1.1 christos
3650 1.1 christos return odd;
3651 1.1 christos }
3652 1.1 christos
3653 1.1 christos /* Compute the location of the next GOT entry, given the allocation
3654 1.1 christos data for a range. */
3655 1.1 christos
3656 1.1 christos inline static bfd_signed_vma
3657 1.1 christos _bfinfdpic_get_got_entry (struct _bfinfdpic_dynamic_got_alloc_data *gad)
3658 1.1 christos {
3659 1.1 christos bfd_signed_vma ret;
3660 1.1 christos
3661 1.1 christos if (gad->odd)
3662 1.1 christos {
3663 1.1 christos /* If there was an odd word left behind, use it. */
3664 1.1 christos ret = gad->odd;
3665 1.1 christos gad->odd = 0;
3666 1.1 christos }
3667 1.1 christos else
3668 1.1 christos {
3669 1.1 christos /* Otherwise, use the word pointed to by cur, reserve the next
3670 1.1 christos as an odd word, and skip to the next pair of words, possibly
3671 1.1 christos wrapping around. */
3672 1.1 christos ret = gad->cur;
3673 1.1 christos gad->odd = gad->cur + 4;
3674 1.1 christos gad->cur += 8;
3675 1.1 christos if (gad->cur == gad->max)
3676 1.1 christos gad->cur = gad->min;
3677 1.1 christos }
3678 1.1 christos
3679 1.1 christos return ret;
3680 1.1 christos }
3681 1.1 christos
3682 1.1 christos /* Compute the location of the next function descriptor entry in the
3683 1.1 christos GOT, given the allocation data for a range. */
3684 1.1 christos
3685 1.1 christos inline static bfd_signed_vma
3686 1.1 christos _bfinfdpic_get_fd_entry (struct _bfinfdpic_dynamic_got_alloc_data *gad)
3687 1.1 christos {
3688 1.1 christos /* If we're at the bottom, wrap around, and only then allocate the
3689 1.1 christos next pair of words. */
3690 1.1 christos if (gad->fdcur == gad->min)
3691 1.1 christos gad->fdcur = gad->max;
3692 1.1 christos return gad->fdcur -= 8;
3693 1.1 christos }
3694 1.1 christos
3695 1.1 christos /* Assign GOT offsets for every GOT entry and function descriptor.
3696 1.1 christos Doing everything in a single pass is tricky. */
3697 1.1 christos
3698 1.1 christos static int
3699 1.1 christos _bfinfdpic_assign_got_entries (void **entryp, void *info_)
3700 1.1 christos {
3701 1.1 christos struct bfinfdpic_relocs_info *entry = *entryp;
3702 1.1 christos struct _bfinfdpic_dynamic_got_plt_info *dinfo = info_;
3703 1.1 christos
3704 1.1 christos if (entry->got17m4)
3705 1.1 christos entry->got_entry = _bfinfdpic_get_got_entry (&dinfo->got17m4);
3706 1.1 christos else if (entry->gothilo)
3707 1.1 christos entry->got_entry = _bfinfdpic_get_got_entry (&dinfo->gothilo);
3708 1.1 christos
3709 1.1 christos if (entry->fdgot17m4)
3710 1.1 christos entry->fdgot_entry = _bfinfdpic_get_got_entry (&dinfo->got17m4);
3711 1.1 christos else if (entry->fdgothilo)
3712 1.1 christos entry->fdgot_entry = _bfinfdpic_get_got_entry (&dinfo->gothilo);
3713 1.1 christos
3714 1.1 christos if (entry->fdgoff17m4)
3715 1.1 christos entry->fd_entry = _bfinfdpic_get_fd_entry (&dinfo->got17m4);
3716 1.1 christos else if (entry->plt && dinfo->got17m4.fdplt)
3717 1.1 christos {
3718 1.1 christos dinfo->got17m4.fdplt -= 8;
3719 1.1 christos entry->fd_entry = _bfinfdpic_get_fd_entry (&dinfo->got17m4);
3720 1.1 christos }
3721 1.1 christos else if (entry->plt)
3722 1.1 christos {
3723 1.1 christos dinfo->gothilo.fdplt -= 8;
3724 1.1 christos entry->fd_entry = _bfinfdpic_get_fd_entry (&dinfo->gothilo);
3725 1.1 christos }
3726 1.1 christos else if (entry->privfd)
3727 1.1 christos entry->fd_entry = _bfinfdpic_get_fd_entry (&dinfo->gothilo);
3728 1.1 christos
3729 1.1 christos return 1;
3730 1.1 christos }
3731 1.1 christos
3732 1.1 christos /* Assign GOT offsets to private function descriptors used by PLT
3733 1.1 christos entries (or referenced by 32-bit offsets), as well as PLT entries
3734 1.1 christos and lazy PLT entries. */
3735 1.1 christos
3736 1.1 christos static int
3737 1.1 christos _bfinfdpic_assign_plt_entries (void **entryp, void *info_)
3738 1.1 christos {
3739 1.1 christos struct bfinfdpic_relocs_info *entry = *entryp;
3740 1.1 christos struct _bfinfdpic_dynamic_got_plt_info *dinfo = info_;
3741 1.1 christos
3742 1.1 christos /* If this symbol requires a local function descriptor, allocate
3743 1.1 christos one. */
3744 1.1 christos if (entry->privfd && entry->fd_entry == 0)
3745 1.1 christos {
3746 1.1 christos if (dinfo->got17m4.fdplt)
3747 1.1 christos {
3748 1.1 christos entry->fd_entry = _bfinfdpic_get_fd_entry (&dinfo->got17m4);
3749 1.1 christos dinfo->got17m4.fdplt -= 8;
3750 1.1 christos }
3751 1.1 christos else
3752 1.1 christos {
3753 1.1 christos BFD_ASSERT (dinfo->gothilo.fdplt);
3754 1.1 christos entry->fd_entry = _bfinfdpic_get_fd_entry (&dinfo->gothilo);
3755 1.1 christos dinfo->gothilo.fdplt -= 8;
3756 1.1 christos }
3757 1.1 christos }
3758 1.1 christos
3759 1.1 christos if (entry->plt)
3760 1.1 christos {
3761 1.1 christos int size;
3762 1.1 christos
3763 1.1 christos /* We use the section's raw size to mark the location of the
3764 1.1 christos next PLT entry. */
3765 1.1 christos entry->plt_entry = bfinfdpic_plt_section (dinfo->g.info)->size;
3766 1.1 christos
3767 1.1 christos /* Figure out the length of this PLT entry based on the
3768 1.1 christos addressing mode we need to reach the function descriptor. */
3769 1.1 christos BFD_ASSERT (entry->fd_entry);
3770 1.1 christos if (entry->fd_entry >= -(1 << (18 - 1))
3771 1.1 christos && entry->fd_entry + 4 < (1 << (18 - 1)))
3772 1.1 christos size = 10;
3773 1.1 christos else
3774 1.1 christos size = 16;
3775 1.1 christos
3776 1.1 christos bfinfdpic_plt_section (dinfo->g.info)->size += size;
3777 1.1 christos }
3778 1.1 christos
3779 1.1 christos if (entry->lazyplt)
3780 1.1 christos {
3781 1.1 christos entry->lzplt_entry = dinfo->g.lzplt;
3782 1.1 christos dinfo->g.lzplt += LZPLT_NORMAL_SIZE;
3783 1.1 christos /* If this entry is the one that gets the resolver stub, account
3784 1.1 christos for the additional instruction. */
3785 1.1 christos if (entry->lzplt_entry % BFINFDPIC_LZPLT_BLOCK_SIZE
3786 1.1 christos == BFINFDPIC_LZPLT_RESOLV_LOC)
3787 1.1 christos dinfo->g.lzplt += LZPLT_RESOLVER_EXTRA;
3788 1.1 christos }
3789 1.1 christos
3790 1.1 christos return 1;
3791 1.1 christos }
3792 1.1 christos
3793 1.1 christos /* Cancel out any effects of calling _bfinfdpic_assign_got_entries and
3794 1.1 christos _bfinfdpic_assign_plt_entries. */
3795 1.1 christos
3796 1.1 christos static int
3797 1.1 christos _bfinfdpic_reset_got_plt_entries (void **entryp, void *ignore ATTRIBUTE_UNUSED)
3798 1.1 christos {
3799 1.1 christos struct bfinfdpic_relocs_info *entry = *entryp;
3800 1.1 christos
3801 1.1 christos entry->got_entry = 0;
3802 1.1 christos entry->fdgot_entry = 0;
3803 1.1 christos entry->fd_entry = 0;
3804 1.1 christos entry->plt_entry = (bfd_vma)-1;
3805 1.1 christos entry->lzplt_entry = (bfd_vma)-1;
3806 1.1 christos
3807 1.1 christos return 1;
3808 1.1 christos }
3809 1.1 christos
3810 1.1 christos /* Follow indirect and warning hash entries so that each got entry
3811 1.1 christos points to the final symbol definition. P must point to a pointer
3812 1.1 christos to the hash table we're traversing. Since this traversal may
3813 1.1 christos modify the hash table, we set this pointer to NULL to indicate
3814 1.1 christos we've made a potentially-destructive change to the hash table, so
3815 1.1 christos the traversal must be restarted. */
3816 1.1 christos static int
3817 1.1 christos _bfinfdpic_resolve_final_relocs_info (void **entryp, void *p)
3818 1.1 christos {
3819 1.1 christos struct bfinfdpic_relocs_info *entry = *entryp;
3820 1.1 christos htab_t *htab = p;
3821 1.1 christos
3822 1.1 christos if (entry->symndx == -1)
3823 1.1 christos {
3824 1.1 christos struct elf_link_hash_entry *h = entry->d.h;
3825 1.1 christos struct bfinfdpic_relocs_info *oentry;
3826 1.1 christos
3827 1.1 christos while (h->root.type == bfd_link_hash_indirect
3828 1.1 christos || h->root.type == bfd_link_hash_warning)
3829 1.1 christos h = (struct elf_link_hash_entry *)h->root.u.i.link;
3830 1.1 christos
3831 1.1 christos if (entry->d.h == h)
3832 1.1 christos return 1;
3833 1.1 christos
3834 1.1 christos oentry = bfinfdpic_relocs_info_for_global (*htab, 0, h, entry->addend,
3835 1.1 christos NO_INSERT);
3836 1.1 christos
3837 1.1 christos if (oentry)
3838 1.1 christos {
3839 1.1 christos /* Merge the two entries. */
3840 1.1 christos bfinfdpic_pic_merge_early_relocs_info (oentry, entry);
3841 1.1 christos htab_clear_slot (*htab, entryp);
3842 1.1 christos return 1;
3843 1.1 christos }
3844 1.1 christos
3845 1.1 christos entry->d.h = h;
3846 1.1 christos
3847 1.1 christos /* If we can't find this entry with the new bfd hash, re-insert
3848 1.1 christos it, and get the traversal restarted. */
3849 1.1 christos if (! htab_find (*htab, entry))
3850 1.1 christos {
3851 1.1 christos htab_clear_slot (*htab, entryp);
3852 1.1 christos entryp = htab_find_slot (*htab, entry, INSERT);
3853 1.1 christos if (! *entryp)
3854 1.1 christos *entryp = entry;
3855 1.1 christos /* Abort the traversal, since the whole table may have
3856 1.1 christos moved, and leave it up to the parent to restart the
3857 1.1 christos process. */
3858 1.1 christos *(htab_t *)p = NULL;
3859 1.1 christos return 0;
3860 1.1 christos }
3861 1.1 christos }
3862 1.1 christos
3863 1.1 christos return 1;
3864 1.1 christos }
3865 1.1.1.10 christos
3866 1.1 christos /* Compute the total size of the GOT, the PLT, the dynamic relocations
3867 1.1 christos section and the rofixup section. Assign locations for GOT and PLT
3868 1.1 christos entries. */
3869 1.1 christos
3870 1.1 christos static bool
3871 1.1 christos _bfinfdpic_size_got_plt (bfd *output_bfd,
3872 1.1 christos struct _bfinfdpic_dynamic_got_plt_info *gpinfop)
3873 1.1 christos {
3874 1.1 christos bfd_signed_vma odd;
3875 1.1 christos bfd_vma limit;
3876 1.1 christos struct bfd_link_info *info = gpinfop->g.info;
3877 1.1 christos bfd *dynobj = elf_hash_table (info)->dynobj;
3878 1.1 christos
3879 1.1 christos memcpy (bfinfdpic_dynamic_got_plt_info (info), &gpinfop->g,
3880 1.1 christos sizeof (gpinfop->g));
3881 1.1 christos
3882 1.1 christos odd = 12;
3883 1.1 christos /* Compute the total size taken by entries in the 18-bit range,
3884 1.1 christos to tell how many PLT function descriptors we can bring into it
3885 1.1 christos without causing it to overflow. */
3886 1.1 christos limit = odd + gpinfop->g.got17m4 + gpinfop->g.fd17m4;
3887 1.1 christos if (limit < (bfd_vma)1 << 18)
3888 1.1 christos limit = ((bfd_vma)1 << 18) - limit;
3889 1.1 christos else
3890 1.1 christos limit = 0;
3891 1.1 christos if (gpinfop->g.fdplt < limit)
3892 1.1 christos limit = gpinfop->g.fdplt;
3893 1.1 christos
3894 1.1 christos /* Determine the ranges of GOT offsets that we can use for each
3895 1.1 christos range of addressing modes. */
3896 1.1 christos odd = _bfinfdpic_compute_got_alloc_data (&gpinfop->got17m4,
3897 1.1 christos 0,
3898 1.1 christos odd,
3899 1.1 christos 16,
3900 1.1 christos gpinfop->g.got17m4,
3901 1.1 christos gpinfop->g.fd17m4,
3902 1.1 christos limit,
3903 1.1 christos (bfd_vma)1 << (18-1));
3904 1.1 christos odd = _bfinfdpic_compute_got_alloc_data (&gpinfop->gothilo,
3905 1.1 christos gpinfop->got17m4.min,
3906 1.1 christos odd,
3907 1.1 christos gpinfop->got17m4.max,
3908 1.1 christos gpinfop->g.gothilo,
3909 1.1 christos gpinfop->g.fdhilo,
3910 1.1 christos gpinfop->g.fdplt - gpinfop->got17m4.fdplt,
3911 1.1 christos (bfd_vma)1 << (32-1));
3912 1.1 christos
3913 1.1 christos /* Now assign (most) GOT offsets. */
3914 1.1 christos htab_traverse (bfinfdpic_relocs_info (info), _bfinfdpic_assign_got_entries,
3915 1.1 christos gpinfop);
3916 1.1 christos
3917 1.1 christos bfinfdpic_got_section (info)->size = gpinfop->gothilo.max
3918 1.1 christos - gpinfop->gothilo.min
3919 1.1 christos /* If an odd word is the last word of the GOT, we don't need this
3920 1.1 christos word to be part of the GOT. */
3921 1.1 christos - (odd + 4 == gpinfop->gothilo.max ? 4 : 0);
3922 1.1 christos if (bfinfdpic_got_section (info)->size == 0)
3923 1.1 christos bfinfdpic_got_section (info)->flags |= SEC_EXCLUDE;
3924 1.1 christos else if (bfinfdpic_got_section (info)->size == 12
3925 1.1 christos && ! elf_hash_table (info)->dynamic_sections_created)
3926 1.1 christos {
3927 1.1 christos bfinfdpic_got_section (info)->flags |= SEC_EXCLUDE;
3928 1.1 christos bfinfdpic_got_section (info)->size = 0;
3929 1.1 christos }
3930 1.1 christos else
3931 1.1.1.10 christos {
3932 1.1 christos bfinfdpic_got_section (info)->contents =
3933 1.1 christos (bfd_byte *) bfd_zalloc (dynobj,
3934 1.1 christos bfinfdpic_got_section (info)->size);
3935 1.1 christos if (bfinfdpic_got_section (info)->contents == NULL)
3936 1.1 christos return false;
3937 1.1 christos }
3938 1.1 christos
3939 1.1 christos if (elf_hash_table (info)->dynamic_sections_created)
3940 1.1 christos /* Subtract the number of lzplt entries, since those will generate
3941 1.1 christos relocations in the pltrel section. */
3942 1.1 christos bfinfdpic_gotrel_section (info)->size =
3943 1.1 christos (gpinfop->g.relocs - gpinfop->g.lzplt / LZPLT_NORMAL_SIZE)
3944 1.1 christos * get_elf_backend_data (output_bfd)->s->sizeof_rel;
3945 1.1 christos else
3946 1.1 christos BFD_ASSERT (gpinfop->g.relocs == 0);
3947 1.1 christos if (bfinfdpic_gotrel_section (info)->size == 0)
3948 1.1 christos bfinfdpic_gotrel_section (info)->flags |= SEC_EXCLUDE;
3949 1.1 christos else
3950 1.1.1.10 christos {
3951 1.1 christos bfinfdpic_gotrel_section (info)->contents =
3952 1.1 christos (bfd_byte *) bfd_zalloc (dynobj,
3953 1.1 christos bfinfdpic_gotrel_section (info)->size);
3954 1.1 christos if (bfinfdpic_gotrel_section (info)->contents == NULL)
3955 1.1 christos return false;
3956 1.1 christos }
3957 1.1 christos
3958 1.1 christos bfinfdpic_gotfixup_section (info)->size = (gpinfop->g.fixups + 1) * 4;
3959 1.1 christos if (bfinfdpic_gotfixup_section (info)->size == 0)
3960 1.1 christos bfinfdpic_gotfixup_section (info)->flags |= SEC_EXCLUDE;
3961 1.1 christos else
3962 1.1.1.10 christos {
3963 1.1 christos bfinfdpic_gotfixup_section (info)->contents =
3964 1.1 christos (bfd_byte *) bfd_zalloc (dynobj,
3965 1.1 christos bfinfdpic_gotfixup_section (info)->size);
3966 1.1 christos if (bfinfdpic_gotfixup_section (info)->contents == NULL)
3967 1.1 christos return false;
3968 1.1 christos }
3969 1.1 christos
3970 1.1 christos if (elf_hash_table (info)->dynamic_sections_created)
3971 1.1 christos bfinfdpic_pltrel_section (info)->size =
3972 1.1 christos gpinfop->g.lzplt / LZPLT_NORMAL_SIZE * get_elf_backend_data (output_bfd)->s->sizeof_rel;
3973 1.1 christos if (bfinfdpic_pltrel_section (info)->size == 0)
3974 1.1 christos bfinfdpic_pltrel_section (info)->flags |= SEC_EXCLUDE;
3975 1.1 christos else
3976 1.1.1.10 christos {
3977 1.1 christos bfinfdpic_pltrel_section (info)->contents =
3978 1.1 christos (bfd_byte *) bfd_zalloc (dynobj,
3979 1.1 christos bfinfdpic_pltrel_section (info)->size);
3980 1.1 christos if (bfinfdpic_pltrel_section (info)->contents == NULL)
3981 1.1 christos return false;
3982 1.1 christos }
3983 1.1 christos
3984 1.1 christos /* Add 4 bytes for every block of at most 65535 lazy PLT entries,
3985 1.1 christos such that there's room for the additional instruction needed to
3986 1.1 christos call the resolver. Since _bfinfdpic_assign_got_entries didn't
3987 1.1 christos account for them, our block size is 4 bytes smaller than the real
3988 1.1 christos block size. */
3989 1.1 christos if (elf_hash_table (info)->dynamic_sections_created)
3990 1.1 christos {
3991 1.1 christos bfinfdpic_plt_section (info)->size = gpinfop->g.lzplt
3992 1.1 christos + ((gpinfop->g.lzplt + (BFINFDPIC_LZPLT_BLOCK_SIZE - 4) - LZPLT_NORMAL_SIZE)
3993 1.1 christos / (BFINFDPIC_LZPLT_BLOCK_SIZE - 4) * LZPLT_RESOLVER_EXTRA);
3994 1.1 christos }
3995 1.1 christos
3996 1.1 christos /* Reset it, such that _bfinfdpic_assign_plt_entries() can use it to
3997 1.1 christos actually assign lazy PLT entries addresses. */
3998 1.1 christos gpinfop->g.lzplt = 0;
3999 1.1 christos
4000 1.1 christos /* Save information that we're going to need to generate GOT and PLT
4001 1.1 christos entries. */
4002 1.1 christos bfinfdpic_got_initial_offset (info) = -gpinfop->gothilo.min;
4003 1.1 christos
4004 1.1 christos if (get_elf_backend_data (output_bfd)->want_got_sym)
4005 1.1 christos elf_hash_table (info)->hgot->root.u.def.value
4006 1.1 christos = bfinfdpic_got_initial_offset (info);
4007 1.1 christos
4008 1.1 christos if (elf_hash_table (info)->dynamic_sections_created)
4009 1.1 christos bfinfdpic_plt_initial_offset (info) =
4010 1.1 christos bfinfdpic_plt_section (info)->size;
4011 1.1 christos
4012 1.1 christos htab_traverse (bfinfdpic_relocs_info (info), _bfinfdpic_assign_plt_entries,
4013 1.1 christos gpinfop);
4014 1.1 christos
4015 1.1 christos /* Allocate the PLT section contents only after
4016 1.1 christos _bfinfdpic_assign_plt_entries has a chance to add the size of the
4017 1.1 christos non-lazy PLT entries. */
4018 1.1 christos if (bfinfdpic_plt_section (info)->size == 0)
4019 1.1 christos bfinfdpic_plt_section (info)->flags |= SEC_EXCLUDE;
4020 1.1 christos else
4021 1.1.1.10 christos {
4022 1.1 christos bfinfdpic_plt_section (info)->contents =
4023 1.1 christos (bfd_byte *) bfd_zalloc (dynobj,
4024 1.1.1.10 christos bfinfdpic_plt_section (info)->size);
4025 1.1 christos if (bfinfdpic_plt_section (info)->contents == NULL)
4026 1.1 christos return false;
4027 1.1 christos }
4028 1.1 christos
4029 1.1.1.10 christos return true;
4030 1.1.1.11 christos }
4031 1.1.1.11 christos
4032 1.1 christos /* Set the sizes of the dynamic sections. */
4033 1.1 christos
4034 1.1 christos static bool
4035 1.1 christos elf32_bfinfdpic_late_size_sections (bfd *output_bfd,
4036 1.1 christos struct bfd_link_info *info)
4037 1.1 christos {
4038 1.1 christos struct elf_link_hash_table *htab;
4039 1.1 christos bfd *dynobj;
4040 1.1.1.11 christos asection *s;
4041 1.1.1.11 christos struct _bfinfdpic_dynamic_got_plt_info gpinfo;
4042 1.1 christos
4043 1.1 christos htab = elf_hash_table (info);
4044 1.1 christos dynobj = htab->dynobj;
4045 1.1 christos if (dynobj == NULL)
4046 1.1.1.6 christos return true;
4047 1.1 christos
4048 1.1.1.2 christos if (htab->dynamic_sections_created)
4049 1.1 christos {
4050 1.1 christos /* Set the contents of the .interp section to the interpreter. */
4051 1.1 christos if (bfd_link_executable (info) && !info->nointerp)
4052 1.1 christos {
4053 1.1 christos s = bfd_get_linker_section (dynobj, ".interp");
4054 1.1 christos BFD_ASSERT (s != NULL);
4055 1.1 christos s->size = sizeof ELF_DYNAMIC_INTERPRETER;
4056 1.1 christos s->contents = (bfd_byte *) ELF_DYNAMIC_INTERPRETER;
4057 1.1 christos }
4058 1.1 christos }
4059 1.1 christos
4060 1.1 christos memset (&gpinfo, 0, sizeof (gpinfo));
4061 1.1 christos gpinfo.g.info = info;
4062 1.1 christos
4063 1.1 christos for (;;)
4064 1.1 christos {
4065 1.1 christos htab_t relocs = bfinfdpic_relocs_info (info);
4066 1.1 christos
4067 1.1 christos htab_traverse (relocs, _bfinfdpic_resolve_final_relocs_info, &relocs);
4068 1.1 christos
4069 1.1 christos if (relocs == bfinfdpic_relocs_info (info))
4070 1.1 christos break;
4071 1.1 christos }
4072 1.1 christos
4073 1.1 christos htab_traverse (bfinfdpic_relocs_info (info), _bfinfdpic_count_got_plt_entries,
4074 1.1 christos &gpinfo.g);
4075 1.1 christos
4076 1.1.1.10 christos /* Allocate space to save the summary information, we're going to
4077 1.1 christos use it if we're doing relaxations. */
4078 1.1.1.2 christos bfinfdpic_dynamic_got_plt_info (info) = bfd_alloc (dynobj, sizeof (gpinfo.g));
4079 1.1 christos
4080 1.1 christos if (!_bfinfdpic_size_got_plt (output_bfd, &gpinfo))
4081 1.1 christos return false;
4082 1.1.1.2 christos
4083 1.1 christos s = bfd_get_linker_section (dynobj, ".dynbss");
4084 1.1 christos if (s && s->size == 0)
4085 1.1 christos s->flags |= SEC_EXCLUDE;
4086 1.1.1.10 christos
4087 1.1 christos s = bfd_get_linker_section (dynobj, ".rela.bss");
4088 1.1 christos if (s && s->size == 0)
4089 1.1.1.10 christos s->flags |= SEC_EXCLUDE;
4090 1.1.1.11 christos
4091 1.1 christos return _bfd_elf_add_dynamic_tags (output_bfd, info, true);
4092 1.1 christos }
4093 1.1.1.6 christos
4094 1.1.1.2 christos static bool
4095 1.1.1.2 christos elf32_bfinfdpic_early_size_sections (bfd *output_bfd,
4096 1.1.1.10 christos struct bfd_link_info *info)
4097 1.1 christos {
4098 1.1.1.10 christos if (!bfd_link_relocatable (info)
4099 1.1 christos && !bfd_elf_stack_segment_size (output_bfd, info,
4100 1.1 christos "__stacksize", DEFAULT_STACK_SIZE))
4101 1.1 christos return false;
4102 1.1 christos
4103 1.1.1.10 christos return true;
4104 1.1 christos }
4105 1.1.1.2 christos
4106 1.1.1.10 christos /* Check whether any of the relocations was optimized away, and
4107 1.1 christos subtract it from the relocation or fixup count. */
4108 1.1 christos static bool
4109 1.1.1.10 christos _bfinfdpic_check_discarded_relocs (bfd *abfd, asection *sec,
4110 1.1 christos struct bfd_link_info *info,
4111 1.1 christos bool *changed)
4112 1.1 christos {
4113 1.1 christos Elf_Internal_Shdr *symtab_hdr;
4114 1.1.1.10 christos struct elf_link_hash_entry **sym_hashes;
4115 1.1 christos Elf_Internal_Rela *rel, *erel;
4116 1.1 christos
4117 1.1 christos if ((sec->flags & SEC_RELOC) == 0
4118 1.1 christos || sec->reloc_count == 0)
4119 1.1 christos return true;
4120 1.1 christos
4121 1.1 christos symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
4122 1.1 christos sym_hashes = elf_sym_hashes (abfd);
4123 1.1 christos
4124 1.1 christos rel = elf_section_data (sec)->relocs;
4125 1.1 christos
4126 1.1 christos /* Now examine each relocation. */
4127 1.1 christos for (erel = rel + sec->reloc_count; rel < erel; rel++)
4128 1.1 christos {
4129 1.1 christos struct elf_link_hash_entry *h;
4130 1.1 christos unsigned long r_symndx;
4131 1.1 christos struct bfinfdpic_relocs_info *picrel;
4132 1.1 christos struct _bfinfdpic_dynamic_got_info *dinfo;
4133 1.1 christos
4134 1.1 christos if (ELF32_R_TYPE (rel->r_info) != R_BFIN_BYTE4_DATA
4135 1.1 christos && ELF32_R_TYPE (rel->r_info) != R_BFIN_FUNCDESC)
4136 1.1 christos continue;
4137 1.1 christos
4138 1.1 christos if (_bfd_elf_section_offset (sec->output_section->owner,
4139 1.1 christos info, sec, rel->r_offset)
4140 1.1 christos != (bfd_vma)-1)
4141 1.1 christos continue;
4142 1.1 christos
4143 1.1 christos r_symndx = ELF32_R_SYM (rel->r_info);
4144 1.1 christos if (r_symndx < symtab_hdr->sh_info)
4145 1.1 christos h = NULL;
4146 1.1 christos else
4147 1.1 christos {
4148 1.1 christos h = sym_hashes[r_symndx - symtab_hdr->sh_info];
4149 1.1 christos while (h->root.type == bfd_link_hash_indirect
4150 1.1 christos || h->root.type == bfd_link_hash_warning)
4151 1.1 christos h = (struct elf_link_hash_entry *)h->root.u.i.link;
4152 1.1 christos }
4153 1.1 christos
4154 1.1 christos if (h != NULL)
4155 1.1 christos picrel = bfinfdpic_relocs_info_for_global (bfinfdpic_relocs_info (info),
4156 1.1 christos abfd, h,
4157 1.1 christos rel->r_addend, NO_INSERT);
4158 1.1 christos else
4159 1.1.1.10 christos picrel = bfinfdpic_relocs_info_for_local (bfinfdpic_relocs_info (info),
4160 1.1 christos abfd, r_symndx,
4161 1.1.1.10 christos rel->r_addend, NO_INSERT);
4162 1.1 christos
4163 1.1 christos if (! picrel)
4164 1.1.1.10 christos return false;
4165 1.1 christos
4166 1.1 christos *changed = true;
4167 1.1 christos dinfo = bfinfdpic_dynamic_got_plt_info (info);
4168 1.1 christos
4169 1.1.1.10 christos _bfinfdpic_count_relocs_fixups (picrel, dinfo, true);
4170 1.1 christos if (ELF32_R_TYPE (rel->r_info) == R_BFIN_BYTE4_DATA)
4171 1.1 christos picrel->relocs32--;
4172 1.1.1.10 christos else /* we know (ELF32_R_TYPE (rel->r_info) == R_BFIN_FUNCDESC) */
4173 1.1 christos picrel->relocsfd--;
4174 1.1 christos _bfinfdpic_count_relocs_fixups (picrel, dinfo, false);
4175 1.1.1.10 christos }
4176 1.1 christos
4177 1.1 christos return true;
4178 1.1 christos }
4179 1.1 christos
4180 1.1.1.10 christos static bool
4181 1.1 christos bfinfdpic_elf_discard_info (bfd *ibfd,
4182 1.1 christos struct elf_reloc_cookie *cookie ATTRIBUTE_UNUSED,
4183 1.1 christos struct bfd_link_info *info)
4184 1.1 christos {
4185 1.1 christos bool changed = false;
4186 1.1.1.2 christos asection *s;
4187 1.1 christos bfd *obfd = NULL;
4188 1.1 christos
4189 1.1.1.10 christos /* Account for relaxation of .eh_frame section. */
4190 1.1 christos for (s = ibfd->sections; s; s = s->next)
4191 1.1 christos if (s->sec_info_type == SEC_INFO_TYPE_EH_FRAME)
4192 1.1 christos {
4193 1.1 christos if (!_bfinfdpic_check_discarded_relocs (ibfd, s, info, &changed))
4194 1.1 christos return false;
4195 1.1 christos obfd = s->output_section->owner;
4196 1.1 christos }
4197 1.1 christos
4198 1.1 christos if (changed)
4199 1.1 christos {
4200 1.1 christos struct _bfinfdpic_dynamic_got_plt_info gpinfo;
4201 1.1 christos
4202 1.1 christos memset (&gpinfo, 0, sizeof (gpinfo));
4203 1.1 christos memcpy (&gpinfo.g, bfinfdpic_dynamic_got_plt_info (info),
4204 1.1 christos sizeof (gpinfo.g));
4205 1.1 christos
4206 1.1 christos /* Clear GOT and PLT assignments. */
4207 1.1.1.10 christos htab_traverse (bfinfdpic_relocs_info (info),
4208 1.1 christos _bfinfdpic_reset_got_plt_entries,
4209 1.1 christos NULL);
4210 1.1.1.10 christos
4211 1.1 christos if (!_bfinfdpic_size_got_plt (obfd, &gpinfo))
4212 1.1 christos return false;
4213 1.1.1.10 christos }
4214 1.1 christos
4215 1.1 christos return true;
4216 1.1 christos }
4217 1.1 christos
4218 1.1 christos static bool
4219 1.1 christos elf32_bfinfdpic_finish_dynamic_sections (bfd *output_bfd,
4220 1.1 christos struct bfd_link_info *info)
4221 1.1 christos {
4222 1.1 christos bfd *dynobj;
4223 1.1 christos asection *sdyn;
4224 1.1 christos
4225 1.1.1.6 christos dynobj = elf_hash_table (info)->dynobj;
4226 1.1.1.6 christos
4227 1.1.1.6 christos if (bfinfdpic_got_section (info))
4228 1.1.1.6 christos {
4229 1.1.1.6 christos BFD_ASSERT (bfinfdpic_gotrel_section (info)->size
4230 1.1.1.6 christos /* PR 17334: It appears that the GOT section can end up
4231 1.1.1.6 christos being bigger than the number of relocs. Presumably
4232 1.1 christos because some relocs have been deleted. A test case has
4233 1.1 christos yet to be generated for verify this, but in the meantime
4234 1.1 christos the test below has been changed from == to >= so that
4235 1.1 christos applications can continue to be built. */
4236 1.1 christos >= (bfinfdpic_gotrel_section (info)->reloc_count
4237 1.1 christos * sizeof (Elf32_External_Rel)));
4238 1.1 christos
4239 1.1 christos if (bfinfdpic_gotfixup_section (info))
4240 1.1 christos {
4241 1.1 christos struct elf_link_hash_entry *hgot = elf_hash_table (info)->hgot;
4242 1.1 christos bfd_vma got_value = hgot->root.u.def.value
4243 1.1 christos + hgot->root.u.def.section->output_section->vma
4244 1.1 christos + hgot->root.u.def.section->output_offset;
4245 1.1 christos
4246 1.1 christos _bfinfdpic_add_rofixup (output_bfd, bfinfdpic_gotfixup_section (info),
4247 1.1.1.7 christos got_value, 0);
4248 1.1 christos
4249 1.1.1.10 christos if (bfinfdpic_gotfixup_section (info)->size
4250 1.1 christos != (bfinfdpic_gotfixup_section (info)->reloc_count * 4))
4251 1.1 christos {
4252 1.1 christos _bfd_error_handler
4253 1.1 christos ("LINKER BUG: .rofixup section size mismatch");
4254 1.1 christos return false;
4255 1.1 christos }
4256 1.1 christos }
4257 1.1 christos }
4258 1.1 christos if (elf_hash_table (info)->dynamic_sections_created)
4259 1.1 christos {
4260 1.1.1.2 christos BFD_ASSERT (bfinfdpic_pltrel_section (info)->size
4261 1.1 christos == (bfinfdpic_pltrel_section (info)->reloc_count
4262 1.1 christos * sizeof (Elf32_External_Rel)));
4263 1.1 christos }
4264 1.1 christos
4265 1.1 christos sdyn = bfd_get_linker_section (dynobj, ".dynamic");
4266 1.1 christos
4267 1.1 christos if (elf_hash_table (info)->dynamic_sections_created)
4268 1.1 christos {
4269 1.1 christos Elf32_External_Dyn * dyncon;
4270 1.1 christos Elf32_External_Dyn * dynconend;
4271 1.1 christos
4272 1.1 christos BFD_ASSERT (sdyn != NULL);
4273 1.1 christos
4274 1.1 christos dyncon = (Elf32_External_Dyn *) sdyn->contents;
4275 1.1 christos dynconend = (Elf32_External_Dyn *) (sdyn->contents + sdyn->size);
4276 1.1 christos
4277 1.1 christos for (; dyncon < dynconend; dyncon++)
4278 1.1 christos {
4279 1.1 christos Elf_Internal_Dyn dyn;
4280 1.1 christos
4281 1.1 christos bfd_elf32_swap_dyn_in (dynobj, dyncon, &dyn);
4282 1.1 christos
4283 1.1 christos switch (dyn.d_tag)
4284 1.1 christos {
4285 1.1 christos default:
4286 1.1 christos break;
4287 1.1 christos
4288 1.1 christos case DT_PLTGOT:
4289 1.1 christos dyn.d_un.d_ptr = bfinfdpic_got_section (info)->output_section->vma
4290 1.1 christos + bfinfdpic_got_section (info)->output_offset
4291 1.1 christos + bfinfdpic_got_initial_offset (info);
4292 1.1 christos bfd_elf32_swap_dyn_out (output_bfd, &dyn, dyncon);
4293 1.1 christos break;
4294 1.1 christos
4295 1.1 christos case DT_JMPREL:
4296 1.1 christos dyn.d_un.d_ptr = bfinfdpic_pltrel_section (info)
4297 1.1 christos ->output_section->vma
4298 1.1 christos + bfinfdpic_pltrel_section (info)->output_offset;
4299 1.1 christos bfd_elf32_swap_dyn_out (output_bfd, &dyn, dyncon);
4300 1.1 christos break;
4301 1.1 christos
4302 1.1 christos case DT_PLTRELSZ:
4303 1.1 christos dyn.d_un.d_val = bfinfdpic_pltrel_section (info)->size;
4304 1.1 christos bfd_elf32_swap_dyn_out (output_bfd, &dyn, dyncon);
4305 1.1.1.10 christos break;
4306 1.1 christos }
4307 1.1 christos }
4308 1.1 christos }
4309 1.1 christos
4310 1.1 christos return true;
4311 1.1.1.10 christos }
4312 1.1.1.2 christos
4313 1.1.1.2 christos /* Adjust a symbol defined by a dynamic object and referenced by a
4314 1.1 christos regular object. */
4315 1.1 christos
4316 1.1 christos static bool
4317 1.1 christos elf32_bfinfdpic_adjust_dynamic_symbol (struct bfd_link_info *info,
4318 1.1 christos struct elf_link_hash_entry *h)
4319 1.1 christos {
4320 1.1 christos bfd * dynobj;
4321 1.1.1.8 christos
4322 1.1 christos dynobj = elf_hash_table (info)->dynobj;
4323 1.1 christos
4324 1.1 christos /* Make sure we know what is going on here. */
4325 1.1 christos BFD_ASSERT (dynobj != NULL
4326 1.1 christos && (h->is_weakalias
4327 1.1 christos || (h->def_dynamic
4328 1.1 christos && h->ref_regular
4329 1.1.1.8 christos && !h->def_regular)));
4330 1.1 christos
4331 1.1.1.8 christos /* If this is a weak symbol, and there is a real definition, the
4332 1.1.1.8 christos processor independent code will have arranged for us to see the
4333 1.1.1.8 christos real definition first, and we can just use the same value. */
4334 1.1.1.8 christos if (h->is_weakalias)
4335 1.1 christos {
4336 1.1 christos struct elf_link_hash_entry *def = weakdef (h);
4337 1.1.1.10 christos BFD_ASSERT (def->root.type == bfd_link_hash_defined);
4338 1.1 christos h->root.u.def.section = def->root.u.def.section;
4339 1.1 christos h->root.u.def.value = def->root.u.def.value;
4340 1.1 christos }
4341 1.1 christos
4342 1.1.1.10 christos return true;
4343 1.1 christos }
4344 1.1 christos
4345 1.1 christos /* Perform any actions needed for dynamic symbols. */
4346 1.1 christos
4347 1.1 christos static bool
4348 1.1 christos elf32_bfinfdpic_finish_dynamic_symbol
4349 1.1.1.10 christos (bfd *output_bfd ATTRIBUTE_UNUSED,
4350 1.1 christos struct bfd_link_info *info ATTRIBUTE_UNUSED,
4351 1.1 christos struct elf_link_hash_entry *h ATTRIBUTE_UNUSED,
4352 1.1 christos Elf_Internal_Sym *sym ATTRIBUTE_UNUSED)
4353 1.1 christos {
4354 1.1 christos return true;
4355 1.1.1.10 christos }
4356 1.1 christos
4357 1.1 christos /* Decide whether to attempt to turn absptr or lsda encodings in
4358 1.1 christos shared libraries into pcrel within the given input section. */
4359 1.1 christos
4360 1.1 christos static bool
4361 1.1 christos bfinfdpic_elf_use_relative_eh_frame
4362 1.1.1.10 christos (bfd *input_bfd ATTRIBUTE_UNUSED,
4363 1.1 christos struct bfd_link_info *info ATTRIBUTE_UNUSED,
4364 1.1 christos asection *eh_frame_section ATTRIBUTE_UNUSED)
4365 1.1 christos {
4366 1.1 christos /* We can't use PC-relative encodings in FDPIC binaries, in general. */
4367 1.1 christos return false;
4368 1.1 christos }
4369 1.1 christos
4370 1.1 christos /* Adjust the contents of an eh_frame_hdr section before they're output. */
4371 1.1 christos
4372 1.1 christos static bfd_byte
4373 1.1 christos bfinfdpic_elf_encode_eh_address (bfd *abfd,
4374 1.1 christos struct bfd_link_info *info,
4375 1.1 christos asection *osec, bfd_vma offset,
4376 1.1 christos asection *loc_sec, bfd_vma loc_offset,
4377 1.1 christos bfd_vma *encoded)
4378 1.1 christos {
4379 1.1 christos struct elf_link_hash_entry *h;
4380 1.1 christos
4381 1.1 christos h = elf_hash_table (info)->hgot;
4382 1.1 christos BFD_ASSERT (h && h->root.type == bfd_link_hash_defined);
4383 1.1 christos
4384 1.1 christos if (! h || (_bfinfdpic_osec_to_segment (abfd, osec)
4385 1.1 christos == _bfinfdpic_osec_to_segment (abfd, loc_sec->output_section)))
4386 1.1 christos return _bfd_elf_encode_eh_address (abfd, info, osec, offset,
4387 1.1 christos loc_sec, loc_offset, encoded);
4388 1.1 christos
4389 1.1 christos BFD_ASSERT (_bfinfdpic_osec_to_segment (abfd, osec)
4390 1.1 christos == (_bfinfdpic_osec_to_segment
4391 1.1 christos (abfd, h->root.u.def.section->output_section)));
4392 1.1 christos
4393 1.1 christos *encoded = osec->vma + offset
4394 1.1 christos - (h->root.u.def.value
4395 1.1 christos + h->root.u.def.section->output_section->vma
4396 1.1 christos + h->root.u.def.section->output_offset);
4397 1.1 christos
4398 1.1 christos return DW_EH_PE_datarel | DW_EH_PE_sdata4;
4399 1.1 christos }
4400 1.1 christos
4401 1.1 christos
4402 1.1 christos
4403 1.1 christos /* Look through the relocs for a section during the first phase.
4404 1.1 christos
4405 1.1 christos Besides handling virtual table relocs for gc, we have to deal with
4406 1.1 christos all sorts of PIC-related relocations. We describe below the
4407 1.1 christos general plan on how to handle such relocations, even though we only
4408 1.1 christos collect information at this point, storing them in hash tables for
4409 1.1 christos perusal of later passes.
4410 1.1 christos
4411 1.1 christos 32 relocations are propagated to the linker output when creating
4412 1.1 christos position-independent output. LO16 and HI16 relocations are not
4413 1.1 christos supposed to be encountered in this case.
4414 1.1 christos
4415 1.1 christos LABEL16 should always be resolvable by the linker, since it's only
4416 1.1 christos used by branches.
4417 1.1 christos
4418 1.1 christos LABEL24, on the other hand, is used by calls. If it turns out that
4419 1.1 christos the target of a call is a dynamic symbol, a PLT entry must be
4420 1.1 christos created for it, which triggers the creation of a private function
4421 1.1 christos descriptor and, unless lazy binding is disabled, a lazy PLT entry.
4422 1.1 christos
4423 1.1 christos GPREL relocations require the referenced symbol to be in the same
4424 1.1 christos segment as _gp, but this can only be checked later.
4425 1.1 christos
4426 1.1 christos All GOT, GOTOFF and FUNCDESC relocations require a .got section to
4427 1.1 christos exist. LABEL24 might as well, since it may require a PLT entry,
4428 1.1 christos that will require a got.
4429 1.1 christos
4430 1.1 christos Non-FUNCDESC GOT relocations require a GOT entry to be created
4431 1.1 christos regardless of whether the symbol is dynamic. However, since a
4432 1.1 christos global symbol that turns out to not be exported may have the same
4433 1.1 christos address of a non-dynamic symbol, we don't assign GOT entries at
4434 1.1 christos this point, such that we can share them in this case. A relocation
4435 1.1 christos for the GOT entry always has to be created, be it to offset a
4436 1.1 christos private symbol by the section load address, be it to get the symbol
4437 1.1 christos resolved dynamically.
4438 1.1 christos
4439 1.1 christos FUNCDESC GOT relocations require a GOT entry to be created, and
4440 1.1 christos handled as if a FUNCDESC relocation was applied to the GOT entry in
4441 1.1 christos an object file.
4442 1.1 christos
4443 1.1 christos FUNCDESC relocations referencing a symbol that turns out to NOT be
4444 1.1 christos dynamic cause a private function descriptor to be created. The
4445 1.1 christos FUNCDESC relocation then decays to a 32 relocation that points at
4446 1.1 christos the private descriptor. If the symbol is dynamic, the FUNCDESC
4447 1.1 christos relocation is propagated to the linker output, such that the
4448 1.1 christos dynamic linker creates the canonical descriptor, pointing to the
4449 1.1 christos dynamically-resolved definition of the function.
4450 1.1 christos
4451 1.1 christos Non-FUNCDESC GOTOFF relocations must always refer to non-dynamic
4452 1.1 christos symbols that are assigned to the same segment as the GOT, but we
4453 1.1 christos can only check this later, after we know the complete set of
4454 1.1 christos symbols defined and/or exported.
4455 1.1 christos
4456 1.1 christos FUNCDESC GOTOFF relocations require a function descriptor to be
4457 1.1 christos created and, unless lazy binding is disabled or the symbol is not
4458 1.1 christos dynamic, a lazy PLT entry. Since we can't tell at this point
4459 1.1 christos whether a symbol is going to be dynamic, we have to decide later
4460 1.1 christos whether to create a lazy PLT entry or bind the descriptor directly
4461 1.1 christos to the private function.
4462 1.1 christos
4463 1.1 christos FUNCDESC_VALUE relocations are not supposed to be present in object
4464 1.1 christos files, but they may very well be simply propagated to the linker
4465 1.1 christos output, since they have no side effect.
4466 1.1 christos
4467 1.1 christos
4468 1.1 christos A function descriptor always requires a FUNCDESC_VALUE relocation.
4469 1.1 christos Whether it's in .plt.rel or not depends on whether lazy binding is
4470 1.1 christos enabled and on whether the referenced symbol is dynamic.
4471 1.1 christos
4472 1.1 christos The existence of a lazy PLT requires the resolverStub lazy PLT
4473 1.1 christos entry to be present.
4474 1.1 christos
4475 1.1 christos
4476 1.1 christos As for assignment of GOT, PLT and lazy PLT entries, and private
4477 1.1 christos descriptors, we might do them all sequentially, but we can do
4478 1.1 christos better than that. For example, we can place GOT entries and
4479 1.1 christos private function descriptors referenced using 12-bit operands
4480 1.1 christos closer to the PIC register value, such that these relocations don't
4481 1.1 christos overflow. Those that are only referenced with LO16 relocations
4482 1.1 christos could come next, but we may as well place PLT-required function
4483 1.1 christos descriptors in the 12-bit range to make them shorter. Symbols
4484 1.1 christos referenced with LO16/HI16 may come next, but we may place
4485 1.1 christos additional function descriptors in the 16-bit range if we can
4486 1.1 christos reliably tell that we've already placed entries that are ever
4487 1.1 christos referenced with only LO16. PLT entries are therefore generated as
4488 1.1 christos small as possible, while not introducing relocation overflows in
4489 1.1 christos GOT or FUNCDESC_GOTOFF relocations. Lazy PLT entries could be
4490 1.1 christos generated before or after PLT entries, but not intermingled with
4491 1.1 christos them, such that we can have more lazy PLT entries in range for a
4492 1.1 christos branch to the resolverStub. The resolverStub should be emitted at
4493 1.1 christos the most distant location from the first lazy PLT entry such that
4494 1.1 christos it's still in range for a branch, or closer, if there isn't a need
4495 1.1 christos for so many lazy PLT entries. Additional lazy PLT entries may be
4496 1.1 christos emitted after the resolverStub, as long as branches are still in
4497 1.1 christos range. If the branch goes out of range, longer lazy PLT entries
4498 1.1 christos are emitted.
4499 1.1 christos
4500 1.1 christos We could further optimize PLT and lazy PLT entries by giving them
4501 1.1 christos priority in assignment to closer-to-gr17 locations depending on the
4502 1.1.1.10 christos number of occurrences of references to them (assuming a function
4503 1.1 christos that's called more often is more important for performance, so its
4504 1.1 christos PLT entry should be faster), or taking hints from the compiler.
4505 1.1 christos Given infinite time and money... :-) */
4506 1.1 christos
4507 1.1 christos static bool
4508 1.1 christos bfinfdpic_check_relocs (bfd *abfd, struct bfd_link_info *info,
4509 1.1 christos asection *sec, const Elf_Internal_Rela *relocs)
4510 1.1 christos {
4511 1.1 christos Elf_Internal_Shdr *symtab_hdr;
4512 1.1 christos struct elf_link_hash_entry **sym_hashes;
4513 1.1.1.6 christos const Elf_Internal_Rela *rel;
4514 1.1.1.10 christos const Elf_Internal_Rela *rel_end;
4515 1.1 christos bfd *dynobj;
4516 1.1 christos struct bfinfdpic_relocs_info *picrel;
4517 1.1 christos
4518 1.1 christos if (bfd_link_relocatable (info))
4519 1.1 christos return true;
4520 1.1 christos
4521 1.1 christos symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
4522 1.1 christos sym_hashes = elf_sym_hashes (abfd);
4523 1.1 christos
4524 1.1 christos dynobj = elf_hash_table (info)->dynobj;
4525 1.1 christos rel_end = relocs + sec->reloc_count;
4526 1.1 christos for (rel = relocs; rel < rel_end; rel++)
4527 1.1 christos {
4528 1.1.1.8 christos struct elf_link_hash_entry *h;
4529 1.1 christos unsigned long r_symndx;
4530 1.1.1.10 christos
4531 1.1.1.10 christos r_symndx = ELF32_R_SYM (rel->r_info);
4532 1.1.1.10 christos if (r_symndx < symtab_hdr->sh_info)
4533 1.1.1.10 christos h = NULL;
4534 1.1.1.10 christos else
4535 1.1.1.10 christos {
4536 1.1 christos h = sym_hashes[r_symndx - symtab_hdr->sh_info];
4537 1.1 christos while (h->root.type == bfd_link_hash_indirect
4538 1.1 christos || h->root.type == bfd_link_hash_warning)
4539 1.1 christos h = (struct elf_link_hash_entry *) h->root.u.i.link;
4540 1.1 christos }
4541 1.1 christos
4542 1.1 christos switch (ELF32_R_TYPE (rel->r_info))
4543 1.1 christos {
4544 1.1 christos case R_BFIN_GOT17M4:
4545 1.1 christos case R_BFIN_GOTHI:
4546 1.1 christos case R_BFIN_GOTLO:
4547 1.1 christos case R_BFIN_FUNCDESC_GOT17M4:
4548 1.1 christos case R_BFIN_FUNCDESC_GOTHI:
4549 1.1 christos case R_BFIN_FUNCDESC_GOTLO:
4550 1.1 christos case R_BFIN_GOTOFF17M4:
4551 1.1 christos case R_BFIN_GOTOFFHI:
4552 1.1 christos case R_BFIN_GOTOFFLO:
4553 1.1 christos case R_BFIN_FUNCDESC_GOTOFF17M4:
4554 1.1 christos case R_BFIN_FUNCDESC_GOTOFFHI:
4555 1.1 christos case R_BFIN_FUNCDESC_GOTOFFLO:
4556 1.1 christos case R_BFIN_FUNCDESC:
4557 1.1 christos case R_BFIN_FUNCDESC_VALUE:
4558 1.1 christos if (! IS_FDPIC (abfd))
4559 1.1 christos goto bad_reloc;
4560 1.1 christos /* Fall through. */
4561 1.1 christos case R_BFIN_PCREL24:
4562 1.1 christos case R_BFIN_PCREL24_JUMP_L:
4563 1.1.1.10 christos case R_BFIN_BYTE4_DATA:
4564 1.1 christos if (IS_FDPIC (abfd) && ! dynobj)
4565 1.1 christos {
4566 1.1 christos elf_hash_table (info)->dynobj = dynobj = abfd;
4567 1.1 christos if (! _bfin_create_got_section (abfd, info))
4568 1.1 christos return false;
4569 1.1 christos }
4570 1.1 christos if (! IS_FDPIC (abfd))
4571 1.1 christos {
4572 1.1 christos picrel = NULL;
4573 1.1 christos break;
4574 1.1 christos }
4575 1.1 christos if (h != NULL)
4576 1.1 christos {
4577 1.1 christos if (h->dynindx == -1)
4578 1.1 christos switch (ELF_ST_VISIBILITY (h->other))
4579 1.1 christos {
4580 1.1 christos case STV_INTERNAL:
4581 1.1 christos case STV_HIDDEN:
4582 1.1 christos break;
4583 1.1 christos default:
4584 1.1 christos bfd_elf_link_record_dynamic_symbol (info, h);
4585 1.1 christos break;
4586 1.1 christos }
4587 1.1 christos picrel
4588 1.1 christos = bfinfdpic_relocs_info_for_global (bfinfdpic_relocs_info (info),
4589 1.1 christos abfd, h,
4590 1.1 christos rel->r_addend, INSERT);
4591 1.1 christos }
4592 1.1.1.10 christos else
4593 1.1 christos picrel = bfinfdpic_relocs_info_for_local (bfinfdpic_relocs_info
4594 1.1 christos (info), abfd, r_symndx,
4595 1.1 christos rel->r_addend, INSERT);
4596 1.1 christos if (! picrel)
4597 1.1 christos return false;
4598 1.1 christos break;
4599 1.1 christos
4600 1.1 christos default:
4601 1.1.1.8 christos picrel = NULL;
4602 1.1 christos break;
4603 1.1 christos }
4604 1.1 christos
4605 1.1 christos switch (ELF32_R_TYPE (rel->r_info))
4606 1.1 christos {
4607 1.1 christos case R_BFIN_PCREL24:
4608 1.1 christos case R_BFIN_PCREL24_JUMP_L:
4609 1.1 christos if (IS_FDPIC (abfd))
4610 1.1.1.9 christos picrel->call++;
4611 1.1 christos break;
4612 1.1 christos
4613 1.1 christos case R_BFIN_FUNCDESC_VALUE:
4614 1.1 christos picrel->relocsfdv++;
4615 1.1 christos if (bfd_section_flags (sec) & SEC_ALLOC)
4616 1.1 christos picrel->relocs32--;
4617 1.1 christos /* Fall through. */
4618 1.1 christos
4619 1.1.1.9 christos case R_BFIN_BYTE4_DATA:
4620 1.1 christos if (! IS_FDPIC (abfd))
4621 1.1 christos break;
4622 1.1 christos
4623 1.1 christos picrel->sym++;
4624 1.1 christos if (bfd_section_flags (sec) & SEC_ALLOC)
4625 1.1 christos picrel->relocs32++;
4626 1.1 christos break;
4627 1.1 christos
4628 1.1 christos case R_BFIN_GOT17M4:
4629 1.1 christos picrel->got17m4++;
4630 1.1 christos break;
4631 1.1 christos
4632 1.1 christos case R_BFIN_GOTHI:
4633 1.1 christos case R_BFIN_GOTLO:
4634 1.1 christos picrel->gothilo++;
4635 1.1 christos break;
4636 1.1 christos
4637 1.1 christos case R_BFIN_FUNCDESC_GOT17M4:
4638 1.1 christos picrel->fdgot17m4++;
4639 1.1 christos break;
4640 1.1 christos
4641 1.1 christos case R_BFIN_FUNCDESC_GOTHI:
4642 1.1 christos case R_BFIN_FUNCDESC_GOTLO:
4643 1.1 christos picrel->fdgothilo++;
4644 1.1 christos break;
4645 1.1 christos
4646 1.1 christos case R_BFIN_GOTOFF17M4:
4647 1.1 christos case R_BFIN_GOTOFFHI:
4648 1.1 christos case R_BFIN_GOTOFFLO:
4649 1.1 christos picrel->gotoff++;
4650 1.1 christos break;
4651 1.1 christos
4652 1.1 christos case R_BFIN_FUNCDESC_GOTOFF17M4:
4653 1.1 christos picrel->fdgoff17m4++;
4654 1.1 christos break;
4655 1.1 christos
4656 1.1 christos case R_BFIN_FUNCDESC_GOTOFFHI:
4657 1.1 christos case R_BFIN_FUNCDESC_GOTOFFLO:
4658 1.1 christos picrel->fdgoffhilo++;
4659 1.1 christos break;
4660 1.1 christos
4661 1.1.1.8 christos case R_BFIN_FUNCDESC:
4662 1.1.1.8 christos picrel->fd++;
4663 1.1.1.8 christos picrel->relocsfd++;
4664 1.1.1.8 christos break;
4665 1.1.1.10 christos
4666 1.1.1.8 christos /* This relocation describes the C++ object vtable hierarchy.
4667 1.1.1.8 christos Reconstruct it for later use during GC. */
4668 1.1.1.8 christos case R_BFIN_GNU_VTINHERIT:
4669 1.1.1.8 christos if (!bfd_elf_gc_record_vtinherit (abfd, sec, h, rel->r_offset))
4670 1.1.1.8 christos return false;
4671 1.1.1.8 christos break;
4672 1.1.1.8 christos
4673 1.1.1.8 christos /* This relocation describes which C++ vtable entries are actually
4674 1.1.1.10 christos used. Record for later use during GC. */
4675 1.1.1.8 christos case R_BFIN_GNU_VTENTRY:
4676 1.1 christos BFD_ASSERT (h != NULL);
4677 1.1 christos if (h != NULL
4678 1.1 christos && !bfd_elf_gc_record_vtentry (abfd, sec, h, rel->r_addend))
4679 1.1 christos return false;
4680 1.1 christos break;
4681 1.1 christos
4682 1.1 christos case R_BFIN_HUIMM16:
4683 1.1 christos case R_BFIN_LUIMM16:
4684 1.1 christos case R_BFIN_PCREL12_JUMP_S:
4685 1.1.1.7 christos case R_BFIN_PCREL10:
4686 1.1.1.7 christos break;
4687 1.1.1.8 christos
4688 1.1.1.8 christos default:
4689 1.1.1.10 christos bad_reloc:
4690 1.1.1.8 christos _bfd_error_handler
4691 1.1 christos /* xgettext:c-format */
4692 1.1 christos (_("%pB: unsupported relocation type %#x"),
4693 1.1.1.10 christos abfd, (int) ELF32_R_TYPE (rel->r_info));
4694 1.1 christos return false;
4695 1.1 christos }
4696 1.1 christos }
4697 1.1 christos
4698 1.1.1.10 christos return true;
4699 1.1 christos }
4700 1.1 christos
4701 1.1 christos /* Set the right machine number for a Blackfin ELF file. */
4702 1.1 christos
4703 1.1 christos static bool
4704 1.1 christos elf32_bfin_object_p (bfd *abfd)
4705 1.1 christos {
4706 1.1.1.10 christos bfd_default_set_arch_mach (abfd, bfd_arch_bfin, 0);
4707 1.1 christos return (((elf_elfheader (abfd)->e_flags & EF_BFIN_FDPIC) != 0)
4708 1.1 christos == (IS_FDPIC (abfd)));
4709 1.1 christos }
4710 1.1.1.10 christos
4711 1.1.1.10 christos static bool
4712 1.1 christos elf32_bfin_set_private_flags (bfd * abfd, flagword flags)
4713 1.1 christos {
4714 1.1 christos elf_elfheader (abfd)->e_flags = flags;
4715 1.1.1.10 christos elf_flags_init (abfd) = true;
4716 1.1.1.2 christos return true;
4717 1.1 christos }
4718 1.1 christos
4719 1.1 christos /* Display the flags field. */
4720 1.1 christos static bool
4721 1.1 christos elf32_bfin_print_private_bfd_data (bfd * abfd, void * ptr)
4722 1.1 christos {
4723 1.1 christos FILE *file = (FILE *) ptr;
4724 1.1 christos flagword flags;
4725 1.1 christos
4726 1.1 christos BFD_ASSERT (abfd != NULL && ptr != NULL);
4727 1.1 christos
4728 1.1 christos /* Print normal ELF private data. */
4729 1.1 christos _bfd_elf_print_private_bfd_data (abfd, ptr);
4730 1.1 christos
4731 1.1 christos flags = elf_elfheader (abfd)->e_flags;
4732 1.1 christos
4733 1.1 christos /* xgettext:c-format */
4734 1.1 christos fprintf (file, _("private flags = %lx:"), elf_elfheader (abfd)->e_flags);
4735 1.1 christos
4736 1.1 christos if (flags & EF_BFIN_PIC)
4737 1.1 christos fprintf (file, " -fpic");
4738 1.1 christos
4739 1.1.1.10 christos if (flags & EF_BFIN_FDPIC)
4740 1.1 christos fprintf (file, " -mfdpic");
4741 1.1 christos
4742 1.1 christos fputc ('\n', file);
4743 1.1 christos
4744 1.1 christos return true;
4745 1.1.1.10 christos }
4746 1.1.1.7 christos
4747 1.1 christos /* Merge backend specific data from an object file to the output
4748 1.1.1.7 christos object file when linking. */
4749 1.1 christos
4750 1.1.1.10 christos static bool
4751 1.1 christos elf32_bfin_merge_private_bfd_data (bfd *ibfd, struct bfd_link_info *info)
4752 1.1.1.9 christos {
4753 1.1.1.9 christos bfd *obfd = info->output_bfd;
4754 1.1.1.10 christos flagword old_flags, new_flags;
4755 1.1.1.9 christos bool error = false;
4756 1.1 christos
4757 1.1 christos /* FIXME: What should be checked when linking shared libraries? */
4758 1.1 christos if ((ibfd->flags & DYNAMIC) != 0)
4759 1.1 christos return true;
4760 1.1 christos
4761 1.1 christos new_flags = elf_elfheader (ibfd)->e_flags;
4762 1.1 christos old_flags = elf_elfheader (obfd)->e_flags;
4763 1.1 christos
4764 1.1 christos if (new_flags & EF_BFIN_FDPIC)
4765 1.1.1.7 christos new_flags &= ~EF_BFIN_PIC;
4766 1.1.1.8 christos
4767 1.1.1.7 christos #ifndef DEBUG
4768 1.1 christos if (0)
4769 1.1 christos #endif
4770 1.1 christos _bfd_error_handler
4771 1.1.1.10 christos ("old_flags = 0x%.8x, new_flags = 0x%.8x, init = %s, filename = %pB",
4772 1.1 christos old_flags, new_flags, elf_flags_init (obfd) ? "yes" : "no", ibfd);
4773 1.1 christos
4774 1.1 christos if (!elf_flags_init (obfd)) /* First call, no flags set. */
4775 1.1 christos {
4776 1.1 christos elf_flags_init (obfd) = true;
4777 1.1.1.10 christos elf_elfheader (obfd)->e_flags = new_flags;
4778 1.1 christos }
4779 1.1.1.7 christos
4780 1.1.1.8 christos if (((new_flags & EF_BFIN_FDPIC) == 0) != (! IS_FDPIC (obfd)))
4781 1.1.1.7 christos {
4782 1.1 christos error = true;
4783 1.1.1.7 christos if (IS_FDPIC (obfd))
4784 1.1.1.8 christos _bfd_error_handler
4785 1.1.1.7 christos (_("%pB: cannot link non-fdpic object file into fdpic executable"),
4786 1.1 christos ibfd);
4787 1.1 christos else
4788 1.1 christos _bfd_error_handler
4789 1.1 christos (_("%pB: cannot link fdpic object file into non-fdpic executable"),
4790 1.1 christos ibfd);
4791 1.1 christos }
4792 1.1 christos
4793 1.1 christos if (error)
4794 1.1 christos bfd_set_error (bfd_error_bad_value);
4795 1.1 christos
4796 1.1 christos return !error;
4797 1.1 christos }
4798 1.1 christos
4799 1.1 christos /* bfin ELF linker hash entry. */
4801 1.1 christos
4802 1.1 christos struct bfin_link_hash_entry
4803 1.1 christos {
4804 1.1 christos struct elf_link_hash_entry root;
4805 1.1 christos
4806 1.1 christos /* Number of PC relative relocs copied for this symbol. */
4807 1.1 christos struct bfin_pcrel_relocs_copied *pcrel_relocs_copied;
4808 1.1 christos };
4809 1.1 christos
4810 1.1 christos #define bfin_hash_entry(ent) ((struct bfin_link_hash_entry *) (ent))
4811 1.1 christos
4812 1.1 christos static struct bfd_hash_entry *
4813 1.1 christos bfin_link_hash_newfunc (struct bfd_hash_entry *entry,
4814 1.1 christos struct bfd_hash_table *table, const char *string)
4815 1.1 christos {
4816 1.1 christos struct bfd_hash_entry *ret = entry;
4817 1.1 christos
4818 1.1 christos /* Allocate the structure if it has not already been allocated by a
4819 1.1 christos subclass. */
4820 1.1 christos if (ret == NULL)
4821 1.1 christos ret = bfd_hash_allocate (table, sizeof (struct bfin_link_hash_entry));
4822 1.1 christos if (ret == NULL)
4823 1.1 christos return ret;
4824 1.1 christos
4825 1.1 christos /* Call the allocation method of the superclass. */
4826 1.1 christos ret = _bfd_elf_link_hash_newfunc (ret, table, string);
4827 1.1 christos if (ret != NULL)
4828 1.1 christos bfin_hash_entry (ret)->pcrel_relocs_copied = NULL;
4829 1.1 christos
4830 1.1 christos return ret;
4831 1.1 christos }
4832 1.1.1.9 christos
4833 1.1.1.9 christos /* Create an bfin ELF linker hash table. */
4834 1.1 christos
4835 1.1.1.2 christos static struct bfd_link_hash_table *
4836 1.1 christos bfin_link_hash_table_create (bfd * abfd)
4837 1.1 christos {
4838 1.1 christos struct elf_link_hash_table *ret;
4839 1.1.1.9 christos size_t amt = sizeof (struct elf_link_hash_table);
4840 1.1 christos
4841 1.1 christos ret = bfd_zmalloc (amt);
4842 1.1 christos if (ret == NULL)
4843 1.1 christos return NULL;
4844 1.1 christos
4845 1.1 christos if (!_bfd_elf_link_hash_table_init (ret, abfd, bfin_link_hash_newfunc,
4846 1.1 christos sizeof (struct elf_link_hash_entry),
4847 1.1.1.9 christos BFIN_ELF_DATA))
4848 1.1 christos {
4849 1.1 christos free (ret);
4850 1.1 christos return NULL;
4851 1.1 christos }
4852 1.1 christos
4853 1.1 christos return &ret->root;
4854 1.1.1.10 christos }
4855 1.1 christos
4856 1.1.1.2 christos /* The size in bytes of an entry in the procedure linkage table. */
4857 1.1 christos
4858 1.1 christos /* Finish up the dynamic sections. */
4859 1.1 christos
4860 1.1 christos static bool
4861 1.1 christos bfin_finish_dynamic_sections (bfd * output_bfd ATTRIBUTE_UNUSED,
4862 1.1 christos struct bfd_link_info *info)
4863 1.1.1.2 christos {
4864 1.1 christos bfd *dynobj;
4865 1.1 christos asection *sdyn;
4866 1.1 christos
4867 1.1 christos dynobj = elf_hash_table (info)->dynobj;
4868 1.1 christos
4869 1.1 christos sdyn = bfd_get_linker_section (dynobj, ".dynamic");
4870 1.1 christos
4871 1.1 christos if (elf_hash_table (info)->dynamic_sections_created)
4872 1.1 christos {
4873 1.1 christos Elf32_External_Dyn *dyncon, *dynconend;
4874 1.1 christos
4875 1.1 christos BFD_ASSERT (sdyn != NULL);
4876 1.1 christos
4877 1.1 christos dyncon = (Elf32_External_Dyn *) sdyn->contents;
4878 1.1 christos dynconend = (Elf32_External_Dyn *) (sdyn->contents + sdyn->size);
4879 1.1 christos for (; dyncon < dynconend; dyncon++)
4880 1.1 christos {
4881 1.1 christos Elf_Internal_Dyn dyn;
4882 1.1.1.10 christos
4883 1.1 christos bfd_elf32_swap_dyn_in (dynobj, dyncon, &dyn);
4884 1.1 christos
4885 1.1 christos }
4886 1.1 christos
4887 1.1 christos }
4888 1.1.1.10 christos return true;
4889 1.1 christos }
4890 1.1.1.2 christos
4891 1.1.1.2 christos /* Finish up dynamic symbol handling. We set the contents of various
4892 1.1.1.2 christos dynamic sections here. */
4893 1.1 christos
4894 1.1 christos static bool
4895 1.1 christos bfin_finish_dynamic_symbol (bfd * output_bfd,
4896 1.1 christos struct bfd_link_info *info,
4897 1.1 christos struct elf_link_hash_entry *h,
4898 1.1 christos Elf_Internal_Sym * sym)
4899 1.1 christos {
4900 1.1 christos if (h->got.offset != (bfd_vma) - 1)
4901 1.1 christos {
4902 1.1.1.8 christos asection *sgot;
4903 1.1 christos asection *srela;
4904 1.1.1.7 christos Elf_Internal_Rela rela;
4905 1.1.1.7 christos bfd_byte *loc;
4906 1.1 christos
4907 1.1 christos /* This symbol has an entry in the global offset table.
4908 1.1 christos Set it up. */
4909 1.1 christos
4910 1.1 christos sgot = elf_hash_table (info)->sgot;
4911 1.1 christos srela = elf_hash_table (info)->srelgot;
4912 1.1 christos BFD_ASSERT (sgot != NULL && srela != NULL);
4913 1.1.1.8 christos
4914 1.1.1.8 christos rela.r_offset = (sgot->output_section->vma
4915 1.1.1.8 christos + sgot->output_offset
4916 1.1.1.8 christos + (h->got.offset & ~(bfd_vma) 1));
4917 1.1.1.6 christos
4918 1.1 christos /* If this is a -Bsymbolic link, and the symbol is defined
4919 1.1 christos locally, we just want to emit a RELATIVE reloc. Likewise if
4920 1.1 christos the symbol was forced to be local because of a version file.
4921 1.1.1.11 christos The entry in the global offset table will already have been
4922 1.1 christos initialized in the relocate_section function. */
4923 1.1 christos if (bfd_link_pic (info)
4924 1.1 christos && (info->symbolic
4925 1.1 christos || h->dynindx == -1 || h->forced_local) && h->def_regular)
4926 1.1 christos {
4927 1.1 christos _bfd_error_handler (_("*** check this relocation %s"), __func__);
4928 1.1 christos rela.r_info = ELF32_R_INFO (0, R_BFIN_PCREL24);
4929 1.1 christos rela.r_addend = bfd_get_signed_32 (output_bfd,
4930 1.1 christos (sgot->contents
4931 1.1 christos +
4932 1.1 christos (h->got.
4933 1.1 christos offset & ~(bfd_vma) 1)));
4934 1.1 christos }
4935 1.1 christos else
4936 1.1 christos {
4937 1.1 christos bfd_put_32 (output_bfd, (bfd_vma) 0,
4938 1.1 christos sgot->contents + (h->got.offset & ~(bfd_vma) 1));
4939 1.1 christos rela.r_info = ELF32_R_INFO (h->dynindx, R_BFIN_GOT);
4940 1.1 christos rela.r_addend = 0;
4941 1.1 christos }
4942 1.1 christos
4943 1.1 christos loc = srela->contents;
4944 1.1 christos loc += srela->reloc_count++ * sizeof (Elf32_External_Rela);
4945 1.1 christos bfd_elf32_swap_reloca_out (output_bfd, &rela, loc);
4946 1.1 christos }
4947 1.1 christos
4948 1.1 christos if (h->needs_copy)
4949 1.1 christos {
4950 1.1 christos BFD_ASSERT (0);
4951 1.1.1.10 christos }
4952 1.1 christos /* Mark _DYNAMIC and _GLOBAL_OFFSET_TABLE_ as absolute. */
4953 1.1 christos if (strcmp (h->root.root.string, "__DYNAMIC") == 0
4954 1.1 christos || h == elf_hash_table (info)->hgot)
4955 1.1 christos sym->st_shndx = SHN_ABS;
4956 1.1 christos
4957 1.1 christos return true;
4958 1.1 christos }
4959 1.1 christos
4960 1.1.1.10 christos /* Adjust a symbol defined by a dynamic object and referenced by a
4961 1.1 christos regular object. The current definition is in some section of the
4962 1.1.1.2 christos dynamic object, but we're not including those sections. We have to
4963 1.1 christos change the definition to something the rest of the link can
4964 1.1 christos understand. */
4965 1.1 christos
4966 1.1 christos static bool
4967 1.1 christos bfin_adjust_dynamic_symbol (struct bfd_link_info *info,
4968 1.1 christos struct elf_link_hash_entry *h)
4969 1.1 christos {
4970 1.1 christos bfd *dynobj;
4971 1.1 christos asection *s;
4972 1.1 christos unsigned int power_of_two;
4973 1.1.1.8 christos
4974 1.1 christos dynobj = elf_hash_table (info)->dynobj;
4975 1.1 christos
4976 1.1 christos /* Make sure we know what is going on here. */
4977 1.1 christos BFD_ASSERT (dynobj != NULL
4978 1.1 christos && (h->needs_plt
4979 1.1 christos || h->is_weakalias
4980 1.1 christos || (h->def_dynamic && h->ref_regular && !h->def_regular)));
4981 1.1 christos
4982 1.1 christos /* If this is a function, put it in the procedure linkage table. We
4983 1.1 christos will fill in the contents of the procedure linkage table later,
4984 1.1 christos when we know the address of the .got section. */
4985 1.1 christos if (h->type == STT_FUNC || h->needs_plt)
4986 1.1 christos {
4987 1.1.1.8 christos BFD_ASSERT(0);
4988 1.1 christos }
4989 1.1.1.8 christos
4990 1.1.1.8 christos /* If this is a weak symbol, and there is a real definition, the
4991 1.1.1.8 christos processor independent code will have arranged for us to see the
4992 1.1.1.8 christos real definition first, and we can just use the same value. */
4993 1.1.1.10 christos if (h->is_weakalias)
4994 1.1 christos {
4995 1.1 christos struct elf_link_hash_entry *def = weakdef (h);
4996 1.1 christos BFD_ASSERT (def->root.type == bfd_link_hash_defined);
4997 1.1 christos h->root.u.def.section = def->root.u.def.section;
4998 1.1 christos h->root.u.def.value = def->root.u.def.value;
4999 1.1 christos return true;
5000 1.1 christos }
5001 1.1 christos
5002 1.1 christos /* This is a reference to a symbol defined by a dynamic object which
5003 1.1.1.6 christos is not a function. */
5004 1.1.1.10 christos
5005 1.1 christos /* If we are creating a shared library, we must presume that the
5006 1.1 christos only references to the symbol are via the global offset table.
5007 1.1 christos For such cases we need not do anything here; the relocations will
5008 1.1 christos be handled correctly by relocate_section. */
5009 1.1 christos if (bfd_link_pic (info))
5010 1.1 christos return true;
5011 1.1 christos
5012 1.1 christos /* We must allocate the symbol in our .dynbss section, which will
5013 1.1 christos become part of the .bss section of the executable. There will be
5014 1.1 christos an entry for this symbol in the .dynsym section. The dynamic
5015 1.1 christos object will contain position independent code, so all references
5016 1.1.1.2 christos from the dynamic object to this symbol will go through the global
5017 1.1 christos offset table. The dynamic linker will use the .dynsym entry to
5018 1.1 christos determine the address it must put in the global offset table, so
5019 1.1.1.6 christos both the dynamic object and the regular object will refer to the
5020 1.1.1.6 christos same memory location for the variable. */
5021 1.1 christos
5022 1.1 christos s = bfd_get_linker_section (dynobj, ".dynbss");
5023 1.1 christos BFD_ASSERT (s != NULL);
5024 1.1 christos
5025 1.1 christos #if 0 /* Bfin does not currently have a COPY reloc. */
5026 1.1 christos /* We must generate a R_BFIN_COPY reloc to tell the dynamic linker to
5027 1.1 christos copy the initial value out of the dynamic object and into the
5028 1.1.1.2 christos runtime process image. We need to remember the offset into the
5029 1.1 christos .rela.bss section we are going to use. */
5030 1.1 christos if ((h->root.u.def.section->flags & SEC_ALLOC) != 0)
5031 1.1 christos {
5032 1.1 christos asection *srel;
5033 1.1.1.6 christos
5034 1.1.1.6 christos srel = bfd_get_linker_section (dynobj, ".rela.bss");
5035 1.1.1.6 christos BFD_ASSERT (srel != NULL);
5036 1.1.1.7 christos srel->size += sizeof (Elf32_External_Rela);
5037 1.1.1.10 christos h->needs_copy = 1;
5038 1.1.1.6 christos }
5039 1.1.1.6 christos #else
5040 1.1 christos if ((h->root.u.def.section->flags & SEC_ALLOC) != 0)
5041 1.1 christos {
5042 1.1 christos _bfd_error_handler (_("the bfin target does not currently support the generation of copy relocations"));
5043 1.1 christos return false;
5044 1.1 christos }
5045 1.1 christos #endif
5046 1.1 christos /* We need to figure out the alignment required for this symbol. I
5047 1.1 christos have no idea how ELF linkers handle this. */
5048 1.1.1.9 christos power_of_two = bfd_log2 (h->size);
5049 1.1 christos if (power_of_two > 3)
5050 1.1.1.9 christos power_of_two = 3;
5051 1.1.1.10 christos
5052 1.1 christos /* Apply the required alignment. */
5053 1.1 christos s->size = BFD_ALIGN (s->size, (bfd_size_type) (1 << power_of_two));
5054 1.1 christos if (power_of_two > bfd_section_alignment (s))
5055 1.1 christos {
5056 1.1 christos if (!bfd_set_section_alignment (s, power_of_two))
5057 1.1 christos return false;
5058 1.1 christos }
5059 1.1 christos
5060 1.1 christos /* Define the symbol as being at this point in the section. */
5061 1.1.1.10 christos h->root.u.def.section = s;
5062 1.1 christos h->root.u.def.value = s->size;
5063 1.1 christos
5064 1.1 christos /* Increment the section size to make room for the symbol. */
5065 1.1 christos s->size += h->size;
5066 1.1 christos
5067 1.1 christos return true;
5068 1.1 christos }
5069 1.1 christos
5070 1.1 christos /* The bfin linker needs to keep track of the number of relocs that it
5071 1.1 christos decides to copy in check_relocs for each symbol. This is so that it
5072 1.1 christos can discard PC relative relocs if it doesn't need them when linking
5073 1.1 christos with -Bsymbolic. We store the information in a field extending the
5074 1.1 christos regular ELF linker hash table. */
5075 1.1 christos
5076 1.1 christos /* This structure keeps track of the number of PC relative relocs we have
5077 1.1 christos copied for a given symbol. */
5078 1.1 christos
5079 1.1 christos struct bfin_pcrel_relocs_copied
5080 1.1 christos {
5081 1.1 christos /* Next section. */
5082 1.1 christos struct bfin_pcrel_relocs_copied *next;
5083 1.1 christos /* A section in dynobj. */
5084 1.1 christos asection *section;
5085 1.1 christos /* Number of relocs copied in this section. */
5086 1.1 christos bfd_size_type count;
5087 1.1 christos };
5088 1.1 christos
5089 1.1 christos /* This function is called via elf_link_hash_traverse if we are
5090 1.1 christos creating a shared object. In the -Bsymbolic case it discards the
5091 1.1 christos space allocated to copy PC relative relocs against symbols which
5092 1.1 christos are defined in regular objects. For the normal shared case, it
5093 1.1 christos discards space for pc-relative relocs that have become local due to
5094 1.1 christos symbol visibility changes. We allocated space for them in the
5095 1.1 christos check_relocs routine, but we won't fill them in in the
5096 1.1.1.10 christos relocate_section routine.
5097 1.1.1.2 christos
5098 1.1 christos We also check whether any of the remaining relocations apply
5099 1.1 christos against a readonly section, and set the DF_TEXTREL flag in this
5100 1.1 christos case. */
5101 1.1 christos
5102 1.1 christos static bool
5103 1.1 christos bfin_discard_copies (struct elf_link_hash_entry *h, void * inf)
5104 1.1 christos {
5105 1.1 christos struct bfd_link_info *info = (struct bfd_link_info *) inf;
5106 1.1 christos struct bfin_pcrel_relocs_copied *s;
5107 1.1 christos
5108 1.1 christos if (!h->def_regular || (!info->symbolic && !h->forced_local))
5109 1.1 christos {
5110 1.1 christos if ((info->flags & DF_TEXTREL) == 0)
5111 1.1 christos {
5112 1.1 christos /* Look for relocations against read-only sections. */
5113 1.1 christos for (s = bfin_hash_entry (h)->pcrel_relocs_copied;
5114 1.1 christos s != NULL; s = s->next)
5115 1.1 christos if ((s->section->flags & SEC_READONLY) != 0)
5116 1.1.1.10 christos {
5117 1.1 christos info->flags |= DF_TEXTREL;
5118 1.1 christos break;
5119 1.1 christos }
5120 1.1 christos }
5121 1.1 christos
5122 1.1 christos return true;
5123 1.1.1.10 christos }
5124 1.1 christos
5125 1.1 christos for (s = bfin_hash_entry (h)->pcrel_relocs_copied;
5126 1.1.1.10 christos s != NULL; s = s->next)
5127 1.1.1.11 christos s->section->size -= s->count * sizeof (Elf32_External_Rela);
5128 1.1.1.11 christos
5129 1.1 christos return true;
5130 1.1 christos }
5131 1.1 christos
5132 1.1.1.10 christos static bool
5133 1.1 christos bfin_late_size_sections (bfd * output_bfd ATTRIBUTE_UNUSED,
5134 1.1 christos struct bfd_link_info *info)
5135 1.1.1.11 christos {
5136 1.1.1.11 christos bfd *dynobj;
5137 1.1 christos asection *s;
5138 1.1 christos bool relocs;
5139 1.1 christos
5140 1.1 christos dynobj = elf_hash_table (info)->dynobj;
5141 1.1.1.8 christos if (dynobj == NULL)
5142 1.1 christos return true;
5143 1.1.1.2 christos
5144 1.1 christos if (elf_hash_table (info)->dynamic_sections_created)
5145 1.1 christos {
5146 1.1 christos /* Set the contents of the .interp section to the interpreter. */
5147 1.1 christos if (bfd_link_executable (info) && !info->nointerp)
5148 1.1 christos {
5149 1.1 christos s = bfd_get_linker_section (dynobj, ".interp");
5150 1.1 christos BFD_ASSERT (s != NULL);
5151 1.1 christos s->size = sizeof ELF_DYNAMIC_INTERPRETER;
5152 1.1.1.8 christos s->contents = (unsigned char *) ELF_DYNAMIC_INTERPRETER;
5153 1.1.1.8 christos }
5154 1.1.1.8 christos }
5155 1.1.1.8 christos else
5156 1.1.1.7 christos {
5157 1.1 christos /* We may have created entries in the .rela.got section.
5158 1.1 christos However, if we are not creating the dynamic sections, we will
5159 1.1 christos not actually use these entries. Reset the size of .rela.got,
5160 1.1 christos which will cause it to get stripped from the output file
5161 1.1 christos below. */
5162 1.1 christos s = elf_hash_table (info)->srelgot;
5163 1.1 christos if (s != NULL)
5164 1.1 christos s->size = 0;
5165 1.1 christos }
5166 1.1 christos
5167 1.1.1.6 christos /* If this is a -Bsymbolic shared link, then we need to discard all
5168 1.1 christos PC relative relocs against symbols defined in a regular object.
5169 1.1.1.2 christos For the normal shared case we discard the PC relative relocs
5170 1.1 christos against symbols that have become local due to visibility changes.
5171 1.1 christos We allocated space for them in the check_relocs routine, but we
5172 1.1 christos will not fill them in in the relocate_section routine. */
5173 1.1 christos if (bfd_link_pic (info))
5174 1.1.1.10 christos elf_link_hash_traverse (elf_hash_table (info),
5175 1.1 christos bfin_discard_copies, info);
5176 1.1 christos
5177 1.1 christos /* The check_relocs and adjust_dynamic_symbol entry points have
5178 1.1.1.10 christos determined the sizes of the various dynamic sections. Allocate
5179 1.1 christos memory for them. */
5180 1.1 christos relocs = false;
5181 1.1 christos for (s = dynobj->sections; s != NULL; s = s->next)
5182 1.1 christos {
5183 1.1 christos const char *name;
5184 1.1.1.8 christos bool strip;
5185 1.1.1.9 christos
5186 1.1 christos if ((s->flags & SEC_LINKER_CREATED) == 0)
5187 1.1.1.10 christos continue;
5188 1.1 christos
5189 1.1.1.10 christos /* It's OK to base decisions on the section name, because none
5190 1.1 christos of the dynobj section names depend upon the input files. */
5191 1.1 christos name = bfd_section_name (s);
5192 1.1 christos
5193 1.1 christos strip = false;
5194 1.1.1.8 christos
5195 1.1.1.8 christos if (startswith (name, ".rela"))
5196 1.1.1.8 christos {
5197 1.1.1.8 christos if (s->size == 0)
5198 1.1.1.8 christos {
5199 1.1.1.8 christos /* If we don't need this section, strip it from the
5200 1.1.1.8 christos output file. This is mostly to handle .rela.bss and
5201 1.1.1.8 christos .rela.plt. We must create both sections in
5202 1.1.1.10 christos create_dynamic_sections, because they must be created
5203 1.1 christos before the linker maps input sections to output
5204 1.1 christos sections. The linker does that before
5205 1.1 christos adjust_dynamic_symbol is called, and it is that
5206 1.1.1.10 christos function which decides whether anything needs to go
5207 1.1 christos into these sections. */
5208 1.1 christos strip = true;
5209 1.1.1.8 christos }
5210 1.1 christos else
5211 1.1 christos {
5212 1.1 christos relocs = true;
5213 1.1.1.10 christos
5214 1.1 christos /* We use the reloc_count field as a counter if we need
5215 1.1 christos to copy relocs into the output file. */
5216 1.1 christos s->reloc_count = 0;
5217 1.1 christos }
5218 1.1 christos }
5219 1.1 christos else if (! startswith (name, ".got"))
5220 1.1 christos {
5221 1.1 christos /* It's not one of our sections, so don't allocate space. */
5222 1.1 christos continue;
5223 1.1 christos }
5224 1.1 christos
5225 1.1 christos if (strip)
5226 1.1 christos {
5227 1.1.1.8 christos s->flags |= SEC_EXCLUDE;
5228 1.1.1.8 christos continue;
5229 1.1.1.8 christos }
5230 1.1.1.8 christos
5231 1.1 christos /* Allocate memory for the section contents. */
5232 1.1 christos /* FIXME: This should be a call to bfd_alloc not bfd_zalloc.
5233 1.1.1.10 christos Unused entries should be reclaimed before the section's contents
5234 1.1 christos are written out, but at the moment this does not happen. Thus in
5235 1.1 christos order to prevent writing out garbage, we initialise the section's
5236 1.1 christos contents to zero. */
5237 1.1 christos s->contents = (bfd_byte *) bfd_zalloc (dynobj, s->size);
5238 1.1 christos if (s->contents == NULL && s->size != 0)
5239 1.1.1.8 christos return false;
5240 1.1.1.8 christos }
5241 1.1.1.8 christos
5242 1.1.1.8 christos if (elf_hash_table (info)->dynamic_sections_created)
5243 1.1 christos {
5244 1.1 christos /* Add some entries to the .dynamic section. We fill in the
5245 1.1 christos values later, in bfin_finish_dynamic_sections, but we
5246 1.1.1.6 christos must add the entries now so that we get the correct size for
5247 1.1 christos the .dynamic section. The DT_DEBUG entry is filled in by the
5248 1.1 christos dynamic linker and used by the debugger. */
5249 1.1.1.10 christos #define add_dynamic_entry(TAG, VAL) \
5250 1.1 christos _bfd_elf_add_dynamic_entry (info, TAG, VAL)
5251 1.1 christos
5252 1.1 christos if (!bfd_link_pic (info))
5253 1.1 christos {
5254 1.1 christos if (!add_dynamic_entry (DT_DEBUG, 0))
5255 1.1 christos return false;
5256 1.1 christos }
5257 1.1 christos
5258 1.1 christos
5259 1.1.1.10 christos if (relocs)
5260 1.1 christos {
5261 1.1 christos if (!add_dynamic_entry (DT_RELA, 0)
5262 1.1 christos || !add_dynamic_entry (DT_RELASZ, 0)
5263 1.1 christos || !add_dynamic_entry (DT_RELAENT,
5264 1.1 christos sizeof (Elf32_External_Rela)))
5265 1.1.1.10 christos return false;
5266 1.1 christos }
5267 1.1 christos
5268 1.1 christos if ((info->flags & DF_TEXTREL) != 0)
5269 1.1 christos {
5270 1.1.1.10 christos if (!add_dynamic_entry (DT_TEXTREL, 0))
5271 1.1 christos return false;
5272 1.1 christos }
5273 1.1 christos }
5274 1.1 christos #undef add_dynamic_entry
5275 1.1 christos
5276 1.1 christos return true;
5277 1.1 christos }
5278 1.1 christos
5279 1.1 christos /* Given a .data section and a .emreloc in-memory section, store
5281 1.1.1.2 christos relocation information into the .emreloc section which can be
5282 1.1.1.2 christos used at runtime to relocate the section. This is called by the
5283 1.1.1.2 christos linker when the --embedded-relocs switch is used. This is called
5284 1.1.1.2 christos after the add_symbols entry point has been called for all the
5285 1.1.1.2 christos objects, and before the final_link entry point is called. */
5286 1.1 christos
5287 1.1 christos bool
5288 1.1 christos bfd_bfin_elf32_create_embedded_relocs (bfd *abfd,
5289 1.1 christos struct bfd_link_info *info,
5290 1.1 christos asection *datasec,
5291 1.1 christos asection *relsec,
5292 1.1 christos char **errmsg)
5293 1.1 christos {
5294 1.1.1.6 christos Elf_Internal_Shdr *symtab_hdr;
5295 1.1 christos Elf_Internal_Sym *isymbuf = NULL;
5296 1.1 christos Elf_Internal_Rela *internal_relocs = NULL;
5297 1.1 christos Elf_Internal_Rela *irel, *irelend;
5298 1.1 christos bfd_byte *p;
5299 1.1.1.10 christos bfd_size_type amt;
5300 1.1 christos
5301 1.1 christos BFD_ASSERT (! bfd_link_relocatable (info));
5302 1.1 christos
5303 1.1 christos *errmsg = NULL;
5304 1.1 christos
5305 1.1.1.2 christos if (datasec->reloc_count == 0)
5306 1.1 christos return true;
5307 1.1 christos
5308 1.1 christos symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
5309 1.1 christos
5310 1.1 christos /* Get a copy of the native relocations. */
5311 1.1 christos internal_relocs = (_bfd_elf_link_read_relocs
5312 1.1 christos (abfd, datasec, NULL, (Elf_Internal_Rela *) NULL,
5313 1.1 christos info->keep_memory));
5314 1.1 christos if (internal_relocs == NULL)
5315 1.1 christos goto error_return;
5316 1.1 christos
5317 1.1 christos amt = (bfd_size_type) datasec->reloc_count * 12;
5318 1.1 christos relsec->contents = (bfd_byte *) bfd_alloc (abfd, amt);
5319 1.1 christos if (relsec->contents == NULL)
5320 1.1 christos goto error_return;
5321 1.1 christos
5322 1.1 christos p = relsec->contents;
5323 1.1 christos
5324 1.1 christos irelend = internal_relocs + datasec->reloc_count;
5325 1.1 christos for (irel = internal_relocs; irel < irelend; irel++, p += 12)
5326 1.1 christos {
5327 1.1 christos asection *targetsec;
5328 1.1 christos
5329 1.1 christos /* We are going to write a four byte longword into the runtime
5330 1.1 christos reloc section. The longword will be the address in the data
5331 1.1.1.8 christos section which must be relocated. It is followed by the name
5332 1.1 christos of the target section NUL-padded or truncated to 8
5333 1.1 christos characters. */
5334 1.1 christos
5335 1.1 christos /* We can only relocate absolute longword relocs at run time. */
5336 1.1 christos if (ELF32_R_TYPE (irel->r_info) != (int) R_BFIN_BYTE4_DATA)
5337 1.1 christos {
5338 1.1 christos *errmsg = _("unsupported relocation type");
5339 1.1 christos bfd_set_error (bfd_error_bad_value);
5340 1.1 christos goto error_return;
5341 1.1 christos }
5342 1.1 christos
5343 1.1 christos /* Get the target section referred to by the reloc. */
5344 1.1 christos if (ELF32_R_SYM (irel->r_info) < symtab_hdr->sh_info)
5345 1.1 christos {
5346 1.1 christos /* A local symbol. */
5347 1.1 christos Elf_Internal_Sym *isym;
5348 1.1 christos
5349 1.1 christos /* Read this BFD's local symbols if we haven't done so already. */
5350 1.1 christos if (isymbuf == NULL)
5351 1.1 christos {
5352 1.1 christos isymbuf = (Elf_Internal_Sym *) symtab_hdr->contents;
5353 1.1 christos if (isymbuf == NULL)
5354 1.1 christos isymbuf = bfd_elf_get_elf_syms (abfd, symtab_hdr,
5355 1.1 christos symtab_hdr->sh_info, 0,
5356 1.1 christos NULL, NULL, NULL);
5357 1.1 christos if (isymbuf == NULL)
5358 1.1 christos goto error_return;
5359 1.1 christos }
5360 1.1 christos
5361 1.1 christos isym = isymbuf + ELF32_R_SYM (irel->r_info);
5362 1.1 christos targetsec = bfd_section_from_elf_index (abfd, isym->st_shndx);
5363 1.1 christos }
5364 1.1 christos else
5365 1.1 christos {
5366 1.1 christos unsigned long indx;
5367 1.1 christos struct elf_link_hash_entry *h;
5368 1.1 christos
5369 1.1 christos /* An external symbol. */
5370 1.1 christos indx = ELF32_R_SYM (irel->r_info) - symtab_hdr->sh_info;
5371 1.1 christos h = elf_sym_hashes (abfd)[indx];
5372 1.1 christos BFD_ASSERT (h != NULL);
5373 1.1 christos if (h->root.type == bfd_link_hash_defined
5374 1.1 christos || h->root.type == bfd_link_hash_defweak)
5375 1.1 christos targetsec = h->root.u.def.section;
5376 1.1 christos else
5377 1.1 christos targetsec = NULL;
5378 1.1 christos }
5379 1.1.1.9 christos
5380 1.1 christos bfd_put_32 (abfd, irel->r_offset + datasec->output_offset, p);
5381 1.1.1.9 christos memset (p + 4, 0, 8);
5382 1.1 christos if (targetsec != NULL)
5383 1.1.1.10 christos strncpy ((char *) p + 4, targetsec->output_section->name, 8);
5384 1.1 christos }
5385 1.1.1.9 christos
5386 1.1.1.9 christos if (symtab_hdr->contents != (unsigned char *) isymbuf)
5387 1.1 christos free (isymbuf);
5388 1.1.1.9 christos if (elf_section_data (datasec)->relocs != internal_relocs)
5389 1.1 christos free (internal_relocs);
5390 1.1.1.10 christos return true;
5391 1.1 christos
5392 1.1 christos error_return:
5393 1.1 christos if (symtab_hdr->contents != (unsigned char *) isymbuf)
5394 1.1 christos free (isymbuf);
5395 1.1 christos if (elf_section_data (datasec)->relocs != internal_relocs)
5396 1.1 christos free (internal_relocs);
5397 1.1.1.8 christos return false;
5398 1.1 christos }
5399 1.1 christos
5400 1.1 christos struct bfd_elf_special_section const elf32_bfin_special_sections[] =
5401 1.1.1.4 christos {
5402 1.1 christos { ".l1.text", 8, -2, SHT_PROGBITS, SHF_ALLOC + SHF_EXECINSTR },
5403 1.1 christos { ".l1.data", 8, -2, SHT_PROGBITS, SHF_ALLOC + SHF_WRITE },
5404 1.1 christos { NULL, 0, 0, 0, 0 }
5405 1.1 christos };
5406 1.1 christos
5407 1.1 christos
5408 1.1 christos #define TARGET_LITTLE_SYM bfin_elf32_vec
5410 1.1 christos #define TARGET_LITTLE_NAME "elf32-bfin"
5411 1.1 christos #define ELF_ARCH bfd_arch_bfin
5412 1.1 christos #define ELF_TARGET_ID BFIN_ELF_DATA
5413 1.1.1.8 christos #define ELF_MACHINE_CODE EM_BLACKFIN
5414 1.1 christos #define ELF_MAXPAGESIZE 0x1000
5415 1.1 christos #define elf_symbol_leading_char '_'
5416 1.1 christos
5417 1.1.1.8 christos #define bfd_elf32_bfd_reloc_type_lookup bfin_bfd_reloc_type_lookup
5418 1.1 christos #define bfd_elf32_bfd_reloc_name_lookup \
5419 1.1 christos bfin_bfd_reloc_name_lookup
5420 1.1.1.8 christos #define elf_info_to_howto bfin_info_to_howto
5421 1.1 christos #define elf_info_to_howto_rel NULL
5422 1.1.1.8 christos #define elf_backend_object_p elf32_bfin_object_p
5423 1.1.1.8 christos
5424 1.1 christos #define bfd_elf32_bfd_is_local_label_name \
5425 1.1.1.8 christos bfin_is_local_label_name
5426 1.1 christos
5427 1.1.1.8 christos #define elf_backend_create_dynamic_sections \
5428 1.1.1.11 christos _bfd_elf_create_dynamic_sections
5429 1.1.1.8 christos #define bfd_elf32_bfd_link_hash_table_create \
5430 1.1 christos bfin_link_hash_table_create
5431 1.1.1.8 christos #define bfd_elf32_bfd_final_link bfd_elf_gc_common_final_link
5432 1.1 christos
5433 1.1.1.8 christos #define elf_backend_check_relocs bfin_check_relocs
5434 1.1.1.8 christos #define elf_backend_adjust_dynamic_symbol \
5435 1.1 christos bfin_adjust_dynamic_symbol
5436 1.1.1.8 christos #define elf_backend_late_size_sections bfin_late_size_sections
5437 1.1 christos #define elf_backend_relocate_section bfin_relocate_section
5438 1.1.1.8 christos #define elf_backend_finish_dynamic_symbol \
5439 1.1 christos bfin_finish_dynamic_symbol
5440 1.1.1.8 christos #define elf_backend_finish_dynamic_sections \
5441 1.1 christos bfin_finish_dynamic_sections
5442 1.1.1.8 christos #define elf_backend_gc_mark_hook bfin_gc_mark_hook
5443 1.1.1.8 christos #define bfd_elf32_bfd_merge_private_bfd_data \
5444 1.1.1.2 christos elf32_bfin_merge_private_bfd_data
5445 1.1 christos #define bfd_elf32_bfd_set_private_flags \
5446 1.1 christos elf32_bfin_set_private_flags
5447 1.1 christos #define bfd_elf32_bfd_print_private_bfd_data \
5448 1.1 christos elf32_bfin_print_private_bfd_data
5449 1.1 christos #define elf_backend_final_write_processing \
5450 1.1 christos elf32_bfin_final_write_processing
5451 1.1.1.8 christos #define elf_backend_reloc_type_class elf32_bfin_reloc_type_class
5452 1.1.1.8 christos #define elf_backend_stack_align 8
5453 1.1 christos #define elf_backend_can_gc_sections 1
5454 1.1 christos #define elf_backend_special_sections elf32_bfin_special_sections
5455 1.1 christos #define elf_backend_can_refcount 1
5456 1.1 christos #define elf_backend_want_got_plt 0
5457 1.1.1.8 christos #define elf_backend_plt_readonly 1
5458 1.1 christos #define elf_backend_want_plt_sym 0
5459 1.1 christos #define elf_backend_got_header_size 12
5460 1.1 christos #define elf_backend_rela_normal 1
5461 1.1.1.8 christos
5462 1.1 christos #include "elf32-target.h"
5463 1.1 christos
5464 1.1.1.8 christos #undef TARGET_LITTLE_SYM
5465 1.1 christos #define TARGET_LITTLE_SYM bfin_elf32_fdpic_vec
5466 1.1 christos #undef TARGET_LITTLE_NAME
5467 1.1.1.8 christos #define TARGET_LITTLE_NAME "elf32-bfinfdpic"
5468 1.1 christos #undef elf32_bed
5469 1.1.1.8 christos #define elf32_bed elf32_bfinfdpic_bed
5470 1.1 christos
5471 1.1 christos #undef elf_backend_got_header_size
5472 1.1 christos #define elf_backend_got_header_size 0
5473 1.1 christos
5474 1.1.1.11 christos #undef elf_backend_relocate_section
5475 1.1.1.11 christos #define elf_backend_relocate_section bfinfdpic_relocate_section
5476 1.1.1.11 christos #undef elf_backend_check_relocs
5477 1.1 christos #define elf_backend_check_relocs bfinfdpic_check_relocs
5478 1.1 christos
5479 1.1 christos #undef bfd_elf32_bfd_link_hash_table_create
5480 1.1 christos #define bfd_elf32_bfd_link_hash_table_create \
5481 1.1 christos bfinfdpic_elf_link_hash_table_create
5482 1.1 christos #undef elf_backend_early_size_sections
5483 1.1 christos #define elf_backend_early_size_sections \
5484 1.1.1.11 christos elf32_bfinfdpic_early_size_sections
5485 1.1.1.11 christos
5486 1.1.1.11 christos #undef elf_backend_create_dynamic_sections
5487 1.1 christos #define elf_backend_create_dynamic_sections \
5488 1.1 christos elf32_bfinfdpic_create_dynamic_sections
5489 1.1 christos #undef elf_backend_adjust_dynamic_symbol
5490 1.1 christos #define elf_backend_adjust_dynamic_symbol \
5491 1.1 christos elf32_bfinfdpic_adjust_dynamic_symbol
5492 1.1 christos #undef elf_backend_late_size_sections
5493 1.1 christos #define elf_backend_late_size_sections \
5494 1.1 christos elf32_bfinfdpic_late_size_sections
5495 1.1 christos #undef elf_backend_finish_dynamic_symbol
5496 1.1 christos #define elf_backend_finish_dynamic_symbol \
5497 1.1 christos elf32_bfinfdpic_finish_dynamic_symbol
5498 1.1 christos #undef elf_backend_finish_dynamic_sections
5499 1.1 christos #define elf_backend_finish_dynamic_sections \
5500 1.1 christos elf32_bfinfdpic_finish_dynamic_sections
5501 1.1 christos
5502 1.1 christos #undef elf_backend_discard_info
5503 1.1 christos #define elf_backend_discard_info \
5504 1.1 christos bfinfdpic_elf_discard_info
5505 1.1 christos #undef elf_backend_can_make_relative_eh_frame
5506 1.1 christos #define elf_backend_can_make_relative_eh_frame \
5507 1.1 christos bfinfdpic_elf_use_relative_eh_frame
5508 1.1.1.8 christos #undef elf_backend_can_make_lsda_relative_eh_frame
5509 1.1 christos #define elf_backend_can_make_lsda_relative_eh_frame \
5510 1.1.1.8 christos bfinfdpic_elf_use_relative_eh_frame
5511 1.1 christos #undef elf_backend_encode_eh_address
5512 1.1 christos #define elf_backend_encode_eh_address \
5513 1.1.1.8 christos bfinfdpic_elf_encode_eh_address
5514 1.1 christos
5515 1.1 christos #undef elf_backend_may_use_rel_p
5516 1.1 christos #define elf_backend_may_use_rel_p 1
5517 1.1 christos #undef elf_backend_may_use_rela_p
5518 1.1 christos #define elf_backend_may_use_rela_p 1
5519 /* We use REL for dynamic relocations only. */
5520 #undef elf_backend_default_use_rela_p
5521 #define elf_backend_default_use_rela_p 1
5522
5523 #undef elf_backend_omit_section_dynsym
5524 #define elf_backend_omit_section_dynsym _bfinfdpic_link_omit_section_dynsym
5525
5526 #include "elf32-target.h"
5527