diff options
Diffstat (limited to 'gold')
-rw-r--r-- | gold/ChangeLog | 10 | ||||
-rw-r--r-- | gold/layout.cc | 20 | ||||
-rw-r--r-- | gold/options.h | 4 |
3 files changed, 28 insertions, 6 deletions
diff --git a/gold/ChangeLog b/gold/ChangeLog index 0ed1a2f..11a5c74 100644 --- a/gold/ChangeLog +++ b/gold/ChangeLog @@ -1,4 +1,12 @@ -2010-09-03 Rafael Espindola <espindola@google.com> +2010-09-09 Rafael Espindola <espindola@google.com> + + * layout.cc (Layout::attach_allocated_section_to_segment): Don't put + sections with different PF_X flags in the same segment. + (Layout::find_first_load_seg): Search all segments to find the first + one. + * options.h (rosegment): New. + +2010-09-08 Rafael Espindola <espindola@google.com> * layout.cc (Layout::set_segment_offsets): Always advance to a new page. diff --git a/gold/layout.cc b/gold/layout.cc index f0a431e..b5490d6 100644 --- a/gold/layout.cc +++ b/gold/layout.cc @@ -1171,10 +1171,11 @@ Layout::attach_allocated_section_to_segment(Output_section* os) bool is_address_set = parameters->options().section_start(os->name(), &addr); // In general the only thing we really care about for PT_LOAD - // segments is whether or not they are writable, so that is how we - // search for them. Large data sections also go into their own - // PT_LOAD segment. People who need segments sorted on some other - // basis will have to use a linker script. + // segments is whether or not they are writable or executable, + // so that is how we search for them. + // Large data sections also go into their own PT_LOAD segment. + // People who need segments sorted on some other basis will + // have to use a linker script. Segment_list::const_iterator p; for (p = this->segment_list_.begin(); @@ -1186,6 +1187,9 @@ Layout::attach_allocated_section_to_segment(Output_section* os) if (!parameters->options().omagic() && ((*p)->flags() & elfcpp::PF_W) != (seg_flags & elfcpp::PF_W)) continue; + if (parameters->options().rosegment() + && ((*p)->flags() & elfcpp::PF_X) != (seg_flags & elfcpp::PF_X)) + continue; // If -Tbss was specified, we need to separate the data and BSS // segments. if (parameters->options().user_set_Tbss()) @@ -1454,6 +1458,7 @@ Layout::define_group_signatures(Symbol_table* symtab) Output_segment* Layout::find_first_load_seg() { + Output_segment* best = NULL; for (Segment_list::const_iterator p = this->segment_list_.begin(); p != this->segment_list_.end(); ++p) @@ -1462,8 +1467,13 @@ Layout::find_first_load_seg() && ((*p)->flags() & elfcpp::PF_R) != 0 && (parameters->options().omagic() || ((*p)->flags() & elfcpp::PF_W) == 0)) - return *p; + { + if (best == NULL || this->segment_precedes(*p, best)) + best = *p; + } } + if (best != NULL) + return best; gold_assert(!this->script_options_->saw_phdrs_clause()); diff --git a/gold/options.h b/gold/options.h index c5e24cc..c990961 100644 --- a/gold/options.h +++ b/gold/options.h @@ -808,6 +808,10 @@ class General_options N_(" Only search directories specified on the command line."), NULL); + DEFINE_bool(rosegment, options::TWO_DASHES, '\0', false, + N_(" Put read-only non-executable sections in their own segment"), + NULL); + DEFINE_string(m, options::EXACTLY_ONE_DASH, 'm', "", N_("Ignored for compatibility"), N_("EMULATION")); |