Added clang-format spec - issue #35

This commit is contained in:
Jozef Kolek 2017-03-31 17:01:20 +02:00
parent e3f63e11cb
commit cb2fd5736f
8 changed files with 1648 additions and 1522 deletions

19
.clang-format Normal file
View File

@ -0,0 +1,19 @@
AlignEscapedNewlinesLeft: true
AllowShortFunctionsOnASingleLine: false
BinPackArguments: false
BinPackParameters: false
BreakBeforeBraces: Attach
ColumnLimit: 80
IndentCaseLabels: true
IndentWidth: 2
Language: Cpp
PointerAlignment: Right
SpaceAfterCStyleCast: true
SpaceBeforeAssignmentOperators: true
SpaceBeforeParens: ControlStatements
SpaceInEmptyParentheses: false
SpacesInCStyleCastParentheses: false
SpacesInParentheses: false
Standard: Cpp11
TabWidth: 2
UseTab: Never

View File

@ -22,9 +22,9 @@ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
*/
#include "parse.h"
#include <iostream>
#include <sstream>
#include "parse.h"
using namespace std;
using namespace peparse;
@ -81,8 +81,12 @@ int printRelocs(void *N, VA relocAddr, reloc_type type) {
return 0;
}
int printSymbols(void *N, std::string &strName, uint32_t &value,
int16_t &sectionNumber, uint16_t &type, uint8_t &storageClass,
int printSymbols(void *N,
std::string &strName,
uint32_t &value,
int16_t &sectionNumber,
uint16_t &type,
uint8_t &storageClass,
uint8_t &numberOfAuxSymbols) {
cout << "Symbol Name: " << strName << endl;
cout << "Symbol Value: 0x" << to_string<uint32_t>(value, hex) << endl;
@ -192,14 +196,13 @@ int printSymbols(void *N, std::string &strName, uint32_t &value,
}
cout << endl;
cout << "Symbol Number of Aux Symbols: " << (uint32_t) numberOfAuxSymbols << endl;
cout << "Symbol Number of Aux Symbols: " << (uint32_t) numberOfAuxSymbols
<< endl;
return 0;
}
int printRsrc(void *N,
resource r)
{
int printRsrc(void *N, resource r) {
if (r.type_str.length())
cout << "Type (string): " << r.type_str << endl;
else
@ -222,8 +225,7 @@ int printSecs(void *N,
VA secBase,
string &secName,
image_section_header s,
bounded_buffer *data)
{
bounded_buffer *data) {
cout << "Sec Name: " << secName << endl;
cout << "Sec Base: 0x" << to_string<uint64_t>(secBase, hex) << endl;
if (data)
@ -342,9 +344,9 @@ int main(int argc, char *argv[]) {
cout << "Resources: " << endl;
IterRsrc(p, printRsrc, NULL);
DestructParsedPE(p);
}
else {
cout << "Error: " << GetPEErr() << " (" << GetPEErrString() << ")" << endl;
} else {
cout << "Error: " << GetPEErr() << " (" << GetPEErrString() << ")"
<< endl;
cout << "Location: " << GetPEErrLoc() << endl;
}
}

View File

@ -22,17 +22,17 @@ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
*/
#include "parse.h"
#include <fstream>
#include <string.h>
#include "parse.h"
#ifdef WIN32
#include <windows.h>
#else
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/mman.h>
#include <fcntl.h>
#include <sys/mman.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
#endif

View File

@ -278,12 +278,8 @@ struct resource_dir_entry_sz {
};
struct resource_dir_entry {
inline resource_dir_entry(void)
: ID(0),
RVA(0),
type(0),
name(0),
lang(0) {}
inline resource_dir_entry(void) : ID(0), RVA(0), type(0), name(0), lang(0) {
}
std::uint32_t ID;
std::uint32_t RVA;

View File

@ -22,13 +22,13 @@ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
*/
#include <string.h>
#include <list>
#include <algorithm>
#include <stdexcept>
#include "parse.h"
#include "nt-headers.h"
#include "to_string.h"
#include <algorithm>
#include <list>
#include <stdexcept>
#include <string.h>
using namespace std;
@ -125,8 +125,7 @@ struct parsed_pe_internal {
::uint32_t err = 0;
std::string err_loc;
static const char *pe_err_str[] = {
"None",
static const char *pe_err_str[] = {"None",
"Out of memory",
"Invalid header",
"Invalid section",
@ -135,8 +134,7 @@ static const char *pe_err_str[] = {
"Unable to read data",
"Unable to open",
"Unable to stat",
"Bad magic"
};
"Bad magic"};
int GetPEErr() {
return err;
@ -150,9 +148,8 @@ string GetPEErrLoc() {
return err_loc;
}
static bool readCString(const bounded_buffer &buffer, ::uint32_t off,
string &result)
{
static bool
readCString(const bounded_buffer &buffer, ::uint32_t off, string &result) {
if (off < buffer.bufLen) {
::uint8_t *p = buffer.buf;
::uint32_t n = buffer.bufLen;
@ -210,7 +207,12 @@ bool parse_resource_id(bounded_buffer *data, ::uint32_t id, string &result) {
return true;
}
bool parse_resource_table(bounded_buffer *sectionData, ::uint32_t o, ::uint32_t virtaddr, ::uint32_t depth, resource_dir_entry *dirent, list<resource> &rsrcs) {
bool parse_resource_table(bounded_buffer *sectionData,
::uint32_t o,
::uint32_t virtaddr,
::uint32_t depth,
resource_dir_entry *dirent,
list<resource> &rsrcs) {
::uint32_t i = 0;
resource_dir_table rdt;
@ -245,21 +247,24 @@ bool parse_resource_table(bounded_buffer *sectionData, ::uint32_t o, ::uint32_t
if (depth == 0) {
rde->type = rde->ID;
if (i < rdt.NameEntries) {
if (!parse_resource_id(sectionData, rde->ID & 0x0FFFFFFF, rde->type_str)) {
if (!parse_resource_id(
sectionData, rde->ID & 0x0FFFFFFF, rde->type_str)) {
return false;
}
}
} else if (depth == 1) {
rde->name = rde->ID;
if (i < rdt.NameEntries) {
if (!parse_resource_id(sectionData, rde->ID & 0x0FFFFFFF, rde->name_str)) {
if (!parse_resource_id(
sectionData, rde->ID & 0x0FFFFFFF, rde->name_str)) {
return false;
}
}
} else if (depth == 2) {
rde->lang = rde->ID;
if (i < rdt.NameEntries) {
if (!parse_resource_id(sectionData, rde->ID & 0x0FFFFFFF, rde->lang_str)) {
if (!parse_resource_id(
sectionData, rde->ID & 0x0FFFFFFF, rde->lang_str)) {
return false;
}
}
@ -268,7 +273,12 @@ bool parse_resource_table(bounded_buffer *sectionData, ::uint32_t o, ::uint32_t
// High bit 0 = RVA to RDT.
// High bit 1 = RVA to RDE.
if (rde->RVA & 0x80000000) {
if (!parse_resource_table(sectionData, rde->RVA & 0x0FFFFFFF, virtaddr, depth + 1, rde, rsrcs)) {
if (!parse_resource_table(sectionData,
rde->RVA & 0x0FFFFFFF,
virtaddr,
depth + 1,
rde,
rsrcs)) {
return false;
}
} else {
@ -336,7 +346,10 @@ bool parse_resource_table(bounded_buffer *sectionData, ::uint32_t o, ::uint32_t
return true;
}
bool getResources(bounded_buffer *b, bounded_buffer *fileBegin, list<section> secs, list<resource> &rsrcs) {
bool getResources(bounded_buffer *b,
bounded_buffer *fileBegin,
list<section> secs,
list<resource> &rsrcs) {
if (b == nullptr)
return false;
@ -346,7 +359,8 @@ bool getResources(bounded_buffer *b, bounded_buffer *fileBegin, list<section> se
continue;
}
if (!parse_resource_table(s.sectionData, 0, s.sec.VirtualAddress, 0, nullptr, rsrcs)) {
if (!parse_resource_table(
s.sectionData, 0, s.sec.VirtualAddress, 0, nullptr, rsrcs)) {
return false;
}
@ -398,9 +412,11 @@ bool getSections( bounded_buffer *b,
}
if (nthdr.OptionalMagic == NT_OPTIONAL_32_MAGIC) {
thisSec.sectionBase = nthdr.OptionalHeader.ImageBase + curSec.VirtualAddress;
thisSec.sectionBase =
nthdr.OptionalHeader.ImageBase + curSec.VirtualAddress;
} else if (nthdr.OptionalMagic == NT_OPTIONAL_64_MAGIC) {
thisSec.sectionBase = nthdr.OptionalHeader64.ImageBase + curSec.VirtualAddress;
thisSec.sectionBase =
nthdr.OptionalHeader64.ImageBase + curSec.VirtualAddress;
} else {
PE_ERR(PEERR_MAGIC);
}
@ -658,10 +674,12 @@ bool getHeader(bounded_buffer *file, pe_header &p, bounded_buffer *&rem) {
::uint32_t rem_size;
if (p.nt.OptionalMagic == NT_OPTIONAL_32_MAGIC) {
// signature + file_header + optional_header_32
rem_size = sizeof(::uint32_t) + sizeof(file_header) + sizeof(optional_header_32);
rem_size =
sizeof(::uint32_t) + sizeof(file_header) + sizeof(optional_header_32);
} else if (p.nt.OptionalMagic == NT_OPTIONAL_64_MAGIC) {
// signature + file_header + optional_header_64
rem_size = sizeof(::uint32_t) + sizeof(file_header) + sizeof(optional_header_64);
rem_size =
sizeof(::uint32_t) + sizeof(file_header) + sizeof(optional_header_64);
} else {
PE_ERR(PEERR_MAGIC);
deleteBuffer(ntBuf);
@ -691,7 +709,8 @@ bool getExports(parsed_pe *p) {
if (p->peHeader.nt.OptionalMagic == NT_OPTIONAL_32_MAGIC) {
addr = exportDir.VirtualAddress + p->peHeader.nt.OptionalHeader.ImageBase;
} else if (p->peHeader.nt.OptionalMagic == NT_OPTIONAL_64_MAGIC) {
addr = exportDir.VirtualAddress + p->peHeader.nt.OptionalHeader64.ImageBase;
addr =
exportDir.VirtualAddress + p->peHeader.nt.OptionalHeader64.ImageBase;
} else {
return false;
}
@ -805,9 +824,11 @@ bool getExports(parsed_pe *p) {
VA ordinalTableVA;
if (p->peHeader.nt.OptionalMagic == NT_OPTIONAL_32_MAGIC) {
ordinalTableVA = ordinalTableRVA + p->peHeader.nt.OptionalHeader.ImageBase;
ordinalTableVA =
ordinalTableRVA + p->peHeader.nt.OptionalHeader.ImageBase;
} else if (p->peHeader.nt.OptionalMagic == NT_OPTIONAL_64_MAGIC) {
ordinalTableVA = ordinalTableRVA + p->peHeader.nt.OptionalHeader64.ImageBase;
ordinalTableVA =
ordinalTableRVA + p->peHeader.nt.OptionalHeader64.ImageBase;
} else {
return false;
}
@ -917,9 +938,11 @@ bool getRelocations(parsed_pe *p) {
section d;
VA vaAddr;
if (p->peHeader.nt.OptionalMagic == NT_OPTIONAL_32_MAGIC) {
vaAddr = relocDir.VirtualAddress + p->peHeader.nt.OptionalHeader.ImageBase;
vaAddr =
relocDir.VirtualAddress + p->peHeader.nt.OptionalHeader.ImageBase;
} else if (p->peHeader.nt.OptionalMagic == NT_OPTIONAL_64_MAGIC) {
vaAddr = relocDir.VirtualAddress + p->peHeader.nt.OptionalHeader64.ImageBase;
vaAddr =
relocDir.VirtualAddress + p->peHeader.nt.OptionalHeader64.ImageBase;
} else {
return false;
}
@ -975,7 +998,8 @@ bool getRelocations(parsed_pe *p) {
if (p->peHeader.nt.OptionalMagic == NT_OPTIONAL_32_MAGIC) {
relocVA = pageRva + offset + p->peHeader.nt.OptionalHeader.ImageBase;
} else if (p->peHeader.nt.OptionalMagic == NT_OPTIONAL_64_MAGIC) {
relocVA = pageRva + offset + p->peHeader.nt.OptionalHeader64.ImageBase;
relocVA =
pageRva + offset + p->peHeader.nt.OptionalHeader64.ImageBase;
} else {
return false;
}
@ -1013,7 +1037,8 @@ bool getImports(parsed_pe *p) {
if (p->peHeader.nt.OptionalMagic == NT_OPTIONAL_32_MAGIC) {
addr = importDir.VirtualAddress + p->peHeader.nt.OptionalHeader.ImageBase;
} else if (p->peHeader.nt.OptionalMagic == NT_OPTIONAL_64_MAGIC) {
addr = importDir.VirtualAddress + p->peHeader.nt.OptionalHeader64.ImageBase;
addr =
importDir.VirtualAddress + p->peHeader.nt.OptionalHeader64.ImageBase;
} else {
return false;
}
@ -1035,8 +1060,7 @@ bool getImports(parsed_pe *p) {
READ_DWORD(c.sectionData, offt, curEnt, AddressRVA);
// are all the fields in curEnt null? then we break
if (curEnt.LookupTableRVA == 0 &&
curEnt.NameRVA == 0 &&
if (curEnt.LookupTableRVA == 0 && curEnt.NameRVA == 0 &&
curEnt.AddressRVA == 0) {
break;
}
@ -1061,30 +1085,36 @@ bool getImports(parsed_pe *p) {
if (!readCString(*nameSec.sectionData, nameOff, modName)) {
return false;
}
std::transform(modName.begin(), modName.end(), modName.begin(), ::toupper);
std::transform(
modName.begin(), modName.end(), modName.begin(), ::toupper);
// then, try and get all of the sub-symbols
VA lookupVA = 0;
if (curEnt.LookupTableRVA != 0) {
if (p->peHeader.nt.OptionalMagic == NT_OPTIONAL_32_MAGIC) {
lookupVA = curEnt.LookupTableRVA + p->peHeader.nt.OptionalHeader.ImageBase;
lookupVA =
curEnt.LookupTableRVA + p->peHeader.nt.OptionalHeader.ImageBase;
} else if (p->peHeader.nt.OptionalMagic == NT_OPTIONAL_64_MAGIC) {
lookupVA = curEnt.LookupTableRVA + p->peHeader.nt.OptionalHeader64.ImageBase;
lookupVA =
curEnt.LookupTableRVA + p->peHeader.nt.OptionalHeader64.ImageBase;
} else {
return false;
}
} else if (curEnt.AddressRVA != 0) {
if (p->peHeader.nt.OptionalMagic == NT_OPTIONAL_32_MAGIC) {
lookupVA = curEnt.AddressRVA + p->peHeader.nt.OptionalHeader.ImageBase;
lookupVA =
curEnt.AddressRVA + p->peHeader.nt.OptionalHeader.ImageBase;
} else if (p->peHeader.nt.OptionalMagic == NT_OPTIONAL_64_MAGIC) {
lookupVA = curEnt.AddressRVA + p->peHeader.nt.OptionalHeader64.ImageBase;
lookupVA =
curEnt.AddressRVA + p->peHeader.nt.OptionalHeader64.ImageBase;
} else {
return false;
}
}
section lookupSec;
if (lookupVA == 0 || !getSecForVA(p->internal->secs, lookupVA, lookupSec)) {
if (lookupVA == 0 ||
!getSecForVA(p->internal->secs, lookupVA, lookupSec)) {
return false;
}
@ -1150,9 +1180,11 @@ bool getImports(parsed_pe *p) {
importent ent;
if (p->peHeader.nt.OptionalMagic == NT_OPTIONAL_32_MAGIC) {
ent.addr = offInTable + curEnt.AddressRVA + p->peHeader.nt.OptionalHeader.ImageBase;
ent.addr = offInTable + curEnt.AddressRVA +
p->peHeader.nt.OptionalHeader.ImageBase;
} else if (p->peHeader.nt.OptionalMagic == NT_OPTIONAL_64_MAGIC) {
ent.addr = offInTable + curEnt.AddressRVA + p->peHeader.nt.OptionalHeader64.ImageBase;
ent.addr = offInTable + curEnt.AddressRVA +
p->peHeader.nt.OptionalHeader64.ImageBase;
} else {
return false;
}
@ -1167,9 +1199,11 @@ bool getImports(parsed_pe *p) {
importent ent;
if (p->peHeader.nt.OptionalMagic == NT_OPTIONAL_32_MAGIC) {
ent.addr = offInTable + curEnt.AddressRVA + p->peHeader.nt.OptionalHeader.ImageBase;
ent.addr = offInTable + curEnt.AddressRVA +
p->peHeader.nt.OptionalHeader.ImageBase;
} else if (p->peHeader.nt.OptionalMagic == NT_OPTIONAL_64_MAGIC) {
ent.addr = offInTable + curEnt.AddressRVA + p->peHeader.nt.OptionalHeader64.ImageBase;
ent.addr = offInTable + curEnt.AddressRVA +
p->peHeader.nt.OptionalHeader64.ImageBase;
} else {
return false;
}
@ -1203,8 +1237,9 @@ bool getSymbolTable(parsed_pe *p) {
return true;
}
uint32_t strTableOffset = p->peHeader.nt.FileHeader.PointerToSymbolTable
+ (p->peHeader.nt.FileHeader.NumberOfSymbols * SYMTAB_RECORD_LEN);
uint32_t strTableOffset =
p->peHeader.nt.FileHeader.PointerToSymbolTable +
(p->peHeader.nt.FileHeader.NumberOfSymbols * SYMTAB_RECORD_LEN);
uint32_t offset = p->peHeader.nt.FileHeader.PointerToSymbolTable;
@ -1296,8 +1331,7 @@ bool getSymbolTable(parsed_pe *p) {
// Read auxiliary symbol records
if (sym.storageClass == IMAGE_SYM_CLASS_EXTERNAL &&
SYMBOL_TYPE_HI(sym) == 0x20 &&
sym.sectionNumber > 0) {
SYMBOL_TYPE_HI(sym) == 0x20 && sym.sectionNumber > 0) {
// Auxiliary Format 1: Function Definitions
for (uint8_t n = 0; n < sym.numberOfAuxSymbols; n++) {
@ -1369,8 +1403,7 @@ bool getSymbolTable(parsed_pe *p) {
sym.aux_symbols_f2.push_back(asym);
}
} else if (sym.storageClass == IMAGE_SYM_CLASS_EXTERNAL &&
sym.sectionNumber == IMAGE_SYM_UNDEFINED &&
sym.value == 0) {
sym.sectionNumber == IMAGE_SYM_UNDEFINED && sym.value == 0) {
// Auxiliary Format 3: Weak Externals
for (uint8_t n = 0; n < sym.numberOfAuxSymbols; n++) {
@ -1613,7 +1646,12 @@ void IterSymbols(parsed_pe *pe, iterSymbol cb, void *cbd) {
list<symbol> &l = pe->internal->symbols;
for (symbol s : l) {
if (cb(cbd, s.strName, s.value, s.sectionNumber, s.type, s.storageClass,
if (cb(cbd,
s.strName,
s.value,
s.sectionNumber,
s.type,
s.storageClass,
s.numberOfAuxSymbols) != 0) {
break;
}
@ -1668,9 +1706,11 @@ bool GetEntryPoint(parsed_pe *pe, VA &v) {
nt_header_32 *nthdr = &pe->peHeader.nt;
if (nthdr->OptionalMagic == NT_OPTIONAL_32_MAGIC) {
v = nthdr->OptionalHeader.AddressOfEntryPoint + nthdr->OptionalHeader.ImageBase;
v = nthdr->OptionalHeader.AddressOfEntryPoint +
nthdr->OptionalHeader.ImageBase;
} else if (nthdr->OptionalMagic == NT_OPTIONAL_64_MAGIC) {
v = nthdr->OptionalHeader64.AddressOfEntryPoint + nthdr->OptionalHeader64.ImageBase;
v = nthdr->OptionalHeader64.AddressOfEntryPoint +
nthdr->OptionalHeader64.ImageBase;
} else {
PE_ERR(PEERR_MAGIC);
return false;

View File

@ -24,8 +24,8 @@ THE SOFTWARE.
#ifndef _PARSE_H
#define _PARSE_H
#include <string>
#include <cstdint>
#include <string>
#include "nt-headers.h"
#include "to_string.h"
@ -34,7 +34,6 @@ THE SOFTWARE.
#define __typeof__(x) std::remove_reference < decltype(x) > ::type
#endif
#define PE_ERR(x) \
err = (pe_err) x; \
err_loc.assign(__func__); \
@ -148,15 +147,14 @@ bool readDword(bounded_buffer *b, std::uint32_t offset, std::uint32_t &out);
bool readQword(bounded_buffer *b, std::uint32_t offset, std::uint64_t &out);
bounded_buffer *readFileToFileBuffer(const char *filePath);
bounded_buffer *splitBuffer(bounded_buffer *b, std::uint32_t from, std::uint32_t to);
bounded_buffer *
splitBuffer(bounded_buffer *b, std::uint32_t from, std::uint32_t to);
void deleteBuffer(bounded_buffer *b);
uint64_t bufLen(bounded_buffer *b);
struct parsed_pe_internal;
typedef struct _pe_header {
nt_header_32 nt;
} pe_header;
typedef struct _pe_header { nt_header_32 nt; } pe_header;
typedef struct _parsed_pe {
bounded_buffer *fileBuffer;
@ -192,7 +190,13 @@ typedef int (*iterReloc)(void *, VA, reloc_type);
void IterRelocs(parsed_pe *pe, iterReloc cb, void *cbd);
// Iterate over symbols (symbol table) in the PE file
typedef int (*iterSymbol)(void *, std::string &, uint32_t &, int16_t &, uint16_t &, uint8_t &, uint8_t &);
typedef int (*iterSymbol)(void *,
std::string &,
uint32_t &,
int16_t &,
uint16_t &,
uint8_t &,
uint8_t &);
void IterSymbols(parsed_pe *pe, iterSymbol cb, void *cbd);
// iterate over the exports
@ -200,7 +204,8 @@ typedef int (*iterExp)(void *, VA, std::string &, std::string &);
void IterExpVA(parsed_pe *pe, iterExp cb, void *cbd);
// iterate over sections
typedef int (*iterSec)(void *, VA secBase, std::string &, image_section_header, bounded_buffer *b);
typedef int (*iterSec)(
void *, VA secBase, std::string &, image_section_header, bounded_buffer *b);
void IterSec(parsed_pe *pe, iterSec cb, void *cbd);
// get byte at VA in PE

View File

@ -4,8 +4,7 @@
namespace peparse {
template <class T>
static
std::string to_string(T t, std::ios_base & (*f)(std::ios_base&)) {
static std::string to_string(T t, std::ios_base &(*f)(std::ios_base &) ) {
std::ostringstream oss;
oss << f << t;
return oss.str();

View File

@ -25,9 +25,9 @@
* SUCH DAMAGE.
*/
#include "parse.h"
#include <Python.h>
#include <structmember.h>
#include "parse.h"
using namespace peparse;
@ -41,30 +41,26 @@ static PyObject *pepy_##OBJ##_get_##ATTR(PyObject *self, void *closure) { \
}
#define OBJECTGETTER(OBJ, ATTR, DOC) \
{ (char *) #ATTR, (getter) pepy_##OBJ##_get_##ATTR, \
(setter) pepy_attr_not_writable, \
(char *) #DOC, NULL }
{ \
(char *) #ATTR, (getter) pepy_##OBJ##_get_##ATTR, \
(setter) pepy_attr_not_writable, (char *) #DOC, NULL \
}
/* 'OPTIONAL' references the fact that these are from the Optional Header */
#define OBJECTGETTER_OPTIONAL(ATTR, DOC) \
{ (char *) #ATTR, (getter) pepy_parsed_get_optional_##ATTR, \
(setter) pepy_attr_not_writable, \
(char *) #DOC, NULL }
{ \
(char *) #ATTR, (getter) pepy_parsed_get_optional_##ATTR, \
(setter) pepy_attr_not_writable, (char *) #DOC, NULL \
}
static PyObject *pepy_error;
typedef struct {
PyObject_HEAD
} pepy;
typedef struct { PyObject_HEAD } pepy;
typedef struct { PyObject_HEAD parsed_pe *pe; } pepy_parsed;
typedef struct {
PyObject_HEAD
parsed_pe *pe;
} pepy_parsed;
typedef struct {
PyObject_HEAD
PyObject *name;
PyObject_HEAD PyObject *name;
PyObject *base;
PyObject *length;
PyObject *virtaddr;
@ -76,8 +72,7 @@ typedef struct {
} pepy_section;
typedef struct {
PyObject_HEAD
PyObject *type_str;
PyObject_HEAD PyObject *type_str;
PyObject *name_str;
PyObject *lang_str;
PyObject *type;
@ -90,32 +85,31 @@ typedef struct {
} pepy_resource;
typedef struct {
PyObject_HEAD
PyObject *name;
PyObject_HEAD PyObject *name;
PyObject *sym;
PyObject *addr;
} pepy_import;
typedef struct {
PyObject_HEAD
PyObject *mod;
PyObject_HEAD PyObject *mod;
PyObject *func;
PyObject *addr;
} pepy_export;
typedef struct {
PyObject_HEAD
PyObject *type;
PyObject_HEAD PyObject *type;
PyObject *addr;
} pepy_relocation;
/* None of the attributes in these objects are writable. */
static int pepy_attr_not_writable(PyObject *self, PyObject *value, void *closure) {
static int
pepy_attr_not_writable(PyObject *self, PyObject *value, void *closure) {
PyErr_SetString(PyExc_TypeError, "Attribute not writable.");
return -1;
}
static PyObject *pepy_import_new(PyTypeObject *type, PyObject *args, PyObject *kwds) {
static PyObject *
pepy_import_new(PyTypeObject *type, PyObject *args, PyObject *kwds) {
pepy_import *self;
self = (pepy_import *) type->tp_alloc(type, 0);
@ -124,7 +118,8 @@ static PyObject *pepy_import_new(PyTypeObject *type, PyObject *args, PyObject *k
}
static int pepy_import_init(pepy_import *self, PyObject *args, PyObject *kwds) {
if (!PyArg_ParseTuple(args, "OOO:pepy_import_init", &self->name, &self->sym, &self->addr))
if (!PyArg_ParseTuple(
args, "OOO:pepy_import_init", &self->name, &self->sym, &self->addr))
return -1;
return 0;
}
@ -144,12 +139,10 @@ static PyGetSetDef pepy_import_getseters[] = {
OBJECTGETTER(import, name, "Name"),
OBJECTGETTER(import, sym, "Symbol"),
OBJECTGETTER(import, addr, "Address"),
{ NULL }
};
{NULL}};
static PyTypeObject pepy_import_type = {
PyObject_HEAD_INIT(NULL)
0, /* ob_size */
PyObject_HEAD_INIT(NULL) 0, /* ob_size */
"pepy.import", /* tp_name */
sizeof(pepy_import), /* tp_basicsize */
0, /* tp_itemsize */
@ -189,7 +182,8 @@ static PyTypeObject pepy_import_type = {
pepy_import_new /* tp_new */
};
static PyObject *pepy_export_new(PyTypeObject *type, PyObject *args, PyObject *kwds) {
static PyObject *
pepy_export_new(PyTypeObject *type, PyObject *args, PyObject *kwds) {
pepy_export *self;
self = (pepy_export *) type->tp_alloc(type, 0);
@ -198,7 +192,8 @@ static PyObject *pepy_export_new(PyTypeObject *type, PyObject *args, PyObject *k
}
static int pepy_export_init(pepy_export *self, PyObject *args, PyObject *kwds) {
if (!PyArg_ParseTuple(args, "OOO:pepy_export_init", &self->mod, &self->func, &self->addr))
if (!PyArg_ParseTuple(
args, "OOO:pepy_export_init", &self->mod, &self->func, &self->addr))
return -1;
return 0;
}
@ -218,12 +213,10 @@ static PyGetSetDef pepy_export_getseters[] = {
OBJECTGETTER(export, mod, "Module"),
OBJECTGETTER(export, func, "Function"),
OBJECTGETTER(export, addr, "Address"),
{ NULL }
};
{NULL}};
static PyTypeObject pepy_export_type = {
PyObject_HEAD_INIT(NULL)
0, /* ob_size */
PyObject_HEAD_INIT(NULL) 0, /* ob_size */
"pepy.export", /* tp_name */
sizeof(pepy_export), /* tp_basicsize */
0, /* tp_itemsize */
@ -263,7 +256,8 @@ static PyTypeObject pepy_export_type = {
pepy_export_new /* tp_new */
};
static PyObject *pepy_relocation_new(PyTypeObject *type, PyObject *args, PyObject *kwds) {
static PyObject *
pepy_relocation_new(PyTypeObject *type, PyObject *args, PyObject *kwds) {
pepy_relocation *self;
self = (pepy_relocation *) type->tp_alloc(type, 0);
@ -271,8 +265,10 @@ static PyObject *pepy_relocation_new(PyTypeObject *type, PyObject *args, PyObjec
return (PyObject *) self;
}
static int pepy_relocation_init(pepy_relocation *self, PyObject *args, PyObject *kwds) {
if (!PyArg_ParseTuple(args, "OO:pepy_relocation_init", &self->type, &self->addr))
static int
pepy_relocation_init(pepy_relocation *self, PyObject *args, PyObject *kwds) {
if (!PyArg_ParseTuple(
args, "OO:pepy_relocation_init", &self->type, &self->addr))
return -1;
return 0;
}
@ -289,12 +285,10 @@ PEPY_OBJECT_GET(relocation, addr)
static PyGetSetDef pepy_relocation_getseters[] = {
OBJECTGETTER(relocation, type, "Type"),
OBJECTGETTER(relocation, addr, "Address"),
{ NULL }
};
{NULL}};
static PyTypeObject pepy_relocation_type = {
PyObject_HEAD_INIT(NULL)
0, /* ob_size */
PyObject_HEAD_INIT(NULL) 0, /* ob_size */
"pepy.relocation", /* tp_name */
sizeof(pepy_relocation), /* tp_basicsize */
0, /* tp_itemsize */
@ -334,7 +328,8 @@ static PyTypeObject pepy_relocation_type = {
pepy_relocation_new /* tp_new */
};
static PyObject *pepy_section_new(PyTypeObject *type, PyObject *args, PyObject *kwds) {
static PyObject *
pepy_section_new(PyTypeObject *type, PyObject *args, PyObject *kwds) {
pepy_section *self;
self = (pepy_section *) type->tp_alloc(type, 0);
@ -342,8 +337,19 @@ static PyObject *pepy_section_new(PyTypeObject *type, PyObject *args, PyObject *
return (PyObject *) self;
}
static int pepy_section_init(pepy_section *self, PyObject *args, PyObject *kwds) {
if (!PyArg_ParseTuple(args, "OOOOOOOOO:pepy_section_init", &self->name, &self->base, &self->length, &self->virtaddr, &self->virtsize, &self->numrelocs, &self->numlinenums, &self->characteristics, &self->data))
static int
pepy_section_init(pepy_section *self, PyObject *args, PyObject *kwds) {
if (!PyArg_ParseTuple(args,
"OOOOOOOOO:pepy_section_init",
&self->name,
&self->base,
&self->length,
&self->virtaddr,
&self->virtsize,
&self->numrelocs,
&self->numlinenums,
&self->characteristics,
&self->data))
return -1;
return 0;
}
@ -381,12 +387,10 @@ static PyGetSetDef pepy_section_getseters[] = {
OBJECTGETTER(section, numlinenums, "Number of line numbers"),
OBJECTGETTER(section, characteristics, "Characteristics"),
OBJECTGETTER(section, data, "Section data"),
{ NULL }
};
{NULL}};
static PyTypeObject pepy_section_type = {
PyObject_HEAD_INIT(NULL)
0, /* ob_size */
PyObject_HEAD_INIT(NULL) 0, /* ob_size */
"pepy.section", /* tp_name */
sizeof(pepy_section), /* tp_basicsize */
0, /* tp_itemsize */
@ -426,7 +430,8 @@ static PyTypeObject pepy_section_type = {
pepy_section_new /* tp_new */
};
static PyObject *pepy_resource_new(PyTypeObject *type, PyObject *args, PyObject *kwds) {
static PyObject *
pepy_resource_new(PyTypeObject *type, PyObject *args, PyObject *kwds) {
pepy_resource *self;
self = (pepy_resource *) type->tp_alloc(type, 0);
@ -434,8 +439,20 @@ static PyObject *pepy_resource_new(PyTypeObject *type, PyObject *args, PyObject
return (PyObject *) self;
}
static int pepy_resource_init(pepy_resource *self, PyObject *args, PyObject *kwds) {
if (!PyArg_ParseTuple(args, "OOOOOOOOOO:pepy_resource_init", &self->type_str, &self->name_str, &self->lang_str, &self->type, &self->name, &self->lang, &self->codepage, &self->RVA, &self->size, &self->data))
static int
pepy_resource_init(pepy_resource *self, PyObject *args, PyObject *kwds) {
if (!PyArg_ParseTuple(args,
"OOOOOOOOOO:pepy_resource_init",
&self->type_str,
&self->name_str,
&self->lang_str,
&self->type,
&self->name,
&self->lang,
&self->codepage,
&self->RVA,
&self->size,
&self->data))
return -1;
return 0;
@ -557,10 +574,11 @@ static PyObject *pepy_resource_type_as_str(PyObject *self, PyObject *args) {
}
static PyMethodDef pepy_resource_methods[] = {
{ "type_as_str", pepy_resource_type_as_str, METH_NOARGS,
{"type_as_str",
pepy_resource_type_as_str,
METH_NOARGS,
"Return the resource type as a string."},
{ NULL }
};
{NULL}};
static PyGetSetDef pepy_resource_getseters[] = {
OBJECTGETTER(resource, type_str, "Type string"),
@ -573,12 +591,10 @@ static PyGetSetDef pepy_resource_getseters[] = {
OBJECTGETTER(resource, RVA, "RVA"),
OBJECTGETTER(resource, size, "Size (specified in RDAT)"),
OBJECTGETTER(resource, data, "Resource data"),
{ NULL }
};
{NULL}};
static PyTypeObject pepy_resource_type = {
PyObject_HEAD_INIT(NULL)
0, /* ob_size */
PyObject_HEAD_INIT(NULL) 0, /* ob_size */
"pepy.resource", /* tp_name */
sizeof(pepy_resource), /* tp_basicsize */
0, /* tp_itemsize */
@ -618,7 +634,8 @@ static PyTypeObject pepy_resource_type = {
pepy_resource_new /* tp_new */
};
static PyObject *pepy_parsed_new(PyTypeObject *type, PyObject *args, PyObject *kwds) {
static PyObject *
pepy_parsed_new(PyTypeObject *type, PyObject *args, PyObject *kwds) {
pepy_parsed *self;
self = (pepy_parsed *) type->tp_alloc(type, 0);
@ -731,8 +748,7 @@ static PyObject *pepy_data_converter(bounded_buffer *data) {
if (!data || !data->buf) {
str = "";
len = 0;
}
else {
} else {
str = (const char *) data->buf;
len = data->bufLen;
}
@ -746,7 +762,11 @@ static PyObject *pepy_data_converter(bounded_buffer *data) {
return ret;
}
int section_callback(void *cbd, VA base, std::string &name, image_section_header s, bounded_buffer *data) {
int section_callback(void *cbd,
VA base,
std::string &name,
image_section_header s,
bounded_buffer *data) {
uint32_t buflen;
PyObject *sect;
PyObject *tuple;
@ -771,10 +791,17 @@ int section_callback(void *cbd, VA base, std::string &name, image_section_header
* The tuple item order is important here. It is passed into the
* section type initialization and parsed there.
*/
tuple = Py_BuildValue("sKKIIHHIO&", name.c_str(), base, buflen,
s.VirtualAddress, s.Misc.VirtualSize,
s.NumberOfRelocations, s.NumberOfLinenumbers,
s.Characteristics, pepy_data_converter, data);
tuple = Py_BuildValue("sKKIIHHIO&",
name.c_str(),
base,
buflen,
s.VirtualAddress,
s.Misc.VirtualSize,
s.NumberOfRelocations,
s.NumberOfLinenumbers,
s.Characteristics,
pepy_data_converter,
data);
if (!tuple)
return 1;
@ -819,7 +846,21 @@ int resource_callback(void *cbd, resource r) {
* The tuple item order is important here. It is passed into the
* section type initialization and parsed there.
*/
tuple = Py_BuildValue("s#s#s#IIIIIIO&", r.type_str.c_str(), r.type_str.length(), r.name_str.c_str(), r.name_str.length(), r.lang_str.c_str(), r.lang_str.length(), r.type, r.name, r.lang, r.codepage, r.RVA, r.size, pepy_data_converter, r.buf);
tuple = Py_BuildValue("s#s#s#IIIIIIO&",
r.type_str.c_str(),
r.type_str.length(),
r.name_str.c_str(),
r.name_str.length(),
r.lang_str.c_str(),
r.lang_str.length(),
r.type,
r.name,
r.lang,
r.codepage,
r.RVA,
r.size,
pepy_data_converter,
r.buf);
if (!tuple)
return 1;
@ -996,7 +1037,8 @@ static PyObject *pepy_parsed_get_relocations(PyObject *self, PyObject *args) {
#define PEPY_PARSED_GET(ATTR, VAL) \
static PyObject *pepy_parsed_get_##ATTR(PyObject *self, void *closure) { \
PyObject *ret = PyInt_FromLong(((pepy_parsed *) self)->pe->peHeader.nt.VAL); \
PyObject *ret = \
PyInt_FromLong(((pepy_parsed *) self)->pe->peHeader.nt.VAL); \
if (!ret) \
PyErr_SetString(PyExc_AttributeError, "Error getting attribute."); \
return ret; \
@ -1018,14 +1060,19 @@ PEPY_PARSED_GET(magic, OptionalMagic)
* This is why "magic" is handled above, and not here.
*/
#define PEPY_PARSED_GET_OPTIONAL(ATTR, VAL) \
static PyObject *pepy_parsed_get_optional_##ATTR(PyObject *self, void *closure) { \
static PyObject *pepy_parsed_get_optional_##ATTR(PyObject *self, \
void *closure) { \
PyObject *ret = NULL; \
if (((pepy_parsed *) self)->pe->peHeader.nt.OptionalMagic == NT_OPTIONAL_32_MAGIC) { \
ret = PyInt_FromLong(((pepy_parsed *) self)->pe->peHeader.nt.OptionalHeader.VAL); \
if (((pepy_parsed *) self)->pe->peHeader.nt.OptionalMagic == \
NT_OPTIONAL_32_MAGIC) { \
ret = PyInt_FromLong( \
((pepy_parsed *) self)->pe->peHeader.nt.OptionalHeader.VAL); \
if (!ret) \
PyErr_SetString(PyExc_AttributeError, "Error getting attribute."); \
} else if (((pepy_parsed *) self)->pe->peHeader.nt.OptionalMagic == NT_OPTIONAL_64_MAGIC) { \
ret = PyInt_FromLong(((pepy_parsed *) self)->pe->peHeader.nt.OptionalHeader64.VAL); \
} else if (((pepy_parsed *) self)->pe->peHeader.nt.OptionalMagic == \
NT_OPTIONAL_64_MAGIC) { \
ret = PyInt_FromLong( \
((pepy_parsed *) self)->pe->peHeader.nt.OptionalHeader64.VAL); \
if (!ret) \
PyErr_SetString(PyExc_AttributeError, "Error getting attribute."); \
} else { \
@ -1063,13 +1110,17 @@ PEPY_PARSED_GET_OPTIONAL(rvasandsize, NumberOfRvaAndSizes);
* BaseOfData is only in PE32, not PE32+. Thus, it uses a non-standard
* getter function compared to the other shared fields.
*/
static PyObject *pepy_parsed_get_optional_baseofdata(PyObject *self, void *closure) {
static PyObject *pepy_parsed_get_optional_baseofdata(PyObject *self,
void *closure) {
PyObject *ret = NULL;
if (((pepy_parsed *) self)->pe->peHeader.nt.OptionalMagic == NT_OPTIONAL_32_MAGIC) {
ret = PyInt_FromLong(((pepy_parsed *) self)->pe->peHeader.nt.OptionalHeader.BaseOfData);
if (((pepy_parsed *) self)->pe->peHeader.nt.OptionalMagic ==
NT_OPTIONAL_32_MAGIC) {
ret = PyInt_FromLong(
((pepy_parsed *) self)->pe->peHeader.nt.OptionalHeader.BaseOfData);
if (!ret)
PyErr_SetString(PyExc_AttributeError, "Error getting attribute.");
} else if (((pepy_parsed *) self)->pe->peHeader.nt.OptionalMagic == NT_OPTIONAL_64_MAGIC) {
} else if (((pepy_parsed *) self)->pe->peHeader.nt.OptionalMagic ==
NT_OPTIONAL_64_MAGIC) {
PyErr_SetString(PyExc_AttributeError, "Not available on PE32+.");
} else {
PyErr_SetString(pepy_error, "Bad magic value.");
@ -1110,33 +1161,46 @@ static PyGetSetDef pepy_parsed_getseters[] = {
OBJECTGETTER_OPTIONAL(loaderflags, "Loader flags"),
OBJECTGETTER_OPTIONAL(rvasandsize, "Number of RVA and sizes"),
/* Base of data is only available in PE32, not PE32+. */
{ (char *) "baseofdata", (getter) pepy_parsed_get_optional_baseofdata,
{(char *) "baseofdata",
(getter) pepy_parsed_get_optional_baseofdata,
(setter) pepy_attr_not_writable,
(char *) "Base address of data", NULL },
{ NULL }
};
(char *) "Base address of data",
NULL},
{NULL}};
static PyMethodDef pepy_parsed_methods[] = {
{ "get_entry_point", pepy_parsed_get_entry_point, METH_NOARGS,
{"get_entry_point",
pepy_parsed_get_entry_point,
METH_NOARGS,
"Return the entry point address."},
{ "get_bytes", pepy_parsed_get_bytes, METH_VARARGS,
{"get_bytes",
pepy_parsed_get_bytes,
METH_VARARGS,
"Return the first N bytes at a given address."},
{ "get_sections", pepy_parsed_get_sections, METH_NOARGS,
{"get_sections",
pepy_parsed_get_sections,
METH_NOARGS,
"Return a list of section objects."},
{ "get_imports", pepy_parsed_get_imports, METH_NOARGS,
{"get_imports",
pepy_parsed_get_imports,
METH_NOARGS,
"Return a list of import objects."},
{ "get_exports", pepy_parsed_get_exports, METH_NOARGS,
{"get_exports",
pepy_parsed_get_exports,
METH_NOARGS,
"Return a list of export objects."},
{ "get_relocations", pepy_parsed_get_relocations, METH_NOARGS,
{"get_relocations",
pepy_parsed_get_relocations,
METH_NOARGS,
"Return a list of relocation objects."},
{ "get_resources", pepy_parsed_get_resources, METH_NOARGS,
{"get_resources",
pepy_parsed_get_resources,
METH_NOARGS,
"Return a list of resource objects."},
{ NULL }
};
{NULL}};
static PyTypeObject pepy_parsed_type = {
PyObject_HEAD_INIT(NULL)
0, /* ob_size */
PyObject_HEAD_INIT(NULL) 0, /* ob_size */
"pepy.parsed", /* tp_name */
sizeof(pepy_parsed), /* tp_basicsize */
0, /* tp_itemsize */
@ -1195,10 +1259,13 @@ static PyObject *pepy_parse(PyObject *self, PyObject *args) {
err_str = (char *) malloc(len);
if (!err_str)
return PyErr_NoMemory();
snprintf(err_str, len, "%s (%s)", GetPEErrString().c_str(), GetPEErrLoc().c_str());
snprintf(err_str,
len,
"%s (%s)",
GetPEErrString().c_str(),
GetPEErrLoc().c_str());
PyErr_SetString(pepy_error, err_str);
}
else
} else
PyErr_SetString(pepy_error, "Unable to init new parsed object.");
return NULL;
}
@ -1207,9 +1274,7 @@ static PyObject *pepy_parse(PyObject *self, PyObject *args) {
}
static PyMethodDef pepy_methods[] = {
{ "parse", pepy_parse, METH_VARARGS, "Parse PE from file." },
{ NULL }
};
{"parse", pepy_parse, METH_VARARGS, "Parse PE from file."}, {NULL}};
PyMODINIT_FUNC initpepy(void) {
PyObject *m;