d00a7b2963e2b9a488b90a9d12be6e1734c3ed10
[deliverable/binutils-gdb.git] / bfd / elf32-ppc.c
1 /* PowerPC-specific support for 32-bit ELF
2 Copyright 1994, 1995 Free Software Foundation, Inc.
3 Written by Ian Lance Taylor, Cygnus Support.
4
5 This file is part of BFD, the Binary File Descriptor library.
6
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
11
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
20
21 /* This file is based on a preliminary PowerPC ELF ABI. The
22 information may not match the final PowerPC ELF ABI. It includes
23 suggestions from the in-progress Embedded PowerPC ABI, and that
24 information may also not match. */
25
26 #include "bfd.h"
27 #include "sysdep.h"
28 #include "libbfd.h"
29 #include "libelf.h"
30
31 static bfd_reloc_status_type ppc_elf_unsupported_reloc
32 PARAMS ((bfd *, arelent *, asymbol *, PTR, asection *, bfd *, char **));
33 static bfd_reloc_status_type ppc_elf_addr16_ha_reloc
34 PARAMS ((bfd *, arelent *, asymbol *, PTR, asection *, bfd *, char **));
35 static bfd_reloc_status_type ppc_elf_got16_reloc
36 PARAMS ((bfd *, arelent *, asymbol *, PTR, asection *, bfd *, char **));
37 static reloc_howto_type *bfd_elf32_bfd_reloc_type_lookup
38 PARAMS ((bfd *abfd, bfd_reloc_code_real_type code));
39 static void powerpc_info_to_howto
40 PARAMS ((bfd *abfd, arelent *cache_ptr, Elf32_Internal_Rela *dst));
41
42 #define USE_RELA
43
44 enum reloc_type
45 {
46 R_PPC_NONE = 0, /* 0 */
47 R_PPC_ADDR32, /* 1 */
48 R_PPC_ADDR24, /* 2 */
49 R_PPC_ADDR16, /* 3 */
50 R_PPC_ADDR16_LO, /* 4 */
51 R_PPC_ADDR16_HI, /* 5 */
52 R_PPC_ADDR16_HA, /* 6 */
53 R_PPC_ADDR14, /* 7 */
54 R_PPC_ADDR14_BRTAKEN, /* 8 */
55 R_PPC_ADDR14_BRNTAKEN, /* 9 */
56 R_PPC_REL24, /* 10 */
57 R_PPC_REL14, /* 11 */
58 R_PPC_REL14_BRTAKEN, /* 12 */
59 R_PPC_REL14_BRNTAKEN, /* 13 */
60 R_PPC_GOT16, /* 14 */
61 R_PPC_GOT16_LO, /* 15 */
62 R_PPC_GOT16_HI, /* 16 */
63 R_PPC_GOT16_HA, /* 17 */
64 R_PPC_PLT24, /* 18 */
65 R_PPC_COPY, /* 19 */
66 R_PPC_GLOB_DAT, /* 20 -- not in final System V spec */
67 R_PPC_JMP_SLOT, /* 21 */
68 R_PPC_RELATIVE, /* 22 */
69 R_PPC_LOCAL24PC, /* 23 */
70 R_PPC_UADDR32, /* 24 */
71 R_PPC_UADDR16, /* 25 */
72 R_PPC_REL32, /* 26 */
73 R_PPC_PLT32, /* 27 */
74 R_PPC_PLTREL32, /* 28 */
75 R_PPC_PLT16_LO, /* 29 */
76 R_PPC_PLT16_HI, /* 30 */
77 R_PPC_PLT16_HA, /* 31 */
78 R_PPC_SDAREL, /* 32 */
79
80 /* Relocations added by Sun. */
81 R_PPC_SECTOFF, /* 33 */
82 R_PPC_SECTOFF_LO, /* 34 */
83 R_PPC_SECTOFF_HI, /* 35 */
84 R_PPC_SECTOFF_HA, /* 36 */
85
86 /* The remaining relocs are from the Embedded ELF ABI, and are not
87 in the SVR4 ELF ABI. */
88 R_PPC_EMB_NADDR32 = 101, /* 101 */
89 R_PPC_EMB_NADDR16, /* 102 */
90 R_PPC_EMB_NADDR16_LO, /* 103 */
91 R_PPC_EMB_NADDR16_HI, /* 104 */
92 R_PPC_EMB_NADDR16_HA, /* 105 */
93 R_PPC_EMB_SDAI16, /* 106 */
94 R_PPC_EMB_SDA2I16, /* 107 */
95 R_PPC_EMB_SDA2REL, /* 108 */
96 R_PPC_EMB_SDA21, /* 109 */
97 R_PPC_EMB_MRKREF, /* 110 */
98 R_PPC_EMB_RELSEC16, /* 111 */
99 R_PPC_EMB_RELST_LO, /* 112 */
100 R_PPC_EMB_RELST_HI, /* 113 */
101 R_PPC_EMB_RELST_HA, /* 114 */
102 R_PPC_EMB_BIT_FLD, /* 115 */
103 R_PPC_EMB_RELSDA, /* 116 */
104 R_PPC_max
105 };
106
107 static reloc_howto_type elf_powerpc_howto_table[] =
108 {
109 /* This reloc does nothing. */
110 HOWTO (R_PPC_NONE, /* type */
111 0, /* rightshift */
112 2, /* size (0 = byte, 1 = short, 2 = long) */
113 32, /* bitsize */
114 false, /* pc_relative */
115 0, /* bitpos */
116 complain_overflow_bitfield, /* complain_on_overflow */
117 bfd_elf_generic_reloc, /* special_function */
118 "R_PPC_NONE", /* name */
119 false, /* partial_inplace */
120 0, /* src_mask */
121 0, /* dst_mask */
122 false), /* pcrel_offset */
123
124 /* A standard 32 bit relocation. */
125 HOWTO (R_PPC_ADDR32, /* type */
126 0, /* rightshift */
127 2, /* size (0 = byte, 1 = short, 2 = long) */
128 32, /* bitsize */
129 false, /* pc_relative */
130 0, /* bitpos */
131 complain_overflow_bitfield, /* complain_on_overflow */
132 bfd_elf_generic_reloc, /* special_function */
133 "R_PPC_ADDR32", /* name */
134 false, /* partial_inplace */
135 0, /* src_mask */
136 0xffffffff, /* dst_mask */
137 false), /* pcrel_offset */
138
139 /* An absolute 26 bit branch; the lower two bits must be zero.
140 FIXME: we don't check that, we just clear them. */
141 HOWTO (R_PPC_ADDR24, /* type */
142 0, /* rightshift */
143 2, /* size (0 = byte, 1 = short, 2 = long) */
144 26, /* bitsize */
145 false, /* pc_relative */
146 0, /* bitpos */
147 complain_overflow_bitfield, /* complain_on_overflow */
148 bfd_elf_generic_reloc, /* special_function */
149 "R_PPC_ADDR24", /* name */
150 false, /* partial_inplace */
151 0, /* src_mask */
152 0x3fffffc, /* dst_mask */
153 false), /* pcrel_offset */
154
155 /* A standard 16 bit relocation. */
156 HOWTO (R_PPC_ADDR16, /* type */
157 0, /* rightshift */
158 1, /* size (0 = byte, 1 = short, 2 = long) */
159 16, /* bitsize */
160 false, /* pc_relative */
161 0, /* bitpos */
162 complain_overflow_bitfield, /* complain_on_overflow */
163 bfd_elf_generic_reloc, /* special_function */
164 "R_PPC_ADDR16", /* name */
165 false, /* partial_inplace */
166 0, /* src_mask */
167 0xffff, /* dst_mask */
168 false), /* pcrel_offset */
169
170 /* A 16 bit relocation without overflow. */
171 HOWTO (R_PPC_ADDR16_LO, /* type */
172 0, /* rightshift */
173 1, /* size (0 = byte, 1 = short, 2 = long) */
174 16, /* bitsize */
175 false, /* pc_relative */
176 0, /* bitpos */
177 complain_overflow_dont,/* complain_on_overflow */
178 bfd_elf_generic_reloc, /* special_function */
179 "R_PPC_ADDR16_LO", /* name */
180 false, /* partial_inplace */
181 0, /* src_mask */
182 0xffff, /* dst_mask */
183 false), /* pcrel_offset */
184
185 /* The high order 16 bits of an address. */
186 HOWTO (R_PPC_ADDR16_HI, /* type */
187 16, /* rightshift */
188 1, /* size (0 = byte, 1 = short, 2 = long) */
189 16, /* bitsize */
190 false, /* pc_relative */
191 0, /* bitpos */
192 complain_overflow_dont, /* complain_on_overflow */
193 bfd_elf_generic_reloc, /* special_function */
194 "R_PPC_ADDR16_HI", /* name */
195 false, /* partial_inplace */
196 0, /* src_mask */
197 0xffff, /* dst_mask */
198 false), /* pcrel_offset */
199
200 /* The high order 16 bits of an address, plus 1 if the contents of
201 the low 16 bits, treated as a signed number, is negative. */
202 HOWTO (R_PPC_ADDR16_HA, /* type */
203 16, /* rightshift */
204 1, /* size (0 = byte, 1 = short, 2 = long) */
205 16, /* bitsize */
206 false, /* pc_relative */
207 0, /* bitpos */
208 complain_overflow_dont, /* complain_on_overflow */
209 ppc_elf_addr16_ha_reloc, /* special_function */
210 "R_PPC_ADDR16_HA", /* name */
211 false, /* partial_inplace */
212 0, /* src_mask */
213 0xffff, /* dst_mask */
214 false), /* pcrel_offset */
215
216 /* An absolute 16 bit branch; the lower two bits must be zero.
217 FIXME: we don't check that, we just clear them. */
218 HOWTO (R_PPC_ADDR14, /* type */
219 0, /* rightshift */
220 2, /* size (0 = byte, 1 = short, 2 = long) */
221 16, /* bitsize */
222 false, /* pc_relative */
223 0, /* bitpos */
224 complain_overflow_bitfield, /* complain_on_overflow */
225 bfd_elf_generic_reloc, /* special_function */
226 "R_PPC_ADDR14", /* name */
227 false, /* partial_inplace */
228 0, /* src_mask */
229 0xfffc, /* dst_mask */
230 false), /* pcrel_offset */
231
232 /* An absolute 16 bit branch, for which bit 10 should be set to
233 indicate that the branch is expected to be taken. The lower two
234 bits must be zero. */
235 HOWTO (R_PPC_ADDR14_BRTAKEN, /* type */
236 0, /* rightshift */
237 2, /* size (0 = byte, 1 = short, 2 = long) */
238 16, /* bitsize */
239 false, /* pc_relative */
240 0, /* bitpos */
241 complain_overflow_bitfield, /* complain_on_overflow */
242 ppc_elf_unsupported_reloc, /* special_function */
243 "R_PPC_ADDR14_BRTAKEN",/* name */
244 false, /* partial_inplace */
245 0, /* src_mask */
246 0xfffc, /* dst_mask */
247 false), /* pcrel_offset */
248
249 /* An absolute 16 bit branch, for which bit 10 should be set to
250 indicate that the branch is not expected to be taken. The lower
251 two bits must be zero. */
252 HOWTO (R_PPC_ADDR14_BRNTAKEN, /* type */
253 0, /* rightshift */
254 2, /* size (0 = byte, 1 = short, 2 = long) */
255 16, /* bitsize */
256 false, /* pc_relative */
257 0, /* bitpos */
258 complain_overflow_bitfield, /* complain_on_overflow */
259 ppc_elf_unsupported_reloc, /* special_function */
260 "R_PPC_ADDR14_BRNTAKEN",/* name */
261 false, /* partial_inplace */
262 0, /* src_mask */
263 0xfffc, /* dst_mask */
264 false), /* pcrel_offset */
265
266 /* A relative 26 bit branch; the lower two bits must be zero. */
267 HOWTO (R_PPC_REL24, /* type */
268 0, /* rightshift */
269 2, /* size (0 = byte, 1 = short, 2 = long) */
270 26, /* bitsize */
271 true, /* pc_relative */
272 0, /* bitpos */
273 complain_overflow_signed, /* complain_on_overflow */
274 bfd_elf_generic_reloc, /* special_function */
275 "R_PPC_REL24", /* name */
276 false, /* partial_inplace */
277 0, /* src_mask */
278 0x3fffffc, /* dst_mask */
279 true), /* pcrel_offset */
280
281 /* A relative 16 bit branch; the lower two bits must be zero. */
282 HOWTO (R_PPC_REL14, /* type */
283 0, /* rightshift */
284 2, /* size (0 = byte, 1 = short, 2 = long) */
285 16, /* bitsize */
286 true, /* pc_relative */
287 0, /* bitpos */
288 complain_overflow_signed, /* complain_on_overflow */
289 bfd_elf_generic_reloc, /* special_function */
290 "R_PPC_REL14", /* name */
291 false, /* partial_inplace */
292 0, /* src_mask */
293 0xfffc, /* dst_mask */
294 true), /* pcrel_offset */
295
296 /* A relative 16 bit branch. Bit 10 should be set to indicate that
297 the branch is expected to be taken. The lower two bits must be
298 zero. */
299 HOWTO (R_PPC_REL14_BRTAKEN, /* type */
300 0, /* rightshift */
301 2, /* size (0 = byte, 1 = short, 2 = long) */
302 16, /* bitsize */
303 false, /* pc_relative */
304 0, /* bitpos */
305 complain_overflow_signed, /* complain_on_overflow */
306 ppc_elf_unsupported_reloc, /* special_function */
307 "R_PPC_REL14_BRTAKEN", /* name */
308 false, /* partial_inplace */
309 0, /* src_mask */
310 0xfffc, /* dst_mask */
311 true), /* pcrel_offset */
312
313 /* A relative 16 bit branch. Bit 10 should be set to indicate that
314 the branch is not expected to be taken. The lower two bits must
315 be zero. */
316 HOWTO (R_PPC_REL14_BRNTAKEN, /* type */
317 0, /* rightshift */
318 2, /* size (0 = byte, 1 = short, 2 = long) */
319 16, /* bitsize */
320 false, /* pc_relative */
321 0, /* bitpos */
322 complain_overflow_signed, /* complain_on_overflow */
323 ppc_elf_unsupported_reloc, /* special_function */
324 "R_PPC_REL14_BRNTAKEN",/* name */
325 false, /* partial_inplace */
326 0, /* src_mask */
327 0xfffc, /* dst_mask */
328 true), /* pcrel_offset */
329
330 /* Like R_PPC_ADDR16, but referring to the GOT table entry for the
331 symbol. */
332 HOWTO (R_PPC_GOT16, /* type */
333 0, /* rightshift */
334 1, /* size (0 = byte, 1 = short, 2 = long) */
335 16, /* bitsize */
336 false, /* pc_relative */
337 0, /* bitpos */
338 complain_overflow_bitfield, /* complain_on_overflow */
339 ppc_elf_got16_reloc, /* special_function */
340 "R_PPC_GOT16", /* name */
341 false, /* partial_inplace */
342 0, /* src_mask */
343 0xffff, /* dst_mask */
344 false), /* pcrel_offset */
345
346 /* Like R_PPC_ADDR16_LO, but referring to the GOT table entry for
347 the symbol. */
348 HOWTO (R_PPC_GOT16_LO, /* type */
349 0, /* rightshift */
350 1, /* size (0 = byte, 1 = short, 2 = long) */
351 16, /* bitsize */
352 false, /* pc_relative */
353 0, /* bitpos */
354 complain_overflow_bitfield, /* complain_on_overflow */
355 ppc_elf_got16_reloc, /* special_function */
356 "R_PPC_GOT16_LO", /* name */
357 false, /* partial_inplace */
358 0, /* src_mask */
359 0xffff, /* dst_mask */
360 false), /* pcrel_offset */
361
362 /* Like R_PPC_ADDR16_HI, but referring to the GOT table entry for
363 the symbol. */
364 HOWTO (R_PPC_GOT16_HI, /* type */
365 16, /* rightshift */
366 1, /* size (0 = byte, 1 = short, 2 = long) */
367 16, /* bitsize */
368 false, /* pc_relative */
369 0, /* bitpos */
370 complain_overflow_bitfield, /* complain_on_overflow */
371 ppc_elf_got16_reloc, /* special_function */
372 "R_PPC_GOT16_HI", /* name */
373 false, /* partial_inplace */
374 0, /* src_mask */
375 0xffff, /* dst_mask */
376 false), /* pcrel_offset */
377
378 /* Like R_PPC_ADDR16_HA, but referring to the GOT table entry for
379 the symbol. FIXME: Not supported. */
380 HOWTO (R_PPC_GOT16_HA, /* type */
381 0, /* rightshift */
382 1, /* size (0 = byte, 1 = short, 2 = long) */
383 16, /* bitsize */
384 false, /* pc_relative */
385 0, /* bitpos */
386 complain_overflow_bitfield, /* complain_on_overflow */
387 ppc_elf_unsupported_reloc, /* special_function */
388 "R_PPC_GOT16_HA", /* name */
389 false, /* partial_inplace */
390 0, /* src_mask */
391 0xffff, /* dst_mask */
392 false), /* pcrel_offset */
393
394 /* Like R_PPC_REL24, but referring to the procedure linkage table
395 entry for the symbol. FIXME: Not supported. */
396 HOWTO (R_PPC_PLT24, /* type */
397 0, /* rightshift */
398 2, /* size (0 = byte, 1 = short, 2 = long) */
399 26, /* bitsize */
400 true, /* pc_relative */
401 0, /* bitpos */
402 complain_overflow_signed, /* complain_on_overflow */
403 bfd_elf_generic_reloc, /* special_function */
404 "R_PPC_PLT24", /* name */
405 false, /* partial_inplace */
406 0, /* src_mask */
407 0x3fffffc, /* dst_mask */
408 true), /* pcrel_offset */
409
410 /* This is used only by the dynamic linker. The symbol should exist
411 both in the object being run and in some shared library. The
412 dynamic linker copies the data addressed by the symbol from the
413 shared library into the object. I have no idea what the purpose
414 of this is. */
415 HOWTO (R_PPC_COPY, /* type */
416 0, /* rightshift */
417 2, /* size (0 = byte, 1 = short, 2 = long) */
418 32, /* bitsize */
419 false, /* pc_relative */
420 0, /* bitpos */
421 complain_overflow_bitfield, /* complain_on_overflow */
422 bfd_elf_generic_reloc, /* special_function */
423 "R_PPC_COPY", /* name */
424 false, /* partial_inplace */
425 0, /* src_mask */
426 0, /* dst_mask */
427 false), /* pcrel_offset */
428
429 /* Like R_PPC_ADDR32, but used when setting global offset table
430 entries. */
431 HOWTO (R_PPC_GLOB_DAT, /* type */
432 0, /* rightshift */
433 2, /* size (0 = byte, 1 = short, 2 = long) */
434 32, /* bitsize */
435 false, /* pc_relative */
436 0, /* bitpos */
437 complain_overflow_bitfield, /* complain_on_overflow */
438 bfd_elf_generic_reloc, /* special_function */
439 "R_PPC_GLOB_DAT", /* name */
440 false, /* partial_inplace */
441 0, /* src_mask */
442 0xffffffff, /* dst_mask */
443 false), /* pcrel_offset */
444
445 /* Marks a procedure linkage table entry for a symbol. */
446 HOWTO (R_PPC_JMP_SLOT, /* type */
447 0, /* rightshift */
448 2, /* size (0 = byte, 1 = short, 2 = long) */
449 32, /* bitsize */
450 false, /* pc_relative */
451 0, /* bitpos */
452 complain_overflow_bitfield, /* complain_on_overflow */
453 bfd_elf_generic_reloc, /* special_function */
454 "R_PPC_JMP_SLOT", /* name */
455 false, /* partial_inplace */
456 0, /* src_mask */
457 0, /* dst_mask */
458 false), /* pcrel_offset */
459
460 /* Used only by the dynamic linker. When the object is run, this
461 longword is set to the load address of the object, plus the
462 addend. */
463 HOWTO (R_PPC_RELATIVE, /* type */
464 0, /* rightshift */
465 2, /* size (0 = byte, 1 = short, 2 = long) */
466 32, /* bitsize */
467 false, /* pc_relative */
468 0, /* bitpos */
469 complain_overflow_bitfield, /* complain_on_overflow */
470 bfd_elf_generic_reloc, /* special_function */
471 "R_PPC_RELATIVE", /* name */
472 false, /* partial_inplace */
473 0, /* src_mask */
474 0xffffffff, /* dst_mask */
475 false), /* pcrel_offset */
476
477 /* Like R_PPC_REL24, but uses the value of the symbol within the
478 object rather than the final value. Normally used for
479 _GLOBAL_OFFSET_TABLE_. FIXME: Not supported. */
480 HOWTO (R_PPC_LOCAL24PC, /* type */
481 0, /* rightshift */
482 2, /* size (0 = byte, 1 = short, 2 = long) */
483 26, /* bitsize */
484 true, /* pc_relative */
485 0, /* bitpos */
486 complain_overflow_signed, /* complain_on_overflow */
487 ppc_elf_unsupported_reloc, /* special_function */
488 "R_PPC_LOCAL24PC", /* name */
489 false, /* partial_inplace */
490 0, /* src_mask */
491 0x3fffffc, /* dst_mask */
492 true), /* pcrel_offset */
493
494 /* Like R_PPC_ADDR32, but may be unaligned. */
495 HOWTO (R_PPC_UADDR32, /* type */
496 0, /* rightshift */
497 2, /* size (0 = byte, 1 = short, 2 = long) */
498 32, /* bitsize */
499 false, /* pc_relative */
500 0, /* bitpos */
501 complain_overflow_bitfield, /* complain_on_overflow */
502 bfd_elf_generic_reloc, /* special_function */
503 "R_PPC_UADDR32", /* name */
504 false, /* partial_inplace */
505 0, /* src_mask */
506 0xffffffff, /* dst_mask */
507 false), /* pcrel_offset */
508
509 /* Like R_PPC_ADDR16, but may be unaligned. */
510 HOWTO (R_PPC_UADDR16, /* type */
511 0, /* rightshift */
512 1, /* size (0 = byte, 1 = short, 2 = long) */
513 16, /* bitsize */
514 false, /* pc_relative */
515 0, /* bitpos */
516 complain_overflow_bitfield, /* complain_on_overflow */
517 bfd_elf_generic_reloc, /* special_function */
518 "R_PPC_UADDR16", /* name */
519 false, /* partial_inplace */
520 0, /* src_mask */
521 0xffff, /* dst_mask */
522 false), /* pcrel_offset */
523
524 /* 32-bit PC relative */
525 HOWTO (R_PPC_REL32, /* type */
526 0, /* rightshift */
527 2, /* size (0 = byte, 1 = short, 2 = long) */
528 32, /* bitsize */
529 true, /* pc_relative */
530 0, /* bitpos */
531 complain_overflow_bitfield, /* complain_on_overflow */
532 bfd_elf_generic_reloc, /* special_function */
533 "R_PPC_REL32", /* name */
534 false, /* partial_inplace */
535 0, /* src_mask */
536 0xffffffff, /* dst_mask */
537 true), /* pcrel_offset */
538
539 /* 32-bit relocation to the symbol's procedure linkage table.
540 FIXEME: not supported. */
541 HOWTO (R_PPC_PLT32, /* type */
542 0, /* rightshift */
543 2, /* size (0 = byte, 1 = short, 2 = long) */
544 32, /* bitsize */
545 false, /* pc_relative */
546 0, /* bitpos */
547 complain_overflow_bitfield, /* complain_on_overflow */
548 ppc_elf_unsupported_reloc, /* special_function */
549 "R_PPC_PLT32", /* name */
550 false, /* partial_inplace */
551 0, /* src_mask */
552 0, /* dst_mask */
553 false), /* pcrel_offset */
554
555 /* 32-bit PC relative relocation to the symbol's procedure linkage table.
556 FIXEME: not supported. */
557 HOWTO (R_PPC_PLTREL32, /* type */
558 0, /* rightshift */
559 2, /* size (0 = byte, 1 = short, 2 = long) */
560 32, /* bitsize */
561 true, /* pc_relative */
562 0, /* bitpos */
563 complain_overflow_bitfield, /* complain_on_overflow */
564 ppc_elf_unsupported_reloc, /* special_function */
565 "R_PPC_PLTREL32", /* name */
566 false, /* partial_inplace */
567 0, /* src_mask */
568 0, /* dst_mask */
569 true), /* pcrel_offset */
570
571 /* Like R_PPC_ADDR16_LO, but referring to the PLT table entry for
572 the symbol. */
573 HOWTO (R_PPC_PLT16_LO, /* type */
574 0, /* rightshift */
575 1, /* size (0 = byte, 1 = short, 2 = long) */
576 16, /* bitsize */
577 false, /* pc_relative */
578 0, /* bitpos */
579 complain_overflow_bitfield, /* complain_on_overflow */
580 ppc_elf_unsupported_reloc, /* special_function */
581 "R_PPC_PLT16_LO", /* name */
582 false, /* partial_inplace */
583 0, /* src_mask */
584 0xffff, /* dst_mask */
585 false), /* pcrel_offset */
586
587 /* Like R_PPC_ADDR16_HI, but referring to the PLT table entry for
588 the symbol. */
589 HOWTO (R_PPC_PLT16_HI, /* type */
590 16, /* rightshift */
591 1, /* size (0 = byte, 1 = short, 2 = long) */
592 16, /* bitsize */
593 false, /* pc_relative */
594 0, /* bitpos */
595 complain_overflow_bitfield, /* complain_on_overflow */
596 ppc_elf_unsupported_reloc, /* special_function */
597 "R_PPC_PLT16_HI", /* name */
598 false, /* partial_inplace */
599 0, /* src_mask */
600 0xffff, /* dst_mask */
601 false), /* pcrel_offset */
602
603 /* Like R_PPC_ADDR16_HA, but referring to the PLT table entry for
604 the symbol. FIXME: Not supported. */
605 HOWTO (R_PPC_PLT16_HA, /* type */
606 0, /* rightshift */
607 1, /* size (0 = byte, 1 = short, 2 = long) */
608 16, /* bitsize */
609 false, /* pc_relative */
610 0, /* bitpos */
611 complain_overflow_bitfield, /* complain_on_overflow */
612 ppc_elf_unsupported_reloc, /* special_function */
613 "R_PPC_PLT16_HA", /* name */
614 false, /* partial_inplace */
615 0, /* src_mask */
616 0xffff, /* dst_mask */
617 false), /* pcrel_offset */
618
619 /* A sign-extended 16 bit value relative to _SDA_BASE, for use with
620 small data items. */
621 HOWTO (R_PPC_SDAREL, /* type */
622 0, /* rightshift */
623 2, /* size (0 = byte, 1 = short, 2 = long) */
624 16, /* bitsize */
625 false, /* pc_relative */
626 0, /* bitpos */
627 complain_overflow_bitfield, /* complain_on_overflow */
628 ppc_elf_unsupported_reloc, /* special_function */
629 "R_PPC_SDAREL", /* name */
630 false, /* partial_inplace */
631 0, /* src_mask */
632 0xffff, /* dst_mask */
633 false), /* pcrel_offset */
634
635 /* These next 4 relocations were added by Sun. */
636 /* 32-bit section relative relocation. FIXME: not supported. */
637 HOWTO (R_PPC_SECTOFF, /* type */
638 0, /* rightshift */
639 2, /* size (0 = byte, 1 = short, 2 = long) */
640 32, /* bitsize */
641 true, /* pc_relative */
642 0, /* bitpos */
643 complain_overflow_bitfield, /* complain_on_overflow */
644 ppc_elf_unsupported_reloc, /* special_function */
645 "R_PPC_SECTOFF", /* name */
646 false, /* partial_inplace */
647 0, /* src_mask */
648 0, /* dst_mask */
649 true), /* pcrel_offset */
650
651 /* 16-bit lower half section relative relocation. FIXME: not supported. */
652 HOWTO (R_PPC_SECTOFF_LO, /* type */
653 0, /* rightshift */
654 1, /* size (0 = byte, 1 = short, 2 = long) */
655 16, /* bitsize */
656 false, /* pc_relative */
657 0, /* bitpos */
658 complain_overflow_bitfield, /* complain_on_overflow */
659 ppc_elf_unsupported_reloc, /* special_function */
660 "R_PPC_SECTOFF_LO", /* name */
661 false, /* partial_inplace */
662 0, /* src_mask */
663 0xffff, /* dst_mask */
664 false), /* pcrel_offset */
665
666 /* 16-bit upper half section relative relocation. FIXME: not supported. */
667 HOWTO (R_PPC_SECTOFF_HI, /* type */
668 16, /* rightshift */
669 1, /* size (0 = byte, 1 = short, 2 = long) */
670 16, /* bitsize */
671 false, /* pc_relative */
672 0, /* bitpos */
673 complain_overflow_bitfield, /* complain_on_overflow */
674 ppc_elf_unsupported_reloc, /* special_function */
675 "R_PPC_SECTOFF_HI", /* name */
676 false, /* partial_inplace */
677 0, /* src_mask */
678 0xffff, /* dst_mask */
679 false), /* pcrel_offset */
680
681 /* 16-bit upper half adjusted section relative relocation. FIXME: not supported. */
682 HOWTO (R_PPC_SECTOFF_HA, /* type */
683 0, /* rightshift */
684 1, /* size (0 = byte, 1 = short, 2 = long) */
685 16, /* bitsize */
686 false, /* pc_relative */
687 0, /* bitpos */
688 complain_overflow_bitfield, /* complain_on_overflow */
689 ppc_elf_unsupported_reloc, /* special_function */
690 "R_PPC_SECTOFF_HA", /* name */
691 false, /* partial_inplace */
692 0, /* src_mask */
693 0xffff, /* dst_mask */
694 false), /* pcrel_offset */
695
696 /* The remaining relocs are from the Embedded ELF ABI, and are not
697 in the SVR4 ELF ABI. */
698
699 /* 32 bit value resulting from the addend minus the symbol */
700 HOWTO (R_PPC_EMB_NADDR32, /* type */
701 0, /* rightshift */
702 2, /* size (0 = byte, 1 = short, 2 = long) */
703 32, /* bitsize */
704 false, /* pc_relative */
705 0, /* bitpos */
706 complain_overflow_bitfield, /* complain_on_overflow */
707 ppc_elf_unsupported_reloc, /* special_function */
708 "R_PPC_EMB_NADDR32", /* name */
709 false, /* partial_inplace */
710 0, /* src_mask */
711 0xffffffff, /* dst_mask */
712 false), /* pcrel_offset */
713
714 /* 16 bit value resulting from the addend minus the symbol */
715 HOWTO (R_PPC_EMB_NADDR16, /* type */
716 0, /* rightshift */
717 1, /* size (0 = byte, 1 = short, 2 = long) */
718 16, /* bitsize */
719 false, /* pc_relative */
720 0, /* bitpos */
721 complain_overflow_bitfield, /* complain_on_overflow */
722 ppc_elf_unsupported_reloc, /* special_function */
723 "R_PPC_EMB_NADDR16", /* name */
724 false, /* partial_inplace */
725 0, /* src_mask */
726 0xffff, /* dst_mask */
727 false), /* pcrel_offset */
728
729 /* 16 bit value resulting from the addend minus the symbol */
730 HOWTO (R_PPC_EMB_NADDR16_LO, /* type */
731 0, /* rightshift */
732 1, /* size (0 = byte, 1 = short, 2 = long) */
733 16, /* bitsize */
734 false, /* pc_relative */
735 0, /* bitpos */
736 complain_overflow_dont,/* complain_on_overflow */
737 ppc_elf_unsupported_reloc, /* special_function */
738 "R_PPC_EMB_ADDR16_LO", /* name */
739 false, /* partial_inplace */
740 0, /* src_mask */
741 0xffff, /* dst_mask */
742 false), /* pcrel_offset */
743
744 /* The high order 16 bits of the addend minus the symbol */
745 HOWTO (R_PPC_EMB_NADDR16_HI, /* type */
746 16, /* rightshift */
747 1, /* size (0 = byte, 1 = short, 2 = long) */
748 16, /* bitsize */
749 false, /* pc_relative */
750 0, /* bitpos */
751 complain_overflow_dont, /* complain_on_overflow */
752 ppc_elf_unsupported_reloc, /* special_function */
753 "R_PPC_EMB_NADDR16_HI", /* name */
754 false, /* partial_inplace */
755 0, /* src_mask */
756 0xffff, /* dst_mask */
757 false), /* pcrel_offset */
758
759 /* The high order 16 bits of the result of the addend minus the address,
760 plus 1 if the contents of the low 16 bits, treated as a signed number,
761 is negative. */
762 HOWTO (R_PPC_EMB_NADDR16_HA, /* type */
763 16, /* rightshift */
764 1, /* size (0 = byte, 1 = short, 2 = long) */
765 16, /* bitsize */
766 false, /* pc_relative */
767 0, /* bitpos */
768 complain_overflow_dont, /* complain_on_overflow */
769 ppc_elf_unsupported_reloc, /* special_function */
770 "R_PPC_EMB_NADDR16_HA", /* name */
771 false, /* partial_inplace */
772 0, /* src_mask */
773 0xffff, /* dst_mask */
774 false), /* pcrel_offset */
775 };
776
777 /* Don't pretend we can deal with unsupported relocs. */
778
779 /*ARGSUSED*/
780 static bfd_reloc_status_type
781 ppc_elf_unsupported_reloc (abfd, reloc_entry, symbol, data, input_section,
782 output_bfd, error_message)
783 bfd *abfd;
784 arelent *reloc_entry;
785 asymbol *symbol;
786 PTR data;
787 asection *input_section;
788 bfd *output_bfd;
789 char **error_message;
790 {
791 abort ();
792 }
793
794 /* Handle the ADDR16_HA reloc by adjusting the reloc addend. */
795
796 static bfd_reloc_status_type
797 ppc_elf_addr16_ha_reloc (abfd, reloc_entry, symbol, data, input_section,
798 output_bfd, error_message)
799 bfd *abfd;
800 arelent *reloc_entry;
801 asymbol *symbol;
802 PTR data;
803 asection *input_section;
804 bfd *output_bfd;
805 char **error_message;
806 {
807 bfd_vma relocation;
808
809 if (output_bfd != (bfd *) NULL)
810 return bfd_elf_generic_reloc (abfd, reloc_entry, symbol, data,
811 input_section, output_bfd, error_message);
812
813 if (bfd_is_com_section (symbol->section))
814 relocation = 0;
815 else
816 relocation = symbol->value;
817
818 relocation += (symbol->section->output_section->vma
819 + symbol->section->output_offset
820 + reloc_entry->addend);
821
822 if ((relocation & 0x8000) != 0)
823 reloc_entry->addend += 0x10000;
824
825 return bfd_reloc_continue;
826 }
827
828 /* Handle the GOT16 reloc. We want to use the offset within the .got
829 section, not the actual VMA. This is appropriate when generating
830 an embedded ELF object, for which the .got section acts like the
831 AIX .toc section. When and if we support PIC code, we will have to
832 change this, perhaps by switching off on the e_type field. */
833
834 static bfd_reloc_status_type
835 ppc_elf_got16_reloc (abfd, reloc_entry, symbol, data, input_section,
836 output_bfd, error_message)
837 bfd *abfd;
838 arelent *reloc_entry;
839 asymbol *symbol;
840 PTR data;
841 asection *input_section;
842 bfd *output_bfd;
843 char **error_message;
844 {
845 asection *sec;
846
847 if (output_bfd != (bfd *) NULL)
848 return bfd_elf_generic_reloc (abfd, reloc_entry, symbol, data,
849 input_section, output_bfd, error_message);
850
851 sec = bfd_get_section (*reloc_entry->sym_ptr_ptr);
852 BFD_ASSERT (bfd_is_und_section (sec)
853 || strcmp (bfd_get_section_name (abfd, sec), ".got") == 0
854 || strcmp (bfd_get_section_name (abfd, sec), ".cgot") == 0);
855 reloc_entry->addend -= sec->output_section->vma;
856 return bfd_reloc_continue;
857 }
858
859 /* Map BFD reloc types to PowerPC ELF reloc types. */
860
861 struct powerpc_reloc_map
862 {
863 unsigned char bfd_reloc_val;
864 unsigned char elf_reloc_val;
865 };
866
867 static const struct powerpc_reloc_map powerpc_reloc_map[] =
868 {
869 { BFD_RELOC_NONE, R_PPC_NONE, },
870 { BFD_RELOC_32, R_PPC_ADDR32 },
871 { BFD_RELOC_32_PCREL, R_PPC_REL32 },
872 { BFD_RELOC_CTOR, R_PPC_ADDR32 },
873 { BFD_RELOC_PPC_B26, R_PPC_REL24 },
874 { BFD_RELOC_PPC_BA26, R_PPC_ADDR24 },
875 { BFD_RELOC_PPC_TOC16, R_PPC_GOT16 },
876 { BFD_RELOC_LO16, R_PPC_ADDR16_LO },
877 { BFD_RELOC_HI16, R_PPC_ADDR16_HI },
878 { BFD_RELOC_HI16_S, R_PPC_ADDR16_HA }
879 };
880
881 static reloc_howto_type *
882 bfd_elf32_bfd_reloc_type_lookup (abfd, code)
883 bfd *abfd;
884 bfd_reloc_code_real_type code;
885 {
886 int i;
887
888 for (i = 0;
889 i < sizeof (powerpc_reloc_map) / sizeof (struct powerpc_reloc_map);
890 i++)
891 {
892 if (powerpc_reloc_map[i].bfd_reloc_val == code)
893 return &elf_powerpc_howto_table[powerpc_reloc_map[i].elf_reloc_val];
894 }
895
896 return NULL;
897 }
898
899 /* Set the howto pointer for a PowerPC ELF reloc. */
900
901 static void
902 powerpc_info_to_howto (abfd, cache_ptr, dst)
903 bfd *abfd;
904 arelent *cache_ptr;
905 Elf32_Internal_Rela *dst;
906 {
907 BFD_ASSERT (ELF32_R_TYPE (dst->r_info) < (unsigned int) R_PPC_max);
908 cache_ptr->howto = &elf_powerpc_howto_table[ELF32_R_TYPE (dst->r_info)];
909 }
910
911 #define TARGET_BIG_SYM bfd_elf32_powerpc_vec
912 #define TARGET_BIG_NAME "elf32-powerpc"
913 #define ELF_ARCH bfd_arch_powerpc
914 #define ELF_MACHINE_CODE EM_PPC
915 #define ELF_MAXPAGESIZE 0x10000
916 #define elf_info_to_howto powerpc_info_to_howto
917
918 #ifdef EM_CYGNUS_POWERPC
919 #define ELF_MACHINE_ALT1 EM_CYGNUS_POWERPC
920 #endif
921
922 #ifdef EM_PPC_OLD
923 #define ELF_MACHINE_ALT2 EM_PPC_OLD
924 #endif
925
926 #include "elf32-target.h"
This page took 0.059676 seconds and 4 git commands to generate.