rockbox/utils/zenutils/libraries/pelib-0.9/pelib/PeHeader.h
Maurus Cuelenaere 6c74a7db80 Fix ZenUtils compilation
git-svn-id: svn://svn.rockbox.org/rockbox/trunk@21242 a1c6a512-1295-4272-9138-f99709370657
2009-06-10 15:14:32 +00:00

2686 lines
84 KiB
C++

/*
* PeHeader.h - Part of the PeLib library.
*
* Copyright (c) 2004 - 2005 Sebastian Porst (webmaster@the-interweb.com)
* All rights reserved.
*
* This software is licensed under the zlib/libpng License.
* For more details see http://www.opensource.org/licenses/zlib-license.php
* or the license information file (license.htm) in the root directory
* of PeLib.
*/
#ifndef PEHEADER_H
#define PEHEADER_H
#include "PeLibAux.h"
#include <string.h>
namespace PeLib
{
class PeHeader
{
// protected:
// virtual void readBaseOfData(InputBuffer& ibBuffer) = 0;
// virtual void rebuildBaseOfData(OutputBuffer& obBuffer) const = 0;
public:
virtual ~PeHeader(){};
};
/// Class that handles the PE header of files.
/**
* This class can read and modify PE headers. It provides set- and get functions to access
* all individual members of a PE header. Furthermore it's possible to validate and rebuild
* PE headers. A PE header includes the IMAGE_Nt_HEADERS and the section definitions of a PE file.
* \todo getIdReservedRva
**/
template<int x>
class PeHeaderT : public PeHeader
{
private:
void readBaseOfData(InputBuffer& ibBuffer, PELIB_IMAGE_NT_HEADERS<x>& header) const;
void rebuildBaseOfData(OutputBuffer& obBuffer) const;
protected:
std::vector<PELIB_IMAGE_SECTION_HEADER> m_vIsh; ///< Stores section header information.
PELIB_IMAGE_NT_HEADERS<x> m_inthHeader; ///< Stores Nt header information.
dword m_uiOffset; ///< Equivalent to the value returned by #PeLib::MzHeader::getAddressOfPeFile
public:
typedef typename FieldSizes<x>::VAR4_8 VAR4_8;
PeHeaderT() : m_uiOffset(0)
{
}
/// Add a section to the header.
int addSection(const std::string& strName, dword dwSize); // EXPORT
unsigned int calcSizeOfImage() const; // EXPORT
/// Returns the unused space after the header.
unsigned int calcSpaceAfterHeader() const; // EXPORT
/// Returns the address of the physically first section (not the first defined section).
unsigned int calcStartOfCode() const; // EXPORT
/// Calculates the offset for a new section of size uiSize.
unsigned int calcOffset() const; // EXPORT
/// Calculates the Rva for a new section of size uiSize.
unsigned int calcRva() const; // EXPORT
/// Returns the number of sections in the current file.
word calcNumberOfSections() const; // EXPORT
void enlargeLastSection(unsigned int uiSize); // EXPORT
/// Returns the section Id of the section that contains the offset.
word getSectionWithOffset(VAR4_8 dwOffset) const; // EXPORT
/// Returns the number of the section which the given relative address points to.
word getSectionWithRva(VAR4_8 rva) const; // EXPORT
bool isValid() const; // EXPORT
bool isValid(unsigned int foo) const; // EXPORT
/// Corrects the current PE header.
void makeValid(dword dwOffset); // EXPORT
/// Converts a file offset to a relative virtual offset.
unsigned int offsetToRva(VAR4_8 dwOffset) const; // EXPORT
/// Converts a file offset to a virtual address.
unsigned int offsetToVa(VAR4_8 dwOffset) const; // EXPORT
/// Reads the PE header of a file.
int read(std::string strFilename, unsigned int uiOffset); // EXPORT
int read(const unsigned char* pcBuffer, unsigned int uiSize, unsigned int uiOffset); // EXPORT
void readHeader(InputBuffer& ibBuffer, PELIB_IMAGE_NT_HEADERS<x>& header) const;
void readDataDirectories(InputBuffer& ibBuffer, PELIB_IMAGE_NT_HEADERS<x>& header) const;
std::vector<PELIB_IMAGE_SECTION_HEADER> readSections(InputBuffer& ibBuffer, PELIB_IMAGE_NT_HEADERS<x>& header) const;
/// Rebuilds the current PE header.
void rebuild(std::vector<byte>& vBuffer) const; // EXPORT
/// Converts a relative virtual address to a file offset.
VAR4_8 rvaToOffset(VAR4_8 dwRva) const; // EXPORT
/// Converts a relative virtual address to a virtual address.
VAR4_8 rvaToVa(VAR4_8 dwRva) const; // EXPORT
/// Calculates the size for the current PE header including all section definitions.
unsigned int size() const;
VAR4_8 vaToRva(VAR4_8 dwRva) const; // EXPORT
VAR4_8 vaToOffset(VAR4_8 dwRva) const; // EXPORT
/// Save the PE header to a file.
int write(std::string strFilename, unsigned int uiOffset) const; // EXPORT
/// Writes sections to a file.
int writeSections(const std::string& strFilename) const; // EXPORT
/// Overwrites a section with new data.
int writeSectionData(const std::string& strFilename, word wSecnr, const std::vector<byte>& vBuffer) const; // EXPORT
// header getters
/// Returns the Signature value of the header.
dword getNtSignature() const; // EXPORT
/// Returns the Machine value of the header.
word getMachine() const; // EXPORT
/// Returns the Sections value of the header.
word getNumberOfSections() const; // EXPORT
/// Returns the TimeDateStamp value of the header.
dword getTimeDateStamp() const; // EXPORT
/// Returns the PointerToSymbolTable value of the header.
dword getPointerToSymbolTable() const; // EXPORT
/// Returns the NumberOfSymbols value of the header.
dword getNumberOfSymbols() const; // EXPORT
/// Returns the SizeOfOptionalHeader value of the header.
word getSizeOfOptionalHeader() const; // EXPORT
/// Returns the Characteristics value of the header.
word getCharacteristics() const; // EXPORT
/// Returns the Magic value of the header.
word getMagic() const; // EXPORT
/// Returns the MajorLinkerVersion value of the header.
byte getMajorLinkerVersion() const; // EXPORT
/// Returns the MinorLinkerVersion value of the header.
byte getMinorLinkerVersion() const; // EXPORT
/// Returns the SizeOfCode value of the header.
dword getSizeOfCode() const; // EXPORT
/// Returns the SizeOfInitializedData value of the header.
dword getSizeOfInitializedData() const; // EXPORT
/// Returns the SizeOfUninitializedData value of the header.
dword getSizeOfUninitializedData() const; // EXPORT
/// Returns the AddressOfEntryPoint value of the header.
dword getAddressOfEntryPoint() const; // EXPORT
/// Returns the BaseOfCode value of the header.
dword getBaseOfCode() const; // EXPORT
/// Returns the ImageBase value of the header.
VAR4_8 getImageBase() const; // EXPORT
/// Returns the SectionAlignment value of the header.
dword getSectionAlignment() const; // EXPORT
/// Returns the FileAlignment value of the header.
dword getFileAlignment() const; // EXPORT
/// Returns the MajorOperatingSystemVersion value of the header.
word getMajorOperatingSystemVersion() const; // EXPORT
/// Returns the MinorOperatingSystemVersion value of the header.
word getMinorOperatingSystemVersion() const; // EXPORT
/// Returns the MajorImageVersion value of the header.
word getMajorImageVersion() const; // EXPORT
/// Returns the MinorImageVersion value of the header.
word getMinorImageVersion() const; // EXPORT
/// Returns the MajorSubsystemVersion value of the header.
word getMajorSubsystemVersion() const; // EXPORT
/// Returns the MinorSubsystemVersion value of the header.
word getMinorSubsystemVersion() const; // EXPORT
/// Returns the Reserved1 value of the header.
dword getWin32VersionValue() const; // EXPORT
/// Returns the SizeOfImage value of the header.
dword getSizeOfImage() const; // EXPORT
/// Returns the SizeOfHeaders value of the header.
dword getSizeOfHeaders() const; // EXPORT
/// Returns the CheckSum value of the header.
dword getCheckSum() const; // EXPORT
/// Returns the Subsystem value of the header.
word getSubsystem() const; // EXPORT
/// Returns the DllCharacteristics value of the header.
word getDllCharacteristics() const; // EXPORT
/// Returns the SizeOfStackReserve value of the header.
VAR4_8 getSizeOfStackReserve() const; // EXPORT
/// Returns the SizeOfStackCommit value of the header.
VAR4_8 getSizeOfStackCommit() const; // EXPORT
/// Returns the SizeOfHeapReserve value of the header.
VAR4_8 getSizeOfHeapReserve() const; // EXPORT
/// Returns the SizeOfHeapCommit value of the header.
VAR4_8 getSizeOfHeapCommit() const; // EXPORT
/// Returns the LoaderFlags value of the header.
dword getLoaderFlags() const; // EXPORT
/// Returns the NumberOfRvaAndSizes value of the header.
dword getNumberOfRvaAndSizes() const; // EXPORT
dword calcNumberOfRvaAndSizes() const; // EXPORT
void addDataDirectory(); // EXPORT
void removeDataDirectory(dword index); // EXPORT
// image directory getters
/// Returns the relative virtual address of the image directory Export.
dword getIddExportRva() const; // EXPORT
/// Returns the size of the image directory Export.
dword getIddExportSize() const; // EXPORT
/// Returns the relative virtual address of the image directory Import.
dword getIddImportRva() const; // EXPORT
/// Returns the size of the image directory Import.
dword getIddImportSize() const; // EXPORT
/// Returns the relative virtual address of the image directory Resource.
dword getIddResourceRva() const; // EXPORT
/// Returns the size of the image directory Resource.
dword getIddResourceSize() const; // EXPORT
/// Returns the relative virtual address of the image directory Exception.
dword getIddExceptionRva() const; // EXPORT
/// Returns the size of the image directory Exception.
dword getIddExceptionSize() const; // EXPORT
/// Returns the relative virtual address of the image directory Security.
dword getIddSecurityRva() const; // EXPORT
/// Returns the size of the image directory Security.
dword getIddSecuritySize() const; // EXPORT
/// Returns the relative virtual address of the image directory Base Reloc.
dword getIddBaseRelocRva() const; // EXPORT
/// Returns the size of the image directory Base Reloc.
dword getIddBaseRelocSize() const; // EXPORT
/// Returns the relative virtual address of the image directory Debug.
dword getIddDebugRva() const; // EXPORT
/// Returns the size of the image directory Debug.
dword getIddDebugSize() const; // EXPORT
/// Returns the relative virtual address of the image directory Architecture.
dword getIddArchitectureRva() const; // EXPORT
/// Returns the size of the image directory Architecture.
dword getIddArchitectureSize() const; // EXPORT
/// Returns the relative virtual address of the image directory GlobalPtr.
dword getIddGlobalPtrRva() const; // EXPORT
/// Returns the size of the image directory GlobalPtr.
dword getIddGlobalPtrSize() const; // EXPORT
/// Returns the relative virtual address of the image directory Tls.
dword getIddTlsRva() const; // EXPORT
/// Returns the size of the image directory Tls.
dword getIddTlsSize() const; // EXPORT
/// Returns the relative virtual address of the image directory LoadConfig.
dword getIddLoadConfigRva() const; // EXPORT
/// Returns the size of the image directory LoadConfig.
dword getIddLoadConfigSize() const; // EXPORT
/// Returns the relative virtual address of the image directory BoundImport.
dword getIddBoundImportRva() const; // EXPORT
/// Returns the size of the image directory BoundImport.
dword getIddBoundImportSize() const; // EXPORT
/// Returns the relative virtual address of the image directory Iat.
dword getIddIatRva() const; // EXPORT
/// Returns the size of the image directory Iat.
dword getIddIatSize() const; // EXPORT
/// Returns the relative virtual address of the image directory DelayImport.
dword getIddDelayImportRva() const; // EXPORT
/// Returns the size of the image directory DelayImport.
dword getIddDelayImportSize() const; // EXPORT
/// Returns the relative virtual address of the image directory COM Descriptor.
dword getIddComHeaderRva() const; // EXPORT
/// Returns the size of the image directory COM Descriptor.
dword getIddComHeaderSize() const; // EXPORT
/// Returns the relative virtual address of an image directory.
dword getImageDataDirectoryRva(dword dwDirectory) const; // EXPORT
/// Returns the size of an image directory.
dword getImageDataDirectorySize(dword dwDirectory) const; // EXPORT
void setImageDataDirectoryRva(dword dwDirectory, dword value); // EXPORT
void setImageDataDirectorySize(dword dwDirectory, dword value); // EXPORT
// section getters
/// Returns the name of a section.
std::string getSectionName(word uiSectionnr) const; // EXPORT
/// Returns the virtual size of a section.
dword getVirtualSize(word uiSectionnr) const; // EXPORT
/// Returns the virtual address of a section.
dword getVirtualAddress(word uiSectionnr) const; // EXPORT
/// Returns the size of a section's raw data.
dword getSizeOfRawData(word uiSectionnr) const; // EXPORT
/// Returns file offset of the data of a section.
dword getPointerToRawData(word uiSectionnr) const; // EXPORT
/// Returns the rva of the relocations of a section.
dword getPointerToRelocations(word uiSectionnr) const; // EXPORT
/// Returns the rva of the line numbers of a section.
dword getPointerToLinenumbers(word uiSectionnr) const; // EXPORT
/// Returns the number of relocations of a section.
dword getNumberOfRelocations(word uiSectionnr) const; // EXPORT
/// Returns the number of line numbers of a section.
dword getNumberOfLinenumbers(word uiSectionnr) const; // EXPORT
/// Returns the characteristics of a section.
dword getCharacteristics(word uiSectionnr) const; // EXPORT _section
// header setters
/// Sets the Signature value of the header.
void setNtSignature(dword value); // EXPORT
/// Sets the Machine value of the header.
void setMachine(word value); // EXPORT
/// Sets the Sections value of the header.
void setNumberOfSections(word value); // EXPORT
/// Sets the TimeDateStamp value of the header.
void setTimeDateStamp(dword value); // EXPORT
/// Sets the PointerToSymbolTable value of the header.
void setPointerToSymbolTable(dword value); // EXPORT
/// Sets the NumberOfSymbols value of the header.
void setNumberOfSymbols(dword value); // EXPORT
/// Sets the SizeOfOptionalHeader value of the header.
void setSizeOfOptionalHeader(word value); // EXPORT
/// Sets the Characteristics value of the header.
void setCharacteristics(word value); // EXPORT _section
/// Sets the Magic value of the header.
void setMagic(word value); // EXPORT
/// Sets the MajorLinkerVersion value of the header.
void setMajorLinkerVersion(byte value); // EXPORT
/// Sets the MinorLinkerVersion value of the header.
void setMinorLinkerVersion(byte value); // EXPORT
/// Sets the SizeOfCode value of the header.
void setSizeOfCode(dword value); // EXPORT
/// Sets the SizeOfInitializedData value of the header.
void setSizeOfInitializedData(dword value); // EXPORT
/// Sets the SizeOfUninitializedData value of the header.
void setSizeOfUninitializedData(dword value); // EXPORT
/// Sets the AddressOfEntryPoint value of the header.
void setAddressOfEntryPoint(dword value); // EXPORT
/// Sets the BaseOfCode value of the header.
void setBaseOfCode(dword value); // EXPORT
/// Sets the ImageBase value of the header.
void setImageBase(VAR4_8 value); // EXPORT
/// Sets the SectionAlignment value of the header.
void setSectionAlignment(dword value); // EXPORT
/// Sets the FileAlignment value of the header.
void setFileAlignment(dword value); // EXPORT
/// Sets the MajorOperatingSystemVersion value of the header.
void setMajorOperatingSystemVersion(word value); // EXPORT
/// Sets the MinorOperatingSystemVersion value of the header.
void setMinorOperatingSystemVersion(word value); // EXPORT
/// Sets the MajorImageVersion value of the header.
void setMajorImageVersion(word value); // EXPORT
/// Sets the MinorImageVersion value of the header.
void setMinorImageVersion(word value); // EXPORT
/// Sets the MajorSubsystemVersion value of the header.
void setMajorSubsystemVersion(word value); // EXPORT
/// Sets the MinorSubsystemVersion value of the header.
void setMinorSubsystemVersion(word value); // EXPORT
/// Sets the Reserved1 value of the header.
void setWin32VersionValue(dword value); // EXPORT
/// Sets the SizeOfImage value of the header.
void setSizeOfImage(dword value); // EXPORT
/// Sets the SizeOfHeaders value of the header.
void setSizeOfHeaders(dword value); // EXPORT
/// Sets the CheckSum value of the header.
void setCheckSum(dword value); // EXPORT
/// Sets the Subsystem value of the header.
void setSubsystem(word value); // EXPORT
/// Sets the DllCharacteristics value of the header.
void setDllCharacteristics(word value); // EXPORT
/// Sets the SizeOfStackReserve value of the header.
void setSizeOfStackReserve(VAR4_8 value); // EXPORT
/// Sets the SizeOfStackCommit value of the header.
void setSizeOfStackCommit(VAR4_8 value); // EXPORT
/// Sets the SizeOfHeapReserve value of the header.
void setSizeOfHeapReserve(VAR4_8 value); // EXPORT
/// Sets the SizeOfHeapCommit value of the header.
void setSizeOfHeapCommit(VAR4_8 value); // EXPORT
/// Sets the LoaderFlags value of the header.
void setLoaderFlags(dword value); // EXPORT
/// Sets the NumberOfRvaAndSizes value of the header.
void setNumberOfRvaAndSizes(dword value); // EXPORT
// image directory getters
void setIddDebugRva(dword dwValue); // EXPORT
void setIddDebugSize(dword dwValue); // EXPORT
void setIddDelayImportRva(dword dwValue); // EXPORT
void setIddDelayImportSize(dword dwValue); // EXPORT
void setIddExceptionRva(dword dwValue); // EXPORT
void setIddExceptionSize(dword dwValue); // EXPORT
void setIddGlobalPtrRva(dword dwValue); // EXPORT
void setIddGlobalPtrSize(dword dwValue); // EXPORT
void setIddIatRva(dword dwValue); // EXPORT
void setIddIatSize(dword dwValue); // EXPORT
void setIddLoadConfigRva(dword dwValue); // EXPORT
void setIddLoadConfigSize(dword dwValue); // EXPORT
void setIddResourceRva(dword dwValue); // EXPORT
void setIddResourceSize(dword dwValue); // EXPORT
void setIddSecurityRva(dword dwValue); // EXPORT
void setIddSecuritySize(dword dwValue); // EXPORT
void setIddTlsRva(dword dwValue); // EXPORT
void setIddTlsSize(dword dwValue); // EXPORT
void setIddImportRva(dword dwValue); // EXPORT
void setIddImportSize(dword dwValue); // EXPORT
void setIddExportRva(dword dwValue); // EXPORT
void setIddExportSize(dword dwValue); // EXPORT
void setIddBaseRelocRva(dword value); // EXPORT
void setIddBaseRelocSize(dword value); // EXPORT
void setIddArchitectureRva(dword value); // EXPORT
void setIddArchitectureSize(dword value); // EXPORT
void setIddComHeaderRva(dword value); // EXPORT
void setIddComHeaderSize(dword value); // EXPORT
/// Set the name of a section.
void setSectionName(word uiSectionnr, std::string strName); // EXPORT
/// Set the virtual size of a section.
void setVirtualSize(word uiSectionnr, dword dwValue); // EXPORT
/// Set the virtual address of a section.
void setVirtualAddress(word uiSectionnr, dword dwValue); // EXPORT
/// Set the size of raw data of a section.
void setSizeOfRawData(word uiSectionnr, dword dwValue); // EXPORT
/// Set the file offset of a section.
void setPointerToRawData(word uiSectionnr, dword dwValue); // EXPORT
/// Set the pointer to relocations of a section.
void setPointerToRelocations(word uiSectionnr, dword dwValue); // EXPORT
/// Set the pointer to linenumbers of a section.
void setPointerToLinenumbers(word uiSectionnr, dword dwValue); // EXPORT
/// Set the number of relocations a section.
void setNumberOfRelocations(word uiSectionnr, dword dwValue); // EXPORT
/// Set the number of linenumbers section.
void setNumberOfLinenumbers(word uiSectionnr, dword dwValue); // EXPORT
/// Set the characteristics of a section.
void setCharacteristics(word uiSectionnr, dword dwValue); // EXPORT
};
class PeHeader32 : public PeHeaderT<32>
{
public:
/// Returns the BaseOfData value of the header.
dword getBaseOfData() const; // EXPORT
/// Sets the BaseOfData value of the header.
void setBaseOfData(dword value); // EXPORT
};
class PeHeader64 : public PeHeaderT<64>
{
};
template<int x>
void PeHeaderT<x>::addDataDirectory()
{
m_inthHeader.dataDirectories.push_back(PELIB_IMAGE_DATA_DIRECTORY());
}
template<int x>
void PeHeaderT<x>::removeDataDirectory(dword index)
{
m_inthHeader.dataDirectories.erase(m_inthHeader.dataDirectories.begin() + index);
}
/**
* Adds a new section to the header. The physical and virtual address as well as the virtual
* size of the section will be determined automatically from the raw size. The section
* characteristics will be set to IMAGE_SCN_MEM_WRITE | IMAGE_SCN_MEM_READ |
* IMAGE_SCN_CNT_INITIALIZED_DATA | IMAGE_SCN_CNT_CODE. All other values will be set to 0.
* Note: It's important that if the current header's FileAlignment and/or SectionAlignment values are
* 0 this function will fail.
* @param strName Name of the new section. If this name is longer than 8 bytes only the first 8 bytes will be used.
* @param dwSize Physical size of the new section in bytes.
* \todo Better code that handles files with 0 sections.
**/
template<int x>
int PeHeaderT<x>::addSection(const std::string& strName, dword dwSize)
{
unsigned int uiSecnr = calcNumberOfSections();
if (!getFileAlignment())
{
return ERROR_NO_FILE_ALIGNMENT;
}
else if (!getSectionAlignment())
{
return ERROR_NO_SECTION_ALIGNMENT;
}
if (uiSecnr) // Always allow 1 section.
{
if (uiSecnr == 0xFFFF)
{
return ERROR_TOO_MANY_SECTIONS;
}
else if (calcSpaceAfterHeader() < PELIB_IMAGE_SECTION_HEADER::size())
{
return ERROR_NOT_ENOUGH_SPACE;
}
}
dword dwOffset = calcOffset(/*dwSize*/);
dword dwRva = calcRva(/*dwSize*/);
PELIB_IMAGE_SECTION_HEADER ishdCurr;
m_vIsh.push_back(ishdCurr);
setSectionName(uiSecnr, strName);
setSizeOfRawData(uiSecnr, alignOffset(dwSize, getFileAlignment()));
setPointerToRawData(uiSecnr, dwOffset);
setVirtualSize(uiSecnr, alignOffset(dwSize, getSectionAlignment()));
setVirtualAddress(uiSecnr, dwRva);
setCharacteristics(uiSecnr, PELIB_IMAGE_SCN_MEM_WRITE | PELIB_IMAGE_SCN_MEM_READ | PELIB_IMAGE_SCN_CNT_INITIALIZED_DATA | PELIB_IMAGE_SCN_CNT_CODE);
return NO_ERROR;
}
/**
* Calculates a valid SizeOfImage value given the information from the current PE header.
* Note that this calculation works in Win2K but probably does not work in Win9X. I didn't test that though.
* @return Valid SizeOfImage value.
**/
template<int x>
unsigned int PeHeaderT<x>::calcSizeOfImage() const
{
// Major note here: It's possible for sections to exist with a Virtual Size of 0.
// That's why it's necessary to use std::max(Vsize, RawSize) here.
// An example for such a file is dbeng6.exe (made by Sybase).
// In this file each and every section has a VSize of 0 but it still runs.
std::vector<PELIB_IMAGE_SECTION_HEADER>::const_iterator ishLastSection = std::max_element(m_vIsh.begin(), m_vIsh.end(), std::mem_fun_ref(&PELIB_IMAGE_SECTION_HEADER::biggerVirtualAddress));
if (ishLastSection->VirtualSize != 0) return ishLastSection->VirtualAddress + ishLastSection->VirtualSize;
return ishLastSection->VirtualAddress + std::max(ishLastSection->VirtualSize, ishLastSection->SizeOfRawData);
}
/**
* Calculates the space between the last byte of the header and the first byte that's used for something
* else (that's either the first section or an image directory).
* @return Unused space after the header.
* \todo There are PE files with sections beginning at offset 0. They
* need to be considered.
**/
template<int x>
unsigned int PeHeaderT<x>::calcSpaceAfterHeader() const
{
return (calcStartOfCode() > size() + m_uiOffset) ? calcStartOfCode() - (size() + m_uiOffset) : 0;
}
/**
* Returns the first offset of the file that's actually used for something different than the header.
* That something is not necessarily code, it can be a data directory too.
* This offset can be the beginning of a section or the beginning of a directory.
* \todo Some optimizization is surely possible here.
* \todo There are PE files with sections beginning at offset 0. They
* need to be considered. Returning 0 for these files doesn't really make sense.
* So far these sections are disregarded.
**/
template<int x>
unsigned int PeHeaderT<x>::calcStartOfCode() const
{
unsigned int directories = calcNumberOfRvaAndSizes();
dword dwMinOffset = 0xFFFFFFFF;
if (directories >= 1 && getIddExportRva() && rvaToOffset(getIddExportRva()) < dwMinOffset) dwMinOffset = rvaToOffset(getIddExportRva());
if (directories >= 2 && getIddImportRva() && rvaToOffset(getIddImportRva()) < dwMinOffset) dwMinOffset = rvaToOffset(getIddImportRva());
if (directories >= 3 && getIddResourceRva() && rvaToOffset(getIddResourceRva()) < dwMinOffset) dwMinOffset = rvaToOffset(getIddResourceRva());
if (directories >= 4 && getIddExceptionRva() && rvaToOffset(getIddExceptionRva()) < dwMinOffset) dwMinOffset = rvaToOffset(getIddExceptionRva());
if (directories >= 5 && getIddSecurityRva() && rvaToOffset(getIddSecurityRva()) < dwMinOffset) dwMinOffset = rvaToOffset(getIddSecurityRva());
if (directories >= 6 && getIddBaseRelocRva() && rvaToOffset(getIddBaseRelocRva()) < dwMinOffset) dwMinOffset = rvaToOffset(getIddBaseRelocRva());
if (directories >= 7 && getIddDebugRva() && rvaToOffset(getIddDebugRva()) < dwMinOffset) dwMinOffset = rvaToOffset(getIddDebugRva());
if (directories >= 8 && getIddArchitectureRva() && rvaToOffset(getIddArchitectureRva()) < dwMinOffset) dwMinOffset = rvaToOffset(getIddArchitectureRva());
if (directories >= 9 && getIddGlobalPtrRva() && rvaToOffset(getIddGlobalPtrRva()) < dwMinOffset) dwMinOffset = rvaToOffset(getIddGlobalPtrRva());
if (directories >= 10 && getIddTlsRva() && rvaToOffset(getIddTlsRva()) < dwMinOffset) dwMinOffset = rvaToOffset(getIddTlsRva());
if (directories >= 11 && getIddLoadConfigRva() && rvaToOffset(getIddLoadConfigRva()) < dwMinOffset) dwMinOffset = rvaToOffset(getIddLoadConfigRva());
if (directories >= 12 && getIddBoundImportRva() && rvaToOffset(getIddBoundImportRva()) < dwMinOffset) dwMinOffset = rvaToOffset(getIddBoundImportRva());
if (directories >= 13 && getIddIatRva() && rvaToOffset(getIddIatRva()) < dwMinOffset) dwMinOffset = rvaToOffset(getIddIatRva());
if (directories >= 14 && getIddDelayImportRva() && rvaToOffset(getIddDelayImportRva()) < dwMinOffset) dwMinOffset = rvaToOffset(getIddDelayImportRva());
if (directories >= 15 && getIddComHeaderRva() && rvaToOffset(getIddComHeaderRva()) < dwMinOffset) dwMinOffset = rvaToOffset(getIddComHeaderRva());
for (word i=0;i<calcNumberOfSections();i++)
{
if ((getPointerToRawData(i) < dwMinOffset || dwMinOffset == 0xFFFFFFFF) && getSizeOfRawData(i))
{
if (getPointerToRawData(i)) dwMinOffset = getPointerToRawData(i);
}
}
return dwMinOffset;
}
/**
* Calculates the file offset for a new section. The file offset will already be aligned to the file's FileAlignment.
* @return Aligned file offset.
* \todo uiSize isn't used yet. Will be used later on to search for caves.
**/
template<int x>
unsigned int PeHeaderT<x>::calcOffset(/*unsigned int uiSize*/) const
{
unsigned int maxoffset = size();
for (word i=0;i<calcNumberOfSections();i++)
{
if (getPointerToRawData(i) + getSizeOfRawData(i) > maxoffset) maxoffset = getPointerToRawData(i) + getSizeOfRawData(i);
}
return alignOffset(maxoffset, getFileAlignment());
}
/**
* Calculates the Rva for a new section. The Rva will already be aligned to the file's SectionAlignment.
* \todo uiSize isn't used yet. Will be used later on to search for caves.
* @return Aligned Rva.
**/
template<int x>
unsigned int PeHeaderT<x>::calcRva(/*unsigned int uiSize*/) const
{
// Major note here: It's possible for sections to exist with a Virtual Size of 0.
// That's why it's necessary to use std::max(Vsize, RawSize) here.
// An example for such a file is dbeng6.exe (made by Sybase).
// In this file each and every section has a VSize of 0 but it still runs.
unsigned int maxoffset = size();
for (word i=0;i<calcNumberOfSections();i++)
{
if (getVirtualAddress(i) + std::max(getVirtualSize(i), getSizeOfRawData(i)) > maxoffset) maxoffset = getVirtualAddress(i) + std::max(getVirtualSize(i), getSizeOfRawData(i));
}
return alignOffset(maxoffset, getSectionAlignment());
}
/**
* Returns the number of currently defined sections. Note that this value can be different from the number
* of sections according to the header (see #PeLib::PeHeaderT<x>::getNumberOfSections).
* @return Number of currently defined sections.
**/
template<int x>
word PeHeaderT<x>::calcNumberOfSections() const
{
return static_cast<PeLib::word>(m_vIsh.size());
}
/**
* Enlarges the physically last section in the file.
* @param uiSize Additional size that's added to the section's size.
**/
template<int x>
void PeHeaderT<x>::enlargeLastSection(unsigned int uiSize)
{
std::vector<PELIB_IMAGE_SECTION_HEADER>::iterator ishLastSection = std::max_element(m_vIsh.begin(), m_vIsh.end(), std::mem_fun_ref(&PELIB_IMAGE_SECTION_HEADER::biggerFileOffset));
unsigned int uiRawDataSize = alignOffset(ishLastSection->SizeOfRawData + uiSize, getFileAlignment());
ishLastSection->SizeOfRawData = uiRawDataSize;
ishLastSection->VirtualSize = ishLastSection->SizeOfRawData;
setSizeOfImage(calcSizeOfImage());
}
/**
* Determines the section which contains the file offset.
* @param dwOffset File offset.
* @return Section Id of the section which contains the offset.
**/
template<int x>
word PeHeaderT<x>::getSectionWithOffset(VAR4_8 dwOffset) const
{
// Offset = 0 must be handled explicitly as there are files
// with sections that begin at offset 0, that means the section
// only exists in memory.
if (!dwOffset) return std::numeric_limits<word>::max();
for (word i=0;i<calcNumberOfSections();i++)
{
// Explicity exclude sections with raw pointer = 0.
dword rawptr = getPointerToRawData(i);
if (rawptr && rawptr <= dwOffset && rawptr + getSizeOfRawData(i) > dwOffset) return i;
}
return std::numeric_limits<word>::max();
}
/**
* Determines the section which contains the Rva.
* @param dwRva A relative virtual address.
* @return Section Id of the section which contains the Rva.
**/
template<int x>
word PeHeaderT<x>::getSectionWithRva(VAR4_8 dwRva) const
{
// Major note here: It's possible for sections to exist with a Virtual Size of 0.
// That's why it's necessary to use std::max(Vsize, RawSize) here.
// An example for such a file is dbeng6.exe (made by Sybase).
// In this file each and every section has a VSize of 0 but it still runs.
for (word i=0;i<calcNumberOfSections();i++)
{
// Weird VC++7 error doesn't allow me to use std::max here.
dword max = getVirtualSize(i) >= getSizeOfRawData(i) ? getVirtualSize(i) : getSizeOfRawData(i);
if (getVirtualAddress(i) <= dwRva && getVirtualAddress(i) + max > dwRva) return i;
}
return -1;
}
/**
* Corrects all faulty values of the current PE header. The following values will be corrected: NtSignature,
* NumberOfSections, SizeOfOptionalHeader, FileAlignment (will be aligned to n*0x200),
* SectionAlignment (will be aligned to n*0x1000), NumberOfRvaAndSizes, SizeOfHeaders, SizeOfImage,
* Magic, Characteristics.
* @param dwOffset Beginning of PeHeader (see #PeLib::MzHeader::getAddressOfPeHeader).
* \todo 32bit and 64bit versions.
**/
template<int x>
void PeHeaderT<x>::makeValid(dword dwOffset)
{
setNtSignature(PELIB_IMAGE_NT_SIGNATURE); // 'PE'
setMachine(PELIB_IMAGE_FILE_MACHINE_I386);
setNumberOfSections(calcNumberOfSections());
// Check if 64 bits.
setSizeOfOptionalHeader(PELIB_IMAGE_OPTIONAL_HEADER<x>::size() + calcNumberOfRvaAndSizes() * 8);
// Check if 64 bits.
dword dwCharacteristics = PELIB_IMAGE_FILE_EXECUTABLE_IMAGE | PELIB_IMAGE_FILE_32BIT_MACHINE;
setCharacteristics(dwCharacteristics);
// Check if 64 bits.
setMagic(PELIB_IMAGE_NT_OPTIONAL_HDR32_MAGIC);
// setImageBase(0x01000000);
// Align file and section alignment values
unsigned int dwAlignedOffset = alignOffset(getSectionAlignment(), 0x1000);
setSectionAlignment(dwAlignedOffset ? dwAlignedOffset : 0x1000);
dwAlignedOffset = alignOffset(getFileAlignment(), 0x200);
setFileAlignment(dwAlignedOffset ? dwAlignedOffset : 0x200);
// setMajorSubsystemVersion(4);
// setSubsystem(IMAGE_SUBSYSTEM_WINDOWS_GUI);
setNumberOfRvaAndSizes(calcNumberOfRvaAndSizes());
// Code below depends on code above. Don't change the order.
dword dwSizeOfHeaders = alignOffset(dwOffset + size(), getFileAlignment());
setSizeOfHeaders(dwSizeOfHeaders);
dword dwSizeOfImage = alignOffset(dwSizeOfHeaders, getSectionAlignment());
for (int i=0;i<calcNumberOfSections();i++)
{
dwSizeOfImage += alignOffset(getVirtualSize(i), getSectionAlignment());
}
dwSizeOfImage = alignOffset(dwSizeOfImage, getSectionAlignment());
setSizeOfImage(dwSizeOfImage);
}
template<int x>
unsigned int PeHeaderT<x>::offsetToRva(VAR4_8 dwOffset) const
{
if (dwOffset < calcStartOfCode()) return dwOffset;
PeLib::word uiSecnr = getSectionWithOffset(dwOffset);
if (uiSecnr == 0xFFFF) return -1;
return getVirtualAddress(uiSecnr) + dwOffset - getPointerToRawData(uiSecnr);
}
/**
* Converts a file offset to a virtual address.
* @param dwOffset File offset.
* @return Virtual Address.
**/
template<int x>
unsigned int PeHeaderT<x>::offsetToVa(VAR4_8 dwOffset) const
{
if (dwOffset < calcStartOfCode()) return getImageBase() + dwOffset;
PeLib::word uiSecnr = getSectionWithOffset(dwOffset);
if (uiSecnr == 0xFFFF) return -1;
return getImageBase() + getVirtualAddress(uiSecnr) + dwOffset - getPointerToRawData(uiSecnr);
}
template<int x>
void PeHeaderT<x>::readHeader(InputBuffer& ibBuffer, PELIB_IMAGE_NT_HEADERS<x>& header) const
{
ibBuffer >> header.Signature;
ibBuffer >> header.FileHeader.Machine;
ibBuffer >> header.FileHeader.NumberOfSections;
ibBuffer >> header.FileHeader.TimeDateStamp;
ibBuffer >> header.FileHeader.PointerToSymbolTable;
ibBuffer >> header.FileHeader.NumberOfSymbols;
ibBuffer >> header.FileHeader.SizeOfOptionalHeader;
ibBuffer >> header.FileHeader.Characteristics;
ibBuffer >> header.OptionalHeader.Magic;
ibBuffer >> header.OptionalHeader.MajorLinkerVersion;
ibBuffer >> header.OptionalHeader.MinorLinkerVersion;
ibBuffer >> header.OptionalHeader.SizeOfCode;
ibBuffer >> header.OptionalHeader.SizeOfInitializedData;
ibBuffer >> header.OptionalHeader.SizeOfUninitializedData;
ibBuffer >> header.OptionalHeader.AddressOfEntryPoint;
ibBuffer >> header.OptionalHeader.BaseOfCode;
readBaseOfData(ibBuffer, header);
ibBuffer >> header.OptionalHeader.ImageBase;
ibBuffer >> header.OptionalHeader.SectionAlignment;
ibBuffer >> header.OptionalHeader.FileAlignment;
ibBuffer >> header.OptionalHeader.MajorOperatingSystemVersion;
ibBuffer >> header.OptionalHeader.MinorOperatingSystemVersion;
ibBuffer >> header.OptionalHeader.MajorImageVersion;
ibBuffer >> header.OptionalHeader.MinorImageVersion;
ibBuffer >> header.OptionalHeader.MajorSubsystemVersion;
ibBuffer >> header.OptionalHeader.MinorSubsystemVersion;
ibBuffer >> header.OptionalHeader.Win32VersionValue;
ibBuffer >> header.OptionalHeader.SizeOfImage;
ibBuffer >> header.OptionalHeader.SizeOfHeaders;
ibBuffer >> header.OptionalHeader.CheckSum;
ibBuffer >> header.OptionalHeader.Subsystem;
ibBuffer >> header.OptionalHeader.DllCharacteristics;
ibBuffer >> header.OptionalHeader.SizeOfStackReserve;
ibBuffer >> header.OptionalHeader.SizeOfStackCommit;
ibBuffer >> header.OptionalHeader.SizeOfHeapReserve;
ibBuffer >> header.OptionalHeader.SizeOfHeapCommit;
ibBuffer >> header.OptionalHeader.LoaderFlags;
ibBuffer >> header.OptionalHeader.NumberOfRvaAndSizes;
}
template<int x>
void PeHeaderT<x>::readDataDirectories(InputBuffer& ibBuffer, PELIB_IMAGE_NT_HEADERS<x>& header) const
{
PELIB_IMAGE_DATA_DIRECTORY idd;
for (unsigned int i=0;i<header.OptionalHeader.NumberOfRvaAndSizes;i++)
{
ibBuffer >> idd.VirtualAddress;
ibBuffer >> idd.Size;
header.dataDirectories.push_back(idd);
}
}
template<int x>
std::vector<PELIB_IMAGE_SECTION_HEADER> PeHeaderT<x>::readSections(InputBuffer& ibBuffer, PELIB_IMAGE_NT_HEADERS<x>& header) const
{
const unsigned int nrSections = header.FileHeader.NumberOfSections;
PELIB_IMAGE_SECTION_HEADER ishCurr;
std::vector<PELIB_IMAGE_SECTION_HEADER> vIshdCurr;
for (unsigned int i=0;i<nrSections;i++)
{
ibBuffer.read(reinterpret_cast<char*>(ishCurr.Name), 8);
ibBuffer >> ishCurr.VirtualSize;
ibBuffer >> ishCurr.VirtualAddress;
ibBuffer >> ishCurr.SizeOfRawData;
ibBuffer >> ishCurr.PointerToRawData;
ibBuffer >> ishCurr.PointerToRelocations;
ibBuffer >> ishCurr.PointerToLinenumbers;
ibBuffer >> ishCurr.NumberOfRelocations;
ibBuffer >> ishCurr.NumberOfLinenumbers;
ibBuffer >> ishCurr.Characteristics;
vIshdCurr.push_back(ishCurr);
}
return vIshdCurr;
}
template<int x>
int PeHeaderT<x>::read(const unsigned char* pcBuffer, unsigned int uiSize, unsigned int uiOffset)
{
if (uiSize < m_inthHeader.size())
{
return ERROR_INVALID_FILE;
}
std::vector<unsigned char> vBuffer(pcBuffer, pcBuffer + m_inthHeader.size());
InputBuffer ibBuffer(vBuffer);
PELIB_IMAGE_NT_HEADERS<x> header;
readHeader(ibBuffer, header);
if (uiSize < m_inthHeader.size() + header.OptionalHeader.NumberOfRvaAndSizes * 8 + header.FileHeader.NumberOfSections * 0x28)
{
return ERROR_INVALID_FILE;
}
vBuffer.resize(header.OptionalHeader.NumberOfRvaAndSizes * 8 + header.FileHeader.NumberOfSections * 0x28);
vBuffer.assign(pcBuffer + m_inthHeader.size(), pcBuffer + m_inthHeader.size() + header.OptionalHeader.NumberOfRvaAndSizes * 8 + header.FileHeader.NumberOfSections * 0x28);
ibBuffer.setBuffer(vBuffer);
readDataDirectories(ibBuffer, header);
m_vIsh = readSections(ibBuffer, header);
std::swap(m_inthHeader, header);
m_uiOffset = uiOffset;
return NO_ERROR;
}
/**
* Reads the PE header from a file Note that this function does not verify if a file is actually a MZ file.
* For this purpose see #PeLib::PeHeaderT<x>::isValid. The only check this function makes is a check to see if
* the file is large enough to be a PE header. If the data is valid doesn't matter.
* @param strFilename Name of the file which will be read.
* @param uiOffset File offset of PE header (see #PeLib::MzHeader::getAddressOfPeHeader).
**/
template<int x>
int PeHeaderT<x>::read(std::string strFilename, unsigned int uiOffset)
{
std::ifstream ifFile(strFilename.c_str(), std::ios::binary);
if (!ifFile)
{
return ERROR_OPENING_FILE;
}
// File too small
if (fileSize(ifFile) < uiOffset + m_inthHeader.size())
{
return ERROR_INVALID_FILE;
}
std::vector<unsigned char> vBuffer(m_inthHeader.size());
ifFile.seekg(uiOffset, std::ios::beg);
ifFile.read(reinterpret_cast<char*>(&vBuffer[0]), static_cast<std::streamsize>(vBuffer.size()));
InputBuffer ibBuffer(vBuffer);
PELIB_IMAGE_NT_HEADERS<x> header;
readHeader(ibBuffer, header);
vBuffer.resize(header.OptionalHeader.NumberOfRvaAndSizes * 8 + header.FileHeader.NumberOfSections * 0x28);
ifFile.read(reinterpret_cast<char*>(&vBuffer[0]), static_cast<std::streamsize>(vBuffer.size()));
if (!ifFile)
{
return ERROR_INVALID_FILE;
}
ibBuffer.setBuffer(vBuffer);
readDataDirectories(ibBuffer, header);
// Sections
// const unsigned int nrSections = header.FileHeader.NumberOfSections;
// if (fileSize(ifFile) < uiOffset + m_inthHeader.size() + nrSections * PELIB_IMAGE_SECTION_HEADER::size())
// {
// return ERROR_INVALID_FILE;
// }
m_vIsh = readSections(ibBuffer, header);
std::swap(m_inthHeader, header);
m_uiOffset = uiOffset;
ifFile.close();
return NO_ERROR;
}
/**
* Rebuilds the PE header so that it can be written to a file. It's not guaranteed that the
* header will be valid. If you want to make sure that the header will be valid you
* must call #PeLib::PeHeaderT<x>::makeValid first.
* @param vBuffer Buffer where the rebuilt header will be stored.
**/
template<int x>
void PeHeaderT<x>::rebuild(std::vector<byte>& vBuffer) const
{
OutputBuffer obBuffer(vBuffer);
obBuffer << m_inthHeader.Signature;
obBuffer << m_inthHeader.FileHeader.Machine;
obBuffer << m_inthHeader.FileHeader.NumberOfSections;
obBuffer << m_inthHeader.FileHeader.TimeDateStamp;
obBuffer << m_inthHeader.FileHeader.PointerToSymbolTable;
obBuffer << m_inthHeader.FileHeader.NumberOfSymbols;
obBuffer << m_inthHeader.FileHeader.SizeOfOptionalHeader;
obBuffer << m_inthHeader.FileHeader.Characteristics;
obBuffer << m_inthHeader.OptionalHeader.Magic;
obBuffer << m_inthHeader.OptionalHeader.MajorLinkerVersion;
obBuffer << m_inthHeader.OptionalHeader.MinorLinkerVersion;
obBuffer << m_inthHeader.OptionalHeader.SizeOfCode;
obBuffer << m_inthHeader.OptionalHeader.SizeOfInitializedData;
obBuffer << m_inthHeader.OptionalHeader.SizeOfUninitializedData;
obBuffer << m_inthHeader.OptionalHeader.AddressOfEntryPoint;
obBuffer << m_inthHeader.OptionalHeader.BaseOfCode;
rebuildBaseOfData(obBuffer);
// obBuffer << m_inthHeader.OptionalHeader.BaseOfData;
obBuffer << m_inthHeader.OptionalHeader.ImageBase;
obBuffer << m_inthHeader.OptionalHeader.SectionAlignment;
obBuffer << m_inthHeader.OptionalHeader.FileAlignment;
obBuffer << m_inthHeader.OptionalHeader.MajorOperatingSystemVersion;
obBuffer << m_inthHeader.OptionalHeader.MinorOperatingSystemVersion;
obBuffer << m_inthHeader.OptionalHeader.MajorImageVersion;
obBuffer << m_inthHeader.OptionalHeader.MinorImageVersion;
obBuffer << m_inthHeader.OptionalHeader.MajorSubsystemVersion;
obBuffer << m_inthHeader.OptionalHeader.MinorSubsystemVersion;
obBuffer << m_inthHeader.OptionalHeader.Win32VersionValue;
obBuffer << m_inthHeader.OptionalHeader.SizeOfImage;
obBuffer << m_inthHeader.OptionalHeader.SizeOfHeaders;
obBuffer << m_inthHeader.OptionalHeader.CheckSum;
obBuffer << m_inthHeader.OptionalHeader.Subsystem;
obBuffer << m_inthHeader.OptionalHeader.DllCharacteristics;
obBuffer << m_inthHeader.OptionalHeader.SizeOfStackReserve;
obBuffer << m_inthHeader.OptionalHeader.SizeOfStackCommit;
obBuffer << m_inthHeader.OptionalHeader.SizeOfHeapReserve;
obBuffer << m_inthHeader.OptionalHeader.SizeOfHeapCommit;
obBuffer << m_inthHeader.OptionalHeader.LoaderFlags;
obBuffer << m_inthHeader.OptionalHeader.NumberOfRvaAndSizes;
// The 0x10 data directories
for (unsigned int i=0;i<calcNumberOfRvaAndSizes();i++)
{
obBuffer << m_inthHeader.dataDirectories[i].VirtualAddress;
obBuffer << m_inthHeader.dataDirectories[i].Size;
}
// The section definitions
const unsigned int nrSections = calcNumberOfSections();
for (unsigned int i=0;i<nrSections;i++)
{
char temp[9] = {0};
strcpy(temp, getSectionName(i).c_str());
obBuffer.add(temp, 8);
obBuffer << m_vIsh[i].VirtualSize;
obBuffer << m_vIsh[i].VirtualAddress;
obBuffer << m_vIsh[i].SizeOfRawData;
obBuffer << m_vIsh[i].PointerToRawData;
obBuffer << m_vIsh[i].PointerToRelocations;
obBuffer << m_vIsh[i].PointerToLinenumbers;
obBuffer << m_vIsh[i].NumberOfRelocations;
obBuffer << m_vIsh[i].NumberOfLinenumbers;
obBuffer << m_vIsh[i].Characteristics;
}
}
/**
* Converts a relative virtual offset to a file offset.
* @param dwRva A relative virtual offset.
* @return A file offset.
* \todo It's not always 0x1000.
**/
template<int x>
typename FieldSizes<x>::VAR4_8 PeHeaderT<x>::rvaToOffset(VAR4_8 dwRva) const
{
// XXX: Not correct
if (dwRva < 0x1000) return dwRva;
PeLib::word uiSecnr = getSectionWithRva(dwRva);
if (uiSecnr == 0xFFFF || dwRva > getVirtualAddress(uiSecnr) + getSizeOfRawData(uiSecnr))
{
return std::numeric_limits<VAR4_8>::max();
}
return getPointerToRawData(uiSecnr) + dwRva - getVirtualAddress(uiSecnr);
}
/**
* Converts a relative virtual offset to a virtual offset.
* @param dwRva A relative virtual offset.
* @return A virtual offset.
**/
template<int x>
typename FieldSizes<x>::VAR4_8 PeHeaderT<x>::rvaToVa(VAR4_8 dwRva) const
{
return getImageBase() + dwRva;
}
/**
* Calculates the size of the current PE header. This includes the actual header and the section definitions.
* @return Size of the current PE header.
* \todo Better handling of files with less than 0x10 directories.
**/
template<int x>
unsigned int PeHeaderT<x>::size() const
{
return m_inthHeader.size() + getNumberOfSections() * PELIB_IMAGE_SECTION_HEADER::size();
}
// \todo Not sure if this works.
template<int x>
typename FieldSizes<x>::VAR4_8 PeHeaderT<x>::vaToRva(VAR4_8 dwRva) const
{
if (dwRva - getImageBase() < calcStartOfCode()) return dwRva - getImageBase();
if (getSectionWithRva(dwRva - getImageBase()) == 0xFFFF) return -1;
return dwRva - getImageBase();
}
template<int x>
typename FieldSizes<x>::VAR4_8 PeHeaderT<x>::vaToOffset(VAR4_8 dwRva) const
{
return rvaToOffset(dwRva - getImageBase());
}
/**
* Saves the PE header to a file. Note that this only saves the header information, if you have added sections
* and want to save these to the file you have to call #PeLib::PeHeaderT<x>::saveSections too. This function also
* does not verify if the PE header is correct. If you want to make sure that the current PE header is valid,
* call #PeLib::PeHeaderT<x>::isValid and #PeLib::PeHeaderT<x>::makeValid first.
* @param strFilename Filename of the file the header will be written to.
* @param uiOffset File offset the header will be written to.
**/
template<int x>
int PeHeaderT<x>::write(std::string strFilename, unsigned int uiOffset) const
{
std::fstream ofFile(strFilename.c_str(), std::ios_base::in);
if (!ofFile)
{
ofFile.clear();
ofFile.open(strFilename.c_str(), std::ios_base::out | std::ios_base::binary);
}
else
{
ofFile.close();
ofFile.open(strFilename.c_str(), std::ios_base::in | std::ios_base::out | std::ios_base::binary);
}
if (!ofFile)
{
return ERROR_OPENING_FILE;
}
ofFile.seekp(uiOffset, std::ios::beg);
std::vector<unsigned char> vBuffer;
rebuild(vBuffer);
ofFile.write(reinterpret_cast<const char*>(&vBuffer[0]), static_cast<unsigned int>(vBuffer.size()));
ofFile.close();
return NO_ERROR;
}
/**
* Overwrites a section's data.
* @param wSecnr Number of the section which will be overwritten.
* @param strFilename Name of the file where the section will be written to.
* @param wSecnr Number of the section that will be written.
* @param vBuffer New data of the section.
**/
template<int x>
int PeHeaderT<x>::writeSectionData(const std::string& strFilename, word wSecnr, const std::vector<byte>& vBuffer) const
{
std::fstream ofFile(strFilename.c_str(), std::ios_base::in);
if (!ofFile)
{
ofFile.clear();
ofFile.open(strFilename.c_str(), std::ios_base::out | std::ios_base::binary);
}
else
{
ofFile.close();
ofFile.open(strFilename.c_str(), std::ios_base::in | std::ios_base::out | std::ios_base::binary);
}
if (!ofFile)
{
ofFile.clear();
return ERROR_OPENING_FILE;
}
ofFile.seekp(getPointerToRawData(wSecnr), std::ios::beg);
ofFile.write(reinterpret_cast<const char*>(&vBuffer[0]), std::min(static_cast<unsigned int>(vBuffer.size()), getSizeOfRawData(wSecnr)));
ofFile.close();
return NO_ERROR;
}
template<int x>
int PeHeaderT<x>::writeSections(const std::string& strFilename) const
{
std::fstream ofFile(strFilename.c_str(), std::ios_base::in);
if (!ofFile)
{
ofFile.clear();
ofFile.open(strFilename.c_str(), std::ios_base::out | std::ios_base::binary);
}
else
{
ofFile.close();
ofFile.open(strFilename.c_str(), std::ios_base::in | std::ios_base::out | std::ios_base::binary);
}
if (!ofFile)
{
return ERROR_OPENING_FILE;
}
unsigned int uiFilesize = fileSize(ofFile);
for (int i=0;i<calcNumberOfSections();i++)
{
if (uiFilesize < getPointerToRawData(i) + getSizeOfRawData(i))
{
unsigned int uiToWrite = getPointerToRawData(i) + getSizeOfRawData(i) - uiFilesize;
std::vector<char> vBuffer(uiToWrite);
ofFile.seekp(0, std::ios::end);
ofFile.write(&vBuffer[0], static_cast<unsigned int>(vBuffer.size()));
uiFilesize = getPointerToRawData(i) + getSizeOfRawData(i);
}
}
ofFile.close();
return NO_ERROR;
}
/**
* Returns the file's Nt signature.
* @return The Nt signature value from the PE header.
**/
template<int x>
dword PeHeaderT<x>::getNtSignature() const
{
return m_inthHeader.Signature;
}
/**
* Returns the file's machine.
* @return The Machine value from the PE header.
**/
template<int x>
word PeHeaderT<x>::getMachine() const
{
return m_inthHeader.FileHeader.Machine;
}
/**
* Returns the file's number of sections as defined in the header. Note that this value can be different
* from the number of defined sections (#see PeLib::PeHeaderT<x>::getNumberOfSections).
* @return The NumberOfSections value from the PE header.
**/
template<int x>
word PeHeaderT<x>::getNumberOfSections() const
{
return m_inthHeader.FileHeader.NumberOfSections;
}
/**
* Returns the file's TimeDateStamp.
* @return The TimeDateStamp value from the PE header.
**/
template<int x>
dword PeHeaderT<x>::getTimeDateStamp() const
{
return m_inthHeader.FileHeader.TimeDateStamp;
}
/**
* Returns the relative virtual address of the file's symbol table.
* @return The PointerToSymbolTable value from the PE header.
**/
template<int x>
dword PeHeaderT<x>::getPointerToSymbolTable() const
{
return m_inthHeader.FileHeader.PointerToSymbolTable;
}
/**
* Returns the number of symbols of the file's symbol table.
* @return The NumberOfSymbols value from the PE header.
**/
template<int x>
dword PeHeaderT<x>::getNumberOfSymbols() const
{
return m_inthHeader.FileHeader.NumberOfSymbols;
}
/**
* Returns the size of optional header of the file.
* @return The SizeOfOptionalHeader value from the PE header.
**/
template<int x>
word PeHeaderT<x>::getSizeOfOptionalHeader() const
{
return m_inthHeader.FileHeader.SizeOfOptionalHeader;
}
/**
* @return The Characteristics value from the PE header.
**/
template<int x>
word PeHeaderT<x>::getCharacteristics() const
{
return m_inthHeader.FileHeader.Characteristics;
}
/**
* @return The Magic value from the PE header.
**/
template<int x>
word PeHeaderT<x>::getMagic() const
{
return m_inthHeader.OptionalHeader.Magic;
}
/**
* @return The MajorLinkerVersion value from the PE header.
**/
template<int x>
byte PeHeaderT<x>::getMajorLinkerVersion() const
{
return m_inthHeader.OptionalHeader.MajorLinkerVersion;
}
/**
* @return The MinorLinkerVersion value from the PE header.
**/
template<int x>
byte PeHeaderT<x>::getMinorLinkerVersion() const
{
return m_inthHeader.OptionalHeader.MinorLinkerVersion;
}
/**
* @return The SizeOfCode value from the PE header.
**/
template<int x>
dword PeHeaderT<x>::getSizeOfCode() const
{
return m_inthHeader.OptionalHeader.SizeOfCode;
}
/**
* @return The SizeOfInitializedData value from the PE header.
**/
template<int x>
dword PeHeaderT<x>::getSizeOfInitializedData() const
{
return m_inthHeader.OptionalHeader.SizeOfInitializedData;
}
/**
* @return The SizeOfUninitializedData value from the PE header.
**/
template<int x>
dword PeHeaderT<x>::getSizeOfUninitializedData() const
{
return m_inthHeader.OptionalHeader.SizeOfUninitializedData;
}
/**
* @return The AddressOfEntryPoint value from the PE header.
**/
template<int x>
dword PeHeaderT<x>::getAddressOfEntryPoint() const
{
return m_inthHeader.OptionalHeader.AddressOfEntryPoint;
}
/**
* @return The BaseOfCode value from the PE header.
**/
template<int x>
dword PeHeaderT<x>::getBaseOfCode() const
{
return m_inthHeader.OptionalHeader.BaseOfCode;
}
/**
* @return The ImageBase value from the PE header.
**/
template<int x>
typename FieldSizes<x>::VAR4_8 PeHeaderT<x>::getImageBase() const
{
return m_inthHeader.OptionalHeader.ImageBase;
}
/**
* @return The SectionAlignment value from the PE header.
**/
template<int x>
dword PeHeaderT<x>::getSectionAlignment() const
{
return m_inthHeader.OptionalHeader.SectionAlignment;
}
/**
* @return The FileAlignment value from the PE header.
**/
template<int x>
dword PeHeaderT<x>::getFileAlignment() const
{
return m_inthHeader.OptionalHeader.FileAlignment;
}
/**
* @return The MajorOperatingSystemVersion value from the PE header.
**/
template<int x>
word PeHeaderT<x>::getMajorOperatingSystemVersion() const
{
return m_inthHeader.OptionalHeader.MajorOperatingSystemVersion;
}
/**
* @return The MinorOperatingSystemVersion value from the PE header.
**/
template<int x>
word PeHeaderT<x>::getMinorOperatingSystemVersion() const
{
return m_inthHeader.OptionalHeader.MinorOperatingSystemVersion;
}
/**
* @return The MajorImageVersion value from the PE header.
**/
template<int x>
word PeHeaderT<x>::getMajorImageVersion() const
{
return m_inthHeader.OptionalHeader.MajorImageVersion;
}
/**
* @return The MinorImageVersion value from the PE header.
**/
template<int x>
word PeHeaderT<x>::getMinorImageVersion() const
{
return m_inthHeader.OptionalHeader.MinorImageVersion;
}
/**
* @return The MajorSubsystemVersion value from the PE header.
**/
template<int x>
word PeHeaderT<x>::getMajorSubsystemVersion() const
{
return m_inthHeader.OptionalHeader.MajorSubsystemVersion;
}
/**
* @return The MinorSubsystemVersion value from the PE header.
**/
template<int x>
word PeHeaderT<x>::getMinorSubsystemVersion() const
{
return m_inthHeader.OptionalHeader.MinorSubsystemVersion;
}
/**
* @return The WinVersionValue value from the PE header.
**/
template<int x>
dword PeHeaderT<x>::getWin32VersionValue() const
{
return m_inthHeader.OptionalHeader.Win32VersionValue;
}
/**
* @return The SizeOfImage value from the PE header.
**/
template<int x>
dword PeHeaderT<x>::getSizeOfImage() const
{
return m_inthHeader.OptionalHeader.SizeOfImage;
}
/**
* @return The SizeOfHeaders value from the PE header.
**/
template<int x>
dword PeHeaderT<x>::getSizeOfHeaders() const
{
return m_inthHeader.OptionalHeader.SizeOfHeaders;
}
/**
* @return The CheckSums value from the PE header.
**/
template<int x>
dword PeHeaderT<x>::getCheckSum() const
{
return m_inthHeader.OptionalHeader.CheckSum;
}
/**
* @return The Subsystem value from the PE header.
**/
template<int x>
word PeHeaderT<x>::getSubsystem() const
{
return m_inthHeader.OptionalHeader.Subsystem;
}
/**
* @return The DllCharacteristics value from the PE header.
**/
template<int x>
word PeHeaderT<x>::getDllCharacteristics() const
{
return m_inthHeader.OptionalHeader.DllCharacteristics;
}
/**
* @return The SizeOfStackReserve value from the PE header.
**/
template<int x>
typename FieldSizes<x>::VAR4_8 PeHeaderT<x>::getSizeOfStackReserve() const
{
return m_inthHeader.OptionalHeader.SizeOfStackReserve;
}
/**
* @return The SizeOfStackCommit value from the PE header.
**/
template<int x>
typename FieldSizes<x>::VAR4_8 PeHeaderT<x>::getSizeOfStackCommit() const
{
return m_inthHeader.OptionalHeader.SizeOfStackCommit;
}
/**
* @return The SizeOfHeapReserve value from the PE header.
**/
template<int x>
typename FieldSizes<x>::VAR4_8 PeHeaderT<x>::getSizeOfHeapReserve() const
{
return m_inthHeader.OptionalHeader.SizeOfHeapReserve;
}
/**
* @return The SizeOfHeapCommit value from the PE header.
**/
template<int x>
typename FieldSizes<x>::VAR4_8 PeHeaderT<x>::getSizeOfHeapCommit() const
{
return m_inthHeader.OptionalHeader.SizeOfHeapCommit;
}
/**
* @return The LoaderFlags value from the PE header.
**/
template<int x>
dword PeHeaderT<x>::getLoaderFlags() const
{
return m_inthHeader.OptionalHeader.LoaderFlags;
}
/**
* @return The NumberOfRvaAndSizes value from the PE header.
**/
template<int x>
dword PeHeaderT<x>::getNumberOfRvaAndSizes() const
{
return m_inthHeader.OptionalHeader.NumberOfRvaAndSizes;
}
template<int x>
dword PeHeaderT<x>::calcNumberOfRvaAndSizes() const
{
return static_cast<dword>(m_inthHeader.dataDirectories.size());
}
/**
* Returns the relative virtual address of the current file's export directory.
* @return The Rva of the Export directory.
**/
template<int x>
dword PeHeaderT<x>::getIddExportRva() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_EXPORT].VirtualAddress;
}
/**
* Returns the size of the current file's export directory.
* @return The sizeof the Export directory.
**/
template<int x>
dword PeHeaderT<x>::getIddExportSize() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_EXPORT].Size;
}
/**
* Returns the relative virtual address of the current file's import directory.
* @return The Rva of the Import directory.
**/
template<int x>
dword PeHeaderT<x>::getIddImportRva() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress;
}
/**
* Returns the size of the current file's import directory.
* @return The size of the Import directory.
**/
template<int x>
dword PeHeaderT<x>::getIddImportSize() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_IMPORT].Size;
}
/**
* Returns the relative virtual address of the current file's resource directory.
* @return The Rva of the Resource directory.
**/
template<int x>
dword PeHeaderT<x>::getIddResourceRva() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_RESOURCE].VirtualAddress;
}
/**
* Returns the size of the current file'resource resource directory.
* @return The size of the Resource directory.
**/
template<int x>
dword PeHeaderT<x>::getIddResourceSize() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_RESOURCE].Size;
}
/**
* Returns the relative virtual address of the current file's exception directory.
* @return The Rva of the Exception directory.
**/
template<int x>
dword PeHeaderT<x>::getIddExceptionRva() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_EXCEPTION].VirtualAddress;
}
/**
* Returns the size of the current file's exception directory.
* @return The size of the Exception directory.
**/
template<int x>
dword PeHeaderT<x>::getIddExceptionSize() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_EXCEPTION].Size;
}
/**
* Returns the relative virtual address of the current file's security directory.
* @return The Rva of the Security directory.
**/
template<int x>
dword PeHeaderT<x>::getIddSecurityRva() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_SECURITY].VirtualAddress;
}
/**
* Returns the size of the current file's security directory.
* @return The size of the Security directory.
**/
template<int x>
dword PeHeaderT<x>::getIddSecuritySize() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_SECURITY].Size;
}
/**
* Returns the relative virtual address of the current file's base reloc directory.
* @return The Rva of the Base Reloc directory.
**/
template<int x>
dword PeHeaderT<x>::getIddBaseRelocRva() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress;
}
/**
* Returns the size of the current file's base reloc directory.
* @return The size of the Base Reloc directory.
**/
template<int x>
dword PeHeaderT<x>::getIddBaseRelocSize() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_BASERELOC].Size;
}
/**
* Returns the relative virtual address of the current file's debug directory.
* @return The Rva of the Debug directory.
**/
template<int x>
dword PeHeaderT<x>::getIddDebugRva() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_DEBUG].VirtualAddress;
}
/**
* Returns the size of the current file's debug directory.
* @return The size of the Debug directory.
**/
template<int x>
dword PeHeaderT<x>::getIddDebugSize() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_DEBUG].Size;
}
/**
* Returns the relative virtual address of the current file's Architecture directory.
* @return The Rva of the Architecture directory.
**/
template<int x>
dword PeHeaderT<x>::getIddArchitectureRva() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_ARCHITECTURE].VirtualAddress;
}
/**
* Returns the size of the current file's Architecture directory.
* @return The size of the Architecture directory.
**/
template<int x>
dword PeHeaderT<x>::getIddArchitectureSize() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_ARCHITECTURE].Size;
}
/**
* Returns the relative virtual address of the current file's global ptr directory.
* @return The Rva of the GlobalPtr directory.
**/
template<int x>
dword PeHeaderT<x>::getIddGlobalPtrRva() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_GLOBALPTR].VirtualAddress;
}
/**
* Returns the size of the current file's global ptr directory.
* @return The size of the GlobalPtr directory.
**/
template<int x>
dword PeHeaderT<x>::getIddGlobalPtrSize() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_GLOBALPTR].Size;
}
/**
* Returns the relative virtual address of the current file's TLS directory.
* @return The Rva of the Tls directory.
**/
template<int x>
dword PeHeaderT<x>::getIddTlsRva() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_TLS].VirtualAddress;
}
/**
* Returns the size of the current file's TLS directory.
* @return The size of the Tls directory.
**/
template<int x>
dword PeHeaderT<x>::getIddTlsSize() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_TLS].Size;
}
/**
* Returns the relative virtual address of the current file's load config directory.
* @return The Rva of the LoadConfig directory.
**/
template<int x>
dword PeHeaderT<x>::getIddLoadConfigRva() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_LOAD_CONFIG].VirtualAddress;
}
/**
* Returns the size of the current file's load config directory.
* @return The size of the LoadConfig directory.
**/
template<int x>
dword PeHeaderT<x>::getIddLoadConfigSize() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_LOAD_CONFIG].Size;
}
/**
* Returns the relative virtual address of the current file's bound import directory.
* @return The Rva of the BoundImport directory.
**/
template<int x>
dword PeHeaderT<x>::getIddBoundImportRva() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_BOUND_IMPORT].VirtualAddress;
}
/**
* Returns the size of the current file's bound import directory.
* @return The size of the BoundImport directory.
**/
template<int x>
dword PeHeaderT<x>::getIddBoundImportSize() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_BOUND_IMPORT].Size;
}
/**
* Returns the relative virtual address of the current file's IAT directory.
* @return The Rva of the IAT directory.
**/
template<int x>
dword PeHeaderT<x>::getIddIatRva() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_IAT].VirtualAddress;
}
/**
* Returns the size of the current file's IAT directory.
* @return The size of the IAT directory.
**/
template<int x>
dword PeHeaderT<x>::getIddIatSize() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_IAT].Size;
}
/**
* Returns the relative virtual address of the current file's Delay Import directory.
* @return The Rva of the DelayImport directory.
**/
template<int x>
dword PeHeaderT<x>::getIddDelayImportRva() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_DELAY_IMPORT].VirtualAddress;
}
/**
* Returns the size of the current file's Delay Import directory.
* @return The size of the DelayImport directory.
**/
template<int x>
dword PeHeaderT<x>::getIddDelayImportSize() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_DELAY_IMPORT].Size;
}
/**
* Returns the relative virtual address of the current file's COM Descriptor directory.
* @return The Rva of the COM Descriptor directory.
**/
template<int x>
dword PeHeaderT<x>::getIddComHeaderRva() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_COM_DESCRIPTOR].VirtualAddress;
}
/**
* Returns the size of the current file's COM Descriptor directory.
* @return The Rva of the COM Descriptor directory.
**/
template<int x>
dword PeHeaderT<x>::getIddComHeaderSize() const
{
return m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_COM_DESCRIPTOR].Size;
}
/**
* Returns the relative virtual address of an image directory.
* @param dwDirectory The identifier of an image directory.
* @return The Rva of the image directory.
**/
template<int x>
dword PeHeaderT<x>::getImageDataDirectoryRva(dword dwDirectory) const
{
return m_inthHeader.dataDirectories[dwDirectory].VirtualAddress;
}
template<int x>
void PeHeaderT<x>::setImageDataDirectoryRva(dword dwDirectory, dword value)
{
m_inthHeader.dataDirectories[dwDirectory].VirtualAddress = value;
}
/**
* Returns the size of an image directory.
* @param dwDirectory The identifier of an image directory.
* @return The size of the image directory.
**/
template<int x>
dword PeHeaderT<x>::getImageDataDirectorySize(dword dwDirectory) const
{
return m_inthHeader.dataDirectories[dwDirectory].Size;
}
template<int x>
void PeHeaderT<x>::setImageDataDirectorySize(dword dwDirectory, dword value)
{
m_inthHeader.dataDirectories[dwDirectory].Size = value;
}
/**
* Returns the name of the section which is specified by the parameter wSectionnr.
* @param wSectionnr Index of the section.
* @return The name of the section.
**/
template<int x>
std::string PeHeaderT<x>::getSectionName(word wSectionnr) const
{
std::string sectionName = "";
for (unsigned int i=0;i<sizeof(m_vIsh[wSectionnr].Name);i++)
{
if (m_vIsh[wSectionnr].Name[i]) sectionName += m_vIsh[wSectionnr].Name[i];
}
return sectionName;
}
/**
* Returns the virtual size of the section which is specified by the parameter wSectionnr.
* @param wSectionnr Index of the section.
* @return The virtual size of the section.
**/
template<int x>
dword PeHeaderT<x>::getVirtualSize(word wSectionnr) const
{
return m_vIsh[wSectionnr].VirtualSize;
}
/**
* Returns the relative virtual address of the section which is specified by the parameter wSectionnr.
* @param wSectionnr Index of the section.
* @return The Rva of the section.
**/
template<int x>
dword PeHeaderT<x>::getVirtualAddress(word wSectionnr) const
{
return m_vIsh[wSectionnr].VirtualAddress;
}
/**
* Returns the size of raw data of the section which is specified by the parameter wSectionnr.
* @param wSectionnr Index of the section.
* @return The size of raw data of the section.
**/
template<int x>
dword PeHeaderT<x>::getSizeOfRawData(word wSectionnr) const
{
return m_vIsh[wSectionnr].SizeOfRawData;
}
/**
* Returns the file offset of the section which is specified by the parameter wSectionnr.
* @param wSectionnr Index of the section.
* @return The file offset of the section.
**/
template<int x>
dword PeHeaderT<x>::getPointerToRawData(word wSectionnr) const
{
return m_vIsh[wSectionnr].PointerToRawData;
}
/**
* Returns the pointer to relocations of the section which is specified by the parameter wSectionnr.
* @param wSectionnr Index of the section.
* @return The pointer to relocations of the section.
**/
template<int x>
dword PeHeaderT<x>::getPointerToRelocations(word wSectionnr) const
{
return m_vIsh[wSectionnr].PointerToRelocations;
}
/**
* Returns the poiner to line numbers of the section which is specified by the parameter wSectionnr.
* @param wSectionnr Index of the section.
* @return The pointer to line numbers of the section.
**/
template<int x>
dword PeHeaderT<x>::getPointerToLinenumbers(word wSectionnr) const
{
return m_vIsh[wSectionnr].PointerToLinenumbers;
}
/**
* Returns the number of relocations of the section which is specified by the parameter wSectionnr.
* @param wSectionnr Index of the section.
* @return The number of relocations of the section.
**/
template<int x>
dword PeHeaderT<x>::getNumberOfRelocations(word wSectionnr) const
{
return m_vIsh[wSectionnr].NumberOfRelocations;
}
/**
* Returns the number of line numbers of the section which is specified by the parameter wSectionnr.
* @param wSectionnr Index of the section.
* @return The number of line numbers of the section.
**/
template<int x>
dword PeHeaderT<x>::getNumberOfLinenumbers(word wSectionnr) const
{
return m_vIsh[wSectionnr].NumberOfLinenumbers;
}
/**
* Returns the characteristics of the section which is specified by the parameter wSectionnr.
* @param wSectionnr Index of the section.
* @return The characteristics of the section.
**/
template<int x>
dword PeHeaderT<x>::getCharacteristics(word wSectionnr) const
{
return m_vIsh[wSectionnr].Characteristics;
}
/**
* Changes the file's Nt signature.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setNtSignature(dword dwValue)
{
m_inthHeader.Signature = dwValue;
}
/**
* Changes the file's Machine.
* @param wValue New value.
**/
template<int x>
void PeHeaderT<x>::setMachine(word wValue)
{
m_inthHeader.FileHeader.Machine = wValue;
}
/**
* Changes the number of sections.
* @param wValue New value.
**/
template<int x>
void PeHeaderT<x>::setNumberOfSections(word wValue)
{
m_inthHeader.FileHeader.NumberOfSections = wValue;
}
/**
* Changes the file's TimeDateStamp.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setTimeDateStamp(dword dwValue)
{
m_inthHeader.FileHeader.TimeDateStamp = dwValue;
}
/**
* Changes the file's PointerToSymbolTable.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setPointerToSymbolTable(dword dwValue)
{
m_inthHeader.FileHeader.PointerToSymbolTable = dwValue;
}
/**
* Changes the file's NumberOfSymbols.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setNumberOfSymbols(dword dwValue)
{
m_inthHeader.FileHeader.NumberOfSymbols = dwValue;
}
/**
* Changes the file's SizeOfOptionalHeader.
* @param wValue New value.
**/
template<int x>
void PeHeaderT<x>::setSizeOfOptionalHeader(word wValue)
{
m_inthHeader.FileHeader.SizeOfOptionalHeader = wValue;
}
/**
* Changes the file's Characteristics.
* @param wValue New value.
**/
template<int x>
void PeHeaderT<x>::setCharacteristics(word wValue)
{
m_inthHeader.FileHeader.Characteristics = wValue;
}
/**
* Changes the file's Magic.
* @param wValue New value.
**/
template<int x>
void PeHeaderT<x>::setMagic(word wValue)
{
m_inthHeader.OptionalHeader.Magic = wValue;
}
/**
* Changes the file's MajorLinkerVersion.
* @param bValue New value.
**/
template<int x>
void PeHeaderT<x>::setMajorLinkerVersion(byte bValue)
{
m_inthHeader.OptionalHeader.MajorLinkerVersion = bValue;
}
/**
* Changes the file's MinorLinkerVersion.
* @param bValue New value.
**/
template<int x>
void PeHeaderT<x>::setMinorLinkerVersion(byte bValue)
{
m_inthHeader.OptionalHeader.MinorLinkerVersion = bValue;
}
/**
* Changes the file's SizeOfCode.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setSizeOfCode(dword dwValue)
{
m_inthHeader.OptionalHeader.SizeOfCode = dwValue;
}
/**
* Changes the file's SizeOfInitializedData.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setSizeOfInitializedData(dword dwValue)
{
m_inthHeader.OptionalHeader.SizeOfInitializedData = dwValue;
}
/**
* Changes the file's SizeOfUninitializedData.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setSizeOfUninitializedData(dword dwValue)
{
m_inthHeader.OptionalHeader.SizeOfUninitializedData = dwValue;
}
/**
* Changes the file's AddressOfEntryPoint.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setAddressOfEntryPoint(dword dwValue)
{
m_inthHeader.OptionalHeader.AddressOfEntryPoint = dwValue;
}
/**
* Changes the file's BaseOfCode.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setBaseOfCode(dword dwValue)
{
m_inthHeader.OptionalHeader.BaseOfCode = dwValue;
}
/**
* Changes the file's ImageBase.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setImageBase(typename FieldSizes<x>::VAR4_8 dwValue)
{
m_inthHeader.OptionalHeader.ImageBase = dwValue;
}
/**
* Changes the file's SectionAlignment.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setSectionAlignment(dword dwValue)
{
m_inthHeader.OptionalHeader.SectionAlignment = dwValue;
}
/**
* Changes the file's FileAlignment.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setFileAlignment(dword dwValue)
{
m_inthHeader.OptionalHeader.FileAlignment = dwValue;
}
/**
* Changes the file's MajorOperatingSystemVersion.
* @param wValue New value.
**/
template<int x>
void PeHeaderT<x>::setMajorOperatingSystemVersion(word wValue)
{
m_inthHeader.OptionalHeader.MajorOperatingSystemVersion = wValue;
}
/**
* Changes the file's MinorOperatingSystemVersion.
* @param wValue New value.
**/
template<int x>
void PeHeaderT<x>::setMinorOperatingSystemVersion(word wValue)
{
m_inthHeader.OptionalHeader.MinorOperatingSystemVersion = wValue;
}
/**
* Changes the file's MajorImageVersion.
* @param wValue New value.
**/
template<int x>
void PeHeaderT<x>::setMajorImageVersion(word wValue)
{
m_inthHeader.OptionalHeader.MajorImageVersion = wValue;
}
/**
* Changes the file's MinorImageVersion.
* @param wValue New value.
**/
template<int x>
void PeHeaderT<x>::setMinorImageVersion(word wValue)
{
m_inthHeader.OptionalHeader.MinorImageVersion = wValue;
}
/**
* Changes the file's MajorSubsystemVersion.
* @param wValue New value.
**/
template<int x>
void PeHeaderT<x>::setMajorSubsystemVersion(word wValue)
{
m_inthHeader.OptionalHeader.MajorSubsystemVersion = wValue;
}
/**
* Changes the file's MinorSubsystemVersion.
* @param wValue New value.
**/
template<int x>
void PeHeaderT<x>::setMinorSubsystemVersion(word wValue)
{
m_inthHeader.OptionalHeader.MinorSubsystemVersion = wValue;
}
/**
* Changes the file's Win32VersionValue.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setWin32VersionValue(dword dwValue)
{
m_inthHeader.OptionalHeader.Win32VersionValue = dwValue;
}
/**
* Changes the file's SizeOfImage.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setSizeOfImage(dword dwValue)
{
m_inthHeader.OptionalHeader.SizeOfImage = dwValue;
}
/**
* Changes the file's SizeOfHeaders.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setSizeOfHeaders(dword dwValue)
{
m_inthHeader.OptionalHeader.SizeOfHeaders = dwValue;
}
/**
* Changes the file's CheckSum.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setCheckSum(dword dwValue)
{
m_inthHeader.OptionalHeader.CheckSum = dwValue;
}
/**
* Changes the file's Subsystem.
* @param wValue New value.
**/
template<int x>
void PeHeaderT<x>::setSubsystem(word wValue)
{
m_inthHeader.OptionalHeader.Subsystem = wValue;
}
/**
* Changes the file's DllCharacteristics.
* @param wValue New value.
**/
template<int x>
void PeHeaderT<x>::setDllCharacteristics(word wValue)
{
m_inthHeader.OptionalHeader.DllCharacteristics = wValue;
}
/**
* Changes the file's SizeOfStackReserve.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setSizeOfStackReserve(typename FieldSizes<x>::VAR4_8 dwValue)
{
m_inthHeader.OptionalHeader.SizeOfStackReserve = dwValue;
}
/**
* Changes the file's SizeOfStackCommit.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setSizeOfStackCommit(typename FieldSizes<x>::VAR4_8 dwValue)
{
m_inthHeader.OptionalHeader.SizeOfStackCommit = dwValue;
}
/**
* Changes the file's SizeOfHeapReserve.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setSizeOfHeapReserve(typename FieldSizes<x>::VAR4_8 dwValue)
{
m_inthHeader.OptionalHeader.SizeOfHeapReserve = dwValue;
}
/**
* Changes the file's SizeOfHeapCommit.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setSizeOfHeapCommit(typename FieldSizes<x>::VAR4_8 dwValue)
{
m_inthHeader.OptionalHeader.SizeOfHeapCommit = dwValue;
}
/**
* Changes the file's LoaderFlags.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setLoaderFlags(dword dwValue)
{
m_inthHeader.OptionalHeader.LoaderFlags = dwValue;
}
/**
* Changes the file's NumberOfRvaAndSizes.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setNumberOfRvaAndSizes(dword dwValue)
{
m_inthHeader.OptionalHeader.NumberOfRvaAndSizes = dwValue;
}
template<int x>
void PeHeaderT<x>::setIddDebugRva(dword dwValue)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_DEBUG].VirtualAddress = dwValue;
}
template<int x>
void PeHeaderT<x>::setIddDebugSize(dword dwValue)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_DEBUG].Size = dwValue;
}
template<int x>
void PeHeaderT<x>::setIddDelayImportRva(dword dwValue)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_DELAY_IMPORT].VirtualAddress = dwValue;
}
template<int x>
void PeHeaderT<x>::setIddDelayImportSize(dword dwValue)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_DELAY_IMPORT].Size = dwValue;
}
template<int x>
void PeHeaderT<x>::setIddExceptionRva(dword dwValue)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_EXCEPTION].VirtualAddress = dwValue;
}
template<int x>
void PeHeaderT<x>::setIddExceptionSize(dword dwValue)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_EXCEPTION].Size = dwValue;
}
template<int x>
void PeHeaderT<x>::setIddGlobalPtrRva(dword dwValue)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_GLOBALPTR].VirtualAddress = dwValue;
}
template<int x>
void PeHeaderT<x>::setIddGlobalPtrSize(dword dwValue)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_GLOBALPTR].Size = dwValue;
}
template<int x>
void PeHeaderT<x>::setIddIatRva(dword dwValue)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_IAT].VirtualAddress = dwValue;
}
template<int x>
void PeHeaderT<x>::setIddIatSize(dword dwValue)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_IAT].Size = dwValue;
}
template<int x>
void PeHeaderT<x>::setIddLoadConfigRva(dword dwValue)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_LOAD_CONFIG].VirtualAddress = dwValue;
}
template<int x>
void PeHeaderT<x>::setIddLoadConfigSize(dword dwValue)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_LOAD_CONFIG].Size = dwValue;
}
template<int x>
void PeHeaderT<x>::setIddResourceRva(dword dwValue)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_RESOURCE].VirtualAddress = dwValue;
}
template<int x>
void PeHeaderT<x>::setIddResourceSize(dword dwValue)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_RESOURCE].Size = dwValue;
}
template<int x>
void PeHeaderT<x>::setIddSecurityRva(dword dwValue)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_SECURITY].VirtualAddress = dwValue;
}
template<int x>
void PeHeaderT<x>::setIddSecuritySize(dword dwValue)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_SECURITY].Size = dwValue;
}
template<int x>
void PeHeaderT<x>::setIddTlsRva(dword dwValue)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_TLS].VirtualAddress = dwValue;
}
template<int x>
void PeHeaderT<x>::setIddTlsSize(dword dwValue)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_TLS].Size = dwValue;
}
/**
* Changes the rva of the file's export directory.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setIddExportRva(dword dwValue)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_EXPORT].VirtualAddress = dwValue;
}
/**
* Changes the size of the file's export directory.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setIddExportSize(dword dwValue)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_EXPORT].Size = dwValue;
}
template<int x>
void PeHeaderT<x>::setIddBaseRelocRva(dword value)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress = value;
}
template<int x>
void PeHeaderT<x>::setIddBaseRelocSize(dword value)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_BASERELOC].Size = value;
}
template<int x>
void PeHeaderT<x>::setIddArchitectureRva(dword value)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_ARCHITECTURE].VirtualAddress = value;
}
template<int x>
void PeHeaderT<x>::setIddArchitectureSize(dword value)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_ARCHITECTURE].Size = value;
}
template<int x>
void PeHeaderT<x>::setIddComHeaderRva(dword value)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_COM_DESCRIPTOR].VirtualAddress = value;
}
template<int x>
void PeHeaderT<x>::setIddComHeaderSize(dword value)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_COM_DESCRIPTOR].Size = value;
}
/**
* Changes the rva of the file's import directory.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setIddImportRva(dword dwValue)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress = dwValue;
}
/**
* Changes the size of the file's import directory.
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setIddImportSize(dword dwValue)
{
m_inthHeader.dataDirectories[PELIB_IMAGE_DIRECTORY_ENTRY_IMPORT].Size = dwValue;
}
/**
* Changes the name of a section.
* @param wSectionnr Identifier of the section
* @param strName New name.
**/
template<int x>
void PeHeaderT<x>::setSectionName(word wSectionnr, std::string strName)
{
strncpy(reinterpret_cast<char*>(m_vIsh[wSectionnr].Name), strName.c_str(), sizeof(m_vIsh[wSectionnr].Name));
}
/**
* Changes the virtual size of a section.
* @param wSectionnr Identifier of the section
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setVirtualSize(word wSectionnr, dword dwValue)
{
m_vIsh[wSectionnr].VirtualSize = dwValue;
}
/**
* Changes the virtual address of a section.
* @param wSectionnr Identifier of the section
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setVirtualAddress(word wSectionnr, dword dwValue)
{
m_vIsh[wSectionnr].VirtualAddress = dwValue;
}
/**
* Changes the size of raw data of a section.
* @param wSectionnr Identifier of the section
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setSizeOfRawData(word wSectionnr, dword dwValue)
{
m_vIsh[wSectionnr].SizeOfRawData = dwValue;
}
/**
* Changes the size of raw data of a section.
* @param wSectionnr Identifier of the section
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setPointerToRawData(word wSectionnr, dword dwValue)
{
m_vIsh[wSectionnr].PointerToRawData = dwValue;
}
/**
* Changes the pointer to relocations of a section.
* @param wSectionnr Identifier of the section
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setPointerToRelocations(word wSectionnr, dword dwValue)
{
m_vIsh[wSectionnr].PointerToRelocations = dwValue;
}
/**
* Changes the pointer to line numbers of a section.
* @param wSectionnr Identifier of the section
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setPointerToLinenumbers(word wSectionnr, dword dwValue)
{
m_vIsh[wSectionnr].PointerToLinenumbers = dwValue;
}
/**
* Changes the number of relocations of a section.
* @param wSectionnr Identifier of the section
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setNumberOfRelocations(word wSectionnr, dword dwValue)
{
m_vIsh[wSectionnr].NumberOfRelocations = dwValue;
}
/**
* Changes the number of line numbers of a section.
* @param wSectionnr Identifier of the section
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setNumberOfLinenumbers(word wSectionnr, dword dwValue)
{
m_vIsh[wSectionnr].NumberOfLinenumbers = dwValue;
}
/**
* Changes the characteristics of a section.
* @param wSectionnr Identifier of the section
* @param dwValue New value.
**/
template<int x>
void PeHeaderT<x>::setCharacteristics(word wSectionnr, dword dwValue)
{
m_vIsh[wSectionnr].Characteristics = dwValue;
}
}
#endif