mirror of
https://github.com/espressif/binutils-gdb.git
synced 2025-06-25 04:49:54 +08:00
Correct the definition of _gp and _GLOBAL_OFFSET_TABLE_ symbols for MIPS.
gold/ * mips.cc (symbol_refs_local): Return false if a symbol is from a dynamic object. (Target_mips::got_section): Make _GLOBAL_OFFSET_TABLE_ STV_HIDDEN. (Target_mips::set_gp): Refactor. Make _gp STT_NOTYPE and STB_LOCAL. (Target_mips::do_finalize_sections): Set _gp after all the checks for creating .got are done. (Target_mips::Scan::global): Remove unused code.
This commit is contained in:

committed by
Cary Coutant

parent
b416fe873e
commit
453018bf44
@ -1,3 +1,14 @@
|
|||||||
|
2017-03-15 Vladimir Radosavljevic <Vladimir.Radosavljevic@imgtec.com>
|
||||||
|
|
||||||
|
* mips.cc (symbol_refs_local): Return false if a symbol
|
||||||
|
is from a dynamic object.
|
||||||
|
(Target_mips::got_section): Make _GLOBAL_OFFSET_TABLE_ STV_HIDDEN.
|
||||||
|
(Target_mips::set_gp): Refactor. Make _gp STT_NOTYPE and
|
||||||
|
STB_LOCAL.
|
||||||
|
(Target_mips::do_finalize_sections): Set _gp after all the checks
|
||||||
|
for creating .got are done.
|
||||||
|
(Target_mips::Scan::global): Remove unused code.
|
||||||
|
|
||||||
2017-02-22 Alan Modra <amodra@gmail.com>
|
2017-02-22 Alan Modra <amodra@gmail.com>
|
||||||
|
|
||||||
* powerpc.cc (Target_powerpc::make_iplt_section): Check that
|
* powerpc.cc (Target_powerpc::make_iplt_section): Check that
|
||||||
|
79
gold/mips.cc
79
gold/mips.cc
@ -2926,8 +2926,7 @@ symbol_refs_local(const Symbol* sym, bool has_dynsym_entry,
|
|||||||
|
|
||||||
// If we don't have a definition in a regular file, then we can't
|
// If we don't have a definition in a regular file, then we can't
|
||||||
// resolve locally. The sym is either undefined or dynamic.
|
// resolve locally. The sym is either undefined or dynamic.
|
||||||
if (sym->source() != Symbol::FROM_OBJECT || sym->object()->is_dynamic()
|
if (sym->is_from_dynobj() || sym->is_undefined())
|
||||||
|| sym->is_undefined())
|
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
// Forced local symbols resolve locally.
|
// Forced local symbols resolve locally.
|
||||||
@ -8378,7 +8377,7 @@ Target_mips<size, big_endian>::got_section(Symbol_table* symtab,
|
|||||||
this->got_,
|
this->got_,
|
||||||
0, 0, elfcpp::STT_OBJECT,
|
0, 0, elfcpp::STT_OBJECT,
|
||||||
elfcpp::STB_GLOBAL,
|
elfcpp::STB_GLOBAL,
|
||||||
elfcpp::STV_DEFAULT, 0,
|
elfcpp::STV_HIDDEN, 0,
|
||||||
false, false);
|
false, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -8391,53 +8390,30 @@ template<int size, bool big_endian>
|
|||||||
void
|
void
|
||||||
Target_mips<size, big_endian>::set_gp(Layout* layout, Symbol_table* symtab)
|
Target_mips<size, big_endian>::set_gp(Layout* layout, Symbol_table* symtab)
|
||||||
{
|
{
|
||||||
if (this->gp_ != NULL)
|
gold_assert(this->gp_ == NULL);
|
||||||
return;
|
|
||||||
|
|
||||||
Output_data* section = layout->find_output_section(".got");
|
|
||||||
if (section == NULL)
|
|
||||||
{
|
|
||||||
// If there is no .got section, gp should be based on .sdata.
|
|
||||||
// TODO(sasa): This is probably not needed. This was needed for older
|
|
||||||
// MIPS architectures which accessed both GOT and .sdata section using
|
|
||||||
// gp-relative addressing. Modern Mips Linux ELF architectures don't
|
|
||||||
// access .sdata using gp-relative addressing.
|
|
||||||
for (Layout::Section_list::const_iterator
|
|
||||||
p = layout->section_list().begin();
|
|
||||||
p != layout->section_list().end();
|
|
||||||
++p)
|
|
||||||
{
|
|
||||||
if (strcmp((*p)->name(), ".sdata") == 0)
|
|
||||||
{
|
|
||||||
section = *p;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
Sized_symbol<size>* gp =
|
Sized_symbol<size>* gp =
|
||||||
static_cast<Sized_symbol<size>*>(symtab->lookup("_gp"));
|
static_cast<Sized_symbol<size>*>(symtab->lookup("_gp"));
|
||||||
if (gp != NULL)
|
|
||||||
|
// Set _gp symbol if the linker script hasn't created it.
|
||||||
|
if (gp == NULL || gp->source() != Symbol::IS_CONSTANT)
|
||||||
{
|
{
|
||||||
if (gp->source() != Symbol::IS_CONSTANT && section != NULL)
|
// If there is no .got section, gp should be based on .sdata.
|
||||||
gp->init_output_data(gp->name(), NULL, section, MIPS_GP_OFFSET, 0,
|
Output_data* gp_section = (this->got_ != NULL
|
||||||
elfcpp::STT_OBJECT,
|
? this->got_->output_section()
|
||||||
elfcpp::STB_GLOBAL,
|
: layout->find_output_section(".sdata"));
|
||||||
elfcpp::STV_DEFAULT, 0,
|
|
||||||
false, false);
|
if (gp_section != NULL)
|
||||||
this->gp_ = gp;
|
gp = static_cast<Sized_symbol<size>*>(symtab->define_in_output_data(
|
||||||
}
|
"_gp", NULL, Symbol_table::PREDEFINED,
|
||||||
else if (section != NULL)
|
gp_section, MIPS_GP_OFFSET, 0,
|
||||||
{
|
elfcpp::STT_NOTYPE,
|
||||||
gp = static_cast<Sized_symbol<size>*>(symtab->define_in_output_data(
|
elfcpp::STB_LOCAL,
|
||||||
"_gp", NULL, Symbol_table::PREDEFINED,
|
elfcpp::STV_DEFAULT,
|
||||||
section, MIPS_GP_OFFSET, 0,
|
0, false, false));
|
||||||
elfcpp::STT_OBJECT,
|
|
||||||
elfcpp::STB_GLOBAL,
|
|
||||||
elfcpp::STV_DEFAULT,
|
|
||||||
0, false, false));
|
|
||||||
this->gp_ = gp;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
this->gp_ = gp;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Set the dynamic symbol indexes. INDEX is the index of the first
|
// Set the dynamic symbol indexes. INDEX is the index of the first
|
||||||
@ -9579,9 +9555,6 @@ Target_mips<size, big_endian>::do_finalize_sections(Layout* layout,
|
|||||||
if (this->got16_addends_.size() > 0)
|
if (this->got16_addends_.size() > 0)
|
||||||
gold_error("Can't find matching LO16 reloc");
|
gold_error("Can't find matching LO16 reloc");
|
||||||
|
|
||||||
// Set _gp value.
|
|
||||||
this->set_gp(layout, symtab);
|
|
||||||
|
|
||||||
// Check for any mips16 stub sections that we can discard.
|
// Check for any mips16 stub sections that we can discard.
|
||||||
if (!parameters->options().relocatable())
|
if (!parameters->options().relocatable())
|
||||||
{
|
{
|
||||||
@ -9748,6 +9721,9 @@ Target_mips<size, big_endian>::do_finalize_sections(Layout* layout,
|
|||||||
this->copy_relocs_.emit_mips(this->rel_dyn_section(layout), symtab, layout,
|
this->copy_relocs_.emit_mips(this->rel_dyn_section(layout), symtab, layout,
|
||||||
this);
|
this);
|
||||||
|
|
||||||
|
// Set _gp value.
|
||||||
|
this->set_gp(layout, symtab);
|
||||||
|
|
||||||
// Emit dynamic relocs.
|
// Emit dynamic relocs.
|
||||||
for (typename std::vector<Dyn_reloc>::iterator p = this->dyn_relocs_.begin();
|
for (typename std::vector<Dyn_reloc>::iterator p = this->dyn_relocs_.begin();
|
||||||
p != this->dyn_relocs_.end();
|
p != this->dyn_relocs_.end();
|
||||||
@ -10865,13 +10841,6 @@ Target_mips<size, big_endian>::Scan::global(
|
|||||||
// looking for relocs that would need to refer to MIPS16 stubs.
|
// looking for relocs that would need to refer to MIPS16 stubs.
|
||||||
mips_sym->set_need_fn_stub();
|
mips_sym->set_need_fn_stub();
|
||||||
|
|
||||||
// A reference to _GLOBAL_OFFSET_TABLE_ implies that we need a got
|
|
||||||
// section. We check here to avoid creating a dynamic reloc against
|
|
||||||
// _GLOBAL_OFFSET_TABLE_.
|
|
||||||
if (!target->has_got_section()
|
|
||||||
&& strcmp(gsym->name(), "_GLOBAL_OFFSET_TABLE_") == 0)
|
|
||||||
target->got_section(symtab, layout);
|
|
||||||
|
|
||||||
// We need PLT entries if there are static-only relocations against
|
// We need PLT entries if there are static-only relocations against
|
||||||
// an externally-defined function. This can technically occur for
|
// an externally-defined function. This can technically occur for
|
||||||
// shared libraries if there are branches to the symbol, although it
|
// shared libraries if there are branches to the symbol, although it
|
||||||
|
Reference in New Issue
Block a user