##// END OF EJS Templates
Fixed some issues on elf parser and generic binary file widget work in progress.
Fixed some issues on elf parser and generic binary file widget work in progress.

File last commit:

r0:76019e856a27 default
r4:00ff7d3b610f default
Show More
elffile.cpp
1075 lines | 27.3 KiB | text/x-c | CppLexer
/*------------------------------------------------------------------------------
-- This file is a part of the SocExplorer Software
-- Copyright (C) 2014, Plasma Physics Laboratory - CNRS
--
-- This program is free software; you can redistribute it and/or modify
-- it under the terms of the GNU General Public License as published by
-- the Free Software Foundation; either version 2 of the License, or
-- (at your option) any later version.
--
-- This program is distributed in the hope that it will be useful,
-- but WITHOUT ANY WARRANTY; without even the implied warranty of
-- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-- GNU General Public License for more details.
--
-- You should have received a copy of the GNU General Public License
-- along with this program; if not, write to the Free Software
-- Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
-------------------------------------------------------------------------------*/
/*-- Author :
Alexis Jeandet
-- Mail :
alexis.jeandet@member.fsf.org
----------------------------------------------------------------------------*/
#include "elffile.h"
#include "srecfile.h"
#include "binaryfile.h"
#include <stdint.h>
ElfFile::ElfFile()
:abstractBinFile()
{
this->opened = false;
this->type_elf = false;
this->elfFile = (int)NULL;
this->e = NULL;
}
ElfFile::ElfFile(const QString &File)
:abstractBinFile()
{
this->opened = false;
this->type_elf = false;
this->elfFile = (int)NULL;
this->e = NULL;
this->p_fileName = File;
openFile(File);
}
ElfFile::~ElfFile()
{
closeFile();
if(scn)free(scn);
if(data)free(data);
for(int i=0;i<this->sections.count();i++)
{
delete this->sections.at(i);
}
this->sections.clear();
for(int i=0;i<this->Segments.count();i++)
{
free(this->Segments.at(i));
}
this->Segments.clear();
for(int i=0;i<symbols.count();i++)
{
delete this->symbols.at(i);
}
this->symbols.clear();
}
bool ElfFile::openFile(const QString &File)
{
this->p_fileName = File;
this->closeFile();
if(elf_version(EV_CURRENT)==EV_NONE)return 0;
#ifdef _ELF_WINDOWS_
this->elfFile = open(File.toStdString().c_str(),O_RDONLY|O_BINARY ,0);
#else
this->elfFile = open(File.toStdString().c_str(),O_RDONLY ,0);
#endif
if(this->elfFile==(int)NULL)return 0;
this->e = elf_begin(this->elfFile,ELF_C_READ,NULL);
if(this->e==NULL)return 0;
this->ek = elf_kind(this->e);
gelf_getehdr (this->e, &this->ehdr );
elf_getshdrstrndx (this->e, &this->shstrndx);
this->updateSegments();
this->updateSections();
this->updateSymbols();
this->opened = true;
return 1;
}
bool ElfFile::isopened()
{
return this->opened;
}
int ElfFile::closeFile()
{
if(this->elfFile!=(int)NULL)
{
if(this->e!=NULL)
{
elf_end(this->e);
this->e = NULL;
}
close(this->elfFile);
this->elfFile = (int)NULL;
}
this->opened = false;
return 0;
}
QList<codeFragment*> ElfFile::getFragments(QStringList fragmentList)
{
QList<codeFragment*> fragments;
if (isopened())
{
for(int i =0;i<fragmentList.count();i++)
{
fragments.append(getFragment(fragmentList.at(i)));
}
}
return fragments;
}
QList<codeFragment*> ElfFile::getFragments()
{
return getFragments(QStringList()<<".data"<<".text");
}
codeFragment *ElfFile::getFragment(const QString &name)
{
codeFragment* fragment= new codeFragment();
for(int i=0;i<getSectionCount();i++)
{
if(getSectionName(i) == name)
{
fragment->data =NULL;
fragment->size = getSectionDatasz(i);
fragment->address = getSectionPaddr(i);
getSectionData(i,&fragment->data);
}
}
return fragment;
}
QString elfresolveMachine(Elf64_Half e_machine)
{
QString machineName;
//Update from with bash script don't write it by yourself!
switch(e_machine)
{
case EM_NONE:
machineName = " No machine ";
break;
case EM_M32:
machineName = " AT&T WE 32100 ";
break;
case EM_SPARC:
machineName = " SUN SPARC ";
break;
case EM_386:
machineName = " Intel 80386 ";
break;
case EM_68K:
machineName = " Motorola m68k family ";
break;
case EM_88K:
machineName = " Motorola m88k family ";
break;
case EM_860:
machineName = " Intel 80860 ";
break;
case EM_MIPS:
machineName = " MIPS R3000 big-endian ";
break;
case EM_S370:
machineName = " IBM System/370 ";
break;
case EM_MIPS_RS3_LE:
machineName = " MIPS R3000 little-endian ";
break;
case EM_PARISC:
machineName = " HPPA ";
break;
case EM_VPP500:
machineName = " Fujitsu VPP500 ";
break;
case EM_SPARC32PLUS:
machineName = " Sun's \"v8plus\" ";
break;
case EM_960:
machineName = " Intel 80960 ";
break;
case EM_PPC:
machineName = " PowerPC ";
break;
case EM_PPC64:
machineName = " PowerPC 64-bit ";
break;
case EM_S390:
machineName = " IBM S390 ";
break;
case EM_V800:
machineName = " NEC V800 series ";
break;
case EM_FR20:
machineName = " Fujitsu FR20 ";
break;
case EM_RH32:
machineName = " TRW RH-32 ";
break;
case EM_RCE:
machineName = " Motorola RCE ";
break;
case EM_ARM:
machineName = " ARM ";
break;
case EM_FAKE_ALPHA:
machineName = " Digital Alpha ";
break;
case EM_SH:
machineName = " Hitachi SH ";
break;
case EM_SPARCV9:
machineName = " SPARC v9 64-bit ";
break;
case EM_TRICORE:
machineName = " Siemens Tricore ";
break;
case EM_ARC:
machineName = " Argonaut RISC Core ";
break;
case EM_H8_300:
machineName = " Hitachi H8/300 ";
break;
case EM_H8_300H:
machineName = " Hitachi H8/300H ";
break;
case EM_H8S:
machineName = " Hitachi H8S ";
break;
case EM_H8_500:
machineName = " Hitachi H8/500 ";
break;
case EM_IA_64:
machineName = " Intel Merced ";
break;
case EM_MIPS_X:
machineName = " Stanford MIPS-X ";
break;
case EM_COLDFIRE:
machineName = " Motorola Coldfire ";
break;
case EM_68HC12:
machineName = " Motorola M68HC12 ";
break;
case EM_MMA:
machineName = " Fujitsu MMA Multimedia Accelerator";
break;
case EM_PCP:
machineName = " Siemens PCP ";
break;
case EM_NCPU:
machineName = " Sony nCPU embeeded RISC ";
break;
case EM_NDR1:
machineName = " Denso NDR1 microprocessor ";
break;
case EM_STARCORE:
machineName = " Motorola Start*Core processor ";
break;
case EM_ME16:
machineName = " Toyota ME16 processor ";
break;
case EM_ST100:
machineName = " STMicroelectronic ST100 processor ";
break;
case EM_TINYJ:
machineName = " Advanced Logic Corp. Tinyj emb.fam";
break;
case EM_X86_64:
machineName = " AMD x86-64 architecture ";
break;
case EM_PDSP:
machineName = " Sony DSP Processor ";
break;
case EM_FX66:
machineName = " Siemens FX66 microcontroller ";
break;
case EM_ST9PLUS:
machineName = " STMicroelectronics ST9+ 8/16 mc ";
break;
case EM_ST7:
machineName = " STmicroelectronics ST7 8 bit mc ";
break;
case EM_68HC16:
machineName = " Motorola MC68HC16 microcontroller ";
break;
case EM_68HC11:
machineName = " Motorola MC68HC11 microcontroller ";
break;
case EM_68HC08:
machineName = " Motorola MC68HC08 microcontroller ";
break;
case EM_68HC05:
machineName = " Motorola MC68HC05 microcontroller ";
break;
case EM_SVX:
machineName = " Silicon Graphics SVx ";
break;
case EM_ST19:
machineName = " STMicroelectronics ST19 8 bit mc ";
break;
case EM_VAX:
machineName = " Digital VAX ";
break;
case EM_CRIS:
machineName = " Axis Communications 32-bit embedded processor ";
break;
case EM_JAVELIN:
machineName = " Infineon Technologies 32-bit embedded processor ";
break;
case EM_FIREPATH:
machineName = " Element 14 64-bit DSP Processor ";
break;
case EM_ZSP:
machineName = " LSI Logic 16-bit DSP Processor ";
break;
case EM_MMIX:
machineName = " Donald Knuth's educational 64-bit processor ";
break;
case EM_HUANY:
machineName = " Harvard University machine-independent object files ";
break;
case EM_PRISM:
machineName = " SiTera Prism ";
break;
case EM_AVR:
machineName = " Atmel AVR 8-bit microcontroller ";
break;
case EM_FR30:
machineName = " Fujitsu FR30 ";
break;
case EM_D10V:
machineName = " Mitsubishi D10V ";
break;
case EM_D30V:
machineName = " Mitsubishi D30V ";
break;
case EM_V850:
machineName = " NEC v850 ";
break;
case EM_M32R:
machineName = " Mitsubishi M32R ";
break;
case EM_MN10300:
machineName = " Matsushita MN10300 ";
break;
case EM_MN10200:
machineName = " Matsushita MN10200 ";
break;
case EM_PJ:
machineName = " picoJava ";
break;
case EM_OPENRISC:
machineName = " OpenRISC 32-bit embedded processor ";
break;
case EM_ARC_A5:
machineName = " ARC Cores Tangent-A5 ";
break;
case EM_XTENSA:
machineName = " Tensilica Xtensa Architecture ";
break;
case EM_AARCH64:
machineName = " ARM AARCH64 ";
break;
case EM_TILEPRO:
machineName = " Tilera TILEPro ";
break;
case EM_MICROBLAZE:
machineName = " Xilinx MicroBlaze ";
break;
case EM_TILEGX:
machineName = " Tilera TILE-Gx ";
break;
case EM_NUM:
machineName = "";
break;
default:
machineName ="Unknow Machine";
break;
}
return machineName;
}
QString ElfFile::getClass()
{
if(this->e!=NULL)
{
int eclass = gelf_getclass(this->e);
if(eclass==ELFCLASS32)return "ELF32";
if(eclass==ELFCLASS64)return "ELF64";
}
return "none";
}
bool ElfFile::iself()
{
return (this->getType()!="Unknow");
}
QString ElfFile::getArchitecture()
{
if(this->e!=NULL)
{
return elfresolveMachine(this->ehdr.e_machine);
}
return "";
}
QString ElfFile::getType()
{
QString kind("");
if(this->e!=NULL)
{
switch(this->ek)
{
case ELF_K_AR:
kind = "Archive";
break;
case ELF_K_ELF:
kind = "Elf";
break;
case ELF_K_COFF:
kind = "COFF";
break;
case ELF_K_NUM:
kind = "NUM";
break;
case ELF_K_NONE:
kind = "Data";
break;
default:
kind = "Unknow";
break;
}
}
return kind;
}
QString ElfFile::getEndianness()
{
if(this->e!=NULL)
{
if(this->ehdr.e_ident[EI_DATA]==ELFDATA2LSB)return "2's complement, little endian";
if(this->ehdr.e_ident[EI_DATA]==ELFDATA2MSB)return "2's complement, big endian";
}
return "none";
}
QString ElfFile::getABI()
{
if(this->e!=NULL)
{
if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_NONE)return "UNIX System V ABI";
if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_SYSV)return "Alias";
if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_HPUX)return "HP-UX";
if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_NETBSD)return "NetBSD";
if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_LINUX)return "Object uses GNU ELF extensions";
if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_SOLARIS)return "Sun Solaris";
if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_AIX)return "IBM AIX";
if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_IRIX)return "SGI Irix";
if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_FREEBSD)return "FreeBSD";
if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_TRU64)return "Compaq TRU64 UNIX";
if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_MODESTO)return " Novell Modesto";
if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_OPENBSD)return "OpenBSD";
if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_ARM_AEABI)return "ARM EABI";
if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_ARM)return "ARM";
if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_STANDALONE)return "Standalone (embedded) application";
}
return "none";
}
qint64 ElfFile::getVersion()
{
if(this->e!=NULL)
{
return this->ehdr.e_version;
}
return -1;
}
qint64 ElfFile::getEntryPointAddress()
{
if(this->e!=NULL)
{
return this->ehdr.e_entry;
}
return -1;
}
int ElfFile::getSectionCount()
{
return (int)this->SectionCount;
}
int ElfFile::getSymbolCount()
{
return (int)this->SymbolCount;
}
int ElfFile::getSegmentCount()
{
return (int)this->SegmentCount;
}
QString ElfFile::getSegmentType(int index)
{
QString type("");
if(this->e!=NULL)
{
if(index < this->Segments.count())
{
switch(this->Segments.at(index)->p_type)
{
case PT_NULL:
type = "Program header table entry unused";
break;
case PT_LOAD:
type = "Loadable program segment";
break;
case PT_DYNAMIC :
type = "Dynamic linking information";
break;
case PT_INTERP:
type ="Program interpreter";
break;
case PT_NOTE:
type = "Auxiliary information";
break;
case PT_SHLIB:
type = "Reserved";
break;
case PT_PHDR:
type = "Entry for header table itself";
break;
case PT_TLS:
type = "Thread-local storage segment";
break;
case PT_NUM:
type = "Number of defined types";
break;
case PT_LOOS:
type = "Start of OS-specific";
break;
case PT_SUNWSTACK:
type = "Stack segment";
break;
case PT_LOPROC:
type = "Start of processor-specific";
break;
case PT_HIPROC:
type = "End of processor-specific";
break;
default:
type = "Unknow Section Type";
break;
}
}
}
return type;
}
qint64 ElfFile::getSegmentOffset(int index)
{
qint64 Offset = -1;
if(this->e!=NULL)
{
if(index < this->Segments.count())
{
Offset = (qint64)this->Segments.at(index)->p_offset;
}
}
return Offset;
}
qint64 ElfFile::getSegmentVaddr(int index)
{
int64_t Vaddr = 0;
if(this->e!=NULL)
{
if(index < this->Segments.count())
{
Vaddr = (int64_t)this->Segments.at(index)->p_vaddr;
}
}
return Vaddr;
}
qint64 ElfFile::getSegmentPaddr(int index)
{
int64_t Paddr=0;
if(this->e!=NULL)
{
if(index < this->Segments.count())
{
Paddr = (int64_t)this->Segments.at(index)->p_paddr;
}
}
return Paddr;
}
qint64 ElfFile::getSectionPaddr(int index)
{
int64_t Paddr=0;
if(this->e!=NULL)
{
if(index < this->sections.count())
{
Paddr = (int64_t)this->sections.at(index)->section_header->sh_addr;
}
}
return Paddr;
}
qint64 ElfFile::getSegmentFilesz(int index)
{
int64_t FileSz=0;
if(this->e!=NULL)
{
if(index < this->Segments.count())
{
FileSz = (int64_t)this->Segments.at(index)->p_filesz;
}
}
return FileSz;
}
qint64 ElfFile::getSectionDatasz(int index)
{
int64_t DataSz=0;
if(this->e!=NULL)
{
if(index < this->sections.count())
{
if(this->sections.at(index)->section_header->sh_type==SHT_NOBITS)
{
DataSz=0;
}
else
{
DataSz = (int64_t)this->sections.at(index)->data->d_size;
}
}
}
return DataSz;
}
bool ElfFile::getSectionData(int index, char **buffer)
{
if(this->e!=NULL)
{
if(index < this->sections.count())
{
*buffer = (char *)malloc(this->sections.at(index)->data->d_size);
memcpy(*buffer,this->sections.at(index)->data->d_buf,this->sections.at(index)->data->d_size);
return true;
}
}
return false;
}
qint64 ElfFile::getSegmentMemsz(int index)
{
int64_t MemSz=0;
if(this->e!=NULL)
{
if(index < this->Segments.count())
{
MemSz = (int64_t)this->Segments.at(index)->p_memsz;
}
}
return MemSz;
}
qint64 ElfFile::getSectionMemsz(int index)
{
int64_t MemSz=0;
if(this->e!=NULL)
{
if(index < this->sections.count())
{
MemSz = (int64_t)this->sections.at(index)->section_header->sh_size;
}
}
return MemSz;
}
QString ElfFile::getSegmentFlags(int index)
{
QString flags("");
if(this->e!=NULL)
{
if(index < this->Segments.count())
{
if((this->Segments.at(index)->p_flags&PF_X) == PF_X)flags+="x";
if((this->Segments.at(index)->p_flags&PF_W) == PF_W)flags+="w";
if((this->Segments.at(index)->p_flags&PF_R) == PF_R)flags+="r";
if((this->Segments.at(index)->p_flags&PF_MASKOS) == PF_MASKOS)flags+=" OS-specific";
if((this->Segments.at(index)->p_flags&PF_MASKPROC) == PF_MASKPROC)flags+=" Processor-specific";
}
}
return flags;
}
QString ElfFile::getSectionName(int index)
{
if((index<sections.count()) && (index>=0))
{
char* nameChr = elf_strptr(this->e , this->shstrndx , this->sections.at(index)->section_header->sh_name);
return QString(nameChr);
}
return "";
}
void ElfFile::updateSections()
{
for(int i=0;i<this->sections.count();i++)
{
delete this->sections.at(i);
}
this->sections.clear();
this->scn = elf_nextscn (this->e , NULL );
this->SectionCount = 0;
while( this->scn != NULL )
{
GElf_Shdr* shdr = (GElf_Shdr*)malloc(sizeof(GElf_Shdr));
gelf_getshdr ( this->scn , shdr );
Elf_Data* data = elf_getdata(this->scn, NULL);
this->sections.append(new Elf_Section(data,shdr));
this->SectionCount+=1;
this->scn = elf_nextscn(e , scn);
}
}
void ElfFile::updateSegments()
{
elf_getphdrnum (this->e , &this->SegmentCount);
for(int i=0;i<this->Segments.count();i++)
{
free(this->Segments.at(i));
}
this->Segments.clear();
for(int i=0;i<(int)this->SegmentCount;i++)
{
GElf_Phdr* header=(GElf_Phdr*)malloc(sizeof(GElf_Phdr));
gelf_getphdr (this->e , i , header );
this->Segments.append(header);
}
}
void ElfFile::updateSymbols()
{
for(int i=0;i<symbols.count();i++)
{
delete this->symbols.at(i);
}
this->symbols.clear();
updateSections(); //Useless in most case but safer to do it
for(int i=0;i<(int)SectionCount;i++)
{
//First find Symbol table
if(this->getSectionName(i)==".symtab")
{
Elf_Section* sec = sections.at(i);
this->SymbolCount = sec->section_header->sh_size / sec->section_header->sh_entsize;
//Then list all symbols
for(int j=0;j<(int)this->SymbolCount;j++)
{
GElf_Sym* esym = (GElf_Sym*)malloc(sizeof(GElf_Sym));
gelf_getsym(sec->data, j, esym);
QString name = elf_strptr(this->e,sec->section_header->sh_link,esym->st_name);
Elf_Symbol* sym = new Elf_Symbol(name,esym);
symbols.append(sym);
}
}
}
}
QString ElfFile::getSectionType(int index)
{
QString type("");
if(this->e!=NULL)
{
if(index < this->sections.count())
{
switch(this->sections.at(index)->section_header->sh_type)
{
case SHT_NULL : type = "Section header table entry unused"; break;
case SHT_PROGBITS : type = "Program data"; break;
case SHT_SYMTAB : type = "Symbol table"; break;
case SHT_STRTAB : type = "String table"; break;
case SHT_RELA : type = "Relocation entries with addends"; break;
case SHT_HASH : type = "Symbol hash table"; break;
case SHT_DYNAMIC : type = "Dynamic linking information"; break;
case SHT_NOTE : type = "Notes"; break;
case SHT_NOBITS :type = "Program space with no data (bss)"; break;
case SHT_REL :type = "Relocation entries, no addends"; break;
case SHT_SHLIB : type = "Reserved"; break;
case SHT_DYNSYM : type = "Dynamic linker symbol table"; break;
case SHT_INIT_ARRAY : type = "Array of constructors"; break;
case SHT_FINI_ARRAY : type = "Array of destructors"; break;
case SHT_PREINIT_ARRAY : type = "Array of pre-constructors"; break;
case SHT_GROUP : type = "Section group"; break;
case SHT_SYMTAB_SHNDX : type = "Extended section indeces"; break;
case SHT_NUM : type = "Number of defined types. "; break;
case SHT_LOOS : type = "Start OS-specific. "; break;
case SHT_LOSUNW : type = "Sun-specific low bound. "; break;
case SHT_SUNW_COMDAT : type = " "; break;
case SHT_SUNW_syminfo : type = " "; break;
case SHT_GNU_verdef : type = "Version definition section. "; break;
case SHT_GNU_verneed : type = "Version needs section. "; break;
case SHT_GNU_versym : type = "Version symbol table. "; break;
case SHT_LOPROC : type = "Start of processor-specific"; break;
case SHT_HIPROC : type = "End of processor-specific"; break;
case SHT_HIUSER : type = "End of application-specific"; break;
}
}
}
return type;
}
int ElfFile::getSectionIndex(QString name)
{
if(this->e!=NULL)
{
for(int i=0;i<sections.count();i++)
{
if(getSectionName(i)==name)
return i;
}
}
return -1;
}
bool ElfFile::sectionIsNobits(int index)
{
if(this->e!=NULL)
{
if(index < this->sections.count())
{
return this->sections.at(index)->section_header->sh_type== SHT_NOBITS;
}
}
return false;
}
QString ElfFile::getSymbolName(int index)
{
if(this->e!=NULL)
{
if(index < this->symbols.count())
{
return symbols.at(index)->name;
}
}
return "";
}
QString ElfFile::getSymbolType(int index)
{
if(this->e!=NULL)
{
if(index < this->symbols.count())
{
int type = GELF_ST_TYPE(symbols.at(index)->sym->st_info);
switch(type)
{
case STT_NOTYPE:
return "No Type";
break;
case STT_OBJECT:
return "Object";
break;
case STT_FUNC:
return "Function";
break;
case STT_SECTION:
return "Section";
break;
case STT_FILE:
return "File";
break;
case STT_COMMON:
return "Common data object";
break;
case STT_TLS:
return "Thread-local data object";
break;
case STT_NUM:
return "Number of defined types";
break;
case STT_LOOS:
return "Start of OS-specific";
break;
case STT_HIOS:
return "End of OS-specific";
break;
case STT_LOPROC:
return "Start of processor-specific";
break;
case STT_HIPROC:
return "End of processor-specific";
break;
default:
return "none";
break;
}
}
}
return "none";
}
quint64 ElfFile::getSymbolSize(int index)
{
if(this->e!=NULL)
{
if((index < this->symbols.count()) && (index>=0))
{
return symbols.at(index)->sym->st_size;
}
}
return 0;
}
QString ElfFile::getSymbolSectionName(int index)
{
if(this->e!=NULL)
{
if((index < this->symbols.count()) && (index>=0))
{
return getSectionName(symbols.at(index)->sym->st_shndx-1);
}
}
return "none";
}
int ElfFile::getSymbolSectionIndex(int index)
{
if(this->e!=NULL)
{
if((index < this->symbols.count()) && (index>=0))
{
return symbols.at(index)->sym->st_shndx;
}
}
return 0;
}
quint64 ElfFile::getSymbolAddress(int index)
{
if(this->e!=NULL)
{
if((index < this->symbols.count()) && (index>=0))
{
return symbols.at(index)->sym->st_value;
}
}
return 0;
}
QString ElfFile::getSymbolLinkType(int index)
{
if(this->e!=NULL)
{
if(index < this->symbols.count())
{
int btype = GELF_ST_BIND(symbols.at(index)->sym->st_info);
switch(btype)
{
case STB_LOCAL:
return "Local";
break;
case STB_GLOBAL:
return "Global";
break;
case STB_WEAK:
return "Weak";
break;
case STB_NUM:
return "Number of defined types";
break;
case STB_LOOS:
return "Start of OS-specific";
break;
case STB_HIOS:
return "End of OS-specific";
break;
case STB_LOPROC:
return "Start of processor-specific";
break;
case STB_HIPROC:
return "End of processor-specific";
break;
default:
return "none";
break;
}
}
}
return "none";
}
bool ElfFile::isElf(const QString &File)
{
int file =0;
#ifdef _ELF_WINDOWS_
file = open(File.toStdString().c_str(),O_RDONLY|O_BINARY ,0);
#else
file = open(File.toStdString().c_str(),O_RDONLY ,0);
#endif
char Magic[4];
if(file!=-1)
{
size_t res = read(file,Magic,4);
close(file);
if((res==4) && (Magic[0]==0x7f) && (Magic[1]==0x45) && (Magic[2]==0x4c) && (Magic[3]==0x46))
{
return true;
}
}
return false;
}
bool ElfFile::toSrec(const QString &File)
{
return srecFile::toSrec(this->getFragments(),File);
}
bool ElfFile::toBinary(const QString &File)
{
return binaryFile::toBinary(getFragments(),File);
}