mirror of
https://github.com/hasherezade/bearparser
synced 2026-06-08 14:32:38 +00:00
138 lines
4.4 KiB
C++
138 lines
4.4 KiB
C++
#pragma once
|
|
#include <map>
|
|
#include <QMap>
|
|
|
|
#include "AbstractByteBuffer.h"
|
|
class Executable;
|
|
|
|
class ExeException : public CustomException
|
|
{
|
|
public:
|
|
ExeException(const QString info) : CustomException(info) {}
|
|
};
|
|
|
|
class ExeBuilder {
|
|
public:
|
|
ExeBuilder() {}
|
|
virtual ~ExeBuilder() {}
|
|
|
|
virtual bool signatureMatches(AbstractByteBuffer *buf) = 0;
|
|
virtual Executable* build(AbstractByteBuffer *buf) = 0;
|
|
virtual QString typeName() = 0;
|
|
};
|
|
|
|
//-------------------------------------------------------------
|
|
|
|
class Executable : public AbstractByteBuffer {
|
|
public:
|
|
enum exe_bits {
|
|
UNKNOWN = 0,
|
|
BITS_16 = 16,
|
|
BITS_32 = 32,
|
|
BITS_64 = 64,
|
|
};
|
|
|
|
enum exe_arch {
|
|
ARCH_UNKNOWN = 0,
|
|
ARCH_INTEL = 1,
|
|
ARCH_ARM = 2,
|
|
EXE_ARCH_COUNT
|
|
};
|
|
|
|
enum addr_type {
|
|
NOT_ADDR = 0,
|
|
RAW = 1,
|
|
RVA = 2,
|
|
VA = 3,
|
|
ADDR_TYPE_COUNT
|
|
};
|
|
|
|
static bool isBit64(Executable *exe) { return (!exe || exe->getBitMode() != Executable::BITS_64) ? false: true; }
|
|
static bool isBit32(Executable *exe) { return (!exe || exe->getBitMode() != Executable::BITS_32) ? false: true; }
|
|
|
|
bool isBit64() { return isBit64(this); }
|
|
bool isBit32() { return isBit32(this); }
|
|
|
|
virtual ~Executable(void) { }
|
|
|
|
virtual exe_bits getBitMode() { return this->bitMode; }
|
|
virtual exe_arch getArch() = 0;
|
|
|
|
virtual bufsize_t getContentSize() { return buf->getContentSize(); }
|
|
virtual BYTE* getContent() { return buf->getContent(); }
|
|
//wrapper:
|
|
virtual offset_t getRawSize() const { return static_cast<offset_t>(buf->getContentSize()); }
|
|
|
|
BYTE* getContentAtPtr(BYTE* ptr, bufsize_t size, bool allowExceptions = false) { return AbstractByteBuffer::getContentAtPtr(ptr, size, allowExceptions); }
|
|
BYTE* getContentAt(offset_t offset, bufsize_t size, bool allowExceptions = false) { return AbstractByteBuffer::getContentAt(offset, size, allowExceptions); }
|
|
|
|
virtual BYTE* getContentAt(offset_t offset, Executable::addr_type aType, bufsize_t size, bool allowExceptions = false);
|
|
//------------------------------
|
|
virtual bufsize_t getMappedSize(Executable::addr_type aType) = 0;
|
|
virtual bufsize_t getAlignment(Executable::addr_type aType) const = 0;
|
|
virtual offset_t getImageBase(bool recalculate = false) = 0;
|
|
virtual offset_t getEntryPoint(Executable::addr_type aType = Executable::RVA) = 0;
|
|
|
|
virtual bufsize_t getImageSize() { return getMappedSize(Executable::VA); }
|
|
|
|
/* All Entry Points of the application, including: main EP, Exports, TLS Callbacks */
|
|
virtual size_t getAllEntryPoints(QMap<offset_t,QString> &entrypoints, Executable::addr_type aType = Executable::RVA)
|
|
{
|
|
offset_t mainEP = getEntryPoint(aType);
|
|
entrypoints.insert(mainEP, "_start");
|
|
return 1;
|
|
}
|
|
|
|
/* conversions */
|
|
virtual bool isValidAddr(offset_t addr, addr_type addrType);
|
|
virtual bool isValidVA(offset_t va) { return isValidAddr(va, Executable::VA); }
|
|
|
|
virtual offset_t convertAddr(offset_t inAddr, Executable::addr_type inType, Executable::addr_type outType);
|
|
|
|
virtual offset_t toRaw(offset_t offset, addr_type addrType, bool allowExceptions = false); //any type of offset to raw
|
|
Executable::addr_type detectAddrType(offset_t addr, Executable::addr_type hintType); //TODO
|
|
|
|
// returns INVALID_ADDR if failed
|
|
// FileAddr <-> RVA
|
|
virtual offset_t rawToRva(offset_t raw) = 0;
|
|
virtual offset_t rvaToRaw(offset_t rva) = 0;
|
|
|
|
// VA <-> RVA
|
|
virtual offset_t VaToRva(offset_t va, bool autodetect = false);
|
|
|
|
virtual offset_t rvaToVa(offset_t rva)
|
|
{
|
|
return (rva == INVALID_ADDR) ? INVALID_ADDR : (rva + this->getImageBase());
|
|
}
|
|
|
|
// VA -> FileAddr
|
|
virtual offset_t vaToRaw(offset_t va)
|
|
{
|
|
if (va == INVALID_ADDR) return INVALID_ADDR;
|
|
|
|
offset_t rva = this->VaToRva(va, true);
|
|
return rvaToRaw(rva);
|
|
}
|
|
|
|
QString getFileName();
|
|
|
|
virtual bool resize(bufsize_t newSize) { return buf->resize(newSize); }
|
|
|
|
virtual bool isResized() { return buf ? buf->isResized() : false; }
|
|
|
|
virtual bool isTruncated() { return buf ? buf->isTruncated() : false; }
|
|
|
|
/* wrappers */
|
|
AbstractByteBuffer* getFileBuffer() const { return buf; }
|
|
bufsize_t getFileSize() const;
|
|
|
|
virtual bool dumpFragment(offset_t offset, bufsize_t size, QString fileName);
|
|
|
|
protected:
|
|
Executable(AbstractByteBuffer *v_buf, exe_bits v_bitMode);
|
|
|
|
exe_bits bitMode;
|
|
AbstractByteBuffer *buf;
|
|
};
|
|
|