Remove address translator from ELFIO

This commit is contained in:
Maschell 2023-01-04 14:42:11 +01:00
parent 8367e0e32c
commit be5574ee9f
5 changed files with 19 additions and 105 deletions

View File

@ -86,7 +86,6 @@ class elfio
sections_ = std::move( other.sections_ ); sections_ = std::move( other.sections_ );
segments_ = std::move( other.segments_ ); segments_ = std::move( other.segments_ );
convertor = std::move( other.convertor ); convertor = std::move( other.convertor );
addr_translator = std::move( other.addr_translator );
compression = std::move( other.compression ); compression = std::move( other.compression );
other.header = nullptr; other.header = nullptr;
@ -102,7 +101,6 @@ class elfio
sections_ = std::move( other.sections_ ); sections_ = std::move( other.sections_ );
segments_ = std::move( other.segments_ ); segments_ = std::move( other.segments_ );
convertor = std::move( other.convertor ); convertor = std::move( other.convertor );
addr_translator = std::move( other.addr_translator );
current_file_pos = other.current_file_pos; current_file_pos = other.current_file_pos;
compression = std::move( other.compression ); compression = std::move( other.compression );
@ -132,11 +130,6 @@ class elfio
create_mandatory_sections(); create_mandatory_sections();
} }
void set_address_translation( std::vector<address_translation>& addr_trans )
{
addr_translator.set_address_translation( addr_trans );
}
//------------------------------------------------------------------------------ //------------------------------------------------------------------------------
bool load( const std::string& file_name, bool is_lazy = false ) bool load( const std::string& file_name, bool is_lazy = false )
{ {
@ -163,7 +156,7 @@ class elfio
std::array<char, EI_NIDENT> e_ident = { 0 }; std::array<char, EI_NIDENT> e_ident = { 0 };
// Read ELF file signature // Read ELF file signature
stream.seekg( addr_translator[0] ); stream.seekg( 0 );
stream.read( e_ident.data(), sizeof( e_ident ) ); stream.read( e_ident.data(), sizeof( e_ident ) );
// Is it ELF file? // Is it ELF file?
@ -237,12 +230,12 @@ class elfio
if ( file_class == ELFCLASS64 ) { if ( file_class == ELFCLASS64 ) {
new_header = std::unique_ptr<elf_header>( new_header = std::unique_ptr<elf_header>(
new ( std::nothrow ) elf_header_impl<Elf64_Ehdr>( new ( std::nothrow ) elf_header_impl<Elf64_Ehdr>(
&convertor, encoding, &addr_translator ) ); &convertor, encoding ) );
} }
else if ( file_class == ELFCLASS32 ) { else if ( file_class == ELFCLASS32 ) {
new_header = std::unique_ptr<elf_header>( new_header = std::unique_ptr<elf_header>(
new ( std::nothrow ) elf_header_impl<Elf32_Ehdr>( new ( std::nothrow ) elf_header_impl<Elf32_Ehdr>(
&convertor, encoding, &addr_translator ) ); &convertor, encoding ) );
} }
else { else {
return nullptr; return nullptr;
@ -259,12 +252,12 @@ class elfio
if ( file_class == ELFCLASS64 ) { if ( file_class == ELFCLASS64 ) {
sections_.emplace_back( sections_.emplace_back(
new ( std::nothrow ) section_impl<Elf64_Shdr>( new ( std::nothrow ) section_impl<Elf64_Shdr>(
&convertor, &addr_translator, compression ) ); &convertor, compression ) );
} }
else if ( file_class == ELFCLASS32 ) { else if ( file_class == ELFCLASS32 ) {
sections_.emplace_back( sections_.emplace_back(
new ( std::nothrow ) section_impl<Elf32_Shdr>( new ( std::nothrow ) section_impl<Elf32_Shdr>(
&convertor, &addr_translator, compression ) ); &convertor, compression ) );
} }
else { else {
sections_.pop_back(); sections_.pop_back();
@ -285,12 +278,12 @@ class elfio
if ( file_class == ELFCLASS64 ) { if ( file_class == ELFCLASS64 ) {
segments_.emplace_back( segments_.emplace_back(
new ( std::nothrow ) new ( std::nothrow )
segment_impl<Elf64_Phdr>( &convertor, &addr_translator ) ); segment_impl<Elf64_Phdr>( &convertor ) );
} }
else if ( file_class == ELFCLASS32 ) { else if ( file_class == ELFCLASS32 ) {
segments_.emplace_back( segments_.emplace_back(
new ( std::nothrow ) new ( std::nothrow )
segment_impl<Elf32_Phdr>( &convertor, &addr_translator ) ); segment_impl<Elf32_Phdr>( &convertor ) );
} }
else { else {
segments_.pop_back(); segments_.pop_back();
@ -397,12 +390,12 @@ class elfio
if ( file_class == ELFCLASS64 ) { if ( file_class == ELFCLASS64 ) {
segments_.emplace_back( segments_.emplace_back(
new ( std::nothrow ) segment_impl<Elf64_Phdr>( new ( std::nothrow ) segment_impl<Elf64_Phdr>(
&convertor, &addr_translator ) ); &convertor) );
} }
else if ( file_class == ELFCLASS32 ) { else if ( file_class == ELFCLASS32 ) {
segments_.emplace_back( segments_.emplace_back(
new ( std::nothrow ) segment_impl<Elf32_Phdr>( new ( std::nothrow ) segment_impl<Elf32_Phdr>(
&convertor, &addr_translator ) ); &convertor ) );
} }
else { else {
segments_.pop_back(); segments_.pop_back();
@ -592,7 +585,6 @@ class elfio
std::vector<std::unique_ptr<section>> sections_; std::vector<std::unique_ptr<section>> sections_;
std::vector<std::unique_ptr<segment>> segments_; std::vector<std::unique_ptr<segment>> segments_;
endianess_convertor convertor; endianess_convertor convertor;
address_translator addr_translator;
std::shared_ptr<compression_interface> compression = nullptr; std::shared_ptr<compression_interface> compression = nullptr;
Elf_Xword current_file_pos = 0; Elf_Xword current_file_pos = 0;

View File

@ -75,9 +75,8 @@ template <class T> class elf_header_impl : public elf_header
public: public:
//------------------------------------------------------------------------------ //------------------------------------------------------------------------------
elf_header_impl( endianess_convertor* convertor, elf_header_impl( endianess_convertor* convertor,
unsigned char encoding, unsigned char encoding )
const address_translator* translator ) : convertor( convertor )
: convertor( convertor ), translator( translator )
{ {
header.e_ident[EI_MAG0] = ELFMAG0; header.e_ident[EI_MAG0] = ELFMAG0;
header.e_ident[EI_MAG1] = ELFMAG1; header.e_ident[EI_MAG1] = ELFMAG1;
@ -101,7 +100,7 @@ template <class T> class elf_header_impl : public elf_header
//------------------------------------------------------------------------------ //------------------------------------------------------------------------------
bool load( std::istream& stream ) override bool load( std::istream& stream ) override
{ {
stream.seekg( ( *translator )[0] ); stream.seekg(0);
stream.read( reinterpret_cast<char*>( &header ), sizeof( header ) ); stream.read( reinterpret_cast<char*>( &header ), sizeof( header ) );
return ( stream.gcount() == sizeof( header ) ); return ( stream.gcount() == sizeof( header ) );
@ -134,7 +133,6 @@ template <class T> class elf_header_impl : public elf_header
private: private:
T header = {}; T header = {};
endianess_convertor* convertor = nullptr; endianess_convertor* convertor = nullptr;
const address_translator* translator = nullptr;
}; };
} // namespace ELFIO } // namespace ELFIO

View File

@ -76,10 +76,8 @@ template <class T> class section_impl : public section
public: public:
//------------------------------------------------------------------------------ //------------------------------------------------------------------------------
section_impl( const endianess_convertor* convertor, section_impl( const endianess_convertor* convertor,
const address_translator* translator,
const std::shared_ptr<compression_interface>& compression ) const std::shared_ptr<compression_interface>& compression )
: convertor( convertor ), translator( translator ), : convertor( convertor ), compression( compression )
compression( compression )
{ {
} }
@ -141,9 +139,6 @@ template <class T> class section_impl : public section
} }
set_size( data_size ); set_size( data_size );
if ( translator->empty() ) {
set_stream_size( data_size );
}
} }
//------------------------------------------------------------------------------ //------------------------------------------------------------------------------
@ -194,9 +189,6 @@ template <class T> class section_impl : public section
} }
} }
set_size( get_size() + size ); set_size( get_size() + size );
if ( translator->empty() ) {
set_stream_size( get_stream_size() + size );
}
} }
} }
@ -235,15 +227,7 @@ template <class T> class section_impl : public section
is_lazy = is_lazy_; is_lazy = is_lazy_;
header = { 0 }; header = { 0 };
if ( translator->empty() ) { stream.seekg( header_offset);
stream.seekg( 0, std::istream::end );
set_stream_size( size_t( stream.tellg() ) );
}
else {
set_stream_size( std::numeric_limits<size_t>::max() );
}
stream.seekg( ( *translator )[header_offset] );
stream.read( reinterpret_cast<char*>( &header ), sizeof( header ) ); stream.read( reinterpret_cast<char*>( &header ), sizeof( header ) );
if ( !is_lazy || is_compressed() ) { if ( !is_lazy || is_compressed() ) {
@ -276,8 +260,7 @@ template <class T> class section_impl : public section
data.reset( new ( std::nothrow ) char[size_t( size ) + 1] ); data.reset( new ( std::nothrow ) char[size_t( size ) + 1] );
if ( ( 0 != size ) && ( nullptr != data ) ) { if ( ( 0 != size ) && ( nullptr != data ) ) {
pstream->seekg( pstream->seekg(( *convertor )( header.sh_offset ));
( *translator )[( *convertor )( header.sh_offset )] );
pstream->read( data.get(), size ); pstream->read( data.get(), size );
if ( static_cast<Elf_Xword>( pstream->gcount() ) != size ) { if ( static_cast<Elf_Xword>( pstream->gcount() ) != size ) {
data = nullptr; data = nullptr;
@ -311,7 +294,6 @@ template <class T> class section_impl : public section
mutable std::unique_ptr<char[]> data; mutable std::unique_ptr<char[]> data;
mutable Elf_Word data_size = 0; mutable Elf_Word data_size = 0;
const endianess_convertor* convertor = nullptr; const endianess_convertor* convertor = nullptr;
const address_translator* translator = nullptr;
const std::shared_ptr<compression_interface> compression = nullptr; const std::shared_ptr<compression_interface> compression = nullptr;
bool is_address_set = false; bool is_address_set = false;
size_t stream_size = 0; size_t stream_size = 0;

View File

@ -72,9 +72,8 @@ template <class T> class segment_impl : public segment
{ {
public: public:
//------------------------------------------------------------------------------ //------------------------------------------------------------------------------
segment_impl( const endianess_convertor* convertor, segment_impl( const endianess_convertor* convertor )
const address_translator* translator ) : convertor( convertor )
: convertor( convertor ), translator( translator )
{ {
} }
@ -167,15 +166,7 @@ template <class T> class segment_impl : public segment
pstream = &stream; pstream = &stream;
is_lazy = is_lazy_; is_lazy = is_lazy_;
if ( translator->empty() ) { stream.seekg( header_offset);
stream.seekg( 0, std::istream::end );
set_stream_size( size_t( stream.tellg() ) );
}
else {
set_stream_size( std::numeric_limits<size_t>::max() );
}
stream.seekg( ( *translator )[header_offset] );
stream.read( reinterpret_cast<char*>( &ph ), sizeof( ph ) ); stream.read( reinterpret_cast<char*>( &ph ), sizeof( ph ) );
is_offset_set = true; is_offset_set = true;
@ -194,7 +185,7 @@ template <class T> class segment_impl : public segment
return true; return true;
} }
pstream->seekg( ( *translator )[( *convertor )( ph.p_offset )] ); pstream->seekg(( *convertor )( ph.p_offset ));
Elf_Xword size = get_file_size(); Elf_Xword size = get_file_size();
if ( size > get_stream_size() ) { if ( size > get_stream_size() ) {
@ -229,7 +220,6 @@ template <class T> class segment_impl : public segment
mutable std::unique_ptr<char[]> data; mutable std::unique_ptr<char[]> data;
std::vector<Elf_Half> sections; std::vector<Elf_Half> sections;
const endianess_convertor* convertor = nullptr; const endianess_convertor* convertor = nullptr;
const address_translator* translator = nullptr;
size_t stream_size = 0; size_t stream_size = 0;
bool is_offset_set = false; bool is_offset_set = false;
mutable bool is_lazy = false; mutable bool is_lazy = false;

View File

@ -158,54 +158,6 @@ class endianess_convertor
bool need_conversion = false; bool need_conversion = false;
}; };
//------------------------------------------------------------------------------
struct address_translation
{
address_translation( uint64_t start, uint64_t size, uint64_t mapped_to )
: start( start ), size( size ), mapped_to( mapped_to ){};
std::streampos start;
std::streampos size;
std::streampos mapped_to;
};
//------------------------------------------------------------------------------
class address_translator
{
public:
//------------------------------------------------------------------------------
void set_address_translation( std::vector<address_translation>& addr_trans )
{
addr_translations = addr_trans;
std::sort(
addr_translations.begin(), addr_translations.end(),
[]( address_translation& a, address_translation& b ) -> bool {
return a.start < b.start;
} );
}
//------------------------------------------------------------------------------
std::streampos operator[]( std::streampos value ) const
{
if ( addr_translations.empty() ) {
return value;
}
for ( auto& t : addr_translations ) {
if ( ( t.start <= value ) && ( ( value - t.start ) < t.size ) ) {
return value - t.start + t.mapped_to;
}
}
return value;
}
bool empty() const { return addr_translations.empty(); }
private:
std::vector<address_translation> addr_translations;
};
//------------------------------------------------------------------------------ //------------------------------------------------------------------------------
inline uint32_t elf_hash( const unsigned char* name ) inline uint32_t elf_hash( const unsigned char* name )
{ {