WIP: More GUI work, use shared_ptr to store Function references.
This commit is contained in:
@@ -3,7 +3,7 @@
|
||||
/* CALL GRAPH NODE */
|
||||
struct CALL_GRAPH
|
||||
{
|
||||
ilFunction proc; /* Pointer to procedure in pProcList */
|
||||
PtrFunction proc; /* Pointer to procedure in pProcList */
|
||||
std::vector<CALL_GRAPH *> outEdges; /* array of out edges */
|
||||
public:
|
||||
void write();
|
||||
@@ -12,8 +12,8 @@ public:
|
||||
}
|
||||
public:
|
||||
void writeNodeCallGraph(int indIdx);
|
||||
bool insertCallGraph(ilFunction caller, ilFunction callee);
|
||||
bool insertCallGraph(Function *caller, ilFunction callee);
|
||||
void insertArc(ilFunction newProc);
|
||||
bool insertCallGraph(PtrFunction caller, PtrFunction callee);
|
||||
//bool insertCallGraph(PtrFunction caller, PtrFunction callee);
|
||||
void insertArc(PtrFunction newProc);
|
||||
};
|
||||
//extern CALL_GRAPH * callGraph; /* Pointer to the head of the call graph */
|
||||
|
||||
@@ -1,5 +1,8 @@
|
||||
#pragma once
|
||||
#include <QtCore/QObject>
|
||||
#include "src/Command.h"
|
||||
#include "project.h"
|
||||
|
||||
class Project;
|
||||
class DccFrontend : public QObject
|
||||
{
|
||||
@@ -14,3 +17,28 @@ signals:
|
||||
|
||||
public slots:
|
||||
};
|
||||
|
||||
struct MachineStateInitialization : public Command {
|
||||
|
||||
MachineStateInitialization() : Command("Initialize simulated machine state",eProject) {}
|
||||
bool execute(CommandContext *ctx) override;
|
||||
};
|
||||
|
||||
struct FindMain : public Command {
|
||||
FindMain() : Command("Locate the main entry point",eProject) {}
|
||||
bool execute(CommandContext *ctx);
|
||||
};
|
||||
|
||||
struct CreateFunction : public Command {
|
||||
QString m_name;
|
||||
SegOffAddr m_addr;
|
||||
FunctionType *m_type;
|
||||
CreateFunction(QString name,SegOffAddr address,FunctionType *f) : Command("Create function",eProject),
|
||||
m_name(name),
|
||||
m_addr(address),
|
||||
m_type(f)
|
||||
{}
|
||||
QString instanceDescription() const override;
|
||||
|
||||
bool execute(CommandContext *ctx) override;
|
||||
};
|
||||
|
||||
@@ -7,7 +7,8 @@
|
||||
#include "CallConvention.h"
|
||||
|
||||
#include <llvm/ADT/ilist.h>
|
||||
//#include <llvm/ADT/ilist_node.h>
|
||||
#include <memory>
|
||||
#include <stdint.h>
|
||||
#include <QtCore/QString>
|
||||
#include <bitset>
|
||||
#include <map>
|
||||
@@ -22,7 +23,7 @@ struct Disassembler;
|
||||
struct Function;
|
||||
struct CALL_GRAPH;
|
||||
struct PROG;
|
||||
|
||||
struct IStructuredTextTarget;
|
||||
struct Function;
|
||||
|
||||
namespace llvm
|
||||
@@ -55,15 +56,11 @@ enum PROC_FLAGS
|
||||
PROC_IJMP =0x00000200,/* Proc incomplete due to indirect jmp */
|
||||
PROC_ICALL =0x00000400, /* Proc incomplete due to indirect call */
|
||||
PROC_HLL =0x00001000, /* Proc is likely to be from a HLL */
|
||||
// CALL_PASCAL =0x00002000, /* Proc uses Pascal calling convention */
|
||||
// CALL_C =0x00004000, /* Proc uses C calling convention */
|
||||
// CALL_UNKNOWN=0x00008000, /* Proc uses unknown calling convention */
|
||||
PROC_NEAR =0x00010000, /* Proc exits with near return */
|
||||
PROC_FAR =0x00020000, /* Proc exits with far return */
|
||||
GRAPH_IRRED =0x00100000, /* Proc generates an irreducible graph */
|
||||
SI_REGVAR =0x00200000, /* SI is used as a stack variable */
|
||||
DI_REGVAR =0x00400000, /* DI is used as a stack variable */
|
||||
//PROC_IS_FUNC=0x00800000, /* Proc is a function - determined by return type */
|
||||
REG_ARGS =0x01000000, /* Proc has registers as arguments */
|
||||
// PROC_VARARG =0x02000000, /* Proc has variable arguments */
|
||||
PROC_OUTPUT =0x04000000, /* C for this proc has been output */
|
||||
@@ -146,7 +143,15 @@ public:
|
||||
}
|
||||
void push_back(BB *v) { m_listBB.push_back(v);}
|
||||
};
|
||||
struct Function : public llvm::ilist_node<Function>
|
||||
typedef std::shared_ptr<struct Function> PtrFunction;
|
||||
enum DecompilationStep : uint32_t {
|
||||
eNotDecoded, // no processing done yet
|
||||
eDisassemblyInProgress,
|
||||
eDissassembled, // low level disassembly done
|
||||
//eStackTracing, // tracing stack depth across function calls
|
||||
|
||||
};
|
||||
struct Function : public std::enable_shared_from_this<Function>
|
||||
{
|
||||
typedef llvm::iplist<BB> BasicBlockListType;
|
||||
// BasicBlock iterators...
|
||||
@@ -154,7 +159,7 @@ struct Function : public llvm::ilist_node<Function>
|
||||
typedef BasicBlockListType::const_iterator const_iterator;
|
||||
protected:
|
||||
BasicBlockListType BasicBlocks; ///< The basic blocks
|
||||
Function(FunctionType *ty) : procEntry(0),depth(0),flg(0),cbParam(0),m_dfsLast(0),numBBs(0),
|
||||
Function(FunctionType *ty) : nStep(eNotDecoded),procEntry(0),depth(0),flg(0),cbParam(0),m_dfsLast(0),numBBs(0),
|
||||
hasCase(false),liveAnal(0)
|
||||
{
|
||||
type = ty;
|
||||
@@ -164,16 +169,16 @@ protected:
|
||||
}
|
||||
|
||||
public:
|
||||
int nStep; // decompilation step number for this function
|
||||
DecompilationStep nStep; // decompilation step number for this function
|
||||
FunctionType * type;
|
||||
uint32_t procEntry; /* label number */
|
||||
QString name; /* Meaningful name for this proc */
|
||||
STATE state; /* Entry state */
|
||||
int depth; /* Depth at which we found it - for printing */
|
||||
uint32_t flg; /* Combination of Icode & Proc flags */
|
||||
int16_t cbParam; /* Probable no. of bytes of parameters */
|
||||
STKFRAME args; /* Array of arguments */
|
||||
LOCAL_ID localId; /* Local identifiers */
|
||||
int depth; /* Depth at which we found it - for printing */
|
||||
uint32_t flg; /* Combination of Icode & Proc flags */
|
||||
int16_t cbParam; /* Probable no. of bytes of parameters */
|
||||
STKFRAME args; /* Array of arguments */
|
||||
LOCAL_ID localId; /* Local identifiers */
|
||||
|
||||
/* Icodes and control flow graph */
|
||||
CIcodeRec Icode; /* Object with ICODE records */
|
||||
@@ -193,9 +198,9 @@ public:
|
||||
delete type;
|
||||
}
|
||||
public:
|
||||
static Function *Create(FunctionType *ty=0,int /*Linkage*/=0,const QString &nm="",void */*module*/=0)
|
||||
static PtrFunction Create(FunctionType *ty=0,int /*Linkage*/=0,const QString &nm="",void */*module*/=0)
|
||||
{
|
||||
Function *r=new Function(ty);
|
||||
PtrFunction r(new Function(ty));
|
||||
r->name = nm;
|
||||
return r;
|
||||
}
|
||||
@@ -237,6 +242,7 @@ public:
|
||||
void controlFlowAnalysis();
|
||||
void newRegArg(iICODE picode, iICODE ticode);
|
||||
void writeProcComments(QTextStream & ostr);
|
||||
void toStructuredText(IStructuredTextTarget *out,int level);
|
||||
|
||||
void displayCFG();
|
||||
void displayStats();
|
||||
@@ -277,31 +283,13 @@ protected:
|
||||
void genLiveKtes();
|
||||
bool findDerivedSeq(derSeq &derivedGi);
|
||||
bool nextOrderGraph(derSeq &derivedGi);
|
||||
void addOutEdgesForConditionalJump(BB* pBB, int next_ip, LLInst *ll);
|
||||
void addOutEdgesForConditionalJump(BB* pBB, int next_ip, LLInst *ll);
|
||||
|
||||
private:
|
||||
bool decodeIndirectJMP(ICODE &pIcode, STATE *pstate, CALL_GRAPH *pcallGraph);
|
||||
bool decodeIndirectJMP2(ICODE &pIcode, STATE *pstate, CALL_GRAPH *pcallGraph);
|
||||
};
|
||||
namespace llvm {
|
||||
template<> struct ilist_traits<typename ::Function>
|
||||
: public ilist_default_traits<typename ::Function> {
|
||||
|
||||
// createSentinel is used to get hold of the node that marks the end of the
|
||||
// list... (same trick used here as in ilist_traits<Instruction>)
|
||||
typename ::Function *createSentinel() const {
|
||||
return static_cast<typename ::Function*>(&Sentinel);
|
||||
}
|
||||
static void destroySentinel(typename ::Function*) {}
|
||||
|
||||
typename ::Function *provideInitialHead() const { return createSentinel(); }
|
||||
typename ::Function *ensureHead(::Function*) const { return createSentinel(); }
|
||||
static void noteHead(typename ::Function*, typename ::Function*) {}
|
||||
|
||||
private:
|
||||
mutable ilist_node<typename ::Function> Sentinel;
|
||||
};
|
||||
}
|
||||
typedef llvm::iplist<Function> FunctionListType;
|
||||
typedef std::list<PtrFunction> FunctionListType;
|
||||
typedef FunctionListType lFunction;
|
||||
typedef lFunction::iterator ilFunction;
|
||||
|
||||
@@ -10,11 +10,11 @@ struct STKFRAME : public SymbolTableCommon<STKSYM>
|
||||
//std::vector<STKSYM> sym;
|
||||
//STKSYM * sym; /* Symbols */
|
||||
int16_t m_minOff; /* Initial offset in stack frame*/
|
||||
int16_t maxOff; /* Maximum offset in stack frame*/
|
||||
int16_t m_maxOff; /* Maximum offset in stack frame*/
|
||||
int cb; /* Number of bytes in arguments */
|
||||
int numArgs; /* No. of arguments in the table*/
|
||||
void adjustForArgType(size_t numArg_, hlType actType_);
|
||||
STKFRAME() : m_minOff(0),maxOff(0),cb(0),numArgs(0)
|
||||
STKFRAME() : m_minOff(0),m_maxOff(0),cb(0),numArgs(0)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
@@ -84,7 +84,7 @@ void parse (CALL_GRAPH * *); /* parser.c */
|
||||
|
||||
extern int strSize (const uint8_t *, char); /* parser.c */
|
||||
//void disassem(int pass, Function * pProc); /* disassem.c */
|
||||
void interactDis(Function *, int initIC); /* disassem.c */
|
||||
void interactDis(const PtrFunction &, int initIC); /* disassem.c */
|
||||
bool JmpInst(llIcode opcode); /* idioms.c */
|
||||
queue::iterator appendQueue(queue &Q, BB *node); /* reducible.c */
|
||||
|
||||
|
||||
@@ -11,10 +11,7 @@ struct IDcc {
|
||||
static IDcc *get();
|
||||
virtual void BaseInit()=0;
|
||||
virtual void Init(QObject *tgt)=0;
|
||||
virtual ilFunction GetFirstFuncHandle()=0;
|
||||
virtual ilFunction GetNextFuncHandle(ilFunction iter)=0;
|
||||
virtual ilFunction GetCurFuncHandle()=0;
|
||||
virtual bool isValidFuncHandle(ilFunction) = 0;
|
||||
virtual PtrFunction GetCurFuncHandle()=0;
|
||||
virtual void analysis_Once()=0;
|
||||
virtual bool load(QString name)=0; // load and preprocess -> find entry point
|
||||
virtual void prtout_asm(IStructuredTextTarget *,int level=0)=0;
|
||||
|
||||
@@ -7,12 +7,16 @@
|
||||
#pragma once
|
||||
#include "bundle.h"
|
||||
|
||||
#include <memory>
|
||||
#include <fstream>
|
||||
#include <vector>
|
||||
#include <QString>
|
||||
#include <QTextStream>
|
||||
|
||||
struct LLInst;
|
||||
struct Function;
|
||||
typedef std::shared_ptr<Function> PtrFunction;
|
||||
|
||||
struct Disassembler
|
||||
{
|
||||
protected:
|
||||
@@ -30,8 +34,8 @@ public:
|
||||
g_lab=0;
|
||||
}
|
||||
public:
|
||||
void disassem(Function *ppProc);
|
||||
void disassem(Function *ppProc, int i);
|
||||
void disassem(PtrFunction ppProc);
|
||||
void disassem(PtrFunction ppProc, int i);
|
||||
void dis1Line(LLInst &inst, int loc_ip, int pass);
|
||||
};
|
||||
/* Definitions for extended keys (first key is zero) */
|
||||
|
||||
@@ -13,6 +13,7 @@
|
||||
#include <QtCore/QString>
|
||||
#include <list>
|
||||
#include <unordered_set>
|
||||
#include <unordered_map>
|
||||
#include <string>
|
||||
#include <stdint.h>
|
||||
#include <assert.h>
|
||||
@@ -60,6 +61,8 @@ struct LoaderMetadata {
|
||||
return QString("b%1%2").arg(compiler_version).arg(codeModelChar());
|
||||
case ePascal:
|
||||
return QString("tp%1").arg(compiler_version);
|
||||
default:
|
||||
return "xxx";
|
||||
}
|
||||
case eMicrosoft:
|
||||
assert(compiler_language==eAnsiCorCPP);
|
||||
@@ -67,6 +70,8 @@ struct LoaderMetadata {
|
||||
case eLogitech:
|
||||
assert(compiler_language==eModula2);
|
||||
return QString("l%1%2").arg(compiler_version).arg(codeModelChar());
|
||||
case eUnknownVendor:
|
||||
return "xxx";
|
||||
}
|
||||
return "xxx";
|
||||
}
|
||||
@@ -85,11 +90,6 @@ class Project : public QObject
|
||||
{
|
||||
Q_OBJECT
|
||||
public:
|
||||
typedef llvm::iplist<Function> FunctionListType;
|
||||
typedef FunctionListType lFunction;
|
||||
typedef FunctionListType::iterator ilFunction;
|
||||
|
||||
public:
|
||||
DosLoader * m_selected_loader;
|
||||
bool m_metadata_available=false;
|
||||
LoaderMetadata m_loader_data;
|
||||
@@ -101,6 +101,8 @@ public:
|
||||
|
||||
PROG prog; /* Loaded program image parameters */
|
||||
CommandStream m_project_command_stream;
|
||||
std::unordered_map<PtrFunction,CommandStream> m_function_streams;
|
||||
|
||||
bool m_error_state;
|
||||
struct PatternLocator *m_pattern_locator;
|
||||
public:
|
||||
@@ -121,9 +123,10 @@ public:
|
||||
const QString & project_name() const {return m_project_name;}
|
||||
const QString & binary_path() const {return m_fname;}
|
||||
QString output_name(const char *ext);
|
||||
ilFunction funcIter(Function *to_find);
|
||||
ilFunction findByEntry(uint32_t entry);
|
||||
ilFunction createFunction(FunctionType *f, const QString & name, SegOffAddr addr);
|
||||
ilFunction funcIter(Function *to_find);
|
||||
PtrFunction findByEntry(uint32_t entry);
|
||||
PtrFunction findByName(const QString &name);
|
||||
PtrFunction createFunction(FunctionType *f, const QString & name, SegOffAddr addr);
|
||||
bool valid(ilFunction iter);
|
||||
|
||||
int getSymIdxByAdd(uint32_t adr);
|
||||
@@ -142,14 +145,15 @@ public:
|
||||
const FunctionListType &functions() const { return pProcList; }
|
||||
FunctionListType &functions() { return pProcList; }
|
||||
|
||||
bool addCommand(Command *cmd) { return m_project_command_stream.add(cmd); emit commandListChanged(); }
|
||||
bool addCommand(Command *cmd);
|
||||
bool addCommand(PtrFunction f, Command *cmd); // Add function level command
|
||||
void dumpAllErrors();
|
||||
void setLoader(DosLoader *ins);
|
||||
void processCommands(int count=1);
|
||||
public slots:
|
||||
void onCommandStreamFinished(bool state);
|
||||
signals:
|
||||
void newFunctionCreated(Function &);
|
||||
void newFunctionCreated(PtrFunction);
|
||||
void loaderSelected();
|
||||
void commandListChanged();
|
||||
protected:
|
||||
|
||||
@@ -49,6 +49,7 @@ struct STKSYM : public SymbolCommon
|
||||
bool hasMacro=false; /* This type needs a macro */
|
||||
QString macro; /* Macro name */
|
||||
bool invalid=false; /* Boolean: invalid entry in formal arg list*/
|
||||
int arrayMembers=1; // for local variables if >1 marks this stack symbol as an array
|
||||
void setArgName(int i)
|
||||
{
|
||||
char buf[32];
|
||||
|
||||
Reference in New Issue
Block a user