2002-06-18 Dave Brolley <brolley@redhat.com>
[binutils.git] / bfd / elf32-mcore.c
blob38e9c13d13c09cff980adadc8e968d183fda618c
1 /* Motorola MCore specific support for 32-bit ELF
2 Copyright 1994, 1995, 1999, 2000, 2001, 2002
3 Free Software Foundation, Inc.
5 This file is part of BFD, the Binary File Descriptor library.
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
21 /* This file is based on a preliminary RCE ELF ABI. The
22 information may not match the final RCE ELF ABI. */
24 #include "bfd.h"
25 #include "sysdep.h"
26 #include "bfdlink.h"
27 #include "libbfd.h"
28 #include "elf-bfd.h"
29 #include "elf/mcore.h"
30 #include <assert.h>
32 #define USE_RELA /* Only USE_REL is actually significant, but this is
33 here are a reminder... */
35 static void mcore_elf_howto_init
36 PARAMS ((void));
37 static reloc_howto_type * mcore_elf_reloc_type_lookup
38 PARAMS ((bfd *, bfd_reloc_code_real_type));
39 static void mcore_elf_info_to_howto
40 PARAMS ((bfd *, arelent *, Elf32_Internal_Rela *));
41 static boolean mcore_elf_set_private_flags
42 PARAMS ((bfd *, flagword));
43 static boolean mcore_elf_merge_private_bfd_data
44 PARAMS ((bfd *, bfd *));
45 static bfd_reloc_status_type mcore_elf_unsupported_reloc
46 PARAMS ((bfd *, arelent *, asymbol *, PTR, asection *, bfd *, char **));
47 static boolean mcore_elf_relocate_section
48 PARAMS ((bfd *, struct bfd_link_info *, bfd *, asection *, bfd_byte *,
49 Elf_Internal_Rela *, Elf_Internal_Sym *, asection **));
50 static asection * mcore_elf_gc_mark_hook
51 PARAMS ((bfd *, struct bfd_link_info *, Elf_Internal_Rela *,
52 struct elf_link_hash_entry *, Elf_Internal_Sym *));
53 static boolean mcore_elf_gc_sweep_hook
54 PARAMS ((bfd *, struct bfd_link_info *, asection *,
55 const Elf_Internal_Rela *));
56 static boolean mcore_elf_check_relocs
57 PARAMS ((bfd *, struct bfd_link_info *, asection *,
58 const Elf_Internal_Rela *));
60 static reloc_howto_type * mcore_elf_howto_table [(int) R_MCORE_max];
62 static reloc_howto_type mcore_elf_howto_raw[] =
64 /* This reloc does nothing. */
65 HOWTO (R_MCORE_NONE, /* type */
66 0, /* rightshift */
67 2, /* size (0 = byte, 1 = short, 2 = long) */
68 32, /* bitsize */
69 false, /* pc_relative */
70 0, /* bitpos */
71 complain_overflow_bitfield, /* complain_on_overflow */
72 NULL, /* special_function */
73 "R_MCORE_NONE", /* name */
74 false, /* partial_inplace */
75 0, /* src_mask */
76 0, /* dst_mask */
77 false), /* pcrel_offset */
79 /* A standard 32 bit relocation. */
80 HOWTO (R_MCORE_ADDR32, /* type */
81 0, /* rightshift */
82 2, /* size (0 = byte, 1 = short, 2 = long) */
83 32, /* bitsize */
84 false, /* pc_relative */
85 0, /* bitpos */
86 complain_overflow_bitfield, /* complain_on_overflow */
87 bfd_elf_generic_reloc, /* special_function */
88 "ADDR32", /* name *//* For compatability with coff/pe port. */
89 false, /* partial_inplace */
90 0x0, /* src_mask */
91 0xffffffff, /* dst_mask */
92 false), /* pcrel_offset */
94 /* 8 bits + 2 zero bits; jmpi/jsri/lrw instructions.
95 Should not appear in object files. */
96 HOWTO (R_MCORE_PCRELIMM8BY4, /* type */
97 2, /* rightshift */
98 1, /* size (0 = byte, 1 = short, 2 = long) */
99 8, /* bitsize */
100 true, /* pc_relative */
101 0, /* bitpos */
102 complain_overflow_bitfield, /* complain_on_overflow */
103 mcore_elf_unsupported_reloc, /* special_function */
104 "R_MCORE_PCRELIMM8BY4",/* name */
105 false, /* partial_inplace */
106 0, /* src_mask */
107 0, /* dst_mask */
108 true), /* pcrel_offset */
110 /* bsr/bt/bf/br instructions; 11 bits + 1 zero bit
111 Span 2k instructions == 4k bytes.
112 Only useful pieces at the relocated address are the opcode (5 bits) */
113 HOWTO (R_MCORE_PCRELIMM11BY2,/* type */
114 1, /* rightshift */
115 1, /* size (0 = byte, 1 = short, 2 = long) */
116 11, /* bitsize */
117 true, /* pc_relative */
118 0, /* bitpos */
119 complain_overflow_signed, /* complain_on_overflow */
120 bfd_elf_generic_reloc, /* special_function */
121 "R_MCORE_PCRELIMM11BY2",/* name */
122 false, /* partial_inplace */
123 0x0, /* src_mask */
124 0x7ff, /* dst_mask */
125 true), /* pcrel_offset */
127 /* 4 bits + 1 zero bit; 'loopt' instruction only; unsupported. */
128 HOWTO (R_MCORE_PCRELIMM4BY2, /* type */
129 1, /* rightshift */
130 1, /* size (0 = byte, 1 = short, 2 = long) */
131 4, /* bitsize */
132 true, /* pc_relative */
133 0, /* bitpos */
134 complain_overflow_bitfield, /* complain_on_overflow */
135 mcore_elf_unsupported_reloc,/* special_function */
136 "R_MCORE_PCRELIMM4BY2",/* name */
137 false, /* partial_inplace */
138 0, /* src_mask */
139 0, /* dst_mask */
140 true), /* pcrel_offset */
142 /* 32-bit pc-relative. Eventually this will help support PIC code. */
143 HOWTO (R_MCORE_PCREL32, /* type */
144 0, /* rightshift */
145 2, /* size (0 = byte, 1 = short, 2 = long) */
146 32, /* bitsize */
147 true, /* pc_relative */
148 0, /* bitpos */
149 complain_overflow_bitfield, /* complain_on_overflow */
150 bfd_elf_generic_reloc, /* special_function */
151 "R_MCORE_PCREL32", /* name */
152 false, /* partial_inplace */
153 0x0, /* src_mask */
154 0xffffffff, /* dst_mask */
155 true), /* pcrel_offset */
157 /* Like PCRELIMM11BY2, this relocation indicates that there is a
158 'jsri' at the specified address. There is a separate relocation
159 entry for the literal pool entry that it references, but we
160 might be able to change the jsri to a bsr if the target turns out
161 to be close enough [even though we won't reclaim the literal pool
162 entry, we'll get some runtime efficiency back]. Note that this
163 is a relocation that we are allowed to safely ignore. */
164 HOWTO (R_MCORE_PCRELJSR_IMM11BY2,/* type */
165 1, /* rightshift */
166 1, /* size (0 = byte, 1 = short, 2 = long) */
167 11, /* bitsize */
168 true, /* pc_relative */
169 0, /* bitpos */
170 complain_overflow_signed, /* complain_on_overflow */
171 bfd_elf_generic_reloc, /* special_function */
172 "R_MCORE_PCRELJSR_IMM11BY2", /* name */
173 false, /* partial_inplace */
174 0x0, /* src_mask */
175 0x7ff, /* dst_mask */
176 true), /* pcrel_offset */
178 /* GNU extension to record C++ vtable hierarchy */
179 HOWTO (R_MCORE_GNU_VTINHERIT, /* type */
180 0, /* rightshift */
181 2, /* size (0 = byte, 1 = short, 2 = long) */
182 0, /* bitsize */
183 false, /* pc_relative */
184 0, /* bitpos */
185 complain_overflow_dont, /* complain_on_overflow */
186 NULL, /* special_function */
187 "R_MCORE_GNU_VTINHERIT", /* name */
188 false, /* partial_inplace */
189 0, /* src_mask */
190 0, /* dst_mask */
191 false), /* pcrel_offset */
193 /* GNU extension to record C++ vtable member usage */
194 HOWTO (R_MCORE_GNU_VTENTRY, /* type */
195 0, /* rightshift */
196 2, /* size (0 = byte, 1 = short, 2 = long) */
197 0, /* bitsize */
198 false, /* pc_relative */
199 0, /* bitpos */
200 complain_overflow_dont,/* complain_on_overflow */
201 _bfd_elf_rel_vtable_reloc_fn, /* special_function */
202 "R_MCORE_GNU_VTENTRY", /* name */
203 false, /* partial_inplace */
204 0, /* src_mask */
205 0, /* dst_mask */
206 false), /* pcrel_offset */
208 HOWTO (R_MCORE_RELATIVE, /* type */
209 0, /* rightshift */
210 2, /* size (0 = byte, 1 = short, 2 = long) */
211 32, /* bitsize */
212 false, /* pc_relative */
213 0, /* bitpos */
214 complain_overflow_signed, /* complain_on_overflow */
215 NULL, /* special_function */
216 "R_MCORE_RELATIVE", /* name */
217 true, /* partial_inplace */
218 0xffffffff, /* src_mask */
219 0xffffffff, /* dst_mask */
220 false) /* pcrel_offset */
223 #ifndef NUM_ELEM
224 #define NUM_ELEM(a) (sizeof (a) / sizeof (a)[0])
225 #endif
227 /* Initialize the mcore_elf_howto_table, so that linear accesses can be done. */
228 static void
229 mcore_elf_howto_init ()
231 unsigned int i;
233 for (i = NUM_ELEM (mcore_elf_howto_raw); i--;)
235 unsigned int type;
237 type = mcore_elf_howto_raw[i].type;
239 BFD_ASSERT (type < NUM_ELEM (mcore_elf_howto_table));
241 mcore_elf_howto_table [type] = & mcore_elf_howto_raw [i];
245 static reloc_howto_type *
246 mcore_elf_reloc_type_lookup (abfd, code)
247 bfd * abfd ATTRIBUTE_UNUSED;
248 bfd_reloc_code_real_type code;
250 enum elf_mcore_reloc_type mcore_reloc = R_MCORE_NONE;
252 switch (code)
254 case BFD_RELOC_NONE: mcore_reloc = R_MCORE_NONE; break;
255 case BFD_RELOC_32: mcore_reloc = R_MCORE_ADDR32; break;
256 case BFD_RELOC_MCORE_PCREL_IMM8BY4: mcore_reloc = R_MCORE_PCRELIMM8BY4; break;
257 case BFD_RELOC_MCORE_PCREL_IMM11BY2: mcore_reloc = R_MCORE_PCRELIMM11BY2; break;
258 case BFD_RELOC_MCORE_PCREL_IMM4BY2: mcore_reloc = R_MCORE_PCRELIMM4BY2; break;
259 case BFD_RELOC_32_PCREL: mcore_reloc = R_MCORE_PCREL32; break;
260 case BFD_RELOC_MCORE_PCREL_JSR_IMM11BY2: mcore_reloc = R_MCORE_PCRELJSR_IMM11BY2; break;
261 case BFD_RELOC_VTABLE_INHERIT: mcore_reloc = R_MCORE_GNU_VTINHERIT; break;
262 case BFD_RELOC_VTABLE_ENTRY: mcore_reloc = R_MCORE_GNU_VTENTRY; break;
263 case BFD_RELOC_RVA: mcore_reloc = R_MCORE_RELATIVE; break;
264 default:
265 return (reloc_howto_type *)NULL;
268 if (! mcore_elf_howto_table [R_MCORE_PCRELIMM8BY4]) /* Initialize howto table if needed */
269 mcore_elf_howto_init ();
271 return mcore_elf_howto_table [(int) mcore_reloc];
274 /* Set the howto pointer for a RCE ELF reloc. */
275 static void
276 mcore_elf_info_to_howto (abfd, cache_ptr, dst)
277 bfd * abfd ATTRIBUTE_UNUSED;
278 arelent * cache_ptr;
279 Elf32_Internal_Rela * dst;
281 if (! mcore_elf_howto_table [R_MCORE_PCRELIMM8BY4]) /* Initialize howto table if needed */
282 mcore_elf_howto_init ();
284 BFD_ASSERT (ELF32_R_TYPE (dst->r_info) < (unsigned int) R_MCORE_max);
286 cache_ptr->howto = mcore_elf_howto_table [ELF32_R_TYPE (dst->r_info)];
289 /* Function to set whether a module needs the -mrelocatable bit set. */
290 static boolean
291 mcore_elf_set_private_flags (abfd, flags)
292 bfd * abfd;
293 flagword flags;
295 BFD_ASSERT (! elf_flags_init (abfd)
296 || elf_elfheader (abfd)->e_flags == flags);
298 elf_elfheader (abfd)->e_flags = flags;
299 elf_flags_init (abfd) = true;
300 return true;
303 /* Merge backend specific data from an object file to the output
304 object file when linking. */
305 static boolean
306 mcore_elf_merge_private_bfd_data (ibfd, obfd)
307 bfd * ibfd;
308 bfd * obfd;
310 flagword old_flags;
311 flagword new_flags;
313 /* Check if we have the same endianess */
314 if (_bfd_generic_verify_endian_match (ibfd, obfd) == false)
315 return false;
317 if ( bfd_get_flavour (ibfd) != bfd_target_elf_flavour
318 || bfd_get_flavour (obfd) != bfd_target_elf_flavour)
319 return true;
321 new_flags = elf_elfheader (ibfd)->e_flags;
322 old_flags = elf_elfheader (obfd)->e_flags;
324 if (! elf_flags_init (obfd)) /* First call, no flags set */
326 elf_flags_init (obfd) = true;
327 elf_elfheader (obfd)->e_flags = new_flags;
329 else if (new_flags == old_flags) /* Compatible flags are ok */
331 else
333 /* FIXME */
336 return true;
339 /* Don't pretend we can deal with unsupported relocs. */
341 static bfd_reloc_status_type
342 mcore_elf_unsupported_reloc (abfd, reloc_entry, symbol, data, input_section,
343 output_bfd, error_message)
344 bfd * abfd;
345 arelent * reloc_entry;
346 asymbol * symbol ATTRIBUTE_UNUSED;
347 PTR data ATTRIBUTE_UNUSED;
348 asection * input_section ATTRIBUTE_UNUSED;
349 bfd * output_bfd ATTRIBUTE_UNUSED;
350 char ** error_message ATTRIBUTE_UNUSED;
352 BFD_ASSERT (reloc_entry->howto != (reloc_howto_type *)0);
354 _bfd_error_handler (_("%s: Relocation %s (%d) is not currently supported.\n"),
355 bfd_archive_filename (abfd),
356 reloc_entry->howto->name,
357 reloc_entry->howto->type);
359 return bfd_reloc_notsupported;
362 /* The RELOCATE_SECTION function is called by the ELF backend linker
363 to handle the relocations for a section.
365 The relocs are always passed as Rela structures; if the section
366 actually uses Rel structures, the r_addend field will always be
367 zero.
369 This function is responsible for adjust the section contents as
370 necessary, and (if using Rela relocs and generating a
371 relocateable output file) adjusting the reloc addend as
372 necessary.
374 This function does not have to worry about setting the reloc
375 address or the reloc symbol index.
377 LOCAL_SYMS is a pointer to the swapped in local symbols.
379 LOCAL_SECTIONS is an array giving the section in the input file
380 corresponding to the st_shndx field of each local symbol.
382 The global hash table entry for the global symbols can be found
383 via elf_sym_hashes (input_bfd).
385 When generating relocateable output, this function must handle
386 STB_LOCAL/STT_SECTION symbols specially. The output symbol is
387 going to be the section symbol corresponding to the output
388 section, which means that the addend must be adjusted
389 accordingly. */
391 static boolean
392 mcore_elf_relocate_section (output_bfd, info, input_bfd, input_section,
393 contents, relocs, local_syms, local_sections)
394 bfd * output_bfd;
395 struct bfd_link_info * info;
396 bfd * input_bfd;
397 asection * input_section;
398 bfd_byte * contents;
399 Elf_Internal_Rela * relocs;
400 Elf_Internal_Sym * local_syms;
401 asection ** local_sections;
403 Elf_Internal_Shdr * symtab_hdr = & elf_tdata (input_bfd)->symtab_hdr;
404 struct elf_link_hash_entry ** sym_hashes = elf_sym_hashes (input_bfd);
405 Elf_Internal_Rela * rel = relocs;
406 Elf_Internal_Rela * relend = relocs + input_section->reloc_count;
407 boolean ret = true;
409 #ifdef DEBUG
410 fprintf (stderr,
411 "mcore_elf_relocate_section called for %s section %s, %ld relocations%s\n",
412 bfd_archive_filename (input_bfd),
413 bfd_section_name(input_bfd, input_section),
414 (long) input_section->reloc_count,
415 (info->relocateable) ? " (relocatable)" : "");
416 #endif
418 if (info->relocateable)
419 return true;
421 if (! mcore_elf_howto_table [R_MCORE_PCRELIMM8BY4]) /* Initialize howto table if needed */
422 mcore_elf_howto_init ();
424 for (; rel < relend; rel++)
426 enum elf_mcore_reloc_type r_type = (enum elf_mcore_reloc_type) ELF32_R_TYPE (rel->r_info);
427 bfd_vma offset = rel->r_offset;
428 bfd_vma addend = rel->r_addend;
429 bfd_reloc_status_type r = bfd_reloc_other;
430 asection * sec = (asection *) 0;
431 reloc_howto_type * howto;
432 bfd_vma relocation;
433 Elf_Internal_Sym * sym = (Elf_Internal_Sym *) 0;
434 unsigned long r_symndx;
435 struct elf_link_hash_entry * h = (struct elf_link_hash_entry *) 0;
436 unsigned short oldinst = 0;
438 /* Unknown relocation handling */
439 if ((unsigned) r_type >= (unsigned) R_MCORE_max
440 || ! mcore_elf_howto_table [(int)r_type])
442 _bfd_error_handler (_("%s: Unknown relocation type %d\n"),
443 bfd_archive_filename (input_bfd),
444 (int) r_type);
446 bfd_set_error (bfd_error_bad_value);
447 ret = false;
448 continue;
451 howto = mcore_elf_howto_table [(int) r_type];
452 r_symndx = ELF32_R_SYM (rel->r_info);
454 /* Complain about known relocation that are not yet supported. */
455 if (howto->special_function == mcore_elf_unsupported_reloc)
457 _bfd_error_handler (_("%s: Relocation %s (%d) is not currently supported.\n"),
458 bfd_archive_filename (input_bfd),
459 howto->name,
460 (int)r_type);
462 bfd_set_error (bfd_error_bad_value);
463 ret = false;
464 continue;
467 if (r_symndx < symtab_hdr->sh_info)
469 sym = local_syms + r_symndx;
470 sec = local_sections [r_symndx];
471 relocation = _bfd_elf_rela_local_sym (output_bfd, sym, sec, rel);
472 addend = rel->r_addend;
474 else
476 h = sym_hashes [r_symndx - symtab_hdr->sh_info];
477 if ( h->root.type == bfd_link_hash_defined
478 || h->root.type == bfd_link_hash_defweak)
480 sec = h->root.u.def.section;
481 relocation = (h->root.u.def.value
482 + sec->output_section->vma
483 + sec->output_offset);
485 else if (h->root.type == bfd_link_hash_undefweak)
486 relocation = 0;
487 else if (info->shared
488 && ELF_ST_VISIBILITY (h->other) == STV_DEFAULT)
489 relocation = 0;
490 else
492 if (! ((*info->callbacks->undefined_symbol)
493 (info, h->root.root.string, input_bfd,
494 input_section, rel->r_offset, true)))
495 return false;
497 ret = false;
498 continue;
502 switch (r_type)
504 default:
505 break;
507 case R_MCORE_PCRELJSR_IMM11BY2:
508 oldinst = bfd_get_16 (input_bfd, contents + offset);
509 #define MCORE_INST_BSR 0xF800
510 bfd_put_16 (input_bfd, (bfd_vma) MCORE_INST_BSR, contents + offset);
511 break;
514 #ifdef DEBUG
515 fprintf (stderr, "\ttype = %s (%d), symbol index = %ld, offset = %ld, addend = %ld\n",
516 howto->name, r_type, r_symndx, (long) offset, (long) addend);
517 #endif
519 r = _bfd_final_link_relocate
520 (howto, input_bfd, input_section, contents, offset, relocation, addend);
522 if (r != bfd_reloc_ok && r_type == R_MCORE_PCRELJSR_IMM11BY2)
524 /* Wasn't ok, back it out and give up. */
525 bfd_put_16 (input_bfd, (bfd_vma) oldinst, contents + offset);
526 r = bfd_reloc_ok;
529 if (r != bfd_reloc_ok)
531 ret = false;
533 switch (r)
535 default:
536 break;
538 case bfd_reloc_overflow:
540 const char * name;
542 if (h != NULL)
543 name = h->root.root.string;
544 else
546 name = bfd_elf_string_from_elf_section
547 (input_bfd, symtab_hdr->sh_link, sym->st_name);
549 if (name == NULL)
550 break;
552 if (* name == '\0')
553 name = bfd_section_name (input_bfd, sec);
556 (*info->callbacks->reloc_overflow)
557 (info, name, howto->name, (bfd_vma) 0, input_bfd, input_section,
558 offset);
560 break;
565 #ifdef DEBUG
566 fprintf (stderr, "\n");
567 #endif
569 return ret;
572 /* Return the section that should be marked against GC for a given
573 relocation. */
575 static asection *
576 mcore_elf_gc_mark_hook (abfd, info, rel, h, sym)
577 bfd * abfd;
578 struct bfd_link_info * info ATTRIBUTE_UNUSED;
579 Elf_Internal_Rela * rel;
580 struct elf_link_hash_entry * h;
581 Elf_Internal_Sym * sym;
583 if (h != NULL)
585 switch (ELF32_R_TYPE (rel->r_info))
587 case R_MCORE_GNU_VTINHERIT:
588 case R_MCORE_GNU_VTENTRY:
589 break;
591 default:
592 switch (h->root.type)
594 case bfd_link_hash_defined:
595 case bfd_link_hash_defweak:
596 return h->root.u.def.section;
598 case bfd_link_hash_common:
599 return h->root.u.c.p->section;
601 default:
602 break;
606 else
608 return bfd_section_from_elf_index (abfd, sym->st_shndx);
611 return NULL;
614 /* Update the got entry reference counts for the section being removed. */
616 static boolean
617 mcore_elf_gc_sweep_hook (abfd, info, sec, relocs)
618 bfd * abfd ATTRIBUTE_UNUSED;
619 struct bfd_link_info * info ATTRIBUTE_UNUSED;
620 asection * sec ATTRIBUTE_UNUSED;
621 const Elf_Internal_Rela * relocs ATTRIBUTE_UNUSED;
623 return true;
626 /* Look through the relocs for a section during the first phase.
627 Since we don't do .gots or .plts, we just need to consider the
628 virtual table relocs for gc. */
630 static boolean
631 mcore_elf_check_relocs (abfd, info, sec, relocs)
632 bfd * abfd;
633 struct bfd_link_info * info;
634 asection * sec;
635 const Elf_Internal_Rela * relocs;
637 Elf_Internal_Shdr * symtab_hdr;
638 struct elf_link_hash_entry ** sym_hashes;
639 struct elf_link_hash_entry ** sym_hashes_end;
640 const Elf_Internal_Rela * rel;
641 const Elf_Internal_Rela * rel_end;
643 if (info->relocateable)
644 return true;
646 symtab_hdr = & elf_tdata (abfd)->symtab_hdr;
647 sym_hashes = elf_sym_hashes (abfd);
648 sym_hashes_end = sym_hashes + symtab_hdr->sh_size / sizeof (Elf32_External_Sym);
649 if (!elf_bad_symtab (abfd))
650 sym_hashes_end -= symtab_hdr->sh_info;
652 rel_end = relocs + sec->reloc_count;
654 for (rel = relocs; rel < rel_end; rel++)
656 struct elf_link_hash_entry * h;
657 unsigned long r_symndx;
659 r_symndx = ELF32_R_SYM (rel->r_info);
661 if (r_symndx < symtab_hdr->sh_info)
662 h = NULL;
663 else
664 h = sym_hashes [r_symndx - symtab_hdr->sh_info];
666 switch (ELF32_R_TYPE (rel->r_info))
668 /* This relocation describes the C++ object vtable hierarchy.
669 Reconstruct it for later use during GC. */
670 case R_MCORE_GNU_VTINHERIT:
671 if (!_bfd_elf32_gc_record_vtinherit (abfd, sec, h, rel->r_offset))
672 return false;
673 break;
675 /* This relocation describes which C++ vtable entries are actually
676 used. Record for later use during GC. */
677 case R_MCORE_GNU_VTENTRY:
678 if (!_bfd_elf32_gc_record_vtentry (abfd, sec, h, rel->r_addend))
679 return false;
680 break;
684 return true;
687 #define TARGET_BIG_SYM bfd_elf32_mcore_big_vec
688 #define TARGET_BIG_NAME "elf32-mcore-big"
689 #define TARGET_LITTLE_SYM bfd_elf32_mcore_little_vec
690 #define TARGET_LITTLE_NAME "elf32-mcore-little"
692 #define ELF_ARCH bfd_arch_mcore
693 #define ELF_MACHINE_CODE EM_MCORE
694 #define ELF_MAXPAGESIZE 0x1000 /* 4k, if we ever have 'em */
695 #define elf_info_to_howto mcore_elf_info_to_howto
696 #define elf_info_to_howto_rel NULL
698 #define bfd_elf32_bfd_merge_private_bfd_data mcore_elf_merge_private_bfd_data
699 #define bfd_elf32_bfd_set_private_flags mcore_elf_set_private_flags
700 #define bfd_elf32_bfd_reloc_type_lookup mcore_elf_reloc_type_lookup
701 #define elf_backend_relocate_section mcore_elf_relocate_section
702 #define elf_backend_gc_mark_hook mcore_elf_gc_mark_hook
703 #define elf_backend_gc_sweep_hook mcore_elf_gc_sweep_hook
704 #define elf_backend_check_relocs mcore_elf_check_relocs
706 #define elf_backend_can_gc_sections 1
707 #define elf_backend_rela_normal 1
709 #include "elf32-target.h"