added Dolphin's ELF reader to the project
This commit is contained in:
		
							
								
								
									
										238
									
								
								src/core/src/elf/elf_reader.cpp
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										238
									
								
								src/core/src/elf/elf_reader.cpp
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,238 @@
 | 
			
		||||
// Copyright 2013 Dolphin Emulator Project
 | 
			
		||||
// Licensed under GPLv2
 | 
			
		||||
// Refer to the license.txt file included.
 | 
			
		||||
 | 
			
		||||
#include <string>
 | 
			
		||||
 | 
			
		||||
#include "common.h"
 | 
			
		||||
#include "mem_map.h"
 | 
			
		||||
 | 
			
		||||
#include "elf/elf_reader.h"
 | 
			
		||||
//#include "Core/Debugger/Debugger_SymbolMap.h"
 | 
			
		||||
//#include "Core/HW/Memmap.h"
 | 
			
		||||
//#include "Core/PowerPC/PPCSymbolDB.h"
 | 
			
		||||
 | 
			
		||||
//void bswap(Elf32_Word &w) {w = Common::swap32(w);}
 | 
			
		||||
//void bswap(Elf32_Half &w) {w = Common::swap16(w);}
 | 
			
		||||
 | 
			
		||||
#define bswap(w) w // Dirty bswap disable for now... 3DS is little endian, anyway
 | 
			
		||||
 | 
			
		||||
static void byteswapHeader(Elf32_Ehdr &ELF_H)
 | 
			
		||||
{
 | 
			
		||||
	bswap(ELF_H.e_type);
 | 
			
		||||
	bswap(ELF_H.e_machine);
 | 
			
		||||
	bswap(ELF_H.e_ehsize);
 | 
			
		||||
	bswap(ELF_H.e_phentsize);
 | 
			
		||||
	bswap(ELF_H.e_phnum);
 | 
			
		||||
	bswap(ELF_H.e_shentsize);
 | 
			
		||||
	bswap(ELF_H.e_shnum);
 | 
			
		||||
	bswap(ELF_H.e_shstrndx);
 | 
			
		||||
	bswap(ELF_H.e_version);
 | 
			
		||||
	bswap(ELF_H.e_entry);
 | 
			
		||||
	bswap(ELF_H.e_phoff);
 | 
			
		||||
	bswap(ELF_H.e_shoff);
 | 
			
		||||
	bswap(ELF_H.e_flags);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static void byteswapSegment(Elf32_Phdr &sec)
 | 
			
		||||
{
 | 
			
		||||
	bswap(sec.p_align);
 | 
			
		||||
	bswap(sec.p_filesz);
 | 
			
		||||
	bswap(sec.p_flags);
 | 
			
		||||
	bswap(sec.p_memsz);
 | 
			
		||||
	bswap(sec.p_offset);
 | 
			
		||||
	bswap(sec.p_paddr);
 | 
			
		||||
	bswap(sec.p_vaddr);
 | 
			
		||||
	bswap(sec.p_type);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static void byteswapSection(Elf32_Shdr &sec)
 | 
			
		||||
{
 | 
			
		||||
	bswap(sec.sh_addr);
 | 
			
		||||
	bswap(sec.sh_addralign);
 | 
			
		||||
	bswap(sec.sh_entsize);
 | 
			
		||||
	bswap(sec.sh_flags);
 | 
			
		||||
	bswap(sec.sh_info);
 | 
			
		||||
	bswap(sec.sh_link);
 | 
			
		||||
	bswap(sec.sh_name);
 | 
			
		||||
	bswap(sec.sh_offset);
 | 
			
		||||
	bswap(sec.sh_size);
 | 
			
		||||
	bswap(sec.sh_type);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
ElfReader::ElfReader(void *ptr)
 | 
			
		||||
{
 | 
			
		||||
	base = (char*)ptr;
 | 
			
		||||
	base32 = (u32 *)ptr;
 | 
			
		||||
	header = (Elf32_Ehdr*)ptr;
 | 
			
		||||
	byteswapHeader(*header);
 | 
			
		||||
 | 
			
		||||
	segments = (Elf32_Phdr *)(base + header->e_phoff);
 | 
			
		||||
	sections = (Elf32_Shdr *)(base + header->e_shoff);
 | 
			
		||||
 | 
			
		||||
	for (int i = 0; i < GetNumSegments(); i++)
 | 
			
		||||
	{
 | 
			
		||||
		byteswapSegment(segments[i]);
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	for (int i = 0; i < GetNumSections(); i++)
 | 
			
		||||
	{
 | 
			
		||||
		byteswapSection(sections[i]);
 | 
			
		||||
	}
 | 
			
		||||
	entryPoint = header->e_entry;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const char *ElfReader::GetSectionName(int section) const
 | 
			
		||||
{
 | 
			
		||||
	if (sections[section].sh_type == SHT_NULL)
 | 
			
		||||
		return nullptr;
 | 
			
		||||
 | 
			
		||||
	int nameOffset = sections[section].sh_name;
 | 
			
		||||
	char *ptr = (char*)GetSectionDataPtr(header->e_shstrndx);
 | 
			
		||||
 | 
			
		||||
	if (ptr)
 | 
			
		||||
		return ptr + nameOffset;
 | 
			
		||||
	else
 | 
			
		||||
		return nullptr;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
bool ElfReader::LoadInto(u32 vaddr)
 | 
			
		||||
{
 | 
			
		||||
	DEBUG_LOG(MASTER_LOG,"String section: %i", header->e_shstrndx);
 | 
			
		||||
 | 
			
		||||
//	sectionOffsets = new u32[GetNumSections()];
 | 
			
		||||
//	sectionAddrs = new u32[GetNumSections()];
 | 
			
		||||
 | 
			
		||||
	// Should we relocate?
 | 
			
		||||
	bRelocate = (header->e_type != ET_EXEC);
 | 
			
		||||
 | 
			
		||||
	if (bRelocate)
 | 
			
		||||
	{
 | 
			
		||||
		DEBUG_LOG(MASTER_LOG,"Relocatable module");
 | 
			
		||||
		entryPoint += vaddr;
 | 
			
		||||
	}
 | 
			
		||||
	else
 | 
			
		||||
	{
 | 
			
		||||
		DEBUG_LOG(MASTER_LOG,"Prerelocated executable");
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	INFO_LOG(MASTER_LOG,"%i segments:", header->e_phnum);
 | 
			
		||||
 | 
			
		||||
	// First pass : Get the bits into RAM
 | 
			
		||||
	u32 segmentVAddr[32];
 | 
			
		||||
 | 
			
		||||
	u32 baseAddress = bRelocate?vaddr:0;
 | 
			
		||||
	for (int i = 0; i < header->e_phnum; i++)
 | 
			
		||||
	{
 | 
			
		||||
		Elf32_Phdr *p = segments + i;
 | 
			
		||||
 | 
			
		||||
		INFO_LOG(MASTER_LOG, "Type: %i Vaddr: %08x Filesz: %i Memsz: %i ", p->p_type, p->p_vaddr, p->p_filesz, p->p_memsz);
 | 
			
		||||
 | 
			
		||||
		if (p->p_type == PT_LOAD)
 | 
			
		||||
		{
 | 
			
		||||
			segmentVAddr[i] = baseAddress + p->p_vaddr;
 | 
			
		||||
			u32 writeAddr = segmentVAddr[i];
 | 
			
		||||
 | 
			
		||||
			const u8 *src = GetSegmentPtr(i);
 | 
			
		||||
			u8 *dst = Memory::GetPointer(writeAddr);
 | 
			
		||||
			u32 srcSize = p->p_filesz;
 | 
			
		||||
			u32 dstSize = p->p_memsz;
 | 
			
		||||
			u32 *s = (u32*)src;
 | 
			
		||||
			u32 *d = (u32*)dst;
 | 
			
		||||
			for (int j = 0; j < (int)(srcSize + 3) / 4; j++)
 | 
			
		||||
			{
 | 
			
		||||
				*d++ = /*_byteswap_ulong*/(*s++);
 | 
			
		||||
			}
 | 
			
		||||
			if (srcSize < dstSize)
 | 
			
		||||
			{
 | 
			
		||||
				//memset(dst + srcSize, 0, dstSize-srcSize); //zero out bss
 | 
			
		||||
			}
 | 
			
		||||
			INFO_LOG(MASTER_LOG,"Loadable Segment Copied to %08x, size %08x", writeAddr, p->p_memsz);
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	/*
 | 
			
		||||
	LOG(MASTER_LOG,"%i sections:", header->e_shnum);
 | 
			
		||||
 | 
			
		||||
	for (int i=0; i<GetNumSections(); i++)
 | 
			
		||||
	{
 | 
			
		||||
		Elf32_Shdr *s = §ions[i];
 | 
			
		||||
		const char *name = GetSectionName(i);
 | 
			
		||||
 | 
			
		||||
		u32 writeAddr = s->sh_addr + baseAddress;
 | 
			
		||||
		sectionOffsets[i] = writeAddr - vaddr;
 | 
			
		||||
		sectionAddrs[i] = writeAddr;
 | 
			
		||||
 | 
			
		||||
		if (s->sh_flags & SHF_ALLOC)
 | 
			
		||||
		{
 | 
			
		||||
			LOG(MASTER_LOG,"Data Section found: %s     Sitting at %08x, size %08x", name, writeAddr, s->sh_size);
 | 
			
		||||
 | 
			
		||||
		}
 | 
			
		||||
		else
 | 
			
		||||
		{
 | 
			
		||||
			LOG(MASTER_LOG,"NonData Section found: %s     Ignoring (size=%08x) (flags=%08x)", name, s->sh_size, s->sh_flags);
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
*/
 | 
			
		||||
	INFO_LOG(MASTER_LOG,"Done loading.");
 | 
			
		||||
	return true;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
SectionID ElfReader::GetSectionByName(const char *name, int firstSection) const
 | 
			
		||||
{
 | 
			
		||||
	for (int i = firstSection; i < header->e_shnum; i++)
 | 
			
		||||
	{
 | 
			
		||||
		const char *secname = GetSectionName(i);
 | 
			
		||||
 | 
			
		||||
		if (secname != nullptr && strcmp(name, secname) == 0)
 | 
			
		||||
			return i;
 | 
			
		||||
	}
 | 
			
		||||
	return -1;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
/* TODO(bunnei): The following is verbatim from Dolphin - needs to be updated for this project:
 | 
			
		||||
 | 
			
		||||
bool ElfReader::LoadSymbols()
 | 
			
		||||
{
 | 
			
		||||
	bool hasSymbols = false;
 | 
			
		||||
	SectionID sec = GetSectionByName(".symtab");
 | 
			
		||||
	if (sec != -1)
 | 
			
		||||
	{
 | 
			
		||||
		int stringSection = sections[sec].sh_link;
 | 
			
		||||
		const char *stringBase = (const char *)GetSectionDataPtr(stringSection);
 | 
			
		||||
 | 
			
		||||
		//We have a symbol table!
 | 
			
		||||
		Elf32_Sym *symtab = (Elf32_Sym *)(GetSectionDataPtr(sec));
 | 
			
		||||
		int numSymbols = sections[sec].sh_size / sizeof(Elf32_Sym);
 | 
			
		||||
		for (int sym = 0; sym < numSymbols; sym++)
 | 
			
		||||
		{
 | 
			
		||||
			int size = Common::swap32(symtab[sym].st_size);
 | 
			
		||||
			if (size == 0)
 | 
			
		||||
				continue;
 | 
			
		||||
 | 
			
		||||
			// int bind = symtab[sym].st_info >> 4;
 | 
			
		||||
			int type = symtab[sym].st_info & 0xF;
 | 
			
		||||
			int sectionIndex = Common::swap16(symtab[sym].st_shndx);
 | 
			
		||||
			int value = Common::swap32(symtab[sym].st_value);
 | 
			
		||||
			const char *name = stringBase + Common::swap32(symtab[sym].st_name);
 | 
			
		||||
			if (bRelocate)
 | 
			
		||||
				value += sectionAddrs[sectionIndex];
 | 
			
		||||
 | 
			
		||||
			int symtype = Symbol::SYMBOL_DATA;
 | 
			
		||||
			switch (type)
 | 
			
		||||
			{
 | 
			
		||||
			case STT_OBJECT:
 | 
			
		||||
				symtype = Symbol::SYMBOL_DATA; break;
 | 
			
		||||
			case STT_FUNC:
 | 
			
		||||
				symtype = Symbol::SYMBOL_FUNCTION; break;
 | 
			
		||||
			default:
 | 
			
		||||
				continue;
 | 
			
		||||
			}
 | 
			
		||||
			g_symbolDB.AddKnownSymbol(value, size, name, symtype);
 | 
			
		||||
			hasSymbols = true;
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
	g_symbolDB.Index();
 | 
			
		||||
	return hasSymbols;
 | 
			
		||||
}
 | 
			
		||||
*/
 | 
			
		||||
							
								
								
									
										75
									
								
								src/core/src/elf/elf_reader.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										75
									
								
								src/core/src/elf/elf_reader.h
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,75 @@
 | 
			
		||||
// Copyright 2013 Dolphin Emulator Project
 | 
			
		||||
// Licensed under GPLv2
 | 
			
		||||
// Refer to the license.txt file included.
 | 
			
		||||
 | 
			
		||||
#pragma once
 | 
			
		||||
 | 
			
		||||
#include "elf/elf_types.h"
 | 
			
		||||
 | 
			
		||||
enum KnownElfTypes
 | 
			
		||||
{
 | 
			
		||||
	KNOWNELF_PSP = 0,
 | 
			
		||||
	KNOWNELF_DS  = 1,
 | 
			
		||||
	KNOWNELF_GBA = 2,
 | 
			
		||||
	KNOWNELF_GC  = 3,
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
typedef int SectionID;
 | 
			
		||||
 | 
			
		||||
class ElfReader
 | 
			
		||||
{
 | 
			
		||||
private:
 | 
			
		||||
	char *base;
 | 
			
		||||
	u32 *base32;
 | 
			
		||||
 | 
			
		||||
	Elf32_Ehdr *header;
 | 
			
		||||
	Elf32_Phdr *segments;
 | 
			
		||||
	Elf32_Shdr *sections;
 | 
			
		||||
 | 
			
		||||
	u32 *sectionAddrs;
 | 
			
		||||
	bool bRelocate;
 | 
			
		||||
	u32 entryPoint;
 | 
			
		||||
 | 
			
		||||
public:
 | 
			
		||||
	ElfReader(void *ptr);
 | 
			
		||||
	~ElfReader() { }
 | 
			
		||||
 | 
			
		||||
	u32 Read32(int off) const { return base32[off>>2]; }
 | 
			
		||||
 | 
			
		||||
	// Quick accessors
 | 
			
		||||
	ElfType GetType() const { return (ElfType)(header->e_type); }
 | 
			
		||||
	ElfMachine GetMachine() const { return (ElfMachine)(header->e_machine); }
 | 
			
		||||
	u32 GetEntryPoint() const { return entryPoint; }
 | 
			
		||||
	u32 GetFlags() const { return (u32)(header->e_flags); }
 | 
			
		||||
	bool LoadInto(u32 vaddr);
 | 
			
		||||
	bool LoadSymbols();
 | 
			
		||||
 | 
			
		||||
	int GetNumSegments() const { return (int)(header->e_phnum); }
 | 
			
		||||
	int GetNumSections() const { return (int)(header->e_shnum); }
 | 
			
		||||
	const u8 *GetPtr(int offset) const { return (u8*)base + offset; }
 | 
			
		||||
	const char *GetSectionName(int section) const;
 | 
			
		||||
	const u8 *GetSectionDataPtr(int section) const
 | 
			
		||||
	{
 | 
			
		||||
		if (section < 0 || section >= header->e_shnum)
 | 
			
		||||
			return nullptr;
 | 
			
		||||
		if (sections[section].sh_type != SHT_NOBITS)
 | 
			
		||||
			return GetPtr(sections[section].sh_offset);
 | 
			
		||||
		else
 | 
			
		||||
			return nullptr;
 | 
			
		||||
	}
 | 
			
		||||
	bool IsCodeSection(int section) const
 | 
			
		||||
	{
 | 
			
		||||
		return sections[section].sh_type == SHT_PROGBITS;
 | 
			
		||||
	}
 | 
			
		||||
	const u8 *GetSegmentPtr(int segment)
 | 
			
		||||
	{
 | 
			
		||||
		return GetPtr(segments[segment].p_offset);
 | 
			
		||||
	}
 | 
			
		||||
	u32 GetSectionAddr(SectionID section) const { return sectionAddrs[section]; }
 | 
			
		||||
	int GetSectionSize(SectionID section) const { return sections[section].sh_size; }
 | 
			
		||||
	SectionID GetSectionByName(const char *name, int firstSection = 0) const; //-1 for not found
 | 
			
		||||
 | 
			
		||||
	bool DidRelocate() {
 | 
			
		||||
		return bRelocate;
 | 
			
		||||
	}
 | 
			
		||||
};
 | 
			
		||||
							
								
								
									
										281
									
								
								src/core/src/elf/elf_types.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										281
									
								
								src/core/src/elf/elf_types.h
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,281 @@
 | 
			
		||||
// Copyright 2013 Dolphin Emulator Project
 | 
			
		||||
// Licensed under GPLv2
 | 
			
		||||
// Refer to the license.txt file included.
 | 
			
		||||
 | 
			
		||||
#pragma once
 | 
			
		||||
 | 
			
		||||
// ELF Header Constants
 | 
			
		||||
 | 
			
		||||
// File type
 | 
			
		||||
enum ElfType
 | 
			
		||||
{
 | 
			
		||||
	ET_NONE   = 0,
 | 
			
		||||
	ET_REL    = 1,
 | 
			
		||||
	ET_EXEC   = 2,
 | 
			
		||||
	ET_DYN    = 3,
 | 
			
		||||
	ET_CORE   = 4,
 | 
			
		||||
	ET_LOPROC = 0xFF00,
 | 
			
		||||
	ET_HIPROC = 0xFFFF,
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
// Machine/Architecture
 | 
			
		||||
enum ElfMachine
 | 
			
		||||
{
 | 
			
		||||
	EM_NONE  = 0,
 | 
			
		||||
	EM_M32   = 1,
 | 
			
		||||
	EM_SPARC = 2,
 | 
			
		||||
	EM_386   = 3,
 | 
			
		||||
	EM_68K   = 4,
 | 
			
		||||
	EM_88K   = 5,
 | 
			
		||||
	EM_860   = 7,
 | 
			
		||||
	EM_MIPS  = 8
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
// File version
 | 
			
		||||
#define EV_NONE    0
 | 
			
		||||
#define EV_CURRENT 1
 | 
			
		||||
 | 
			
		||||
// Identification index
 | 
			
		||||
#define EI_MAG0    0
 | 
			
		||||
#define EI_MAG1    1
 | 
			
		||||
#define EI_MAG2    2
 | 
			
		||||
#define EI_MAG3    3
 | 
			
		||||
#define EI_CLASS   4
 | 
			
		||||
#define EI_DATA    5
 | 
			
		||||
#define EI_VERSION 6
 | 
			
		||||
#define EI_PAD     7
 | 
			
		||||
#define EI_NIDENT 16
 | 
			
		||||
 | 
			
		||||
// Magic number
 | 
			
		||||
#define ELFMAG0 0x7F
 | 
			
		||||
#define ELFMAG1  'E'
 | 
			
		||||
#define ELFMAG2  'L'
 | 
			
		||||
#define ELFMAG3  'F'
 | 
			
		||||
 | 
			
		||||
// File class
 | 
			
		||||
#define ELFCLASSNONE 0
 | 
			
		||||
#define ELFCLASS32   1
 | 
			
		||||
#define ELFCLASS64   2
 | 
			
		||||
 | 
			
		||||
// Encoding
 | 
			
		||||
#define ELFDATANONE 0
 | 
			
		||||
#define ELFDATA2LSB 1
 | 
			
		||||
#define ELFDATA2MSB 2
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
// Sections constants
 | 
			
		||||
 | 
			
		||||
// Section indexes
 | 
			
		||||
#define SHN_UNDEF          0
 | 
			
		||||
#define SHN_LORESERVE 0xFF00
 | 
			
		||||
#define SHN_LOPROC    0xFF00
 | 
			
		||||
#define SHN_HIPROC    0xFF1F
 | 
			
		||||
#define SHN_ABS       0xFFF1
 | 
			
		||||
#define SHN_COMMON    0xFFF2
 | 
			
		||||
#define SHN_HIRESERVE 0xFFFF
 | 
			
		||||
 | 
			
		||||
// Section types
 | 
			
		||||
#define SHT_NULL            0
 | 
			
		||||
#define SHT_PROGBITS        1
 | 
			
		||||
#define SHT_SYMTAB          2
 | 
			
		||||
#define SHT_STRTAB          3
 | 
			
		||||
#define SHT_RELA            4
 | 
			
		||||
#define SHT_HASH            5
 | 
			
		||||
#define SHT_DYNAMIC         6
 | 
			
		||||
#define SHT_NOTE            7
 | 
			
		||||
#define SHT_NOBITS          8
 | 
			
		||||
#define SHT_REL             9
 | 
			
		||||
#define SHT_SHLIB          10
 | 
			
		||||
#define SHT_DYNSYM         11
 | 
			
		||||
#define SHT_LOPROC 0x70000000
 | 
			
		||||
#define SHT_HIPROC 0x7FFFFFFF
 | 
			
		||||
#define SHT_LOUSER 0x80000000
 | 
			
		||||
#define SHT_HIUSER 0xFFFFFFFF
 | 
			
		||||
 | 
			
		||||
// Custom section types
 | 
			
		||||
#define SHT_PSPREL 0x700000a0
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
// Section flags
 | 
			
		||||
enum ElfSectionFlags
 | 
			
		||||
{
 | 
			
		||||
	SHF_WRITE     = 0x1,
 | 
			
		||||
	SHF_ALLOC     = 0x2,
 | 
			
		||||
	SHF_EXECINSTR = 0x4,
 | 
			
		||||
	SHF_MASKPROC  = 0xF0000000,
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
// Symbol binding
 | 
			
		||||
#define STB_LOCAL   0
 | 
			
		||||
#define STB_GLOBAL  1
 | 
			
		||||
#define STB_WEAK    2
 | 
			
		||||
#define STB_LOPROC 13
 | 
			
		||||
#define STB_HIPROC 15
 | 
			
		||||
 | 
			
		||||
// Symbol types
 | 
			
		||||
#define STT_NOTYPE   0
 | 
			
		||||
#define STT_OBJECT   1
 | 
			
		||||
#define STT_FUNC     2
 | 
			
		||||
#define STT_SECTION  3
 | 
			
		||||
#define STT_FILE     4
 | 
			
		||||
#define STT_LOPROC  13
 | 
			
		||||
#define STT_HIPROC  15
 | 
			
		||||
 | 
			
		||||
// Undefined name
 | 
			
		||||
#define STN_UNDEF 0
 | 
			
		||||
 | 
			
		||||
// Relocation types
 | 
			
		||||
#define R_386_NONE      0
 | 
			
		||||
#define R_386_32        1
 | 
			
		||||
#define R_386_PC32      2
 | 
			
		||||
#define R_386_GOT32     3
 | 
			
		||||
#define R_386_PLT32     4
 | 
			
		||||
#define R_386_COPY      5
 | 
			
		||||
#define R_386_GLOB_DAT  6
 | 
			
		||||
#define R_386_JMP_SLOT  7
 | 
			
		||||
#define R_386_RELATIVE  8
 | 
			
		||||
#define R_386_GOTOFF    9
 | 
			
		||||
#define R_386_GOTPC    10
 | 
			
		||||
 | 
			
		||||
// Segment types
 | 
			
		||||
#define PT_NULL             0
 | 
			
		||||
#define PT_LOAD             1
 | 
			
		||||
#define PT_DYNAMIC          2
 | 
			
		||||
#define PT_INTERP           3
 | 
			
		||||
#define PT_NOTE             4
 | 
			
		||||
#define PT_SHLIB            5
 | 
			
		||||
#define PT_PHDR             6
 | 
			
		||||
#define PT_LOPROC  0x70000000
 | 
			
		||||
#define PT_HIPROC  0x7FFFFFFF
 | 
			
		||||
 | 
			
		||||
// Segment flags
 | 
			
		||||
#define PF_X 1
 | 
			
		||||
#define PF_W 2
 | 
			
		||||
#define PF_R 4
 | 
			
		||||
 | 
			
		||||
// Dynamic Array Tags
 | 
			
		||||
#define DT_NULL              0
 | 
			
		||||
#define DT_NEEDED            1
 | 
			
		||||
#define DT_PLTRELSZ          2
 | 
			
		||||
#define DT_PLTGOT            3
 | 
			
		||||
#define DT_HASH              4
 | 
			
		||||
#define DT_STRTAB            5
 | 
			
		||||
#define DT_SYMTAB            6
 | 
			
		||||
#define DT_RELA              7
 | 
			
		||||
#define DT_RELASZ            8
 | 
			
		||||
#define DT_RELAENT           9
 | 
			
		||||
#define DT_STRSZ            10
 | 
			
		||||
#define DT_SYMENT           11
 | 
			
		||||
#define DT_INIT             12
 | 
			
		||||
#define DT_FINI             13
 | 
			
		||||
#define DT_SONAME           14
 | 
			
		||||
#define DT_RPATH            15
 | 
			
		||||
#define DT_SYMBOLIC         16
 | 
			
		||||
#define DT_REL              17
 | 
			
		||||
#define DT_RELSZ            18
 | 
			
		||||
#define DT_RELENT           19
 | 
			
		||||
#define DT_PLTREL           20
 | 
			
		||||
#define DT_DEBUG            21
 | 
			
		||||
#define DT_TEXTREL          22
 | 
			
		||||
#define DT_JMPREL           23
 | 
			
		||||
#define DT_LOPROC   0x70000000
 | 
			
		||||
#define DT_HIPROC   0x7FFFFFFF
 | 
			
		||||
 | 
			
		||||
typedef unsigned int  Elf32_Addr;
 | 
			
		||||
typedef unsigned short Elf32_Half;
 | 
			
		||||
typedef unsigned int  Elf32_Off;
 | 
			
		||||
typedef signed   int  Elf32_Sword;
 | 
			
		||||
typedef unsigned int  Elf32_Word;
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
// ELF file header
 | 
			
		||||
struct Elf32_Ehdr
 | 
			
		||||
{
 | 
			
		||||
	unsigned char e_ident[EI_NIDENT];
 | 
			
		||||
	Elf32_Half    e_type;
 | 
			
		||||
	Elf32_Half    e_machine;
 | 
			
		||||
	Elf32_Word    e_version;
 | 
			
		||||
	Elf32_Addr    e_entry;
 | 
			
		||||
	Elf32_Off     e_phoff;
 | 
			
		||||
	Elf32_Off     e_shoff;
 | 
			
		||||
	Elf32_Word    e_flags;
 | 
			
		||||
	Elf32_Half    e_ehsize;
 | 
			
		||||
	Elf32_Half    e_phentsize;
 | 
			
		||||
	Elf32_Half    e_phnum;
 | 
			
		||||
	Elf32_Half    e_shentsize;
 | 
			
		||||
	Elf32_Half    e_shnum;
 | 
			
		||||
	Elf32_Half    e_shstrndx;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
// Section header
 | 
			
		||||
struct Elf32_Shdr
 | 
			
		||||
{
 | 
			
		||||
	Elf32_Word sh_name;
 | 
			
		||||
	Elf32_Word sh_type;
 | 
			
		||||
	Elf32_Word sh_flags;
 | 
			
		||||
	Elf32_Addr sh_addr;
 | 
			
		||||
	Elf32_Off  sh_offset;
 | 
			
		||||
	Elf32_Word sh_size;
 | 
			
		||||
	Elf32_Word sh_link;
 | 
			
		||||
	Elf32_Word sh_info;
 | 
			
		||||
	Elf32_Word sh_addralign;
 | 
			
		||||
	Elf32_Word sh_entsize;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
// Segment header
 | 
			
		||||
struct Elf32_Phdr
 | 
			
		||||
{
 | 
			
		||||
	Elf32_Word p_type;
 | 
			
		||||
	Elf32_Off  p_offset;
 | 
			
		||||
	Elf32_Addr p_vaddr;
 | 
			
		||||
	Elf32_Addr p_paddr;
 | 
			
		||||
	Elf32_Word p_filesz;
 | 
			
		||||
	Elf32_Word p_memsz;
 | 
			
		||||
	Elf32_Word p_flags;
 | 
			
		||||
	Elf32_Word p_align;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
// Symbol table entry
 | 
			
		||||
struct Elf32_Sym
 | 
			
		||||
{
 | 
			
		||||
	Elf32_Word    st_name;
 | 
			
		||||
	Elf32_Addr    st_value;
 | 
			
		||||
	Elf32_Word    st_size;
 | 
			
		||||
	unsigned char st_info;
 | 
			
		||||
	unsigned char st_other;
 | 
			
		||||
	Elf32_Half    st_shndx;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
#define ELF32_ST_BIND(i)   ((i)>>4)
 | 
			
		||||
#define ELF32_ST_TYPE(i)   ((i)&0xf)
 | 
			
		||||
#define ELF32_ST_INFO(b,t) (((b)<<4)+((t)&0xf))
 | 
			
		||||
 | 
			
		||||
// Relocation entries
 | 
			
		||||
struct Elf32_Rel
 | 
			
		||||
{
 | 
			
		||||
	Elf32_Addr r_offset;
 | 
			
		||||
	Elf32_Word r_info;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
struct Elf32_Rela
 | 
			
		||||
{
 | 
			
		||||
	Elf32_Addr  r_offset;
 | 
			
		||||
	Elf32_Word  r_info;
 | 
			
		||||
	Elf32_Sword r_addend;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
#define ELF32_R_SYM(i) ((i)>>8)
 | 
			
		||||
#define ELF32_R_TYPE(i) ((unsigned char)(i))
 | 
			
		||||
#define ELF32_R_INFO(s,t) (((s)<<8 )+(unsigned char)(t))
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
struct Elf32_Dyn
 | 
			
		||||
{
 | 
			
		||||
	Elf32_Sword d_tag;
 | 
			
		||||
	union
 | 
			
		||||
	{
 | 
			
		||||
		Elf32_Word d_val;
 | 
			
		||||
		Elf32_Addr d_ptr;
 | 
			
		||||
	} d_un;
 | 
			
		||||
};
 | 
			
		||||
		Reference in New Issue
	
	Block a user