mirror of
https://github.com/serge1/ELFIO.git
synced 2024-12-26 18:15:40 +00:00
Implement address translation for segments
This commit is contained in:
parent
b527ea992a
commit
511086598a
@ -77,11 +77,11 @@ class elfio
|
||||
|
||||
elfio( elfio&& other ) noexcept : sections( this ), segments( this )
|
||||
{
|
||||
header = std::move(other.header);
|
||||
sections_ = std::move(other.sections_);
|
||||
segments_ = std::move(other.segments_);
|
||||
convertor = std::move(other.convertor);
|
||||
current_file_pos = std::move(other.current_file_pos);
|
||||
header = std::move( other.header );
|
||||
sections_ = std::move( other.sections_ );
|
||||
segments_ = std::move( other.segments_ );
|
||||
convertor = std::move( other.convertor );
|
||||
current_file_pos = std::move( other.current_file_pos );
|
||||
|
||||
other.header = nullptr;
|
||||
other.sections_.clear();
|
||||
@ -93,11 +93,11 @@ class elfio
|
||||
if ( this != &other ) {
|
||||
clean();
|
||||
|
||||
header = std::move(other.header);
|
||||
sections_ = std::move(other.sections_);
|
||||
segments_ = std::move(other.segments_);
|
||||
convertor = std::move(other.convertor);
|
||||
current_file_pos = std::move(other.current_file_pos);
|
||||
header = std::move( other.header );
|
||||
sections_ = std::move( other.sections_ );
|
||||
segments_ = std::move( other.segments_ );
|
||||
convertor = std::move( other.convertor );
|
||||
current_file_pos = std::move( other.current_file_pos );
|
||||
|
||||
other.header = nullptr;
|
||||
other.sections_.clear();
|
||||
@ -445,10 +445,12 @@ class elfio
|
||||
unsigned char file_class = header->get_class();
|
||||
|
||||
if ( file_class == ELFCLASS64 ) {
|
||||
new_segment = new segment_impl<Elf64_Phdr>( &convertor );
|
||||
new_segment =
|
||||
new segment_impl<Elf64_Phdr>( &convertor, &addr_translator );
|
||||
}
|
||||
else if ( file_class == ELFCLASS32 ) {
|
||||
new_segment = new segment_impl<Elf32_Phdr>( &convertor );
|
||||
new_segment =
|
||||
new segment_impl<Elf32_Phdr>( &convertor, &addr_translator );
|
||||
}
|
||||
else {
|
||||
return nullptr;
|
||||
@ -539,10 +541,12 @@ class elfio
|
||||
unsigned char file_class = header->get_class();
|
||||
|
||||
if ( file_class == ELFCLASS64 ) {
|
||||
seg = new segment_impl<Elf64_Phdr>( &convertor );
|
||||
seg = new segment_impl<Elf64_Phdr>( &convertor,
|
||||
&addr_translator );
|
||||
}
|
||||
else if ( file_class == ELFCLASS32 ) {
|
||||
seg = new segment_impl<Elf32_Phdr>( &convertor );
|
||||
seg = new segment_impl<Elf32_Phdr>( &convertor,
|
||||
&addr_translator );
|
||||
}
|
||||
else {
|
||||
return false;
|
||||
|
@ -193,8 +193,13 @@ template <class T> class section_impl : public section
|
||||
std::fill_n( reinterpret_cast<char*>( &header ), sizeof( header ),
|
||||
'\0' );
|
||||
|
||||
// stream.seekg( 0, stream.end );
|
||||
set_stream_size( 0xFFFFFFFF /*stream.tellg()*/ );
|
||||
if ( translator->empty() ) {
|
||||
stream.seekg( 0, stream.end );
|
||||
set_stream_size( stream.tellg() );
|
||||
}
|
||||
else {
|
||||
set_stream_size( 0xFFFFFFFFFFFFFFFF );
|
||||
}
|
||||
|
||||
stream.seekg( ( *translator )( header_offset ) );
|
||||
stream.read( reinterpret_cast<char*>( &header ), sizeof( header ) );
|
||||
|
@ -71,8 +71,10 @@ template <class T> class segment_impl : public segment
|
||||
{
|
||||
public:
|
||||
//------------------------------------------------------------------------------
|
||||
segment_impl( endianess_convertor* convertor )
|
||||
: stream_size( 0 ), index( 0 ), data( nullptr ), convertor( convertor )
|
||||
segment_impl( const endianess_convertor* convertor,
|
||||
const address_translator* translator )
|
||||
: convertor( convertor ), translator( translator ), stream_size( 0 ),
|
||||
index( 0 ), data( nullptr )
|
||||
{
|
||||
is_offset_set = false;
|
||||
std::fill_n( reinterpret_cast<char*>( &ph ), sizeof( ph ), '\0' );
|
||||
@ -166,16 +168,20 @@ template <class T> class segment_impl : public segment
|
||||
//------------------------------------------------------------------------------
|
||||
void load( std::istream& stream, std::streampos header_offset ) override
|
||||
{
|
||||
if ( translator->empty() ) {
|
||||
stream.seekg( 0, stream.end );
|
||||
set_stream_size( stream.tellg() );
|
||||
}
|
||||
else {
|
||||
set_stream_size( 0xFFFFFFFFFFFFFFFF );
|
||||
}
|
||||
|
||||
stream.seekg( 0, stream.end );
|
||||
set_stream_size( stream.tellg() );
|
||||
|
||||
stream.seekg( header_offset );
|
||||
stream.seekg( ( *translator )( header_offset ) );
|
||||
stream.read( reinterpret_cast<char*>( &ph ), sizeof( ph ) );
|
||||
is_offset_set = true;
|
||||
|
||||
if ( PT_NULL != get_type() && 0 != get_file_size() ) {
|
||||
stream.seekg( ( *convertor )( ph.p_offset ) );
|
||||
stream.seekg( ( *translator )( ( *convertor )( ph.p_offset ) ) );
|
||||
Elf_Xword size = get_file_size();
|
||||
|
||||
if ( size > get_stream_size() ) {
|
||||
@ -205,12 +211,13 @@ template <class T> class segment_impl : public segment
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
private:
|
||||
T ph;
|
||||
Elf_Half index;
|
||||
char* data;
|
||||
std::vector<Elf_Half> sections;
|
||||
endianess_convertor* convertor;
|
||||
bool is_offset_set;
|
||||
T ph;
|
||||
Elf_Half index;
|
||||
char* data;
|
||||
std::vector<Elf_Half> sections;
|
||||
const endianess_convertor* convertor;
|
||||
const address_translator* translator;
|
||||
bool is_offset_set;
|
||||
};
|
||||
|
||||
} // namespace ELFIO
|
||||
|
@ -199,6 +199,8 @@ class address_translator
|
||||
return value;
|
||||
}
|
||||
|
||||
bool empty() const { return translation.empty(); }
|
||||
|
||||
private:
|
||||
std::vector<address_translation> translation;
|
||||
};
|
||||
|
@ -88,9 +88,8 @@ int main( int argc, char** argv )
|
||||
|
||||
if ( elffile.load( std::string( "/proc/" ) + argv[1] + "/mem" ) ) {
|
||||
dump::header( std::cout, elffile );
|
||||
dump::section_headers( std::cout, elffile );
|
||||
dump::segment_headers( std::cout, elffile );
|
||||
dump::symbol_tables( std::cout, elffile );
|
||||
dump::segment_datas( std::cout, elffile );
|
||||
}
|
||||
else {
|
||||
std::cout << "Can't open " << std::string( "/proc/" ) + argv[1] + "/mem"
|
||||
|
Loading…
Reference in New Issue
Block a user