+2009-12-16 Doug Kwan <dougkwan@google.com>
+
+ * arm.cc (Arm_relobj::scan_sections_for_stubs): Exclude ICF-eliminated
+ sections.
+ * object.cc (Sized_relobj::do_finalize_local_symbols): Handle
+ relaxed input sections.
+ * output.cc (Output_section::find_relaxed_input_section): Change
+ return type to Output_relaxed_input_section pointer. Adjust code
+ for new type of relaxed_input_section_map_.
+ * output.h (Output_section::find_relaxed_input_section): Change
+ return type to Output_relaxed_input_section pointer.
+ (Output_section::Output_relaxed_input_section_by_input_section_map):
+ New type.
+ (Output_section::relaxed_input_section_map_): Change type to
+ Output_section::Output_relaxed_input_section_by_input_section_map.
+ * symtab.cc (Symbol_table::compute_final_value): Handle relaxed
+ input section.
+
2009-12-15 Ian Lance Taylor <iant@google.com>
* layout.cc (Layout::create_shstrtab): Only write out after input
}
Output_section* os = out_sections[index];
- if (os == NULL)
+ if (os == NULL
+ || symtab->is_section_folded(this, index))
{
// This relocation section is against a section which we
- // discarded.
+ // discarded or if the section is folded into another
+ // section due to ICF.
continue;
}
Arm_address output_offset = this->get_output_section_offset(index);
os = folded_obj->output_section(folded.second);
gold_assert(os != NULL);
secoffset = folded_obj->get_output_section_offset(folded.second);
- gold_assert(secoffset != invalid_address);
+
+ // This could be a relaxed input section.
+ if (secoffset == invalid_address)
+ {
+ const Output_relaxed_input_section* relaxed_section =
+ os->find_relaxed_input_section(folded_obj, folded.second);
+ gold_assert(relaxed_section != NULL);
+ secoffset = relaxed_section->address() - os->address();
+ }
}
if (os == NULL)
// Find an relaxed input section corresponding to an input section
// in OBJECT with index SHNDX.
-const Output_section_data*
+const Output_relaxed_input_section*
Output_section::find_relaxed_input_section(const Relobj* object,
unsigned int shndx) const
{
}
Input_section_specifier iss(object, shndx);
- Output_section_data_by_input_section_map::const_iterator p =
+ Output_relaxed_input_section_by_input_section_map::const_iterator p =
this->relaxed_input_section_map_.find(iss);
if (p != this->relaxed_input_section_map_.end())
return p->second;
// Find a relaxed input section to an input section in OBJECT
// with index SHNDX. Return NULL if none is found.
- const Output_section_data*
+ const Output_relaxed_input_section*
find_relaxed_input_section(const Relobj* object, unsigned int shndx) const;
// Print merge statistics to stderr.
Input_section_specifier::equal_to>
Output_section_data_by_input_section_map;
+ // Map that link Input_section_specifier to Output_relaxed_input_section.
+ typedef Unordered_map<Input_section_specifier, Output_relaxed_input_section*,
+ Input_section_specifier::hash,
+ Input_section_specifier::equal_to>
+ Output_relaxed_input_section_by_input_section_map;
+
// Map used during relaxation of existing sections. This map
// an input section specifier to an input section list index.
// We assume that Input_section_list is a vector.
// Map from input sections to relaxed input sections. This is mutable
// because it is updated lazily. We may need to update it in a
// const qualified method.
- mutable Output_section_data_by_input_section_map relaxed_input_section_map_;
+ mutable Output_relaxed_input_section_by_input_section_map
+ relaxed_input_section_map_;
// Whether relaxed_input_section_map_ is valid.
mutable bool is_relaxed_input_section_map_valid_;
};
{
Relobj* relobj = static_cast<Relobj*>(symobj);
Output_section* os = relobj->output_section(shndx);
- uint64_t secoff64 = relobj->output_section_offset(shndx);
if (this->is_section_folded(relobj, shndx))
{
shndx);
gold_assert(folded.first != NULL);
Relobj* folded_obj = reinterpret_cast<Relobj*>(folded.first);
- os = folded_obj->output_section(folded.second);
+ unsigned folded_shndx = folded.second;
+
+ os = folded_obj->output_section(folded_shndx);
gold_assert(os != NULL);
- secoff64 = folded_obj->output_section_offset(folded.second);
+
+ // Replace (relobj, shndx) with canonical ICF input section.
+ shndx = folded_shndx;
+ relobj = folded_obj;
}
+ uint64_t secoff64 = relobj->output_section_offset(shndx);
if (os == NULL)
{
bool static_or_reloc = (parameters->doing_static_link() ||