aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDoug Kwan <dougkwan@google.com>2009-12-17 00:00:26 +0000
committerDoug Kwan <dougkwan@google.com>2009-12-17 00:00:26 +0000
commitd6344fb5ba8bfe0219f91c52e296707dbcdb07e3 (patch)
tree2a6c65ec60d4c8c400166139e1dc436368182b1f
parent21f8908e380ed50e16a153aae25ba9cffd6f28af (diff)
downloadgdb-d6344fb5ba8bfe0219f91c52e296707dbcdb07e3.zip
gdb-d6344fb5ba8bfe0219f91c52e296707dbcdb07e3.tar.gz
gdb-d6344fb5ba8bfe0219f91c52e296707dbcdb07e3.tar.bz2
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.
-rw-r--r--gold/ChangeLog18
-rw-r--r--gold/arm.cc6
-rw-r--r--gold/object.cc10
-rw-r--r--gold/output.cc4
-rw-r--r--gold/output.h11
-rw-r--r--gold/symtab.cc11
6 files changed, 50 insertions, 10 deletions
diff --git a/gold/ChangeLog b/gold/ChangeLog
index 86ed4e8..b6cd629 100644
--- a/gold/ChangeLog
+++ b/gold/ChangeLog
@@ -1,3 +1,21 @@
+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
diff --git a/gold/arm.cc b/gold/arm.cc
index 03cc697..b02afbe 100644
--- a/gold/arm.cc
+++ b/gold/arm.cc
@@ -3645,10 +3645,12 @@ Arm_relobj<big_endian>::scan_sections_for_stubs(
}
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);
diff --git a/gold/object.cc b/gold/object.cc
index 798e42d..9baf227 100644
--- a/gold/object.cc
+++ b/gold/object.cc
@@ -1683,7 +1683,15 @@ Sized_relobj<size, big_endian>::do_finalize_local_symbols(unsigned int 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)
diff --git a/gold/output.cc b/gold/output.cc
index 61c2ba6..440d4f2 100644
--- a/gold/output.cc
+++ b/gold/output.cc
@@ -2224,7 +2224,7 @@ Output_section::find_merge_section(const Relobj* object,
// 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
{
@@ -2247,7 +2247,7 @@ Output_section::find_relaxed_input_section(const Relobj* object,
}
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;
diff --git a/gold/output.h b/gold/output.h
index 6631aa1..3b060c8 100644
--- a/gold/output.h
+++ b/gold/output.h
@@ -2599,7 +2599,7 @@ class Output_section : public Output_data
// 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.
@@ -3190,6 +3190,12 @@ class Output_section : public Output_data
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.
@@ -3358,7 +3364,8 @@ class Output_section : public Output_data
// 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_;
};
diff --git a/gold/symtab.cc b/gold/symtab.cc
index 7e8a890..8cd4a40 100644
--- a/gold/symtab.cc
+++ b/gold/symtab.cc
@@ -2413,7 +2413,6 @@ Symbol_table::compute_final_value(
{
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))
{
@@ -2423,11 +2422,17 @@ Symbol_table::compute_final_value(
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() ||