PR32690, assertion failure in lang_size_relro_segment
Alan Modra
amodra@gmail.com
Mon Feb 17 22:54:55 GMT 2025
I'm going to commit this after a little testing. I'm fairly certain
there are more places where the new function should be used, but that
can be done with a followup patch.
This introduces a new function which should be used whenever the
linker needs to increase section alignment after mapping input to
output sections.
PR ld/32690
* linker.c (bfd_link_align_section): New function.
* elflink.c (_bfd_elf_adjust_dynamic_copy): Use it.
* bfd-in2.h: Regenerate.
diff --git a/bfd/bfd-in2.h b/bfd/bfd-in2.h
index 4aa814abe79..c29ff2bbc66 100644
--- a/bfd/bfd-in2.h
+++ b/bfd/bfd-in2.h
@@ -2964,6 +2964,8 @@ const char *bfd_format_string (bfd_format format);
&& bfd_is_abs_section ((H)->u.def.section) \
&& !(H)->rel_from_abs)
+bool bfd_link_align_section (asection *, unsigned int);
+
bool bfd_link_split_section (bfd *abfd, asection *sec);
#define bfd_link_split_section(abfd, sec) \
diff --git a/bfd/elflink.c b/bfd/elflink.c
index df6eb250961..f65b6bf0f95 100644
--- a/bfd/elflink.c
+++ b/bfd/elflink.c
@@ -3384,12 +3384,9 @@ _bfd_elf_adjust_dynamic_copy (struct bfd_link_info *info,
--power_of_two;
}
- if (power_of_two > bfd_section_alignment (dynbss))
- {
- /* Adjust the section alignment if needed. */
- if (!bfd_set_section_alignment (dynbss, power_of_two))
- return false;
- }
+ /* Adjust the section alignment if needed. */
+ if (!bfd_link_align_section (dynbss, power_of_two))
+ return false;
/* We make sure that the symbol will be aligned properly. */
dynbss->size = BFD_ALIGN (dynbss->size, mask + 1);
diff --git a/bfd/linker.c b/bfd/linker.c
index 1c466e501d5..e7f0c1ad404 100644
--- a/bfd/linker.c
+++ b/bfd/linker.c
@@ -1854,7 +1854,47 @@ _bfd_generic_link_add_one_symbol (struct bfd_link_info *info,
return true;
}
-
+
+/*
+FUNCTION
+ bfd_link_align_section
+
+SYNOPSIS
+ bool bfd_link_align_section (asection *, unsigned int);
+
+DESCRIPTION
+ Increase section alignment if the current section alignment is
+ less than the requested value. Adjust output section
+ alignment too, so that linker layout adjusts for alignment on
+ the current lang_size_sections pass. This is important for
+ lang_size_relro_segment. If the output section alignment
+ isn't adjusted, the linker will place the output section at an
+ address depending on its current alignment. When sizing the
+ output section, input sections attached transfer any increase
+ in alignment to the output section, which will affect layout
+ for the next sizing pass. Which is all well and good except
+ that lang_size_relro_segment for the current sizing pass uses
+ that possibly increased alignment with a layout that doesn't
+ suit.
+*/
+
+bool
+bfd_link_align_section (asection *sec, unsigned int align_p2)
+{
+ if (align_p2 > bfd_section_alignment (sec))
+ {
+ if (!bfd_set_section_alignment (sec, align_p2))
+ return false;
+ asection *osec = sec->output_section;
+ if (osec && align_p2 > bfd_section_alignment (osec))
+ {
+ if (!bfd_set_section_alignment (osec, align_p2))
+ return false;
+ }
+ }
+ return true;
+}
+
/* Generic final link routine. */
bool
--
Alan Modra
More information about the Binutils
mailing list