00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025 #include "bfd.h"
00026 #include "sysdep.h"
00027 #include "libbfd.h"
00028 #include "elf-bfd.h"
00029 #include "elf/m32r.h"
00030
00031 static bfd_reloc_status_type m32r_elf_10_pcrel_reloc
00032 PARAMS ((bfd *, arelent *, asymbol *, PTR, asection *, bfd *, char **));
00033 static bfd_reloc_status_type m32r_elf_do_10_pcrel_reloc
00034 PARAMS ((bfd *, reloc_howto_type *, asection *,
00035 bfd_byte *, bfd_vma, asection *, bfd_vma, bfd_vma));
00036 static bfd_reloc_status_type m32r_elf_hi16_reloc
00037 PARAMS ((bfd *, arelent *, asymbol *, PTR, asection *, bfd *, char **));
00038 static void m32r_elf_relocate_hi16
00039 PARAMS ((bfd *, int, Elf_Internal_Rela *, Elf_Internal_Rela *,
00040 bfd_byte *, bfd_vma));
00041 bfd_reloc_status_type m32r_elf_lo16_reloc
00042 PARAMS ((bfd *, arelent *, asymbol *, PTR, asection *, bfd *, char **));
00043 bfd_reloc_status_type m32r_elf_generic_reloc
00044 PARAMS ((bfd *, arelent *, asymbol *, PTR, asection *, bfd *, char **));
00045 static bfd_reloc_status_type m32r_elf_sda16_reloc
00046 PARAMS ((bfd *, arelent *, asymbol *, PTR, asection *, bfd *, char **));
00047 static reloc_howto_type *bfd_elf32_bfd_reloc_type_lookup
00048 PARAMS ((bfd *abfd, bfd_reloc_code_real_type code));
00049 static void m32r_info_to_howto_rel
00050 PARAMS ((bfd *, arelent *, Elf_Internal_Rela *));
00051 static void m32r_info_to_howto
00052 PARAMS ((bfd *, arelent *, Elf_Internal_Rela *));
00053 bfd_boolean _bfd_m32r_elf_section_from_bfd_section
00054 PARAMS ((bfd *, asection *, int *));
00055 void _bfd_m32r_elf_symbol_processing
00056 PARAMS ((bfd *, asymbol *));
00057 static bfd_boolean m32r_elf_add_symbol_hook
00058 PARAMS ((bfd *, struct bfd_link_info *, Elf_Internal_Sym *,
00059 const char **, flagword *, asection **, bfd_vma *));
00060 static bfd_boolean m32r_elf_relocate_section
00061 PARAMS ((bfd *, struct bfd_link_info *, bfd *, asection *, bfd_byte *,
00062 Elf_Internal_Rela *, Elf_Internal_Sym *, asection **));
00063 static bfd_reloc_status_type m32r_elf_final_sda_base
00064 PARAMS ((bfd *, struct bfd_link_info *, const char **, bfd_vma *));
00065 static bfd_boolean m32r_elf_object_p
00066 PARAMS ((bfd *));
00067 static void m32r_elf_final_write_processing
00068 PARAMS ((bfd *, bfd_boolean));
00069 static bfd_boolean m32r_elf_set_private_flags
00070 PARAMS ((bfd *, flagword));
00071 static bfd_boolean m32r_elf_merge_private_bfd_data
00072 PARAMS ((bfd *, bfd *));
00073 static bfd_boolean m32r_elf_print_private_bfd_data
00074 PARAMS ((bfd *, PTR));
00075 static bfd_boolean m32r_elf_gc_sweep_hook
00076 PARAMS ((bfd *, struct bfd_link_info *, asection *,
00077 const Elf_Internal_Rela *));
00078 static bfd_boolean m32r_elf_check_relocs
00079 PARAMS ((bfd *, struct bfd_link_info *, asection *,
00080 const Elf_Internal_Rela *));
00081
00082 static bfd_boolean m32r_elf_adjust_dynamic_symbol
00083 PARAMS ((struct bfd_link_info *, struct elf_link_hash_entry *));
00084 static bfd_boolean m32r_elf_size_dynamic_sections
00085 PARAMS ((bfd *, struct bfd_link_info *));
00086
00087 asection * m32r_elf_gc_mark_hook
00088 PARAMS ((asection *, struct bfd_link_info *, Elf_Internal_Rela *,
00089 struct elf_link_hash_entry *, Elf_Internal_Sym *));
00090
00091 static bfd_boolean m32r_elf_create_dynamic_sections
00092 PARAMS ((bfd *, struct bfd_link_info *));
00093
00094 static bfd_boolean m32r_elf_finish_dynamic_sections
00095 PARAMS ((bfd *, struct bfd_link_info *));
00096
00097 static bfd_boolean m32r_elf_finish_dynamic_symbol
00098 PARAMS ((bfd *, struct bfd_link_info *, struct elf_link_hash_entry *,
00099 Elf_Internal_Sym *));
00100
00101 static bfd_boolean allocate_dynrelocs
00102 PARAMS ((struct elf_link_hash_entry *, PTR));
00103 static bfd_boolean readonly_dynrelocs
00104 PARAMS ((struct elf_link_hash_entry *, PTR));
00105 static enum elf_reloc_type_class m32r_elf_reloc_type_class
00106 PARAMS ((const Elf_Internal_Rela *));
00107 static bfd_boolean m32r_elf_fake_sections
00108 PARAMS ((bfd *, Elf_Internal_Shdr *, asection *));
00109
00110 #define NOP_INSN 0x7000
00111 #define MAKE_PARALLEL(insn) ((insn) | 0x8000)
00112
00113
00114
00115
00116
00117
00118
00119
00120
00121
00122
00123
00124
00125
00126
00127
00128
00129 #define ELF_DYNAMIC_INTERPRETER "/usr/lib/libc.so.1"
00130
00131
00132
00133 #define M32R_NOP 0x7000f000
00134
00135 #define PLT_EMPTY 0x10101010
00136
00137
00138
00139 #define PLT_ENTRY_SIZE 20
00140 #define PLT_HEADER_SIZE 20
00141
00142
00143
00144
00145
00146 #define PLT0_ENTRY_WORD0 0xd6c00000
00147 #define PLT0_ENTRY_WORD1 0x86e60000
00148 #define PLT0_ENTRY_WORD2 0x24e626c6
00149 #define PLT0_ENTRY_WORD3 0x1fc6f000
00150 #define PLT0_ENTRY_WORD4 PLT_EMPTY
00151
00152 #define PLT0_PIC_ENTRY_WORD0 0xa4cc0004
00153 #define PLT0_PIC_ENTRY_WORD1 0xa6cc0008
00154 #define PLT0_PIC_ENTRY_WORD2 0x1fc6f000
00155 #define PLT0_PIC_ENTRY_WORD3 PLT_EMPTY
00156 #define PLT0_PIC_ENTRY_WORD4 PLT_EMPTY
00157
00158 #define PLT_ENTRY_WORD0 0xe6000000
00159 #define PLT_ENTRY_WORD1 0x06acf000
00160 #define PLT_ENTRY_WORD0b 0xd6c00000
00161 #define PLT_ENTRY_WORD1b 0x86e60000
00162 #define PLT_ENTRY_WORD2 0x26c61fc6
00163 #define PLT_ENTRY_WORD3 0xe5000000
00164 #define PLT_ENTRY_WORD4 0xff000000
00165
00166
00167 static reloc_howto_type m32r_elf_howto_table[] =
00168 {
00169
00170 HOWTO (R_M32R_NONE,
00171 0,
00172 2,
00173 32,
00174 FALSE,
00175 0,
00176 complain_overflow_bitfield,
00177 bfd_elf_generic_reloc,
00178 "R_M32R_NONE",
00179 FALSE,
00180 0,
00181 0,
00182 FALSE),
00183
00184
00185 HOWTO (R_M32R_16,
00186 0,
00187 1,
00188 16,
00189 FALSE,
00190 0,
00191 complain_overflow_bitfield,
00192 m32r_elf_generic_reloc,
00193 "R_M32R_16",
00194 TRUE,
00195 0xffff,
00196 0xffff,
00197 FALSE),
00198
00199
00200 HOWTO (R_M32R_32,
00201 0,
00202 2,
00203 32,
00204 FALSE,
00205 0,
00206 complain_overflow_bitfield,
00207 m32r_elf_generic_reloc,
00208 "R_M32R_32",
00209 TRUE,
00210 0xffffffff,
00211 0xffffffff,
00212 FALSE),
00213
00214
00215 HOWTO (R_M32R_24,
00216 0,
00217 2,
00218 24,
00219 FALSE,
00220 0,
00221 complain_overflow_unsigned,
00222 m32r_elf_generic_reloc,
00223 "R_M32R_24",
00224 TRUE,
00225 0xffffff,
00226 0xffffff,
00227 FALSE),
00228
00229
00230
00231
00232
00233
00234
00235
00236
00237 HOWTO (R_M32R_10_PCREL,
00238 2,
00239 1,
00240 10,
00241 TRUE,
00242 0,
00243 complain_overflow_signed,
00244 m32r_elf_10_pcrel_reloc,
00245 "R_M32R_10_PCREL",
00246 FALSE,
00247 0xff,
00248 0xff,
00249 TRUE),
00250
00251
00252 HOWTO (R_M32R_18_PCREL,
00253 2,
00254 2,
00255 16,
00256 TRUE,
00257 0,
00258 complain_overflow_signed,
00259 bfd_elf_generic_reloc,
00260 "R_M32R_18_PCREL",
00261 FALSE,
00262 0xffff,
00263 0xffff,
00264 TRUE),
00265
00266
00267
00268
00269
00270
00271 HOWTO (R_M32R_26_PCREL,
00272 2,
00273 2,
00274 26,
00275 TRUE,
00276 0,
00277 complain_overflow_signed,
00278 bfd_elf_generic_reloc,
00279 "R_M32R_26_PCREL",
00280 FALSE,
00281 0xffffff,
00282 0xffffff,
00283 TRUE),
00284
00285
00286 HOWTO (R_M32R_HI16_ULO,
00287 16,
00288 2,
00289 16,
00290 FALSE,
00291 0,
00292 complain_overflow_dont,
00293 m32r_elf_hi16_reloc,
00294 "R_M32R_HI16_ULO",
00295 TRUE,
00296 0x0000ffff,
00297 0x0000ffff,
00298 FALSE),
00299
00300
00301 HOWTO (R_M32R_HI16_SLO,
00302 16,
00303 2,
00304 16,
00305 FALSE,
00306 0,
00307 complain_overflow_dont,
00308 m32r_elf_hi16_reloc,
00309 "R_M32R_HI16_SLO",
00310 TRUE,
00311 0x0000ffff,
00312 0x0000ffff,
00313 FALSE),
00314
00315
00316 HOWTO (R_M32R_LO16,
00317 0,
00318 2,
00319 16,
00320 FALSE,
00321 0,
00322 complain_overflow_dont,
00323 m32r_elf_lo16_reloc,
00324 "R_M32R_LO16",
00325 TRUE,
00326 0x0000ffff,
00327 0x0000ffff,
00328 FALSE),
00329
00330
00331 HOWTO (R_M32R_SDA16,
00332 0,
00333 2,
00334 16,
00335 FALSE,
00336 0,
00337 complain_overflow_signed,
00338 m32r_elf_sda16_reloc,
00339 "R_M32R_SDA16",
00340 TRUE,
00341 0x0000ffff,
00342 0x0000ffff,
00343 FALSE),
00344
00345
00346 HOWTO (R_M32R_GNU_VTINHERIT,
00347 0,
00348 2,
00349 0,
00350 FALSE,
00351 0,
00352 complain_overflow_dont,
00353 NULL,
00354 "R_M32R_GNU_VTINHERIT",
00355 FALSE,
00356 0,
00357 0,
00358 FALSE),
00359
00360
00361 HOWTO (R_M32R_GNU_VTENTRY,
00362 0,
00363 2,
00364 0,
00365 FALSE,
00366 0,
00367 complain_overflow_dont,
00368 _bfd_elf_rel_vtable_reloc_fn,
00369 "R_M32R_GNU_VTENTRY",
00370 FALSE,
00371 0,
00372 0,
00373 FALSE),
00374
00375 EMPTY_HOWTO (13),
00376 EMPTY_HOWTO (14),
00377 EMPTY_HOWTO (15),
00378 EMPTY_HOWTO (16),
00379 EMPTY_HOWTO (17),
00380 EMPTY_HOWTO (18),
00381 EMPTY_HOWTO (19),
00382 EMPTY_HOWTO (20),
00383 EMPTY_HOWTO (21),
00384 EMPTY_HOWTO (22),
00385 EMPTY_HOWTO (23),
00386 EMPTY_HOWTO (24),
00387 EMPTY_HOWTO (25),
00388 EMPTY_HOWTO (26),
00389 EMPTY_HOWTO (27),
00390 EMPTY_HOWTO (28),
00391 EMPTY_HOWTO (29),
00392 EMPTY_HOWTO (30),
00393 EMPTY_HOWTO (31),
00394 EMPTY_HOWTO (32),
00395
00396
00397 HOWTO (R_M32R_16_RELA,
00398 0,
00399 1,
00400 16,
00401 FALSE,
00402 0,
00403 complain_overflow_bitfield,
00404 bfd_elf_generic_reloc,
00405 "R_M32R_16_RELA",
00406 FALSE,
00407 0xffff,
00408 0xffff,
00409 FALSE),
00410
00411
00412 HOWTO (R_M32R_32_RELA,
00413 0,
00414 2,
00415 32,
00416 FALSE,
00417 0,
00418 complain_overflow_bitfield,
00419 bfd_elf_generic_reloc,
00420 "R_M32R_32_RELA",
00421 FALSE,
00422 0xffffffff,
00423 0xffffffff,
00424 FALSE),
00425
00426
00427 HOWTO (R_M32R_24_RELA,
00428 0,
00429 2,
00430 24,
00431 FALSE,
00432 0,
00433 complain_overflow_unsigned,
00434 bfd_elf_generic_reloc,
00435 "R_M32R_24_RELA",
00436 FALSE,
00437 0xffffff,
00438 0xffffff,
00439 FALSE),
00440
00441 HOWTO (R_M32R_10_PCREL_RELA,
00442 2,
00443 1,
00444 10,
00445 TRUE,
00446 0,
00447 complain_overflow_signed,
00448 m32r_elf_10_pcrel_reloc,
00449 "R_M32R_10_PCREL_RELA",
00450 FALSE,
00451 0xff,
00452 0xff,
00453 TRUE),
00454
00455
00456 HOWTO (R_M32R_18_PCREL_RELA,
00457 2,
00458 2,
00459 16,
00460 TRUE,
00461 0,
00462 complain_overflow_signed,
00463 bfd_elf_generic_reloc,
00464 "R_M32R_18_PCREL_RELA",
00465 FALSE,
00466 0xffff,
00467 0xffff,
00468 TRUE),
00469
00470
00471 HOWTO (R_M32R_26_PCREL_RELA,
00472 2,
00473 2,
00474 26,
00475 TRUE,
00476 0,
00477 complain_overflow_signed,
00478 bfd_elf_generic_reloc,
00479 "R_M32R_26_PCREL_RELA",
00480 FALSE,
00481 0xffffff,
00482 0xffffff,
00483 TRUE),
00484
00485
00486 HOWTO (R_M32R_HI16_ULO_RELA,
00487 16,
00488 2,
00489 16,
00490 FALSE,
00491 0,
00492 complain_overflow_dont,
00493 bfd_elf_generic_reloc,
00494 "R_M32R_HI16_ULO_RELA",
00495 FALSE,
00496 0x0000ffff,
00497 0x0000ffff,
00498 FALSE),
00499
00500
00501 HOWTO (R_M32R_HI16_SLO_RELA,
00502 16,
00503 2,
00504 16,
00505 FALSE,
00506 0,
00507 complain_overflow_dont,
00508 bfd_elf_generic_reloc,
00509 "R_M32R_HI16_SLO_RELA",
00510 FALSE,
00511 0x0000ffff,
00512 0x0000ffff,
00513 FALSE),
00514
00515
00516 HOWTO (R_M32R_LO16_RELA,
00517 0,
00518 2,
00519 16,
00520 FALSE,
00521 0,
00522 complain_overflow_dont,
00523 bfd_elf_generic_reloc,
00524 "R_M32R_LO16_RELA",
00525 FALSE,
00526 0x0000ffff,
00527 0x0000ffff,
00528 FALSE),
00529
00530
00531 HOWTO (R_M32R_SDA16_RELA,
00532 0,
00533 2,
00534 16,
00535 FALSE,
00536 0,
00537 complain_overflow_signed,
00538 bfd_elf_generic_reloc,
00539 "R_M32R_SDA16_RELA",
00540 TRUE,
00541 0x0000ffff,
00542 0x0000ffff,
00543 FALSE),
00544
00545
00546 HOWTO (R_M32R_RELA_GNU_VTINHERIT,
00547 0,
00548 2,
00549 0,
00550 FALSE,
00551 0,
00552 complain_overflow_dont,
00553 NULL,
00554 "R_M32R_RELA_GNU_VTINHERIT",
00555 FALSE,
00556 0,
00557 0,
00558 FALSE),
00559
00560
00561 HOWTO (R_M32R_RELA_GNU_VTENTRY,
00562 0,
00563 2,
00564 0,
00565 FALSE,
00566 0,
00567 complain_overflow_dont,
00568 _bfd_elf_rel_vtable_reloc_fn,
00569 "R_M32R_RELA_GNU_VTENTRY",
00570 FALSE,
00571 0,
00572 0,
00573 FALSE),
00574
00575 EMPTY_HOWTO (45),
00576 EMPTY_HOWTO (46),
00577 EMPTY_HOWTO (47),
00578
00579
00580
00581 HOWTO (R_M32R_GOT24,
00582 0,
00583 2,
00584 24,
00585 FALSE,
00586 0,
00587 complain_overflow_unsigned,
00588 bfd_elf_generic_reloc,
00589 "R_M32R_GOT24",
00590 FALSE,
00591 0xffffff,
00592 0xffffff,
00593 FALSE),
00594
00595
00596
00597 HOWTO (R_M32R_26_PLTREL,
00598 2,
00599 2,
00600 24,
00601 TRUE,
00602 0,
00603 complain_overflow_signed,
00604 bfd_elf_generic_reloc,
00605 "R_M32R_26_PLTREL",
00606 FALSE,
00607 0xffffff,
00608 0xffffff,
00609 TRUE),
00610
00611
00612
00613
00614
00615
00616 HOWTO (R_M32R_COPY,
00617 0,
00618 2,
00619 32,
00620 FALSE,
00621 0,
00622 complain_overflow_bitfield,
00623 bfd_elf_generic_reloc,
00624 "R_M32R_COPY",
00625 FALSE,
00626 0xffffffff,
00627 0xffffffff,
00628 FALSE),
00629
00630
00631
00632 HOWTO (R_M32R_GLOB_DAT,
00633 0,
00634 2,
00635 32,
00636 FALSE,
00637 0,
00638 complain_overflow_bitfield,
00639 bfd_elf_generic_reloc,
00640 "R_M32R_GLOB_DAT",
00641 FALSE,
00642 0xffffffff,
00643 0xffffffff,
00644 FALSE),
00645
00646
00647 HOWTO (R_M32R_JMP_SLOT,
00648 0,
00649 2,
00650 32,
00651 FALSE,
00652 0,
00653 complain_overflow_bitfield,
00654 bfd_elf_generic_reloc,
00655 "R_M32R_JMP_SLOT",
00656 FALSE,
00657 0xffffffff,
00658 0xffffffff,
00659 FALSE),
00660
00661
00662
00663
00664 HOWTO (R_M32R_RELATIVE,
00665 0,
00666 2,
00667 32,
00668 FALSE,
00669 0,
00670 complain_overflow_bitfield,
00671 bfd_elf_generic_reloc,
00672 "R_M32R_RELATIVE",
00673 FALSE,
00674 0xffffffff,
00675 0xffffffff,
00676 FALSE),
00677
00678 HOWTO (R_M32R_GOTOFF,
00679 0,
00680 2,
00681 24,
00682 FALSE,
00683 0,
00684 complain_overflow_bitfield,
00685 bfd_elf_generic_reloc,
00686 "R_M32R_GOTOFF",
00687 FALSE,
00688 0xffffff,
00689 0xffffff,
00690 FALSE),
00691
00692
00693
00694 HOWTO (R_M32R_GOTPC24,
00695 0,
00696 2,
00697 24,
00698 TRUE,
00699 0,
00700 complain_overflow_unsigned,
00701 bfd_elf_generic_reloc,
00702 "R_M32R_GOTPC24",
00703 FALSE,
00704 0xffffff,
00705 0xffffff,
00706 TRUE),
00707
00708
00709
00710 HOWTO (R_M32R_GOT16_HI_ULO,
00711 16,
00712 2,
00713 16,
00714 FALSE,
00715 0,
00716 complain_overflow_dont,
00717 bfd_elf_generic_reloc,
00718 "R_M32R_GOT16_HI_ULO",
00719 FALSE,
00720 0x0000ffff,
00721 0x0000ffff,
00722 FALSE),
00723
00724
00725
00726 HOWTO (R_M32R_GOT16_HI_SLO,
00727 16,
00728 2,
00729 16,
00730 FALSE,
00731 0,
00732 complain_overflow_dont,
00733 bfd_elf_generic_reloc,
00734 "R_M32R_GOT16_HI_SLO",
00735 FALSE,
00736 0x0000ffff,
00737 0x0000ffff,
00738 FALSE),
00739
00740
00741
00742 HOWTO (R_M32R_GOT16_LO,
00743 0,
00744 2,
00745 16,
00746 FALSE,
00747 0,
00748 complain_overflow_dont,
00749 bfd_elf_generic_reloc,
00750 "R_M32R_GOT16_LO",
00751 FALSE,
00752 0x0000ffff,
00753 0x0000ffff,
00754 FALSE),
00755
00756
00757
00758
00759 HOWTO (R_M32R_GOTPC_HI_ULO,
00760 16,
00761 2,
00762 16,
00763 FALSE,
00764 0,
00765 complain_overflow_dont,
00766 bfd_elf_generic_reloc,
00767 "R_M32R_GOTPC_HI_ULO",
00768 FALSE,
00769 0x0000ffff,
00770 0x0000ffff,
00771 TRUE),
00772
00773
00774
00775
00776 HOWTO (R_M32R_GOTPC_HI_SLO,
00777 16,
00778 2,
00779 16,
00780 FALSE,
00781 0,
00782 complain_overflow_dont,
00783 bfd_elf_generic_reloc,
00784 "R_M32R_GOTPC_HI_SLO",
00785 FALSE,
00786 0x0000ffff,
00787 0x0000ffff,
00788 TRUE),
00789
00790
00791
00792
00793 HOWTO (R_M32R_GOTPC_LO,
00794 0,
00795 2,
00796 16,
00797 FALSE,
00798 0,
00799 complain_overflow_dont,
00800 bfd_elf_generic_reloc,
00801 "R_M32R_GOTPC_LO",
00802 FALSE,
00803 0x0000ffff,
00804 0x0000ffff,
00805 TRUE),
00806
00807 HOWTO (R_M32R_GOTOFF_HI_ULO,
00808 16,
00809 2,
00810 16,
00811 FALSE,
00812 0,
00813 complain_overflow_dont,
00814 bfd_elf_generic_reloc,
00815 "R_M32R_GOTOFF_HI_ULO",
00816 FALSE,
00817 0x0000ffff,
00818 0x0000ffff,
00819 FALSE),
00820
00821 HOWTO (R_M32R_GOTOFF_HI_SLO,
00822 16,
00823 2,
00824 16,
00825 FALSE,
00826 0,
00827 complain_overflow_dont,
00828 bfd_elf_generic_reloc,
00829 "R_M32R_GOTOFF_HI_SLO",
00830 FALSE,
00831 0x0000ffff,
00832 0x0000ffff,
00833 FALSE),
00834
00835 HOWTO (R_M32R_GOTOFF_LO,
00836 0,
00837 2,
00838 16,
00839 FALSE,
00840 0,
00841 complain_overflow_dont,
00842 bfd_elf_generic_reloc,
00843 "R_M32R_GOTOFF_LO",
00844 FALSE,
00845 0x0000ffff,
00846 0x0000ffff,
00847 FALSE),
00848 };
00849
00850
00851
00852 static bfd_reloc_status_type
00853 m32r_elf_10_pcrel_reloc (abfd, reloc_entry, symbol, data,
00854 input_section, output_bfd, error_message)
00855 bfd * abfd;
00856 arelent * reloc_entry;
00857 asymbol * symbol;
00858 PTR data;
00859 asection * input_section;
00860 bfd * output_bfd;
00861 char ** error_message ATTRIBUTE_UNUSED;
00862 {
00863
00864 if (output_bfd != (bfd *) NULL
00865 && (symbol->flags & BSF_SECTION_SYM) == 0
00866 && (! reloc_entry->howto->partial_inplace
00867 || reloc_entry->addend == 0))
00868 {
00869 reloc_entry->address += input_section->output_offset;
00870 return bfd_reloc_ok;
00871 }
00872
00873 if (output_bfd != NULL)
00874 {
00875
00876 return bfd_reloc_continue;
00877 }
00878
00879 return m32r_elf_do_10_pcrel_reloc (abfd, reloc_entry->howto,
00880 input_section,
00881 data, reloc_entry->address,
00882 symbol->section,
00883 (symbol->value
00884 + symbol->section->output_section->vma
00885 + symbol->section->output_offset),
00886 reloc_entry->addend);
00887 }
00888
00889
00890
00891 static bfd_reloc_status_type
00892 m32r_elf_do_10_pcrel_reloc (abfd, howto, input_section, data, offset,
00893 symbol_section, symbol_value, addend)
00894 bfd *abfd;
00895 reloc_howto_type *howto;
00896 asection *input_section;
00897 bfd_byte *data;
00898 bfd_vma offset;
00899 asection *symbol_section ATTRIBUTE_UNUSED;
00900 bfd_vma symbol_value;
00901 bfd_vma addend;
00902 {
00903 bfd_signed_vma relocation;
00904 unsigned long x;
00905 bfd_reloc_status_type status;
00906
00907
00908 if (offset > bfd_get_section_limit (abfd, input_section))
00909 return bfd_reloc_outofrange;
00910
00911 relocation = symbol_value + addend;
00912
00913 relocation -= (input_section->output_section->vma
00914 + input_section->output_offset);
00915
00916
00917 relocation -= (offset & -(bfd_vma) 4);
00918
00919 if (relocation < -0x200 || relocation > 0x1ff)
00920 status = bfd_reloc_overflow;
00921 else
00922 status = bfd_reloc_ok;
00923
00924 x = bfd_get_16 (abfd, data + offset);
00925 relocation >>= howto->rightshift;
00926 relocation <<= howto->bitpos;
00927 x = (x & ~howto->dst_mask) | (((x & howto->src_mask) + relocation) & howto->dst_mask);
00928 bfd_put_16 (abfd, (bfd_vma) x, data + offset);
00929
00930 return status;
00931 }
00932
00933
00934
00935
00936
00937
00938
00939
00940
00941
00942
00943
00944
00945
00946
00947
00948
00949 struct m32r_hi16
00950 {
00951 struct m32r_hi16 *next;
00952 bfd_byte *addr;
00953 bfd_vma addend;
00954 };
00955
00956
00957
00958 static struct m32r_hi16 *m32r_hi16_list;
00959
00960 static bfd_reloc_status_type
00961 m32r_elf_hi16_reloc (abfd, reloc_entry, symbol, data,
00962 input_section, output_bfd, error_message)
00963 bfd *abfd ATTRIBUTE_UNUSED;
00964 arelent *reloc_entry;
00965 asymbol *symbol;
00966 PTR data;
00967 asection *input_section;
00968 bfd *output_bfd;
00969 char **error_message ATTRIBUTE_UNUSED;
00970 {
00971 bfd_reloc_status_type ret;
00972 bfd_vma relocation;
00973 struct m32r_hi16 *n;
00974
00975
00976
00977
00978 if (output_bfd != (bfd *) NULL
00979 && (symbol->flags & BSF_SECTION_SYM) == 0
00980 && reloc_entry->addend == 0)
00981 {
00982 reloc_entry->address += input_section->output_offset;
00983 return bfd_reloc_ok;
00984 }
00985
00986
00987 if (reloc_entry->address > bfd_get_section_limit (abfd, input_section))
00988 return bfd_reloc_outofrange;
00989
00990 ret = bfd_reloc_ok;
00991 if (bfd_is_und_section (symbol->section)
00992 && output_bfd == (bfd *) NULL)
00993 ret = bfd_reloc_undefined;
00994
00995 if (bfd_is_com_section (symbol->section))
00996 relocation = 0;
00997 else
00998 relocation = symbol->value;
00999
01000 relocation += symbol->section->output_section->vma;
01001 relocation += symbol->section->output_offset;
01002 relocation += reloc_entry->addend;
01003
01004
01005 n = (struct m32r_hi16 *) bfd_malloc ((bfd_size_type) sizeof *n);
01006 if (n == NULL)
01007 return bfd_reloc_outofrange;
01008 n->addr = (bfd_byte *) data + reloc_entry->address;
01009 n->addend = relocation;
01010 n->next = m32r_hi16_list;
01011 m32r_hi16_list = n;
01012
01013 if (output_bfd != (bfd *) NULL)
01014 reloc_entry->address += input_section->output_offset;
01015
01016 return ret;
01017 }
01018
01019
01020
01021 static void
01022 m32r_elf_relocate_hi16 (input_bfd, type, relhi, rello, contents, addend)
01023 bfd *input_bfd;
01024 int type;
01025 Elf_Internal_Rela *relhi;
01026 Elf_Internal_Rela *rello;
01027 bfd_byte *contents;
01028 bfd_vma addend;
01029 {
01030 unsigned long insn;
01031 bfd_vma addlo;
01032
01033 insn = bfd_get_32 (input_bfd, contents + relhi->r_offset);
01034
01035 addlo = bfd_get_32 (input_bfd, contents + rello->r_offset);
01036 if (type == R_M32R_HI16_SLO)
01037 addlo = ((addlo & 0xffff) ^ 0x8000) - 0x8000;
01038 else
01039 addlo &= 0xffff;
01040
01041 addend += ((insn & 0xffff) << 16) + addlo;
01042
01043
01044 if (type == R_M32R_HI16_SLO
01045 && (addend & 0x8000) != 0)
01046 addend += 0x10000;
01047
01048 bfd_put_32 (input_bfd,
01049 (insn & 0xffff0000) | ((addend >> 16) & 0xffff),
01050 contents + relhi->r_offset);
01051 }
01052
01053
01054
01055
01056
01057 bfd_reloc_status_type
01058 m32r_elf_lo16_reloc (input_bfd, reloc_entry, symbol, data,
01059 input_section, output_bfd, error_message)
01060 bfd *input_bfd;
01061 arelent *reloc_entry;
01062 asymbol *symbol;
01063 PTR data;
01064 asection *input_section;
01065 bfd *output_bfd;
01066 char **error_message;
01067 {
01068
01069
01070
01071 if (output_bfd != (bfd *) NULL
01072 && (symbol->flags & BSF_SECTION_SYM) == 0
01073 && reloc_entry->addend == 0)
01074 {
01075 reloc_entry->address += input_section->output_offset;
01076 return bfd_reloc_ok;
01077 }
01078
01079 if (m32r_hi16_list != NULL)
01080 {
01081 struct m32r_hi16 *l;
01082
01083 l = m32r_hi16_list;
01084 while (l != NULL)
01085 {
01086 unsigned long insn;
01087 unsigned long val;
01088 unsigned long vallo;
01089 struct m32r_hi16 *next;
01090
01091
01092
01093
01094 insn = bfd_get_32 (input_bfd, l->addr);
01095 vallo = ((bfd_get_32 (input_bfd, (bfd_byte *) data + reloc_entry->address)
01096 & 0xffff) ^ 0x8000) - 0x8000;
01097 val = ((insn & 0xffff) << 16) + vallo;
01098 val += l->addend;
01099
01100
01101 if ((val & 0x8000) != 0)
01102 val += 0x10000;
01103
01104 insn = (insn &~ (bfd_vma) 0xffff) | ((val >> 16) & 0xffff);
01105 bfd_put_32 (input_bfd, (bfd_vma) insn, l->addr);
01106
01107 next = l->next;
01108 free (l);
01109 l = next;
01110 }
01111
01112 m32r_hi16_list = NULL;
01113 }
01114
01115
01116
01117
01118
01119
01120 return m32r_elf_generic_reloc (input_bfd, reloc_entry, symbol, data,
01121 input_section, output_bfd, error_message);
01122 }
01123
01124
01125
01126
01127 bfd_reloc_status_type
01128 m32r_elf_generic_reloc (input_bfd, reloc_entry, symbol, data,
01129 input_section, output_bfd, error_message)
01130 bfd *input_bfd;
01131 arelent *reloc_entry;
01132 asymbol *symbol;
01133 PTR data;
01134 asection *input_section;
01135 bfd *output_bfd;
01136 char **error_message ATTRIBUTE_UNUSED;
01137 {
01138 bfd_reloc_status_type ret;
01139 bfd_vma relocation;
01140 bfd_byte *inplace_address;
01141
01142
01143
01144
01145 if (output_bfd != (bfd *) NULL
01146 && (symbol->flags & BSF_SECTION_SYM) == 0
01147 && reloc_entry->addend == 0)
01148 {
01149 reloc_entry->address += input_section->output_offset;
01150 return bfd_reloc_ok;
01151 }
01152
01153
01154
01155
01156
01157
01158
01159
01160 if (reloc_entry->address > bfd_get_section_limit (input_bfd, input_section))
01161 return bfd_reloc_outofrange;
01162
01163 ret = bfd_reloc_ok;
01164 if (bfd_is_und_section (symbol->section)
01165 && output_bfd == (bfd *) NULL)
01166 ret = bfd_reloc_undefined;
01167
01168 if (bfd_is_com_section (symbol->section)
01169 || output_bfd != (bfd *) NULL)
01170 relocation = 0;
01171 else
01172 relocation = symbol->value;
01173
01174
01175 if (output_bfd == (bfd *) NULL)
01176 {
01177 relocation += symbol->section->output_section->vma;
01178 relocation += symbol->section->output_offset;
01179 }
01180
01181 relocation += reloc_entry->addend;
01182 inplace_address = (bfd_byte *) data + reloc_entry->address;
01183
01184 #define DOIT(x) \
01185 x = ( (x & ~reloc_entry->howto->dst_mask) | \
01186 (((x & reloc_entry->howto->src_mask) + relocation) & \
01187 reloc_entry->howto->dst_mask))
01188
01189 switch (reloc_entry->howto->size)
01190 {
01191 case 1:
01192 {
01193 short x = bfd_get_16 (input_bfd, inplace_address);
01194 DOIT (x);
01195 bfd_put_16 (input_bfd, (bfd_vma) x, inplace_address);
01196 }
01197 break;
01198 case 2:
01199 {
01200 unsigned long x = bfd_get_32 (input_bfd, inplace_address);
01201 DOIT (x);
01202 bfd_put_32 (input_bfd, (bfd_vma)x , inplace_address);
01203 }
01204 break;
01205 default:
01206 BFD_ASSERT (0);
01207 }
01208
01209 if (output_bfd != (bfd *) NULL)
01210 reloc_entry->address += input_section->output_offset;
01211
01212 return ret;
01213 }
01214
01215
01216
01217
01218
01219
01220
01221 static bfd_reloc_status_type
01222 m32r_elf_sda16_reloc (abfd, reloc_entry, symbol, data,
01223 input_section, output_bfd, error_message)
01224 bfd *abfd ATTRIBUTE_UNUSED;
01225 arelent *reloc_entry;
01226 asymbol *symbol;
01227 PTR data ATTRIBUTE_UNUSED;
01228 asection *input_section;
01229 bfd *output_bfd;
01230 char **error_message ATTRIBUTE_UNUSED;
01231 {
01232
01233 if (output_bfd != (bfd *) NULL
01234 && (symbol->flags & BSF_SECTION_SYM) == 0
01235 && (! reloc_entry->howto->partial_inplace
01236 || reloc_entry->addend == 0))
01237 {
01238 reloc_entry->address += input_section->output_offset;
01239 return bfd_reloc_ok;
01240 }
01241
01242 if (output_bfd != NULL)
01243 {
01244
01245 return bfd_reloc_continue;
01246 }
01247
01248
01249
01250 abort ();
01251 }
01252
01253
01254
01255 struct m32r_reloc_map
01256 {
01257 bfd_reloc_code_real_type bfd_reloc_val;
01258 unsigned char elf_reloc_val;
01259 };
01260
01261 #ifdef USE_M32R_OLD_RELOC
01262 static const struct m32r_reloc_map m32r_reloc_map_old[] =
01263 {
01264 { BFD_RELOC_NONE, R_M32R_NONE },
01265 { BFD_RELOC_16, R_M32R_16 },
01266 { BFD_RELOC_32, R_M32R_32 },
01267 { BFD_RELOC_M32R_24, R_M32R_24 },
01268 { BFD_RELOC_M32R_10_PCREL, R_M32R_10_PCREL },
01269 { BFD_RELOC_M32R_18_PCREL, R_M32R_18_PCREL },
01270 { BFD_RELOC_M32R_26_PCREL, R_M32R_26_PCREL },
01271 { BFD_RELOC_M32R_HI16_ULO, R_M32R_HI16_ULO },
01272 { BFD_RELOC_M32R_HI16_SLO, R_M32R_HI16_SLO },
01273 { BFD_RELOC_M32R_LO16, R_M32R_LO16 },
01274 { BFD_RELOC_M32R_SDA16, R_M32R_SDA16 },
01275 { BFD_RELOC_VTABLE_INHERIT, R_M32R_GNU_VTINHERIT },
01276 { BFD_RELOC_VTABLE_ENTRY, R_M32R_GNU_VTENTRY },
01277 };
01278 #else
01279 static const struct m32r_reloc_map m32r_reloc_map[] =
01280 {
01281 { BFD_RELOC_NONE, R_M32R_NONE },
01282 { BFD_RELOC_16, R_M32R_16_RELA },
01283 { BFD_RELOC_32, R_M32R_32_RELA },
01284 { BFD_RELOC_M32R_24, R_M32R_24_RELA },
01285 { BFD_RELOC_M32R_10_PCREL, R_M32R_10_PCREL_RELA },
01286 { BFD_RELOC_M32R_18_PCREL, R_M32R_18_PCREL_RELA },
01287 { BFD_RELOC_M32R_26_PCREL, R_M32R_26_PCREL_RELA },
01288 { BFD_RELOC_M32R_HI16_ULO, R_M32R_HI16_ULO_RELA },
01289 { BFD_RELOC_M32R_HI16_SLO, R_M32R_HI16_SLO_RELA },
01290 { BFD_RELOC_M32R_LO16, R_M32R_LO16_RELA },
01291 { BFD_RELOC_M32R_SDA16, R_M32R_SDA16_RELA },
01292 { BFD_RELOC_VTABLE_INHERIT, R_M32R_RELA_GNU_VTINHERIT },
01293 { BFD_RELOC_VTABLE_ENTRY, R_M32R_RELA_GNU_VTENTRY },
01294
01295 { BFD_RELOC_M32R_GOT24, R_M32R_GOT24 },
01296 { BFD_RELOC_M32R_26_PLTREL, R_M32R_26_PLTREL },
01297 { BFD_RELOC_M32R_COPY, R_M32R_COPY },
01298 { BFD_RELOC_M32R_GLOB_DAT, R_M32R_GLOB_DAT },
01299 { BFD_RELOC_M32R_JMP_SLOT, R_M32R_JMP_SLOT },
01300 { BFD_RELOC_M32R_RELATIVE, R_M32R_RELATIVE },
01301 { BFD_RELOC_M32R_GOTOFF, R_M32R_GOTOFF },
01302 { BFD_RELOC_M32R_GOTPC24, R_M32R_GOTPC24 },
01303 { BFD_RELOC_M32R_GOT16_HI_ULO, R_M32R_GOT16_HI_ULO },
01304 { BFD_RELOC_M32R_GOT16_HI_SLO, R_M32R_GOT16_HI_SLO },
01305 { BFD_RELOC_M32R_GOT16_LO, R_M32R_GOT16_LO },
01306 { BFD_RELOC_M32R_GOTPC_HI_ULO, R_M32R_GOTPC_HI_ULO },
01307 { BFD_RELOC_M32R_GOTPC_HI_SLO, R_M32R_GOTPC_HI_SLO },
01308 { BFD_RELOC_M32R_GOTPC_LO, R_M32R_GOTPC_LO },
01309 { BFD_RELOC_M32R_GOTOFF_HI_ULO, R_M32R_GOTOFF_HI_ULO },
01310 { BFD_RELOC_M32R_GOTOFF_HI_SLO, R_M32R_GOTOFF_HI_SLO },
01311 { BFD_RELOC_M32R_GOTOFF_LO, R_M32R_GOTOFF_LO },
01312 };
01313 #endif
01314
01315 static reloc_howto_type *
01316 bfd_elf32_bfd_reloc_type_lookup (abfd, code)
01317 bfd *abfd ATTRIBUTE_UNUSED;
01318 bfd_reloc_code_real_type code;
01319 {
01320 unsigned int i;
01321
01322 #ifdef USE_M32R_OLD_RELOC
01323 for (i = 0;
01324 i < sizeof (m32r_reloc_map_old) / sizeof (struct m32r_reloc_map);
01325 i++)
01326 {
01327 if (m32r_reloc_map_old[i].bfd_reloc_val == code)
01328 return &m32r_elf_howto_table[m32r_reloc_map_old[i].elf_reloc_val];
01329 }
01330 #else
01331
01332 for (i = 0;
01333 i < sizeof (m32r_reloc_map) / sizeof (struct m32r_reloc_map);
01334 i++)
01335 {
01336 if (m32r_reloc_map[i].bfd_reloc_val == code)
01337 return &m32r_elf_howto_table[m32r_reloc_map[i].elf_reloc_val];
01338 }
01339 #endif
01340
01341 return NULL;
01342 }
01343
01344
01345
01346 static void
01347 m32r_info_to_howto_rel (abfd, cache_ptr, dst)
01348 bfd *abfd ATTRIBUTE_UNUSED;
01349 arelent *cache_ptr;
01350 Elf_Internal_Rela *dst;
01351 {
01352 unsigned int r_type;
01353
01354 r_type = ELF32_R_TYPE (dst->r_info);
01355 BFD_ASSERT (ELF32_R_TYPE(dst->r_info) <= (unsigned int) R_M32R_GNU_VTENTRY);
01356 cache_ptr->howto = &m32r_elf_howto_table[r_type];
01357 }
01358
01359 static void
01360 m32r_info_to_howto (abfd, cache_ptr, dst)
01361 bfd *abfd ATTRIBUTE_UNUSED;
01362 arelent *cache_ptr;
01363 Elf_Internal_Rela *dst;
01364 {
01365 BFD_ASSERT ((ELF32_R_TYPE(dst->r_info) == (unsigned int) R_M32R_NONE)
01366 || ((ELF32_R_TYPE(dst->r_info) > (unsigned int) R_M32R_GNU_VTENTRY)
01367 && (ELF32_R_TYPE(dst->r_info) < (unsigned int) R_M32R_max)));
01368 cache_ptr->howto = &m32r_elf_howto_table[ELF32_R_TYPE(dst->r_info)];
01369 }
01370
01371
01372
01373
01374
01375 bfd_boolean
01376 _bfd_m32r_elf_section_from_bfd_section (abfd, sec, retval)
01377 bfd *abfd ATTRIBUTE_UNUSED;
01378 asection *sec;
01379 int *retval;
01380 {
01381 if (strcmp (bfd_get_section_name (abfd, sec), ".scommon") == 0)
01382 {
01383 *retval = SHN_M32R_SCOMMON;
01384 return TRUE;
01385 }
01386 return FALSE;
01387 }
01388
01389
01390
01391
01392
01393
01394
01395 static asection m32r_elf_scom_section;
01396 static asymbol m32r_elf_scom_symbol;
01397 static asymbol *m32r_elf_scom_symbol_ptr;
01398
01399
01400
01401 void
01402 _bfd_m32r_elf_symbol_processing (abfd, asym)
01403 bfd *abfd ATTRIBUTE_UNUSED;
01404 asymbol *asym;
01405 {
01406 elf_symbol_type *elfsym;
01407
01408 elfsym = (elf_symbol_type *) asym;
01409
01410 switch (elfsym->internal_elf_sym.st_shndx)
01411 {
01412 case SHN_M32R_SCOMMON:
01413 if (m32r_elf_scom_section.name == NULL)
01414 {
01415
01416 m32r_elf_scom_section.name = ".scommon";
01417 m32r_elf_scom_section.flags = SEC_IS_COMMON;
01418 m32r_elf_scom_section.output_section = &m32r_elf_scom_section;
01419 m32r_elf_scom_section.symbol = &m32r_elf_scom_symbol;
01420 m32r_elf_scom_section.symbol_ptr_ptr = &m32r_elf_scom_symbol_ptr;
01421 m32r_elf_scom_symbol.name = ".scommon";
01422 m32r_elf_scom_symbol.flags = BSF_SECTION_SYM;
01423 m32r_elf_scom_symbol.section = &m32r_elf_scom_section;
01424 m32r_elf_scom_symbol_ptr = &m32r_elf_scom_symbol;
01425 }
01426 asym->section = &m32r_elf_scom_section;
01427 asym->value = elfsym->internal_elf_sym.st_size;
01428 break;
01429 }
01430 }
01431
01432
01433
01434
01435
01436
01437 static bfd_boolean
01438 m32r_elf_add_symbol_hook (abfd, info, sym, namep, flagsp, secp, valp)
01439 bfd *abfd;
01440 struct bfd_link_info *info;
01441 Elf_Internal_Sym *sym;
01442 const char **namep;
01443 flagword *flagsp ATTRIBUTE_UNUSED;
01444 asection **secp;
01445 bfd_vma *valp;
01446 {
01447 if (! info->relocatable
01448 && (*namep)[0] == '_' && (*namep)[1] == 'S'
01449 && strcmp (*namep, "_SDA_BASE_") == 0
01450 && is_elf_hash_table (info->hash))
01451 {
01452
01453
01454
01455
01456
01457 struct elf_link_hash_entry *h;
01458 struct bfd_link_hash_entry *bh;
01459 asection *s = bfd_get_section_by_name (abfd, ".sdata");
01460
01461
01462
01463 if (s == NULL)
01464 {
01465 flagword flags = (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS
01466 | SEC_IN_MEMORY | SEC_LINKER_CREATED);
01467
01468 s = bfd_make_section_anyway (abfd, ".sdata");
01469 if (s == NULL)
01470 return FALSE;
01471 bfd_set_section_flags (abfd, s, flags);
01472 bfd_set_section_alignment (abfd, s, 2);
01473 }
01474
01475 bh = bfd_link_hash_lookup (info->hash, "_SDA_BASE_",
01476 FALSE, FALSE, FALSE);
01477
01478 if ((bh == NULL || bh->type == bfd_link_hash_undefined)
01479 && !(_bfd_generic_link_add_one_symbol (info,
01480 abfd,
01481 "_SDA_BASE_",
01482 BSF_GLOBAL,
01483 s,
01484 (bfd_vma) 32768,
01485 (const char *) NULL,
01486 FALSE,
01487 get_elf_backend_data (abfd)->collect,
01488 &bh)))
01489 return FALSE;
01490 h = (struct elf_link_hash_entry *) bh;
01491 h->type = STT_OBJECT;
01492 }
01493
01494 switch (sym->st_shndx)
01495 {
01496 case SHN_M32R_SCOMMON:
01497 *secp = bfd_make_section_old_way (abfd, ".scommon");
01498 (*secp)->flags |= SEC_IS_COMMON;
01499 *valp = sym->st_size;
01500 break;
01501 }
01502
01503 return TRUE;
01504 }
01505
01506
01507
01508
01509
01510
01511
01512 static bfd_reloc_status_type
01513 m32r_elf_final_sda_base (output_bfd, info, error_message, psb)
01514 bfd *output_bfd;
01515 struct bfd_link_info *info;
01516 const char **error_message;
01517 bfd_vma *psb;
01518 {
01519 if (elf_gp (output_bfd) == 0)
01520 {
01521 struct bfd_link_hash_entry *h;
01522
01523 h = bfd_link_hash_lookup (info->hash, "_SDA_BASE_", FALSE, FALSE, TRUE);
01524 if (h != (struct bfd_link_hash_entry *) NULL
01525 && h->type == bfd_link_hash_defined)
01526 elf_gp (output_bfd) = (h->u.def.value
01527 + h->u.def.section->output_section->vma
01528 + h->u.def.section->output_offset);
01529 else
01530 {
01531
01532 *psb = elf_gp (output_bfd) = 4;
01533 *error_message =
01534 (const char *) _("SDA relocation when _SDA_BASE_ not defined");
01535 return bfd_reloc_dangerous;
01536 }
01537 }
01538 *psb = elf_gp (output_bfd);
01539 return bfd_reloc_ok;
01540 }
01541
01542
01543 #define elf_m32r_sizeof_plt(info) PLT_ENTRY_SIZE
01544
01545
01546
01547
01548
01549
01550
01551
01552
01553
01554 struct elf_m32r_pcrel_relocs_copied
01555 {
01556
01557 struct elf_m32r_pcrel_relocs_copied *next;
01558
01559 asection *section;
01560
01561 bfd_size_type count;
01562 };
01563
01564
01565
01566
01567
01568
01569
01570 struct elf_m32r_dyn_relocs
01571 {
01572 struct elf_m32r_dyn_relocs *next;
01573
01574
01575 asection *sec;
01576
01577
01578 bfd_size_type count;
01579
01580
01581 bfd_size_type pc_count;
01582 };
01583
01584
01585
01586
01587 struct elf_m32r_link_hash_entry
01588 {
01589 struct elf_link_hash_entry root;
01590
01591
01592 struct elf_m32r_dyn_relocs *dyn_relocs;
01593
01594
01595
01596
01597
01598 };
01599
01600
01601
01602 struct elf_m32r_link_hash_table
01603 {
01604 struct elf_link_hash_table root;
01605
01606
01607 asection *sgot;
01608 asection *sgotplt;
01609 asection *srelgot;
01610 asection *splt;
01611 asection *srelplt;
01612 asection *sdynbss;
01613 asection *srelbss;
01614
01615
01616 struct sym_sec_cache sym_sec;
01617 };
01618
01619
01620
01621 #define m32r_elf_link_hash_traverse(table, func, info) \
01622 (elf_link_hash_traverse \
01623 (&(table)->root, \
01624 (bfd_boolean (*) PARAMS ((struct elf_link_hash_entry *, PTR))) (func), \
01625 (info)))
01626
01627
01628
01629
01630 #define m32r_elf_hash_table(p) \
01631 ((struct elf_m32r_link_hash_table *) ((p)->hash))
01632
01633
01634 static struct bfd_hash_entry *
01635 m32r_elf_link_hash_newfunc (struct bfd_hash_entry *, struct bfd_hash_table *,
01636 const char * );
01637
01638 static struct bfd_hash_entry *
01639 m32r_elf_link_hash_newfunc (entry, table, string)
01640 struct bfd_hash_entry *entry;
01641 struct bfd_hash_table *table;
01642 const char *string;
01643 {
01644 struct elf_m32r_link_hash_entry *ret =
01645 (struct elf_m32r_link_hash_entry *) entry;
01646
01647
01648
01649 if (ret == (struct elf_m32r_link_hash_entry *) NULL)
01650 ret = ((struct elf_m32r_link_hash_entry *)
01651 bfd_hash_allocate (table,
01652 sizeof (struct elf_m32r_link_hash_entry)));
01653 if (ret == (struct elf_m32r_link_hash_entry *) NULL)
01654 return (struct bfd_hash_entry *) ret;
01655
01656
01657 ret = ((struct elf_m32r_link_hash_entry *)
01658 _bfd_elf_link_hash_newfunc ((struct bfd_hash_entry *) ret,
01659 table, string));
01660 if (ret != (struct elf_m32r_link_hash_entry *) NULL)
01661 {
01662 struct elf_m32r_link_hash_entry *eh;
01663
01664 eh = (struct elf_m32r_link_hash_entry *) ret;
01665 eh->dyn_relocs = NULL;
01666
01667
01668 }
01669
01670 return (struct bfd_hash_entry *) ret;
01671 }
01672
01673
01674 static struct bfd_link_hash_table *m32r_elf_link_hash_table_create (bfd *);
01675
01676 static struct bfd_link_hash_table *
01677 m32r_elf_link_hash_table_create (abfd)
01678 bfd *abfd;
01679 {
01680 struct elf_m32r_link_hash_table *ret;
01681 bfd_size_type amt = sizeof (struct elf_m32r_link_hash_table);
01682
01683 ret = (struct elf_m32r_link_hash_table *) bfd_malloc (amt);
01684 if (ret == (struct elf_m32r_link_hash_table *) NULL)
01685 return NULL;
01686
01687 if (! _bfd_elf_link_hash_table_init (&ret->root, abfd,
01688 m32r_elf_link_hash_newfunc))
01689 {
01690 free (ret);
01691 return NULL;
01692 }
01693
01694 ret->sgot = NULL;
01695 ret->sgotplt = NULL;
01696 ret->srelgot = NULL;
01697 ret->splt = NULL;
01698 ret->srelplt = NULL;
01699 ret->sdynbss = NULL;
01700 ret->srelbss = NULL;
01701 ret->sym_sec.abfd = NULL;
01702
01703 return &ret->root.root;
01704 }
01705
01706
01707
01708 static bfd_boolean create_got_section (bfd *, struct bfd_link_info *);
01709
01710 static bfd_boolean
01711 create_got_section (dynobj, info)
01712 bfd *dynobj;
01713 struct bfd_link_info *info;
01714 {
01715 struct elf_m32r_link_hash_table *htab;
01716
01717 if (! _bfd_elf_create_got_section (dynobj, info))
01718 return FALSE;
01719
01720 htab = m32r_elf_hash_table (info);
01721 htab->sgot = bfd_get_section_by_name (dynobj, ".got");
01722 htab->sgotplt = bfd_get_section_by_name (dynobj, ".got.plt");
01723 if (! htab->sgot || ! htab->sgotplt)
01724 abort ();
01725
01726 htab->srelgot = bfd_make_section (dynobj, ".rela.got");
01727 if (htab->srelgot == NULL
01728 || ! bfd_set_section_flags (dynobj, htab->srelgot,
01729 (SEC_ALLOC
01730 | SEC_LOAD
01731 | SEC_HAS_CONTENTS
01732 | SEC_IN_MEMORY
01733 | SEC_LINKER_CREATED
01734 | SEC_READONLY))
01735 || ! bfd_set_section_alignment (dynobj, htab->srelgot, 2))
01736 return FALSE;
01737
01738 return TRUE;
01739 }
01740
01741
01742
01743 static bfd_boolean
01744 m32r_elf_create_dynamic_sections (abfd, info)
01745 bfd *abfd;
01746 struct bfd_link_info *info;
01747 {
01748 struct elf_m32r_link_hash_table *htab;
01749 flagword flags, pltflags;
01750 register asection *s;
01751 const struct elf_backend_data *bed = get_elf_backend_data (abfd);
01752 int ptralign = 2;
01753
01754 htab = m32r_elf_hash_table (info);
01755
01756
01757
01758
01759 flags = (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS | SEC_IN_MEMORY
01760 | SEC_LINKER_CREATED);
01761
01762 pltflags = flags;
01763 pltflags |= SEC_CODE;
01764 if (bed->plt_not_loaded)
01765 pltflags &= ~ (SEC_LOAD | SEC_HAS_CONTENTS);
01766 if (bed->plt_readonly)
01767 pltflags |= SEC_READONLY;
01768
01769 s = bfd_make_section (abfd, ".plt");
01770 htab->splt = s;
01771 if (s == NULL
01772 || ! bfd_set_section_flags (abfd, s, pltflags)
01773 || ! bfd_set_section_alignment (abfd, s, bed->plt_alignment))
01774 return FALSE;
01775
01776 if (bed->want_plt_sym)
01777 {
01778
01779
01780 struct bfd_link_hash_entry *bh = NULL;
01781 struct elf_link_hash_entry *h;
01782 if (! (_bfd_generic_link_add_one_symbol
01783 (info, abfd, "_PROCEDURE_LINKAGE_TABLE_", BSF_GLOBAL, s,
01784 (bfd_vma) 0, (const char *) NULL, FALSE,
01785 get_elf_backend_data (abfd)->collect, &bh)))
01786 return FALSE;
01787 h = (struct elf_link_hash_entry *) bh;
01788 h->def_regular = 1;
01789 h->type = STT_OBJECT;
01790
01791 if (info->shared
01792 && ! bfd_elf_link_record_dynamic_symbol (info, h))
01793 return FALSE;
01794 }
01795
01796 s = bfd_make_section (abfd,
01797 bed->default_use_rela_p ? ".rela.plt" : ".rel.plt");
01798 htab->srelplt = s;
01799 if (s == NULL
01800 || ! bfd_set_section_flags (abfd, s, flags | SEC_READONLY)
01801 || ! bfd_set_section_alignment (abfd, s, ptralign))
01802 return FALSE;
01803
01804 if (htab->sgot == NULL
01805 && ! create_got_section (abfd, info))
01806 return FALSE;
01807
01808 {
01809 const char *secname;
01810 char *relname;
01811 flagword secflags;
01812 asection *sec;
01813
01814 for (sec = abfd->sections; sec; sec = sec->next)
01815 {
01816 secflags = bfd_get_section_flags (abfd, sec);
01817 if ((secflags & (SEC_DATA | SEC_LINKER_CREATED))
01818 || ((secflags & SEC_HAS_CONTENTS) != SEC_HAS_CONTENTS))
01819 continue;
01820 secname = bfd_get_section_name (abfd, sec);
01821 relname = (char *) bfd_malloc ((bfd_size_type) strlen (secname) + 6);
01822 strcpy (relname, ".rela");
01823 strcat (relname, secname);
01824 if (bfd_get_section_by_name (abfd, secname))
01825 continue;
01826 s = bfd_make_section (abfd, relname);
01827 if (s == NULL
01828 || ! bfd_set_section_flags (abfd, s, flags | SEC_READONLY)
01829 || ! bfd_set_section_alignment (abfd, s, ptralign))
01830 return FALSE;
01831 }
01832 }
01833
01834 if (bed->want_dynbss)
01835 {
01836
01837
01838
01839
01840
01841
01842 s = bfd_make_section (abfd, ".dynbss");
01843 htab->sdynbss = s;
01844 if (s == NULL
01845 || ! bfd_set_section_flags (abfd, s, SEC_ALLOC))
01846 return FALSE;
01847
01848
01849
01850
01851
01852
01853
01854
01855
01856
01857
01858 if (! info->shared)
01859 {
01860 s = bfd_make_section (abfd,
01861 (bed->default_use_rela_p
01862 ? ".rela.bss" : ".rel.bss"));
01863 htab->srelbss = s;
01864 if (s == NULL
01865 || ! bfd_set_section_flags (abfd, s, flags | SEC_READONLY)
01866 || ! bfd_set_section_alignment (abfd, s, ptralign))
01867 return FALSE;
01868 }
01869 }
01870
01871 return TRUE;
01872 }
01873
01874
01875 static void m32r_elf_copy_indirect_symbol (const struct elf_backend_data *,
01876 struct elf_link_hash_entry *,
01877 struct elf_link_hash_entry *);
01878
01879 static void
01880 m32r_elf_copy_indirect_symbol (const struct elf_backend_data *bed,
01881 struct elf_link_hash_entry *dir,
01882 struct elf_link_hash_entry *ind)
01883 {
01884 struct elf_m32r_link_hash_entry *edir, *eind;
01885
01886 edir = (struct elf_m32r_link_hash_entry *) dir;
01887 eind = (struct elf_m32r_link_hash_entry *) ind;
01888
01889 if (eind->dyn_relocs != NULL)
01890 {
01891 if (edir->dyn_relocs != NULL)
01892 {
01893 struct elf_m32r_dyn_relocs **pp;
01894 struct elf_m32r_dyn_relocs *p;
01895
01896 if (ind->root.type == bfd_link_hash_indirect)
01897 abort ();
01898
01899
01900
01901 for (pp = &eind->dyn_relocs; (p = *pp) != NULL; )
01902 {
01903 struct elf_m32r_dyn_relocs *q;
01904
01905 for (q = edir->dyn_relocs; q != NULL; q = q->next)
01906 if (q->sec == p->sec)
01907 {
01908 q->pc_count += p->pc_count;
01909 q->count += p->count;
01910 *pp = p->next;
01911 break;
01912 }
01913 if (q == NULL)
01914 pp = &p->next;
01915 }
01916 *pp = edir->dyn_relocs;
01917 }
01918
01919 edir->dyn_relocs = eind->dyn_relocs;
01920 eind->dyn_relocs = NULL;
01921 }
01922
01923
01924
01925
01926
01927
01928
01929 _bfd_elf_link_hash_copy_indirect (bed, dir, ind);
01930 }
01931
01932
01933
01934
01935
01936
01937
01938
01939 static bfd_boolean
01940 m32r_elf_adjust_dynamic_symbol (info, h)
01941 struct bfd_link_info *info;
01942 struct elf_link_hash_entry *h;
01943 {
01944 struct elf_m32r_link_hash_table *htab;
01945 struct elf_m32r_link_hash_entry *eh;
01946 struct elf_m32r_dyn_relocs *p;
01947 bfd *dynobj;
01948 asection *s;
01949 unsigned int power_of_two;
01950
01951 #ifdef DEBUG_PIC
01952 printf("m32r_elf_adjust_dynamic_symbol()\n");
01953 #endif
01954
01955 dynobj = elf_hash_table (info)->dynobj;
01956
01957
01958 BFD_ASSERT (dynobj != NULL
01959 && (h->needs_plt
01960 || h->u.weakdef != NULL
01961 || (h->def_dynamic
01962 && h->ref_regular
01963 && !h->def_regular)));
01964
01965
01966
01967
01968
01969 if (h->type == STT_FUNC
01970 || h->needs_plt)
01971 {
01972 if (! info->shared
01973 && !h->def_dynamic
01974 && !h->ref_dynamic
01975 && h->root.type != bfd_link_hash_undefweak
01976 && h->root.type != bfd_link_hash_undefined)
01977 {
01978
01979
01980
01981
01982
01983 h->plt.offset = (bfd_vma) -1;
01984 h->needs_plt = 0;
01985 }
01986
01987 return TRUE;
01988 }
01989 else
01990 h->plt.offset = (bfd_vma) -1;
01991
01992
01993
01994
01995 if (h->u.weakdef != NULL)
01996 {
01997 BFD_ASSERT (h->u.weakdef->root.type == bfd_link_hash_defined
01998 || h->u.weakdef->root.type == bfd_link_hash_defweak);
01999 h->root.u.def.section = h->u.weakdef->root.u.def.section;
02000 h->root.u.def.value = h->u.weakdef->root.u.def.value;
02001 return TRUE;
02002 }
02003
02004
02005
02006
02007
02008
02009
02010
02011 if (info->shared)
02012 return TRUE;
02013
02014
02015
02016 if (!h->non_got_ref)
02017 return TRUE;
02018
02019
02020 if (info->nocopyreloc)
02021 {
02022 h->non_got_ref = 0;
02023 return TRUE;
02024 }
02025
02026 eh = (struct elf_m32r_link_hash_entry *) h;
02027 for (p = eh->dyn_relocs; p != NULL; p = p->next)
02028 {
02029 s = p->sec->output_section;
02030 if (s != NULL && (s->flags & (SEC_READONLY | SEC_HAS_CONTENTS)) != 0)
02031 break;
02032 }
02033
02034
02035
02036
02037 if (p == NULL)
02038 {
02039 h->non_got_ref = 0;
02040 return TRUE;
02041 }
02042
02043
02044
02045
02046
02047
02048
02049
02050
02051
02052
02053 htab = m32r_elf_hash_table (info);
02054 s = htab->sdynbss;
02055 BFD_ASSERT (s != NULL);
02056
02057
02058
02059
02060
02061 if ((h->root.u.def.section->flags & SEC_ALLOC) != 0)
02062 {
02063 asection *srel;
02064
02065 srel = htab->srelbss;
02066 BFD_ASSERT (srel != NULL);
02067 srel->size += sizeof (Elf32_External_Rela);
02068 h->needs_copy = 1;
02069 }
02070
02071
02072
02073 power_of_two = bfd_log2 (h->size);
02074 if (power_of_two > 3)
02075 power_of_two = 3;
02076
02077
02078 s->size = BFD_ALIGN (s->size, (bfd_size_type) (1 << power_of_two));
02079 if (power_of_two > bfd_get_section_alignment (dynobj, s))
02080 {
02081 if (! bfd_set_section_alignment (dynobj, s, power_of_two))
02082 return FALSE;
02083 }
02084
02085
02086 h->root.u.def.section = s;
02087 h->root.u.def.value = s->size;
02088
02089
02090 s->size += h->size;
02091
02092 return TRUE;
02093 }
02094
02095
02096
02097
02098 static bfd_boolean
02099 allocate_dynrelocs (h, inf)
02100 struct elf_link_hash_entry *h;
02101 PTR inf;
02102 {
02103 struct bfd_link_info *info;
02104 struct elf_m32r_link_hash_table *htab;
02105 struct elf_m32r_link_hash_entry *eh;
02106 struct elf_m32r_dyn_relocs *p;
02107
02108 if (h->root.type == bfd_link_hash_indirect)
02109 return TRUE;
02110
02111 if (h->root.type == bfd_link_hash_warning)
02112
02113
02114
02115 h = (struct elf_link_hash_entry *) h->root.u.i.link;
02116
02117 info = (struct bfd_link_info *) inf;
02118 htab = m32r_elf_hash_table (info);
02119
02120 eh = (struct elf_m32r_link_hash_entry *) h;
02121
02122
02123
02124
02125
02126
02127
02128
02129
02130
02131
02132 if (htab->root.dynamic_sections_created
02133 && h->plt.refcount > 0)
02134 {
02135
02136
02137 if (h->dynindx == -1
02138 && !h->forced_local)
02139 {
02140 if (! bfd_elf_link_record_dynamic_symbol (info, h))
02141 return FALSE;
02142 }
02143
02144 if (WILL_CALL_FINISH_DYNAMIC_SYMBOL (1, info->shared, h))
02145 {
02146 asection *s = htab->splt;
02147
02148
02149
02150 if (s->size == 0)
02151 s->size += PLT_ENTRY_SIZE;
02152
02153 h->plt.offset = s->size;
02154
02155
02156
02157
02158
02159
02160 if (! info->shared
02161 && !h->def_regular)
02162 {
02163 h->root.u.def.section = s;
02164 h->root.u.def.value = h->plt.offset;
02165 }
02166
02167
02168 s->size += PLT_ENTRY_SIZE;
02169
02170
02171
02172 htab->sgotplt->size += 4;
02173
02174
02175 htab->srelplt->size += sizeof (Elf32_External_Rela);
02176 }
02177 else
02178 {
02179 h->plt.offset = (bfd_vma) -1;
02180 h->needs_plt = 0;
02181 }
02182 }
02183 else
02184 {
02185 h->plt.offset = (bfd_vma) -1;
02186 h->needs_plt = 0;
02187 }
02188
02189 if (h->got.refcount > 0)
02190 {
02191 asection *s;
02192 bfd_boolean dyn;
02193
02194
02195
02196 if (h->dynindx == -1
02197 && !h->forced_local)
02198 {
02199 if (! bfd_elf_link_record_dynamic_symbol (info, h))
02200 return FALSE;
02201 }
02202
02203 s = htab->sgot;
02204
02205 h->got.offset = s->size;
02206 s->size += 4;
02207 dyn = htab->root.dynamic_sections_created;
02208 if (WILL_CALL_FINISH_DYNAMIC_SYMBOL (dyn, info->shared, h))
02209 htab->srelgot->size += sizeof (Elf32_External_Rela);
02210 }
02211 else
02212 h->got.offset = (bfd_vma) -1;
02213
02214 if (eh->dyn_relocs == NULL)
02215 return TRUE;
02216
02217
02218
02219
02220
02221
02222
02223 if (info->shared)
02224 {
02225 if (h->def_regular
02226 && (h->forced_local
02227 || info->symbolic))
02228 {
02229 struct elf_m32r_dyn_relocs **pp;
02230 for (pp = &eh->dyn_relocs; (p = *pp) != NULL; )
02231 {
02232 p->count -= p->pc_count;
02233 p->pc_count = 0;
02234 if (p->count == 0)
02235 *pp = p->next;
02236 else
02237 pp = &p->next;
02238 }
02239 }
02240 }
02241 else
02242 {
02243
02244
02245
02246
02247 if (!h->non_got_ref
02248 && ((h->def_dynamic
02249 && !h->def_regular)
02250 || (htab->root.dynamic_sections_created
02251 && (h->root.type == bfd_link_hash_undefweak
02252 || h->root.type == bfd_link_hash_undefined))))
02253 {
02254
02255
02256 if (h->dynindx == -1
02257 && !h->forced_local)
02258 {
02259 if (! bfd_elf_link_record_dynamic_symbol (info, h))
02260 return FALSE;
02261 }
02262
02263
02264
02265 if (h->dynindx != -1)
02266 goto keep;
02267 }
02268
02269 eh->dyn_relocs = NULL;
02270
02271 keep: ;
02272 }
02273
02274
02275 for (p = eh->dyn_relocs; p != NULL; p = p->next)
02276 {
02277 asection *sreloc = elf_section_data (p->sec)->sreloc;
02278 sreloc->size += p->count * sizeof (Elf32_External_Rela);
02279 }
02280
02281 return TRUE;
02282 }
02283
02284
02285 static bfd_boolean
02286 readonly_dynrelocs (h, inf)
02287 struct elf_link_hash_entry *h;
02288 PTR inf;
02289 {
02290 struct elf_m32r_link_hash_entry *eh;
02291 struct elf_m32r_dyn_relocs *p;
02292
02293 if (h->root.type == bfd_link_hash_warning)
02294 h = (struct elf_link_hash_entry *) h->root.u.i.link;
02295
02296 eh = (struct elf_m32r_link_hash_entry *) h;
02297 for (p = eh->dyn_relocs; p != NULL; p = p->next)
02298 {
02299 asection *s = p->sec->output_section;
02300
02301 if (s != NULL && (s->flags & SEC_READONLY) != 0)
02302 {
02303 struct bfd_link_info *info = (struct bfd_link_info *) inf;
02304
02305 info->flags |= DF_TEXTREL;
02306
02307
02308 return FALSE;
02309 }
02310 }
02311 return TRUE;
02312 }
02313
02314
02315
02316 static bfd_boolean
02317 m32r_elf_size_dynamic_sections (output_bfd, info)
02318 bfd *output_bfd ATTRIBUTE_UNUSED;
02319 struct bfd_link_info *info;
02320 {
02321 struct elf_m32r_link_hash_table *htab;
02322 bfd *dynobj;
02323 asection *s;
02324 bfd_boolean relocs;
02325 bfd *ibfd;
02326
02327 #ifdef DEBUG_PIC
02328 printf("m32r_elf_size_dynamic_sections()\n");
02329 #endif
02330
02331 htab = m32r_elf_hash_table (info);
02332 dynobj = htab->root.dynobj;
02333 BFD_ASSERT (dynobj != NULL);
02334
02335 if (htab->root.dynamic_sections_created)
02336 {
02337
02338 if (! info->shared)
02339 {
02340 s = bfd_get_section_by_name (dynobj, ".interp");
02341 BFD_ASSERT (s != NULL);
02342 s->size = sizeof ELF_DYNAMIC_INTERPRETER;
02343 s->contents = (unsigned char *) ELF_DYNAMIC_INTERPRETER;
02344 }
02345 }
02346
02347
02348
02349 for (ibfd = info->input_bfds; ibfd != NULL; ibfd = ibfd->link_next)
02350 {
02351 bfd_signed_vma *local_got;
02352 bfd_signed_vma *end_local_got;
02353 bfd_size_type locsymcount;
02354 Elf_Internal_Shdr *symtab_hdr;
02355 asection *srel;
02356
02357 if (bfd_get_flavour (ibfd) != bfd_target_elf_flavour)
02358 continue;
02359
02360 for (s = ibfd->sections; s != NULL; s = s->next)
02361 {
02362 struct elf_m32r_dyn_relocs *p;
02363
02364 for (p = ((struct elf_m32r_dyn_relocs *)
02365 elf_section_data (s)->local_dynrel);
02366 p != NULL;
02367 p = p->next)
02368 {
02369 if (! bfd_is_abs_section (p->sec)
02370 && bfd_is_abs_section (p->sec->output_section))
02371 {
02372
02373
02374
02375
02376 }
02377 else if (p->count != 0)
02378 {
02379 srel = elf_section_data (p->sec)->sreloc;
02380 srel->size += p->count * sizeof (Elf32_External_Rela);
02381 if ((p->sec->output_section->flags & SEC_READONLY) != 0)
02382 info->flags |= DF_TEXTREL;
02383 }
02384 }
02385 }
02386
02387 local_got = elf_local_got_refcounts (ibfd);
02388 if (!local_got)
02389 continue;
02390
02391 symtab_hdr = &elf_tdata (ibfd)->symtab_hdr;
02392 locsymcount = symtab_hdr->sh_info;
02393 end_local_got = local_got + locsymcount;
02394 s = htab->sgot;
02395 srel = htab->srelgot;
02396 for (; local_got < end_local_got; ++local_got)
02397 {
02398 if (*local_got > 0)
02399 {
02400 *local_got = s->size;
02401 s->size += 4;
02402 if (info->shared)
02403 srel->size += sizeof (Elf32_External_Rela);
02404 }
02405 else
02406 *local_got = (bfd_vma) -1;
02407 }
02408 }
02409
02410
02411
02412 elf_link_hash_traverse (&htab->root, allocate_dynrelocs, (PTR) info);
02413
02414
02415
02416 relocs = FALSE;
02417 for (s = dynobj->sections; s != NULL; s = s->next)
02418 {
02419 if ((s->flags & SEC_LINKER_CREATED) == 0)
02420 continue;
02421
02422 if (s == htab->splt
02423 || s == htab->sgot
02424 || s == htab->sgotplt)
02425 {
02426
02427
02428 }
02429 else if (strncmp (bfd_get_section_name (dynobj, s), ".rela", 5) == 0)
02430 {
02431 if (s->size != 0 && s != htab->srelplt)
02432 relocs = TRUE;
02433
02434
02435
02436 s->reloc_count = 0;
02437 }
02438 else
02439 {
02440
02441 continue;
02442 }
02443
02444 if (s->size == 0)
02445 {
02446
02447
02448
02449
02450
02451
02452
02453
02454
02455 _bfd_strip_section_from_output (info, s);
02456 continue;
02457 }
02458
02459
02460
02461
02462
02463
02464 s->contents = (bfd_byte *) bfd_zalloc (dynobj, s->size);
02465 if (s->contents == NULL)
02466 return FALSE;
02467 }
02468
02469 if (htab->root.dynamic_sections_created)
02470 {
02471
02472
02473
02474
02475
02476 #define add_dynamic_entry(TAG, VAL) \
02477 _bfd_elf_add_dynamic_entry (info, TAG, VAL)
02478
02479 if (! info->shared)
02480 {
02481 if (! add_dynamic_entry (DT_DEBUG, 0))
02482 return FALSE;
02483 }
02484
02485 if (htab->splt->size != 0)
02486 {
02487 if (! add_dynamic_entry (DT_PLTGOT, 0)
02488 || ! add_dynamic_entry (DT_PLTRELSZ, 0)
02489 || ! add_dynamic_entry (DT_PLTREL, DT_RELA)
02490 || ! add_dynamic_entry (DT_JMPREL, 0))
02491 return FALSE;
02492 }
02493
02494 if (relocs)
02495 {
02496 if (! add_dynamic_entry (DT_RELA, 0)
02497 || ! add_dynamic_entry (DT_RELASZ, 0)
02498 || ! add_dynamic_entry (DT_RELAENT,
02499 sizeof (Elf32_External_Rela)))
02500 return FALSE;
02501
02502
02503
02504 if ((info->flags & DF_TEXTREL) == 0)
02505 elf_link_hash_traverse (&htab->root, readonly_dynrelocs,
02506 (PTR) info);
02507
02508 if ((info->flags & DF_TEXTREL) != 0)
02509 {
02510 if (! add_dynamic_entry (DT_TEXTREL, 0))
02511 return FALSE;
02512 }
02513 }
02514 }
02515 #undef add_dynamic_entry
02516
02517 return TRUE;
02518 }
02519
02520
02521
02522
02523
02524
02525
02526
02527
02528
02529
02530
02531
02532
02533
02534
02535
02536
02537
02538
02539
02540
02541
02542
02543
02544
02545
02546
02547
02548
02549
02550
02551
02552 static bfd_boolean
02553 m32r_elf_relocate_section (output_bfd, info, input_bfd, input_section,
02554 contents, relocs, local_syms, local_sections)
02555 bfd *output_bfd ATTRIBUTE_UNUSED;
02556 struct bfd_link_info *info;
02557 bfd *input_bfd;
02558 asection *input_section;
02559 bfd_byte *contents;
02560 Elf_Internal_Rela *relocs;
02561 Elf_Internal_Sym *local_syms;
02562 asection **local_sections;
02563 {
02564 Elf_Internal_Shdr *symtab_hdr = &elf_tdata (input_bfd)->symtab_hdr;
02565 struct elf_link_hash_entry **sym_hashes = elf_sym_hashes (input_bfd);
02566 Elf_Internal_Rela *rel, *relend;
02567
02568 bfd_boolean ret = TRUE;
02569
02570 struct elf_m32r_link_hash_table *htab = m32r_elf_hash_table (info);
02571 bfd *dynobj;
02572 bfd_vma *local_got_offsets;
02573 asection *sgot, *splt, *sreloc;
02574 bfd_vma high_address = bfd_get_section_limit (input_bfd, input_section);
02575
02576 dynobj = htab->root.dynobj;
02577 local_got_offsets = elf_local_got_offsets (input_bfd);
02578
02579 sgot = htab->sgot;
02580 splt = htab->splt;
02581 sreloc = NULL;
02582
02583 rel = relocs;
02584 relend = relocs + input_section->reloc_count;
02585 for (; rel < relend; rel++)
02586 {
02587 int r_type;
02588 reloc_howto_type *howto;
02589 unsigned long r_symndx;
02590 struct elf_link_hash_entry *h;
02591
02592
02593
02594
02595 bfd_vma addend = rel->r_addend;
02596 bfd_vma offset = rel->r_offset;
02597 Elf_Internal_Sym *sym;
02598 asection *sec;
02599 const char *sym_name;
02600 bfd_reloc_status_type r;
02601 const char *errmsg = NULL;
02602 bfd_boolean use_rel = FALSE;
02603
02604 h = NULL;
02605 r_type = ELF32_R_TYPE (rel->r_info);
02606 if (r_type < 0 || r_type >= (int) R_M32R_max)
02607 {
02608 (*_bfd_error_handler) (_("%B: unknown relocation type %d"),
02609 input_bfd,
02610 (int) r_type);
02611 bfd_set_error (bfd_error_bad_value);
02612 ret = FALSE;
02613 continue;
02614 }
02615
02616 if (r_type == R_M32R_GNU_VTENTRY
02617 || r_type == R_M32R_GNU_VTINHERIT
02618 || r_type == R_M32R_NONE
02619 || r_type == R_M32R_RELA_GNU_VTENTRY
02620 || r_type == R_M32R_RELA_GNU_VTINHERIT)
02621 continue;
02622
02623 if (r_type <= R_M32R_GNU_VTENTRY)
02624 use_rel = TRUE;
02625
02626 howto = m32r_elf_howto_table + r_type;
02627 r_symndx = ELF32_R_SYM (rel->r_info);
02628
02629 if (info->relocatable && use_rel)
02630 {
02631
02632
02633
02634
02635 sec = NULL;
02636 if (r_symndx >= symtab_hdr->sh_info)
02637 {
02638
02639 continue;
02640 }
02641
02642
02643 sym = local_syms + r_symndx;
02644 sym_name = "<local symbol>";
02645
02646 if (ELF_ST_TYPE (sym->st_info) != STT_SECTION)
02647 {
02648
02649 continue;
02650 }
02651
02652 sec = local_sections[r_symndx];
02653 addend += sec->output_offset + sym->st_value;
02654
02655
02656
02657 if (! howto->partial_inplace)
02658 continue;
02659
02660
02661 if (r_type != R_M32R_HI16_SLO && r_type != R_M32R_HI16_ULO)
02662 r = _bfd_relocate_contents (howto, input_bfd,
02663 addend, contents + offset);
02664 else
02665 {
02666 Elf_Internal_Rela *lorel;
02667
02668
02669
02670
02671 for (lorel = rel + 1;
02672 (lorel < relend
02673 && (ELF32_R_TYPE (lorel->r_info) == R_M32R_HI16_SLO
02674 || ELF32_R_TYPE (lorel->r_info) == R_M32R_HI16_ULO));
02675 lorel++)
02676 continue;
02677 if (lorel < relend
02678 && ELF32_R_TYPE (lorel->r_info) == R_M32R_LO16)
02679 {
02680 m32r_elf_relocate_hi16 (input_bfd, r_type, rel, lorel,
02681 contents, addend);
02682 r = bfd_reloc_ok;
02683 }
02684 else
02685 r = _bfd_relocate_contents (howto, input_bfd,
02686 addend, contents + offset);
02687 }
02688 }
02689 else
02690 {
02691 bfd_vma relocation;
02692
02693
02694 sym = NULL;
02695 sec = NULL;
02696 h = NULL;
02697
02698 if (r_symndx < symtab_hdr->sh_info)
02699 {
02700
02701 sym = local_syms + r_symndx;
02702 sec = local_sections[r_symndx];
02703 sym_name = "<local symbol>";
02704
02705 if (!use_rel)
02706 {
02707 relocation = _bfd_elf_rela_local_sym (output_bfd, sym, &sec, rel);
02708 addend = rel->r_addend;
02709
02710 if (info->relocatable)
02711 {
02712
02713
02714
02715
02716 if (ELF_ST_TYPE (sym->st_info) == STT_SECTION)
02717 rel->r_addend += sec->output_offset + sym->st_value;
02718
02719 continue;
02720 }
02721 }
02722 else
02723 {
02724 relocation = (sec->output_section->vma
02725 + sec->output_offset
02726 + sym->st_value);
02727 }
02728 }
02729 else
02730 {
02731
02732 if (info->relocatable && !use_rel)
02733 continue;
02734
02735 h = sym_hashes[r_symndx - symtab_hdr->sh_info];
02736 while (h->root.type == bfd_link_hash_indirect
02737 || h->root.type == bfd_link_hash_warning)
02738 h = (struct elf_link_hash_entry *) h->root.u.i.link;
02739 sym_name = h->root.root.string;
02740
02741 if (h->root.type == bfd_link_hash_defined
02742 || h->root.type == bfd_link_hash_defweak)
02743 {
02744 bfd_boolean dyn;
02745 sec = h->root.u.def.section;
02746
02747 dyn = htab->root.dynamic_sections_created;
02748 sec = h->root.u.def.section;
02749 if (r_type == R_M32R_GOTPC24
02750 || (r_type == R_M32R_GOTPC_HI_ULO
02751 || r_type == R_M32R_GOTPC_HI_SLO
02752 || r_type == R_M32R_GOTPC_LO)
02753 || (r_type == R_M32R_26_PLTREL
02754 && h->plt.offset != (bfd_vma) -1)
02755 || ((r_type == R_M32R_GOT24
02756 || r_type == R_M32R_GOT16_HI_ULO
02757 || r_type == R_M32R_GOT16_HI_SLO
02758 || r_type == R_M32R_GOT16_LO)
02759 && WILL_CALL_FINISH_DYNAMIC_SYMBOL (dyn,
02760 info->shared, h)
02761 && (! info->shared
02762 || (! info->symbolic && h->dynindx != -1)
02763 || !h->def_regular))
02764 || (info->shared
02765 && ((! info->symbolic && h->dynindx != -1)
02766 || !h->def_regular)
02767 && (((r_type == R_M32R_16_RELA
02768 || r_type == R_M32R_32_RELA
02769 || r_type == R_M32R_24_RELA
02770 || r_type == R_M32R_HI16_ULO_RELA
02771 || r_type == R_M32R_HI16_SLO_RELA
02772 || r_type == R_M32R_LO16_RELA)
02773 && !h->forced_local)
02774 || r_type == R_M32R_10_PCREL_RELA
02775 || r_type == R_M32R_18_PCREL_RELA
02776 || r_type == R_M32R_26_PCREL_RELA)
02777 && ((input_section->flags & SEC_ALLOC) != 0
02778
02779
02780
02781
02782 || ((input_section->flags & SEC_DEBUGGING) != 0
02783 && h->def_dynamic))))
02784 {
02785
02786
02787
02788 relocation = 0;
02789 }
02790 else if (sec->output_section == NULL)
02791 {
02792 (*_bfd_error_handler)
02793 (_("%s: warning: unresolvable relocation against symbol `%s' from %s section"),
02794 bfd_get_filename (input_bfd), h->root.root.string,
02795 bfd_get_section_name (input_bfd, input_section));
02796
02797 relocation = 0;
02798 }
02799 else
02800 relocation = (h->root.u.def.value
02801 + sec->output_section->vma
02802 + sec->output_offset);
02803 }
02804 else if (h->root.type == bfd_link_hash_undefweak)
02805 relocation = 0;
02806 else if (info->unresolved_syms_in_objects == RM_IGNORE
02807 && ELF_ST_VISIBILITY (h->other) == STV_DEFAULT)
02808 relocation = 0;
02809 else
02810 {
02811 if (! ((*info->callbacks->undefined_symbol)
02812 (info, h->root.root.string, input_bfd,
02813 input_section, offset,
02814 (info->unresolved_syms_in_objects == RM_GENERATE_ERROR
02815 || ELF_ST_VISIBILITY (h->other)))))
02816 return FALSE;
02817 relocation = 0;
02818 }
02819 }
02820
02821
02822 if (offset > high_address)
02823 {
02824 r = bfd_reloc_outofrange;
02825 goto check_reloc;
02826 }
02827
02828 switch ((int) r_type)
02829 {
02830 case R_M32R_GOTOFF:
02831
02832
02833
02834
02835
02836
02837 BFD_ASSERT (sgot != NULL);
02838
02839 relocation = -(relocation - sgot->output_section->vma);
02840 rel->r_addend = -rel->r_addend;
02841 break;
02842
02843 case R_M32R_GOTOFF_HI_ULO:
02844 case R_M32R_GOTOFF_HI_SLO:
02845 case R_M32R_GOTOFF_LO:
02846 BFD_ASSERT (sgot != NULL);
02847
02848 relocation -= sgot->output_section->vma;
02849
02850 if ((r_type == R_M32R_GOTOFF_HI_SLO)
02851 && ((relocation + rel->r_addend) & 0x8000))
02852 rel->r_addend += 0x10000;
02853 break;
02854
02855 case R_M32R_GOTPC24:
02856
02857
02858
02859 relocation = sgot->output_section->vma;
02860 break;
02861
02862 case R_M32R_GOTPC_HI_ULO:
02863 case R_M32R_GOTPC_HI_SLO:
02864 case R_M32R_GOTPC_LO:
02865 {
02866
02867
02868
02869
02870
02871
02872
02873
02874
02875 relocation = sgot->output_section->vma;
02876 relocation -= (input_section->output_section->vma
02877 + input_section->output_offset
02878 + rel->r_offset);
02879 if ((r_type == R_M32R_GOTPC_HI_SLO)
02880 && ((relocation + rel->r_addend) & 0x8000))
02881 rel->r_addend += 0x10000;
02882
02883 break;
02884 }
02885 case R_M32R_GOT16_HI_ULO:
02886 case R_M32R_GOT16_HI_SLO:
02887 case R_M32R_GOT16_LO:
02888
02889 case R_M32R_GOT24:
02890
02891
02892 BFD_ASSERT (sgot != NULL);
02893
02894 if (h != NULL)
02895 {
02896 bfd_boolean dyn;
02897 bfd_vma off;
02898
02899 off = h->got.offset;
02900 BFD_ASSERT (off != (bfd_vma) -1);
02901
02902 dyn = htab->root.dynamic_sections_created;
02903 if (! WILL_CALL_FINISH_DYNAMIC_SYMBOL (dyn, info->shared, h)
02904 || (info->shared
02905 && (info->symbolic
02906 || h->dynindx == -1
02907 || h->forced_local)
02908 && h->def_regular))
02909 {
02910
02911
02912
02913
02914
02915
02916
02917
02918
02919
02920
02921
02922 if ((off & 1) != 0)
02923 off &= ~1;
02924 else
02925 {
02926 bfd_put_32 (output_bfd, relocation,
02927 sgot->contents + off);
02928 h->got.offset |= 1;
02929 }
02930 }
02931
02932 relocation = sgot->output_offset + off;
02933 }
02934 else
02935 {
02936 bfd_vma off;
02937 bfd_byte *loc;
02938
02939 BFD_ASSERT (local_got_offsets != NULL
02940 && local_got_offsets[r_symndx] != (bfd_vma) -1);
02941
02942 off = local_got_offsets[r_symndx];
02943
02944
02945
02946
02947 if ((off & 1) != 0)
02948 off &= ~1;
02949 else
02950 {
02951 bfd_put_32 (output_bfd, relocation, sgot->contents + off);
02952
02953 if (info->shared)
02954 {
02955 asection *srelgot;
02956 Elf_Internal_Rela outrel;
02957
02958
02959
02960 srelgot = bfd_get_section_by_name (dynobj, ".rela.got");
02961 BFD_ASSERT (srelgot != NULL);
02962
02963 outrel.r_offset = (sgot->output_section->vma
02964 + sgot->output_offset
02965 + off);
02966 outrel.r_info = ELF32_R_INFO (0, R_M32R_RELATIVE);
02967 outrel.r_addend = relocation;
02968 loc = srelgot->contents;
02969 loc += srelgot->reloc_count * sizeof(Elf32_External_Rela);
02970 bfd_elf32_swap_reloca_out (output_bfd, &outrel,loc);
02971 ++srelgot->reloc_count;
02972 }
02973
02974 local_got_offsets[r_symndx] |= 1;
02975 }
02976
02977 relocation = sgot->output_offset + off;
02978 }
02979 if ((r_type == R_M32R_GOT16_HI_SLO)
02980 && ((relocation + rel->r_addend) & 0x8000))
02981 rel->r_addend += 0x10000;
02982
02983 break;
02984
02985 case R_M32R_26_PLTREL:
02986
02987
02988
02989
02990
02991
02992 if (h == NULL)
02993 break;
02994
02995
02996
02997
02998 if (h->forced_local)
02999 break;
03000
03001 if (h->plt.offset == (bfd_vma) -1)
03002 {
03003
03004
03005
03006 break;
03007 }
03008
03009 relocation = (splt->output_section->vma
03010 + splt->output_offset
03011 + h->plt.offset);
03012 break;
03013
03014 case R_M32R_HI16_SLO_RELA:
03015 {
03016 if ((relocation + rel->r_addend) & 0x8000)
03017 {
03018 rel->r_addend += 0x10000;
03019 }
03020 }
03021
03022 case R_M32R_16_RELA:
03023 case R_M32R_24_RELA:
03024 case R_M32R_32_RELA:
03025 case R_M32R_18_PCREL_RELA:
03026 case R_M32R_26_PCREL_RELA:
03027 case R_M32R_HI16_ULO_RELA:
03028 case R_M32R_LO16_RELA:
03029 if (info->shared
03030 && r_symndx != 0
03031 && (input_section->flags & SEC_ALLOC) != 0
03032 && ((r_type != R_M32R_18_PCREL_RELA
03033 && r_type != R_M32R_26_PCREL_RELA)
03034 || (h != NULL
03035 && h->dynindx != -1
03036 && (! info->symbolic
03037 || !h->def_regular))))
03038 {
03039 Elf_Internal_Rela outrel;
03040 bfd_boolean skip, relocate;
03041 bfd_byte *loc;
03042
03043
03044
03045
03046
03047 if (sreloc == NULL)
03048 {
03049 const char *name;
03050
03051 name = (bfd_elf_string_from_elf_section
03052 (input_bfd,
03053 elf_elfheader (input_bfd)->e_shstrndx,
03054 elf_section_data (input_section)->rel_hdr.sh_name));
03055 if (name == NULL)
03056 return FALSE;
03057
03058 BFD_ASSERT (strncmp (name, ".rela", 5) == 0
03059 && strcmp (bfd_get_section_name (input_bfd,
03060 input_section),
03061 name + 5) == 0);
03062
03063 sreloc = bfd_get_section_by_name (dynobj, name);
03064 BFD_ASSERT (sreloc != NULL);
03065 }
03066
03067 skip = FALSE;
03068 relocate = FALSE;
03069
03070 outrel.r_offset = _bfd_elf_section_offset (output_bfd,
03071 info,
03072 input_section,
03073 rel->r_offset);
03074 if (outrel.r_offset == (bfd_vma) -1)
03075 skip = TRUE;
03076 else if (outrel.r_offset == (bfd_vma) -2)
03077 skip = TRUE, relocate = TRUE;
03078 outrel.r_offset += (input_section->output_section->vma
03079 + input_section->output_offset);
03080
03081 if (skip)
03082 memset (&outrel, 0, sizeof outrel);
03083 else if (r_type == R_M32R_18_PCREL_RELA
03084 || r_type == R_M32R_26_PCREL_RELA)
03085 {
03086 BFD_ASSERT (h != NULL && h->dynindx != -1);
03087 outrel.r_info = ELF32_R_INFO (h->dynindx, r_type);
03088 outrel.r_addend = rel->r_addend;
03089 }
03090 else
03091 {
03092
03093
03094 if (h == NULL
03095 || ((info->symbolic || h->dynindx == -1)
03096 && h->def_regular))
03097 {
03098 relocate = TRUE;
03099 outrel.r_info = ELF32_R_INFO (0, R_M32R_RELATIVE);
03100 outrel.r_addend = relocation + rel->r_addend;
03101 }
03102 else
03103 {
03104 BFD_ASSERT (h->dynindx != -1);
03105 outrel.r_info = ELF32_R_INFO (h->dynindx, r_type);
03106 outrel.r_addend = relocation + rel->r_addend;
03107 }
03108 }
03109
03110 loc = sreloc->contents;
03111 loc += sreloc->reloc_count * sizeof(Elf32_External_Rela);
03112 bfd_elf32_swap_reloca_out (output_bfd, &outrel,loc);
03113 ++sreloc->reloc_count;
03114
03115
03116
03117
03118
03119 if (! relocate)
03120 continue;
03121 }
03122 break;
03123
03124 case (int) R_M32R_10_PCREL :
03125 r = m32r_elf_do_10_pcrel_reloc (input_bfd, howto, input_section,
03126 contents, offset,
03127 sec, relocation, addend);
03128 goto check_reloc;
03129
03130 case (int) R_M32R_HI16_SLO :
03131 case (int) R_M32R_HI16_ULO :
03132 {
03133 Elf_Internal_Rela *lorel;
03134
03135
03136
03137
03138 for (lorel = rel + 1;
03139 (lorel < relend
03140 && (ELF32_R_TYPE (lorel->r_info) == R_M32R_HI16_SLO
03141 || ELF32_R_TYPE (lorel->r_info) == R_M32R_HI16_ULO));
03142 lorel++)
03143 continue;
03144 if (lorel < relend
03145 && ELF32_R_TYPE (lorel->r_info) == R_M32R_LO16)
03146 {
03147 m32r_elf_relocate_hi16 (input_bfd, r_type, rel, lorel,
03148 contents, relocation + addend);
03149 r = bfd_reloc_ok;
03150 }
03151 else
03152 r = _bfd_final_link_relocate (howto, input_bfd, input_section,
03153 contents, offset,
03154 relocation, addend);
03155 }
03156
03157 goto check_reloc;
03158
03159 case (int) R_M32R_SDA16_RELA:
03160 case (int) R_M32R_SDA16 :
03161 {
03162 const char *name;
03163
03164 BFD_ASSERT (sec != NULL);
03165 name = bfd_get_section_name (abfd, sec);
03166
03167 if (strcmp (name, ".sdata") == 0
03168 || strcmp (name, ".sbss") == 0
03169 || strcmp (name, ".scommon") == 0)
03170 {
03171 bfd_vma sda_base;
03172 bfd *out_bfd = sec->output_section->owner;
03173
03174 r = m32r_elf_final_sda_base (out_bfd, info,
03175 &errmsg,
03176 &sda_base);
03177 if (r != bfd_reloc_ok)
03178 {
03179 ret = FALSE;
03180 goto check_reloc;
03181 }
03182
03183
03184
03185 relocation -= sda_base;
03186
03187 }
03188 else
03189 {
03190 (*_bfd_error_handler)
03191 (_("%B: The target (%s) of an %s relocation is in the wrong section (%A)"),
03192 input_bfd,
03193 sec,
03194 sym_name,
03195 m32r_elf_howto_table[(int) r_type].name);
03196
03197 ret = FALSE;
03198 continue;
03199 }
03200 }
03201
03202
03203 default :
03204
03205 r = _bfd_final_link_relocate (howto, input_bfd, input_section,
03206 contents, offset,
03207 relocation, addend);
03208 goto check_reloc;
03209 }
03210
03211 r = _bfd_final_link_relocate (howto, input_bfd, input_section,
03212 contents, rel->r_offset,
03213 relocation, rel->r_addend);
03214
03215 }
03216
03217 check_reloc:
03218
03219 if (r != bfd_reloc_ok)
03220 {
03221
03222 const char *name;
03223
03224 if (h != NULL)
03225 name = h->root.root.string;
03226 else
03227 {
03228 name = (bfd_elf_string_from_elf_section
03229 (input_bfd, symtab_hdr->sh_link, sym->st_name));
03230 if (name == NULL || *name == '\0')
03231 name = bfd_section_name (input_bfd, sec);
03232 }
03233
03234 if (errmsg != NULL)
03235 goto common_error;
03236
03237 switch (r)
03238 {
03239 case bfd_reloc_overflow:
03240 if (! ((*info->callbacks->reloc_overflow)
03241 (info, (h ? &h->root : NULL), name, howto->name,
03242 (bfd_vma) 0, input_bfd, input_section, offset)))
03243 return FALSE;
03244 break;
03245
03246 case bfd_reloc_undefined:
03247 if (! ((*info->callbacks->undefined_symbol)
03248 (info, name, input_bfd, input_section,
03249 offset, TRUE)))
03250 return FALSE;
03251 break;
03252
03253 case bfd_reloc_outofrange:
03254 errmsg = _("internal error: out of range error");
03255 goto common_error;
03256
03257 case bfd_reloc_notsupported:
03258 errmsg = _("internal error: unsupported relocation error");
03259 goto common_error;
03260
03261 case bfd_reloc_dangerous:
03262 errmsg = _("internal error: dangerous error");
03263 goto common_error;
03264
03265 default:
03266 errmsg = _("internal error: unknown error");
03267
03268
03269 common_error:
03270 if (!((*info->callbacks->warning)
03271 (info, errmsg, name, input_bfd, input_section,
03272 offset)))
03273 return FALSE;
03274 break;
03275 }
03276 }
03277 }
03278
03279 return ret;
03280 }
03281
03282
03283
03284 static bfd_boolean
03285 m32r_elf_finish_dynamic_symbol (output_bfd, info, h, sym)
03286 bfd *output_bfd;
03287 struct bfd_link_info *info;
03288 struct elf_link_hash_entry *h;
03289 Elf_Internal_Sym *sym;
03290 {
03291 struct elf_m32r_link_hash_table *htab;
03292 bfd *dynobj;
03293 bfd_byte *loc;
03294
03295 #ifdef DEBUG_PIC
03296 printf("m32r_elf_finish_dynamic_symbol()\n");
03297 #endif
03298
03299 htab = m32r_elf_hash_table (info);
03300 dynobj = htab->root.dynobj;
03301
03302 if (h->plt.offset != (bfd_vma) -1)
03303 {
03304 asection *splt;
03305 asection *sgot;
03306 asection *srela;
03307
03308 bfd_vma plt_index;
03309 bfd_vma got_offset;
03310 Elf_Internal_Rela rela;
03311
03312
03313
03314
03315 BFD_ASSERT (h->dynindx != -1);
03316
03317 splt = htab->splt;
03318 sgot = htab->sgotplt;
03319 srela = htab->srelplt;
03320 BFD_ASSERT (splt != NULL && sgot != NULL && srela != NULL);
03321
03322
03323
03324
03325
03326 plt_index = h->plt.offset / PLT_ENTRY_SIZE - 1;
03327
03328
03329
03330
03331 got_offset = (plt_index + 3) * 4;
03332
03333
03334 if (! info->shared)
03335 {
03336 bfd_put_32 (output_bfd,
03337 (PLT_ENTRY_WORD0b
03338 + (((sgot->output_section->vma
03339 + sgot->output_offset
03340 + got_offset) >> 16) & 0xffff)),
03341 splt->contents + h->plt.offset);
03342 bfd_put_32 (output_bfd,
03343 (PLT_ENTRY_WORD1b
03344 + ((sgot->output_section->vma
03345 + sgot->output_offset
03346 + got_offset) & 0xffff)),
03347 splt->contents + h->plt.offset + 4);
03348 bfd_put_32 (output_bfd, PLT_ENTRY_WORD2,
03349 splt->contents + h->plt.offset + 8);
03350 bfd_put_32 (output_bfd,
03351 (PLT_ENTRY_WORD3
03352 + plt_index * sizeof (Elf32_External_Rela)),
03353 splt->contents + h->plt.offset + 12);
03354 bfd_put_32 (output_bfd,
03355 (PLT_ENTRY_WORD4
03356 + (((unsigned int) ((- (h->plt.offset + 16)) >> 2)) & 0xffffff)),
03357 splt->contents + h->plt.offset + 16);
03358 }
03359 else
03360 {
03361 bfd_put_32 (output_bfd,
03362 PLT_ENTRY_WORD0 + got_offset,
03363 splt->contents + h->plt.offset);
03364 bfd_put_32 (output_bfd, PLT_ENTRY_WORD1,
03365 splt->contents + h->plt.offset + 4);
03366 bfd_put_32 (output_bfd, PLT_ENTRY_WORD2,
03367 splt->contents + h->plt.offset + 8);
03368 bfd_put_32 (output_bfd,
03369 (PLT_ENTRY_WORD3
03370 + plt_index * sizeof (Elf32_External_Rela)),
03371 splt->contents + h->plt.offset + 12);
03372 bfd_put_32 (output_bfd,
03373 (PLT_ENTRY_WORD4
03374 + (((unsigned int) ((- (h->plt.offset + 16)) >> 2)) & 0xffffff)),
03375 splt->contents + h->plt.offset + 16);
03376 }
03377
03378
03379 bfd_put_32 (output_bfd,
03380 (splt->output_section->vma
03381 + splt->output_offset
03382 + h->plt.offset
03383 + 12),
03384 sgot->contents + got_offset);
03385
03386
03387 rela.r_offset = (sgot->output_section->vma
03388 + sgot->output_offset
03389 + got_offset);
03390 rela.r_info = ELF32_R_INFO (h->dynindx, R_M32R_JMP_SLOT);
03391 rela.r_addend = 0;
03392 loc = srela->contents;
03393 loc += plt_index * sizeof(Elf32_External_Rela);
03394 bfd_elf32_swap_reloca_out (output_bfd, &rela, loc);
03395
03396 if (!h->def_regular)
03397 {
03398
03399
03400 sym->st_shndx = SHN_UNDEF;
03401 }
03402 }
03403
03404 if (h->got.offset != (bfd_vma) -1)
03405 {
03406 asection *sgot;
03407 asection *srela;
03408 Elf_Internal_Rela rela;
03409
03410
03411
03412
03413 sgot = htab->sgot;
03414 srela = htab->srelgot;
03415 BFD_ASSERT (sgot != NULL && srela != NULL);
03416
03417 rela.r_offset = (sgot->output_section->vma
03418 + sgot->output_offset
03419 + (h->got.offset &~ 1));
03420
03421
03422
03423
03424
03425
03426 if (info->shared
03427 && (info->symbolic
03428 || h->dynindx == -1
03429 || h->forced_local)
03430 && h->def_regular)
03431 {
03432 rela.r_info = ELF32_R_INFO (0, R_M32R_RELATIVE);
03433 rela.r_addend = (h->root.u.def.value
03434 + h->root.u.def.section->output_section->vma
03435 + h->root.u.def.section->output_offset);
03436 }
03437 else
03438 {
03439 BFD_ASSERT((h->got.offset & 1) == 0);
03440 bfd_put_32 (output_bfd, (bfd_vma) 0, sgot->contents + h->got.offset);
03441 rela.r_info = ELF32_R_INFO (h->dynindx, R_M32R_GLOB_DAT);
03442 rela.r_addend = 0;
03443 }
03444
03445 loc = srela->contents;
03446 loc += srela->reloc_count * sizeof(Elf32_External_Rela);
03447 bfd_elf32_swap_reloca_out (output_bfd, &rela, loc);
03448 ++srela->reloc_count;
03449 }
03450
03451 if (h->needs_copy)
03452 {
03453 asection *s;
03454 Elf_Internal_Rela rela;
03455
03456
03457
03458 BFD_ASSERT (h->dynindx != -1
03459 && (h->root.type == bfd_link_hash_defined
03460 || h->root.type == bfd_link_hash_defweak));
03461
03462 s = bfd_get_section_by_name (h->root.u.def.section->owner,
03463 ".rela.bss");
03464 BFD_ASSERT (s != NULL);
03465
03466 rela.r_offset = (h->root.u.def.value
03467 + h->root.u.def.section->output_section->vma
03468 + h->root.u.def.section->output_offset);
03469 rela.r_info = ELF32_R_INFO (h->dynindx, R_M32R_COPY);
03470 rela.r_addend = 0;
03471 loc = s->contents;
03472 loc += s->reloc_count * sizeof(Elf32_External_Rela);
03473 bfd_elf32_swap_reloca_out (output_bfd, &rela, loc);
03474 ++s->reloc_count;
03475 }
03476
03477
03478 if (strcmp (h->root.root.string, "_DYNAMIC") == 0
03479 || strcmp (h->root.root.string, "_GLOBAL_OFFSET_TABLE_") == 0)
03480 sym->st_shndx = SHN_ABS;
03481
03482 return TRUE;
03483 }
03484
03485
03486
03487
03488 static bfd_boolean
03489 m32r_elf_finish_dynamic_sections (output_bfd, info)
03490 bfd *output_bfd;
03491 struct bfd_link_info *info;
03492 {
03493 struct elf_m32r_link_hash_table *htab;
03494 bfd *dynobj;
03495 asection *sdyn;
03496 asection *sgot;
03497
03498 #ifdef DEBUG_PIC
03499 printf("m32r_elf_finish_dynamic_sections()\n");
03500 #endif
03501
03502 htab = m32r_elf_hash_table (info);
03503 dynobj = htab->root.dynobj;
03504
03505 sgot = htab->sgotplt;
03506 sdyn = bfd_get_section_by_name (dynobj, ".dynamic");
03507
03508 if (htab->root.dynamic_sections_created)
03509 {
03510 asection *splt;
03511 Elf32_External_Dyn *dyncon, *dynconend;
03512
03513 BFD_ASSERT (sgot != NULL && sdyn != NULL);
03514
03515 dyncon = (Elf32_External_Dyn *) sdyn->contents;
03516 dynconend = (Elf32_External_Dyn *) (sdyn->contents + sdyn->size);
03517
03518 for (; dyncon < dynconend; dyncon++)
03519 {
03520 Elf_Internal_Dyn dyn;
03521 const char *name;
03522 asection *s;
03523
03524 bfd_elf32_swap_dyn_in (dynobj, dyncon, &dyn);
03525
03526 switch (dyn.d_tag)
03527 {
03528 default:
03529 break;
03530
03531 case DT_PLTGOT:
03532 name = ".got";
03533 s = htab->sgot->output_section;
03534 goto get_vma;
03535 case DT_JMPREL:
03536 name = ".rela.plt";
03537 s = htab->srelplt->output_section;
03538 get_vma:
03539 BFD_ASSERT (s != NULL);
03540 dyn.d_un.d_ptr = s->vma;
03541 bfd_elf32_swap_dyn_out (output_bfd, &dyn, dyncon);
03542 break;
03543
03544 case DT_PLTRELSZ:
03545 s = htab->srelplt->output_section;
03546 BFD_ASSERT (s != NULL);
03547 dyn.d_un.d_val = s->size;
03548 bfd_elf32_swap_dyn_out (output_bfd, &dyn, dyncon);
03549 break;
03550
03551 case DT_RELASZ:
03552
03553
03554
03555
03556
03557
03558
03559
03560
03561 if (htab->srelplt != NULL)
03562 {
03563 s = htab->srelplt->output_section;
03564 dyn.d_un.d_val -= s->size;
03565 }
03566 bfd_elf32_swap_dyn_out (output_bfd, &dyn, dyncon);
03567 break;
03568 }
03569 }
03570
03571
03572 splt = htab->splt;
03573 if (splt && splt->size > 0)
03574 {
03575 if (info->shared)
03576 {
03577 bfd_put_32 (output_bfd, PLT0_PIC_ENTRY_WORD0, splt->contents);
03578 bfd_put_32 (output_bfd, PLT0_PIC_ENTRY_WORD1, splt->contents + 4);
03579 bfd_put_32 (output_bfd, PLT0_PIC_ENTRY_WORD2, splt->contents + 8);
03580 bfd_put_32 (output_bfd, PLT0_PIC_ENTRY_WORD3, splt->contents + 12);
03581 bfd_put_32 (output_bfd, PLT0_PIC_ENTRY_WORD4, splt->contents + 16);
03582 }
03583 else
03584 {
03585 unsigned long addr;
03586
03587 addr = sgot->output_section->vma + sgot->output_offset + 4;
03588 bfd_put_32 (output_bfd,
03589 PLT0_ENTRY_WORD0 | ((addr >> 16) & 0xffff),
03590 splt->contents);
03591 bfd_put_32 (output_bfd,
03592 PLT0_ENTRY_WORD1 | (addr & 0xffff),
03593 splt->contents + 4);
03594 bfd_put_32 (output_bfd, PLT0_ENTRY_WORD2, splt->contents + 8);
03595 bfd_put_32 (output_bfd, PLT0_ENTRY_WORD3, splt->contents + 12);
03596 bfd_put_32 (output_bfd, PLT0_ENTRY_WORD4, splt->contents + 16);
03597 }
03598
03599 elf_section_data (splt->output_section)->this_hdr.sh_entsize =
03600 PLT_ENTRY_SIZE;
03601 }
03602 }
03603
03604
03605 if (sgot && sgot->size > 0)
03606 {
03607 if (sdyn == NULL)
03608 bfd_put_32 (output_bfd, (bfd_vma) 0, sgot->contents);
03609 else
03610 bfd_put_32 (output_bfd,
03611 sdyn->output_section->vma + sdyn->output_offset,
03612 sgot->contents);
03613 bfd_put_32 (output_bfd, (bfd_vma) 0, sgot->contents + 4);
03614 bfd_put_32 (output_bfd, (bfd_vma) 0, sgot->contents + 8);
03615
03616 elf_section_data (sgot->output_section)->this_hdr.sh_entsize = 4;
03617 }
03618
03619 return TRUE;
03620 }
03621
03622
03623
03624 static bfd_boolean
03625 m32r_elf_object_p (abfd)
03626 bfd *abfd;
03627 {
03628 switch (elf_elfheader (abfd)->e_flags & EF_M32R_ARCH)
03629 {
03630 default:
03631 case E_M32R_ARCH: (void) bfd_default_set_arch_mach (abfd, bfd_arch_m32r, bfd_mach_m32r); break;
03632 case E_M32RX_ARCH: (void) bfd_default_set_arch_mach (abfd, bfd_arch_m32r, bfd_mach_m32rx); break;
03633 case E_M32R2_ARCH: (void) bfd_default_set_arch_mach (abfd, bfd_arch_m32r, bfd_mach_m32r2); break;
03634 }
03635 return TRUE;
03636 }
03637
03638
03639 static void
03640 m32r_elf_final_write_processing (abfd, linker)
03641 bfd *abfd;
03642 bfd_boolean linker ATTRIBUTE_UNUSED;
03643 {
03644 unsigned long val;
03645
03646 switch (bfd_get_mach (abfd))
03647 {
03648 default:
03649 case bfd_mach_m32r: val = E_M32R_ARCH; break;
03650 case bfd_mach_m32rx: val = E_M32RX_ARCH; break;
03651 case bfd_mach_m32r2: val = E_M32R2_ARCH; break;
03652 }
03653
03654 elf_elfheader (abfd)->e_flags &=~ EF_M32R_ARCH;
03655 elf_elfheader (abfd)->e_flags |= val;
03656 }
03657
03658
03659 static bfd_boolean
03660 m32r_elf_set_private_flags (abfd, flags)
03661 bfd *abfd;
03662 flagword flags;
03663 {
03664 BFD_ASSERT (!elf_flags_init (abfd)
03665 || elf_elfheader (abfd)->e_flags == flags);
03666
03667 elf_elfheader (abfd)->e_flags = flags;
03668 elf_flags_init (abfd) = TRUE;
03669 return TRUE;
03670 }
03671
03672
03673
03674 static bfd_boolean
03675 m32r_elf_merge_private_bfd_data (ibfd, obfd)
03676 bfd *ibfd;
03677 bfd *obfd;
03678 {
03679 flagword out_flags;
03680 flagword in_flags;
03681
03682 if ( bfd_get_flavour (ibfd) != bfd_target_elf_flavour
03683 || bfd_get_flavour (obfd) != bfd_target_elf_flavour)
03684 return TRUE;
03685
03686 in_flags = elf_elfheader (ibfd)->e_flags;
03687 out_flags = elf_elfheader (obfd)->e_flags;
03688
03689 if (! elf_flags_init (obfd))
03690 {
03691
03692
03693
03694
03695
03696
03697 if (bfd_get_arch_info (ibfd)->the_default)
03698 return TRUE;
03699
03700 elf_flags_init (obfd) = TRUE;
03701 elf_elfheader (obfd)->e_flags = in_flags;
03702
03703 if (bfd_get_arch (obfd) == bfd_get_arch (ibfd)
03704 && bfd_get_arch_info (obfd)->the_default)
03705 {
03706 return bfd_set_arch_mach (obfd, bfd_get_arch (ibfd), bfd_get_mach (ibfd));
03707 }
03708
03709 return TRUE;
03710 }
03711
03712
03713 if (in_flags == out_flags)
03714 return TRUE;
03715
03716 if ((in_flags & EF_M32R_ARCH) != (out_flags & EF_M32R_ARCH))
03717 {
03718 if ( ((in_flags & EF_M32R_ARCH) != E_M32R_ARCH)
03719 || ((out_flags & EF_M32R_ARCH) == E_M32R_ARCH)
03720 || ((in_flags & EF_M32R_ARCH) == E_M32R2_ARCH))
03721 {
03722 (*_bfd_error_handler)
03723 (_("%B: Instruction set mismatch with previous modules"), ibfd);
03724
03725 bfd_set_error (bfd_error_bad_value);
03726 return FALSE;
03727 }
03728 }
03729
03730 return TRUE;
03731 }
03732
03733
03734 static bfd_boolean
03735 m32r_elf_print_private_bfd_data (abfd, ptr)
03736 bfd *abfd;
03737 PTR ptr;
03738 {
03739 FILE * file = (FILE *) ptr;
03740
03741 BFD_ASSERT (abfd != NULL && ptr != NULL);
03742
03743 _bfd_elf_print_private_bfd_data (abfd, ptr);
03744
03745 fprintf (file, _("private flags = %lx"), elf_elfheader (abfd)->e_flags);
03746
03747 switch (elf_elfheader (abfd)->e_flags & EF_M32R_ARCH)
03748 {
03749 default:
03750 case E_M32R_ARCH: fprintf (file, _(": m32r instructions")); break;
03751 case E_M32RX_ARCH: fprintf (file, _(": m32rx instructions")); break;
03752 case E_M32R2_ARCH: fprintf (file, _(": m32r2 instructions")); break;
03753 }
03754
03755 fputc ('\n', file);
03756
03757 return TRUE;
03758 }
03759
03760 asection *
03761 m32r_elf_gc_mark_hook (sec, info, rel, h, sym)
03762 asection *sec;
03763 struct bfd_link_info *info ATTRIBUTE_UNUSED;
03764 Elf_Internal_Rela *rel;
03765 struct elf_link_hash_entry *h;
03766 Elf_Internal_Sym *sym;
03767 {
03768 if (h != NULL)
03769 {
03770 switch (ELF32_R_TYPE (rel->r_info))
03771 {
03772 case R_M32R_GNU_VTINHERIT:
03773 case R_M32R_GNU_VTENTRY:
03774 case R_M32R_RELA_GNU_VTINHERIT:
03775 case R_M32R_RELA_GNU_VTENTRY:
03776 break;
03777
03778 default:
03779 switch (h->root.type)
03780 {
03781 case bfd_link_hash_defined:
03782 case bfd_link_hash_defweak:
03783 return h->root.u.def.section;
03784
03785 case bfd_link_hash_common:
03786 return h->root.u.c.p->section;
03787
03788 default:
03789 break;
03790 }
03791 }
03792 }
03793 else
03794 return bfd_section_from_elf_index (sec->owner, sym->st_shndx);
03795
03796 return NULL;
03797 }
03798
03799 static bfd_boolean
03800 m32r_elf_gc_sweep_hook (abfd, info, sec, relocs)
03801 bfd *abfd ATTRIBUTE_UNUSED;
03802 struct bfd_link_info *info ATTRIBUTE_UNUSED;
03803 asection *sec ATTRIBUTE_UNUSED;
03804 const Elf_Internal_Rela *relocs ATTRIBUTE_UNUSED;
03805 {
03806
03807 Elf_Internal_Shdr *symtab_hdr;
03808 struct elf_link_hash_entry **sym_hashes;
03809 bfd_signed_vma *local_got_refcounts;
03810 const Elf_Internal_Rela *rel, *relend;
03811
03812 elf_section_data (sec)->local_dynrel = NULL;
03813
03814 symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
03815 sym_hashes = elf_sym_hashes (abfd);
03816 local_got_refcounts = elf_local_got_refcounts (abfd);
03817
03818 relend = relocs + sec->reloc_count;
03819 for (rel = relocs; rel < relend; rel++)
03820 {
03821 unsigned long r_symndx;
03822 struct elf_link_hash_entry *h = NULL;
03823
03824 r_symndx = ELF32_R_SYM (rel->r_info);
03825 if (r_symndx >= symtab_hdr->sh_info)
03826 {
03827 h = sym_hashes[r_symndx - symtab_hdr->sh_info];
03828 while (h->root.type == bfd_link_hash_indirect
03829 || h->root.type == bfd_link_hash_warning)
03830 h = (struct elf_link_hash_entry *) h->root.u.i.link;
03831 }
03832
03833 switch (ELF32_R_TYPE (rel->r_info))
03834 {
03835 case R_M32R_GOT16_HI_ULO:
03836 case R_M32R_GOT16_HI_SLO:
03837 case R_M32R_GOT16_LO:
03838 case R_M32R_GOTOFF:
03839 case R_M32R_GOTOFF_HI_ULO:
03840 case R_M32R_GOTOFF_HI_SLO:
03841 case R_M32R_GOTOFF_LO:
03842 case R_M32R_GOT24:
03843 case R_M32R_GOTPC_HI_ULO:
03844 case R_M32R_GOTPC_HI_SLO:
03845 case R_M32R_GOTPC_LO:
03846 case R_M32R_GOTPC24:
03847 if (h != NULL)
03848 {
03849 if (h->got.refcount > 0)
03850 h->got.refcount--;
03851 }
03852 else
03853 {
03854 if (local_got_refcounts && local_got_refcounts[r_symndx] > 0)
03855 local_got_refcounts[r_symndx]--;
03856 }
03857 break;
03858
03859 case R_M32R_16_RELA:
03860 case R_M32R_24_RELA:
03861 case R_M32R_32_RELA:
03862 case R_M32R_HI16_ULO_RELA:
03863 case R_M32R_HI16_SLO_RELA:
03864 case R_M32R_LO16_RELA:
03865 case R_M32R_SDA16_RELA:
03866 case R_M32R_18_PCREL_RELA:
03867 case R_M32R_26_PCREL_RELA:
03868 if (h != NULL)
03869 {
03870 struct elf_m32r_link_hash_entry *eh;
03871 struct elf_m32r_dyn_relocs **pp;
03872 struct elf_m32r_dyn_relocs *p;
03873
03874 if (!info->shared && h->plt.refcount > 0)
03875 h->plt.refcount -= 1;
03876
03877 eh = (struct elf_m32r_link_hash_entry *) h;
03878
03879 for (pp = &eh->dyn_relocs; (p = *pp) != NULL; pp = &p->next)
03880 if (p->sec == sec)
03881 {
03882 if (ELF32_R_TYPE (rel->r_info) == R_M32R_26_PCREL_RELA
03883 || ELF32_R_TYPE (rel->r_info) == R_M32R_26_PCREL_RELA)
03884 p->pc_count -= 1;
03885 p->count -= 1;
03886 if (p->count == 0)
03887 *pp = p->next;
03888 break;
03889 }
03890 }
03891 break;
03892
03893 case R_M32R_26_PLTREL:
03894 if (h != NULL)
03895 {
03896 if (h->plt.refcount > 0)
03897 h->plt.refcount--;
03898 }
03899 break;
03900
03901 default:
03902 break;
03903 }
03904 }
03905
03906 return TRUE;
03907 }
03908
03909
03910
03911
03912
03913 static bfd_boolean
03914 m32r_elf_check_relocs (abfd, info, sec, relocs)
03915 bfd *abfd;
03916 struct bfd_link_info *info;
03917 asection *sec;
03918 const Elf_Internal_Rela *relocs;
03919 {
03920 Elf_Internal_Shdr *symtab_hdr;
03921 struct elf_link_hash_entry **sym_hashes, **sym_hashes_end;
03922 const Elf_Internal_Rela *rel;
03923 const Elf_Internal_Rela *rel_end;
03924 struct elf_m32r_link_hash_table *htab;
03925 bfd *dynobj;
03926 bfd_vma *local_got_offsets;
03927 asection *sgot, *srelgot, *sreloc;
03928
03929 if (info->relocatable)
03930 return TRUE;
03931
03932 sgot = srelgot = sreloc = NULL;
03933
03934 symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
03935 sym_hashes = elf_sym_hashes (abfd);
03936 sym_hashes_end = sym_hashes + symtab_hdr->sh_size/sizeof (Elf32_External_Sym);
03937 if (!elf_bad_symtab (abfd))
03938 sym_hashes_end -= symtab_hdr->sh_info;
03939
03940 htab = m32r_elf_hash_table (info);
03941 dynobj = htab->root.dynobj;
03942 local_got_offsets = elf_local_got_offsets (abfd);
03943
03944 rel_end = relocs + sec->reloc_count;
03945 for (rel = relocs; rel < rel_end; rel++)
03946 {
03947 int r_type;
03948 struct elf_link_hash_entry *h;
03949 unsigned long r_symndx;
03950
03951 r_symndx = ELF32_R_SYM (rel->r_info);
03952 r_type = ELF32_R_TYPE (rel->r_info);
03953 if (r_symndx < symtab_hdr->sh_info)
03954 h = NULL;
03955 else
03956 h = sym_hashes[r_symndx - symtab_hdr->sh_info];
03957
03958
03959 if (htab->sgot == NULL)
03960 {
03961 switch (r_type)
03962 {
03963 case R_M32R_GOT16_HI_ULO:
03964 case R_M32R_GOT16_HI_SLO:
03965 case R_M32R_GOTOFF:
03966 case R_M32R_GOTOFF_HI_ULO:
03967 case R_M32R_GOTOFF_HI_SLO:
03968 case R_M32R_GOTOFF_LO:
03969 case R_M32R_GOT16_LO:
03970 case R_M32R_GOTPC24:
03971 case R_M32R_GOTPC_HI_ULO:
03972 case R_M32R_GOTPC_HI_SLO:
03973 case R_M32R_GOTPC_LO:
03974 case R_M32R_GOT24:
03975 if (dynobj == NULL)
03976 htab->root.dynobj = dynobj = abfd;
03977 if (! create_got_section (dynobj, info))
03978 return FALSE;
03979 break;
03980
03981 default:
03982 break;
03983 }
03984 }
03985
03986 switch (r_type)
03987 {
03988 case R_M32R_GOT16_HI_ULO:
03989 case R_M32R_GOT16_HI_SLO:
03990 case R_M32R_GOT16_LO:
03991 case R_M32R_GOT24:
03992
03993 if (h != NULL)
03994 h->got.refcount += 1;
03995 else
03996 {
03997 bfd_signed_vma *local_got_refcounts;
03998
03999
04000
04001 local_got_refcounts = elf_local_got_refcounts (abfd);
04002 if (local_got_refcounts == NULL)
04003 {
04004 bfd_size_type size;
04005
04006 size = symtab_hdr->sh_info;
04007 size *= sizeof (bfd_signed_vma);
04008 local_got_refcounts = ((bfd_signed_vma *)
04009 bfd_zalloc (abfd, size));
04010 if (local_got_refcounts == NULL)
04011 return FALSE;
04012 elf_local_got_refcounts (abfd) = local_got_refcounts;
04013 }
04014 local_got_refcounts[r_symndx] += 1;
04015 }
04016 break;
04017
04018 case R_M32R_26_PLTREL:
04019
04020
04021
04022
04023
04024
04025
04026
04027 if (h == NULL)
04028 continue;
04029
04030 if (h->forced_local)
04031 break;
04032
04033 h->needs_plt = 1;
04034 h->plt.refcount += 1;
04035 break;
04036
04037 case R_M32R_16_RELA:
04038 case R_M32R_24_RELA:
04039 case R_M32R_32_RELA:
04040 case R_M32R_HI16_ULO_RELA:
04041 case R_M32R_HI16_SLO_RELA:
04042 case R_M32R_LO16_RELA:
04043 case R_M32R_SDA16_RELA:
04044 case R_M32R_18_PCREL_RELA:
04045 case R_M32R_26_PCREL_RELA:
04046
04047 if (h != NULL && !info->shared)
04048 {
04049 h->non_got_ref = 1;
04050 h->plt.refcount += 1;
04051 }
04052
04053
04054
04055
04056
04057
04058
04059
04060
04061
04062
04063
04064
04065
04066
04067
04068
04069
04070
04071
04072 if ((info->shared
04073 && (sec->flags & SEC_ALLOC) != 0
04074 && ((r_type != R_M32R_26_PCREL_RELA
04075 && r_type != R_M32R_18_PCREL_RELA)
04076 || (h != NULL
04077 && (! info->symbolic
04078 || h->root.type == bfd_link_hash_defweak
04079 || !h->def_regular))))
04080 || (!info->shared
04081 && (sec->flags & SEC_ALLOC) != 0
04082 && h != NULL
04083 && (h->root.type == bfd_link_hash_defweak
04084 || !h->def_regular)))
04085 {
04086 struct elf_m32r_dyn_relocs *p;
04087 struct elf_m32r_dyn_relocs **head;
04088
04089 if (dynobj == NULL)
04090 htab->root.dynobj = dynobj = abfd;
04091
04092
04093
04094
04095 if (sreloc == NULL)
04096 {
04097 const char *name;
04098
04099 name = (bfd_elf_string_from_elf_section
04100 (abfd,
04101 elf_elfheader (abfd)->e_shstrndx,
04102 elf_section_data (sec)->rel_hdr.sh_name));
04103 if (name == NULL)
04104 return FALSE;
04105
04106 BFD_ASSERT (strncmp (name, ".rela", 5) == 0
04107 && strcmp (bfd_get_section_name (abfd, sec),
04108 name + 5) == 0);
04109
04110 sreloc = bfd_get_section_by_name (dynobj, name);
04111 if (sreloc == NULL)
04112 {
04113 flagword flags;
04114
04115 sreloc = bfd_make_section (dynobj, name);
04116 flags = (SEC_HAS_CONTENTS | SEC_READONLY
04117 | SEC_IN_MEMORY | SEC_LINKER_CREATED);
04118 if ((sec->flags & SEC_ALLOC) != 0)
04119 flags |= SEC_ALLOC | SEC_LOAD;
04120 if (sreloc == NULL
04121 || ! bfd_set_section_flags (dynobj, sreloc, flags)
04122 || ! bfd_set_section_alignment (dynobj, sreloc, 2))
04123 return FALSE;
04124 }
04125 elf_section_data (sec)->sreloc = sreloc;
04126 }
04127
04128
04129
04130 if (h != NULL)
04131 head = &((struct elf_m32r_link_hash_entry *) h)->dyn_relocs;
04132 else
04133 {
04134 asection *s;
04135
04136
04137 s = bfd_section_from_r_symndx (abfd, &htab->sym_sec,
04138 sec, r_symndx);
04139 if (s == NULL)
04140 return FALSE;
04141
04142 head = ((struct elf_m32r_dyn_relocs **)
04143 &elf_section_data (s)->local_dynrel);
04144 }
04145
04146 p = *head;
04147 if (p == NULL || p->sec != sec)
04148 {
04149 bfd_size_type amt = sizeof (*p);
04150 p = ((struct elf_m32r_dyn_relocs *) bfd_alloc (dynobj, amt));
04151 if (p == NULL)
04152 return FALSE;
04153 p->next = *head;
04154 *head = p;
04155 p->sec = sec;
04156 p->count = 0;
04157 p->pc_count = 0;
04158 }
04159
04160 p->count += 1;
04161 if (ELF32_R_TYPE (rel->r_info) == R_M32R_26_PCREL_RELA
04162 || ELF32_R_TYPE (rel->r_info) == R_M32R_18_PCREL_RELA)
04163 p->pc_count += 1;
04164 }
04165 break;
04166
04167
04168
04169 case R_M32R_RELA_GNU_VTINHERIT:
04170 case R_M32R_GNU_VTINHERIT:
04171 if (!bfd_elf_gc_record_vtinherit (abfd, sec, h, rel->r_offset))
04172 return FALSE;
04173 break;
04174
04175
04176
04177 case R_M32R_GNU_VTENTRY:
04178 if (!bfd_elf_gc_record_vtentry (abfd, sec, h, rel->r_offset))
04179 return FALSE;
04180 break;
04181 case R_M32R_RELA_GNU_VTENTRY:
04182 if (!bfd_elf_gc_record_vtentry (abfd, sec, h, rel->r_addend))
04183 return FALSE;
04184 break;
04185 }
04186 }
04187
04188 return TRUE;
04189 }
04190
04191 static struct bfd_elf_special_section const m32r_elf_special_sections[]=
04192 {
04193 { ".sdata", 6, -2, SHT_PROGBITS, SHF_ALLOC + SHF_WRITE },
04194 { ".sbss", 5, -2, SHT_NOBITS, SHF_ALLOC + SHF_WRITE },
04195 { NULL, 0, 0, 0, 0 }
04196 };
04197
04198 static bfd_boolean
04199 m32r_elf_fake_sections (abfd, hdr, sec)
04200 bfd *abfd;
04201 Elf_Internal_Shdr *hdr ATTRIBUTE_UNUSED;
04202 asection *sec;
04203 {
04204 register const char *name;
04205
04206 name = bfd_get_section_name (abfd, sec);
04207
04208
04209
04210
04211
04212
04213
04214
04215
04216
04217
04218
04219 if ((sec->flags & SEC_RELOC) != 0)
04220 {
04221 struct bfd_elf_section_data *esd;
04222 bfd_size_type amt = sizeof (Elf_Internal_Shdr);
04223
04224 esd = elf_section_data (sec);
04225 BFD_ASSERT (esd->rel_hdr2 == NULL);
04226 esd->rel_hdr2 = (Elf_Internal_Shdr *) bfd_zalloc (abfd, amt);
04227 if (!esd->rel_hdr2)
04228 return FALSE;
04229 _bfd_elf_init_reloc_shdr (abfd, esd->rel_hdr2, sec,
04230 !sec->use_rela_p);
04231 }
04232
04233 return TRUE;
04234 }
04235
04236 static enum elf_reloc_type_class
04237 m32r_elf_reloc_type_class (rela)
04238 const Elf_Internal_Rela *rela;
04239 {
04240 switch ((int) ELF32_R_TYPE (rela->r_info))
04241 {
04242 case R_M32R_RELATIVE:
04243 return reloc_class_relative;
04244 case R_M32R_JMP_SLOT:
04245 return reloc_class_plt;
04246 case R_M32R_COPY:
04247 return reloc_class_copy;
04248 default:
04249 return reloc_class_normal;
04250 }
04251 }
04252
04253 #define ELF_ARCH bfd_arch_m32r
04254 #define ELF_MACHINE_CODE EM_M32R
04255 #define ELF_MACHINE_ALT1 EM_CYGNUS_M32R
04256 #define ELF_MAXPAGESIZE 0x1
04257
04258 #define TARGET_BIG_SYM bfd_elf32_m32r_vec
04259 #define TARGET_BIG_NAME "elf32-m32r"
04260 #define TARGET_LITTLE_SYM bfd_elf32_m32rle_vec
04261 #define TARGET_LITTLE_NAME "elf32-m32rle"
04262
04263 #define elf_info_to_howto m32r_info_to_howto
04264 #define elf_info_to_howto_rel m32r_info_to_howto_rel
04265 #define elf_backend_section_from_bfd_section _bfd_m32r_elf_section_from_bfd_section
04266 #define elf_backend_symbol_processing _bfd_m32r_elf_symbol_processing
04267 #define elf_backend_add_symbol_hook m32r_elf_add_symbol_hook
04268 #define elf_backend_relocate_section m32r_elf_relocate_section
04269 #define elf_backend_gc_mark_hook m32r_elf_gc_mark_hook
04270 #define elf_backend_gc_sweep_hook m32r_elf_gc_sweep_hook
04271 #define elf_backend_check_relocs m32r_elf_check_relocs
04272
04273 #define elf_backend_create_dynamic_sections m32r_elf_create_dynamic_sections
04274 #define bfd_elf32_bfd_link_hash_table_create m32r_elf_link_hash_table_create
04275 #define elf_backend_size_dynamic_sections m32r_elf_size_dynamic_sections
04276 #define elf_backend_finish_dynamic_sections m32r_elf_finish_dynamic_sections
04277 #define elf_backend_adjust_dynamic_symbol m32r_elf_adjust_dynamic_symbol
04278 #define elf_backend_finish_dynamic_symbol m32r_elf_finish_dynamic_symbol
04279 #define elf_backend_reloc_type_class m32r_elf_reloc_type_class
04280 #define elf_backend_copy_indirect_symbol m32r_elf_copy_indirect_symbol
04281
04282 #define elf_backend_can_gc_sections 1
04283
04284
04285
04286 #define elf_backend_can_refcount 1
04287 #define elf_backend_want_got_plt 1
04288 #define elf_backend_plt_readonly 1
04289 #define elf_backend_want_plt_sym 0
04290 #define elf_backend_got_header_size 12
04291
04292 #define elf_backend_may_use_rel_p 1
04293 #ifdef USE_M32R_OLD_RELOC
04294 #define elf_backend_default_use_rela_p 0
04295 #define elf_backend_may_use_rela_p 0
04296 #else
04297 #define elf_backend_default_use_rela_p 1
04298 #define elf_backend_may_use_rela_p 1
04299 #define elf_backend_fake_sections m32r_elf_fake_sections
04300 #endif
04301
04302 #define elf_backend_object_p m32r_elf_object_p
04303 #define elf_backend_final_write_processing m32r_elf_final_write_processing
04304 #define bfd_elf32_bfd_merge_private_bfd_data m32r_elf_merge_private_bfd_data
04305 #define bfd_elf32_bfd_set_private_flags m32r_elf_set_private_flags
04306 #define bfd_elf32_bfd_print_private_bfd_data m32r_elf_print_private_bfd_data
04307 #define elf_backend_special_sections m32r_elf_special_sections
04308
04309 #include "elf32-target.h"
04310
04311 #undef ELF_MAXPAGESIZE
04312 #define ELF_MAXPAGESIZE 0x1000
04313
04314 #undef TARGET_BIG_SYM
04315 #define TARGET_BIG_SYM bfd_elf32_m32rlin_vec
04316 #undef TARGET_BIG_NAME
04317 #define TARGET_BIG_NAME "elf32-m32r-linux"
04318 #undef TARGET_LITTLE_SYM
04319 #define TARGET_LITTLE_SYM bfd_elf32_m32rlelin_vec
04320 #undef TARGET_LITTLE_NAME
04321 #define TARGET_LITTLE_NAME "elf32-m32rle-linux"
04322 #undef elf32_bed
04323 #define elf32_bed elf32_m32r_lin_bed
04324
04325 #include "elf32-target.h"
04326