1 /* ELF program property support.
2 Copyright (C) 2017-2025 Free Software Foundation, Inc.
4 This file is part of BFD, the Binary File Descriptor library.
6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 3 of the License, or
9 (at your option) any later version.
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with this program; if not, write to the Free Software
18 Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
19 MA 02110-1301, USA. */
21 /* GNU program property draft is at:
23 https://github.com/hjl-tools/linux-abi/wiki/property-draft.pdf
31 /* Get a property, allocate a new one if needed. */
34 _bfd_elf_get_property (bfd
*abfd
, unsigned int type
, unsigned int datasz
)
36 elf_property_list
*p
, **lastp
;
38 if (bfd_get_flavour (abfd
) != bfd_target_elf_flavour
)
40 /* Never should happen. */
44 /* Keep the property list in order of type. */
45 lastp
= &elf_properties (abfd
);
46 for (p
= *lastp
; p
; p
= p
->next
)
48 /* Reuse the existing entry. */
49 if (type
== p
->property
.pr_type
)
51 if (datasz
> p
->property
.pr_datasz
)
53 /* This can happen when mixing 32-bit and 64-bit objects. */
54 p
->property
.pr_datasz
= datasz
;
58 else if (type
< p
->property
.pr_type
)
62 p
= (elf_property_list
*) bfd_alloc (abfd
, sizeof (*p
));
65 _bfd_error_handler (_("%pB: out of memory in _bfd_elf_get_property"),
69 memset (p
, 0, sizeof (*p
));
70 p
->property
.pr_type
= type
;
71 p
->property
.pr_datasz
= datasz
;
77 /* Parse GNU properties. */
80 _bfd_elf_parse_gnu_properties (bfd
*abfd
, Elf_Internal_Note
*note
)
82 const struct elf_backend_data
*bed
= get_elf_backend_data (abfd
);
83 unsigned int align_size
= bed
->s
->elfclass
== ELFCLASS64
? 8 : 4;
84 bfd_byte
*ptr
= (bfd_byte
*) note
->descdata
;
85 bfd_byte
*ptr_end
= ptr
+ note
->descsz
;
87 if (note
->descsz
< 8 || (note
->descsz
% align_size
) != 0)
91 (_("warning: %pB: corrupt GNU_PROPERTY_TYPE (%ld) size: %#lx"),
92 abfd
, note
->type
, note
->descsz
);
96 while (ptr
!= ptr_end
)
102 if ((size_t) (ptr_end
- ptr
) < 8)
105 type
= bfd_h_get_32 (abfd
, ptr
);
106 datasz
= bfd_h_get_32 (abfd
, ptr
+ 4);
109 if (datasz
> (size_t) (ptr_end
- ptr
))
112 (_("warning: %pB: corrupt GNU_PROPERTY_TYPE (%ld) type (0x%x) datasz: 0x%x"),
113 abfd
, note
->type
, type
, datasz
);
114 /* Clear all properties. */
115 elf_properties (abfd
) = NULL
;
119 if (type
>= GNU_PROPERTY_LOPROC
)
121 if (bed
->elf_machine_code
== EM_NONE
)
123 /* Ignore processor-specific properties with generic ELF
124 target vector. They should be handled by the matching
125 ELF target vector. */
128 else if (type
< GNU_PROPERTY_LOUSER
129 && bed
->parse_gnu_properties
)
131 enum elf_property_kind kind
132 = bed
->parse_gnu_properties (abfd
, type
, ptr
, datasz
);
133 if (kind
== property_corrupt
)
135 /* Clear all properties. */
136 elf_properties (abfd
) = NULL
;
139 else if (kind
!= property_ignored
)
147 case GNU_PROPERTY_STACK_SIZE
:
148 if (datasz
!= align_size
)
151 (_("warning: %pB: corrupt stack size: 0x%x"),
153 /* Clear all properties. */
154 elf_properties (abfd
) = NULL
;
157 prop
= _bfd_elf_get_property (abfd
, type
, datasz
);
159 prop
->u
.number
= bfd_h_get_64 (abfd
, ptr
);
161 prop
->u
.number
= bfd_h_get_32 (abfd
, ptr
);
162 prop
->pr_kind
= property_number
;
165 case GNU_PROPERTY_NO_COPY_ON_PROTECTED
:
169 (_("warning: %pB: corrupt no copy on protected size: 0x%x"),
171 /* Clear all properties. */
172 elf_properties (abfd
) = NULL
;
175 prop
= _bfd_elf_get_property (abfd
, type
, datasz
);
176 elf_has_no_copy_on_protected (abfd
) = true;
177 prop
->pr_kind
= property_number
;
180 case GNU_PROPERTY_MEMORY_SEAL
:
184 (_("warning: %pB: corrupt memory sealing size: 0x%x"),
186 /* Clear all properties. */
187 elf_properties (abfd
) = NULL
;
190 prop
= _bfd_elf_get_property (abfd
, type
, datasz
);
191 prop
->pr_kind
= property_number
;
195 if ((type
>= GNU_PROPERTY_UINT32_AND_LO
196 && type
<= GNU_PROPERTY_UINT32_AND_HI
)
197 || (type
>= GNU_PROPERTY_UINT32_OR_LO
198 && type
<= GNU_PROPERTY_UINT32_OR_HI
))
203 (_("error: %pB: <corrupt property (0x%x) size: 0x%x>"),
205 /* Clear all properties. */
206 elf_properties (abfd
) = NULL
;
209 prop
= _bfd_elf_get_property (abfd
, type
, datasz
);
210 prop
->u
.number
|= bfd_h_get_32 (abfd
, ptr
);
211 prop
->pr_kind
= property_number
;
212 if (type
== GNU_PROPERTY_1_NEEDED
214 & GNU_PROPERTY_1_NEEDED_INDIRECT_EXTERN_ACCESS
)
217 elf_has_indirect_extern_access (abfd
) = true;
218 /* GNU_PROPERTY_NO_COPY_ON_PROTECTED is implied. */
219 elf_has_no_copy_on_protected (abfd
) = true;
228 (_("warning: %pB: unsupported GNU_PROPERTY_TYPE (%ld) type: 0x%x"),
229 abfd
, note
->type
, type
);
232 ptr
+= (datasz
+ (align_size
- 1)) & ~ (align_size
- 1);
238 /* Merge GNU property BPROP with APROP. If APROP isn't NULL, return TRUE
239 if APROP is updated. Otherwise, return TRUE if BPROP should be merged
243 elf_merge_gnu_properties (struct bfd_link_info
*info
, bfd
*abfd
, bfd
*bbfd
,
244 elf_property
*aprop
, elf_property
*bprop
)
246 const struct elf_backend_data
*bed
= get_elf_backend_data (abfd
);
247 unsigned int pr_type
= aprop
!= NULL
? aprop
->pr_type
: bprop
->pr_type
;
251 if (bed
->merge_gnu_properties
!= NULL
252 && pr_type
>= GNU_PROPERTY_LOPROC
253 && pr_type
< GNU_PROPERTY_LOUSER
)
254 return bed
->merge_gnu_properties (info
, abfd
, bbfd
, aprop
, bprop
);
258 case GNU_PROPERTY_STACK_SIZE
:
259 if (aprop
!= NULL
&& bprop
!= NULL
)
261 if (bprop
->u
.number
> aprop
->u
.number
)
263 aprop
->u
.number
= bprop
->u
.number
;
270 case GNU_PROPERTY_NO_COPY_ON_PROTECTED
:
271 case GNU_PROPERTY_MEMORY_SEAL
:
272 /* Return TRUE if APROP is NULL to indicate that BPROP should
274 return aprop
== NULL
;
278 if (pr_type
>= GNU_PROPERTY_UINT32_OR_LO
279 && pr_type
<= GNU_PROPERTY_UINT32_OR_HI
)
281 if (aprop
!= NULL
&& bprop
!= NULL
)
283 number
= aprop
->u
.number
;
284 aprop
->u
.number
= number
| bprop
->u
.number
;
285 /* Remove the property if all bits are empty. */
286 if (aprop
->u
.number
== 0)
288 aprop
->pr_kind
= property_remove
;
292 updated
= number
!= (unsigned int) aprop
->u
.number
;
296 /* Only one of APROP and BPROP can be NULL. */
299 if (aprop
->u
.number
== 0)
301 /* Remove APROP if all bits are empty. */
302 aprop
->pr_kind
= property_remove
;
308 /* Return TRUE if APROP is NULL and all bits of BPROP
309 aren't empty to indicate that BPROP should be added
311 updated
= bprop
->u
.number
!= 0;
316 else if (pr_type
>= GNU_PROPERTY_UINT32_AND_LO
317 && pr_type
<= GNU_PROPERTY_UINT32_AND_HI
)
319 /* Only one of APROP and BPROP can be NULL:
320 1. APROP & BPROP when both APROP and BPROP aren't NULL.
321 2. If APROP is NULL, remove x86 feature.
322 3. Otherwise, do nothing.
324 if (aprop
!= NULL
&& bprop
!= NULL
)
326 number
= aprop
->u
.number
;
327 aprop
->u
.number
= number
& bprop
->u
.number
;
328 updated
= number
!= (unsigned int) aprop
->u
.number
;
329 /* Remove the property if all feature bits are cleared. */
330 if (aprop
->u
.number
== 0)
331 aprop
->pr_kind
= property_remove
;
335 /* There should be no AND properties since some input
336 doesn't have them. */
339 aprop
->pr_kind
= property_remove
;
346 /* Never should happen. */
353 /* Return the property of TYPE on *LISTP and remove it from *LISTP if RM is
354 true. Return NULL if not found. */
356 static elf_property
*
357 elf_find_and_remove_property (elf_property_list
**listp
,
358 unsigned int type
, bool rm
)
360 elf_property_list
*list
;
362 for (list
= *listp
; list
; list
= list
->next
)
364 if (type
== list
->property
.pr_type
)
366 /* Remove this property. */
369 return &list
->property
;
371 else if (type
< list
->property
.pr_type
)
379 /* Merge GNU property list *LISTP in ABFD with FIRST_PBFD. */
382 elf_merge_gnu_property_list (struct bfd_link_info
*info
, bfd
*first_pbfd
,
383 bfd
*abfd
, elf_property_list
**listp
)
385 elf_property_list
*p
, **lastp
;
390 /* Merge each GNU property in FIRST_PBFD with the one on *LISTP. */
391 lastp
= &elf_properties (first_pbfd
);
392 for (p
= *lastp
; p
; p
= p
->next
)
393 if (p
->property
.pr_kind
!= property_remove
)
395 if (p
->property
.pr_kind
== property_number
)
398 number
= p
->property
.u
.number
;
402 pr
= elf_find_and_remove_property (listp
, p
->property
.pr_type
,
404 /* Pass NULL to elf_merge_gnu_properties for the property which
406 elf_merge_gnu_properties (info
, first_pbfd
, abfd
, &p
->property
, pr
);
407 if (p
->property
.pr_kind
== property_remove
)
409 if (info
->has_map_file
)
414 info
->callbacks
->minfo
415 (_("Removed property %W to merge %pB (0x%v) "
417 (bfd_vma
) p
->property
.pr_type
, first_pbfd
,
418 number
, abfd
, pr
->u
.number
);
420 info
->callbacks
->minfo
421 (_("Removed property %W to merge %pB (0x%v) "
422 "and %pB (not found)\n"),
423 (bfd_vma
) p
->property
.pr_type
, first_pbfd
,
429 info
->callbacks
->minfo
430 (_("Removed property %W to merge %pB and %pB\n"),
431 (bfd_vma
) p
->property
.pr_type
, first_pbfd
, abfd
);
433 info
->callbacks
->minfo
434 (_("Removed property %W to merge %pB and %pB "
436 (bfd_vma
) p
->property
.pr_type
, first_pbfd
, abfd
);
440 /* Remove this property. */
448 if (p
->property
.u
.number
!= number
449 || p
->property
.u
.number
!= pr
->u
.number
)
450 info
->callbacks
->minfo
451 (_("Updated property %W (0x%v) to merge %pB (0x%v) "
453 (bfd_vma
) p
->property
.pr_type
, p
->property
.u
.number
,
454 first_pbfd
, number
, abfd
, pr
->u
.number
);
458 if (p
->property
.u
.number
!= number
)
459 info
->callbacks
->minfo
460 (_("Updated property %W (%v) to merge %pB (0x%v) "
461 "and %pB (not found)\n"),
462 (bfd_vma
) p
->property
.pr_type
, p
->property
.u
.number
,
463 first_pbfd
, number
, abfd
);
469 /* Merge the remaining properties on *LISTP with FIRST_PBFD. */
470 for (p
= *listp
; p
!= NULL
; p
= p
->next
)
472 if (p
->property
.pr_kind
== property_number
)
475 number
= p
->property
.u
.number
;
480 if (elf_merge_gnu_properties (info
, first_pbfd
, abfd
, NULL
, &p
->property
))
482 if (p
->property
.pr_type
== GNU_PROPERTY_NO_COPY_ON_PROTECTED
)
483 elf_has_no_copy_on_protected (first_pbfd
) = true;
485 pr
= _bfd_elf_get_property (first_pbfd
, p
->property
.pr_type
,
486 p
->property
.pr_datasz
);
487 /* It must be a new property. */
488 if (pr
->pr_kind
!= property_unknown
)
490 /* Add a new property. */
495 pr
= elf_find_and_remove_property (&elf_properties (first_pbfd
),
501 info
->callbacks
->minfo
502 (_("Removed property %W to merge %pB (not found) and "
504 (bfd_vma
) p
->property
.pr_type
, first_pbfd
, abfd
,
507 info
->callbacks
->minfo
508 (_("Removed property %W to merge %pB and %pB\n"),
509 (bfd_vma
) p
->property
.pr_type
, first_pbfd
, abfd
);
511 else if (pr
->pr_kind
!= property_remove
)
517 /* Get GNU property section size. */
520 elf_get_gnu_property_section_size (elf_property_list
*list
,
521 unsigned int align_size
)
526 /* Compute the output section size. */
527 descsz
= offsetof (Elf_External_Note
, name
[sizeof "GNU"]);
528 descsz
= (descsz
+ 3) & -(unsigned int) 4;
530 for (; list
!= NULL
; list
= list
->next
)
533 /* Check if this property should be skipped. */
534 if (list
->property
.pr_kind
== property_remove
)
536 /* There are 4 byte type + 4 byte datasz for each property. */
537 if (list
->property
.pr_type
== GNU_PROPERTY_STACK_SIZE
)
540 datasz
= list
->property
.pr_datasz
;
541 size
+= 4 + 4 + datasz
;
542 /* Align each property. */
543 size
= (size
+ (align_size
- 1)) & ~(align_size
- 1);
549 /* Write GNU properties. */
552 elf_write_gnu_properties (struct bfd_link_info
*info
,
553 bfd
*abfd
, bfd_byte
*contents
,
554 elf_property_list
*list
, unsigned int size
,
555 unsigned int align_size
)
559 Elf_External_Note
*e_note
;
561 e_note
= (Elf_External_Note
*) contents
;
562 descsz
= offsetof (Elf_External_Note
, name
[sizeof "GNU"]);
563 descsz
= (descsz
+ 3) & -(unsigned int) 4;
564 bfd_h_put_32 (abfd
, sizeof "GNU", &e_note
->namesz
);
565 bfd_h_put_32 (abfd
, size
- descsz
, &e_note
->descsz
);
566 bfd_h_put_32 (abfd
, NT_GNU_PROPERTY_TYPE_0
, &e_note
->type
);
567 memcpy (e_note
->name
, "GNU", sizeof "GNU");
570 for (; list
!= NULL
; list
= list
->next
)
572 /* Check if this property should be skipped. */
573 if (list
->property
.pr_kind
== property_remove
)
575 /* There are 4 byte type + 4 byte datasz for each property. */
576 if (list
->property
.pr_type
== GNU_PROPERTY_STACK_SIZE
)
579 datasz
= list
->property
.pr_datasz
;
580 bfd_h_put_32 (abfd
, list
->property
.pr_type
, contents
+ size
);
581 bfd_h_put_32 (abfd
, datasz
, contents
+ size
+ 4);
584 /* Write out property value. */
585 switch (list
->property
.pr_kind
)
587 case property_number
:
591 /* Never should happen. */
598 /* Save the pointer to GNU_PROPERTY_1_NEEDED so that it
599 can be updated later if needed. */
601 && list
->property
.pr_type
== GNU_PROPERTY_1_NEEDED
)
602 info
->needed_1_p
= contents
+ size
;
603 bfd_h_put_32 (abfd
, list
->property
.u
.number
,
608 bfd_h_put_64 (abfd
, list
->property
.u
.number
,
615 /* Never should happen. */
620 /* Align each property. */
621 size
= (size
+ (align_size
- 1)) & ~ (align_size
- 1);
626 _bfd_elf_link_create_gnu_property_sec (struct bfd_link_info
*info
, bfd
*elf_bfd
,
627 unsigned int elfclass
)
631 sec
= bfd_make_section_with_flags (elf_bfd
,
632 NOTE_GNU_PROPERTY_SECTION_NAME
,
640 info
->callbacks
->einfo (_("%F%P: failed to create GNU property section\n"));
642 if (!bfd_set_section_alignment (sec
,
643 elfclass
== ELFCLASS64
? 3 : 2))
644 info
->callbacks
->einfo (_("%F%pA: failed to align section\n"),
647 elf_section_type (sec
) = SHT_NOTE
;
652 /* Set up GNU properties. Return the first relocatable ELF input with
653 GNU properties if found. Otherwise, return NULL. */
656 _bfd_elf_link_setup_gnu_properties (struct bfd_link_info
*info
)
658 bfd
*abfd
, *first_pbfd
= NULL
, *elf_bfd
= NULL
;
659 elf_property_list
*list
;
661 bool has_properties
= false;
662 const struct elf_backend_data
*bed
663 = get_elf_backend_data (info
->output_bfd
);
664 unsigned int elfclass
= bed
->s
->elfclass
;
665 int elf_machine_code
= bed
->elf_machine_code
;
668 /* Find the first relocatable ELF input with GNU properties. */
669 for (abfd
= info
->input_bfds
; abfd
!= NULL
; abfd
= abfd
->link
.next
)
670 if (bfd_get_flavour (abfd
) == bfd_target_elf_flavour
671 && (abfd
->flags
& DYNAMIC
) == 0
673 == get_elf_backend_data (abfd
)->elf_machine_code
)
674 && (elfclass
== get_elf_backend_data (abfd
)->s
->elfclass
))
676 /* Ignore GNU properties from ELF objects with different machine
677 code or class. Also skip objects without a GNU_PROPERTY note
681 if (elf_properties (abfd
) != NULL
)
683 has_properties
= true;
685 if (bfd_get_section_by_name (abfd
,
686 NOTE_GNU_PROPERTY_SECTION_NAME
)
689 /* Keep .note.gnu.property section in FIRST_PBFD. */
696 if (info
->indirect_extern_access
> 0 && elf_bfd
!= NULL
)
698 /* Support -z indirect-extern-access. */
699 if (first_pbfd
== NULL
)
701 sec
= _bfd_elf_link_create_gnu_property_sec (info
, elf_bfd
, elfclass
);
702 first_pbfd
= elf_bfd
;
703 has_properties
= true;
706 p
= _bfd_elf_get_property (first_pbfd
, GNU_PROPERTY_1_NEEDED
, 4);
707 if (p
->pr_kind
== property_unknown
)
709 /* Create GNU_PROPERTY_1_NEEDED. */
711 = GNU_PROPERTY_1_NEEDED_INDIRECT_EXTERN_ACCESS
;
712 p
->pr_kind
= property_number
;
716 |= GNU_PROPERTY_1_NEEDED_INDIRECT_EXTERN_ACCESS
;
721 if (info
->memory_seal
)
723 /* Support -z no-memory-seal. */
724 if (first_pbfd
== NULL
)
726 sec
= _bfd_elf_link_create_gnu_property_sec (info
, elf_bfd
, elfclass
);
727 first_pbfd
= elf_bfd
;
728 has_properties
= true;
731 p
= _bfd_elf_get_property (first_pbfd
, GNU_PROPERTY_MEMORY_SEAL
, 0);
732 if (p
->pr_kind
== property_unknown
)
734 /* Create GNU_PROPERTY_NO_MEMORY_SEAL. */
735 p
->u
.number
= GNU_PROPERTY_MEMORY_SEAL
;
736 p
->pr_kind
= property_number
;
740 elf_find_and_remove_property (&elf_properties (elf_bfd
),
741 GNU_PROPERTY_MEMORY_SEAL
, true);
744 /* Do nothing if there is no .note.gnu.property section. */
748 /* Merge .note.gnu.property sections. */
749 info
->callbacks
->minfo (_("\n"));
750 info
->callbacks
->minfo (_("Merging program properties\n"));
751 info
->callbacks
->minfo (_("\n"));
753 for (abfd
= info
->input_bfds
; abfd
!= NULL
; abfd
= abfd
->link
.next
)
754 if (abfd
!= first_pbfd
755 && (abfd
->flags
& (DYNAMIC
| BFD_PLUGIN
| BFD_LINKER_CREATED
)) == 0)
757 elf_property_list
*null_ptr
= NULL
;
758 elf_property_list
**listp
= &null_ptr
;
760 /* Merge .note.gnu.property section in relocatable ELF input. */
761 if (bfd_get_flavour (abfd
) == bfd_target_elf_flavour
)
763 list
= elf_properties (abfd
);
765 /* Ignore GNU properties from ELF objects with different
769 == get_elf_backend_data (abfd
)->elf_machine_code
))
770 listp
= &elf_properties (abfd
);
775 /* Merge properties with FIRST_PBFD. FIRST_PBFD can be NULL
776 when all properties are from ELF objects with different
777 machine code or class. */
778 if (first_pbfd
!= NULL
)
779 elf_merge_gnu_property_list (info
, first_pbfd
, abfd
, listp
);
783 /* Discard the .note.gnu.property section in this bfd. */
784 sec
= bfd_get_section_by_name (abfd
,
785 NOTE_GNU_PROPERTY_SECTION_NAME
);
787 sec
->output_section
= bfd_abs_section_ptr
;
791 /* Rewrite .note.gnu.property section so that GNU properties are
792 always sorted by type even if input GNU properties aren't sorted. */
793 if (first_pbfd
!= NULL
)
797 unsigned int align_size
= elfclass
== ELFCLASS64
? 8 : 4;
799 sec
= bfd_get_section_by_name (first_pbfd
,
800 NOTE_GNU_PROPERTY_SECTION_NAME
);
801 BFD_ASSERT (sec
!= NULL
);
803 /* Update stack size in .note.gnu.property with -z stack-size=N
805 if (info
->stacksize
> 0)
807 bfd_vma stacksize
= info
->stacksize
;
809 p
= _bfd_elf_get_property (first_pbfd
, GNU_PROPERTY_STACK_SIZE
,
811 if (p
->pr_kind
== property_unknown
)
813 /* Create GNU_PROPERTY_STACK_SIZE. */
814 p
->u
.number
= stacksize
;
815 p
->pr_kind
= property_number
;
817 else if (stacksize
> p
->u
.number
)
818 p
->u
.number
= stacksize
;
820 else if (elf_properties (first_pbfd
) == NULL
)
822 /* Discard .note.gnu.property section if all properties have
824 sec
->output_section
= bfd_abs_section_ptr
;
828 /* Fix up GNU properties. */
829 if (bed
->fixup_gnu_properties
)
830 bed
->fixup_gnu_properties (info
, &elf_properties (first_pbfd
));
832 if (elf_properties (first_pbfd
) == NULL
)
834 /* Discard .note.gnu.property section if all properties have
836 sec
->output_section
= bfd_abs_section_ptr
;
840 /* Compute the section size. */
841 list
= elf_properties (first_pbfd
);
842 size
= elf_get_gnu_property_section_size (list
, align_size
);
844 /* Update .note.gnu.property section now. */
846 contents
= (bfd_byte
*) bfd_zalloc (first_pbfd
, size
);
848 if (info
->indirect_extern_access
<= 0)
850 /* Get GNU_PROPERTY_1_NEEDED properties. */
851 p
= elf_find_and_remove_property (&elf_properties (first_pbfd
),
852 GNU_PROPERTY_1_NEEDED
, false);
855 if (info
->indirect_extern_access
< 0)
857 /* Set indirect_extern_access to 1 to indicate that
858 it is turned on by input properties. */
860 & GNU_PROPERTY_1_NEEDED_INDIRECT_EXTERN_ACCESS
)
862 info
->indirect_extern_access
= 1;
865 /* Turn off indirect external access. */
867 &= ~GNU_PROPERTY_1_NEEDED_INDIRECT_EXTERN_ACCESS
;
871 elf_write_gnu_properties (info
, first_pbfd
, contents
, list
, size
,
874 /* Cache the section contents for elf_link_input_bfd. */
876 elf_section_data (sec
)->this_hdr
.contents
= contents
;
878 /* If GNU_PROPERTY_NO_COPY_ON_PROTECTED is set, protected data
879 symbol is defined in the shared object. */
880 if (elf_has_no_copy_on_protected (first_pbfd
))
881 info
->extern_protected_data
= false;
883 if (info
->indirect_extern_access
> 0)
885 /* For indirect external access, don't generate copy
886 relocations. NB: Set to nocopyreloc to 2 to indicate
887 that it is implied by indirect_extern_access. */
888 info
->nocopyreloc
= 2;
889 info
->extern_protected_data
= false;
896 /* Convert GNU property size. */
899 _bfd_elf_convert_gnu_property_size (bfd
*ibfd
, bfd
*obfd
)
901 unsigned int align_size
;
902 const struct elf_backend_data
*bed
;
903 elf_property_list
*list
= elf_properties (ibfd
);
905 bed
= get_elf_backend_data (obfd
);
906 align_size
= bed
->s
->elfclass
== ELFCLASS64
? 8 : 4;
908 /* Get the output .note.gnu.property section size. */
909 return elf_get_gnu_property_section_size (list
, align_size
);
912 /* Convert GNU properties. */
915 _bfd_elf_convert_gnu_properties (bfd
*ibfd
, asection
*isec
,
916 bfd
*obfd
, bfd_byte
**ptr
,
917 bfd_size_type
*ptr_size
)
921 unsigned int align_shift
;
922 const struct elf_backend_data
*bed
;
923 elf_property_list
*list
= elf_properties (ibfd
);
925 bed
= get_elf_backend_data (obfd
);
926 align_shift
= bed
->s
->elfclass
== ELFCLASS64
? 3 : 2;
928 /* Get the output .note.gnu.property section size. */
929 size
= bfd_section_size (isec
->output_section
);
931 /* Update the output .note.gnu.property section alignment. */
932 bfd_set_section_alignment (isec
->output_section
, align_shift
);
934 if (size
> bfd_section_size (isec
))
936 contents
= (bfd_byte
*) bfd_malloc (size
);
937 if (contents
== NULL
)
947 /* Generate the output .note.gnu.property section. */
948 elf_write_gnu_properties (NULL
, ibfd
, contents
, list
, size
,