&& 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) \
--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);
return true;
}
-\f
+
+/*
+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