GNU Binutils with patches for OS216
修订版 | 85e95c9817429ff3fa50224697609f4ae0148fdb (tree) |
---|---|
时间 | 2018-02-22 23:39:19 |
作者 | Nick Clifton <nickc@redh...> |
Commiter | Nick Clifton |
Another merge
@@ -1,3 +1,21 @@ | ||
1 | +2018-02-09 Eric Botcazou <ebotcazou@adacore.com> | |
2 | + | |
3 | + * elfxx-sparc.c (UNDEFINED_WEAK_RESOLVED_TO_ZERO): Reorder conditions. | |
4 | + (sparc_elf_append_rela): Assert that there is enough room in section. | |
5 | + (_bfd_sparc_elf_copy_indirect_symbol): Fix formatting. | |
6 | + (_bfd_sparc_elf_adjust_dynamic_symbol): Minor tweak. | |
7 | + (allocate_dynrelocs): Remove outdated comments and reorder conditions. | |
8 | + For a symbol subject to a GOT relocation, reserve a slot in the | |
9 | + relocation section if the symbol isn't dynamic and we are in PIC mode. | |
10 | + (_bfd_sparc_elf_relocate_section) <R_SPARC_GOTDATA_OP>: If relocation | |
11 | + is relaxed and a slot was reserved, generate a R_SPARC_NONE relocation. | |
12 | + <R_SPARC_GOTDATA_OP_HIX22>: Adjust comments. | |
13 | + <R_SPARC_PC10>: Reorder conditions. Remove always-false assertion. | |
14 | + (_bfd_sparc_elf_finish_dynamic_symbol): Rename local_undefweak into | |
15 | + resolved_to_zero. Do not generate a dynamic GOT relocation for an | |
16 | + undefined weak symbol with non-default visibility. Remove superfluous | |
17 | + 'else' and fix formatting. | |
18 | + | |
1 | 19 | 2017-12-19 Alan Modra <amodra@gmail.com> |
2 | 20 | |
3 | 21 | PR 22626 |
@@ -689,13 +689,13 @@ struct _bfd_sparc_elf_dyn_relocs | ||
689 | 689 | 1. Has non-GOT/non-PLT relocations in text section. |
690 | 690 | Or |
691 | 691 | 2. Has no GOT/PLT relocation. */ |
692 | -#define UNDEFINED_WEAK_RESOLVED_TO_ZERO(INFO, EH) \ | |
693 | - ((EH)->elf.root.type == bfd_link_hash_undefweak \ | |
694 | - && bfd_link_executable (INFO) \ | |
695 | - && (_bfd_sparc_elf_hash_table (INFO)->interp == NULL \ | |
696 | - || !(EH)->has_got_reloc \ | |
697 | - || (EH)->has_non_got_reloc \ | |
698 | - || !(INFO)->dynamic_undefined_weak)) | |
692 | +#define UNDEFINED_WEAK_RESOLVED_TO_ZERO(INFO, EH) \ | |
693 | + ((EH)->elf.root.type == bfd_link_hash_undefweak \ | |
694 | + && bfd_link_executable (INFO) \ | |
695 | + && (_bfd_sparc_elf_hash_table (INFO)->interp == NULL \ | |
696 | + || !(INFO)->dynamic_undefined_weak \ | |
697 | + || (EH)->has_non_got_reloc \ | |
698 | + || !(EH)->has_got_reloc)) | |
699 | 699 | |
700 | 700 | /* SPARC ELF linker hash entry. */ |
701 | 701 |
@@ -770,6 +770,7 @@ sparc_elf_append_rela (bfd *abfd, asection *s, Elf_Internal_Rela *rel) | ||
770 | 770 | bfd_byte *loc; |
771 | 771 | |
772 | 772 | bed = get_elf_backend_data (abfd); |
773 | + BFD_ASSERT (s->reloc_count * bed->s->sizeof_rela < s->size); | |
773 | 774 | loc = s->contents + (s->reloc_count++ * bed->s->sizeof_rela); |
774 | 775 | bed->s->swap_reloca_out (abfd, rel, loc); |
775 | 776 | } |
@@ -1330,8 +1331,7 @@ _bfd_sparc_elf_copy_indirect_symbol (struct bfd_link_info *info, | ||
1330 | 1331 | eind->dyn_relocs = NULL; |
1331 | 1332 | } |
1332 | 1333 | |
1333 | - if (ind->root.type == bfd_link_hash_indirect | |
1334 | - && dir->got.refcount <= 0) | |
1334 | + if (ind->root.type == bfd_link_hash_indirect && dir->got.refcount <= 0) | |
1335 | 1335 | { |
1336 | 1336 | edir->tls_type = eind->tls_type; |
1337 | 1337 | eind->tls_type = GOT_UNKNOWN; |
@@ -2178,8 +2178,8 @@ _bfd_sparc_elf_adjust_dynamic_symbol (struct bfd_link_info *info, | ||
2178 | 2178 | if (h->plt.refcount <= 0 |
2179 | 2179 | || (h->type != STT_GNU_IFUNC |
2180 | 2180 | && (SYMBOL_CALLS_LOCAL (info, h) |
2181 | - || (ELF_ST_VISIBILITY (h->other) != STV_DEFAULT | |
2182 | - && h->root.type == bfd_link_hash_undefweak)))) | |
2181 | + || (h->root.type == bfd_link_hash_undefweak | |
2182 | + && ELF_ST_VISIBILITY (h->other) != STV_DEFAULT)))) | |
2183 | 2183 | { |
2184 | 2184 | /* This case can occur if we saw a WPLT30 reloc in an input |
2185 | 2185 | file, but the symbol was never referred to by a dynamic |
@@ -2306,12 +2306,11 @@ allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf) | ||
2306 | 2306 | && h->def_regular |
2307 | 2307 | && h->ref_regular)) |
2308 | 2308 | { |
2309 | - /* Make sure this symbol is output as a dynamic symbol. | |
2310 | - Undefined weak syms won't yet be marked as dynamic. */ | |
2311 | - if (h->dynindx == -1 | |
2312 | - && !h->forced_local | |
2313 | - && !resolved_to_zero | |
2314 | - && h->root.type == bfd_link_hash_undefweak) | |
2309 | + /* Undefined weak syms won't yet be marked as dynamic. */ | |
2310 | + if (h->root.type == bfd_link_hash_undefweak | |
2311 | + && !resolved_to_zero | |
2312 | + && h->dynindx == -1 | |
2313 | + && !h->forced_local) | |
2315 | 2314 | { |
2316 | 2315 | if (! bfd_elf_link_record_dynamic_symbol (info, h)) |
2317 | 2316 | return FALSE; |
@@ -2419,12 +2418,11 @@ allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf) | ||
2419 | 2418 | bfd_boolean dyn; |
2420 | 2419 | int tls_type = _bfd_sparc_elf_hash_entry(h)->tls_type; |
2421 | 2420 | |
2422 | - /* Make sure this symbol is output as a dynamic symbol. | |
2423 | - Undefined weak syms won't yet be marked as dynamic. */ | |
2424 | - if (h->dynindx == -1 | |
2425 | - && !h->forced_local | |
2426 | - && !resolved_to_zero | |
2427 | - && h->root.type == bfd_link_hash_undefweak) | |
2421 | + /* Undefined weak syms won't yet be marked as dynamic. */ | |
2422 | + if (h->root.type == bfd_link_hash_undefweak | |
2423 | + && !resolved_to_zero | |
2424 | + && h->dynindx == -1 | |
2425 | + && !h->forced_local) | |
2428 | 2426 | { |
2429 | 2427 | if (! bfd_elf_link_record_dynamic_symbol (info, h)) |
2430 | 2428 | return FALSE; |
@@ -2438,21 +2436,25 @@ allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf) | ||
2438 | 2436 | s->size += SPARC_ELF_WORD_BYTES (htab); |
2439 | 2437 | dyn = htab->elf.dynamic_sections_created; |
2440 | 2438 | /* R_SPARC_TLS_IE_{HI22,LO10} needs one dynamic relocation, |
2441 | - R_SPARC_TLS_GD_{HI22,LO10} needs one if local symbol and two if | |
2442 | - global. No dynamic relocations are needed against resolved | |
2443 | - undefined weak symbols in an executable. */ | |
2439 | + R_SPARC_TLS_GD_{HI22,LO10} needs one if local and two if global. */ | |
2444 | 2440 | if ((tls_type == GOT_TLS_GD && h->dynindx == -1) |
2445 | 2441 | || tls_type == GOT_TLS_IE |
2446 | 2442 | || h->type == STT_GNU_IFUNC) |
2447 | 2443 | htab->elf.srelgot->size += SPARC_ELF_RELA_BYTES (htab); |
2448 | 2444 | else if (tls_type == GOT_TLS_GD) |
2449 | 2445 | htab->elf.srelgot->size += 2 * SPARC_ELF_RELA_BYTES (htab); |
2450 | - else if (((ELF_ST_VISIBILITY (h->other) == STV_DEFAULT | |
2451 | - && !resolved_to_zero) | |
2452 | - || h->root.type != bfd_link_hash_undefweak) | |
2453 | - && WILL_CALL_FINISH_DYNAMIC_SYMBOL (dyn, | |
2454 | - bfd_link_pic (info), | |
2455 | - h)) | |
2446 | + else if ((WILL_CALL_FINISH_DYNAMIC_SYMBOL (dyn, bfd_link_pic (info), h) | |
2447 | + /* Even if the symbol isn't dynamic, we may generate a | |
2448 | + reloc for the dynamic linker in PIC mode. */ | |
2449 | + || (h->dynindx == -1 | |
2450 | + && !h->forced_local | |
2451 | + && h->root.type != bfd_link_hash_undefweak | |
2452 | + && bfd_link_pic (info))) | |
2453 | + /* No dynamic relocations are needed against resolved | |
2454 | + undefined weak symbols in an executable. */ | |
2455 | + && !(h->root.type == bfd_link_hash_undefweak | |
2456 | + && (ELF_ST_VISIBILITY (h->other) != STV_DEFAULT | |
2457 | + || resolved_to_zero))) | |
2456 | 2458 | htab->elf.srelgot->size += SPARC_ELF_RELA_BYTES (htab); |
2457 | 2459 | } |
2458 | 2460 | else |
@@ -2562,12 +2564,11 @@ allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf) | ||
2562 | 2564 | && (h->root.type == bfd_link_hash_undefweak |
2563 | 2565 | || h->root.type == bfd_link_hash_undefined)))) |
2564 | 2566 | { |
2565 | - /* Make sure this symbol is output as a dynamic symbol. | |
2566 | - Undefined weak syms won't yet be marked as dynamic. */ | |
2567 | - if (h->dynindx == -1 | |
2568 | - && !h->forced_local | |
2569 | - && !resolved_to_zero | |
2570 | - && h->root.type == bfd_link_hash_undefweak) | |
2567 | + /* Undefined weak syms won't yet be marked as dynamic. */ | |
2568 | + if (h->root.type == bfd_link_hash_undefweak | |
2569 | + && !resolved_to_zero | |
2570 | + && h->dynindx == -1 | |
2571 | + && !h->forced_local) | |
2571 | 2572 | { |
2572 | 2573 | if (! bfd_elf_link_record_dynamic_symbol (info, h)) |
2573 | 2574 | return FALSE; |
@@ -3332,6 +3333,26 @@ _bfd_sparc_elf_relocate_section (bfd *output_bfd, | ||
3332 | 3333 | /* {ld,ldx} [%rs1 + %rs2], %rd --> add %rs1, %rs2, %rd */ |
3333 | 3334 | relocation = 0x80000000 | (insn & 0x3e07c01f); |
3334 | 3335 | bfd_put_32 (output_bfd, relocation, contents + rel->r_offset); |
3336 | + | |
3337 | + /* If the symbol is global but not dynamic, an .rela.* slot has | |
3338 | + been allocated for it in the GOT so output R_SPARC_NONE here. | |
3339 | + See also the handling of other GOT relocations just below. */ | |
3340 | + if (h != NULL | |
3341 | + && h->dynindx == -1 | |
3342 | + && !h->forced_local | |
3343 | + && h->root.type != bfd_link_hash_undefweak | |
3344 | + && (h->got.offset & 1) == 0 | |
3345 | + && bfd_link_pic (info)) | |
3346 | + { | |
3347 | + asection *s = htab->elf.srelgot; | |
3348 | + Elf_Internal_Rela outrel; | |
3349 | + | |
3350 | + BFD_ASSERT (s != NULL); | |
3351 | + | |
3352 | + memset (&outrel, 0, sizeof outrel); | |
3353 | + sparc_elf_append_rela (output_bfd, s, &outrel); | |
3354 | + h->got.offset |= 1; | |
3355 | + } | |
3335 | 3356 | } |
3336 | 3357 | continue; |
3337 | 3358 | } |
@@ -3384,19 +3405,17 @@ _bfd_sparc_elf_relocate_section (bfd *output_bfd, | ||
3384 | 3405 | off &= ~1; |
3385 | 3406 | else |
3386 | 3407 | { |
3387 | - SPARC_ELF_PUT_WORD (htab, output_bfd, relocation, | |
3388 | - htab->elf.sgot->contents + off); | |
3389 | - h->got.offset |= 1; | |
3390 | - | |
3408 | + /* If this symbol isn't dynamic in PIC mode, treat it | |
3409 | + like a local symbol in PIC mode below. */ | |
3391 | 3410 | if (h->dynindx == -1 |
3392 | 3411 | && !h->forced_local |
3393 | 3412 | && h->root.type != bfd_link_hash_undefweak |
3394 | 3413 | && bfd_link_pic (info)) |
3395 | - { | |
3396 | - /* If this symbol isn't dynamic in PIC | |
3397 | - generate R_SPARC_RELATIVE here. */ | |
3398 | - relative_reloc = TRUE; | |
3399 | - } | |
3414 | + relative_reloc = TRUE; | |
3415 | + else | |
3416 | + SPARC_ELF_PUT_WORD (htab, output_bfd, relocation, | |
3417 | + htab->elf.sgot->contents + off); | |
3418 | + h->got.offset |= 1; | |
3400 | 3419 | } |
3401 | 3420 | } |
3402 | 3421 | else |
@@ -3416,6 +3435,8 @@ _bfd_sparc_elf_relocate_section (bfd *output_bfd, | ||
3416 | 3435 | off &= ~1; |
3417 | 3436 | else |
3418 | 3437 | { |
3438 | + /* For a local symbol in PIC mode, we need to generate a | |
3439 | + R_SPARC_RELATIVE reloc for the dynamic linker. */ | |
3419 | 3440 | if (bfd_link_pic (info)) |
3420 | 3441 | { |
3421 | 3442 | relative_reloc = TRUE; |
@@ -3429,12 +3450,9 @@ _bfd_sparc_elf_relocate_section (bfd *output_bfd, | ||
3429 | 3450 | |
3430 | 3451 | if (relative_reloc) |
3431 | 3452 | { |
3432 | - asection *s; | |
3453 | + asection *s = htab->elf.srelgot; | |
3433 | 3454 | Elf_Internal_Rela outrel; |
3434 | 3455 | |
3435 | - /* We need to generate a R_SPARC_RELATIVE reloc | |
3436 | - for the dynamic linker. */ | |
3437 | - s = htab->elf.srelgot; | |
3438 | 3456 | BFD_ASSERT (s != NULL); |
3439 | 3457 | |
3440 | 3458 | outrel.r_offset = (htab->elf.sgot->output_section->vma |
@@ -3560,9 +3578,9 @@ _bfd_sparc_elf_relocate_section (bfd *output_bfd, | ||
3560 | 3578 | in PIE. */ |
3561 | 3579 | if ((bfd_link_pic (info) |
3562 | 3580 | && (h == NULL |
3563 | - || ((ELF_ST_VISIBILITY (h->other) == STV_DEFAULT | |
3564 | - && !resolved_to_zero) | |
3565 | - || h->root.type != bfd_link_hash_undefweak)) | |
3581 | + || !(h->root.type == bfd_link_hash_undefweak | |
3582 | + && (ELF_ST_VISIBILITY (h->other) != STV_DEFAULT | |
3583 | + || resolved_to_zero))) | |
3566 | 3584 | && (! howto->pc_relative |
3567 | 3585 | || !SYMBOL_CALLS_LOCAL (info, h))) |
3568 | 3586 | || (!bfd_link_pic (info) |
@@ -3649,7 +3667,6 @@ _bfd_sparc_elf_relocate_section (bfd *output_bfd, | ||
3649 | 3667 | || !SYMBOLIC_BIND (info, h) |
3650 | 3668 | || !h->def_regular)) |
3651 | 3669 | { |
3652 | - BFD_ASSERT (h->dynindx != -1); | |
3653 | 3670 | outrel.r_info = SPARC_ELF_R_INFO (htab, rel, h->dynindx, r_type); |
3654 | 3671 | outrel.r_addend = rel->r_addend; |
3655 | 3672 | } |
@@ -4494,7 +4511,7 @@ _bfd_sparc_elf_finish_dynamic_symbol (bfd *output_bfd, | ||
4494 | 4511 | struct _bfd_sparc_elf_link_hash_table *htab; |
4495 | 4512 | const struct elf_backend_data *bed; |
4496 | 4513 | struct _bfd_sparc_elf_link_hash_entry *eh; |
4497 | - bfd_boolean local_undefweak; | |
4514 | + bfd_boolean resolved_to_zero; | |
4498 | 4515 | |
4499 | 4516 | htab = _bfd_sparc_elf_hash_table (info); |
4500 | 4517 | BFD_ASSERT (htab != NULL); |
@@ -4505,7 +4522,7 @@ _bfd_sparc_elf_finish_dynamic_symbol (bfd *output_bfd, | ||
4505 | 4522 | /* We keep PLT/GOT entries without dynamic PLT/GOT relocations for |
4506 | 4523 | resolved undefined weak symbols in executable so that their |
4507 | 4524 | references have value 0 at run-time. */ |
4508 | - local_undefweak = UNDEFINED_WEAK_RESOLVED_TO_ZERO (info, eh); | |
4525 | + resolved_to_zero = UNDEFINED_WEAK_RESOLVED_TO_ZERO (info, eh); | |
4509 | 4526 | |
4510 | 4527 | if (h->plt.offset != (bfd_vma) -1) |
4511 | 4528 | { |
@@ -4630,8 +4647,7 @@ _bfd_sparc_elf_finish_dynamic_symbol (bfd *output_bfd, | ||
4630 | 4647 | loc += rela_index * bed->s->sizeof_rela; |
4631 | 4648 | bed->s->swap_reloca_out (output_bfd, &rela, loc); |
4632 | 4649 | |
4633 | - if (!local_undefweak | |
4634 | - && !h->def_regular) | |
4650 | + if (!resolved_to_zero && !h->def_regular) | |
4635 | 4651 | { |
4636 | 4652 | /* Mark the symbol as undefined, rather than as defined in |
4637 | 4653 | the .plt section. Leave the value alone. */ |
@@ -4645,12 +4661,14 @@ _bfd_sparc_elf_finish_dynamic_symbol (bfd *output_bfd, | ||
4645 | 4661 | } |
4646 | 4662 | } |
4647 | 4663 | |
4648 | - /* Don't generate dynamic GOT relocation against undefined weak | |
4649 | - symbol in executable. */ | |
4664 | + /* Don't generate dynamic GOT relocation against resolved undefined weak | |
4665 | + symbols in an executable. */ | |
4650 | 4666 | if (h->got.offset != (bfd_vma) -1 |
4651 | 4667 | && _bfd_sparc_elf_hash_entry(h)->tls_type != GOT_TLS_GD |
4652 | 4668 | && _bfd_sparc_elf_hash_entry(h)->tls_type != GOT_TLS_IE |
4653 | - && !local_undefweak) | |
4669 | + && !(h->root.type == bfd_link_hash_undefweak | |
4670 | + && (ELF_ST_VISIBILITY (h->other) != STV_DEFAULT | |
4671 | + || resolved_to_zero))) | |
4654 | 4672 | { |
4655 | 4673 | asection *sgot; |
4656 | 4674 | asection *srela; |
@@ -4686,8 +4704,8 @@ _bfd_sparc_elf_finish_dynamic_symbol (bfd *output_bfd, | ||
4686 | 4704 | + (h->got.offset & ~(bfd_vma) 1)); |
4687 | 4705 | return TRUE; |
4688 | 4706 | } |
4689 | - else if (bfd_link_pic (info) | |
4690 | - && SYMBOL_REFERENCES_LOCAL (info, h)) | |
4707 | + | |
4708 | + if (bfd_link_pic (info) && SYMBOL_REFERENCES_LOCAL (info, h)) | |
4691 | 4709 | { |
4692 | 4710 | asection *sec = h->root.u.def.section; |
4693 | 4711 | if (h->type == STT_GNU_IFUNC) |
@@ -1,4 +1,4 @@ | ||
1 | -#define BFD_VERSION_DATE 20180110 | |
1 | +#define BFD_VERSION_DATE 20180115 | |
2 | 2 | #define BFD_VERSION @bfd_version@ |
3 | 3 | #define BFD_VERSION_STRING @bfd_version_package@ @bfd_version_string@ |
4 | 4 | #define REPORT_BUGS_TO @report_bugs_to@ |
@@ -1,3 +1,11 @@ | ||
1 | +2018-01-12 Eric Christopher <echristo@gmail.com> | |
2 | + | |
3 | + Apply from master: | |
4 | + 2018-01-12 Sterling Augustine <saugustine@google.com> | |
5 | + | |
6 | + * cref.cc (Cref_inputs::Cref_table_compare::operator): Add | |
7 | + conditionals and calls to is_forwarder. | |
8 | + | |
1 | 9 | 2017-12-01 Cary Coutant <ccoutant@gmail.com> |
2 | 10 | |
3 | 11 | PR gold/22309 |
@@ -236,9 +236,13 @@ Cref_inputs::Cref_table_compare::operator()(const Symbol* s1, | ||
236 | 236 | } |
237 | 237 | |
238 | 238 | // We should never have two different symbols with the same name and |
239 | - // version. | |
239 | + // version, where one doesn't forward to the other. | |
240 | 240 | if (s1 == s2) |
241 | 241 | return false; |
242 | + if (s1->is_forwarder() && !s2->is_forwarder()) | |
243 | + return true; | |
244 | + if (!s1->is_forwarder() && s2->is_forwarder()) | |
245 | + return false; | |
242 | 246 | gold_unreachable(); |
243 | 247 | } |
244 | 248 |