summaryrefslogtreecommitdiff
path: root/gold/object.cc
diff options
context:
space:
mode:
authorCary Coutant <ccoutant@google.com>2010-06-10 17:20:27 +0000
committerCary Coutant <ccoutant@google.com>2010-06-10 17:20:27 +0000
commitf3a2388fc96c63c0233cdc3449ea61cf36e4975b (patch)
treed073b85cc10872fe8a3f3a93207f829932255370 /gold/object.cc
parent7530c4809276954eebc6cfa9a41452d15da31bdb (diff)
downloadbinutils-gdb-f3a2388fc96c63c0233cdc3449ea61cf36e4975b.tar.gz
* object.cc (Sized_relobj::do_layout): Defer layout for reloc sections.
(Sized_relobj::do_layout_deferred_sections): Do layout for deferred reloc sections. * object.h (Sized_relobj::deferred_layout_relocs_): New data member. PR 11683 * symtab.h (Symbol::is_placeholder): New member function. * target-reloc.h (relocate_section): Check for placeholder symbols. * testsuite/Makefile.am (plugin_test_8): New test. (plugin_test_9): New test. * testsuite/Makefile.in: Regenerate.
Diffstat (limited to 'gold/object.cc')
-rw-r--r--gold/object.cc41
1 files changed, 41 insertions, 0 deletions
diff --git a/gold/object.cc b/gold/object.cc
index 24fd5862960..b034ee209ac 100644
--- a/gold/object.cc
+++ b/gold/object.cc
@@ -1371,6 +1371,17 @@ Sized_relobj<size, big_endian>::do_layout(Symbol_table* symtab,
}
Output_section* data_section = out_sections[data_shndx];
+ if (data_section == reinterpret_cast<Output_section*>(2))
+ {
+ // The layout for the data section was deferred, so we need
+ // to defer the relocation section, too.
+ const char* name = pnames + shdr.get_sh_name();
+ this->deferred_layout_relocs_.push_back(
+ Deferred_layout(i, name, pshdr, 0, elfcpp::SHT_NULL));
+ out_sections[i] = reinterpret_cast<Output_section*>(2);
+ out_section_offsets[i] = invalid_address;
+ continue;
+ }
if (data_section == NULL)
{
out_sections[i] = NULL;
@@ -1471,6 +1482,36 @@ Sized_relobj<size, big_endian>::do_layout_deferred_sections(Layout* layout)
}
this->deferred_layout_.clear();
+
+ // Now handle the deferred relocation sections.
+
+ Output_sections& out_sections(this->output_sections());
+ std::vector<Address>& out_section_offsets(this->section_offsets_);
+
+ for (deferred = this->deferred_layout_relocs_.begin();
+ deferred != this->deferred_layout_relocs_.end();
+ ++deferred)
+ {
+ unsigned int shndx = deferred->shndx_;
+ typename This::Shdr shdr(deferred->shdr_data_);
+ unsigned int data_shndx = this->adjust_shndx(shdr.get_sh_info());
+
+ Output_section* data_section = out_sections[data_shndx];
+ if (data_section == NULL)
+ {
+ out_sections[shndx] = NULL;
+ out_section_offsets[shndx] = invalid_address;
+ continue;
+ }
+
+ Relocatable_relocs* rr = new Relocatable_relocs();
+ this->set_relocatable_relocs(shndx, rr);
+
+ Output_section* os = layout->layout_reloc(this, shndx, shdr,
+ data_section, rr);
+ out_sections[shndx] = os;
+ out_section_offsets[shndx] = invalid_address;
+ }
}
// Add the symbols to the symbol table.