Add section type verification for hash section

This commit is contained in:
Serge Lamikhov-Center 2021-07-23 09:57:56 +03:00
parent 17f2d71f30
commit 46b1e22414
2 changed files with 31 additions and 23 deletions

View File

@ -521,6 +521,7 @@ typedef uint64_t Elf64_Off;
#define SHT_PREINIT_ARRAY 16
#define SHT_GROUP 17
#define SHT_SYMTAB_SHNDX 18
#define SHT_GNU_HASH 0x6FFFFFF6
#define SHT_LOOS 0x60000000
#define SHT_HIOS 0x6fffffff
#define SHT_LOPROC 0x70000000
@ -738,6 +739,7 @@ typedef uint64_t Elf64_Off;
#define DT_PREINIT_ARRAY 32
#define DT_PREINIT_ARRAYSZ 33
#define DT_MAXPOSTAGS 34
#define DT_GNU_HASH 0x6ffffef5
#define DT_LOOS 0x6000000D
#define DT_HIOS 0x6ffff000
#define DT_LOPROC 0x70000000

View File

@ -30,10 +30,11 @@ template <class S> class symbol_section_accessor_template
{
public:
//------------------------------------------------------------------------------
symbol_section_accessor_template( const elfio& elf_file,
S* symbol_section )
symbol_section_accessor_template( const elfio& elf_file, S* symbol_section )
: elf_file( elf_file ), symbol_section( symbol_section )
{
hash_section = 0;
hash_section_index = 0;
find_hash_section();
}
@ -85,24 +86,27 @@ template <class S> class symbol_section_accessor_template
bool ret = false;
if ( 0 != get_hash_table_index() ) {
Elf_Word nbucket = *(const Elf_Word*)hash_section->get_data();
Elf_Word nchain = *(const Elf_Word*)( hash_section->get_data() +
sizeof( Elf_Word ) );
Elf_Word val = elf_hash( (const unsigned char*)name.c_str() );
Elf_Word y = *(const Elf_Word*)( hash_section->get_data() +
( 2 + val % nbucket ) *
sizeof( Elf_Word ) );
std::string str;
get_symbol( y, str, value, size, bind, type, section_index, other );
while ( str != name && STN_UNDEF != y && y < nchain ) {
y = *(const Elf_Word*)( hash_section->get_data() +
( 2 + nbucket + y ) *
sizeof( Elf_Word ) );
if ( hash_section->get_type() == SHT_HASH ) {
Elf_Word nbucket = *(const Elf_Word*)hash_section->get_data();
Elf_Word nchain = *(const Elf_Word*)( hash_section->get_data() +
sizeof( Elf_Word ) );
Elf_Word val = elf_hash( (const unsigned char*)name.c_str() );
Elf_Word y = *(const Elf_Word*)( hash_section->get_data() +
( 2 + val % nbucket ) *
sizeof( Elf_Word ) );
std::string str;
get_symbol( y, str, value, size, bind, type, section_index,
other );
}
if ( str == name ) {
ret = true;
while ( str != name && STN_UNDEF != y && y < nchain ) {
y = *(const Elf_Word*)( hash_section->get_data() +
( 2 + nbucket + y ) *
sizeof( Elf_Word ) );
get_symbol( y, str, value, size, bind, type, section_index,
other );
}
if ( str == name ) {
ret = true;
}
}
}
else {
@ -252,14 +256,16 @@ template <class S> class symbol_section_accessor_template
//------------------------------------------------------------------------------
void find_hash_section()
{
hash_section = 0;
hash_section_index = 0;
Elf_Half nSecNo = elf_file.sections.size();
for ( Elf_Half i = 0; i < nSecNo && 0 == hash_section_index; ++i ) {
Elf_Half nSecNo = elf_file.sections.size();
for ( Elf_Half i = 0; i < nSecNo; ++i ) {
const section* sec = elf_file.sections[i];
if ( sec->get_link() == symbol_section->get_index() ) {
if ( sec->get_link() == symbol_section->get_index() &&
( sec->get_type() == SHT_HASH ||
sec->get_type() == SHT_GNU_HASH ||
sec->get_type() == DT_GNU_HASH ) ) {
hash_section = sec;
hash_section_index = i;
break;
}
}
}